在 2022/4/14 00:31, Eugenio Pérez 写道:
> Now that different vqs can have different ASIDs its easier to track them
> using reference counters.
>
> QEMU's glib version still does not have them so we've copied g_rc_box,
> so the implementation can be converted to glib's one when the minimum
> version is raised.
>
> Signed-off-by: Eugenio Pérez <eperezma@redhat.com>
> ---
I'm not sure if it's too early to introduce things like this since we
have at most 2 ASIDs. This is probably only needed when we want to
expose ASIDs to guest.
Let's see how it goes for the following patch anyhow.
Thanks
> hw/virtio/vhost-iova-tree.h | 5 +++--
> hw/virtio/vhost-iova-tree.c | 21 +++++++++++++++++++--
> 2 files changed, 22 insertions(+), 4 deletions(-)
>
> diff --git a/hw/virtio/vhost-iova-tree.h b/hw/virtio/vhost-iova-tree.h
> index 6a4f24e0f9..2fc825d7b1 100644
> --- a/hw/virtio/vhost-iova-tree.h
> +++ b/hw/virtio/vhost-iova-tree.h
> @@ -16,8 +16,9 @@
> typedef struct VhostIOVATree VhostIOVATree;
>
> VhostIOVATree *vhost_iova_tree_new(uint64_t iova_first, uint64_t iova_last);
> -void vhost_iova_tree_delete(VhostIOVATree *iova_tree);
> -G_DEFINE_AUTOPTR_CLEANUP_FUNC(VhostIOVATree, vhost_iova_tree_delete);
> +VhostIOVATree *vhost_iova_tree_acquire(VhostIOVATree *iova_tree);
> +void vhost_iova_tree_release(VhostIOVATree *iova_tree);
> +G_DEFINE_AUTOPTR_CLEANUP_FUNC(VhostIOVATree, vhost_iova_tree_release);
>
> const DMAMap *vhost_iova_tree_find_iova(const VhostIOVATree *iova_tree,
> const DMAMap *map);
> diff --git a/hw/virtio/vhost-iova-tree.c b/hw/virtio/vhost-iova-tree.c
> index 55fed1fefb..31445cbdfc 100644
> --- a/hw/virtio/vhost-iova-tree.c
> +++ b/hw/virtio/vhost-iova-tree.c
> @@ -28,6 +28,9 @@ struct VhostIOVATree {
>
> /* IOVA address to qemu memory maps. */
> IOVATree *iova_taddr_map;
> +
> + /* Reference count */
> + size_t refcnt;
> };
>
> /**
> @@ -44,14 +47,28 @@ VhostIOVATree *vhost_iova_tree_new(hwaddr iova_first, hwaddr iova_last)
> tree->iova_last = iova_last;
>
> tree->iova_taddr_map = iova_tree_new();
> + tree->refcnt = 1;
> return tree;
> }
>
> /**
> - * Delete an iova tree
> + * Increases the reference count of the iova tree
> + */
> +VhostIOVATree *vhost_iova_tree_acquire(VhostIOVATree *iova_tree)
> +{
> + ++iova_tree->refcnt;
> + return iova_tree;
> +}
> +
> +/**
> + * Decrease reference counter of iova tree, freeing if it reaches 0
> */
> -void vhost_iova_tree_delete(VhostIOVATree *iova_tree)
> +void vhost_iova_tree_release(VhostIOVATree *iova_tree)
> {
> + if (--iova_tree->refcnt) {
> + return;
> + }
> +
> iova_tree_destroy(iova_tree->iova_taddr_map);
> g_free(iova_tree);
> }