10

I've been spending a good chunk of time looking at some 3rd party applications that were successful in "reproducing" (although I believe not necessarily by understanding the algorithm completely but simply extracting the core of the logic from the original binaries and replicating it into their own programs) the main logic for simulating an Apple TV server with full AirPlay mirroring support, to name a few:

  1. AirServer (OSX/Windows)
  2. Reflector (OSX/Windows)
  3. AirReceiver (Android)
  4. X-Mirage (OSX/Windows)
  5. AirPin PRO (Android)
  6. EZCast Screen (Android)
  7. Xiaomi Milian (Android/runs on Xiaomi Box)

By looking at their decompiled code and some other references on the web, most of the protocol aspect is already known/relatively easy to figure out and I did it already, so no sweat there, the key part I'm having a tough time understanding how these guys were able to pull it off is related to the FairPlay decryption portion (i.e.: when receiving and responding to the fp-setup challenges as well as decrypting the AES key sent in the last step of the challenge).

They all seem to have extracted the white-boxed/obfuscated functions out of Apple's original airtunesd/fairplayd daemon code and embedded it into their source, delegating the calls to seed/encrypt/decrypt to it.

I noticed in some iOS devices this daemon also exist (most likely used to encrypt the feed when mirroring the screen via AirPlay to a compatible server) but was wondering how different this really is from the one shipped with the Apple TV and if my assumptions are actually correct (is that were most of these guys are taking this code from?).

Was hoping either someone with previous experience or a little more knowledge on the topic could shed some light/pointers so I could find a way to at least do the same these guys were able to accomplish (which is not really deobfuscating the code but just extracting it to embed in their own programs).

PS: For clarity, aside from confirmation I was looking for some pointers as to how one would be able to extract compilable code from a said binary, given my attempts at disassembling and decompiling via IDA Pro haven't provided me with much that I can reuse to compile new code that reproduces that piece of the puzzle.

6
  • Have you considered contacting any of the authors of the listed software to ask this question? Don't forget to post the results if you get anything useful! :)
    – ixje
    Jan 28, 2015 at 13:46
  • 1
    I did (for some), already expecting nothing to be shared :) didn't get anything back. Jan 28, 2015 at 17:30
  • At one point in time during the development of my project I bumped into an [open source implementation] (github.com/espes/Slave-in-the-Magic-Mirror) that addressed the issue by running the original Apple iOS binary code (from airtunesd) in an ARM emulator in Python and mapped the functions as Python bindings. At least they didn't have to extract the original functions from the binary and recompile/link into their binaries (given it's all python). Jan 28, 2015 at 17:50
  • I ended up following a similar approach but using the insights I acquired from analyzing the implementation from VMLite's rplay where the Apple DRM runs on a remote server and is called upon during the challenge phase of the mirroring connection. Jan 28, 2015 at 17:51
  • @RobertoAndrade, is it illegal to sell those commercial apps? Why Apple didn't stop them?
    – RRN
    May 3, 2020 at 9:40

4 Answers 4

5

I have spent some time to look into Apple's airplay mirroring support, which is encrypted by fairplay protocol. After investigating serveral existing commercial applications I have finally managed to get a way of decrypting fairplay protected streams. I have extended the shairplay code to demostrate this ability. Please look at https://github.com/foxsen/shairplay, parts of the README.md:

Update by foxsen, 2015/4/20: Experimental support for fairplay protocol and airplay:

  • fairplay encrpted audio is supported (et == 3)
  • AAC-ELD audio is supported(untested yet)
  • airplay service framework is added, up to the point that the mirroring connection starts streaming. But the UI and callbacks to be done.
  • fairplay support is performed via interactions with a server

Because I have not enough time and interest to do all the other necessary coding to make a full open source solution that support mirroring, I hope people can help to continue the project or port my code into other projects like kodi. I am willing to help with related issues.

The dirty works are hidden in my server app. During a session with fairplay, we need to interact with the server for three times to get the job done. You can read the code above to learn how. When I get more time, I prepare the write something about this part of work. Basically it involves some reverse engineering and a lot of tricks to rebuild a relocatable object from part of a binary.

Public access to that app is open and free for personal visits now. If anybody want to use it in commercial environment, you can contact me.

Happy hacking.

9
  • This is basically the same thing I ended up doing. rPlay from VMLite also does the same. I'm curious to share notes as to how you went about building the server component and am happy to share mine (although also not open source). Let me know. Apr 20, 2015 at 17:02
  • In fact, a easy way to setup server is to utilize existing .so from apps like reflector. A chroot environment can run android .so in linux:) Then you can use dlopen and call its functions. I go further than this to practise my skills. I reverse some part of the code to understand more. When what left is only tedious repeat, I stopped and then write a series of scripts to draw out part of the binary, re-add symbol table and relocation entries, with some fixups it becomes a relocatable .o that can be linked to my server app. Roughly so.
    – foxsen
    Apr 21, 2015 at 0:00
  • I don't really care much about the airplay itself. But your question about how to port part of a binary logic into a new binary raises my interest. Now I prove that this can be done. I am considering to write some articles on this topic since it is very interesting, all kinds of binary manupulations. Maybe i can write some general tools for this.
    – foxsen
    Apr 21, 2015 at 0:11
  • yeah, that's precisely what I was looking for on an answer. So although you were able to do it (just like the dozen other apps I listed) doesn't mean you have answered the question :) Let me know once you're able to share more on the approach to porting the functions over (yeah the .so on android is precisely what I had done), as what I originally wanted to do was to extract the functions and link them against my program instead. Apr 21, 2015 at 0:14
  • Since your approach is also coincidentally being applied to reproduce the FairPlay decryption functions, I think sharing the details here is probably the best option, but in case you want to also share the more generic answer on this other post I have going (where AirPlay/FairPlay is out of the scope of question), I'd appreciate it too: reverseengineering.stackexchange.com/questions/6759/… Apr 21, 2015 at 11:09
0

The general process is to have the official DRM decrypt what you want and the grab it. Clutch does this on iOS. Decompiling is a separate topic, as big if not bigger than the DRM subversion.

1
  • Well, that's the core of the question, all these solutions were able to "bring" the official DRM decryption logic into their binaries (my original guess was by decompiling it - although obfuscated - and recompiling it into their binaries as a black box without actually understanding it). Question is how were they able to achieve that? I see all the same logic on their binaries but can't figure out (other than via decompilation) how to port the logic over to my own program in the same black-box style. Nov 24, 2014 at 18:10
0

I have been looking at this also for a while now and came to the exact same conclusion as you. The only method I see viable is to decompile what you have and embed into your new process. Maybe we can discuss this further.

1
  • We've been trying this route without much success given the complexity of the functions and the challenges decompilers have in putting together code that can be reassembled/recompiled. Would love to collaborate further on this if it's a topic of common interest. Any particular method suits you better to do so? Nov 29, 2014 at 15:55
0

From my work (on applications I will not disclose) I will give a short conclusion. The device does not use the older AirPlay methods. e.g. there isn't just a single key that can decrypt across any device. You must have a server, we call it an "AirPlay server", that the device calls for a decryption key for that specific session. The rest of the work is done on the device (decryption). So the device asks the server, server responds with a key, device uses the key for decryption. Most of the actual work is done on the device.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.