Skip to content

Commit 6dab4c8

Browse files
committed
README changes
1 parent 384e082 commit 6dab4c8

5 files changed

Lines changed: 101 additions & 127 deletions

File tree

README.md

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,14 @@
1-
<p align="center">
2-
<img src="assets/banner.jpg" align="center" width="500" title="VMAware">
3-
<br>
4-
<img align="center" src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
5-
<img align="center" src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
6-
<img align="center" src="https://img.shields.io/badge/License-MIT-yellow.svg">
7-
<a href="https://deepwiki.com/kernelwernel/VMAware"><img align="center" src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
8-
9-
<div align="center">
10-
<b>VMAware</b> (VM + Aware) is a cross-platform C++ framework for virtual machine detection.
11-
<br>
12-
<br>
13-
<a href="README_CN.md">中文 🇨🇳</a> | <a href="README_FR.md">Français 🇫🇷</a> | <a href="README_KR.md">한국어 🇰🇷</a>
14-
</div>
15-
</p>
1+
<div align="center">
2+
<h1>VMAware</h1>
3+
<img src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
4+
<img src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
5+
<img src="https://img.shields.io/badge/License-MIT-yellow.svg">
6+
<a href="https://deepwiki.com/kernelwernel/VMAware"><img src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
7+
<br><br>
8+
<b>VMAware</b> (VM + Aware) is a cross-platform C++ framework for virtual machine detection.
9+
<br><br>
10+
<a href="README_CN.md">中文 🇨🇳</a> | <a href="README_FR.md">Français 🇫🇷</a> | <a href="README_KR.md">한국어 🇰🇷</a>
11+
</div>
1612

1713
- - -
1814

README_CN.md

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,14 @@
1-
<p align="center">
2-
<img src="assets/banner.jpg" align="center" width="500" title="VMAware">
3-
<br>
4-
<img align="center" src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
5-
<img align="center" src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
6-
<img align="center" src="https://img.shields.io/badge/License-MIT-yellow.svg">
7-
<a href="https://deepwiki.com/kernelwernel/VMAware"><img align="center" src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
8-
9-
<div align="center">
10-
<b>VMAware</b> (VM + Aware) 是一个跨平台的C++虚拟机检测库。
11-
<br>
12-
<br>
13-
<a href="README.md">English 🇬🇧</a> | <a href="README_FR.md">Français 🇫🇷</a> | <a href="README_KR.md">한국어 🇰🇷</a>
14-
</div>
15-
</p>
1+
<div align="center">
2+
<h1>VMAware</h1>
3+
<img src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
4+
<img src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
5+
<img src="https://img.shields.io/badge/License-MIT-yellow.svg">
6+
<a href="https://deepwiki.com/kernelwernel/VMAware"><img src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
7+
<br><br>
8+
<b>VMAware</b> (VM + Aware) 是一个跨平台的C++虚拟机检测库。
9+
<br><br>
10+
<a href="README.md">English 🇬🇧</a> | <a href="README_FR.md">Français 🇫🇷</a> | <a href="README_KR.md">한국어 🇰🇷</a>
11+
</div>
1612

1713
- - -
1814

README_FR.md

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,14 @@
1-
<p align="center">
2-
<img src="assets/banner.jpg" align="center" width="500" title="VMAware">
3-
<br>
4-
<img align="center" src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
5-
<img align="center" src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
6-
<img align="center" src="https://img.shields.io/badge/License-MIT-yellow.svg">
7-
<a href="https://deepwiki.com/kernelwernel/VMAware"><img align="center" src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
8-
9-
<div align="center">
10-
<b>VMAware</b> (VM + Aware) est une bibliothèque C++ multiplateforme pour la détection des machines virtuelles.
11-
<br>
12-
<br>
13-
<a href="README.md">English 🇬🇧</a> | <a href="README_CN.md">中文 🇨🇳</a> | <a href="README_KR.md">한국어 🇰🇷</a>
14-
</div>
15-
</p>
1+
<div align="center">
2+
<h1>VMAware</h1>
3+
<img src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
4+
<img src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
5+
<img src="https://img.shields.io/badge/License-MIT-yellow.svg">
6+
<a href="https://deepwiki.com/kernelwernel/VMAware"><img src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
7+
<br><br>
8+
<b>VMAware</b> (VM + Aware) est une bibliothèque C++ multiplateforme pour la détection des machines virtuelles.
9+
<br><br>
10+
<a href="README.md">English 🇬🇧</a> | <a href="README_CN.md">中文 🇨🇳</a> | <a href="README_KR.md">한국어 🇰🇷</a>
11+
</div>
1612

