## ###################################################################
##
##     Copyright Freescale Semiconductor, Inc. 2011
##
##     Processor : 56F84xxx
##
##     Abstract  :
##
##     This file is used by the linker. It describes files to be linked,
##     memory ranges, stack size, etc. For detailed description about linker
##     command files see CodeWarrior documentation.
##
## ###################################################################

###############################################################################
# The following section determines how Flash and RAM will be allocated for the
# application.  It will require modification in the event the software is 
# modified.  The nature in how each segment is allocated is cumbersome, however
# it is necessary to ensure program flash is contiguous.  A contiguous memory
# footprint for the application is desired, since it facilliates programming
# silicon in the field.
###############################################################################
MEMORY {
    .pIntvectorBoot     (RWX):  ORIGIN=0x000000,  LENGTH=0x000004
    .pFlashConfig       (RX) :  ORIGIN=0x000200,  LENGTH=0x000008  # 16 bytes reserved for IFR    
    .ppFlash            (RWX):  ORIGIN=0x068000,  LENGTH=0x003800  # secondary flash for user code
    .pFlash             (RWX):  ORIGIN=0x06B600,  LENGTH=0x000A00  # secondary flash for bootloader
    .xDFlash			(RW)  : ORIGIN=0x008000,  LENGTH=0x004000  # mirror of .pFlash
    .xRAM_bss           (RW) :  ORIGIN=0x000000,  LENGTH=0x000400
    .xRAM_data          (RWX):  ORIGIN=0x000400,  LENGTH=0x000200
    .xRAM               (RW) :  ORIGIN=0x000600,  LENGTH=0x001A00
    .xRAM_code          (RW) :  ORIGIN=0x002000,  LENGTH=0x002000  # mirror of .pRAM
    .pRAM               (RWX):  ORIGIN=0x062000,  LENGTH=0x002000  # RAM code
    .xPeripherals       (RW) :  ORIGIN=0x00E000,  LENGTH=0x002000 # off-platform perihperal address space
}

KEEP_SECTION { interrupt_vectorsboot.text, interrupt_vectors.text }
FORCE_ACTIVE {Ffisr_sci_rx_full,Frx_data}

SECTIONS {

    ###########################################################################
    # This following three sections contain program code intended for flash.
    # The reset vector is duplicated by the first two sections to be consistent
    # with other PE templates.
    ###########################################################################
    .interrupt_vectorsboot : {
        F_vector_addr = .;
        * (interrupt_vectorsboot.text)
        Fpflash_index = .;
    } > .pIntvectorBoot

	.FlashConfig : {
		WRITEH(0xFFFF);	# 0
		WRITEH(0xFFFF); # 1
		WRITEH(0xFFFF); # 2
		WRITEH(0xFFFF); # 3
		WRITEH(0xFFFF); # 4
		WRITEH(0xFFFF); # 5
		WRITEH(0xFFFF);	# 6, security byte
#		WRITEH(0xFFBE);	# 6, security byte
		WRITEH(0xFFFF); # 7
	} >.pFlashConfig
 
    .ApplicationCode : {
    	_pFlash_code_start  = .;
        # Note: The function _EntryPoint should be placed at the beginning
        #       of the code
        OBJECT (F_EntryPoint, Cpu.c)
        
        # Remaining .text sections
        * (rtlib.text)
        * (startup.text)
        * (fp_engine.text)
        * (user.text)
        * (.text)

        # save address where for the data start in pROM
        Fpflash_mirror = .;
        Fpflash_index = .;
        # calculate the address of code in x flash
        _dflash_code_start = .  - ADDR(.ppFlash) + ADDR(.xDFlash);
    } > .pFlash

    ###########################################################################
    # This section allocates memory in RAM for any zero-initiailized globals 
    # in the application.  Runtime code writes zero to each location of RAM
    # used by this section. 
    ###########################################################################
    .data_in_x_ram_bss : {
        # .bss sections
        F_Xbss_start_addr = .;
        _START_BSS = .;
        OBJECT (Frx_data, bootloader_lib.c)
        * (rtlib.bss.lo)
        * (rtlib.bss)
        * (.bss.char)         # used if "Emit Separate Char Data Section" enabled
        * (.bss)
        _END_BSS   = .;
        F_Xbss_length = _END_BSS - _START_BSS;    
    } > .xRAM_bss
    
    
    ###########################################################################
    # This section allocates memory in RAM for any program code in the 
    # application not intended for flash.  The opcodes are mirrored into Flash
    # and copied into RAM at runtime.
    ###########################################################################
    .prog_in_p_flash_ROM : AT(Fpflash_mirror) {
        Fpram_start = .;
        _pram_start = .;

        # This line defines the location of the interrupt vector table.  It is
        # used by "Cpu.C" to set the INTC_VBA register.
        F_vba = .;
        F_vba = (F_vba / 256); 
        * (interrupt_vectors.text)
        * (pram_code.text)
        
        # save data end and calculate data block size
        Fpram_end = .;
        Fpram_size = Fpram_end - Fpram_start;
        _pram_size = Fpram_size;
        Fpflash_mirror2 = Fpflash_mirror + Fpram_size;
        Fpflash_index = Fpflash_mirror + Fpram_size;
        
        # calculate the corresponding d flash address in x mem for data
        Fdflash_mirror2 = _dflash_code_start + Fpram_size;
    } > .pRAM

    ###########################################################################
    # This section allocates memory in RAM for any constants and non-zero
    # initialized global variables in the application.  The actual data values
    # are mirrored into Flash and copied into RAM at runtime.
    ###########################################################################
    .data_in_p_flash_ROM : AT(Fpflash_mirror2) {
        Fxram_start = .;
        * (.const.data.char)    # used if "Emit Separate Char Data Section" enabled
        * (.const.data)
        * (fp_state.data)
        * (rtlib.data)
        * (.data.char)          # used if "Emit Separate Char Data Section" enabled
        * (.data)
        . = ALIGN(2);
        # save data end and calculate data block size
        Fxram_end = .;
        Fxram_size = Fxram_end - Fxram_start;
        Fpflash_index = Fpflash_mirror2 + Fxram_size;
    } > .xRAM_data

    ###########################################################################
    # This section defines the stack pointer and heap
    ###########################################################################
    .data_in_x_ram : {
        /* Setup the HEAP address */
        . = ALIGN(4);
        _HEAP_ADDR = .;
        _HEAP_SIZE = 0x0000;
        _HEAP_END = _HEAP_ADDR + _HEAP_SIZE;
        . = _HEAP_END;

        /* SETUP the STACK address */
        _min_stack_size = 0x0200;
        _stack_addr = _HEAP_END;
        _stack_end  = _stack_addr + _min_stack_size;
        . = _stack_end;
        
        // store page buffer
        * (flash_page.page)

        __DATA_END=.;
    } > .xRAM

    # Peripheral registers for PESL
    FArchIO = ADDR(.xPeripherals);
    
    # Export HEAP and STACK to runtime libraries
    F_heap_addr    = _HEAP_ADDR;
    F_heap_end     = _HEAP_END;
    F_Lstack_addr  = _HEAP_END;
    F_StackAddr    = _HEAP_END;
    F_StackEndAddr = _stack_end - 1;

    # runtime code __init_sections uses these globals:
    F_Ldata_size     = 0;
    F_Ldata_RAM_addr = 0x0000;
    F_Ldata_ROM_addr = 0;
    F_xROM_to_xRAM   = 0x0000;
    F_pROM_to_xRAM   = 0x0000;
    F_start_bss      = _START_BSS;
    F_end_bss        = _END_BSS;
	F_dflash_code_start = _dflash_code_start;
	F_dram_code_start = ADDR(.xRAM_code);
	F_dram_code_size  = _pram_size;
}
