Beware that this post is related to an SDK in maintenance mode
More Info: Consider nRF Connect SDK for new designs
This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Why Isn't There Support For Validating The Secure Bootloader On Boot?

While the nRF5 SDK offers great support for validating the SoftDevice and application firmware in internal NOR Flash on every boot, it looks like that's not the case for the secure bootloader, despite the fact that it looks like support for this basically exists.

What I see is that in version 6.1.0 of nrfutil, if I generate a DFU package containing both a SoftDevice and a secure bootloader, and with sd-boot-validation set to VALIDATE_ECDSA_P256_SHA256, the boot validation structure for the SD is set to VALIDATE_ECDSA_P256_SHA256 as expected, but the boot validation structure for the secure bootloader itself is set as VALIDATE_CRC, and that structure includes what looks like a valid 32-bit CRC for the secure bootloader.

During the application of the DFU package, postvalidate_sd_bl() in nrf_dfu_validation.c calls boot_validation_extract() for the secure bootloader, in order to validate the unzipped copy of the secure bootloader that was temporarily stored in NOR Flash, before it is written to its final location in high NOR Flash. In order to perform that validation, boot_validation_extract() is using the CRC for the secure bootloader provided in the DFU package; this succeeds but then displays a warning that says "Boot validation of bootloader is not supported and will be ignored".

However, it appears that the VALIDATE_CRC type and the stored CRC for the secure bootloader are both actually stored in the  s_dfu_settings.boot_validation_bootloader structure that is written to NOR Flash, and so could be used by the bootloader to validate itself on future boots, even though that's not happening today. In other words, it seems like it should be trivial to modify app_is_valid() in nrf_bootloader.c to add a call to boot_validate() for the secure bootloader alongside those that already exist for the application and SD.

Based on this research, I have three questions:

1) Why isn't Nordic already supporting validation of the secure bootloader on each boot. It seems like you walked right up to edge of supporting the validation of the secure bootloader's image in NOR Flash on each boot, but then opted not to support it. I'm assuming you had a good reason for making that decision. What was it? Is there a reason that using the data already stored from the DFU package to validate the secure bootloader on each boot is not a good idea.

2) Since clearly the secure bootloader's image stored temporarily in NOR Flash is being validated using its CRC before being copied into its permanent position, is there a reason that the nrfutil utility didn't provide support for using VALIDATE_ECDSA_P256_SHA256 to validate the secure bootloader in this case?

3) I want to verify that my understanding regarding the utilization of internal NOR Flash during DFU is correct. If I am applying a DFU package containing all three elements (app, SD, and secure bootloader), it looks like the following approach is taken.

  • The entire DFU package is written to an unused portion of NOR Flash (I"m assuming this is written to high NOR Flash, just below the secure bootloader)
  • The current application firmware is erased.
  • The SD and secure bootloader images are incrementally unzipped and temporarily written to the where the application firmware used to be
  • The SD and secure bootloader images are validated in their temporary locations
  • The SD and secure bootloader images are written to their permanent locations in low NOR Flash
  • The system is reset
  • The application firmware is incrementally unzipped and written to its permanent location
  • The application firmware is validated in its permanent location
Parents
  • Hi,

    1) Why isn't Nordic already supporting validation of the secure bootloader on each boot. It seems like you walked right up to edge of supporting the validation of the secure bootloader's image in NOR Flash on each boot, but then opted not to support it. I'm assuming you had a good reason for making that decision. What was it? Is there a reason that using the data already stored from the DFU package to validate the secure bootloader on each boot is not a good idea.

    I'ts a bit complicated, but basically we are already confident that the bootloader, if present, can be trusted. We achieve that by securing the new version of everything you put on the device (through signed DFU), and any update always happens after a "root of trust reset". MBR and Bootloader are both protected (ACL/BROT). Failed bootloader DFU will leave the old bootloader intact. The last step of bootloader DFU, copying the new bootloader to its final location, is restarted by the MBR if interrupted (e.g. power loss), ensuring that the copy will always take place in its entirety.

    Checking the bootloader on boot could reveal broken flash, but in that case the device is already broken. Another potential issue is losing the (private) DFU signing key to an attacker, but boot validation cannot protect against that. You should always keep the private key secret, and never put it on a device that an attacker has physical access to. The firmware validation is designed using asymmetric cryptography for this exact reason.

    I recommend having a look at Secure boot and firmware updates, for more information.

    2) Since clearly the secure bootloader's image stored temporarily in NOR Flash is being validated using its CRC before being copied into its permanent position, is there a reason that the nrfutil utility didn't provide support for using VALIDATE_ECDSA_P256_SHA256 to validate the secure bootloader in this case?

    I think  has already given a good answer to this one, combined with my answers to 1) above.

    3) I want to verify that my understanding regarding the utilization of internal NOR Flash during DFU is correct. If I am applying a DFU package containing all three elements (app, SD, and secure bootloader), it looks like the following approach is taken.

    Almost, although not quite. Have a look at Device Firmware Update process, and the sub-pages. These are the main corrections:

    • The zip is not copied directly to the device, it is copied in unzipped form, and more specifically in the form of an init packet (meta data) and a binary blob (the actual firmware).
    • What happens to the original application depends on factors such as whether you do dual-bank or single-bank DFU. For SD + BL + APP updates, it is actually two updates after each other (first SD + BL, then APP).
    • Copying of the BL is done from the master boot record (MBR).
    • When the bootloader checks the application on every boot, it is in order to decide whether to jump to the application (successful check) or enter DFU mode (failing check). This is needed because the application cannot always be trusted to be valid and/or present. For instance it gets overwritten during single-bank DFU.

    Regards,
    Terje

