Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause
2 : : * Copyright(C) 2021 Marvell.
3 : : */
4 : : #ifndef __CN10K_RX_H__
5 : : #define __CN10K_RX_H__
6 : :
7 : : #include <rte_ethdev.h>
8 : : #include <rte_security_driver.h>
9 : : #include <rte_vect.h>
10 : : #include "cn10k_rxtx.h"
11 : :
12 : : #define NSEC_PER_SEC 1000000000L
13 : :
14 : : #define NIX_RX_OFFLOAD_NONE (0)
15 : : #define NIX_RX_OFFLOAD_RSS_F BIT(0)
16 : : #define NIX_RX_OFFLOAD_PTYPE_F BIT(1)
17 : : #define NIX_RX_OFFLOAD_CHECKSUM_F BIT(2)
18 : : #define NIX_RX_OFFLOAD_MARK_UPDATE_F BIT(3)
19 : : #define NIX_RX_OFFLOAD_TSTAMP_F BIT(4)
20 : : #define NIX_RX_OFFLOAD_VLAN_STRIP_F BIT(5)
21 : : #define NIX_RX_OFFLOAD_SECURITY_F BIT(6)
22 : : #define NIX_RX_OFFLOAD_MAX (NIX_RX_OFFLOAD_SECURITY_F << 1)
23 : :
24 : : /* Flags to control cqe_to_mbuf conversion function.
25 : : * Defining it from backwards to denote its been
26 : : * not used as offload flags to pick function
27 : : */
28 : : #define NIX_RX_REAS_F BIT(12)
29 : : #define NIX_RX_VWQE_F BIT(13)
30 : : #define NIX_RX_MULTI_SEG_F BIT(14)
31 : :
32 : : #define CNXK_NIX_CQ_ENTRY_SZ 128
33 : : #define NIX_DESCS_PER_LOOP 4
34 : : #define CQE_CAST(x) ((struct nix_cqe_hdr_s *)(x))
35 : : #define CQE_SZ(x) ((x) * CNXK_NIX_CQ_ENTRY_SZ)
36 : :
37 : : #define CQE_PTR_OFF(b, i, o, f) \
38 : : (((f) & NIX_RX_VWQE_F) ? \
39 : : (uint64_t *)(((uintptr_t)((uint64_t *)(b))[i]) + (o)) : \
40 : : (uint64_t *)(((uintptr_t)(b)) + CQE_SZ(i) + (o)))
41 : : #define CQE_PTR_DIFF(b, i, o, f) \
42 : : (((f) & NIX_RX_VWQE_F) ? \
43 : : (uint64_t *)(((uintptr_t)((uint64_t *)(b))[i]) - (o)) : \
44 : : (uint64_t *)(((uintptr_t)(b)) + CQE_SZ(i) - (o)))
45 : :
46 : : #define NIX_RX_SEC_UCC_CONST \
47 : : ((RTE_MBUF_F_RX_IP_CKSUM_BAD >> 1) | \
48 : : ((RTE_MBUF_F_RX_IP_CKSUM_GOOD | RTE_MBUF_F_RX_L4_CKSUM_GOOD) >> 1) << 8 | \
49 : : ((RTE_MBUF_F_RX_IP_CKSUM_GOOD | RTE_MBUF_F_RX_L4_CKSUM_BAD) >> 1) << 16 | \
50 : : ((RTE_MBUF_F_RX_IP_CKSUM_GOOD | RTE_MBUF_F_RX_L4_CKSUM_GOOD) >> 1) << 32 | \
51 : : ((RTE_MBUF_F_RX_IP_CKSUM_GOOD | RTE_MBUF_F_RX_L4_CKSUM_GOOD) >> 1) << 48)
52 : :
53 : : #ifdef RTE_LIBRTE_MEMPOOL_DEBUG
54 : : static inline void
55 : : nix_mbuf_validate_next(struct rte_mbuf *m)
56 : : {
57 : : if (m->nb_segs == 1 && m->next) {
58 : : rte_panic("mbuf->next[%p] valid when mbuf->nb_segs is %d",
59 : : m->next, m->nb_segs);
60 : : }
61 : : }
62 : : #else
63 : : static inline void
64 : : nix_mbuf_validate_next(struct rte_mbuf *m)
65 : : {
66 : : RTE_SET_USED(m);
67 : : }
68 : : #endif
69 : :
70 : : #define NIX_RX_SEC_REASSEMBLY_F \
71 : : (NIX_RX_REAS_F | NIX_RX_OFFLOAD_SECURITY_F)
72 : :
73 : : static inline rte_eth_ip_reassembly_dynfield_t *
74 : : cnxk_ip_reassembly_dynfield(struct rte_mbuf *mbuf,
75 : : int ip_reassembly_dynfield_offset)
76 : : {
77 : 0 : return RTE_MBUF_DYNFIELD(mbuf, ip_reassembly_dynfield_offset,
78 : : rte_eth_ip_reassembly_dynfield_t *);
79 : : }
80 : :
81 : : union mbuf_initializer {
82 : : struct {
83 : : uint16_t data_off;
84 : : uint16_t refcnt;
85 : : uint16_t nb_segs;
86 : : uint16_t port;
87 : : } fields;
88 : : uint64_t value;
89 : : };
90 : :
91 : : static __rte_always_inline uint64_t
92 : : nix_clear_data_off(uint64_t oldval)
93 : : {
94 : : union mbuf_initializer mbuf_init = {.value = oldval};
95 : :
96 : : mbuf_init.fields.data_off = 0;
97 : : return mbuf_init.value;
98 : : }
99 : :
100 : : static __rte_always_inline struct rte_mbuf *
101 : : nix_get_mbuf_from_cqe(void *cq, const uint64_t data_off)
102 : : {
103 : : rte_iova_t buff;
104 : :
105 : : /* Skip CQE, NIX_RX_PARSE_S and SG HDR(9 DWORDs) and peek buff addr */
106 : : buff = *((rte_iova_t *)((uint64_t *)cq + 9));
107 : : return (struct rte_mbuf *)(buff - data_off);
108 : : }
109 : :
110 : : static __rte_always_inline void
111 : : nix_sec_flush_meta_burst(uint16_t lmt_id, uint64_t data, uint16_t lnum,
112 : : uintptr_t aura_handle)
113 : : {
114 : : uint64_t pa;
115 : :
116 : : /* Prepare PA and Data */
117 : : pa = roc_npa_aura_handle_to_base(aura_handle) + NPA_LF_AURA_BATCH_FREE0;
118 : : pa |= ((data & 0x7) << 4);
119 : :
120 : : data >>= 3;
121 : : data <<= 19;
122 : : data |= (uint64_t)lmt_id;
123 : : data |= (uint64_t)(lnum - 1) << 12;
124 : :
125 : : roc_lmt_submit_steorl(data, pa);
126 : : }
127 : :
128 : : static __rte_always_inline void
129 : : nix_sec_flush_meta(uintptr_t laddr, uint16_t lmt_id, uint8_t loff,
130 : : uintptr_t aura_handle)
131 : : {
132 : : uint64_t pa;
133 : :
134 : : /* laddr is pointing to first pointer */
135 : 0 : laddr -= 8;
136 : :
137 : : /* Trigger free either on lmtline full or different aura handle */
138 : : pa = roc_npa_aura_handle_to_base(aura_handle) + NPA_LF_AURA_BATCH_FREE0;
139 : :
140 : : /* Update aura handle */
141 : 0 : *(uint64_t *)laddr = (((uint64_t)(loff & 0x1) << 32) |
142 : : roc_npa_aura_handle_to_aura(aura_handle));
143 : :
144 : : pa |= ((uint64_t)(loff >> 1) << 4);
145 : : roc_lmt_submit_steorl(lmt_id, pa);
146 : : }
147 : :
148 : : #if defined(RTE_ARCH_ARM64)
149 : : static __rte_always_inline uint64_t
150 : : nix_sec_reass_frags_get(const struct cpt_parse_hdr_s *hdr, struct rte_mbuf **next_mbufs)
151 : : {
152 : : const struct cpt_frag_info_s *finfo;
153 : : uint32_t offset = hdr->w2.fi_offset;
154 : : const uint64_t *frag_ptr;
155 : : uint64x2_t frags23;
156 : : uint16x4_t fsz_w1;
157 : :
158 : : /* offset of 0 implies 256B, otherwise it implies offset*8B */
159 : : offset = (((offset - 1) & 0x1f) + 1) * 8;
160 : : finfo = RTE_PTR_ADD(hdr, offset);
161 : : frag_ptr = (const uint64_t *)(finfo + 1);
162 : : frags23 = vrev64q_u8(vld1q_u64(frag_ptr));
163 : :
164 : : next_mbufs[0] = ((struct rte_mbuf *)rte_be_to_cpu_64(hdr->frag1_wqe_ptr) - 1);
165 : : next_mbufs[1] = ((struct rte_mbuf *)vgetq_lane_u64(frags23, 0) - 1);
166 : : next_mbufs[2] = ((struct rte_mbuf *)vgetq_lane_u64(frags23, 1) - 1);
167 : :
168 : : fsz_w1 = vreinterpret_u16_u64(vdup_n_u64(finfo->w1.u64));
169 : : fsz_w1 = vrev16_u8(fsz_w1);
170 : : return vget_lane_u64(vreinterpret_u64_u16(fsz_w1), 0);
171 : : }
172 : :
173 : : static __rte_always_inline void
174 : : nix_sec_reass_first_frag_update(struct rte_mbuf *head, const uint8_t *m_ipptr,
175 : : uint64_t fsz, uint64_t cq_w1, uint16_t *ihl)
176 : : {
177 : : union nix_rx_parse_u *rx = (union nix_rx_parse_u *)((uintptr_t)(head + 1) + 8);
178 : : uint16_t fragx_sum = vaddv_u16(vreinterpret_u16_u64(vdup_n_u64(fsz)));
179 : : uint8_t lcptr = rx->lcptr;
180 : : uint16_t tot_len;
181 : : uint32_t cksum;
182 : : uint8_t *ipptr;
183 : :
184 : : ipptr = (uint8_t *)head->buf_addr + head->data_off + lcptr;
185 : : /* Find the L3 header length and update inner pkt based on meta lc type */
186 : : if (((cq_w1 >> 40) & 0xF) == NPC_LT_LC_IP) {
187 : : const struct rte_ipv4_hdr *m_hdr = (const struct rte_ipv4_hdr *)m_ipptr;
188 : : struct rte_ipv4_hdr *hdr = (struct rte_ipv4_hdr *)ipptr;
189 : :
190 : : *ihl = (m_hdr->version_ihl & 0xf) << 2;
191 : :
192 : : hdr->fragment_offset = 0;
193 : : tot_len = rte_cpu_to_be_16(fragx_sum + *ihl);
194 : : hdr->total_length = tot_len;
195 : : /* Perform incremental checksum based on meta pkt ip hdr */
196 : : cksum = m_hdr->hdr_checksum;
197 : : cksum += m_hdr->fragment_offset;
198 : : cksum += 0xFFFF;
199 : : cksum += m_hdr->total_length;
200 : : cksum += (uint16_t)(~tot_len);
201 : : cksum = (cksum & 0xFFFF) + ((cksum & 0xFFFF0000) >> 16);
202 : : hdr->hdr_checksum = cksum;
203 : :
204 : : head->pkt_len = lcptr + *ihl + fragx_sum;
205 : : } else {
206 : : struct rte_ipv6_hdr *hdr = (struct rte_ipv6_hdr *)ipptr;
207 : : size_t ext_len = sizeof(struct rte_ipv6_hdr);
208 : : uint8_t *nxt_hdr = (uint8_t *)hdr;
209 : : uint8_t *nxt_proto = &hdr->proto;
210 : : int nh = hdr->proto;
211 : :
212 : : *ihl = 0;
213 : : tot_len = 0;
214 : : while (nh != -EINVAL) {
215 : : nxt_hdr += ext_len;
216 : : *ihl += ext_len;
217 : : if (nh == IPPROTO_FRAGMENT) {
218 : : *nxt_proto = *nxt_hdr;
219 : : tot_len = *ihl;
220 : : }
221 : : nh = rte_ipv6_get_next_ext(nxt_hdr, nh, &ext_len);
222 : : nxt_proto = nxt_hdr;
223 : : }
224 : :
225 : : /* Remove the frag header by moving header 8 bytes forward */
226 : : hdr->payload_len = rte_cpu_to_be_16(fragx_sum + *ihl -
227 : : 8 - sizeof(struct rte_ipv6_hdr));
228 : :
229 : : /* tot_len is sum of all IP header's length before fragment header */
230 : : rte_memcpy(rte_pktmbuf_mtod_offset(head, void *, 8),
231 : : rte_pktmbuf_mtod(head, void *),
232 : : lcptr + tot_len);
233 : :
234 : : head->data_len -= 8;
235 : : head->data_off += 8;
236 : : head->pkt_len = lcptr + *ihl - 8 + fragx_sum;
237 : : /* ihl l3hdr size value should be up to fragment header for next frags */
238 : : *ihl = tot_len + 8;
239 : : }
240 : : }
241 : :
242 : : #else
243 : : static __rte_always_inline uint64_t
244 : : nix_sec_reass_frags_get(const struct cpt_parse_hdr_s *hdr, struct rte_mbuf **next_mbufs)
245 : : {
246 : : RTE_SET_USED(hdr);
247 : 0 : next_mbufs[0] = NULL;
248 : 0 : next_mbufs[1] = NULL;
249 : 0 : next_mbufs[2] = NULL;
250 : : return 0;
251 : : }
252 : :
253 : : static __rte_always_inline void
254 : : nix_sec_reass_first_frag_update(struct rte_mbuf *head, const uint8_t *m_ipptr,
255 : : uint64_t fsz, uint64_t cq_w1, uint16_t *ihl)
256 : : {
257 : : RTE_SET_USED(head);
258 : : RTE_SET_USED(m_ipptr);
259 : : RTE_SET_USED(fsz);
260 : : RTE_SET_USED(cq_w1);
261 : : *ihl = 0;
262 : : }
263 : : #endif
264 : :
265 : : static struct rte_mbuf *
266 : : nix_sec_attach_frags(const struct cpt_parse_hdr_s *hdr,
267 : : struct rte_mbuf *head,
268 : : struct cn10k_inb_priv_data *inb_priv,
269 : : const uint64_t mbuf_init)
270 : : {
271 : : uint8_t num_frags = hdr->w0.num_frags;
272 : : struct rte_mbuf *next_mbufs[3];
273 : : union nix_rx_parse_u *frag_rx;
274 : : struct rte_mbuf *mbuf;
275 : : uint64_t ol_flags;
276 : : uint16_t frag_size;
277 : : uint8_t frag_i = 0;
278 : : uint16_t rlen;
279 : : uint64_t *wqe;
280 : : int off;
281 : :
282 : : off = inb_priv->reass_dynfield_off;
283 : : ol_flags = BIT_ULL(inb_priv->reass_dynflag_bit);
284 : : ol_flags |= RTE_MBUF_F_RX_SEC_OFFLOAD;
285 : :
286 : : /* Get frags list */
287 : : nix_sec_reass_frags_get(hdr, next_mbufs);
288 : :
289 : : /* Frag-0: */
290 : : wqe = (uint64_t *)(head + 1);
291 : : rlen = ((*(wqe + 10)) >> 16) & 0xFFFF;
292 : :
293 : : frag_rx = (union nix_rx_parse_u *)(wqe + 1);
294 : :
295 : : head->ol_flags = ol_flags;
296 : : /* Update dynamic field with userdata */
297 : : *rte_security_dynfield(head) = (uint64_t)inb_priv->userdata;
298 : :
299 : : num_frags--;
300 : : mbuf = head;
301 : :
302 : : /* Frag-1+: */
303 : : while (num_frags) {
304 : : cnxk_ip_reassembly_dynfield(mbuf, off)->next_frag = next_mbufs[frag_i];
305 : : cnxk_ip_reassembly_dynfield(mbuf, off)->nb_frags = num_frags;
306 : : mbuf = next_mbufs[frag_i];
307 : : wqe = (uint64_t *)(mbuf + 1);
308 : : rlen = ((*(wqe + 10)) >> 16) & 0xFFFF;
309 : :
310 : : frag_rx = (union nix_rx_parse_u *)(wqe + 1);
311 : : frag_size = rlen + frag_rx->lcptr - frag_rx->laptr;
312 : :
313 : : *(uint64_t *)(&mbuf->rearm_data) = mbuf_init;
314 : : mbuf->data_len = frag_size;
315 : : mbuf->pkt_len = frag_size;
316 : : mbuf->ol_flags = ol_flags;
317 : :
318 : : /* Update dynamic field with userdata */
319 : : *rte_security_dynfield(mbuf) = (uint64_t)inb_priv->userdata;
320 : :
321 : : /* Mark frag as get */
322 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
323 : :
324 : : num_frags--;
325 : : frag_i++;
326 : : }
327 : : cnxk_ip_reassembly_dynfield(mbuf, off)->nb_frags = 0;
328 : : cnxk_ip_reassembly_dynfield(mbuf, off)->next_frag = NULL;
329 : :
330 : : return head;
331 : : }
332 : :
333 : : static __rte_always_inline struct rte_mbuf *
334 : : nix_sec_reassemble_frags(const struct cpt_parse_hdr_s *hdr, struct rte_mbuf *head,
335 : : uint64_t cq_w1, uint64_t cq_w5, uint64_t mbuf_init)
336 : : {
337 : : uint8_t num_frags = hdr->w0.num_frags;
338 : : union nix_rx_parse_u *frag_rx;
339 : : struct rte_mbuf *next_mbufs[3];
340 : : uint16_t data_off, b_off;
341 : : const uint8_t *m_ipptr;
342 : : uint16_t l3_hdr_size;
343 : : struct rte_mbuf *mbuf;
344 : : uint16_t frag_size;
345 : : uint64_t fsz_w1;
346 : : uint64_t *wqe;
347 : :
348 : : /* Base data offset */
349 : : b_off = mbuf_init & 0xFFFFUL;
350 : : mbuf_init &= ~0xFFFFUL;
351 : :
352 : : /* Get list of all fragments and frag sizes */
353 : : fsz_w1 = nix_sec_reass_frags_get(hdr, next_mbufs);
354 : :
355 : : /* Frag-0: */
356 : : wqe = (uint64_t *)(head + 1);
357 : :
358 : : /* First fragment data len is already update by caller */
359 : : m_ipptr = ((const uint8_t *)hdr + ((cq_w5 >> 16) & 0xFF));
360 : : nix_sec_reass_first_frag_update(head, m_ipptr, fsz_w1, cq_w1, &l3_hdr_size);
361 : : fsz_w1 >>= 16;
362 : :
363 : : /* Frag-1: */
364 : : head->next = next_mbufs[0];
365 : : mbuf = next_mbufs[0];
366 : : wqe = (uint64_t *)(mbuf + 1);
367 : : frag_rx = (union nix_rx_parse_u *)(wqe + 1);
368 : : frag_size = fsz_w1 & 0xFFFF;
369 : : fsz_w1 >>= 16;
370 : :
371 : : data_off = b_off + frag_rx->lcptr + l3_hdr_size;
372 : : *(uint64_t *)(&mbuf->rearm_data) = mbuf_init | data_off;
373 : : mbuf->data_len = frag_size;
374 : :
375 : : /* Mark frag as get */
376 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
377 : :
378 : : /* Frag-2: */
379 : : if (num_frags > 2) {
380 : : mbuf->next = next_mbufs[1];
381 : : mbuf = next_mbufs[1];
382 : : wqe = (uint64_t *)(mbuf + 1);
383 : : frag_rx = (union nix_rx_parse_u *)(wqe + 1);
384 : : frag_size = fsz_w1 & 0xFFFF;
385 : : fsz_w1 >>= 16;
386 : :
387 : : data_off = b_off + frag_rx->lcptr + l3_hdr_size;
388 : : *(uint64_t *)(&mbuf->rearm_data) = mbuf_init | data_off;
389 : : mbuf->data_len = frag_size;
390 : :
391 : : /* Mark frag as get */
392 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
393 : : }
394 : :
395 : : /* Frag-3: */
396 : : if (num_frags > 3) {
397 : : mbuf->next = next_mbufs[2];
398 : : mbuf = next_mbufs[2];
399 : : wqe = (uint64_t *)(mbuf + 1);
400 : : frag_rx = (union nix_rx_parse_u *)(wqe + 1);
401 : : frag_size = fsz_w1 & 0xFFFF;
402 : : fsz_w1 >>= 16;
403 : :
404 : : data_off = b_off + frag_rx->lcptr + l3_hdr_size;
405 : : *(uint64_t *)(&mbuf->rearm_data) = mbuf_init | data_off;
406 : : mbuf->data_len = frag_size;
407 : :
408 : : /* Mark frag as get */
409 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
410 : : }
411 : :
412 : : head->nb_segs = num_frags;
413 : : return head;
414 : : }
415 : :
416 : : static inline struct rte_mbuf *
417 : 0 : nix_sec_oop_process(const struct cpt_parse_hdr_s *hdr, struct rte_mbuf *mbuf, uint64_t *mbuf_init)
418 : : {
419 [ # # ]: 0 : uintptr_t wqe = rte_be_to_cpu_64(hdr->wqe_ptr);
420 : : union nix_rx_parse_u *inner_rx;
421 : : struct rte_mbuf *inner;
422 : : uint16_t data_off;
423 : :
424 : 0 : inner = ((struct rte_mbuf *)wqe) - 1;
425 : :
426 : 0 : inner_rx = (union nix_rx_parse_u *)(wqe + 8);
427 : 0 : inner->pkt_len = inner_rx->pkt_lenm1 + 1;
428 : 0 : inner->data_len = inner_rx->pkt_lenm1 + 1;
429 : :
430 : : /* Mark inner mbuf as get */
431 : : RTE_MEMPOOL_CHECK_COOKIES(inner->pool,
432 : : (void **)&inner, 1, 1);
433 : : /* Update rearm data for full mbuf as it has
434 : : * cpt parse header that needs to be skipped.
435 : : *
436 : : * Since meta pool will not have private area while
437 : : * ethdev RQ's first skip would be considering private area
438 : : * calculate actual data off and update in meta mbuf.
439 : : */
440 : 0 : data_off = (uintptr_t)hdr - (uintptr_t)mbuf->buf_addr;
441 : 0 : data_off += sizeof(struct cpt_parse_hdr_s);
442 : 0 : data_off += hdr->w0.pad_len;
443 : 0 : *mbuf_init &= ~0xFFFFUL;
444 : 0 : *mbuf_init |= (uint64_t)data_off;
445 : :
446 : 0 : *rte_security_oop_dynfield(mbuf) = inner;
447 : : /* Return outer instead of inner mbuf as inner mbuf would have original encrypted packet */
448 : 0 : return mbuf;
449 : : }
450 : :
451 : : static __rte_always_inline struct rte_mbuf *
452 : : nix_sec_meta_to_mbuf_sc(uint64_t cq_w1, uint64_t cq_w5, const uint64_t sa_base,
453 : : uintptr_t laddr, uint8_t *loff, struct rte_mbuf *mbuf,
454 : : uint16_t data_off, const uint16_t flags,
455 : : uint64_t mbuf_init)
456 : : {
457 : 0 : const void *__p = (void *)((uintptr_t)mbuf + (uint16_t)data_off);
458 : : const struct cpt_parse_hdr_s *hdr = (const struct cpt_parse_hdr_s *)__p;
459 : : struct cn10k_inb_priv_data *inb_priv;
460 : : struct rte_mbuf *inner = NULL;
461 : : uint32_t sa_idx;
462 : : uint16_t ucc;
463 : : uint32_t len;
464 : : uintptr_t ip;
465 : : void *inb_sa;
466 : : uint64_t w0;
467 : :
468 [ # # # # : 0 : if (!(cq_w1 & BIT(11)))
# # # # #
# # # ]
469 : : return mbuf;
470 : :
471 [ # # # # : 0 : if (flags & NIX_RX_REAS_F && hdr->w0.pkt_fmt == ROC_IE_OT_SA_PKT_FMT_FULL) {
# # # # #
# # # ]
472 : 0 : inner = nix_sec_oop_process(hdr, mbuf, &mbuf_init);
473 : : } else {
474 [ # # # # : 0 : inner = (struct rte_mbuf *)(rte_be_to_cpu_64(hdr->wqe_ptr) -
# # # # #
# # # ]
475 : : sizeof(struct rte_mbuf));
476 : :
477 : : /* Store meta in lmtline to free
478 : : * Assume all meta's from same aura.
479 : : */
480 : 0 : *(uint64_t *)(laddr + (*loff << 3)) = (uint64_t)mbuf;
481 : 0 : *loff = *loff + 1;
482 : : }
483 : :
484 : : /* Get SPI from CPT_PARSE_S's cookie(already swapped) */
485 : 0 : w0 = hdr->w0.u64;
486 [ # # # # : 0 : sa_idx = w0 >> 32;
# # # # #
# # # ]
487 : :
488 : : inb_sa = roc_nix_inl_ot_ipsec_inb_sa(sa_base, sa_idx);
489 : : inb_priv = roc_nix_inl_ot_ipsec_inb_sa_sw_rsvd(inb_sa);
490 : :
491 : : /* Cryptodev injected packet can be identified from SA IDX 0xFFFFFFFF, and
492 : : * Ethdev injected packet can be identified with match ID 0xFFFF.
493 : : */
494 [ # # # # : 0 : if (flags & NIX_RX_REAS_F && (sa_idx == 0xFFFFFFFF || hdr->w0.match_id == 0xFFFFU)) {
# # # # #
# # # # #
# # # # #
# # # #
# ]
495 : 0 : *(uint64_t *)(&inner->rearm_data) = (mbuf_init & ~(BIT_ULL(16) - 1)) |
496 : 0 : inner->data_off;
497 [ # # # # : 0 : if (hdr->w0.match_id == 0xFFFFU)
# # # # #
# # # ]
498 : 0 : *rte_security_dynfield(inner) = (uint64_t)inb_priv->userdata;
499 : : } else {
500 : : /* Update dynamic field with userdata */
501 : 0 : *rte_security_dynfield(inner) = (uint64_t)inb_priv->userdata;
502 : 0 : *(uint64_t *)(&inner->rearm_data) = mbuf_init;
503 : : }
504 : :
505 : : /* Get ucc from cpt parse header */
506 : 0 : ucc = hdr->w3.hw_ccode;
507 : :
508 : : /* Calculate inner packet length as IP total len + l2 len */
509 : 0 : ip = (uintptr_t)hdr + ((cq_w5 >> 16) & 0xFF);
510 : 0 : ip += ((cq_w1 >> 40) & 0x6);
511 [ # # # # : 0 : len = rte_be_to_cpu_16(*(uint16_t *)ip);
# # # # #
# # # ]
512 : 0 : len += ((cq_w5 >> 16) & 0xFF) - (cq_w5 & 0xFF);
513 [ # # # # : 0 : len += (cq_w1 & BIT(42)) ? 40 : 0;
# # # # #
# # # ]
514 : :
515 : 0 : inner->pkt_len = len;
516 : 0 : inner->data_len = len;
517 : :
518 : 0 : inner->ol_flags = ((CPT_COMP_HWGOOD_MASK & (1U << ucc)) ?
519 [ # # # # : 0 : RTE_MBUF_F_RX_SEC_OFFLOAD :
# # # # #
# # # ]
520 : : (RTE_MBUF_F_RX_SEC_OFFLOAD |
521 : : RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED));
522 : :
523 : 0 : ucc = hdr->w3.uc_ccode;
524 : :
525 [ # # # # : 0 : if (ucc && ucc < 0xED) {
# # # # #
# # # ]
526 : 0 : inner->ol_flags |= RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED;
527 : : } else {
528 : 0 : ucc += 3; /* To make codes in 0xFx series except 0 */
529 : 0 : inner->ol_flags |= ((ucc & 0xF0) == 0xF0) ?
530 : 0 : ((NIX_RX_SEC_UCC_CONST >> ((ucc & 0xF) << 3))
531 [ # # # # : 0 : & 0xFF) << 1 : RTE_MBUF_F_RX_IP_CKSUM_GOOD;
# # # # #
# # # ]
532 : : }
533 : :
534 : : if (!(flags & NIX_RX_REAS_F) || hdr->w0.pkt_fmt != ROC_IE_OT_SA_PKT_FMT_FULL) {
535 : : /* Mark meta mbuf as put */
536 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 0);
537 : :
538 : : /* Mark inner mbuf as get */
539 : : RTE_MEMPOOL_CHECK_COOKIES(inner->pool, (void **)&inner, 1, 1);
540 : : }
541 : :
542 : : /* Skip reassembly processing when multi-seg is enabled */
543 : : if (!(flags & NIX_RX_MULTI_SEG_F) && (flags & NIX_RX_REAS_F) && hdr->w0.num_frags) {
544 : : if ((!(hdr->w0.err_sum) || roc_ie_ot_ucc_is_success(hdr->w3.uc_ccode)) &&
545 : : !(hdr->w0.reas_sts)) {
546 : : /* Reassembly success */
547 : : nix_sec_reassemble_frags(hdr, inner, cq_w1, cq_w5, mbuf_init);
548 : :
549 : : /* Update dynamic field with userdata */
550 : : *rte_security_dynfield(inner) =
551 : : (uint64_t)inb_priv->userdata;
552 : :
553 : : /* Assume success */
554 : : inner->ol_flags = RTE_MBUF_F_RX_SEC_OFFLOAD;
555 : : } else {
556 : : /* Reassembly failure */
557 : : nix_sec_attach_frags(hdr, inner, inb_priv, mbuf_init);
558 : : }
559 : : }
560 : : return inner;
561 : : }
562 : :
563 : : #if defined(RTE_ARCH_ARM64)
564 : :
565 : : static __rte_always_inline void
566 : : nix_sec_meta_to_mbuf(uint64_t cq_w1, uint64_t cq_w5, uintptr_t inb_sa,
567 : : uintptr_t cpth, struct rte_mbuf *inner,
568 : : uint8x16_t *rx_desc_field1, uint64_t *ol_flags,
569 : : const uint16_t flags, uint64x2_t *rearm)
570 : : {
571 : : const struct cpt_parse_hdr_s *hdr =
572 : : (const struct cpt_parse_hdr_s *)cpth;
573 : : uint64_t mbuf_init = vgetq_lane_u64(*rearm, 0);
574 : : struct cn10k_inb_priv_data *inb_priv;
575 : : uintptr_t p;
576 : :
577 : : /* Clear checksum flags */
578 : : *ol_flags &= ~(RTE_MBUF_F_RX_L4_CKSUM_MASK |
579 : : RTE_MBUF_F_RX_IP_CKSUM_MASK);
580 : :
581 : :
582 : : if (flags & NIX_RX_REAS_F && !inb_sa) {
583 : : /* Clear and update original lower 16 bit of data offset */
584 : : *rearm = (*rearm & ~(BIT_ULL(16) - 1)) | inner->data_off;
585 : : } else {
586 : : /* Get SPI from CPT_PARSE_S's cookie(already swapped) */
587 : : inb_priv = roc_nix_inl_ot_ipsec_inb_sa_sw_rsvd((void *)inb_sa);
588 : : /* Update dynamic field with userdata */
589 : : *rte_security_dynfield(inner) = (uint64_t)inb_priv->userdata;
590 : : }
591 : :
592 : : /* Clear and update original lower 16 bit of data offset */
593 : : if (flags & NIX_RX_REAS_F && hdr->w0.match_id == 0xFFFFU)
594 : : *rearm = (*rearm & ~(BIT_ULL(16) - 1)) | inner->data_off;
595 : :
596 : : /* Mark inner mbuf as get */
597 : : if (!(flags & NIX_RX_REAS_F) ||
598 : : hdr->w0.pkt_fmt != ROC_IE_OT_SA_PKT_FMT_FULL)
599 : : RTE_MEMPOOL_CHECK_COOKIES(inner->pool, (void **)&inner, 1, 1);
600 : :
601 : : if (!(flags & NIX_RX_MULTI_SEG_F) && flags & NIX_RX_REAS_F && hdr->w0.num_frags) {
602 : : if ((!(hdr->w0.err_sum) || roc_ie_ot_ucc_is_success(hdr->w3.uc_ccode)) &&
603 : : !(hdr->w0.reas_sts)) {
604 : : /* First frag len */
605 : : inner->pkt_len = vgetq_lane_u16(*rx_desc_field1, 2);
606 : : inner->data_len = vgetq_lane_u16(*rx_desc_field1, 4);
607 : : p = (uintptr_t)&inner->rearm_data;
608 : : *(uint64_t *)p = mbuf_init;
609 : :
610 : : /* Reassembly success */
611 : : nix_sec_reassemble_frags(hdr, inner, cq_w1, cq_w5, mbuf_init);
612 : :
613 : : /* Assume success */
614 : : *ol_flags |= RTE_MBUF_F_RX_SEC_OFFLOAD;
615 : :
616 : : /* Update pkt_len and data_len */
617 : : *rx_desc_field1 = vsetq_lane_u16(inner->pkt_len,
618 : : *rx_desc_field1, 2);
619 : : *rx_desc_field1 = vsetq_lane_u16(inner->data_len,
620 : : *rx_desc_field1, 4);
621 : :
622 : : /* Data offset might be updated */
623 : : mbuf_init = *(uint64_t *)p;
624 : : *rearm = vsetq_lane_u64(mbuf_init, *rearm, 0);
625 : : } else {
626 : : /* Reassembly failure */
627 : : if (inb_sa) {
628 : : nix_sec_attach_frags(hdr, inner, inb_priv, mbuf_init);
629 : : *ol_flags |= inner->ol_flags;
630 : : }
631 : : }
632 : : } else if (flags & NIX_RX_REAS_F) {
633 : : /* Without fragmentation but may have to handle OOP session */
634 : : if (hdr->w0.pkt_fmt == ROC_IE_OT_SA_PKT_FMT_FULL) {
635 : : uint64_t mbuf_init = 0;
636 : :
637 : : /* Caller has already prepared to return second pass
638 : : * mbuf and inner mbuf is actually outer.
639 : : * Store original buffer pointer in dynfield.
640 : : */
641 : : nix_sec_oop_process(hdr, inner, &mbuf_init);
642 : : /* Clear and update lower 16 bit of data offset */
643 : : *rearm = (*rearm & ~(BIT_ULL(16) - 1)) | mbuf_init;
644 : : }
645 : : }
646 : : }
647 : : #endif
648 : :
649 : : static __rte_always_inline uint32_t
650 : : nix_ptype_get(const void *const lookup_mem, const uint64_t in)
651 : : {
652 : : const uint16_t *const ptype = lookup_mem;
653 : 0 : const uint16_t lh_lg_lf = (in & 0xFFF0000000000000) >> 52;
654 : 0 : const uint16_t tu_l2 = ptype[(in & 0x000FFFF000000000) >> 36];
655 : 0 : const uint16_t il4_tu = ptype[PTYPE_NON_TUNNEL_ARRAY_SZ + lh_lg_lf];
656 : :
657 : 0 : return (il4_tu << PTYPE_NON_TUNNEL_WIDTH) | tu_l2;
658 : : }
659 : :
660 : : static __rte_always_inline uint32_t
661 : : nix_rx_olflags_get(const void *const lookup_mem, const uint64_t in)
662 : : {
663 : : const uint32_t *const ol_flags =
664 : : (const uint32_t *)((const uint8_t *)lookup_mem +
665 : : PTYPE_ARRAY_SZ);
666 : :
667 : 0 : return ol_flags[(in & 0xfff00000) >> 20];
668 : : }
669 : :
670 : : static inline uint64_t
671 : 0 : nix_update_match_id(const uint16_t match_id, uint64_t ol_flags,
672 : : struct rte_mbuf *mbuf)
673 : : {
674 : : /* There is no separate bit to check match_id
675 : : * is valid or not? and no flag to identify it is an
676 : : * RTE_FLOW_ACTION_TYPE_FLAG vs RTE_FLOW_ACTION_TYPE_MARK
677 : : * action. The former case addressed through 0 being invalid
678 : : * value and inc/dec match_id pair when MARK is activated.
679 : : * The later case addressed through defining
680 : : * CNXK_FLOW_MARK_DEFAULT as value for
681 : : * RTE_FLOW_ACTION_TYPE_MARK.
682 : : * This would translate to not use
683 : : * CNXK_FLOW_ACTION_FLAG_DEFAULT - 1 and
684 : : * CNXK_FLOW_ACTION_FLAG_DEFAULT for match_id.
685 : : * i.e valid mark_id's are from
686 : : * 0 to CNXK_FLOW_ACTION_FLAG_DEFAULT - 2
687 : : */
688 [ # # ]: 0 : if (likely(match_id)) {
689 : 0 : ol_flags |= RTE_MBUF_F_RX_FDIR;
690 [ # # ]: 0 : if (match_id != CNXK_FLOW_ACTION_FLAG_DEFAULT) {
691 : 0 : ol_flags |= RTE_MBUF_F_RX_FDIR_ID;
692 : 0 : mbuf->hash.fdir.hi = match_id - 1;
693 : : }
694 : : }
695 : :
696 : 0 : return ol_flags;
697 : : }
698 : :
699 : : static __rte_always_inline void
700 : : nix_cqe_xtract_mseg(const union nix_rx_parse_u *rx, struct rte_mbuf *mbuf,
701 : : uint64_t rearm, uintptr_t cpth, uintptr_t sa_base, const uint16_t flags)
702 : : {
703 : : const struct cpt_parse_hdr_s *hdr = (const struct cpt_parse_hdr_s *)cpth;
704 : : struct cn10k_inb_priv_data *inb_priv = NULL;
705 : : uint8_t num_frags = 0, frag_i = 0;
706 : : struct rte_mbuf *next_mbufs[3];
707 : : const rte_iova_t *iova_list;
708 : : bool reas_success = false;
709 : : uint16_t later_skip = 0;
710 : : struct rte_mbuf *head;
711 : : const rte_iova_t *eol;
712 : : bool rx_inj = false;
713 : : uint64_t cq_w5 = 0;
714 : : uint16_t ihl = 0;
715 : : uint64_t fsz = 0;
716 : : int dyn_off = 0;
717 : : uint8_t nb_segs;
718 : : uint16_t sg_len;
719 : : uint64_t cq_w1;
720 : : int64_t len;
721 : : uint64_t sg;
722 : : uintptr_t p;
723 : :
724 : 0 : cq_w1 = *(const uint64_t *)rx;
725 : : if (flags & NIX_RX_REAS_F)
726 : : cq_w5 = *((const uint64_t *)rx + 4);
727 : : /* Use inner rx parse for meta pkts sg list */
728 [ # # # # : 0 : if (cq_w1 & BIT(11) && flags & NIX_RX_OFFLOAD_SECURITY_F) {
# # # # #
# # # ]
729 : : const uint64_t *wqe;
730 : : /* Rx Inject packet must have Match ID 0xFFFF and for this
731 : : * wqe will get from address stored at mbuf+1 location
732 : : */
733 [ # # # # : 0 : rx_inj = ((flags & NIX_RX_REAS_F) && ((hdr->w0.match_id == 0xFFFFU) ||
# # # # #
# # # ]
734 [ # # # # : 0 : (hdr->w0.cookie == 0xFFFFFFFFU)));
# # # # #
# # # ]
735 [ # # # # : 0 : if (rx_inj)
# # # # #
# # # ]
736 : 0 : wqe = (const uint64_t *)*((uint64_t *)(mbuf + 1));
737 : : else
738 : 0 : wqe = (const uint64_t *)(mbuf + 1);
739 : :
740 [ # # # # : 0 : if (!(flags & NIX_RX_REAS_F) || hdr->w0.pkt_fmt != ROC_IE_OT_SA_PKT_FMT_FULL)
# # # # #
# # # ]
741 : 0 : rx = (const union nix_rx_parse_u *)(wqe + 1);
742 : : }
743 : :
744 : 0 : sg = *(const uint64_t *)(rx + 1);
745 : 0 : nb_segs = (sg >> 48) & 0x3;
746 : :
747 : : if (nb_segs == 1 && !(flags & NIX_RX_REAS_F))
748 : : return;
749 : :
750 : : /* For security we have already updated right pkt_len */
751 [ # # # # : 0 : if (cq_w1 & BIT(11) && flags & NIX_RX_OFFLOAD_SECURITY_F) {
# # # # #
# # # ]
752 : 0 : len = mbuf->pkt_len;
753 : :
754 : : /* Handle reassembly with multi segs */
755 [ # # # # : 0 : if (flags & NIX_RX_REAS_F && hdr->w0.num_frags) {
# # # # #
# # # ]
756 : : void *inb_sa;
757 : :
758 : 0 : num_frags = hdr->w0.num_frags;
759 [ # # # # : 0 : inb_sa = roc_nix_inl_ot_ipsec_inb_sa(sa_base, hdr->w0.u64 >> 32);
# # # # #
# # # ]
760 : : inb_priv = roc_nix_inl_ot_ipsec_inb_sa_sw_rsvd(inb_sa);
761 : : ihl = 0;
762 : :
763 : 0 : dyn_off = inb_priv->reass_dynfield_off;
764 : : fsz = nix_sec_reass_frags_get(hdr, next_mbufs);
765 : 0 : num_frags -= 1;
766 : :
767 [ # # # # : 0 : if (!(hdr->w0.reas_sts) &&
# # # # #
# # # ]
768 [ # # # # : 0 : (!(hdr->w0.err_sum) ||
# # # # #
# # # # #
# # # # #
# # # #
# ]
769 [ # # # # : 0 : roc_ie_ot_ucc_is_success(hdr->w3.uc_ccode)))
# # # # #
# # # ]
770 : : reas_success = true;
771 : : }
772 : : } else {
773 : 0 : len = rx->pkt_lenm1 + 1;
774 : : }
775 : :
776 : 0 : mbuf->pkt_len = len - (flags & NIX_RX_OFFLOAD_TSTAMP_F ? CNXK_NIX_TIMESYNC_RX_OFFSET : 0);
777 : 0 : mbuf->nb_segs = nb_segs;
778 : : head = mbuf;
779 : 0 : mbuf->data_len =
780 : 0 : (sg & 0xFFFF) - (flags & NIX_RX_OFFLOAD_TSTAMP_F ? CNXK_NIX_TIMESYNC_RX_OFFSET : 0);
781 : 0 : eol = ((const rte_iova_t *)(rx + 1) + ((rx->desc_sizem1 + 1) << 1));
782 : : again:
783 : 0 : len -= mbuf->data_len;
784 : 0 : sg = sg >> 16;
785 : : /* Skip SG_S and first IOVA*/
786 : 0 : iova_list = ((const rte_iova_t *)(rx + 1)) + 2;
787 : 0 : nb_segs--;
788 : :
789 : 0 : later_skip = (uintptr_t)mbuf->buf_addr - (uintptr_t)mbuf;
790 : :
791 [ # # # # : 0 : while (nb_segs) {
# # # # #
# # # ]
792 [ # # # # : 0 : if (!(flags & NIX_RX_REAS_F) || !rx_inj)
# # # # #
# # # ]
793 : 0 : mbuf->next = (struct rte_mbuf *)(*iova_list - later_skip);
794 : 0 : mbuf = mbuf->next;
795 : :
796 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
797 : :
798 : 0 : sg_len = sg & 0XFFFF;
799 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
800 : : /* Adjust last mbuf data length with negative offset for
801 : : * security pkts if needed.
802 : : */
803 : 0 : len -= sg_len;
804 [ # # # # : 0 : sg_len = (len > 0) ? sg_len : (sg_len + len);
# # # # #
# # # ]
805 : 0 : len = (len > 0) ? len : 0;
806 : : }
807 : :
808 : 0 : mbuf->data_len = sg_len;
809 : 0 : sg = sg >> 16;
810 : : p = (uintptr_t)&mbuf->rearm_data;
811 [ # # # # : 0 : if (!(flags & NIX_RX_REAS_F) || !rx_inj)
# # # # #
# # # ]
812 : 0 : *(uint64_t *)p = rearm & ~0xFFFF;
813 : 0 : nb_segs--;
814 : 0 : iova_list++;
815 : :
816 [ # # # # : 0 : if (!nb_segs && (iova_list + 1 < eol)) {
# # # # #
# # # # #
# # # # #
# # # #
# ]
817 : 0 : sg = *(const uint64_t *)(iova_list);
818 : 0 : nb_segs = (sg >> 48) & 0x3;
819 : 0 : head->nb_segs += nb_segs;
820 : : iova_list = (const rte_iova_t *)(iova_list + 1);
821 : : }
822 : : }
823 : :
824 [ # # # # : 0 : if ((flags & NIX_RX_REAS_F) && (cq_w1 & BIT(11)) && num_frags) {
# # # # #
# # # # #
# # # # #
# # # #
# ]
825 : 0 : struct rte_mbuf *next_frag = next_mbufs[frag_i];
826 : : uint16_t lcptr, ldptr = 0;
827 : :
828 : 0 : rx = (const union nix_rx_parse_u *)((uintptr_t)(next_frag + 1) + 8);
829 : 0 : lcptr = (*((const uint64_t *)rx + 4) >> 16) & 0xFF;
830 : 0 : eol = ((const rte_iova_t *)(rx + 1) + ((rx->desc_sizem1 + 1) << 1));
831 : 0 : sg = *(const uint64_t *)(rx + 1);
832 : 0 : nb_segs = (sg >> 48) & 0x3;
833 : :
834 [ # # # # : 0 : if (reas_success) {
# # # # #
# # # ]
835 : : /* Update first fragment info */
836 : : if (!frag_i) {
837 : : const uint8_t *ipptr;
838 : :
839 : : ipptr = ((const uint8_t *)hdr + ((cq_w5 >> 16) & 0xFF));
840 : : nix_sec_reass_first_frag_update(head, ipptr, fsz, cq_w1, &ihl);
841 : : fsz >>= 16;
842 : : }
843 : 0 : mbuf->next = next_frag;
844 : 0 : head->nb_segs += nb_segs;
845 : : len = fsz & 0xFFFF;
846 : : fsz >>= 16;
847 : : ldptr = ihl + lcptr;
848 : : } else {
849 : 0 : len = ((eol[0] >> 16) & 0xFFFF) + lcptr;
850 : 0 : head->ol_flags |= BIT_ULL(inb_priv->reass_dynflag_bit) |
851 : : RTE_MBUF_F_RX_SEC_OFFLOAD;
852 : 0 : cnxk_ip_reassembly_dynfield(head, dyn_off)->next_frag = next_frag;
853 : 0 : cnxk_ip_reassembly_dynfield(head, dyn_off)->nb_frags = num_frags;
854 : : /* Update dynamic field with userdata from prev head */
855 : 0 : *rte_security_dynfield(next_frag) = *rte_security_dynfield(head);
856 : : head = next_frag;
857 : 0 : head->pkt_len = len - (flags & NIX_RX_OFFLOAD_TSTAMP_F ?
858 : : CNXK_NIX_TIMESYNC_RX_OFFSET : 0);
859 : : head->nb_segs = nb_segs;
860 : : }
861 : : mbuf = next_frag;
862 : : p = (uintptr_t)&mbuf->rearm_data;
863 : 0 : *(uint64_t *)p = rearm + ldptr;
864 : 0 : mbuf->data_len = (sg & 0xFFFF) - ldptr -
865 : : (flags & NIX_RX_OFFLOAD_TSTAMP_F ?
866 : : CNXK_NIX_TIMESYNC_RX_OFFSET : 0);
867 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
868 : 0 : num_frags--;
869 : 0 : frag_i++;
870 : 0 : goto again;
871 [ # # # # : 0 : } else if ((flags & NIX_RX_REAS_F) && (cq_w1 & BIT(11)) && !reas_success &&
# # # # #
# # # # #
# # # # #
# # # #
# ]
872 [ # # # # : 0 : hdr->w0.pkt_fmt == ROC_IE_OT_SA_PKT_FMT_FULL) {
# # # # #
# # # ]
873 [ # # # # : 0 : uintptr_t wqe = rte_be_to_cpu_64(hdr->wqe_ptr);
# # # # #
# # # ]
874 : :
875 : : /* Process OOP packet inner buffer mseg. reas_success flag is used here only
876 : : * to avoid looping.
877 : : */
878 : 0 : mbuf = ((struct rte_mbuf *)wqe) - 1;
879 : 0 : rx = (const union nix_rx_parse_u *)(wqe + 8);
880 : 0 : eol = ((const rte_iova_t *)(rx + 1) + ((rx->desc_sizem1 + 1) << 1));
881 : 0 : sg = *(const uint64_t *)(rx + 1);
882 : 0 : nb_segs = (sg >> 48) & 0x3;
883 : :
884 : :
885 : 0 : len = mbuf->pkt_len;
886 : : p = (uintptr_t)&mbuf->rearm_data;
887 : 0 : *(uint64_t *)p = rearm;
888 : 0 : mbuf->data_len = (sg & 0xFFFF) -
889 : : (flags & NIX_RX_OFFLOAD_TSTAMP_F ?
890 : : CNXK_NIX_TIMESYNC_RX_OFFSET : 0);
891 : : head = mbuf;
892 : 0 : head->nb_segs = nb_segs;
893 : : /* Using this flag to avoid looping in case of OOP */
894 : : reas_success = true;
895 : 0 : goto again;
896 : : }
897 : :
898 : : /* Update for last failure fragment */
899 [ # # # # : 0 : if ((flags & NIX_RX_REAS_F) && frag_i && !reas_success) {
# # # # #
# # # ]
900 : 0 : cnxk_ip_reassembly_dynfield(head, dyn_off)->next_frag = NULL;
901 : 0 : cnxk_ip_reassembly_dynfield(head, dyn_off)->nb_frags = 0;
902 : : }
903 : : }
904 : :
905 : : static __rte_always_inline void
906 : : cn10k_nix_cqe_to_mbuf(const struct nix_cqe_hdr_s *cq, const uint32_t tag,
907 : : struct rte_mbuf *mbuf, const void *lookup_mem,
908 : : const uint64_t val, const uintptr_t cpth, const uintptr_t sa_base,
909 : : const uint16_t flag)
910 : : {
911 : 0 : const union nix_rx_parse_u *rx =
912 : : (const union nix_rx_parse_u *)((const uint64_t *)cq + 1);
913 : 0 : const uint64_t w1 = *(const uint64_t *)rx;
914 : 0 : uint16_t len = rx->pkt_lenm1 + 1;
915 : : uint64_t ol_flags = 0;
916 : : uintptr_t p;
917 : :
918 : : if (flag & NIX_RX_OFFLOAD_PTYPE_F)
919 : 0 : mbuf->packet_type = nix_ptype_get(lookup_mem, w1);
920 : : else
921 : : mbuf->packet_type = 0;
922 : :
923 : : if (flag & NIX_RX_OFFLOAD_RSS_F) {
924 : 0 : mbuf->hash.rss = tag;
925 : : ol_flags |= RTE_MBUF_F_RX_RSS_HASH;
926 : : }
927 : :
928 : : /* Skip rx ol flags extraction for Security packets */
929 [ # # # # : 0 : if ((!(flag & NIX_RX_SEC_REASSEMBLY_F) || !(w1 & BIT(11))) &&
# # # # #
# # # ]
930 : : flag & NIX_RX_OFFLOAD_CHECKSUM_F)
931 : 0 : ol_flags |= (uint64_t)nix_rx_olflags_get(lookup_mem, w1);
932 : :
933 : : if (flag & NIX_RX_OFFLOAD_VLAN_STRIP_F) {
934 [ # # # # : 0 : if (rx->vtag0_gone) {
# # # # #
# # # ]
935 : 0 : ol_flags |= RTE_MBUF_F_RX_VLAN | RTE_MBUF_F_RX_VLAN_STRIPPED;
936 : 0 : mbuf->vlan_tci = rx->vtag0_tci;
937 : : }
938 [ # # # # : 0 : if (rx->vtag1_gone) {
# # # # #
# # # ]
939 : 0 : ol_flags |= RTE_MBUF_F_RX_QINQ | RTE_MBUF_F_RX_QINQ_STRIPPED;
940 : 0 : mbuf->vlan_tci_outer = rx->vtag1_tci;
941 : : }
942 : : }
943 : :
944 : : if (flag & NIX_RX_OFFLOAD_MARK_UPDATE_F)
945 : 0 : ol_flags = nix_update_match_id(rx->match_id, ol_flags, mbuf);
946 : :
947 : : /* Packet data length and ol flags is already updated for sec */
948 [ # # # # : 0 : if (flag & NIX_RX_SEC_REASSEMBLY_F && w1 & BIT_ULL(11)) {
# # # # #
# # # ]
949 : 0 : mbuf->ol_flags |= ol_flags;
950 : : } else {
951 : 0 : mbuf->ol_flags = ol_flags;
952 : 0 : mbuf->pkt_len = len;
953 : 0 : mbuf->data_len = len;
954 : : p = (uintptr_t)&mbuf->rearm_data;
955 : 0 : *(uint64_t *)p = val;
956 : : }
957 : :
958 : : if (flag & NIX_RX_MULTI_SEG_F)
959 : : /*
960 : : * For multi segment packets, mbuf length correction according
961 : : * to Rx timestamp length will be handled later during
962 : : * timestamp data process.
963 : : * Hence, timestamp flag argument is not required.
964 : : */
965 : : nix_cqe_xtract_mseg(rx, mbuf, val, cpth, sa_base, flag & ~NIX_RX_OFFLOAD_TSTAMP_F);
966 : : }
967 : :
968 : : static inline uint16_t
969 : : nix_rx_nb_pkts(struct cn10k_eth_rxq *rxq, const uint64_t wdata,
970 : : const uint16_t pkts, const uint32_t qmask)
971 : : {
972 : : uint32_t available = rxq->available;
973 : :
974 : : /* Update the available count if cached value is not enough */
975 : : if (unlikely(available < pkts)) {
976 : : uint64_t reg, head, tail;
977 : :
978 : : /* Use LDADDA version to avoid reorder */
979 : : reg = roc_atomic64_add_sync(wdata, rxq->cq_status);
980 : : /* CQ_OP_STATUS operation error */
981 : : if (reg & BIT_ULL(NIX_CQ_OP_STAT_OP_ERR) ||
982 : : reg & BIT_ULL(NIX_CQ_OP_STAT_CQ_ERR))
983 : : return 0;
984 : :
985 : : tail = reg & 0xFFFFF;
986 : : head = (reg >> 20) & 0xFFFFF;
987 : : if (tail < head)
988 : : available = tail - head + qmask + 1;
989 : : else
990 : : available = tail - head;
991 : :
992 : : rxq->available = available;
993 : : }
994 : :
995 : : return RTE_MIN(pkts, available);
996 : : }
997 : :
998 : : static __rte_always_inline void
999 : : cn10k_nix_mbuf_to_tstamp(struct rte_mbuf *mbuf,
1000 : : struct cnxk_timesync_info *tstamp,
1001 : : const uint8_t ts_enable, uint64_t *tstamp_ptr)
1002 : : {
1003 : : if (ts_enable) {
1004 : 0 : mbuf->pkt_len -= CNXK_NIX_TIMESYNC_RX_OFFSET;
1005 : 0 : mbuf->data_len -= CNXK_NIX_TIMESYNC_RX_OFFSET;
1006 : :
1007 : : /* Reading the rx timestamp inserted by CGX, viz at
1008 : : * starting of the packet data.
1009 : : */
1010 : 0 : *tstamp_ptr = ((*tstamp_ptr >> 32) * NSEC_PER_SEC) +
1011 : 0 : (*tstamp_ptr & 0xFFFFFFFFUL);
1012 : 0 : *cnxk_nix_timestamp_dynfield(mbuf, tstamp) =
1013 [ # # ]: 0 : rte_be_to_cpu_64(*tstamp_ptr);
1014 : : /* RTE_MBUF_F_RX_IEEE1588_TMST flag needs to be set only in case
1015 : : * PTP packets are received.
1016 : : */
1017 [ # # ]: 0 : if (mbuf->packet_type == RTE_PTYPE_L2_ETHER_TIMESYNC) {
1018 : 0 : tstamp->rx_tstamp =
1019 : : *cnxk_nix_timestamp_dynfield(mbuf, tstamp);
1020 : 0 : tstamp->rx_ready = 1;
1021 : 0 : mbuf->ol_flags |= RTE_MBUF_F_RX_IEEE1588_PTP |
1022 : : RTE_MBUF_F_RX_IEEE1588_TMST |
1023 : 0 : tstamp->rx_tstamp_dynflag;
1024 : : }
1025 : : }
1026 : : }
1027 : :
1028 : : static __rte_always_inline uint16_t
1029 : : cn10k_nix_recv_pkts(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts,
1030 : : const uint16_t flags)
1031 : : {
1032 : : struct cn10k_eth_rxq *rxq = rx_queue;
1033 : : const uint64_t mbuf_init = rxq->mbuf_initializer;
1034 : : const void *lookup_mem = rxq->lookup_mem;
1035 : : const uint64_t data_off = rxq->data_off;
1036 : : struct rte_mempool *meta_pool = NULL;
1037 : : const uintptr_t desc = rxq->desc;
1038 : : const uint64_t wdata = rxq->wdata;
1039 : : const uint32_t qmask = rxq->qmask;
1040 : : uint64_t lbase = rxq->lmt_base;
1041 : : uint16_t packets = 0, nb_pkts;
1042 : : uint8_t loff = 0, lnum = 0;
1043 : : uint32_t head = rxq->head;
1044 : : struct nix_cqe_hdr_s *cq;
1045 : : struct rte_mbuf *mbuf;
1046 : : uint64_t aura_handle;
1047 : : uint64_t sa_base = 0;
1048 : : uintptr_t cpth = 0;
1049 : : uint16_t lmt_id;
1050 : : uint64_t laddr;
1051 : :
1052 : : nb_pkts = nix_rx_nb_pkts(rxq, wdata, pkts, qmask);
1053 : :
1054 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
1055 : : aura_handle = rxq->meta_aura;
1056 : : sa_base = rxq->sa_base;
1057 : : sa_base &= ~(ROC_NIX_INL_SA_BASE_ALIGN - 1);
1058 : : ROC_LMT_BASE_ID_GET(lbase, lmt_id);
1059 : : laddr = lbase;
1060 : : laddr += 8;
1061 : : if (flags & NIX_RX_REAS_F)
1062 : : meta_pool = (struct rte_mempool *)rxq->meta_pool;
1063 : : }
1064 : :
1065 : : while (packets < nb_pkts) {
1066 : : /* Prefetch N desc ahead */
1067 : : rte_prefetch_non_temporal(
1068 : : (void *)(desc + (CQE_SZ((head + 2) & qmask))));
1069 : : cq = (struct nix_cqe_hdr_s *)(desc + CQE_SZ(head));
1070 : :
1071 : : mbuf = nix_get_mbuf_from_cqe(cq, data_off);
1072 : :
1073 : : /* Mark mempool obj as "get" as it is alloc'ed by NIX */
1074 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
1075 : :
1076 : : /* Translate meta to mbuf */
1077 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
1078 : : const uint64_t cq_w1 = *((const uint64_t *)cq + 1);
1079 : : const uint64_t cq_w5 = *((const uint64_t *)cq + 5);
1080 : :
1081 : : cpth = ((uintptr_t)mbuf + (uint16_t)data_off);
1082 : :
1083 : : /* Update mempool pointer for full mode pkt */
1084 : : if ((flags & NIX_RX_REAS_F) && (cq_w1 & BIT(11)) &&
1085 : : !((*(uint64_t *)cpth) & BIT(15)))
1086 : : mbuf->pool = meta_pool;
1087 : :
1088 : : mbuf = nix_sec_meta_to_mbuf_sc(cq_w1, cq_w5, sa_base, laddr,
1089 : : &loff, mbuf, data_off,
1090 : : flags, mbuf_init);
1091 : : }
1092 : :
1093 : : cn10k_nix_cqe_to_mbuf(cq, cq->tag, mbuf, lookup_mem, mbuf_init,
1094 : : cpth, sa_base, flags);
1095 : : cn10k_nix_mbuf_to_tstamp(mbuf, rxq->tstamp,
1096 : : (flags & NIX_RX_OFFLOAD_TSTAMP_F),
1097 : : (uint64_t *)((uint8_t *)mbuf
1098 : : + data_off));
1099 : : rx_pkts[packets++] = mbuf;
1100 : : roc_prefetch_store_keep(mbuf);
1101 : : head++;
1102 : : head &= qmask;
1103 : :
1104 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
1105 : : /* Flush when we don't have space for 4 meta */
1106 : : if ((15 - loff) < 1) {
1107 : : nix_sec_flush_meta(laddr, lmt_id + lnum, loff,
1108 : : aura_handle);
1109 : : lnum++;
1110 : : lnum &= BIT_ULL(ROC_LMT_LINES_PER_CORE_LOG2) -
1111 : : 1;
1112 : : /* First pointer starts at 8B offset */
1113 : : laddr = (uintptr_t)LMT_OFF(lbase, lnum, 8);
1114 : : loff = 0;
1115 : : }
1116 : : }
1117 : : }
1118 : :
1119 : : rxq->head = head;
1120 : : rxq->available -= nb_pkts;
1121 : :
1122 : : /* Free all the CQs that we've processed */
1123 : : plt_write64((wdata | nb_pkts), rxq->cq_door);
1124 : :
1125 : : /* Free remaining meta buffers if any */
1126 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F && loff)
1127 : : nix_sec_flush_meta(laddr, lmt_id + lnum, loff, aura_handle);
1128 : :
1129 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F)
1130 : : rte_io_wmb();
1131 : :
1132 : : return nb_pkts;
1133 : : }
1134 : :
1135 : : static __rte_always_inline uint16_t
1136 : : cn10k_nix_flush_recv_pkts(void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts,
1137 : : const uint16_t flags)
1138 : : {
1139 : : struct cn10k_eth_rxq *rxq = rx_queue;
1140 : : const uint64_t mbuf_init = rxq->mbuf_initializer;
1141 : : const void *lookup_mem = rxq->lookup_mem;
1142 : : const uint64_t data_off = rxq->data_off;
1143 : : struct rte_mempool *meta_pool = NULL;
1144 : : const uint64_t wdata = rxq->wdata;
1145 : : const uint32_t qmask = rxq->qmask;
1146 : : const uintptr_t desc = rxq->desc;
1147 : : uint64_t lbase = rxq->lmt_base;
1148 : : uint16_t packets = 0, nb_pkts;
1149 : : uint16_t lmt_id __rte_unused;
1150 : : uint32_t head = rxq->head;
1151 : : struct nix_cqe_hdr_s *cq;
1152 : : struct rte_mbuf *mbuf;
1153 : : uint64_t sa_base = 0;
1154 : : uintptr_t cpth = 0;
1155 : : uint8_t loff = 0;
1156 : : uint64_t laddr;
1157 : :
1158 : : nb_pkts = nix_rx_nb_pkts(rxq, wdata, pkts, qmask);
1159 : :
1160 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
1161 : : sa_base = rxq->sa_base;
1162 : : sa_base &= ~(ROC_NIX_INL_SA_BASE_ALIGN - 1);
1163 : : ROC_LMT_BASE_ID_GET(lbase, lmt_id);
1164 : : laddr = lbase;
1165 : : laddr += 8;
1166 : : if (flags & NIX_RX_REAS_F)
1167 : : meta_pool = (struct rte_mempool *)rxq->meta_pool;
1168 : : }
1169 : :
1170 : : while (packets < nb_pkts) {
1171 : : /* Prefetch N desc ahead */
1172 : : rte_prefetch_non_temporal((void *)(desc + (CQE_SZ((head + 2) & qmask))));
1173 : : cq = (struct nix_cqe_hdr_s *)(desc + CQE_SZ(head));
1174 : :
1175 : : mbuf = nix_get_mbuf_from_cqe(cq, data_off);
1176 : :
1177 : : /* Mark mempool obj as "get" as it is alloc'ed by NIX */
1178 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf->pool, (void **)&mbuf, 1, 1);
1179 : :
1180 : : /* Translate meta to mbuf */
1181 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
1182 : : const uint64_t cq_w1 = *((const uint64_t *)cq + 1);
1183 : : const uint64_t cq_w5 = *((const uint64_t *)cq + 5);
1184 : : struct rte_mbuf *meta_buf = mbuf;
1185 : :
1186 : : cpth = ((uintptr_t)meta_buf + (uint16_t)data_off);
1187 : :
1188 : : /* Update mempool pointer for full mode pkt */
1189 : : if ((flags & NIX_RX_REAS_F) && (cq_w1 & BIT(11)) &&
1190 : : !((*(uint64_t *)cpth) & BIT(15)))
1191 : : meta_buf->pool = meta_pool;
1192 : :
1193 : : mbuf = nix_sec_meta_to_mbuf_sc(cq_w1, cq_w5, sa_base, laddr, &loff,
1194 : : meta_buf, data_off, flags, mbuf_init);
1195 : : /* Free Meta mbuf, not use LMT line for flush as this will be called
1196 : : * from non-datapath i.e. dev_stop case.
1197 : : */
1198 : : if (loff) {
1199 : : roc_npa_aura_op_free(meta_buf->pool->pool_id, 0,
1200 : : (uint64_t)meta_buf);
1201 : : loff = 0;
1202 : : }
1203 : : }
1204 : :
1205 : : cn10k_nix_cqe_to_mbuf(cq, cq->tag, mbuf, lookup_mem, mbuf_init,
1206 : : cpth, sa_base, flags);
1207 : : cn10k_nix_mbuf_to_tstamp(mbuf, rxq->tstamp,
1208 : : (flags & NIX_RX_OFFLOAD_TSTAMP_F),
1209 : : (uint64_t *)((uint8_t *)mbuf + data_off));
1210 : : rx_pkts[packets++] = mbuf;
1211 : : roc_prefetch_store_keep(mbuf);
1212 : : head++;
1213 : : head &= qmask;
1214 : : }
1215 : :
1216 : : rxq->head = head;
1217 : : rxq->available -= nb_pkts;
1218 : :
1219 : : /* Free all the CQs that we've processed */
1220 : : plt_write64((wdata | nb_pkts), rxq->cq_door);
1221 : :
1222 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F)
1223 : : rte_io_wmb();
1224 : :
1225 : : return nb_pkts;
1226 : : }
1227 : :
1228 : : #if defined(RTE_ARCH_ARM64)
1229 : : static __rte_always_inline uint16_t
1230 : : cn10k_nix_rx_inj_prepare_mseg(struct rte_mbuf *m, uint64_t *cmd)
1231 : : {
1232 : : union nix_send_sg_s *sg, l_sg;
1233 : : struct rte_mbuf *m_next;
1234 : : uint16_t segdw, nb_segs;
1235 : : uint64_t len, dlen;
1236 : : uint64_t *slist;
1237 : :
1238 : : sg = (union nix_send_sg_s *)cmd;
1239 : : l_sg.u = sg->u;
1240 : : l_sg.u &= 0xC00000000000000; /* LD_TYPE */
1241 : : l_sg.subdc = NIX_SUBDC_SG;
1242 : : nb_segs = m->nb_segs;
1243 : : len = m->pkt_len;
1244 : : slist = &cmd[1];
1245 : :
1246 : : /* Fill mbuf segments */
1247 : : do {
1248 : : *slist = rte_pktmbuf_iova(m);
1249 : : dlen = m->data_len;
1250 : : len -= dlen;
1251 : :
1252 : : /* Set the segment length */
1253 : : l_sg.u |= ((uint64_t)dlen << (l_sg.segs << 4));
1254 : : l_sg.segs += 1;
1255 : : slist++;
1256 : : nb_segs--;
1257 : : if (l_sg.segs > 2 && nb_segs) {
1258 : : sg->u = l_sg.u;
1259 : : /* Next SG subdesc */
1260 : : sg = (union nix_send_sg_s *)slist;
1261 : : l_sg.u = sg->u;
1262 : : l_sg.u &= 0xC00000000000000; /* LD_TYPE */
1263 : : l_sg.subdc = NIX_SUBDC_SG;
1264 : : slist++;
1265 : : }
1266 : : m_next = m->next;
1267 : : m = m_next;
1268 : : } while (nb_segs);
1269 : :
1270 : : /* Add remaining bytes of data to last seg */
1271 : : if (len) {
1272 : : uint8_t shft = (l_sg.subdc == NIX_SUBDC_SG) ? ((l_sg.segs - 1) << 4) : 0;
1273 : : dlen = ((l_sg.u >> shft) & 0xFFFFULL) + len;
1274 : : l_sg.u = l_sg.u & ~(0xFFFFULL << shft);
1275 : : l_sg.u |= dlen << shft;
1276 : : }
1277 : : /* Write the last subdc out */
1278 : : sg->u = l_sg.u;
1279 : :
1280 : : segdw = (uint64_t *)slist - cmd;
1281 : : /* Roundup extra dwords to multiple of 2 */
1282 : : segdw = (segdw >> 1) + (segdw & 0x1);
1283 : : return segdw;
1284 : : }
1285 : :
1286 : : static __rte_always_inline uint16_t
1287 : : cn10k_nix_inj_pkts(struct rte_security_session **sess, struct cnxk_ethdev_inj_cfg *inj_cfg,
1288 : : struct rte_mbuf **tx_pkts, uint16_t nb_pkts)
1289 : : {
1290 : : uintptr_t c_lbase = inj_cfg->lmt_base;
1291 : : struct cn10k_sec_sess_priv sess_priv;
1292 : : uint64_t sa_base = inj_cfg->sa_base;
1293 : : uint16_t c_lmt_id, burst, left, i;
1294 : : uintptr_t cptres, rxphdr, dptr;
1295 : : struct rte_mbuf *m, *last;
1296 : : uint8_t lnum, shft, loff;
1297 : : uint64x2_t cmd01, cmd23;
1298 : : uint64_t ucode_cmd[4];
1299 : : rte_iova_t c_io_addr;
1300 : : uint64_t *laddr;
1301 : : uint64_t sa, w0;
1302 : : uint16_t segdw;
1303 : :
1304 : : /* Get LMT base address and LMT ID as lcore id */
1305 : : ROC_LMT_CPT_BASE_ID_GET(c_lbase, c_lmt_id);
1306 : : c_io_addr = inj_cfg->io_addr;
1307 : :
1308 : : left = nb_pkts;
1309 : : again:
1310 : : burst = left > 32 ? 32 : left;
1311 : :
1312 : : lnum = 0;
1313 : : loff = 0;
1314 : : shft = 16;
1315 : :
1316 : : for (i = 0; i < burst; i++) {
1317 : : m = tx_pkts[i];
1318 : : sess_priv.u64 = sess[i]->fast_mdata;
1319 : : last = rte_pktmbuf_lastseg(m);
1320 : :
1321 : : cptres = rte_pktmbuf_mtod_offset(last, uintptr_t, last->data_len);
1322 : : cptres += BIT_ULL(7);
1323 : : cptres = (cptres - 1) & ~(BIT_ULL(7) - 1);
1324 : :
1325 : : if (m->nb_segs > 1) {
1326 : : /* Will reserve NIX Rx descriptor with SG list after end of
1327 : : * last mbuf data location. and pointer to this will be
1328 : : * stored at 1st mbuf space for Rx path multi-seg processing.
1329 : : */
1330 : : /* Pointer to WQE header */
1331 : : *(uint64_t *)(m + 1) = cptres;
1332 : : /* Reserve 8 Dwords of WQE Hdr + Rx Parse Hdr */
1333 : : rxphdr = cptres + 8;
1334 : : dptr = rxphdr + 7 * 8;
1335 : : /* Prepare Multiseg SG list */
1336 : : segdw = cn10k_nix_rx_inj_prepare_mseg(m, (uint64_t *)(dptr));
1337 : : *(uint64_t *)rxphdr = (uint64_t)(segdw - 1) << 12;
1338 : : cptres += 64 + segdw * 16;
1339 : : ucode_cmd[1] = dptr | ((uint64_t)m->nb_segs << 60);
1340 : : } else {
1341 : : dptr = (uint64_t)rte_pktmbuf_iova(m);
1342 : : ucode_cmd[1] = dptr;
1343 : : }
1344 : :
1345 : : /* Prepare CPT instruction */
1346 : : /* CPT word 0 and 1 */
1347 : : cmd01 = vdupq_n_u64(0);
1348 : : w0 = inj_cfg->cmd_w0 | ((uint64_t)m->l2_len - 2) << 24 | (uint64_t)m->l2_len << 16;
1349 : : cmd01 = vsetq_lane_u64(w0, cmd01, 0);
1350 : : cmd01 = vsetq_lane_u64(cptres, cmd01, 1);
1351 : :
1352 : : /* CPT word 2 and 3 */
1353 : : cmd23 = vdupq_n_u64(0);
1354 : : /* Set PF func */
1355 : : w0 &= 0xFFFF000000000000UL;
1356 : : cmd23 = vsetq_lane_u64(w0, cmd23, 0);
1357 : : cmd23 = vsetq_lane_u64(((uint64_t)m + sizeof(struct rte_mbuf)) | 1, cmd23, 1);
1358 : :
1359 : : sa_base &= ~0xFFFFUL;
1360 : : sa = (uintptr_t)roc_nix_inl_ot_ipsec_inb_sa(sa_base, sess_priv.sa_idx);
1361 : : ucode_cmd[0] = (ROC_IE_OT_MAJOR_OP_PROCESS_INBOUND_IPSEC << 48 | 1UL << 54 |
1362 : : ((uint64_t)sess_priv.chksum) << 32 |
1363 : : ((uint64_t)sess_priv.dec_ttl) << 34 | m->pkt_len);
1364 : :
1365 : : ucode_cmd[2] = 0;
1366 : : ucode_cmd[3] = (ROC_CPT_DFLT_ENG_GRP_SE_IE << 61 | 1UL << 60 | sa);
1367 : :
1368 : : /* Move to our line */
1369 : : laddr = LMT_OFF(c_lbase, lnum, loff ? 64 : 0);
1370 : :
1371 : : /* Write CPT instruction to lmt line */
1372 : : vst1q_u64(laddr, cmd01);
1373 : : vst1q_u64((laddr + 2), cmd23);
1374 : :
1375 : : *(__uint128_t *)(laddr + 4) = *(__uint128_t *)ucode_cmd;
1376 : : *(__uint128_t *)(laddr + 6) = *(__uint128_t *)(ucode_cmd + 2);
1377 : :
1378 : : loff = !loff;
1379 : : lnum = lnum + (loff ? 0 : 1);
1380 : : shft = shft + (loff ? 0 : 3);
1381 : : }
1382 : :
1383 : : left -= burst;
1384 : : tx_pkts += burst;
1385 : : sess += burst;
1386 : :
1387 : : cn10k_nix_sec_steorl(c_io_addr, c_lmt_id, lnum, loff, shft);
1388 : :
1389 : : rte_io_wmb();
1390 : : if (left)
1391 : : goto again;
1392 : :
1393 : : return nb_pkts;
1394 : : }
1395 : : #else
1396 : : static __rte_always_inline uint16_t
1397 : : cn10k_nix_inj_pkts(struct rte_security_session **sess, struct cnxk_ethdev_inj_cfg *inj_cfg,
1398 : : struct rte_mbuf **tx_pkts, uint16_t nb_pkts)
1399 : : {
1400 : : RTE_SET_USED(sess);
1401 : : RTE_SET_USED(inj_cfg);
1402 : : RTE_SET_USED(tx_pkts);
1403 : : RTE_SET_USED(nb_pkts);
1404 : : return 0;
1405 : : }
1406 : : #endif
1407 : :
1408 : : #if defined(RTE_ARCH_ARM64)
1409 : :
1410 : : static __rte_always_inline uint64_t
1411 : : nix_vlan_update(const uint64_t w2, uint64_t ol_flags, uint8x16_t *f)
1412 : : {
1413 : : if (w2 & BIT_ULL(21) /* vtag0_gone */) {
1414 : : ol_flags |= RTE_MBUF_F_RX_VLAN | RTE_MBUF_F_RX_VLAN_STRIPPED;
1415 : : *f = vsetq_lane_u16((uint16_t)(w2 >> 32), *f, 5);
1416 : : }
1417 : :
1418 : : return ol_flags;
1419 : : }
1420 : :
1421 : : static __rte_always_inline uint64_t
1422 : : nix_qinq_update(const uint64_t w2, uint64_t ol_flags, struct rte_mbuf *mbuf)
1423 : : {
1424 : : if (w2 & BIT_ULL(23) /* vtag1_gone */) {
1425 : : ol_flags |= RTE_MBUF_F_RX_QINQ | RTE_MBUF_F_RX_QINQ_STRIPPED;
1426 : : mbuf->vlan_tci_outer = (uint16_t)(w2 >> 48);
1427 : : }
1428 : :
1429 : : return ol_flags;
1430 : : }
1431 : :
1432 : : #define NIX_PUSH_META_TO_FREE(_mbuf, _laddr, _loff_p) \
1433 : : do { \
1434 : : *(uint64_t *)((_laddr) + (*(_loff_p) << 3)) = (uint64_t)_mbuf; \
1435 : : *(_loff_p) = *(_loff_p) + 1; \
1436 : : /* Mark meta mbuf as put */ \
1437 : : RTE_MEMPOOL_CHECK_COOKIES(_mbuf->pool, (void **)&_mbuf, 1, 0); \
1438 : : } while (0)
1439 : :
1440 : : static __rte_always_inline uint16_t
1441 : : cn10k_nix_recv_pkts_vector(void *args, struct rte_mbuf **mbufs, uint16_t pkts,
1442 : : const uint16_t flags, void *lookup_mem,
1443 : : struct cnxk_timesync_info *tstamp,
1444 : : uintptr_t lmt_base, uint64_t meta_aura)
1445 : : {
1446 : : struct cn10k_eth_rxq *rxq = args;
1447 : : const uint64_t mbuf_initializer = (flags & NIX_RX_VWQE_F) ?
1448 : : *(uint64_t *)args :
1449 : : rxq->mbuf_initializer;
1450 : : const uint64x2_t data_off = flags & NIX_RX_VWQE_F ?
1451 : : vdupq_n_u64(RTE_PKTMBUF_HEADROOM) :
1452 : : vdupq_n_u64(rxq->data_off);
1453 : : const uint32_t qmask = flags & NIX_RX_VWQE_F ? 0 : rxq->qmask;
1454 : : const uint64_t wdata = flags & NIX_RX_VWQE_F ? 0 : rxq->wdata;
1455 : : const uintptr_t desc = flags & NIX_RX_VWQE_F ? 0 : rxq->desc;
1456 : : uint64x2_t cq0_w8, cq1_w8, cq2_w8, cq3_w8, mbuf01, mbuf23;
1457 : : uintptr_t cpth0 = 0, cpth1 = 0, cpth2 = 0, cpth3 = 0;
1458 : : uint64_t ol_flags0, ol_flags1, ol_flags2, ol_flags3;
1459 : : uint64x2_t rearm0 = vdupq_n_u64(mbuf_initializer);
1460 : : uint64x2_t rearm1 = vdupq_n_u64(mbuf_initializer);
1461 : : uint64x2_t rearm2 = vdupq_n_u64(mbuf_initializer);
1462 : : uint64x2_t rearm3 = vdupq_n_u64(mbuf_initializer);
1463 : : struct rte_mbuf *mbuf0, *mbuf1, *mbuf2, *mbuf3;
1464 : : uint8_t loff = 0, lnum = 0, shft = 0;
1465 : : struct rte_mempool *meta_pool = NULL;
1466 : : uint8x16_t f0, f1, f2, f3;
1467 : : uint16_t lmt_id, d_off;
1468 : : uint64_t lbase, laddr;
1469 : : uintptr_t sa_base = 0;
1470 : : uint16_t packets = 0;
1471 : : uint16_t pkts_left;
1472 : : uint32_t head;
1473 : : uintptr_t cq0;
1474 : :
1475 : : if (!(flags & NIX_RX_VWQE_F)) {
1476 : : lookup_mem = rxq->lookup_mem;
1477 : : head = rxq->head;
1478 : :
1479 : : pkts = nix_rx_nb_pkts(rxq, wdata, pkts, qmask);
1480 : : pkts_left = pkts & (NIX_DESCS_PER_LOOP - 1);
1481 : : /* Packets has to be floor-aligned to NIX_DESCS_PER_LOOP */
1482 : : pkts = RTE_ALIGN_FLOOR(pkts, NIX_DESCS_PER_LOOP);
1483 : : if (flags & NIX_RX_OFFLOAD_TSTAMP_F)
1484 : : tstamp = rxq->tstamp;
1485 : :
1486 : : cq0 = desc + CQE_SZ(head);
1487 : : rte_prefetch0(CQE_PTR_OFF(cq0, 0, 64, flags));
1488 : : rte_prefetch0(CQE_PTR_OFF(cq0, 1, 64, flags));
1489 : : rte_prefetch0(CQE_PTR_OFF(cq0, 2, 64, flags));
1490 : : rte_prefetch0(CQE_PTR_OFF(cq0, 3, 64, flags));
1491 : : } else {
1492 : : RTE_SET_USED(head);
1493 : : }
1494 : :
1495 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
1496 : : if (flags & NIX_RX_VWQE_F) {
1497 : : uint64_t sg_w1;
1498 : : uint16_t port;
1499 : :
1500 : : mbuf0 = (struct rte_mbuf *)((uintptr_t)mbufs[0] -
1501 : : sizeof(struct rte_mbuf));
1502 : : /* Pick first mbuf's aura handle assuming all
1503 : : * mbufs are from a vec and are from same RQ.
1504 : : */
1505 : : if (!meta_aura)
1506 : : meta_aura = mbuf0->pool->pool_id;
1507 : : /* Calculate offset from mbuf to actual data area */
1508 : : /* Zero aura's first skip i.e mbuf setup might not match the actual
1509 : : * offset as first skip is taken from second pass RQ. So compute
1510 : : * using diff b/w first SG pointer and mbuf addr.
1511 : : */
1512 : : sg_w1 = *(uint64_t *)((uintptr_t)mbufs[0] + 72);
1513 : : d_off = (sg_w1 - (uint64_t)mbuf0);
1514 : :
1515 : : /* Get SA Base from lookup tbl using port_id */
1516 : : port = mbuf_initializer >> 48;
1517 : : sa_base = cnxk_nix_sa_base_get(port, lookup_mem);
1518 : : if (flags & NIX_RX_REAS_F)
1519 : : meta_pool = (struct rte_mempool *)cnxk_nix_inl_metapool_get(port,
1520 : : lookup_mem);
1521 : :
1522 : : lbase = lmt_base;
1523 : : } else {
1524 : : meta_aura = rxq->meta_aura;
1525 : : d_off = rxq->data_off;
1526 : : sa_base = rxq->sa_base;
1527 : : lbase = rxq->lmt_base;
1528 : : if (flags & NIX_RX_REAS_F)
1529 : : meta_pool = (struct rte_mempool *)rxq->meta_pool;
1530 : : }
1531 : : sa_base &= ~(ROC_NIX_INL_SA_BASE_ALIGN - 1);
1532 : : ROC_LMT_BASE_ID_GET(lbase, lmt_id);
1533 : : lnum = 0;
1534 : : laddr = lbase;
1535 : : laddr += 8;
1536 : : }
1537 : :
1538 : : while (packets < pkts) {
1539 : : if (!(flags & NIX_RX_VWQE_F)) {
1540 : : /* Exit loop if head is about to wrap and become
1541 : : * unaligned.
1542 : : */
1543 : : if (((head + NIX_DESCS_PER_LOOP - 1) & qmask) <
1544 : : NIX_DESCS_PER_LOOP) {
1545 : : pkts_left += (pkts - packets);
1546 : : break;
1547 : : }
1548 : :
1549 : : cq0 = desc + CQE_SZ(head);
1550 : : } else {
1551 : : cq0 = (uintptr_t)&mbufs[packets];
1552 : : }
1553 : :
1554 : : if (flags & NIX_RX_VWQE_F) {
1555 : : if (pkts - packets > 4) {
1556 : : rte_prefetch_non_temporal(CQE_PTR_OFF(cq0,
1557 : : 4, 0, flags));
1558 : : rte_prefetch_non_temporal(CQE_PTR_OFF(cq0,
1559 : : 5, 0, flags));
1560 : : rte_prefetch_non_temporal(CQE_PTR_OFF(cq0,
1561 : : 6, 0, flags));
1562 : : rte_prefetch_non_temporal(CQE_PTR_OFF(cq0,
1563 : : 7, 0, flags));
1564 : :
1565 : : if (likely(pkts - packets > 8)) {
1566 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1567 : : 8, 0, flags));
1568 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1569 : : 9, 0, flags));
1570 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1571 : : 10, 0, flags));
1572 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1573 : : 11, 0, flags));
1574 : : if (pkts - packets > 12) {
1575 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1576 : : 12, 0, flags));
1577 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1578 : : 13, 0, flags));
1579 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1580 : : 14, 0, flags));
1581 : : rte_prefetch1(CQE_PTR_OFF(cq0,
1582 : : 15, 0, flags));
1583 : : }
1584 : : }
1585 : :
1586 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1587 : : 4, RTE_PKTMBUF_HEADROOM, flags));
1588 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1589 : : 5, RTE_PKTMBUF_HEADROOM, flags));
1590 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1591 : : 6, RTE_PKTMBUF_HEADROOM, flags));
1592 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1593 : : 7, RTE_PKTMBUF_HEADROOM, flags));
1594 : :
1595 : : if (likely(pkts - packets > 8)) {
1596 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1597 : : 8, RTE_PKTMBUF_HEADROOM, flags));
1598 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1599 : : 9, RTE_PKTMBUF_HEADROOM, flags));
1600 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1601 : : 10, RTE_PKTMBUF_HEADROOM, flags));
1602 : : rte_prefetch0(CQE_PTR_DIFF(cq0,
1603 : : 11, RTE_PKTMBUF_HEADROOM, flags));
1604 : : }
1605 : : }
1606 : : } else {
1607 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F &&
1608 : : pkts - packets > 4) {
1609 : : /* Fetch cpt parse header */
1610 : : void *p0 =
1611 : : (void *)*CQE_PTR_OFF(cq0, 4, 72, flags);
1612 : : void *p1 =
1613 : : (void *)*CQE_PTR_OFF(cq0, 5, 72, flags);
1614 : : void *p2 =
1615 : : (void *)*CQE_PTR_OFF(cq0, 6, 72, flags);
1616 : : void *p3 =
1617 : : (void *)*CQE_PTR_OFF(cq0, 7, 72, flags);
1618 : : rte_prefetch0(p0);
1619 : : rte_prefetch0(p1);
1620 : : rte_prefetch0(p2);
1621 : : rte_prefetch0(p3);
1622 : : }
1623 : :
1624 : : if (pkts - packets > 8) {
1625 : : if (flags) {
1626 : : rte_prefetch0(CQE_PTR_OFF(cq0, 8, 0, flags));
1627 : : rte_prefetch0(CQE_PTR_OFF(cq0, 9, 0, flags));
1628 : : rte_prefetch0(CQE_PTR_OFF(cq0, 10, 0, flags));
1629 : : rte_prefetch0(CQE_PTR_OFF(cq0, 11, 0, flags));
1630 : : }
1631 : : rte_prefetch0(CQE_PTR_OFF(cq0, 8, 64, flags));
1632 : : rte_prefetch0(CQE_PTR_OFF(cq0, 9, 64, flags));
1633 : : rte_prefetch0(CQE_PTR_OFF(cq0, 10, 64, flags));
1634 : : rte_prefetch0(CQE_PTR_OFF(cq0, 11, 64, flags));
1635 : : }
1636 : : }
1637 : :
1638 : : if (!(flags & NIX_RX_VWQE_F)) {
1639 : : /* Get NIX_RX_SG_S for size and buffer pointer */
1640 : : cq0_w8 = vld1q_u64(CQE_PTR_OFF(cq0, 0, 64, flags));
1641 : : cq1_w8 = vld1q_u64(CQE_PTR_OFF(cq0, 1, 64, flags));
1642 : : cq2_w8 = vld1q_u64(CQE_PTR_OFF(cq0, 2, 64, flags));
1643 : : cq3_w8 = vld1q_u64(CQE_PTR_OFF(cq0, 3, 64, flags));
1644 : :
1645 : : /* Extract mbuf from NIX_RX_SG_S */
1646 : : mbuf01 = vzip2q_u64(cq0_w8, cq1_w8);
1647 : : mbuf23 = vzip2q_u64(cq2_w8, cq3_w8);
1648 : : mbuf01 = vqsubq_u64(mbuf01, data_off);
1649 : : mbuf23 = vqsubq_u64(mbuf23, data_off);
1650 : : } else {
1651 : : mbuf01 =
1652 : : vsubq_u64(vld1q_u64((uint64_t *)cq0),
1653 : : vdupq_n_u64(sizeof(struct rte_mbuf)));
1654 : : mbuf23 =
1655 : : vsubq_u64(vld1q_u64((uint64_t *)(cq0 + 16)),
1656 : : vdupq_n_u64(sizeof(struct rte_mbuf)));
1657 : : }
1658 : :
1659 : : /* Move mbufs to scalar registers for future use */
1660 : : mbuf0 = (struct rte_mbuf *)vgetq_lane_u64(mbuf01, 0);
1661 : : mbuf1 = (struct rte_mbuf *)vgetq_lane_u64(mbuf01, 1);
1662 : : mbuf2 = (struct rte_mbuf *)vgetq_lane_u64(mbuf23, 0);
1663 : : mbuf3 = (struct rte_mbuf *)vgetq_lane_u64(mbuf23, 1);
1664 : :
1665 : : /* Mark mempool obj as "get" as it is alloc'ed by NIX */
1666 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf0->pool, (void **)&mbuf0, 1, 1);
1667 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf1->pool, (void **)&mbuf1, 1, 1);
1668 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf2->pool, (void **)&mbuf2, 1, 1);
1669 : : RTE_MEMPOOL_CHECK_COOKIES(mbuf3->pool, (void **)&mbuf3, 1, 1);
1670 : :
1671 : : if (!(flags & NIX_RX_VWQE_F)) {
1672 : : /* Mask to get packet len from NIX_RX_SG_S */
1673 : : const uint8x16_t shuf_msk = {
1674 : : 0xFF, 0xFF, /* pkt_type set as unknown */
1675 : : 0xFF, 0xFF, /* pkt_type set as unknown */
1676 : : 0, 1, /* octet 1~0, low 16 bits pkt_len */
1677 : : 0xFF, 0xFF, /* skip high 16it pkt_len, zero out */
1678 : : 0, 1, /* octet 1~0, 16 bits data_len */
1679 : : 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
1680 : :
1681 : : /* Form the rx_descriptor_fields1 with pkt_len and data_len */
1682 : : f0 = vqtbl1q_u8(cq0_w8, shuf_msk);
1683 : : f1 = vqtbl1q_u8(cq1_w8, shuf_msk);
1684 : : f2 = vqtbl1q_u8(cq2_w8, shuf_msk);
1685 : : f3 = vqtbl1q_u8(cq3_w8, shuf_msk);
1686 : : }
1687 : :
1688 : : /* Load CQE word0 and word 1 */
1689 : : const uint64_t cq0_w0 = *CQE_PTR_OFF(cq0, 0, 0, flags);
1690 : : const uint64_t cq0_w1 = *CQE_PTR_OFF(cq0, 0, 8, flags);
1691 : : const uint64_t cq0_w2 = *CQE_PTR_OFF(cq0, 0, 16, flags);
1692 : : const uint64_t cq1_w0 = *CQE_PTR_OFF(cq0, 1, 0, flags);
1693 : : const uint64_t cq1_w1 = *CQE_PTR_OFF(cq0, 1, 8, flags);
1694 : : const uint64_t cq1_w2 = *CQE_PTR_OFF(cq0, 1, 16, flags);
1695 : : const uint64_t cq2_w0 = *CQE_PTR_OFF(cq0, 2, 0, flags);
1696 : : const uint64_t cq2_w1 = *CQE_PTR_OFF(cq0, 2, 8, flags);
1697 : : const uint64_t cq2_w2 = *CQE_PTR_OFF(cq0, 2, 16, flags);
1698 : : const uint64_t cq3_w0 = *CQE_PTR_OFF(cq0, 3, 0, flags);
1699 : : const uint64_t cq3_w1 = *CQE_PTR_OFF(cq0, 3, 8, flags);
1700 : : const uint64_t cq3_w2 = *CQE_PTR_OFF(cq0, 3, 16, flags);
1701 : :
1702 : : if (flags & NIX_RX_VWQE_F) {
1703 : : uint16_t psize0, psize1, psize2, psize3;
1704 : :
1705 : : psize0 = (cq0_w2 & 0xFFFF) + 1;
1706 : : psize1 = (cq1_w2 & 0xFFFF) + 1;
1707 : : psize2 = (cq2_w2 & 0xFFFF) + 1;
1708 : : psize3 = (cq3_w2 & 0xFFFF) + 1;
1709 : :
1710 : : f0 = vdupq_n_u64(0);
1711 : : f1 = vdupq_n_u64(0);
1712 : : f2 = vdupq_n_u64(0);
1713 : : f3 = vdupq_n_u64(0);
1714 : :
1715 : : f0 = vsetq_lane_u16(psize0, f0, 2);
1716 : : f0 = vsetq_lane_u16(psize0, f0, 4);
1717 : :
1718 : : f1 = vsetq_lane_u16(psize1, f1, 2);
1719 : : f1 = vsetq_lane_u16(psize1, f1, 4);
1720 : :
1721 : : f2 = vsetq_lane_u16(psize2, f2, 2);
1722 : : f2 = vsetq_lane_u16(psize2, f2, 4);
1723 : :
1724 : : f3 = vsetq_lane_u16(psize3, f3, 2);
1725 : : f3 = vsetq_lane_u16(psize3, f3, 4);
1726 : : }
1727 : :
1728 : : if (flags & NIX_RX_OFFLOAD_RSS_F) {
1729 : : /* Fill rss in the rx_descriptor_fields1 */
1730 : : f0 = vsetq_lane_u32(cq0_w0, f0, 3);
1731 : : f1 = vsetq_lane_u32(cq1_w0, f1, 3);
1732 : : f2 = vsetq_lane_u32(cq2_w0, f2, 3);
1733 : : f3 = vsetq_lane_u32(cq3_w0, f3, 3);
1734 : : ol_flags0 = RTE_MBUF_F_RX_RSS_HASH;
1735 : : ol_flags1 = RTE_MBUF_F_RX_RSS_HASH;
1736 : : ol_flags2 = RTE_MBUF_F_RX_RSS_HASH;
1737 : : ol_flags3 = RTE_MBUF_F_RX_RSS_HASH;
1738 : : } else {
1739 : : ol_flags0 = 0;
1740 : : ol_flags1 = 0;
1741 : : ol_flags2 = 0;
1742 : : ol_flags3 = 0;
1743 : : }
1744 : :
1745 : : if (flags & NIX_RX_OFFLOAD_PTYPE_F) {
1746 : : /* Fill packet_type in the rx_descriptor_fields1 */
1747 : : f0 = vsetq_lane_u32(nix_ptype_get(lookup_mem, cq0_w1),
1748 : : f0, 0);
1749 : : f1 = vsetq_lane_u32(nix_ptype_get(lookup_mem, cq1_w1),
1750 : : f1, 0);
1751 : : f2 = vsetq_lane_u32(nix_ptype_get(lookup_mem, cq2_w1),
1752 : : f2, 0);
1753 : : f3 = vsetq_lane_u32(nix_ptype_get(lookup_mem, cq3_w1),
1754 : : f3, 0);
1755 : : }
1756 : :
1757 : : if (flags & NIX_RX_OFFLOAD_CHECKSUM_F) {
1758 : : ol_flags0 |= (uint64_t)nix_rx_olflags_get(lookup_mem, cq0_w1);
1759 : : ol_flags1 |= (uint64_t)nix_rx_olflags_get(lookup_mem, cq1_w1);
1760 : : ol_flags2 |= (uint64_t)nix_rx_olflags_get(lookup_mem, cq2_w1);
1761 : : ol_flags3 |= (uint64_t)nix_rx_olflags_get(lookup_mem, cq3_w1);
1762 : : }
1763 : :
1764 : : /* Translate meta to mbuf */
1765 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
1766 : : uint64_t cq0_w5 = *CQE_PTR_OFF(cq0, 0, 40, flags);
1767 : : uint64_t cq1_w5 = *CQE_PTR_OFF(cq0, 1, 40, flags);
1768 : : uint64_t cq2_w5 = *CQE_PTR_OFF(cq0, 2, 40, flags);
1769 : : uint64_t cq3_w5 = *CQE_PTR_OFF(cq0, 3, 40, flags);
1770 : : uint8_t code;
1771 : :
1772 : : uint64x2_t inner0, inner1, inner2, inner3;
1773 : : uint64x2_t wqe01, wqe23, sa01, sa23;
1774 : : uint16x4_t lens, l2lens, ltypes;
1775 : : uint64x2_t mask01, mask23;
1776 : : uint8x8_t ucc;
1777 : :
1778 : : cpth0 = (uintptr_t)mbuf0 + d_off;
1779 : : cpth1 = (uintptr_t)mbuf1 + d_off;
1780 : : cpth2 = (uintptr_t)mbuf2 + d_off;
1781 : : cpth3 = (uintptr_t)mbuf3 + d_off;
1782 : :
1783 : : inner0 = vld1q_u64((const uint64_t *)cpth0);
1784 : : inner1 = vld1q_u64((const uint64_t *)cpth1);
1785 : : inner2 = vld1q_u64((const uint64_t *)cpth2);
1786 : : inner3 = vld1q_u64((const uint64_t *)cpth3);
1787 : :
1788 : : /* Extract and reverse wqe pointers */
1789 : : wqe01 = vzip2q_u64(inner0, inner1);
1790 : : wqe23 = vzip2q_u64(inner2, inner3);
1791 : : wqe01 = vrev64q_u8(wqe01);
1792 : : wqe23 = vrev64q_u8(wqe23);
1793 : : /* Adjust wqe pointers to point to mbuf */
1794 : : wqe01 = vsubq_u64(wqe01,
1795 : : vdupq_n_u64(sizeof(struct rte_mbuf)));
1796 : : wqe23 = vsubq_u64(wqe23,
1797 : : vdupq_n_u64(sizeof(struct rte_mbuf)));
1798 : :
1799 : : /* Extract sa idx from cookie area and add to sa_base */
1800 : : sa01 = vzip1q_u64(inner0, inner1);
1801 : : sa23 = vzip1q_u64(inner2, inner3);
1802 : :
1803 : : sa01 = vshrq_n_u64(sa01, 32);
1804 : : sa23 = vshrq_n_u64(sa23, 32);
1805 : :
1806 : : /* Crypto Look-aside Rx Inject case */
1807 : : mask01 = vceqq_u64(sa01, vdupq_n_u64(0xFFFFFFFF));
1808 : : mask23 = vceqq_u64(sa23, vdupq_n_u64(0xFFFFFFFF));
1809 : :
1810 : : sa01 = vshlq_n_u64(sa01,
1811 : : ROC_NIX_INL_OT_IPSEC_INB_SA_SZ_LOG2);
1812 : : sa23 = vshlq_n_u64(sa23,
1813 : : ROC_NIX_INL_OT_IPSEC_INB_SA_SZ_LOG2);
1814 : : sa01 = vaddq_u64(sa01, vdupq_n_u64(sa_base));
1815 : : sa23 = vaddq_u64(sa23, vdupq_n_u64(sa_base));
1816 : :
1817 : : if (flags & NIX_RX_REAS_F) {
1818 : : sa01 = vbicq_u64(sa01, mask01);
1819 : : sa23 = vbicq_u64(sa23, mask23);
1820 : : }
1821 : :
1822 : : const uint8x16x2_t tbl = {{
1823 : : {
1824 : : /* ROC_IE_OT_UCC_SUCCESS_PKT_IP_BADCSUM */
1825 : : RTE_MBUF_F_RX_IP_CKSUM_BAD >> 1,
1826 : : /* ROC_IE_OT_UCC_SUCCESS_PKT_L4_GOODCSUM */
1827 : : (RTE_MBUF_F_RX_IP_CKSUM_GOOD |
1828 : : RTE_MBUF_F_RX_L4_CKSUM_GOOD) >> 1,
1829 : : /* ROC_IE_OT_UCC_SUCCESS_PKT_L4_BADCSUM */
1830 : : (RTE_MBUF_F_RX_IP_CKSUM_GOOD |
1831 : : RTE_MBUF_F_RX_L4_CKSUM_BAD) >> 1,
1832 : : 1,
1833 : : /* ROC_IE_OT_UCC_SUCCESS_PKT_UDPESP_NZCSUM */
1834 : : (RTE_MBUF_F_RX_IP_CKSUM_GOOD |
1835 : : RTE_MBUF_F_RX_L4_CKSUM_GOOD) >> 1,
1836 : : 1,
1837 : : /* ROC_IE_OT_UCC_SUCCESS_PKT_UDP_ZEROCSUM */
1838 : : (RTE_MBUF_F_RX_IP_CKSUM_GOOD |
1839 : : RTE_MBUF_F_RX_L4_CKSUM_GOOD) >> 1,
1840 : : 3, 1, 3, 3, 3, 3, 1, 3, 1,
1841 : : },
1842 : : {
1843 : : 1, 1, 1,
1844 : : /* ROC_IE_OT_UCC_SUCCESS_PKT_IP_GOODCSUM */
1845 : : RTE_MBUF_F_RX_IP_CKSUM_GOOD >> 1,
1846 : : /* Rest 0 to indicate RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED */
1847 : : 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1848 : : },
1849 : : }};
1850 : :
1851 : : const uint8x8_t err_off = {
1852 : : /* UCC */
1853 : : 0xED,
1854 : : /* HW_CCODE 0:6 -> 7:D */
1855 : : -7,
1856 : : 0xED,
1857 : : -7,
1858 : : 0xED,
1859 : : -7,
1860 : : 0xED,
1861 : : -7,
1862 : : };
1863 : :
1864 : : ucc = vdup_n_u8(0);
1865 : : ucc = vset_lane_u16(*(uint16_t *)(cpth0 + 30), ucc, 0);
1866 : : ucc = vset_lane_u16(*(uint16_t *)(cpth1 + 30), ucc, 1);
1867 : : ucc = vset_lane_u16(*(uint16_t *)(cpth2 + 30), ucc, 2);
1868 : : ucc = vset_lane_u16(*(uint16_t *)(cpth3 + 30), ucc, 3);
1869 : : ucc = vsub_u8(ucc, err_off);
1870 : :
1871 : : /* Table lookup to get the corresponding flags, Out of the range
1872 : : * from this lookup will have value 0 and consider as
1873 : : * RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED.
1874 : : */
1875 : : ucc = vqtbl2_u8(tbl, ucc);
1876 : :
1877 : : RTE_BUILD_BUG_ON(NPC_LT_LC_IP != 2);
1878 : : RTE_BUILD_BUG_ON(NPC_LT_LC_IP_OPT != 3);
1879 : : RTE_BUILD_BUG_ON(NPC_LT_LC_IP6 != 4);
1880 : : RTE_BUILD_BUG_ON(NPC_LT_LC_IP6_EXT != 5);
1881 : :
1882 : : ltypes = vdup_n_u16(0);
1883 : : ltypes = vset_lane_u16((cq0_w1 >> 40) & 0x6, ltypes, 0);
1884 : : ltypes = vset_lane_u16((cq1_w1 >> 40) & 0x6, ltypes, 1);
1885 : : ltypes = vset_lane_u16((cq2_w1 >> 40) & 0x6, ltypes, 2);
1886 : : ltypes = vset_lane_u16((cq3_w1 >> 40) & 0x6, ltypes, 3);
1887 : :
1888 : : /* Extract and reverse l3 length from IPv4/IPv6 hdr
1889 : : * that is in same cacheline most probably as cpth.
1890 : : */
1891 : : cpth0 += ((cq0_w5 >> 16) & 0xFF) +
1892 : : vget_lane_u16(ltypes, 0);
1893 : : cpth1 += ((cq1_w5 >> 16) & 0xFF) +
1894 : : vget_lane_u16(ltypes, 1);
1895 : : cpth2 += ((cq2_w5 >> 16) & 0xFF) +
1896 : : vget_lane_u16(ltypes, 2);
1897 : : cpth3 += ((cq3_w5 >> 16) & 0xFF) +
1898 : : vget_lane_u16(ltypes, 3);
1899 : : lens = vdup_n_u16(0);
1900 : : lens = vset_lane_u16(*(uint16_t *)cpth0, lens, 0);
1901 : : lens = vset_lane_u16(*(uint16_t *)cpth1, lens, 1);
1902 : : lens = vset_lane_u16(*(uint16_t *)cpth2, lens, 2);
1903 : : lens = vset_lane_u16(*(uint16_t *)cpth3, lens, 3);
1904 : : lens = vrev16_u8(lens);
1905 : :
1906 : : /* Add l2 length to l3 lengths */
1907 : : l2lens = vdup_n_u16(0);
1908 : : l2lens = vset_lane_u16(((cq0_w5 >> 16) & 0xFF) -
1909 : : (cq0_w5 & 0xFF),
1910 : : l2lens, 0);
1911 : : l2lens = vset_lane_u16(((cq1_w5 >> 16) & 0xFF) -
1912 : : (cq1_w5 & 0xFF),
1913 : : l2lens, 1);
1914 : : l2lens = vset_lane_u16(((cq2_w5 >> 16) & 0xFF) -
1915 : : (cq2_w5 & 0xFF),
1916 : : l2lens, 2);
1917 : : l2lens = vset_lane_u16(((cq3_w5 >> 16) & 0xFF) -
1918 : : (cq3_w5 & 0xFF),
1919 : : l2lens, 3);
1920 : : lens = vadd_u16(lens, l2lens);
1921 : :
1922 : : /* L3 header adjust */
1923 : : const int8x8_t l3adj = {
1924 : : 0, 0, 0, 0, 40, 0, 0, 0,
1925 : : };
1926 : : lens = vadd_u16(lens, vtbl1_u8(l3adj, ltypes));
1927 : :
1928 : : /* Initialize rearm data when reassembly is enabled as
1929 : : * data offset might change.
1930 : : */
1931 : : if (flags & NIX_RX_REAS_F) {
1932 : : rearm0 = vdupq_n_u64(mbuf_initializer);
1933 : : rearm1 = vdupq_n_u64(mbuf_initializer);
1934 : : rearm2 = vdupq_n_u64(mbuf_initializer);
1935 : : rearm3 = vdupq_n_u64(mbuf_initializer);
1936 : : }
1937 : :
1938 : : /* Checksum ol_flags will be cleared if mbuf is meta */
1939 : : if (cq0_w1 & BIT(11)) {
1940 : : uintptr_t wqe = vgetq_lane_u64(wqe01, 0);
1941 : : uintptr_t sa = vgetq_lane_u64(sa01, 0);
1942 : : uint16_t len = vget_lane_u16(lens, 0);
1943 : :
1944 : : cpth0 = (uintptr_t)mbuf0 + d_off;
1945 : :
1946 : : /* Free meta to aura */
1947 : : if (!(flags & NIX_RX_REAS_F) ||
1948 : : *(uint64_t *)cpth0 & BIT_ULL(15)) {
1949 : : /* Free meta to aura */
1950 : : NIX_PUSH_META_TO_FREE(mbuf0, laddr,
1951 : : &loff);
1952 : : mbuf01 = vsetq_lane_u64(wqe, mbuf01, 0);
1953 : : mbuf0 = (struct rte_mbuf *)wqe;
1954 : : } else if (flags & NIX_RX_REAS_F) {
1955 : : /* Update meta pool for full mode pkts */
1956 : : mbuf0->pool = meta_pool;
1957 : : }
1958 : :
1959 : : /* Update pkt_len and data_len */
1960 : : f0 = vsetq_lane_u16(len, f0, 2);
1961 : : f0 = vsetq_lane_u16(len, f0, 4);
1962 : :
1963 : : nix_sec_meta_to_mbuf(cq0_w1, cq0_w5, sa, cpth0,
1964 : : mbuf0, &f0, &ol_flags0,
1965 : : flags, &rearm0);
1966 : : code = vget_lane_u8(ucc, 0);
1967 : : ol_flags0 |= code ? (code > 1 ? ((uint64_t)code) << 1 : 0) :
1968 : : RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED;
1969 : :
1970 : : ol_flags0 |= ((uint64_t)(vget_lane_u8(ucc, 1)) << 18);
1971 : : }
1972 : :
1973 : : if (cq1_w1 & BIT(11)) {
1974 : : uintptr_t wqe = vgetq_lane_u64(wqe01, 1);
1975 : : uintptr_t sa = vgetq_lane_u64(sa01, 1);
1976 : : uint16_t len = vget_lane_u16(lens, 1);
1977 : :
1978 : : cpth1 = (uintptr_t)mbuf1 + d_off;
1979 : :
1980 : : /* Free meta to aura */
1981 : : if (!(flags & NIX_RX_REAS_F) ||
1982 : : *(uint64_t *)cpth1 & BIT_ULL(15)) {
1983 : : NIX_PUSH_META_TO_FREE(mbuf1, laddr,
1984 : : &loff);
1985 : : mbuf01 = vsetq_lane_u64(wqe, mbuf01, 1);
1986 : : mbuf1 = (struct rte_mbuf *)wqe;
1987 : : } else if (flags & NIX_RX_REAS_F) {
1988 : : /* Update meta pool for full mode pkts */
1989 : : mbuf1->pool = meta_pool;
1990 : : }
1991 : :
1992 : : /* Update pkt_len and data_len */
1993 : : f1 = vsetq_lane_u16(len, f1, 2);
1994 : : f1 = vsetq_lane_u16(len, f1, 4);
1995 : :
1996 : : nix_sec_meta_to_mbuf(cq1_w1, cq1_w5, sa, cpth1,
1997 : : mbuf1, &f1, &ol_flags1,
1998 : : flags, &rearm1);
1999 : : code = vget_lane_u8(ucc, 2);
2000 : : ol_flags1 |= code ? (code > 1 ? ((uint64_t)code) << 1 : 0) :
2001 : : RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED;
2002 : : ol_flags1 |= ((uint64_t)(vget_lane_u8(ucc, 3)) << 18);
2003 : : }
2004 : :
2005 : : if (cq2_w1 & BIT(11)) {
2006 : : uintptr_t wqe = vgetq_lane_u64(wqe23, 0);
2007 : : uintptr_t sa = vgetq_lane_u64(sa23, 0);
2008 : : uint16_t len = vget_lane_u16(lens, 2);
2009 : :
2010 : : cpth2 = (uintptr_t)mbuf2 + d_off;
2011 : :
2012 : : /* Free meta to aura */
2013 : : if (!(flags & NIX_RX_REAS_F) ||
2014 : : *(uint64_t *)cpth2 & BIT_ULL(15)) {
2015 : : NIX_PUSH_META_TO_FREE(mbuf2, laddr,
2016 : : &loff);
2017 : : mbuf23 = vsetq_lane_u64(wqe, mbuf23, 0);
2018 : : mbuf2 = (struct rte_mbuf *)wqe;
2019 : : } else if (flags & NIX_RX_REAS_F) {
2020 : : /* Update meta pool for full mode pkts */
2021 : : mbuf2->pool = meta_pool;
2022 : : }
2023 : :
2024 : : /* Update pkt_len and data_len */
2025 : : f2 = vsetq_lane_u16(len, f2, 2);
2026 : : f2 = vsetq_lane_u16(len, f2, 4);
2027 : :
2028 : : nix_sec_meta_to_mbuf(cq2_w1, cq2_w5, sa, cpth2,
2029 : : mbuf2, &f2, &ol_flags2,
2030 : : flags, &rearm2);
2031 : : code = vget_lane_u8(ucc, 4);
2032 : : ol_flags2 |= code ? (code > 1 ? ((uint64_t)code) << 1 : 0) :
2033 : : RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED;
2034 : : ol_flags2 |= ((uint64_t)(vget_lane_u8(ucc, 5)) << 18);
2035 : : }
2036 : :
2037 : : if (cq3_w1 & BIT(11)) {
2038 : : uintptr_t wqe = vgetq_lane_u64(wqe23, 1);
2039 : : uintptr_t sa = vgetq_lane_u64(sa23, 1);
2040 : : uint16_t len = vget_lane_u16(lens, 3);
2041 : :
2042 : : cpth3 = (uintptr_t)mbuf3 + d_off;
2043 : :
2044 : : /* Free meta to aura */
2045 : : if (!(flags & NIX_RX_REAS_F) ||
2046 : : *(uint64_t *)cpth3 & BIT_ULL(15)) {
2047 : : NIX_PUSH_META_TO_FREE(mbuf3, laddr,
2048 : : &loff);
2049 : : mbuf23 = vsetq_lane_u64(wqe, mbuf23, 1);
2050 : : mbuf3 = (struct rte_mbuf *)wqe;
2051 : : } else if (flags & NIX_RX_REAS_F) {
2052 : : /* Update meta pool for full mode pkts */
2053 : : mbuf3->pool = meta_pool;
2054 : : }
2055 : :
2056 : : /* Update pkt_len and data_len */
2057 : : f3 = vsetq_lane_u16(len, f3, 2);
2058 : : f3 = vsetq_lane_u16(len, f3, 4);
2059 : :
2060 : : nix_sec_meta_to_mbuf(cq3_w1, cq3_w5, sa, cpth3,
2061 : : mbuf3, &f3, &ol_flags3,
2062 : : flags, &rearm3);
2063 : : code = vget_lane_u8(ucc, 6);
2064 : : ol_flags3 |= code ? (code > 1 ? ((uint64_t)code) << 1 : 0) :
2065 : : RTE_MBUF_F_RX_SEC_OFFLOAD_FAILED;
2066 : : ol_flags3 |= ((uint64_t)(vget_lane_u8(ucc, 7)) << 18);
2067 : : }
2068 : : }
2069 : :
2070 : : if (flags & NIX_RX_OFFLOAD_VLAN_STRIP_F) {
2071 : :
2072 : : ol_flags0 = nix_vlan_update(cq0_w2, ol_flags0, &f0);
2073 : : ol_flags1 = nix_vlan_update(cq1_w2, ol_flags1, &f1);
2074 : : ol_flags2 = nix_vlan_update(cq2_w2, ol_flags2, &f2);
2075 : : ol_flags3 = nix_vlan_update(cq3_w2, ol_flags3, &f3);
2076 : :
2077 : : ol_flags0 = nix_qinq_update(cq0_w2, ol_flags0, mbuf0);
2078 : : ol_flags1 = nix_qinq_update(cq1_w2, ol_flags1, mbuf1);
2079 : : ol_flags2 = nix_qinq_update(cq2_w2, ol_flags2, mbuf2);
2080 : : ol_flags3 = nix_qinq_update(cq3_w2, ol_flags3, mbuf3);
2081 : : }
2082 : :
2083 : : if (flags & NIX_RX_OFFLOAD_MARK_UPDATE_F) {
2084 : : ol_flags0 = nix_update_match_id(
2085 : : *(uint16_t *)CQE_PTR_OFF(cq0, 0, 38, flags),
2086 : : ol_flags0, mbuf0);
2087 : : ol_flags1 = nix_update_match_id(
2088 : : *(uint16_t *)CQE_PTR_OFF(cq0, 1, 38, flags),
2089 : : ol_flags1, mbuf1);
2090 : : ol_flags2 = nix_update_match_id(
2091 : : *(uint16_t *)CQE_PTR_OFF(cq0, 2, 38, flags),
2092 : : ol_flags2, mbuf2);
2093 : : ol_flags3 = nix_update_match_id(
2094 : : *(uint16_t *)CQE_PTR_OFF(cq0, 3, 38, flags),
2095 : : ol_flags3, mbuf3);
2096 : : }
2097 : :
2098 : : if ((flags & NIX_RX_OFFLOAD_TSTAMP_F) &&
2099 : : ((flags & NIX_RX_VWQE_F) && tstamp)) {
2100 : : const uint16x8_t len_off = {
2101 : : 0, /* ptype 0:15 */
2102 : : 0, /* ptype 16:32 */
2103 : : CNXK_NIX_TIMESYNC_RX_OFFSET, /* pktlen 0:15*/
2104 : : 0, /* pktlen 16:32 */
2105 : : CNXK_NIX_TIMESYNC_RX_OFFSET, /* datalen 0:15 */
2106 : : 0,
2107 : : 0,
2108 : : 0};
2109 : : const uint32x4_t ptype = {RTE_PTYPE_L2_ETHER_TIMESYNC,
2110 : : RTE_PTYPE_L2_ETHER_TIMESYNC,
2111 : : RTE_PTYPE_L2_ETHER_TIMESYNC,
2112 : : RTE_PTYPE_L2_ETHER_TIMESYNC};
2113 : : const uint64_t ts_olf = RTE_MBUF_F_RX_IEEE1588_PTP |
2114 : : RTE_MBUF_F_RX_IEEE1588_TMST |
2115 : : tstamp->rx_tstamp_dynflag;
2116 : : const uint32x4_t and_mask = {0x1, 0x2, 0x4, 0x8};
2117 : : uint64x2_t ts01, ts23, mask;
2118 : : uint64_t ts[4];
2119 : : uint8_t res;
2120 : :
2121 : : /* Subtract timesync length from total pkt length. */
2122 : : f0 = vsubq_u16(f0, len_off);
2123 : : f1 = vsubq_u16(f1, len_off);
2124 : : f2 = vsubq_u16(f2, len_off);
2125 : : f3 = vsubq_u16(f3, len_off);
2126 : :
2127 : : /* Get the address of actual timestamp. */
2128 : : ts01 = vaddq_u64(mbuf01, data_off);
2129 : : ts23 = vaddq_u64(mbuf23, data_off);
2130 : : /* Load timestamp from address. */
2131 : : ts01 = vsetq_lane_u64(*(uint64_t *)vgetq_lane_u64(ts01,
2132 : : 0),
2133 : : ts01, 0);
2134 : : ts01 = vsetq_lane_u64(*(uint64_t *)vgetq_lane_u64(ts01,
2135 : : 1),
2136 : : ts01, 1);
2137 : : ts23 = vsetq_lane_u64(*(uint64_t *)vgetq_lane_u64(ts23,
2138 : : 0),
2139 : : ts23, 0);
2140 : : ts23 = vsetq_lane_u64(*(uint64_t *)vgetq_lane_u64(ts23,
2141 : : 1),
2142 : : ts23, 1);
2143 : : /* Convert from be to cpu byteorder. */
2144 : : ts01 = vrev64q_u8(ts01);
2145 : : ts23 = vrev64q_u8(ts23);
2146 : : /* Store timestamp into scalar for later use. */
2147 : : ts[0] = vgetq_lane_u64(ts01, 0);
2148 : : ts[1] = vgetq_lane_u64(ts01, 1);
2149 : : ts[2] = vgetq_lane_u64(ts23, 0);
2150 : : ts[3] = vgetq_lane_u64(ts23, 1);
2151 : :
2152 : : /* Store timestamp into dynfield. */
2153 : : *cnxk_nix_timestamp_dynfield(mbuf0, tstamp) = ts[0];
2154 : : *cnxk_nix_timestamp_dynfield(mbuf1, tstamp) = ts[1];
2155 : : *cnxk_nix_timestamp_dynfield(mbuf2, tstamp) = ts[2];
2156 : : *cnxk_nix_timestamp_dynfield(mbuf3, tstamp) = ts[3];
2157 : :
2158 : : /* Generate ptype mask to filter L2 ether timesync */
2159 : : mask = vdupq_n_u32(vgetq_lane_u32(f0, 0));
2160 : : mask = vsetq_lane_u32(vgetq_lane_u32(f1, 0), mask, 1);
2161 : : mask = vsetq_lane_u32(vgetq_lane_u32(f2, 0), mask, 2);
2162 : : mask = vsetq_lane_u32(vgetq_lane_u32(f3, 0), mask, 3);
2163 : :
2164 : : /* Match against L2 ether timesync. */
2165 : : mask = vceqq_u32(mask, ptype);
2166 : : /* Convert from vector from scalar mask */
2167 : : res = vaddvq_u32(vandq_u32(mask, and_mask));
2168 : : res &= 0xF;
2169 : :
2170 : : if (res) {
2171 : : /* Fill in the ol_flags for any packets that
2172 : : * matched.
2173 : : */
2174 : : ol_flags0 |= ((res & 0x1) ? ts_olf : 0);
2175 : : ol_flags1 |= ((res & 0x2) ? ts_olf : 0);
2176 : : ol_flags2 |= ((res & 0x4) ? ts_olf : 0);
2177 : : ol_flags3 |= ((res & 0x8) ? ts_olf : 0);
2178 : :
2179 : : /* Update Rxq timestamp with the latest
2180 : : * timestamp.
2181 : : */
2182 : : tstamp->rx_ready = 1;
2183 : : tstamp->rx_tstamp = ts[31 - rte_clz32(res)];
2184 : : }
2185 : : }
2186 : :
2187 : : /* Form rearm_data with ol_flags */
2188 : : rearm0 = vsetq_lane_u64(ol_flags0, rearm0, 1);
2189 : : rearm1 = vsetq_lane_u64(ol_flags1, rearm1, 1);
2190 : : rearm2 = vsetq_lane_u64(ol_flags2, rearm2, 1);
2191 : : rearm3 = vsetq_lane_u64(ol_flags3, rearm3, 1);
2192 : :
2193 : : /* Update rx_descriptor_fields1 */
2194 : : vst1q_u64((uint64_t *)mbuf0->rx_descriptor_fields1, f0);
2195 : : vst1q_u64((uint64_t *)mbuf1->rx_descriptor_fields1, f1);
2196 : : vst1q_u64((uint64_t *)mbuf2->rx_descriptor_fields1, f2);
2197 : : vst1q_u64((uint64_t *)mbuf3->rx_descriptor_fields1, f3);
2198 : :
2199 : : /* Update rearm_data */
2200 : : vst1q_u64((uint64_t *)mbuf0->rearm_data, rearm0);
2201 : : vst1q_u64((uint64_t *)mbuf1->rearm_data, rearm1);
2202 : : vst1q_u64((uint64_t *)mbuf2->rearm_data, rearm2);
2203 : : vst1q_u64((uint64_t *)mbuf3->rearm_data, rearm3);
2204 : :
2205 : : if (flags & NIX_RX_MULTI_SEG_F) {
2206 : : /* Multi segment is enable build mseg list for
2207 : : * individual mbufs in scalar mode.
2208 : : */
2209 : : nix_cqe_xtract_mseg((union nix_rx_parse_u *)
2210 : : (CQE_PTR_OFF(cq0, 0, 8, flags)),
2211 : : mbuf0, mbuf_initializer, cpth0, sa_base, flags);
2212 : : nix_cqe_xtract_mseg((union nix_rx_parse_u *)
2213 : : (CQE_PTR_OFF(cq0, 1, 8, flags)),
2214 : : mbuf1, mbuf_initializer, cpth1, sa_base, flags);
2215 : : nix_cqe_xtract_mseg((union nix_rx_parse_u *)
2216 : : (CQE_PTR_OFF(cq0, 2, 8, flags)),
2217 : : mbuf2, mbuf_initializer, cpth2, sa_base, flags);
2218 : : nix_cqe_xtract_mseg((union nix_rx_parse_u *)
2219 : : (CQE_PTR_OFF(cq0, 3, 8, flags)),
2220 : : mbuf3, mbuf_initializer, cpth3, sa_base, flags);
2221 : : }
2222 : :
2223 : : /* Store the mbufs to rx_pkts */
2224 : : vst1q_u64((uint64_t *)&mbufs[packets], mbuf01);
2225 : : vst1q_u64((uint64_t *)&mbufs[packets + 2], mbuf23);
2226 : :
2227 : : nix_mbuf_validate_next(mbuf0);
2228 : : nix_mbuf_validate_next(mbuf1);
2229 : : nix_mbuf_validate_next(mbuf2);
2230 : : nix_mbuf_validate_next(mbuf3);
2231 : :
2232 : : packets += NIX_DESCS_PER_LOOP;
2233 : :
2234 : : if (!(flags & NIX_RX_VWQE_F)) {
2235 : : /* Advance head pointer and packets */
2236 : : head += NIX_DESCS_PER_LOOP;
2237 : : head &= qmask;
2238 : : }
2239 : :
2240 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F) {
2241 : : /* Check if lmtline border is crossed and adjust lnum */
2242 : : if (loff > 15) {
2243 : : /* Update aura handle */
2244 : : *(uint64_t *)(laddr - 8) =
2245 : : (((uint64_t)(15 & 0x1) << 32) |
2246 : : roc_npa_aura_handle_to_aura(meta_aura));
2247 : : loff = loff - 15;
2248 : : shft += 3;
2249 : :
2250 : : lnum++;
2251 : : laddr = (uintptr_t)LMT_OFF(lbase, lnum, 8);
2252 : : /* Pick the pointer from 16th index and put it
2253 : : * at end of this new line.
2254 : : */
2255 : : *(uint64_t *)(laddr + (loff << 3) - 8) =
2256 : : *(uint64_t *)(laddr - 8);
2257 : : }
2258 : :
2259 : : /* Flush it when we are in 16th line and might
2260 : : * overflow it
2261 : : */
2262 : : if (lnum >= 15 && loff >= 12) {
2263 : : /* 16 LMT Line size m1 */
2264 : : uint64_t data = BIT_ULL(48) - 1;
2265 : :
2266 : : /* Update aura handle */
2267 : : *(uint64_t *)(laddr - 8) =
2268 : : (((uint64_t)(loff & 0x1) << 32) |
2269 : : roc_npa_aura_handle_to_aura(meta_aura));
2270 : :
2271 : : data = (data & ~(0x7UL << shft)) |
2272 : : (((uint64_t)loff >> 1) << shft);
2273 : :
2274 : : /* Send up to 16 lmt lines of pointers */
2275 : : nix_sec_flush_meta_burst(lmt_id, data, lnum + 1,
2276 : : meta_aura);
2277 : : rte_io_wmb();
2278 : : lnum = 0;
2279 : : loff = 0;
2280 : : shft = 0;
2281 : : /* First pointer starts at 8B offset */
2282 : : laddr = (uintptr_t)LMT_OFF(lbase, lnum, 8);
2283 : : }
2284 : : }
2285 : : }
2286 : :
2287 : : if (flags & NIX_RX_OFFLOAD_SECURITY_F && loff) {
2288 : : /* 16 LMT Line size m1 */
2289 : : uint64_t data = BIT_ULL(48) - 1;
2290 : :
2291 : : /* Update aura handle */
2292 : : *(uint64_t *)(laddr - 8) =
2293 : : (((uint64_t)(loff & 0x1) << 32) |
2294 : : roc_npa_aura_handle_to_aura(meta_aura));
2295 : :
2296 : : data = (data & ~(0x7UL << shft)) |
2297 : : (((uint64_t)loff >> 1) << shft);
2298 : :
2299 : : /* Send up to 16 lmt lines of pointers */
2300 : : nix_sec_flush_meta_burst(lmt_id, data, lnum + 1, meta_aura);
2301 : : if (flags & NIX_RX_VWQE_F)
2302 : : plt_io_wmb();
2303 : : }
2304 : :
2305 : : if (flags & NIX_RX_VWQE_F)
2306 : : return packets;
2307 : :
2308 : : rxq->head = head;
2309 : : rxq->available -= packets;
2310 : :
2311 : : rte_io_wmb();
2312 : : /* Free all the CQs that we've processed */
2313 : : plt_write64((rxq->wdata | packets), rxq->cq_door);
2314 : :
2315 : : if (unlikely(pkts_left))
2316 : : packets += cn10k_nix_recv_pkts(args, &mbufs[packets], pkts_left,
2317 : : flags);
2318 : :
2319 : : return packets;
2320 : : }
2321 : :
2322 : : #else
2323 : :
2324 : : static inline uint16_t
2325 : : cn10k_nix_recv_pkts_vector(void *args, struct rte_mbuf **mbufs, uint16_t pkts,
2326 : : const uint16_t flags, void *lookup_mem,
2327 : : struct cnxk_timesync_info *tstamp,
2328 : : uintptr_t lmt_base, uint64_t meta_aura)
2329 : : {
2330 : : RTE_SET_USED(args);
2331 : : RTE_SET_USED(mbufs);
2332 : : RTE_SET_USED(pkts);
2333 : : RTE_SET_USED(flags);
2334 : : RTE_SET_USED(lookup_mem);
2335 : : RTE_SET_USED(tstamp);
2336 : : RTE_SET_USED(lmt_base);
2337 : : RTE_SET_USED(meta_aura);
2338 : :
2339 : : return 0;
2340 : : }
2341 : :
2342 : : #endif
2343 : :
2344 : :
2345 : : #define RSS_F NIX_RX_OFFLOAD_RSS_F
2346 : : #define PTYPE_F NIX_RX_OFFLOAD_PTYPE_F
2347 : : #define CKSUM_F NIX_RX_OFFLOAD_CHECKSUM_F
2348 : : #define MARK_F NIX_RX_OFFLOAD_MARK_UPDATE_F
2349 : : #define TS_F NIX_RX_OFFLOAD_TSTAMP_F
2350 : : #define RX_VLAN_F NIX_RX_OFFLOAD_VLAN_STRIP_F
2351 : : #define R_SEC_F NIX_RX_OFFLOAD_SECURITY_F
2352 : :
2353 : : /* [R_SEC_F] [RX_VLAN_F] [TS] [MARK] [CKSUM] [PTYPE] [RSS] */
2354 : : #define NIX_RX_FASTPATH_MODES_0_15 \
2355 : : R(no_offload, NIX_RX_OFFLOAD_NONE) \
2356 : : R(rss, RSS_F) \
2357 : : R(ptype, PTYPE_F) \
2358 : : R(ptype_rss, PTYPE_F | RSS_F) \
2359 : : R(cksum, CKSUM_F) \
2360 : : R(cksum_rss, CKSUM_F | RSS_F) \
2361 : : R(cksum_ptype, CKSUM_F | PTYPE_F) \
2362 : : R(cksum_ptype_rss, CKSUM_F | PTYPE_F | RSS_F) \
2363 : : R(mark, MARK_F) \
2364 : : R(mark_rss, MARK_F | RSS_F) \
2365 : : R(mark_ptype, MARK_F | PTYPE_F) \
2366 : : R(mark_ptype_rss, MARK_F | PTYPE_F | RSS_F) \
2367 : : R(mark_cksum, MARK_F | CKSUM_F) \
2368 : : R(mark_cksum_rss, MARK_F | CKSUM_F | RSS_F) \
2369 : : R(mark_cksum_ptype, MARK_F | CKSUM_F | PTYPE_F) \
2370 : : R(mark_cksum_ptype_rss, MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2371 : :
2372 : : #define NIX_RX_FASTPATH_MODES_16_31 \
2373 : : R(ts, TS_F) \
2374 : : R(ts_rss, TS_F | RSS_F) \
2375 : : R(ts_ptype, TS_F | PTYPE_F) \
2376 : : R(ts_ptype_rss, TS_F | PTYPE_F | RSS_F) \
2377 : : R(ts_cksum, TS_F | CKSUM_F) \
2378 : : R(ts_cksum_rss, TS_F | CKSUM_F | RSS_F) \
2379 : : R(ts_cksum_ptype, TS_F | CKSUM_F | PTYPE_F) \
2380 : : R(ts_cksum_ptype_rss, TS_F | CKSUM_F | PTYPE_F | RSS_F) \
2381 : : R(ts_mark, TS_F | MARK_F) \
2382 : : R(ts_mark_rss, TS_F | MARK_F | RSS_F) \
2383 : : R(ts_mark_ptype, TS_F | MARK_F | PTYPE_F) \
2384 : : R(ts_mark_ptype_rss, TS_F | MARK_F | PTYPE_F | RSS_F) \
2385 : : R(ts_mark_cksum, TS_F | MARK_F | CKSUM_F) \
2386 : : R(ts_mark_cksum_rss, TS_F | MARK_F | CKSUM_F | RSS_F) \
2387 : : R(ts_mark_cksum_ptype, TS_F | MARK_F | CKSUM_F | PTYPE_F) \
2388 : : R(ts_mark_cksum_ptype_rss, TS_F | MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2389 : :
2390 : : #define NIX_RX_FASTPATH_MODES_32_47 \
2391 : : R(vlan, RX_VLAN_F) \
2392 : : R(vlan_rss, RX_VLAN_F | RSS_F) \
2393 : : R(vlan_ptype, RX_VLAN_F | PTYPE_F) \
2394 : : R(vlan_ptype_rss, RX_VLAN_F | PTYPE_F | RSS_F) \
2395 : : R(vlan_cksum, RX_VLAN_F | CKSUM_F) \
2396 : : R(vlan_cksum_rss, RX_VLAN_F | CKSUM_F | RSS_F) \
2397 : : R(vlan_cksum_ptype, RX_VLAN_F | CKSUM_F | PTYPE_F) \
2398 : : R(vlan_cksum_ptype_rss, RX_VLAN_F | CKSUM_F | PTYPE_F | RSS_F) \
2399 : : R(vlan_mark, RX_VLAN_F | MARK_F) \
2400 : : R(vlan_mark_rss, RX_VLAN_F | MARK_F | RSS_F) \
2401 : : R(vlan_mark_ptype, RX_VLAN_F | MARK_F | PTYPE_F) \
2402 : : R(vlan_mark_ptype_rss, RX_VLAN_F | MARK_F | PTYPE_F | RSS_F) \
2403 : : R(vlan_mark_cksum, RX_VLAN_F | MARK_F | CKSUM_F) \
2404 : : R(vlan_mark_cksum_rss, RX_VLAN_F | MARK_F | CKSUM_F | RSS_F) \
2405 : : R(vlan_mark_cksum_ptype, RX_VLAN_F | MARK_F | CKSUM_F | PTYPE_F) \
2406 : : R(vlan_mark_cksum_ptype_rss, \
2407 : : RX_VLAN_F | MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2408 : :
2409 : : #define NIX_RX_FASTPATH_MODES_48_63 \
2410 : : R(vlan_ts, RX_VLAN_F | TS_F) \
2411 : : R(vlan_ts_rss, RX_VLAN_F | TS_F | RSS_F) \
2412 : : R(vlan_ts_ptype, RX_VLAN_F | TS_F | PTYPE_F) \
2413 : : R(vlan_ts_ptype_rss, RX_VLAN_F | TS_F | PTYPE_F | RSS_F) \
2414 : : R(vlan_ts_cksum, RX_VLAN_F | TS_F | CKSUM_F) \
2415 : : R(vlan_ts_cksum_rss, RX_VLAN_F | TS_F | CKSUM_F | RSS_F) \
2416 : : R(vlan_ts_cksum_ptype, RX_VLAN_F | TS_F | CKSUM_F | PTYPE_F) \
2417 : : R(vlan_ts_cksum_ptype_rss, \
2418 : : RX_VLAN_F | TS_F | CKSUM_F | PTYPE_F | RSS_F) \
2419 : : R(vlan_ts_mark, RX_VLAN_F | TS_F | MARK_F) \
2420 : : R(vlan_ts_mark_rss, RX_VLAN_F | TS_F | MARK_F | RSS_F) \
2421 : : R(vlan_ts_mark_ptype, RX_VLAN_F | TS_F | MARK_F | PTYPE_F) \
2422 : : R(vlan_ts_mark_ptype_rss, RX_VLAN_F | TS_F | MARK_F | PTYPE_F | RSS_F) \
2423 : : R(vlan_ts_mark_cksum, RX_VLAN_F | TS_F | MARK_F | CKSUM_F) \
2424 : : R(vlan_ts_mark_cksum_rss, RX_VLAN_F | TS_F | MARK_F | CKSUM_F | RSS_F) \
2425 : : R(vlan_ts_mark_cksum_ptype, \
2426 : : RX_VLAN_F | TS_F | MARK_F | CKSUM_F | PTYPE_F) \
2427 : : R(vlan_ts_mark_cksum_ptype_rss, \
2428 : : RX_VLAN_F | TS_F | MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2429 : :
2430 : : #define NIX_RX_FASTPATH_MODES_64_79 \
2431 : : R(sec, R_SEC_F) \
2432 : : R(sec_rss, R_SEC_F | RSS_F) \
2433 : : R(sec_ptype, R_SEC_F | PTYPE_F) \
2434 : : R(sec_ptype_rss, R_SEC_F | PTYPE_F | RSS_F) \
2435 : : R(sec_cksum, R_SEC_F | CKSUM_F) \
2436 : : R(sec_cksum_rss, R_SEC_F | CKSUM_F | RSS_F) \
2437 : : R(sec_cksum_ptype, R_SEC_F | CKSUM_F | PTYPE_F) \
2438 : : R(sec_cksum_ptype_rss, R_SEC_F | CKSUM_F | PTYPE_F | RSS_F) \
2439 : : R(sec_mark, R_SEC_F | MARK_F) \
2440 : : R(sec_mark_rss, R_SEC_F | MARK_F | RSS_F) \
2441 : : R(sec_mark_ptype, R_SEC_F | MARK_F | PTYPE_F) \
2442 : : R(sec_mark_ptype_rss, R_SEC_F | MARK_F | PTYPE_F | RSS_F) \
2443 : : R(sec_mark_cksum, R_SEC_F | MARK_F | CKSUM_F) \
2444 : : R(sec_mark_cksum_rss, R_SEC_F | MARK_F | CKSUM_F | RSS_F) \
2445 : : R(sec_mark_cksum_ptype, R_SEC_F | MARK_F | CKSUM_F | PTYPE_F) \
2446 : : R(sec_mark_cksum_ptype_rss, \
2447 : : R_SEC_F | MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2448 : :
2449 : : #define NIX_RX_FASTPATH_MODES_80_95 \
2450 : : R(sec_ts, R_SEC_F | TS_F) \
2451 : : R(sec_ts_rss, R_SEC_F | TS_F | RSS_F) \
2452 : : R(sec_ts_ptype, R_SEC_F | TS_F | PTYPE_F) \
2453 : : R(sec_ts_ptype_rss, R_SEC_F | TS_F | PTYPE_F | RSS_F) \
2454 : : R(sec_ts_cksum, R_SEC_F | TS_F | CKSUM_F) \
2455 : : R(sec_ts_cksum_rss, R_SEC_F | TS_F | CKSUM_F | RSS_F) \
2456 : : R(sec_ts_cksum_ptype, R_SEC_F | TS_F | CKSUM_F | PTYPE_F) \
2457 : : R(sec_ts_cksum_ptype_rss, R_SEC_F | TS_F | CKSUM_F | PTYPE_F | RSS_F) \
2458 : : R(sec_ts_mark, R_SEC_F | TS_F | MARK_F) \
2459 : : R(sec_ts_mark_rss, R_SEC_F | TS_F | MARK_F | RSS_F) \
2460 : : R(sec_ts_mark_ptype, R_SEC_F | TS_F | MARK_F | PTYPE_F) \
2461 : : R(sec_ts_mark_ptype_rss, R_SEC_F | TS_F | MARK_F | PTYPE_F | RSS_F) \
2462 : : R(sec_ts_mark_cksum, R_SEC_F | TS_F | MARK_F | CKSUM_F) \
2463 : : R(sec_ts_mark_cksum_rss, R_SEC_F | TS_F | MARK_F | CKSUM_F | RSS_F) \
2464 : : R(sec_ts_mark_cksum_ptype, \
2465 : : R_SEC_F | TS_F | MARK_F | CKSUM_F | PTYPE_F) \
2466 : : R(sec_ts_mark_cksum_ptype_rss, \
2467 : : R_SEC_F | TS_F | MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2468 : :
2469 : : #define NIX_RX_FASTPATH_MODES_96_111 \
2470 : : R(sec_vlan, R_SEC_F | RX_VLAN_F) \
2471 : : R(sec_vlan_rss, R_SEC_F | RX_VLAN_F | RSS_F) \
2472 : : R(sec_vlan_ptype, R_SEC_F | RX_VLAN_F | PTYPE_F) \
2473 : : R(sec_vlan_ptype_rss, R_SEC_F | RX_VLAN_F | PTYPE_F | RSS_F) \
2474 : : R(sec_vlan_cksum, R_SEC_F | RX_VLAN_F | CKSUM_F) \
2475 : : R(sec_vlan_cksum_rss, R_SEC_F | RX_VLAN_F | CKSUM_F | RSS_F) \
2476 : : R(sec_vlan_cksum_ptype, R_SEC_F | RX_VLAN_F | CKSUM_F | PTYPE_F) \
2477 : : R(sec_vlan_cksum_ptype_rss, \
2478 : : R_SEC_F | RX_VLAN_F | CKSUM_F | PTYPE_F | RSS_F) \
2479 : : R(sec_vlan_mark, R_SEC_F | RX_VLAN_F | MARK_F) \
2480 : : R(sec_vlan_mark_rss, R_SEC_F | RX_VLAN_F | MARK_F | RSS_F) \
2481 : : R(sec_vlan_mark_ptype, R_SEC_F | RX_VLAN_F | MARK_F | PTYPE_F) \
2482 : : R(sec_vlan_mark_ptype_rss, \
2483 : : R_SEC_F | RX_VLAN_F | MARK_F | PTYPE_F | RSS_F) \
2484 : : R(sec_vlan_mark_cksum, R_SEC_F | RX_VLAN_F | MARK_F | CKSUM_F) \
2485 : : R(sec_vlan_mark_cksum_rss, \
2486 : : R_SEC_F | RX_VLAN_F | MARK_F | CKSUM_F | RSS_F) \
2487 : : R(sec_vlan_mark_cksum_ptype, \
2488 : : R_SEC_F | RX_VLAN_F | MARK_F | CKSUM_F | PTYPE_F) \
2489 : : R(sec_vlan_mark_cksum_ptype_rss, \
2490 : : R_SEC_F | RX_VLAN_F | MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2491 : :
2492 : : #define NIX_RX_FASTPATH_MODES_112_127 \
2493 : : R(sec_vlan_ts, R_SEC_F | RX_VLAN_F | TS_F) \
2494 : : R(sec_vlan_ts_rss, R_SEC_F | RX_VLAN_F | TS_F | RSS_F) \
2495 : : R(sec_vlan_ts_ptype, R_SEC_F | RX_VLAN_F | TS_F | PTYPE_F) \
2496 : : R(sec_vlan_ts_ptype_rss, R_SEC_F | RX_VLAN_F | TS_F | PTYPE_F | RSS_F) \
2497 : : R(sec_vlan_ts_cksum, R_SEC_F | RX_VLAN_F | TS_F | CKSUM_F) \
2498 : : R(sec_vlan_ts_cksum_rss, R_SEC_F | RX_VLAN_F | TS_F | CKSUM_F | RSS_F) \
2499 : : R(sec_vlan_ts_cksum_ptype, \
2500 : : R_SEC_F | RX_VLAN_F | TS_F | CKSUM_F | PTYPE_F) \
2501 : : R(sec_vlan_ts_cksum_ptype_rss, \
2502 : : R_SEC_F | RX_VLAN_F | TS_F | CKSUM_F | PTYPE_F | RSS_F) \
2503 : : R(sec_vlan_ts_mark, R_SEC_F | RX_VLAN_F | TS_F | MARK_F) \
2504 : : R(sec_vlan_ts_mark_rss, R_SEC_F | RX_VLAN_F | TS_F | MARK_F | RSS_F) \
2505 : : R(sec_vlan_ts_mark_ptype, \
2506 : : R_SEC_F | RX_VLAN_F | TS_F | MARK_F | PTYPE_F) \
2507 : : R(sec_vlan_ts_mark_ptype_rss, \
2508 : : R_SEC_F | RX_VLAN_F | TS_F | MARK_F | PTYPE_F | RSS_F) \
2509 : : R(sec_vlan_ts_mark_cksum, \
2510 : : R_SEC_F | RX_VLAN_F | TS_F | MARK_F | CKSUM_F) \
2511 : : R(sec_vlan_ts_mark_cksum_rss, \
2512 : : R_SEC_F | RX_VLAN_F | TS_F | MARK_F | CKSUM_F | RSS_F) \
2513 : : R(sec_vlan_ts_mark_cksum_ptype, \
2514 : : R_SEC_F | RX_VLAN_F | TS_F | MARK_F | CKSUM_F | PTYPE_F) \
2515 : : R(sec_vlan_ts_mark_cksum_ptype_rss, \
2516 : : R_SEC_F | RX_VLAN_F | TS_F | MARK_F | CKSUM_F | PTYPE_F | RSS_F)
2517 : :
2518 : :
2519 : : #define NIX_RX_FASTPATH_MODES \
2520 : : NIX_RX_FASTPATH_MODES_0_15 \
2521 : : NIX_RX_FASTPATH_MODES_16_31 \
2522 : : NIX_RX_FASTPATH_MODES_32_47 \
2523 : : NIX_RX_FASTPATH_MODES_48_63 \
2524 : : NIX_RX_FASTPATH_MODES_64_79 \
2525 : : NIX_RX_FASTPATH_MODES_80_95 \
2526 : : NIX_RX_FASTPATH_MODES_96_111 \
2527 : : NIX_RX_FASTPATH_MODES_112_127 \
2528 : :
2529 : : #define R(name, flags) \
2530 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_##name( \
2531 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts); \
2532 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_mseg_##name( \
2533 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts); \
2534 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_vec_##name( \
2535 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts); \
2536 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_vec_mseg_##name( \
2537 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts); \
2538 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_reas_##name( \
2539 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts); \
2540 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_reas_mseg_##name(\
2541 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts); \
2542 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_reas_vec_##name( \
2543 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts); \
2544 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_reas_vec_mseg_##name( \
2545 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts);
2546 : :
2547 : : NIX_RX_FASTPATH_MODES
2548 : : #undef R
2549 : :
2550 : : #define NIX_RX_RECV(fn, flags) \
2551 : : uint16_t __rte_noinline __rte_hot fn( \
2552 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts) \
2553 : : { \
2554 : : return cn10k_nix_recv_pkts(rx_queue, rx_pkts, pkts, (flags)); \
2555 : : }
2556 : :
2557 : : #define NIX_RX_RECV_MSEG(fn, flags) NIX_RX_RECV(fn, flags | NIX_RX_MULTI_SEG_F)
2558 : :
2559 : : #define NIX_RX_RECV_VEC(fn, flags) \
2560 : : uint16_t __rte_noinline __rte_hot fn( \
2561 : : void *rx_queue, struct rte_mbuf **rx_pkts, uint16_t pkts) \
2562 : : { \
2563 : : return cn10k_nix_recv_pkts_vector(rx_queue, rx_pkts, pkts, \
2564 : : (flags), NULL, NULL, 0, 0); \
2565 : : }
2566 : :
2567 : : #define NIX_RX_RECV_VEC_MSEG(fn, flags) \
2568 : : NIX_RX_RECV_VEC(fn, flags | NIX_RX_MULTI_SEG_F)
2569 : :
2570 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_all_offload(void *rx_queue,
2571 : : struct rte_mbuf **rx_pkts,
2572 : : uint16_t pkts);
2573 : :
2574 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_vec_all_offload(void *rx_queue,
2575 : : struct rte_mbuf **rx_pkts,
2576 : : uint16_t pkts);
2577 : :
2578 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_all_offload_tst(void *rx_queue,
2579 : : struct rte_mbuf **rx_pkts,
2580 : : uint16_t pkts);
2581 : :
2582 : : uint16_t __rte_noinline __rte_hot cn10k_nix_recv_pkts_vec_all_offload_tst(void *rx_queue,
2583 : : struct rte_mbuf **rx_pkts,
2584 : : uint16_t pkts);
2585 : :
2586 : : #endif /* __CN10K_RX_H__ */
|