blob: b3d2b76028dd4193f7fbc96621af052d1ef6486d [file] [log] [blame]
Shubham Kulkarni052561d2021-07-20 11:42:44 +05301/*
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -03002 * SPDX-FileCopyrightText: 2021 Espressif Systems (Shanghai) CO LTD
Shubham Kulkarni052561d2021-07-20 11:42:44 +05303 *
4 * SPDX-License-Identifier: Apache-2.0
5 */
6
7#include <bootutil/bootutil.h>
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -03008#include <bootutil/bootutil_log.h>
9#include <bootutil/fault_injection_hardening.h>
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053010#include <bootutil/image.h>
11
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -030012#include "bootloader_init.h"
Almir Okato14763b12021-11-25 00:45:26 -030013#include "bootloader_utility.h"
14#include "bootloader_random.h"
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053015
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -030016#if defined(CONFIG_EFUSE_VIRTUAL_KEEP_IN_FLASH) || defined(CONFIG_SECURE_BOOT)
17#include "esp_efuse.h"
18#endif
19#ifdef CONFIG_SECURE_BOOT
20#include "esp_secure_boot.h"
21#endif
Almir Okato14763b12021-11-25 00:45:26 -030022#ifdef CONFIG_SECURE_FLASH_ENC_ENABLED
23#include "esp_flash_encrypt.h"
24#endif
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -030025
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -030026#include "esp_loader.h"
27#include "os/os_malloc.h"
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053028
Almir Okatoa1d641d2022-02-21 19:31:46 -030029#define IMAGE_INDEX_0 0
30#define IMAGE_INDEX_1 1
31
32#define PRIMARY_SLOT 0
33#define SECONDARY_SLOT 1
34
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -030035#ifdef CONFIG_SECURE_BOOT
36extern esp_err_t check_and_generate_secure_boot_keys(void);
37#endif
38
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053039void do_boot(struct boot_rsp *rsp)
40{
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -030041 BOOT_LOG_INF("br_image_off = 0x%x", rsp->br_image_off);
42 BOOT_LOG_INF("ih_hdr_size = 0x%x", rsp->br_hdr->ih_hdr_size);
Almir Okatoa1d641d2022-02-21 19:31:46 -030043 int slot = (rsp->br_image_off == CONFIG_ESP_IMAGE0_PRIMARY_START_ADDRESS) ? PRIMARY_SLOT : SECONDARY_SLOT;
Almir Okatoc4b30582022-05-06 14:59:43 -030044 start_cpu0_image(IMAGE_INDEX_0, slot, rsp->br_hdr->ih_hdr_size);
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053045}
Shubham Kulkarni052561d2021-07-20 11:42:44 +053046
Almir Okatoa1d641d2022-02-21 19:31:46 -030047#ifdef CONFIG_ESP_MULTI_PROCESSOR_BOOT
48int read_image_header(uint32_t img_index, uint32_t slot, struct image_header *img_header)
49{
50 const struct flash_area *fap;
51 int area_id;
52 int rc = 0;
53
54 area_id = flash_area_id_from_multi_image_slot(img_index, slot);
55 rc = flash_area_open(area_id, &fap);
56 if (rc != 0) {
57 rc = BOOT_EFLASH;
58 goto done;
59 }
60
61 if (flash_area_read(fap, 0, img_header, sizeof(struct image_header))) {
62 rc = BOOT_EFLASH;
63 goto done;
64 }
65
66 BOOT_LOG_INF("Image offset = 0x%x", fap->fa_off);
67 BOOT_LOG_INF("Image header size = 0x%x", img_header->ih_hdr_size);
68
69done:
70 flash_area_close(fap);
71 return rc;
72}
73
74void do_boot_appcpu(uint32_t img_index, uint32_t slot)
75{
Almir Okatoa1d641d2022-02-21 19:31:46 -030076 struct image_header img_header;
77
78 if (read_image_header(img_index, slot, &img_header) != 0) {
79 FIH_PANIC;
80 }
81
Almir Okatoc4b30582022-05-06 14:59:43 -030082 start_cpu1_image(img_index, slot, img_header.ih_hdr_size);
Almir Okatoa1d641d2022-02-21 19:31:46 -030083}
84#endif
85
Shubham Kulkarni052561d2021-07-20 11:42:44 +053086int main()
87{
Almir Okatofa173df2022-04-19 01:10:30 -030088 if (bootloader_init() != ESP_OK) {
89 FIH_PANIC;
90 }
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -030091
Almir Okato14763b12021-11-25 00:45:26 -030092 BOOT_LOG_INF("Enabling RNG early entropy source...");
93 bootloader_random_enable();
94
95 /* Rough steps for a first boot when Secure Boot and/or Flash Encryption are still disabled on device:
96 * Secure Boot:
97 * 1) Calculate the SHA-256 hash digest of the public key and write to EFUSE.
98 * 2) Validate the application images and prepare the booting process.
99 * 3) Burn EFUSE to enable Secure Boot V2 (ABS_DONE_0).
100 * Flash Encryption:
101 * 4) Generate Flash Encryption key and write to EFUSE.
102 * 5) Encrypt flash in-place including bootloader, image primary/secondary slot and scratch.
103 * 6) Burn EFUSE to enable Flash Encryption.
104 * 7) Reset system to ensure Flash Encryption cache resets properly.
105 */
106
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300107#ifdef CONFIG_EFUSE_VIRTUAL_KEEP_IN_FLASH
108 BOOT_LOG_WRN("eFuse virtual mode is enabled. If Secure boot or Flash encryption is enabled then it does not provide any security. FOR TESTING ONLY!");
109 esp_efuse_init_virtual_mode_in_flash(CONFIG_EFUSE_VIRTUAL_OFFSET, CONFIG_EFUSE_VIRTUAL_SIZE);
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530110#endif
Shubham Kulkarni052561d2021-07-20 11:42:44 +0530111
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300112#ifdef CONFIG_SECURE_BOOT
Almir Okato14763b12021-11-25 00:45:26 -0300113 /* Steps 1 (see above for full description):
114 * 1) Compute digest of the public key.
115 */
116
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300117 BOOT_LOG_INF("enabling secure boot v2...");
118
119 bool sb_hw_enabled = esp_secure_boot_enabled();
120
121 if (sb_hw_enabled) {
122 BOOT_LOG_INF("secure boot v2 is already enabled, continuing..");
123 } else {
124 esp_efuse_batch_write_begin(); /* Batch all efuse writes at the end of this function */
125
126 esp_err_t err;
127 err = check_and_generate_secure_boot_keys();
128 if (err != ESP_OK) {
129 esp_efuse_batch_write_cancel();
130 FIH_PANIC;
131 }
132 }
133#endif
134
135 BOOT_LOG_INF("*** Booting MCUboot build %s ***", MCUBOOT_VER);
136
Almir Okatoeb6b7bf2021-09-07 17:06:35 -0300137 os_heap_init();
138
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300139 struct boot_rsp rsp;
Almir Okato14763b12021-11-25 00:45:26 -0300140
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530141 fih_int fih_rc = FIH_FAILURE;
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300142
Almir Okato14763b12021-11-25 00:45:26 -0300143 /* Step 2 (see above for full description):
144 * 2) MCUboot validates the application images and prepares the booting process.
145 */
146
Almir Okatoa1d641d2022-02-21 19:31:46 -0300147 /* MCUboot's boot_go validates and checks all images for update and returns
148 * the load information for booting the main image
149 */
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530150 FIH_CALL(boot_go, fih_rc, &rsp);
151 if (fih_not_eq(fih_rc, FIH_SUCCESS)) {
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -0300152 BOOT_LOG_ERR("Unable to find bootable image");
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300153#ifdef CONFIG_SECURE_BOOT
154 esp_efuse_batch_write_cancel();
155#endif
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530156 FIH_PANIC;
Shubham Kulkarni052561d2021-07-20 11:42:44 +0530157 }
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300158
159#ifdef CONFIG_SECURE_BOOT
Almir Okato14763b12021-11-25 00:45:26 -0300160 /* Step 3 (see above for full description):
161 * 3) Burn EFUSE to enable Secure Boot V2.
162 */
163
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300164 if (!sb_hw_enabled) {
165 BOOT_LOG_INF("blowing secure boot efuse...");
166 esp_err_t err;
167 err = esp_secure_boot_enable_secure_features();
168 if (err != ESP_OK) {
169 esp_efuse_batch_write_cancel();
170 FIH_PANIC;
171 }
172
173 err = esp_efuse_batch_write_commit();
174 if (err != ESP_OK) {
175 BOOT_LOG_ERR("Error programming security eFuses (err=0x%x).", err);
176 FIH_PANIC;
177 }
178
179#ifdef CONFIG_SECURE_BOOT_ENABLE_AGGRESSIVE_KEY_REVOKE
180 assert(esp_efuse_read_field_bit(ESP_EFUSE_SECURE_BOOT_AGGRESSIVE_REVOKE));
181#endif
182
183 assert(esp_secure_boot_enabled());
184 BOOT_LOG_INF("Secure boot permanently enabled");
185 }
186#endif
187
Almir Okato14763b12021-11-25 00:45:26 -0300188#ifdef CONFIG_SECURE_FLASH_ENC_ENABLED
189 /* Step 4, 5 & 6 (see above for full description):
190 * 4) Generate Flash Encryption key and write to EFUSE.
191 * 5) Encrypt flash in-place including bootloader, image primary/secondary slot and scratch.
192 * 6) Burn EFUSE to enable flash encryption
193 */
194
195 int rc;
196
197 BOOT_LOG_INF("Checking flash encryption...");
198 bool flash_encryption_enabled = esp_flash_encryption_enabled();
199 rc = esp_flash_encrypt_check_and_update();
200 if (rc != ESP_OK) {
201 BOOT_LOG_ERR("Flash encryption check failed (%d).", rc);
202 FIH_PANIC;
203 }
204
205 /* Step 7 (see above for full description):
206 * 7) Reset system to ensure flash encryption cache resets properly.
207 */
208 if (!flash_encryption_enabled && esp_flash_encryption_enabled()) {
209 BOOT_LOG_INF("Resetting with flash encryption enabled...");
210 bootloader_reset();
211 }
212#endif
213
214 BOOT_LOG_INF("Disabling RNG early entropy source...");
215 bootloader_random_disable();
216
Almir Okatoa1d641d2022-02-21 19:31:46 -0300217#ifdef CONFIG_ESP_MULTI_PROCESSOR_BOOT
218 /* Multi image independent boot
219 * Boot on the second processor happens before the image0 boot
220 */
221 do_boot_appcpu(IMAGE_INDEX_1, PRIMARY_SLOT);
222#endif
223
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530224 do_boot(&rsp);
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300225
Shubham Kulkarni052561d2021-07-20 11:42:44 +0530226 while(1);
227}