[svn] GnuPG - r5062 - in trunk: . sm tools

svn author wk cvs at cvs.gnupg.org
Thu Jul 2 11:49:32 CEST 2009


Author: wk
Date: 2009-07-02 11:49:31 +0200 (Thu, 02 Jul 2009)
New Revision: 5062

Modified:
   trunk/NEWS
   trunk/sm/ChangeLog
   trunk/sm/call-agent.c
   trunk/sm/certreqgen-ui.c
   trunk/sm/gpgsm.h
   trunk/tools/gpgsm-gencert.sh
Log:
Create a pkcs#10 request directly from a card.
Deprecate gpgsm-gencert.sh script.


Modified: trunk/sm/ChangeLog
===================================================================
--- trunk/sm/ChangeLog	2009-07-01 18:30:33 UTC (rev 5061)
+++ trunk/sm/ChangeLog	2009-07-02 09:49:31 UTC (rev 5062)
@@ -1,3 +1,11 @@
+2009-07-02  Werner Koch  <wk at g10code.com>
+
+	* certreqgen-ui.c (gpgsm_gencertreq_tty): Allow using a key from a
+	card.
+	* call-agent.c (gpgsm_agent_scd_serialno)
+	(scd_serialno_status_cb, store_serialno): New.
+	(scd_keypairinfo_status_cb, gpgsm_agent_scd_keypairinfo): New.
+
 2009-07-01  Werner Koch  <wk at g10code.com>
 
 	* certreqgen-ui.c (check_keygrip): New.

Modified: trunk/NEWS
===================================================================
--- trunk/NEWS	2009-07-01 18:30:33 UTC (rev 5061)
+++ trunk/NEWS	2009-07-02 09:49:31 UTC (rev 5062)
@@ -3,11 +3,13 @@
 
  This is a BETA version!
 
- * Minor bnug fixes
+ * Minor bug fixes.
 
- * gpgsm --gen-key now implements a --batch mode.
+ * gpgsm --gen-key implements a --batch mode.
 
+ * gpgsm --gen-key implements all features of gpgsm-gencert.sh.
 
+
 Noteworthy changes in version 2.0.12 (2009-06-17)
 -------------------------------------------------
 

Modified: trunk/sm/call-agent.c
===================================================================
--- trunk/sm/call-agent.c	2009-07-01 18:30:33 UTC (rev 5061)
+++ trunk/sm/call-agent.c	2009-07-02 09:49:31 UTC (rev 5062)
@@ -538,9 +538,151 @@
   return 0;
 }
 
+
 
+/* Take the serial number from LINE and return it verbatim in a newly
+   allocated string.  We make sure that only hex characters are
+   returned. */
+static char *
+store_serialno (const char *line)
+{
+  const char *s;
+  char *p;
 
+  for (s=line; hexdigitp (s); s++)
+    ;
+  p = xtrymalloc (s + 1 - line);
+  if (p)
+    {
+      memcpy (p, line, s-line);
+      p[s-line] = 0;
+    }
+  return p;
+}
+
+
+/* Callback for the gpgsm_agent_serialno fucntion.  */
 static int
