blob: c8e86e3f9e489f77587687189853531b095a64c0 [file] [log] [blame]
/*
* Copyright (c) 2013-2014 Wind River Systems, Inc.
* Copyright (c) 2016-2017 Jean-Paul Etienne <fractalclone@gmail.com>
* Copyright (c) 2018 Foundries.io Ltd
*
* This file is based on:
*
* - include/arch/arm/cortex_m/scripts/linker.ld
* - include/arch/riscv/common/linker.ld
* - include/arch/riscv/pulpino/linker.ld
*
* SPDX-License-Identifier: Apache-2.0
*/
#define _LINKER
#define _ASMLANGUAGE
#include <generated_dts_board.h>
#include <autoconf.h>
#include <linker/sections.h>
#include <linker/linker-defs.h>
#include <linker/linker-tool.h>
/*
* Extra efforts would need to be taken to ensure the IRQ handlers are within
* jumping distance of the vector table in non-XIP builds, so avoid them.
*/
#define ROMABLE_REGION ROM
#define RAMABLE_REGION RAM
#define VECTOR_SIZE CONFIG_RISCV_RV32M1_VECTOR_SIZE
#ifdef CONFIG_USE_CODE_PARTITION
#ifdef CONFIG_BOOTLOADER_MCUBOOT
#define ROM_BASE (DT_CODE_PARTITION_OFFSET)
#define ROM_SIZE (DT_CODE_PARTITION_SIZE)
#define VECTOR_BASE (ROM_BASE + CONFIG_TEXT_SECTION_OFFSET)
#else
#define ROM_BASE DT_CODE_PARTITION_OFFSET
#define ROM_SIZE (DT_CODE_PARTITION_SIZE - VECTOR_SIZE)
#define VECTOR_BASE (ROM_BASE + ROM_SIZE)
#endif
#else
#define ROM_BASE DT_FLASH_BASE_ADDRESS
#define ROM_SIZE (KB(DT_FLASH_SIZE) - VECTOR_SIZE)
#define VECTOR_BASE (ROM_BASE + ROM_SIZE)
#endif
#define RAM_BASE DT_SRAM_BASE_ADDRESS
#define RAM_SIZE KB(DT_SRAM_SIZE)
MEMORY
{
ROM (rx) : ORIGIN = ROM_BASE, LENGTH = ROM_SIZE
/*
* Each RISC-V core on this chip (RI5CY and ZERO-RISCY) has
* a vector table at the end of its flash bank. They are relocatable
* at runtime, but we need to put the reset vectors in hardcoded places.
*
* (The Arm core vector tables are at the beginning of each
* flash bank.)
*/
#ifndef CONFIG_BOOTLOADER_MCUBOOT
VECTORS (rx) : ORIGIN = VECTOR_BASE, LENGTH = VECTOR_SIZE
#endif
RAM (rwx) : ORIGIN = RAM_BASE, LENGTH = RAM_SIZE
/*
* Special section, not included in the final binary, used
* to generate interrupt tables. See include/linker/intlist.ld.
*/
IDT_LIST (wx) : ORIGIN = 0xFFFFF7FF, LENGTH = 2K
}
ENTRY(CONFIG_KERNEL_ENTRY)
SECTIONS
{
#include <linker/rel-sections.ld>
SECTION_PROLOGUE(.plt,,)
{
*(.plt)
}
SECTION_PROLOGUE(.iplt,,)
{
*(.iplt)
}
GROUP_START(ROM)
_image_rom_start = ROM_BASE;
SECTION_PROLOGUE(_TEXT_SECTION_NAME,,)
{
. = CONFIG_TEXT_SECTION_OFFSET;
. = ALIGN(4);
/*
* Respect for CONFIG_TEXT_SECTION_OFFSET is mandatory
* for MCUboot support, so .reset.* and .exception.*
* must come after that offset from ROM_BASE.
*/
#ifdef CONFIG_BOOTLOADER_MCUBOOT
/*
* For CONFIG_BOOTLOADER_MCUBOOT, the vector table is located at the
* end of the image header of the MCUboot. After the tagert image is
* boot, the register Machine Trap-Vector Base Address (MTVEC) is
* set with the value of _vector_start in the reset handler.
*/
_vector_start = .;
KEEP(*(.vectors.*))
_vector_end = .;
. = ALIGN(4);
#endif
KEEP(*(.reset.*))
KEEP(*(".exception.entry.*")) /* contains __irq_wrapper */
*(".exception.other.*")
KEEP(*(.openocd_debug))
KEEP(*(".openocd_debug.*"))
_image_text_start = .;
*(.text .text.*)
*(.gnu.linkonce.t.*)
*(.eh_frame)
} GROUP_LINK_IN(ROM)
_image_text_end = .;
_image_rodata_start = .;
#include <linker/common-rom.ld>
SECTION_PROLOGUE(_RODATA_SECTION_NAME,,)
{
. = ALIGN(4);
*(.srodata)
*(".srodata.*")
*(.rodata)
*(.rodata.*)
*(.gnu.linkonce.r.*)
/* Located in generated directory. This file is populated by the
* zephyr_linker_sources() Cmake function.
*/
#include <snippets-rodata.ld>
} GROUP_LINK_IN(ROMABLE_REGION)
#include <linker/cplusplus-rom.ld>
_image_rodata_end = .;
_image_rom_end = .;
#ifndef CONFIG_BOOTLOADER_MCUBOOT
/* The vector table goes into core-dependent flash locations. */
SECTION_PROLOGUE(vectors,,)
{
_vector_start = .;
KEEP(*(.vectors.*))
} GROUP_LINK_IN(VECTORS)
_vector_end = .;
#endif
GROUP_END(ROM)
GROUP_START(RAM)
SECTION_DATA_PROLOGUE(_DATA_SECTION_NAME,,)
{
. = ALIGN(4);
_image_ram_start = .;
__data_ram_start = .;
*(.data)
*(.data.*)
*(.gnu.linkonce.s.*)
/* https://groups.google.com/a/groups.riscv.org/d/msg/sw-dev/60IdaZj27dY/TKT3hbNlAgAJ */
*(.sdata .sdata.* .gnu.linkonce.s.*)
*(.sdata2 .sdata2.* .gnu.linkonce.s2.*)
/* Located in generated directory. This file is populated by the
* zephyr_linker_sources() Cmake function.
*/
#include <snippets-rwdata.ld>
} GROUP_DATA_LINK_IN(RAMABLE_REGION, ROMABLE_REGION)
#include <linker/common-ram.ld>
#include <linker/cplusplus-ram.ld>
__data_ram_end = .;
__data_rom_start = LOADADDR(_DATA_SECTION_NAME);
SECTION_DATA_PROLOGUE(_BSS_SECTION_NAME,(NOLOAD),)
{
/*
* For performance, BSS section is assumed to be 4 byte aligned and
* a multiple of 4 bytes, so it can be cleared in words.
*/
. = ALIGN(4);
__bss_start = .;
*(.bss .bss.*)
*(.sbss .sbss.*)
COMMON_SYMBOLS
/* Ensure 4 byte alignment for the entire section. */
. = ALIGN(4);
__bss_end = .;
} GROUP_DATA_LINK_IN(RAMABLE_REGION, RAMABLE_REGION)
SECTION_PROLOGUE(_NOINIT_SECTION_NAME,(NOLOAD),)
{
/*
* This section is used for non-initialized objects that
* will not be cleared during the boot process.
*/
*(.noinit .noinit.*)
/* Located in generated directory. This file is populated by the
* zephyr_linker_sources() Cmake function.
*/
#include <snippets-noinit.ld>
} GROUP_LINK_IN(RAMABLE_REGION)
/* Located in generated directory. This file is populated by the
* zephyr_linker_sources() Cmake function.
*/
#include <snippets-ram-sections.ld>
_image_ram_end = .;
_end = .; /* end of image */
GROUP_END(RAM)
#ifdef CONFIG_CUSTOM_SECTIONS_LD
/* Located in project source directory */
#include <custom-sections.ld>
#endif
/* Located in generated directory. This file is populated by the
* zephyr_linker_sources() Cmake function.
*/
#include <snippets-sections.ld>
#ifdef CONFIG_GEN_ISR_TABLES
/* Bogus section, post-processed during the build to initialize interrupts. */
#include <linker/intlist.ld>
#endif
#include <linker/debug-sections.ld>
SECTION_PROLOGUE(.riscv.attributes, 0,)
{
KEEP(*(.riscv.attributes))
KEEP(*(.gnu.attributes))
}
/*
* Pulpino toolchains emit these sections; we don't care about them,
* but need to avoid build system warnings about orphaned sections.
*/
SECTION_PROLOGUE(.Pulp_Chip.Info,,)
{
*(.Pulp_Chip.*)
}
}