Intentional Exercise – Hacker101 CTF – @lautarovculic

Difficulty: Moderate

Skills: Android

Flags: 1

Flag 1/1

First, we need wait until the APK is building.

Download the .APK file.

Decompile the .APK with apktool

				
					apktool d level13.apk
				
			
  • The target SDK is 28 (Android 9.0).

Then, install the APK with ADB to our Android Device, I use Genymotion.

				
					adb install level13.apk
				
			

Open the app and

🤔🤔🤔🤔🤔🤔🤔🤔🤔🤔

So let’s order this..

When the App is open, we see an WebView:

				
					/appRoot?&hash=61f4518d844a9bd27bb971e55a23cd6cf3a9f5ef7f46285461cf6cf135918a1a
				
			

And if we click on “Flag”, we will redirect to:

				
					/appRoot/flagBearer
				
			

And an Invalid request message.

So this made me think that the key is the URL.

Well.. let’s inspect the Java source code. With jadx-gui

Note: URL is your private Hacker101 instance.

MainActivity.java > onCreate

				
					public void onCreate(Bundle bundle) {
        super.onCreate(bundle);
        setContentView(R.layout.activity_main);
        WebView webView = (WebView) findViewById(R.id.webview);
        webView.setWebViewClient(new WebViewClient());
        Uri data = getIntent().getData();
        String str = "https://URL.ctf.hacker101.com/appRoot";
        String str2 = BuildConfig.FLAVOR;
        if (data != null) {
            str2 = data.toString().substring(28);
            str = "https://URL.ctf.hacker101.com/appRoot" + str2;
        }
        if (!str.contains("?")) {
            str = str + "?";
        }
        try {
            MessageDigest messageDigest = MessageDigest.getInstance("SHA-256");
            messageDigest.update("s00p3rs3cr3tk3y".getBytes(StandardCharsets.UTF_8));
            messageDigest.update(str2.getBytes(StandardCharsets.UTF_8));
            webView.loadUrl(str + "&hash=" + String.format("%064x", new BigInteger(1, messageDigest.digest())));
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
    }
				
			

Looking and analyzing the code, I my head this is:

				
					str = https://URL.ctf.hacker101.com/appRoot
				
			

We can assume that str + str2 is:

				
					https://URL.ctf.hacker101.com/appRoot/flagBearer 
				
			

Because:

				
					if (data != null) {
            str2 = data.toString().substring(28);
            str = "https://URL.ctf.hacker101.com/appRoot" + str2;
        }
				
			

And then:

				
					if (!str.contains("?")) {
            str = str + "?";
        }
				
			

If https://URL.ctf.hacker101.com/appRoot/flagBearer no contains “?” then, add it.

Until now, we have:

				
					https://URL.ctf.hacker101.com/appRoot/flagBearer?
				
			

And in the end, we have:

				
					try {
            MessageDigest messageDigest = MessageDigest.getInstance("SHA-256");
            messageDigest.update("s00p3rs3cr3tk3y".getBytes(StandardCharsets.UTF_8));
            messageDigest.update(str2.getBytes(StandardCharsets.UTF_8));
            webView.loadUrl(str + "&hash=" + String.format("%064x", new BigInteger(1, messageDigest.digest())));
        } catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
        }
				
			

So, now the value of the URL is:

				
					https://URL.ctf.hacker101.com/appRoot/flagBearer?&hash=
				
			

We have the MessageDigest instance, that use SHA-256

In first place, is s00p3rs3cr3tk3y

That in SHA-256 is

				
					61f4518d844a9bd27bb971e55a23cd6cf3a9f5ef7f46285461cf6cf135918a1a
				
			

(Remember the first URL)

But the messageDigest is update with the str2 value, that is /flagBearer

Then, this is the “key”:

				
					s00p3rs3cr3tk3y/flagBearer
				
			

The SHA-256 can be calculated with this script that I made:

				
					import hashlib

# key
key = "s00p3rs3cr3tk3y/flagBearer"

# get SHA-256
hash_sha256 = hashlib.sha256(key.encode()).hexdigest()

# print
print("[*] The hash is:", hash_sha256)
print("--------------------------------------------------------------------")
print("Then, the final URL is: https://URL.ctf.hacker101.com/appRoot/flagBearer?&hash=" + hash_sha256)
				
			

Then, the final URL is

				
					https://URL.ctf.hacker101.com/appRoot/flagBearer?&hash=<HASH>
				
			

At this point you can check your desktop browser to get the flag. But we can try “fix” the App (or try get the Flag easily).

In the MainActivity.smali code, we can replace the first URL (When the WebView is created/loaded).

				
					 .line 24
    invoke-virtual {v0}, Landroid/content/Intent;->getData()Landroid/net/Uri;

    move-result-object v0

    const-string v1, "https://URL.ctf.hacker101.com/appRoot"

    const-string v2, ""

    if-eqz v0, :cond_0

    .line 28
				
			

At the line 55 of the file, we can replace *https://URL.ctf.hacker101.com/appRoot*

to

https://URL.ctf.hacker101.com/appRoot/flagBearer?&hash=HASH

Then build and sign the new .APK and remove the old App, then install.

				
					apktool b level13
				
			
				
					apksigner sign --ks name.keystore --ks-key-alias alias --out apk.apk level13/dist/level13.apk
				
			
				
					adb install apk.apk
				
			

And here is:

I hope you found it useful (:

Leave a Reply

Your email address will not be published. Required fields are marked *