Function __builtin_return_address returns invalid address
Affects | Status | Importance | Assigned to | Milestone | |
---|---|---|---|---|---|
GNU Arm Embedded Toolchain |
In Progress
|
Undecided
|
Mihail-Calin Ionescu |
Bug Description
The problem only applies to Cortex-M0 and any GCC release 6 and 7. Previous versions work correctly.
Consider the following code:
__attribute_
void *retaddr;
__attribute_
void xxxxtest(void) {
retaddr = __builtin_
/* Used for enforcing registers stacking.*/
asm volatile("" : : : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
}
It produces the following asm:
8001940: b5f0 push {r4, r5, r6, r7, lr}
8001942: 46de mov lr, fp <=========== HERE LR is used as a scratchpad
8001944: 4657 mov r7, sl
8001946: 464e mov r6, r9
8001948: 4645 mov r5, r8
800194a: 4672 mov r2, lr <=========== HERE LR is accessed for return address
800194c: 4b04 ldr r3, [pc, #16] ; (8001960 <xxxxtest+0x20>)
800194e: b5e0 push {r5, r6, r7, lr}
8001950: 601a str r2, [r3, #0]
8001952: bc3c pop {r2, r3, r4, r5}
8001954: 4690 mov r8, r2
8001956: 4699 mov r9, r3
8001958: 46a2 mov sl, r4
800195a: 46ab mov fp, r5
800195c: bdf0 pop {r4, r5, r6, r7, pc}
The problem is in the function entry code, where callee-saved registers are stacked. LR is used as scratchpad @8001942 before the return address is taken @800194a.
This problem broke the ChibiOS port for Cortex-M0 using the latest compilers, the builtin is used for enforcing context switch after nested ISRs execution, a very critical bit of code, there is no easy way to workaround this.
Used compiler options are: -mcpu=cortex-m0 -mthumb -O2 -ggdb -fomit-
Disabling optimizations hides the problem.
tags: | added: chibios |
Changed in gcc-arm-embedded: | |
assignee: | nobody → Mihail-Calin Ionescu (mihail.ionescu) |
Changed in gcc-arm-embedded: | |
status: | New → In Progress |