Skip to content

Commit 85c26cb

Browse files
committed
[Explicit Module Builds] Move generation of explicit auto-link flags to a toolchain-specific method
This way we can adopt a feature of a specific platform's linker separately from the others
1 parent 0c2ef21 commit 85c26cb

File tree

7 files changed

+91
-11
lines changed

7 files changed

+91
-11
lines changed

Sources/SwiftDriver/ExplicitModuleBuilds/ExplicitDependencyBuildPlanner.swift

+1-11
Original file line numberDiff line numberDiff line change
@@ -421,17 +421,7 @@ public typealias ExternalTargetModuleDetailsMap = [ModuleDependencyId: ExternalT
421421
allLinkLibraries.append(linkLibrary)
422422
}
423423
}
424-
425-
for linkLibrary in allLinkLibraries {
426-
if !linkLibrary.isFramework {
427-
commandLine.appendFlag("-l\(linkLibrary.linkName)")
428-
} else {
429-
commandLine.appendFlag(.Xlinker)
430-
commandLine.appendFlag("-framework")
431-
commandLine.appendFlag(.Xlinker)
432-
commandLine.appendFlag(linkLibrary.linkName)
433-
}
434-
}
424+
toolchain.addAutoLinkFlags(for: allLinkLibraries, to: &commandLine)
435425
}
436426

437427
/// Resolve all module dependencies of the main module and add them to the lists of

Sources/SwiftDriver/Toolchains/DarwinToolchain.swift

+14
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,20 @@ public final class DarwinToolchain: Toolchain {
114114
}
115115
}
116116

117+
public func addAutoLinkFlags(for linkLibraries: [LinkLibraryInfo], to commandLine: inout [Job.ArgTemplate]) {
118+
for linkLibrary in linkLibraries {
119+
if !linkLibrary.isFramework {
120+
commandLine.appendFlag(.Xlinker)
121+
commandLine.appendFlag("-possible-l\(linkLibrary.linkName)")
122+
} else {
123+
commandLine.appendFlag(.Xlinker)
124+
commandLine.appendFlag("-possible_framework")
125+
commandLine.appendFlag(.Xlinker)
126+
commandLine.appendFlag(linkLibrary.linkName)
127+
}
128+
}
129+
}
130+
117131
public func defaultSDKPath(_ target: Triple?) throws -> AbsolutePath? {
118132
let hostIsMacOS: Bool
119133
#if os(macOS)

Sources/SwiftDriver/Toolchains/GenericUnixToolchain.swift

+6
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,12 @@ public final class GenericUnixToolchain: Toolchain {
7878
}
7979
}
8080

