Architecture
A deep dive into how xcross reimplements the iOS build, signing and CoreDevice launch pipeline for Flutter and Compose Multiplatform in pure Dart.
A thin CLI over focused Dart packages. Two front ends (Flutter, Compose) share one back end (SDK, signing, device).
Flutter front endengine cache ·
frontend_server · SwiftPM pluginsCompose front endGradle klib ·
konanc framework · ObjC/Swift runnerNative back endDarwin SDK ·
clang · ld64.lld · .app assemblySigningGrandSlam + ADI · provisioning · in-process codesign
DeviceRSD tunnel · CoreDevice launch · gdb-remote attach
Pipelines
xcross flutter run
├─ FlutterPacker
│ ├─ IosEngineCache engine artifacts pinned to the SDK's engine hash
│ ├─ FlutterDebugBundler frontend_server → app.dill → App.framework (JIT)
│ ├─ SwiftPM plugins swift build → libFlutterPluginsGenerated.dylib
│ ├─ RunnerShim clang / ld64.lld → Runner Mach-O
│ └─ assemble Flutter.framework + Info.plist + assets → .app
├─ in-process codesign → install
└─ CoreDeviceLauncher RSD tunnel → launch suspended → gdb-remote attach
└─ HotReloadController DevFS + VM Service ⇄ frontend_server
xcross compose run
├─ ComposePacker
│ ├─ Resolving toolchain JDK 21+ · Kotlin/Native prebuilt
│ ├─ Compiling Kotlin sources Gradle → klib
│ ├─ Building <App>.framework konanc (fingerprinted, skipped if unchanged)
│ ├─ Compiling Runner ObjC or SwiftUI host → Mach-O
│ └─ Assembling <App>.app
├─ in-process codesign → install
└─ CoreDeviceLauncher RSD tunnel → launch → native attach
└─ ComposeWatchSession r → rebuild if changed → reinstall → relaunch
Flutter: engine and kernel
- Engine: downloads exactly what
flutterwould cache for your SDK’s engine hash. The engine is never modified. On Linux and Windows, SDK iOS artifacts are reused only when theFlutterEnginerevision matches, so a staleprecachecan’t ship an “Invalid SDK hash” black screen. - Kernel:
frontend_servercompiles your Dart toapp.dill. Debug mode is JIT, so nogen_snapshot, so no macOS. - Plugins: SwiftPM plugins build into one dylib with a generated registrant. CocoaPods-only plugins are skipped.
- Dependencies: since 2.0, SwiftPM resolves the whole plugin graph natively. URL dependencies are no longer cloned or rewritten to path dependencies. An xcross manifest compiler applies host fixes to every manifest SwiftPM evaluates, without touching
Package.swift. - Macros: SwiftUI,
#Preview(including UIKit and widget previews) and FoundationModels macros expand through the Open Apple Macros server. Release bundles ship it prebuilt, so the first build doesn’t compile swift-syntax.tools.OpenAppleMacrosServerpoints at another server. - Assets: shaders compile with the host
impellerc, likeflutter build. Icon fonts are tree shaken in profile and release builds (--[no-]tree-shake-icons). Package licenses survive iOS builds.
Compose: Kotlin/Native
- Toolchain:
xcross compose setupfetches the Kotlin/Native prebuilt matching your project and patches its host config for the Darwin SDK. - Framework:
konanclinks the iOS framework. Inputs and flags are fingerprinted, so unchanged builds skip it (~145 s → ~12 s). - Runner: a generated ObjC host for
ComposeUIViewController, or your SwiftUI@main.
Shared back end
Darwin SDK
darwin_sdk_kit unpacks Xcode.xip with pure-Dart xar/pbzx/cpio readers.Native link
clang + ld64.lld against the SDK. No xcodebuild.Signing
apple_developer_kit: GrandSlam login, provisioning, Mach-O signing in Dart, offline from cached profiles.Launch
dart_mobile_device: RSD tunnel, CoreDevice launch, gdb-remote.Flutter hot reload
Savefile watcher
Incremental compile
frontend_serverUploadDevFS over VM Service
Reload
reloadSources + reassembleR resets the compiler, uploads a full dill and restarts each FlutterView. The frontend_server also serves expression evaluation for the debugger.
IDE debugging
xcross_dap is a DAP server over the same VM Service. VS Code reaches it through a shim that only intercepts "xcross": true configs, JetBrains through an LSP4IJ run configuration.
Packages
| Package | Role |
|---|---|
cli_kit | Logging, spinners, process running |
darwin_sdk_kit | Xcode archive extraction, SDK bundles |
apple_developer_kit | Apple login, provisioning, codesign |
dart_mobile_device | Tunnels, install, launch, port forwarding |
frontend_server_kit | Incremental kernel compile, hot reload |
open_apple_macros | Apple macro plugin server (SwiftUI, Previews, FoundationModels) |
xcross | CLI, Flutter packer, Compose packer, DAP |