diff --git a/components/bootloader/subproject/main/bootloader_start.c b/components/bootloader/subproject/main/bootloader_start.c index 770fd96190..77fc6b9509 100644 --- a/components/bootloader/subproject/main/bootloader_start.c +++ b/components/bootloader/subproject/main/bootloader_start.c @@ -262,8 +262,8 @@ static esp_partition_pos_t index_to_partition(const bootloader_state_t *bs, int return bs->test; } - if (index >= 0 && index < MAX_OTA_SLOTS) { - return bs->ota[index % bs->app_count]; + if (index >= 0 && index < MAX_OTA_SLOTS && index < bs->app_count) { + return bs->ota[index]; } esp_partition_pos_t invalid = { 0 }; @@ -272,15 +272,16 @@ static esp_partition_pos_t index_to_partition(const bootloader_state_t *bs, int static void log_invalid_app_partition(int index) { + const char *not_bootable = " is not bootable"; /* save a few string literal bytes */ switch(index) { case FACTORY_INDEX: - ESP_LOGE(TAG, "Factory app partition is not bootable"); + ESP_LOGE(TAG, "Factory app partition%s", not_bootable); break; case TEST_APP_INDEX: - ESP_LOGE(TAG, "Factory test app partition is not bootable"); + ESP_LOGE(TAG, "Factory test app partition%s", not_bootable); break; default: - ESP_LOGE(TAG, "OTA app partition slot %d is not bootable", index); + ESP_LOGE(TAG, "OTA app partition slot %d%s", index, not_bootable); break; } } @@ -367,6 +368,8 @@ static bool try_load_partition(const esp_partition_pos_t *partition, esp_image_m return false; } +#define TRY_LOG_FORMAT "Trying partition index %d offs 0x%x size 0x%x" + /* Load the app for booting. Start from partition 'start_index', if not bootable then work backwards to FACTORY_INDEX * (ie try any OTA slots in descending order and then the factory partition). * @@ -382,29 +385,29 @@ static bool load_boot_image(const bootloader_state_t *bs, int start_index, esp_i esp_partition_pos_t part; /* work backwards from start_index, down to the factory app */ - do { - ESP_LOGD(TAG, "Trying partition index %d...", index); + for(index = start_index; index >= FACTORY_INDEX; index--) { part = index_to_partition(bs, index); - ESP_LOGD(TAG, "part offs 0x%x size 0x%x", part.offset, part.size); - if (try_load_partition(&part, result)) { - return true; + if (part.size == 0) { + continue; } - if (part.size > 0) { - log_invalid_app_partition(index); - } - index--; - } while(index >= FACTORY_INDEX); - - /* failing that work forwards from start_index, try valid OTA slots */ - index = start_index + 1; - while (index < bs->app_count) { - ESP_LOGD(TAG, "Trying partition index %d...", index); - part = index_to_partition(bs, index); + ESP_LOGD(TAG, TRY_LOG_FORMAT, index, part.offset, part.size); + if (try_load_partition(&part, result)) { + return true; + } + log_invalid_app_partition(index); + } + + /* failing that work forwards from start_index, try valid OTA slots */ + for(index = start_index + 1; index < bs->app_count; index++) { + part = index_to_partition(bs, index); + if (part.size == 0) { + continue; + } + ESP_LOGD(TAG, TRY_LOG_FORMAT, index, part.offset, part.size); if (try_load_partition(&part, result)) { return true; } log_invalid_app_partition(index); - index++; } if (try_load_partition(&bs->test, result)) { diff --git a/components/bootloader_support/src/esp_image_format.c b/components/bootloader_support/src/esp_image_format.c index f19365d8d7..f053a20692 100644 --- a/components/bootloader_support/src/esp_image_format.c +++ b/components/bootloader_support/src/esp_image_format.c @@ -65,7 +65,7 @@ static esp_err_t verify_segment_header(int index, const esp_image_segment_header static esp_err_t verify_checksum(bootloader_sha256_handle_t sha_handle, uint32_t checksum_word, esp_image_metadata_t *data); -static esp_err_t __attribute__((unused)) verify_secure_boot(bootloader_sha256_handle_t sha_handle, esp_image_metadata_t *data); +static esp_err_t __attribute__((unused)) verify_secure_boot_signature(bootloader_sha256_handle_t sha_handle, esp_image_metadata_t *data); static esp_err_t __attribute__((unused)) verify_simple_hash(bootloader_sha256_handle_t sha_handle, esp_image_metadata_t *data); esp_err_t esp_image_load(esp_image_load_mode_t mode, const esp_partition_pos_t *part, esp_image_metadata_t *data) @@ -159,21 +159,32 @@ goto err; FAIL_LOAD("Image length %d doesn't fit in partition length %d", data->image_len, part->size); } + bool is_bootloader = (data->start_addr == ESP_BOOTLOADER_OFFSET); + /* For secure boot, we don't verify signature on bootloaders. + + For non-secure boot, we don't verify any SHA-256 hash appended to the bootloader because esptool.py may have + rewritten the header - rely on esptool.py having verified the bootloader at flashing time, instead. + */ + if (!is_bootloader) { #ifdef CONFIG_SECURE_BOOT_ENABLED - err = verify_secure_boot(sha_handle, data); + // secure boot images have a signature appended + err = verify_secure_boot_signature(sha_handle, data); +#else + // No secure boot, but SHA-256 can be appended for basic corruption detection + if (sha_handle != NULL) { + err = verify_simple_hash(sha_handle, data); + } +#endif // CONFIG_SECURE_BOOT_ENABLED + } else { // is_bootloader + // bootloader may still have a sha256 digest handle open + if (sha_handle != NULL) { + bootloader_sha256_finish(sha_handle, NULL); + } + } sha_handle = NULL; if (err != ESP_OK) { goto err; } -#else // No secure boot, but SHA-256 can be appended for basic corruption detection - if (sha_handle != NULL) { - err = verify_simple_hash(sha_handle, data); - sha_handle = NULL; - if (err != ESP_OK) { - goto err; - } - } -#endif #ifdef BOOTLOADER_BUILD if (do_load) { // Need to deobfuscate RAM @@ -446,7 +457,7 @@ static esp_err_t verify_checksum(bootloader_sha256_handle_t sha_handle, uint32_t static void debug_log_hash(const uint8_t *image_hash, const char *caption); -static esp_err_t verify_secure_boot(bootloader_sha256_handle_t sha_handle, esp_image_metadata_t *data) +static esp_err_t verify_secure_boot_signature(bootloader_sha256_handle_t sha_handle, esp_image_metadata_t *data) { uint8_t image_hash[HASH_LEN] = { 0 };