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