crypto/ipsec_mb: add chacha_poly PMD
authorKai Ji <kai.ji@intel.com>
Fri, 15 Oct 2021 14:39:56 +0000 (14:39 +0000)
committerAkhil Goyal <gakhil@marvell.com>
Wed, 20 Oct 2021 13:33:16 +0000 (15:33 +0200)
Add in new chacha20_poly1305 PMD to the ipsec_mb framework.

Signed-off-by: Kai Ji <kai.ji@intel.com>
Signed-off-by: Ciara Power <ciara.power@intel.com>
Acked-by: Ray Kinsella <mdr@ashroe.eu>
Acked-by: Fan Zhang <roy.fan.zhang@intel.com>
Acked-by: Akhil Goyal <gakhil@marvell.com>
MAINTAINERS
doc/guides/cryptodevs/chacha20_poly1305.rst [new file with mode: 0644]
doc/guides/cryptodevs/features/chacha20_poly1305.ini [new file with mode: 0644]
doc/guides/cryptodevs/index.rst
doc/guides/rel_notes/release_21_11.rst
drivers/crypto/ipsec_mb/ipsec_mb_private.h
drivers/crypto/ipsec_mb/meson.build
drivers/crypto/ipsec_mb/pmd_chacha_poly.c [new file with mode: 0644]
drivers/crypto/ipsec_mb/pmd_chacha_poly_priv.h [new file with mode: 0644]

index 9c6aff4..587632d 100644 (file)
@@ -1067,11 +1067,13 @@ M: Pablo de Lara <pablo.de.lara.guarch@intel.com>
 F: drivers/crypto/ipsec_mb/
 F: doc/guides/cryptodevs/aesni_gcm.rst
 F: doc/guides/cryptodevs/aesni_mb.rst
+F: doc/guides/cryptodevs/chacha20_poly1305.rst
 F: doc/guides/cryptodevs/kasumi.rst
 F: doc/guides/cryptodevs/snow3g.rst
 F: doc/guides/cryptodevs/zuc.rst
 F: doc/guides/cryptodevs/features/aesni_gcm.ini
 F: doc/guides/cryptodevs/features/aesni_mb.ini
+F: doc/guides/cryptodevs/features/chacha20_poly1305.ini
 F: doc/guides/cryptodevs/features/kasumi.ini
 F: doc/guides/cryptodevs/features/snow3g.ini
 F: doc/guides/cryptodevs/features/zuc.ini
