mirror of
git://git.gnupg.org/gnupg.git
synced 2025-07-03 22:56:33 +02:00
gpg: Allow importing keys with duplicated long key ids.
* g10/keydb.c (keydb_handle): Add field no_caching. (keyblock_cache): Repalce field kid by fpr. (keydb_disable_caching): New. (keydb_search): Use the fingerprint as cache index. * g10/import.c (import_one): Use the fingerprint and not the kid to lookup the key. Call keydb_disable_caching beofre re-searching for update. * tests/openpgp/import.test: Add a test case. Signed-off-by: Werner Koch <wk@gnupg.org>
This commit is contained in:
parent
a256722537
commit
c60814a5ce
4 changed files with 51 additions and 20 deletions
33
g10/keydb.c
33
g10/keydb.c
|
@ -68,6 +68,7 @@ struct keydb_handle
|
|||
int locked;
|
||||
int found;
|
||||
unsigned long skipped_long_blobs;
|
||||
int no_caching;
|
||||
int current;
|
||||
int used; /* Number of items in ACTIVE. */
|
||||
struct resource_item active[MAX_KEYDB_RESOURCES];
|
||||
|
@ -75,7 +76,7 @@ struct keydb_handle
|
|||
|
||||
|
||||
/* This is a simple cache used to return the last result of a
|
||||
successful long kid search. This works only for keybox resources
|
||||
successful fingerprint search. This works only for keybox resources
|
||||
because (due to lack of a copy_keyblock function) we need to store
|
||||
an image of the keyblock which is fortunately instantly available
|
||||
for keyboxes. */
|
||||
|
@ -87,7 +88,7 @@ enum keyblock_cache_states {
|
|||
|
||||
struct {
|
||||
enum keyblock_cache_states state;
|
||||
u32 kid[2];
|
||||
byte fpr[MAX_FINGERPRINT_LEN];
|
||||
iobuf_t iobuf; /* Image of the keyblock. */
|
||||
u32 *sigstatus;
|
||||
int pk_no;
|
||||
|
@ -570,6 +571,7 @@ keydb_new (void)
|
|||
return hd;
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
keydb_release (KEYDB_HANDLE hd)
|
||||
{
|
||||
|
@ -600,6 +602,17 @@ keydb_release (KEYDB_HANDLE hd)
|
|||
}
|
||||
|
||||
|
||||
/* Set a flag on handle to not use cached results. This is required
|
||||
for updating a keyring. Fixme: Using a new parameter for keydb_new
|
||||
might be a better solution. */
|
||||
void
|
||||
keydb_disable_caching (KEYDB_HANDLE hd)
|
||||
{
|
||||
if (hd)
|
||||
hd->no_caching = 1;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Return the name of the current resource. This is function first
|
||||
* looks for the last found found, then for the current search
|
||||
|
@ -1407,10 +1420,12 @@ keydb_search (KEYDB_HANDLE hd, KEYDB_SEARCH_DESC *desc,
|
|||
if (DBG_CACHE)
|
||||
dump_search_desc ("keydb_search", desc, ndesc);
|
||||
|
||||
if (ndesc == 1 && desc[0].mode == KEYDB_SEARCH_MODE_LONG_KID
|
||||
if (!hd->no_caching
|
||||
&& ndesc == 1
|
||||
&& (desc[0].mode == KEYDB_SEARCH_MODE_FPR20
|
||||
|| desc[0].mode == KEYDB_SEARCH_MODE_FPR)
|
||||
&& keyblock_cache.state == KEYBLOCK_CACHE_FILLED
|
||||
&& keyblock_cache.kid[0] == desc[0].u.kid[0]
|
||||
&& keyblock_cache.kid[1] == desc[0].u.kid[1])
|
||||
&& !memcmp (keyblock_cache.fpr, desc[0].u.fpr, 20))
|
||||
{
|
||||
/* (DESCINDEX is already set). */
|
||||
if (DBG_CLOCK)
|
||||
|
@ -1450,11 +1465,13 @@ keydb_search (KEYDB_HANDLE hd, KEYDB_SEARCH_DESC *desc,
|
|||
: rc);
|
||||
|
||||
keyblock_cache_clear ();
|
||||
if (!rc && ndesc == 1 && desc[0].mode == KEYDB_SEARCH_MODE_LONG_KID)
|
||||
if (!hd->no_caching
|
||||
&& !rc
|
||||
&& ndesc == 1 && (desc[0].mode == KEYDB_SEARCH_MODE_FPR20
|
||||
|| desc[0].mode == KEYDB_SEARCH_MODE_FPR))
|
||||
{
|
||||
keyblock_cache.state = KEYBLOCK_CACHE_PREPARED;
|
||||
keyblock_cache.kid[0] = desc[0].u.kid[0];
|
||||
keyblock_cache.kid[1] = desc[0].u.kid[1];
|
||||
memcpy (keyblock_cache.fpr, desc[0].u.fpr, 20);
|
||||
}
|
||||
|
||||
if (DBG_CLOCK)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue