get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

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

{
    "id": 58541,
    "url": "http://patches.dpdk.org/api/patches/58541/?format=api",
    "web_url": "http://patches.dpdk.org/project/dpdk/patch/e55e2ca864b8e02b0cc1596bf6a9efe93227da4f.1567529480.git.vladimir.medvedkin@intel.com/",
    "project": {
        "id": 1,
        "url": "http://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": "<e55e2ca864b8e02b0cc1596bf6a9efe93227da4f.1567529480.git.vladimir.medvedkin@intel.com>",
    "list_archive_url": "https://inbox.dpdk.org/dev/e55e2ca864b8e02b0cc1596bf6a9efe93227da4f.1567529480.git.vladimir.medvedkin@intel.com",
    "date": "2019-09-03T16:55:32",
    "name": "[v1,5/5] app: add test-sad application",
    "commit_ref": null,
    "pull_url": null,
    "state": "superseded",
    "archived": true,
    "hash": "2d1de5155d5dd1d49f888a056ec2f3ef76088666",
    "submitter": {
        "id": 1216,
        "url": "http://patches.dpdk.org/api/people/1216/?format=api",
        "name": "Vladimir Medvedkin",
        "email": "vladimir.medvedkin@intel.com"
    },
    "delegate": {
        "id": 6690,
        "url": "http://patches.dpdk.org/api/users/6690/?format=api",
        "username": "akhil",
        "first_name": "akhil",
        "last_name": "goyal",
        "email": "gakhil@marvell.com"
    },
    "mbox": "http://patches.dpdk.org/project/dpdk/patch/e55e2ca864b8e02b0cc1596bf6a9efe93227da4f.1567529480.git.vladimir.medvedkin@intel.com/mbox/",
    "series": [
        {
            "id": 6225,
            "url": "http://patches.dpdk.org/api/series/6225/?format=api",
            "web_url": "http://patches.dpdk.org/project/dpdk/list/?series=6225",
            "date": "2019-09-03T16:55:27",
            "name": "ipsec: add inbound SAD",
            "version": 1,
            "mbox": "http://patches.dpdk.org/series/6225/mbox/"
        }
    ],
    "comments": "http://patches.dpdk.org/api/patches/58541/comments/",
    "check": "fail",
    "checks": "http://patches.dpdk.org/api/patches/58541/checks/",
    "tags": {},
    "related": [],
    "headers": {
        "Return-Path": "<dev-bounces@dpdk.org>",
        "X-Original-To": "patchwork@dpdk.org",
        "Delivered-To": "patchwork@dpdk.org",
        "Received": [
            "from [92.243.14.124] (localhost [127.0.0.1])\n\tby dpdk.org (Postfix) with ESMTP id 353A71ECB5;\n\tTue,  3 Sep 2019 18:56:08 +0200 (CEST)",
            "from mga18.intel.com (mga18.intel.com [134.134.136.126])\n\tby dpdk.org (Postfix) with ESMTP id 8F0AD1EC0D\n\tfor <dev@dpdk.org>; Tue,  3 Sep 2019 18:55:56 +0200 (CEST)",
            "from fmsmga002.fm.intel.com ([10.253.24.26])\n\tby orsmga106.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384;\n\t03 Sep 2019 09:55:56 -0700",
            "from silpixa00400072.ir.intel.com ([10.237.222.213])\n\tby fmsmga002.fm.intel.com with ESMTP; 03 Sep 2019 09:55:54 -0700"
        ],
        "X-Amp-Result": "SKIPPED(no attachment in message)",
        "X-Amp-File-Uploaded": "False",
        "X-ExtLoop1": "1",
        "X-IronPort-AV": "E=Sophos;i=\"5.64,463,1559545200\"; d=\"scan'208\";a=\"212063968\"",
        "From": "Vladimir Medvedkin <vladimir.medvedkin@intel.com>",
        "To": "dev@dpdk.org",
        "Cc": "konstantin.ananyev@intel.com, bernard.iremonger@intel.com,\n\takhil.goyal@nxp.com",
        "Date": "Tue,  3 Sep 2019 17:55:32 +0100",
        "Message-Id": "<e55e2ca864b8e02b0cc1596bf6a9efe93227da4f.1567529480.git.vladimir.medvedkin@intel.com>",
        "X-Mailer": "git-send-email 2.7.4",
        "In-Reply-To": [
            "<cover.1567529480.git.vladimir.medvedkin@intel.com>",
            "<cover.1567529480.git.vladimir.medvedkin@intel.com>"
        ],
        "References": [
            "<cover.1567529480.git.vladimir.medvedkin@intel.com>",
            "<1565709186-273340-1-git-send-email-vladimir.medvedkin@intel.com>\n\t<cover.1567529480.git.vladimir.medvedkin@intel.com>"
        ],
        "Subject": "[dpdk-dev] [PATCH v1 5/5] app: add test-sad application",
        "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\t<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\t<mailto:dev-request@dpdk.org?subject=subscribe>",
        "Errors-To": "dev-bounces@dpdk.org",
        "Sender": "\"dev\" <dev-bounces@dpdk.org>"
    },
    "content": "Usage example and performance evaluation for the ipsec SAD library\n\nSigned-off-by: Vladimir Medvedkin <vladimir.medvedkin@intel.com>\n---\n app/Makefile             |   1 +\n app/meson.build          |   3 +-\n app/test-sad/Makefile    |  18 ++\n app/test-sad/main.c      | 420 +++++++++++++++++++++++++++++++++++++++++++++++\n app/test-sad/meson.build |   6 +\n 5 files changed, 447 insertions(+), 1 deletion(-)\n create mode 100644 app/test-sad/Makefile\n create mode 100644 app/test-sad/main.c\n create mode 100644 app/test-sad/meson.build",
    "diff": "diff --git a/app/Makefile b/app/Makefile\nindex 28acbce..db9d2d5 100644\n--- a/app/Makefile\n+++ b/app/Makefile\n@@ -10,6 +10,7 @@ DIRS-$(CONFIG_RTE_LIBRTE_PDUMP) += pdump\n DIRS-$(CONFIG_RTE_LIBRTE_ACL) += test-acl\n DIRS-$(CONFIG_RTE_LIBRTE_CMDLINE) += test-cmdline\n DIRS-$(CONFIG_RTE_LIBRTE_PIPELINE) += test-pipeline\n+DIRS-$(CONFIG_RTE_LIBRTE_IPSEC) += test-sad\n \n ifeq ($(CONFIG_RTE_LIBRTE_BBDEV),y)\n DIRS-$(CONFIG_RTE_TEST_BBDEV) += test-bbdev\ndiff --git a/app/meson.build b/app/meson.build\nindex b0e6afb..71109cc 100644\n--- a/app/meson.build\n+++ b/app/meson.build\n@@ -15,7 +15,8 @@ apps = [\n \t'test-crypto-perf',\n \t'test-eventdev',\n \t'test-pipeline',\n-\t'test-pmd']\n+\t'test-pmd',\n+\t'test-sad']\n \n # for BSD only\n lib_execinfo = cc.find_library('execinfo', required: false)\ndiff --git a/app/test-sad/Makefile b/app/test-sad/Makefile\nnew file mode 100644\nindex 0000000..9b35413\n--- /dev/null\n+++ b/app/test-sad/Makefile\n@@ -0,0 +1,18 @@\n+# SPDX-License-Identifier: BSD-3-Clause\n+# Copyright(c) 2010-2014 Intel Corporation\n+\n+include $(RTE_SDK)/mk/rte.vars.mk\n+\n+ifeq ($(CONFIG_RTE_LIBRTE_IPSEC),y)\n+\n+APP = testsad\n+\n+CFLAGS += $(WERROR_FLAGS)\n+CFLAGS += -DALLOW_EXPERIMENTAL_API\n+\n+# all source are stored in SRCS-y\n+SRCS-y := main.c\n+\n+include $(RTE_SDK)/mk/rte.app.mk\n+\n+endif\ndiff --git a/app/test-sad/main.c b/app/test-sad/main.c\nnew file mode 100644\nindex 0000000..039397f\n--- /dev/null\n+++ b/app/test-sad/main.c\n@@ -0,0 +1,420 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2019 Intel Corporation\n+ */\n+\n+#include <rte_string_fns.h>\n+#include <rte_ipsec_sad.h>\n+#include <getopt.h>\n+#include <string.h>\n+#include <stdio.h>\n+#include <sys/types.h>\n+#include <sys/socket.h>\n+#include <netinet/in.h>\n+#include <arpa/inet.h>\n+\n+#include <rte_cycles.h>\n+#include <rte_errno.h>\n+#include <rte_ip.h>\n+#include <rte_random.h>\n+#include <rte_malloc.h>\n+#include <rte_ipsec_sad.h>\n+\n+#define\tPRINT_USAGE_START\t\"%s [EAL options] --\\n\"\n+\n+#define GET_CB_FIELD(in, fd, base, lim, dlm)\tdo {\t\t\\\n+\tunsigned long val;\t\t\t\t\t\\\n+\tchar *end_fld;\t\t\t\t\t\t\\\n+\terrno = 0;\t\t\t\t\t\t\\\n+\tval = strtoul((in), &end_fld, (base));\t\t\t\\\n+\tif (errno != 0 || end_fld[0] != (dlm) || val > (lim))\t\\\n+\t\treturn -EINVAL;\t\t\t\t\t\\\n+\t(fd) = (typeof(fd))val;\t\t\t\t\t\\\n+\t(in) = end_fld + 1;\t\t\t\t\t\\\n+} while (0)\n+\n+#define\tDEF_RULE_NUM\t\t0x10000\n+#define\tDEF_TUPLES_NUM\t0x100000\n+\n+static struct {\n+\tconst char\t*prgname;\n+\tconst char\t*rules_file;\n+\tconst char\t*tuples_file;\n+\tuint32_t\tnb_rules;\n+\tuint32_t\tnb_tuples;\n+\tuint32_t\tnb_rules_32;\n+\tuint32_t\tnb_rules_64;\n+\tuint32_t\tnb_rules_96;\n+\tuint32_t\tnb_tuples_rnd;\n+\tuint8_t\t\tfract_32;\n+\tuint8_t\t\tfract_64;\n+\tuint8_t\t\tfract_96;\n+\tuint8_t\t\tfract_rnd_tuples;\n+} config = {\n+\t.rules_file = NULL,\n+\t.tuples_file = NULL,\n+\t.nb_rules = DEF_RULE_NUM,\n+\t.nb_tuples = DEF_TUPLES_NUM,\n+\t.nb_rules_32 = 0,\n+\t.nb_rules_64 = 0,\n+\t.nb_rules_96 = 0,\n+\t.nb_tuples_rnd = 0,\n+\t.fract_32 = 90,\n+\t.fract_64 = 9,\n+\t.fract_96 = 1,\n+\t.fract_rnd_tuples = 0\n+};\n+\n+enum {\n+\tCB_RULE_SPI,\n+\tCB_RULE_DIP,\n+\tCB_RULE_SIP,\n+\tCB_RULE_LEN,\n+\tCB_RULE_NUM,\n+};\n+\n+static char line[LINE_MAX];\n+struct rule {\n+\tstruct rte_ipsec_sadv4_key tuple;\n+\tint rule_type;\n+};\n+\n+static struct rule *rules_tbl;\n+static struct rule *tuples_tbl;\n+\n+static int\n+parse_distrib(const char *in)\n+{\n+\tint a, b, c;\n+\n+\tGET_CB_FIELD(in, a, 0, UINT8_MAX, '/');\n+\tGET_CB_FIELD(in, b, 0, UINT8_MAX, '/');\n+\tGET_CB_FIELD(in, c, 0, UINT8_MAX, 0);\n+\n+\tif ((a + b + c) != 100)\n+\t\treturn -EINVAL;\n+\n+\tconfig.fract_32 = a;\n+\tconfig.fract_64 = b;\n+\tconfig.fract_96 = c;\n+\n+\treturn 0;\n+}\n+\n+static void\n+print_config(void)\n+{\n+\tfprintf(stdout,\n+\t\t\"Rules total: %u\\n\"\n+\t\t\"Configured rules distribution SPI/SPI_DIP/SIP_DIP_SIP:\"\n+\t\t\"%u/%u/%u\\n\"\n+\t\t\"SPI only rules: %u\\n\"\n+\t\t\"SPI_DIP  rules: %u\\n\"\n+\t\t\"SPI_DIP_SIP rules: %u\\n\"\n+\t\t\"Lookup tuples: %u\\n\"\n+\t\t\"Configured fraction of random tuples: %u\\n\"\n+\t\t\"Random lookup tuples: %u\\n\",\n+\t\tconfig.nb_rules, config.fract_32, config.fract_64,\n+\t\tconfig.fract_96, config.nb_rules_32, config.nb_rules_64,\n+\t\tconfig.nb_rules_96, config.nb_tuples, config.fract_rnd_tuples,\n+\t\tconfig.nb_tuples_rnd);\n+}\n+\n+static void\n+print_usage(void)\n+{\n+\tfprintf(stdout,\n+\t\tPRINT_USAGE_START\n+\t\t\"[-f <rules file>]\\n\"\n+\t\t\"[-t <tuples file for lookup>]\\n\"\n+\t\t\"[-n <rules number (if -f is not specified)>]\\n\"\n+\t\t\"[-l <lookup tuples number (if -t is not specified)>]\\n\"\n+\t\t\"[-d <\\\"/\\\" separated rules length distribution\"\n+\t\t\"(if -f is not specified)>]\\n\"\n+\t\t\"[-r <random tuples fraction to lookup\"\n+\t\t\"(if -t is not specified)>]\\n\",\n+\t\tconfig.prgname);\n+\n+}\n+\n+static int\n+get_str_num(FILE *f, int num)\n+{\n+\tint n_lines = 0;\n+\n+\tif (f != NULL) {\n+\t\twhile (fgets(line, sizeof(line), f) != NULL)\n+\t\t\tn_lines++;\n+\t\trewind(f);\n+\t} else {\n+\t\tn_lines = num;\n+\t}\n+\treturn n_lines;\n+}\n+\n+static int\n+parse_file(FILE *f, struct rule *tbl, int rule_tbl)\n+{\n+\tint ret, i, j = 0;\n+\tchar *s, *sp, *in[CB_RULE_NUM];\n+\tstatic const char *dlm = \" \\t\\n\";\n+\tint string_tok_nb = RTE_DIM(in);\n+\n+\tstring_tok_nb -= (rule_tbl == 0) ? 1 : 0;\n+\twhile (fgets(line, sizeof(line), f) != NULL) {\n+\t\ts = line;\n+\t\tfor (i = 0; i != string_tok_nb; i++) {\n+\t\t\tin[i] = strtok_r(s, dlm, &sp);\n+\t\t\tif (in[i] == NULL)\n+\t\t\t\treturn -EINVAL;\n+\t\t\ts = NULL;\n+\t\t}\n+\t\tGET_CB_FIELD(in[CB_RULE_SPI], tbl[j].tuple.spi, 0,\n+\t\t\t\tUINT32_MAX, 0);\n+\n+\t\tret = inet_pton(AF_INET, in[CB_RULE_DIP], &tbl[j].tuple.dip);\n+\t\tif (ret != 1)\n+\t\t\treturn -EINVAL;\n+\t\tret = inet_pton(AF_INET, in[CB_RULE_SIP], &tbl[j].tuple.sip);\n+\t\tif (ret != 1)\n+\t\t\treturn -EINVAL;\n+\t\tif ((rule_tbl) && (in[CB_RULE_LEN] != NULL)) {\n+\t\t\tif (strcmp(in[CB_RULE_LEN], \"SPI_DIP_SIP\") == 0) {\n+\t\t\t\ttbl[j].rule_type = RTE_IPSEC_SAD_SPI_DIP_SIP;\n+\t\t\t\tconfig.nb_rules_96++;\n+\t\t\t} else if (strcmp(in[CB_RULE_LEN], \"SPI_DIP\") == 0) {\n+\t\t\t\ttbl[j].rule_type = RTE_IPSEC_SAD_SPI_DIP;\n+\t\t\t\tconfig.nb_rules_64++;\n+\t\t\t} else if (strcmp(in[CB_RULE_LEN], \"SPI\") == 0) {\n+\t\t\t\ttbl[j].rule_type = RTE_IPSEC_SAD_SPI_ONLY;\n+\t\t\t\tconfig.nb_rules_32++;\n+\t\t\t} else {\n+\t\t\t\treturn -EINVAL;\n+\t\t\t}\n+\t\t}\n+\t\tj++;\n+\t}\n+\treturn 0;\n+}\n+\n+static void\n+get_random_rules(struct rule *tbl, uint32_t nb_rules, int rule_tbl)\n+{\n+\tunsigned i, rnd;\n+\tint rule_type;\n+\n+\tfor (i = 0; i < nb_rules; i++) {\n+\t\trnd = rte_rand() % 100;\n+\t\tif (rule_tbl) {\n+\t\t\ttbl[i].tuple.spi = rte_rand();\n+\t\t\ttbl[i].tuple.dip = rte_rand();\n+\t\t\ttbl[i].tuple.sip = rte_rand();\n+\t\t\tif (rnd >= (100UL - config.fract_32)) {\n+\t\t\t\trule_type = RTE_IPSEC_SAD_SPI_ONLY;\n+\t\t\t\tconfig.nb_rules_32++;\n+\t\t\t} else if (rnd >= (100UL - (config.fract_32 +\n+\t\t\t\t\tconfig.fract_64))) {\n+\t\t\t\trule_type = RTE_IPSEC_SAD_SPI_DIP;\n+\t\t\t\tconfig.nb_rules_64++;\n+\t\t\t} else {\n+\t\t\t\trule_type = RTE_IPSEC_SAD_SPI_DIP_SIP;\n+\t\t\t\tconfig.nb_rules_96++;\n+\t\t\t}\n+\t\t\ttbl[i].rule_type = rule_type;\n+\t\t} else {\n+\t\t\tif (rnd >= 100UL - config.fract_rnd_tuples) {\n+\t\t\t\ttbl[i].tuple.spi = rte_rand();\n+\t\t\t\ttbl[i].tuple.dip = rte_rand();\n+\t\t\t\ttbl[i].tuple.sip = rte_rand();\n+\t\t\t\tconfig.nb_tuples_rnd++;\n+\t\t\t} else {\n+\t\t\t\ttbl[i].tuple.spi = rules_tbl[i %\n+\t\t\t\t\tconfig.nb_rules].tuple.spi;\n+\t\t\t\ttbl[i].tuple.dip = rules_tbl[i %\n+\t\t\t\t\tconfig.nb_rules].tuple.dip;\n+\t\t\t\ttbl[i].tuple.sip = rules_tbl[i %\n+\t\t\t\t\tconfig.nb_rules].tuple.sip;\n+\t\t\t}\n+\t\t}\n+\t}\n+}\n+\n+static void\n+tbl_init(struct rule **tbl, uint32_t *n_entries,\n+\tconst char *file_name, int rule_tbl)\n+{\n+\tFILE *f = NULL;\n+\tint ret;\n+\tconst char *rules = \"rules\";\n+\tconst char *tuples = \"tuples\";\n+\n+\tif (file_name != NULL) {\n+\t\tf = fopen(file_name, \"r\");\n+\t\tif (f == NULL)\n+\t\t\trte_exit(-EINVAL, \"failed to open file: %s\\n\",\n+\t\t\t\tfile_name);\n+\t}\n+\n+\tprintf(\"init %s table...\", (rule_tbl) ? rules : tuples);\n+\t*n_entries = get_str_num(f, *n_entries);\n+\tprintf(\"%d entries\\n\", *n_entries);\n+\t*tbl = rte_zmalloc(NULL, sizeof(struct rule) * *n_entries,\n+\t\tRTE_CACHE_LINE_SIZE);\n+\tif (*tbl == NULL)\n+\t\trte_exit(-ENOMEM, \"failed to allocate tbl\\n\");\n+\n+\tif (f != NULL) {\n+\t\tprintf(\"parse file %s\\n\", file_name);\n+\t\tret = parse_file(f, *tbl, rule_tbl);\n+\t\tif (ret != 0)\n+\t\t\trte_exit(-EINVAL, \"failed to parse file %s\\n\"\n+\t\t\t\t\"rules file must be: \"\n+\t\t\t\t\"<uint32_t: spi> <space> \"\n+\t\t\t\t\"<ip_addr: dip> <space> \"\n+\t\t\t\t\"<ip_addr: sip> <space> \"\n+\t\t\t\t\"<string: SPI|SPI_DIP|SIP_DIP_SIP>\\n\"\n+\t\t\t\t\"tuples file must be: \"\n+\t\t\t\t\"<uint32_t: spi> <space> \"\n+\t\t\t\t\"<ip_addr: dip> <space> \"\n+\t\t\t\t\"<ip_addr: sip>\\n\",\n+\t\t\t\tfile_name);\n+\t} else {\n+\t\tprintf(\"generate random values in %s table\\n\",\n+\t\t\t(rule_tbl) ? rules : tuples);\n+\t\tget_random_rules(*tbl, *n_entries, rule_tbl);\n+\t}\n+\tif (f != NULL)\n+\t\tfclose(f);\n+}\n+\n+static void\n+parse_opts(int argc, char **argv)\n+{\n+\tint opt, ret;\n+\tchar *endptr;\n+\n+\twhile ((opt = getopt(argc, argv, \"f:t:n:d:l:r:\")) != -1) {\n+\t\tswitch (opt) {\n+\t\tcase 'f':\n+\t\t\tconfig.rules_file = optarg;\n+\t\t\tbreak;\n+\t\tcase 't':\n+\t\t\tconfig.tuples_file = optarg;\n+\t\t\tbreak;\n+\t\tcase 'n':\n+\t\t\terrno = 0;\n+\t\t\tconfig.nb_rules = strtoul(optarg, &endptr, 10);\n+\t\t\tif ((errno != 0) || (config.nb_rules == 0)) {\n+\t\t\t\tprint_usage();\n+\t\t\t\trte_exit(-EINVAL, \"Invalid option -n\\n\");\n+\t\t\t}\n+\t\t\tbreak;\n+\t\tcase 'd':\n+\t\t\tret = parse_distrib(optarg);\n+\t\t\tif (ret != 0) {\n+\t\t\t\tprint_usage();\n+\t\t\t\trte_exit(-EINVAL, \"Invalid option -d\\n\");\n+\t\t\t}\n+\t\t\tbreak;\n+\t\tcase 'l':\n+\t\t\terrno = 0;\n+\t\t\tconfig.nb_tuples = strtoul(optarg, &endptr, 10);\n+\t\t\tif ((errno != 0) || (config.nb_tuples == 0)) {\n+\t\t\t\tprint_usage();\n+\t\t\t\trte_exit(-EINVAL, \"Invalid option -l\\n\");\n+\t\t\t}\n+\t\t\tbreak;\n+\t\tcase 'r':\n+\t\t\terrno = 0;\n+\t\t\tconfig.fract_rnd_tuples = strtoul(optarg, &endptr, 10);\n+\t\t\tif ((errno != 0) || (config.fract_rnd_tuples == 0) ||\n+\t\t\t\t\t(config.fract_rnd_tuples >= 100)) {\n+\t\t\t\tprint_usage();\n+\t\t\t\trte_exit(-EINVAL, \"Invalid option -r\\n\");\n+\t\t\t}\n+\t\t\tbreak;\n+\t\tdefault:\n+\t\t\tprint_usage();\n+\t\t\trte_exit(-EINVAL, \"Invalid options\\n\");\n+\t\t}\n+\t}\n+}\n+\n+#define BURST_SZ\t64\n+static void\n+lookup(struct rte_ipsec_sad *sad)\n+{\n+\tint ret, j;\n+\tunsigned i;\n+\tconst union rte_ipsec_sad_key *keys[BURST_SZ];\n+\tvoid *vals[BURST_SZ];\n+\tuint64_t start, acc = 0;\n+\n+\tfor (i = 0; i < config.nb_tuples; i += BURST_SZ) {\n+\t\tfor (j = 0; j < BURST_SZ; j++)\n+\t\t\tkeys[j] = (union rte_ipsec_sad_key *)\n+\t\t\t\t(&tuples_tbl[i + j].tuple);\n+\t\tstart = rte_rdtsc();\n+\t\tret = rte_ipsec_sad_lookup(sad, keys, BURST_SZ, vals);\n+\t\tacc += rte_rdtsc() - start;\n+\t\tif (ret < 0)\n+\t\t\trte_exit(-EINVAL, \"Lookup failed\\n\");\n+\t}\n+\tprintf(\"Average lookup cycles %lu\\n\", acc / config.nb_tuples);\n+}\n+\n+int\n+main(int argc, char **argv)\n+{\n+\tint ret;\n+\tunsigned i;\n+\tstruct rte_ipsec_sad *sad;\n+\tstruct rte_ipsec_sad_conf conf;\n+\tuint64_t start;\n+\n+\tret = rte_eal_init(argc, argv);\n+\tif (ret < 0)\n+\t\trte_panic(\"Cannot init EAL\\n\");\n+\n+\targc -= ret;\n+\targv += ret;\n+\n+\tconfig.prgname = argv[0];\n+\n+\tparse_opts(argc, argv);\n+\ttbl_init(&rules_tbl, &config.nb_rules, config.rules_file, 1);\n+\ttbl_init(&tuples_tbl, &config.nb_tuples, config.tuples_file, 0);\n+\tif (config.rules_file != NULL) {\n+\t\tconfig.fract_32 = (100 * config.nb_rules_32) / config.nb_rules;\n+\t\tconfig.fract_64 = (100 * config.nb_rules_64) / config.nb_rules;\n+\t\tconfig.fract_96 = (100 * config.nb_rules_96) / config.nb_rules;\n+\t}\n+\tif (config.tuples_file != NULL) {\n+\t\tconfig.fract_rnd_tuples = 0;\n+\t\tconfig.nb_tuples_rnd = 0;\n+\t}\n+\tconf.socket_id = -1;\n+\tconf.max_sa[RTE_IPSEC_SAD_SPI_ONLY] = config.nb_rules * 2;\n+\tconf.max_sa[RTE_IPSEC_SAD_SPI_DIP] = config.nb_rules * 2;\n+\tconf.max_sa[RTE_IPSEC_SAD_SPI_DIP_SIP] = config.nb_rules * 2;\n+\tconf.flags = RTE_IPSEC_SAD_FLAG_IPV4|RTE_IPSEC_SAD_FLAG_RW_CONCURRENCY;\n+\tsad = rte_ipsec_sad_create(\"test\", &conf);\n+\tif (sad == NULL)\n+\t\trte_exit(-rte_errno, \"can not allocate SAD table\\n\");\n+\n+\tprint_config();\n+\n+\tstart = rte_rdtsc();\n+\tfor (i = 0; i < config.nb_rules; i++) {\n+\t\tret = rte_ipsec_sad_add(sad,\n+\t\t\t(union rte_ipsec_sad_key *)&rules_tbl[i].tuple,\n+\t\t\trules_tbl[i].rule_type, &rules_tbl[i]);\n+\t\tif (ret != 0)\n+\t\t\trte_exit(ret, \"can not add rule to SAD table\\n\");\n+\t}\n+\tprintf(\"Average ADD cycles: %lu\\n\",\n+\t\t(rte_rdtsc() - start) / config.nb_rules);\n+\n+\tlookup(sad);\n+\n+\treturn 0;\n+}\ndiff --git a/app/test-sad/meson.build b/app/test-sad/meson.build\nnew file mode 100644\nindex 0000000..31f9aab\n--- /dev/null\n+++ b/app/test-sad/meson.build\n@@ -0,0 +1,6 @@\n+# SPDX-License-Identifier: BSD-3-Clause\n+# Copyright(c) 2019 Intel Corporation\n+\n+allow_experimental_apis = true\n+sources = files('main.c')\n+deps += ['ipsec', 'net']\n",
    "prefixes": [
        "v1",
        "5/5"
    ]
}