Skip to content

Instantly share code, notes, and snippets.

@claudiok
Created May 24, 2017 19:19
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save claudiok/5dd9fd01b9628e35f0b48884471e58cf to your computer and use it in GitHub Desktop.
Save claudiok/5dd9fd01b9628e35f0b48884471e58cf to your computer and use it in GitHub Desktop.
diff --git a/nova/tests/unit/virt/libvirt/test_config.py b/nova/tests/unit/virt/libvirt/test_config.py
index 99382f5..04b056c 100644
--- a/nova/tests/unit/virt/libvirt/test_config.py
+++ b/nova/tests/unit/virt/libvirt/test_config.py
@@ -1845,6 +1845,7 @@ class LibvirtConfigGuestFeatureTest(LibvirtConfigBaseTest):
obj.relaxed = True
obj.vapic = True
obj.spinlocks = True
+ obj.vendor_id = True
xml = obj.to_xml()
self.assertXmlEqual(xml, """
@@ -1852,8 +1853,20 @@ class LibvirtConfigGuestFeatureTest(LibvirtConfigBaseTest):
<relaxed state="on"/>
<vapic state="on"/>
<spinlocks state="on" retries="4095"/>
+ <vendor_id state="on" value="MyFake_KVM"/>
</hyperv>""")
+ def test_feature_kvm_hidden(self):
+
+ obj = config.LibvirtConfigGuestFeatureKVM()
+ obj.hidden = True
+
+ xml = obj.to_xml()
+ self.assertXmlEqual(xml, """
+ <kvm>
+ <hidden state="on"/>
+ </kvm>""")
+
class LibvirtConfigGuestTest(LibvirtConfigBaseTest):
diff --git a/nova/tests/unit/virt/libvirt/test_driver.py b/nova/tests/unit/virt/libvirt/test_driver.py
index 9ac130c..61857e0 100644
--- a/nova/tests/unit/virt/libvirt/test_driver.py
+++ b/nova/tests/unit/virt/libvirt/test_driver.py
@@ -3159,6 +3159,53 @@ class LibvirtConnTestCase(test.NoDBTestCase):
self.assertEqual(8191, cfg.features[2].spinlock_retries)
self.assertTrue(cfg.features[2].vapic)
+ @mock.patch.object(host.Host, 'has_min_version')
+ def test_get_guest_config_windows_hide_kvm(self, mock_version):
+ mock_version.return_value = True
+ drvr = libvirt_driver.LibvirtDriver(fake.FakeVirtAPI(), True)
+ instance_ref = objects.Instance(**self.test_instance)
+ instance_ref['os_type'] = 'windows'
+ instance_ref.flavor.extra_specs = {'hw:hide_kvm': 'True'}
+ image_meta = objects.ImageMeta.from_dict(self.test_image_meta)
+
+ disk_info = blockinfo.get_disk_info(CONF.libvirt.virt_type,
+ instance_ref,
+ image_meta)
+ cfg = drvr._get_guest_config(instance_ref,
+ _fake_network_info(self, 1),
+ image_meta, disk_info)
+
+ self.assertEqual(4, len(cfg.features))
+ self.assertIsInstance(cfg.features[2],
+ vconfig.LibvirtConfigGuestFeatureHyperV)
+ self.assertIsInstance(cfg.features[3],
+ vconfig.LibvirtConfigGuestFeatureKVM)
+
+ self.assertTrue(cfg.features[2].vendor_id)
+ self.assertEqual('MyFake_KVM', cfg.features[2].vendor_id_name)
+ self.assertTrue(cfg.features[3].hidden)
+
+ @mock.patch.object(host.Host, 'has_min_version')
+ def test_get_guest_config_non_windows_hide_kvm(self, mock_version):
+ mock_version.return_value = True
+ drvr = libvirt_driver.LibvirtDriver(fake.FakeVirtAPI(), True)
+ instance_ref = objects.Instance(**self.test_instance)
+ instance_ref.flavor.extra_specs = {'hw:hide_kvm': 'True'}
+ image_meta = objects.ImageMeta.from_dict(self.test_image_meta)
+
+ disk_info = blockinfo.get_disk_info(CONF.libvirt.virt_type,
+ instance_ref,
+ image_meta)
+ cfg = drvr._get_guest_config(instance_ref,
+ _fake_network_info(self, 1),
+ image_meta, disk_info)
+
+ self.assertEqual(3, len(cfg.features))
+ self.assertIsInstance(cfg.features[2],
+ vconfig.LibvirtConfigGuestFeatureKVM)
+
+ self.assertTrue(cfg.features[2].hidden)
+
def test_get_guest_config_with_two_nics(self):
drvr = libvirt_driver.LibvirtDriver(fake.FakeVirtAPI(), True)
instance_ref = objects.Instance(**self.test_instance)
diff --git a/nova/virt/libvirt/config.py b/nova/virt/libvirt/config.py
index 1cf4d4f..ed98ee0 100644
--- a/nova/virt/libvirt/config.py
+++ b/nova/virt/libvirt/config.py
@@ -2004,6 +2004,7 @@ class LibvirtConfigGuestFeatureHyperV(LibvirtConfigGuestFeature):
# QEMU requires at least this value to be set
MIN_SPINLOCK_RETRIES = 4095
+ DEFAULT_VENDOR_ID = "MyFake_KVM"
def __init__(self, **kwargs):
super(LibvirtConfigGuestFeatureHyperV, self).__init__("hyperv",
@@ -2013,6 +2014,8 @@ class LibvirtConfigGuestFeatureHyperV(LibvirtConfigGuestFeature):
self.vapic = False
self.spinlocks = False
self.spinlock_retries = self.MIN_SPINLOCK_RETRIES
+ self.vendor_id = False
+ self.vendor_id_name = self.DEFAULT_VENDOR_ID
def format_dom(self):
root = super(LibvirtConfigGuestFeatureHyperV, self).format_dom()
@@ -2024,6 +2027,26 @@ class LibvirtConfigGuestFeatureHyperV(LibvirtConfigGuestFeature):
if self.spinlocks:
root.append(etree.Element("spinlocks", state="on",
retries=str(self.spinlock_retries)))
+ if self.vendor_id:
+ root.append(etree.Element("vendor_id", state="on",
+ value=self.vendor_id_name))
+
+ return root
+
+
+class LibvirtConfigGuestFeatureKVM(LibvirtConfigGuestFeature):
+
+ def __init__(self, **kwargs):
+ super(LibvirtConfigGuestFeatureKVM, self).__init__("kvm",
+ **kwargs)
+
+ self.hidden = True
+
+ def format_dom(self):
+ root = super(LibvirtConfigGuestFeatureKVM, self).format_dom()
+
+ if self.hidden:
+ root.append(etree.Element("hidden", state="on"))
return root
diff --git a/nova/virt/libvirt/driver.py b/nova/virt/libvirt/driver.py
index 3cc061d..e33bc3f 100644
--- a/nova/virt/libvirt/driver.py
+++ b/nova/virt/libvirt/driver.py
@@ -4177,7 +4177,7 @@ class LibvirtDriver(driver.ComputeDriver):
tmhyperv.present = True
clk.add_timer(tmhyperv)
- def _set_features(self, guest, os_type, caps, virt_type):
+ def _set_features(self, guest, os_type, caps, virt_type, flavor):
if virt_type == "xen":
# PAE only makes sense in X86
if caps.host.cpu.arch in (fields.Architecture.I686,
@@ -4189,6 +4189,11 @@ class LibvirtDriver(driver.ComputeDriver):
guest.features.append(vconfig.LibvirtConfigGuestFeatureACPI())
guest.features.append(vconfig.LibvirtConfigGuestFeatureAPIC())
+ # figure out if we are supposed to configure KVM so the
+ # guest is unaware running under it
+ hide_kvm = strutils.bool_from_string(
+ flavor.extra_specs.get('hw:hide_kvm', 'no'))
+
if (virt_type in ("qemu", "kvm") and
os_type == 'windows'):
hv = vconfig.LibvirtConfigGuestFeatureHyperV()
@@ -4200,8 +4205,16 @@ class LibvirtDriver(driver.ComputeDriver):
# with Microsoft
hv.spinlock_retries = 8191
hv.vapic = True
+ if hide_kvm:
+ hv.vendor_id = True
guest.features.append(hv)
+ if (virt_type in ("qemu", "kvm")) and hide_kvm:
+ kv = vconfig.LibvirtConfigGuestFeatureKVM()
+ kv.hidden = True # hide KVM from guest for NVidia GPU passthrough
+ guest.features.append(kv)
+
+
def _check_number_of_serial_console(self, num_ports):
virt_type = CONF.libvirt.virt_type
if (virt_type in ("kvm", "qemu") and
@@ -4716,7 +4729,7 @@ class LibvirtDriver(driver.ComputeDriver):
self._conf_non_lxc_uml(virt_type, guest, root_device_name, rescue,
instance, inst_path, image_meta, disk_info)
- self._set_features(guest, instance.os_type, caps, virt_type)
+ self._set_features(guest, instance.os_type, caps, virt_type, flavor)
self._set_clock(guest, instance.os_type, image_meta, virt_type)
storage_configs = self._get_guest_storage_config(
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment