/*
** ###################################################################
**     Processor:           CVM0128
**     Compiler:            IAR ANSI C/C++ Compiler for ARM
**
**     Abstract:
**         Linker file for the IAR ANSI C/C++ Compiler for ARM
**
**     Copyright (c) 2022, Shenzhen CVA Innovation CO.,LTD
**     All rights reserved.
**
**     Shenzhen CVA Innovation CO.,LTD (CVA chip) is supplying this file for use
**     exclusively with CVA's microcontroller products. This file can be freely
**     distributed within development tools that are supporting such microcontroller
**     products.
** 
**     THIS SOFTWARE IS PROVIDED "AS IS".  NO WARRANTIES, WHETHER EXPRESS, IMPLIED
**     OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF
**     MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE.
**     CVA SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL,
**     OR CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
**
**     http:                 www.cvachip.com
**
** ###################################################################
*/

/* If symbol __flash_vector_table__=1 is defined at link time
 * the interrupt vector will not be copied to RAM.
 * Warning: Using the interrupt vector from FLASH will not allow
 * INT_SYS_InstallHandler because the section is Read Only.
 */

/* If want to debug the asw code without bootloader, please enable the define */
//define symbol __asw_debug_en__ =  0x00000001;

define symbol __flash_vector_table__ =  0x00000001;

define symbol __ram_vector_table_size__ =  isdefinedsymbol(__flash_vector_table__) ? 0 : 0x00000200;
define symbol __ram_vector_table_offset__ =  isdefinedsymbol(__flash_vector_table__) ? 0 : 0x000001FF;

/* Flash */
define symbol m_interrupts_start       = isdefinedsymbol(__asw_debug_en__) ? 0 : 0x00010000;
define symbol m_interrupts_end         = isdefinedsymbol(__asw_debug_en__) ? 0 : 0x000100BF;

define symbol m_asw_header_start       = 0x000100C0;
define symbol m_asw_header_end         = 0x000100ff;

define symbol m_asw_code_start         = 0x00010100;
define symbol m_asw_code_end           = 0x00037FF7;

define symbol m_asw_tail_start          = 0x00037FF8;
define symbol m_asw_tail_end            = 0x00037FFB;

define symbol m_asw_crc_start          = 0x00037FFC;
define symbol m_asw_crc_end            = 0x00037FFF;

/* .data space */
define symbol m_interrupts_ram_start   = 0x20000000;
define symbol m_interrupts_ram_end     = 0x20000000 + __ram_vector_table_offset__;

define symbol m_data_start             = m_interrupts_ram_start + __ram_vector_table_size__;
define symbol m_data_end               = m_data_start + 0x000007FF;

/* .bss stack ... */
define symbol m_data_2_start           = m_data_end + 0x00000001;
define symbol m_data_2_end             = 0x200037EF;

/* No initial Ram space: 16 Bytes */
define symbol m_data_noinit_start    = 0x20003FF0;
define symbol m_data_noinit_end      = 0x20003FFF;

/* Stack space: 512 Bytes */
/* Stack & Heap Sizes */
if (isdefinedsymbol(__stack_size__)) {
  define symbol __size_cstack__        = __stack_size__;
} else {
  define symbol __size_cstack__        = 0x00000200;
}

if (isdefinedsymbol(__heap_size__)) {
  define symbol __size_heap__          = __heap_size__;
} else {
  define symbol __size_heap__          = 0x00000000;
}

define exported symbol __VECTOR_TABLE          = m_interrupts_start;
define exported symbol __VECTOR_RAM            = isdefinedsymbol(__flash_vector_table__) ? m_interrupts_start : m_interrupts_ram_start;
define exported symbol __RAM_VECTOR_TABLE_SIZE = __ram_vector_table_size__;

define exported symbol __RAM_START             = m_interrupts_ram_start;
define exported symbol __RAM_END               = m_data_noinit_end;

define memory mem with size = 4G;

define region m_asw_header_region       = mem:[from m_asw_header_start to m_asw_header_end];

define region m_asw_code_region         = mem:[from m_interrupts_start to m_interrupts_end]
                                        | mem:[from m_asw_code_start to m_asw_code_end];
  
define region m_asw_tail_region          = mem:[from m_asw_tail_start to m_asw_tail_end]; 
define region m_asw_crc_region          = mem:[from m_asw_crc_start to m_asw_crc_end];
                                        
define region DATA_region               = mem:[from m_data_start to m_data_end];

define region DATA_noinit_region        = mem:[from m_data_noinit_start to m_data_noinit_end];

define region DATA_region_2             = mem:[from m_data_2_start to m_data_2_end-__size_cstack__];
define region CSTACK_region             = mem:[from m_data_2_end-__size_cstack__+1 to m_data_2_end];
define region m_interrupts_ram_region   = mem:[from m_interrupts_ram_start to m_interrupts_ram_end];


define block CSTACK    with alignment = 8, size = __size_cstack__   { };
define block HEAP      with alignment = 8, size = __size_heap__     { };
define block RW        { readwrite };
define block ZI        { zi };


define block customSectionBlock { section .customSection };

define block __CODE_ROM   { section .textrw_init };
define block __CODE_RAM   { section .textrw  };

initialize manually       { section .textrw };
initialize manually       { section .bss, section .bss.no_init};
initialize manually       { section .customSection, section .code_ram};
initialize manually       { section .data};
initialize manually       { section __DLIB_PERTHREAD };

do not initialize         { section .no_init, section .bss, section .data, section __DLIB_PERTHREAD, section .customSection};

place at address mem: m_interrupts_start    { readonly section .intvec };
place in m_asw_code_region                  { readonly };
place in m_asw_code_region                  { block __CODE_ROM };
place in DATA_region                        { block RW };
place in DATA_region                        { block __CODE_RAM };
place in DATA_region_2                      { first block customSectionBlock };
place in DATA_region_2                      { block ZI };
place in DATA_region_2                      { last block HEAP };
place in CSTACK_region                      { block CSTACK };
place in m_interrupts_ram_region            { section m_interrupts_ram };
place in DATA_noinit_region                 { readwrite section .bss.no_init };
place in m_asw_header_region                { readonly section .asw_header};
place in m_asw_tail_region                  { readonly section .asw_tail};
place in m_asw_crc_region                   { readonly section .checksum};