diff --git a/doc/guides/cryptodevs/chacha20_poly1305.rst b/doc/guides/cryptodevs/chacha20_poly1305.rst
new file mode 100644 (file)
index 0000000..4db2608
--- /dev/null
@@ -0,0 +1,99 @@
+..  SPDX-License-Identifier: BSD-3-Clause
+    Copyright(c) 2021 Intel Corporation.
+
+Chacha20-poly1305 Crypto Poll Mode Driver
+=========================================
+
+The Chacha20-poly1305 PMD provides poll mode crypto driver support for
+utilizing `Intel IPSec Multi-buffer library <https://github.com/01org/intel-ipsec-mb>`_.
+
+Features
+--------
+
+Chacha20-poly1305 PMD has support for:
+
+AEAD algorithms:
+
+* RTE_CRYPTO_AEAD_CHACHA20_POLY1305
+
+
+Installation
+------------
+
+To build DPDK with the Chacha20-poly1305 PMD the user is required to download
+the multi-buffer library from `here <https://github.com/01org/intel-ipsec-mb>`_
+and compile it on their user system before building DPDK.
+The latest version of the library supported by this PMD is v1.0, which
+can be downloaded from `<https://github.com/01org/intel-ipsec-mb/archive/v1.0.zip>`_.
+
+After downloading the library, the user needs to unpack and compile it
+on their system before building DPDK:
+
+.. code-block:: console
+
+    make
+    make install
+
+The library requires NASM to be built. Depending on the library version, it might
+require a minimum NASM version (e.g. v0.54 requires at least NASM 2.14).
+
+NASM is packaged for different OS. However, on some OS the version is too old,
+so a manual installation is required. In that case, NASM can be downloaded from
+`NASM website <https://www.nasm.us/pub/nasm/releasebuilds/?C=M;O=D>`_.
+Once it is downloaded, extract it and follow these steps:
+
+.. code-block:: console
+
+    ./configure
+    make
+    make install
+
+.. note::
+
+   Compilation of the Multi-Buffer library is broken when GCC < 5.0, if library <= v0.53.
+   If a lower GCC version than 5.0, the workaround proposed by the following link
+   should be used: `<https://github.com/intel/intel-ipsec-mb/issues/40>`_.
+
+As a reference, the following table shows a mapping between the past DPDK versions
+and the external crypto libraries supported by them:
+
+.. _table_chacha20_poly1305_versions:
+
+.. table:: DPDK and external crypto library version compatibility
+
+   =============  ================================
+   DPDK version   Crypto library version
+   =============  ================================
+   21.11+         Multi-buffer library 1.0*
+   =============  ================================
+
+\* Multi-buffer library 1.0 or newer only works for Meson but not Make build system.
+
+Initialization
+--------------
+
+In order to enable this virtual crypto PMD, user must:
+
+* Build the multi buffer library (explained in Installation section).
+
+To use the PMD in an application, user must:
+
+* Call rte_vdev_init("crypto_chacha20_poly1305") within the application.
+
+* Use --vdev="crypto_chacha20_poly1305" in the EAL options, which will call
+  rte_vdev_init() internally.
+
+The following parameters (all optional) can be provided in the previous two calls:
+
+* socket_id: Specify the socket where the memory for the device is going to be allocated
+  (by default, socket_id will be the socket where the core that is creating the PMD is running on).
+
+* max_nb_queue_pairs: Specify the maximum number of queue pairs in the device (8 by default).
+
+* max_nb_sessions: Specify the maximum number of sessions that can be created (2048 by default).
+
+Example:
+
+.. code-block:: console
+
+    --vdev="crypto_chacha20_poly1305,socket_id=0,max_nb_sessions=128"
diff --git a/doc/guides/cryptodevs/features/chacha20_poly1305.ini b/doc/guides/cryptodevs/features/chacha20_poly1305.ini
new file mode 100644 (file)
index 0000000..3353e03
--- /dev/null
@@ -0,0 +1,35 @@
+;
+; Supported features of the 'chacha20_poly1305' crypto driver.
+;
+; Refer to default.ini for the full list of available PMD features.
+;
+[Features]
+Symmetric crypto       = Y
+Sym operation chaining = Y
+Symmetric sessionless  = Y
+Non-Byte aligned data  = Y
+In Place SGL           = Y
+OOP SGL In LB  Out     = Y
+OOP LB  In LB  Out     = Y
+CPU crypto             = Y
+
+;
+; Supported crypto algorithms of the 'chacha20_poly1305' crypto driver.
+;
+[Cipher]
+
+;
+; Supported authentication algorithms of the 'chacha20_poly1305' crypto driver.
+;
+[Auth]
+
+;
+; Supported AEAD algorithms of the 'chacha20_poly1305' crypto driver.
+;
+[AEAD]
+CHACHA20-POLY1305 = Y
+
+;
+; Supported Asymmetric algorithms of the 'chacha20_poly1305' crypto driver.
+;
+[Asymmetric]
index 0f981c7..3dcc2ec 100644 (file)
@@ -16,6 +16,7 @@ Crypto Device Drivers
     bcmfs
     caam_jr
     ccp
+    chacha20_poly1305
     cnxk
     dpaa2_sec
     dpaa_sec
index 3edcdb5..5f27ab1 100644 (file)
@@ -235,6 +235,7 @@ New Features
     * KASUMI PMD.
     * SNOW3G PMD.
     * ZUC PMD.
+    * CHACHA20_POLY1305 - A new PMD added.
 
 * **Updated the aesni_mb crypto PMD.**
 
index fef3fca..866722d 100644 (file)
@@ -49,6 +49,9 @@ extern RTE_DEFINE_PER_LCORE(IMB_MGR *, mb_mgr);
 #define CRYPTODEV_NAME_ZUC_PMD crypto_zuc
 /**< IPSEC Multi buffer PMD zuc device name */
 
+#define CRYPTODEV_NAME_CHACHA20_POLY1305_PMD crypto_chacha20_poly1305
+/**< IPSEC Multi buffer PMD chacha20_poly1305 device name */
+
 /** PMD LOGTYPE DRIVER, common to all PMDs */
 extern int ipsec_mb_logtype_driver;
 #define IPSEC_MB_LOG(level, fmt, ...)                                         \
