Older versions of gcc-arm-none-eabi, such as gcc-arm-none-eabi-9-2019-q4-major , have bug where the global address of the stack guard is placed on the stack as a canary rather than the actual value of the stack guard. Furthermore, the embedded environments that this toolchain targets often lack Address Space Layout Randomization, meaning the address is in itself constant and knowable, and therefore not useful as a canary.
Would it be possible to issue a fix, or warning about the problem and a call to update to newer versions?
gcc-arm-none-eabi-9-2019-q4-major
CFLAGS = --specs=nano.specs --specs=nosys.specs -O0 -mcpu-cortex-m4 -mthumb -fstack-protector-strong
Examined generated code using the debugger and objdump and observed:
000c0704 <main>:
c0704: b580 push {r7, lr}
c0706: b0a2 sub sp, #136 ; 0x88
c0708: af00 add r7, sp, #0
c070a: 4b17 ldr r3, [pc, #92] ; (c0768 <main+0x64>)
c070c: 681b ldr r3, [r3, #0]
c070e: f8c7 3084 str.w r3, [r7, #132] ; 0x84
c0712: f04f 0300 mov.w r3, #0
c0716: 2300 movs r3, #0
c0718: 603b str r3, [r7, #0]
c071a: e010 b.n c073e <main+0x3a>
...
c0766: bd80 pop {r7, pc}
c0768: 000c0c34 This is NOT the address of __stack_chk_guard
c076c: 400fff00
...
000c0c30 <_global_impure_ptr>:
c0c30: 00118008
c0c34: 00118460 From the map file this is the address of __stack_chk_guard
c0c38: 202a2a2a
c0c3c: 63617473
c0c40: 6d73206b
The code sequence at the beginning of main stores the address of __stack_chk_guard on the stack not the value. From the map file:
.bss.__stack_chk_guard 0x0000000000118460 0x4
If I build the same code with arm-none-eabi-gcc-8-2019-q3-update
000c06f4 <main>:
c06f4: b580 push {r7, lr}
c06f6: b0a2 sub sp, #136 ; 0x88
c06f8: af00 add r7, sp, #0
c06fa: 4b16 ldr r3, [pc, #88] ; (c0754 <main+0x60>)
c06fc: 681b ldr r3, [r3, #0]
c06fe: f8c7 3084 str.w r3, [r7, #132] ; 0x84
c0702: 2300 movs r3, #0
c0704: 603b str r3, [r7, #0]
c0706: e010 b.n c072a <main+0x36>
...
c0752: bd80 pop {r7, pc}
c0754: 00118460 This is the address of __stack_chk_guard from the map file
c0758: 400fff00
.bss.__stack_chk_guard 0x0000000000118460 0x4
Am I misunderstanding SSP? I thought the value of the guard variable is saved on functions stack. The GCC 9 code is saving the address of __stack_chk_guard.
Older versions of gcc-arm-none-eabi, such as gcc-arm- none-eabi- 9-2019- q4-major , have bug where the global address of the stack guard is placed on the stack as a canary rather than the actual value of the stack guard. Furthermore, the embedded environments that this toolchain targets often lack Address Space Layout Randomization, meaning the address is in itself constant and knowable, and therefore not useful as a canary.
The bug has been reported in the past by Daniel Worley (https:/ /launchpad. net/~dswbike) but was not addressed. It was also described at length by Christian Reitter (https:/ /blog.inhq. net/posts/ faulty- stack-canary- arm-systems/).
Would it be possible to issue a fix, or warning about the problem and a call to update to newer versions?
gcc-arm- none-eabi- 9-2019- q4-major protector- strong impure_ ptr>: stack_chk_ guard 0x0000000000118460 0x4
CFLAGS = --specs=nano.specs --specs=nosys.specs -O0 -mcpu-cortex-m4 -mthumb -fstack-
Examined generated code using the debugger and objdump and observed:
000c0704 <main>:
c0704: b580 push {r7, lr}
c0706: b0a2 sub sp, #136 ; 0x88
c0708: af00 add r7, sp, #0
c070a: 4b17 ldr r3, [pc, #92] ; (c0768 <main+0x64>)
c070c: 681b ldr r3, [r3, #0]
c070e: f8c7 3084 str.w r3, [r7, #132] ; 0x84
c0712: f04f 0300 mov.w r3, #0
c0716: 2300 movs r3, #0
c0718: 603b str r3, [r7, #0]
c071a: e010 b.n c073e <main+0x3a>
...
c0766: bd80 pop {r7, pc}
c0768: 000c0c34 This is NOT the address of __stack_chk_guard
c076c: 400fff00
...
000c0c30 <_global_
c0c30: 00118008
c0c34: 00118460 From the map file this is the address of __stack_chk_guard
c0c38: 202a2a2a
c0c3c: 63617473
c0c40: 6d73206b
The code sequence at the beginning of main stores the address of __stack_chk_guard on the stack not the value. From the map file:
.bss.__
If I build the same code with arm-none- eabi-gcc- 8-2019- q3-update
000c06f4 <main>:
c06f4: b580 push {r7, lr}
c06f6: b0a2 sub sp, #136 ; 0x88
c06f8: af00 add r7, sp, #0
c06fa: 4b16 ldr r3, [pc, #88] ; (c0754 <main+0x60>)
c06fc: 681b ldr r3, [r3, #0]
c06fe: f8c7 3084 str.w r3, [r7, #132] ; 0x84
c0702: 2300 movs r3, #0
c0704: 603b str r3, [r7, #0]
c0706: e010 b.n c072a <main+0x36>
...
c0752: bd80 pop {r7, pc}
c0754: 00118460 This is the address of __stack_chk_guard from the map file
c0758: 400fff00
.bss.__ stack_chk_ guard 0x0000000000118460 0x4
Am I misunderstanding SSP? I thought the value of the guard variable is saved on functions stack. The GCC 9 code is saving the address of __stack_chk_guard.