* trustdb.h, trustdb.c (clean_uids_from_key): New. Walk through the
[gnupg.git] / g10 / keyedit.c
1 /* keyedit.c - keyedit stuff
2  * Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004,
3  *               2005 Free Software Foundation, Inc.
4  *
5  * This file is part of GnuPG.
6  *
7  * GnuPG is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 2 of the License, or
10  * (at your option) any later version.
11  *
12  * GnuPG is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
20  */
21
22 #include <config.h>
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26 #include <errno.h>
27 #include <assert.h>
28 #include <ctype.h>
29 #ifdef HAVE_LIBREADLINE
30 #include <stdio.h>
31 #include <readline/readline.h>
32 #endif
33 #include "options.h"
34 #include "packet.h"
35 #include "errors.h"
36 #include "iobuf.h"
37 #include "keydb.h"
38 #include "memory.h"
39 #include "photoid.h"
40 #include "util.h"
41 #include "main.h"
42 #include "trustdb.h"
43 #include "filter.h"
44 #include "ttyio.h"
45 #include "status.h"
46 #include "i18n.h"
47 #include "keyserver-internal.h"
48
49 static void show_prefs( PKT_user_id *uid, PKT_signature *selfsig, int verbose);
50 static void show_key_with_all_names( KBNODE keyblock, int only_marked,
51             int with_revoker, int with_fpr, int with_subkeys, int with_prefs );
52 static void show_key_and_fingerprint( KBNODE keyblock );
53 static int menu_adduid( KBNODE keyblock, KBNODE sec_keyblock, int photo );
54 static void menu_deluid( KBNODE pub_keyblock, KBNODE sec_keyblock );
55 static int  menu_delsig( KBNODE pub_keyblock );
56 static int menu_clean_sigs_from_uids(KBNODE keyblock);
57 static int menu_clean_uids_from_key(KBNODE keyblock);
58 static void menu_delkey( KBNODE pub_keyblock, KBNODE sec_keyblock );
59 static int menu_addrevoker( KBNODE pub_keyblock,
60                             KBNODE sec_keyblock, int sensitive );
61 static int menu_expire( KBNODE pub_keyblock, KBNODE sec_keyblock );
62 static int menu_set_primary_uid( KBNODE pub_keyblock, KBNODE sec_keyblock );
63 static int menu_set_preferences( KBNODE pub_keyblock, KBNODE sec_keyblock );
64 static int menu_set_keyserver_url (const char *url,
65                                    KBNODE pub_keyblock, KBNODE sec_keyblock );
66 static int menu_select_uid( KBNODE keyblock, int idx );
67 static int menu_select_uid_namehash( KBNODE keyblock, const char *namehash );
68 static int menu_select_key( KBNODE keyblock, int idx );
69 static int count_uids( KBNODE keyblock );
70 static int count_uids_with_flag( KBNODE keyblock, unsigned flag );
71 static int count_keys_with_flag( KBNODE keyblock, unsigned flag );
72 static int count_selected_uids( KBNODE keyblock );
73 static int real_uids_left( KBNODE keyblock );
74 static int count_selected_keys( KBNODE keyblock );
75 static int menu_revsig( KBNODE keyblock );
76 static int menu_revuid( KBNODE keyblock, KBNODE sec_keyblock );
77 static int menu_revkey( KBNODE pub_keyblock, KBNODE sec_keyblock );
78 static int menu_revsubkey( KBNODE pub_keyblock, KBNODE sec_keyblock );
79 static int enable_disable_key( KBNODE keyblock, int disable );
80 static void menu_showphoto( KBNODE keyblock );
81
82 static int update_trust=0;
83
84 #define CONTROL_D ('D' - 'A' + 1)
85
86 #define NODFLG_BADSIG (1<<0)  /* bad signature */
87 #define NODFLG_NOKEY  (1<<1)  /* no public key */
88 #define NODFLG_SIGERR (1<<2)  /* other sig error */
89
90 #define NODFLG_MARK_A (1<<4)  /* temporary mark */
91 #define NODFLG_DELSIG (1<<5)  /* to be deleted */
92
93 #define NODFLG_SELUID (1<<8)  /* indicate the selected userid */
94 #define NODFLG_SELKEY (1<<9)  /* indicate the selected key */
95 #define NODFLG_SELSIG (1<<10) /* indicate a selected signature */
96
97 struct sign_attrib {
98     int non_exportable,non_revocable;
99     struct revocation_reason_info *reason;
100     byte trust_depth,trust_value;
101     char *trust_regexp;
102 };
103
104
105 #ifdef ENABLE_CARD_SUPPORT
106 /* Given a node SEC_NODE with a secret key or subkey, locate the
107    corresponding public key from pub_keyblock. */
108 static PKT_public_key *
109 find_pk_from_sknode (KBNODE pub_keyblock, KBNODE sec_node)
110 {
111   KBNODE node = pub_keyblock;
112   PKT_secret_key *sk;
113   PKT_public_key *pk;
114   
115   if (sec_node->pkt->pkttype == PKT_SECRET_KEY
116       && node->pkt->pkttype == PKT_PUBLIC_KEY)
117     return node->pkt->pkt.public_key;
118   if (sec_node->pkt->pkttype != PKT_SECRET_SUBKEY)
119     return NULL;
120   sk = sec_node->pkt->pkt.secret_key;
121   for (; node; node = node->next)
122     if (node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
123       {
124         pk = node->pkt->pkt.public_key;
125         if (pk->keyid[0] == sk->keyid[0] && pk->keyid[1] == sk->keyid[1])
126           return pk;
127       }
128       
129   return NULL;
130 }
131 #endif /* ENABLE_CARD_SUPPORT */
132
133
134 /* TODO: Fix duplicated code between here and the check-sigs/list-sigs
135    code in keylist.c. */
136 static int
137 print_and_check_one_sig_colon( KBNODE keyblock, KBNODE node,
138                                int *inv_sigs, int *no_key, int *oth_err,
139                                int *is_selfsig, int print_without_key )
140 {
141   PKT_signature *sig = node->pkt->pkt.signature;
142   int rc, sigrc;
143
144   /* TODO: Make sure a cached sig record here still has the pk that
145      issued it.  See also keylist.c:list_keyblock_print */
146
147   switch((rc=check_key_signature(keyblock,node,is_selfsig)))
148     {
149     case 0:
150       node->flag &= ~(NODFLG_BADSIG|NODFLG_NOKEY|NODFLG_SIGERR);
151       sigrc = '!';
152       break;
153     case G10ERR_BAD_SIGN:
154       node->flag = NODFLG_BADSIG;
155       sigrc = '-';
156       if( inv_sigs )
157         ++*inv_sigs;
158       break;
159     case G10ERR_NO_PUBKEY:
160     case G10ERR_UNU_PUBKEY:
161       node->flag = NODFLG_NOKEY;
162       sigrc = '?';
163       if( no_key )
164         ++*no_key;
165       break;
166     default:
167       node->flag = NODFLG_SIGERR;
168       sigrc = '%';
169       if( oth_err )
170         ++*oth_err;
171       break;
172     }
173
174   if( sigrc != '?' || print_without_key )
175     {
176       printf("sig:%c::%d:%08lX%08lX:%lu:%lu:",
177              sigrc,sig->pubkey_algo,(ulong)sig->keyid[0],(ulong)sig->keyid[1],
178              (ulong)sig->timestamp,(ulong)sig->expiredate);
179
180       if(sig->trust_depth || sig->trust_value)
181         printf("%d %d",sig->trust_depth,sig->trust_value);
182
183       printf(":");
184
185       if(sig->trust_regexp)
186         print_string(stdout,sig->trust_regexp,strlen(sig->trust_regexp),':');
187
188       printf("::%02x%c\n",sig->sig_class,sig->flags.exportable?'x':'l');
189
190       if(opt.show_subpackets)
191         print_subpackets_colon(sig);
192     }
193
194   return (sigrc == '!');
195 }
196
197
198 /****************
199  * Print information about a signature, check it and return true
200  * if the signature is okay. NODE must be a signature packet.
201  */
202 static int
203 print_and_check_one_sig( KBNODE keyblock, KBNODE node,
204                          int *inv_sigs, int *no_key, int *oth_err,
205                         int *is_selfsig, int print_without_key )
206 {
207     PKT_signature *sig = node->pkt->pkt.signature;
208     int rc, sigrc;
209     int is_rev = sig->sig_class == 0x30;
210
211     /* TODO: Make sure a cached sig record here still has the pk that
212        issued it.  See also keylist.c:list_keyblock_print */
213
214     switch( (rc = check_key_signature( keyblock, node, is_selfsig)) ) {
215       case 0:
216         node->flag &= ~(NODFLG_BADSIG|NODFLG_NOKEY|NODFLG_SIGERR);
217         sigrc = '!';
218         break;
219       case G10ERR_BAD_SIGN:
220         node->flag = NODFLG_BADSIG;
221         sigrc = '-';
222         if( inv_sigs )
223             ++*inv_sigs;
224         break;
225       case G10ERR_NO_PUBKEY:
226       case G10ERR_UNU_PUBKEY:
227         node->flag = NODFLG_NOKEY;
228         sigrc = '?';
229         if( no_key )
230             ++*no_key;
231         break;
232       default:
233         node->flag = NODFLG_SIGERR;
234         sigrc = '%';
235         if( oth_err )
236             ++*oth_err;
237         break;
238     }
239     if( sigrc != '?' || print_without_key ) {
240         tty_printf("%s%c%c %c%c%c%c%c%c %s %s",
241                    is_rev? "rev":"sig",sigrc,
242                    (sig->sig_class-0x10>0 &&
243                     sig->sig_class-0x10<4)?'0'+sig->sig_class-0x10:' ',
244                    sig->flags.exportable?' ':'L',
245                    sig->flags.revocable?' ':'R',
246                    sig->flags.policy_url?'P':' ',
247                    sig->flags.notation?'N':' ',
248                    sig->flags.expired?'X':' ',
249                    (sig->trust_depth>9)?'T':
250                    (sig->trust_depth>0)?'0'+sig->trust_depth:' ',
251                    keystr(sig->keyid),datestr_from_sig(sig));
252         if(opt.list_options&LIST_SHOW_SIG_EXPIRE)
253           tty_printf(" %s",expirestr_from_sig(sig));
254         tty_printf("  ");
255         if( sigrc == '%' )
256             tty_printf("[%s] ", g10_errstr(rc) );
257         else if( sigrc == '?' )
258             ;
259         else if( *is_selfsig ) {
260             tty_printf( is_rev? _("[revocation]")
261                               : _("[self-signature]") );
262         }
263         else
264           {
265             size_t n;
266             char *p = get_user_id( sig->keyid, &n );
267             tty_print_utf8_string2(p, n, opt.screen_columns-keystrlen()-26-
268                                ((opt.list_options&LIST_SHOW_SIG_EXPIRE)?11:0));
269             m_free(p);
270           }
271         tty_printf("\n");
272
273         if(sig->flags.policy_url && (opt.list_options&LIST_SHOW_POLICY_URLS))
274           show_policy_url(sig,3,0);
275
276         if(sig->flags.notation && (opt.list_options&LIST_SHOW_NOTATIONS))
277           show_notation(sig,3,0,
278                         ((opt.list_options&LIST_SHOW_STD_NOTATIONS)?1:0)+
279                         ((opt.list_options&LIST_SHOW_USER_NOTATIONS)?2:0));
280
281         if(sig->flags.pref_ks && (opt.list_options&LIST_SHOW_KEYSERVER_URLS))
282           show_keyserver_url(sig,3,0);
283     }
284
285     return (sigrc == '!');
286 }
287
288
289
290 /****************
291  * Check the keysigs and set the flags to indicate errors.
292  * Returns true if error found.
293  */
294 static int
295 check_all_keysigs( KBNODE keyblock, int only_selected )
296 {
297     KBNODE kbctx;
298     KBNODE node;
299     int inv_sigs = 0;
300     int no_key = 0;
301     int oth_err = 0;
302     int has_selfsig = 0;
303     int mis_selfsig = 0;
304     int selected = !only_selected;
305     int anyuid = 0;
306
307     for( kbctx=NULL; (node=walk_kbnode( keyblock, &kbctx, 0)) ; ) {
308         if( node->pkt->pkttype == PKT_USER_ID ) {
309             PKT_user_id *uid = node->pkt->pkt.user_id;
310
311             if( only_selected )
312                 selected = (node->flag & NODFLG_SELUID);
313             if( selected ) {
314                 tty_printf("uid  ");
315                 tty_print_utf8_string( uid->name, uid->len );
316                 tty_printf("\n");
317                 if( anyuid && !has_selfsig )
318                     mis_selfsig++;
319                 has_selfsig = 0;
320                 anyuid = 1;
321             }
322         }
323         else if( selected && node->pkt->pkttype == PKT_SIGNATURE
324                  && ( (node->pkt->pkt.signature->sig_class&~3) == 0x10
325                      || node->pkt->pkt.signature->sig_class == 0x30 )  ) {
326             int selfsig;
327
328             if( print_and_check_one_sig( keyblock, node, &inv_sigs,
329                                         &no_key, &oth_err, &selfsig, 0 ) ) {
330                 if( selfsig )
331                     has_selfsig = 1;
332             }
333             /* Hmmm: should we update the trustdb here? */
334         }
335     }
336     if( !has_selfsig )
337         mis_selfsig++;
338     if( inv_sigs == 1 )
339         tty_printf(_("1 bad signature\n") );
340     else if( inv_sigs )
341         tty_printf(_("%d bad signatures\n"), inv_sigs );
342     if( no_key == 1 )
343         tty_printf(_("1 signature not checked due to a missing key\n") );
344     else if( no_key )
345         tty_printf(_("%d signatures not checked due to missing keys\n"), no_key );
346     if( oth_err == 1 )
347         tty_printf(_("1 signature not checked due to an error\n") );
348     else if( oth_err )
349         tty_printf(_("%d signatures not checked due to errors\n"), oth_err );
350     if( mis_selfsig == 1 )
351         tty_printf(_("1 user ID without valid self-signature detected\n"));
352     else if( mis_selfsig  )
353         tty_printf(_("%d user IDs without valid self-signatures detected\n"),
354                                                                     mis_selfsig);
355
356     return inv_sigs || no_key || oth_err || mis_selfsig;
357 }
358
359
360 static int
361 sign_mk_attrib( PKT_signature *sig, void *opaque )
362 {
363     struct sign_attrib *attrib = opaque;
364     byte buf[8];
365
366     if( attrib->non_exportable ) {
367         buf[0] = 0; /* not exportable */
368         build_sig_subpkt( sig, SIGSUBPKT_EXPORTABLE, buf, 1 );
369     }
370
371     if( attrib->non_revocable ) {
372         buf[0] = 0; /* not revocable */
373         build_sig_subpkt( sig, SIGSUBPKT_REVOCABLE, buf, 1 );
374     }
375
376     if( attrib->reason )
377         revocation_reason_build_cb( sig, attrib->reason );
378
379     if(attrib->trust_depth)
380       {
381         /* Not critical.  If someone doesn't understand trust sigs,
382            this can still be a valid regular signature. */
383         buf[0] = attrib->trust_depth;
384         buf[1] = attrib->trust_value;
385         build_sig_subpkt(sig,SIGSUBPKT_TRUST,buf,2);
386
387         /* Critical.  If someone doesn't understands regexps, this
388            whole sig should be invalid.  Note the +1 for the length -
389            regexps are null terminated. */
390         if(attrib->trust_regexp)
391           build_sig_subpkt(sig,SIGSUBPKT_FLAG_CRITICAL|SIGSUBPKT_REGEXP,
392                            attrib->trust_regexp,
393                            strlen(attrib->trust_regexp)+1);
394       }
395
396     return 0;
397 }
398
399 static void
400 trustsig_prompt(byte *trust_value,byte *trust_depth,char **regexp)
401 {
402   char *p;
403
404   *trust_value=0;
405   *trust_depth=0;
406   *regexp=NULL;
407
408   /* Same string as pkclist.c:do_edit_ownertrust */
409   tty_printf(_("Please decide how far you trust this user to correctly verify"
410                " other users' keys\n(by looking at passports, checking"
411                " fingerprints from different sources, etc.)\n"));
412   tty_printf("\n");
413   tty_printf (_("  %d = I trust marginally\n"), 1);
414   tty_printf (_("  %d = I trust fully\n"), 2);
415   tty_printf("\n");
416
417   while(*trust_value==0)
418     {
419       p = cpr_get("trustsig_prompt.trust_value",_("Your selection? "));
420       trim_spaces(p);
421       cpr_kill_prompt();
422       /* 60 and 120 are as per RFC2440 */
423       if(p[0]=='1' && !p[1])
424         *trust_value=60;
425       else if(p[0]=='2' && !p[1])
426         *trust_value=120;
427       m_free(p);
428     }
429
430   tty_printf("\n");
431
432   tty_printf(_(
433               "Please enter the depth of this trust signature.\n"
434               "A depth greater than 1 allows the key you are signing to make\n"
435               "trust signatures on your behalf.\n"));
436   tty_printf("\n");
437
438   while(*trust_depth==0)
439     {
440       p = cpr_get("trustsig_prompt.trust_depth",_("Your selection? "));
441       trim_spaces(p);
442       cpr_kill_prompt();
443       *trust_depth=atoi(p);
444       m_free(p);
445     }
446
447   tty_printf("\n");
448
449   tty_printf(_("Please enter a domain to restrict this signature, "
450                "or enter for none.\n"));
451
452   tty_printf("\n");
453
454   p=cpr_get("trustsig_prompt.trust_regexp",_("Your selection? "));
455   trim_spaces(p);
456   cpr_kill_prompt();
457
458   if(strlen(p)>0)
459     {
460       char *q=p;
461       int regexplen=100,ind;
462
463       *regexp=m_alloc(regexplen);
464
465       /* Now mangle the domain the user entered into a regexp.  To do
466          this, \-escape everything that isn't alphanumeric, and attach
467          "<[^>]+[@.]" to the front, and ">$" to the end. */
468
469       strcpy(*regexp,"<[^>]+[@.]");
470       ind=strlen(*regexp);
471
472       while(*q)
473         {
474           if(!((*q>='A' && *q<='Z')
475                || (*q>='a' && *q<='z') || (*q>='0' && *q<='9')))
476             (*regexp)[ind++]='\\';
477
478           (*regexp)[ind++]=*q;
479
480           if((regexplen-ind)<3)
481             {
482               regexplen+=100;
483               *regexp=m_realloc(*regexp,regexplen);
484             }
485
486           q++;
487         }
488
489       (*regexp)[ind]='\0';
490       strcat(*regexp,">$");
491     }
492
493   m_free(p);
494   tty_printf("\n");
495 }
496
497 /****************
498  * Loop over all locusr and and sign the uids after asking.
499  * If no user id is marked, all user ids will be signed;
500  * if some user_ids are marked those will be signed.
501  */
502 static int
503 sign_uids( KBNODE keyblock, STRLIST locusr, int *ret_modified,
504            int local, int nonrevocable, int trust, int interactive )
505 {
506     int rc = 0;
507     SK_LIST sk_list = NULL;
508     SK_LIST sk_rover = NULL;
509     PKT_secret_key *sk = NULL;
510     KBNODE node, uidnode;
511     PKT_public_key *primary_pk=NULL;
512     int select_all = !count_selected_uids(keyblock) || interactive;
513     int all_v3=1;
514
515     /* Are there any non-v3 sigs on this key already? */
516     if(PGP2)
517       for(node=keyblock;node;node=node->next)
518         if(node->pkt->pkttype==PKT_SIGNATURE &&
519            node->pkt->pkt.signature->version>3)
520           {
521             all_v3=0;
522             break;
523           }
524
525     /* build a list of all signators.
526      *    
527      * We use the CERT flag to request the primary which must always
528      * be one which is capable of signing keys.  I can't see a reason
529      * why to sign keys using a subkey.  Implementation of USAGE_CERT
530      * is just a hack in getkey.c and does not mean that a subkey
531      * marked as certification capable will be used */
532     rc=build_sk_list( locusr, &sk_list, 0, PUBKEY_USAGE_SIG|PUBKEY_USAGE_CERT);
533     if( rc )
534         goto leave;
535
536     /* loop over all signators */
537     for( sk_rover = sk_list; sk_rover; sk_rover = sk_rover->next ) {
538         u32 sk_keyid[2],pk_keyid[2];
539         char *p,*trust_regexp=NULL;
540         int force_v4=0,class=0,selfsig=0;
541         u32 duration=0,timestamp=0;
542         byte trust_depth=0,trust_value=0;
543
544         if(local || nonrevocable || trust ||
545            opt.cert_policy_url || opt.cert_notation_data)
546           force_v4=1;
547
548         /* we have to use a copy of the sk, because make_keysig_packet
549          * may remove the protection from sk and if we did other
550          * changes to the secret key, we would save the unprotected
551          * version */
552         if( sk )
553             free_secret_key(sk);
554         sk = copy_secret_key( NULL, sk_rover->sk );
555         keyid_from_sk( sk, sk_keyid );
556         /* set mark A for all selected user ids */
557         for( node=keyblock; node; node = node->next ) {
558             if( select_all || (node->flag & NODFLG_SELUID) )
559                 node->flag |= NODFLG_MARK_A;
560             else
561                 node->flag &= ~NODFLG_MARK_A;
562         }
563         /* reset mark for uids which are already signed */
564         uidnode = NULL;
565         for( node=keyblock; node; node = node->next ) {
566             if( node->pkt->pkttype == PKT_PUBLIC_KEY ) {
567                 primary_pk=node->pkt->pkt.public_key;
568                 keyid_from_pk( primary_pk, pk_keyid );
569
570                 /* Is this a self-sig? */
571                 if(pk_keyid[0]==sk_keyid[0] && pk_keyid[1]==sk_keyid[1])
572                   {
573                     selfsig=1;
574                     /* Do not force a v4 sig here, otherwise it would
575                        be difficult to remake a v3 selfsig.  If this
576                        is a v3->v4 promotion case, then we set
577                        force_v4 later anyway. */
578                     force_v4=0;
579                   }
580             }
581             else if( node->pkt->pkttype == PKT_USER_ID )
582               {
583                 uidnode = (node->flag & NODFLG_MARK_A)? node : NULL;
584                 if(uidnode)
585                   {
586                     int yesreally=0;
587                     char *user=utf8_to_native(uidnode->pkt->pkt.user_id->name,
588                                               uidnode->pkt->pkt.user_id->len,
589                                               0);
590
591                     if(uidnode->pkt->pkt.user_id->is_revoked)
592                       {
593                         tty_printf(_("User ID \"%s\" is revoked."),user);
594
595                         if(selfsig)
596                           tty_printf("\n");
597                         else if(opt.expert)
598                           {
599                             tty_printf("\n");
600                             /* No, so remove the mark and continue */
601                             if(!cpr_get_answer_is_yes("sign_uid.revoke_okay",
602                                                       _("Are you sure you "
603                                                         "still want to sign "
604                                                         "it? (y/N) ")))
605                               {
606                                 uidnode->flag &= ~NODFLG_MARK_A;
607                                 uidnode=NULL;
608                               }
609                             else if(interactive)
610                               yesreally=1;
611                           }
612                         else
613                           {
614                             uidnode->flag &= ~NODFLG_MARK_A;
615                             uidnode=NULL;
616                             tty_printf(_("  Unable to sign.\n"));
617                           }
618                       }
619                     else if(uidnode->pkt->pkt.user_id->is_expired)
620                       {
621                         tty_printf(_("User ID \"%s\" is expired."),user);
622
623                         if(selfsig)
624                           tty_printf("\n");
625                         else if(opt.expert)
626                           {
627                             tty_printf("\n");
628                             /* No, so remove the mark and continue */
629                             if(!cpr_get_answer_is_yes("sign_uid.expire_okay",
630                                                       _("Are you sure you "
631                                                         "still want to sign "
632                                                         "it? (y/N) ")))
633                               {
634                                 uidnode->flag &= ~NODFLG_MARK_A;
635                                 uidnode=NULL;
636                               }
637                             else if(interactive)
638                               yesreally=1;
639                           }
640                         else
641                           {
642                             uidnode->flag &= ~NODFLG_MARK_A;
643                             uidnode=NULL;
644                             tty_printf(_("  Unable to sign.\n"));
645                           }
646                       }
647                     else if(!uidnode->pkt->pkt.user_id->created && !selfsig)
648                       {
649                         tty_printf(_("User ID \"%s\" is not self-signed."),
650                                    user);
651
652                         if(opt.expert)
653                           {
654                             tty_printf("\n");
655                             /* No, so remove the mark and continue */
656                             if(!cpr_get_answer_is_yes("sign_uid.nosig_okay",
657                                                       _("Are you sure you "
658                                                         "still want to sign "
659                                                         "it? (y/N) ")))
660                               {
661                                 uidnode->flag &= ~NODFLG_MARK_A;
662                                 uidnode=NULL;
663                               }
664                             else if(interactive)
665                               yesreally=1;
666                           }
667                         else
668                           {
669                             uidnode->flag &= ~NODFLG_MARK_A;
670                             uidnode=NULL;
671                             tty_printf(_("  Unable to sign.\n"));
672                           }
673                       }
674
675                     if(uidnode && interactive && !yesreally)
676                       {
677                         tty_printf(_("User ID \"%s\" is signable.  "),user);
678                         if(!cpr_get_answer_is_yes("sign_uid.sign_okay",
679                                                   _("Sign it? (y/N) ")))
680                           {
681                             uidnode->flag &= ~NODFLG_MARK_A;
682                             uidnode=NULL;
683                           }
684                       }
685
686                     m_free(user);
687                   }
688               }
689             else if( uidnode && node->pkt->pkttype == PKT_SIGNATURE
690                 && (node->pkt->pkt.signature->sig_class&~3) == 0x10 ) {
691                 if( sk_keyid[0] == node->pkt->pkt.signature->keyid[0]
692                     && sk_keyid[1] == node->pkt->pkt.signature->keyid[1] ) {
693                     char buf[50];
694                     char *user=utf8_to_native(uidnode->pkt->pkt.user_id->name,
695                                               uidnode->pkt->pkt.user_id->len,
696                                               0);
697
698                     /* It's a v3 self-sig.  Make it into a v4 self-sig? */
699                     if(node->pkt->pkt.signature->version<4 && selfsig)
700                       {
701                         tty_printf(_("The self-signature on \"%s\"\n"
702                                      "is a PGP 2.x-style signature.\n"),user);
703  
704                         /* Note that the regular PGP2 warning below
705                            still applies if there are no v4 sigs on
706                            this key at all. */
707
708                         if(opt.expert)
709                           if(cpr_get_answer_is_yes("sign_uid.v4_promote_okay",
710                                                    _("Do you want to promote "
711                                                      "it to an OpenPGP self-"
712                                                      "signature? (y/N) ")))
713                             {
714                               force_v4=1;
715                               node->flag|=NODFLG_DELSIG;
716                               m_free(user);
717                               continue;
718                             }
719                       }
720
721                     /* Is the current signature expired? */
722                     if(node->pkt->pkt.signature->flags.expired)
723                       {
724                         tty_printf(_("Your current signature on \"%s\"\n"
725                                      "has expired.\n"),user);
726
727                         if(cpr_get_answer_is_yes("sign_uid.replace_expired_okay",
728                                                  _("Do you want to issue a "
729                                                    "new signature to replace "
730                                                    "the expired one? (y/N) ")))
731                           {
732                             /* Mark these for later deletion.  We
733                                don't want to delete them here, just in
734                                case the replacement signature doesn't
735                                happen for some reason.  We only delete
736                                these after the replacement is already
737                                in place. */
738
739                             node->flag|=NODFLG_DELSIG;
740                             m_free(user);
741                             continue;
742                           }
743                       }
744
745                     if(!node->pkt->pkt.signature->flags.exportable && !local)
746                       {
747                         /* It's a local sig, and we want to make a
748                            exportable sig. */
749                         tty_printf(_("Your current signature on \"%s\"\n"
750                                      "is a local signature.\n"),user);
751
752                         if(cpr_get_answer_is_yes("sign_uid.local_promote_okay",
753                                                  _("Do you want to promote "
754                                                    "it to a full exportable "
755                                                    "signature? (y/N) ")))
756                           {
757                             /* Mark these for later deletion.  We
758                                don't want to delete them here, just in
759                                case the replacement signature doesn't
760                                happen for some reason.  We only delete
761                                these after the replacement is already
762                                in place. */
763
764                             node->flag|=NODFLG_DELSIG;
765                             m_free(user);
766                             continue;
767                           }
768                       }
769
770                     /* Fixme: see whether there is a revocation in which
771                      * case we should allow to sign it again. */
772                     if (!node->pkt->pkt.signature->flags.exportable && local)
773                       tty_printf(_(
774                               "\"%s\" was already locally signed by key %s\n"),
775                                  user,keystr_from_sk(sk));
776                     else
777                       tty_printf(_("\"%s\" was already signed by key %s\n"),
778                                  user,keystr_from_sk(sk));
779
780                     if(opt.expert
781                        && cpr_get_answer_is_yes("sign_uid.dupe_okay",
782                                                 _("Do you want to sign it "
783                                                   "again anyway? (y/N) ")))
784                       {
785                         /* Don't delete the old sig here since this is
786                            an --expert thing. */
787                         m_free(user);
788                         continue;
789                       }
790
791                     sprintf (buf, "%08lX%08lX",
792                              (ulong)sk->keyid[0], (ulong)sk->keyid[1] );
793                     write_status_text (STATUS_ALREADY_SIGNED, buf);
794                     uidnode->flag &= ~NODFLG_MARK_A; /* remove mark */
795
796                     m_free(user);
797                 }
798             }
799         }
800
801         /* check whether any uids are left for signing */
802         if( !count_uids_with_flag(keyblock, NODFLG_MARK_A) )
803           {
804             tty_printf(_("Nothing to sign with key %s\n"),keystr_from_sk(sk));
805             continue;
806           }
807
808         /* Ask whether we really should sign these user id(s) */
809         tty_printf("\n");
810         show_key_with_all_names( keyblock, 1, 0, 1, 0, 0 );
811         tty_printf("\n");
812
813         if(primary_pk->expiredate && !selfsig)
814           {
815             u32 now=make_timestamp();
816
817             if(primary_pk->expiredate<=now)
818               {
819                 tty_printf(_("This key has expired!"));
820
821                 if(opt.expert)
822                   {
823                     tty_printf("  ");
824                     if(!cpr_get_answer_is_yes("sign_uid.expired_okay",
825                                               _("Are you sure you still "
826                                                 "want to sign it? (y/N) ")))
827                       continue;
828                   }
829                 else
830                   {
831                     tty_printf(_("  Unable to sign.\n"));
832                     continue;
833                   }
834               }
835             else
836               {
837                 char *answer;
838
839                 tty_printf(_("This key is due to expire on %s.\n"),
840                            expirestr_from_pk(primary_pk));
841
842                 answer=cpr_get("sign_uid.expire",
843                                _("Do you want your signature to "
844                                  "expire at the same time? (Y/n) "));
845                 if(answer_is_yes_no_default(answer,1))
846                   {
847                     /* This fixes the signature timestamp we're going
848                        to make as now.  This is so the expiration date
849                        is exactly correct, and not a few seconds off
850                        (due to the time it takes to answer the
851                        questions, enter the passphrase, etc). */
852                     timestamp=now;
853                     duration=primary_pk->expiredate-now;
854                     force_v4=1;
855                   }
856
857                 cpr_kill_prompt();
858                 m_free(answer);
859               }
860           }
861
862         /* Only ask for duration if we haven't already set it to match
863            the expiration of the pk */
864         if(!duration && !selfsig)
865           {
866             if(opt.ask_cert_expire)
867               duration=ask_expire_interval(1,opt.def_cert_expire);
868             else
869               duration=parse_expire_string(opt.def_cert_expire);
870           }
871
872         if(duration)
873           force_v4=1;
874
875         /* Is --pgp2 on, it's a v3 key, all the sigs on the key are
876            currently v3 and we're about to sign it with a v4 sig?  If
877            so, danger! */
878         if(PGP2 && all_v3 &&
879            (sk->version>3 || force_v4) && primary_pk->version<=3)
880           {
881             tty_printf(_("You may not make an OpenPGP signature on a "
882                          "PGP 2.x key while in --pgp2 mode.\n"));
883             tty_printf(_("This would make the key unusable in PGP 2.x.\n"));
884
885             if(opt.expert)
886               {
887                 if(!cpr_get_answer_is_yes("sign_uid.v4_on_v3_okay",
888                                           _("Are you sure you still "
889                                             "want to sign it? (y/N) ")))
890                   continue;
891
892                 all_v3=0;
893               }
894             else
895               continue;
896           }
897
898         if(selfsig)
899           ;
900         else
901           {
902             if(opt.batch || !opt.ask_cert_level)
903               class=0x10+opt.def_cert_level;
904             else
905               {
906                 char *answer;
907
908                 tty_printf(_("How carefully have you verified the key you are "
909                              "about to sign actually belongs\nto the person "
910                              "named above?  If you don't know what to "
911                              "answer, enter \"0\".\n"));
912                 tty_printf("\n");
913                 tty_printf(_("   (0) I will not answer.%s\n"),
914                            opt.def_cert_level==0?" (default)":"");
915                 tty_printf(_("   (1) I have not checked at all.%s\n"),
916                            opt.def_cert_level==1?" (default)":"");
917                 tty_printf(_("   (2) I have done casual checking.%s\n"),
918                            opt.def_cert_level==2?" (default)":"");
919                 tty_printf(_("   (3) I have done very careful checking.%s\n"),
920                            opt.def_cert_level==3?" (default)":"");
921                 tty_printf("\n");
922
923                 while(class==0)
924                   {
925                     answer = cpr_get("sign_uid.class",_("Your selection? "
926                                         "(enter `?' for more information): "));
927                     if(answer[0]=='\0')
928                       class=0x10+opt.def_cert_level; /* Default */
929                     else if(ascii_strcasecmp(answer,"0")==0)
930                       class=0x10; /* Generic */
931                     else if(ascii_strcasecmp(answer,"1")==0)
932                       class=0x11; /* Persona */
933                     else if(ascii_strcasecmp(answer,"2")==0)
934                       class=0x12; /* Casual */
935                     else if(ascii_strcasecmp(answer,"3")==0)
936                       class=0x13; /* Positive */
937                     else
938                       tty_printf(_("Invalid selection.\n"));
939
940                     m_free(answer);
941                   }
942               }
943
944             if(trust)
945               trustsig_prompt(&trust_value,&trust_depth,&trust_regexp);
946           }
947
948         p=get_user_id_native(sk_keyid);
949         tty_printf(_("Are you sure that you want to sign this key with your\n"
950                      "key \"%s\" (%s)\n"),p,keystr_from_sk(sk));
951         m_free(p);
952
953         if(selfsig)
954           {
955             tty_printf("\n");
956             tty_printf(_("This will be a self-signature.\n"));
957
958             if( local )
959               {
960                 tty_printf("\n");
961                 tty_printf(
962                          _("WARNING: the signature will not be marked "
963                            "as non-exportable.\n"));
964               }
965
966             if( nonrevocable )
967               {
968                 tty_printf("\n");
969                 tty_printf(
970                          _("WARNING: the signature will not be marked "
971                            "as non-revocable.\n"));
972               }
973           }
974         else
975           {
976             if( local )
977               {
978                 tty_printf("\n");
979                 tty_printf(
980                      _("The signature will be marked as non-exportable.\n"));
981               }
982
983             if( nonrevocable )
984               {
985                 tty_printf("\n");
986                 tty_printf(
987                       _("The signature will be marked as non-revocable.\n"));
988               }
989
990             switch(class)
991               {
992               case 0x11:
993                 tty_printf("\n");
994                 tty_printf(_("I have not checked this key at all.\n"));
995                 break;
996
997               case 0x12:
998                 tty_printf("\n");
999                 tty_printf(_("I have checked this key casually.\n"));
1000                 break;
1001
1002               case 0x13:
1003                 tty_printf("\n");
1004                 tty_printf(_("I have checked this key very carefully.\n"));
1005                 break;
1006               }
1007           }
1008
1009         tty_printf("\n");
1010
1011         if( opt.batch && opt.answer_yes )
1012           ;
1013         else if( !cpr_get_answer_is_yes("sign_uid.okay",
1014                                         _("Really sign? (y/N) ")) )
1015             continue;
1016
1017         /* now we can sign the user ids */
1018       reloop: /* (must use this, because we are modifing the list) */
1019         primary_pk = NULL;
1020         for( node=keyblock; node; node = node->next ) {
1021             if( node->pkt->pkttype == PKT_PUBLIC_KEY )
1022                 primary_pk = node->pkt->pkt.public_key;
1023             else if( node->pkt->pkttype == PKT_USER_ID
1024                      && (node->flag & NODFLG_MARK_A) ) {
1025                 PACKET *pkt;
1026                 PKT_signature *sig;
1027                 struct sign_attrib attrib;
1028
1029                 assert( primary_pk );
1030                 memset( &attrib, 0, sizeof attrib );
1031                 attrib.non_exportable = local;
1032                 attrib.non_revocable = nonrevocable;
1033                 attrib.trust_depth = trust_depth;
1034                 attrib.trust_value = trust_value;
1035                 attrib.trust_regexp = trust_regexp;
1036                 node->flag &= ~NODFLG_MARK_A;
1037
1038                 /* we force creation of a v4 signature for local
1039                  * signatures, otherwise we would not generate the
1040                  * subpacket with v3 keys and the signature becomes
1041                  * exportable */
1042
1043                 if(selfsig)
1044                   rc = make_keysig_packet( &sig, primary_pk,
1045                                            node->pkt->pkt.user_id,
1046                                            NULL,
1047                                            sk,
1048                                            0x13, 0, force_v4?4:0, 0, 0,
1049                                            keygen_add_std_prefs, primary_pk);
1050                 else
1051                   rc = make_keysig_packet( &sig, primary_pk,
1052                                            node->pkt->pkt.user_id,
1053                                            NULL,
1054                                            sk,
1055                                            class, 0, force_v4?4:0,
1056                                            timestamp, duration,
1057                                            sign_mk_attrib, &attrib );
1058                 if( rc ) {
1059                     log_error(_("signing failed: %s\n"), g10_errstr(rc));
1060                     goto leave;
1061                 }
1062
1063                 *ret_modified = 1; /* we changed the keyblock */
1064                 update_trust = 1;
1065
1066                 pkt = m_alloc_clear( sizeof *pkt );
1067                 pkt->pkttype = PKT_SIGNATURE;
1068                 pkt->pkt.signature = sig;
1069                 insert_kbnode( node, new_kbnode(pkt), PKT_SIGNATURE );
1070                 goto reloop;
1071             }
1072         }
1073
1074         /* Delete any sigs that got promoted */
1075         for( node=keyblock; node; node = node->next )
1076           if( node->flag & NODFLG_DELSIG)
1077             delete_kbnode(node);
1078     } /* end loop over signators */
1079
1080   leave:
1081     release_sk_list( sk_list );
1082     if( sk )
1083         free_secret_key(sk);
1084     return rc;
1085 }
1086
1087
1088
1089 /****************
1090  * Change the passphrase of the primary and all secondary keys.
1091  * We use only one passphrase for all keys.
1092  */
1093 static int
1094 change_passphrase( KBNODE keyblock )
1095 {
1096     int rc = 0;
1097     int changed=0;
1098     KBNODE node;
1099     PKT_secret_key *sk;
1100     char *passphrase = NULL;
1101     int no_primary_secrets = 0;
1102     int any;
1103
1104     node = find_kbnode( keyblock, PKT_SECRET_KEY );
1105     if( !node ) {
1106         log_error("Oops; secret key not found anymore!\n");
1107         goto leave;
1108     }
1109     sk = node->pkt->pkt.secret_key;
1110
1111     for (any = 0, node=keyblock; node; node = node->next) {
1112         if (node->pkt->pkttype == PKT_SECRET_KEY 
1113             || node->pkt->pkttype == PKT_SECRET_SUBKEY) {
1114             PKT_secret_key *tmpsk = node->pkt->pkt.secret_key;
1115             if (!(tmpsk->is_protected
1116                   && (tmpsk->protect.s2k.mode == 1001 
1117                       || tmpsk->protect.s2k.mode == 1002))) {
1118                 any = 1;
1119                 break;
1120             }
1121         }
1122     }
1123     if (!any) {
1124         tty_printf (_("Key has only stub or on-card key items - "
1125                       "no passphrase to change.\n"));
1126         goto leave;
1127     }
1128         
1129     /* See how to handle this key.  */
1130     switch( is_secret_key_protected( sk ) ) {
1131       case -1:
1132         rc = G10ERR_PUBKEY_ALGO;
1133         break;
1134       case 0:
1135         tty_printf(_("This key is not protected.\n"));
1136         break;
1137       default:
1138         if( sk->protect.s2k.mode == 1001 ) {
1139             tty_printf(_("Secret parts of primary key are not available.\n"));
1140             no_primary_secrets = 1;
1141         }
1142         else if( sk->protect.s2k.mode == 1002 ) {
1143             tty_printf(_("Secret parts of primary key are stored on-card.\n"));
1144             no_primary_secrets = 1;
1145         }
1146         else {
1147             tty_printf(_("Key is protected.\n"));
1148             rc = check_secret_key( sk, 0 );
1149             if( !rc )
1150                 passphrase = get_last_passphrase();
1151         }
1152         break;
1153     }
1154
1155     /* Unprotect all subkeys (use the supplied passphrase or ask)*/
1156     for(node=keyblock; !rc && node; node = node->next ) {
1157         if( node->pkt->pkttype == PKT_SECRET_SUBKEY ) {
1158             PKT_secret_key *subsk = node->pkt->pkt.secret_key;
1159             if ( !(subsk->is_protected
1160                    && (subsk->protect.s2k.mode == 1001 
1161                        || subsk->protect.s2k.mode == 1002))) {
1162                 set_next_passphrase( passphrase );
1163                 rc = check_secret_key( subsk, 0 );
1164                 if( !rc && !passphrase )
1165                     passphrase = get_last_passphrase();
1166             }
1167         }
1168     }
1169
1170     if( rc )
1171         tty_printf(_("Can't edit this key: %s\n"), g10_errstr(rc));
1172     else {
1173         DEK *dek = NULL;
1174         STRING2KEY *s2k = m_alloc_secure( sizeof *s2k );
1175         const char *errtext = NULL;
1176
1177         tty_printf(_("Enter the new passphrase for this secret key.\n\n") );
1178
1179         set_next_passphrase( NULL );
1180         for(;;) {
1181             s2k->mode = opt.s2k_mode;
1182             s2k->hash_algo = S2K_DIGEST_ALGO;
1183             dek = passphrase_to_dek( NULL, 0, opt.s2k_cipher_algo,
1184                                      s2k, 2, errtext, NULL);
1185             if( !dek ) {
1186                 errtext = N_("passphrase not correctly repeated; try again");
1187                 tty_printf ("%s.\n", _(errtext));
1188             }
1189             else if( !dek->keylen ) {
1190                 rc = 0;
1191                 tty_printf(_( "You don't want a passphrase -"
1192                             " this is probably a *bad* idea!\n\n"));
1193                 if( cpr_get_answer_is_yes("change_passwd.empty.okay",
1194                                _("Do you really want to do this? (y/N) ")))
1195                   {
1196                     changed++;
1197                     break;
1198                   }
1199             }
1200             else { /* okay */
1201                 rc = 0;
1202                 if( !no_primary_secrets ) {
1203                     sk->protect.algo = dek->algo;
1204                     sk->protect.s2k = *s2k;
1205                     rc = protect_secret_key( sk, dek );
1206                 }
1207                 for(node=keyblock; !rc && node; node = node->next ) {
1208                     if( node->pkt->pkttype == PKT_SECRET_SUBKEY ) {
1209                         PKT_secret_key *subsk = node->pkt->pkt.secret_key;
1210                         if ( !(subsk->is_protected
1211                                && (subsk->protect.s2k.mode == 1001 
1212                                    || subsk->protect.s2k.mode == 1002))) {
1213                             subsk->protect.algo = dek->algo;
1214                             subsk->protect.s2k = *s2k;
1215                             rc = protect_secret_key( subsk, dek );
1216                         }
1217                     }
1218                 }
1219                 if( rc )
1220                     log_error("protect_secret_key failed: %s\n",
1221                               g10_errstr(rc) );
1222                 else
1223                     changed++;
1224                 break;
1225             }
1226         }
1227         m_free(s2k);
1228         m_free(dek);
1229     }
1230
1231   leave:
1232     m_free( passphrase );
1233     set_next_passphrase( NULL );
1234     return changed && !rc;
1235 }
1236
1237
1238 /****************
1239  * There are some keys out (due to a bug in gnupg), where the sequence
1240  * of the packets is wrong.  This function fixes that.
1241  * Returns: true if the keyblock has been fixed.
1242  *
1243  * Note:  This function does not work if there is more than one user ID.
1244  */
1245 static int
1246 fix_keyblock( KBNODE keyblock )
1247 {
1248     KBNODE node, last, subkey;
1249     int fixed=0;
1250
1251     /* locate key signatures of class 0x10..0x13 behind sub key packets */
1252     for( subkey=last=NULL, node = keyblock; node;
1253                                             last=node, node = node->next ) {
1254         switch( node->pkt->pkttype ) {
1255           case PKT_PUBLIC_SUBKEY:
1256           case PKT_SECRET_SUBKEY:
1257             if( !subkey )
1258                 subkey = last; /* actually it is the one before the subkey */
1259             break;
1260           case PKT_SIGNATURE:
1261             if( subkey ) {
1262                 PKT_signature *sig = node->pkt->pkt.signature;
1263                 if( sig->sig_class >= 0x10 && sig->sig_class <= 0x13 ) {
1264                     log_info(_(
1265                         "moving a key signature to the correct place\n"));
1266                     last->next = node->next;
1267                     node->next = subkey->next;
1268                     subkey->next = node;
1269                     node = last;
1270                     fixed=1;
1271                 }
1272             }
1273             break;
1274           default: break;
1275         }
1276     }
1277
1278     return fixed;
1279 }
1280
1281 static int
1282 parse_sign_type(const char *str,int *localsig,int *nonrevokesig,int *trustsig)
1283 {
1284   const char *p=str;
1285
1286   while(*p)
1287     {
1288       if(ascii_strncasecmp(p,"l",1)==0)
1289         {
1290           *localsig=1;
1291           p++;
1292         }
1293       else if(ascii_strncasecmp(p,"nr",2)==0)
1294         {
1295           *nonrevokesig=1;
1296           p+=2;
1297         }
1298       else if(ascii_strncasecmp(p,"t",1)==0)
1299         {
1300           *trustsig=1;
1301           p++;
1302         }
1303       else
1304         return 0;
1305     }
1306
1307   return 1;
1308 }
1309
1310 \f
1311 /****************
1312  * Menu driven key editor.  If seckey_check is true, then a secret key
1313  * that matches username will be looked for.  If it is false, not all
1314  * commands will be available.
1315  *
1316  * Note: to keep track of some selection we use node->mark MARKBIT_xxxx.
1317  */
1318
1319 /* Need an SK for this command */
1320 #define KEYEDIT_NEED_SK 1
1321 /* Cannot be viewing the SK for this command */
1322 #define KEYEDIT_NOT_SK  2
1323 /* Must be viewing the SK for this command */
1324 #define KEYEDIT_ONLY_SK 4
1325 /* Match the tail of the string */
1326 #define KEYEDIT_TAIL_MATCH 8
1327
1328 enum cmdids
1329   {
1330     cmdNONE = 0,
1331     cmdQUIT, cmdHELP, cmdFPR, cmdLIST, cmdSELUID, cmdCHECK, cmdSIGN,
1332     cmdREVSIG, cmdREVKEY, cmdREVUID, cmdDELSIG, cmdPRIMARY, cmdDEBUG,
1333     cmdSAVE, cmdADDUID, cmdADDPHOTO, cmdDELUID, cmdADDKEY, cmdDELKEY,
1334     cmdADDREVOKER, cmdTOGGLE, cmdSELKEY, cmdPASSWD, cmdTRUST, cmdPREF,
1335     cmdEXPIRE, cmdENABLEKEY, cmdDISABLEKEY, cmdSHOWPREF, cmdSETPREF,
1336     cmdPREFKS, cmdINVCMD, cmdSHOWPHOTO, cmdUPDTRUST, cmdCHKTRUST,
1337     cmdADDCARDKEY, cmdKEYTOCARD, cmdBKUPTOCARD, cmdCLEAN, cmdNOP
1338   };
1339
1340 static struct
1341 {
1342   const char *name;
1343   enum cmdids id;
1344   int flags;
1345   const char *desc;
1346 } cmds[] =
1347   { 
1348     { "quit"    , cmdQUIT      , 0, N_("quit this menu") },
1349     { "q"       , cmdQUIT      , 0, NULL   },
1350     { "save"    , cmdSAVE      , 0, N_("save and quit") },
1351     { "help"    , cmdHELP      , 0, N_("show this help") },
1352     { "?"       , cmdHELP      , 0, NULL   },
1353     { "fpr"     , cmdFPR       , 0, N_("show key fingerprint") },
1354     { "list"    , cmdLIST      , 0, N_("list key and user IDs") },
1355     { "l"       , cmdLIST      , 0, NULL   },
1356     { "uid"     , cmdSELUID    , 0, N_("select user ID N") },
1357     { "key"     , cmdSELKEY    , 0, N_("select subkey N") },
1358     { "check"   , cmdCHECK     , 0, N_("check signatures") },
1359     { "c"       , cmdCHECK     , 0, NULL },
1360     { "sign"    , cmdSIGN      , KEYEDIT_NOT_SK|KEYEDIT_TAIL_MATCH,
1361       N_("sign selected user IDs [* see below for related commands]") },
1362     { "s"       , cmdSIGN      , KEYEDIT_NOT_SK, NULL },
1363     /* "lsign" and friends will never match since "sign" comes first
1364        and it is a tail match.  They are just here so they show up in
1365        the help menu. */
1366     { "lsign"   , cmdNOP       , 0, N_("sign selected user IDs locally") },
1367     { "tsign"   , cmdNOP       , 0,
1368       N_("sign selected user IDs with a trust signature") },
1369     { "nrsign"  , cmdNOP       , 0,
1370       N_("sign selected user IDs with a non-revocable signature") },
1371
1372     { "debug"   , cmdDEBUG     , 0, NULL },
1373     { "adduid"  , cmdADDUID    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1374       N_("add a user ID") },
1375     { "addphoto", cmdADDPHOTO  , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1376       N_("add a photo ID") },
1377     { "deluid"  , cmdDELUID    , KEYEDIT_NOT_SK,
1378       N_("delete selected user IDs") },
1379     /* delphoto is really deluid in disguise */
1380     { "delphoto", cmdDELUID    , KEYEDIT_NOT_SK, NULL },
1381
1382     { "addkey"  , cmdADDKEY    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1383       N_("add a subkey") },
1384
1385 #ifdef ENABLE_CARD_SUPPORT
1386     { "addcardkey", cmdADDCARDKEY , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1387       N_("add a key to a smartcard") },
1388     { "keytocard", cmdKEYTOCARD , KEYEDIT_NEED_SK|KEYEDIT_ONLY_SK, 
1389       N_("move a key to a smartcard")},
1390     { "bkuptocard", cmdBKUPTOCARD , KEYEDIT_NEED_SK|KEYEDIT_ONLY_SK, 
1391       N_("move a backup key to a smartcard")},
1392 #endif /*ENABLE_CARD_SUPPORT*/
1393
1394     { "delkey"  , cmdDELKEY    , KEYEDIT_NOT_SK,
1395       N_("delete selected subkeys") },
1396     { "addrevoker",cmdADDREVOKER,KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1397       N_("add a revocation key") },
1398     { "delsig"  , cmdDELSIG    , KEYEDIT_NOT_SK,
1399       N_("delete signatures from the selected user IDs") },
1400     { "expire"  , cmdEXPIRE    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1401       N_("change the expiration date for the key or selected subkeys") },
1402     { "primary" , cmdPRIMARY   , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1403       N_("flag the selected user ID as primary")},
1404     { "toggle"  , cmdTOGGLE    , KEYEDIT_NEED_SK,
1405       N_("toggle between the secret and public key listings") },
1406     { "t"       , cmdTOGGLE    , KEYEDIT_NEED_SK, NULL },
1407     { "pref"    , cmdPREF      , KEYEDIT_NOT_SK,
1408       N_("list preferences (expert)")},
1409     { "showpref", cmdSHOWPREF  , KEYEDIT_NOT_SK,
1410       N_("list preferences (verbose)") },
1411     { "setpref" , cmdSETPREF   , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1412       N_("set preference list for the selected user IDs") },
1413     /* Alias */
1414     { "updpref" , cmdSETPREF   , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK, NULL },
1415
1416     { "keyserver",cmdPREFKS    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1417       N_("set preferred keyserver URL for the selected user IDs")},
1418     { "passwd"  , cmdPASSWD    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1419       N_("change the passphrase") },
1420     /* Alias */
1421     { "password", cmdPASSWD    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK, NULL },
1422
1423     { "trust"   , cmdTRUST     , KEYEDIT_NOT_SK, N_("change the ownertrust") },
1424     { "revsig"  , cmdREVSIG    , KEYEDIT_NOT_SK,
1425       N_("revoke signatures on the selected user IDs") },
1426     { "revuid"  , cmdREVUID    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1427       N_("revoke selected user IDs") },
1428     /* Alias */
1429     { "revphoto", cmdREVUID    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK, NULL },
1430
1431     { "revkey"  , cmdREVKEY    , KEYEDIT_NOT_SK|KEYEDIT_NEED_SK,
1432       N_("revoke key or selected subkeys") },
1433     { "enable"  , cmdENABLEKEY , KEYEDIT_NOT_SK, N_("enable key") },
1434     { "disable" , cmdDISABLEKEY, KEYEDIT_NOT_SK, N_("disable key") },
1435     { "showphoto",cmdSHOWPHOTO , 0, N_("show selected photo IDs") },
1436     { "clean",    cmdCLEAN     , KEYEDIT_NOT_SK, NULL },
1437     { NULL, cmdNONE, 0, NULL }
1438   };
1439
1440
1441 #ifdef HAVE_LIBREADLINE
1442
1443 /* These two functions are used by readline for command completion. */
1444
1445 static char *
1446 command_generator(const char *text,int state)
1447 {
1448   static int list_index,len;
1449   const char *name;
1450
1451   /* If this is a new word to complete, initialize now.  This includes
1452      saving the length of TEXT for efficiency, and initializing the
1453      index variable to 0. */
1454   if(!state)
1455     {
1456       list_index=0;
1457       len=strlen(text);
1458     }
1459
1460   /* Return the next partial match */
1461   while((name=cmds[list_index].name))
1462     {
1463       /* Only complete commands that have help text */
1464       if(cmds[list_index++].desc && strncmp(name,text,len)==0)
1465         return strdup(name);
1466     }
1467
1468   return NULL;
1469 }
1470
1471 static char **
1472 keyedit_completion(const char *text, int start, int end)
1473 {
1474   /* If we are at the start of a line, we try and command-complete.
1475      If not, just do nothing for now. */
1476
1477   if(start==0)
1478     return rl_completion_matches(text,command_generator);
1479
1480   rl_attempted_completion_over=1;
1481
1482   return NULL;
1483 }
1484 #endif /* HAVE_LIBREADLINE */
1485
1486
1487 void
1488 keyedit_menu( const char *username, STRLIST locusr,
1489               STRLIST commands, int quiet, int seckey_check )
1490 {
1491     enum cmdids cmd = 0;
1492     int rc = 0;
1493     KBNODE keyblock = NULL;
1494     KEYDB_HANDLE kdbhd = NULL;
1495     KBNODE sec_keyblock = NULL;
1496     KEYDB_HANDLE sec_kdbhd = NULL;
1497     KBNODE cur_keyblock;
1498     char *answer = NULL;
1499     int redisplay = 1;
1500     int modified = 0;
1501     int sec_modified = 0;
1502     int toggle;
1503     int have_commands = !!commands;
1504
1505     if ( opt.command_fd != -1 )
1506         ;
1507     else if( opt.batch && !have_commands )
1508       {
1509         log_error(_("can't do this in batch mode\n"));
1510         goto leave;
1511       }
1512
1513 #ifdef HAVE_W32_SYSTEM
1514     /* Due to Windows peculiarities we need to make sure that the
1515        trustdb stale check is done before we open another file
1516        (i.e. by searching for a key).  In theory we could make sure
1517        that the files are closed after use but the open/close caches
1518        inhibits that and flushing the cache right before the stale
1519        check is not easy to implement.  Thus we take the easy way out
1520        and run the stale check as early as possible.  Note, that for
1521        non- W32 platforms it is run indirectly trough a call to
1522        get_validity ().  */
1523     check_trustdb_stale ();
1524 #endif
1525
1526     /* Get the public key */
1527     rc = get_pubkey_byname (NULL, username, &keyblock, &kdbhd, 1);
1528     if( rc )
1529         goto leave;
1530     if( fix_keyblock( keyblock ) )
1531         modified++;
1532     if( collapse_uids( &keyblock ) )
1533         modified++;
1534     reorder_keyblock(keyblock);
1535
1536     if(seckey_check)
1537       {/* see whether we have a matching secret key */
1538         PKT_public_key *pk = keyblock->pkt->pkt.public_key;
1539
1540         sec_kdbhd = keydb_new (1);
1541         {
1542             byte afp[MAX_FINGERPRINT_LEN];
1543             size_t an;
1544
1545             fingerprint_from_pk (pk, afp, &an);
1546             while (an < MAX_FINGERPRINT_LEN) 
1547                 afp[an++] = 0;
1548             rc = keydb_search_fpr (sec_kdbhd, afp);
1549         }
1550         if (!rc)
1551           {
1552             rc = keydb_get_keyblock (sec_kdbhd, &sec_keyblock);
1553             if (rc)
1554               {
1555                 log_error (_("error reading secret keyblock \"%s\": %s\n"),
1556                            username, g10_errstr(rc));
1557               }
1558             else
1559               {
1560                 merge_keys_and_selfsig( sec_keyblock );
1561                 if( fix_keyblock( sec_keyblock ) )
1562                   sec_modified++;
1563               }
1564           }
1565
1566         if (rc) {
1567             sec_keyblock = NULL;
1568             keydb_release (sec_kdbhd); sec_kdbhd = NULL;
1569             rc = 0;
1570         }
1571
1572         if( sec_keyblock && !quiet )
1573           tty_printf(_("Secret key is available.\n"));
1574     }
1575
1576     toggle = 0;
1577     cur_keyblock = keyblock;
1578     for(;;) { /* main loop */
1579         int i, arg_number, photo;
1580         const char *arg_string = "";
1581         char *p;
1582         PKT_public_key *pk=keyblock->pkt->pkt.public_key;
1583
1584         tty_printf("\n");
1585
1586         if( redisplay && !quiet )
1587           {
1588             show_key_with_all_names( cur_keyblock, 0, 1, 0, 1, 0 );
1589             tty_printf("\n");
1590             redisplay = 0;
1591           }
1592         do {
1593             m_free(answer);
1594             if( have_commands ) {
1595                 if( commands ) {
1596                     answer = m_strdup( commands->d );
1597                     commands = commands->next;
1598                 }
1599                 else if( opt.batch ) {
1600                     answer = m_strdup("quit");
1601                 }
1602                 else
1603                     have_commands = 0;
1604             }
1605             if( !have_commands )
1606               {
1607                 tty_enable_completion(keyedit_completion);
1608                 answer = cpr_get_no_help("keyedit.prompt", _("Command> "));
1609                 cpr_kill_prompt();
1610                 tty_disable_completion();
1611               }
1612             trim_spaces(answer);
1613         } while( *answer == '#' );
1614
1615         arg_number = 0; /* Yes, here is the init which egcc complains about */
1616         photo = 0; /* This too */
1617         if( !*answer )
1618             cmd = cmdLIST;
1619         else if( *answer == CONTROL_D )
1620             cmd = cmdQUIT;
1621         else if( digitp(answer ) ) {
1622             cmd = cmdSELUID;
1623             arg_number = atoi(answer);
1624         }
1625         else {
1626             if( (p=strchr(answer,' ')) ) {
1627                 *p++ = 0;
1628                 trim_spaces(answer);
1629                 trim_spaces(p);
1630                 arg_number = atoi(p);
1631                 arg_string = p;
1632             }
1633
1634             for(i=0; cmds[i].name; i++ )
1635               {
1636                 if(cmds[i].flags & KEYEDIT_TAIL_MATCH)
1637                   {
1638                     size_t l=strlen(cmds[i].name);
1639                     size_t a=strlen(answer);
1640                     if(a>=l)
1641                       {
1642                         if(ascii_strcasecmp(&answer[a-l],cmds[i].name)==0)
1643                           {
1644                             answer[a-l]='\0';
1645                             break;
1646                           }
1647                       }
1648                   }
1649                 else if( !ascii_strcasecmp( answer, cmds[i].name ) )
1650                   break;
1651               }
1652             if((cmds[i].flags & KEYEDIT_NEED_SK) && !sec_keyblock )
1653               {
1654                 tty_printf(_("Need the secret key to do this.\n"));
1655                 cmd = cmdNOP;
1656               }
1657             else if(((cmds[i].flags & KEYEDIT_NOT_SK) && sec_keyblock
1658                      && toggle)
1659                     ||((cmds[i].flags & KEYEDIT_ONLY_SK) && sec_keyblock
1660                        && !toggle))
1661               {
1662                 tty_printf(_("Please use the command \"toggle\" first.\n"));
1663                 cmd = cmdNOP;
1664               }
1665             else
1666               cmd = cmds[i].id;
1667         }
1668         switch( cmd )
1669           {
1670           case cmdHELP:
1671             for(i=0; cmds[i].name; i++ )
1672               {
1673                 if((cmds[i].flags & KEYEDIT_NEED_SK) && !sec_keyblock )
1674                   ; /* skip if we do not have the secret key */
1675                 else if( cmds[i].desc )
1676                   tty_printf("%-11s %s\n", cmds[i].name, _(cmds[i].desc) );
1677               }
1678
1679             tty_printf("\n");
1680             tty_printf(_(
1681 "* The `sign' command may be prefixed with an `l' for local "
1682 "signatures (lsign),\n"
1683 "  a `t' for trust signatures (tsign), an `nr' for non-revocable signatures\n"
1684 "  (nrsign), or any combination thereof (ltsign, tnrsign, etc.).\n"));
1685
1686             break;
1687
1688           case cmdLIST:
1689             redisplay = 1;
1690             break;
1691
1692           case cmdFPR:
1693             show_key_and_fingerprint( keyblock );
1694             break;
1695
1696           case cmdSELUID:
1697             if(strlen(arg_string)==NAMEHASH_LEN*2)
1698               redisplay=menu_select_uid_namehash(cur_keyblock,arg_string);
1699             else
1700               redisplay=menu_select_uid(cur_keyblock,arg_number);
1701             break;
1702
1703           case cmdSELKEY:
1704             if( menu_select_key( cur_keyblock, arg_number ) )
1705                 redisplay = 1;
1706             break;
1707
1708           case cmdCHECK:
1709             /* we can only do this with the public key becuase the
1710              * check functions can't cope with secret keys and it
1711              * is questionable whether this would make sense at all */
1712             check_all_keysigs( keyblock, count_selected_uids(keyblock) );
1713             break;
1714
1715           case cmdSIGN: /* sign (only the public key) */
1716             {
1717               int localsig=0,nonrevokesig=0,trustsig=0,interactive=0;
1718
1719               if( pk->is_revoked )
1720                 {
1721                   tty_printf(_("Key is revoked."));
1722
1723                   if(opt.expert)
1724                     {
1725                       tty_printf("  ");
1726                       if(!cpr_get_answer_is_yes("keyedit.sign_revoked.okay",
1727                                                 _("Are you sure you still want"
1728                                                   " to sign it? (y/N) ")))
1729                         break;
1730                     }
1731                   else
1732                     {
1733                       tty_printf(_("  Unable to sign.\n"));
1734                       break;
1735                     }
1736                 }
1737
1738               if(count_uids(keyblock) > 1 && !count_selected_uids(keyblock)
1739                  && !cpr_get_answer_is_yes("keyedit.sign_all.okay",
1740                                            _("Really sign all user IDs?"
1741                                              " (y/N) ")))
1742                 interactive=1;
1743
1744               /* What sort of signing are we doing? */
1745               if(!parse_sign_type(answer,&localsig,&nonrevokesig,&trustsig))
1746                 {
1747                   tty_printf(_("Unknown signature type `%s'\n"),answer);
1748                   break;
1749                 }
1750
1751               sign_uids(keyblock, locusr, &modified,
1752                         localsig, nonrevokesig, trustsig, interactive);
1753             }
1754             break;
1755
1756           case cmdDEBUG:
1757             dump_kbnode( cur_keyblock );
1758             break;
1759
1760           case cmdTOGGLE:
1761             toggle = !toggle;
1762             cur_keyblock = toggle? sec_keyblock : keyblock;
1763             redisplay = 1;
1764             break;
1765
1766           case cmdADDPHOTO:
1767             if (RFC2440 || RFC1991 || PGP2)
1768               {
1769                 tty_printf(
1770                    _("This command is not allowed while in %s mode.\n"),
1771                    RFC2440?"OpenPGP":PGP2?"PGP2":"RFC-1991");
1772                 break;
1773               }
1774             photo=1;
1775             /* fall through */
1776
1777           case cmdADDUID:
1778             if( menu_adduid( keyblock, sec_keyblock, photo ) )
1779               {
1780                 update_trust = 1;
1781                 redisplay = 1;
1782                 sec_modified = modified = 1;
1783                 merge_keys_and_selfsig( sec_keyblock );
1784                 merge_keys_and_selfsig( keyblock );
1785               }
1786             break;
1787
1788           case cmdDELUID: {
1789                 int n1;
1790
1791                 if( !(n1=count_selected_uids(keyblock)) )
1792                     tty_printf(_("You must select at least one user ID.\n"));
1793                 else if( real_uids_left(keyblock) < 1 )
1794                     tty_printf(_("You can't delete the last user ID!\n"));
1795                 else if( cpr_get_answer_is_yes("keyedit.remove.uid.okay",
1796                 n1 > 1? _("Really remove all selected user IDs? (y/N) ")
1797                             : _("Really remove this user ID? (y/N) ")
1798                        ) ) {
1799                     menu_deluid( keyblock, sec_keyblock );
1800                     redisplay = 1;
1801                     modified = 1;
1802                     if( sec_keyblock )
1803                        sec_modified = 1;
1804                 }
1805             }
1806             break;
1807
1808           case cmdDELSIG: {
1809                 int n1;
1810
1811                 if( !(n1=count_selected_uids(keyblock)) )
1812                     tty_printf(_("You must select at least one user ID.\n"));
1813                 else if( menu_delsig( keyblock ) ) {
1814                     /* no redisplay here, because it may scroll away some
1815                      * status output of delsig */
1816                     modified = 1;
1817                 }
1818             }
1819             break;
1820
1821           case cmdADDKEY:
1822             if( generate_subkeypair( keyblock, sec_keyblock ) ) {
1823                 redisplay = 1;
1824                 sec_modified = modified = 1;
1825                 merge_keys_and_selfsig( sec_keyblock );
1826                 merge_keys_and_selfsig( keyblock );
1827             }
1828             break;
1829
1830 #ifdef ENABLE_CARD_SUPPORT
1831           case cmdADDCARDKEY:
1832             if (card_generate_subkey (keyblock, sec_keyblock)) {
1833                 redisplay = 1;
1834                 sec_modified = modified = 1;
1835                 merge_keys_and_selfsig( sec_keyblock );
1836                 merge_keys_and_selfsig( keyblock );
1837             }
1838             break;
1839
1840         case cmdKEYTOCARD:
1841           {
1842             KBNODE node=NULL;
1843             switch ( count_selected_keys (sec_keyblock) )
1844               {
1845               case 0:
1846                 if (cpr_get_answer_is_yes("keyedit.keytocard.use_primary",
1847                                      _("Really move the primary key? (y/N) ")))
1848                   node = sec_keyblock;
1849                 break;
1850               case 1:
1851                 for (node = sec_keyblock; node; node = node->next )
1852                   {
1853                     if (node->pkt->pkttype == PKT_SECRET_SUBKEY 
1854                         && node->flag & NODFLG_SELKEY)
1855                       break;
1856                   }
1857                 break;
1858               default:
1859                 tty_printf(_("You must select exactly one key.\n"));
1860                 break;
1861               }
1862             if (node)
1863               {
1864                 PKT_public_key *xxpk = find_pk_from_sknode (keyblock, node);
1865                 if (card_store_subkey (node, xxpk?xxpk->pubkey_usage:0))
1866                   {
1867                     redisplay = 1;
1868                     sec_modified = 1;
1869                   }
1870               }
1871           }
1872           break;
1873
1874         case cmdBKUPTOCARD:
1875           {
1876             /* Ask for a filename, check whether this is really a
1877                backup key as generated by the card generation, parse
1878                that key and store it on card. */
1879             KBNODE node;
1880             const char *fname;
1881             PACKET *pkt;
1882             IOBUF a;
1883
1884             fname = arg_string;
1885             if (!*fname)
1886               {
1887                 tty_printf (_("Command expects a filename argument\n"));
1888                 break;
1889               }
1890
1891             /* Open that file.  */
1892             a = iobuf_open (fname);
1893             if (a && is_secured_file (iobuf_get_fd (a)))
1894               {
1895                 iobuf_close (a);
1896                 a = NULL;
1897                 errno = EPERM;
1898               }
1899             if (!a)
1900               {
1901                 tty_printf (_("Can't open `%s': %s\n"),
1902                             fname, strerror(errno));
1903                 break;
1904               }
1905             
1906             /* Parse and check that file.  */
1907             pkt = xmalloc (sizeof *pkt);
1908             init_packet (pkt);
1909             rc = parse_packet (a, pkt);
1910             iobuf_close (a);
1911             iobuf_ioctl (NULL, 2, 0, (char*)fname); /* (invalidate cache).  */
1912             if (!rc 
1913                 && pkt->pkttype != PKT_SECRET_KEY 
1914                 && pkt->pkttype != PKT_SECRET_SUBKEY)
1915               rc = G10ERR_NO_SECKEY;
1916             if (rc)
1917               {
1918                 tty_printf(_("Error reading backup key from `%s': %s\n"),
1919                            fname, g10_errstr (rc));
1920                 free_packet (pkt);
1921                 xfree (pkt);
1922                 break;
1923               }
1924             node = new_kbnode (pkt);
1925
1926             /* Store it.  */
1927             if (card_store_subkey (node, 0))
1928               {
1929                 redisplay = 1;
1930                 sec_modified = 1;
1931               }
1932             release_kbnode (node);
1933           }
1934           break;
1935
1936 #endif /* ENABLE_CARD_SUPPORT */
1937
1938           case cmdDELKEY: {
1939                 int n1;
1940
1941                 if( !(n1=count_selected_keys( keyblock )) )
1942                     tty_printf(_("You must select at least one key.\n"));
1943                 else if( !cpr_get_answer_is_yes( "keyedit.remove.subkey.okay",
1944                        n1 > 1?
1945                    _("Do you really want to delete the selected keys? (y/N) "):
1946                         _("Do you really want to delete this key? (y/N) ")
1947                        ))
1948                     ;
1949                 else {
1950                     menu_delkey( keyblock, sec_keyblock );
1951                     redisplay = 1;
1952                     modified = 1;
1953                     if( sec_keyblock )
1954                        sec_modified = 1;
1955                 }
1956             }
1957             break;
1958
1959           case cmdADDREVOKER:
1960             {
1961               int sensitive=0;
1962
1963               if(ascii_strcasecmp(arg_string,"sensitive")==0)
1964                 sensitive=1;
1965               if( menu_addrevoker( keyblock, sec_keyblock, sensitive ) ) {
1966                 redisplay = 1;
1967                 sec_modified = modified = 1;
1968                 merge_keys_and_selfsig( sec_keyblock );
1969                 merge_keys_and_selfsig( keyblock );
1970               }
1971             }
1972             break;
1973
1974           case cmdREVUID: {
1975                 int n1;
1976
1977                 if( !(n1=count_selected_uids(keyblock)) )
1978                     tty_printf(_("You must select at least one user ID.\n"));
1979                 else if( cpr_get_answer_is_yes(
1980                             "keyedit.revoke.uid.okay",
1981                        n1 > 1? _("Really revoke all selected user IDs? (y/N) ")
1982                              : _("Really revoke this user ID? (y/N) ")
1983                        ) ) {
1984                   if(menu_revuid(keyblock,sec_keyblock))
1985                     {
1986                       modified=1;
1987                       redisplay=1;
1988                     }
1989                 }
1990             }
1991             break;
1992
1993           case cmdREVKEY:
1994             {
1995               int n1;
1996
1997               if( !(n1=count_selected_keys( keyblock )) )
1998                 {
1999                   if(cpr_get_answer_is_yes("keyedit.revoke.subkey.okay",
2000                                            _("Do you really want to revoke"
2001                                              " the entire key? (y/N) ")))
2002                     {
2003                       if(menu_revkey(keyblock,sec_keyblock))
2004                         modified=1;
2005
2006                       redisplay=1;
2007                     }
2008                 }
2009               else if(cpr_get_answer_is_yes("keyedit.revoke.subkey.okay",
2010                                             n1 > 1?
2011                                             _("Do you really want to revoke"
2012                                               " the selected subkeys? (y/N) "):
2013                                             _("Do you really want to revoke"
2014                                               " this subkey? (y/N) ")))
2015                 {
2016                   if( menu_revsubkey( keyblock, sec_keyblock ) )
2017                     modified = 1;
2018
2019                   redisplay = 1;
2020                 }
2021
2022               if(modified)
2023                 merge_keys_and_selfsig( keyblock );
2024             }
2025             break;
2026
2027           case cmdEXPIRE:
2028             if( menu_expire( keyblock, sec_keyblock ) )
2029               {
2030                 merge_keys_and_selfsig( sec_keyblock );
2031                 merge_keys_and_selfsig( keyblock );
2032                 sec_modified = 1;
2033                 modified = 1;
2034                 redisplay = 1;
2035               }
2036             break;
2037
2038           case cmdPRIMARY:
2039             if( menu_set_primary_uid ( keyblock, sec_keyblock ) ) {
2040                 merge_keys_and_selfsig( keyblock );
2041                 modified = 1;
2042                 redisplay = 1;
2043             }
2044             break;
2045
2046           case cmdPASSWD:
2047             if( change_passphrase( sec_keyblock ) )
2048                 sec_modified = 1;
2049             break;
2050
2051           case cmdTRUST:
2052             if(opt.trust_model==TM_EXTERNAL)
2053               {
2054                 tty_printf(_("Owner trust may not be set while "
2055                              "using an user provided trust database\n"));
2056                 break;
2057               }
2058
2059             show_key_with_all_names( keyblock, 0, 0, 0, 1, 0 );
2060             tty_printf("\n");
2061             if( edit_ownertrust( find_kbnode( keyblock,
2062                                  PKT_PUBLIC_KEY )->pkt->pkt.public_key, 1 ) ) {
2063                 redisplay = 1;
2064                 /* No real need to set update_trust here as
2065                    edit_ownertrust() calls revalidation_mark()
2066                    anyway. */
2067                 update_trust=1;
2068             }
2069             break;
2070
2071           case cmdPREF:
2072             show_key_with_all_names( keyblock, 0, 0, 0, 0, 1 );
2073             break;
2074
2075           case cmdSHOWPREF:
2076             show_key_with_all_names( keyblock, 0, 0, 0, 0, 2 );
2077             break;
2078
2079           case cmdSETPREF:
2080             {
2081               PKT_user_id *tempuid;
2082
2083               keygen_set_std_prefs(!*arg_string?"default" : arg_string, 0);
2084
2085               tempuid=keygen_get_std_prefs();
2086               tty_printf(_("Set preference list to:\n"));
2087               show_prefs(tempuid,NULL,1);
2088               free_user_id(tempuid);
2089
2090               if(cpr_get_answer_is_yes("keyedit.setpref.okay",
2091                                        count_selected_uids (keyblock)?
2092                                        _("Really update the preferences"
2093                                          " for the selected user IDs? (y/N) "):
2094                                        _("Really update the preferences? (y/N) ")))
2095                 {
2096                   if ( menu_set_preferences (keyblock, sec_keyblock) )
2097                     {
2098                       merge_keys_and_selfsig (keyblock);
2099                       modified = 1;
2100                       redisplay = 1;
2101                     }
2102                 }
2103             }
2104             break;
2105
2106           case cmdPREFKS:
2107             if( menu_set_keyserver_url ( *arg_string?arg_string:NULL,
2108                                          keyblock, sec_keyblock ) )
2109               {
2110                 merge_keys_and_selfsig( keyblock );
2111                 modified = 1;
2112                 redisplay = 1;
2113               }
2114             break;
2115
2116           case cmdNOP:
2117             break;
2118
2119           case cmdREVSIG:
2120             if( menu_revsig( keyblock ) ) {
2121                 redisplay = 1;
2122                 modified = 1;
2123             }
2124             break;
2125
2126           case cmdENABLEKEY:
2127           case cmdDISABLEKEY:
2128             if( enable_disable_key( keyblock, cmd == cmdDISABLEKEY ) ) {
2129                 redisplay = 1;
2130                 modified = 1;
2131             }
2132             break;
2133
2134           case cmdSHOWPHOTO:
2135             menu_showphoto(keyblock);
2136             break;
2137
2138           case cmdCLEAN:
2139             {
2140               if(*arg_string)
2141                 {
2142                   if(ascii_strcasecmp(arg_string,"sigs")==0
2143                      || ascii_strcasecmp(arg_string,"signatures")==0
2144                      || ascii_strcasecmp(arg_string,"certs")==0
2145                      || ascii_strcasecmp(arg_string,"certificates")==0)
2146                     modified=menu_clean_sigs_from_uids(keyblock);
2147                   else if(ascii_strcasecmp(arg_string,"uids")==0)
2148                     redisplay=modified=menu_clean_uids_from_key(keyblock);
2149                   else if(ascii_strcasecmp(arg_string,"all")==0)
2150                     {
2151                       modified=menu_clean_sigs_from_uids(keyblock);
2152                       modified+=menu_clean_uids_from_key(keyblock);
2153                       redisplay=modified;
2154                     }
2155                   else
2156                     tty_printf(_("Unable to clean `%s'\n"),arg_string);
2157                 }
2158               else
2159                 tty_printf(_("Please specify item to clean: `sigs',"
2160                              " `uids', or `all'\n"));
2161             }
2162             break;
2163
2164           case cmdQUIT:
2165             if( have_commands )
2166                 goto leave;
2167             if( !modified && !sec_modified )
2168                 goto leave;
2169             if( !cpr_get_answer_is_yes("keyedit.save.okay",
2170                                         _("Save changes? (y/N) ")) ) {
2171                 if( cpr_enabled()
2172                     || cpr_get_answer_is_yes("keyedit.cancel.okay",
2173                                              _("Quit without saving? (y/N) ")))
2174                     goto leave;
2175                 break;
2176             }
2177             /* fall thru */
2178           case cmdSAVE:
2179             if( modified || sec_modified  ) {
2180                 if( modified ) {
2181                     rc = keydb_update_keyblock (kdbhd, keyblock);
2182                     if( rc ) {
2183                         log_error(_("update failed: %s\n"), g10_errstr(rc) );
2184                         break;
2185                     }
2186                 }
2187                 if( sec_modified ) {
2188                     rc = keydb_update_keyblock (sec_kdbhd, sec_keyblock );
2189                     if( rc ) {
2190                         log_error( _("update secret failed: %s\n"),
2191                                    g10_errstr(rc) );
2192                         break;
2193                     }
2194                 }
2195             }
2196             else
2197                 tty_printf(_("Key not changed so no update needed.\n"));
2198
2199             if( update_trust )
2200               {
2201                 revalidation_mark ();
2202                 update_trust=0;
2203               }
2204             goto leave;
2205
2206           case cmdINVCMD:
2207           default:
2208             tty_printf("\n");
2209             tty_printf(_("Invalid command  (try \"help\")\n"));
2210             break;
2211         }
2212     } /* end main loop */
2213
2214   leave:
2215     release_kbnode( keyblock );
2216     release_kbnode( sec_keyblock );
2217     keydb_release (kdbhd);
2218     m_free(answer);
2219 }
2220
2221
2222 \f
2223 /****************
2224  * show preferences of a public keyblock.
2225  */
2226 static void
2227 show_prefs (PKT_user_id *uid, PKT_signature *selfsig, int verbose)
2228 {
2229     const prefitem_t fake={0,0};
2230     const prefitem_t *prefs;
2231     int i;
2232
2233     if( !uid )
2234         return;
2235
2236     if( uid->prefs )
2237         prefs=uid->prefs;
2238     else if(verbose)
2239         prefs=&fake;
2240     else
2241       return;
2242
2243     if (verbose) {
2244         int any, des_seen=0, sha1_seen=0, uncomp_seen=0;
2245
2246         tty_printf ("     ");
2247         tty_printf (_("Cipher: "));
2248         for(i=any=0; prefs[i].type; i++ ) {
2249             if( prefs[i].type == PREFTYPE_SYM ) {
2250                 const char *s = cipher_algo_to_string (prefs[i].value);
2251                 
2252                 if (any)
2253                     tty_printf (", ");
2254                 any = 1;
2255                 /* We don't want to display strings for experimental algos */
2256                 if (s && prefs[i].value < 100 )
2257                     tty_printf ("%s", s );
2258                 else
2259                     tty_printf ("[%d]", prefs[i].value);
2260                 if (prefs[i].value == CIPHER_ALGO_3DES )
2261                     des_seen = 1;
2262             }    
2263         }
2264         if (!des_seen) {
2265             if (any)
2266                 tty_printf (", ");
2267             tty_printf ("%s",cipher_algo_to_string(CIPHER_ALGO_3DES));
2268         }
2269         tty_printf ("\n     ");
2270         tty_printf (_("Digest: "));
2271         for(i=any=0; prefs[i].type; i++ ) {
2272             if( prefs[i].type == PREFTYPE_HASH ) {
2273                 const char *s = digest_algo_to_string (prefs[i].value);
2274                 
2275                 if (any)
2276                     tty_printf (", ");
2277                 any = 1;
2278                 /* We don't want to display strings for experimental algos */
2279                 if (s && prefs[i].value < 100 )
2280                     tty_printf ("%s", s );
2281                 else
2282                     tty_printf ("[%d]", prefs[i].value);
2283                 if (prefs[i].value == DIGEST_ALGO_SHA1 )
2284                     sha1_seen = 1;
2285             }
2286         }
2287         if (!sha1_seen) {
2288             if (any)
2289                 tty_printf (", ");
2290             tty_printf ("%s",digest_algo_to_string(DIGEST_ALGO_SHA1));
2291         }
2292         tty_printf ("\n     ");
2293         tty_printf (_("Compression: "));
2294         for(i=any=0; prefs[i].type; i++ ) {
2295             if( prefs[i].type == PREFTYPE_ZIP ) {
2296                 const char *s=compress_algo_to_string(prefs[i].value);
2297                 
2298                 if (any)
2299                     tty_printf (", ");
2300                 any = 1;
2301                 /* We don't want to display strings for experimental algos */
2302                 if (s && prefs[i].value < 100 )
2303                     tty_printf ("%s", s );
2304                 else
2305                     tty_printf ("[%d]", prefs[i].value);
2306                 if (prefs[i].value == COMPRESS_ALGO_NONE )
2307                     uncomp_seen = 1;
2308             }
2309         }
2310         if (!uncomp_seen) {
2311             if (any)
2312                 tty_printf (", ");
2313             else {
2314               tty_printf ("%s",compress_algo_to_string(COMPRESS_ALGO_ZIP));
2315               tty_printf (", ");
2316             }
2317             tty_printf ("%s",compress_algo_to_string(COMPRESS_ALGO_NONE));
2318         }
2319         if(uid->mdc_feature || !uid->ks_modify)
2320           {
2321             tty_printf ("\n     ");
2322             tty_printf (_("Features: "));
2323             any=0;
2324             if(uid->mdc_feature)
2325               {
2326                 tty_printf ("MDC");
2327                 any=1;
2328               }
2329             if(!uid->ks_modify)
2330               {
2331                 if(any)
2332                   tty_printf (", ");
2333                 tty_printf (_("Keyserver no-modify"));
2334               }
2335           }
2336         tty_printf("\n");
2337
2338         if(selfsig)
2339           {
2340             const byte *pref_ks;
2341             size_t pref_ks_len;
2342
2343             pref_ks=parse_sig_subpkt(selfsig->hashed,
2344                                      SIGSUBPKT_PREF_KS,&pref_ks_len);
2345             if(pref_ks && pref_ks_len)
2346               {
2347                 tty_printf ("     ");
2348                 tty_printf(_("Preferred keyserver: "));
2349                 tty_print_utf8_string(pref_ks,pref_ks_len);
2350                 tty_printf("\n");
2351               }
2352           }
2353     }
2354     else {
2355         tty_printf("    ");
2356         for(i=0; prefs[i].type; i++ ) {
2357             tty_printf( " %c%d", prefs[i].type == PREFTYPE_SYM   ? 'S' :
2358                                  prefs[i].type == PREFTYPE_HASH  ? 'H' :
2359                                  prefs[i].type == PREFTYPE_ZIP ? 'Z':'?',
2360                                  prefs[i].value);
2361         }
2362         if (uid->mdc_feature)
2363             tty_printf (" [mdc]");
2364         if (!uid->ks_modify)
2365             tty_printf (" [no-ks-modify]");
2366         tty_printf("\n");
2367     }
2368 }
2369
2370
2371 /* This is the version of show_key_with_all_names used when
2372    opt.with_colons is used.  It prints all available data in a easy to
2373    parse format and does not translate utf8 */
2374 static void
2375 show_key_with_all_names_colon (KBNODE keyblock)
2376 {
2377   KBNODE node;
2378   int i, j, ulti_hack=0;
2379   byte pk_version=0;
2380   PKT_public_key *primary=NULL;
2381
2382   /* the keys */
2383   for ( node = keyblock; node; node = node->next )
2384     {
2385       if (node->pkt->pkttype == PKT_PUBLIC_KEY
2386           || (node->pkt->pkttype == PKT_PUBLIC_SUBKEY) )
2387         {
2388           PKT_public_key *pk = node->pkt->pkt.public_key;
2389           u32 keyid[2];
2390
2391           if (node->pkt->pkttype == PKT_PUBLIC_KEY)
2392             {
2393               pk_version = pk->version;
2394               primary=pk;
2395             }
2396
2397           keyid_from_pk (pk, keyid);
2398
2399           fputs (node->pkt->pkttype == PKT_PUBLIC_KEY?"pub:":"sub:", stdout);
2400           if (!pk->is_valid)
2401             putchar ('i');
2402           else if (pk->is_revoked)
2403             putchar ('r');
2404           else if (pk->has_expired)
2405             putchar ('e');
2406           else if (!(opt.fast_list_mode || opt.no_expensive_trust_checks ))
2407             {
2408               int trust = get_validity_info (pk, NULL);
2409               if(trust=='u')
2410                 ulti_hack=1;
2411               putchar (trust);
2412             }
2413
2414           printf (":%u:%d:%08lX%08lX:%lu:%lu::",
2415                   nbits_from_pk (pk),
2416                   pk->pubkey_algo,
2417                   (ulong)keyid[0], (ulong)keyid[1],
2418                   (ulong)pk->timestamp,
2419                   (ulong)pk->expiredate );
2420           if (node->pkt->pkttype==PKT_PUBLIC_KEY
2421               && !(opt.fast_list_mode || opt.no_expensive_trust_checks ))
2422             putchar(get_ownertrust_info (pk));
2423           putchar(':');
2424           putchar('\n');
2425           
2426           print_fingerprint (pk, NULL, 0);
2427
2428           /* print the revoker record */
2429           if( !pk->revkey && pk->numrevkeys )
2430             BUG();
2431           else
2432             {
2433               for (i=0; i < pk->numrevkeys; i++)
2434                 {
2435                   byte *p;
2436
2437                   printf ("rvk:::%d::::::", pk->revkey[i].algid);
2438                   p = pk->revkey[i].fpr;
2439                   for (j=0; j < 20; j++, p++ )
2440                     printf ("%02X", *p);
2441                   printf (":%02x%s:\n", pk->revkey[i].class,
2442                           (pk->revkey[i].class&0x40)?"s":"");
2443                 }
2444             }
2445         }
2446     }
2447   
2448     /* the user ids */
2449     i = 0;
2450     for (node = keyblock; node; node = node->next) 
2451       {
2452         if ( node->pkt->pkttype == PKT_USER_ID )
2453           {
2454             PKT_user_id *uid = node->pkt->pkt.user_id;
2455
2456             ++i;
2457
2458             if(uid->attrib_data)
2459               printf("uat:");
2460             else
2461               printf("uid:");
2462
2463             if ( uid->is_revoked )
2464               printf("r::::::::");
2465             else if ( uid->is_expired )
2466               printf("e::::::::");
2467             else if ( opt.fast_list_mode || opt.no_expensive_trust_checks )
2468               printf("::::::::");
2469             else
2470               {
2471                 int uid_validity;
2472
2473                 if( primary && !ulti_hack )
2474                   uid_validity = get_validity_info( primary, uid );
2475                 else
2476                   uid_validity = 'u';
2477                 printf("%c::::::::",uid_validity);
2478               }
2479
2480             if(uid->attrib_data)
2481               printf ("%u %lu",uid->numattribs,uid->attrib_len);
2482             else
2483               print_string (stdout, uid->name, uid->len, ':');
2484
2485             putchar (':');
2486             /* signature class */
2487             putchar (':');
2488             /* capabilities */
2489             putchar (':');
2490             /* preferences */
2491             if (pk_version>3 || uid->selfsigversion>3)
2492               {
2493                 const prefitem_t *prefs = uid->prefs;
2494                 
2495                 for (j=0; prefs && prefs[j].type; j++)
2496                   {
2497                     if (j)
2498                       putchar (' ');
2499                     printf ("%c%d", prefs[j].type == PREFTYPE_SYM   ? 'S' :
2500                             prefs[j].type == PREFTYPE_HASH  ? 'H' :
2501                             prefs[j].type == PREFTYPE_ZIP ? 'Z':'?',
2502                             prefs[j].value);
2503                   } 
2504                 if (uid->mdc_feature)
2505                   printf (",mdc");
2506                 if (!uid->ks_modify)
2507                   printf (",no-ks-modify");
2508               } 
2509             putchar (':');
2510             /* flags */
2511             printf ("%d,", i);
2512             if (uid->is_primary)
2513               putchar ('p');
2514             if (uid->is_revoked)
2515               putchar ('r');
2516             if (uid->is_expired)
2517               putchar ('e');
2518             if ((node->flag & NODFLG_SELUID))
2519               putchar ('s');
2520             if ((node->flag & NODFLG_MARK_A))
2521               putchar ('m');
2522             putchar (':');
2523             putchar('\n');
2524           }
2525       }
2526 }
2527
2528
2529 /****************
2530  * Display the key a the user ids, if only_marked is true, do only
2531  * so for user ids with mark A flag set and dont display the index number
2532  */
2533 static void
2534 show_key_with_all_names( KBNODE keyblock, int only_marked, int with_revoker,
2535                          int with_fpr, int with_subkeys, int with_prefs )
2536 {
2537     KBNODE node;
2538     int i;
2539     int do_warn = 0;
2540     byte pk_version=0;
2541     PKT_public_key *primary=NULL;
2542
2543     if (opt.with_colons)
2544       {
2545         show_key_with_all_names_colon (keyblock);
2546         return;
2547       }
2548
2549     /* the keys */
2550     for( node = keyblock; node; node = node->next ) {
2551         if( node->pkt->pkttype == PKT_PUBLIC_KEY
2552             || (with_subkeys && node->pkt->pkttype == PKT_PUBLIC_SUBKEY) ) {
2553             PKT_public_key *pk = node->pkt->pkt.public_key;
2554             const char *otrust="err",*trust="err";
2555
2556             if( node->pkt->pkttype == PKT_PUBLIC_KEY ) {
2557                 /* do it here, so that debug messages don't clutter the
2558                  * output */
2559                 static int did_warn = 0;
2560
2561                 trust = get_validity_string (pk, NULL);
2562                 otrust = get_ownertrust_string (pk);
2563
2564                 /* Show a warning once */
2565                 if (!did_warn
2566                     && (get_validity (pk, NULL) & TRUST_FLAG_PENDING_CHECK)) {
2567                     did_warn = 1;
2568                     do_warn = 1;
2569                 }
2570
2571                 pk_version=pk->version;
2572                 primary=pk;
2573             }
2574
2575             if(pk->is_revoked)
2576               {
2577                 char *user=get_user_id_string_native(pk->revoked.keyid);
2578                 const char *algo=pubkey_algo_to_string(pk->revoked.algo);
2579                 tty_printf(_("This key was revoked on %s by %s key %s\n"),
2580                            revokestr_from_pk(pk),algo?algo:"?",user);
2581                 m_free(user);
2582               }
2583
2584             if(with_revoker)
2585               {
2586                 if( !pk->revkey && pk->numrevkeys )
2587                   BUG();
2588                 else
2589                   for(i=0;i<pk->numrevkeys;i++)
2590                     {
2591                       u32 r_keyid[2];
2592                       char *user;
2593                       const char *algo=
2594                         pubkey_algo_to_string(pk->revkey[i].algid);
2595
2596                       keyid_from_fingerprint(pk->revkey[i].fpr,
2597                                              MAX_FINGERPRINT_LEN,r_keyid);
2598
2599                       user=get_user_id_string_native(r_keyid);
2600                       tty_printf(_("This key may be revoked by %s key %s"),
2601                                  algo?algo:"?",user);
2602
2603                       if(pk->revkey[i].class&0x40)
2604                         {
2605                           tty_printf(" ");
2606                           tty_printf(_("(sensitive)"));
2607                         }
2608
2609                       tty_printf ("\n");
2610                       m_free(user);
2611                     }
2612               }
2613
2614             keyid_from_pk(pk,NULL);
2615             tty_printf("%s%c %4u%c/%s  ",
2616                        node->pkt->pkttype == PKT_PUBLIC_KEY? "pub":"sub",
2617                        (node->flag & NODFLG_SELKEY)? '*':' ',
2618                        nbits_from_pk( pk ),
2619                        pubkey_letter( pk->pubkey_algo ),
2620                        keystr(pk->keyid));
2621
2622             tty_printf(_("created: %s"),datestr_from_pk(pk));
2623             tty_printf("  ");
2624             if(pk->is_revoked)
2625               tty_printf(_("revoked: %s"),revokestr_from_pk(pk));
2626             else if(pk->has_expired)
2627               tty_printf(_("expired: %s"),expirestr_from_pk(pk));
2628             else
2629               tty_printf(_("expires: %s"),expirestr_from_pk(pk));
2630             tty_printf("  ");
2631             tty_printf(_("usage: %s"),usagestr_from_pk(pk));
2632             tty_printf("\n");
2633
2634             if( node->pkt->pkttype == PKT_PUBLIC_KEY )
2635               {
2636                 if(opt.trust_model!=TM_ALWAYS)
2637                   {
2638                     tty_printf("%*s", (int)keystrlen()+13,"");
2639                     /* Ownertrust is only meaningful for the PGP or
2640                        classic trust models */
2641                     if(opt.trust_model==TM_PGP || opt.trust_model==TM_CLASSIC)
2642                       {
2643                         int width=14-strlen(otrust);
2644                         if(width<=0)
2645                           width=1;
2646                         tty_printf(_("trust: %s"), otrust);
2647                         tty_printf("%*s",width,"");
2648                       }
2649                     
2650                     tty_printf(_("validity: %s"), trust );
2651                     tty_printf("\n");
2652                   }
2653                 if( node->pkt->pkttype == PKT_PUBLIC_KEY
2654                     && (get_ownertrust (pk)&TRUST_FLAG_DISABLED))
2655                   {
2656                     tty_printf("*** ");
2657                     tty_printf(_("This key has been disabled"));
2658                     tty_printf("\n");
2659                   }
2660               }
2661
2662             if( node->pkt->pkttype == PKT_PUBLIC_KEY && with_fpr )
2663               {
2664                 print_fingerprint ( pk, NULL, 2 );
2665                 tty_printf("\n");
2666               }
2667         }
2668         else if( node->pkt->pkttype == PKT_SECRET_KEY
2669             || (with_subkeys && node->pkt->pkttype == PKT_SECRET_SUBKEY) )
2670           {
2671             PKT_secret_key *sk = node->pkt->pkt.secret_key;
2672             tty_printf("%s%c %4u%c/%s  ",
2673                        node->pkt->pkttype == PKT_SECRET_KEY? "sec":"ssb",
2674                        (node->flag & NODFLG_SELKEY)? '*':' ',
2675                        nbits_from_sk( sk ),
2676                        pubkey_letter( sk->pubkey_algo ),
2677                        keystr_from_sk(sk));
2678             tty_printf(_("created: %s"),datestr_from_sk(sk));
2679             tty_printf("  ");
2680             tty_printf(_("expires: %s"),expirestr_from_sk(sk));
2681             tty_printf("\n");
2682             if (sk->is_protected && sk->protect.s2k.mode == 1002)
2683               {
2684                 tty_printf("                     ");
2685                 tty_printf(_("card-no: ")); 
2686                 if (sk->protect.ivlen == 16
2687                     && !memcmp (sk->protect.iv, "\xD2\x76\x00\x01\x24\x01", 6))
2688                   { /* This is an OpenPGP card. */
2689                     for (i=8; i < 14; i++)
2690                       {
2691                         if (i == 10)
2692                           tty_printf (" ");
2693                         tty_printf ("%02X", sk->protect.iv[i]);
2694                       }
2695                   }
2696                 else
2697                   { /* Something is wrong: Print all. */
2698                     for (i=0; i < sk->protect.ivlen; i++)
2699                       tty_printf ("%02X", sk->protect.iv[i]);
2700                   }
2701                 tty_printf ("\n");
2702               }
2703           }
2704     }
2705     
2706     /* the user ids */
2707
2708     i = 0;
2709     for( node = keyblock; node; node = node->next )
2710       {
2711         if( node->pkt->pkttype == PKT_USER_ID
2712             && !is_deleted_kbnode(node))
2713           {
2714             PKT_user_id *uid = node->pkt->pkt.user_id;
2715             ++i;
2716             if( !only_marked || (only_marked && (node->flag & NODFLG_MARK_A)))
2717               {
2718                 if(!only_marked && primary)
2719                   tty_printf("%s ",uid_trust_string_fixed(primary,uid));
2720
2721                 if( only_marked )
2722                   tty_printf("     ");
2723                 else if( node->flag & NODFLG_SELUID )
2724                   tty_printf("(%d)* ", i);
2725                 else if( uid->is_primary )
2726                   tty_printf("(%d). ", i);
2727                 else
2728                   tty_printf("(%d)  ", i);
2729                 tty_print_utf8_string( uid->name, uid->len );
2730                 tty_printf("\n");
2731                 if( with_prefs )
2732                   {
2733                     if(pk_version>3 || uid->selfsigversion>3)
2734                       {
2735                         PKT_signature *selfsig=NULL;
2736                         KBNODE signode;
2737
2738                         for(signode=node->next;
2739                             signode && signode->pkt->pkttype==PKT_SIGNATURE;
2740                             signode=signode->next)
2741                           {
2742                             if(signode->pkt->pkt.signature->
2743                                flags.chosen_selfsig)
2744                               {
2745                                 selfsig=signode->pkt->pkt.signature;
2746                                 break;
2747                               }
2748                           }
2749
2750                         show_prefs (uid, selfsig, with_prefs == 2);
2751                       }
2752                     else
2753                       tty_printf(_("There are no preferences on a"
2754                                    " PGP 2.x-style user ID.\n"));
2755                   }
2756               }
2757           }
2758       }
2759
2760     if (do_warn)
2761         tty_printf (_("Please note that the shown key validity"
2762                       " is not necessarily correct\n"
2763                       "unless you restart the program.\n")); 
2764 }
2765
2766
2767 /* Display basic key information.  This fucntion is suitable to show
2768    information on the key without any dependencies on the trustdb or
2769    any other internal GnuPG stuff.  KEYBLOCK may either be a public or
2770    a secret key.*/
2771 void
2772 show_basic_key_info ( KBNODE keyblock )
2773 {
2774   KBNODE node;
2775   int i;
2776
2777   /* The primary key */
2778   for (node = keyblock; node; node = node->next)
2779     {
2780       if (node->pkt->pkttype == PKT_PUBLIC_KEY)
2781         {
2782           PKT_public_key *pk = node->pkt->pkt.public_key;
2783           
2784           /* Note, we use the same format string as in other show
2785              functions to make the translation job easier. */
2786           tty_printf ("%s  %4u%c/%s  ",
2787                       node->pkt->pkttype == PKT_PUBLIC_KEY? "pub":"sub",
2788                       nbits_from_pk( pk ),
2789                       pubkey_letter( pk->pubkey_algo ),
2790                       keystr_from_pk(pk));
2791           tty_printf(_("created: %s"),datestr_from_pk(pk));
2792           tty_printf("  ");
2793           tty_printf(_("expires: %s"),expirestr_from_pk(pk));
2794           tty_printf("\n");
2795           print_fingerprint ( pk, NULL, 3 );
2796           tty_printf("\n");
2797         }
2798       else if (node->pkt->pkttype == PKT_SECRET_KEY)
2799         {
2800           PKT_secret_key *sk = node->pkt->pkt.secret_key;
2801           tty_printf("%s  %4u%c/%s",
2802                      node->pkt->pkttype == PKT_SECRET_KEY? "sec":"ssb",
2803                      nbits_from_sk( sk ),
2804                      pubkey_letter( sk->pubkey_algo ),
2805                      keystr_from_sk(sk));
2806           tty_printf(_("created: %s"),datestr_from_sk(sk));
2807           tty_printf("  ");
2808           tty_printf(_("expires: %s"),expirestr_from_sk(sk));
2809           tty_printf("\n");
2810           print_fingerprint (NULL, sk, 3 );
2811           tty_printf("\n");
2812         }
2813     }
2814
2815   /* The user IDs. */
2816   for (i=0, node = keyblock; node; node = node->next)
2817     {
2818       if (node->pkt->pkttype == PKT_USER_ID)
2819         {
2820           PKT_user_id *uid = node->pkt->pkt.user_id;
2821           ++i;
2822      
2823           tty_printf ("     ");
2824           if (uid->is_revoked)
2825             tty_printf("[%s] ",_("revoked"));
2826           else if ( uid->is_expired )
2827             tty_printf("[%s] ",_("expired"));
2828           tty_print_utf8_string (uid->name, uid->len);
2829           tty_printf ("\n");
2830         }
2831     }
2832 }
2833
2834 static void
2835 show_key_and_fingerprint( KBNODE keyblock )
2836 {
2837   KBNODE node;
2838   PKT_public_key *pk = NULL;
2839
2840   for( node = keyblock; node; node = node->next )
2841     {
2842       if( node->pkt->pkttype == PKT_PUBLIC_KEY )
2843         {
2844           pk = node->pkt->pkt.public_key;
2845           tty_printf("pub   %4u%c/%s %s ",
2846                      nbits_from_pk( pk ),
2847                      pubkey_letter( pk->pubkey_algo ),
2848                      keystr_from_pk(pk),
2849                      datestr_from_pk(pk) );
2850         }
2851       else if( node->pkt->pkttype == PKT_USER_ID )
2852         {
2853           PKT_user_id *uid = node->pkt->pkt.user_id;
2854           tty_print_utf8_string( uid->name, uid->len );
2855           break;
2856         }
2857     }
2858   tty_printf("\n");
2859   if( pk )
2860     print_fingerprint( pk, NULL, 2 );
2861 }
2862
2863
2864 /* Show a warning if no uids on the key have the primary uid flag
2865    set. */
2866 static void
2867 no_primary_warning(KBNODE keyblock)
2868 {
2869   KBNODE node;
2870   int have_primary=0,uid_count=0;
2871
2872   /* TODO: if we ever start behaving differently with a primary or
2873      non-primary attribute ID, we will need to check for attributes
2874      here as well. */
2875
2876   for(node=keyblock; node; node = node->next)
2877     {
2878       if(node->pkt->pkttype==PKT_USER_ID
2879          && node->pkt->pkt.user_id->attrib_data==NULL)
2880         {
2881           uid_count++;
2882
2883           if(node->pkt->pkt.user_id->is_primary==2)
2884             {
2885               have_primary=1;
2886               break;
2887             }
2888         }
2889     }
2890
2891   if(uid_count>1 && !have_primary)
2892     log_info(_("WARNING: no user ID has been marked as primary.  This command"
2893                " may\n              cause a different user ID to become"
2894                " the assumed primary.\n"));
2895 }
2896
2897 /****************
2898  * Ask for a new user id, do the selfsignature and put it into
2899  * both keyblocks.
2900  * Return true if there is a new user id
2901  */
2902 static int
2903 menu_adduid( KBNODE pub_keyblock, KBNODE sec_keyblock, int photo)
2904 {
2905     PKT_user_id *uid;
2906     PKT_public_key *pk=NULL;
2907     PKT_secret_key *sk=NULL;
2908     PKT_signature *sig=NULL;
2909     PACKET *pkt;
2910     KBNODE node;
2911     KBNODE pub_where=NULL, sec_where=NULL;
2912     int rc;
2913
2914     for( node = pub_keyblock; node; pub_where = node, node = node->next ) {
2915         if( node->pkt->pkttype == PKT_PUBLIC_KEY )
2916             pk = node->pkt->pkt.public_key;
2917         else if( node->pkt->pkttype == PKT_PUBLIC_SUBKEY )
2918             break;
2919     }
2920     if( !node ) /* no subkey */
2921         pub_where = NULL;
2922     for( node = sec_keyblock; node; sec_where = node, node = node->next ) {
2923         if( node->pkt->pkttype == PKT_SECRET_KEY )
2924             sk = copy_secret_key( NULL, node->pkt->pkt.secret_key);
2925         else if( node->pkt->pkttype == PKT_SECRET_SUBKEY )
2926             break;
2927     }
2928     if( !node ) /* no subkey */
2929         sec_where = NULL;
2930     assert(pk && sk);
2931
2932     if(photo) {
2933       int hasattrib=0;
2934
2935       for( node = pub_keyblock; node; node = node->next )
2936         if( node->pkt->pkttype == PKT_USER_ID &&
2937             node->pkt->pkt.user_id->attrib_data!=NULL)
2938           {
2939             hasattrib=1;
2940             break;
2941           }
2942
2943       /* It is legal but bad for compatibility to add a photo ID to a
2944          v3 key as it means that PGP2 will not be able to use that key
2945          anymore.  Also, PGP may not expect a photo on a v3 key.
2946          Don't bother to ask this if the key already has a photo - any
2947          damage has already been done at that point. -dms */
2948       if(pk->version==3 && !hasattrib)
2949         {
2950           if(opt.expert)
2951             {
2952               tty_printf(_("WARNING: This is a PGP2-style key.  "
2953                            "Adding a photo ID may cause some versions\n"
2954                            "         of PGP to reject this key.\n"));
2955
2956               if(!cpr_get_answer_is_yes("keyedit.v3_photo.okay",
2957                                         _("Are you sure you still want "
2958                                           "to add it? (y/N) ")))
2959                 return 0;
2960             }
2961           else
2962             {
2963               tty_printf(_("You may not add a photo ID to "
2964                            "a PGP2-style key.\n"));
2965               return 0;
2966             }
2967         }
2968
2969       uid = generate_photo_id(pk);
2970     } else
2971       uid = generate_user_id();
2972     if( !uid )
2973         return 0;
2974
2975     rc = make_keysig_packet( &sig, pk, uid, NULL, sk, 0x13, 0, 0, 0, 0,
2976                              keygen_add_std_prefs, pk );
2977     free_secret_key( sk );
2978     if( rc ) {
2979         log_error("signing failed: %s\n", g10_errstr(rc) );
2980         free_user_id(uid);
2981         return 0;
2982     }
2983
2984     /* insert/append to secret keyblock */
2985     pkt = m_alloc_clear( sizeof *pkt );
2986     pkt->pkttype = PKT_USER_ID;
2987     pkt->pkt.user_id = scopy_user_id(uid);
2988     node = new_kbnode(pkt);
2989     if( sec_where )
2990         insert_kbnode( sec_where, node, 0 );
2991     else
2992         add_kbnode( sec_keyblock, node );
2993     pkt = m_alloc_clear( sizeof *pkt );
2994     pkt->pkttype = PKT_SIGNATURE;
2995     pkt->pkt.signature = copy_signature(NULL, sig);
2996     if( sec_where )
2997         insert_kbnode( node, new_kbnode(pkt), 0 );
2998     else
2999         add_kbnode( sec_keyblock, new_kbnode(pkt) );
3000     /* insert/append to public keyblock */
3001     pkt = m_alloc_clear( sizeof *pkt );
3002     pkt->pkttype = PKT_USER_ID;
3003     pkt->pkt.user_id = uid;
3004     node = new_kbnode(pkt);
3005     if( pub_where )
3006         insert_kbnode( pub_where, node, 0 );
3007     else
3008         add_kbnode( pub_keyblock, node );
3009     pkt = m_alloc_clear( sizeof *pkt );
3010     pkt->pkttype = PKT_SIGNATURE;
3011     pkt->pkt.signature = copy_signature(NULL, sig);
3012     if( pub_where )
3013         insert_kbnode( node, new_kbnode(pkt), 0 );
3014     else
3015         add_kbnode( pub_keyblock, new_kbnode(pkt) );
3016     return 1;
3017 }
3018
3019
3020 /****************
3021  * Remove all selected userids from the keyrings
3022  */
3023 static void
3024 menu_deluid( KBNODE pub_keyblock, KBNODE sec_keyblock )
3025 {
3026     KBNODE node;
3027     int selected=0;
3028
3029     for( node = pub_keyblock; node; node = node->next ) {
3030         if( node->pkt->pkttype == PKT_USER_ID ) {
3031             selected = node->flag & NODFLG_SELUID;
3032             if( selected ) {
3033                 /* Only cause a trust update if we delete a
3034                    non-revoked user id */
3035                 if(!node->pkt->pkt.user_id->is_revoked)
3036                   update_trust=1;
3037                 delete_kbnode( node );
3038                 if( sec_keyblock ) {
3039                     KBNODE snode;
3040                     int s_selected = 0;
3041                     PKT_user_id *uid = node->pkt->pkt.user_id;
3042                     for( snode = sec_keyblock; snode; snode = snode->next ) {
3043                         if( snode->pkt->pkttype == PKT_USER_ID ) {
3044                             PKT_user_id *suid = snode->pkt->pkt.user_id;
3045
3046                             s_selected =
3047                                 (uid->len == suid->len
3048                                  && !memcmp( uid->name, suid->name, uid->len));
3049                             if( s_selected )
3050                                 delete_kbnode( snode );
3051                         }
3052                         else if( s_selected
3053                                  && snode->pkt->pkttype == PKT_SIGNATURE )
3054                             delete_kbnode( snode );
3055                         else if( snode->pkt->pkttype == PKT_SECRET_SUBKEY )
3056                             s_selected = 0;
3057                     }
3058                 }
3059             }
3060         }
3061         else if( selected && node->pkt->pkttype == PKT_SIGNATURE )
3062             delete_kbnode( node );
3063         else if( node->pkt->pkttype == PKT_PUBLIC_SUBKEY )
3064             selected = 0;
3065     }
3066     commit_kbnode( &pub_keyblock );
3067     if( sec_keyblock )
3068         commit_kbnode( &sec_keyblock );
3069 }
3070
3071
3072 static int
3073 menu_delsig( KBNODE pub_keyblock )
3074 {
3075     KBNODE node;
3076     PKT_user_id *uid = NULL;
3077     int changed=0;
3078
3079     for( node = pub_keyblock; node; node = node->next ) {
3080         if( node->pkt->pkttype == PKT_USER_ID ) {
3081             uid = (node->flag & NODFLG_SELUID)? node->pkt->pkt.user_id : NULL;
3082         }
3083         else if( uid && node->pkt->pkttype == PKT_SIGNATURE ) {
3084            int okay, valid, selfsig, inv_sig, no_key, other_err;
3085
3086             tty_printf("uid  ");
3087             tty_print_utf8_string( uid->name, uid->len );
3088             tty_printf("\n");
3089
3090             okay = inv_sig = no_key = other_err = 0;
3091             if(opt.with_colons)
3092               valid = print_and_check_one_sig_colon( pub_keyblock, node,
3093                                                &inv_sig, &no_key, &other_err,
3094                                                &selfsig, 1 );
3095             else
3096               valid = print_and_check_one_sig( pub_keyblock, node,
3097                                                &inv_sig, &no_key, &other_err,
3098                                                &selfsig, 1 );
3099
3100            if( valid ) {
3101                okay = cpr_get_answer_yes_no_quit(
3102                    "keyedit.delsig.valid",
3103                    _("Delete this good signature? (y/N/q)"));
3104
3105                /* Only update trust if we delete a good signature.
3106                   The other two cases do not affect trust. */
3107                if(okay)
3108                  update_trust=1;
3109            }
3110            else if( inv_sig || other_err )
3111                okay = cpr_get_answer_yes_no_quit(
3112                    "keyedit.delsig.invalid",
3113                    _("Delete this invalid signature? (y/N/q)"));
3114            else if( no_key )
3115                okay = cpr_get_answer_yes_no_quit(
3116                    "keyedit.delsig.unknown",
3117                    _("Delete this unknown signature? (y/N/q)"));
3118
3119             if( okay == -1 )
3120                 break;
3121            if( okay && selfsig && !cpr_get_answer_is_yes(
3122                                "keyedit.delsig.selfsig",
3123                               _("Really delete this self-signature? (y/N)") ))
3124                 okay = 0;
3125             if( okay ) {
3126                 delete_kbnode( node );
3127                 changed++;
3128             }
3129
3130         }
3131         else if( node->pkt->pkttype == PKT_PUBLIC_SUBKEY )
3132             uid = NULL;
3133     }
3134
3135     if( changed ) {
3136         commit_kbnode( &pub_keyblock );
3137         tty_printf( changed == 1? _("Deleted %d signature.\n")
3138                                 : _("Deleted %d signatures.\n"), changed );
3139     }
3140     else
3141         tty_printf( _("Nothing deleted.\n") );
3142
3143     return changed;
3144 }
3145
3146 static int
3147 menu_clean_sigs_from_uids(KBNODE keyblock)
3148 {
3149   KBNODE uidnode;
3150   int modified=0;
3151   int select_all=!count_selected_uids(keyblock);
3152
3153   for(uidnode=keyblock;uidnode;uidnode=uidnode->next)
3154     {
3155       if(uidnode->pkt->pkttype==PKT_USER_ID
3156          && (uidnode->flag&NODFLG_SELUID || select_all))
3157         {
3158           int deleted;
3159           char *user=utf8_to_native(uidnode->pkt->pkt.user_id->name,
3160                                     uidnode->pkt->pkt.user_id->len,
3161                                     0);
3162           deleted=clean_sigs_from_uid(keyblock,uidnode,opt.verbose);
3163           if(deleted)
3164             {
3165               tty_printf(deleted==1?
3166                          _("User ID \"%s\": %d signature removed.\n"):
3167                          _("User ID \"%s\": %d signatures removed.\n"),
3168                          user,deleted);
3169               modified=1;
3170             }
3171           else
3172             tty_printf(_("User ID \"%s\": already clean.\n"),user);
3173
3174           m_free(user);
3175         }
3176     }
3177
3178   return modified;
3179 }
3180
3181 static int
3182 menu_clean_uids_from_key(KBNODE keyblock)
3183 {
3184   KBNODE node;
3185   int modified;
3186
3187   modified=clean_uids_from_key(keyblock,opt.verbose);
3188
3189   if(modified)
3190     {
3191       for(node=keyblock->next;node;node=node->next)
3192         {
3193           if(node->pkt->pkttype==PKT_USER_ID && is_deleted_kbnode(node))
3194             {
3195               char *reason;
3196               char *user=utf8_to_native(node->pkt->pkt.user_id->name,
3197                                         node->pkt->pkt.user_id->len,0);
3198
3199               if(node->pkt->pkt.user_id->is_revoked)
3200                 reason=_("revoked");
3201               else if(node->pkt->pkt.user_id->is_expired)
3202                 reason=_("expired");
3203               else
3204                 reason=_("invalid");
3205
3206               tty_printf(_("User ID \"%s\" removed: %s\n"),user,reason);
3207
3208               m_free(user);
3209             }
3210         }
3211     }
3212   else
3213     tty_printf(_("No user IDs are removable.\n"));
3214
3215   return modified;
3216 }
3217
3218 /****************
3219  * Remove some of the secondary keys
3220  */
3221 static void
3222 menu_delkey( KBNODE pub_keyblock, KBNODE sec_keyblock )
3223 {
3224     KBNODE node;
3225     int selected=0;
3226
3227     for( node = pub_keyblock; node; node = node->next ) {
3228         if( node->pkt->pkttype == PKT_PUBLIC_SUBKEY ) {
3229             selected = node->flag & NODFLG_SELKEY;
3230             if( selected ) {
3231                 delete_kbnode( node );
3232                 if( sec_keyblock ) {
3233                     KBNODE snode;
3234                     int s_selected = 0;
3235                     u32 ki[2];
3236
3237                     keyid_from_pk( node->pkt->pkt.public_key, ki );
3238                     for( snode = sec_keyblock; snode; snode = snode->next ) {
3239                         if( snode->pkt->pkttype == PKT_SECRET_SUBKEY ) {
3240                             u32 ki2[2];
3241
3242                             keyid_from_sk( snode->pkt->pkt.secret_key, ki2 );
3243                             s_selected = (ki[0] == ki2[0] && ki[1] == ki2[1]);
3244                             if( s_selected )
3245                                 delete_kbnode( snode );
3246                         }
3247                         else if( s_selected
3248                                  && snode->pkt->pkttype == PKT_SIGNATURE )
3249                             delete_kbnode( snode );
3250                         else
3251