CVE-2026-20253: Splunk Enterprise Unauthenticated File Write Endpoint
Updated August 12, 2026 · Written by PWNMI — see About.
Splunk Enterprise is a real, widely-deployed log-aggregation and analytics platform — not a toy target, and CVE-2026-20253 is a good example of how an internal service bundled into a much larger product can quietly widen its attack surface. The bug lives in Splunk's PostgreSQL Sidecar Service, reachable through splunkd's own raw REST passthrough at <host>/<region>/splunkd/__raw/v1/postgres/recovery/backup — an endpoint that responds to an unauthenticated request instead of rejecting it outright. CVSS 9.8 (network, no auth, no user interaction). Affects Splunk Enterprise 10.2.0–10.2.3 and 10.0.0–10.0.6; fixed in 10.0.7, 10.2.4, and 10.4.0 (advisory SVD-2026-0603). Detection tooling and the exact vulnerable path from watchtowrlabs/watchTowr-vs-Splunk-CVE-2026-20253.
What you'll practice: reading a detection PoC's exact vulnerable-vs-patched signature instead of assuming "got a response" means "vulnerable," standing up a real enterprise product from its own official image and finding a REST passthrough path that isn't in the public advisory text, and being honest about the difference between confirming a bug is reachable and confirming its full impact — a distinction this lab can't fully collapse, and shouldn't pretend to.
Set up the lab
New to Docker or git, or unsure what the commands below are actually doing? See Docker for Security Labs and Git for Security Work first.
Get the lab files from pwnmihq/resources:
git clone --filter=blob:none --sparse https://github.com/pwnmihq/resources
cd resources
git sparse-checkout set cve-labs/CVE-2026-20253
cd cve-labs/CVE-2026-20253
docker compose up -d
Splunk's container has its own healthcheck, and it takes a while — roughly 60–90 seconds for Ansible-driven provisioning to finish and the management port to come up. Poll until it reports healthy before moving on:
docker compose ps
Once it's healthy, capture the container and its IP:
CONTAINER=$(docker compose ps -q target)
IP=$(docker inspect $CONTAINER --format '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}')
Splunk Web listens on port 8000 — plain HTTP by default in this image, not HTTPS.
Understanding the vulnerability
Per Splunk's own advisory, the PostgreSQL Sidecar Service endpoint accepts requests without properly enforcing authentication first — a request reaches the handler and gets processed before any credential check would normally reject it. The endpoint's job is a recovery/backup operation against Splunk's internal PostgreSQL component; reachable pre-auth, that's a network attacker directing a file-creation/truncation operation without ever proving who they are, which is exactly what a 9.8 network/no-auth/no-user-interaction score describes.
What this lab actually confirms — and what it deliberately doesn't — matters here. The public detection tooling checks for a specific response signature that only a vulnerable build produces, not the file write itself. That's still real, meaningful signal: a patched instance behaves differently at exactly this step, before any file operation would occur. It's not the same claim as "watched a file get created," and this walkthrough won't pretend otherwise.
Exploitation
Confirm the endpoint responds at all — a dummy Basic auth header is enough, since the vulnerable behavior happens before any credential is actually checked:
curl -X POST -H "Authorization: Basic ZGFnOg==" http://$IP:8000/en-US/splunkd/__raw/v1/postgres/recovery/backup
A vulnerable build returns HTTP 400 with the body Failed to decode request. A patched build returns 401 instead — the request never gets far enough to produce that specific error, because auth is actually enforced first.
Now run the researcher's own detection tool against the target, rather than hand-rolling the same check:
git clone https://github.com/watchtowrlabs/watchTowr-vs-Splunk-CVE-2026-20253
cd watchTowr-vs-Splunk-CVE-2026-20253
python3 watchTowr-vs-Splunk-CVE-2026-20253.py -H http://$IP:8000 -r en-US
[+] VULNERABLE - access to /v1/postgres/recovery/backup not blocked
Stop here and be precise about what that output means. It confirms the endpoint is reachable pre-auth and produces the exact signature the researcher identified as distinguishing a vulnerable build from a patched one — genuine, specific, verifiable signal, not a guess. It does not confirm the underlying arbitrary file creation/truncation primitive actually firing; the tool is explicit in its own README that "no exploitation attempts are performed by this script." Treat a detection oracle's confirmed signature as real evidence of the bug's presence — because it is — without inflating it into a claim of full exploitation you didn't actually perform.
Cleanup
Nothing to clean up. The detection tool used here is read-only against the target — no file was written, no state was changed on the Splunk instance beyond normal request logging. Tear the lab down when you're done:
docker compose down -v
Lessons worth keeping
- A detection oracle is real evidence, not a placeholder for real evidence. A response signature that only a vulnerable build produces is genuine confirmation of the bug's presence, even when the researcher's own tooling deliberately stops short of triggering the full impact. Don't discount it, and don't overstate it into something it isn't either.
- Enterprise products bundle services you didn't sign up to think about. A log-analytics platform shipping an internal PostgreSQL sidecar, reachable through the product's own REST passthrough, is exactly the kind of attack surface that doesn't show up if you only reason about "what Splunk is for."
- A CVSS score describes severity, not what you personally verified. 9.8 is Splunk's and the CVE record's own assessment of impact if fully exploited. What this lab walkthrough actually demonstrated is narrower than that, and saying so plainly is more useful than borrowing the score's authority for a claim this specific pass didn't earn.
Next step
For another real, CVSS-critical, pre-auth network bug verified with the same discipline, see CVE-2026-34197 (Apache ActiveMQ). For more on the curl invocations used to probe the raw endpoint here, see the curl cheat sheet.
Get new write-ups in your inbox
New roadmaps, tool walkthroughs, and lab write-ups. No spam. Unsubscribe anytime.