记一次VMware的崩溃调试分析过程

颁布功夫 2020-08-11

1.钻研布景


VMware Workstation是一款主流的虚构机软件,近期宝运莱官方网站ADLab安全钻研员在使用VMware虚构机的过程中遇到虚构机异常崩溃的问题,当从7zip中直接将文件拖拽到VMware虚构机中,会造成虚构机异常关关。目前已测试过VMware 15.5.0、15.5.2、15.5.5 以及7zip 19.0、20.02等版本。本文将通过对VMware和7zip法式进行跟踪分析,最终定位虚构机异常关关原因。

2.VMware端调试分析

使用WinDbg-I指令将WinDbg设置为即时调试器,VMware-vmx.exe法式崩溃后自动弹出WinDbg。仓库信息如下:


640?wx_fmt=png


调试信息显示stack buffer overrun异常,最初揣度可能是缓冲区溢露马脚。


640?wx_fmt=png


通过查问资料后发现,从Windows 8起头,Windows设计了一个新的中断INT 29H,用以急剧抛出失败,在sdk中被申明为__fastfail, __fastfail内部函数不会返回。


系统结构
指令
代码参数的地位
x86
int 0x29
ecx
x64
int 0x29
rcx
ARM
操作码 0xDEFB
r0


在上图中,法式终止于int 29h,而它的参数为0xa,对应FAST_FAIL_GUARD_ICALL_CHECK_FAILURE,由此揣度问题可能呈此刻CFG的查抄过程中。


640?wx_fmt=png


从函数挪用栈中vmware_vmx+0x58b21地址向上追忆,动态调试法式,比力法式正常运行与异常崩溃的函数挪用区别,定位到与法式崩溃有关的函数sub_1400965A0。


使用Windbg Attach vmware-vmx.exe法式,在sub_1400965A0函数设置断点,起头动态调试。从7z打开的压缩文件中拖拽cdp.pcapng的文件,法式在断点处停下。通过动态调试可知该函数中calloc分配了三个堆空间,别离用于存放:主机一时文件蹊径temp_path、指标文件名file_name以及VMware中的缓存目录名vm_cache_dir_name。


640?wx_fmt=png


但是打开主机Temp目录下却没有发现该文件,因而初步判定这是法式崩溃原因。持续往下看,3个文件有关参数全都传入了sub_140579b30函数。


640?wx_fmt=png


进入函数sub_140579b30,定位temp_path参数的处置。其中,sub_14057FF90函数对传入的temp_path进行了逐一遍历,sub_1405B2080函数对传入的temp_path进行了犯法性查抄。下面沉点分析sub_140576460函数。


640?wx_fmt=png


sub_140576460函数将蹊径参数temp_path传入了sub_14049DA50。


640?wx_fmt=png


首先,函数sub_14049DA50通过sub_140477C70对字符串进行了处置。而后,挪用wstat64获取相应蹊径的文件状态,若是成功获取则保留到一个结构体中,不然返回0xffffffff。由于Temp目录下并未发现备份文件,导致获取状态失败,从而返回0xffffffff。


640?wx_fmt=png

640?wx_fmt=png


返回0xffffffff后,沉新回到sub_140579b30函数中,法式跳出while循环达到如下地位,输出谬误信息并跳转至sub_140572A70。


640?wx_fmt=png


从sub_140572A70最终执行到sub_1400960C0,达到如下地位将vmware_vmx+0xb1ed90处的值赋给了rsi,即为0。


640?wx_fmt=png


持续往下执行,将rsi中0值赋值到rax中,而后挪用0x7ff8fab0c510处,即ntdll!LdrpDispatchUserCallTarget。


640?wx_fmt=png


此处与静态下的过程有一点分歧,静态下该处挪用如下:


640?wx_fmt=png


若是依照静态过程执行,该当达到sub_1407C7650,即如下地位:


640?wx_fmt=png

