首页
社区
课程
招聘
[求助]内核Hook函数 在KeStackAttachProcess时无法读写指针参数
2024-5-9 00:17 1183

[求助]内核Hook函数 在KeStackAttachProcess时无法读写指针参数

2024-5-9 00:17
1183

这两天在研究通过Hook内核Nt函数进行通讯

发现当我在

KeStackAttachProcess()

KeStackAttachProcess()

这两个函数之间读/写参数指针(req),会导致蓝屏崩溃

不知道有没有大牛知道这是为什么导致的,我之前用IO通讯的时候则没有这个问题,可以在任意位置读写

目前的解决方案是在进入挂靠之前定义临时变量存储要从参数指针(req)读取的值,出了挂靠之后再对参数指针(req)进行操作
虽然不大影响但是有点膈应,怕以后不小心就蓝了忘记这茬

以下是代码

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
NTSTATUS hk_NtUserShowSystemCursor(Reqest* req)
{
    if (req == NULL || req->signature == NULL) {
        LOG_INFO("return originFunc 1\n");
        return oNtUserShowSystemCursor();
    }
 
    if (req->signature == 0xAB505) {
        LOG_INFO("into communicate\n");
        req->succeed = false;
        switch (req->type)
        {
        case 001:
            GetMoudleInfo * moudleInput = (GetMoudleInfo*)req->data;
 
            PEPROCESS process;
            KAPC_STATE ApcState;
 
            if (NT_SUCCESS(PsLookupProcessByProcessId((HANDLE)moudleInput->pid, &process)) && (PsGetProcessExitStatus(process) == STATUS_PENDING)) {
 
                UNICODE_STRING unicodeStr = { 0 };
                ANSI_STRING ansiStr;
                RtlInitAnsiString(&ansiStr, moudleInput->moudleName);
                RtlAnsiStringToUnicodeString(&unicodeStr, &ansiStr, TRUE);
 
                BOOLEAN IsWow64 = (PsGetProcessWow64Process(process) != NULL) ? TRUE : FALSE;
 
                if (MmIsAddressValid(process)) {
 
                    KeStackAttachProcess((PRKPROCESS)process, &ApcState);
 
                    ULONG moduleSize = 0;
                    PVOID addr = GetUserModuleInfo(process, &unicodeStr, IsWow64, &moduleSize);
 
                    LOG_INFO("moduleSize: %d\n", moduleSize);
                    LOG_INFO("moduleAddr: %p\n", addr);
 
                    KeUnstackDetachProcess(&ApcState);
 
                    //必须在KeUnstackDetachProcess()之后 或者KeStackAttachProcess()之前读/写参数指针 不然会蓝屏
                    moudleInput->moudleBaseAddress = addr;
                    moudleInput->moudleSize = moduleSize;
                    req->succeed = true;
                    LOG_INFO("set\n");
                }
                RtlFreeUnicodeString(&unicodeStr);
                ObDereferenceObject(process);
            }
            break;
        }
    }
    else {
        LOG_INFO("return originFunc 2\n");
        return oNtUserShowSystemCursor();
    }
}

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

收藏
点赞0
打赏
分享
最新回复 (5)
雪    币: 2163
活跃值: (3604)
能力值: ( LV6,RANK:90 )
在线值:
发帖
回帖
粉丝
R0g 2 2024-5-9 00:19
2
0
req不在全局页面,是用户层过来的参数吧
雪    币: 4
能力值: ( LV1,RANK:0 )
在线值:
发帖
回帖
粉丝
mb_owiqdaph 2024-5-9 00:21
3
0
是的 在R3调用这个函数
雪    币: 2072
活跃值: (630)
能力值: ( LV7,RANK:100 )
在线值:
发帖
回帖
粉丝
sidyhe 1 2024-5-9 10:24
4
0
切进程就会切页表, R0地址所有进程共享, R3地址仅限当前进程

解决方法
1. 像你这样在内核态做次拷贝
2. 使用MDL把此内存重新映射为内核地址, 再切
雪    币: 4
能力值: ( LV1,RANK:0 )
在线值:
发帖
回帖
粉丝
mb_owiqdaph 2024-5-9 13:08
5
0
sidyhe 切进程就会切页表, R0地址所有进程共享, R3地址仅限当前进程 解决方法 1. 像你这样在内核态做次拷贝 2. 使用MDL把此内存重新映射为内核地址, 再切
懂了 感谢大牛 看起来第二种更吃力且麻烦 还是用次拷贝吧
雪    币: 916
活跃值: (3655)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
逆向爱好者 4天前
6
0
oudleinput这个指针哪来的
游客
登录 | 注册 方可回帖
返回