gpg: Make sure we only have a single SQL statement.
[gnupg.git] / g10 / misc.c
1 /* misc.c - miscellaneous functions
2  * Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
3  *               2008, 2009, 2010 Free Software Foundation, Inc.
4  * Copyright (C) 2014 Werner Koch
5  *
6  * This file is part of GnuPG.
7  *
8  * GnuPG is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; either version 3 of the License, or
11  * (at your option) any later version.
12  *
13  * GnuPG is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, see <http://www.gnu.org/licenses/>.
20  */
21
22 #include <config.h>
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26 #include <unistd.h>
27 #include <errno.h>
28 #if defined(__linux__) && defined(__alpha__) && __GLIBC__ < 2
29 #include <asm/sysinfo.h>
30 #include <asm/unistd.h>
31 #endif
32 #ifdef HAVE_SETRLIMIT
33 #include <time.h>
34 #include <sys/time.h>
35 #include <sys/resource.h>
36 #endif
37 #ifdef ENABLE_SELINUX_HACKS
38 #include <sys/stat.h>
39 #endif
40
41 #ifdef HAVE_W32_SYSTEM
42 #include <time.h>
43 #include <process.h>
44 #ifdef HAVE_WINSOCK2_H
45 # include <winsock2.h>
46 #endif
47 #include <windows.h>
48 #include <shlobj.h>
49 #ifndef CSIDL_APPDATA
50 #define CSIDL_APPDATA 0x001a
51 #endif
52 #ifndef CSIDL_LOCAL_APPDATA
53 #define CSIDL_LOCAL_APPDATA 0x001c
54 #endif
55 #ifndef CSIDL_FLAG_CREATE
56 #define CSIDL_FLAG_CREATE 0x8000
57 #endif
58 #endif /*HAVE_W32_SYSTEM*/
59
60 #include "gpg.h"
61 #ifdef HAVE_W32_SYSTEM
62 # include "status.h"
63 #endif /*HAVE_W32_SYSTEM*/
64 #include "util.h"
65 #include "main.h"
66 #include "photoid.h"
67 #include "options.h"
68 #include "call-agent.h"
69 #include "i18n.h"
70
71 #include <assert.h>
72
73
74 #ifdef ENABLE_SELINUX_HACKS
75 /* A object and a global variable to keep track of files marked as
76    secured. */
77 struct secured_file_item
78 {
79   struct secured_file_item *next;
80   ino_t ino;
81   dev_t dev;
82 };
83 static struct secured_file_item *secured_files;
84 #endif /*ENABLE_SELINUX_HACKS*/
85
86
87
88
89 /* For the sake of SELinux we want to restrict access through gpg to
90    certain files we keep under our own control.  This function
91    registers such a file and is_secured_file may then be used to
92    check whether a file has ben registered as secured. */
93 void
94 register_secured_file (const char *fname)
95 {
96 #ifdef ENABLE_SELINUX_HACKS
97   struct stat buf;
98   struct secured_file_item *sf;
99
100   /* Note that we stop immediatley if something goes wrong here. */
101   if (stat (fname, &buf))
102     log_fatal (_("fstat of '%s' failed in %s: %s\n"), fname,
103                "register_secured_file", strerror (errno));
104 /*   log_debug ("registering '%s' i=%lu.%lu\n", fname, */
105 /*              (unsigned long)buf.st_dev, (unsigned long)buf.st_ino); */
106   for (sf=secured_files; sf; sf = sf->next)
107     {
108       if (sf->ino == buf.st_ino && sf->dev == buf.st_dev)
109         return; /* Already registered.  */
110     }
111
112   sf = xmalloc (sizeof *sf);
113   sf->ino = buf.st_ino;
114   sf->dev = buf.st_dev;
115   sf->next = secured_files;
116   secured_files = sf;
117 #else /*!ENABLE_SELINUX_HACKS*/
118   (void)fname;
119 #endif /*!ENABLE_SELINUX_HACKS*/
120 }
121
122 /* Remove a file registered as secure. */
123 void
124 unregister_secured_file (const char *fname)
125 {
126 #ifdef ENABLE_SELINUX_HACKS
127   struct stat buf;
128   struct secured_file_item *sf, *sfprev;
129
130   if (stat (fname, &buf))
131     {
132       log_error (_("fstat of '%s' failed in %s: %s\n"), fname,
133                  "unregister_secured_file", strerror (errno));
134       return;
135     }
136 /*   log_debug ("unregistering '%s' i=%lu.%lu\n", fname,  */
137 /*              (unsigned long)buf.st_dev, (unsigned long)buf.st_ino); */
138   for (sfprev=NULL,sf=secured_files; sf; sfprev=sf, sf = sf->next)
139     {
140       if (sf->ino == buf.st_ino && sf->dev == buf.st_dev)
141         {
142           if (sfprev)
143             sfprev->next = sf->next;
144           else
145             secured_files = sf->next;
146           xfree (sf);
147           return;
148         }
149     }
150 #else /*!ENABLE_SELINUX_HACKS*/
151   (void)fname;
152 #endif /*!ENABLE_SELINUX_HACKS*/
153 }
154
155 /* Return true if FD is corresponds to a secured file.  Using -1 for
156    FS is allowed and will return false. */
157 int
158 is_secured_file (int fd)
159 {
160 #ifdef ENABLE_SELINUX_HACKS
161   struct stat buf;
162   struct secured_file_item *sf;
163
164   if (fd == -1)
165     return 0; /* No file descriptor so it can't be secured either.  */
166
167   /* Note that we print out a error here and claim that a file is
168      secure if something went wrong. */
169   if (fstat (fd, &buf))
170     {
171       log_error (_("fstat(%d) failed in %s: %s\n"), fd,
172                  "is_secured_file", strerror (errno));
173       return 1;
174     }
175 /*   log_debug ("is_secured_file (%d) i=%lu.%lu\n", fd, */
176 /*              (unsigned long)buf.st_dev, (unsigned long)buf.st_ino); */
177   for (sf=secured_files; sf; sf = sf->next)
178     {
179       if (sf->ino == buf.st_ino && sf->dev == buf.st_dev)
180         return 1; /* Yes.  */
181     }
182 #else /*!ENABLE_SELINUX_HACKS*/
183   (void)fd;
184 #endif /*!ENABLE_SELINUX_HACKS*/
185   return 0; /* No. */
186 }
187
188 /* Return true if FNAME is corresponds to a secured file.  Using NULL,
189    "" or "-" for FS is allowed and will return false. This function is
190    used before creating a file, thus it won't fail if the file does
191    not exist. */
192 int
193 is_secured_filename (const char *fname)
194 {
195 #ifdef ENABLE_SELINUX_HACKS
196   struct stat buf;
197   struct secured_file_item *sf;
198
199   if (iobuf_is_pipe_filename (fname) || !*fname)
200     return 0;
201
202   /* Note that we print out a error here and claim that a file is
203      secure if something went wrong. */
204   if (stat (fname, &buf))
205     {
206       if (errno == ENOENT || errno == EPERM || errno == EACCES)
207         return 0;
208       log_error (_("fstat of '%s' failed in %s: %s\n"), fname,
209                  "is_secured_filename", strerror (errno));
210       return 1;
211     }
212 /*   log_debug ("is_secured_filename (%s) i=%lu.%lu\n", fname, */
213 /*              (unsigned long)buf.st_dev, (unsigned long)buf.st_ino); */
214   for (sf=secured_files; sf; sf = sf->next)
215     {
216       if (sf->ino == buf.st_ino && sf->dev == buf.st_dev)
217         return 1; /* Yes.  */
218     }
219 #else /*!ENABLE_SELINUX_HACKS*/
220   (void)fname;
221 #endif /*!ENABLE_SELINUX_HACKS*/
222   return 0; /* No. */
223 }
224
225
226
227 u16
228 checksum_u16( unsigned n )
229 {
230     u16 a;
231
232     a  = (n >> 8) & 0xff;
233     a += n & 0xff;
234     return a;
235 }
236
237
238 u16
239 checksum( byte *p, unsigned n )
240 {
241     u16 a;
242
243     for(a=0; n; n-- )
244         a += *p++;
245     return a;
246 }
247
248 u16
249 checksum_mpi (gcry_mpi_t a)
250 {
251   u16 csum;
252   byte *buffer;
253   size_t nbytes;
254
255   if ( gcry_mpi_print (GCRYMPI_FMT_PGP, NULL, 0, &nbytes, a) )
256     BUG ();
257   /* Fixme: For numbers not in secure memory we should use a stack
258    * based buffer and only allocate a larger one if mpi_print returns
259    * an error. */
260   buffer = (gcry_is_secure(a)?
261             gcry_xmalloc_secure (nbytes) : gcry_xmalloc (nbytes));
262   if ( gcry_mpi_print (GCRYMPI_FMT_PGP, buffer, nbytes, NULL, a) )
263     BUG ();
264   csum = checksum (buffer, nbytes);
265   xfree (buffer);
266   return csum;
267 }
268
269
270 void
271 print_pubkey_algo_note (pubkey_algo_t algo)
272 {
273   if(algo >= 100 && algo <= 110)
274     {
275       static int warn=0;
276       if(!warn)
277         {
278           warn=1;
279           es_fflush (es_stdout);
280           log_info (_("WARNING: using experimental public key algorithm %s\n"),
281                     openpgp_pk_algo_name (algo));
282         }
283     }
284   else if (algo == PUBKEY_ALGO_ELGAMAL)
285     {
286       es_fflush (es_stdout);
287       log_info (_("WARNING: Elgamal sign+encrypt keys are deprecated\n"));
288     }
289 }
290
291 void
292 print_cipher_algo_note (cipher_algo_t algo)
293 {
294   if(algo >= 100 && algo <= 110)
295     {
296       static int warn=0;
297       if(!warn)
298         {
299           warn=1;
300           es_fflush (es_stdout);
301           log_info (_("WARNING: using experimental cipher algorithm %s\n"),
302                     openpgp_cipher_algo_name (algo));
303         }
304     }
305 }
306
307 void
308 print_digest_algo_note (digest_algo_t algo)
309 {
310   int deprecated = 0;
311   const enum gcry_md_algos galgo = map_md_openpgp_to_gcry (algo);
312   const struct weakhash *weak;
313
314   if(algo >= 100 && algo <= 110)
315     {
316       static int warn=0;
317       if(!warn)
318         {
319           warn=1;
320           es_fflush (es_stdout);
321           log_info (_("WARNING: using experimental digest algorithm %s\n"),
322                     gcry_md_algo_name (galgo));
323         }
324     }
325   else if(algo == DIGEST_ALGO_MD5)
326     deprecated = 1;
327   else
328       for (weak = opt.additional_weak_digests; weak != NULL; weak = weak->next)
329         if (weak->algo == galgo)
330           deprecated = 1;
331
332   if (deprecated)
333     {
334       es_fflush (es_stdout);
335       log_info (_("WARNING: digest algorithm %s is deprecated\n"),
336                 gcry_md_algo_name (galgo));
337     }
338 }
339
340
341 void
342 print_digest_rejected_note (enum gcry_md_algos algo)
343 {
344   static int shown;
345
346   if (!shown)
347     {
348       es_fflush (es_stdout);
349       log_info
350         (_("Note: signatures using the %s algorithm are rejected\n"),
351          gcry_md_algo_name(algo));
352       shown = 1;
353     }
354 }
355
356
357 /* Map OpenPGP algo numbers to those used by Libgcrypt.  We need to do
358    this for algorithms we implemented in Libgcrypt after they become
359    part of OpenPGP.  */
360 enum gcry_cipher_algos
361 map_cipher_openpgp_to_gcry (cipher_algo_t algo)
362 {
363   switch (algo)
364     {
365     case CIPHER_ALGO_NONE:        return GCRY_CIPHER_NONE;
366
367 #ifdef GPG_USE_IDEA
368     case CIPHER_ALGO_IDEA:        return GCRY_CIPHER_IDEA;
369 #else
370     case CIPHER_ALGO_IDEA:        return 0;
371 #endif
372
373     case CIPHER_ALGO_3DES:        return GCRY_CIPHER_3DES;
374
375 #ifdef GPG_USE_CAST5
376     case CIPHER_ALGO_CAST5:       return GCRY_CIPHER_CAST5;
377 #else
378     case CIPHER_ALGO_CAST5:       return 0;
379 #endif
380
381 #ifdef GPG_USE_BLOWFISH
382     case CIPHER_ALGO_BLOWFISH:    return GCRY_CIPHER_BLOWFISH;
383 #else
384     case CIPHER_ALGO_BLOWFISH:    return 0;
385 #endif
386
387 #ifdef GPG_USE_AES128
388     case CIPHER_ALGO_AES:         return GCRY_CIPHER_AES;
389 #else
390     case CIPHER_ALGO_AES:         return 0;
391 #endif
392
393 #ifdef GPG_USE_AES192
394     case CIPHER_ALGO_AES192:      return GCRY_CIPHER_AES192;
395 #else
396     case CIPHER_ALGO_AES192:      return 0;
397 #endif
398
399 #ifdef GPG_USE_AES256
400     case CIPHER_ALGO_AES256:      return GCRY_CIPHER_AES256;
401 #else
402     case CIPHER_ALGO_AES256:      return 0;
403 #endif
404
405 #ifdef GPG_USE_TWOFISH
406     case CIPHER_ALGO_TWOFISH:     return GCRY_CIPHER_TWOFISH;
407 #else
408     case CIPHER_ALGO_TWOFISH:     return 0;
409 #endif
410
411 #ifdef GPG_USE_CAMELLIA128
412     case CIPHER_ALGO_CAMELLIA128: return GCRY_CIPHER_CAMELLIA128;
413 #else
414     case CIPHER_ALGO_CAMELLIA128: return 0;
415 #endif
416
417 #ifdef GPG_USE_CAMELLIA192
418     case CIPHER_ALGO_CAMELLIA192: return GCRY_CIPHER_CAMELLIA192;
419 #else
420     case CIPHER_ALGO_CAMELLIA192: return 0;
421 #endif
422
423 #ifdef GPG_USE_CAMELLIA256
424     case CIPHER_ALGO_CAMELLIA256: return GCRY_CIPHER_CAMELLIA256;
425 #else
426     case CIPHER_ALGO_CAMELLIA256: return 0;
427 #endif
428     }
429   return 0;
430 }
431
432 /* The inverse function of above.  */
433 static cipher_algo_t
434 map_cipher_gcry_to_openpgp (enum gcry_cipher_algos algo)
435 {
436   switch (algo)
437     {
438     case GCRY_CIPHER_NONE:        return CIPHER_ALGO_NONE;
439     case GCRY_CIPHER_IDEA:        return CIPHER_ALGO_IDEA;
440     case GCRY_CIPHER_3DES:        return CIPHER_ALGO_3DES;
441     case GCRY_CIPHER_CAST5:       return CIPHER_ALGO_CAST5;
442     case GCRY_CIPHER_BLOWFISH:    return CIPHER_ALGO_BLOWFISH;
443     case GCRY_CIPHER_AES:         return CIPHER_ALGO_AES;
444     case GCRY_CIPHER_AES192:      return CIPHER_ALGO_AES192;
445     case GCRY_CIPHER_AES256:      return CIPHER_ALGO_AES256;
446     case GCRY_CIPHER_TWOFISH:     return CIPHER_ALGO_TWOFISH;
447     case GCRY_CIPHER_CAMELLIA128: return CIPHER_ALGO_CAMELLIA128;
448     case GCRY_CIPHER_CAMELLIA192: return CIPHER_ALGO_CAMELLIA192;
449     case GCRY_CIPHER_CAMELLIA256: return CIPHER_ALGO_CAMELLIA256;
450     default: return 0;
451     }
452 }
453
454 /* Map Gcrypt public key algorithm numbers to those used by OpenPGP.
455    FIXME: This mapping is used at only two places - we should get rid
456    of it.  */
457 pubkey_algo_t
458 map_pk_gcry_to_openpgp (enum gcry_pk_algos algo)
459 {
460   switch (algo)
461     {
462     case GCRY_PK_ECDSA:  return PUBKEY_ALGO_ECDSA;
463     case GCRY_PK_ECDH:   return PUBKEY_ALGO_ECDH;
464     default: return algo < 110 ? algo : 0;
465     }
466 }
467
468
469 /* Return the block length of an OpenPGP cipher algorithm.  */
470 int
471 openpgp_cipher_blocklen (cipher_algo_t algo)
472 {
473   /* We use the numbers from OpenPGP to be sure that we get the right
474      block length.  This is so that the packet parsing code works even
475      for unknown algorithms (for which we assume 8 due to tradition).
476
477      NOTE: If you change the the returned blocklen above 16, check
478      the callers because they may use a fixed size buffer of that
479      size. */
480   switch (algo)
481     {
482     case CIPHER_ALGO_AES:
483     case CIPHER_ALGO_AES192:
484     case CIPHER_ALGO_AES256:
485     case CIPHER_ALGO_TWOFISH:
486     case CIPHER_ALGO_CAMELLIA128:
487     case CIPHER_ALGO_CAMELLIA192:
488     case CIPHER_ALGO_CAMELLIA256:
489       return 16;
490
491     default:
492       return 8;
493     }
494 }
495
496 /****************
497  * Wrapper around the libgcrypt function with additonal checks on
498  * the OpenPGP contraints for the algo ID.
499  */
500 int
501 openpgp_cipher_test_algo (cipher_algo_t algo)
502 {
503   enum gcry_cipher_algos ga;
504
505   ga = map_cipher_openpgp_to_gcry (algo);
506   if (!ga)
507     return gpg_error (GPG_ERR_CIPHER_ALGO);
508
509   return gcry_cipher_test_algo (ga);
510 }
511
512 /* Map the OpenPGP cipher algorithm whose ID is contained in ALGORITHM to a
513    string representation of the algorithm name.  For unknown algorithm
514    IDs this function returns "?".  */
515 const char *
516 openpgp_cipher_algo_name (cipher_algo_t algo)
517 {
518   switch (algo)
519     {
520     case CIPHER_ALGO_NONE:        break;
521     case CIPHER_ALGO_IDEA:        return "IDEA";
522     case CIPHER_ALGO_3DES:        return "3DES";
523     case CIPHER_ALGO_CAST5:       return "CAST5";
524     case CIPHER_ALGO_BLOWFISH:    return "BLOWFISH";
525     case CIPHER_ALGO_AES:         return "AES";
526     case CIPHER_ALGO_AES192:      return "AES192";
527     case CIPHER_ALGO_AES256:      return "AES256";
528     case CIPHER_ALGO_TWOFISH:     return "TWOFISH";
529     case CIPHER_ALGO_CAMELLIA128: return "CAMELLIA128";
530     case CIPHER_ALGO_CAMELLIA192: return "CAMELLIA192";
531     case CIPHER_ALGO_CAMELLIA256: return "CAMELLIA256";
532     }
533   return "?";
534 }
535
536
537 /* Return 0 if ALGO is a supported OpenPGP public key algorithm.  */
538 int
539 openpgp_pk_test_algo (pubkey_algo_t algo)
540 {
541   return openpgp_pk_test_algo2 (algo, 0);
542 }
543
544
545 /* Return 0 if ALGO is a supported OpenPGP public key algorithm and
546    allows the usage USE.  */
547 int
548 openpgp_pk_test_algo2 (pubkey_algo_t algo, unsigned int use)
549 {
550   enum gcry_pk_algos ga = 0;
551   size_t use_buf = use;
552
553   switch (algo)
554     {
555 #ifdef GPG_USE_RSA
556     case PUBKEY_ALGO_RSA:       ga = GCRY_PK_RSA;   break;
557     case PUBKEY_ALGO_RSA_E:     ga = GCRY_PK_RSA_E; break;
558     case PUBKEY_ALGO_RSA_S:     ga = GCRY_PK_RSA_S; break;
559 #else
560     case PUBKEY_ALGO_RSA:       break;
561     case PUBKEY_ALGO_RSA_E:     break;
562     case PUBKEY_ALGO_RSA_S:     break;
563 #endif
564
565     case PUBKEY_ALGO_ELGAMAL_E: ga = GCRY_PK_ELG;   break;
566     case PUBKEY_ALGO_DSA:       ga = GCRY_PK_DSA;   break;
567
568 #ifdef GPG_USE_ECDH
569     case PUBKEY_ALGO_ECDH:      ga = GCRY_PK_ECC;   break;
570 #else
571     case PUBKEY_ALGO_ECDH:      break;
572 #endif
573
574 #ifdef GPG_USE_ECDSA
575     case PUBKEY_ALGO_ECDSA:     ga = GCRY_PK_ECC;   break;
576 #else
577     case PUBKEY_ALGO_ECDSA:     break;
578 #endif
579
580 #ifdef GPG_USE_EDDSA
581     case PUBKEY_ALGO_EDDSA:     ga = GCRY_PK_ECC;   break;
582 #else
583     case PUBKEY_ALGO_EDDSA:     break;
584 #endif
585
586     case PUBKEY_ALGO_ELGAMAL:
587       /* Dont't allow type 20 keys unless in rfc2440 mode.  */
588       if (RFC2440)
589         ga = GCRY_PK_ELG;
590       break;
591     }
592   if (!ga)
593     return gpg_error (GPG_ERR_PUBKEY_ALGO);
594
595   /* No check whether Libgcrypt has support for the algorithm.  */
596   return gcry_pk_algo_info (ga, GCRYCTL_TEST_ALGO, NULL, &use_buf);
597 }
598
599
600 int
601 openpgp_pk_algo_usage ( int algo )
602 {
603     int use = 0;
604
605     /* They are hardwired in gpg 1.0. */
606     switch ( algo ) {
607       case PUBKEY_ALGO_RSA:
608           use = (PUBKEY_USAGE_CERT | PUBKEY_USAGE_SIG
609                  | PUBKEY_USAGE_ENC | PUBKEY_USAGE_AUTH);
610           break;
611       case PUBKEY_ALGO_RSA_E:
612       case PUBKEY_ALGO_ECDH:
613           use = PUBKEY_USAGE_ENC;
614           break;
615       case PUBKEY_ALGO_RSA_S:
616           use = PUBKEY_USAGE_CERT | PUBKEY_USAGE_SIG;
617           break;
618       case PUBKEY_ALGO_ELGAMAL:
619           if (RFC2440)
620              use = PUBKEY_USAGE_ENC;
621           break;
622       case PUBKEY_ALGO_ELGAMAL_E:
623           use = PUBKEY_USAGE_ENC;
624           break;
625       case PUBKEY_ALGO_DSA:
626           use = PUBKEY_USAGE_CERT | PUBKEY_USAGE_SIG | PUBKEY_USAGE_AUTH;
627           break;
628       case PUBKEY_ALGO_ECDSA:
629       case PUBKEY_ALGO_EDDSA:
630           use = PUBKEY_USAGE_CERT | PUBKEY_USAGE_SIG | PUBKEY_USAGE_AUTH;
631       default:
632           break;
633     }
634     return use;
635 }
636
637 /* Map the OpenPGP pubkey algorithm whose ID is contained in ALGO to a
638    string representation of the algorithm name.  For unknown algorithm
639    IDs this function returns "?".  */
640 const char *
641 openpgp_pk_algo_name (pubkey_algo_t algo)
642 {
643   switch (algo)
644     {
645     case PUBKEY_ALGO_RSA:
646     case PUBKEY_ALGO_RSA_E:
647     case PUBKEY_ALGO_RSA_S:     return "RSA";
648     case PUBKEY_ALGO_ELGAMAL:
649     case PUBKEY_ALGO_ELGAMAL_E: return "ELG";
650     case PUBKEY_ALGO_DSA:       return "DSA";
651     case PUBKEY_ALGO_ECDH:      return "ECDH";
652     case PUBKEY_ALGO_ECDSA:     return "ECDSA";
653     case PUBKEY_ALGO_EDDSA:     return "EDDSA";
654     }
655   return "?";
656 }
657
658
659 /* Explicit mapping of OpenPGP digest algos to Libgcrypt.  */
660 /* FIXME: We do not yes use it everywhere.  */
661 enum gcry_md_algos
662 map_md_openpgp_to_gcry (digest_algo_t algo)
663 {
664   switch (algo)
665     {
666 #ifdef GPG_USE_MD5
667     case DIGEST_ALGO_MD5:    return GCRY_MD_MD5;
668 #else
669     case DIGEST_ALGO_MD5:    return 0;
670 #endif
671
672     case DIGEST_ALGO_SHA1:   return GCRY_MD_SHA1;
673
674 #ifdef GPG_USE_RMD160
675     case DIGEST_ALGO_RMD160: return GCRY_MD_RMD160;
676 #else
677     case DIGEST_ALGO_RMD160: return 0;
678 #endif
679
680 #ifdef GPG_USE_SHA224
681     case DIGEST_ALGO_SHA224: return GCRY_MD_SHA224;
682 #else
683     case DIGEST_ALGO_SHA224: return 0;
684 #endif
685
686     case DIGEST_ALGO_SHA256: return GCRY_MD_SHA256;
687
688 #ifdef GPG_USE_SHA384
689     case DIGEST_ALGO_SHA384: return GCRY_MD_SHA384;
690 #else
691     case DIGEST_ALGO_SHA384: return 0;
692 #endif
693
694 #ifdef GPG_USE_SHA512
695     case DIGEST_ALGO_SHA512: return GCRY_MD_SHA512;
696 #else
697     case DIGEST_ALGO_SHA512: return 0;
698 #endif
699     }
700   return 0;
701 }
702
703
704 /* Return 0 if ALGO is suitable and implemented OpenPGP hash
705    algorithm.  */
706 int
707 openpgp_md_test_algo (digest_algo_t algo)
708 {
709   enum gcry_md_algos ga;
710
711   ga = map_md_openpgp_to_gcry (algo);
712   if (!ga)
713     return gpg_error (GPG_ERR_DIGEST_ALGO);
714
715   return gcry_md_test_algo (ga);
716 }
717
718
719 /* Map the OpenPGP digest algorithm whose ID is contained in ALGO to a
720    string representation of the algorithm name.  For unknown algorithm
721    IDs this function returns "?".  */
722 const char *
723 openpgp_md_algo_name (int algo)
724 {
725   switch (algo)
726     {
727     case DIGEST_ALGO_MD5:    return "MD5";
728     case DIGEST_ALGO_SHA1:   return "SHA1";
729     case DIGEST_ALGO_RMD160: return "RIPEMD160";
730     case DIGEST_ALGO_SHA256: return "SHA256";
731     case DIGEST_ALGO_SHA384: return "SHA384";
732     case DIGEST_ALGO_SHA512: return "SHA512";
733     case DIGEST_ALGO_SHA224: return "SHA224";
734     }
735   return "?";
736 }
737
738
739 static unsigned long
740 get_signature_count (PKT_public_key *pk)
741 {
742 #ifdef ENABLE_CARD_SUPPORT
743   struct agent_card_info_s info;
744
745   (void)pk;
746   if (!agent_scd_getattr ("SIG-COUNTER",&info))
747     return info.sig_counter;
748   else
749     return 0;
750 #else
751   (void)pk;
752   return 0;
753 #endif
754 }
755
756 /* Expand %-strings.  Returns a string which must be xfreed.  Returns
757    NULL if the string cannot be expanded (too large). */
758 char *
759 pct_expando(const char *string,struct expando_args *args)
760 {
761   const char *ch=string;
762   int idx=0,maxlen=0,done=0;
763   u32 pk_keyid[2]={0,0},sk_keyid[2]={0,0};
764   char *ret=NULL;
765
766   if(args->pk)
767     keyid_from_pk(args->pk,pk_keyid);
768
769   if(args->pksk)
770     keyid_from_pk (args->pksk, sk_keyid);
771
772   /* This is used so that %k works in photoid command strings in
773      --list-secret-keys (which of course has a sk, but no pk). */
774   if(!args->pk && args->pksk)
775     keyid_from_pk (args->pksk, pk_keyid);
776
777   while(*ch!='\0')
778     {
779       if(!done)
780         {
781           /* 8192 is way bigger than we'll need here */
782           if(maxlen>=8192)
783             goto fail;
784
785           maxlen+=1024;
786           ret=xrealloc(ret,maxlen);
787         }
788
789       done=0;
790
791       if(*ch=='%')
792         {
793           switch(*(ch+1))
794             {
795             case 's': /* short key id */
796               if(idx+8<maxlen)
797                 {
798                   sprintf(&ret[idx],"%08lX",(ulong)sk_keyid[1]);
799                   idx+=8;
800                   done=1;
801                 }
802               break;
803
804             case 'S': /* long key id */
805               if(idx+16<maxlen)
806                 {
807                   sprintf(&ret[idx],"%08lX%08lX",
808                           (ulong)sk_keyid[0],(ulong)sk_keyid[1]);
809                   idx+=16;
810                   done=1;
811                 }
812               break;
813
814             case 'k': /* short key id */
815               if(idx+8<maxlen)
816                 {
817                   sprintf(&ret[idx],"%08lX",(ulong)pk_keyid[1]);
818                   idx+=8;
819                   done=1;
820                 }
821               break;
822
823             case 'K': /* long key id */
824               if(idx+16<maxlen)
825                 {
826                   sprintf(&ret[idx],"%08lX%08lX",
827                           (ulong)pk_keyid[0],(ulong)pk_keyid[1]);
828                   idx+=16;
829                   done=1;
830                 }
831               break;
832
833             case 'U': /* z-base-32 encoded user id hash. */
834               if (args->namehash)
835                 {
836                   char *tmp = zb32_encode (args->namehash, 8*20);
837                   if (tmp)
838                     {
839                       if (idx + strlen (tmp) < maxlen)
840                         {
841                           strcpy (ret+idx, tmp);
842                           idx += strlen (tmp);
843                         }
844                       xfree (tmp);
845                       done = 1;
846                     }
847                 }
848               break;
849
850             case 'c': /* signature count from card, if any. */
851               if(idx+10<maxlen)
852                 {
853                   sprintf (&ret[idx],"%lu", get_signature_count (args->pksk));
854                   idx+=strlen(&ret[idx]);
855                   done=1;
856                 }
857               break;
858
859             case 'f': /* Fingerprint of key being signed */
860             case 'p': /* Fingerprint of the primary key making the signature. */
861             case 'g': /* Fingerprint of thge key making the signature.  */
862               {
863                 byte array[MAX_FINGERPRINT_LEN];
864                 size_t len;
865                 int i;
866
867                 if ((*(ch+1))=='f' && args->pk)
868                   fingerprint_from_pk (args->pk, array, &len);
869                 else if ((*(ch+1))=='p' && args->pksk)
870                   {
871                     if(args->pksk->flags.primary)
872                       fingerprint_from_pk (args->pksk, array, &len);
873                     else if (args->pksk->main_keyid[0]
874                              || args->pksk->main_keyid[1])
875                       {
876                         /* Not the primary key: Find the fingerprint
877                            of the primary key.  */
878                         PKT_public_key *pk=
879                           xmalloc_clear(sizeof(PKT_public_key));
880
881                         if (!get_pubkey_fast (pk,args->pksk->main_keyid))
882                           fingerprint_from_pk (pk, array, &len);
883                         else
884                           memset (array, 0, (len=MAX_FINGERPRINT_LEN));
885                         free_public_key (pk);
886                       }
887                     else /* Oops: info about the primary key missing.  */
888                       memset(array,0,(len=MAX_FINGERPRINT_LEN));
889                   }
890                 else if((*(ch+1))=='g' && args->pksk)
891                   fingerprint_from_pk (args->pksk, array, &len);
892                 else
893                   memset(array,0,(len=MAX_FINGERPRINT_LEN));
894
895                 if(idx+(len*2)<maxlen)
896                   {
897                     for(i=0;i<len;i++)
898                       {
899                         sprintf(&ret[idx],"%02X",array[i]);
900                         idx+=2;
901                       }
902                     done=1;
903                   }
904               }
905               break;
906
907             case 'v': /* validity letters */
908               if(args->validity_info && idx+1<maxlen)
909                 {
910                   ret[idx++]=args->validity_info;
911                   ret[idx]='\0';
912                   done=1;
913                 }
914               break;
915
916               /* The text string types */
917             case 't':
918             case 'T':
919             case 'V':
920               {
921                 const char *str=NULL;
922
923                 switch(*(ch+1))
924                   {
925                   case 't': /* e.g. "jpg" */
926                     str=image_type_to_string(args->imagetype,0);
927                     break;
928
929                   case 'T': /* e.g. "image/jpeg" */
930                     str=image_type_to_string(args->imagetype,2);
931                     break;
932
933                   case 'V': /* e.g. "full", "expired", etc. */
934                     str=args->validity_string;
935                     break;
936                   }
937
938                 if(str && idx+strlen(str)<maxlen)
939                   {
940                     strcpy(&ret[idx],str);
941                     idx+=strlen(str);
942                     done=1;
943                   }
944               }
945               break;
946
947             case '%':
948               if(idx+1<maxlen)
949                 {
950                   ret[idx++]='%';
951                   ret[idx]='\0';
952                   done=1;
953                 }
954               break;
955
956               /* Any unknown %-keys (like %i, %o, %I, and %O) are
957                  passed through for later expansion.  Note this also
958                  handles the case where the last character in the
959                  string is a '%' - the terminating \0 will end up here
960                  and properly terminate the string. */
961             default:
962               if(idx+2<maxlen)
963                 {
964                   ret[idx++]='%';
965                   ret[idx++]=*(ch+1);
966                   ret[idx]='\0';
967                   done=1;
968                 }
969               break;
970               }
971
972           if(done)
973             ch++;
974         }
975       else
976         {
977           if(idx+1<maxlen)
978             {
979               ret[idx++]=*ch;
980               ret[idx]='\0';
981               done=1;
982             }
983         }
984
985       if(done)
986         ch++;
987     }
988
989   return ret;
990
991  fail:
992   xfree(ret);
993   return NULL;
994 }
995
996 void
997 deprecated_warning(const char *configname,unsigned int configlineno,
998                    const char *option,const char *repl1,const char *repl2)
999 {
1000   if(configname)
1001     {
1002       if(strncmp("--",option,2)==0)
1003         option+=2;
1004
1005       if(strncmp("--",repl1,2)==0)
1006         repl1+=2;
1007
1008       log_info(_("%s:%d: deprecated option \"%s\"\n"),
1009                configname,configlineno,option);
1010     }
1011   else
1012     log_info(_("WARNING: \"%s\" is a deprecated option\n"),option);
1013
1014   log_info(_("please use \"%s%s\" instead\n"),repl1,repl2);
1015 }
1016
1017
1018 void
1019 deprecated_command (const char *name)
1020 {
1021   log_info(_("WARNING: \"%s\" is a deprecated command - do not use it\n"),
1022            name);
1023 }
1024
1025
1026 void
1027 obsolete_scdaemon_option (const char *configname, unsigned int configlineno,
1028                           const char *name)
1029 {
1030   if (configname)
1031     log_info (_("%s:%u: \"%s\" is obsolete in this file"
1032                 " - it only has effect in %s\n"),
1033               configname, configlineno, name, SCDAEMON_NAME EXTSEP_S "conf");
1034   else
1035     log_info (_("WARNING: \"%s%s\" is an obsolete option"
1036                 " - it has no effect except on %s\n"),
1037               "--", name, SCDAEMON_NAME);
1038 }
1039
1040
1041 /*
1042  * Wrapper around gcry_cipher_map_name to provide a fallback using the
1043  * "Sn" syntax as used by the preference strings.
1044  */
1045 int
1046 string_to_cipher_algo (const char *string)
1047 {
1048   int val;
1049
1050   val = map_cipher_gcry_to_openpgp (gcry_cipher_map_name (string));
1051   if (!val && string && (string[0]=='S' || string[0]=='s'))
1052     {
1053       char *endptr;
1054
1055       string++;
1056       val = strtol (string, &endptr, 10);
1057       if (!*string || *endptr || openpgp_cipher_test_algo (val))
1058         val = 0;
1059     }
1060
1061   return val;
1062 }
1063
1064 /*
1065  * Wrapper around gcry_md_map_name to provide a fallback using the
1066  * "Hn" syntax as used by the preference strings.
1067  */
1068 int
1069 string_to_digest_algo (const char *string)
1070 {
1071   int val;
1072
1073   /* FIXME: We should make use of our wrapper fucntion and not assume
1074      that there is a 1 to 1 mapping between OpenPGP and Libgcrypt.  */
1075   val = gcry_md_map_name (string);
1076   if (!val && string && (string[0]=='H' || string[0]=='h'))
1077     {
1078       char *endptr;
1079
1080       string++;
1081       val = strtol (string, &endptr, 10);
1082       if (!*string || *endptr || openpgp_md_test_algo (val))
1083         val = 0;
1084     }
1085
1086   return val;
1087 }
1088
1089
1090
1091 const char *
1092 compress_algo_to_string(int algo)
1093 {
1094   const char *s=NULL;
1095
1096   switch(algo)
1097     {
1098     case COMPRESS_ALGO_NONE:
1099       s=_("Uncompressed");
1100       break;
1101
1102     case COMPRESS_ALGO_ZIP:
1103       s="ZIP";
1104       break;
1105
1106     case COMPRESS_ALGO_ZLIB:
1107       s="ZLIB";
1108       break;
1109
1110 #ifdef HAVE_BZIP2
1111     case COMPRESS_ALGO_BZIP2:
1112       s="BZIP2";
1113       break;
1114 #endif
1115     }
1116
1117   return s;
1118 }
1119
1120 int
1121 string_to_compress_algo(const char *string)
1122 {
1123   /* TRANSLATORS: See doc/TRANSLATE about this string. */
1124   if(match_multistr(_("uncompressed|none"),string))
1125     return 0;
1126   else if(ascii_strcasecmp(string,"uncompressed")==0)
1127     return 0;
1128   else if(ascii_strcasecmp(string,"none")==0)
1129     return 0;
1130   else if(ascii_strcasecmp(string,"zip")==0)
1131     return 1;
1132   else if(ascii_strcasecmp(string,"zlib")==0)
1133     return 2;
1134 #ifdef HAVE_BZIP2
1135   else if(ascii_strcasecmp(string,"bzip2")==0)
1136     return 3;
1137 #endif
1138   else if(ascii_strcasecmp(string,"z0")==0)
1139     return 0;
1140   else if(ascii_strcasecmp(string,"z1")==0)
1141     return 1;
1142   else if(ascii_strcasecmp(string,"z2")==0)
1143     return 2;
1144 #ifdef HAVE_BZIP2
1145   else if(ascii_strcasecmp(string,"z3")==0)
1146     return 3;
1147 #endif
1148   else
1149     return -1;
1150 }
1151
1152 int
1153 check_compress_algo(int algo)
1154 {
1155   switch (algo)
1156     {
1157     case 0: return 0;
1158 #ifdef HAVE_ZIP
1159     case 1:
1160     case 2: return 0;
1161 #endif
1162 #ifdef HAVE_BZIP2
1163     case 3: return 0;
1164 #endif
1165     default: return GPG_ERR_COMPR_ALGO;
1166     }
1167 }
1168
1169 int
1170 default_cipher_algo(void)
1171 {
1172   if(opt.def_cipher_algo)
1173     return opt.def_cipher_algo;
1174   else if(opt.personal_cipher_prefs)
1175     return opt.personal_cipher_prefs[0].value;
1176   else
1177     return opt.s2k_cipher_algo;
1178 }
1179
1180 /* There is no default_digest_algo function, but see
1181    sign.c:hash_for() */
1182
1183 int
1184 default_compress_algo(void)
1185 {
1186   if(opt.compress_algo!=-1)
1187     return opt.compress_algo;
1188   else if(opt.personal_compress_prefs)
1189     return opt.personal_compress_prefs[0].value;
1190   else
1191     return DEFAULT_COMPRESS_ALGO;
1192 }
1193
1194 const char *
1195 compliance_option_string(void)
1196 {
1197   char *ver="???";
1198
1199   switch(opt.compliance)
1200     {
1201     case CO_GNUPG:   return "--gnupg";
1202     case CO_RFC4880: return "--openpgp";
1203     case CO_RFC2440: return "--rfc2440";
1204     case CO_PGP6:    return "--pgp6";
1205     case CO_PGP7:    return "--pgp7";
1206     case CO_PGP8:    return "--pgp8";
1207     }
1208
1209   return ver;
1210 }
1211
1212 void
1213 compliance_failure(void)
1214 {
1215   char *ver="???";
1216
1217   switch(opt.compliance)
1218     {
1219     case CO_GNUPG:
1220       ver="GnuPG";
1221       break;
1222
1223     case CO_RFC4880:
1224       ver="OpenPGP";
1225       break;
1226
1227     case CO_RFC2440:
1228       ver="OpenPGP (older)";
1229       break;
1230
1231     case CO_PGP6:
1232       ver="PGP 6.x";
1233       break;
1234
1235     case CO_PGP7:
1236       ver="PGP 7.x";
1237       break;
1238
1239     case CO_PGP8:
1240       ver="PGP 8.x";
1241       break;
1242     }
1243
1244   log_info(_("this message may not be usable by %s\n"),ver);
1245   opt.compliance=CO_GNUPG;
1246 }
1247
1248 /* Break a string into successive option pieces.  Accepts single word
1249    options and key=value argument options. */
1250 char *
1251 optsep(char **stringp)
1252 {
1253   char *tok,*end;
1254
1255   tok=*stringp;
1256   if(tok)
1257     {
1258       end=strpbrk(tok," ,=");
1259       if(end)
1260         {
1261           int sawequals=0;
1262           char *ptr=end;
1263
1264           /* what we need to do now is scan along starting with *end,
1265              If the next character we see (ignoring spaces) is an =
1266              sign, then there is an argument. */
1267
1268           while(*ptr)
1269             {
1270               if(*ptr=='=')
1271                 sawequals=1;
1272               else if(*ptr!=' ')
1273                 break;
1274               ptr++;
1275             }
1276
1277           /* There is an argument, so grab that too.  At this point,
1278              ptr points to the first character of the argument. */
1279           if(sawequals)
1280             {
1281               /* Is it a quoted argument? */
1282               if(*ptr=='"')
1283                 {
1284                   ptr++;
1285                   end=strchr(ptr,'"');
1286                   if(end)
1287                     end++;
1288                 }
1289               else
1290                 end=strpbrk(ptr," ,");
1291             }
1292
1293           if(end && *end)
1294             {
1295               *end='\0';
1296               *stringp=end+1;
1297             }
1298           else
1299             *stringp=NULL;
1300         }
1301       else
1302         *stringp=NULL;
1303     }
1304
1305   return tok;
1306 }
1307
1308 /* Breaks an option value into key and value.  Returns NULL if there
1309    is no value.  Note that "string" is modified to remove the =value
1310    part. */
1311 char *
1312 argsplit(char *string)
1313 {
1314   char *equals,*arg=NULL;
1315
1316   equals=strchr(string,'=');
1317   if(equals)
1318     {
1319       char *quote,*space;
1320
1321       *equals='\0';
1322       arg=equals+1;
1323
1324       /* Quoted arg? */
1325       quote=strchr(arg,'"');
1326       if(quote)
1327         {
1328           arg=quote+1;
1329
1330           quote=strchr(arg,'"');
1331           if(quote)
1332             *quote='\0';
1333         }
1334       else
1335         {
1336           size_t spaces;
1337
1338           /* Trim leading spaces off of the arg */
1339           spaces=strspn(arg," ");
1340           arg+=spaces;
1341         }
1342
1343       /* Trim tailing spaces off of the tag */
1344       space=strchr(string,' ');
1345       if(space)
1346         *space='\0';
1347     }
1348
1349   return arg;
1350 }
1351
1352 /* Return the length of the initial token, leaving off any
1353    argument. */
1354 static size_t
1355 optlen(const char *s)
1356 {
1357   char *end=strpbrk(s," =");
1358
1359   if(end)
1360     return end-s;
1361   else
1362     return strlen(s);
1363 }
1364
1365 int
1366 parse_options(char *str,unsigned int *options,
1367               struct parse_options *opts,int noisy)
1368 {
1369   char *tok;
1370
1371   if (str && !strcmp (str, "help"))
1372     {
1373       int i,maxlen=0;
1374
1375       /* Figure out the longest option name so we can line these up
1376          neatly. */
1377       for(i=0;opts[i].name;i++)
1378         if(opts[i].help && maxlen<strlen(opts[i].name))
1379           maxlen=strlen(opts[i].name);
1380
1381       for(i=0;opts[i].name;i++)
1382         if(opts[i].help)
1383           es_printf("%s%*s%s\n",opts[i].name,
1384                     maxlen+2-(int)strlen(opts[i].name),"",_(opts[i].help));
1385
1386       g10_exit(0);
1387     }
1388
1389   while((tok=optsep(&str)))
1390     {
1391       int i,rev=0;
1392       char *otok=tok;
1393
1394       if(tok[0]=='\0')
1395         continue;
1396
1397       if(ascii_strncasecmp("no-",tok,3)==0)
1398         {
1399           rev=1;
1400           tok+=3;
1401         }
1402
1403       for(i=0;opts[i].name;i++)
1404         {
1405           size_t toklen=optlen(tok);
1406
1407           if(ascii_strncasecmp(opts[i].name,tok,toklen)==0)
1408             {
1409               /* We have a match, but it might be incomplete */
1410               if(toklen!=strlen(opts[i].name))
1411                 {
1412                   int j;
1413
1414                   for(j=i+1;opts[j].name;j++)
1415                     {
1416                       if(ascii_strncasecmp(opts[j].name,tok,toklen)==0)
1417                         {
1418                           if(noisy)
1419                             log_info(_("ambiguous option '%s'\n"),otok);
1420                           return 0;
1421                         }
1422                     }
1423                 }
1424
1425               if(rev)
1426                 {
1427                   *options&=~opts[i].bit;
1428                   if(opts[i].value)
1429                     *opts[i].value=NULL;
1430                 }
1431               else
1432                 {
1433                   *options|=opts[i].bit;
1434                   if(opts[i].value)
1435                     *opts[i].value=argsplit(tok);
1436                 }
1437               break;
1438             }
1439         }
1440
1441       if(!opts[i].name)
1442         {
1443           if(noisy)
1444             log_info(_("unknown option '%s'\n"),otok);
1445           return 0;
1446         }
1447     }
1448
1449   return 1;
1450 }
1451
1452
1453 /* Similar to access(2), but uses PATH to find the file. */
1454 int
1455 path_access(const char *file,int mode)
1456 {
1457   char *envpath;
1458   int ret=-1;
1459
1460   envpath=getenv("PATH");
1461
1462   if(!envpath
1463 #ifdef HAVE_DRIVE_LETTERS
1464      || (((file[0]>='A' && file[0]<='Z')
1465           || (file[0]>='a' && file[0]<='z'))
1466          && file[1]==':')
1467 #else
1468      || file[0]=='/'
1469 #endif
1470      )
1471     return access(file,mode);
1472   else
1473     {
1474       /* At least as large as, but most often larger than we need. */
1475       char *buffer=xmalloc(strlen(envpath)+1+strlen(file)+1);
1476       char *split,*item,*path=xstrdup(envpath);
1477
1478       split=path;
1479
1480       while((item=strsep(&split,PATHSEP_S)))
1481         {
1482           strcpy(buffer,item);
1483           strcat(buffer,"/");
1484           strcat(buffer,file);
1485           ret=access(buffer,mode);
1486           if(ret==0)
1487             break;
1488         }
1489
1490       xfree(path);
1491       xfree(buffer);
1492     }
1493
1494   return ret;
1495 }
1496
1497
1498 \f
1499 /* Return the number of public key parameters as used by OpenPGP.  */
1500 int
1501 pubkey_get_npkey (pubkey_algo_t algo)
1502 {
1503   switch (algo)
1504     {
1505     case PUBKEY_ALGO_RSA:
1506     case PUBKEY_ALGO_RSA_E:
1507     case PUBKEY_ALGO_RSA_S:     return 2;
1508     case PUBKEY_ALGO_ELGAMAL_E: return 3;
1509     case PUBKEY_ALGO_DSA:       return 4;
1510     case PUBKEY_ALGO_ECDH:      return 3;
1511     case PUBKEY_ALGO_ECDSA:     return 2;
1512     case PUBKEY_ALGO_ELGAMAL:   return 3;
1513     case PUBKEY_ALGO_EDDSA:     return 2;
1514     }
1515   return 0;
1516 }
1517
1518
1519 /* Return the number of secret key parameters as used by OpenPGP.  */
1520 int
1521 pubkey_get_nskey (pubkey_algo_t algo)
1522 {
1523   switch (algo)
1524     {
1525     case PUBKEY_ALGO_RSA:
1526     case PUBKEY_ALGO_RSA_E:
1527     case PUBKEY_ALGO_RSA_S:     return 6;
1528     case PUBKEY_ALGO_ELGAMAL_E: return 4;
1529     case PUBKEY_ALGO_DSA:       return 5;
1530     case PUBKEY_ALGO_ECDH:      return 4;
1531     case PUBKEY_ALGO_ECDSA:     return 3;
1532     case PUBKEY_ALGO_ELGAMAL:   return 4;
1533     case PUBKEY_ALGO_EDDSA:     return 3;
1534     }
1535   return 0;
1536 }
1537
1538 /* Temporary helper. */
1539 int
1540 pubkey_get_nsig (pubkey_algo_t algo)
1541 {
1542   switch (algo)
1543     {
1544     case PUBKEY_ALGO_RSA:
1545     case PUBKEY_ALGO_RSA_E:
1546     case PUBKEY_ALGO_RSA_S:     return 1;
1547     case PUBKEY_ALGO_ELGAMAL_E: return 0;
1548     case PUBKEY_ALGO_DSA:       return 2;
1549     case PUBKEY_ALGO_ECDH:      return 0;
1550     case PUBKEY_ALGO_ECDSA:     return 2;
1551     case PUBKEY_ALGO_ELGAMAL:   return 2;
1552     case PUBKEY_ALGO_EDDSA:     return 2;
1553     }
1554   return 0;
1555 }
1556
1557
1558 /* Temporary helper. */
1559 int
1560 pubkey_get_nenc (pubkey_algo_t algo)
1561 {
1562   switch (algo)
1563     {
1564     case PUBKEY_ALGO_RSA:
1565     case PUBKEY_ALGO_RSA_E:
1566     case PUBKEY_ALGO_RSA_S:     return 1;
1567     case PUBKEY_ALGO_ELGAMAL_E: return 2;
1568     case PUBKEY_ALGO_DSA:       return 0;
1569     case PUBKEY_ALGO_ECDH:      return 2;
1570     case PUBKEY_ALGO_ECDSA:     return 0;
1571     case PUBKEY_ALGO_ELGAMAL:   return 2;
1572     case PUBKEY_ALGO_EDDSA:     return 0;
1573     }
1574   return 0;
1575 }
1576
1577
1578 /* Temporary helper. */
1579 unsigned int
1580 pubkey_nbits( int algo, gcry_mpi_t *key )
1581 {
1582   int rc, nbits;
1583   gcry_sexp_t sexp;
1584
1585   if (algo == PUBKEY_ALGO_DSA
1586       && key[0] && key[1] && key[2] && key[3])
1587     {
1588       rc = gcry_sexp_build (&sexp, NULL,
1589                             "(public-key(dsa(p%m)(q%m)(g%m)(y%m)))",
1590                             key[0], key[1], key[2], key[3] );
1591     }
1592   else if ((algo == PUBKEY_ALGO_ELGAMAL || algo == PUBKEY_ALGO_ELGAMAL_E)
1593            && key[0] && key[1] && key[2])
1594     {
1595       rc = gcry_sexp_build (&sexp, NULL,
1596                             "(public-key(elg(p%m)(g%m)(y%m)))",
1597                             key[0], key[1], key[2] );
1598     }
1599   else if (is_RSA (algo)
1600            && key[0] && key[1])
1601     {
1602       rc = gcry_sexp_build (&sexp, NULL,
1603                             "(public-key(rsa(n%m)(e%m)))",
1604                             key[0], key[1] );
1605     }
1606   else if ((algo == PUBKEY_ALGO_ECDSA || algo == PUBKEY_ALGO_ECDH
1607             || algo == PUBKEY_ALGO_EDDSA)
1608            && key[0] && key[1])
1609     {
1610       char *curve = openpgp_oid_to_str (key[0]);
1611       if (!curve)
1612         rc = gpg_error_from_syserror ();
1613       else
1614         {
1615           rc = gcry_sexp_build (&sexp, NULL,
1616                                 "(public-key(ecc(curve%s)(q%m)))",
1617                                 curve, key[1]);
1618           xfree (curve);
1619         }
1620     }
1621   else
1622     return 0;
1623
1624   if (rc)
1625     BUG ();
1626
1627   nbits = gcry_pk_get_nbits (sexp);
1628   gcry_sexp_release (sexp);
1629   return nbits;
1630 }
1631
1632
1633
1634 int
1635 mpi_print (estream_t fp, gcry_mpi_t a, int mode)
1636 {
1637   int n = 0;
1638   size_t nwritten;
1639
1640   if (!a)
1641     return es_fprintf (fp, "[MPI_NULL]");
1642   if (!mode)
1643     {
1644       unsigned int n1;
1645       n1 = gcry_mpi_get_nbits(a);
1646       n += es_fprintf (fp, "[%u bits]", n1);
1647     }
1648   else if (gcry_mpi_get_flag (a, GCRYMPI_FLAG_OPAQUE))
1649     {
1650       unsigned int nbits;
1651       unsigned char *p = gcry_mpi_get_opaque (a, &nbits);
1652       if (!p)
1653         n += es_fprintf (fp, "[invalid opaque value]");
1654       else
1655         {
1656           if (!es_write_hexstring (fp, p, (nbits + 7)/8, 0, &nwritten))
1657             n += nwritten;
1658         }
1659     }
1660   else
1661     {
1662       unsigned char *buffer;
1663       size_t buflen;
1664
1665       if (gcry_mpi_aprint (GCRYMPI_FMT_USG, &buffer, &buflen, a))
1666         BUG ();
1667       if (!es_write_hexstring (fp, buffer, buflen, 0, &nwritten))
1668         n += nwritten;
1669       gcry_free (buffer);
1670     }
1671   return n;
1672 }
1673
1674
1675 /* pkey[1] or skey[1] is Q for ECDSA, which is an uncompressed point,
1676    i.e.  04 <x> <y> */
1677 unsigned int
1678 ecdsa_qbits_from_Q (unsigned int qbits)
1679 {
1680   if ((qbits%8) > 3)
1681     {
1682       log_error (_("ECDSA public key is expected to be in SEC encoding "
1683                    "multiple of 8 bits\n"));
1684       return 0;
1685     }
1686   qbits -= qbits%8;
1687   qbits /= 2;
1688   return qbits;
1689 }
1690
1691
1692 /* Ignore signatures and certifications made over certain digest
1693  * algorithms by default, MD5 is considered weak.  This allows users
1694  * to deprecate support for other algorithms as well.
1695  */
1696 void
1697 additional_weak_digest (const char* digestname)
1698 {
1699   struct weakhash *weak = NULL;
1700   const enum gcry_md_algos algo = string_to_digest_algo(digestname);
1701
1702   if (algo == GCRY_MD_MD5)
1703     return; /* MD5 is always considered weak, no need to add it.  */
1704
1705   if (algo == GCRY_MD_NONE)
1706     {
1707       log_error(_("Unknown weak digest '%s'\n"), digestname);
1708       return;
1709     }
1710
1711   /* Check to ensure it's not already present.  */
1712   for (weak = opt.additional_weak_digests; weak != NULL; weak = weak->next)
1713     {
1714       if (algo == weak->algo)
1715         return;
1716     }
1717
1718   /* Add it to the head of the list.  */
1719   weak = xmalloc(sizeof(*weak));
1720   weak->algo = algo;
1721   weak->next = opt.additional_weak_digests;
1722   opt.additional_weak_digests = weak;
1723 }