前言
双机调试的搭建是一个调试很有用的东西,但是检测手段也很多。而采用vmware + exdi + 一些插件的形式,完成不走windows 的kd.dll的双机调试逻辑,虽然会损失一些便利性,但是配合过vmware虚拟化的虚拟机,可以达到无视检测双机调试的目的,得益于一些开源项目的帮助,这个环境搭建起来是非常方便的。
EXDI全称是The Extended Debugging Interface (EXDI),其实就是在windbg的调试引擎和被调试者的连接中做了一层适配,常规走kdcom.dll的双机调试可以认为是windbg原生的调试通道,但是EXDI的存在,让windbg可以调试一些gdb remote的情况:
准备工作
单纯的exdi + windbg其实调试起来非常简单,但是因为没有KeDebuggerBlock那些解密的信息,所以windbg什么都不知道,模块也显示不出来,只能当个无情的单步跟踪机器。
所以需要下面的开源库:
GitHub – fly55555/ExdiGdbSrv: WinDbg-Samples ExdiGdbSrv fork 修复了一部分Vmware调试的问题
GitHub – fly55555/ExdiHelper: 对Windbg以Exdi模式下调试windows做一些修复
在本地编译之后,exdihelper是windbg的插件,主要功能是负责解密KdDebuggerDataBlock,使得windbg可以使用一些基本的调试指令,不过他这个地方!pte修的不好,ptebase是使用特征码定位的,其实可以用页表自映射找。
此外,ExdiGdbSrv编译出来有很多东西,大概是这些:
步骤
准备好刚才那两个编译完成的开源项目,打开需要调试的虚拟机的vmx,在结尾添加如下内容:
debugStub.listen.guest64 = “TRUE”
debugStub.hideBreakpoints = “TRUE”
debugStub.listen.guest64.remote = “TRUE”
monitor.debugOnStartGuest64 = “TRUE“
这样,打开虚拟机,就可以直接用gdb远程调试连接了,端口默认是8864,可以自己指定.
注意,此时开启虚拟机,无论是原生的windbg exdi和ida都可以remote调试,但是原因前面说过,此时调试体验基本上没有:
ida有个Debugger,使用gdb-remote调试。
所以我们使用刚才那两个编译好的东东,首先把ExdiGdbSrv编译出来的所有东西替换windbg:
项目还自带脚本,依次执行init和start脚本,
可以看到,我们现在已经连上了,而且模块是有的
但是绝大部分windbg常用双机调试指令无法使用:
这个时候我们需要手动加载Exdihelper.dll
0: kd> .load F:\tools\debug\windbg_preview2\plugins\ExdiHelper.dll
0: kd> !rox
此时绝大部分指令可以正常使用,查看一些内核调试标志位,不出意外,没在调试:
总结
这毕竟不是windows原生的双机调试,所以一些基于kd.dll的常用调试方法也没办法使用,我目前遇到的不足有
- 无法使用魔法断点,比如在驱动内部__debugbreak(),无法接管这个异常,会蓝屏。
- 无法使用.process /i EPROCESS附加到指定进程的上下文
- 无法使用执行调试断点
- 使用内存断点的时候有时候有点问题