1713
- - -
1814

README_KR.md

Lines changed: 11 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,14 @@
1-
<p align="center">
2-
<img src="assets/banner.jpg" align="center" width="500" title="VMAware">
3-
<br>
4-
<img align="center" src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
5-
<img align="center" src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
6-
<img align="center" src="https://img.shields.io/badge/License-MIT-yellow.svg">
7-
<a href="https://deepwiki.com/kernelwernel/VMAware"><img align="center" src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
8-
9-
<div align="center">
10-
<b>VMAware</b> (VM + Aware)는 가상 머신 탐지를 위한 크로스 플랫폼 C++ 라이브러리 입니다.
11-
<br>
12-
<br>
13-
<a href="README.md">English 🇬🇧</a> | <a href="README_CN.md">中文 🇨🇳</a> | <a href="README_FR.md">Français 🇫🇷</a>
14-
</div>
15-
</p>
1+
2+
<div align="center">
3+
<h1>VMAware</h1>
4+
<img src="https://img.shields.io/github/actions/workflow/status/kernelwernel/VMAware/cross-platform-build.yml">
5+
<img src="https://img.shields.io/github/downloads/kernelwernel/VMAware/total">
6+
<img src="https://img.shields.io/badge/License-MIT-yellow.svg">
7+
<a href="https://deepwiki.com/kernelwernel/VMAware"><img src="https://deepwiki.com/badge.svg" alt="Ask DeepWiki"></a>
8+
<b>VMAware</b> (VM + Aware)는 가상 머신 탐지를 위한 크로스 플랫폼 C++ 라이브러리 입니다.
9+
<br><br>
10+
<a href="README.md">English 🇬🇧</a> | <a href="README_CN.md">中文 🇨🇳</a> | <a href="README_FR.md">Français 🇫🇷</a>
11+
</div>
1612

1713
- - -
1814

src/vmaware.hpp

