Commit a0ffb4c1 authored by Mark Zhang's avatar Mark Zhang Committed by Jason Gunthorpe

RDMA/mlx5: Use different doorbell memory for different processes

In a fork scenario, the parent and child can have same virtual address and
also share the uverbs fd.  That causes to the list_for_each_entry search
return same doorbell physical page for all processes, even though that
page has been COW' or copied.

This patch takes the mm_struct into consideration during search, to make
sure that VA's belonging to different processes are not intermixed.

Resolves the malfunction of uverbs after fork in some specific cases.

Fixes: e126ba97 ("mlx5: Add driver for Mellanox Connect-IB adapters")
Link: https://lore.kernel.org/r/feacc23fe0bc6e1088c6824d5583798745e72405.1622726212.git.leonro@nvidia.comReviewed-by: default avatarJason Gunthorpe <jgg@nvidia.com>
Signed-off-by: default avatarMark Zhang <markzhang@nvidia.com>
Signed-off-by: default avatarLeon Romanovsky <leonro@nvidia.com>
Signed-off-by: default avatarJason Gunthorpe <jgg@nvidia.com>
parent a3e74fb9
...@@ -41,6 +41,7 @@ struct mlx5_ib_user_db_page { ...@@ -41,6 +41,7 @@ struct mlx5_ib_user_db_page {
struct ib_umem *umem; struct ib_umem *umem;
unsigned long user_virt; unsigned long user_virt;
int refcnt; int refcnt;
struct mm_struct *mm;
}; };
int mlx5_ib_db_map_user(struct mlx5_ib_ucontext *context, int mlx5_ib_db_map_user(struct mlx5_ib_ucontext *context,
...@@ -53,7 +54,8 @@ int mlx5_ib_db_map_user(struct mlx5_ib_ucontext *context, ...@@ -53,7 +54,8 @@ int mlx5_ib_db_map_user(struct mlx5_ib_ucontext *context,
mutex_lock(&context->db_page_mutex); mutex_lock(&context->db_page_mutex);
list_for_each_entry(page, &context->db_page_list, list) list_for_each_entry(page, &context->db_page_list, list)
if (page->user_virt == (virt & PAGE_MASK)) if ((current->mm == page->mm) &&
(page->user_virt == (virt & PAGE_MASK)))
goto found; goto found;
page = kmalloc(sizeof(*page), GFP_KERNEL); page = kmalloc(sizeof(*page), GFP_KERNEL);
...@@ -71,6 +73,8 @@ int mlx5_ib_db_map_user(struct mlx5_ib_ucontext *context, ...@@ -71,6 +73,8 @@ int mlx5_ib_db_map_user(struct mlx5_ib_ucontext *context,
kfree(page); kfree(page);
goto out; goto out;
} }
mmgrab(current->mm);
page->mm = current->mm;
list_add(&page->list, &context->db_page_list); list_add(&page->list, &context->db_page_list);
...@@ -91,6 +95,7 @@ void mlx5_ib_db_unmap_user(struct mlx5_ib_ucontext *context, struct mlx5_db *db) ...@@ -91,6 +95,7 @@ void mlx5_ib_db_unmap_user(struct mlx5_ib_ucontext *context, struct mlx5_db *db)
if (!--db->u.user_page->refcnt) { if (!--db->u.user_page->refcnt) {
list_del(&db->u.user_page->list); list_del(&db->u.user_page->list);
mmdrop(db->u.user_page->mm);
ib_umem_release(db->u.user_page->umem); ib_umem_release(db->u.user_page->umem);
kfree(db->u.user_page); kfree(db->u.user_page);
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment