1# SPDX-License-Identifier: Apache-2.0 2 3set_property(TARGET linker PROPERTY devices_start_symbol "Image$$device$$Base") 4 5find_program(CMAKE_LINKER ${CROSS_COMPILE}armlink PATHS ${TOOLCHAIN_HOME} NO_DEFAULT_PATH) 6 7add_custom_target(armlink) 8 9function(toolchain_ld_force_undefined_symbols) 10 foreach(symbol ${ARGN}) 11 zephyr_link_libraries(--undefined=${symbol}) 12 endforeach() 13endfunction() 14 15macro(configure_linker_script linker_script_gen linker_pass_define) 16 set(STEERING_FILE) 17 set(STEERING_C) 18 set(STEERING_FILE_ARG) 19 set(STEERING_C_ARG) 20 set(linker_pass_define_list ${linker_pass_define}) 21 set(cmake_linker_script_settings 22 ${PROJECT_BINARY_DIR}/include/generated/ld_script_settings_${linker_pass_define}.cmake 23 ) 24 25 if("LINKER_ZEPHYR_FINAL" IN_LIST linker_pass_define_list) 26 set(STEERING_FILE ${CMAKE_CURRENT_BINARY_DIR}/armlink_symbol_steering.steer) 27 set(STEERING_C ${CMAKE_CURRENT_BINARY_DIR}/armlink_symbol_steering.c) 28 set(STEERING_FILE_ARG "-DSTEERING_FILE=${STEERING_FILE}") 29 set(STEERING_C_ARG "-DSTEERING_C=${STEERING_C}") 30 endif() 31 32 file(GENERATE OUTPUT ${cmake_linker_script_settings} CONTENT 33 "set(FORMAT \"$<TARGET_PROPERTY:linker,FORMAT>\" CACHE INTERNAL \"\")\n 34 set(ENTRY \"$<TARGET_PROPERTY:linker,ENTRY>\" CACHE INTERNAL \"\")\n 35 set(MEMORY_REGIONS \"$<TARGET_PROPERTY:linker,MEMORY_REGIONS>\" CACHE INTERNAL \"\")\n 36 set(GROUPS \"$<TARGET_PROPERTY:linker,GROUPS>\" CACHE INTERNAL \"\")\n 37 set(SECTIONS \"$<TARGET_PROPERTY:linker,SECTIONS>\" CACHE INTERNAL \"\")\n 38 set(SECTION_SETTINGS \"$<TARGET_PROPERTY:linker,SECTION_SETTINGS>\" CACHE INTERNAL \"\")\n 39 set(SYMBOLS \"$<TARGET_PROPERTY:linker,SYMBOLS>\" CACHE INTERNAL \"\")\n 40 " 41 ) 42 add_custom_command( 43 OUTPUT ${linker_script_gen} 44 ${STEERING_FILE} 45 ${STEERING_C} 46 COMMAND ${CMAKE_COMMAND} 47 -C ${DEVICE_API_LINKER_SECTIONS_CMAKE} 48 -C ${cmake_linker_script_settings} 49 -DPASS="${linker_pass_define}" 50 ${STEERING_FILE_ARG} 51 ${STEERING_C_ARG} 52 -DOUT_FILE=${CMAKE_CURRENT_BINARY_DIR}/${linker_script_gen} 53 -P ${ZEPHYR_BASE}/cmake/linker/armlink/scatter_script.cmake 54 DEPENDS ${DEVICE_API_LD_TARGET} 55 ) 56 57 if("LINKER_ZEPHYR_FINAL" IN_LIST linker_pass_define_list) 58 add_library(armlink_steering OBJECT ${STEERING_C}) 59 target_link_libraries(armlink_steering PRIVATE zephyr_interface) 60 endif() 61endmacro() 62 63function(toolchain_ld_link_elf) 64 cmake_parse_arguments( 65 TOOLCHAIN_LD_LINK_ELF # prefix of output variables 66 "" # list of names of the boolean arguments 67 "TARGET_ELF;OUTPUT_MAP;LINKER_SCRIPT" # list of names of scalar arguments 68 "LIBRARIES_PRE_SCRIPT;LIBRARIES_POST_SCRIPT;DEPENDENCIES" # list of names of list arguments 69 ${ARGN} # input args to parse 70 ) 71 72 foreach(lib ${ZEPHYR_LIBS_PROPERTY}) 73 if(NOT ${lib} STREQUAL arch__arm__core__cortex_m) 74 list(APPEND ZEPHYR_LIBS_OBJECTS $<TARGET_OBJECTS:${lib}>) 75 list(APPEND ZEPHYR_LIBS_OBJECTS $<TARGET_PROPERTY:${lib},LINK_LIBRARIES>) 76 endif() 77 endforeach() 78 79 target_link_libraries( 80 ${TOOLCHAIN_LD_LINK_ELF_TARGET_ELF} 81 ${TOOLCHAIN_LD_LINK_ELF_LIBRARIES_PRE_SCRIPT} 82 --scatter=${TOOLCHAIN_LD_LINK_ELF_LINKER_SCRIPT} 83 ${TOOLCHAIN_LD_LINK_ELF_LIBRARIES_POST_SCRIPT} 84 $<TARGET_OBJECTS:arch__arm__core__cortex_m> 85 --map --list=${TOOLCHAIN_LD_LINK_ELF_OUTPUT_MAP} 86 ${ZEPHYR_LIBS_OBJECTS} 87 kernel 88 $<TARGET_OBJECTS:${OFFSETS_LIB}> 89 --library_type=microlib 90 --entry=$<TARGET_PROPERTY:linker,ENTRY> 91 "--keep=\"*.o(.init_*)\"" 92 "--keep=\"*.o(.device_*)\"" 93 $<TARGET_OBJECTS:armlink_steering> 94 --edit=${CMAKE_CURRENT_BINARY_DIR}/armlink_symbol_steering.steer 95 # Resolving symbols using generated steering files will emit the warnings 6331 and 6332. 96 # Steering files are used because we want to be able to use `__device_end` instead of `Image$$device$$Limit`. 97 # Thus silence those two warnings. 98 --diag_suppress=6331,6332 99 # The scatter file is generated, and thus sometimes input sections are specified 100 # even though there will be no such sections found in the libraries linked. 101 --diag_suppress=6314 102 # We use empty execution sections in order to define custom symbols, such as 103 # __kernel_ram_x symbols, but nothing will go in those section, so silence 104 # the warning. Note, marking the section EMPTY causes armlink to reserve the 105 # address which in some cases leads to overlapping section errors. 106 --diag_suppress=6312 107 # Use of '.gnu.linkonce' sections. Those are used by ld, and # supported by armlink, albeit 108 # deprecated there. For current ARMClang support phase, we accept this warning, but we should 109 # look into changing to COMDAT groups. 110 --diag_suppress=6092 111 # Wildcard matching of keep sections, Those are needed for gnu ld, and thus we inherit the same 112 # keep flags and apply them to armlink. Consider adjusting keep flags per linker in future. 113 --diag_suppress=6319 114 # Match pattern for an unused section that is being removed. 115 --diag_suppress=6329 116 ${TOOLCHAIN_LIBS_OBJECTS} 117 118 ${TOOLCHAIN_LD_LINK_ELF_DEPENDENCIES} 119 ) 120endfunction(toolchain_ld_link_elf) 121 122# This function will generate the correct CMAKE_C_LINK_EXECUTABLE / CMAKE_CXX_LINK_EXECUTABLE 123# rule to ensure that standard c and runtime libraries are correctly placed 124# and the end of link invocation and doesn't appear in the middle of the link 125# command invocation. 126macro(toolchain_linker_finalize) 127 set(zephyr_std_libs) 128 get_property(link_order TARGET linker PROPERTY link_order_library) 129 foreach(lib ${link_order}) 130 get_property(link_flag TARGET linker PROPERTY ${lib}_library) 131 set(zephyr_std_libs "${zephyr_std_libs} ${link_flag}") 132 endforeach() 133 134 set(common_link "<LINK_FLAGS> <LINK_LIBRARIES> <OBJECTS> ${zephyr_std_libs} -o <TARGET>") 135 set(CMAKE_C_LINK_EXECUTABLE "<CMAKE_LINKER> <CMAKE_C_LINK_FLAGS> ${common_link}") 136 set(CMAKE_CXX_LINK_EXECUTABLE "<CMAKE_LINKER> <CMAKE_CXX_LINK_FLAGS> ${common_link}") 137 set(CMAKE_ASM_LINK_EXECUTABLE "<CMAKE_LINKER> <CMAKE_ASM_LINK_FLAGS> ${common_link}") 138endmacro() 139 140include(${ZEPHYR_BASE}/cmake/linker/ld/target_relocation.cmake) 141include(${ZEPHYR_BASE}/cmake/linker/ld/target_configure.cmake) 142