Reverse engineering a mobile app is the process of analyzing the compiled app to extract information about its source code. The goal of reverse engineering is to comprehend the code.
Reverse engineering is the process of reconstructing the semantics of a compiled program's source code. In other words, you take the program apart, run it, simulate parts of it, and do other unspeakable things to it to understand what it does and how.
How can an attacker use reverse engineering?
- To enable black-box testing of mobile apps. - Modern apps often include controls that will hinder dynamic analysis. SSL pinning and end-to-end (E2E) encryption sometimes prevent you from intercepting or manipulating traffic with a proxy. Root detection could prevent the app from running on a rooted device, preventing you from using advanced testing tools. You must be able to deactivate these defenses.
- To enhance static analysis in black-box security testing - In a black-box test, static analysis of the app bytecode or binary code helps you understand the internal logic of the app. It also allows you to identify flaws such as hard-coded credentials.
How to get an APK File
For the analysis of android applications we need the apk file. In Google Play Store, there is no option to download an APK file. So the very obvious question arises, that is from where to get the apk file for android application?
If we are lucky, we can get the apk of the required application by simply googling myapp apk file. But we can never be sure that we will get the APK file for all the applications and more than that it is not safe to download and install APK files from untrusted websites.
Fortunately, we can use adb tool to extract APK from our android device.
For extracting APK from android device:- Download and install ADB tool on your desktop.
- Connect Android device to a laptop and start ADB CLI.
-
Determine the package name of the application using:
adb shell pm list packages
-
Get the full pathname of the APK file for the desired package.
adb shell pm path com.example.someapp
-
Using the full pathname from Step 2, pull the APK file from the Android device.
adb pull /data/app/com.example.someapp-2.apk path/to/desired/destination
Using APKTool for reverse Engineering
Apktool is very simple to use, but also very powerful. It has two main functionalities: decode and build.
Decoding is for making APK data readable (and modifiable), while building is for transforming the decoded files into an APK file again. For this, Apktool makes use of smali, a disassembler for DEX files. This turns the actual Dalvik bytecode into an intermediate representation (smali code) that can be modified. With baksmali you can reassemble smali code into DEX files, effectively allowing modifications to app code.
Disassembling an APK is pretty simple:apktool decode -o output_dir application.apk
Here is an example output of smali code of a MainActivity class, as generated by Apktool:
.class public Lcom/example/ui/MainActivity;
.super Lcom/example/ui/BaseActivity;
.source "Application"
# interfaces
.implements Lx/lz;
.implements Lx/ma;
.implements Lx/mo;
.implements Lx/mp;
# instance fields
.field private m:Ljava/util/HashMap;
.annotation system Ldalvik/annotation/Signature;
value = {
"Ljava/util/HashMap<",
"Ljava/lang/Integer;",
"Lorg/apache/cordova/CordovaPlugin;",
">;"
}
.end annotation
.end field
So, once Apktool has done its job, you get a file structure like this:
output_dir/
├── AndroidManifest.xml
├── apktool.yml
├── assets
├── lib
├── original
├── res
├── smali
├── smali_classes2
└── unknown
Tampering Reverse Engineered Code
Tampering is the process of changing a mobile app (either the compiled app or the running process) or its environment to affect its behavior. For example, an app might refuse to run on your rooted test device, making it impossible to run some of your tests. In such cases, you'll want to alter the app's behavior.
Tampering Techniques
-
Binary Patching
Patching is the process of changing the compiled app, e.g., changing code in binary executables, modifying Java bytecode, or tampering with resources. This process is known as modding in the mobile game hacking scene. Patches can be applied in many ways, including editing binary files in a hex editor and decompiling, editing, and re-assembling an app. -
Code Injection
Code injection is a very powerful technique that allows you to explore and modify processes at runtime. Injection can be implemented in various ways, but you'll get by without knowing all the details thanks to freely available, well-documented tools that automate the process. These tools give you direct access to process memory and important structures such as live objects instantiated by the app. They come with many utility functions that are useful for resolving loaded libraries, hooking methods and native functions, and more. Process memory tampering is more difficult to detect than file patching, so it is the preferred method in most cases. Substrate, Frida, and Xposed are the most widely used hooking and code injection frameworks in the mobile industry.
Recompiling Android APK
Modern mobile operating systems strictly enforce code signing, so running modified apps is not as straightforward as it used to be in desktop environments.
Fortunately, patching is not very difficult if you work on your own device. You simply have to re-sign the app or disable the default code signature verification facilities to run modified code.
- apktool — tool for reverse engineering Android apk files. In this case we are using to extract files from apk and rebuild.
- keytool — Java tool for creating keys/certs, that comes with the JDK.
- jarsigner Java tool for signing JAR/APK files, that comes with the JDK.
We can use,
apktool b application
After recompiling (building) the apk the new apk will be generated in the Dist folder.
Application -- Dist- application.apk
The APK must be signed before you run on your device.
Before signing an apk, create a key if you don’t have an existing one. If prompted for a password, create your own password.-
To generate a key
keytool -genkey -v -keystore my-release-key.keystore -alias alias_name \ -keyalg RSA -keysize 2048 -validity 10000
-
Sign the apk
Now sign the APK with the key:jarsigner -verbose my-release-key.keystore my_application.apk alias_name
-
Verify apk
jarsigner -verify -verbose -certs my_application.apk