Juicy Bar CTF - Dynamic Code Analysis
In this post, we’ll walk through the solutions for all four dynamic analysis challenges. I followed the official Frida Android tutorial (https://frida.re/docs/android/) to set up Frida before starting the challenge.
Meet with Frida
1 - Description
2 - Obtaining 1st Flag
Obtaining the first flag was straightforward. I created a Frida script to hook the target function and print its return value, which revealed the flag.
3 - Obtaining 2nd Flag
The second flag was more challenging, involving checks on a static member, return value, and class member variables. To bypass this, I developed a Frida script that dynamically modified the return value and member variables at runtime, which allowed me to retrieve the flag.
4 - Obtaining 3rd Flag
The third flag involved verifying that the value of UUID.randomUUID().toString() was a specific, non-random UUID. I wrote a script to hook the UUID.toString() method directly, capture its output, and successfully retrieve the flag.
Obfuscated Secrets
1 - Description
2 - Obtaining Flag
The obfuscated secrets challenge was trickier due to its heavily obfuscated encryption function. To be honest, I leveraged ChatGPT to analyze and understand the function. Once I had a clear picture, I developed a hook script to capture the IV, key, and the encrypted/decrypted values during runtime.
The code output indicated that the decrypted message was “check IV and key,” which resembled hex values. When I converted those hex values to ASCII, I successfully obtained the flag.
Brute Force
1 - Description
2 - Obtaining Flag
The brute force challenge was straightforward. I wrote a Frida script that instantiates the target class and calls the getFlag method with values from 0000 to 9999 inside a try-catch block. If no error occurred, the input was the correct PIN, and the flag was revealed.
Time Your Attack
1 - Description
2 - Obtaining Flag
The “Time Your Attack” challenge was very difficult. I relied on ChatGPT to help me understand the partially decompiled code, which included a significant amount of assembly instructions that made analysis challenging.
After analyzing the decompiled function, I realized it verifies the 10-digit PIN one digit at a time. If a digit is correct, the function takes longer to respond, allowing a timing attack to deduce the PIN step by step.
I then created a script that exploited this timing behavior to brute force the PIN. Due to noisy output, I collected 200 samples per digit to accurately measure the response time and reliably identify each correct digit.