首页
社区
课程
招聘
[讨论]64位下的inline Hook
发表于: 2017-11-17 00:22 10386

[讨论]64位下的inline Hook

2017-11-17 00:22
10386
最近在研究64位下的inline Hook,在网上搜了搜,找到了两种方法。

1
2
3
1. 48H B8H XX XX XX XX XX XX XX XX 50H C3H 12字节
 
2. FFH,25H,0,0,0,0,XX XX XX XX XX XX XX XX 14 字节

第一种好像会影响寄存器的值,我就用了第二种,写了如下代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
CPP:
 
InlineHook_x64::InlineHook_x64(void)
{
    pOldAPI = NULL;            //此指针pOldAP
    strcpy(szOldAPI, "\xFF\x25\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00");//先清空原数据
    strcpy(szNewAPI,"\xFF\x25\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00");//初始跳转数据
    MessageBox(0, L"", L"", 0);
}
 
 
InlineHook_x64::~InlineHook_x64(void)
{
}
//*********************HOOK API的函数*************************//
bool InlineHook_x64::HookAPI(char const * ModuleName,char const * ApiName,PVOID NewAPI)
{
    //找到API函数在内存中的地址
    pOldAPI = 0;
    HMODULE hModule = LoadLibraryA(ModuleName); 
    pOldAPI = (PVOID)GetProcAddress(hModule, ApiName);
 
    WCHAR msg[64];
     
 
    memcpy(szNewAPI + 6, &pOldAPI, 8);
    wsprintf(msg, L"GetProcAddress:%p\nszNewAPI:%p\n", pOldAPI, szNewAPI);
    MessageBox(0, msg, L"", 0);
 
 
    DWORD64 dwJmpAddr = 0
    dwJmpAddr = (DWORD64)NewAPI; 
    memcpy(szNewAPI + 6, &dwJmpAddr, 8); 
    FreeLibrary(hModule); 
    ReadProcessMemory ((void*)-1, pOldAPI, szOldAPI, 14, NULL);    //读出原来的前12个字节 
    WriteProcessMemory((void*)-1, pOldAPI, szNewAPI, 14, NULL);    //写入我们处理后的12个字节 
    wsprintf(msg, L"WriteProcessMemory:%p\ndwJmpAddr:%p\n", pOldAPI, dwJmpAddr);
    MessageBox(0, msg, L"", 0);
    return true;
}
 
H:
 
class InlineHook_x64
{
public:
    InlineHook_x64(void);
    ~InlineHook_x64(void);
    PVOID pOldAPI ;            //此指针pOldAPI保存原来API函数的地址(通过GetProcAddress获取)
    char  szOldAPI[14];                //存放原来API函数在内存中的前12个字节
    char  szNewAPI[14];    //存放64位的跳转地址
    //*********************停止HOOK的函数************************//
    void UnHook();
    //*********************重新HOOK API 的函数********************//
    void ReHook();
    //*********************HOOK API的函数*************************//
    bool HookAPI(char const * ModuleName,char const * ApiName,PVOID NewAPI);
};
1
2
3
4
5
6
7
8
9
DLLMAIN:
 
void GameD3D_HOOK()
{
    //MessageBox(0, L"GameD3D_HOOK", L"", 0);
    InlineHook_x64 hook;
    hook.HookAPI("d3d9.dll""Direct3DCreate9", (PVOID)New_Direct3DCreate9);
    //MessageBox(0, L"GameD3D_HOOK", L"", 0);
}
直接注入微软D3DSDK demo:
Microsoft DirectX SDK (June 2010)\Samples\C++\Direct3D\Bin\x64\StateManager.exe
奇怪的是它居然没跳入我的HOOK函数New_Direct3DCreate9,写的代码有问题么?这问题折磨我一天了,来大神带我走出痛苦的深渊吧。



[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

收藏
免费
支持
分享
最新回复 (6)
雪    币: 269
活跃值: (906)
能力值: ( LV12,RANK:345 )
在线值:
发帖
回帖
粉丝
2
这种问题自己调试下看看原地址有没有被改成跳转指令,跳转地址对不对不就知道了?64位主要是注意需要8字节保存地址
2017-11-17 10:56
0
雪    币: 5734
活跃值: (1737)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
3
目测没有写入成功  代码段需要修改内存页属性
2017-11-17 15:49
0
雪    币: 202
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
4
小艾 目测没有写入成功 代码段需要修改内存页属性
有道理,我以为DLL都是自己人了就不要改内存属性,VirtualProtect(pOldAPI,  14,  PAGE_EXECUTE_READWRITE,  &oldpro);写在WriteProcessMemory就可以了吧,我回去试试。感谢
2017-11-17 18:41
0
雪    币: 202
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
AJISky 这种问题自己调试下看看原地址有没有被改成跳转指令,跳转地址对不对不就知道了?64位主要是注意需要8字节保存地址
我用的是vs2017,内存察看器不知道怎么调出来,只能用ce看,再一个DLL调试的话好像得有被调试程序的源代码才能调试,现在用对话框调试,网上搜索没结果,可以的话你教我啊。
2017-11-17 18:49
0
雪    币: 202
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
找到问题了,赋初值的时候strcpy_s换成memcpy就清零了,但是依旧没有跳转到我的函数里
2017-11-18 02:18
0
雪    币: 341
活跃值: (1020)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
7
ff 25这种方法好像8字节的地址被截断了;
/*
The absolute jump is (x64) :
48 b8 ef cd ab 89 67 45 23 01   mov rax, 0x0123456789abcdef
ff e0                                            jmp rax
And for x86 :
b8 67 45 23 01   mov eax, 0x01234567
ff e0                    jmp eax
*/(摘自某位网友的回复。这个好像可以)
2018-7-11 12:59
0
游客
登录 | 注册 方可回帖
返回

账号登录
验证码登录

忘记密码?
没有账号?立即免费注册