1
0
mirror of git://git.gnupg.org/gnupg.git synced 2024-05-28 21:50:02 +02:00

kbx: Let keydb_search skip unwanted blobs.

* kbx/keybox.h (keybox_blobtype_t): New.
* kbx/keybox-defs.h (BLOBTYPE_*): Replace by KEYBOX_BLOBTYPE_*.
* kbx/keybox-search.c (keybox_search): Add arg want_blobtype and skip
non-matching blobs.
* sm/keydb.c (keydb_search): Pass KEYBOX_BLOBTYPE_X509 to keybox_search.
* g10/keydb.c (keydb_search): Pass KEYBOX_BLOBTYPE_PGP to keybox_search.
--

Without this fix a listing of all keys would fail because the wrong
blob type would be returned for the gpg or gpgsm.

Signed-off-by: Werner Koch <wk@gnupg.org>
This commit is contained in:
Werner Koch 2014-10-31 12:15:34 +01:00
parent 28ae8ad70b
commit 935edf88ab
9 changed files with 61 additions and 51 deletions

View File

@ -1448,7 +1448,8 @@ keydb_search (KEYDB_HANDLE hd, KEYDB_SEARCH_DESC *desc,
break; break;
case KEYDB_RESOURCE_TYPE_KEYBOX: case KEYDB_RESOURCE_TYPE_KEYBOX:
rc = keybox_search (hd->active[hd->current].u.kb, desc, rc = keybox_search (hd->active[hd->current].u.kb, desc,
ndesc, descindex, &hd->skipped_long_blobs); ndesc, KEYBOX_BLOBTYPE_PGP,
descindex, &hd->skipped_long_blobs);
break; break;
} }
if (rc == -1 || gpg_err_code (rc) == GPG_ERR_EOF) if (rc == -1 || gpg_err_code (rc) == GPG_ERR_EOF)

View File

