gpg: Change format for the key size in --list-key and --edit-key.
[gnupg.git] / g10 / keylist.c
1 /* keylist.c - Print information about OpenPGP keys
2  * Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006,
3  *               2008, 2010, 2012 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 <stdio.h>
23 #include <stdlib.h>
24 #include <string.h>
25 #include <errno.h>
26 #include <assert.h>
27 #ifdef HAVE_DOSISH_SYSTEM
28 #include <fcntl.h>              /* for setmode() */
29 #endif
30
31 #include "gpg.h"
32 #include "options.h"
33 #include "packet.h"
34 #include "status.h"
35 #include "keydb.h"
36 #include "photoid.h"
37 #include "util.h"
38 #include "ttyio.h"
39 #include "trustdb.h"
40 #include "main.h"
41 #include "i18n.h"
42 #include "status.h"
43 #include "call-agent.h"
44
45 static void list_all (int);
46 static void list_one (strlist_t names, int secret);
47 static void locate_one (ctrl_t ctrl, strlist_t names);
48 static void print_card_serialno (const char *serialno);
49
50 struct sig_stats
51 {
52   int inv_sigs;
53   int no_key;
54   int oth_err;
55 };
56
57 /* The stream used to write attribute packets to.  */
58 static estream_t attrib_fp;
59
60
61 /* List the keys.  If list is NULL, all available keys are listed.
62    With LOCATE_MODE set the locate algorithm is used to find a
63    key.  */
64 void
65 public_key_list (ctrl_t ctrl, strlist_t list, int locate_mode)
66 {
67   if (opt.with_colons)
68     {
69       byte trust_model, marginals, completes, cert_depth, min_cert_level;
70       ulong created, nextcheck;
71
72       read_trust_options (&trust_model, &created, &nextcheck,
73                           &marginals, &completes, &cert_depth, &min_cert_level);
74
75       es_fprintf (es_stdout, "tru:");
76
77       if (nextcheck && nextcheck <= make_timestamp ())
78         es_fprintf (es_stdout, "o");
79       if (trust_model != opt.trust_model)
80         es_fprintf (es_stdout, "t");
81       if (opt.trust_model == TM_PGP || opt.trust_model == TM_CLASSIC)
82         {
83           if (marginals != opt.marginals_needed)
84             es_fprintf (es_stdout, "m");
85           if (completes != opt.completes_needed)
86             es_fprintf (es_stdout, "c");
87           if (cert_depth != opt.max_cert_depth)
88             es_fprintf (es_stdout, "d");
89           if (min_cert_level != opt.min_cert_level)
90             es_fprintf (es_stdout, "l");
91         }
92
93       es_fprintf (es_stdout, ":%d:%lu:%lu", trust_model, created, nextcheck);
94
95       /* Only show marginals, completes, and cert_depth in the classic
96          or PGP trust models since they are not meaningful
97          otherwise. */
98
99       if (trust_model == TM_PGP || trust_model == TM_CLASSIC)
100         es_fprintf (es_stdout, ":%d:%d:%d", marginals, completes, cert_depth);
101
102       es_fprintf (es_stdout, "\n");
103     }
104
105   /* We need to do the stale check right here because it might need to
106      update the keyring while we already have the keyring open.  This
107      is very bad for W32 because of a sharing violation. For real OSes
108      it might lead to false results if we are later listing a keyring
109      which is associated with the inode of a deleted file.  */
110   check_trustdb_stale ();
111
112   if (locate_mode)
113     locate_one (ctrl, list);
114   else if (!list)
115     list_all (0);
116   else
117     list_one (list, 0);
118 }
119
120
121 void
122 secret_key_list (ctrl_t ctrl, strlist_t list)
123 {
124   (void)ctrl;
125
126   check_trustdb_stale ();
127
128   if (!list)
129     list_all (1);
130   else                          /* List by user id */
131     list_one (list, 1);
132 }
133
134 void
135 print_seckey_info (PKT_public_key *pk)
136 {
137   u32 keyid[2];
138   char *p;
139   char pkstrbuf[PUBKEY_STRING_SIZE];
140
141   keyid_from_pk (pk, keyid);
142   p = get_user_id_native (keyid);
143
144   tty_printf ("\nsec  %s/%s %s %s\n",
145               pubkey_string (pk, pkstrbuf, sizeof pkstrbuf),
146               keystr (keyid), datestr_from_pk (pk), p);
147
148   xfree (p);
149 }
150
151 /* Print information about the public key.  With FP passed as NULL,
152    the tty output interface is used, otherwise output is directted to
153    the given stream.  */
154 void
155 print_pubkey_info (estream_t fp, PKT_public_key * pk)
156 {
157   u32 keyid[2];
158   char *p;
159   char pkstrbuf[PUBKEY_STRING_SIZE];
160
161   keyid_from_pk (pk, keyid);
162
163   /* If the pk was chosen by a particular user ID, that is the one to
164      print.  */
165   if (pk->user_id)
166     p = utf8_to_native (pk->user_id->name, pk->user_id->len, 0);
167   else
168     p = get_user_id_native (keyid);
169
170   if (fp)
171     tty_printf ("\n");
172   tty_fprintf (fp, "pub  %s/%s %s %s\n",
173                pubkey_string (pk, pkstrbuf, sizeof pkstrbuf),
174                keystr (keyid), datestr_from_pk (pk), p);
175   xfree (p);
176 }
177
178
179 /* Print basic information of a secret key including the card serial
180    number information.  */
181 #ifdef ENABLE_CARD_SUPPORT
182 void
183 print_card_key_info (estream_t fp, kbnode_t keyblock)
184 {
185   kbnode_t node;
186   char *hexgrip;
187   char *serialno;
188   int s2k_char;
189   char pkstrbuf[PUBKEY_STRING_SIZE];
190
191   for (node = keyblock; node; node = node->next)
192     {
193       if (node->pkt->pkttype == PKT_PUBLIC_KEY
194           || node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
195         {
196           int rc;
197           PKT_public_key *pk = node->pkt->pkt.public_key;
198
199           serialno = NULL;
200           rc = hexkeygrip_from_pk (pk, &hexgrip);
201           if (rc)
202             {
203               log_error ("error computing a keygrip: %s\n", gpg_strerror (rc));
204               s2k_char = '?';
205             }
206           else if (!agent_get_keyinfo (NULL, hexgrip, &serialno))
207             s2k_char = serialno? '>':' ';
208           else
209             s2k_char = '#';  /* Key not found.  */
210
211           tty_fprintf (fp, "%s%c  %s/%s  ",
212                        node->pkt->pkttype == PKT_PUBLIC_KEY ? "sec" : "ssb",
213                        s2k_char,
214                        pubkey_string (pk, pkstrbuf, sizeof pkstrbuf),
215                        keystr_from_pk (pk));
216           tty_fprintf (fp, _("created: %s"), datestr_from_pk (pk));
217           tty_fprintf (fp, "  ");
218           tty_fprintf (fp, _("expires: %s"), expirestr_from_pk (pk));
219           if (serialno)
220             {
221               tty_fprintf (fp, "\n                      ");
222               tty_fprintf (fp, _("card-no: "));
223               if (strlen (serialno) == 32
224                   && !strncmp (serialno, "D27600012401", 12))
225                 {
226                   /* This is an OpenPGP card.  Print the relevant part.  */
227                   /* Example: D2760001240101010001000003470000 */
228                   /*                          xxxxyyyyyyyy     */
229                   tty_fprintf (fp, "%.*s %.*s", 4, serialno+16, 8, serialno+20);
230                 }
231               else
232                 tty_fprintf (fp, "%s", serialno);
233             }
234           tty_fprintf (fp, "\n");
235           xfree (hexgrip);
236           xfree (serialno);
237         }
238     }
239 }
240 #endif /*ENABLE_CARD_SUPPORT*/
241
242
243 /* Flags = 0x01 hashed 0x02 critical.  */
244 static void
245 status_one_subpacket (sigsubpkttype_t type, size_t len, int flags,
246                       const byte * buf)
247 {
248   char status[40];
249
250   /* Don't print these. */
251   if (len > 256)
252     return;
253
254   snprintf (status, sizeof status,
255             "%d %u %u ", type, flags, (unsigned int) len);
256
257   write_status_text_and_buffer (STATUS_SIG_SUBPACKET, status, buf, len, 0);
258 }
259
260
261 /* Print a policy URL.  Allowed values for MODE are:
262  *   0 - print to stdout.
263  *   1 - use log_info and emit status messages.
264  *   2 - emit only status messages.
265  */
266 void
267 show_policy_url (PKT_signature * sig, int indent, int mode)
268 {
269   const byte *p;
270   size_t len;
271   int seq = 0, crit;
272   estream_t fp = mode ? log_get_stream () : es_stdout;
273
274   while ((p =
275           enum_sig_subpkt (sig->hashed, SIGSUBPKT_POLICY, &len, &seq, &crit)))
276     {
277       if (mode != 2)
278         {
279           int i;
280           const char *str;
281
282           for (i = 0; i < indent; i++)
283             es_putc (' ', fp);
284
285           if (crit)
286             str = _("Critical signature policy: ");
287           else
288             str = _("Signature policy: ");
289           if (mode)
290             log_info ("%s", str);
291           else
292             es_fprintf (fp, "%s", str);
293           print_utf8_buffer (fp, p, len);
294           es_fprintf (fp, "\n");
295         }
296
297       if (mode)
298         write_status_buffer (STATUS_POLICY_URL, p, len, 0);
299     }
300 }
301
302
303 /*
304   mode=0 for stdout.
305   mode=1 for log_info + status messages
306   mode=2 for status messages only
307 */
308 /* TODO: use this */
309 void
310 show_keyserver_url (PKT_signature * sig, int indent, int mode)
311 {
312   const byte *p;
313   size_t len;
314   int seq = 0, crit;
315   estream_t fp = mode ? log_get_stream () : es_stdout;
316
317   while ((p =
318           enum_sig_subpkt (sig->hashed, SIGSUBPKT_PREF_KS, &len, &seq,
319                            &crit)))
320     {
321       if (mode != 2)
322         {
323           int i;
324           const char *str;
325
326           for (i = 0; i < indent; i++)
327             es_putc (' ', es_stdout);
328
329           if (crit)
330             str = _("Critical preferred keyserver: ");
331           else
332             str = _("Preferred keyserver: ");
333           if (mode)
334             log_info ("%s", str);
335           else
336             es_fprintf (es_stdout, "%s", str);
337           print_utf8_buffer (fp, p, len);
338           es_fprintf (fp, "\n");
339         }
340
341       if (mode)
342         status_one_subpacket (SIGSUBPKT_PREF_KS, len,
343                               (crit ? 0x02 : 0) | 0x01, p);
344     }
345 }
346
347 /*
348   mode=0 for stdout.
349   mode=1 for log_info + status messages
350   mode=2 for status messages only
351
352   Defined bits in WHICH:
353     1 == standard notations
354     2 == user notations
355 */
356 void
357 show_notation (PKT_signature * sig, int indent, int mode, int which)
358 {
359   estream_t fp = mode ? log_get_stream () : es_stdout;
360   struct notation *nd, *notations;
361
362   if (which == 0)
363     which = 3;
364
365   notations = sig_to_notation (sig);
366
367   /* There may be multiple notations in the same sig. */
368   for (nd = notations; nd; nd = nd->next)
369     {
370       if (mode != 2)
371         {
372           int has_at = !!strchr (nd->name, '@');
373
374           if ((which & 1 && !has_at) || (which & 2 && has_at))
375             {
376               int i;
377               const char *str;
378
379               for (i = 0; i < indent; i++)
380                 es_putc (' ', es_stdout);
381
382               if (nd->flags.critical)
383                 str = _("Critical signature notation: ");
384               else
385                 str = _("Signature notation: ");
386               if (mode)
387                 log_info ("%s", str);
388               else
389                 es_fprintf (es_stdout, "%s", str);
390               /* This is all UTF8 */
391               print_utf8_buffer (fp, nd->name, strlen (nd->name));
392               es_fprintf (fp, "=");
393               print_utf8_buffer (fp, nd->value, strlen (nd->value));
394               es_fprintf (fp, "\n");
395             }
396         }
397
398       if (mode)
399         {
400           write_status_buffer (STATUS_NOTATION_NAME,
401                                nd->name, strlen (nd->name), 0);
402           write_status_buffer (STATUS_NOTATION_DATA,
403                                nd->value, strlen (nd->value), 50);
404         }
405     }
406
407   free_notation (notations);
408 }
409
410 static void
411 print_signature_stats (struct sig_stats *s)
412 {
413   if (s->inv_sigs == 1)
414     tty_printf (_("1 bad signature\n"));
415   else if (s->inv_sigs)
416     tty_printf (_("%d bad signatures\n"), s->inv_sigs);
417   if (s->no_key == 1)
418     tty_printf (_("1 signature not checked due to a missing key\n"));
419   else if (s->no_key)
420     tty_printf (_("%d signatures not checked due to missing keys\n"),
421                 s->no_key);
422   if (s->oth_err == 1)
423     tty_printf (_("1 signature not checked due to an error\n"));
424   else if (s->oth_err)
425     tty_printf (_("%d signatures not checked due to errors\n"), s->oth_err);
426 }
427
428 static void
429 list_all (int secret)
430 {
431   KEYDB_HANDLE hd;
432   KBNODE keyblock = NULL;
433   int rc = 0;
434   const char *lastresname, *resname;
435   struct sig_stats stats;
436
437   memset (&stats, 0, sizeof (stats));
438
439   hd = keydb_new ();
440   if (!hd)
441     rc = gpg_error (GPG_ERR_GENERAL);
442   else
443     rc = keydb_search_first (hd);
444   if (rc)
445     {
446       if (gpg_err_code (rc) != GPG_ERR_NOT_FOUND)
447         log_error ("keydb_search_first failed: %s\n", g10_errstr (rc));
448       goto leave;
449     }
450
451   lastresname = NULL;
452   do
453     {
454       rc = keydb_get_keyblock (hd, &keyblock);
455       if (rc)
456         {
457           log_error ("keydb_get_keyblock failed: %s\n", g10_errstr (rc));
458           goto leave;
459         }
460       if (secret && agent_probe_any_secret_key (NULL, keyblock))
461         ; /* Secret key listing requested but this isn't one.  */
462       else
463         {
464           if (!opt.with_colons)
465             {
466               resname = keydb_get_resource_name (hd);
467               if (lastresname != resname)
468                 {
469                   int i;
470
471                   es_fprintf (es_stdout, "%s\n", resname);
472                   for (i = strlen (resname); i; i--)
473                     es_putc ('-', es_stdout);
474                   es_putc ('\n', es_stdout);
475                   lastresname = resname;
476                 }
477             }
478           merge_keys_and_selfsig (keyblock);
479           list_keyblock (keyblock, secret, opt.fingerprint,
480                          opt.check_sigs ? &stats : NULL);
481         }
482       release_kbnode (keyblock);
483       keyblock = NULL;
484     }
485   while (!(rc = keydb_search_next (hd)));
486   if (rc && gpg_err_code (rc) != GPG_ERR_NOT_FOUND)
487     log_error ("keydb_search_next failed: %s\n", g10_errstr (rc));
488
489   if (opt.check_sigs && !opt.with_colons)
490     print_signature_stats (&stats);
491
492 leave:
493   release_kbnode (keyblock);
494   keydb_release (hd);
495 }
496
497
498 static void
499 list_one (strlist_t names, int secret)
500 {
501   int rc = 0;
502   KBNODE keyblock = NULL;
503   GETKEY_CTX ctx;
504   const char *resname;
505   const char *keyring_str = _("Keyring");
506   int i;
507   struct sig_stats stats;
508
509   memset (&stats, 0, sizeof (stats));
510
511   /* fixme: using the bynames function has the disadvantage that we
512    * don't know wether one of the names given was not found.  OTOH,
513    * this function has the advantage to list the names in the
514    * sequence as defined by the keyDB and does not duplicate
515    * outputs.  A solution could be do test whether all given have
516    * been listed (this needs a way to use the keyDB search
517    * functions) or to have the search function return indicators for
518    * found names.  Yet another way is to use the keydb search
519    * facilities directly. */
520   rc = getkey_bynames (&ctx, NULL, names, secret, &keyblock);
521   if (rc)
522     {
523       log_error ("error reading key: %s\n", g10_errstr (rc));
524       get_pubkey_end (ctx);
525       return;
526     }
527
528   do
529     {
530       if ((opt.list_options & LIST_SHOW_KEYRING) && !opt.with_colons)
531         {
532           resname = keydb_get_resource_name (get_ctx_handle (ctx));
533           es_fprintf (es_stdout, "%s: %s\n", keyring_str, resname);
534           for (i = strlen (resname) + strlen (keyring_str) + 2; i; i--)
535             es_putc ('-', es_stdout);
536           es_putc ('\n', es_stdout);
537         }
538       list_keyblock (keyblock, secret, opt.fingerprint,
539                      (!secret && opt.check_sigs)? &stats : NULL);
540       release_kbnode (keyblock);
541     }
542   while (!getkey_next (ctx, NULL, &keyblock));
543   getkey_end (ctx);
544
545   if (opt.check_sigs && !opt.with_colons)
546     print_signature_stats (&stats);
547 }
548
549
550 static void
551 locate_one (ctrl_t ctrl, strlist_t names)
552 {
553   int rc = 0;
554   strlist_t sl;
555   GETKEY_CTX ctx = NULL;
556   KBNODE keyblock = NULL;
557   struct sig_stats stats;
558
559   memset (&stats, 0, sizeof (stats));
560
561   for (sl = names; sl; sl = sl->next)
562     {
563       rc = get_pubkey_byname (ctrl, &ctx, NULL, sl->d, &keyblock, NULL, 1, 0);
564       if (rc)
565         {
566           if (gpg_err_code (rc) != GPG_ERR_NO_PUBKEY)
567             log_error ("error reading key: %s\n", g10_errstr (rc));
568         }
569       else
570         {
571           do
572             {
573               list_keyblock (keyblock, 0, opt.fingerprint,
574                              opt.check_sigs ? &stats : NULL);
575               release_kbnode (keyblock);
576             }
577           while (ctx && !get_pubkey_next (ctx, NULL, &keyblock));
578           get_pubkey_end (ctx);
579           ctx = NULL;
580         }
581     }
582
583   if (opt.check_sigs && !opt.with_colons)
584     print_signature_stats (&stats);
585 }
586
587
588 static void
589 print_key_data (PKT_public_key * pk)
590 {
591   int n = pk ? pubkey_get_npkey (pk->pubkey_algo) : 0;
592   int i;
593
594   for (i = 0; i < n; i++)
595     {
596       es_fprintf (es_stdout, "pkd:%d:%u:", i, mpi_get_nbits (pk->pkey[i]));
597       mpi_print (es_stdout, pk->pkey[i], 1);
598       es_putc (':', es_stdout);
599       es_putc ('\n', es_stdout);
600     }
601 }
602
603 static void
604 print_capabilities (PKT_public_key *pk, KBNODE keyblock)
605 {
606   unsigned int use = pk->pubkey_usage;
607   int c_printed = 0;
608
609   if (use & PUBKEY_USAGE_ENC)
610     es_putc ('e', es_stdout);
611
612   if (use & PUBKEY_USAGE_SIG)
613     {
614       es_putc ('s', es_stdout);
615       if (pk->flags.primary)
616         {
617           es_putc ('c', es_stdout);
618           /* The PUBKEY_USAGE_CERT flag was introduced later and we
619              used to always print 'c' for a primary key.  To avoid any
620              regression here we better track whether we printed 'c'
621              already.  */
622           c_printed = 1;
623         }
624     }
625
626   if ((use & PUBKEY_USAGE_CERT) && !c_printed)
627     es_putc ('c', es_stdout);
628
629   if ((use & PUBKEY_USAGE_AUTH))
630     es_putc ('a', es_stdout);
631
632   if ((use & PUBKEY_USAGE_UNKNOWN))
633     es_putc ('?', es_stdout);
634
635   if (keyblock)
636     {
637       /* Figure out the usable capabilities.  */
638       KBNODE k;
639       int enc = 0, sign = 0, cert = 0, auth = 0, disabled = 0;
640
641       for (k = keyblock; k; k = k->next)
642         {
643           if (k->pkt->pkttype == PKT_PUBLIC_KEY
644               || k->pkt->pkttype == PKT_PUBLIC_SUBKEY)
645             {
646               pk = k->pkt->pkt.public_key;
647
648               if (pk->flags.primary)
649                 disabled = pk_is_disabled (pk);
650
651               if (pk->flags.valid && !pk->flags.revoked && !pk->has_expired)
652                 {
653                   if (pk->pubkey_usage & PUBKEY_USAGE_ENC)
654                     enc = 1;
655                   if (pk->pubkey_usage & PUBKEY_USAGE_SIG)
656                     {
657                       sign = 1;
658                       if (pk->flags.primary)
659                         cert = 1;
660                     }
661                   if (pk->pubkey_usage & PUBKEY_USAGE_CERT)
662                     cert = 1;
663                   if ((pk->pubkey_usage & PUBKEY_USAGE_AUTH))
664                     auth = 1;
665                 }
666             }
667         }
668       if (enc)
669         es_putc ('E', es_stdout);
670       if (sign)
671         es_putc ('S', es_stdout);
672       if (cert)
673         es_putc ('C', es_stdout);
674       if (auth)
675         es_putc ('A', es_stdout);
676       if (disabled)
677         es_putc ('D', es_stdout);
678     }
679
680   es_putc (':', es_stdout);
681 }
682
683
684 /* FLAGS: 0x01 hashed
685           0x02 critical  */
686 static void
687 print_one_subpacket (sigsubpkttype_t type, size_t len, int flags,
688                      const byte * buf)
689 {
690   size_t i;
691
692   es_fprintf (es_stdout, "spk:%d:%u:%u:", type, flags, (unsigned int) len);
693
694   for (i = 0; i < len; i++)
695     {
696       /* printable ascii other than : and % */
697       if (buf[i] >= 32 && buf[i] <= 126 && buf[i] != ':' && buf[i] != '%')
698         es_fprintf (es_stdout, "%c", buf[i]);
699       else
700         es_fprintf (es_stdout, "%%%02X", buf[i]);
701     }
702
703   es_fprintf (es_stdout, "\n");
704 }
705
706
707 void
708 print_subpackets_colon (PKT_signature * sig)
709 {
710   byte *i;
711
712   assert (opt.show_subpackets);
713
714   for (i = opt.show_subpackets; *i; i++)
715     {
716       const byte *p;
717       size_t len;
718       int seq, crit;
719
720       seq = 0;
721
722       while ((p = enum_sig_subpkt (sig->hashed, *i, &len, &seq, &crit)))
723         print_one_subpacket (*i, len, 0x01 | (crit ? 0x02 : 0), p);
724
725       seq = 0;
726
727       while ((p = enum_sig_subpkt (sig->unhashed, *i, &len, &seq, &crit)))
728         print_one_subpacket (*i, len, 0x00 | (crit ? 0x02 : 0), p);
729     }
730 }
731
732
733 void
734 dump_attribs (const PKT_user_id *uid, PKT_public_key *pk)
735 {
736   int i;
737
738   if (!attrib_fp)
739     return;
740
741   for (i = 0; i < uid->numattribs; i++)
742     {
743       if (is_status_enabled ())
744         {
745           byte array[MAX_FINGERPRINT_LEN], *p;
746           char buf[(MAX_FINGERPRINT_LEN * 2) + 90];
747           size_t j, n;
748
749           if (!pk)
750             BUG ();
751           fingerprint_from_pk (pk, array, &n);
752
753           p = array;
754           for (j = 0; j < n; j++, p++)
755             sprintf (buf + 2 * j, "%02X", *p);
756
757           sprintf (buf + strlen (buf), " %lu %u %u %u %lu %lu %u",
758                    (ulong) uid->attribs[i].len, uid->attribs[i].type, i + 1,
759                    uid->numattribs, (ulong) uid->created,
760                    (ulong) uid->expiredate,
761                    ((uid->is_primary ? 0x01 : 0) | (uid->
762                                                     is_revoked ? 0x02 : 0) |
763                     (uid->is_expired ? 0x04 : 0)));
764           write_status_text (STATUS_ATTRIBUTE, buf);
765         }
766
767       es_fwrite (uid->attribs[i].data, uid->attribs[i].len, 1, attrib_fp);
768       es_fflush (attrib_fp);
769     }
770 }
771
772
773 static void
774 list_keyblock_print (KBNODE keyblock, int secret, int fpr, void *opaque)
775 {
776   int rc;
777   KBNODE kbctx;
778   KBNODE node;
779   PKT_public_key *pk;
780   struct sig_stats *stats = opaque;
781   int skip_sigs = 0;
782   int s2k_char;
783   char *hexgrip = NULL;
784   char *serialno = NULL;
785   char pkstrbuf[PUBKEY_STRING_SIZE];
786
787   /* Get the keyid from the keyblock.  */
788   node = find_kbnode (keyblock, PKT_PUBLIC_KEY);
789   if (!node)
790     {
791       log_error ("Oops; key lost!\n");
792       dump_kbnode (keyblock);
793       return;
794     }
795
796   pk = node->pkt->pkt.public_key;
797
798   if (secret || opt.with_keygrip)
799     {
800       rc = hexkeygrip_from_pk (pk, &hexgrip);
801       if (rc)
802         log_error ("error computing a keygrip: %s\n", gpg_strerror (rc));
803     }
804
805   if (secret)
806     {
807       if (!agent_get_keyinfo (NULL, hexgrip, &serialno))
808         s2k_char = serialno? '>':' ';
809       else
810         s2k_char = '#';  /* Key not found.  */
811     }
812   else
813     s2k_char = ' ';
814
815   check_trustdb_stale ();
816
817
818   es_fprintf (es_stdout, "%s%c  %s/%s %s",
819               secret? "sec":"pub",
820               s2k_char,
821               pubkey_string (pk, pkstrbuf, sizeof pkstrbuf),
822               keystr_from_pk (pk), datestr_from_pk (pk));
823
824   if (pk->pubkey_algo == PUBKEY_ALGO_ECDSA
825       || pk->pubkey_algo == PUBKEY_ALGO_EDDSA
826       || pk->pubkey_algo == PUBKEY_ALGO_ECDH)
827     {
828       char *curve = openpgp_oid_to_str (pk->pkey[0]);
829       const char *name = openpgp_oid_to_curve (curve);
830       if (!*name || *name == '?')
831         name = curve;
832       es_fprintf (es_stdout, " %s", name);
833       xfree (curve);
834     }
835
836   if (pk->flags.revoked)
837     {
838       es_fprintf (es_stdout, " [");
839       es_fprintf (es_stdout, _("revoked: %s"), revokestr_from_pk (pk));
840       es_fprintf (es_stdout, "]");
841     }
842   else if (pk->has_expired)
843     {
844       es_fprintf (es_stdout, " [");
845       es_fprintf (es_stdout, _("expired: %s"), expirestr_from_pk (pk));
846       es_fprintf (es_stdout, "]");
847     }
848   else if (pk->expiredate)
849     {
850       es_fprintf (es_stdout, " [");
851       es_fprintf (es_stdout, _("expires: %s"), expirestr_from_pk (pk));
852       es_fprintf (es_stdout, "]");
853     }
854
855 #if 0
856   /* I need to think about this some more.  It's easy enough to
857      include, but it looks sort of confusing in the listing... */
858   if (opt.list_options & LIST_SHOW_VALIDITY)
859     {
860       int validity = get_validity (pk, NULL);
861       es_fprintf (es_stdout, " [%s]", trust_value_to_string (validity));
862     }
863 #endif
864
865   es_fprintf (es_stdout, "\n");
866
867   if (fpr)
868     print_fingerprint (pk, 0);
869
870   if (opt.with_keygrip && hexgrip)
871     es_fprintf (es_stdout, "      Keygrip = %s\n", hexgrip);
872
873   if (serialno)
874     print_card_serialno (serialno);
875
876   if (opt.with_key_data)
877     print_key_data (pk);
878
879   for (kbctx = NULL; (node = walk_kbnode (keyblock, &kbctx, 0));)
880     {
881       if (node->pkt->pkttype == PKT_USER_ID && !opt.fast_list_mode)
882         {
883           PKT_user_id *uid = node->pkt->pkt.user_id;
884
885           if (pk && (uid->is_expired || uid->is_revoked)
886               && !(opt.list_options & LIST_SHOW_UNUSABLE_UIDS))
887             {
888               skip_sigs = 1;
889               continue;
890             }
891           else
892             skip_sigs = 0;
893
894           if (attrib_fp && uid->attrib_data != NULL)
895             dump_attribs (uid, pk);
896
897           if ((uid->is_revoked || uid->is_expired)
898               || ((opt.list_options & LIST_SHOW_UID_VALIDITY) && pk))
899             {
900               const char *validity;
901               int indent;
902
903               validity = uid_trust_string_fixed (pk, uid);
904               indent =
905                 (keystrlen () + 9) -
906                 atoi (uid_trust_string_fixed (NULL, NULL));
907
908               if (indent < 0 || indent > 40)
909                 indent = 0;
910
911               es_fprintf (es_stdout, "uid%*s%s ", indent, "", validity);
912             }
913           else
914             es_fprintf (es_stdout, "uid%*s", (int) keystrlen () + 10, "");
915
916           print_utf8_buffer (es_stdout, uid->name, uid->len);
917           es_putc ('\n', es_stdout);
918
919           if ((opt.list_options & LIST_SHOW_PHOTOS) && uid->attribs != NULL)
920             show_photos (uid->attribs, uid->numattribs, pk, uid);
921         }
922       else if (node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
923         {
924           PKT_public_key *pk2 = node->pkt->pkt.public_key;
925
926           if ((pk2->flags.revoked || pk2->has_expired)
927               && !(opt.list_options & LIST_SHOW_UNUSABLE_SUBKEYS))
928             {
929               skip_sigs = 1;
930               continue;
931             }
932           else
933             skip_sigs = 0;
934
935           xfree (serialno); serialno = NULL;
936           xfree (hexgrip); hexgrip = NULL;
937           if (secret || opt.with_keygrip)
938             {
939               rc = hexkeygrip_from_pk (pk2, &hexgrip);
940               if (rc)
941                 log_error ("error computing a keygrip: %s\n",
942                            gpg_strerror (rc));
943             }
944           if (secret)
945             {
946               if (!agent_get_keyinfo (NULL, hexgrip, &serialno))
947                 s2k_char = serialno? '>':' ';
948               else
949                 s2k_char = '#';  /* Key not found.  */
950             }
951           else
952             s2k_char = ' ';
953
954           es_fprintf (es_stdout, "%s%c  %s/%s %s",
955                   secret? "ssb":"sub",
956                   s2k_char,
957                   pubkey_string (pk2, pkstrbuf, sizeof pkstrbuf),
958                   keystr_from_pk (pk2), datestr_from_pk (pk2));
959
960           if (pk2->pubkey_algo == PUBKEY_ALGO_ECDSA
961               || pk2->pubkey_algo == PUBKEY_ALGO_EDDSA
962               || pk2->pubkey_algo == PUBKEY_ALGO_ECDH)
963             {
964               char *curve = openpgp_oid_to_str (pk2->pkey[0]);
965               const char *name = openpgp_oid_to_curve (curve);
966               if (!*name || *name == '?')
967                 name = curve;
968               es_fprintf (es_stdout, " %s", name);
969               xfree (curve);
970             }
971
972           if (pk2->flags.revoked)
973             {
974               es_fprintf (es_stdout, " [");
975               es_fprintf (es_stdout, _("revoked: %s"), revokestr_from_pk (pk2));
976               es_fprintf (es_stdout, "]");
977             }
978           else if (pk2->has_expired)
979             {
980               es_fprintf (es_stdout, " [");
981               es_fprintf (es_stdout, _("expired: %s"), expirestr_from_pk (pk2));
982               es_fprintf (es_stdout, "]");
983             }
984           else if (pk2->expiredate)
985             {
986               es_fprintf (es_stdout, " [");
987               es_fprintf (es_stdout, _("expires: %s"), expirestr_from_pk (pk2));
988               es_fprintf (es_stdout, "]");
989             }
990           es_putc ('\n', es_stdout);
991           if (fpr > 1)
992             {
993               print_fingerprint (pk2, 0);
994               if (serialno)
995                 print_card_serialno (serialno);
996             }
997           if (opt.with_keygrip && hexgrip)
998             es_fprintf (es_stdout, "      Keygrip = %s\n", hexgrip);
999           if (opt.with_key_data)
1000             print_key_data (pk2);
1001         }
1002       else if (opt.list_sigs
1003                && node->pkt->pkttype == PKT_SIGNATURE && !skip_sigs)
1004         {
1005           PKT_signature *sig = node->pkt->pkt.signature;
1006           int sigrc;
1007           char *sigstr;
1008
1009           if (stats)
1010             {
1011               rc = check_key_signature (keyblock, node, NULL);
1012               switch (gpg_err_code (rc))
1013                 {
1014                 case 0:
1015                   sigrc = '!';
1016                   break;
1017                 case GPG_ERR_BAD_SIGNATURE:
1018                   stats->inv_sigs++;
1019                   sigrc = '-';
1020                   break;
1021                 case GPG_ERR_NO_PUBKEY:
1022                 case GPG_ERR_UNUSABLE_PUBKEY:
1023                   stats->no_key++;
1024                   continue;
1025                 default:
1026                   stats->oth_err++;
1027                   sigrc = '%';
1028                   break;
1029                 }
1030
1031               /* TODO: Make sure a cached sig record here still has
1032                  the pk that issued it.  See also
1033                  keyedit.c:print_and_check_one_sig */
1034             }
1035           else
1036             {
1037               rc = 0;
1038               sigrc = ' ';
1039             }
1040
1041           if (sig->sig_class == 0x20 || sig->sig_class == 0x28
1042               || sig->sig_class == 0x30)
1043             sigstr = "rev";
1044           else if ((sig->sig_class & ~3) == 0x10)
1045             sigstr = "sig";
1046           else if (sig->sig_class == 0x18)
1047             sigstr = "sig";
1048           else if (sig->sig_class == 0x1F)
1049             sigstr = "sig";
1050           else
1051             {
1052               es_fprintf (es_stdout, "sig                             "
1053                       "[unexpected signature class 0x%02x]\n",
1054                       sig->sig_class);
1055               continue;
1056             }
1057
1058           es_fputs (sigstr, es_stdout);
1059           es_fprintf (es_stdout, "%c%c %c%c%c%c%c%c %s %s",
1060                   sigrc, (sig->sig_class - 0x10 > 0 &&
1061                           sig->sig_class - 0x10 <
1062                           4) ? '0' + sig->sig_class - 0x10 : ' ',
1063                   sig->flags.exportable ? ' ' : 'L',
1064                   sig->flags.revocable ? ' ' : 'R',
1065                   sig->flags.policy_url ? 'P' : ' ',
1066                   sig->flags.notation ? 'N' : ' ',
1067                   sig->flags.expired ? 'X' : ' ',
1068                   (sig->trust_depth > 9) ? 'T' : (sig->trust_depth >
1069                                                   0) ? '0' +
1070                   sig->trust_depth : ' ', keystr (sig->keyid),
1071                   datestr_from_sig (sig));
1072           if (opt.list_options & LIST_SHOW_SIG_EXPIRE)
1073             es_fprintf (es_stdout, " %s", expirestr_from_sig (sig));
1074           es_fprintf (es_stdout, "  ");
1075           if (sigrc == '%')
1076             es_fprintf (es_stdout, "[%s] ", g10_errstr (rc));
1077           else if (sigrc == '?')
1078             ;
1079           else if (!opt.fast_list_mode)
1080             {
1081               size_t n;
1082               char *p = get_user_id (sig->keyid, &n);
1083               print_utf8_buffer (es_stdout, p, n);
1084               xfree (p);
1085             }
1086           es_putc ('\n', es_stdout);
1087
1088           if (sig->flags.policy_url
1089               && (opt.list_options & LIST_SHOW_POLICY_URLS))
1090             show_policy_url (sig, 3, 0);
1091
1092           if (sig->flags.notation && (opt.list_options & LIST_SHOW_NOTATIONS))
1093             show_notation (sig, 3, 0,
1094                            ((opt.
1095                              list_options & LIST_SHOW_STD_NOTATIONS) ? 1 : 0)
1096                            +
1097                            ((opt.
1098                              list_options & LIST_SHOW_USER_NOTATIONS) ? 2 :
1099                             0));
1100
1101           if (sig->flags.pref_ks
1102               && (opt.list_options & LIST_SHOW_KEYSERVER_URLS))
1103             show_keyserver_url (sig, 3, 0);
1104
1105           /* fixme: check or list other sigs here */
1106         }
1107     }
1108   es_putc ('\n', es_stdout);
1109   xfree (serialno);
1110   xfree (hexgrip);
1111 }
1112
1113 void
1114 print_revokers (PKT_public_key * pk)
1115 {
1116   /* print the revoker record */
1117   if (!pk->revkey && pk->numrevkeys)
1118     BUG ();
1119   else
1120     {
1121       int i, j;
1122
1123       for (i = 0; i < pk->numrevkeys; i++)
1124         {
1125           byte *p;
1126
1127           es_fprintf (es_stdout, "rvk:::%d::::::", pk->revkey[i].algid);
1128           p = pk->revkey[i].fpr;
1129           for (j = 0; j < 20; j++, p++)
1130             es_fprintf (es_stdout, "%02X", *p);
1131           es_fprintf (es_stdout, ":%02x%s:\n", pk->revkey[i].class,
1132                   (pk->revkey[i].class & 0x40) ? "s" : "");
1133         }
1134     }
1135 }
1136
1137 static void
1138 list_keyblock_colon (KBNODE keyblock, int secret, int fpr)
1139 {
1140   int rc;
1141   KBNODE kbctx;
1142   KBNODE node;
1143   PKT_public_key *pk;
1144   u32 keyid[2];
1145   int trustletter = 0;
1146   int ulti_hack = 0;
1147   int i;
1148   char *p;
1149   char *hexgrip = NULL;
1150   char *serialno = NULL;
1151   int stubkey;
1152
1153   /* Get the keyid from the keyblock.  */
1154   node = find_kbnode (keyblock, PKT_PUBLIC_KEY);
1155   if (!node)
1156     {
1157       log_error ("Oops; key lost!\n");
1158       dump_kbnode (keyblock);
1159       return;
1160     }
1161
1162   pk = node->pkt->pkt.public_key;
1163   if (secret || opt.with_keygrip || opt.with_key_data)
1164     {
1165       rc = hexkeygrip_from_pk (pk, &hexgrip);
1166       if (rc)
1167         log_error ("error computing a keygrip: %s\n", gpg_strerror (rc));
1168     }
1169   stubkey = 0;
1170   if (secret && agent_get_keyinfo (NULL, hexgrip, &serialno))
1171     stubkey = 1;  /* Key not found.  */
1172
1173   keyid_from_pk (pk, keyid);
1174   es_fputs (secret? "sec:":"pub:", es_stdout);
1175   if (!pk->flags.valid)
1176     es_putc ('i', es_stdout);
1177   else if (pk->flags.revoked)
1178     es_putc ('r', es_stdout);
1179   else if (pk->has_expired)
1180     es_putc ('e', es_stdout);
1181   else if (opt.fast_list_mode || opt.no_expensive_trust_checks)
1182     ;
1183   else
1184     {
1185       trustletter = get_validity_info (pk, NULL);
1186       if (trustletter == 'u')
1187         ulti_hack = 1;
1188       es_putc (trustletter, es_stdout);
1189     }
1190
1191   es_fprintf (es_stdout, ":%u:%d:%08lX%08lX:%s:%s::",
1192           nbits_from_pk (pk),
1193           pk->pubkey_algo,
1194           (ulong) keyid[0], (ulong) keyid[1],
1195           colon_datestr_from_pk (pk), colon_strtime (pk->expiredate));
1196
1197   if (!opt.fast_list_mode && !opt.no_expensive_trust_checks)
1198     es_putc (get_ownertrust_info (pk), es_stdout);
1199   es_putc (':', es_stdout);
1200
1201   es_putc (':', es_stdout);
1202   es_putc (':', es_stdout);
1203   print_capabilities (pk, keyblock);
1204   es_putc (':', es_stdout);             /* End of field 13. */
1205   es_putc (':', es_stdout);             /* End of field 14. */
1206   if (secret)
1207     {
1208       if (stubkey)
1209         es_putc ('#', es_stdout);
1210       else if (serialno)
1211         es_fputs (serialno, es_stdout);
1212     }
1213   es_putc (':', es_stdout);             /* End of field 15. */
1214   es_putc (':', es_stdout);             /* End of field 16. */
1215   if (pk->pubkey_algo == PUBKEY_ALGO_ECDSA
1216       || pk->pubkey_algo == PUBKEY_ALGO_EDDSA
1217       || pk->pubkey_algo == PUBKEY_ALGO_ECDH)
1218     {
1219       char *curve = openpgp_oid_to_str (pk->pkey[0]);
1220       const char *name = openpgp_oid_to_curve (curve);
1221       if (!*name || *name == '?')
1222         name = curve;
1223       es_fputs (name, es_stdout);
1224       xfree (curve);
1225     }
1226   es_putc (':', es_stdout);             /* End of field 17. */
1227   es_putc ('\n', es_stdout);
1228
1229   print_revokers (pk);
1230   if (fpr)
1231     print_fingerprint (pk, 0);
1232   if (opt.with_key_data || opt.with_keygrip)
1233     {
1234       if (hexgrip)
1235         es_fprintf (es_stdout, "grp:::::::::%s:\n", hexgrip);
1236       if (opt.with_key_data)
1237         print_key_data (pk);
1238     }
1239
1240   for (kbctx = NULL; (node = walk_kbnode (keyblock, &kbctx, 0));)
1241     {
1242       if (node->pkt->pkttype == PKT_USER_ID && !opt.fast_list_mode)
1243         {
1244           char *str;
1245           PKT_user_id *uid = node->pkt->pkt.user_id;
1246
1247           if (attrib_fp && node->pkt->pkt.user_id->attrib_data != NULL)
1248             dump_attribs (node->pkt->pkt.user_id, pk);
1249           /*
1250            * Fixme: We need a valid flag here too
1251            */
1252           str = uid->attrib_data ? "uat" : "uid";
1253           if (uid->is_revoked)
1254             es_fprintf (es_stdout, "%s:r::::", str);
1255           else if (uid->is_expired)
1256             es_fprintf (es_stdout, "%s:e::::", str);
1257           else if (opt.no_expensive_trust_checks)
1258             es_fprintf (es_stdout, "%s:::::", str);
1259           else
1260             {
1261               int uid_validity;
1262
1263               if (pk && !ulti_hack)
1264                 uid_validity = get_validity_info (pk, uid);
1265               else
1266                 uid_validity = 'u';
1267               es_fprintf (es_stdout, "%s:%c::::", str, uid_validity);
1268             }
1269
1270           es_fprintf (es_stdout, "%s:", colon_strtime (uid->created));
1271           es_fprintf (es_stdout, "%s:", colon_strtime (uid->expiredate));
1272
1273           namehash_from_uid (uid);
1274
1275           for (i = 0; i < 20; i++)
1276             es_fprintf (es_stdout, "%02X", uid->namehash[i]);
1277
1278           es_fprintf (es_stdout, "::");
1279
1280           if (uid->attrib_data)
1281             es_fprintf (es_stdout, "%u %lu", uid->numattribs, uid->attrib_len);
1282           else
1283             es_write_sanitized (es_stdout, uid->name, uid->len, ":", NULL);
1284           es_putc (':', es_stdout);
1285           es_putc ('\n', es_stdout);
1286         }
1287       else if (node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
1288         {
1289           u32 keyid2[2];
1290           PKT_public_key *pk2;
1291
1292           pk2 = node->pkt->pkt.public_key;
1293           xfree (hexgrip); hexgrip = NULL;
1294           xfree (serialno); serialno = NULL;
1295           if (secret || opt.with_keygrip || opt.with_key_data)
1296             {
1297               rc = hexkeygrip_from_pk (pk2, &hexgrip);
1298               if (rc)
1299                 log_error ("error computing a keygrip: %s\n",
1300                            gpg_strerror (rc));
1301             }
1302           stubkey = 0;
1303           if (secret && agent_get_keyinfo (NULL, hexgrip, &serialno))
1304             stubkey = 1;  /* Key not found.  */
1305
1306           keyid_from_pk (pk2, keyid2);
1307           es_fputs (secret? "ssb:":"sub:", es_stdout);
1308           if (!pk2->flags.valid)
1309             es_putc ('i', es_stdout);
1310           else if (pk2->flags.revoked)
1311             es_putc ('r', es_stdout);
1312           else if (pk2->has_expired)
1313             es_putc ('e', es_stdout);
1314           else if (opt.fast_list_mode || opt.no_expensive_trust_checks)
1315             ;
1316           else
1317             {
1318               /* TRUSTLETTER should always be defined here. */
1319               if (trustletter)
1320                 es_fprintf (es_stdout, "%c", trustletter);
1321             }
1322           es_fprintf (es_stdout, ":%u:%d:%08lX%08lX:%s:%s:::::",
1323                   nbits_from_pk (pk2),
1324                   pk2->pubkey_algo,
1325                   (ulong) keyid2[0], (ulong) keyid2[1],
1326                   colon_datestr_from_pk (pk2), colon_strtime (pk2->expiredate)
1327                   /* fixme: add LID and ownertrust here */
1328             );
1329           print_capabilities (pk2, NULL);
1330           es_putc (':', es_stdout);     /* End of field 13. */
1331           es_putc (':', es_stdout);     /* End of field 14. */
1332           if (secret)
1333             {
1334               if (stubkey)
1335                 es_putc ('#', es_stdout);
1336               else if (serialno)
1337                 es_fputs (serialno, es_stdout);
1338             }
1339           es_putc (':', es_stdout);     /* End of field 15. */
1340           es_putc (':', es_stdout);     /* End of field 16. */
1341           if (pk->pubkey_algo == PUBKEY_ALGO_ECDSA
1342               || pk->pubkey_algo == PUBKEY_ALGO_EDDSA
1343               || pk->pubkey_algo == PUBKEY_ALGO_ECDH)
1344             {
1345               char *curve = openpgp_oid_to_str (pk->pkey[0]);
1346               const char *name = openpgp_oid_to_curve (curve);
1347               if (!*name || *name == '?')
1348                 name = curve;
1349               es_fputs (name, es_stdout);
1350               xfree (curve);
1351             }
1352           es_putc (':', es_stdout);     /* End of field 17. */
1353           es_putc ('\n', es_stdout);
1354           if (fpr > 1)
1355             print_fingerprint (pk2, 0);
1356           if (opt.with_key_data || opt.with_keygrip)
1357             {
1358               if (hexgrip)
1359                 es_fprintf (es_stdout, "grp:::::::::%s:\n", hexgrip);
1360               if (opt.with_key_data)
1361                 print_key_data (pk2);
1362             }
1363         }
1364       else if (opt.list_sigs && node->pkt->pkttype == PKT_SIGNATURE)
1365         {
1366           PKT_signature *sig = node->pkt->pkt.signature;
1367           int sigrc, fprokay = 0;
1368           char *sigstr;
1369           size_t fplen;
1370           byte fparray[MAX_FINGERPRINT_LEN];
1371
1372           if (sig->sig_class == 0x20 || sig->sig_class == 0x28
1373               || sig->sig_class == 0x30)
1374             sigstr = "rev";
1375           else if ((sig->sig_class & ~3) == 0x10)
1376             sigstr = "sig";
1377           else if (sig->sig_class == 0x18)
1378             sigstr = "sig";
1379           else if (sig->sig_class == 0x1F)
1380             sigstr = "sig";
1381           else
1382             {
1383               es_fprintf (es_stdout, "sig::::::::::%02x%c:\n",
1384                       sig->sig_class, sig->flags.exportable ? 'x' : 'l');
1385               continue;
1386             }
1387
1388           if (opt.check_sigs)
1389             {
1390               PKT_public_key *signer_pk = NULL;
1391
1392               fflush (stdout);
1393               if (opt.no_sig_cache)
1394                 signer_pk = xmalloc_clear (sizeof (PKT_public_key));
1395
1396               rc = check_key_signature2 (keyblock, node, NULL, signer_pk,
1397                                          NULL, NULL, NULL);
1398               switch (gpg_err_code (rc))
1399                 {
1400                 case 0:
1401                   sigrc = '!';
1402                   break;
1403                 case GPG_ERR_BAD_SIGNATURE:
1404                   sigrc = '-';
1405                   break;
1406                 case GPG_ERR_NO_PUBKEY:
1407                 case GPG_ERR_UNUSABLE_PUBKEY:
1408                   sigrc = '?';
1409                   break;
1410                 default:
1411                   sigrc = '%';
1412                   break;
1413                 }
1414
1415               if (opt.no_sig_cache)
1416                 {
1417                   if (!rc)
1418                     {
1419                       fingerprint_from_pk (signer_pk, fparray, &fplen);
1420                       fprokay = 1;
1421                     }
1422                   free_public_key (signer_pk);
1423                 }
1424             }
1425           else
1426             {
1427               rc = 0;
1428               sigrc = ' ';
1429             }
1430           es_fputs (sigstr, es_stdout);
1431           es_putc (':', es_stdout);
1432           if (sigrc != ' ')
1433             es_putc (sigrc, es_stdout);
1434           es_fprintf (es_stdout, "::%d:%08lX%08lX:%s:%s:", sig->pubkey_algo,
1435                   (ulong) sig->keyid[0], (ulong) sig->keyid[1],
1436                   colon_datestr_from_sig (sig),
1437                   colon_expirestr_from_sig (sig));
1438
1439           if (sig->trust_depth || sig->trust_value)
1440             es_fprintf (es_stdout, "%d %d", sig->trust_depth, sig->trust_value);
1441           es_fprintf (es_stdout, ":");
1442
1443           if (sig->trust_regexp)
1444             es_write_sanitized (es_stdout, sig->trust_regexp,
1445                                 strlen (sig->trust_regexp), ":", NULL);
1446           es_fprintf (es_stdout, ":");
1447
1448           if (sigrc == '%')
1449             es_fprintf (es_stdout, "[%s] ", g10_errstr (rc));
1450           else if (sigrc == '?')
1451             ;
1452           else if (!opt.fast_list_mode)
1453             {
1454               size_t n;
1455               p = get_user_id (sig->keyid, &n);
1456               es_write_sanitized (es_stdout, p, n, ":", NULL);
1457               xfree (p);
1458             }
1459           es_fprintf (es_stdout, ":%02x%c::", sig->sig_class,
1460                   sig->flags.exportable ? 'x' : 'l');
1461
1462           if (opt.no_sig_cache && opt.check_sigs && fprokay)
1463             {
1464               for (i = 0; i < fplen; i++)
1465                 es_fprintf (es_stdout, "%02X", fparray[i]);
1466             }
1467
1468           es_fprintf (es_stdout, ":::%d:\n", sig->digest_algo);
1469
1470           if (opt.show_subpackets)
1471             print_subpackets_colon (sig);
1472
1473           /* fixme: check or list other sigs here */
1474         }
1475     }
1476
1477   xfree (hexgrip);
1478   xfree (serialno);
1479 }
1480
1481 /*
1482  * Reorder the keyblock so that the primary user ID (and not attribute
1483  * packet) comes first.  Fixme: Replace this by a generic sort
1484  * function.  */
1485 static void
1486 do_reorder_keyblock (KBNODE keyblock, int attr)
1487 {
1488   KBNODE primary = NULL, primary0 = NULL, primary2 = NULL;
1489   KBNODE last, node;
1490
1491   for (node = keyblock; node; primary0 = node, node = node->next)
1492     {
1493       if (node->pkt->pkttype == PKT_USER_ID &&
1494           ((attr && node->pkt->pkt.user_id->attrib_data) ||
1495            (!attr && !node->pkt->pkt.user_id->attrib_data)) &&
1496           node->pkt->pkt.user_id->is_primary)
1497         {
1498           primary = primary2 = node;
1499           for (node = node->next; node; primary2 = node, node = node->next)
1500             {
1501               if (node->pkt->pkttype == PKT_USER_ID
1502                   || node->pkt->pkttype == PKT_PUBLIC_SUBKEY
1503                   || node->pkt->pkttype == PKT_SECRET_SUBKEY)
1504                 {
1505                   break;
1506                 }
1507             }
1508           break;
1509         }
1510     }
1511   if (!primary)
1512     return; /* No primary key flag found (should not happen).  */
1513
1514   for (last = NULL, node = keyblock; node; last = node, node = node->next)
1515     {
1516       if (node->pkt->pkttype == PKT_USER_ID)
1517         break;
1518     }
1519   assert (node);
1520   assert (last);         /* The user ID is never the first packet.  */
1521   assert (primary0);     /* Ditto (this is the node before primary).  */
1522   if (node == primary)
1523     return; /* Already the first one.  */
1524
1525   last->next = primary;
1526   primary0->next = primary2->next;
1527   primary2->next = node;
1528 }
1529
1530 void
1531 reorder_keyblock (KBNODE keyblock)
1532 {
1533   do_reorder_keyblock (keyblock, 1);
1534   do_reorder_keyblock (keyblock, 0);
1535 }
1536
1537 void
1538 list_keyblock (KBNODE keyblock, int secret, int fpr, void *opaque)
1539 {
1540   reorder_keyblock (keyblock);
1541   if (opt.with_colons)
1542     list_keyblock_colon (keyblock, secret, fpr);
1543   else
1544     list_keyblock_print (keyblock, secret, fpr, opaque);
1545 }
1546
1547 /*
1548  * Function to print the finperprint.
1549  * mode 0: as used in key listings, opt.with_colons is honored
1550  *      1: print using log_info ()
1551  *      2: direct use of tty
1552  *      3: direct use of tty but only primary key.
1553  *
1554  * Modes 1 and 2 will try and print both subkey and primary key
1555  * fingerprints.  A MODE with bit 7 set is used internally.
1556  */
1557 void
1558 print_fingerprint (PKT_public_key *pk, int mode)
1559 {
1560   byte array[MAX_FINGERPRINT_LEN], *p;
1561   size_t i, n;
1562   estream_t fp;
1563   const char *text;
1564   int primary = 0;
1565
1566   if (pk->main_keyid[0] == pk->keyid[0]
1567       && pk->main_keyid[1] == pk->keyid[1])
1568     primary = 1;
1569
1570   /* Just to be safe */
1571   if ((mode & 0x80) && !primary)
1572     {
1573       log_error ("primary key is not really primary!\n");
1574       return;
1575     }
1576
1577   mode &= ~0x80;
1578
1579   if (!primary && (mode == 1 || mode == 2))
1580     {
1581       PKT_public_key *primary_pk = xmalloc_clear (sizeof (*primary_pk));
1582       get_pubkey (primary_pk, pk->main_keyid);
1583       print_fingerprint (primary_pk, mode | 0x80);
1584       free_public_key (primary_pk);
1585     }
1586
1587   if (mode == 1)
1588     {
1589       fp = log_get_stream ();
1590       if (primary)
1591         text = _("Primary key fingerprint:");
1592       else
1593         text = _("     Subkey fingerprint:");
1594     }
1595   else if (mode == 2)
1596     {
1597       fp = NULL; /* Use tty.  */
1598       if (primary)
1599         /* TRANSLATORS: this should fit into 24 bytes to that the
1600          * fingerprint data is properly aligned with the user ID */
1601         text = _(" Primary key fingerprint:");
1602       else
1603         text = _("      Subkey fingerprint:");
1604     }
1605   else if (mode == 3)
1606     {
1607       fp = NULL; /* Use tty.  */
1608       text = _("      Key fingerprint =");
1609     }
1610   else
1611     {
1612       fp = es_stdout;
1613       text = _("      Key fingerprint =");
1614     }
1615
1616   fingerprint_from_pk (pk, array, &n);
1617   p = array;
1618   if (opt.with_colons && !mode)
1619     {
1620       es_fprintf (fp, "fpr:::::::::");
1621       for (i = 0; i < n; i++, p++)
1622         es_fprintf (fp, "%02X", *p);
1623       es_putc (':', fp);
1624     }
1625   else
1626     {
1627       tty_fprintf (fp, "%s", text);
1628       if (n == 20)
1629         {
1630           for (i = 0; i < n; i++, i++, p += 2)
1631             tty_fprintf (fp, "%s %02X%02X", i==10? " ":"", *p, p[1]);
1632         }
1633       else
1634         {
1635           for (i = 0; i < n; i++, p++)
1636             tty_fprintf (fp, "%s %02X", (i && !(i % 8))? " ":"", *p);
1637         }
1638     }
1639   tty_fprintf (fp, "\n");
1640 }
1641
1642 /* Print the serial number of an OpenPGP card if available.  */
1643 static void
1644 print_card_serialno (const char *serialno)
1645 {
1646   if (!serialno)
1647     return;
1648   if (opt.with_colons)
1649     return; /* Handled elsewhere. */
1650
1651   es_fputs (_("      Card serial no. ="), es_stdout);
1652   es_putc (' ', es_stdout);
1653   if (strlen (serialno) == 32 && !strncmp (serialno, "D27600012401", 12))
1654     {
1655       /* This is an OpenPGP card.  Print the relevant part.  */
1656       /* Example: D2760001240101010001000003470000 */
1657       /*                          xxxxyyyyyyyy     */
1658       es_fprintf (es_stdout, "%.*s %.*s", 4, serialno+16, 8, serialno+20);
1659     }
1660  else
1661    es_fputs (serialno, es_stdout);
1662   es_putc ('\n', es_stdout);
1663 }
1664
1665
1666
1667 void
1668 set_attrib_fd (int fd)
1669 {
1670   static int last_fd = -1;
1671
1672   if (fd != -1 && last_fd == fd)
1673     return;
1674
1675   /* Fixme: Do we need to check for the log stream here?  */
1676   if (attrib_fp && attrib_fp != log_get_stream ())
1677     es_fclose (attrib_fp);
1678   attrib_fp = NULL;
1679   if (fd == -1)
1680     return;
1681
1682 #ifdef HAVE_DOSISH_SYSTEM
1683   setmode (fd, O_BINARY);
1684 #endif
1685   if (fd == 1)
1686     attrib_fp = es_stdout;
1687   else if (fd == 2)
1688     attrib_fp = es_stderr;
1689   else
1690     attrib_fp = es_fdopen (fd, "wb");
1691   if (!attrib_fp)
1692     {
1693       log_fatal ("can't open fd %d for attribute output: %s\n",
1694                  fd, strerror (errno));
1695     }
1696
1697   last_fd = fd;
1698 }