From 5fdc9797702912d4d0097f9ef66fa856ae3cb452 Mon Sep 17 00:00:00 2001 From: Tobias Brunner Date: Tue, 1 Dec 2020 11:43:40 +0100 Subject: [PATCH] openssl: Extract helper function to derive a shared DH secret --- .../plugins/openssl/openssl_util.c | 43 +++++++++++++++++ .../plugins/openssl/openssl_util.h | 10 ++++ .../openssl/openssl_x_diffie_hellman.c | 47 +------------------ 3 files changed, 55 insertions(+), 45 deletions(-) diff --git a/src/libstrongswan/plugins/openssl/openssl_util.c b/src/libstrongswan/plugins/openssl/openssl_util.c index ac6784a23..55fe80ae8 100644 --- a/src/libstrongswan/plugins/openssl/openssl_util.c +++ b/src/libstrongswan/plugins/openssl/openssl_util.c @@ -29,6 +29,49 @@ #define ASN1_STRING_get0_data(a) ASN1_STRING_data((ASN1_STRING*)a) #endif +/* + * Described in header + */ +bool openssl_compute_shared_key(EVP_PKEY *priv, EVP_PKEY *pub, chunk_t *shared) +{ + EVP_PKEY_CTX *ctx; + bool success = FALSE; + + ctx = EVP_PKEY_CTX_new(priv, NULL); + if (!ctx) + { + return FALSE; + } + + if (EVP_PKEY_derive_init(ctx) <= 0) + { + goto error; + } + + if (EVP_PKEY_derive_set_peer(ctx, pub) <= 0) + { + goto error; + } + + if (EVP_PKEY_derive(ctx, NULL, &shared->len) <= 0) + { + goto error; + } + + *shared = chunk_alloc(shared->len); + + if (EVP_PKEY_derive(ctx, shared->ptr, &shared->len) <= 0) + { + goto error; + } + + success = TRUE; + +error: + EVP_PKEY_CTX_free(ctx); + return success; +} + /** * Described in header. */ diff --git a/src/libstrongswan/plugins/openssl/openssl_util.h b/src/libstrongswan/plugins/openssl/openssl_util.h index c610433b1..eb2a3788b 100644 --- a/src/libstrongswan/plugins/openssl/openssl_util.h +++ b/src/libstrongswan/plugins/openssl/openssl_util.h @@ -36,6 +36,16 @@ */ #define EC_FIELD_ELEMENT_LEN(group) ((EC_GROUP_get_degree(group) + 7) / 8) +/** + * Derives a shared DH secret from the given keys. + * + * @param priv private key + * @param pub public key + * @param shared shared secret + * @return TRUE on success, FALSE otherwise + */ +bool openssl_compute_shared_key(EVP_PKEY *priv, EVP_PKEY *pub, chunk_t *shared); + /** * Creates a hash of a given type of a chunk of data. * diff --git a/src/libstrongswan/plugins/openssl/openssl_x_diffie_hellman.c b/src/libstrongswan/plugins/openssl/openssl_x_diffie_hellman.c index 37943f5bf..3d41eb95a 100644 --- a/src/libstrongswan/plugins/openssl/openssl_x_diffie_hellman.c +++ b/src/libstrongswan/plugins/openssl/openssl_x_diffie_hellman.c @@ -20,6 +20,7 @@ #if OPENSSL_VERSION_NUMBER >= 0x1010100fL && !defined(OPENSSL_NO_ECDH) #include "openssl_x_diffie_hellman.h" +#include "openssl_util.h" #include @@ -71,50 +72,6 @@ static int map_key_type(diffie_hellman_group_t group) } } -/** - * Compute the shared secret - */ -static bool compute_shared_key(private_diffie_hellman_t *this, EVP_PKEY *pub, - chunk_t *shared_secret) -{ - EVP_PKEY_CTX *ctx; - bool success = FALSE; - - ctx = EVP_PKEY_CTX_new(this->key, NULL); - if (!ctx) - { - return FALSE; - } - - if (EVP_PKEY_derive_init(ctx) <= 0) - { - goto error; - } - - if (EVP_PKEY_derive_set_peer(ctx, pub) <= 0) - { - goto error; - } - - if (EVP_PKEY_derive(ctx, NULL, &shared_secret->len) <= 0) - { - goto error; - } - - *shared_secret = chunk_alloc(shared_secret->len); - - if (EVP_PKEY_derive(ctx, shared_secret->ptr, &shared_secret->len) <= 0) - { - goto error; - } - - success = TRUE; - -error: - EVP_PKEY_CTX_free(ctx); - return success; -} - METHOD(diffie_hellman_t, set_other_public_value, bool, private_diffie_hellman_t *this, chunk_t value) { @@ -136,7 +93,7 @@ METHOD(diffie_hellman_t, set_other_public_value, bool, chunk_clear(&this->shared_secret); - if (!compute_shared_key(this, pub, &this->shared_secret)) + if (!openssl_compute_shared_key(this->key, pub, &this->shared_secret)) { DBG1(DBG_LIB, "%N shared secret computation failed", diffie_hellman_group_names, this->group);