1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: testpgp.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_extensions.hxx"
33 #include <sal/types.h>
34 #include <rtl/memory.h>
36 #include <rtl/wstring>
38 #include <vos/macros.hxx>
40 #ifndef _USR_SMARTSERVICES_HXX_
41 #include <usr/smartservices.hxx>
43 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
44 #include <com/sun/star/io/XInputStream.hpp>
45 #include <com/sun/star/io/XOutputStream.hpp>
46 #include <com/sun/star/pgp/RecipientsEvent.hpp>
47 #include <com/sun/star/pgp/SignatureEvent.hpp>
48 #include <com/sun/star/pgp/XPGPDecoder.hpp>
49 #include <com/sun/star/pgp/XPGPDecoderListener.hpp>
50 #include <com/sun/star/pgp/XPGPEncoder.hpp>
51 #include <com/sun/star/pgp/XPGPPreferences.hpp>
52 #include <com/sun/star/uno/XInterface.hpp>
53 #include <com/sun/star/uno/Any.h>
54 #include <com/sun/star/uno/Reference.h>
55 #include <com/sun/star/uno/Sequence.hxx>
56 #include <cppuhelper/weak.hxx>
65 using namespace com::sun::star::lang
;
66 using namespace com::sun::star::io
;
67 using namespace com::sun::star::pgp
;
68 using namespace com::sun::star::uno
;
70 /*========================================================================
72 * DataSource_Impl interface.
74 *======================================================================*/
75 class DataSource_Impl
:
79 Sequence
<sal_Int8
> m_buffer
;
84 DataSource_Impl (int fd
= 0);
85 virtual ~DataSource_Impl (void);
87 void setBuffer (const Sequence
<sal_Int8
> &rBuffer
);
91 virtual sal_Bool SAL_CALL
queryInterface (
92 const Uik
&rUik
, Any
&rIfc
) throw(RuntimeException
);
94 virtual void SAL_CALL
acquire (void) throw(RuntimeException
);
96 virtual void SAL_CALL
release (void) throw(RuntimeException
);
100 virtual sal_Int32 SAL_CALL
readBytes (
101 Sequence
<sal_Int8
> &rData
, sal_Int32 nBytesToRead
)
102 throw (NotConnectedException
,
103 BufferSizeExceededException
,
106 virtual sal_Int32 SAL_CALL
readSomeBytes (
107 Sequence
<sal_Int8
> &rData
, sal_Int32 nMaxBytesToRead
)
108 throw (NotConnectedException
,
109 BufferSizeExceededException
,
112 virtual void SAL_CALL
skipBytes (sal_Int32 nBytesToSkip
)
113 throw (NotConnectedException
,
114 BufferSizeExceededException
,
117 virtual sal_Int32 SAL_CALL
available (void)
118 throw (NotConnectedException
, IOException
);
120 virtual void SAL_CALL
closeInput (void)
121 throw (NotConnectedException
, IOException
);
124 /*========================================================================
126 * DataSink_Impl interface.
128 *======================================================================*/
129 class DataSink_Impl
:
133 Sequence
<sal_Int8
> m_buffer
;
136 DataSink_Impl (void);
137 virtual ~DataSink_Impl (void);
139 const Sequence
<sal_Int8
>& getBuffer (void) const { return m_buffer
; }
143 virtual sal_Bool SAL_CALL
queryInterface (
144 const Uik
&rUik
, Any
&rIfc
) throw(RuntimeException
);
146 virtual void SAL_CALL
acquire (void) throw(RuntimeException
);
147 virtual void SAL_CALL
release (void) throw(RuntimeException
);
151 virtual void SAL_CALL
writeBytes (
152 const Sequence
<sal_Int8
> &rBuffer
)
153 throw (NotConnectedException
,
154 BufferSizeExceededException
,
157 virtual void SAL_CALL
flush (void)
158 throw (NotConnectedException
,
159 BufferSizeExceededException
,
162 virtual void SAL_CALL
closeOutput (void)
163 throw (NotConnectedException
,
164 BufferSizeExceededException
,
168 /*========================================================================
170 * DecoderListener_Impl interface.
172 *======================================================================*/
173 class DecoderListener_Impl
:
175 public XPGPDecoderListener
178 DecoderListener_Impl (void);
179 virtual ~DecoderListener_Impl (void);
183 virtual sal_Bool SAL_CALL
queryInterface (
184 const Uik
&rUik
, Any
&rIfc
) throw(RuntimeException
);
186 virtual void SAL_CALL
acquire (void) throw(RuntimeException
);
188 virtual void SAL_CALL
release (void) throw(RuntimeException
);
192 virtual void SAL_CALL
disposing (const EventObject
&rSource
);
194 /** XPGPDecoderListener.
196 virtual void SAL_CALL
decrypted (const RecipientsEvent
&rEvent
);
197 virtual void SAL_CALL
verified (const SignatureEvent
&rEvent
);
200 /*========================================================================
202 * DataSource_Impl implementation.
204 *======================================================================*/
208 DataSource_Impl::DataSource_Impl (int fd
)
209 : m_fd (fd
), m_position (0)
216 DataSource_Impl::~DataSource_Impl (void)
221 * DataSource_Impl: setBuffer.
223 void DataSource_Impl::setBuffer (const Sequence
<sal_Int8
> &rBuffer
)
226 if (!m_buffer
.getLength())
228 // Fill buffer from file descriptor.
230 rtl_zeroMemory (buffer
, sizeof(buffer
));
232 int k
= read (m_fd
, buffer
, sizeof(buffer
));
235 sal_Int32 n
= m_buffer
.getLength();
236 m_buffer
.realloc (n
+ k
);
238 rtl_copyMemory (m_buffer
.getArray() + n
, buffer
, k
);
241 rtl_zeroMemory (buffer
, k
);
242 k
= read (m_fd
, buffer
, sizeof(buffer
));
249 * XInterface: queryInterface.
251 sal_Bool SAL_CALL
DataSource_Impl::queryInterface (
252 const Uik
&rUik
, Any
&rIfc
) throw(RuntimeException
)
254 if (com::sun::star::uno::queryInterface (
256 SAL_STATIC_CAST (XInputStream
*, this)))
259 return OWeakObject::queryInterface (rUik
, rIfc
);
263 * XInterface: acquire.
265 void SAL_CALL
DataSource_Impl::acquire (void) throw(RuntimeException
)
267 OWeakObject::acquire();
271 * XInterface: release.
273 void SAL_CALL
DataSource_Impl::release (void) throw(RuntimeException
)
275 OWeakObject::release();
279 * XInputStream: readBytes.
281 sal_Int32 SAL_CALL
DataSource_Impl::readBytes (
282 Sequence
<sal_Int8
> &rData
, sal_Int32 nBytesToRead
)
283 throw (NotConnectedException
, BufferSizeExceededException
, IOException
)
285 if (nBytesToRead
< 0)
288 sal_Int32 k
= m_buffer
.getLength() - m_position
;
289 k
= VOS_BOUND(k
, 0, nBytesToRead
);
294 rData
.getArray(), m_buffer
.getConstArray() + m_position
, k
);
301 * XInputStream: readSomeBytes.
303 sal_Int32 SAL_CALL
DataSource_Impl::readSomeBytes (
304 Sequence
<sal_Int8
> &rData
, sal_Int32 nMaxBytesToRead
)
305 throw (NotConnectedException
, BufferSizeExceededException
, IOException
)
307 return readBytes (rData
, nMaxBytesToRead
);
311 * XInputStream: skipBytes.
313 void SAL_CALL
DataSource_Impl::skipBytes (sal_Int32 nBytesToSkip
)
314 throw (NotConnectedException
, BufferSizeExceededException
, IOException
)
316 if (nBytesToSkip
< 0)
319 m_position
+= nBytesToSkip
;
323 * XInputStream: available.
325 sal_Int32 SAL_CALL
DataSource_Impl::available (void)
326 throw (NotConnectedException
, IOException
)
328 sal_Int32 k
= m_buffer
.getLength() - m_position
;
329 return ((k
> 0) ? k
: 0);
333 * XInputStream: closeInput.
335 void SAL_CALL
DataSource_Impl::closeInput (void)
336 throw (NotConnectedException
, IOException
)
340 /*========================================================================
342 * DataSink_Impl implementation.
344 *======================================================================*/
348 DataSink_Impl::DataSink_Impl (void)
355 DataSink_Impl::~DataSink_Impl (void)
360 * XInterface: queryInterface.
362 sal_Bool SAL_CALL
DataSink_Impl::queryInterface (
363 const Uik
&rUik
, Any
&rIfc
) throw(RuntimeException
)
365 if (com::sun::star::uno::queryInterface (
367 SAL_STATIC_CAST (XOutputStream
*, this)))
370 return OWeakObject::queryInterface (rUik
, rIfc
);
374 * XInterface: acquire.
376 void SAL_CALL
DataSink_Impl::acquire (void) throw(RuntimeException
)
378 OWeakObject::acquire();
382 * XInterface: release.
384 void SAL_CALL
DataSink_Impl::release (void) throw(RuntimeException
)
386 OWeakObject::release();
390 * XOutputStream: writeBytes.
392 void SAL_CALL
DataSink_Impl::writeBytes (const Sequence
<sal_Int8
> &rBuffer
)
393 throw (NotConnectedException
, BufferSizeExceededException
, IOException
)
395 if (rBuffer
.getLength())
397 sal_Int32 n
= m_buffer
.getLength();
398 m_buffer
.realloc (n
+ rBuffer
.getLength());
401 m_buffer
.getArray() + n
,
402 rBuffer
.getConstArray(),
403 rBuffer
.getLength());
408 * XOutputStream: flush.
410 void SAL_CALL
DataSink_Impl::flush (void)
411 throw (NotConnectedException
, BufferSizeExceededException
, IOException
)
413 if (m_buffer
.getLength())
415 // Write data to stdout.
416 const sal_Int8
*pData
= m_buffer
.getConstArray();
417 sal_Int32 nData
= m_buffer
.getLength();
419 int prev
= ::setmode (1, O_BINARY
);
422 int k
= ::write (1, pData
, nData
);
424 ::write (1, "\n", 1);
431 * XOutputStream: closeOutput.
433 void SAL_CALL
DataSink_Impl::closeOutput (void)
434 throw (NotConnectedException
, BufferSizeExceededException
, IOException
)
439 /*========================================================================
441 * DecoderListener_Impl implementation.
443 *======================================================================*/
445 * DecoderListener_Impl.
447 DecoderListener_Impl::DecoderListener_Impl (void)
452 * ~DecoderListener_Impl.
454 DecoderListener_Impl::~DecoderListener_Impl (void)
459 * XInterface: queryInterface.
461 sal_Bool SAL_CALL
DecoderListener_Impl::queryInterface (
462 const Uik
&rUik
, Any
&rIfc
) throw(RuntimeException
)
464 if (com::sun::star::uno::queryInterface (
466 SAL_STATIC_CAST (XEventListener
*, this),
467 SAL_STATIC_CAST (XPGPDecoderListener
*, this)))
470 return OWeakObject::queryInterface (rUik
, rIfc
);
474 * XInterface: acquire.
476 void SAL_CALL
DecoderListener_Impl::acquire (void) throw(RuntimeException
)
478 OWeakObject::acquire();
482 * XInterface: release.
484 void SAL_CALL
DecoderListener_Impl::release (void) throw(RuntimeException
)
486 OWeakObject::release();
490 * XEventListener: disposing.
492 void SAL_CALL
DecoderListener_Impl::disposing (const EventObject
&rSource
)
497 * XPGPDecoderListener: decrypted.
499 void SAL_CALL
DecoderListener_Impl::decrypted (const RecipientsEvent
&rEvent
)
504 * XPGPDecoderListener: verified.
506 void SAL_CALL
DecoderListener_Impl::verified (const SignatureEvent
&rEvent
)
510 /*========================================================================
514 *======================================================================*/
515 inline rtl::OWString
S2U (const sal_Char
*ascii
)
517 return rtl::OWString::createFromAscii (ascii
);
523 * queryModuleActivator.
525 BOOL
queryModuleActivator (
526 const XServiceManagerRef
&rxManager
,
527 XServiceActivatorRef
&rxActivator
)
529 XServiceProviderRef xProv
;
530 XInterfaceRef xProvInst
;
532 xProv
= rxManager
->queryServiceProvider (
533 L
"stardiv.uno.ServiceActivator.module");
536 printf ("Error: no ServiceActivator service.\n");
540 xProvInst
= xProv
->createInstance();
543 printf ("Error: no ServiceActivator instance.\n");
547 return xProvInst
->queryInterface (
548 XServiceActivator::getSmartUik(), rxActivator
);
555 const XServiceActivatorRef
&rxActivator
,
558 String
aModule ("module://");
561 NAMESPACE_VOS(ORealDynamicLoader
)::computeModuleName (
562 prefix
, pBuffer
, sizeof(pBuffer
));
565 return rxActivator
->install (
566 StringToUString (aModule
, CHARSET_SYSTEM
));
573 const XServiceActivatorRef
&rxActivator
,
576 String
aModule ("module://");
579 NAMESPACE_VOS(ORealDynamicLoader
)::computeModuleName (
580 prefix
, pBuffer
, sizeof(pBuffer
));
583 return rxActivator
->deinstall (
584 StringToUString (aModule
, CHARSET_SYSTEM
));
592 int SAL_CALL
main (int argc
, char **argv
)
596 OPTION_INSTALL
= 0x01,
597 OPTION_UNINSTALL
= 0x02,
599 OPTION_DECRYPT
= 0x04,
600 OPTION_ENCRYPT
= 0x08,
608 unsigned long nOptions
= 0;
610 for (int i
= 1; i
< argc
; i
++)
612 const char *opt
= argv
[i
];
618 nOptions
|= OPTION_INSTALL
;
622 nOptions
|= OPTION_UNINSTALL
;
626 nOptions
|= OPTION_DECRYPT
;
630 nOptions
|= OPTION_ENCRYPT
;
634 nOptions
|= OPTION_SIGN
;
638 nOptions
|= OPTION_FILE
;
643 nOptions
|= OPTION_HELP
;
649 if (nOptions
& OPTION_FILE
)
651 if ((fd
= open (argv
[i
], O_RDONLY
| O_BINARY
)) < 0)
653 printf ("Error: can't open file: %s\n", argv
[i
]);
660 if ((nOptions
== 0) || (nOptions
& OPTION_HELP
))
662 printf ("Options:\n");
663 printf ("-i\tinstall module\n");
664 printf ("-u\tuninstall module\n");
665 printf ("-d\tdecrypt and verify\n");
666 printf ("-e\tencrypt test pattern\n");
667 printf ("-s\tsign test pattern\n");
668 printf ("-h\thelp\n");
672 Reference
<XMultiServiceFactory
> xManager (
673 usr::createDefaultSmartRegistryServiceFactory());
676 printf ("Error: no ProcessServiceManager.\n");
679 usr::setProcessServiceFactory (xManager
);
681 if (nOptions
& OPTION_INSTALL
)
684 XServiceActivatorRef xActivator
;
685 if (queryModuleActivator (xManager
, xActivator
))
687 if (install (xActivator
, "pgp"))
688 printf ("Module PGP installed.\n");
690 printf ("Error: module PGP not installed.\n");
692 nOptions
&= ~OPTION_INSTALL
;
696 if (nOptions
& (OPTION_DECRYPT
| OPTION_ENCRYPT
| OPTION_SIGN
))
698 Reference
<XMultiServiceFactory
> xProv (
699 xManager
->createInstance (
700 S2U("com.sun.star.pgp.PGPFactory")),
704 printf ("Error: no PGPFactory service.\n");
708 Reference
<XInterface
> xProvInst (
709 xProv
->createInstance (
710 S2U("com.sun.star.pgp.SimplePGPMailer")));
713 printf ("Error: no SimplePGPMailer service.\n");
717 Reference
<XPGPPreferences
> xPrefs (xProvInst
, UNO_QUERY
);
720 unsigned long nDefaults
= 0;
722 if (xPrefs
->getEncryptByDefault())
723 nDefaults
|= OPTION_ENCRYPT
;
724 if (xPrefs
->getSignByDefault())
725 nDefaults
|= OPTION_SIGN
;
726 if (xPrefs
->getAutoDecrypt())
727 nDefaults
|= OPTION_DECRYPT
;
734 static const sal_Int8 pData
[] = "" /* "Hello PGP World." */;
735 Sequence
<sal_Int8
> buffer (pData
, sizeof (pData
) - 1);
737 if (nOptions
& (OPTION_ENCRYPT
| OPTION_SIGN
))
739 Reference
<XPGPEncoder
> xEncoder (xProvInst
, UNO_QUERY
);
742 printf ("Error: no PGPEncoder interface.\n");
746 DataSource_Impl
*source
= new DataSource_Impl (fd
);
747 source
->setBuffer (buffer
);
749 DataSink_Impl
*sink
= new DataSink_Impl
;
751 Reference
<XInputStream
> xPlainText (source
);
752 Reference
<XOutputStream
> xCipherText (sink
);
754 if (nOptions
& OPTION_ENCRYPT
)
756 rtl::OWString aRecipients
[] =
758 S2U("er@stardiv.de"),
759 // L"mhu@stardivision.de",
763 sal_Int32 nRecipients
=
764 sizeof(aRecipients
) / sizeof(aRecipients
[0]);
766 if (nOptions
& OPTION_SIGN
)
768 xEncoder
->encryptAndSign (
769 Sequence
<rtl::OWString
>(aRecipients
, nRecipients
),
772 nOptions
&= ~OPTION_SIGN
;
777 Sequence
<rtl::OWString
>(aRecipients
, nRecipients
),
781 nOptions
&= ~OPTION_ENCRYPT
;
784 if (nOptions
& OPTION_SIGN
)
786 sal_Bool bDataIsAscii
= (fd
== 0); // stdin.
792 nOptions
&= ~OPTION_SIGN
;
795 buffer
= sink
->getBuffer();
798 if (nOptions
& OPTION_DECRYPT
)
800 Reference
<XPGPDecoder
> xDecoder (xProvInst
, UNO_QUERY
);
803 printf ("Error: no PGPDecoder interface.\n");
807 DataSource_Impl
*source
= new DataSource_Impl
;
808 source
->setBuffer (buffer
);
810 DataSink_Impl
*sink
= new DataSink_Impl
;
812 Reference
<XInputStream
> xCipherText (source
);
813 Reference
<XOutputStream
> xPlainText (sink
);
815 Reference
<XPGPDecoderListener
> xListener (
816 new DecoderListener_Impl
);
817 xDecoder
->addDecoderListener (xListener
);
819 xDecoder
->decryptAndVerify (
822 nOptions
&= ~OPTION_DECRYPT
;
824 xDecoder
->removeDecoderListener (xListener
);
826 buffer
= sink
->getBuffer();
830 if (nOptions
& OPTION_UNINSTALL
)
833 XServiceActivatorRef xActivator
;
834 if (queryModuleActivator (xManager
, xActivator
))
836 if (uninstall (xActivator
, "pgp"))
837 printf ("Module PGP uninstalled.\n");
839 printf ("Error: module PGP not uninstalled.\n");
841 nOptions
&= ~OPTION_UNINSTALL
;