According to ARM Architecture Procedure Call Standard (AAPCS) on the ARMv6-M, and ARMv7-M architecture in it says:
"Although the processor hardware allows SP to be at any word aligned address at function boundaries, standard programming practice requires C program code to ensure that the SP is at a 64-bit (doubleword) aligned address."
What does it mean that the Stack pointer has to be at a 64 bit aligned address?
I read about this recently, as I saw some redundant re-alignment code in a Reset_Handler.
For Cortex-M3, Cortex-M4 and Cortex-M7, it'll be beneficial to align the stack on an 8-byte boundary, since the LDRD instruction would require this.
In other words: If you pass a 64-bit integer on the stack to a subroutine, for instance as the third or fourth parameter, then it'll be stored on the stack.
The compiler would most likely use LDRD / STRD for reading/writing the 64-bit integer.
There is probably no benefit in aligning the stack on an 8-byte boundary on the Cortex-M0 and Cortex-M0+, except from if the compiler is making assumptions like jyiu says. I would expect this to happen if the compiler generates forward-compatible code (that is sometimes necessary if two different cores; eg. Cortex-M0 and Cortex-M4 are implemented on the same chip and they share code).
You can find more information about this in the ARM Information Center.
As for my own use, my own subroutines / code does not require an 8-byte aligned stack pointer (not even my C-code).
Unfortunately, it would not be 100% safe to turn it off, unless your compiler has a switch to ignore 8-byte stack-alignment and you rebuild your C-libraries so you can link against compatible libraries.
(The calling-convention must match all linked code, otherwise you may experience that your code suddenly fail "for no apparent reason").
I'm pretty certain LDRD only required 4-byte alignment whenever it is implemented but yes I think it probably is a good idea try and get double word alignment in case the bus supports 8-byte transfers. It also just looks wrong having 64-bit items split over a double word boundary.
For some legacy processors the LDRD in ARM state has 8 byte alignment requirement. But no such requirement for LDRD in ARMv7-M.
regards,
Joseph
Thanks for that. As they say it's the things you know but ain't so that catch you.
Yes, indeed, this is helpful and good information.
-So there will be no problems with alignment faults regarding LDRD if SP is not aligned on an 8-byte boundary.
I would expect that keeping the 8-byte boundary might help when it comes to cache and speed.
Yes. For processors with 64-bit interface (e.g. Cortex-M7), having such data alignment would be more efficient. It could also made debugging easier (e.g. when setting up data watchpoint).
It also avoids corner cases where a 64-bit access go across boundaries of different memory types, which can result in unpredictable behavior according the the architecture specification.