xref: /dpdk/lib/ipsec/rte_ipsec.h (revision aae98b8c6690ccc49d7a1536a1b1ee1264de49a7)
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2018-2020 Intel Corporation
3  */
4 
5 #ifndef _RTE_IPSEC_H_
6 #define _RTE_IPSEC_H_
7 
8 /**
9  * @file rte_ipsec.h
10  *
11  * RTE IPsec support.
12  *
13  * librte_ipsec provides a framework for data-path IPsec protocol
14  * processing (ESP/AH).
15  */
16 
17 #include <rte_ipsec_sa.h>
18 #include <rte_mbuf.h>
19 
20 struct rte_ipsec_session;
21 
22 /**
23  * IPsec state for stateless processing of a batch of IPsec packets.
24  */
25 struct rte_ipsec_state {
26 	/**
27 	 * 64 bit sequence number to be used for the first packet of the
28 	 * batch of packets.
29 	 */
30 	uint64_t sqn;
31 };
32 
33 /**
34  * IPsec session specific functions that will be used to:
35  * - prepare - for input mbufs and given IPsec session prepare crypto ops
36  *   that can be enqueued into the cryptodev associated with given session
37  *   (see *rte_ipsec_pkt_crypto_prepare* below for more details).
38  * - prepare_stateless - similar to prepare, but further processing is done
39  *   based on IPsec state provided by the 'state' parameter.
40  * - process - finalize processing of packets after crypto-dev finished
41  *   with them or process packets that are subjects to inline IPsec offload
42  *   (see rte_ipsec_pkt_process for more details).
43  */
44 struct rte_ipsec_sa_pkt_func {
45 	union {
46 		uint16_t (*async)(const struct rte_ipsec_session *ss,
47 				struct rte_mbuf *mb[],
48 				struct rte_crypto_op *cop[],
49 				uint16_t num);
50 		uint16_t (*sync)(const struct rte_ipsec_session *ss,
51 				struct rte_mbuf *mb[],
52 				uint16_t num);
53 	} prepare;
54 	union {
55 		uint16_t (*async)(const struct rte_ipsec_session *ss,
56 				struct rte_mbuf *mb[],
57 				struct rte_crypto_op *cop[],
58 				uint16_t num,
59 				struct rte_ipsec_state *state);
60 		uint16_t (*sync)(const struct rte_ipsec_session *ss,
61 				struct rte_mbuf *mb[],
62 				uint16_t num,
63 				struct rte_ipsec_state *state);
64 	} prepare_stateless;
65 	uint16_t (*process)(const struct rte_ipsec_session *ss,
66 				struct rte_mbuf *mb[],
67 				uint16_t num);
68 };
69 
70 /**
71  * rte_ipsec_session is an aggregate structure that defines particular
72  * IPsec Security Association IPsec (SA) on given security/crypto device:
73  * - pointer to the SA object
74  * - security session action type
75  * - pointer to security/crypto session, plus other related data
76  * - session/device specific functions to prepare/process IPsec packets.
77  */
78 struct __rte_cache_aligned rte_ipsec_session {
79 	/**
80 	 * SA that session belongs to.
81 	 * Note that multiple sessions can belong to the same SA.
82 	 */
83 	struct rte_ipsec_sa *sa;
84 	/** session action type */
85 	enum rte_security_session_action_type type;
86 	/** session and related data */
87 	union {
88 		struct {
89 			struct rte_cryptodev_sym_session *ses;
90 			uint8_t dev_id;
91 		} crypto;
92 		struct {
93 			struct rte_security_session *ses;
94 			struct rte_security_ctx *ctx;
95 			uint32_t ol_flags;
96 		} security;
97 	};
98 	/** functions to prepare/process IPsec packets */
99 	struct rte_ipsec_sa_pkt_func pkt_func;
100 };
101 
102 /**
103  * Checks that inside given rte_ipsec_session crypto/security fields
104  * are filled correctly and setups function pointers based on these values.
105  * Expects that all fields except IPsec processing function pointers
106  * (*pkt_func*) will be filled correctly by caller.
107  * @param ss
108  *   Pointer to the *rte_ipsec_session* object
109  * @return
110  *   - Zero if operation completed successfully.
111  *   - -EINVAL if the parameters are invalid.
112  */
113 int
114 rte_ipsec_session_prepare(struct rte_ipsec_session *ss);
115 
116 /**
117  * For input mbufs and given IPsec session prepare crypto ops that can be
118  * enqueued into the cryptodev associated with given session.
119  * expects that for each input packet:
120  *      - l2_len, l3_len are setup correctly
121  * Note that erroneous mbufs are not freed by the function,
122  * but are placed beyond last valid mbuf in the *mb* array.
123  * It is a user responsibility to handle them further.
124  * @param ss
125  *   Pointer to the *rte_ipsec_session* object the packets belong to.
126  * @param mb
127  *   The address of an array of *num* pointers to *rte_mbuf* structures
128  *   which contain the input packets.
129  * @param cop
130  *   The address of an array of *num* pointers to the output *rte_crypto_op*
131  *   structures.
132  * @param num
133  *   The maximum number of packets to process.
134  * @return
135  *   Number of successfully processed packets, with error code set in rte_errno.
136  */
137 static inline uint16_t
138 rte_ipsec_pkt_crypto_prepare(const struct rte_ipsec_session *ss,
139 	struct rte_mbuf *mb[], struct rte_crypto_op *cop[], uint16_t num)
140 {
141 	return ss->pkt_func.prepare.async(ss, mb, cop, num);
142 }
143 
144 static inline uint16_t
145 rte_ipsec_pkt_cpu_prepare(const struct rte_ipsec_session *ss,
146 	struct rte_mbuf *mb[], uint16_t num)
147 {
148 	return ss->pkt_func.prepare.sync(ss, mb, num);
149 }
150 
151 /**
152  * Same as *rte_ipsec_pkt_crypto_prepare*, but processing is done based on
153  * IPsec state provided by the 'state' parameter. Internal IPsec state won't
154  * be updated when this API is called.
155  *
156  * For input mbufs and given IPsec session prepare crypto ops that can be
157  * enqueued into the cryptodev associated with given session.
158  * expects that for each input packet:
159  *      - l2_len, l3_len are setup correctly
160  * Note that erroneous mbufs are not freed by the function,
161  * but are placed beyond last valid mbuf in the *mb* array.
162  * It is a user responsibility to handle them further.
163  * @param ss
164  *   Pointer to the *rte_ipsec_session* object the packets belong to.
165  * @param mb
166  *   The address of an array of *num* pointers to *rte_mbuf* structures
167  *   which contain the input packets.
168  * @param cop
169  *   The address of an array of *num* pointers to the output *rte_crypto_op*
170  *   structures.
171  * @param num
172  *   The maximum number of packets to process.
173  * @param state
174  *   The IPsec state to be used for processing current batch of packets.
175  * @return
176  *   Number of successfully processed packets, with error code set in rte_errno.
177  */
178 __rte_experimental
179 static inline uint16_t
180 rte_ipsec_pkt_crypto_prepare_stateless(const struct rte_ipsec_session *ss,
181 	struct rte_mbuf *mb[], struct rte_crypto_op *cop[], uint16_t num,
182 	struct rte_ipsec_state *state)
183 {
184 	return ss->pkt_func.prepare_stateless.async(ss, mb, cop, num, state);
185 }
186 
187 /**
188  * Same as *rte_ipsec_pkt_crypto_prepare_stateless*, but processing is done
189  * in synchronous mode.
190  *
191  * @param ss
192  *   Pointer to the *rte_ipsec_session* object the packets belong to.
193  * @param mb
194  *   The address of an array of *num* pointers to *rte_mbuf* structures
195  *   which contain the input packets.
196  * @param num
197  *   The maximum number of packets to process.
198  * @param state
199  *   The IPsec state to be used for processing current batch of packets.
200  * @return
201  *   Number of successfully processed packets, with error code set in rte_errno.
202  */
203 __rte_experimental
204 static inline uint16_t
205 rte_ipsec_pkt_cpu_prepare_stateless(const struct rte_ipsec_session *ss,
206 	struct rte_mbuf *mb[], uint16_t num, struct rte_ipsec_state *state)
207 {
208 	return ss->pkt_func.prepare_stateless.sync(ss, mb, num, state);
209 }
210 
211 /**
212  * Finalise processing of packets after crypto-dev finished with them or
213  * process packets that are subjects to inline IPsec offload.
214  * Expects that for each input packet:
215  *      - l2_len, l3_len are setup correctly
216  * Output mbufs will be:
217  * inbound - decrypted & authenticated, ESP(AH) related headers removed,
218  * *l2_len* and *l3_len* fields are updated.
219  * outbound - appropriate mbuf fields (ol_flags, tx_offloads, etc.)
220  * properly setup, if necessary - IP headers updated, ESP(AH) fields added,
221  * Note that erroneous mbufs are not freed by the function,
222  * but are placed beyond last valid mbuf in the *mb* array.
223  * It is a user responsibility to handle them further.
224  * @param ss
225  *   Pointer to the *rte_ipsec_session* object the packets belong to.
226  * @param mb
227  *   The address of an array of *num* pointers to *rte_mbuf* structures
228  *   which contain the input packets.
229  * @param num
230  *   The maximum number of packets to process.
231  * @return
232  *   Number of successfully processed packets, with error code set in rte_errno.
233  */
234 static inline uint16_t
235 rte_ipsec_pkt_process(const struct rte_ipsec_session *ss, struct rte_mbuf *mb[],
236 	uint16_t num)
237 {
238 	return ss->pkt_func.process(ss, mb, num);
239 }
240 
241 
242 /**
243  * Enable per SA telemetry for a specific SA.
244  * Note that this function is not thread safe
245  * @param sa
246  *   Pointer to the *rte_ipsec_sa* object that will have telemetry enabled.
247  * @return
248  *   0 on success, negative value otherwise.
249  */
250 int
251 rte_ipsec_telemetry_sa_add(const struct rte_ipsec_sa *sa);
252 
253 /**
254  * Disable per SA telemetry for a specific SA.
255  * Note that this function is not thread safe
256  * @param sa
257  *   Pointer to the *rte_ipsec_sa* object that will have telemetry disabled.
258  */
259 void
260 rte_ipsec_telemetry_sa_del(const struct rte_ipsec_sa *sa);
261 
262 #include <rte_ipsec_group.h>
263 
264 #ifdef __cplusplus
265 extern "C" {
266 #endif
267 
268 #ifdef __cplusplus
269 }
270 #endif
271 
272 #endif /* _RTE_IPSEC_H_ */
273