Softdevice disable and enable with freertos issue for radio test

Hi,

My application is written on top of freertos ble example. I need to integrate radio test example as well for certification. I am running into errors when I try to enable the ble stack after disabling it.

The flow is as follows. 

  • Send a command to start radio test.
  • disable the softdevice.
  • start a timer to enable the softdevice later.
  • start the radio test.
  • suspend the softdevice task.

When the time elapses

  • radio test cancel
  • ble init
  • resume the softdevice task.

Below is the rough code for the same.

void nrf_sdh_freertos_deinit(void)
{

     // Use the handle to suspend the task.
     if( m_softdevice_task != NULL )
     {
         vTaskSuspend( m_softdevice_task );
     }
}

void nrf_sdh_freertos_reinit(void)
{

     // Use the handle to resume the task.
     if( m_softdevice_task != NULL )
     {
        vTaskResume( m_softdevice_task );
     }


}


void command_handler(){

    if(command_received){
    
            CRITICAL_REGION_ENTER();
            
            ble_conn_params_stop();
            NRF_LOG_INFO("disabling sd %d",nrf_sdh_is_enabled());
            nrf_sdh_disable_request();
            
            start_restart_timer();
            
            memset(&m_test_config, 0, sizeof(m_test_config));
            m_test_config.type              = RX;
            m_test_config.mode              = m_config.mode;
            m_test_config.params.rx.channel = m_config.channel_start;
            m_test_config.params.rx.pattern = m_config.tx_pattern;
            radio_test_start(&m_test_config);
            CRITICAL_REGION_EXIT();
            NRF_LOG_INFO("deiniting the task");
            
            nrf_sdh_freertos_deinit();
    }

}


static void start_restart_timer(void) {
  NRF_LOG_INFO("START TIMER");
   if (pdPASS != xTimerStart(m_restart_timer, OSTIMER_WAIT_FOR_QUEUE))
    {
        APP_ERROR_HANDLER(NRF_ERROR_NO_MEM);
    }

}



static void restart_timeout_handler(TimerHandle_t xTimer)
{ 
UNUSED_PARAMETER(xTimer);
ret_code_t err_code;

  restart_count++;
  NRF_LOG_INFO("resetting count %d",restart_count);
  if(restart_count >= RESTART_TIME_IN_SEC){
    restart_count=0;
    NRF_LOG_INFO("softdevice enabling\r\n");

    radio_test_cancel();

    if(nrf_sdh_is_enabled() == false){
     
      ble_stack_init();
      gap_params_init();
      gatt_init();
      services_init();
      advertising_init();
      conn_params_init();
      peer_manager_init();
      //services_init(); uncommenting this gives NO_MEMORY error
      nrf_sdh_freertos_reinit();
      err_code = ble_advertising_start(&m_advertising, BLE_ADV_MODE_FAST);
      APP_ERROR_CHECK(err_code);
    }
    if (pdPASS != xTimerStop(m_restart_timer, OSTIMER_WAIT_FOR_QUEUE))
    {
        APP_ERROR_HANDLER(NRF_ERROR_NO_MEM);
    }


  }
}

But this gave NRF_ERROR_INTERNAL in ble_conn_params_init(). So I added the the check as below inside ble_conn_params_init()

 if(p_instance->timer_id ==NULL)
 {
 p_instance->timer_id = &m_timer_data[i];

        err_code = app_timer_create(&p_instance->timer_id,
                            APP_TIMER_MODE_SINGLE_SHOT,
                            update_timeout_handler);
        if (err_code != NRF_SUCCESS)
        {
            return NRF_ERROR_INTERNAL;
        }
    }

With this I am able to disable the softdevice by sending command and enable again after the timer elapsed. Then able to send command to disable again, but when it tries to enable the softdevice again I am getting the below error.

<error> peer_manager_gcm: Could not acquire conn_state user flags. Increase BLE_CONN_STATE_USER_FLAG_COUNT in the ble_conn_state module.
<error> peer_manager: pm_init failed because gcm_init() returned NRF_ERROR_INTERNAL.
<error> app: ERROR 3 [NRF_ERROR_INTERNAL] at C:\UH\Workspace\nRF_tina\R1_integration\projects\ultrahuman_R1_V0_0_0_17_Master_CD_w\main.c:3736
PC at: 0x000384E1

Is the flow I am doing wrong? How can I disable and enable softdevice for testing the radio ?

Thanks,

Vishnu 

Related