crypto/cnxk: support null authentication in IPsec
[dpdk.git] / drivers / crypto / cnxk / cn9k_ipsec_la_ops.h
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(C) 2021 Marvell.
3  */
4
5 #ifndef __CN9K_IPSEC_LA_OPS_H__
6 #define __CN9K_IPSEC_LA_OPS_H__
7
8 #include <rte_crypto_sym.h>
9 #include <rte_security.h>
10
11 #include "cn9k_ipsec.h"
12
13 static __rte_always_inline int32_t
14 ipsec_po_out_rlen_get(struct cn9k_ipsec_sa *sa, uint32_t plen)
15 {
16         uint32_t enc_payload_len;
17
18         enc_payload_len = RTE_ALIGN_CEIL(plen + sa->rlens.roundup_len,
19                                          sa->rlens.roundup_byte);
20
21         return sa->rlens.partial_len + enc_payload_len;
22 }
23
24 static __rte_always_inline int
25 process_outb_sa(struct rte_crypto_op *cop, struct cn9k_ipsec_sa *sa,
26                 struct cpt_inst_s *inst)
27 {
28         const unsigned int hdr_len = sizeof(struct roc_ie_on_outb_hdr);
29         struct rte_crypto_sym_op *sym_op = cop->sym;
30         struct rte_mbuf *m_src = sym_op->m_src;
31         uint32_t dlen, rlen, extend_tail;
32         struct roc_ie_on_outb_sa *out_sa;
33         struct roc_ie_on_outb_hdr *hdr;
34
35         out_sa = &sa->out_sa;
36
37         dlen = rte_pktmbuf_pkt_len(m_src) + hdr_len;
38         rlen = ipsec_po_out_rlen_get(sa, dlen - hdr_len);
39
40         extend_tail = rlen - dlen;
41         if (unlikely(extend_tail > rte_pktmbuf_tailroom(m_src))) {
42                 plt_dp_err("Not enough tail room");
43                 return -ENOMEM;
44         }
45
46         m_src->data_len += extend_tail;
47         m_src->pkt_len += extend_tail;
48
49         hdr = (struct roc_ie_on_outb_hdr *)rte_pktmbuf_prepend(m_src, hdr_len);
50         if (unlikely(hdr == NULL)) {
51                 plt_dp_err("Not enough head room");
52                 return -ENOMEM;
53         }
54
55         memcpy(&hdr->iv[0],
56                rte_crypto_op_ctod_offset(cop, uint8_t *, sa->cipher_iv_off),
57                sa->cipher_iv_len);
58         hdr->seq = rte_cpu_to_be_32(sa->seq_lo);
59         hdr->ip_id = rte_cpu_to_be_32(sa->ip_id);
60
61         out_sa->common_sa.esn_hi = sa->seq_hi;
62
63         sa->ip_id++;
64         sa->esn++;
65
66         /* Prepare CPT instruction */
67         inst->w4.u64 = sa->inst.w4 | dlen;
68         inst->dptr = rte_pktmbuf_iova(m_src);
69         inst->rptr = inst->dptr;
70         inst->w7.u64 = sa->inst.w7;
71
72         return 0;
73 }
74
75 static __rte_always_inline int
76 process_inb_sa(struct rte_crypto_op *cop, struct cn9k_ipsec_sa *sa,
77                struct cpt_inst_s *inst)
78 {
79         struct rte_crypto_sym_op *sym_op = cop->sym;
80         struct rte_mbuf *m_src = sym_op->m_src;
81
82         /* Prepare CPT instruction */
83         inst->w4.u64 = sa->inst.w4 | rte_pktmbuf_pkt_len(m_src);
84         inst->dptr = rte_pktmbuf_iova(m_src);
85         inst->rptr = inst->dptr;
86         inst->w7.u64 = sa->inst.w7;
87
88         return 0;
89 }
90 #endif /* __CN9K_IPSEC_LA_OPS_H__ */