target-ppc: Allow eventual removal of old migration mistakes
authorDavid Gibson <david@gibson.dropbear.id.au>
Mon, 21 Nov 2016 05:29:30 +0000 (16:29 +1100)
committerDavid Gibson <david@gibson.dropbear.id.au>
Wed, 23 Nov 2016 01:00:48 +0000 (12:00 +1100)
Until very recently, the vmstate for ppc cpus included some poorly
thought out VMSTATE_EQUAL() components, that can easily break
migration compatibility, and did so between qemu-2.6 and later
versions.  A hack was recently added which fixes this migration
breakage, but it leaves the unhelpful cruft of these fields in the
migration stream.

This patch adds a new cpu property allowing these fields to be removed
from the stream entirely.  For the pseries-2.8 machine type - which
comes after the fix - and for all non-pseries machine types - which
aren't mature enough to care about cross-version migration - we remove
the fields from the stream.

For pseries-2.7 and earlier, The migration hack remains in place,
allowing backwards and forwards migration with the older machine
types.

This restricts the migration compatibility cruft to older machine
types, and at least opens the possibility of eventually deprecating
and removing it entirely.

Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
Reviewed-by: Dr. David Alan Gilbert <dgilbert@redhat.com>
Reviewed-by: Thomas Huth <thuth@redhat.com>
Reviewed-by: Greg Kurz <groug@kaod.org>
Reviewed-by: Alexey Kardashevskiy <aik@ozlabs.ru>
hw/ppc/spapr.c
target-ppc/cpu.h
target-ppc/machine.c
target-ppc/translate_init.c

index 54b88d3f94bc11ac98c22aa0f8cb06aa142a8b32..775ad2e1d9c042659240d573e5c60bb46539518e 100644 (file)
@@ -2767,6 +2767,11 @@ DEFINE_SPAPR_MACHINE(2_8, "2.8", true);
         .driver   = TYPE_SPAPR_PCI_HOST_BRIDGE,     \
         .property = "mem64_win_size",               \
         .value    = "0",                            \
+    },                                              \
+    {                                               \
+        .driver = TYPE_POWERPC_CPU,                 \
+        .property = "pre-2.8-migration",            \
+        .value    = "on",                           \
     },
 
 static void phb_placement_2_7(sPAPRMachineState *spapr, uint32_t index,
index 7798b2ec2382caffe77f59fe2e1c0b8abc42d38e..2a50c43689379bb598d95a069ec1ab1d81175d25 100644 (file)
@@ -1167,7 +1167,8 @@ struct PowerPCCPU {
     uint32_t max_compat;
     uint32_t cpu_version;
 
-    /* fields used only during migration for compatibility hacks */
+    /* Fields related to migration compatibility hacks */
+    bool pre_2_8_migration;
     target_ulong mig_msr_mask;
     uint64_t mig_insns_flags;
     uint64_t mig_insns_flags2;
index fcac263c7dea759c3262a6d8557acc10a2bab047..18c16d251254867cf6cfbb6fe271ba03c1111d42 100644 (file)
@@ -135,6 +135,13 @@ static const VMStateInfo vmstate_info_avr = {
 #define VMSTATE_AVR_ARRAY(_f, _s, _n)                             \
     VMSTATE_AVR_ARRAY_V(_f, _s, _n, 0)
 
+static bool cpu_pre_2_8_migration(void *opaque, int version_id)
+{
+    PowerPCCPU *cpu = opaque;
+
+    return cpu->pre_2_8_migration;
+}
+
 static void cpu_pre_save(void *opaque)
 {
     PowerPCCPU *cpu = opaque;
@@ -178,10 +185,12 @@ static void cpu_pre_save(void *opaque)
     }
 
     /* Hacks for migration compatibility between 2.6, 2.7 & 2.8 */
-    cpu->mig_msr_mask = env->msr_mask;
-    cpu->mig_insns_flags = env->insns_flags & insns_compat_mask;
-    cpu->mig_insns_flags2 = env->insns_flags2 & insns_compat_mask2;
-    cpu->mig_nb_BATs = env->nb_BATs;
+    if (cpu->pre_2_8_migration) {
+        cpu->mig_msr_mask = env->msr_mask;
+        cpu->mig_insns_flags = env->insns_flags & insns_compat_mask;
+        cpu->mig_insns_flags2 = env->insns_flags2 & insns_compat_mask2;
+        cpu->mig_nb_BATs = env->nb_BATs;
+    }
 }
 
 static int cpu_post_load(void *opaque, int version_id)
@@ -582,10 +591,11 @@ const VMStateDescription vmstate_ppc_cpu = {
         /* FIXME: access_type? */
 
         /* Sanity checking */
-        VMSTATE_UINTTL(mig_msr_mask, PowerPCCPU),
-        VMSTATE_UINT64(mig_insns_flags, PowerPCCPU),
-        VMSTATE_UINT64(mig_insns_flags2, PowerPCCPU),
-        VMSTATE_UINT32(mig_nb_BATs, PowerPCCPU),
+        VMSTATE_UINTTL_TEST(mig_msr_mask, PowerPCCPU, cpu_pre_2_8_migration),
+        VMSTATE_UINT64_TEST(mig_insns_flags, PowerPCCPU, cpu_pre_2_8_migration),
+        VMSTATE_UINT64_TEST(mig_insns_flags2, PowerPCCPU,
+                            cpu_pre_2_8_migration),
+        VMSTATE_UINT32_TEST(mig_nb_BATs, PowerPCCPU, cpu_pre_2_8_migration),
         VMSTATE_END_OF_LIST()
     },
     .subsections = (const VMStateDescription*[]) {
index 208fa1ea534c3538eff2ca39f777be43c7d0f302..626e03186cdacd71c5b19ccc626dd8476df5897b 100644 (file)
@@ -10520,6 +10520,11 @@ static gchar *ppc_gdb_arch_name(CPUState *cs)
 #endif
 }
 
+static Property ppc_cpu_properties[] = {
+    DEFINE_PROP_BOOL("pre-2.8-migration", PowerPCCPU, pre_2_8_migration, false),
+    DEFINE_PROP_END_OF_LIST(),
+};
+
 static void ppc_cpu_class_init(ObjectClass *oc, void *data)
 {
     PowerPCCPUClass *pcc = POWERPC_CPU_CLASS(oc);
@@ -10532,6 +10537,7 @@ static void ppc_cpu_class_init(ObjectClass *oc, void *data)
     pcc->interrupts_big_endian = ppc_cpu_interrupts_big_endian_always;
     dc->realize = ppc_cpu_realizefn;
     dc->unrealize = ppc_cpu_unrealizefn;
+    dc->props = ppc_cpu_properties;
 
     pcc->parent_reset = cc->reset;
     cc->reset = ppc_cpu_reset;