
On Thu, 30 Jun 2011 11:08:32 +0800 Gui Jianfeng <guijianfeng@cn.fujitsu.com> wrote:
Currently, libvirt makes use of sched_setaffinity() to set Guest processes's cpu affinity. But, sometimes, for instance, when QEmu uses vhost-net, the kernel part of vhost will create a kernel thread for some purpose. In this case, such kernel thread won't inherit QEmu's cpu affinity.
Is that issue able to be fixed by cpuset ? Thanks, -Kame
This patch enables cpuset cgroup in libvirt and setting cpu affinity by configuring cpuset cgroup.
Signed-off-by: Gui Jianfeng <guijianfeng@cn.fujitsu.com>
--- src/libvirt_private.syms | 1 + src/qemu/qemu_cgroup.c | 22 ++++++++++++++++++++++ src/qemu/qemu_conf.c | 3 ++- src/util/cgroup.c | 18 ++++++++++++++++++ src/util/cgroup.h | 2 ++ 5 files changed, 45 insertions(+), 1 deletions(-)
diff --git a/src/libvirt_private.syms b/src/libvirt_private.syms index 626ac6c..e7aebc7 100644 --- a/src/libvirt_private.syms +++ b/src/libvirt_private.syms @@ -83,6 +83,7 @@ virCgroupMounted; virCgroupPathOfController; virCgroupRemove; virCgroupSetBlkioWeight; +virCgroupCpusetSetcpus; virCgroupSetCpuShares; virCgroupSetFreezerState; virCgroupSetMemory; diff --git a/src/qemu/qemu_cgroup.c b/src/qemu/qemu_cgroup.c index 1298924..eb92409 100644 --- a/src/qemu/qemu_cgroup.c +++ b/src/qemu/qemu_cgroup.c @@ -296,6 +296,28 @@ int qemuSetupCgroup(struct qemud_driver *driver, } }
+ if (vm->def->cpumask != NULL) { + if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_CPUSET)) { + char *cpumask = NULL; + if ((cpumask = + virDomainCpuSetFormat(vm->def->cpumask, vm->def->cpumasklen)) == NULL) + goto cleanup; + + rc = virCgroupCpusetSetcpus(cgroup, cpumask); + if(rc != 0) { + virReportSystemError(-rc, + _("Unable to set cpus for domain %s"), + vm->def->name); + VIR_FREE(cpumask); + goto cleanup; + } + VIR_FREE(cpumask); + } else { + qemuReportError(VIR_ERR_CONFIG_UNSUPPORTED, + _("Cpuset is not available on this host")); + } + } + if (vm->def->blkio.weight != 0) { if (qemuCgroupControllerActive(driver, VIR_CGROUP_CONTROLLER_BLKIO)) { rc = virCgroupSetBlkioWeight(cgroup, vm->def->blkio.weight); diff --git a/src/qemu/qemu_conf.c b/src/qemu/qemu_conf.c index 3d8aba4..8b478c4 100644 --- a/src/qemu/qemu_conf.c +++ b/src/qemu/qemu_conf.c @@ -307,7 +307,8 @@ int qemudLoadDriverConfig(struct qemud_driver *driver, (1 << VIR_CGROUP_CONTROLLER_CPU) | (1 << VIR_CGROUP_CONTROLLER_DEVICES) | (1 << VIR_CGROUP_CONTROLLER_MEMORY) | - (1 << VIR_CGROUP_CONTROLLER_BLKIO); + (1 << VIR_CGROUP_CONTROLLER_BLKIO) | + (1 << VIR_CGROUP_CONTROLLER_CPUSET); } for (i = 0 ; i < VIR_CGROUP_CONTROLLER_LAST ; i++) { if (driver->cgroupControllers & (1 << i)) { diff --git a/src/util/cgroup.c b/src/util/cgroup.c index 2e5ef46..89b2ad4 100644 --- a/src/util/cgroup.c +++ b/src/util/cgroup.c @@ -472,6 +472,24 @@ static int virCgroupCpuSetInherit(virCgroupPtr parent, virCgroupPtr group) return rc; }
+int virCgroupCpusetSetcpus(virCgroupPtr group, char *cpustring) +{ + int rc = 0; + const char *key = "cpuset.cpus"; + + VIR_DEBUG("Cpuset: set %s for %s/%s", cpustring, group->path, key); + + rc = virCgroupSetValueStr(group, + VIR_CGROUP_CONTROLLER_CPUSET, + key, + cpustring); + + if (rc != 0) + VIR_ERROR("Failed to set %s for %s/%s", cpustring, group->path, key); + + return rc; +} + static int virCgroupSetMemoryUseHierarchy(virCgroupPtr group) { int rc = 0; diff --git a/src/util/cgroup.h b/src/util/cgroup.h index 8ae756d..ca6a68a 100644 --- a/src/util/cgroup.h +++ b/src/util/cgroup.h @@ -30,6 +30,8 @@ enum {
VIR_ENUM_DECL(virCgroupController);
+int virCgroupCpusetSetcpus(virCgroupPtr group, char *cpustring); + int virCgroupForDriver(const char *name, virCgroupPtr *group, int privileged, -- 1.7.1