From 4020039065afdce265b5140e1d4989da87b42280 Mon Sep 17 00:00:00 2001 From: Marc Prud'hommeaux Date: Sat, 17 May 2025 16:39:38 -0400 Subject: [PATCH 1/2] Make SwiftSDKMetadataV4.sdkRootPath optional --- Sources/PackageModel/SwiftSDKs/SwiftSDK.swift | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/Sources/PackageModel/SwiftSDKs/SwiftSDK.swift b/Sources/PackageModel/SwiftSDKs/SwiftSDK.swift index cdcdfd781f4..767460ed862 100644 --- a/Sources/PackageModel/SwiftSDKs/SwiftSDK.swift +++ b/Sources/PackageModel/SwiftSDKs/SwiftSDK.swift @@ -350,7 +350,9 @@ public struct SwiftSDK: Equatable { fileprivate init(_ properties: SwiftSDKMetadataV4.TripleProperties, swiftSDKDirectory: Basics.AbsolutePath? = nil) throws { if let swiftSDKDirectory { self.init( - sdkRootPath: try AbsolutePath(validating: properties.sdkRootPath, relativeTo: swiftSDKDirectory), + sdkRootPath: try properties.sdkRootPath.map { + try AbsolutePath(validating: $0, relativeTo: swiftSDKDirectory) + }, swiftResourcesPath: try properties.swiftResourcesPath.map { try AbsolutePath(validating: $0, relativeTo: swiftSDKDirectory) }, @@ -369,7 +371,9 @@ public struct SwiftSDK: Equatable { ) } else { self.init( - sdkRootPath: try AbsolutePath(validating: properties.sdkRootPath), + sdkRootPath: try properties.sdkRootPath.map { + try AbsolutePath(validating: $0) + }, swiftResourcesPath: try properties.swiftResourcesPath.map { try AbsolutePath(validating: $0) }, @@ -1167,7 +1171,7 @@ struct SerializedDestinationV3: Decodable { struct SwiftSDKMetadataV4: Decodable { struct TripleProperties: Codable { /// Path relative to `swift-sdk.json` containing SDK root. - var sdkRootPath: String + var sdkRootPath: String? /// Path relative to `swift-sdk.json` containing Swift resources for dynamic linking. var swiftResourcesPath: String? From afdaa3f1b76fb3f3f1c6b2bd6a1342147e6f39d4 Mon Sep 17 00:00:00 2001 From: Marc Prud'hommeaux Date: Sun, 18 May 2025 16:07:14 -0400 Subject: [PATCH 2/2] Add test case for androidWithoutSDKRootPathSwiftSDKv4 --- Tests/PackageModelTests/SwiftSDKTests.swift | 42 +++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/Tests/PackageModelTests/SwiftSDKTests.swift b/Tests/PackageModelTests/SwiftSDKTests.swift index 7f7a5dd9650..d3c6b2f0643 100644 --- a/Tests/PackageModelTests/SwiftSDKTests.swift +++ b/Tests/PackageModelTests/SwiftSDKTests.swift @@ -25,6 +25,7 @@ private let hostTriple = try! Triple("arm64-apple-darwin22.1.0") private let olderHostTriple = try! Triple("arm64-apple-darwin20.1.0") private let linuxGNUTargetTriple = try! Triple("x86_64-unknown-linux-gnu") private let linuxMuslTargetTriple = try! Triple("x86_64-unknown-linux-musl") +private let androidTargetTriple = try! Triple("aarch64-unknown-linux-android28") private let wasiTargetTriple = try! Triple("wasm32-unknown-wasi") private let extraFlags = BuildFlags( cCompilerFlags: ["-fintegrated-as"], @@ -186,6 +187,20 @@ private let toolsetRootSwiftSDKv4 = ( """# as SerializedJSON ) +private let androidWithoutSDKRootPathSwiftSDKv4 = ( + path: bundleRootPath.appending(component: "androidWithoutSDKRootPathSwiftSDKv4.json"), + json: #""" + { + "targetTriples": { + "\#(androidTargetTriple.tripleString)": { + "toolsetPaths": ["/tools/otherToolsNoRoot.json"] + } + }, + "schemaVersion": "4.0" + } + """# as SerializedJSON +) + private let missingToolsetSwiftSDKv4 = ( path: bundleRootPath.appending(component: "missingToolsetSwiftSDKv4.json"), json: #""" @@ -351,6 +366,23 @@ private let parsedToolsetRootDestination = SwiftSDK( ) ) +private let parsedToolsetNoSDKRootPathDestination = SwiftSDK( + targetTriple: androidTargetTriple, + toolset: .init( + knownTools: [ + .librarian: .init(path: try! AbsolutePath(validating: "\(usrBinTools[.librarian]!)")), + .linker: .init(path: try! AbsolutePath(validating: "\(usrBinTools[.linker]!)")), + .debugger: .init(path: try! AbsolutePath(validating: "\(usrBinTools[.debugger]!)")), + ], + rootPaths: [] + ), + pathsConfiguration: .init( + sdkRootPath: nil, + toolsetPaths: ["/tools/otherToolsNoRoot.json"] + .map { try! AbsolutePath(validating: $0) } + ) +) + private let testFiles: [(path: AbsolutePath, json: SerializedJSON)] = [ destinationV1, destinationV2, @@ -365,6 +397,7 @@ private let testFiles: [(path: AbsolutePath, json: SerializedJSON)] = [ invalidVersionSwiftSDKv4, invalidToolsetSwiftSDKv4, wasiWithoutToolsetsSwiftSDKv4, + androidWithoutSDKRootPathSwiftSDKv4, otherToolsNoRoot, someToolsWithRoot, invalidToolset, @@ -488,6 +521,15 @@ final class SwiftSDKTests: XCTestCase { XCTAssertEqual(toolsetRootSwiftSDKv4Decoded, [parsedToolsetRootDestination]) + let androidWithoutSDKRootPathSwiftSDKv4Decoded = try SwiftSDK.decode( + fromFile: androidWithoutSDKRootPathSwiftSDKv4.path, + hostToolchainBinDir: toolchainBinAbsolutePath, + fileSystem: fs, + observabilityScope: observability + ) + + XCTAssertEqual(androidWithoutSDKRootPathSwiftSDKv4Decoded, [parsedToolsetNoSDKRootPathDestination]) + XCTAssertThrowsError(try SwiftSDK.decode( fromFile: missingToolsetSwiftSDKv4.path, hostToolchainBinDir: toolchainBinAbsolutePath,