Android Security Findings

Accessing application /data/data without root

Case 1:

If the app is debug-able you could do:

$ adb shell
$ run-as <app-package-id>
$ cat /data/data/<app-package-id>/shared_prefs/prefs.xml

Run grep " 1 /" /data/system/packages.list to list all debug-able apps

Case 2:

Otherwise....

$ adb backup -f ~/data.ab -noapk com.bplus.vtpay

or

adb backup "-noapk com.innogames.enterprise.elvenar"

$ java -jar abe.jar unpack ~/data.ab vtpay.tar "" (abe)

$ apps/com.bplus.vtpay/sp/vtp_shared_user_info.xml

Local Storage Attack

Devices: Android(8.1), Ubuntu PC Paper: https://www.exploit-db.com/docs/46466

POC:

  1. Using adb pull /data/data/app1/files/default.realm /mnt/sdcard/ so, we just copied the default realm file

  2. Grep for the sensitive information that we want to replace with $ strings default.realm| grep "passwd"

  3. Analyze and find its binary address $ hexdump -C default.realm For exp:

  4. Replace the binary $ sed -i "s/\x36\x61/\x35\x61/g" default.realm Or MacOS $ gsed -i "s/\x36\x61/\x35\x61/g" default.realm

The Simplest way to do this is

private void deleteAppData() {
try {
// clearing app data
String packageName = getApplicationContext().getPackageName();
Runtime runtime = Runtime.getRuntime();
runtime.exec("pm clear "+packageName);
} catch (Exception e) {
e.printStackTrace();
}
}

This will clear the data and remove your app from memory. It is equivalent to clear data option under Settings --> Application Manager --> Your App --> Clear data.

This will remove the data completely as well as force close the app

The Android platform provides a convenient way to store preferences and even big files thanks to the SharedPreferences interface. Even if the data stored in these shared preferences is hidden in a masked directory, it is possible to retrieve the data easily if the device is rooted.

Consequently, if the information stored by the application is sensitive, it might be necessary to encrypt the data stored in the shared preferences. It is possible to do so in two ways :

Use a cryptographic library to encrypt/decrypt the values (and eventually the keys) of the SharedPreferences. There are many state of the art java cryptographic library javax.crypto, Bouncycastle2 and Concealed[3] Use a library providing a SharedPreferences wrapper. These libraries are very convenient as the developer does not have to care about which algorithm has to be used. Meanwhile, using these libraries can lead to a lack of flexibility and some of them are not using safe algorithms. Consequently they may not be trust to store very sensitive data. One of the most used libraries providing this kind of wrapping feature is SecurePrefences [4]. In you choose this solution, you can instantiate a SecurePreferences extending SharedPreferences in a very straightforward way : SecurePreferences securePreferences = new SecurePreferences(context, "MyPassword", null); SecurePreferencesExample.java hosted with ❤ by GitHub These two methods are based on symmetric cypher algorithm such as AES (with an appropriate key size). It leads to wonder : which key should-we use ? Indeed if we use a static key, the preferences can be decrypted by retro-engineering the application. So, the best solution would be to use a pin-code/passphrase that the user has to type when the application starts. Another possibility is to use the Fingerprint API [15] (available since API 23) which provides a safe and fluent way to authenticate. Unfortunately this approach cannot fits every application’s user experience. For instance if we want to display some information stored before the pin code is typed, then we cannot use this secure encryption system.

Hopefully Android provides a safe way to generate a key which will be unique for each couple application/device : the KeyStore. Android KeyStore’s goal is to allow applications to put private keys in a place where they cannot be retrieved by another application or by materially accessing the data stored on the device. The mechanism is pretty simple : the first time, you run your application to check whether a private key linked to your application is present or not. If not, you generate one and you store it in the KeyStore. If the private key is already present, you can use it as a cryptographically safe key to decipher a SharedPreferences data thanks to the algorithms described above. Obaro Ogbo wrote a detailed article [11] describing in depth how to use the KeyStore to generate a Private/Public Key couple. The main drawback of the KeyStore is that it is available only since API 18. Still, there is a backport library which provides compatibility since API 14 [14] (this not an “official” backport so you have to use it at your own risk).

Consequently we can propose the following decision diagram when deciding which type of preference system we should use:

Android-Reports-and-Resources

HackerOne Reports

Hardcoded credentials

Disclosure of all uploads via hardcoded api secret

https://hackerone.com/reports/351555

RCE

RCE in TinyCards for Android

https://hackerone.com/reports/281605

Session theft

Steal user session

https://hackerone.com/reports/328486

Steal files

Token leakage due to stolen files via unprotected Activity

https://hackerone.com/reports/288955

Steal files due to exported services

https://hackerone.com/reports/258460

Steal files due to unprotected exported Activity

https://hackerone.com/reports/161710

Steal files due to insecure data storage

https://hackerone.com/reports/44727

Insecure local data storage, makes it easy to steal files

https://hackerone.com/reports/57918

Bypasses

Golden techniques to bypass host validations

https://hackerone.com/reports/431002

Two-factor authentication bypass due to vuln endpoint

https://hackerone.com/reports/202425

Another endpoint Auth bypass

https://hackerone.com/reports/205000

XSS

HTML Injection in BatterySaveArticleRenderer WebView

https://hackerone.com/reports/176065

XSS via SAMLAuthActivity

https://hackerone.com/reports/283058

XSS in ImageViewerActivity

https://hackerone.com/reports/283063

XSS via start ContentActivity

https://hackerone.com/reports/189793

XSS on Owncloud webview

https://hackerone.com/reports/87835

Privilege Escalation

Intent Spoofing

https://hackerone.com/reports/97295

Access of some not exported content providers

https://hackerone.com/reports/272044

Access protected components via intent

https://hackerone.com/reports/200427

Fragment injection

https://hackerone.com/reports/43988

Javascript injection

https://hackerone.com/reports/54631

Intercept Broadcasts

Possible to intercept broadcasts about file uploads

https://hackerone.com/reports/167481

Vulnerable exported broadcast reciever

https://hackerone.com/reports/289000

View every network request response's information

https://hackerone.com/reports/56002

Practice Apps

Android-InsecureBankv2

Vulnerable Android application for developers and security enthusiasts to learn about Android insecurities

Damn Insecure and Vulnerable app

Damn Insecure and vulnerable App for Android

OWASP-GoatDroid-Project

OWASP GoatDroid is a fully functional and self-contained training environment for educating developers and testers on Android security

Sieve mwrlabs

Sieve is a small Password Manager app created to showcase some of the common vulnerabilities found in Android applications.

Resources

OWASP top 10 2016

OWASP mobile testing guide

Android Reversing 101

Detect secret leaks in Android apps online

Android Security Guidelines

Attacking vulnerable Broadcast Recievers

Android Webview Vulnerabilities

Android reverse engineering recon

Webview addjavascriptinterface RCE

Install PLayStore On Android Emulator

Android Bug Bounty Tips