I'm trying to create a method so a users can initiate an OTA update from a paired device. To that end I've written something which is supposed to invalidate the data at the BOOTLOADER_SETTINGS_ADDRESS to invalidate the current app and then call a system reset to run through the bootloader. Once working I will call this routine (start_bootloader()) on a given event from the paired device.
My problem is I can't understand pstorage and how to use it to invalidate the data at the BOOTLOADER_SETTINGS_ADDRESS. In looking through some examples (in the bootloader code for example, which most of the following is from) I can't see how the code actually specifies the BOOTLOADER_SETTINGS_ADDRESS as where to write the data. I see how it gets the data from that address.
The code below does not throw any errors it just does nothing. When I break at the sd_nvic_SystemReset(); call no memory locations have been affected and the app just restarts.
Note that I do NOT have a bootloader installed. I have set up to flash a device with softdevice, application and bootloader, setting the BOOTLOADER_SETTINGS_ADDRESS correctly and the BOOT_ADDR correctly so that everything works (i.e. it starts up in the application). If a corrupt the data used to flash the BOOTLOADER_SETTINGS_ADDRESS it goes to the bootloader and I can OTA the applications.
So what I'm asking is what am I doing wrong with pstorage below so that it is NOT changing the BOOTLOADER_SETTINGS_ADDRESS.
typedef enum
{
BOOTLOADER_UPDATING,
BOOTLOADER_SETTINGS_SAVING,
BOOTLOADER_COMPLETE,
BOOTLOADER_TIMEOUT,
BOOTLOADER_RESET,
} bootloader_status_t;
static pstorage_handle_t m_bootsettings_handle; /**< Pstorage handle to use for registration and identifying the bootloader module on subsequent calls to the pstorage module for load and store of bootloader setting in flash. */
static bootloader_status_t m_update_status; /**< Current update status for the bootloader module to ensure correct behaviour when updating settings and when update completes. */
static void pstorage_callback_handler(pstorage_handle_t * handle, uint8_t op_code, uint32_t result, uint8_t * p_data, uint32_t data_len)
{
// Do Nothing For Now
APP_ERROR_CHECK(result);
}
/*@brief Function for access to bootloader setting */
void bootloader_util_settings_get(const bootloader_settings_t** pp_bootloader_settings)
{
// Read only pointer to bootloader settings in flash.
*pp_bootloader_settings = (bootloader_settings_t*)BOOTLOADER_SETTINGS_ADDRESS;
}
void bootloader_settings_save(bootloader_settings_t * p_settings)
{
uint32_t err_code = pstorage_clear(&m_bootsettings_handle, sizeof(bootloader_settings_t));
APP_ERROR_CHECK(err_code);
err_code = pstorage_store(&m_bootsettings_handle,
(uint8_t *)p_settings,
sizeof(bootloader_settings_t),
0);
APP_ERROR_CHECK(err_code);
}
void start_bootloader()
{
uint32_t err_code = NRF_SUCCESS;
pstorage_module_param_t storage_params;
// sd_softdevice_disable();
storage_params.cb = pstorage_callback_handler;
storage_params.block_size = sizeof(bootloader_settings_t);
storage_params.block_count = 1;
err_code = pstorage_init();
if (err_code != NRF_SUCCESS)
{
return err_code;
}
err_code = pstorage_register(&storage_params, &m_bootsettings_handle);
if (err_code != NRF_SUCCESS)
{
return err_code;
}
// m_bootsettings_handle.block_id = BOOTLOADER_SETTINGS_ADDRESS;
static bootloader_settings_t settings;
const bootloader_settings_t * p_bootloader_settings;
bootloader_util_settings_get(&p_bootloader_settings);
settings.bank_0_crc = p_bootloader_settings->bank_0_crc;
settings.bank_0_size = p_bootloader_settings->bank_0_size;
settings.bank_0 = BANK_VALID_APP;
settings.bank_1 = p_bootloader_settings->bank_1;
bootloader_settings_save(&settings);
sd_nvic_SystemReset();
}