Reply
  • Hi,

    1) Why isn't Nordic already supporting validation of the secure bootloader on each boot. It seems like you walked right up to edge of supporting the validation of the secure bootloader's image in NOR Flash on each boot, but then opted not to support it. I'm assuming you had a good reason for making that decision. What was it? Is there a reason that using the data already stored from the DFU package to validate the secure bootloader on each boot is not a good idea.

    I'ts a bit complicated, but basically we are already confident that the bootloader, if present, can be trusted. We achieve that by securing the new version of everything you put on the device (through signed DFU), and any update always happens after a "root of trust reset". MBR and Bootloader are both protected (ACL/BROT). Failed bootloader DFU will leave the old bootloader intact. The last step of bootloader DFU, copying the new bootloader to its final location, is restarted by the MBR if interrupted (e.g. power loss), ensuring that the copy will always take place in its entirety.

    Checking the bootloader on boot could reveal broken flash, but in that case the device is already broken. Another potential issue is losing the (private) DFU signing key to an attacker, but boot validation cannot protect against that. You should always keep the private key secret, and never put it on a device that an attacker has physical access to. The firmware validation is designed using asymmetric cryptography for this exact reason.

    I recommend having a look at Secure boot and firmware updates, for more information.

    2) Since clearly the secure bootloader's image stored temporarily in NOR Flash is being validated using its CRC before being copied into its permanent position, is there a reason that the nrfutil utility didn't provide support for using VALIDATE_ECDSA_P256_SHA256 to validate the secure bootloader in this case?

    I think  has already given a good answer to this one, combined with my answers to 1) above.

    3) I want to verify that my understanding regarding the utilization of internal NOR Flash during DFU is correct. If I am applying a DFU package containing all three elements (app, SD, and secure bootloader), it looks like the following approach is taken.

    Almost, although not quite. Have a look at Device Firmware Update process, and the sub-pages. These are the main corrections:

    • The zip is not copied directly to the device, it is copied in unzipped form, and more specifically in the form of an init packet (meta data) and a binary blob (the actual firmware).
    • What happens to the original application depends on factors such as whether you do dual-bank or single-bank DFU. For SD + BL + APP updates, it is actually two updates after each other (first SD + BL, then APP).
    • Copying of the BL is done from the master boot record (MBR).
    • When the bootloader checks the application on every boot, it is in order to decide whether to jump to the application (successful check) or enter DFU mode (failing check). This is needed because the application cannot always be trusted to be valid and/or present. For instance it gets overwritten during single-bank DFU.

    Regards,
    Terje

Children
No Data
Related