Skip to content

Commit 8716d0f

Browse files
committed
Create one Android SDK per Swift SDK
This matches what WebAssembly is doing, and avoids an issue where multiple installed Android Swift SDKs would cause the build to fail.
1 parent e3d484f commit 8716d0f

File tree

3 files changed

+44
-26
lines changed

3 files changed

+44
-26
lines changed

Sources/SWBAndroidPlatform/Plugin.swift

Lines changed: 42 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -149,26 +149,44 @@ struct AndroidPlatformExtension: PlatformInfoExtension {
149149
hostOperatingSystem: context.hostOperatingSystem
150150
)) ?? []
151151

152-
let swiftSettings: [String: PropertyListItem]
153-
// FIXME: We need a way to narrow down the list, possibly by passing down a Swift SDK identifier from SwiftPM
154-
// The resource path should be the same for all triples in an Android Swift SDK
155-
if let androidSwiftSDK = androidSwiftSDKs.only, let swiftResourceDir = Set(androidSwiftSDK.targetTriples.values.map { tripleProperties in androidSwiftSDK.path.join(tripleProperties.swiftResourcesPath) }).only {
156-
swiftSettings = [
157-
"SWIFT_LIBRARY_PATH": .plString(swiftResourceDir.join("android").str),
158-
"SWIFT_RESOURCE_DIR": .plString(swiftResourceDir.str),
159-
"SWIFT_TARGET_TRIPLE": .plString("$(CURRENT_ARCH)-unknown-$(SWIFT_PLATFORM_TARGET_PREFIX)$(LLVM_TARGET_TRIPLE_SUFFIX)"),
160-
"LIBRARY_SEARCH_PATHS": "$(inherited) $(SWIFT_RESOURCE_DIR)/../$(__ANDROID_TRIPLE_$(CURRENT_ARCH))",
161-
].merging(abis.map {
162-
("__ANDROID_TRIPLE_\($0.value.llvm_triple.arch)", .plString($0.value.triple))
163-
}, uniquingKeysWith: { _, new in new })
164-
} else {
165-
swiftSettings = [:]
166-
}
152+
return try androidSwiftSDKs.map { androidSwiftSDK in
153+
let perArchSwiftResourceDirs = try Dictionary(grouping: androidSwiftSDK.targetTriples, by: { try LLVMTriple($0.key).arch }).mapValues {
154+
let paths = Set($0.compactMap { $0.value.swiftResourcesPath })
155+
guard let path = paths.only else {
156+
throw StubError.error("The resource path should be the same for all triples of the same architecture in an Android Swift SDK")
157+
}
158+
return Path(path)
159+
}
160+
161+
return sdk(
162+
canonicalName: androidSwiftSDK.identifier,
163+
androidPlatform: androidPlatform,
164+
androidNdk: androidNdk,
165+
defaultProperties: defaultProperties,
166+
customProperties: [
167+
"SWIFT_TARGET_TRIPLE": .plString("$(CURRENT_ARCH)-unknown-$(SWIFT_PLATFORM_TARGET_PREFIX)$(LLVM_TARGET_TRIPLE_SUFFIX)"),
168+
"LIBRARY_SEARCH_PATHS": "$(inherited) $(SWIFT_RESOURCE_DIR)/../$(__ANDROID_TRIPLE_$(CURRENT_ARCH))",
169+
].merging(perArchSwiftResourceDirs.map {
170+
[
171+
("SWIFT_LIBRARY_PATH[arch=\($0.key)]", .plString($0.value.join("android").str)),
172+
("SWIFT_RESOURCE_DIR[arch=\($0.key)]", .plString($0.value.str)),
173+
]
174+
}.flatMap { $0 }, uniquingKeysWith: { _, new in new }).merging(abis.map {
175+
("__ANDROID_TRIPLE_\($0.value.llvm_triple.arch)", .plString($0.value.triple))
176+
}, uniquingKeysWith: { _, new in new }))
177+
} + [
178+
// Fallback SDK for when there are no Swift SDKs (Android SDK is still usable for C/C++-only code)
179+
sdk(androidPlatform: androidPlatform, androidNdk: androidNdk, defaultProperties: defaultProperties)
180+
]
181+
}
167182

