What if 'portYIELD_FROM_ISR' not used?

anonymous wrote on Monday, May 25, 2009:


I’m completely new to FreeRTOS but also hooked (I’m using the STM32 Primer 1 Port). There is one major point that is driving me crazy with regard to Binary Sempahores.


Suppose ‘Task_One’ (which happens to be the single highest proirity task) blocks to wait for an ISR execute:
    ‘if( xSemaphoreTake( xSemaphore, LONG_TIME ) == pdTRUE )’

During the execution of a lower priority task, ‘Task_Four’, the ISR interrupts and executes the line:
    ‘xSemaphoreGiveFromISR( xSemaphore, &xHigherPriorityTaskWoken );’

If our ISR does not end with:
    ‘portYIELD_FROM_ISR( xHigherPriorityTaskWoken );’

what would happen? Would ‘Task_Four’ continue execution? Would ‘Task_One’ begin after the next ‘SysTick’?


Also, does our ISR have a greater priority than the Scheduler?

I hope someone can help! Thanks, Nick.

richard_damon wrote on Monday, May 25, 2009:

If the interrupt service routine does not call portYIELD_FROM_ISR then the task switch will be delayed until the next time the scheduler is activated, either by another interrupt (including the timer tick), or the current task blocks or yields.

As for comparing the “priority” of the ISR and the Scheduler, that question really doesn’t make sense. There are several different types of priority in a computer. Interrupts have a priority order, where higher priority interrupts are processed before lower priority interrupts, and possibly might be able to even interrupt the lower priority interrupt. On this scale, the task timer tick is normally given the lowest priority level, and while the Scheduler isn’t itself an ISR, it is called by some ISRs (like the timer tick, or your ISR if you call portYIELD_FROM_ISR).

Tasks also have priorities, but ISRs are not tasks (the scheduler isn’t responsible for getting an ISR to run), and neither is the Scheduler a task (it is responsible for controlling the execution of tasks).

anonymous wrote on Monday, May 25, 2009:

Thanks Richard. I have a better understanding now I think.

So (for example), my ISR for a square wave generator (using a capture/compare module) and my ISR for a UART will be able to pre-empt normal scheduler operations (that happen to be executing) because:

1) I have given my ISRs high interrupt priorities.
2) FreeRTOS has given the scheduler SysTick a low priority (probably the lowest).

Also thanks for highlighting that parts of the scheduler are actually being called by my own ISRs (eg portYIELD_FROM_ISR) as well on the SysTick vector.

Would it be right to think that when ‘taskENTER_CRITICAL’ is used, my own ISRs would be disabled until ‘taskEXIT_CRITICAL’ is called?

Sorry if any of this seems obvious but I am really new to this and I need to get a feel for what is going on.

Cheers, Nick.

richard_damon wrote on Monday, May 25, 2009:

Note that only the scheduler action of figuring out the highest priority task and the switching over to it actually happen in the timer tick, the actually running of the task is at non-interrupt levels.

Critical Regions (bounded by taskENTER_CRITICAL and taskEXIT_CRITICAL) will disable the interrupt. In some ports, they only disable some interrupts, those of a level low enough that they are allowed to call FreeRTOS routines, others, which are not alllowed to call these might still be enabled. Other ports disable all the interrupts.

anonymous wrote on Monday, May 25, 2009:

Thanks ever so much. I feel a lot more confident now about how the system operates.

Regards, Nick.