get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

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

{
    "id": 43817,
    "url": "http://patches.dpdk.org/api/patches/43817/?format=api",
    "web_url": "http://patches.dpdk.org/project/dpdk/patch/1535026093-101872-8-git-send-email-ciara.power@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": "<1535026093-101872-8-git-send-email-ciara.power@intel.com>",
    "list_archive_url": "https://inbox.dpdk.org/dev/1535026093-101872-8-git-send-email-ciara.power@intel.com",
    "date": "2018-08-23T12:08:09",
    "name": "[07/11] telemetry: add tests for telemetry api",
    "commit_ref": null,
    "pull_url": null,
    "state": "superseded",
    "archived": true,
    "hash": "ca67622a1fa1318ee03e205f35291fc7fb3f6c2e",
    "submitter": {
        "id": 978,
        "url": "http://patches.dpdk.org/api/people/978/?format=api",
        "name": "Power, Ciara",
        "email": "ciara.power@intel.com"
    },
    "delegate": {
        "id": 1,
        "url": "http://patches.dpdk.org/api/users/1/?format=api",
        "username": "tmonjalo",
        "first_name": "Thomas",
        "last_name": "Monjalon",
        "email": "thomas@monjalon.net"
    },
    "mbox": "http://patches.dpdk.org/project/dpdk/patch/1535026093-101872-8-git-send-email-ciara.power@intel.com/mbox/",
    "series": [
        {
            "id": 1038,
            "url": "http://patches.dpdk.org/api/series/1038/?format=api",
            "web_url": "http://patches.dpdk.org/project/dpdk/list/?series=1038",
            "date": "2018-08-23T12:08:02",
            "name": "introduce telemetry library",
            "version": 1,
            "mbox": "http://patches.dpdk.org/series/1038/mbox/"
        }
    ],
    "comments": "http://patches.dpdk.org/api/patches/43817/comments/",
    "check": "fail",
    "checks": "http://patches.dpdk.org/api/patches/43817/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 C50955681;\n\tThu, 23 Aug 2018 14:08:41 +0200 (CEST)",
            "from mga06.intel.com (mga06.intel.com [134.134.136.31])\n\tby dpdk.org (Postfix) with ESMTP id 4220A4CB5\n\tfor <dev@dpdk.org>; Thu, 23 Aug 2018 14:08:35 +0200 (CEST)",
            "from fmsmga005.fm.intel.com ([10.253.24.32])\n\tby orsmga104.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384;\n\t23 Aug 2018 05:08:34 -0700",
            "from silpixa00399503.ir.intel.com ([10.237.222.102])\n\tby fmsmga005.fm.intel.com with ESMTP; 23 Aug 2018 05:08:33 -0700"
        ],
        "X-Amp-Result": "SKIPPED(no attachment in message)",
        "X-Amp-File-Uploaded": "False",
        "X-ExtLoop1": "1",
        "X-IronPort-AV": "E=Sophos;i=\"5.53,278,1531810800\"; d=\"scan'208\";a=\"256613870\"",
        "From": "Ciara Power <ciara.power@intel.com>",
        "To": "harry.van.haaren@intel.com, brian.archbold@intel.com,\n\temma.kenny@intel.com, ciara.power@intel.com",
        "Cc": "dev@dpdk.org",
        "Date": "Thu, 23 Aug 2018 13:08:09 +0100",
        "Message-Id": "<1535026093-101872-8-git-send-email-ciara.power@intel.com>",
        "X-Mailer": "git-send-email 2.7.4",
        "In-Reply-To": "<1535026093-101872-1-git-send-email-ciara.power@intel.com>",
        "References": "<1535026093-101872-1-git-send-email-ciara.power@intel.com>",
        "Subject": "[dpdk-dev] [PATCH 07/11] telemetry: add tests for telemetry api",
        "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": "This patch adds all tests for the Telemetry API.\nThe tests added include a parser test, selftest, and socket\nmessaging tests.\n\nThe parser tests pass valid and invalid messages to the parser\nto ensure the correct return values are received.\nThe selftest tests basic functions in the Telemetry API such as\nregistering, unregistering, and initialisation.\nThe socket messaging tests pass messages through the socket and\nvalidates the return message, to ensure the Telemetry API is\nresponding correctly.\n\nSigned-off-by: Ciara Power <ciara.power@intel.com>\nSigned-off-by: Brian Archbold <brian.archbold@intel.com>\n---\n drivers/telemetry/telemetry/telemetry_driver.c    |   7 +\n lib/librte_telemetry/Makefile                     |   1 +\n lib/librte_telemetry/meson.build                  |   4 +-\n lib/librte_telemetry/rte_telemetry.c              | 616 +++++++++++++++++++++-\n lib/librte_telemetry/rte_telemetry.h              |  12 +\n lib/librte_telemetry/rte_telemetry_internal.h     |   3 +\n lib/librte_telemetry/rte_telemetry_parser_test.c  | 574 ++++++++++++++++++++\n lib/librte_telemetry/rte_telemetry_parser_test.h  |  39 ++\n lib/librte_telemetry/rte_telemetry_socket_tests.h |  36 ++\n lib/librte_telemetry/rte_telemetry_version.map    |   1 +\n 10 files changed, 1290 insertions(+), 3 deletions(-)\n create mode 100644 lib/librte_telemetry/rte_telemetry_parser_test.c\n create mode 100644 lib/librte_telemetry/rte_telemetry_parser_test.h\n create mode 100644 lib/librte_telemetry/rte_telemetry_socket_tests.h",
    "diff": "diff --git a/drivers/telemetry/telemetry/telemetry_driver.c b/drivers/telemetry/telemetry/telemetry_driver.c\nindex c56f60c..125a89c 100644\n--- a/drivers/telemetry/telemetry/telemetry_driver.c\n+++ b/drivers/telemetry/telemetry/telemetry_driver.c\n@@ -15,6 +15,13 @@ telemetry_probe(struct rte_vdev_device *vdev)\n \tint ret;\n \n \tRTE_SET_USED(vdev);\n+\tret = rte_telemetry_selftest();\n+\tif (ret < 0) {\n+\t\tprintf(\"Error - Selftest failed\\n\");\n+\t\treturn -1;\n+\t}\n+\tprintf(\"Success - Selftest passed\\n\");\n+\n \tret = rte_telemetry_init(rte_socket_id());\n \tif (ret < 0) {\n \t\tprintf(\"Error - Telemetry initialisation failed\\n\");\ndiff --git a/lib/librte_telemetry/Makefile b/lib/librte_telemetry/Makefile\nindex df8fdd9..d766c82 100644\n--- a/lib/librte_telemetry/Makefile\n+++ b/lib/librte_telemetry/Makefile\n@@ -20,6 +20,7 @@ LIBABIVER := 1\n # library source files\n SRCS-$(CONFIG_RTE_LIBRTE_TELEMETRY) := rte_telemetry.c\n SRCS-$(CONFIG_RTE_LIBRTE_TELEMETRY) += rte_telemetry_parser.c\n+SRCS-$(CONFIG_RTE_LIBRTE_TELEMETRY) += rte_telemetry_parser_test.c\n \n # export include files\n SYMLINK-$(CONFIG_RTE_LIBRTE_TELEMETRY)-include := rte_telemetry.h\ndiff --git a/lib/librte_telemetry/meson.build b/lib/librte_telemetry/meson.build\nindex 7450f96..57dd83d 100644\n--- a/lib/librte_telemetry/meson.build\n+++ b/lib/librte_telemetry/meson.build\n@@ -1,8 +1,8 @@\n # SPDX-License-Identifier: BSD-3-Clause\n # Copyright(c) 2018 Intel Corporation\n \n-sources = files('rte_telemetry.c', 'rte_telemetry_parser.c')\n-headers = files('rte_telemetry.h', 'rte_telemetry_internal.h', 'rte_telemetry_parser.h')\n+sources = files('rte_telemetry.c', 'rte_telemetry_parser.c', 'rte_telemetry_parser_test.c')\n+headers = files('rte_telemetry.h', 'rte_telemetry_internal.h', 'rte_telemetry_parser.h', 'rte_telemetry_parser_test.h')\n deps += ['metrics', 'ethdev']\n cflags += '-DALLOW_EXPERIMENTAL_API'\n jansson = cc.find_library('jansson', required: true)\ndiff --git a/lib/librte_telemetry/rte_telemetry.c b/lib/librte_telemetry/rte_telemetry.c\nindex ba04d3d..ecf644b 100644\n--- a/lib/librte_telemetry/rte_telemetry.c\n+++ b/lib/librte_telemetry/rte_telemetry.c\n@@ -16,16 +16,34 @@\n #include \"rte_telemetry.h\"\n #include \"rte_telemetry_internal.h\"\n #include \"rte_telemetry_parser.h\"\n+#include \"rte_telemetry_parser_test.h\"\n+#include \"rte_telemetry_socket_tests.h\"\n \n #define BUF_SIZE 1024\n #define ACTION_POST 1\n #define SLEEP_TIME 10\n \n #define DEFAULT_DPDK_PATH \"/var/run/.rte_telemetry\"\n+#define SELFTEST_VALID_CLIENT \"/var/run/valid_client\"\n+#define SELFTEST_INVALID_CLIENT \"/var/run/invalid_client\"\n+#define SOCKET_TEST_CLIENT_PATH \"/var/run/client\"\n \n const char *socket_path = DEFAULT_DPDK_PATH;\n static telemetry_impl *static_telemetry;\n \n+struct telemetry_message_test {\n+\tchar *test_name;\n+\tint (*test_func_ptr)(struct telemetry_impl *telemetry, int fd);\n+};\n+\n+struct json_data {\n+\tchar *status_code;\n+\tchar *data;\n+\tint port;\n+\tchar *stat_name;\n+\tint stat_value;\n+};\n+\n int32_t\n rte_telemetry_check_port_activity(int port_id)\n {\n@@ -634,7 +652,7 @@ rte_telemetry_reg_ethdev_to_metrics(uint16_t port_id)\n static int32_t\n rte_telemetry_initial_accept(struct telemetry_impl *telemetry)\n {\n-\tint pid;\n+\tint pid, ret;\n \n \tRTE_ETH_FOREACH_DEV(pid) {\n \t\ttelemetry->reg_index =\n@@ -648,6 +666,17 @@ rte_telemetry_initial_accept(struct telemetry_impl *telemetry)\n \t\treturn -1;\n \t}\n \ttelemetry->metrics_register_done = 1;\n+\tret = rte_telemetry_socket_messaging_testing(telemetry->reg_index,\n+\t\ttelemetry->server_fd);\n+\tif (ret < 0)\n+\t\treturn -1;\n+\n+\tret = rte_telemetry_parser_test(telemetry);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Parser Tests Failed\\n\");\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - All Parser Tests Passed\\n\");\n \n \treturn 0;\n }\n@@ -1108,6 +1137,591 @@ rte_telemetry_parse_client_message(struct telemetry_impl *telemetry, char *buf)\n \treturn -1;\n }\n \n+int32_t\n+rte_telemetry_dummy_client_socket(const char *valid_client_path)\n+{\n+\tint sockfd = socket(AF_UNIX, SOCK_STREAM, 0);\n+\tif (sockfd < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Test socket creation failure\\n\");\n+\t\treturn -1;\n+\t}\n+\tstruct sockaddr_un addr = {0};\n+\taddr.sun_family = AF_UNIX;\n+\tstrlcpy(addr.sun_path, valid_client_path, sizeof(addr.sun_path));\n+\tunlink(valid_client_path);\n+\n+\tif (bind(sockfd, (struct sockaddr *)&addr, sizeof(addr)) < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Test socket binding failure\\n\");\n+\t\treturn -1;\n+\t}\n+\tif (listen(sockfd, 1) < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Listen failure\\n\");\n+\t\treturn -1;\n+\t}\n+\treturn sockfd;\n+}\n+\n+int32_t\n+rte_telemetry_selftest(void)\n+{\n+\tconst char *invalid_client_path = SELFTEST_INVALID_CLIENT;\n+\tconst char *valid_client_path = SELFTEST_VALID_CLIENT;\n+\tint ret, sockfd;\n+\n+\tTELEMETRY_LOG_INFO(\"Selftest\\n\");\n+\n+\tret = rte_telemetry_init(rte_socket_id());\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Valid initialisation test\"\n+\t\t\t\" failed\\n\");\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Valid initialisation test passed\\n\");\n+\n+\tret = rte_telemetry_init(rte_socket_id());\n+\tif (ret != -EALREADY) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Invalid initialisation test \"\n+\t\t\t\"failed\\n\");\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Invalid initialisation test passed\\n\");\n+\n+\tret = rte_telemetry_unregister_client(static_telemetry,\n+\t\tinvalid_client_path);\n+\tif (ret != -EPERM) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Invalid unregister test failed\\n\");\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Invalid unregister test passed\\n\");\n+\n+\tsockfd = rte_telemetry_dummy_client_socket(valid_client_path);\n+\tif (sockfd < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Test socket creation failed\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tret = rte_telemetry_register_client(static_telemetry,\n+\t\tvalid_client_path);\n+\tif (ret != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Valid register test failed: %i\\n\",\n+\t\t\tret);\n+\t\treturn -1;\n+\t}\n+\taccept(sockfd, NULL, NULL);\n+\tTELEMETRY_LOG_INFO(\"Success - Valid register test passed\\n\");\n+\n+\tret = rte_telemetry_register_client(static_telemetry,\n+\t\tvalid_client_path);\n+\tif (ret != -EINVAL) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Invalid register test failed: %i\\n\",\n+\t\t\tret);\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Invalid register test passed\\n\");\n+\n+\tret = rte_telemetry_unregister_client(static_telemetry,\n+\t\tinvalid_client_path);\n+\tif (ret != -1) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Invalid unregister test failed: \"\n+\t\t\t\"%i\\n\", ret);\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Invalid unregister test passed\\n\");\n+\n+\tret = rte_telemetry_unregister_client(static_telemetry,\n+\t\tvalid_client_path);\n+\tif (ret != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Valid unregister test failed: %i\"\n+\t\t\t\"\\n\", ret);\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Valid unregister test passed\\n\");\n+\n+\tret = rte_telemetry_cleanup();\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - cleanup() test failed\\n\");\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Valid cleanup test passed\\n\");\n+\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_socket_messaging_testing(int index, int socket)\n+{\n+\tstruct telemetry_impl *telemetry = calloc(1, sizeof(telemetry_impl));\n+\tint fd, bad_send_fd, send_fd, bad_fd, bad_recv_fd, recv_fd, ret;\n+\n+\tif (!telemetry) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - could not initialize \"\n+\t\t\t\"Telemetry API\\n\");\n+\t\treturn -1;\n+\t}\n+\ttelemetry->server_fd = socket;\n+\ttelemetry->reg_index = index;\n+\tTELEMETRY_LOG_INFO(\"Beginning Telemetry socket message Selftest\\n\");\n+\trte_telemetry_socket_test_setup(telemetry, &send_fd, &recv_fd);\n+\tTELEMETRY_LOG_INFO(\"Register valid client test\\n\");\n+\n+\tret = rte_telemetry_socket_register_test(telemetry, &fd, send_fd,\n+\t\trecv_fd);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Register valid client test \"\n+\t\t\t\"failed!\\n\");\n+\t\tfree(telemetry);\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Register valid client test passed!\\n\");\n+\n+\tTELEMETRY_LOG_INFO(\"Register invalid/same client test\\n\");\n+\tret = rte_telemetry_socket_test_setup(telemetry, &bad_send_fd,\n+\t\t&bad_recv_fd);\n+\tret = rte_telemetry_socket_register_test(telemetry, &bad_fd,\n+\t\tbad_send_fd, bad_recv_fd);\n+\tif (!ret) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Register invalid/same client test \"\n+\t\t\t\"failed!\\n\");\n+\t\tfree(telemetry);\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - Register invalid/same client test \"\n+\t\t\"passed!\\n\");\n+\n+\tret = rte_telemetry_json_socket_message_test(telemetry, fd);\n+\tif (ret < 0) {\n+\t\tfree(telemetry);\n+\t\treturn -1;\n+\t}\n+\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_socket_register_test(struct telemetry_impl *telemetry, int *fd,\n+\tint send_fd, int recv_fd)\n+{\n+\tint ret;\n+\tchar good_req_string[BUF_SIZE];\n+\n+\tsnprintf(good_req_string, sizeof(good_req_string),\n+\t\"{\\\"action\\\":1,\\\"command\\\":\\\"clients\\\",\\\"data\\\":{\\\"client_path\\\"\"\n+\t\t\":\\\"%s\\\"}}\", SOCKET_TEST_CLIENT_PATH);\n+\n+\tlisten(recv_fd, 1);\n+\tret = send(send_fd, good_req_string, strlen(good_req_string), 0);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not send message over \"\n+\t\t\t\"socket\\n\");\n+\t\treturn -1;\n+\t}\n+\trte_telemetry_run(telemetry);\n+\tif (telemetry->register_fail_count != 0)\n+\t\treturn -1;\n+\t*fd = accept(recv_fd, NULL, NULL);\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_socket_test_setup(struct telemetry_impl *telemetry, int *send_fd,\n+\tint *recv_fd)\n+{\n+\tint ret;\n+\tconst char *client_path = SOCKET_TEST_CLIENT_PATH;\n+\t*send_fd = socket(AF_UNIX, SOCK_STREAM, 0);\n+\t*recv_fd = socket(AF_UNIX, SOCK_STREAM, 0);\n+\n+\tlisten(telemetry->server_fd, 5);\n+\tstruct sockaddr_un addr = {0};\n+\taddr.sun_family = AF_UNIX;\n+\tstrlcpy(addr.sun_path, socket_path, sizeof(addr.sun_path));\n+\tret = connect(*send_fd, (struct sockaddr *) &addr, sizeof(addr));\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - could not connect socket\\n\");\n+\t\treturn -1;\n+\t}\n+\ttelemetry->accept_fd = accept(telemetry->server_fd, NULL, NULL);\n+\n+\tstruct sockaddr_un addrs = {0};\n+\taddrs.sun_family = AF_UNIX;\n+\tstrlcpy(addrs.sun_path, client_path, sizeof(addrs.sun_path));\n+\tunlink(client_path);\n+\n+\tret = bind(*recv_fd, (struct sockaddr *)&addrs, sizeof(addrs));\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - could not bind socket\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\treturn 0;\n+}\n+\n+static int32_t\n+rte_telemetry_stat_parse(char *buf, struct json_data *json_data_struct)\n+{\n+\tjson_error_t error;\n+\tjson_t *root = json_loads(buf, 0, &error);\n+\tint arraylen, i;\n+\tjson_t *status, *dataArray, *port, *stats, *name, *value,\n+\t*dataArrayObj, *statsArrayObj;\n+\n+\tstats = NULL;\n+\tport = NULL;\n+\tname = NULL;\n+\n+\tif (buf == NULL) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - JSON message is NULL\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tif (!root) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not load JSON object from \"\n+\t\t\t\"data passed in : %s\\n\", error.text);\n+\t\treturn -EPERM;\n+\t} else if (!json_is_object(root)) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - JSON Request is not a JSON \"\n+\t\t\t\"object\\n\");\n+\t\tjson_decref(root);\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tstatus = json_object_get(root, \"status_code\");\n+\tif (!status) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Request does not have status \"\n+\t\t\t\"field\\n\");\n+\t\treturn -EINVAL;\n+\t} else if (!json_is_string(status)) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Status value is not a String\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tjson_data_struct->status_code = strdup(json_string_value(status));\n+\n+\tdataArray = json_object_get(root, \"data\");\n+\tif (!dataArray) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Request does not have data field\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\tarraylen = json_array_size(dataArray);\n+\tif (arraylen == 0) {\n+\t\tjson_data_struct->data = \"null\";\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tfor (i = 0; i < arraylen; i++) {\n+\t\tdataArrayObj = json_array_get(dataArray, i);\n+\t\tport = json_object_get(dataArrayObj, \"port\");\n+\t\tstats = json_object_get(dataArrayObj, \"stats\");\n+\t}\n+\n+\tif (!port) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Request does not have port field\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\tif (!json_is_integer(port)) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Port value is not an integer\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tjson_data_struct->port = json_integer_value(port);\n+\n+\tif (!stats) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Request does not have stats \"\n+\t\t\t\"field\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tarraylen = json_array_size(stats);\n+\tfor (i = 0; i < arraylen; i++) {\n+\t\tstatsArrayObj = json_array_get(stats, i);\n+\t\tname = json_object_get(statsArrayObj, \"name\");\n+\t\tvalue = json_object_get(statsArrayObj, \"value\");\n+\t}\n+\tif (!name) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Request does not have name field\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\tif (!json_is_string(name)) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Stat name value is not a string\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\tjson_data_struct->stat_name = strdup(json_string_value(name));\n+\n+\tif (!value) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Request does not have value \"\n+\t\t\t\"field\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\tif (!json_is_integer(value)) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Stat value is not an integer\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\tjson_data_struct->stat_value = json_integer_value(value);\n+\treturn 0;\n+}\n+\n+static void\n+rte_telemetry_free_test_data(struct json_data *data)\n+{\n+\tfree(data->status_code);\n+\tfree(data->stat_name);\n+\tfree(data);\n+}\n+\n+int32_t\n+rte_telemetry_valid_json_test(struct telemetry_impl *telemetry, int fd)\n+{\n+\tint ret;\n+\tchar buf[BUF_SIZE];\n+\tstruct json_data *data_struct;\n+\tconst char *status = \"Status OK: 200\";\n+\tint port = 0;\n+\tconst char *name = \"rx_good_packets\";\n+\tint value = 0;\n+\tint fail_count = 0;\n+\tconst char *valid_json_message = \"{\\\"action\\\":0,\\\"command\\\":\"\n+\t\"\\\"ports_stats_values_by_name\\\",\\\"data\\\":{\\\"ports\\\"\"\n+\t\":[0],\\\"stats\\\":[\\\"rx_good_packets\\\"]}}\";\n+\n+\tret = send(fd, valid_json_message, strlen(valid_json_message), 0);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not send message over \"\n+\t\t\t\"socket\\n\");\n+\t\treturn -1;\n+\t}\n+\trte_telemetry_run(telemetry);\n+\tint buffer_read = 0;\n+\terrno = 0;\n+\tbuffer_read = recv(fd, buf, BUF_SIZE-1, 0);\n+\n+\tif (buffer_read == -1) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Read error\\n\");\n+\t\treturn -1;\n+\t}\n+\tbuf[buffer_read] = '\\0';\n+\tdata_struct = calloc(1, sizeof(struct json_data));\n+\tret = rte_telemetry_stat_parse(buf, data_struct);\n+\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not parse stats\\n\");\n+\t\tfail_count++;\n+\t}\n+\n+\tif (strcmp(data_struct->status_code, status) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\" Error - Status code is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\tif (data_struct->port != port) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Port is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\tif (strcmp(data_struct->stat_name, name) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Stat name is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\tif (data_struct->stat_value != value) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Stat value is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\trte_telemetry_free_test_data(data_struct);\n+\tif (fail_count > 0)\n+\t\treturn -1;\n+\n+\t\tTELEMETRY_LOG_INFO(\"Success - Passed valid JSON message test \"\n+\t\t\t\"passed\\n\");\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_invalid_json_test(struct telemetry_impl *telemetry, int fd)\n+{\n+\tint ret;\n+\tchar buf[BUF_SIZE];\n+\tint fail_count = 0;\n+\tconst char *invalid_json = \"{]\";\n+\tconst char *status = \"Status Error: Unknown\";\n+\tconst char *data = \"null\";\n+\tstruct json_data *data_struct;\n+\tint buffer_read = 0;\n+\terrno = 0;\n+\n+\tret = send(fd, invalid_json, strlen(invalid_json), 0);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not send message over \"\n+\t\t\t\"socket\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\trte_telemetry_run(telemetry);\n+\tbuffer_read = recv(fd, buf, BUF_SIZE-1, 0);\n+\n+\tif (buffer_read == -1) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Read error\\n\");\n+\t\treturn -1;\n+\t}\n+\tbuf[buffer_read] = '\\0';\n+\n+\tdata_struct = calloc(1, sizeof(struct json_data));\n+\tret = rte_telemetry_stat_parse(buf, data_struct);\n+\n+\tif (ret < 0)\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not parse stats\\n\");\n+\n+\tif (strcmp(data_struct->status_code, status) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Status code is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\tif (strcmp(data_struct->data, data) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Data status is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\trte_telemetry_free_test_data(data_struct);\n+\tif (fail_count > 0)\n+\t\treturn -1;\n+\n+\tTELEMETRY_LOG_INFO(\"Success - Passed invalid JSON message test\\n\");\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_json_contents_test(struct telemetry_impl *telemetry, int fd)\n+{\n+\tint ret;\n+\tchar buf[BUF_SIZE];\n+\tint fail_count = 0;\n+\tchar *status = \"Status Error: Invalid Argument 404\";\n+\tchar *data = \"null\";\n+\tstruct json_data *data_struct;\n+\tconst char *invalid_contents = \"{\\\"action\\\":0,\\\"command\\\":\"\n+\t\"\\\"ports_stats_values_by_name\\\",\\\"data\\\":{\\\"ports\\\"\"\n+\t\":[0],\\\"stats\\\":[\\\"some_invalid_param\\\",\"\n+\t\"\\\"another_invalid_param\\\"]}}\";\n+\tint buffer_read = 0;\n+\terrno = 0;\n+\n+\tret = send(fd, invalid_contents, strlen(invalid_contents), 0);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not send message over \"\n+\t\t\t\"socket\\n\");\n+\t\treturn -1;\n+\t}\n+\trte_telemetry_run(telemetry);\n+\tbuffer_read = recv(fd, buf, BUF_SIZE-1, 0);\n+\tif (buffer_read == -1) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Read error\\n\");\n+\t\treturn -1;\n+\t}\n+\tbuf[buffer_read] = '\\0';\n+\tdata_struct = calloc(1, sizeof(struct json_data));\n+\tret = rte_telemetry_stat_parse(buf, data_struct);\n+\n+\tif (ret < 0)\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not parse stats\\n\");\n+\n+\tif (strcmp(data_struct->status_code, status) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Status code is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\tif (strcmp(data_struct->data, data) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Data status is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\trte_telemetry_free_test_data(data_struct);\n+\tif (fail_count > 0)\n+\t\treturn -1;\n+\n+\tTELEMETRY_LOG_INFO(\"Success - Passed invalid JSON content test\\n\");\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_json_empty_test(struct telemetry_impl *telemetry, int fd)\n+{\n+\tint ret;\n+\tchar buf[BUF_SIZE];\n+\tint fail_count = 0;\n+\tconst char *status = \"Status Error: Invalid Argument 404\";\n+\tchar *data = \"null\";\n+\tstruct json_data *data_struct;\n+\tconst char *empty_json  = \"{}\";\n+\tint buffer_read = 0;\n+\terrno = 0;\n+\n+\tret = (send(fd, empty_json, strlen(empty_json), 0));\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not send message over \"\n+\t\t\t\"socket\\n\");\n+\t\treturn -1;\n+\t}\n+\trte_telemetry_run(telemetry);\n+\tbuffer_read = recv(fd, buf, BUF_SIZE-1, 0);\n+\tif (buffer_read == -1) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Read error\\n\");\n+\t\treturn -1;\n+\t}\n+\tbuf[buffer_read] = '\\0';\n+\tdata_struct = calloc(1, sizeof(struct json_data));\n+\tret = rte_telemetry_stat_parse(buf, data_struct);\n+\n+\tif (ret < 0)\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not parse stats\\n\");\n+\n+\tif (strcmp(data_struct->status_code, status) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Status code is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\tif (strcmp(data_struct->data, data) != 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Data status is invalid\\n\");\n+\t\tfail_count++;\n+\t}\n+\trte_telemetry_free_test_data(data_struct);\n+\tif (fail_count > 0)\n+\t\treturn -1;\n+\n+\tTELEMETRY_LOG_INFO(\"Success - Passed JSON empty message test\\n\");\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_json_socket_message_test(struct telemetry_impl *telemetry, int fd)\n+{\n+\tuint16_t i;\n+\tint ret, fail_count;\n+\n+\tfail_count = 0;\n+\tstruct telemetry_message_test socket_json_tests[] = {\n+\t\t{.test_name = \"Invalid JSON test\",\n+\t\t\t.test_func_ptr = rte_telemetry_invalid_json_test},\n+\t\t{.test_name = \"Valid JSON test\",\n+\t\t\t.test_func_ptr = rte_telemetry_valid_json_test},\n+\t\t{.test_name = \"JSON contents test\",\n+\t\t\t.test_func_ptr = rte_telemetry_json_contents_test},\n+\t\t{.test_name = \"JSON empty tests\",\n+\t\t\t.test_func_ptr = rte_telemetry_json_empty_test}\n+\t\t};\n+\n+#define NUM_TESTS (sizeof(socket_json_tests)/sizeof(socket_json_tests[0]))\n+\n+\tfor (i = 0; i < NUM_TESTS; i++) {\n+\t\tTELEMETRY_LOG_INFO(\"%s\\n\",\n+\t\t\t socket_json_tests[i].test_name);\n+\t\tret = (socket_json_tests[i].test_func_ptr)\n+\t\t\t(telemetry, fd);\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - %s failed\\n\",\n+\t\t\t\t socket_json_tests[i].test_name);\n+\t\t\tfail_count++;\n+\t\t}\n+\t}\n+\tif (fail_count > 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Failed %i JSON socket message \"\n+\t\t\t\"test(s)\", fail_count);\n+\t\treturn -1;\n+\t}\n+\tTELEMETRY_LOG_INFO(\"Success - All JSON tests passed\\n\");\n+\treturn 0;\n+}\n+\n int telemetry_log_level;\n RTE_INIT(rte_telemetry_log_init);\n \ndiff --git a/lib/librte_telemetry/rte_telemetry.h b/lib/librte_telemetry/rte_telemetry.h\nindex b691845..4f187b7 100644\n--- a/lib/librte_telemetry/rte_telemetry.h\n+++ b/lib/librte_telemetry/rte_telemetry.h\n@@ -37,4 +37,16 @@ rte_telemetry_init(uint32_t socket_id);\n int32_t\n rte_telemetry_cleanup(void);\n \n+/**\n+ * Runs various tests to ensure telemetry initialisation and register/unregister\n+ * functions are working correctly.\n+ *\n+ * @return\n+ *  0 on success when all tests have passed\n+ * @return\n+ *  -1 on failure when the test has failed\n+ */\n+int32_t\n+rte_telemetry_selftest(void);\n+\n #endif\ndiff --git a/lib/librte_telemetry/rte_telemetry_internal.h b/lib/librte_telemetry/rte_telemetry_internal.h\nindex ef417f2..3e21b79 100644\n--- a/lib/librte_telemetry/rte_telemetry_internal.h\n+++ b/lib/librte_telemetry/rte_telemetry_internal.h\n@@ -65,4 +65,7 @@ int32_t\n rte_telemetry_send_ports_stats_values(uint32_t *metric_ids, int num_metric_ids,\n \tuint32_t *port_ids, int num_port_ids, struct telemetry_impl *telemetry);\n \n+int32_t\n+rte_telemetry_socket_messaging_testing(int index, int socket);\n+\n #endif\ndiff --git a/lib/librte_telemetry/rte_telemetry_parser_test.c b/lib/librte_telemetry/rte_telemetry_parser_test.c\nnew file mode 100644\nindex 0000000..4fa442d\n--- /dev/null\n+++ b/lib/librte_telemetry/rte_telemetry_parser_test.c\n@@ -0,0 +1,574 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2018 Intel Corporation\n+ */\n+\n+\n+#include <stdio.h>\n+#include <stdint.h>\n+#include <string.h>\n+#include <errno.h>\n+#include <jansson.h>\n+#include <sys/socket.h>\n+#include <sys/un.h>\n+#include <unistd.h>\n+\n+#include <rte_common.h>\n+#include <rte_tailq.h>\n+#include <rte_string_fns.h>\n+\n+#include \"rte_telemetry_parser.h\"\n+\n+#define ACTION_GET 0\n+#define ACTION_DELETE 2\n+\n+#define INV_ACTION_VAL 0\n+#define INV_COMMAND_VAL 1\n+#define INV_DATA_VAL 2\n+#define INV_ACTION_FIELD 3\n+#define INV_COMMAND_FIELD 4\n+#define INV_DATA_FIELD 5\n+#define INV_JSON_FORMAT 6\n+#define VALID_REQ 7\n+\n+\n+#define TEST_CLIENT \"/var/run/test_client\"\n+\n+int32_t\n+rte_telemetry_create_test_socket(struct telemetry_impl *telemetry,\n+\tconst char *test_client_path)\n+{\n+\n+\tint ret, sockfd;\n+\n+\tif (!telemetry) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Telemetry argument has not been \"\n+\t\t\t\"initialised\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tsockfd = socket(AF_UNIX, SOCK_STREAM, 0);\n+\tif (sockfd < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Test socket creation failure\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tstruct sockaddr_un addr = {0};\n+\taddr.sun_family = AF_UNIX;\n+\tstrlcpy(addr.sun_path, test_client_path, sizeof(addr.sun_path));\n+\tunlink(test_client_path);\n+\n+\tif (bind(sockfd, (struct sockaddr *)&addr, sizeof(addr)) < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Test socket binding failure\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tif (listen(sockfd, 1) < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Listen failure\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tret = rte_telemetry_register_client(telemetry, test_client_path);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Register dummy client failed: %i\",\n+\t\t\tret);\n+\t\treturn -1;\n+\t}\n+\n+\tret = accept(sockfd, NULL, NULL);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Socket accept failed\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tstruct telemetry_client *client;\n+\tTAILQ_FOREACH(client, &telemetry->client_list_head, client_list)\n+\t\ttelemetry->request_client = client;\n+\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_format_port_stat_ids(int *port_ids, int num_port_ids,\n+\tconst char * const *stat_names, int num_stat_names, json_t **data)\n+{\n+\n+\tint ret;\n+\tjson_t *stat_names_json_array = NULL;\n+\tjson_t *port_ids_json_array = NULL;\n+\tif (num_port_ids < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Port Ids Count invalid\\n\");\n+\t\tgoto fail;\n+\t}\n+\n+\t*data = json_object();\n+\tif (!*data) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Data json object creation failed\\n\");\n+\t\tgoto fail;\n+\t}\n+\n+\tport_ids_json_array = json_array();\n+\tif (!port_ids_json_array) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - port_ids_json_array creation \"\n+\t\t\t\"failed\\n\");\n+\t\tgoto fail;\n+\t}\n+\n+\tuint32_t i;\n+\tfor (i = 0; i < (uint32_t) num_port_ids; i++) {\n+\t\tret = json_array_append(port_ids_json_array,\n+\t\t\t json_integer(port_ids[i]));\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - JSON array creation \"\n+\t\t\t\t\"failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\t}\n+\n+\tret = json_object_set_new(*data, \"ports\", port_ids_json_array);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Setting 'ports' value in data object\"\n+\t\t\t\" failed\\n\");\n+\t\tgoto fail;\n+\t}\n+\n+\tif (stat_names) {\n+\n+\t\tif (num_stat_names < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Stat Names Count invalid\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\n+\t\tstat_names_json_array = json_array();\n+\t\tif (!stat_names_json_array) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - stat_names_json_array \"\n+\t\t\t\t\"creation failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\n+\t\tuint32_t i;\n+\t\tfor (i = 0; i < (uint32_t) num_stat_names; i++) {\n+\t\t\tret = json_array_append(stat_names_json_array,\n+\t\t\t\t json_string(stat_names[i]));\n+\t\t\tif (ret < 0) {\n+\t\t\t\tTELEMETRY_LOG_ERR(\"Error - JSON array creation \"\n+\t\t\t\t\t\" failed\\n\");\n+\t\t\t\tgoto fail;\n+\t\t\t}\n+\t\t}\n+\n+\t\tret = json_object_set_new(*data, \"stats\",\n+\t\t\tstat_names_json_array);\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting 'stats' value in \"\n+\t\t\t\t\"data object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\n+\t}\n+\treturn 0;\n+\n+fail:\n+\tif (*data)\n+\t\tjson_decref(*data);\n+\tif (stat_names_json_array)\n+\t\tjson_decref(stat_names_json_array);\n+\tif (port_ids_json_array)\n+\t\tjson_decref(port_ids_json_array);\n+\treturn -1;\n+}\n+\n+int32_t\n+rte_telemetry_create_json_request(int action, char *command,\n+\tconst char *client_path, int *port_ids, int num_port_ids,\n+\tconst char * const *stat_names, int num_stat_names, char **request,\n+\tint inv_choice)\n+{\n+\tint ret;\n+\tjson_t *root = json_object();\n+\n+\tif (!root) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not create root json \"\n+\t\t\t\"object\\n\");\n+\t\tgoto fail;\n+\t}\n+\n+\tif (inv_choice == INV_ACTION_FIELD) {\n+\t\tret = json_object_set_new(root, \"ac--on\", json_integer(action));\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting invalid action \"\n+\t\t\t\t\"field in root object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\t} else {\n+\t\tret = json_object_set_new(root, \"action\", json_integer(action));\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting valid action field \"\n+\t\t\t\t\"in root object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\t}\n+\n+\tif (inv_choice == INV_COMMAND_FIELD) {\n+\t\tret = json_object_set_new(root, \"co---nd\",\n+\t\t\tjson_string(command));\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting invalid command \"\n+\t\t\t\t\"field in root object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\t} else {\n+\t\tret = json_object_set_new(root, \"command\",\n+\t\t\tjson_string(command));\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting valid command \"\n+\t\t\t\t\"field in root object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\t}\n+\n+\tjson_t *data = json_null();\n+\tif (client_path) {\n+\t\tdata = json_object();\n+\t\tif (!data) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Data json object creation \"\n+\t\t\t\t\"failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\n+\t\tret = json_object_set_new(data, \"client_path\",\n+\t\t\t json_string(client_path));\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting valid client_path \"\n+\t\t\t\t\"field in data object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\n+\t} else if (port_ids) {\n+\t\tret = rte_telemetry_format_port_stat_ids(port_ids, num_port_ids,\n+\t\t stat_names, num_stat_names, &data);\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Formatting Port/Stat \"\n+\t\t\t\t\"arrays failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\n+\t}\n+\n+\tif (inv_choice == INV_DATA_FIELD) {\n+\t\tret = json_object_set_new(root, \"d--a\", data);\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting invalid data \"\n+\t\t\t\t\"field in data object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\t} else {\n+\t\tret = json_object_set_new(root, \"data\", data);\n+\t\tif (ret < 0) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Setting valid data field \"\n+\t\t\t\t\"in data object failed\\n\");\n+\t\t\tgoto fail;\n+\t\t}\n+\t}\n+\n+\t*request = json_dumps(root, 0);\n+\tif (!*request) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Converting JSON root object to \"\n+\t\t\t\"char* failed\\n\");\n+\t\tgoto fail;\n+\t}\n+\n+\tjson_decref(root);\n+\treturn 0;\n+\n+fail:\n+\tif (root)\n+\t\tjson_decref(root);\n+\treturn -1;\n+}\n+\n+int32_t\n+rte_telemetry_send_get_ports_and_stats_request(struct telemetry_impl *telemetry,\n+\tint action_choice, char *command_choice, int inv_choice)\n+{\n+\tint ret;\n+\tchar *request;\n+\n+\tif (!telemetry) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Telemetry argument has not been \"\n+\t\t\t\"initialised\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tchar *client_path_data = NULL;\n+\n+\tif (inv_choice == INV_ACTION_VAL)\n+\t\taction_choice = -1;\n+\telse if (inv_choice == INV_COMMAND_VAL)\n+\t\tcommand_choice = \"INVALID_COMMAND\";\n+\telse if (inv_choice == INV_DATA_VAL)\n+\t\tclient_path_data = \"INVALID_DATA\";\n+\n+\tret = rte_telemetry_create_json_request(action_choice, command_choice,\n+\tclient_path_data, NULL, -1, NULL, -1, &request, inv_choice);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not create JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tif (inv_choice == INV_JSON_FORMAT)\n+\t\trequest++;\n+\n+\tret = rte_telemetry_parse(telemetry, request);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_WARN(\"Warning - Could not parse JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_send_get_ports_details_request(struct telemetry_impl *telemetry,\n+\tint action_choice, int *port_ids, int num_port_ids, int inv_choice)\n+{\n+\tint ret;\n+\tchar *request;\n+\tif (!telemetry) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Telemetry argument has not been \"\n+\t\t\t\"initialised\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tchar *command = \"ports_details\";\n+\n+\tif (inv_choice == INV_ACTION_VAL)\n+\t\taction_choice = -1;\n+\telse if (inv_choice == INV_COMMAND_VAL)\n+\t\tcommand = \"INVALID_COMMAND\";\n+\telse if (inv_choice == INV_DATA_VAL)\n+\t\tport_ids = NULL;\n+\n+\n+\tret =  rte_telemetry_create_json_request(action_choice, command, NULL,\n+\t\tport_ids, num_port_ids, NULL, -1, &request, inv_choice);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not create JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tif (inv_choice == INV_JSON_FORMAT)\n+\t\trequest++;\n+\n+\tret = rte_telemetry_parse(telemetry, request);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_WARN(\"Warning - Could not parse JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_send_stats_values_by_name_request(struct telemetry_impl\n+\t*telemetry, int action_choice, int *port_ids, int num_port_ids,\n+\tconst char * const *stat_names, int num_stat_names,\n+\tint inv_choice)\n+{\n+\tint ret;\n+\tchar *request;\n+\n+\tif (!telemetry) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Telemetry argument has not been \"\n+\t\t\t\"initialised\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tchar *command = \"ports_stats_values_by_name\";\n+\n+\tif (inv_choice == INV_ACTION_VAL)\n+\t\taction_choice = -1;\n+\telse if (inv_choice == INV_COMMAND_VAL)\n+\t\tcommand = \"INVALID_COMMAND\";\n+\telse if (inv_choice == INV_DATA_VAL) {\n+\t\tport_ids = NULL;\n+\t\tstat_names = NULL;\n+\t}\n+\n+\n+\tret =  rte_telemetry_create_json_request(action_choice, command, NULL,\n+\t\tport_ids, num_port_ids, stat_names, num_stat_names,\n+\t\t&request, inv_choice);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not create JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tif (inv_choice == INV_JSON_FORMAT)\n+\t\trequest++;\n+\n+\tret = rte_telemetry_parse(telemetry, request);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_WARN(\"Warning - Could not parse JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_send_unreg_request(struct telemetry_impl *telemetry,\n+\tint action_choice, const char *client_path, int inv_choice)\n+{\n+\tint ret;\n+\tchar *request;\n+\n+\tif (!telemetry) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Telemetry argument has not been \"\n+\t\t\t\"initialised\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tchar *command = \"clients\";\n+\n+\tif (inv_choice == INV_ACTION_VAL)\n+\t\taction_choice = -1;\n+\telse if (inv_choice == INV_COMMAND_VAL)\n+\t\tcommand = \"INVALID_COMMAND\";\n+\telse if (inv_choice == INV_DATA_VAL)\n+\t\tclient_path = NULL;\n+\n+\tret = rte_telemetry_create_json_request(action_choice, command,\n+\t\tclient_path, NULL, -1, NULL, -1, &request, inv_choice);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not create JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tif (inv_choice == INV_JSON_FORMAT)\n+\t\trequest++;\n+\n+\tret = rte_telemetry_parse(telemetry, request);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_WARN(\"Warning - Could not parse JSON Request\\n\");\n+\t\treturn -1;\n+\t}\n+\treturn 0;\n+}\n+\n+int32_t\n+rte_telemetry_parser_test(struct telemetry_impl *telemetry)\n+{\n+\tint ret;\n+\n+\tif (!telemetry) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Telemetry argument has not been \"\n+\t\t\t\"initialised\\n\");\n+\t\treturn -EINVAL;\n+\t}\n+\n+\tconst char *client_path = TEST_CLIENT;\n+\tret = rte_telemetry_create_test_socket(telemetry, client_path);\n+\tif (ret < 0) {\n+\t\tTELEMETRY_LOG_ERR(\"Error - Could not create test request \"\n+\t\t\t\"client socket\\n\");\n+\t\treturn -1;\n+\t}\n+\n+\tint port_ids[] = {0, 1};\n+\tint num_port_ids = RTE_DIM(port_ids);\n+\n+\tstatic const char * const stat_names[] = {\"tx_good_packets\",\n+\t\t \"rx_good_packets\"};\n+\tint num_stat_names = RTE_DIM(stat_names);\n+\n+\tstatic const char * const test_types[] = {\n+\t\t\"INVALID ACTION VALUE TESTS\",\n+\t\t\"INVALID COMMAND VALUE TESTS\",\n+\t\t\"INVALID DATA VALUE TESTS\",\n+\t\t\"INVALID ACTION FIELD TESTS\",\n+\t\t\"INVALID COMMAND FIELD TESTS\",\n+\t\t\"INVALID DATA FIELD TESTS\",\n+\t\t\"INVALID JSON FORMAT TESTS\",\n+\t\t\"VALID TESTS\"\n+\t};\n+\n+\n+#define NUM_TEST_TYPES (sizeof(test_types)/sizeof(const char * const))\n+\n+\tuint32_t i;\n+\tfor (i = 0; i < NUM_TEST_TYPES; i++) {\n+\t\tTELEMETRY_LOG_INFO(\"%s\\n\",\n+\t\t\ttest_types[i]);\n+\n+\t\tret = rte_telemetry_send_get_ports_and_stats_request(telemetry,\n+\t\t\tACTION_GET, \"ports\", i);\n+\t\tif (ret != 0 && i == VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get ports valid test \"\n+\t\t\t\t\"failed\\n\");\n+\t\t\treturn -EPERM;\n+\t\t} else if (ret != -1 && i != VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get ports invalid test\"\n+\t\t\t\t\" failed\\n\");\n+\t\t\treturn -EPERM;\n+\t\t}\n+\n+\t\tTELEMETRY_LOG_INFO(\"Success - Get ports test passed\\n\");\n+\n+\t\tret = rte_telemetry_send_get_ports_details_request(telemetry,\n+\t\t\tACTION_GET, port_ids, num_port_ids, i);\n+\t\tif (ret != 0 && i == VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get ports details valid\\n\");\n+\t\t\treturn -EPERM;\n+\t\t} else if (ret != -1 && i != VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get ports details \"\n+\t\t\t\t\"invalid\\n\");\n+\t\t\treturn -EPERM;\n+\t\t}\n+\n+\t\tTELEMETRY_LOG_INFO(\"Success - Get ports details test passed\\n\");\n+\n+\t\tret = rte_telemetry_send_get_ports_and_stats_request(telemetry,\n+\t\t\tACTION_GET, \"port_stats\", i);\n+\t\tif (ret != 0  && i == VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get port stats valid \"\n+\t\t\t\t\"test\\n\");\n+\t\t\treturn -EPERM;\n+\t\t} else if (ret != -1 && i != VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get ports stats invalid\"\n+\t\t\t\t\" test failed\\n\");\n+\t\t\treturn -EPERM;\n+\t\t}\n+\n+\t\tTELEMETRY_LOG_INFO(\"Success - Get ports stats test passed\\n\");\n+\n+\t\tret = rte_telemetry_send_stats_values_by_name_request(telemetry,\n+\t\t\tACTION_GET, port_ids, num_port_ids,\n+\t\t\tstat_names, num_stat_names, i);\n+\t\tif (ret != 0 && i == VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get ports stats values by\"\n+\t\t\t\t\" name valid test failed\\n\");\n+\t\t\treturn -EPERM;\n+\t\t} else if (ret != -1 && i != VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Get ports stats values by\"\n+\t\t\t\t\" name invalid test failed\\n\");\n+\t\t\treturn -EPERM;\n+\t\t}\n+\n+\t\tTELEMETRY_LOG_INFO(\"Success - Get ports stats values by name\"\n+\t\t\t\" test passed\\n\");\n+\n+\t\tret = rte_telemetry_send_unreg_request(telemetry, ACTION_DELETE,\n+\t\t\tclient_path, i);\n+\t\tif (ret != 0 && i == VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Deregister valid test \"\n+\t\t\t\t\"failed\\n\");\n+\t\t\treturn -EPERM;\n+\t\t} else if (ret != -1 && i != VALID_REQ) {\n+\t\t\tTELEMETRY_LOG_ERR(\"Error - Deregister invalid test\"\n+\t\t\t\t\" failed\\n\");\n+\t\t\treturn -EPERM;\n+\t\t}\n+\n+\t\tTELEMETRY_LOG_INFO(\"Success - Deregister test passed\\n\");\n+\t}\n+\n+\treturn 0;\n+}\ndiff --git a/lib/librte_telemetry/rte_telemetry_parser_test.h b/lib/librte_telemetry/rte_telemetry_parser_test.h\nnew file mode 100644\nindex 0000000..6ada852\n--- /dev/null\n+++ b/lib/librte_telemetry/rte_telemetry_parser_test.h\n@@ -0,0 +1,39 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2018 Intel Corporation\n+ */\n+\n+#ifndef _RTE_TELEMETRY_PARSER_TEST_H_\n+#define _RTE_TELEMETRY_PARSER_TEST_H_\n+\n+int32_t\n+rte_telemetry_parser_test(struct telemetry_impl *telemetry);\n+\n+int32_t\n+rte_telemetry_format_port_stat_ids(int *port_ids, int num_port_ids,\n+\tconst char * const stat_names, int num_stat_names, json_t **data);\n+\n+int32_t\n+rte_telemetry_create_json_request(int action, char *command,\n+\tconst char *client_path, int *port_ids, int num_port_ids,\n+\tconst char * const stat_names, int num_stat_names, char **request,\n+\tint inv_choice);\n+\n+int32_t\n+rte_telemetry_send_get_ports_and_stats_request(struct telemetry_impl *telemetry,\n+\tint action_choice, char *command_choice, int inv_choice);\n+\n+int32_t\n+rte_telemetry_send_get_ports_details_request(struct telemetry_impl *telemetry,\n+\tint action_choice, int *port_ids, int num_port_ids, int inv_choice);\n+\n+int32_t\n+rte_telemetry_send_stats_values_by_name_request(struct telemetry_impl\n+\t*telemetry, int action_choice, int *port_ids, int num_port_ids,\n+\tconst char * const stat_names, int num_stat_names,\n+\tint inv_choice);\n+\n+int32_t\n+rte_telemetry_send_unreg_request(int action_choice, const char *client_path,\n+\tint inv_choice);\n+\n+#endif\ndiff --git a/lib/librte_telemetry/rte_telemetry_socket_tests.h b/lib/librte_telemetry/rte_telemetry_socket_tests.h\nnew file mode 100644\nindex 0000000..db9167c\n--- /dev/null\n+++ b/lib/librte_telemetry/rte_telemetry_socket_tests.h\n@@ -0,0 +1,36 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2018 Intel Corporation\n+ */\n+\n+#include <stdbool.h>\n+\n+#include \"rte_telemetry_internal.h\"\n+\n+#ifndef _RTE_TELEMETRY_SOCKET_TESTING_H_\n+#define _RTE_TELEMETRY_SOCKET_TESTING_H_\n+\n+int32_t\n+rte_telemetry_json_socket_message_test(struct telemetry_impl *telemetry,\n+\tint fd);\n+\n+int32_t\n+rte_telemetry_invalid_json_test(struct telemetry_impl *telemetry, int fd);\n+\n+int32_t\n+rte_telemetry_valid_json_test(struct telemetry_impl *telemetry, int fd);\n+\n+int32_t\n+rte_telemetry_json_contents_test(struct telemetry_impl *telemetry, int fd);\n+\n+int32_t\n+rte_telemetry_json_empty_test(struct telemetry_impl *telemetry, int fd);\n+\n+int32_t\n+rte_telemetry_socket_register_test(struct telemetry_impl *telemetry, int *fd,\n+\tint send_fd, int recv_fd);\n+\n+int32_t\n+rte_telemetry_socket_test_setup(struct telemetry_impl *telemetry, int *send_fd,\n+\tint *recv_fd);\n+\n+#endif\ndiff --git a/lib/librte_telemetry/rte_telemetry_version.map b/lib/librte_telemetry/rte_telemetry_version.map\nindex efd437d..5ce5680 100644\n--- a/lib/librte_telemetry/rte_telemetry_version.map\n+++ b/lib/librte_telemetry/rte_telemetry_version.map\n@@ -2,5 +2,6 @@ DPDK_18.05 {\n \tglobal:\n \n \trte_telemetry_init;\n+\trte_telemetry_selftest;\n \tlocal: *;\n };\n",
    "prefixes": [
        "07/11"
    ]
}