vmaware
A VM / hypervisor / sandbox detection library for Rust – a faithful port of the VMAware C library with additional Windows-focused hardening.
Features
| Feature | Description |
|---|---|
| 86 detection techniques | CPUID tricks, registry keys, driver lists, BIOS strings, firmware, kernel objects, and more |
| Hell's Gate + Halo's Gate | On Windows x86-64, all NtQuerySystemInformation / NtOpenDirectoryObject calls are issued via direct syscall instructions, completely bypassing the ntdll trampolines that Windows Defender ATP and other EDR products hook |
| Cross-platform | Compiles on Windows, Linux, and macOS; platform-appropriate techniques are selected automatically |
no_std-friendly API surface |
The public API (detect, brand, percentage, check) is simple and allocation-light |
| Single-header usable as a library | Add it to Cargo.toml and call vmaware::detect(None) |
Quick start
# Cargo.toml
[]
= "0.2"
use ;
API
/// Returns true when a virtual machine is detected.
/// Pass `None` to run all applicable techniques.
;
/// Returns the most likely VM brand.
;
/// VM confidence as a percentage (0–100).
;
/// Number of techniques that fired.
;
/// All brands that contributed evidence.
;
/// Run a single technique by ID.
;
/// Hyper-X environment classification (RealVM / ArtifactVM / Enlightenment).
;
/// Human-readable conclusion string.
;
Selective technique execution
Use a Flagset to run only the techniques you care about:
use ;
// Run a single named technique
let found = check;
// Run a custom subset
let mut fs = new;
fs.set;
fs.set;
fs.set;
if detect
Syscall spoofing (Windows x86-64)
EDR products such as Windows Defender ATP install userland hooks by
overwriting the first few bytes of sensitive ntdll stubs with a jmp to their
monitoring code. When NtQuerySystemInformation is called to enumerate loaded
drivers or query hypervisor information, the EDR intercepts the call and can
flag or block it.
VMAware avoids this by implementing Hell's Gate:
- The PEB (
gs:[0x60]) is walked directly to find ntdll's in-memory base
address — noGetModuleHandlecall. - ntdll's PE export table is parsed in-place to locate each NT stub's VA.
- The syscall number is read from the clean stub bytes
(4C 8B D1 B8 XX XX XX XX=mov r10,rcx ; mov eax,<nr>). - If a stub is hooked (starts with
E9/jmp), Halo's Gate recovers the
correct number by scanning ±32 neighbouring stubs whose numbers are
sequential. - The
syscallinstruction is executed directly from our own code page,
never passing through any hooked ntdll trampoline.
The public vmaware::syscall module exposes the resolver if you want to use
it in your own code:
Supported VM brands (70+)
VMware, VirtualBox, QEMU/KVM, Hyper-V, Xen, Parallels, Docker, WSL, Bochs, DBVM, VPC, Sandboxie, Cuckoo, Wine, BlueStacks, Azure Hyper-V, AWS Nitro, GCE, OpenStack, AMD SEV/SEV-ES/SEV-SNP, and many more.
Platform support
| Platform | Supported | Notes |
|---|---|---|
| Windows x86-64 | ✅ Full | Hell's Gate syscall spoofing active |
| Windows ARM64 | ✅ Partial | Syscall spoofing falls back to GetProcAddress |
| Linux x86-64 | ✅ Full | 31 Linux-specific techniques |
| macOS x86-64 / arm64 | ⚠️ Partial | 6 macOS techniques (stubs for rest) |
Detection threshold
A VM is declared when the accumulated technique score reaches 150 points
out of a maximum of 300 points (HIGH_THRESHOLD_SCORE). Individual
technique scores range from 10 (low confidence, e.g. BootLogo) to 100
(definitive, e.g. VMware backdoor port, VmID CPUID response).
License
MIT – see LICENSE.
Original C/C++ library by kernelwernel.