Skip to content

Commit

Permalink
cmake: linker generator: group symbol from section
Browse files Browse the repository at this point in the history
The root cause of zephyrproject-rtos#38591 was region symbols being placed before the
section description for data region.

Some region start symbols are placed before section description, other
region start symbols are placed inside the first section in the region
and thus identical to the sections own first symbol.

To support both schemes with the linker generator, a new
`SYMBOL SECTION` argument has been added to the zephyr_linker_group()
function.

The ld_script.cmake linker script generator has been updated to support
the new argument so that generated ld linker script has identical
behavior to the templated ld linker scripts.

Signed-off-by: Torsten Rasmussen <[email protected]>
  • Loading branch information
tejlmand authored and cfriedt committed Sep 24, 2021
1 parent 15e834a commit 57ab034
Show file tree
Hide file tree
Showing 3 changed files with 31 additions and 5 deletions.
15 changes: 12 additions & 3 deletions cmake/extensions.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -3083,8 +3083,8 @@ function(zephyr_linker_dts_memory)
endfunction()

# Usage:
# zephyr_linker_group(NAME <name> [VMA <region|group>] [LMA <region|group>])
# zephyr_linker_group(NAME <name> GROUP <group>)
# zephyr_linker_group(NAME <name> [VMA <region|group>] [LMA <region|group>] [SYMBOL <SECTION>])
# zephyr_linker_group(NAME <name> GROUP <group> [SYMBOL <SECTION>])
#
# Zephyr linker group.
# This function specifies a group inside a memory region or another group.
Expand All @@ -3108,6 +3108,8 @@ endfunction()
# If a group is used then the VMA region of that group will be used.
# LMA <region|group> : Memory region or group to be used for this group.
# GROUP <group> : Place the new group inside the existing group <group>
# SYMBOL <SECTION> : Specify that start symbol of the region should be identical
# to the start address of the first section in the group.
#
# Note: VMA and LMA are mutual exclusive with GROUP
#
Expand Down Expand Up @@ -3153,7 +3155,8 @@ endfunction()
# | |
# +---------------------+
function(zephyr_linker_group)
set(single_args "NAME;GROUP;LMA;VMA")
set(single_args "NAME;GROUP;LMA;SYMBOL;VMA")
set(symbol_values SECTION)
cmake_parse_arguments(GROUP "" "${single_args}" "" ${ARGN})

if(GROUP_UNPARSED_ARGUMENTS)
Expand All @@ -3168,6 +3171,12 @@ function(zephyr_linker_group)
)
endif()

if(DEFINED GROUP_SYMBOL)
if(NOT ${GROUP_SYMBOL} IN_LIST symbol_values)
message(FATAL_ERROR "zephyr_linker_group(SYMBOL ...) given unknown value")
endif()
endif()

set(GROUP)
zephyr_linker_arg_val_list(GROUP "${single_args}")

Expand Down
18 changes: 17 additions & 1 deletion cmake/linker/ld/ld_script.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -98,13 +98,19 @@ function(group_to_string)
set(${STRING_STRING} "${${STRING_STRING}}\n . = ${address};\n\n")
else()
get_property(name GLOBAL PROPERTY ${STRING_OBJECT}_NAME)
get_property(symbol GLOBAL PROPERTY ${STRING_OBJECT}_SYMBOL)
string(TOLOWER ${name} name)
set(${STRING_STRING} "${${STRING_STRING}}\n __${name}_start = .;\n")

get_objects(LIST sections OBJECT ${STRING_OBJECT} TYPE SECTION)
list(GET sections 0 section)
get_property(first_section_name GLOBAL PROPERTY ${section}_NAME)

if(DEFINED first_section_name AND "${symbol}" STREQUAL "SECTION")
set_property(GLOBAL APPEND PROPERTY ${section}_START_SYMBOLS __${name}_start)
else()
set(${STRING_STRING} "${${STRING_STRING}}\n __${name}_start = .;\n")
endif()

set(${STRING_STRING} "${${STRING_STRING}}\n __${name}_size = __${name}_end - __${name}_start;\n")
set(${STRING_STRING} "${${STRING_STRING}}\n __${name}_load_start = LOADADDR(${first_section_name});\n")
endif()
Expand Down Expand Up @@ -178,6 +184,7 @@ function(section_to_string)
get_property(noinit GLOBAL PROPERTY ${STRING_SECTION}_NOINIT)
get_property(nosymbols GLOBAL PROPERTY ${STRING_SECTION}_NOSYMBOLS)
get_property(parent GLOBAL PROPERTY ${STRING_SECTION}_PARENT)
get_property(start_syms GLOBAL PROPERTY ${STRING_SECTION}_START_SYMBOLS)

string(REGEX REPLACE "^[\.]" "" name_clean "${name}")
string(REPLACE "." "_" name_clean "${name_clean}")
Expand All @@ -204,6 +211,11 @@ function(section_to_string)
endif()

set(TEMP "${name} ${address}${type} :${secalign}\n{")

foreach(start_symbol ${start_syms})
set(TEMP "${TEMP}\n ${start_symbol} = .;")
endforeach()

if(NOT nosymbols)
set(TEMP "${TEMP}\n __${name_clean}_start = .;")
endif()
Expand Down Expand Up @@ -273,6 +285,10 @@ function(section_to_string)
set(TEMP "${TEMP}\n __${name_clean}_end = .;")
endif()

if(DEFINED extra_symbol_end)
set(TEMP "${TEMP}\n ${extra_symbol_end} = .;")
endif()

set(TEMP "${TEMP}\n}")

get_property(parent_type GLOBAL PROPERTY ${parent}_OBJ_TYPE)
Expand Down
3 changes: 2 additions & 1 deletion cmake/linker/linker_script_common.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -58,11 +58,12 @@ function(get_parent)
endfunction()

function(create_group)
cmake_parse_arguments(OBJECT "" "GROUP;LMA;NAME;OBJECT;VMA" "" ${ARGN})
cmake_parse_arguments(OBJECT "" "GROUP;LMA;NAME;OBJECT;SYMBOL;VMA" "" ${ARGN})

set_property(GLOBAL PROPERTY GROUP_${OBJECT_NAME} TRUE)
set_property(GLOBAL PROPERTY GROUP_${OBJECT_NAME}_OBJ_TYPE GROUP)
set_property(GLOBAL PROPERTY GROUP_${OBJECT_NAME}_NAME ${OBJECT_NAME})
set_property(GLOBAL PROPERTY GROUP_${OBJECT_NAME}_SYMBOL ${OBJECT_SYMBOL})

if(DEFINED OBJECT_GROUP)
find_object(OBJECT parent NAME ${OBJECT_GROUP})
Expand Down

0 comments on commit 57ab034

Please sign in to comment.