Skip to content

Commit 8e71bde

Browse files
committed
Add support for building Swift on Android targets
Swift Build currently has support for building C/C++ code on Android; this extends it to Swift. Concretely, this fixes the position of the version number in the triple passed to swiftc for Android targets, and adds the relevant search paths to find Swift standard libraries and other content in the Swift SDK. The sysroot still comes from an Android NDK found on the system; the sysroot in the Swift SDK is ignored based on the intended direction around supporting Android targets in Swift.
1 parent 64d201f commit 8e71bde

File tree

2 files changed

+36
-5
lines changed

2 files changed

+36
-5
lines changed

Sources/SWBAndroidPlatform/AndroidSDK.swift

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -57,10 +57,10 @@ struct AndroidSDK: Sendable {
5757
}
5858

5959
struct LLVMTriple: Codable {
60-
let arch: String
61-
let vendor: String
62-
let system: String
63-
let environment: String
60+
var arch: String
61+
var vendor: String
62+
var system: String
63+
var environment: String
6464

6565
var description: String {
6666
"\(arch)-\(vendor)-\(system)-\(environment)"

Sources/SWBAndroidPlatform/Plugin.swift

Lines changed: 32 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -116,6 +116,37 @@ struct AndroidSDKRegistryExtension: SDKRegistryExtension {
116116
return []
117117
}
118118

119+
let allPossibleTriples = abis.values.flatMap { abi in
120+
(max(deploymentTargetRange.min, abi.min_os_version)...deploymentTargetRange.max).map { deploymentTarget in
121+
var triple = abi.llvm_triple
122+
triple.vendor = "unknown" // Android NDK uses "none", Swift SDKs use "unknown"
123+
triple.environment += "\(deploymentTarget)"
124+
return triple
125+
}
126+
}.map(\.description)
127+
128+
let androidSwiftSDKs = (try? SwiftSDK.findSDKs(
129+
targetTriples: allPossibleTriples,
130+
fs: context.fs,
131+
hostOperatingSystem: context.hostOperatingSystem
132+
)) ?? []
133+
134+
let swiftSettings: [String: PropertyListItem]
135+
// FIXME: We need a way to narrow down the list, possibly by passing down a Swift SDK identifier from SwiftPM
136+
// The resource path should be the same for all triples in an Android Swift SDK
137+
if let androidSwiftSDK = androidSwiftSDKs.only, let swiftResourceDir = Set(androidSwiftSDK.targetTriples.values.map { tripleProperties in androidSwiftSDK.path.join(tripleProperties.swiftResourcesPath) }).only {
138+
swiftSettings = [
139+
"SWIFT_LIBRARY_PATH": .plString(swiftResourceDir.join("android").str),
140+
"SWIFT_RESOURCE_DIR": .plString(swiftResourceDir.str),
141+
"SWIFT_TARGET_TRIPLE": .plString("$(CURRENT_ARCH)-unknown-$(SWIFT_PLATFORM_TARGET_PREFIX)$(LLVM_TARGET_TRIPLE_SUFFIX)"),
142+
"LIBRARY_SEARCH_PATHS": "$(inherited) $(SWIFT_RESOURCE_DIR)/../$(__ANDROID_TRIPLE_$(CURRENT_ARCH))",
143+
].merging(abis.map {
144+
("__ANDROID_TRIPLE_\($0.value.llvm_triple.arch)", .plString($0.value.triple))
145+
}, uniquingKeysWith: { _, new in new })
146+
} else {
147+
swiftSettings = [:]
148+
}
149+
119150
return [(androidSdk.sysroot ?? .root, androidPlatform, [
120151
"Type": .plString("SDK"),
121152
"Version": .plString("0.0.0"),
@@ -129,7 +160,7 @@ struct AndroidSDKRegistryExtension: SDKRegistryExtension {
129160
// FIXME: Make this configurable in a better way so we don't need to push build settings at the SDK definition level
130161
"LLVM_TARGET_TRIPLE_OS_VERSION": .plString("linux"),
131162
"LLVM_TARGET_TRIPLE_SUFFIX": .plString("-android$(ANDROID_DEPLOYMENT_TARGET)"),
132-
]),
163+
].merging(swiftSettings, uniquingKeysWith: { _, new in new })),
133164
"SupportedTargets": .plDict([
134165
"android": .plDict([
135166
"Archs": .plArray(abis.map { .plString($0.value.llvm_triple.arch) }),

0 commit comments

Comments
 (0)