In grafting, the scion is the branch joined onto a rootstock: here, Apple's stack grafted onto Android.
Run an emulated iPhone 11 on a Google Pixel 10, using a Tensor-tuned Android port of the Inferno QEMU fork.
Aim: experimentation, debugging and performance research. See docs/ETHICS.md for what this project deliberately doesn't do, and docs/HANDOFF.md for the current technical state.
Status (2026-10-22): two backends.
- QEMU (Pyre): iOS 14 on an emulated iPhone 11 boots to the home screen. It's slow: every Apple CPU instruction goes through QEMU's TCG JIT.
- AVF (hardware virtualization): Apple's open-source XNU (via HackiOS) runs as a pKVM guest on the Pixel's own CPU cores, with the iOS 16.5 userland. It reaches the home screen in about 80 s. Touch is still being fixed.
iOS 16.5 booting and at the home screen in a pKVM virtual machine on a Pixel 10. The text at the bottom is the test app's debug log.
This project ships no Apple software: no IPSWs, keys, firmware, ROMs or pre-made disk images in the
repository or its releases. For the QEMU backend you prepare those yourself on a Mac by following the upstream
Inferno guide. For the AVF backend, the owner's ios-bundle workflow builds an encrypted, private bundle of the
app and iOS 16.5 (see docs/ETHICS.md, point 6). This repo then gets the result running on the
phone.
Mac (one-time setup) Pixel 10
───────────────────── ─────────────────────────────────────
Inferno guide: restore + FS patches adb app ── foreground service
tools/ipsw_probe.py (pick an IPSW) ───▶ └─ libqemu-system-aarch64.so (t8030)
tools/package_vm.py (pack for phone) ├─ VNC on a unix socket ─▶ ScreenView (touch → MT-SPI)
└─ HMP monitor socket ◀─ button bar (F2–F6)
third_party/infernois Scion-Project/pyre'spixelbranch: upstream Inferno plus the Android/Tensor patches (see below).native/build-android.shcross-compiles QEMU and its static deps (glib, pixman, nettle+GMP, libtasn1, lzfse) with the NDK, and drops the binary intoapp/src/main/jniLibs.app/is a dependency-free Kotlin app. It launches QEMU, shows the screen, and maps touches and the hardware buttons.
Only the iPhone 11 (iPhone12,1, board n104ap) gets as far as the UI in Inferno.
| iOS | Verdict | Why |
|---|---|---|
| 14.x | ✅ supported | Documented to boot to SpringBoard. The guide uses 14.0 beta 5 (18A5351d). |
| 13, 15–18, 26 | 🧪 experimental | The t8030 machine recognises the kernel, but reaching the UI isn't documented. |
| anything else (e.g. 27) | ❌ unsupported | Unknown kernel version; QEMU cannot boot it. |
There's one more hard requirement: preparing a build needs the SEP firmware decryption key for that exact build. This project doesn't provide, find or fetch keys, firmware or ROMs.
tools/ipsw_probe.py checks a specific IPSW. It reads the zip index and
BuildManifest.plist (from a local file, or from a URL via HTTP range
requests, about 600 KiB), then reports a verdict and every file the guide's
steps need:
$ tools/ipsw_probe.py --list # iPhone12,1 versions with verdicts (metadata only)
$ tools/ipsw_probe.py ~/Downloads/iPhone11,8,iPhone12,1_14.8_18H17_Restore.ipsw
✅ SUPPORTED: iOS 14.8 (18H17) [iPhone12,1, iPhone11,8]
files for the Inferno setup steps:
✓ kernel_research kernelcache.research.iphone12b
✓ device_tree Firmware/all_flash/DeviceTree.n104ap.im4p
✓ sep_firmware Firmware/all_flash/sep-firmware.n104.RELEASE.im4p
✓ restore_ramdisk_erase 018-61661-017.dmg
✓ restore_trustcache Firmware/018-61661-017.dmg.trustcache
…The app also checks the prepared files before booting. It verifies the
IMG4/IM4P/IM4M headers and payload types, for example that the SEP firmware
was decrypted and re-packed as rsep, plus the sep_nvram size and that
every disk is present.
docs/PHONE-QUICKSTART.md is the end-to-end guide (Mac → Pixel): checking the IPSW, preparing the VM, packaging, installing the app, importing, starting, the display and buttons, the debug bundle, and current limits. In short:
- Prepare the VM on a Mac. Follow the upstream Inferno manual all the way through: restore, filesystem patches, and the first boot with data migration. Doing this by hand is upstream's explicit request, so this repo doesn't automate it.
- Package it:
tools/package_vm.py ~/InfernoDatawritesphone-vm(root disk → qcow2, plusvm.properties). Add--pushtoadb pushit too, or copy the folder to the phone and use Import VM folder… in the app. - Build and install the app:
git submodule update --init native/build-android.sh # first run builds deps too (~10 min) ./gradlew installDebug - Open Scion, check that everything is ✓, keep vCPUs at 4 (#33), then tap Start. If it fails, tap Share debug bundle and send the zip.
These are taken from the Pixel 10 kernel source (azagramac/pixel10-kernel-aosp, SoC "lga"):
| cpu | core | max clock |
|---|---|---|
| 0–1 | Cortex-A520 | 2.25 GHz |
| 2–6 | Cortex-A725 | 3.05 GHz |
| 7 | Cortex-X4 | 3.78 GHz |
GPU: Imagination (Rogue-family DDK, BVNC 71.2.2448.1212), 396–1094 MHz.
- vCPU pinning: the iPhone 11 has 6 application cores and 1 SEP core
(
-smp 7). Thepixelbranch addsQEMU_VCPU_AFFINITY. By default ("auto") the app derives it from the vCPU count: the application vCPUs go on the 6 big cores and the last (SEP) vCPU on the little ones, e.g.2-7;2-7;2-7;0-1for-smp 4. You can override it in the app. - Compiler tuning:
-march=armv8.2-a+crypto+dotprod+rcpc -mtune=cortex-x4. This is the baseline every Tensor G5 core supports. SVE is left to runtime detection. - Hardware virtualization is a separate, experimental track. Pixels ship pKVM through Android's Virtualization Framework (AVF), which a sideloaded app can use after an adb permission grant. But AVF runs VMs in the system's own crosvm, and Apple-only CPU instructions don't exist on Tensor cores, so it isn't a drop-in replacement. The default backend is QEMU's TCG JIT; the AVF backend is being explored in scion-avf and will become a selectable option in the app (#19).
docs/ROADMAP.md has the performance plan, including what using the PowerVR GPU would take.
- Android build fixes: bionic has no
shm_open, so it usesmemfd_createinstead. QEMU_VCPU_AFFINITYvCPU pinning for big.LITTLE hosts.- Upstream branding removed, as the branding notice requires for derivative builds. The boot splash is now optional (black screen without it), so the build no longer needs libpng.
The emulator is the work of the ChefKiss Inferno team (built on
TrungNguyen1909's qemu-t8030 and on QEMU). This project is not affiliated
with or endorsed by ChefKiss, and Apple is not affiliated with either. Please
consider supporting upstream. Upstream asks that
contributions to Inferno itself be written by humans, so keep that in mind
before sending anything from here upstream.
This repo is licensed under the AGPL-3.0, matching Inferno's own code. The Inferno fork keeps its GPL-3.0/AGPL-3.0 licensing.
You're responsible for complying with Apple's license agreements and the laws where you live.

