get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

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

{
    "id": 76899,
    "url": "http://patches.dpdk.org/api/patches/76899/?format=api",
    "web_url": "http://patches.dpdk.org/project/dpdk/patch/1599556475-27820-16-git-send-email-arybchenko@solarflare.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": "<1599556475-27820-16-git-send-email-arybchenko@solarflare.com>",
    "list_archive_url": "https://inbox.dpdk.org/dev/1599556475-27820-16-git-send-email-arybchenko@solarflare.com",
    "date": "2020-09-08T09:14:35",
    "name": "[14/14] net/sfc: move MCDI helpers to common driver",
    "commit_ref": null,
    "pull_url": null,
    "state": "superseded",
    "archived": true,
    "hash": "5ee5964a04ee0e14ba77c77cdabfc9a420773c66",
    "submitter": {
        "id": 607,
        "url": "http://patches.dpdk.org/api/people/607/?format=api",
        "name": "Andrew Rybchenko",
        "email": "arybchenko@solarflare.com"
    },
    "delegate": {
        "id": 319,
        "url": "http://patches.dpdk.org/api/users/319/?format=api",
        "username": "fyigit",
        "first_name": "Ferruh",
        "last_name": "Yigit",
        "email": "ferruh.yigit@amd.com"
    },
    "mbox": "http://patches.dpdk.org/project/dpdk/patch/1599556475-27820-16-git-send-email-arybchenko@solarflare.com/mbox/",
    "series": [
        {
            "id": 12014,
            "url": "http://patches.dpdk.org/api/series/12014/?format=api",
            "web_url": "http://patches.dpdk.org/project/dpdk/list/?series=12014",
            "date": "2020-09-08T09:14:20",
            "name": "net/sfc: factor out common driver library",
            "version": 1,
            "mbox": "http://patches.dpdk.org/series/12014/mbox/"
        }
    ],
    "comments": "http://patches.dpdk.org/api/patches/76899/comments/",
    "check": "warning",
    "checks": "http://patches.dpdk.org/api/patches/76899/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 6154EA04AA;\n\tTue,  8 Sep 2020 11:18:12 +0200 (CEST)",
            "from [92.243.14.124] (localhost [127.0.0.1])\n\tby dpdk.org (Postfix) with ESMTP id 4F8531C1BB;\n\tTue,  8 Sep 2020 11:16:11 +0200 (CEST)",
            "from dispatch1-us1.ppe-hosted.com (dispatch1-us1.ppe-hosted.com\n [67.231.154.164]) by dpdk.org (Postfix) with ESMTP id AD5F91C18E\n for <dev@dpdk.org>; Tue,  8 Sep 2020 11:16:06 +0200 (CEST)",
            "from mx1-us1.ppe-hosted.com (unknown [10.110.50.144])\n by dispatch1-us1.ppe-hosted.com (PPE Hosted ESMTP Server) with ESMTP id\n 589E1200C4 for <dev@dpdk.org>; Tue,  8 Sep 2020 09:16:06 +0000 (UTC)",
            "from us4-mdac16-61.at1.mdlocal (unknown [10.110.50.154])\n by mx1-us1.ppe-hosted.com (PPE Hosted ESMTP Server) with ESMTP id 36172800EC\n for <dev@dpdk.org>; Tue,  8 Sep 2020 09:16:06 +0000 (UTC)",
            "from mx1-us1.ppe-hosted.com (unknown [10.110.50.12])\n by mx1-us1.ppe-hosted.com (PPE Hosted ESMTP Server) with ESMTPS id AA3FA40136\n for <dev@dpdk.org>; Tue,  8 Sep 2020 09:14:57 +0000 (UTC)",
            "from webmail.solarflare.com (uk.solarflare.com [193.34.186.16])\n (using TLSv1.2 with cipher ECDHE-RSA-AES256-SHA384 (256/256 bits))\n (No client certificate requested)\n by mx1-us1.ppe-hosted.com (PPE Hosted ESMTP Server) with ESMTPS id 11BB240071\n for <dev@dpdk.org>; Tue,  8 Sep 2020 09:14:57 +0000 (UTC)",
            "from ukex01.SolarFlarecom.com (10.17.10.4) by\n ukex01.SolarFlarecom.com (10.17.10.4) with Microsoft SMTP Server (TLS) id\n 15.0.1497.2; Tue, 8 Sep 2020 10:14:50 +0100",
            "from opal.uk.solarflarecom.com (10.17.10.1) by\n ukex01.SolarFlarecom.com (10.17.10.4) with Microsoft SMTP Server id\n 15.0.1497.2 via Frontend Transport; Tue, 8 Sep 2020 10:14:50 +0100",
            "from ukv-loginhost.uk.solarflarecom.com\n (ukv-loginhost.uk.solarflarecom.com [10.17.10.39])\n by opal.uk.solarflarecom.com (8.13.8/8.13.8) with ESMTP id 0889En0T032447\n for <dev@dpdk.org>; Tue, 8 Sep 2020 10:14:49 +0100",
            "from ukv-loginhost.uk.solarflarecom.com (localhost [127.0.0.1])\n by ukv-loginhost.uk.solarflarecom.com (Postfix) with ESMTP id CFEC11613AB\n for <dev@dpdk.org>; Tue,  8 Sep 2020 10:14:49 +0100 (BST)"
        ],
        "X-Virus-Scanned": "Proofpoint Essentials engine",
        "From": "Andrew Rybchenko <arybchenko@solarflare.com>",
        "To": "<dev@dpdk.org>",
        "Date": "Tue, 8 Sep 2020 10:14:35 +0100",
        "Message-ID": "<1599556475-27820-16-git-send-email-arybchenko@solarflare.com>",
        "X-Mailer": "git-send-email 1.8.3.1",
        "In-Reply-To": "<1599556475-27820-1-git-send-email-arybchenko@solarflare.com>",
        "References": "<1599556475-27820-1-git-send-email-arybchenko@solarflare.com>",
        "MIME-Version": "1.0",
        "Content-Type": "text/plain",
        "X-TM-AS-Product-Ver": "SMEX-12.5.0.1300-8.6.1012-25652.003",
        "X-TM-AS-Result": "No-16.077800-8.000000-10",
        "X-TMASE-MatchedRID": "UYy6qaIgCawOunQLDaXUBP3HILfxLV/9aeMaKzvXUpnRmpwtWlELp9nf\n JrUSEbFDMdqMWOXDAJTgLc5WU85ONq0iin8P0KjVT7O/YHJhINDVy4hHC3/gyLZk7gsuflVKY6s\n q+xRPSkD2Jb4m2Gw+EyPIolTqysMKeDPho5Jw+XCgcOgSnZOzMactle1frZabfkiy7TTogYa7Jw\n D4pCENFJFbAbroydJRhrjkhjhEe6+v6XrOv9OTH5N65fjGjYMQdkP4mJNdW+x90pZYV0vx9XGEu\n Q+dMAabbXRjJgWvj8vFW4nueYtaI+mwWKp2/We3caD+wPaBYtZQdXu/xf76ueMO0ez+CNLSuqBE\n 5JB7VxGo/ZGHCqwNWFnJbES9mdxApIyEjDucfRU+NrfDUTEXxFF5adRR2Ej1dBaEtWosUzWbfnT\n Dz+a2OV3heIBNVDnDQkXFL6ugRxOfJKoJNVF/JPgAhuaFie7S9/x+2nQH35Ix7ZAwjnj1hqKkU0\n t47vZIdT86lTeOQqwnu+ManF2AdX1v/5buqFaOh4xZ8LCgzAxaNaxZBRbNWoNrxWMc29wLhmQTd\n IAaP8RuEaSUBN9mh7/nK9j4xFuhPIeX4ggjD6QAkh0TeBSwayWo4o4gXl+Q01c7LSleBSEuDhoR\n +qZH1x1wzDHVf16cyer92EreVsw3fzE3wKa/rKIBnfMCFBiCLPSJu5jov2bJeCU6fGMNn6PFjJE\n Fr+olwXCBO/GKkVqOhzOa6g8KrZRMZUCEHkRt",
        "X-TM-AS-User-Approved-Sender": "Yes",
        "X-TM-AS-User-Blocked-Sender": "No",
        "X-TMASE-Result": "10--16.077800-8.000000",
        "X-TMASE-Version": "SMEX-12.5.0.1300-8.6.1012-25652.003",
        "X-MDID": "1599556562-3mwQkE_6yi1d",
        "Subject": "[dpdk-dev] [PATCH 14/14] net/sfc: move MCDI helpers to common driver",
        "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": "These helper will be reused by other libefx consumers, e.g. vDPA\ndriver.\n\nSigned-off-by: Andrew Rybchenko <arybchenko@solarflare.com>\nReviewed-by: Andy Moreton <amoreton@xilinx.com>\n---\n drivers/common/sfc_efx/Makefile               |   1 +\n drivers/common/sfc_efx/meson.build            |   1 +\n .../sfc_efx/rte_common_sfc_efx_version.map    |   9 +-\n drivers/common/sfc_efx/sfc_efx_mcdi.c         | 343 ++++++++++++++++++\n .../sfc_efx/sfc_efx_mcdi.h}                   |  12 +-\n drivers/net/sfc/sfc.h                         |   3 +-\n drivers/net/sfc/sfc_mcdi.c                    | 333 +----------------\n 7 files changed, 360 insertions(+), 342 deletions(-)\n create mode 100644 drivers/common/sfc_efx/sfc_efx_mcdi.c\n rename drivers/{net/sfc/sfc_mcdi.h => common/sfc_efx/sfc_efx_mcdi.h} (81%)",
    "diff": "diff --git a/drivers/common/sfc_efx/Makefile b/drivers/common/sfc_efx/Makefile\nindex 0bd6a593e9..bcbb15e789 100644\n--- a/drivers/common/sfc_efx/Makefile\n+++ b/drivers/common/sfc_efx/Makefile\n@@ -58,6 +58,7 @@ EXPORT_MAP := rte_common_sfc_efx_version.map\n #\n \n SRCS-y += sfc_efx.c\n+SRCS-y += sfc_efx_mcdi.c\n \n VPATH += $(SRCDIR)/base\n \ndiff --git a/drivers/common/sfc_efx/meson.build b/drivers/common/sfc_efx/meson.build\nindex 8fab4df792..b7a0763a34 100644\n--- a/drivers/common/sfc_efx/meson.build\n+++ b/drivers/common/sfc_efx/meson.build\n@@ -34,6 +34,7 @@ objs = [base_objs]\n \n sources = files(\n \t'sfc_efx.c',\n+\t'sfc_efx_mcdi.c',\n )\n \n includes += include_directories('base')\ndiff --git a/drivers/common/sfc_efx/rte_common_sfc_efx_version.map b/drivers/common/sfc_efx/rte_common_sfc_efx_version.map\nindex 0c719e8250..8c010c90ac 100644\n--- a/drivers/common/sfc_efx/rte_common_sfc_efx_version.map\n+++ b/drivers/common/sfc_efx/rte_common_sfc_efx_version.map\n@@ -47,13 +47,7 @@ DPDK_21 {\n \tefx_mac_stats_update;\n \tefx_mac_stats_upload;\n \n-\tefx_mcdi_fini;\n-\tefx_mcdi_get_proxy_handle;\n-\tefx_mcdi_init;\n \tefx_mcdi_new_epoch;\n-\tefx_mcdi_request_abort;\n-\tefx_mcdi_request_poll;\n-\tefx_mcdi_request_start;\n \n \tefx_nic_cfg_get;\n \tefx_nic_create;\n@@ -118,5 +112,8 @@ DPDK_21 {\n \tefx_tx_qpush;\n \tefx_txq_size;\n \n+\tsfc_efx_mcdi_init;\n+\tsfc_efx_mcdi_fini;\n+\n \tlocal: *;\n };\ndiff --git a/drivers/common/sfc_efx/sfc_efx_mcdi.c b/drivers/common/sfc_efx/sfc_efx_mcdi.c\nnew file mode 100644\nindex 0000000000..7eb565bbd6\n--- /dev/null\n+++ b/drivers/common/sfc_efx/sfc_efx_mcdi.c\n@@ -0,0 +1,343 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ *\n+ * Copyright(c) 2019-2020 Xilinx, Inc.\n+ * Copyright(c) 2016-2019 Solarflare Communications Inc.\n+ *\n+ * This software was jointly developed between OKTET Labs (under contract\n+ * for Solarflare) and Solarflare Communications, Inc.\n+ */\n+\n+#include <rte_cycles.h>\n+\n+#include \"efx.h\"\n+#include \"efx_mcdi.h\"\n+#include \"efx_regs_mcdi.h\"\n+\n+#include \"sfc_efx_mcdi.h\"\n+#include \"sfc_efx_debug.h\"\n+\n+#define SFC_EFX_MCDI_POLL_INTERVAL_MIN_US\t10\t\t/* 10us */\n+#define SFC_EFX_MCDI_POLL_INTERVAL_MAX_US\t(US_PER_S / 10)\t/* 100ms */\n+#define SFC_EFX_MCDI_WATCHDOG_INTERVAL_US\t(10 * US_PER_S)\t/* 10s */\n+\n+#define sfc_efx_mcdi_log(mcdi, level, ...) \\\n+\tdo {\t\t\t\t\t\t\t\t\\\n+\t\tconst struct sfc_efx_mcdi *_mcdi = (mcdi);\t\t\\\n+\t\t\t\t\t\t\t\t\t\\\n+\t\trte_log(level, _mcdi->logtype,\t\t\t\t\\\n+\t\t\tRTE_FMT(\"%s\" RTE_FMT_HEAD(__VA_ARGS__ ,) \"\\n\",\t\\\n+\t\t\t\t_mcdi->log_prefix,\t\t\t\\\n+\t\t\t\tRTE_FMT_TAIL(__VA_ARGS__,)));\t\t\\\n+\t} while (0)\n+\n+#define sfc_efx_mcdi_crit(mcdi, ...) \\\n+\tsfc_efx_mcdi_log(mcdi, RTE_LOG_CRIT, __VA_ARGS__)\n+\n+#define sfc_efx_mcdi_err(mcdi, ...) \\\n+\tsfc_efx_mcdi_log(mcdi, RTE_LOG_ERR, __VA_ARGS__)\n+\n+#define sfc_efx_mcdi_warn(mcdi, ...) \\\n+\tsfc_efx_mcdi_log(mcdi, RTE_LOG_WARNING, __VA_ARGS__)\n+\n+#define sfc_efx_mcdi_info(mcdi, ...) \\\n+\tsfc_efx_mcdi_log(mcdi, RTE_LOG_INFO, __VA_ARGS__)\n+\n+/** Level value used by MCDI log statements */\n+#define SFC_EFX_LOG_LEVEL_MCDI\tRTE_LOG_INFO\n+\n+#define sfc_efx_log_mcdi(mcdi, ...) \\\n+\tsfc_efx_mcdi_log(mcdi, SFC_EFX_LOG_LEVEL_MCDI, __VA_ARGS__)\n+\n+static void\n+sfc_efx_mcdi_timeout(struct sfc_efx_mcdi *mcdi)\n+{\n+\tsfc_efx_mcdi_warn(mcdi, \"MC TIMEOUT\");\n+\n+\tsfc_efx_mcdi_crit(mcdi, \"MCDI timeout handling is not implemented\");\n+\tsfc_efx_mcdi_crit(mcdi, \"NIC is unusable\");\n+\tmcdi->state = SFC_EFX_MCDI_DEAD;\n+}\n+\n+static inline boolean_t\n+sfc_efx_mcdi_proxy_event_available(struct sfc_efx_mcdi *mcdi)\n+{\n+\tmcdi->proxy_handle = 0;\n+\tmcdi->proxy_result = ETIMEDOUT;\n+\tmcdi->ops->mgmt_evq_poll(mcdi->ops_cookie);\n+\tif (mcdi->proxy_result != ETIMEDOUT)\n+\t\treturn B_TRUE;\n+\n+\treturn B_FALSE;\n+}\n+\n+static void\n+sfc_efx_mcdi_poll(struct sfc_efx_mcdi *mcdi, boolean_t proxy)\n+{\n+\tefx_nic_t *enp;\n+\tunsigned int delay_total;\n+\tunsigned int delay_us;\n+\tboolean_t aborted __rte_unused;\n+\n+\tdelay_total = 0;\n+\tdelay_us = SFC_EFX_MCDI_POLL_INTERVAL_MIN_US;\n+\tenp = mcdi->nic;\n+\n+\tdo {\n+\t\tboolean_t poll_completed;\n+\n+\t\tpoll_completed = (proxy) ?\n+\t\t\t\tsfc_efx_mcdi_proxy_event_available(mcdi) :\n+\t\t\t\tefx_mcdi_request_poll(enp);\n+\t\tif (poll_completed)\n+\t\t\treturn;\n+\n+\t\tif (delay_total > SFC_EFX_MCDI_WATCHDOG_INTERVAL_US) {\n+\t\t\tif (!proxy) {\n+\t\t\t\taborted = efx_mcdi_request_abort(enp);\n+\t\t\t\tSFC_EFX_ASSERT(aborted);\n+\t\t\t\tsfc_efx_mcdi_timeout(mcdi);\n+\t\t\t}\n+\n+\t\t\treturn;\n+\t\t}\n+\n+\t\trte_delay_us(delay_us);\n+\n+\t\tdelay_total += delay_us;\n+\n+\t\t/* Exponentially back off the poll frequency */\n+\t\tRTE_BUILD_BUG_ON(SFC_EFX_MCDI_POLL_INTERVAL_MAX_US >\n+\t\t\t\t UINT_MAX / 2);\n+\t\tdelay_us *= 2;\n+\t\tif (delay_us > SFC_EFX_MCDI_POLL_INTERVAL_MAX_US)\n+\t\t\tdelay_us = SFC_EFX_MCDI_POLL_INTERVAL_MAX_US;\n+\n+\t} while (1);\n+}\n+\n+static void\n+sfc_efx_mcdi_execute(void *arg, efx_mcdi_req_t *emrp)\n+{\n+\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n+\tuint32_t proxy_handle;\n+\n+\tif (mcdi->state == SFC_EFX_MCDI_DEAD) {\n+\t\temrp->emr_rc = ENOEXEC;\n+\t\treturn;\n+\t}\n+\n+\trte_spinlock_lock(&mcdi->lock);\n+\n+\tSFC_EFX_ASSERT(mcdi->state == SFC_EFX_MCDI_INITIALIZED);\n+\n+\tefx_mcdi_request_start(mcdi->nic, emrp, B_FALSE);\n+\tsfc_efx_mcdi_poll(mcdi, B_FALSE);\n+\n+\tif (efx_mcdi_get_proxy_handle(mcdi->nic, emrp, &proxy_handle) == 0) {\n+\t\t/*\n+\t\t * Authorization is required for the MCDI request;\n+\t\t * wait for an MCDI proxy response event to bring\n+\t\t * a non-zero proxy handle (should be the same as\n+\t\t * the value obtained above) and operation status\n+\t\t */\n+\t\tsfc_efx_mcdi_poll(mcdi, B_TRUE);\n+\n+\t\tif ((mcdi->proxy_handle != 0) &&\n+\t\t    (mcdi->proxy_handle != proxy_handle)) {\n+\t\t\tsfc_efx_mcdi_err(mcdi, \"Unexpected MCDI proxy event\");\n+\t\t\temrp->emr_rc = EFAULT;\n+\t\t} else if (mcdi->proxy_result == 0) {\n+\t\t\t/*\n+\t\t\t * Authorization succeeded; re-issue the original\n+\t\t\t * request and poll for an ordinary MCDI response\n+\t\t\t */\n+\t\t\tefx_mcdi_request_start(mcdi->nic, emrp, B_FALSE);\n+\t\t\tsfc_efx_mcdi_poll(mcdi, B_FALSE);\n+\t\t} else {\n+\t\t\temrp->emr_rc = mcdi->proxy_result;\n+\t\t\tsfc_efx_mcdi_err(mcdi,\n+\t\t\t\t\"MCDI proxy authorization failed (handle=%08x, result=%d)\",\n+\t\t\t\tproxy_handle, mcdi->proxy_result);\n+\t\t}\n+\t}\n+\n+\trte_spinlock_unlock(&mcdi->lock);\n+}\n+\n+static void\n+sfc_efx_mcdi_ev_cpl(void *arg)\n+{\n+\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n+\n+\tRTE_SET_USED(mcdi);\n+\tSFC_EFX_ASSERT(mcdi->state == SFC_EFX_MCDI_INITIALIZED);\n+\n+\t/* MCDI is polled, completions are not expected */\n+\tSFC_EFX_ASSERT(0);\n+}\n+\n+static void\n+sfc_efx_mcdi_exception(void *arg, efx_mcdi_exception_t eme)\n+{\n+\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n+\n+\tsfc_efx_mcdi_warn(mcdi, \"MC %s\",\n+\t    (eme == EFX_MCDI_EXCEPTION_MC_REBOOT) ? \"REBOOT\" :\n+\t    (eme == EFX_MCDI_EXCEPTION_MC_BADASSERT) ? \"BADASSERT\" : \"UNKNOWN\");\n+\n+\tmcdi->ops->sched_restart(mcdi->ops_cookie);\n+}\n+\n+#define SFC_MCDI_LOG_BUF_SIZE\t128\n+\n+static size_t\n+sfc_efx_mcdi_do_log(const struct sfc_efx_mcdi *mcdi,\n+\t\tchar *buffer, void *data, size_t data_size,\n+\t\tsize_t pfxsize, size_t position)\n+{\n+\tuint32_t *words = data;\n+\t/* Space separator plus 2 characters per byte */\n+\tconst size_t word_str_space = 1 + 2 * sizeof(*words);\n+\tsize_t i;\n+\n+\tfor (i = 0; i < data_size; i += sizeof(*words)) {\n+\t\tif (position + word_str_space >=\n+\t\t    SFC_MCDI_LOG_BUF_SIZE) {\n+\t\t\t/* Flush at SFC_MCDI_LOG_BUF_SIZE with backslash\n+\t\t\t * at the end which is required by netlogdecode.\n+\t\t\t */\n+\t\t\tbuffer[position] = '\\0';\n+\t\t\tsfc_efx_log_mcdi(mcdi, \"%s \\\\\", buffer);\n+\t\t\t/* Preserve prefix for the next log message */\n+\t\t\tposition = pfxsize;\n+\t\t}\n+\t\tposition += snprintf(buffer + position,\n+\t\t\t\t     SFC_MCDI_LOG_BUF_SIZE - position,\n+\t\t\t\t     \" %08x\", *words);\n+\t\twords++;\n+\t}\n+\treturn position;\n+}\n+\n+static void\n+sfc_efx_mcdi_logger(void *arg, efx_log_msg_t type,\n+\t\tvoid *header, size_t header_size,\n+\t\tvoid *data, size_t data_size)\n+{\n+\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n+\tchar buffer[SFC_MCDI_LOG_BUF_SIZE];\n+\tsize_t pfxsize;\n+\tsize_t start;\n+\n+\t/*\n+\t * Unlike the other cases, MCDI logging implies more onerous work\n+\t * needed to produce a message. If the dynamic log level prevents\n+\t * the end result from being printed, the CPU time will be wasted.\n+\t *\n+\t * To avoid wasting time, the actual level is examined in advance.\n+\t */\n+\tif (rte_log_get_level(mcdi->logtype) < (int)SFC_EFX_LOG_LEVEL_MCDI)\n+\t\treturn;\n+\n+\t/* The format including prefix added by sfc_efx_log_mcdi() is the\n+\t * format consumed by the Solarflare netlogdecode tool.\n+\t */\n+\tpfxsize = snprintf(buffer, sizeof(buffer), \"MCDI RPC %s:\",\n+\t\t\t   type == EFX_LOG_MCDI_REQUEST ? \"REQ\" :\n+\t\t\t   type == EFX_LOG_MCDI_RESPONSE ? \"RESP\" : \"???\");\n+\tstart = sfc_efx_mcdi_do_log(mcdi, buffer, header, header_size,\n+\t\t\t\t    pfxsize, pfxsize);\n+\tstart = sfc_efx_mcdi_do_log(mcdi, buffer, data, data_size,\n+\t\t\t\t    pfxsize, start);\n+\tif (start != pfxsize) {\n+\t\tbuffer[start] = '\\0';\n+\t\tsfc_efx_log_mcdi(mcdi, \"%s\", buffer);\n+\t}\n+}\n+\n+static void\n+sfc_efx_mcdi_ev_proxy_response(void *arg, uint32_t handle, efx_rc_t result)\n+{\n+\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n+\n+\tmcdi->proxy_handle = handle;\n+\tmcdi->proxy_result = result;\n+}\n+\n+int\n+sfc_efx_mcdi_init(struct sfc_efx_mcdi *mcdi,\n+\t\t  uint32_t logtype, const char *log_prefix, efx_nic_t *nic,\n+\t\t  const struct sfc_efx_mcdi_ops *ops, void *ops_cookie)\n+{\n+\tsize_t max_msg_size;\n+\tefx_mcdi_transport_t *emtp;\n+\tint rc;\n+\n+\tif (ops->dma_alloc == NULL || ops->dma_free == NULL ||\n+\t    ops->sched_restart == NULL || ops->mgmt_evq_poll == NULL)\n+\t\treturn EINVAL;\n+\n+\tSFC_EFX_ASSERT(mcdi->state == SFC_EFX_MCDI_UNINITIALIZED);\n+\n+\trte_spinlock_init(&mcdi->lock);\n+\n+\tmcdi->ops = ops;\n+\tmcdi->ops_cookie = ops_cookie;\n+\tmcdi->nic = nic;\n+\n+\tmcdi->state = SFC_EFX_MCDI_INITIALIZED;\n+\n+\tmcdi->logtype = logtype;\n+\tmcdi->log_prefix = log_prefix;\n+\n+\tmax_msg_size = sizeof(uint32_t) + MCDI_CTL_SDU_LEN_MAX_V2;\n+\trc = ops->dma_alloc(ops_cookie, \"mcdi\", max_msg_size, &mcdi->mem);\n+\tif (rc != 0)\n+\t\tgoto fail_dma_alloc;\n+\n+\temtp = &mcdi->transport;\n+\temtp->emt_context = mcdi;\n+\temtp->emt_dma_mem = &mcdi->mem;\n+\temtp->emt_execute = sfc_efx_mcdi_execute;\n+\temtp->emt_ev_cpl = sfc_efx_mcdi_ev_cpl;\n+\temtp->emt_exception = sfc_efx_mcdi_exception;\n+\temtp->emt_logger = sfc_efx_mcdi_logger;\n+\temtp->emt_ev_proxy_response = sfc_efx_mcdi_ev_proxy_response;\n+\n+\tsfc_efx_mcdi_info(mcdi, \"init MCDI\");\n+\trc = efx_mcdi_init(mcdi->nic, emtp);\n+\tif (rc != 0)\n+\t\tgoto fail_mcdi_init;\n+\n+\treturn 0;\n+\n+fail_mcdi_init:\n+\tmemset(emtp, 0, sizeof(*emtp));\n+\tops->dma_free(ops_cookie, &mcdi->mem);\n+\n+fail_dma_alloc:\n+\tmcdi->state = SFC_EFX_MCDI_UNINITIALIZED;\n+\treturn rc;\n+}\n+\n+void\n+sfc_efx_mcdi_fini(struct sfc_efx_mcdi *mcdi)\n+{\n+\tefx_mcdi_transport_t *emtp;\n+\n+\temtp = &mcdi->transport;\n+\n+\trte_spinlock_lock(&mcdi->lock);\n+\n+\tSFC_EFX_ASSERT(mcdi->state == SFC_EFX_MCDI_INITIALIZED ||\n+\t\t       mcdi->state == SFC_EFX_MCDI_DEAD);\n+\tmcdi->state = SFC_EFX_MCDI_UNINITIALIZED;\n+\n+\tsfc_efx_mcdi_info(mcdi, \"fini MCDI\");\n+\tefx_mcdi_fini(mcdi->nic);\n+\tmemset(emtp, 0, sizeof(*emtp));\n+\n+\trte_spinlock_unlock(&mcdi->lock);\n+\n+\tmcdi->ops->dma_free(mcdi->ops_cookie, &mcdi->mem);\n+}\ndiff --git a/drivers/net/sfc/sfc_mcdi.h b/drivers/common/sfc_efx/sfc_efx_mcdi.h\nsimilarity index 81%\nrename from drivers/net/sfc/sfc_mcdi.h\nrename to drivers/common/sfc_efx/sfc_efx_mcdi.h\nindex e3a637aeb7..836afacddc 100644\n--- a/drivers/net/sfc/sfc_mcdi.h\n+++ b/drivers/common/sfc_efx/sfc_efx_mcdi.h\n@@ -7,8 +7,8 @@\n  * for Solarflare) and Solarflare Communications, Inc.\n  */\n \n-#ifndef _SFC_MCDI_H\n-#define _SFC_MCDI_H\n+#ifndef _SFC_EFX_MCDI_H\n+#define _SFC_EFX_MCDI_H\n \n #include <stdint.h>\n \n@@ -62,8 +62,14 @@ struct sfc_efx_mcdi {\n \tconst char\t\t\t*log_prefix;\n };\n \n+int sfc_efx_mcdi_init(struct sfc_efx_mcdi *mcdi,\n+\t\t      uint32_t logtype, const char *log_prefix,\n+\t\t      efx_nic_t *nic,\n+\t\t      const struct sfc_efx_mcdi_ops *ops, void *ops_cookie);\n+void sfc_efx_mcdi_fini(struct sfc_efx_mcdi *mcdi);\n+\n #ifdef __cplusplus\n }\n #endif\n \n-#endif  /* _SFC_MCDI_H */\n+#endif  /* _SFC_EFX_MCDI_H */\ndiff --git a/drivers/net/sfc/sfc.h b/drivers/net/sfc/sfc.h\nindex b20fecb4f8..fa7c79b80b 100644\n--- a/drivers/net/sfc/sfc.h\n+++ b/drivers/net/sfc/sfc.h\n@@ -21,10 +21,11 @@\n \n #include \"efx.h\"\n \n+#include \"sfc_efx_mcdi.h\"\n+\n #include \"sfc_debug.h\"\n #include \"sfc_log.h\"\n #include \"sfc_filter.h\"\n-#include \"sfc_mcdi.h\"\n \n #ifdef __cplusplus\n extern \"C\" {\ndiff --git a/drivers/net/sfc/sfc_mcdi.c b/drivers/net/sfc/sfc_mcdi.c\nindex ff2bc14c5d..644dd9c980 100644\n--- a/drivers/net/sfc/sfc_mcdi.c\n+++ b/drivers/net/sfc/sfc_mcdi.c\n@@ -7,344 +7,13 @@\n  * for Solarflare) and Solarflare Communications, Inc.\n  */\n \n-#include <rte_cycles.h>\n+#include \"sfc_efx_mcdi.h\"\n \n-#include \"efx.h\"\n-#include \"efx_mcdi.h\"\n-#include \"efx_regs_mcdi.h\"\n-\n-#include \"sfc_mcdi.h\"\n #include \"sfc.h\"\n #include \"sfc_debug.h\"\n #include \"sfc_log.h\"\n #include \"sfc_ev.h\"\n \n-#define SFC_EFX_MCDI_POLL_INTERVAL_MIN_US\t10\t\t/* 10us */\n-#define SFC_EFX_MCDI_POLL_INTERVAL_MAX_US\t(US_PER_S / 10)\t/* 100ms */\n-#define SFC_EFX_MCDI_WATCHDOG_INTERVAL_US\t(10 * US_PER_S)\t/* 10s */\n-\n-#define sfc_efx_mcdi_log(mcdi, level, ...) \\\n-\tdo {\t\t\t\t\t\t\t\t\\\n-\t\tconst struct sfc_efx_mcdi *_mcdi = (mcdi);\t\t\\\n-\t\t\t\t\t\t\t\t\t\\\n-\t\trte_log(level, _mcdi->logtype,\t\t\t\t\\\n-\t\t\tRTE_FMT(\"%s\" RTE_FMT_HEAD(__VA_ARGS__ ,) \"\\n\",\t\\\n-\t\t\t\t_mcdi->log_prefix,\t\t\t\\\n-\t\t\t\tRTE_FMT_TAIL(__VA_ARGS__,)));\t\t\\\n-\t} while (0)\n-\n-#define sfc_efx_mcdi_crit(mcdi, ...) \\\n-\tsfc_efx_mcdi_log(mcdi, RTE_LOG_CRIT, __VA_ARGS__)\n-\n-#define sfc_efx_mcdi_err(mcdi, ...) \\\n-\tsfc_efx_mcdi_log(mcdi, RTE_LOG_ERR, __VA_ARGS__)\n-\n-#define sfc_efx_mcdi_warn(mcdi, ...) \\\n-\tsfc_efx_mcdi_log(mcdi, RTE_LOG_WARNING, __VA_ARGS__)\n-\n-#define sfc_efx_mcdi_info(mcdi, ...) \\\n-\tsfc_efx_mcdi_log(mcdi, RTE_LOG_INFO, __VA_ARGS__)\n-\n-/** Level value used by MCDI log statements */\n-#define SFC_EFX_LOG_LEVEL_MCDI\tRTE_LOG_INFO\n-\n-#define sfc_efx_log_mcdi(mcdi, ...) \\\n-\tsfc_efx_mcdi_log(mcdi, SFC_EFX_LOG_LEVEL_MCDI, __VA_ARGS__)\n-\n-static void\n-sfc_efx_mcdi_timeout(struct sfc_efx_mcdi *mcdi)\n-{\n-\tsfc_efx_mcdi_warn(mcdi, \"MC TIMEOUT\");\n-\n-\tmcdi->state = SFC_EFX_MCDI_DEAD;\n-\tsfc_efx_mcdi_crit(mcdi,\n-\t\t\"MCDI timeout handling is not implemented - NIC is unusable\");\n-}\n-\n-static inline boolean_t\n-sfc_efx_mcdi_proxy_event_available(struct sfc_efx_mcdi *mcdi)\n-{\n-\tmcdi->proxy_handle = 0;\n-\tmcdi->proxy_result = ETIMEDOUT;\n-\tmcdi->ops->mgmt_evq_poll(mcdi->ops_cookie);\n-\tif (mcdi->proxy_result != ETIMEDOUT)\n-\t\treturn B_TRUE;\n-\n-\treturn B_FALSE;\n-}\n-\n-static void\n-sfc_efx_mcdi_poll(struct sfc_efx_mcdi *mcdi, boolean_t proxy)\n-{\n-\tefx_nic_t *enp;\n-\tunsigned int delay_total;\n-\tunsigned int delay_us;\n-\tboolean_t aborted __rte_unused;\n-\n-\tdelay_total = 0;\n-\tdelay_us = SFC_EFX_MCDI_POLL_INTERVAL_MIN_US;\n-\tenp = mcdi->nic;\n-\n-\tdo {\n-\t\tboolean_t poll_completed;\n-\n-\t\tpoll_completed = (proxy) ?\n-\t\t\t\tsfc_efx_mcdi_proxy_event_available(mcdi) :\n-\t\t\t\tefx_mcdi_request_poll(enp);\n-\t\tif (poll_completed)\n-\t\t\treturn;\n-\n-\t\tif (delay_total > SFC_EFX_MCDI_WATCHDOG_INTERVAL_US) {\n-\t\t\tif (!proxy) {\n-\t\t\t\taborted = efx_mcdi_request_abort(enp);\n-\t\t\t\tSFC_ASSERT(aborted);\n-\t\t\t\tsfc_efx_mcdi_timeout(mcdi);\n-\t\t\t}\n-\n-\t\t\treturn;\n-\t\t}\n-\n-\t\trte_delay_us(delay_us);\n-\n-\t\tdelay_total += delay_us;\n-\n-\t\t/* Exponentially back off the poll frequency */\n-\t\tRTE_BUILD_BUG_ON(SFC_EFX_MCDI_POLL_INTERVAL_MAX_US >\n-\t\t\t\t UINT_MAX / 2);\n-\t\tdelay_us *= 2;\n-\t\tif (delay_us > SFC_EFX_MCDI_POLL_INTERVAL_MAX_US)\n-\t\t\tdelay_us = SFC_EFX_MCDI_POLL_INTERVAL_MAX_US;\n-\n-\t} while (1);\n-}\n-\n-static void\n-sfc_efx_mcdi_execute(void *arg, efx_mcdi_req_t *emrp)\n-{\n-\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n-\tuint32_t proxy_handle;\n-\n-\tif (mcdi->state == SFC_EFX_MCDI_DEAD) {\n-\t\temrp->emr_rc = ENOEXEC;\n-\t\treturn;\n-\t}\n-\n-\trte_spinlock_lock(&mcdi->lock);\n-\n-\tSFC_ASSERT(mcdi->state == SFC_EFX_MCDI_INITIALIZED);\n-\n-\tefx_mcdi_request_start(mcdi->nic, emrp, B_FALSE);\n-\tsfc_efx_mcdi_poll(mcdi, B_FALSE);\n-\n-\tif (efx_mcdi_get_proxy_handle(mcdi->nic, emrp, &proxy_handle) == 0) {\n-\t\t/*\n-\t\t * Authorization is required for the MCDI request;\n-\t\t * wait for an MCDI proxy response event to bring\n-\t\t * a non-zero proxy handle (should be the same as\n-\t\t * the value obtained above) and operation status\n-\t\t */\n-\t\tsfc_efx_mcdi_poll(mcdi, B_TRUE);\n-\n-\t\tif ((mcdi->proxy_handle != 0) &&\n-\t\t    (mcdi->proxy_handle != proxy_handle)) {\n-\t\t\tsfc_efx_mcdi_err(mcdi, \"Unexpected MCDI proxy event\");\n-\t\t\temrp->emr_rc = EFAULT;\n-\t\t} else if (mcdi->proxy_result == 0) {\n-\t\t\t/*\n-\t\t\t * Authorization succeeded; re-issue the original\n-\t\t\t * request and poll for an ordinary MCDI response\n-\t\t\t */\n-\t\t\tefx_mcdi_request_start(mcdi->nic, emrp, B_FALSE);\n-\t\t\tsfc_efx_mcdi_poll(mcdi, B_FALSE);\n-\t\t} else {\n-\t\t\temrp->emr_rc = mcdi->proxy_result;\n-\t\t\tsfc_efx_mcdi_err(mcdi,\n-\t\t\t\t\"MCDI proxy authorization failed (handle=%08x, result=%d)\",\n-\t\t\t\tproxy_handle, mcdi->proxy_result);\n-\t\t}\n-\t}\n-\n-\trte_spinlock_unlock(&mcdi->lock);\n-}\n-\n-static void\n-sfc_efx_mcdi_ev_cpl(void *arg)\n-{\n-\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n-\n-\tRTE_SET_USED(mcdi);\n-\tSFC_ASSERT(mcdi->state == SFC_EFX_MCDI_INITIALIZED);\n-\n-\t/* MCDI is polled, completions are not expected */\n-\tSFC_ASSERT(0);\n-}\n-\n-static void\n-sfc_efx_mcdi_exception(void *arg, efx_mcdi_exception_t eme)\n-{\n-\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n-\n-\tsfc_efx_mcdi_warn(mcdi, \"MC %s\",\n-\t    (eme == EFX_MCDI_EXCEPTION_MC_REBOOT) ? \"REBOOT\" :\n-\t    (eme == EFX_MCDI_EXCEPTION_MC_BADASSERT) ? \"BADASSERT\" : \"UNKNOWN\");\n-\n-\tmcdi->ops->sched_restart(mcdi->ops_cookie);\n-}\n-\n-#define SFC_MCDI_LOG_BUF_SIZE\t128\n-\n-static size_t\n-sfc_efx_mcdi_do_log(const struct sfc_efx_mcdi *mcdi,\n-\t\tchar *buffer, void *data, size_t data_size,\n-\t\tsize_t pfxsize, size_t position)\n-{\n-\tuint32_t *words = data;\n-\t/* Space separator plus 2 characters per byte */\n-\tconst size_t word_str_space = 1 + 2 * sizeof(*words);\n-\tsize_t i;\n-\n-\tfor (i = 0; i < data_size; i += sizeof(*words)) {\n-\t\tif (position + word_str_space >=\n-\t\t    SFC_MCDI_LOG_BUF_SIZE) {\n-\t\t\t/* Flush at SFC_MCDI_LOG_BUF_SIZE with backslash\n-\t\t\t * at the end which is required by netlogdecode.\n-\t\t\t */\n-\t\t\tbuffer[position] = '\\0';\n-\t\t\tsfc_efx_log_mcdi(mcdi, \"%s \\\\\", buffer);\n-\t\t\t/* Preserve prefix for the next log message */\n-\t\t\tposition = pfxsize;\n-\t\t}\n-\t\tposition += snprintf(buffer + position,\n-\t\t\t\t     SFC_MCDI_LOG_BUF_SIZE - position,\n-\t\t\t\t     \" %08x\", *words);\n-\t\twords++;\n-\t}\n-\treturn position;\n-}\n-\n-static void\n-sfc_efx_mcdi_logger(void *arg, efx_log_msg_t type,\n-\t\tvoid *header, size_t header_size,\n-\t\tvoid *data, size_t data_size)\n-{\n-\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n-\tchar buffer[SFC_MCDI_LOG_BUF_SIZE];\n-\tsize_t pfxsize;\n-\tsize_t start;\n-\n-\t/*\n-\t * Unlike the other cases, MCDI logging implies more onerous work\n-\t * needed to produce a message. If the dynamic log level prevents\n-\t * the end result from being printed, the CPU time will be wasted.\n-\t *\n-\t * To avoid wasting time, the actual level is examined in advance.\n-\t */\n-\tif (rte_log_get_level(mcdi->logtype) < (int)SFC_EFX_LOG_LEVEL_MCDI)\n-\t\treturn;\n-\n-\t/* The format including prefix added by sfc_efx_log_mcdi() is the\n-\t * format consumed by the Solarflare netlogdecode tool.\n-\t */\n-\tpfxsize = snprintf(buffer, sizeof(buffer), \"MCDI RPC %s:\",\n-\t\t\t   type == EFX_LOG_MCDI_REQUEST ? \"REQ\" :\n-\t\t\t   type == EFX_LOG_MCDI_RESPONSE ? \"RESP\" : \"???\");\n-\tstart = sfc_efx_mcdi_do_log(mcdi, buffer, header, header_size,\n-\t\t\t\t    pfxsize, pfxsize);\n-\tstart = sfc_efx_mcdi_do_log(mcdi, buffer, data, data_size,\n-\t\t\t\t    pfxsize, start);\n-\tif (start != pfxsize) {\n-\t\tbuffer[start] = '\\0';\n-\t\tsfc_efx_log_mcdi(mcdi, \"%s\", buffer);\n-\t}\n-}\n-\n-static void\n-sfc_efx_mcdi_ev_proxy_response(void *arg, uint32_t handle, efx_rc_t result)\n-{\n-\tstruct sfc_efx_mcdi *mcdi = (struct sfc_efx_mcdi *)arg;\n-\n-\tmcdi->proxy_handle = handle;\n-\tmcdi->proxy_result = result;\n-}\n-\n-static int\n-sfc_efx_mcdi_init(struct sfc_efx_mcdi *mcdi,\n-\t\t  uint32_t logtype, const char *log_prefix, efx_nic_t *nic,\n-\t\t  const struct sfc_efx_mcdi_ops *ops, void *ops_cookie)\n-{\n-\tsize_t max_msg_size;\n-\tefx_mcdi_transport_t *emtp;\n-\tint rc;\n-\n-\tif (ops->dma_alloc == NULL || ops->dma_free == NULL ||\n-\t    ops->sched_restart == NULL || ops->mgmt_evq_poll == NULL)\n-\t\treturn EINVAL;\n-\n-\tSFC_ASSERT(mcdi->state == SFC_EFX_MCDI_UNINITIALIZED);\n-\n-\trte_spinlock_init(&mcdi->lock);\n-\n-\tmcdi->ops = ops;\n-\tmcdi->ops_cookie = ops_cookie;\n-\tmcdi->nic = nic;\n-\n-\tmcdi->state = SFC_EFX_MCDI_INITIALIZED;\n-\n-\tmcdi->logtype = logtype;\n-\tmcdi->log_prefix = log_prefix;\n-\n-\tmax_msg_size = sizeof(uint32_t) + MCDI_CTL_SDU_LEN_MAX_V2;\n-\trc = ops->dma_alloc(ops_cookie, \"mcdi\", max_msg_size, &mcdi->mem);\n-\tif (rc != 0)\n-\t\tgoto fail_dma_alloc;\n-\n-\temtp = &mcdi->transport;\n-\temtp->emt_context = mcdi;\n-\temtp->emt_dma_mem = &mcdi->mem;\n-\temtp->emt_execute = sfc_efx_mcdi_execute;\n-\temtp->emt_ev_cpl = sfc_efx_mcdi_ev_cpl;\n-\temtp->emt_exception = sfc_efx_mcdi_exception;\n-\temtp->emt_logger = sfc_efx_mcdi_logger;\n-\temtp->emt_ev_proxy_response = sfc_efx_mcdi_ev_proxy_response;\n-\n-\tsfc_efx_mcdi_info(mcdi, \"init MCDI\");\n-\trc = efx_mcdi_init(mcdi->nic, emtp);\n-\tif (rc != 0)\n-\t\tgoto fail_mcdi_init;\n-\n-\treturn 0;\n-\n-fail_mcdi_init:\n-\tmemset(emtp, 0, sizeof(*emtp));\n-\tops->dma_free(ops_cookie, &mcdi->mem);\n-\n-fail_dma_alloc:\n-\tmcdi->state = SFC_EFX_MCDI_UNINITIALIZED;\n-\treturn rc;\n-}\n-\n-static void\n-sfc_efx_mcdi_fini(struct sfc_efx_mcdi *mcdi)\n-{\n-\tefx_mcdi_transport_t *emtp;\n-\n-\temtp = &mcdi->transport;\n-\n-\trte_spinlock_lock(&mcdi->lock);\n-\n-\tSFC_ASSERT(mcdi->state == SFC_EFX_MCDI_INITIALIZED ||\n-\t\t   mcdi->state == SFC_EFX_MCDI_DEAD);\n-\tmcdi->state = SFC_EFX_MCDI_UNINITIALIZED;\n-\n-\tsfc_efx_mcdi_info(mcdi, \"fini MCDI\");\n-\tefx_mcdi_fini(mcdi->nic);\n-\tmemset(emtp, 0, sizeof(*emtp));\n-\n-\trte_spinlock_unlock(&mcdi->lock);\n-\n-\tmcdi->ops->dma_free(mcdi->ops_cookie, &mcdi->mem);\n-}\n-\n static sfc_efx_mcdi_dma_alloc_cb sfc_mcdi_dma_alloc;\n static int\n sfc_mcdi_dma_alloc(void *cookie, const char *name, size_t len,\n",
    "prefixes": [
        "14/14"
    ]
}