sd_flash_* operations no longer working after SDK(14.2) -> (15.2) and SD(5.1) -> (6.1.1) migration

Hi there,

I'm in the midst of migrating between SDK14.2->15.2, and SD 5.1->6.1

I'm calling sd_flash_write() and sd_flash_page_erase() before enabling the SoftDevice with no issue, however, once I enable the softdevice these functions return NRF_ERROR_BUSY indefinitely. This happens even though I have not started advertising. I have tried calling it 10,000 times with a delay of 1ms between tries, and still always get NRF_ERROR_BUSY.

I would prefer to use the SoftDevice directly (as opposed to Fstorage) to leverage it's async properties.

Do you know why this method used to work where now it does not? 

Attached is my sdk_config.h if that helps

Thanks,

Matthew

Parents
  • Hi,

    Do the first call to sd_flash_write()/sd_flash_page_erase() after enabling the softdevice return successfully?

    Are you processing the events from the softdevice? E.g through the Softdevice handler library, etc?

    Are you calling the functions from main context or interrupt context? Can you post a minimal code showing how we can reproduce this problem?

    I would prefer to use the SoftDevice directly (as opposed to Fstorage) to leverage it's async properties.

    Fstorage is also using the sd_flash* API in its Softdevice backend. It is not possible to write/erase the flash through NVMC peripheral when the softdevice is enabled, without using the Softdevice APIs.

    Best regards,
    Jørgen

  • Hi Jorgen,

    I think I have identified part of the issue.

    I can call many successful sd_flash* operations before enabling the SD, but but after I enable the SD, it always returns busy. However, if I do not call an sd_flash* function before enabling the SD, sd_flash* invocations return NRF_SUCCESS the first time, and NRF_BUSY thereafter.

    (I am using the Softdevice handler library by calling nrf_sdh_enable_request(), though I am not registering an nrf_soc observer.)

    Example:

      ret_code_t err_code = (ret_code_t)NRF_SUCCESS;
    
      // Initialize the SoftDevice handler module.
      err_code = (ret_code_t)nrf_sdh_enable_request();//returns NRF_SUCCESS
    
      // Fetch the start address of the application RAM.
      uint8_t const conn_cfg_tag = 1;                
      uint32_t ram_start = 0;
      err_code = (ret_code_t)nrf_sdh_ble_default_cfg_set(conn_cfg_tag, &ram_start);  
    
      // enable SoftDevice
      err_code = (ret_code_t)sd_ble_enable(&ram_start);
    
      err_code = sd_flash_page_erase(0x76);// returns NRF_SUCCESS
      
      rf_delay_ms(90); //flash operation takes maximum of 90ms
    
      err_code = sd_flash_page_erase(0x76);// returns NRF_BUSY


    Example 2:

      ret_code_t err_code = (ret_code_t)NRF_SUCCESS;
    
      // Initialize the SoftDevice handler module.
      err_code = (ret_code_t)nrf_sdh_enable_request();//returns NRF_SUCCESS
    
      // Fetch the start address of the application RAM.
      uint8_t const conn_cfg_tag = 1;                
      uint32_t ram_start = 0;
      err_code = (ret_code_t)nrf_sdh_ble_default_cfg_set(conn_cfg_tag, &ram_start);  
    
      err_code = sd_flash_page_erase(0x76);// returns NRF_SUCCESS
    
      // enable SoftDevice
      err_code = (ret_code_t)sd_ble_enable(&ram_start);
      
      rf_delay_ms(90); //flash operation takes maximum of 90ms
    
      err_code = sd_flash_page_erase(0x76);// returns NRF_BUSY

    I'm calling these functions in the main context.

    In regards to fstorage, it's my understanding that nrf_fstorage_write() enqueues a flash write operation onto the application event queue (which is eventually serviced through a call to app_sched_execute()), whereas sd_flash* directly kicks of a flash operation (blocking if SD enabled, async if not). Is this correct?

    Thanks

  • in my last paragraph, I meant to say *async if SD enabled, blocking if not*

Reply Children
No Data
Related