2023-06-01 11:42 PM
I am using Nucleo F411RE dev borad. When I using the FreeRTOS, I found that the xTaskNotifyFromISR always stuck.
my handler function as below and I can enter it normally.
the program stop at
---------------------------------------------------------------------------
/* USER CODE BEGIN 4 */
void button_interrupt_handler(void) {
SEGGER_SYSVIEW_PrintfTarget("button_interrupt_handler\n");
BaseType_t pxHigherPriorityTaskWoken;
pxHigherPriorityTaskWoken = pdFALSE;
traceISR_ENTER();
SEGGER_SYSVIEW_PrintfTarget("next_task_handle %X\n",next_task_handle);
SEGGER_SYSVIEW_PrintfTarget("eNoAction %X\n",eNoAction);
SEGGER_SYSVIEW_PrintfTarget("pxHigherPriorityTaskWoken %X\n",pxHigherPriorityTaskWoken);
xTaskNotifyFromISR(next_task_handle, 0, eNoAction, &pxHigherPriorityTaskWoken);
//xTaskNotify(task2_handle, 0, eNoAction);
/* once the ISR exits, the below macro makes higher priority task which got unblocked to resume on the CPU */
portYIELD_FROM_ISR(pxHigherPriorityTaskWoken);
traceISR_EXIT();
}
xTaskNotifyFromISR(next_task_handle, 0, eNoAction, &pxHigherPriorityTaskWoken);
-------------------------------------------------------------------------
I follow the trace and the finialy stop at
------------------------------------------------
configASSERT( xTaskToNotify );
----------------------------------------------------
in the tasks.c file of FreeRTOS
The actual function as below
----------------------------------------------------------
#if ( configUSE_TASK_NOTIFICATIONS == 1 )
BaseType_t xTaskGenericNotifyFromISR( TaskHandle_t xTaskToNotify,
UBaseType_t uxIndexToNotify,
uint32_t ulValue,
eNotifyAction eAction,
uint32_t * pulPreviousNotificationValue,
BaseType_t * pxHigherPriorityTaskWoken )
{
TCB_t * pxTCB;
uint8_t ucOriginalNotifyState;
BaseType_t xReturn = pdPASS;
UBaseType_t uxSavedInterruptStatus;
configASSERT( xTaskToNotify );
configASSERT( uxIndexToNotify < configTASK_NOTIFICATION_ARRAY_ENTRIES );
/* RTOS ports that support interrupt nesting have the concept of a
* maximum system call (or maximum API call) interrupt priority.
* Interrupts that are above the maximum system call priority are keep
* permanently enabled, even when the RTOS kernel is in a critical section,
* but cannot make any calls to FreeRTOS API functions. If configASSERT()
* is defined in FreeRTOSConfig.h then
* portASSERT_IF_INTERRUPT_PRIORITY_INVALID() will result in an assertion
* failure if a FreeRTOS API function is called from an interrupt that has
* been assigned a priority above the configured maximum system call
* priority. Only FreeRTOS functions that end in FromISR can be called
* from interrupts that have been assigned a priority at or (logically)
* below the maximum system call interrupt priority. FreeRTOS maintains a
* separate interrupt safe API to ensure interrupt entry is as fast and as
* simple as possible. More information (albeit Cortex-M specific) is
* provided on the following link:
* https://www.FreeRTOS.org/RTOS-Cortex-M3-M4.html */
portASSERT_IF_INTERRUPT_PRIORITY_INVALID();
pxTCB = xTaskToNotify;
uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR();
{
if( pulPreviousNotificationValue != NULL )
{
*pulPreviousNotificationValue = pxTCB->ulNotifiedValue[ uxIndexToNotify ];
}
ucOriginalNotifyState = pxTCB->ucNotifyState[ uxIndexToNotify ];
pxTCB->ucNotifyState[ uxIndexToNotify ] = taskNOTIFICATION_RECEIVED;
switch( eAction )
{
case eSetBits:
pxTCB->ulNotifiedValue[ uxIndexToNotify ] |= ulValue;
break;
case eIncrement:
( pxTCB->ulNotifiedValue[ uxIndexToNotify ] )++;
break;
omit................
-----------------------------------------------------------
Anyone have similar case?
2023-06-02 12:51 AM
Read the comment you found in FreeRTOS code and apply it. The interrupt using FreeRTOS sync mechanisms must have priority numerically higher (=logically lower) than FreeRTOS call priority.