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

What have changed on multiprotocol/ble_app_gzll example between SDK14.0 and SDK14.2?

FormerMember
FormerMember

Hello, I use the pca10040 and the problem is in 14.0 eaxmple,when I push the button switch the protocol mode like : ble->gzll->ble and then I find the example loop into this function:

static void expired_timers_handler(uint32_t         ticks_elapsed,
                                   uint32_t         ticks_previous,
                                   timer_node_t **  p_restart_list_head)
{
    uint32_t ticks_expired = 0;

while (mp_timer_id_head != NULL)
{
    timer_node_t * p_timer;
    timer_node_t * p_timer_expired;

    // Auto variable for current timer node.
    p_timer = mp_timer_id_head;

    // Do nothing if timer did not expire
    if (ticks_elapsed < p_timer->ticks_to_expire)
    {
        p_timer->ticks_to_expire -= ticks_elapsed;
        break;
    }

    // Decrement ticks_elapsed and collect expired ticks.
    ticks_elapsed -= p_timer->ticks_to_expire;
    ticks_expired += p_timer->ticks_to_expire;

    // Timer expired, set ticks_to_expire zero.
    p_timer->ticks_to_expire = 0;

    // Remove the expired timer from head.
    p_timer_expired  = mp_timer_id_head;
    mp_timer_id_head = p_timer->next;

    // Timer will be restarted if periodic.
    if (p_timer->ticks_periodic_interval != 0)
    {
        p_timer->ticks_at_start       = (ticks_previous + ticks_expired) & MAX_RTC_COUNTER_VAL;
        p_timer->ticks_first_interval = p_timer->ticks_periodic_interval;
        p_timer->next                 = *p_restart_list_head;
        *p_restart_list_head          = p_timer_expired;
    }
    }
}

