diff options
Diffstat (limited to 'drivers/vfio')
-rw-r--r-- | drivers/vfio/iommufd.c | 24 |
1 files changed, 17 insertions, 7 deletions
diff --git a/drivers/vfio/iommufd.c b/drivers/vfio/iommufd.c index db4efbd56042..0695a06db30d 100644 --- a/drivers/vfio/iommufd.c +++ b/drivers/vfio/iommufd.c @@ -138,10 +138,18 @@ static const struct iommufd_access_ops vfio_user_ops = { int vfio_iommufd_emulated_bind(struct vfio_device *vdev, struct iommufd_ctx *ictx, u32 *out_device_id) { + struct iommufd_access *user; + lockdep_assert_held(&vdev->dev_set->lock); - vdev->iommufd_ictx = ictx; iommufd_ctx_get(ictx); + user = iommufd_access_create(ictx, &vfio_user_ops, vdev); + if (IS_ERR(user)) { + iommufd_ctx_put(ictx); + return PTR_ERR(user); + } + vdev->iommufd_access = user; + vdev->iommufd_ictx = ictx; return 0; } EXPORT_SYMBOL_GPL(vfio_iommufd_emulated_bind); @@ -152,6 +160,7 @@ void vfio_iommufd_emulated_unbind(struct vfio_device *vdev) if (vdev->iommufd_access) { iommufd_access_destroy(vdev->iommufd_access); + vdev->iommufd_attached = false; vdev->iommufd_access = NULL; } iommufd_ctx_put(vdev->iommufd_ictx); @@ -161,15 +170,16 @@ EXPORT_SYMBOL_GPL(vfio_iommufd_emulated_unbind); int vfio_iommufd_emulated_attach_ioas(struct vfio_device *vdev, u32 *pt_id) { - struct iommufd_access *user; + int rc; lockdep_assert_held(&vdev->dev_set->lock); - user = iommufd_access_create(vdev->iommufd_ictx, *pt_id, &vfio_user_ops, - vdev); - if (IS_ERR(user)) - return PTR_ERR(user); - vdev->iommufd_access = user; + if (vdev->iommufd_attached) + return -EBUSY; + rc = iommufd_access_attach(vdev->iommufd_access, *pt_id); + if (rc) + return rc; + vdev->iommufd_attached = true; return 0; } EXPORT_SYMBOL_GPL(vfio_iommufd_emulated_attach_ioas); |