forked from swiftlang/swift
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathSwiftHandleGybSources.cmake
176 lines (164 loc) · 6.84 KB
/
SwiftHandleGybSources.cmake
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
include(SwiftAddCustomCommandTarget)
include(SwiftSetIfArchBitness)
# Create a target to process single gyb source with the 'gyb' tool.
#
# handle_gyb_source_single(
# dependency_out_var_name
# SOURCE src_gyb
# OUTPUT output
# [FLAGS [flags ...]])
# [DEPENDS [depends ...]]
# [COMMENT comment])
#
# dependency_out_var_name
# The name of a variable, to be set in the parent scope to be the target
# target that invoke gyb.
#
# src_gyb
# .gyb suffixed source file
#
# output
# Output filename to be generated
#
# flags ...
# gyb flags in addition to ${SWIFT_GYB_FLAGS}.
#
# depends ...
# gyb flags in addition to 'src_gyb' and sources of gyb itself.
#
# comment
# Additional comment.
function(handle_gyb_source_single dependency_out_var_name)
set(options)
set(single_value_args SOURCE OUTPUT COMMENT)
set(multi_value_args FLAGS DEPENDS)
cmake_parse_arguments(
GYB_SINGLE # prefix
"${options}" "${single_value_args}" "${multi_value_args}" ${ARGN})
set(gyb_tool "${SWIFT_SOURCE_DIR}/utils/gyb")
set(gyb_tool_source "${gyb_tool}" "${gyb_tool}.py")
get_filename_component(dir "${GYB_SINGLE_OUTPUT}" DIRECTORY)
get_filename_component(basename "${GYB_SINGLE_OUTPUT}" NAME)
# Handle foo.gyb in pattern ``gyb.expand('foo.gyb'`` as a dependency
set(gyb_expand_deps "")
file(READ "${GYB_SINGLE_SOURCE}" gyb_file)
string(REGEX MATCHALL "\\\$\{[\r\n\t ]*gyb.expand\\\([\r\n\t ]*[\'\"]([^\'\"]*)[\'\"]" gyb_expand_matches "${gyb_file}")
foreach(match ${gyb_expand_matches})
string(REGEX MATCH "[\'\"]\([^\'\"]*\)[\'\"]" gyb_dep "${match}")
list(APPEND gyb_expand_deps "${CMAKE_MATCH_1}")
endforeach()
list(REMOVE_DUPLICATES gyb_expand_deps)
add_custom_command_target(
dependency_target
COMMAND
"${CMAKE_COMMAND}" -E make_directory "${dir}"
COMMAND
"${PYTHON_EXECUTABLE}" "${gyb_tool}" ${SWIFT_GYB_FLAGS} ${GYB_SINGLE_FLAGS} -o "${GYB_SINGLE_OUTPUT}.tmp" "${GYB_SINGLE_SOURCE}"
COMMAND
"${CMAKE_COMMAND}" -E copy_if_different "${GYB_SINGLE_OUTPUT}.tmp" "${GYB_SINGLE_OUTPUT}"
COMMAND
"${CMAKE_COMMAND}" -E remove "${GYB_SINGLE_OUTPUT}.tmp"
OUTPUT "${GYB_SINGLE_OUTPUT}"
DEPENDS "${gyb_tool_source}" "${GYB_SINGLE_DEPENDS}" "${GYB_SINGLE_SOURCE}" "${gyb_expand_deps}"
COMMENT "Generating ${basename} from ${GYB_SINGLE_SOURCE} ${GYB_SINGLE_COMMENT}"
WORKING_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}"
SOURCES "${GYB_SINGLE_SOURCE}"
IDEMPOTENT)
set("${dependency_out_var_name}" "${dependency_target}" PARENT_SCOPE)
endfunction()
# Create a target to process .gyb files with the 'gyb' tool.
#
# handle_gyb_sources(
# dependency_out_var_name
# sources_var_name
# arch)
#
# Replace, in ${sources_var_name}, the given .gyb-suffixed sources with
# their un-suffixed intermediate files, which will be generated by processing
# the .gyb files with gyb.
#
# dependency_out_var_name
# The name of a variable, to be set in the parent scope to the list of
# targets that invoke gyb. Every target that depends on the generated
# sources should depend on ${dependency_out_var_name} targets.
#
# arch
# The architecture that the files will be compiled for. If this is
# false, the files are architecture-independent and will be emitted
# into ${CMAKE_CURRENT_BINARY_DIR} instead of an architecture-specific
# destination; this is useful for generated include files.
function(handle_gyb_sources dependency_out_var_name sources_var_name arch)
set(extra_gyb_flags "")
if (arch)
set_if_arch_bitness(ptr_size
ARCH "${arch}"
CASE_32_BIT "4"
CASE_64_BIT "8")
set(extra_gyb_flags "-DCMAKE_SIZEOF_VOID_P=${ptr_size}")
endif()
set(dependency_targets)
set(de_gybbed_sources)
set(gyb_extra_sources
"${SWIFT_SOURCE_DIR}/utils/GYBUnicodeDataUtils.py"
"${SWIFT_SOURCE_DIR}/utils/SwiftIntTypes.py"
"${SWIFT_SOURCE_DIR}/utils/UnicodeData/GraphemeBreakProperty.txt"
"${SWIFT_SOURCE_DIR}/utils/UnicodeData/GraphemeBreakTest.txt"
"${SWIFT_SOURCE_DIR}/utils/gyb_stdlib_support.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/__init__.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/Child.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/kinds.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/Node.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/AttributeNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/AvailabilityNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/CommonNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/DeclNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/ExprNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/GenericNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/NodeSerializationCodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/PatternNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/StmtNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/TypeNodes.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/Token.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/Trivia.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_syntax_support/Traits.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_sourcekit_support/__init__.py"
"${SWIFT_SOURCE_DIR}/utils/gyb_sourcekit_support/UIDs.py")
foreach (src ${${sources_var_name}})
# On Windows (using Visual Studio), the generated project files assume that the
# generated GYB files will be in the source, not binary directory.
# We can work around this by modifying the root directory when generating VS projects.
if ("${CMAKE_GENERATOR_PLATFORM}" MATCHES "Visual Studio")
set(dir_root ${CMAKE_CURRENT_SOURCE_DIR})
else()
set(dir_root ${CMAKE_CURRENT_BINARY_DIR})
endif()
if (arch)
set(dir "${dir_root}/${ptr_size}")
else()
set(dir "${dir_root}")
endif()
# get_filename_component(src_sans_gyb ${src} NAME_WLE)
string(REGEX REPLACE "\.gyb$" "" src_sans_gyb ${src})
set(output_file_name "${dir}/${src_sans_gyb}")
list(APPEND de_gybbed_sources "${output_file_name}")
handle_gyb_source_single(dependency_target
SOURCE "${src}"
OUTPUT "${output_file_name}"
FLAGS ${extra_gyb_flags}
DEPENDS "${gyb_extra_sources}"
COMMENT "with ptr size = ${ptr_size}")
list(APPEND dependency_targets "${dependency_target}")
endforeach()
set("${dependency_out_var_name}" "${dependency_targets}" PARENT_SCOPE)
set("${sources_var_name}" "${de_gybbed_sources}" PARENT_SCOPE)
endfunction()
function(add_gyb_target target sources)
set(options)
set(single_value_args ARCH)
set(multi_value_args)
cmake_parse_arguments(GYB
"${options}" "${single_value_args}" "${multi_value_args}" ${ARGN})
handle_gyb_sources(gyb_sources_depends sources "${GYB_ARCH}")
add_custom_target(${target}
DEPENDS "${gyb_sources_depends}")
endfunction()