diff options
Diffstat (limited to 'crypto/cms/cms_pwri.c')
-rw-r--r-- | crypto/cms/cms_pwri.c | 117 |
1 files changed, 66 insertions, 51 deletions
diff --git a/crypto/cms/cms_pwri.c b/crypto/cms/cms_pwri.c index d7414883396c..2373092bed55 100644 --- a/crypto/cms/cms_pwri.c +++ b/crypto/cms/cms_pwri.c @@ -1,7 +1,7 @@ /* - * Copyright 2009-2018 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2009-2022 The OpenSSL Project Authors. All Rights Reserved. * - * Licensed under the OpenSSL license (the "License"). You may not use + * 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 * in the file LICENSE in the source distribution or at * https://www.openssl.org/source/license.html @@ -15,15 +15,16 @@ #include <openssl/cms.h> #include <openssl/rand.h> #include <openssl/aes.h> -#include "cms_local.h" +#include "internal/sizes.h" #include "crypto/asn1.h" +#include "cms_local.h" int CMS_RecipientInfo_set0_password(CMS_RecipientInfo *ri, unsigned char *pass, ossl_ssize_t passlen) { CMS_PasswordRecipientInfo *pwri; if (ri->type != CMS_RECIPINFO_PASS) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_SET0_PASSWORD, CMS_R_NOT_PWRI); + ERR_raise(ERR_LIB_CMS, CMS_R_NOT_PWRI); return 0; } @@ -42,16 +43,21 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms, ossl_ssize_t passlen, const EVP_CIPHER *kekciph) { + STACK_OF(CMS_RecipientInfo) *ris; CMS_RecipientInfo *ri = NULL; - CMS_EnvelopedData *env; + CMS_EncryptedContentInfo *ec; CMS_PasswordRecipientInfo *pwri; EVP_CIPHER_CTX *ctx = NULL; X509_ALGOR *encalg = NULL; unsigned char iv[EVP_MAX_IV_LENGTH]; int ivlen; + const CMS_CTX *cms_ctx = ossl_cms_get0_cmsctx(cms); - env = cms_get0_enveloped(cms); - if (!env) + ec = ossl_cms_get0_env_enc_content(cms); + if (ec == NULL) + return NULL; + ris = CMS_get0_RecipientInfos(cms); + if (ris == NULL) return NULL; if (wrap_nid <= 0) @@ -62,15 +68,14 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms, /* Get from enveloped data */ if (kekciph == NULL) - kekciph = env->encryptedContentInfo->cipher; + kekciph = ec->cipher; if (kekciph == NULL) { - CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, CMS_R_NO_CIPHER); + ERR_raise(ERR_LIB_CMS, CMS_R_NO_CIPHER); return NULL; } if (wrap_nid != NID_id_alg_PWRI_KEK) { - CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, - CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM); + ERR_raise(ERR_LIB_CMS, CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM); return NULL; } @@ -80,34 +85,41 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms, goto merr; } ctx = EVP_CIPHER_CTX_new(); + if (ctx == NULL) { + ERR_raise(ERR_LIB_CMS, ERR_R_MALLOC_FAILURE); + goto err; + } if (EVP_EncryptInit_ex(ctx, kekciph, NULL, NULL, NULL) <= 0) { - CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_EVP_LIB); + ERR_raise(ERR_LIB_CMS, ERR_R_EVP_LIB); goto err; } - ivlen = EVP_CIPHER_CTX_iv_length(ctx); + ivlen = EVP_CIPHER_CTX_get_iv_length(ctx); + if (ivlen < 0) { + ERR_raise(ERR_LIB_CMS, ERR_R_EVP_LIB); + goto err; + } if (ivlen > 0) { - if (RAND_bytes(iv, ivlen) <= 0) + if (RAND_bytes_ex(ossl_cms_ctx_get0_libctx(cms_ctx), iv, ivlen, 0) <= 0) goto err; if (EVP_EncryptInit_ex(ctx, NULL, NULL, NULL, iv) <= 0) { - CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_EVP_LIB); + ERR_raise(ERR_LIB_CMS, ERR_R_EVP_LIB); goto err; } encalg->parameter = ASN1_TYPE_new(); if (!encalg->parameter) { - CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_MALLOC_FAILURE); + ERR_raise(ERR_LIB_CMS, ERR_R_MALLOC_FAILURE); goto err; } if (EVP_CIPHER_param_to_asn1(ctx, encalg->parameter) <= 0) { - CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, - CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR); + ERR_raise(ERR_LIB_CMS, CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR); goto err; } } - encalg->algorithm = OBJ_nid2obj(EVP_CIPHER_CTX_type(ctx)); + encalg->algorithm = OBJ_nid2obj(EVP_CIPHER_CTX_get_type(ctx)); EVP_CIPHER_CTX_free(ctx); ctx = NULL; @@ -123,6 +135,7 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms, ri->type = CMS_RECIPINFO_PASS; pwri = ri->d.pwri; + pwri->cms_ctx = cms_ctx; /* Since this is overwritten, free up empty structure already there */ X509_ALGOR_free(pwri->keyEncryptionAlgorithm); pwri->keyEncryptionAlgorithm = X509_ALGOR_new(); @@ -146,19 +159,19 @@ CMS_RecipientInfo *CMS_add0_recipient_password(CMS_ContentInfo *cms, pwri->keyDerivationAlgorithm = PKCS5_pbkdf2_set(iter, NULL, 0, -1, -1); - if (!pwri->keyDerivationAlgorithm) + if (pwri->keyDerivationAlgorithm == NULL) goto err; CMS_RecipientInfo_set0_password(ri, pass, passlen); pwri->version = 0; - if (!sk_CMS_RecipientInfo_push(env->recipientInfos, ri)) + if (!sk_CMS_RecipientInfo_push(ris, ri)) goto merr; return ri; merr: - CMSerr(CMS_F_CMS_ADD0_RECIPIENT_PASSWORD, ERR_R_MALLOC_FAILURE); + ERR_raise(ERR_LIB_CMS, ERR_R_MALLOC_FAILURE); err: EVP_CIPHER_CTX_free(ctx); if (ri) @@ -177,7 +190,7 @@ static int kek_unwrap_key(unsigned char *out, size_t *outlen, const unsigned char *in, size_t inlen, EVP_CIPHER_CTX *ctx) { - size_t blocklen = EVP_CIPHER_CTX_block_size(ctx); + size_t blocklen = EVP_CIPHER_CTX_get_block_size(ctx); unsigned char *tmp; int outl, rv = 0; if (inlen < 2 * blocklen) { @@ -189,7 +202,7 @@ static int kek_unwrap_key(unsigned char *out, size_t *outlen, return 0; } if ((tmp = OPENSSL_malloc(inlen)) == NULL) { - CMSerr(CMS_F_KEK_UNWRAP_KEY, ERR_R_MALLOC_FAILURE); + ERR_raise(ERR_LIB_CMS, ERR_R_MALLOC_FAILURE); return 0; } /* setup IV by decrypting last two blocks */ @@ -230,9 +243,9 @@ static int kek_unwrap_key(unsigned char *out, size_t *outlen, static int kek_wrap_key(unsigned char *out, size_t *outlen, const unsigned char *in, size_t inlen, - EVP_CIPHER_CTX *ctx) + EVP_CIPHER_CTX *ctx, const CMS_CTX *cms_ctx) { - size_t blocklen = EVP_CIPHER_CTX_block_size(ctx); + size_t blocklen = EVP_CIPHER_CTX_get_block_size(ctx); size_t olen; int dummy; /* @@ -258,7 +271,8 @@ static int kek_wrap_key(unsigned char *out, size_t *outlen, memcpy(out + 4, in, inlen); /* Add random padding to end */ if (olen > inlen + 4 - && RAND_bytes(out + 4 + inlen, olen - 4 - inlen) <= 0) + && RAND_bytes_ex(ossl_cms_ctx_get0_libctx(cms_ctx), out + 4 + inlen, + olen - 4 - inlen, 0) <= 0) return 0; /* Encrypt twice */ if (!EVP_EncryptUpdate(ctx, out, &dummy, out, olen) @@ -273,31 +287,32 @@ static int kek_wrap_key(unsigned char *out, size_t *outlen, /* Encrypt/Decrypt content key in PWRI recipient info */ -int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri, - int en_de) +int ossl_cms_RecipientInfo_pwri_crypt(const CMS_ContentInfo *cms, + CMS_RecipientInfo *ri, int en_de) { CMS_EncryptedContentInfo *ec; CMS_PasswordRecipientInfo *pwri; int r = 0; X509_ALGOR *algtmp, *kekalg = NULL; EVP_CIPHER_CTX *kekctx = NULL; - const EVP_CIPHER *kekcipher; + char name[OSSL_MAX_NAME_SIZE]; + EVP_CIPHER *kekcipher; unsigned char *key = NULL; size_t keylen; + const CMS_CTX *cms_ctx = ossl_cms_get0_cmsctx(cms); - ec = cms->d.envelopedData->encryptedContentInfo; + ec = ossl_cms_get0_env_enc_content(cms); pwri = ri->d.pwri; - if (!pwri->pass) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, CMS_R_NO_PASSWORD); + if (pwri->pass == NULL) { + ERR_raise(ERR_LIB_CMS, CMS_R_NO_PASSWORD); return 0; } algtmp = pwri->keyEncryptionAlgorithm; if (!algtmp || OBJ_obj2nid(algtmp->algorithm) != NID_id_alg_PWRI_KEK) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, - CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM); + ERR_raise(ERR_LIB_CMS, CMS_R_UNSUPPORTED_KEY_ENCRYPTION_ALGORITHM); return 0; } @@ -305,30 +320,30 @@ int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri, algtmp->parameter); if (kekalg == NULL) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, - CMS_R_INVALID_KEY_ENCRYPTION_PARAMETER); + ERR_raise(ERR_LIB_CMS, CMS_R_INVALID_KEY_ENCRYPTION_PARAMETER); return 0; } - kekcipher = EVP_get_cipherbyobj(kekalg->algorithm); + OBJ_obj2txt(name, sizeof(name), kekalg->algorithm, 0); + kekcipher = EVP_CIPHER_fetch(ossl_cms_ctx_get0_libctx(cms_ctx), name, + ossl_cms_ctx_get0_propq(cms_ctx)); - if (!kekcipher) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, CMS_R_UNKNOWN_CIPHER); - return 0; + if (kekcipher == NULL) { + ERR_raise(ERR_LIB_CMS, CMS_R_UNKNOWN_CIPHER); + goto err; } kekctx = EVP_CIPHER_CTX_new(); if (kekctx == NULL) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, ERR_R_MALLOC_FAILURE); - return 0; + ERR_raise(ERR_LIB_CMS, ERR_R_MALLOC_FAILURE); + goto err; } /* Fixup cipher based on AlgorithmIdentifier to set IV etc */ if (!EVP_CipherInit_ex(kekctx, kekcipher, NULL, NULL, NULL, en_de)) goto err; EVP_CIPHER_CTX_set_padding(kekctx, 0); if (EVP_CIPHER_asn1_to_param(kekctx, kekalg->parameter) <= 0) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, - CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR); + ERR_raise(ERR_LIB_CMS, CMS_R_CIPHER_PARAMETER_INITIALISATION_ERROR); goto err; } @@ -339,7 +354,7 @@ int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri, if (EVP_PBE_CipherInit(algtmp->algorithm, (char *)pwri->pass, pwri->passlen, algtmp->parameter, kekctx, en_de) < 0) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, ERR_R_EVP_LIB); + ERR_raise(ERR_LIB_CMS, ERR_R_EVP_LIB); goto err; } @@ -347,7 +362,7 @@ int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri, if (en_de) { - if (!kek_wrap_key(NULL, &keylen, ec->key, ec->keylen, kekctx)) + if (!kek_wrap_key(NULL, &keylen, ec->key, ec->keylen, kekctx, cms_ctx)) goto err; key = OPENSSL_malloc(keylen); @@ -355,7 +370,7 @@ int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri, if (key == NULL) goto err; - if (!kek_wrap_key(key, &keylen, ec->key, ec->keylen, kekctx)) + if (!kek_wrap_key(key, &keylen, ec->key, ec->keylen, kekctx, cms_ctx)) goto err; pwri->encryptedKey->data = key; pwri->encryptedKey->length = keylen; @@ -363,13 +378,13 @@ int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri, key = OPENSSL_malloc(pwri->encryptedKey->length); if (key == NULL) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, ERR_R_MALLOC_FAILURE); + ERR_raise(ERR_LIB_CMS, ERR_R_MALLOC_FAILURE); goto err; } if (!kek_unwrap_key(key, &keylen, pwri->encryptedKey->data, pwri->encryptedKey->length, kekctx)) { - CMSerr(CMS_F_CMS_RECIPIENTINFO_PWRI_CRYPT, CMS_R_UNWRAP_FAILURE); + ERR_raise(ERR_LIB_CMS, CMS_R_UNWRAP_FAILURE); goto err; } @@ -382,7 +397,7 @@ int cms_RecipientInfo_pwri_crypt(CMS_ContentInfo *cms, CMS_RecipientInfo *ri, r = 1; err: - + EVP_CIPHER_free(kekcipher); EVP_CIPHER_CTX_free(kekctx); if (!r) |