summaryrefslogtreecommitdiffstats
path: root/kbx
diff options
context:
space:
mode:
authorWerner Koch <wk@gnupg.org>2006-10-20 13:38:48 +0200
committerWerner Koch <wk@gnupg.org>2006-10-20 13:38:48 +0200
commit58785c880d4540e0f75738b3b10a8a03c35d5ee1 (patch)
tree3b1a8732c3d3f8132bfaab9447a9252d4235b852 /kbx
parent* gpgkeys_hkp.c (curl_mrindex_writer): Print a warning if we see HTML (diff)
downloadgnupg2-58785c880d4540e0f75738b3b10a8a03c35d5ee1.tar.xz
gnupg2-58785c880d4540e0f75738b3b10a8a03c35d5ee1.zip
Allow to select X.509 certificates using the keygrip.
Diffstat (limited to 'kbx')
-rw-r--r--kbx/ChangeLog7
-rw-r--r--kbx/keybox-search-desc.h2
-rw-r--r--kbx/keybox-search.c84
3 files changed, 93 insertions, 0 deletions
diff --git a/kbx/ChangeLog b/kbx/ChangeLog
index 8a3c66596..52962eae0 100644
--- a/kbx/ChangeLog
+++ b/kbx/ChangeLog
@@ -1,3 +1,10 @@
+2006-10-20 Werner Koch <wk@g10code.com>
+
+ * keybox-search.c (blob_x509_has_grip, has_keygrip): New.
+ (keybox_search): Implement new search mode.
+ * keybox-search-desc.h (KEYDB_SEARCH_MODE_KEYGRIP): New.
+ (keydb_search_desc): New member GRIP.
+
2006-09-20 Werner Koch <wk@g10code.com>
* Makefile.am ($(PROGRAMS): New.
diff --git a/kbx/keybox-search-desc.h b/kbx/keybox-search-desc.h
index f3a69d0f1..16668e8fc 100644
--- a/kbx/keybox-search-desc.h
+++ b/kbx/keybox-search-desc.h
@@ -45,6 +45,7 @@ typedef enum {
KEYDB_SEARCH_MODE_ISSUER_SN,
KEYDB_SEARCH_MODE_SN,
KEYDB_SEARCH_MODE_SUBJECT,
+ KEYDB_SEARCH_MODE_KEYGRIP,
KEYDB_SEARCH_MODE_FIRST,
KEYDB_SEARCH_MODE_NEXT
} KeydbSearchMode;
@@ -59,6 +60,7 @@ struct keydb_search_desc {
const char *name;
unsigned char fpr[24];
unsigned char kid[8];
+ unsigned char grip[20];
} u;
};
diff --git a/kbx/keybox-search.c b/kbx/keybox-search.c
index f95e6eb06..5a205a813 100644
--- a/kbx/keybox-search.c
+++ b/kbx/keybox-search.c
@@ -29,6 +29,7 @@
#include "../jnlib/stringhelp.h" /* ascii_xxxx() */
#include "keybox-defs.h"
+#include <gcrypt.h>
#define xtoi_1(p) (*(p) <= '9'? (*(p)- '0'): \
@@ -456,6 +457,75 @@ blob_cmp_mail (KEYBOXBLOB blob, const char *name, size_t namelen, int substr)
}
+#ifdef KEYBOX_WITH_X509
+/* Return true if the key in BLOB matches the 20 bytes keygrip GRIP.
+ We don't have the keygrips as meta data, thus wen need to parse the
+ certificate. Fixme: We might wat to return proper error codes
+ instead of failing a search for invalid certificates etc. */
+static int
+blob_x509_has_grip (KEYBOXBLOB blob, const unsigned char *grip)
+{
+ int rc;
+ const unsigned char *buffer;
+ size_t length;
+ size_t cert_off, cert_len;
+ ksba_reader_t reader = NULL;
+ ksba_cert_t cert = NULL;
+ ksba_sexp_t p = NULL;
+ gcry_sexp_t s_pkey;
+ unsigned char array[20];
+ unsigned char *rcp;
+ size_t n;
+
+ buffer = _keybox_get_blob_image (blob, &length);
+ if (length < 40)
+ return 0; /* Too short. */
+ cert_off = get32 (buffer+8);
+ cert_len = get32 (buffer+12);
+ if (cert_off+cert_len > length)
+ return 0; /* Too short. */
+
+ rc = ksba_reader_new (&reader);
+ if (rc)
+ return 0; /* Problem with ksba. */
+ rc = ksba_reader_set_mem (reader, buffer+cert_off, cert_len);
+ if (rc)
+ goto failed;
+ rc = ksba_cert_new (&cert);
+ if (rc)
+ goto failed;
+ rc = ksba_cert_read_der (cert, reader);
+ if (rc)
+ goto failed;
+ p = ksba_cert_get_public_key (cert);
+ if (!p)
+ goto failed;
+ n = gcry_sexp_canon_len (p, 0, NULL, NULL);
+ if (!n)
+ goto failed;
+ rc = gcry_sexp_sscan (&s_pkey, NULL, (char*)p, n);
+ if (rc)
+ {
+ gcry_sexp_release (s_pkey);
+ goto failed;
+ }
+ rcp = gcry_pk_get_keygrip (s_pkey, array);
+ gcry_sexp_release (s_pkey);
+ if (!rcp)
+ goto failed; /* Can't calculate keygrip. */
+
+ xfree (p);
+ ksba_cert_release (cert);
+ ksba_reader_release (reader);
+ return !memcmp (array, grip, 20);
+ failed:
+ xfree (p);
+ ksba_cert_release (cert);
+ ksba_reader_release (reader);
+ return 0;
+}
+#endif /*KEYBOX_WITH_X509*/
+
/*
@@ -479,6 +549,16 @@ has_fingerprint (KEYBOXBLOB blob, const unsigned char *fpr)
return blob_cmp_fpr (blob, fpr);
}
+static inline int
+has_keygrip (KEYBOXBLOB blob, const unsigned char *grip)
+{
+#ifdef KEYBOX_WITH_X509
+ if (blob_get_type (blob) == BLOBTYPE_X509)
+ return blob_x509_has_grip (blob, grip);
+#endif
+ return 0;
+}
+
static inline int
has_issuer (KEYBOXBLOB blob, const char *name)
@@ -809,6 +889,10 @@ keybox_search (KEYBOX_HANDLE hd, KEYBOX_SEARCH_DESC *desc, size_t ndesc)
if (has_fingerprint (blob, desc[n].u.fpr))
goto found;
break;
+ case KEYDB_SEARCH_MODE_KEYGRIP:
+ if (has_keygrip (blob, desc[n].u.grip))
+ goto found;
+ break;
case KEYDB_SEARCH_MODE_FIRST:
goto found;
break;