81+
public func addAutoLinkFlags(for linkLibraries: [LinkLibraryInfo], to commandLine: inout [Job.ArgTemplate]) {
82+
for linkLibrary in linkLibraries {
83+
commandLine.appendFlag("-l\(linkLibrary.linkName)")
84+
}
85+
}
86+
8187
/// Retrieve the absolute path for a given tool.
8288
public func getToolPath(_ tool: Tool) throws -> AbsolutePath {
8389
// Check the cache

Sources/SwiftDriver/Toolchains/Toolchain.swift

+3
Original file line numberDiff line numberDiff line change
@@ -115,6 +115,9 @@ public protocol Toolchain {
115115
/// Constructs a proper output file name for a linker product.
116116
func makeLinkerOutputFilename(moduleName: String, type: LinkOutputType) -> String
117117

118+
/// Adds linker flags corresponding to the specified set of link libraries
119+
func addAutoLinkFlags(for linkLibraries: [LinkLibraryInfo], to commandLine: inout [Job.ArgTemplate])
120+
118121
/// Perform platform-specific argument validation.
119122
func validateArgs(_ parsedOptions: inout ParsedOptions,
120123
targetTriple: Triple,

Sources/SwiftDriver/Toolchains/WebAssemblyToolchain.swift

+6
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,12 @@ public final class WebAssemblyToolchain: Toolchain {
7979
}
8080
}
8181

82+
public func addAutoLinkFlags(for linkLibraries: [LinkLibraryInfo], to commandLine: inout [Job.ArgTemplate]) {
83+
for linkLibrary in linkLibraries {
84+
commandLine.appendFlag("-l\(linkLibrary.linkName)")
85+
}
86+
}
87+
8288
/// Retrieve the absolute path for a given tool.
8389
public func getToolPath(_ tool: Tool) throws -> AbsolutePath {
8490
// Check the cache

Sources/SwiftDriver/Toolchains/WindowsToolchain.swift

+6
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,12 @@ extension WindowsToolchain.ToolchainValidationError {
113113
}
114114
}
115115

116+
public func addAutoLinkFlags(for linkLibraries: [LinkLibraryInfo], to commandLine: inout [Job.ArgTemplate]) {
117+
for linkLibrary in linkLibraries {
118+
commandLine.appendFlag("-l\(linkLibrary.linkName)")
119+
}
120+
}
121+
116122
public func defaultSDKPath(_ target: Triple?) throws -> AbsolutePath? {
117123
// TODO(compnerd): replicate the SPM processing of the SDKInfo.plist
118124
if let SDKROOT = env["SDKROOT"] {

Tests/SwiftDriverTests/ExplicitModuleBuildTests.swift

+55
Original file line numberDiff line numberDiff line change
@@ -500,6 +500,61 @@ final class ExplicitModuleBuildTests: XCTestCase {
500500
}
501501
}
502502

503+
func testExplicitLinkFlags() throws {
504+
try withTemporaryDirectory { path in
505+
let (_, _, toolchain, _) = try getDriverArtifactsForScanning()
506+
507+
let main = path.appending(component: "testExplicitLinkLibraries.swift")
508+
try localFileSystem.writeFileContents(main, bytes:
509+
"""
510+
import C;import E;import G;
511+
"""
512+
)
513+
514+
let cHeadersPath: AbsolutePath =
515+
try testInputsPath.appending(component: "ExplicitModuleBuilds")
516+
.appending(component: "CHeaders")
517+
let bridgingHeaderpath: AbsolutePath =
518+
cHeadersPath.appending(component: "Bridging.h")
519+
let swiftModuleInterfacesPath: AbsolutePath =
520+
try testInputsPath.appending(component: "ExplicitModuleBuilds")
521+
.appending(component: "Swift")
522+
let sdkArgumentsForTesting = (try? Driver.sdkArgumentsForTesting()) ?? []
523+
524+
// Verify the dependency scanner supports link library reporting
525+
let dependencyOracle = InterModuleDependencyOracle()
526+
let scanLibPath = try XCTUnwrap(toolchain.lookupSwiftScanLib())
527+
try dependencyOracle.verifyOrCreateScannerInstance(swiftScanLibPath: scanLibPath)
528+
guard try dependencyOracle.supportsLinkLibraries() else {
529+
throw XCTSkip("libSwiftScan does not support link library reporting.")
530+
}
531+
532+
let args = ["swiftc",
533+
"-I", cHeadersPath.nativePathString(escaped: true),
534+
"-I", swiftModuleInterfacesPath.nativePathString(escaped: true),
535+
"-explicit-module-build", "-explicit-auto-linking",
536+
"-import-objc-header", bridgingHeaderpath.nativePathString(escaped: true),
537+
main.nativePathString(escaped: true)] + sdkArgumentsForTesting
538+
var driver = try Driver(args: args)
539+
let jobs = try driver.planBuild()
540+
541+
let linkJob = try jobs.findJob(.link)
542+
if driver.targetTriple.isDarwin {
543+
XCTAssertTrue(linkJob.commandLine.contains("-possible-lswiftCore"))
544+
XCTAssertTrue(linkJob.commandLine.contains("-possible-lswift_StringProcessing"))
545+
XCTAssertTrue(linkJob.commandLine.contains("-possible-lobjc"))
546+
XCTAssertTrue(linkJob.commandLine.contains("-possible-lswift_Concurrency"))
547+
XCTAssertTrue(linkJob.commandLine.contains("-possible-lswiftSwiftOnoneSupport"))
548+
} else {
549+
XCTAssertTrue(linkJob.commandLine.contains("-lswiftCore"))
550+
XCTAssertTrue(linkJob.commandLine.contains("-lswift_StringProcessing"))
551+
XCTAssertTrue(linkJob.commandLine.contains("-lobjc"))
552+
XCTAssertTrue(linkJob.commandLine.contains("-lswift_Concurrency"))
553+
XCTAssertTrue(linkJob.commandLine.contains("-lswiftSwiftOnoneSupport"))
554+
}
555+
}
556+
}
557+
503558
func testExplicitLinkLibraries() throws {
504559
try withTemporaryDirectory { path in
505560
let (_, _, toolchain, _) = try getDriverArtifactsForScanning()

0 commit comments

Comments
 (0)