# A Tale of Two Formats: Exploiting Insecure XML and ZIP File Parsers to Create a Web Shell

Custom .xyz ZIP+XML package upload parsed with unsafe defaults allowed XXE file read and Zip Slip overwrite of a JSP template, yielding a web shell.

- Payout: Research
- Severity: critical
- Program: vulnapp.com
- Write-up by: Eugene Lim
- Disclosed: 2020-02-18
- Write-up quality: 7/10
- Original: https://spaceraccoon.dev/a-tale-of-two-formats-exploiting-insecure-xml-and-zip-file-parsers-to-create-a/
- Library page: https://bugbountylibrary.com/r/blog%3Aspaceraccoon-dev-a-tale-of-two-formats-exploiting-insecure-xml-and-zip-file-parsers-to-create-a
- Tags: area:web domain:web impact:data-leak impact:rce kind:research platform:research sev:critical tech:java technique:chained vuln:file-upload vuln:path-traversal vuln:xxe

**Target:** File upload endpoint processing custom .xyz ZIP/XML packages
**Root cause:** Java XML parser had external entities enabled by default, and the ZIP extraction routine did not sanitize entry filenames, allowing traversal outside the temp directory.
**Steps:**
1. Upload a .xyz ZIP containing manifest.xml with `<!DOCTYPE title [<!ENTITY xxe SYSTEM 'file:///etc/hosts'>]>` and `&xxe;` in title; observe file contents reflected.
2. Use directory external entities like `file:///home/web/resources/templates` to enumerate the filesystem.
3. Identify `/home/web/resources/templates/sitemap.jsp` matching the live `/sitemap` page.
4. Use evilarc to build a ZIP entry named `../../../../../../home/web/resources/templates/sitemap.jsp` containing original sitemap content plus a JSP web shell gated by a secret query param.
5. Upload package, refresh `/sitemap?spaceraccooon=ls` (cache initially served stale page) until shell executes.
**How found:** Recognized .xyz as a ZIP+XML manifest format, tested XSS first (sanitized), then XXE. Remote entity failed (likely egress firewall), so retried with local file entity and got /etc/hosts reflected; then probed the ZIP extraction step for traversal.
**Exploitation:** Attacker uploads a crafted package; the server unzips it, overwriting a JSP template in the web root with a web shell, then requests the page with a secret parameter to run commands as the web user.
**Escalation:** XXE directory listing was used to locate a writable template path, chaining file-read into arbitrary file write and RCE.
**Insight:** When a remote XXE entity fails, don't conclude XXE is blocked—retry with local file and directory entities; directory entities (`file:///path`) enumerate filesystem layout to find writable web-root paths for a Zip Slip overwrite.
