diff --git a/wolfcrypt/src/port/maxim/max3266x.c b/wolfcrypt/src/port/maxim/max3266x.c index 752613cf4ec..988c34bd67a 100644 --- a/wolfcrypt/src/port/maxim/max3266x.c +++ b/wolfcrypt/src/port/maxim/max3266x.c @@ -245,7 +245,16 @@ int wc_MxcShaCryptoCb(wc_CryptoInfo* info) int wc_MxcCryptoCb(int devIdArg, wc_CryptoInfo* info, void* ctx) { int ret; +#ifdef MAX3266X_SHA_CB + int savedDevId; + wc_MXC_Sha *srcMxcCtx; + wc_MXC_Sha *dstMxcCtx; + int *srcDevId; + int *dstDevId; + word32 copySize; +#endif (void)ctx; + (void)devIdArg; if (info == NULL) { return BAD_FUNC_ARG; @@ -265,6 +274,132 @@ int wc_MxcCryptoCb(int devIdArg, wc_CryptoInfo* info, void* ctx) MAX3266X_MSG("Using MXC SHA HW Callback:"); ret = wc_MxcShaCryptoCb(info); /* Determine SHA HW or SW */ break; + case WC_ALGO_TYPE_COPY: + MAX3266X_MSG("Using MXC Copy Callback:"); + if (info->copy.algo == WC_ALGO_TYPE_HASH) { + srcMxcCtx = NULL; + dstMxcCtx = NULL; + srcDevId = NULL; + dstDevId = NULL; + copySize = 0; + /* Get pointers and size based on hash type */ + switch (info->copy.type) { + #ifndef NO_SHA + case WC_HASH_TYPE_SHA: + srcMxcCtx = &((wc_Sha*)info->copy.src)->mxcCtx; + dstMxcCtx = &((wc_Sha*)info->copy.dst)->mxcCtx; + srcDevId = &((wc_Sha*)info->copy.src)->devId; + dstDevId = &((wc_Sha*)info->copy.dst)->devId; + copySize = sizeof(wc_Sha); + break; + #endif + #ifdef WOLFSSL_SHA224 + case WC_HASH_TYPE_SHA224: + srcMxcCtx = &((wc_Sha224*)info->copy.src)->mxcCtx; + dstMxcCtx = &((wc_Sha224*)info->copy.dst)->mxcCtx; + srcDevId = &((wc_Sha224*)info->copy.src)->devId; + dstDevId = &((wc_Sha224*)info->copy.dst)->devId; + copySize = sizeof(wc_Sha224); + break; + #endif + #ifndef NO_SHA256 + case WC_HASH_TYPE_SHA256: + srcMxcCtx = &((wc_Sha256*)info->copy.src)->mxcCtx; + dstMxcCtx = &((wc_Sha256*)info->copy.dst)->mxcCtx; + srcDevId = &((wc_Sha256*)info->copy.src)->devId; + dstDevId = &((wc_Sha256*)info->copy.dst)->devId; + copySize = sizeof(wc_Sha256); + break; + #endif + #ifdef WOLFSSL_SHA384 + case WC_HASH_TYPE_SHA384: + srcMxcCtx = &((wc_Sha384*)info->copy.src)->mxcCtx; + dstMxcCtx = &((wc_Sha384*)info->copy.dst)->mxcCtx; + srcDevId = &((wc_Sha384*)info->copy.src)->devId; + dstDevId = &((wc_Sha384*)info->copy.dst)->devId; + copySize = sizeof(wc_Sha384); + break; + #endif + #ifdef WOLFSSL_SHA512 + case WC_HASH_TYPE_SHA512: + srcMxcCtx = &((wc_Sha512*)info->copy.src)->mxcCtx; + dstMxcCtx = &((wc_Sha512*)info->copy.dst)->mxcCtx; + srcDevId = &((wc_Sha512*)info->copy.src)->devId; + dstDevId = &((wc_Sha512*)info->copy.dst)->devId; + copySize = sizeof(wc_Sha512); + break; + #endif + default: + return WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE); + } + /* Software copy */ + savedDevId = *srcDevId; + XMEMCPY(info->copy.dst, info->copy.src, copySize); + *dstDevId = savedDevId; + /* Hardware copy - handles shallow copy from XMEMCPY */ + ret = wc_MXC_TPU_SHA_Copy(srcMxcCtx, dstMxcCtx); + } + else { + ret = WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE); + } + break; + case WC_ALGO_TYPE_FREE: + MAX3266X_MSG("Using MXC Free Callback:"); + if (info->free.algo == WC_ALGO_TYPE_HASH) { + dstMxcCtx = NULL; + dstDevId = NULL; + copySize = 0; + /* Get pointers and size based on hash type */ + switch (info->free.type) { + #ifndef NO_SHA + case WC_HASH_TYPE_SHA: + dstMxcCtx = &((wc_Sha*)info->free.obj)->mxcCtx; + dstDevId = &((wc_Sha*)info->free.obj)->devId; + copySize = sizeof(wc_Sha); + break; + #endif + #ifdef WOLFSSL_SHA224 + case WC_HASH_TYPE_SHA224: + dstMxcCtx = &((wc_Sha224*)info->free.obj)->mxcCtx; + dstDevId = &((wc_Sha224*)info->free.obj)->devId; + copySize = sizeof(wc_Sha224); + break; + #endif + #ifndef NO_SHA256 + case WC_HASH_TYPE_SHA256: + dstMxcCtx = &((wc_Sha256*)info->free.obj)->mxcCtx; + dstDevId = &((wc_Sha256*)info->free.obj)->devId; + copySize = sizeof(wc_Sha256); + break; + #endif + #ifdef WOLFSSL_SHA384 + case WC_HASH_TYPE_SHA384: + dstMxcCtx = &((wc_Sha384*)info->free.obj)->mxcCtx; + dstDevId = &((wc_Sha384*)info->free.obj)->devId; + copySize = sizeof(wc_Sha384); + break; + #endif + #ifdef WOLFSSL_SHA512 + case WC_HASH_TYPE_SHA512: + dstMxcCtx = &((wc_Sha512*)info->free.obj)->mxcCtx; + dstDevId = &((wc_Sha512*)info->free.obj)->devId; + copySize = sizeof(wc_Sha512); + break; + #endif + default: + return WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE); + } + /* Hardware free */ + wc_MXC_TPU_SHA_Free(dstMxcCtx); + /* Software free */ + *dstDevId = INVALID_DEVID; + ForceZero(info->free.obj, copySize); + ret = 0; + } + else { + ret = WC_NO_ERR_TRACE(CRYPTOCB_UNAVAILABLE); + } + break; #endif /* MAX3266X_SHA_CB */ default: MAX3266X_MSG("Callback not support with MXC, using SW"); @@ -708,18 +843,42 @@ int wc_MXC_TPU_SHA_Copy(wc_MXC_Sha* src, wc_MXC_Sha* dst) if (src == NULL || dst == NULL) { return BAD_FUNC_ARG; } - dst->used = src->used; - dst->size = src->size; - if (dst->msg == src->msg && src->msg != 0) { - /* Allocate new memory for dst->msg if it points to the same location */ - /* as src->msg */ - dst->msg = (unsigned char*)XMALLOC(src->size, NULL, - DYNAMIC_TYPE_TMP_BUFFER); - if (dst->msg == NULL) { - return MEMORY_E; /* Handle memory allocation failure */ + + /* Handle case where src has no data */ + if (src->msg == NULL || src->size == 0) { + /* Free dst if it has different data, then zero it */ + if (dst->msg != NULL && dst->msg != src->msg) { + wc_MXC_TPU_SHA_Free(dst); + } + else { + dst->msg = NULL; + dst->used = 0; + dst->size = 0; } + return 0; } - XMEMCPY(dst->msg, src->msg, src->size); + + /* Only free dst if it points to different memory than src */ + if (dst->msg != NULL && dst->msg != src->msg) { + wc_MXC_TPU_SHA_Free(dst); + } + else { + /* Reset dst without freeing (would free src's buffer) */ + dst->msg = NULL; + dst->used = 0; + dst->size = 0; + } + + /* Allocate new buffer for dst */ + dst->msg = (unsigned char*)XMALLOC(src->size, NULL, + DYNAMIC_TYPE_TMP_BUFFER); + if (dst->msg == NULL) { + return MEMORY_E; + } + + XMEMCPY(dst->msg, src->msg, src->used); + dst->used = src->used; + dst->size = src->size; return 0; } @@ -729,10 +888,17 @@ void wc_MXC_TPU_SHA_Free(wc_MXC_Sha* hash) { if (hash == NULL) { return; /* Hash Struct is Null already, dont edit potentially */ - /* undefined memory */ + /* undefined memory by accident */ } - XFREE(hash->msg, NULL, DYNAMIC_TYPE_TMP_BUFFER); - wc_MXC_TPU_SHA_Init(hash); /* sets hash->msg to null + zero's attributes */ + /* Securely zero the buffer before freeing */ + if (hash->msg != NULL) { + ForceZero(hash->msg, hash->size); + XFREE(hash->msg, NULL, DYNAMIC_TYPE_TMP_BUFFER); + } + /* Reset struct members to initial state */ + hash->msg = NULL; + hash->used = 0; + hash->size = 0; return; } diff --git a/wolfcrypt/src/sha256.c b/wolfcrypt/src/sha256.c index 690af7564c1..22fb946329b 100644 --- a/wolfcrypt/src/sha256.c +++ b/wolfcrypt/src/sha256.c @@ -1106,7 +1106,19 @@ int wc_InitSha256_ex(wc_Sha256* sha256, void* heap, int devId) return ret; sha256->heap = heap; +#ifdef WOLF_CRYPTO_CB + sha256->devId = devId; + sha256->devCtx = NULL; +#else (void)devId; +#endif + +#ifdef MAX3266X_SHA_CB + ret = wc_MXC_TPU_SHA_Init(&(sha256->mxcCtx)); + if (ret != 0) { + return ret; + } +#endif #ifdef WOLFSSL_SMALL_STACK_CACHE sha256->W = NULL; @@ -2138,6 +2150,12 @@ static WC_INLINE int Transform_Sha256_Len(wc_Sha256* sha256, const byte* data, sha224->devId = devId; sha224->devCtx = NULL; #endif + #ifdef MAX3266X_SHA_CB + ret = wc_MXC_TPU_SHA_Init(&(sha224->mxcCtx)); + if (ret != 0) { + return ret; + } + #endif #if defined(WOLFSSL_USE_ESP32_CRYPT_HASH_HW) #if defined(NO_WOLFSSL_ESP32_CRYPT_HASH_SHA224) /* We know this is a fresh, uninitialized item, so set to INIT */ diff --git a/wolfssl/wolfcrypt/port/maxim/max3266x.h b/wolfssl/wolfcrypt/port/maxim/max3266x.h index 969c328c3fc..86f361fc6ff 100644 --- a/wolfssl/wolfcrypt/port/maxim/max3266x.h +++ b/wolfssl/wolfcrypt/port/maxim/max3266x.h @@ -33,6 +33,8 @@ /* Some extra conditions when using callbacks */ #if defined(WOLF_CRYPTO_CB) #define MAX3266X_CB + #define WOLF_CRYPTO_CB_COPY /* Enable copy callback for deep copy */ + #define WOLF_CRYPTO_CB_FREE /* Enable free callback for proper cleanup */ #ifdef MAX3266X_MATH #error Cannot have MAX3266X_MATH and MAX3266X_CB #endif