1 /*
2  * SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 #pragma once
7 
8 #include <stdbool.h>
9 #include <esp_err.h>
10 #include "esp_flash_partitions.h"
11 #include "esp_app_format.h"
12 #include "esp_assert.h"
13 
14 #ifdef __cplusplus
15 extern "C" {
16 #endif
17 
18 #define ESP_ERR_IMAGE_BASE       0x2000
19 #define ESP_ERR_IMAGE_FLASH_FAIL (ESP_ERR_IMAGE_BASE + 1)
20 #define ESP_ERR_IMAGE_INVALID    (ESP_ERR_IMAGE_BASE + 2)
21 
22 /* Support for app/bootloader image parsing
23    Can be compiled as part of app or bootloader code.
24 */
25 
26 #define ESP_IMAGE_HASH_LEN 32 /* Length of the appended SHA-256 digest */
27 
28 /* Structure to hold on-flash image metadata */
29 typedef struct {
30   uint32_t start_addr;   /* Start address of image */
31   esp_image_header_t image; /* Header for entire image */
32   esp_image_segment_header_t segments[ESP_IMAGE_MAX_SEGMENTS]; /* Per-segment header data */
33   uint32_t segment_data[ESP_IMAGE_MAX_SEGMENTS]; /* Data offsets for each segment */
34   uint32_t image_len; /* Length of image on flash, in bytes */
35   uint8_t image_digest[32]; /* appended SHA-256 digest */
36   uint32_t secure_version; /* secure version for anti-rollback, it is covered by sha256 (set if CONFIG_BOOTLOADER_APP_ANTI_ROLLBACK=y) */
37 } esp_image_metadata_t;
38 
39 typedef enum {
40     ESP_IMAGE_VERIFY,            /* Verify image contents, not load to memory, load metadata. Print errors. */
41     ESP_IMAGE_VERIFY_SILENT,     /* Verify image contents, not load to memory, load metadata. Don't print errors. */
42 #ifdef BOOTLOADER_BUILD
43     ESP_IMAGE_LOAD,              /* Verify image contents, load to memory, load metadata. Print errors. */
44     ESP_IMAGE_LOAD_NO_VALIDATE,  /* Not verify image contents, load to memory, load metadata. Print errors. */
45 #endif
46 } esp_image_load_mode_t;
47 
48 typedef struct {
49     esp_partition_pos_t partition;  /*!< Partition of application which worked before goes to the deep sleep. */
50     uint16_t reboot_counter;        /*!< Reboot counter. Reset only when power is off. */
51     union {
52         struct {
53             uint8_t factory_reset_state         : 1;  /* True when Factory reset has occurred */
54             uint8_t reserve                     : 7;  /* Reserve */
55         };
56         uint8_t val;
57     } flags;
58     uint8_t reserve;                /*!< Reserve */
59 #ifdef CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC
60     uint8_t custom[CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC_SIZE]; /*!< Reserve for custom propose */
61 #endif
62     uint32_t crc;                   /*!< Check sum crc32 */
63 } rtc_retain_mem_t;
64 
65 
66 ESP_STATIC_ASSERT(offsetof(rtc_retain_mem_t, crc) == sizeof(rtc_retain_mem_t) - sizeof(uint32_t), "CRC field must be the last field of rtc_retain_mem_t structure");
67 
68 #ifdef CONFIG_BOOTLOADER_RESERVE_RTC_MEM
69 
70 #ifdef CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC
71 ESP_STATIC_ASSERT(CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC_SIZE % 4 == 0, "CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC_SIZE must be a multiple of 4 bytes");
72 /* The custom field must be the penultimate field */
73 ESP_STATIC_ASSERT(offsetof(rtc_retain_mem_t, custom) == sizeof(rtc_retain_mem_t) - sizeof(uint32_t) - CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC_SIZE,
74                "custom field in rtc_retain_mem_t structure must be the field before the CRC one");
75 #endif
76 
77 ESP_STATIC_ASSERT(CONFIG_BOOTLOADER_RESERVE_RTC_SIZE % 4 == 0, "CONFIG_BOOTLOADER_RESERVE_RTC_SIZE must be a multiple of 4 bytes");
78 
79 #ifdef CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC
80 #define ESP_BOOTLOADER_RESERVE_RTC (CONFIG_BOOTLOADER_RESERVE_RTC_SIZE + CONFIG_BOOTLOADER_CUSTOM_RESERVE_RTC_SIZE)
81 #else
82 #define ESP_BOOTLOADER_RESERVE_RTC (CONFIG_BOOTLOADER_RESERVE_RTC_SIZE)
83 #endif
84 
85 ESP_STATIC_ASSERT(sizeof(rtc_retain_mem_t) <= ESP_BOOTLOADER_RESERVE_RTC, "Reserved RTC area must exceed size of rtc_retain_mem_t");
86 #endif // CONFIG_BOOTLOADER_RESERVE_RTC_MEM
87 
88 /**
89  * @brief Verify an app image.
90  *
91  * If encryption is enabled, data will be transparently decrypted.
92  *
93  * @param mode Mode of operation (verify, silent verify, or load).
94  * @param part Partition to load the app from.
95  * @param[inout] data Pointer to the image metadata structure which is be filled in by this function.
96  *                    'start_addr' member should be set (to the start address of the image.)
97  *                    Other fields will all be initialised by this function.
98  *
99  * Image validation checks:
100  * - Magic byte.
101  * - Partition smaller than 16MB.
102  * - All segments & image fit in partition.
103  * - 8 bit image checksum is valid.
104  * - SHA-256 of image is valid (if image has this appended).
105  * - (Signature) if signature verification is enabled.
106  *
107  * @return
108  * - ESP_OK if verify or load was successful
109  * - ESP_ERR_IMAGE_FLASH_FAIL if a SPI flash error occurs
110  * - ESP_ERR_IMAGE_INVALID if the image appears invalid.
111  * - ESP_ERR_INVALID_ARG if the partition or data pointers are invalid.
112  */
113 esp_err_t esp_image_verify(esp_image_load_mode_t mode, const esp_partition_pos_t *part, esp_image_metadata_t *data);
114 
115 /**
116  * @brief Get metadata of app
117  *
118  * If encryption is enabled, data will be transparently decrypted.
119  *
120  * @param part Partition to load the app from.
121  * @param[out] metadata Pointer to the image metadata structure which is be filled in by this function.
122  *                      Fields will all be initialised by this function.
123  *
124  * @return
125  * - ESP_OK if filling of metadata was successful
126  */
127 esp_err_t esp_image_get_metadata(const esp_partition_pos_t *part, esp_image_metadata_t *metadata);
128 
129 /**
130  * @brief Verify and load an app image (available only in space of bootloader).
131  *
132  * If encryption is enabled, data will be transparently decrypted.
133  *
134  * @param part Partition to load the app from.
135  * @param[inout] data Pointer to the image metadata structure which is be filled in by this function.
136  *                    'start_addr' member should be set (to the start address of the image.)
137  *                    Other fields will all be initialised by this function.
138  *
139  * Image validation checks:
140  * - Magic byte.
141  * - Partition smaller than 16MB.
142  * - All segments & image fit in partition.
143  * - 8 bit image checksum is valid.
144  * - SHA-256 of image is valid (if image has this appended).
145  * - (Signature) if signature verification is enabled.
146  *
147  * @return
148  * - ESP_OK if verify or load was successful
149  * - ESP_ERR_IMAGE_FLASH_FAIL if a SPI flash error occurs
150  * - ESP_ERR_IMAGE_INVALID if the image appears invalid.
151  * - ESP_ERR_INVALID_ARG if the partition or data pointers are invalid.
152  */
153 esp_err_t bootloader_load_image(const esp_partition_pos_t *part, esp_image_metadata_t *data);
154 
155 /**
156  * @brief Load an app image without verification (available only in space of bootloader).
157  *
158  * If encryption is enabled, data will be transparently decrypted.
159  *
160  * @param part Partition to load the app from.
161  * @param[inout] data Pointer to the image metadata structure which is be filled in by this function.
162  *                    'start_addr' member should be set (to the start address of the image.)
163  *                    Other fields will all be initialised by this function.
164  *
165  * @return
166  * - ESP_OK if verify or load was successful
167  * - ESP_ERR_IMAGE_FLASH_FAIL if a SPI flash error occurs
168  * - ESP_ERR_IMAGE_INVALID if the image appears invalid.
169  * - ESP_ERR_INVALID_ARG if the partition or data pointers are invalid.
170  */
171 esp_err_t bootloader_load_image_no_verify(const esp_partition_pos_t *part, esp_image_metadata_t *data);
172 
173 /**
174  * @brief Verify the bootloader image.
175  *
176  * @param[out] If result is ESP_OK and this pointer is non-NULL, it
177  * will be set to the length of the bootloader image.
178  *
179  * @return As per esp_image_load_metadata().
180  */
181 esp_err_t esp_image_verify_bootloader(uint32_t *length);
182 
183 /**
184  * @brief Verify the bootloader image.
185  *
186  * @param[out] Metadata for the image. Only valid if result is ESP_OK.
187  *
188  * @return As per esp_image_load_metadata().
189  */
190 esp_err_t esp_image_verify_bootloader_data(esp_image_metadata_t *data);
191 
192 /**
193  * @brief Get the flash size of the image
194  *
195  * @param app_flash_size The value configured in the image header
196  * @return Actual size, in bytes.
197  */
198 int esp_image_get_flash_size(esp_image_flash_size_t app_flash_size);
199 
200 
201 typedef struct {
202     uint32_t drom_addr;
203     uint32_t drom_load_addr;
204     uint32_t drom_size;
205     uint32_t irom_addr;
206     uint32_t irom_load_addr;
207     uint32_t irom_size;
208 } esp_image_flash_mapping_t;
209 
210 #ifdef __cplusplus
211 }
212 #endif
213