Interrupt Handler

Hi folks, In the Micrium uC/OS-II, which is the RTOS I used to work in my previous work, there is a pair of API functions OSIntEnter and OSIntExit intended to notify the Kernel about the interrupt being processed, I think in order to prevent Scheduler switching to some task during the interrupt and also to keep track of interrupt nesting. This example is taken from the Micrium web-site: MyISR: Save CPU registers; OSIntEnter(); /* Or, OSIntNestingCtr++ */ : Process ISR; : OSIntExit(); Restore CPU registers; Return from interrupt; The same approach exists in the Segger’s embOS. They have a similar API: OSINTEnter() and OSINTExit() I don’t see a similar API in the FreeRTOS (checked in the User Manual). If it is indeed true, would one here be so kind as to explain me why in the FreeRTOS I don’t need to notify the Scheduler about the interrupt being processed? Thanks in advance for any help!

Interrupt Handler

For most ports ( platforms ), FreeRTOS does not have an equivalent of OSIntEnter()/OSIntExit() But for instance, for Atmel’s UC3A, there is such a thing: ~~~ attribute((naked)) void spi0interrupthandler(void) { portENTERSWITCHINGISR(); { handlerspi(0); } portEXITSWITCHINGISR(); } ~~~ The interrupt is declared as naked, i.e. without the usual save and restore context. In stead, the two macro’s take care of this. Note that in this case, the return value of handler_spi() determines if a task switch is required ( register r0 ). For platforms using ARM, the interrupt handlers are simpler: they look like ordinary functions. In all cases, within an interrupt handler, you can only use a subset of the FreeRTOS API’s, i.e. the ones that end with FromISR

Interrupt Handler

Thank you very much for spending your time to answer my question.
For most ports ( platforms ), FreeRTOS does not have an equivalent of OSIntEnter()/OSIntExit() So the question is how the Scheduler knows the code is running from interrupt? Isn’t there a danger that it will switch the interrupt to some task ? Doesn’t the scheduler run from PendSV , so seemingly it can do this unwanted context switching. The interrupt is declared as naked, i.e. without the usual save and restore context. In stead, the two macro’s take care of this. Actually I found the function portENTERSWITCHINGISR(); on the web, but by some reason I didn’t find it in the User Guide, therefore I didn’t understand what is the function intended for. I also didn’t find this function in my FreeRTOS project (FreeRTOS 9.0 for now). Did you mean to say that I have to always call portENTERSWITCHINGISR() and portEXITSWITCHINGISR inside my ISR?
Also can I assume that this specific ISR API takes care to prevent the context switching while an ISR running is ongoing?

Interrupt Handler

So the question is how the Scheduler knows the code is running from interrupt? Isn’t there a danger that it will switch the interrupt to some task? Doesn’t the scheduler run from PendSV , so seemingly it can do this unwanted context switching.
You do not have to worry about this. You just write the ISR code, keeping it as short as possible. If a context switch becomes necessary, it will take place after your ISR is ready.
Did you mean to say that I have to always call portENTERSWITCHINGISR() and portEXITSWITCHINGISR inside my ISR?
No, that is not necessary, unless you’re using a platform like Atmel UC3.
Also can I assume that this specific ISR API takes care to prevent the context switching while an ISR running is ongoing?
As for ARM: this has to do with priorities: the priority of your ISR’s should higher than the priority of PendSV. If you have configASSERT(), the CPU priority will be checked in every API you call from an ISR.

Interrupt Handler

As for ARM: this has to do with priorities: the priority of your ISR’s should higher than the priority of PendSV.
But PendSV does have a higher priority… As I understand the priority of PendSV is configurable, but… doesn’t kernel itself takes care for that ?
If you have configASSERT(), the CPU priority will be checked in every API you call from an ISR.
I checked a dozen of API , but didn’t find where the priority is checked. Do you have a single example? What exactly is checked with the configASSERT? Very appreciate your help, thank you!

Interrupt Handler

Just found some staff that is helpfull for my recent questions that I would like to share here: https://www.freertos.org/RTOS-Cortex-M3-M4.html Frankly, I didn’t like this approach, too confusing IMHO.

Interrupt Handler

About configASSERT() : it is a macro that will halt your program in case an expression can not be asserted ( i.e. evaluates to zero ). Read more about configASSERT() here.
But PendSV does have a higher priority…
The higher the number, the lower the priority
As I understand the priority of PendSV is configurable
Sure it is. You can use ISR’s with a lower priority as long as they do nothing with the FreeRTOS kernel.
but… doesn’t kernel itself takes care for that ?
Like I said, the kernel can check the current ISR priority during every FromISR() API. This is being done for instance in xQueueGenericSendFromISR() when it calls the macro portASSERT_IF_INTERRUPT_PRIORITY_INVALID(). The page you mention is indeed very clear and helpful

Interrupt Handler

Hello Hein Given the mentioned above OSIntEnter()/OSIntExit() do not exist in FreeRTOS, may I assume that the RTOS Interrupt Latency is zero in the FreeRTOS? So far, I used to think that the overhead of the OSIntEnter()/OSIntExit() is the “Interrupt Latency” added by RTOS. Am i mistaken?

Interrupt Handler

In FreeRTOS there is a separate API for use in interrupts – namely the functions with “FromISR” in their name. There are pros and cons to any approach of course, but FreeRTOS’s approach here means: 1) You do not need to tell the kernel you are in an interrupt, you just have to use the right API functions when you are. 2) The API functions can be tuned for use when inside interrupts – for example you can’t block inside an interrupt so there is no block time parameter to pass into an ISR safe function and no logic in the implementation of the ISR function to handle blocking. 3) The non ISR functions can also be tuned as they do not need to check to see if you are inside an interrupt before deciding what to do.

Interrupt Handler

Thanks!