2006-06-09 Marcus Brinkmann <marcus@g10code.de>
[gnupg.git] / sm / fingerprint.c
index ec1ed91..9441483 100644 (file)
@@ -42,8 +42,9 @@
    If there is a problem , the function does never return NULL but a
    digest of all 0xff.
  */
-char *
-gpgsm_get_fingerprint (KsbaCert cert, int algo, char *array, int *r_len)
+unsigned char *
+gpgsm_get_fingerprint (ksba_cert_t cert, int algo,
+                       unsigned char *array, int *r_len)
 {
   gcry_md_hd_t md;
   int rc, len;
@@ -83,7 +84,7 @@ gpgsm_get_fingerprint (KsbaCert cert, int algo, char *array, int *r_len)
 
 /* Return an allocated buffer with the formatted fingerprint */
 char *
-gpgsm_get_fingerprint_string (KsbaCert cert, int algo)
+gpgsm_get_fingerprint_string (ksba_cert_t cert, int algo)
 {
   unsigned char digest[MAX_DIGEST_LEN];
   char *buf;
@@ -105,7 +106,7 @@ gpgsm_get_fingerprint_string (KsbaCert cert, int algo)
 /* Return an allocated buffer with the formatted fingerprint as one
    large hexnumber */
 char *
-gpgsm_get_fingerprint_hexstring (KsbaCert cert, int algo)
+gpgsm_get_fingerprint_hexstring (ksba_cert_t cert, int algo)
 {
   unsigned char digest[MAX_DIGEST_LEN];
   char *buf;
@@ -127,7 +128,7 @@ gpgsm_get_fingerprint_hexstring (KsbaCert cert, int algo)
 /* Return a certificate ID.  These are the last 4 bytes of the SHA-1
    fingerprint. */
 unsigned long
-gpgsm_get_short_fingerprint (KsbaCert cert)
+gpgsm_get_short_fingerprint (ksba_cert_t cert)
 {
   unsigned char digest[20];
 
@@ -140,12 +141,12 @@ gpgsm_get_short_fingerprint (KsbaCert cert)
    key parameters expressed as an canoncial encoded S-Exp.  array must
    be 20 bytes long. returns the array or a newly allocated one if the
    passed one was NULL */
-char *
-gpgsm_get_keygrip (KsbaCert cert, char *array)
+unsigned char *
+gpgsm_get_keygrip (ksba_cert_t cert, unsigned char *array)
 {
   gcry_sexp_t s_pkey;
   int rc;
-  KsbaSexp p;
+  ksba_sexp_t p;
   size_t n;
   
   p = ksba_cert_get_public_key (cert);
@@ -153,14 +154,14 @@ gpgsm_get_keygrip (KsbaCert cert, char *array)
     return NULL; /* oops */
 
   if (DBG_X509)
-    log_debug ("get_keygrip for public key: %s\n", p);
+    log_debug ("get_keygrip for public key\n");
   n = gcry_sexp_canon_len (p, 0, NULL, NULL);
   if (!n)
     {
       log_error ("libksba did not return a proper S-Exp\n");
       return NULL;
     }
-  rc = gcry_sexp_sscan ( &s_pkey, NULL, p, n);
+  rc = gcry_sexp_sscan ( &s_pkey, NULL, (char*)p, n);
   xfree (p);
   if (rc)
     {
@@ -184,7 +185,7 @@ gpgsm_get_keygrip (KsbaCert cert, char *array)
 /* Return an allocated buffer with the keygrip of CERT in from of an
    hexstring.  NULL is returned in case of error */
 char *
-gpgsm_get_keygrip_hexstring (KsbaCert cert)
+gpgsm_get_keygrip_hexstring (ksba_cert_t cert)
 {
   unsigned char grip[20];
   char *buf, *p;
@@ -198,6 +199,66 @@ gpgsm_get_keygrip_hexstring (KsbaCert cert)
 }
 
 
+/* Return the PK algorithm used by CERT as well as the length in bits
+   of the public key at NBITS. */
+int
+gpgsm_get_key_algo_info (ksba_cert_t cert, unsigned int *nbits)
+{
+  gcry_sexp_t s_pkey;
+  int rc;
+  ksba_sexp_t p;
+  size_t n;
+  gcry_sexp_t l1, l2;
+  const char *name;
+  char namebuf[128];
+
+  if (nbits)
+    *nbits = 0;
+
+  p = ksba_cert_get_public_key (cert);
+  if (!p)
+    return 0; 
+  n = gcry_sexp_canon_len (p, 0, NULL, NULL);
+  if (!n)
+    {
+      xfree (p);
+      return 0;
+    }
+  rc = gcry_sexp_sscan (&s_pkey, NULL, (char *)p, n);
+  xfree (p);
+  if (rc)
+    return 0;
+
+  if (nbits)
+    *nbits = gcry_pk_get_nbits (s_pkey);
+
+  /* Breaking the algorithm out of the S-exp is a bit of a challenge ... */
+  l1 = gcry_sexp_find_token (s_pkey, "public-key", 0);
+  if (!l1)
+    {
+      gcry_sexp_release (s_pkey);
+      return 0;
+    }
+  l2 = gcry_sexp_cadr (l1);
+  gcry_sexp_release (l1);
+  l1 = l2;
+  name = gcry_sexp_nth_data (l1, 0, &n);
+  if (name)
+    {
+      if (n > sizeof namebuf -1)
+        n = sizeof namebuf -1;
+      memcpy (namebuf, name, n);
+      namebuf[n] = 0;
+    }
+  else
+    *namebuf = 0;
+  gcry_sexp_release (l1);
+  gcry_sexp_release (s_pkey);
+  return gcry_pk_map_name (namebuf);
+}
+
+
+
 \f
 /* For certain purposes we need a certificate id which has an upper
    limit of the size.  We use the hash of the issuer name and the
@@ -209,10 +270,10 @@ gpgsm_get_keygrip_hexstring (KsbaCert cert)
    The caller must free the string.
 */
 char *
-gpgsm_get_certid (KsbaCert cert)
+gpgsm_get_certid (ksba_cert_t cert)
 {
-  KsbaSexp serial;
-  unsigned char *p;
+  ksba_sexp_t serial;
+  char *p;
   char *endp;
   unsigned char hash[20];
   unsigned long n;
@@ -228,7 +289,7 @@ gpgsm_get_certid (KsbaCert cert)
   serial = ksba_cert_get_serial (cert);
   if (!serial)
     return NULL; /* oops: no serial number */
-  p = serial;
+  p = (char *)serial;
   if (*p != '(')
     {
       log_error ("Ooops: invalid serial number\n");
@@ -257,7 +318,7 @@ gpgsm_get_certid (KsbaCert cert)
     sprintf (endp, "%02X", hash[i]);
   *endp++ = '.';
   for (i=0; i < n; i++, endp += 2)
-    sprintf (endp, "%02X", p[i]);
+    sprintf (endp, "%02X", ((unsigned char*)p)[i]);
   *endp = 0;
 
   xfree (serial);
@@ -267,5 +328,3 @@ gpgsm_get_certid (KsbaCert cert)
 
 
 
-
-