[PATCH net-next 08/15] net/mlx5: LAG: replace fixed MLX5_MAX_PORTS arrays with dynamic allocation

From: Tariq Toukan

Date: Tue Nov 03 2026 - 14:34:06 EST


From: Shay Drory <shayd@xxxxxxxxxx>

Converts two fixed-size arrays sized to MLX5_MAX_PORTS into
dynamically allocated pointers:

- lag_mpesw.pf_metadata in mpesw.c/mpesw.h, sized by ldev->max_fns
- mdev array in mlx5_lag_query_cong_counters(), sized by ldev->ports

The cong-counters array is sized by ldev->ports, which is fixed at ldev
allocation, rather than by the LAG mode, so a mode change between the
allocation and filling the array cannot overflow it. The query loop is
bounded by the number of entries actually filled. A virt LAG is not
aggregated and queries only the given device, as its members are not
LAG ports.

Thus, removes the hard dependency on MLX5_MAX_PORTS.

Signed-off-by: Shay Drory <shayd@xxxxxxxxxx>
Reviewed-by: Mark Bloch <mbloch@xxxxxxxxxx>
Reviewed-by: Moshe Shemesh <moshe@xxxxxxxxxx>
Signed-off-by: Tariq Toukan <tariqt@xxxxxxxxxx>
---
drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c | 15 +++++++--------
.../net/ethernet/mellanox/mlx5/core/lag/mpesw.c | 12 ++++++++++++
.../net/ethernet/mellanox/mlx5/core/lag/mpesw.h | 2 +-
3 files changed, 20 insertions(+), 9 deletions(-)

diff --git a/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c b/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c
index 2b76d119cfa6..b873eb91fd0d 100644
--- a/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c
+++ b/drivers/net/ethernet/mellanox/mlx5/core/lag/lag.c
@@ -2917,7 +2917,9 @@ int mlx5_lag_query_cong_counters(struct mlx5_core_dev *dev,
if (!out)
return -ENOMEM;

- mdev = kvzalloc(sizeof(mdev[0]) * MLX5_MAX_PORTS, GFP_KERNEL);
+ ldev = mlx5_lag_dev(dev);
+ num_ports = ldev ? max_t(int, ldev->ports, 1) : 1;
+ mdev = kcalloc(num_ports, sizeof(mdev[0]), GFP_KERNEL);
if (!mdev) {
ret = -ENOMEM;
goto free_out;
@@ -2926,20 +2928,17 @@ int mlx5_lag_query_cong_counters(struct mlx5_core_dev *dev,
memset(values, 0, sizeof(*values) * num_counters);

spin_lock_irqsave(&lag_lock, flags);
- ldev = mlx5_lag_dev(dev);
- if (ldev && __mlx5_lag_is_active(ldev)) {
- num_ports = ldev->ports;
+ if (ldev && __mlx5_lag_is_active(ldev) && !ldev->virt_lag) {
mlx5_ldev_for_each(i, 0, ldev) {
fn = mlx5_lag_fn(ldev, i);
mdev[idx++] = fn->dev;
}
} else {
- num_ports = 1;
- mdev[MLX5_LAG_P1] = dev;
+ mdev[idx++] = dev;
}
spin_unlock_irqrestore(&lag_lock, flags);

- for (i = 0; i < num_ports; ++i) {
+ for (i = 0; i < idx; ++i) {
u32 in[MLX5_ST_SZ_DW(query_cong_statistics_in)] = {};

MLX5_SET(query_cong_statistics_in, in, opcode,
@@ -2954,7 +2953,7 @@ int mlx5_lag_query_cong_counters(struct mlx5_core_dev *dev,
}

free_mdev:
- kvfree(mdev);
+ kfree(mdev);
free_out:
kvfree(out);
return ret;
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.c b/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.c
index 6e3bef276611..584436668a5c 100644
--- a/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.c
+++ b/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.c
@@ -15,6 +15,9 @@ static void mlx5_mpesw_metadata_cleanup(struct mlx5_lag *ldev)
u32 pf_metadata;
int i;

+ if (!ldev->lag_mpesw.pf_metadata)
+ return;
+
mlx5_lag_for_each(i, 0, ldev, MLX5_LAG_FILTER_ALL) {
dev = mlx5_lag_fn(ldev, i)->dev;
esw = dev->priv.eswitch;
@@ -27,6 +30,9 @@ static void mlx5_mpesw_metadata_cleanup(struct mlx5_lag *ldev)
mlx5_esw_match_metadata_free(esw, pf_metadata);
ldev->lag_mpesw.pf_metadata[i] = 0;
}
+
+ kfree(ldev->lag_mpesw.pf_metadata);
+ ldev->lag_mpesw.pf_metadata = NULL;
}

static int mlx5_mpesw_metadata_set(struct mlx5_lag *ldev)
@@ -36,6 +42,12 @@ static int mlx5_mpesw_metadata_set(struct mlx5_lag *ldev)
u32 pf_metadata;
int i, err;

+ ldev->lag_mpesw.pf_metadata =
+ kcalloc(ldev->max_fns, sizeof(*ldev->lag_mpesw.pf_metadata),
+ GFP_KERNEL);
+ if (!ldev->lag_mpesw.pf_metadata)
+ return -ENOMEM;
+
mlx5_lag_for_each(i, 0, ldev, MLX5_LAG_FILTER_ALL) {
dev = mlx5_lag_fn(ldev, i)->dev;
esw = dev->priv.eswitch;
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.h b/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.h
index 5099723ba0f7..6296e3edd38c 100644
--- a/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.h
+++ b/drivers/net/ethernet/mellanox/mlx5/core/lag/mpesw.h
@@ -9,7 +9,7 @@

struct lag_mpesw {
struct work_struct mpesw_work;
- u32 pf_metadata[MLX5_MAX_PORTS];
+ u32 *pf_metadata;
};

enum mpesw_op {
--
2.44.0