diff --git a/wolfcrypt/src/aes.c b/wolfcrypt/src/aes.c index 1c8d569ed..924b27e39 100644 --- a/wolfcrypt/src/aes.c +++ b/wolfcrypt/src/aes.c @@ -3361,20 +3361,40 @@ int wc_AesSetIV(Aes* aes, const byte* iv) #endif /* WOLFSSL_AES_COUNTER */ -#ifdef HAVE_AESGCM - /* - * The IV for AES GCM, stored in struct Aes's member reg, is comprised of - * three parts in order: - * 1. The implicit IV. This is generated from the PRF using the shared - * secrets between endpoints. It is 4 bytes long. - * 2. The explicit IV. This is set by the user of the AES. It needs to be - * unique for each call to encrypt. The explicit IV is shared with the - * other end of the transaction in the clear. - * 3. The counter. Each block of data is encrypted with its own sequence - * number counter. + * The IV for AES GCM and CCM, stored in struct Aes's member reg, is comprised + * of two parts in order: + * 1. The fixed field which may be 0 or 4 bytes long. In TLS, this is set + * to the implicit IV. + * 2. The explicit IV is generated by wolfCrypt. It needs to be managed + * by wolfCrypt to ensure the IV is unique for each call to encrypt. + * The IV may be a 96-bit random value, or the 32-bit fixed value and a + * 64-bit set of 0 or random data. The final 32-bits of reg is used as a + * block counter during the encryption. */ +enum { + GCM_NONCE_SZ = 12, + CCM_NONCE_MIN_SZ = 7, + CCM_NONCE_MAX_SZ = 13, + CTR_SZ = 4, + AES_IV_FIXED_SZ = 4 +}; + +#if (defined(HAVE_AESGCM) && !defined(WC_NO_RNG)) || defined(HAVE_AESCCM) +static INLINE void IncCtr(byte* ctr, word32 ctrSz) +{ + int i; + for (i = ctrSz-1; i >= 0; i--) { + if (++ctr[i]) + break; + } +} +#endif /* HAVE_AESGCM || HAVE_AESCCM */ + + +#ifdef HAVE_AESGCM + #if defined(HAVE_COLDFIRE_SEC) #error "Coldfire SEC doesn't currently support AES-GCM mode" @@ -3383,11 +3403,6 @@ int wc_AesSetIV(Aes* aes, const byte* iv) #endif -enum { - NONCE_SZ = 12, - CTR_SZ = 4 -}; - #if !defined(FREESCALE_LTC_AES_GCM) static INLINE void IncrementGcmCounter(byte* inOutCtr) { @@ -7482,7 +7497,7 @@ int AES_GCM_encrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, ctr = counter; XMEMSET(initialCounter, 0, AES_BLOCK_SIZE); - if (ivSz == NONCE_SZ) { + if (ivSz == GCM_NONCE_SZ) { XMEMCPY(initialCounter, iv, ivSz); initialCounter[AES_BLOCK_SIZE - 1] = 1; } @@ -7494,10 +7509,10 @@ int AES_GCM_encrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, #ifdef WOLFSSL_PIC32MZ_CRYPT if (blocks) { /* use intitial IV for PIC32 HW, but don't use it below */ - XMEMCPY(aes->reg, ctr, AES_BLOCK_SIZE); + XMEMCPY(aes->tmp, ctr, AES_BLOCK_SIZE); ret = wc_Pic32AesCrypt( - aes->key, aes->keylen, aes->reg, AES_BLOCK_SIZE, + aes->key, aes->keylen, aes->tmp, AES_BLOCK_SIZE, out, in, (blocks * AES_BLOCK_SIZE), PIC32_ENCRYPTION, PIC32_ALGO_AES, PIC32_CRYPTOALGO_AES_GCM); if (ret != 0) @@ -7569,7 +7584,7 @@ int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz, defined(WOLFSSL_STM32F7)) /* additional argument checks - STM32 HW only supports 12 byte IV */ - if (ivSz != NONCE_SZ) { + if (ivSz != GCM_NONCE_SZ) { return BAD_FUNC_ARG; } @@ -7717,7 +7732,7 @@ int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz, } /* additional argument checks - STM32 HW only supports 12 byte IV */ - if (ivSz != NONCE_SZ) { + if (ivSz != GCM_NONCE_SZ) { return BAD_FUNC_ARG; } @@ -7851,7 +7866,7 @@ int AES_GCM_decrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, ctr = counter; XMEMSET(initialCounter, 0, AES_BLOCK_SIZE); - if (ivSz == NONCE_SZ) { + if (ivSz == GCM_NONCE_SZ) { XMEMCPY(initialCounter, iv, ivSz); initialCounter[AES_BLOCK_SIZE - 1] = 1; } @@ -7872,10 +7887,10 @@ int AES_GCM_decrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, #ifdef WOLFSSL_PIC32MZ_CRYPT if (blocks) { /* use intitial IV for PIC32 HW, but don't use it below */ - XMEMCPY(aes->reg, ctr, AES_BLOCK_SIZE); + XMEMCPY(aes->tmp, ctr, AES_BLOCK_SIZE); ret = wc_Pic32AesCrypt( - aes->key, aes->keylen, aes->reg, AES_BLOCK_SIZE, + aes->key, aes->keylen, aes->tmp, AES_BLOCK_SIZE, out, in, (blocks * AES_BLOCK_SIZE), PIC32_DECRYPTION, PIC32_ALGO_AES, PIC32_CRYPTOALGO_AES_GCM); if (ret != 0) @@ -7933,8 +7948,11 @@ int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz, #endif /* argument checks */ - if (aes == NULL || out == NULL || in == NULL || iv == NULL || - authTag == NULL || authTagSz > AES_BLOCK_SIZE) { + /* If the sz is non-zero, both in and out must be set. If sz is 0, + * in and out are don't cares, as this is is the GMAC case. */ + if (aes == NULL || iv == NULL || (sz != 0 && (in == NULL || out == NULL)) || + authTag == NULL || authTagSz > AES_BLOCK_SIZE || authTagSz == 0) { + return BAD_FUNC_ARG; } @@ -8018,25 +8036,131 @@ int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz, #ifndef WC_NO_RNG -int wc_AesGcmEncrypt_ex(Aes* aes, byte* out, const byte* in, word32 sz, - byte* iv, word32 ivSz, byte* authTag, word32 authTagSz, - const byte* authIn, word32 authInSz, WC_RNG* rng) +int wc_AesGcmSetIV(Aes* aes, const byte* extIv, word32 ivSz, + const byte* ivFixed, word32 ivFixedSz, + WC_RNG* rng) { int ret = 0; - if (aes == NULL || out == NULL || (in == NULL && sz != 0) || - iv == NULL || ivSz == 0 || (authIn == NULL && authInSz != 0) || - rng == NULL) { + if (aes == NULL || + (extIv != NULL && ivFixed != NULL) || + (extIv == NULL && ivFixed == NULL && rng == NULL) || + (ivFixed == NULL && ivFixedSz != 0) || + (ivFixed != NULL && ivFixedSz != AES_IV_FIXED_SZ) || + ivSz != GCM_NONCE_SZ) { + + ret = BAD_FUNC_ARG; + } + + if (ret == 0) { + byte* iv = (byte*)aes->reg; + + if (extIv == NULL) { + if (ivFixedSz) + XMEMCPY((byte*)aes->reg, ivFixed, ivFixedSz); + + if (rng == NULL) + XMEMSET(iv + ivFixedSz, 0, ivSz - ivFixedSz); + else + ret = wc_RNG_GenerateBlock(rng, + iv + ivFixedSz, ivSz - ivFixedSz); + } + else + XMEMCPY(iv, extIv, ivSz); + } + + if (ret == 0) { + /* If the IV is 96-bits, allow for a 2^64 invocation counter. */ + aes->invokeCtr[0] = 0; + aes->invokeCtr[1] = 0; + } + + return ret; +} + + +int wc_AesGcmEncrypt_ex(Aes* aes, byte* out, const byte* in, word32 sz, + byte* ivOut, word32 ivOutSz, + byte* authTag, word32 authTagSz, + const byte* authIn, word32 authInSz) +{ + int ret = 0; + + if (aes == NULL || (sz != 0 && (in == NULL || out == NULL)) || + ivOut == NULL || ivOutSz != GCM_NONCE_SZ || + (authIn == NULL && authInSz != 0)) { + + ret = BAD_FUNC_ARG; + } + + if (ret == 0) { + aes->invokeCtr[0]++; + if (aes->invokeCtr[0] == 0) { + aes->invokeCtr[1]++; + if (aes->invokeCtr[1] == 0) + ret = AES_GCM_OVERFLOW_E; + } + } + + if (ret == 0) { + ret = wc_AesGcmEncrypt(aes, out, in, sz, + (byte*)aes->reg, GCM_NONCE_SZ, + authTag, authTagSz, + authIn, authInSz); + XMEMCPY(ivOut, aes->reg, GCM_NONCE_SZ); + IncCtr((byte*)aes->reg, GCM_NONCE_SZ); + } + + return ret; +} + +int wc_Gmac(const byte* key, word32 keySz, byte* iv, word32 ivSz, + const byte* authIn, word32 authInSz, + byte* authTag, word32 authTagSz, WC_RNG* rng) +{ + Aes aes; + int ret = 0; + + if (key == NULL || iv == NULL || ivSz != GCM_NONCE_SZ || + (authIn == NULL && authInSz != 0) || authTag == NULL || + authTagSz == 0 || rng == NULL) { ret = BAD_FUNC_ARG; } if (ret == 0) - ret = wc_RNG_GenerateBlock(rng, iv, ivSz); + ret = wc_AesGcmSetKey(&aes, key, keySz); + if (ret == 0) + ret = wc_AesGcmSetIV(&aes, NULL, GCM_NONCE_SZ, NULL, 0, rng); + if (ret == 0) + ret = wc_AesGcmEncrypt_ex(&aes, NULL, NULL, 0, iv, ivSz, + authTag, authTagSz, authIn, authInSz); + ForceZero(&aes, sizeof(aes)); + + return ret; +} + +int wc_GmacVerify(const byte* key, word32 keySz, + const byte* iv, word32 ivSz, + const byte* authIn, word32 authInSz, + const byte* authTag, word32 authTagSz) +{ + Aes aes; + int ret = 0; + + if (key == NULL || iv == NULL || ivSz != GCM_NONCE_SZ || + (authIn == NULL && authInSz != 0) || authTag == NULL || + authTagSz == 0 || authTagSz > AES_BLOCK_SIZE) { + + ret = BAD_FUNC_ARG; + } if (ret == 0) - ret = wc_AesGcmEncrypt(aes, out, in, sz, iv, ivSz, - authTag, authTagSz, authIn, authInSz); + ret = wc_AesGcmSetKey(&aes, key, keySz); + if (ret == 0) + ret = wc_AesGcmDecrypt(&aes, NULL, NULL, 0, iv, ivSz, + authTag, authTagSz, authIn, authInSz); + ForceZero(&aes, sizeof(aes)); return ret; } @@ -8375,7 +8499,72 @@ int wc_AesCcmDecrypt(Aes* aes, byte* out, const byte* in, word32 inSz, return result; } + #endif /* HAVE_AES_DECRYPT */ + +#ifndef WC_NO_RNG + +int wc_AesCcmSetNonce(Aes* aes, const byte* nonce, word32 nonceSz) +{ + int ret = 0; + + if (aes == NULL || nonce == NULL || + nonceSz < CCM_NONCE_MIN_SZ || nonceSz > CCM_NONCE_MAX_SZ) { + + ret = BAD_FUNC_ARG; + } + + if (ret == 0) { + XMEMCPY(aes->reg, nonce, nonceSz); + aes->nonceSz = nonceSz; + + /* Invocation counter should be 2^61 */ + aes->invokeCtr[0] = 0; + aes->invokeCtr[1] = 0xE0000000; + } + + return ret; +} + + +int wc_AesCcmEncrypt_ex(Aes* aes, byte* out, const byte* in, word32 sz, + byte* ivOut, word32 ivOutSz, + byte* authTag, word32 authTagSz, + const byte* authIn, word32 authInSz) +{ + int ret = 0; + + if (aes == NULL || out == NULL || + (in == NULL && sz != 0) || + ivOut == NULL || + (authIn == NULL && authInSz != 0) || + (ivOutSz != aes->nonceSz)) { + + ret = BAD_FUNC_ARG; + } + + if (ret == 0) { + aes->invokeCtr[0]++; + if (aes->invokeCtr[0] == 0) { + aes->invokeCtr[1]++; + if (aes->invokeCtr[1] == 0) + ret = AES_CCM_OVERFLOW_E; + } + } + + if (ret == 0) { + ret = wc_AesCcmEncrypt(aes, out, in, sz, + (byte*)aes->reg, aes->nonceSz, + authTag, authTagSz, + authIn, authInSz); + XMEMCPY(ivOut, aes->reg, aes->nonceSz); + IncCtr((byte*)aes->reg, aes->nonceSz); + } + + return ret; +} + +#endif /* WC_NO_RNG */ #endif /* software AES CCM */ #endif /* HAVE_AESCCM */ diff --git a/wolfcrypt/src/error.c b/wolfcrypt/src/error.c index 4a639335a..f6355dab1 100644 --- a/wolfcrypt/src/error.c +++ b/wolfcrypt/src/error.c @@ -470,6 +470,12 @@ const char* wc_GetErrorString(int error) case ECDHE_KAT_FIPS_E: return "wolfcrypt FIPS ECDHE Known Answer Test Failure"; + case AES_GCM_OVERFLOW_E: + return "AES-GCM invocation counter overflow"; + + case AES_CCM_OVERFLOW_E: + return "AES-CCM invocation counter overflow"; + default: return "unknown error number"; diff --git a/wolfcrypt/test/test.c b/wolfcrypt/test/test.c index 982b4eaed..0449f17d5 100644 --- a/wolfcrypt/test/test.c +++ b/wolfcrypt/test/test.c @@ -6600,9 +6600,10 @@ int aesgcm_test(void) #endif /* HAVE_AES_DECRYPT */ #endif /* WOLFSSL_AES_256 */ - /* Test encrypt with internally generated IV */ -#if !defined(WC_NO_RNG) && \ +#if !defined(HAVE_FIPS) || \ (defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2)) + /* Test encrypt with internally generated IV */ +#ifndef WC_NO_RNG { WC_RNG rng; byte randIV[12]; @@ -6617,9 +6618,15 @@ int aesgcm_test(void) XMEMSET(resultP, 0, sizeof(resultP)); wc_AesGcmSetKey(&enc, k1, sizeof(k1)); - result = wc_AesGcmEncrypt_ex(&enc, resultC, p, sizeof(p), - randIV, sizeof(randIV), resultT, sizeof(resultT), - a, sizeof(a), &rng); + result = wc_AesGcmSetIV(&enc, NULL, sizeof(randIV), NULL, 0, &rng); + if (result != 0) + return -8213; + + result = wc_AesGcmEncrypt_ex(&enc, + resultC, p, sizeof(p), + randIV, sizeof(randIV), + resultT, sizeof(resultT), + a, sizeof(a)); #if defined(WOLFSSL_ASYNC_CRYPT) result = wc_AsyncWait(result, &enc.asyncDev, WC_ASYNC_FLAG_NONE); #endif @@ -6636,8 +6643,10 @@ int aesgcm_test(void) return -8210; } - result = wc_AesGcmDecrypt(&enc, resultP, resultC, sizeof(resultC), - randIV, sizeof(randIV), resultT, sizeof(resultT), + result = wc_AesGcmDecrypt(&enc, + resultP, resultC, sizeof(resultC), + randIV, sizeof(randIV), + resultT, sizeof(resultT), a, sizeof(a)); #if defined(WOLFSSL_ASYNC_CRYPT) result = wc_AsyncWait(result, &enc.asyncDev, WC_ASYNC_FLAG_NONE); @@ -6648,7 +6657,8 @@ int aesgcm_test(void) return -8212; wc_FreeRng(&rng); } -#endif /* WC_NO_RNG && FIPSv2 */ +#endif /* WC_NO_RNG */ +#endif wc_AesFree(&enc); @@ -6681,7 +6691,8 @@ int gmac_test(void) 0xaa, 0x10, 0xf1, 0x6d, 0x22, 0x7d, 0xc4, 0x1b }; -#if !defined(HAVE_FIPS) +#if !defined(HAVE_FIPS) || \ + (defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2)) /* FIPS builds only allow 16-byte auth tags. */ /* This sample uses a 15-byte auth tag. */ const byte k2[] = @@ -6704,7 +6715,7 @@ int gmac_test(void) 0xc6, 0x81, 0x79, 0x8e, 0x3d, 0xda, 0xb0, 0x9f, 0x8d, 0x83, 0xb0, 0xbb, 0x14, 0xb6, 0x91 }; -#endif /* HAVE_FIPS */ +#endif byte tag[16]; @@ -6715,12 +6726,54 @@ int gmac_test(void) if (XMEMCMP(t1, tag, sizeof(t1)) != 0) return -4400; -#if !defined(HAVE_FIPS) +#if !defined(HAVE_FIPS) || \ + (defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2)) XMEMSET(tag, 0, sizeof(tag)); wc_GmacSetKey(&gmac, k2, sizeof(k2)); wc_GmacUpdate(&gmac, iv2, sizeof(iv2), a2, sizeof(a2), tag, sizeof(t2)); if (XMEMCMP(t2, tag, sizeof(t2)) != 0) return -4401; + +#ifndef WC_NO_RNG + { + const byte badT[] = + { + 0xde, 0xad, 0xbe, 0xef, 0x17, 0x2e, 0xd0, 0x43, + 0xaa, 0x10, 0xf1, 0x6d, 0x22, 0x7d, 0xc4, 0x1b + }; + + WC_RNG rng; + byte iv[12]; + + #ifndef HAVE_FIPS + if (wc_InitRng_ex(&rng, HEAP_HINT, devId) != 0) + return -8214; + #else + if (wc_InitRng(&rng) != 0) + return -8214; + #endif + + if (wc_GmacVerify(k1, sizeof(k1), iv1, sizeof(iv1), a1, sizeof(a1), + t1, sizeof(t1)) != 0) + return -8215; + if (wc_GmacVerify(k1, sizeof(k1), iv1, sizeof(iv1), a1, sizeof(a1), + badT, sizeof(badT)) != AES_GCM_AUTH_E) + return -8216; + if (wc_GmacVerify(k2, sizeof(k2), iv2, sizeof(iv2), a2, sizeof(a2), + t2, sizeof(t2)) != 0) + return -8217; + + XMEMSET(tag, 0, sizeof(tag)); + XMEMSET(iv, 0, sizeof(iv)); + if (wc_Gmac(k1, sizeof(k1), iv, sizeof(iv), a1, sizeof(a1), + tag, sizeof(tag), &rng) != 0) + return -8218; + if (wc_GmacVerify(k1, sizeof(k1), iv, sizeof(iv), a1, sizeof(a1), + tag, sizeof(tag)) != 0) + return -8219; + wc_FreeRng(&rng); + } +#endif /* WC_NO_RNG */ #endif /* HAVE_FIPS */ return 0; @@ -6775,6 +6828,7 @@ int aesccm_test(void) byte t2[sizeof(t)]; byte p2[sizeof(p)]; byte c2[sizeof(c)]; + byte iv2[sizeof(iv)]; int result; @@ -6817,6 +6871,26 @@ int aesccm_test(void) if (XMEMCMP(p2, c2, sizeof(p2))) return -4507; + XMEMSET(&enc, 0, sizeof(Aes)); /* clear context */ + XMEMSET(t2, 0, sizeof(t2)); + XMEMSET(c2, 0, sizeof(c2)); + XMEMSET(p2, 0, sizeof(p2)); + XMEMSET(iv2, 0, sizeof(iv2)); + + if (wc_AesCcmSetKey(&enc, k, sizeof(k)) != 0) + return -8220; + if (wc_AesCcmSetNonce(&enc, iv, sizeof(iv)) != 0) + return -8221; + if (wc_AesCcmEncrypt_ex(&enc, c2, p, sizeof(c2), iv2, sizeof(iv2), + t2, sizeof(t2), a, sizeof(a)) != 0) + return -8222; + if (XMEMCMP(iv, iv2, sizeof(iv2))) + return -8223; + if (XMEMCMP(c, c2, sizeof(c2))) + return -8224; + if (XMEMCMP(t, t2, sizeof(t2))) + return -8225; + return 0; } #endif /* HAVE_AESCCM WOLFSSL_AES_128 */ diff --git a/wolfssl/wolfcrypt/aes.h b/wolfssl/wolfcrypt/aes.h index 44b77df11..184c65efd 100644 --- a/wolfssl/wolfcrypt/aes.h +++ b/wolfssl/wolfcrypt/aes.h @@ -109,6 +109,12 @@ typedef struct Aes { ALIGN16 word32 reg[AES_BLOCK_SIZE / sizeof(word32)]; /* for CBC mode */ ALIGN16 word32 tmp[AES_BLOCK_SIZE / sizeof(word32)]; /* same */ +#if defined(HAVE_AESGCM) || defined(HAVE_AESCCM) + word32 invokeCtr[2]; +#endif +#ifdef HAVE_AESCCM + word32 nonceSz; +#endif #ifdef HAVE_AESGCM ALIGN16 byte H[AES_BLOCK_SIZE]; #ifdef GCM_TABLE @@ -200,6 +206,7 @@ WOLFSSL_API int wc_AesEcbDecrypt(Aes* aes, byte* out, WOLFSSL_API int wc_AesSetKeyDirect(Aes* aes, const byte* key, word32 len, const byte* iv, int dir); #endif + #ifdef HAVE_AESGCM #ifdef WOLFSSL_XILINX_CRYPT WOLFSSL_API int wc_AesGcmSetKey_ex(Aes* aes, const byte* key, word32 len, @@ -218,18 +225,29 @@ WOLFSSL_API int wc_AesEcbDecrypt(Aes* aes, byte* out, const byte* authIn, word32 authInSz); #ifndef WC_NO_RNG + WOLFSSL_API int wc_AesGcmSetIV(Aes* aes, const byte* extIv, word32 ivSz, + const byte* ivFixed, word32 ivFixedSz, + WC_RNG* rng); WOLFSSL_API int wc_AesGcmEncrypt_ex(Aes* aes, byte* out, - const byte* in, word32 sz, - byte* iv, word32 ivSz, - byte* authTag, word32 authTagSz, - const byte* authIn, word32 authInSz, - WC_RNG* rng); + const byte* in, word32 sz, + byte* ivOut, word32 ivOutSz, + byte* authTag, word32 authTagSz, + const byte* authIn, word32 authInSz); #endif /* WC_NO_RNG */ WOLFSSL_API int wc_GmacSetKey(Gmac* gmac, const byte* key, word32 len); WOLFSSL_API int wc_GmacUpdate(Gmac* gmac, const byte* iv, word32 ivSz, const byte* authIn, word32 authInSz, byte* authTag, word32 authTagSz); +#ifndef WC_NO_RNG + WOLFSSL_API int wc_Gmac(const byte* key, word32 keySz, byte* iv, word32 ivSz, + const byte* authIn, word32 authInSz, + byte* authTag, word32 authTagSz, WC_RNG* rng); + WOLFSSL_API int wc_GmacVerify(const byte* key, word32 keySz, + const byte* iv, word32 ivSz, + const byte* authIn, word32 authInSz, + const byte* authTag, word32 authTagSz); +#endif /* WC_NO_RNG */ WOLFSSL_LOCAL void GHASH(Aes* aes, const byte* a, word32 aSz, const byte* c, word32 cSz, byte* s, word32 sSz); #endif /* HAVE_AESGCM */ @@ -245,6 +263,13 @@ WOLFSSL_API int wc_AesEcbDecrypt(Aes* aes, byte* out, const byte* nonce, word32 nonceSz, const byte* authTag, word32 authTagSz, const byte* authIn, word32 authInSz); + WOLFSSL_API int wc_AesCcmSetNonce(Aes* aes, + const byte* nonce, word32 nonceSz); + WOLFSSL_API int wc_AesCcmEncrypt_ex(Aes* aes, byte* out, + const byte* in, word32 sz, + byte* ivOut, word32 ivOutSz, + byte* authTag, word32 authTagSz, + const byte* authIn, word32 authInSz); #endif /* HAVE_AESCCM */ #ifdef HAVE_AES_KEYWRAP WOLFSSL_API int wc_AesKeyWrap(const byte* key, word32 keySz, diff --git a/wolfssl/wolfcrypt/error-crypt.h b/wolfssl/wolfcrypt/error-crypt.h index f2fe93128..9319838aa 100644 --- a/wolfssl/wolfcrypt/error-crypt.h +++ b/wolfssl/wolfcrypt/error-crypt.h @@ -208,8 +208,10 @@ enum { AESCCM_KAT_FIPS_E = -257, /* AESCCM KAT failure */ SHA3_KAT_FIPS_E = -258, /* SHA-3 KAT failure */ ECDHE_KAT_FIPS_E = -259, /* ECDHE KAT failure */ + AES_GCM_OVERFLOW_E = -260, /* AES-GCM invocation counter overflow. */ + AES_CCM_OVERFLOW_E = -261, /* AES-CCM invocation counter overflow. */ - WC_LAST_E = -259, /* Update this to indicate last error */ + WC_LAST_E = -261, /* Update this to indicate last error */ MIN_CODE_E = -300 /* errors -101 - -299 */ /* add new companion error id strings for any new error codes