Stack placement

The initial pointer to the stack area can be selected at boot, by setting the desired memory address in the first word of the IV table, which corresponds to the beginning of the binary image loaded in flash.

This pointer may be set at compile time, in different ways. The simple example from Chapter 4, The Boot-Up Procedure, shows how it is possible to assign a specific area for the stack, or using symbols exported from the linker script.

Using the linker script as a central point to describe memory regions and segments makes the code more portable across similar platforms.

Since our STM32F407 provides an additional, tightly coupled, 64 KB memory bank at address 0x10000000, we may want to reserve its lower 16 KB for the execution stack, and keep the rest in a separate section for later use. The linker script must define the region on top, in the MEMORY block:

MEMORY
{
FLASH (rx) : ORIGIN = 0x00000000, LENGTH = 1M
SRAM (rwx) : ORIGIN = 0x20000000, LENGTH = 128K
CCRAM(rwx) : ORIGIN = 0x10000000, LENGTH = 64K
}

Two symbols may now be exported at the end of the file, by assigning constant, pre-defined values:

_stack_size = 16 * 1024;
_stack_end = ORIGIN(CCRAM) + _stack_size;

The values of _stack_size and _stack_end can be accessed by the application as ordinary C symbols. _stack_end is placed at address 0 when the vector table is initialized, to indicate the highest stack address:

__attribute__ ((section(".isr_vector")))
void (* const IV[])(void) =
{
(void (*)(void))(&_end_stack),
isr_reset, // Reset
isr_fault, // NMI
isr_fault, // HardFault
/* more interrupt routines follow */

A common strategy used to organize memory in a bare-metal application running with a single contiguous area in RAM is to place the initial stack pointer at the highest available address at the end of the memory. This way, the stack is free to grow from the top of the memory down, while the application can still use the memory to allocate dynamic objects from the lowest address that is not used by any other section. While this mechanism is considered the most efficient, giving the illusion that it is possible to use up until the last byte of RAM available, it is dangerous because the two areas growing in opposite directions may collide, leading to unpredictable results.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset