* verify.c (_gpgme_verify_status_handler): Handle TRUST_* status

lines so that a claim can be made without looking up the key.
(gpgme_get_sig_string_attr): New.
(gpgme_get_sig_ulong_attr): New.

* gpgme.h (GpgmeAttr): Added GPGME_ATTR_SIG_STATUS.

* rungpg.h: Add new status codes from gpg 1.0.7 and formatted the
list to align with the status.h file from gnupg.

* gpgme.h (GpgmeSigStat): Add _GOOD_EXP and _GOOD_EXPKEY.
* verify.c (_gpgme_verify_status_handler, finish_sig): Handle
these new status codes.  Store the expiration time
This commit is contained in:
Werner Koch 2002-05-03 14:06:56 +00:00
parent 6c4d6748f6
commit f14bf86fee
6 changed files with 166 additions and 12 deletions

12
NEWS
View File

@ -1,3 +1,9 @@
* The signature verfication functions are extended. Instead of
always returning GPGME_SIG_STATUS_GOOD, the functions return more
specific codes for expired signatures. 2 new functions may be used
to retrieve more specific information like the signature expiartion
time and a validut information of the key without looking up the key.
* The current passphrase callback and progress meter callback can be * The current passphrase callback and progress meter callback can be
retrieved with the new functions gpgme_get_passphrase_cb and retrieved with the new functions gpgme_get_passphrase_cb and
gpgme_get_progress_cb respectively. gpgme_get_progress_cb respectively.
@ -9,6 +15,12 @@ gpgme_get_progress_cb NEW
GpgmeDataEncoding NEW GpgmeDataEncoding NEW
gpgme_data_set_encoding NEW gpgme_data_set_encoding NEW
gpgme_data_get_encoding NEW gpgme_data_get_encoding NEW
GPGME_SIG_STAT_GOOD_EXP NEW
GPGME_SIG_STAT_GOOD_EXPKEY NEW
gpgme_op_verify CHANGED: Returns more status codes.
GPGME_ATTR_SIG_STATUS NEW
gpgme_get_sig_string_attr NEW
gpgme_get_sig_ulong_attr NEW
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Noteworthy changes in version 0.3.5 (2002-04-01) Noteworthy changes in version 0.3.5 (2002-04-01)

View File

@ -1,3 +1,19 @@
2002-05-03 Werner Koch <wk@gnupg.org>
* verify.c (_gpgme_verify_status_handler): Handle TRUST_* status
lines so that a claim can be made without looking up the key.
(gpgme_get_sig_string_attr): New.
(gpgme_get_sig_ulong_attr): New.
* gpgme.h (GpgmeAttr): Added GPGME_ATTR_SIG_STATUS.
* rungpg.h: Add new status codes from gpg 1.0.7 and formatted the
list to align with the status.h file from gnupg.
* gpgme.h (GpgmeSigStat): Add _GOOD_EXP and _GOOD_EXPKEY.
* verify.c (_gpgme_verify_status_handler, finish_sig): Handle
these new status codes. Store the expiration time
2002-04-27 Werner Koch <wk@gnupg.org> 2002-04-27 Werner Koch <wk@gnupg.org>
* gpgme.h (GpgmeData_Encoding): New. * gpgme.h (GpgmeData_Encoding): New.

View File

