Skip to content

Commit 0988236

Browse files
authored
Merge pull request #68082 from rintaro/swift-swift-linux
[CMake] Support Macros in Linux
2 parents 2548312 + 0aa0aac commit 0988236

File tree

22 files changed

+266
-110
lines changed

22 files changed

+266
-110
lines changed

CMakeLists.txt

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -794,6 +794,7 @@ include(SwiftConfigureSDK)
794794
include(SwiftComponents)
795795
include(SwiftList)
796796
include(AddPureSwift)
797+
include(SetRPATH)
797798

798799
# Configure swift include, install, build components.
799800
swift_configure_components()
@@ -952,6 +953,12 @@ if(SWIFT_PATH_TO_EARLYSWIFTSYNTAX_BUILD_DIR)
952953
else()
953954
set(SWIFT_SWIFT_PARSER TRUE)
954955
include(${SWIFT_PATH_TO_EARLYSWIFTSYNTAX_TARGETS})
956+
957+
if(SWIFT_HOST_VARIANT_SDK STREQUAL "LINUX" AND NOT BOOTSTRAPPING_MODE STREQUAL "HOSTTOOLS")
958+
# Only "HOSTTOOLS" is supported in Linux when Swift parser integration is enabled.
959+
message(WARNING "Force setting BOOTSTRAPPING=HOSTTOOLS because Swift parser integration is enabled")
960+
set(BOOTSTRAPPING_MODE "HOSTTOOLS")
961+
endif()
955962
endif()
956963
endif()
957964

SwiftCompilerSources/CMakeLists.txt

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -235,7 +235,7 @@ else()
235235
#
236236
# step 1: generate a dummy source file, which just includes all headers
237237
# defined in include/swift/module.modulemap
238-
file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/HeaderDependencies.cpp"
238+
file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/HeaderDependencies.cpp.tmp"
239239
"
240240
#include \"Basic/BridgedSwiftObject.h\"
241241
#include \"Basic/BasicBridging.h\"
@@ -251,6 +251,12 @@ else()
251251
252252
#include \"Parse/RegexParserBridging.h\"
253253
")
254+
add_custom_command(
255+
OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/HeaderDependencies.cpp"
256+
COMMAND ${CMAKE_COMMAND} -E copy_if_different
257+
"${CMAKE_CURRENT_BINARY_DIR}/HeaderDependencies.cpp.tmp"
258+
"${CMAKE_CURRENT_BINARY_DIR}/HeaderDependencies.cpp"
259+
)
254260

255261
# step 2: build a library containing that source file. This library depends on all the included header files.
256262
# The swift modules can now depend on that target.

cmake/modules/AddPureSwift.cmake

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,25 @@ function(_add_host_swift_compile_options name)
6565
_add_host_variant_swift_sanitizer_flags(${name})
6666
endfunction()
6767

68+
function(_set_pure_swift_link_flags name relpath_to_lib_dir)
69+
if(SWIFT_HOST_VARIANT_SDK STREQUAL "LINUX")
70+
# Don't add builder's stdlib RPATH automatically.
71+
target_compile_options(${name} PRIVATE
72+
$<$<COMPILE_LANGUAGE:Swift>:-no-toolchain-stdlib-rpath>
73+
)
74+
75+
set_property(TARGET ${name}
76+
APPEND PROPERTY INSTALL_RPATH
77+
# At runtime, use swiftCore in the current just-built toolchain.
78+
# NOTE: This relies on the ABI being the same as the builder.
79+
"$ORIGIN/${relpath_to_lib_dir}/swift/${SWIFT_SDK_${SWIFT_HOST_VARIANT_SDK}_LIB_SUBDIR}"
80+
)
81+
# NOTE: At this point we don't have any pure swift executables/shared
82+
# libraries required for building runtime/stdlib. So we don't need to add
83+
# RPATH to the builder's runtime.
84+
endif()
85+
endfunction()
86+
6887
# Add a new "pure" Swift host library.
6988
#
7089
# "Pure" Swift host libraries can only contain Swift code, and will be built
@@ -266,6 +285,7 @@ function(add_pure_swift_host_tool name)
266285
# Create the library.
267286
add_executable(${name} ${APSHT_SOURCES})
268287
_add_host_swift_compile_options(${name})
288+
_set_pure_swift_link_flags(${name} "../lib")
269289

