This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

Information regarding BLE DFU and a mesh application

Hi, I would like to share some valuable information regarding the BLE DFU (secure bootloader) and a MESH application which uses persistent storage for provisioning data. I do see there are quite a few topics on it in the devzone. There is already a comprehensive step by step guide on BLE DFU:

https://devzone.nordicsemi.com/nordic/nordic-blog/b/blog/posts/getting-started-with-nordics-secure-dfu-bootloader

Although this guide helped a lot, I still could not get my application to work with a bootloader. Obviously because the setup is different as well. 

Setup:

  1. SDK V15.3
  2. SDK MESH V3.10
  3. NRF52840 DK
  4. SEGGER Embedded Studio V4.12
  5. Softdevice S140 V6.1.1
  6. PERSISTENT STORAGE ENABLED (#define PERSISTENT_STORAGE 1 in sdk_config.h) 

Information: MBR, UICR, Soft device
As far as my knowledge goes, when reset, the MBR (Master Boot Record) will read the UICR BOOTLOADER address. In the SDK this is the address of NRF_UICR->NRFFW[0]. If there is something in that register, the reset handler of the bootloader will be called. If there is nothing (0xFFFFFFFF for erased flash) the soft device reset handler is called which runs the application (if there is one).

Issue 1: Bootloader settings incorrect flash placement
When you create the bootloader settings (.hex file), the guide states to run the following command:
nrfutil settings generate --family NRF52 --application yourApplication.hex --application-version 0 --bootloader-version 0 --bl-settings-version 1 bootloader_setting.hex
This is not incorrect, but it is not correct for the NRF52840

Navigating to the nrfutils directory and file:
C:\Python27\Lib\site-packages\nordicsemi\dfu\bl_dfu_sett.py
This is where nrfutils decide where to place the bootloader settings in flash. Note that for --family NRF52 the settings will be placed in 0x0007F000 (line 106). For --family NRF52840 the settings are placed in 0x000FF000.

Looking at the secure bootloader flash_placement.xml file:
<MemorySegment name="bootloader_settings_page" start="0x000FF000" size="0x1000">

The settings page is read from 0x000FF000. So when generating the bootloader settings for the NRF52840, instead of:
nrfutil settings generate --family NRF52 --application yourApplication.hex --application-version 0 --bootloader-version 0 --bl-settings-version 1 bootloader_setting.hex

Use:
nrfutil settings generate --family NRF52840 --application yourApplication.hex --application-version 0 --bootloader-version 0 --bl-settings-version 1 bootloader_setting.hex

This will place the bootloader settings in the correct flash address.


The bootloader_setting.hex file can be added to nRF Connect to see the flash placement of the file. Also, you can run the secure bootloader debug version to get an output log. The log will tell you if a valid application was found or not. That should sort out the bootloader settings issue.

Issue 2: BLE Secure bootloader causes mesh application to hang
After creating the correct bootloader settings (issue mentioned above), my application was detected and executed. But the application hung up.

HEX files present on the device are:
bootloader.hex, bootloader_settings.hex, s140_nrf52_6.1.1_softdevice.hex, application.hex


The problem occurred can be explained by navigating to:
mesh_stack_init()->nrf_mesh_init()->mesh_config_init()->mesh_config_backend_init()->mesh_config_backend_glue_init()->flash_manager_init()->flash_manager_defrag_init().


In flash_manager_defrag.c line 598 if (BOOTLOADERADDR()... the application reads the NRF_UICR->NRFFW[0] register. Even with the bootloader present in flash, this kept returning 0xFFFFFFFF. This results in the wrong location of mp_recovery_area which causes an ASSERT further down the call stack.

Solution:
Read back the register with nrfjprog:
nrfjprog --memrd 0x10001014

The address returns 0xFFFFFFFF


Now write to that register with nrfjprog:
nrfjprog -f nrf52 --memwr 0x10001014 --val 0xf8000
Note that the value 0xf8000 is going to depend on FLASH_START in the SEGGER settings in section placement macros.

Read back the register and verify that the value is changed:
nrfjprog --memrd 0x10001014 should return 0xf8000 (or whatever value you have written).

It is important to note that this will only have an effect once the device is power cycled. Power cycle the device. The application was now detected and executed perfectly. Also, the correct bootloader address was set.

Now I understand that you can do this direct write to the address in your application, it does feel like a hack though. The secure ble dfu already performs that write. But when reading back that address in a debug session or nrfjprog, it is still 0xFFFFFFFF. Not sure why this is happening though. It is happening with the debug and the normal version.

Hope the information is useful:)

Regards

Chris

  • Hi Chris, 

    Thanks for your very useful information. I will update the blog to cover information for nRF52840. 

    Regarding issue #2. I think the main problem is that nRF Mesh SDK v3.1 is not compatible with SDK v15.3 . It should be used with SDK v15.2 

    One of the main difference between SDK v15.2 and SDK v15.3 regarding the bootloader is the change of where the bootloader address is configured. Please have a look at my post here.

    In the new Mesh SDK that we releasing shortly, this should be solved. 

  • I have done all my development so far with mesh sdk 3.10 and sdk 15.30. How much of a problem is this. Is it definitely required to downgrade to 15.20? If yes, is there some guide I can follow? Also, do you know when the new mesh sdk will be released? 

  • I did the change from 15.3 to 15.2, no guide required. Only required for major migration. Well done Nordic for keeping everything the same! Literally just changed the SDK root.

    I will just retest all my software to make sure everything is working fine. Only thing that seems to be not working are the Leds. Probably something simple. Also I have seen that the mesh application gets stuck a lot of times during provisioning. It gets stuck at "sending composition data get". But this is not the place to discuss it, I will open a ticket for that.

    Thanks for making me aware of the compatibility:) 

  • I don't think you need to downgrade to SDK v15.2. It was just that SDK v15.2 was the latest when we released the Mesh SDK v3.1.

    I'm not sure on the exact date of Mesh SDK v3.2 but it should be out in 1-2 weeks. 

Related