]>
Commit | Line | Data |
---|---|---|
11fdf7f2 TL |
1 | /* SPDX-License-Identifier: BSD-3-Clause |
2 | * Copyright(c) 2016-2018 Intel Corporation | |
7c673cae FG |
3 | */ |
4 | ||
5 | #include <rte_common.h> | |
7c673cae FG |
6 | #include <rte_hexdump.h> |
7 | #include <rte_cryptodev.h> | |
8 | #include <rte_cryptodev_pmd.h> | |
11fdf7f2 | 9 | #include <rte_bus_vdev.h> |
7c673cae FG |
10 | #include <rte_malloc.h> |
11 | #include <rte_cpuflags.h> | |
12 | ||
13 | #include "rte_zuc_pmd_private.h" | |
11fdf7f2 | 14 | #define ZUC_MAX_BURST 4 |
7c673cae FG |
15 | #define BYTE_LEN 8 |
16 | ||
11fdf7f2 | 17 | static uint8_t cryptodev_driver_id; |
7c673cae FG |
18 | |
19 | /** Get xform chain order. */ | |
20 | static enum zuc_operation | |
21 | zuc_get_mode(const struct rte_crypto_sym_xform *xform) | |
22 | { | |
23 | if (xform == NULL) | |
24 | return ZUC_OP_NOT_SUPPORTED; | |
25 | ||
26 | if (xform->next) | |
27 | if (xform->next->next != NULL) | |
28 | return ZUC_OP_NOT_SUPPORTED; | |
29 | ||
30 | if (xform->type == RTE_CRYPTO_SYM_XFORM_AUTH) { | |
31 | if (xform->next == NULL) | |
32 | return ZUC_OP_ONLY_AUTH; | |
33 | else if (xform->next->type == RTE_CRYPTO_SYM_XFORM_CIPHER) | |
34 | return ZUC_OP_AUTH_CIPHER; | |
35 | else | |
36 | return ZUC_OP_NOT_SUPPORTED; | |
37 | } | |
38 | ||
39 | if (xform->type == RTE_CRYPTO_SYM_XFORM_CIPHER) { | |
40 | if (xform->next == NULL) | |
41 | return ZUC_OP_ONLY_CIPHER; | |
42 | else if (xform->next->type == RTE_CRYPTO_SYM_XFORM_AUTH) | |
43 | return ZUC_OP_CIPHER_AUTH; | |
44 | else | |
45 | return ZUC_OP_NOT_SUPPORTED; | |
46 | } | |
47 | ||
48 | return ZUC_OP_NOT_SUPPORTED; | |
49 | } | |
50 | ||
51 | ||
52 | /** Parse crypto xform chain and set private session parameters. */ | |
53 | int | |
54 | zuc_set_session_parameters(struct zuc_session *sess, | |
55 | const struct rte_crypto_sym_xform *xform) | |
56 | { | |
57 | const struct rte_crypto_sym_xform *auth_xform = NULL; | |
58 | const struct rte_crypto_sym_xform *cipher_xform = NULL; | |
59 | enum zuc_operation mode; | |
60 | ||
61 | /* Select Crypto operation - hash then cipher / cipher then hash */ | |
62 | mode = zuc_get_mode(xform); | |
63 | ||
64 | switch (mode) { | |
65 | case ZUC_OP_CIPHER_AUTH: | |
66 | auth_xform = xform->next; | |
67 | ||
68 | /* Fall-through */ | |
69 | case ZUC_OP_ONLY_CIPHER: | |
70 | cipher_xform = xform; | |
71 | break; | |
72 | case ZUC_OP_AUTH_CIPHER: | |
73 | cipher_xform = xform->next; | |
74 | /* Fall-through */ | |
75 | case ZUC_OP_ONLY_AUTH: | |
76 | auth_xform = xform; | |
77 | break; | |
78 | case ZUC_OP_NOT_SUPPORTED: | |
79 | default: | |
11fdf7f2 TL |
80 | ZUC_LOG(ERR, "Unsupported operation chain order parameter"); |
81 | return -ENOTSUP; | |
7c673cae FG |
82 | } |
83 | ||
84 | if (cipher_xform) { | |
85 | /* Only ZUC EEA3 supported */ | |
86 | if (cipher_xform->cipher.algo != RTE_CRYPTO_CIPHER_ZUC_EEA3) | |
11fdf7f2 TL |
87 | return -ENOTSUP; |
88 | ||
89 | if (cipher_xform->cipher.iv.length != ZUC_IV_KEY_LENGTH) { | |
90 | ZUC_LOG(ERR, "Wrong IV length"); | |
7c673cae | 91 | return -EINVAL; |
11fdf7f2 TL |
92 | } |
93 | sess->cipher_iv_offset = cipher_xform->cipher.iv.offset; | |
94 | ||
7c673cae | 95 | /* Copy the key */ |
11fdf7f2 TL |
96 | memcpy(sess->pKey_cipher, cipher_xform->cipher.key.data, |
97 | ZUC_IV_KEY_LENGTH); | |
7c673cae FG |
98 | } |
99 | ||
100 | if (auth_xform) { | |
101 | /* Only ZUC EIA3 supported */ | |
102 | if (auth_xform->auth.algo != RTE_CRYPTO_AUTH_ZUC_EIA3) | |
11fdf7f2 TL |
103 | return -ENOTSUP; |
104 | ||
105 | if (auth_xform->auth.digest_length != ZUC_DIGEST_LENGTH) { | |
106 | ZUC_LOG(ERR, "Wrong digest length"); | |
7c673cae | 107 | return -EINVAL; |
11fdf7f2 TL |
108 | } |
109 | ||
7c673cae | 110 | sess->auth_op = auth_xform->auth.op; |
11fdf7f2 TL |
111 | |
112 | if (auth_xform->auth.iv.length != ZUC_IV_KEY_LENGTH) { | |
113 | ZUC_LOG(ERR, "Wrong IV length"); | |
114 | return -EINVAL; | |
115 | } | |
116 | sess->auth_iv_offset = auth_xform->auth.iv.offset; | |
117 | ||
7c673cae | 118 | /* Copy the key */ |
11fdf7f2 TL |
119 | memcpy(sess->pKey_hash, auth_xform->auth.key.data, |
120 | ZUC_IV_KEY_LENGTH); | |
7c673cae FG |
121 | } |
122 | ||
123 | ||
124 | sess->op = mode; | |
125 | ||
126 | return 0; | |
127 | } | |
128 | ||
129 | /** Get ZUC session. */ | |
130 | static struct zuc_session * | |
131 | zuc_get_session(struct zuc_qp *qp, struct rte_crypto_op *op) | |
132 | { | |
11fdf7f2 TL |
133 | struct zuc_session *sess = NULL; |
134 | ||
135 | if (op->sess_type == RTE_CRYPTO_OP_WITH_SESSION) { | |
136 | if (likely(op->sym->session != NULL)) | |
137 | sess = (struct zuc_session *)get_sym_session_private_data( | |
138 | op->sym->session, | |
139 | cryptodev_driver_id); | |
140 | } else { | |
141 | void *_sess = NULL; | |
142 | void *_sess_private_data = NULL; | |
143 | ||
144 | if (rte_mempool_get(qp->sess_mp, (void **)&_sess)) | |
7c673cae FG |
145 | return NULL; |
146 | ||
9f95a23c TL |
147 | if (rte_mempool_get(qp->sess_mp_priv, |
148 | (void **)&_sess_private_data)) | |
7c673cae FG |
149 | return NULL; |
150 | ||
11fdf7f2 | 151 | sess = (struct zuc_session *)_sess_private_data; |
7c673cae FG |
152 | |
153 | if (unlikely(zuc_set_session_parameters(sess, | |
11fdf7f2 TL |
154 | op->sym->xform) != 0)) { |
155 | rte_mempool_put(qp->sess_mp, _sess); | |
9f95a23c | 156 | rte_mempool_put(qp->sess_mp_priv, _sess_private_data); |
11fdf7f2 TL |
157 | sess = NULL; |
158 | } | |
159 | op->sym->session = (struct rte_cryptodev_sym_session *)_sess; | |
160 | set_sym_session_private_data(op->sym->session, | |
161 | cryptodev_driver_id, _sess_private_data); | |
7c673cae FG |
162 | } |
163 | ||
11fdf7f2 TL |
164 | if (unlikely(sess == NULL)) |
165 | op->status = RTE_CRYPTO_OP_STATUS_INVALID_SESSION; | |
166 | ||
167 | ||
7c673cae FG |
168 | return sess; |
169 | } | |
170 | ||
11fdf7f2 | 171 | /** Encrypt/decrypt mbufs. */ |
7c673cae FG |
172 | static uint8_t |
173 | process_zuc_cipher_op(struct rte_crypto_op **ops, | |
11fdf7f2 | 174 | struct zuc_session **sessions, |
7c673cae FG |
175 | uint8_t num_ops) |
176 | { | |
177 | unsigned i; | |
178 | uint8_t processed_ops = 0; | |
179 | uint8_t *src[ZUC_MAX_BURST], *dst[ZUC_MAX_BURST]; | |
11fdf7f2 | 180 | uint8_t *iv[ZUC_MAX_BURST]; |
7c673cae FG |
181 | uint32_t num_bytes[ZUC_MAX_BURST]; |
182 | uint8_t *cipher_keys[ZUC_MAX_BURST]; | |
11fdf7f2 | 183 | struct zuc_session *sess; |
7c673cae FG |
184 | |
185 | for (i = 0; i < num_ops; i++) { | |
11fdf7f2 TL |
186 | if (((ops[i]->sym->cipher.data.length % BYTE_LEN) != 0) |
187 | || ((ops[i]->sym->cipher.data.offset | |
188 | % BYTE_LEN) != 0)) { | |
7c673cae | 189 | ops[i]->status = RTE_CRYPTO_OP_STATUS_INVALID_ARGS; |
11fdf7f2 | 190 | ZUC_LOG(ERR, "Data Length or offset"); |
7c673cae FG |
191 | break; |
192 | } | |
193 | ||
11fdf7f2 TL |
194 | sess = sessions[i]; |
195 | ||
196 | #ifdef RTE_LIBRTE_PMD_ZUC_DEBUG | |
197 | if (!rte_pktmbuf_is_contiguous(ops[i]->sym->m_src) || | |
198 | (ops[i]->sym->m_dst != NULL && | |
199 | !rte_pktmbuf_is_contiguous( | |
200 | ops[i]->sym->m_dst))) { | |
201 | ZUC_LOG(ERR, "PMD supports only contiguous mbufs, " | |
202 | "op (%p) provides noncontiguous mbuf as " | |
203 | "source/destination buffer.\n", ops[i]); | |
7c673cae | 204 | ops[i]->status = RTE_CRYPTO_OP_STATUS_INVALID_ARGS; |
7c673cae FG |
205 | break; |
206 | } | |
11fdf7f2 | 207 | #endif |
7c673cae FG |
208 | |
209 | src[i] = rte_pktmbuf_mtod(ops[i]->sym->m_src, uint8_t *) + | |
210 | (ops[i]->sym->cipher.data.offset >> 3); | |
211 | dst[i] = ops[i]->sym->m_dst ? | |
212 | rte_pktmbuf_mtod(ops[i]->sym->m_dst, uint8_t *) + | |
213 | (ops[i]->sym->cipher.data.offset >> 3) : | |
214 | rte_pktmbuf_mtod(ops[i]->sym->m_src, uint8_t *) + | |
215 | (ops[i]->sym->cipher.data.offset >> 3); | |
11fdf7f2 TL |
216 | iv[i] = rte_crypto_op_ctod_offset(ops[i], uint8_t *, |
217 | sess->cipher_iv_offset); | |
7c673cae FG |
218 | num_bytes[i] = ops[i]->sym->cipher.data.length >> 3; |
219 | ||
11fdf7f2 | 220 | cipher_keys[i] = sess->pKey_cipher; |
7c673cae FG |
221 | |
222 | processed_ops++; | |
223 | } | |
224 | ||
11fdf7f2 | 225 | sso_zuc_eea3_n_buffer(cipher_keys, iv, src, dst, |
7c673cae FG |
226 | num_bytes, processed_ops); |
227 | ||
228 | return processed_ops; | |
229 | } | |
230 | ||
11fdf7f2 | 231 | /** Generate/verify hash from mbufs. */ |
7c673cae | 232 | static int |
11fdf7f2 TL |
233 | process_zuc_hash_op(struct zuc_qp *qp, struct rte_crypto_op **ops, |
234 | struct zuc_session **sessions, | |
7c673cae FG |
235 | uint8_t num_ops) |
236 | { | |
237 | unsigned i; | |
238 | uint8_t processed_ops = 0; | |
239 | uint8_t *src; | |
240 | uint32_t *dst; | |
241 | uint32_t length_in_bits; | |
11fdf7f2 TL |
242 | uint8_t *iv; |
243 | struct zuc_session *sess; | |
7c673cae FG |
244 | |
245 | for (i = 0; i < num_ops; i++) { | |
7c673cae FG |
246 | /* Data must be byte aligned */ |
247 | if ((ops[i]->sym->auth.data.offset % BYTE_LEN) != 0) { | |
248 | ops[i]->status = RTE_CRYPTO_OP_STATUS_INVALID_ARGS; | |
11fdf7f2 | 249 | ZUC_LOG(ERR, "Offset"); |
7c673cae FG |
250 | break; |
251 | } | |
252 | ||
11fdf7f2 TL |
253 | sess = sessions[i]; |
254 | ||
7c673cae FG |
255 | length_in_bits = ops[i]->sym->auth.data.length; |
256 | ||
257 | src = rte_pktmbuf_mtod(ops[i]->sym->m_src, uint8_t *) + | |
258 | (ops[i]->sym->auth.data.offset >> 3); | |
11fdf7f2 TL |
259 | iv = rte_crypto_op_ctod_offset(ops[i], uint8_t *, |
260 | sess->auth_iv_offset); | |
7c673cae | 261 | |
11fdf7f2 TL |
262 | if (sess->auth_op == RTE_CRYPTO_AUTH_OP_VERIFY) { |
263 | dst = (uint32_t *)qp->temp_digest; | |
7c673cae | 264 | |
11fdf7f2 TL |
265 | sso_zuc_eia3_1_buffer(sess->pKey_hash, |
266 | iv, src, | |
7c673cae FG |
267 | length_in_bits, dst); |
268 | /* Verify digest. */ | |
269 | if (memcmp(dst, ops[i]->sym->auth.digest.data, | |
11fdf7f2 | 270 | ZUC_DIGEST_LENGTH) != 0) |
7c673cae | 271 | ops[i]->status = RTE_CRYPTO_OP_STATUS_AUTH_FAILED; |
7c673cae FG |
272 | } else { |
273 | dst = (uint32_t *)ops[i]->sym->auth.digest.data; | |
274 | ||
11fdf7f2 TL |
275 | sso_zuc_eia3_1_buffer(sess->pKey_hash, |
276 | iv, src, | |
7c673cae FG |
277 | length_in_bits, dst); |
278 | } | |
279 | processed_ops++; | |
280 | } | |
281 | ||
282 | return processed_ops; | |
283 | } | |
284 | ||
11fdf7f2 | 285 | /** Process a batch of crypto ops which shares the same operation type. */ |
7c673cae | 286 | static int |
11fdf7f2 TL |
287 | process_ops(struct rte_crypto_op **ops, enum zuc_operation op_type, |
288 | struct zuc_session **sessions, | |
7c673cae FG |
289 | struct zuc_qp *qp, uint8_t num_ops, |
290 | uint16_t *accumulated_enqueued_ops) | |
291 | { | |
292 | unsigned i; | |
293 | unsigned enqueued_ops, processed_ops; | |
294 | ||
11fdf7f2 | 295 | switch (op_type) { |
7c673cae FG |
296 | case ZUC_OP_ONLY_CIPHER: |
297 | processed_ops = process_zuc_cipher_op(ops, | |
11fdf7f2 | 298 | sessions, num_ops); |
7c673cae FG |
299 | break; |
300 | case ZUC_OP_ONLY_AUTH: | |
11fdf7f2 | 301 | processed_ops = process_zuc_hash_op(qp, ops, sessions, |
7c673cae FG |
302 | num_ops); |
303 | break; | |
304 | case ZUC_OP_CIPHER_AUTH: | |
11fdf7f2 | 305 | processed_ops = process_zuc_cipher_op(ops, sessions, |
7c673cae | 306 | num_ops); |
11fdf7f2 | 307 | process_zuc_hash_op(qp, ops, sessions, processed_ops); |
7c673cae FG |
308 | break; |
309 | case ZUC_OP_AUTH_CIPHER: | |
11fdf7f2 | 310 | processed_ops = process_zuc_hash_op(qp, ops, sessions, |
7c673cae | 311 | num_ops); |
11fdf7f2 | 312 | process_zuc_cipher_op(ops, sessions, processed_ops); |
7c673cae FG |
313 | break; |
314 | default: | |
315 | /* Operation not supported. */ | |
316 | processed_ops = 0; | |
317 | } | |
318 | ||
319 | for (i = 0; i < num_ops; i++) { | |
320 | /* | |
321 | * If there was no error/authentication failure, | |
322 | * change status to successful. | |
323 | */ | |
324 | if (ops[i]->status == RTE_CRYPTO_OP_STATUS_NOT_PROCESSED) | |
325 | ops[i]->status = RTE_CRYPTO_OP_STATUS_SUCCESS; | |
326 | /* Free session if a session-less crypto op. */ | |
11fdf7f2 TL |
327 | if (ops[i]->sess_type == RTE_CRYPTO_OP_SESSIONLESS) { |
328 | memset(sessions[i], 0, sizeof(struct zuc_session)); | |
329 | memset(ops[i]->sym->session, 0, | |
9f95a23c TL |
330 | rte_cryptodev_sym_get_existing_header_session_size( |
331 | ops[i]->sym->session)); | |
332 | rte_mempool_put(qp->sess_mp_priv, sessions[i]); | |
7c673cae FG |
333 | rte_mempool_put(qp->sess_mp, ops[i]->sym->session); |
334 | ops[i]->sym->session = NULL; | |
335 | } | |
336 | } | |
337 | ||
338 | enqueued_ops = rte_ring_enqueue_burst(qp->processed_ops, | |
11fdf7f2 | 339 | (void **)ops, processed_ops, NULL); |
7c673cae FG |
340 | qp->qp_stats.enqueued_count += enqueued_ops; |
341 | *accumulated_enqueued_ops += enqueued_ops; | |
342 | ||
343 | return enqueued_ops; | |
344 | } | |
345 | ||
346 | static uint16_t | |
347 | zuc_pmd_enqueue_burst(void *queue_pair, struct rte_crypto_op **ops, | |
348 | uint16_t nb_ops) | |
349 | { | |
350 | struct rte_crypto_op *c_ops[ZUC_MAX_BURST]; | |
351 | struct rte_crypto_op *curr_c_op; | |
352 | ||
11fdf7f2 TL |
353 | struct zuc_session *curr_sess; |
354 | struct zuc_session *sessions[ZUC_MAX_BURST]; | |
355 | enum zuc_operation prev_zuc_op = ZUC_OP_NOT_SUPPORTED; | |
356 | enum zuc_operation curr_zuc_op; | |
7c673cae FG |
357 | struct zuc_qp *qp = queue_pair; |
358 | unsigned i; | |
359 | uint8_t burst_size = 0; | |
360 | uint16_t enqueued_ops = 0; | |
361 | uint8_t processed_ops; | |
362 | ||
363 | for (i = 0; i < nb_ops; i++) { | |
364 | curr_c_op = ops[i]; | |
365 | ||
7c673cae | 366 | curr_sess = zuc_get_session(qp, curr_c_op); |
11fdf7f2 | 367 | if (unlikely(curr_sess == NULL)) { |
7c673cae FG |
368 | curr_c_op->status = |
369 | RTE_CRYPTO_OP_STATUS_INVALID_SESSION; | |
370 | break; | |
371 | } | |
372 | ||
11fdf7f2 TL |
373 | curr_zuc_op = curr_sess->op; |
374 | ||
375 | /* | |
376 | * Batch ops that share the same operation type | |
377 | * (cipher only, auth only...). | |
378 | */ | |
379 | if (burst_size == 0) { | |
380 | prev_zuc_op = curr_zuc_op; | |
381 | c_ops[0] = curr_c_op; | |
382 | sessions[0] = curr_sess; | |
383 | burst_size++; | |
384 | } else if (curr_zuc_op == prev_zuc_op) { | |
385 | c_ops[burst_size] = curr_c_op; | |
386 | sessions[burst_size] = curr_sess; | |
387 | burst_size++; | |
7c673cae FG |
388 | /* |
389 | * When there are enough ops to process in a batch, | |
390 | * process them, and start a new batch. | |
391 | */ | |
392 | if (burst_size == ZUC_MAX_BURST) { | |
11fdf7f2 TL |
393 | processed_ops = process_ops(c_ops, curr_zuc_op, |
394 | sessions, qp, burst_size, | |
395 | &enqueued_ops); | |
7c673cae FG |
396 | if (processed_ops < burst_size) { |
397 | burst_size = 0; | |
398 | break; | |
399 | } | |
400 | ||
401 | burst_size = 0; | |
7c673cae FG |
402 | } |
403 | } else { | |
404 | /* | |
11fdf7f2 TL |
405 | * Different operation type, process the ops |
406 | * of the previous type. | |
7c673cae | 407 | */ |
11fdf7f2 TL |
408 | processed_ops = process_ops(c_ops, prev_zuc_op, |
409 | sessions, qp, burst_size, | |
410 | &enqueued_ops); | |
7c673cae FG |
411 | if (processed_ops < burst_size) { |
412 | burst_size = 0; | |
413 | break; | |
414 | } | |
415 | ||
416 | burst_size = 0; | |
11fdf7f2 | 417 | prev_zuc_op = curr_zuc_op; |
7c673cae | 418 | |
11fdf7f2 TL |
419 | c_ops[0] = curr_c_op; |
420 | sessions[0] = curr_sess; | |
421 | burst_size++; | |
7c673cae FG |
422 | } |
423 | } | |
424 | ||
425 | if (burst_size != 0) { | |
11fdf7f2 TL |
426 | /* Process the crypto ops of the last operation type. */ |
427 | processed_ops = process_ops(c_ops, prev_zuc_op, | |
428 | sessions, qp, burst_size, | |
429 | &enqueued_ops); | |
7c673cae FG |
430 | } |
431 | ||
432 | qp->qp_stats.enqueue_err_count += nb_ops - enqueued_ops; | |
433 | return enqueued_ops; | |
434 | } | |
435 | ||
436 | static uint16_t | |
437 | zuc_pmd_dequeue_burst(void *queue_pair, | |
438 | struct rte_crypto_op **c_ops, uint16_t nb_ops) | |
439 | { | |
440 | struct zuc_qp *qp = queue_pair; | |
441 | ||
442 | unsigned nb_dequeued; | |
443 | ||
444 | nb_dequeued = rte_ring_dequeue_burst(qp->processed_ops, | |
11fdf7f2 | 445 | (void **)c_ops, nb_ops, NULL); |
7c673cae FG |
446 | qp->qp_stats.dequeued_count += nb_dequeued; |
447 | ||
448 | return nb_dequeued; | |
449 | } | |
450 | ||
11fdf7f2 | 451 | static int cryptodev_zuc_remove(struct rte_vdev_device *vdev); |
7c673cae FG |
452 | |
453 | static int | |
454 | cryptodev_zuc_create(const char *name, | |
11fdf7f2 TL |
455 | struct rte_vdev_device *vdev, |
456 | struct rte_cryptodev_pmd_init_params *init_params) | |
7c673cae FG |
457 | { |
458 | struct rte_cryptodev *dev; | |
7c673cae | 459 | struct zuc_private *internals; |
11fdf7f2 | 460 | uint64_t cpu_flags = RTE_CRYPTODEV_FF_CPU_SSE; |
7c673cae FG |
461 | |
462 | ||
11fdf7f2 | 463 | dev = rte_cryptodev_pmd_create(name, &vdev->device, init_params); |
7c673cae | 464 | if (dev == NULL) { |
11fdf7f2 | 465 | ZUC_LOG(ERR, "failed to create cryptodev vdev"); |
7c673cae FG |
466 | goto init_error; |
467 | } | |
468 | ||
11fdf7f2 | 469 | dev->driver_id = cryptodev_driver_id; |
7c673cae FG |
470 | dev->dev_ops = rte_zuc_pmd_ops; |
471 | ||
472 | /* Register RX/TX burst functions for data path. */ | |
473 | dev->dequeue_burst = zuc_pmd_dequeue_burst; | |
474 | dev->enqueue_burst = zuc_pmd_enqueue_burst; | |
475 | ||
476 | dev->feature_flags = RTE_CRYPTODEV_FF_SYMMETRIC_CRYPTO | | |
477 | RTE_CRYPTODEV_FF_SYM_OPERATION_CHAINING | | |
478 | cpu_flags; | |
479 | ||
480 | internals = dev->data->dev_private; | |
481 | ||
482 | internals->max_nb_queue_pairs = init_params->max_nb_queue_pairs; | |
7c673cae FG |
483 | |
484 | return 0; | |
485 | init_error: | |
11fdf7f2 TL |
486 | ZUC_LOG(ERR, "driver %s: failed", |
487 | init_params->name); | |
7c673cae | 488 | |
11fdf7f2 | 489 | cryptodev_zuc_remove(vdev); |
7c673cae FG |
490 | return -EFAULT; |
491 | } | |
492 | ||
493 | static int | |
11fdf7f2 | 494 | cryptodev_zuc_probe(struct rte_vdev_device *vdev) |
7c673cae | 495 | { |
11fdf7f2 TL |
496 | struct rte_cryptodev_pmd_init_params init_params = { |
497 | "", | |
498 | sizeof(struct zuc_private), | |
499 | rte_socket_id(), | |
500 | RTE_CRYPTODEV_PMD_DEFAULT_MAX_NB_QUEUE_PAIRS | |
7c673cae | 501 | }; |
11fdf7f2 TL |
502 | const char *name; |
503 | const char *input_args; | |
7c673cae | 504 | |
11fdf7f2 TL |
505 | name = rte_vdev_device_name(vdev); |
506 | if (name == NULL) | |
507 | return -EINVAL; | |
508 | input_args = rte_vdev_device_args(vdev); | |
7c673cae | 509 | |
11fdf7f2 | 510 | rte_cryptodev_pmd_parse_input_args(&init_params, input_args); |
7c673cae | 511 | |
11fdf7f2 | 512 | return cryptodev_zuc_create(name, vdev, &init_params); |
7c673cae FG |
513 | } |
514 | ||
515 | static int | |
11fdf7f2 | 516 | cryptodev_zuc_remove(struct rte_vdev_device *vdev) |
7c673cae | 517 | { |
11fdf7f2 TL |
518 | |
519 | struct rte_cryptodev *cryptodev; | |
520 | const char *name; | |
521 | ||
522 | name = rte_vdev_device_name(vdev); | |
7c673cae FG |
523 | if (name == NULL) |
524 | return -EINVAL; | |
525 | ||
11fdf7f2 TL |
526 | cryptodev = rte_cryptodev_pmd_get_named_dev(name); |
527 | if (cryptodev == NULL) | |
528 | return -ENODEV; | |
7c673cae | 529 | |
11fdf7f2 | 530 | return rte_cryptodev_pmd_destroy(cryptodev); |
7c673cae FG |
531 | } |
532 | ||
533 | static struct rte_vdev_driver cryptodev_zuc_pmd_drv = { | |
534 | .probe = cryptodev_zuc_probe, | |
535 | .remove = cryptodev_zuc_remove | |
536 | }; | |
537 | ||
11fdf7f2 TL |
538 | static struct cryptodev_driver zuc_crypto_drv; |
539 | ||
7c673cae FG |
540 | RTE_PMD_REGISTER_VDEV(CRYPTODEV_NAME_ZUC_PMD, cryptodev_zuc_pmd_drv); |
541 | RTE_PMD_REGISTER_PARAM_STRING(CRYPTODEV_NAME_ZUC_PMD, | |
542 | "max_nb_queue_pairs=<int> " | |
7c673cae | 543 | "socket_id=<int>"); |
11fdf7f2 TL |
544 | RTE_PMD_REGISTER_CRYPTO_DRIVER(zuc_crypto_drv, cryptodev_zuc_pmd_drv.driver, |
545 | cryptodev_driver_id); | |
546 | ||
547 | RTE_INIT(zuc_init_log) | |
548 | { | |
549 | zuc_logtype_driver = rte_log_register("pmd.crypto.zuc"); | |
550 | } |