Skip to content

Commit c8f1de2

Browse files
[Cmake] Add supplemental cmake modules (#81180)
Adds common CMAKE modules to be used by the supplemental libraries. Namely: * ResourceEmbedding * PlatformInfo * gyb * EmitSwiftInterface * CatalystSupport
1 parent 2eaa0e9 commit c8f1de2

File tree

5 files changed

+266
-0
lines changed

5 files changed

+266
-0
lines changed
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
# Add flags for generating the zippered target variant in the build
2+
3+
# Initialize `${PROJECT_NAME}_VARIANT_MODULE_TRIPLE` if the driver is able to emit
4+
# modules for the target variant.
5+
6+
if(${PROJECT_NAME}_COMPILER_VARIANT_TARGET)
7+
add_compile_options(
8+
"$<$<COMPILE_LANGUAGE:C,CXX>:SHELL:-darwin-target-variant ${${PROJECT_NAME}_COMPILER_VARIANT_TARGET}>"
9+
"$<$<COMPILE_LANGUAGE:Swift>:SHELL:-target-variant ${${PROJECT_NAME}_COMPILER_VARIANT_TARGET}>"
10+
11+
# TODO: Remove me once we have a driver with
12+
# https://github.com/swiftlang/swift-driver/pull/1803
13+
"$<$<COMPILE_LANGUAGE:Swift>:SHELL:-Xclang-linker -darwin-target-variant -Xclang-linker ${${PROJECT_NAME}_COMPILER_VARIANT_TARGET}>")
14+
15+
add_link_options(
16+
"$<$<LINK_LANGUAGE:C,CXX>:SHELL:-darwin-target-variant ${${PROJECT_NAME}_COMPILER_VARIANT_TARGET}>"
17+
"$<$<LINK_LANGUAGE:Swift>:SHELL:-target-variant ${${PROJECT_NAME}_COMPILER_VARIANT_TARGET}>"
18+
19+
# TODO: Remove me once we have a driver with
20+
# https://github.com/swiftlang/swift-driver/pull/1803
21+
"$<$<LINK_LANGUAGE:Swift>:SHELL:-Xclang-linker -darwin-target-variant -Xclang-linker ${${PROJECT_NAME}_COMPILER_VARIANT_TARGET}>")
22+
23+
# TODO: Once we are guaranteed to have a driver with the variant module path
24+
# support everywhere, we should integrate this into PlatformInfo.cmake
25+
check_compiler_flag(Swift "-emit-variant-module-path ${CMAKE_CURRENT_BINARY_DIR}/CompilerID/variant.swiftmodule" HAVE_Swift_VARIANT_MODULE_PATH_FLAG)
26+
if(HAVE_Swift_VARIANT_MODULE_PATH_FLAG)
27+
# Get variant module triple
28+
set(module_triple_command "${CMAKE_Swift_COMPILER}" -print-target-info -target ${${PROJECT_NAME}_COMPILER_VARIANT_TARGET})
29+
execute_process(COMMAND ${module_triple_command} OUTPUT_VARIABLE target_info_json)
30+
message(CONFIGURE_LOG "Swift target variant info: ${target_info_json}")
31+
32+
33+
string(JSON module_triple GET "${target_info_json}" "target" "moduleTriple")
34+
set(${PROJECT_NAME}_VARIANT_MODULE_TRIPLE "${module_triple}" CACHE STRING "Triple used for installed swift{module,interface} files for the target variant")
35+
mark_as_advanced(${PROJECT_NAME}_VARIANT_MODULE_TRIPLE)
36+
message(CONFIGURE_LOG "Swift target variant module triple: ${module_triple}")
37+
endif()
38+
endif()
Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
# Generate and install swift interface files
2+
3+
# TODO: CMake should learn how to model library evolution and generate this
4+
# stuff automatically.
5+
6+
7+
# Generate a swift interface file for the target if library evolution is enabled
8+
function(emit_swift_interface target)
9+
# Generate the target-variant binary swift module when performing zippered
10+
# build
11+
if(${PROJECT_NAME}_VARIANT_MODULE_TRIPLE)
12+
set(variant_module_tmp_dir "${CMAKE_CURRENT_BINARY_DIR}/${target}-${${PROJECT_NAME}_VARIANT_MODULE_TRIPLE}")
13+
file(MAKE_DIRECTORY "${variant_module_tmp_dir}")
14+
target_compile_options(${target} PRIVATE
15+
"$<$<COMPILE_LANGUAGE:Swift>:SHELL:-emit-variant-module-path ${variant_module_tmp_dir}/${target}.swiftmodule>")
16+
endif()
17+
18+
# Generate textual swift interfaces is library-evolution is enabled
19+
if(${PROJECT_NAME}_ENABLE_LIBRARY_EVOLUTION)
20+
target_compile_options(${target} PRIVATE
21+
$<$<COMPILE_LANGUAGE:Swift>:-emit-module-interface-path$<SEMICOLON>${CMAKE_CURRENT_BINARY_DIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftinterface>
22+
$<$<COMPILE_LANGUAGE:Swift>:-emit-private-module-interface-path$<SEMICOLON>${CMAKE_CURRENT_BINARY_DIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.private.swiftinterface>
23+
$<$<COMPILE_LANGUAGE:Swift>:-library-level$<SEMICOLON>api>
24+
$<$<COMPILE_LANGUAGE:Swift>:-Xfrontend$<SEMICOLON>-require-explicit-availability=ignore>)
25+
26+
# Emit catalyst swiftmodules and interfaces
27+
if(${PROJECT_NAME}_VARIANT_MODULE_TRIPLE)
28+
target_compile_options(${target} PRIVATE
29+
"$<$<COMPILE_LANGUAGE:Swift>:SHELL:-emit-variant-module-interface-path ${variant_module_tmp_dir}/${target}.swiftinterface>"
30+
"$<$<COMPILE_LANGUAGE:Swift>:SHELL:-emit-variant-private-module-interface-path ${variant_module_tmp_dir}/${target}.private.swiftinterface>")
31+
endif()
32+
endif()
33+
endfunction()
34+
35+
# Install the generated swift interface file for the target if library evolution
36+
# is enabled.
37+
function(install_swift_interface target)
38+
# Install binary swift modules
39+
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftmodule"
40+
RENAME "${${PROJECT_NAME}_MODULE_TRIPLE}.swiftmodule"
41+
DESTINATION "${${PROJECT_NAME}_INSTALL_SWIFTMODULEDIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftmodule"
42+
COMPONENT ${PROJECT_NAME}_development)
43+
if(${PROJECT_NAME}_VARIANT_MODULE_TRIPLE)
44+
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/${target}-${${PROJECT_NAME}_VARIANT_MODULE_TRIPLE}/${target}.swiftmodule"
45+
RENAME "${${PROJECT_NAME}_VARIANT_MODULE_TRIPLE}.swiftmodule"
46+
DESTINATION "${${PROJECT_NAME}_INSTALL_SWIFTMODULEDIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftmodule"
47+
COMPONENT ${PROJECT_NAME}_development)
48+
endif()
49+
50+
# Install Swift interfaces if library-evolution is enabled
51+
if(${PROJECT_NAME}_ENABLE_LIBRARY_EVOLUTION)
52+
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftinterface"
53+
RENAME "${${PROJECT_NAME}_MODULE_TRIPLE}.swiftinterface"
54+
DESTINATION "${${PROJECT_NAME}_INSTALL_SWIFTMODULEDIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftmodule"
55+
COMPONENT ${PROJECT_NAME}_development)
56+
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.private.swiftinterface"
57+
RENAME "${${PROJECT_NAME}_MODULE_TRIPLE}.private.swiftinterface"
58+
DESTINATION "${${PROJECT_NAME}_INSTALL_SWIFTMODULEDIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftmodule"
59+
COMPONENT ${PROJECT_NAME}_development)
60+
61+
# Install catalyst interface files
62+
if(${PROJECT_NAME}_VARIANT_MODULE_TRIPLE)
63+
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/${target}-${${PROJECT_NAME}_VARIANT_MODULE_TRIPLE}/${target}.swiftinterface"
64+
RENAME "${${PROJECT_NAME}_VARIANT_MODULE_TRIPLE}.swiftinterface"
65+
DESTINATION "${${PROJECT_NAME}_INSTALL_SWIFTMODULEDIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftmodule"
66+
COMPONENT ${PROJECT_NAME}_development)
67+
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/${target}-${${PROJECT_NAME}_VARIANT_MODULE_TRIPLE}/${target}.private.swiftinterface"
68+
RENAME "${${PROJECT_NAME}_VARIANT_MODULE_TRIPLE}.private.swiftinterface"
69+
DESTINATION "${${PROJECT_NAME}_INSTALL_SWIFTMODULEDIR}/$<TARGET_PROPERTY:${target},Swift_MODULE_NAME>.swiftmodule"
70+
COMPONENT ${PROJECT_NAME}_development)
71+
endif()
72+
endif()
73+
endfunction()
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
if(NOT ${PROJECT_NAME}_SIZEOF_POINTER)
2+
set(${PROJECT_NAME}_SIZEOF_POINTER "${CMAKE_SIZEOF_VOID_P}" CACHE STRING "Size of a pointer in bytes")
3+
message(CONFIGURE_LOG "Stdlib Pointer size: ${CMAKE_SIZEOF_VOID_P}")
4+
mark_as_advanced(${PROJECT_NAME}_SIZEOF_POINTER)
5+
endif()
6+
7+
# TODO: This logic should migrate to CMake once CMake supports installing swiftmodules
8+
set(module_triple_command "${CMAKE_Swift_COMPILER}" -print-target-info)
9+
if(CMAKE_Swift_COMPILER_TARGET)
10+
list(APPEND module_triple_command -target ${CMAKE_Swift_COMPILER_TARGET})
11+
endif()
12+
execute_process(COMMAND ${module_triple_command} OUTPUT_VARIABLE target_info_json)
13+
message(CONFIGURE_LOG "Swift target info: ${module_triple_command}\n"
14+
"${target_info_json}")
15+
16+
if(NOT ${PROJECT_NAME}_MODULE_TRIPLE)
17+
string(JSON module_triple GET "${target_info_json}" "target" "moduleTriple")
18+
set(${PROJECT_NAME}_MODULE_TRIPLE "${module_triple}" CACHE STRING "Triple used for installed swift{doc,module,interface} files")
19+
mark_as_advanced(${PROJECT_NAME}_MODULE_TRIPLE)
20+
21+
message(CONFIGURE_LOG "Swift module triple: ${module_triple}")
22+
endif()
23+
24+
if(NOT ${PROJECT_NAME}_PLATFORM_SUBDIR)
25+
string(JSON platform GET "${target_info_json}" "target" "platform")
26+
set(${PROJECT_NAME}_PLATFORM_SUBDIR "${platform}" CACHE STRING "Platform name used for installed swift{doc,module,interface} files")
27+
mark_as_advanced(${PROJECT_NAME}_PLATFORM_SUBDIR)
28+
29+
message(CONFIGURE_LOG "Swift platform: ${platform}")
30+
endif()
31+
32+
if(NOT ${PROJECT_NAME}_ARCH_SUBDIR)
33+
string(JSON arch GET "${target_info_json}" "target" "arch")
34+
set(${PROJECT_NAME}_ARCH_SUBDIR "${arch}" CACHE STRING "Architecture used for setting the architecture subdirectory")
35+
mark_as_advanced(${PROJECT_NAME}_ARCH_SUBDIR)
36+
37+
message(CONFIGURE_LOG "Swift Arch: ${arch}")
38+
endif()
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
function(generate_plist project_name project_version target)
2+
set(PLIST_INFO_PLIST "Info.plist")
3+
set(PLIST_INFO_NAME "${project_name}")
4+
5+
# Underscores aren't permitted in the bundle identifier.
6+
string(REPLACE "_" "" PLIST_INFO_UTI "com.apple.dt.runtime.${PLIST_INFO_NAME}")
7+
set(PLIST_INFO_VERSION "${project_version}")
8+
set(PLIST_INFO_BUILD_VERSION "${project_version}")
9+
10+
set(PLIST_INFO_PLIST_OUT "${PLIST_INFO_PLIST}")
11+
set(PLIST_INFO_PLIST_IN "${PROJECT_SOURCE_DIR}/${PLIST_INFO_PLIST}.in")
12+
13+
if(APPLE)
14+
target_link_options(${target} PRIVATE
15+
"SHELL:-Xlinker -sectcreate -Xlinker __TEXT -Xlinker __info_plist -Xlinker ${CMAKE_CURRENT_BINARY_DIR}/${PLIST_INFO_PLIST_OUT}")
16+
endif()
17+
18+
configure_file(
19+
"${PLIST_INFO_PLIST_IN}"
20+
"${PLIST_INFO_PLIST_OUT}"
21+
@ONLY
22+
NEWLINE_STYLE UNIX)
23+
24+
set_property(TARGET ${target} APPEND PROPERTY LINK_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/${PLIST_INFO_PLIST_OUT}")
25+
26+
# If Application Extensions are enabled, pass the linker flag marking
27+
# the dylib as safe.
28+
if (CXX_SUPPORTS_FAPPLICATION_EXTENSION AND (NOT DISABLE_APPLICATION_EXTENSION))
29+
list(APPEND link_flags "-Wl,-application_extension")
30+
endif()
31+
endfunction()
32+
33+
# FIXME: it appears that `CMAKE_MT` evaluates to an empty string which prevents
34+
# the use of the variable. This aliases `MT` to `CMAKE_MT` and tries to fallback
35+
# to known spellings for the tool.
36+
if(WIN32 AND BUILD_SHARED_LIBS)
37+
find_program(MT HINTS ${CMAKE_MT} NAMES mt llvm-mt REQUIRED)
38+
endif()
39+
40+
function(embed_manifest target)
41+
get_target_property(_EM_TARGET_TYPE ${target} TYPE)
42+
if(NOT "${_EM_TARGET_TYPE}" MATCHES "SHARED_LIBRARY|EXECUTABLE")
43+
return()
44+
endif()
45+
46+
get_target_property(_EM_BINARY_DIR ${target} BINARY_DIR)
47+
get_target_property(_EM_NAME ${target} NAME)
48+
49+
# Evaluate variables
50+
file(CONFIGURE
51+
OUTPUT ${_EM_BINARY_DIR}/${_EM_NAME}-${PROJECT_VERSION}.1.manifest.in
52+
CONTENT [[<?xml version="1.0" encoding="utf-8" standalone="yes"?>
53+
<assembly manifestversion="1.0" xmlns="urn:schemas-microsoft-com:asm.v1">
54+
<assemblyIdentity
55+
name="$<TARGET_NAME:@target@>"
56+
processorArchitecture="@CMAKE_SYSTEM_PROCESSOR@"
57+
type="win32"
58+
version="@PROJECT_VERSION@" />
59+
<file name="$<TARGET_FILE_NAME:@target@>" />
60+
</assembly>]])
61+
# Evaluate generator expression
62+
file(GENERATE
63+
OUTPUT ${_EM_BINARY_DIR}/${_EM_NAME}-${PROJECT_VERSION}.1.manifest
64+
INPUT ${_EM_BINARY_DIR}/${_EM_NAME}-${PROJECT_VERSION}.1.manifest.in)
65+
66+
if(WIN32)
67+
add_custom_command(TARGET ${target} POST_BUILD
68+
COMMAND "${MT}" -nologo -manifest "${_EM_BINARY_DIR}/${_EM_NAME}-${PROJECT_VERSION}.1.manifest" "-outputresource:$<TARGET_FILE:${target}>;#1")
69+
endif()
70+
endfunction()
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
find_package(Python3 REQUIRED COMPONENTS Interpreter)
2+
3+
# Create a target to expand a gyb source
4+
# target_name: Name of the target
5+
# FLAGS list of flags passed to gyb
6+
# DEPENDS list of dependencies
7+
# COMMENT Custom comment
8+
function(gyb_expand source output)
9+
set(flags)
10+
set(arguments)
11+
set(multival_arguments FLAGS DEPENDS)
12+
cmake_parse_arguments(GYB "${flags}" "${arguments}" "${multival_arguments}" ${ARGN})
13+
14+
get_filename_component(full_output_path ${output} ABSOLUTE BASE_DIR "${CMAKE_CURRENT_BINARY_DIR}")
15+
get_filename_component(dir "${full_output_path}" DIRECTORY)
16+
get_filename_component(fname "${full_output_path}" NAME)
17+
18+
file(READ "${source}" gyb_src)
19+
string(REGEX MATCHALL "\\\$\{[\r\n\t ]*gyb.expand\\\([\r\n\t ]*[\'\"]([^\'\"]*)[\'\"]" gyb_expand_matches "${gyb_src}")
20+
foreach(match ${gyb_expand_matches})
21+
string(REGEX MATCH "[\'\"]\([^\'\"]*\)[\'\"]" gyb_dep "${match}")
22+
list(APPEND gyb_expand_deps "${CMAKE_MATCH_1}")
23+
endforeach()
24+
list(REMOVE_DUPLICATES gyb_expand_deps)
25+
26+
set(utils_dir "${${PROJECT_NAME}_SWIFTC_SOURCE_DIR}/utils/")
27+
set(gyb_tool "${utils_dir}/gyb")
28+
29+
# All the tidbits to track for changes
30+
list(APPEND GYB_DEPENDS
31+
"${source}"
32+
"${utils_dir}/GYBUnicodeDataUtils.py"
33+
"${utils_dir}/SwiftIntTypes.py"
34+
"${utils_dir}/SwiftFloatingPointTypes.py"
35+
"${utils_dir}/UnicodeData/GraphemeBreakProperty.txt"
36+
"${utils_dir}/UnicodeData/GraphemeBreakTest.txt"
37+
"${utils_dir}/gyb_stdlib_support.py")
38+
add_custom_command(
39+
OUTPUT "${full_output_path}"
40+
COMMAND "${CMAKE_COMMAND}" -E make_directory "${dir}"
41+
COMMAND "${CMAKE_COMMAND}" -E env "$<TARGET_FILE:Python3::Interpreter>" "${gyb_tool}" ${GYB_FLAGS} -o "${full_output_path}.tmp" "${source}"
42+
COMMAND "${CMAKE_COMMAND}" -E copy_if_different "${full_output_path}.tmp" "${full_output_path}"
43+
COMMAND "${CMAKE_COMMAND}" -E remove "${full_output_path}.tmp"
44+
DEPENDS ${gyb_tool} ${gyb_tool}.py ${GYB_DEPENDS} ${gyb_expand_deps}
45+
COMMENT "Generating GYB source ${fname} from ${source}"
46+
WORKING_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}")
47+
endfunction()

0 commit comments

Comments
 (0)