fixed WOW64 PEB address retrival on Windows 10

This commit is contained in:
mrexodia 2017-06-06 21:35:54 +02:00
parent 7cffd0df6d
commit e2abc789e9
No known key found for this signature in database
GPG Key ID: FC89E0AAA0C1AAD8
2 changed files with 57 additions and 41 deletions

View File

@ -189,13 +189,10 @@ static bool FixPebInProcess(HANDLE hProcess, bool Hide)
void* heapForceFlagsAddress = 0; void* heapForceFlagsAddress = 0;
DWORD heapForceFlags = 0; DWORD heapForceFlags = 0;
// getting the PEB64 doesnt work anymore since WIN10 creators update as the PEB32+0x1000 offset doesnt seem to be correct anymore #ifndef _WIN64
// maybe earlier as some comments suggested. at least this code causes crashes of debuggee as of that update only PEB64 myPEB64 = {0};
// in theory, we could get the PEB64 via TEB64 (TitanEngine.Hider GetTEBLocation64) or via ntdll.Wow64QueryInformationProcess64 void* AddressOfPEB64 = GetPEBLocation64(hProcess);
//#ifndef _WIN64 #endif
// PEB64 myPEB64 = {0};
// void* AddressOfPEB64 = GetPEBLocation64(hProcess);
//#endif
void* AddressOfPEB = GetPEBLocation(hProcess); void* AddressOfPEB = GetPEBLocation(hProcess);
@ -204,12 +201,12 @@ static bool FixPebInProcess(HANDLE hProcess, bool Hide)
if(ReadProcessMemory(hProcess, AddressOfPEB, (void*)&myPEB, sizeof(PEB_CURRENT), &ueNumberOfBytesRead)) if(ReadProcessMemory(hProcess, AddressOfPEB, (void*)&myPEB, sizeof(PEB_CURRENT), &ueNumberOfBytesRead))
{ {
//#ifndef _WIN64 #ifndef _WIN64
// if(AddressOfPEB64) if(AddressOfPEB64)
// { {
// ReadProcessMemory(hProcess, AddressOfPEB64, (void*)&myPEB64, sizeof(PEB64), &ueNumberOfBytesRead); ReadProcessMemory(hProcess, AddressOfPEB64, (void*)&myPEB64, sizeof(PEB64), &ueNumberOfBytesRead);
// } }
//#endif #endif
if(Hide) if(Hide)
{ {
@ -217,22 +214,19 @@ static bool FixPebInProcess(HANDLE hProcess, bool Hide)
myPEB.BeingDebugged = FALSE; myPEB.BeingDebugged = FALSE;
myPEB.NtGlobalFlag &= ~0x70; myPEB.NtGlobalFlag &= ~0x70;
//#ifndef _WIN64 #ifndef _WIN64
// myPEB64.BeingDebugged = FALSE; myPEB64.BeingDebugged = FALSE;
// myPEB64.NtGlobalFlag &= ~0x70; myPEB64.NtGlobalFlag &= ~0x70;
//#endif #endif
//TODO: backup heap flags //TODO: backup heap flags
//#ifdef _WIN64 #ifdef _WIN64
// heapFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapFlagsOffset(true)); heapFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapFlagsOffset(true));
// heapForceFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapForceFlagsOffset(true)); heapForceFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapForceFlagsOffset(true));
//#else #else
// heapFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapFlagsOffset(false));
// heapForceFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapForceFlagsOffset(false));
//#endif //_WIN64
heapFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapFlagsOffset(false)); heapFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapFlagsOffset(false));
heapForceFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapForceFlagsOffset(false)); heapForceFlagsAddress = (void*)((LONG_PTR)myPEB.ProcessHeap + getHeapForceFlagsOffset(false));
#endif //_WIN64
ReadProcessMemory(hProcess, heapFlagsAddress, &heapFlags, sizeof(DWORD), 0); ReadProcessMemory(hProcess, heapFlagsAddress, &heapFlags, sizeof(DWORD), 0);
ReadProcessMemory(hProcess, heapForceFlagsAddress, &heapForceFlags, sizeof(DWORD), 0); ReadProcessMemory(hProcess, heapForceFlagsAddress, &heapForceFlags, sizeof(DWORD), 0);
@ -245,19 +239,19 @@ static bool FixPebInProcess(HANDLE hProcess, bool Hide)
else else
{ {
myPEB.BeingDebugged = TRUE; myPEB.BeingDebugged = TRUE;
//#ifndef _WIN64 #ifndef _WIN64
// myPEB64.BeingDebugged = TRUE; myPEB64.BeingDebugged = TRUE;
//#endif #endif
} }
if(WriteProcessMemory(hProcess, AddressOfPEB, (void*)&myPEB, sizeof(PEB_CURRENT), &ueNumberOfBytesRead)) if(WriteProcessMemory(hProcess, AddressOfPEB, (void*)&myPEB, sizeof(PEB_CURRENT), &ueNumberOfBytesRead))
{ {
//#ifndef _WIN64 #ifndef _WIN64
// if(AddressOfPEB64) if(AddressOfPEB64)
// { {
// WriteProcessMemory(hProcess, AddressOfPEB64, (void*)&myPEB64, sizeof(PEB64), &ueNumberOfBytesRead); WriteProcessMemory(hProcess, AddressOfPEB64, (void*)&myPEB64, sizeof(PEB64), &ueNumberOfBytesRead);
// } }
//#endif #endif
return true; return true;
} }
} }

