Skip to content

Commit 2234d74

Browse files
committed
[Explicit Module Builds] Add libSwiftScan API for scanner cache serialization/deserialization
swiftlang/swift#37723 added API to libSwiftScan to save and restore the dependency scanner's state on the filesystem. This PR adds this API to the corresponding client code in the driver.
1 parent 02dd592 commit 2234d74

File tree

6 files changed

+93
-26
lines changed

6 files changed

+93
-26
lines changed

Package.resolved

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Sources/CSwiftScan/include/swiftscan_header.h

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -200,17 +200,20 @@ typedef struct {
200200
//=== Scanner Functions ---------------------------------------------------===//
201201
swiftscan_scanner_t (*swiftscan_scanner_create)(void);
202202
void (*swiftscan_scanner_dispose)(swiftscan_scanner_t);
203-
204203
swiftscan_dependency_graph_t
205204
(*swiftscan_dependency_graph_create)(swiftscan_scanner_t, swiftscan_scan_invocation_t);
206-
207205
swiftscan_batch_scan_result_t *
208206
(*swiftscan_batch_scan_result_create)(swiftscan_scanner_t,
209207
swiftscan_batch_scan_input_t *,
210208
swiftscan_scan_invocation_t);
211-
212209
swiftscan_import_set_t
213210
(*swiftscan_import_set_create)(swiftscan_scanner_t, swiftscan_scan_invocation_t);
211+
212+
//=== Scanner Cache Functions ---------------------------------------------===//
213+
void (*swiftscan_scanner_cache_serialize)(swiftscan_scanner_t scanner, const char * path);
214+
bool (*swiftscan_scanner_cache_load)(swiftscan_scanner_t scanner, const char * path);
215+
bool (*swiftscan_scanner_cache_reset)(swiftscan_scanner_t scanner);
216+
214217
} swiftscan_functions_t;
215218

216219
#endif // SWIFT_C_DEPENDENCY_SCAN_H

Sources/SwiftDriver/ExplicitModuleBuilds/InterModuleDependencies/InterModuleDependencyOracle.swift

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,33 @@ public class InterModuleDependencyOracle {
7373
}
7474
}
7575

76+
@_spi(Testing) public func serializeScannerCache(to path: AbsolutePath) {
77+
guard let swiftScan = swiftScanLibInstance else {
78+
fatalError("Attempting to serialize scanner cache with no scanner instance.")
79+
}
80+
if swiftScan.canLoadStoreScannerCache() {
81+
swiftScan.serializeScannerCache(to: path)
82+
}
83+
}
84+
85+
@_spi(Testing) public func loadScannerCache(from path: AbsolutePath) {
86+
guard let swiftScan = swiftScanLibInstance else {
87+
fatalError("Attempting to load scanner cache with no scanner instance.")
88+
}
89+
if swiftScan.canLoadStoreScannerCache() {
90+
swiftScan.loadScannerCache(from: path)
91+
}
92+
}
93+
94+
@_spi(Testing) public func resetScannerCache() {
95+
guard let swiftScan = swiftScanLibInstance else {
96+
fatalError("Attempting to reset scanner cache with no scanner instance.")
97+
}
98+
if swiftScan.canLoadStoreScannerCache() {
99+
swiftScan.resetScannerCache()
100+
}
101+
}
102+
76103
private var hasScannerInstance: Bool { self.swiftScanLibInstance != nil }
77104

78105
/// Queue to sunchronize accesses to the scanner

Sources/SwiftDriver/Jobs/CompileJob.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -93,7 +93,7 @@ extension Driver {
9393
.privateSwiftInterface, .swiftSourceInfoFile, .diagnostics, .objcHeader, .swiftDeps,
9494
.remap, .tbd, .moduleTrace, .yamlOptimizationRecord, .bitstreamOptimizationRecord, .pcm,
9595
.pch, .clangModuleMap, .jsonCompilerFeatures, .jsonTargetInfo, .jsonSwiftArtifacts,
96-
.indexUnitOutputPath, nil:
96+
.indexUnitOutputPath, .modDepCache, nil:
9797
return false
9898
}
9999
}
@@ -444,7 +444,7 @@ extension FileType {
444444
.diagnostics, .objcHeader, .image, .swiftDeps, .moduleTrace, .tbd,
445445
.yamlOptimizationRecord, .bitstreamOptimizationRecord, .swiftInterface,
446446
.privateSwiftInterface, .swiftSourceInfoFile, .clangModuleMap, .jsonSwiftArtifacts,
447-
.indexUnitOutputPath:
447+
.indexUnitOutputPath, .modDepCache:
448448
fatalError("Output type can never be a primary output")
449449
}
450450
}

