llext: define add_llext_target() for llext compilation
This patch defines a generic function that encapsulates all the architecture-specific machinery needed to compile llexts from source files. Current tests are updated to use this function. Output and source files must be specified using the OUTPUT and SOURCES arguments. Only one source file is currently supported. Arch-specific flags will be added automatically. The C_FLAGS argument can be used to pass additional compiler flags to the compilation of the source file. Signed-off-by: Luca Burelli <l.burelli@arduino.cc>
This commit is contained in:
parent
3f65552446
commit
0747cd3358
2 changed files with 97 additions and 27 deletions
|
@ -34,6 +34,7 @@ include(CheckCXXCompilerFlag)
|
|||
# 5. Zephyr linker functions
|
||||
# 5.1. zephyr_linker*
|
||||
# 6 Function helper macros
|
||||
# 7 Linkable loadable extensions (llext)
|
||||
|
||||
########################################################
|
||||
# 1. Zephyr-aware extensions
|
||||
|
@ -4792,3 +4793,92 @@ macro(zephyr_check_flags_exclusive function prefix)
|
|||
)
|
||||
endif()
|
||||
endmacro()
|
||||
|
||||
########################################################
|
||||
# 7. Linkable loadable extensions (llext)
|
||||
########################################################
|
||||
#
|
||||
# These functions simplify the creation and management of linkable
|
||||
# loadable extensions (llexts).
|
||||
#
|
||||
|
||||
# Add a custom target that compiles a single source file to a .llext file.
|
||||
#
|
||||
# Output and source files must be specified using the OUTPUT and SOURCES
|
||||
# arguments. Only one source file is currently supported.
|
||||
#
|
||||
# Arch-specific flags will be added automatically. The C_FLAGS argument
|
||||
# can be used to pass additional compiler flags to the compilation of
|
||||
# the source file.
|
||||
#
|
||||
# Example usage:
|
||||
# add_llext_target(hello_world
|
||||
# OUTPUT ${PROJECT_BINARY_DIR}/hello_world.llext
|
||||
# SOURCES ${PROJECT_SOURCE_DIR}/src/llext/hello_world.c
|
||||
# C_FLAGS -Werror
|
||||
# )
|
||||
# will compile the source file src/llext/hello_world.c to a file
|
||||
# ${PROJECT_BINARY_DIR}/hello_world.llext, adding -Werror to the compilation.
|
||||
#
|
||||
function(add_llext_target target_name)
|
||||
set(single_args OUTPUT)
|
||||
set(multi_args SOURCES;C_FLAGS)
|
||||
cmake_parse_arguments(PARSE_ARGV 1 LLEXT "${options}" "${single_args}" "${multi_args}")
|
||||
|
||||
# Check that the llext subsystem is enabled for this build
|
||||
if (NOT CONFIG_LLEXT)
|
||||
message(FATAL_ERROR "add_llext_target: CONFIG_LLEXT must be enabled")
|
||||
endif()
|
||||
|
||||
# Output file must be provided
|
||||
if(NOT LLEXT_OUTPUT)
|
||||
message(FATAL_ERROR "add_llext_target: OUTPUT argument must be provided")
|
||||
endif()
|
||||
|
||||
# Source list length must currently be 1
|
||||
list(LENGTH LLEXT_SOURCES source_count)
|
||||
if(NOT source_count EQUAL 1)
|
||||
message(FATAL_ERROR "add_llext_target: only one source file is supported")
|
||||
endif()
|
||||
|
||||
set(output_file ${LLEXT_OUTPUT})
|
||||
set(source_file ${LLEXT_SOURCES})
|
||||
get_filename_component(output_name ${output_file} NAME)
|
||||
|
||||
# Add user-visible target and dependency
|
||||
add_custom_target(${target_name}
|
||||
COMMENT "Compiling ${output_name}"
|
||||
DEPENDS ${output_file}
|
||||
)
|
||||
|
||||
# Compile the source file to an .llext file
|
||||
if(CONFIG_ARM)
|
||||
list(PREPEND LLEXT_C_FLAGS "-mlong-calls" "-mthumb")
|
||||
add_custom_command(OUTPUT ${output_file}
|
||||
COMMAND ${CMAKE_C_COMPILER} ${LLEXT_C_FLAGS} -c
|
||||
-I ${ZEPHYR_BASE}/include
|
||||
-imacros ${AUTOCONF_H}
|
||||
-o ${output_file}
|
||||
${source_file}
|
||||
DEPENDS ${source_file}
|
||||
)
|
||||
elseif(CONFIG_XTENSA)
|
||||
list(PREPEND LLEXT_C_FLAGS "-shared" "-fPIC" "-nostdlib" "-nodefaultlibs")
|
||||
get_filename_component(output_dir ${output_file} DIRECTORY)
|
||||
get_filename_component(output_name_we ${output_file} NAME_WE)
|
||||
set(pre_output_file ${output_dir}/${output_name_we}.pre.llext)
|
||||
add_custom_command(OUTPUT ${output_file}
|
||||
COMMAND ${CMAKE_C_COMPILER} ${LLEXT_C_FLAGS}
|
||||
-I ${ZEPHYR_BASE}/include
|
||||
-imacros ${AUTOCONF_H}
|
||||
-o ${pre_output_file}
|
||||
${source_file}
|
||||
COMMAND ${CROSS_COMPILE}strip -R .xt.*
|
||||
-o ${output_file}
|
||||
${pre_output_file}
|
||||
DEPENDS ${source_file}
|
||||
)
|
||||
else()
|
||||
message(FATAL_ERROR "add_llext_target: unsupported architecture")
|
||||
endif()
|
||||
endfunction()
|
||||
|
|
|
@ -7,34 +7,14 @@ project(hello_world)
|
|||
|
||||
if(NOT CONFIG_MODULES OR CONFIG_LLEXT_TEST_HELLO STREQUAL "m")
|
||||
|
||||
# TODO check which architecture is being used
|
||||
if(CONFIG_ARM)
|
||||
set(CMAKE_C_FLAGS "-mlong-calls" "-mthumb")
|
||||
set(llext_src_file ${PROJECT_SOURCE_DIR}/hello_world.c)
|
||||
set(llext_bin_file ${PROJECT_BINARY_DIR}/hello_world.llext)
|
||||
|
||||
add_custom_command(OUTPUT ${PROJECT_BINARY_DIR}/hello_world.llext
|
||||
COMMAND ${CMAKE_C_COMPILER} ${CMAKE_C_FLAGS} -c
|
||||
-I ${PROJECT_SOURCE_DIR}/../../../../include
|
||||
-imacros${PROJECT_BINARY_DIR}/../zephyr/include/generated/autoconf.h
|
||||
-o ${PROJECT_BINARY_DIR}/hello_world.llext
|
||||
${PROJECT_SOURCE_DIR}/hello_world.c
|
||||
)
|
||||
elseif(CONFIG_XTENSA)
|
||||
set(CMAKE_C_FLAGS "-shared" "-fPIC" "-nostdlib" "-nodefaultlibs")
|
||||
add_llext_target(hello_world
|
||||
OUTPUT ${llext_bin_file}
|
||||
SOURCES ${llext_src_file}
|
||||
)
|
||||
|
||||
add_custom_command(OUTPUT ${PROJECT_BINARY_DIR}/hello_world.llext
|
||||
COMMAND ${CMAKE_C_COMPILER} ${CMAKE_C_FLAGS}
|
||||
-I ${PROJECT_SOURCE_DIR}/../../../../include
|
||||
-imacros${PROJECT_BINARY_DIR}/../zephyr/include/generated/autoconf.h
|
||||
-o ${PROJECT_BINARY_DIR}/hello_world.pre.llext
|
||||
${PROJECT_SOURCE_DIR}/hello_world.c
|
||||
COMMAND ${CROSS_COMPILE}strip -R .xt.*
|
||||
-o ${PROJECT_BINARY_DIR}/hello_world.llext
|
||||
${PROJECT_BINARY_DIR}/hello_world.pre.llext
|
||||
)
|
||||
endif()
|
||||
|
||||
set(HELLO_WORLD_LLEXT ${PROJECT_BINARY_DIR}/hello_world.llext PARENT_SCOPE)
|
||||
|
||||
add_custom_target(hello_world DEPENDS ${PROJECT_BINARY_DIR}/hello_world.llext)
|
||||
set(HELLO_WORLD_LLEXT ${llext_bin_file} PARENT_SCOPE)
|
||||
|
||||
endif()
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue