From nobody Sat Feb 7 08:00:52 2026 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) client-ip=208.118.235.17; envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org; helo=lists.gnu.org; Authentication-Results: mx.zoho.com; spf=pass (zoho.com: domain of gnu.org designates 208.118.235.17 as permitted sender) smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org; Return-Path: Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) by mx.zohomail.com with SMTPS id 1496421404624315.61189521609595; Fri, 2 Jun 2017 09:36:44 -0700 (PDT) Received: from localhost ([::1]:50720 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dGpZ4-0000mT-Sv for importer@patchew.org; Fri, 02 Jun 2017 12:36:42 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:34494) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1dGpX9-0007wB-PZ for qemu-devel@nongnu.org; Fri, 02 Jun 2017 12:34:45 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1dGpX8-0006Pb-FY for qemu-devel@nongnu.org; Fri, 02 Jun 2017 12:34:43 -0400 Received: from mx1.redhat.com ([209.132.183.28]:35854) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1dGpX8-0006OG-7D for qemu-devel@nongnu.org; Fri, 02 Jun 2017 12:34:42 -0400 Received: from smtp.corp.redhat.com (int-mx01.intmail.prod.int.phx2.redhat.com [10.5.11.11]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id 4520415D9; Fri, 2 Jun 2017 16:34:41 +0000 (UTC) Received: from redhat.com (ovpn-125-45.rdu2.redhat.com [10.10.125.45]) by smtp.corp.redhat.com (Postfix) with SMTP id D42897E21D; Fri, 2 Jun 2017 16:34:40 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.3.2 mx1.redhat.com 4520415D9 Authentication-Results: ext-mx05.extmail.prod.ext.phx2.redhat.com; dmarc=none (p=none dis=none) header.from=redhat.com Authentication-Results: ext-mx05.extmail.prod.ext.phx2.redhat.com; spf=pass smtp.mailfrom=mst@redhat.com DKIM-Filter: OpenDKIM Filter v2.11.0 mx1.redhat.com 4520415D9 Date: Fri, 2 Jun 2017 19:34:40 +0300 From: "Michael S. Tsirkin" To: qemu-devel@nongnu.org Message-ID: <1496421247-857-6-git-send-email-mst@redhat.com> References: <1496421247-857-1-git-send-email-mst@redhat.com> MIME-Version: 1.0 Content-Disposition: inline In-Reply-To: <1496421247-857-1-git-send-email-mst@redhat.com> X-Mutt-Fcc: =sent X-Scanned-By: MIMEDefang 2.79 on 10.5.11.11 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.29]); Fri, 02 Jun 2017 16:34:41 +0000 (UTC) X-detected-operating-system: by eggs.gnu.org: GNU/Linux 2.2.x-3.x [generic] [fuzzy] X-Received-From: 209.132.183.28 Subject: [Qemu-devel] [PULL 5/8] vhost: rework IOTLB messaging X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Peter Maydell , Maxime Coquelin Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org Sender: "Qemu-devel" X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" From: Maxime Coquelin This patch reworks IOTLB messaging to prepare for vhost-user device IOTLB support. IOTLB messages handling is extracted from vhost-kernel backend, so that only the messages transport remains backend specifics. Signed-off-by: Maxime Coquelin Reviewed-by: Michael S. Tsirkin Signed-off-by: Michael S. Tsirkin --- include/hw/virtio/vhost-backend.h | 23 ++++--- hw/virtio/vhost-backend.c | 130 +++++++++++++++++++++-------------= ---- hw/virtio/vhost.c | 8 +-- 3 files changed, 92 insertions(+), 69 deletions(-) diff --git a/include/hw/virtio/vhost-backend.h b/include/hw/virtio/vhost-ba= ckend.h index c3cf4a7..a7a5f22 100644 --- a/include/hw/virtio/vhost-backend.h +++ b/include/hw/virtio/vhost-backend.h @@ -27,6 +27,7 @@ struct vhost_vring_file; struct vhost_vring_state; struct vhost_vring_addr; struct vhost_scsi_target; +struct vhost_iotlb_msg; =20 typedef int (*vhost_backend_init)(struct vhost_dev *dev, void *opaque); typedef int (*vhost_backend_cleanup)(struct vhost_dev *dev); @@ -81,12 +82,8 @@ typedef int (*vhost_vsock_set_guest_cid_op)(struct vhost= _dev *dev, typedef int (*vhost_vsock_set_running_op)(struct vhost_dev *dev, int start= ); typedef void (*vhost_set_iotlb_callback_op)(struct vhost_dev *dev, int enabled); -typedef int (*vhost_update_device_iotlb_op)(struct vhost_dev *dev, - uint64_t iova, uint64_t uaddr, - uint64_t len, - IOMMUAccessFlags perm); -typedef int (*vhost_invalidate_device_iotlb_op)(struct vhost_dev *dev, - uint64_t iova, uint64_t le= n); +typedef int (*vhost_send_device_iotlb_msg_op)(struct vhost_dev *dev, + struct vhost_iotlb_msg *imsg= ); =20 typedef struct VhostOps { VhostBackendType backend_type; @@ -120,8 +117,7 @@ typedef struct VhostOps { vhost_vsock_set_guest_cid_op vhost_vsock_set_guest_cid; vhost_vsock_set_running_op vhost_vsock_set_running; vhost_set_iotlb_callback_op vhost_set_iotlb_callback; - vhost_update_device_iotlb_op vhost_update_device_iotlb; - vhost_invalidate_device_iotlb_op vhost_invalidate_device_iotlb; + vhost_send_device_iotlb_msg_op vhost_send_device_iotlb_msg; } VhostOps; =20 extern const VhostOps user_ops; @@ -129,4 +125,15 @@ extern const VhostOps user_ops; int vhost_set_backend_type(struct vhost_dev *dev, VhostBackendType backend_type); =20 +int vhost_backend_update_device_iotlb(struct vhost_dev *dev, + uint64_t iova, uint64_t uaddr, + uint64_t len, + IOMMUAccessFlags perm); + +int vhost_backend_invalidate_device_iotlb(struct vhost_dev *dev, + uint64_t iova, uint64_t l= en); + +int vhost_backend_handle_iotlb_msg(struct vhost_dev *dev, + struct vhost_iotlb_msg *imsg); + #endif /* VHOST_BACKEND_H */ diff --git a/hw/virtio/vhost-backend.c b/hw/virtio/vhost-backend.c index be927b8..4e31de1 100644 --- a/hw/virtio/vhost-backend.c +++ b/hw/virtio/vhost-backend.c @@ -192,7 +192,6 @@ static void vhost_kernel_iotlb_read(void *opaque) ssize_t len; =20 while ((len =3D read((uintptr_t)dev->opaque, &msg, sizeof msg)) > 0) { - struct vhost_iotlb_msg *imsg =3D &msg.iotlb; if (len < sizeof msg) { error_report("Wrong vhost message len: %d", (int)len); break; @@ -201,70 +200,21 @@ static void vhost_kernel_iotlb_read(void *opaque) error_report("Unknown vhost iotlb message type"); break; } - switch (imsg->type) { - case VHOST_IOTLB_MISS: - vhost_device_iotlb_miss(dev, imsg->iova, - imsg->perm !=3D VHOST_ACCESS_RO); - break; - case VHOST_IOTLB_UPDATE: - case VHOST_IOTLB_INVALIDATE: - error_report("Unexpected IOTLB message type"); - break; - case VHOST_IOTLB_ACCESS_FAIL: - /* FIXME: report device iotlb error */ - break; - default: - break; - } - } -} =20 -static int vhost_kernel_update_device_iotlb(struct vhost_dev *dev, - uint64_t iova, uint64_t uaddr, - uint64_t len, - IOMMUAccessFlags perm) -{ - struct vhost_msg msg; - msg.type =3D VHOST_IOTLB_MSG; - msg.iotlb.iova =3D iova; - msg.iotlb.uaddr =3D uaddr; - msg.iotlb.size =3D len; - msg.iotlb.type =3D VHOST_IOTLB_UPDATE; - - switch (perm) { - case IOMMU_RO: - msg.iotlb.perm =3D VHOST_ACCESS_RO; - break; - case IOMMU_WO: - msg.iotlb.perm =3D VHOST_ACCESS_WO; - break; - case IOMMU_RW: - msg.iotlb.perm =3D VHOST_ACCESS_RW; - break; - default: - g_assert_not_reached(); - } - - if (write((uintptr_t)dev->opaque, &msg, sizeof msg) !=3D sizeof msg) { - error_report("Fail to update device iotlb"); - return -EFAULT; + vhost_backend_handle_iotlb_msg(dev, &msg.iotlb); } - - return 0; } =20 -static int vhost_kernel_invalidate_device_iotlb(struct vhost_dev *dev, - uint64_t iova, uint64_t le= n) +static int vhost_kernel_send_device_iotlb_msg(struct vhost_dev *dev, + struct vhost_iotlb_msg *imsg) { struct vhost_msg msg; =20 msg.type =3D VHOST_IOTLB_MSG; - msg.iotlb.iova =3D iova; - msg.iotlb.size =3D len; - msg.iotlb.type =3D VHOST_IOTLB_INVALIDATE; + msg.iotlb =3D *imsg; =20 if (write((uintptr_t)dev->opaque, &msg, sizeof msg) !=3D sizeof msg) { - error_report("Fail to invalidate device iotlb"); + error_report("Fail to update device iotlb"); return -EFAULT; } =20 @@ -311,8 +261,7 @@ static const VhostOps kernel_ops =3D { .vhost_vsock_set_running =3D vhost_kernel_vsock_set_running, #endif /* CONFIG_VHOST_VSOCK */ .vhost_set_iotlb_callback =3D vhost_kernel_set_iotlb_callback, - .vhost_update_device_iotlb =3D vhost_kernel_update_device_iotlb, - .vhost_invalidate_device_iotlb =3D vhost_kernel_invalidate_device_= iotlb, + .vhost_send_device_iotlb_msg =3D vhost_kernel_send_device_iotlb_ms= g, }; =20 int vhost_set_backend_type(struct vhost_dev *dev, VhostBackendType backend= _type) @@ -333,3 +282,70 @@ int vhost_set_backend_type(struct vhost_dev *dev, Vhos= tBackendType backend_type) =20 return r; } + +int vhost_backend_update_device_iotlb(struct vhost_dev *dev, + uint64_t iova, uint64_t uaddr, + uint64_t len, + IOMMUAccessFlags perm) +{ + struct vhost_iotlb_msg imsg; + + imsg.iova =3D iova; + imsg.uaddr =3D uaddr; + imsg.size =3D len; + imsg.type =3D VHOST_IOTLB_UPDATE; + + switch (perm) { + case IOMMU_RO: + imsg.perm =3D VHOST_ACCESS_RO; + break; + case IOMMU_WO: + imsg.perm =3D VHOST_ACCESS_WO; + break; + case IOMMU_RW: + imsg.perm =3D VHOST_ACCESS_RW; + break; + default: + return -EINVAL; + } + + return dev->vhost_ops->vhost_send_device_iotlb_msg(dev, &imsg); +} + +int vhost_backend_invalidate_device_iotlb(struct vhost_dev *dev, + uint64_t iova, uint64_t l= en) +{ + struct vhost_iotlb_msg imsg; + + imsg.iova =3D iova; + imsg.size =3D len; + imsg.type =3D VHOST_IOTLB_INVALIDATE; + + return dev->vhost_ops->vhost_send_device_iotlb_msg(dev, &imsg); +} + +int vhost_backend_handle_iotlb_msg(struct vhost_dev *dev, + struct vhost_iotlb_msg *imsg) +{ + int ret =3D 0; + + switch (imsg->type) { + case VHOST_IOTLB_MISS: + ret =3D vhost_device_iotlb_miss(dev, imsg->iova, + imsg->perm !=3D VHOST_ACCESS_RO); + break; + case VHOST_IOTLB_ACCESS_FAIL: + /* FIXME: report device iotlb error */ + error_report("Access failure IOTLB message type not supported"); + ret =3D -ENOTSUP; + break; + case VHOST_IOTLB_UPDATE: + case VHOST_IOTLB_INVALIDATE: + default: + error_report("Unexpected IOTLB message type"); + ret =3D -EINVAL; + break; + } + + return ret; +} diff --git a/hw/virtio/vhost.c b/hw/virtio/vhost.c index 8fab12d..6eddb09 100644 --- a/hw/virtio/vhost.c +++ b/hw/virtio/vhost.c @@ -724,8 +724,8 @@ static void vhost_iommu_unmap_notify(IOMMUNotifier *n, = IOMMUTLBEntry *iotlb) struct vhost_dev *hdev =3D iommu->hdev; hwaddr iova =3D iotlb->iova + iommu->iommu_offset; =20 - if (hdev->vhost_ops->vhost_invalidate_device_iotlb(hdev, iova, - iotlb->addr_mask + = 1)) { + if (vhost_backend_invalidate_device_iotlb(hdev, iova, + iotlb->addr_mask + 1)) { error_report("Fail to invalidate device iotlb"); } } @@ -993,8 +993,8 @@ int vhost_device_iotlb_miss(struct vhost_dev *dev, uint= 64_t iova, int write) len =3D MIN(iotlb.addr_mask + 1, len); iova =3D iova & ~iotlb.addr_mask; =20 - ret =3D dev->vhost_ops->vhost_update_device_iotlb(dev, iova, uaddr, - len, iotlb.perm); + ret =3D vhost_backend_update_device_iotlb(dev, iova, uaddr, + len, iotlb.perm); if (ret) { error_report("Fail to update device iotlb"); goto out; --=20 MST