From 1b17f332219f1b5935b5745b4e98a21baa3ede94 Mon Sep 17 00:00:00 2001 From: Doug Gregor Date: Thu, 20 Jul 2023 10:28:52 -0700 Subject: [PATCH 1/3] [Macros on Darwin] Use device platform paths when building for the simulator To avoid having duplicated macro implementations in both the device and simulator platforms, when building for a simulator platform, pass `-external-plugin-path` that points into the *device* platform. There is no need to have macro implementations in the simulator platforms. Implements rdar://112563633 --- .../Toolchains/DarwinToolchain.swift | 18 ++++++++++++++---- .../SDKs/iPhoneOS.sdk/SDKSettings.json | 4 ++++ .../SDKs/iPhoneSimulator.sdk/SDKSettings.json | 4 ++++ Tests/SwiftDriverTests/SwiftDriverTests.swift | 14 ++++++++++++-- 4 files changed, 34 insertions(+), 6 deletions(-) create mode 100644 TestInputs/PlatformChecks/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/SDKSettings.json create mode 100644 TestInputs/PlatformChecks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/SDKSettings.json diff --git a/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift b/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift index 3cbff2106..a70adf24c 100644 --- a/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift +++ b/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift @@ -434,13 +434,23 @@ public final class DarwinToolchain: Toolchain { commandLine.appendFlag(.externalPluginPath) commandLine.appendFlag("\(sdkPathRoot.localPluginPath.name)#\(sdkPathRoot.pluginServerPath.name.spm_shellEscaped())") - // Default paths for compiler plugins within the platform (accessed via that - // platform's plugin server). - let platformPathRoot = VirtualPath.lookup(sdkPath) + // Determine the platform path. For simulator platforms, look into the + // corresponding device platform instance. + let origPlatformPath = VirtualPath.lookup(sdkPath) .parentDirectory .parentDirectory .parentDirectory - .appending(components: "Developer", "usr") + let platformPath: VirtualPath + if let simulatorRange = origPlatformPath.basename.range(of: "Simulator.platform") { + let devicePlatform = origPlatformPath.basename.replacingCharacters(in: simulatorRange, with: "OS.platform") + platformPath = origPlatformPath.parentDirectory.appending(component: devicePlatform) + } else { + platformPath = origPlatformPath + } + + // Default paths for compiler plugins within the platform (accessed via that + // platform's plugin server). + let platformPathRoot = platformPath.appending(components: "Developer", "usr") commandLine.appendFlag(.externalPluginPath) commandLine.appendFlag("\(platformPathRoot.pluginPath.name)#\(platformPathRoot.pluginServerPath.name.spm_shellEscaped())") diff --git a/TestInputs/PlatformChecks/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/SDKSettings.json b/TestInputs/PlatformChecks/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/SDKSettings.json new file mode 100644 index 000000000..9c61188fb --- /dev/null +++ b/TestInputs/PlatformChecks/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/SDKSettings.json @@ -0,0 +1,4 @@ +{ + "Version": "13.0", + "CanonicalName": "iphoneos13.0" +} diff --git a/TestInputs/PlatformChecks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/SDKSettings.json b/TestInputs/PlatformChecks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/SDKSettings.json new file mode 100644 index 000000000..bf57dcd27 --- /dev/null +++ b/TestInputs/PlatformChecks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/SDKSettings.json @@ -0,0 +1,4 @@ +{ + "Version": "15.0", + "CanonicalName": "iphonesimulator15.0" +} diff --git a/Tests/SwiftDriverTests/SwiftDriverTests.swift b/Tests/SwiftDriverTests/SwiftDriverTests.swift index 6a62ad7a3..026c5906f 100644 --- a/Tests/SwiftDriverTests/SwiftDriverTests.swift +++ b/Tests/SwiftDriverTests/SwiftDriverTests.swift @@ -6869,7 +6869,13 @@ final class SwiftDriverTests: XCTestCase { } func testPluginPaths() throws { - let sdkRoot = testInputsPath.appending(component: "SDKChecks").appending(component: "iPhoneOS.sdk") + try pluginPathTest(platform: "iPhoneOS", searchPlatform: "iPhoneOS") + try pluginPathTest(platform: "iPhoneSimulator", searchPlatform: "iPhoneOS") + } + + func pluginPathTest(platform: String, searchPlatform: String) throws { + let sdkRoot = testInputsPath.appending( + components: ["PlatformChecks", "\(platform).platform", "Developer", "SDKs", "\(platform).sdk"]) 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"]) guard driver.isFrontendArgSupported(.pluginPath) && driver.isFrontendArgSupported(.externalPluginPath) else { return @@ -6909,7 +6915,11 @@ final class SwiftDriverTests: XCTestCase { XCTAssertNotNil(sdkLocalPluginPathIndex) XCTAssertLessThan(sdkPluginPathIndex!, sdkLocalPluginPathIndex!) - let platformPath = sdkRoot.parentDirectory.parentDirectory.parentDirectory.appending(components: "Developer", "usr") + let origPlatformPath = + sdkRoot.parentDirectory.parentDirectory.parentDirectory.parentDirectory + .appending(component: "\(searchPlatform).platform") + + let platformPath = origPlatformPath.appending(components: "Developer", "usr") let platformServerPath = platformPath.appending(components: "bin", "swift-plugin-server").pathString let platformPluginPath = platformPath.appending(components: "lib", "swift", "host", "plugins") From 20c26c20829b5170d287d524d1c0d37b76738309 Mon Sep 17 00:00:00 2001 From: Doug Gregor Date: Thu, 20 Jul 2023 10:33:49 -0700 Subject: [PATCH 2/3] [Platform paths for Darwin macros] Don't escape paths --- Sources/SwiftDriver/Toolchains/DarwinToolchain.swift | 8 ++++---- Tests/SwiftDriverTests/SwiftDriverTests.swift | 4 ++-- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift b/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift index a70adf24c..cf099be5b 100644 --- a/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift +++ b/Sources/SwiftDriver/Toolchains/DarwinToolchain.swift @@ -429,10 +429,10 @@ public final class DarwinToolchain: Toolchain { // that SDK's plugin server). let sdkPathRoot = VirtualPath.lookup(sdkPath).appending(components: "usr") commandLine.appendFlag(.externalPluginPath) - commandLine.appendFlag("\(sdkPathRoot.pluginPath.name)#\(sdkPathRoot.pluginServerPath.name.spm_shellEscaped())") + commandLine.appendFlag("\(sdkPathRoot.pluginPath.name)#\(sdkPathRoot.pluginServerPath.name)") commandLine.appendFlag(.externalPluginPath) - commandLine.appendFlag("\(sdkPathRoot.localPluginPath.name)#\(sdkPathRoot.pluginServerPath.name.spm_shellEscaped())") + commandLine.appendFlag("\(sdkPathRoot.localPluginPath.name)#\(sdkPathRoot.pluginServerPath.name)") // Determine the platform path. For simulator platforms, look into the // corresponding device platform instance. @@ -452,10 +452,10 @@ public final class DarwinToolchain: Toolchain { // platform's plugin server). let platformPathRoot = platformPath.appending(components: "Developer", "usr") commandLine.appendFlag(.externalPluginPath) - commandLine.appendFlag("\(platformPathRoot.pluginPath.name)#\(platformPathRoot.pluginServerPath.name.spm_shellEscaped())") + commandLine.appendFlag("\(platformPathRoot.pluginPath.name)#\(platformPathRoot.pluginServerPath.name)") commandLine.appendFlag(.externalPluginPath) - commandLine.appendFlag("\(platformPathRoot.localPluginPath.name)#\(platformPathRoot.pluginServerPath.name.spm_shellEscaped())") + commandLine.appendFlag("\(platformPathRoot.localPluginPath.name)#\(platformPathRoot.pluginServerPath.name)") } } } diff --git a/Tests/SwiftDriverTests/SwiftDriverTests.swift b/Tests/SwiftDriverTests/SwiftDriverTests.swift index 026c5906f..75dad4da2 100644 --- a/Tests/SwiftDriverTests/SwiftDriverTests.swift +++ b/Tests/SwiftDriverTests/SwiftDriverTests.swift @@ -6876,7 +6876,7 @@ final class SwiftDriverTests: XCTestCase { func pluginPathTest(platform: String, searchPlatform: String) throws { let sdkRoot = testInputsPath.appending( components: ["PlatformChecks", "\(platform).platform", "Developer", "SDKs", "\(platform).sdk"]) - 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"]) + var driver = try Driver(args: ["swiftc", "-typecheck", "foo.swift", "-sdk", VirtualPath.absolute(sdkRoot).name, "-plugin-path", "PluginA", "-external-plugin-path", "Plugin~B#Bexe", "-load-plugin-library", "PluginB2", "-plugin-path", "PluginC"]) guard driver.isFrontendArgSupported(.pluginPath) && driver.isFrontendArgSupported(.externalPluginPath) else { return } @@ -6889,7 +6889,7 @@ final class SwiftDriverTests: XCTestCase { let pluginAIndex = job.commandLine.firstIndex(of: .path(VirtualPath.relative(.init("PluginA")))) XCTAssertNotNil(pluginAIndex) - let pluginBIndex = job.commandLine.firstIndex(of: .path(VirtualPath.relative(.init("PluginB#Bexe")))) + let pluginBIndex = job.commandLine.firstIndex(of: .path(VirtualPath.relative(.init("Plugin~B#Bexe")))) XCTAssertNotNil(pluginBIndex) XCTAssertLessThan(pluginAIndex!, pluginBIndex!) From b80daded64fcb2c7a4f8a9f46c5929dc8c13e01e Mon Sep 17 00:00:00 2001 From: Doug Gregor Date: Thu, 20 Jul 2023 15:49:40 -0700 Subject: [PATCH 3/3] [Platform macros] Make test inputs more realistic and complicated ... to make sure we're not missing any odd corner cases here. --- .../Developer/SDKs/iPhoneOS13.0.sdk}/SDKSettings.json | 0 .../SDKs/iPhoneSimulator15.0.sdk}/SDKSettings.json | 0 Tests/SwiftDriverTests/SwiftDriverTests.swift | 8 ++++---- 3 files changed, 4 insertions(+), 4 deletions(-) rename TestInputs/{PlatformChecks/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk => Platform Checks/iPhoneOS.platform/Developer/SDKs/iPhoneOS13.0.sdk}/SDKSettings.json (100%) rename TestInputs/{PlatformChecks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk => Platform Checks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator15.0.sdk}/SDKSettings.json (100%) diff --git a/TestInputs/PlatformChecks/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/SDKSettings.json b/TestInputs/Platform Checks/iPhoneOS.platform/Developer/SDKs/iPhoneOS13.0.sdk/SDKSettings.json similarity index 100% rename from TestInputs/PlatformChecks/iPhoneOS.platform/Developer/SDKs/iPhoneOS.sdk/SDKSettings.json rename to TestInputs/Platform Checks/iPhoneOS.platform/Developer/SDKs/iPhoneOS13.0.sdk/SDKSettings.json diff --git a/TestInputs/PlatformChecks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/SDKSettings.json b/TestInputs/Platform Checks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator15.0.sdk/SDKSettings.json similarity index 100% rename from TestInputs/PlatformChecks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator.sdk/SDKSettings.json rename to TestInputs/Platform Checks/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator15.0.sdk/SDKSettings.json diff --git a/Tests/SwiftDriverTests/SwiftDriverTests.swift b/Tests/SwiftDriverTests/SwiftDriverTests.swift index 75dad4da2..f8e8a070b 100644 --- a/Tests/SwiftDriverTests/SwiftDriverTests.swift +++ b/Tests/SwiftDriverTests/SwiftDriverTests.swift @@ -6869,13 +6869,13 @@ final class SwiftDriverTests: XCTestCase { } func testPluginPaths() throws { - try pluginPathTest(platform: "iPhoneOS", searchPlatform: "iPhoneOS") - try pluginPathTest(platform: "iPhoneSimulator", searchPlatform: "iPhoneOS") + try pluginPathTest(platform: "iPhoneOS", sdk: "iPhoneOS13.0", searchPlatform: "iPhoneOS") + try pluginPathTest(platform: "iPhoneSimulator", sdk: "iPhoneSimulator15.0", searchPlatform: "iPhoneOS") } - func pluginPathTest(platform: String, searchPlatform: String) throws { + func pluginPathTest(platform: String, sdk: String, searchPlatform: String) throws { let sdkRoot = testInputsPath.appending( - components: ["PlatformChecks", "\(platform).platform", "Developer", "SDKs", "\(platform).sdk"]) + components: ["Platform Checks", "\(platform).platform", "Developer", "SDKs", "\(sdk).sdk"]) var driver = try Driver(args: ["swiftc", "-typecheck", "foo.swift", "-sdk", VirtualPath.absolute(sdkRoot).name, "-plugin-path", "PluginA", "-external-plugin-path", "Plugin~B#Bexe", "-load-plugin-library", "PluginB2", "-plugin-path", "PluginC"]) guard driver.isFrontendArgSupported(.pluginPath) && driver.isFrontendArgSupported(.externalPluginPath) else { return