[libvirt] [PATCH 2/3 v4] [UPDATED] PowerPC : Add support for launching VMs in 'compat' mode.

Prerna Saxena prerna at linux.vnet.ibm.com
Tue Oct 28 11:13:59 UTC 2014


Apologies, I accidentally posted the older version. Pls ignore the
previously posted patch 2/3. The updated patch is here :

>From a98d6787dc4f1d39ae36d78799ecf36018377ec7 Mon Sep 17 00:00:00 2001
From: Prerna Saxena <prerna at linux.vnet.ibm.com>
Date: Tue, 28 Oct 2014 15:05:59 +0530
Subject: [PATCH 2/3] PowerPC : Add support for launching VMs in 'compat' mode.

PowerISA allows processors to run VMs in binary compatibility ("compat")
mode supporting an older version of ISA. QEMU has recently added support to
explicitly denote a VM running in compatibility mode through commit 6d9412ea
& 8dfa3a5e85.
Now, a "compat" mode VM can be run by invoking this qemu commandline on a
POWER8 host:  -cpu host,compat=power7.

This patch allows libvirt to extend the "fallback" semantics of cpu model to
describe this new mode for PowerKVM guests.
As an example:
When a user wants to request a power7 vm to run in compatibility mode on
a Power8 host, this can be described in XML as follows :
  <cpu mode='host-model' match='exact'>
    <model fallback='compat'>power7</model>
  </cpu>

Signed-off-by: Prerna Saxena <prerna at linux.vnet.ibm.com>
Signed-off-by: Li Zhang <zhlcindy at linux.vnet.ibm.com>
Signed-off-by: Pradipta Kr. Banerjee <bpradip at in.ibm.com>
---
 docs/formatdomain.html.in     | 17 ++++++++++++++++-
 docs/schemas/domaincommon.rng |  1 +
 src/conf/cpu_conf.c           |  4 +++-
 src/conf/cpu_conf.h           |  1 +
 src/cpu/cpu_powerpc.c         | 14 ++++----------
 src/qemu/qemu_command.c       | 11 ++++++++++-
 6 files changed, 35 insertions(+), 13 deletions(-)

diff --git a/docs/formatdomain.html.in b/docs/formatdomain.html.in
index 0099ce7..babca04 100644
--- a/docs/formatdomain.html.in
+++ b/docs/formatdomain.html.in
@@ -1047,7 +1047,22 @@
           (such as CPUID level) that don't work. Until these issues are fixed,
           it's a good idea to avoid using <code>host-model</code> and use
           <code>custom</code> mode with just the CPU model from host
-          capabilities XML.</dd>
+          capabilities XML.
+          <span class="since">(Since 1.2.10)</span> Libvirt on ppc64 introduces
+          a new mode <code>compat</code> to model PowerPC cpus running in binary
+          compatibility mode. PowerISA allows processors to run VMs in binary
+          compatibility ("compat") mode supporting an older version of ISA. For
+          example, when a user wants to request a power7 vm to run in
+          compatibility mode on a power8 host, this can be described in XML
+          as follows :
+<pre>
+  <cpu mode='host-model'>
+    <model fallback='compat'<power7 <model/>
+    <topology sockets='1' cores='2' threads='1'/>
+  </cpu>
+  ...</pre>
+          </dd>
+
           <dt><code>host-passthrough</code></dt>
           <dd>With this mode, the CPU visible to the guest should be exactly
           the same as the host CPU even in the aspects that libvirt does not
diff --git a/docs/schemas/domaincommon.rng b/docs/schemas/domaincommon.rng
index 20d81ae..ebab482 100644
--- a/docs/schemas/domaincommon.rng
+++ b/docs/schemas/domaincommon.rng
@@ -4067,6 +4067,7 @@
           <choice>
             <value>allow</value>
             <value>forbid</value>
+            <value>compat</value>
           </choice>
         </attribute>
       </optional>
