本文翻译自:
https://blog.trendmicro.com/trendlabs-security-intelligence/use-after-free-uaf-vulnerability-cve-2018-8373-in-vbscript-engine-affects-internet-explorer-to-run-shellcode/


Trend Micro研究人员7月11日发现一个高风险IE漏洞,研究人员发送漏洞细节给微软并帮助修复了该漏洞。漏洞CVE编号为CVE-2018-8373,影响Windows最新版本的VBScript引擎,因为Windows 10 Redstone 3 (RS3)默认不启用VBScript,所以IE 11未受到影响。

研究人员发现了恶意web流量中的利用,下图是使用的恶意URL:

图1. 使用的恶意URL

研究人员该漏洞利用使用了Heuristics(启发)的思想,而且利用样本使用了与CVE-2018-8174漏洞利用相似的混淆技术,也是VBScript引擎远程代码执行漏洞。

图2. CVE-2018-8373(左)与CVE-2018-8174(右)比较

下面是样本漏洞利用使用的运行shellcode的方法:

图3. CVE-2018-8373(左)与CVE-2018-8174(右)运行shellcode方法比较

研究人员怀疑该漏洞利用样本来自于同一个创建者。研究人员分析样本发现使用了vbscript.dll的一个新的use-after-free (UAF)漏洞,该漏洞在最新的VBScript引擎中还未修复。

漏洞起源分析

研究原始的漏洞利用是经过混淆的,本文通过POC解释漏洞被利用的过程:

图4. IE漏洞PoC

PoC定义了MyClass类,其中有一个叫做array的成员变量和2个成员函数,Class_InitializeDefault Property Get PClass_Initialize是一种不建议使用的方法,现在已经被新的过程所替代。当对象初始化的时候,会被自动唤醒。在PoC中,Class_Initialize是重载的,当调用VBScriptClass::InitializeClass时,处理的是重载的函数。

默认属性是一个不需要特殊说明就开源访问的类属性。在PoC中,默认的Default Property Get函数会重载MyClass的默认属性。当调用被用来访问cls时,也会处理重载的函数。

漏洞的触发流会简化为下面三步:

1. 设置cls = New MyClass

设置会调用重载的函数Class_Initialize。在Class_Initialize中, ReDim array(2)会调用vbscript!RedimPreservearray来创建元素数是3的数组:

图5. 内存中的ReDim array(2)

2.cls.array(2)

调用vbscript!Accessarray来获取数组元素的地址。在vbscript!Accessarray中,首先会检查数组元素的索引是否越界:

图6. 检查vbscript!Accessarray中的元素索引

然后计算元素的地址,保存到栈中,并返回下面的值:

图7. 在栈中保存元素地址

3. cls.array(2)=cls

cls.array(2)=cls会调用vbscript!AssignVar来设置MyClass的默认属性值为cls.array(2)。获取MyClass的默认属性值后,会调用 Public Default Property Get P并执行Public Default Property Get P中的ReDim array(1)脚本,释放原来的`array.pvData``:

图8.释放原来的pvData

array(2)的地址仍然保存在栈中,Public Default Property Get P的返回值会访问释放的内存,并触发vbscript!AssignVar中的use-after-free (UAF)漏洞:

图9. vbscript!AssignVar中的奔溃

vbscript!Accessarray会检查数组元素索引是否越界。在获取类的默认属性值后,会差法脚本回调函数Default Property Get修改数组的长度,然后在vbscript!AssignVar中访问时就不需要检查数组的元素了。

漏洞利用分析

漏洞的利用过程可以简化为以下三个步骤:

  • 利用漏洞来修改二维数组的长度为0x0FFFFFFF
  • 实现Read/Write原语;
  • 欺骗CONTEXT结构,执行shellcode。

下面详细分析以下漏洞的利用:

1. 修改二维数组长度

首先,漏洞会定义两个数组,在下图中标记为array1array2array1就是前面PoC中描述的数组,array2是一个二维数组,其中每个元素的值都是3。

图10. 定义array2

然后使用脚本回调函数Default Property Get释放原来的array1.pvData,设置array2为新的array1.pvData。因为原来array1.pvData的大小和array2.SAFEARRAY结构是相同的,在内存中是0x30字节。一些array2.SAFEARRAY结构会服用array1.pvData释放的内存。同时,Default Property Get的返回值0x0FFFFFFFF会覆盖array2.SAFEARRAY的结构SAFEARRAYBOUND,并修改二维数组的长度为0x0FFFFFFF

图11. 定义Default Property Get

图12. 修改数组长度的步骤

2. RW原语

然后得到数组array1 (index_vuln)(0x0FFFFFFE, 2),其长度被UAF修改过了。通过索索array1的元素,可以在下面的脚本中找到index_vuln

图13. 搜索array1 (index_vuln)(0x0FFFFFFE, 2)

然后使用array1(index_vuln)(0x0FFFFFFE, 2)实现out-of-bounds (OOB),并找出2个用于类型混淆的数组元素。

图14、15. 搜索两个数组的元素

然后漏洞就得到了两个数组元素:array1(index_B)(0, 0)array1(index_vuln)(index_A, 0),在内存中的距离为8字节。在内存中搜索的完全利用如下:

图16. 在内存中搜索的方法说明

最后,使用2个数组元素来实现read and write原语:

图17. RW原语的实现

3. 运行shellcode

使用原语来泄露模块的地址:

图18. 泄露模块的地址

通过修改一些变种的VarType0x4d,并把值修改为0,可以调用vbscript!VAR::Clear,然后调用栈会修改返回地址为NtContinue的地址和假的CONTEXT结构来运行shellcode:

图19. 修改变种

图20. 运行shellcode

基于以上分析,该漏洞很容易就可以利用。而且这是今年发现的第二个VB引擎漏洞利用,因此,研究人员认为很快会有其他的VB引擎漏洞利用出现。

IoC
哈希值 (SHA256):
0d6fe137790e2ebdf4fac2dd500656f3a6f74c0d1598251929ea3558f965675f – detected as HTML_EXPLOIT.YYRV

点击收藏 | 1 关注 | 1
  • 动动手指,沙发就是你的了!
登录 后跟帖