thebeanogamer / rpms / qemu-kvm

Forked from rpms/qemu-kvm 5 months ago
Clone
ed5979
From 9fb47ad317ad8cdda9960190d499ad6c3a9817f0 Mon Sep 17 00:00:00 2001
ed5979
From: Greg Kurz <groug@kaod.org>
ed5979
Date: Thu, 19 Jan 2023 18:24:23 +0100
ed5979
Subject: [PATCH 18/20] Revert "vhost-user: Monitor slave channel in
ed5979
 vhost_user_read()"
ed5979
MIME-Version: 1.0
ed5979
Content-Type: text/plain; charset=UTF-8
ed5979
Content-Transfer-Encoding: 8bit
ed5979
ed5979
RH-Author: Laurent Vivier <lvivier@redhat.com>
ed5979
RH-MergeRequest: 146: Fix vhost-user with dpdk
ed5979
RH-Bugzilla: 2155173
ed5979
RH-Acked-by: Cindy Lu <lulu@redhat.com>
ed5979
RH-Acked-by: Greg Kurz (RH) <gkurz@redhat.com>
ed5979
RH-Acked-by: Eugenio PĂ©rez <eperezma@redhat.com>
ed5979
RH-Commit: [1/2] c583a7f121ca9c93c9a2ad17bf0ccf5c1241dc99 (lvivier/qemu-kvm-centos)
ed5979
ed5979
This reverts commit db8a3772e300c1a656331a92da0785d81667dc81.
ed5979
ed5979
Motivation : this is breaking vhost-user with DPDK as reported in [0].
ed5979
ed5979
Received unexpected msg type. Expected 22 received 40
ed5979
Fail to update device iotlb
ed5979
Received unexpected msg type. Expected 40 received 22
ed5979
Received unexpected msg type. Expected 22 received 11
ed5979
Fail to update device iotlb
ed5979
Received unexpected msg type. Expected 11 received 22
ed5979
vhost VQ 1 ring restore failed: -71: Protocol error (71)
ed5979
Received unexpected msg type. Expected 22 received 11
ed5979
Fail to update device iotlb
ed5979
Received unexpected msg type. Expected 11 received 22
ed5979
vhost VQ 0 ring restore failed: -71: Protocol error (71)
ed5979
unable to start vhost net: 71: falling back on userspace virtio
ed5979
ed5979
The failing sequence that leads to the first error is :
ed5979
- QEMU sends a VHOST_USER_GET_STATUS (40) request to DPDK on the master
ed5979
  socket
ed5979
- QEMU starts a nested event loop in order to wait for the
ed5979
  VHOST_USER_GET_STATUS response and to be able to process messages from
ed5979
  the slave channel
ed5979
- DPDK sends a couple of legitimate IOTLB miss messages on the slave
ed5979
  channel
ed5979
- QEMU processes each IOTLB request and sends VHOST_USER_IOTLB_MSG (22)
ed5979
  updates on the master socket
ed5979
- QEMU assumes to receive a response for the latest VHOST_USER_IOTLB_MSG
ed5979
  but it gets the response for the VHOST_USER_GET_STATUS instead
ed5979
ed5979
The subsequent errors have the same root cause : the nested event loop
ed5979
breaks the order by design. It lures QEMU to expect responses to the
ed5979
latest message sent on the master socket to arrive first.
ed5979
ed5979
Since this was only needed for DAX enablement which is still not merged
ed5979
upstream, just drop the code for now. A working solution will have to
ed5979
be merged later on. Likely protect the master socket with a mutex
ed5979
and service the slave channel with a separate thread, as discussed with
ed5979
Maxime in the mail thread below.
ed5979
ed5979
[0] https://lore.kernel.org/qemu-devel/43145ede-89dc-280e-b953-6a2b436de395@redhat.com/
ed5979
ed5979
Reported-by: Yanghang Liu <yanghliu@redhat.com>
ed5979
Buglink: https://bugzilla.redhat.com/show_bug.cgi?id=2155173
ed5979
Signed-off-by: Greg Kurz <groug@kaod.org>
ed5979
Message-Id: <20230119172424.478268-2-groug@kaod.org>
ed5979
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
ed5979
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
ed5979
Acked-by: Stefan Hajnoczi <stefanha@redhat.com>
ed5979
Acked-by: Maxime Coquelin <maxime.coquelin@redhat.com>
ed5979
(cherry picked from commit f340a59d5a852d75ae34555723694c7e8eafbd0c)
ed5979
Signed-off-by: Laurent Vivier <lvivier@redhat.com>
ed5979
---
ed5979
 hw/virtio/vhost-user.c | 35 +++--------------------------------