@ -131,7 +131,9 @@ typedef enum
GPGME_SIG_STAT_NOKEY = 3, GPGME_SIG_STAT_NOKEY = 3,
GPGME_SIG_STAT_NOSIG = 4, GPGME_SIG_STAT_NOSIG = 4,
GPGME_SIG_STAT_ERROR = 5, GPGME_SIG_STAT_ERROR = 5,
GPGME_SIG_STAT_DIFF = 6 GPGME_SIG_STAT_DIFF = 6,
GPGME_SIG_STAT_GOOD_EXP = 7,
GPGME_SIG_STAT_GOOD_EXPKEY = 8
} }
GpgmeSigStat; GpgmeSigStat;
@ -144,7 +146,7 @@ typedef enum
} }
GpgmeSigMode; GpgmeSigMode;
/* The available key attributes. */ /* The available key and signature attributes. */
typedef enum typedef enum
{ {
GPGME_ATTR_KEYID = 1, GPGME_ATTR_KEYID = 1,
@ -174,7 +176,8 @@ typedef enum
GPGME_ATTR_KEY_DISABLED = 25, GPGME_ATTR_KEY_DISABLED = 25,
GPGME_ATTR_SERIAL = 26, GPGME_ATTR_SERIAL = 26,
GPGME_ATTR_ISSUER = 27, GPGME_ATTR_ISSUER = 27,
GPGME_ATTR_CHAINID = 28 GPGME_ATTR_CHAINID = 28,
GPGME_ATTR_SIG_STATUS = 29
} }
GpgmeAttr; GpgmeAttr;
@ -289,6 +292,16 @@ GpgmeKey gpgme_signers_enum (const GpgmeCtx ctx, int seq);
const char *gpgme_get_sig_status (GpgmeCtx ctx, int idx, const char *gpgme_get_sig_status (GpgmeCtx ctx, int idx,
GpgmeSigStat *r_stat, time_t *r_created); GpgmeSigStat *r_stat, time_t *r_created);
/* Retrieve certain attributes of a signature. IDX is the index
number of the signature after a successful verify operation. WHAT
is an attribute where GPGME_ATTR_EXPIRE is probably the most useful
one. RESERVED must be passed as 0. */
unsigned long gpgme_get_sig_ulong_attr (GpgmeCtx c, int idx,
GpgmeAttr what, int reserved);
const char *gpgme_get_sig_string_attr (GpgmeCtx c, int idx,
GpgmeAttr what, int reserved);
/* Get the key used to create signature IDX in CTX and return it in /* Get the key used to create signature IDX in CTX and return it in
R_KEY. */ R_KEY. */
GpgmeError gpgme_get_sig_key (GpgmeCtx ctx, int idx, GpgmeKey *r_key); GpgmeError gpgme_get_sig_key (GpgmeCtx ctx, int idx, GpgmeKey *r_key);

View File

@ -1,6 +1,6 @@
/* key.c - Key and keyList objects /* key.c - Key and keyList objects
* Copyright (C) 2000 Werner Koch (dd9jn) * Copyright (C) 2000 Werner Koch (dd9jn)
* Copyright (C) 2001 g10 Code GmbH * Copyright (C) 2001, 2002 g10 Code GmbH
* *
* This file is part of GPGME. * This file is part of GPGME.
* *
@ -869,6 +869,9 @@ gpgme_key_get_string_attr ( GpgmeKey key, GpgmeAttr what,
case GPGME_ATTR_CHAINID: case GPGME_ATTR_CHAINID:
val = key->chain_id; val = key->chain_id;
break; break;
case GPGME_ATTR_SIG_STATUS:
/* not of any use here */
break;
} }
return val; return val;
} }

View File

