call vportfree from isr

smarini1963 wrote on Saturday, August 14, 2010:

I need of some help:
calling a vportfree function from isr crash the system.

this succeed because the vport free port for arm7 use vTaskSuspendAll internally.
I use the heap_2.c file

there is a way to solve this problem?

davedoors wrote on Saturday, August 14, 2010:

Never call a function that does not end in FromISR from an ISR.

richard_damon wrote on Saturday, August 14, 2010:

As was said, calling any FreeRTOS function that doesn’t end in FromISR in an ISR is an invitation for trouble. As it turns out, memory management (malloc/free type functions) do not work well in an ISR, because of there need to set up periods where they are not disturbed while they manipulate structures shared among multiple tasks (the free store list). In general, there are 3 categories of ways to implement this: Disabling Interrupt, Disabling the Scheduler, or a Mutex. Some of the manipulations that a memory management routine does may take long enough that you sometimes don’t want to use the disabling interrupt method (so FreeRTOS uses a Disabling the Scheduler method), but this is not compatible with the use of memory management during isrs, as that needs to use the Disabling Interrupt method.

One option is to take the memory management routines (vPortFree, vPortMalloc) and rewrite them (that is one reason it is nice to use open source, you have the source to modify) to use critical sections instead of schedule disabling, and then add a FromISR version that assumes it is in an interrupt and thus doesn’t need the critical section. It would then be nice to submit this version back for others to use, maybe as a heap_2isr.c

The other option is to change the structure of your program a bit. If you only need free in the isr, once solution would be to set up a queue that rather than actually doing the free in the isr, it pushes the memory pointer on the queue, and then a task pops the pointer off and calls free. If you need to allocate in the isr, it gets a bit trickier, but often the buffer size needed is known ahead of time, so you can preallocate a buffer(s) for it to use.

smarini1963 wrote on Wednesday, August 18, 2010:

this means that using the file heap_2.c create a file heap_2isr.c
and internally substitute to tasksuspendall the portENTER_CRITICAL()
and to taskresume all the portEXIT_CRITICAL()

is it right?


richard_damon wrote on Thursday, August 19, 2010:

Yes, and then create another function vPortFreeFromISR that is just like vPortFree except it omits the portENTER_CRITICAL() and portEXIT_CRITICAL() and use THAT function inside the ISR.