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