SOAP WSDL and XXE: Hunting Legacy XML Bugs for Bounty
SOAP stacks age poorly in public bug bounty scopes. A forgotten ?wsdl link still describes operations, types, and sometimes internal hostnames. The parser behind those operations may still expand XML external entities even when the rest of the company moved to JSON.
You are hunting two things: a map, and a parser that trusts too much.
Start with the contract
Request likely WSDL and discovery paths: /service?wsdl, /soap/app?wsdl, *.asmx?WSDL, and gateway routes that still advertise text/xml. Save the WSDL. Note SOAP actions, bindings, and whether the document embeds or imports other schemas.
Imports are interesting for SSRF-shaped follow-ups later, but XXE usually lives in the request body the endpoint accepts. Generate or capture a valid SOAP envelope for a low-risk operation—something like a version check or a read of your own record. If schemaLocation points at a remote host influenced by admin config, park that as a possible SSRF note and finish the body test first.
Probe entities without collateral damage
Classic XXE inserts a DOCTYPE with an external entity and references it in a field the server reflects or stores:
<?xml version="1.0"?>
<!DOCTYPE foo [
<!ENTITY xxe SYSTEM "file:///etc/hostname">
]>
Prefer out-of-band detection when local file read is uncertain. Point an entity at a collaborator URL you control and watch for a DNS or HTTP hit. That proves the parser fetched attacker-controlled content. Do not request cloud metadata URLs or internal admin panels on shared production networks unless the program explicitly allows it and you keep the blast radius tiny.
Parameter entity tricks and UTF-16 / charset confusions still appear on older Java and .NET XML stacks. Change one variable at a time. Keep the SOAPAction and Content-Type close to a legitimate client so you are testing the XML parser, not an unrelated gateway rejection.
MTOM attachments deserve a pass. A binary part might skip text-entity checks while a sibling XML part still expands DTDs. Test the XML piece even when the operation expects a file.
Prove impact with owned data
A collaborator ping alone may land as medium depending on policy. Stronger proofs show a returned file fragment from a harmless path, or entity expansion that injects your canary string into a SOAP fault or business field. Blind XXE that only hits your listener still demonstrates server-side fetch capability—describe the trust boundary clearly.
Watch for second-order XXE: an upload of XML that is parsed later by a backend worker. Those are easy to miss if you only test the synchronous HTTP response.
Reporting and remediation
Include the WSDL URL, the exact SOAP operation, the entity payload with secrets redacted, and evidence of fetch or disclosure. State parser family if you know it from headers or stack traces.
Fixes: disable DTDs and external entities in the XML parser, reject unexpected DOCTYPE declarations, keep WSDL off the public internet or behind the same auth as the service, and prefer JSON endpoints where the business allows. CWE-611 is the short name triage already understands.
Legacy XML is not exotic anymore. It is simply easy to forget. Your job is a safe entity probe and a sentence that says what the server fetched for you.