[Feature Request] Stack overflow checking of MSP on Cortex-M
Is your feature request related to a problem? Please describe. There are stack overflow check for all task stacks. But for, at least some, ARM Cortex-M MCUs there is a separate stack for exceptions/ISR. This stack is never checked for overflow.
Describe the solution you'd like Ideally it would just be part of the normal stack checking. But I am unsure if it can be made to work with all targeted MCUs.
Describe alternatives you've considered Alternatively, @drnadler (link) made some effort to implement it along with some other stuff regarding STM and newlib.
Additional context None
This is something that is hard to implement generically. One way could be to use MPU to catch MSP overflows. You can use a block of memory for main stack and put a red block right after it. The red block is blocked all access using MPU and any access to it will result in memory fault.
How about doing it in the STM32 port when doing context switch in xPortPendSVHandler, and just checking the MSP stack in the same way as taskCHECK_FOR_STACK_OVERFLOW() checks the task stack?
Basically deriving from @DRNadler and add the overflow checking in the task switching
The same Cortex-M3 port runs on all Cortex-M3 and M4 devices, and the same Cortex-M4F port runs on all Cortex-M4F and M7 devices - so there is no separate STM32 port. That means there is a big issue in regards to portability as the kernel has no way of knowing where the end of the MSP stack is. Some linker scripts define it explicitly, whereas others just set the start of the stack to the top of ram and let it grow until it hits something. We can do overflow checking in a portable way on the task stacks because the kernel creates the stack (or is passed in the stack if created statically) so it knows where both extremes are.
As Richard explained, we do not have a separate STM32 port. If you want to do it for your application, you can possibly use traceTASK_SWITCHED_OUT macro and put a check for MSP overflow there?
The same Cortex-M3 port runs on all Cortex-M3 and M4 devices, and the same Cortex-M4F port runs on all Cortex-M4F and M7 devices - so there is no separate STM32 port
My mistake, of course there is no STM32 port - What I meant to say was the Cortex-M ports.
That means there is a big issue in regards to portability as the kernel has no way of knowing where the end of the MSP stack is.
You would have to define a maximum MSP Stack size. It could be in the linker script. But for this purpose it would have to be in the FreeRTOS config. It will only be used for overflow checking anyway
... others just set the start of the stack to the top of ram and let it grow until it hits something.
And this is really the issue. At the moment you can enable stack overflow checking. But it does not check every/all stacks, so you might have a stack overflow you didn't know about.
I am not sure if all Cortex-M4F/M7 has MSP stack, but I imagine so. In that case, I don't see the problem in adding a configMAX_MSP_STACK_SIZE (or whatever) and check the MSP stack in xPortPendSVHandler. If this is not the case - then I agree, it becomes difficult to port.
If you think it completely impractical I will have to resort to using the trace macro as @aggarg suggests. I can also propose a solution in a pull-request if it helps?
You would have to define a maximum MSP Stack size. It could be in the linker script. But for this purpose it would have to be in the FreeRTOS config. It will only be used for overflow checking anyway
For overflow checking to be meaningful, the defined size should be correct i.e. the defined size should be size of main stack. As Richard mentioned, many times that is not defined and MSP is allowed to grow in the remaining RAM.
For overflow checking to be meaningful, the defined size should be correct ...
I don't see how it can be incorrect
... i.e. the defined size should be size of main stack ...
The main stack is just as well defined as the MSP stack
... many times that is not defined and MSP is allowed to grow in the remaining RAM.
And this is the problem - you have no way of knowing if it is growing into used RAM.
It is up to the user to define a maximum MSP stack size, just as with every task stack. There is really no difference.
Even if an MSP stack size is defined in the linker script. FreeRTOS /* Set the msp back to the start of the stack. */ in prvPortStartFirstTask(). Which will most likely make the definition in the linker script useless.
The thing that does help is, that the MSP stack can grow, without problem, until it runs out of unused memory, whereas for the task stacks, they will cause problems as soon as they overflow the stack with just a single byte.
I think I will propose a solution, and we can discuss it from there.
We look forward to a solution so we can discuss the specifics of MSP stack checking. Closing this issue.