@@ -62,6 +65,7 @@ enum ipsec_mb_pmd_types {
        IPSEC_MB_PMD_TYPE_KASUMI,
        IPSEC_MB_PMD_TYPE_SNOW3G,
        IPSEC_MB_PMD_TYPE_ZUC,
+       IPSEC_MB_PMD_TYPE_CHACHA20_POLY1305,
        IPSEC_MB_N_PMD_TYPES
 };
 
@@ -85,6 +89,7 @@ extern uint8_t pmd_driver_id_aesni_gcm;
 extern uint8_t pmd_driver_id_kasumi;
 extern uint8_t pmd_driver_id_snow3g;
 extern uint8_t pmd_driver_id_zuc;
+extern uint8_t pmd_driver_id_chacha20_poly1305;
 
 /** Helper function. Gets driver ID based on PMD type */
 static __rte_always_inline uint8_t
@@ -101,6 +106,8 @@ ipsec_mb_get_driver_id(enum ipsec_mb_pmd_types pmd_type)
                return pmd_driver_id_snow3g;
        case IPSEC_MB_PMD_TYPE_ZUC:
                return pmd_driver_id_zuc;
+       case IPSEC_MB_PMD_TYPE_CHACHA20_POLY1305:
+               return pmd_driver_id_chacha20_poly1305;
        default:
                break;
        }
