blob: 3f4d5a0644288aab7d1330d5d6932e8f23e05821 [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"
Almir Okatodb2024e2023-08-24 15:40:26 -030015#include "bootloader_soc.h"
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053016
Almir Okato54ef4842023-03-07 17:56:53 -030017#include "esp_assert.h"
18
Almir Okatoe8cbc0d2022-06-13 10:45:39 -030019#ifdef CONFIG_MCUBOOT_SERIAL
20#include "boot_serial/boot_serial.h"
21#include "serial_adapter/serial_adapter.h"
22
23const struct boot_uart_funcs boot_funcs = {
24 .read = console_read,
25 .write = console_write
26};
27#endif
28
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -030029#if defined(CONFIG_EFUSE_VIRTUAL_KEEP_IN_FLASH) || defined(CONFIG_SECURE_BOOT)
30#include "esp_efuse.h"
31#endif
32#ifdef CONFIG_SECURE_BOOT
33#include "esp_secure_boot.h"
34#endif
Almir Okato14763b12021-11-25 00:45:26 -030035#ifdef CONFIG_SECURE_FLASH_ENC_ENABLED
36#include "esp_flash_encrypt.h"
37#endif
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -030038
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -030039#include "esp_loader.h"
40#include "os/os_malloc.h"
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053041
Almir Okatoa1d641d2022-02-21 19:31:46 -030042#define IMAGE_INDEX_0 0
43#define IMAGE_INDEX_1 1
44
45#define PRIMARY_SLOT 0
46#define SECONDARY_SLOT 1
47
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -030048#ifdef CONFIG_SECURE_BOOT
49extern esp_err_t check_and_generate_secure_boot_keys(void);
50#endif
51
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053052void do_boot(struct boot_rsp *rsp)
53{
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -030054 BOOT_LOG_INF("br_image_off = 0x%x", rsp->br_image_off);
55 BOOT_LOG_INF("ih_hdr_size = 0x%x", rsp->br_hdr->ih_hdr_size);
Almir Okatoa1d641d2022-02-21 19:31:46 -030056 int slot = (rsp->br_image_off == CONFIG_ESP_IMAGE0_PRIMARY_START_ADDRESS) ? PRIMARY_SLOT : SECONDARY_SLOT;
Almir Okatoc4b30582022-05-06 14:59:43 -030057 start_cpu0_image(IMAGE_INDEX_0, slot, rsp->br_hdr->ih_hdr_size);
Shubham Kulkarni8787bb02021-07-20 11:46:03 +053058}
Shubham Kulkarni052561d2021-07-20 11:42:44 +053059
Almir Okatoa1d641d2022-02-21 19:31:46 -030060#ifdef CONFIG_ESP_MULTI_PROCESSOR_BOOT
61int read_image_header(uint32_t img_index, uint32_t slot, struct image_header *img_header)
62{
63 const struct flash_area *fap;
64 int area_id;
65 int rc = 0;
66
67 area_id = flash_area_id_from_multi_image_slot(img_index, slot);
68 rc = flash_area_open(area_id, &fap);
69 if (rc != 0) {
70 rc = BOOT_EFLASH;
71 goto done;
72 }
73
74 if (flash_area_read(fap, 0, img_header, sizeof(struct image_header))) {
75 rc = BOOT_EFLASH;
76 goto done;
77 }
78
79 BOOT_LOG_INF("Image offset = 0x%x", fap->fa_off);
80 BOOT_LOG_INF("Image header size = 0x%x", img_header->ih_hdr_size);
81
82done:
83 flash_area_close(fap);
84 return rc;
85}
86
87void do_boot_appcpu(uint32_t img_index, uint32_t slot)
88{
Almir Okatoa1d641d2022-02-21 19:31:46 -030089 struct image_header img_header;
90
91 if (read_image_header(img_index, slot, &img_header) != 0) {
92 FIH_PANIC;
93 }
94
Almir Okatoc4b30582022-05-06 14:59:43 -030095 start_cpu1_image(img_index, slot, img_header.ih_hdr_size);
Almir Okatoa1d641d2022-02-21 19:31:46 -030096}
97#endif
98
Shubham Kulkarni052561d2021-07-20 11:42:44 +053099int main()
100{
Almir Okatofa173df2022-04-19 01:10:30 -0300101 if (bootloader_init() != ESP_OK) {
102 FIH_PANIC;
103 }
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300104
Almir Okato14763b12021-11-25 00:45:26 -0300105 /* Rough steps for a first boot when Secure Boot and/or Flash Encryption are still disabled on device:
106 * Secure Boot:
107 * 1) Calculate the SHA-256 hash digest of the public key and write to EFUSE.
108 * 2) Validate the application images and prepare the booting process.
109 * 3) Burn EFUSE to enable Secure Boot V2 (ABS_DONE_0).
110 * Flash Encryption:
111 * 4) Generate Flash Encryption key and write to EFUSE.
112 * 5) Encrypt flash in-place including bootloader, image primary/secondary slot and scratch.
113 * 6) Burn EFUSE to enable Flash Encryption.
114 * 7) Reset system to ensure Flash Encryption cache resets properly.
115 */
116
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300117#ifdef CONFIG_EFUSE_VIRTUAL_KEEP_IN_FLASH
118 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!");
119 esp_efuse_init_virtual_mode_in_flash(CONFIG_EFUSE_VIRTUAL_OFFSET, CONFIG_EFUSE_VIRTUAL_SIZE);
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530120#endif
Shubham Kulkarni052561d2021-07-20 11:42:44 +0530121
Almir Okatodb2024e2023-08-24 15:40:26 -0300122#if defined(CONFIG_SECURE_BOOT) || defined(CONFIG_SECURE_FLASH_ENC_ENABLED)
123 esp_err_t err;
124#endif
125
126#ifdef CONFIG_SECURE_BOOT_FLASH_ENC_KEYS_BURN_TOGETHER
127 if (esp_secure_boot_enabled() ^ esp_flash_encrypt_initialized_once()) {
128 BOOT_LOG_ERR("Secure Boot and Flash Encryption cannot be enabled separately, only together (their keys go into one eFuse key block)");
129 FIH_PANIC;
130 }
131
132 if (!esp_secure_boot_enabled() || !esp_flash_encryption_enabled()) {
133 esp_efuse_batch_write_begin();
134 }
135#endif // CONFIG_SECURE_BOOT_FLASH_ENC_KEYS_BURN_TOGETHER
136
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300137#ifdef CONFIG_SECURE_BOOT
Almir Okato14763b12021-11-25 00:45:26 -0300138 /* Steps 1 (see above for full description):
139 * 1) Compute digest of the public key.
140 */
141
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300142 BOOT_LOG_INF("enabling secure boot v2...");
143
144 bool sb_hw_enabled = esp_secure_boot_enabled();
145
146 if (sb_hw_enabled) {
147 BOOT_LOG_INF("secure boot v2 is already enabled, continuing..");
148 } else {
149 esp_efuse_batch_write_begin(); /* Batch all efuse writes at the end of this function */
150
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300151 err = check_and_generate_secure_boot_keys();
152 if (err != ESP_OK) {
153 esp_efuse_batch_write_cancel();
154 FIH_PANIC;
155 }
156 }
157#endif
158
Almir Okatoeb6b7bf2021-09-07 17:06:35 -0300159 os_heap_init();
160
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300161 struct boot_rsp rsp;
Almir Okato14763b12021-11-25 00:45:26 -0300162
Michael Grand5047f032022-11-24 16:49:56 +0100163 FIH_DECLARE(fih_rc, FIH_FAILURE);
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300164
Almir Okatoe8cbc0d2022-06-13 10:45:39 -0300165#ifdef CONFIG_MCUBOOT_SERIAL
166 boot_console_init();
167 if (boot_serial_detect_pin()) {
168 BOOT_LOG_INF("Enter the serial recovery mode");
169 boot_serial_start(&boot_funcs);
170 }
171#endif
172
Almir Okato14763b12021-11-25 00:45:26 -0300173 /* Step 2 (see above for full description):
174 * 2) MCUboot validates the application images and prepares the booting process.
175 */
176
Almir Okatoa1d641d2022-02-21 19:31:46 -0300177 /* MCUboot's boot_go validates and checks all images for update and returns
178 * the load information for booting the main image
179 */
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530180 FIH_CALL(boot_go, fih_rc, &rsp);
Michael Grand5047f032022-11-24 16:49:56 +0100181 if (FIH_NOT_EQ(fih_rc, FIH_SUCCESS)) {
Gustavo Henrique Niheid985d222021-11-12 14:21:12 -0300182 BOOT_LOG_ERR("Unable to find bootable image");
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300183#ifdef CONFIG_SECURE_BOOT
184 esp_efuse_batch_write_cancel();
185#endif
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530186 FIH_PANIC;
Shubham Kulkarni052561d2021-07-20 11:42:44 +0530187 }
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300188
189#ifdef CONFIG_SECURE_BOOT
Almir Okato14763b12021-11-25 00:45:26 -0300190 /* Step 3 (see above for full description):
191 * 3) Burn EFUSE to enable Secure Boot V2.
192 */
193
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300194 if (!sb_hw_enabled) {
195 BOOT_LOG_INF("blowing secure boot efuse...");
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300196 err = esp_secure_boot_enable_secure_features();
197 if (err != ESP_OK) {
198 esp_efuse_batch_write_cancel();
199 FIH_PANIC;
200 }
201
202 err = esp_efuse_batch_write_commit();
203 if (err != ESP_OK) {
204 BOOT_LOG_ERR("Error programming security eFuses (err=0x%x).", err);
205 FIH_PANIC;
206 }
207
208#ifdef CONFIG_SECURE_BOOT_ENABLE_AGGRESSIVE_KEY_REVOKE
209 assert(esp_efuse_read_field_bit(ESP_EFUSE_SECURE_BOOT_AGGRESSIVE_REVOKE));
210#endif
211
Almir Okatodb2024e2023-08-24 15:40:26 -0300212#ifndef CONFIG_SECURE_BOOT_FLASH_ENC_KEYS_BURN_TOGETHER
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300213 assert(esp_secure_boot_enabled());
214 BOOT_LOG_INF("Secure boot permanently enabled");
Almir Okatodb2024e2023-08-24 15:40:26 -0300215#endif
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300216 }
217#endif
218
Almir Okato14763b12021-11-25 00:45:26 -0300219#ifdef CONFIG_SECURE_FLASH_ENC_ENABLED
220 /* Step 4, 5 & 6 (see above for full description):
221 * 4) Generate Flash Encryption key and write to EFUSE.
222 * 5) Encrypt flash in-place including bootloader, image primary/secondary slot and scratch.
223 * 6) Burn EFUSE to enable flash encryption
224 */
Almir Okato14763b12021-11-25 00:45:26 -0300225 BOOT_LOG_INF("Checking flash encryption...");
Almir Okatodb2024e2023-08-24 15:40:26 -0300226 bool flash_encryption_enabled = esp_flash_encrypt_state();
227 if (!flash_encryption_enabled) {
228#ifdef CONFIG_SECURE_FLASH_REQUIRE_ALREADY_ENABLED
229 BOOT_LOG_ERR("flash encryption is not enabled, and SECURE_FLASH_REQUIRE_ALREADY_ENABLED is set, refusing to boot.");
Almir Okato14763b12021-11-25 00:45:26 -0300230 FIH_PANIC;
Almir Okatodb2024e2023-08-24 15:40:26 -0300231#endif // CONFIG_SECURE_FLASH_REQUIRE_ALREADY_ENABLED
232
233 if (esp_flash_encrypt_is_write_protected(true)) {
234 FIH_PANIC;
235 }
236
237 err = esp_flash_encrypt_init();
238 if (err != ESP_OK) {
239 BOOT_LOG_ERR("Initialization of Flash Encryption key failed (%d)", err);
240 FIH_PANIC;
241 }
Almir Okato14763b12021-11-25 00:45:26 -0300242 }
243
Almir Okatodb2024e2023-08-24 15:40:26 -0300244 if (!flash_encryption_enabled) {
245 err = esp_flash_encrypt_contents();
246 if (err != ESP_OK) {
247 BOOT_LOG_ERR("Encryption flash contents failed (%d)", err);
248 FIH_PANIC;
249 }
250
251 err = esp_flash_encrypt_enable();
252 if (err != ESP_OK) {
253 BOOT_LOG_ERR("Enabling of Flash encryption failed (%d)", err);
254 FIH_PANIC;
255 }
256 }
257
258#ifdef CONFIG_SECURE_BOOT_FLASH_ENC_KEYS_BURN_TOGETHER
259 if (!esp_secure_boot_enabled() || !flash_encryption_enabled) {
260 err = esp_efuse_batch_write_commit();
261 if (err != ESP_OK) {
262 BOOT_LOG_ERR("Error programming eFuses (err=0x%x).", err);
263 FIH_PANIC;
264 }
265 assert(esp_secure_boot_enabled());
266 BOOT_LOG_INF("Secure boot permanently enabled");
267 }
268#endif // CONFIG_SECURE_BOOT_FLASH_ENC_KEYS_BURN_TOGETHER
269
Almir Okato14763b12021-11-25 00:45:26 -0300270 /* Step 7 (see above for full description):
271 * 7) Reset system to ensure flash encryption cache resets properly.
272 */
273 if (!flash_encryption_enabled && esp_flash_encryption_enabled()) {
274 BOOT_LOG_INF("Resetting with flash encryption enabled...");
275 bootloader_reset();
276 }
277#endif
278
279 BOOT_LOG_INF("Disabling RNG early entropy source...");
280 bootloader_random_disable();
281
Almir Okatodb2024e2023-08-24 15:40:26 -0300282 /* Disable glitch reset after all the security checks are completed.
283 * Glitch detection can be falsely triggered by EMI interference (high RF TX power, etc)
284 * and to avoid such false alarms, disable it.
285 */
286 bootloader_ana_clock_glitch_reset_config(false);
287
Almir Okatoa1d641d2022-02-21 19:31:46 -0300288#ifdef CONFIG_ESP_MULTI_PROCESSOR_BOOT
289 /* Multi image independent boot
290 * Boot on the second processor happens before the image0 boot
291 */
292 do_boot_appcpu(IMAGE_INDEX_1, PRIMARY_SLOT);
293#endif
294
Shubham Kulkarni8787bb02021-07-20 11:46:03 +0530295 do_boot(&rsp);
Gustavo Henrique Nihei523ef3f2021-11-12 17:53:18 -0300296
Shubham Kulkarni052561d2021-07-20 11:42:44 +0530297 while(1);
298}