aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/drivers/vdpa/mlx5/core/mr.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/vdpa/mlx5/core/mr.c')
-rw-r--r--drivers/vdpa/mlx5/core/mr.c87
1 files changed, 47 insertions, 40 deletions
diff --git a/drivers/vdpa/mlx5/core/mr.c b/drivers/vdpa/mlx5/core/mr.c
index abd6a6fb122f..00eff5a07152 100644
--- a/drivers/vdpa/mlx5/core/mr.c
+++ b/drivers/vdpa/mlx5/core/mr.c
@@ -495,30 +495,51 @@ static void destroy_user_mr(struct mlx5_vdpa_dev *mvdev, struct mlx5_vdpa_mr *mr
static void _mlx5_vdpa_destroy_mr(struct mlx5_vdpa_dev *mvdev, struct mlx5_vdpa_mr *mr)
{
- if (!mr->initialized)
- return;
-
if (mr->user_mr)
destroy_user_mr(mvdev, mr);
else
destroy_dma_mr(mvdev, mr);
-
- mr->initialized = false;
}
void mlx5_vdpa_destroy_mr(struct mlx5_vdpa_dev *mvdev,
struct mlx5_vdpa_mr *mr)
{
+ if (!mr)
+ return;
+
mutex_lock(&mvdev->mr_mtx);
_mlx5_vdpa_destroy_mr(mvdev, mr);
+ if (mvdev->mr == mr)
+ mvdev->mr = NULL;
+
+ mutex_unlock(&mvdev->mr_mtx);
+
+ kfree(mr);
+}
+
+void mlx5_vdpa_update_mr(struct mlx5_vdpa_dev *mvdev,
+ struct mlx5_vdpa_mr *new_mr,
+ unsigned int asid)
+{
+ struct mlx5_vdpa_mr *old_mr = mvdev->mr;
+
+ mutex_lock(&mvdev->mr_mtx);
+
+ mvdev->mr = new_mr;
+ if (old_mr) {
+ _mlx5_vdpa_destroy_mr(mvdev, old_mr);
+ kfree(old_mr);
+ }
+
mutex_unlock(&mvdev->mr_mtx);
+
}
void mlx5_vdpa_destroy_mr_resources(struct mlx5_vdpa_dev *mvdev)
{
- mlx5_vdpa_destroy_mr(mvdev, &mvdev->mr);
+ mlx5_vdpa_destroy_mr(mvdev, mvdev->mr);
prune_iotlb(mvdev);
}
@@ -528,52 +549,36 @@ static int _mlx5_vdpa_create_mr(struct mlx5_vdpa_dev *mvdev,
{
int err;
- if (mr->initialized)
- return 0;
-
if (iotlb)
err = create_user_mr(mvdev, mr, iotlb);
else
err = create_dma_mr(mvdev, mr);
- if (err)
- return err;
-
- mr->initialized = true;
-
- return 0;
+ return err;
}
-int mlx5_vdpa_create_mr(struct mlx5_vdpa_dev *mvdev,
- struct mlx5_vdpa_mr *mr,
- struct vhost_iotlb *iotlb)
+struct mlx5_vdpa_mr *mlx5_vdpa_create_mr(struct mlx5_vdpa_dev *mvdev,
+ struct vhost_iotlb *iotlb)
{
+ struct mlx5_vdpa_mr *mr;
int err;
+ mr = kzalloc(sizeof(*mr), GFP_KERNEL);
+ if (!mr)
+ return ERR_PTR(-ENOMEM);
+
mutex_lock(&mvdev->mr_mtx);
err = _mlx5_vdpa_create_mr(mvdev, mr, iotlb);
mutex_unlock(&mvdev->mr_mtx);
- return err;
-}
-
-int mlx5_vdpa_handle_set_map(struct mlx5_vdpa_dev *mvdev, struct vhost_iotlb *iotlb,
- bool *change_map, unsigned int asid)
-{
- struct mlx5_vdpa_mr *mr = &mvdev->mr;
- int err = 0;
+ if (err)
+ goto out_err;
- *change_map = false;
- mutex_lock(&mvdev->mr_mtx);
- if (mr->initialized) {
- mlx5_vdpa_info(mvdev, "memory map update\n");
- *change_map = true;
- }
- if (!*change_map)
- err = _mlx5_vdpa_create_mr(mvdev, mr, iotlb);
- mutex_unlock(&mvdev->mr_mtx);
+ return mr;
- return err;
+out_err:
+ kfree(mr);
+ return ERR_PTR(err);
}
int mlx5_vdpa_update_cvq_iotlb(struct mlx5_vdpa_dev *mvdev,
@@ -597,11 +602,13 @@ int mlx5_vdpa_update_cvq_iotlb(struct mlx5_vdpa_dev *mvdev,
int mlx5_vdpa_create_dma_mr(struct mlx5_vdpa_dev *mvdev)
{
- int err;
+ struct mlx5_vdpa_mr *mr;
- err = mlx5_vdpa_create_mr(mvdev, &mvdev->mr, NULL);
- if (err)
- return err;
+ mr = mlx5_vdpa_create_mr(mvdev, NULL);
+ if (IS_ERR(mr))
+ return PTR_ERR(mr);
+
+ mlx5_vdpa_update_mr(mvdev, mr, 0);
return mlx5_vdpa_update_cvq_iotlb(mvdev, NULL, 0);
}