@ -591,7 +591,7 @@ create_blob_header (KEYBOXBLOB blob, int blobtype, int as_ephemeral)
/* space where we write keyIDs and and other stuff so that the /* space where we write keyIDs and and other stuff so that the
pointers can actually point to somewhere */ pointers can actually point to somewhere */
if (blobtype == BLOBTYPE_PGP) if (blobtype == KEYBOX_BLOBTYPE_PGP)
{ {
/* We need to store the keyids for all pgp v3 keys because those key /* We need to store the keyids for all pgp v3 keys because those key
IDs are not part of the fingerprint. While we are doing that, we IDs are not part of the fingerprint. While we are doing that, we
@ -611,7 +611,7 @@ create_blob_header (KEYBOXBLOB blob, int blobtype, int as_ephemeral)
} }
} }
if (blobtype == BLOBTYPE_X509) if (blobtype == KEYBOX_BLOBTYPE_X509)
{ {
/* We don't want to point to ASN.1 encoded UserIDs (DNs) but to /* We don't want to point to ASN.1 encoded UserIDs (DNs) but to
the utf-8 string represenation of them */ the utf-8 string represenation of them */
@ -750,7 +750,7 @@ _keybox_create_openpgp_blob (KEYBOXBLOB *r_blob,
init_membuf (&blob->bufbuf, 1024); init_membuf (&blob->bufbuf, 1024);
blob->buf = &blob->bufbuf; blob->buf = &blob->bufbuf;
err = create_blob_header (blob, BLOBTYPE_PGP, as_ephemeral); err = create_blob_header (blob, KEYBOX_BLOBTYPE_PGP, as_ephemeral);
if (err) if (err)
goto leave; goto leave;
err = pgp_create_blob_keyblock (blob, image, imagelen); err = pgp_create_blob_keyblock (blob, image, imagelen);
@ -937,7 +937,7 @@ _keybox_create_x509_blob (KEYBOXBLOB *r_blob, ksba_cert_t cert,
init_membuf (&blob->bufbuf, 1024); init_membuf (&blob->bufbuf, 1024);
blob->buf = &blob->bufbuf; blob->buf = &blob->bufbuf;
/* write out what we already have */ /* write out what we already have */
rc = create_blob_header (blob, BLOBTYPE_X509, as_ephemeral); rc = create_blob_header (blob, KEYBOX_BLOBTYPE_X509, as_ephemeral);
if (rc) if (rc)
goto leave; goto leave;
rc = x509_create_blob_cert (blob, cert); rc = x509_create_blob_cert (blob, cert);
@ -1031,7 +1031,7 @@ _keybox_get_blob_fileoffset (KEYBOXBLOB blob)
void void
_keybox_update_header_blob (KEYBOXBLOB blob, int for_openpgp) _keybox_update_header_blob (KEYBOXBLOB blob, int for_openpgp)
{ {
if (blob->bloblen >= 32 && blob->blob[4] == BLOBTYPE_HEADER) if (blob->bloblen >= 32 && blob->blob[4] == KEYBOX_BLOBTYPE_HEADER)
{ {
u32 val = make_timestamp (); u32 val = make_timestamp ();

View File

@ -44,14 +44,6 @@
#include "keybox.h" #include "keybox.h"
enum {
BLOBTYPE_EMPTY = 0,
BLOBTYPE_HEADER = 1,
BLOBTYPE_PGP = 2,
BLOBTYPE_X509 = 3
};
typedef struct keyboxblob *KEYBOXBLOB; typedef struct keyboxblob *KEYBOXBLOB;

View File

@ -205,17 +205,17 @@ _keybox_dump_blob (KEYBOXBLOB blob, FILE *fp)
type = buffer[4]; type = buffer[4];
switch (type) switch (type)
{ {
case BLOBTYPE_EMPTY: case KEYBOX_BLOBTYPE_EMPTY:
fprintf (fp, "Type: Empty\n"); fprintf (fp, "Type: Empty\n");
return 0; return 0;
case BLOBTYPE_HEADER: case KEYBOX_BLOBTYPE_HEADER:
fprintf (fp, "Type: Header\n"); fprintf (fp, "Type: Header\n");
return dump_header_blob (buffer, length, fp); return dump_header_blob (buffer, length, fp);
case BLOBTYPE_PGP: case KEYBOX_BLOBTYPE_PGP:
fprintf (fp, "Type: OpenPGP\n"); fprintf (fp, "Type: OpenPGP\n");
break; break;
case BLOBTYPE_X509: case KEYBOX_BLOBTYPE_X509:
fprintf (fp, "Type: X.509\n"); fprintf (fp, "Type: X.509\n");
break; break;
default: default:
@ -271,7 +271,7 @@ _keybox_dump_blob (KEYBOXBLOB blob, FILE *fp)
fprintf (fp, "Key-Count: %lu\n", nkeys ); fprintf (fp, "Key-Count: %lu\n", nkeys );
if (!nkeys) if (!nkeys)
fprintf (fp, "[Error: no keys]\n"); fprintf (fp, "[Error: no keys]\n");
if (nkeys > 1 && type == BLOBTYPE_X509) if (nkeys > 1 && type == KEYBOX_BLOBTYPE_X509)
fprintf (fp, "[Error: only one key allowed for X509]\n"); fprintf (fp, "[Error: only one key allowed for X509]\n");
keyinfolen = get16 (buffer + 18 ); keyinfolen = get16 (buffer + 18 );
@ -321,13 +321,13 @@ _keybox_dump_blob (KEYBOXBLOB blob, FILE *fp)
uidoff = get32( p ); uidoff = get32( p );
uidlen = get32( p+4 ); uidlen = get32( p+4 );
if (type == BLOBTYPE_X509 && !n) if (type == KEYBOX_BLOBTYPE_X509 && !n)
{ {
fprintf (fp, "Issuer-Off: %lu\n", uidoff ); fprintf (fp, "Issuer-Off: %lu\n", uidoff );
fprintf (fp, "Issuer-Len: %lu\n", uidlen ); fprintf (fp, "Issuer-Len: %lu\n", uidlen );
fprintf (fp, "Issuer: \""); fprintf (fp, "Issuer: \"");
} }
else if (type == BLOBTYPE_X509 && n == 1) else if (type == KEYBOX_BLOBTYPE_X509 && n == 1)
{ {
fprintf (fp, "Subject-Off: %lu\n", uidoff ); fprintf (fp, "Subject-Off: %lu\n", uidoff );
fprintf (fp, "Subject-Len: %lu\n", uidlen ); fprintf (fp, "Subject-Len: %lu\n", uidlen );
@ -342,12 +342,12 @@ _keybox_dump_blob (KEYBOXBLOB blob, FILE *fp)
print_string (fp, buffer+uidoff, uidlen, '\"'); print_string (fp, buffer+uidoff, uidlen, '\"');
fputs ("\"\n", fp); fputs ("\"\n", fp);
uflags = get16 (p + 8); uflags = get16 (p + 8);
if (type == BLOBTYPE_X509 && !n) if (type == KEYBOX_BLOBTYPE_X509 && !n)
{ {
fprintf (fp, "Issuer-Flags: %04lX\n", uflags ); fprintf (fp, "Issuer-Flags: %04lX\n", uflags );
fprintf (fp, "Issuer-Validity: %d\n", p[10] ); fprintf (fp, "Issuer-Validity: %d\n", p[10] );
} }
else if (type == BLOBTYPE_X509 && n == 1) else if (type == KEYBOX_BLOBTYPE_X509 && n == 1)
{ {
fprintf (fp, "Subject-Flags: %04lX\n", uflags ); fprintf (fp, "Subject-Flags: %04lX\n", uflags );
fprintf (fp, "Subject-Validity: %d\n", p[10] ); fprintf (fp, "Subject-Validity: %d\n", p[10] );
@ -452,12 +452,12 @@ hash_blob_rawdata (KEYBOXBLOB blob, unsigned char *digest)
type = buffer[4]; type = buffer[4];
switch (type) switch (type)
{ {
case BLOBTYPE_PGP: case KEYBOX_BLOBTYPE_PGP:
case BLOBTYPE_X509: case KEYBOX_BLOBTYPE_X509:
break; break;
case BLOBTYPE_EMPTY: case KEYBOX_BLOBTYPE_EMPTY:
case BLOBTYPE_HEADER: case KEYBOX_BLOBTYPE_HEADER:
default: default:
memset (digest, 0, 20); memset (digest, 0, 20);
return 0; return 0;
@ -519,16 +519,16 @@ update_stats (KEYBOXBLOB blob, struct file_stats_s *s)
type = buffer[4]; type = buffer[4];
switch (type) switch (type)
{ {
case BLOBTYPE_EMPTY: case KEYBOX_BLOBTYPE_EMPTY:
s->empty_blob_count++; s->empty_blob_count++;
return 0; return 0;
case BLOBTYPE_HEADER: case KEYBOX_BLOBTYPE_HEADER:
s->header_blob_count++; s->header_blob_count++;
return 0; return 0;
case BLOBTYPE_PGP: case KEYBOX_BLOBTYPE_PGP:
s->pgp_blob_count++; s->pgp_blob_count++;
break; break;
case BLOBTYPE_X509: case KEYBOX_BLOBTYPE_X509:
s->x509_blob_count++; s->x509_blob_count++;
break; break;
default: default:

View File

@ -154,7 +154,7 @@ _keybox_write_header_blob (FILE *fp, int for_openpgp)
/* Length of this blob. */ /* Length of this blob. */
image[3] = 32; image[3] = 32;
image[4] = BLOBTYPE_HEADER; image[4] = KEYBOX_BLOBTYPE_HEADER;
image[5] = 1; /* Version */ image[5] = 1; /* Version */
if (for_openpgp) if (for_openpgp)
image[7] = 0x02; /* OpenPGP data may be available. */ image[7] = 0x02; /* OpenPGP data may be available. */

View File

@ -573,7 +573,7 @@ static inline int
has_keygrip (KEYBOXBLOB blob, const unsigned char *grip) has_keygrip (KEYBOXBLOB blob, const unsigned char *grip)
{ {
#ifdef KEYBOX_WITH_X509 #ifdef KEYBOX_WITH_X509
if (blob_get_type (blob) == BLOBTYPE_X509) if (blob_get_type (blob) == KEYBOX_BLOBTYPE_X509)
return blob_x509_has_grip (blob, grip); return blob_x509_has_grip (blob, grip);
#endif #endif
return 0; return 0;
@ -587,7 +587,7 @@ has_issuer (KEYBOXBLOB blob, const char *name)
return_val_if_fail (name, 0); return_val_if_fail (name, 0);
if (blob_get_type (blob) != BLOBTYPE_X509) if (blob_get_type (blob) != KEYBOX_BLOBTYPE_X509)
return 0; return 0;
namelen = strlen (name); namelen = strlen (name);
@ -603,7 +603,7 @@ has_issuer_sn (KEYBOXBLOB blob, const char *name,
return_val_if_fail (name, 0); return_val_if_fail (name, 0);
return_val_if_fail (sn, 0); return_val_if_fail (sn, 0);
if (blob_get_type (blob) != BLOBTYPE_X509) if (blob_get_type (blob) != KEYBOX_BLOBTYPE_X509)
return 0; return 0;
namelen = strlen (name); namelen = strlen (name);
@ -617,7 +617,7 @@ has_sn (KEYBOXBLOB blob, const unsigned char *sn, int snlen)
{ {
return_val_if_fail (sn, 0); return_val_if_fail (sn, 0);
if (blob_get_type (blob) != BLOBTYPE_X509) if (blob_get_type (blob) != KEYBOX_BLOBTYPE_X509)
return 0; return 0;
return blob_cmp_sn (blob, sn, snlen); return blob_cmp_sn (blob, sn, snlen);
} }
@ -629,7 +629,7 @@ has_subject (KEYBOXBLOB blob, const char *name)
return_val_if_fail (name, 0); return_val_if_fail (name, 0);
if (blob_get_type (blob) != BLOBTYPE_X509) if (blob_get_type (blob) != KEYBOX_BLOBTYPE_X509)
return 0; return 0;
namelen = strlen (name); namelen = strlen (name);
@ -646,12 +646,12 @@ has_username (KEYBOXBLOB blob, const char *name, int substr)
return_val_if_fail (name, 0); return_val_if_fail (name, 0);
btype = blob_get_type (blob); btype = blob_get_type (blob);
if (btype != BLOBTYPE_PGP && btype != BLOBTYPE_X509) if (btype != KEYBOX_BLOBTYPE_PGP && btype != KEYBOX_BLOBTYPE_X509)
return 0; return 0;
namelen = strlen (name); namelen = strlen (name);
return blob_cmp_name (blob, -1 /* all subject/user names */, name, return blob_cmp_name (blob, -1 /* all subject/user names */, name,
namelen, substr, (btype == BLOBTYPE_X509)); namelen, substr, (btype == KEYBOX_BLOBTYPE_X509));
} }
@ -664,16 +664,17 @@ has_mail (KEYBOXBLOB blob, const char *name, int substr)
return_val_if_fail (name, 0); return_val_if_fail (name, 0);
btype = blob_get_type (blob); btype = blob_get_type (blob);
if (btype != BLOBTYPE_PGP && btype != BLOBTYPE_X509) if (btype != KEYBOX_BLOBTYPE_PGP && btype != KEYBOX_BLOBTYPE_X509)
return 0; return 0;
if (btype == BLOBTYPE_PGP && *name == '<') if (btype == KEYBOX_BLOBTYPE_PGP && *name == '<')
name++; /* Hack to remove the leading '<' for gpg. */ name++; /* Hack to remove the leading '<' for gpg. */
namelen = strlen (name); namelen = strlen (name);
if (namelen && name[namelen-1] == '>') if (namelen && name[namelen-1] == '>')
namelen--; namelen--;
return blob_cmp_mail (blob, name, namelen, substr, (btype == BLOBTYPE_X509)); return blob_cmp_mail (blob, name, namelen, substr,
(btype == KEYBOX_BLOBTYPE_X509));
} }
@ -719,10 +720,12 @@ keybox_search_reset (KEYBOX_HANDLE hd)
/* Note: When in ephemeral mode the search function does visit all /* Note: When in ephemeral mode the search function does visit all
blobs but in standard mode, blobs flagged as ephemeral are ignored. blobs but in standard mode, blobs flagged as ephemeral are ignored.
If WANT_BLOBTYPE is not 0 only blobs of this type are considered.
The value at R_SKIPPED is updated by the number of skipped long The value at R_SKIPPED is updated by the number of skipped long
records (counts PGP and X.509). */ records (counts PGP and X.509). */
int int
keybox_search (KEYBOX_HANDLE hd, KEYBOX_SEARCH_DESC *desc, size_t ndesc, keybox_search (KEYBOX_HANDLE hd, KEYBOX_SEARCH_DESC *desc, size_t ndesc,
keybox_blobtype_t want_blobtype,
size_t *r_descindex, unsigned long *r_skipped) size_t *r_descindex, unsigned long *r_skipped)
{ {
int rc; int rc;
@ -851,6 +854,7 @@ keybox_search (KEYBOX_HANDLE hd, KEYBOX_SEARCH_DESC *desc, size_t ndesc,
for (;;) for (;;)
{ {
unsigned int blobflags; unsigned int blobflags;
int blobtype;
_keybox_release_blob (blob); blob = NULL; _keybox_release_blob (blob); blob = NULL;
rc = _keybox_read_blob (&blob, hd->fp); rc = _keybox_read_blob (&blob, hd->fp);
@ -864,9 +868,11 @@ keybox_search (KEYBOX_HANDLE hd, KEYBOX_SEARCH_DESC *desc, size_t ndesc,
if (rc) if (rc)
break; break;
if (blob_get_type (blob) == BLOBTYPE_HEADER) blobtype = blob_get_type (blob);
if (blobtype == KEYBOX_BLOBTYPE_HEADER)
continue;
if (want_blobtype && blobtype != want_blobtype)
continue; continue;
blobflags = blob_get_blob_flags (blob); blobflags = blob_get_blob_flags (blob);
if (!hd->ephemeral && (blobflags & 2)) if (!hd->ephemeral && (blobflags & 2))
@ -1025,7 +1031,7 @@ keybox_get_keyblock (KEYBOX_HANDLE hd, iobuf_t *r_iobuf,
if (!hd->found.blob) if (!hd->found.blob)
return gpg_error (GPG_ERR_NOTHING_FOUND); return gpg_error (GPG_ERR_NOTHING_FOUND);
if (blob_get_type (hd->found.blob) != BLOBTYPE_PGP) if (blob_get_type (hd->found.blob) != KEYBOX_BLOBTYPE_PGP)
return gpg_error (GPG_ERR_WRONG_BLOB_TYPE); return gpg_error (GPG_ERR_WRONG_BLOB_TYPE);
buffer = _keybox_get_blob_image (hd->found.blob, &length); buffer = _keybox_get_blob_image (hd->found.blob, &length);
@ -1077,7 +1083,7 @@ keybox_get_cert (KEYBOX_HANDLE hd, ksba_cert_t *r_cert)
if (!hd->found.blob) if (!hd->found.blob)
return gpg_error (GPG_ERR_NOTHING_FOUND); return gpg_error (GPG_ERR_NOTHING_FOUND);
if (blob_get_type (hd->found.blob) != BLOBTYPE_X509) if (blob_get_type (hd->found.blob) != KEYBOX_BLOBTYPE_X509)
return gpg_error (GPG_ERR_WRONG_BLOB_TYPE); return gpg_error (GPG_ERR_WRONG_BLOB_TYPE);
buffer = _keybox_get_blob_image (hd->found.blob, &length); buffer = _keybox_get_blob_image (hd->found.blob, &length);

View File

@ -282,7 +282,8 @@ blob_filecopy (int mode, const char *fname, KEYBOXBLOB blob,
failsafe the blob type.) */ failsafe the blob type.) */
while ( (nread = fread (buffer, 1, DIM(buffer), fp)) > 0 ) while ( (nread = fread (buffer, 1, DIM(buffer), fp)) > 0 )
{ {
if (first_record && for_openpgp && buffer[4] == BLOBTYPE_HEADER) if (first_record && for_openpgp
&& buffer[4] == KEYBOX_BLOBTYPE_HEADER)
{ {
first_record = 0; first_record = 0;
buffer[7] |= 0x02; /* OpenPGP data may be available. */ buffer[7] |= 0x02; /* OpenPGP data may be available. */
@ -446,7 +447,7 @@ keybox_update_keyblock (KEYBOX_HANDLE hd, const void *image, size_t imagelen)
return gpg_error (GPG_ERR_INV_VALUE); return gpg_error (GPG_ERR_INV_VALUE);
if (!hd->found.blob) if (!hd->found.blob)
return gpg_error (GPG_ERR_NOTHING_FOUND); return gpg_error (GPG_ERR_NOTHING_FOUND);
if (blob_get_type (hd->found.blob) != BLOBTYPE_PGP) if (blob_get_type (hd->found.blob) != KEYBOX_BLOBTYPE_PGP)
return gpg_error (GPG_ERR_WRONG_BLOB_TYPE); return gpg_error (GPG_ERR_WRONG_BLOB_TYPE);
fname = hd->kb->fname; fname = hd->kb->fname;
if (!fname) if (!fname)
@ -704,7 +705,7 @@ keybox_compress (KEYBOX_HANDLE hd)
size_t length; size_t length;
buffer = _keybox_get_blob_image (blob, &length); buffer = _keybox_get_blob_image (blob, &length);
if (length > 4 && buffer[4] == BLOBTYPE_HEADER) if (length > 4 && buffer[4] == KEYBOX_BLOBTYPE_HEADER)
{ {
u32 last_maint = ((buffer[20] << 24) | (buffer[20+1] << 16) u32 last_maint = ((buffer[20] << 24) | (buffer[20+1] << 16)
| (buffer[20+2] << 8) | (buffer[20+3])); | (buffer[20+2] << 8) | (buffer[20+3]));
@ -751,7 +752,7 @@ keybox_compress (KEYBOX_HANDLE hd)
if (first_blob) if (first_blob)
{ {
first_blob = 0; first_blob = 0;
if (length > 4 && buffer[4] == BLOBTYPE_HEADER) if (length > 4 && buffer[4] == KEYBOX_BLOBTYPE_HEADER)
{ {
/* Write out the blob with an updated maintenance time /* Write out the blob with an updated maintenance time
stamp and if needed (ie. used by gpg) set the openpgp stamp and if needed (ie. used by gpg) set the openpgp
@ -769,7 +770,7 @@ keybox_compress (KEYBOX_HANDLE hd)
break; break;
any_changes = 1; any_changes = 1;
} }
else if (length > 4 && buffer[4] == BLOBTYPE_HEADER) else if (length > 4 && buffer[4] == KEYBOX_BLOBTYPE_HEADER)
{ {
/* Oops: There is another header record - remove it. */ /* Oops: There is another header record - remove it. */
any_changes = 1; any_changes = 1;

View File

@ -56,6 +56,14 @@ typedef enum
#define KEYBOX_FLAG_BLOB_SECRET 1 #define KEYBOX_FLAG_BLOB_SECRET 1
#define KEYBOX_FLAG_BLOB_EPHEMERAL 2 #define KEYBOX_FLAG_BLOB_EPHEMERAL 2
/* The keybox blob types. */
typedef enum
{
KEYBOX_BLOBTYPE_EMPTY = 0,
KEYBOX_BLOBTYPE_HEADER = 1,
KEYBOX_BLOBTYPE_PGP = 2,
KEYBOX_BLOBTYPE_X509 = 3
} keybox_blobtype_t;
/*-- keybox-init.c --*/ /*-- keybox-init.c --*/
@ -87,6 +95,7 @@ int keybox_get_flags (KEYBOX_HANDLE hd, int what, int idx, unsigned int *value);
int keybox_search_reset (KEYBOX_HANDLE hd); int keybox_search_reset (KEYBOX_HANDLE hd);
int keybox_search (KEYBOX_HANDLE hd, KEYBOX_SEARCH_DESC *desc, size_t ndesc, int keybox_search (KEYBOX_HANDLE hd, KEYBOX_SEARCH_DESC *desc, size_t ndesc,
keybox_blobtype_t want_blobtype,
size_t *r_descindex, unsigned long *r_skipped); size_t *r_descindex, unsigned long *r_skipped);

View File

@ -972,6 +972,7 @@ keydb_search (KEYDB_HANDLE hd, KEYDB_SEARCH_DESC *desc, size_t ndesc)
break; break;
case KEYDB_RESOURCE_TYPE_KEYBOX: case KEYDB_RESOURCE_TYPE_KEYBOX:
rc = keybox_search (hd->active[hd->current].u.kr, desc, ndesc, rc = keybox_search (hd->active[hd->current].u.kr, desc, ndesc,
KEYBOX_BLOBTYPE_X509,
NULL, &skipped); NULL, &skipped);
break; break;
} }