欢迎来到 嗅灵易学

零基础也能上手的脚本技术课,一对一答疑带你入门

[原创]非静态成员函数定位及HOOK以DirectX内部成员函数为例

[原创]非静态成员函数定位及HOOK以DirectX内部成员函数为例

本方法相对比较通用,以HOOK DirectX 的内部成员函数为例,Dx的DLL,如d3d9.dll ,D3DX9_42.dlll并没有导出API,只导出了部分如Direct3DCreate9,而关键功能函数如DrawIndexedPrimitive没有导出。
以D3DX9_42.dlll的D3XFont类的DrawTextA为例子
   第一步:编写一个程序,调用要HOOK的功能函数,以DX的例子BasicHLSL(路径:\\Microsoft DirectX SDK (February 2010)\Samples\C++\Direct3D\BasicHLSL)为模板,在OnResetDevice函数(选这个函数是因为,改变下设置就可以激活)中添加代码

DWORD dwAddrPtr2=0x11223344; //这个用于CE搜索内存定位(包括只读属性)

    __asm

    {

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

    }

    RECT rect = { 10, 10, 500,200 };

    DWORD DW5=g_pFont->DrawTextA(NULL, "XXXXXXXXXXX", -1, &rect, 0,D3DCOLOR_XRGB(255,255,255));

    __asm

    {

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

        nop;

    }

    DWORD dwAddrPtr3=0x11223345; //用于定位


编译运行程序,CE搜索0x11223344 然后上下找有2堆NOP的中间会有一个CALL eax或edx之类的,在此处下断,获取call的地址即为函数所在的地址如0x1000147B(此时,对应同一版本的DLL已经是基址,但对不同系统和版本的地址是不一样的).
接下来获取所有版本的函数地址
搜索上面得到的1000147B,会找到一个或多个调用该地址的2级地址,然后根据成员函数的数量和测试,可以定位调用的函数。
如下
D3DXDebugMute+3A08 - 8B C1            - mov eax,ecx

D3DXDebugMute+3A0A - 33 C9            - xor ecx,ecx

D3DXDebugMute+3A0C - C7 00 8017B203   - mov [eax],10001780: [D3DXDebugMute+1E21]            ;//10001780为ID3DXFont类的开始

D3DXDebugMute+3A12 - 8D 90 A4040000   - lea edx,[eax+000004A4]

D3DXDebugMute+3A18 - 89 0A            - mov [edx],ecx

D3DXDebugMute+3A1A - 89 4A 04         - mov [edx+04],ecx

D3DXDebugMute+3A1D - 8D 90 AC040000   - lea edx,[eax+000004AC]


此处10001780+成员函数顺序(顺序查看SDK)*4 此处DrawTextA顺序为第15个,就是10001780+14*4读取该偏移地址刚好是1000147B这个
通用特征码提取,C7 00 ?? ?? ?? ?? 8D 90 ?? ?? ?? ??
有了特征码
然后就可以用Detour开始HOOK了。
这个方法能做很多事,如:性能优化,修改游戏,调用XX....
人无完人,若有疏漏,欢迎指正交流

注意:上传附件及图片大小不得大于30M。

⚠️ 版权声明:
本博客所有内容(含教程、源码、工具)仅供个人技术学习与研究交流使用,严禁商用、倒卖、二次分发及非法用途
未经作者书面授权,任何组织或个人不得转载、复制或用于其他平台,违者将追究相关责任。

0 0 0 举报
复制成功