Skip to content

Commit a20c388

Browse files
authored
Feature to opt out of tracking .swiftdoc and .swiftsourceinfo Files (#1179)
This PR introduces configuration options aimed at optimizing CI build processes by excluding non-essential Swift documentation and source info files, files that don't serve as inputs to other build targets. By introducing flags to control the exclusion of these files, we aim to reduce unnecessary network I/O and improve build performance in specific CI environments. (non-dev facing only) Features Introduced: - `swift.emit_swiftdoc` - This feature is enabled by default. - Opting out of this feature will prevent .swiftdoc files from being tracked by `SwiftInfo` provider, though they will still be generated by the Swift compiler. - These documentation files are generally used for IDE features and are not required in certain CI contexts, such as non-developer-facing validation suites. - `swift.emit_swiftsourceinfo` - This feature is enabled by default. - When this feature is disabled, .swiftsourceinfo files, which support source-level debugging, will also be excluded from build outputs and will not be tracked by `SwiftInfo` provider. It is important to note that, by default, the Swift compiler generates .swiftdoc and .swiftsourceinfo files as part of the output when using the `-emit-module` flag. As of now, this behavior is consistent, given the absence of compiler options in Swift that permit controlling the generation of these files.
1 parent 380d040 commit a20c388

File tree

7 files changed

+180
-14
lines changed

7 files changed

+180
-14
lines changed

swift/internal/compiling.bzl

Lines changed: 29 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,9 @@ load(
4848
"SWIFT_FEATURE_EMIT_BC",
4949
"SWIFT_FEATURE_EMIT_C_MODULE",
5050
"SWIFT_FEATURE_EMIT_PRIVATE_SWIFTINTERFACE",
51+
"SWIFT_FEATURE_EMIT_SWIFTDOC",
5152
"SWIFT_FEATURE_EMIT_SWIFTINTERFACE",
53+
"SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO",
5254
"SWIFT_FEATURE_EMIT_SYMBOL_GRAPH",
5355
"SWIFT_FEATURE_ENABLE_BATCH_MODE",
5456
"SWIFT_FEATURE_ENABLE_LIBRARY_EVOLUTION",
@@ -2372,12 +2374,24 @@ def compile(
23722374
swift_toolchain.generated_header_module_implicit_deps_providers.swift_infos
23732375
)
23742376

2377+
# Determine if `.swiftdoc` and `.swiftsourceinfo` files should be included.
2378+
include_swiftdoc = is_feature_enabled(
2379+
feature_configuration = feature_configuration,
2380+
feature_name = SWIFT_FEATURE_EMIT_SWIFTDOC,
2381+
)
2382+
include_swiftsourceinfo = is_feature_enabled(
2383+
feature_configuration = feature_configuration,
2384+
feature_name = SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO,
2385+
)
2386+
23752387
compile_outputs, other_outputs = _declare_compile_outputs(
23762388
srcs = srcs,
23772389
actions = actions,
23782390
feature_configuration = feature_configuration,
23792391
generated_header_name = generated_header_name,
23802392
generated_module_deps_swift_infos = generated_module_deps_swift_infos,
2393+
include_swiftdoc = include_swiftdoc,
2394+
include_swiftsourceinfo = include_swiftsourceinfo,
23812395
module_name = module_name,
23822396
target_name = target_name,
23832397
user_compile_flags = copts,
@@ -2401,27 +2415,31 @@ def compile(
24012415
# various things (such as the filename prefix for param files generated
24022416
# for that action). This guarantees some predictability.
24032417
compile_outputs.swiftmodule_file,
2404-
compile_outputs.swiftdoc_file,
2405-
compile_outputs.swiftsourceinfo_file,
24062418
compile_outputs.generated_header_file,
24072419
compile_outputs.symbol_graph_directory,
24082420
]) + other_outputs
2421+
if include_swiftdoc:
2422+
all_derived_outputs.append(compile_outputs.swiftdoc_file)
2423+
if include_swiftsourceinfo:
2424+
all_derived_outputs.append(compile_outputs.swiftsourceinfo_file)
24092425
else:
24102426
all_compile_outputs = compact([
24112427
# The `.swiftmodule` file is explicitly listed as the first output
24122428
# because it will always exist and because Bazel uses it as a key for
24132429
# various things (such as the filename prefix for param files generated
24142430
# for that action). This guarantees some predictability.
24152431
compile_outputs.swiftmodule_file,
2416-
compile_outputs.swiftdoc_file,
24172432
compile_outputs.swiftinterface_file,
24182433
compile_outputs.private_swiftinterface_file,
2419-
compile_outputs.swiftsourceinfo_file,
24202434
compile_outputs.generated_header_file,
24212435
compile_outputs.indexstore_directory,
24222436
compile_outputs.macro_expansion_directory,
24232437
compile_outputs.symbol_graph_directory,
24242438
]) + compile_outputs.object_files + other_outputs
2439+
if include_swiftdoc:
2440+
all_compile_outputs.append(compile_outputs.swiftdoc_file)
2441+
if include_swiftsourceinfo:
2442+
all_compile_outputs.append(compile_outputs.swiftsourceinfo_file)
24252443
all_derived_outputs = []
24262444

24272445
# Merge the providers from our dependencies so that we have one each for
@@ -2921,6 +2939,8 @@ def _declare_compile_outputs(
29212939
feature_configuration,
29222940
generated_header_name,
29232941
generated_module_deps_swift_infos,
2942+
include_swiftdoc,
2943+
include_swiftsourceinfo,
29242944
module_name,
29252945
srcs,
29262946
target_name,
@@ -2936,6 +2956,8 @@ def _declare_compile_outputs(
29362956
generated_module_deps_swift_infos: `SwiftInfo` providers from
29372957
dependencies of the module for the generated header of the target
29382958
being compiled.
2959+
include_swiftdoc: If .swiftdoc file should be included or not.
2960+
include_swiftsourceinfo: If .swiftsourceinfo file should be included or not.
29392961
module_name: The name of the Swift module being compiled.
29402962
srcs: The list of source files that will be compiled.
29412963
target_name: The name (excluding package path) of the target being
@@ -2963,11 +2985,12 @@ def _declare_compile_outputs(
29632985
swiftdoc_file = derived_files.swiftdoc(
29642986
actions = actions,
29652987
module_name = module_name,
2966-
)
2988+
) if include_swiftdoc else None
2989+
29672990
swiftsourceinfo_file = derived_files.swiftsourceinfo(
29682991
actions = actions,
29692992
module_name = module_name,
2970-
)
2993+
) if include_swiftsourceinfo else None
29712994

29722995
if are_all_features_enabled(
29732996
feature_configuration = feature_configuration,

swift/internal/feature_names.bzl

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -343,3 +343,13 @@ SWIFT_FEATURE__SUPPORTS_MACROS = "swift._supports_macros"
343343

344344
# Pass -warnings-as-errors to the compiler.
345345
SWIFT_FEATURE_TREAT_WARNINGS_AS_ERRORS = "swift.treat_warnings_as_errors"
346+
347+
# Defines whether .swiftdoc files are included in build outputs.
348+
# This feature is enabled by default.
349+
# Note: If opted out of this feature, .swiftdoc are generated by the compiler but excluded from Bazel's tracking.
350+
SWIFT_FEATURE_EMIT_SWIFTDOC = "swift.emit_swiftdoc"
351+
352+
# Defines whether .swiftsourceinfo files are included in build outputs.
353+
# This feature is enabled by default.
354+
# Note: If opted out of this feature, .swiftsourceinfo are generated by the compiler but excluded from Bazel's tracking.
355+
SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO = "swift.emit_swiftsourceinfo"

swift/internal/swift_autoconfiguration.bzl

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ load(
2828
"@build_bazel_rules_swift//swift/internal:feature_names.bzl",
2929
"SWIFT_FEATURE_CODEVIEW_DEBUG_INFO",
3030
"SWIFT_FEATURE_DEBUG_PREFIX_MAP",
31+
"SWIFT_FEATURE_EMIT_SWIFTDOC",
32+
"SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO",
3133
"SWIFT_FEATURE_ENABLE_BATCH_MODE",
3234
"SWIFT_FEATURE_ENABLE_SKIP_FUNCTION_BODIES",
3335
"SWIFT_FEATURE_FILE_PREFIX_MAP",
@@ -365,6 +367,8 @@ def _create_windows_toolchain(repository_ctx):
365367
enabled_features = [
366368
SWIFT_FEATURE_CODEVIEW_DEBUG_INFO,
367369
SWIFT_FEATURE_DEBUG_PREFIX_MAP,
370+
SWIFT_FEATURE_EMIT_SWIFTDOC,
371+
SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO,
368372
SWIFT_FEATURE_ENABLE_BATCH_MODE,
369373
SWIFT_FEATURE_ENABLE_SKIP_FUNCTION_BODIES,
370374
SWIFT_FEATURE_SUPPORTS_PRIVATE_DEPS,

swift/internal/swift_toolchain.bzl

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,8 @@ load(
3434
"SWIFT_FEATURE_CACHEABLE_SWIFTMODULES",
3535
"SWIFT_FEATURE_COVERAGE_PREFIX_MAP",
3636
"SWIFT_FEATURE_DEBUG_PREFIX_MAP",
37+
"SWIFT_FEATURE_EMIT_SWIFTDOC",
38+
"SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO",
3739
"SWIFT_FEATURE_MODULE_MAP_HOME_IS_CWD",
3840
"SWIFT_FEATURE_NO_GENERATED_MODULE_MAP",
3941
"SWIFT_FEATURE_OPT_USES_WMO",
@@ -315,6 +317,8 @@ def _swift_toolchain_impl(ctx):
315317
SWIFT_FEATURE_CACHEABLE_SWIFTMODULES,
316318
SWIFT_FEATURE_COVERAGE_PREFIX_MAP,
317319
SWIFT_FEATURE_DEBUG_PREFIX_MAP,
320+
SWIFT_FEATURE_EMIT_SWIFTDOC,
321+
SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO,
318322
SWIFT_FEATURE_NO_GENERATED_MODULE_MAP,
319323
SWIFT_FEATURE_OPT_USES_WMO,
320324
SWIFT_FEATURE_USE_GLOBAL_MODULE_CACHE,

swift/internal/xcode_swift_toolchain.bzl

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,8 @@ load(
3535
"SWIFT_FEATURE_COVERAGE",
3636
"SWIFT_FEATURE_COVERAGE_PREFIX_MAP",
3737
"SWIFT_FEATURE_DEBUG_PREFIX_MAP",
38+
"SWIFT_FEATURE_EMIT_SWIFTDOC",
39+
"SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO",
3840
"SWIFT_FEATURE_ENABLE_BATCH_MODE",
3941
"SWIFT_FEATURE_ENABLE_SKIP_FUNCTION_BODIES",
4042
"SWIFT_FEATURE_FILE_PREFIX_MAP",
@@ -614,6 +616,8 @@ def _xcode_swift_toolchain_impl(ctx):
614616
SWIFT_FEATURE_CACHEABLE_SWIFTMODULES,
615617
SWIFT_FEATURE_COVERAGE_PREFIX_MAP,
616618
SWIFT_FEATURE_DEBUG_PREFIX_MAP,
619+
SWIFT_FEATURE_EMIT_SWIFTDOC,
620+
SWIFT_FEATURE_EMIT_SWIFTSOURCEINFO,
617621
SWIFT_FEATURE_ENABLE_BATCH_MODE,
618622
SWIFT_FEATURE_ENABLE_SKIP_FUNCTION_BODIES,
619623
SWIFT_FEATURE_OBJC_LINK_FLAGS,

test/rules/provider_test.bzl

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -243,6 +243,16 @@ def _compare_expected_files(env, access_description, expected, actual):
243243
"""
244244
actual = _normalize_collection(actual)
245245

246+
expected_is_subset = "*" in expected
247+
expected_include = [
248+
s
249+
for s in expected
250+
if not s.startswith("-") and s != "*"
251+
]
252+
253+
if actual == [None] and not expected_include:
254+
return
255+
246256
if (
247257
not types.is_list(actual) or
248258
any([type(item) != "File" for item in actual])
@@ -259,13 +269,6 @@ def _compare_expected_files(env, access_description, expected, actual):
259269
return
260270

261271
remaining = list(actual)
262-
263-
expected_is_subset = "*" in expected
264-
expected_include = [
265-
s
266-
for s in expected
267-
if not s.startswith("-") and s != "*"
268-
]
269272
expected_exclude = [s[1:] for s in expected if s.startswith("-")]
270273

271274
# For every expected file, pick off the first actual that we find that has

test/split_derived_files_tests.bzl

Lines changed: 119 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,36 @@ split_swiftmodule_skip_function_bodies_test = make_action_command_line_test_rule
5656
],
5757
},
5858
)
59+
default_no_split_no_emit_swiftdoc_test = make_provider_test_rule(
60+
config_settings = {
61+
"//command_line_option:features": [
62+
"-swift.emit_swiftdoc",
63+
],
64+
},
65+
)
66+
default_no_split_no_emit_swiftsourceinfo_test = make_provider_test_rule(
67+
config_settings = {
68+
"//command_line_option:features": [
69+
"-swift.emit_swiftsourceinfo",
70+
],
71+
},
72+
)
73+
split_no_emit_swiftdoc_test = make_provider_test_rule(
74+
config_settings = {
75+
"//command_line_option:features": [
76+
"-swift.emit_swiftdoc",
77+
"swift.split_derived_files_generation",
78+
],
79+
},
80+
)
81+
split_no_emit_swiftsourceinfo_test = make_provider_test_rule(
82+
config_settings = {
83+
"//command_line_option:features": [
84+
"-swift.emit_swiftsourceinfo",
85+
"swift.split_derived_files_generation",
86+
],
87+
},
88+
)
5989
split_swiftmodule_indexing_test = make_action_command_line_test_rule(
6090
config_settings = {
6191
"//command_line_option:features": [
@@ -124,7 +154,7 @@ def split_derived_files_test_suite(name):
124154
)
125155

126156
default_no_split_provider_test(
127-
name = "{}_default_no_split_provider".format(name),
157+
name = "{}_default_no_split_provider_swiftmodule".format(name),
128158
expected_files = [
129159
"test_fixtures_debug_settings_simple.swiftmodule",
130160
],
@@ -134,6 +164,94 @@ def split_derived_files_test_suite(name):
134164
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
135165
)
136166

167+
default_no_split_provider_test(
168+
name = "{}_default_no_split_provider_swiftdoc".format(name),
169+
expected_files = [
170+
"test_fixtures_debug_settings_simple.swiftdoc",
171+
],
172+
field = "direct_modules.swift.swiftdoc",
173+
provider = "SwiftInfo",
174+
tags = [name],
175+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
176+
)
177+
178+
default_no_split_provider_test(
179+
name = "{}_default_no_split_provider_swiftsourceinfo".format(name),
180+
expected_files = [
181+
"test_fixtures_debug_settings_simple.swiftsourceinfo",
182+
],
183+
field = "direct_modules.swift.swiftsourceinfo",
184+
provider = "SwiftInfo",
185+
tags = [name],
186+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
187+
)
188+
189+
default_no_split_no_emit_swiftdoc_test(
190+
name = "{}_default_no_split_provider_no_emit_swiftdoc".format(name),
191+
expected_files = [
192+
"-test_fixtures_debug_settings_simple.swiftdoc",
193+
],
194+
field = "direct_modules.swift.swiftdoc",
195+
provider = "SwiftInfo",
196+
tags = [name],
197+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
198+
)
199+
200+
default_no_split_no_emit_swiftsourceinfo_test(
201+
name = "{}_default_no_split_provider_no_emit_swiftsourceinfo".format(name),
202+
expected_files = [
203+
"-test_fixtures_debug_settings_simple.swiftsourceinfo",
204+
],
205+
field = "direct_modules.swift.swiftsourceinfo",
206+
provider = "SwiftInfo",
207+
tags = [name],
208+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
209+
)
210+
211+
split_swiftmodule_provider_test(
212+
name = "{}_split_provider_swiftdoc".format(name),
213+
field = "direct_modules.swift.swiftdoc",
214+
expected_files = [
215+
"test_fixtures_debug_settings_simple.swiftdoc",
216+
],
217+
provider = "SwiftInfo",
218+
tags = [name],
219+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
220+
)
221+
222+
split_swiftmodule_provider_test(
223+
name = "{}_split_provider_swiftsourceinfo".format(name),
224+
field = "direct_modules.swift.swiftsourceinfo",
225+
expected_files = [
226+
"test_fixtures_debug_settings_simple.swiftsourceinfo",
227+
],
228+
provider = "SwiftInfo",
229+
tags = [name],
230+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
231+
)
232+
233+
split_no_emit_swiftdoc_test(
234+
name = "{}_split_provider_no_emit_swiftdoc".format(name),
235+
field = "direct_modules.swift.swiftdoc",
236+
expected_files = [
237+
"-test_fixtures_debug_settings_simple.swiftdoc",
238+
],
239+
provider = "SwiftInfo",
240+
tags = [name],
241+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
242+
)
243+
244+
split_no_emit_swiftsourceinfo_test(
245+
name = "{}_split_provider_no_emit_swiftsourceinfo".format(name),
246+
field = "direct_modules.swift.swiftsourceinfo",
247+
expected_files = [
248+
"-test_fixtures_debug_settings_simple.swiftsourceinfo",
249+
],
250+
provider = "SwiftInfo",
251+
tags = [name],
252+
target_under_test = "@build_bazel_rules_swift//test/fixtures/debug_settings:simple",
253+
)
254+
137255
default_no_split_provider_test(
138256
name = "{}_default_no_split_provider_ccinfo".format(name),
139257
expected_files = [

0 commit comments

Comments
 (0)