forked from wolfSSL/wolfssl
Test 2 part GCM data and EVP context re-use
This commit is contained in:
21
tests/api.c
21
tests/api.c
@ -35362,25 +35362,40 @@ static void test_wolfssl_EVP_aes_gcm_AAD_2_parts(void)
|
||||
|
||||
printf(testingFmt, "wolfssl_EVP_aes_gcm_AAD_2_parts");
|
||||
|
||||
/* Send AAD in 1 part */
|
||||
/* Send AAD and data in 1 part */
|
||||
AssertNotNull(ctx = EVP_CIPHER_CTX_new());
|
||||
AssertIntEQ(EVP_EncryptInit_ex(ctx, EVP_aes_128_gcm(), NULL, NULL, NULL), 1);
|
||||
AssertIntEQ(EVP_EncryptInit_ex(ctx, NULL, NULL, key, iv), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, NULL, &len, aad, sizeof(aad)), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, out1Part, &len, cleartext, sizeof(cleartext)), 1);
|
||||
AssertIntEQ(EVP_EncryptFinal_ex(ctx, out1Part, &len), 1);
|
||||
AssertIntEQ(len, sizeof(cleartext));
|
||||
AssertIntEQ(EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_GET_TAG, 16, outTag1Part), 1);
|
||||
EVP_CIPHER_CTX_free(ctx);
|
||||
|
||||
/* Send AAD in 2 parts */
|
||||
/* Send AAD and data in 2 parts */
|
||||
AssertNotNull(ctx = EVP_CIPHER_CTX_new());
|
||||
AssertIntEQ(EVP_EncryptInit_ex(ctx, EVP_aes_128_gcm(), NULL, NULL, NULL), 1);
|
||||
AssertIntEQ(EVP_EncryptInit_ex(ctx, NULL, NULL, key, iv), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, NULL, &len, aad, 1), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, NULL, &len, aad + 1, sizeof(aad) - 1), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, out2Part, &len, cleartext, sizeof(cleartext)), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, out2Part, &len, cleartext, 1), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, out2Part, &len, cleartext + 1,
|
||||
sizeof(cleartext) - 1), 1);
|
||||
AssertIntEQ(EVP_EncryptFinal_ex(ctx, out2Part, &len), 1);
|
||||
AssertIntEQ(len, sizeof(cleartext));
|
||||
AssertIntEQ(EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_GET_TAG, 16, outTag2Part), 1);
|
||||
|
||||
AssertIntEQ(XMEMCMP(out1Part, out2Part, sizeof(out1Part)), 0);
|
||||
AssertIntEQ(XMEMCMP(outTag1Part, outTag2Part, sizeof(outTag1Part)), 0);
|
||||
|
||||
/* Test AAD re-use */
|
||||
AssertIntEQ(EVP_EncryptInit_ex(ctx, EVP_aes_128_gcm(), NULL, NULL, NULL), 1);
|
||||
AssertIntEQ(EVP_EncryptInit_ex(ctx, NULL, NULL, key, iv), 1);
|
||||
AssertIntEQ(EVP_EncryptUpdate(ctx, out1Part, &len, cleartext, sizeof(cleartext)), 1);
|
||||
AssertIntEQ(EVP_EncryptFinal_ex(ctx, out1Part, &len), 1);
|
||||
AssertIntEQ(len, sizeof(cleartext));
|
||||
AssertIntEQ(EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_GET_TAG, 16, outTag1Part), 1);
|
||||
EVP_CIPHER_CTX_free(ctx);
|
||||
|
||||
AssertIntEQ(XMEMCMP(out1Part, out2Part, sizeof(out1Part)), 0);
|
||||
|
@ -572,72 +572,26 @@ static int wolfSSL_EVP_CipherUpdate_GCM(WOLFSSL_EVP_CIPHER_CTX *ctx,
|
||||
int ret = 0;
|
||||
|
||||
*outl = inl;
|
||||
if (ctx->enc) {
|
||||
if (out) {
|
||||
if (ctx->gcmAuthIn) {
|
||||
/* authenticated, non-confidential data */
|
||||
XMEMSET(ctx->authTag, 0, ctx->authTagSz);
|
||||
ret = wc_AesGcmEncrypt(&ctx->cipher.aes, NULL, NULL, 0,
|
||||
ctx->iv, ctx->ivSz, ctx->authTag, ctx->authTagSz,
|
||||
ctx->gcmAuthIn, ctx->gcmAuthInSz);
|
||||
/* Reset partial authTag error for AAD*/
|
||||
if (ret == AES_GCM_AUTH_E)
|
||||
ret = 0;
|
||||
if (ret == 0) {
|
||||
XFREE(ctx->gcmAuthIn, NULL, DYNAMIC_TYPE_OPENSSL);
|
||||
ctx->gcmAuthIn = NULL;
|
||||
ctx->gcmAuthInSz = 0;
|
||||
}
|
||||
if (out) {
|
||||
/* Buffer input for one-shot API */
|
||||
if (ret == 0) {
|
||||
byte* tmp;
|
||||
tmp = (byte*)XREALLOC(ctx->gcmBuffer,
|
||||
ctx->gcmBufferLen + inl, NULL,
|
||||
DYNAMIC_TYPE_OPENSSL);
|
||||
if (tmp) {
|
||||
XMEMCPY(tmp + ctx->gcmBufferLen, in, inl);
|
||||
ctx->gcmBufferLen += inl;
|
||||
ctx->gcmBuffer = tmp;
|
||||
*outl = 0;
|
||||
}
|
||||
else {
|
||||
ret = MEMORY_E;
|
||||
}
|
||||
|
||||
/* encrypt confidential data*/
|
||||
if (ret == 0)
|
||||
ret = wc_AesGcmEncrypt(&ctx->cipher.aes, out, in, inl,
|
||||
ctx->iv, ctx->ivSz, ctx->authTag, ctx->authTagSz,
|
||||
NULL, 0);
|
||||
}
|
||||
else {
|
||||
ret = wolfSSL_EVP_CipherUpdate_GCM_AAD(ctx, in, inl);
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (out) {
|
||||
byte* tmp;
|
||||
|
||||
if (ctx->gcmAuthIn) {
|
||||
/* authenticated, non-confidential data*/
|
||||
ret = wc_AesGcmDecrypt(&ctx->cipher.aes, NULL, NULL, 0,
|
||||
ctx->iv, ctx->ivSz,
|
||||
ctx->authTag, ctx->authTagSz,
|
||||
ctx->gcmAuthIn, ctx->gcmAuthInSz);
|
||||
/* Reset partial authTag error for AAD*/
|
||||
if (ret == AES_GCM_AUTH_E)
|
||||
ret = 0;
|
||||
if (ret == 0) {
|
||||
XFREE(ctx->gcmAuthIn, NULL, DYNAMIC_TYPE_OPENSSL);
|
||||
ctx->gcmAuthIn = NULL;
|
||||
ctx->gcmAuthInSz = 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (ret == 0) {
|
||||
tmp = (byte*)XREALLOC(ctx->gcmDecryptBuffer,
|
||||
ctx->gcmDecryptBufferLen + inl, NULL,
|
||||
DYNAMIC_TYPE_OPENSSL);
|
||||
if (tmp) {
|
||||
XMEMCPY(tmp + ctx->gcmDecryptBufferLen, in, inl);
|
||||
ctx->gcmDecryptBufferLen += inl;
|
||||
ctx->gcmDecryptBuffer = tmp;
|
||||
*outl = 0;
|
||||
}
|
||||
else {
|
||||
ret = MEMORY_E;
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
ret = wolfSSL_EVP_CipherUpdate_GCM_AAD(ctx, in, inl);
|
||||
}
|
||||
ret = wolfSSL_EVP_CipherUpdate_GCM_AAD(ctx, in, inl);
|
||||
}
|
||||
|
||||
if (ret != 0) {
|
||||
@ -810,25 +764,51 @@ int wolfSSL_EVP_CipherFinal(WOLFSSL_EVP_CIPHER_CTX *ctx,
|
||||
case AES_128_GCM_TYPE:
|
||||
case AES_192_GCM_TYPE:
|
||||
case AES_256_GCM_TYPE:
|
||||
if (!ctx->enc && ctx->gcmDecryptBuffer &&
|
||||
ctx->gcmDecryptBufferLen > 0) {
|
||||
/* decrypt confidential data*/
|
||||
ret = wc_AesGcmDecrypt(&ctx->cipher.aes, out,
|
||||
ctx->gcmDecryptBuffer, ctx->gcmDecryptBufferLen,
|
||||
ctx->iv, ctx->ivSz, ctx->authTag, ctx->authTagSz,
|
||||
NULL, 0);
|
||||
if (ctx->gcmBuffer &&
|
||||
ctx->gcmBufferLen > 0) {
|
||||
if (ctx->gcmAuthIn) {
|
||||
/* authenticated, non-confidential data*/
|
||||
if (ctx->enc) {
|
||||
XMEMSET(ctx->authTag, 0, ctx->authTagSz);
|
||||
ret = wc_AesGcmEncrypt(&ctx->cipher.aes, NULL, NULL, 0,
|
||||
ctx->iv, ctx->ivSz, ctx->authTag, ctx->authTagSz,
|
||||
ctx->gcmAuthIn, ctx->gcmAuthInSz);
|
||||
}
|
||||
else {
|
||||
ret = wc_AesGcmDecrypt(&ctx->cipher.aes, NULL, NULL, 0,
|
||||
ctx->iv, ctx->ivSz, ctx->authTag, ctx->authTagSz,
|
||||
ctx->gcmAuthIn, ctx->gcmAuthInSz);
|
||||
/* Reset partial authTag error for AAD*/
|
||||
if (ret == AES_GCM_AUTH_E)
|
||||
ret = 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (ctx->enc)
|
||||
/* encrypt confidential data*/
|
||||
ret = wc_AesGcmEncrypt(&ctx->cipher.aes, out,
|
||||
ctx->gcmBuffer, ctx->gcmBufferLen,
|
||||
ctx->iv, ctx->ivSz, ctx->authTag, ctx->authTagSz,
|
||||
NULL, 0);
|
||||
else
|
||||
/* decrypt confidential data*/
|
||||
ret = wc_AesGcmDecrypt(&ctx->cipher.aes, out,
|
||||
ctx->gcmBuffer, ctx->gcmBufferLen,
|
||||
ctx->iv, ctx->ivSz, ctx->authTag, ctx->authTagSz,
|
||||
NULL, 0);
|
||||
|
||||
if (ret == 0) {
|
||||
ret = WOLFSSL_SUCCESS;
|
||||
*outl = ctx->gcmDecryptBufferLen;
|
||||
*outl = ctx->gcmBufferLen;
|
||||
}
|
||||
else {
|
||||
ret = WOLFSSL_FAILURE;
|
||||
*outl = 0;
|
||||
}
|
||||
|
||||
XFREE(ctx->gcmDecryptBuffer, NULL, DYNAMIC_TYPE_OPENSSL);
|
||||
ctx->gcmDecryptBuffer = NULL;
|
||||
ctx->gcmDecryptBufferLen = 0;
|
||||
XFREE(ctx->gcmBuffer, NULL, DYNAMIC_TYPE_OPENSSL);
|
||||
ctx->gcmBuffer = NULL;
|
||||
ctx->gcmBufferLen = 0;
|
||||
}
|
||||
else {
|
||||
*outl = 0;
|
||||
@ -4156,11 +4136,11 @@ int wolfSSL_EVP_MD_type(const WOLFSSL_EVP_MD *md)
|
||||
ctx->cipherType = WOLFSSL_EVP_CIPH_TYPE_INIT; /* not yet initialized */
|
||||
ctx->keyLen = 0;
|
||||
#ifdef HAVE_AESGCM
|
||||
if (ctx->gcmDecryptBuffer) {
|
||||
XFREE(ctx->gcmDecryptBuffer, NULL, DYNAMIC_TYPE_OPENSSL);
|
||||
ctx->gcmDecryptBuffer = NULL;
|
||||
if (ctx->gcmBuffer) {
|
||||
XFREE(ctx->gcmBuffer, NULL, DYNAMIC_TYPE_OPENSSL);
|
||||
ctx->gcmBuffer = NULL;
|
||||
}
|
||||
ctx->gcmDecryptBufferLen = 0;
|
||||
ctx->gcmBufferLen = 0;
|
||||
if (ctx->gcmAuthIn) {
|
||||
XFREE(ctx->gcmAuthIn, NULL, DYNAMIC_TYPE_OPENSSL);
|
||||
ctx->gcmAuthIn = NULL;
|
||||
|
@ -354,8 +354,8 @@ struct WOLFSSL_EVP_CIPHER_CTX {
|
||||
#define HAVE_WOLFSSL_EVP_CIPHER_CTX_IV
|
||||
int ivSz;
|
||||
#ifdef HAVE_AESGCM
|
||||
byte* gcmDecryptBuffer;
|
||||
int gcmDecryptBufferLen;
|
||||
byte* gcmBuffer;
|
||||
int gcmBufferLen;
|
||||
ALIGN16 unsigned char authTag[AES_BLOCK_SIZE];
|
||||
int authTagSz;
|
||||
byte* gcmAuthIn;
|
||||
|
Reference in New Issue
Block a user