From d329222eb5859a233d054fa2abc85551b486a1ad Mon Sep 17 00:00:00 2001 From: Keith Packard Date: Tue, 9 May 2023 13:57:04 -0700 Subject: [PATCH] include/zephyr: Fix linker scripts to define _end after all static RAM data The Zephyr linker scripts have inconsistent ordering of various chunks of data which lands in RAM at runtime. This leads to the value of _end not being consistently defined as the maximum address of static variables used in the application. Create a helper linker fragment, zephyr/linker/ram-end.ld, which can be included after the last possible definition of RAM data, that consistently sets _image_ram_end, _end and z_mapped_end. Signed-off-by: Keith Packard (cherry picked from commit 710422ec5e57e6b88d0821a31cee30fcc194094c) --- boards/x86/qemu_x86/qemu_x86_tiny.ld | 11 ++++++----- include/zephyr/arch/arc/v2/linker.ld | 8 ++++---- .../arm/aarch32/cortex_a_r/scripts/linker.ld | 13 ++++++------- .../arm/aarch32/cortex_m/scripts/linker.ld | 9 ++++----- include/zephyr/arch/arm64/scripts/linker.ld | 12 ++++++------ include/zephyr/arch/mips/linker.ld | 7 ++++--- include/zephyr/arch/nios2/linker.ld | 10 ++++------ include/zephyr/arch/riscv/common/linker.ld | 11 +++++------ include/zephyr/arch/sparc/linker.ld | 7 ++++--- include/zephyr/arch/x86/ia32/linker.ld | 8 ++++---- include/zephyr/arch/x86/intel64/linker.ld | 10 ++++++---- include/zephyr/linker/ram-end.ld | 14 ++++++++++++++ soc/arm64/nxp_imx/mimx9/linker.ld | 19 +++++++++---------- soc/riscv/openisa_rv32m1/linker.ld | 9 ++++----- soc/riscv/riscv-ite/it8xxx2/linker.ld | 11 +++++------ .../riscv-privileged/andes_v5/ae350/linker.ld | 11 +++++------ soc/xtensa/intel_adsp/ace/ace-link.ld | 2 ++ 17 files changed, 92 insertions(+), 80 deletions(-) create mode 100644 include/zephyr/linker/ram-end.ld diff --git a/boards/x86/qemu_x86/qemu_x86_tiny.ld b/boards/x86/qemu_x86/qemu_x86_tiny.ld index aea569b85fe3ff..c53e2a7b409804 100644 --- a/boards/x86/qemu_x86/qemu_x86_tiny.ld +++ b/boards/x86/qemu_x86/qemu_x86_tiny.ld @@ -788,14 +788,9 @@ SECTIONS __kernel_ram_end = KERNEL_BASE_ADDR + KERNEL_RAM_SIZE; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; - _image_ram_end = .; _image_ram_all = (KERNEL_BASE_ADDR + KERNEL_RAM_SIZE) - _image_ram_start; - z_mapped_end = .; z_mapped_size = z_mapped_end - z_mapped_start; - _end = .; /* end of image */ - - GROUP_END(RAMABLE_REGION) #ifndef LINKER_ZEPHYR_FINAL /* static interrupts */ @@ -823,6 +818,12 @@ SECTIONS */ #include +#define LAST_RAM_ALIGN MMU_PAGE_ALIGN + +#include + + GROUP_END(RAMABLE_REGION) + #include /DISCARD/ : { *(.note.GNU-stack) } diff --git a/include/zephyr/arch/arc/v2/linker.ld b/include/zephyr/arch/arc/v2/linker.ld index d33866370dafcc..a7751d961194e6 100644 --- a/include/zephyr/arch/arc/v2/linker.ld +++ b/include/zephyr/arch/arc/v2/linker.ld @@ -246,8 +246,6 @@ SECTIONS { MPU_MIN_SIZE_ALIGN /* Define linker symbols */ - _image_ram_end = .; - _end = .; /* end of image */ __kernel_ram_end = .; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; @@ -278,13 +276,15 @@ SECTIONS { } GROUP_DATA_LINK_IN(YCCM, RAMABLE_REGION) #endif - GROUP_END(RAMABLE_REGION) - /* Located in generated directory. This file is populated by the * zephyr_linker_sources() Cmake function. */ #include +#include + + GROUP_END(RAMABLE_REGION) + #include SECTION_PROLOGUE(.ARC.attributes, 0,) { diff --git a/include/zephyr/arch/arm/aarch32/cortex_a_r/scripts/linker.ld b/include/zephyr/arch/arm/aarch32/cortex_a_r/scripts/linker.ld index fb206d8d7e6f73..a27dd55a8cf29a 100644 --- a/include/zephyr/arch/arm/aarch32/cortex_a_r/scripts/linker.ld +++ b/include/zephyr/arch/arm/aarch32/cortex_a_r/scripts/linker.ld @@ -332,16 +332,9 @@ SECTIONS /* Define linker symbols */ - . = ALIGN(_region_min_align); - _image_ram_end = .; - _end = .; /* end of image */ - z_mapped_end = .; - __kernel_ram_end = RAM_ADDR + RAM_SIZE; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; - GROUP_END(RAMABLE_REGION) - #if DT_NODE_HAS_STATUS(DT_CHOSEN(zephyr_ocm), okay) GROUP_START(OCM) @@ -373,6 +366,12 @@ GROUP_END(OCM) */ #include +#define LAST_RAM_ALIGN . = ALIGN(_region_min_align); + +#include + + GROUP_END(RAMABLE_REGION) + #include SECTION_PROLOGUE(.ARM.attributes, 0,) diff --git a/include/zephyr/arch/arm/aarch32/cortex_m/scripts/linker.ld b/include/zephyr/arch/arm/aarch32/cortex_m/scripts/linker.ld index 567e213fe6d158..b170b514a9cea6 100644 --- a/include/zephyr/arch/arm/aarch32/cortex_m/scripts/linker.ld +++ b/include/zephyr/arch/arm/aarch32/cortex_m/scripts/linker.ld @@ -361,14 +361,9 @@ SECTIONS /* Define linker symbols */ - _image_ram_end = .; - _end = .; /* end of image */ - __kernel_ram_end = RAM_ADDR + RAM_SIZE; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; - GROUP_END(RAMABLE_REGION) - #if DT_NODE_HAS_STATUS(DT_CHOSEN(zephyr_itcm), okay) GROUP_START(ITCM) @@ -426,6 +421,10 @@ GROUP_END(DTCM) */ #include +#include + + GROUP_END(RAMABLE_REGION) + #include /DISCARD/ : { *(.note.GNU-stack) } diff --git a/include/zephyr/arch/arm64/scripts/linker.ld b/include/zephyr/arch/arm64/scripts/linker.ld index 5500e8c1386434..fa08b730304785 100644 --- a/include/zephyr/arch/arm64/scripts/linker.ld +++ b/include/zephyr/arch/arm64/scripts/linker.ld @@ -295,21 +295,21 @@ SECTIONS /* Define linker symbols */ - MMU_ALIGN; - _image_ram_end = .; - _end = .; /* end of image */ - z_mapped_end = .; - __kernel_ram_end = RAM_ADDR + RAM_SIZE; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; - GROUP_END(RAMABLE_REGION) /* Located in generated directory. This file is populated by the * zephyr_linker_sources() Cmake function. */ #include +#define LAST_RAM_ALIGN MMU_ALIGN; + +#include + + GROUP_END(RAMABLE_REGION) + #include SECTION_PROLOGUE(.ARM.attributes, 0,) diff --git a/include/zephyr/arch/mips/linker.ld b/include/zephyr/arch/mips/linker.ld index 8bc91ee114f428..cbff890822c723 100644 --- a/include/zephyr/arch/mips/linker.ld +++ b/include/zephyr/arch/mips/linker.ld @@ -181,14 +181,15 @@ SECTIONS #include - _image_ram_end = .; - _end = .; /* end of image */ - /* Located in generated directory. This file is populated by the * zephyr_linker_sources() Cmake function. */ #include +#include + + GROUP_END(RAMABLE_REGION) + #include .mdebug.abi32 : { diff --git a/include/zephyr/arch/nios2/linker.ld b/include/zephyr/arch/nios2/linker.ld index 1814302c2a6416..6958533eaf6b53 100644 --- a/include/zephyr/arch/nios2/linker.ld +++ b/include/zephyr/arch/nios2/linker.ld @@ -259,17 +259,15 @@ SECTIONS #include - /* Define linker symbols */ - _image_ram_end = .; - _end = .; /* end of image */ - - GROUP_END(RAMABLE_REGION) - /* Located in generated directory. This file is populated by the * zephyr_linker_sources() Cmake function. */ #include +#include + + GROUP_END(RAMABLE_REGION) + #include } diff --git a/include/zephyr/arch/riscv/common/linker.ld b/include/zephyr/arch/riscv/common/linker.ld index 181cf553186fbb..3dbec5f0a201e1 100644 --- a/include/zephyr/arch/riscv/common/linker.ld +++ b/include/zephyr/arch/riscv/common/linker.ld @@ -305,11 +305,6 @@ SECTIONS __data_region_end = .; - MPU_MIN_SIZE_ALIGN - - _image_ram_end = .; - _end = .; /* end of image */ - __kernel_ram_end = .; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; @@ -370,7 +365,11 @@ GROUP_END(DTCM) */ #include - GROUP_END(RAMABLE_REGION) +#define LAST_RAM_ALIGN MPU_MIN_SIZE_ALIGN + +#include + + GROUP_END(RAMABLE_REGION) #include diff --git a/include/zephyr/arch/sparc/linker.ld b/include/zephyr/arch/sparc/linker.ld index 36e884302e45d5..725339ef0b7cd8 100644 --- a/include/zephyr/arch/sparc/linker.ld +++ b/include/zephyr/arch/sparc/linker.ld @@ -154,14 +154,15 @@ SECTIONS #include - _image_ram_end = .; - _end = .; /* end of image */ - /* Located in generated directory. This file is populated by the * zephyr_linker_sources() Cmake function. */ #include +#include + + GROUP_END(RAMABLE_REGION) + #include /DISCARD/ : { *(.note.GNU-stack) } diff --git a/include/zephyr/arch/x86/ia32/linker.ld b/include/zephyr/arch/x86/ia32/linker.ld index 1305860ee70cbd..c6db8f8ae75e8a 100644 --- a/include/zephyr/arch/x86/ia32/linker.ld +++ b/include/zephyr/arch/x86/ia32/linker.ld @@ -503,14 +503,10 @@ SECTIONS __kernel_ram_end = KERNEL_BASE_ADDR + KERNEL_RAM_SIZE; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; - _image_ram_end = .; _image_ram_all = (KERNEL_BASE_ADDR + KERNEL_RAM_SIZE) - _image_ram_start; z_mapped_end = .; z_mapped_size = z_mapped_end - z_mapped_start; - _end = .; /* end of image */ - - GROUP_END(RAMABLE_REGION) #ifndef LINKER_ZEPHYR_FINAL /* static interrupts */ @@ -538,6 +534,10 @@ SECTIONS */ #include +#include + + GROUP_END(RAMABLE_REGION) + #include /DISCARD/ : { *(.note.GNU-stack) } diff --git a/include/zephyr/arch/x86/intel64/linker.ld b/include/zephyr/arch/x86/intel64/linker.ld index f2fd47ad54ea30..8949b94e657fdf 100644 --- a/include/zephyr/arch/x86/intel64/linker.ld +++ b/include/zephyr/arch/x86/intel64/linker.ld @@ -192,10 +192,12 @@ SECTIONS /* Must be last in RAM */ #include - MMU_PAGE_ALIGN - _image_ram_end = .; - z_mapped_end = .; - _end = .; + +#define LAST_RAM_ALIGN MMU_PAGE_ALIGN + +#include + + GROUP_END(RAMABLE_REGION) /* All unused memory also owned by the kernel for heaps */ __kernel_ram_end = KERNEL_BASE_ADDR + KERNEL_RAM_SIZE; diff --git a/include/zephyr/linker/ram-end.ld b/include/zephyr/linker/ram-end.ld new file mode 100644 index 00000000000000..61b06a4ecb6146 --- /dev/null +++ b/include/zephyr/linker/ram-end.ld @@ -0,0 +1,14 @@ +/* + * Added after the very last allocation that might land in RAM to define the various + * end-of-used-memory symbols + */ + + SECTION_PROLOGUE(.last_ram_section,,) + { +#ifdef LAST_RAM_ALIGN + LAST_RAM_ALIGN +#endif + _image_ram_end = .; + _end = .; /* end of image */ + z_mapped_end = .; + } GROUP_NOLOAD_LINK_IN(RAMABLE_REGION, RAMABLE_REGION) diff --git a/soc/arm64/nxp_imx/mimx9/linker.ld b/soc/arm64/nxp_imx/mimx9/linker.ld index 1562fbdaf509c7..102d9f1b0445d8 100644 --- a/soc/arm64/nxp_imx/mimx9/linker.ld +++ b/soc/arm64/nxp_imx/mimx9/linker.ld @@ -312,21 +312,20 @@ SECTIONS /* Define linker symbols */ - MMU_ALIGN; - _image_ram_end = .; - _end = .; /* end of image */ - z_mapped_end = .; - - __kernel_ram_end = RAM_ADDR + RAM_SIZE; - __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; - - GROUP_END(RAMABLE_REGION) - /* Located in generated directory. This file is populated by the * zephyr_linker_sources() Cmake function. */ #include +#define LAST_RAM_ALIGN MMU_ALIGN; + +#include + + GROUP_END(RAMABLE_REGION) + + __kernel_ram_end = RAM_ADDR + RAM_SIZE; + __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; + #include SECTION_PROLOGUE(.ARM.attributes, 0,) diff --git a/soc/riscv/openisa_rv32m1/linker.ld b/soc/riscv/openisa_rv32m1/linker.ld index 1ec6fa4ef4dee6..7ade2d4e8dd3ca 100644 --- a/soc/riscv/openisa_rv32m1/linker.ld +++ b/soc/riscv/openisa_rv32m1/linker.ld @@ -233,16 +233,15 @@ SECTIONS */ #include - _image_ram_end = .; - _end = .; /* end of image */ - - GROUP_END(RAM) - /* Located in generated directory. This file is populated by the * zephyr_linker_sources() Cmake function. */ #include +#include + + GROUP_END(RAMABLE_REGION) + #ifdef CONFIG_GEN_ISR_TABLES /* Bogus section, post-processed during the build to initialize interrupts. */ #include diff --git a/soc/riscv/riscv-ite/it8xxx2/linker.ld b/soc/riscv/riscv-ite/it8xxx2/linker.ld index 2aabe427b007fc..798e1ae6dc3825 100644 --- a/soc/riscv/riscv-ite/it8xxx2/linker.ld +++ b/soc/riscv/riscv-ite/it8xxx2/linker.ld @@ -356,11 +356,6 @@ SECTIONS __data_region_end = .; - MPU_MIN_SIZE_ALIGN - - _image_ram_end = .; - _end = .; /* end of image */ - __kernel_ram_end = .; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; @@ -369,7 +364,11 @@ SECTIONS */ #include - GROUP_END(RAMABLE_REGION) +#define LAST_RAM_ALIGN MPU_MIN_SIZE_ALIGN + +#include + + GROUP_END(RAMABLE_REGION) #include diff --git a/soc/riscv/riscv-privileged/andes_v5/ae350/linker.ld b/soc/riscv/riscv-privileged/andes_v5/ae350/linker.ld index 8e3acde20b18f8..9e613a0d930147 100644 --- a/soc/riscv/riscv-privileged/andes_v5/ae350/linker.ld +++ b/soc/riscv/riscv-privileged/andes_v5/ae350/linker.ld @@ -274,11 +274,6 @@ SECTIONS __data_region_end = .; - MPU_MIN_SIZE_ALIGN - - _image_ram_end = .; - _end = .; /* end of image */ - __kernel_ram_end = .; __kernel_ram_size = __kernel_ram_end - __kernel_ram_start; @@ -339,7 +334,11 @@ GROUP_END(DTCM) */ #include - GROUP_END(RAMABLE_REGION) +#define LAST_RAM_ALIGN MPU_MIN_SIZE_ALIGN + +#include + + GROUP_END(RAMABLE_REGION) #include diff --git a/soc/xtensa/intel_adsp/ace/ace-link.ld b/soc/xtensa/intel_adsp/ace/ace-link.ld index 516e2b7137c2c9..a4aaf6b8087d90 100644 --- a/soc/xtensa/intel_adsp/ace/ace-link.ld +++ b/soc/xtensa/intel_adsp/ace/ace-link.ld @@ -403,6 +403,8 @@ SECTIONS { _unused_ram_start_marker = .; *(.unused_ram_start_marker) *(.unused_ram_start_marker.*) + _end = .; + z_mapped_end = .; } >ram . = L2_SRAM_BASE + L2_SRAM_SIZE;