Lines changed: 57 additions & 67 deletions
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,7 @@
3232
* - License: MIT
3333
*
3434
* MIT License
35-
*
35+
*
3636
* Copyright (c) 2026 kernelwernel
3737
*
3838
* Permission is hereby granted, free of charge, to any person obtaining a copy
@@ -13179,29 +13179,29 @@ struct VM {
1317913179
return hypervisor_detected;
1318013180
#endif
1318113181
}
13182-
13183-
1318413182
/**
1318513183
* @brief Check whether a hypervisor leaks EFER.SVME into guest context via SVM instruction fault type
13186-
* @category Windows, x86
13184+
* @category Windows, x86_64, AMD
1318713185
* @implements VM::SVM_EXCEPTIONS
1318813186
*/
1318913187
[[nodiscard]] static bool svm_exceptions() {
13190-
#if (x86)
13191-
if (!cpu::is_amd()) {
13192-
debug("SVM_EXCEPTIONS: AMD CPU not detected, skipping");
13188+
if (!x86 || !cpu::is_amd()) {
13189+
debug("SVM_EXCEPTIONS: neither AMD or x86 detected, skipping");
1319313190
return false;
1319413191
}
1319513192

13196-
if (util::hyper_x() == HYPERV_ARTIFACT_VM) {
13193+
const auto hx = util::hyper_x();
13194+
if (hx == HYPERV_ARTIFACT_VM || hx == HYPERV_REAL_VM || hx == HYPERV_ENLIGHTENMENT) {
13195+
debug("SVM_EXCEPTIONS: Hyper-V active, skipping");
1319713196
return false;
1319813197
}
1319913198

1320013199
u32 eax = 0, ebx = 0, ecx = 0, edx = 0;
1320113200
cpu::cpuid(eax, ebx, ecx, edx, 0x80000001);
13202-
const bool svmcpuid_visible = ((ecx >> 2) & 1) != 0;
13201+
const bool svmcpuid_visible = (ecx >> 2) & 1;
1320313202

1320413203
const HMODULE ntdll = util::get_ntdll();
13204+
1320513205
if (!ntdll) {
1320613206
return false;
1320713207
}
@@ -13222,103 +13222,93 @@ struct VM {
1322213222
util::get_function_address(ntdll, names, funcs, ARRAYSIZE(names));
1322313223

1322413224
const auto nt_allocate_virtual_memory = reinterpret_cast<nt_allocate_virtual_memory_t>(funcs[0]);
13225-
const auto nt_protect_virtual_memory = reinterpret_cast<nt_protect_virtual_memory_t>(funcs[1]);
13226-
const auto nt_free_virtual_memory = reinterpret_cast<nt_free_virtual_memory_t>(funcs[2]);
13225+
const auto nt_protect_virtual_memory = reinterpret_cast<nt_protect_virtual_memory_t>(funcs[1]);
13226+
const auto nt_free_virtual_memory = reinterpret_cast<nt_free_virtual_memory_t>(funcs[2]);
1322713227
const auto nt_flush_instruction_cache = reinterpret_cast<nt_flush_instruction_cache_t>(funcs[3]);
1322813228

13229-
if (!nt_allocate_virtual_memory || !nt_protect_virtual_memory || !nt_free_virtual_memory || !nt_flush_instruction_cache) {
13229+
if (
13230+
(!nt_allocate_virtual_memory) ||
13231+
(!nt_protect_virtual_memory) ||
13232+
(!nt_free_virtual_memory) ||
13233+
(!nt_flush_instruction_cache)
13234+
) {
1323013235
return false;
1323113236
}
13237+
1323213238

13233-
constexpr std::array<std::array<u8, 4>, 5> opcodes{ {
13239+
constexpr u8 opcodes[][4] = {
1323413240
{ 0x0F, 0x01, 0xD8, 0xC3 }, // VMRUN
1323513241
{ 0x0F, 0x01, 0xDA, 0xC3 }, // VMLOAD
1323613242
{ 0x0F, 0x01, 0xDB, 0xC3 }, // VMSAVE
1323713243
{ 0x0F, 0x01, 0xDD, 0xC3 }, // CLGI
1323813244
{ 0x0F, 0x01, 0xDF, 0xC3 } // INVLPGA
13239-
} };
13245+
};
1324013246

13241-
constexpr SIZE_T opcode_size = 4;
1324213247
const HANDLE current_process = reinterpret_cast<HANDLE>(-1);
13248+
constexpr u32 opcode_size = 4;
1324313249

1324413250
for (const auto& opcode : opcodes) {
1324513251
PVOID base_address = nullptr;
1324613252
SIZE_T region_size = 0x1000;
1324713253

13248-
auto free_region = [&]() {
13249-
if (base_address) {
13250-
SIZE_T free_size = 0;
13251-
nt_free_virtual_memory(current_process, &base_address, &free_size, MEM_RELEASE);
13252-
base_address = nullptr;
13253-
}
13254-
};
13255-
1325613254
NTSTATUS status = nt_allocate_virtual_memory(
13257-
current_process,
13258-
&base_address,
13259-
0,
13260-
&region_size,
13261-
MEM_COMMIT | MEM_RESERVE,
13262-
PAGE_EXECUTE_READWRITE
13255+
current_process, &base_address, 0, &region_size,
13256+
MEM_COMMIT | MEM_RESERVE, PAGE_EXECUTE_READWRITE
1326313257
);
1326413258

1326513259
if (!NT_SUCCESS(status)) {
1326613260
continue;
1326713261
}
1326813262

13269-
memcpy(base_address, opcode.data(), opcode_size);
13263+
memcpy(base_address, opcode, opcode_size);
1327013264
nt_flush_instruction_cache(current_process, base_address, opcode_size);
1327113265

1327213266
ULONG old_protect = 0;
1327313267
PVOID protect_address = base_address;
1327413268
SIZE_T protect_size = region_size;
1327513269

1327613270
status = nt_protect_virtual_memory(
13277-
current_process,
13278-
&protect_address,
13279-
&protect_size,
13280-
PAGE_EXECUTE_READ,
13281-
&old_protect
13271+
current_process, &protect_address, &protect_size,
13272+
PAGE_EXECUTE_READ, &old_protect
1328213273
);
1328313274

13284-
if (!NT_SUCCESS(status)) {
13285-
free_region();
13286-
continue;
13287-
}
13288-
13289-
nt_flush_instruction_cache(current_process, base_address, opcode_size);
13275+
if (NT_SUCCESS(status)) {
13276+
nt_flush_instruction_cache(current_process, base_address, opcode_size);
1329013277

13291-
DWORD exception_status = 0;
13292-
bool fault_hit = false;
13278+
DWORD exception_status = 0;
13279+
bool fault_hit = false;
1329313280

13294-
__try {
13295-
reinterpret_cast<void(*)()>(base_address)();
13296-
}
13297-
__except (exception_status = GetExceptionCode(), EXCEPTION_EXECUTE_HANDLER) {
13298-
fault_hit = true;
13299-
}
13281+
__try {
13282+
const auto execute_svm = reinterpret_cast<void(*)()>(base_address);
13283+
execute_svm();
13284+
}
13285+
__except (exception_status = GetExceptionCode(), EXCEPTION_EXECUTE_HANDLER) {
13286+
fault_hit = true;
13287+
}
1330013288

13301-
free_region();
13289+
SIZE_T free_size = 0;
13290+
nt_free_virtual_memory(current_process, &base_address, &free_size, MEM_RELEASE);
1330213291

13303-
if (!fault_hit) {
13304-
continue;
13305-
}
13292+
if (fault_hit) {
13293+
if (exception_status == EXCEPTION_ILLEGAL_INSTRUCTION) {
13294+
continue;
13295+
}
1330613296

13307-
if (exception_status == EXCEPTION_ILLEGAL_INSTRUCTION) {
13308-
continue;
13309-
}
13297+
if (svmcpuid_visible) {
13298+
debug("SVM_EXCEPTIONS: #GP with SVM CPUID visible, VM detected");
13299+
} else {
13300+
debug("SVM_EXCEPTIONS: #GP with SVM CPUID hidden, VM spoofing CPUID detected");
13301+
core::add(brand_enum::NULL_BRAND, 100);
13302+
}
1331013303

13311-
if (svmcpuid_visible) {
13312-
debug("SVM_EXCEPTIONS: Detected SVM hypervisor");
13313-
}
13314-
else {
13315-
debug("SVM_EXCEPTIONS: Detected SVM hypervisor hiding CPU capabilities");
13316-
core::add(brand_enum::NULL_BRAND, 150);
13304+
return true;
13305+
}
13306+
} else {
13307+
SIZE_T free_size = 0;
13308+
nt_free_virtual_memory(current_process, &base_address, &free_size, MEM_RELEASE);
1331713309
}
13318-
13319-
return true;
1332013310
}
13321-
#endif
13311+
1332213312
return false;
1332313313
}
1332413314

@@ -14600,9 +14590,9 @@ std::array<VM::core::technique, VM::enum_size + 1> VM::core::technique_table = [
1460014590
#if (WINDOWS)
1460114591
{VM::TRAP, {100, VM::trap}},
1460214592
{VM::KVM_INTERCEPTION, {100, VM::kvm_interception}},
14603-
{VM::SVM_EXCEPTIONS, {100, VM::svm_exceptions}},
1460414593
{VM::INTERRUPT_SHADOW, {100, VM::interrupt_shadow}},
1460514594
{VM::EIP_OVERFLOW, {100, VM::eip_overflow}},
14595+
{VM::SVM_EXCEPTIONS, {25, VM::svm_exceptions}},
1460614596
{VM::HYPERVISOR_HOOK, {100, VM::hypervisor_hook}},
1460714597
{VM::SINGLE_STEP, {100, VM::single_step}},
1460814598
{VM::NVRAM, {100, VM::nvram}},
@@ -14714,4 +14704,4 @@ std::array<VM::core::technique, VM::enum_size + 1> VM::core::technique_table = [
1471414704
return table;
1471514705
}();
1471614706

14717-
#endif // include guard end
14707+
#endif // include guard end

0 commit comments

Comments
 (0)