get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

GET /api/patches/67797/?format=api
HTTP 200 OK
Allow: GET, PUT, PATCH, HEAD, OPTIONS
Content-Type: application/json
Vary: Accept

{
    "id": 67797,
    "url": "https://patches.dpdk.org/api/patches/67797/?format=api",
    "web_url": "https://patches.dpdk.org/project/dpdk/patch/20200403163656.60545-2-david.coyle@intel.com/",
    "project": {
        "id": 1,
        "url": "https://patches.dpdk.org/api/projects/1/?format=api",
        "name": "DPDK",
        "link_name": "dpdk",
        "list_id": "dev.dpdk.org",
        "list_email": "dev@dpdk.org",
        "web_url": "http://core.dpdk.org",
        "scm_url": "git://dpdk.org/dpdk",
        "webscm_url": "http://git.dpdk.org/dpdk",
        "list_archive_url": "https://inbox.dpdk.org/dev",
        "list_archive_url_format": "https://inbox.dpdk.org/dev/{}",
        "commit_url_format": ""
    },
    "msgid": "<20200403163656.60545-2-david.coyle@intel.com>",
    "list_archive_url": "https://inbox.dpdk.org/dev/20200403163656.60545-2-david.coyle@intel.com",
    "date": "2020-04-03T16:36:53",
    "name": "[v2,1/4] raw/common: add multi-function interface",
    "commit_ref": null,
    "pull_url": null,
    "state": "superseded",
    "archived": true,
    "hash": "cd62b640de0bbc5945644383c0f687fbff8b8b1e",
    "submitter": {
        "id": 961,
        "url": "https://patches.dpdk.org/api/people/961/?format=api",
        "name": "Coyle, David",
        "email": "david.coyle@intel.com"
    },
    "delegate": null,
    "mbox": "https://patches.dpdk.org/project/dpdk/patch/20200403163656.60545-2-david.coyle@intel.com/mbox/",
    "series": [
        {
            "id": 9194,
            "url": "https://patches.dpdk.org/api/series/9194/?format=api",
            "web_url": "https://patches.dpdk.org/project/dpdk/list/?series=9194",
            "date": "2020-04-03T16:36:52",
            "name": "introduce multi-function processing support",
            "version": 2,
            "mbox": "https://patches.dpdk.org/series/9194/mbox/"
        }
    ],
    "comments": "https://patches.dpdk.org/api/patches/67797/comments/",
    "check": "fail",
    "checks": "https://patches.dpdk.org/api/patches/67797/checks/",
    "tags": {},
    "related": [],
    "headers": {
        "Return-Path": "<dev-bounces@dpdk.org>",
        "X-Original-To": "patchwork@inbox.dpdk.org",
        "Delivered-To": "patchwork@inbox.dpdk.org",
        "Received": [
            "from dpdk.org (dpdk.org [92.243.14.124])\n\tby inbox.dpdk.org (Postfix) with ESMTP id CFA80A0562;\n\tFri,  3 Apr 2020 18:48:44 +0200 (CEST)",
            "from [92.243.14.124] (localhost [127.0.0.1])\n\tby dpdk.org (Postfix) with ESMTP id 113371C1D8;\n\tFri,  3 Apr 2020 18:48:38 +0200 (CEST)",
            "from mga17.intel.com (mga17.intel.com [192.55.52.151])\n by dpdk.org (Postfix) with ESMTP id 103341C1D2\n for <dev@dpdk.org>; Fri,  3 Apr 2020 18:48:35 +0200 (CEST)",
            "from fmsmga004.fm.intel.com ([10.253.24.48])\n by fmsmga107.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384;\n 03 Apr 2020 09:48:34 -0700",
            "from silpixa00399912.ir.intel.com (HELO\n silpixa00399912.ger.corp.intel.com) ([10.237.223.64])\n by fmsmga004.fm.intel.com with ESMTP; 03 Apr 2020 09:48:32 -0700"
        ],
        "IronPort-SDR": [
            "\n XHZn/6+nHc8VX4OhuT58HeIg42IJ31E4/C0aLq2xJolHeGy6fv2o9rOp4BFzKmzhGiN9Z6BIFz\n SXajAiOuSdpQ==",
            "\n +f5+p8mK1iVIUPjyqHveAn4wKOBybe+tCpRvs1Fk/4wwbSWvv6n/sVh+hin14+YOQlXiHHL+B7\n rYkuUGBAndPg=="
        ],
        "X-Amp-Result": "SKIPPED(no attachment in message)",
        "X-Amp-File-Uploaded": "False",
        "X-ExtLoop1": "1",
        "X-IronPort-AV": "E=Sophos;i=\"5.72,340,1580803200\"; d=\"scan'208\";a=\"274016880\"",
        "From": "David Coyle <david.coyle@intel.com>",
        "To": "dev@dpdk.org",
        "Cc": "declan.doherty@intel.com, fiona.trahe@intel.com,\n pablo.de.lara.guarch@intel.com, brendan.ryan@intel.com,\n shreyansh.jain@nxp.com, hemant.agrawal@nxp.com,\n David Coyle <david.coyle@intel.com>,\n Mairtin o Loingsigh <mairtin.oloingsigh@intel.com>",
        "Date": "Fri,  3 Apr 2020 17:36:53 +0100",
        "Message-Id": "<20200403163656.60545-2-david.coyle@intel.com>",
        "X-Mailer": "git-send-email 2.17.1",
        "In-Reply-To": "<20200403163656.60545-1-david.coyle@intel.com>",
        "References": "<20200403163656.60545-1-david.coyle@intel.com>",
        "Subject": "[dpdk-dev] [PATCH v2 1/4] raw/common: add multi-function interface",
        "X-BeenThere": "dev@dpdk.org",
        "X-Mailman-Version": "2.1.15",
        "Precedence": "list",
        "List-Id": "DPDK patches and discussions <dev.dpdk.org>",
        "List-Unsubscribe": "<https://mails.dpdk.org/options/dev>,\n <mailto:dev-request@dpdk.org?subject=unsubscribe>",
        "List-Archive": "<http://mails.dpdk.org/archives/dev/>",
        "List-Post": "<mailto:dev@dpdk.org>",
        "List-Help": "<mailto:dev-request@dpdk.org?subject=help>",
        "List-Subscribe": "<https://mails.dpdk.org/listinfo/dev>,\n <mailto:dev-request@dpdk.org?subject=subscribe>",
        "Errors-To": "dev-bounces@dpdk.org",
        "Sender": "\"dev\" <dev-bounces@dpdk.org>"
    },
    "content": "The multi-function interface provides a flexible and extensible\nway of combining one or more packet processing functions into a\nsingle operation. The interface can be used by applications to\nsend the combined operations to a optimized software or hardware\naccelerator via a raw device.\n\nSigned-off-by: David Coyle <david.coyle@intel.com>\nSigned-off-by: Mairtin o Loingsigh <mairtin.oloingsigh@intel.com>\n---\n\nIn particular, looking for feedback on the meson script changes\nthat were required to build the drivers/raw/common/multi_fn\ndirectory. Thank you.\n\n config/common_base                            |   5 +\n drivers/meson.build                           |   5 +\n drivers/raw/Makefile                          |   1 +\n drivers/raw/common/Makefile                   |   8 +\n drivers/raw/common/meson.build                |   7 +\n drivers/raw/common/multi_fn/Makefile          |  27 ++\n drivers/raw/common/multi_fn/meson.build       |   9 +\n .../multi_fn/rte_common_multi_fn_version.map  |  11 +\n drivers/raw/common/multi_fn/rte_multi_fn.c    | 166 +++++++++\n drivers/raw/common/multi_fn/rte_multi_fn.h    | 350 ++++++++++++++++++\n .../raw/common/multi_fn/rte_multi_fn_driver.h |  55 +++\n meson.build                                   |   4 +\n mk/rte.app.mk                                 |   1 +\n 13 files changed, 649 insertions(+)\n create mode 100644 drivers/raw/common/Makefile\n create mode 100644 drivers/raw/common/meson.build\n create mode 100644 drivers/raw/common/multi_fn/Makefile\n create mode 100644 drivers/raw/common/multi_fn/meson.build\n create mode 100644 drivers/raw/common/multi_fn/rte_common_multi_fn_version.map\n create mode 100644 drivers/raw/common/multi_fn/rte_multi_fn.c\n create mode 100644 drivers/raw/common/multi_fn/rte_multi_fn.h\n create mode 100644 drivers/raw/common/multi_fn/rte_multi_fn_driver.h",
    "diff": "diff --git a/config/common_base b/config/common_base\nindex c31175f9d..4f004968b 100644\n--- a/config/common_base\n+++ b/config/common_base\n@@ -818,6 +818,11 @@ CONFIG_RTE_LIBRTE_PMD_OCTEONTX2_EP_RAWDEV=y\n #\n CONFIG_RTE_LIBRTE_PMD_NTB_RAWDEV=y\n \n+#\n+# Compile multi-fn raw device interface\n+#\n+CONFIG_RTE_LIBRTE_MULTI_FN_COMMON=n\n+\n #\n # Compile librte_ring\n #\ndiff --git a/drivers/meson.build b/drivers/meson.build\nindex 5502bf992..4e0caeff3 100644\n--- a/drivers/meson.build\n+++ b/drivers/meson.build\n@@ -10,6 +10,7 @@ dpdk_driver_classes = ['common',\n \t       'bus',\n \t       'mempool', # depends on common and bus.\n \t       'net',     # depends on common, bus, mempool\n+\t       'raw/common',\n \t       'raw',     # depends on common, bus and net.\n \t       'crypto',  # depends on common, bus and mempool (net in future).\n \t       'compress', # depends on common, bus, mempool.\n@@ -212,5 +213,9 @@ foreach class:dpdk_driver_classes\n \t\tendif # build\n \tendforeach\n \n+\tif class.contains('/')\n+\t\tclass_split = class.split('/')\n+\t\tclass = '_'.join(class_split)\n+\tendif\n \tset_variable(class + '_drivers', class_drivers)\n endforeach\ndiff --git a/drivers/raw/Makefile b/drivers/raw/Makefile\nindex 80b043eb1..e16da8d95 100644\n--- a/drivers/raw/Makefile\n+++ b/drivers/raw/Makefile\n@@ -14,5 +14,6 @@ DIRS-$(CONFIG_RTE_LIBRTE_PMD_IOAT_RAWDEV) += ioat\n DIRS-$(CONFIG_RTE_LIBRTE_PMD_NTB_RAWDEV) += ntb\n DIRS-$(CONFIG_RTE_LIBRTE_PMD_OCTEONTX2_DMA_RAWDEV) += octeontx2_dma\n DIRS-$(CONFIG_RTE_LIBRTE_PMD_OCTEONTX2_EP_RAWDEV) += octeontx2_ep\n+DIRS-y += common\n \n include $(RTE_SDK)/mk/rte.subdir.mk\ndiff --git a/drivers/raw/common/Makefile b/drivers/raw/common/Makefile\nnew file mode 100644\nindex 000000000..5c9ad399f\n--- /dev/null\n+++ b/drivers/raw/common/Makefile\n@@ -0,0 +1,8 @@\n+# SPDX-License-Identifier: BSD-3-Clause\n+# Copyright(c) 2020 Intel Corporation.\n+\n+include $(RTE_SDK)/mk/rte.vars.mk\n+\n+DIRS-$(CONFIG_RTE_LIBRTE_MULTI_FN_COMMON) += multi_fn\n+\n+include $(RTE_SDK)/mk/rte.subdir.mk\ndiff --git a/drivers/raw/common/meson.build b/drivers/raw/common/meson.build\nnew file mode 100644\nindex 000000000..1a8334348\n--- /dev/null\n+++ b/drivers/raw/common/meson.build\n@@ -0,0 +1,7 @@\n+# SPDX-License-Identifier: BSD-3-Clause\n+# Copyright(c) 2020 Intel Corporation.\n+\n+drivers = ['multi_fn']\n+std_deps = ['rawdev']\n+config_flag_fmt = 'RTE_LIBRTE_@0@_COMMON'\n+driver_name_fmt = 'rte_common_@0@'\ndiff --git a/drivers/raw/common/multi_fn/Makefile b/drivers/raw/common/multi_fn/Makefile\nnew file mode 100644\nindex 000000000..7ffbc6bb6\n--- /dev/null\n+++ b/drivers/raw/common/multi_fn/Makefile\n@@ -0,0 +1,27 @@\n+# SPDX-License-Identifier: BSD-3-Clause\n+# Copyright(c) 2020 Intel Corporation.\n+\n+include $(RTE_SDK)/mk/rte.vars.mk\n+\n+# library name\n+LIB = librte_multi_fn.a\n+\n+# build flags\n+CFLAGS += -O3\n+CFLAGS += $(WERROR_FLAGS)\n+CFLAGS += -DALLOW_EXPERIMENTAL_API\n+\n+# versioning export map\n+EXPORT_MAP := rte_common_multi_fn_version.map\n+\n+# external library dependencies\n+LDLIBS += -lrte_eal\n+LDLIBS += -lrte_mempool\n+LDLIBS += -lrte_rawdev\n+\n+SRCS-y += rte_multi_fn.c\n+\n+SYMLINK-y-include += rte_multi_fn.h\n+SYMLINK-y-include += rte_multi_fn_driver.h\n+\n+include $(RTE_SDK)/mk/rte.lib.mk\ndiff --git a/drivers/raw/common/multi_fn/meson.build b/drivers/raw/common/multi_fn/meson.build\nnew file mode 100644\nindex 000000000..ec331362c\n--- /dev/null\n+++ b/drivers/raw/common/multi_fn/meson.build\n@@ -0,0 +1,9 @@\n+# SPDX-License-Identifier: BSD-3-Clause\n+# Copyright(c) 2020 Intel Corporation.\n+\n+sources = files('rte_multi_fn.c')\n+\n+deps = ['rawdev', 'cryptodev', 'compressdev']\n+allow_experimental_apis = true\n+\n+install_headers('rte_multi_fn.h')\ndiff --git a/drivers/raw/common/multi_fn/rte_common_multi_fn_version.map b/drivers/raw/common/multi_fn/rte_common_multi_fn_version.map\nnew file mode 100644\nindex 000000000..ff04827da\n--- /dev/null\n+++ b/drivers/raw/common/multi_fn/rte_common_multi_fn_version.map\n@@ -0,0 +1,11 @@\n+EXPERIMENTAL {\n+\tglobal:\n+\n+\trte_multi_fn_session_create;\n+\trte_multi_fn_session_destroy;\n+\trte_multi_fn_op_pool_create;\n+\trte_multi_fn_op_bulk_alloc;\n+\trte_multi_fn_op_free;\n+\n+\tlocal: *;\n+};\ndiff --git a/drivers/raw/common/multi_fn/rte_multi_fn.c b/drivers/raw/common/multi_fn/rte_multi_fn.c\nnew file mode 100644\nindex 000000000..4f8e7fd94\n--- /dev/null\n+++ b/drivers/raw/common/multi_fn/rte_multi_fn.c\n@@ -0,0 +1,166 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2020 Intel Corporation.\n+ */\n+\n+#include <ctype.h>\n+#include <stdio.h>\n+#include <stdlib.h>\n+#include <string.h>\n+#include <stdarg.h>\n+#include <errno.h>\n+#include <stdint.h>\n+#include <inttypes.h>\n+#include <sys/types.h>\n+#include <sys/queue.h>\n+\n+#include <rte_string_fns.h>\n+#include <rte_byteorder.h>\n+#include <rte_log.h>\n+#include <rte_debug.h>\n+#include <rte_dev.h>\n+#include <rte_memory.h>\n+#include <rte_memcpy.h>\n+#include <rte_memzone.h>\n+#include <rte_eal.h>\n+#include <rte_per_lcore.h>\n+#include <rte_lcore.h>\n+#include <rte_atomic.h>\n+#include <rte_branch_prediction.h>\n+#include <rte_common.h>\n+#include <rte_malloc.h>\n+#include <rte_errno.h>\n+#include <rte_rawdev.h>\n+\n+#include \"rte_multi_fn_driver.h\"\n+#include \"rte_multi_fn.h\"\n+\n+/* Dynamic log identifier */\n+static int multi_fn_logtype;\n+\n+/* Logging Macros */\n+#define MF_LOG(level, fmt, args...) \\\n+\trte_log(RTE_LOG_ ## level, multi_fn_logtype, \\\n+\t\t\"%s() line %u: \" fmt \"\\n\", \\\n+\t\t__func__, __LINE__, ##args)\n+#define MF_DEBUG(fmt, args...) \\\n+\tMF_LOG(DEBUG, fmt, ## args)\n+#define MF_INFO(fmt, args...) \\\n+\tMF_LOG(INFO, fmt, ## args)\n+#define MF_ERR(fmt, args...) \\\n+\tMF_LOG(ERR, fmt, ## args)\n+#define MF_WARN(fmt, args...) \\\n+\tMF_LOG(WARNING, fmt, ## args)\n+\n+static void\n+multi_fn_op_init(struct rte_mempool *mempool,\n+\t\t __rte_unused void *opaque_arg,\n+\t\t void *op_data,\n+\t\t __rte_unused unsigned int i)\n+{\n+\tstruct rte_multi_fn_op *op = op_data;\n+\n+\tmemset(op_data, 0, mempool->elt_size);\n+\n+\top->overall_status = RTE_MULTI_FN_OP_STATUS_NOT_PROCESSED;\n+\top->mempool = mempool;\n+}\n+\n+struct rte_multi_fn_session *\n+rte_multi_fn_session_create(uint16_t dev_id,\n+\t\t\t    struct rte_multi_fn_xform *xform,\n+\t\t\t    int socket_id)\n+{\n+\tstruct rte_rawdev *rawdev;\n+\tstruct rte_rawdev_info info = {0};\n+\tstruct rte_multi_fn_ops *mf_ops;\n+\n+\tif (xform == NULL) {\n+\t\tMF_ERR(\"NULL xform for multi-function session create\");\n+\t\treturn NULL;\n+\t}\n+\n+\tif (rte_rawdev_info_get(dev_id, &info) < 0) {\n+\t\tMF_ERR(\"Invalid dev_id=%d\", dev_id);\n+\t\treturn NULL;\n+\t}\n+\n+\trawdev = &rte_rawdevs[dev_id];\n+\n+\tmf_ops = *((struct rte_multi_fn_ops **)(rawdev->dev_private));\n+\n+\tRTE_FUNC_PTR_OR_ERR_RET(*mf_ops->session_create, NULL);\n+\treturn (*mf_ops->session_create)(rawdev, xform, socket_id);\n+}\n+\n+int\n+rte_multi_fn_session_destroy(uint16_t dev_id, struct rte_multi_fn_session *sess)\n+{\n+\tstruct rte_rawdev *rawdev;\n+\tstruct rte_rawdev_info info = {0};\n+\tstruct rte_multi_fn_ops *mf_ops;\n+\n+\tif (rte_rawdev_info_get(dev_id, &info) < 0) {\n+\t\tMF_ERR(\"Invalid dev_id=%d\", dev_id);\n+\t\treturn -EINVAL;\n+\t}\n+\n+\trawdev = &rte_rawdevs[dev_id];\n+\n+\tmf_ops = *((struct rte_multi_fn_ops **)(rawdev->dev_private));\n+\n+\tRTE_FUNC_PTR_OR_ERR_RET(*mf_ops->session_destroy, -ENOTSUP);\n+\treturn (*mf_ops->session_destroy)(rawdev, sess);\n+}\n+\n+struct rte_mempool *\n+rte_multi_fn_op_pool_create(const char *name,\n+\t\t\t    uint32_t nb_elts,\n+\t\t\t    uint32_t cache_size,\n+\t\t\t    uint16_t priv_size,\n+\t\t\t    int socket_id)\n+{\n+\tuint32_t elt_size = sizeof(struct rte_multi_fn_op) + priv_size;\n+\n+\t/* Lookup mempool in case already allocated */\n+\tstruct rte_mempool *mp = rte_mempool_lookup(name);\n+\n+\tif (mp != NULL) {\n+\t\tif (mp->elt_size != elt_size ||\n+\t\t    mp->cache_size < cache_size ||\n+\t\t    mp->size < nb_elts) {\n+\t\t\tmp = NULL;\n+\t\t\tMF_ERR(\"Mempool %s already exists but with \"\n+\t\t\t       \"incompatible parameters\",\n+\t\t\t       name);\n+\t\t\treturn NULL;\n+\t\t}\n+\n+\t\treturn mp;\n+\t}\n+\n+\tmp = rte_mempool_create(name,\n+\t\t\t\tnb_elts,\n+\t\t\t\telt_size,\n+\t\t\t\tcache_size,\n+\t\t\t\t0,\n+\t\t\t\tNULL,\n+\t\t\t\tNULL,\n+\t\t\t\tmulti_fn_op_init,\n+\t\t\t\tNULL,\n+\t\t\t\tsocket_id,\n+\t\t\t\t0);\n+\n+\tif (mp == NULL) {\n+\t\tMF_ERR(\"Failed to create mempool %s\", name);\n+\t\treturn NULL;\n+\t}\n+\n+\treturn mp;\n+}\n+\n+RTE_INIT(rte_multi_fn_log_init)\n+{\n+\tmulti_fn_logtype = rte_log_register(\"pmd.raw.common.multi_fn\");\n+\tif (multi_fn_logtype >= 0)\n+\t\trte_log_set_level(multi_fn_logtype, RTE_LOG_INFO);\n+}\ndiff --git a/drivers/raw/common/multi_fn/rte_multi_fn.h b/drivers/raw/common/multi_fn/rte_multi_fn.h\nnew file mode 100644\nindex 000000000..7290737f9\n--- /dev/null\n+++ b/drivers/raw/common/multi_fn/rte_multi_fn.h\n@@ -0,0 +1,350 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2020 Intel Corporation.\n+ */\n+\n+#ifndef _RTE_MULTI_FN_H_\n+#define _RTE_MULTI_FN_H_\n+\n+#ifdef __cplusplus\n+extern \"C\" {\n+#endif\n+\n+#include <rte_compat.h>\n+#include <rte_common.h>\n+#include <rte_mbuf.h>\n+#include <rte_memory.h>\n+#include <rte_mempool.h>\n+#include <rte_comp.h>\n+#include <rte_crypto.h>\n+#include <rte_rawdev.h>\n+\n+/** Error Detection Algorithms */\n+enum rte_multi_fn_err_detect_algorithm {\n+\tRTE_MULTI_FN_ERR_DETECT_CRC32_ETH,\n+\t/**< CRC32 Ethernet */\n+\tRTE_MULTI_FN_ERR_DETECT_BIP32\n+\t/**< BIP32 */\n+};\n+\n+/** Error Detection Operation Types */\n+enum rte_multi_fn_err_detect_operation {\n+\tRTE_MULTI_FN_ERR_DETECT_OP_VERIFY,\n+\t/**< Verify error detection result */\n+\tRTE_MULTI_FN_ERR_DETECT_OP_GENERATE\n+\t/**< Generate error detection result */\n+};\n+\n+/** Error Detection Status */\n+enum rte_multi_fn_err_detect_op_status {\n+\tRTE_MULTI_FN_ERR_DETECT_OP_STATUS_SUCCESS,\n+\t/**< Operation completed successfully */\n+\tRTE_MULTI_FN_ERR_DETECT_OP_STATUS_NOT_PROCESSED,\n+\t/**< Operation has not yet been processed by a device */\n+\tRTE_MULTI_FN_ERR_DETECT_OP_STATUS_VERIFY_FAILED,\n+\t/**< Verification failed */\n+\tRTE_MULTI_FN_ERR_DETECT_OP_STATUS_ERROR\n+\t/**< Error handling operation */\n+};\n+\n+struct rte_multi_fn_err_detect_xform {\n+\tenum rte_multi_fn_err_detect_operation op;\n+\t/**< Error detection operation type */\n+\tenum rte_multi_fn_err_detect_algorithm algo;\n+\t/**< Error detection algorithm */\n+};\n+\n+/** Error Detection Operation */\n+struct rte_multi_fn_err_detect_op {\n+\tstruct rte_mbuf *m_src; /**< Source mbuf */\n+\tenum rte_multi_fn_err_detect_op_status status;\n+\t/**< Operation status */\n+\n+\tstruct {\n+\t\tuint16_t offset;\n+\t\t/**<\n+\t\t * Starting point for error detection processing, specified\n+\t\t * as the number of bytes from start of the packet in the\n+\t\t * source mbuf\n+\t\t */\n+\t\tuint16_t length;\n+\t\t/**<\n+\t\t * The length, in bytes, of the source mbuf on which the error\n+\t\t * detection operation will be computed\n+\t\t */\n+\t} data; /**< Data offset and length for error detection */\n+\n+\tstruct {\n+\t\tuint8_t *data;\n+\t\t/**<\n+\t\t * This points to the location where the error detection\n+\t\t * result should be written (in the case of generation) or\n+\t\t * where the purported result exists (in the case of\n+\t\t * verification)\n+\t\t *\n+\t\t * The caller must ensure the required length of physically\n+\t\t * contiguous memory is available at this address\n+\t\t *\n+\t\t * For a CRC, this may point into the mbuf packet data. For\n+\t\t * an operation such as a BIP, this may point to a memory\n+\t\t * location after the op\n+\t\t *\n+\t\t * For generation, the result will overwrite any data at this\n+\t\t * location\n+\t\t */\n+\t\trte_iova_t phys_addr;\n+\t\t/**< Physical address of output data */\n+\t} output; /**< Output location */\n+};\n+\n+/**\n+ * Multi-function transform types\n+ */\n+enum rte_multi_fn_xform_type {\n+\tRTE_MULTI_FN_XFORM_TYPE_UNDEFINED,\n+\t/**< Undefined transform type */\n+\tRTE_MULTI_FN_XFORM_TYPE_CRYPTO_SYM,\n+\t/**< Symmetric crypto transform type */\n+\tRTE_MULTI_FN_XFORM_TYPE_CRYPTO_ASYM,\n+\t/**< Asymmetric crypto transform type */\n+\tRTE_MULTI_FN_XFORM_TYPE_COMP,\n+\t/**< Compression transform type */\n+\tRTE_MULTI_FN_XFORM_TYPE_ERR_DETECT\n+\t/**< Error detection transform type */\n+};\n+\n+/**\n+ * Multi-function transform setup data\n+ *\n+ * This structure is used to specify the multi-function transforms required.\n+ * Multiple transforms can be chained together to specify a chain of transforms\n+ * such as symmetric crypto followed by error detection, or compression followed\n+ * by symmetric crypto. Each transform structure holds a single transform, with\n+ * the type field specifying which transform is contained within the union.\n+ */\n+struct rte_multi_fn_xform {\n+\tstruct rte_multi_fn_xform *next;\n+\t/**<\n+\t * Next transform in the chain\n+\t * - the last transform in the chain MUST set this to NULL\n+\t */\n+\tenum rte_multi_fn_xform_type type;\n+\t/**< Transform type */\n+\n+\tRTE_STD_C11\n+\tunion {\n+\t\tstruct rte_crypto_sym_xform crypto_sym;\n+\t\t/**< Symmetric crypto transform */\n+\t\tstruct rte_crypto_asym_xform crypto_asym;\n+\t\t/**< Asymmetric crypto transform */\n+\t\tstruct rte_comp_xform comp;\n+\t\t/**< Compression transform */\n+\t\tstruct rte_multi_fn_err_detect_xform err_detect;\n+\t\t/**< Error detection transform */\n+\t};\n+};\n+\n+/**\n+ * Multi-function operation status\n+ */\n+enum rte_multi_fn_op_status {\n+\tRTE_MULTI_FN_OP_STATUS_SUCCESS,\n+\t/**< Operation completed successfully */\n+\tRTE_MULTI_FN_OP_STATUS_NOT_PROCESSED,\n+\t/**< Operation has not yet been processed by a device */\n+\tRTE_MULTI_FN_OP_STATUS_FAILURE,\n+\t/**< Operation completed with failure */\n+\tRTE_MULTI_FN_STATUS_INVALID_SESSION,\n+\t/**< Operation failed due to invalid session arguments */\n+};\n+\n+/**\n+ * Multi-function session\n+ */\n+struct rte_multi_fn_session;\n+\n+/**\n+ * Operation data\n+ */\n+struct rte_multi_fn_op {\n+\tstruct rte_multi_fn_op *next;\n+\t/**<\n+\t * Next operation in the chain\n+\t * - the last operation in the chain MUST set this to NULL\n+\t */\n+\tstruct rte_multi_fn_session *sess;\n+\t/**< Handle for the associated multi fn session */\n+\n+\tstruct rte_mempool *mempool;\n+\t/**< Mempool from which the operation is allocated */\n+\n+\tstruct rte_mbuf *m_src; /**< Source mbuf */\n+\tstruct rte_mbuf *m_dst; /**< Destination mbuf */\n+\n+\tenum rte_multi_fn_op_status overall_status;\n+\t/**<\n+\t * Overall operation status\n+\t * - indicates if all the operations in the chain succeeded or if any\n+\t *   one of them failed\n+\t */\n+\n+\tuint8_t op_status;\n+\t/**<\n+\t * Individual operation status\n+\t * - indicates the status of the individual operation in the chain\n+\t */\n+\n+\tRTE_STD_C11\n+\tunion {\n+\t\tstruct rte_crypto_sym_op crypto_sym;\n+\t\t/**< Symmetric crypto operation */\n+\t\tstruct rte_crypto_asym_op crypto_asym;\n+\t\t/**< Asymmetric crypto operation */\n+\t\tstruct rte_comp_op comp;\n+\t\t/**< Compression operation */\n+\t\tstruct rte_multi_fn_err_detect_op err_detect;\n+\t\t/**< Error detection operation */\n+\t};\n+};\n+\n+/**\n+ * Device information structure\n+ *\n+ * This structure is returned from rte_rawdev_info_get() with information\n+ * about the device\n+ */\n+struct rte_multi_fn_dev_info {\n+\tuint16_t max_nb_queues;\n+\t/**<\n+\t * Maximum number of queue pairs that can be configured on the\n+\t * device\n+\t */\n+};\n+\n+/**\n+ * Device configuration structure\n+ *\n+ * This structure should be passed to rte_rawdev_configure() to configure\n+ * a device\n+ */\n+struct rte_multi_fn_dev_config {\n+\tuint16_t nb_queues; /**< Number of queue pairs to configure */\n+\tunsigned int socket_id; /**< Socket to allocate queues on */\n+};\n+\n+/**\n+ * Queue pair configuration structure\n+ *\n+ * This should be passed to rte_rawdev_queue_setup() to configure a queue pair\n+ */\n+struct rte_multi_fn_qp_config {\n+\tuint32_t nb_descriptors; /**< Number of descriptors per queue pair */\n+};\n+\n+/**\n+ * Create multi-function session as specified by the transform chain\n+ *\n+ * @param   dev_id\tThe identifier of the device\n+ * @param   xform\tPointer to the first element of the session transform\n+ *\t\t\tchain\n+ * @param   socket_id\tSocket to allocate the session on\n+ *\n+ * @return\n+ *  - Pointer to session, if successful\n+ *  - NULL, on failure\n+ */\n+__rte_experimental\n+struct rte_multi_fn_session *\n+rte_multi_fn_session_create(uint16_t dev_id,\n+\t\t\t    struct rte_multi_fn_xform *xform,\n+\t\t\t    int socket_id);\n+\n+/**\n+ * Free memory associated with a multi-function session\n+ *\n+ * @param   dev_id\tThe identifier of the device\n+ * @param   sess\tMulti-function session to be freed\n+ *\n+ * @return\n+ *  - 0, if successful\n+ *  - -EINVAL, if session is NULL\n+ *  - -EBUSY, if not all session data has been freed\n+ */\n+__rte_experimental\n+int\n+rte_multi_fn_session_destroy(uint16_t dev_id,\n+\t\t\t     struct rte_multi_fn_session *sess);\n+\n+/**\n+ * Creates a multi-function operation pool\n+ *\n+ * @param   name\tPool name\n+ * @param   nb_elts\tNumber of elements in pool\n+ * @param   cache_size  Number of elements to cache on lcore, see\n+ *                      *rte_mempool_create* for further details about\n+ *                      cache size\n+ * @param   priv_size\tSize of private data to allocate with each\n+ *                      operation\n+ * @param   socket_id   Socket to allocate memory on\n+ *\n+ * @return\n+ *  - Pointer to mempool, if successful\n+ *  - NULL, on failure\n+ */\n+__rte_experimental\n+struct rte_mempool *\n+rte_multi_fn_op_pool_create(const char *name,\n+\t\t\t    uint32_t nb_elts,\n+\t\t\t    uint32_t cache_size,\n+\t\t\t    uint16_t priv_size,\n+\t\t\t    int socket_id);\n+\n+/**\n+ * Bulk allocate multi-function operations from a mempool with default\n+ * parameters set\n+ *\n+ * @param   mempool\tMulti-function operation mempool\n+ * @param   ops\t\tArray to place allocated multi-function operations\n+ * @param   nb_ops\tNumber of multi-function operations to allocate\n+ *\n+ * @returns\n+ * - nb_ops, if the number of operations requested were allocated\n+ * - 0, if the requested number of ops are not available. None are allocated in\n+ *   this case\n+ */\n+__rte_experimental\n+static inline unsigned\n+rte_multi_fn_op_bulk_alloc(struct rte_mempool *mempool,\n+\t\t\t   struct rte_multi_fn_op **ops,\n+\t\t\t   uint16_t nb_ops)\n+{\n+\tint i;\n+\n+\tif (rte_mempool_get_bulk(mempool, (void **)ops, nb_ops) == 0) {\n+\t\tfor (i = 0; i < nb_ops; i++)\n+\t\t\tops[i]->overall_status =\n+\t\t\t\tRTE_MULTI_FN_OP_STATUS_NOT_PROCESSED;\n+\n+\t\treturn nb_ops;\n+\t}\n+\n+\treturn 0;\n+}\n+\n+/**\n+ * Free multi-function operation back to it's mempool\n+ *\n+ * @param   op\t\tMulti-function operation\n+ */\n+__rte_experimental\n+static inline void\n+rte_multi_fn_op_free(struct rte_multi_fn_op *op)\n+{\n+\tif (op != NULL && op->mempool != NULL)\n+\t\trte_mempool_put(op->mempool, op);\n+}\n+\n+#ifdef __cplusplus\n+}\n+#endif\n+\n+#endif /* _RTE_MULTI_FN_H_ */\ndiff --git a/drivers/raw/common/multi_fn/rte_multi_fn_driver.h b/drivers/raw/common/multi_fn/rte_multi_fn_driver.h\nnew file mode 100644\nindex 000000000..7e1e57fa3\n--- /dev/null\n+++ b/drivers/raw/common/multi_fn/rte_multi_fn_driver.h\n@@ -0,0 +1,55 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2020 Intel Corporation.\n+ */\n+\n+#ifndef _RTE_MULTI_FN_DRIVER_H_\n+#define _RTE_MULTI_FN_DRIVER_H_\n+\n+#ifdef __cplusplus\n+extern \"C\" {\n+#endif\n+\n+#include <rte_compat.h>\n+#include <rte_common.h>\n+#include <rte_rawdev.h>\n+#include <rte_multi_fn.h>\n+\n+/**\n+ * Multi-function session\n+ */\n+struct rte_multi_fn_session {\n+\tvoid *sess_private_data;\n+};\n+\n+/**\n+ * Session create function pointer type\n+ */\n+typedef struct rte_multi_fn_session *(*multi_fn_session_create_t)(\n+\t\t\t\t\t\tstruct rte_rawdev *,\n+\t\t\t\t\t\tstruct rte_multi_fn_xform *,\n+\t\t\t\t\t\tint);\n+\n+/**\n+ * Session destroy function pointer type\n+ */\n+typedef int (*multi_fn_session_destroy_t)(struct rte_rawdev *,\n+\t\t\t\t\t  struct rte_multi_fn_session *);\n+\n+/**\n+ * Structure containing multi-function ops to create and destroy a session.\n+ *\n+ * This structure MUST be the first element of the device's private data\n+ * structure pointed to by rte_rawdev->dev_private\n+ */\n+struct rte_multi_fn_ops {\n+\tmulti_fn_session_create_t session_create;\n+\t/**< Create session function pointer */\n+\tmulti_fn_session_destroy_t session_destroy;\n+\t/**< Destroy session function pointer */\n+};\n+\n+#ifdef __cplusplus\n+}\n+#endif\n+\n+#endif /* _RTE_MULTI_FN_DRIVER_H_ */\ndiff --git a/meson.build b/meson.build\nindex d36580438..de952fa98 100644\n--- a/meson.build\n+++ b/meson.build\n@@ -102,6 +102,10 @@ message(output_message + '\\n')\n \n output_message = '\\n===============\\nDrivers Enabled\\n===============\\n'\n foreach class:dpdk_driver_classes\n+\tif class.contains('/')\n+\t\tclass_split = class.split('/')\n+\t\tclass = '_'.join(class_split)\n+\tendif\n \tclass_drivers = get_variable(class + '_drivers')\n \toutput_message += '\\n' + class + ':\\n\\t'\n \toutput_count = 0\ndiff --git a/mk/rte.app.mk b/mk/rte.app.mk\nindex d295ca0a5..b836d220d 100644\n--- a/mk/rte.app.mk\n+++ b/mk/rte.app.mk\n@@ -347,6 +347,7 @@ _LDLIBS-$(CONFIG_RTE_LIBRTE_PMD_IOAT_RAWDEV)   += -lrte_rawdev_ioat\n _LDLIBS-$(CONFIG_RTE_LIBRTE_PMD_NTB_RAWDEV) += -lrte_rawdev_ntb\n _LDLIBS-$(CONFIG_RTE_LIBRTE_PMD_OCTEONTX2_DMA_RAWDEV) += -lrte_rawdev_octeontx2_dma\n _LDLIBS-$(CONFIG_RTE_LIBRTE_PMD_OCTEONTX2_EP_RAWDEV) += -lrte_rawdev_octeontx2_ep\n+_LDLIBS-$(CONFIG_RTE_LIBRTE_MULTI_FN_COMMON) += -lrte_multi_fn\n endif # CONFIG_RTE_LIBRTE_RAWDEV\n \n endif # !CONFIG_RTE_BUILD_SHARED_LIBS\n",
    "prefixes": [
        "v2",
        "1/4"
    ]
}