基于IO端口检测虚拟机

通过执行特权指令探测 Vmware;
  因为在虚拟机中指定功能号 0xa 则会从指定端口获取虚拟机版本信息到指定的目的操作数地址;
  另外 0x14 则是获取虚拟机内存大小,当获取的值大于0说明在虚拟机中。

#include <stdio.h>
#include <Windows.h>


/*
通过执行特权指令探测 Vmware
因为在虚拟机中指定功能号 0xa 则会从指定端口获取虚拟机版本信息到指定的目的操作数地址
另外 0x14 则是获取虚拟机内存大小,当获取的值大于0说明在虚拟机中
*/
bool CheckVmByIO()
{
    bool bRet = true;

    // 检测虚拟机与主机通信的IO端口。
    __try 
    {
        _asm
        {
            push ebx
            push ecx
            push edx

            mov eax, 'VMXh'    ;
            mov ebx, 0        ; 设置未非'VMXh'值,接收in指令的返回值(VMware 版本)
            mov ecx, 10        ; 指定功能号, 用于获取VMware版本
            mov edx, 'VX'    ; 设置端口号
            in eax, dx        ; 从端口'VX'读取VMware版本
            cmp ebx, 'VMXh'    ; 如果是在虚拟机里,ebx中会有'VMXh'
            setz[bRet]        ; 返回值bool

            pop edx
            pop ecx
            pop ebx
        }
    }
    __except (EXCEPTION_EXECUTE_HANDLER)    // 不在虚拟机中则触发异常
    {
        // 获取不到VMware版本,而发生可被识别的异常
        bRet = FALSE;
    }
    return bRet;
}

int main()
{
    bool rRet = CheckVmByIO();
    if (rRet == TRUE)
    {
        MessageBox(0, "存在VM", "提示", MB_OK);
        return 0;
    }

    while (TRUE)
    {
        printf("run\n");
    }

    return 0;
}

 

posted @ 2022-04-10 16:44  人类观察者  阅读(160)  评论(0编辑  收藏  举报