Skip to content

Implementation of OpenGL on windows guest virtual machine using Mesa/Virgl protocol.

License

Notifications You must be signed in to change notification settings

tenclass/mvisor-win-vgpu-driver

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

43 Commits
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Mvisor Windows Guest VGPU Driver

Abstract

  • A full Windows guest OpenGL driver implemention for the Mvisor virtio-vgpu device, it provides OpenGL 4.x by translating OpenGL api requests to Mesa Virgl Render Commands, and then delivering these commands from guest application to Virglrenderer on the host.
  • ATTENTION: Rebuild virglrenderer with old version in order to align with mesa in guest
git clone https://gitlab.freedesktop.org/virgl/virglrenderer
get reset --hard 8df4cba170940dad9350a99900293adbcef39b6c
  • We have tested it by using Cinema4D and GPUTest on windows 10 guest, the driver worked very nice.
  • We can use Mvisor+VGPU to create a VM with OpenGL acceleration, regardless of the limitations of graphics card virtualization. By the way, we have created 20 VMs on a single T4 card with 16G video memory, each running Cinema 4D rendering, the operation of the VM (Virtual Machine) was still very smooth.

Screenshot

GpuTest

Cinema4D

Compile

User Mode Driver

    Build Environment: VS2019 or MinGW-W64

    Run build.bat in the usermode directory, it will download the Mesa project, patch it, and build it automatically. After building, you will get MvisorVGPUx64.dll and opengl32.dll in the build directory.

Kernel Mode Driver

    Build Environment: VS2019 + WDK10.0

    It's a WDF kernel mode driver, after building, you will get vgpu.sys, vgpu.inf and vgpu.cat in the build directory.

Install

  1. Change you guest VM to test-sign mode and reboot, otherwise the driver would not work because of the windows driver sign-check.
bcdedit.exe /set testsigning on
  1. Just run install.bat in our release package, it will help you to prepare the environment and install the drivers.

Current Status

  • You need to add this part of config to let Mvisor create VM with vgpu device.
  - class: virtio-vgpu
    memory: 1G
    staging: Yes
    blob: Yes
    node: /dev/dri/renderD128
  • We choose Direct-IO as the data transport type between usermode and kernelmode in guest vm now, but using Nether-IO may get better performance.
  • We have implemented all the features supported on linux host, but the blob feature was not supported in VM migration.
  • In order to use blob feature, you may need to patch the vrend_state.inferred_gl_caching_type in Virglrenderer to let your guest driver get VIRGL_CAP_ARB_BUFFER_STORAGE.
   if (has_feature(feat_arb_buffer_storage) && !vrend_state.use_external_blob) {
      const char *vendor = (const char *)glGetString(GL_VENDOR);
      bool is_mesa = ((strstr(renderer, "Mesa") != NULL) || (strstr(renderer, "DRM") != NULL) ||
                      (strstr(renderer, "llvmpipe") != NULL));
      /*
       * Intel GPUs (aside from Atom, which doesn't expose GL4.5) are cache-coherent.
       * Mesa AMDGPUs use write-combine mappings for coherent/persistent memory (see
       * RADEON_FLAG_GTT_WC in si_buffer.c/r600_buffer_common.c). For Nvidia, we can guess and
       * check.  Long term, maybe a GL extension or using VK could replace these heuristics.
       *
       * Note Intel VMX ignores the caching type returned from virglrenderer, while AMD SVM and
       * ARM honor it.
       */
      if (is_mesa) {
         if (strstr(vendor, "Intel") != NULL)
            vrend_state.inferred_gl_caching_type = VIRGL_RENDERER_MAP_CACHE_CACHED;
         else if (strstr(vendor, "AMD") != NULL)
            vrend_state.inferred_gl_caching_type = VIRGL_RENDERER_MAP_CACHE_WC;
         else if (strstr(vendor, "Mesa") != NULL)
            vrend_state.inferred_gl_caching_type = VIRGL_RENDERER_MAP_CACHE_CACHED;
      } else {
         /* This is an educated guess since things don't explode with VMX + Nvidia. */
         if (strstr(renderer, "NVIDIA") != NULL)
            vrend_state.inferred_gl_caching_type = VIRGL_RENDERER_MAP_CACHE_UNCACHED;
      }

      if (vrend_state.inferred_gl_caching_type)
         caps->v2.capability_bits |= VIRGL_CAP_ARB_BUFFER_STORAGE;
   }

References