diff --git a/components/mbedtls/port/psa_driver/esp_aes/psa_crypto_driver_esp_cmac.c b/components/mbedtls/port/psa_driver/esp_aes/psa_crypto_driver_esp_cmac.c index c75101e143c..0387a1bff04 100644 --- a/components/mbedtls/port/psa_driver/esp_aes/psa_crypto_driver_esp_cmac.c +++ b/components/mbedtls/port/psa_driver/esp_aes/psa_crypto_driver_esp_cmac.c @@ -198,6 +198,11 @@ psa_status_t esp_cmac_mac_setup(esp_cmac_operation_t *operation, if (status != PSA_SUCCESS) { return status; } + /* After hashing, key_buffer_size is set to the hash size, which + * should be <= block_size. Verify this for static analysis. */ + if (key_buffer_size > block_size) { + return PSA_ERROR_CORRUPTION_DETECTED; + } } /* A 0-length key is not commonly used in HMAC when used as a MAC, * but it is permitted. It is common when HMAC is used in HKDF, for @@ -216,14 +221,34 @@ psa_status_t esp_cmac_mac_setup(esp_cmac_operation_t *operation, for (i = 0; i < key_buffer_size; i++) { ipad[i] ^= 0x36; } - memset(ipad + key_buffer_size, 0x36, block_size - key_buffer_size); + /* Only fill remaining bytes if key_buffer_size < block_size. + * When key_buffer_size == block_size, the entire buffer is already + * processed, so no padding is needed. This check also prevents + * out-of-bounds pointer arithmetic (ipad + key_buffer_size would be + * out of bounds when key_buffer_size == block_size == sizeof(ipad)). */ + if (key_buffer_size < block_size) { + /* At this point: key_buffer_size < block_size <= sizeof(ipad), + * so ipad + key_buffer_size is guaranteed to be within bounds. */ + size_t fill_size = block_size - key_buffer_size; + memset(ipad + key_buffer_size, 0x36, fill_size); + } /* Copy the key material from ipad to opad, flipping the requisite bits, * and filling the rest of opad with the requisite constant. */ for (i = 0; i < key_buffer_size; i++) { operation->opad[i] = ipad[i] ^ 0x36 ^ 0x5C; } - memset(operation->opad + key_buffer_size, 0x5C, block_size - key_buffer_size); + /* Only fill remaining bytes if key_buffer_size < block_size. + * When key_buffer_size == block_size, the entire buffer is already + * processed, so no padding is needed. This check also prevents + * out-of-bounds pointer arithmetic (operation->opad + key_buffer_size + * would be out of bounds when key_buffer_size == block_size == sizeof(operation->opad)). */ + if (key_buffer_size < block_size) { + /* At this point: key_buffer_size < block_size <= sizeof(operation->opad), + * so operation->opad + key_buffer_size is guaranteed to be within bounds. */ + size_t fill_size = block_size - key_buffer_size; + memset(operation->opad + key_buffer_size, 0x5C, fill_size); + } status = esp_sha_hash_setup(&operation->hmac_operation, hash_alg); if (status != PSA_SUCCESS) { return status; diff --git a/components/wpa_supplicant/esp_supplicant/src/crypto/crypto_mbedtls.c b/components/wpa_supplicant/esp_supplicant/src/crypto/crypto_mbedtls.c index 55077212fb8..12cdf1daaa2 100644 --- a/components/wpa_supplicant/esp_supplicant/src/crypto/crypto_mbedtls.c +++ b/components/wpa_supplicant/esp_supplicant/src/crypto/crypto_mbedtls.c @@ -304,8 +304,7 @@ static int hmac_vector(psa_algorithm_t alg, int ret = 0; psa_key_id_t key_id = 0; if (key == NULL || key_len == 0 || num_elem == 0 || addr == NULL || len == NULL || mac == NULL) { - ret = -1; - goto err; + return -1; } psa_status_t status; @@ -316,13 +315,14 @@ static int hmac_vector(psa_algorithm_t alg, psa_set_key_type(&attributes, PSA_KEY_TYPE_HMAC); psa_set_key_bits(&attributes, 8 * key_len); + psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT; + status = psa_import_key(&attributes, key, key_len, &key_id); if (status != PSA_SUCCESS) { ret = -1; goto err; } - psa_mac_operation_t operation = PSA_MAC_OPERATION_INIT; status = psa_mac_sign_setup(&operation, key_id, PSA_ALG_HMAC(alg)); if (status != PSA_SUCCESS) { ret = -1; @@ -354,13 +354,13 @@ static int hmac_vector(psa_algorithm_t alg, return ret; err: - if (ret != 0) { if (key_id) { psa_destroy_key(key_id); } psa_mac_abort(&operation); } + psa_reset_key_attributes(&attributes); return ret; }