bootutil: Replace hash with SHA384 when P384 is used
Currently all the hashing functionality is done with SHA256
but if we would like to use ECDSA-P384 that requires SHA384
as the hashing algorithm, but MCUboot is using SHA256
for image hashing and public key hashing. This commit modifies
the hashing operations to use SHA384 thus SHA256 can be omitted
which is beneficial from a code size standpoint.
Signed-off-by: Roland Mikhel <roland.mikhel@arm.com>
Change-Id: I59230f76f88e0b42ad6383b2c9b71b73f33d7dd7
diff --git a/boot/bootutil/src/image_validate.c b/boot/bootutil/src/image_validate.c
index 8260e59..d045a3e 100644
--- a/boot/bootutil/src/image_validate.c
+++ b/boot/bootutil/src/image_validate.c
@@ -33,7 +33,7 @@
#include <flash_map_backend/flash_map_backend.h>
#include "bootutil/image.h"
-#include "bootutil/crypto/sha256.h"
+#include "bootutil/crypto/sha.h"
#include "bootutil/sign_key.h"
#include "bootutil/security_cnt.h"
#include "bootutil/fault_injection_hardening.h"
@@ -57,7 +57,9 @@
#include "bootutil_priv.h"
/*
- * Compute SHA256 over the image.
+ * Compute SHA hash over the image.
+ * (SHA384 if ECDSA-P384 is being used,
+ * SHA256 otherwise).
*/
static int
bootutil_img_hash(struct enc_key_data *enc_state, int image_index,
@@ -65,7 +67,7 @@
uint8_t *tmp_buf, uint32_t tmp_buf_sz, uint8_t *hash_result,
uint8_t *seed, int seed_len)
{
- bootutil_sha256_context sha256_ctx;
+ bootutil_sha_context sha_ctx;
uint32_t blk_sz;
uint32_t size;
uint16_t hdr_size;
@@ -99,12 +101,12 @@
}
#endif
- bootutil_sha256_init(&sha256_ctx);
+ bootutil_sha_init(&sha_ctx);
/* in some cases (split image) the hash is seeded with data from
* the loader image */
if (seed && (seed_len > 0)) {
- bootutil_sha256_update(&sha256_ctx, seed, seed_len);
+ bootutil_sha_update(&sha_ctx, seed, seed_len);
}
/* Hash is computed over image header and image itself. */
@@ -116,9 +118,9 @@
size += hdr->ih_protect_tlv_size;
#ifdef MCUBOOT_RAM_LOAD
- bootutil_sha256_update(&sha256_ctx,
- (void*)(IMAGE_RAM_BASE + hdr->ih_load_addr),
- size);
+ bootutil_sha_update(&sha_ctx,
+ (void*)(IMAGE_RAM_BASE + hdr->ih_load_addr),
+ size);
#else
for (off = 0; off < size; off += blk_sz) {
blk_sz = size - off;
@@ -140,7 +142,7 @@
#endif
rc = flash_area_read(fap, off, tmp_buf, blk_sz);
if (rc) {
- bootutil_sha256_drop(&sha256_ctx);
+ bootutil_sha_drop(&sha_ctx);
return rc;
}
#ifdef MCUBOOT_ENC_IMAGES
@@ -153,11 +155,11 @@
}
}
#endif
- bootutil_sha256_update(&sha256_ctx, tmp_buf, blk_sz);
+ bootutil_sha_update(&sha_ctx, tmp_buf, blk_sz);
}
#endif /* MCUBOOT_RAM_LOAD */
- bootutil_sha256_finish(&sha256_ctx, hash_result);
- bootutil_sha256_drop(&sha256_ctx);
+ bootutil_sha_finish(&sha_ctx, hash_result);
+ bootutil_sha_drop(&sha_ctx);
return 0;
}
@@ -170,6 +172,7 @@
*/
#if (defined(MCUBOOT_SIGN_RSA) + \
defined(MCUBOOT_SIGN_EC256) + \
+ defined(MCUBOOT_SIGN_EC384) + \
defined(MCUBOOT_SIGN_ED25519)) > 1
#error "Only a single signature type is supported!"
#endif
@@ -185,6 +188,7 @@
# define SIG_BUF_SIZE (MCUBOOT_SIGN_RSA_LEN / 8)
# define EXPECTED_SIG_LEN(x) ((x) == SIG_BUF_SIZE) /* 2048 bits */
#elif defined(MCUBOOT_SIGN_EC256) || \
+ defined(MCUBOOT_SIGN_EC384) || \
defined(MCUBOOT_SIGN_EC)
# define EXPECTED_SIG_TLV IMAGE_TLV_ECDSA_SIG
# define SIG_BUF_SIZE 128
@@ -202,26 +206,26 @@
static int
bootutil_find_key(uint8_t *keyhash, uint8_t keyhash_len)
{
- bootutil_sha256_context sha256_ctx;
+ bootutil_sha_context sha_ctx;
int i;
const struct bootutil_key *key;
- uint8_t hash[32];
+ uint8_t hash[IMAGE_HASH_SIZE];
- if (keyhash_len > 32) {
+ if (keyhash_len > IMAGE_HASH_SIZE) {
return -1;
}
for (i = 0; i < bootutil_key_cnt; i++) {
key = &bootutil_keys[i];
- bootutil_sha256_init(&sha256_ctx);
- bootutil_sha256_update(&sha256_ctx, key->key, *key->len);
- bootutil_sha256_finish(&sha256_ctx, hash);
+ bootutil_sha_init(&sha_ctx);
+ bootutil_sha_update(&sha_ctx, key->key, *key->len);
+ bootutil_sha_finish(&sha_ctx, hash);
if (!memcmp(hash, keyhash, keyhash_len)) {
- bootutil_sha256_drop(&sha256_ctx);
+ bootutil_sha_drop(&sha_ctx);
return i;
}
}
- bootutil_sha256_drop(&sha256_ctx);
+ bootutil_sha_drop(&sha_ctx);
return -1;
}
#else
@@ -229,17 +233,17 @@
static int
bootutil_find_key(uint8_t image_index, uint8_t *key, uint16_t key_len)
{
- bootutil_sha256_context sha256_ctx;
- uint8_t hash[32];
- uint8_t key_hash[32];
+ bootutil_sha_context sha_ctx;
+ uint8_t hash[IMAGE_HASH_SIZE];
+ uint8_t key_hash[IMAGE_HASH_SIZE];
size_t key_hash_size = sizeof(key_hash);
int rc;
FIH_DECLARE(fih_rc, FIH_FAILURE);
- bootutil_sha256_init(&sha256_ctx);
- bootutil_sha256_update(&sha256_ctx, key, key_len);
- bootutil_sha256_finish(&sha256_ctx, hash);
- bootutil_sha256_drop(&sha256_ctx);
+ bootutil_sha_init(&sha_ctx);
+ bootutil_sha_update(&sha_ctx, key, key_len);
+ bootutil_sha_finish(&sha_ctx, hash);
+ bootutil_sha_drop(&sha_ctx);
rc = boot_retrieve_public_key_hash(image_index, key_hash, &key_hash_size);
if (rc) {
@@ -337,7 +341,7 @@
uint32_t off;
uint16_t len;
uint16_t type;
- int sha256_valid = 0;
+ int image_hash_valid = 0;
#ifdef EXPECTED_SIG_TLV
FIH_DECLARE(valid_signature, FIH_FAILURE);
int key_id = -1;
@@ -348,7 +352,7 @@
#endif /* EXPECTED_SIG_TLV */
struct image_tlv_iter it;
uint8_t buf[SIG_BUF_SIZE];
- uint8_t hash[32];
+ uint8_t hash[IMAGE_HASH_SIZE];
int rc = 0;
FIH_DECLARE(fih_rc, FIH_FAILURE);
#ifdef MCUBOOT_HW_ROLLBACK_PROT
@@ -364,7 +368,7 @@
}
if (out_hash) {
- memcpy(out_hash, hash, 32);
+ memcpy(out_hash, hash, IMAGE_HASH_SIZE);
}
rc = bootutil_tlv_iter_begin(&it, hdr, fap, IMAGE_TLV_ANY, false);
@@ -389,11 +393,8 @@
break;
}
- if (type == IMAGE_TLV_SHA256) {
- /*
- * Verify the SHA256 image hash. This must always be
- * present.
- */
+ if (type == EXPECTED_HASH_TLV) {
+ /* Verify the image hash. This must always be present. */
if (len != sizeof(hash)) {
rc = -1;
goto out;
@@ -409,14 +410,14 @@
goto out;
}
- sha256_valid = 1;
+ image_hash_valid = 1;
#ifdef EXPECTED_SIG_TLV
#ifndef MCUBOOT_HW_KEY
} else if (type == IMAGE_TLV_KEYHASH) {
/*
* Determine which key we should be checking.
*/
- if (len > 32) {
+ if (len > IMAGE_HASH_SIZE) {
rc = -1;
goto out;
}
@@ -506,7 +507,7 @@
}
}
- rc = !sha256_valid;
+ rc = !image_hash_valid;
if (rc) {
goto out;
}