Support mlx5 flow steering with RAW data
Subsystems (5)
cover Support mlx5 flow steering with RAW data
From: Leon Romanovsky <[email protected]>
Changelog v0->v1:
* Fixed ADD_UVERBS_ATTRIBUTES_SIMPLE macro to pass the real address. �* Replaced UA_ALLOC_AND_COPY to regular copy_from
* Added UVERBS_ATTR_NO_DATA new macro for cleaner code.
* Used ib_dev from uobj when it exists.
* ib_is_destroy_retryable was replaced by ib_destroy_usecnt
-------------------------------------------------------------------------
Quoted 1 line
From Yishai:
This series introduces vendor create and destroy flow methods on the uverbs flow object by using the KABI infra-structure.
It's done in a way that enables the driver to get its specific device attributes in a raw data to match its underlay specification while still using the generic ib_flow object for cleanup and code sharing.
In addition, a specific mlx5 matcher object and its create/destroy methods were introduced. This object matches the underlay flow steering mask specification and is used as part of mlx5 create flow input data.
This series supports IB_QP/TIR as its flow steering destination as applicable today via the ib_create_flow API, however, it adds also an option to work with DEVX object which its destination can be both TIR and flow table.
Few changes were done in the mlx5 core layer to support forward compatible for the device specification raw data and to support flow table when the DEVX destination is used.
As part of this series the default IB destroy handler (i.e. uverbs_destroy_def_handler()) was exposed from IB core to be used by the drivers and existing code was refactored to use it.
Thanks
Yishai Hadas (8):
net/mlx5: Add forward compatible support for the FTE match data net/mlx5: Add support for flow table destination number IB/mlx5: Introduce flow steering matcher object
IB: Consider ib_flow creation by the KABI infrastructure IB/mlx5: Introduce vendor create and destroy flow methods IB/mlx5: Support adding flow steering rule by raw data IB/mlx5: Add support for a flow table destination IB/mlx5: Expose vendor flow trees
drivers/infiniband/core/uverbs_cmd.c | 4 + drivers/infiniband/core/uverbs_std_types.c | 5 +- .../infiniband/core/uverbs_std_types_flow_action.c | 3 +- drivers/infiniband/hw/mlx5/Makefile | 1 + drivers/infiniband/hw/mlx5/devx.c | 22 ++ drivers/infiniband/hw/mlx5/flow.c | 254 +++++++++++++++++++++ drivers/infiniband/hw/mlx5/main.c | 230 +++++++++++++++++-- drivers/infiniband/hw/mlx5/mlx5_ib.h | 31 +++ .../mellanox/mlx5/core/diag/fs_tracepoint.c | 3 + drivers/net/ethernet/mellanox/mlx5/core/fs_cmd.c | 23 +- drivers/net/ethernet/mellanox/mlx5/core/fs_core.c | 81 +------ include/linux/mlx5/fs.h | 1 + include/linux/mlx5/mlx5_ifc.h | 1 + include/rdma/ib_verbs.h | 15 ++ include/rdma/uverbs_ioctl.h | 2 + include/rdma/uverbs_named_ioctl.h | 29 ++- include/uapi/rdma/mlx5_user_ioctl_cmds.h | 50 +++- 17 files changed, 635 insertions(+), 120 deletions(-) create mode 100644 drivers/infiniband/hw/mlx5/flow.c
PATCH 1/8 net/mlx5: Add forward compatible support for the FTE match data
From: Yishai Hadas <[email protected]>
Use the PRM size including the reserved when working with the FTE match data.
This comes to support forward compatibility for cases that current reserved data will be exposed by the firmware and could be used by an application by DEVX without changing the kernel.
Also drop some driver checks around the match criteria leaving the work for firmware to enable forward compatibility for future bits there.
--- drivers/net/ethernet/mellanox/mlx5/core/fs_core.c | 77 +---------------------- 1 file changed, 1 insertion(+), 76 deletions(-)
drivers/net/ethernet/mellanox/mlx5/core/fs_core.c +1 -76
@@ -309,89 +309,17 @@ static struct fs_prio *find_prio(struct mlx5_flow_namespace *ns,return NULL ; } -static bool check_last_reserved (const u32 *match_criteria) -{ -char *match_criteria_reserved = -MLX5_ADDR_OF (fte_match_param, match_criteria,MLX5_FTE_MATCH_PARAM_RESERVED ); - -return !match_criteria_reserved[0 ] && - !memcmp (match_criteria_reserved, match_criteria_reserved +1 , -MLX5_FLD_SZ_BYTES (fte_match_param, -MLX5_FTE_MATCH_PARAM_RESERVED ) -1 ); -} - -static bool check_valid_mask (u8 match_criteria_enable,const u32 *match_criteria) -{ -if (match_criteria_enable & ~( - (1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_OUTER_HEADERS ) | - (1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_MISC_PARAMETERS ) | - (1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_INNER_HEADERS ) | - (1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_MISC_PARAMETERS_2 ))) -return false; - -if (!(match_criteria_enable & -1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_OUTER_HEADERS )) { -char *fg_type_mask =MLX5_ADDR_OF (fte_match_param, - match_criteria, outer_headers); - -if (fg_type_mask[0 ] || -memcmp (fg_type_mask, fg_type_mask +1 , -MLX5_ST_SZ_BYTES (fte_match_set_lyr_2_4) -1 )) -return false; - } - -if (!(match_criteria_enable & -1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_MISC_PARAMETERS )) { -char *fg_type_mask =MLX5_ADDR_OF (fte_match_param, - match_criteria, misc_parameters); - -if (fg_type_mask[0 ] || -memcmp (fg_type_mask, fg_type_mask +1 , -MLX5_ST_SZ_BYTES (fte_match_set_misc) -1 )) -return false; - } - -if (!(match_criteria_enable & -1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_INNER_HEADERS )) { -char *fg_type_mask =MLX5_ADDR_OF (fte_match_param, - match_criteria, inner_headers); - -if (fg_type_mask[0 ] || -memcmp (fg_type_mask, fg_type_mask +1 , -MLX5_ST_SZ_BYTES (fte_match_set_lyr_2_4) -1 )) -return false; - } - -if (!(match_criteria_enable & -1 <<MLX5_CREATE_FLOW_GROUP_IN_MATCH_CRITERIA_ENABLE_MISC_PARAMETERS_2 )) { -char *fg_type_mask =MLX5_ADDR_OF (fte_match_param, - match_criteria, misc_parameters_2); - -if (fg_type_mask[0 ] || -memcmp (fg_type_mask, fg_type_mask +1 , -MLX5_ST_SZ_BYTES (fte_match_set_misc2) -1 )) -return false; - } - -return check_last_reserved (match_criteria); -} -static bool check_valid_spec (const struct mlx5_flow_spec *spec) {int i; -if (!check_valid_mask (spec->match_criteria_enable, spec->match_criteria)) { -pr_warn ("mlx5_core: Match criteria given mismatches match_criteria_enable\n" ); -return false; - } -for (i =0 ; i <MLX5_ST_SZ_DW_MATCH_PARAM ; i++)if (spec->match_value[i] & ~spec->match_criteria[i]) {pr_warn ("mlx5_core: match_value differs from match_criteria\n" );return false; } -return check_last_reserved (spec->match_value); +return true; }static struct mlx5_flow_root_namespace *find_root (struct fs_node *node)
@@ -1158,9 +1086,6 @@ struct mlx5_flow_group *mlx5_create_flow_group(struct mlx5_flow_table *ft,struct mlx5_flow_group *fg;int err; -if (!check_valid_mask (match_criteria_enable, match_criteria)) -return ERR_PTR (-EINVAL ); -if (ft->autogroup.active)return ERR_PTR (-EPERM );
Signature · 1 line
2.14.4
Re: [PATCH mlx5-next v1 1/8] net/mlx5: Add forward compatible support for the FTE match data
Quoted 4 lines · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Use the PRM size including the reserved when working with the FTE match data.
is this actually a bug fix?
Quoted 3 lines
This comes to support forward compatibility for cases that current reserved data will be exposed by the firmware and could be used by an application by DEVX without changing the kernel.
something went wrong in the phrasing/wording of "used by an application by DEVX" I can't follow on that part of the sentence, please try to improve/fix it.
Quoted 2 lines
Also drop some driver checks around the match criteria leaving the work for firmware to enable forward compatibility for future bits there.
not following,
OTOH we can always patch the kernel to add new bits for checking, why remove these checks?
OTOH, suppose today we check that one of four bits is set and now one added bit #5 and the
kernel doesn't check it, what removing the existing four checks buys you?
Re: [PATCH mlx5-next v1 1/8] net/mlx5: Add forward compatible support for the FTE match data
Quoted 7 lines · Or Gerlitz
Quoted 4 lines · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Use the PRM size including the reserved when working with the FTE match data.
is this actually a bug fix?
No, it's some requirement from the new API to enable forward compatible support without changing the kernel code.
Quoted 5 lines
Quoted 2 lines
Also drop some driver checks around the match criteria leaving the work for firmware to enable forward compatibility for future bits there.
not following,
Same as for the 'reserved' field but also for extending the 'match criteria' field with new bits without changing the kernel.
Quoted 3 lines
OTOH, suppose today we check that one of four bits is set and now one added bit #5 and the
kernel doesn't check it, what removing the existing four checks buys you?
The idea was to have one place for those checking (i.e. firmware) instead of splitting between legacy to new bits. (i.e. driver vs firmware).
Re: [PATCH mlx5-next v1 1/8] net/mlx5: Add forward compatible support for the FTE match data
Quoted 11 lines · Yishai Hadas
Quoted 7 lines · Or Gerlitz
Quoted 4 lines · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Use the PRM size including the reserved when working with the FTE match data.
is this actually a bug fix?
No, it's some requirement from the new API to enable forward compatible support without changing the kernel code.
ok, but
Quoted 7 lines
Quoted 4 lines
Quoted 2 lines
Also drop some driver checks around the match criteria leaving the work for firmware to enable forward compatibility for future bits there.
not following,
Same as for the 'reserved' field but also for extending the 'match criteria' field with new bits without changing the kernel.
-- we need a clear memo as part of your change-logs and/or cover-letter/s that explains the overall approach/design for doing-things-without-changing-the-kernel,
does this exist? the arch/approach need not be deciphered from the code or change logs
snapshots but rather stated clearly.
Re: [PATCH mlx5-next v1 1/8] net/mlx5: Add forward compatible support for the FTE match data
Quoted 6 lines · Or Gerlitz
Quoted 3 lines · Yishai Hadas
Quoted 2 lines · Or Gerlitz
Quoted 1 line · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Quoted 8 lines
Quoted 2 lines
Quoted 2 lines
Quoted 2 lines
Use the PRM size including the reserved when working with the FTE match data.
-- we need a clear memo as part of your change-logs and/or cover-letter/s that explains the overall approach/design for doing-things-without-changing-the-kernel,
does this exist?
Yes, the DEVX series that was previously accepted clearly stated that this is its target as part of its cover-letter [1]. This motivation appears also as part of this specific commit log.
From the cover letter:
"The main purpose here is to make the user space driver as independent as possible from the kernel so that future device functionality and commands can be activated with minimal to none kernel changes.
PATCH 2/8 net/mlx5: Add support for flow table destination number
In reply to Leon RomanovskyFrom: Yishai Hadas <[email protected]>
Add support to set a destination from a flow table number. This functionality will be used in downstream patches from this series by the DEVX stuff.
--- .../mellanox/mlx5/core/diag/fs_tracepoint.c | 3 +++ drivers/net/ethernet/mellanox/mlx5/core/fs_cmd.c | 23 +++++++++++++--------- drivers/net/ethernet/mellanox/mlx5/core/fs_core.c | 4 +++- include/linux/mlx5/fs.h | 1 + include/linux/mlx5/mlx5_ifc.h | 1 + 5 files changed, 22 insertions(+), 10 deletions(-)
drivers/net/ethernet/mellanox/mlx5/core/diag/fs_tracepoint.c +3 -0
@@ -240,6 +240,9 @@ const char *parse_fs_dst(struct trace_seq *p,case MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE :trace_seq_printf (p,"ft=%p\n" , dst->ft);break ; +case MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE_NUM : +trace_seq_printf (p,"ft_num=%u\n" , dst->ft_num); +break ;case MLX5_FLOW_DESTINATION_TYPE_TIR :trace_seq_printf (p,"tir=%u\n" , dst->tir_num);break ;
drivers/net/ethernet/mellanox/mlx5/core/fs_cmd.c +14 -9
@@ -362,18 +362,20 @@ static int mlx5_cmd_set_fte(struct mlx5_core_dev *dev,int list_size =0 ;list_for_each_entry (dst, &fte->node.children, node.list) { -unsigned int id; +unsigned int id, type = dst->dest_attr.type; -if (dst->dest_attr.type ==MLX5_FLOW_DESTINATION_TYPE_COUNTER ) +if (type ==MLX5_FLOW_DESTINATION_TYPE_COUNTER )continue ; -MLX5_SET (dest_format_struct, in_dests, destination_type, - dst->dest_attr.type); -if (dst->dest_attr.type == -MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE ) { +switch (type) { +case MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE_NUM : + id = dst->dest_attr.ft_num; + type =MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE ; +break ; +case MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE : id = dst->dest_attr.ft->id; - }else if (dst->dest_attr.type == -MLX5_FLOW_DESTINATION_TYPE_VPORT ) { +break ; +case MLX5_FLOW_DESTINATION_TYPE_VPORT : id = dst->dest_attr.vport.num; MLX5_SET(dest_format_struct, in_dests, destination_eswitch_owner_vhca_id_valid,
@@ -381,9 +383,12 @@ static int mlx5_cmd_set_fte(struct mlx5_core_dev *dev,MLX5_SET (dest_format_struct, in_dests, destination_eswitch_owner_vhca_id, dst->dest_attr.vport.vhca_id); - }else { +break ; +default : id = dst->dest_attr.tir_num; } + +MLX5_SET (dest_format_struct, in_dests, destination_type, type);MLX5_SET (dest_format_struct, in_dests, destination_id, id); in_dests +=MLX5_ST_SZ_BYTES (dest_format_struct); list_size++;
drivers/net/ethernet/mellanox/mlx5/core/fs_core.c +3 -1
@@ -1356,7 +1356,9 @@ static bool mlx5_flow_dests_cmp(struct mlx5_flow_destination *d1, (d1->type ==MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE && d1->ft == d2->ft) || (d1->type ==MLX5_FLOW_DESTINATION_TYPE_TIR && - d1->tir_num == d2->tir_num)) + d1->tir_num == d2->tir_num) || + (d1->type ==MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE_NUM && + d1->ft_num == d2->ft_num)) return true; }
include/linux/mlx5/fs.h +1 -0
@@ -89,6 +89,7 @@ struct mlx5_flow_destination {enum mlx5_flow_destination_type type;union {u32 tir_num; +u32 ft_num;struct mlx5_flow_table *ft;struct mlx5_fc *counter;struct {
include/linux/mlx5/mlx5_ifc.h +1 -0
@@ -1181,6 +1181,7 @@ enum mlx5_flow_destination_type {MLX5_FLOW_DESTINATION_TYPE_PORT =0x99 ,MLX5_FLOW_DESTINATION_TYPE_COUNTER =0x100 , + MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE_NUM = 0x101, }; struct mlx5_ifc_dest_format_struct_bits {
Signature · 1 line
2.14.4
Re: [PATCH mlx5-next v1 2/8] net/mlx5: Add support for flow table destination number
Quoted 5 lines · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Add support to set a destination from a flow table number. This functionality will be used in downstream patches from this series by the DEVX stuff.
Reading your cover letter, I still don't understand what is missing in the current mlx5
fs core API for your needs. After all, you do create flow tables from the IB driver through
fs core calls, right? so @ the end of the day, you have the FT pointer to provide the core,
why you need the FT number?
Re: [PATCH mlx5-next v1 2/8] net/mlx5: Add support for flow table destination number
Quoted 7 lines · Or Gerlitz
Quoted 5 lines · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Add support to set a destination from a flow table number. This functionality will be used in downstream patches from this series by the DEVX stuff.
Quoted 5 lines
Reading your cover letter, I still don't understand what is missing in the current mlx5 fs core API for your needs. After all, you do create flow tables from the IB driver through fs core calls, right? so @ the end of the day, you have the FT pointer to provide the core, why you need the FT number?
Via the devx API userspace can create flow tables directly without going to the driver's flow steering core.
Jason
Re: [PATCH mlx5-next v1 2/8] net/mlx5: Add support for flow table destination number
Quoted 8 lines · Jason Gunthorpe
Quoted 7 lines · Or Gerlitz
Quoted 5 lines · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Add support to set a destination from a flow table number. This functionality will be used in downstream patches from this series by the DEVX stuff.
Quoted 8 lines
Quoted 5 lines
Reading your cover letter, I still don't understand what is missing in the current mlx5 fs core API for your needs. After all, you do create flow tables from the IB driver through fs core calls, right? so @ the end of the day, you have the FT pointer to provide the core, why you need the FT number?
Via the devx API userspace can create flow tables directly without going to the driver's flow steering core.
so why you change the core?
Re: [PATCH mlx5-next v1 2/8] net/mlx5: Add support for flow table destination number
Quoted 15 lines · Or Gerlitz
Quoted 14 lines · Jason Gunthorpe
Quoted 12 lines · Or Gerlitz
Quoted 5 lines · Leon Romanovsky
From: Yishai Hadas <[email protected]>
Add support to set a destination from a flow table number. This functionality will be used in downstream patches from this series by the DEVX stuff.
Reading your cover letter, I still don't understand what is missing in the current mlx5 fs core API for your needs. After all, you do create flow tables from the IB driver through fs core calls, right? so @ the end of the day, you have the FT pointer to provide the core, why you need the FT number?
Quoted 4 lines
Quoted 2 lines
Via the devx API userspace can create flow tables directly without going to the driver's flow steering core.
so why you change the core?
User space flow tables don't get any traffic until they are linked into the main steering. The only ID the kernel gets for them when adding this link is the actual PRM handle, not a pointer - hence the change.
Jason
PATCH 3/8 IB/mlx5: Introduce flow steering matcher object
In reply to Leon RomanovskyFrom: Yishai Hadas <[email protected]>
Introduce flow steering matcher object and its create and destroy methods.
This matcher object holds some mlx5 specific driver properties that matches the underlay device specification when an mlx5 flow steering group is created.
It will be used in downstream patches to be part of mlx5 specific create flow method.
--- .../infiniband/core/uverbs_std_types_flow_action.c | 3 +- drivers/infiniband/hw/mlx5/Makefile | 1 + drivers/infiniband/hw/mlx5/flow.c | 137 +++++++++++++++++++++ drivers/infiniband/hw/mlx5/mlx5_ib.h | 11 ++ include/rdma/uverbs_ioctl.h | 2 + include/uapi/rdma/mlx5_user_ioctl_cmds.h | 33 ++++- 6 files changed, 184 insertions(+), 3 deletions(-) create mode 100644 drivers/infiniband/hw/mlx5/flow.c
drivers/infiniband/core/uverbs_std_types_flow_action.c +1 -2
@@ -376,8 +376,7 @@ static const struct uverbs_attr_spec uverbs_flow_action_esp_keymat[] = {static const struct uverbs_attr_spec uverbs_flow_action_esp_replay[] = { [IB_UVERBS_FLOW_ACTION_ESP_REPLAY_NONE ] = { .type =UVERBS_ATTR_TYPE_PTR_IN , -/* No need to specify any data */ -UVERBS_ATTR_SIZE (0 ,0 ), +UVERBS_ATTR_NO_DATA (), }, [IB_UVERBS_FLOW_ACTION_ESP_REPLAY_BMP ] = { .type =UVERBS_ATTR_TYPE_PTR_IN ,
drivers/infiniband/hw/mlx5/Makefile +1 -0
@@ -4,3 +4,4 @@ mlx5_ib-y := main.o cq.o doorbell.o qp.o mem.o srq.o mr.o ah.o mad.o gsi.o ib_vi mlx5_ib-$(CONFIG_INFINIBAND_ON_DEMAND_PAGING) += odp.o mlx5_ib-$(CONFIG_MLX5_ESWITCH) += ib_rep.o mlx5_ib-$(CONFIG_INFINIBAND_USER_ACCESS) += devx.o +mlx5_ib-$(CONFIG_INFINIBAND_USER_ACCESS) += flow.o
drivers/infiniband/hw/mlx5/flow.c new file +137 -0
137 lines not on this page · raw message
drivers/infiniband/hw/mlx5/mlx5_ib.h +11 -0
@@ -46,6 +46,7 @@#include <rdma/ib_user_verbs.h> #include <rdma/mlx5-abi.h> #include <rdma/uverbs_ioctl.h> +#include <rdma/mlx5_user_ioctl_cmds.h> #define mlx5_ib_dbg(dev, format, arg...) \ pr_debug("%s:%s:%d:(pid %d): " format, (dev)->ib_dev.name, __func__, \
@@ -179,6 +180,16 @@ struct mlx5_ib_flow_handler {struct ib_counters *ibcounters; }; +struct mlx5_ib_flow_matcher { +struct mlx5_ib_match_params matcher_mask; +int mask_len; +enum mlx5_ib_flow_type flow_type; +u16 priority; +struct mlx5_core_dev *mdev; +atomic_t usecnt; +u8 match_criteria_enable; +}; +struct mlx5_ib_flow_db {struct mlx5_ib_flow_prio prios[MLX5_IB_NUM_FLOW_FT ];struct mlx5_ib_flow_prio sniffer[MLX5_IB_NUM_SNIFFER_FTS ];
include/rdma/uverbs_ioctl.h +2 -0
@@ -204,6 +204,8 @@ struct uverbs_object_tree_def {#define UVERBS_ATTR_SIZE (_min_len, _len) \ .u.ptr.min_len = _min_len, .u.ptr.len = _len +#define UVERBS_ATTR_NO_DATA () UVERBS_ATTR_SIZE(0, 0) +/* * Specifies a uapi structure that cannot be extended. The user must always * supply the whole structure and nothing more. The structure must be declared
include/uapi/rdma/mlx5_user_ioctl_cmds.h +32 -1
@@ -33,6 +33,7 @@#ifndef MLX5_USER_IOCTL_CMDS_H #define MLX5_USER_IOCTL_CMDS_H +#include <linux/types.h> #include <rdma/ib_user_ioctl_cmds.h> enum mlx5_ib_create_flow_action_attrs {
@@ -112,10 +113,40 @@ enum mlx5_ib_devx_umem_methods { MLX5_IB_METHOD_DEVX_UMEM_DEREG, }; -enum mlx5_ib_devx_objects { +enum mlx5_ib_objects {MLX5_IB_OBJECT_DEVX = (1U <<UVERBS_ID_NS_SHIFT ),MLX5_IB_OBJECT_DEVX_OBJ ,MLX5_IB_OBJECT_DEVX_UMEM , +MLX5_IB_OBJECT_FLOW_MATCHER , +}; + +enum mlx5_ib_flow_matcher_create_attrs { +MLX5_IB_ATTR_FLOW_MATCHER_CREATE_HANDLE = (1U <<UVERBS_ID_NS_SHIFT ), +MLX5_IB_ATTR_FLOW_MATCHER_MATCH_MASK , +MLX5_IB_ATTR_FLOW_MATCHER_FLOW_TYPE , +MLX5_IB_ATTR_FLOW_MATCHER_MATCH_CRITERIA , +}; + +enum mlx5_ib_flow_matcher_destroy_attrs { +MLX5_IB_ATTR_FLOW_MATCHER_DESTROY_HANDLE = (1U <<UVERBS_ID_NS_SHIFT ), +}; + +enum mlx5_ib_flow_matcher_methods { +MLX5_IB_METHOD_FLOW_MATCHER_CREATE = (1U <<UVERBS_ID_NS_SHIFT ), +MLX5_IB_METHOD_FLOW_MATCHER_DESTROY , +}; + +#define MLX5_IB_DW_MATCH_PARAM 0x80 + +struct mlx5_ib_match_params { +__u32 match_params[MLX5_IB_DW_MATCH_PARAM ]; +}; + +enum mlx5_ib_flow_type { +MLX5_IB_FLOW_TYPE_NORMAL , +MLX5_IB_FLOW_TYPE_SNIFFER , +MLX5_IB_FLOW_TYPE_ALL_DEFAULT , +MLX5_IB_FLOW_TYPE_MC_DEFAULT , };#endif
Signature · 1 line
2.14.4
PATCH 4/8 IB: Consider ib_flow creation by the KABI infrastructure
In reply to Leon RomanovskyFrom: Yishai Hadas <[email protected]>
This patch considers the case that ib_flow is created by some device driver with its specific parameters using the KABI infrastructure.
In that case both QP and ib_uflow_resources might not be applicable. Downstream patches from this series use the above functionality.
--- drivers/infiniband/core/uverbs_cmd.c | 4 ++++ drivers/infiniband/core/uverbs_std_types.c | 5 +++-- include/rdma/ib_verbs.h | 1 + 3 files changed, 8 insertions(+), 2 deletions(-)
drivers/infiniband/core/uverbs_cmd.c +4 -0
@@ -2771,6 +2771,9 @@ void ib_uverbs_flow_resources_free(struct ib_uflow_resources *uflow_res) {unsigned int i; +if (!uflow_res) +return ; +for (i =0 ; i < uflow_res->collection_num; i++)atomic_dec (&uflow_res->collection[i]->usecnt);
@@ -3590,6 +3593,7 @@ int ib_uverbs_ex_create_flow(struct ib_uverbs_file *file, }atomic_inc (&qp->usecnt); flow_id->qp = qp; + flow_id->device = qp->device; flow_id->uobject = uobj; uobj->object = flow_id; uflow =container_of (uobj,typeof (*uflow), uobject);
drivers/infiniband/core/uverbs_std_types.c +3 -2
@@ -54,9 +54,10 @@ static int uverbs_free_flow(struct ib_uobject *uobject,struct ib_qp *qp = flow->qp;int ret; - ret = qp->device->destroy_flow (flow); + ret = flow->device->destroy_flow (flow);if (!ret) { -atomic_dec (&qp->usecnt); +if (qp) +atomic_dec (&qp->usecnt);ib_uverbs_flow_resources_free (uflow->resources); }
include/rdma/ib_verbs.h +1 -0
@@ -2079,6 +2079,7 @@ struct ib_flow_attr {struct ib_flow {struct ib_qp *qp; +struct ib_device *device;struct ib_uobject *uobject; };
Signature · 1 line
2.14.4
PATCH 5/8 IB/mlx5: Introduce vendor create and destroy flow methods
In reply to Leon RomanovskyFrom: Yishai Hadas <[email protected]>
Introduce vendor create and destroy flow methods on the uverbs flow object.
This enables the driver to get its specific device attributes to match the underlay specification while still using the generic ib_flow object for cleanup and code sharing.
The IB object's attributes are set via ib_set_flow() helper function.
The specific implementation for the given specification is added in downstream patches.
--- drivers/infiniband/hw/mlx5/devx.c | 22 +++++++ drivers/infiniband/hw/mlx5/flow.c | 108 +++++++++++++++++++++++++++++++ drivers/infiniband/hw/mlx5/main.c | 9 +++ drivers/infiniband/hw/mlx5/mlx5_ib.h | 15 +++++ include/rdma/ib_verbs.h | 14 ++++ include/rdma/uverbs_named_ioctl.h | 29 +++++---- include/uapi/rdma/mlx5_user_ioctl_cmds.h | 17 +++++ 7 files changed, 202 insertions(+), 12 deletions(-)
drivers/infiniband/hw/mlx5/devx.c +22 -0
@@ -89,6 +89,28 @@ void mlx5_ib_devx_destroy(struct mlx5_ib_dev *dev,mlx5_cmd_exec (dev->mdev, in,sizeof (in), out,sizeof (out)); } +bool mlx5_ib_devx_is_flow_dest (void *obj,int *dest_id,int *dest_type) +{ +struct devx_obj *devx_obj = obj; +u16 opcode =MLX5_GET (general_obj_in_cmd_hdr, devx_obj->dinbox, opcode); + +switch (opcode) { +case MLX5_CMD_OP_DESTROY_TIR : + *dest_type =MLX5_FLOW_DESTINATION_TYPE_TIR ; + *dest_id =MLX5_GET (general_obj_in_cmd_hdr, devx_obj->dinbox, + obj_id); +return true; + +case MLX5_CMD_OP_DESTROY_FLOW_TABLE : + *dest_type =MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE ; + *dest_id =MLX5_GET (destroy_flow_table_in, devx_obj->dinbox, + table_id); +return true; +default : +return false; + } +} +static int devx_is_valid_obj_id (struct devx_obj *obj,const void *in) {u16 opcode =MLX5_GET (general_obj_in_cmd_hdr, in, opcode);
drivers/infiniband/hw/mlx5/flow.c +108 -0
120 lines not on this page · raw message
drivers/infiniband/hw/mlx5/main.c +9 -0
@@ -3643,6 +3643,15 @@ static struct ib_flow *mlx5_ib_create_flow(struct ib_qp *qp,return ERR_PTR (err); } +struct mlx5_ib_flow_handler * +mlx5_ib_raw_fs_rule_add (struct mlx5_ib_dev *dev, +struct mlx5_ib_flow_matcher *fs_matcher, +void *cmd_in,int inlen,int dest_id, +int dest_type) +{ +return ERR_PTR (-EOPNOTSUPP ); +} +static u32 mlx5_ib_flow_action_flags_to_accel_xfrm_flags (u32 mlx5_flags) {u32 flags =0 ;
drivers/infiniband/hw/mlx5/mlx5_ib.h +15 -0
@@ -1236,6 +1236,12 @@ int mlx5_ib_devx_create(struct mlx5_ib_dev *dev,void mlx5_ib_devx_destroy (struct mlx5_ib_dev *dev,struct mlx5_ib_ucontext *context);const struct uverbs_object_tree_def *mlx5_ib_get_devx_tree (void ); +struct mlx5_ib_flow_handler *mlx5_ib_raw_fs_rule_add (struct mlx5_ib_dev *dev, +struct mlx5_ib_flow_matcher *fs_matcher, +void *cmd_in, +int inlen,int dest_id, +int dest_type); +bool mlx5_ib_devx_is_flow_dest (void *obj,int *dest_id,int *dest_type);#else static inline int mlx5_ib_devx_create(struct mlx5_ib_dev *dev,
@@ -1244,6 +1250,15 @@ static inline void mlx5_ib_devx_destroy(struct mlx5_ib_dev *dev, struct mlx5_ib_ucontext *context) {}static inline const struct uverbs_object_tree_def *mlx5_ib_get_devx_tree (void ) {return NULL ; } +static inline struct mlx5_ib_flow_handler * +mlx5_ib_raw_fs_rule_add (struct mlx5_ib_dev *dev, +struct mlx5_ib_flow_matcher *fs_matcher, +void *cmd_in, +int inlen,int dest_id, +int dest_type) {return -EOPNOTSUPP ; }; +static inline bool +mlx5_ib_devx_is_flow_dest (void *obj,int *dest_id, +int *dest_type) {return false; };#endif static inline void init_query_mad (struct ib_smp *mad) {
include/rdma/ib_verbs.h +14 -0
@@ -4137,6 +4137,20 @@ ib_get_vector_affinity(struct ib_device *device, int comp_vector) } +static inline void ib_set_flow (struct ib_uobject *uobj,struct ib_flow *ibflow, +struct ib_qp *qp,struct ib_device *device) +{ + uobj->object = ibflow; + ibflow->uobject = uobj; + +if (qp) { +atomic_inc (&qp->usecnt); + ibflow->qp = qp; + } + + ibflow->device = device; +} +/** * rdma_roce_rescan_device - Rescan all of the network devices in the system * and add their gids, as needed, to the relevant RoCE devices.
include/rdma/uverbs_named_ioctl.h +17 -12
@@ -97,22 +97,14 @@ .methods = &UVERBS_OBJECT_METHODS(_object_id) \ } -/* Used by drivers to declare a complete parsing tree for a single method that -* differs only in having additional driver specific attributes. +/* Used by drivers to declare a complete parsing tree for new methods */ -#define ADD_UVERBS_ATTRIBUTES_SIMPLE (_name, _object_id, _method_id, ...) \ - static const struct uverbs_attr_def *const UVERBS_METHOD_ATTRS( \ - _method_id)[] = { __VA_ARGS__ }; \ - static const struct uverbs_method_def UVERBS_METHOD(_method_id) = { \ - .id = _method_id, \ - .num_attrs = ARRAY_SIZE(UVERBS_METHOD_ATTRS(_method_id)), \ - .attrs = &UVERBS_METHOD_ATTRS(_method_id), \ - }; \ +#define ADD_UVERBS_METHODS (_name, _object_id, ...) \ static const struct uverbs_method_def *const UVERBS_OBJECT_METHODS( \ - _object_id)[] = { &UVERBS_METHOD(_method_id) }; \ + _object_id)[] = { __VA_ARGS__ }; \ static const struct uverbs_object_def _name##_struct = { \ .id = _object_id, \ - .num_methods = 1, \ + .num_methods = ARRAY_SIZE(UVERBS_OBJECT_METHODS(_object_id)), \ .methods = &UVERBS_OBJECT_METHODS(_object_id) \ }; \ static const struct uverbs_object_def *const _name##_ptrs[] = { \
@@ -123,4 +115,17 @@ .objects = &_name##_ptrs, \ } +/* Used by drivers to declare a complete parsing tree for a single method that +* differs only in having additional driver specific attributes. +*/ +#define ADD_UVERBS_ATTRIBUTES_SIMPLE (_name, _object_id, _method_id, ...) \ + static const struct uverbs_attr_def *const UVERBS_METHOD_ATTRS( \ + _method_id)[] = { __VA_ARGS__ }; \ + static const struct uverbs_method_def UVERBS_METHOD(_method_id) = { \ + .id = _method_id, \ + .num_attrs = ARRAY_SIZE(UVERBS_METHOD_ATTRS(_method_id)), \ + .attrs = &UVERBS_METHOD_ATTRS(_method_id), \ + }; \ + ADD_UVERBS_METHODS(_name, _object_id, &UVERBS_METHOD(_method_id)) +#endif
include/uapi/rdma/mlx5_user_ioctl_cmds.h +17 -0
@@ -149,4 +149,21 @@ enum mlx5_ib_flow_type { MLX5_IB_FLOW_TYPE_MC_DEFAULT, }; +enum mlx5_ib_create_flow_attrs { +MLX5_IB_ATTR_CREATE_FLOW_HANDLE = (1U <<UVERBS_ID_NS_SHIFT ), +MLX5_IB_ATTR_CREATE_FLOW_MATCH_VALUE , +MLX5_IB_ATTR_CREATE_FLOW_DEST_QP , +MLX5_IB_ATTR_CREATE_FLOW_DEST_DEVX , +MLX5_IB_ATTR_CREATE_FLOW_MATCHER , +}; + +enum mlx5_ib_destoy_flow_attrs { +MLX5_IB_ATTR_DESTROY_FLOW_HANDLE = (1U <<UVERBS_ID_NS_SHIFT ), +}; + +enum mlx5_ib_flow_methods { +MLX5_IB_METHOD_CREATE_FLOW = (1U <<UVERBS_ID_NS_SHIFT ), +MLX5_IB_METHOD_DESTROY_FLOW , +}; +#endif
Signature · 1 line
2.14.4
PATCH 6/8 IB/mlx5: Support adding flow steering rule by raw data
In reply to Leon RomanovskyFrom: Yishai Hadas <[email protected]>
Add support to set a public flow steering rule which its destination is a TIR by using raw specification data.
The logic follows the verbs API but instead of using ib_spec(s) the raw input data is used.
--- drivers/infiniband/hw/mlx5/main.c | 216 ++++++++++++++++++++++++++++++++--- drivers/infiniband/hw/mlx5/mlx5_ib.h | 2 + 2 files changed, 201 insertions(+), 17 deletions(-)
drivers/infiniband/hw/mlx5/main.c +199 -17
@@ -2980,11 +2980,11 @@ static void counters_clear_description(struct ib_counters *counters)static int mlx5_ib_destroy_flow (struct ib_flow *flow_id) { -struct mlx5_ib_dev *dev =to_mdev (flow_id->qp->device);struct mlx5_ib_flow_handler *handler =container_of (flow_id, struct mlx5_ib_flow_handler, ibflow);struct mlx5_ib_flow_handler *iter, *tmp; +struct mlx5_ib_dev *dev = handler->dev;mutex_lock (&dev->flow_db->lock);
@@ -3002,6 +3002,8 @@ static int mlx5_ib_destroy_flow(struct ib_flow *flow_id)counters_clear_description (handler->ibcounters);mutex_unlock (&dev->flow_db->lock); +if (handler->flow_matcher) +atomic_dec (&handler->flow_matcher->usecnt);kfree (handler);return 0 ;
@@ -3022,6 +3024,26 @@ enum flow_table_type {#define MLX5_FS_MAX_TYPES 6#define MLX5_FS_MAX_ENTRIES BIT(16) + +static struct mlx5_ib_flow_prio *_get_prio (struct mlx5_flow_namespace *ns, +struct mlx5_ib_flow_prio *prio, +int priority, +int num_entries,int num_groups) +{ +struct mlx5_flow_table *ft; + + ft =mlx5_create_auto_grouped_flow_table (ns, priority, + num_entries, + num_groups, +0 ,0 ); +if (IS_ERR (ft)) +return ERR_CAST (ft); + + prio->flow_table = ft; + prio->refcount =0 ; +return prio; +} +static struct mlx5_ib_flow_prio *get_flow_table (struct mlx5_ib_dev *dev,struct ib_flow_attr *flow_attr,enum flow_table_type ft_type)
@@ -3034,7 +3056,6 @@ static struct mlx5_ib_flow_prio *get_flow_table(struct mlx5_ib_dev *dev,int num_entries;int num_groups;int priority; -int err =0 ; max_table_size =BIT (MLX5_CAP_FLOWTABLE_NIC_RX (dev->mdev, log_max_ft_size));
@@ -3084,21 +3105,10 @@ static struct mlx5_ib_flow_prio *get_flow_table(struct mlx5_ib_dev *dev,return ERR_PTR (-ENOMEM ); ft = prio->flow_table; -if (!ft) { - ft =mlx5_create_auto_grouped_flow_table (ns, priority, - num_entries, - num_groups, -0 ,0 ); - -if (!IS_ERR (ft)) { - prio->refcount =0 ; - prio->flow_table = ft; - }else { - err =PTR_ERR (ft); - } - } +if (!ft) +return _get_prio (ns, prio, priority, num_entries, num_groups); -return err ?ERR_PTR (err) : prio; +return prio; } static void set_underlay_qp(struct mlx5_ib_dev *dev,
@@ -3357,6 +3367,7 @@ static struct mlx5_ib_flow_handler *_create_flow_rule(struct mlx5_ib_dev *dev, ft_prio->refcount++; handler->prio = ft_prio; + handler->dev = dev; ft_prio->flow_table = ft; free:
@@ -3643,13 +3654,184 @@ static struct ib_flow *mlx5_ib_create_flow(struct ib_qp *qp,return ERR_PTR (err); } +static struct mlx5_ib_flow_prio *_get_flow_table (struct mlx5_ib_dev *dev, +int priority,bool mcast) +{ +int max_table_size; +struct mlx5_flow_namespace *ns =NULL ; +struct mlx5_ib_flow_prio *prio; + + max_table_size =BIT (MLX5_CAP_FLOWTABLE_NIC_RX (dev->mdev, + log_max_ft_size)); +if (max_table_size <MLX5_FS_MAX_ENTRIES ) +return ERR_PTR (-ENOMEM ); + +if (mcast) + priority =MLX5_IB_FLOW_MCAST_PRIO ; +else + priority =ib_prio_to_core_prio (priority, false); + + ns =mlx5_get_flow_namespace (dev->mdev,MLX5_FLOW_NAMESPACE_BYPASS ); +if (!ns) +return ERR_PTR (-ENOTSUPP ); + + prio = &dev->flow_db->prios[priority]; + +if (prio->flow_table) +return prio; + +return _get_prio (ns, prio, priority,MLX5_FS_MAX_ENTRIES , +MLX5_FS_MAX_TYPES ); +} + +static struct mlx5_ib_flow_handler * +_create_raw_flow_rule (struct mlx5_ib_dev *dev, +struct mlx5_ib_flow_prio *ft_prio, +struct mlx5_flow_destination *dst, +struct mlx5_ib_flow_matcher *fs_matcher, +void *cmd_in,int inlen) +{ +struct mlx5_ib_flow_handler *handler; +struct mlx5_flow_act flow_act = {.flow_tag =MLX5_FS_DEFAULT_FLOW_TAG }; +struct mlx5_flow_spec *spec; +struct mlx5_flow_table *ft = ft_prio->flow_table; +int err =0 ; + + spec =kvzalloc (sizeof (*spec),GFP_KERNEL ); + handler =kzalloc (sizeof (*handler),GFP_KERNEL ); +if (!handler || !spec) { + err = -ENOMEM ; + goto free; + } + +INIT_LIST_HEAD (&handler->list); + +memcpy (spec->match_value, cmd_in, inlen); +memcpy (spec->match_criteria, fs_matcher->matcher_mask.match_params, + fs_matcher->mask_len); + spec->match_criteria_enable = fs_matcher->match_criteria_enable; + + flow_act.action |=MLX5_FLOW_CONTEXT_ACTION_FWD_DEST ; + handler->rule =mlx5_add_flow_rules (ft, spec, + &flow_act, dst,1 ); + +if (IS_ERR (handler->rule)) { + err =PTR_ERR (handler->rule); + goto free; + } + + ft_prio->refcount++; + handler->prio = ft_prio; + handler->dev = dev; + ft_prio->flow_table = ft; + +free: +if (err) +kfree (handler); +kvfree (spec); +return err ?ERR_PTR (err) : handler; +} + +static bool raw_fs_is_multicast (struct mlx5_ib_flow_matcher *fs_matcher, +void *match_v) +{ +void *match_c; +void *match_v_set_lyr_2_4, *match_c_set_lyr_2_4; +void *dmac, *dmac_mask; +void *ipv4, *ipv4_mask; + +if (!(fs_matcher->match_criteria_enable & + (1 <<MATCH_CRITERIA_ENABLE_OUTER_BIT ))) +return false; + + match_c = fs_matcher->matcher_mask.match_params; + match_v_set_lyr_2_4 =MLX5_ADDR_OF (fte_match_param, match_v, + outer_headers); + match_c_set_lyr_2_4 =MLX5_ADDR_OF (fte_match_param, match_c, + outer_headers); + + dmac =MLX5_ADDR_OF (fte_match_set_lyr_2_4, match_v_set_lyr_2_4, + dmac_47_16); + dmac_mask =MLX5_ADDR_OF (fte_match_set_lyr_2_4, match_c_set_lyr_2_4, + dmac_47_16); + +if (is_multicast_ether_addr (dmac) && +is_multicast_ether_addr (dmac_mask)) +return true; + + ipv4 =MLX5_ADDR_OF (fte_match_set_lyr_2_4, match_v_set_lyr_2_4, + dst_ipv4_dst_ipv6.ipv4_layout.ipv4); + + ipv4_mask =MLX5_ADDR_OF (fte_match_set_lyr_2_4, match_c_set_lyr_2_4, + dst_ipv4_dst_ipv6.ipv4_layout.ipv4); + +if (ipv4_is_multicast (*(__be32 *)(ipv4)) && +ipv4_is_multicast (*(__be32 *)(ipv4_mask))) +return true; + +return false; +} +struct mlx5_ib_flow_handler *mlx5_ib_raw_fs_rule_add (struct mlx5_ib_dev *dev,struct mlx5_ib_flow_matcher *fs_matcher,void *cmd_in,int inlen,int dest_id,int dest_type) { -return ERR_PTR (-EOPNOTSUPP ); +struct mlx5_flow_destination *dst; +struct mlx5_ib_flow_prio *ft_prio; +int priority = fs_matcher->priority; +struct mlx5_ib_flow_handler *handler; +bool mcast; +int err; + +if (fs_matcher->flow_type !=MLX5_IB_FLOW_TYPE_NORMAL ) +return ERR_PTR (-EOPNOTSUPP ); + +if (fs_matcher->priority >MLX5_IB_FLOW_LAST_PRIO ) +return ERR_PTR (-ENOMEM ); + +if (dest_type !=MLX5_FLOW_DESTINATION_TYPE_TIR ) +return ERR_PTR (-ENOTSUPP ); + + dst =kzalloc (sizeof (*dst),GFP_KERNEL ); +if (!dst) +return ERR_PTR (-ENOMEM ); + + mcast =raw_fs_is_multicast (fs_matcher, cmd_in); +mutex_lock (&dev->flow_db->lock); + + ft_prio =_get_flow_table (dev, priority, mcast); +if (IS_ERR (ft_prio)) { + err =PTR_ERR (ft_prio); + goto unlock; + } + + dst->type = dest_type; + dst->tir_num = dest_id; + handler =_create_raw_flow_rule (dev, ft_prio, dst, fs_matcher, cmd_in, + inlen); + +if (IS_ERR (handler)) { + err =PTR_ERR (handler); + goto destroy_ft; + } + +mutex_unlock (&dev->flow_db->lock); +atomic_inc (&fs_matcher->usecnt); + handler->flow_matcher = fs_matcher; + +kfree (dst); + +return handler; + +destroy_ft: +put_flow_table (dev, ft_prio, false); +unlock: +mutex_unlock (&dev->flow_db->lock); +kfree (dst); + +return ERR_PTR (err); }static u32 mlx5_ib_flow_action_flags_to_accel_xfrm_flags (u32 mlx5_flags)
drivers/infiniband/hw/mlx5/mlx5_ib.h +2 -0
@@ -178,6 +178,8 @@ struct mlx5_ib_flow_handler {struct mlx5_ib_flow_prio *prio;struct mlx5_flow_handle *rule;struct ib_counters *ibcounters; +struct mlx5_ib_dev *dev; +struct mlx5_ib_flow_matcher *flow_matcher; };struct mlx5_ib_flow_matcher {
Signature · 1 line
2.14.4
PATCH 7/8 IB/mlx5: Add support for a flow table destination
In reply to Leon RomanovskyFrom: Yishai Hadas <[email protected]>
Add support to set a destination that is a flow table, this can come from the DEVX destination.
--- drivers/infiniband/hw/mlx5/main.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-)
drivers/infiniband/hw/mlx5/main.c +8 -5
@@ -3791,9 +3791,6 @@ mlx5_ib_raw_fs_rule_add(struct mlx5_ib_dev *dev,if (fs_matcher->priority >MLX5_IB_FLOW_LAST_PRIO )return ERR_PTR (-ENOMEM ); -if (dest_type !=MLX5_FLOW_DESTINATION_TYPE_TIR ) -return ERR_PTR (-ENOTSUPP ); - dst =kzalloc (sizeof (*dst),GFP_KERNEL );if (!dst)return ERR_PTR (-ENOMEM );
@@ -3807,8 +3804,14 @@ mlx5_ib_raw_fs_rule_add(struct mlx5_ib_dev *dev, goto unlock; } - dst->type = dest_type; - dst->tir_num = dest_id; +if (dest_type ==MLX5_FLOW_DESTINATION_TYPE_TIR ) { + dst->type = dest_type; + dst->tir_num = dest_id; + }else { + dst->type =MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE_NUM ; + dst->ft_num = dest_id; + } + handler =_create_raw_flow_rule (dev, ft_prio, dst, fs_matcher, cmd_in, inlen);
Signature · 1 line
2.14.4
PATCH 8/8 IB/mlx5: Expose vendor flow trees
In reply to Leon RomanovskyFrom: Yishai Hadas <[email protected]>
Expose mlx5 flow trees to be used by upper layers.
--- drivers/infiniband/hw/mlx5/flow.c | 9 +++++++++ drivers/infiniband/hw/mlx5/main.c | 4 +++- drivers/infiniband/hw/mlx5/mlx5_ib.h | 3 +++ 3 files changed, 15 insertions(+), 1 deletion(-)
drivers/infiniband/hw/mlx5/flow.c +9 -0
@@ -243,3 +243,12 @@ DECLARE_UVERBS_NAMED_OBJECT(MLX5_IB_OBJECT_FLOW_MATCHER,DECLARE_UVERBS_OBJECT_TREE (flow_objects, &UVERBS_OBJECT (MLX5_IB_OBJECT_FLOW_MATCHER )); +int mlx5_ib_get_flow_trees (const struct uverbs_object_tree_def **root) +{ +int i =0 ; + + root[i++] = &flow_objects; + root[i++] = &mlx5_ib_fs; + +return i; +}
drivers/infiniband/hw/mlx5/main.c +3 -1
@@ -5537,7 +5537,7 @@ ADD_UVERBS_ATTRIBUTES_SIMPLE(UVERBS_ATTR_TYPE (u64), UA_MANDATORY)); -#define NUM_TREES 3 +#define NUM_TREES 5static int populate_specs_root (struct mlx5_ib_dev *dev) {const struct uverbs_object_tree_def *default_root[NUM_TREES +1 ] = {
@@ -5557,6 +5557,8 @@ static int populate_specs_root(struct mlx5_ib_dev *dev) !WARN_ON(num_trees >= ARRAY_SIZE(default_root))) default_root[num_trees++] = mlx5_ib_get_devx_tree(); + num_trees +=mlx5_ib_get_flow_trees (default_root + num_trees); + dev->ib_dev.driver_specs_root =uverbs_alloc_spec_tree (num_trees, default_root);
drivers/infiniband/hw/mlx5/mlx5_ib.h +3 -0
@@ -1244,6 +1244,7 @@ struct mlx5_ib_flow_handler *mlx5_ib_raw_fs_rule_add(struct mlx5_ib_dev *dev, int inlen, int dest_id, int dest_type);bool mlx5_ib_devx_is_flow_dest (void *obj,int *dest_id,int *dest_type); +int mlx5_ib_get_flow_trees (const struct uverbs_object_tree_def **root);#else static inline int mlx5_ib_devx_create(struct mlx5_ib_dev *dev,
@@ -1261,6 +1262,8 @@ mlx5_ib_raw_fs_rule_add(struct mlx5_ib_dev *dev,static inline bool mlx5_ib_devx_is_flow_dest (void *obj,int *dest_id,int *dest_type) {return false; }; +static inline int +mlx5_ib_get_flow_trees (const struct uverbs_object_tree_def **root) {return 0 ; };#endif static inline void init_query_mad (struct ib_smp *mad) {
Signature · 1 line
2.14.4