From ad0047e97b2847412ee28bad6a3bfb48395add35 Mon Sep 17 00:00:00 2001 From: Stephen Finucane Date: Fri, 26 Feb 2016 10:55:55 +0000 Subject: [PATCH] virt/hardware: Check for threads when "required" The 'require' case "requires" the presence of hardware threads on a host. At present, this check is done using the NUMATopology filter. Unfortunately, this means that if this filter is disabled then instances can be scheduled on invalid hosts. Resolve this by adding a new check to be run when hosts are actually scheduling. Change-Id: Ia9e4784e02ca9ce7a3d81c962b95bee100f6db42 Closes-bug: #1550269 --- nova/tests/unit/virt/test_hardware.py | 16 ++++++++++++++++ nova/virt/hardware.py | 9 ++++++++- 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/nova/tests/unit/virt/test_hardware.py b/nova/tests/unit/virt/test_hardware.py index f1fcb59f172f..8f75879af264 100644 --- a/nova/tests/unit/virt/test_hardware.py +++ b/nova/tests/unit/virt/test_hardware.py @@ -2263,6 +2263,22 @@ class CPUPinningCellTestCase(test.NoDBTestCase, _CPUPinningTestCaseBase): got_pinning = {x: x for x in range(0, 4)} self.assertEqual(got_pinning, inst_pin.cpu_pinning) + def test_get_pinning_require_policy_no_siblings(self): + host_pin = objects.NUMACell( + id=0, + cpuset=set([0, 1, 2, 3, 4, 5, 6, 7]), + memory=4096, memory_usage=0, + pinned_cpus=set([]), + siblings=[], + mempages=[]) + inst_pin = objects.InstanceNUMACell( + cpuset=set([0, 1, 2, 3]), + memory=2048, + cpu_policy=fields.CPUAllocationPolicy.DEDICATED, + cpu_thread_policy=fields.CPUThreadAllocationPolicy.REQUIRE) + inst_pin = hw._numa_fit_instance_cell_with_pinning(host_pin, inst_pin) + self.assertIsNone(inst_pin) + def test_get_pinning_require_policy_too_few_siblings(self): host_pin = objects.NUMACell( id=0, diff --git a/nova/virt/hardware.py b/nova/virt/hardware.py index 7aa28017c3a9..d8eff008ad5d 100644 --- a/nova/virt/hardware.py +++ b/nova/virt/hardware.py @@ -25,7 +25,7 @@ import six import nova.conf from nova import context from nova import exception -from nova.i18n import _ +from nova.i18n import _, _LI from nova import objects from nova.objects import fields from nova.objects import instance as obj_instance @@ -842,6 +842,13 @@ def _numa_fit_instance_cell_with_pinning(host_cell, instance_cell): host_cell.free_siblings, instance_cell, host_cell.id, max(map(len, host_cell.siblings))) else: + if (instance_cell.cpu_thread_policy == + fields.CPUThreadAllocationPolicy.REQUIRE): + LOG.info(_LI("Host does not support hyperthreading or " + "hyperthreading is disabled, but 'require' " + "threads policy was requested.")) + return + # Straightforward to pin to available cpus when there is no # hyperthreading on the host free_cpus = [set([cpu]) for cpu in host_cell.free_cpus]