The Trap Flag (TF) is a special bit in the CPU's EFLAGS register that forces the processor to generate a single-step exception after every instruction. This behavior is commonly used in debugging to trace program flow one instruction at a time.
- Locate the address of the target syscall, for example,
NtAllocateVirtualMemory. - Enable the Trap Flag on the current thread using
GetThreadContextandSetThreadContext. - Invoke the
NtAllocateVirtualMemorysyscall with random dummy parameters. When execution reaches thesyscallinstruction, the VEH will capture the syscall number ofNtAllocateVirtualMemory. - Obtain the address of a whitelisted syscall. These are syscalls rarely monitored by security software, such as
NtDrawText. - Call
NtDrawTextwith the original parameters intended forNtAllocateVirtualMemory. Here, the VEH replaces the syscall number ofNtDrawTextwith that ofNtAllocateVirtualMemorywhen it reaches thesyscallinstruction.
This approach bypasses user-land hooks placed on NtAllocateVirtualMemory, while also feeding any security software hooking it with invalid, random parameters.
Use the INVOKE_SYSCALL macro by passing:
dwSyscallHash- The Murmur Hash of the target syscall.STATUS- AnNTSTATUSvariable that will hold the result returned by the syscall....- The actual parameters to be passed to the syscall identified bydwSyscallHash.
The image below showcases the invocation of NtAllocateVirtualMemory, NtProtectVirtualMemory, and NtCreateThreadEx syscalls using the INVOKE_SYSCALL macro.