Sources/SwiftDriver/SwiftScan/SwiftScan.swift

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -181,6 +181,26 @@ internal final class SwiftScan {
181181
return resultGraphMap
182182
}
183183

184+
@_spi(Testing) public func canLoadStoreScannerCache() -> Bool {
185+
return api.swiftscan_scanner_cache_load != nil &&
186+
api.swiftscan_scanner_cache_serialize != nil &&
187+
api.swiftscan_scanner_cache_reset != nil
188+
}
189+
190+
func serializeScannerCache(to path: AbsolutePath) {
191+
api.swiftscan_scanner_cache_serialize(scanner,
192+
path.description.cString(using: String.Encoding.utf8))
193+
}
194+
195+
func loadScannerCache(from path: AbsolutePath) {
196+
api.swiftscan_scanner_cache_load(scanner,
197+
path.description.cString(using: String.Encoding.utf8))
198+
}
199+
200+
func resetScannerCache() {
201+
api.swiftscan_scanner_cache_reset(scanner)
202+
}
203+
184204
@_spi(Testing) public func canQuerySupportedArguments() -> Bool {
185205
return api.swiftscan_compiler_supported_arguments_query != nil &&
186206
api.swiftscan_string_set_dispose != nil
@@ -226,13 +246,22 @@ private extension swiftscan_functions_t {
226246
}
227247
return sym
228248
}
249+
// Supported features/flags query
229250
self.swiftscan_string_set_dispose =
230251
try loadOptional("swiftscan_string_set_dispose")
231252
self.swiftscan_compiler_supported_arguments_query =
232253
try loadOptional("swiftscan_compiler_supported_arguments_query")
233254
self.swiftscan_compiler_supported_features_query =
234255
try loadOptional("swiftscan_compiler_supported_features_query")
235256

