From d9f3227f673b7d5aa0bdb822a2cc6be17e10f3e0 Mon Sep 17 00:00:00 2001 From: Shay Drory Date: Wed, 23 Sep 2026 13:38:20 +0300 Subject: [PATCH] net/mlx5: LAG, allocate v2p_map dynamically v2p_map was a fixed array sized MLX5_MAX_PORTS * MLX5_LAG_MAX_HASH_BUCKETS embedded in struct mlx5_lag. Turn it into a pointer allocated in mlx5_lag_dev_alloc() once ldev->ports is known, sized by the actual port count, and free it in mlx5_ldev_free(). The ldev->ports / ldev->buckets initialization is moved up so the allocation can use it. The matching scratch buffer in mlx5_modify_lag() is converted from a MLX5_MAX_PORTS-sized stack array to a kcalloc() of the same extent, with the trailing teardown reworked through a goto so the buffer is freed on every path. The memcpy() that previously relied on sizeof() of the stack array now uses the explicit ldev->ports * MLX5_LAG_MAX_HASH_BUCKETS span. No functional change; this removes v2p_map's dependency on MLX5_MAX_PORTS. Signed-off-by: Shay Drory Reviewed-by: Moshe Shemesh Reviewed-by: Akiva Goldberger Signed-off-by: Tariq Toukan Link: https://patch.msgid.link/20260923103830.1183-4-tariqt@nvidia.com Signed-off-by: Jakub Kicinski --- .../net/ethernet/mellanox/mlx5/core/lag/lag.c | 38 ++++++++++++++----- .../net/ethernet/mellanox/mlx5/core/lag/lag.h | 2 +- 2 files changed, 29 insertions(+), 11 deletions(-) diff --git a/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c b/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c index dd14cdc378de..6321f985c071 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c @@ -308,6 +308,7 @@ static void mlx5_ldev_free(struct kref *ref) cancel_work_sync(&ldev->speed_update_work); destroy_workqueue(ldev->wq); mutex_destroy(&ldev->lock); + kfree(ldev->v2p_map); kfree(ldev); } @@ -330,11 +331,16 @@ static struct mlx5_lag *mlx5_lag_dev_alloc(struct mlx5_core_dev *dev) if (!ldev) return NULL; + ldev->ports = MLX5_CAP_GEN(dev, num_lag_ports); + ldev->buckets = 1; + ldev->v2p_map = kcalloc(ldev->ports * MLX5_LAG_MAX_HASH_BUCKETS, + sizeof(*ldev->v2p_map), GFP_KERNEL); + if (!ldev->v2p_map) + goto err_v2p_map; + ldev->wq = create_singlethread_workqueue("mlx5_lag"); - if (!ldev->wq) { - kfree(ldev); - return NULL; - } + if (!ldev->wq) + goto err_wq; kref_init(&ldev->ref); mutex_init(&ldev->lock); @@ -358,10 +364,13 @@ static struct mlx5_lag *mlx5_lag_dev_alloc(struct mlx5_core_dev *dev) mlx5_core_err(dev, "Failed to init multipath lag err=%d\n", err); - ldev->ports = MLX5_CAP_GEN(dev, num_lag_ports); - ldev->buckets = 1; - return ldev; + +err_wq: + kfree(ldev->v2p_map); +err_v2p_map: + kfree(ldev); + return NULL; } int mlx5_lag_dev_get_netdev_idx(struct mlx5_lag *ldev, @@ -853,8 +862,8 @@ void mlx5_modify_lag(struct mlx5_lag *ldev, struct lag_tracker *tracker) { int first_idx = mlx5_lag_get_dev_index_by_seq(ldev, MLX5_LAG_P1); - u8 ports[MLX5_MAX_PORTS * MLX5_LAG_MAX_HASH_BUCKETS] = {}; struct mlx5_core_dev *dev0; + u8 *ports; int idx; int err; int i; @@ -864,6 +873,12 @@ void mlx5_modify_lag(struct mlx5_lag *ldev, return; dev0 = mlx5_lag_pf(ldev, first_idx)->dev; + + ports = kcalloc(ldev->ports * MLX5_LAG_MAX_HASH_BUCKETS, + sizeof(*ports), GFP_KERNEL); + if (!ports) + return; + mlx5_infer_tx_affinity_mapping(tracker, ldev, ldev->buckets, ports); mlx5_ldev_for_each(i, 0, ldev) { @@ -876,9 +891,10 @@ void mlx5_modify_lag(struct mlx5_lag *ldev, mlx5_core_err(dev0, "Failed to modify LAG (%d)\n", err); - return; + goto out; } - memcpy(ldev->v2p_map, ports, sizeof(ports)); + memcpy(ldev->v2p_map, ports, + ldev->ports * MLX5_LAG_MAX_HASH_BUCKETS); mlx5_lag_print_mapping(dev0, ldev, tracker, ldev->mode_flags); @@ -899,6 +915,8 @@ void mlx5_modify_lag(struct mlx5_lag *ldev, ndev); dev_put(ndev); } +out: + kfree(ports); } static int mlx5_lag_set_port_sel_mode(struct mlx5_lag *ldev, diff --git a/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.h b/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.h index e9f0ef83ce1d..8552792b9035 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.h +++ b/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.h @@ -85,7 +85,7 @@ struct mlx5_lag { u8 ports; u8 buckets; int mode_changes_in_progress; - u8 v2p_map[MLX5_MAX_PORTS * MLX5_LAG_MAX_HASH_BUCKETS]; + u8 *v2p_map; struct kref ref; struct xarray pfs; struct lag_tracker tracker;