From 3bfe9005e5ae0b513bf5f449d6cf558f9b4d9e1f Mon Sep 17 00:00:00 2001 From: Shane Lontis Date: Tue, 20 Aug 2019 08:54:41 +1000 Subject: [PATCH] Add aes_ccm to provider Add Cleanups for gcm - based on the changes to ccm. Reviewed-by: Richard Levitte Reviewed-by: Patrick Steuer (Merged from https://github.com/openssl/openssl/pull/9280) --- crypto/err/openssl.txt | 16 +- crypto/evp/evp_enc.c | 6 + crypto/modes/build.info | 4 +- providers/common/ciphers/aes.c | 1 - providers/common/ciphers/aes_ccm_s390x.c | 263 ++++++++++ providers/common/ciphers/build.info | 4 +- providers/common/ciphers/ccm.c | 486 ++++++++++++++++++ providers/common/ciphers/ccm_hw.c | 199 +++++++ providers/common/ciphers/ciphers_ccm.h | 125 +++++ providers/common/ciphers/ciphers_gcm.h | 40 +- providers/common/ciphers/ciphers_locl.h | 74 +-- providers/common/ciphers/gcm.c | 53 +- .../common/include/internal/provider_algs.h | 6 + .../include/internal/providercommonerr.h | 15 +- providers/common/provider_err.c | 9 +- providers/default/defltprov.c | 7 + providers/fips/fipsprov.c | 19 + test/recipes/30-test_evp_data/evpciph.txt | 6 + 18 files changed, 1238 insertions(+), 95 deletions(-) create mode 100644 providers/common/ciphers/aes_ccm_s390x.c create mode 100644 providers/common/ciphers/ccm.c create mode 100644 providers/common/ciphers/ccm_hw.c create mode 100644 providers/common/ciphers/ciphers_ccm.h diff --git a/crypto/err/openssl.txt b/crypto/err/openssl.txt index 49e3120ce9..a545636447 100644 --- a/crypto/err/openssl.txt +++ b/crypto/err/openssl.txt @@ -547,15 +547,15 @@ EC_F_ECDH_COMPUTE_KEY:246:ECDH_compute_key EC_F_ECDH_SIMPLE_COMPUTE_KEY:257:ecdh_simple_compute_key EC_F_ECDSA_DO_SIGN_EX:251:ECDSA_do_sign_ex EC_F_ECDSA_DO_VERIFY:252:ECDSA_do_verify +EC_F_ECDSA_S390X_NISTP_SIGN_SIG:313:ecdsa_s390x_nistp_sign_sig +EC_F_ECDSA_S390X_NISTP_VERIFY_SIG:314:ecdsa_s390x_nistp_verify_sig EC_F_ECDSA_SIGN_EX:254:ECDSA_sign_ex EC_F_ECDSA_SIGN_SETUP:248:ECDSA_sign_setup EC_F_ECDSA_SIG_NEW:265:ECDSA_SIG_new -EC_F_ECDSA_VERIFY:253:ECDSA_verify EC_F_ECDSA_SIMPLE_SIGN_SETUP:310:ecdsa_simple_sign_setup EC_F_ECDSA_SIMPLE_SIGN_SIG:311:ecdsa_simple_sign_sig EC_F_ECDSA_SIMPLE_VERIFY_SIG:312:ecdsa_simple_verify_sig -EC_F_ECDSA_S390X_NISTP_SIGN_SIG:313:ecdsa_s390x_nistp_sign_sig -EC_F_ECDSA_S390X_NISTP_VERIFY_SIG:314:ecdsa_s390x_nistp_verify_sig +EC_F_ECDSA_VERIFY:253:ECDSA_verify EC_F_ECD_ITEM_VERIFY:270:ecd_item_verify EC_F_ECKEY_PARAM2TYPE:223:eckey_param2type EC_F_ECKEY_PARAM_DECODE:212:eckey_param_decode @@ -1150,12 +1150,12 @@ PROV_F_AESNI_INIT_KEY:101:aesni_init_key PROV_F_AES_BLOCK_FINAL:102:aes_block_final PROV_F_AES_BLOCK_UPDATE:103:aes_block_update PROV_F_AES_CIPHER:104:aes_cipher -PROV_F_AES_GET_CTX_PARAMS:105:aes_get_ctx_params -PROV_F_AES_SET_CTX_PARAMS:106:aes_set_ctx_params PROV_F_AES_DINIT:107:aes_dinit PROV_F_AES_DUPCTX:108:aes_dupctx PROV_F_AES_EINIT:109:aes_einit +PROV_F_AES_GET_CTX_PARAMS:105:aes_get_ctx_params PROV_F_AES_INIT_KEY:110:aes_init_key +PROV_F_AES_SET_CTX_PARAMS:106:aes_set_ctx_params PROV_F_AES_STREAM_UPDATE:111:aes_stream_update PROV_F_AES_T4_INIT_KEY:112:aes_t4_init_key PROV_F_BLAKE2_MAC_INIT:115:blake2_mac_init @@ -2712,13 +2712,19 @@ PROV_R_FAILED_TO_GET_PARAMETER:103:failed to get parameter PROV_R_FAILED_TO_SET_PARAMETER:104:failed to set parameter PROV_R_INVALID_AAD:108:invalid aad PROV_R_INVALID_CUSTOM_LENGTH:111:invalid custom length +PROV_R_INVALID_DATA:115:invalid data +PROV_R_INVALID_IVLEN:116:invalid ivlen PROV_R_INVALID_IV_LENGTH:109:invalid iv length +PROV_R_INVALID_KEYLEN:117:invalid keylen PROV_R_INVALID_KEY_LENGTH:105:invalid key length PROV_R_INVALID_SALT_LENGTH:112:invalid salt length PROV_R_INVALID_TAG:110:invalid tag +PROV_R_INVALID_TAGLEN:118:invalid taglen PROV_R_NOT_XOF_OR_INVALID_LENGTH:113:not xof or invalid length PROV_R_NO_KEY_SET:114:no key set PROV_R_OUTPUT_BUFFER_TOO_SMALL:106:output buffer too small +PROV_R_TAG_NOTSET:119:tag notset +PROV_R_TAG_NOT_NEEDED:120:tag not needed PROV_R_WRONG_FINAL_BLOCK_LENGTH:107:wrong final block length RAND_R_ADDITIONAL_INPUT_TOO_LONG:102:additional input too long RAND_R_ALREADY_INSTANTIATED:103:already instantiated diff --git a/crypto/evp/evp_enc.c b/crypto/evp/evp_enc.c index 42d8099ec7..51a6423c82 100644 --- a/crypto/evp/evp_enc.c +++ b/crypto/evp/evp_enc.c @@ -169,6 +169,12 @@ int EVP_CipherInit_ex(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *cipher, case NID_aria_256_gcm: case NID_aria_192_gcm: case NID_aria_128_gcm: + case NID_aes_256_ccm: + case NID_aes_192_ccm: + case NID_aes_128_ccm: + case NID_aria_256_ccm: + case NID_aria_192_ccm: + case NID_aria_128_ccm: break; default: goto legacy; diff --git a/crypto/modes/build.info b/crypto/modes/build.info index a93586690c..fa5e52f50e 100644 --- a/crypto/modes/build.info +++ b/crypto/modes/build.info @@ -48,9 +48,9 @@ IF[{- !$disabled{asm} -}] ENDIF ENDIF -$COMMON=cbc128.c ctr128.c cfb128.c ofb128.c gcm128.c $MODESASM +$COMMON=cbc128.c ctr128.c cfb128.c ofb128.c gcm128.c ccm128.c $MODESASM SOURCE[../../libcrypto]=$COMMON \ - cts128.c ccm128.c xts128.c wrap128.c ocb128.c siv128.c + cts128.c xts128.c wrap128.c ocb128.c siv128.c DEFINE[../../libcrypto]=$MODESDEF SOURCE[../../providers/fips]=$COMMON DEFINE[../../providers/fips]=$MODESDEF diff --git a/providers/common/ciphers/aes.c b/providers/common/ciphers/aes.c index 26b8c4475a..1b1074af16 100644 --- a/providers/common/ciphers/aes.c +++ b/providers/common/ciphers/aes.c @@ -401,7 +401,6 @@ IMPLEMENT_cipher(ctr, CTR, 0, 256, 8, 128) IMPLEMENT_cipher(ctr, CTR, 0, 192, 8, 128) IMPLEMENT_cipher(ctr, CTR, 0, 128, 8, 128) - #define IMPLEMENT_funcs(mode, kbits, type) \ const OSSL_DISPATCH aes##kbits##mode##_functions[] = { \ { OSSL_FUNC_CIPHER_NEWCTX, (void (*)(void))aes_##kbits##_##mode##_newctx },\ diff --git a/providers/common/ciphers/aes_ccm_s390x.c b/providers/common/ciphers/aes_ccm_s390x.c new file mode 100644 index 0000000000..c5aa6bc309 --- /dev/null +++ b/providers/common/ciphers/aes_ccm_s390x.c @@ -0,0 +1,263 @@ +/* + * Copyright 2001-2019 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 + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#define S390X_CCM_AAD_FLAG 0x40 + +static int s390x_aes_ccm_init_key(PROV_CCM_CTX *ctx, + const unsigned char *key, size_t keylen) +{ + PROV_AES_CCM_CTX *sctx = (PROV_AES_CCM_CTX *)ctx; + + sctx->ccm.s390x.fc = S390X_AES_FC(keylen); + memcpy(&sctx->ccm.s390x.kmac.k, key, keylen); + /* Store encoded m and l. */ + sctx->ccm.s390x.nonce.b[0] = ((ctx->l - 1) & 0x7) + | (((ctx->m - 2) >> 1) & 0x7) << 3; + memset(sctx->ccm.s390x.nonce.b + 1, 0, sizeof(sctx->ccm.s390x.nonce.b)); + sctx->ccm.s390x.blocks = 0; + ctx->key_set = 1; + return 1; +} + +static int s390x_aes_ccm_setiv(PROV_CCM_CTX *ctx, + const unsigned char *nonce, size_t noncelen, + size_t mlen) +{ + PROV_AES_CCM_CTX *sctx = (PROV_AES_CCM_CTX *)ctx; + + sctx->ccm.s390x.nonce.b[0] &= ~S390X_CCM_AAD_FLAG; + sctx->ccm.s390x.nonce.g[1] = mlen; + memcpy(sctx->ccm.s390x.nonce.b + 1, nonce, 15 - ctx->l); + return 1; +} + +/*- + * Process additional authenticated data. Code is big-endian. + */ +static int s390x_aes_ccm_setaad(PROV_CCM_CTX *ctx, + const unsigned char *aad, size_t alen) +{ + PROV_AES_CCM_CTX *sctx = (PROV_AES_CCM_CTX *)ctx; + unsigned char *ptr; + int i, rem; + + if (!alen) + return 1; + + sctx->ccm.s390x.nonce.b[0] |= S390X_CCM_AAD_FLAG; + + /* Suppress 'type-punned pointer dereference' warning. */ + ptr = sctx->ccm.s390x.buf.b; + + if (alen < ((1 << 16) - (1 << 8))) { + *(uint16_t *)ptr = alen; + i = 2; + } else if (sizeof(alen) == 8 + && alen >= (size_t)1 << (32 % (sizeof(alen) * 8))) { + *(uint16_t *)ptr = 0xffff; + *(uint64_t *)(ptr + 2) = alen; + i = 10; + } else { + *(uint16_t *)ptr = 0xfffe; + *(uint32_t *)(ptr + 2) = alen; + i = 6; + } + + while (i < 16 && alen) { + sctx->ccm.s390x.buf.b[i] = *aad; + ++aad; + --alen; + ++i; + } + while (i < 16) { + sctx->ccm.s390x.buf.b[i] = 0; + ++i; + } + + sctx->ccm.s390x.kmac.icv.g[0] = 0; + sctx->ccm.s390x.kmac.icv.g[1] = 0; + s390x_kmac(sctx->ccm.s390x.nonce.b, 32, sctx->ccm.s390x.fc, + &sctx->ccm.s390x.kmac); + sctx->ccm.s390x.blocks += 2; + + rem = alen & 0xf; + alen &= ~(size_t)0xf; + if (alen) { + s390x_kmac(aad, alen, sctx->ccm.s390x.fc, &sctx->ccm.s390x.kmac); + sctx->ccm.s390x.blocks += alen >> 4; + aad += alen; + } + if (rem) { + for (i = 0; i < rem; i++) + sctx->ccm.s390x.kmac.icv.b[i] ^= aad[i]; + + s390x_km(sctx->ccm.s390x.kmac.icv.b, 16, + sctx->ccm.s390x.kmac.icv.b, sctx->ccm.s390x.fc, + sctx->ccm.s390x.kmac.k); + sctx->ccm.s390x.blocks++; + } + return 1; +} + +/*- + * En/de-crypt plain/cipher-text. Compute tag from plaintext. Returns 1 for + * success. + */ +static int s390x_aes_ccm_auth_encdec(PROV_CCM_CTX *ctx, + const unsigned char *in, + unsigned char *out, size_t len, int enc) +{ + PROV_AES_CCM_CTX *sctx = (PROV_AES_CCM_CTX *)ctx; + size_t n, rem; + unsigned int i, l, num; + unsigned char flags; + + flags = sctx->ccm.s390x.nonce.b[0]; + if (!(flags & S390X_CCM_AAD_FLAG)) { + s390x_km(sctx->ccm.s390x.nonce.b, 16, sctx->ccm.s390x.kmac.icv.b, + sctx->ccm.s390x.fc, sctx->ccm.s390x.kmac.k); + sctx->ccm.s390x.blocks++; + } + l = flags & 0x7; + sctx->ccm.s390x.nonce.b[0] = l; + + /*- + * Reconstruct length from encoded length field + * and initialize it with counter value. + */ + n = 0; + for (i = 15 - l; i < 15; i++) { + n |= sctx->ccm.s390x.nonce.b[i]; + sctx->ccm.s390x.nonce.b[i] = 0; + n <<= 8; + } + n |= sctx->ccm.s390x.nonce.b[15]; + sctx->ccm.s390x.nonce.b[15] = 1; + + if (n != len) + return 0; /* length mismatch */ + + if (enc) { + /* Two operations per block plus one for tag encryption */ + sctx->ccm.s390x.blocks += (((len + 15) >> 4) << 1) + 1; + if (sctx->ccm.s390x.blocks > (1ULL << 61)) + return 0; /* too much data */ + } + + num = 0; + rem = len & 0xf; + len &= ~(size_t)0xf; + + if (enc) { + /* mac-then-encrypt */ + if (len) + s390x_kmac(in, len, sctx->ccm.s390x.fc, &sctx->ccm.s390x.kmac); + if (rem) { + for (i = 0; i < rem; i++) + sctx->ccm.s390x.kmac.icv.b[i] ^= in[len + i]; + + s390x_km(sctx->ccm.s390x.kmac.icv.b, 16, + sctx->ccm.s390x.kmac.icv.b, + sctx->ccm.s390x.fc, sctx->ccm.s390x.kmac.k); + } + + CRYPTO_ctr128_encrypt_ctr32(in, out, len + rem, &sctx->ccm.ks.ks, + sctx->ccm.s390x.nonce.b, sctx->ccm.s390x.buf.b, + &num, (ctr128_f)AES_ctr32_encrypt); + } else { + /* decrypt-then-mac */ + CRYPTO_ctr128_encrypt_ctr32(in, out, len + rem, &sctx->ccm.ks.ks, + sctx->ccm.s390x.nonce.b, sctx->ccm.s390x.buf.b, + &num, (ctr128_f)AES_ctr32_encrypt); + + if (len) + s390x_kmac(out, len, sctx->ccm.s390x.fc, &sctx->ccm.s390x.kmac); + if (rem) { + for (i = 0; i < rem; i++) + sctx->ccm.s390x.kmac.icv.b[i] ^= out[len + i]; + + s390x_km(sctx->ccm.s390x.kmac.icv.b, 16, + sctx->ccm.s390x.kmac.icv.b, + sctx->ccm.s390x.fc, sctx->ccm.s390x.kmac.k); + } + } + /* encrypt tag */ + for (i = 15 - l; i < 16; i++) + sctx->ccm.s390x.nonce.b[i] = 0; + + s390x_km(sctx->ccm.s390x.nonce.b, 16, sctx->ccm.s390x.buf.b, + sctx->ccm.s390x.fc, sctx->ccm.s390x.kmac.k); + sctx->ccm.s390x.kmac.icv.g[0] ^= sctx->ccm.s390x.buf.g[0]; + sctx->ccm.s390x.kmac.icv.g[1] ^= sctx->ccm.s390x.buf.g[1]; + + sctx->ccm.s390x.nonce.b[0] = flags; /* restore flags field */ + return 1; +} + + +static int s390x_aes_ccm_gettag(PROV_CCM_CTX *ctx, + unsigned char *tag, size_t tlen) +{ + PROV_AES_CCM_CTX *sctx = (PROV_AES_CCM_CTX *)ctx; + + if (tlen > ctx->m) + return 0; + memcpy(tag, sctx->ccm.s390x.kmac.icv.b, tlen); + return 1; +} + +static int s390x_aes_ccm_auth_encrypt(PROV_CCM_CTX *ctx, + const unsigned char *in, + unsigned char *out, size_t len, + unsigned char *tag, size_t taglen) +{ + int rv; + + rv = s390x_aes_ccm_auth_encdec(ctx, in, out, len, 1); + if (rv && tag != NULL) + rv = s390x_aes_ccm_gettag(ctx, tag, taglen); + return rv; +} + +static int s390x_aes_ccm_auth_decrypt(PROV_CCM_CTX *ctx, + const unsigned char *in, + unsigned char *out, size_t len, + unsigned char *expected_tag, + size_t taglen) +{ + int rv = 0; + PROV_AES_CCM_CTX *sctx = (PROV_AES_CCM_CTX *)ctx; + + rv = s390x_aes_ccm_auth_encdec(ctx, in, out, len, 0); + if (rv) { + if (CRYPTO_memcmp(sctx->ccm.s390x.kmac.icv.b, expected_tag, ctx->m) != 0) + rv = 0; + } + if (rv == 0) + OPENSSL_cleanse(out, len); + return rv; +} + +static const PROV_CCM_HW s390x_aes_ccm = { + s390x_aes_ccm_init_key, + s390x_aes_ccm_setiv, + s390x_aes_ccm_setaad, + s390x_aes_ccm_auth_encrypt, + s390x_aes_ccm_auth_decrypt, + s390x_aes_ccm_gettag +}; + +const PROV_CCM_HW *PROV_AES_HW_ccm(size_t keybits) +{ + if ((keybits == 128 && S390X_aes_128_ccm_CAPABLE) + || (keybits == 192 && S390X_aes_192_ccm_CAPABLE) + || (keybits == 256 && S390X_aes_256_ccm_CAPABLE)) + return &s390x_aes_ccm; + return &aes_ccm; +} diff --git a/providers/common/ciphers/build.info b/providers/common/ciphers/build.info index 45f493de7e..6702d701ff 100644 --- a/providers/common/ciphers/build.info +++ b/providers/common/ciphers/build.info @@ -1,5 +1,7 @@ LIBS=../../../libcrypto -$COMMON=block.c aes.c aes_basic.c gcm.c gcm_hw.c ciphers_common.c + +$COMMON=block.c aes.c aes_basic.c gcm.c gcm_hw.c ciphers_common.c \ + ccm.c ccm_hw.c SOURCE[../../../libcrypto]=$COMMON INCLUDE[../../../libcrypto]=. ../../../crypto diff --git a/providers/common/ciphers/ccm.c b/providers/common/ciphers/ccm.c new file mode 100644 index 0000000000..67a127ac20 --- /dev/null +++ b/providers/common/ciphers/ccm.c @@ -0,0 +1,486 @@ +/* + * Copyright 2019 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 + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include +#include "internal/provider_algs.h" +#include "internal/providercommonerr.h" +#include "ciphers_locl.h" + +/* TODO(3.0) Figure out what flags are really needed here */ +#define CCM_FLAGS (EVP_CIPH_FLAG_AEAD_CIPHER | EVP_CIPH_FLAG_DEFAULT_ASN1 \ + | EVP_CIPH_CUSTOM_IV | EVP_CIPH_FLAG_CUSTOM_CIPHER \ + | EVP_CIPH_ALWAYS_CALL_INIT | EVP_CIPH_CTRL_INIT \ + | EVP_CIPH_CUSTOM_COPY) + +static OSSL_OP_cipher_encrypt_init_fn ccm_einit; +static OSSL_OP_cipher_decrypt_init_fn ccm_dinit; +static OSSL_OP_cipher_get_ctx_params_fn ccm_get_ctx_params; +static OSSL_OP_cipher_set_ctx_params_fn ccm_set_ctx_params; +static OSSL_OP_cipher_update_fn ccm_stream_update; +static OSSL_OP_cipher_final_fn ccm_stream_final; +static OSSL_OP_cipher_cipher_fn ccm_cipher; + +static int ccm_cipher_internal(PROV_CCM_CTX *ctx, unsigned char *out, + size_t *padlen, const unsigned char *in, + size_t len); + +static int ccm_tls_init(PROV_CCM_CTX *ctx, unsigned char *aad, size_t alen) +{ + size_t len; + + if (alen != EVP_AEAD_TLS1_AAD_LEN) + return 0; + + /* Save the aad for later use. */ + memcpy(ctx->buf, aad, alen); + ctx->tls_aad_len = alen; + + len = ctx->buf[alen - 2] << 8 | ctx->buf[alen - 1]; + if (len < EVP_CCM_TLS_EXPLICIT_IV_LEN) + return 0; + + /* Correct length for explicit iv. */ + len -= EVP_CCM_TLS_EXPLICIT_IV_LEN; + + if (!ctx->enc) { + if (len < ctx->m) + return 0; + /* Correct length for tag. */ + len -= ctx->m; + } + ctx->buf[alen - 2] = (unsigned char)(len >> 8); + ctx->buf[alen - 1] = (unsigned char)(len & 0xff); + + /* Extra padding: tag appended to record. */ + return ctx->m; +} + +static int ccm_tls_iv_set_fixed(PROV_CCM_CTX *ctx, unsigned char *fixed, + size_t flen) +{ + if (flen != EVP_CCM_TLS_FIXED_IV_LEN) + return 0; + + /* Copy to first part of the iv. */ + memcpy(ctx->iv, fixed, flen); + return 1; +} + +static size_t ccm_get_ivlen(PROV_CCM_CTX *ctx) +{ + return 15 - ctx->l; +} + +static int ccm_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +{ + PROV_CCM_CTX *ctx = (PROV_CCM_CTX *)vctx; + const OSSL_PARAM *p; + size_t sz; + + p = OSSL_PARAM_locate_const(params, OSSL_CIPHER_PARAM_AEAD_TAG); + if (p != NULL) { + if (p->data_type != OSSL_PARAM_OCTET_STRING) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GET_PARAMETER); + return 0; + } + if ((p->data_size & 1) || (p->data_size < 4) || p->data_size > 16) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_TAGLEN); + return 0; + } + + if (p->data != NULL) { + if (ctx->enc) { + ERR_raise(ERR_LIB_PROV, PROV_R_TAG_NOT_NEEDED); + return 0; + } + memcpy(ctx->buf, p->data, p->data_size); + ctx->tag_set = 1; + } + ctx->m = p->data_size; + } + + p = OSSL_PARAM_locate_const(params, OSSL_CIPHER_PARAM_AEAD_IVLEN); + if (p != NULL) { + size_t ivlen; + + if (!OSSL_PARAM_get_size_t(p, &sz)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GET_PARAMETER); + return 0; + } + ivlen = 15 - sz; + if (ivlen < 2 || ivlen > 8) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_IVLEN); + return 0; + } + ctx->l = ivlen; + } + + p = OSSL_PARAM_locate_const(params, OSSL_CIPHER_PARAM_AEAD_TLS1_AAD); + if (p != NULL) { + if (p->data_type != OSSL_PARAM_OCTET_STRING) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GET_PARAMETER); + return 0; + } + sz = ccm_tls_init(ctx, p->data, p->data_size); + if (sz == 0) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DATA); + return 0; + } + ctx->tls_aad_pad_sz = sz; + } + + p = OSSL_PARAM_locate_const(params, OSSL_CIPHER_PARAM_AEAD_TLS1_IV_FIXED); + if (p != NULL) { + if (p->data_type != OSSL_PARAM_OCTET_STRING) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GET_PARAMETER); + return 0; + } + if (ccm_tls_iv_set_fixed(ctx, p->data, p->data_size) == 0) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_IVLEN); + return 0; + } + } + + return 1; +} + +static int ccm_get_ctx_params(void *vctx, OSSL_PARAM params[]) +{ + PROV_CCM_CTX *ctx = (PROV_CCM_CTX *)vctx; + OSSL_PARAM *p; + + p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_IVLEN); + if (p != NULL && !OSSL_PARAM_set_int(p, ccm_get_ivlen(ctx))) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); + return 0; + } + + p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_IV); + if (p != NULL) { + if (ccm_get_ivlen(ctx) != p->data_size) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_IVLEN); + return 0; + } + if (!OSSL_PARAM_set_octet_string(p, ctx->iv, p->data_size)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); + return 0; + } + } + + p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_KEYLEN); + if (p != NULL && !OSSL_PARAM_set_int(p, ctx->keylen)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); + return 0; + } + + p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_AEAD_TLS1_AAD_PAD); + if (p != NULL && !OSSL_PARAM_set_size_t(p, ctx->tls_aad_pad_sz)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); + return 0; + } + + p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_AEAD_TAG); + if (p != NULL) { + if (!ctx->enc || !ctx->tag_set) { + ERR_raise(ERR_LIB_PROV, PROV_R_TAG_NOTSET); + return 0; + } + if (p->data_type != OSSL_PARAM_OCTET_STRING) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); + return 0; + } + if (!ctx->hw->gettag(ctx, p->data, p->data_size)) + return 0; + ctx->tag_set = 0; + ctx->iv_set = 0; + ctx->len_set = 0; + } + return 1; +} + +static int ccm_init(void *vctx, const unsigned char *key, size_t keylen, + const unsigned char *iv, size_t ivlen, int enc) +{ + PROV_CCM_CTX *ctx = (PROV_CCM_CTX *)vctx; + + ctx->enc = enc; + + if (iv != NULL) { + if (ivlen != ccm_get_ivlen(ctx)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_IVLEN); + return 0; + } + + memcpy(ctx->iv, iv, ivlen); + ctx->iv_set = 1; + } + if (key != NULL) { + if (keylen != ctx->keylen) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEYLEN); + return 0; + } + return ctx->hw->setkey(ctx, key, keylen); + } + return 1; +} + +static int ccm_einit(void *vctx, const unsigned char *key, size_t keylen, + const unsigned char *iv, size_t ivlen) +{ + return ccm_init(vctx, key, keylen, iv, ivlen, 1); +} + +static int ccm_dinit(void *vctx, const unsigned char *key, size_t keylen, + const unsigned char *iv, size_t ivlen) +{ + return ccm_init(vctx, key, keylen, iv, ivlen, 0); +} + +static int ccm_stream_update(void *vctx, unsigned char *out, size_t *outl, + size_t outsize, const unsigned char *in, + size_t inl) +{ + PROV_CCM_CTX *ctx = (PROV_CCM_CTX *)vctx; + + if (outsize < inl) { + ERR_raise(ERR_LIB_PROV, PROV_R_OUTPUT_BUFFER_TOO_SMALL); + return 0; + } + + if (!ccm_cipher_internal(ctx, out, outl, in, inl)) { + ERR_raise(ERR_LIB_PROV, PROV_R_CIPHER_OPERATION_FAILED); + return 0; + } + return 1; +} + +static int ccm_stream_final(void *vctx, unsigned char *out, size_t *outl, + size_t outsize) +{ + PROV_CCM_CTX *ctx = (PROV_CCM_CTX *)vctx; + int i; + + i = ccm_cipher_internal(ctx, out, outl, NULL, 0); + if (i <= 0) + return 0; + + *outl = 0; + return 1; +} + +static int ccm_cipher(void *vctx, + unsigned char *out, size_t *outl, size_t outsize, + const unsigned char *in, size_t inl) +{ + PROV_CCM_CTX *ctx = (PROV_CCM_CTX *)vctx; + + if (outsize < inl) { + ERR_raise(ERR_LIB_PROV, PROV_R_OUTPUT_BUFFER_TOO_SMALL); + return -1; + } + + if (ccm_cipher_internal(ctx, out, outl, in, inl) <= 0) + return -1; + + *outl = inl; + return 1; +} + +/* Copy the buffered iv */ +static int ccm_set_iv(PROV_CCM_CTX *ctx, size_t mlen) +{ + const PROV_CCM_HW *hw = ctx->hw; + + if (!hw->setiv(ctx, ctx->iv, ccm_get_ivlen(ctx), mlen)) + return 0; + ctx->len_set = 1; + return 1; +} + +static int ccm_tls_cipher(PROV_CCM_CTX *ctx, + unsigned char *out, size_t *padlen, + const unsigned char *in, size_t len) +{ + int rv = 0; + size_t olen = 0; + + /* Encrypt/decrypt must be performed in place */ + if (out != in || len < (EVP_CCM_TLS_EXPLICIT_IV_LEN + (size_t)ctx->m)) + goto err; + + /* If encrypting set explicit IV from sequence number (start of AAD) */ + if (ctx->enc) + memcpy(out, ctx->buf, EVP_CCM_TLS_EXPLICIT_IV_LEN); + /* Get rest of IV from explicit IV */ + memcpy(ctx->iv + EVP_CCM_TLS_FIXED_IV_LEN, in, EVP_CCM_TLS_EXPLICIT_IV_LEN); + /* Correct length value */ + len -= EVP_CCM_TLS_EXPLICIT_IV_LEN + ctx->m; + if (!ccm_set_iv(ctx, len)) + goto err; + + /* Use saved AAD */ + if (!ctx->hw->setaad(ctx, ctx->buf, ctx->tls_aad_len)) + goto err; + + /* Fix buffer to point to payload */ + in += EVP_CCM_TLS_EXPLICIT_IV_LEN; + out += EVP_CCM_TLS_EXPLICIT_IV_LEN; + if (ctx->enc) { + if (!ctx->hw->auth_encrypt(ctx, in, out, len, out + len, ctx->m)) + goto err; + olen = len + EVP_CCM_TLS_EXPLICIT_IV_LEN + ctx->m; + } else { + if (!ctx->hw->auth_decrypt(ctx, in, out, len, + (unsigned char *)in + len, ctx->m)) + goto err; + olen = len; + } + rv = 1; +err: + *padlen = olen; + return rv; +} + +static int ccm_cipher_internal(PROV_CCM_CTX *ctx, unsigned char *out, + size_t *padlen, const unsigned char *in, + size_t len) +{ + int rv = 0; + size_t olen = 0; + const PROV_CCM_HW *hw = ctx->hw; + + /* If no key set, return error */ + if (!ctx->key_set) + return 0; + + if (ctx->tls_aad_len >= 0) + return ccm_tls_cipher(ctx, out, padlen, in, len); + + /* EVP_*Final() doesn't return any data */ + if (in == NULL && out != NULL) + return 1; + + if (!ctx->iv_set) + goto err; + + if (out == NULL) { + if (in == NULL) { + if (!ccm_set_iv(ctx, len)) + goto err; + } else { + /* If we have AAD, we need a message length */ + if (!ctx->len_set && len) + goto err; + if (!hw->setaad(ctx, in, len)) + goto err; + } + } else { + /* If not set length yet do it */ + if (!ctx->len_set && !ccm_set_iv(ctx, len)) + goto err; + + if (ctx->enc) { + if (!hw->auth_encrypt(ctx, in, out, len, NULL, 0)) + goto err; + ctx->tag_set = 1; + } else { + /* The tag must be set before actually decrypting data */ + if (!ctx->tag_set) + goto err; + + if (!hw->auth_decrypt(ctx, in, out, len, ctx->buf, ctx->m)) + goto err; + /* Finished - reset flags so calling this method again will fail */ + ctx->iv_set = 0; + ctx->tag_set = 0; + ctx->len_set = 0; + } + } + olen = len; + rv = 1; +err: + *padlen = olen; + return rv; +} + +static void ccm_initctx(PROV_CCM_CTX *ctx, size_t keybits, + const PROV_CCM_HW *hw) +{ + ctx->keylen = keybits / 8; + ctx->key_set = 0; + ctx->iv_set = 0; + ctx->tag_set = 0; + ctx->len_set = 0; + ctx->l = 8; + ctx->m = 12; + ctx->tls_aad_len = -1; + ctx->hw = hw; +} + +static void ccm_finalctx(PROV_CCM_CTX *ctx) +{ + OPENSSL_cleanse(ctx->iv, sizeof(ctx->iv)); +} + +/*- Algorithm specific methods for CCM mode */ + +static void *aes_ccm_newctx(void *provctx, size_t keybits) +{ + PROV_AES_CCM_CTX *ctx = OPENSSL_zalloc(sizeof(*ctx)); + + ccm_initctx(&ctx->base, keybits, PROV_AES_HW_ccm(keybits)); + return ctx; +} + +static OSSL_OP_cipher_freectx_fn aes_ccm_freectx; +static void aes_ccm_freectx(void *vctx) +{ + PROV_AES_CCM_CTX *ctx = (PROV_AES_CCM_CTX *)vctx; + + ccm_finalctx((PROV_CCM_CTX *)ctx); + OPENSSL_clear_free(ctx, sizeof(*ctx)); +} + +/*- CCM Dispatch macros */ + +/* aes128ccm_functions */ +IMPLEMENT_aead_cipher(aes, ccm, CCM, CCM_FLAGS, 128, 8, 96); +/* aes192ccm_functions */ +IMPLEMENT_aead_cipher(aes, ccm, CCM, CCM_FLAGS, 192, 8, 96); +/* aes256ccm_functions */ +IMPLEMENT_aead_cipher(aes, ccm, CCM, CCM_FLAGS, 256, 8, 96); + +#if !defined(OPENSSL_NO_ARIA) && !defined(FIPS_MODE) +static void *aria_ccm_newctx(void *provctx, size_t keybits) +{ + PROV_ARIA_CCM_CTX *ctx = OPENSSL_zalloc(sizeof(*ctx)); + + ccm_initctx(&ctx->base, keybits, PROV_ARIA_HW_ccm(keybits)); + return ctx; +} + +static OSSL_OP_cipher_freectx_fn aria_ccm_freectx; +static void aria_ccm_freectx(void *vctx) +{ + PROV_ARIA_CCM_CTX *ctx = (PROV_ARIA_CCM_CTX *)vctx; + + ccm_finalctx((PROV_CCM_CTX *)ctx); + OPENSSL_clear_free(ctx, sizeof(*ctx)); +} + +/* aria128ccm functions */ +IMPLEMENT_aead_cipher(aria, ccm, CCM, CCM_FLAGS, 128, 8, 96); +/* aria192ccm functions */ +IMPLEMENT_aead_cipher(aria, ccm, CCM, CCM_FLAGS, 192, 8, 96); +/* aria256ccm functions */ +IMPLEMENT_aead_cipher(aria, ccm, CCM, CCM_FLAGS, 256, 8, 96); +#endif /* !defined(OPENSSL_NO_ARIA) && !defined(FIPS_MODE) */ diff --git a/providers/common/ciphers/ccm_hw.c b/providers/common/ciphers/ccm_hw.c new file mode 100644 index 0000000000..c59d88d7e0 --- /dev/null +++ b/providers/common/ciphers/ccm_hw.c @@ -0,0 +1,199 @@ +/* + * Copyright 2019 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 + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include "ciphers_locl.h" +#include "internal/aes_platform.h" + +#define AES_CCM_SET_KEY_FN(fn_set_enc_key, fn_blk, fn_ccm_enc, fn_ccm_dec) \ + fn_set_enc_key(key, keylen * 8, &actx->ccm.ks.ks); \ + CRYPTO_ccm128_init(&ctx->ccm_ctx, ctx->m, ctx->l, &actx->ccm.ks.ks, \ + (block128_f)fn_blk); \ + ctx->str = ctx->enc ? (ccm128_f)fn_ccm_enc : (ccm128_f)fn_ccm_dec; \ + ctx->key_set = 1; + +static int ccm_generic_aes_init_key(PROV_CCM_CTX *ctx, + const unsigned char *key, size_t keylen) +{ + PROV_AES_CCM_CTX *actx = (PROV_AES_CCM_CTX *)ctx; + +#ifdef HWAES_CAPABLE + if (HWAES_CAPABLE) { + AES_CCM_SET_KEY_FN(HWAES_set_encrypt_key, HWAES_encrypt, NULL, NULL); + } else +#endif /* HWAES_CAPABLE */ +#ifdef VPAES_CAPABLE + if (VPAES_CAPABLE) { + AES_CCM_SET_KEY_FN(vpaes_set_encrypt_key, vpaes_encrypt, NULL, NULL); + } else +#endif + { + AES_CCM_SET_KEY_FN(AES_set_encrypt_key, AES_encrypt, NULL, NULL) + } + return 1; +} + +static int ccm_generic_setiv(PROV_CCM_CTX *ctx, const unsigned char *nonce, + size_t nlen, size_t mlen) +{ + return CRYPTO_ccm128_setiv(&ctx->ccm_ctx, nonce, nlen, mlen) == 0; +} + +static int ccm_generic_setaad(PROV_CCM_CTX *ctx, const unsigned char *aad, + size_t alen) +{ + CRYPTO_ccm128_aad(&ctx->ccm_ctx, aad, alen); + return 1; +} + +static int ccm_generic_gettag(PROV_CCM_CTX *ctx, unsigned char *tag, + size_t tlen) +{ + return CRYPTO_ccm128_tag(&ctx->ccm_ctx, tag, tlen) > 0; +} + +static int ccm_generic_auth_encrypt(PROV_CCM_CTX *ctx, const unsigned char *in, + unsigned char *out, size_t len, + unsigned char *tag, size_t taglen) +{ + int rv; + + if (ctx->str != NULL) + rv = CRYPTO_ccm128_encrypt_ccm64(&ctx->ccm_ctx, in, + out, len, ctx->str) == 0; + else + rv = CRYPTO_ccm128_encrypt(&ctx->ccm_ctx, in, out, len) == 0; + + if (rv == 1 && tag != NULL) + rv = (CRYPTO_ccm128_tag(&ctx->ccm_ctx, tag, taglen) > 0); + return rv; +} + +static int ccm_generic_auth_decrypt(PROV_CCM_CTX *ctx, const unsigned char *in, + unsigned char *out, size_t len, + unsigned char *expected_tag, + size_t taglen) +{ + int rv = 0; + + if (ctx->str != NULL) + rv = CRYPTO_ccm128_decrypt_ccm64(&ctx->ccm_ctx, in, out, len, + ctx->str) == 0; + else + rv = CRYPTO_ccm128_decrypt(&ctx->ccm_ctx, in, out, len) == 0; + if (rv) { + unsigned char tag[16]; + + if (!CRYPTO_ccm128_tag(&ctx->ccm_ctx, tag, taglen) + || CRYPTO_memcmp(tag, expected_tag, taglen) != 0) + rv = 0; + } + if (rv == 0) + OPENSSL_cleanse(out, len); + return rv; +} + +static const PROV_CCM_HW aes_ccm = { + ccm_generic_aes_init_key, + ccm_generic_setiv, + ccm_generic_setaad, + ccm_generic_auth_encrypt, + ccm_generic_auth_decrypt, + ccm_generic_gettag +}; + +#if defined(S390X_aes_128_CAPABLE) +# include "aes_ccm_s390x.c" +#elif defined(AESNI_CAPABLE) + +/* AES-NI section */ +static int ccm_aesni_init_key(PROV_CCM_CTX *ctx, + const unsigned char *key, size_t keylen) +{ + PROV_AES_CCM_CTX *actx = (PROV_AES_CCM_CTX *)ctx; + + AES_CCM_SET_KEY_FN(aesni_set_encrypt_key, aesni_encrypt, + aesni_ccm64_encrypt_blocks, aesni_ccm64_decrypt_blocks); + return 1; +} + +static const PROV_CCM_HW aesni_ccm = { + ccm_aesni_init_key, + ccm_generic_setiv, + ccm_generic_setaad, + ccm_generic_auth_encrypt, + ccm_generic_auth_decrypt, + ccm_generic_gettag +}; + +const PROV_CCM_HW *PROV_AES_HW_ccm(size_t keybits) +{ + return AESNI_CAPABLE ? &aesni_ccm : &aes_ccm; +} + +#elif defined(SPARC_AES_CAPABLE) +/* Fujitsu SPARC64 X support */ +static int ccm_t4_aes_init_key(PROV_CCM_CTX *ctx, + const unsigned char *key, size_t keylen) +{ + PROV_AES_CCM_CTX *actx = (PROV_AES_CCM_CTX *)ctx; + + AES_CCM_SET_KEY_FN(aes_t4_set_encrypt_key, aes_t4_encrypt, NULL, NULL); + return 1; +} + +static const PROV_CCM_HW t4_aes_ccm = { + ccm_t4_aes_init_key, + ccm_generic_setiv, + ccm_generic_setaad, + ccm_generic_auth_encrypt, + ccm_generic_auth_decrypt, + ccm_generic_gettag +}; + +const PROV_CCM_HW *PROV_AES_HW_ccm(size_t keybits) +{ + return SPARC_AES_CAPABLE ? &t4_aes_ccm : &aes_ccm; +} + +#else +const PROV_CCM_HW *PROV_AES_HW_ccm(size_t keybits) +{ + return &aes_ccm; +} +#endif + +#if !defined(OPENSSL_NO_ARIA) && !defined(FIPS_MODE) +/* ARIA CCM Algorithm specific methods */ +static int ccm_aria_init_key(PROV_CCM_CTX *ctx, + const unsigned char *key, size_t keylen) +{ + PROV_ARIA_CCM_CTX *actx = (PROV_ARIA_CCM_CTX *)ctx; + + aria_set_encrypt_key(key, keylen * 8, &actx->ks.ks); + CRYPTO_ccm128_init(&ctx->ccm_ctx, ctx->m, ctx->l, &actx->ks.ks, + (block128_f)aria_encrypt); + ctx->str = NULL; + ctx->key_set = 1; + return 1; +} + +static const PROV_CCM_HW ccm_aria = { + ccm_aria_init_key, + ccm_generic_setiv, + ccm_generic_setaad, + ccm_generic_auth_encrypt, + ccm_generic_auth_decrypt, + ccm_generic_gettag +}; +const PROV_CCM_HW *PROV_ARIA_HW_ccm(size_t keybits) +{ + return &ccm_aria; +} +#endif /* OPENSSL_NO_ARIA */ diff --git a/providers/common/ciphers/ciphers_ccm.h b/providers/common/ciphers/ciphers_ccm.h new file mode 100644 index 0000000000..1560d28b4f --- /dev/null +++ b/providers/common/ciphers/ciphers_ccm.h @@ -0,0 +1,125 @@ +/* + * Copyright 2019 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 + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +typedef struct prov_ccm_hw_st PROV_CCM_HW; + +#if defined(OPENSSL_CPUID_OBJ) && defined(__s390__) +/*- + * KMAC-AES parameter block - begin + * (see z/Architecture Principles of Operation >= SA22-7832-08) + */ +typedef struct S390X_kmac_params_st { + union { + unsigned long long g[2]; + unsigned char b[16]; + } icv; + unsigned char k[32]; +} S390X_KMAC_PARAMS; +/* KMAC-AES parameter block - end */ +#endif + +/* Base structure that is shared by AES & ARIA for CCM MODE */ +typedef struct prov_ccm_st { + int enc; + int key_set; /* Set if key initialised */ + int iv_set; /* Set if an iv is set */ + int tag_set; /* Set if tag is valid */ + int len_set; /* Set if message length set */ + size_t l, m; /* L and M parameters from RFC3610 */ + size_t keylen; + int tls_aad_len; /* TLS AAD length */ + int tls_aad_pad_sz; + unsigned char iv[AES_BLOCK_SIZE]; + unsigned char buf[AES_BLOCK_SIZE]; + CCM128_CONTEXT ccm_ctx; + ccm128_f str; + const PROV_CCM_HW *hw; /* hardware specific methods */ +} PROV_CCM_CTX; + +typedef struct prov_aes_ccm_ctx_st { + PROV_CCM_CTX base; /* Must be first */ + union { + OSSL_UNION_ALIGN; + /*- + * Padding is chosen so that s390x.kmac.k overlaps with ks.ks and + * fc with ks.ks.rounds. Remember that on s390x, an AES_KEY's + * rounds field is used to store the function code and that the key + * schedule is not stored (if aes hardware support is detected). + */ + struct { + unsigned char pad[16]; + AES_KEY ks; + } ks; +#if defined(OPENSSL_CPUID_OBJ) && defined(__s390__) + struct { + S390X_KMAC_PARAMS kmac; + unsigned long long blocks; + union { + unsigned long long g[2]; + unsigned char b[AES_BLOCK_SIZE]; + } nonce; + union { + unsigned long long g[2]; + unsigned char b[AES_BLOCK_SIZE]; + } buf; + unsigned char dummy_pad[168]; + unsigned int fc; /* fc has same offset as ks.ks.rounds */ + } s390x; +#endif /* defined(OPENSSL_CPUID_OBJ) && defined(__s390__) */ + } ccm; +} PROV_AES_CCM_CTX; + +PROV_CIPHER_FUNC(int, CCM_cipher, (PROV_CCM_CTX *ctx, unsigned char *out, \ + size_t *padlen, const unsigned char *in, \ + size_t len)); +PROV_CIPHER_FUNC(int, CCM_setkey, (PROV_CCM_CTX *ctx, \ + const unsigned char *key, size_t keylen)); +PROV_CIPHER_FUNC(int, CCM_setiv, (PROV_CCM_CTX *dat, \ + const unsigned char *iv, size_t ivlen, \ + size_t mlen)); +PROV_CIPHER_FUNC(int, CCM_setaad, (PROV_CCM_CTX *ctx, \ + const unsigned char *aad, size_t aadlen)); +PROV_CIPHER_FUNC(int, CCM_auth_encrypt, (PROV_CCM_CTX *ctx, \ + const unsigned char *in, \ + unsigned char *out, size_t len, \ + unsigned char *tag, size_t taglen)); +PROV_CIPHER_FUNC(int, CCM_auth_decrypt, (PROV_CCM_CTX *ctx, \ + const unsigned char *in, \ + unsigned char *out, size_t len, \ + unsigned char *tag, size_t taglen)); +PROV_CIPHER_FUNC(int, CCM_gettag, (PROV_CCM_CTX *ctx, \ + unsigned char *tag, size_t taglen)); + +/* + * CCM Mode internal method table used to handle hardware specific differences, + * (and different algorithms). + */ +struct prov_ccm_hw_st { + OSSL_CCM_setkey_fn setkey; + OSSL_CCM_setiv_fn setiv; + OSSL_CCM_setaad_fn setaad; + OSSL_CCM_auth_encrypt_fn auth_encrypt; + OSSL_CCM_auth_decrypt_fn auth_decrypt; + OSSL_CCM_gettag_fn gettag; +}; + +const PROV_CCM_HW *PROV_AES_HW_ccm(size_t keylen); + +#if !defined(OPENSSL_NO_ARIA) && !defined(FIPS_MODE) +# include "internal/aria.h" +typedef struct prov_aria_ccm_ctx_st { + PROV_CCM_CTX base; /* Must be first */ + union { + OSSL_UNION_ALIGN; + ARIA_KEY ks; + } ks; /* ARIA key schedule to use */ +} PROV_ARIA_CCM_CTX; + +const PROV_CCM_HW *PROV_ARIA_HW_ccm(size_t keylen); +#endif /* !defined(OPENSSL_NO_ARIA) && !defined(FIPS_MODE) */ diff --git a/providers/common/ciphers/ciphers_gcm.h b/providers/common/ciphers/ciphers_gcm.h index badab28aea..8b4698f4d2 100644 --- a/providers/common/ciphers/ciphers_gcm.h +++ b/providers/common/ciphers/ciphers_gcm.h @@ -16,6 +16,34 @@ typedef struct prov_gcm_hw_st PROV_GCM_HW; #define GCM_IV_MAX_SIZE 64 #define GCM_TAG_MAX_SIZE 16 + +#if defined(OPENSSL_CPUID_OBJ) && defined(__s390__) +/*- + * KMA-GCM-AES parameter block - begin + * (see z/Architecture Principles of Operation >= SA22-7832-11) + */ +typedef struct S390X_kma_params_st { + unsigned char reserved[12]; + union { + unsigned int w; + unsigned char b[4]; + } cv; /* 32 bit counter value */ + union { + unsigned long long g[2]; + unsigned char b[16]; + } t; /* tag */ + unsigned char h[16]; /* hash subkey */ + unsigned long long taadl; /* total AAD length */ + unsigned long long tpcl; /* total plaintxt/ciphertxt len */ + union { + unsigned long long g[2]; + unsigned int w[4]; + } j0; /* initial counter value */ + unsigned char k[32]; /* key */ +} S390X_KMA_PARAMS; + +#endif + typedef struct prov_gcm_ctx_st { int enc; /* Set to 1 if we are encrypting or 0 otherwise */ int mode; /* The mode that we are using */ @@ -80,17 +108,17 @@ typedef struct prov_aes_gcm_ctx_st { } plat; } PROV_AES_GCM_CTX; -OSSL_CIPHER_FUNC(int, GCM_setkey, (PROV_GCM_CTX *ctx, const unsigned char *key, +PROV_CIPHER_FUNC(int, GCM_setkey, (PROV_GCM_CTX *ctx, const unsigned char *key, size_t keylen)); -OSSL_CIPHER_FUNC(int, GCM_setiv, (PROV_GCM_CTX *dat, const unsigned char *iv, +PROV_CIPHER_FUNC(int, GCM_setiv, (PROV_GCM_CTX *dat, const unsigned char *iv, size_t ivlen)); -OSSL_CIPHER_FUNC(int, GCM_aadupdate, (PROV_GCM_CTX *ctx, +PROV_CIPHER_FUNC(int, GCM_aadupdate, (PROV_GCM_CTX *ctx, const unsigned char *aad, size_t aadlen)); -OSSL_CIPHER_FUNC(int, GCM_cipherupdate, (PROV_GCM_CTX *ctx, +PROV_CIPHER_FUNC(int, GCM_cipherupdate, (PROV_GCM_CTX *ctx, const unsigned char *in, size_t len, unsigned char *out)); -OSSL_CIPHER_FUNC(int, GCM_cipherfinal, (PROV_GCM_CTX *ctx, unsigned char *tag)); -OSSL_CIPHER_FUNC(int, GCM_oneshot, (PROV_GCM_CTX *ctx, unsigned char *aad, +PROV_CIPHER_FUNC(int, GCM_cipherfinal, (PROV_GCM_CTX *ctx, unsigned char *tag)); +PROV_CIPHER_FUNC(int, GCM_oneshot, (PROV_GCM_CTX *ctx, unsigned char *aad, size_t aad_len, const unsigned char *in, size_t in_len, unsigned char *out, unsigned char *tag, size_t taglen)); diff --git a/providers/common/ciphers/ciphers_locl.h b/providers/common/ciphers/ciphers_locl.h index 9930c3288d..13a2952326 100644 --- a/providers/common/ciphers/ciphers_locl.h +++ b/providers/common/ciphers/ciphers_locl.h @@ -14,40 +14,15 @@ #include "internal/cryptlib.h" #include "internal/modes_int.h" -#if defined(OPENSSL_CPUID_OBJ) && defined(__s390__) -/*- - * KMA-GCM-AES parameter block - begin - * (see z/Architecture Principles of Operation >= SA22-7832-11) - */ -typedef struct S390X_kma_params_st { - unsigned char reserved[12]; - union { - unsigned int w; - unsigned char b[4]; - } cv; /* 32 bit counter value */ - union { - unsigned long long g[2]; - unsigned char b[16]; - } t; /* tag */ - unsigned char h[16]; /* hash subkey */ - unsigned long long taadl; /* total AAD length */ - unsigned long long tpcl; /* total plaintxt/ciphertxt len */ - union { - unsigned long long g[2]; - unsigned int w[4]; - } j0; /* initial counter value */ - unsigned char k[32]; /* key */ -} S390X_KMA_PARAMS; - -#endif - -typedef struct prov_aes_cipher_st PROV_AES_CIPHER; - #define IV_STATE_UNINITIALISED 0 /* initial state is not initialized */ #define IV_STATE_BUFFERED 1 /* iv has been copied to the iv buffer */ #define IV_STATE_COPIED 2 /* iv has been copied from the iv buffer */ #define IV_STATE_FINISHED 3 /* the iv has been used - so don't reuse it */ +#define PROV_CIPHER_FUNC(type, name, args) typedef type (* OSSL_##name##_fn)args + +typedef struct prov_aes_cipher_st PROV_AES_CIPHER; + typedef struct prov_aes_key_st { union { OSSL_UNION_ALIGN; @@ -122,14 +97,13 @@ typedef struct prov_aes_key_st { } PROV_AES_KEY; struct prov_aes_cipher_st { - int (*init)(PROV_AES_KEY *dat, const uint8_t *key, size_t keylen); - int (*cipher)(PROV_AES_KEY *dat, uint8_t *out, const uint8_t *in, + int (*init)(PROV_AES_KEY *dat, const uint8_t *key, size_t keylen); + int (*cipher)(PROV_AES_KEY *dat, uint8_t *out, const uint8_t *in, size_t inl); }; -#define OSSL_CIPHER_FUNC(type, name, args) typedef type (* OSSL_##name##_fn)args - #include "ciphers_gcm.h" +#include "ciphers_ccm.h" const PROV_AES_CIPHER *PROV_AES_CIPHER_ecb(size_t keylen); const PROV_AES_CIPHER *PROV_AES_CIPHER_cbc(size_t keylen); @@ -155,3 +129,37 @@ OSSL_OP_cipher_settable_ctx_params_fn cipher_aead_settable_ctx_params; int cipher_default_get_params(OSSL_PARAM params[], int md, unsigned long flags, int kbits, int blkbits, int ivbits); +#define IMPLEMENT_aead_cipher(alg, lc, UCMODE, flags, kbits, blkbits, ivbits) \ + static OSSL_OP_cipher_get_params_fn alg##_##kbits##_##lc##_get_params; \ + static int alg##_##kbits##_##lc##_get_params(OSSL_PARAM params[]) \ + { \ + return cipher_default_get_params(params, EVP_CIPH_##UCMODE##_MODE, \ + flags, kbits, blkbits, ivbits); \ + } \ + static OSSL_OP_cipher_newctx_fn alg##kbits##lc##_newctx; \ + static void * alg##kbits##lc##_newctx(void *provctx) \ + { \ + return alg##_##lc##_newctx(provctx, kbits); \ + } \ + const OSSL_DISPATCH alg##kbits##lc##_functions[] = { \ + { OSSL_FUNC_CIPHER_NEWCTX, (void (*)(void))alg##kbits##lc##_newctx }, \ + { OSSL_FUNC_CIPHER_FREECTX, (void (*)(void))alg##_##lc##_freectx }, \ + { OSSL_FUNC_CIPHER_ENCRYPT_INIT, (void (*)(void)) lc##_einit }, \ + { OSSL_FUNC_CIPHER_DECRYPT_INIT, (void (*)(void)) lc##_dinit }, \ + { OSSL_FUNC_CIPHER_UPDATE, (void (*)(void)) lc##_stream_update }, \ + { OSSL_FUNC_CIPHER_FINAL, (void (*)(void)) lc##_stream_final }, \ + { OSSL_FUNC_CIPHER_CIPHER, (void (*)(void)) lc##_cipher }, \ + { OSSL_FUNC_CIPHER_GET_PARAMS, \ + (void (*)(void)) alg##_##kbits##_##lc##_get_params }, \ + { OSSL_FUNC_CIPHER_GET_CTX_PARAMS, \ + (void (*)(void)) lc##_get_ctx_params }, \ + { OSSL_FUNC_CIPHER_SET_CTX_PARAMS, \ + (void (*)(void)) lc##_set_ctx_params }, \ + { OSSL_FUNC_CIPHER_GETTABLE_PARAMS, \ + (void (*)(void))cipher_default_gettable_params }, \ + { OSSL_FUNC_CIPHER_GETTABLE_CTX_PARAMS, \ + (void (*)(void))cipher_aead_gettable_ctx_params }, \ + { OSSL_FUNC_CIPHER_SETTABLE_CTX_PARAMS, \ + (void (*)(void))cipher_aead_settable_ctx_params }, \ + { 0, NULL } \ + } diff --git a/providers/common/ciphers/gcm.c b/providers/common/ciphers/gcm.c index 7644f81f21..50f79f6293 100644 --- a/providers/common/ciphers/gcm.c +++ b/providers/common/ciphers/gcm.c @@ -105,9 +105,9 @@ static int gcm_get_ctx_params(void *vctx, OSSL_PARAM params[]) size_t sz; p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_IVLEN); - if (p != NULL) { - if (!OSSL_PARAM_set_int(p, ctx->ivlen)) - return 0; + if (p != NULL && !OSSL_PARAM_set_int(p, ctx->ivlen)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); + return 0; } p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_KEYLEN); if (p != NULL && !OSSL_PARAM_set_int(p, ctx->keylen)) { @@ -513,41 +513,6 @@ err: return rv; } -#define IMPLEMENT_cipher(alg, lcmode, UCMODE, flags, kbits, blkbits, ivbits) \ - static OSSL_OP_cipher_get_params_fn alg##_##kbits##_##lcmode##_get_params; \ - static int alg##_##kbits##_##lcmode##_get_params(OSSL_PARAM params[]) \ - { \ - return cipher_default_get_params(params, EVP_CIPH_##UCMODE##_MODE, \ - flags, kbits, blkbits, ivbits); \ - } \ - static OSSL_OP_cipher_newctx_fn alg##kbits##gcm_newctx; \ - static void *alg##kbits##gcm_newctx(void *provctx) \ - { \ - return alg##_gcm_newctx(provctx, kbits); \ - } \ - const OSSL_DISPATCH alg##kbits##gcm_functions[] = { \ - { OSSL_FUNC_CIPHER_ENCRYPT_INIT, (void (*)(void))gcm_einit }, \ - { OSSL_FUNC_CIPHER_DECRYPT_INIT, (void (*)(void))gcm_dinit }, \ - { OSSL_FUNC_CIPHER_UPDATE, (void (*)(void))gcm_stream_update }, \ - { OSSL_FUNC_CIPHER_FINAL, (void (*)(void))gcm_stream_final }, \ - { OSSL_FUNC_CIPHER_CIPHER, (void (*)(void))gcm_cipher }, \ - { OSSL_FUNC_CIPHER_NEWCTX, (void (*)(void)) alg##kbits##gcm_newctx }, \ - { OSSL_FUNC_CIPHER_FREECTX, (void (*)(void)) alg##_gcm_freectx }, \ - { OSSL_FUNC_CIPHER_GET_PARAMS, \ - (void (*)(void)) alg##_##kbits##_##lcmode##_get_params }, \ - { OSSL_FUNC_CIPHER_GET_CTX_PARAMS, \ - (void (*)(void))gcm_get_ctx_params }, \ - { OSSL_FUNC_CIPHER_SET_CTX_PARAMS, \ - (void (*)(void))gcm_set_ctx_params }, \ - { OSSL_FUNC_CIPHER_GETTABLE_PARAMS, \ - (void (*)(void))cipher_default_gettable_params }, \ - { OSSL_FUNC_CIPHER_GETTABLE_CTX_PARAMS, \ - (void (*)(void))cipher_aead_gettable_ctx_params }, \ - { OSSL_FUNC_CIPHER_SETTABLE_CTX_PARAMS, \ - (void (*)(void))cipher_aead_settable_ctx_params }, \ - { 0, NULL } \ - } - static void *aes_gcm_newctx(void *provctx, size_t keybits) { PROV_AES_GCM_CTX *ctx = OPENSSL_zalloc(sizeof(*ctx)); @@ -568,11 +533,11 @@ static void aes_gcm_freectx(void *vctx) } /* aes128gcm_functions */ -IMPLEMENT_cipher(aes, gcm, GCM, AEAD_GCM_FLAGS, 128, 8, 96); +IMPLEMENT_aead_cipher(aes, gcm, GCM, AEAD_GCM_FLAGS, 128, 8, 96); /* aes192gcm_functions */ -IMPLEMENT_cipher(aes, gcm, GCM, AEAD_GCM_FLAGS, 192, 8, 96); +IMPLEMENT_aead_cipher(aes, gcm, GCM, AEAD_GCM_FLAGS, 192, 8, 96); /* aes256gcm_functions */ -IMPLEMENT_cipher(aes, gcm, GCM, AEAD_GCM_FLAGS, 256, 8, 96); +IMPLEMENT_aead_cipher(aes, gcm, GCM, AEAD_GCM_FLAGS, 256, 8, 96); #if !defined(OPENSSL_NO_ARIA) && !defined(FIPS_MODE) @@ -596,10 +561,10 @@ static void aria_gcm_freectx(void *vctx) } /* aria128gcm_functions */ -IMPLEMENT_cipher(aria, gcm, GCM, AEAD_GCM_FLAGS, 128, 8, 96); +IMPLEMENT_aead_cipher(aria, gcm, GCM, AEAD_GCM_FLAGS, 128, 8, 96); /* aria192gcm_functions */ -IMPLEMENT_cipher(aria, gcm, GCM, AEAD_GCM_FLAGS, 192, 8, 96); +IMPLEMENT_aead_cipher(aria, gcm, GCM, AEAD_GCM_FLAGS, 192, 8, 96); /* aria256gcm_functions */ -IMPLEMENT_cipher(aria, gcm, GCM, AEAD_GCM_FLAGS, 256, 8, 96); +IMPLEMENT_aead_cipher(aria, gcm, GCM, AEAD_GCM_FLAGS, 256, 8, 96); #endif /* !defined(OPENSSL_NO_ARIA) && !defined(FIPS_MODE) */ diff --git a/providers/common/include/internal/provider_algs.h b/providers/common/include/internal/provider_algs.h index 3260d93673..99e4351314 100644 --- a/providers/common/include/internal/provider_algs.h +++ b/providers/common/include/internal/provider_algs.h @@ -60,10 +60,16 @@ extern const OSSL_DISPATCH aes128ctr_functions[]; extern const OSSL_DISPATCH aes256gcm_functions[]; extern const OSSL_DISPATCH aes192gcm_functions[]; extern const OSSL_DISPATCH aes128gcm_functions[]; +extern const OSSL_DISPATCH aes256ccm_functions[]; +extern const OSSL_DISPATCH aes192ccm_functions[]; +extern const OSSL_DISPATCH aes128ccm_functions[]; #ifndef OPENSSL_NO_ARIA extern const OSSL_DISPATCH aria256gcm_functions[]; extern const OSSL_DISPATCH aria192gcm_functions[]; extern const OSSL_DISPATCH aria128gcm_functions[]; +extern const OSSL_DISPATCH aria256ccm_functions[]; +extern const OSSL_DISPATCH aria192ccm_functions[]; +extern const OSSL_DISPATCH aria128ccm_functions[]; #endif /* OPENSSL_NO_ARIA */ /* MACs */ diff --git a/providers/common/include/internal/providercommonerr.h b/providers/common/include/internal/providercommonerr.h index 3835d35d96..bf8f451d32 100644 --- a/providers/common/include/internal/providercommonerr.h +++ b/providers/common/include/internal/providercommonerr.h @@ -28,14 +28,19 @@ int ERR_load_PROV_strings(void); # define PROV_F_AES_BLOCK_FINAL 0 # define PROV_F_AES_BLOCK_UPDATE 0 # define PROV_F_AES_CIPHER 0 -# define PROV_F_AES_GET_CTX_PARAMS 0 -# define PROV_F_AES_SET_CTX_PARAMS 0 # define PROV_F_AES_DINIT 0 # define PROV_F_AES_DUPCTX 0 # define PROV_F_AES_EINIT 0 +# define PROV_F_AES_GET_CTX_PARAMS 0 # define PROV_F_AES_INIT_KEY 0 +# define PROV_F_AES_SET_CTX_PARAMS 0 # define PROV_F_AES_STREAM_UPDATE 0 # define PROV_F_AES_T4_INIT_KEY 0 +# define PROV_F_BLAKE2_MAC_INIT 0 +# define PROV_F_BLAKE2_MAC_SET_PARAMS 0 +# define PROV_F_GMAC_SET_PARAMS 0 +# define PROV_F_KMAC_SET_PARAMS 0 +# define PROV_F_POLY1305_SET_PARAMS 0 # define PROV_F_PROV_AES_KEY_GENERIC_INIT 0 # define PROV_F_TRAILINGDATA 0 # define PROV_F_UNPADBLOCK 0 @@ -51,13 +56,19 @@ int ERR_load_PROV_strings(void); # define PROV_R_FAILED_TO_SET_PARAMETER 104 # define PROV_R_INVALID_AAD 108 # define PROV_R_INVALID_CUSTOM_LENGTH 111 +# define PROV_R_INVALID_DATA 115 +# define PROV_R_INVALID_IVLEN 116 # define PROV_R_INVALID_IV_LENGTH 109 +# define PROV_R_INVALID_KEYLEN 117 # define PROV_R_INVALID_KEY_LENGTH 105 # define PROV_R_INVALID_SALT_LENGTH 112 # define PROV_R_INVALID_TAG 110 +# define PROV_R_INVALID_TAGLEN 118 # define PROV_R_NOT_XOF_OR_INVALID_LENGTH 113 # define PROV_R_NO_KEY_SET 114 # define PROV_R_OUTPUT_BUFFER_TOO_SMALL 106 +# define PROV_R_TAG_NOTSET 119 +# define PROV_R_TAG_NOT_NEEDED 120 # define PROV_R_WRONG_FINAL_BLOCK_LENGTH 107 #endif diff --git a/providers/common/provider_err.c b/providers/common/provider_err.c index b7f90057d4..9d9f484e42 100644 --- a/providers/common/provider_err.c +++ b/providers/common/provider_err.c @@ -26,16 +26,23 @@ static const ERR_STRING_DATA PROV_str_reasons[] = { {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_AAD), "invalid aad"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_CUSTOM_LENGTH), "invalid custom length"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_DATA), "invalid data"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_IVLEN), "invalid ivlen"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_IV_LENGTH), "invalid iv length"}, - {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_KEY_LENGTH), "invalid key length"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_KEYLEN), "invalid keylen"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_KEY_LENGTH), + "invalid key length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_SALT_LENGTH), "invalid salt length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_TAG), "invalid tag"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_TAGLEN), "invalid taglen"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NOT_XOF_OR_INVALID_LENGTH), "not xof or invalid length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NO_KEY_SET), "no key set"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_OUTPUT_BUFFER_TOO_SMALL), "output buffer too small"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_TAG_NOTSET), "tag notset"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_TAG_NOT_NEEDED), "tag not needed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_WRONG_FINAL_BLOCK_LENGTH), "wrong final block length"}, {0, NULL} diff --git a/providers/default/defltprov.c b/providers/default/defltprov.c index 535c05252a..6621e49b9c 100644 --- a/providers/default/defltprov.c +++ b/providers/default/defltprov.c @@ -116,13 +116,20 @@ static const OSSL_ALGORITHM deflt_ciphers[] = { { "AES-256-CTR", "default=yes", aes256ctr_functions }, { "AES-192-CTR", "default=yes", aes192ctr_functions }, { "AES-128-CTR", "default=yes", aes128ctr_functions }, +/* TODO(3.0) Add aliases when they are supported */ { "id-aes256-GCM", "default=yes", aes256gcm_functions }, { "id-aes192-GCM", "default=yes", aes192gcm_functions }, { "id-aes128-GCM", "default=yes", aes128gcm_functions }, + { "id-aes256-CCM", "default=yes", aes256ccm_functions }, + { "id-aes192-CCM", "default=yes", aes192ccm_functions }, + { "id-aes128-CCM", "default=yes", aes128ccm_functions }, #ifndef OPENSSL_NO_ARIA { "ARIA-256-GCM", "default=yes", aria256gcm_functions }, { "ARIA-192-GCM", "default=yes", aria192gcm_functions }, { "ARIA-128-GCM", "default=yes", aria128gcm_functions }, + { "ARIA-256-CCM", "default=yes", aria256ccm_functions }, + { "ARIA-192-CCM", "default=yes", aria192ccm_functions }, + { "ARIA-128-CCM", "default=yes", aria128ccm_functions }, #endif /* OPENSSL_NO_ARIA */ { NULL, NULL, NULL } }; diff --git a/providers/fips/fipsprov.c b/providers/fips/fipsprov.c index 7afe4f911a..839581bbe9 100644 --- a/providers/fips/fipsprov.c +++ b/providers/fips/fipsprov.c @@ -265,6 +265,21 @@ const char *ossl_prov_util_nid_to_name(int nid) return "AES-192-CTR"; case NID_aes_128_ctr: return "AES-128-CTR"; + /* TODO(3.0) Change these when we have aliases */ + case NID_aes_256_gcm: + return "id-aes256-GCM"; + case NID_aes_192_gcm: + return "id-aes192-GCM"; + case NID_aes_128_gcm: + return "id-aes128-GCM"; + case NID_aes_256_ccm: + return "id-aes256-CCM"; + case NID_aes_192_ccm: + return "id-aes192-CCM"; + case NID_aes_128_ccm: + return "id-aes128-CCM"; + default: + break; } return NULL; @@ -302,9 +317,13 @@ static const OSSL_ALGORITHM fips_ciphers[] = { { "AES-256-CTR", "fips=yes", aes256ctr_functions }, { "AES-192-CTR", "fips=yes", aes192ctr_functions }, { "AES-128-CTR", "fips=yes", aes128ctr_functions }, + /* TODO(3.0) Add aliases for these ciphers */ { "id-aes256-GCM", "fips=yes", aes256gcm_functions }, { "id-aes192-GCM", "fips=yes", aes192gcm_functions }, { "id-aes128-GCM", "fips=yes", aes128gcm_functions }, + { "id-aes256-CCM", "fips=yes", aes256ccm_functions }, + { "id-aes192-CCM", "fips=yes", aes192ccm_functions }, + { "id-aes128-CCM", "fips=yes", aes128ccm_functions }, { NULL, NULL, NULL } }; diff --git a/test/recipes/30-test_evp_data/evpciph.txt b/test/recipes/30-test_evp_data/evpciph.txt index 182c456896..4bff1c2dbf 100644 --- a/test/recipes/30-test_evp_data/evpciph.txt +++ b/test/recipes/30-test_evp_data/evpciph.txt @@ -2371,6 +2371,7 @@ Title = ARIA CCM test vectors from IETF draft-ietf-avtcore-aria-srtp-02 # 16-byte Tag Cipher = ARIA-128-CCM +Availablein = default Key = 974bee725d44fc3992267b284c3c6750 IV = 000020e8f5eb00000000315e AAD = 8008315ebf2e6fe020e8f5eb @@ -2379,6 +2380,7 @@ Plaintext = f57af5fd4ae19562976ec57a5a7ad55a5af5c5e5c5fdf5c55ad57a4a7272d57262e9 Ciphertext = 621e408a2e455505b39f704dcbac4307daabbd6d670abc4e42f2fd2fca263f094f4683e6fb0b10c5093d42b69dce0ba546520e7c4400975713f3bde93ef131160b9cbcd6df78a1502be7c6ea8d395b9ed0078819c3105c0ab92cb67b16ba51bb1f53508738bf7a37c9a905439b88b7af9d51a407916fdfea8d43bf253721846dc1671391225fc58d9d0693c8ade6a4ffb034ee6543dd4e651b7a084eae60f855 Cipher = ARIA-256-CCM +Availablein = default Key = 0c5ffd37a11edc42c325287fc0604f2e3e8cd5671a00fe3216aa5eb105783b54 IV = 000020e8f5eb00000000315e AAD = 8008315ebf2e6fe020e8f5eb @@ -2389,6 +2391,7 @@ Ciphertext = ff78128ee18ee3cb9fb0d20726a017ff67fbd09d3a4c38aa32f6d306d3fdda378e4 # 8-byte Tag Cipher = ARIA-128-CCM +Availablein = default Key = 974bee725d44fc3992267b284c3c6750 IV = 000020e8f5eb00000000315e AAD = 8008315ebf2e6fe020e8f5eb @@ -2397,6 +2400,7 @@ Plaintext = f57af5fd4ae19562976ec57a5a7ad55a5af5c5e5c5fdf5c55ad57a4a7272d57262e9 Ciphertext = 621e408a2e455505b39f704dcbac4307daabbd6d670abc4e42f2fd2fca263f094f4683e6fb0b10c5093d42b69dce0ba546520e7c4400975713f3bde93ef131160b9cbcd6df78a1502be7c6ea8d395b9ed0078819c3105c0ab92cb67b16ba51bb1f53508738bf7a37c9a905439b88b7af9d51a407916fdfea8d43bf253721846dc1671391225fc58d9d0693c8ade6a4ffb034ee6543dd4e651b7a084eae60f855 Cipher = ARIA-256-CCM +Availablein = default Key = 0c5ffd37a11edc42c325287fc0604f2e3e8cd5671a00fe3216aa5eb105783b54 IV = 000020e8f5eb00000000315e AAD = 8008315ebf2e6fe020e8f5eb @@ -2407,6 +2411,7 @@ Ciphertext = ff78128ee18ee3cb9fb0d20726a017ff67fbd09d3a4c38aa32f6d306d3fdda378e4 # 12-byte Tag Cipher = ARIA-128-CCM +Availablein = default Key = 974bee725d44fc3992267b284c3c6750 IV = 000020e8f5eb00000000315e AAD = 8008315ebf2e6fe020e8f5eb @@ -2415,6 +2420,7 @@ Plaintext = f57af5fd4ae19562976ec57a5a7ad55a5af5c5e5c5fdf5c55ad57a4a7272d57262e9 Ciphertext = 621e408a2e455505b39f704dcbac4307daabbd6d670abc4e42f2fd2fca263f094f4683e6fb0b10c5093d42b69dce0ba546520e7c4400975713f3bde93ef131160b9cbcd6df78a1502be7c6ea8d395b9ed0078819c3105c0ab92cb67b16ba51bb1f53508738bf7a37c9a905439b88b7af9d51a407916fdfea8d43bf253721846dc1671391225fc58d9d0693c8ade6a4ffb034ee6543dd4e651b7a084eae60f855 Cipher = ARIA-256-CCM +Availablein = default Key = 0c5ffd37a11edc42c325287fc0604f2e3e8cd5671a00fe3216aa5eb105783b54 IV = 000020e8f5eb00000000315e AAD = 8008315ebf2e6fe020e8f5eb