Multidex trick to unpack Android/BianLian
This article explains how to unpack sample sha256
5b9049c392eaf83b12b98419f14ece1b00042592b003a17e4e6f0fb466281368 which was served from http://videofullizlesite9356[.]site/ApiServices-Files92752/Down at the beginning of January 2022 (see this tweet). The malware poses as a Video player and appears to be a member of the Bian Lian malware family (see former analysis 1 and 2). Although the malware has similarities with BankBot, I believe this precise sample is not a banker malware (it does not attempt to steal your banking credentials or steal from your bank account) but the Bian Lian bot (bulk send of SMS, USSD calls etc).
Update Jan 17, 2022. Let’s try and clarify. Bian Lian is a “generic” bot. It may be used to steal passwords of banking apps. Some current samples seem to be particularly interested in stealing credentials from turkish banks.
Kudos to @U039b with whom I began this reverse engineering, and @ReBensk, @malwrhunterteam.
Summary (spoiler?) for those who don’t want to read it all :)
The malware does not use
DexClassLoaderto unpack the payload DEX. Instead it loads the payload as a secondary DEX through multidex support. The packer re-implements multidex support and mainly changes names & adds asset decryption.
You can use my Java program to decrypt the asset and access the payload.
What makes this sample difficult to unpack
The most common packing mechanism consists in loading a hidden DEX with
DexClassLoader. The sample does not use
InMemoryDexClassLoader). Therefore, we cannot unpack by creating a hook on
DexClassLoader that dumps its first file argument.
This malware uses another mechanism to side load its payload. I’ll discuss at the end of the article (section “So, how is the DEX loaded if not with DexClassLoader?”). But first, let’s unpack, because actually if your goal is to analyze the payload, you don’t really need to understand how it is loaded.
Detecting it is packed
The main activity is
com.pmmynubv.nommztx.MainActivity, which is not present in the wrapping APK but in the contained payload.
Understanding the packing mechanism takes a little bit of time, because all strings are obfuscated (fortunately JEB decrypts nearly all of them) and
DexClassLoader — typically to load a DEX — is not used.
The flow is the following. The manifest references
com.brazzers.naughty.g as the application. Indeed,
Application and can be seen as the main entry point of the app. One of the first methods to be called is the protected method
attachBaseContext, the malware calls a cascade of functions which (1) locate an asset named
G9ugwFtlG1.jwi, (2) deflates it and (3) finally decrypts it using a home-made algorithm with hard coded key
G9ugwFtlG1, .jwi, GIUh9JHGUIGIUHGokfewrofij58YV6UhYUF7gjhgv are found in a malware’s configuration class com.brazzers.naughty.h, but note they are all obfuscated.
The obfuscation is not complex: a XOR with a fixed character, nevertheless I was happy JEB did the work automatically for me!
If you want to follow the calls:
- com.brazzers.naughty.a.a(Context, File, File…)
- com.brazzers.naughty.b.a(Context, String…)
- com.brazzers.naughty.b.a(ZipFile, ZipEntry…)
- com.brazzers.naughty.k.a(String, InputStream, OutputStream)
We’ll see later the malware is actually following the normal flow for loading secondary DEXes, except the names are obfuscated.
Automating the unpacking
I basically copied the malware’s unpacking code in
com.brazzers.naughty.k.a, did a little adaptation, and finally worked out a Java program that automatically unpacks the malware (get the code here). Run the program in the directory where
G9ugwFtIG1.jwi is available (
./assets/7G8Uwty), and it will unpack and create a
unpacked.zip which contains the payload DEX.
$ unzip -l unpacked.zip
Length Date Time Name
--------- ---------- ----- ----
906456 2022-01-14 11:05 classes.dex
906456 1 file
So, how is the DEX loaded if not with DexClassLoader?
The malware uses the multidex scheme to load the payload as secondary DEX. This method has existed for a couple of years (e.g. Android/Rootnik using it in 2017), but I hadn’t seen it for a while. In 2022, it seems we have a new packer in the wild which uses this technique as the same packer is used here in a sample of Flubot.
The technique consists in re-writing the way applications load multiple DEX. The Android code can be found here. The classes
MultiDexApplication are the core of the functionality. They implement support of APKs with multiple DEX. Everything begins in indeed in
MultiDexApplication.The malware re-implements
MultiDexExtractor with little changes part code re-organization and obfuscated names:
MultiDexApplicationis found in
MultiDexis within in
The two main functional changes are :
- Changes in file and folder names. The extracted DEX will be located in a directory named
hf8U6UUIwiqaGgoinstead of the standard
secondary-dexesname, the extracted suffix will be
.zip, and some other minor details like the lock file name is changed to
MultiDex.lock. The goal is obviously to complicate reverse engineering, but also to make the files less noticeable should they be spotted during extraction on the device.
- Deflating and decryption of the secondary DEXes. Compare the original code with the malware’s version below.
The next article will deal with the reverse engineering of the payload DEX.
More recent samples of January 14 (today)
Some newer samples of that malicious video application have been released today: see Twitter. I haven’t looked in all samples yet, but at least the first one, 01658_Video_Oynatıcı.apk (sha256:
d105764cd5383acacd463517691a0a7578847a8174664fc2c1da5efd8a30719d) does not use the same packer. It uses the common
DexClassLoader method, actually the same packing mechanism as this sample. Watch for the unpacked payload in a file named
generic_x86_64:/data/data/com.friend.bronze/app_DynamicOptDex # ls
The payload DEX (
maXclr.json) is a Bian Lian sample.
— the Crypto Girl