1 | /* SPDX-License-Identifier: GPL-2.0 OR Linux-OpenIB */ |
2 | /* Copyright (c) 2020 NVIDIA CORPORATION. All rights reserved. */ |
3 | |
4 | #ifndef _DR_STE_ |
5 | #define _DR_STE_ |
6 | |
7 | #include "dr_types.h" |
8 | |
9 | #define STE_IPV4 0x1 |
10 | #define STE_IPV6 0x2 |
11 | #define STE_TCP 0x1 |
12 | #define STE_UDP 0x2 |
13 | #define STE_SPI 0x3 |
14 | #define IP_VERSION_IPV4 0x4 |
15 | #define IP_VERSION_IPV6 0x6 |
16 | #define STE_SVLAN 0x1 |
17 | #define STE_CVLAN 0x2 |
18 | #define HDR_LEN_L2_MACS 0xC |
19 | #define HDR_LEN_L2_VLAN 0x4 |
20 | #define HDR_LEN_L2_ETHER 0x2 |
21 | #define HDR_LEN_L2 (HDR_LEN_L2_MACS + HDR_LEN_L2_ETHER) |
22 | #define HDR_LEN_L2_W_VLAN (HDR_LEN_L2 + HDR_LEN_L2_VLAN) |
23 | |
24 | /* Set to STE a specific value using DR_STE_SET */ |
25 | #define DR_STE_SET_VAL(lookup_type, tag, t_fname, spec, s_fname, value) do { \ |
26 | if ((spec)->s_fname) { \ |
27 | MLX5_SET(ste_##lookup_type, tag, t_fname, value); \ |
28 | (spec)->s_fname = 0; \ |
29 | } \ |
30 | } while (0) |
31 | |
32 | /* Set to STE spec->s_fname to tag->t_fname set spec->s_fname as used */ |
33 | #define DR_STE_SET_TAG(lookup_type, tag, t_fname, spec, s_fname) \ |
34 | DR_STE_SET_VAL(lookup_type, tag, t_fname, spec, s_fname, spec->s_fname) |
35 | |
36 | /* Set to STE -1 to tag->t_fname and set spec->s_fname as used */ |
37 | #define DR_STE_SET_ONES(lookup_type, tag, t_fname, spec, s_fname) \ |
38 | DR_STE_SET_VAL(lookup_type, tag, t_fname, spec, s_fname, -1) |
39 | |
40 | #define DR_STE_SET_TCP_FLAGS(lookup_type, tag, spec) do { \ |
41 | MLX5_SET(ste_##lookup_type, tag, tcp_ns, !!((spec)->tcp_flags & (1 << 8))); \ |
42 | MLX5_SET(ste_##lookup_type, tag, tcp_cwr, !!((spec)->tcp_flags & (1 << 7))); \ |
43 | MLX5_SET(ste_##lookup_type, tag, tcp_ece, !!((spec)->tcp_flags & (1 << 6))); \ |
44 | MLX5_SET(ste_##lookup_type, tag, tcp_urg, !!((spec)->tcp_flags & (1 << 5))); \ |
45 | MLX5_SET(ste_##lookup_type, tag, tcp_ack, !!((spec)->tcp_flags & (1 << 4))); \ |
46 | MLX5_SET(ste_##lookup_type, tag, tcp_psh, !!((spec)->tcp_flags & (1 << 3))); \ |
47 | MLX5_SET(ste_##lookup_type, tag, tcp_rst, !!((spec)->tcp_flags & (1 << 2))); \ |
48 | MLX5_SET(ste_##lookup_type, tag, tcp_syn, !!((spec)->tcp_flags & (1 << 1))); \ |
49 | MLX5_SET(ste_##lookup_type, tag, tcp_fin, !!((spec)->tcp_flags & (1 << 0))); \ |
50 | } while (0) |
51 | |
52 | #define DR_STE_SET_MPLS(lookup_type, mask, in_out, tag) do { \ |
53 | struct mlx5dr_match_misc2 *_mask = mask; \ |
54 | u8 *_tag = tag; \ |
55 | DR_STE_SET_TAG(lookup_type, _tag, mpls0_label, _mask, \ |
56 | in_out##_first_mpls_label);\ |
57 | DR_STE_SET_TAG(lookup_type, _tag, mpls0_s_bos, _mask, \ |
58 | in_out##_first_mpls_s_bos); \ |
59 | DR_STE_SET_TAG(lookup_type, _tag, mpls0_exp, _mask, \ |
60 | in_out##_first_mpls_exp); \ |
61 | DR_STE_SET_TAG(lookup_type, _tag, mpls0_ttl, _mask, \ |
62 | in_out##_first_mpls_ttl); \ |
63 | } while (0) |
64 | |
65 | #define DR_STE_SET_FLEX_PARSER_FIELD(tag, fname, caps, spec) do { \ |
66 | u8 parser_id = (caps)->flex_parser_id_##fname; \ |
67 | u8 *parser_ptr = dr_ste_calc_flex_parser_offset(tag, parser_id); \ |
68 | *(__be32 *)parser_ptr = cpu_to_be32((spec)->fname);\ |
69 | (spec)->fname = 0;\ |
70 | } while (0) |
71 | |
72 | #define DR_STE_IS_OUTER_MPLS_OVER_GRE_SET(_misc) (\ |
73 | (_misc)->outer_first_mpls_over_gre_label || \ |
74 | (_misc)->outer_first_mpls_over_gre_exp || \ |
75 | (_misc)->outer_first_mpls_over_gre_s_bos || \ |
76 | (_misc)->outer_first_mpls_over_gre_ttl) |
77 | |
78 | #define DR_STE_IS_OUTER_MPLS_OVER_UDP_SET(_misc) (\ |
79 | (_misc)->outer_first_mpls_over_udp_label || \ |
80 | (_misc)->outer_first_mpls_over_udp_exp || \ |
81 | (_misc)->outer_first_mpls_over_udp_s_bos || \ |
82 | (_misc)->outer_first_mpls_over_udp_ttl) |
83 | |
84 | enum dr_ste_action_modify_type_l3 { |
85 | DR_STE_ACTION_MDFY_TYPE_L3_NONE = 0x0, |
86 | DR_STE_ACTION_MDFY_TYPE_L3_IPV4 = 0x1, |
87 | DR_STE_ACTION_MDFY_TYPE_L3_IPV6 = 0x2, |
88 | }; |
89 | |
90 | enum dr_ste_action_modify_type_l4 { |
91 | DR_STE_ACTION_MDFY_TYPE_L4_NONE = 0x0, |
92 | DR_STE_ACTION_MDFY_TYPE_L4_TCP = 0x1, |
93 | DR_STE_ACTION_MDFY_TYPE_L4_UDP = 0x2, |
94 | }; |
95 | |
96 | enum { |
97 | HDR_MPLS_OFFSET_LABEL = 12, |
98 | HDR_MPLS_OFFSET_EXP = 9, |
99 | HDR_MPLS_OFFSET_S_BOS = 8, |
100 | HDR_MPLS_OFFSET_TTL = 0, |
101 | }; |
102 | |
103 | u16 mlx5dr_ste_conv_bit_to_byte_mask(u8 *bit_mask); |
104 | |
105 | static inline u8 * |
106 | dr_ste_calc_flex_parser_offset(u8 *tag, u8 parser_id) |
107 | { |
108 | /* Calculate tag byte offset based on flex parser id */ |
109 | return tag + 4 * (3 - (parser_id % 4)); |
110 | } |
111 | |
112 | #define DR_STE_CTX_BUILDER(fname) \ |
113 | ((*build_##fname##_init)(struct mlx5dr_ste_build *sb, \ |
114 | struct mlx5dr_match_param *mask)) |
115 | |
116 | struct mlx5dr_ste_ctx { |
117 | /* Builders */ |
118 | void DR_STE_CTX_BUILDER(eth_l2_src_dst); |
119 | void DR_STE_CTX_BUILDER(eth_l3_ipv6_src); |
120 | void DR_STE_CTX_BUILDER(eth_l3_ipv6_dst); |
121 | void DR_STE_CTX_BUILDER(eth_l3_ipv4_5_tuple); |
122 | void DR_STE_CTX_BUILDER(eth_l2_src); |
123 | void DR_STE_CTX_BUILDER(eth_l2_dst); |
124 | void DR_STE_CTX_BUILDER(eth_l2_tnl); |
125 | void DR_STE_CTX_BUILDER(eth_l3_ipv4_misc); |
126 | void DR_STE_CTX_BUILDER(eth_ipv6_l3_l4); |
127 | void DR_STE_CTX_BUILDER(mpls); |
128 | void DR_STE_CTX_BUILDER(tnl_gre); |
129 | void DR_STE_CTX_BUILDER(tnl_mpls); |
130 | void DR_STE_CTX_BUILDER(tnl_mpls_over_gre); |
131 | void DR_STE_CTX_BUILDER(tnl_mpls_over_udp); |
132 | void DR_STE_CTX_BUILDER(icmp); |
133 | void DR_STE_CTX_BUILDER(general_purpose); |
134 | void DR_STE_CTX_BUILDER(eth_l4_misc); |
135 | void DR_STE_CTX_BUILDER(tnl_vxlan_gpe); |
136 | void DR_STE_CTX_BUILDER(tnl_geneve); |
137 | void DR_STE_CTX_BUILDER(tnl_geneve_tlv_opt); |
138 | void DR_STE_CTX_BUILDER(tnl_geneve_tlv_opt_exist); |
139 | void DR_STE_CTX_BUILDER(register_0); |
140 | void DR_STE_CTX_BUILDER(register_1); |
141 | void DR_STE_CTX_BUILDER(src_gvmi_qpn); |
142 | void DR_STE_CTX_BUILDER(flex_parser_0); |
143 | void DR_STE_CTX_BUILDER(flex_parser_1); |
144 | void DR_STE_CTX_BUILDER(tnl_gtpu); |
145 | void DR_STE_CTX_BUILDER(tnl_header_0_1); |
146 | void DR_STE_CTX_BUILDER(tnl_gtpu_flex_parser_0); |
147 | void DR_STE_CTX_BUILDER(tnl_gtpu_flex_parser_1); |
148 | |
149 | /* Getters and Setters */ |
150 | void (*ste_init)(u8 *hw_ste_p, u16 lu_type, |
151 | bool is_rx, u16 gvmi); |
152 | void (*set_next_lu_type)(u8 *hw_ste_p, u16 lu_type); |
153 | u16 (*get_next_lu_type)(u8 *hw_ste_p); |
154 | bool (*is_miss_addr_set)(u8 *hw_ste_p); |
155 | void (*set_miss_addr)(u8 *hw_ste_p, u64 miss_addr); |
156 | u64 (*get_miss_addr)(u8 *hw_ste_p); |
157 | void (*set_hit_addr)(u8 *hw_ste_p, u64 icm_addr, u32 ht_size); |
158 | void (*set_byte_mask)(u8 *hw_ste_p, u16 byte_mask); |
159 | u16 (*get_byte_mask)(u8 *hw_ste_p); |
160 | |
161 | /* Actions */ |
162 | u32 actions_caps; |
163 | void (*set_actions_rx)(struct mlx5dr_domain *dmn, |
164 | u8 *action_type_set, |
165 | u32 actions_caps, |
166 | u8 *hw_ste_arr, |
167 | struct mlx5dr_ste_actions_attr *attr, |
168 | u32 *added_stes); |
169 | void (*set_actions_tx)(struct mlx5dr_domain *dmn, |
170 | u8 *action_type_set, |
171 | u32 actions_caps, |
172 | u8 *hw_ste_arr, |
173 | struct mlx5dr_ste_actions_attr *attr, |
174 | u32 *added_stes); |
175 | u32 modify_field_arr_sz; |
176 | const struct mlx5dr_ste_action_modify_field *modify_field_arr; |
177 | void (*set_action_set)(u8 *hw_action, |
178 | u8 hw_field, |
179 | u8 shifter, |
180 | u8 length, |
181 | u32 data); |
182 | void (*set_action_add)(u8 *hw_action, |
183 | u8 hw_field, |
184 | u8 shifter, |
185 | u8 length, |
186 | u32 data); |
187 | void (*set_action_copy)(u8 *hw_action, |
188 | u8 dst_hw_field, |
189 | u8 dst_shifter, |
190 | u8 dst_len, |
191 | u8 src_hw_field, |
192 | u8 src_shifter); |
193 | int (*set_action_decap_l3_list)(void *data, |
194 | u32 data_sz, |
195 | u8 *hw_action, |
196 | u32 hw_action_sz, |
197 | u16 *used_hw_action_num); |
198 | int (*alloc_modify_hdr_chunk)(struct mlx5dr_action *action); |
199 | void (*dealloc_modify_hdr_chunk)(struct mlx5dr_action *action); |
200 | |
201 | /* Send */ |
202 | void (*prepare_for_postsend)(u8 *hw_ste_p, u32 ste_size); |
203 | }; |
204 | |
205 | struct mlx5dr_ste_ctx *mlx5dr_ste_get_ctx_v0(void); |
206 | struct mlx5dr_ste_ctx *mlx5dr_ste_get_ctx_v1(void); |
207 | struct mlx5dr_ste_ctx *mlx5dr_ste_get_ctx_v2(void); |
208 | |
209 | #endif /* _DR_STE_ */ |
210 | |