270290
if(SWIFT_HOST_VARIANT_SDK IN_LIST SWIFT_DARWIN_PLATFORMS)
271291
set_property(TARGET ${name}

cmake/modules/AddSwift.cmake

Lines changed: 45 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -548,11 +548,11 @@ function(_add_swift_runtime_link_flags target relpath_to_lib_dir bootstrapping)
548548
target_link_libraries(${target} PRIVATE "swiftCore")
549549
550550
target_link_directories(${target} PRIVATE ${host_lib_dir})
551-
if(ASRLF_BOOTSTRAPPING_MODE STREQUAL "HOSTTOOLS")
552-
set(swift_runtime_rpath "${host_lib_dir}")
553-
else()
554-
set(swift_runtime_rpath "$ORIGIN/${relpath_to_lib_dir}/swift/${SWIFT_SDK_${SWIFT_HOST_VARIANT_SDK}_LIB_SUBDIR}")
555-
endif()
551+
552+
# At runtime, use swiftCore in the current toolchain.
553+
# For building stdlib, LD_LIBRARY_PATH will be set to builder's stdlib
554+
# FIXME: This assumes the ABI hasn't changed since the builder.
555+
set(swift_runtime_rpath "$ORIGIN/${relpath_to_lib_dir}/swift/${SWIFT_SDK_${SWIFT_HOST_VARIANT_SDK}_LIB_SUBDIR}")
556556
557557
elseif(ASRLF_BOOTSTRAPPING_MODE STREQUAL "BOOTSTRAPPING")
558558
# At build time link against the built swift libraries from the
@@ -576,9 +576,6 @@ function(_add_swift_runtime_link_flags target relpath_to_lib_dir bootstrapping)
576576
endif()
577577
578578
if(SWIFT_SWIFT_PARSER)
579-
# Make sure we can find the early SwiftSyntax libraries.
580-
target_link_directories(${target} PRIVATE "${SWIFT_PATH_TO_EARLYSWIFTSYNTAX_BUILD_DIR}/lib/swift/host")
581-
582579
# For the "end step" of bootstrapping configurations, we need to be
583580
# able to fall back to the SDK directory for libswiftCore et al.
584581
if (BOOTSTRAPPING_MODE MATCHES "BOOTSTRAPPING.*")
@@ -832,8 +829,43 @@ macro(add_swift_lib_subdirectory name)
832829
add_llvm_subdirectory(SWIFT LIB ${name})
833830
endmacro()
834831
832+
# Add a new Swift host executable.
833+
#
834+
# Usage:
835+
# add_swift_host_tool(name
836+
# [HAS_SWIFT_MODULES | DOES_NOT_USE_SWIFT]
837+
# [THINLTO_LD64_ADD_FLTO_CODEGEN_ONLY]
838+
#
839+
# [BOOTSTRAPPING 0|1]
840+
# [SWIFT_COMPONENT component]
841+
# [LLVM_LINK_COMPONENTS comp1 ...]
842+
# source1 [source2 source3 ...])
843+
#
844+
# name
845+
# Name of the executable (e.g., swift-frontend).
846+
#
847+
# HAS_SWIFT_MODULES
848+
# Whether to link with SwiftCompilerSources library
849+
#
850+
# DOES_NOT_USE_SWIFT
851+
# Do not link with swift runtime
852+
#
853+
# THINLTO_LD64_ADD_FLTO_CODEGEN_ONLY
854+
# Opt-out of LLVM IR optimizations when linking ThinLTO with ld64
855+
#
856+
# BOOTSTRAPPING
857+
# Bootstrapping stage.
858+
#
859+
# SWIFT_COMPONENT
860+
# Installation component where this tool belongs to.
861+
#
862+
# LLVM_LINK_COMPONENTS
863+
# LLVM components this library depends on.
864+
#
865+
# source1 ...
866+
# Sources to add into this executable.
835867
function(add_swift_host_tool executable)
836-
set(options HAS_SWIFT_MODULES THINLTO_LD64_ADD_FLTO_CODEGEN_ONLY)
868+
set(options HAS_SWIFT_MODULES DOES_NOT_USE_SWIFT THINLTO_LD64_ADD_FLTO_CODEGEN_ONLY)
837869
set(single_parameter_options SWIFT_COMPONENT BOOTSTRAPPING)
838870
set(multiple_parameter_options LLVM_LINK_COMPONENTS)
839871
@@ -889,12 +921,12 @@ function(add_swift_host_tool executable)
889921
endif()
890922
891923
# Once the new Swift parser is linked in, every host tool has Swift modules.
892-
if (SWIFT_SWIFT_PARSER)
924+
if (SWIFT_SWIFT_PARSER AND NOT ASHT_DOES_NOT_USE_SWIFT)
893925
set(ASHT_HAS_SWIFT_MODULES ON)
894926
endif()
895927
896928
if (ASHT_HAS_SWIFT_MODULES)
897-
_add_swift_runtime_link_flags(${executable} "../lib" "${ASHT_BOOTSTRAPPING}")
929+
_add_swift_runtime_link_flags(${executable} "../lib" "${ASHT_BOOTSTRAPPING}")
898930
endif()
899931
900932
llvm_update_compile_flags(${executable})
@@ -967,7 +999,8 @@ function(add_swift_host_tool executable)
967999
swift_install_in_component(TARGETS ${executable}
9681000
RUNTIME
9691001
DESTINATION bin
970-
COMPONENT ${ASHT_SWIFT_COMPONENT})
1002+
COMPONENT ${ASHT_SWIFT_COMPONENT}
1003+
)
9711004

