From nobody Sun Sep 14 18:26:44 2025 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id DF4EFC46467 for ; Thu, 19 Jan 2023 06:17:00 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229696AbjASGQ7 (ORCPT ); Thu, 19 Jan 2023 01:16:59 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:48736 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229689AbjASGQn (ORCPT ); Thu, 19 Jan 2023 01:16:43 -0500 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id ECA8066CC0 for ; Wed, 18 Jan 2023 22:15:41 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1674108940; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=jOnSvm4IzUcYhqfj06jz0gGlZdA5hsRgPecmLO10cwQ=; b=T89R2smW9FC3HPdx80Q6GenBd9jkQxr97tKZPF+Cz19tE5oau7/VpKHc8WwJEf5O2N56Qa 1txKT5kU07dR05LpciSWK3zv2PVHWL/vHEpk/8i5Q8Ajgwuoy3pEr4pqKuO6bc7wbrzAL0 n6Efdox5IU6XRie+M7afY9pvmlhInD8= Received: from mimecast-mx02.redhat.com (mx3-rdu2.redhat.com [66.187.233.73]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-196-v6b9GdA3MzKcCikf44txmA-1; Thu, 19 Jan 2023 01:15:37 -0500 X-MC-Unique: v6b9GdA3MzKcCikf44txmA-1 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id 44FF8280605A; Thu, 19 Jan 2023 06:15:37 +0000 (UTC) Received: from localhost.localdomain (ovpn-13-97.pek2.redhat.com [10.72.13.97]) by smtp.corp.redhat.com (Postfix) with ESMTP id D5F541121315; Thu, 19 Jan 2023 06:15:33 +0000 (UTC) From: Jason Wang To: mst@redhat.com, jasowang@redhat.com Cc: elic@nvidia.com, gdawar@amd.com, tanuj.kamde@amd.com, linux-kernel@vger.kernel.org, virtualization@lists.linux-foundation.org Subject: [PATCH V2 1/5] virtio_ring: per virtqueue dma device Date: Thu, 19 Jan 2023 14:15:21 +0800 Message-Id: <20230119061525.75068-2-jasowang@redhat.com> In-Reply-To: <20230119061525.75068-1-jasowang@redhat.com> References: <20230119061525.75068-1-jasowang@redhat.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Scanned-By: MIMEDefang 3.1 on 10.11.54.3 Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" This patch introduces a per virtqueue dma device. This will be used for virtio devices whose virtqueue are backed by different underlayer devices. One example is the vDPA that where the control virtqueue could be implemented through software mediation. Some of the work are actually done before since the helper like vring_dma_device(). This work left are: - Let vring_dma_device() return the per virtqueue dma device instead of the vdev's parent. - Allow passing a dma_device when creating the virtqueue through a new helper, old vring creation helper will keep using vdev's parent. Reviewed-by: Eli Cohen Tested-by: Eli Cohen Signed-off-by: Jason Wang --- drivers/virtio/virtio_ring.c | 133 ++++++++++++++++++++++++----------- include/linux/virtio_ring.h | 16 +++++ 2 files changed, 109 insertions(+), 40 deletions(-) diff --git a/drivers/virtio/virtio_ring.c b/drivers/virtio/virtio_ring.c index 723c4e29e1d3..41144b5246a8 100644 --- a/drivers/virtio/virtio_ring.c +++ b/drivers/virtio/virtio_ring.c @@ -202,6 +202,9 @@ struct vring_virtqueue { /* DMA, allocation, and size information */ bool we_own_ring; =20 + /* Device used for doing DMA */ + struct device *dma_dev; + #ifdef DEBUG /* They're supposed to lock for us. */ unsigned int in_use; @@ -219,7 +222,8 @@ static struct virtqueue *__vring_new_virtqueue(unsigned= int index, bool context, bool (*notify)(struct virtqueue *), void (*callback)(struct virtqueue *), - const char *name); + const char *name, + struct device *dma_dev); static struct vring_desc_extra *vring_alloc_desc_extra(unsigned int num); static void vring_free(struct virtqueue *_vq); =20 @@ -297,10 +301,11 @@ size_t virtio_max_dma_size(struct virtio_device *vdev) EXPORT_SYMBOL_GPL(virtio_max_dma_size); =20 static void *vring_alloc_queue(struct virtio_device *vdev, size_t size, - dma_addr_t *dma_handle, gfp_t flag) + dma_addr_t *dma_handle, gfp_t flag, + struct device *dma_dev) { if (vring_use_dma_api(vdev)) { - return dma_alloc_coherent(vdev->dev.parent, size, + return dma_alloc_coherent(dma_dev, size, dma_handle, flag); } else { void *queue =3D alloc_pages_exact(PAGE_ALIGN(size), flag); @@ -330,10 +335,11 @@ static void *vring_alloc_queue(struct virtio_device *= vdev, size_t size, } =20 static void vring_free_queue(struct virtio_device *vdev, size_t size, - void *queue, dma_addr_t dma_handle) + void *queue, dma_addr_t dma_handle, + struct device *dma_dev) { if (vring_use_dma_api(vdev)) - dma_free_coherent(vdev->dev.parent, size, queue, dma_handle); + dma_free_coherent(dma_dev, size, queue, dma_handle); else free_pages_exact(queue, PAGE_ALIGN(size)); } @@ -341,11 +347,11 @@ static void vring_free_queue(struct virtio_device *vd= ev, size_t size, /* * The DMA ops on various arches are rather gnarly right now, and * making all of the arch DMA ops work on the vring device itself - * is a mess. For now, we use the parent device for DMA ops. + * is a mess. */ static inline struct device *vring_dma_dev(const struct vring_virtqueue *v= q) { - return vq->vq.vdev->dev.parent; + return vq->dma_dev; } =20 /* Map one sg entry. */ @@ -1032,11 +1038,12 @@ static int vring_alloc_state_extra_split(struct vri= ng_virtqueue_split *vring_spl } =20 static void vring_free_split(struct vring_virtqueue_split *vring_split, - struct virtio_device *vdev) + struct virtio_device *vdev, struct device *dma_dev) { vring_free_queue(vdev, vring_split->queue_size_in_bytes, vring_split->vring.desc, - vring_split->queue_dma_addr); + vring_split->queue_dma_addr, + dma_dev); =20 kfree(vring_split->desc_state); kfree(vring_split->desc_extra); @@ -1046,7 +1053,8 @@ static int vring_alloc_queue_split(struct vring_virtq= ueue_split *vring_split, struct virtio_device *vdev, u32 num, unsigned int vring_align, - bool may_reduce_num) + bool may_reduce_num, + struct device *dma_dev) { void *queue =3D NULL; dma_addr_t dma_addr; @@ -1061,7 +1069,8 @@ static int vring_alloc_queue_split(struct vring_virtq= ueue_split *vring_split, for (; num && vring_size(num, vring_align) > PAGE_SIZE; num /=3D 2) { queue =3D vring_alloc_queue(vdev, vring_size(num, vring_align), &dma_addr, - GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO); + GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO, + dma_dev); if (queue) break; if (!may_reduce_num) @@ -1074,7 +1083,8 @@ static int vring_alloc_queue_split(struct vring_virtq= ueue_split *vring_split, if (!queue) { /* Try to get a single page. You are my only hope! */ queue =3D vring_alloc_queue(vdev, vring_size(num, vring_align), - &dma_addr, GFP_KERNEL | __GFP_ZERO); + &dma_addr, GFP_KERNEL | __GFP_ZERO, + dma_dev); } if (!queue) return -ENOMEM; @@ -1100,21 +1110,22 @@ static struct virtqueue *vring_create_virtqueue_spl= it( bool context, bool (*notify)(struct virtqueue *), void (*callback)(struct virtqueue *), - const char *name) + const char *name, + struct device *dma_dev) { struct vring_virtqueue_split vring_split =3D {}; struct virtqueue *vq; int err; =20 err =3D vring_alloc_queue_split(&vring_split, vdev, num, vring_align, - may_reduce_num); + may_reduce_num, dma_dev); if (err) return NULL; =20 vq =3D __vring_new_virtqueue(index, &vring_split, vdev, weak_barriers, - context, notify, callback, name); + context, notify, callback, name, dma_dev); if (!vq) { - vring_free_split(&vring_split, vdev); + vring_free_split(&vring_split, vdev, dma_dev); return NULL; } =20 @@ -1132,7 +1143,8 @@ static int virtqueue_resize_split(struct virtqueue *_= vq, u32 num) =20 err =3D vring_alloc_queue_split(&vring_split, vdev, num, vq->split.vring_align, - vq->split.may_reduce_num); + vq->split.may_reduce_num, + vring_dma_dev(vq)); if (err) goto err; =20 @@ -1150,7 +1162,7 @@ static int virtqueue_resize_split(struct virtqueue *_= vq, u32 num) return 0; =20 err_state_extra: - vring_free_split(&vring_split, vdev); + vring_free_split(&vring_split, vdev, vring_dma_dev(vq)); err: virtqueue_reinit_split(vq); return -ENOMEM; @@ -1841,22 +1853,26 @@ static struct vring_desc_extra *vring_alloc_desc_ex= tra(unsigned int num) } =20 static void vring_free_packed(struct vring_virtqueue_packed *vring_packed, - struct virtio_device *vdev) + struct virtio_device *vdev, + struct device *dma_dev) { if (vring_packed->vring.desc) vring_free_queue(vdev, vring_packed->ring_size_in_bytes, vring_packed->vring.desc, - vring_packed->ring_dma_addr); + vring_packed->ring_dma_addr, + dma_dev); =20 if (vring_packed->vring.driver) vring_free_queue(vdev, vring_packed->event_size_in_bytes, vring_packed->vring.driver, - vring_packed->driver_event_dma_addr); + vring_packed->driver_event_dma_addr, + dma_dev); =20 if (vring_packed->vring.device) vring_free_queue(vdev, vring_packed->event_size_in_bytes, vring_packed->vring.device, - vring_packed->device_event_dma_addr); + vring_packed->device_event_dma_addr, + dma_dev); =20 kfree(vring_packed->desc_state); kfree(vring_packed->desc_extra); @@ -1864,7 +1880,7 @@ static void vring_free_packed(struct vring_virtqueue_= packed *vring_packed, =20 static int vring_alloc_queue_packed(struct vring_virtqueue_packed *vring_p= acked, struct virtio_device *vdev, - u32 num) + u32 num, struct device *dma_dev) { struct vring_packed_desc *ring; struct vring_packed_desc_event *driver, *device; @@ -1875,7 +1891,8 @@ static int vring_alloc_queue_packed(struct vring_virt= queue_packed *vring_packed, =20 ring =3D vring_alloc_queue(vdev, ring_size_in_bytes, &ring_dma_addr, - GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO); + GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO, + dma_dev); if (!ring) goto err; =20 @@ -1887,7 +1904,8 @@ static int vring_alloc_queue_packed(struct vring_virt= queue_packed *vring_packed, =20 driver =3D vring_alloc_queue(vdev, event_size_in_bytes, &driver_event_dma_addr, - GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO); + GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO, + dma_dev); if (!driver) goto err; =20 @@ -1897,7 +1915,8 @@ static int vring_alloc_queue_packed(struct vring_virt= queue_packed *vring_packed, =20 device =3D vring_alloc_queue(vdev, event_size_in_bytes, &device_event_dma_addr, - GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO); + GFP_KERNEL | __GFP_NOWARN | __GFP_ZERO, + dma_dev); if (!device) goto err; =20 @@ -1909,7 +1928,7 @@ static int vring_alloc_queue_packed(struct vring_virt= queue_packed *vring_packed, return 0; =20 err: - vring_free_packed(vring_packed, vdev); + vring_free_packed(vring_packed, vdev, dma_dev); return -ENOMEM; } =20 @@ -1987,13 +2006,14 @@ static struct virtqueue *vring_create_virtqueue_pac= ked( bool context, bool (*notify)(struct virtqueue *), void (*callback)(struct virtqueue *), - const char *name) + const char *name, + struct device *dma_dev) { struct vring_virtqueue_packed vring_packed =3D {}; struct vring_virtqueue *vq; int err; =20 - if (vring_alloc_queue_packed(&vring_packed, vdev, num)) + if (vring_alloc_queue_packed(&vring_packed, vdev, num, dma_dev)) goto err_ring; =20 vq =3D kmalloc(sizeof(*vq), GFP_KERNEL); @@ -2014,6 +2034,7 @@ static struct virtqueue *vring_create_virtqueue_packe= d( vq->broken =3D false; #endif vq->packed_ring =3D true; + vq->dma_dev =3D dma_dev; vq->use_dma_api =3D vring_use_dma_api(vdev); =20 vq->indirect =3D virtio_has_feature(vdev, VIRTIO_RING_F_INDIRECT_DESC) && @@ -2040,7 +2061,7 @@ static struct virtqueue *vring_create_virtqueue_packe= d( err_state_extra: kfree(vq); err_vq: - vring_free_packed(&vring_packed, vdev); + vring_free_packed(&vring_packed, vdev, dma_dev); err_ring: return NULL; } @@ -2052,7 +2073,7 @@ static int virtqueue_resize_packed(struct virtqueue *= _vq, u32 num) struct virtio_device *vdev =3D _vq->vdev; int err; =20 - if (vring_alloc_queue_packed(&vring_packed, vdev, num)) + if (vring_alloc_queue_packed(&vring_packed, vdev, num, vring_dma_dev(vq))) goto err_ring; =20 err =3D vring_alloc_state_extra_packed(&vring_packed); @@ -2069,7 +2090,7 @@ static int virtqueue_resize_packed(struct virtqueue *= _vq, u32 num) return 0; =20 err_state_extra: - vring_free_packed(&vring_packed, vdev); + vring_free_packed(&vring_packed, vdev, vring_dma_dev(vq)); err_ring: virtqueue_reinit_packed(vq); return -ENOMEM; @@ -2481,7 +2502,8 @@ static struct virtqueue *__vring_new_virtqueue(unsign= ed int index, bool context, bool (*notify)(struct virtqueue *), void (*callback)(struct virtqueue *), - const char *name) + const char *name, + struct device *dma_dev) { struct vring_virtqueue *vq; int err; @@ -2507,6 +2529,7 @@ static struct virtqueue *__vring_new_virtqueue(unsign= ed int index, #else vq->broken =3D false; #endif + vq->dma_dev =3D dma_dev; vq->use_dma_api =3D vring_use_dma_api(vdev); =20 vq->indirect =3D virtio_has_feature(vdev, VIRTIO_RING_F_INDIRECT_DESC) && @@ -2549,14 +2572,39 @@ struct virtqueue *vring_create_virtqueue( if (virtio_has_feature(vdev, VIRTIO_F_RING_PACKED)) return vring_create_virtqueue_packed(index, num, vring_align, vdev, weak_barriers, may_reduce_num, - context, notify, callback, name); + context, notify, callback, name, vdev->dev.parent); =20 return vring_create_virtqueue_split(index, num, vring_align, vdev, weak_barriers, may_reduce_num, - context, notify, callback, name); + context, notify, callback, name, vdev->dev.parent); } EXPORT_SYMBOL_GPL(vring_create_virtqueue); =20 +struct virtqueue *vring_create_virtqueue_dma( + unsigned int index, + unsigned int num, + unsigned int vring_align, + struct virtio_device *vdev, + bool weak_barriers, + bool may_reduce_num, + bool context, + bool (*notify)(struct virtqueue *), + void (*callback)(struct virtqueue *), + const char *name, + struct device *dma_dev) +{ + + if (virtio_has_feature(vdev, VIRTIO_F_RING_PACKED)) + return vring_create_virtqueue_packed(index, num, vring_align, + vdev, weak_barriers, may_reduce_num, + context, notify, callback, name, dma_dev); + + return vring_create_virtqueue_split(index, num, vring_align, + vdev, weak_barriers, may_reduce_num, + context, notify, callback, name, dma_dev); +} +EXPORT_SYMBOL_GPL(vring_create_virtqueue_dma); + /** * virtqueue_resize - resize the vring of vq * @_vq: the struct virtqueue we're talking about. @@ -2645,7 +2693,8 @@ struct virtqueue *vring_new_virtqueue(unsigned int in= dex, =20 vring_init(&vring_split.vring, num, pages, vring_align); return __vring_new_virtqueue(index, &vring_split, vdev, weak_barriers, - context, notify, callback, name); + context, notify, callback, name, + vdev->dev.parent); } EXPORT_SYMBOL_GPL(vring_new_virtqueue); =20 @@ -2658,17 +2707,20 @@ static void vring_free(struct virtqueue *_vq) vring_free_queue(vq->vq.vdev, vq->packed.ring_size_in_bytes, vq->packed.vring.desc, - vq->packed.ring_dma_addr); + vq->packed.ring_dma_addr, + vring_dma_dev(vq)); =20 vring_free_queue(vq->vq.vdev, vq->packed.event_size_in_bytes, vq->packed.vring.driver, - vq->packed.driver_event_dma_addr); + vq->packed.driver_event_dma_addr, + vring_dma_dev(vq)); =20 vring_free_queue(vq->vq.vdev, vq->packed.event_size_in_bytes, vq->packed.vring.device, - vq->packed.device_event_dma_addr); + vq->packed.device_event_dma_addr, + vring_dma_dev(vq)); =20 kfree(vq->packed.desc_state); kfree(vq->packed.desc_extra); @@ -2676,7 +2728,8 @@ static void vring_free(struct virtqueue *_vq) vring_free_queue(vq->vq.vdev, vq->split.queue_size_in_bytes, vq->split.vring.desc, - vq->split.queue_dma_addr); + vq->split.queue_dma_addr, + vring_dma_dev(vq)); } } if (!vq->packed_ring) { diff --git a/include/linux/virtio_ring.h b/include/linux/virtio_ring.h index 8b8af1a38991..8b95b69ef694 100644 --- a/include/linux/virtio_ring.h +++ b/include/linux/virtio_ring.h @@ -76,6 +76,22 @@ struct virtqueue *vring_create_virtqueue(unsigned int in= dex, void (*callback)(struct virtqueue *vq), const char *name); =20 +/* + * Creates a virtqueue and allocates the descriptor ring with per + * virtqueue DMA device. + */ +struct virtqueue *vring_create_virtqueue_dma(unsigned int index, + unsigned int num, + unsigned int vring_align, + struct virtio_device *vdev, + bool weak_barriers, + bool may_reduce_num, + bool ctx, + bool (*notify)(struct virtqueue *vq), + void (*callback)(struct virtqueue *vq), + const char *name, + struct device *dma_dev); + /* * Creates a virtqueue with a standard layout but a caller-allocated * ring. --=20 2.25.1 From nobody Sun Sep 14 18:26:44 2025 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id B94AFC00A5A for ; Thu, 19 Jan 2023 06:16:43 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229674AbjASGQm (ORCPT ); Thu, 19 Jan 2023 01:16:42 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:48678 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229468AbjASGQj (ORCPT ); Thu, 19 Jan 2023 01:16:39 -0500 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 268CC66CDB for ; Wed, 18 Jan 2023 22:15:44 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1674108943; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=bKtmWzjGbhnlXcNdJOP0P8dah+AWLJO1bW5+obdp/Uc=; b=edNp9wM0SYcJz4bdK/cUCHtjU9eWiLTZTsW6cys0vdcml3dE5+WTr3fwE8Hbu717lN7DT+ 7e062Rz96acIzBHJSABXGnp4PXORAQELF4YYHxhvJfNQdVIwNyozsJ7zT4eH9HqzD4rz3Q JaSWeaA2RrgAdOmTV7CsvNkPwdvKM+E= Received: from mimecast-mx02.redhat.com (mimecast-mx02.redhat.com [66.187.233.88]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-516-IBRknEX8PwiykbLfboCRWg-1; Thu, 19 Jan 2023 01:15:41 -0500 X-MC-Unique: IBRknEX8PwiykbLfboCRWg-1 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id 6C6D885CBE0; Thu, 19 Jan 2023 06:15:41 +0000 (UTC) Received: from localhost.localdomain (ovpn-13-97.pek2.redhat.com [10.72.13.97]) by smtp.corp.redhat.com (Postfix) with ESMTP id 0B2871121315; Thu, 19 Jan 2023 06:15:37 +0000 (UTC) From: Jason Wang To: mst@redhat.com, jasowang@redhat.com Cc: elic@nvidia.com, gdawar@amd.com, tanuj.kamde@amd.com, linux-kernel@vger.kernel.org, virtualization@lists.linux-foundation.org Subject: [PATCH V2 2/5] vdpa: introduce get_vq_dma_device() Date: Thu, 19 Jan 2023 14:15:22 +0800 Message-Id: <20230119061525.75068-3-jasowang@redhat.com> In-Reply-To: <20230119061525.75068-1-jasowang@redhat.com> References: <20230119061525.75068-1-jasowang@redhat.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Scanned-By: MIMEDefang 3.1 on 10.11.54.3 Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" This patch introduces a new method to query the dma device that is use for a specific virtqueue. Reviewed-by: Eli Cohen Tested-by: Eli Cohen Signed-off-by: Jason Wang --- include/linux/vdpa.h | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/include/linux/vdpa.h b/include/linux/vdpa.h index 6d0f5e4e82c2..3ec13aee35f5 100644 --- a/include/linux/vdpa.h +++ b/include/linux/vdpa.h @@ -282,6 +282,11 @@ struct vdpa_map_file { * @iova: iova to be unmapped * @size: size of the area * Returns integer: success (0) or error (< 0) + * @get_vq_dma_dev: Get the dma device for a specific + * virtqueue (optional) + * @vdev: vdpa device + * @idx: virtqueue index + * Returns pointer to structure device or error (NULL) * @free: Free resources that belongs to vDPA (optional) * @vdev: vdpa device */ @@ -341,6 +346,7 @@ struct vdpa_config_ops { u64 iova, u64 size); int (*set_group_asid)(struct vdpa_device *vdev, unsigned int group, unsigned int asid); + struct device *(*get_vq_dma_dev)(struct vdpa_device *vdev, u16 idx); =20 /* Free device resources */ void (*free)(struct vdpa_device *vdev); --=20 2.25.1 From nobody Sun Sep 14 18:26:44 2025 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 9BDE5C00A5A for ; Thu, 19 Jan 2023 06:16:58 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229898AbjASGQ5 (ORCPT ); Thu, 19 Jan 2023 01:16:57 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:48712 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229690AbjASGQn (ORCPT ); Thu, 19 Jan 2023 01:16:43 -0500 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.133.124]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id EC0BEE3 for ; Wed, 18 Jan 2023 22:15:49 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1674108949; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=bCPNv1jA64AAqs6kIoQB13LtER9mryXWXv7FUgbd/1w=; b=dgTpjS9ILGDldWi5dptAH8ElphiNNHDpys8rhkbQDnp4/AUVBo+7v0CqD369pIDFwdGHIA hCrqzwW3umfCAAumFVnvo3BTRwdf9atmcujHAmPt9Q1TSiVsohd5YK76mT66f6jABDZFo0 MwYolitof/xVHWriYDx4THlA7MNbCBQ= Received: from mimecast-mx02.redhat.com (mimecast-mx02.redhat.com [66.187.233.88]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-594-B1gWfFU9MPStkjrxEx4H-g-1; Thu, 19 Jan 2023 01:15:45 -0500 X-MC-Unique: B1gWfFU9MPStkjrxEx4H-g-1 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id 942498A0100; Thu, 19 Jan 2023 06:15:45 +0000 (UTC) Received: from localhost.localdomain (ovpn-13-97.pek2.redhat.com [10.72.13.97]) by smtp.corp.redhat.com (Postfix) with ESMTP id 31C881121315; Thu, 19 Jan 2023 06:15:41 +0000 (UTC) From: Jason Wang To: mst@redhat.com, jasowang@redhat.com Cc: elic@nvidia.com, gdawar@amd.com, tanuj.kamde@amd.com, linux-kernel@vger.kernel.org, virtualization@lists.linux-foundation.org Subject: [PATCH V2 3/5] virtio-vdpa: support per vq dma device Date: Thu, 19 Jan 2023 14:15:23 +0800 Message-Id: <20230119061525.75068-4-jasowang@redhat.com> In-Reply-To: <20230119061525.75068-1-jasowang@redhat.com> References: <20230119061525.75068-1-jasowang@redhat.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Scanned-By: MIMEDefang 3.1 on 10.11.54.3 Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" This patch adds the support of per vq dma device for virito-vDPA. vDPA parents then are allowed to use different DMA devices. This is useful for the parents that have software or emulated virtqueues. Reviewed-by: Eli Cohen Tested-by: Eli Cohen Signed-off-by: Jason Wang --- drivers/virtio/virtio_vdpa.c | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/drivers/virtio/virtio_vdpa.c b/drivers/virtio/virtio_vdpa.c index 9670cc79371d..d7f5af62ddaa 100644 --- a/drivers/virtio/virtio_vdpa.c +++ b/drivers/virtio/virtio_vdpa.c @@ -135,6 +135,7 @@ virtio_vdpa_setup_vq(struct virtio_device *vdev, unsign= ed int index, { struct virtio_vdpa_device *vd_dev =3D to_virtio_vdpa_device(vdev); struct vdpa_device *vdpa =3D vd_get_vdpa(vdev); + struct device *dma_dev; const struct vdpa_config_ops *ops =3D vdpa->config; struct virtio_vdpa_vq_info *info; struct vdpa_callback cb; @@ -175,9 +176,15 @@ virtio_vdpa_setup_vq(struct virtio_device *vdev, unsig= ned int index, =20 /* Create the vring */ align =3D ops->get_vq_align(vdpa); - vq =3D vring_create_virtqueue(index, max_num, align, vdev, - true, may_reduce_num, ctx, - virtio_vdpa_notify, callback, name); + + if (ops->get_vq_dma_dev) + dma_dev =3D ops->get_vq_dma_dev(vdpa, index); + else + dma_dev =3D vdpa_get_dma_dev(vdpa); + vq =3D vring_create_virtqueue_dma(index, max_num, align, vdev, + true, may_reduce_num, ctx, + virtio_vdpa_notify, callback, + name, dma_dev); if (!vq) { err =3D -ENOMEM; goto error_new_virtqueue; --=20 2.25.1 From nobody Sun Sep 14 18:26:44 2025 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id D5294C00A5A for ; Thu, 19 Jan 2023 06:17:06 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S229958AbjASGRF (ORCPT ); Thu, 19 Jan 2023 01:17:05 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:48748 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229695AbjASGQn (ORCPT ); Thu, 19 Jan 2023 01:16:43 -0500 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.129.124]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 8393E654E9 for ; Wed, 18 Jan 2023 22:15:56 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1674108955; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=+SMXVPjE8hhIEfNKKmiT1OISlo/3YeTVVQSZ6tsGfyw=; b=E4aJJE21ZfCud8z4vU2Q0H93kMyNwuHIGHJHffsm7jv6XhWqO2823Gj/rgzgGbqstQr0Tv vDMGLIpu5+M55T/YfRaYRt4I2r/5vsXnNVDppU7N7LJib7haQTVT/FKKZAw/TtjJF9X1Ct oQVnCyIDGh/3LRxQAXv1xMFdRhqJx7E= Received: from mimecast-mx02.redhat.com (mimecast-mx02.redhat.com [66.187.233.88]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-631-RCiPZeyiPgOMvVWjSTK2PA-1; Thu, 19 Jan 2023 01:15:50 -0500 X-MC-Unique: RCiPZeyiPgOMvVWjSTK2PA-1 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id C1298811E9C; Thu, 19 Jan 2023 06:15:49 +0000 (UTC) Received: from localhost.localdomain (ovpn-13-97.pek2.redhat.com [10.72.13.97]) by smtp.corp.redhat.com (Postfix) with ESMTP id 5F04E1121315; Thu, 19 Jan 2023 06:15:45 +0000 (UTC) From: Jason Wang To: mst@redhat.com, jasowang@redhat.com Cc: elic@nvidia.com, gdawar@amd.com, tanuj.kamde@amd.com, linux-kernel@vger.kernel.org, virtualization@lists.linux-foundation.org Subject: [PATCH V2 4/5] vdpa: set dma mask for vDPA device Date: Thu, 19 Jan 2023 14:15:24 +0800 Message-Id: <20230119061525.75068-5-jasowang@redhat.com> In-Reply-To: <20230119061525.75068-1-jasowang@redhat.com> References: <20230119061525.75068-1-jasowang@redhat.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Scanned-By: MIMEDefang 3.1 on 10.11.54.3 Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" Setting DMA mask for vDPA device in case that there are virtqueue that is not backed by DMA so the vDPA device could be advertised as the DMA device that is used by DMA API for software emulated virtqueues. Reviewed-by: Eli Cohen Tested-by: Eli Cohen Signed-off-by: Jason Wang --- drivers/vdpa/vdpa.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/vdpa/vdpa.c b/drivers/vdpa/vdpa.c index 8ef7aa1365cc..6821b2850bbb 100644 --- a/drivers/vdpa/vdpa.c +++ b/drivers/vdpa/vdpa.c @@ -39,6 +39,11 @@ static int vdpa_dev_probe(struct device *d) u32 max_num, min_num =3D 1; int ret =3D 0; =20 + d->dma_mask =3D &d->coherent_dma_mask; + ret =3D dma_set_mask_and_coherent(d, DMA_BIT_MASK(64)); + if (ret) + return ret; + max_num =3D ops->get_vq_num_max(vdev); if (ops->get_vq_num_min) min_num =3D ops->get_vq_num_min(vdev); --=20 2.25.1 From nobody Sun Sep 14 18:26:44 2025 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id EFC44C38142 for ; Thu, 19 Jan 2023 06:17:20 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S230064AbjASGRT (ORCPT ); Thu, 19 Jan 2023 01:17:19 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:48772 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229792AbjASGQv (ORCPT ); Thu, 19 Jan 2023 01:16:51 -0500 Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.129.124]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 9AF78360BE for ; Wed, 18 Jan 2023 22:16:05 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1674108964; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding: in-reply-to:in-reply-to:references:references; bh=7ggS+8BEq6Y5BuiP5CUK1tAuZNnVqha6988K92SB/Gc=; b=fdTz1b6yVy/KAmjzHDOaU6f3DVyi28VLw0+srQwQKeDzdg9BOwwRlxQv/Km8SwwOCc4mrI bn88TOscpSVTgxVzqbD+mdqurQP8VxbcsmGIB/ogAnS2mv4TwILDjI0fvyHSr50W2T72KQ pS1WbD2esp067ubGYd84qirBeIZCvEk= Received: from mimecast-mx02.redhat.com (mx3-rdu2.redhat.com [66.187.233.73]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-673-_7yl938FMyWjqThxXudjuQ-1; Thu, 19 Jan 2023 01:15:54 -0500 X-MC-Unique: _7yl938FMyWjqThxXudjuQ-1 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id E9C7C280605A; Thu, 19 Jan 2023 06:15:53 +0000 (UTC) Received: from localhost.localdomain (ovpn-13-97.pek2.redhat.com [10.72.13.97]) by smtp.corp.redhat.com (Postfix) with ESMTP id 876441121315; Thu, 19 Jan 2023 06:15:50 +0000 (UTC) From: Jason Wang To: mst@redhat.com, jasowang@redhat.com Cc: elic@nvidia.com, gdawar@amd.com, tanuj.kamde@amd.com, linux-kernel@vger.kernel.org, virtualization@lists.linux-foundation.org Subject: [PATCH V2 5/5] vdpa: mlx5: support per virtqueue dma device Date: Thu, 19 Jan 2023 14:15:25 +0800 Message-Id: <20230119061525.75068-6-jasowang@redhat.com> In-Reply-To: <20230119061525.75068-1-jasowang@redhat.com> References: <20230119061525.75068-1-jasowang@redhat.com> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Scanned-By: MIMEDefang 3.1 on 10.11.54.3 Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Content-Type: text/plain; charset="utf-8" This patch implements per virtqueue dma device for mlx5_vdpa. This is needed for virtio_vdpa to work for CVQ which is backed by vringh but not DMA. We simply advertise the vDPA device itself as the DMA device for CVQ then DMA API can simply use PA so the identical mapping for CVQ can still be used. Otherwise the identical (1:1) mapping won't work when platform IOMMU is enabled since the IOVA is allocated on demand which is not necessarily the PA. This fixes the following crash when mlx5 vDPA device is bound to virtio-vdpa with platform IOMMU enabled but not in passthrough mode: BUG: unable to handle page fault for address: ff2fb3063deb1002 #PF: supervisor read access in kernel mode #PF: error_code(0x0000) - not-present page PGD 1393001067 P4D 1393002067 PUD 0 Oops: 0000 [#1] PREEMPT SMP NOPTI CPU: 55 PID: 8923 Comm: kworker/u112:3 Kdump: loaded Not tainted 6.1.0+ #7 Hardware name: Dell Inc. PowerEdge R750/0PJ80M, BIOS 1.5.4 12/17/2021 Workqueue: mlx5_vdpa_wq mlx5_cvq_kick_handler [mlx5_vdpa] RIP: 0010:vringh_getdesc_iotlb+0x93/0x1d0 [vringh] Code: 14 25 40 ef 01 00 83 82 c0 0a 00 00 01 48 2b 05 93 5a 1b ea 8b 4c 24 = 14 48 c1 f8 06 48 c1 e0 0c 48 03 05 90 5a 1b ea 48 01 c8 <0f> b7 00 83 aa c= 0 0a 00 00 01 65 ff 0d bc e4 41 3f 0f 84 05 01 00 RSP: 0018:ff46821ba664fdf8 EFLAGS: 00010282 RAX: ff2fb3063deb1002 RBX: 0000000000000a20 RCX: 0000000000000002 RDX: ff2fb318d2f94380 RSI: 0000000000000002 RDI: 0000000000000001 RBP: ff2fb3065e832410 R08: ff46821ba664fe00 R09: 0000000000000001 R10: 0000000000000000 R11: 000000000000000d R12: ff2fb3065e832488 R13: ff2fb3065e8324a8 R14: ff2fb3065e8324c8 R15: ff2fb3065e8324a8 FS: 0000000000000000(0000) GS:ff2fb3257fac0000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: ff2fb3063deb1002 CR3: 0000001392010006 CR4: 0000000000771ee0 DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 PKRU: 55555554 Call Trace: mlx5_cvq_kick_handler+0x89/0x2b0 [mlx5_vdpa] process_one_work+0x1e2/0x3b0 ? rescuer_thread+0x390/0x390 worker_thread+0x50/0x3a0 ? rescuer_thread+0x390/0x390 kthread+0xd6/0x100 ? kthread_complete_and_exit+0x20/0x20 ret_from_fork+0x1f/0x30 Reviewed-by: Eli Cohen Tested-by: Eli Cohen Signed-off-by: Jason Wang --- Changes since V1: - make mlx5_get_vq_dma_dev() static --- drivers/vdpa/mlx5/net/mlx5_vnet.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/drivers/vdpa/mlx5/net/mlx5_vnet.c b/drivers/vdpa/mlx5/net/mlx5= _vnet.c index 6632651b1e54..97d1ada7f4db 100644 --- a/drivers/vdpa/mlx5/net/mlx5_vnet.c +++ b/drivers/vdpa/mlx5/net/mlx5_vnet.c @@ -2682,6 +2682,16 @@ static int mlx5_vdpa_set_map(struct vdpa_device *vde= v, unsigned int asid, return err; } =20 +static struct device *mlx5_get_vq_dma_dev(struct vdpa_device *vdev, u16 id= x) +{ + struct mlx5_vdpa_dev *mvdev =3D to_mvdev(vdev); + + if (is_ctrl_vq_idx(mvdev, idx)) + return &vdev->dev; + + return mvdev->vdev.dma_dev; +} + static void mlx5_vdpa_free(struct vdpa_device *vdev) { struct mlx5_vdpa_dev *mvdev =3D to_mvdev(vdev); @@ -2897,6 +2907,7 @@ static const struct vdpa_config_ops mlx5_vdpa_ops =3D= { .get_generation =3D mlx5_vdpa_get_generation, .set_map =3D mlx5_vdpa_set_map, .set_group_asid =3D mlx5_set_group_asid, + .get_vq_dma_dev =3D mlx5_get_vq_dma_dev, .free =3D mlx5_vdpa_free, .suspend =3D mlx5_vdpa_suspend, }; --=20 2.25.1