C언어,ARM

LinkerScript - stm32_flash.ld

안녕1999 2016. 9. 9. 23:30

/*
*****************************************************************************
**
**  File        : stm32_flash.ld
**
**  Abstract    : Linker script for STM32F207 Device with
**                1MByte FLASH, 128KByte SRAM
**
**                Set heap size, stack size and stack location according
**                to application requirements.
**
**                Set memory bank area and size if external memory is used.
**
**  Target      : STMicroelectronics STM32
**
**  Environment : Eclipse with CDT plugin and GCC compiler from CodeSourcery
**
**			 Author           Date        Comment
**~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
** 		    T.Kamenicky      24/06/11    Upravil kod stazen z netu
**			T.Kamenicky		 13/10/11	 Predelal na STM32F2
**			T.Kamenicky		 29/11/11    Pridal podporu externi SRAM
**
*****************************************************************************
*/

/* Entry Point */
/* This define entry point for linker, this address is used for CPU too as absolute first function */
ENTRY(Reset_Handler)

/* Highest address of the user mode stack, _estack is end of stack */
_estack = 0x20020000;    /* end of 128K RAM */

/* Generate a link error if heap and stack don't fit into RAM */
/* Heap is zero because we use own malloc implementation. The amount of heap is calculated 
 * from free space after compilation, see last section for RAM area */
_Min_Heap_Size = 0x0;      /* required amount of heap  */

/* This stack is used for main function. If FreeRTOS is used this stack is used by OS itself. */
/* The size of stack for tasks is defined in freertos config file and when creating the task. */
_Min_Stack_Size = 0x600; /* required amount of stack */

/* Specify the memory areas */
MEMORY
{
  FLASH (rx)      : ORIGIN = 0x08000000, LENGTH = 1022K		  /* This is main program area */
  FACTORY_VAR(rx) :	ORIGIN = 0x080FF800, LENGTH = 2K 		  /* This area is used for factory values, such as MAC address, ID...etc */
  RAM (xrw)       : ORIGIN = 0x20000000, LENGTH = 128K        /* This is RAM area */
  FSMC_SRAM (rx)  : ORIGIN = 0x64000000, LENGTH = 2048K       /* This is useful for external memory, like thru FSMC peripheral */
}

/* Library configurations */
GROUP(libgcc.a libc.a libm.a libnosys.a)

/* Linker script to place sections and symbol values. Should be used together
 * with other linker script that defines memory regions FLASH and RAM.
 * It references following symbols, which must be defined in code:
 *   Reset_Handler : Entry of reset handler
 *
 * It defines following symbols, which code can use without definition:
 *   __exidx_start
 *   __exidx_end
 *   __etext
 *   __data_start__
 *   __preinit_array_start
 *   __preinit_array_end
 *   __init_array_start
 *   __init_array_end
 *   __fini_array_start
 *   __fini_array_end
 *   __data_end__
 *   __bss_start__
 *   __bss_end__
 *   __end__
 *   end
 *   __HeapLimit
 *   __StackLimit
 *   __StackTop
 *   __stack
 */
ENTRY(Reset_Handler)

