xref: /AOO41X/main/extensions/workben/testpgp.cxx (revision 2a97ec55f1442d65917e8c8b82a55ab76c9ff676)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_extensions.hxx"
26 #include <sal/types.h>
27 #include <rtl/memory.h>
28 #ifndef _RTL_WSTRING_
29 #include <rtl/wstring>
30 #endif
31 #include <vos/macros.hxx>
32 
33 #ifndef _USR_SMARTSERVICES_HXX_
34 #include <usr/smartservices.hxx>
35 #endif
36 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
37 #include <com/sun/star/io/XInputStream.hpp>
38 #include <com/sun/star/io/XOutputStream.hpp>
39 #include <com/sun/star/pgp/RecipientsEvent.hpp>
40 #include <com/sun/star/pgp/SignatureEvent.hpp>
41 #include <com/sun/star/pgp/XPGPDecoder.hpp>
42 #include <com/sun/star/pgp/XPGPDecoderListener.hpp>
43 #include <com/sun/star/pgp/XPGPEncoder.hpp>
44 #include <com/sun/star/pgp/XPGPPreferences.hpp>
45 #include <com/sun/star/uno/XInterface.hpp>
46 #include <com/sun/star/uno/Any.h>
47 #include <com/sun/star/uno/Reference.h>
48 #include <com/sun/star/uno/Sequence.hxx>
49 #include <cppuhelper/weak.hxx>
50 
51 #include <stdio.h>
52 #include <stdlib.h>
53 #include <string.h>
54 
55 #include <fcntl.h>
56 #include <io.h>
57 
58 using namespace com::sun::star::lang;
59 using namespace com::sun::star::io;
60 using namespace com::sun::star::pgp;
61 using namespace com::sun::star::uno;
62 
63 /*========================================================================
64  *
65  * DataSource_Impl interface.
66  *
67  *======================================================================*/
68 class DataSource_Impl :
69     public OWeakObject,
70     public XInputStream
71 {
72     Sequence<sal_Int8> m_buffer;
73     sal_Int32          m_position;
74     int                m_fd;
75 
76 public:
77     DataSource_Impl (int fd = 0);
78     virtual ~DataSource_Impl (void);
79 
80     void setBuffer (const Sequence<sal_Int8> &rBuffer);
81 
82     /** XInterface.
83      */
84     virtual sal_Bool SAL_CALL queryInterface (
85         const Uik &rUik, Any &rIfc) throw(RuntimeException);
86 
87     virtual void SAL_CALL acquire (void) throw(RuntimeException);
88 
89     virtual void SAL_CALL release (void) throw(RuntimeException);
90 
91     /** XInputStream.
92      */
93     virtual sal_Int32 SAL_CALL readBytes (
94         Sequence<sal_Int8> &rData, sal_Int32 nBytesToRead)
95         throw (NotConnectedException,
96                BufferSizeExceededException,
97                IOException);
98 
99     virtual sal_Int32 SAL_CALL readSomeBytes (
100         Sequence<sal_Int8> &rData, sal_Int32 nMaxBytesToRead)
101         throw (NotConnectedException,
102                BufferSizeExceededException,
103                IOException);
104 
105     virtual void SAL_CALL skipBytes (sal_Int32 nBytesToSkip)
106         throw (NotConnectedException,
107                BufferSizeExceededException,
108                IOException);
109 
110     virtual sal_Int32 SAL_CALL available (void)
111         throw (NotConnectedException, IOException);
112 
113     virtual void SAL_CALL closeInput (void)
114         throw (NotConnectedException, IOException);
115 };
116 
117 /*========================================================================
118  *
119  * DataSink_Impl interface.
120  *
121  *======================================================================*/
122 class DataSink_Impl :
123     public OWeakObject,
124     public XOutputStream
125 {
126     Sequence<sal_Int8> m_buffer;
127 
128 public:
129     DataSink_Impl (void);
130     virtual ~DataSink_Impl (void);
131 
getBuffer(void) const132     const Sequence<sal_Int8>& getBuffer (void) const { return m_buffer; }
133 
134     /** XInterface.
135      */
136     virtual sal_Bool SAL_CALL queryInterface (
137         const Uik &rUik, Any &rIfc) throw(RuntimeException);
138 
139     virtual void SAL_CALL acquire (void) throw(RuntimeException);
140     virtual void SAL_CALL release (void) throw(RuntimeException);
141 
142     /** XOutputStream.
143      */
144     virtual void SAL_CALL writeBytes (
145         const Sequence<sal_Int8> &rBuffer)
146         throw (NotConnectedException,
147                BufferSizeExceededException,
148                IOException);
149 
150     virtual void SAL_CALL flush (void)
151         throw (NotConnectedException,
152                BufferSizeExceededException,
153                IOException);
154 
155     virtual void SAL_CALL closeOutput (void)
156         throw (NotConnectedException,
157                BufferSizeExceededException,
158                IOException);
159 };
160 
161 /*========================================================================
162  *
163  * DecoderListener_Impl interface.
164  *
165  *======================================================================*/
166 class DecoderListener_Impl :
167     public OWeakObject,
168     public XPGPDecoderListener
169 {
170 public:
171     DecoderListener_Impl (void);
172     virtual ~DecoderListener_Impl (void);
173 
174     /** XInterface.
175      */
176     virtual sal_Bool SAL_CALL queryInterface (
177         const Uik &rUik, Any &rIfc) throw(RuntimeException);
178 
179     virtual void SAL_CALL acquire (void) throw(RuntimeException);
180 
181     virtual void SAL_CALL release (void) throw(RuntimeException);
182 
183     /** XEventListener.
184      */
185     virtual void SAL_CALL disposing (const EventObject &rSource);
186 
187     /** XPGPDecoderListener.
188      */
189     virtual void SAL_CALL decrypted (const RecipientsEvent &rEvent);
190     virtual void SAL_CALL verified  (const SignatureEvent &rEvent);
191 };
192 
193 /*========================================================================
194  *
195  * DataSource_Impl implementation.
196  *
197  *======================================================================*/
198 /*
199  * DataSource_Impl.
200  */
DataSource_Impl(int fd)201 DataSource_Impl::DataSource_Impl (int fd)
202     : m_fd (fd), m_position (0)
203 {
204 }
205 
206 /*
207  * ~DataSource_Impl.
208  */
~DataSource_Impl(void)209 DataSource_Impl::~DataSource_Impl (void)
210 {
211 }
212 
213 /*
214  * DataSource_Impl: setBuffer.
215  */
setBuffer(const Sequence<sal_Int8> & rBuffer)216 void DataSource_Impl::setBuffer (const Sequence<sal_Int8> &rBuffer)
217 {
218     m_buffer = rBuffer;
219     if (!m_buffer.getLength())
220     {
221         // Fill buffer from file descriptor.
222         char buffer[1024];
223         rtl_zeroMemory (buffer, sizeof(buffer));
224 
225         int k = read (m_fd, buffer, sizeof(buffer));
226         while (k > 0)
227         {
228             sal_Int32 n = m_buffer.getLength();
229             m_buffer.realloc (n + k);
230 
231             rtl_copyMemory (m_buffer.getArray() + n, buffer, k);
232             n += k;
233 
234             rtl_zeroMemory (buffer, k);
235             k = read (m_fd, buffer, sizeof(buffer));
236         }
237     }
238     m_position = 0;
239 }
240 
241 /*
242  * XInterface: queryInterface.
243  */
queryInterface(const Uik & rUik,Any & rIfc)244 sal_Bool SAL_CALL DataSource_Impl::queryInterface (
245     const Uik &rUik, Any &rIfc) throw(RuntimeException)
246 {
247     if (com::sun::star::uno::queryInterface (
248         rUik, rIfc,
249         SAL_STATIC_CAST (XInputStream*, this)))
250         return sal_True;
251     else
252         return OWeakObject::queryInterface (rUik, rIfc);
253 }
254 
255 /*
256  * XInterface: acquire.
257  */
acquire(void)258 void SAL_CALL DataSource_Impl::acquire (void) throw(RuntimeException)
259 {
260     OWeakObject::acquire();
261 }
262 
263 /*
264  * XInterface: release.
265  */
release(void)266 void SAL_CALL DataSource_Impl::release (void) throw(RuntimeException)
267 {
268     OWeakObject::release();
269 }
270 
271 /*
272  * XInputStream: readBytes.
273  */
readBytes(Sequence<sal_Int8> & rData,sal_Int32 nBytesToRead)274 sal_Int32 SAL_CALL DataSource_Impl::readBytes (
275     Sequence<sal_Int8> &rData, sal_Int32 nBytesToRead)
276     throw (NotConnectedException, BufferSizeExceededException, IOException)
277 {
278     if (nBytesToRead < 0)
279         throw IOException();
280 
281     sal_Int32 k = m_buffer.getLength() - m_position;
282     k = VOS_BOUND(k, 0, nBytesToRead);
283     if (k > 0)
284     {
285         rData.realloc(k);
286         rtl_copyMemory (
287             rData.getArray(), m_buffer.getConstArray() + m_position, k);
288         m_position += k;
289     }
290     return k;
291 }
292 
293 /*
294  * XInputStream: readSomeBytes.
295  */
readSomeBytes(Sequence<sal_Int8> & rData,sal_Int32 nMaxBytesToRead)296 sal_Int32 SAL_CALL DataSource_Impl::readSomeBytes (
297     Sequence<sal_Int8> &rData, sal_Int32 nMaxBytesToRead)
298     throw (NotConnectedException, BufferSizeExceededException, IOException)
299 {
300     return readBytes (rData, nMaxBytesToRead);
301 }
302 
303 /*
304  * XInputStream: skipBytes.
305  */
skipBytes(sal_Int32 nBytesToSkip)306 void SAL_CALL DataSource_Impl::skipBytes (sal_Int32 nBytesToSkip)
307     throw (NotConnectedException, BufferSizeExceededException, IOException)
308 {
309     if (nBytesToSkip < 0)
310         throw IOException();
311 
312     m_position += nBytesToSkip;
313 }
314 
315 /*
316  * XInputStream: available.
317  */
available(void)318 sal_Int32 SAL_CALL DataSource_Impl::available (void)
319     throw (NotConnectedException, IOException)
320 {
321     sal_Int32 k = m_buffer.getLength() - m_position;
322     return ((k > 0) ? k : 0);
323 }
324 
325 /*
326  * XInputStream: closeInput.
327  */
closeInput(void)328 void SAL_CALL DataSource_Impl::closeInput (void)
329     throw (NotConnectedException, IOException)
330 {
331 }
332 
333 /*========================================================================
334  *
335  * DataSink_Impl implementation.
336  *
337  *======================================================================*/
338 /*
339  * DataSink_Impl.
340  */
DataSink_Impl(void)341 DataSink_Impl::DataSink_Impl (void)
342 {
343 }
344 
345 /*
346  * ~DataSink_Impl.
347  */
~DataSink_Impl(void)348 DataSink_Impl::~DataSink_Impl (void)
349 {
350 }
351 
352 /*
353  * XInterface: queryInterface.
354  */
queryInterface(const Uik & rUik,Any & rIfc)355 sal_Bool SAL_CALL DataSink_Impl::queryInterface (
356     const Uik &rUik, Any &rIfc) throw(RuntimeException)
357 {
358     if (com::sun::star::uno::queryInterface (
359         rUik, rIfc,
360         SAL_STATIC_CAST (XOutputStream*, this)))
361         return sal_True;
362     else
363         return OWeakObject::queryInterface (rUik, rIfc);
364 }
365 
366 /*
367  * XInterface: acquire.
368  */
acquire(void)369 void SAL_CALL DataSink_Impl::acquire (void) throw(RuntimeException)
370 {
371     OWeakObject::acquire();
372 }
373 
374 /*
375  * XInterface: release.
376  */
release(void)377 void SAL_CALL DataSink_Impl::release (void) throw(RuntimeException)
378 {
379     OWeakObject::release();
380 }
381 
382 /*
383  * XOutputStream: writeBytes.
384  */
writeBytes(const Sequence<sal_Int8> & rBuffer)385 void SAL_CALL DataSink_Impl::writeBytes (const Sequence<sal_Int8> &rBuffer)
386     throw (NotConnectedException, BufferSizeExceededException, IOException)
387 {
388     if (rBuffer.getLength())
389     {
390         sal_Int32 n = m_buffer.getLength();
391         m_buffer.realloc (n + rBuffer.getLength());
392 
393         rtl_copyMemory (
394             m_buffer.getArray() + n,
395             rBuffer.getConstArray(),
396             rBuffer.getLength());
397     }
398 }
399 
400 /*
401  * XOutputStream: flush.
402  */
flush(void)403 void SAL_CALL DataSink_Impl::flush (void)
404     throw (NotConnectedException, BufferSizeExceededException, IOException)
405 {
406     if (m_buffer.getLength())
407     {
408         // Write data to stdout.
409         const sal_Int8 *pData = m_buffer.getConstArray();
410         sal_Int32       nData = m_buffer.getLength();
411 
412         int prev = ::setmode (1, O_BINARY);
413         if (!(prev < 0))
414         {
415             int k = ::write (1, pData, nData);
416             if (k > 0)
417                 ::write (1, "\n", 1);
418             ::setmode (1, prev);
419         }
420     }
421 }
422 
423 /*
424  * XOutputStream: closeOutput.
425  */
closeOutput(void)426 void SAL_CALL DataSink_Impl::closeOutput (void)
427     throw (NotConnectedException, BufferSizeExceededException, IOException)
428 {
429     flush();
430 }
431 
432 /*========================================================================
433  *
434  * DecoderListener_Impl implementation.
435  *
436  *======================================================================*/
437 /*
438  * DecoderListener_Impl.
439  */
DecoderListener_Impl(void)440 DecoderListener_Impl::DecoderListener_Impl (void)
441 {
442 }
443 
444 /*
445  * ~DecoderListener_Impl.
446  */
~DecoderListener_Impl(void)447 DecoderListener_Impl::~DecoderListener_Impl (void)
448 {
449 }
450 
451 /*
452  * XInterface: queryInterface.
453  */
queryInterface(const Uik & rUik,Any & rIfc)454 sal_Bool SAL_CALL DecoderListener_Impl::queryInterface (
455     const Uik &rUik, Any &rIfc) throw(RuntimeException)
456 {
457     if (com::sun::star::uno::queryInterface (
458         rUik, rIfc,
459         SAL_STATIC_CAST (XEventListener*, this),
460         SAL_STATIC_CAST (XPGPDecoderListener*, this)))
461         return sal_True;
462     else
463         return OWeakObject::queryInterface (rUik, rIfc);
464 }
465 
466 /*
467  * XInterface: acquire.
468  */
acquire(void)469 void SAL_CALL DecoderListener_Impl::acquire (void) throw(RuntimeException)
470 {
471     OWeakObject::acquire();
472 }
473 
474 /*
475  * XInterface: release.
476  */
release(void)477 void SAL_CALL DecoderListener_Impl::release (void) throw(RuntimeException)
478 {
479     OWeakObject::release();
480 }
481 
482 /*
483  * XEventListener: disposing.
484  */
disposing(const EventObject & rSource)485 void SAL_CALL DecoderListener_Impl::disposing (const EventObject &rSource)
486 {
487 }
488 
489 /*
490  * XPGPDecoderListener: decrypted.
491  */
decrypted(const RecipientsEvent & rEvent)492 void SAL_CALL DecoderListener_Impl::decrypted (const RecipientsEvent &rEvent)
493 {
494 }
495 
496 /*
497  * XPGPDecoderListener: verified.
498  */
verified(const SignatureEvent & rEvent)499 void SAL_CALL DecoderListener_Impl::verified (const SignatureEvent &rEvent)
500 {
501 }
502 
503 /*========================================================================
504  *
505  * Main.
506  *
507  *======================================================================*/
S2U(const sal_Char * ascii)508 inline rtl::OWString S2U (const sal_Char *ascii)
509 {
510     return rtl::OWString::createFromAscii (ascii);
511 }
512 
513 #if 0  /* OLD */
514 
515 /*
516  * queryModuleActivator.
517  */
518 BOOL queryModuleActivator (
519     const XServiceManagerRef &rxManager,
520     XServiceActivatorRef     &rxActivator)
521 {
522     XServiceProviderRef xProv;
523     XInterfaceRef       xProvInst;
524 
525     xProv = rxManager->queryServiceProvider (
526         L"stardiv.uno.ServiceActivator.module");
527     if (!xProv.is())
528     {
529         printf ("Error: no ServiceActivator service.\n");
530         return FALSE;
531     }
532 
533     xProvInst = xProv->createInstance();
534     if (!xProvInst.is())
535     {
536         printf ("Error: no ServiceActivator instance.\n");
537         return FALSE;
538     }
539 
540     return xProvInst->queryInterface (
541         XServiceActivator::getSmartUik(), rxActivator);
542 }
543 
544 /*
545  * install.
546  */
547 BOOL install (
548     const XServiceActivatorRef &rxActivator,
549     const char                 *prefix)
550 {
551     String aModule ("module://");
552     char   pBuffer[1024];
553 
554     vos::ORealDynamicLoader::computeModuleName (
555         prefix, pBuffer, sizeof(pBuffer));
556     aModule += pBuffer;
557 
558     return rxActivator->install (
559         StringToUString (aModule, CHARSET_SYSTEM));
560 }
561 
562 /*
563  * uninstall.
564  */
565 BOOL uninstall (
566     const XServiceActivatorRef &rxActivator,
567     const char                 *prefix)
568 {
569     String aModule ("module://");
570     char   pBuffer[1024];
571 
572     vos::ORealDynamicLoader::computeModuleName (
573         prefix, pBuffer, sizeof(pBuffer));
574     aModule += pBuffer;
575 
576     return rxActivator->deinstall (
577         StringToUString (aModule, CHARSET_SYSTEM));
578 }
579 
580 #endif /* OLD */
581 
582 /*
583  * main.
584  */
main(int argc,char ** argv)585 int SAL_CALL main (int argc, char **argv)
586 {
587     enum Option
588     {
589         OPTION_INSTALL   = 0x01,
590         OPTION_UNINSTALL = 0x02,
591 
592         OPTION_DECRYPT   = 0x04,
593         OPTION_ENCRYPT   = 0x08,
594         OPTION_SIGN      = 0x10,
595 
596         OPTION_FILE      = 0x20,
597         OPTION_HELP      = 0x40
598     };
599 
600     int fd = 0;
601     unsigned long nOptions = 0;
602 
603     for (int i = 1; i < argc; i++)
604     {
605         const char *opt = argv[i];
606         if (opt[0] == '-')
607         {
608             switch (opt[1])
609             {
610                 case 'i':
611                     nOptions |= OPTION_INSTALL;
612                     break;
613 
614                 case 'u':
615                     nOptions |= OPTION_UNINSTALL;
616                     break;
617 
618                 case 'd':
619                     nOptions |= OPTION_DECRYPT;
620                     break;
621 
622                 case 'e':
623                     nOptions |= OPTION_ENCRYPT;
624                     break;
625 
626                 case 's':
627                     nOptions |= OPTION_SIGN;
628                     break;
629 
630                 case 'f':
631                     nOptions |= OPTION_FILE;
632                     break;
633 
634                 case 'h':
635                 default:
636                     nOptions |= OPTION_HELP;
637                     break;
638             }
639         }
640         else
641         {
642             if (nOptions & OPTION_FILE)
643             {
644                 if ((fd = open (argv[i], O_RDONLY | O_BINARY)) < 0)
645                 {
646                     printf ("Error: can't open file: %s\n", argv[i]);
647                     exit (0);
648                 }
649             }
650         }
651     }
652 
653     if ((nOptions == 0) || (nOptions & OPTION_HELP))
654     {
655         printf ("Options:\n");
656         printf ("-i\tinstall module\n");
657         printf ("-u\tuninstall module\n");
658         printf ("-d\tdecrypt and verify\n");
659         printf ("-e\tencrypt test pattern\n");
660         printf ("-s\tsign test pattern\n");
661         printf ("-h\thelp\n");
662         exit (0);
663     }
664 
665     Reference<XMultiServiceFactory> xManager (
666         usr::createDefaultSmartRegistryServiceFactory());
667     if (!xManager.is())
668     {
669         printf ("Error: no ProcessServiceManager.\n");
670         exit (1);
671     }
672     usr::setProcessServiceFactory (xManager);
673 
674     if (nOptions & OPTION_INSTALL)
675     {
676 #if 0  /* OLD */
677         XServiceActivatorRef xActivator;
678         if (queryModuleActivator (xManager, xActivator))
679         {
680             if (install (xActivator, "pgp"))
681                 printf ("Module PGP installed.\n");
682             else
683                 printf ("Error: module PGP not installed.\n");
684         }
685         nOptions &= ~OPTION_INSTALL;
686 #endif /* OLD */
687     }
688 
689     if (nOptions & (OPTION_DECRYPT | OPTION_ENCRYPT | OPTION_SIGN))
690     {
691         Reference<XMultiServiceFactory> xProv (
692             xManager->createInstance (
693                 S2U("com.sun.star.pgp.PGPFactory")),
694             UNO_QUERY);
695         if (!xProv.is())
696         {
697             printf ("Error: no PGPFactory service.\n");
698             exit (1);
699         }
700 
701         Reference<XInterface> xProvInst (
702             xProv->createInstance (
703                 S2U("com.sun.star.pgp.SimplePGPMailer")));
704         if (!xProvInst.is())
705         {
706             printf ("Error: no SimplePGPMailer service.\n");
707             exit (2);
708         }
709 
710         Reference<XPGPPreferences> xPrefs (xProvInst, UNO_QUERY);
711         if (xPrefs.is())
712         {
713             unsigned long nDefaults = 0;
714 
715             if (xPrefs->getEncryptByDefault())
716                 nDefaults |= OPTION_ENCRYPT;
717             if (xPrefs->getSignByDefault())
718                 nDefaults |= OPTION_SIGN;
719             if (xPrefs->getAutoDecrypt())
720                 nDefaults |= OPTION_DECRYPT;
721 
722             if (nDefaults)
723             {
724             }
725         }
726 
727         static const sal_Int8 pData[] = "" /* "Hello PGP World." */;
728         Sequence<sal_Int8> buffer (pData, sizeof (pData) - 1);
729 
730         if (nOptions & (OPTION_ENCRYPT | OPTION_SIGN))
731         {
732             Reference<XPGPEncoder> xEncoder (xProvInst, UNO_QUERY);
733             if (!xEncoder.is())
734             {
735                 printf ("Error: no PGPEncoder interface.\n");
736                 exit (4);
737             }
738 
739             DataSource_Impl *source = new DataSource_Impl (fd);
740             source->setBuffer (buffer);
741 
742             DataSink_Impl *sink = new DataSink_Impl;
743 
744             Reference<XInputStream>  xPlainText  (source);
745             Reference<XOutputStream> xCipherText (sink);
746 
747             if (nOptions & OPTION_ENCRYPT)
748             {
749                 rtl::OWString aRecipients[] =
750                 {
751                     S2U("er@stardiv.de"),
752                     // L"mhu@stardivision.de",
753                     S2U("mhu@rabbit")
754                 };
755 
756                 sal_Int32 nRecipients =
757                     sizeof(aRecipients) / sizeof(aRecipients[0]);
758 
759                 if (nOptions & OPTION_SIGN)
760                 {
761                     xEncoder->encryptAndSign (
762                         Sequence<rtl::OWString>(aRecipients, nRecipients),
763                         xPlainText,
764                         xCipherText);
765                     nOptions &= ~OPTION_SIGN;
766                 }
767                 else
768                 {
769                     xEncoder->encrypt (
770                         Sequence<rtl::OWString>(aRecipients, nRecipients),
771                         xPlainText,
772                         xCipherText);
773                 }
774                 nOptions &= ~OPTION_ENCRYPT;
775             }
776 
777             if (nOptions & OPTION_SIGN)
778             {
779                 sal_Bool bDataIsAscii = (fd == 0); // stdin.
780 
781                 xEncoder->sign (
782                     bDataIsAscii,
783                     xPlainText,
784                     xCipherText);
785                 nOptions &= ~OPTION_SIGN;
786             }
787 
788             buffer = sink->getBuffer();
789         }
790 
791         if (nOptions & OPTION_DECRYPT)
792         {
793             Reference<XPGPDecoder> xDecoder (xProvInst, UNO_QUERY);
794             if (!xDecoder.is())
795             {
796                 printf ("Error: no PGPDecoder interface.\n");
797                 exit (5);
798             }
799 
800             DataSource_Impl *source = new DataSource_Impl;
801             source->setBuffer (buffer);
802 
803             DataSink_Impl *sink = new DataSink_Impl;
804 
805             Reference<XInputStream>  xCipherText (source);
806             Reference<XOutputStream> xPlainText  (sink);
807 
808             Reference<XPGPDecoderListener> xListener (
809                 new DecoderListener_Impl);
810             xDecoder->addDecoderListener (xListener);
811 
812             xDecoder->decryptAndVerify (
813                 xCipherText,
814                 xPlainText);
815             nOptions &= ~OPTION_DECRYPT;
816 
817             xDecoder->removeDecoderListener (xListener);
818 
819             buffer = sink->getBuffer();
820         }
821     }
822 
823     if (nOptions & OPTION_UNINSTALL)
824     {
825 #if 0  /* OLD */
826         XServiceActivatorRef xActivator;
827         if (queryModuleActivator (xManager, xActivator))
828         {
829             if (uninstall (xActivator, "pgp"))
830                 printf ("Module PGP uninstalled.\n");
831             else
832                 printf ("Error: module PGP not uninstalled.\n");
833         }
834         nOptions &= ~OPTION_UNINSTALL;
835 #endif /* OLD */
836     }
837 
838     return 0;
839 }
840 
841