Skip to content

Commit 28b1bf8

Browse files
authored
Merge pull request #1378 from DougGregor/executable-plugin-paths-5.9
[5.9] Add SDK and platform paths to plugin executables
2 parents 7555785 + d6e556f commit 28b1bf8

File tree

3 files changed

+112
-17
lines changed

3 files changed

+112
-17
lines changed

Sources/SwiftDriver/Jobs/FrontendJobHelpers.swift

+16-15
Original file line numberDiff line numberDiff line change
@@ -255,22 +255,11 @@ extension Driver {
255255
try commandLine.appendLast(.emitMacroExpansionFiles, from: &parsedOptions)
256256
}
257257

258-
if isFrontendArgSupported(.pluginPath) {
259-
try commandLine.appendAll(.pluginPath, from: &parsedOptions)
260-
261-
let defaultPluginPath = try toolchain.executableDir.parentDirectory
262-
.appending(components: "lib", "swift", "host", "plugins")
263-
commandLine.appendFlag(.pluginPath)
264-
commandLine.appendPath(defaultPluginPath)
265-
266-
let localPluginPath = try toolchain.executableDir.parentDirectory
267-
.appending(components: "local", "lib", "swift", "host", "plugins")
268-
commandLine.appendFlag(.pluginPath)
269-
commandLine.appendPath(localPluginPath)
270-
}
271-
258+
// Emit user-provided plugin paths, in order.
272259
if isFrontendArgSupported(.externalPluginPath) {
273-
try commandLine.appendAll(.externalPluginPath, from: &parsedOptions)
260+
try commandLine.appendAll(.pluginPath, .externalPluginPath, .loadPluginLibrary, .loadPluginExecutable, from: &parsedOptions)
261+
} else if isFrontendArgSupported(.pluginPath) {
262+
try commandLine.appendAll(.pluginPath, .loadPluginLibrary, from: &parsedOptions)
274263
}
275264

276265
// Pass down -user-module-version if we are working with a compiler that
@@ -381,6 +370,18 @@ extension Driver {
381370
inputs: &inputs,
382371
frontendTargetInfo: frontendTargetInfo,
383372
driver: &self)
373+
374+
// Platform-agnostic options that need to happen after platform-specific ones.
375+
if isFrontendArgSupported(.pluginPath) {
376+
// Default paths for compiler plugins found within the toolchain
377+
// (loaded as shared libraries).
378+
let pluginPathRoot = VirtualPath.absolute(try toolchain.executableDir.parentDirectory)
379+
commandLine.appendFlag(.pluginPath)
380+
commandLine.appendPath(pluginPathRoot.pluginPath)
381+
382+
commandLine.appendFlag(.pluginPath)
383+
commandLine.appendPath(pluginPathRoot.localPluginPath)
384+
}
384385
}
385386

386387
mutating func addFrontendSupplementaryOutputArguments(commandLine: inout [Job.ArgTemplate],

Sources/SwiftDriver/Toolchains/DarwinToolchain.swift

+44
Original file line numberDiff line numberDiff line change
@@ -421,6 +421,30 @@ public final class DarwinToolchain: Toolchain {
421421
commandLine.appendFlag(.clangTarget)
422422
commandLine.appendFlag(clangTargetTriple)
423423
}
424+
425+
if driver.isFrontendArgSupported(.externalPluginPath) {
426+
// Default paths for compiler plugins found within an SDK (accessed via
427+
// that SDK's plugin server).
428+
let sdkPathRoot = VirtualPath.lookup(sdkPath).appending(components: "usr")
429+
commandLine.appendFlag(.externalPluginPath)
430+
commandLine.appendFlag("\(sdkPathRoot.pluginPath.name)#\(sdkPathRoot.pluginServerPath.name.spm_shellEscaped())")
431+
432+
commandLine.appendFlag(.externalPluginPath)
433+
commandLine.appendFlag("\(sdkPathRoot.localPluginPath.name)#\(sdkPathRoot.pluginServerPath.name.spm_shellEscaped())")
434+
435+
// Default paths for compiler plugins within the platform (accessed via that
436+
// platform's plugin server).
437+
let platformPathRoot = VirtualPath.lookup(sdkPath)
438+
.parentDirectory
439+
.parentDirectory
440+
.parentDirectory
441+
.appending(components: "Developer", "usr")
442+
commandLine.appendFlag(.externalPluginPath)
443+
commandLine.appendFlag("\(platformPathRoot.pluginPath.name)#\(platformPathRoot.pluginServerPath.name.spm_shellEscaped())")
444+
445+
commandLine.appendFlag(.externalPluginPath)
446+
commandLine.appendFlag("\(platformPathRoot.localPluginPath.name)#\(platformPathRoot.pluginServerPath.name.spm_shellEscaped())")
447+
}
424448
}
425449
}
426450

@@ -441,3 +465,23 @@ private extension Version {
441465
return self.description
442466
}
443467
}
468+
469+
extension VirtualPath {
470+
// Given a virtual path pointing into a toolchain/SDK/platform, produce the
471+
// path to `swift-plugin-server`.
472+
fileprivate var pluginServerPath: VirtualPath {
473+
self.appending(components: "bin", "swift-plugin-server")
474+
}
475+
476+
// Given a virtual path pointing into a toolchain/SDK/platform, produce the
477+
// path to the plugins.
478+
var pluginPath: VirtualPath {
479+
self.appending(components: "lib", "swift", "host", "plugins")
480+
}
481+
482+
// Given a virtual path pointing into a toolchain/SDK/platform, produce the
483+
// path to the plugins.
484+
var localPluginPath: VirtualPath {
485+
self.appending(component: "local").pluginPath
486+
}
487+
}