SECTIONS
{
   /* The startup code goes first into FLASH */
  .isr_vector :
  {
    . = ALIGN(4);
    KEEP(*(.isr_vector)) /* Startup code */
    . = ALIGN(4);
  } >FLASH

  /* The program code and other data goes into FLASH */
  .text :
  {
    . = ALIGN(4);
    *(.text)           /* .text sections (code) */
    *(.text*)          /* .text* sections (code) */
    *(.rodata)         /* .rodata sections (constants, strings, etc.) */
    *(.rodata*)        /* .rodata* sections (constants, strings, etc.) */
    *(.glue_7)         /* glue arm to thumb code */
    *(.glue_7t)        /* glue thumb to arm code */

    KEEP (*(.init))
    KEEP (*(.fini))

     . = ALIGN(4);
    _etext = .;        /* define a global symbols at end of code */
  } >FLASH

  /* .ARM.extab names a section that contains exception unwinding information.  See EHABI for details. */
  /* .ARM.exidx names a section that contains index entries for section unwinding.  See EHABI for details. */
   .ARM.extab   : { *(.ARM.extab* .gnu.linkonce.armextab.*) } >FLASH
    .ARM : {
    __exidx_start = .;
      *(.ARM.exidx*)
      __exidx_end = .;
    } >FLASH

  /* Is used for compiler information, which is located only in elf file */
  .ARM.attributes 0 : { *(.ARM.attributes) }

  /* Those sections is used for initializing dynamic objects used in C++ */
 .preinit_array     :
  {
    PROVIDE_HIDDEN (__preinit_array_start = .);
    KEEP (*(.preinit_array*))
    PROVIDE_HIDDEN (__preinit_array_end = .);
  } >FLASH
  .init_array :
  {
    PROVIDE_HIDDEN (__init_array_start = .);
    KEEP (*(SORT(.init_array.*)))
    KEEP (*(.init_array*))
    PROVIDE_HIDDEN (__init_array_end = .);
  } >FLASH
  .fini_array :
  {
    PROVIDE_HIDDEN (__fini_array_start = .);
    KEEP (*(.fini_array*))
    KEEP (*(SORT(.fini_array.*)))
    PROVIDE_HIDDEN (__fini_array_end = .);
  } >FLASH

  /* used by the startup as memory location to initialize data */
  /* from this point the content of flash is copied to ram */
  _sidata = .;

  /* Initialized data sections goes into RAM, load LMA copy after code */
  .data : AT ( _sidata )
  {
    . = ALIGN(4);
    _sdata = .;        /* create a global symbol at data start */
    *(.data)           /* .data sections */
    *(.data*)          /* .data* sections */

    . = ALIGN(4);
    _edata = .;       /* define a global symbol at data end */
  } >RAM

  _SRAM_data = _sidata + _edata - _sdata;

  /* Second part of inicialized section goes into SRAM conected thru FSMC */
  /* FSMC_SRAM section, code must be located here explicitly            */
  /* unsigned long int __attribute__ ((section (".sram_data"))) my_initialized_number = 0xAABBCCDD; */
  .fsmc_sram_data : AT ( _SRAM_data )
  {
  	. = ALIGN(4);
    _iSRAM_data = .;        
    *(.sram_data)      
    *(.sram_data*)
    
    . = ALIGN(4);
    _iSRAM_data_end = .;   
  } >FSMC_SRAM
  
  .fsmc_sram_bss : AT ( _iSRAM_data_end )
  {
    _iSRAM_null_data = .;       
    *(.sram_bss)
    *(.sram_bss*)
    
    . = ALIGN(4);
    _iSRAM_null_data_end = .;
  } >FSMC_SRAM
  
  .fsmc_sram_perma : AT ( _iSRAM_null_data_end )
  {
    _iSRAM_perma_data = .;       
    *(.sram_perma)
    *(.sram_perma*)
    
    . = ALIGN(4);
    _iSRAM_perma_data_end = .;
  } >FSMC_SRAM
  
   /* Uninitialized data section */
  . = ALIGN(4);
  
  .bss : AT ( _edata )
  {
    /* This is used by the startup in order to initialize the .bss secion */
    _sbss = .;         /* define a global symbol at bss start */
    __bss_start__ = _sbss;
    *(.bss)
    *(.bss*)
    *(COMMON)

    . = ALIGN(4);
    _ebss = .;         /* define a global symbol at bss end */
    __bss_end__ = _ebss;
  } >RAM
  
  /* Those numbers are used for SRAM init */
  PROVIDE ( _linker_sram_start = _iSRAM_data );
  PROVIDE ( _linker_sram_data_end = _iSRAM_data_end );
  PROVIDE ( _linker_sram_end = _iSRAM_null_data_end );
  PROVIDE ( _linker_sram_inits = _SRAM_data );
  
  /* Those numbers are used for malloc and sbrk functions */
  PROVIDE ( _linker_memory_start = _sdata );
  PROVIDE ( _linker_heap_start = _ebss );
  PROVIDE ( _linker_heap_end = (_estack - _Min_Stack_Size) );
  PROVIDE ( _linker_memory_end = _estack );
  PROVIDE ( _end = _ebss );

   /* User_heap_stack section, used to check that there is enough RAM left */
  ._user_heap_stack : AT ( _linker_heap_end )
  {
    . = ALIGN(4);
    . = . + _Min_Heap_Size;
    . = . + _Min_Stack_Size;
    . = ALIGN(4);
  } >RAM

 /* FLASH memory area for factory default values                          */
  /* Example of usage: extern int foo(void) __attribute__ ((section (".fvtext"))); */
  /* unsigned long int my_factory_number_changed_in_production = 0xAABBCCDD __attribute__ ((section (".fvrodata"))); */ 
  .factory_values :
  {
    . = ALIGN(4);
    *(.fvtext)        /* .fvtext sections (code) */
    *(.fvtext*)       /* .fvtext* sections (code)  */
    *(.fvrodata)      /* read-only data (constants) */
    *(.fvrodata*)
    . = ALIGN(4);
  } >FACTORY_VAR

  /* Remove information from the standard libraries */
  /DISCARD/ :
  {
    libc.a ( * )
    libm.a ( * )
    libgcc.a ( * )
  }
}