Secure APIs against XEE Attacks(XML Injection Attacks)

1 minute read

Recently while testing my REST API for invalid XML data, I found an XEE susceptibility.

XEE attacks are possible as we send xml payloads which get parsed by the parsers at runtime. Major XEE attacks can be clasified as

  1. XML Injection Attacks
  2. XML Expansion Attacks

XML Injection attacks can be made using external url or schema file references in the xml payload. One can point to an url that never returns, turning the request into a kind of DOS attack. Similarly by referencing an external file it is also possible to gain access to the files present on the server, if the file system access is not properly implemented on the same.

XML Expansion attacks, are made by using doctype references in the xml payload, which are recursive or just huge. LOL attack is a famous example of the same. An example payload can be seen as below,


<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<!DOCTYPE foo [ <!ENTITY a "1234567890" > <!ENTITY b "&a;&a;&a;&a;&a;&a;&a;&a;&a;&a;" > <!ENTITY c "&b;&b;&b;&b;&b;&b;&b;&b;&b;&b;" > <!ENTITY d "&c;&c;&c;&c;&c;&c;&c;&c;&c;&c;" > <!ENTITY e "&d;&d;&d;&d;&d;&d;&d;&d;&d;&d;" > <!ENTITY f "&e;&e;&e;&e;&e;&e;&e;&e;&e;&e;" > <!ENTITY g "&f;&f;&f;&f;&f;&f;&f;&f;&f;&f;" > <!ENTITY h "&g;&g;&g;&g;&g;&g;&g;&g;&g;&g;" > <!ENTITY i "&h;&h;&h;&h;&h;&h;&h;&h;&h;&h;" > <!ENTITY j "&i;&i;&i;&i;&i;&i;&i;&i;&i;&i;" > ]> 
<sometag xmlns="somensreference">
<data>&j;</data>
</sometag>

I found it quite peculiar to ensure that APIs are secure from these attacks.

When using RestEasy, the easiest way to do this was to write a custom rest easy content provider, implementing javax.ws.rs.ext.MessageBodyReader<Object> interface.

Then ensuring that the unmarshaller instance that gets provided to the contentprovider, has the following flags set on it.


javax.xml.parsers.SAXParserFactory factory = SAXParserFactory.newInstance();
factory.setFeature("http://xml.org/sax/features/validation", false);
factory.setFeature("http://xml.org/sax/features/namespaces", true);
factory.setFeature("http://xml.org/sax/features/external-general-entities", false);
factory.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
factory.setFeature(XMLConstants.FEATURE_SECURE_PROCESSING, true);
factory.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);

We can use the factory created above to create an XMLReader and use it to unmarshal the xml.


org.xml.sax.XMLReader reader = factory.newSAXParser().getXMLReader();
//Get the unmarshaller here
javax.xml.bind.Unmarshaller unmarshaller = getUnMarshaller();
//source- variable which get you a reference to the input xml, payload
unmarshaller.unmarshal(new SAXSource(createXmlReader(), source));

Hope that helps us secure our APIs from unwanted XML attacks.