Add support for signed images in single loader mode
Signed-off-by: Wouter Cappelle <wouter.cappelle@crodeon.com>
This commit is contained in:
parent
f9dbf68374
commit
953a76180d
|
@ -58,6 +58,10 @@
|
|||
#include "bootutil_priv.h"
|
||||
#endif
|
||||
|
||||
#ifdef MCUBOOT_ENC_IMAGES
|
||||
#include "single_loader.h"
|
||||
#endif
|
||||
|
||||
#include "serial_recovery_cbor.h"
|
||||
#include "bootutil/boot_hooks.h"
|
||||
|
||||
|
@ -200,6 +204,17 @@ bs_list(char *buf, int len)
|
|||
fih_rc, image_index, slot);
|
||||
if (fih_eq(fih_rc, BOOT_HOOK_REGULAR))
|
||||
{
|
||||
#ifdef MCUBOOT_ENC_IMAGES
|
||||
if (slot == 0 && IS_ENCRYPTED(&hdr)) {
|
||||
/* Clear the encrypted flag we didn't supply a key
|
||||
* This flag could be set if there was a decryption in place
|
||||
* performed before. We will try to validate the image without
|
||||
* decryption by clearing the flag in the heder. If
|
||||
* still encrypted the validation will fail.
|
||||
*/
|
||||
hdr.ih_flags &= ~(ENCRYPTIONFLAGS);
|
||||
}
|
||||
#endif
|
||||
FIH_CALL(bootutil_img_validate, fih_rc, NULL, 0, &hdr, fap, tmpbuf, sizeof(tmpbuf),
|
||||
NULL, 0, NULL);
|
||||
}
|
||||
|
@ -437,6 +452,13 @@ out:
|
|||
|
||||
boot_serial_output();
|
||||
flash_area_close(fap);
|
||||
|
||||
#ifdef MCUBOOT_ENC_IMAGES
|
||||
if (curr_off == img_size) {
|
||||
/* Last sector received, now start a decryption on the image if it is encrypted*/
|
||||
rc = boot_handle_enc_fw();
|
||||
}
|
||||
#endif //#ifdef MCUBOOT_ENC_IMAGES
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
|
@ -149,6 +149,7 @@ struct image_tlv {
|
|||
uint16_t it_len; /* Data length (not including TLV header). */
|
||||
};
|
||||
|
||||
#define ENCRYPTIONFLAGS (IMAGE_F_ENCRYPTED_AES128 | IMAGE_F_ENCRYPTED_AES256)
|
||||
#define IS_ENCRYPTED(hdr) (((hdr)->ih_flags & IMAGE_F_ENCRYPTED_AES128) \
|
||||
|| ((hdr)->ih_flags & IMAGE_F_ENCRYPTED_AES256))
|
||||
#define MUST_DECRYPT(fap, idx, hdr) \
|
||||
|
|
|
@ -143,7 +143,7 @@ zephyr_library_sources(
|
|||
)
|
||||
endif()
|
||||
|
||||
if(CONFIG_BOOT_SIGNATURE_TYPE_ECDSA_P256 OR CONFIG_BOOT_ENCRYPT_EC256)
|
||||
if(CONFIG_BOOT_SIGNATURE_TYPE_ECDSA_P256 OR CONFIG_BOOT_ENCRYPT_EC256 OR CONFIG_BOOT_SERIAL_ENCRYPT_EC256)
|
||||
zephyr_library_include_directories(
|
||||
${MBEDTLS_ASN1_DIR}/include
|
||||
)
|
||||
|
@ -158,6 +158,7 @@ if(CONFIG_BOOT_SIGNATURE_TYPE_ECDSA_P256 OR CONFIG_BOOT_ENCRYPT_EC256)
|
|||
${BOOT_DIR}/zephyr/include
|
||||
${TINYCRYPT_DIR}/include
|
||||
)
|
||||
zephyr_include_directories(${TINYCRYPT_DIR}/include)
|
||||
|
||||
zephyr_library_sources(
|
||||
${TINYCRYPT_DIR}/source/ecc.c
|
||||
|
@ -231,7 +232,7 @@ elseif(CONFIG_BOOT_SIGNATURE_TYPE_ED25519 OR CONFIG_BOOT_ENCRYPT_X25519)
|
|||
)
|
||||
endif()
|
||||
|
||||
if(CONFIG_BOOT_ENCRYPT_EC256 OR CONFIG_BOOT_ENCRYPT_X25519)
|
||||
if(CONFIG_BOOT_ENCRYPT_EC256 OR CONFIG_BOOT_ENCRYPT_X25519 OR CONFIG_BOOT_SERIAL_ENCRYPT_EC256)
|
||||
zephyr_library_sources(
|
||||
${TINYCRYPT_DIR}/source/aes_encrypt.c
|
||||
${TINYCRYPT_DIR}/source/aes_decrypt.c
|
||||
|
@ -304,6 +305,47 @@ if(NOT CONFIG_BOOT_SIGNATURE_KEY_FILE STREQUAL "")
|
|||
zephyr_library_sources(${GENERATED_PUBKEY})
|
||||
endif()
|
||||
|
||||
# CONF_FILE points to the KConfig configuration files of the bootloader.
|
||||
unset(CONF_DIR)
|
||||
foreach(filepath ${CONF_FILE})
|
||||
file(READ ${filepath} temp_text)
|
||||
string(FIND "${temp_text}" ${CONFIG_BOOT_ENCRYPTION_KEY_FILE} match)
|
||||
if(${match} GREATER_EQUAL 0)
|
||||
if(NOT DEFINED CONF_DIR)
|
||||
get_filename_component(CONF_DIR ${filepath} DIRECTORY)
|
||||
else()
|
||||
message(FATAL_ERROR "Encryption key file defined in multiple conf files")
|
||||
endif()
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
|
||||
if(NOT CONFIG_BOOT_ENCRYPTION_KEY_FILE STREQUAL "")
|
||||
if(IS_ABSOLUTE ${CONFIG_BOOT_ENCRYPTION_KEY_FILE})
|
||||
set(KEY_FILE ${CONFIG_BOOT_ENCRYPTION_KEY_FILE})
|
||||
elseif((DEFINED CONF_DIR) AND
|
||||
(EXISTS ${CONF_DIR}/${CONFIG_BOOT_ENCRYPTION_KEY_FILE}))
|
||||
set(KEY_FILE ${CONF_DIR}/${CONFIG_BOOT_ENCRYPTION_KEY_FILE})
|
||||
else()
|
||||
set(KEY_FILE ${MCUBOOT_DIR}/${CONFIG_BOOT_ENCRYPTION_KEY_FILE})
|
||||
endif()
|
||||
message("MCUBoot bootloader key file: ${KEY_FILE}")
|
||||
|
||||
set(GENERATED_ENCKEY ${ZEPHYR_BINARY_DIR}/autogen-enckey.c)
|
||||
add_custom_command(
|
||||
OUTPUT ${GENERATED_ENCKEY}
|
||||
COMMAND
|
||||
${PYTHON_EXECUTABLE}
|
||||
${MCUBOOT_DIR}/scripts/imgtool.py
|
||||
getpriv
|
||||
-k
|
||||
${KEY_FILE}
|
||||
> ${GENERATED_ENCKEY}
|
||||
DEPENDS ${KEY_FILE}
|
||||
)
|
||||
zephyr_library_sources(${GENERATED_ENCKEY})
|
||||
endif()
|
||||
|
||||
if(CONFIG_MCUBOOT_CLEANUP_ARM_CORE)
|
||||
zephyr_library_sources(
|
||||
${BOOT_DIR}/zephyr/arm_cleanup.c
|
||||
|
|
|
@ -292,6 +292,21 @@ config BOOT_ENCRYPT_X25519
|
|||
described under "ECIES-X25519 encryption" in docs/encrypted_images.md.
|
||||
endif # !SINGLE_APPLICATION_SLOT
|
||||
|
||||
config BOOT_ENCRYPTION_KEY_FILE
|
||||
string "encryption key file"
|
||||
depends on BOOT_ENCRYPT_EC256 || BOOT_SERIAL_ENCRYPT_EC256
|
||||
default "enc-ec256-priv.pem" if BOOT_SIGNATURE_TYPE_ECDSA_P256
|
||||
default ""
|
||||
help
|
||||
You can use either absolute or relative path.
|
||||
In case relative path is used, the build system assumes that it starts
|
||||
from the directory where the MCUBoot KConfig configuration file is
|
||||
located. If the key file is not there, the build system uses relative
|
||||
path that starts from the MCUBoot repository root directory.
|
||||
The key file will be parsed by imgtool's getpriv command and a .c source
|
||||
with the public key information will be written in a format expected by
|
||||
MCUboot.
|
||||
|
||||
config BOOT_MAX_IMG_SECTORS
|
||||
int "Maximum number of sectors per image slot"
|
||||
default 128
|
||||
|
@ -581,6 +596,16 @@ config BOOT_MGMT_CUSTOM_IMG_LIST
|
|||
statuses (custom property) for all images.
|
||||
|
||||
endif # ENABLE_MGMT_PERUSER
|
||||
|
||||
config BOOT_SERIAL_ENCRYPT_EC256
|
||||
bool "Support for encrypted upgrade images using ECIES-P256 in serial recovery upload"
|
||||
default n
|
||||
help
|
||||
If y, uploaded images via serial recovery can be decrypted
|
||||
on the fly when upgrading to the primary slot. The
|
||||
encryption mechanism used in this case is ECIES using primitives
|
||||
described under "ECIES-P256 encryption" in docs/encrypted_images.md.
|
||||
|
||||
endif # MCUBOOT_SERIAL
|
||||
|
||||
config BOOT_INTR_VEC_RELOC
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
#include "config-rsa.h"
|
||||
#elif defined(CONFIG_BOOT_SIGNATURE_TYPE_ECDSA_P256) || \
|
||||
defined(CONFIG_BOOT_ENCRYPT_EC256) || \
|
||||
defined(CONFIG_BOOT_SERIAL_ENCRYPT_EC256) || \
|
||||
(defined(CONFIG_BOOT_ENCRYPT_X25519) && !defined(CONFIG_BOOT_SIGNATURE_TYPE_ED25519))
|
||||
#include "config-asn1.h"
|
||||
#elif defined(CONFIG_BOOT_SIGNATURE_TYPE_ED25519)
|
||||
|
|
|
@ -109,6 +109,11 @@
|
|||
#define MCUBOOT_ENCRYPT_EC256
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_BOOT_SERIAL_ENCRYPT_EC256
|
||||
#define MCUBOOT_ENC_IMAGES
|
||||
#define MCUBOOT_ENCRYPT_EC256
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_BOOT_ENCRYPT_X25519
|
||||
#define MCUBOOT_ENC_IMAGES
|
||||
#define MCUBOOT_ENCRYPT_X25519
|
||||
|
|
|
@ -0,0 +1,20 @@
|
|||
/*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*
|
||||
* Copyright (c) 2021-2021 Crodeon Technologies
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef H_SINGLE_LOADER_
|
||||
#define H_SINGLE_LOADER_
|
||||
#include "bootutil/fault_injection_hardening.h"
|
||||
|
||||
/**
|
||||
* Handle an encrypted firmware in the main flash.
|
||||
* This will decrypt the image inplace
|
||||
*/
|
||||
int boot_handle_enc_fw();
|
||||
|
||||
fih_int boot_image_validate(const struct flash_area *fa_p,
|
||||
struct image_header *hdr);
|
||||
#endif
|
|
@ -186,15 +186,8 @@ const struct bootutil_key bootutil_enc_key = {
|
|||
.len = &enc_priv_key_len,
|
||||
};
|
||||
#elif defined(MCUBOOT_ENCRYPT_EC256)
|
||||
unsigned char enc_priv_key[] = {
|
||||
0x30, 0x81, 0x43, 0x02, 0x01, 0x00, 0x30, 0x13, 0x06, 0x07, 0x2a, 0x86,
|
||||
0x48, 0xce, 0x3d, 0x02, 0x01, 0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d,
|
||||
0x03, 0x01, 0x07, 0x04, 0x29, 0x30, 0x27, 0x02, 0x01, 0x01, 0x04, 0x20,
|
||||
0xf6, 0x1e, 0x51, 0x9d, 0xf8, 0xfa, 0xdd, 0xa1, 0xb7, 0xd9, 0xa9, 0x64,
|
||||
0x64, 0x3b, 0x54, 0xd0, 0x3d, 0xd0, 0x1f, 0xe5, 0x78, 0xd9, 0x17, 0x98,
|
||||
0xa5, 0x28, 0xca, 0xcc, 0x6b, 0x67, 0x9e, 0x06, 0xa1, 0x44,
|
||||
};
|
||||
static unsigned int enc_priv_key_len = 70;
|
||||
extern const unsigned char enc_priv_key[];
|
||||
extern unsigned int enc_priv_key_len;
|
||||
const struct bootutil_key bootutil_enc_key = {
|
||||
.key = enc_priv_key,
|
||||
.len = &enc_priv_key_len,
|
||||
|
|
|
@ -19,7 +19,7 @@ BOOT_LOG_MODULE_DECLARE(mcuboot);
|
|||
static const struct flash_area *_fa_p;
|
||||
static struct image_header _hdr = { 0 };
|
||||
|
||||
#ifdef MCUBOOT_VALIDATE_PRIMARY_SLOT
|
||||
#if defined(MCUBOOT_VALIDATE_PRIMARY_SLOT) || defined(MCUBOOT_VALIDATE_PRIMARY_SLOT_ONCE)
|
||||
/**
|
||||
* Validate hash of a primary boot image.
|
||||
*
|
||||
|
@ -28,7 +28,7 @@ static struct image_header _hdr = { 0 };
|
|||
*
|
||||
* @return FIH_SUCCESS on success, error code otherwise
|
||||
*/
|
||||
inline static fih_int
|
||||
fih_int
|
||||
boot_image_validate(const struct flash_area *fa_p,
|
||||
struct image_header *hdr)
|
||||
{
|
||||
|
@ -41,12 +41,21 @@ boot_image_validate(const struct flash_area *fa_p,
|
|||
* the pointer from compilation.
|
||||
*/
|
||||
/* Validate hash */
|
||||
if (hdr->ih_flags & IMAGE_F_ENCRYPTED)
|
||||
{
|
||||
/* Clear the encrypted flag we didn't supply a key
|
||||
* This flag could be set if there was a decryption in place
|
||||
* was performed. We will try to validate the image, and if still
|
||||
* encrypted the validation will fail, and go in panic mode
|
||||
*/
|
||||
hdr->ih_flags &= ~IMAGE_F_ENCRYPTED;
|
||||
}
|
||||
FIH_CALL(bootutil_img_validate, fih_rc, NULL, 0, hdr, fa_p, tmpbuf,
|
||||
BOOT_TMPBUF_SZ, NULL, 0, NULL);
|
||||
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
#endif /* MCUBOOT_VALIDATE_PRIMARY_SLOT */
|
||||
#endif /* MCUBOOT_VALIDATE_PRIMARY_SLOT || MCUBOOT_VALIDATE_PRIMARY_SLOT_ONCE*/
|
||||
|
||||
|
||||
/**
|
||||
|
@ -90,6 +99,302 @@ boot_image_load_header(const struct flash_area *fa_p,
|
|||
return 0;
|
||||
}
|
||||
|
||||
#ifdef MCUBOOT_ENC_IMAGES
|
||||
|
||||
/**
|
||||
* Validate hash of a primary boot image doing on the fly decryption as well
|
||||
*
|
||||
* @param[in] fa_p flash area pointer
|
||||
* @param[in] hdr boot image header pointer
|
||||
*
|
||||
* @return FIH_SUCCESS on success, error code otherwise
|
||||
*/
|
||||
inline static fih_int
|
||||
boot_image_validate_encrypted(const struct flash_area *fa_p,
|
||||
struct image_header *hdr)
|
||||
{
|
||||
static uint8_t tmpbuf[BOOT_TMPBUF_SZ];
|
||||
fih_int fih_rc = FIH_FAILURE;
|
||||
|
||||
struct boot_loader_state boot_data;
|
||||
struct boot_loader_state *state = &boot_data;
|
||||
struct boot_status _bs;
|
||||
struct boot_status *bs = &_bs;
|
||||
uint8_t image_index;
|
||||
int rc;
|
||||
|
||||
memset(&boot_data, 0, sizeof(struct boot_loader_state));
|
||||
image_index = BOOT_CURR_IMG(state);
|
||||
if (MUST_DECRYPT(fa_p, image_index, hdr)) {
|
||||
rc = boot_enc_load(BOOT_CURR_ENC(state), image_index, hdr, fa_p, bs);
|
||||
if (rc < 0) {
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
if (rc == 0 && boot_enc_set_key(BOOT_CURR_ENC(state), 0, bs)) {
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
}
|
||||
FIH_CALL(bootutil_img_validate, fih_rc, BOOT_CURR_ENC(state), image_index,
|
||||
hdr, fa_p, tmpbuf, BOOT_TMPBUF_SZ, NULL, 0, NULL);
|
||||
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
|
||||
/*
|
||||
* Compute the total size of the given image. Includes the size of
|
||||
* the TLVs.
|
||||
*/
|
||||
static int
|
||||
read_image_size(const struct flash_area *fa_p,
|
||||
struct image_header *hdr,
|
||||
uint32_t *size)
|
||||
{
|
||||
struct image_tlv_info info;
|
||||
uint32_t off;
|
||||
uint32_t protect_tlv_size;
|
||||
int rc;
|
||||
|
||||
off = BOOT_TLV_OFF(hdr);
|
||||
|
||||
if (flash_area_read(fa_p, off, &info, sizeof(info))) {
|
||||
rc = BOOT_EFLASH;
|
||||
goto done;
|
||||
}
|
||||
|
||||
protect_tlv_size = hdr->ih_protect_tlv_size;
|
||||
if (info.it_magic == IMAGE_TLV_PROT_INFO_MAGIC) {
|
||||
if (protect_tlv_size != info.it_tlv_tot) {
|
||||
rc = BOOT_EBADIMAGE;
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (flash_area_read(fa_p, off + info.it_tlv_tot, &info, sizeof(info))) {
|
||||
rc = BOOT_EFLASH;
|
||||
goto done;
|
||||
}
|
||||
} else if (protect_tlv_size != 0) {
|
||||
rc = BOOT_EBADIMAGE;
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (info.it_magic != IMAGE_TLV_INFO_MAGIC) {
|
||||
rc = BOOT_EBADIMAGE;
|
||||
goto done;
|
||||
}
|
||||
|
||||
*size = off + protect_tlv_size + info.it_tlv_tot;
|
||||
rc = 0;
|
||||
|
||||
done:
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* reads, decrypts in memory & write back the decrypted image in the same region
|
||||
* This function is NOT power failsafe since the image is decrypted in ram (stack)
|
||||
*
|
||||
* @param flash_area The ID of the source flash area.
|
||||
* @param off_src The offset within the flash area to
|
||||
* copy from.
|
||||
* @param sz The number of bytes to copy. should match erase sector
|
||||
*
|
||||
* @return 0 on success; nonzero on failure.
|
||||
*/
|
||||
int
|
||||
decrypt_region_inplace(struct boot_loader_state *state,
|
||||
const struct flash_area *fap,
|
||||
struct image_header *hdr,
|
||||
uint32_t off, uint32_t sz)
|
||||
{
|
||||
uint32_t bytes_copied;
|
||||
int chunk_sz;
|
||||
int rc;
|
||||
uint32_t tlv_off;
|
||||
size_t blk_off;
|
||||
uint16_t idx;
|
||||
uint32_t blk_sz;
|
||||
uint8_t image_index;
|
||||
|
||||
static uint8_t buf[1024] __attribute__((aligned));
|
||||
assert(sz <= sizeof buf);
|
||||
|
||||
bytes_copied = 0;
|
||||
while (bytes_copied < sz) {
|
||||
if (sz - bytes_copied > sizeof buf) {
|
||||
chunk_sz = sizeof buf;
|
||||
} else {
|
||||
chunk_sz = sz - bytes_copied;
|
||||
}
|
||||
|
||||
rc = flash_area_read(fap, off + bytes_copied, buf, chunk_sz);
|
||||
if (rc != 0) {
|
||||
return BOOT_EFLASH;
|
||||
}
|
||||
|
||||
image_index = BOOT_CURR_IMG(state);
|
||||
if (IS_ENCRYPTED(hdr)) {
|
||||
blk_sz = chunk_sz;
|
||||
idx = 0;
|
||||
if (off + bytes_copied < hdr->ih_hdr_size) {
|
||||
/* do not decrypt header */
|
||||
if (hdr->ih_hdr_size > (off + bytes_copied + chunk_sz)) {
|
||||
/* all bytes in header, skip decryption */
|
||||
blk_sz = 0;
|
||||
}
|
||||
else {
|
||||
blk_sz = off + bytes_copied + chunk_sz - hdr->ih_hdr_size;
|
||||
}
|
||||
|
||||
blk_off = 0;
|
||||
idx = hdr->ih_hdr_size;
|
||||
} else {
|
||||
blk_off = ((off + bytes_copied) - hdr->ih_hdr_size) & 0xf;
|
||||
}
|
||||
tlv_off = BOOT_TLV_OFF(hdr);
|
||||
if (off + bytes_copied + chunk_sz > tlv_off) {
|
||||
/* do not decrypt TLVs */
|
||||
if (off + bytes_copied >= tlv_off) {
|
||||
blk_sz = 0;
|
||||
} else {
|
||||
blk_sz = tlv_off - (off + bytes_copied);
|
||||
}
|
||||
}
|
||||
boot_encrypt(BOOT_CURR_ENC(state), image_index, fap,
|
||||
(off + bytes_copied + idx) - hdr->ih_hdr_size, blk_sz,
|
||||
blk_off, &buf[idx]);
|
||||
}
|
||||
rc = flash_area_erase(fap, off + bytes_copied, chunk_sz);
|
||||
if (rc != 0) {
|
||||
return BOOT_EFLASH;
|
||||
}
|
||||
rc = flash_area_write(fap, off + bytes_copied, buf, chunk_sz);
|
||||
if (rc != 0) {
|
||||
return BOOT_EFLASH;
|
||||
}
|
||||
|
||||
bytes_copied += chunk_sz;
|
||||
|
||||
MCUBOOT_WATCHDOG_FEED();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if a image was encrypted into the first slot, and decrypt it
|
||||
* in place. this operation is not power failsafe.
|
||||
*
|
||||
* The operation is done by checking the last flash sector, and using it as a
|
||||
* temporarely scratch partition. The
|
||||
*
|
||||
* @param[in] fa_p flash area pointer
|
||||
* @param[in] hdr boot image header pointer
|
||||
*
|
||||
* @return FIH_SUCCESS on success, error code otherwise
|
||||
*/
|
||||
inline static fih_int
|
||||
decrypt_image_inplace(const struct flash_area *fa_p,
|
||||
struct image_header *hdr)
|
||||
{
|
||||
fih_int fih_rc = FIH_FAILURE;
|
||||
int rc;
|
||||
struct boot_loader_state boot_data;
|
||||
struct boot_loader_state *state = &boot_data;
|
||||
struct boot_status _bs;
|
||||
struct boot_status *bs = &_bs;
|
||||
size_t size;
|
||||
size_t sect_size;
|
||||
size_t sect_count;
|
||||
size_t sect;
|
||||
uint8_t image_index;
|
||||
struct flash_sector sector;
|
||||
|
||||
memset(&boot_data, 0, sizeof(struct boot_loader_state));
|
||||
memset(&_bs, 0, sizeof(struct boot_status));
|
||||
|
||||
/* Get size from last sector to know page/sector erase size */
|
||||
rc = flash_area_sector_from_off(boot_status_off(fa_p), §or);
|
||||
|
||||
|
||||
image_index = BOOT_CURR_IMG(state);
|
||||
|
||||
if (MUST_DECRYPT(fa_p, image_index, hdr)) {
|
||||
#if 0 //Skip this step?, the image will just not boot if it's not decrypted properly
|
||||
/* First check if the encrypted image is a good image before decrypting */
|
||||
FIH_CALL(boot_image_validate_encrypted,fih_rc,_fa_p,&_hdr);
|
||||
if (fih_not_eq(fih_rc, FIH_SUCCESS)) {
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
#endif
|
||||
memset(&boot_data, 0, sizeof(struct boot_loader_state));
|
||||
/* Load the encryption keys into cache */
|
||||
rc = boot_enc_load(BOOT_CURR_ENC(state), image_index, hdr, fa_p, bs);
|
||||
if (rc < 0) {
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
if (rc == 0 && boot_enc_set_key(BOOT_CURR_ENC(state), 0, bs)) {
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Expected encrypted image! */
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
|
||||
uint32_t src_size = 0;
|
||||
rc = read_image_size(fa_p,hdr, &src_size);
|
||||
if (rc != 0) {
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
|
||||
sect_size = sector.fs_size;
|
||||
sect_count = fa_p->fa_size / sect_size;
|
||||
for (sect = 0, size = 0; size < src_size && sect < sect_count; sect++) {
|
||||
rc = decrypt_region_inplace(state, fa_p,hdr, size, sect_size);
|
||||
if (rc != 0) {
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
size += sect_size;
|
||||
}
|
||||
|
||||
fih_rc = FIH_SUCCESS;
|
||||
FIH_RET(fih_rc);
|
||||
}
|
||||
|
||||
int
|
||||
boot_handle_enc_fw()
|
||||
{
|
||||
int rc = -1;
|
||||
fih_int fih_rc = FIH_FAILURE;
|
||||
|
||||
rc = flash_area_open(FLASH_AREA_IMAGE_PRIMARY(0), &_fa_p);
|
||||
assert(rc == 0);
|
||||
|
||||
rc = boot_image_load_header(_fa_p, &_hdr);
|
||||
if (rc != 0) {
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (IS_ENCRYPTED(&_hdr)) {
|
||||
//encrypted, we need to decrypt in place
|
||||
FIH_CALL(decrypt_image_inplace,fih_rc,_fa_p,&_hdr);
|
||||
if (fih_not_eq(fih_rc, FIH_SUCCESS)) {
|
||||
rc = -1;
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
rc = 0;
|
||||
}
|
||||
|
||||
out:
|
||||
flash_area_close(_fa_p);
|
||||
return rc;
|
||||
}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Gather information on image and prepare for booting.
|
||||
|
|
Loading…
Reference in New Issue