View File

@ -47,6 +47,7 @@ __declspec(dllexport) void* TITCALL GetTEBLocation(HANDLE hThread)
__declspec(dllexport) void* TITCALL GetTEBLocation64(HANDLE hThread) __declspec(dllexport) void* TITCALL GetTEBLocation64(HANDLE hThread)
{ {
//TODO: this might return garbage on Windows 10
#ifndef _WIN64 #ifndef _WIN64
if(IsThisProcessWow64()) if(IsThisProcessWow64())
{ {
@ -64,20 +65,41 @@ __declspec(dllexport) void* TITCALL GetTEBLocation64(HANDLE hThread)
__declspec(dllexport) void* TITCALL GetPEBLocation64(HANDLE hProcess) __declspec(dllexport) void* TITCALL GetPEBLocation64(HANDLE hProcess)
{ {
void* PebAddress = 0;
#ifndef _WIN64 #ifndef _WIN64
if(IsThisProcessWow64()) if(IsThisProcessWow64())
{ {
//Only WOW64 processes have 2 PEBs typedef NTSTATUS(WINAPI * t_NtWow64QueryInformationProcess64)(HANDLE ProcessHandle, PROCESSINFOCLASS ProcessInformationClass, PVOID ProcessInformation, ULONG ProcessInformationLength, PULONG ReturnLength);
DWORD peb32 = (DWORD)GetPEBLocation(hProcess); static auto _NtWow64QueryInformationProcess64 = (t_NtWow64QueryInformationProcess64)GetProcAddress(GetModuleHandleW(L"ntdll.dll"), "NtWow64QueryInformationProcess64");
if(peb32) if(_NtWow64QueryInformationProcess64)
{ {
// this offset is WRONG as of Win10 Creators Update.See comment in Global.Engine.Hider.cpp:192 struct PROCESS_BASIC_INFORMATION64
peb32 += 0x1000; //PEB64 after PEB32 {
return (void*)peb32; DWORD ExitStatus;
DWORD64 PebBaseAddress;
DWORD64 AffinityMask;
DWORD BasePriority;
DWORD64 UniqueProcessId;
DWORD64 InheritedFromUniqueProcessId;
} myProcessBasicInformation[5];
ULONG RequiredLen = 0;
if(_NtWow64QueryInformationProcess64(hProcess, ProcessBasicInformation, myProcessBasicInformation, sizeof(PROCESS_BASIC_INFORMATION64), &RequiredLen) == STATUS_SUCCESS)
{
PebAddress = (void*)myProcessBasicInformation->PebBaseAddress;
}
else
{
if(_NtWow64QueryInformationProcess64(hProcess, ProcessBasicInformation, myProcessBasicInformation, RequiredLen, &RequiredLen) == STATUS_SUCCESS)
{
PebAddress = (void*)myProcessBasicInformation->PebBaseAddress;
}
}
} }
} }
#endif //_WIN64 #endif //_WIN64
return 0; return PebAddress;
} }
__declspec(dllexport) bool TITCALL HideDebugger(HANDLE hProcess, DWORD PatchAPILevel) __declspec(dllexport) bool TITCALL HideDebugger(HANDLE hProcess, DWORD PatchAPILevel)