2020#ifdef CONFIG_NRF_MCUBOOT_BOOT_REQUEST
2121#include <bootutil/boot_request.h>
2222#endif /* CONFIG_NRF_MCUBOOT_BOOT_REQUEST */
23+ #if defined(CONFIG_FPROTECT ) && defined(CONFIG_NCS_MCUBOOT_BOOTCONF_LOCK_WRITES )
24+ #include <fprotect.h>
25+ #endif
26+
27+ #define IMAGE_TLV_INSTALLER_IMAGE 0xa0
2328
2429BOOT_LOG_MODULE_DECLARE (mcuboot );
2530
2631/* Variables passed outside of unit via poiters. */
2732static const struct flash_area * _fa_p ;
2833static struct image_header _hdr = { 0 };
2934
35+ #if defined(CONFIG_FPROTECT ) && defined(CONFIG_NCS_MCUBOOT_BOOTCONF_LOCK_WRITES )
36+ static bool boot_image_is_installer (const struct flash_area * fa_p ,
37+ const struct image_header * hdr )
38+ {
39+ struct image_tlv_iter it ;
40+ uint32_t off ;
41+ uint16_t len ;
42+ uint8_t installer = 0 ;
43+ int rc ;
44+
45+ if (hdr -> ih_protect_tlv_size == 0 ) {
46+ return false;
47+ }
48+
49+ rc = bootutil_tlv_iter_begin (& it , hdr , fa_p , IMAGE_TLV_INSTALLER_IMAGE , true);
50+ if (rc != 0 ) {
51+ return false;
52+ }
53+
54+ rc = bootutil_tlv_iter_next (& it , & off , & len , NULL );
55+ if (rc != 0 || len != sizeof (installer )) {
56+ return false;
57+ }
58+
59+ rc = LOAD_IMAGE_DATA (hdr , fa_p , off , & installer , sizeof (installer ));
60+
61+ return rc == 0 && installer == 1 ;
62+ }
63+
64+ static int protect_firmware_loader (void )
65+ {
66+ const struct flash_area * fa_p ;
67+ int rc ;
68+
69+ rc = flash_area_open (FLASH_AREA_IMAGE_SECONDARY (0 ), & fa_p );
70+ if (rc != 0 ) {
71+ return rc ;
72+ }
73+
74+ rc = fprotect_area (flash_area_get_off (fa_p ), flash_area_get_size (fa_p ));
75+ flash_area_close (fa_p );
76+
77+ return rc ;
78+ }
79+ #else
80+ #define boot_image_is_installer (_fa_p , _hdr ) false
81+ #endif
82+
3083#if defined(MCUBOOT_VALIDATE_PRIMARY_SLOT ) || defined(MCUBOOT_VALIDATE_PRIMARY_SLOT_ONCE )
3184/**
3285 * Validate hash of a primary boot image.
@@ -110,7 +163,7 @@ boot_image_validate_once(const struct flash_area *fa_p,
110163 *
111164 * @return FIH_SUCCESS on success; non-zero on failure.
112165 */
113- static fih_ret validate_image_slot (int slot , struct boot_rsp * rsp )
166+ static fih_ret validate_image_slot (int slot , struct boot_rsp * rsp , bool * is_installer )
114167{
115168 int rc = -1 ;
116169 FIH_DECLARE (fih_rc , FIH_FAILURE );
@@ -142,6 +195,7 @@ static fih_ret validate_image_slot(int slot, struct boot_rsp *rsp)
142195 rsp -> br_flash_dev_id = flash_area_get_device_id (_fa_p );
143196 rsp -> br_image_off = flash_area_get_off (_fa_p );
144197 rsp -> br_hdr = & _hdr ;
198+ * is_installer = boot_image_is_installer (_fa_p , & _hdr );
145199
146200other :
147201 flash_area_close (_fa_p );
@@ -163,6 +217,7 @@ fih_ret
163217boot_go (struct boot_rsp * rsp )
164218{
165219 bool boot_firmware_loader = false;
220+ bool booting_installer = false;
166221 FIH_DECLARE (fih_rc , FIH_FAILURE );
167222
168223 BOOT_LOG_DBG ("boot_go: firmware loader" );
@@ -194,18 +249,33 @@ boot_go(struct boot_rsp *rsp)
194249
195250 /* Check if firmware loader button is pressed. TODO: check all entrance methods */
196251 if (boot_firmware_loader == true) {
197- FIH_CALL (validate_image_slot , fih_rc , FLASH_AREA_IMAGE_SECONDARY (0 ), rsp );
252+ FIH_CALL (validate_image_slot , fih_rc , FLASH_AREA_IMAGE_SECONDARY (0 ), rsp ,
253+ & booting_installer );
198254
199255 if (FIH_EQ (fih_rc , FIH_SUCCESS )) {
256+ #if defined(CONFIG_FPROTECT ) && defined(CONFIG_NCS_MCUBOOT_BOOTCONF_LOCK_WRITES )
257+ if (protect_firmware_loader () != 0 ) {
258+ FIH_RET (FIH_FAILURE );
259+ }
260+ #endif
200261 FIH_RET (fih_rc );
201262 }
202263 }
203264
204- FIH_CALL (validate_image_slot , fih_rc , FLASH_AREA_IMAGE_PRIMARY (0 ), rsp );
265+ FIH_CALL (validate_image_slot , fih_rc , FLASH_AREA_IMAGE_PRIMARY (0 ), rsp ,
266+ & booting_installer );
205267
206268#ifdef CONFIG_BOOT_FIRMWARE_LOADER_NO_APPLICATION
207269 if (FIH_NOT_EQ (fih_rc , FIH_SUCCESS )) {
208- FIH_CALL (validate_image_slot , fih_rc , FLASH_AREA_IMAGE_SECONDARY (0 ), rsp );
270+ FIH_CALL (validate_image_slot , fih_rc , FLASH_AREA_IMAGE_SECONDARY (0 ), rsp ,
271+ & booting_installer );
272+ }
273+ #endif
274+
275+ #if defined(CONFIG_FPROTECT ) && defined(CONFIG_NCS_MCUBOOT_BOOTCONF_LOCK_WRITES )
276+ if (FIH_EQ (fih_rc , FIH_SUCCESS ) && !booting_installer &&
277+ protect_firmware_loader () != 0 ) {
278+ FIH_RET (FIH_FAILURE );
209279 }
210280#endif
211281
0 commit comments