diff --git a/src/conf/cpu_conf.c b/src/conf/cpu_conf.c
index 9b7fbb0..e12d3db 100644
--- a/src/conf/cpu_conf.c
+++ b/src/conf/cpu_conf.c
@@ -47,7 +47,8 @@ VIR_ENUM_IMPL(virCPUMatch, VIR_CPU_MATCH_LAST,
 
 VIR_ENUM_IMPL(virCPUFallback, VIR_CPU_FALLBACK_LAST,
               "allow",
-              "forbid")
+              "forbid",
+              "compat")
 
 VIR_ENUM_IMPL(virCPUFeaturePolicy, VIR_CPU_FEATURE_LAST,
               "force",
@@ -619,6 +620,7 @@ virCPUDefFormatBuf(virBufferPtr buf,
         return 0;
 
     formatModel = (def->mode == VIR_CPU_MODE_CUSTOM ||
+                   def->mode == VIR_CPU_MODE_HOST_MODEL ||
                    (flags & VIR_DOMAIN_XML_UPDATE_CPU));
     formatFallback = (def->type == VIR_CPU_TYPE_GUEST &&
                       (def->mode == VIR_CPU_MODE_HOST_MODEL ||
diff --git a/src/conf/cpu_conf.h b/src/conf/cpu_conf.h
index d45210b..69d8584 100644
--- a/src/conf/cpu_conf.h
+++ b/src/conf/cpu_conf.h
@@ -65,6 +65,7 @@ VIR_ENUM_DECL(virCPUMatch)
 typedef enum {
     VIR_CPU_FALLBACK_ALLOW,
     VIR_CPU_FALLBACK_FORBID,
+    VIR_CPU_FALLBACK_COMPAT,
 
     VIR_CPU_FALLBACK_LAST
 } virCPUFallback;
diff --git a/src/cpu/cpu_powerpc.c b/src/cpu/cpu_powerpc.c
index d591c18..abe9047 100644
--- a/src/cpu/cpu_powerpc.c
+++ b/src/cpu/cpu_powerpc.c
@@ -479,7 +479,8 @@ ppcDecode(virCPUDefPtr cpu,
         goto cleanup;
     }
 
-    if (!cpuModelIsAllowed(model->name, models, nmodels)) {
+    if (cpu->fallback != VIR_CPU_FALLBACK_COMPAT &&
+        !cpuModelIsAllowed(model->name, models, nmodels)) {
         virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
                        _("CPU model %s is not supported by hypervisor"),
                        model->name);
@@ -562,8 +563,8 @@ ppcUpdate(virCPUDefPtr guest,
 static virCPUDefPtr
 ppcBaseline(virCPUDefPtr *cpus,
             unsigned int ncpus,
-            const char **models,
-            unsigned int nmodels,
+            const char **models ATTRIBUTE_UNUSED,
+            unsigned int nmodels ATTRIBUTE_UNUSED,
             unsigned int flags)
 {
     struct ppc_map *map = NULL;
@@ -583,13 +584,6 @@ ppcBaseline(virCPUDefPtr *cpus,
         goto error;
     }
 
-    if (!cpuModelIsAllowed(model->name, models, nmodels)) {
-        virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
-                        _("CPU model %s is not supported by hypervisor"),
-                        model->name);
-        goto error;
-    }
-
     for (i = 0; i < ncpus; i++) {
         const struct ppc_vendor *vnd;
 
diff --git a/src/qemu/qemu_command.c b/src/qemu/qemu_command.c
index d60f274..3143bd8 100644
--- a/src/qemu/qemu_command.c
+++ b/src/qemu/qemu_command.c
@@ -6221,7 +6221,9 @@ qemuBuildCpuModelArgStr(virQEMUDriverPtr driver,
         *hasHwVirt = hasSVM > 0 ? true : false;
     }
 
-    if (cpu->mode == VIR_CPU_MODE_HOST_PASSTHROUGH) {
+    if ((cpu->mode == VIR_CPU_MODE_HOST_PASSTHROUGH) ||
+        ((cpu->mode == VIR_CPU_MODE_HOST_MODEL) &&
+          ARCH_IS_PPC64(def->os.arch))) {
         const char *mode = virCPUModeTypeToString(cpu->mode);
         if (!virQEMUCapsGet(qemuCaps, QEMU_CAPS_CPU_HOST)) {
             virReportError(VIR_ERR_CONFIG_UNSUPPORTED,
@@ -6236,6 +6238,13 @@ qemuBuildCpuModelArgStr(virQEMUDriverPtr driver,
             goto cleanup;
         }
         virBufferAddLit(buf, "host");
+
+        if (ARCH_IS_PPC64(def->os.arch) &&
+            cpu->mode == VIR_CPU_MODE_HOST_MODEL &&
+            cpu->fallback == VIR_CPU_FALLBACK_COMPAT) {
+            virBufferAsprintf(buf, ",compat=%s", def->cpu->model);
+        }
+
     } else {
         if (VIR_ALLOC(guest) < 0)
             goto cleanup;
-- 
1.9.3




More information about the libvir-list mailing list