But when I use the example in the SDK14.2 it never happens. All I to do is just run the two examples without changing anything.And I just want to know why in sdk14.2 the problem has solved. Thank you.

  • Could you describe the issue you have in SDK v14.0 in more detail ? What exactly is the behavior when the error happens ? and how to reproduce the error ? I don't think getting inside expired_timers_handler() is a bug.

  • FormerMember
    0 FormerMember

    Hi,Hung Bui. There is no error code reported from the logging.And the behavior of the error is that the mp_timer_id_head value condition never be NULL and the break point at the end of the function will never reached.The comment bellow has the debug info about this value. To reproduce the error is only switching the mode from ble to gazell and gazell to ble for one or two times and the problem is always ocurred by switching gazell mode to ble mode.

  • FormerMember
    0 FormerMember

    Hi, Hung Bui Here is the debug info about the mp_timer_id_headimage description.

    Fortunately I have found the key code between SDK14.0 and SDK14.2. In SDK 14.0 components\softdevice\common\nrf_sdh.c, I found the function nrf_sdh_enable_request(void) like:

            ret_code_t nrf_sdh_enable_request(void)
        {
            ret_code_t ret_code;
        
            if (m_nrf_sdh_enabled)
            {
                return NRF_ERROR_INVALID_STATE;
            }
        
            m_nrf_sdh_continue = true;
        
            // Notify observers about SoftDevice enable request.
            if (sdh_request_observer_notify(NRF_SDH_EVT_ENABLE_REQUEST) == NRF_ERROR_BUSY)
            {
                // Enable process was stopped.
                return NRF_SUCCESS;
            }
        
            // Notify observers about starting SoftDevice enable process.
            sdh_state_observer_notify(NRF_SDH_EVT_STATE_ENABLE_PREPARE);
        
            nrf_clock_lf_cfg_t const clock_lf_cfg =
            {
                .source        = NRF_SDH_CLOCK_LF_SRC,
                .rc_ctiv       = NRF_SDH_CLOCK_LF_RC_CTIV,
                .rc_temp_ctiv  = NRF_SDH_CLOCK_LF_RC_TEMP_CTIV,
            #ifdef S132
                .accuracy      = NRF_SDH_CLOCK_LF_XTAL_ACCURACY
            #else
                .xtal_accuracy = NRF_SDH_CLOCK_LF_XTAL_ACCURACY
            #endif
            };
        
            #ifdef ANT_LICENSE_KEY
                ret_code = sd_softdevice_enable(&clock_lf_cfg, app_error_fault_handler, ANT_LICENSE_KEY);
            #else
                ret_code = sd_softdevice_enable(&clock_lf_cfg, app_error_fault_handler);
            #endif
        
            if (ret_code != NRF_SUCCESS)
            {
                return ret_code;
            }
    
        m_nrf_sdh_enabled   = true;
        m_nrf_sdh_continue  = false;
        m_nrf_sdh_suspended = false;
    
        // Enable BLE event interrupt (interrupt priority has already been set by the stack).
    #ifdef SOFTDEVICE_PRESENT
        ret_code = sd_nvic_EnableIRQ((IRQn_Type)SD_EVT_IRQn);
        if (ret_code != NRF_SUCCESS)
        {
            return ret_code;
        }
    #else
        //In case of serialization, NVIC must be accessed directly.
        NVIC_EnableIRQ(SD_EVT_IRQn);
    #endif
    
        // Notify observers about a finished SoftDevice enable process.
        sdh_state_observer_notify(NRF_SDH_EVT_STATE_ENABLED);
    
        return NRF_SUCCESS;
    }
    

    And in SDK14.2 components\softdevice\common\nrf_sdh.c, the function like:

    ret_code_t nrf_sdh_enable_request(void)
    {
        ret_code_t ret_code;
    
        if (m_nrf_sdh_enabled)
        {
            return NRF_ERROR_INVALID_STATE;
        }
    
        m_nrf_sdh_continue = true;
    
        // Notify observers about SoftDevice enable request.
        if (sdh_request_observer_notify(NRF_SDH_EVT_ENABLE_REQUEST) == NRF_ERROR_BUSY)
        {
            // Enable process was stopped.
            return NRF_SUCCESS;
        }
    
        // Notify observers about starting SoftDevice enable process.
        sdh_state_observer_notify(NRF_SDH_EVT_STATE_ENABLE_PREPARE);
    
        nrf_clock_lf_cfg_t const clock_lf_cfg =
        {
            .source        = NRF_SDH_CLOCK_LF_SRC,
            .rc_ctiv       = NRF_SDH_CLOCK_LF_RC_CTIV,
            .rc_temp_ctiv  = NRF_SDH_CLOCK_LF_RC_TEMP_CTIV,
        #ifdef S140
            .xtal_accuracy = NRF_SDH_CLOCK_LF_XTAL_ACCURACY
        #else
            .accuracy      = NRF_SDH_CLOCK_LF_XTAL_ACCURACY
        #endif
        };
    
        #ifdef ANT_LICENSE_KEY
            ret_code = sd_softdevice_enable(&clock_lf_cfg, app_error_fault_handler, ANT_LICENSE_KEY);
        #else
            ret_code = sd_softdevice_enable(&clock_lf_cfg, app_error_fault_handler);
        #endif
    
        if (ret_code != NRF_SUCCESS)
        {
            return ret_code;
        }
    
        m_nrf_sdh_enabled   = true;
        m_nrf_sdh_continue  = false;
        m_nrf_sdh_suspended = false;
    
    #ifndef S140
        // Set the interrupt priority after enabling the SoftDevice, since
        // sd_softdevice_enable() sets the SoftDevice interrupt priority.
        swi_interrupt_priority_workaround();
    #endif
    
        // Enable event interrupt.
        // Interrupt priority has already been set by the stack.
        softdevices_evt_irq_enable();
    
        // Notify observers about a finished SoftDevice enable process.
        sdh_state_observer_notify(NRF_SDH_EVT_STATE_ENABLED);
    
        return NRF_SUCCESS;
    }
    

    Funtion swi_interrupt_priority_workaround() has fixed this problem:).

  • Thanks Gxbicq for pointing out. It was the changed in SDK v5.0 to set default priority for the interrupts to 6 caused the issue. I will report this in the known issues for SDK v14 list.

Related