1/* 2 * Copyright (c) 2011-2014, Wind River Systems, Inc. 3 * Copyright (c) 2019-2020 Intel Corp. 4 * 5 * SPDX-License-Identifier: Apache-2.0 6 */ 7 8/** 9 * @file Directives for linker MEMORY regions for all x86 10 * 11 * By default, the kernel is linked at its physical address and all addresses 12 * are in RAM. 13 * 14 * If CONFIG_XIP is enabled, then another MEMORY region is declared for ROM, 15 * and this is where the Zephyr image is booted from. The linker LMAs and VMAs 16 * are set up, such that read/write data/bss have their VMA addresses 17 * in RAM and are copied from flash at boot. Text/rodata linked in-place in 18 * flash. 19 * 20 * If CONFIG_MMU is enabled, then the ROM region in MEMORY is used to set the 21 * LMA for all sections relative to physical address. The virtual address VMAs 22 * for all sections are relative to the base virtual address for the kernel. 23 * Setting LMAs here helps let QEMU or any other ELF-aware loader know where to 24 * physically load the image. 25 */ 26 27#ifndef ARCH_X86_MEMORY_LD 28#define ARCH_X86_MEMORY_LD 29 30#include <zephyr/devicetree.h> 31#include <zephyr/linker/devicetree_regions.h> 32#include <zephyr/kernel/mm.h> 33 34/* Bounds of physical RAM from DTS */ 35#define PHYS_RAM_ADDR DT_REG_ADDR(DT_CHOSEN(zephyr_sram)) 36#define PHYS_RAM_SIZE DT_REG_SIZE(DT_CHOSEN(zephyr_sram)) 37 38/* Virtual base address for the kernel; with CONFIG_MMU this is not necessarily 39 * the same as its physical location, although an identity mapping for RAM 40 * is still supported by setting CONFIG_KERNEL_VM_BASE=CONFIG_SRAM_BASE_ADDRESS. 41 */ 42#ifdef K_MEM_IS_VM_KERNEL 43#define KERNEL_BASE_ADDR (CONFIG_KERNEL_VM_BASE + CONFIG_KERNEL_VM_OFFSET) 44#define KERNEL_RAM_SIZE (CONFIG_KERNEL_VM_SIZE - CONFIG_KERNEL_VM_OFFSET) 45#define PHYS_RAM_AVAIL (PHYS_RAM_SIZE - CONFIG_SRAM_OFFSET) 46#else 47#define KERNEL_BASE_ADDR (PHYS_RAM_ADDR + CONFIG_SRAM_OFFSET) 48#define KERNEL_RAM_SIZE (PHYS_RAM_SIZE - CONFIG_SRAM_OFFSET) 49#endif 50 51/* "kernel RAM" for linker VMA allocations starts at the offset */ 52 53#if defined(CONFIG_ROM_END_OFFSET) 54#define ROM_END_OFFSET CONFIG_ROM_END_OFFSET 55#else 56#define ROM_END_OFFSET 0 57#endif 58 59#ifdef CONFIG_XIP 60 /* "ROM" is flash, we leave rodata and text there and just copy in data. 61 * Board-level DTS must specify a flash region that doesn't overlap with 62 * sram0, so that DT_PHYS_LOAD_ADDR is set. 63 */ 64 #define FLASH_ROM_SIZE (DT_REG_SIZE(DT_CHOSEN(zephyr_flash)) - ROM_END_OFFSET) 65 #define PHYS_LOAD_ADDR DT_REG_ADDR(DT_CHOSEN(zephyr_flash)) 66#else 67 /* Physical RAM location where the kernel image is loaded */ 68 #define PHYS_LOAD_ADDR (PHYS_RAM_ADDR + CONFIG_SRAM_OFFSET) 69#endif /* CONFIG_XIP */ 70 71#ifdef CONFIG_X86_64 72/* Locore must be addressable by real mode and so cannot extend past 64K. 73 * Skip reserved stuff in the first page 74 */ 75#define LOCORE_BASE 0x1000 76#define LOCORE_SIZE (0x10000 - LOCORE_BASE) 77 78#if PHYS_RAM_ADDR != CONFIG_KERNEL_VM_BASE 79#error Virtual kernel linking is not yet implemented for 64-bit 80#endif 81#endif /* CONFIG_X86_64 */ 82 83MEMORY 84 { 85#if defined(CONFIG_XIP) 86 /* Address range where the kernel will be installed on a flash part (XIP), 87 * or copied into physical RAM by a loader (MMU) 88 */ 89 ROM (rx) : ORIGIN = PHYS_LOAD_ADDR, LENGTH = FLASH_ROM_SIZE 90#elif defined(K_MEM_IS_VM_KERNEL) 91 ROM (rx) : ORIGIN = PHYS_LOAD_ADDR, LENGTH = PHYS_RAM_AVAIL 92#endif 93 /* Linear address range to link the kernel. If non-XIP, everything is 94 * linked in this space. Otherwise, rodata and text are linked at their 95 * physical ROM locations 96 */ 97 RAM (wx) : ORIGIN = KERNEL_BASE_ADDR, LENGTH = KERNEL_RAM_SIZE 98 LINKER_DT_REGIONS() 99 100#ifdef CONFIG_X86_64 101 /* Special low-memory area for bootstrapping other CPUs from real mode */ 102 LOCORE (wx) : ORIGIN = LOCORE_BASE, LENGTH = LOCORE_SIZE 103#else 104 /* 105 * On 32-bit x86, fake memory area for build-time IDT generation data. 106 * 64-bit doesn't use this, interrupts are all managed at runtime. 107 * 108 * It doesn't matter where this region goes as it is stripped from the 109 * final ELF image. The address doesn't even have to be valid on the 110 * target. However, it shouldn't overlap any other regions. 111 */ 112 113 IDT_LIST : ORIGIN = 0xFFFF1000, LENGTH = 2K 114#endif /* !CONFIG_X86_64 */ 115 } 116#endif /* ARCH_X86_MEMORY_LD */ 117