diff options
Diffstat (limited to 'providers/implementations/kdfs/krb5kdf.c')
-rw-r--r-- | providers/implementations/kdfs/krb5kdf.c | 41 |
1 files changed, 34 insertions, 7 deletions
diff --git a/providers/implementations/kdfs/krb5kdf.c b/providers/implementations/kdfs/krb5kdf.c index 8516a3f824af..566afa74fece 100644 --- a/providers/implementations/kdfs/krb5kdf.c +++ b/providers/implementations/kdfs/krb5kdf.c @@ -1,5 +1,5 @@ /* - * Copyright 2018-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -34,6 +34,7 @@ /* KRB5 KDF defined in RFC 3961, Section 5.1 */ static OSSL_FUNC_kdf_newctx_fn krb5kdf_new; +static OSSL_FUNC_kdf_dupctx_fn krb5kdf_dup; static OSSL_FUNC_kdf_freectx_fn krb5kdf_free; static OSSL_FUNC_kdf_reset_fn krb5kdf_reset; static OSSL_FUNC_kdf_derive_fn krb5kdf_derive; @@ -63,10 +64,8 @@ static void *krb5kdf_new(void *provctx) if (!ossl_prov_is_running()) return NULL; - if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) == NULL) { - ERR_raise(ERR_LIB_PROV, ERR_R_MALLOC_FAILURE); + if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) == NULL) return NULL; - } ctx->provctx = provctx; return ctx; } @@ -102,6 +101,27 @@ static int krb5kdf_set_membuf(unsigned char **dst, size_t *dst_len, return OSSL_PARAM_get_octet_string(p, (void **)dst, 0, dst_len); } +static void *krb5kdf_dup(void *vctx) +{ + const KRB5KDF_CTX *src = (const KRB5KDF_CTX *)vctx; + KRB5KDF_CTX *dest; + + dest = krb5kdf_new(src->provctx); + if (dest != NULL) { + if (!ossl_prov_memdup(src->key, src->key_len, + &dest->key, &dest->key_len) + || !ossl_prov_memdup(src->constant, src->constant_len, + &dest->constant , &dest->constant_len) + || !ossl_prov_cipher_copy(&dest->cipher, &src->cipher)) + goto err; + } + return dest; + + err: + krb5kdf_free(dest); + return NULL; +} + static int krb5kdf_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { @@ -137,7 +157,7 @@ static int krb5kdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) KRB5KDF_CTX *ctx = vctx; OSSL_LIB_CTX *provctx = PROV_LIBCTX_OF(ctx->provctx); - if (params == NULL) + if (ossl_param_is_empty(params)) return 1; if (!ossl_prov_cipher_load_from_params(&ctx->cipher, params, provctx)) @@ -198,6 +218,7 @@ static const OSSL_PARAM *krb5kdf_gettable_ctx_params(ossl_unused void *ctx, const OSSL_DISPATCH ossl_kdf_krb5kdf_functions[] = { { OSSL_FUNC_KDF_NEWCTX, (void(*)(void))krb5kdf_new }, + { OSSL_FUNC_KDF_DUPCTX, (void(*)(void))krb5kdf_dup }, { OSSL_FUNC_KDF_FREECTX, (void(*)(void))krb5kdf_free }, { OSSL_FUNC_KDF_RESET, (void(*)(void))krb5kdf_reset }, { OSSL_FUNC_KDF_DERIVE, (void(*)(void))krb5kdf_derive }, @@ -209,7 +230,7 @@ const OSSL_DISPATCH ossl_kdf_krb5kdf_functions[] = { (void(*)(void))krb5kdf_gettable_ctx_params }, { OSSL_FUNC_KDF_GET_CTX_PARAMS, (void(*)(void))krb5kdf_get_ctx_params }, - { 0, NULL } + OSSL_DISPATCH_END }; #ifndef OPENSSL_NO_DES @@ -254,7 +275,7 @@ static int fixup_des3_key(unsigned char *key) * * block = 0 * for k: 1 -> K - * block += s[N(k-1)..(N-1)k] (one's complement addition) + * block += s[N(k-1)..(N-1)k] (ones'-complement addition) * * Optimizing for space we compute: * for each l in L-1 -> 0: @@ -395,6 +416,12 @@ static int KRB5KDF(const EVP_CIPHER *cipher, ENGINE *engine, /* Initialize input block */ blocksize = EVP_CIPHER_CTX_get_block_size(ctx); + if (blocksize == 0) { + ERR_raise(ERR_LIB_PROV, PROV_R_MISSING_CIPHER); + ret = 0; + goto out; + } + if (constant_len > blocksize) { ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_CONSTANT_LENGTH); ret = 0; |