Renamed g10.c to gpg.c
[gnupg.git] / g10 / gpg.c
1 /* gpg.c - The GnuPG utility (main for gpg)
2  * Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004,
3  *               2005 Free Software Foundation, Inc.
4  *
5  * This file is part of GnuPG.
6  *
7  * GnuPG is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 2 of the License, or
10  * (at your option) any later version.
11  *
12  * GnuPG is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,
20  * USA.
21  */
22
23 #include <config.h>
24 #include <errno.h>
25 #include <stdio.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <ctype.h>
29 #include <unistd.h>
30 #include <assert.h>
31 #ifdef HAVE_DOSISH_SYSTEM
32 #include <fcntl.h> /* for setmode() */
33 #endif
34 #ifdef HAVE_STAT
35 #include <sys/stat.h> /* for stat() */
36 #endif
37 #include <fcntl.h>
38
39 #define INCLUDED_BY_MAIN_MODULE 1
40 #include "packet.h"
41 #include "iobuf.h"
42 #include "memory.h"
43 #include "util.h"
44 #include "main.h"
45 #include "options.h"
46 #include "keydb.h"
47 #include "trustdb.h"
48 #include "mpi.h"
49 #include "cipher.h"
50 #include "filter.h"
51 #include "ttyio.h"
52 #include "i18n.h"
53 #include "status.h"
54 #include "g10defs.h"
55 #include "keyserver-internal.h"
56 #include "exec.h"
57 #include "cardglue.h"
58 #ifdef ENABLE_CARD_SUPPORT
59 #include "ccid-driver.h"
60 #endif
61
62 #if defined(HAVE_DOSISH_SYSTEM) || defined(__CYGWIN__)
63 #define MY_O_BINARY  O_BINARY
64 #ifndef S_IRGRP
65 # define S_IRGRP 0
66 # define S_IWGRP 0
67 #endif
68 #else
69 #define MY_O_BINARY  0
70 #endif
71
72
73 enum cmd_and_opt_values
74   {
75     aNull = 0,
76     oArmor        = 'a',
77     aDetachedSign = 'b',
78     aSym          = 'c',
79     aDecrypt      = 'd',
80     aEncr         = 'e',
81     oInteractive  = 'i',
82     oKOption      = 'k',
83     oDryRun       = 'n',
84     oOutput       = 'o',
85     oQuiet        = 'q',
86     oRecipient    = 'r',
87     oHiddenRecipient = 'R',
88     aSign         = 's',
89     oTextmodeShort= 't',
90     oLocalUser    = 'u',
91     oVerbose      = 'v',
92     oCompress     = 'z',
93     oSetNotation  = 'N',
94     aListSecretKeys = 'K',
95     oBatch        = 500,
96     oMaxOutput,
97     oSigNotation,
98     oCertNotation,
99     oShowNotation,
100     oNoShowNotation,
101     aEncrFiles,
102     aEncrSym,
103     aDecryptFiles,
104     aClearsign,
105     aStore,
106     aKeygen,
107     aSignEncr,
108     aSignEncrSym,
109     aSignSym,
110     aSignKey,
111     aLSignKey,
112     aListConfig,
113     aGPGConfList,
114     aListPackets,
115     aEditKey,
116     aDeleteKeys,
117     aDeleteSecretKeys,
118     aDeleteSecretAndPublicKeys,
119     aKMode,
120     aKModeC,
121     aImport,
122     aFastImport,
123     aVerify,
124     aVerifyFiles,
125     aListKeys,
126     aListSigs,
127     aSendKeys,
128     aRecvKeys,
129     aSearchKeys,
130     aExport,
131     aExportSecret,
132     aExportSecretSub,
133     aCheckKeys,
134     aGenRevoke,
135     aDesigRevoke,
136     aPrimegen,
137     aPrintMD,
138     aPrintMDs,
139     aCheckTrustDB,
140     aUpdateTrustDB,
141     aFixTrustDB,
142     aListTrustDB,
143     aListTrustPath,
144     aExportOwnerTrust,
145     aListOwnerTrust,
146     aImportOwnerTrust,
147     aDeArmor,
148     aEnArmor,
149     aGenRandom,
150     aPipeMode,
151     aRebuildKeydbCaches,
152     aRefreshKeys,
153     aCardStatus,
154     aCardEdit,
155     aChangePIN,
156
157     oTextmode,
158     oNoTextmode,
159     oExpert,
160     oNoExpert,
161     oDefSigExpire,
162     oAskSigExpire,
163     oNoAskSigExpire,
164     oDefCertExpire,
165     oAskCertExpire,
166     oNoAskCertExpire,
167     oDefCertLevel,
168     oMinCertLevel,
169     oAskCertLevel,
170     oNoAskCertLevel,
171     oFingerprint,
172     oWithFingerprint,
173     oAnswerYes,
174     oAnswerNo,
175     oKeyring,
176     oPrimaryKeyring,
177     oSecretKeyring,
178     oShowKeyring,
179     oDefaultKey,
180     oDefRecipient,
181     oDefRecipientSelf,
182     oNoDefRecipient,
183     oOptions,
184     oDebug,
185     oDebugAll,
186     oDebugCCIDDriver,
187     oStatusFD,
188     oStatusFile,
189     oAttributeFD,
190     oAttributeFile,
191     oEmitVersion,
192     oNoEmitVersion,
193     oCompletesNeeded,
194     oMarginalsNeeded,
195     oMaxCertDepth,
196     oLoadExtension,
197     oGnuPG,
198     oRFC1991,
199     oRFC2440,
200     oOpenPGP,
201     oPGP2,
202     oPGP6,
203     oPGP7,
204     oPGP8,
205     oRFC2440Text,
206     oNoRFC2440Text,
207     oCipherAlgo,
208     oDigestAlgo,
209     oCertDigestAlgo,
210     oCompressAlgo,
211     oCompressLevel,
212     oBZ2CompressLevel,
213     oBZ2DecompressLowmem,
214     oPasswd,
215     oPasswdFD,
216     oPasswdFile,
217     oCommandFD,
218     oCommandFile,
219     oQuickRandom,
220     oNoVerbose,
221     oTrustDBName,
222     oNoSecmemWarn,
223     oRequireSecmem,
224     oNoRequireSecmem,
225     oNoPermissionWarn,
226     oNoMDCWarn,
227     oNoArmor,
228     oNoDefKeyring,
229     oNoGreeting,
230     oNoTTY,
231     oNoOptions,
232     oNoBatch,
233     oHomedir,
234     oWithColons,
235     oWithKeyData,
236     oSkipVerify,
237     oCompressKeys,
238     oCompressSigs,
239     oAlwaysTrust,
240     oTrustModel,
241     oForceOwnertrust,
242     oRunAsShmCP,
243     oSetFilename,
244     oForYourEyesOnly,
245     oNoForYourEyesOnly,
246     oSetPolicyURL,
247     oSigPolicyURL,
248     oCertPolicyURL,
249     oShowPolicyURL,
250     oNoShowPolicyURL,
251     oSigKeyserverURL,
252     oUseEmbeddedFilename,
253     oNoUseEmbeddedFilename,
254     oComment,
255     oDefaultComment,
256     oNoComments,
257     oThrowKeyids,
258     oNoThrowKeyids,
259     oShowPhotos,
260     oNoShowPhotos,
261     oPhotoViewer,
262     oForceV3Sigs,
263     oNoForceV3Sigs,
264     oForceV4Certs,
265     oNoForceV4Certs,
266     oForceMDC,
267     oNoForceMDC,
268     oDisableMDC,
269     oNoDisableMDC,
270     oS2KMode,
271     oS2KDigest,
272     oS2KCipher,
273     oSimpleSKChecksum,                          
274     oDisplayCharset,
275     oNotDashEscaped,
276     oEscapeFrom,
277     oNoEscapeFrom,
278     oLockOnce,
279     oLockMultiple,
280     oLockNever,
281     oKeyServer,
282     oKeyServerOptions,
283     oImportOptions,
284     oExportOptions,
285     oListOptions,
286     oVerifyOptions,
287     oTempDir,
288     oExecPath,
289     oEncryptTo,
290     oHiddenEncryptTo,
291     oNoEncryptTo,
292     oLoggerFD,
293     oLoggerFile,
294     oUtf8Strings,
295     oNoUtf8Strings,
296     oDisableCipherAlgo,
297     oDisablePubkeyAlgo,
298     oAllowNonSelfsignedUID,
299     oNoAllowNonSelfsignedUID,
300     oAllowFreeformUID,
301     oNoAllowFreeformUID,
302     oAllowSecretKeyImport,                      
303     oEnableSpecialFilenames,
304     oNoLiteral,
305     oSetFilesize,
306     oHonorHttpProxy,
307     oFastListMode,
308     oListOnly,
309     oIgnoreTimeConflict,
310     oIgnoreValidFrom,
311     oIgnoreCrcError,
312     oIgnoreMDCError,
313     oShowSessionKey,
314     oOverrideSessionKey,
315     oNoRandomSeedFile,
316     oAutoKeyRetrieve,
317     oNoAutoKeyRetrieve,
318     oUseAgent,
319     oNoUseAgent,
320     oGpgAgentInfo,
321     oMergeOnly,
322     oTryAllSecrets,
323     oTrustedKey,
324     oNoExpensiveTrustChecks,
325     oFixedListMode,
326     oNoSigCache,
327     oNoSigCreateCheck,
328     oAutoCheckTrustDB,
329     oNoAutoCheckTrustDB,
330     oPreservePermissions,
331     oDefaultPreferenceList,
332     oPersonalCipherPreferences,
333     oPersonalDigestPreferences,
334     oPersonalCompressPreferences,
335     oDisplay,
336     oTTYname,
337     oTTYtype,
338     oLCctype,
339     oLCmessages,
340     oGroup,
341     oUnGroup,
342     oNoGroups,
343     oStrict,
344     oNoStrict,
345     oMangleDosFilenames,
346     oNoMangleDosFilenames,
347     oEnableProgressFilter,
348     oMultifile,
349     oKeyidFormat,
350     oExitOnStatusWriteError,
351     oLimitCardInsertTries,
352
353     oReaderPort,
354     octapiDriver,
355     opcscDriver,
356     oDisableCCID,
357
358     oNoop
359   };
360
361
362 static ARGPARSE_OPTS opts[] = {
363
364     { 300, NULL, 0, N_("@Commands:\n ") },
365
366     { aSign, "sign",      256, N_("|[file]|make a signature")},
367     { aClearsign, "clearsign", 256, N_("|[file]|make a clear text signature")},
368     { aDetachedSign, "detach-sign", 256, N_("make a detached signature")},
369     { aEncr, "encrypt",   256, N_("encrypt data")},
370     { aEncrFiles, "encrypt-files", 256, "@"},
371     { aSym, "symmetric", 256, N_("encryption only with symmetric cipher")},
372     { aStore, "store",     256, "@"},
373     { aDecrypt, "decrypt",   256, N_("decrypt data (default)")},
374     { aDecryptFiles, "decrypt-files", 256, "@"},
375     { aVerify, "verify"   , 256, N_("verify a signature")},
376     { aVerifyFiles, "verify-files" , 256, "@" },
377     { aListKeys, "list-keys", 256, N_("list keys")},
378     { aListKeys, "list-public-keys", 256, "@" },
379     { aListSigs, "list-sigs", 256, N_("list keys and signatures")},
380     { aCheckKeys, "check-sigs",256, N_("list and check key signatures")},
381     { oFingerprint, "fingerprint", 256, N_("list keys and fingerprints")},
382     { aListSecretKeys, "list-secret-keys", 256, N_("list secret keys")},
383     { aKeygen,     "gen-key",  256, N_("generate a new key pair")},
384     { aDeleteKeys,"delete-keys",256,N_("remove keys from the public keyring")},
385     { aDeleteSecretKeys, "delete-secret-keys",256,
386                                     N_("remove keys from the secret keyring")},
387     { aSignKey,  "sign-key"   ,256, N_("sign a key")},
388     { aLSignKey, "lsign-key"  ,256, N_("sign a key locally")},
389     { aEditKey,  "edit-key"   ,256, N_("sign or edit a key")},
390     { aGenRevoke, "gen-revoke",256, N_("generate a revocation certificate")},
391     { aDesigRevoke, "desig-revoke",256, "@" },
392     { aExport, "export"           , 256, N_("export keys") },
393     { aSendKeys, "send-keys"     , 256, N_("export keys to a key server") },
394     { aRecvKeys, "recv-keys"     , 256, N_("import keys from a key server") },
395     { aSearchKeys, "search-keys" , 256,
396                                     N_("search for keys on a key server") },
397     { aRefreshKeys, "refresh-keys", 256,
398                                     N_("update all keys from a keyserver")},
399     { aExportSecret, "export-secret-keys" , 256, "@" },
400     { aExportSecretSub, "export-secret-subkeys" , 256, "@" },
401     { aImport, "import",      256     , N_("import/merge keys")},
402     { aFastImport, "fast-import",  256 , "@"},
403 #ifdef ENABLE_CARD_SUPPORT
404     { aCardStatus,  "card-status", 256, N_("print the card status")},
405     { aCardEdit,   "card-edit",  256, N_("change data on a card")},
406     { aChangePIN,  "change-pin", 256, N_("change a card's PIN")},
407 #endif
408     { aListConfig, "list-config", 256, "@"},
409     { aGPGConfList, "gpgconf-list", 256, "@" },
410     { aListPackets, "list-packets",256, "@"},
411     { aExportOwnerTrust, "export-ownertrust", 256, "@"},
412     { aImportOwnerTrust, "import-ownertrust", 256, "@"},
413     { aUpdateTrustDB,
414               "update-trustdb",0 , N_("update the trust database")},
415     { aCheckTrustDB, "check-trustdb", 0, "@"},
416     { aFixTrustDB, "fix-trustdb", 0, "@"},
417     { aDeArmor, "dearmor", 256, "@"},
418     { aDeArmor, "dearmour", 256, "@"},
419     { aEnArmor, "enarmor", 256, "@"},
420     { aEnArmor, "enarmour", 256, "@"},
421     { aPrintMD,  "print-md" , 256, N_("|algo [files]|print message digests")},
422     { aPrimegen, "gen-prime" , 256, "@" },
423     { aGenRandom, "gen-random" , 256, "@" },
424
425     { 301, NULL, 0, N_("@\nOptions:\n ") },
426
427     { oArmor, "armor",     0, N_("create ascii armored output")},
428     { oArmor, "armour",     0, "@" },
429     { oRecipient, "recipient", 2, N_("|NAME|encrypt for NAME")},
430     { oHiddenRecipient, "hidden-recipient", 2, "@" },
431     { oRecipient, "remote-user", 2, "@"},  /* old option name */
432     { oDefRecipient, "default-recipient", 2, "@"},
433     { oDefRecipientSelf, "default-recipient-self", 0, "@"},
434     { oNoDefRecipient, "no-default-recipient", 0, "@" },
435     { oTempDir, "temp-directory", 2, "@" },
436     { oExecPath, "exec-path", 2, "@" },
437     { oEncryptTo, "encrypt-to", 2, "@" },
438     { oHiddenEncryptTo, "hidden-encrypt-to", 2, "@" },
439     { oNoEncryptTo, "no-encrypt-to", 0, "@" },
440     { oLocalUser, "local-user",2, N_("use this user-id to sign or decrypt")},
441     { oCompress, NULL, 1, N_("|N|set compress level N (0 disables)") },
442     { oCompressLevel, "compress-level", 1, "@" },
443     { oBZ2CompressLevel, "bzip2-compress-level", 1, "@" },
444     { oBZ2DecompressLowmem, "bzip2-decompress-lowmem", 0, "@" },
445     { oTextmodeShort, NULL,   0, "@"},
446     { oTextmode, "textmode",  0, N_("use canonical text mode")},
447     { oNoTextmode, "no-textmode",  0, "@"},
448     { oExpert, "expert",   0, "@"},
449     { oNoExpert, "no-expert",   0, "@"},
450     { oDefSigExpire, "default-sig-expire", 2, "@"},
451     { oAskSigExpire, "ask-sig-expire",   0, "@"},
452     { oNoAskSigExpire, "no-ask-sig-expire",   0, "@"},
453     { oDefCertExpire, "default-cert-expire", 2, "@"},
454     { oAskCertExpire, "ask-cert-expire",   0, "@"},
455     { oNoAskCertExpire, "no-ask-cert-expire",   0, "@"},
456     { oDefCertLevel, "default-cert-level", 1, "@"},
457     { oMinCertLevel, "min-cert-level", 1, "@"},
458     { oAskCertLevel, "ask-cert-level",   0, "@"},
459     { oNoAskCertLevel, "no-ask-cert-level",   0, "@"},
460     { oOutput, "output",    2, N_("use as output file")},
461     { oMaxOutput, "max-output", 16|4, "@" },
462     { oVerbose, "verbose",   0, N_("verbose") },
463     { oQuiet,   "quiet",   0, "@"},
464     { oNoTTY, "no-tty", 0, "@"},
465     { oForceV3Sigs, "force-v3-sigs", 0, "@"},
466     { oNoForceV3Sigs, "no-force-v3-sigs", 0, "@"},
467     { oForceV4Certs, "force-v4-certs", 0, "@"},
468     { oNoForceV4Certs, "no-force-v4-certs", 0, "@"},
469     { oForceMDC, "force-mdc", 0, "@"},
470     { oNoForceMDC, "no-force-mdc", 0, "@" },
471     { oDisableMDC, "disable-mdc", 0, "@"},
472     { oNoDisableMDC, "no-disable-mdc", 0, "@" },
473     { oDryRun, "dry-run",   0, N_("do not make any changes") },
474     { oInteractive, "interactive", 0, N_("prompt before overwriting") },
475     { oUseAgent, "use-agent",0, "@"},
476     { oNoUseAgent, "no-use-agent",0, "@"},
477     { oGpgAgentInfo, "gpg-agent-info",2, "@"},
478     { oBatch, "batch", 0, "@"},
479     { oAnswerYes, "yes", 0, "@"},
480     { oAnswerNo, "no", 0, "@"},
481     { oKeyring, "keyring", 2, "@"},
482     { oPrimaryKeyring, "primary-keyring",2, "@" },
483     { oSecretKeyring, "secret-keyring", 2, "@"},
484     { oShowKeyring, "show-keyring", 0, "@"},
485     { oDefaultKey, "default-key", 2, "@"},
486     { oKeyServer, "keyserver", 2, "@"},
487     { oKeyServerOptions, "keyserver-options",2,"@"},
488     { oImportOptions, "import-options",2,"@"},
489     { oExportOptions, "export-options",2,"@"},
490     { oListOptions, "list-options",2,"@"},
491     { oVerifyOptions, "verify-options",2,"@"},
492     { oDisplayCharset, "display-charset", 2, "@"},
493     { oDisplayCharset, "charset", 2, "@"},
494     { oOptions, "options", 2, "@"},
495     { oDebug, "debug"     ,4|16, "@"},
496     { oDebugAll, "debug-all" ,0, "@"},
497     { oStatusFD, "status-fd" ,1, "@"},
498     { oStatusFile, "status-file" ,2, "@"},
499     { oAttributeFD, "attribute-fd" ,1, "@" },
500     { oAttributeFile, "attribute-file" ,2, "@" },
501     { oNoop, "sk-comments", 0,   "@"},
502     { oNoop, "no-sk-comments", 0,   "@"},
503     { oCompletesNeeded, "completes-needed", 1, "@"},
504     { oMarginalsNeeded, "marginals-needed", 1, "@"},
505     { oMaxCertDepth,    "max-cert-depth", 1, "@" },
506     { oTrustedKey, "trusted-key", 2, "@"},
507     { oLoadExtension, "load-extension", 2, "@"},
508     { oGnuPG, "gnupg",   0, "@"},
509     { oGnuPG, "no-pgp2", 0, "@"},
510     { oGnuPG, "no-pgp6", 0, "@"},
511     { oGnuPG, "no-pgp7", 0, "@"},
512     { oGnuPG, "no-pgp8", 0, "@"},
513     { oRFC1991, "rfc1991",   0, "@"},
514     { oRFC2440, "rfc2440", 0, "@" },
515     { oOpenPGP, "openpgp", 0, N_("use strict OpenPGP behavior")},
516     { oPGP2, "pgp2", 0, N_("generate PGP 2.x compatible messages")},
517     { oPGP6, "pgp6", 0, "@"},
518     { oPGP7, "pgp7", 0, "@"},
519     { oPGP8, "pgp8", 0, "@"},
520     { oRFC2440Text, "rfc2440-text", 0, "@"},
521     { oNoRFC2440Text, "no-rfc2440-text", 0, "@"},
522     { oS2KMode, "s2k-mode", 1, "@"},
523     { oS2KDigest, "s2k-digest-algo", 2, "@"},
524     { oS2KCipher, "s2k-cipher-algo", 2, "@"},
525     { oSimpleSKChecksum, "simple-sk-checksum", 0, "@"},
526     { oCipherAlgo, "cipher-algo", 2, "@"},
527     { oDigestAlgo, "digest-algo", 2, "@"},
528     { oCertDigestAlgo, "cert-digest-algo", 2 , "@" },
529     { oCompressAlgo,"compress-algo", 2, "@"},
530     { oCompressAlgo, "compression-algo", 2, "@"}, /* Alias */
531     { oThrowKeyids, "throw-keyid", 0, "@"},
532     { oThrowKeyids, "throw-keyids", 0, "@"},
533     { oNoThrowKeyids, "no-throw-keyid", 0, "@" },
534     { oNoThrowKeyids, "no-throw-keyids", 0, "@" },
535     { oShowPhotos,   "show-photos", 0, "@" },
536     { oNoShowPhotos, "no-show-photos", 0, "@" },
537     { oPhotoViewer,  "photo-viewer", 2, "@" },
538     { oSetNotation,  "set-notation", 2, "@" },
539     { oSetNotation,  "notation-data", 2, "@" }, /* Alias */
540     { oSigNotation,  "sig-notation", 2, "@" },
541     { oCertNotation, "cert-notation", 2, "@" },
542
543     { 302, NULL, 0, N_(
544   "@\n(See the man page for a complete listing of all commands and options)\n"
545                       )},
546
547     { 303, NULL, 0, N_("@\nExamples:\n\n"
548     " -se -r Bob [file]          sign and encrypt for user Bob\n"
549     " --clearsign [file]         make a clear text signature\n"
550     " --detach-sign [file]       make a detached signature\n"
551     " --list-keys [names]        show keys\n"
552     " --fingerprint [names]      show fingerprints\n"  ) },
553
554   /* hidden options */
555     { aListOwnerTrust, "list-ownertrust", 256, "@"}, /* deprecated */
556     { aPrintMDs, "print-mds" , 256, "@"}, /* old */
557     { aListTrustDB, "list-trustdb",0 , "@"},
558     /* Not yet used */
559     /* { aListTrustPath, "list-trust-path",0, "@"}, */
560     { aPipeMode,  "pipemode", 0, "@" },
561     { oKOption, NULL,    0, "@"},
562     { oPasswd, "passphrase",2, "@" },
563     { oPasswdFD, "passphrase-fd",1, "@" },
564     { oPasswdFile, "passphrase-file",2, "@" },
565     { oCommandFD, "command-fd",1, "@" },
566     { oCommandFile, "command-file",2, "@" },
567     { oQuickRandom, "quick-random", 0, "@"},
568     { oNoVerbose, "no-verbose", 0, "@"},
569     { oTrustDBName, "trustdb-name", 2, "@" },
570     { oNoSecmemWarn, "no-secmem-warning", 0, "@" },
571     { oRequireSecmem,"require-secmem", 0, "@" },
572     { oNoRequireSecmem,"no-require-secmem", 0, "@" },
573     { oNoPermissionWarn, "no-permission-warning", 0, "@" },
574     { oNoMDCWarn, "no-mdc-warning", 0, "@" },
575     { oNoArmor, "no-armor",   0, "@"},
576     { oNoArmor, "no-armour",   0, "@"},
577     { oNoDefKeyring, "no-default-keyring", 0, "@" },
578     { oNoGreeting, "no-greeting", 0, "@" },
579     { oNoOptions, "no-options", 0, "@" }, /* shortcut for --options /dev/null */
580     { oHomedir, "homedir", 2, "@" },   /* defaults to "~/.gnupg" */
581     { oNoBatch, "no-batch", 0, "@" },
582     { oWithColons, "with-colons", 0, "@"},
583     { oWithKeyData,"with-key-data", 0, "@"},
584     { aListKeys, "list-key", 0, "@" }, /* alias */
585     { aListSigs, "list-sig", 0, "@" }, /* alias */
586     { aCheckKeys, "check-sig",0, "@" }, /* alias */
587     { oSkipVerify, "skip-verify",0, "@" },
588     { oCompressKeys, "compress-keys",0, "@"},
589     { oCompressSigs, "compress-sigs",0, "@"},
590     { oDefCertLevel, "default-cert-check-level", 1, "@"}, /* Old option */
591     { oAlwaysTrust, "always-trust", 0, "@"},
592     { oTrustModel, "trust-model", 2, "@"},
593     { oForceOwnertrust, "force-ownertrust", 2, "@"},
594     { oRunAsShmCP, "run-as-shm-coprocess", 4, "@" },
595     { oSetFilename, "set-filename", 2, "@" },
596     { oForYourEyesOnly, "for-your-eyes-only", 0, "@" },
597     { oNoForYourEyesOnly, "no-for-your-eyes-only", 0, "@" },
598     { oSetPolicyURL, "set-policy-url", 2, "@" },
599     { oSigPolicyURL, "sig-policy-url", 2, "@" },
600     { oCertPolicyURL, "cert-policy-url", 2, "@" },
601     { oShowPolicyURL, "show-policy-url", 0, "@" },
602     { oNoShowPolicyURL, "no-show-policy-url", 0, "@" },
603     { oSigKeyserverURL, "sig-keyserver-url", 2, "@" },
604     { oShowNotation, "show-notation", 0, "@" },
605     { oNoShowNotation, "no-show-notation", 0, "@" },
606     { oComment, "comment", 2, "@" },
607     { oDefaultComment, "default-comment", 0, "@" },
608     { oNoComments, "no-comments", 0, "@" },
609     { oEmitVersion, "emit-version", 0, "@"},
610     { oNoEmitVersion, "no-emit-version", 0, "@"},
611     { oNoEmitVersion, "no-version", 0, "@"}, /* alias */
612     { oNotDashEscaped, "not-dash-escaped", 0, "@" },
613     { oEscapeFrom, "escape-from-lines", 0, "@" },
614     { oNoEscapeFrom, "no-escape-from-lines", 0, "@" },
615     { oLockOnce, "lock-once", 0, "@" },
616     { oLockMultiple, "lock-multiple", 0, "@" },
617     { oLockNever, "lock-never", 0, "@" },
618     { oLoggerFD, "logger-fd",1, "@" },
619     { oLoggerFile, "logger-file",2, "@" },
620     { oUseEmbeddedFilename, "use-embedded-filename", 0, "@" },
621     { oNoUseEmbeddedFilename, "no-use-embedded-filename", 0, "@" },
622     { oUtf8Strings, "utf8-strings", 0, "@" },
623     { oNoUtf8Strings, "no-utf8-strings", 0, "@" },
624     { oWithFingerprint, "with-fingerprint", 0, "@" },
625     { oDisableCipherAlgo,  "disable-cipher-algo", 2, "@" },
626     { oDisablePubkeyAlgo,  "disable-pubkey-algo", 2, "@" },
627     { oAllowNonSelfsignedUID, "allow-non-selfsigned-uid", 0, "@" },
628     { oNoAllowNonSelfsignedUID, "no-allow-non-selfsigned-uid", 0, "@" },
629     { oAllowFreeformUID, "allow-freeform-uid", 0, "@" },
630     { oNoAllowFreeformUID, "no-allow-freeform-uid", 0, "@" },
631     { oNoLiteral, "no-literal", 0, "@" },
632     { oSetFilesize, "set-filesize", 20, "@" },
633     { oHonorHttpProxy,"honor-http-proxy", 0, "@" },
634     { oFastListMode,"fast-list-mode", 0, "@" },
635     { oFixedListMode,"fixed-list-mode", 0, "@" },
636     { oListOnly, "list-only", 0, "@"},
637     { oIgnoreTimeConflict, "ignore-time-conflict", 0, "@" },
638     { oIgnoreValidFrom,    "ignore-valid-from",    0, "@" },
639     { oIgnoreCrcError, "ignore-crc-error", 0,"@" },
640     { oIgnoreMDCError, "ignore-mdc-error", 0,"@" },
641     { oShowSessionKey, "show-session-key", 0, "@" },
642     { oOverrideSessionKey, "override-session-key", 2, "@" },
643     { oNoRandomSeedFile,  "no-random-seed-file", 0, "@" },
644     { oAutoKeyRetrieve, "auto-key-retrieve", 0, "@" },
645     { oNoAutoKeyRetrieve, "no-auto-key-retrieve", 0, "@" },
646     { oNoSigCache,         "no-sig-cache", 0, "@" },
647     { oNoSigCreateCheck,   "no-sig-create-check", 0, "@" },
648     { oAutoCheckTrustDB, "auto-check-trustdb", 0, "@"},
649     { oNoAutoCheckTrustDB, "no-auto-check-trustdb", 0, "@"},
650     { oMergeOnly,         "merge-only", 0, "@" },
651     { oAllowSecretKeyImport, "allow-secret-key-import", 0, "@" },
652     { oTryAllSecrets,  "try-all-secrets", 0, "@" },
653     { oEnableSpecialFilenames, "enable-special-filenames", 0, "@" },
654     { oNoExpensiveTrustChecks, "no-expensive-trust-checks", 0, "@" },
655     { aDeleteSecretAndPublicKeys, "delete-secret-and-public-keys",256, "@" },
656     { aRebuildKeydbCaches, "rebuild-keydb-caches", 256, "@"},
657     { oPreservePermissions, "preserve-permissions", 0, "@"},
658     { oDefaultPreferenceList,  "default-preference-list", 2, "@"},
659     { oPersonalCipherPreferences,  "personal-cipher-preferences", 2, "@"},
660     { oPersonalDigestPreferences,  "personal-digest-preferences", 2, "@"},
661     { oPersonalCompressPreferences,  "personal-compress-preferences", 2, "@"},
662     /* Aliases.  I constantly mistype these, and assume other people
663        do as well. */
664     { oPersonalCipherPreferences, "personal-cipher-prefs", 2, "@"},
665     { oPersonalDigestPreferences, "personal-digest-prefs", 2, "@"},
666     { oPersonalCompressPreferences, "personal-compress-prefs", 2, "@"},
667     { oDisplay,    "display",     2, "@" },
668     { oTTYname,    "ttyname",     2, "@" },
669     { oTTYtype,    "ttytype",     2, "@" },
670     { oLCctype,    "lc-ctype",    2, "@" },
671     { oLCmessages, "lc-messages", 2, "@" },
672     { oGroup,      "group",       2, "@" },
673     { oUnGroup,    "ungroup",     2, "@" },
674     { oNoGroups,   "no-groups",    0, "@" },
675     { oStrict,     "strict",      0, "@" },
676     { oNoStrict,   "no-strict",   0, "@" },
677     { oMangleDosFilenames, "mangle-dos-filenames", 0, "@" },
678     { oNoMangleDosFilenames, "no-mangle-dos-filenames", 0, "@" },
679     { oEnableProgressFilter, "enable-progress-filter", 0, "@" },
680     { oMultifile, "multifile", 0, "@" },
681     { oKeyidFormat, "keyid-format", 2, "@" },
682     { oExitOnStatusWriteError, "exit-on-status-write-error", 0, "@" },
683     { oLimitCardInsertTries, "limit-card-insert-tries", 1, "@"},
684
685     { oReaderPort, "reader-port",    2, "@"},
686     { octapiDriver, "ctapi-driver",  2, "@"},
687     { opcscDriver, "pcsc-driver",    2, "@"},
688     { oDisableCCID, "disable-ccid", 0, "@"},
689 #if defined(ENABLE_CARD_SUPPORT) && defined(HAVE_LIBUSB)
690     { oDebugCCIDDriver, "debug-ccid-driver", 0, "@"},
691 #endif
692     /* These are aliases to help users of the PGP command line product
693        use gpg with minimal pain.  Many commands are common already as
694        they seem to have borrowed commands from us.  Now I'm returning
695        the favor. */
696     { oLocalUser, "sign-with", 2, "@" },
697     { oRecipient, "user", 2, "@" },
698     {0,NULL,0,NULL}
699 };
700
701
702 #ifdef ENABLE_SELINUX_HACKS
703 #define ALWAYS_ADD_KEYRINGS 1
704 #else
705 #define ALWAYS_ADD_KEYRINGS 0
706 #endif
707
708
709 int g10_errors_seen = 0;
710
711 static int utf8_strings = 0;
712 static int maybe_setuid = 1;
713
714 static char *build_list( const char *text, char letter,
715                          const char *(*mapf)(int), int (*chkf)(int) );
716 static void set_cmd( enum cmd_and_opt_values *ret_cmd,
717                         enum cmd_and_opt_values new_cmd );
718 static void print_mds( const char *fname, int algo );
719 static void add_notation_data( const char *string, int which );
720 static void add_policy_url( const char *string, int which );
721 static void add_keyserver_url( const char *string, int which );
722
723 const char *
724 strusage( int level )
725 {
726   static char *digests, *pubkeys, *ciphers, *zips;
727     const char *p;
728     switch( level ) {
729       case 11: p = "gpg (GnuPG)";
730         break;
731       case 13: p = VERSION; break;
732       case 17: p = PRINTABLE_OS_NAME; break;
733       case 19: p =
734             _("Please report bugs to <gnupg-bugs@gnu.org>.\n");
735         break;
736
737 #ifdef IS_DEVELOPMENT_VERSION
738       case 20:
739         p="NOTE: THIS IS A DEVELOPMENT VERSION!";
740         break;
741       case 21:
742         p="It is only intended for test purposes and should NOT be";
743         break;
744       case 22:
745         p="used in a production environment or with production keys!";
746         break;
747 #endif
748
749       case 1:
750       case 40:  p =
751             _("Usage: gpg [options] [files] (-h for help)");
752         break;
753       case 41:  p =
754             _("Syntax: gpg [options] [files]\n"
755               "sign, check, encrypt or decrypt\n"
756               "default operation depends on the input data\n");
757         break;
758
759       case 31: p = "\nHome: "; break;
760 #ifndef __riscos__
761       case 32: p = opt.homedir; break;
762 #else /* __riscos__ */
763       case 32: p = make_filename(opt.homedir, NULL); break;
764 #endif /* __riscos__ */
765       case 33: p = _("\nSupported algorithms:\n"); break;
766       case 34:
767         if( !pubkeys )
768             pubkeys = build_list(_("Pubkey: "), 0, pubkey_algo_to_string,
769                                                         check_pubkey_algo );
770         p = pubkeys;
771         break;
772       case 35:
773         if( !ciphers )
774             ciphers = build_list(_("Cipher: "), 'S', cipher_algo_to_string,
775                                                         check_cipher_algo );
776         p = ciphers;
777         break;
778       case 36:
779         if( !digests )
780             digests = build_list(_("Hash: "), 'H', digest_algo_to_string,
781                                                         check_digest_algo );
782         p = digests;
783         break;
784       case 37:
785         if( !zips )
786             zips = build_list(_("Compression: "),'Z',compress_algo_to_string,
787                                                         check_compress_algo);
788         p = zips;
789         break;
790
791       default:  p = default_strusage(level);
792     }
793     return p;
794 }
795
796
797 static char *
798 build_list( const char *text, char letter,
799             const char * (*mapf)(int), int (*chkf)(int) )
800 {
801     int i;
802     const char *s;
803     size_t n=strlen(text)+2;
804     char *list, *p, *line=NULL;
805
806     if( maybe_setuid )
807         secmem_init( 0 );    /* drop setuid */
808
809     for(i=0; i <= 110; i++ )
810         if( !chkf(i) && (s=mapf(i)) )
811             n += strlen(s) + 7 + 2;
812     list = xmalloc( 21 + n ); *list = 0;
813     for(p=NULL, i=0; i <= 110; i++ ) {
814         if( !chkf(i) && (s=mapf(i)) ) {
815             if( !p ) {
816                 p = stpcpy( list, text );
817                 line=p;
818             }
819             else
820                 p = stpcpy( p, ", ");
821
822             if(strlen(line)>60) {
823               int spaces=strlen(text);
824
825               list=xrealloc(list,n+spaces+1);
826               /* realloc could move the block, so find the end again */
827               p=list;
828               while(*p)
829                 p++;
830
831               p=stpcpy(p, "\n");
832               line=p;
833               for(;spaces;spaces--)
834                 p=stpcpy(p, " ");
835             }
836
837             p = stpcpy(p, s );
838             if(opt.verbose && letter)
839               {
840                 char num[8];
841                 sprintf(num," (%c%d)",letter,i);
842                 p = stpcpy(p,num);
843               }
844         }
845     }
846     if( p )
847         p = stpcpy(p, "\n" );
848     return list;
849 }
850
851
852 static void
853 i18n_init(void)
854 {
855 #ifdef USE_SIMPLE_GETTEXT
856     set_gettext_file (PACKAGE, "Software\\GNU\\GnuPG");
857 #else
858 #ifdef ENABLE_NLS
859     setlocale( LC_ALL, "" );
860     bindtextdomain( PACKAGE, G10_LOCALEDIR );
861     textdomain( PACKAGE );
862 #endif
863 #endif
864 }
865
866 static void
867 wrong_args( const char *text)
868 {
869     fputs(_("usage: gpg [options] "),stderr);
870     fputs(text,stderr);
871     putc('\n',stderr);
872     g10_exit(2);
873 }
874
875
876 static char *
877 make_username( const char *string )
878 {
879     char *p;
880     if( utf8_strings )
881         p = xstrdup(string);
882     else
883         p = native_to_utf8( string );
884     return p;
885 }
886
887
888 static void
889 set_debug(void)
890 {
891     if( opt.debug & DBG_MEMORY_VALUE )
892         memory_debug_mode = 1;
893     if( opt.debug & DBG_MEMSTAT_VALUE )
894         memory_stat_debug_mode = 1;
895     if( opt.debug & DBG_MPI_VALUE )
896         mpi_debug_mode = 1;
897     if( opt.debug & DBG_CIPHER_VALUE )
898         g10c_debug_mode = 1;
899     if( opt.debug & DBG_IOBUF_VALUE )
900         iobuf_debug_mode = 1;
901
902 }
903
904
905 /* We need the home directory also in some other directories, so make
906    sure that both variables are always in sync. */
907 static void
908 set_homedir (char *dir)
909 {
910   if (!dir)
911     dir = "";
912   g10_opt_homedir = opt.homedir = dir;
913 }
914
915
916 /* We set the screen dimensions for UI purposes.  Do not allow screens
917    smaller than 80x24 for the sake of simplicity. */
918 static void
919 set_screen_dimensions(void)
920 {
921 #ifndef _WIN32
922   char *str;
923
924   str=getenv("COLUMNS");
925   if(str)
926     opt.screen_columns=atoi(str);
927
928   str=getenv("LINES");
929   if(str)
930     opt.screen_lines=atoi(str);
931 #endif
932
933   if(opt.screen_columns<80 || opt.screen_columns>255)
934     opt.screen_columns=80;
935
936   if(opt.screen_lines<24 || opt.screen_lines>255)
937     opt.screen_lines=24;
938 }
939
940
941 /* Helper to open a file FNAME either for reading or writing to be
942    used with --status-file etc functions.  Not generally useful but it
943    avoids the riscos specific functions and well some Windows people
944    might like it too.  Prints an error message and returns -1 on
945    error. On success the file descriptor is returned.  */
946 static int
947 open_info_file (const char *fname, int for_write)
948 {
949 #ifdef __riscos__
950   return riscos_fdopenfile (fname, for_write);
951 #elif defined (ENABLE_SELINUX_HACKS)
952   /* We can't allow these even when testing for a secured filename
953      because files to be secured might not yet been secured.  This is
954      similar to the option file but in that case it is unlikely that
955      sensitive information may be retrieved by means of error
956      messages.  */
957   return -1;
958 #else 
959   int fd;
960
961 /*   if (is_secured_filename (fname)) */
962 /*     { */
963 /*       fd = -1; */
964 /*       errno = EPERM; */
965 /*     } */
966 /*   else */
967 /*     { */
968       do
969         {
970           if (for_write)
971             fd = open (fname, O_CREAT | O_TRUNC | O_WRONLY,
972                         S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP);
973           else
974             fd = open (fname, O_RDONLY | MY_O_BINARY);
975         }
976       while (fd == -1 && errno == EINTR);
977 /*     } */
978   if ( fd == -1)
979     log_error ( for_write? _("can't create `%s': %s\n")
980                          : _("can't open `%s': %s\n"), fname, strerror(errno));
981   
982   return fd;
983 #endif
984 }
985
986 static void
987 set_cmd( enum cmd_and_opt_values *ret_cmd, enum cmd_and_opt_values new_cmd )
988 {
989     enum cmd_and_opt_values cmd = *ret_cmd;
990
991     if( !cmd || cmd == new_cmd )
992         cmd = new_cmd;
993     else if( cmd == aSign && new_cmd == aEncr )
994         cmd = aSignEncr;
995     else if( cmd == aEncr && new_cmd == aSign )
996         cmd = aSignEncr;
997     else if( cmd == aSign && new_cmd == aSym )
998         cmd = aSignSym;
999     else if( cmd == aSym && new_cmd == aSign )
1000         cmd = aSignSym;
1001     else if( cmd == aSym && new_cmd == aEncr )
1002         cmd = aEncrSym;
1003     else if( cmd == aEncr && new_cmd == aSym )
1004         cmd = aEncrSym;
1005     else if( cmd == aKMode && new_cmd == aSym )
1006         cmd = aKModeC;
1007     else if (cmd == aSignEncr && new_cmd == aSym)
1008         cmd = aSignEncrSym;
1009     else if (cmd == aSignSym && new_cmd == aEncr)
1010         cmd = aSignEncrSym;
1011     else if (cmd == aEncrSym && new_cmd == aSign)
1012         cmd = aSignEncrSym;
1013     else if(    ( cmd == aSign     && new_cmd == aClearsign )
1014              || ( cmd == aClearsign && new_cmd == aSign )  )
1015         cmd = aClearsign;
1016     else {
1017         log_error(_("conflicting commands\n"));
1018         g10_exit(2);
1019     }
1020
1021     *ret_cmd = cmd;
1022 }
1023
1024
1025 static void
1026 add_group(char *string)
1027 {
1028   char *name,*value;
1029   struct groupitem *item;
1030
1031   /* Break off the group name */
1032   name=strsep(&string,"=");
1033   if(string==NULL)
1034     {
1035       log_error(_("no = sign found in group definition `%s'\n"),name);
1036       return;
1037     }
1038
1039   trim_trailing_ws(name,strlen(name));
1040
1041   /* Does this group already exist? */
1042   for(item=opt.grouplist;item;item=item->next)
1043     if(strcasecmp(item->name,name)==0)
1044       break;
1045
1046   if(!item)
1047     {
1048       item=xmalloc(sizeof(struct groupitem));
1049       item->name=name;
1050       item->next=opt.grouplist;
1051       item->values=NULL;
1052       opt.grouplist=item;
1053     }
1054
1055   /* Break apart the values */
1056   while ((value= strsep(&string," \t")))
1057     {
1058       if (*value)
1059         add_to_strlist2(&item->values,value,utf8_strings);
1060     }
1061 }
1062
1063
1064 static void
1065 rm_group(char *name)
1066 {
1067   struct groupitem *item,*last=NULL;
1068
1069   trim_trailing_ws(name,strlen(name));
1070
1071   for(item=opt.grouplist;item;last=item,item=item->next)
1072     {
1073       if(strcasecmp(item->name,name)==0)
1074         {
1075           if(last)
1076             last->next=item->next;
1077           else
1078             opt.grouplist=item->next;
1079
1080           free_strlist(item->values);
1081           xfree(item);
1082           break;
1083         }
1084     }
1085 }
1086
1087
1088 /* We need to check three things.
1089
1090    0) The homedir.  It must be x00, a directory, and owned by the
1091    user.
1092
1093    1) The options/gpg.conf file.  Okay unless it or its containing
1094    directory is group or other writable or not owned by us.  Disable
1095    exec in this case.
1096
1097    2) Extensions.  Same as #1.
1098
1099    Returns true if the item is unsafe. */
1100 static int
1101 check_permissions(const char *path,int item)
1102 {
1103 #if defined(HAVE_STAT) && !defined(HAVE_DOSISH_SYSTEM)
1104   static int homedir_cache=-1;
1105   char *tmppath,*dir;
1106   struct stat statbuf,dirbuf;
1107   int homedir=0,ret=0,checkonly=0;
1108   int perm=0,own=0,enc_dir_perm=0,enc_dir_own=0;
1109
1110   if(opt.no_perm_warn)
1111     return 0;
1112
1113   assert(item==0 || item==1 || item==2);
1114
1115   /* extensions may attach a path */
1116   if(item==2 && path[0]!=DIRSEP_C)
1117     {
1118       if(strchr(path,DIRSEP_C))
1119         tmppath=make_filename(path,NULL);
1120       else
1121         tmppath=make_filename(GNUPG_LIBDIR,path,NULL);
1122     }
1123   else
1124     tmppath=xstrdup(path);
1125
1126   /* If the item is located in the homedir, but isn't the homedir,
1127      don't continue if we already checked the homedir itself.  This is
1128      to avoid user confusion with an extra options file warning which
1129      could be rectified if the homedir itself had proper
1130      permissions. */
1131   if(item!=0 && homedir_cache>-1
1132      && ascii_strncasecmp(opt.homedir,tmppath,strlen(opt.homedir))==0)
1133     {
1134       ret=homedir_cache;
1135       goto end;
1136     }
1137
1138   /* It's okay if the file or directory doesn't exist */
1139   if(stat(tmppath,&statbuf)!=0)
1140     {
1141       ret=0;
1142       goto end;
1143     }
1144
1145   /* Now check the enclosing directory.  Theoretically, we could walk
1146      this test up to the root directory /, but for the sake of sanity,
1147      I'm stopping at one level down. */
1148   dir=make_dirname(tmppath);
1149
1150   if(stat(dir,&dirbuf)!=0 || !S_ISDIR(dirbuf.st_mode))
1151     {
1152       /* Weird error */
1153       ret=1;
1154       goto end;
1155     }
1156
1157   xfree(dir);
1158
1159   /* Assume failure */
1160   ret=1;
1161
1162   if(item==0)
1163     {
1164       /* The homedir must be x00, a directory, and owned by the user. */
1165
1166       if(S_ISDIR(statbuf.st_mode))
1167         {
1168           if(statbuf.st_uid==getuid())
1169             {
1170               if((statbuf.st_mode & (S_IRWXG|S_IRWXO))==0)
1171                 ret=0;
1172               else
1173                 perm=1;
1174             }
1175           else
1176             own=1;
1177
1178           homedir_cache=ret;
1179         }
1180     }
1181   else if(item==1 || item==2)
1182     {
1183       /* The options or extension file.  Okay unless it or its
1184          containing directory is group or other writable or not owned
1185          by us or root. */
1186
1187       if(S_ISREG(statbuf.st_mode))
1188         {
1189           if(statbuf.st_uid==getuid() || statbuf.st_uid==0)
1190             {
1191               if((statbuf.st_mode & (S_IWGRP|S_IWOTH))==0)
1192                 {
1193                   /* it's not writable, so make sure the enclosing
1194                      directory is also not writable */
1195                   if(dirbuf.st_uid==getuid() || dirbuf.st_uid==0)
1196                     {
1197                       if((dirbuf.st_mode & (S_IWGRP|S_IWOTH))==0)
1198                         ret=0;
1199                       else
1200                         enc_dir_perm=1;
1201                     }
1202                   else
1203                     enc_dir_own=1;
1204                 }
1205               else
1206                 {
1207                   /* it's writable, so the enclosing directory had
1208                      better not let people get to it. */
1209                   if(dirbuf.st_uid==getuid() || dirbuf.st_uid==0)
1210                     {
1211                       if((dirbuf.st_mode & (S_IRWXG|S_IRWXO))==0)
1212                         ret=0;
1213                       else
1214                         perm=enc_dir_perm=1; /* unclear which one to fix! */
1215                     }
1216                   else
1217                     enc_dir_own=1;
1218                 }
1219             }
1220           else
1221             own=1;
1222         }
1223     }
1224   else
1225     BUG();
1226
1227   if(!checkonly)
1228     {
1229       if(own)
1230         {
1231           if(item==0)
1232             log_info(_("WARNING: unsafe ownership on"
1233                        " homedir `%s'\n"),tmppath);
1234           else if(item==1)
1235             log_info(_("WARNING: unsafe ownership on"
1236                        " configuration file `%s'\n"),tmppath);
1237           else
1238             log_info(_("WARNING: unsafe ownership on"
1239                        " extension `%s'\n"),tmppath);
1240         }
1241       if(perm)
1242         {
1243           if(item==0)
1244             log_info(_("WARNING: unsafe permissions on"
1245                        " homedir `%s'\n"),tmppath);
1246           else if(item==1)
1247             log_info(_("WARNING: unsafe permissions on"
1248                        " configuration file `%s'\n"),tmppath);
1249           else
1250             log_info(_("WARNING: unsafe permissions on"
1251                        " extension `%s'\n"),tmppath);
1252         }
1253       if(enc_dir_own)
1254         {
1255           if(item==0)
1256             log_info(_("WARNING: unsafe enclosing directory ownership on"
1257                        " homedir `%s'\n"),tmppath);
1258           else if(item==1)
1259             log_info(_("WARNING: unsafe enclosing directory ownership on"
1260                        " configuration file `%s'\n"),tmppath);
1261           else
1262             log_info(_("WARNING: unsafe enclosing directory ownership on"
1263                        " extension `%s'\n"),tmppath);
1264         }
1265       if(enc_dir_perm)
1266         {
1267           if(item==0)
1268             log_info(_("WARNING: unsafe enclosing directory permissions on"
1269                        " homedir `%s'\n"),tmppath);
1270           else if(item==1)
1271             log_info(_("WARNING: unsafe enclosing directory permissions on"
1272                        " configuration file `%s'\n"),tmppath);
1273           else
1274             log_info(_("WARNING: unsafe enclosing directory permissions on"
1275                        " extension `%s'\n"),tmppath);
1276         }
1277     }
1278
1279  end:
1280   xfree(tmppath);
1281
1282   if(homedir)
1283     homedir_cache=ret;
1284
1285   return ret;
1286
1287 #endif /* HAVE_STAT && !HAVE_DOSISH_SYSTEM */
1288
1289   return 0;
1290 }
1291
1292
1293 static void
1294 print_algo_numbers(int (*checker)(int))
1295 {
1296   int i,first=1;
1297
1298   for(i=0;i<=110;i++)
1299     {
1300       if(!checker(i))
1301         {
1302           if(first)
1303             first=0;
1304           else
1305             printf(";");
1306           printf("%d",i);
1307         }
1308     }
1309 }
1310
1311
1312 /* In the future, we can do all sorts of interesting configuration
1313    output here.  For now, just give "group" as the Enigmail folks need
1314    it, and pubkey, cipher, hash, and compress as they may be useful
1315    for frontends. */
1316 static void
1317 list_config(char *items)
1318 {
1319   int show_all=(items==NULL);
1320   char *name=NULL;
1321
1322   if(!opt.with_colons)
1323     return;
1324
1325   while(show_all || (name=strsep(&items," ")))
1326     {
1327       int any=0;
1328
1329       if(show_all || ascii_strcasecmp(name,"group")==0)
1330         {
1331           struct groupitem *iter;
1332
1333           for(iter=opt.grouplist;iter;iter=iter->next)
1334             {
1335               STRLIST sl;
1336
1337               printf("cfg:group:");
1338               print_string(stdout,iter->name,strlen(iter->name),':');
1339               printf(":");
1340
1341               for(sl=iter->values;sl;sl=sl->next)
1342                 {
1343                   print_string2(stdout,sl->d,strlen(sl->d),':',';');
1344                   if(sl->next)
1345                     printf(";");
1346                 }
1347
1348               printf("\n");
1349             }
1350
1351           any=1;
1352         }
1353
1354       if(show_all || ascii_strcasecmp(name,"version")==0)
1355         {
1356           printf("cfg:version:");
1357           print_string(stdout,VERSION,strlen(VERSION),':');
1358           printf("\n");
1359           any=1;
1360         }
1361
1362       if(show_all || ascii_strcasecmp(name,"pubkey")==0)
1363         {
1364           printf("cfg:pubkey:");
1365           print_algo_numbers(check_pubkey_algo);
1366           printf("\n");
1367           any=1;
1368         }
1369
1370       if(show_all || ascii_strcasecmp(name,"cipher")==0)
1371         {
1372           printf("cfg:cipher:");
1373           print_algo_numbers(check_cipher_algo);
1374           printf("\n");
1375           any=1;
1376         }
1377
1378       if(show_all
1379          || ascii_strcasecmp(name,"digest")==0
1380          || ascii_strcasecmp(name,"hash")==0)
1381         {
1382           printf("cfg:digest:");
1383           print_algo_numbers(check_digest_algo);
1384           printf("\n");
1385           any=1;
1386         }
1387
1388       if(show_all || ascii_strcasecmp(name,"compress")==0)
1389         {
1390           printf("cfg:compress:");
1391           print_algo_numbers(check_compress_algo);
1392           printf("\n");
1393           any=1;
1394         }
1395
1396       if(show_all || ascii_strcasecmp(name,"ccid-reader-id")==0)
1397         {
1398 #if defined(ENABLE_CARD_SUPPORT) && defined(HAVE_LIBUSB)
1399           char *p, *p2, *list = ccid_get_reader_list ();
1400
1401           for (p=list; p && (p2 = strchr (p, '\n')); p = p2+1)
1402             {
1403               *p2 = 0;
1404               printf("cfg:ccid-reader-id:%s\n", p);
1405             }
1406           free (list);
1407 #endif
1408           any=1;
1409         }
1410
1411       if(show_all)
1412         break;
1413
1414       if(!any)
1415         log_error(_("unknown configuration item `%s'\n"),name);
1416     }
1417 }
1418
1419
1420 /* List options and default values in the GPG Conf format.  This is a
1421    new tool distributed with gnupg 1.9.x but we also want some limited
1422    support in older gpg versions.  The output is the name of the
1423    configuration file and a list of options available for editing by
1424    gpgconf.  */
1425 static void
1426 gpgconf_list (const char *configfile)
1427 {
1428   /* The following definitions are taken from gnupg/tools/gpgconf-comp.c.  */
1429 #define GC_OPT_FLAG_NONE        0UL
1430 #define GC_OPT_FLAG_DEFAULT     (1UL << 4)
1431
1432   printf ("gpgconf-gpg.conf:%lu:\"%s\n",
1433           GC_OPT_FLAG_DEFAULT,configfile?configfile:"/dev/null");
1434   printf ("verbose:%lu:\n", GC_OPT_FLAG_NONE);
1435   printf ("quiet:%lu:\n",   GC_OPT_FLAG_NONE);
1436   printf ("keyserver:%lu:\n", GC_OPT_FLAG_NONE);
1437   printf ("reader-port:%lu:\n", GC_OPT_FLAG_NONE);
1438 }
1439
1440
1441 static int
1442 parse_subpacket_list(char *list)
1443 {
1444   char *tok;
1445   byte subpackets[128],i;
1446   int count=0;
1447
1448   if(!list)
1449     {
1450       /* No arguments means all subpackets */
1451       memset(subpackets+1,1,sizeof(subpackets)-1);
1452       count=127;
1453     }
1454   else
1455     {
1456       memset(subpackets,0,sizeof(subpackets));
1457
1458       /* Merge with earlier copy */
1459       if(opt.show_subpackets)
1460         {
1461           byte *in;
1462
1463           for(in=opt.show_subpackets;*in;in++)
1464             {
1465               if(*in>127 || *in<1)
1466                 BUG();
1467
1468               if(!subpackets[*in])
1469                 count++;
1470               subpackets[*in]=1;
1471             }
1472         }
1473
1474       while((tok=strsep(&list," ,")))
1475         {
1476           if(!*tok)
1477             continue;
1478
1479           i=atoi(tok);
1480           if(i>127 || i<1)
1481             return 0;
1482
1483           if(!subpackets[i])
1484             count++;
1485           subpackets[i]=1;
1486         }
1487     }
1488
1489   xfree(opt.show_subpackets);
1490   opt.show_subpackets=xmalloc(count+1);
1491   opt.show_subpackets[count--]=0;
1492
1493   for(i=1;i<128 && count>=0;i++)
1494     if(subpackets[i])
1495       opt.show_subpackets[count--]=i;
1496
1497   return 1;
1498 }
1499
1500
1501 static int
1502 parse_list_options(char *str)
1503 {
1504   char *subpackets=""; /* something that isn't NULL */
1505   struct parse_options lopts[]=
1506     {
1507       {"show-photos",LIST_SHOW_PHOTOS,NULL,
1508        N_("display photo IDs during key listings")},
1509       {"show-policy-urls",LIST_SHOW_POLICY_URLS,NULL,
1510        N_("show policy URLs during signature listings")},
1511       {"show-notations",LIST_SHOW_NOTATIONS,NULL,
1512        N_("show all notations during signature listings")},
1513       {"show-std-notations",LIST_SHOW_STD_NOTATIONS,NULL,
1514        N_("show IETF standard notations during signature listings")},
1515       {"show-standard-notations",LIST_SHOW_STD_NOTATIONS,NULL,
1516        NULL},
1517       {"show-user-notations",LIST_SHOW_USER_NOTATIONS,NULL,
1518        N_("show user-supplied notations during signature listings")},
1519       {"show-keyserver-urls",LIST_SHOW_KEYSERVER_URLS,NULL,
1520        N_("show preferred keyserver URLs during signature listings")},
1521       {"show-uid-validity",LIST_SHOW_UID_VALIDITY,NULL,
1522        N_("show user ID validity during key listings")},
1523       {"show-unusable-uids",LIST_SHOW_UNUSABLE_UIDS,NULL,
1524        N_("show revoked and expired user IDs in key listings")},
1525       {"show-unusable-subkeys",LIST_SHOW_UNUSABLE_SUBKEYS,NULL,
1526        N_("show revoked and expired subkeys in key listings")},
1527       {"show-keyring",LIST_SHOW_KEYRING,NULL,
1528        N_("show the keyring name in key listings")},
1529       {"show-sig-expire",LIST_SHOW_SIG_EXPIRE,NULL,
1530        N_("show expiration dates during signature listings")},
1531       {"show-sig-subpackets",LIST_SHOW_SIG_SUBPACKETS,NULL,
1532        NULL},
1533       {NULL,0,NULL,NULL}
1534     };
1535
1536   /* C99 allows for non-constant initializers, but we'd like to
1537      compile everywhere, so fill in the show-sig-subpackets argument
1538      here.  Note that if the parse_options array changes, we'll have
1539      to change the subscript here. */
1540   lopts[12].value=&subpackets;
1541
1542   if(parse_options(str,&opt.list_options,lopts,1))
1543     {
1544       if(opt.list_options&LIST_SHOW_SIG_SUBPACKETS)
1545         {
1546           /* Unset so users can pass multiple lists in. */
1547           opt.list_options&=~LIST_SHOW_SIG_SUBPACKETS;
1548           if(!parse_subpacket_list(subpackets))
1549             return 0;
1550         }
1551       else if(subpackets==NULL && opt.show_subpackets)
1552         {
1553           /* User did 'no-show-subpackets' */
1554           xfree(opt.show_subpackets);
1555           opt.show_subpackets=NULL;
1556         }
1557
1558       return 1;
1559     }
1560   else
1561     return 0;
1562 }
1563
1564
1565 /* Collapses argc/argv into a single string that must be freed */
1566 static char *
1567 collapse_args(int argc,char *argv[])
1568 {
1569   char *str=NULL;
1570   int i,first=1,len=0;
1571
1572   for(i=0;i<argc;i++)
1573     {
1574       len+=strlen(argv[i])+2;
1575       str=xrealloc(str,len);
1576       if(first)
1577         {
1578           str[0]='\0';
1579           first=0;
1580         }
1581       else
1582         strcat(str," ");
1583
1584       strcat(str,argv[i]);
1585     }
1586
1587   return str;
1588 }
1589
1590 static void
1591 parse_trust_model(const char *model)
1592 {
1593   if(ascii_strcasecmp(model,"pgp")==0)
1594     opt.trust_model=TM_PGP;
1595   else if(ascii_strcasecmp(model,"classic")==0)
1596     opt.trust_model=TM_CLASSIC;
1597   else if(ascii_strcasecmp(model,"always")==0)
1598     opt.trust_model=TM_ALWAYS;
1599   else if(ascii_strcasecmp(model,"direct")==0)
1600     opt.trust_model=TM_DIRECT;
1601   else if(ascii_strcasecmp(model,"auto")==0)
1602     opt.trust_model=TM_AUTO;
1603   else
1604     log_error("unknown trust model `%s'\n",model);
1605 }
1606
1607 int
1608 main (int argc, char **argv )
1609 {
1610     ARGPARSE_ARGS pargs;
1611     IOBUF a;
1612     int rc=0;
1613     int orig_argc;
1614     char **orig_argv;
1615     const char *fname;
1616     char *username;
1617     int may_coredump;
1618     STRLIST sl, remusr= NULL, locusr=NULL;
1619     STRLIST nrings=NULL, sec_nrings=NULL;
1620     armor_filter_context_t afx;
1621     int detached_sig = 0;
1622     FILE *configfp = NULL;
1623     char *configname = NULL;
1624     char *save_configname = NULL;
1625     unsigned configlineno;
1626     int parse_debug = 0;
1627     int default_config = 1;
1628     int default_keyring = 1;
1629     int greeting = 0;
1630     int nogreeting = 0;
1631     int use_random_seed = 1;
1632     enum cmd_and_opt_values cmd = 0;
1633     const char *trustdb_name = NULL;
1634     char *def_cipher_string = NULL;
1635     char *def_digest_string = NULL;
1636     char *compress_algo_string = NULL;
1637     char *cert_digest_string = NULL;
1638     char *s2k_cipher_string = NULL;
1639     char *s2k_digest_string = NULL;
1640     char *pers_cipher_list = NULL;
1641     char *pers_digest_list = NULL;
1642     char *pers_compress_list = NULL;
1643     int eyes_only=0;
1644     int multifile=0;
1645     int pwfd = -1;
1646     int with_fpr = 0; /* make an option out of --fingerprint */
1647     int any_explicit_recipient = 0;
1648     int require_secmem=0,got_secmem=0;
1649 #ifdef USE_SHM_COPROCESSING
1650     ulong requested_shm_size=0;
1651 #endif
1652
1653 #ifdef __riscos__
1654     opt.lock_once = 1;
1655 #endif /* __riscos__ */
1656
1657     trap_unaligned();
1658     secmem_set_flags( secmem_get_flags() | 2 ); /* suspend warnings */
1659     /* Please note that we may running SUID(ROOT), so be very CAREFUL
1660      * when adding any stuff between here and the call to
1661      * secmem_init()  somewhere after the option parsing
1662      */
1663     log_set_name("gpg");
1664     secure_randoxmalloc(); /* put random number into secure memory */
1665     may_coredump = disable_core_dumps();
1666     init_signals();
1667     create_dotlock(NULL); /* register locking cleanup */
1668     i18n_init();
1669     opt.command_fd = -1; /* no command fd */
1670     opt.compress_level = -1; /* defaults to standard compress level */
1671     opt.bz2_compress_level = -1; /* defaults to standard compress level */
1672     /* note: if you change these lines, look at oOpenPGP */
1673     opt.def_cipher_algo = 0;
1674     opt.def_digest_algo = 0;
1675     opt.cert_digest_algo = 0;
1676     opt.compress_algo = -1; /* defaults to DEFAULT_COMPRESS_ALGO */
1677     opt.s2k_mode = 3; /* iterated+salted */
1678 #ifdef USE_CAST5
1679     opt.s2k_cipher_algo = CIPHER_ALGO_CAST5;
1680 #else
1681     opt.s2k_cipher_algo = CIPHER_ALGO_3DES;
1682 #endif
1683     opt.completes_needed = 1;
1684     opt.marginals_needed = 3;
1685     opt.max_cert_depth = 5;
1686     opt.pgp2_workarounds = 1;
1687     opt.force_v3_sigs = 1;
1688     opt.escape_from = 1;
1689     opt.import_options=IMPORT_SK2PK;
1690     opt.export_options=EXPORT_ATTRIBUTES;
1691     opt.keyserver_options.import_options=IMPORT_REPAIR_PKS_SUBKEY_BUG;
1692     opt.keyserver_options.export_options=EXPORT_ATTRIBUTES;
1693     opt.keyserver_options.options=
1694       KEYSERVER_INCLUDE_SUBKEYS|KEYSERVER_INCLUDE_REVOKED|KEYSERVER_TRY_DNS_SRV|KEYSERVER_HONOR_KEYSERVER_URL;
1695     opt.verify_options=
1696       VERIFY_SHOW_POLICY_URLS|VERIFY_SHOW_STD_NOTATIONS|VERIFY_SHOW_KEYSERVER_URLS;
1697     opt.trust_model=TM_AUTO;
1698     opt.mangle_dos_filenames=0;
1699     opt.min_cert_level=2;
1700     set_screen_dimensions();
1701     opt.keyid_format=KF_SHORT;
1702     opt.rfc2440_text=1;
1703     opt.def_sig_expire="0";
1704     opt.def_cert_expire="0";
1705     set_homedir ( default_homedir () );
1706
1707 #ifdef ENABLE_CARD_SUPPORT
1708 # ifdef _WIN32
1709     opt.pcsc_driver = "winscard.dll"; 
1710 #else
1711     opt.pcsc_driver = "libpcsclite.so"; 
1712 #endif
1713 #endif /*ENABLE_CARD_SUPPORT*/
1714
1715     /* check whether we have a config file on the commandline */
1716     orig_argc = argc;
1717     orig_argv = argv;
1718     pargs.argc = &argc;
1719     pargs.argv = &argv;
1720     pargs.flags= 1|(1<<6);  /* do not remove the args, ignore version */
1721     while( arg_parse( &pargs, opts) ) {
1722         if( pargs.r_opt == oDebug || pargs.r_opt == oDebugAll )
1723             parse_debug++;
1724         else if( pargs.r_opt == oOptions ) {
1725             /* yes there is one, so we do not try the default one, but
1726              * read the option file when it is encountered at the commandline
1727              */
1728             default_config = 0;
1729         }
1730         else if( pargs.r_opt == oNoOptions )
1731             default_config = 0; /* --no-options */
1732         else if( pargs.r_opt == oHomedir )
1733             set_homedir ( pargs.r.ret_str );
1734         else if( pargs.r_opt == oNoPermissionWarn )
1735             opt.no_perm_warn=1;
1736         else if (pargs.r_opt == oStrict )
1737           {
1738             opt.strict=1;
1739             log_set_strict(1);
1740           }
1741         else if (pargs.r_opt == oNoStrict )
1742           {
1743             opt.strict=0;
1744             log_set_strict(0);
1745           }
1746 #ifdef USE_SHM_COPROCESSING
1747         else if( pargs.r_opt == oRunAsShmCP ) {
1748             /* does not make sense in a options file, we do it here,
1749              * so that we are the able to drop setuid as soon as possible */
1750             opt.shm_coprocess = 1;
1751             requested_shm_size = pargs.r.ret_ulong;
1752         }
1753         else if ( pargs.r_opt == oStatusFD ) {
1754             /* this is needed to ensure that the status-fd filedescriptor is
1755              * initialized when init_shm_coprocessing() is called */
1756             set_status_fd( iobuf_translate_file_handle (pargs.r.ret_int, 1) );
1757         }
1758 #endif
1759     }
1760
1761 #ifdef HAVE_DOSISH_SYSTEM
1762     if ( strchr (opt.homedir,'\\') ) {
1763         char *d, *buf = xmalloc (strlen (opt.homedir)+1);
1764         const char *s = opt.homedir;
1765         for (d=buf,s=opt.homedir; *s; s++)
1766             *d++ = *s == '\\'? '/': *s;
1767         *d = 0;
1768         set_homedir (buf);
1769     }
1770 #endif
1771 #ifdef USE_SHM_COPROCESSING
1772     if( opt.shm_coprocess ) {
1773         init_shm_coprocessing(requested_shm_size, 1 );
1774     }
1775 #endif
1776     /* initialize the secure memory. */
1777     got_secmem=secmem_init( 32768 );
1778     maybe_setuid = 0;
1779     /* Okay, we are now working under our real uid */
1780
1781 #if defined(HAVE_GETUID) && defined(HAVE_GETEUID)
1782     /* There should be no way to get to this spot while still carrying
1783        setuid privs.  Just in case, bomb out if we are. */
1784     if(getuid()!=geteuid())
1785       BUG();
1786 #endif
1787
1788     set_native_charset (NULL); /* Try to auto set the character set */
1789
1790     /* Try for a version specific config file first */
1791     if( default_config )
1792       {
1793         char *name=xstrdup("gpg" EXTSEP_S "conf-" SAFE_VERSION);
1794         char *ver=&name[strlen("gpg" EXTSEP_S "conf-")];
1795
1796         do
1797           {
1798             if(configname)
1799               {
1800                 char *tok;
1801
1802                 xfree(configname);
1803                 configname=NULL;
1804
1805                 if((tok=strrchr(ver,SAFE_VERSION_DASH)))
1806                   *tok='\0';
1807                 else if((tok=strrchr(ver,SAFE_VERSION_DOT)))
1808                   *tok='\0';
1809                 else
1810                   break;
1811               }
1812
1813             configname = make_filename(opt.homedir,name,NULL);
1814           }
1815         while(access(configname,R_OK));
1816
1817         xfree(name);
1818
1819         if(!configname)
1820           configname=make_filename(opt.homedir, "gpg" EXTSEP_S "conf", NULL );
1821         if (!access (configname, R_OK))
1822           { /* Print a warning when both config files are present. */
1823             char *p = make_filename(opt.homedir, "options", NULL );
1824             if (!access (p, R_OK))
1825               log_info (_("NOTE: old default options file `%s' ignored\n"), p);
1826             xfree (p);
1827           }
1828         else
1829           { /* Keep on using the old default one. */
1830             xfree (configname);
1831             configname = make_filename(opt.homedir, "options", NULL );
1832           }
1833       }
1834     argc = orig_argc;
1835     argv = orig_argv;
1836     pargs.argc = &argc;
1837     pargs.argv = &argv;
1838     pargs.flags=  1;  /* do not remove the args */
1839
1840     /* By this point we have a homedir, and cannot change it. */
1841     check_permissions(opt.homedir,0);
1842
1843   next_pass:
1844     if( configname ) {
1845       if(check_permissions(configname,1))
1846         {
1847           /* If any options file is unsafe, then disable any external
1848              programs for keyserver calls or photo IDs.  Since the
1849              external program to call is set in the options file, a
1850              unsafe options file can lead to an arbitrary program
1851              being run. */
1852
1853           opt.exec_disable=1;
1854         }
1855
1856         configlineno = 0;
1857         configfp = fopen( configname, "r" );
1858         if (configfp && is_secured_file (fileno (configfp)))
1859           {
1860             fclose (configfp);
1861             configfp = NULL;
1862             errno = EPERM;
1863           }
1864         if( !configfp ) {
1865             if( default_config ) {
1866                 if( parse_debug )
1867                     log_info(_("NOTE: no default option file `%s'\n"),
1868                                                             configname );
1869             }
1870             else {
1871                 log_error(_("option file `%s': %s\n"),
1872                                     configname, strerror(errno) );
1873                 g10_exit(2);
1874             }
1875             xfree(configname); configname = NULL;
1876         }
1877         if( parse_debug && configname )
1878             log_info(_("reading options from `%s'\n"), configname );
1879         default_config = 0;
1880     }
1881
1882     while( optfile_parse( configfp, configname, &configlineno,
1883                                                 &pargs, opts) )
1884       {
1885         switch( pargs.r_opt )
1886           {
1887           case aCheckKeys: 
1888           case aListConfig:
1889           case aGPGConfList:
1890           case aListPackets:
1891           case aImport: 
1892           case aFastImport: 
1893           case aSendKeys: 
1894           case aRecvKeys: 
1895           case aSearchKeys:
1896           case aRefreshKeys:
1897           case aExport: 
1898             set_cmd (&cmd, pargs.r_opt);
1899             break;
1900           case aListKeys: set_cmd( &cmd, aListKeys); break;
1901           case aListSigs: set_cmd( &cmd, aListSigs); break;
1902           case aExportSecret: set_cmd( &cmd, aExportSecret); break;
1903           case aExportSecretSub: set_cmd( &cmd, aExportSecretSub); break;
1904           case aDeleteSecretKeys:
1905             set_cmd( &cmd, aDeleteSecretKeys);
1906             greeting=1;
1907             break;
1908           case aDeleteSecretAndPublicKeys:
1909             set_cmd( &cmd, aDeleteSecretAndPublicKeys);
1910             greeting=1; 
1911             break;
1912           case aDeleteKeys: set_cmd( &cmd, aDeleteKeys); greeting=1; break;
1913
1914           case aDetachedSign: detached_sig = 1; set_cmd( &cmd, aSign ); break;
1915           case aSym: set_cmd( &cmd, aSym); break;
1916
1917           case aDecryptFiles: multifile=1; /* fall through */
1918           case aDecrypt: set_cmd( &cmd, aDecrypt); break;
1919
1920           case aEncrFiles: multifile=1; /* fall through */
1921           case aEncr: set_cmd( &cmd, aEncr); break;
1922
1923           case aVerifyFiles: multifile=1; /* fall through */
1924           case aVerify: set_cmd( &cmd, aVerify); break;
1925
1926           case aSign: set_cmd( &cmd, aSign );  break;
1927           case aKeygen: set_cmd( &cmd, aKeygen); greeting=1; break;
1928           case aSignKey: set_cmd( &cmd, aSignKey); break;
1929           case aLSignKey: set_cmd( &cmd, aLSignKey); break;
1930           case aStore: set_cmd( &cmd, aStore); break;
1931           case aEditKey: set_cmd( &cmd, aEditKey); greeting=1; break;
1932           case aClearsign: set_cmd( &cmd, aClearsign); break;
1933           case aGenRevoke: set_cmd( &cmd, aGenRevoke); break;
1934           case aDesigRevoke: set_cmd( &cmd, aDesigRevoke); break;
1935           case aPrimegen: set_cmd( &cmd, aPrimegen); break;
1936           case aGenRandom: set_cmd( &cmd, aGenRandom); break;
1937           case aPrintMD: set_cmd( &cmd, aPrintMD); break;
1938           case aPrintMDs: set_cmd( &cmd, aPrintMDs); break;
1939           case aListTrustDB: set_cmd( &cmd, aListTrustDB); break;
1940           case aCheckTrustDB: set_cmd( &cmd, aCheckTrustDB); break;
1941           case aUpdateTrustDB: set_cmd( &cmd, aUpdateTrustDB); break;
1942           case aFixTrustDB: set_cmd( &cmd, aFixTrustDB); break;
1943           case aListTrustPath: set_cmd( &cmd, aListTrustPath); break;
1944           case aDeArmor: set_cmd( &cmd, aDeArmor); break;
1945           case aEnArmor: set_cmd( &cmd, aEnArmor); break;
1946           case aListOwnerTrust:
1947             deprecated_warning(configname,configlineno,
1948                                "--list-ownertrust","--export-ownertrust","");
1949           case aExportOwnerTrust: set_cmd( &cmd, aExportOwnerTrust); break;
1950           case aImportOwnerTrust: set_cmd( &cmd, aImportOwnerTrust); break;
1951           case aPipeMode:
1952             deprecated_command ("--pipemode");
1953             set_cmd( &cmd, aPipeMode);
1954             break;
1955
1956           case aRebuildKeydbCaches: set_cmd( &cmd, aRebuildKeydbCaches); break;
1957
1958 #ifdef ENABLE_CARD_SUPPORT
1959           case aCardStatus: set_cmd (&cmd, aCardStatus); break;
1960           case aCardEdit: set_cmd (&cmd, aCardEdit); break;
1961           case aChangePIN: set_cmd (&cmd, aChangePIN); break;
1962           case oReaderPort:
1963             card_set_reader_port (pargs.r.ret_str);
1964             break;
1965           case octapiDriver: opt.ctapi_driver = pargs.r.ret_str; break;
1966           case opcscDriver: opt.pcsc_driver = pargs.r.ret_str; break;
1967           case oDisableCCID: opt.disable_ccid = 1; break;
1968 #endif /* ENABLE_CARD_SUPPORT*/
1969
1970           case oArmor: opt.armor = 1; opt.no_armor=0; break;
1971           case oOutput: opt.outfile = pargs.r.ret_str; break;
1972           case oMaxOutput: opt.max_output = pargs.r.ret_ulong; break;
1973           case oQuiet: opt.quiet = 1; break;
1974           case oNoTTY: tty_no_terminal(1); break;
1975           case oDryRun: opt.dry_run = 1; break;
1976           case oInteractive: opt.interactive = 1; break;
1977           case oVerbose:
1978             g10_opt_verbose++;
1979             opt.verbose++;
1980             opt.list_options|=LIST_SHOW_UNUSABLE_UIDS;
1981             opt.list_options|=LIST_SHOW_UNUSABLE_SUBKEYS;
1982             break;
1983           case oKOption: set_cmd( &cmd, aKMode ); break;
1984
1985           case oBatch: opt.batch = 1; nogreeting = 1; break;
1986           case oUseAgent:
1987 #ifndef __riscos__
1988             opt.use_agent = 1;
1989 #else /* __riscos__ */
1990             opt.use_agent = 0;
1991             riscos_not_implemented("use-agent");
1992 #endif /* __riscos__ */
1993             break;
1994           case oNoUseAgent: opt.use_agent = 0; break;
1995           case oGpgAgentInfo: opt.gpg_agent_info = pargs.r.ret_str; break;
1996           case oAnswerYes: opt.answer_yes = 1; break;
1997           case oAnswerNo: opt.answer_no = 1; break;
1998           case oKeyring: append_to_strlist( &nrings, pargs.r.ret_str); break;
1999           case oPrimaryKeyring:
2000             sl=append_to_strlist( &nrings, pargs.r.ret_str);
2001             sl->flags=2;
2002             break;
2003           case oShowKeyring:
2004             deprecated_warning(configname,configlineno,"--show-keyring",
2005                                "--list-options ","show-keyring");
2006             opt.list_options|=LIST_SHOW_KEYRING;
2007             break;
2008           case oDebug: opt.debug |= pargs.r.ret_ulong; break;
2009           case oDebugAll: opt.debug = ~0; break;
2010           case oDebugCCIDDriver: 
2011 #if defined(ENABLE_CARD_SUPPORT) && defined(HAVE_LIBUSB)
2012             ccid_set_debug_level (ccid_set_debug_level (1)+1);
2013 #endif
2014             break;
2015           case oStatusFD:
2016             set_status_fd( iobuf_translate_file_handle (pargs.r.ret_int, 1) );
2017             break;
2018           case oStatusFile:
2019             set_status_fd ( open_info_file (pargs.r.ret_str, 1) );
2020             break;
2021           case oAttributeFD:
2022             set_attrib_fd(iobuf_translate_file_handle (pargs.r.ret_int, 1));
2023             break;
2024           case oAttributeFile:
2025             set_attrib_fd ( open_info_file (pargs.r.ret_str, 1) );
2026             break;
2027           case oLoggerFD:
2028             log_set_logfile( NULL,
2029                              iobuf_translate_file_handle (pargs.r.ret_int, 1));
2030             break;
2031           case oLoggerFile:
2032             log_set_logfile( NULL, open_info_file (pargs.r.ret_str, 1) );
2033             break;
2034
2035           case oWithFingerprint:
2036             opt.with_fingerprint = 1;
2037             with_fpr=1; /*fall thru*/
2038           case oFingerprint: opt.fingerprint++; break;
2039           case oSecretKeyring:
2040             append_to_strlist( &sec_nrings, pargs.r.ret_str);
2041             break;
2042           case oOptions:
2043             /* config files may not be nested (silently ignore them) */
2044             if( !configfp ) {
2045                 xfree(configname);
2046                 configname = xstrdup(pargs.r.ret_str);
2047                 goto next_pass;
2048             }
2049             break;
2050           case oNoArmor: opt.no_armor=1; opt.armor=0; break;
2051           case oNoDefKeyring: default_keyring = 0; break;
2052           case oNoGreeting: nogreeting = 1; break;
2053           case oNoVerbose: g10_opt_verbose = 0;
2054                            opt.verbose = 0; opt.list_sigs=0; break;
2055           case oQuickRandom: quick_random_gen(1); break;
2056           case oEmitVersion: opt.no_version=0; break;
2057           case oNoEmitVersion: opt.no_version=1; break;
2058           case oCompletesNeeded: opt.completes_needed = pargs.r.ret_int; break;
2059           case oMarginalsNeeded: opt.marginals_needed = pargs.r.ret_int; break;
2060           case oMaxCertDepth: opt.max_cert_depth = pargs.r.ret_int; break;
2061           case oTrustDBName: trustdb_name = pargs.r.ret_str; break;
2062           case oDefaultKey: opt.def_secret_key = pargs.r.ret_str; break;
2063           case oDefRecipient:
2064                     if( *pargs.r.ret_str )
2065                         opt.def_recipient = make_username(pargs.r.ret_str);
2066                     break;
2067           case oDefRecipientSelf:
2068                     xfree(opt.def_recipient); opt.def_recipient = NULL;
2069                     opt.def_recipient_self = 1;
2070                     break;
2071           case oNoDefRecipient:
2072                     xfree(opt.def_recipient); opt.def_recipient = NULL;
2073                     opt.def_recipient_self = 0;
2074                     break;
2075           case oNoOptions: opt.no_homedir_creation = 1; break; /* no-options */
2076           case oHomedir: break;
2077           case oNoBatch: opt.batch = 0; break;
2078           case oWithKeyData: opt.with_key_data=1; /* fall thru */
2079           case oWithColons: opt.with_colons=':'; break;
2080
2081           case oSkipVerify: opt.skip_verify=1; break;
2082           case oCompressKeys: opt.compress_keys = 1; break;
2083           case aListSecretKeys: set_cmd( &cmd, aListSecretKeys); break;
2084             /* There are many programs (like mutt) that call gpg with
2085                --always-trust so keep this option around for a long
2086                time. */
2087           case oAlwaysTrust: opt.trust_model=TM_ALWAYS; break;
2088           case oTrustModel:
2089             parse_trust_model(pargs.r.ret_str);
2090             break;
2091           case oForceOwnertrust:
2092             log_info(_("NOTE: %s is not for normal use!\n"),
2093                      "--force-ownertrust");
2094             opt.force_ownertrust=string_to_trust_value(pargs.r.ret_str);
2095             if(opt.force_ownertrust==-1)
2096               {
2097                 log_error("invalid ownertrust `%s'\n",pargs.r.ret_str);
2098                 opt.force_ownertrust=0;
2099               }
2100             break;
2101           case oLoadExtension:
2102 #ifndef __riscos__
2103 #if defined(USE_DYNAMIC_LINKING) || defined(_WIN32)
2104             if(check_permissions(pargs.r.ret_str,2))
2105               log_info(_("cipher extension `%s' not loaded due to"
2106                          " unsafe permissions\n"),pargs.r.ret_str);
2107             else
2108               register_cipher_extension(orig_argc? *orig_argv:NULL,
2109                                         pargs.r.ret_str);
2110 #endif
2111 #else /* __riscos__ */
2112             riscos_not_implemented("load-extension");
2113 #endif /* __riscos__ */
2114             break;
2115           case oRFC1991:
2116             opt.compliance = CO_RFC1991;
2117             opt.force_v4_certs = 0;
2118             opt.escape_from = 1;
2119             break;
2120           case oOpenPGP:
2121           case oRFC2440:
2122             /* TODO: When 2440bis becomes a RFC, set new values for
2123                oOpenPGP. */
2124             opt.rfc2440_text=1;
2125             opt.compliance = CO_RFC2440;
2126             opt.allow_non_selfsigned_uid = 1;
2127             opt.allow_freeform_uid = 1;
2128             opt.pgp2_workarounds = 0;
2129             opt.escape_from = 0;
2130             opt.force_v3_sigs = 0;
2131             opt.compress_keys = 0;          /* not mandated, but we do it */
2132             opt.compress_sigs = 0;          /* ditto. */
2133             opt.not_dash_escaped = 0;
2134             opt.def_cipher_algo = 0;
2135             opt.def_digest_algo = 0;
2136             opt.cert_digest_algo = 0;
2137             opt.compress_algo = -1;
2138             opt.s2k_mode = 3; /* iterated+salted */
2139             opt.s2k_digest_algo = DIGEST_ALGO_SHA1;
2140             opt.s2k_cipher_algo = CIPHER_ALGO_3DES;
2141             break;
2142           case oPGP2:  opt.compliance = CO_PGP2;  break;
2143           case oPGP6:  opt.compliance = CO_PGP6;  break;
2144           case oPGP7:  opt.compliance = CO_PGP7;  break;
2145           case oPGP8:  opt.compliance = CO_PGP8;  break;
2146           case oGnuPG: opt.compliance = CO_GNUPG; break;
2147           case oCompressSigs: opt.compress_sigs = 1; break;
2148           case oRFC2440Text: opt.rfc2440_text=1; break;
2149           case oNoRFC2440Text: opt.rfc2440_text=0; break;
2150           case oRunAsShmCP:
2151 #ifndef __riscos__
2152 # ifndef USE_SHM_COPROCESSING
2153             /* not possible in the option file,
2154              * but we print the warning here anyway */
2155             log_error("shared memory coprocessing is not available\n");
2156 # endif
2157 #else /* __riscos__ */
2158             riscos_not_implemented("run-as-shm-coprocess");
2159 #endif /* __riscos__ */
2160             break;
2161           case oSetFilename: opt.set_filename = pargs.r.ret_str; break;
2162           case oForYourEyesOnly: eyes_only = 1; break;
2163           case oNoForYourEyesOnly: eyes_only = 0; break;
2164           case oSetPolicyURL:
2165             add_policy_url(pargs.r.ret_str,0);
2166             add_policy_url(pargs.r.ret_str,1);
2167             break;
2168           case oSigPolicyURL: add_policy_url(pargs.r.ret_str,0); break;
2169           case oCertPolicyURL: add_policy_url(pargs.r.ret_str,1); break;
2170           case oShowPolicyURL:
2171             deprecated_warning(configname,configlineno,"--show-policy-url",
2172                                "--list-options ","show-policy-urls");
2173             deprecated_warning(configname,configlineno,"--show-policy-url",
2174                                "--verify-options ","show-policy-urls");
2175             opt.list_options|=LIST_SHOW_POLICY_URLS;
2176             opt.verify_options|=VERIFY_SHOW_POLICY_URLS;
2177             break;
2178           case oNoShowPolicyURL:
2179             deprecated_warning(configname,configlineno,"--no-show-policy-url",
2180                                "--list-options ","no-show-policy-urls");
2181             deprecated_warning(configname,configlineno,"--no-show-policy-url",
2182                                "--verify-options ","no-show-policy-urls");
2183             opt.list_options&=~LIST_SHOW_POLICY_URLS;
2184             opt.verify_options&=~VERIFY_SHOW_POLICY_URLS;
2185             break;
2186           case oSigKeyserverURL: add_keyserver_url(pargs.r.ret_str,0); break;
2187           case oUseEmbeddedFilename: opt.use_embedded_filename = 1; break;
2188           case oNoUseEmbeddedFilename: opt.use_embedded_filename = 0; break;
2189           case oComment:
2190             if(pargs.r.ret_str[0])
2191               append_to_strlist(&opt.comments,pargs.r.ret_str);
2192             break;
2193           case oDefaultComment:
2194             deprecated_warning(configname,configlineno,
2195                                "--default-comment","--no-comments","");
2196             /* fall through */
2197           case oNoComments:
2198             free_strlist(opt.comments);
2199             opt.comments=NULL;
2200             break;
2201           case oThrowKeyids: opt.throw_keyid = 1; break;
2202           case oNoThrowKeyids: opt.throw_keyid = 0; break;
2203           case oShowPhotos:
2204             deprecated_warning(configname,configlineno,"--show-photos",
2205                                "--list-options ","show-photos");
2206             deprecated_warning(configname,configlineno,"--show-photos",
2207                                "--verify-options ","show-photos");
2208             opt.list_options|=LIST_SHOW_PHOTOS;
2209             opt.verify_options|=VERIFY_SHOW_PHOTOS;
2210             break;
2211           case oNoShowPhotos:
2212             deprecated_warning(configname,configlineno,"--no-show-photos",
2213                                "--list-options ","no-show-photos");
2214             deprecated_warning(configname,configlineno,"--no-show-photos",
2215                                "--verify-options ","no-show-photos");
2216             opt.list_options&=~LIST_SHOW_PHOTOS;
2217             opt.verify_options&=~VERIFY_SHOW_PHOTOS;
2218             break;
2219           case oPhotoViewer: opt.photo_viewer = pargs.r.ret_str; break;
2220           case oForceV3Sigs: opt.force_v3_sigs = 1; break;
2221           case oNoForceV3Sigs: opt.force_v3_sigs = 0; break;
2222           case oForceV4Certs: opt.force_v4_certs = 1; break;
2223           case oNoForceV4Certs: opt.force_v4_certs = 0; break;
2224           case oForceMDC: opt.force_mdc = 1; break;
2225           case oNoForceMDC: opt.force_mdc = 0; break;
2226           case oDisableMDC: opt.disable_mdc = 1; break;
2227           case oNoDisableMDC: opt.disable_mdc = 0; break;
2228           case oS2KMode:   opt.s2k_mode = pargs.r.ret_int; break;
2229           case oS2KDigest: s2k_digest_string = xstrdup(pargs.r.ret_str); break;
2230           case oS2KCipher: s2k_cipher_string = xstrdup(pargs.r.ret_str); break;
2231           case oSimpleSKChecksum: opt.simple_sk_checksum = 1; break;
2232           case oNoEncryptTo: opt.no_encrypt_to = 1; break;
2233           case oEncryptTo: /* store the recipient in the second list */
2234             sl = add_to_strlist2( &remusr, pargs.r.ret_str, utf8_strings );
2235             sl->flags = 1;
2236             break;
2237           case oHiddenEncryptTo: /* store the recipient in the second list */
2238             sl = add_to_strlist2( &remusr, pargs.r.ret_str, utf8_strings );
2239             sl->flags = 1|2;
2240             break;
2241           case oRecipient: /* store the recipient */
2242             add_to_strlist2( &remusr, pargs.r.ret_str, utf8_strings );
2243             any_explicit_recipient = 1;
2244             break;
2245           case oHiddenRecipient: /* store the recipient with a flag */
2246             sl = add_to_strlist2( &remusr, pargs.r.ret_str, utf8_strings );
2247             sl->flags = 2;
2248             any_explicit_recipient = 1;
2249             break;
2250           case oTextmodeShort: opt.textmode = 2; break;
2251           case oTextmode: opt.textmode=1;  break;
2252           case oNoTextmode: opt.textmode=0;  break;
2253           case oExpert: opt.expert = 1; break;
2254           case oNoExpert: opt.expert = 0; break;
2255           case oDefSigExpire:
2256             if(*pargs.r.ret_str!='\0')
2257               {
2258                 if(parse_expire_string(pargs.r.ret_str)==(u32)-1)
2259                   log_error(_("`%s' is not a valid signature expiration\n"),
2260                             pargs.r.ret_str);
2261                 else
2262                   opt.def_sig_expire=pargs.r.ret_str;
2263               }
2264             break;
2265           case oAskSigExpire: opt.ask_sig_expire = 1; break;
2266           case oNoAskSigExpire: opt.ask_sig_expire = 0; break;
2267           case oDefCertExpire:
2268             if(*pargs.r.ret_str!='\0')
2269               {
2270                 if(parse_expire_string(pargs.r.ret_str)==(u32)-1)
2271                   log_error(_("`%s' is not a valid signature expiration\n"),
2272                             pargs.r.ret_str);
2273                 else
2274                   opt.def_cert_expire=pargs.r.ret_str;
2275               }
2276             break;
2277           case oAskCertExpire: opt.ask_cert_expire = 1; break;
2278           case oNoAskCertExpire: opt.ask_cert_expire = 0; break;
2279           case oDefCertLevel: opt.def_cert_level=pargs.r.ret_int; break;
2280           case oMinCertLevel: opt.min_cert_level=pargs.r.ret_int; break;
2281           case oAskCertLevel: opt.ask_cert_level = 1; break;
2282           case oNoAskCertLevel: opt.ask_cert_level = 0; break;
2283           case oLocalUser: /* store the local users */
2284             add_to_strlist2( &locusr, pargs.r.ret_str, utf8_strings );
2285             break;
2286           case oCompress:
2287             /* this is the -z command line option */
2288             opt.compress_level = opt.bz2_compress_level = pargs.r.ret_int;
2289             break;
2290           case oCompressLevel: opt.compress_level = pargs.r.ret_int; break;
2291           case oBZ2CompressLevel: opt.bz2_compress_level = pargs.r.ret_int; break;
2292           case oBZ2DecompressLowmem: opt.bz2_decompress_lowmem=1; break;
2293           case oPasswd:
2294             set_passphrase_from_string(pargs.r.ret_str);
2295             break;
2296           case oPasswdFD:
2297             pwfd = iobuf_translate_file_handle (pargs.r.ret_int, 0);
2298             opt.use_agent = 0;
2299             break;
2300           case oPasswdFile:
2301             pwfd = open_info_file (pargs.r.ret_str, 0);
2302             break;
2303           case oCommandFD:
2304             opt.command_fd = iobuf_translate_file_handle (pargs.r.ret_int, 0);
2305             break;
2306           case oCommandFile:
2307             opt.command_fd = open_info_file (pargs.r.ret_str, 0);
2308             break;
2309           case oCipherAlgo: 
2310             def_cipher_string = xstrdup(pargs.r.ret_str);
2311             break;
2312           case oDigestAlgo:
2313             def_digest_string = xstrdup(pargs.r.ret_str);
2314             break;
2315           case oCompressAlgo:
2316             /* If it is all digits, stick a Z in front of it for
2317                later.  This is for backwards compatibility with
2318                versions that took the compress algorithm number. */
2319             {
2320               char *pt=pargs.r.ret_str;
2321               while(*pt)
2322                 {
2323                   if (!isascii (*pt) || !isdigit (*pt))
2324                     break;
2325
2326                   pt++;
2327                 }
2328
2329               if(*pt=='\0')
2330                 {
2331                   compress_algo_string=xmalloc(strlen(pargs.r.ret_str)+2);
2332                   strcpy(compress_algo_string,"Z");
2333                   strcat(compress_algo_string,pargs.r.ret_str);
2334                 }
2335               else
2336                 compress_algo_string = xstrdup(pargs.r.ret_str);
2337             }
2338             break;
2339           case oCertDigestAlgo: cert_digest_string = xstrdup(pargs.r.ret_str); break;
2340           case oNoSecmemWarn: secmem_set_flags( secmem_get_flags() | 1 ); break;
2341           case oRequireSecmem: require_secmem=1; break;
2342           case oNoRequireSecmem: require_secmem=0; break;
2343           case oNoPermissionWarn: opt.no_perm_warn=1; break;
2344           case oNoMDCWarn: opt.no_mdc_warn=1; break;
2345           case oDisplayCharset:
2346             if( set_native_charset( pargs.r.ret_str ) )
2347                 log_error(_("`%s' is not a valid character set\n"),
2348                           pargs.r.ret_str);
2349             break;
2350           case oNotDashEscaped: opt.not_dash_escaped = 1; break;
2351           case oEscapeFrom: opt.escape_from = 1; break;
2352           case oNoEscapeFrom: opt.escape_from = 0; break;
2353           case oLockOnce: opt.lock_once = 1; break;
2354           case oLockNever: disable_dotlock(); break;
2355           case oLockMultiple:
2356 #ifndef __riscos__
2357             opt.lock_once = 0;
2358 #else /* __riscos__ */
2359             riscos_not_implemented("lock-multiple");
2360 #endif /* __riscos__ */
2361             break;
2362           case oKeyServer:
2363             opt.keyserver=parse_keyserver_uri(pargs.r.ret_str,0,
2364                                               configname,configlineno);
2365             if(!opt.keyserver)
2366               log_error(_("could not parse keyserver URL\n"));
2367             break;
2368           case oKeyServerOptions:
2369             if(!parse_keyserver_options(pargs.r.ret_str))
2370               {
2371                 if(configname)
2372                   log_error(_("%s:%d: invalid keyserver options\n"),
2373                             configname,configlineno);
2374                 else
2375                   log_error(_("invalid keyserver options\n"));
2376               }
2377             break;
2378           case oImportOptions:
2379             if(!parse_import_options(pargs.r.ret_str,&opt.import_options,1))
2380               {
2381                 if(configname)
2382                   log_error(_("%s:%d: invalid import options\n"),
2383                             configname,configlineno);
2384                 else
2385                   log_error(_("invalid import options\n"));
2386               }
2387             break;
2388           case oExportOptions:
2389             if(!parse_export_options(pargs.r.ret_str,&opt.export_options,1))
2390               {
2391                 if(configname)
2392                   log_error(_("%s:%d: invalid export options\n"),
2393                             configname,configlineno);
2394                 else
2395                   log_error(_("invalid export options\n"));
2396               }
2397             break;
2398           case oListOptions:
2399             if(!parse_list_options(pargs.r.ret_str))
2400               {
2401                 if(configname)
2402                   log_error(_("%s:%d: invalid list options\n"),
2403                             configname,configlineno);
2404                 else
2405                   log_error(_("invalid list options\n"));
2406               }
2407             break;
2408           case oVerifyOptions:
2409             {
2410               struct parse_options vopts[]=
2411                 {
2412                   {"show-photos",VERIFY_SHOW_PHOTOS,NULL,
2413                    N_("display photo IDs during signature verification")},
2414                   {"show-policy-urls",VERIFY_SHOW_POLICY_URLS,NULL,
2415                    N_("show policy URLs during signature verification")},
2416                   {"show-notations",VERIFY_SHOW_NOTATIONS,NULL,
2417                    N_("show all notations during signature verification")},
2418                   {"show-std-notations",VERIFY_SHOW_STD_NOTATIONS,NULL,
2419                    N_("show IETF standard notations during signature verification")},
2420                   {"show-standard-notations",VERIFY_SHOW_STD_NOTATIONS,NULL,
2421                    NULL},
2422                   {"show-user-notations",VERIFY_SHOW_USER_NOTATIONS,NULL,
2423                    N_("show user-supplied notations during signature verification")},
2424                   {"show-keyserver-urls",VERIFY_SHOW_KEYSERVER_URLS,NULL,
2425                    N_("show preferred keyserver URLs during signature verification")},
2426                   {"show-uid-validity",VERIFY_SHOW_UID_VALIDITY,NULL,
2427                    N_("show user ID validity during signature verification")},
2428                   {"show-unusable-uids",VERIFY_SHOW_UNUSABLE_UIDS,NULL,
2429                    N_("show revoked and expired user IDs in signature verification")},
2430                   {NULL,0,NULL,NULL}
2431                 };
2432
2433               if(!parse_options(pargs.r.ret_str,&opt.verify_options,vopts,1))
2434                 {
2435                   if(configname)
2436                     log_error(_("%s:%d: invalid verify options\n"),
2437                               configname,configlineno);
2438                   else
2439                     log_error(_("invalid verify options\n"));
2440                 }
2441             }
2442             break;
2443           case oTempDir: opt.temp_dir=pargs.r.ret_str; break;
2444           case oExecPath:
2445             if(set_exec_path(pargs.r.ret_str))
2446               log_error(_("unable to set exec-path to %s\n"),pargs.r.ret_str);
2447             else
2448               opt.exec_path_set=1;
2449             break;
2450           case oSetNotation:
2451             add_notation_data( pargs.r.ret_str, 0 );
2452             add_notation_data( pargs.r.ret_str, 1 );
2453             break;
2454           case oSigNotation: add_notation_data( pargs.r.ret_str, 0 ); break;
2455           case oCertNotation: add_notation_data( pargs.r.ret_str, 1 ); break;
2456           case oShowNotation:
2457             deprecated_warning(configname,configlineno,"--show-notation",
2458                                "--list-options ","show-notations");
2459             deprecated_warning(configname,configlineno,"--show-notation",
2460                                "--verify-options ","show-notations");
2461             opt.list_options|=LIST_SHOW_NOTATIONS;
2462             opt.verify_options|=VERIFY_SHOW_NOTATIONS;
2463             break;
2464           case oNoShowNotation:
2465             deprecated_warning(configname,configlineno,"--no-show-notation",
2466                                "--list-options ","no-show-notations");
2467             deprecated_warning(configname,configlineno,"--no-show-notation",
2468                                "--verify-options ","no-show-notations");
2469             opt.list_options&=~LIST_SHOW_NOTATIONS;
2470             opt.verify_options&=~VERIFY_SHOW_NOTATIONS;
2471             break;
2472           case oUtf8Strings: utf8_strings = 1; break;
2473           case oNoUtf8Strings: utf8_strings = 0; break;
2474           case oDisableCipherAlgo:
2475                 disable_cipher_algo( string_to_cipher_algo(pargs.r.ret_str) );
2476                 break;
2477           case oDisablePubkeyAlgo:
2478                 disable_pubkey_algo( string_to_pubkey_algo(pargs.r.ret_str) );
2479                 break;
2480           case oNoSigCache: opt.no_sig_cache = 1; break;
2481           case oNoSigCreateCheck: opt.no_sig_create_check = 1; break;
2482           case oAllowNonSelfsignedUID: opt.allow_non_selfsigned_uid = 1; break;
2483           case oNoAllowNonSelfsignedUID: opt.allow_non_selfsigned_uid=0; break;
2484           case oAllowFreeformUID: opt.allow_freeform_uid = 1; break;
2485           case oNoAllowFreeformUID: opt.allow_freeform_uid = 0; break;
2486           case oNoLiteral: opt.no_literal = 1; break;
2487           case oSetFilesize: opt.set_filesize = pargs.r.ret_ulong; break;
2488           case oHonorHttpProxy:
2489                 add_to_strlist(&opt.keyserver_options.other,"http-proxy");
2490                 deprecated_warning(configname,configlineno,
2491                                    "--honor-http-proxy",
2492                                    "--keyserver-options ","http-proxy");
2493                 break;
2494           case oFastListMode: opt.fast_list_mode = 1; break;
2495           case oFixedListMode: opt.fixed_list_mode = 1; break;
2496           case oListOnly: opt.list_only=1; break;
2497           case oIgnoreTimeConflict: opt.ignore_time_conflict = 1; break;
2498           case oIgnoreValidFrom: opt.ignore_valid_from = 1; break;
2499           case oIgnoreCrcError: opt.ignore_crc_error = 1; break;
2500           case oIgnoreMDCError: opt.ignore_mdc_error = 1; break;
2501           case oNoRandomSeedFile: use_random_seed = 0; break;
2502           case oAutoKeyRetrieve:
2503           case oNoAutoKeyRetrieve:
2504                 if(pargs.r_opt==oAutoKeyRetrieve)
2505                   opt.keyserver_options.options|=KEYSERVER_AUTO_KEY_RETRIEVE;
2506                 else
2507                   opt.keyserver_options.options&=~KEYSERVER_AUTO_KEY_RETRIEVE;
2508
2509                 deprecated_warning(configname,configlineno,
2510                            pargs.r_opt==oAutoKeyRetrieve?"--auto-key-retrieve":
2511                                "--no-auto-key-retrieve","--keyserver-options ",
2512                            pargs.r_opt==oAutoKeyRetrieve?"auto-key-retrieve":
2513                                "no-auto-key-retrieve");
2514                 break;
2515           case oShowSessionKey: opt.show_session_key = 1; break;
2516           case oOverrideSessionKey:
2517                 opt.override_session_key = pargs.r.ret_str;
2518                 break;
2519           case oMergeOnly:
2520                 deprecated_warning(configname,configlineno,"--merge-only",
2521                                    "--import-options ","merge-only");
2522                 opt.import_options|=IMPORT_MERGE_ONLY;
2523             break;
2524           case oAllowSecretKeyImport: /* obsolete */ break;
2525           case oTryAllSecrets: opt.try_all_secrets = 1; break;
2526           case oTrustedKey: register_trusted_key( pargs.r.ret_str ); break;
2527           case oEnableSpecialFilenames:
2528             iobuf_enable_special_filenames (1);
2529             break;
2530           case oNoExpensiveTrustChecks: opt.no_expensive_trust_checks=1; break;
2531           case oAutoCheckTrustDB: opt.no_auto_check_trustdb=0; break;
2532           case oNoAutoCheckTrustDB: opt.no_auto_check_trustdb=1; break;
2533           case oPreservePermissions: opt.preserve_permissions=1; break;
2534           case oDefaultPreferenceList:
2535             opt.def_preference_list = pargs.r.ret_str;
2536             break;
2537           case oPersonalCipherPreferences:
2538             pers_cipher_list=pargs.r.ret_str;
2539             break;
2540           case oPersonalDigestPreferences:
2541             pers_digest_list=pargs.r.ret_str;
2542             break;
2543           case oPersonalCompressPreferences:
2544             pers_compress_list=pargs.r.ret_str;
2545             break;
2546           case oDisplay: opt.display = pargs.r.ret_str; break;
2547           case oTTYname: opt.ttyname = pargs.r.ret_str; break;
2548           case oTTYtype: opt.ttytype = pargs.r.ret_str; break;
2549           case oLCctype: opt.lc_ctype = pargs.r.ret_str; break;
2550           case oLCmessages: opt.lc_messages = pargs.r.ret_str; break;
2551           case oGroup: add_group(pargs.r.ret_str); break;
2552           case oUnGroup: rm_group(pargs.r.ret_str); break;
2553           case oNoGroups:
2554             while(opt.grouplist)
2555               {
2556                 struct groupitem *iter=opt.grouplist;
2557                 free_strlist(iter->values);
2558                 opt.grouplist=opt.grouplist->next;
2559                 xfree(iter);
2560               }
2561             break;
2562           case oStrict: opt.strict=1; log_set_strict(1); break;
2563           case oNoStrict: opt.strict=0; log_set_strict(0); break;
2564           case oMangleDosFilenames: opt.mangle_dos_filenames = 1; break;
2565           case oNoMangleDosFilenames: opt.mangle_dos_filenames = 0; break;
2566           case oEnableProgressFilter: opt.enable_progress_filter = 1; break;
2567           case oMultifile: multifile=1; break;
2568           case oKeyidFormat:
2569             if(ascii_strcasecmp(pargs.r.ret_str,"short")==0)
2570               opt.keyid_format=KF_SHORT;
2571             else if(ascii_strcasecmp(pargs.r.ret_str,"long")==0)
2572               opt.keyid_format=KF_LONG;
2573             else if(ascii_strcasecmp(pargs.r.ret_str,"0xshort")==0)
2574               opt.keyid_format=KF_0xSHORT;
2575             else if(ascii_strcasecmp(pargs.r.ret_str,"0xlong")==0)
2576               opt.keyid_format=KF_0xLONG;
2577             else
2578               log_error("unknown keyid-format `%s'\n",pargs.r.ret_str);
2579             break;
2580
2581           case oExitOnStatusWriteError:
2582             opt.exit_on_status_write_error = 1;
2583             break;
2584
2585           case oLimitCardInsertTries: 
2586             opt.limit_card_insert_tries = pargs.r.ret_int; 
2587             break;
2588
2589   
2590           case oNoop: break;
2591
2592           default : pargs.err = configfp? 1:2; break;
2593           }
2594       }
2595
2596
2597     if( configfp ) {
2598         fclose( configfp );
2599         configfp = NULL;
2600         /* Remember the first config file name. */
2601         if (!save_configname)
2602           save_configname = configname;
2603         else
2604           xfree(configname);
2605         configname = NULL;
2606         goto next_pass;
2607     }
2608     xfree( configname ); configname = NULL;
2609     if( log_get_errorcount(0) )
2610         g10_exit(2);
2611
2612     /* The command --gpgconf-list is pretty simple and may be called
2613        directly after the option parsing. */
2614     if (cmd == aGPGConfList)
2615       {
2616         gpgconf_list (save_configname);
2617         g10_exit (0);
2618       }
2619     xfree (save_configname);
2620
2621     if( nogreeting )
2622         greeting = 0;
2623
2624     if( greeting ) {
2625         fprintf(stderr, "%s %s; %s\n",
2626                         strusage(11), strusage(13), strusage(14) );
2627         fprintf(stderr, "%s\n", strusage(15) );
2628     }
2629 #ifdef IS_DEVELOPMENT_VERSION
2630     if( !opt.batch )
2631       {
2632         const char *s;
2633
2634         if((s=strusage(20)))
2635           log_info("%s\n",s);
2636         if((s=strusage(21)))
2637           log_info("%s\n",s);
2638         if((s=strusage(22)))
2639           log_info("%s\n",s);
2640       }
2641 #endif
2642
2643     if (opt.verbose > 2)
2644         log_info ("using character set `%s'\n", get_native_charset ());
2645
2646     if( may_coredump && !opt.quiet )
2647         log_info(_("WARNING: program may create a core file!\n"));
2648
2649     if (eyes_only) {
2650       if (opt.set_filename)
2651           log_info(_("WARNING: %s overrides %s\n"),
2652                    "--for-your-eyes-only","--set-filename");
2653
2654       opt.set_filename="_CONSOLE";
2655     }
2656
2657     if (opt.no_literal) {
2658         log_info(_("NOTE: %s is not for normal use!\n"), "--no-literal");
2659         if (opt.textmode)
2660             log_error(_("%s not allowed with %s!\n"),
2661                        "--textmode", "--no-literal" );
2662         if (opt.set_filename)
2663             log_error(_("%s makes no sense with %s!\n"),
2664                         eyes_only?"--for-your-eyes-only":"--set-filename",
2665                         "--no-literal" );
2666     }
2667
2668 #ifndef ENABLE_AGENT_SUPPORT   
2669     if (opt.use_agent) {
2670       log_info(_("NOTE: %s is not available in this version\n"),
2671                "--use-agent");
2672       opt.use_agent = 0;
2673     }
2674 #endif /*!ENABLE_AGENT_SUPPORT*/
2675
2676     if (opt.set_filesize)
2677         log_info(_("NOTE: %s is not for normal use!\n"), "--set-filesize");
2678     if( opt.batch )
2679         tty_batchmode( 1 );
2680
2681     secmem_set_flags( secmem_get_flags() & ~2 ); /* resume warnings */
2682
2683     if(require_secmem && !got_secmem)
2684       {
2685         log_info(_("will not run with insecure memory due to %s\n"),
2686                  "--require-secmem");
2687         g10_exit(2);
2688       }
2689
2690     set_debug();
2691
2692     /* Do these after the switch(), so they can override settings. */
2693     if(PGP2)
2694       {
2695         int unusable=0;
2696
2697         if(cmd==aSign && !detached_sig)
2698           {
2699             log_info(_("you can only make detached or clear signatures "
2700                        "while in --pgp2 mode\n"));
2701             unusable=1;
2702           }
2703         else if(cmd==aSignEncr || cmd==aSignSym)
2704           {
2705             log_info(_("you can't sign and encrypt at the "
2706                        "same time while in --pgp2 mode\n"));
2707             unusable=1;
2708           }
2709         else if(argc==0 && (cmd==aSign || cmd==aEncr || cmd==aSym))
2710           {
2711             log_info(_("you must use files (and not a pipe) when "
2712                        "working with --pgp2 enabled.\n"));
2713             unusable=1;
2714           }
2715         else if(cmd==aEncr || cmd==aSym)
2716           {
2717             /* Everything else should work without IDEA (except using
2718                a secret key encrypted with IDEA and setting an IDEA
2719                preference, but those have their own error
2720                messages). */
2721
2722             if(check_cipher_algo(CIPHER_ALGO_IDEA))
2723               {
2724                 log_info(_("encrypting a message in --pgp2 mode requires "
2725                            "the IDEA cipher\n"));
2726                 idea_cipher_warn(1);
2727                 unusable=1;
2728               }
2729             else if(cmd==aSym)
2730               {
2731                 /* This only sets IDEA for symmetric encryption
2732                    since it is set via select_algo_from_prefs for
2733                    pk encryption. */
2734                 xfree(def_cipher_string);
2735                 def_cipher_string = xstrdup("idea");
2736               }
2737
2738             /* PGP2 can't handle the output from the textmode
2739                filter, so we disable it for anything that could
2740                create a literal packet (only encryption and
2741                symmetric encryption, since we disable signing
2742                above). */
2743             if(!unusable)
2744               opt.textmode=0;
2745           }
2746
2747         if(unusable)
2748           compliance_failure();
2749         else
2750           {
2751             opt.force_v4_certs = 0;
2752             opt.escape_from = 1;
2753             opt.force_v3_sigs = 1;
2754             opt.pgp2_workarounds = 1;
2755             opt.ask_sig_expire = 0;
2756             opt.ask_cert_expire = 0;
2757             xfree(def_digest_string);
2758             def_digest_string = xstrdup("md5");
2759             xfree(s2k_digest_string);
2760             s2k_digest_string = xstrdup("md5");
2761             opt.compress_algo = COMPRESS_ALGO_ZIP;
2762           }
2763       }
2764     else if(PGP6)
2765       {
2766         opt.escape_from=1;
2767         opt.force_v3_sigs=1;
2768         opt.ask_sig_expire=0;
2769       }
2770     else if(PGP7)
2771       {
2772         opt.escape_from=1;
2773         opt.force_v3_sigs=1;
2774         opt.ask_sig_expire=0;
2775       }
2776     else if(PGP8)
2777       {
2778         opt.escape_from=1;
2779       }
2780
2781     /* must do this after dropping setuid, because string_to...
2782      * may try to load an module */
2783     if( def_cipher_string ) {
2784         opt.def_cipher_algo = string_to_cipher_algo(def_cipher_string);
2785         if(opt.def_cipher_algo==0 &&
2786            (ascii_strcasecmp(def_cipher_string,"idea")==0
2787             || ascii_strcasecmp(def_cipher_string,"s1")==0))
2788           idea_cipher_warn(1);
2789         xfree(def_cipher_string); def_cipher_string = NULL;
2790         if( check_cipher_algo(opt.def_cipher_algo) )
2791             log_error(_("selected cipher algorithm is invalid\n"));
2792     }
2793     if( def_digest_string ) {
2794         opt.def_digest_algo = string_to_digest_algo(def_digest_string);
2795         xfree(def_digest_string); def_digest_string = NULL;
2796         if( check_digest_algo(opt.def_digest_algo) )
2797             log_error(_("selected digest algorithm is invalid\n"));
2798     }
2799     if( compress_algo_string ) {
2800         opt.compress_algo = string_to_compress_algo(compress_algo_string);
2801         xfree(compress_algo_string); compress_algo_string = NULL;
2802         if( check_compress_algo(opt.compress_algo) )
2803             log_error(_("selected compression algorithm is invalid\n"));
2804     }
2805     if( cert_digest_string ) {
2806         opt.cert_digest_algo = string_to_digest_algo(cert_digest_string);
2807         xfree(cert_digest_string); cert_digest_string = NULL;
2808         if( check_digest_algo(opt.cert_digest_algo) )
2809             log_error(_("selected certification digest algorithm is invalid\n"));
2810     }
2811     if( s2k_cipher_string ) {
2812         opt.s2k_cipher_algo = string_to_cipher_algo(s2k_cipher_string);
2813         xfree(s2k_cipher_string); s2k_cipher_string = NULL;
2814         if( check_cipher_algo(opt.s2k_cipher_algo) )
2815             log_error(_("selected cipher algorithm is invalid\n"));
2816     }
2817     if( s2k_digest_string ) {
2818         opt.s2k_digest_algo = string_to_digest_algo(s2k_digest_string);
2819         xfree(s2k_digest_string); s2k_digest_string = NULL;
2820         if( check_digest_algo(opt.s2k_digest_algo) )
2821             log_error(_("selected digest algorithm is invalid\n"));
2822     }
2823     if( opt.completes_needed < 1 )
2824       log_error(_("completes-needed must be greater than 0\n"));
2825     if( opt.marginals_needed < 2 )
2826       log_error(_("marginals-needed must be greater than 1\n"));
2827     if( opt.max_cert_depth < 1 || opt.max_cert_depth > 255 )
2828       log_error(_("max-cert-depth must be in the range from 1 to 255\n"));
2829     if(opt.def_cert_level<0 || opt.def_cert_level>3)
2830       log_error(_("invalid default-cert-level; must be 0, 1, 2, or 3\n"));
2831     if( opt.min_cert_level < 1 || opt.min_cert_level > 3 )
2832       log_error(_("invalid min-cert-level; must be 1, 2, or 3\n"));
2833     switch( opt.s2k_mode ) {
2834       case 0:
2835         log_info(_("NOTE: simple S2K mode (0) is strongly discouraged\n"));
2836         break;
2837       case 1: case 3: break;
2838       default:
2839         log_error(_("invalid S2K mode; must be 0, 1 or 3\n"));
2840     }
2841
2842     /* This isn't actually needed, but does serve to error out if the
2843        string is invalid. */
2844     if(opt.def_preference_list &&
2845         keygen_set_std_prefs(opt.def_preference_list,0))
2846       log_error(_("invalid default preferences\n"));
2847
2848     /* We provide defaults for the personal digest list.  This is
2849        SHA-1. */
2850     if(!pers_digest_list)
2851       pers_digest_list="h2";
2852
2853     if(pers_cipher_list &&
2854        keygen_set_std_prefs(pers_cipher_list,PREFTYPE_SYM))
2855       log_error(_("invalid personal cipher preferences\n"));
2856
2857     if(pers_digest_list &&
2858        keygen_set_std_prefs(pers_digest_list,PREFTYPE_HASH))
2859       log_error(_("invalid personal digest preferences\n"));
2860
2861     if(pers_compress_list &&
2862        keygen_set_std_prefs(pers_compress_list,PREFTYPE_ZIP))
2863       log_error(_("invalid personal compress preferences\n"));
2864
2865     /* We don't support all possible commands with multifile yet */
2866     if(multifile)
2867       {
2868         char *cmdname;
2869
2870         switch(cmd)
2871           {
2872           case aSign:
2873             cmdname="--sign";
2874             break;
2875           case aClearsign:
2876             cmdname="--clearsign";
2877             break;
2878           case aDetachedSign:
2879             cmdname="--detach-sign";
2880             break;
2881           case aSym:
2882             cmdname="--symmetric";
2883             break;
2884           case aEncrSym:
2885             cmdname="--symmetric --encrypt";
2886             break;
2887           case aStore:
2888             cmdname="--store";
2889             break;
2890           default:
2891             cmdname=NULL;
2892             break;
2893           }
2894
2895         if(cmdname)
2896           log_error(_("%s does not yet work with %s\n"),cmdname,"--multifile");
2897       }
2898
2899     if( log_get_errorcount(0) )
2900         g10_exit(2);
2901
2902     if(opt.compress_level==0)
2903       opt.compress_algo=COMPRESS_ALGO_NONE;
2904
2905     /* Check our chosen algorithms against the list of legal
2906        algorithms. */
2907
2908     if(!GNUPG)
2909       {
2910         const char *badalg=NULL;
2911         preftype_t badtype=PREFTYPE_NONE;
2912
2913         if(opt.def_cipher_algo
2914            && !algo_available(PREFTYPE_SYM,opt.def_cipher_algo,NULL))
2915           {
2916             badalg=cipher_algo_to_string(opt.def_cipher_algo);
2917             badtype=PREFTYPE_SYM;
2918           }
2919         else if(opt.def_digest_algo
2920                 && !algo_available(PREFTYPE_HASH,opt.def_digest_algo,NULL))
2921           {
2922             badalg=digest_algo_to_string(opt.def_digest_algo);
2923             badtype=PREFTYPE_HASH;
2924           }
2925         else if(opt.cert_digest_algo
2926                 && !algo_available(PREFTYPE_HASH,opt.cert_digest_algo,NULL))
2927           {
2928             badalg=digest_algo_to_string(opt.cert_digest_algo);
2929             badtype=PREFTYPE_HASH;
2930           }
2931         else if(opt.compress_algo!=-1
2932                 && !algo_available(PREFTYPE_ZIP,opt.compress_algo,NULL))
2933           {
2934             badalg=compress_algo_to_string(opt.compress_algo);
2935             badtype=PREFTYPE_ZIP;
2936           }
2937
2938         if(badalg)
2939           {
2940             switch(badtype)
2941               {
2942               case PREFTYPE_SYM:
2943                 log_info(_("you may not use cipher algorithm `%s'"
2944                            " while in %s mode\n"),
2945                          badalg,compliance_option_string());
2946                 break;
2947               case PREFTYPE_HASH:
2948                 log_info(_("you may not use digest algorithm `%s'"
2949                            " while in %s mode\n"),
2950                          badalg,compliance_option_string());
2951                 break;
2952               case PREFTYPE_ZIP:
2953                 log_info(_("you may not use compression algorithm `%s'"
2954                            " while in %s mode\n"),
2955                          badalg,compliance_option_string());
2956                 break;
2957               default:
2958                 BUG();
2959               }
2960
2961             compliance_failure();
2962           }
2963       }
2964
2965     /* set the random seed file */
2966     if( use_random_seed ) {
2967         char *p = make_filename(opt.homedir, "random_seed", NULL );
2968         set_random_seed_file(p);
2969         if (!access (p, F_OK))
2970           register_secured_file (p);
2971         xfree(p);
2972     }
2973
2974     if( !cmd && opt.fingerprint && !with_fpr ) {
2975         set_cmd( &cmd, aListKeys);
2976     }
2977
2978     if( cmd == aKMode || cmd == aKModeC ) { /* kludge to be compatible to pgp */
2979         if( cmd == aKModeC ) {
2980             opt.fingerprint = 1;
2981             cmd = aKMode;
2982         }
2983         opt.list_sigs = 0;
2984         if( opt.verbose > 2 )
2985             opt.check_sigs++;
2986         if( opt.verbose > 1 )
2987             opt.list_sigs++;
2988
2989         opt.verbose = opt.verbose > 1;
2990         g10_opt_verbose = opt.verbose;
2991     }
2992
2993     /* kludge to let -sat generate a clear text signature */
2994     if( opt.textmode == 2 && !detached_sig && opt.armor && cmd == aSign )
2995         cmd = aClearsign;
2996
2997     if( opt.verbose > 1 )
2998         set_packet_list_mode(1);
2999
3000     /* Add the keyrings, but not for some special commands and not in
3001        case of "-kvv userid keyring".  Also avoid adding the secret
3002        keyring for a couple of commands to avoid unneeded access in
3003        case the secrings are stored on a floppy.
3004        
3005        We always need to add the keyrings if we are running under
3006        SELinux, this is so that the rings are added to the list of
3007        secured files. */
3008     if( ALWAYS_ADD_KEYRINGS 
3009         || (cmd != aDeArmor && cmd != aEnArmor
3010             && !(cmd == aKMode && argc == 2 )) ) 
3011       {
3012         if (ALWAYS_ADD_KEYRINGS
3013             || (cmd != aCheckKeys && cmd != aListSigs && cmd != aListKeys
3014                 && cmd != aVerify && cmd != aSym))
3015           {
3016             if (!sec_nrings || default_keyring) /* add default secret rings */
3017               keydb_add_resource ("secring" EXTSEP_S "gpg", 4, 1);
3018             for (sl = sec_nrings; sl; sl = sl->next)
3019               keydb_add_resource ( sl->d, 0, 1 );
3020           }
3021         if( !nrings || default_keyring )  /* add default ring */
3022             keydb_add_resource ("pubring" EXTSEP_S "gpg", 4, 0);
3023         for(sl = nrings; sl; sl = sl->next )
3024             keydb_add_resource ( sl->d, sl->flags, 0 );
3025       }
3026     FREE_STRLIST(nrings);
3027     FREE_STRLIST(sec_nrings);
3028
3029
3030     if( pwfd != -1 )  /* read the passphrase now. */
3031         read_passphrase_from_fd( pwfd );
3032
3033     fname = argc? *argv : NULL;
3034
3035     switch( cmd ) {
3036       case aPrimegen:
3037       case aPrintMD:
3038       case aPrintMDs:
3039       case aGenRandom:
3040       case aDeArmor:
3041       case aEnArmor:
3042       case aFixTrustDB:
3043         break;
3044       case aExportOwnerTrust: rc = setup_trustdb( 0, trustdb_name ); break;
3045       case aListTrustDB: rc = setup_trustdb( argc? 1:0, trustdb_name ); break;
3046       default: rc = setup_trustdb(1, trustdb_name ); break;
3047     }
3048     if( rc )
3049         log_error(_("failed to initialize the TrustDB: %s\n"), g10_errstr(rc));
3050
3051
3052     switch (cmd)
3053       {
3054       case aStore: 
3055       case aSym:  
3056       case aSign: 
3057       case aSignSym: 
3058       case aClearsign: 
3059         if (!opt.quiet && any_explicit_recipient)
3060           log_info (_("WARNING: recipients (-r) given "
3061                       "without using public key encryption\n"));
3062         break;
3063       default:
3064         break;
3065       }
3066
3067     switch( cmd )
3068       {
3069       case aStore: /* only store the file */
3070         if( argc > 1 )
3071             wrong_args(_("--store [filename]"));
3072         if( (rc = encode_store(fname)) )
3073             log_error ("storing `%s' failed: %s\n",
3074                        print_fname_stdin(fname),g10_errstr(rc) );
3075         break;
3076       case aSym: /* encrypt the given file only with the symmetric cipher */
3077         if( argc > 1 )
3078             wrong_args(_("--symmetric [filename]"));
3079         if( (rc = encode_symmetric(fname)) )
3080             log_error (_("symmetric encryption of `%s' failed: %s\n"),
3081                         print_fname_stdin(fname),g10_errstr(rc) );
3082         break;
3083
3084       case aEncr: /* encrypt the given file */
3085         if(multifile)
3086           encode_crypt_files(argc, argv, remusr);
3087         else
3088           {
3089             if( argc > 1 )
3090               wrong_args(_("--encrypt [filename]"));
3091             if( (rc = encode_crypt(fname,remusr,0)) )
3092               log_error("%s: encryption failed: %s\n",
3093                         print_fname_stdin(fname), g10_errstr(rc) );
3094           }
3095         break;
3096
3097       case aEncrSym:
3098         /* This works with PGP 8 in the sense that it acts just like a
3099            symmetric message.  It doesn't work at all with 2 or 6.  It
3100            might work with 7, but alas, I don't have a copy to test
3101            with right now. */
3102         if( argc > 1 )
3103           wrong_args(_("--symmetric --encrypt [filename]"));
3104         else if(opt.s2k_mode==0)
3105           log_error(_("you cannot use --symmetric --encrypt"
3106                       " with --s2k-mode 0\n"));
3107         else if(PGP2 || PGP6 || PGP7 || RFC1991)
3108           log_error(_("you cannot use --symmetric --encrypt"
3109                       " while in %s mode\n"),compliance_option_string());
3110         else
3111           {
3112             if( (rc = encode_crypt(fname,remusr,1)) )
3113               log_error("%s: encryption failed: %s\n",
3114                         print_fname_stdin(fname), g10_errstr(rc) );
3115           }
3116         break;
3117
3118       case aSign: /* sign the given file */
3119         sl = NULL;
3120         if( detached_sig ) { /* sign all files */
3121             for( ; argc; argc--, argv++ )
3122                 add_to_strlist( &sl, *argv );
3123         }
3124         else {
3125             if( argc > 1 )
3126                 wrong_args(_("--sign [filename]"));
3127             if( argc ) {
3128                 sl = xmalloc_clear( sizeof *sl + strlen(fname));
3129                 strcpy(sl->d, fname);
3130             }
3131         }
3132         if( (rc = sign_file( sl, detached_sig, locusr, 0, NULL, NULL)) )
3133             log_error("signing failed: %s\n", g10_errstr(rc) );
3134         free_strlist(sl);
3135         break;
3136
3137       case aSignEncr: /* sign and encrypt the given file */
3138         if( argc > 1 )
3139             wrong_args(_("--sign --encrypt [filename]"));
3140         if( argc ) {
3141             sl = xmalloc_clear( sizeof *sl + strlen(fname));
3142             strcpy(sl->d, fname);
3143         }
3144         else
3145             sl = NULL;
3146         if( (rc = sign_file(sl, detached_sig, locusr, 1, remusr, NULL)) )
3147             log_error("%s: sign+encrypt failed: %s\n",
3148                       print_fname_stdin(fname), g10_errstr(rc) );
3149         free_strlist(sl);
3150         break;
3151
3152       case aSignEncrSym: /* sign and encrypt the given file */
3153         if( argc > 1 )
3154             wrong_args(_("--symmetric --sign --encrypt [filename]"));
3155         else if(opt.s2k_mode==0)
3156           log_error(_("you cannot use --symmetric --sign --encrypt"
3157                       " with --s2k-mode 0\n"));
3158         else if(PGP2 || PGP6 || PGP7 || RFC1991)
3159           log_error(_("you cannot use --symmetric --sign --encrypt"
3160                       " while in %s mode\n"),compliance_option_string());
3161         else
3162           {
3163             if( argc )
3164               {
3165                 sl = xmalloc_clear( sizeof *sl + strlen(fname));
3166                 strcpy(sl->d, fname);
3167               }
3168             else
3169               sl = NULL;
3170             if( (rc = sign_file(sl, detached_sig, locusr, 2, remusr, NULL)) )
3171               log_error("%s: symmetric+sign+encrypt failed: %s\n",
3172                         print_fname_stdin(fname), g10_errstr(rc) );
3173             free_strlist(sl);
3174           }
3175         break;
3176
3177       case aSignSym: /* sign and conventionally encrypt the given file */
3178         if (argc > 1)
3179             wrong_args(_("--sign --symmetric [filename]"));
3180         rc = sign_symencrypt_file (fname, locusr);
3181         if (rc)
3182             log_error("%s: sign+symmetric failed: %s\n",
3183                       print_fname_stdin(fname), g10_errstr(rc) );
3184         break;
3185
3186       case aClearsign: /* make a clearsig */
3187         if( argc > 1 )
3188             wrong_args(_("--clearsign [filename]"));
3189         if( (rc = clearsign_file(fname, locusr, NULL)) )
3190             log_error("%s: clearsign failed: %s\n",
3191                       print_fname_stdin(fname), g10_errstr(rc) );
3192         break;
3193
3194       case aVerify:
3195         if(multifile)
3196           {
3197             if( (rc = verify_files( argc, argv ) ))
3198               log_error("verify files failed: %s\n", g10_errstr(rc) );
3199           }
3200         else
3201           {
3202             if( (rc = verify_signatures( argc, argv ) ))
3203               log_error("verify signatures failed: %s\n", g10_errstr(rc) );
3204           }
3205         break;
3206
3207       case aDecrypt:
3208         if(multifile)
3209           decrypt_messages(argc, argv);
3210         else
3211           {
3212             if( argc > 1 )
3213               wrong_args(_("--decrypt [filename]"));
3214             if( (rc = decrypt_message( fname ) ))
3215               log_error("decrypt_message failed: %s\n", g10_errstr(rc) );
3216           }
3217         break;
3218             
3219       case aSignKey:
3220         if( argc != 1 )
3221           wrong_args(_("--sign-key user-id"));
3222         /* fall through */
3223       case aLSignKey:
3224         if( argc != 1 )
3225           wrong_args(_("--lsign-key user-id"));
3226         /* fall through */
3227
3228         sl=NULL;
3229
3230         if(cmd==aSignKey)
3231           append_to_strlist(&sl,"sign");
3232         else if(cmd==aLSignKey)
3233           append_to_strlist(&sl,"lsign");
3234         else
3235           BUG();
3236
3237         append_to_strlist( &sl, "save" );
3238         username = make_username( fname );
3239         keyedit_menu(fname, locusr, sl, 0, 0 );
3240         xfree(username);
3241         free_strlist(sl);
3242         break;
3243
3244       case aEditKey: /* Edit a key signature */
3245         if( !argc )
3246             wrong_args(_("--edit-key user-id [commands]"));
3247         username = make_username( fname );
3248         if( argc > 1 ) {
3249             sl = NULL;
3250             for( argc--, argv++ ; argc; argc--, argv++ )
3251                 append_to_strlist( &sl, *argv );
3252             keyedit_menu( username, locusr, sl, 0, 1 );
3253             free_strlist(sl);
3254         }
3255         else
3256             keyedit_menu(username, locusr, NULL, 0, 1 );
3257         xfree(username);
3258         break;
3259
3260       case aDeleteKeys:
3261       case aDeleteSecretKeys:
3262       case aDeleteSecretAndPublicKeys:
3263         sl = NULL;
3264         /* I'm adding these in reverse order as add_to_strlist2
3265            reverses them again, and it's easier to understand in the
3266            proper order :) */
3267         for( ; argc; argc-- )
3268           add_to_strlist2( &sl, argv[argc-1], utf8_strings );
3269         delete_keys(sl,cmd==aDeleteSecretKeys,cmd==aDeleteSecretAndPublicKeys);
3270         free_strlist(sl);
3271         break;
3272
3273       case aCheckKeys:
3274         opt.check_sigs = 1;
3275       case aListSigs:
3276         opt.list_sigs = 1;
3277       case aListKeys:
3278         sl = NULL;
3279         for( ; argc; argc--, argv++ )
3280             add_to_strlist2( &sl, *argv, utf8_strings );
3281         public_key_list( sl );
3282         free_strlist(sl);
3283         break;
3284       case aListSecretKeys:
3285         sl = NULL;
3286         for( ; argc; argc--, argv++ )
3287             add_to_strlist2( &sl, *argv, utf8_strings );
3288         secret_key_list( sl );
3289         free_strlist(sl);
3290         break;
3291
3292       case aKMode: /* list keyring -- NOTE: This will be removed soon */
3293         if( argc < 2 ) { /* -kv [userid] */
3294             sl = NULL;
3295             if (argc && **argv)
3296                 add_to_strlist2( &sl, *argv, utf8_strings );
3297             public_key_list( sl );
3298             free_strlist(sl);
3299         }
3300         else if( argc == 2 ) { /* -kv userid keyring */
3301             if( access( argv[1], R_OK ) ) {
3302                 log_error(_("can't open `%s': %s\n"),
3303                                print_fname_stdin(argv[1]), strerror(errno));
3304             }
3305             else {
3306                 /* add keyring (default keyrings are not registered in this
3307                  * special case */
3308                 keydb_add_resource( argv[1], 0, 0 );
3309                 sl = NULL;
3310                 if (**argv)
3311                     add_to_strlist2( &sl, *argv, utf8_strings );
3312                 public_key_list( sl );
3313                 free_strlist(sl);
3314             }
3315         }
3316         else
3317             wrong_args(_("-k[v][v][v][c] [user-id] [keyring]") );
3318         break;
3319
3320       case aKeygen: /* generate a key */
3321         if( opt.batch ) {
3322             if( argc > 1 )
3323                 wrong_args("--gen-key [parameterfile]");
3324             generate_keypair( argc? *argv : NULL, NULL, NULL );
3325         }
3326         else {
3327             if( argc )
3328                 wrong_args("--gen-key");
3329             generate_keypair(NULL, NULL, NULL);
3330         }
3331         break;
3332
3333       case aFastImport:
3334         opt.import_options |= IMPORT_FAST;
3335       case aImport:
3336         import_keys( argc? argv:NULL, argc, NULL, opt.import_options );
3337         break;
3338
3339       case aExport:
3340       case aSendKeys:
3341       case aRecvKeys:
3342         sl = NULL;
3343         for( ; argc; argc--, argv++ )
3344             add_to_strlist2( &sl, *argv, utf8_strings );
3345         if( cmd == aSendKeys )
3346             rc=keyserver_export( sl );
3347         else if( cmd == aRecvKeys )
3348             rc=keyserver_import( sl );
3349         else
3350             rc=export_pubkeys( sl, opt.export_options );
3351         if(rc)
3352           {
3353             if(cmd==aSendKeys)
3354               log_error(_("keyserver send failed: %s\n"),g10_errstr(rc));
3355             else if(cmd==aRecvKeys)
3356               log_error(_("keyserver receive failed: %s\n"),g10_errstr(rc));
3357             else
3358               log_error(_("key export failed: %s\n"),g10_errstr(rc));
3359           }
3360         free_strlist(sl);
3361         break;
3362
3363      case aSearchKeys:
3364         sl = NULL;
3365         for( ; argc; argc--, argv++ )
3366           append_to_strlist2( &sl, *argv, utf8_strings );
3367         rc=keyserver_search( sl );
3368         if(rc)
3369           log_error(_("keyserver search failed: %s\n"),g10_errstr(rc));
3370         free_strlist(sl);
3371         break;
3372
3373       case aRefreshKeys:
3374         sl = NULL;
3375         for( ; argc; argc--, argv++ )
3376             add_to_strlist2( &sl, *argv, utf8_strings );
3377         rc=keyserver_refresh(sl);
3378         if(rc)
3379           log_error(_("keyserver refresh failed: %s\n"),g10_errstr(rc));
3380         free_strlist(sl);
3381         break;
3382
3383       case aExportSecret:
3384         sl = NULL;
3385         for( ; argc; argc--, argv++ )
3386             add_to_strlist2( &sl, *argv, utf8_strings );
3387         export_seckeys( sl );
3388         free_strlist(sl);
3389         break;
3390
3391       case aExportSecretSub:
3392         sl = NULL;
3393         for( ; argc; argc--, argv++ )
3394             add_to_strlist2( &sl, *argv, utf8_strings );
3395         export_secsubkeys( sl );
3396         free_strlist(sl);
3397         break;
3398
3399       case aGenRevoke:
3400         if( argc != 1 )
3401             wrong_args("--gen-revoke user-id");
3402         username =  make_username(*argv);
3403         gen_revoke( username );
3404         xfree( username );
3405         break;
3406
3407       case aDesigRevoke:
3408         if( argc != 1 )
3409             wrong_args("--desig-revoke user-id");
3410         username =  make_username(*argv);
3411         gen_desig_revoke( username );
3412         xfree( username );
3413         break;
3414
3415       case aDeArmor:
3416         if( argc > 1 )
3417             wrong_args("--dearmor [file]");
3418         rc = dearmor_file( argc? *argv: NULL );
3419         if( rc )
3420             log_error(_("dearmoring failed: %s\n"), g10_errstr(rc));
3421         break;
3422
3423       case aEnArmor:
3424         if( argc > 1 )
3425             wrong_args("--enarmor [file]");
3426         rc = enarmor_file( argc? *argv: NULL );
3427         if( rc )
3428             log_error(_("enarmoring failed: %s\n"), g10_errstr(rc));
3429         break;
3430
3431
3432       case aPrimegen:
3433         {   int mode = argc < 2 ? 0 : atoi(*argv);
3434
3435             if( mode == 1 && argc == 2 ) {
3436                 mpi_print( stdout, generate_public_prime( atoi(argv[1]) ), 1);
3437             }
3438             else if( mode == 2 && argc == 3 ) {
3439                 mpi_print( stdout, generate_elg_prime(
3440                                              0, atoi(argv[1]),
3441                                              atoi(argv[2]), NULL,NULL ), 1);
3442             }
3443             else if( mode == 3 && argc == 3 ) {
3444                 MPI *factors;
3445                 mpi_print( stdout, generate_elg_prime(
3446                                              1, atoi(argv[1]),
3447                                              atoi(argv[2]), NULL,&factors ), 1);
3448                 putchar('\n');
3449                 mpi_print( stdout, factors[0], 1 ); /* print q */
3450             }
3451             else if( mode == 4 && argc == 3 ) {
3452                 MPI g = mpi_alloc(1);
3453                 mpi_print( stdout, generate_elg_prime(
3454                                                  0, atoi(argv[1]),
3455                                                  atoi(argv[2]), g, NULL ), 1);
3456                 putchar('\n');
3457                 mpi_print( stdout, g, 1 );
3458                 mpi_free(g);
3459             }
3460             else
3461                 wrong_args("--gen-prime mode bits [qbits] ");
3462             putchar('\n');
3463         }
3464         break;
3465
3466       case aGenRandom:
3467         {
3468             int level = argc ? atoi(*argv):0;
3469             int count = argc > 1 ? atoi(argv[1]): 0;
3470             int endless = !count;
3471
3472             if( argc < 1 || argc > 2 || level < 0 || level > 2 || count < 0 )
3473                 wrong_args("--gen-random 0|1|2 [count]");
3474
3475             while( endless || count ) {
3476                 byte *p;
3477                 /* Wee need a multiple of 3, so that in case of
3478                    armored output we get a correct string.  No
3479                    linefolding is done, as it is best to levae this to
3480                    other tools */
3481                 size_t n = !endless && count < 99? count : 99;
3482
3483                 p = get_random_bits( n*8, level, 0);
3484 #ifdef HAVE_DOSISH_SYSTEM
3485                 setmode ( fileno(stdout), O_BINARY );
3486 #endif
3487                 if (opt.armor) {
3488                     char *tmp = make_radix64_string (p, n);
3489                     fputs (tmp, stdout);
3490                     xfree (tmp);
3491                     if (n%3 == 1)
3492                       putchar ('=');
3493                     if (n%3)
3494                       putchar ('=');
3495                 } else {
3496                     fwrite( p, n, 1, stdout );
3497                 }
3498                 xfree(p);
3499                 if( !endless )
3500                     count -= n;
3501             }
3502             if (opt.armor)
3503                 putchar ('\n');
3504         }
3505         break;
3506
3507       case aPrintMD:
3508         if( argc < 1)
3509             wrong_args("--print-md algo [files]");
3510         {
3511             int all_algos = (**argv=='*' && !(*argv)[1]);
3512             int algo = all_algos? 0 : string_to_digest_algo(*argv);
3513
3514             if( !algo && !all_algos )
3515                 log_error(_("invalid hash algorithm `%s'\n"), *argv );
3516             else {
3517                 argc--; argv++;
3518                 if( !argc )
3519                     print_mds(NULL, algo);
3520                 else {
3521                     for(; argc; argc--, argv++ )
3522                         print_mds(*argv, algo);
3523                 }
3524             }
3525         }
3526         break;
3527
3528       case aPrintMDs: /* old option */
3529         if( !argc )
3530             print_mds(NULL,0);
3531         else {
3532             for(; argc; argc--, argv++ )
3533                 print_mds(*argv,0);
3534         }
3535         break;
3536
3537       case aListTrustDB:
3538         if( !argc )
3539             list_trustdb(NULL);
3540         else {
3541             for( ; argc; argc--, argv++ )
3542                 list_trustdb( *argv );
3543         }
3544         break;
3545
3546       case aUpdateTrustDB:
3547         if( argc )
3548             wrong_args("--update-trustdb");
3549         update_trustdb();
3550         break;
3551
3552       case aCheckTrustDB:
3553         /* Old versions allowed for arguments - ignore them */
3554         check_trustdb();
3555         break;
3556
3557       case aFixTrustDB:
3558         log_error("this command is not yet implemented.\n");
3559         log_error("A workaround is to use \"--export-ownertrust\", remove\n");
3560         log_error("the trustdb file and do an \"--import-ownertrust\".\n" );
3561         break;
3562
3563       case aListTrustPath:
3564         if( !argc )
3565             wrong_args("--list-trust-path <user-ids>");
3566         for( ; argc; argc--, argv++ ) {
3567             username = make_username( *argv );
3568             list_trust_path( username );
3569             xfree(username);
3570         }
3571         break;
3572
3573       case aExportOwnerTrust:
3574         if( argc )
3575             wrong_args("--export-ownertrust");
3576         export_ownertrust();
3577         break;
3578
3579       case aImportOwnerTrust:
3580         if( argc > 1 )
3581             wrong_args("--import-ownertrust [file]");
3582         import_ownertrust( argc? *argv:NULL );
3583         break;
3584       
3585       case aPipeMode:
3586         if ( argc )
3587             wrong_args ("--pipemode");
3588         run_in_pipemode ();
3589         break;
3590
3591       case aRebuildKeydbCaches:
3592         if (argc)
3593             wrong_args ("--rebuild-keydb-caches");
3594         keydb_rebuild_caches (1);
3595         break;
3596
3597 #ifdef ENABLE_CARD_SUPPORT
3598       case aCardStatus:
3599         if (argc)
3600             wrong_args ("--card-status");
3601         card_status (stdout, NULL, 0);
3602         break;
3603
3604       case aCardEdit:
3605         if (argc) {
3606             sl = NULL;
3607             for (argc--, argv++ ; argc; argc--, argv++)
3608                 append_to_strlist (&sl, *argv);
3609             card_edit (sl);
3610             free_strlist (sl);
3611         }
3612         else
3613             card_edit (NULL);
3614         break;
3615
3616       case aChangePIN:
3617         if (!argc)
3618             change_pin (0,1);
3619         else if (argc == 1)
3620             change_pin (atoi (*argv),1);
3621         else
3622         wrong_args ("--change-pin [no]");
3623         break;
3624 #endif /* ENABLE_CARD_SUPPORT*/
3625
3626       case aListConfig:
3627         {
3628           char *str=collapse_args(argc,argv);
3629           list_config(str);
3630           xfree(str);
3631         }
3632         break;
3633
3634       case aListPackets:
3635         opt.list_packets=2;
3636       default:
3637         if( argc > 1 )
3638             wrong_args(_("[filename]"));
3639         /* Issue some output for the unix newbie */
3640         if( !fname && !opt.outfile && isatty( fileno(stdin) )
3641                 && isatty( fileno(stdout) ) && isatty( fileno(stderr) ) )
3642             log_info(_("Go ahead and type your message ...\n"));
3643
3644         a = iobuf_open(fname);
3645         if (a && is_secured_file (iobuf_get_fd (a)))
3646           {
3647             iobuf_close (a);
3648             a = NULL;
3649             errno = EPERM;
3650           }
3651         if( !a )
3652             log_error(_("can't open `%s'\n"), print_fname_stdin(fname));
3653         else {
3654
3655             if( !opt.no_armor ) {
3656                 if( use_armor_filter( a ) ) {
3657                     memset( &afx, 0, sizeof afx);
3658                     iobuf_push_filter( a, armor_filter, &afx );
3659                 }
3660             }
3661             if( cmd == aListPackets ) {
3662                 set_packet_list_mode(1);
3663                 opt.list_packets=1;
3664             }
3665             rc = proc_packets(NULL, a );
3666             if( rc )
3667                 log_error("processing message failed: %s\n", g10_errstr(rc) );
3668             iobuf_close(a);
3669         }
3670         break;
3671       }
3672
3673     /* cleanup */
3674     FREE_STRLIST(remusr);
3675     FREE_STRLIST(locusr);
3676     g10_exit(0);
3677     return 8; /*NEVER REACHED*/
3678 }
3679
3680
3681 void
3682 g10_exit( int rc )
3683 {
3684 #ifdef ENABLE_CARD_SUPPORT
3685     card_close ();
3686 #endif
3687     update_random_seed_file();
3688     if( opt.debug & DBG_MEMSTAT_VALUE ) {
3689         m_print_stats("on exit");
3690         random_dump_stats();
3691     }
3692     if( opt.debug )
3693         secmem_dump_stats();
3694     secmem_term();
3695     rc = rc? rc : log_get_errorcount(0)? 2 :
3696                         g10_errors_seen? 1 : 0;
3697     exit(rc );
3698 }
3699
3700
3701 /* Pretty-print hex hashes.  This assumes at least an 80-character
3702    display, but there are a few other similar assumptions in the
3703    display code. */
3704 static void
3705 print_hex( MD_HANDLE md, int algo, const char *fname )
3706 {
3707   int i,n,count,indent=0;
3708   const byte *p;
3709
3710   if(fname)
3711     indent=printf("%s: ",fname);
3712
3713   if(indent>40)
3714     {
3715       printf("\n");
3716       indent=0;
3717     }
3718
3719   if(algo==DIGEST_ALGO_RMD160)
3720     indent+=printf("RMD160 = ");
3721   else if(algo>0)
3722     indent+=printf("%6s = ",digest_algo_to_string(algo));
3723   else
3724     algo=abs(algo);
3725
3726   count=indent;
3727
3728   p = md_read( md, algo );
3729   n = md_digest_length(algo);
3730
3731   count+=printf("%02X",*p++);
3732
3733   for(i=1;i<n;i++,p++)
3734     {
3735       if(n==16)
3736         {
3737           if(count+2>79)
3738             {
3739               printf("\n%*s",indent," ");
3740               count=indent;
3741             }
3742           else
3743             count+=printf(" ");
3744
3745           if(!(i%8))
3746             count+=printf(" ");
3747         }
3748       else if (n==20)
3749         {
3750           if(!(i%2))
3751             {
3752               if(count+4>79)
3753                 {
3754                   printf("\n%*s",indent," ");
3755                   count=indent;
3756                 }
3757               else
3758                 count+=printf(" ");
3759             }
3760
3761           if(!(i%10))
3762             count+=printf(" ");
3763         }
3764       else
3765         {
3766           if(!(i%4))
3767             {
3768               if(count+8>79)
3769                 {
3770                   printf("\n%*s",indent," ");
3771                   count=indent;
3772                 }
3773               else
3774                 count+=printf(" ");
3775             }
3776         }
3777
3778       count+=printf("%02X",*p);
3779     }
3780
3781   printf("\n");
3782 }
3783
3784 static void
3785 print_hashline( MD_HANDLE md, int algo, const char *fname )
3786 {
3787     int i, n;
3788     const byte *p;
3789     
3790     if ( fname ) {
3791         for (p = fname; *p; p++ ) {
3792             if ( *p <= 32 || *p > 127 || *p == ':' || *p == '%' )
3793                 printf("%%%02X", *p );
3794             else 
3795                 putchar( *p );
3796         }
3797     }
3798     putchar(':');
3799     printf("%d:", algo );
3800     p = md_read( md, algo );
3801     n = md_digest_length(algo);
3802     for(i=0; i < n ; i++, p++ ) 
3803         printf("%02X", *p );
3804     putchar(':');
3805     putchar('\n');
3806 }
3807
3808 static void
3809 print_mds( const char *fname, int algo )
3810 {
3811     FILE *fp;
3812     char buf[1024];
3813     size_t n;
3814     MD_HANDLE md;
3815
3816     if( !fname ) {
3817         fp = stdin;
3818 #ifdef HAVE_DOSISH_SYSTEM
3819         setmode ( fileno(fp) , O_BINARY );
3820 #endif
3821     }
3822     else {
3823         fp = fopen( fname, "rb" );
3824         if (fp && is_secured_file (fileno (fp)))
3825           {
3826             fclose (fp);
3827             fp = NULL;
3828             errno = EPERM;
3829           }
3830     }
3831     if( !fp ) {
3832         log_error("%s: %s\n", fname?fname:"[stdin]", strerror(errno) );
3833         return;
3834     }
3835
3836     md = md_open( 0, 0 );
3837     if( algo )
3838         md_enable( md, algo );
3839     else {
3840         md_enable( md, DIGEST_ALGO_MD5 );
3841         md_enable( md, DIGEST_ALGO_SHA1 );
3842         md_enable( md, DIGEST_ALGO_RMD160 );
3843 #ifdef USE_SHA256
3844         md_enable( md, DIGEST_ALGO_SHA256 );
3845 #endif
3846 #ifdef USE_SHA512
3847         md_enable( md, DIGEST_ALGO_SHA384 );
3848         md_enable( md, DIGEST_ALGO_SHA512 );
3849 #endif
3850     }
3851
3852     while( (n=fread( buf, 1, DIM(buf), fp )) )
3853         md_write( md, buf, n );
3854     if( ferror(fp) )
3855         log_error("%s: %s\n", fname?fname:"[stdin]", strerror(errno) );
3856     else {
3857         md_final(md);
3858         if ( opt.with_colons ) {
3859             if ( algo ) 
3860                 print_hashline( md, algo, fname );
3861             else {
3862                 print_hashline( md, DIGEST_ALGO_MD5, fname );
3863                 print_hashline( md, DIGEST_ALGO_SHA1, fname );
3864                 print_hashline( md, DIGEST_ALGO_RMD160, fname );
3865 #ifdef USE_SHA256
3866                 print_hashline( md, DIGEST_ALGO_SHA256, fname );
3867 #endif
3868 #ifdef USE_SHA512
3869                 print_hashline( md, DIGEST_ALGO_SHA384, fname );
3870                 print_hashline( md, DIGEST_ALGO_SHA512, fname );
3871 #endif
3872             }
3873         }
3874         else {
3875             if( algo )
3876                print_hex(md,-algo,fname);
3877             else {
3878                 print_hex( md, DIGEST_ALGO_MD5, fname );
3879                 print_hex( md, DIGEST_ALGO_SHA1, fname );
3880                 print_hex( md, DIGEST_ALGO_RMD160, fname );
3881 #ifdef USE_SHA256
3882                 print_hex( md, DIGEST_ALGO_SHA256, fname );
3883 #endif
3884 #ifdef USE_SHA512
3885                 print_hex( md, DIGEST_ALGO_SHA384, fname );
3886                 print_hex( md, DIGEST_ALGO_SHA512, fname );
3887 #endif
3888             }
3889         }
3890     }
3891     md_close(md);
3892
3893     if( fp != stdin )
3894         fclose(fp);
3895 }
3896
3897
3898 /****************
3899  * Check the supplied name,value string and add it to the notation
3900  * data to be used for signatures.  which==0 for sig notations, and 1
3901  * for cert notations.
3902 */
3903 static void
3904 add_notation_data( const char *string, int which )
3905 {
3906     const char *s;
3907     STRLIST sl,*notation_data;
3908     int critical=0;
3909     int highbit=0;
3910     int saw_at=0;
3911
3912     if(which)
3913       notation_data=&opt.cert_notation_data;
3914     else
3915       notation_data=&opt.sig_notation_data;
3916
3917     if( *string == '!' ) {
3918         critical = 1;
3919         string++;
3920     }
3921
3922     /* If and when the IETF assigns some official name tags, we'll
3923        have to add them here. */
3924
3925     for( s=string ; *s != '='; s++ )
3926       {
3927         if( *s=='@')
3928           saw_at++;
3929
3930         if( !*s || !isascii (*s) || (!isgraph(*s) && !isspace(*s)) )
3931           {
3932             log_error(_("a notation name must have only printable characters "
3933                         "or spaces, and end with an '='\n") );
3934             return;
3935           }
3936       }
3937
3938     if(!saw_at && !opt.expert)
3939       {
3940         log_error(_("a user notation name must contain the '@' character\n"));
3941         return;
3942       }
3943     if (saw_at > 1)
3944       {
3945         log_error(_("a notation name must not contain more than "
3946                     "one '@' character\n"));
3947         return;
3948       }
3949
3950     /* we only support printable text - therefore we enforce the use
3951      * of only printable characters (an empty value is valid) */
3952     for( s++; *s ; s++ ) {
3953         if ( isascii (*s) )
3954           highbit = 1;
3955         else if (iscntrl(*s)) {
3956             log_error(_("a notation value must not use"
3957                         " any control characters\n") );
3958             return;
3959         }
3960     }
3961
3962     if( highbit )   /* must use UTF8 encoding */
3963         sl = add_to_strlist2( notation_data, string, utf8_strings );
3964     else
3965         sl = add_to_strlist( notation_data, string );
3966
3967     if( critical )
3968         sl->flags |= 1;
3969 }
3970
3971 static void
3972 add_policy_url( const char *string, int which )
3973 {
3974   unsigned int i,critical=0;
3975   STRLIST sl;
3976
3977   if(*string=='!')
3978     {
3979       string++;
3980       critical=1;
3981     }
3982
3983   for(i=0;i<strlen(string);i++)
3984     if( !isascii (string[i]) || iscntrl(string[i]))
3985       break;
3986
3987   if(i==0 || i<strlen(string))
3988     {
3989       if(which)
3990         log_error(_("the given certification policy URL is invalid\n"));
3991       else
3992         log_error(_("the given signature policy URL is invalid\n"));
3993     }
3994
3995   if(which)
3996     sl=add_to_strlist( &opt.cert_policy_url, string );
3997   else
3998     sl=add_to_strlist( &opt.sig_policy_url, string );
3999
4000   if(critical)
4001     sl->flags |= 1;    
4002 }
4003
4004 static void
4005 add_keyserver_url( const char *string, int which )
4006 {
4007   unsigned int i,critical=0;
4008   STRLIST sl;
4009
4010   if(*string=='!')
4011     {
4012       string++;
4013       critical=1;
4014     }
4015
4016   for(i=0;i<strlen(string);i++)
4017     if( !isascii (string[i]) || iscntrl(string[i]))
4018       break;
4019
4020   if(i==0 || i<strlen(string))
4021     {
4022       if(which)
4023         BUG();
4024       else
4025         log_error(_("the given preferred keyserver URL is invalid\n"));
4026     }
4027
4028   if(which)
4029     BUG();
4030   else
4031     sl=add_to_strlist( &opt.sig_keyserver_url, string );
4032
4033   if(critical)
4034     sl->flags |= 1;    
4035 }