Tests/SwiftDriverTests/SwiftDriverTests.swift

+52-2
Original file line numberDiff line numberDiff line change
@@ -6757,14 +6757,64 @@ final class SwiftDriverTests: XCTestCase {
67576757
}
67586758

67596759
func testPluginPaths() throws {
6760-
var driver = try Driver(args: ["swiftc", "-typecheck", "foo.swift"])
6761-
guard driver.isFrontendArgSupported(.pluginPath) else {
6760+
let sdkRoot = testInputsPath.appending(component: "SDKChecks").appending(component: "iPhoneOS.sdk")
6761+
var driver = try Driver(args: ["swiftc", "-typecheck", "foo.swift", "-sdk", VirtualPath.absolute(sdkRoot).name, "-plugin-path", "PluginA", "-external-plugin-path", "PluginB#Bexe", "-load-plugin-library", "PluginB2", "-plugin-path", "PluginC"])
6762+
guard driver.isFrontendArgSupported(.pluginPath) && driver.isFrontendArgSupported(.externalPluginPath) else {
67626763
return
67636764
}
67646765

67656766
let jobs = try driver.planBuild().removingAutolinkExtractJobs()
67666767
XCTAssertEqual(jobs.count, 1)
67676768
let job = jobs.first!
6769+
6770+
// Check that the we have the plugin paths we expect, in the order we expect.
6771+
let pluginAIndex = job.commandLine.firstIndex(of: .path(VirtualPath.relative(.init("PluginA"))))
6772+
XCTAssertNotNil(pluginAIndex)
6773+
6774+
let pluginBIndex = job.commandLine.firstIndex(of: .path(VirtualPath.relative(.init("PluginB#Bexe"))))
6775+
XCTAssertNotNil(pluginBIndex)
6776+
XCTAssertLessThan(pluginAIndex!, pluginBIndex!)
6777+
6778+
let pluginB2Index = job.commandLine.firstIndex(of: .path(VirtualPath.relative(.init("PluginB2"))))
6779+
XCTAssertNotNil(pluginB2Index)
6780+
XCTAssertLessThan(pluginBIndex!, pluginB2Index!)
6781+
6782+
let pluginCIndex = job.commandLine.firstIndex(of: .path(VirtualPath.relative(.init("PluginC"))))
6783+
XCTAssertNotNil(pluginCIndex)
6784+
XCTAssertLessThan(pluginB2Index!, pluginCIndex!)
6785+
6786+
#if os(macOS)
6787+
XCTAssertTrue(job.commandLine.contains(.flag("-external-plugin-path")))
6788+
let sdkServerPath = sdkRoot.appending(components: "usr", "bin", "swift-plugin-server").pathString
6789+
let sdkPluginPath = sdkRoot.appending(components: "usr", "lib", "swift", "host", "plugins").pathString
6790+
6791+
let sdkPluginPathIndex = job.commandLine.firstIndex(of: .flag("\(sdkPluginPath)#\(sdkServerPath)"))
6792+
XCTAssertNotNil(sdkPluginPathIndex)
6793+
XCTAssertLessThan(pluginCIndex!, sdkPluginPathIndex!)
6794+
6795+
let sdkLocalPluginPath = sdkRoot.appending(components: "usr", "local", "lib", "swift", "host", "plugins").pathString
6796+
let sdkLocalPluginPathIndex = job.commandLine.firstIndex(of: .flag("\(sdkLocalPluginPath)#\(sdkServerPath)"))
6797+
XCTAssertNotNil(sdkLocalPluginPathIndex)
6798+
XCTAssertLessThan(sdkPluginPathIndex!, sdkLocalPluginPathIndex!)
6799+
6800+
let platformPath = sdkRoot.parentDirectory.parentDirectory.parentDirectory.appending(components: "Developer", "usr")
6801+
let platformServerPath = platformPath.appending(components: "bin", "swift-plugin-server").pathString
6802+
6803+
let platformPluginPath = platformPath.appending(components: "lib", "swift", "host", "plugins")
6804+
let platformPluginPathIndex = job.commandLine.firstIndex(of: .flag("\(platformPluginPath)#\(platformServerPath)"))
6805+
XCTAssertNotNil(platformPluginPathIndex)
6806+
XCTAssertLessThan(sdkLocalPluginPathIndex!, platformPluginPathIndex!)
6807+
6808+
let platformLocalPluginPath = platformPath.appending(components: "local", "lib", "swift", "host", "plugins")
6809+
let platformLocalPluginPathIndex = job.commandLine.firstIndex(of: .flag("\(platformLocalPluginPath)#\(platformServerPath)"))
6810+
XCTAssertNotNil(platformLocalPluginPathIndex)
6811+
XCTAssertLessThan(platformPluginPathIndex!, platformLocalPluginPathIndex!)
6812+
6813+
let toolchainPluginPathIndex = job.commandLine.firstIndex(of: .path(.absolute(try driver.toolchain.executableDir.parentDirectory.appending(components: "lib", "swift", "host", "plugins"))))
6814+
XCTAssertNotNil(toolchainPluginPathIndex)
6815+
XCTAssertLessThan(platformLocalPluginPathIndex!, toolchainPluginPathIndex!)
6816+
#endif
6817+
67686818
XCTAssertTrue(job.commandLine.contains(.flag("-plugin-path")))
67696819
XCTAssertTrue(job.commandLine.contains(.path(.absolute(try driver.toolchain.executableDir.parentDirectory.appending(components: "lib", "swift", "host", "plugins")))))
67706820
XCTAssertTrue(job.commandLine.contains(.path(.absolute(try driver.toolchain.executableDir.parentDirectory.appending(components: "local", "lib", "swift", "host", "plugins")))))

0 commit comments

Comments
 (0)