168-
return [(androidNdk.sysroot.path, androidPlatform, [
183+
private func sdk(canonicalName: String? = nil, androidPlatform: Platform, androidNdk: AndroidSDK.NDK, defaultProperties: [String: PropertyListItem], customProperties: [String: PropertyListItem] = [:]) -> (path: Path, platform: SWBCore.Platform?, data: [String: PropertyListItem]) {
184+
return (androidNdk.sysroot.path, androidPlatform, [
169185
"Type": .plString("SDK"),
170-
"Version": .plString("0.0.0"),
171-
"CanonicalName": .plString("android"),
186+
"Version": .plString(androidNdk.version.description),
187+
"CanonicalName": .plString(canonicalName ?? "android\(androidNdk.version.description)"),
188+
// "android.ndk" is an alias for the "Android SDK without a Swift SDK" scenario in order for tests to deterministically pick a single Android destination regardless of how many Android Swift SDKs may be installed.
189+
"Aliases": .plArray([.plString("android")] + (canonicalName == nil ? [.plString("android.ndk")] : [])),
172190
"IsBaseSDK": .plBool(true),
173191
"DefaultProperties": .plDict([
174192
"PLATFORM_NAME": .plString("android"),
@@ -178,14 +196,14 @@ struct AndroidPlatformExtension: PlatformInfoExtension {
178196
// FIXME: Make this configurable in a better way so we don't need to push build settings at the SDK definition level
179197
"LLVM_TARGET_TRIPLE_OS_VERSION": .plString("$(SWIFT_PLATFORM_TARGET_PREFIX)"),
180198
"LLVM_TARGET_TRIPLE_SUFFIX": .plString("-android$($(DEPLOYMENT_TARGET_SETTING_NAME))"),
181-
].merging(swiftSettings, uniquingKeysWith: { _, new in new })),
199+
].merging(customProperties, uniquingKeysWith: { _, new in new })),
182200
"SupportedTargets": .plDict([
183201
"android": .plDict([
184-
"Archs": .plArray(abis.map { .plString($0.value.llvm_triple.arch) }),
202+
"Archs": .plArray(androidNdk.abis.map { .plString($0.value.llvm_triple.arch) }),
185203
"DeploymentTargetSettingName": .plString("ANDROID_DEPLOYMENT_TARGET"),
186-
"DefaultDeploymentTarget": .plString("\(deploymentTargetRange.min)"),
187-
"MinimumDeploymentTarget": .plString("\(deploymentTargetRange.min)"),
188-
"MaximumDeploymentTarget": .plString("\(deploymentTargetRange.max)"),
204+
"DefaultDeploymentTarget": .plString("\(androidNdk.deploymentTargetRange.min)"),
205+
"MinimumDeploymentTarget": .plString("\(androidNdk.deploymentTargetRange.min)"),
206+
"MaximumDeploymentTarget": .plString("\(androidNdk.deploymentTargetRange.max)"),
189207
"LLVMTargetTripleEnvironment": .plString("android"), // FIXME: androideabi for armv7!
190208
"LLVMTargetTripleSys": .plString("linux"),
191209
"LLVMTargetTripleVendor": .plString("none"),
@@ -194,7 +212,7 @@ struct AndroidPlatformExtension: PlatformInfoExtension {
194212
"Toolchains": .plArray([
195213
.plString("android")
196214
])
197-
])]
215+
])
198216
}
199217
}
200218

Sources/SWBTestSupport/RunDestinationTestSupport.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -281,7 +281,7 @@ extension _RunDestinationInfo {
281281

282282
/// A run destination targeting Android generic device, using the public SDK.
283283
package static var android: Self {
284-
return .init(platform: "android", sdk: "android", sdkVariant: "android", targetArchitecture: "undefined_arch", supportedArchitectures: ["armv7", "aarch64", "riscv64", "i686", "x86_64"], disableOnlyActiveArch: true)
284+
return .init(platform: "android", sdk: "android.ndk", sdkVariant: "android", targetArchitecture: "undefined_arch", supportedArchitectures: ["armv7", "aarch64", "riscv64", "i686", "x86_64"], disableOnlyActiveArch: true)
285285
}
286286

287287
/// A run destination targeting QNX generic device, using the public SDK.

Tests/SWBAndroidPlatformTests/SWBAndroidPlatformTests.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ fileprivate struct AndroidBuildOperationTests: CoreBasedTests {
3939
"CODE_SIGNING_ALLOWED": "NO",
4040
"DEFINES_MODULE": "YES",
4141
"PRODUCT_NAME": "$(TARGET_NAME)",
42-
"SDKROOT": "android",
42+
"SDKROOT": "android.ndk",
4343
"SUPPORTED_PLATFORMS": "android",
4444
"ANDROID_DEPLOYMENT_TARGET": "22.0",
4545
"ANDROID_DEPLOYMENT_TARGET[arch=riscv64]": "35.0",

0 commit comments

Comments
 (0)