Forcing context switch after call to xSemaphoreGiveFromISR

jstoezel wrote on Tuesday, January 20, 2015:

Hi:

I am supporting a code base that uses xSemaphoreGiveFromISR (in both FreeRTOS 4.1 and 7.6), but does not try to force a context after a task might have been awoken (i.e. neither the return value of xSemaphoreGiveFromISR (4.1) nor the 2nd argument (7.6) are checked to decide whether a call to portYIELD_FROM_ISR() is required).

This code has been running for some time, being called from the tick hook and “seems to work”.

What is the downfall of not calling portYIELD_FROM_ISR once the semaphore is given from the ISR? Does the task eventually get awoken by some other mechanism, and this issue becomes transparent to the user?
Or is it that this specific xSemaphoreGiveFromISR call never requires forcing a context switch? This semaphore is waking up the task with the highest priority in the system.

A second question, related to the difference in API between 4.1 and 7.6 for xSemaphoreGiveFromISR. In 4.1 the second argument is passed by value, while on 7.6 it is passed by reference. The xSemaphoreGiveFromISR example for 7.6 shows to use the argument as means to decide whether or not a context switch is required, while on 4.1 the return value of the function used to be used.
Looking at the code for 7.6 and comparing with 4.1, it seems the return function of xSemaphoreGiveFromISR in 7.6 could also be used to decide whether a context switch is required. Is this a fair assumption?

Last, in 4.1 can portYIELD() be called from an ISR context? More precisely for the AT91SAM7S port:
#define portYIELD() asm volatile ( “SWI” );

For this port there doesn’t seem to be a version available to be called from the ISRs.

Regards,
JS

rtel wrote on Tuesday, January 20, 2015:

Relevant to V7.6 only:

In a normal ISR, the last parameter to xSemaphoreGiveFromISR() has no effect as to whether calling the function unblocks a task or not. xSemaphoreGiveFromISR() will always unblock a task if there was a task blocked on the semaphore. When the task is unblocked it is moved to the Ready state - so it is available for selection by the scheduler. The last parameter just lets you know if the task that was unblocked has a priority above that of the currently running task (the task that the interrupt interrupted).

If you do not use the last parameter then the unblocked task will remain in the ready state until the scheduler runs again. The scheduler will run again when the currently running task Blocks, or a tick interrupt occurs. Then the scheduler will select a new task to run, which will be the task unblocked by the semaphore if at that time it has the highest priority. So the worst case is the task does not run until the next tick interrupt.

If you do use the last parameter in the way documented for your port then the scheduler will run immediately and the interrupt will return directly to the unblocked task if it is the highest priority task in the ready state.

In this case however, the function is called from the tick hook, which means the scheduler is about to run anyway so the last parameter will make no difference at all to when the task will run. In this case the most efficient thing to do is set the last parameter to NULL so it is not used at all. That assumes V7.6 allows the last parameter to be NULL - that capability was introduced within the last few years.

Definitely don’t call SWI from an interrupt. Use the method documented for your port.

As far V4.1 - sorry, that is too old so we are unable to support it. We would have to download an old archive of the code, unzip it and re-familiarise ourselves with how it works. FreeRTOS is currently on V8.2.0, V4.1 is 8 years old.

Regards.

jstoezel wrote on Friday, January 23, 2015:

Hi:

Thank you for the detailed reply. Your comments have been taken into
account.

JS

On Tue, Jan 20, 2015 at 9:48 AM, Real Time Engineers ltd. <rtel@users.sf.net

wrote:

Relevant to V7.6 only:

In a normal ISR, the last parameter to xSemaphoreGiveFromISR() has no
effect as to whether calling the function unblocks a task or not.
xSemaphoreGiveFromISR() will always unblock a task if there was a task
blocked on the semaphore. When the task is unblocked it is moved to the
Ready state - so it is available for selection by the scheduler. The last
parameter just lets you know if the task that was unblocked has a priority
above that of the currently running task (the task that the interrupt
interrupted).

If you do not use the last parameter then the unblocked task will remain
in the ready state until the scheduler runs again. The scheduler will run
again when the currently running task Blocks, or a tick interrupt occurs.
Then the scheduler will select a new task to run, which will be the task
unblocked by the semaphore if at that time it has the highest priority. So
the worst case is the task does not run until the next tick interrupt.

If you do use the last parameter in the way documented for your port then
the scheduler will run immediately and the interrupt will return directly
to the unblocked task if it is the highest priority task in the ready state.

In this case however, the function is called from the tick hook, which
means the scheduler is about to run anyway so the last parameter will make
no difference at all to when the task will run. In this case the most
efficient thing to do is set the last parameter to NULL so it is not used
at all. That assumes V7.6 allows the last parameter to be NULL - that
capability was introduced within the last few years.

Definitely don’t call SWI from an interrupt. Use the method documented for
your port.

As far V4.1 - sorry, that is too old so we are unable to support it. We
would have to download an old archive of the code, unzip it and
re-familiarise ourselves with how it works. FreeRTOS is currently on
V8.2.0, V4.1 is 8 years old.

Regards.

Forcing context switch after call to xSemaphoreGiveFromISR
https://sourceforge.net/p/freertos/discussion/382005/thread/af58644e/?limit=25#0344

Sent from sourceforge.net because you indicated interest in
https://sourceforge.net/p/freertos/discussion/382005/

To unsubscribe from further messages, please visit
https://sourceforge.net/auth/subscriptions/