diff options
| -rw-r--r-- | src/decrypt.c | 9 | ||||
| -rw-r--r-- | src/encrypt.c | 9 | ||||
| -rw-r--r-- | src/genkey.c | 9 | ||||
| -rw-r--r-- | src/gpgme.h.in | 3 | ||||
| -rw-r--r-- | src/op-support.c | 24 | ||||
| -rw-r--r-- | src/ops.h | 4 | ||||
| -rw-r--r-- | src/passphrase.c | 13 | ||||
| -rw-r--r-- | src/passwd.c | 9 | ||||
| -rw-r--r-- | src/sign.c | 10 | ||||
| -rw-r--r-- | src/status-table.c | 1 | ||||
| -rw-r--r-- | src/verify.c | 9 | 
11 files changed, 98 insertions, 2 deletions
| diff --git a/src/decrypt.c b/src/decrypt.c index 4fd92c61..4db68a10 100644 --- a/src/decrypt.c +++ b/src/decrypt.c @@ -38,6 +38,9 @@ typedef struct  {    struct _gpgme_op_decrypt_result result; +  /* The error code from a FAILURE status line or 0.  */ +  gpg_error_t failure_code; +    int okay;    int failed; @@ -192,6 +195,10 @@ _gpgme_decrypt_status_handler (void *priv, gpgme_status_code_t code,    switch (code)      { +    case GPGME_STATUS_FAILURE: +      opd->failure_code = _gpgme_parse_failure (args); +      break; +      case GPGME_STATUS_EOF:        /* FIXME: These error values should probably be attributed to  	 the underlying crypto engine (as error source).  */ @@ -199,6 +206,8 @@ _gpgme_decrypt_status_handler (void *priv, gpgme_status_code_t code,  	return gpg_error (GPG_ERR_DECRYPT_FAILED);        else if (!opd->okay)  	return gpg_error (GPG_ERR_NO_DATA); +      else if (opd->failure_code) +        return opd->failure_code;        break;      case GPGME_STATUS_DECRYPTION_INFO: diff --git a/src/encrypt.c b/src/encrypt.c index 792c25c5..9f5134de 100644 --- a/src/encrypt.c +++ b/src/encrypt.c @@ -36,6 +36,9 @@ typedef struct  {    struct _gpgme_op_encrypt_result result; +  /* The error code from a FAILURE status line or 0.  */ +  gpg_error_t failure_code; +    /* A pointer to the next pointer of the last invalid recipient in       the list.  This makes appending new invalid recipients painless       while preserving the order.  */ @@ -114,9 +117,15 @@ _gpgme_encrypt_status_handler (void *priv, gpgme_status_code_t code,    switch (code)      { +    case GPGME_STATUS_FAILURE: +      opd->failure_code = _gpgme_parse_failure (args); +      break; +      case GPGME_STATUS_EOF:        if (opd->result.invalid_recipients)  	return gpg_error (GPG_ERR_UNUSABLE_PUBKEY); +      if (opd->failure_code) +        return opd->failure_code;        break;      case GPGME_STATUS_INV_RECP: diff --git a/src/genkey.c b/src/genkey.c index 18765dde..3afd3b41 100644 --- a/src/genkey.c +++ b/src/genkey.c @@ -37,6 +37,9 @@ typedef struct  {    struct _gpgme_op_genkey_result result; +  /* The error code from a FAILURE status line or 0.  */ +  gpg_error_t failure_code; +    /* The key parameters passed to the crypto engine.  */    gpgme_data_t key_parameter;  } *op_data_t; @@ -118,10 +121,16 @@ genkey_status_handler (void *priv, gpgme_status_code_t code, char *args)  	}        break; +    case GPGME_STATUS_FAILURE: +      opd->failure_code = _gpgme_parse_failure (args); +      break; +      case GPGME_STATUS_EOF:        /* FIXME: Should return some more useful error value.  */        if (!opd->result.primary && !opd->result.sub)  	return gpg_error (GPG_ERR_GENERAL); +      else if (opd->failure_code) +        return opd->failure_code;        break;      case GPGME_STATUS_INQUIRE_MAXLEN: diff --git a/src/gpgme.h.in b/src/gpgme.h.in index 76055708..432d18a1 100644 --- a/src/gpgme.h.in +++ b/src/gpgme.h.in @@ -548,7 +548,8 @@ typedef enum      GPGME_STATUS_ATTRIBUTE = 89,      GPGME_STATUS_BEGIN_SIGNING = 90,      GPGME_STATUS_KEY_NOT_CREATED = 91, -    GPGME_STATUS_INQUIRE_MAXLEN = 92 +    GPGME_STATUS_INQUIRE_MAXLEN = 92, +    GPGME_STATUS_FAILURE = 93    }  gpgme_status_code_t; diff --git a/src/op-support.c b/src/op-support.c index 2bcb3a35..02940efd 100644 --- a/src/op-support.c +++ b/src/op-support.c @@ -337,3 +337,27 @@ _gpgme_parse_plaintext (char *args, char **filenamep)      }    return 0;  } + + +/* Parse a FAILURE status line and return the error code.  ARGS is +   modified to contain the location part.  */ +gpgme_error_t +_gpgme_parse_failure (char *args) +{ +  char *where, *which; + +  where = strchr (args, ' '); +  if (!where) +    return trace_gpg_error (GPG_ERR_INV_ENGINE); + +  *where = '\0'; +  which = where + 1; + +  where = strchr (which, ' '); +  if (where) +    *where = '\0'; + +  where = args; + +  return atoi (which); +} @@ -65,6 +65,10 @@ gpgme_error_t _gpgme_parse_inv_recp (char *args, gpgme_invalid_key_t *key);     FILENAMEP.  */  gpgme_error_t _gpgme_parse_plaintext (char *args, char **filenamep); +/* Parse a FAILURE status line and return the error code.  ARGS is +   modified to contain the location part.  */ +gpgme_error_t _gpgme_parse_failure (char *args); +  /* From verify.c.  */ diff --git a/src/passphrase.c b/src/passphrase.c index 5d656b17..c88e57d2 100644 --- a/src/passphrase.c +++ b/src/passphrase.c @@ -128,6 +128,19 @@ _gpgme_passphrase_status_handler (void *priv, gpgme_status_code_t code,          }        break; +    case GPGME_STATUS_FAILURE: +      /* We abuse this status handler to forward FAILURE status codes +         to the caller.  This should better be done in a generic +         handler, but for now this is sufficient.  */ +      if (ctx->status_cb) +        { +          err = ctx->status_cb (ctx->status_cb_value, "FAILURE", args); +          if (err) +            return err; +        } +      break; + +      default:        /* Ignore all other codes.  */        break; diff --git a/src/passwd.c b/src/passwd.c index e832026d..ff30df01 100644 --- a/src/passwd.c +++ b/src/passwd.c @@ -30,6 +30,9 @@  typedef struct  { +  /* The error code from a FAILURE status line or 0.  */ +  gpg_error_t failure_code; +    int success_seen;    int error_seen;  } *op_data_t; @@ -92,6 +95,10 @@ passwd_status_handler (void *priv, gpgme_status_code_t code, char *args)        opd->success_seen = 1;        break; +    case GPGME_STATUS_FAILURE: +      opd->failure_code = _gpgme_parse_failure (args); +      break; +      case GPGME_STATUS_EOF:        /* In case the OpenPGP engine does not properly implement the           passwd command we won't get a success status back and thus we @@ -102,6 +109,8 @@ passwd_status_handler (void *priv, gpgme_status_code_t code, char *args)        if (ctx->protocol == GPGME_PROTOCOL_OpenPGP            && !opd->error_seen && !opd->success_seen)          err = gpg_error (GPG_ERR_NOT_SUPPORTED); +      else if (opd->failure_code) +        err = opd->failure_code;        break;      default: @@ -39,6 +39,9 @@ typedef struct  {    struct _gpgme_op_sign_result result; +  /* The error code from a FAILURE status line or 0.  */ +  gpg_error_t failure_code; +    /* A pointer to the next pointer of the last invalid signer in       the list.  This makes appending new invalid signers painless       while preserving the order.  */ @@ -327,6 +330,10 @@ _gpgme_sign_status_handler (void *priv, gpgme_status_code_t code, char *args)        opd->last_signer_p = &(*opd->last_signer_p)->next;        break; +    case GPGME_STATUS_FAILURE: +      opd->failure_code = _gpgme_parse_failure (args); +      break; +      case GPGME_STATUS_EOF:        /* The UI server does not send information about the created           signature.  This is irrelevant for this protocol and thus we @@ -335,7 +342,7 @@ _gpgme_sign_status_handler (void *priv, gpgme_status_code_t code, char *args)  	err = gpg_error (GPG_ERR_UNUSABLE_SECKEY);        else if (!opd->sig_created_seen                 && ctx->protocol != GPGME_PROTOCOL_UISERVER) -	err = gpg_error (GPG_ERR_GENERAL); +	err = opd->failure_code? opd->failure_code:gpg_error (GPG_ERR_GENERAL);        break;      case GPGME_STATUS_INQUIRE_MAXLEN: @@ -374,6 +381,7 @@ sign_init_result (gpgme_ctx_t ctx, int ignore_inv_recp)    opd = hook;    if (err)      return err; +  opd->failure_code = 0;    opd->last_signer_p = &opd->result.invalid_signers;    opd->last_sig_p = &opd->result.signatures;    opd->ignore_inv_recp = !!ignore_inv_recp; diff --git a/src/status-table.c b/src/status-table.c index c85fa951..6d428d71 100644 --- a/src/status-table.c +++ b/src/status-table.c @@ -66,6 +66,7 @@ static struct status_table_s status_table[] =    { "ERRSIG", GPGME_STATUS_ERRSIG },    { "EXPKEYSIG", GPGME_STATUS_EXPKEYSIG },    { "EXPSIG", GPGME_STATUS_EXPSIG }, +  { "FAILURE", GPGME_STATUS_FAILURE },    { "FILE_DONE", GPGME_STATUS_FILE_DONE },    { "FILE_ERROR", GPGME_STATUS_FILE_ERROR },    { "FILE_START", GPGME_STATUS_FILE_START }, diff --git a/src/verify.c b/src/verify.c index 84487ee4..75914e22 100644 --- a/src/verify.c +++ b/src/verify.c @@ -38,6 +38,9 @@ typedef struct  {    struct _gpgme_op_verify_result result; +  /* The error code from a FAILURE status line or 0.  */ +  gpg_error_t failure_code; +    gpgme_signature_t current_sig;    int did_prepare_new_sig;    int only_newsig_seen; @@ -769,6 +772,10 @@ _gpgme_verify_status_handler (void *priv, gpgme_status_code_t code, char *args)           error code if we are not ready to process this status.  */        return parse_error (sig, args, !!sig ); +    case GPGME_STATUS_FAILURE: +      opd->failure_code = _gpgme_parse_failure (args); +      break; +      case GPGME_STATUS_EOF:        if (sig && !opd->did_prepare_new_sig)  	calc_sig_summary (sig); @@ -795,6 +802,8 @@ _gpgme_verify_status_handler (void *priv, gpgme_status_code_t code, char *args)            opd->current_sig = NULL;          }        opd->only_newsig_seen = 0; +      if (opd->failure_code) +        return opd->failure_code;        break;      case GPGME_STATUS_PLAINTEXT: | 
