What is Hell's Gate and how it enables red team trade-craft?
Learn what is Hell's Gate technique for direct syscalls and how to use it for red team trade-craft.
Do you love driving? I do too.
Let’s say you are driving on a highway with multiple checkpoints where police officers stop and inspect every car. To avoid getting caught, you discover a tunnel that lets you reach your destination without passing through any checkpoints. This is similar to what Hell’s Gate does in Windows. It allows red team operators to bypass security checkpoints (API hooks) and communicate directly with the operating system, making detection much harder.
Follow my journey of 100 Days of Red Team on WhatsApp, Telegram or Discord.
Hell’s Gate is a technique to evade detection by security solutions that rely on API monitoring. Normally, when a program wants to perform a sensitive action, such as creating a process or allocating memory, it calls a Windows API function like NtAllocateVirtualMemory
. Security solutions often hook these API functions to detect malicious behavior. However, Hell’s Gate allows attackers to avoid these hooks by dynamically retrieving syscall numbers from the ntdll.dll
module in memory instead of using the standard API calls. By doing this, they can execute syscalls directly, making it much harder for security tools to detect their activity.
In traditional direct syscall techniques, red team operators often hardcode System Service Numbers (SSNs) or syscall IDs into their code. However, there is a significant problem, hard-coded SSNs can quickly become outdated because Microsoft frequently changes syscall numbers in new Windows updates. For example, a direct syscall code that works on Windows 10 might fail on Windows 11 if the syscall numbers have changed. Hell’s Gate solves this problem by retrieving the latest syscall numbers at runtime instead of relying on hard-coded values.
Below is the overall flow of Hell’s Gate technique:
The first step is to access to the Thread Environment Block (TEB)
From there, access the
PEB
Go through the
PEB
and get the base address fromntdll.dll
Access the
EAT
fromntdll.dll
Use
djb2
hashing on all native functions in the codeHash the function names retrieved from
EAT
using thedjb2
algorithmCompare the hashed function names with the hashed entries in
EAT
If they match, store the function address in
VX_TABLE
asVX_TABLE_ENTRY
.Based on the (absolut)
function address
, do an opcode comparison of thesyscall stub
from the native functions in ntdll.dll to check if the function is hooked or not.Additionally, based on checking the opcodes for the
syscall
andreturn
instruction, check if they are not too far apart to avoid executing a wrong native function or syscall.Use the
HellsGate
function to prepare the execution of a direct syscall.Use the
HellDescent
function to proceed the execution of a direct syscall
One drawback of this technique is that it required a clean version of ntdll.dll i.e. not hooked by the EDR.
If you want to dive deep into the details of how Hell’s Gate technique works, read the Hell’s Gate paper published by am0nsec and RtlMateusz. Also, go through the article Exploring Hell's Gate by Daniel Feichter.
am0nsec and RtlMateusz have also published a PoC for this technique.
Red Team Notes
Hell’s Gate dynamically retrieves syscall numbers from ntdll.dll at runtime using the PEB and EAT parsing, bypassing API hooks placed by security tools. This enhances stealth in red team operations by evading user-mode monitoring and ensuring compatibility across Windows versions.
Follow my journey of 100 Days of Red Team on WhatsApp, Telegram or Discord.