28c4cca16a40a5f608b9bd0aacd1c0c851c213de
[gnupg.git] / sm / gpgsm.c
1 /* gpgsm.c - GnuPG for S/MIME 
2  *      Copyright (C) 2001, 2002 Free Software Foundation, Inc.
3  *
4  * This file is part of GnuPG.
5  *
6  * GnuPG is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * GnuPG is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
19  */
20
21 #include <config.h>
22 #include <errno.h>
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26 #include <ctype.h>
27 #include <unistd.h>
28 #include <fcntl.h>
29
30 #include <gcrypt.h>
31 #include "gpgsm.h"
32 #include "../assuan/assuan.h" /* malloc hooks */
33 #include "../kbx/keybox.h" /* malloc hooks */
34 #include "i18n.h"
35 #include "keydb.h"
36 #include "sysutils.h"
37
38 enum cmd_and_opt_values {
39   aNull = 0,
40   oArmor        = 'a',
41   aDetachedSign = 'b',
42   aSym          = 'c',
43   aDecrypt      = 'd',
44   aEncr         = 'e',
45   oInteractive  = 'i',
46   oKOption      = 'k',
47   oDryRun       = 'n',
48   oOutput       = 'o',
49   oQuiet        = 'q',
50   oRecipient    = 'r',
51   aSign         = 's',
52   oTextmodeShort= 't',
53   oUser         = 'u',
54   oVerbose      = 'v',
55   oCompress     = 'z',
56   oNotation     = 'N',
57   oBatch        = 500,
58   aClearsign,
59   aStore,
60   aKeygen,
61   aSignEncr,
62   aSignKey,
63   aLSignKey,
64   aListPackets,
65   aEditKey,
66   aDeleteKey,
67   aImport,
68   aVerify,
69   aVerifyFiles,
70   aListKeys,
71   aListExternalKeys,
72   aListSigs,
73   aListSecretKeys,
74   aSendKeys,
75   aRecvKeys,
76   aExport,
77   aCheckKeys,
78   aServer,                        
79   aLearnCard,
80
81   oOptions,
82   oDebug,
83   oDebugAll,
84   oDebugWait,
85   oDebugNoChainValidation,
86   oLogFile,
87
88   oEnableSpecialFilenames,
89
90   oAgentProgram,
91   oDisplay,
92   oTTYname,
93   oTTYtype,
94   oLCctype,
95   oLCmessages,
96
97   oDirmngrProgram,
98   oFakedSystemTime,
99
100
101   oAssumeArmor,
102   oAssumeBase64,
103   oAssumeBinary,
104
105   oBase64,
106   oNoArmor,
107
108   oDisableCRLChecks,
109   oEnableCRLChecks,
110
111   oIncludeCerts,
112   oPolicyFile,
113   oDisablePolicyChecks,
114   oEnablePolicyChecks,
115   oAutoIssuerKeyRetrieve,
116   
117
118   oTextmode,
119   oFingerprint,
120   oWithFingerprint,
121   oAnswerYes,
122   oAnswerNo,
123   oKeyring,
124   oSecretKeyring,
125   oDefaultKey,
126   oDefRecipient,
127   oDefRecipientSelf,
128   oNoDefRecipient,
129   oStatusFD,
130   oNoComment,
131   oNoVersion,
132   oEmitVersion,
133   oCompletesNeeded,
134   oMarginalsNeeded,
135   oMaxCertDepth,
136   oLoadExtension,
137   oRFC1991,
138   oOpenPGP,
139   oCipherAlgo,
140   oDigestAlgo,
141   oCompressAlgo,
142   oPasswdFD,
143   oCommandFD,
144   oNoVerbose,
145   oTrustDBName,
146   oNoSecmemWarn,
147   oNoDefKeyring,
148   oNoGreeting,
149   oNoTTY,
150   oNoOptions,
151   oNoBatch,
152   oHomedir,
153   oWithColons,
154   oWithKeyData,
155   oSkipVerify,
156   oCompressKeys,
157   oCompressSigs,
158   oAlwaysTrust,
159   oRunAsShmCP,
160   oSetFilename,
161   oSetPolicyURL,
162   oUseEmbeddedFilename,
163   oComment,
164   oDefaultComment,
165   oThrowKeyid,
166   oForceV3Sigs,
167   oForceMDC,
168   oS2KMode,
169   oS2KDigest,
170   oS2KCipher,
171   oCharset,
172   oNotDashEscaped,
173   oEscapeFrom,
174   oLockOnce,
175   oLockMultiple,
176   oLockNever,
177   oKeyServer,
178   oEncryptTo,
179   oNoEncryptTo,
180   oLoggerFD,
181   oUtf8Strings,
182   oNoUtf8Strings,
183   oDisableCipherAlgo,
184   oDisablePubkeyAlgo,
185   oAllowNonSelfsignedUID,
186   oAllowFreeformUID,
187   oNoLiteral,
188   oSetFilesize,
189   oHonorHttpProxy,
190   oFastListMode,
191   oListOnly,
192   oIgnoreTimeConflict,
193   oNoRandomSeedFile,
194   oNoAutoKeyRetrieve,
195   oUseAgent,
196   oMergeOnly,
197   oTryAllSecrets,
198   oTrustedKey,
199   oEmuMDEncodeBug,
200   aDummy
201  };
202
203
204 static ARGPARSE_OPTS opts[] = {
205
206     { 300, NULL, 0, N_("@Commands:\n ") },
207
208     { aSign, "sign",      256, N_("|[file]|make a signature")},
209     { aClearsign, "clearsign", 256, N_("|[file]|make a clear text signature") },
210     { aDetachedSign, "detach-sign", 256, N_("make a detached signature")},
211     { aEncr, "encrypt",   256, N_("encrypt data")},
212     { aSym, "symmetric", 256, N_("encryption only with symmetric cipher")},
213     { aDecrypt, "decrypt",   256, N_("decrypt data (default)")},
214     { aVerify, "verify"   , 256, N_("verify a signature")},
215     { aVerifyFiles, "verify-files" , 256, "@" },
216     { aListKeys, "list-keys", 256, N_("list keys")},
217     { aListExternalKeys, "list-external-keys", 256, N_("list external keys")},
218     { aListSecretKeys, "list-secret-keys", 256, N_("list secret keys")},
219     { aListSigs,   "list-sigs", 256, N_("list certificate chain")}, 
220     { aListSigs,   "check-sigs",256, "@"},
221     { oFingerprint, "fingerprint", 256, N_("list keys and fingerprints")},
222     { aListSecretKeys, "list-secret-keys", 256, N_("list secret keys")},
223     { aKeygen,     "gen-key",  256, N_("generate a new key pair")},
224     { aDeleteKey, "delete-key",256, N_("remove key from the public keyring")},
225     { aSendKeys, "send-keys"     , 256, N_("export keys to a key server") },
226     { aRecvKeys, "recv-keys"     , 256, N_("import keys from a key server") },
227     { aImport, "import",      256     , N_("import certificates")},
228     { aExport, "export",      256     , N_("export certificates")},
229     { aLearnCard, "learn-card", 256 ,N_("register a smartcard")},
230     { aServer, "server",      256, N_("run in server mode")},
231     { oLogFile, "log-file"   ,2, N_("use a log file for the server")},
232     
233
234     { 301, NULL, 0, N_("@\nOptions:\n ") },
235
236     { oArmor, "armor",     0, N_("create ascii armored output")},
237     { oArmor, "armour",    0, "@" },
238     { oBase64, "base64",    0, N_("create base-64 encoded output")},
239     
240     { oAssumeArmor,  "assume-armor", 0, N_("assume input is in PEM format")},
241     { oAssumeBase64, "assume-base64", 0,
242                                       N_("assume input is in base-64 format")},
243     { oAssumeBinary, "assume-binary", 0,
244                                       N_("assume input is in binary format")},
245
246     { oRecipient, "recipient", 2, N_("|NAME|encrypt for NAME")},
247
248
249     { oDisableCRLChecks, "disable-crl-checks", 0, N_("never consult a CRL")},
250     { oEnableCRLChecks, "enable-crl-checks", 0, "@"},
251
252     { oIncludeCerts, "include-certs", 1,
253                                  N_("|N|number of certificates to include") },
254
255     { oPolicyFile, "policy-file", 2,
256                     N_("|FILE|take policy information from FILE") },
257
258     { oDisablePolicyChecks, "disable-policy-checks", 0,
259                            N_("do not check certificate policies")},
260     { oEnablePolicyChecks, "enable-policy-checks", 0, "@"},
261
262     { oAutoIssuerKeyRetrieve, "auto-issuer-key-retrieve", 0, 
263       N_("fetch missing issuer certificates")},
264
265 #if 0
266     { oDefRecipient, "default-recipient" ,2,
267                                   N_("|NAME|use NAME as default recipient")},
268     { oDefRecipientSelf, "default-recipient-self" ,0,
269                                 N_("use the default key as default recipient")},
270     { oNoDefRecipient, "no-default-recipient", 0, "@" },
271     { oEncryptTo, "encrypt-to", 2, "@" },
272     { oNoEncryptTo, "no-encrypt-to", 0, "@" },
273
274 #endif
275     { oUser, "local-user",2, N_("use this user-id to sign or decrypt")},
276
277 #if 0
278     { oCompress, NULL,        1, N_("|N|set compress level N (0 disables)") },
279     { oTextmodeShort, NULL,   0, "@"},
280     { oTextmode, "textmode",  0, N_("use canonical text mode")},
281 #endif
282
283     { oOutput, "output",    2, N_("use as output file")},
284     { oVerbose, "verbose",   0, N_("verbose") },
285     { oQuiet,   "quiet",   0, N_("be somewhat more quiet") },
286     { oNoTTY, "no-tty", 0, N_("don't use the terminal at all") },
287 #if 0
288     { oForceV3Sigs, "force-v3-sigs", 0, N_("force v3 signatures") },
289     { oForceMDC, "force-mdc", 0, N_("always use a MDC for encryption") },
290 #endif
291     { oDryRun, "dry-run",   0, N_("do not make any changes") },
292   /*{ oInteractive, "interactive", 0, N_("prompt before overwriting") }, */
293     /*{ oUseAgent, "use-agent",0, N_("use the gpg-agent")},*/
294     { oBatch, "batch",     0, N_("batch mode: never ask")},
295     { oAnswerYes, "yes",       0, N_("assume yes on most questions")},
296     { oAnswerNo,  "no",        0, N_("assume no on most questions")},
297
298     { oKeyring, "keyring"   ,2, N_("add this keyring to the list of keyrings")},
299     { oSecretKeyring, "secret-keyring" ,2, N_("add this secret keyring to the list")},
300     { oDefaultKey, "default-key" ,2, N_("|NAME|use NAME as default secret key")},
301     { oKeyServer, "keyserver",2, N_("|HOST|use this keyserver to lookup keys")},
302     { oCharset, "charset"   , 2, N_("|NAME|set terminal charset to NAME") },
303     { oOptions, "options"   , 2, N_("read options from file")},
304
305     { oDebug, "debug"     ,4|16, "@"},
306     { oDebugAll, "debug-all" ,0, "@"},
307     { oDebugWait, "debug-wait" ,1, "@"},
308     { oDebugNoChainValidation, "debug-no-chain-validation" ,0, "@"},
309     { oStatusFD, "status-fd" ,1, N_("|FD|write status info to this FD") },
310     { aDummy, "no-comment", 0,   "@"},
311     { aDummy, "completes-needed", 1, "@"},
312     { aDummy, "marginals-needed", 1, "@"},
313     { oMaxCertDepth,    "max-cert-depth", 1, "@" },
314     { aDummy, "trusted-key", 2, "@"},
315     { oLoadExtension, "load-extension" ,2,
316       N_("|FILE|load extension module FILE")},
317     { aDummy, "rfc1991",   0, "@"},
318     { aDummy, "openpgp",   0, "@"},
319     { aDummy, "s2k-mode",  1, "@"},
320     { aDummy, "s2k-digest-algo",2, "@"},
321     { aDummy, "s2k-cipher-algo",2, "@"},
322     { oCipherAlgo, "cipher-algo", 2 , N_("|NAME|use cipher algorithm NAME")},
323     { oDigestAlgo, "digest-algo", 2 ,
324       N_("|NAME|use message digest algorithm NAME")},
325 #if 0
326     { oCompressAlgo, "compress-algo", 1 , N_("|N|use compress algorithm N")},
327 #endif
328     { aDummy, "throw-keyid", 0, "@"},
329     { aDummy, "notation-data", 2, "@"},
330
331     { 302, NULL, 0, N_(
332   "@\n(See the man page for a complete listing of all commands and options)\n"
333                       )},
334
335     { 303, NULL, 0, N_("@\nExamples:\n\n"
336     " -se -r Bob [file]          sign and encrypt for user Bob\n"
337     " --clearsign [file]         make a clear text signature\n"
338     " --detach-sign [file]       make a detached signature\n"
339     " --list-keys [names]        show keys\n"
340     " --fingerprint [names]      show fingerprints\n"  ) },
341
342   /* hidden options */
343     { oNoVerbose, "no-verbose", 0, "@"},
344
345     { oEnableSpecialFilenames, "enable-special-filenames", 0, "@" },
346
347
348     { oTrustDBName, "trustdb-name", 2, "@" },
349     { oNoSecmemWarn, "no-secmem-warning", 0, "@" }, 
350     { oNoArmor, "no-armor",   0, "@"},
351     { oNoArmor, "no-armour",   0, "@"},
352     { oNoDefKeyring, "no-default-keyring", 0, "@" },
353     { oNoGreeting, "no-greeting", 0, "@" },
354     { oNoOptions, "no-options", 0, "@" }, /* shortcut for --options /dev/null */
355     { oHomedir, "homedir", 2, "@" },   /* defaults to "~/.gnupg" */
356     { oAgentProgram, "agent-program", 2 , "@" },
357     { oDisplay,    "display",     2, "@" },
358     { oTTYname,    "ttyname",     2, "@" },
359     { oTTYtype,    "ttytype",     2, "@" },
360     { oLCctype,    "lc-ctype",    2, "@" },
361     { oLCmessages, "lc-messages", 2, "@" },
362     { oDirmngrProgram, "dirmngr-program", 2 , "@" },
363     { oFakedSystemTime, "faked-system-time", 4, "@" }, /* (epoch time) */
364
365
366     { oNoBatch, "no-batch", 0, "@" },
367     { oWithColons, "with-colons", 0, "@"},
368     { oWithKeyData,"with-key-data", 0, "@"},
369     { aListKeys, "list-key", 0, "@" }, /* alias */
370     { aListSigs, "list-sig", 0, "@" }, /* alias */
371     { aListSigs, "check-sig",0, "@" }, /* alias */
372     { oSkipVerify, "skip-verify",0, "@" },
373     { oCompressKeys, "compress-keys",0, "@"},
374     { oCompressSigs, "compress-sigs",0, "@"},
375     { oAlwaysTrust, "always-trust", 0, "@"},
376     { oNoVersion, "no-version", 0, "@"},
377     { oLockOnce, "lock-once", 0, "@" },
378     { oLockMultiple, "lock-multiple", 0, "@" },
379     { oLockNever, "lock-never", 0, "@" },
380     { oLoggerFD, "logger-fd",1, "@" },
381     { oWithFingerprint, "with-fingerprint", 0, "@" },
382     { oDisableCipherAlgo,  "disable-cipher-algo", 2, "@" },
383     { oDisablePubkeyAlgo,  "disable-pubkey-algo", 2, "@" },
384     { oHonorHttpProxy,"honor-http-proxy", 0, "@" },
385     { oListOnly, "list-only", 0, "@"},
386     { oIgnoreTimeConflict, "ignore-time-conflict", 0, "@" },
387     { oNoRandomSeedFile,  "no-random-seed-file", 0, "@" },
388 {0} };
389
390
391
392 int gpgsm_errors_seen = 0;
393
394 /* It is possible that we are currentlu running under setuid permissions */
395 static int maybe_setuid = 1;
396
397 /* Option --enable-special-filenames */
398 static int allow_special_filenames;
399
400
401 static char *build_list (const char *text,
402                          const char *(*mapf)(int), int (*chkf)(int));
403 static void set_cmd (enum cmd_and_opt_values *ret_cmd,
404                      enum cmd_and_opt_values new_cmd );
405
406 static void emergency_cleanup (void);
407 static int check_special_filename (const char *fname);
408 static int open_read (const char *filename);
409 static FILE *open_fwrite (const char *filename);
410
411
412 static int
413 our_pk_test_algo (int algo)
414 {
415   return 1;
416 }
417
418 static int
419 our_cipher_test_algo (int algo)
420 {
421   return 1;
422 }
423
424 static int
425 our_md_test_algo (int algo)
426 {
427   return 1;
428 }
429
430 static const char *
431 my_strusage( int level )
432 {
433   static char *digests, *pubkeys, *ciphers;
434   const char *p;
435
436   switch (level)
437     {
438     case 11: p = "gpgsm (GnuPG)";
439       break;
440     case 13: p = VERSION; break;
441     case 17: p = PRINTABLE_OS_NAME; break;
442     case 19: p = _("Please report bugs to <" PACKAGE_BUGREPORT ">.\n");
443       break;
444     case 1:
445     case 40: p = _("Usage: gpgsm [options] [files] (-h for help)");
446       break;
447     case 41:
448       p = _("Syntax: gpgsm [options] [files]\n"
449             "sign, check, encrypt or decrypt using the S/MIME protocol\n"
450             "default operation depends on the input data\n");
451       break;
452
453     case 31: p = "\nHome: "; break;
454     case 32: p = opt.homedir; break;
455     case 33: p = _("\nSupported algorithms:\n"); break;
456     case 34:
457       if (!ciphers)
458         ciphers = build_list ("Cipher: ", gcry_cipher_algo_name,
459                               our_cipher_test_algo );
460       p = ciphers;
461       break;
462     case 35:
463       if (!pubkeys)
464         pubkeys = build_list ("Pubkey: ", gcry_pk_algo_name,
465                               our_pk_test_algo );
466       p = pubkeys;
467       break;
468     case 36:
469       if (!digests)
470         digests = build_list("Hash: ", gcry_md_algo_name, our_md_test_algo );
471       p = digests;
472       break;
473       
474     default: p = NULL; break;
475     }
476   return p;
477 }
478
479
480 static char *
481 build_list (const char *text, const char * (*mapf)(int), int (*chkf)(int))
482 {
483   int i;
484   size_t n=strlen(text)+2;
485   char *list, *p;
486   
487   if (maybe_setuid) {
488     gcry_control (GCRYCTL_DROP_PRIVS); /* drop setuid */
489   }
490
491   for (i=1; i < 110; i++ )
492     if (!chkf(i))
493       n += strlen(mapf(i)) + 2;
494   list = xmalloc (21 + n);
495   *list = 0;
496   for (p=NULL, i=1; i < 110; i++)
497     {
498       if (!chkf(i))
499         {
500           if( !p )
501             p = stpcpy (list, text );
502           else
503             p = stpcpy (p, ", ");
504           p = stpcpy (p, mapf(i) );
505         }
506     }
507   if (p)
508     p = stpcpy(p, "\n" );
509   return list;
510 }
511
512
513 static void
514 i18n_init(void)
515 {
516 #ifdef USE_SIMPLE_GETTEXT
517   set_gettext_file (PACKAGE);
518 #else
519 # ifdef ENABLE_NLS
520 #  ifdef HAVE_LC_MESSAGES
521   setlocale (LC_TIME, "");
522   setlocale (LC_MESSAGES, "");
523 #  else
524   setlocale (LC_ALL, "" );
525 #  endif
526   bindtextdomain (PACKAGE, LOCALEDIR);
527   textdomain (PACKAGE);
528 # endif
529 #endif
530 }
531
532
533 static void
534 wrong_args (const char *text)
535 {
536   fputs (_("usage: gpgsm [options] "), stderr);
537   fputs (text, stderr);
538   putc ('\n', stderr);
539   gpgsm_exit (2);
540 }
541
542
543 static void
544 set_debug(void)
545 {
546   if (opt.debug & DBG_MPI_VALUE)
547     gcry_control (GCRYCTL_SET_DEBUG_FLAGS, 2);
548   if (opt.debug & DBG_CRYPTO_VALUE )
549     gcry_control (GCRYCTL_SET_DEBUG_FLAGS, 1);
550 }
551
552
553 static void
554 set_cmd (enum cmd_and_opt_values *ret_cmd, enum cmd_and_opt_values new_cmd)
555 {
556   enum cmd_and_opt_values cmd = *ret_cmd;
557
558   if (!cmd || cmd == new_cmd)
559     cmd = new_cmd;
560   else if ( cmd == aSign && new_cmd == aEncr )
561     cmd = aSignEncr;
562   else if ( cmd == aEncr && new_cmd == aSign )
563     cmd = aSignEncr;
564   else if ( (cmd == aSign && new_cmd == aClearsign)
565             || (cmd == aClearsign && new_cmd == aSign) )
566     cmd = aClearsign;
567   else 
568     {
569       log_error(_("conflicting commands\n"));
570       gpgsm_exit(2);
571     }
572
573   *ret_cmd = cmd;
574 }
575
576
577 int
578 main ( int argc, char **argv)
579 {
580   ARGPARSE_ARGS pargs;
581   int orig_argc;
582   char **orig_argv;
583   const char *fname;
584   /*  char *username;*/
585   int may_coredump;
586   STRLIST sl, remusr= NULL, locusr=NULL;
587   STRLIST nrings=NULL;
588   int detached_sig = 0;
589   FILE *configfp = NULL;
590   char *configname = NULL;
591   unsigned configlineno;
592   int parse_debug = 0;
593   int default_config =1;
594   int default_keyring = 1;
595   char *logfile = NULL;
596   int greeting = 0;
597   int nogreeting = 0;
598   int debug_wait = 0;
599   int use_random_seed = 1;
600   int with_fpr = 0;
601   char *def_digest_string = NULL;
602   enum cmd_and_opt_values cmd = 0;
603   struct server_control_s ctrl;
604   CERTLIST recplist = NULL;
605   CERTLIST signerlist = NULL;
606
607   /* trap_unaligned ();*/
608   set_strusage (my_strusage);
609   gcry_control (GCRYCTL_SUSPEND_SECMEM_WARN);
610   /* Please note that we may running SUID(ROOT), so be very CAREFUL
611      when adding any stuff between here and the call to secmem_init()
612      somewhere after the option parsing */
613   log_set_prefix ("gpgsm", 1);
614   /* check that the libraries are suitable.  Do it here because the
615      option parse may need services of the library */
616   if (!gcry_check_version (NEED_LIBGCRYPT_VERSION) )
617     {
618       log_fatal( _("libgcrypt is too old (need %s, have %s)\n"),
619                  NEED_LIBGCRYPT_VERSION, gcry_check_version (NULL) );
620     }
621   if (!ksba_check_version (NEED_KSBA_VERSION) )
622     {
623       log_fatal( _("libksba is too old (need %s, have %s)\n"),
624                  NEED_KSBA_VERSION, ksba_check_version (NULL) );
625     }
626
627   gcry_control (GCRYCTL_USE_SECURE_RNDPOOL);
628
629   may_coredump = disable_core_dumps ();
630   
631   gnupg_init_signals (0, emergency_cleanup);
632   
633   create_dotlock (NULL); /* register locking cleanup */
634   i18n_init();
635
636   opt.def_cipher_algoid = "1.2.840.113549.3.7";  /*des-EDE3-CBC*/
637 #ifdef __MINGW32__
638   opt.homedir = read_w32_registry_string ( NULL,
639                                            "Software\\GNU\\GnuPG", "HomeDir" );
640 #else
641   opt.homedir = getenv ("GNUPGHOME");
642 #endif
643   if (!opt.homedir || !*opt.homedir ) 
644     opt.homedir = GNUPG_DEFAULT_HOMEDIR;
645
646   /* first check whether we have a config file on the commandline */
647   orig_argc = argc;
648   orig_argv = argv;
649   pargs.argc = &argc;
650   pargs.argv = &argv;
651   pargs.flags= 1|(1<<6);  /* do not remove the args, ignore version */
652   while (arg_parse( &pargs, opts))
653     {
654       if (pargs.r_opt == oDebug || pargs.r_opt == oDebugAll)
655         parse_debug++;
656       else if (pargs.r_opt == oOptions)
657         { /* yes there is one, so we do not try the default one but
658              read the config file when it is encountered at the
659              commandline */
660           default_config = 0;
661         }
662       else if (pargs.r_opt == oNoOptions)
663         default_config = 0; /* --no-options */
664       else if (pargs.r_opt == oHomedir)
665         opt.homedir = pargs.r.ret_str;
666     }
667   
668   
669   /* initialize the secure memory. */
670   gcry_control (GCRYCTL_INIT_SECMEM, 16384, 0);
671   maybe_setuid = 0;
672
673   /* 
674      Now we are now working under our real uid 
675   */
676
677   ksba_set_malloc_hooks (gcry_malloc, gcry_realloc, gcry_free );
678   assuan_set_malloc_hooks (gcry_malloc, gcry_realloc, gcry_free);
679   keybox_set_malloc_hooks (gcry_malloc, gcry_realloc, gcry_free);
680
681   /* Setup a default control structure for command line mode */
682   memset (&ctrl, 0, sizeof ctrl);
683   gpgsm_init_default_ctrl (&ctrl);
684   ctrl.no_server = 1;
685   ctrl.status_fd = -1; /* not status output */
686   ctrl.autodetect_encoding = 1;
687
688   /* set the default option file */
689   if (default_config )
690     configname = make_filename (opt.homedir, "gpgsm.conf", NULL);
691   /* cet the default policy file */
692   opt.policy_file = make_filename (opt.homedir, "policies.txt", NULL);
693   
694   argc        = orig_argc;
695   argv        = orig_argv;
696   pargs.argc  = &argc;
697   pargs.argv  = &argv;
698   pargs.flags =  1;  /* do not remove the args */
699
700  next_pass:
701   if (configname) {
702     configlineno = 0;
703     configfp = fopen (configname, "r");
704     if (!configfp)
705       {
706         if (default_config)
707           {
708             if (parse_debug)
709               log_info (_("NOTE: no default option file `%s'\n"), configname);
710           }
711         else 
712           {
713             log_error (_("option file `%s': %s\n"), configname, strerror(errno));
714             gpgsm_exit(2);
715           }
716         xfree(configname);
717         configname = NULL;
718       }
719     if (parse_debug && configname)
720       log_info (_("reading options from `%s'\n"), configname);
721     default_config = 0;
722   }
723
724   while (optfile_parse (configfp, configname, &configlineno, &pargs, opts))
725     {
726       switch (pargs.r_opt)
727         {
728         case aServer: 
729           opt.batch = 1;
730           set_cmd (&cmd, aServer);
731           break;
732
733         case aCheckKeys: set_cmd (&cmd, aCheckKeys); break;
734         case aImport: set_cmd (&cmd, aImport); break;
735         case aSendKeys: set_cmd (&cmd, aSendKeys); break;
736         case aRecvKeys: set_cmd (&cmd, aRecvKeys); break;
737         case aExport: set_cmd (&cmd, aExport); break;
738         case aListKeys: set_cmd (&cmd, aListKeys); break;
739         case aListExternalKeys: set_cmd (&cmd, aListExternalKeys); break;
740         case aListSecretKeys: set_cmd (&cmd, aListSecretKeys); break;
741         case aListSigs: set_cmd (&cmd, aListSigs); break;
742
743         case aLearnCard: set_cmd (&cmd, aLearnCard); break;
744
745         case aDeleteKey:
746           set_cmd (&cmd, aDeleteKey);
747           /*greeting=1;*/
748           break;
749
750         case aDetachedSign:
751           detached_sig = 1;
752           set_cmd (&cmd, aSign ); 
753           break;
754           
755         case aSym: set_cmd (&cmd, aSym); break;
756         case aDecrypt: set_cmd (&cmd, aDecrypt); break;
757         case aEncr: set_cmd (&cmd, aEncr); break;
758         case aSign: set_cmd (&cmd, aSign );  break;
759         case aKeygen: set_cmd (&cmd, aKeygen); greeting=1; break;
760         case aClearsign: set_cmd (&cmd, aClearsign); break;
761         case aVerify: set_cmd (&cmd, aVerify); break;
762
763
764           /* output encoding selection */
765         case oArmor:
766           ctrl.create_pem = 1;
767           break;
768         case oBase64: 
769           ctrl.create_pem = 0;
770           ctrl.create_base64 = 1;
771           break;
772         case oNoArmor: 
773           ctrl.create_pem = 0;
774           ctrl.create_base64 = 0;
775           break;
776           
777           /* Input encoding selection */
778         case oAssumeArmor:
779           ctrl.autodetect_encoding = 0;
780           ctrl.is_pem = 1;
781           ctrl.is_base64 = 0;
782           break;
783         case oAssumeBase64:
784           ctrl.autodetect_encoding = 0;
785           ctrl.is_pem = 0;
786           ctrl.is_base64 = 1;
787           break;
788         case oAssumeBinary:
789           ctrl.autodetect_encoding = 0;
790           ctrl.is_pem = 0;
791           ctrl.is_base64 = 0;
792           break;
793
794         case oDisableCRLChecks:
795           opt.no_crl_check = 1;
796           break;
797         case oEnableCRLChecks:
798           opt.no_crl_check = 0;
799           break;
800
801         case oIncludeCerts: ctrl.include_certs = pargs.r.ret_int; break;
802
803         case oPolicyFile:
804           xfree (opt.policy_file);
805           if (*pargs.r.ret_str)
806             opt.policy_file = xstrdup (pargs.r.ret_str);
807           else
808             opt.policy_file = NULL;
809           break;
810
811         case oDisablePolicyChecks:
812           opt.no_policy_check = 1;
813           break;
814         case oEnablePolicyChecks:
815           opt.no_policy_check = 0;
816           break;
817           
818         case oAutoIssuerKeyRetrieve:
819           opt.auto_issuer_key_retrieve = 1;
820           break;
821
822         case oOutput: opt.outfile = pargs.r.ret_str; break;
823
824         
825         case oQuiet: opt.quiet = 1; break;
826         case oNoTTY: /* fixme:tty_no_terminal(1);*/ break;
827         case oDryRun: opt.dry_run = 1; break;
828
829         case oVerbose:
830           opt.verbose++;
831           gcry_control (GCRYCTL_SET_VERBOSITY, (int)opt.verbose);
832           break;
833         case oNoVerbose:
834           opt.verbose = 0;
835           gcry_control (GCRYCTL_SET_VERBOSITY, (int)opt.verbose);
836           break;
837
838         case oLogFile: logfile = pargs.r.ret_str; break;
839           
840         case oBatch: 
841           opt.batch = 1;
842           greeting = 0;
843           break;
844         case oNoBatch: opt.batch = 0; break;
845           
846         case oAnswerYes: opt.answer_yes = 1; break;
847         case oAnswerNo: opt.answer_no = 1; break;
848
849         case oKeyring: append_to_strlist (&nrings, pargs.r.ret_str); break;
850
851         case oDebug: opt.debug |= pargs.r.ret_ulong; break;
852         case oDebugAll: opt.debug = ~0; break;
853         case oDebugWait: debug_wait = pargs.r.ret_int; break;
854         case oDebugNoChainValidation: opt.no_chain_validation = 1; break;
855
856         case oStatusFD: ctrl.status_fd = pargs.r.ret_int; break;
857         case oLoggerFD: log_set_fd (pargs.r.ret_int ); break;
858         case oWithFingerprint:
859           with_fpr=1; /*fall thru*/
860         case oFingerprint:
861           opt.fingerprint++;
862           break;
863
864         case oOptions:
865           /* config files may not be nested (silently ignore them) */
866           if (!configfp)
867             {
868               xfree(configname);
869               configname = xstrdup (pargs.r.ret_str);
870               goto next_pass;
871             }
872           break;
873         case oNoOptions: break; /* no-options */
874         case oHomedir: opt.homedir = pargs.r.ret_str; break;
875         case oAgentProgram: opt.agent_program = pargs.r.ret_str;  break;
876         case oDisplay: opt.display = xstrdup (pargs.r.ret_str); break;
877         case oTTYname: opt.ttyname = xstrdup (pargs.r.ret_str); break;
878         case oTTYtype: opt.ttytype = xstrdup (pargs.r.ret_str); break;
879         case oLCctype: opt.lc_ctype = xstrdup (pargs.r.ret_str); break;
880         case oLCmessages: opt.lc_messages = xstrdup (pargs.r.ret_str); break;
881         case oDirmngrProgram: opt.dirmngr_program = pargs.r.ret_str;  break;
882           
883         case oFakedSystemTime:
884           gnupg_set_time ( (time_t)pargs.r.ret_ulong, 0);
885           break;
886
887         case oNoDefKeyring: default_keyring = 0; break;
888         case oNoGreeting: nogreeting = 1; break;
889
890         case oDefaultKey:
891           /* fixme:opt.def_secret_key = pargs.r.ret_str;*/
892           break;
893         case oDefRecipient:
894           if (*pargs.r.ret_str)
895             opt.def_recipient = xstrdup (pargs.r.ret_str);
896           break;
897         case oDefRecipientSelf:
898           xfree (opt.def_recipient);
899           opt.def_recipient = NULL;
900           opt.def_recipient_self = 1;
901           break;
902         case oNoDefRecipient:
903           xfree (opt.def_recipient);
904           opt.def_recipient = NULL;
905           opt.def_recipient_self = 0;
906           break;
907
908         case oWithKeyData: opt.with_key_data=1; /* fall thru */
909         case oWithColons: ctrl.with_colons = 1; break;
910
911         case oSkipVerify: opt.skip_verify=1; break;
912
913         case oNoEncryptTo: /*fixme: opt.no_encrypt_to = 1;*/ break;
914         case oEncryptTo: /* store the recipient in the second list */
915           sl = add_to_strlist (&remusr, pargs.r.ret_str);
916           sl->flags = 1;
917           break;
918
919         case oRecipient: /* store the recipient */
920           add_to_strlist ( &remusr, pargs.r.ret_str);
921           break;
922
923         case oTextmodeShort: /*fixme:opt.textmode = 2;*/ break;
924         case oTextmode: /*fixme:opt.textmode=1;*/  break;
925
926         case oUser: /* store the local users, the first one is the default */
927           if (!opt.local_user)
928             opt.local_user = pargs.r.ret_str;
929           add_to_strlist (&locusr, pargs.r.ret_str);
930           break;
931
932         case oNoSecmemWarn:
933           gcry_control (GCRYCTL_DISABLE_SECMEM_WARN); 
934           break;
935
936         case oCipherAlgo:
937           opt.def_cipher_algoid = pargs.r.ret_str;
938           break;
939
940         case oDisableCipherAlgo: 
941           {
942             int algo = gcry_cipher_map_name (pargs.r.ret_str);
943             gcry_cipher_ctl (NULL, GCRYCTL_DISABLE_ALGO, &algo, sizeof algo);
944           }
945           break;
946         case oDisablePubkeyAlgo: 
947           {
948             int algo = gcry_pk_map_name (pargs.r.ret_str);
949             gcry_pk_ctl (GCRYCTL_DISABLE_ALGO,&algo, sizeof algo );
950           }
951           break;
952
953         case oIgnoreTimeConflict: opt.ignore_time_conflict = 1; break;
954         case oNoRandomSeedFile: use_random_seed = 0; break;
955
956         case oEnableSpecialFilenames: allow_special_filenames =1; break;
957           
958
959         case aDummy:
960           break;
961         default: 
962           pargs.err = configfp? 1:2; 
963           break;
964         }
965     }
966
967   if (configfp)
968     {
969       fclose (configfp);
970       configfp = NULL;
971       xfree (configname);
972       configname = NULL;
973       goto next_pass;
974     }
975   
976   xfree (configname);
977   configname = NULL;
978
979   if (log_get_errorcount(0))
980     gpgsm_exit(2);
981   
982   if (nogreeting)
983     greeting = 0;
984   
985   if (greeting)
986     {
987       fprintf(stderr, "%s %s; %s\n",
988               strusage(11), strusage(13), strusage(14) );
989       fprintf(stderr, "%s\n", strusage(15) );
990     }
991 #  ifdef IS_DEVELOPMENT_VERSION
992   if (!opt.batch)
993     {
994       log_info ("NOTE: THIS IS A DEVELOPMENT VERSION!\n");
995       log_info ("It is only intended for test purposes and should NOT be\n");
996       log_info ("used in a production environment or with production keys!\n");
997     }
998 #  endif
999
1000   if (may_coredump && !opt.quiet)
1001     log_info (_("WARNING: program may create a core file!\n"));
1002
1003   if (logfile)
1004     {
1005       log_set_file (logfile);
1006       log_set_prefix (NULL, 1|2|4);
1007     }
1008
1009   if (gnupg_faked_time_p ())
1010     {
1011       log_info (_("WARNING: running with faked system time: "));
1012       gpgsm_dump_time (gnupg_get_time ());
1013       log_printf ("\n");
1014     }
1015   
1016 /*FIXME    if (opt.batch) */
1017 /*      tty_batchmode (1); */
1018
1019   gcry_control (GCRYCTL_RESUME_SECMEM_WARN);
1020
1021   set_debug ();
1022
1023   /* FIXME: should set filenames of libgcrypt explicitly
1024    * gpg_opt_homedir = opt.homedir; */
1025
1026   /* must do this after dropping setuid, because the mapping functions
1027      may try to load an module and we may have disabled an algorithm */
1028   if ( !gcry_cipher_map_name (opt.def_cipher_algoid)
1029        || !gcry_cipher_mode_from_oid (opt.def_cipher_algoid))
1030     log_error (_("selected cipher algorithm is invalid\n"));
1031
1032   if (def_digest_string)
1033     {
1034       opt.def_digest_algo = gcry_md_map_name (def_digest_string);
1035       xfree (def_digest_string);
1036       def_digest_string = NULL;
1037       if (our_md_test_algo(opt.def_digest_algo) )
1038         log_error (_("selected digest algorithm is invalid\n"));
1039     }
1040
1041   if (log_get_errorcount(0))
1042     gpgsm_exit(2);
1043   
1044   /* set the random seed file */
1045   if (use_random_seed) {
1046     char *p = make_filename (opt.homedir, "random_seed", NULL);
1047 #if 0
1048 #warning set_random_seed_file not yet available in Libgcrypt
1049     set_random_seed_file(p);
1050 #endif
1051     xfree(p);
1052   }
1053
1054
1055   if (!cmd && opt.fingerprint && !with_fpr)
1056     set_cmd (&cmd, aListKeys);
1057   
1058   if (!nrings && default_keyring)  /* add default keybox */
1059     keydb_add_resource ("pubring.kbx", 0, 0);
1060   for (sl = nrings; sl; sl = sl->next)
1061     keydb_add_resource (sl->d, 0, 0);
1062   FREE_STRLIST(nrings);
1063
1064
1065   for (sl = locusr; sl; sl = sl->next)
1066     {
1067       int rc = gpgsm_add_to_certlist (&ctrl, sl->d, 1, &signerlist);
1068       if (rc)
1069         {
1070           log_error (_("can't sign using `%s': %s\n"),
1071                      sl->d, gnupg_strerror (rc));
1072           gpgsm_status2 (&ctrl, STATUS_INV_RECP,
1073                          rc == -1? "1":
1074                          rc == GNUPG_No_Public_Key?       "1":
1075                          rc == GNUPG_Ambiguous_Name?      "2":
1076                          rc == GNUPG_Wrong_Key_Usage?     "3":
1077                          rc == GNUPG_Certificate_Revoked? "4":
1078                          rc == GNUPG_Certificate_Expired? "5":
1079                          rc == GNUPG_No_CRL_Known?        "6":
1080                          rc == GNUPG_CRL_Too_Old?         "7":
1081                          rc == GNUPG_No_Policy_Match?     "8":
1082                          rc == GNUPG_No_Secret_Key?       "9":
1083                          "0",
1084                          sl->d, NULL);
1085         }
1086     }
1087   for (sl = remusr; sl; sl = sl->next)
1088     {
1089       int rc = gpgsm_add_to_certlist (&ctrl, sl->d, 0, &recplist);
1090       if (rc)
1091         {
1092           log_error (_("can't encrypt to `%s': %s\n"),
1093                      sl->d, gnupg_strerror (rc));
1094           gpgsm_status2 (&ctrl, STATUS_INV_RECP,
1095                          rc == -1? "1":
1096                          rc == GNUPG_No_Public_Key?       "1":
1097                          rc == GNUPG_Ambiguous_Name?      "2":
1098                          rc == GNUPG_Wrong_Key_Usage?     "3":
1099                          rc == GNUPG_Certificate_Revoked? "4":
1100                          rc == GNUPG_Certificate_Expired? "5":
1101                          rc == GNUPG_No_CRL_Known?        "6":
1102                          rc == GNUPG_CRL_Too_Old?         "7":
1103                          rc == GNUPG_No_Policy_Match?     "8":
1104                          "0",
1105                          sl->d, NULL);
1106         }
1107   }
1108   if (log_get_errorcount(0))
1109     gpgsm_exit(1); /* must stop for invalid recipients */
1110   
1111
1112   
1113   fname = argc? *argv : NULL;
1114   
1115   switch (cmd)
1116     {
1117     case aServer:
1118       if (debug_wait)
1119         {
1120           log_debug ("waiting for debugger - my pid is %u .....\n",
1121                      (unsigned int)getpid());
1122           sleep (debug_wait);
1123           log_debug ("... okay\n");
1124          }
1125       gpgsm_server ();
1126       break;
1127
1128     case aEncr: /* encrypt the given file */
1129       if (!argc)
1130         gpgsm_encrypt (&ctrl, recplist, 0, stdout); /* from stdin */
1131       else if (argc == 1)
1132         gpgsm_encrypt (&ctrl, recplist, open_read (*argv), stdout); /* from file */
1133       else
1134         wrong_args (_("--encrypt [datafile]"));
1135       break;
1136
1137     case aSign: /* sign the given file */
1138       /* FIXME: We don't handle --output yet. We should also allow
1139          to concatenate multiple files for signing because that is
1140          what gpg does.*/
1141       if (!argc)
1142         gpgsm_sign (&ctrl, signerlist,
1143                     0, detached_sig, stdout); /* create from stdin */
1144       else if (argc == 1)
1145         gpgsm_sign (&ctrl, signerlist,
1146                     open_read (*argv), detached_sig, stdout); /* from file */
1147       else
1148         wrong_args (_("--sign [datafile]"));
1149       break;
1150         
1151     case aSignEncr: /* sign and encrypt the given file */
1152       log_error ("this command has not yet been implemented\n");
1153       break;
1154
1155     case aClearsign: /* make a clearsig */
1156       log_error ("this command has not yet been implemented\n");
1157       break;
1158
1159     case aVerify:
1160       {
1161         FILE *fp = NULL;
1162
1163         if (argc == 2 && opt.outfile)
1164           log_info ("option --output ignored for a detached signature\n");
1165         else if (opt.outfile)
1166           fp = open_fwrite (opt.outfile);
1167
1168         if (!argc)
1169           gpgsm_verify (&ctrl, 0, -1, fp); /* normal signature from stdin */
1170         else if (argc == 1)
1171           gpgsm_verify (&ctrl, open_read (*argv), -1, fp); /* std signature */
1172         else if (argc == 2) /* detached signature (sig, detached) */
1173           gpgsm_verify (&ctrl, open_read (*argv), open_read (argv[1]), NULL); 
1174         else
1175           wrong_args (_("--verify [signature [detached_data]]"));
1176
1177         if (fp && fp != stdout)
1178           fclose (fp);
1179       }
1180       break;
1181
1182     case aVerifyFiles:
1183       log_error ("this command has not yet been implemented\n");
1184       break;
1185
1186     case aDecrypt:
1187       if (!argc)
1188         gpgsm_decrypt (&ctrl, 0, stdout); /* from stdin */
1189       else if (argc == 1)
1190         gpgsm_decrypt (&ctrl, open_read (*argv), stdout); /* from file */
1191       else
1192         wrong_args (_("--decrypt [filename]"));
1193       break;
1194
1195     case aDeleteKey:
1196       for (sl=NULL; argc; argc--, argv++)
1197         add_to_strlist (&sl, *argv);
1198       gpgsm_delete (&ctrl, sl);
1199       free_strlist(sl);
1200       break;
1201
1202     case aListSigs:
1203       ctrl.with_chain = 1;
1204     case aListKeys:
1205       for (sl=NULL; argc; argc--, argv++)
1206         add_to_strlist (&sl, *argv);
1207       gpgsm_list_keys (&ctrl, sl, stdout, (0 | (1<<6)));
1208       free_strlist(sl);
1209       break;
1210
1211     case aListExternalKeys:
1212       for (sl=NULL; argc; argc--, argv++)
1213         add_to_strlist (&sl, *argv);
1214       gpgsm_list_keys (&ctrl, sl, stdout, (0 | (1<<7)));
1215       free_strlist(sl);
1216       break;
1217
1218     case aListSecretKeys:
1219       for (sl=NULL; argc; argc--, argv++)
1220         add_to_strlist (&sl, *argv);
1221       gpgsm_list_keys (&ctrl, sl, stdout, (2 | (1<<6)));
1222       free_strlist(sl);
1223       break;
1224
1225     case aKeygen: /* generate a key */
1226       log_error ("this function is not yet available from the commandline\n");
1227       break;
1228
1229     case aImport:
1230       if (!argc)
1231         gpgsm_import (&ctrl, 0);
1232       else
1233         {
1234           for (; argc; argc--, argv++)
1235             gpgsm_import (&ctrl, open_read (*argv));
1236         }
1237       break;
1238
1239     case aExport:
1240       for (sl=NULL; argc; argc--, argv++)
1241         add_to_strlist (&sl, *argv);
1242       gpgsm_export (&ctrl, sl, stdout);
1243       free_strlist(sl);
1244       break;
1245
1246       
1247     case aSendKeys:
1248     case aRecvKeys:
1249       log_error ("this command has not yet been implemented\n");
1250       break;
1251
1252
1253     case aLearnCard:
1254       if (argc)
1255         wrong_args ("--learn-card");
1256       else
1257         {
1258           int rc = gpgsm_agent_learn ();
1259           if (rc)
1260             log_error ("error learning card: %s\n", gnupg_strerror (rc));
1261         }
1262       break;
1263
1264
1265     default:
1266         log_error ("invalid command (there is no implicit command)\n");
1267         break;
1268     }
1269   
1270   /* cleanup */
1271   gpgsm_release_certlist (recplist);
1272   gpgsm_release_certlist (signerlist);
1273   FREE_STRLIST(remusr);
1274   FREE_STRLIST(locusr);
1275   gpgsm_exit(0);
1276   return 8; /*NEVER REACHED*/
1277 }
1278
1279 /* Note: This function is used by signal handlers!. */
1280 static void
1281 emergency_cleanup (void)
1282 {
1283   gcry_control (GCRYCTL_TERM_SECMEM );
1284 }
1285
1286
1287 void
1288 gpgsm_exit (int rc)
1289 {
1290   #if 0
1291 #warning no update_random_seed_file
1292   update_random_seed_file();
1293   #endif
1294 #if 0
1295   /* at this time a bit annoying */
1296   if (opt.debug & DBG_MEMSTAT_VALUE)
1297     {
1298       gcry_control( GCRYCTL_DUMP_MEMORY_STATS );
1299       gcry_control( GCRYCTL_DUMP_RANDOM_STATS );
1300     }
1301   if (opt.debug)
1302     gcry_control (GCRYCTL_DUMP_SECMEM_STATS );
1303 #endif
1304   emergency_cleanup ();
1305   rc = rc? rc : log_get_errorcount(0)? 2 : gpgsm_errors_seen? 1 : 0;
1306   exit (rc);
1307 }
1308
1309
1310 void
1311 gpgsm_init_default_ctrl (struct server_control_s *ctrl)
1312 {
1313   ctrl->include_certs = 1;  /* only include the signer's cert */
1314 }
1315
1316
1317
1318 /* Check whether the filename has the form "-&nnnn", where n is a
1319    non-zero number.  Returns this number or -1 if it is not the case.  */
1320 static int
1321 check_special_filename (const char *fname)
1322 {
1323   if (allow_special_filenames
1324       && fname && *fname == '-' && fname[1] == '&' ) {
1325     int i;
1326     
1327     fname += 2;
1328     for (i=0; isdigit (fname[i]); i++ )
1329       ;
1330     if ( !fname[i] ) 
1331       return atoi (fname);
1332   }
1333   return -1;
1334 }
1335
1336
1337
1338 /* Open the FILENAME for read and return the filedescriptor.  Stop
1339    with an error message in case of problems.  "-" denotes stdin and
1340    if special filenames are allowed the given fd is opened instead. */
1341 static int 
1342 open_read (const char *filename)
1343 {
1344   int fd;
1345
1346   if (filename[0] == '-' && !filename[1])
1347     return 0; /* stdin */
1348   fd = check_special_filename (filename);
1349   if (fd != -1)
1350     return fd;
1351   fd = open (filename, O_RDONLY);
1352   if (fd == -1)
1353     {
1354       log_error (_("can't open `%s': %s\n"), filename, strerror (errno));
1355       gpgsm_exit (2);
1356     }
1357   return fd;
1358 }
1359
1360 /* Open FILENAME for fwrite and return the stream.  Stop with an error
1361    message in case of problems.  "-" denotes stdout and if special
1362    filenames are allowed the given fd is opened instead. Caller must
1363    close the returned stream unless it is stdout. */
1364 static FILE *
1365 open_fwrite (const char *filename)
1366 {
1367   int fd;
1368   FILE *fp;
1369
1370   if (filename[0] == '-' && !filename[1])
1371     return stdout;
1372
1373   fd = check_special_filename (filename);
1374   if (fd != -1)
1375     {
1376       fp = fdopen (dup (fd), "wb");
1377       if (!fp)
1378         {
1379           log_error ("fdopen(%d) failed: %s\n", fd, strerror (errno));
1380           gpgsm_exit (2);
1381         }
1382       return fp;
1383     }
1384   fp = fopen (filename, "wb");
1385   if (!fp)
1386     {
1387       log_error (_("can't open `%s': %s\n"), filename, strerror (errno));
1388       gpgsm_exit (2);
1389     }
1390   return fp;
1391 }