Showing posts with label Emulator. Show all posts
Showing posts with label Emulator. Show all posts

Monday, July 29, 2013

An Introduction to CobraDroid 1.0

I'm finally happy to say that the beta for my ongoing project called "CobraDroid" is fully released!  The project was actually released back in March on my website, but the source was just pushed to GitHub recently.  I wanted to talk a little about what CobraDroid is, what it can do for analysts, and what you can expect in the upcoming months.

What Can CobraDroid 1.0 Beta Do?

CobraDroid is a modified Android emulator image designed for individuals who want to perform application security assessments or analyze malware for the Android platform. It is not a service where you upload an application and receive a summary of activity, and it is not a black-box (there are plenty of those out there).  It should help you with performing your analysis, but keep in mind it will not perform all the analysis for you. It is released under the Apache Software License 2.0, so you are free to download, modify, and use the source.  The beta is mostly a teaser for what is to come, but it includes:
  • Configurable radio values (MIED, MDN, IMSI, SIM card serial number, and voicemail number)
  • Dynamically configurable “build.prop” values
  • Configurable SSL certificate validation bypassing 
  • Enhanced proxy capabilities
  • Additional user-space utilities
This should be enough to get you started, and already provides more functionality than the standard Android emulator.

What's Next?

The beta version of CobraDroid 1.0 is still lacking in terms of functionality and features.  Luckily, I've been hard at work on lots of new features.  I don't want to give away all the fun, but from a high level you can expect 1.0 to include:
  • A newer, hand-ported kernel (say goodbye to the 2.6.29 Goldfish kernel)
  • Full Bash shell + Busybox
  • Application specific packet-capturing
  • Java bytecode instrumentation
  • Mercury and LiME integration 
  • ..and more!
Many of these features are actually already implemented, but in a state of QA.  CobraDroid 1.0 should be ready to roll by the end of the summer, so stay tuned!

BruCON 2013

If by chance you are attending BruCON 2013, come check out my talk on CobraDroid and see a demo of the tool!  Hopefully I'll be presenting the tool in the states soon as well sometime soon.

If you are interested in trying CobraDroid, check out the getting started page.  Of course, feedback and comments are always welcome.

-jakev

Thursday, October 4, 2012

Building a Better Emulator - Part 1

I prefer using the Android emulator to a real phone for some application assessments for many reasons.  Unfortunately, not all apps run properly on the emulator.  This series of posts will focus on modifications we can make to our emulators to allow more control and flexibility during application assessments.  This first post will focus on controlling device identifiers and numbers.

Sometimes an application will obtain the device phone number and device identifiers and submit these to a remote server, maybe for authentication or authorization (such as white-listing phone numbers per provider).  The easiest way to obtain this information in an application is the use the TelephonyManager class.  We will focus on the following methods of the TelephonyManager class:
  • getDeviceId()
  • getLine1Number()
  • getVoiceMailNumber()
  • getSubscriberId()
  • getSimSerialNumber()
Some details about how this class works can be found here.  Basically these methods are used to access some values that are stored in the base-band emulator.  On Linux, the emulator is a file called  "$ANDROID_SDK_HOME/tools/emulator-arm" and the values are contained in this binary.  By default, the device ID (on the emulator it's the IMEI) is hard-coded as 000000000000000, and our phone number is  1555521%s, where "%s" is the 4 digit TCP port that the emulator is running on.  If we want to control these values on the emulator we are out of luck (without doing some modifications).  It is possible to do a find/replace in the "emulator-arm" binary for the IMEI and this post provides a patch to recompile the "emulator-arm" file to allow for these values to be set in a configuration file which is another alternative.  But even with this patch we can not change the phone number and voicemail number.  The method in this post will involve modifying some Android system libraries to allow for control of these values.

We have two options for performing the modifications: 1) Download the Android source code from the AOSP page, make the modifications in the Java source, and then build a custom version of Android, or 2) we can make the modifications to the compiled system libraries that are present on our Android emulator.  I chose to take option two because of the hardware requirements and testing speed of options one (building Android can take awhile).  So the first step was to find the TelephonyManager files in the Android source.  Note: For the remainder of this post, I will be using Android API 10.

 Not hard to find, they're in the "/frameworks/base/telephony/java/android/telephony/" directory.


Being in the "framework" directory gives us some hints as to where the files exist on the device.  When we build Android, all of these sources will eventually make their way into Dalvik DEX byte-code, and are zipped (but with JAR extension + META-INF directory) along with any other necessary files. They are placed in the "/system/framework/" directory on the device.


When the system boots, the Android system will take the "classes.dex" from each of these system library JARs, verify and optimize them, then store them on the "data" partition in the directory "/data/dalvik-cache/".  We'll need to modify the JARs if we want to make any system library changes.  The JAR that contains our compiled TelephonyManager DEX code is "/system/framework/framework.jar".

We first need to pull this file off the device.  We can then unzip the "framework.jar", and use "baksmali" to disassemble the "classes.dex" file.  Now we can do a simple grep to find our class of interest.


Now lets switch gears quick and get the replacement code ready.  I decided to replace our methods of interest with code that opened a file on the SD card and read the values from there.  The following code can be used as replacement code for the getDeviceId() method.


