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 * Copyright (C) 2013, 2014 Werner Koch
6 * This file is part of GnuPG.
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.
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.
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, see <https://www.gnu.org/licenses/>.
27 #ifdef HAVE_DOSISH_SYSTEM
28 # include <fcntl.h> /* for setmode() */
43 #include "call-agent.h"
44 #include "mbox-util.h"
49 static void list_all (ctrl_t, int, int);
50 static void list_one (ctrl_t ctrl,
51 strlist_t names, int secret, int mark_secret);
52 static void locate_one (ctrl_t ctrl, strlist_t names);
53 static void print_card_serialno (const char *serialno);
55 struct keylist_context
57 int check_sigs; /* If set signatures shall be verified. */
58 int good_sigs; /* Counter used if CHECK_SIGS is set. */
59 int inv_sigs; /* Counter used if CHECK_SIGS is set. */
60 int no_key; /* Counter used if CHECK_SIGS is set. */
61 int oth_err; /* Counter used if CHECK_SIGS is set. */
62 int no_validity; /* Do not show validity. */
66 static void list_keyblock (ctrl_t ctrl,
67 kbnode_t keyblock, int secret, int has_secret,
68 int fpr, struct keylist_context *listctx);
71 /* The stream used to write attribute packets to. */
72 static estream_t attrib_fp;
75 /* Release resources from a keylist context. */
77 keylist_context_release (struct keylist_context *listctx)
79 (void)listctx; /* Nothing to release. */
83 /* List the keys. If list is NULL, all available keys are listed.
84 With LOCATE_MODE set the locate algorithm is used to find a
87 public_key_list (ctrl_t ctrl, strlist_t list, int locate_mode)
89 #ifndef NO_TRUST_MODELS
92 byte trust_model, marginals, completes, cert_depth, min_cert_level;
93 ulong created, nextcheck;
95 read_trust_options (&trust_model, &created, &nextcheck,
96 &marginals, &completes, &cert_depth, &min_cert_level);
98 es_fprintf (es_stdout, "tru:");
100 if (nextcheck && nextcheck <= make_timestamp ())
101 es_fprintf (es_stdout, "o");
102 if (trust_model != opt.trust_model)
103 es_fprintf (es_stdout, "t");
104 if (opt.trust_model == TM_PGP || opt.trust_model == TM_CLASSIC
105 || opt.trust_model == TM_TOFU_PGP)
107 if (marginals != opt.marginals_needed)
108 es_fprintf (es_stdout, "m");
109 if (completes != opt.completes_needed)
110 es_fprintf (es_stdout, "c");
111 if (cert_depth != opt.max_cert_depth)
112 es_fprintf (es_stdout, "d");
113 if (min_cert_level != opt.min_cert_level)
114 es_fprintf (es_stdout, "l");
117 es_fprintf (es_stdout, ":%d:%lu:%lu", trust_model, created, nextcheck);
119 /* Only show marginals, completes, and cert_depth in the classic
120 or PGP trust models since they are not meaningful
123 if (trust_model == TM_PGP || trust_model == TM_CLASSIC)
124 es_fprintf (es_stdout, ":%d:%d:%d", marginals, completes, cert_depth);
125 es_fprintf (es_stdout, "\n");
127 #endif /*!NO_TRUST_MODELS*/
129 /* We need to do the stale check right here because it might need to
130 update the keyring while we already have the keyring open. This
131 is very bad for W32 because of a sharing violation. For real OSes
132 it might lead to false results if we are later listing a keyring
133 which is associated with the inode of a deleted file. */
134 check_trustdb_stale (ctrl);
137 tofu_begin_batch_update (ctrl);
141 locate_one (ctrl, list);
143 list_all (ctrl, 0, opt.with_secret);
145 list_one (ctrl, list, 0, opt.with_secret);
148 tofu_end_batch_update (ctrl);
154 secret_key_list (ctrl_t ctrl, strlist_t list)
158 check_trustdb_stale (ctrl);
161 list_all (ctrl, 1, 0);
162 else /* List by user id */
163 list_one (ctrl, list, 1, 0);
167 format_seckey_info (PKT_public_key *pk)
171 char pkstrbuf[PUBKEY_STRING_SIZE];
174 keyid_from_pk (pk, keyid);
175 p = get_user_id_native (keyid);
177 info = xtryasprintf ("sec %s/%s %s %s",
178 pubkey_string (pk, pkstrbuf, sizeof pkstrbuf),
179 keystr (keyid), datestr_from_pk (pk), p);
187 print_seckey_info (PKT_public_key *pk)
189 char *p = format_seckey_info (pk);
190 tty_printf ("\n%s\n", p);
194 /* Print information about the public key. With FP passed as NULL,
195 the tty output interface is used, otherwise output is directted to
198 print_pubkey_info (estream_t fp, PKT_public_key *pk)
202 char pkstrbuf[PUBKEY_STRING_SIZE];
204 keyid_from_pk (pk, keyid);
206 /* If the pk was chosen by a particular user ID, that is the one to
209 p = utf8_to_native (pk->user_id->name, pk->user_id->len, 0);
211 p = get_user_id_native (keyid);
215 tty_fprintf (fp, "%s %s/%s %s %s\n",
216 pk->flags.primary? "pub":"sub",
217 pubkey_string (pk, pkstrbuf, sizeof pkstrbuf),
218 keystr (keyid), datestr_from_pk (pk), p);
223 /* Print basic information of a secret key including the card serial
224 number information. */
225 #ifdef ENABLE_CARD_SUPPORT
227 print_card_key_info (estream_t fp, kbnode_t keyblock)
233 char pkstrbuf[PUBKEY_STRING_SIZE];
236 for (node = keyblock; node; node = node->next)
238 if (node->pkt->pkttype == PKT_PUBLIC_KEY
239 || node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
242 PKT_public_key *pk = node->pkt->pkt.public_key;
245 rc = hexkeygrip_from_pk (pk, &hexgrip);
248 log_error ("error computing a keygrip: %s\n", gpg_strerror (rc));
251 else if (!agent_get_keyinfo (NULL, hexgrip, &serialno, NULL))
252 s2k_char = serialno? '>':' ';
254 s2k_char = '#'; /* Key not found. */
256 tty_fprintf (fp, "%s%c %s/%s %n",
257 node->pkt->pkttype == PKT_PUBLIC_KEY ? "sec" : "ssb",
259 pubkey_string (pk, pkstrbuf, sizeof pkstrbuf),
262 tty_fprintf (fp, _("created: %s"), datestr_from_pk (pk));
263 tty_fprintf (fp, " ");
264 tty_fprintf (fp, _("expires: %s"), expirestr_from_pk (pk));
267 tty_fprintf (fp, "\n%*s%s", indent, "", _("card-no: "));
268 if (strlen (serialno) == 32
269 && !strncmp (serialno, "D27600012401", 12))
271 /* This is an OpenPGP card. Print the relevant part. */
272 /* Example: D2760001240101010001000003470000 */
274 tty_fprintf (fp, "%.*s %.*s", 4, serialno+16, 8, serialno+20);
277 tty_fprintf (fp, "%s", serialno);
279 tty_fprintf (fp, "\n");
285 #endif /*ENABLE_CARD_SUPPORT*/
288 /* Flags = 0x01 hashed 0x02 critical. */
290 status_one_subpacket (sigsubpkttype_t type, size_t len, int flags,
295 /* Don't print these. */
299 snprintf (status, sizeof status,
300 "%d %u %u ", type, flags, (unsigned int) len);
302 write_status_text_and_buffer (STATUS_SIG_SUBPACKET, status, buf, len, 0);
306 /* Print a policy URL. Allowed values for MODE are:
307 * -1 - print to the TTY
308 * 0 - print to stdout.
309 * 1 - use log_info and emit status messages.
310 * 2 - emit only status messages.
313 show_policy_url (PKT_signature * sig, int indent, int mode)
318 estream_t fp = mode < 0? NULL : mode ? log_get_stream () : es_stdout;
321 enum_sig_subpkt (sig->hashed, SIGSUBPKT_POLICY, &len, &seq, &crit)))
327 tty_fprintf (fp, "%*s", indent, "");
330 str = _("Critical signature policy: ");
332 str = _("Signature policy: ");
334 log_info ("%s", str);
336 tty_fprintf (fp, "%s", str);
337 tty_print_utf8_string2 (fp, p, len, 0);
338 tty_fprintf (fp, "\n");
342 write_status_buffer (STATUS_POLICY_URL, p, len, 0);
347 /* Print a keyserver URL. Allowed values for MODE are:
348 * -1 - print to the TTY
349 * 0 - print to stdout.
350 * 1 - use log_info and emit status messages.
351 * 2 - emit only status messages.
354 show_keyserver_url (PKT_signature * sig, int indent, int mode)
359 estream_t fp = mode < 0? NULL : mode ? log_get_stream () : es_stdout;
362 enum_sig_subpkt (sig->hashed, SIGSUBPKT_PREF_KS, &len, &seq,
369 tty_fprintf (fp, "%*s", indent, "");
372 str = _("Critical preferred keyserver: ");
374 str = _("Preferred keyserver: ");
376 log_info ("%s", str);
378 tty_fprintf (es_stdout, "%s", str);
379 tty_print_utf8_string2 (fp, p, len, 0);
380 tty_fprintf (fp, "\n");
384 status_one_subpacket (SIGSUBPKT_PREF_KS, len,
385 (crit ? 0x02 : 0) | 0x01, p);
390 /* Print notation data. Allowed values for MODE are:
391 * -1 - print to the TTY
392 * 0 - print to stdout.
393 * 1 - use log_info and emit status messages.
394 * 2 - emit only status messages.
396 * Defined bits in WHICH:
397 * 1 - standard notations
401 show_notation (PKT_signature * sig, int indent, int mode, int which)
403 estream_t fp = mode < 0? NULL : mode ? log_get_stream () : es_stdout;
404 notation_t nd, notations;
409 notations = sig_to_notation (sig);
411 /* There may be multiple notations in the same sig. */
412 for (nd = notations; nd; nd = nd->next)
416 int has_at = !!strchr (nd->name, '@');
418 if ((which & 1 && !has_at) || (which & 2 && has_at))
422 tty_fprintf (fp, "%*s", indent, "");
424 if (nd->flags.critical)
425 str = _("Critical signature notation: ");
427 str = _("Signature notation: ");
429 log_info ("%s", str);
431 tty_fprintf (es_stdout, "%s", str);
432 /* This is all UTF8 */
433 tty_print_utf8_string2 (fp, nd->name, strlen (nd->name), 0);
434 tty_fprintf (fp, "=");
435 tty_print_utf8_string2 (fp, nd->value, strlen (nd->value), 0);
436 /* (We need to use log_printf so that the next call to a
437 log function does not insert an extra LF.) */
441 tty_fprintf (fp, "\n");
447 write_status_buffer (STATUS_NOTATION_NAME,
448 nd->name, strlen (nd->name), 0);
449 if (nd->flags.critical || nd->flags.human)
450 write_status_text (STATUS_NOTATION_FLAGS,
451 nd->flags.critical && nd->flags.human? "1 1" :
452 nd->flags.critical? "1 0" : "0 1");
453 write_status_buffer (STATUS_NOTATION_DATA,
454 nd->value, strlen (nd->value), 50);
458 free_notation (notations);
463 print_signature_stats (struct keylist_context *s)
466 return; /* Signature checking was not requested. */
469 log_info (ngettext("%d good signature\n",
470 "%d good signatures\n", s->good_sigs), s->good_sigs);
473 log_info (ngettext("%d bad signature\n",
474 "%d bad signatures\n", s->inv_sigs), s->inv_sigs);
477 log_info (ngettext("%d signature not checked due to a missing key\n",
478 "%d signatures not checked due to missing keys\n",
479 s->no_key), s->no_key);
482 log_info (ngettext("%d signature not checked due to an error\n",
483 "%d signatures not checked due to errors\n",
484 s->oth_err), s->oth_err);
488 /* List all keys. If SECRET is true only secret keys are listed. If
489 MARK_SECRET is true secret keys are indicated in a public key
492 list_all (ctrl_t ctrl, int secret, int mark_secret)
495 KBNODE keyblock = NULL;
498 const char *lastresname, *resname;
499 struct keylist_context listctx;
501 memset (&listctx, 0, sizeof (listctx));
503 listctx.check_sigs = 1;
507 rc = gpg_error_from_syserror ();
509 rc = keydb_search_first (hd);
512 if (gpg_err_code (rc) != GPG_ERR_NOT_FOUND)
513 log_error ("keydb_search_first failed: %s\n", gpg_strerror (rc));
520 rc = keydb_get_keyblock (hd, &keyblock);
523 if (gpg_err_code (rc) == GPG_ERR_LEGACY_KEY)
524 continue; /* Skip legacy keys. */
525 log_error ("keydb_get_keyblock failed: %s\n", gpg_strerror (rc));
529 if (secret || mark_secret)
530 any_secret = !agent_probe_any_secret_key (NULL, keyblock);
534 if (secret && !any_secret)
535 ; /* Secret key listing requested but this isn't one. */
538 if (!opt.with_colons)
540 resname = keydb_get_resource_name (hd);
541 if (lastresname != resname)
545 es_fprintf (es_stdout, "%s\n", resname);
546 for (i = strlen (resname); i; i--)
547 es_putc ('-', es_stdout);
548 es_putc ('\n', es_stdout);
549 lastresname = resname;
552 merge_keys_and_selfsig (keyblock);
553 list_keyblock (ctrl, keyblock, secret, any_secret, opt.fingerprint,
556 release_kbnode (keyblock);
559 while (!(rc = keydb_search_next (hd)));
560 es_fflush (es_stdout);
561 if (rc && gpg_err_code (rc) != GPG_ERR_NOT_FOUND)
562 log_error ("keydb_search_next failed: %s\n", gpg_strerror (rc));
563 if (keydb_get_skipped_counter (hd))
564 log_info (ngettext("Warning: %lu key skipped due to its large size\n",
565 "Warning: %lu keys skipped due to their large sizes\n",
566 keydb_get_skipped_counter (hd)),
567 keydb_get_skipped_counter (hd));
569 if (opt.check_sigs && !opt.with_colons)
570 print_signature_stats (&listctx);
573 keylist_context_release (&listctx);
574 release_kbnode (keyblock);
580 list_one (ctrl_t ctrl, strlist_t names, int secret, int mark_secret)
583 KBNODE keyblock = NULL;
586 const char *keyring_str = _("Keyring");
588 struct keylist_context listctx;
590 memset (&listctx, 0, sizeof (listctx));
591 if (!secret && opt.check_sigs)
592 listctx.check_sigs = 1;
594 /* fixme: using the bynames function has the disadvantage that we
595 * don't know wether one of the names given was not found. OTOH,
596 * this function has the advantage to list the names in the
597 * sequence as defined by the keyDB and does not duplicate
598 * outputs. A solution could be do test whether all given have
599 * been listed (this needs a way to use the keyDB search
600 * functions) or to have the search function return indicators for
601 * found names. Yet another way is to use the keydb search
602 * facilities directly. */
603 rc = getkey_bynames (&ctx, NULL, names, secret, &keyblock);
606 log_error ("error reading key: %s\n", gpg_strerror (rc));
613 if ((opt.list_options & LIST_SHOW_KEYRING) && !opt.with_colons)
615 resname = keydb_get_resource_name (get_ctx_handle (ctx));
616 es_fprintf (es_stdout, "%s: %s\n", keyring_str, resname);
617 for (i = strlen (resname) + strlen (keyring_str) + 2; i; i--)
618 es_putc ('-', es_stdout);
619 es_putc ('\n', es_stdout);
622 keyblock, secret, mark_secret, opt.fingerprint, &listctx);
623 release_kbnode (keyblock);
625 while (!getkey_next (ctx, NULL, &keyblock));
628 if (opt.check_sigs && !opt.with_colons)
629 print_signature_stats (&listctx);
631 keylist_context_release (&listctx);
636 locate_one (ctrl_t ctrl, strlist_t names)
640 GETKEY_CTX ctx = NULL;
641 KBNODE keyblock = NULL;
642 struct keylist_context listctx;
644 memset (&listctx, 0, sizeof (listctx));
646 listctx.check_sigs = 1;
648 for (sl = names; sl; sl = sl->next)
650 rc = get_best_pubkey_byname (ctrl, &ctx, NULL, sl->d, &keyblock, 1, 0);
653 if (gpg_err_code (rc) != GPG_ERR_NO_PUBKEY)
654 log_error ("error reading key: %s\n", gpg_strerror (rc));
655 else if (opt.verbose)
656 log_info (_("key \"%s\" not found: %s\n"),
657 sl->d, gpg_strerror (rc));
663 list_keyblock (ctrl, keyblock, 0, 0, opt.fingerprint, &listctx);
664 release_kbnode (keyblock);
666 while (ctx && !getkey_next (ctx, NULL, &keyblock));
672 if (opt.check_sigs && !opt.with_colons)
673 print_signature_stats (&listctx);
675 keylist_context_release (&listctx);
680 print_key_data (PKT_public_key * pk)
682 int n = pk ? pubkey_get_npkey (pk->pubkey_algo) : 0;
685 for (i = 0; i < n; i++)
687 es_fprintf (es_stdout, "pkd:%d:%u:", i, mpi_get_nbits (pk->pkey[i]));
688 mpi_print (es_stdout, pk->pkey[i], 1);
689 es_putc (':', es_stdout);
690 es_putc ('\n', es_stdout);
695 print_capabilities (PKT_public_key *pk, KBNODE keyblock)
697 unsigned int use = pk->pubkey_usage;
700 if (use & PUBKEY_USAGE_ENC)
701 es_putc ('e', es_stdout);
703 if (use & PUBKEY_USAGE_SIG)
705 es_putc ('s', es_stdout);
706 if (pk->flags.primary)
708 es_putc ('c', es_stdout);
709 /* The PUBKEY_USAGE_CERT flag was introduced later and we
710 used to always print 'c' for a primary key. To avoid any
711 regression here we better track whether we printed 'c'
717 if ((use & PUBKEY_USAGE_CERT) && !c_printed)
718 es_putc ('c', es_stdout);
720 if ((use & PUBKEY_USAGE_AUTH))
721 es_putc ('a', es_stdout);
723 if ((use & PUBKEY_USAGE_UNKNOWN))
724 es_putc ('?', es_stdout);
728 /* Figure out the usable capabilities. */
730 int enc = 0, sign = 0, cert = 0, auth = 0, disabled = 0;
732 for (k = keyblock; k; k = k->next)
734 if (k->pkt->pkttype == PKT_PUBLIC_KEY
735 || k->pkt->pkttype == PKT_PUBLIC_SUBKEY)
737 pk = k->pkt->pkt.public_key;
739 if (pk->flags.primary)
740 disabled = pk_is_disabled (pk);
742 if (pk->flags.valid && !pk->flags.revoked && !pk->has_expired)
744 if (pk->pubkey_usage & PUBKEY_USAGE_ENC)
746 if (pk->pubkey_usage & PUBKEY_USAGE_SIG)
749 if (pk->flags.primary)
752 if (pk->pubkey_usage & PUBKEY_USAGE_CERT)
754 if ((pk->pubkey_usage & PUBKEY_USAGE_AUTH))
760 es_putc ('E', es_stdout);
762 es_putc ('S', es_stdout);
764 es_putc ('C', es_stdout);
766 es_putc ('A', es_stdout);
768 es_putc ('D', es_stdout);
771 es_putc (':', es_stdout);
775 /* FLAGS: 0x01 hashed
778 print_one_subpacket (sigsubpkttype_t type, size_t len, int flags,
783 es_fprintf (es_stdout, "spk:%d:%u:%u:", type, flags, (unsigned int) len);
785 for (i = 0; i < len; i++)
787 /* printable ascii other than : and % */
788 if (buf[i] >= 32 && buf[i] <= 126 && buf[i] != ':' && buf[i] != '%')
789 es_fprintf (es_stdout, "%c", buf[i]);
791 es_fprintf (es_stdout, "%%%02X", buf[i]);
794 es_fprintf (es_stdout, "\n");
799 print_subpackets_colon (PKT_signature * sig)
803 log_assert (opt.show_subpackets);
805 for (i = opt.show_subpackets; *i; i++)
813 while ((p = enum_sig_subpkt (sig->hashed, *i, &len, &seq, &crit)))
814 print_one_subpacket (*i, len, 0x01 | (crit ? 0x02 : 0), p);
818 while ((p = enum_sig_subpkt (sig->unhashed, *i, &len, &seq, &crit)))
819 print_one_subpacket (*i, len, 0x00 | (crit ? 0x02 : 0), p);
825 dump_attribs (const PKT_user_id *uid, PKT_public_key *pk)
832 for (i = 0; i < uid->numattribs; i++)
834 if (is_status_enabled ())
836 byte array[MAX_FINGERPRINT_LEN], *p;
837 char buf[(MAX_FINGERPRINT_LEN * 2) + 90];
842 fingerprint_from_pk (pk, array, &n);
845 for (j = 0; j < n; j++, p++)
846 sprintf (buf + 2 * j, "%02X", *p);
848 sprintf (buf + strlen (buf), " %lu %u %u %u %lu %lu %u",
849 (ulong) uid->attribs[i].len, uid->attribs[i].type, i + 1,
850 uid->numattribs, (ulong) uid->created,
851 (ulong) uid->expiredate,
852 ((uid->is_primary ? 0x01 : 0) | (uid->
853 is_revoked ? 0x02 : 0) |
854 (uid->is_expired ? 0x04 : 0)));
855 write_status_text (STATUS_ATTRIBUTE, buf);
858 es_fwrite (uid->attribs[i].data, uid->attribs[i].len, 1, attrib_fp);
859 es_fflush (attrib_fp);
865 list_keyblock_print (ctrl_t ctrl, kbnode_t keyblock, int secret, int fpr,
866 struct keylist_context *listctx)
873 char *hexgrip = NULL;
874 char *serialno = NULL;
876 /* Get the keyid from the keyblock. */
877 node = find_kbnode (keyblock, PKT_PUBLIC_KEY);
880 log_error ("Oops; key lost!\n");
881 dump_kbnode (keyblock);
885 pk = node->pkt->pkt.public_key;
887 if (secret || opt.with_keygrip)
889 rc = hexkeygrip_from_pk (pk, &hexgrip);
891 log_error ("error computing a keygrip: %s\n", gpg_strerror (rc));
896 /* Encode some info about the secret key in SECRET. */
897 if (!agent_get_keyinfo (NULL, hexgrip, &serialno, NULL))
898 secret = serialno? 3 : 1;
900 secret = 2; /* Key not found. */
903 if (!listctx->no_validity)
904 check_trustdb_stale (ctrl);
906 /* Print the "pub" line and in KF_NONE mode the fingerprint. */
907 print_key_line (es_stdout, pk, secret);
910 print_fingerprint (NULL, pk, 0);
912 if (opt.with_keygrip && hexgrip)
913 es_fprintf (es_stdout, " Keygrip = %s\n", hexgrip);
916 print_card_serialno (serialno);
918 if (opt.with_key_data)
921 for (kbctx = NULL; (node = walk_kbnode (keyblock, &kbctx, 0));)
923 if (node->pkt->pkttype == PKT_USER_ID)
925 PKT_user_id *uid = node->pkt->pkt.user_id;
927 int kl = opt.keyid_format == KF_NONE? 10 : keystrlen ();
929 if ((uid->is_expired || uid->is_revoked)
930 && !(opt.list_options & LIST_SHOW_UNUSABLE_UIDS))
938 if (attrib_fp && uid->attrib_data != NULL)
939 dump_attribs (uid, pk);
941 if ((uid->is_revoked || uid->is_expired)
942 || ((opt.list_options & LIST_SHOW_UID_VALIDITY)
943 && !listctx->no_validity))
945 const char *validity;
947 validity = uid_trust_string_fixed (ctrl, pk, uid);
948 indent = ((kl + (opt.legacy_list_mode? 9:11))
949 - atoi (uid_trust_string_fixed (ctrl, NULL, NULL)));
950 if (indent < 0 || indent > 40)
953 es_fprintf (es_stdout, "uid%*s%s ", indent, "", validity);
957 indent = kl + (opt.legacy_list_mode? 10:12);
958 es_fprintf (es_stdout, "uid%*s", indent, "");
961 print_utf8_buffer (es_stdout, uid->name, uid->len);
962 es_putc ('\n', es_stdout);
964 if (opt.with_wkd_hash)
966 char *mbox, *hash, *p;
969 mbox = mailbox_from_userid (uid->name);
970 if (mbox && (p = strchr (mbox, '@')))
973 gcry_md_hash_buffer (GCRY_MD_SHA1, hashbuf,
974 mbox, strlen (mbox));
975 hash = zb32_encode (hashbuf, 8*20);
978 es_fprintf (es_stdout, " %*s%s@%s\n",
979 indent, "", hash, p);
986 if ((opt.list_options & LIST_SHOW_PHOTOS) && uid->attribs != NULL)
987 show_photos (ctrl, uid->attribs, uid->numattribs, pk, uid);
989 else if (node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
991 PKT_public_key *pk2 = node->pkt->pkt.public_key;
993 if ((pk2->flags.revoked || pk2->has_expired)
994 && !(opt.list_options & LIST_SHOW_UNUSABLE_SUBKEYS))
1002 xfree (serialno); serialno = NULL;
1003 xfree (hexgrip); hexgrip = NULL;
1004 if (secret || opt.with_keygrip)
1006 rc = hexkeygrip_from_pk (pk2, &hexgrip);
1008 log_error ("error computing a keygrip: %s\n",
1013 if (!agent_get_keyinfo (NULL, hexgrip, &serialno, NULL))
1014 secret = serialno? 3 : 1;
1016 secret = '2'; /* Key not found. */
1019 /* Print the "sub" line. */
1020 print_key_line (es_stdout, pk2, secret);
1021 if (fpr > 1 || opt.with_subkey_fingerprint)
1023 print_fingerprint (NULL, pk2, 0);
1025 print_card_serialno (serialno);
1027 if (opt.with_keygrip && hexgrip)
1028 es_fprintf (es_stdout, " Keygrip = %s\n", hexgrip);
1029 if (opt.with_key_data)
1030 print_key_data (pk2);
1032 else if (opt.list_sigs
1033 && node->pkt->pkttype == PKT_SIGNATURE && !skip_sigs)
1035 PKT_signature *sig = node->pkt->pkt.signature;
1039 if (listctx->check_sigs)
1041 rc = check_key_signature (keyblock, node, NULL);
1042 switch (gpg_err_code (rc))
1045 listctx->good_sigs++;
1048 case GPG_ERR_BAD_SIGNATURE:
1049 listctx->inv_sigs++;
1052 case GPG_ERR_NO_PUBKEY:
1053 case GPG_ERR_UNUSABLE_PUBKEY:
1062 /* TODO: Make sure a cached sig record here still has
1063 the pk that issued it. See also
1064 keyedit.c:print_and_check_one_sig */
1072 if (sig->sig_class == 0x20 || sig->sig_class == 0x28
1073 || sig->sig_class == 0x30)
1075 else if ((sig->sig_class & ~3) == 0x10)
1077 else if (sig->sig_class == 0x18)
1079 else if (sig->sig_class == 0x1F)
1083 es_fprintf (es_stdout, "sig "
1084 "[unexpected signature class 0x%02x]\n",
1089 es_fputs (sigstr, es_stdout);
1090 es_fprintf (es_stdout, "%c%c %c%c%c%c%c%c %s %s",
1091 sigrc, (sig->sig_class - 0x10 > 0 &&
1092 sig->sig_class - 0x10 <
1093 4) ? '0' + sig->sig_class - 0x10 : ' ',
1094 sig->flags.exportable ? ' ' : 'L',
1095 sig->flags.revocable ? ' ' : 'R',
1096 sig->flags.policy_url ? 'P' : ' ',
1097 sig->flags.notation ? 'N' : ' ',
1098 sig->flags.expired ? 'X' : ' ',
1099 (sig->trust_depth > 9) ? 'T' : (sig->trust_depth >
1101 sig->trust_depth : ' ', keystr (sig->keyid),
1102 datestr_from_sig (sig));
1103 if (opt.list_options & LIST_SHOW_SIG_EXPIRE)
1104 es_fprintf (es_stdout, " %s", expirestr_from_sig (sig));
1105 es_fprintf (es_stdout, " ");
1107 es_fprintf (es_stdout, "[%s] ", gpg_strerror (rc));
1108 else if (sigrc == '?')
1110 else if (!opt.fast_list_mode)
1113 char *p = get_user_id (sig->keyid, &n);
1114 print_utf8_buffer (es_stdout, p, n);
1117 es_putc ('\n', es_stdout);
1119 if (sig->flags.policy_url
1120 && (opt.list_options & LIST_SHOW_POLICY_URLS))
1121 show_policy_url (sig, 3, 0);
1123 if (sig->flags.notation && (opt.list_options & LIST_SHOW_NOTATIONS))
1124 show_notation (sig, 3, 0,
1126 list_options & LIST_SHOW_STD_NOTATIONS) ? 1 : 0)
1129 list_options & LIST_SHOW_USER_NOTATIONS) ? 2 :
1132 if (sig->flags.pref_ks
1133 && (opt.list_options & LIST_SHOW_KEYSERVER_URLS))
1134 show_keyserver_url (sig, 3, 0);
1136 /* fixme: check or list other sigs here */
1139 es_putc ('\n', es_stdout);
1145 print_revokers (estream_t fp, PKT_public_key * pk)
1147 /* print the revoker record */
1148 if (!pk->revkey && pk->numrevkeys)
1154 for (i = 0; i < pk->numrevkeys; i++)
1158 es_fprintf (fp, "rvk:::%d::::::", pk->revkey[i].algid);
1159 p = pk->revkey[i].fpr;
1160 for (j = 0; j < 20; j++, p++)
1161 es_fprintf (fp, "%02X", *p);
1162 es_fprintf (fp, ":%02x%s:\n",
1163 pk->revkey[i].class,
1164 (pk->revkey[i].class & 0x40) ? "s" : "");
1170 /* List a key in colon mode. If SECRET is true this is a secret key
1171 record (i.e. requested via --list-secret-key). If HAS_SECRET a
1172 secret key is available even if SECRET is not set. */
1174 list_keyblock_colon (ctrl_t ctrl, kbnode_t keyblock,
1175 int secret, int has_secret)
1182 int trustletter = 0;
1183 int trustletter_print;
1184 int ownertrust_print;
1187 char *hexgrip_buffer = NULL;
1188 const char *hexgrip = NULL;
1189 char *serialno = NULL;
1192 /* Get the keyid from the keyblock. */
1193 node = find_kbnode (keyblock, PKT_PUBLIC_KEY);
1196 log_error ("Oops; key lost!\n");
1197 dump_kbnode (keyblock);
1201 pk = node->pkt->pkt.public_key;
1202 if (secret || has_secret || opt.with_keygrip || opt.with_key_data)
1204 rc = hexkeygrip_from_pk (pk, &hexgrip_buffer);
1206 log_error ("error computing a keygrip: %s\n", gpg_strerror (rc));
1207 /* In the error case we print an empty string so that we have a
1208 * "grp" record for each and subkey - even if it is empty. This
1209 * may help to prevent sync problems. */
1210 hexgrip = hexgrip_buffer? hexgrip_buffer : "";
1213 if ((secret || has_secret)
1214 && agent_get_keyinfo (NULL, hexgrip, &serialno, NULL))
1215 stubkey = 1; /* Key not found. */
1217 keyid_from_pk (pk, keyid);
1218 if (!pk->flags.valid)
1219 trustletter_print = 'i';
1220 else if (pk->flags.revoked)
1221 trustletter_print = 'r';
1222 else if (pk->has_expired)
1223 trustletter_print = 'e';
1224 else if (opt.fast_list_mode || opt.no_expensive_trust_checks)
1225 trustletter_print = 0;
1228 trustletter = get_validity_info (ctrl, keyblock, pk, NULL);
1229 if (trustletter == 'u')
1231 trustletter_print = trustletter;
1234 if (!opt.fast_list_mode && !opt.no_expensive_trust_checks)
1235 ownertrust_print = get_ownertrust_info (pk);
1237 ownertrust_print = 0;
1239 es_fputs (secret? "sec:":"pub:", es_stdout);
1240 if (trustletter_print)
1241 es_putc (trustletter_print, es_stdout);
1242 es_fprintf (es_stdout, ":%u:%d:%08lX%08lX:%s:%s::",
1245 (ulong) keyid[0], (ulong) keyid[1],
1246 colon_datestr_from_pk (pk), colon_strtime (pk->expiredate));
1248 if (ownertrust_print)
1249 es_putc (ownertrust_print, es_stdout);
1250 es_putc (':', es_stdout);
1252 es_putc (':', es_stdout);
1253 es_putc (':', es_stdout);
1254 print_capabilities (pk, keyblock);
1255 es_putc (':', es_stdout); /* End of field 13. */
1256 es_putc (':', es_stdout); /* End of field 14. */
1257 if (secret || has_secret)
1260 es_putc ('#', es_stdout);
1262 es_fputs (serialno, es_stdout);
1263 else if (has_secret)
1264 es_putc ('+', es_stdout);
1266 es_putc (':', es_stdout); /* End of field 15. */
1267 es_putc (':', es_stdout); /* End of field 16. */
1268 if (pk->pubkey_algo == PUBKEY_ALGO_ECDSA
1269 || pk->pubkey_algo == PUBKEY_ALGO_EDDSA
1270 || pk->pubkey_algo == PUBKEY_ALGO_ECDH)
1272 char *curve = openpgp_oid_to_str (pk->pkey[0]);
1273 const char *name = openpgp_oid_to_curve (curve, 0);
1276 es_fputs (name, es_stdout);
1279 es_putc (':', es_stdout); /* End of field 17. */
1280 es_putc (':', es_stdout); /* End of field 18. */
1281 es_putc ('\n', es_stdout);
1283 print_revokers (es_stdout, pk);
1284 print_fingerprint (NULL, pk, 0);
1286 es_fprintf (es_stdout, "grp:::::::::%s:\n", hexgrip);
1287 if (opt.with_key_data)
1288 print_key_data (pk);
1290 for (kbctx = NULL; (node = walk_kbnode (keyblock, &kbctx, 0));)
1292 if (node->pkt->pkttype == PKT_USER_ID)
1294 PKT_user_id *uid = node->pkt->pkt.user_id;
1297 if (attrib_fp && uid->attrib_data != NULL)
1298 dump_attribs (uid, pk);
1300 if (uid->is_revoked)
1302 else if (uid->is_expired)
1304 else if (opt.no_expensive_trust_checks)
1309 uid_validity = get_validity_info (ctrl, keyblock, pk, uid);
1311 es_fputs (uid->attrib_data? "uat:":"uid:", es_stdout);
1313 es_putc (uid_validity, es_stdout);
1314 es_fputs ("::::", es_stdout);
1316 es_fprintf (es_stdout, "%s:", colon_strtime (uid->created));
1317 es_fprintf (es_stdout, "%s:", colon_strtime (uid->expiredate));
1319 namehash_from_uid (uid);
1321 for (i = 0; i < 20; i++)
1322 es_fprintf (es_stdout, "%02X", uid->namehash[i]);
1324 es_fprintf (es_stdout, "::");
1326 if (uid->attrib_data)
1327 es_fprintf (es_stdout, "%u %lu", uid->numattribs, uid->attrib_len);
1329 es_write_sanitized (es_stdout, uid->name, uid->len, ":", NULL);
1330 es_putc (':', es_stdout);
1331 es_putc ('\n', es_stdout);
1333 if (!uid->attrib_data && opt.with_tofu_info
1334 && (opt.trust_model == TM_TOFU || opt.trust_model == TM_TOFU_PGP))
1336 /* Print a "tfs" record. */
1337 tofu_write_tfs_record (ctrl, es_stdout, pk, uid->name);
1341 else if (node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
1344 PKT_public_key *pk2;
1345 int need_hexgrip = !!hexgrip;
1347 pk2 = node->pkt->pkt.public_key;
1348 xfree (hexgrip_buffer); hexgrip_buffer = NULL; hexgrip = NULL;
1349 xfree (serialno); serialno = NULL;
1351 || secret || has_secret || opt.with_keygrip || opt.with_key_data)
1353 rc = hexkeygrip_from_pk (pk2, &hexgrip_buffer);
1355 log_error ("error computing a keygrip: %s\n",
1357 hexgrip = hexgrip_buffer? hexgrip_buffer : "";
1360 if ((secret||has_secret)
1361 && agent_get_keyinfo (NULL, hexgrip, &serialno, NULL))
1362 stubkey = 1; /* Key not found. */
1364 keyid_from_pk (pk2, keyid2);
1365 es_fputs (secret? "ssb:":"sub:", es_stdout);
1366 if (!pk2->flags.valid)
1367 es_putc ('i', es_stdout);
1368 else if (pk2->flags.revoked)
1369 es_putc ('r', es_stdout);
1370 else if (pk2->has_expired)
1371 es_putc ('e', es_stdout);
1372 else if (opt.fast_list_mode || opt.no_expensive_trust_checks)
1376 /* TRUSTLETTER should always be defined here. */
1378 es_fprintf (es_stdout, "%c", trustletter);
1380 es_fprintf (es_stdout, ":%u:%d:%08lX%08lX:%s:%s:::::",
1381 nbits_from_pk (pk2),
1383 (ulong) keyid2[0], (ulong) keyid2[1],
1384 colon_datestr_from_pk (pk2), colon_strtime (pk2->expiredate)
1385 /* fixme: add LID and ownertrust here */
1387 print_capabilities (pk2, NULL);
1388 es_putc (':', es_stdout); /* End of field 13. */
1389 es_putc (':', es_stdout); /* End of field 14. */
1390 if (secret || has_secret)
1393 es_putc ('#', es_stdout);
1395 es_fputs (serialno, es_stdout);
1396 else if (has_secret)
1397 es_putc ('+', es_stdout);
1399 es_putc (':', es_stdout); /* End of field 15. */
1400 es_putc (':', es_stdout); /* End of field 16. */
1401 if (pk2->pubkey_algo == PUBKEY_ALGO_ECDSA
1402 || pk2->pubkey_algo == PUBKEY_ALGO_EDDSA
1403 || pk2->pubkey_algo == PUBKEY_ALGO_ECDH)
1405 char *curve = openpgp_oid_to_str (pk2->pkey[0]);
1406 const char *name = openpgp_oid_to_curve (curve, 0);
1409 es_fputs (name, es_stdout);
1412 es_putc (':', es_stdout); /* End of field 17. */
1413 es_putc ('\n', es_stdout);
1414 print_fingerprint (NULL, pk2, 0);
1416 es_fprintf (es_stdout, "grp:::::::::%s:\n", hexgrip);
1417 if (opt.with_key_data)
1418 print_key_data (pk2);
1420 else if (opt.list_sigs && node->pkt->pkttype == PKT_SIGNATURE)
1422 PKT_signature *sig = node->pkt->pkt.signature;
1423 int sigrc, fprokay = 0;
1426 byte fparray[MAX_FINGERPRINT_LEN];
1430 if (sig->sig_class == 0x20 || sig->sig_class == 0x28
1431 || sig->sig_class == 0x30)
1433 else if ((sig->sig_class & ~3) == 0x10)
1435 else if (sig->sig_class == 0x18)
1437 else if (sig->sig_class == 0x1F)
1441 es_fprintf (es_stdout, "sig::::::::::%02x%c:\n",
1442 sig->sig_class, sig->flags.exportable ? 'x' : 'l');
1448 PKT_public_key *signer_pk = NULL;
1451 if (opt.no_sig_cache)
1452 signer_pk = xmalloc_clear (sizeof (PKT_public_key));
1454 rc = check_key_signature2 (keyblock, node, NULL, signer_pk,
1456 switch (gpg_err_code (rc))
1461 case GPG_ERR_BAD_SIGNATURE:
1464 case GPG_ERR_NO_PUBKEY:
1465 case GPG_ERR_UNUSABLE_PUBKEY:
1473 if (opt.no_sig_cache)
1477 fingerprint_from_pk (signer_pk, fparray, &fplen);
1480 free_public_key (signer_pk);
1489 if (sigrc != '%' && sigrc != '?' && !opt.fast_list_mode)
1490 siguid = get_user_id (sig->keyid, &siguidlen);
1498 es_fputs (sigstr, es_stdout);
1499 es_putc (':', es_stdout);
1501 es_putc (sigrc, es_stdout);
1502 es_fprintf (es_stdout, "::%d:%08lX%08lX:%s:%s:", sig->pubkey_algo,
1503 (ulong) sig->keyid[0], (ulong) sig->keyid[1],
1504 colon_datestr_from_sig (sig),
1505 colon_expirestr_from_sig (sig));
1507 if (sig->trust_depth || sig->trust_value)
1508 es_fprintf (es_stdout, "%d %d", sig->trust_depth, sig->trust_value);
1509 es_fprintf (es_stdout, ":");
1511 if (sig->trust_regexp)
1512 es_write_sanitized (es_stdout, sig->trust_regexp,
1513 strlen (sig->trust_regexp), ":", NULL);
1514 es_fprintf (es_stdout, ":");
1517 es_fprintf (es_stdout, "[%s] ", gpg_strerror (rc));
1519 es_write_sanitized (es_stdout, siguid, siguidlen, ":", NULL);
1521 es_fprintf (es_stdout, ":%02x%c::", sig->sig_class,
1522 sig->flags.exportable ? 'x' : 'l');
1524 if (opt.no_sig_cache && opt.check_sigs && fprokay)
1526 for (i = 0; i < fplen; i++)
1527 es_fprintf (es_stdout, "%02X", fparray[i]);
1530 es_fprintf (es_stdout, ":::%d:\n", sig->digest_algo);
1532 if (opt.show_subpackets)
1533 print_subpackets_colon (sig);
1535 /* fixme: check or list other sigs here */
1540 xfree (hexgrip_buffer);
1545 * Reorder the keyblock so that the primary user ID (and not attribute
1546 * packet) comes first. Fixme: Replace this by a generic sort
1549 do_reorder_keyblock (KBNODE keyblock, int attr)
1551 KBNODE primary = NULL, primary0 = NULL, primary2 = NULL;
1554 for (node = keyblock; node; primary0 = node, node = node->next)
1556 if (node->pkt->pkttype == PKT_USER_ID &&
1557 ((attr && node->pkt->pkt.user_id->attrib_data) ||
1558 (!attr && !node->pkt->pkt.user_id->attrib_data)) &&
1559 node->pkt->pkt.user_id->is_primary)
1561 primary = primary2 = node;
1562 for (node = node->next; node; primary2 = node, node = node->next)
1564 if (node->pkt->pkttype == PKT_USER_ID
1565 || node->pkt->pkttype == PKT_PUBLIC_SUBKEY
1566 || node->pkt->pkttype == PKT_SECRET_SUBKEY)
1575 return; /* No primary key flag found (should not happen). */
1577 for (last = NULL, node = keyblock; node; last = node, node = node->next)
1579 if (node->pkt->pkttype == PKT_USER_ID)
1583 log_assert (last); /* The user ID is never the first packet. */
1584 log_assert (primary0); /* Ditto (this is the node before primary). */
1585 if (node == primary)
1586 return; /* Already the first one. */
1588 last->next = primary;
1589 primary0->next = primary2->next;
1590 primary2->next = node;
1594 reorder_keyblock (KBNODE keyblock)
1596 do_reorder_keyblock (keyblock, 1);
1597 do_reorder_keyblock (keyblock, 0);
1601 list_keyblock (ctrl_t ctrl,
1602 KBNODE keyblock, int secret, int has_secret, int fpr,
1603 struct keylist_context *listctx)
1605 reorder_keyblock (keyblock);
1607 if (opt.with_colons)
1608 list_keyblock_colon (ctrl, keyblock, secret, has_secret);
1610 list_keyblock_print (ctrl, keyblock, secret, fpr, listctx);
1613 es_fflush (es_stdout);
1617 /* Public function used by keygen to list a keyblock. If NO_VALIDITY
1618 * is set the validity of a key is never shown. */
1620 list_keyblock_direct (ctrl_t ctrl,
1621 kbnode_t keyblock, int secret, int has_secret, int fpr,
1624 struct keylist_context listctx;
1626 memset (&listctx, 0, sizeof (listctx));
1627 listctx.no_validity = !!no_validity;
1628 list_keyblock (ctrl, keyblock, secret, has_secret, fpr, &listctx);
1629 keylist_context_release (&listctx);
1633 /* Print an hex digit in ICAO spelling. */
1635 print_icao_hexdigit (estream_t fp, int c)
1637 static const char *list[16] = {
1638 "Zero", "One", "Two", "Three", "Four", "Five", "Six", "Seven",
1639 "Eight", "Niner", "Alfa", "Bravo", "Charlie", "Delta", "Echo", "Foxtrot"
1642 tty_fprintf (fp, "%s", list[c&15]);
1647 * Function to print the finperprint.
1648 * mode 0: as used in key listings, opt.with_colons is honored
1649 * 1: print using log_info ()
1650 * 2: direct use of tty
1651 * 3: direct use of tty but only primary key.
1652 * 4: direct use of tty but only subkey.
1653 * 10: Same as 0 but with_colons etc is ignored.
1654 * 20: Same as 0 but using a compact format.
1656 * Modes 1 and 2 will try and print both subkey and primary key
1657 * fingerprints. A MODE with bit 7 set is used internally. If
1658 * OVERRIDE_FP is not NULL that stream will be used in 0 instead
1659 * of es_stdout or instead of the TTY in modes 2 and 3.
1662 print_fingerprint (estream_t override_fp, PKT_public_key *pk, int mode)
1664 char hexfpr[2*MAX_FINGERPRINT_LEN+1];
1670 int with_colons = opt.with_colons;
1671 int with_icao = opt.with_icao_spelling;
1680 else if (mode == 20)
1687 if (!opt.fingerprint && !opt.with_fingerprint
1688 && opt.with_subkey_fingerprint)
1691 if (pk->main_keyid[0] == pk->keyid[0]
1692 && pk->main_keyid[1] == pk->keyid[1])
1695 /* Just to be safe */
1696 if ((mode & 0x80) && !primary)
1698 log_error ("primary key is not really primary!\n");
1704 if (!primary && (mode == 1 || mode == 2))
1706 PKT_public_key *primary_pk = xmalloc_clear (sizeof (*primary_pk));
1707 get_pubkey (primary_pk, pk->main_keyid);
1708 print_fingerprint (override_fp, primary_pk, (mode | 0x80));
1709 free_public_key (primary_pk);
1714 fp = log_get_stream ();
1716 text = _("Primary key fingerprint:");
1718 text = _(" Subkey fingerprint:");
1722 fp = override_fp; /* Use tty or given stream. */
1724 /* TRANSLATORS: this should fit into 24 bytes so that the
1725 * fingerprint data is properly aligned with the user ID */
1726 text = _(" Primary key fingerprint:");
1728 text = _(" Subkey fingerprint:");
1732 fp = override_fp; /* Use tty or given stream. */
1733 text = _(" Key fingerprint =");
1737 fp = override_fp; /* Use tty or given stream. */
1738 text = _(" Subkey fingerprint:");
1742 fp = override_fp? override_fp : es_stdout;
1743 if (opt.keyid_format == KF_NONE)
1745 text = " "; /* To indent ICAO spelling. */
1749 text = _(" Key fingerprint =");
1752 hexfingerprint (pk, hexfpr, sizeof hexfpr);
1753 if (with_colons && !mode)
1755 es_fprintf (fp, "fpr:::::::::%s:", hexfpr);
1757 else if (compact && !opt.fingerprint && !opt.with_fingerprint)
1759 tty_fprintf (fp, "%*s%s", 6, "", hexfpr);
1763 char fmtfpr[MAX_FORMATTED_FINGERPRINT_LEN + 1];
1764 format_hexfingerprint (hexfpr, fmtfpr, sizeof fmtfpr);
1766 tty_fprintf (fp, "%*s%s", 6, "", fmtfpr);
1768 tty_fprintf (fp, "%s %s", text, fmtfpr);
1770 tty_fprintf (fp, "\n");
1771 if (!with_colons && with_icao)
1774 tty_fprintf (fp, "%*s\"", (int)strlen(text)+1, "");
1775 for (i = 0, p = hexfpr; *p; i++, p++)
1780 tty_fprintf (fp, "\n%*s ", (int)strlen(text)+1, "");
1782 tty_fprintf (fp, " ");
1784 tty_fprintf (fp, " ");
1785 print_icao_hexdigit (fp, xtoi_1 (p));
1787 tty_fprintf (fp, "\"\n");
1791 /* Print the serial number of an OpenPGP card if available. */
1793 print_card_serialno (const char *serialno)
1797 if (opt.with_colons)
1798 return; /* Handled elsewhere. */
1800 es_fputs (_(" Card serial no. ="), es_stdout);
1801 es_putc (' ', es_stdout);
1802 if (strlen (serialno) == 32 && !strncmp (serialno, "D27600012401", 12))
1804 /* This is an OpenPGP card. Print the relevant part. */
1805 /* Example: D2760001240101010001000003470000 */
1807 es_fprintf (es_stdout, "%.*s %.*s", 4, serialno+16, 8, serialno+20);
1810 es_fputs (serialno, es_stdout);
1811 es_putc ('\n', es_stdout);
1815 /* Print a public or secret (sub)key line. Example:
1817 * pub dsa2048 2007-12-31 [SC] [expires: 2018-12-31]
1818 * 80615870F5BAD690333686D0F2AD85AC1E42B367
1820 * Some global options may result in a different output format. If
1821 * SECRET is set, "sec" or "ssb" is used instead of "pub" or "sub" and
1822 * depending on the value a flag character is shown:
1824 * 1 := ' ' Regular secret key
1825 * 2 := '#' Stub secret key
1826 * 3 := '>' Secret key is on a token.
1829 print_key_line (estream_t fp, PKT_public_key *pk, int secret)
1831 char pkstrbuf[PUBKEY_STRING_SIZE];
1833 tty_fprintf (fp, "%s%c %s",
1834 pk->flags.primary? (secret? "sec":"pub")
1835 /**/ : (secret? "ssb":"sub"),
1836 secret == 2? '#' : secret == 3? '>' : ' ',
1837 pubkey_string (pk, pkstrbuf, sizeof pkstrbuf));
1838 if (opt.keyid_format != KF_NONE)
1839 tty_fprintf (fp, "/%s", keystr_from_pk (pk));
1840 tty_fprintf (fp, " %s", datestr_from_pk (pk));
1842 if ((opt.list_options & LIST_SHOW_USAGE))
1844 tty_fprintf (fp, " [%s]", usagestr_from_pk (pk, 0));
1846 if (pk->flags.revoked)
1848 tty_fprintf (fp, " [");
1849 tty_fprintf (fp, _("revoked: %s"), revokestr_from_pk (pk));
1850 tty_fprintf (fp, "]");
1852 else if (pk->has_expired)
1854 tty_fprintf (fp, " [");
1855 tty_fprintf (fp, _("expired: %s"), expirestr_from_pk (pk));
1856 tty_fprintf (fp, "]");
1858 else if (pk->expiredate)
1860 tty_fprintf (fp, " [");
1861 tty_fprintf (fp, _("expires: %s"), expirestr_from_pk (pk));
1862 tty_fprintf (fp, "]");
1866 /* I need to think about this some more. It's easy enough to
1867 include, but it looks sort of confusing in the listing... */
1868 if (opt.list_options & LIST_SHOW_VALIDITY)
1870 int validity = get_validity (ctrl, pk, NULL, NULL, 0);
1871 tty_fprintf (fp, " [%s]", trust_value_to_string (validity));
1875 if (pk->pubkey_algo >= 100)
1876 tty_fprintf (fp, " [experimental algorithm %d]", pk->pubkey_algo);
1878 tty_fprintf (fp, "\n");
1880 /* if the user hasn't explicitly asked for human-readable
1881 fingerprints, show compact fpr of primary key: */
1882 if (pk->flags.primary &&
1883 !opt.fingerprint && !opt.with_fingerprint)
1884 print_fingerprint (fp, pk, 20);
1889 set_attrib_fd (int fd)
1891 static int last_fd = -1;
1893 if (fd != -1 && last_fd == fd)
1896 /* Fixme: Do we need to check for the log stream here? */
1897 if (attrib_fp && attrib_fp != log_get_stream ())
1898 es_fclose (attrib_fp);
1903 #ifdef HAVE_DOSISH_SYSTEM
1904 setmode (fd, O_BINARY);
1907 attrib_fp = es_stdout;
1909 attrib_fp = es_stderr;
1911 attrib_fp = es_fdopen (fd, "wb");
1914 log_fatal ("can't open fd %d for attribute output: %s\n",
1915 fd, strerror (errno));