257+
// Dependency scanner serialization/deserialization features
258+
self.swiftscan_scanner_cache_serialize =
259+
try loadOptional("swiftscan_scanner_cache_serialize")
260+
self.swiftscan_scanner_cache_load =
261+
try loadOptional("swiftscan_scanner_cache_load")
262+
self.swiftscan_scanner_cache_reset =
263+
try loadOptional("swiftscan_scanner_cache_reset")
264+
236265
// MARK: Required Methods
237266
func loadRequired<T>(_ symbol: String) throws -> T {
238267
guard let sym: T = dlsym(swiftscan, symbol: symbol) else {

Sources/SwiftDriver/Utilities/FileType.swift

Lines changed: 28 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
/// The raw values for these enumerations describe the default extension for
1616
/// the file type.
1717
public enum FileType: String, Hashable, CaseIterable, Codable {
18-
/// Swift source file.
18+
/// Swift source file
1919
case swift
2020

2121
/// (Canonical) SIL source file
@@ -27,34 +27,34 @@ public enum FileType: String, Hashable, CaseIterable, Codable {
2727
/// AST dump
2828
case ast
2929

30-
/// An executable image.
30+
/// An executable image
3131
case image = "out"
3232

33-
/// An object file.
33+
/// An object file
3434
case object = "o"
3535

36-
/// A dSYM directory.
36+
/// A dSYM directory
3737
case dSYM
3838

39-
/// A file containing make-style dependencies.
39+
/// A file containing make-style dependencies
4040
case dependencies = "d"
4141

4242
/// An autolink input file
4343
case autolink
4444

45-
/// A compiled Swift module file.
45+
/// A compiled Swift module file
4646
case swiftModule = "swiftmodule"
4747

48-
/// Swift documentation for a module.
48+
/// Swift documentation for a module
4949
case swiftDocumentation = "swiftdoc"
5050

51-
/// A textual Swift interface file.
51+
/// A textual Swift interface file
5252
case swiftInterface = "swiftinterface"
5353

54-
/// An SPI Swift Interface file.
54+
/// An SPI Swift Interface file
5555
case privateSwiftInterface = "private.swiftinterface"
5656

57-
/// Serialized source information.
57+
/// Serialized source information
5858
case swiftSourceInfoFile = "swiftsourceinfo"
5959

6060
/// Assembler source.
@@ -78,16 +78,19 @@ public enum FileType: String, Hashable, CaseIterable, Codable {
7878
/// Objective-C header
7979
case objcHeader = "h"
8080

81-
/// Swift dependencies file.
81+
/// Swift dependencies file
8282
case swiftDeps = "swiftdeps"
8383

84+
/// Serialized dependency scanner state
85+
case modDepCache = "moddepcache"
86+
8487
/// Remapping file
8588
case remap
8689

8790
/// Imported modules.
8891
case importedModules = "importedmodules"
8992

90-
/// Text-based dylib (TBD) file.
93+
/// Text-based dylib (TBD) file
9194
case tbd
9295

9396
/// JSON-based Module Dependency Scanner output
@@ -102,27 +105,27 @@ public enum FileType: String, Hashable, CaseIterable, Codable {
102105
/// JSON-based binary Swift module artifact description
103106
case jsonSwiftArtifacts = "artifacts.json"
104107

105-
/// Module trace file.
108+
/// Module trace file
106109
///
107110
/// Module traces are used by Apple's internal build infrastructure. Apple
108111
/// engineers can see more details on the "Swift module traces" page in the
109112
/// Swift section of the internal wiki.
110113
case moduleTrace = "trace.json"
111114

112-
/// Indexing data directory.
115+
/// Indexing data directory
113116
///
114-
/// The extension isn't real.
117+
/// The extension isn't real, rather this FileType specifies a directory path.
115118
case indexData
116119

117120
/// Output path to record in the indexing data store
118121
///
119122
/// This is only needed for use as a key in the output file map.
120123
case indexUnitOutputPath
121124

122-
/// Optimization record.
125+
/// Optimization record
123126
case yamlOptimizationRecord = "opt.yaml"
124127

125-
/// Bitstream optimization record.
128+
/// Bitstream optimization record
126129
case bitstreamOptimizationRecord = "opt.bitstream"
127130

128131
/// Clang compiler module file
@@ -169,6 +172,9 @@ extension FileType: CustomStringConvertible {
169172
case .swiftDeps:
170173
return "swift-dependencies"
171174

175+
case .modDepCache:
176+
return "dependency-scanner-cache"
177+
172178
case .jsonDependencies:
173179
return "json-dependencies"
174180

@@ -218,7 +224,7 @@ extension FileType {
218224
.swiftDeps, .moduleTrace, .tbd, .yamlOptimizationRecord, .bitstreamOptimizationRecord,
219225
.swiftInterface, .privateSwiftInterface, .swiftSourceInfoFile, .jsonDependencies,
220226
.clangModuleMap, .jsonTargetInfo, .jsonCompilerFeatures, .jsonSwiftArtifacts,
221-
.indexUnitOutputPath:
227+
.indexUnitOutputPath, .modDepCache:
222228
return false
223229
}
224230
}
@@ -289,6 +295,8 @@ extension FileType {
289295
return "objc-header"
290296
case .swiftDeps:
291297
return "swift-dependencies"
298+
case .modDepCache:
299+
return "dependency-scanner-cache"
292300
case .jsonDependencies:
293301
return "json-dependencies"
294302
case .jsonTargetInfo:
@@ -327,7 +335,7 @@ extension FileType {
327335
case .image, .object, .dSYM, .pch, .sib, .raw_sib, .swiftModule,
328336
.swiftDocumentation, .swiftSourceInfoFile, .llvmBitcode, .diagnostics,
329337
.pcm, .swiftDeps, .remap, .indexData, .bitstreamOptimizationRecord,
330-
.indexUnitOutputPath:
338+
.indexUnitOutputPath, .modDepCache:
331339
return false
332340
}
333341
}
@@ -341,7 +349,7 @@ extension FileType {
341349
case .swift, .sil, .sib, .ast, .image, .dSYM, .dependencies, .autolink,
342350
.swiftModule, .swiftDocumentation, .swiftInterface, .privateSwiftInterface,
343351
.swiftSourceInfoFile, .raw_sil, .raw_sib, .diagnostics, .objcHeader, .swiftDeps, .remap,
344-
.importedModules, .tbd, .moduleTrace, .indexData, .yamlOptimizationRecord,
352+
.importedModules, .tbd, .moduleTrace, .indexData, .yamlOptimizationRecord, .modDepCache,
345353
.bitstreamOptimizationRecord, .pcm, .pch, .jsonDependencies, .clangModuleMap,
346354
.jsonCompilerFeatures, .jsonTargetInfo, .jsonSwiftArtifacts, .indexUnitOutputPath:
347355
return false

0 commit comments

Comments
 (0)