@@ -3052,6 +3052,7 @@ struct VM {
30523052
30533053 for (const auto & check : dll_checks) {
30543054 if (GetModuleHandleA (check.dll_name ) != nullptr ) {
3055+ debug (" DLL: Found " , check.dll_name , " (" , check.brand , " )" );
30553056 return core::add (check.brand );
30563057 }
30573058 }
@@ -3272,7 +3273,7 @@ struct VM {
32723273 wow64RedirectDisabled = true ;
32733274 }
32743275
3275- // Use the system directory instead of the Windows directory.
3276+ // System directory instead of the Windows directory
32763277 char szSysDir[MAX_PATH] = { 0 };
32773278 if (GetSystemDirectoryA (szSysDir, MAX_PATH) == 0 ) {
32783279 if (wow64RedirectDisabled) {
@@ -3281,23 +3282,26 @@ struct VM {
32813282 return false ;
32823283 }
32833284
3284- constexpr std::array<const char *, 29 > vbox_and_vmware = { {
3285- " drivers\\ Vmmouse.sys" ,
3286- " drivers\\ Vmusbmouse.sys" ,
3287- " drivers\\ vm3dgl.dll" ,
3288- " drivers\\ vmdum.dll" ,
3289- " drivers\\ VmGuestLibJava.dll" ,
3290- " drivers\\ vm3dver.dll" ,
3291- " drivers\\ vmtray.dll" ,
3292- " drivers\\ VMToolsHook.dll" ,
3293- " drivers\\ vmGuestLib.dll" ,
3294- " drivers\\ vmhgfs.dll" ,
3285+ constexpr std::array<const char *, 12 > vmwareFiles = { {
3286+ " drivers\\ Vmmouse.sys" ,
3287+ " drivers\\ Vmusbmouse.sys" ,
3288+ " drivers\\ vm3dgl.dll" ,
3289+ " drivers\\ vmdum.dll" ,
3290+ " drivers\\ VmGuestLibJava.dll" ,
3291+ " drivers\\ vm3dver.dll" ,
3292+ " drivers\\ vmtray.dll" ,
3293+ " drivers\\ VMToolsHook.dll" ,
3294+ " drivers\\ vmGuestLib.dll" ,
3295+ " drivers\\ vmhgfs.dll" ,
3296+ " vm3dum64_loader.dll" ,
3297+ " vm3dum64_10.dll"
3298+ } };
3299+
3300+ constexpr std::array<const char *, 17 > vboxFiles = { {
32953301 " drivers\\ VBoxMouse.sys" ,
32963302 " drivers\\ VBoxGuest.sys" ,
32973303 " drivers\\ VBoxSF.sys" ,
32983304 " drivers\\ VBoxVideo.sys" ,
3299- " vm3dum64_loader.dll" ,
3300- " vm3dum64_10.dll" ,
33013305 " vboxoglpackspu.dll" ,
33023306 " vboxoglpassthroughspu.dll" ,
33033307 " vboxservice.exe" ,
@@ -3341,25 +3345,21 @@ struct VM {
33413345 " drivers\\ vpc-s3.sys"
33423346 } };
33433347
3344- u8 vbox = 0 , vmware = 0 , kvm = 0 , vpc = 0 , parallels = 0 ;
3345-
3346- auto file_exists = [](const char * path) -> bool {
3347- DWORD attrs = GetFileAttributesA (path);
3348- return (attrs != INVALID_FILE_ATTRIBUTES) && !(attrs & FILE_ATTRIBUTE_DIRECTORY);
3349- };
3348+ u8 vmware = 0 , vbox = 0 , kvm = 0 , vpc = 0 , parallels = 0 ;
33503349
33513350 auto checkFiles = [&](const auto & files, u8 & count) {
33523351 for (const auto & relativePath : files) {
33533352 char szPath[MAX_PATH] = { 0 };
3354- // system directory + relative path, so for example: C:\Windows\System32\ + drivers\VBoxMouse.sys
3353+ // Combination of the system directory with the relative path
33553354 PathCombineA (szPath, szSysDir, relativePath);
3356- if (file_exists (szPath)) {
3355+ if (util::exists (szPath)) {
33573356 count++;
33583357 }
33593358 }
33603359 };
33613360
3362- checkFiles (vbox_and_vmware, vbox);
3361+ checkFiles (vmwareFiles, vmware);
3362+ checkFiles (vboxFiles, vbox);
33633363 checkFiles (kvmFiles, kvm);
33643364 checkFiles (parallelsFiles, parallels);
33653365 checkFiles (vpcFiles, vpc);
@@ -3368,28 +3368,30 @@ struct VM {
33683368 Wow64RevertWow64FsRedirection (&oldValue);
33693369 }
33703370
3371- if (file_exists (" C:\\ ProgramData\\ Microsoft\\ Windows\\ Start Menu\\ Programs\\ StartUp\\ agent.pyw" )) {
3371+ if (util::exists (" C:\\ ProgramData\\ Microsoft\\ Windows\\ Start Menu\\ Programs\\ StartUp\\ agent.pyw" )) {
3372+ debug (" VM Files: Found startup agent (agent.pyw), indicating CUCKOO VM." );
33723373 return core::add (brands::CUCKOO);
33733374 }
3374-
33753375 if (vbox > vmware && vbox > kvm && vbox > vpc && vbox > parallels) {
3376+ debug (" VM Files: Detected VBox files with count " , vbox);
33763377 return core::add (brands::VBOX);
33773378 }
33783379 if (vmware > vbox && vmware > kvm && vmware > vpc && vmware > parallels) {
3380+ debug (" VM Files: Detected VMware files with count " , vmware);
33793381 return core::add (brands::VMWARE);
33803382 }
33813383 if (kvm > vbox && kvm > vmware && kvm > vpc && kvm > parallels) {
3384+ debug (" VM Files: Detected KVM files with count " , kvm);
33823385 return core::add (brands::KVM);
33833386 }
33843387 if (vpc > vbox && vpc > vmware && vpc > kvm && vpc > parallels) {
3388+ debug (" VM Files: Detected VPC files with count " , vpc);
33853389 return core::add (brands::VPC);
33863390 }
33873391 if (parallels > vbox && parallels > vmware && parallels > kvm && parallels > vpc) {
3392+ debug (" VM Files: Detected Parallels files with count " , parallels);
33883393 return core::add (brands::PARALLELS);
33893394 }
3390- if (vbox > 0 && vmware > 0 && kvm > 0 && vpc > 0 && parallels > 0 ) {
3391- return true ;
3392- }
33933395
33943396 return false ;
33953397#endif
@@ -3808,39 +3810,50 @@ struct VM {
38083810 * @implements VM::VM_PROCESSES
38093811 */
38103812 [[nodiscard]] static bool vm_processes () {
3811- #if (!WINDOWS)
3813+ #if (!WINDOWS)
38123814 return false ;
3813- #else
3814- if (util::is_proc_running ((" joeboxserver.exe" )) || util::is_proc_running ((" joeboxcontrol.exe" ))) {
3815+ #else
3816+ if (util::is_proc_running (" joeboxserver.exe" ) || util::is_proc_running (" joeboxcontrol.exe" )) {
3817+ debug (" VM_PROCESSES: Detected JoeBox process." );
38153818 return core::add (brands::JOEBOX);
38163819 }
38173820
3818- if (util::is_proc_running ((" prl_cc.exe" )) || util::is_proc_running ((" prl_tools.exe" ))) {
3821+ if (util::is_proc_running (" prl_cc.exe" ) || util::is_proc_running (" prl_tools.exe" )) {
3822+ debug (" VM_PROCESSES: Detected Parallels process." );
38193823 return core::add (brands::PARALLELS);
38203824 }
38213825
3822- if (util::is_proc_running ((" vboxservice.exe" )) || util::is_proc_running ((" vboxtray.exe" ))) {
3826+ if (util::is_proc_running (" vboxservice.exe" ) || util::is_proc_running (" vboxtray.exe" )) {
3827+ debug (" VM_PROCESSES: Detected VBox process." );
38233828 return core::add (brands::VBOX);
38243829 }
38253830
3826- if (util::is_proc_running ((" vmsrvc.exe" )) || util::is_proc_running ((" vmusrvc.exe" ))) {
3831+ if (util::is_proc_running (" vmsrvc.exe" ) || util::is_proc_running (" vmusrvc.exe" )) {
3832+ debug (" VM_PROCESSES: Detected VPC process." );
38273833 return core::add (brands::VPC);
38283834 }
38293835
3830- if (util::is_proc_running ((" xenservice.exe" )) || util::is_proc_running ((" xsvc_depriv.exe" ))) {
3836+ if (util::is_proc_running (" xenservice.exe" ) || util::is_proc_running (" xsvc_depriv.exe" )) {
3837+ debug (" VM_PROCESSES: Detected Xen process." );
38313838 return core::add (brands::XEN);
38323839 }
38333840
3834- if (util::is_proc_running ((" vm3dservice.exe" )) || util::is_proc_running ((" VGAuthService.exe" )) || util::is_proc_running ((" vmtoolsd.exe" ))) {
3841+ if (util::is_proc_running (" vm3dservice.exe" ) ||
3842+ util::is_proc_running (" VGAuthService.exe" ) ||
3843+ util::is_proc_running (" vmtoolsd.exe" )) {
3844+ debug (" VM_PROCESSES: Detected VMware process." );
38353845 return core::add (brands::VMWARE);
38363846 }
38373847
3838- if (util::is_proc_running ((" vdagent.exe" )) || util::is_proc_running ((" vdservice.exe" )) || util::is_proc_running ((" qemuwmi.exe" ))) {
3848+ if (util::is_proc_running (" vdagent.exe" ) ||
3849+ util::is_proc_running (" vdservice.exe" ) ||
3850+ util::is_proc_running (" qemuwmi.exe" )) {
3851+ debug (" VM_PROCESSES: Detected QEMU process." );
38393852 return core::add (brands::QEMU);
38403853 }
38413854
38423855 return false ;
3843- #endif
3856+ #endif
38443857 }
38453858
38463859
@@ -4385,6 +4398,7 @@ struct VM {
43854398 if (dwType == REG_SZ || dwType == REG_EXPAND_SZ || dwType == REG_MULTI_SZ) {
43864399 buffer[bufferSize - 1 ] = ' \0 ' ;
43874400 if (strstr (buffer, comp_string) != nullptr ) {
4401+ debug (" HKLM_REGISTRIES: Found " , comp_string, " in " , subKey, " for brand " , p_brand);
43884402 core::add (p_brand);
43894403 count++;
43904404 }
@@ -6595,20 +6609,20 @@ struct VM {
65956609 }
65966610
65976611 if (lowestReservedAddrRangeEnd != lowestLoaderReservedAddrRangeEnd) {
6598- return false ; // No VM detected
6612+ return false ;
65996613 }
66006614
6601- /* Now check for Hyper-V or VirtualBox by memory ranges */
6615+ /* Hyper-V and VirtualBox by memory ranges */
66026616 for (DWORD i = 0 ; i < phys_count; i++) {
66036617 if (phys[i].address == HYPERV_PHYS_LO && (phys[i].address + phys[i].size ) == HYPERV_PHYS_HI) {
6604- return true ; // Detected Hyper-V
6618+ return core::add (VM::brands::HYPERV);
66056619 }
66066620 if (phys[i].address == VBOX_PHYS_LO && (phys[i].address + phys[i].size ) == VBOX_PHYS_HI) {
6607- return true ; // Detected VirtualBox
6621+ return core::add (VM::brands::VBOX);
66086622 }
66096623 }
66106624
6611- return false ; // Possibly VM, but unable to identify platform
6625+ return false ;
66126626#endif
66136627 }
66146628
@@ -7463,7 +7477,6 @@ struct VM {
74637477#if (!WINDOWS)
74647478 return false ;
74657479#else
7466-
74677480 typedef struct _SYSTEM_MODULE_INFORMATION {
74687481 PVOID Reserved[2 ];
74697482 PVOID ImageBaseAddress;
@@ -7545,6 +7558,8 @@ struct VM {
75457558 strstr (driverPath, " VBoxMouse" ) ||
75467559 strstr (driverPath, " VBoxSF" )
75477560 ) {
7561+ debug (" DRIVER_NAMES: Detected VBox driver: " , driverPath);
7562+ ntFreeVirtualMemory (hProcess, &allocatedMemory, ®ionSize, MEM_RELEASE);
75487563 return core::add (brands::VBOX);
75497564 }
75507565
@@ -7553,6 +7568,8 @@ struct VM {
75537568 strstr (driverPath, " vmmouse" ) ||
75547569 strstr (driverPath, " vmmemctl" )
75557570 ) {
7571+ debug (" DRIVER_NAMES: Detected VMware driver: " , driverPath);
7572+ ntFreeVirtualMemory (hProcess, &allocatedMemory, ®ionSize, MEM_RELEASE);
75567573 return core::add (brands::VMWARE);
75577574 }
75587575 }
@@ -7889,15 +7906,18 @@ struct VM {
78897906 CloseHandle (handle4);
78907907
78917908 if (result) {
7909+ debug (" VM_DEVICES: Detected VBox related device handles." );
78927910 return core::add (brands::VBOX);
78937911 }
78947912
78957913 if (handle5 != INVALID_HANDLE_VALUE) {
78967914 CloseHandle (handle5);
7915+ debug (" VM_DEVICES: Detected VMware related device (HGFS)." );
78977916 return core::add (brands::VMWARE);
78987917 }
78997918 if (handle6 != INVALID_HANDLE_VALUE) {
79007919 CloseHandle (handle6);
7920+ debug (" VM_DEVICES: Detected Cuckoo related device (pipe)." );
79017921 return core::add (brands::CUCKOO);
79027922 }
79037923
@@ -8470,7 +8490,7 @@ struct VM {
84708490 QueryPerformanceCounter (&endQPC);
84718491 LONGLONG dummyTime = endQPC.QuadPart - startQPC.QuadPart ;
84728492
8473- const bool qpc_check = (dummyTime != 0 ) && ((cpuIdTime / dummyTime) > 1100 );
8493+ const bool qpc_check = (dummyTime != 0 ) && ((cpuIdTime / dummyTime) > 1500 );
84748494 debug (" QPC check - CPUID: " , cpuIdTime, " ns, Dummy: " , dummyTime, " ns, Ratio: " , (cpuIdTime / dummyTime));
84758495
84768496 // TSC sync check across cores. Try reading the invariant TSC on two different cores to attempt to detect vCPU timers being shared
@@ -8674,7 +8694,6 @@ struct VM {
86748694 if (pNtQuerySystemInformation) {
86758695 SYSTEM_HYPERVISOR_DETAIL_INFORMATION hvInfo = { {} };
86768696 const NTSTATUS status = pNtQuerySystemInformation (static_cast <SYSTEM_INFORMATION_CLASS>(0x9F ), &hvInfo, sizeof (hvInfo), nullptr );
8677-
86788697 if (status != 0 ) {
86798698 return false ;
86808699 }
@@ -8975,6 +8994,7 @@ struct VM {
89758994
89768995 for (size_t j = 0 ; j < badPoolCount; ++j) {
89778996 if (currentTag == BadPoolDwords[j]) {
8997+ debug (" Bad Pools: Detected bad pool tag: 0x" , std::hex, currentTag, std::dec);
89788998 ++bad_pool_number;
89798999 break ;
89809000 }
@@ -9814,7 +9834,6 @@ struct VM {
98149834 if (!ntqsi)
98159835 return false ;
98169836
9817- // List of target strings (all are now treated as valid hits)
98189837 constexpr const char * targets[] = {
98199838 " Parallels Software International" , " Parallels(R)" , " innotek" ,
98209839 " Oracle" , " VirtualBox" , " VS2005R2" , " VMware, Inc." ,
@@ -10068,6 +10087,7 @@ struct VM {
1006810087 }
1006910088 }
1007010089
10090+ debug (" UNKNOWN_MANUFACTURER: CPU brand '" , brand, " ' did not match known vendor IDs." );
1007110091 return true ; // no known manufacturer matched, likely a VM
1007210092 }
1007310093
@@ -11668,7 +11688,7 @@ std::pair<VM::enum_flags, VM::core::technique> VM::core::technique_list[] = {
1166811688 { VM::CPU_BRAND, { 50 , VM::cpu_brand } },
1166911689 { VM::HYPERVISOR_BIT, { 100 , VM::hypervisor_bit}} ,
1167011690 { VM::HYPERVISOR_STR, { 75 , VM::hypervisor_str } },
11671- { VM::TIMER, { 20 , VM::timer } },
11691+ { VM::TIMER, { 45 , VM::timer } },
1167211692 { VM::THREADCOUNT, { 35 , VM::thread_count } },
1167311693 { VM::MAC, { 20 , VM::mac_address_check } },
1167411694 { VM::TEMPERATURE, { 15 , VM::temperature } },
0 commit comments