9721005
swift_is_installing_component(${ASHT_SWIFT_COMPONENT} is_installing)
9731006
endif()

cmake/modules/AddSwiftUnittests.cmake

Lines changed: 25 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,32 @@ add_custom_target(SwiftUnitTests)
55

66
set_target_properties(SwiftUnitTests PROPERTIES FOLDER "Tests")
77

8+
# Add a new Swift unit test executable.
9+
#
10+
# Usage:
11+
# add_swift_unittest(name
12+
# [IS_TARGET_TEST]
13+
# source1 [source2 source3 ...])
14+
#
15+
# name
16+
# Name of the test (e.g., SwiftASTTest).
17+
#
18+
# IS_TARGET_TEST
19+
# Indicates this is a test for target libraries. Not host library.
20+
# This avoids linking with toolchains stdlib.
21+
#
22+
# source1 ...
23+
# Sources to add into this executable.
824
function(add_swift_unittest test_dirname)
25+
cmake_parse_arguments(ASU
26+
"IS_TARGET_TEST"
27+
""
28+
""
29+
${ARGN})
30+
931
# *NOTE* Even though "add_unittest" does not have llvm in its name, it is a
1032
# function defined by AddLLVM.cmake.
11-
add_unittest(SwiftUnitTests ${test_dirname} ${ARGN})
33+
add_unittest(SwiftUnitTests ${test_dirname} ${ASU_UNPARSED_ARGUMENTS})
1234

1335
set_target_properties(${test_dirname} PROPERTIES LINKER_LANGUAGE CXX)
1436

@@ -89,7 +111,8 @@ function(add_swift_unittest test_dirname)
89111
endif()
90112
endif()
91113

92-
if (SWIFT_SWIFT_PARSER)
114+
if (SWIFT_SWIFT_PARSER AND NOT ASU_IS_TARGET_TEST)
115+
# Link to stdlib the compiler uses.
93116
_add_swift_runtime_link_flags(${test_dirname} "../../lib" "")
94117
set_property(TARGET ${test_dirname} PROPERTY BUILD_WITH_INSTALL_RPATH OFF)
95118
endif()

cmake/modules/SetRPATH.cmake

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
set(SWIFT_SET_RPATH_SCRIPT_FILE "${CMAKE_CURRENT_LIST_FILE}")
2+
3+
function(swift_get_set_rpath_script_file out_var)
4+
set(${out_var} "${SWIFT_SET_RPATH_SCRIPT_FILE}" PARENT_SCOPE)
5+
endfunction()
6+
7+
# Actual RPATH_CHANGE operation to the file.
8+
function(_swift_set_rpath_impl file new_rpath)
9+
# FIXME: Handle non-ELF files. We can't use RPATH_SET because it's only available CMake 3.21.0
10+
execute_process(
11+
COMMAND readelf -Wd "${file}"
12+
COMMAND grep -Po "R(UN)?PATH.*\\[\\K[^\\]]*"
13+
OUTPUT_VARIABLE current_rpath
14+
)
15+
string(STRIP "${current_rpath}" current_rpath)
16+
17+
# NOTE: RPATH_CHANGE is not documented, and works only for ELF and XCOFF.
18+
file(RPATH_CHANGE FILE "${file}" OLD_RPATH "${current_rpath}" NEW_RPATH "${new_rpath}")
19+
endfunction()
20+
21+
# For 'cmake -P <scirpt>'.
22+
if (SWIFT_SET_RPATH_FILE AND SWIFT_SET_RPATH_NEW_RPATH)
23+
_swift_set_rpath_impl("${SWIFT_SET_RPATH_FILE}" "${SWIFT_SET_RPATH_NEW_RPATH}")
24+
endif()

