draw.per - THCon 2021
Draw APK - THCon 2021
- 14 solves
- 249 points
First steps
As the challenge creator tells me this app is “based on a Trojan Horse” and it is “not recommended to install it on a real smartphone”, even if there is actually “no malicious payload”, I am very reluctant at first to test the app, even in an emulator.
So, I start off with my favorite static analysis combination: DroidLysis and JEB. The results are disappointing, I spot several “suspicious” parts (use of com.andrognito
for example) but they are False Positives.
Dexcalibur and Zip
I decide therefore to run the app in an Android emulator, instrumented with Dexcalibur. I use the default set of hooks, and spawn the app. Nothing important happens until I click on the Settings menu. There, I notice the creation of a files.zip
.
I find this suspicious: apart if configuration elements are zipped (but why? storing them in shared preferences seems easier), I see no reason why the app would need to create a Zip file.
I retrieve the zip file via ADB. It contains:
- ExtClass.enc: this file is obviously encrypted
- inf.enc: same, encrypted.
- theme.jpg: this file is a … PNG image. I don’t know why eog (Eye of Gnome) refuses to open it, but Gimp has no problem to open it.
It says we have been pwned. So, I am obviously in the right direction :)
Dexcalibur and Dex
Then, I notice in Dexcalibur that a Dalvik Executable is loaded (highly suspicious):
I grab the DEX via ADB. It is a valid DEX file, that I immediately decompile. The code is simple, with a single class ExtClass
, and methods such as isInfected()
: exactly what I expect in a challenge.
ExtClass code
The image of the Zip is used by the method changeWallpaper()
. It sets it as wallpaper.
|
|
I am interested in method checkInf()
, which decrypts inf.enc
file. As this file is small (48 bytes), it could very well hold the encrypted flag.
|
|
I write the matching standalone Java code, but when I run it, it fails with no available provider for AES_256/CBC/PKCS7Padding.
How to lose time, silly
At this point thinking that if my computer does not have this provider, for sure Android phones and emulators have it, so I am going to hook the decryption method doFinal
and display the decrypted text.
I hook doFinal
and ensure that it displays the decrypted result (ret
).
Then, I spawn the malware (note each time, I have to uninstall it and re-install it, to run it clean):
I considered hooking directly checkInf()
, except I can’t with Dexcalibur because it is from dynamically loaded code and Dexcalibur does not find it. It is possible to write a Frida hook instead (without using Dexcalibur), but I’m lazy and don’t do it.
So, I get the result of the decrypted text and re-build the file… except this is useless, because those bytes are not from inf.enc
but the decrypted value of ExtClass.enc
!
And unfortunately, I register no other call to doFinal()
for inf.enc
… Dead end.
Back on track
I consider my Java decryption code and search on Internet why it does not find a provider for this algorithm and where I can find one.
I bump into this page which says that PKCS7 padding is not supported by Java, only PKCS5 (naming issue see the stackoverflow page). So, I simply change PKCS7 padding to PKCS5 in my code.
|
|
Solution
Bingo.
|
|
How does it work?
When the end-user selects Settings, this starts SettingsActivity
.
At some point, this calls method invoke
on the SettingsActivity
.
This calls a method named executePayload
.
|
|
This method:
- Retrieves external files via
loadServerFiles()
. This downloadsfiles.zip
from a Google Drive. Then, it unzips the file and decrypts the DEX. Note the secret key and IV are different from the one used to decryptinf.enc
. - Checks the integrity of the external DEX. This consists in checking the SHA256 hash against the expected one.
- Calls
executePayload.1
. This will load the DEX (withPathClassLoader
, something I did not detect with DroidLysis at the time of the challenge), callinitLib
from the dynamic class, check if the smartphone is infected withisInfected
and finally modify the wallpaper.