The following code snippet, compiled with "arm-none-eabi-gcc -mthumb -mcpu=cortex-m3 -Os", generates code sequences that will cause the functions to behave incorrectly.
struct foo { int a; int b; };
void __attribute__((naked)) frob(struct foo a, int b, int c) {
__asm("bx lr");
}
struct foo __attribute__((naked)) return_a_foo(int a, int b, int c) {
__asm("bx lr");
}
The following code snippet, compiled with "arm-none-eabi-gcc -mthumb -mcpu=cortex-m3 -Os", generates code sequences that will cause the functions to behave incorrectly.
struct foo { int a; int b; }; _((naked) ) frob(struct foo a, int b, int c) { _((naked) ) return_a_foo(int a, int b, int c) {
void __attribute_
__asm("bx lr");
}
struct foo __attribute_
__asm("bx lr");
}
Dissasembly:
00000000 <frob>:
0: ab02 add r3, sp, #8
2: e903 0003 stmdb r3, {r0, r1}
6: 4770 bx lr
00000008 <return_a_foo>:
8: 4603 mov r3, r0
a: 4770 bx lr
c: 4618 mov r0, r3
r3 is clobbered in both functions, which corrupts the "int c" parameter. And the "frob" function writes into the caller's stack frame!