+scd_serialno_status_cb (void *opaque, const char *line)
+{
+  char **r_serialno = opaque;
+  const char *keyword = line;
+  int keywordlen;
+
+  for (keywordlen=0; *line && !spacep (line); line++, keywordlen++)
+    ;
+  while (spacep (line))
+    line++;
+
+  if (keywordlen == 8 && !memcmp (keyword, "SERIALNO", keywordlen))
+    {
+      xfree (*r_serialno);
+      *r_serialno = store_serialno (line);
+    }
+
+  return 0;
+}
+
+
+/* Call the agent to read the serial number of the current card.  */
+int
+gpgsm_agent_scd_serialno (ctrl_t ctrl, char **r_serialno)
+{
+  int rc;
+  char *serialno = NULL;
+ 
+  *r_serialno = NULL;
+  rc = start_agent (ctrl);
+  if (rc)
+    return rc;
+
+  rc = assuan_transact (agent_ctx, "SCD SERIALNO",
+                        NULL, NULL,
+                        default_inq_cb, ctrl,
+                        scd_serialno_status_cb, &serialno);
+  if (!rc && !serialno)
+    rc = gpg_error (GPG_ERR_INTERNAL);
+  if (rc)
+    {
+      xfree (serialno);
+      return rc;
+    }
+  *r_serialno = serialno;
+  return 0;
+}
+
+
+
+/* Callback for the gpgsm_agent_serialno fucntion.  */
+static int
+scd_keypairinfo_status_cb (void *opaque, const char *line)
+{
+  strlist_t *listaddr = opaque;
+  const char *keyword = line;
+  int keywordlen;
+  strlist_t sl;
+  char *p;
+
+  for (keywordlen=0; *line && !spacep (line); line++, keywordlen++)
+    ;
+  while (spacep (line))
+    line++;
+
+  if (keywordlen == 11 && !memcmp (keyword, "KEYPAIRINFO", keywordlen))
+    {
+      sl = append_to_strlist (listaddr, line);
+      p = sl->d;
+      /* Make sure that we only have two tokes so that future
+         extensions of the format won't change the format expected by
+         the caller.  */
+      while (*p && !spacep (p))
+        p++;
+      if (*p)
+        {
+          while (spacep (p))
+            p++;
+          while (*p && !spacep (p))
+            p++;
+          *p = 0;
+        }
+    }
+
+  return 0;
+}
+
+
+/* Call the agent to read the keypairinfo lines of the current card.
+   The list is returned as a string made up of the keygrip, a space
+   and the keyid.  */
+int
+gpgsm_agent_scd_keypairinfo (ctrl_t ctrl, strlist_t *r_list)
+{
+  int rc;
+  strlist_t list = NULL;
+ 
+  *r_list = NULL;
+  rc = start_agent (ctrl);
+  if (rc)
+    return rc;
+
+  rc = assuan_transact (agent_ctx, "SCD LEARN --force",
+                        NULL, NULL,
+                        default_inq_cb, ctrl,
+                        scd_keypairinfo_status_cb, &list);
+  if (!rc && !list)
+    rc = gpg_error (GPG_ERR_NO_DATA);
+  if (rc)
+    {
+      free_strlist (list);
+      return rc;
+    }
+  *r_list = list;
+  return 0;
+}
+
+
+
+static int
 istrusted_status_cb (void *opaque, const char *line)
 {
   struct rootca_flags_s *flags = opaque;

Modified: trunk/sm/certreqgen-ui.c
===================================================================
--- trunk/sm/certreqgen-ui.c	2009-07-01 18:30:33 UTC (rev 5061)
+++ trunk/sm/certreqgen-ui.c	2009-07-02 09:49:31 UTC (rev 5062)
@@ -97,8 +97,8 @@
   size_t publiclen;
   int algo;
 
-  if (hexgrip[0] == '0' && hexgrip[1] == 'x')
-    hexgrip += 2;
+  if (hexgrip[0] == '&')
+    hexgrip++;
 
   err = gpgsm_agent_readkey (ctrl, 0, hexgrip, &public);
   if (err)
@@ -132,6 +132,7 @@
   int selection;
   estream_t fp = NULL;
   int method;
+  char *keytype_buffer = NULL;
   const char *keytype;
   char *keygrip = NULL;
   unsigned int nbits;
@@ -205,24 +206,70 @@
           if (!*answer)
             goto again;
           else if (strlen (answer) != 40 &&
-                   !(answer[0] == '0' && answer[1] == 'x' 
-                     && strlen (answer+2) == 40))
+                   !(answer[0] == '&' && strlen (answer+1) == 40))
             tty_printf (_("Not a valid keygrip (expecting 40 hex digits)\n"));
           else if (!(keytype = check_keygrip (ctrl, answer)) )
             tty_printf (_("No key with this keygrip\n"));
           else
             break; /* Okay.  */
         }
-      nbits = 1024; /* A dummy value is sufficient.  */
       xfree (keygrip);
       keygrip = answer;
       answer = NULL;
