* gpgme.h: Add GPGME_ATTR_SIG_SUMMARY and the GPGME_SIGSUM_
constants. * verify.c (calc_sig_summary): New. (gpgme_get_sig_ulong_attr): And use it here.
This commit is contained in:
parent
8ac95a9772
commit
6b89172051
1
NEWS
1
NEWS
@ -3,6 +3,7 @@ Noteworthy changes in version CVS-HEAD
|
||||
|
||||
* Interface changes relative to the 0.3.6 release:
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
GPGME_ATTR_ERRTOK NEW
|
||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
Noteworthy changes in version 0.3.7 (2002-06-04)
|
||||
|
@ -1,3 +1,7 @@
|
||||
2002-06-10 Werner Koch <wk@gnupg.org>
|
||||
|
||||
* gpgme.texi (Verify): Document attribute GPGME_ATTR_ERRTOK.
|
||||
|
||||
2002-06-04 Marcus Brinkmann <marcus@g10code.de>
|
||||
|
||||
* gpgme.texi (Multi Threading): Document new autodetection.
|
||||
@ -183,3 +187,13 @@
|
||||
* fdl.texi: Likewise.
|
||||
* Makefile.am (info_TEXINFOS): New variable.
|
||||
(gpgme_TEXINFOS): Likewise.
|
||||
|
||||
Copyright 2002 g10 Code GmbH
|
||||
|
||||
This file is free software; as a special exception the author gives
|
||||
unlimited permission to copy and/or distribute it, with or without
|
||||
modifications, as long as this notice is preserved.
|
||||
|
||||
This file is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY, to the extent permitted by law; without even the
|
||||
implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
|
@ -2217,16 +2217,17 @@ fingerprint of the key which signed the plaintext, or @code{NULL} if
|
||||
no verification could be performed.
|
||||
@end deftypefun
|
||||
|
||||
@deftypefun {const char *} gpgme_get_sig_string_attr (@w{GpgmeCtx @var{ctx}}, @w{int @var{idx}}, @w{GpgmeAttr @var{waht}}, @w{int @var{reserved}})
|
||||
@deftypefun {const char *} gpgme_get_sig_string_attr (@w{GpgmeCtx @var{ctx}}, @w{int @var{idx}}, @w{GpgmeAttr @var{what}}, @w{int @var{reserved}})
|
||||
This function is similar to @code{gpgme_get_sig_status} but may be used
|
||||
to retrieve more detailed information. @var{ctx} should be the context
|
||||
used for the last signature verification, @var{idx} is used to enumerate
|
||||
over all signatures starting with @code{0} and @var{reserved} should be
|
||||
@code{0} for now.
|
||||
|
||||
The only attribute @var{what} currently supported is
|
||||
The attributes @var{what} currently supports are
|
||||
@code{GPGME_ATTR_FPR} to return the fingerprint of the key used to
|
||||
create the signature.
|
||||
create the signature and @code{GPGME_ERRTOK} to return a token
|
||||
with a more detailed error description.
|
||||
@end deftypefun
|
||||
|
||||
@deftypefun {const char *} gpgme_get_sig_ulong_attr (@w{GpgmeCtx @var{ctx}}, @w{int @var{idx}}, @w{GpgmeAttr @var{waht}}, @w{int @var{reserved}})
|
||||
|
@ -1,3 +1,21 @@
|
||||
2002-06-11 Werner Koch <wk@gnupg.org>
|
||||
|
||||
* gpgme.h: Add GPGME_ATTR_SIG_SUMMARY and the GPGME_SIGSUM_
|
||||
constants.
|
||||
* verify.c (calc_sig_summary): New.
|
||||
(gpgme_get_sig_ulong_attr): And use it here.
|
||||
|
||||
2002-06-10 Werner Koch <wk@gnupg.org>
|
||||
|
||||
* rungpg.h: Add new status codes TRUNCATED and ERROR.
|
||||
* verify.c (is_token, copy_token): New.
|
||||
(_gpgme_verify_status_handler): Use copy_token, handle the new
|
||||
ERROR status and store the errorcode used withgpgsm and trust
|
||||
status codes.
|
||||
* gpgme.h: New attribute ERRTOK.
|
||||
* key.c (gpgme_key_get_string_attr): Add dummy case for it.
|
||||
(gpgme_get_sig_string_attr): Use it here to return the last error.
|
||||
|
||||
2002-06-10 Marcus Brinkmann <marcus@g10code.de>
|
||||
|
||||
* engine-gpgsm.c (_gpgme_gpgsm_start): Move the code that sets the
|
||||
|
@ -137,6 +137,23 @@ typedef enum
|
||||
}
|
||||
GpgmeSigStat;
|
||||
|
||||
/* Flags used with the GPGME_ATTR_SIG_SUMMARY. */
|
||||
enum
|
||||
{
|
||||
GPGME_SIGSUM_VALID = 0x0001, /* The signature is fully valid */
|
||||
GPGME_SIGSUM_GREEN = 0x0002, /* The signature is good. */
|
||||
GPGME_SIGSUM_RED = 0x0004, /* The signature is bad. */
|
||||
GPGME_SIGSUM_KEY_REVOKED = 0x0010, /* One key has been revoked. */
|
||||
GPGME_SIGSUM_KEY_EXPIRED = 0x0020, /* One key has expired. */
|
||||
GPGME_SIGSUM_SIG_EXPIRED = 0x0040, /* The signature has expired. */
|
||||
GPGME_SIGSUM_KEY_MISSING = 0x0080, /* Can't verify: key missing. */
|
||||
GPGME_SIGSUM_CRL_MISSING = 0x0100, /* CRL not available. */
|
||||
GPGME_SIGSUM_CRL_TOO_OLD = 0x0200, /* Available CRL is too old. */
|
||||
GPGME_SIGSUM_BAD_POLICY = 0x0400, /* A policy was not met. */
|
||||
GPGME_SIGSUM_SYS_ERROR = 0x0800 /* A system error occured. */
|
||||
};
|
||||
|
||||
|
||||
/* The available signature modes. */
|
||||
typedef enum
|
||||
{
|
||||
@ -177,7 +194,9 @@ typedef enum
|
||||
GPGME_ATTR_SERIAL = 26,
|
||||
GPGME_ATTR_ISSUER = 27,
|
||||
GPGME_ATTR_CHAINID = 28,
|
||||
GPGME_ATTR_SIG_STATUS = 29
|
||||
GPGME_ATTR_SIG_STATUS = 29,
|
||||
GPGME_ATTR_ERRTOK = 30,
|
||||
GPGME_ATTR_SIG_SUMMARY = 31
|
||||
}
|
||||
GpgmeAttr;
|
||||
|
||||
|
@ -990,6 +990,7 @@ gpgme_key_get_string_attr (GpgmeKey key, GpgmeAttr what,
|
||||
val = key->chain_id;
|
||||
break;
|
||||
case GPGME_ATTR_SIG_STATUS:
|
||||
case GPGME_ATTR_ERRTOK:
|
||||
/* Not of any use here. */
|
||||
break;
|
||||
}
|
||||
|
@ -79,8 +79,3 @@ GpgmeError _gpgme_key_append_name ( GpgmeKey key, const char *s );
|
||||
|
||||
|
||||
#endif /* KEY_H */
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
@ -102,7 +102,9 @@ typedef enum {
|
||||
STATUS_ALREADY_SIGNED ,
|
||||
STATUS_SIGEXPIRED ,
|
||||
STATUS_EXPSIG ,
|
||||
STATUS_EXPKEYSIG
|
||||
STATUS_EXPKEYSIG ,
|
||||
STATUS_TRUNCATED ,
|
||||
STATUS_ERROR ,
|
||||
} GpgStatusCode;
|
||||
|
||||
typedef void (*GpgStatusHandler)( GpgmeCtx, GpgStatusCode code, char *args );
|
||||
|
136
gpgme/verify.c
136
gpgme/verify.c
@ -44,6 +44,7 @@ struct verify_result_s
|
||||
ulong timestamp; /* Signature creation time. */
|
||||
ulong exptimestamp; /* signature exipration time or 0 */
|
||||
GpgmeValidity validity;
|
||||
char trust_errtok[31]; /* error token send with the trust status */
|
||||
};
|
||||
|
||||
|
||||
@ -59,6 +60,44 @@ _gpgme_release_verify_result (VerifyResult result)
|
||||
}
|
||||
}
|
||||
|
||||
/* Check whether STRING starts with TOKEN and return true in this
|
||||
case. This is case insensitive. If NEXT is not NULL return the
|
||||
number of bytes to be added to STRING to get to the next token; a
|
||||
returned value of 0 indicates end of line. */
|
||||
static int
|
||||
is_token (const char *string, const char *token, size_t *next)
|
||||
{
|
||||
size_t n = 0;
|
||||
|
||||
for (;*string && *token && *string == *token; string++, token++, n++)
|
||||
;
|
||||
if (*token || (*string != ' ' && !*string))
|
||||
return 0;
|
||||
if (next)
|
||||
{
|
||||
for (; *string == ' '; string++, n++)
|
||||
;
|
||||
*next = n;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
static size_t
|
||||
copy_token (const char *string, char *buffer, size_t length)
|
||||
{
|
||||
const char *s = string;
|
||||
char *p = buffer;
|
||||
size_t i;
|
||||
|
||||
for (i = 1; i < length && *s && *s != ' ' ; i++)
|
||||
*p++ = *s++;
|
||||
*p = 0;
|
||||
/* conmtinue scanning in case the copy was truncated */
|
||||
while (*s && *s != ' ')
|
||||
s++;
|
||||
return s - string;
|
||||
}
|
||||
|
||||
|
||||
/* FIXME: Check that we are adding this to the correct signature. */
|
||||
static void
|
||||
@ -147,6 +186,7 @@ void
|
||||
_gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
|
||||
{
|
||||
char *p;
|
||||
size_t n;
|
||||
int i;
|
||||
|
||||
if (ctx->error)
|
||||
@ -184,11 +224,8 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
|
||||
|
||||
case STATUS_VALIDSIG:
|
||||
ctx->result.verify->status = GPGME_SIG_STAT_GOOD;
|
||||
p = ctx->result.verify->fpr;
|
||||
for (i = 0; i < DIM(ctx->result.verify->fpr)
|
||||
&& args[i] && args[i] != ' ' ; i++)
|
||||
*p++ = args[i];
|
||||
*p = 0;
|
||||
i = copy_token (args, ctx->result.verify->fpr,
|
||||
DIM(ctx->result.verify->fpr));
|
||||
/* Skip the formatted date. */
|
||||
while (args[i] && args[i] == ' ')
|
||||
i++;
|
||||
@ -203,16 +240,13 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
|
||||
case STATUS_BADSIG:
|
||||
ctx->result.verify->status = GPGME_SIG_STAT_BAD;
|
||||
/* Store the keyID in the fpr field. */
|
||||
p = ctx->result.verify->fpr;
|
||||
for (i = 0; i < DIM(ctx->result.verify->fpr)
|
||||
&& args[i] && args[i] != ' ' ; i++)
|
||||
*p++ = args[i];
|
||||
*p = 0;
|
||||
copy_token (args, ctx->result.verify->fpr,
|
||||
DIM(ctx->result.verify->fpr));
|
||||
break;
|
||||
|
||||
case STATUS_ERRSIG:
|
||||
/* The return code is the 6th argument, if it is 9, the problem
|
||||
is a missing key. */
|
||||
is a missing key. Note that this is not emitted by gpgsm */
|
||||
for (p = args, i = 0; p && *p && i < 5; i++)
|
||||
{
|
||||
p = strchr (p, ' ');
|
||||
@ -225,11 +259,8 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
|
||||
else
|
||||
ctx->result.verify->status = GPGME_SIG_STAT_ERROR;
|
||||
/* Store the keyID in the fpr field. */
|
||||
p = ctx->result.verify->fpr;
|
||||
for (i = 0; i < DIM(ctx->result.verify->fpr)
|
||||
&& args[i] && args[i] != ' ' ; i++)
|
||||
*p++ = args[i];
|
||||
*p = 0;
|
||||
copy_token (args, ctx->result.verify->fpr,
|
||||
DIM(ctx->result.verify->fpr));
|
||||
break;
|
||||
|
||||
case STATUS_NOTATION_NAME:
|
||||
@ -240,13 +271,19 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
|
||||
|
||||
case STATUS_TRUST_UNDEFINED:
|
||||
ctx->result.verify->validity = GPGME_VALIDITY_UNKNOWN;
|
||||
copy_token (args, ctx->result.verify->trust_errtok,
|
||||
DIM(ctx->result.verify->trust_errtok));
|
||||
break;
|
||||
case STATUS_TRUST_NEVER:
|
||||
ctx->result.verify->validity = GPGME_VALIDITY_NEVER;
|
||||
copy_token (args, ctx->result.verify->trust_errtok,
|
||||
DIM(ctx->result.verify->trust_errtok));
|
||||
break;
|
||||
case STATUS_TRUST_MARGINAL:
|
||||
if (ctx->result.verify->status == GPGME_SIG_STAT_GOOD)
|
||||
ctx->result.verify->validity = GPGME_VALIDITY_MARGINAL;
|
||||
copy_token (args, ctx->result.verify->trust_errtok,
|
||||
DIM(ctx->result.verify->trust_errtok));
|
||||
break;
|
||||
case STATUS_TRUST_FULLY:
|
||||
case STATUS_TRUST_ULTIMATE:
|
||||
@ -257,6 +294,20 @@ _gpgme_verify_status_handler (GpgmeCtx ctx, GpgStatusCode code, char *args)
|
||||
case STATUS_END_STREAM:
|
||||
break;
|
||||
|
||||
case STATUS_ERROR:
|
||||
/* Generic error, we need this for gpgsm (and maybe for gpg in future)
|
||||
to get error descriptions. */
|
||||
if (is_token (args, "verify.findkey", &n) && n)
|
||||
{
|
||||
args += n;
|
||||
if (is_token (args, "No_Public_Key", NULL))
|
||||
ctx->result.verify->status = GPGME_SIG_STAT_NOKEY;
|
||||
else
|
||||
ctx->result.verify->status = GPGME_SIG_STAT_ERROR;
|
||||
|
||||
}
|
||||
break;
|
||||
|
||||
case STATUS_EOF:
|
||||
finish_sig (ctx,1);
|
||||
|
||||
@ -451,6 +502,55 @@ gpgme_get_sig_status (GpgmeCtx c, int idx,
|
||||
return result->fpr;
|
||||
}
|
||||
|
||||
|
||||
/* Build a summary vector from RESULT. */
|
||||
static unsigned long
|
||||
calc_sig_summary (VerifyResult result)
|
||||
{
|
||||
unsigned long sum = 0;
|
||||
|
||||
if (result->validity == GPGME_VALIDITY_FULL
|
||||
|| result->validity == GPGME_VALIDITY_ULTIMATE)
|
||||
{
|
||||
if (result->status == GPGME_SIG_STAT_GOOD
|
||||
|| result->status == GPGME_SIG_STAT_GOOD_EXP
|
||||
|| result->status == GPGME_SIG_STAT_GOOD_EXPKEY)
|
||||
sum |= GPGME_SIGSUM_GREEN;
|
||||
}
|
||||
else if (result->validity == GPGME_VALIDITY_NEVER)
|
||||
{
|
||||
if (result->status == GPGME_SIG_STAT_GOOD
|
||||
|| result->status == GPGME_SIG_STAT_GOOD_EXP
|
||||
|| result->status == GPGME_SIG_STAT_GOOD_EXPKEY)
|
||||
sum |= GPGME_SIGSUM_RED;
|
||||
}
|
||||
else if (result->status == GPGME_SIG_STAT_BAD)
|
||||
sum |= GPGME_SIGSUM_RED;
|
||||
|
||||
/* fixme: handle the case when key and message are expired. */
|
||||
if (result->status == GPGME_SIG_STAT_GOOD_EXP)
|
||||
sum |= GPGME_SIGSUM_SIG_EXPIRED;
|
||||
else if (result->status == GPGME_SIG_STAT_GOOD_EXPKEY)
|
||||
sum |= GPGME_SIGSUM_KEY_EXPIRED;
|
||||
else if (result->status == GPGME_SIG_STAT_NOKEY)
|
||||
sum |= GPGME_SIGSUM_KEY_MISSING;
|
||||
else if (result->status == GPGME_SIG_STAT_ERROR)
|
||||
sum |= GPGME_SIGSUM_SYS_ERROR;
|
||||
|
||||
/* FIXME: Set GPGME_SIGSUM_KEY_REVOKED. */
|
||||
/* FIXME: Set GPGME_SIGSUM_CRL_MISSING. */
|
||||
/* FIXME: Set GPGME_SIGSUM_CRL_TOO_OLD. */
|
||||
/* FIXME: Set GPGME_SIGSUM_BAD_POLICY. */
|
||||
|
||||
/* That the valid flag when the signature is unquestionable
|
||||
valid. */
|
||||
if ((sum & GPGME_SIGSUM_GREEN) && !(sum & ~GPGME_SIGSUM_GREEN))
|
||||
sum |= GPGME_SIGSUM_VALID;
|
||||
|
||||
return sum;
|
||||
}
|
||||
|
||||
|
||||
const char *
|
||||
gpgme_get_sig_string_attr (GpgmeCtx c, int idx, GpgmeAttr what, int reserved)
|
||||
{
|
||||
@ -471,6 +571,8 @@ gpgme_get_sig_string_attr (GpgmeCtx c, int idx, GpgmeAttr what, int reserved)
|
||||
{
|
||||
case GPGME_ATTR_FPR:
|
||||
return result->fpr;
|
||||
case GPGME_ATTR_ERRTOK:
|
||||
return result->trust_errtok;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@ -502,6 +604,8 @@ gpgme_get_sig_ulong_attr (GpgmeCtx c, int idx, GpgmeAttr what, int reserved)
|
||||
return (unsigned long)result->validity;
|
||||
case GPGME_ATTR_SIG_STATUS:
|
||||
return (unsigned long)result->status;
|
||||
case GPGME_ATTR_SIG_SUMMARY:
|
||||
return calc_sig_summary (result);
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
@ -1,3 +1,7 @@
|
||||
2002-06-10 Werner Koch <wk@gnupg.org>
|
||||
|
||||
* gpgsm/t-verify.c (print_sig_stat): Print the error token.
|
||||
|
||||
2002-06-04 Werner Koch <wk@gnupg.org>
|
||||
|
||||
* gpgsm/t-encrypt.c (main): Add a simple option parser and allow
|
||||
|
@ -118,8 +118,9 @@ print_sig_stat ( GpgmeCtx ctx, GpgmeSigStat status )
|
||||
idx, (unsigned long)created,
|
||||
gpgme_get_sig_ulong_attr (ctx, idx, GPGME_ATTR_EXPIRE, 0),
|
||||
status_string(status) );
|
||||
printf ("sig %d: fpr/keyid: `%s' validity: %s\n",
|
||||
printf ("sig %d: fpr/keyid: `%s' exterr: `%s' validity: %s\n",
|
||||
idx, s,
|
||||
gpgme_get_sig_string_attr (ctx, idx, GPGME_ATTR_ERRTOK, 0),
|
||||
validity_string (gpgme_get_sig_ulong_attr
|
||||
(ctx, idx, GPGME_ATTR_VALIDITY, 0)) );
|
||||
if ( !gpgme_get_sig_key (ctx, idx, &key) ) {
|
||||
|
Loading…
Reference in New Issue
Block a user