Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause
2 : : * Copyright(C) 2024 Marvell.
3 : : */
4 : :
5 : : #include <rte_cryptodev.h>
6 : : #include <rte_eventdev.h>
7 : : #include <rte_pmd_cnxk.h>
8 : : #include <rte_security.h>
9 : : #include <rte_security_driver.h>
10 : :
11 : : #include <cn20k_ethdev.h>
12 : : #include <cn20k_rx.h>
13 : : #include <cnxk_security.h>
14 : : #include <roc_priv.h>
15 : :
16 : : PLT_STATIC_ASSERT(offsetof(struct rte_pmd_cnxk_ipsec_inb_sa, ctx.ar_winbits) ==
17 : : offsetof(struct roc_ow_ipsec_inb_sa, ctx.ar_winbits));
18 : :
19 : : PLT_STATIC_ASSERT(offsetof(struct rte_pmd_cnxk_ipsec_outb_sa, ctx.mib_pkts) ==
20 : : offsetof(struct roc_ow_ipsec_outb_sa, ctx.mib_pkts));
21 : :
22 : : PLT_STATIC_ASSERT(RTE_PMD_CNXK_CTX_MAX_CKEY_LEN == ROC_CTX_MAX_CKEY_LEN);
23 : : PLT_STATIC_ASSERT(RTE_PMD_CNXK_CTX_MAX_OPAD_IPAD_LEN == RTE_PMD_CNXK_CTX_MAX_OPAD_IPAD_LEN);
24 : :
25 : : PLT_STATIC_ASSERT(RTE_PMD_CNXK_AR_WIN_SIZE_MIN == ROC_AR_WIN_SIZE_MIN);
26 : : PLT_STATIC_ASSERT(RTE_PMD_CNXK_AR_WIN_SIZE_MAX == ROC_AR_WIN_SIZE_MAX);
27 : : PLT_STATIC_ASSERT(RTE_PMD_CNXK_LOG_MIN_AR_WIN_SIZE_M1 == ROC_LOG_MIN_AR_WIN_SIZE_M1);
28 : : PLT_STATIC_ASSERT(RTE_PMD_CNXK_AR_WINBITS_SZ == ROC_AR_WINBITS_SZ);
29 : :
30 : : static struct rte_cryptodev_capabilities cn20k_eth_sec_crypto_caps[] = {
31 : : { /* AES GCM */
32 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
33 : : {.sym = {
34 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AEAD,
35 : : {.aead = {
36 : : .algo = RTE_CRYPTO_AEAD_AES_GCM,
37 : : .block_size = 16,
38 : : .key_size = {
39 : : .min = 16,
40 : : .max = 32,
41 : : .increment = 8
42 : : },
43 : : .digest_size = {
44 : : .min = 16,
45 : : .max = 16,
46 : : .increment = 0
47 : : },
48 : : .aad_size = {
49 : : .min = 8,
50 : : .max = 12,
51 : : .increment = 4
52 : : },
53 : : .iv_size = {
54 : : .min = 12,
55 : : .max = 12,
56 : : .increment = 0
57 : : }
58 : : }, }
59 : : }, }
60 : : },
61 : : { /* AES CBC */
62 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
63 : : {.sym = {
64 : : .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER,
65 : : {.cipher = {
66 : : .algo = RTE_CRYPTO_CIPHER_AES_CBC,
67 : : .block_size = 16,
68 : : .key_size = {
69 : : .min = 16,
70 : : .max = 32,
71 : : .increment = 8
72 : : },
73 : : .iv_size = {
74 : : .min = 16,
75 : : .max = 16,
76 : : .increment = 0
77 : : }
78 : : }, }
79 : : }, }
80 : : },
81 : : { /* AES CTR */
82 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
83 : : {.sym = {
84 : : .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER,
85 : : {.cipher = {
86 : : .algo = RTE_CRYPTO_CIPHER_AES_CTR,
87 : : .block_size = 16,
88 : : .key_size = {
89 : : .min = 16,
90 : : .max = 32,
91 : : .increment = 8
92 : : },
93 : : .iv_size = {
94 : : .min = 12,
95 : : .max = 16,
96 : : .increment = 4
97 : : }
98 : : }, }
99 : : }, }
100 : : },
101 : : { /* 3DES CBC */
102 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
103 : : {.sym = {
104 : : .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER,
105 : : {.cipher = {
106 : : .algo = RTE_CRYPTO_CIPHER_3DES_CBC,
107 : : .block_size = 8,
108 : : .key_size = {
109 : : .min = 24,
110 : : .max = 24,
111 : : .increment = 0
112 : : },
113 : : .iv_size = {
114 : : .min = 8,
115 : : .max = 16,
116 : : .increment = 8
117 : : }
118 : : }, }
119 : : }, }
120 : : },
121 : : { /* AES-XCBC */
122 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
123 : : { .sym = {
124 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH,
125 : : {.auth = {
126 : : .algo = RTE_CRYPTO_AUTH_AES_XCBC_MAC,
127 : : .block_size = 16,
128 : : .key_size = {
129 : : .min = 16,
130 : : .max = 16,
131 : : .increment = 0
132 : : },
133 : : .digest_size = {
134 : : .min = 12,
135 : : .max = 12,
136 : : .increment = 0,
137 : : },
138 : : }, }
139 : : }, }
140 : : },
141 : : { /* SHA1 HMAC */
142 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
143 : : {.sym = {
144 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH,
145 : : {.auth = {
146 : : .algo = RTE_CRYPTO_AUTH_SHA1_HMAC,
147 : : .block_size = 64,
148 : : .key_size = {
149 : : .min = 20,
150 : : .max = 64,
151 : : .increment = 1
152 : : },
153 : : .digest_size = {
154 : : .min = 12,
155 : : .max = 12,
156 : : .increment = 0
157 : : },
158 : : }, }
159 : : }, }
160 : : },
161 : : { /* SHA256 HMAC */
162 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
163 : : {.sym = {
164 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH,
165 : : {.auth = {
166 : : .algo = RTE_CRYPTO_AUTH_SHA256_HMAC,
167 : : .block_size = 64,
168 : : .key_size = {
169 : : .min = 1,
170 : : .max = 1024,
171 : : .increment = 1
172 : : },
173 : : .digest_size = {
174 : : .min = 16,
175 : : .max = 32,
176 : : .increment = 16
177 : : },
178 : : }, }
179 : : }, }
180 : : },
181 : : { /* SHA384 HMAC */
182 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
183 : : {.sym = {
184 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH,
185 : : {.auth = {
186 : : .algo = RTE_CRYPTO_AUTH_SHA384_HMAC,
187 : : .block_size = 64,
188 : : .key_size = {
189 : : .min = 1,
190 : : .max = 1024,
191 : : .increment = 1
192 : : },
193 : : .digest_size = {
194 : : .min = 24,
195 : : .max = 48,
196 : : .increment = 24
197 : : },
198 : : }, }
199 : : }, }
200 : : },
201 : : { /* SHA512 HMAC */
202 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
203 : : {.sym = {
204 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH,
205 : : {.auth = {
206 : : .algo = RTE_CRYPTO_AUTH_SHA512_HMAC,
207 : : .block_size = 128,
208 : : .key_size = {
209 : : .min = 1,
210 : : .max = 1024,
211 : : .increment = 1
212 : : },
213 : : .digest_size = {
214 : : .min = 32,
215 : : .max = 64,
216 : : .increment = 32
217 : : },
218 : : }, }
219 : : }, }
220 : : },
221 : : { /* AES GMAC (AUTH) */
222 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
223 : : {.sym = {
224 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH,
225 : : {.auth = {
226 : : .algo = RTE_CRYPTO_AUTH_AES_GMAC,
227 : : .block_size = 16,
228 : : .key_size = {
229 : : .min = 16,
230 : : .max = 32,
231 : : .increment = 8
232 : : },
233 : : .digest_size = {
234 : : .min = 8,
235 : : .max = 16,
236 : : .increment = 4
237 : : },
238 : : .iv_size = {
239 : : .min = 12,
240 : : .max = 12,
241 : : .increment = 0
242 : : }
243 : : }, }
244 : : }, }
245 : : },
246 : : { /* AES CCM */
247 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
248 : : {.sym = {
249 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AEAD,
250 : : {.aead = {
251 : : .algo = RTE_CRYPTO_AEAD_AES_CCM,
252 : : .block_size = 16,
253 : : .key_size = {
254 : : .min = 16,
255 : : .max = 32,
256 : : .increment = 8
257 : : },
258 : : .digest_size = {
259 : : .min = 16,
260 : : .max = 16,
261 : : .increment = 0
262 : : },
263 : : .aad_size = {
264 : : .min = 8,
265 : : .max = 12,
266 : : .increment = 4
267 : : },
268 : : .iv_size = {
269 : : .min = 11,
270 : : .max = 13,
271 : : .increment = 1
272 : : }
273 : : }, }
274 : : }, }
275 : : },
276 : : { /* NULL (AUTH) */
277 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
278 : : {.sym = {
279 : : .xform_type = RTE_CRYPTO_SYM_XFORM_AUTH,
280 : : {.auth = {
281 : : .algo = RTE_CRYPTO_AUTH_NULL,
282 : : .block_size = 1,
283 : : .key_size = {
284 : : .min = 0,
285 : : .max = 0,
286 : : .increment = 0
287 : : },
288 : : .digest_size = {
289 : : .min = 0,
290 : : .max = 0,
291 : : .increment = 0
292 : : },
293 : : }, },
294 : : }, },
295 : : },
296 : : { /* NULL (CIPHER) */
297 : : .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
298 : : {.sym = {
299 : : .xform_type = RTE_CRYPTO_SYM_XFORM_CIPHER,
300 : : {.cipher = {
301 : : .algo = RTE_CRYPTO_CIPHER_NULL,
302 : : .block_size = 1,
303 : : .key_size = {
304 : : .min = 0,
305 : : .max = 0,
306 : : .increment = 0
307 : : },
308 : : .iv_size = {
309 : : .min = 0,
310 : : .max = 0,
311 : : .increment = 0
312 : : }
313 : : }, },
314 : : }, }
315 : : },
316 : :
317 : : RTE_CRYPTODEV_END_OF_CAPABILITIES_LIST()
318 : : };
319 : :
320 : : static const struct rte_security_capability cn20k_eth_sec_ipsec_capabilities[] = {
321 : : { /* IPsec Inline Protocol ESP Tunnel Ingress */
322 : : .action = RTE_SECURITY_ACTION_TYPE_INLINE_PROTOCOL,
323 : : .protocol = RTE_SECURITY_PROTOCOL_IPSEC,
324 : : .ipsec = {
325 : : .proto = RTE_SECURITY_IPSEC_SA_PROTO_ESP,
326 : : .mode = RTE_SECURITY_IPSEC_SA_MODE_TUNNEL,
327 : : .direction = RTE_SECURITY_IPSEC_SA_DIR_INGRESS,
328 : : .replay_win_sz_max = ROC_AR_WIN_SIZE_MAX,
329 : : .options = {
330 : : .udp_encap = 1,
331 : : .udp_ports_verify = 1,
332 : : .copy_df = 1,
333 : : .copy_dscp = 1,
334 : : .copy_flabel = 1,
335 : : .tunnel_hdr_verify = RTE_SECURITY_IPSEC_TUNNEL_VERIFY_SRC_DST_ADDR,
336 : : .dec_ttl = 1,
337 : : .ip_csum_enable = 1,
338 : : .l4_csum_enable = 1,
339 : : .stats = 1,
340 : : .esn = 1,
341 : : .ingress_oop = 1,
342 : : },
343 : : },
344 : : .crypto_capabilities = cn20k_eth_sec_crypto_caps,
345 : : .ol_flags = RTE_SECURITY_TX_OLOAD_NEED_MDATA
346 : : },
347 : : { /* IPsec Inline Protocol ESP Tunnel Egress */
348 : : .action = RTE_SECURITY_ACTION_TYPE_INLINE_PROTOCOL,
349 : : .protocol = RTE_SECURITY_PROTOCOL_IPSEC,
350 : : .ipsec = {
351 : : .proto = RTE_SECURITY_IPSEC_SA_PROTO_ESP,
352 : : .mode = RTE_SECURITY_IPSEC_SA_MODE_TUNNEL,
353 : : .direction = RTE_SECURITY_IPSEC_SA_DIR_EGRESS,
354 : : .replay_win_sz_max = ROC_AR_WIN_SIZE_MAX,
355 : : .options = {
356 : : .iv_gen_disable = 1,
357 : : .udp_encap = 1,
358 : : .udp_ports_verify = 1,
359 : : .copy_df = 1,
360 : : .copy_dscp = 1,
361 : : .copy_flabel = 1,
362 : : .dec_ttl = 1,
363 : : .ip_csum_enable = 1,
364 : : .l4_csum_enable = 1,
365 : : .stats = 1,
366 : : .esn = 1,
367 : : },
368 : : },
369 : : .crypto_capabilities = cn20k_eth_sec_crypto_caps,
370 : : .ol_flags = RTE_SECURITY_TX_OLOAD_NEED_MDATA
371 : : },
372 : : { /* IPsec Inline Protocol ESP Transport Egress */
373 : : .action = RTE_SECURITY_ACTION_TYPE_INLINE_PROTOCOL,
374 : : .protocol = RTE_SECURITY_PROTOCOL_IPSEC,
375 : : .ipsec = {
376 : : .proto = RTE_SECURITY_IPSEC_SA_PROTO_ESP,
377 : : .mode = RTE_SECURITY_IPSEC_SA_MODE_TRANSPORT,
378 : : .direction = RTE_SECURITY_IPSEC_SA_DIR_EGRESS,
379 : : .replay_win_sz_max = ROC_AR_WIN_SIZE_MAX,
380 : : .options = {
381 : : .iv_gen_disable = 1,
382 : : .udp_encap = 1,
383 : : .udp_ports_verify = 1,
384 : : .copy_df = 1,
385 : : .copy_dscp = 1,
386 : : .dec_ttl = 1,
387 : : .ip_csum_enable = 1,
388 : : .l4_csum_enable = 1,
389 : : .stats = 1,
390 : : .esn = 1,
391 : : .ingress_oop = 1,
392 : : },
393 : : },
394 : : .crypto_capabilities = cn20k_eth_sec_crypto_caps,
395 : : .ol_flags = RTE_SECURITY_TX_OLOAD_NEED_MDATA
396 : : },
397 : : { /* IPsec Inline Protocol ESP Transport Ingress */
398 : : .action = RTE_SECURITY_ACTION_TYPE_INLINE_PROTOCOL,
399 : : .protocol = RTE_SECURITY_PROTOCOL_IPSEC,
400 : : .ipsec = {
401 : : .proto = RTE_SECURITY_IPSEC_SA_PROTO_ESP,
402 : : .mode = RTE_SECURITY_IPSEC_SA_MODE_TRANSPORT,
403 : : .direction = RTE_SECURITY_IPSEC_SA_DIR_INGRESS,
404 : : .replay_win_sz_max = ROC_AR_WIN_SIZE_MAX,
405 : : .options = {
406 : : .udp_encap = 1,
407 : : .udp_ports_verify = 1,
408 : : .copy_df = 1,
409 : : .copy_dscp = 1,
410 : : .dec_ttl = 1,
411 : : .ip_csum_enable = 1,
412 : : .l4_csum_enable = 1,
413 : : .stats = 1,
414 : : .esn = 1,
415 : : .ingress_oop = 1,
416 : : },
417 : : },
418 : : .crypto_capabilities = cn20k_eth_sec_crypto_caps,
419 : : .ol_flags = RTE_SECURITY_TX_OLOAD_NEED_MDATA
420 : : },
421 : : };
422 : :
423 : : #define SEC_CAPS_LEN (RTE_DIM(cn20k_eth_sec_ipsec_capabilities) + 1)
424 : :
425 : : static struct rte_security_capability cn20k_eth_sec_capabilities[SEC_CAPS_LEN];
426 : :
427 : : static inline void
428 : : cnxk_pktmbuf_free_no_cache(struct rte_mbuf *mbuf)
429 : : {
430 : : struct rte_mbuf *next;
431 : :
432 [ # # # # ]: 0 : if (!mbuf)
433 : : return;
434 : : do {
435 : 0 : next = mbuf->next;
436 [ # # # # ]: 0 : roc_npa_aura_op_free(mbuf->pool->pool_id, 1, (rte_iova_t)mbuf);
437 : : mbuf = next;
438 [ # # # # ]: 0 : } while (mbuf != NULL);
439 : : }
440 : :
441 : : static void
442 [ # # ]: 0 : cn20k_eth_sec_post_event(struct rte_eth_dev *eth_dev, void *sa, enum nix_inl_event_type type,
443 : : uint16_t uc_compcode, uint16_t compcode, struct rte_mbuf *mbuf)
444 : : {
445 : : struct rte_eth_event_ipsec_desc desc;
446 : : struct cn20k_sec_sess_priv sess_priv;
447 : : struct cn20k_outb_priv_data *outb_priv;
448 : : struct cn20k_inb_priv_data *inb_priv;
449 : : static uint64_t warn_cnt;
450 : : uint64_t life_unit;
451 : :
452 : : memset(&desc, 0, sizeof(desc));
453 : 0 : sess_priv.u64 = 0;
454 : :
455 [ # # ]: 0 : if (type == NIX_INL_INB_CPT_CQ) {
456 : : struct roc_ow_ipsec_inb_sa *inb_sa = (struct roc_ow_ipsec_inb_sa *)sa;
457 : : inb_priv = roc_nix_inl_ow_ipsec_inb_sa_sw_rsvd(sa);
458 : 0 : desc.metadata = (uint64_t)inb_priv->userdata;
459 : 0 : life_unit = inb_sa->w2.s.life_unit;
460 : : } else {
461 : : struct roc_ow_ipsec_outb_sa *outb_sa = (struct roc_ow_ipsec_outb_sa *)sa;
462 : : outb_priv = roc_nix_inl_ow_ipsec_outb_sa_sw_rsvd(sa);
463 : 0 : desc.metadata = (uint64_t)outb_priv->userdata;
464 : 0 : life_unit = outb_sa->w2.s.life_unit;
465 : : }
466 : :
467 [ # # ]: 0 : if (mbuf)
468 : 0 : sess_priv.u64 = *rte_security_dynfield(mbuf);
469 : :
470 [ # # # # : 0 : switch (uc_compcode) {
# ]
471 : 0 : case ROC_IE_OW_UCC_ERR_SA_OVERFLOW:
472 : 0 : desc.subtype = RTE_ETH_EVENT_IPSEC_ESN_OVERFLOW;
473 : 0 : break;
474 : 0 : case ROC_IE_OW_UCC_ERR_SA_EXPIRED:
475 [ # # ]: 0 : if (life_unit == ROC_IE_OW_SA_LIFE_UNIT_PKTS)
476 : 0 : desc.subtype = RTE_ETH_EVENT_IPSEC_SA_PKT_HARD_EXPIRY;
477 : : else
478 : 0 : desc.subtype = RTE_ETH_EVENT_IPSEC_SA_BYTE_HARD_EXPIRY;
479 : : break;
480 : 0 : case ROC_IE_OW_UCC_SUCCESS_SA_SOFTEXP_FIRST:
481 : : case ROC_IE_OW_UCC_SUCCESS_SA_SOFTEXP_AGAIN:
482 [ # # ]: 0 : if (life_unit == ROC_IE_OW_SA_LIFE_UNIT_PKTS)
483 : 0 : desc.subtype = RTE_ETH_EVENT_IPSEC_SA_PKT_EXPIRY;
484 : : else
485 : 0 : desc.subtype = RTE_ETH_EVENT_IPSEC_SA_BYTE_EXPIRY;
486 : : break;
487 : 0 : case ROC_IE_OW_UCC_ERR_PKT_IP:
488 : 0 : warn_cnt++;
489 [ # # ]: 0 : if (warn_cnt % 10000 == 0)
490 : 0 : plt_warn("Outbound error, bad ip pkt, mbuf %p,"
491 : : "sa_index %u (total warnings %" PRIu64 ")",
492 : : mbuf, sess_priv.sa_idx, warn_cnt);
493 : 0 : desc.subtype = -uc_compcode;
494 : 0 : break;
495 : 0 : default:
496 : 0 : warn_cnt++;
497 [ # # ]: 0 : if (warn_cnt % 10000 == 0)
498 : 0 : plt_warn("Outbound error, mbuf %p, sa_index %u,"
499 : : " compcode %x uc %x,"
500 : : " (total warnings %" PRIu64 ")",
501 : : mbuf, sess_priv.sa_idx, compcode, uc_compcode, warn_cnt);
502 : 0 : desc.subtype = -uc_compcode;
503 : 0 : break;
504 : : }
505 : :
506 : 0 : rte_eth_dev_callback_process(eth_dev, RTE_ETH_EVENT_IPSEC, &desc);
507 : 0 : }
508 : :
509 : : static const char *
510 : : get_inl_event_type(enum nix_inl_event_type type)
511 : : {
512 : 0 : switch (type) {
513 : : case NIX_INL_OUTB_CPT_CQ:
514 : : return "NIX_INL_OUTB_CPT_CQ";
515 : 0 : case NIX_INL_INB_CPT_CQ:
516 : 0 : return "NIX_INL_INB_CPT_CQ";
517 : 0 : case NIX_INL_SSO:
518 : 0 : return "NIX_INL_SSO";
519 : 0 : case NIX_INL_SOFT_EXPIRY_THRD:
520 : 0 : return "NIX_INL_SOFT_EXPIRY_THRD";
521 : :
522 : 0 : default:
523 : 0 : return "Unknown event";
524 : : }
525 : : }
526 : :
527 : : void
528 [ # # # # : 0 : cn20k_eth_sec_sso_work_cb(uint64_t *gw, void *args, enum nix_inl_event_type type, void *cq_s,
# ]
529 : : uint32_t port_id)
530 : : {
531 : : struct rte_eth_event_ipsec_desc desc;
532 : : struct cn20k_sec_sess_priv sess_priv;
533 : : struct cn20k_outb_priv_data *outb_priv;
534 : : struct roc_ow_ipsec_outb_sa *outb_sa;
535 : : struct cpt_cn20k_res_s *res;
536 : : struct rte_eth_dev *eth_dev;
537 : : struct cnxk_eth_dev *dev;
538 : : uint16_t dlen_adj, rlen;
539 : : struct rte_mbuf *mbuf;
540 : : uintptr_t sa_base;
541 : : uintptr_t nixtx;
542 : : uint8_t port;
543 : :
544 : 0 : plt_nix_dbg("Received %s event", get_inl_event_type(type));
545 : :
546 [ # # # ]: 0 : switch ((gw[0] >> 28) & 0xF) {
547 : 0 : case RTE_EVENT_TYPE_ETHDEV:
548 : : /* Event from inbound inline dev due to IPSEC packet bad L4 */
549 : 0 : mbuf = (struct rte_mbuf *)(gw[1] - sizeof(struct rte_mbuf));
550 : 0 : plt_nix_dbg("Received mbuf %p from inline dev inbound", mbuf);
551 : : cnxk_pktmbuf_free_no_cache(mbuf);
552 : 0 : return;
553 : 0 : case RTE_EVENT_TYPE_CPU:
554 : : /* Check for subtype */
555 [ # # ]: 0 : if (((gw[0] >> 20) & 0xFF) == CNXK_ETHDEV_SEC_OUTB_EV_SUB) {
556 : : /* Event from outbound inline error */
557 : 0 : mbuf = (struct rte_mbuf *)gw[1];
558 : : break;
559 : : }
560 : : /* Fall through */
561 : : default:
562 [ # # ]: 0 : if (type) {
563 : : struct cpt_cq_s *cqs = (struct cpt_cq_s *)cq_s;
564 : :
565 [ # # ]: 0 : if (type == NIX_INL_INB_CPT_CQ) {
566 : : struct cn20k_inb_priv_data *inb_priv;
567 : :
568 : : inb_priv = roc_nix_inl_ow_ipsec_inb_sa_sw_rsvd(args);
569 [ # # # # ]: 0 : if (inb_priv->eth_sec && inb_priv->eth_sec->eth_dev) {
570 : : eth_dev = inb_priv->eth_sec->eth_dev;
571 : : } else {
572 : 0 : plt_err("Inbound CPT CQ event: no eth_dev in SA priv");
573 : 0 : return;
574 : : }
575 : : } else {
576 [ # # ]: 0 : if (port_id >= RTE_MAX_ETHPORTS) {
577 : 0 : plt_err("CPT CQ event: invalid port_id %u", port_id);
578 : 0 : return;
579 : : }
580 : 0 : eth_dev = &rte_eth_devices[port_id];
581 : : }
582 : :
583 [ # # ]: 0 : if (type < NIX_INL_SSO) {
584 : 0 : cn20k_eth_sec_post_event(eth_dev, args, type,
585 : 0 : (uint16_t)cqs->w0.s.uc_compcode,
586 : 0 : (uint16_t)cqs->w0.s.compcode, NULL);
587 : 0 : return;
588 : : }
589 [ # # ]: 0 : if (type == NIX_INL_SOFT_EXPIRY_THRD) {
590 : : outb_sa = (struct roc_ow_ipsec_outb_sa *)args;
591 : : outb_priv = roc_nix_inl_ow_ipsec_outb_sa_sw_rsvd(outb_sa);
592 : 0 : desc.metadata = (uint64_t)outb_priv->userdata;
593 [ # # ]: 0 : if (outb_sa->w2.s.life_unit == ROC_IE_OW_SA_LIFE_UNIT_PKTS)
594 : 0 : desc.subtype = RTE_ETH_EVENT_IPSEC_SA_PKT_EXPIRY;
595 : : else
596 : 0 : desc.subtype = RTE_ETH_EVENT_IPSEC_SA_BYTE_EXPIRY;
597 : : }
598 : 0 : rte_eth_dev_callback_process(eth_dev, RTE_ETH_EVENT_IPSEC, &desc);
599 : : } else {
600 : 0 : plt_err("Unknown event gw[0] = 0x%016lx, gw[1] = 0x%016lx", gw[0], gw[1]);
601 : : }
602 : : return;
603 : : }
604 : :
605 : : /* Get ethdev port from tag */
606 : 0 : port = gw[0] & 0xFF;
607 : 0 : eth_dev = &rte_eth_devices[port];
608 : : dev = cnxk_eth_pmd_priv(eth_dev);
609 : :
610 : 0 : sess_priv.u64 = *rte_security_dynfield(mbuf);
611 : : /* Calculate dlen adj */
612 : 0 : dlen_adj = mbuf->pkt_len - mbuf->l2_len;
613 : 0 : rlen = (dlen_adj + sess_priv.roundup_len) + (sess_priv.roundup_byte - 1);
614 : 0 : rlen &= ~(uint64_t)(sess_priv.roundup_byte - 1);
615 : 0 : rlen += sess_priv.partial_len;
616 : 0 : dlen_adj = rlen - dlen_adj;
617 : :
618 : : /* Find the res area residing on next cacheline after end of data */
619 : 0 : nixtx = rte_pktmbuf_mtod(mbuf, uintptr_t) + mbuf->pkt_len + dlen_adj;
620 : : nixtx += BIT_ULL(7);
621 : 0 : nixtx = (nixtx - 1) & ~(BIT_ULL(7) - 1);
622 : 0 : res = (struct cpt_cn20k_res_s *)nixtx;
623 : :
624 : 0 : plt_nix_dbg("Outbound error, mbuf %p, sa_index %u, compcode %x uc %x", mbuf,
625 : : sess_priv.sa_idx, res->compcode, res->uc_compcode);
626 : :
627 : 0 : sess_priv.u64 = *rte_security_dynfield(mbuf);
628 : :
629 : 0 : sa_base = dev->outb.sa_base;
630 : 0 : outb_sa = roc_nix_inl_ow_ipsec_outb_sa(sa_base, sess_priv.sa_idx);
631 : :
632 : 0 : cn20k_eth_sec_post_event(eth_dev, outb_sa, type, res->uc_compcode, res->compcode, mbuf);
633 : :
634 : : cnxk_pktmbuf_free_no_cache(mbuf);
635 : : }
636 : :
637 : : static void
638 : 0 : outb_dbg_iv_update(struct roc_ow_ipsec_outb_sa *outb_sa, const char *__iv_str)
639 : : {
640 : 0 : uint8_t *iv_dbg = outb_sa->iv.iv_dbg;
641 : 0 : char *iv_str = strdup(__iv_str);
642 : : char *iv_b = NULL, len = 16;
643 : : char *save;
644 : : int i;
645 : :
646 [ # # ]: 0 : if (!iv_str)
647 : 0 : return;
648 : :
649 [ # # ]: 0 : if (outb_sa->w2.s.enc_type == ROC_IE_SA_ENC_AES_GCM ||
650 : 0 : outb_sa->w2.s.enc_type == ROC_IE_SA_ENC_AES_CTR ||
651 [ # # ]: 0 : outb_sa->w2.s.enc_type == ROC_IE_SA_ENC_AES_CCM ||
652 [ # # ]: 0 : outb_sa->w2.s.auth_type == ROC_IE_SA_AUTH_AES_GMAC) {
653 : 0 : memset(outb_sa->iv.s.iv_dbg1, 0, sizeof(outb_sa->iv.s.iv_dbg1));
654 : 0 : memset(outb_sa->iv.s.iv_dbg2, 0, sizeof(outb_sa->iv.s.iv_dbg2));
655 : :
656 : : iv_dbg = outb_sa->iv.s.iv_dbg1;
657 [ # # ]: 0 : for (i = 0; i < 4; i++) {
658 [ # # ]: 0 : iv_b = strtok_r(i ? NULL : iv_str, ",", &save);
659 [ # # ]: 0 : if (!iv_b)
660 : : break;
661 : 0 : iv_dbg[i] = strtoul(iv_b, NULL, 0);
662 : : }
663 [ # # ]: 0 : *(uint32_t *)iv_dbg = rte_be_to_cpu_32(*(uint32_t *)iv_dbg);
664 : :
665 : : iv_dbg = outb_sa->iv.s.iv_dbg2;
666 [ # # ]: 0 : for (i = 0; i < 4; i++) {
667 : 0 : iv_b = strtok_r(NULL, ",", &save);
668 [ # # ]: 0 : if (!iv_b)
669 : : break;
670 : 0 : iv_dbg[i] = strtoul(iv_b, NULL, 0);
671 : : }
672 [ # # ]: 0 : *(uint32_t *)iv_dbg = rte_be_to_cpu_32(*(uint32_t *)iv_dbg);
673 : :
674 : : } else {
675 : : iv_dbg = outb_sa->iv.iv_dbg;
676 : : memset(iv_dbg, 0, sizeof(outb_sa->iv.iv_dbg));
677 : :
678 [ # # ]: 0 : for (i = 0; i < len; i++) {
679 [ # # ]: 0 : iv_b = strtok_r(i ? NULL : iv_str, ",", &save);
680 [ # # ]: 0 : if (!iv_b)
681 : : break;
682 : 0 : iv_dbg[i] = strtoul(iv_b, NULL, 0);
683 : : }
684 [ # # ]: 0 : *(uint64_t *)iv_dbg = rte_be_to_cpu_64(*(uint64_t *)iv_dbg);
685 [ # # ]: 0 : *(uint64_t *)&iv_dbg[8] = rte_be_to_cpu_64(*(uint64_t *)&iv_dbg[8]);
686 : : }
687 : :
688 : : /* Update source of IV */
689 : 0 : outb_sa->w2.s.iv_src = ROC_IE_OW_SA_IV_SRC_FROM_SA;
690 : 0 : free(iv_str);
691 : : }
692 : :
693 : : static void
694 : 0 : cn20k_eth_sec_inb_sa_misc_fill(struct roc_ow_ipsec_inb_sa *sa,
695 : : struct rte_security_ipsec_xform *ipsec_xfrm)
696 : : {
697 : : struct roc_ow_ipsec_inb_ctx_update_reg *ctx;
698 : : size_t offset;
699 : :
700 [ # # ]: 0 : if (sa->w2.s.enc_type != ROC_IE_SA_ENC_AES_GCM)
701 : : return;
702 : :
703 : : /* Update ctx push size for AES GCM */
704 : : offset = offsetof(struct roc_ow_ipsec_inb_sa, hmac_opad_ipad);
705 : : ctx = (struct roc_ow_ipsec_inb_ctx_update_reg *)((uint8_t *)sa + offset);
706 : 0 : sa->w0.s.hw_ctx_off = offset / 8;
707 : 0 : sa->w0.s.ctx_push_size = sa->w0.s.hw_ctx_off + 1;
708 : :
709 [ # # ]: 0 : if (ipsec_xfrm->life.bytes_soft_limit)
710 : 0 : ctx->soft_life = ipsec_xfrm->life.bytes_soft_limit + 1;
711 : :
712 [ # # ]: 0 : if (ipsec_xfrm->life.packets_soft_limit)
713 : 0 : ctx->soft_life = ipsec_xfrm->life.packets_soft_limit + 1;
714 : :
715 [ # # ]: 0 : if (ipsec_xfrm->life.bytes_hard_limit)
716 : 0 : ctx->hard_life = ipsec_xfrm->life.bytes_hard_limit + 1;
717 : :
718 [ # # ]: 0 : if (ipsec_xfrm->life.packets_hard_limit)
719 : 0 : ctx->hard_life = ipsec_xfrm->life.packets_hard_limit + 1;
720 : : }
721 : :
722 : : static int
723 : 0 : cn20k_eth_sec_outb_sa_misc_fill(struct roc_nix *roc_nix, struct roc_ow_ipsec_outb_sa *sa,
724 : : void *sa_cptr, struct rte_security_ipsec_xform *ipsec_xfrm,
725 : : uint32_t sa_idx)
726 : : {
727 : : struct roc_ow_ipsec_outb_ctx_update_reg *ctx;
728 : : uint64_t *ring_base, ring_addr;
729 : : size_t offset;
730 : :
731 [ # # ]: 0 : if (sa->w2.s.enc_type == ROC_IE_SA_ENC_AES_GCM) {
732 : : offset = offsetof(struct roc_ow_ipsec_outb_sa, hmac_opad_ipad);
733 : 0 : ctx = (struct roc_ow_ipsec_outb_ctx_update_reg *)((uint8_t *)sa + offset);
734 : 0 : sa->w0.s.hw_ctx_off = offset / 8;
735 : 0 : sa->w0.s.ctx_push_size = sa->w0.s.hw_ctx_off + 1;
736 : :
737 [ # # ]: 0 : if (ipsec_xfrm->esn.value)
738 : 0 : ctx->esn_val = ipsec_xfrm->esn.value - 1;
739 : :
740 [ # # ]: 0 : if (ipsec_xfrm->life.bytes_soft_limit)
741 : 0 : ctx->soft_life = ipsec_xfrm->life.bytes_soft_limit + 1;
742 : :
743 [ # # ]: 0 : if (ipsec_xfrm->life.packets_soft_limit)
744 : 0 : ctx->soft_life = ipsec_xfrm->life.packets_soft_limit + 1;
745 : :
746 [ # # ]: 0 : if (ipsec_xfrm->life.bytes_hard_limit)
747 : 0 : ctx->hard_life = ipsec_xfrm->life.bytes_hard_limit + 1;
748 : :
749 [ # # ]: 0 : if (ipsec_xfrm->life.packets_hard_limit)
750 : 0 : ctx->hard_life = ipsec_xfrm->life.packets_hard_limit + 1;
751 : : } else {
752 : 0 : ctx = &sa->ctx;
753 : : }
754 : :
755 [ # # ]: 0 : if (roc_nix_inl_is_cq_ena(roc_nix))
756 : 0 : goto done;
757 : :
758 [ # # ]: 0 : if (ipsec_xfrm->life.bytes_soft_limit | ipsec_xfrm->life.packets_soft_limit) {
759 : 0 : ring_base = roc_nix_inl_outb_ring_base_get(roc_nix);
760 [ # # ]: 0 : if (ring_base == NULL)
761 : : return -ENOTSUP;
762 : :
763 : 0 : ring_addr = ring_base[sa_idx >> ROC_NIX_SOFT_EXP_ERR_RING_MAX_ENTRY_LOG2];
764 : 0 : ctx->err_ctl.s.mode = ROC_IE_OW_ERR_CTL_MODE_RING;
765 : 0 : ctx->err_ctl.s.address = ring_addr >> 3;
766 : 0 : sa->w0.s.ctx_id = ((uintptr_t)sa_cptr >> 51) & 0x1ff;
767 : : }
768 : 0 : done:
769 : : return 0;
770 : : }
771 : :
772 : : static int
773 [ # # ]: 0 : cn20k_eth_sec_session_create(void *device, struct rte_security_session_conf *conf,
774 : : struct rte_security_session *sess)
775 : : {
776 : : struct rte_eth_dev *eth_dev = (struct rte_eth_dev *)device;
777 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
778 : : struct rte_security_ipsec_xform *ipsec;
779 : : struct cn20k_sec_sess_priv sess_priv;
780 : : struct rte_crypto_sym_xform *crypto;
781 : 0 : struct cnxk_eth_sec_sess *eth_sec = SECURITY_GET_SESS_PRIV(sess);
782 : 0 : struct roc_nix *nix = &dev->nix;
783 : : bool inbound, inl_dev;
784 : : rte_spinlock_t *lock;
785 : 0 : char tbuf[128] = {0};
786 : : int rc = 0;
787 : :
788 [ # # ]: 0 : if (conf->action_type != RTE_SECURITY_ACTION_TYPE_INLINE_PROTOCOL)
789 : : return -ENOTSUP;
790 : :
791 [ # # ]: 0 : if (conf->protocol != RTE_SECURITY_PROTOCOL_IPSEC)
792 : : return -ENOTSUP;
793 : :
794 [ # # ]: 0 : if (nix->custom_inb_sa)
795 : : return -ENOTSUP;
796 : :
797 [ # # ]: 0 : if (rte_security_dynfield_register() < 0)
798 : : return -ENOTSUP;
799 : :
800 [ # # # # ]: 0 : if (conf->ipsec.options.ip_reassembly_en && dev->reass_dynfield_off < 0) {
801 [ # # ]: 0 : if (rte_eth_ip_reassembly_dynfield_register(&dev->reass_dynfield_off,
802 : : &dev->reass_dynflag_bit) < 0)
803 : 0 : return -rte_errno;
804 : : }
805 : :
806 [ # # # # ]: 0 : if (conf->ipsec.options.ingress_oop && rte_security_oop_dynfield_offset < 0) {
807 : : /* Register for security OOP dynfield if required */
808 [ # # ]: 0 : if (rte_security_oop_dynfield_register() < 0)
809 : 0 : return -rte_errno;
810 : : }
811 : :
812 : : /* We cannot support inbound reassembly and OOP together */
813 [ # # ]: 0 : if (conf->ipsec.options.ip_reassembly_en && conf->ipsec.options.ingress_oop) {
814 : 0 : plt_err("Cannot support Inbound reassembly and OOP together");
815 : 0 : return -ENOTSUP;
816 : : }
817 : :
818 : 0 : ipsec = &conf->ipsec;
819 : 0 : crypto = conf->crypto_xform;
820 : :
821 : 0 : rc = cnxk_ipsec_xform_verify(ipsec, crypto);
822 [ # # ]: 0 : if (rc) {
823 : 0 : plt_err("Crypto xform verify failed, rc=%d", rc);
824 : 0 : return rc;
825 : : }
826 : :
827 : 0 : inbound = !!(ipsec->direction == RTE_SECURITY_IPSEC_SA_DIR_INGRESS);
828 [ # # ]: 0 : inl_dev = !!dev->inb.inl_dev;
829 : :
830 : : memset(eth_sec, 0, sizeof(struct cnxk_eth_sec_sess));
831 : 0 : eth_sec->eth_dev = eth_dev;
832 : 0 : sess_priv.u64 = 0;
833 : :
834 [ # # ]: 0 : lock = inbound ? &dev->inb.lock : &dev->outb.lock;
835 : : rte_spinlock_lock(lock);
836 : :
837 : : /* Acquire lock on inline dev for inbound */
838 [ # # ]: 0 : if (inbound && inl_dev)
839 : 0 : roc_nix_inl_dev_lock();
840 : :
841 [ # # ]: 0 : if (inbound) {
842 : : struct roc_ow_ipsec_inb_sa *inb_sa, *inb_sa_dptr;
843 : : struct cn20k_inb_priv_data *inb_priv;
844 : : uint32_t spi_mask;
845 : : uintptr_t sa;
846 : :
847 : : PLT_STATIC_ASSERT(sizeof(struct cn20k_inb_priv_data) <
848 : : ROC_NIX_INL_OW_IPSEC_INB_SW_RSVD);
849 : :
850 : 0 : spi_mask = roc_nix_inl_inb_spi_range(nix, inl_dev, NULL, NULL);
851 : :
852 : : /* Search if a session already exits */
853 [ # # ]: 0 : if (cnxk_eth_sec_sess_get_by_sa_idx(dev, ipsec->spi & spi_mask, true)) {
854 : 0 : plt_err("Inbound SA with SPI/SA index %u already in use", ipsec->spi);
855 : : rc = -EEXIST;
856 : 0 : goto err;
857 : : }
858 : :
859 : : /* Get Inbound SA from NIX_RX_IPSEC_SA_BASE */
860 : 0 : sa = roc_nix_inl_inb_sa_get(nix, inl_dev, ipsec->spi);
861 [ # # # # ]: 0 : if (!sa && dev->inb.inl_dev) {
862 : : snprintf(tbuf, sizeof(tbuf),
863 : : "Failed to create ingress sa, inline dev "
864 : : "not found or spi not in range");
865 : : rc = -ENOTSUP;
866 : 0 : goto err;
867 [ # # ]: 0 : } else if (!sa) {
868 : : snprintf(tbuf, sizeof(tbuf), "Failed to create ingress sa");
869 : : rc = -EFAULT;
870 : 0 : goto err;
871 : : }
872 : :
873 : 0 : inb_sa = (struct roc_ow_ipsec_inb_sa *)sa;
874 : :
875 : : /* Check if SA is already in use */
876 [ # # ]: 0 : if (inb_sa->w2.s.valid) {
877 : 0 : snprintf(tbuf, sizeof(tbuf), "Inbound SA with SPI %u already in use",
878 : : ipsec->spi);
879 : : rc = -EBUSY;
880 : 0 : goto err;
881 : : }
882 : :
883 : 0 : inb_sa_dptr = (struct roc_ow_ipsec_inb_sa *)dev->inb.sa_dptr;
884 : : memset(inb_sa_dptr, 0, sizeof(struct roc_ow_ipsec_inb_sa));
885 : :
886 : : /* Fill inbound sa params */
887 : 0 : rc = cnxk_ow_ipsec_inb_sa_fill(inb_sa_dptr, ipsec, crypto, 0);
888 [ # # ]: 0 : if (rc) {
889 : : snprintf(tbuf, sizeof(tbuf), "Failed to init inbound sa, rc=%d", rc);
890 : 0 : goto err;
891 : : }
892 : :
893 : 0 : rc = roc_npc_skip_size_pkind_get(&dev->npc);
894 [ # # ]: 0 : if (rc >= 0)
895 : 0 : inb_sa_dptr->w0.s.pkind = rc;
896 : :
897 : 0 : cn20k_eth_sec_inb_sa_misc_fill(inb_sa_dptr, ipsec);
898 : :
899 : : inb_priv = roc_nix_inl_ow_ipsec_inb_sa_sw_rsvd(inb_sa);
900 : : /* Back pointer to get eth_sec */
901 : 0 : inb_priv->eth_sec = eth_sec;
902 : : /* Save userdata in inb private area */
903 : 0 : inb_priv->userdata = conf->userdata;
904 : :
905 : : /* Save SA index/SPI in cookie for now */
906 : 0 : inb_sa_dptr->w1.s.cookie = ipsec->spi & spi_mask;
907 : :
908 [ # # ]: 0 : if (ipsec->options.stats == 1) {
909 : : /* Enable mib counters */
910 : 0 : inb_sa_dptr->w0.s.count_mib_bytes = 1;
911 : 0 : inb_sa_dptr->w0.s.count_mib_pkts = 1;
912 : : }
913 : :
914 : : /* Prepare session priv */
915 : 0 : sess_priv.inb_sa = 1;
916 : 0 : sess_priv.sa_idx = ipsec->spi & spi_mask;
917 : :
918 : : /* Pointer from eth_sec -> inb_sa */
919 : 0 : eth_sec->sa = inb_sa;
920 : 0 : eth_sec->sess = sess;
921 : 0 : eth_sec->sa_idx = ipsec->spi & spi_mask;
922 : 0 : eth_sec->spi = ipsec->spi;
923 : 0 : eth_sec->inl_dev = !!dev->inb.inl_dev;
924 : 0 : eth_sec->inb = true;
925 : 0 : eth_sec->inb_oop = !!ipsec->options.ingress_oop;
926 : :
927 : 0 : TAILQ_INSERT_TAIL(&dev->inb.list, eth_sec, entry);
928 : 0 : dev->inb.nb_sess++;
929 : : /* Sync session in context cache */
930 : 0 : rc = roc_nix_inl_ctx_write(&dev->nix, inb_sa_dptr, eth_sec->sa, eth_sec->inb,
931 : : sizeof(struct roc_ow_ipsec_inb_sa));
932 [ # # ]: 0 : if (rc)
933 : 0 : goto err;
934 : :
935 [ # # ]: 0 : if (conf->ipsec.options.ip_reassembly_en) {
936 : 0 : inb_priv->reass_dynfield_off = dev->reass_dynfield_off;
937 : 0 : inb_priv->reass_dynflag_bit = dev->reass_dynflag_bit;
938 : : }
939 : :
940 [ # # ]: 0 : if (ipsec->options.ingress_oop)
941 : 0 : dev->inb.nb_oop++;
942 : :
943 : : /* Update function pointer to handle OOP sessions */
944 [ # # # # ]: 0 : if (dev->inb.nb_oop && !(dev->rx_offload_flags & NIX_RX_REAS_F)) {
945 : 0 : dev->rx_offload_flags |= NIX_RX_REAS_F;
946 : 0 : cn20k_eth_set_rx_function(eth_dev);
947 [ # # ]: 0 : if (cnxk_ethdev_rx_offload_cb)
948 : 0 : cnxk_ethdev_rx_offload_cb(eth_dev->data->port_id, NIX_RX_REAS_F);
949 : : }
950 : : } else {
951 : : struct roc_ow_ipsec_outb_sa *outb_sa, *outb_sa_dptr;
952 : : struct cn20k_outb_priv_data *outb_priv;
953 : : struct cnxk_ipsec_outb_rlens *rlens;
954 : 0 : uint64_t sa_base = dev->outb.sa_base;
955 : : const char *iv_str;
956 : : uint32_t sa_idx;
957 : :
958 : : PLT_STATIC_ASSERT(sizeof(struct cn20k_outb_priv_data) <
959 : : ROC_NIX_INL_OW_IPSEC_OUTB_SW_RSVD);
960 : :
961 : : /* Alloc an sa index */
962 : 0 : rc = cnxk_eth_outb_sa_idx_get(dev, &sa_idx, ipsec->spi);
963 [ # # ]: 0 : if (rc)
964 : 0 : goto err;
965 : :
966 : 0 : outb_sa = roc_nix_inl_ow_ipsec_outb_sa(sa_base, sa_idx);
967 : : outb_priv = roc_nix_inl_ow_ipsec_outb_sa_sw_rsvd(outb_sa);
968 : 0 : rlens = &outb_priv->rlens;
969 : :
970 : 0 : outb_sa_dptr = (struct roc_ow_ipsec_outb_sa *)dev->outb.sa_dptr;
971 : : memset(outb_sa_dptr, 0, sizeof(struct roc_ow_ipsec_outb_sa));
972 : :
973 : : /* Fill outbound sa params */
974 : 0 : rc = cnxk_ow_ipsec_outb_sa_fill(outb_sa_dptr, ipsec, crypto, 0);
975 [ # # ]: 0 : if (rc) {
976 : : snprintf(tbuf, sizeof(tbuf), "Failed to init outbound sa, rc=%d", rc);
977 : 0 : rc |= cnxk_eth_outb_sa_idx_put(dev, sa_idx);
978 : 0 : goto err;
979 : : }
980 : :
981 [ # # ]: 0 : if (conf->ipsec.options.iv_gen_disable == 1) {
982 : 0 : iv_str = getenv("ETH_SEC_IV_OVR");
983 [ # # ]: 0 : if (iv_str)
984 : 0 : outb_dbg_iv_update(outb_sa_dptr, iv_str);
985 : : }
986 : : /* Fill outbound sa misc params */
987 : 0 : rc = cn20k_eth_sec_outb_sa_misc_fill(&dev->nix, outb_sa_dptr, outb_sa, ipsec,
988 : : sa_idx);
989 [ # # ]: 0 : if (rc) {
990 : : snprintf(tbuf, sizeof(tbuf), "Failed to init outb sa misc params, rc=%d",
991 : : rc);
992 : 0 : rc |= cnxk_eth_outb_sa_idx_put(dev, sa_idx);
993 : 0 : goto err;
994 : : }
995 : :
996 : : /* Save userdata */
997 : 0 : outb_priv->userdata = conf->userdata;
998 : 0 : outb_priv->sa_idx = sa_idx;
999 : 0 : outb_priv->eth_sec = eth_sec;
1000 : :
1001 : : /* Save rlen info */
1002 : 0 : cnxk_ipsec_outb_rlens_get(rlens, ipsec, crypto);
1003 : :
1004 [ # # ]: 0 : if (ipsec->options.stats == 1) {
1005 : : /* Enable mib counters */
1006 : 0 : outb_sa_dptr->w0.s.count_mib_bytes = 1;
1007 : 0 : outb_sa_dptr->w0.s.count_mib_pkts = 1;
1008 : : }
1009 : :
1010 : : /* Prepare session priv */
1011 : 0 : sess_priv.sa_idx = outb_priv->sa_idx;
1012 : 0 : sess_priv.roundup_byte = rlens->roundup_byte;
1013 : 0 : sess_priv.roundup_len = rlens->roundup_len;
1014 : 0 : sess_priv.partial_len = rlens->partial_len;
1015 : 0 : sess_priv.mode = outb_sa_dptr->w2.s.ipsec_mode;
1016 : 0 : sess_priv.outer_ip_ver = outb_sa_dptr->w2.s.outer_ip_ver;
1017 : : /* Propagate inner checksum enable from SA to fast path */
1018 : 0 : sess_priv.chksum =
1019 [ # # ]: 0 : (!ipsec->options.ip_csum_enable << 1 | !ipsec->options.l4_csum_enable);
1020 : 0 : sess_priv.dec_ttl = ipsec->options.dec_ttl;
1021 : 0 : sess_priv.cpt_cq_ena = roc_nix_inl_is_cq_ena(&dev->nix);
1022 : :
1023 : : /* Pointer from eth_sec -> outb_sa */
1024 : 0 : eth_sec->sa = outb_sa;
1025 : 0 : eth_sec->sess = sess;
1026 : 0 : eth_sec->sa_idx = sa_idx;
1027 : 0 : eth_sec->spi = ipsec->spi;
1028 : :
1029 : 0 : TAILQ_INSERT_TAIL(&dev->outb.list, eth_sec, entry);
1030 : 0 : dev->outb.nb_sess++;
1031 : : /* Sync session in context cache */
1032 : 0 : rc = roc_nix_inl_ctx_write(&dev->nix, outb_sa_dptr, eth_sec->sa, eth_sec->inb,
1033 : : sizeof(struct roc_ow_ipsec_outb_sa));
1034 [ # # ]: 0 : if (rc)
1035 : 0 : goto err;
1036 : : }
1037 [ # # ]: 0 : if (inbound && inl_dev)
1038 : 0 : roc_nix_inl_dev_unlock();
1039 : : rte_spinlock_unlock(lock);
1040 : :
1041 [ # # ]: 0 : plt_nix_dbg("Created %s session with spi=%u, sa_idx=%u inl_dev=%u",
1042 : : inbound ? "inbound" : "outbound", eth_sec->spi, eth_sec->sa_idx,
1043 : : eth_sec->inl_dev);
1044 : : /*
1045 : : * Update fast path info in priv area.
1046 : : */
1047 : 0 : sess->fast_mdata = sess_priv.u64;
1048 : :
1049 : 0 : return 0;
1050 : 0 : err:
1051 [ # # ]: 0 : if (inbound && inl_dev)
1052 : 0 : roc_nix_inl_dev_unlock();
1053 : : rte_spinlock_unlock(lock);
1054 : :
1055 [ # # ]: 0 : if (rc)
1056 : 0 : plt_err("%s", tbuf);
1057 : : return rc;
1058 : : }
1059 : :
1060 : : static int
1061 : 0 : cn20k_eth_sec_session_destroy(void *device, struct rte_security_session *sess)
1062 : : {
1063 : : struct rte_eth_dev *eth_dev = (struct rte_eth_dev *)device;
1064 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1065 : : struct cnxk_eth_sec_sess *eth_sec;
1066 : : rte_spinlock_t *lock;
1067 : : void *sa_dptr;
1068 : :
1069 : 0 : eth_sec = cnxk_eth_sec_sess_get_by_sess(dev, sess);
1070 [ # # ]: 0 : if (!eth_sec)
1071 : : return -ENOENT;
1072 [ # # ]: 0 : if (dev->nix.custom_inb_sa)
1073 : : return -ENOTSUP;
1074 : :
1075 [ # # ]: 0 : lock = eth_sec->inb ? &dev->inb.lock : &dev->outb.lock;
1076 : : rte_spinlock_lock(lock);
1077 : :
1078 [ # # ]: 0 : if (eth_sec->inl_dev)
1079 : 0 : roc_nix_inl_dev_lock();
1080 : :
1081 [ # # ]: 0 : if (eth_sec->inb) {
1082 : : /* Disable SA */
1083 : 0 : sa_dptr = dev->inb.sa_dptr;
1084 : 0 : roc_ow_ipsec_inb_sa_init(sa_dptr);
1085 : :
1086 : 0 : roc_nix_inl_ctx_write(&dev->nix, sa_dptr, eth_sec->sa, eth_sec->inb,
1087 : : sizeof(struct roc_ow_ipsec_inb_sa));
1088 [ # # ]: 0 : TAILQ_REMOVE(&dev->inb.list, eth_sec, entry);
1089 : 0 : dev->inb.nb_sess--;
1090 [ # # ]: 0 : if (eth_sec->inb_oop)
1091 : 0 : dev->inb.nb_oop--;
1092 : :
1093 : : /* Clear offload flags if was used by OOP */
1094 [ # # # # ]: 0 : if (!dev->inb.nb_oop && !dev->inb.reass_en &&
1095 [ # # ]: 0 : dev->rx_offload_flags & NIX_RX_REAS_F) {
1096 : 0 : dev->rx_offload_flags &= ~NIX_RX_REAS_F;
1097 : 0 : cn20k_eth_set_rx_function(eth_dev);
1098 : : }
1099 : : } else {
1100 : : /* Disable SA */
1101 : 0 : sa_dptr = dev->outb.sa_dptr;
1102 : 0 : roc_ow_ipsec_outb_sa_init(sa_dptr);
1103 : :
1104 : 0 : roc_nix_inl_ctx_write(&dev->nix, sa_dptr, eth_sec->sa, eth_sec->inb,
1105 : : sizeof(struct roc_ow_ipsec_outb_sa));
1106 : : /* Release Outbound SA index */
1107 : 0 : cnxk_eth_outb_sa_idx_put(dev, eth_sec->sa_idx);
1108 [ # # ]: 0 : TAILQ_REMOVE(&dev->outb.list, eth_sec, entry);
1109 : 0 : dev->outb.nb_sess--;
1110 : : }
1111 [ # # ]: 0 : if (eth_sec->inl_dev)
1112 : 0 : roc_nix_inl_dev_unlock();
1113 : :
1114 : : rte_spinlock_unlock(lock);
1115 : :
1116 [ # # ]: 0 : plt_nix_dbg("Destroyed %s session with spi=%u, sa_idx=%u, inl_dev=%u",
1117 : : eth_sec->inb ? "inbound" : "outbound", eth_sec->spi, eth_sec->sa_idx,
1118 : : eth_sec->inl_dev);
1119 : :
1120 : 0 : return 0;
1121 : : }
1122 : :
1123 : : static const struct rte_security_capability *
1124 : 0 : cn20k_eth_sec_capabilities_get(void *device __rte_unused)
1125 : : {
1126 : 0 : return cn20k_eth_sec_capabilities;
1127 : : }
1128 : :
1129 : : static int
1130 [ # # ]: 0 : cn20k_eth_sec_session_update(void *device, struct rte_security_session *sess,
1131 : : struct rte_security_session_conf *conf)
1132 : : {
1133 : : struct rte_eth_dev *eth_dev = (struct rte_eth_dev *)device;
1134 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1135 : : struct rte_security_ipsec_xform *ipsec;
1136 : : struct cn20k_sec_sess_priv sess_priv;
1137 : : struct rte_crypto_sym_xform *crypto;
1138 : : struct cnxk_eth_sec_sess *eth_sec;
1139 : : bool inbound;
1140 : : int rc;
1141 : :
1142 [ # # ]: 0 : if (conf->action_type != RTE_SECURITY_ACTION_TYPE_INLINE_PROTOCOL ||
1143 : : conf->protocol != RTE_SECURITY_PROTOCOL_IPSEC)
1144 : : return -ENOENT;
1145 : :
1146 : 0 : ipsec = &conf->ipsec;
1147 : 0 : crypto = conf->crypto_xform;
1148 : 0 : inbound = !!(ipsec->direction == RTE_SECURITY_IPSEC_SA_DIR_INGRESS);
1149 : :
1150 : 0 : eth_sec = cnxk_eth_sec_sess_get_by_sess(dev, sess);
1151 [ # # ]: 0 : if (!eth_sec)
1152 : : return -ENOENT;
1153 : :
1154 : 0 : eth_sec->spi = conf->ipsec.spi;
1155 : :
1156 [ # # ]: 0 : if (inbound) {
1157 : : struct roc_ow_ipsec_inb_sa *inb_sa_dptr, *inb_sa;
1158 : : struct cn20k_inb_priv_data *inb_priv;
1159 : :
1160 : 0 : inb_sa = eth_sec->sa;
1161 : : inb_priv = roc_nix_inl_ow_ipsec_inb_sa_sw_rsvd(inb_sa);
1162 : 0 : inb_sa_dptr = (struct roc_ow_ipsec_inb_sa *)dev->inb.sa_dptr;
1163 : : memset(inb_sa_dptr, 0, sizeof(struct roc_ow_ipsec_inb_sa));
1164 : :
1165 : 0 : rc = cnxk_ow_ipsec_inb_sa_fill(inb_sa_dptr, ipsec, crypto, 0);
1166 [ # # ]: 0 : if (rc)
1167 : : return -EINVAL;
1168 : :
1169 : 0 : rc = roc_npc_skip_size_pkind_get(&dev->npc);
1170 [ # # ]: 0 : if (rc >= 0)
1171 : 0 : inb_sa_dptr->w0.s.pkind = rc;
1172 : :
1173 : 0 : cn20k_eth_sec_inb_sa_misc_fill(inb_sa_dptr, ipsec);
1174 : :
1175 : : /* Use cookie for original data */
1176 : 0 : inb_sa_dptr->w1.s.cookie = inb_sa->w1.s.cookie;
1177 : :
1178 [ # # ]: 0 : if (ipsec->options.stats == 1) {
1179 : : /* Enable mib counters */
1180 : 0 : inb_sa_dptr->w0.s.count_mib_bytes = 1;
1181 : 0 : inb_sa_dptr->w0.s.count_mib_pkts = 1;
1182 : : }
1183 : :
1184 : 0 : rc = roc_nix_inl_ctx_write(&dev->nix, inb_sa_dptr, eth_sec->sa, eth_sec->inb,
1185 : : sizeof(struct roc_ow_ipsec_inb_sa));
1186 [ # # ]: 0 : if (rc)
1187 : : return -EINVAL;
1188 : :
1189 : : /* Save userdata in inb private area */
1190 : 0 : inb_priv->userdata = conf->userdata;
1191 : : } else {
1192 : : struct roc_ow_ipsec_outb_sa *outb_sa_dptr, *outb_sa;
1193 : : struct cn20k_outb_priv_data *outb_priv;
1194 : : struct cnxk_ipsec_outb_rlens *rlens;
1195 : :
1196 : 0 : outb_sa = eth_sec->sa;
1197 : : outb_priv = roc_nix_inl_ow_ipsec_outb_sa_sw_rsvd(outb_sa);
1198 : 0 : rlens = &outb_priv->rlens;
1199 : 0 : outb_sa_dptr = (struct roc_ow_ipsec_outb_sa *)dev->outb.sa_dptr;
1200 : : memset(outb_sa_dptr, 0, sizeof(struct roc_ow_ipsec_outb_sa));
1201 : :
1202 : 0 : rc = cnxk_ow_ipsec_outb_sa_fill(outb_sa_dptr, ipsec, crypto, 0);
1203 [ # # ]: 0 : if (rc)
1204 : : return -EINVAL;
1205 : :
1206 : : /* Fill outbound sa misc params */
1207 : 0 : rc = cn20k_eth_sec_outb_sa_misc_fill(&dev->nix, outb_sa_dptr, outb_sa, ipsec,
1208 : : eth_sec->sa_idx);
1209 [ # # ]: 0 : if (rc) {
1210 : 0 : plt_err("Failed to init outb sa misc params, rc=%d", rc);
1211 : 0 : return rc;
1212 : : }
1213 : :
1214 : : /* Save rlen info */
1215 : 0 : cnxk_ipsec_outb_rlens_get(rlens, ipsec, crypto);
1216 : :
1217 [ # # ]: 0 : if (ipsec->options.stats == 1) {
1218 : : /* Enable mib counters */
1219 : 0 : outb_sa_dptr->w0.s.count_mib_bytes = 1;
1220 : 0 : outb_sa_dptr->w0.s.count_mib_pkts = 1;
1221 : : }
1222 : :
1223 : 0 : sess_priv.u64 = 0;
1224 : 0 : sess_priv.sa_idx = outb_priv->sa_idx;
1225 : 0 : sess_priv.roundup_byte = rlens->roundup_byte;
1226 : 0 : sess_priv.roundup_len = rlens->roundup_len;
1227 : 0 : sess_priv.partial_len = rlens->partial_len;
1228 : 0 : sess_priv.mode = outb_sa_dptr->w2.s.ipsec_mode;
1229 : 0 : sess_priv.outer_ip_ver = outb_sa_dptr->w2.s.outer_ip_ver;
1230 : : /* Propagate inner checksum enable from SA to fast path */
1231 : 0 : sess_priv.chksum =
1232 [ # # ]: 0 : (!ipsec->options.ip_csum_enable << 1 | !ipsec->options.l4_csum_enable);
1233 : 0 : sess_priv.dec_ttl = ipsec->options.dec_ttl;
1234 : :
1235 : 0 : sess_priv.cpt_cq_ena = roc_nix_inl_is_cq_ena(&dev->nix);
1236 : 0 : rc = roc_nix_inl_ctx_write(&dev->nix, outb_sa_dptr, eth_sec->sa, eth_sec->inb,
1237 : : sizeof(struct roc_ow_ipsec_outb_sa));
1238 [ # # ]: 0 : if (rc)
1239 : : return -EINVAL;
1240 : :
1241 : : /* Save userdata */
1242 : 0 : outb_priv->userdata = conf->userdata;
1243 : 0 : sess->fast_mdata = sess_priv.u64;
1244 : : }
1245 : :
1246 : : return 0;
1247 : : }
1248 : :
1249 : : static int
1250 : 0 : cn20k_eth_sec_session_stats_get(void *device, struct rte_security_session *sess,
1251 : : struct rte_security_stats *stats)
1252 : : {
1253 : : struct rte_eth_dev *eth_dev = (struct rte_eth_dev *)device;
1254 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1255 : : struct cnxk_eth_sec_sess *eth_sec;
1256 : : size_t offset;
1257 : : int rc;
1258 : :
1259 : 0 : eth_sec = cnxk_eth_sec_sess_get_by_sess(dev, sess);
1260 [ # # ]: 0 : if (eth_sec == NULL)
1261 : : return -EINVAL;
1262 : :
1263 : 0 : rc = roc_nix_inl_sa_sync(&dev->nix, eth_sec->sa, eth_sec->inb, ROC_NIX_INL_SA_OP_FLUSH);
1264 [ # # ]: 0 : if (rc)
1265 : : return -EINVAL;
1266 : : rte_delay_ms(1);
1267 : :
1268 : 0 : stats->protocol = RTE_SECURITY_PROTOCOL_IPSEC;
1269 : :
1270 [ # # ]: 0 : if (eth_sec->inb) {
1271 : 0 : struct roc_ow_ipsec_inb_sa *sa = (struct roc_ow_ipsec_inb_sa *)eth_sec->sa;
1272 : : struct roc_ow_ipsec_inb_ctx_update_reg *ctx;
1273 : :
1274 [ # # ]: 0 : if (sa->w2.s.enc_type == ROC_IE_SA_ENC_AES_GCM) {
1275 : : offset = offsetof(struct roc_ow_ipsec_inb_sa, hmac_opad_ipad);
1276 : 0 : ctx = (struct roc_ow_ipsec_inb_ctx_update_reg *)((uint8_t *)sa + offset);
1277 : : } else {
1278 : 0 : ctx = &sa->ctx;
1279 : : }
1280 : :
1281 : 0 : stats->ipsec.ipackets = ctx->mib_pkts;
1282 : 0 : stats->ipsec.ibytes = ctx->mib_octs;
1283 : : } else {
1284 : 0 : struct roc_ow_ipsec_outb_sa *sa = (struct roc_ow_ipsec_outb_sa *)eth_sec->sa;
1285 : : struct roc_ow_ipsec_outb_ctx_update_reg *ctx;
1286 : :
1287 [ # # ]: 0 : if (sa->w2.s.enc_type == ROC_IE_SA_ENC_AES_GCM) {
1288 : : offset = offsetof(struct roc_ow_ipsec_outb_sa, hmac_opad_ipad);
1289 : 0 : ctx = (struct roc_ow_ipsec_outb_ctx_update_reg *)((uint8_t *)sa + offset);
1290 : : } else {
1291 : 0 : ctx = &sa->ctx;
1292 : : }
1293 : :
1294 : 0 : stats->ipsec.opackets = ctx->mib_pkts;
1295 : 0 : stats->ipsec.obytes = ctx->mib_octs;
1296 : : }
1297 : :
1298 : : return 0;
1299 : : }
1300 : :
1301 : : static void
1302 : 0 : eth_sec_caps_add(struct rte_security_capability eth_sec_caps[], uint32_t *idx,
1303 : : const struct rte_security_capability *caps, uint32_t nb_caps)
1304 : : {
1305 [ # # ]: 0 : PLT_VERIFY(*idx + nb_caps < SEC_CAPS_LEN);
1306 : :
1307 [ # # ]: 0 : rte_memcpy(ð_sec_caps[*idx], caps, nb_caps * sizeof(caps[0]));
1308 : 0 : *idx += nb_caps;
1309 : 0 : }
1310 : :
1311 : : static uint16_t __rte_hot
1312 : 0 : cn20k_eth_sec_inb_rx_inject(void *device, struct rte_mbuf **pkts,
1313 : : struct rte_security_session **sess, uint16_t nb_pkts)
1314 : : {
1315 : : struct rte_eth_dev *eth_dev = (struct rte_eth_dev *)device;
1316 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1317 : :
1318 : 0 : return cn20k_nix_inj_pkts(sess, &dev->inj_cfg, pkts, nb_pkts);
1319 : : }
1320 : :
1321 : : static int
1322 : 0 : cn20k_eth_sec_rx_inject_config(void *device, uint16_t port_id, bool enable)
1323 : : {
1324 : : struct rte_eth_dev *eth_dev = (struct rte_eth_dev *)device;
1325 : : struct cnxk_eth_dev *dev = cnxk_eth_pmd_priv(eth_dev);
1326 : : uint64_t channel, pf_func, inj_match_id = 0xFFFFUL;
1327 : : struct cnxk_ethdev_inj_cfg *inj_cfg;
1328 : 0 : struct roc_nix *nix = &dev->nix;
1329 : : struct roc_cpt_lf *inl_lf;
1330 : : uint64_t sa_base;
1331 : :
1332 [ # # ]: 0 : if (!rte_eth_dev_is_valid_port(port_id))
1333 : : return -EINVAL;
1334 : :
1335 [ # # ]: 0 : if (eth_dev->data->dev_started || !eth_dev->data->dev_configured)
1336 : : return -EBUSY;
1337 : :
1338 [ # # ]: 0 : if (!roc_nix_inl_inb_rx_inject_enable(nix, dev->inb.inl_dev))
1339 : : return -ENOTSUP;
1340 : :
1341 : 0 : roc_idev_nix_rx_inject_set(port_id, enable);
1342 : :
1343 : 0 : inl_lf = roc_nix_inl_inb_inj_lf_get(nix);
1344 [ # # ]: 0 : if (!inl_lf)
1345 : : return -ENOTSUP;
1346 : 0 : sa_base = roc_nix_inl_inb_sa_base_get(nix, dev->inb.inl_dev);
1347 : :
1348 : : inj_cfg = &dev->inj_cfg;
1349 : 0 : inj_cfg->sa_base = sa_base | eth_dev->data->port_id;
1350 : 0 : inj_cfg->io_addr = inl_lf->io_addr;
1351 : 0 : inj_cfg->lmt_base = nix->lmt_base;
1352 : 0 : channel = roc_nix_get_base_chan(nix);
1353 : 0 : pf_func = roc_idev_nix_inl_dev_pffunc_get();
1354 : 0 : inj_cfg->cmd_w0 = pf_func << 48 | inj_match_id << 32 | channel << 4;
1355 : :
1356 : 0 : return 0;
1357 : : }
1358 : :
1359 : : #define CPT_LMTST_BURST 32
1360 : : static uint16_t
1361 : 0 : cn20k_inl_dev_submit(struct roc_nix_inl_dev_q *q, void *inst, uint16_t nb_inst)
1362 : : {
1363 : 0 : uintptr_t lbase = q->lmt_base;
1364 : : uint8_t lnum, shft, loff;
1365 : : uint16_t left, burst;
1366 : : rte_iova_t io_addr;
1367 : : uint16_t lmt_id;
1368 : :
1369 : : /* Check the flow control to avoid the queue overflow */
1370 [ # # ]: 0 : if (cnxk_nix_inl_fc_check(q->fc_addr, &q->fc_addr_sw, q->nb_desc, nb_inst))
1371 : : return 0;
1372 : :
1373 : : io_addr = q->io_addr;
1374 : : ROC_LMT_CPT_BASE_ID_GET(lbase, lmt_id);
1375 : :
1376 : : left = nb_inst;
1377 : 0 : again:
1378 : 0 : burst = left > CPT_LMTST_BURST ? CPT_LMTST_BURST : left;
1379 : :
1380 : : lnum = 0;
1381 : : loff = 0;
1382 : : shft = 16;
1383 : 0 : memcpy(PLT_PTR_CAST(lbase), inst, burst * sizeof(struct cpt_inst_s));
1384 : : loff = (burst % 2) ? 1 : 0;
1385 : : lnum = (burst / 2);
1386 : : shft = shft + (lnum * 3);
1387 : :
1388 : 0 : left -= burst;
1389 : : cn20k_nix_sec_steorl(io_addr, lmt_id, lnum, loff, shft);
1390 : 0 : rte_io_wmb();
1391 [ # # ]: 0 : if (left) {
1392 : 0 : inst = RTE_PTR_ADD(inst, burst * sizeof(struct cpt_inst_s));
1393 : 0 : goto again;
1394 : : }
1395 : : return nb_inst;
1396 : : }
1397 : :
1398 : : void
1399 : 0 : cn20k_eth_sec_ops_override(void)
1400 : : {
1401 : : static int init_once;
1402 : 0 : uint32_t idx = 0;
1403 : :
1404 [ # # ]: 0 : if (init_once)
1405 : 0 : return;
1406 [ # # ]: 0 : init_once = 1;
1407 : :
1408 [ # # ]: 0 : if (roc_feature_nix_has_inl_ipsec())
1409 : 0 : eth_sec_caps_add(cn20k_eth_sec_capabilities, &idx, cn20k_eth_sec_ipsec_capabilities,
1410 : : RTE_DIM(cn20k_eth_sec_ipsec_capabilities));
1411 : :
1412 : 0 : cn20k_eth_sec_capabilities[idx].action = RTE_SECURITY_ACTION_TYPE_NONE;
1413 : :
1414 : : /* Update platform specific ops */
1415 : 0 : cnxk_eth_sec_ops.session_create = cn20k_eth_sec_session_create;
1416 : 0 : cnxk_eth_sec_ops.session_destroy = cn20k_eth_sec_session_destroy;
1417 : 0 : cnxk_eth_sec_ops.capabilities_get = cn20k_eth_sec_capabilities_get;
1418 : 0 : cnxk_eth_sec_ops.session_update = cn20k_eth_sec_session_update;
1419 : 0 : cnxk_eth_sec_ops.session_stats_get = cn20k_eth_sec_session_stats_get;
1420 : 0 : cnxk_eth_sec_ops.rx_inject_configure = cn20k_eth_sec_rx_inject_config;
1421 : 0 : cnxk_eth_sec_ops.inb_pkt_rx_inject = cn20k_eth_sec_inb_rx_inject;
1422 : :
1423 : : /* Update platform specific rte_pmd_cnxk ops */
1424 : 0 : cnxk_pmd_ops.inl_dev_submit = cn20k_inl_dev_submit;
1425 : : }
|