OTA: Episode IV : A new hope

The much needed "search" functionality in an OTA

Jonathan Levin, (@Morpheus______), http://newosxbook.com/ - 08/31/2016

About

While doing massive searches for strings inside binaries all across the iOS filesystem, it struck me I've overlooked something really, really simple and stupid - Since AAPL graciously provides the full unencrypted filesystem as one jumbo archive, it would be MUCH faster to just search inside the OTA!

So what changed?

A super simple fix - when I enumerate the OTA (so that you can, say, extract a file with -e) I now search its contents using a simple memmem(3). If I find whatever is supplied as a search string (with the new -s) I print out the offset in the would-be-extracted file:

Why is this useful?

Because you can now do searches all across [Watch/Tv/i]OS filesystems just by keeping the OTAs archives (that is, post pbzx and xz) on your filesystem. WAY MORE EFFICIENT than doing a find . | xargs grep ... for Oh-So-Many reasons, not the least of which is SPEED - search completes in mere seconds. This is especially useful for, say, entitlements...

https://www.theiphonewiki.com/wiki/OTA_Updates/iPhone/10.x, etc for OTA downloads!
root@Jormungandr (.../OS/10.0.1GM)# wget http://appldnld.apple.com/ios10.0/031-7.../8232ba9fdb7cb393d0e2d5c1de943a35f15aab5c.zip

root@Jormungandr (.../OS/10.0.1GM)# unzip 823*.zip
  ..
  extracting: AssetData/payloadv2/payload
  ..
root@Jormungandr (.../OS/10.0.1GM)# cd AssetData/payloadv2
root@Jormungandr (.../OS/10.0.1GM/AssetData/payloadv2) # cat payload | pbzx > p.xz            
root@Jormungandr (.../OS/10.0.1GM/AssetData/payloadv2) # xz -d p.xz
root@Jormungandr (.../OS/10.0.1GM)# cd ../..
root@Jormungandr (.../OS/10.0.1GM)# ota -s com.apple.private.security.container-manager AssetData/payloadv2/p
Found in Entry: System/Library/PrivateFrameworks/MobileContainerManager.framework/Support/containermanagerd, relative offset: 65b9d (Absolute: daf7f641)
Found in Entry: usr/libexec/keybagd, relative offset: 4a7cf (Absolute: fac9cd2c)
Found in Entry: usr/libexec/lsd, relative offset: 87ff (Absolute: fc3f5860)

Or, for symbols - since they have to be somewhere as TEXT, right...? so:

root@Jormungandr (.../OS/10.0.1GM)# ota -s sandbox_init AssetData/payloadv2/p
Found in Entry: System/Library/Caches/com.apple.dyld/dyld_shared_cache_arm64, relative offset: 19fd5564 (Absolute: 35c0bbb4)
Found in Entry: System/Library/Caches/com.apple.dyld/dyld_shared_cache_arm64, relative offset: 2590bd58 (Absolute: 415423a8)
...
Found in Entry: usr/libexec/wifiFirmwareLoader, relative offset: c91d (Absolute: fe49ab3d)
Found in Entry: usr/libexec/wifiFirmwareLoader, relative offset: daf4 (Absolute: fe49bd14)
Found in Entry: usr/sbin/mDNSResponder, relative offset: 9a27d (Absolute: 1004a4ddb)
Found in Entry: usr/sbin/mDNSResponder, relative offset: 9a293 (Absolute: 1004a4df1)
Found in Entry: usr/sbin/mDNSResponder, relative offset: ac8ad (Absolute: 1004b740b)
Found in Entry: usr/sbin/mDNSResponder, relative offset: ae4e9 (Absolute: 1004b9047)
Found in Entry: usr/sbin/mDNSResponder, relative offset: b7761 (Absolute: 1004c22bf)

Or, for users of an XPC service (assuming not via dylib, though):

root@Jormungandr (.../OS/10.0.1GM)# ota -s com.apple.dprivacyd AssetData/payloadv2/p
Found in Entry: Applications/MobileNotes.app/MobileNotes, relative offset: 304586 (Absolute: 64f6c86)
Found in Entry: System/Library/Caches/com.apple.dyld/dyld_shared_cache_arm64, relative offset: 1cfd12a8 (Absolute: 38c078f8)
Found in Entry: System/Library/Caches/com.apple.dyld/dyld_shared_cache_arm64, relative offset: 1cfd1320 (Absolute: 38c07970)
...
Found in Entry: System/Library/Caches/com.apple.xpcd/xpcd_cache.dylib, relative offset: 1e07a4 (Absolute: 7538b0e7)
Found in Entry: System/Library/LaunchDaemons/com.apple.dprivacyd.plist, relative offset: af (Absolute: 9140d7a2)
Found in Entry: System/Library/LaunchDaemons/com.apple.dprivacyd.plist, relative offset: ea (Absolute: 9140d7dd)
Found in Entry: System/Library/LaunchDaemons/com.apple.jetsamproperties.N61.plist, relative offset: 1c57 (Absolute: 9141733b)
Found in Entry: System/Library/LaunchDaemons/com.apple.jetsamproperties.N71.plist, relative offset: 1c98 (Absolute: 914201e2)
Found in Entry: System/Library/LaunchDaemons/com.apple.jetsamproperties.N71m.plist, relative offset: 1c98 (Absolute: 914290c9)
Found in Entry: usr/libexec/dprivacyd, relative offset: 827c (Absolute: fa2fc0de)

Or, for seeing who's hard coding a particular file:

root@Jormungandr (.../OS/10.0.1GM) #ota -s var/MobileDevice/ProvisioningProfiles  AssetData/payloadv2/p   21:31
Found in Entry: System/Library/Caches/com.apple.dyld/dyld_shared_cache_arm64, relative offset: de01250 (Absolute: 29a378a0)
Found in Entry: System/Library/Caches/com.apple.dyld/dyld_shared_cache_armv7s, relative offset: bf2590c (Absolute: 58653fb7)
Found in Entry: usr/libexec/keybagd, relative offset: 2a538 (Absolute: fac7ca95)
Found in Entry: usr/libexec/mobile_obliterator, relative offset: 1e453 (Absolute: fd15a16c)

Limitations

This only tells you which file in the OTA your string is found. No RegExps, just hard coded strings. If it tells you file is shared_cache or Mach-O, use jtool -F from that point. Unfortunately, that's very common for XPC clients (since they use some framework abstraction, but if you get the symbol wrapping it, the problem can be reduced to the symbol use-case.

...And, since you're probably wondering about MOXiI 2 (a.k.a *OSI, Volume III)

It's actually done. And exceeded 400 pages. Sick, but comprehensive. Being reviewed by my expert team, and - more importantly - tested on a jailbroken iOS 10 β 8, which already proved a few nasty surprises. Yes, it's coming, Yes, soon, and I mean, imminently. Just bear with me.

In the meantime, have I mentioned Technologeeks' OS X and iOS for Reverse Engineers training has a new session up, October 31st, in NYC? Register now and you'll get a free (optionally, signed) copy.

Sources

OTA.c (updated with -s functionality)

Greets

  • AAPL: For totally dropping encryption everywhere (but shame on you for breaking sandbox_inspect!!!!!!)
  • Luca For being the world's greatest jailbreaker