cmake/modules/SwiftImplicitImport.cmake

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ function(swift_supports_implicit_module module_name out_var)
66
"${CMAKE_Swift_COMPILER}"
77
-Xfrontend -disable-implicit-${module_name}-module-import
88
-Xfrontend -parse-stdlib
9-
-c - -o /dev/null
9+
-parse -
1010
INPUT_FILE
1111
"${CMAKE_BINARY_DIR}/tmp/empty-check-${module_name}.swift"
1212
OUTPUT_QUIET ERROR_QUIET

cmake/modules/SwiftUtils.cmake

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,16 @@ function(get_bootstrapping_swift_lib_dir bs_lib_dir bootstrapping)
107107
elseif("${bootstrapping}" STREQUAL "")
108108
get_bootstrapping_path(bs_lib_dir ${lib_dir} "1")
109109
endif()
110+
elseif(BOOTSTRAPPING_MODE STREQUAL "HOSTTOOLS")
111+
if(SWIFT_HOST_VARIANT_SDK MATCHES "LINUX|ANDROID|OPENBSD|FREEBSD")
112+
# Compiler's INSTALL_RPATH is set to libs in the build directory
113+
# For building stdlib, use stdlib in the builder's resource directory
114+
# because the runtime may not be built yet.
115+
# FIXME: This assumes the ABI hasn't changed since the builder.
116+
get_filename_component(swift_bin_dir ${CMAKE_Swift_COMPILER} DIRECTORY)
117+
get_filename_component(swift_dir ${swift_bin_dir} DIRECTORY)
118+
set(bs_lib_dir "${swift_dir}/lib/swift/${SWIFT_SDK_${SWIFT_HOST_VARIANT_SDK}_LIB_SUBDIR}")
119+
endif()
110120
endif()
111121
set(bs_lib_dir ${bs_lib_dir} PARENT_SCOPE)
112122
endfunction()

lib/CMakeLists.txt

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ if (SWIFT_SWIFT_PARSER)
3333
list(TRANSFORM SWIFT_SYNTAX_MODULES PREPEND "SwiftSyntax::"
3434
OUTPUT_VARIABLE SWIFT_SYNTAX_TARGETS)
3535

