When the default cpuset or automatic numa placement is used libvirt
would place the whole parent cgroup in the specified cpuset. This then
disallowed to re-pin the vcpus to a different cpu.
This patch pins only the vcpu threads to the default cpuset and thus
allows to re-pin them later.
The following config would fail to start:
<domain type='kvm'>
...
<vcpu placement='static' cpuset='0-1'
current='2'>4</vcpu>
<cputune>
<vcpupin vcpu='0' cpuset='2-3'/>
...
This is a regression since a39f69d2b.
---
src/qemu/qemu_cgroup.c | 51 +++++++++++++++++++-------------------------------
1 file changed, 19 insertions(+), 32 deletions(-)
diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c
index be02ede..8674ab8 100644
--- a/src/qemu/qemu_cgroup.c
+++ b/src/qemu/qemu_cgroup.c
@@ -645,8 +645,6 @@ static int
qemuSetupCpusetCgroup(virDomainObjPtr vm)
{
qemuDomainObjPrivatePtr priv = vm->privateData;
- char *cpu_mask = NULL;
- int ret = -1;
if (!virCgroupHasController(priv->cgroup, VIR_CGROUP_CONTROLLER_CPUSET))
return 0;
@@ -654,25 +652,7 @@ qemuSetupCpusetCgroup(virDomainObjPtr vm)
if (virCgroupSetCpusetMemoryMigrate(priv->cgroup, true) < 0)
return -1;
- if (vm->def->cpumask ||
- (vm->def->placement_mode == VIR_DOMAIN_CPU_PLACEMENT_MODE_AUTO)) {
-
- if (vm->def->placement_mode == VIR_DOMAIN_CPU_PLACEMENT_MODE_AUTO)
- cpu_mask = virBitmapFormat(priv->autoCpuset);
- else
- cpu_mask = virBitmapFormat(vm->def->cpumask);
-
- if (!cpu_mask)
- goto cleanup;
-
- if (virCgroupSetCpusetCpus(priv->cgroup, cpu_mask) < 0)
- goto cleanup;
- }
-
- ret = 0;
- cleanup:
- VIR_FREE(cpu_mask);
- return ret;
+ return 0;
}
@@ -1079,20 +1059,27 @@ qemuSetupCgroupForVcpu(virDomainObjPtr vm)
/* Set vcpupin in cgroup if vcpupin xml is provided */
if (virCgroupHasController(priv->cgroup, VIR_CGROUP_CONTROLLER_CPUSET)) {
- /* find the right CPU to pin, otherwise
- * qemuSetupCgroupVcpuPin will fail. */
- for (j = 0; j < def->cputune.nvcpupin; j++) {
- if (def->cputune.vcpupin[j]->id != i)
- continue;
+ virBitmapPtr cpumap = NULL;
- if (qemuSetupCgroupVcpuPin(cgroup_vcpu,
- def->cputune.vcpupin,
- def->cputune.nvcpupin,
- i) < 0)
- goto cleanup;
+ /* try to use the default cpu maps */
+ if (vm->def->placement_mode == VIR_DOMAIN_CPU_PLACEMENT_MODE_AUTO)
+ cpumap = priv->autoCpuset;
+ else
+ cpumap = vm->def->cpumask;
- break;
+ /* lookup a more specific pinning info */
+ for (j = 0; j < def->cputune.nvcpupin; j++) {
+ if (def->cputune.vcpupin[j]->id == i) {
+ cpumap = def->cputune.vcpupin[j]->cpumask;
+ break;
+ }
}
+
+ if (!cpumap)
+ continue;
+
+ if (qemuSetupCgroupEmulatorPin(cgroup_vcpu, cpumap) < 0)
+ goto cleanup;
}
virCgroupFree(&cgroup_vcpu);
--
2.2.2