From 9a30ebb516ed4789369c04c05685649ebd50b6c7 Mon Sep 17 00:00:00 2001 From: "Dr. David Alan Gilbert" Date: Wed, 12 Oct 2016 23:38:28 +0200 Subject: [PATCH 4/6] Workaround rhel6 ctrl_guest_offloads machine type mismatch RH-Author: Dr. David Alan Gilbert Message-id: <20161012173828.21399-2-dgilbert@redhat.com> Patchwork-id: 72511 O-Subject: [RHEL-7.4/7.3.z qemu-kvm-rhev PATCH 1/1] Workaround rhel6 ctrl_guest_offloads machine type mismatch Bugzilla: 1392876 RH-Acked-by: Paolo Bonzini RH-Acked-by: Michael S. Tsirkin RH-Acked-by: Laszlo Ersek From: "Dr. David Alan Gilbert" RHEL6's 6.5 and 6.6 machine types enable the ctrl_guest_offloads feature on virtio-net-pci, unfortunately RHEL7's definition of the 6.5 and 6.6 machine types are missing that flag. This works around it by allowing an incoming migration with the guest flag set (for the bad machine types). Fixing the machine type definitions would break migration from this version to an earlier 7.x. Note: Restarting the VM after this import will still keep the old (broken) machine type and turn the feature off. Signed-off-by: Dr. David Alan Gilbert Signed-off-by: Miroslav Rezanina --- hw/i386/pc_piix.c | 10 ++++++++++ hw/virtio/virtio.c | 22 +++++++++++++++++++++- include/hw/virtio/virtio.h | 1 + 3 files changed, 32 insertions(+), 1 deletion(-) diff --git a/hw/i386/pc_piix.c b/hw/i386/pc_piix.c index 002945b..ba04b47 100644 --- a/hw/i386/pc_piix.c +++ b/hw/i386/pc_piix.c @@ -1478,6 +1478,11 @@ DEFINE_PC_MACHINE(rhel700, "pc-i440fx-rhel7.0.0", pc_init_rhel700, .driver = TYPE_X86_CPU,\ .property = "3dnowext",\ .value = "off",\ + },\ + {\ + .driver = "virtio-net-pci",\ + .property = "__com.redhat_rhel6_ctrl_guest_workaround", \ + .value = "on",\ }, static void pc_compat_rhel660(MachineState *machine) @@ -1572,6 +1577,11 @@ DEFINE_PC_MACHINE(rhel650, "rhel6.5.0", pc_init_rhel650, .driver = TYPE_X86_CPU,\ .property = "sep",\ .value = "off",\ + },\ + {\ + .driver = "virtio-net-pci",\ + .property = "__com.redhat_rhel6_ctrl_guest_workaround", \ + .value = "off",\ }, static void pc_compat_rhel640(MachineState *machine) diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c index f22099f..94edd61 100644 --- a/hw/virtio/virtio.c +++ b/hw/virtio/virtio.c @@ -24,6 +24,7 @@ #include "migration/migration.h" #include "hw/virtio/virtio-access.h" +#include "standard-headers/linux/virtio_net.h" /* * The alignment to use between consumer and producer parts of vring. * x86 pagesize again. This is the default, used by transports like PCI @@ -1461,7 +1462,24 @@ void virtio_save(VirtIODevice *vdev, QEMUFile *f) static int virtio_set_features_nocheck(VirtIODevice *vdev, uint64_t val) { VirtioDeviceClass *k = VIRTIO_DEVICE_GET_CLASS(vdev); - bool bad = (val & ~(vdev->host_features)) != 0; + bool bad; + uint64_t ctrl_guest_mask = 1ull << VIRTIO_NET_F_CTRL_GUEST_OFFLOADS; + + if (vdev->rhel6_ctrl_guest_workaround && (val & ctrl_guest_mask) && + !(vdev->host_features & ctrl_guest_mask)) { + /* + * This works around a mistake in the definition of the rhel6.[56].0 + * machinetypes, ctrl-guest-offload was not set in qemu-kvm-rhev for + * those machine types, but is set on the rhel6 qemu-kvm-rhev build. + * If an incoming rhel6 guest uses it then we need to allow it. + * Note: There's a small race where a guest read the flag but didn't + * declare it's useage yet. + */ + fprintf(stderr, "RHEL6 ctrl_guest_offload workaround\n"); + vdev->host_features |= ctrl_guest_mask; + } + + bad = (val & ~(vdev->host_features)) != 0; val &= vdev->host_features; if (k->set_features) { @@ -1927,6 +1945,8 @@ static void virtio_device_unrealize(DeviceState *dev, Error **errp) static Property virtio_properties[] = { DEFINE_VIRTIO_COMMON_FEATURES(VirtIODevice, host_features), + DEFINE_PROP_BOOL("__com.redhat_rhel6_ctrl_guest_workaround", VirtIODevice, + rhel6_ctrl_guest_workaround, false), DEFINE_PROP_END_OF_LIST(), }; diff --git a/include/hw/virtio/virtio.h b/include/hw/virtio/virtio.h index 6a37065..dffd387 100644 --- a/include/hw/virtio/virtio.h +++ b/include/hw/virtio/virtio.h @@ -91,6 +91,7 @@ struct VirtIODevice char *bus_name; uint8_t device_endian; bool use_guest_notifier_mask; + bool rhel6_ctrl_guest_workaround; QLIST_HEAD(, VirtQueue) *vector_queues; }; -- 1.8.3.1