index c712c2a..d7037da 100644 (file)
@@ -25,6 +25,7 @@ sources = files('ipsec_mb_private.c',
                'ipsec_mb_ops.c',
                'pmd_aesni_mb.c',
                'pmd_aesni_gcm.c',
+               'pmd_chacha_poly.c',
                'pmd_kasumi.c',
                'pmd_snow3g.c',
                'pmd_zuc.c'
diff --git a/drivers/crypto/ipsec_mb/pmd_chacha_poly.c b/drivers/crypto/ipsec_mb/pmd_chacha_poly.c
new file mode 100644 (file)
index 0000000..d953d6e
--- /dev/null
@@ -0,0 +1,408 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright(c) 2021 Intel Corporation
+ */
+
+#include "pmd_chacha_poly_priv.h"
+
+/** Parse crypto xform chain and set private session parameters. */
+static int
+chacha20_poly1305_session_configure(IMB_MGR * mb_mgr __rte_unused,
+               void *priv_sess, const struct rte_crypto_sym_xform *xform)
+{
+       struct chacha20_poly1305_session *sess = priv_sess;
+       const struct rte_crypto_sym_xform *auth_xform;
+       const struct rte_crypto_sym_xform *cipher_xform;
+       const struct rte_crypto_sym_xform *aead_xform;
+
+       uint8_t key_length;
+       const uint8_t *key;
+       enum ipsec_mb_operation mode;
+       int ret = 0;
+
+       ret = ipsec_mb_parse_xform(xform, &mode, &auth_xform,
+                               &cipher_xform, &aead_xform);
+       if (ret)
+               return ret;
+
+       sess->op = mode;
+
+       switch (sess->op) {
+       case IPSEC_MB_OP_AEAD_AUTHENTICATED_ENCRYPT:
+       case IPSEC_MB_OP_AEAD_AUTHENTICATED_DECRYPT:
+               if (aead_xform->aead.algo !=
+                               RTE_CRYPTO_AEAD_CHACHA20_POLY1305) {
+                       IPSEC_MB_LOG(ERR,
+                       "The only combined operation supported is CHACHA20 POLY1305");
+                       ret = -ENOTSUP;
+                       goto error_exit;
+               }
+               /* Set IV parameters */
+               sess->iv.offset = aead_xform->aead.iv.offset;
+               sess->iv.length = aead_xform->aead.iv.length;
+               key_length = aead_xform->aead.key.length;
+               key = aead_xform->aead.key.data;
+               sess->aad_length = aead_xform->aead.aad_length;
+               sess->req_digest_length = aead_xform->aead.digest_length;
+               break;
+       default:
+               IPSEC_MB_LOG(
+                   ERR, "Wrong xform type, has to be AEAD or authentication");
+               ret = -ENOTSUP;
+               goto error_exit;
+       }
+
+       /* IV check */
+       if (sess->iv.length != CHACHA20_POLY1305_IV_LENGTH &&
+               sess->iv.length != 0) {
+               IPSEC_MB_LOG(ERR, "Wrong IV length");
+               ret = -EINVAL;
+               goto error_exit;
+       }
+
+       /* Check key length */
+       if (key_length != CHACHA20_POLY1305_KEY_SIZE) {
+               IPSEC_MB_LOG(ERR, "Invalid key length");
+               ret = -EINVAL;
+               goto error_exit;
+       } else {
+               memcpy(sess->key, key, CHACHA20_POLY1305_KEY_SIZE);
+       }
+
+       /* Digest check */
+       if (sess->req_digest_length !=  CHACHA20_POLY1305_DIGEST_LENGTH) {
+               IPSEC_MB_LOG(ERR, "Invalid digest length");
+               ret = -EINVAL;
+               goto error_exit;
+       } else {
+               sess->gen_digest_length = CHACHA20_POLY1305_DIGEST_LENGTH;
+       }
+
+error_exit:
+       return ret;
+}
+
+/**
+ * Process a crypto operation, calling
+ * the direct chacha poly API from the multi buffer library.
+ *
+ * @param      qp              queue pair
+ * @param      op              symmetric crypto operation
+ * @param      session         chacha poly session
+ *
+ * @return
+ * - Return 0 if success
+ */
+static int
+chacha20_poly1305_crypto_op(struct ipsec_mb_qp *qp, struct rte_crypto_op *op,
+               struct chacha20_poly1305_session *session)
+{
+       struct chacha20_poly1305_qp_data *qp_data =
+                                       ipsec_mb_get_qp_private_data(qp);
+       uint8_t *src, *dst;
+       uint8_t *iv_ptr;
+       struct rte_crypto_sym_op *sym_op = op->sym;
+       struct rte_mbuf *m_src = sym_op->m_src;
+       uint32_t offset, data_offset, data_length;
+       uint32_t part_len, data_len;
+       int total_len;
+       uint8_t *tag;
+       unsigned int oop = 0;
+
+       offset = sym_op->aead.data.offset;
+       data_offset = offset;
+       data_length = sym_op->aead.data.length;
+       RTE_ASSERT(m_src != NULL);
+
+       while (offset >= m_src->data_len && data_length != 0) {
+               offset -= m_src->data_len;
+               m_src = m_src->next;
+
+               RTE_ASSERT(m_src != NULL);
+       }
+
+       src = rte_pktmbuf_mtod_offset(m_src, uint8_t *, offset);
+
+       data_len = m_src->data_len - offset;
+       part_len = (data_len < data_length) ? data_len :
+                       data_length;
+
+       /* In-place */
+       if (sym_op->m_dst == NULL || (sym_op->m_dst == sym_op->m_src))
+               dst = src;
+       /* Out-of-place */
+       else {
+               oop = 1;
+               /* Segmented destination buffer is not supported
+                * if operation is Out-of-place
+                */
+               RTE_ASSERT(rte_pktmbuf_is_contiguous(sym_op->m_dst));
+               dst = rte_pktmbuf_mtod_offset(sym_op->m_dst, uint8_t *,
+                                       data_offset);
+       }
+
+       iv_ptr = rte_crypto_op_ctod_offset(op, uint8_t *,
+                               session->iv.offset);
+
+       IMB_CHACHA20_POLY1305_INIT(qp->mb_mgr, session->key,
+                               &qp_data->chacha20_poly1305_ctx_data,
+                               iv_ptr, sym_op->aead.aad.data,
+                               (uint64_t)session->aad_length);
+
+       if (session->op == IPSEC_MB_OP_AEAD_AUTHENTICATED_ENCRYPT) {
+               IMB_CHACHA20_POLY1305_ENC_UPDATE(qp->mb_mgr,
+                               session->key,
+                               &qp_data->chacha20_poly1305_ctx_data,
+                               dst, src, (uint64_t)part_len);
+               total_len = data_length - part_len;
+
+               while (total_len) {
+                       m_src = m_src->next;
+                       RTE_ASSERT(m_src != NULL);
+
+                       src = rte_pktmbuf_mtod(m_src, uint8_t *);
+                       if (oop)
+                               dst += part_len;
+                       else
+                               dst = src;
+                       part_len = (m_src->data_len < total_len) ?
+                                       m_src->data_len : total_len;
+
+                       if (dst == NULL || src == NULL) {
+                               IPSEC_MB_LOG(ERR, "Invalid src or dst input");
+                               return -EINVAL;
+                       }
+                       IMB_CHACHA20_POLY1305_ENC_UPDATE(qp->mb_mgr,
+                                       session->key,
+                                       &qp_data->chacha20_poly1305_ctx_data,
+                                       dst, src, (uint64_t)part_len);
+                       total_len -= part_len;
+                       if (total_len < 0) {
+                               IPSEC_MB_LOG(ERR, "Invalid part len");
+                               return -EINVAL;
+                       }
+               }
+
+               tag = sym_op->aead.digest.data;
+               IMB_CHACHA20_POLY1305_ENC_FINALIZE(qp->mb_mgr,
+                                       &qp_data->chacha20_poly1305_ctx_data,
+                                       tag, session->gen_digest_length);
+
+       } else {
+               IMB_CHACHA20_POLY1305_DEC_UPDATE(qp->mb_mgr,
+                                       session->key,
+                                       &qp_data->chacha20_poly1305_ctx_data,
+                                       dst, src, (uint64_t)part_len);
+
+               total_len = data_length - part_len;
+
+               while (total_len) {
+                       m_src = m_src->next;
+
+                       RTE_ASSERT(m_src != NULL);
+
+                       src = rte_pktmbuf_mtod(m_src, uint8_t *);
+                       if (oop)
+                               dst += part_len;
+                       else
+                               dst = src;
+                       part_len = (m_src->data_len < total_len) ?
+                                       m_src->data_len : total_len;
+
+                       if (dst == NULL || src == NULL) {
+                               IPSEC_MB_LOG(ERR, "Invalid src or dst input");
+                               return -EINVAL;
+                       }
+                       IMB_CHACHA20_POLY1305_DEC_UPDATE(qp->mb_mgr,
+                                       session->key,
+                                       &qp_data->chacha20_poly1305_ctx_data,
+                                       dst, src, (uint64_t)part_len);
+                       total_len -= part_len;
+                       if (total_len < 0) {
+                               IPSEC_MB_LOG(ERR, "Invalid part len");
+                               return -EINVAL;
+                       }
+               }
+
+               tag = qp_data->temp_digest;
+               IMB_CHACHA20_POLY1305_DEC_FINALIZE(qp->mb_mgr,
+                                       &qp_data->chacha20_poly1305_ctx_data,
+                                       tag, session->gen_digest_length);
+       }
+
+       return 0;
+}
+
+/**
+ * Process a completed chacha poly op
+ *
+ * @param qp           Queue Pair to process
+ * @param op           Crypto operation
+ * @param sess         Crypto session
+ *
+ * @return
+ * - void
+ */
+static void
+post_process_chacha20_poly1305_crypto_op(struct ipsec_mb_qp *qp,
+               struct rte_crypto_op *op,
+               struct chacha20_poly1305_session *session)
+{
+       struct chacha20_poly1305_qp_data *qp_data =
+                                       ipsec_mb_get_qp_private_data(qp);
+
+       op->status = RTE_CRYPTO_OP_STATUS_SUCCESS;
+       /* Verify digest if required */
+       if (session->op == IPSEC_MB_OP_AEAD_AUTHENTICATED_DECRYPT ||
+                       session->op == IPSEC_MB_OP_HASH_VERIFY_ONLY) {
+               uint8_t *digest = op->sym->aead.digest.data;
+               uint8_t *tag = qp_data->temp_digest;
+
+#ifdef RTE_LIBRTE_PMD_CHACHA20_POLY1305_DEBUG
+               rte_hexdump(stdout, "auth tag (orig):",
+                               digest, session->req_digest_length);
+               rte_hexdump(stdout, "auth tag (calc):",
+                               tag, session->req_digest_length);
+#endif
+               if (memcmp(tag, digest, session->req_digest_length) != 0)
+                       op->status = RTE_CRYPTO_OP_STATUS_AUTH_FAILED;
+
+       }
+
+}
+
+/**
+ * Process a completed Chacha20_poly1305 request
+ *
+ * @param qp           Queue Pair to process
+ * @param op           Crypto operation
+ * @param sess         Crypto session
+ *
+ * @return
+ * - void
+ */
+static void
+handle_completed_chacha20_poly1305_crypto_op(struct ipsec_mb_qp *qp,
+               struct rte_crypto_op *op,
+               struct chacha20_poly1305_session *sess)
+{
+       post_process_chacha20_poly1305_crypto_op(qp, op, sess);
+
+       /* Free session if a session-less crypto op */
+       if (op->sess_type == RTE_CRYPTO_OP_SESSIONLESS) {
+               memset(sess, 0, sizeof(struct chacha20_poly1305_session));
+               memset(op->sym->session, 0,
+                       rte_cryptodev_sym_get_existing_header_session_size(
+                               op->sym->session));
+               rte_mempool_put(qp->sess_mp_priv, sess);
+               rte_mempool_put(qp->sess_mp, op->sym->session);
+               op->sym->session = NULL;
+       }
+}
+
+static uint16_t
+chacha20_poly1305_pmd_dequeue_burst(void *queue_pair,
+               struct rte_crypto_op **ops, uint16_t nb_ops)
+{
+       struct chacha20_poly1305_session *sess;
+       struct ipsec_mb_qp *qp = queue_pair;
+
+       int retval = 0;
+       unsigned int i = 0, nb_dequeued;
+
+       nb_dequeued = rte_ring_dequeue_burst(qp->ingress_queue,
+                       (void **)ops, nb_ops, NULL);
+
+       for (i = 0; i < nb_dequeued; i++) {
+
+               sess = ipsec_mb_get_session_private(qp, ops[i]);
+               if (unlikely(sess == NULL)) {
+                       ops[i]->status = RTE_CRYPTO_OP_STATUS_INVALID_ARGS;
+                       qp->stats.dequeue_err_count++;
+                       break;
+               }
+
+               retval = chacha20_poly1305_crypto_op(qp, ops[i], sess);
+               if (retval < 0) {
+                       ops[i]->status = RTE_CRYPTO_OP_STATUS_INVALID_ARGS;
+                       qp->stats.dequeue_err_count++;
+                       break;
+               }
+
+               handle_completed_chacha20_poly1305_crypto_op(qp, ops[i], sess);
+       }
+
+       qp->stats.dequeued_count += i;
+
+       return i;
+}
+
+struct rte_cryptodev_ops chacha20_poly1305_pmd_ops = {
+       .dev_configure = ipsec_mb_config,
+       .dev_start = ipsec_mb_start,
+       .dev_stop = ipsec_mb_stop,
+       .dev_close = ipsec_mb_close,
+
+       .stats_get = ipsec_mb_stats_get,
+       .stats_reset = ipsec_mb_stats_reset,
+
+       .dev_infos_get = ipsec_mb_info_get,
+
+       .queue_pair_setup = ipsec_mb_qp_setup,
+       .queue_pair_release = ipsec_mb_qp_release,
+
+       .sym_session_get_size = ipsec_mb_sym_session_get_size,
+       .sym_session_configure = ipsec_mb_sym_session_configure,
+       .sym_session_clear = ipsec_mb_sym_session_clear
+};
+
+struct rte_cryptodev_ops *rte_chacha20_poly1305_pmd_ops =
+                                               &chacha20_poly1305_pmd_ops;
+
+static int
+chacha20_poly1305_probe(struct rte_vdev_device *vdev)
+{
+       return ipsec_mb_create(vdev, IPSEC_MB_PMD_TYPE_CHACHA20_POLY1305);
+}
+
+static struct rte_vdev_driver cryptodev_chacha20_poly1305_pmd_drv = {
+       .probe = chacha20_poly1305_probe,
+       .remove = ipsec_mb_remove
+};
+
+static struct cryptodev_driver chacha20_poly1305_crypto_drv;
+
+RTE_PMD_REGISTER_VDEV(CRYPTODEV_NAME_CHACHA20_POLY1305_PMD,
+                                       cryptodev_chacha20_poly1305_pmd_drv);
+RTE_PMD_REGISTER_ALIAS(CRYPTODEV_NAME_CHACHA20_POLY1305_PMD,
+                                       cryptodev_chacha20_poly1305_pmd);
+RTE_PMD_REGISTER_PARAM_STRING(CRYPTODEV_NAME_CHACHA20_POLY1305_PMD,
+                              "max_nb_queue_pairs=<int> socket_id=<int>");
+RTE_PMD_REGISTER_CRYPTO_DRIVER(chacha20_poly1305_crypto_drv,
+                               cryptodev_chacha20_poly1305_pmd_drv.driver,
+                               pmd_driver_id_chacha20_poly1305);
+
+/* Constructor function to register chacha20_poly1305 PMD */
+RTE_INIT(ipsec_mb_register_chacha20_poly1305)
+{
+       struct ipsec_mb_internals *chacha_poly_data
+               = &ipsec_mb_pmds[IPSEC_MB_PMD_TYPE_CHACHA20_POLY1305];
+
+       chacha_poly_data->caps = chacha20_poly1305_capabilities;
+       chacha_poly_data->dequeue_burst = chacha20_poly1305_pmd_dequeue_burst;
+       chacha_poly_data->feature_flags =
+               RTE_CRYPTODEV_FF_SYMMETRIC_CRYPTO |
+               RTE_CRYPTODEV_FF_SYM_OPERATION_CHAINING |
+               RTE_CRYPTODEV_FF_IN_PLACE_SGL |
+               RTE_CRYPTODEV_FF_OOP_SGL_IN_LB_OUT |
+               RTE_CRYPTODEV_FF_OOP_LB_IN_LB_OUT |
+               RTE_CRYPTODEV_FF_SYM_CPU_CRYPTO |
+               RTE_CRYPTODEV_FF_SYM_SESSIONLESS;
+       chacha_poly_data->internals_priv_size = 0;
+       chacha_poly_data->ops = &chacha20_poly1305_pmd_ops;
+       chacha_poly_data->qp_priv_size =
+                       sizeof(struct chacha20_poly1305_qp_data);
+       chacha_poly_data->session_configure =
+                       chacha20_poly1305_session_configure;
+       chacha_poly_data->session_priv_size =
+                       sizeof(struct chacha20_poly1305_session);
+}
diff --git a/drivers/crypto/ipsec_mb/pmd_chacha_poly_priv.h b/drivers/crypto/ipsec_mb/pmd_chacha_poly_priv.h
new file mode 100644 (file)
index 0000000..842f62f
--- /dev/null
@@ -0,0 +1,74 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright(c) 2021 Intel Corporation
+ */
+
+#ifndef _PMD_CHACHA_POLY_PRIV_H_
+#define _PMD_CHACHA_POLY_PRIV_H_
+
+#include "ipsec_mb_private.h"
+
+#define CHACHA20_POLY1305_IV_LENGTH 12
+#define CHACHA20_POLY1305_DIGEST_LENGTH 16
+#define CHACHA20_POLY1305_KEY_SIZE  32
+
+static const
+struct rte_cryptodev_capabilities chacha20_poly1305_capabilities[] = {
+       {/* CHACHA20-POLY1305 */
+           .op = RTE_CRYPTO_OP_TYPE_SYMMETRIC,
+           {.sym = {
+                       .xform_type = RTE_CRYPTO_SYM_XFORM_AEAD,
+                   {.aead = {
+                               .algo = RTE_CRYPTO_AEAD_CHACHA20_POLY1305,
+                               .block_size = 64,
+                               .key_size = {
+                                       .min = 32,
+                                       .max = 32,
+                                       .increment = 0},
+                               .digest_size = {
+                                       .min = 16,
+                                       .max = 16,
+                                       .increment = 0},
+                               .aad_size = {
+                                       .min = 0,
+                                       .max = 240,
+                                       .increment = 1},
+                               .iv_size = {
+                                       .min = 12,
+                                       .max = 12,
+                                       .increment = 0},
+                           },
+                       }
+               },}
+       },
+       RTE_CRYPTODEV_END_OF_CAPABILITIES_LIST()
+};
+
+uint8_t pmd_driver_id_chacha20_poly1305;
+
+/** CHACHA20 POLY1305 private session structure */
+struct chacha20_poly1305_session {
+       struct {
+               uint16_t length;
+               uint16_t offset;
+       } iv;
+       /**< IV parameters */
+       uint16_t aad_length;
+       /**< AAD length */
+       uint16_t req_digest_length;
+       /**< Requested digest length */
+       uint16_t gen_digest_length;
+       /**< Generated digest length */
+       uint8_t key[CHACHA20_POLY1305_KEY_SIZE];
+       enum ipsec_mb_operation op;
+} __rte_cache_aligned;
+
+struct chacha20_poly1305_qp_data {
+       struct chacha20_poly1305_context_data chacha20_poly1305_ctx_data;
+       uint8_t temp_digest[CHACHA20_POLY1305_DIGEST_LENGTH];
+       /**< Buffer used to store the digest generated
+        * by the driver when verifying a digest provided
+        * by the user (using authentication verify operation)
+        */
+};
+
+#endif /* _PMD_CHACHA_POLY_PRIV_H_ */