Commit 9831200edf for openssl.org
commit 9831200edfe71ad676799a06673d80e6ea3990e2
Author: Neil Horman <nhorman@openssl.org>
Date: Tue Sep 9 09:47:34 2025 -0400
support passing prop querys to composite algs
We have several composite alg usages (i.e. MAC/KDF) which pick the right
digest implementation when using an engine, but fail to get the right
one when using a provider because we don't pass the propquery in a
parameter to their instantiation.
Fix them up by constructing the appropriate parameters
Reviewed-by: Matt Caswell <matt@openssl.org>
Reviewed-by: Shane Lontis <shane.lontis@oracle.com>
Reviewed-by: Paul Dale <ppzgs1@gmail.com>
(Merged from https://github.com/openssl/openssl/pull/28461)
diff --git a/crypto/evp/mac_lib.c b/crypto/evp/mac_lib.c
index 58ddf76151..2a7fa12043 100644
--- a/crypto/evp/mac_lib.c
+++ b/crypto/evp/mac_lib.c
@@ -259,8 +259,9 @@ unsigned char *EVP_Q_mac(OSSL_LIB_CTX *libctx,
unsigned char *out, size_t outsize, size_t *outlen)
{
EVP_MAC *mac = EVP_MAC_fetch(libctx, name, propq);
- OSSL_PARAM subalg_param[] = { OSSL_PARAM_END, OSSL_PARAM_END };
- EVP_MAC_CTX *ctx = NULL;
+ OSSL_PARAM subalg_param[3];
+ OSSL_PARAM *p = subalg_param;
+ EVP_MAC_CTX *ctx = NULL;
size_t len = 0;
unsigned char *res = NULL;
@@ -284,9 +285,26 @@ unsigned char *EVP_Q_mac(OSSL_LIB_CTX *libctx,
goto err;
}
}
- subalg_param[0] =
- OSSL_PARAM_construct_utf8_string(param_name, (char *)subalg, 0);
+ *p++ = OSSL_PARAM_construct_utf8_string(param_name, (char *)subalg, 0);
}
+
+ /*
+ * If we passed in a property query, make sure the underlying algorithm uses it.
+ * Compound algorithms may fetch other underlying algorithms (i.e. a MAC algorithm
+ * may use a digest algorithm as part of its internal work), and the MAC decides which
+ * implementation of the underlying digest to use based on the
+ * OSSL_ALG_PARAM_PROPERTIES parameter, rather than the propq value passed in the
+ * EVP_MAC_fetch call above.
+ * If we don't set this parameter, then the MAC alg may use the default provider
+ * to allocate an underlying digest, rather than the one that we would have gotten
+ * by using the propq value here.
+ */
+ if (propq != NULL)
+ *p++ = OSSL_PARAM_construct_utf8_string(OSSL_ALG_PARAM_PROPERTIES,
+ (char *)propq, 0);
+
+ *p = OSSL_PARAM_construct_end();
+
/* Single-shot - on NULL key input, set dummy key value for EVP_MAC_Init. */
if (key == NULL && keylen == 0)
key = data;
diff --git a/ssl/record/methods/tls1_meth.c b/ssl/record/methods/tls1_meth.c
index f369d9246d..ac31d359c9 100644
--- a/ssl/record/methods/tls1_meth.c
+++ b/ssl/record/methods/tls1_meth.c
@@ -28,6 +28,7 @@ static int tls1_set_crypto_state(OSSL_RECORD_LAYER *rl, int level,
{
EVP_CIPHER_CTX *ciph_ctx;
EVP_PKEY *mac_key;
+ OSSL_PARAM params[3], *p = params;
int enc = (rl->direction == OSSL_RECORD_DIRECTION_WRITE) ? 1 : 0;
if (level != OSSL_RECORD_PROTECTION_LEVEL_APPLICATION)
@@ -73,10 +74,24 @@ static int tls1_set_crypto_state(OSSL_RECORD_LAYER *rl, int level,
mac_key = EVP_PKEY_new_mac_key(mactype, NULL, mackey,
(int)mackeylen);
}
+
+ *p++ = OSSL_PARAM_construct_utf8_string(OSSL_MAC_PARAM_DIGEST,
+ (char *)EVP_MD_get0_name(md), 0);
+
+ /*
+ * We want the underlying mac to use our passed property query when allocating
+ * its internal digest as well
+ */
+ if (rl->propq != NULL)
+ *p++ = OSSL_PARAM_construct_utf8_string(OSSL_MAC_PARAM_PROPERTIES,
+ (char *)rl->propq, 0);
+
+ *p = OSSL_PARAM_construct_end();
+
if (mac_key == NULL
|| EVP_DigestSignInit_ex(rl->md_ctx, NULL, EVP_MD_get0_name(md),
rl->libctx, rl->propq, mac_key,
- NULL) <= 0) {
+ params) <= 0) {
EVP_PKEY_free(mac_key);
ERR_raise(ERR_LIB_SSL, ERR_R_INTERNAL_ERROR);
return OSSL_RECORD_RETURN_FATAL;
diff --git a/ssl/statem/extensions.c b/ssl/statem/extensions.c
index b3158dfd77..d637e06d53 100644
--- a/ssl/statem/extensions.c
+++ b/ssl/statem/extensions.c
@@ -19,6 +19,7 @@
#include "../ssl_local.h"
#include "statem_local.h"
#include <openssl/ocsp.h>
+#include <openssl/core_names.h>
static int final_renegotiate(SSL_CONNECTION *s, unsigned int context, int sent);
static int init_server_name(SSL_CONNECTION *s, unsigned int context);
@@ -1536,6 +1537,7 @@ int tls_psk_do_binder(SSL_CONNECTION *s, const EVP_MD *md,
int ret = -1;
int usepskfored = 0;
SSL_CTX *sctx = SSL_CONNECTION_GET_CTX(s);
+ OSSL_PARAM params[3] = { OSSL_PARAM_END, OSSL_PARAM_END, OSSL_PARAM_END };
/* Ensure cast to size_t is safe */
if (!ossl_assert(hashsizei > 0)) {
@@ -1666,9 +1668,15 @@ int tls_psk_do_binder(SSL_CONNECTION *s, const EVP_MD *md,
if (!sign)
binderout = tmpbinder;
+ if (sctx->propq != NULL) {
+ params[0] = OSSL_PARAM_construct_utf8_string(OSSL_MAC_PARAM_DIGEST,
+ (char *)EVP_MD_get0_name(md), 0);
+ params[1] = OSSL_PARAM_construct_utf8_string(OSSL_MAC_PARAM_PROPERTIES,
+ (char *)sctx->propq, 0);
+ }
bindersize = hashsize;
if (EVP_DigestSignInit_ex(mctx, NULL, EVP_MD_get0_name(md), sctx->libctx,
- sctx->propq, mackey, NULL) <= 0
+ sctx->propq, mackey, params) <= 0
|| EVP_DigestSignUpdate(mctx, hash, hashsize) <= 0
|| EVP_DigestSignFinal(mctx, binderout, &bindersize) <= 0
|| bindersize != hashsize) {
diff --git a/ssl/t1_enc.c b/ssl/t1_enc.c
index a28a1532f1..a53a8c290f 100644
--- a/ssl/t1_enc.c
+++ b/ssl/t1_enc.c
@@ -35,7 +35,7 @@ static int tls1_PRF(SSL_CONNECTION *s,
const EVP_MD *md = ssl_prf_md(s);
EVP_KDF *kdf;
EVP_KDF_CTX *kctx = NULL;
- OSSL_PARAM params[8], *p = params;
+ OSSL_PARAM params[9], *p = params;
const char *mdname;
if (md == NULL) {
@@ -71,6 +71,13 @@ static int tls1_PRF(SSL_CONNECTION *s,
(void *)seed4, (size_t)seed4_len);
*p++ = OSSL_PARAM_construct_octet_string(OSSL_KDF_PARAM_SEED,
(void *)seed5, (size_t)seed5_len);
+ /*
+ * If we have a propery query string, the kdf needs to know about it in the event
+ * the specific kdf in use allocated a digest as part of its implementation
+ */
+ if (SSL_CONNECTION_GET_CTX(s)->propq != NULL)
+ *p++ = OSSL_PARAM_construct_utf8_string(OSSL_KDF_PARAM_PROPERTIES,
+ (char *)SSL_CONNECTION_GET_CTX(s)->propq, 0);
*p = OSSL_PARAM_construct_end();
if (EVP_KDF_derive(kctx, out, olen, params)) {
EVP_KDF_CTX_free(kctx);
diff --git a/ssl/tls13_enc.c b/ssl/tls13_enc.c
index 5953de3233..489fafd521 100644
--- a/ssl/tls13_enc.c
+++ b/ssl/tls13_enc.c
@@ -39,7 +39,7 @@ int tls13_hkdf_expand_ex(OSSL_LIB_CTX *libctx, const char *propq,
{
EVP_KDF *kdf = EVP_KDF_fetch(libctx, OSSL_KDF_NAME_TLS1_3_KDF, propq);
EVP_KDF_CTX *kctx;
- OSSL_PARAM params[7], *p = params;
+ OSSL_PARAM params[8], *p = params;
int mode = EVP_PKEY_HKDEF_MODE_EXPAND_ONLY;
const char *mdname = EVP_MD_get0_name(md);
int ret;
@@ -84,6 +84,10 @@ int tls13_hkdf_expand_ex(OSSL_LIB_CTX *libctx, const char *propq,
*p++ = OSSL_PARAM_construct_octet_string(OSSL_KDF_PARAM_DATA,
(unsigned char *)data,
datalen);
+ if (propq != NULL)
+ *p++ = OSSL_PARAM_construct_utf8_string(OSSL_KDF_PARAM_PROPERTIES,
+ (char *)propq, 0);
+
*p++ = OSSL_PARAM_construct_end();
ret = EVP_KDF_derive(kctx, out, outlen, params) <= 0;