The code is pretty straightforward.  It reads "/mnt/sdcard/device_ids.txt" and uses some matching to get the desired value.  If at any point an exception occurs, the method logs this and just returns the default value.  The other methods were slightly different, but the concept was the same.

To get the Smali equivalent code, I used "ant" to build the app, them used "apktool" to decode the APK file. From here, it was just a direct replacement into the getDeviceId() method of the "TelephonyManager.smali" file.


With the modifications complete we can reverse the process: convert the Smali code back to DEX with "smali", zip the files back up as "framework.jar", and push the new archive to the "/system/framework/" directory.


The final step is to create a new system partition, and we can use the method posted here.  Restarting the emulator with the new system partition will result in our custom library being loaded.

And there we go! The return of any of these methods is now controlled by the contents of the "/mnt/sdcard/device_ids.txt" file.  For those who want to just make the changes and go, I've included a working version of the "framework.jar" for API 10 if people would like to grab it, push it to your emulator, then build a new system image.  If at any point you no longer want to control these values, you can just remove the "/mnt/sdcard/device_ids.txt" file, and the "real" getXX() method will be called.  If anyone observes any unusual instability or errors, please contact me!  Note: Use this library at your own risk.  I do not suggest using this library on a real device!

To make things even easier, I wrote an application to help manage the "/mnt/sdcard/device_ids.txt" file, so you can make changes instantly.  You can grab the app source or APK file from my Github repositories, as well as the "framework.jar" and a sample "device_ids.txt".


I'll continue to post more changes to help with application assessments over the next few months. :)

-jakev

Monday, June 18, 2012

Making Persistent Changes to an Android Emulator

When working on an Android emulator, we sometimes want to make changes that can survive a reboot.  This isn’t a problem for things like installing applications (which is usually what you are using the emulator for), because of the way that the AVD Manager creates your virtual device.  However, system changes (that is, changes to the /system partition) will not survive on a reboot.  There are legitimate reasons to do this; here are just a few off the top of my head:

  • Adding or modifying system binaries in the /system/bin or /system/xbin directories
  • Adding entries to the /system/etc/hosts file for redirection for specific domains
  • Changing settings in the /system/build.prop file such as the device manufacture and phone model (for apps that refuse to run on certain devices)
  • Adding entries to the android cert file at /system/etc/security/cacerts.bks so that the device trusts self-signed certificates (again, for proxying)
This post will show you how you can make changes to files on the system partition on your Android emulator that will persist.

First let’s make an Android virtual device (AVD).  I’m going to use API 8, the standard Froyo distribution, for the target.  Note that I’m creating a SD card image with this AVD that is 512MB.  This should be plenty of space to store temporary system image.  I chose the name “Froyo” but you can use whatever you like.



When we press “Create AVD”, the AVD Manager creates some files in the ~/.android/avd/ directory (this location may vary on Windows).  Specifically, it creates:
  • [avd_name].ini - A file containing configuration settings that point to the AVD’s directory
  • [avd_name].avd - A directory containing settings and file-system images specific to this AVD – the SD card image and the user data image are a couple examples (others are created after the AVD boots up)
Our ./Froyo.avd/config.ini file looks like this:

The contents of the Froyo.avd directory:

 
The remaining file-system images are common to all AVD of a specific API level, and can be found at $SDK_HOME/platforms/android-*/images/.  This will focus on changes to the system.img partition.  This, by default, is mounted as read-only (just as a real device would), and even if you remount the drive and make changes, they will not persist on a system reboot.  Our goal is to make a custom system.img file, and have the AVD load this image instead of the default image.

Before we get started, you’ll need to obtain a copy of the mkfs.yaffs2 utility compiled for ARM.  Go ahead and start our new emulator, making sure to specify a safe “partition-size”.

 

Once the emulator boots, we can make the changes we wish to reflect on our custom system image.  For this example, I’ll change the “ro.product.brand” field in the system/build.prop file, but you could do any changes you want.  First we need to pull the /system/build.prop file so that we can edit it (no editor is available from the shell).  We can accomplish this with the command:

 
 
Then we can edit the file (Disclaimer - editing this file may affect the stability of the system!):

 

Now we can remount the system partition as read-write and push the new file to the device:

 

If all your changes are complete, the next step is to run the mkfs.yaffs2 utility on the device to create a *.img file we can use.  To make this easier, I wrote a small shell script (getimage.sh) to automate the steps.  The steps should be easily followed by reading the script.




Running the script yields the following output:

  

We now have a file called _system.img in our current working directory.  At this point we have two options.

Option 1 – Replace the Global system.img
If you are alright with the change applying to all of the AVD’s that you run at this particular API level, you can simply move the new image where the old image was.  It’s important to back-up the old system.img in case something went terribly wrong.  As stated above, the image files are located at $SDK_HOME/platforms/android-*/images/.



Now when you restart your AVD, you should see the changes.

Option 2 – Modify the AVD's Configuration
Let’s say that you want this change to apply only to this specific AVD.  This can be accomplished by cloning the images directory, and then modifying our AVD's configuration.



The line we need to change is the "image.sysdir.1" parameter of the Froyo.avd/config.ini file:



And we're done!  Hope this helps some people with customizing their emulator images.

-jakev