@ -31,24 +31,30 @@ typedef enum {
STATUS_ENTER , STATUS_ENTER ,
STATUS_LEAVE , STATUS_LEAVE ,
STATUS_ABORT , STATUS_ABORT ,
STATUS_GOODSIG , STATUS_GOODSIG ,
STATUS_BADSIG , STATUS_BADSIG ,
STATUS_ERRSIG , STATUS_ERRSIG ,
STATUS_BADARMOR , STATUS_BADARMOR ,
STATUS_RSA_OR_IDEA , STATUS_RSA_OR_IDEA ,
STATUS_SIGEXPIRED , STATUS_KEYEXPIRED ,
STATUS_KEYREVOKED , STATUS_KEYREVOKED ,
STATUS_TRUST_UNDEFINED , STATUS_TRUST_UNDEFINED ,
STATUS_TRUST_NEVER , STATUS_TRUST_NEVER ,
STATUS_TRUST_MARGINAL , STATUS_TRUST_MARGINAL ,
STATUS_TRUST_FULLY , STATUS_TRUST_FULLY ,
STATUS_TRUST_ULTIMATE , STATUS_TRUST_ULTIMATE ,
STATUS_SHM_INFO , STATUS_SHM_INFO ,
STATUS_SHM_GET , STATUS_SHM_GET ,
STATUS_SHM_GET_BOOL , STATUS_SHM_GET_BOOL ,
STATUS_SHM_GET_HIDDEN , STATUS_SHM_GET_HIDDEN ,
STATUS_NEED_PASSPHRASE , STATUS_NEED_PASSPHRASE ,
STATUS_UNEXPECTED ,
STATUS_VALIDSIG , STATUS_VALIDSIG ,
STATUS_SIG_ID , STATUS_SIG_ID ,
STATUS_ENC_TO , STATUS_ENC_TO ,
@ -69,10 +75,12 @@ typedef enum {
STATUS_FILE_START , STATUS_FILE_START ,
STATUS_FILE_DONE , STATUS_FILE_DONE ,
STATUS_FILE_ERROR , STATUS_FILE_ERROR ,
STATUS_BEGIN_DECRYPTION , STATUS_BEGIN_DECRYPTION ,
STATUS_END_DECRYPTION , STATUS_END_DECRYPTION ,
STATUS_BEGIN_ENCRYPTION , STATUS_BEGIN_ENCRYPTION ,
STATUS_END_ENCRYPTION , STATUS_END_ENCRYPTION ,
STATUS_DELETE_PROBLEM , STATUS_DELETE_PROBLEM ,
STATUS_GET_BOOL , STATUS_GET_BOOL ,
STATUS_GET_LINE , STATUS_GET_LINE ,
@ -80,16 +88,21 @@ typedef enum {
STATUS_GOT_IT , STATUS_GOT_IT ,
STATUS_PROGRESS , STATUS_PROGRESS ,
STATUS_SIG_CREATED , STATUS_SIG_CREATED ,
STATUS_KEY_CREATED ,
STATUS_SESSION_KEY , STATUS_SESSION_KEY ,
STATUS_NOTATION_NAME , STATUS_NOTATION_NAME ,
STATUS_NOTATION_DATA , STATUS_NOTATION_DATA ,
STATUS_USERID_HINT ,
STATUS_POLICY_URL , STATUS_POLICY_URL ,
STATUS_BEGIN_STREAM , STATUS_BEGIN_STREAM ,
STATUS_END_STREAM , STATUS_END_STREAM ,
STATUS_KEY_CREATED ,
STATUS_USERID_HINT ,
STATUS_UNEXPECTED ,
STATUS_INV_RECP , STATUS_INV_RECP ,
STATUS_NO_RECP STATUS_NO_RECP ,
STATUS_ALREADY_SIGNED ,
STATUS_SIGEXPIRED ,
STATUS_EXPSIG ,
STATUS_EXPKEYSIG
} GpgStatusCode; } GpgStatusCode;
typedef void (*GpgStatusHandler)( GpgmeCtx, GpgStatusCode code, char *args ); typedef void (*GpgStatusHandler)( GpgmeCtx, GpgStatusCode code, char *args );

View File

@ -35,12 +35,15 @@ struct verify_result_s
{ {
struct verify_result_s *next; struct verify_result_s *next;
GpgmeSigStat status; GpgmeSigStat status;
GpgmeSigStat expstatus; /* only used by finish_sig */
GpgmeData notation; /* We store an XML fragment here. */ GpgmeData notation; /* We store an XML fragment here. */
int collecting; /* Private to finish_sig(). */ int collecting; /* Private to finish_sig(). */
int notation_in_data; /* Private to add_notation(). */ int notation_in_data; /* Private to add_notation(). */
char fpr[41]; /* Fingerprint of a good signature or keyid of char fpr[41]; /* Fingerprint of a good signature or keyid of
a bad one. */ a bad one. */
ulong timestamp; /* Signature creation time. */ ulong timestamp; /* Signature creation time. */
ulong exptimestamp; /* signature exipration time or 0 */
GpgmeValidity validity;
}; };
@ -113,6 +116,9 @@ add_notation (GpgmeCtx ctx, GpgStatusCode code, const char *data)
static void static void
finish_sig (GpgmeCtx ctx, int stop) finish_sig (GpgmeCtx ctx, int stop)
{ {
if (ctx->result.verify->status == GPGME_SIG_STAT_GOOD)
ctx->result.verify->status = ctx->result.verify->expstatus;
if (stop) if (stop)
return; /* nothing to do */ return; /* nothing to do */
@ -147,7 +153,11 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
return; return;
test_and_allocate_result (ctx, verify); test_and_allocate_result (ctx, verify);
if (code == STATUS_GOODSIG || code == STATUS_BADSIG || code == STATUS_ERRSIG) if (code == STATUS_GOODSIG
|| code == STATUS_EXPSIG
|| code == STATUS_EXPKEYSIG
|| code == STATUS_BADSIG
|| code == STATUS_ERRSIG)
{ {
finish_sig (ctx,0); finish_sig (ctx,0);
if (ctx->error) if (ctx->error)
@ -161,7 +171,15 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
break; break;
case STATUS_GOODSIG: case STATUS_GOODSIG:
/* We only look at VALIDSIG */ ctx->result.verify->expstatus = GPGME_SIG_STAT_GOOD;
break;
case STATUS_EXPSIG:
ctx->result.verify->expstatus = GPGME_SIG_STAT_GOOD_EXP;
break;
case STATUS_EXPKEYSIG:
ctx->result.verify->expstatus = GPGME_SIG_STAT_GOOD_EXPKEY;
break; break;
case STATUS_VALIDSIG: case STATUS_VALIDSIG:
@ -177,7 +195,9 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
while (args[i] && args[i] != ' ') while (args[i] && args[i] != ' ')
i++; i++;
/* And get the timestamp. */ /* And get the timestamp. */
ctx->result.verify->timestamp = strtoul (args+i, NULL, 10); ctx->result.verify->timestamp = strtoul (args+i, &p, 10);
if (args[i])
ctx->result.verify->exptimestamp = strtoul (p, NULL, 10);
break; break;
case STATUS_BADSIG: case STATUS_BADSIG:
@ -218,6 +238,22 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
add_notation (ctx, code, args); add_notation (ctx, code, args);
break; break;
case STATUS_TRUST_UNDEFINED:
ctx->result.verify->validity = GPGME_VALIDITY_UNKNOWN;
break;
case STATUS_TRUST_NEVER:
ctx->result.verify->validity = GPGME_VALIDITY_NEVER;
break;
case STATUS_TRUST_MARGINAL:
if (ctx->result.verify->status == GPGME_SIG_STAT_GOOD)
ctx->result.verify->validity = GPGME_VALIDITY_MARGINAL;
break;
case STATUS_TRUST_FULLY:
case STATUS_TRUST_ULTIMATE:
if (ctx->result.verify->status == GPGME_SIG_STAT_GOOD)
ctx->result.verify->validity = GPGME_VALIDITY_FULL;
break;
case STATUS_END_STREAM: case STATUS_END_STREAM:
break; break;
@ -353,6 +389,8 @@ _gpgme_intersect_stati (VerifyResult result)
* GPGME_SIG_STAT_ERROR: Due to some other error the check could not be done. * GPGME_SIG_STAT_ERROR: Due to some other error the check could not be done.
* GPGME_SIG_STAT_DIFF: There is more than 1 signature and they have not * GPGME_SIG_STAT_DIFF: There is more than 1 signature and they have not
* the same status. * the same status.
* GPGME_SIG_STAT_GOOD_EXP: The signature is good but has expired.
* GPGME_SIG_STAT_GOOD_KEYEXP: The signature is good but the key has expired.
* *
* Return value: 0 on success or an errorcode if something not related to * Return value: 0 on success or an errorcode if something not related to
* the signature itself did go wrong. * the signature itself did go wrong.
@ -415,6 +453,64 @@ gpgme_get_sig_status (GpgmeCtx c, int idx,
return result->fpr; return result->fpr;
} }
const char *
gpgme_get_sig_string_attr (GpgmeCtx c, int idx, GpgmeAttr what, int reserved)
{
VerifyResult result;
if (!c || c->pending || !c->result.verify)
return NULL; /* No results yet or verification error. */
if (reserved)
return NULL; /* We might want to use it to enumerate attributes of
one signature */
for (result = c->result.verify;
result && idx > 0; result = result->next, idx--)
;
if (!result)
return NULL; /* No more signatures. */
switch (what)
{
case GPGME_ATTR_FPR:
return result->fpr;
default:
break;
}
return NULL;
}
unsigned long
gpgme_get_sig_ulong_attr (GpgmeCtx c, int idx, GpgmeAttr what, int reserved)
{
VerifyResult result;
if (!c || c->pending || !c->result.verify)
return 0; /* No results yet or verification error. */
if (reserved)
return 0;
for (result = c->result.verify;
result && idx > 0; result = result->next, idx--)
;
if (!result)
return 0; /* No more signatures. */
switch (what)
{
case GPGME_ATTR_CREATED:
return result->timestamp;
case GPGME_ATTR_EXPIRE:
return result->exptimestamp;
case GPGME_ATTR_VALIDITY:
return (unsigned long)result->validity;
case GPGME_ATTR_SIG_STATUS:
return (unsigned long)result->status;
default:
break;
}
return 0;
}
/** /**
* gpgme_get_sig_key: * gpgme_get_sig_key:
@ -465,3 +561,4 @@ gpgme_get_sig_key (GpgmeCtx c, int idx, GpgmeKey *r_key)
} }
return err; return err;
} }