* main.h, keygen.c (keygen_add_keyserver_url): Signature callback for
authorDavid Shaw <dshaw@jabberwocky.com>
Sun, 31 Aug 2003 03:45:41 +0000 (03:45 +0000)
committerDavid Shaw <dshaw@jabberwocky.com>
Sun, 31 Aug 2003 03:45:41 +0000 (03:45 +0000)
adding a keyserver URL.

* keyedit.c (keyedit_menu, menu_set_keyserver_url): New command to set
preferred keyserver to specified (or all) user IDs.

* build-packet.c (build_sig_subpkt): Set preferred keyserver flag while
building a preferred keyserver subpacket.

* keylist.c (show_policy_url): Policy URLs might be UTF8.

* keyedit.c (menu_addrevoker): Fix leaking a few bytes.

g10/ChangeLog
g10/build-packet.c
g10/keyedit.c
g10/keygen.c
g10/keylist.c
g10/main.h

index c683455..c3a6ecf 100644 (file)
@@ -1,3 +1,18 @@
+2003-08-30  David Shaw  <dshaw@jabberwocky.com>
+
+       * main.h, keygen.c (keygen_add_keyserver_url): Signature callback
+       for adding a keyserver URL.
+
+       * keyedit.c (keyedit_menu, menu_set_keyserver_url): New command to
+       set preferred keyserver to specified (or all) user IDs.
+
+       * build-packet.c (build_sig_subpkt): Set preferred keyserver flag
+       while building a preferred keyserver subpacket.
+
+       * keylist.c (show_policy_url): Policy URLs might be UTF8.
+
+       * keyedit.c (menu_addrevoker): Fix leaking a few bytes.
+
 2003-08-29  David Shaw  <dshaw@jabberwocky.com>
 
        * keyedit.c (show_key_with_all_names): Use list-option
