From nobody Tue Nov 11 03:16:11 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1561110126; cv=none; d=zoho.com; s=zohoarc; b=e3yqO/VanwyJ+nLZawthYJyL6P89xpFagszz5gWPfvWIEm3fu5mmNeFSt95jrCiDOpWN2RXqaZAaudB6Gm/C38Lfb34UExrZiFjxKqT09mT+Y5TiAJ80UL9xD2CZfuG9zz5i9dUXcMAFN/z8y4j6I4/zGW84N/CfEDuw4NPzY+Y= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zoho.com; s=zohoarc; t=1561110126; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To:ARC-Authentication-Results; bh=gxXaaEXWqUSiZErDET4DPnC4ZMMwK923givk9eD4X6s=; b=KrR58LEokQsBOinHIxlKOhC/aVazXrcWxjaiL4sVBxJRErAEKdxU+e4ybsUcWo9UxigMctr39TCUIc8R8AQrlHvVPafTAJNx9U95j2bLzj2IGA3RNcK2cASArk+JfBi1OXfmw6B/YZFnn5BVtfLmjyAKHz6/0OBY/KW5/qMGTEk= ARC-Authentication-Results: i=1; mx.zoho.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail header.from= (p=none dis=none) header.from= Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1561110126193403.41637892982067; Fri, 21 Jun 2019 02:42:06 -0700 (PDT) Received: from localhost ([::1]:57468 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG3W-0005sh-Ug for importer@patchew.org; Fri, 21 Jun 2019 05:42:02 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:49454) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG23-0004d8-IY for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:34 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1heG20-0002MG-GX for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:31 -0400 Received: from mx1.redhat.com ([209.132.183.28]:51446) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1heG20-0002LQ-C8 for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:28 -0400 Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.phx2.redhat.com [10.5.11.16]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 5D67A3082E21; Fri, 21 Jun 2019 09:40:27 +0000 (UTC) Received: from localhost (ovpn-117-248.ams2.redhat.com [10.36.117.248]) by smtp.corp.redhat.com (Postfix) with ESMTP id 1F3145C22B; Fri, 21 Jun 2019 09:40:17 +0000 (UTC) From: Stefan Hajnoczi To: Date: Fri, 21 Jun 2019 10:40:02 +0100 Message-Id: <20190621094005.4134-2-stefanha@redhat.com> In-Reply-To: <20190621094005.4134-1-stefanha@redhat.com> References: <20190621094005.4134-1-stefanha@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.16 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.46]); Fri, 21 Jun 2019 09:40:27 +0000 (UTC) Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] X-Received-From: 209.132.183.28 Subject: [Qemu-devel] [PATCH 1/4] libvhost-user: add vmsg_set_reply_u64() helper X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Michael S. Tsirkin" , "Dr. David Alan Gilbert" , Sebastien Boeuf , Gerd Hoffmann , Stefan Hajnoczi , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" Content-Type: text/plain; charset="utf-8" The VhostUserMsg request is reused as the reply by message processing functions. This is risky since request fields may corrupt the reply if the vhost-user message handler function forgets to re-initialize them. Changing this practice would be very invasive but we can introduce a helper function to make u64 payload replies safe. This also eliminates code duplication in message processing functions. Signed-off-by: Stefan Hajnoczi Reviewed-by: Marc-Andr=C3=A9 Lureau --- contrib/libvhost-user/libvhost-user.c | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/contrib/libvhost-user/libvhost-user.c b/contrib/libvhost-user/= libvhost-user.c index 443b7e08c3..a8657c7af2 100644 --- a/contrib/libvhost-user/libvhost-user.c +++ b/contrib/libvhost-user/libvhost-user.c @@ -216,6 +216,15 @@ vmsg_close_fds(VhostUserMsg *vmsg) } } =20 +/* Set reply payload.u64 and clear request flags and fd_num */ +static void vmsg_set_reply_u64(VhostUserMsg *vmsg, uint64_t val) +{ + vmsg->flags =3D 0; /* defaults will be set by vu_send_reply() */ + vmsg->size =3D sizeof(vmsg->payload.u64); + vmsg->payload.u64 =3D val; + vmsg->fd_num =3D 0; +} + /* A test to see if we have userfault available */ static bool have_userfault(void) @@ -1168,10 +1177,7 @@ vu_get_protocol_features_exec(VuDev *dev, VhostUserM= sg *vmsg) features |=3D dev->iface->get_protocol_features(dev); } =20 - vmsg->payload.u64 =3D features; - vmsg->size =3D sizeof(vmsg->payload.u64); - vmsg->fd_num =3D 0; - + vmsg_set_reply_u64(vmsg, features); return true; } =20 @@ -1307,17 +1313,14 @@ out: static bool vu_set_postcopy_listen(VuDev *dev, VhostUserMsg *vmsg) { - vmsg->payload.u64 =3D -1; - vmsg->size =3D sizeof(vmsg->payload.u64); - if (dev->nregions) { vu_panic(dev, "Regions already registered at postcopy-listen"); + vmsg_set_reply_u64(vmsg, -1); return true; } dev->postcopy_listening =3D true; =20 - vmsg->flags =3D VHOST_USER_VERSION | VHOST_USER_REPLY_MASK; - vmsg->payload.u64 =3D 0; /* Success */ + vmsg_set_reply_u64(vmsg, 0); return true; } =20 @@ -1332,10 +1335,7 @@ vu_set_postcopy_end(VuDev *dev, VhostUserMsg *vmsg) DPRINT("%s: Done close\n", __func__); } =20 - vmsg->fd_num =3D 0; - vmsg->payload.u64 =3D 0; - vmsg->size =3D sizeof(vmsg->payload.u64); - vmsg->flags =3D VHOST_USER_VERSION | VHOST_USER_REPLY_MASK; + vmsg_set_reply_u64(vmsg, 0); DPRINT("%s: exit\n", __func__); return true; } --=20 2.21.0 From nobody Tue Nov 11 03:16:11 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1561110163; cv=none; d=zoho.com; s=zohoarc; b=e0zN+sxBUp1w2UffUDpYqL9z4bbuMJL2u6Jb7aJA6eSFBnxqtWdrE8itf0NpMEd6SDtt7CjcQvUnLV0xl2URVQShhKMPSm2D28b3YyQQOJ9GBfLN2/U2pfqkPvonDqysthg7/M11DmQc/ke3PZ4bOAPnx30JL42KOgsz7aazGy4= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zoho.com; s=zohoarc; t=1561110163; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To:ARC-Authentication-Results; bh=GPWrmS2FBo5ixhyJdnoulHFAG2gklMH2ZDBghuCPIY0=; b=PmZXkXKyu63Ppu9LlMqpF357TEV3NY7ecHxOv+QC8euBF6sRphOCbc8fjVR1n3GAlzlLxosXKJXuH4OdhcvqMh+spBLTBRGs/aDBheS71OlYWzltKqUmjvjv6r8jTQAsaFMvPAtVKC1MUekxzdnqeWKL3O0WvliSuMB7PmM9Cow= ARC-Authentication-Results: i=1; mx.zoho.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail header.from= (p=none dis=none) header.from= Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 156111016391259.51521972009368; Fri, 21 Jun 2019 02:42:43 -0700 (PDT) Received: from localhost ([::1]:57470 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG48-0006C0-9n for importer@patchew.org; Fri, 21 Jun 2019 05:42:42 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:49486) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG2F-0004ox-M7 for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:46 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1heG2C-0002RK-Jw for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:43 -0400 Received: from mx1.redhat.com ([209.132.183.28]:41650) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1heG2B-0002Qg-0F for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:39 -0400 Received: from smtp.corp.redhat.com (int-mx02.intmail.prod.int.phx2.redhat.com [10.5.11.12]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 5A43F3091786; Fri, 21 Jun 2019 09:40:38 +0000 (UTC) Received: from localhost (ovpn-117-248.ams2.redhat.com [10.36.117.248]) by smtp.corp.redhat.com (Postfix) with ESMTP id B23F160FAB; Fri, 21 Jun 2019 09:40:28 +0000 (UTC) From: Stefan Hajnoczi To: Date: Fri, 21 Jun 2019 10:40:03 +0100 Message-Id: <20190621094005.4134-3-stefanha@redhat.com> In-Reply-To: <20190621094005.4134-1-stefanha@redhat.com> References: <20190621094005.4134-1-stefanha@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.79 on 10.5.11.12 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.41]); Fri, 21 Jun 2019 09:40:38 +0000 (UTC) Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] X-Received-From: 209.132.183.28 Subject: [Qemu-devel] [PATCH 2/4] libvhost-user: support many virtqueues X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Michael S. Tsirkin" , "Dr. David Alan Gilbert" , Sebastien Boeuf , Gerd Hoffmann , Stefan Hajnoczi , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" Content-Type: text/plain; charset="utf-8" Currently libvhost-user is hardcoded to at most 8 virtqueues. The device backend should decide the number of virtqueues, not libvhost-user. This is important for multiqueue device backends where the guest driver needs an accurate number of virtqueues. This change breaks libvhost-user and libvhost-user-glib API stability. There is no stability guarantee yet, so make this change now and update all in-tree library users. This patch touches up vhost-user-blk, vhost-user-gpu, vhost-user-input, vhost-user-scsi, and vhost-user-bridge. If the device has a fixed number of queues that exact number is used. Otherwise the previous default of 8 virtqueues is used. vu_init() and vug_init() can now fail if malloc() returns NULL. I considered aborting with an error in libvhost-user but it should be safe to instantiate new vhost-user instances at runtime without risk of terminating the process. Therefore callers need to handle the vu_init() failure now. vhost-user-blk and vhost-user-scsi duplicate virtqueue index checks that are already performed by libvhost-user. This code would need to be modified to use max_queues but remove it completely instead since it's redundant. Signed-off-by: Stefan Hajnoczi Reviewed-by: Marc-Andr=C3=A9 Lureau --- contrib/libvhost-user/libvhost-user-glib.h | 2 +- contrib/libvhost-user/libvhost-user.h | 10 ++++-- contrib/libvhost-user/libvhost-user-glib.c | 12 +++++-- contrib/libvhost-user/libvhost-user.c | 32 ++++++++++++----- contrib/vhost-user-blk/vhost-user-blk.c | 16 +++++---- contrib/vhost-user-gpu/main.c | 9 ++++- contrib/vhost-user-input/main.c | 11 +++++- contrib/vhost-user-scsi/vhost-user-scsi.c | 21 +++++------ tests/vhost-user-bridge.c | 42 ++++++++++++++-------- 9 files changed, 104 insertions(+), 51 deletions(-) diff --git a/contrib/libvhost-user/libvhost-user-glib.h b/contrib/libvhost-= user/libvhost-user-glib.h index d3200f3afc..64d539d93a 100644 --- a/contrib/libvhost-user/libvhost-user-glib.h +++ b/contrib/libvhost-user/libvhost-user-glib.h @@ -25,7 +25,7 @@ typedef struct VugDev { GSource *src; } VugDev; =20 -void vug_init(VugDev *dev, int socket, +bool vug_init(VugDev *dev, uint16_t max_queues, int socket, vu_panic_cb panic, const VuDevIface *iface); void vug_deinit(VugDev *dev); =20 diff --git a/contrib/libvhost-user/libvhost-user.h b/contrib/libvhost-user/= libvhost-user.h index 3b888ff0a5..46b600799b 100644 --- a/contrib/libvhost-user/libvhost-user.h +++ b/contrib/libvhost-user/libvhost-user.h @@ -25,7 +25,6 @@ #define VHOST_USER_F_PROTOCOL_FEATURES 30 #define VHOST_LOG_PAGE 4096 =20 -#define VHOST_MAX_NR_VIRTQUEUE 8 #define VIRTQUEUE_MAX_SIZE 1024 =20 #define VHOST_MEMORY_MAX_NREGIONS 8 @@ -353,7 +352,7 @@ struct VuDev { int sock; uint32_t nregions; VuDevRegion regions[VHOST_MEMORY_MAX_NREGIONS]; - VuVirtq vq[VHOST_MAX_NR_VIRTQUEUE]; + VuVirtq *vq; VuDevInflightInfo inflight_info; int log_call_fd; int slave_fd; @@ -362,6 +361,7 @@ struct VuDev { uint64_t features; uint64_t protocol_features; bool broken; + uint16_t max_queues; =20 /* @set_watch: add or update the given fd to the watch set, * call cb when condition is met */ @@ -391,6 +391,7 @@ typedef struct VuVirtqElement { /** * vu_init: * @dev: a VuDev context + * @max_queues: maximum number of virtqueues * @socket: the socket connected to vhost-user master * @panic: a panic callback * @set_watch: a set_watch callback @@ -398,8 +399,11 @@ typedef struct VuVirtqElement { * @iface: a VuDevIface structure with vhost-user device callbacks * * Intializes a VuDev vhost-user context. + * + * Returns: true on success, false on failure. **/ -void vu_init(VuDev *dev, +bool vu_init(VuDev *dev, + uint16_t max_queues, int socket, vu_panic_cb panic, vu_set_watch_cb set_watch, diff --git a/contrib/libvhost-user/libvhost-user-glib.c b/contrib/libvhost-= user/libvhost-user-glib.c index 42660a1b36..99edd2f3de 100644 --- a/contrib/libvhost-user/libvhost-user-glib.c +++ b/contrib/libvhost-user/libvhost-user-glib.c @@ -131,18 +131,24 @@ static void vug_watch(VuDev *dev, int condition, void= *data) } } =20 -void -vug_init(VugDev *dev, int socket, +bool +vug_init(VugDev *dev, uint16_t max_queues, int socket, vu_panic_cb panic, const VuDevIface *iface) { g_assert(dev); g_assert(iface); =20 - vu_init(&dev->parent, socket, panic, set_watch, remove_watch, iface); + if (!vu_init(&dev->parent, max_queues, socket, panic, set_watch, + remove_watch, iface)) { + return false; + } + dev->fdmap =3D g_hash_table_new_full(NULL, NULL, NULL, (GDestroyNotify) g_source_destroy); =20 dev->src =3D vug_source_new(dev, socket, G_IO_IN, vug_watch, NULL); + + return true; } =20 void diff --git a/contrib/libvhost-user/libvhost-user.c b/contrib/libvhost-user/= libvhost-user.c index a8657c7af2..0c88431e8f 100644 --- a/contrib/libvhost-user/libvhost-user.c +++ b/contrib/libvhost-user/libvhost-user.c @@ -493,9 +493,9 @@ vu_get_features_exec(VuDev *dev, VhostUserMsg *vmsg) static void vu_set_enable_all_rings(VuDev *dev, bool enabled) { - int i; + uint16_t i; =20 - for (i =3D 0; i < VHOST_MAX_NR_VIRTQUEUE; i++) { + for (i =3D 0; i < dev->max_queues; i++) { dev->vq[i].enable =3D enabled; } } @@ -916,7 +916,7 @@ vu_check_queue_msg_file(VuDev *dev, VhostUserMsg *vmsg) { int index =3D vmsg->payload.u64 & VHOST_USER_VRING_IDX_MASK; =20 - if (index >=3D VHOST_MAX_NR_VIRTQUEUE) { + if (index >=3D dev->max_queues) { vmsg_close_fds(vmsg); vu_panic(dev, "Invalid queue index: %u", index); return false; @@ -1213,7 +1213,7 @@ vu_set_vring_enable_exec(VuDev *dev, VhostUserMsg *vm= sg) DPRINT("State.index: %d\n", index); DPRINT("State.enable: %d\n", enable); =20 - if (index >=3D VHOST_MAX_NR_VIRTQUEUE) { + if (index >=3D dev->max_queues) { vu_panic(dev, "Invalid vring_enable index: %u", index); return false; } @@ -1582,7 +1582,7 @@ vu_deinit(VuDev *dev) } dev->nregions =3D 0; =20 - for (i =3D 0; i < VHOST_MAX_NR_VIRTQUEUE; i++) { + for (i =3D 0; i < dev->max_queues; i++) { VuVirtq *vq =3D &dev->vq[i]; =20 if (vq->call_fd !=3D -1) { @@ -1627,18 +1627,23 @@ vu_deinit(VuDev *dev) if (dev->sock !=3D -1) { close(dev->sock); } + + free(dev->vq); + dev->vq =3D NULL; } =20 -void +bool vu_init(VuDev *dev, + uint16_t max_queues, int socket, vu_panic_cb panic, vu_set_watch_cb set_watch, vu_remove_watch_cb remove_watch, const VuDevIface *iface) { - int i; + uint16_t i; =20 + assert(max_queues > 0); assert(socket >=3D 0); assert(set_watch); assert(remove_watch); @@ -1654,18 +1659,27 @@ vu_init(VuDev *dev, dev->iface =3D iface; dev->log_call_fd =3D -1; dev->slave_fd =3D -1; - for (i =3D 0; i < VHOST_MAX_NR_VIRTQUEUE; i++) { + + dev->vq =3D malloc(max_queues * sizeof(dev->vq[0])); + if (!dev->vq) { + DPRINT("%s: failed to malloc virtqueues\n", __func__); + return false; + } + + for (i =3D 0; i < max_queues; i++) { dev->vq[i] =3D (VuVirtq) { .call_fd =3D -1, .kick_fd =3D -1, .err_fd =3D -1, .notification =3D true, }; } + + return true; } =20 VuVirtq * vu_get_queue(VuDev *dev, int qidx) { - assert(qidx < VHOST_MAX_NR_VIRTQUEUE); + assert(qidx < dev->max_queues); return &dev->vq[qidx]; } =20 diff --git a/contrib/vhost-user-blk/vhost-user-blk.c b/contrib/vhost-user-b= lk/vhost-user-blk.c index 86a3987744..ae61034656 100644 --- a/contrib/vhost-user-blk/vhost-user-blk.c +++ b/contrib/vhost-user-blk/vhost-user-blk.c @@ -25,6 +25,10 @@ #include #endif =20 +enum { + VHOST_USER_BLK_MAX_QUEUES =3D 8, +}; + struct virtio_blk_inhdr { unsigned char status; }; @@ -334,12 +338,6 @@ static void vub_process_vq(VuDev *vu_dev, int idx) VuVirtq *vq; int ret; =20 - if ((idx < 0) || (idx >=3D VHOST_MAX_NR_VIRTQUEUE)) { - fprintf(stderr, "VQ Index out of range: %d\n", idx); - vub_panic_cb(vu_dev, NULL); - return; - } - gdev =3D container_of(vu_dev, VugDev, parent); vdev_blk =3D container_of(gdev, VubDev, parent); assert(vdev_blk); @@ -631,7 +629,11 @@ int main(int argc, char **argv) vdev_blk->enable_ro =3D true; } =20 - vug_init(&vdev_blk->parent, csock, vub_panic_cb, &vub_iface); + if (!vug_init(&vdev_blk->parent, VHOST_USER_BLK_MAX_QUEUES, csock, + vub_panic_cb, &vub_iface)) { + fprintf(stderr, "Failed to initialized libvhost-user-glib\n"); + goto err; + } =20 g_main_loop_run(vdev_blk->loop); =20 diff --git a/contrib/vhost-user-gpu/main.c b/contrib/vhost-user-gpu/main.c index 04b753046f..b45d2019b4 100644 --- a/contrib/vhost-user-gpu/main.c +++ b/contrib/vhost-user-gpu/main.c @@ -25,6 +25,10 @@ #include "virgl.h" #include "vugbm.h" =20 +enum { + VHOST_USER_GPU_MAX_QUEUES =3D 2, +}; + struct virtio_gpu_simple_resource { uint32_t resource_id; uint32_t width; @@ -1169,7 +1173,10 @@ main(int argc, char *argv[]) exit(EXIT_FAILURE); } =20 - vug_init(&g.dev, fd, vg_panic, &vuiface); + if (!vug_init(&g.dev, VHOST_USER_GPU_MAX_QUEUES, fd, vg_panic, &vuifac= e)) { + g_printerr("Failed to initialize libvhost-user-glib.\n"); + exit(EXIT_FAILURE); + } =20 loop =3D g_main_loop_new(NULL, FALSE); g_main_loop_run(loop); diff --git a/contrib/vhost-user-input/main.c b/contrib/vhost-user-input/mai= n.c index 8b4e7d2536..449fd2171a 100644 --- a/contrib/vhost-user-input/main.c +++ b/contrib/vhost-user-input/main.c @@ -17,6 +17,10 @@ #include "standard-headers/linux/virtio_input.h" #include "qapi/error.h" =20 +enum { + VHOST_USER_INPUT_MAX_QUEUES =3D 2, +}; + typedef struct virtio_input_event virtio_input_event; typedef struct virtio_input_config virtio_input_config; =20 @@ -384,7 +388,12 @@ main(int argc, char *argv[]) g_printerr("Invalid vhost-user socket.\n"); exit(EXIT_FAILURE); } - vug_init(&vi.dev, fd, vi_panic, &vuiface); + + if (!vug_init(&vi.dev, VHOST_USER_INPUT_MAX_QUEUES, fd, vi_panic, + &vuiface)) { + g_printerr("Failed to initialize libvhost-user-glib.\n"); + exit(EXIT_FAILURE); + } =20 loop =3D g_main_loop_new(NULL, FALSE); g_main_loop_run(loop); diff --git a/contrib/vhost-user-scsi/vhost-user-scsi.c b/contrib/vhost-user= -scsi/vhost-user-scsi.c index 496dd6e693..0fc14d7899 100644 --- a/contrib/vhost-user-scsi/vhost-user-scsi.c +++ b/contrib/vhost-user-scsi/vhost-user-scsi.c @@ -19,6 +19,10 @@ =20 #define VUS_ISCSI_INITIATOR "iqn.2016-11.com.nutanix:vhost-user-scsi" =20 +enum { + VHOST_USER_SCSI_MAX_QUEUES =3D 8, +}; + typedef struct VusIscsiLun { struct iscsi_context *iscsi_ctx; int iscsi_lun; @@ -231,11 +235,6 @@ static void vus_proc_req(VuDev *vu_dev, int idx) =20 gdev =3D container_of(vu_dev, VugDev, parent); vdev_scsi =3D container_of(gdev, VusDev, parent); - if (idx < 0 || idx >=3D VHOST_MAX_NR_VIRTQUEUE) { - g_warning("VQ Index out of range: %d", idx); - vus_panic_cb(vu_dev, NULL); - return; - } =20 vq =3D vu_get_queue(vu_dev, idx); if (!vq) { @@ -295,12 +294,6 @@ static void vus_queue_set_started(VuDev *vu_dev, int i= dx, bool started) =20 assert(vu_dev); =20 - if (idx < 0 || idx >=3D VHOST_MAX_NR_VIRTQUEUE) { - g_warning("VQ Index out of range: %d", idx); - vus_panic_cb(vu_dev, NULL); - return; - } - vq =3D vu_get_queue(vu_dev, idx); =20 if (idx =3D=3D 0 || idx =3D=3D 1) { @@ -398,7 +391,11 @@ int main(int argc, char **argv) goto err; } =20 - vug_init(&vdev_scsi->parent, csock, vus_panic_cb, &vus_iface); + if (!vug_init(&vdev_scsi->parent, VHOST_USER_SCSI_MAX_QUEUES, csock, + vus_panic_cb, &vus_iface)) { + g_printerr("Failed to initialize libvhost-user-glib\n"); + goto err; + } =20 g_main_loop_run(vdev_scsi->loop); =20 diff --git a/tests/vhost-user-bridge.c b/tests/vhost-user-bridge.c index 0bb03af0e5..c4e350e1f5 100644 --- a/tests/vhost-user-bridge.c +++ b/tests/vhost-user-bridge.c @@ -45,6 +45,10 @@ } \ } while (0) =20 +enum { + VHOST_USER_BRIDGE_MAX_QUEUES =3D 8, +}; + typedef void (*CallbackFunc)(int sock, void *ctx); =20 typedef struct Event { @@ -512,12 +516,16 @@ vubr_accept_cb(int sock, void *ctx) } DPRINT("Got connection from remote peer on sock %d\n", conn_fd); =20 - vu_init(&dev->vudev, - conn_fd, - vubr_panic, - vubr_set_watch, - vubr_remove_watch, - &vuiface); + if (!vu_init(&dev->vudev, + VHOST_USER_BRIDGE_MAX_QUEUES, + conn_fd, + vubr_panic, + vubr_set_watch, + vubr_remove_watch, + &vuiface)) { + fprintf(stderr, "Failed to initialize libvhost-user\n"); + exit(1); + } =20 dispatcher_add(&dev->dispatcher, conn_fd, ctx, vubr_receive_cb); dispatcher_remove(&dev->dispatcher, sock); @@ -560,12 +568,18 @@ vubr_new(const char *path, bool client) if (connect(dev->sock, (struct sockaddr *)&un, len) =3D=3D -1) { vubr_die("connect"); } - vu_init(&dev->vudev, - dev->sock, - vubr_panic, - vubr_set_watch, - vubr_remove_watch, - &vuiface); + + if (!vu_init(&dev->vudev, + VHOST_USER_BRIDGE_MAX_QUEUES, + dev->sock, + vubr_panic, + vubr_set_watch, + vubr_remove_watch, + &vuiface)) { + fprintf(stderr, "Failed to initialize libvhost-user\n"); + exit(1); + } + cb =3D vubr_receive_cb; } =20 @@ -584,7 +598,7 @@ static void *notifier_thread(void *arg) int qidx; =20 while (true) { - for (qidx =3D 0; qidx < VHOST_MAX_NR_VIRTQUEUE; qidx++) { + for (qidx =3D 0; qidx < VHOST_USER_BRIDGE_MAX_QUEUES; qidx++) { uint16_t *n =3D vubr->notifier.addr + pagesize * qidx; =20 if (*n =3D=3D qidx) { @@ -616,7 +630,7 @@ vubr_host_notifier_setup(VubrDev *dev) void *addr; int fd; =20 - length =3D getpagesize() * VHOST_MAX_NR_VIRTQUEUE; + length =3D getpagesize() * VHOST_USER_BRIDGE_MAX_QUEUES; =20 fd =3D mkstemp(template); if (fd < 0) { --=20 2.21.0 From nobody Tue Nov 11 03:16:11 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1561110368; cv=none; d=zoho.com; s=zohoarc; b=gAhvRnH3+wikgoxDX8pb9Bx+PyLNk/GzOKaDeyq8pDOcaUQ7DL+p1185cqF859LArQgrVQvZ/Q4lontGzQa+sTMRZj5x62PiDICJYGJFkZX4jN/o9/VrsN2nzyKRPG61cjeEU5RQVNhN2oUnMmfYjpgF9XS+kn4H5FWtOUDuhPk= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zoho.com; s=zohoarc; t=1561110368; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To:ARC-Authentication-Results; bh=LsQFUaKhXvX++eTgRso1YX+mQy5XZMfjEm3CmCkt3rg=; b=Xs6srZoUGlDfkYrPWyWf5s/GwZxy22vhpuXnqK8KzmHsbbZG9rboGZT4Lv+tPXNCrrHcJPtOCa4aKUpVmG1yybCZ3U39C4qGYV6d1ggn2FmbuwTmQkcegAyOVurDP48DF24ABiEeCc80lnlGB3+70QMnB3nI/gwLnfE51f0+dCc= ARC-Authentication-Results: i=1; mx.zoho.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail header.from= (p=none dis=none) header.from= Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1561110368158733.5431287891797; Fri, 21 Jun 2019 02:46:08 -0700 (PDT) Received: from localhost ([::1]:57522 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG7R-0000bI-5R for importer@patchew.org; Fri, 21 Jun 2019 05:46:05 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:49518) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG2O-0004wj-VU for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:57 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1heG2L-0002Tg-TL for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:52 -0400 Received: from mx1.redhat.com ([209.132.183.28]:39748) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1heG2L-0002TN-Os for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:40:49 -0400 Received: from smtp.corp.redhat.com (int-mx08.intmail.prod.int.phx2.redhat.com [10.5.11.23]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 17FBA30833BE; Fri, 21 Jun 2019 09:40:49 +0000 (UTC) Received: from localhost (ovpn-117-248.ams2.redhat.com [10.36.117.248]) by smtp.corp.redhat.com (Postfix) with ESMTP id CCACE19C4F; Fri, 21 Jun 2019 09:40:39 +0000 (UTC) From: Stefan Hajnoczi To: Date: Fri, 21 Jun 2019 10:40:04 +0100 Message-Id: <20190621094005.4134-4-stefanha@redhat.com> In-Reply-To: <20190621094005.4134-1-stefanha@redhat.com> References: <20190621094005.4134-1-stefanha@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.84 on 10.5.11.23 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.44]); Fri, 21 Jun 2019 09:40:49 +0000 (UTC) Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] X-Received-From: 209.132.183.28 Subject: [Qemu-devel] [PATCH 3/4] libvhost-user: implement VHOST_USER_PROTOCOL_F_MQ X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Michael S. Tsirkin" , "Dr. David Alan Gilbert" , Sebastien Boeuf , Gerd Hoffmann , Stefan Hajnoczi , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" Content-Type: text/plain; charset="utf-8" Existing vhost-user device backends, including vhost-user-scsi and vhost-user-blk, support multiqueue but libvhost-user currently does not advertise this. VHOST_USER_PROTOCOL_F_MQ enables the VHOST_USER_GET_QUEUE_NUM request needed for a vhost-user master to query the number of queues. For example, QEMU's vhost-user-net master depends on VHOST_USER_PROTOCOL_F_MQ for multiqueue. If you're wondering how any device backend with more than one virtqueue functions today, it's because device types with a fixed number of virtqueues do not require querying the number of queues. Therefore the vhost-user master for vhost-user-input with 2 virtqueues, for example, doesn't actually depend on VHOST_USER_PROTOCOL_F_MQ. It just enables virtqueues 0 and 1 without asking. Let there be multiqueue! Suggested-by: Sebastien Boeuf Signed-off-by: Stefan Hajnoczi Reviewed-by: Marc-Andr=C3=A9 Lureau --- contrib/libvhost-user/libvhost-user.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/contrib/libvhost-user/libvhost-user.c b/contrib/libvhost-user/= libvhost-user.c index 0c88431e8f..312c54f260 100644 --- a/contrib/libvhost-user/libvhost-user.c +++ b/contrib/libvhost-user/libvhost-user.c @@ -1160,7 +1160,8 @@ vu_set_vring_err_exec(VuDev *dev, VhostUserMsg *vmsg) static bool vu_get_protocol_features_exec(VuDev *dev, VhostUserMsg *vmsg) { - uint64_t features =3D 1ULL << VHOST_USER_PROTOCOL_F_LOG_SHMFD | + uint64_t features =3D 1ULL << VHOST_USER_PROTOCOL_F_MQ | + 1ULL << VHOST_USER_PROTOCOL_F_LOG_SHMFD | 1ULL << VHOST_USER_PROTOCOL_F_SLAVE_REQ | 1ULL << VHOST_USER_PROTOCOL_F_HOST_NOTIFIER | 1ULL << VHOST_USER_PROTOCOL_F_SLAVE_SEND_FD; @@ -1200,8 +1201,8 @@ vu_set_protocol_features_exec(VuDev *dev, VhostUserMs= g *vmsg) static bool vu_get_queue_num_exec(VuDev *dev, VhostUserMsg *vmsg) { - DPRINT("Function %s() not implemented yet.\n", __func__); - return false; + vmsg_set_reply_u64(vmsg, dev->max_queues); + return true; } =20 static bool --=20 2.21.0 From nobody Tue Nov 11 03:16:11 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) client-ip=209.51.188.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail(p=none dis=none) header.from=redhat.com ARC-Seal: i=1; a=rsa-sha256; t=1561110359; cv=none; d=zoho.com; s=zohoarc; b=g8QpI5nR5kSBG/EApblCDmZ0HA+nfhOPvkel/zpeksx04W5axEYsrOpT2lW+UslTUOyx/E6gPseAhJujGo3fbTAXvZ1nnj6AYEyAs28hrL4PNmVblBNFif3E7I7nnLG8bx1O05MrecqR0YHxwTd3JIBmw4ZC3Mwmn9Er+kJok14= ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zoho.com; s=zohoarc; t=1561110359; h=Content-Transfer-Encoding:Cc:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To:ARC-Authentication-Results; bh=lb6/4aex4eqmMscBpoyEZ0xLfOw0yA7wBN1dws/e+Bo=; b=aLALSOFiNdQMeNcfWp5sKwzSLYHQh7ltPuf/uUPe2gCFtvm2r9pSjoMs4x4pd7KUCwT63am2Mxk/QnsmjIm7TVuUCmD8lmR1LMDuPWonPg3aq16Vu9RfqOFk3hr+1oGZZB5cGe5joq2d9xT52d9899LXOaVrbK0X8FzdcCxRX88= ARC-Authentication-Results: i=1; mx.zoho.com; spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; dmarc=fail header.from= (p=none dis=none) header.from= Return-Path: Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by mx.zohomail.com with SMTPS id 1561110359006545.0301834678696; Fri, 21 Jun 2019 02:45:59 -0700 (PDT) Received: from localhost ([::1]:57520 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG7K-0000Pv-26 for importer@patchew.org; Fri, 21 Jun 2019 05:45:58 -0400 Received: from eggs.gnu.org ([2001:470:142:3::10]:49552) by lists.gnu.org with esmtp (Exim 4.86_2) (envelope-from ) id 1heG2a-0005Ep-2H for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:41:07 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1heG2X-0002YN-0C for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:41:04 -0400 Received: from mx1.redhat.com ([209.132.183.28]:48606) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1heG2W-0002Xa-Qm for qemu-devel@nongnu.org; Fri, 21 Jun 2019 05:41:00 -0400 Received: from smtp.corp.redhat.com (int-mx07.intmail.prod.int.phx2.redhat.com [10.5.11.22]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 252FD3082B68; Fri, 21 Jun 2019 09:41:00 +0000 (UTC) Received: from localhost (ovpn-117-248.ams2.redhat.com [10.36.117.248]) by smtp.corp.redhat.com (Postfix) with ESMTP id 773AF1001B30; Fri, 21 Jun 2019 09:40:50 +0000 (UTC) From: Stefan Hajnoczi To: Date: Fri, 21 Jun 2019 10:40:05 +0100 Message-Id: <20190621094005.4134-5-stefanha@redhat.com> In-Reply-To: <20190621094005.4134-1-stefanha@redhat.com> References: <20190621094005.4134-1-stefanha@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.84 on 10.5.11.22 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.45]); Fri, 21 Jun 2019 09:41:00 +0000 (UTC) Content-Transfer-Encoding: quoted-printable X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] X-Received-From: 209.132.183.28 Subject: [Qemu-devel] [PATCH 4/4] docs: avoid vhost-user-net specifics in multiqueue section X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: "Michael S. Tsirkin" , "Dr. David Alan Gilbert" , Sebastien Boeuf , Gerd Hoffmann , Stefan Hajnoczi , =?UTF-8?q?Marc-Andr=C3=A9=20Lureau?= Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" Content-Type: text/plain; charset="utf-8" The "Multiple queue support" section makes references to vhost-user-net "queue pairs". This is confusing for two reasons: 1. This actually applies to all device types, not just vhost-user-net. 2. VHOST_USER_GET_QUEUE_NUM returns the number of virtqueues, not the number of queue pairs. Reword the section so that the vhost-user-net specific part is relegated to the very end: we acknowledge that vhost-user-net historically automatically enabled the first queue pair. Signed-off-by: Stefan Hajnoczi Reviewed-by: Marc-Andr=C3=A9 Lureau --- docs/interop/vhost-user.rst | 21 +++++++++++---------- 1 file changed, 11 insertions(+), 10 deletions(-) diff --git a/docs/interop/vhost-user.rst b/docs/interop/vhost-user.rst index dc0ff9211f..5750668aba 100644 --- a/docs/interop/vhost-user.rst +++ b/docs/interop/vhost-user.rst @@ -324,19 +324,20 @@ must support changing some configuration aspects on t= he fly. Multiple queue support ---------------------- =20 -Multiple queue is treated as a protocol extension, hence the slave has -to implement protocol features first. The multiple queues feature is -supported only when the protocol feature ``VHOST_USER_PROTOCOL_F_MQ`` -(bit 0) is set. +Multiple queue support allows the slave to advertise the maximum number of +queues. This is treated as a protocol extension, hence the slave has to +implement protocol features first. The multiple queues feature is supported +only when the protocol feature ``VHOST_USER_PROTOCOL_F_MQ`` (bit 0) is set. =20 -The max number of queue pairs the slave supports can be queried with -message ``VHOST_USER_GET_QUEUE_NUM``. Master should stop when the -number of requested queues is bigger than that. +The max number of queues the slave supports can be queried with message +``VHOST_USER_GET_QUEUE_NUM``. Master should stop when the number of reques= ted +queues is bigger than that. =20 As all queues share one connection, the master uses a unique index for each -queue in the sent message to identify a specified queue. One queue pair -is enabled initially. More queues are enabled dynamically, by sending -message ``VHOST_USER_SET_VRING_ENABLE``. +queue in the sent message to identify a specified queue. + +The master enables queues by sending message ``VHOST_USER_SET_VRING_ENABLE= ``. +vhost-user-net has historically automatically enabled the first queue pair. =20 Migration --------- --=20 2.21.0