crypto/qat: add symmetric session file
[dpdk.git] / drivers / crypto / qat / qat_crypto.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2015-2018 Intel Corporation
3  */
4
5 #include <rte_mempool.h>
6 #include <rte_mbuf.h>
7 #include <rte_hexdump.h>
8 #include <rte_crypto_sym.h>
9 #include <rte_byteorder.h>
10 #include <rte_pci.h>
11 #include <rte_bus_pci.h>
12
13 #include <openssl/evp.h>
14
15 #include "qat_logs.h"
16 #include "qat_sym_session.h"
17 #include "qat_crypto.h"
18 #include "adf_transport_access_macros.h"
19
20 #define BYTE_LENGTH    8
21 /* bpi is only used for partial blocks of DES and AES
22  * so AES block len can be assumed as max len for iv, src and dst
23  */
24 #define BPI_MAX_ENCR_IV_LEN ICP_QAT_HW_AES_BLK_SZ
25
26 /** Encrypt a single partial block
27  *  Depends on openssl libcrypto
28  *  Uses ECB+XOR to do CFB encryption, same result, more performant
29  */
30 static inline int
31 bpi_cipher_encrypt(uint8_t *src, uint8_t *dst,
32                 uint8_t *iv, int ivlen, int srclen,
33                 void *bpi_ctx)
34 {
35         EVP_CIPHER_CTX *ctx = (EVP_CIPHER_CTX *)bpi_ctx;
36         int encrypted_ivlen;
37         uint8_t encrypted_iv[BPI_MAX_ENCR_IV_LEN];
38         uint8_t *encr = encrypted_iv;
39
40         /* ECB method: encrypt the IV, then XOR this with plaintext */
41         if (EVP_EncryptUpdate(ctx, encrypted_iv, &encrypted_ivlen, iv, ivlen)
42                                                                 <= 0)
43                 goto cipher_encrypt_err;
44
45         for (; srclen != 0; --srclen, ++dst, ++src, ++encr)
46                 *dst = *src ^ *encr;
47
48         return 0;
49
50 cipher_encrypt_err:
51         PMD_DRV_LOG(ERR, "libcrypto ECB cipher encrypt failed");
52         return -EINVAL;
53 }
54
55 /** Decrypt a single partial block
56  *  Depends on openssl libcrypto
57  *  Uses ECB+XOR to do CFB encryption, same result, more performant
58  */
59 static inline int
60 bpi_cipher_decrypt(uint8_t *src, uint8_t *dst,
61                 uint8_t *iv, int ivlen, int srclen,
62                 void *bpi_ctx)
63 {
64         EVP_CIPHER_CTX *ctx = (EVP_CIPHER_CTX *)bpi_ctx;
65         int encrypted_ivlen;
66         uint8_t encrypted_iv[BPI_MAX_ENCR_IV_LEN];
67         uint8_t *encr = encrypted_iv;
68
69         /* ECB method: encrypt (not decrypt!) the IV, then XOR with plaintext */
70         if (EVP_EncryptUpdate(ctx, encrypted_iv, &encrypted_ivlen, iv, ivlen)
71                                                                 <= 0)
72                 goto cipher_decrypt_err;
73
74         for (; srclen != 0; --srclen, ++dst, ++src, ++encr)
75                 *dst = *src ^ *encr;
76
77         return 0;
78
79 cipher_decrypt_err:
80         PMD_DRV_LOG(ERR, "libcrypto ECB cipher decrypt for BPI IV failed");
81         return -EINVAL;
82 }
83
84 /** Creates a context in either AES or DES in ECB mode
85  *  Depends on openssl libcrypto
86  */
87 static inline uint32_t
88 adf_modulo(uint32_t data, uint32_t shift);
89
90 static inline int
91 qat_write_hw_desc_entry(struct rte_crypto_op *op, uint8_t *out_msg,
92                 struct qat_crypto_op_cookie *qat_op_cookie, struct qat_qp *qp);
93
94 static inline uint32_t
95 qat_bpicipher_preprocess(struct qat_session *ctx,
96                                 struct rte_crypto_op *op)
97 {
98         int block_len = qat_cipher_get_block_size(ctx->qat_cipher_alg);
99         struct rte_crypto_sym_op *sym_op = op->sym;
100         uint8_t last_block_len = block_len > 0 ?
101                         sym_op->cipher.data.length % block_len : 0;
102
103         if (last_block_len &&
104                         ctx->qat_dir == ICP_QAT_HW_CIPHER_DECRYPT) {
105
106                 /* Decrypt last block */
107                 uint8_t *last_block, *dst, *iv;
108                 uint32_t last_block_offset = sym_op->cipher.data.offset +
109                                 sym_op->cipher.data.length - last_block_len;
110                 last_block = (uint8_t *) rte_pktmbuf_mtod_offset(sym_op->m_src,
111                                 uint8_t *, last_block_offset);
112
113                 if (unlikely(sym_op->m_dst != NULL))
114                         /* out-of-place operation (OOP) */
115                         dst = (uint8_t *) rte_pktmbuf_mtod_offset(sym_op->m_dst,
116                                                 uint8_t *, last_block_offset);
117                 else
118                         dst = last_block;
119
120                 if (last_block_len < sym_op->cipher.data.length)
121                         /* use previous block ciphertext as IV */
122                         iv = last_block - block_len;
123                 else
124                         /* runt block, i.e. less than one full block */
125                         iv = rte_crypto_op_ctod_offset(op, uint8_t *,
126                                         ctx->cipher_iv.offset);
127
128 #ifdef RTE_LIBRTE_PMD_QAT_DEBUG_TX
129                 rte_hexdump(stdout, "BPI: src before pre-process:", last_block,
130                         last_block_len);
131                 if (sym_op->m_dst != NULL)
132                         rte_hexdump(stdout, "BPI: dst before pre-process:", dst,
133                                 last_block_len);
134 #endif
135                 bpi_cipher_decrypt(last_block, dst, iv, block_len,
136                                 last_block_len, ctx->bpi_ctx);
137 #ifdef RTE_LIBRTE_PMD_QAT_DEBUG_TX
138                 rte_hexdump(stdout, "BPI: src after pre-process:", last_block,
139                         last_block_len);
140                 if (sym_op->m_dst != NULL)
141                         rte_hexdump(stdout, "BPI: dst after pre-process:", dst,
142                                 last_block_len);
143 #endif
144         }
145
146         return sym_op->cipher.data.length - last_block_len;
147 }
148
149 static inline uint32_t
150 qat_bpicipher_postprocess(struct qat_session *ctx,
151                                 struct rte_crypto_op *op)
152 {
153         int block_len = qat_cipher_get_block_size(ctx->qat_cipher_alg);
154         struct rte_crypto_sym_op *sym_op = op->sym;
155         uint8_t last_block_len = block_len > 0 ?
156                         sym_op->cipher.data.length % block_len : 0;
157
158         if (last_block_len > 0 &&
159                         ctx->qat_dir == ICP_QAT_HW_CIPHER_ENCRYPT) {
160
161                 /* Encrypt last block */
162                 uint8_t *last_block, *dst, *iv;
163                 uint32_t last_block_offset;
164
165                 last_block_offset = sym_op->cipher.data.offset +
166                                 sym_op->cipher.data.length - last_block_len;
167                 last_block = (uint8_t *) rte_pktmbuf_mtod_offset(sym_op->m_src,
168                                 uint8_t *, last_block_offset);
169
170                 if (unlikely(sym_op->m_dst != NULL))
171                         /* out-of-place operation (OOP) */
172                         dst = (uint8_t *) rte_pktmbuf_mtod_offset(sym_op->m_dst,
173                                                 uint8_t *, last_block_offset);
174                 else
175                         dst = last_block;
176
177                 if (last_block_len < sym_op->cipher.data.length)
178                         /* use previous block ciphertext as IV */
179                         iv = dst - block_len;
180                 else
181                         /* runt block, i.e. less than one full block */
182                         iv = rte_crypto_op_ctod_offset(op, uint8_t *,
183                                         ctx->cipher_iv.offset);
184
185 #ifdef RTE_LIBRTE_PMD_QAT_DEBUG_RX
186                 rte_hexdump(stdout, "BPI: src before post-process:", last_block,
187                         last_block_len);
188                 if (sym_op->m_dst != NULL)
189                         rte_hexdump(stdout, "BPI: dst before post-process:",
190                                         dst, last_block_len);
191 #endif
192                 bpi_cipher_encrypt(last_block, dst, iv, block_len,
193                                 last_block_len, ctx->bpi_ctx);
194 #ifdef RTE_LIBRTE_PMD_QAT_DEBUG_RX
195                 rte_hexdump(stdout, "BPI: src after post-process:", last_block,
196                         last_block_len);
197                 if (sym_op->m_dst != NULL)
198                         rte_hexdump(stdout, "BPI: dst after post-process:", dst,
199                                 last_block_len);
200 #endif
201         }
202         return sym_op->cipher.data.length - last_block_len;
203 }
204
205 static inline void
206 txq_write_tail(struct qat_qp *qp, struct qat_queue *q) {
207         WRITE_CSR_RING_TAIL(qp->mmap_bar_addr, q->hw_bundle_number,
208                         q->hw_queue_number, q->tail);
209         q->nb_pending_requests = 0;
210         q->csr_tail = q->tail;
211 }
212
213 uint16_t
214 qat_pmd_enqueue_op_burst(void *qp, struct rte_crypto_op **ops,
215                 uint16_t nb_ops)
216 {
217         register struct qat_queue *queue;
218         struct qat_qp *tmp_qp = (struct qat_qp *)qp;
219         register uint32_t nb_ops_sent = 0;
220         register struct rte_crypto_op **cur_op = ops;
221         register int ret;
222         uint16_t nb_ops_possible = nb_ops;
223         register uint8_t *base_addr;
224         register uint32_t tail;
225         int overflow;
226
227         if (unlikely(nb_ops == 0))
228                 return 0;
229
230         /* read params used a lot in main loop into registers */
231         queue = &(tmp_qp->tx_q);
232         base_addr = (uint8_t *)queue->base_addr;
233         tail = queue->tail;
234
235         /* Find how many can actually fit on the ring */
236         tmp_qp->inflights16 += nb_ops;
237         overflow = tmp_qp->inflights16 - queue->max_inflights;
238         if (overflow > 0) {
239                 tmp_qp->inflights16 -= overflow;
240                 nb_ops_possible = nb_ops - overflow;
241                 if (nb_ops_possible == 0)
242                         return 0;
243         }
244
245         while (nb_ops_sent != nb_ops_possible) {
246                 ret = qat_write_hw_desc_entry(*cur_op, base_addr + tail,
247                         tmp_qp->op_cookies[tail / queue->msg_size], tmp_qp);
248                 if (ret != 0) {
249                         tmp_qp->stats.enqueue_err_count++;
250                         /*
251                          * This message cannot be enqueued,
252                          * decrease number of ops that wasn't sent
253                          */
254                         tmp_qp->inflights16 -= nb_ops_possible - nb_ops_sent;
255                         if (nb_ops_sent == 0)
256                                 return 0;
257                         goto kick_tail;
258                 }
259
260                 tail = adf_modulo(tail + queue->msg_size, queue->modulo);
261                 nb_ops_sent++;
262                 cur_op++;
263         }
264 kick_tail:
265         queue->tail = tail;
266         tmp_qp->stats.enqueued_count += nb_ops_sent;
267         queue->nb_pending_requests += nb_ops_sent;
268         if (tmp_qp->inflights16 < QAT_CSR_TAIL_FORCE_WRITE_THRESH ||
269                         queue->nb_pending_requests > QAT_CSR_TAIL_WRITE_THRESH) {
270                 txq_write_tail(tmp_qp, queue);
271         }
272         return nb_ops_sent;
273 }
274
275 static inline
276 void rxq_free_desc(struct qat_qp *qp, struct qat_queue *q)
277 {
278         uint32_t old_head, new_head;
279         uint32_t max_head;
280
281         old_head = q->csr_head;
282         new_head = q->head;
283         max_head = qp->nb_descriptors * q->msg_size;
284
285         /* write out free descriptors */
286         void *cur_desc = (uint8_t *)q->base_addr + old_head;
287
288         if (new_head < old_head) {
289                 memset(cur_desc, ADF_RING_EMPTY_SIG_BYTE, max_head - old_head);
290                 memset(q->base_addr, ADF_RING_EMPTY_SIG_BYTE, new_head);
291         } else {
292                 memset(cur_desc, ADF_RING_EMPTY_SIG_BYTE, new_head - old_head);
293         }
294         q->nb_processed_responses = 0;
295         q->csr_head = new_head;
296
297         /* write current head to CSR */
298         WRITE_CSR_RING_HEAD(qp->mmap_bar_addr, q->hw_bundle_number,
299                             q->hw_queue_number, new_head);
300 }
301
302 uint16_t
303 qat_pmd_dequeue_op_burst(void *qp, struct rte_crypto_op **ops,
304                 uint16_t nb_ops)
305 {
306         struct qat_queue *rx_queue, *tx_queue;
307         struct qat_qp *tmp_qp = (struct qat_qp *)qp;
308         uint32_t msg_counter = 0;
309         struct rte_crypto_op *rx_op;
310         struct icp_qat_fw_comn_resp *resp_msg;
311         uint32_t head;
312
313         rx_queue = &(tmp_qp->rx_q);
314         tx_queue = &(tmp_qp->tx_q);
315         head = rx_queue->head;
316         resp_msg = (struct icp_qat_fw_comn_resp *)
317                         ((uint8_t *)rx_queue->base_addr + head);
318
319         while (*(uint32_t *)resp_msg != ADF_RING_EMPTY_SIG &&
320                         msg_counter != nb_ops) {
321                 rx_op = (struct rte_crypto_op *)(uintptr_t)
322                                 (resp_msg->opaque_data);
323
324 #ifdef RTE_LIBRTE_PMD_QAT_DEBUG_RX
325                 rte_hexdump(stdout, "qat_response:", (uint8_t *)resp_msg,
326                         sizeof(struct icp_qat_fw_comn_resp));
327 #endif
328                 if (ICP_QAT_FW_COMN_STATUS_FLAG_OK !=
329                                 ICP_QAT_FW_COMN_RESP_CRYPTO_STAT_GET(
330                                         resp_msg->comn_hdr.comn_status)) {
331                         rx_op->status = RTE_CRYPTO_OP_STATUS_AUTH_FAILED;
332                 } else {
333                         struct qat_session *sess = (struct qat_session *)
334                                         get_session_private_data(
335                                         rx_op->sym->session,
336                                         cryptodev_qat_driver_id);
337
338                         if (sess->bpi_ctx)
339                                 qat_bpicipher_postprocess(sess, rx_op);
340                         rx_op->status = RTE_CRYPTO_OP_STATUS_SUCCESS;
341                 }
342
343                 head = adf_modulo(head + rx_queue->msg_size, rx_queue->modulo);
344                 resp_msg = (struct icp_qat_fw_comn_resp *)
345                                 ((uint8_t *)rx_queue->base_addr + head);
346                 *ops = rx_op;
347                 ops++;
348                 msg_counter++;
349         }
350         if (msg_counter > 0) {
351                 rx_queue->head = head;
352                 tmp_qp->stats.dequeued_count += msg_counter;
353                 rx_queue->nb_processed_responses += msg_counter;
354                 tmp_qp->inflights16 -= msg_counter;
355
356                 if (rx_queue->nb_processed_responses > QAT_CSR_HEAD_WRITE_THRESH)
357                         rxq_free_desc(tmp_qp, rx_queue);
358         }
359         /* also check if tail needs to be advanced */
360         if (tmp_qp->inflights16 <= QAT_CSR_TAIL_FORCE_WRITE_THRESH &&
361                         tx_queue->tail != tx_queue->csr_tail) {
362                 txq_write_tail(tmp_qp, tx_queue);
363         }
364         return msg_counter;
365 }
366
367 static inline int
368 qat_sgl_fill_array(struct rte_mbuf *buf, uint64_t buff_start,
369                 struct qat_alg_buf_list *list, uint32_t data_len)
370 {
371         int nr = 1;
372
373         uint32_t buf_len = rte_pktmbuf_iova(buf) -
374                         buff_start + rte_pktmbuf_data_len(buf);
375
376         list->bufers[0].addr = buff_start;
377         list->bufers[0].resrvd = 0;
378         list->bufers[0].len = buf_len;
379
380         if (data_len <= buf_len) {
381                 list->num_bufs = nr;
382                 list->bufers[0].len = data_len;
383                 return 0;
384         }
385
386         buf = buf->next;
387         while (buf) {
388                 if (unlikely(nr == QAT_SGL_MAX_NUMBER)) {
389                         PMD_DRV_LOG(ERR, "QAT PMD exceeded size of QAT SGL"
390                                         " entry(%u)",
391                                         QAT_SGL_MAX_NUMBER);
392                         return -EINVAL;
393                 }
394
395                 list->bufers[nr].len = rte_pktmbuf_data_len(buf);
396                 list->bufers[nr].resrvd = 0;
397                 list->bufers[nr].addr = rte_pktmbuf_iova(buf);
398
399                 buf_len += list->bufers[nr].len;
400                 buf = buf->next;
401
402                 if (buf_len > data_len) {
403                         list->bufers[nr].len -=
404                                 buf_len - data_len;
405                         buf = NULL;
406                 }
407                 ++nr;
408         }
409         list->num_bufs = nr;
410
411         return 0;
412 }
413
414 static inline void
415 set_cipher_iv(uint16_t iv_length, uint16_t iv_offset,
416                 struct icp_qat_fw_la_cipher_req_params *cipher_param,
417                 struct rte_crypto_op *op,
418                 struct icp_qat_fw_la_bulk_req *qat_req)
419 {
420         /* copy IV into request if it fits */
421         if (iv_length <= sizeof(cipher_param->u.cipher_IV_array)) {
422                 rte_memcpy(cipher_param->u.cipher_IV_array,
423                                 rte_crypto_op_ctod_offset(op, uint8_t *,
424                                         iv_offset),
425                                 iv_length);
426         } else {
427                 ICP_QAT_FW_LA_CIPH_IV_FLD_FLAG_SET(
428                                 qat_req->comn_hdr.serv_specif_flags,
429                                 ICP_QAT_FW_CIPH_IV_64BIT_PTR);
430                 cipher_param->u.s.cipher_IV_ptr =
431                                 rte_crypto_op_ctophys_offset(op,
432                                         iv_offset);
433         }
434 }
435
436 /** Set IV for CCM is special case, 0th byte is set to q-1
437  *  where q is padding of nonce in 16 byte block
438  */
439 static inline void
440 set_cipher_iv_ccm(uint16_t iv_length, uint16_t iv_offset,
441                 struct icp_qat_fw_la_cipher_req_params *cipher_param,
442                 struct rte_crypto_op *op, uint8_t q, uint8_t aad_len_field_sz)
443 {
444         rte_memcpy(((uint8_t *)cipher_param->u.cipher_IV_array) +
445                         ICP_QAT_HW_CCM_NONCE_OFFSET,
446                         rte_crypto_op_ctod_offset(op, uint8_t *,
447                                 iv_offset) + ICP_QAT_HW_CCM_NONCE_OFFSET,
448                         iv_length);
449         *(uint8_t *)&cipher_param->u.cipher_IV_array[0] =
450                         q - ICP_QAT_HW_CCM_NONCE_OFFSET;
451
452         if (aad_len_field_sz)
453                 rte_memcpy(&op->sym->aead.aad.data[ICP_QAT_HW_CCM_NONCE_OFFSET],
454                         rte_crypto_op_ctod_offset(op, uint8_t *,
455                                 iv_offset) + ICP_QAT_HW_CCM_NONCE_OFFSET,
456                         iv_length);
457 }
458
459 static inline int
460 qat_write_hw_desc_entry(struct rte_crypto_op *op, uint8_t *out_msg,
461                 struct qat_crypto_op_cookie *qat_op_cookie, struct qat_qp *qp)
462 {
463         int ret = 0;
464         struct qat_session *ctx;
465         struct icp_qat_fw_la_cipher_req_params *cipher_param;
466         struct icp_qat_fw_la_auth_req_params *auth_param;
467         register struct icp_qat_fw_la_bulk_req *qat_req;
468         uint8_t do_auth = 0, do_cipher = 0, do_aead = 0;
469         uint32_t cipher_len = 0, cipher_ofs = 0;
470         uint32_t auth_len = 0, auth_ofs = 0;
471         uint32_t min_ofs = 0;
472         uint64_t src_buf_start = 0, dst_buf_start = 0;
473         uint8_t do_sgl = 0;
474
475 #ifdef RTE_LIBRTE_PMD_QAT_DEBUG_TX
476         if (unlikely(op->type != RTE_CRYPTO_OP_TYPE_SYMMETRIC)) {
477                 PMD_DRV_LOG(ERR, "QAT PMD only supports symmetric crypto "
478                                 "operation requests, op (%p) is not a "
479                                 "symmetric operation.", op);
480                 return -EINVAL;
481         }
482 #endif
483         if (unlikely(op->sess_type == RTE_CRYPTO_OP_SESSIONLESS)) {
484                 PMD_DRV_LOG(ERR, "QAT PMD only supports session oriented"
485                                 " requests, op (%p) is sessionless.", op);
486                 return -EINVAL;
487         }
488
489         ctx = (struct qat_session *)get_session_private_data(
490                         op->sym->session, cryptodev_qat_driver_id);
491
492         if (unlikely(ctx == NULL)) {
493                 PMD_DRV_LOG(ERR, "Session was not created for this device");
494                 return -EINVAL;
495         }
496
497         if (unlikely(ctx->min_qat_dev_gen > qp->qat_dev_gen)) {
498                 PMD_DRV_LOG(ERR, "Session alg not supported on this device gen");
499                 op->status = RTE_CRYPTO_OP_STATUS_INVALID_SESSION;
500                 return -EINVAL;
501         }
502
503
504
505         qat_req = (struct icp_qat_fw_la_bulk_req *)out_msg;
506         rte_mov128((uint8_t *)qat_req, (const uint8_t *)&(ctx->fw_req));
507         qat_req->comn_mid.opaque_data = (uint64_t)(uintptr_t)op;
508         cipher_param = (void *)&qat_req->serv_specif_rqpars;
509         auth_param = (void *)((uint8_t *)cipher_param + sizeof(*cipher_param));
510
511         if (ctx->qat_cmd == ICP_QAT_FW_LA_CMD_HASH_CIPHER ||
512                         ctx->qat_cmd == ICP_QAT_FW_LA_CMD_CIPHER_HASH) {
513                 /* AES-GCM or AES-CCM */
514                 if (ctx->qat_hash_alg == ICP_QAT_HW_AUTH_ALGO_GALOIS_128 ||
515                                 ctx->qat_hash_alg == ICP_QAT_HW_AUTH_ALGO_GALOIS_64 ||
516                                 (ctx->qat_cipher_alg == ICP_QAT_HW_CIPHER_ALGO_AES128
517                                 && ctx->qat_mode == ICP_QAT_HW_CIPHER_CTR_MODE
518                                 && ctx->qat_hash_alg ==
519                                                 ICP_QAT_HW_AUTH_ALGO_AES_CBC_MAC)) {
520                         do_aead = 1;
521                 } else {
522                         do_auth = 1;
523                         do_cipher = 1;
524                 }
525         } else if (ctx->qat_cmd == ICP_QAT_FW_LA_CMD_AUTH) {
526                 do_auth = 1;
527                 do_cipher = 0;
528         } else if (ctx->qat_cmd == ICP_QAT_FW_LA_CMD_CIPHER) {
529                 do_auth = 0;
530                 do_cipher = 1;
531         }
532
533         if (do_cipher) {
534
535                 if (ctx->qat_cipher_alg ==
536                                          ICP_QAT_HW_CIPHER_ALGO_SNOW_3G_UEA2 ||
537                         ctx->qat_cipher_alg == ICP_QAT_HW_CIPHER_ALGO_KASUMI ||
538                         ctx->qat_cipher_alg ==
539                                 ICP_QAT_HW_CIPHER_ALGO_ZUC_3G_128_EEA3) {
540
541                         if (unlikely(
542                                 (cipher_param->cipher_length % BYTE_LENGTH != 0)
543                                  || (cipher_param->cipher_offset
544                                                         % BYTE_LENGTH != 0))) {
545                                 PMD_DRV_LOG(ERR,
546                   "SNOW3G/KASUMI/ZUC in QAT PMD only supports byte aligned values");
547                                 op->status = RTE_CRYPTO_OP_STATUS_INVALID_ARGS;
548                                 return -EINVAL;
549                         }
550                         cipher_len = op->sym->cipher.data.length >> 3;
551                         cipher_ofs = op->sym->cipher.data.offset >> 3;
552
553                 } else if (ctx->bpi_ctx) {
554                         /* DOCSIS - only send complete blocks to device
555                          * Process any partial block using CFB mode.
556                          * Even if 0 complete blocks, still send this to device
557                          * to get into rx queue for post-process and dequeuing
558                          */
559                         cipher_len = qat_bpicipher_preprocess(ctx, op);
560                         cipher_ofs = op->sym->cipher.data.offset;
561                 } else {
562                         cipher_len = op->sym->cipher.data.length;
563                         cipher_ofs = op->sym->cipher.data.offset;
564                 }
565
566                 set_cipher_iv(ctx->cipher_iv.length, ctx->cipher_iv.offset,
567                                 cipher_param, op, qat_req);
568                 min_ofs = cipher_ofs;
569         }
570
571         if (do_auth) {
572
573                 if (ctx->qat_hash_alg == ICP_QAT_HW_AUTH_ALGO_SNOW_3G_UIA2 ||
574                         ctx->qat_hash_alg == ICP_QAT_HW_AUTH_ALGO_KASUMI_F9 ||
575                         ctx->qat_hash_alg ==
576                                 ICP_QAT_HW_AUTH_ALGO_ZUC_3G_128_EIA3) {
577                         if (unlikely((auth_param->auth_off % BYTE_LENGTH != 0)
578                                 || (auth_param->auth_len % BYTE_LENGTH != 0))) {
579                                 PMD_DRV_LOG(ERR,
580                 "For SNOW3G/KASUMI/ZUC, QAT PMD only supports byte aligned values");
581                                 op->status = RTE_CRYPTO_OP_STATUS_INVALID_ARGS;
582                                 return -EINVAL;
583                         }
584                         auth_ofs = op->sym->auth.data.offset >> 3;
585                         auth_len = op->sym->auth.data.length >> 3;
586
587                         auth_param->u1.aad_adr =
588                                         rte_crypto_op_ctophys_offset(op,
589                                                         ctx->auth_iv.offset);
590
591                 } else if (ctx->qat_hash_alg ==
592                                         ICP_QAT_HW_AUTH_ALGO_GALOIS_128 ||
593                                 ctx->qat_hash_alg ==
594                                         ICP_QAT_HW_AUTH_ALGO_GALOIS_64) {
595                         /* AES-GMAC */
596                         set_cipher_iv(ctx->auth_iv.length,
597                                 ctx->auth_iv.offset,
598                                 cipher_param, op, qat_req);
599                         auth_ofs = op->sym->auth.data.offset;
600                         auth_len = op->sym->auth.data.length;
601
602                         auth_param->u1.aad_adr = 0;
603                         auth_param->u2.aad_sz = 0;
604
605                         /*
606                          * If len(iv)==12B fw computes J0
607                          */
608                         if (ctx->auth_iv.length == 12) {
609                                 ICP_QAT_FW_LA_GCM_IV_LEN_FLAG_SET(
610                                         qat_req->comn_hdr.serv_specif_flags,
611                                         ICP_QAT_FW_LA_GCM_IV_LEN_12_OCTETS);
612
613                         }
614                 } else {
615                         auth_ofs = op->sym->auth.data.offset;
616                         auth_len = op->sym->auth.data.length;
617
618                 }
619                 min_ofs = auth_ofs;
620
621                 if (likely(ctx->qat_hash_alg != ICP_QAT_HW_AUTH_ALGO_NULL))
622                         auth_param->auth_res_addr =
623                                         op->sym->auth.digest.phys_addr;
624
625         }
626
627         if (do_aead) {
628                 /*
629                  * This address may used for setting AAD physical pointer
630                  * into IV offset from op
631                  */
632                 rte_iova_t aad_phys_addr_aead = op->sym->aead.aad.phys_addr;
633                 if (ctx->qat_hash_alg ==
634                                 ICP_QAT_HW_AUTH_ALGO_GALOIS_128 ||
635                                 ctx->qat_hash_alg ==
636                                         ICP_QAT_HW_AUTH_ALGO_GALOIS_64) {
637                         /*
638                          * If len(iv)==12B fw computes J0
639                          */
640                         if (ctx->cipher_iv.length == 12) {
641                                 ICP_QAT_FW_LA_GCM_IV_LEN_FLAG_SET(
642                                         qat_req->comn_hdr.serv_specif_flags,
643                                         ICP_QAT_FW_LA_GCM_IV_LEN_12_OCTETS);
644                         }
645
646                         set_cipher_iv(ctx->cipher_iv.length,
647                                         ctx->cipher_iv.offset,
648                                         cipher_param, op, qat_req);
649
650                 } else if (ctx->qat_hash_alg ==
651                                 ICP_QAT_HW_AUTH_ALGO_AES_CBC_MAC) {
652
653                         /* In case of AES-CCM this may point to user selected memory
654                          * or iv offset in cypto_op
655                          */
656                         uint8_t *aad_data = op->sym->aead.aad.data;
657                         /* This is true AAD length, it not includes 18 bytes of
658                          * preceding data
659                          */
660                         uint8_t aad_ccm_real_len = 0;
661
662                         uint8_t aad_len_field_sz = 0;
663                         uint32_t msg_len_be =
664                                         rte_bswap32(op->sym->aead.data.length);
665
666                         if (ctx->aad_len > ICP_QAT_HW_CCM_AAD_DATA_OFFSET) {
667                                 aad_len_field_sz = ICP_QAT_HW_CCM_AAD_LEN_INFO;
668                                 aad_ccm_real_len = ctx->aad_len -
669                                         ICP_QAT_HW_CCM_AAD_B0_LEN -
670                                         ICP_QAT_HW_CCM_AAD_LEN_INFO;
671                         } else {
672                                 /*
673                                  * aad_len not greater than 18, so no actual aad data,
674                                  * then use IV after op for B0 block
675                                  */
676                                 aad_data = rte_crypto_op_ctod_offset(op, uint8_t *,
677                                                 ctx->cipher_iv.offset);
678                                 aad_phys_addr_aead =
679                                                 rte_crypto_op_ctophys_offset(op,
680                                                                 ctx->cipher_iv.offset);
681                         }
682
683                         uint8_t q = ICP_QAT_HW_CCM_NQ_CONST - ctx->cipher_iv.length;
684
685                         aad_data[0] = ICP_QAT_HW_CCM_BUILD_B0_FLAGS(aad_len_field_sz,
686                                                         ctx->digest_length, q);
687
688                         if (q > ICP_QAT_HW_CCM_MSG_LEN_MAX_FIELD_SIZE) {
689                                 memcpy(aad_data + ctx->cipher_iv.length +
690                                         ICP_QAT_HW_CCM_NONCE_OFFSET
691                                         + (q - ICP_QAT_HW_CCM_MSG_LEN_MAX_FIELD_SIZE),
692                                         (uint8_t *)&msg_len_be,
693                                         ICP_QAT_HW_CCM_MSG_LEN_MAX_FIELD_SIZE);
694                         } else {
695                                 memcpy(aad_data + ctx->cipher_iv.length +
696                                         ICP_QAT_HW_CCM_NONCE_OFFSET,
697                                         (uint8_t *)&msg_len_be
698                                         + (ICP_QAT_HW_CCM_MSG_LEN_MAX_FIELD_SIZE
699                                         - q), q);
700                         }
701
702                         if (aad_len_field_sz > 0) {
703                                 *(uint16_t *)&aad_data[ICP_QAT_HW_CCM_AAD_B0_LEN]
704                                                 = rte_bswap16(aad_ccm_real_len);
705
706                                 if ((aad_ccm_real_len + aad_len_field_sz)
707                                                 % ICP_QAT_HW_CCM_AAD_B0_LEN) {
708                                         uint8_t pad_len = 0;
709                                         uint8_t pad_idx = 0;
710
711                                         pad_len = ICP_QAT_HW_CCM_AAD_B0_LEN -
712                                                 ((aad_ccm_real_len + aad_len_field_sz) %
713                                                         ICP_QAT_HW_CCM_AAD_B0_LEN);
714                                         pad_idx = ICP_QAT_HW_CCM_AAD_B0_LEN +
715                                                 aad_ccm_real_len + aad_len_field_sz;
716                                         memset(&aad_data[pad_idx],
717                                                         0, pad_len);
718                                 }
719
720                         }
721
722                         set_cipher_iv_ccm(ctx->cipher_iv.length,
723                                         ctx->cipher_iv.offset,
724                                         cipher_param, op, q,
725                                         aad_len_field_sz);
726
727                 }
728
729                 cipher_len = op->sym->aead.data.length;
730                 cipher_ofs = op->sym->aead.data.offset;
731                 auth_len = op->sym->aead.data.length;
732                 auth_ofs = op->sym->aead.data.offset;
733
734                 auth_param->u1.aad_adr = aad_phys_addr_aead;
735                 auth_param->auth_res_addr = op->sym->aead.digest.phys_addr;
736                 min_ofs = op->sym->aead.data.offset;
737         }
738
739         if (op->sym->m_src->next || (op->sym->m_dst && op->sym->m_dst->next))
740                 do_sgl = 1;
741
742         /* adjust for chain case */
743         if (do_cipher && do_auth)
744                 min_ofs = cipher_ofs < auth_ofs ? cipher_ofs : auth_ofs;
745
746         if (unlikely(min_ofs >= rte_pktmbuf_data_len(op->sym->m_src) && do_sgl))
747                 min_ofs = 0;
748
749         if (unlikely(op->sym->m_dst != NULL)) {
750                 /* Out-of-place operation (OOP)
751                  * Don't align DMA start. DMA the minimum data-set
752                  * so as not to overwrite data in dest buffer
753                  */
754                 src_buf_start =
755                         rte_pktmbuf_iova_offset(op->sym->m_src, min_ofs);
756                 dst_buf_start =
757                         rte_pktmbuf_iova_offset(op->sym->m_dst, min_ofs);
758
759         } else {
760                 /* In-place operation
761                  * Start DMA at nearest aligned address below min_ofs
762                  */
763                 src_buf_start =
764                         rte_pktmbuf_iova_offset(op->sym->m_src, min_ofs)
765                                                 & QAT_64_BTYE_ALIGN_MASK;
766
767                 if (unlikely((rte_pktmbuf_iova(op->sym->m_src) -
768                                         rte_pktmbuf_headroom(op->sym->m_src))
769                                                         > src_buf_start)) {
770                         /* alignment has pushed addr ahead of start of mbuf
771                          * so revert and take the performance hit
772                          */
773                         src_buf_start =
774                                 rte_pktmbuf_iova_offset(op->sym->m_src,
775                                                                 min_ofs);
776                 }
777                 dst_buf_start = src_buf_start;
778         }
779
780         if (do_cipher || do_aead) {
781                 cipher_param->cipher_offset =
782                                 (uint32_t)rte_pktmbuf_iova_offset(
783                                 op->sym->m_src, cipher_ofs) - src_buf_start;
784                 cipher_param->cipher_length = cipher_len;
785         } else {
786                 cipher_param->cipher_offset = 0;
787                 cipher_param->cipher_length = 0;
788         }
789
790         if (do_auth || do_aead) {
791                 auth_param->auth_off = (uint32_t)rte_pktmbuf_iova_offset(
792                                 op->sym->m_src, auth_ofs) - src_buf_start;
793                 auth_param->auth_len = auth_len;
794         } else {
795                 auth_param->auth_off = 0;
796                 auth_param->auth_len = 0;
797         }
798
799         qat_req->comn_mid.dst_length =
800                 qat_req->comn_mid.src_length =
801                 (cipher_param->cipher_offset + cipher_param->cipher_length)
802                 > (auth_param->auth_off + auth_param->auth_len) ?
803                 (cipher_param->cipher_offset + cipher_param->cipher_length)
804                 : (auth_param->auth_off + auth_param->auth_len);
805
806         if (do_sgl) {
807
808                 ICP_QAT_FW_COMN_PTR_TYPE_SET(qat_req->comn_hdr.comn_req_flags,
809                                 QAT_COMN_PTR_TYPE_SGL);
810                 ret = qat_sgl_fill_array(op->sym->m_src, src_buf_start,
811                                 &qat_op_cookie->qat_sgl_list_src,
812                                 qat_req->comn_mid.src_length);
813                 if (ret) {
814                         PMD_DRV_LOG(ERR, "QAT PMD Cannot fill sgl array");
815                         return ret;
816                 }
817
818                 if (likely(op->sym->m_dst == NULL))
819                         qat_req->comn_mid.dest_data_addr =
820                                 qat_req->comn_mid.src_data_addr =
821                                 qat_op_cookie->qat_sgl_src_phys_addr;
822                 else {
823                         ret = qat_sgl_fill_array(op->sym->m_dst,
824                                         dst_buf_start,
825                                         &qat_op_cookie->qat_sgl_list_dst,
826                                                 qat_req->comn_mid.dst_length);
827
828                         if (ret) {
829                                 PMD_DRV_LOG(ERR, "QAT PMD Cannot "
830                                                 "fill sgl array");
831                                 return ret;
832                         }
833
834                         qat_req->comn_mid.src_data_addr =
835                                 qat_op_cookie->qat_sgl_src_phys_addr;
836                         qat_req->comn_mid.dest_data_addr =
837                                         qat_op_cookie->qat_sgl_dst_phys_addr;
838                 }
839         } else {
840                 qat_req->comn_mid.src_data_addr = src_buf_start;
841                 qat_req->comn_mid.dest_data_addr = dst_buf_start;
842         }
843
844 #ifdef RTE_LIBRTE_PMD_QAT_DEBUG_TX
845         rte_hexdump(stdout, "qat_req:", qat_req,
846                         sizeof(struct icp_qat_fw_la_bulk_req));
847         rte_hexdump(stdout, "src_data:",
848                         rte_pktmbuf_mtod(op->sym->m_src, uint8_t*),
849                         rte_pktmbuf_data_len(op->sym->m_src));
850         if (do_cipher) {
851                 uint8_t *cipher_iv_ptr = rte_crypto_op_ctod_offset(op,
852                                                 uint8_t *,
853                                                 ctx->cipher_iv.offset);
854                 rte_hexdump(stdout, "cipher iv:", cipher_iv_ptr,
855                                 ctx->cipher_iv.length);
856         }
857
858         if (do_auth) {
859                 if (ctx->auth_iv.length) {
860                         uint8_t *auth_iv_ptr = rte_crypto_op_ctod_offset(op,
861                                                         uint8_t *,
862                                                         ctx->auth_iv.offset);
863                         rte_hexdump(stdout, "auth iv:", auth_iv_ptr,
864                                                 ctx->auth_iv.length);
865                 }
866                 rte_hexdump(stdout, "digest:", op->sym->auth.digest.data,
867                                 ctx->digest_length);
868         }
869
870         if (do_aead) {
871                 rte_hexdump(stdout, "digest:", op->sym->aead.digest.data,
872                                 ctx->digest_length);
873                 rte_hexdump(stdout, "aad:", op->sym->aead.aad.data,
874                                 ctx->aad_len);
875         }
876 #endif
877         return 0;
878 }
879
880 static inline uint32_t adf_modulo(uint32_t data, uint32_t shift)
881 {
882         uint32_t div = data >> shift;
883         uint32_t mult = div << shift;
884
885         return data - mult;
886 }
887
888 void qat_crypto_sym_stats_get(struct rte_cryptodev *dev,
889                 struct rte_cryptodev_stats *stats)
890 {
891         int i;
892         struct qat_qp **qp = (struct qat_qp **)(dev->data->queue_pairs);
893
894         PMD_INIT_FUNC_TRACE();
895         if (stats == NULL) {
896                 PMD_DRV_LOG(ERR, "invalid stats ptr NULL");
897                 return;
898         }
899         for (i = 0; i < dev->data->nb_queue_pairs; i++) {
900                 if (qp[i] == NULL) {
901                         PMD_DRV_LOG(DEBUG, "Uninitialised queue pair");
902                         continue;
903                 }
904
905                 stats->enqueued_count += qp[i]->stats.enqueued_count;
906                 stats->dequeued_count += qp[i]->stats.dequeued_count;
907                 stats->enqueue_err_count += qp[i]->stats.enqueue_err_count;
908                 stats->dequeue_err_count += qp[i]->stats.dequeue_err_count;
909         }
910 }
911
912 void qat_crypto_sym_stats_reset(struct rte_cryptodev *dev)
913 {
914         int i;
915         struct qat_qp **qp = (struct qat_qp **)(dev->data->queue_pairs);
916
917         PMD_INIT_FUNC_TRACE();
918         for (i = 0; i < dev->data->nb_queue_pairs; i++)
919                 memset(&(qp[i]->stats), 0, sizeof(qp[i]->stats));
920         PMD_DRV_LOG(DEBUG, "QAT crypto: stats cleared");
921 }