threadx
threadx copied to clipboard
Wrong SPSR value in tx_thread_stack_build.S for Cortex A53 ports.
I've been evaluating the Cortex A53 port for both the SMP and non-SMP ports and it appears to me that the SPSR value pushed into the stack frame does not set bit 0 which causes the stack pointer to select SP_EL0 instead of keeping the stack pointer from the respective execution level that the code is running in. The rest of the code does not seem to expect this behavior. I've noticed that in the cortex_a5x port this issue has already been resolved. Can the cortex_a5x implementation be copied over to the Cortex A53 ports?
Here are the Cortex A53 code sections that I'm aware of that do it wrong: ports_smp/cortex_a53_smp/gnu/src/tx_thread_stack_build.S#L140 ports/cortex_a53/gnu/src/tx_thread_stack_build.S#L140
And this is the cortex_a5x code section that does this correctly: ports/cortex_a5x/ac6/src/tx_thread_stack_build.S#L150
Hi @rodfrazer - this issue has come up before. Have you looked at this issue: https://github.com/azure-rtos/threadx/issues/161
I did see that other issue but I don't see the code from the cortex-a5x port being replicated into any of the other ports yet to address the problem. Is that still planned to happen in a future release?
I am not sure the a5x code should be propagated to the other ports. What EL are you operating in?
I happen to be running in EL2 mode, but it seems to me like this code breaks in EL1, EL2 or EL3 mode. With the M[0] bit clear in the SPSR the ERET that executes to enter the thread context is going to implement the SP_EL0 stack pointer regardless of what context the scheduler may be operating in but I see no code in the ports that seems to contemplate that. There doesn't appear to be any code configuring and maintaining SP_EL0 in the scheduler code, so my assumption is that the scheduler expects the stack pointer to remain on the SP_ELx stack pointer.
On my target the SP_EL0 stack pointer is pointing to 0x0 as I never expect it to be used, and accesses on my target to address 0 - 1M will cause an access fault. So when I start the RTOS and the _tx_thread_schedule_loop executes the ERET to start my first thread, the first instruction at _tx_thread_shell_entry pushes to the stack and my target experiences the fault due to accessing location 0x0 from the SP_EL0 stack pointer. When I change the code to configure an SPSR with the M[0] bit set, then I get normal expected operation as I start the kernel and the SP_ELx stack pointer is allowed to persist through the ERET instruction.