OTA revisited - a quick followup
A simple script to recreate the iOS filesystem on your Mac
Jonathan Levin, @Technologeeks, http://newosxbook.com/ - 09/24/15
About
iOS 9 9.2 is out , and we are once more in an unbreakable window. This is very likely temporary, but AAPL has put some seriously remarkable efforts into getting things right this time. Vectors in the good ol' DYLD are all but gone, and the new "System Integrity Protection" (a.k.a "rootless") is a royal pain (though still bypassable).
Researchers trying to find faults in the system - by analyzing its binaries - can easily get the full image thanks to @Xerub's keys for the iPhone 5. This, however, only covers 32-bit. For 64-bit, there are no publicly available decryption keys. Fortunately, the OTA vector described in detail by yours truly in a previous article still works. Said article also contains a small tool - aptly named ota - to extract the payload files, once de-pbzx'ed and xz -d
'ed. It also refers to the use of bxpatch
for files. Fellow iPhoneWiki user npupyshev has a working sample of bxpatch in this this GitHub, which you can use. For those lazy to compile, I put it in the download.
Because I'm actively reversing iOS 9 for MOXiI 2, I wrote a small script to enable me to use an OTA zip (which you can get easily through the iPhone Wiki along with the base filesystem on a jailbroken device - in my case 8.4 9.0.2 on an iPhone 7,2 8,2 - to reconstruct the filesystem on the host. I'm attaching it here.
Dec 12 2015: Update: Just tested this on the 9.2 OTA (from 9.0.2). Works :-)
Feb 04 2016: Can use this with the jumbo OTA updates as well (9.3b3 works)
Feb 16 2016: Wait, there's more - Part Three
Usage:
Say you grabbed an update zip from AAPL - put it in some directory, and unzip it
Zephyr:OTA morpheus$ unzip 076577b6c8473847597916af4888f5508efaa861.zip
Archive: 076577b6c8473847597916af4888f5508efaa861.zip
Archive: 076577b6c8473847597916af4888f5508efaa861.zip
inflating: META-INF/com.apple.ZipMetadata.plist
inflating: AssetData/Info.plist
inflating: AssetData/boot/BuildManifest.plist
extracting: AssetData/boot/Firmware/all_flash/all_flash.n61ap.production/DeviceTree.n61ap.im4p
inflating: AssetData/boot/Firmware/all_flash/all_flash.n61ap.production/DeviceTree.n61ap.im4p.plist
extracting: AssetData/boot/Firmware/all_flash/all_flash.n61ap.production/LLB.n61.RELEASE.im4p
..
..
..
extracting: AssetData/payloadv2/prepare_patches/usr/standalone/update/Mav10.Release.bbfw
creating: AssetData/payloadv2/prepare_patches/usr/standalone/update/ramdisk/
inflating: AssetData/payloadv2/prepare_patches/usr/standalone/update/ramdisk/H7SURamDisk.dmg
inflating: AssetData/payloadv2/prepare_payload
inflating: AssetData/payloadv2/removed.txt
inflating: AssetData/post.bom
inflating: AssetData/pre.bom
inflating: Info.plist
Next, unpack the tar file from this link, and you will see:
Zepyhr:/tmp morpheus$ mkdir New; cd New
Zepyhr:/tmp/New morpheus$ tar xvf OTApack.tar
x applyota.sh
x bxpatch
x liblzma.dylib # Just in case you don't have it
x ota.c # The source for ota, in case you want that too
x otaa
It is assumed at this point that you have A connected iOS device with the base image to which the OTA update applies. You can connect it over usbmuxd, or over WiFi - that's irrelevant, so as long as you change the lines in the script which need changing, namely:
DEFIOSDEV=root@phontifex-2 # likely root@localhost for you DEFIOSPORT=2222 # Leave 2222 if via USBMux UNPACKED_OTA_DIR=~/Downloads/OTA # Point at where OTA was unzipped
At any rate, you can then run the small applyota.sh
script, like so:
Zephyr:New morpheus$ ./applyota.sh sbin/launchd
Retrieving launchd from your device...
launchd 100% 267KB 266.9KB/s 00:00
Patching sbin/launchd with patch from /Users/morpheus/Downloads/OTA/AssetData/payloadv2/patches/sbin/launchd
Zephyr:New morpheus$ ls -l sbin/launchd
-rw-r--r-- 1 morpheus staff 290368 Sep 24 09:05 sbin/launchd
# Verify with jtool - if --sig doesn't complain, the signature is intact
Zephyr:New morpheus$ jtool --sig !$
jtool --sig sbin/launchd
Blob at offset: 288432 (1936 bytes) is an embedded signature
Code Directory (1590 bytes)
Version: 20100
Flags: adhoc
Identifier: com.apple.xpc.launchd
CDHash: 35577f3f4f03f37309e4df4576013c85a7d9c5ef
# of Hashes: 71 code + 5 special
Hashes @170 size: 20 Type: SHA-1
Empty requirement set
Entitlements (258 bytes) (use --ent to view)
Blob Wrapper (8 bytes) (0x10000 is CMS (RFC3852) signature)
And this also works recursively (which is why I made the script in the first place!)
Zephyr:New morpheus$ ./applyota.sh usr Directory mode usr recursing /Users/morpheus/Downloads/OTA/AssetData/payloadv2/patches/usr/bin Directory mode usr/bin Retrieving DumpBasebandCrash from your device... DumpBasebandCrash 100% 36KB 36.1KB/s 00:00 Patching usr/bin/DumpBasebandCrash with patch from /Users/morpheus/Downloads/OTA/AssetData/payloadv2/patches/usr/bin/DumpBasebandCrash Retrieving brctl from your device... brctl 100% 148KB 148.1KB/s 00:00 .. Patching usr/libexec/wifiFirmwareLoader with patch from /Users/morpheus/Downloads/OTA/AssetData/payloadv2/patches/usr/libexec/wifiFirmwareLoader Retrieving xpcproxy from your device... xpcproxy 100% 40KB 40.1KB/s 00:00 Patching usr/libexec/xpcproxy with patch from /Users/morpheus/Downloads/OTA/AssetData/payloadv2/patches/usr/libexec/xpcproxy recursing /Users/morpheus/Downloads/OTA/AssetData/payloadv2/patches/usr/sbin Directory mode usr/sbin .. Retrieving coreos-oscar2.image from your device... coreos-oscar2.image 100% 113KB 113.5KB/s 00:00 Patching usr/standalone/firmware/oscar/coreos-oscar2.image with patch from /Users/morpheus/Downloads/OTA/AssetData/payloadv2/patches/usr/standalone/firmware/oscar/coreos-oscar2.image # Examine: Zephyr:New morpheus$ ls -R usr bin lib libexec sbin share standalone usr/bin: DumpBasebandCrash brctl powerlogd simulatecrash usr/lib: # the perennial favorite, dyld.. StandardDMCFiles dyld system xpc ... usr/libexec: # Where the wild things are BackupAgent biometrickitd misagent ptpd BackupAgent2 bootpd misd resourcegrabberd CrashHousekeeping bulletindistributord mobile_assertion_agent rolld DuetHeuristic-BM cc_fips_test mobile_diagnostics_relay routined FSTaskScheduler configd mobile_file_relay rtcreportingd FinishRestoreFromBackup corecaptured mobile_house_arrest screenshotsyncd MobileGestaltHelper crash_mover mobile_installation_proxy securityd NANDTaskScheduler demod mobile_obliterator seputil OTAPKIAssetTool dhcpd mobile_storage_proxy sharingd OTATaskingAgent diagnosticd mobileassetd splashboardd PreboardService eventkitsyncd mtmergeprops springboardservicesrelay ProxiedCrashCopier fmfd nanomediaremotelinkagent streaming_zip_conduit PurpleReverseProxy fseventsd nanoregistrylaunchd swcd SafariCloudHistoryPushAgent ftp-proxy nehelper syslog_relay SyncAgent gamecontrollerd networkd_privileged timed UserEventAgent hangtracerd nlcd tipsd addressbooksyncd hostapd notification_proxy transitd afcd ios_diagnostics_relay nptocompaniond tursd aitd keybagd nsurlsessiond tzd amfid languageassetd nsurlstoraged tzinit aosnotifyd limitadtrackingd oscard tzlinkd assertiond lockbot pcapd wapic atc lockdownd pfd webinspectord atwakeup lsd pkd wifiFirmwareLoader backboardd mc_mobile_tunnel pkreporter xpcproxy usr/sbin: BTAvrcp BlueTool filecoordinationd notifyd scselect BTLEServer addNetworkInterface ipconfig nvram scutil BTMap aslmanager mDNSResponder pppd syslogd BTPbap cfprefsd mDNSResponderHelper racoon wifid BTServer distnoted mediaserverd rtadvd wirelessproxd usr/share: firmware mecabra misc tokenizer zoneinfo.default usr/share/firmware: multitouch wifi ...
.. which is the next best thing to having the decrypted DMG at your disposal.
Q&A
- Where are all the rest of the files?
This script handles only patches. Those files which are in full are in the payload.00[0-8] files. Following the last article to the letter with the attached ota tool will get you all of the files. This will look something like:
# You dont have to do this as root.. I just was at the time bash-3.2# pwd /Users/morpheus/Downloads/OTA/AssetData/payloadv2 bash-3.2# ls links.txt payload.001 payload.004 payload.007 prepare_patches patches payload.002 payload.005 payload.008 prepare_payload payload.000 payload.003 payload.006 payload_chunks.txt removed.txt bash-3.2# for p in in payload.* ; do ~/bin/pbzx $p > extracted.$p.xz; done .. bash-3.2# file extracted.* extracted.payload.000.xz: xz compressed data extracted.payload.001.xz: xz compressed data extracted.payload.002.xz: xz compressed data extracted.payload.003.xz: xz compressed data extracted.payload.004.xz: xz compressed data extracted.payload.005.xz: xz compressed data extracted.payload.006.xz: xz compressed data extracted.payload.007.xz: xz compressed data extracted.payload.008.xz: xz compressed data bash-3.2# for i in extracted.*; do xz -d $i; done # Then apply the ota tool (-e '*' to extract, or just -l to list) bash-3.2# for i in extracted.*; do ~/bin/otaa -l $i; done Applications/AACredentialRecoveryDialog.app/Info.plist Applications/AACredentialRecoveryDialog.app/_CodeSignature/CodeResources Applications/AccountAuthenticationDialog.app/Info.plist Applications/AccountAuthenticationDialog.app/_CodeSignature/CodeResources ... # To look for a file in the extracted payload bash-3.2# for i in extracted.*; do ~/bin/otaa -l $i; done | grep sbin usr/sbin/WirelessRadioManagerd usr/sbin/absd usr/sbin/fairplayd.H2 usr/sbin/spindump # Then extract bash-3.2# for i in extracted.*; do ~/bin/otaa -e usr/sbin/absd $i ; done bash-3.2# ls -l usr/sbin/absd -rw-r--r-- 1 root staff 583552 Sep 24 19:59 usr/sbin/absd
- What about the shared library cache?
Good question. I haven't figured out the .dydiff format yet, but apparently I don't need to - connect an iOS 9 device to XCode, and it will suck all the libraries + full symbols automatically, and shove them in ~/Library/Developer/Xcode somewhere. Why? I don't know. Yet another case of AAPL shutting doors and opening windows.
- I'm getting weird errors/jtool complains/etc - You're probably using an incorrect OTA zip for your iOS device. Make sure the iPhone/iPod/iPad model number is right. I tested this on my iPhone 6 (7,2), and it worked splendidly well.
- I want this for Linux! - Well this is a shell script, so it should work - if you compile the binaries for ELF.. ota.c is ANSI C, and should compile neatly for Linux. npupyshev's code will likely also compile for Linux, though I can't say I've tried. The script flow would be exactly the same
- Where do I say thanks/complain/bitch/comment/flame? Right here.