initial commit
This commit is contained in:
Executable
+86
@@ -0,0 +1,86 @@
|
||||
/**
|
||||
* evasion_anti_debug.c — Anti-debugging checks
|
||||
*
|
||||
* Checks:
|
||||
* 1. IsDebuggerPresent()
|
||||
* 2. NtQueryInformationProcess (ProcessDebugPort)
|
||||
* 3. Timing check (RDTSC delta)
|
||||
* 4. NtGlobalFlag in PEB
|
||||
*
|
||||
* If a debugger is detected, calls ExitProcess(0) silently.
|
||||
*/
|
||||
|
||||
#include <windows.h>
|
||||
#include <winternl.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "api_resolve.h"
|
||||
|
||||
#ifdef EVASION_ANTI_DEBUG
|
||||
|
||||
static void exit_if_debugged(void) {
|
||||
g_api.pExitProcess(0);
|
||||
}
|
||||
|
||||
/* Basic API check */
|
||||
static void check_is_debugger_present(void) {
|
||||
if (g_api.pIsDebuggerPresent()) {
|
||||
exit_if_debugged();
|
||||
}
|
||||
}
|
||||
|
||||
/* NtQueryInformationProcess — ProcessDebugPort (class 7) */
|
||||
static void check_debug_port(void) {
|
||||
if (!g_api.pNtQueryInformationProcess) return;
|
||||
|
||||
DWORD_PTR debug_port = 0;
|
||||
NTSTATUS status = g_api.pNtQueryInformationProcess(
|
||||
g_api.pGetCurrentProcess(), 7 /* ProcessDebugPort */,
|
||||
&debug_port, sizeof(debug_port), NULL);
|
||||
if (status == 0 && debug_port != 0) {
|
||||
exit_if_debugged();
|
||||
}
|
||||
}
|
||||
|
||||
/* Timing check: debugger single-stepping causes large RDTSC deltas */
|
||||
static void check_timing(void) {
|
||||
LARGE_INTEGER freq, t1, t2;
|
||||
if (!g_api.pQueryPerformanceFrequency(&freq)) return;
|
||||
g_api.pQueryPerformanceCounter(&t1);
|
||||
|
||||
/* Do some trivial work */
|
||||
volatile int x = 0;
|
||||
for (int i = 0; i < 100; i++) x += i;
|
||||
|
||||
g_api.pQueryPerformanceCounter(&t2);
|
||||
/* If more than 500ms elapsed for trivial work, likely being debugged */
|
||||
double elapsed_ms = (double)(t2.QuadPart - t1.QuadPart) / freq.QuadPart * 1000.0;
|
||||
if (elapsed_ms > 500.0) {
|
||||
exit_if_debugged();
|
||||
}
|
||||
}
|
||||
|
||||
/* NtGlobalFlag in PEB — set when process is created under a debugger */
|
||||
static void check_nt_global_flag(void) {
|
||||
#ifdef _WIN64
|
||||
/* PEB is at GS:[0x60], NtGlobalFlag at offset 0xBC */
|
||||
PPEB peb = (PPEB)__readgsqword(0x60);
|
||||
DWORD flags = *(DWORD *)((uint8_t *)peb + 0xBC);
|
||||
#else
|
||||
PPEB peb = (PPEB)__readfsdword(0x30);
|
||||
DWORD flags = *(DWORD *)((uint8_t *)peb + 0x68);
|
||||
#endif
|
||||
/* FLG_HEAP_ENABLE_TAIL_CHECK | FLG_HEAP_ENABLE_FREE_CHECK | FLG_HEAP_VALIDATE_PARAMETERS */
|
||||
if (flags & 0x70) {
|
||||
exit_if_debugged();
|
||||
}
|
||||
}
|
||||
|
||||
void evasion_anti_debug_init(void) {
|
||||
check_is_debugger_present();
|
||||
check_debug_port();
|
||||
check_timing();
|
||||
check_nt_global_flag();
|
||||
}
|
||||
|
||||
#endif /* EVASION_ANTI_DEBUG */
|
||||
Reference in New Issue
Block a user