+      nbits = 1024; /* A dummy value is sufficient.  */
     }
   else /* method == 3 */
     {
-      tty_printf ("Not yet supported; "
-                  "use the gpgsm-gencert.sh script instead\n");
-      goto again;
+      char *serialno;
+      strlist_t keypairlist, sl;
+      int count;
+
+      err = gpgsm_agent_scd_serialno (ctrl, &serialno);
+      if (err)
+        {
+          tty_printf (_("error reading the card: %s\n"), gpg_strerror (err));
+          goto again;
+        }
+      tty_printf (_("Serial number of the card: %s\n"), serialno);
+      xfree (serialno);
+
+      err = gpgsm_agent_scd_keypairinfo (ctrl, &keypairlist);
+      if (err)
+        {
+          tty_printf (_("error reading the card: %s\n"), gpg_strerror (err));
+          goto again;
+        }
+
+      do
+        {
+          tty_printf (_("Available keys:\n"));
+          for (count=1,sl=keypairlist; sl; sl = sl->next, count++)
+            tty_printf ("   (%d) %s\n", count, sl->d);
+          xfree (answer);
+          answer = tty_get (_("Your selection? "));
+          tty_kill_prompt ();
+          trim_spaces (answer);
+          selection = atoi (answer);
+        }
+      while (!(selection > 0 && selection < count));
+
+      for (count=1,sl=keypairlist; sl; sl = sl->next, count++)
+        if (count == selection)
+          break;
+
+      s = sl->d;
+      while (*s && !spacep (s))
+        s++;
+      while (spacep (s))
+        s++;
+
+      xfree (keygrip);
+      keygrip = NULL;
+      xfree (keytype_buffer);
+      keytype_buffer = xasprintf ("card:%s", s);
+      free_strlist (keypairlist);
+      keytype = keytype_buffer;
+      nbits = 1024; /* A dummy value is sufficient.  */
     }
 
   /* Ask for the key usage.  */
@@ -358,6 +405,7 @@
   es_fclose (fp);
   xfree (answer);
   xfree (subject_name);
+  xfree (keytype_buffer);
   xfree (keygrip);
   xfree (get_membuf (&mb_email, NULL));
   xfree (get_membuf (&mb_dns, NULL));

Modified: trunk/sm/gpgsm.h
===================================================================
--- trunk/sm/gpgsm.h	2009-07-01 18:30:33 UTC (rev 5061)
+++ trunk/sm/gpgsm.h	2009-07-02 09:49:31 UTC (rev 5062)
@@ -388,6 +388,8 @@
                         ksba_const_sexp_t keyparms, ksba_sexp_t *r_pubkey);
 int gpgsm_agent_readkey (ctrl_t ctrl, int fromcard, const char *hexkeygrip,
                          ksba_sexp_t *r_pubkey);
+int gpgsm_agent_scd_serialno (ctrl_t ctrl, char **r_serialno);
+int gpgsm_agent_scd_keypairinfo (ctrl_t ctrl, strlist_t *r_list);
 int gpgsm_agent_istrusted (ctrl_t ctrl, ksba_cert_t cert, const char *hexfpr,
                            struct rootca_flags_s *rootca_flags);
 int gpgsm_agent_havekey (ctrl_t ctrl, const char *hexkeygrip);

Modified: trunk/tools/gpgsm-gencert.sh
===================================================================
--- trunk/tools/gpgsm-gencert.sh	2009-07-01 18:30:33 UTC (rev 5061)
+++ trunk/tools/gpgsm-gencert.sh	2009-07-02 09:49:31 UTC (rev 5062)
@@ -83,7 +83,9 @@
 }
 
 
-
+echo "WARNING: This script is deprecated; please use" >&2
+echo "           gpgsm --gen-key" >&2
+echo "         instead." >&2
 KEY_TYPE=""
 while [ -z "$KEY_TYPE" ]; do
   query_user_menu "Key type" "RSA" "Existing key" "Direct from card"




More information about the Gnupg-commits mailing list