36-
set(SWIFT_SYNTAX_LIBRARIES_SOURCE_DIR
36+
set(SWIFT_SYNTAX_LIBRARIES_BUILD_DIR
3737
"${SWIFT_PATH_TO_EARLYSWIFTSYNTAX_BUILD_DIR}/lib/swift/host")
3838
set(SWIFT_HOST_LIBRARIES_DEST_DIR
3939
"${CMAKE_LIBRARY_OUTPUT_DIRECTORY}/swift/host")
@@ -53,17 +53,35 @@ if (SWIFT_SWIFT_PARSER)
5353
# Copy over all of the shared libraries from earlyswiftsyntax so they can
5454
# be found via RPATH.
5555
foreach (sharedlib ${SWIFT_SYNTAX_SHARED_LIBRARIES})
56+
set(add_origin_rpath)
57+
if(SWIFT_HOST_VARIANT_SDK STREQUAL "LINUX")
58+
# At runtime, use swiftCore in the current toolchain.
59+
swift_get_set_rpath_script_file(setrpath_command)
60+
set(add_origin_rpath COMMAND ${CMAKE_COMMAND}
61+
"-DSWIFT_SET_RPATH_FILE=${SWIFT_HOST_LIBRARIES_DEST_DIR}/${sharedlib}"
62+
"-DSWIFT_SET_RPATH_NEW_RPATH='$$ORIGIN:$$ORIGIN/../${SWIFT_SDK_${SWIFT_HOST_VARIANT_SDK}_LIB_SUBDIR}'"
63+
-P "${setrpath_command}"
64+
)
65+
endif()
66+
5667
add_custom_command(
5768
OUTPUT "${SWIFT_HOST_LIBRARIES_DEST_DIR}/${sharedlib}"
58-
DEPENDS "${SWIFT_SYNTAX_LIBRARIES_SOURCE_DIR}/${sharedlib}"
59-
COMMAND ${CMAKE_COMMAND} -E copy_if_different ${SWIFT_SYNTAX_LIBRARIES_SOURCE_DIR}/${sharedlib} ${SWIFT_HOST_LIBRARIES_DEST_DIR}/${sharedlib}
69+
DEPENDS "${SWIFT_SYNTAX_LIBRARIES_BUILD_DIR}/${sharedlib}"
70+
COMMAND ${CMAKE_COMMAND} -E copy_if_different ${SWIFT_SYNTAX_LIBRARIES_BUILD_DIR}/${sharedlib} ${SWIFT_HOST_LIBRARIES_DEST_DIR}/${sharedlib}
71+
${add_origin_rpath}
6072
)
6173

6274
add_custom_target(copy_swiftSyntaxLibrary_${sharedlib}
6375
DEPENDS "${SWIFT_HOST_LIBRARIES_DEST_DIR}/${sharedlib}"
6476
COMMENT "Copying ${sharedlib}"
6577
)
6678

79+
swift_install_in_component(
80+
PROGRAMS "${SWIFT_HOST_LIBRARIES_DEST_DIR}/${sharedlib}"
81+
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/host"
82+
COMPONENT compiler
83+
)
84+
6785
add_dependencies(swiftSyntaxLibraries copy_swiftSyntaxLibrary_${sharedlib})
6886
endforeach()
6987

@@ -76,7 +94,7 @@ if (SWIFT_SWIFT_PARSER)
7694
foreach(module_dir ${SWIFT_SYNTAX_MODULE_DIRS})
7795
# Find all of the source module files.
7896
file(GLOB module_files
79-
"${SWIFT_SYNTAX_LIBRARIES_SOURCE_DIR}/${module_dir}/*.swiftinterface")
97+
"${SWIFT_SYNTAX_LIBRARIES_BUILD_DIR}/${module_dir}/*.swiftinterface")
8098

8199
# Determine the destination module files.
82100
set(dest_module_files)
@@ -98,6 +116,12 @@ if (SWIFT_SWIFT_PARSER)
98116
COMMENT "Copying ${module_dir}"
99117
)
100118

119+
swift_install_in_component(
120+
FILES ${dest_module_files}
121+
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/host/${module_dir}"
122+
COMPONENT compiler
123+
)
124+
101125
add_dependencies(swiftSyntaxLibraries copy_swiftSyntaxModule_${module_dir})
102126
endforeach()
103127

lib/Macros/CMakeLists.txt

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,19 @@ function(add_swift_macro_library name)
3131
# Add the library.
3232
add_pure_swift_host_library(${name} SHARED ${ASML_SOURCES})
3333

34+
# Add rpath to 'lib/{platform}'
35+
file(RELATIVE_PATH relpath_to_lib
36+
"${SWIFT_HOST_PLUGINS_DEST_DIR}"
37+
"${CMAKE_LIBRARY_OUTPUT_DIRECTORY}"
38+
)
39+
_set_pure_swift_link_flags(${name} "${relpath_to_lib}")
40+
41+
# Add rpath to 'lib/host'
42+
if(SWIFT_HOST_VARIANT_SDK STREQUAL "LINUX")
43+
set_property(TARGET ${name}
44+
APPEND PROPERTY INSTALL_RPATH "$ORIGIN/..")
45+
endif()
46+
3447
# If we don't have the Swift swift parser, bail out, because the above
3548
# add_pure_swift_host_library did nothing.
3649
if (NOT SWIFT_SWIFT_PARSER)
@@ -44,12 +57,14 @@ function(add_swift_macro_library name)
4457
LIBRARY_OUTPUT_DIRECTORY "${SWIFT_HOST_PLUGINS_DEST_DIR}"
4558
)
4659

60+
set(destination_dir "lib${LLVM_LIBDIR_SUFFIX}/swift/host/plugins")
61+
4762
swift_install_in_component(TARGETS ${name}
4863
LIBRARY
49-
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/host/plugins"
64+
DESTINATION "${destination_dir}"
5065
COMPONENT compiler
5166
ARCHIVE
52-
DESTINATION "lib${LLVM_LIBDIR_SUFFIX}/swift/host/plugins"
67+
DESTINATION "${destination_dir}"
5368
COMPONENT compiler)
5469

5570
# Export this macro plugin target.

0 commit comments

Comments
 (0)