cancel
Showing results for 
Search instead for 
Did you mean: 

STM32L4 + FreeRTOS - taskENTER_CRITICAL does not disable interrupts

MMits.1
Associate II

I use FreeRTOS on a STM32L432 - the FreeRTOS port that STM delivers.

When I call "taskENTER_CRITICAL" it should disable all interrupts on the CPU, but fetching the BASEPRI register value tells me that the BASEPRI is still 0 (= all interrupts enabled).

Is this a bug in the FreeRTOS portation?

7 REPLIES 7
KnarfB
Principal III

It works for me on STM32CubeIDE 1.7.0 and a freshly created STM32 FreeRTOS project. Macro taskENTER_CRITICAL() is portENTER_CRITICAL() is vPortEnterCritical() calling portDISABLE_INTERRUPTS() which is vPortRaiseBASEPRI() moving configMAX_SYSCALL_INTERRUPT_PRIORITY (0x80) to BASEPRI.

MMits.1
Associate II

Yes, it does generate that code for me as well (my FreeRTOS SYSCALL priority is 3, not 8, but thats a detail). Only, that it does not actually SET that value when called.

   prim1 = __get_PRIMASK();
   taskENTER_CRITICAL();
   prim2 = __get_PRIMASK();
   taskEXIT_CRITICAL();
   prim3 = __get_PRIMASK();

result: prim1 = prim2 = prim3 = 0

whereas (using the CMSIS functions):

   prim1 = __get_PRIMASK();
   __disable_irq();
   prim2 = __get_PRIMASK();
   __enable_irq();
   prim3 = __get_PRIMASK();

prim1 = prim3 = 0

prim2 = 1

Well, but PRIMASK (Armv6-M) is not BASEPRI (Armv7-M), see e.g. https://community.arm.com/developer/ip-products/system/b/embedded-blog/posts/cutting-through-the-confusion-with-arm-cortex-m-interrupt-priorities

FreeRTOS intentionally leaves the interrupt with highest priorities on if possible, see https://www.freertos.org/taskENTER_CRITICAL_taskEXIT_CRITICAL.html

hth

KnarfB

Bloody hell, I didn't know that. Let me dive into things for a moment, I'll be right back with an update

   prim1 = __get_BASEPRI();
   taskENTER_CRITICAL();
   prim2 = __get_BASEPRI();
   taskEXIT_CRITICAL();
   prim3 = __get_BASEPRI();

Yes, this shows what I expect:

prim1 = 0

prim2 = 3

prim3 = 0

Thanks for clarification.

> prim2 = 3

Really? Lower 4 BASEPRI bits are not writable, so maybe the value is 0x30? (3 << configPRIO_BITS)

Yes, 0x30.

My bad, was writing in a hurry​