index 86aa07d..af97be4 100644 (file)
@@ -747,6 +747,10 @@ build_sig_subpkt (PKT_signature *sig, sigsubpkttype_t type,
        sig->flags.policy_url=1;
        break;
 
+      case SIGSUBPKT_PREF_KS:
+       sig->flags.pref_ks=1;
+       break;
+
       case SIGSUBPKT_EXPORTABLE:
        if(buffer[0])
          sig->flags.exportable=1;
index 5b6f4f9..db1589a 100644 (file)
@@ -55,6 +55,7 @@ static int menu_addrevoker( KBNODE pub_keyblock,
 static int menu_expire( KBNODE pub_keyblock, KBNODE sec_keyblock );
 static int menu_set_primary_uid( KBNODE pub_keyblock, KBNODE sec_keyblock );
 static int menu_set_preferences( KBNODE pub_keyblock, KBNODE sec_keyblock );
+static int menu_set_keyserver_url (KBNODE pub_keyblock, KBNODE sec_keyblock );
 static int menu_select_uid( KBNODE keyblock, int idx );
 static int menu_select_key( KBNODE keyblock, int idx );
 static int count_uids( KBNODE keyblock );
@@ -173,6 +174,9 @@ print_and_check_one_sig( KBNODE keyblock, KBNODE node,
 
        if(sig->flags.notation && (opt.list_options&LIST_SHOW_NOTATION))
          show_notation(sig,3,0);
+
+       if(sig->flags.pref_ks && (opt.list_options&LIST_SHOW_KEYSERVER))
+         show_keyserver_url(sig,3,0);
     }
 
     return (sigrc == '!');
@@ -1106,7 +1110,8 @@ keyedit_menu( const char *username, STRLIST locusr, STRLIST commands,
           cmdADDPHOTO, cmdDELUID, cmdADDKEY, cmdDELKEY, cmdADDREVOKER,
           cmdTOGGLE, cmdSELKEY, cmdPASSWD, cmdTRUST, cmdPREF, cmdEXPIRE,
           cmdENABLEKEY, cmdDISABLEKEY, cmdSHOWPREF, cmdSETPREF, cmdUPDPREF,
-          cmdINVCMD, cmdSHOWPHOTO, cmdUPDTRUST, cmdCHKTRUST, cmdNOP };
+          cmdPREFKS, cmdINVCMD, cmdSHOWPHOTO, cmdUPDTRUST, cmdCHKTRUST,
+          cmdNOP };
     static struct { const char *name;
                    enum cmdids id;
                    int need_sk;
@@ -1151,6 +1156,7 @@ keyedit_menu( const char *username, STRLIST locusr, STRLIST commands,
        { N_("showpref"), cmdSHOWPREF  , 0,1,0, N_("list preferences (verbose)") },
        { N_("setpref") , cmdSETPREF   , 1,1,0, N_("set preference list") },
        { N_("updpref") , cmdUPDPREF   , 1,1,0, N_("updated preferences") },
+       { N_("keyserver"),cmdPREFKS    , 1,1,0, N_("set preferred keyserver")},
        { N_("passwd")  , cmdPASSWD    , 1,1,0, N_("change the passphrase") },
        { N_("trust")   , cmdTRUST     , 0,1,0, N_("change the ownertrust") },
        { N_("revsig")  , cmdREVSIG    , 0,1,0, N_("revoke signatures") },
@@ -1604,6 +1610,14 @@ keyedit_menu( const char *username, STRLIST locusr, STRLIST commands,
             }
            break;
 
+         case cmdPREFKS:
+           if( menu_set_keyserver_url ( keyblock, sec_keyblock ) ) {
+               merge_keys_and_selfsig( keyblock );
+               modified = 1;
+               redisplay = 1;
+           }
+           break;
+
          case cmdNOP:
            break;
 
@@ -2654,16 +2668,22 @@ menu_addrevoker( KBNODE pub_keyblock, KBNODE sec_keyblock, int sensitive )
       answer=cpr_get_utf8("keyedit.add_revoker",
                          _("Enter the user ID of the designated revoker: "));
       if(answer[0]=='\0' || answer[0]=='\004')
-       goto fail;
+       {
+         m_free(answer);
+         goto fail;
+       }
 
       rc=get_pubkey_byname(revoker_pk,answer,NULL,NULL,1);
 
       if(rc)
        {
          log_error (_("key `%s' not found: %s\n"),answer,g10_errstr(rc));
+         m_free(answer);
          continue;
        }
 
+      m_free(answer);
+
       fingerprint_from_pk(revoker_pk,revkey.fpr,&fprlen);
       if(fprlen!=20)
        {
@@ -3140,6 +3160,100 @@ menu_set_preferences (KBNODE pub_keyblock, KBNODE sec_keyblock )
 }
 
 
+static int
+menu_set_keyserver_url (KBNODE pub_keyblock, KBNODE sec_keyblock )
+{
+    PKT_secret_key *sk;    /* copy of the main sk */
+    PKT_public_key *main_pk;
+    PKT_user_id *uid;
+    KBNODE node;
+    u32 keyid[2];
+    int selected, select_all;
+    int modified = 0;
+    char *answer;
+
+    no_primary_warning(pub_keyblock,1);
+
+    answer=cpr_get_utf8("keyedit.add_keyserver",
+                       _("Enter your preferred keyserver URL: "));
+    if(answer[0]=='\0' || answer[0]=='\004')
+      {
+       m_free(answer);
+       return 0;
+      }
+
+    select_all = !count_selected_uids (pub_keyblock);
+
+    node = find_kbnode( sec_keyblock, PKT_SECRET_KEY );
+    sk = copy_secret_key( NULL, node->pkt->pkt.secret_key);
+
+    /* Now we can actually change the self signature(s) */
+    main_pk = NULL;
+    uid = NULL;
+    selected = 0;
+    for ( node=pub_keyblock; node; node = node->next ) {
+       if ( node->pkt->pkttype == PKT_PUBLIC_SUBKEY )
+            break; /* ready */
+
+       if ( node->pkt->pkttype == PKT_PUBLIC_KEY ) {
+           main_pk = node->pkt->pkt.public_key;
+           keyid_from_pk( main_pk, keyid );
+       }
+       else if ( node->pkt->pkttype == PKT_USER_ID ) {
+           uid = node->pkt->pkt.user_id;
+                   selected = select_all || (node->flag & NODFLG_SELUID);
+        }
+       else if ( main_pk && uid && selected
+                  && node->pkt->pkttype == PKT_SIGNATURE ) {
+           PKT_signature *sig = node->pkt->pkt.signature;
+           if ( keyid[0] == sig->keyid[0] && keyid[1] == sig->keyid[1]
+                && (uid && (sig->sig_class&~3) == 0x10) ) {
+             if( sig->version < 4 ) {
+               char *user=utf8_to_native(uid->name,strlen(uid->name),0);
+
+               log_info(_("skipping v3 self-signature on user id \"%s\"\n"),
+                        user);
+               m_free(user);
+             }
+             else {
+               /* This is a selfsignature which is to be replaced 
+                 * We have to ignore v3 signatures because they are
+                 * not able to carry the preferences */
+               PKT_signature *newsig;
+               PACKET *newpkt;
+                int rc;
+
+                rc = update_keysig_packet (&newsig, sig,
+                                           main_pk, uid, NULL,
+                                           sk,
+                                           keygen_add_keyserver_url,
+                                           answer );
+                if( rc ) {
+                    log_error ("update_keysig_packet failed: %s\n",
+                               g10_errstr(rc));
+                   m_free(answer);
+                   free_secret_key( sk );
+                    return 0;
+                }
+                /* replace the packet */
+                newpkt = m_alloc_clear( sizeof *newpkt );
+                newpkt->pkttype = PKT_SIGNATURE;
+                newpkt->pkt.signature = newsig;
+                free_packet( node->pkt );
+                m_free( node->pkt );
+                node->pkt = newpkt;
+                modified = 1;
+             }
+            }
+       }
+    }
+
+    m_free(answer);
+    free_secret_key( sk );
+    return modified;
+}
+
+
 /****************
  * Select one user id or remove all selection if index is 0.
  * Returns: True if the selection changed;
index edf9bad..4b736e1 100644 (file)
@@ -581,6 +581,16 @@ keygen_add_std_prefs( PKT_signature *sig, void *opaque )
 }
 
 int
+keygen_add_keyserver_url(PKT_signature *sig, void *opaque)
+{
+  const char *url=opaque;
+
+  build_sig_subpkt(sig,SIGSUBPKT_PREF_KS,url,strlen(url));
+
+  return 0;
+}
+
+int
 keygen_add_revkey(PKT_signature *sig, void *opaque)
 {
   struct revocation_key *revkey=opaque;
index dace1e7..c5f6bb7 100644 (file)
@@ -174,7 +174,6 @@ show_policy_url(PKT_signature *sig,int indent,int mode)
          for(i=0;i<indent;i++)
            putchar(' ');
 
-         /* This isn't UTF8 as it is a URL(?) */
          if(crit)
            str=_("Critical signature policy: ");
          else
@@ -183,7 +182,7 @@ show_policy_url(PKT_signature *sig,int indent,int mode)
            log_info("%s",str);
          else
            printf("%s",str);
-         print_string(fp,p,len,0);
+         print_utf8_string(fp,p,len);
          fprintf(fp,"\n");
        }
 
@@ -216,7 +215,6 @@ show_keyserver_url(PKT_signature *sig,int indent,int mode)
          for(i=0;i<indent;i++)
            putchar(' ');
 
-         /* This isn't UTF8 as it is a URL(?) */
          if(crit)
            str=_("Critical preferred keyserver: ");
          else
@@ -225,7 +223,7 @@ show_keyserver_url(PKT_signature *sig,int indent,int mode)
            log_info("%s",str);
          else
            printf("%s",str);
-         print_string(fp,p,len,0);
+         print_utf8_string(fp,p,len);
          fprintf(fp,"\n");
        }
 
index 285500c..4da7724 100644 (file)
@@ -149,6 +149,7 @@ PKT_user_id *keygen_get_std_prefs (void);
 int keygen_add_key_expire( PKT_signature *sig, void *opaque );
 int keygen_add_std_prefs( PKT_signature *sig, void *opaque );
 int keygen_upd_std_prefs( PKT_signature *sig, void *opaque );
+int keygen_add_keyserver_url(PKT_signature *sig, void *opaque);
 int keygen_add_revkey(PKT_signature *sig, void *opaque);
 int generate_subkeypair( KBNODE pub_keyblock, KBNODE sec_keyblock );