From: Patrisious Haddad Date: Tue, 17 Jun 2025 08:19:16 +0000 (+0300) Subject: RDMA/mlx5: Add multiple priorities support to RDMA TRANSPORT userspace tables X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=40852c890119ebf39a741f50db13ae941f230d05;p=thirdparty%2Flinux.git RDMA/mlx5: Add multiple priorities support to RDMA TRANSPORT userspace tables Support the creation of RDMA TRANSPORT tables over multiple priorities via matcher creation. Signed-off-by: Patrisious Haddad Reviewed-by: Mark Bloch Link: https://patch.msgid.link/bb38e50ae4504e979c6568d41939402a4cf15635.1750148083.git.leon@kernel.org Signed-off-by: Leon Romanovsky --- diff --git a/drivers/infiniband/hw/mlx5/fs.c b/drivers/infiniband/hw/mlx5/fs.c index 680627f1de336..ebcc05f766e1c 100644 --- a/drivers/infiniband/hw/mlx5/fs.c +++ b/drivers/infiniband/hw/mlx5/fs.c @@ -1966,7 +1966,8 @@ _get_flow_table(struct mlx5_ib_dev *dev, u16 user_priority, break; case MLX5_FLOW_NAMESPACE_RDMA_TRANSPORT_RX: case MLX5_FLOW_NAMESPACE_RDMA_TRANSPORT_TX: - if (ib_port == 0 || user_priority > MLX5_RDMA_TRANSPORT_BYPASS_PRIO) + if (ib_port == 0 || + user_priority >= MLX5_RDMA_TRANSPORT_BYPASS_PRIO) return ERR_PTR(-EINVAL); ret = mlx5_ib_fill_transport_ns_info(dev, ns_type, &flags, &vport_idx, &vport, @@ -2016,10 +2017,10 @@ _get_flow_table(struct mlx5_ib_dev *dev, u16 user_priority, prio = &dev->flow_db->rdma_tx[priority]; break; case MLX5_FLOW_NAMESPACE_RDMA_TRANSPORT_RX: - prio = &dev->flow_db->rdma_transport_rx[ib_port - 1]; + prio = &dev->flow_db->rdma_transport_rx[priority][ib_port - 1]; break; case MLX5_FLOW_NAMESPACE_RDMA_TRANSPORT_TX: - prio = &dev->flow_db->rdma_transport_tx[ib_port - 1]; + prio = &dev->flow_db->rdma_transport_tx[priority][ib_port - 1]; break; default: return ERR_PTR(-EINVAL); } @@ -3466,31 +3467,40 @@ static const struct ib_device_ops flow_ops = { int mlx5_ib_fs_init(struct mlx5_ib_dev *dev) { + int i, j; + dev->flow_db = kzalloc(sizeof(*dev->flow_db), GFP_KERNEL); if (!dev->flow_db) return -ENOMEM; - dev->flow_db->rdma_transport_rx = kcalloc(dev->num_ports, - sizeof(struct mlx5_ib_flow_prio), - GFP_KERNEL); - if (!dev->flow_db->rdma_transport_rx) - goto free_flow_db; + for (i = 0; i < MLX5_RDMA_TRANSPORT_BYPASS_PRIO; i++) { + dev->flow_db->rdma_transport_rx[i] = + kcalloc(dev->num_ports, + sizeof(struct mlx5_ib_flow_prio), GFP_KERNEL); + if (!dev->flow_db->rdma_transport_rx[i]) + goto free_rdma_transport_rx; + } - dev->flow_db->rdma_transport_tx = kcalloc(dev->num_ports, - sizeof(struct mlx5_ib_flow_prio), - GFP_KERNEL); - if (!dev->flow_db->rdma_transport_tx) - goto free_rdma_transport_rx; + for (j = 0; j < MLX5_RDMA_TRANSPORT_BYPASS_PRIO; j++) { + dev->flow_db->rdma_transport_tx[j] = + kcalloc(dev->num_ports, + sizeof(struct mlx5_ib_flow_prio), GFP_KERNEL); + if (!dev->flow_db->rdma_transport_tx[j]) + goto free_rdma_transport_tx; + } mutex_init(&dev->flow_db->lock); ib_set_device_ops(&dev->ib_dev, &flow_ops); return 0; +free_rdma_transport_tx: + while (j--) + kfree(dev->flow_db->rdma_transport_tx[j]); free_rdma_transport_rx: - kfree(dev->flow_db->rdma_transport_rx); -free_flow_db: + while (i--) + kfree(dev->flow_db->rdma_transport_rx[i]); kfree(dev->flow_db); return -ENOMEM; } diff --git a/drivers/infiniband/hw/mlx5/fs.h b/drivers/infiniband/hw/mlx5/fs.h index 2ebe86e5be108..7abba0e2837cf 100644 --- a/drivers/infiniband/hw/mlx5/fs.h +++ b/drivers/infiniband/hw/mlx5/fs.h @@ -13,6 +13,8 @@ void mlx5_ib_fs_cleanup_anchor(struct mlx5_ib_dev *dev); static inline void mlx5_ib_fs_cleanup(struct mlx5_ib_dev *dev) { + int i; + /* When a steering anchor is created, a special flow table is also * created for the user to reference. Since the user can reference it, * the kernel cannot trust that when the user destroys the steering @@ -25,8 +27,10 @@ static inline void mlx5_ib_fs_cleanup(struct mlx5_ib_dev *dev) * is a safe assumption that all references are gone. */ mlx5_ib_fs_cleanup_anchor(dev); - kfree(dev->flow_db->rdma_transport_tx); - kfree(dev->flow_db->rdma_transport_rx); + for (i = 0; i < MLX5_RDMA_TRANSPORT_BYPASS_PRIO; i++) + kfree(dev->flow_db->rdma_transport_tx[i]); + for (i = 0; i < MLX5_RDMA_TRANSPORT_BYPASS_PRIO; i++) + kfree(dev->flow_db->rdma_transport_rx[i]); kfree(dev->flow_db); } #endif /* _MLX5_IB_FS_H */ diff --git a/drivers/infiniband/hw/mlx5/mlx5_ib.h b/drivers/infiniband/hw/mlx5/mlx5_ib.h index 802633ccf9d9d..a012e24d3afe9 100644 --- a/drivers/infiniband/hw/mlx5/mlx5_ib.h +++ b/drivers/infiniband/hw/mlx5/mlx5_ib.h @@ -320,8 +320,8 @@ struct mlx5_ib_flow_db { struct mlx5_ib_flow_prio rdma_tx[MLX5_IB_NUM_FLOW_FT]; struct mlx5_ib_flow_prio opfcs[MLX5_IB_OPCOUNTER_MAX]; struct mlx5_flow_table *lag_demux_ft; - struct mlx5_ib_flow_prio *rdma_transport_rx; - struct mlx5_ib_flow_prio *rdma_transport_tx; + struct mlx5_ib_flow_prio *rdma_transport_rx[MLX5_RDMA_TRANSPORT_BYPASS_PRIO]; + struct mlx5_ib_flow_prio *rdma_transport_tx[MLX5_RDMA_TRANSPORT_BYPASS_PRIO]; /* Protect flow steering bypass flow tables * when add/del flow rules. * only single add/removal of flow steering rule could be done