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

Instrumenting FreeRTOS 10 from SDK15.3 to support Segger SystemView v3.10

Hi,

I am trying to evaluate the nrf52840. I am following the instruction to instrument the FreeRTOS from the Nordic SDK15.3.  I managed to follow most of the instructions.  The only step I am having a hard time is instrumenting the ARM-CM4F/port.c.  The problem is xPortSysTickHandler() does not match the patch file. 

My setup includes:

  • nrf52840-DK
  • SDK15.3
  • Segger SystemView v3.10

Below is the patch instruction:

    diff -rupN org/Source/portable/GCC/ARM_CM4F/port.c new/Source/portable/GCC/ARM_CM4F/port.c
    --- org/Source/portable/GCC/ARM_CM4F/port.c 2017-11-28 13:48:34.000000000 -0800
    +++ new/Source/portable/GCC/ARM_CM4F/port.c 2017-12-11 01:16:01.771230000 -0800
    @@ -493,14 +493,20 @@ void xPortSysTickHandler( void )
        save and then restore the interrupt mask value as its value is already
        known. */
        portDISABLE_INTERRUPTS();
    + traceISR_ENTER();
        {
            /* Increment the RTOS tick. */
            if( xTaskIncrementTick() != pdFALSE )
            {
    +            traceISR_EXIT_TO_SCHEDULER();
                /* A context switch is required. Context switching is performed in
                the PendSV interrupt. Pend the PendSV interrupt. */
                portNVIC_INT_CTRL_REG = portNVIC_PENDSVSET_BIT;
            }
    +        else
    +        {
    +             traceISR_EXIT();
    +        }
        }
        portENABLE_INTERRUPTS();
    }

Below is the freertos.portable.CMSIS.nrf52/port_cmsis_systick.c, xPortSysTickHandler() from the SDK15.3

    void xPortSysTickHandler( void )
    {
    #if configUSE_TICKLESS_IDLE == 1
        nrf_rtc_event_clear(portNRF_RTC_REG, NRF_RTC_EVENT_COMPARE_0);
    #endif

    BaseType_t switch_req = pdFALSE;
    uint32_t isrstate = portSET_INTERRUPT_MASK_FROM_ISR();

    uint32_t systick_counter = nrf_rtc_counter_get(portNRF_RTC_REG);
    nrf_rtc_event_clear(portNRF_RTC_REG, NRF_RTC_EVENT_TICK);

    if (configUSE_DISABLE_TICK_AUTO_CORRECTION_DEBUG == 0)
    {
        /* check FreeRTOSConfig.h file for more details on configUSE_DISABLE_TICK_AUTO_CORRECTION_DEBUG */
        TickType_t diff;
        diff = (systick_counter - xTaskGetTickCount()) & portNRF_RTC_MAXTICKS;

        /* At most 1 step if scheduler is suspended - the xTaskIncrementTick
        * would return the tick state from the moment when suspend function was called. */
        if ((diff > 1) && (xTaskGetSchedulerState() != taskSCHEDULER_RUNNING))
        {
            diff = 1;
        }
        while ((diff--) > 0)
        {
            switch_req |= xTaskIncrementTick();
        }
    }
    else
    {
        switch_req = xTaskIncrementTick();
    }

    /* Increment the RTOS tick as usual which checks if there is a need for rescheduling */
    if ( switch_req != pdFALSE )
    {
        /* A context switch is required. Context switching is performed in
        the PendSV interrupt. Pend the PendSV interrupt. */
        SCB->ICSR = SCB_ICSR_PENDSVSET_Msk;
        __SEV();
    }

        portCLEAR_INTERRUPT_MASK_FROM_ISR( isrstate );
    }

Thank you,

L

  • Try this

        void xPortSysTickHandler( void )
        {
        #if configUSE_TICKLESS_IDLE == 1
            nrf_rtc_event_clear(portNRF_RTC_REG, NRF_RTC_EVENT_COMPARE_0);
        #endif
    
        BaseType_t switch_req = pdFALSE;
        uint32_t isrstate = portSET_INTERRUPT_MASK_FROM_ISR();
    +
    +   traceISR_ENTER();
    +
        uint32_t systick_counter = nrf_rtc_counter_get(portNRF_RTC_REG);
        nrf_rtc_event_clear(portNRF_RTC_REG, NRF_RTC_EVENT_TICK);
    
        if (configUSE_DISABLE_TICK_AUTO_CORRECTION_DEBUG == 0)
        {
            /* check FreeRTOSConfig.h file for more details on configUSE_DISABLE_TICK_AUTO_CORRECTION_DEBUG */
            TickType_t diff;
            diff = (systick_counter - xTaskGetTickCount()) & portNRF_RTC_MAXTICKS;
    
            /* At most 1 step if scheduler is suspended - the xTaskIncrementTick
            * would return the tick state from the moment when suspend function was called. */
            if ((diff > 1) && (xTaskGetSchedulerState() != taskSCHEDULER_RUNNING))
            {
                diff = 1;
            }
            while ((diff--) > 0)
            {
                switch_req |= xTaskIncrementTick();
            }
        }
        else
        {
            switch_req = xTaskIncrementTick();
        }
    
        /* Increment the RTOS tick as usual which checks if there is a need for rescheduling */
        if ( switch_req != pdFALSE )
        {
    +       traceISR_EXIT_TO_SCHEDULER();
    +
            /* A context switch is required. Context switching is performed in
            the PendSV interrupt. Pend the PendSV interrupt. */
            SCB->ICSR = SCB_ICSR_PENDSVSET_Msk;
            __SEV();
        }
    +   else
    +   {
    +      traceISR_EXIT();
    +   }
    
            portCLEAR_INTERRUPT_MASK_FROM_ISR( isrstate );
        }

  • Hi Susheel,

    Thanks the response.  Your suggestion matches my interpretation of the patch.  But I was still unable to connected to the NRF52 with the SystemView tool.  My issue was that I had to change the target setting in the SystemView tool.  Maybe it was obvious, but all the documents that I have read and troubleshooting pages never mentioned it.  I found it by accident.  I hope this help someone else.  Thanks again.

    L

Related