[libvirt] [PATCH 2/3] conf: Initialize the pinning policy for vcpus

Osier Yang jyang at redhat.com
Wed Oct 10 11:14:05 UTC 2012


There are two branches to specifiy the pinning policy for vcpus.

1) def->cpuset:

   <vcpu cpuset='0-10,^6'>6</vcpu>

2) def->cputune.vcpupins:

   <cputune>
     <vcpupin vcpuid='1' cpuset='0-5'/>
   </cputune>

def->cputune.vcpupins only maintains the pinning policy only for
vcpus have <vcpupin> specified explictly, this works fine before
cgroup is widely used for domain. But since now cgroup uses
def->cputune.vcpupins to setup the cgroups for each vcpus thread,
it means the vcpus which doesn't has <vcpupin> specified will
be ignored for cgroup setting.

To fix the problem, the patch initialize vcpupin for each vcpu
which doesn't has <vcpupin> specified as def->cpuset.

Problem example without this patch:

1. % virsh start dom
Domain dom started


2. % virsh dumpxml dom
<vcpu placement='static' cpuset='3'>4</vcpu>

3. % virsh vcpuinfo dom
VCPU: 0
CPU: 0
State: running
CPU time: 8.3s
CPU Affinity: yyyyyyyy

VCPU: 1
CPU: 4
State: running
CPU time: 2.4s
CPU Affinity: yyyyyyyy

VCPU: 2
CPU: 0
State: running
CPU time: 4.1s
CPU Affinity: yyyyyyyy

VCPU: 3
CPU: 1
State: running
CPU time: 2.8s
CPU Affinity: yyyyyyyy

---
 src/conf/domain_conf.c |   35 +++++++++++++++++++++++++++++++++++
 1 files changed, 35 insertions(+), 0 deletions(-)

diff --git a/src/conf/domain_conf.c b/src/conf/domain_conf.c
index 87e0c6b..2d14489 100644
--- a/src/conf/domain_conf.c
+++ b/src/conf/domain_conf.c
@@ -8772,6 +8772,41 @@ static virDomainDefPtr virDomainDefParseXML(virCapsPtr caps,
     }
     VIR_FREE(nodes);
 
+    /* Initialize the pinning policy for vcpus which doesn't has
+     * the policy specified explicitly as def->cpuset.
+     */
+    if (def->cpumask) {
+        if (!def->cputune.vcpupin) {
+            if (VIR_ALLOC_N(def->cputune.vcpupin, def->vcpus) < 0) {
+                virReportOOMError();
+                goto error;
+            }
+        } else {
+            if (VIR_REALLOC_N(def->cputune.vcpupin, def->vcpus) < 0) {
+                virReportOOMError();
+                goto error;
+            }
+        }
+
+        for (i = 0; i < def->vcpus; i++) {
+            if (!virDomainVcpuPinIsDuplicate(def->cputune.vcpupin,
+                                             def->cputune.nvcpupin,
+                                             i)) {
+                virDomainVcpuPinDefPtr vcpupin = NULL;
+
+                if (VIR_ALLOC(vcpupin) < 0) {
+                    virReportOOMError();
+                    goto error;
+                }
+
+                vcpupin->cpumask = virBitmapNew(VIR_DOMAIN_CPUMASK_LEN);
+                virBitmapCopy(vcpupin->cpumask, def->cpumask);
+                vcpupin->vcpuid = i;
+                def->cputune.vcpupin[def->cputune.nvcpupin++] = vcpupin;
+            }
+        }
+    }
+
     if ((n = virXPathNodeSet("./cputune/emulatorpin", ctxt, &nodes)) < 0) {
         virReportError(VIR_ERR_INTERNAL_ERROR, "%s",
                        _("cannot extract emulatorpin nodes"));
-- 
1.7.7.6




More information about the libvir-list mailing list