doc: announce renaming of mbuf offload flags
[dpdk.git] / drivers / net / cnxk / cnxk_lookup.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(C) 2021 Marvell.
3  */
4
5 #include <rte_common.h>
6 #include <rte_memzone.h>
7
8 #include "cnxk_ethdev.h"
9
10 /* NIX_RX_PARSE_S's ERRCODE + ERRLEV (12 bits) */
11 #define ERRCODE_ERRLEN_WIDTH 12
12 #define ERR_ARRAY_SZ         ((BIT(ERRCODE_ERRLEN_WIDTH)) * sizeof(uint32_t))
13
14 #define SA_TBL_SZ       (RTE_MAX_ETHPORTS * sizeof(uint64_t))
15 #define LOOKUP_ARRAY_SZ (PTYPE_ARRAY_SZ + ERR_ARRAY_SZ + SA_TBL_SZ)
16 const uint32_t *
17 cnxk_nix_supported_ptypes_get(struct rte_eth_dev *eth_dev)
18 {
19         RTE_SET_USED(eth_dev);
20
21         static const uint32_t ptypes[] = {
22                 RTE_PTYPE_L2_ETHER_QINQ,      /* LB */
23                 RTE_PTYPE_L2_ETHER_VLAN,      /* LB */
24                 RTE_PTYPE_L2_ETHER_TIMESYNC,  /* LB */
25                 RTE_PTYPE_L2_ETHER_ARP,       /* LC */
26                 RTE_PTYPE_L2_ETHER_NSH,       /* LC */
27                 RTE_PTYPE_L2_ETHER_FCOE,      /* LC */
28                 RTE_PTYPE_L2_ETHER_MPLS,      /* LC */
29                 RTE_PTYPE_L3_IPV4,            /* LC */
30                 RTE_PTYPE_L3_IPV4_EXT,        /* LC */
31                 RTE_PTYPE_L3_IPV6,            /* LC */
32                 RTE_PTYPE_L3_IPV6_EXT,        /* LC */
33                 RTE_PTYPE_L4_TCP,             /* LD */
34                 RTE_PTYPE_L4_UDP,             /* LD */
35                 RTE_PTYPE_L4_SCTP,            /* LD */
36                 RTE_PTYPE_L4_ICMP,            /* LD */
37                 RTE_PTYPE_L4_IGMP,            /* LD */
38                 RTE_PTYPE_TUNNEL_GRE,         /* LD */
39                 RTE_PTYPE_TUNNEL_ESP,         /* LD */
40                 RTE_PTYPE_TUNNEL_NVGRE,       /* LD */
41                 RTE_PTYPE_TUNNEL_VXLAN,       /* LE */
42                 RTE_PTYPE_TUNNEL_GENEVE,      /* LE */
43                 RTE_PTYPE_TUNNEL_GTPC,        /* LE */
44                 RTE_PTYPE_TUNNEL_GTPU,        /* LE */
45                 RTE_PTYPE_TUNNEL_VXLAN_GPE,   /* LE */
46                 RTE_PTYPE_TUNNEL_MPLS_IN_GRE, /* LE */
47                 RTE_PTYPE_TUNNEL_MPLS_IN_UDP, /* LE */
48                 RTE_PTYPE_INNER_L2_ETHER,     /* LF */
49                 RTE_PTYPE_INNER_L3_IPV4,      /* LG */
50                 RTE_PTYPE_INNER_L3_IPV6,      /* LG */
51                 RTE_PTYPE_INNER_L4_TCP,       /* LH */
52                 RTE_PTYPE_INNER_L4_UDP,       /* LH */
53                 RTE_PTYPE_INNER_L4_SCTP,      /* LH */
54                 RTE_PTYPE_INNER_L4_ICMP,      /* LH */
55                 RTE_PTYPE_UNKNOWN,
56         };
57
58         return ptypes;
59 }
60
61 /*
62  * +------------------ +------------------ +
63  * |  | IL4 | IL3| IL2 | TU | L4 | L3 | L2 |
64  * +-------------------+-------------------+
65  *
66  * +-------------------+------------------ +
67  * |  | LH | LG  | LF  | LE | LD | LC | LB |
68  * +-------------------+-------------------+
69  *
70  * ptype       [LE - LD - LC - LB]  = TU  - L4 -  L3  - T2
71  * ptype_tunnel[LH - LG - LF]  = IL4 - IL3 - IL2 - TU
72  *
73  */
74 static void
75 nix_create_non_tunnel_ptype_array(uint16_t *ptype)
76 {
77         uint8_t lb, lc, ld, le;
78         uint16_t val;
79         uint32_t idx;
80
81         for (idx = 0; idx < PTYPE_NON_TUNNEL_ARRAY_SZ; idx++) {
82                 lb = idx & 0xF;
83                 lc = (idx & 0xF0) >> 4;
84                 ld = (idx & 0xF00) >> 8;
85                 le = (idx & 0xF000) >> 12;
86                 val = RTE_PTYPE_UNKNOWN;
87
88                 switch (lb) {
89                 case NPC_LT_LB_STAG_QINQ:
90                         val |= RTE_PTYPE_L2_ETHER_QINQ;
91                         break;
92                 case NPC_LT_LB_CTAG:
93                         val |= RTE_PTYPE_L2_ETHER_VLAN;
94                         break;
95                 }
96
97                 switch (lc) {
98                 case NPC_LT_LC_ARP:
99                         val |= RTE_PTYPE_L2_ETHER_ARP;
100                         break;
101                 case NPC_LT_LC_NSH:
102                         val |= RTE_PTYPE_L2_ETHER_NSH;
103                         break;
104                 case NPC_LT_LC_FCOE:
105                         val |= RTE_PTYPE_L2_ETHER_FCOE;
106                         break;
107                 case NPC_LT_LC_MPLS:
108                         val |= RTE_PTYPE_L2_ETHER_MPLS;
109                         break;
110                 case NPC_LT_LC_IP:
111                         val |= RTE_PTYPE_L3_IPV4;
112                         break;
113                 case NPC_LT_LC_IP_OPT:
114                         val |= RTE_PTYPE_L3_IPV4_EXT;
115                         break;
116                 case NPC_LT_LC_IP6:
117                         val |= RTE_PTYPE_L3_IPV6;
118                         break;
119                 case NPC_LT_LC_IP6_EXT:
120                         val |= RTE_PTYPE_L3_IPV6_EXT;
121                         break;
122                 case NPC_LT_LC_PTP:
123                         val |= RTE_PTYPE_L2_ETHER_TIMESYNC;
124                         break;
125                 }
126
127                 switch (ld) {
128                 case NPC_LT_LD_TCP:
129                         val |= RTE_PTYPE_L4_TCP;
130                         break;
131                 case NPC_LT_LD_UDP:
132                         val |= RTE_PTYPE_L4_UDP;
133                         break;
134                 case NPC_LT_LD_SCTP:
135                         val |= RTE_PTYPE_L4_SCTP;
136                         break;
137                 case NPC_LT_LD_ICMP:
138                 case NPC_LT_LD_ICMP6:
139                         val |= RTE_PTYPE_L4_ICMP;
140                         break;
141                 case NPC_LT_LD_IGMP:
142                         val |= RTE_PTYPE_L4_IGMP;
143                         break;
144                 case NPC_LT_LD_GRE:
145                         val |= RTE_PTYPE_TUNNEL_GRE;
146                         break;
147                 case NPC_LT_LD_NVGRE:
148                         val |= RTE_PTYPE_TUNNEL_NVGRE;
149                         break;
150                 }
151
152                 switch (le) {
153                 case NPC_LT_LE_VXLAN:
154                         val |= RTE_PTYPE_TUNNEL_VXLAN;
155                         break;
156                 case NPC_LT_LE_ESP:
157                         val |= RTE_PTYPE_TUNNEL_ESP;
158                         break;
159                 case NPC_LT_LE_VXLANGPE:
160                         val |= RTE_PTYPE_TUNNEL_VXLAN_GPE;
161                         break;
162                 case NPC_LT_LE_GENEVE:
163                         val |= RTE_PTYPE_TUNNEL_GENEVE;
164                         break;
165                 case NPC_LT_LE_GTPC:
166                         val |= RTE_PTYPE_TUNNEL_GTPC;
167                         break;
168                 case NPC_LT_LE_GTPU:
169                         val |= RTE_PTYPE_TUNNEL_GTPU;
170                         break;
171                 case NPC_LT_LE_TU_MPLS_IN_GRE:
172                         val |= RTE_PTYPE_TUNNEL_MPLS_IN_GRE;
173                         break;
174                 case NPC_LT_LE_TU_MPLS_IN_UDP:
175                         val |= RTE_PTYPE_TUNNEL_MPLS_IN_UDP;
176                         break;
177                 }
178                 ptype[idx] = val;
179         }
180 }
181
182 #define TU_SHIFT(x) ((x) >> PTYPE_NON_TUNNEL_WIDTH)
183 static void
184 nix_create_tunnel_ptype_array(uint16_t *ptype)
185 {
186         uint8_t lf, lg, lh;
187         uint16_t val;
188         uint32_t idx;
189
190         /* Skip non tunnel ptype array memory */
191         ptype = ptype + PTYPE_NON_TUNNEL_ARRAY_SZ;
192
193         for (idx = 0; idx < PTYPE_TUNNEL_ARRAY_SZ; idx++) {
194                 lf = idx & 0xF;
195                 lg = (idx & 0xF0) >> 4;
196                 lh = (idx & 0xF00) >> 8;
197                 val = RTE_PTYPE_UNKNOWN;
198
199                 switch (lf) {
200                 case NPC_LT_LF_TU_ETHER:
201                         val |= TU_SHIFT(RTE_PTYPE_INNER_L2_ETHER);
202                         break;
203                 }
204                 switch (lg) {
205                 case NPC_LT_LG_TU_IP:
206                         val |= TU_SHIFT(RTE_PTYPE_INNER_L3_IPV4);
207                         break;
208                 case NPC_LT_LG_TU_IP6:
209                         val |= TU_SHIFT(RTE_PTYPE_INNER_L3_IPV6);
210                         break;
211                 }
212                 switch (lh) {
213                 case NPC_LT_LH_TU_TCP:
214                         val |= TU_SHIFT(RTE_PTYPE_INNER_L4_TCP);
215                         break;
216                 case NPC_LT_LH_TU_UDP:
217                         val |= TU_SHIFT(RTE_PTYPE_INNER_L4_UDP);
218                         break;
219                 case NPC_LT_LH_TU_SCTP:
220                         val |= TU_SHIFT(RTE_PTYPE_INNER_L4_SCTP);
221                         break;
222                 case NPC_LT_LH_TU_ICMP:
223                 case NPC_LT_LH_TU_ICMP6:
224                         val |= TU_SHIFT(RTE_PTYPE_INNER_L4_ICMP);
225                         break;
226                 }
227
228                 ptype[idx] = val;
229         }
230 }
231
232 static void
233 nix_create_rx_ol_flags_array(void *mem)
234 {
235         uint16_t idx, errcode, errlev;
236         uint32_t val, *ol_flags;
237
238         /* Skip ptype array memory */
239         ol_flags = (uint32_t *)((uint8_t *)mem + PTYPE_ARRAY_SZ);
240
241         for (idx = 0; idx < BIT(ERRCODE_ERRLEN_WIDTH); idx++) {
242                 errlev = idx & 0xf;
243                 errcode = (idx & 0xff0) >> 4;
244
245                 val = PKT_RX_IP_CKSUM_UNKNOWN;
246                 val |= PKT_RX_L4_CKSUM_UNKNOWN;
247                 val |= PKT_RX_OUTER_L4_CKSUM_UNKNOWN;
248
249                 switch (errlev) {
250                 case NPC_ERRLEV_RE:
251                         /* Mark all errors as BAD checksum errors
252                          * including Outer L2 length mismatch error
253                          */
254                         if (errcode) {
255                                 val |= PKT_RX_IP_CKSUM_BAD;
256                                 val |= PKT_RX_L4_CKSUM_BAD;
257                         } else {
258                                 val |= PKT_RX_IP_CKSUM_GOOD;
259                                 val |= PKT_RX_L4_CKSUM_GOOD;
260                         }
261                         break;
262                 case NPC_ERRLEV_LC:
263                         if (errcode == NPC_EC_OIP4_CSUM ||
264                             errcode == NPC_EC_IP_FRAG_OFFSET_1) {
265                                 val |= PKT_RX_IP_CKSUM_BAD;
266                                 val |= PKT_RX_OUTER_IP_CKSUM_BAD;
267                         } else {
268                                 val |= PKT_RX_IP_CKSUM_GOOD;
269                         }
270                         break;
271                 case NPC_ERRLEV_LG:
272                         if (errcode == NPC_EC_IIP4_CSUM)
273                                 val |= PKT_RX_IP_CKSUM_BAD;
274                         else
275                                 val |= PKT_RX_IP_CKSUM_GOOD;
276                         break;
277                 case NPC_ERRLEV_NIX:
278                         if (errcode == NIX_RX_PERRCODE_OL4_CHK ||
279                             errcode == NIX_RX_PERRCODE_OL4_LEN ||
280                             errcode == NIX_RX_PERRCODE_OL4_PORT) {
281                                 val |= PKT_RX_IP_CKSUM_GOOD;
282                                 val |= PKT_RX_L4_CKSUM_BAD;
283                                 val |= PKT_RX_OUTER_L4_CKSUM_BAD;
284                         } else if (errcode == NIX_RX_PERRCODE_IL4_CHK ||
285                                    errcode == NIX_RX_PERRCODE_IL4_LEN ||
286                                    errcode == NIX_RX_PERRCODE_IL4_PORT) {
287                                 val |= PKT_RX_IP_CKSUM_GOOD;
288                                 val |= PKT_RX_L4_CKSUM_BAD;
289                         } else if (errcode == NIX_RX_PERRCODE_IL3_LEN ||
290                                    errcode == NIX_RX_PERRCODE_OL3_LEN) {
291                                 val |= PKT_RX_IP_CKSUM_BAD;
292                         } else {
293                                 val |= PKT_RX_IP_CKSUM_GOOD;
294                                 val |= PKT_RX_L4_CKSUM_GOOD;
295                         }
296                         break;
297                 }
298                 ol_flags[idx] = val;
299         }
300 }
301
302 void *
303 cnxk_nix_fastpath_lookup_mem_get(void)
304 {
305         const char name[] = CNXK_NIX_FASTPATH_LOOKUP_MEM;
306         const struct rte_memzone *mz;
307         void *mem;
308
309         mz = rte_memzone_lookup(name);
310         if (mz != NULL)
311                 return mz->addr;
312
313         /* Request for the first time */
314         mz = rte_memzone_reserve_aligned(name, LOOKUP_ARRAY_SZ, SOCKET_ID_ANY,
315                                          0, ROC_ALIGN);
316         if (mz != NULL) {
317                 mem = mz->addr;
318                 /* Form the ptype array lookup memory */
319                 nix_create_non_tunnel_ptype_array(mem);
320                 nix_create_tunnel_ptype_array(mem);
321                 /* Form the rx ol_flags based on errcode */
322                 nix_create_rx_ol_flags_array(mem);
323                 return mem;
324         }
325         return NULL;
326 }