From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from eggs.gnu.org ([2001:4830:134:3::10]:54988) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1c0xaG-00038r-7d for qemu-devel@nongnu.org; Sun, 30 Oct 2016 17:24:05 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1c0xaE-0006o4-VR for qemu-devel@nongnu.org; Sun, 30 Oct 2016 17:24:04 -0400 Received: from mx1.redhat.com ([209.132.183.28]:60414) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1c0xaE-0006nn-Nu for qemu-devel@nongnu.org; Sun, 30 Oct 2016 17:24:02 -0400 Date: Sun, 30 Oct 2016 23:23:59 +0200 From: "Michael S. Tsirkin" Message-ID: <1477850917-1214-15-git-send-email-mst@redhat.com> References: <1477850917-1214-1-git-send-email-mst@redhat.com> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <1477850917-1214-1-git-send-email-mst@redhat.com> Subject: [Qemu-devel] [PULL 14/47] virtio: inline virtio_queue_set_host_notifier_fd_handler List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , To: qemu-devel@nongnu.org Cc: Peter Maydell , Paolo Bonzini , Cornelia Huck From: Paolo Bonzini Of the three possible parameter combinations for virtio_queue_set_host_notifier_fd_handler: - assign=true/set_handler=true is only called from virtio_device_start_ioeventfd - assign=false/set_handler=false is called from set_host_notifier_internal but it only does something when reached from virtio_device_stop_ioeventfd_impl; otherwise there is no EventNotifier set on qemu_get_aio_context(). - assign=true/set_handler=false is called from set_host_notifier_internal, but it is not doing anything: with the new start_ioeventfd and stop_ioeventfd methods, there is never an EventNotifier set on qemu_get_aio_context() at this point. This is enforced by the assertion in virtio_bus_set_host_notifier. Reviewed-by: Cornelia Huck Signed-off-by: Paolo Bonzini Reviewed-by: Michael S. Tsirkin Signed-off-by: Michael S. Tsirkin --- include/hw/virtio/virtio.h | 3 +-- hw/virtio/virtio-bus.c | 19 +++++++++++-------- hw/virtio/virtio.c | 27 +++++++++------------------ 3 files changed, 21 insertions(+), 28 deletions(-) diff --git a/include/hw/virtio/virtio.h b/include/hw/virtio/virtio.h index 2fcd23c..ac65d6a 100644 --- a/include/hw/virtio/virtio.h +++ b/include/hw/virtio/virtio.h @@ -272,8 +272,7 @@ int virtio_device_start_ioeventfd(VirtIODevice *vdev); void virtio_device_stop_ioeventfd(VirtIODevice *vdev); bool virtio_device_ioeventfd_enabled(VirtIODevice *vdev); EventNotifier *virtio_queue_get_host_notifier(VirtQueue *vq); -void virtio_queue_set_host_notifier_fd_handler(VirtQueue *vq, bool assign, - bool set_handler); +void virtio_queue_host_notifier_read(EventNotifier *n); void virtio_queue_aio_set_host_notifier_handler(VirtQueue *vq, AioContext *ctx, void (*fn)(VirtIODevice *, VirtQueue *)); diff --git a/hw/virtio/virtio-bus.c b/hw/virtio/virtio-bus.c index fd105b8..670746c 100644 --- a/hw/virtio/virtio-bus.c +++ b/hw/virtio/virtio-bus.c @@ -163,19 +163,22 @@ static int set_host_notifier_internal(DeviceState *proxy, VirtioBusState *bus, __func__, strerror(-r), r); return r; } - virtio_queue_set_host_notifier_fd_handler(vq, true, false); - r = k->ioeventfd_assign(proxy, notifier, n, assign); + r = k->ioeventfd_assign(proxy, notifier, n, true); if (r < 0) { error_report("%s: unable to assign ioeventfd: %d", __func__, r); - virtio_queue_set_host_notifier_fd_handler(vq, false, false); - event_notifier_cleanup(notifier); - return r; + goto cleanup_event_notifier; } + return 0; } else { - k->ioeventfd_assign(proxy, notifier, n, assign); - virtio_queue_set_host_notifier_fd_handler(vq, false, false); - event_notifier_cleanup(notifier); + k->ioeventfd_assign(proxy, notifier, n, false); } + +cleanup_event_notifier: + /* Test and clear notifier after disabling event, + * in case poll callback didn't have time to run. + */ + virtio_queue_host_notifier_read(notifier); + event_notifier_cleanup(notifier); return r; } diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c index b738163..bcbcfe0 100644 --- a/hw/virtio/virtio.c +++ b/hw/virtio/virtio.c @@ -2042,7 +2042,7 @@ void virtio_queue_aio_set_host_notifier_handler(VirtQueue *vq, AioContext *ctx, } } -static void virtio_queue_host_notifier_read(EventNotifier *n) +void virtio_queue_host_notifier_read(EventNotifier *n) { VirtQueue *vq = container_of(n, VirtQueue, host_notifier); if (event_notifier_test_and_clear(n)) { @@ -2050,22 +2050,6 @@ static void virtio_queue_host_notifier_read(EventNotifier *n) } } -void virtio_queue_set_host_notifier_fd_handler(VirtQueue *vq, bool assign, - bool set_handler) -{ - if (assign && set_handler) { - event_notifier_set_handler(&vq->host_notifier, true, - virtio_queue_host_notifier_read); - } else { - event_notifier_set_handler(&vq->host_notifier, true, NULL); - } - if (!assign) { - /* Test and clear notifier before after disabling event, - * in case poll callback didn't have time to run. */ - virtio_queue_host_notifier_read(&vq->host_notifier); - } -} - EventNotifier *virtio_queue_get_host_notifier(VirtQueue *vq) { return &vq->host_notifier; @@ -2148,6 +2132,7 @@ static int virtio_device_start_ioeventfd_impl(VirtIODevice *vdev) int n, r, err; for (n = 0; n < VIRTIO_QUEUE_MAX; n++) { + VirtQueue *vq = &vdev->vq[n]; if (!virtio_queue_get_num(vdev, n)) { continue; } @@ -2156,7 +2141,8 @@ static int virtio_device_start_ioeventfd_impl(VirtIODevice *vdev) err = r; goto assign_error; } - virtio_queue_set_host_notifier_fd_handler(&vdev->vq[n], true, true); + event_notifier_set_handler(&vq->host_notifier, true, + virtio_queue_host_notifier_read); } for (n = 0; n < VIRTIO_QUEUE_MAX; n++) { @@ -2171,10 +2157,12 @@ static int virtio_device_start_ioeventfd_impl(VirtIODevice *vdev) assign_error: while (--n >= 0) { + VirtQueue *vq = &vdev->vq[n]; if (!virtio_queue_get_num(vdev, n)) { continue; } + event_notifier_set_handler(&vq->host_notifier, true, NULL); r = virtio_bus_set_host_notifier(qbus, n, false); assert(r >= 0); } @@ -2195,9 +2183,12 @@ static void virtio_device_stop_ioeventfd_impl(VirtIODevice *vdev) int n, r; for (n = 0; n < VIRTIO_QUEUE_MAX; n++) { + VirtQueue *vq = &vdev->vq[n]; + if (!virtio_queue_get_num(vdev, n)) { continue; } + event_notifier_set_handler(&vq->host_notifier, true, NULL); r = virtio_bus_set_host_notifier(qbus, n, false); assert(r >= 0); } -- MST