ed5979
 1 file changed, 3 insertions(+), 32 deletions(-)
ed5979
ed5979
diff --git a/hw/virtio/vhost-user.c b/hw/virtio/vhost-user.c
ed5979
index 8f635844af..0ac00eb901 100644
ed5979
--- a/hw/virtio/vhost-user.c
ed5979
+++ b/hw/virtio/vhost-user.c
ed5979
@@ -356,35 +356,6 @@ end:
ed5979
     return G_SOURCE_REMOVE;
ed5979
 }
ed5979
 
ed5979
-static gboolean slave_read(QIOChannel *ioc, GIOCondition condition,
ed5979
-                           gpointer opaque);
ed5979
-
ed5979
-/*
ed5979
- * This updates the read handler to use a new event loop context.
ed5979
- * Event sources are removed from the previous context : this ensures
ed5979
- * that events detected in the previous context are purged. They will
ed5979
- * be re-detected and processed in the new context.
ed5979
- */
ed5979
-static void slave_update_read_handler(struct vhost_dev *dev,
ed5979
-                                      GMainContext *ctxt)
ed5979
-{
ed5979
-    struct vhost_user *u = dev->opaque;
ed5979
-
ed5979
-    if (!u->slave_ioc) {
ed5979
-        return;
ed5979
-    }
ed5979
-
ed5979
-    if (u->slave_src) {
ed5979
-        g_source_destroy(u->slave_src);
ed5979
-        g_source_unref(u->slave_src);
ed5979
-    }
ed5979
-
ed5979
-    u->slave_src = qio_channel_add_watch_source(u->slave_ioc,
ed5979
-                                                G_IO_IN | G_IO_HUP,
ed5979
-                                                slave_read, dev, NULL,
ed5979
-                                                ctxt);
ed5979
-}
ed5979
-
ed5979
 static int vhost_user_read(struct vhost_dev *dev, VhostUserMsg *msg)
ed5979
 {
ed5979
     struct vhost_user *u = dev->opaque;
ed5979
@@ -406,7 +377,6 @@ static int vhost_user_read(struct vhost_dev *dev, VhostUserMsg *msg)
ed5979
      * be prepared for re-entrancy. So we create a new one and switch chr
ed5979
      * to use it.
ed5979
      */
ed5979
-    slave_update_read_handler(dev, ctxt);
ed5979
     qemu_chr_be_update_read_handlers(chr->chr, ctxt);
ed5979
     qemu_chr_fe_add_watch(chr, G_IO_IN | G_IO_HUP, vhost_user_read_cb, &data);
ed5979
 
ed5979
@@ -418,7 +388,6 @@ static int vhost_user_read(struct vhost_dev *dev, VhostUserMsg *msg)
ed5979
      * context that have been processed by the nested loop are purged.
ed5979
      */
ed5979
     qemu_chr_be_update_read_handlers(chr->chr, prev_ctxt);
ed5979
-    slave_update_read_handler(dev, NULL);
ed5979
 
ed5979
     g_main_loop_unref(loop);
ed5979
     g_main_context_unref(ctxt);
ed5979
@@ -1802,7 +1771,9 @@ static int vhost_setup_slave_channel(struct vhost_dev *dev)
ed5979
         return -ECONNREFUSED;
ed5979
     }
ed5979
     u->slave_ioc = ioc;
ed5979
-    slave_update_read_handler(dev, NULL);
ed5979
+    u->slave_src = qio_channel_add_watch_source(u->slave_ioc,
ed5979
+                                                G_IO_IN | G_IO_HUP,
ed5979
+                                                slave_read, dev, NULL, NULL);
ed5979
 
ed5979
     if (reply_supported) {
ed5979
         msg.hdr.flags |= VHOST_USER_NEED_REPLY_MASK;
ed5979
-- 
ed5979
2.31.1
ed5979