RDMA/mlx5: use kmalloc() for UMR translation buffers

mlx5r_umr_alloc_xlt() allocates physically contiguous scratch buffers
that are DMA mapped only in the DMA_TO_DEVICE direction. kmalloc()
provides the required contiguity and alignment for these sizes while
preserving the existing GFP allocation policy.

The emergency translation buffer has the same requirements. Convert all
of these UMR buffers to kmalloc() and release them with kfree(), which no
longer requires the caller to supply the allocation order.

Link: https://patch.msgid.link/20260715-get_pages-to-kmalloc-v1-4-b0b7fce288be@nvidia.com
Acked-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Signed-off-by: Leon Romanovsky <leonro@nvidia.com>
This commit is contained in:
Leon Romanovsky 2026-07-16 05:03:32 -04:00 committed by Leon Romanovsky
parent ed3760b376
commit b2022068de
2 changed files with 9 additions and 10 deletions

View File

@ -5500,13 +5500,13 @@ static int __init mlx5_ib_init(void)
{
int ret;
xlt_emergency_page = (void *)__get_free_page(GFP_KERNEL);
xlt_emergency_page = kmalloc(PAGE_SIZE, GFP_KERNEL);
if (!xlt_emergency_page)
return -ENOMEM;
mlx5_ib_event_wq = alloc_ordered_workqueue("mlx5_ib_event_wq", 0);
if (!mlx5_ib_event_wq) {
free_page((unsigned long)xlt_emergency_page);
kfree(xlt_emergency_page);
return -ENOMEM;
}
@ -5540,7 +5540,7 @@ static int __init mlx5_ib_init(void)
mlx5_ib_qp_event_cleanup();
qp_event_err:
destroy_workqueue(mlx5_ib_event_wq);
free_page((unsigned long)xlt_emergency_page);
kfree(xlt_emergency_page);
return ret;
}
@ -5553,7 +5553,7 @@ static void __exit mlx5_ib_cleanup(void)
mlx5_ib_qp_event_cleanup();
destroy_workqueue(mlx5_ib_event_wq);
free_page((unsigned long)xlt_emergency_page);
kfree(xlt_emergency_page);
}
module_init(mlx5_ib_init);

View File

@ -1,6 +1,7 @@
// SPDX-License-Identifier: GPL-2.0 OR Linux-OpenIB
/* Copyright (c) 2022, NVIDIA CORPORATION & AFFILIATES. */
#include <linux/slab.h>
#include <rdma/ib_umem_odp.h>
#include <rdma/iter.h>
#include "mlx5_ib.h"
@ -517,22 +518,20 @@ static void *mlx5r_umr_alloc_xlt(size_t *nents, size_t ent_size, gfp_t gfp_mask)
size = min_t(size_t, ent_size * ALIGN(*nents, xlt_chunk_align),
MLX5_MAX_UMR_CHUNK);
*nents = size / ent_size;
res = (void *)__get_free_pages(gfp_mask | __GFP_NOWARN,
get_order(size));
res = kmalloc(size, gfp_mask | __GFP_NOWARN);
if (res)
return res;
if (size > MLX5_SPARE_UMR_CHUNK) {
size = MLX5_SPARE_UMR_CHUNK;
*nents = size / ent_size;
res = (void *)__get_free_pages(gfp_mask | __GFP_NOWARN,
get_order(size));
res = kmalloc(size, gfp_mask | __GFP_NOWARN);
if (res)
return res;
}
*nents = PAGE_SIZE / ent_size;
res = (void *)__get_free_page(gfp_mask);
res = kmalloc(PAGE_SIZE, gfp_mask);
if (res)
return res;
@ -548,7 +547,7 @@ static void mlx5r_umr_free_xlt(void *xlt, size_t length)
return;
}
free_pages((unsigned long)xlt, get_order(length));
kfree(xlt);
}
static void mlx5r_umr_unmap_free_xlt(struct mlx5_ib_dev *dev, void *xlt,