Android Project Mainline: How Modular System Updates Work
Google's most important defense against Android fragmentation isn't a new OS version — it's a delivery system that bypasses it entirely. Project Mainline turns monolithic system updates into 50+ independently updatable modules delivered through Play.
For a decade, Android's Achilles' heel was update velocity. A critical TLS vulnerability patched in AOSP could take 6-12 months to reach a Samsung or Xiaomi device because every fix had to be integrated by the SoC vendor, validated by the OEM, certified by carriers, and finally delivered as a multi-gigabyte OTA. Project Mainline, launched with Android 10 and expanded to 54 modules by Android 15, was Google's architectural answer: make core OS components updatable like apps, directly via Google Play.
It's easy to dismiss Mainline as "Google Play System Updates" — the user-facing name in Settings — but the engineering underneath is a fundamental re-partitioning of Android. It creates a new immutable, versioned, and rollback-safe layer between AOSP and the vendor stack. For engineers shipping devices or securing fleets, understanding APEX, staged installation, and module boundaries is now as essential as understanding Treble.
Why Monolithic Updates Failed
Before Mainline, Android was a single /system image. Media codecs, DNS resolver, permission controller, and even core crypto (Conscrypt) were all built together. Patching one meant rebuilding and retesting everything. Treble (Android 8.0) fixed the vendor boundary by separating /vendor and /system with a stable Vendor NDK and HAL interface, but it didn't solve framework fragmentation — OEMs still controlled when the framework itself shipped.
Mainline attacks the other side of the stack: it extracts security-sensitive, compatibility-critical, and API-sensitive components out of /system and into separately signed, separately versioned containers. Google can then push a fix for Stagefright-style media codec bugs or DNS-over-TLS behavior to 3.5 billion devices in days, not quarters, without OEM involvement. This is also a sustainability play — devices that no longer receive full OS upgrades can still receive Mainline patches for years, extending usable life as we explored in our analysis of recycled materials and long-term device support.
Mainline is not an OTA replacement. Annual Android version upgrades still exist for framework APIs and kernel changes. Mainline is a parallel, higher-cadence channel for components where Google needs central control: security, privacy, and consistency. Think of it as micro-OTAs governed by Play infrastructure rather than carrier infrastructure.
The Two Container Formats: APEX and APKM
Mainline modules come in two flavors, chosen based on whether the module contains native code and needs early boot availability.
| Feature | 5G NR | Wi-Fi 7 | Bluetooth 5.4 |
|---|---|---|---|
| Peak Throughput | 20 Gbps | 46 Gbps | 2 Mbps |
| Latency | 1–4 ms | 1–2 ms | 3–6 ms |
| Range | Several km | 30–50 m | 100–400 m |
| Power Draw | High | Medium | Ultra-low |
| Primary Use | Cellular data | Local networking | Peripherals/IoT |
1. APEX (Android Pony EXpress)
APEX is an ext4 filesystem image wrapped in a signed container, mounted at boot via loopback and dm-verity. It behaves like a mini-system partition. APEX is required for native libraries, runtime (ART), and anything needed before the package manager starts. Examples: com.android.conscrypt, com.android.media, com.android.art.
Each APEX declares a manifest with version, dependencies, and apexKeys:
{
"name": "com.android.conscrypt",
"version": 340818000,
"versionName": "2024-12-01",
"preInstallHook": "bin/installConscrypt.sh",
"postInstallHook": "bin/postInstall.sh",
"apexKeys": "conscrypt.apex.pubkey",
"provideNativeLibs": ["libconscrypt_jni.so"],
"requireNativeLibs": ["libcrypto.so"]
}
At build time, apexer creates a signed .apex file. On device, apexd verifies the vbmeta signature, checks compatibility with com.android.vndk.current, stages it to /data/apex/active, and activates it on next boot. Two slots are kept for A/B rollback — if boot fails, the device automatically reverts.
2. APKM / APK-in-APEX
For Java/Kotlin-only components that can be updated live, Google uses APKM (or APK inside an APEX shim). These are standard APKs installed to /apex but managed by PackageManager. This allows no-reboot updates and instant rollback via Play. Examples: com.android.permission (Permission Controller), com.android.documentsui, com.android.cellbroadcast.
Developers can inspect active modules:
# List all APEX packages and versions
adb shell apex list --all
# Check staged session (before reboot)
adb shell pm get-staged-apex
# Force a Mainline update check (gmscore)
adb shell am broadcast -a com.google.android.gms.UPDATE_MAINLINE \
--es extra_force_update true
# Verify Conscrypt provider version
adb shell dumpsys package com.android.conscrypt | grep versionName
This dual-format approach is crucial for thermal and performance stability — native codecs in APEX can be hot-fixed without recompiling the entire media framework, avoiding risky thermal profile regressions.
Architecture: Where Mainline Lives in the Stack
What Can Mainline Actually Update? The 2026 Module List
As of Android 15, Google lists 37 mandatory Mainline modules and ~17 optional/updatable modules for OEMs that ship Google Mobile Services. The table below shows representative categories and why they matter for fleet security and app consistency.
| Module (package) | Format | What It Ships | Impact |
|---|---|---|---|
| Media com.android.media | APEX | MediaCodec, extractors, Stagefright | Fixes critical codec CVEs without full OTA |
| Conscrypt com.android.conscrypt | APEX | TLS stack, BoringSSL bridge | Unified TLS 1.3 behavior across OEMs |
| ART com.android.art | APEX | Android Runtime, libcore | GC and JIT improvements without OS upgrade |
| Networking com.android.tethering | APKM | DNS resolver, captive portal, tethering | DNS-over-TLS/HTTPS patches; latency fixes relevant to cloud gaming latency |
| Permissions com.android.permission | APKM | Permission Controller, Safety Center | New privacy UIs backported silently |
| Wi-Fi / Bluetooth com.android.wifi, bt | APEX | Host stack, config | Rapid WPA3 and BLE fixes |
| Stat & AD Services com.android.adservices | APK | Privacy Sandbox, StatsD | Privacy features updated like an app |
From an app developer perspective, the Networking and Conscrypt modules are the most consequential — they eliminate the long tail of devices where Security.getProvider("Conscrypt") behaved differently. For users, the Permission module means Android's privacy dashboard can evolve even if the OEM has abandoned the OS version.
Update Flow: Staged, Verified, Rollback-Safe
Unlike a traditional OTA that writes to /system, Mainline uses a staged install with strong rollback guarantees borrowed from A/B updates and Apex's two-slot model.
1. Train delivery: Google bundles compatible module versions into a "train" (e.g., 2026-08-01). The train is published to Play and gated by ro.apex.updatable and build fingerprint checks. Devices download APEX payloads via GMS's com.google.android.apex package.
2. Staging: apexd stages the new APEX to /data/apex/active and creates a staged session via pm install --apex. The system validates certificates, version codes (must be > current), and VNDK compatibility.
3. Activation: For APEX, the new image is mounted on next boot via dm-verity. For APK, activation is live. rollback manager keeps the previous APEX for one boot; if apexd detects a boot failure or crash loop, it automatically flips back.
4. Telemetry: Google's Mainline infrastructure monitors failure rates per module train. If a module causes ANRs, it is halted server-side within hours — a level of granularity impossible with full OTAs.
This flow has a subtle UX implication: Mainline is less disruptive for display calibration than full OTAs. Because it rarely touches SurfaceFlinger or display drivers, issues like PWM dimming behavior remain tied to vendor display firmware, not Mainline trains — a useful isolation for debugging.
Security Model
Each APEX is signed with Google's release key and verified with AVB (Android Verified Boot). The public key is baked into /system/etc/security/otacerts.zip and apexd enforces that an attacker cannot downgrade a module — versionCode must increase monotonically. Additionally, Mainline modules run under the same SELinux domains as their pre-Mainline equivalents; extracting them to APEX did not widen privilege. In fact, it narrowed attack surface: media extractors now run in a tighter sandbox mount namespace.
Comparison: Treble vs. Mainline vs. Full OTA
Treble decouples the vendor HAL so full OS upgrades are easier for OEMs. Mainline decouples framework components so Google can patch without OEMs. Full OTA still remains for kernel, SystemUI, and API level bumps. The most resilient fleets rely on all three.
Treble (2017-present): One-time architectural split. Reduces OEM work for Android version upgrades from ~9 months to ~3 months, but still OEM-dependent.
Mainline (2019-present): Continuous delivery of ~50 modules via Play. OEM-independent, A/B rollback, often weekly cadence for security trains. Requires Google Mobile Services.
Full OTA (legacy): Complete /system + /vendor + boot.img replacement. Carrier-certified, large download (2-4 GB), full reboot, full CTS cycle. Necessary for API level and kernel updates.
Limitations and Real-World Challenges
Mainline is not a panacea. First, it only applies to GMS-certified devices. AOSP forks, Amazon Fire, and Chinese-market phones without Play cannot receive Mainline trains — they remain fully dependent on vendor OTAs.
Second, modules are tightly version-gated. An OEM that aggressively forks Conscrypt or modifies media codecs outside the Mainline boundary will fail Mainline CTS and cannot ship GMS. This constraint is intentional for consistency, but it limits OEM differentiation.
Third, APEX size bloat is real. Each APEX is a loop-mounted ext4 image with its own inode table. On low-end devices with 32 GB storage, 20+ APEXes consume measurable overhead. Google has mitigated this by compressing APEX with DICE signatures and sharing APEX libraries via com.android.vndk, but storage-constrained designs still need careful budgeting.
Finally, observability is still weak for end users. Settings > About > Android version > Google Play system update shows only a date (e.g., "August 1, 2026"), not per-module versions. For fleet managers, adb shell dumpsys package or Play Console's device catalog is the only reliable audit trail.
Conclusion: The Quiet Revolution
Project Mainline rarely makes headlines because it's designed to be invisible. Yet its effect is profound: critical CVEs that once lingered for a year now close in weeks; TLS behavior converges across the ecosystem; and privacy features reach users without waiting for Android 17. For hardware engineers and fleet operators, the takeaway is clear — treat Google Play System Update version as a first-class compliance signal, alongside patch level and kernel version. In the era of modular Android, the OS is no longer a monolith you ship; it's a set of continuously delivered components you must version, verify, and monitor.