Mr Robot Writeup (Vulnhub Intermediate Machine)
Based on the show, Mr. Robot. This VM has three keys hidden in different locations. Your goal is to find all three. Each key is progressively difficult to find. The VM isn’t too difficult. There isn’t any advanced exploitation or reverse engineering. The level is considered beginner-intermediate.
Overview
Mr. Robot is a beginner-intermediate Linux machine from Vulnhub. It’s based on the show Mr. Robot and has some cool references to it.
We start with enumeration of a Wordpress website. We discover an exposed login page and encoded credentials. Once we get into dashboard, we modify a template and gain remote access.
Next, we compromise another user by cracking his hash and getting his password. We discover that Nmap has SUID bit set on the machine, which is very insecure because of Nmap’s functionality.
We get 3 flags along the way: 1. on special website page, 2. as user flag and 3. as root flag.
Nmap scan
Starting with Nmap scan.
┌──(kali㉿kali)-[~]
└─$ sudo nmap -Pn -A 192.168.1.70 -T5
Starting Nmap 7.95 ( https://nmap.org ) at 2025-05-01 07:53 EDT
Nmap scan report for 192.168.1.70
Host is up (0.00032s latency).
Not shown: 997 filtered tcp ports (no-response)
PORT STATE SERVICE VERSION
22/tcp closed ssh
80/tcp open http Apache httpd
|_http-server-header: Apache
|_http-title: Site doesn't have a title (text/html).
443/tcp open ssl/http Apache httpd
| ssl-cert: Subject: commonName=www.example.com
| Not valid before: 2015-09-16T10:45:03
|_Not valid after: 2025-09-13T10:45:03
|_http-title: Site doesn't have a title (text/html).
|_http-server-header: Apache
MAC Address: 08:00:27:D1:27:D7 (PCS Systemtechnik/Oracle VirtualBox virtual NIC)
Aggressive OS guesses: Linux 3.10 - 4.11 (98%), Linux 3.13 - 4.4 (98%), Linux 3.16 - 4.6 (96%), Linux 3.2 - 4.14 (94%), Linux 3.8 - 3.16 (94%), Linux 4.10 (94%), Linux 3.2 - 3.8 (93%), Linux 3.16 (93%), Linux 4.4 (93%), Linux 3.13 or 4.2 (92%)
No exact OS matches for host (test conditions non-ideal).
Network Distance: 1 hop
TRACEROUTE
HOP RTT ADDRESS
1 0.31 ms 192.168.1.70
OS and Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 23.80 seconds
The Nmap scan showed 2 open ports. Port 80 for HTTP and port 443 for HTTPS Apache server. Port 22 (SSH) seems to be closed. Let’s check out the web server.
Web enumeration
When I opened the website, I saw a fancy Linux boot screen, after which I got greeted with Fsociety’s CLI-style web application. I had couple commands available, each giving me different Mr Robot experience. The website served as Fsociety’s revolution program, where anyone could join.

I ran Gobuster to perform directory fuzzing and got couple interesting results back.
┌──(kali㉿kali)-[~]
└─$ gobuster dir -u "http://192.168.1.70" -w /usr/share/wordlists/dirb/common.txt -t 64 -r
===============================================================
Gobuster v3.6
by OJ Reeves (@TheColonial) & Christian Mehlmauer (@firefart)
===============================================================
[+] Url: http://192.168.1.70
[+] Method: GET
[+] Threads: 64
[+] Wordlist: /usr/share/wordlists/dirb/common.txt
[+] Negative Status codes: 404
[+] User Agent: gobuster/3.6
[+] Follow Redirect: true
[+] Timeout: 10s
===============================================================
Starting gobuster in directory enumeration mode
===============================================================
/.htaccess (Status: 403) [Size: 218]
/.htpasswd (Status: 403) [Size: 218]
/blog (Status: 403) [Size: 214]
/dashboard (Status: 200) [Size: 2664]
/index.php (Status: 200) [Size: 1188]
/license (Status: 200) [Size: 309]
/phpmyadmin (Status: 403) [Size: 94]
/robots.txt (Status: 200) [Size: 41]
/wp-includes (Status: 403) [Size: 221]
/wp-content (Status: 200) [Size: 0]
/wp-config (Status: 200) [Size: 0]
/wp-login (Status: 200) [Size: 2664]
/wp-admin (Status: 200) [Size: 2664]
==============================================
[PLUS LOTS OF OTHER UNIMPORTANT DIRECTORIES]
==============================================
Progress: 4614 / 4615 (99.98%)
Based on the results, it’s safe to assume that we are dealing with Wordpress CMS, possibly for managing some blog on the website. Nevertheless, we should inspect all the available directories, go through their source code and look for hints and flags.
There’s “robots.txt” file, which tells web crawlers (like Googlebot) which parts of the website should or shouldn’t be indexed on the clear web. Inside, we have 2 interesting entries.

The “key-1-of-3.txt” file contains our first flag.
![]() |
first flag on page exposed by “robots.txt” |
The other “fsocity.dic” file contains a long list of words, possibly wordlist that could be helpful later.
This was the only interesting thing I could find in the discovered directories at first. Now, we should pay more attention to the Wordpress itself, as it’s often a goldmine full of misconfigurations.
When dealing with Wordpress CMS, it’s always a good idea to run WPScan, which is a tool made specifically for scanning Wordpress sites, enumerating vulnerable plugins and themes, checking for exposed config backups, database exports or brute-forcing login pages. It’s even more powerful with API token, which you get once you sign up on it’s website.
I ran WPScan, which gave me a lot of information.

It listed a few potentially vulnerable plugins, but nothing that could help me at the moment. I had to look elsewhere. Luckily, there are a lot of attack vectors when it comes to Wordpress.
Obtaining credentials for user “elliot” & logging into Wordpress
Another very well-known thing about exposed Wordpress login page is that it gives different error messages, based on if you enter a valid or invalid username. This small flaw allows us to perform username enumeration.
For this attack, I used Hydra, the online login brute-forcing tool. Hydra can brute-force lots of logins, including SSH, SMB, MySQL, HTTP and many more. The syntax is a bit weird, but nothing too bad. I used the “fsocity.dic” file I found earlier as a wordlist for usernames. It’s important to specify what text appears in the response for invalid user. After all that, I started the attack.
![]() |
Hydra discovered user “elliot” |
I let it run for some time and got one successful hit. Hydra was able to find user “elliot”.
Next, I re-ran Hydra with username “elliot” and the “rockyou” password wordlist, hoping to get valid credentials. Unfortunately, after couple minutes of waiting, I wasn’t able to get another good hit.
![]() |
cannot crack Elliot’s password |
I felt a bit stuck here. When you start to stagnate for some time like I did, it’s good to look back on all your findings, perform additional enumeration or simply take a small break. I looked back, re-checked all my findings and figured something out, which I originally missed. You may be surprised to hear that this Hydra brute-forcing I showed you above was not necessary at all.
Going back to directory enumeration with Gobuster, there were a lot of pages available. The one page that I wasn’t paying enough attention to was “/license”.

This page seemingly only contained a simple message, but there was more. You just simply need to scroll down a bit to get some invaluable information, which I missed the first time.

There was a base64 encoded string hidden at the very bottom of the page. I brought it to CyberChef and decoded the string. And I got the credentials for user “elliot” with the password.

No need for any brute-forcing BS :D.
Gaining reverse shell by modifying 404 template
I used these credentials to get onto the Wordpress dashboard.

Now, once we get inside the Wordpress dashboard, things will get far more interesting. Many things can go wrong here, like using outdated and vulnerable plugins or templates, which could lead to RCE. We can check that our user “elliot” has administrative privileges.

Probably the most common way to get RCE in Wordpress is to modify the templates for pages like 404, header, foot, stylesheet etc. This method works here as well. We can simply navigate from the menu to “Appearance→Editor” and select a template from the right. Probably the easiest one is the 404 page, which loads whenever the client requests a non-existing page.
We can test the RCE by injecting malicious code into the template. To demonstrate this, I’m gonna use the “echo” command first. To begin, I write the code to the template and save it.
![]() |
injected PHP code that prints a message |
Next, I can request any non-existent page and look into the source code of the response.
![]() |
message showed up in the response, confirming RCE |
There it is, our message made it onto the website. Now let’s get a reverse shell.
I used a simple Bash reverse shell from Pentestmonkey, wrapping it in “bash -c” just to be sure that it executes correctly.
![]() |
injected PHP code that connects back to my listener with Bash |
I set up my listener and visited a non-existing page.

And I got the reverse shell as user “daemon”.

Cracking password for user “robot”
I found myself in the directory with all the pages from the website. Now that I have read access over them, I can look at any file I want. Especially interesting one is the “wp-config.php”, which contains credentials for internal MySQL database.

You can use these to login into MySQL and dump the database. I tried it, but you’re not gonna find a lot there, just some hashed passwords for the Wordpress users, not system users.

More importantly, there is only one user named “robot” on the machine and we have a read access over his home directory, not over all his files though.
We can see 2 files there. Second flag and MD5 hash of robot’s password.
daemon@linux:/home/robot$ ls -la
ls -la
total 16
drwxr-xr-x 2 root 4096 Nov 13 2015 .
drwxr-xr-x 3 root 4096 Nov 13 2015 ..
-r-------- 1 robot 33 Nov 13 2015 key-2-of-3.txt
-rw-r--r-- 1 robot 39 Nov 13 2015 password.raw-md5
daemon@linux:/home/robot$ cat password.raw-md5
cat password.raw-md5
robot:c3fcd3d76192e4007dfb496cca67e13b
I quickly grabbed the hash and ran John the Ripper. Less than a second, and we had the password.
┌──(kali㉿kali)-[~]
└─$ john hash.txt --wordlist=Downloads/rockyou.txt --format=Raw-MD5
Using default input encoding: UTF-8
Loaded 1 password hash (Raw-MD5 [MD5 128/128 AVX 4x3])
Warning: no OpenMP support for this hash type, consider --fork=4
Press 'q' or Ctrl-C to abort, almost any other key for status
abcdefghijklmnopqrstuvwxyz (?)
1g 0:00:00:00 DONE (2025-05-02 13:58) 100.0g/s 4051Kp/s 4051Kc/s 4051KC/s bologna1..122984
Use the "--show --format=Raw-MD5" options to display all of the cracked passwords reliably
Session completed.
After that, I switched to user “robot” and entered his password. Second flag was off for grabs.
daemon@linux:/home/robot$ su robot
su robot
Password: abcdefghijklmnopqrstuvwxyz
robot@linux:~$ id
id
uid=1002(robot) gid=1002(robot) groups=1002(robot)
robot@linux:~$ ls -la
ls -la
total 16
drwxr-xr-x 2 root root 4096 Nov 13 2015 .
drwxr-xr-x 3 root root 4096 Nov 13 2015 ..
-r-------- 1 robot robot 33 Nov 13 2015 key-2-of-3.txt
-rw-r--r-- 1 robot robot 39 Nov 13 2015 password.raw-md5
robot@linux:~$ cat key-2-of-3.txt
cat key-2-of-3.txt
822c73956184f694993bede3eb39f959
Abusing SUID bit set on Nmap & getting root shell
As usual, I went down my checklist of privilege escalation techniques. Firstly, I checked what sudo permissions my user “robot” has. And there were none.
robot@linux:~$ sudo -l
sudo -l
[sudo] password for robot: abcdefghijklmnopqrstuvwxyz
Sorry, user robot may not run sudo on linux.
Another good PE vector is abusing SUID bits set on the wrong binaries. All that means is that the binary can be ran with the permissions of it’s owner. Turned out that this is the correct approach.
![]() |
Nmap has SUID bit set and can be executed as root |
Very common binaries, except for one. There was Nmap listed as well. Nmap should not have the SUID bit set, because it’s functionality allows it’s users to spawn a shell, even root shell with elevated privileges.
So I went to GTFObins, which holds various ways to exploit insecurely configured binaries. Nmap has so called interactive mode, which we can use to spawn a root shell.

We simply have to switch to the interactive mode and invoke the root shell.
![]() |
switching to interactive mode, spawning a root shell |
The third and final flag is waiting in the “/root” directory.
# cd /root
cd /root
# ls -la
ls -la
total 32
drwx------ 3 root root 4096 Nov 13 2015 .
drwxr-xr-x 22 root root 4096 Sep 16 2015 ..
-rw------- 1 root root 4058 Nov 14 2015 .bash_history
-rw-r--r-- 1 root root 3274 Sep 16 2015 .bashrc
drwx------ 2 root root 4096 Nov 13 2015 .cache
-rw-r--r-- 1 root root 0 Nov 13 2015 firstboot_done
-r-------- 1 root root 33 Nov 13 2015 key-3-of-3.txt
-rw-r--r-- 1 root root 140 Feb 20 2014 .profile
-rw------- 1 root root 1024 Sep 16 2015 .rnd
# cat key-3-of-3.txt
cat key-3-of-3.txt
04787ddef27c3dee1ee161b21670b4e4
And that’s it. Here’s the list of all collected flags:

Summary
Mr Robot is an intermediate machine from Vulnhub (or TryHackMe). This entire challenge is based on Mr Robot show, containing a lot of cool references and shots from the original series. There are 3 flags scattered throughout the machine, where the final one is in the “/root” directory. The website on this box is running Wordpress, which is a great opportunity for us to practice Wordpress exploitation, as there is a lot that could went wrong. We eventually get ourselves a pair of credentials and gain access to the dashboard. Once there, we inject malicious PHP code into 404 template (famous Wordpress vulnerability) and get a foothold. We crack an MD5 hash of another system user, compromising him. At last, we abuse insecure SUID bit set over Nmap in a way that gives us the root shell and full control over the machine. Since I love the Mr Robot show, I can appreciate all the references on this machine. Also Wordpress exploitation is always a lot of fun. I would recommend this box to anyone, who has some experience and wants to improve and sharpen his skills, perhaps even learn something new. Beginners shouldn’t be discouraged, though, because you can learn a lot about Wordpress CMS during your walkthrough, too.
Comments
Post a Comment