From 6b1e5fa4873ff2f7741f996961f26ab9818ee190 Mon Sep 17 00:00:00 2001 From: Matt Caswell Date: Wed, 25 Mar 2020 12:12:59 +0000 Subject: [PATCH] Put an error on the stack in the event of a fetch failure Fetch failures are a common problem and it is useful to have detailed information about what was requested in the event of a failure. Reviewed-by: Tomas Mraz Reviewed-by: Richard Levitte (Merged from https://github.com/openssl/openssl/pull/11405) --- crypto/context.c | 9 +++++++ crypto/evp/evp_fetch.c | 54 ++++++++++++++++++++++++++++++++----- crypto/evp/pkey_mac.c | 6 ++++- include/internal/cryptlib.h | 1 + 4 files changed, 63 insertions(+), 7 deletions(-) diff --git a/crypto/context.c b/crypto/context.c index dcf960bfa7..35530174b8 100644 --- a/crypto/context.c +++ b/crypto/context.c @@ -172,6 +172,15 @@ OPENSSL_CTX *openssl_ctx_get_concrete(OPENSSL_CTX *ctx) return ctx; } +int openssl_ctx_is_default(OPENSSL_CTX *ctx) +{ +#ifndef FIPS_MODE + if (ctx == NULL || ctx == default_context) + return 1; +#endif + return 0; +} + static void openssl_ctx_generic_new(void *parent_ign, void *ptr_ign, CRYPTO_EX_DATA *ad, int index, long argl_ign, void *argp) diff --git a/crypto/evp/evp_fetch.c b/crypto/evp/evp_fetch.c index da7f33e95e..e808bf818f 100644 --- a/crypto/evp/evp_fetch.c +++ b/crypto/evp/evp_fetch.c @@ -294,9 +294,26 @@ void *evp_generic_fetch(OPENSSL_CTX *libctx, int operation_id, int (*up_ref_method)(void *), void (*free_method)(void *)) { - return inner_evp_generic_fetch(libctx, - operation_id, 0, name, properties, - new_method, up_ref_method, free_method); + void *ret = inner_evp_generic_fetch(libctx, + operation_id, 0, name, properties, + new_method, up_ref_method, free_method); + + if (ret == NULL) { + int code = EVP_R_FETCH_FAILED; + +#ifdef FIPS_MODE + ERR_raise(ERR_LIB_EVP, code); +#else + ERR_raise_data(ERR_LIB_EVP, code, + "%s, Algorithm (%s), Properties (%s)", + (openssl_ctx_is_default(libctx) + ? "Default library context" + : "Non-default library context"), + name = NULL ? "" : name, + properties == NULL ? "" : properties); +#endif + } + return ret; } /* @@ -314,9 +331,34 @@ void *evp_generic_fetch_by_number(OPENSSL_CTX *libctx, int operation_id, int (*up_ref_method)(void *), void (*free_method)(void *)) { - return inner_evp_generic_fetch(libctx, - operation_id, name_id, NULL, properties, - new_method, up_ref_method, free_method); + void *ret = inner_evp_generic_fetch(libctx, + operation_id, name_id, NULL, + properties, new_method, up_ref_method, + free_method); + + if (ret == NULL) { + int code = EVP_R_FETCH_FAILED; + +#ifdef FIPS_MODE + ERR_raise(ERR_LIB_EVP, code); +#else + { + OSSL_NAMEMAP *namemap = ossl_namemap_stored(libctx); + const char *name = (namemap == NULL) + ? NULL + : ossl_namemap_num2name(namemap, name_id, 0); + + ERR_raise_data(ERR_LIB_EVP, code, + "%s, Algorithm (%s), Properties (%s)", + (openssl_ctx_is_default(libctx) + ? "Default library context" + : "Non-default library context"), + name = NULL ? "" : name, + properties == NULL ? "" : properties); + } +#endif + } + return ret; } int EVP_set_default_properties(OPENSSL_CTX *libctx, const char *propq) diff --git a/crypto/evp/pkey_mac.c b/crypto/evp/pkey_mac.c index 7430b62b0b..7452e0320d 100644 --- a/crypto/evp/pkey_mac.c +++ b/crypto/evp/pkey_mac.c @@ -51,7 +51,11 @@ static int pkey_mac_init(EVP_PKEY_CTX *ctx) MAC_PKEY_CTX *hctx; /* We're being smart and using the same base NIDs for PKEY and for MAC */ int nid = ctx->pmeth->pkey_id; - EVP_MAC *mac = EVP_MAC_fetch(ctx->libctx, OBJ_nid2sn(nid), ctx->propquery); + EVP_MAC *mac; + + ERR_set_mark(); + mac = EVP_MAC_fetch(ctx->libctx, OBJ_nid2sn(nid), ctx->propquery); + ERR_pop_to_mark(); /* * mac == NULL may actually be ok in some situations. In an diff --git a/include/internal/cryptlib.h b/include/internal/cryptlib.h index 19e2c9744e..9a60f413bf 100644 --- a/include/internal/cryptlib.h +++ b/include/internal/cryptlib.h @@ -165,6 +165,7 @@ typedef struct openssl_ctx_method { } OPENSSL_CTX_METHOD; OPENSSL_CTX *openssl_ctx_get_concrete(OPENSSL_CTX *ctx); +int openssl_ctx_is_default(OPENSSL_CTX *ctx); /* Functions to retrieve pointers to data by index */ void *openssl_ctx_get_data(OPENSSL_CTX *, int /* index */, -- 2.25.1