在ntdll.dll被加载之前,该处数据仍旧为上图所示地址:


640?wx_fmt=png


后来在ntdll.dll中执行CFG(ControlFlowGuard)� ;せ�,将vmware_vmx+0x7c9668地址处数据进行了改写,从而执行到ntdll!LdrpDispatchUserCallTarget中。


640?wx_fmt=png


在ntdll!LdrpDispatchUserCallTarget函数中,取r11+r10*8处的值赋值给r11时出现了问题,该地址为空,就造成了空指针引用,从而执行了int 29h,造成异常。然而,即便没有CFG机造,法式也会在执杏装jmp rax”处崩溃,通过下图能够看出,CFG机造仅仅是在正本法式跳转指令前增长了一些查抄。


640?wx_fmt=png

640?wx_fmt=png


至此,VMware崩溃的原因根本分析分了然。另一个疑难是,为什么7zip已经在系统Temp下天生了文件,并且VMware也已经获取到了蹊径参数,却在移动前自动删除了文件呢。这就必要从7zip中寻找答案。


3.7zip端调试分析

由上一节分析可知,Vmware crash原因是Temp目录下文件被删除。阅读7zip源码,锁定了CPP/Windows/FileDir.cpp中的文件删除函数。


640?wx_fmt=png


使用WinDbg加载7zip,而后在Remove函数地位进行下断,法式运行后进行拖拽操作,在Remove函数中断后对应的挪用仓库如下所示。


640?wx_fmt=png


仓库中7zFM+0x5b212地址位于函数CPanel::OnDrag中,该函数为鼠标拖拽操作函数。当检测到对7zip打开的目录进行操作时,便会在Temp目录下天生一个以7zE开头的随机定名文件夹。


640?wx_fmt=png


而后,将该文件夹设置为指标目录,并且设置了一些数据及IpDropSourse结构体。


640?wx_fmt=png


持续往下能够看到一个DoDragDrop函数,该函数职能是进行OLE拖放有关操作,通过检测光标的行为别离挪用一些步骤并返回对应的数值。


640?wx_fmt=png


而后,凭据DoDragDrop函数的返回致反判断光标的拖拽是否有效,从而执行对应的操作。


640?wx_fmt=png


从7zip中拖拽文件到虚构机,由于无法获知文件拖拽的指标蹊径,因而DoDragDrop会返回DRAGDROP_S_CANCEL(0x40101),不会执行拷贝操作的分支,而是直接将Temp目录下天生的一时目录删除。


640?wx_fmt=png


4.幼 结


7zip压缩包中文件拖拽操作会触发DoDragDrop函数挪用,该函数会获取文件数据及光标终场的地位。但是将文件拖拽到VMware窗口时,DoDragDrop函数不能获取正确的指标蹊径,因而无法将文件拷贝到指标地位,从而直接删除一时文件,最终导致VMware无法获取文件状态造成崩溃。


参考链接:

[1]https://0cch.com/2016/12/13/int29h/

[2]https://docs.microsoft.com/en-us/windows/win32/api/ole2/nf-ole2-dodragdrop

[3]https://github.com/kornelski/7z/tree/20e38032e62bd6bb3a176d51bce0558b16dd51e2



宝运莱官方网站积极防御尝试室(ADLab)


ADLab成立于1999年,是中国安全行业最早成立的攻防技术钻研尝试室之一,微软MAPP打算主题成员,“黑雀攻击”概想首推者。截止目前,ADLab已通过CVE累计颁布安全缝隙近1100个,通过 CNVD/CNNVD累计颁布安全缝隙900余个,持续维持国际网络安全领域一流水准。尝试室钻研方向涵盖操作系统与利用系统安全钻延注移动智能终端安全钻延注物联网智能设备安全钻延注Web安全钻延注工控系统安全钻延注云安全钻研。钻研成就利用于产品主题技术钻延注国度沉点科技项目攻关、专业安全服务等。


lab.jpg