/* Generate a link error if heap and stack don't fit into RAM */
_Min_Heap_Size  = 0x200;      /* required amount of heap  */
_Min_Stack_Size = 0x400; /* required amount of stack */

/* Specify the memory areas */
MEMORY
{
    FLASH           (RX)  : ORIGIN = 0x00000000, LENGTH = 0x0000FFF8
    SRAM            (RWX) : ORIGIN = 0x20000000, LENGTH = 0x00001000
    BCR_CONFIG      (R)   : ORIGIN = 0x41C00000, LENGTH = 0x00000080
    BSL_CONFIG      (R)   : ORIGIN = 0x41C00100, LENGTH = 0x00000080

}

/* Note: SRAM length must match MPPC/MEMSS config! Please edit it manually. */

REGION_ALIAS("REGION_TEXT", FLASH);
REGION_ALIAS("REGION_BSS", SRAM);
REGION_ALIAS("REGION_DATA", SRAM);
REGION_ALIAS("REGION_STACK", SRAM);
REGION_ALIAS("REGION_HEAP", SRAM);
REGION_ALIAS("REGION_TEXT_RAM", SRAM);
REGION_ALIAS("REGION_ARM_EXIDX", FLASH);
REGION_ALIAS("REGION_ARM_EXTAB", FLASH);

/* Define output sections */
SECTIONS
{
    /* section for the interrupt vector area                                 */
    PROVIDE (_intvecs_base_address =
        DEFINED(_intvecs_base_address) ? _intvecs_base_address : 0x00000000);

    .intvecs (_intvecs_base_address) : AT (_intvecs_base_address) {
        KEEP (*(.intvecs))
    } > REGION_TEXT

    PROVIDE (_vtable_base_address =
        DEFINED(_vtable_base_address) ? _vtable_base_address : 0x20000000);

    .vtable (_vtable_base_address) : AT (_vtable_base_address) {
        KEEP (*(.vtable))
    } > REGION_DATA

   .text : {
        CREATE_OBJECT_SYMBOLS
        KEEP (*(.text))
        . = ALIGN(0x8);
        *(.text.*)
        . = ALIGN(0x8);
        KEEP (*(.ctors))
        . = ALIGN(0x8);
        KEEP (*(.dtors))
        . = ALIGN(0x8);
        __init_array_start = .;
        KEEP (*(.init_array*))
        . = ALIGN(0x8);
        __init_array_end = .;
        KEEP (*(.init))
        . = ALIGN(0x8);
        KEEP (*(.fini*))
        . = ALIGN(0x8);
    } > REGION_TEXT AT> REGION_TEXT

    .ramfunc : {
        __ramfunct_load__ = LOADADDR (.ramfunc);
        __ramfunct_start__ = .;
       *(.ramfunc)
       . = ALIGN(0x8);
       __ramfunct_end__ = .;
    } > REGION_TEXT_RAM AT> REGION_TEXT

    .rodata : {
        *(.rodata)
        . = ALIGN(0x8);
        *(.rodata.*)
        . = ALIGN(0x8);
    } > REGION_TEXT AT> REGION_TEXT


    .ARM.exidx : {
        __exidx_start = .;
        *(.ARM.exidx* .gnu.linkonce.armexidx.*)
        __exidx_end = .;
    } > REGION_ARM_EXIDX AT> REGION_ARM_EXIDX

    .ARM.extab : {
        KEEP (*(.ARM.extab* .gnu.linkonce.armextab.*))
         . = ALIGN(0x8);
    } > REGION_ARM_EXTAB AT> REGION_ARM_EXTAB

    __etext = .;

    .data : {
        __data_load__ = LOADADDR (.data);
        __data_start__ = .;
        KEEP (*(.data))
        KEEP (*(.data*))
        . = ALIGN (8);
        __data_end__ = .;
    } > REGION_DATA AT> REGION_TEXT

    .bss : {
        __bss_start__ = .;
        *(.shbss)
        KEEP (*(.bss))
        *(.bss.*)
        *(COMMON)
        . = ALIGN (4);
        __bss_end__ = .;
    } > REGION_BSS AT> REGION_BSS

    .heap : {
        __heap_start__ = .;
        end = __heap_start__;
        _end = end;
        __end = end;
        KEEP (*(.heap))
        __heap_end__ = .;
        __HeapLimit = __heap_end__;
    } > REGION_HEAP AT> REGION_HEAP

    .stack (NOLOAD) : ALIGN(0x8) {
        _stack = .;
        KEEP(*(.stack))
    } > REGION_STACK AT> REGION_STACK

    .BCRConfig :
    {
        KEEP(*(.BCRConfig))
    } > BCR_CONFIG

    .BSLConfig :
    {
        KEEP(*(.BSLConfig))
    } > BSL_CONFIG

    __StackTop = ORIGIN(REGION_STACK) + LENGTH(REGION_STACK);
    PROVIDE(__stack = __StackTop);
}
