From 607f70a5d24d2df9c63861434c4ba1991226ee34 Mon Sep 17 00:00:00 2001 Message-Id: <607f70a5d24d2df9c63861434c4ba1991226ee34@dist-git> From: Andrea Bolognani Date: Tue, 11 Jun 2019 10:55:03 +0200 Subject: [PATCH] qemu: Fix qemuProcessInitCpuAffinity() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Ever since the feature was introduced with commit 0f8e7ae33ace, it has contained a logic error in that it attempted to use a NUMA node map where a CPU map was expected. Because of that, guests using might fail to start: # virsh start guest error: Failed to start domain guest error: cannot set CPU affinity on process 40055: Invalid argument This was particularly easy to trigger on POWER 8 machines, where secondary threads always show up as offline in the host: having in the guest configuration, for example, would result in libvirt trying to set the process affinity so that it would prefer running on CPU 1, but since that's a secondary thread and thus shows up as offline, the operation would fail, and so would starting the guest. Use the newly introduced virNumaNodesetToCPUset() to convert the NUMA node map to a CPU map, which in the example above would be 48,56,64,72,80,88 - a valid input for virProcessSetAffinity(). https://bugzilla.redhat.com/show_bug.cgi?id=1703661 Signed-off-by: Andrea Bolognani Reviewed-by: Ján Tomko (cherry picked from commit 5f2212c062c720716b7701fa0a5511311dc6e906) https://bugzilla.redhat.com/show_bug.cgi?id=1716908 Signed-off-by: Andrea Bolognani Message-Id: <20190611085506.12564-4-abologna@redhat.com> Reviewed-by: Ján Tomko --- src/qemu/qemu_process.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/qemu/qemu_process.c b/src/qemu/qemu_process.c index 8b05cef80c..a3b71354e1 100644 --- a/src/qemu/qemu_process.c +++ b/src/qemu/qemu_process.c @@ -2382,11 +2382,16 @@ qemuProcessInitCpuAffinity(virDomainObjPtr vm) if (virDomainNumaGetNodeCount(vm->def->numa) <= 1 && virDomainNumatuneGetMode(vm->def->numa, -1, &mem_mode) == 0 && mem_mode == VIR_DOMAIN_NUMATUNE_MEM_STRICT) { + virBitmapPtr nodeset = NULL; + if (virDomainNumatuneMaybeGetNodeset(vm->def->numa, priv->autoNodeset, - &cpumapToSet, + &nodeset, -1) < 0) goto cleanup; + + if (virNumaNodesetToCPUset(nodeset, &cpumapToSet) < 0) + goto cleanup; } else if (vm->def->cputune.emulatorpin) { cpumapToSet = vm->def->cputune.emulatorpin; } else { -- 2.22.0