Pages

Sunday, 16 March 2014

Running ARM apps on Android x86

Well a year's passed since my last post. It's been a busy one at that! Feel free to skip to the bottom if you just want the instructions on how to get libhoudini running on Android x86...

These past few months I've being playing with a customized flavour of Android x86 and virtualization (I'm loving OpenStack!). For those of you who don't know it's a project to get Android running on various Intel x86 architecture based platforms based of the vanilla Android Open Source Project from Google.. Yes, that's right - you can run native Android on your PC or Mac! No more horrendously slow Android Emulator.

Well, almost.

Android x86 runs super fast on most bits of Intel hardware. The majority of apps will function fine as well, at least if they're 100% written in Java. But the fact is a lot of apps also have native libraries built into them (compiled using the NDK and written usually in C or C++). When developers prepare an app for release they can choose what architecture(s) to compile their native library binaries for. Most will at least compile for ARM but in the interest of cutting down on the size of the APK a lot skip x86 and others (MIPS etc). Google Play does apparently allow you to have a separate APK for each architecture so you won't need to worry about having a few useless-to-the-many MBs of x86 code in the APK that your ARM users install. Many developers maybe unaware of this feature, and I'm sure some developers are just not aware that x86 versions of Android devices are emerging more and more.

So where does that leave us? You emulate ARM architecture on your x86 hardware. From what little research I've done into the Android Emulator itself, I believe the entire OS is ARM based so there's a tonne of constant emulation that needs to be done, hence the major performance cost. With Android x86, most of the code is executed natively (i.e. critical/normal programs run fast) and the code that is only available in ARM compiled binaries is translated real-time into instructions your x86 CPU can understand.

This is done with a little library called Houdini. libhoudini is a Binary Translator (translates ARM ABI to x86 ABI) developed by Intel and is close sourced. The information on the internet is really sparse and there's a lot of broken links so I'm hoping this blog article will stay around for a while and be helpful to some. From what I gather the original libhoudini libraries were ripped from a Lenono K900 device that runs x86 hardware. Intel must've provided their binaries to Lenovo for release. That work was done by the BuilDroid project which seems to have changed names to AndroVM and now Genymotion (a great online Android Emulator that allows you to choose a range of device types, resolution types, Android versions etc).

So on to the fun stuff, the instructions on how to get libhoudini installed and configured on Android x86. I just test against a branch based on the 4.2.2 tree so I can't say how well it'll work on other versions.

1. Have the AOSP project source code download and the build environment all setup. We'll call this $AOSP.
2. Download and unarchive libhoudini-patch-and-binaries.tgz.
3. Copy the contents of <...>/libhoudini-patch-and-binaries/system/lib to $AOSP/out/target/product/<product name>/system/lib
4. cd $AOSP/dalvik
5. git apply -v <...>/libhoudini-patch-and-binaries/jb-houdini.patch
6. Add the following line to $AOSP/device/<your hardware manufacturer>/<device name>/system.prop (e.g. device/ibm/thinkpad/system.prop):
ro.product.cpu.abi2=armeabi
7. Build and deploy your Android x86 OS.
8. Try running an app with ARM-only libraries and if it doesn't crash you're lucky!

I had success running my own apps, Facebook and Angry Birds.
I didn't have much luck with Unity based games.