get:
Show a patch.

patch:
Update a patch.

put:
Update a patch.

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

{
    "id": 110223,
    "url": "https://patches.dpdk.org/api/patches/110223/?format=api",
    "web_url": "https://patches.dpdk.org/project/dpdk/patch/20220425053446.921528-5-robinx.zhang@intel.com/",
    "project": {
        "id": 1,
        "url": "https://patches.dpdk.org/api/projects/1/?format=api",
        "name": "DPDK",
        "link_name": "dpdk",
        "list_id": "dev.dpdk.org",
        "list_email": "dev@dpdk.org",
        "web_url": "http://core.dpdk.org",
        "scm_url": "git://dpdk.org/dpdk",
        "webscm_url": "http://git.dpdk.org/dpdk",
        "list_archive_url": "https://inbox.dpdk.org/dev",
        "list_archive_url_format": "https://inbox.dpdk.org/dev/{}",
        "commit_url_format": ""
    },
    "msgid": "<20220425053446.921528-5-robinx.zhang@intel.com>",
    "list_archive_url": "https://inbox.dpdk.org/dev/20220425053446.921528-5-robinx.zhang@intel.com",
    "date": "2022-04-25T05:34:45",
    "name": "[v4,4/5] ethdev: format module EEPROM for SFF-8472",
    "commit_ref": null,
    "pull_url": null,
    "state": "superseded",
    "archived": true,
    "hash": "83a59120529621636fc018d7c5b5bb36eae0e897",
    "submitter": {
        "id": 2004,
        "url": "https://patches.dpdk.org/api/people/2004/?format=api",
        "name": "Robin Zhang",
        "email": "robinx.zhang@intel.com"
    },
    "delegate": null,
    "mbox": "https://patches.dpdk.org/project/dpdk/patch/20220425053446.921528-5-robinx.zhang@intel.com/mbox/",
    "series": [
        {
            "id": 22654,
            "url": "https://patches.dpdk.org/api/series/22654/?format=api",
            "web_url": "https://patches.dpdk.org/project/dpdk/list/?series=22654",
            "date": "2022-04-25T05:34:41",
            "name": "add telemetry command for show module EEPROM",
            "version": 4,
            "mbox": "https://patches.dpdk.org/series/22654/mbox/"
        }
    ],
    "comments": "https://patches.dpdk.org/api/patches/110223/comments/",
    "check": "success",
    "checks": "https://patches.dpdk.org/api/patches/110223/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 mails.dpdk.org (mails.dpdk.org [217.70.189.124])\n\tby inbox.dpdk.org (Postfix) with ESMTP id B01AFA00BE;\n\tMon, 25 Apr 2022 07:40:23 +0200 (CEST)",
            "from [217.70.189.124] (localhost [127.0.0.1])\n\tby mails.dpdk.org (Postfix) with ESMTP id 14F5542822;\n\tMon, 25 Apr 2022 07:39:46 +0200 (CEST)",
            "from mga18.intel.com (mga18.intel.com [134.134.136.126])\n by mails.dpdk.org (Postfix) with ESMTP id 998C74281C\n for <dev@dpdk.org>; Mon, 25 Apr 2022 07:39:43 +0200 (CEST)",
            "from orsmga008.jf.intel.com ([10.7.209.65])\n by orsmga106.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384;\n 24 Apr 2022 22:39:43 -0700",
            "from intel-cd-odc-robin.cd.intel.com ([10.240.178.191])\n by orsmga008-auth.jf.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384;\n 24 Apr 2022 22:39:40 -0700"
        ],
        "DKIM-Signature": "v=1; a=rsa-sha256; c=relaxed/simple;\n d=intel.com; i=@intel.com; q=dns/txt; s=Intel;\n t=1650865183; x=1682401183;\n h=from:to:cc:subject:date:message-id:in-reply-to:\n references:mime-version:content-transfer-encoding;\n bh=jCmLA9A7++9HEs+XNVBiUI2jMikiJk7V5qZho0bjmfc=;\n b=YjIcF2I5pMgg1Vqzlpt535fP+HWN8LsXji/LDOpQC4z/0mhsn4W6pMqK\n 72hg9crEKg8Xs/MK7OsotlwvaT3N60u+AOtWBj7Zi09zElZcqUy1ykyYL\n ep1q3DtPJSaH+DKQ1XxpbLK6sM21vfXwRM/bU0z0bj3hQx42xHwsJIoQT\n rxTQxgMWHOFO+mPzzgdJm0m/+3QFF3zbiV9U5Ss5b44jR022K+51xdHNT\n qtJ6EQDEX2UcZth9JdBiafuGTSH8QaMmuExeTPjd319UljhoJvP9ctGWL\n C4PqngwGNjOSCuyD1JJFvBz2ya0bLzbL8H8qh894EPfPO4wop4Bsm2AsJ Q==;",
        "X-IronPort-AV": [
            "E=McAfee;i=\"6400,9594,10327\"; a=\"247070542\"",
            "E=Sophos;i=\"5.90,287,1643702400\"; d=\"scan'208\";a=\"247070542\"",
            "E=Sophos;i=\"5.90,287,1643702400\"; d=\"scan'208\";a=\"579087330\""
        ],
        "From": "Robin Zhang <robinx.zhang@intel.com>",
        "To": "dev@dpdk.org",
        "Cc": "qiming.yang@intel.com, qi.z.zhang@intel.com, stevex.yang@intel.com,\n thomas@monjalon.net, andrew.rybchenko@oktetlabs.ru,\n bruce.richardson@intel.com, david.marchand@redhat.com,\n Robin Zhang <robinx.zhang@intel.com>",
        "Subject": "[PATCH v4 4/5] ethdev: format module EEPROM for SFF-8472",
        "Date": "Mon, 25 Apr 2022 05:34:45 +0000",
        "Message-Id": "<20220425053446.921528-5-robinx.zhang@intel.com>",
        "X-Mailer": "git-send-email 2.25.1",
        "In-Reply-To": "<20220425053446.921528-1-robinx.zhang@intel.com>",
        "References": "<20220215101853.919735-1-robinx.zhang@intel.com>\n <20220425053446.921528-1-robinx.zhang@intel.com>",
        "MIME-Version": "1.0",
        "Content-Transfer-Encoding": "8bit",
        "X-BeenThere": "dev@dpdk.org",
        "X-Mailman-Version": "2.1.29",
        "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"
    },
    "content": "This patch implements format module EEPROM information for\nSFF-8472 Rev 12.0\n\nSigned-off-by: Robin Zhang <robinx.zhang@intel.com>\n---\n lib/ethdev/ethdev_sff_telemetry.c |   4 +\n lib/ethdev/meson.build            |   1 +\n lib/ethdev/sff_8472.c             | 287 ++++++++++++++++++++++++++++++\n 3 files changed, 292 insertions(+)\n create mode 100644 lib/ethdev/sff_8472.c",
    "diff": "diff --git a/lib/ethdev/ethdev_sff_telemetry.c b/lib/ethdev/ethdev_sff_telemetry.c\nindex aa1e859068..fa93b35275 100644\n--- a/lib/ethdev/ethdev_sff_telemetry.c\n+++ b/lib/ethdev/ethdev_sff_telemetry.c\n@@ -67,6 +67,10 @@ sff_port_module_eeprom_display(uint16_t port_id, struct sff_item *items)\n \tcase RTE_ETH_MODULE_SFF_8079:\n \t\tsff_8079_show_all(einfo.data, items);\n \t\tbreak;\n+\tcase RTE_ETH_MODULE_SFF_8472:\n+\t\tsff_8079_show_all(einfo.data, items);\n+\t\tsff_8472_show_all(einfo.data, items);\n+\t\tbreak;\n \tdefault:\n \t\tRTE_ETHDEV_LOG(NOTICE, \"Unsupported module type: %u\\n\", minfo.type);\n \t\tbreak;\ndiff --git a/lib/ethdev/meson.build b/lib/ethdev/meson.build\nindex d94860da0c..4d81a35c09 100644\n--- a/lib/ethdev/meson.build\n+++ b/lib/ethdev/meson.build\n@@ -14,6 +14,7 @@ sources = files(\n         'ethdev_sff_telemetry.c',\n         'sff_common.c',\n         'sff_8079.c',\n+        'sff_8472.c',\n )\n \n headers = files(\ndiff --git a/lib/ethdev/sff_8472.c b/lib/ethdev/sff_8472.c\nnew file mode 100644\nindex 0000000000..b4869d69c0\n--- /dev/null\n+++ b/lib/ethdev/sff_8472.c\n@@ -0,0 +1,287 @@\n+/* SPDX-License-Identifier: BSD-3-Clause\n+ * Copyright(c) 2022 Intel Corporation\n+ *\n+ * Implements SFF-8472 optics diagnostics.\n+ *\n+ */\n+\n+#include <stdio.h>\n+#include <math.h>\n+#include <arpa/inet.h>\n+#include <rte_mbuf.h>\n+#include <rte_ethdev.h>\n+#include <rte_flow.h>\n+#include \"sff_common.h\"\n+#include \"ethdev_sff_telemetry.h\"\n+\n+/* Offsets in decimal, for direct comparison with the SFF specs */\n+\n+/* A0-based EEPROM offsets for DOM support checks */\n+#define SFF_A0_DOM                        92\n+#define SFF_A0_OPTIONS                    93\n+#define SFF_A0_COMP                       94\n+\n+/* EEPROM bit values for various registers */\n+#define SFF_A0_DOM_EXTCAL                 (1 << 4)\n+#define SFF_A0_DOM_INTCAL                 (1 << 5)\n+#define SFF_A0_DOM_IMPL                   (1 << 6)\n+#define SFF_A0_DOM_PWRT                   (1 << 3)\n+\n+#define SFF_A0_OPTIONS_AW                 (1 << 7)\n+\n+/*\n+ * This is the offset at which the A2 page is in the EEPROM\n+ * blob returned by the kernel.\n+ */\n+#define SFF_A2_BASE                       0x100\n+\n+/* A2-based offsets for DOM */\n+#define SFF_A2_TEMP                       96\n+#define SFF_A2_TEMP_HALRM                 0\n+#define SFF_A2_TEMP_LALRM                 2\n+#define SFF_A2_TEMP_HWARN                 4\n+#define SFF_A2_TEMP_LWARN                 6\n+\n+#define SFF_A2_VCC                        98\n+#define SFF_A2_VCC_HALRM                  8\n+#define SFF_A2_VCC_LALRM                  10\n+#define SFF_A2_VCC_HWARN                  12\n+#define SFF_A2_VCC_LWARN                  14\n+\n+#define SFF_A2_BIAS                       100\n+#define SFF_A2_BIAS_HALRM                 16\n+#define SFF_A2_BIAS_LALRM                 18\n+#define SFF_A2_BIAS_HWARN                 20\n+#define SFF_A2_BIAS_LWARN                 22\n+\n+#define SFF_A2_TX_PWR                     102\n+#define SFF_A2_TX_PWR_HALRM               24\n+#define SFF_A2_TX_PWR_LALRM               26\n+#define SFF_A2_TX_PWR_HWARN               28\n+#define SFF_A2_TX_PWR_LWARN               30\n+\n+#define SFF_A2_RX_PWR                     104\n+#define SFF_A2_RX_PWR_HALRM               32\n+#define SFF_A2_RX_PWR_LALRM               34\n+#define SFF_A2_RX_PWR_HWARN               36\n+#define SFF_A2_RX_PWR_LWARN               38\n+\n+#define SFF_A2_ALRM_FLG                   112\n+#define SFF_A2_WARN_FLG                   116\n+\n+/* 32-bit little-endian calibration constants */\n+#define SFF_A2_CAL_RXPWR4                 56\n+#define SFF_A2_CAL_RXPWR3                 60\n+#define SFF_A2_CAL_RXPWR2                 64\n+#define SFF_A2_CAL_RXPWR1                 68\n+#define SFF_A2_CAL_RXPWR0                 72\n+\n+/* 16-bit little endian calibration constants */\n+#define SFF_A2_CAL_TXI_SLP                76\n+#define SFF_A2_CAL_TXI_OFF                78\n+#define SFF_A2_CAL_TXPWR_SLP              80\n+#define SFF_A2_CAL_TXPWR_OFF              82\n+#define SFF_A2_CAL_T_SLP                  84\n+#define SFF_A2_CAL_T_OFF                  86\n+#define SFF_A2_CAL_V_SLP                  88\n+#define SFF_A2_CAL_V_OFF                  90\n+\n+static struct sff_8472_aw_flags {\n+\tconst char *str;        /* Human-readable string, null at the end */\n+\tint offset;             /* A2-relative address offset */\n+\tuint8_t value;          /* Alarm is on if (offset & value) != 0. */\n+} sff_8472_aw_flags[] = {\n+\t{ \"Laser bias current high alarm\",   SFF_A2_ALRM_FLG, (1 << 3) },\n+\t{ \"Laser bias current low alarm\",    SFF_A2_ALRM_FLG, (1 << 2) },\n+\t{ \"Laser bias current high warning\", SFF_A2_WARN_FLG, (1 << 3) },\n+\t{ \"Laser bias current low warning\",  SFF_A2_WARN_FLG, (1 << 2) },\n+\n+\t{ \"Laser output power high alarm\",   SFF_A2_ALRM_FLG, (1 << 1) },\n+\t{ \"Laser output power low alarm\",    SFF_A2_ALRM_FLG, (1 << 0) },\n+\t{ \"Laser output power high warning\", SFF_A2_WARN_FLG, (1 << 1) },\n+\t{ \"Laser output power low warning\",  SFF_A2_WARN_FLG, (1 << 0) },\n+\n+\t{ \"Module temperature high alarm\",   SFF_A2_ALRM_FLG, (1 << 7) },\n+\t{ \"Module temperature low alarm\",    SFF_A2_ALRM_FLG, (1 << 6) },\n+\t{ \"Module temperature high warning\", SFF_A2_WARN_FLG, (1 << 7) },\n+\t{ \"Module temperature low warning\",  SFF_A2_WARN_FLG, (1 << 6) },\n+\n+\t{ \"Module voltage high alarm\",   SFF_A2_ALRM_FLG, (1 << 5) },\n+\t{ \"Module voltage low alarm\",    SFF_A2_ALRM_FLG, (1 << 4) },\n+\t{ \"Module voltage high warning\", SFF_A2_WARN_FLG, (1 << 5) },\n+\t{ \"Module voltage low warning\",  SFF_A2_WARN_FLG, (1 << 4) },\n+\n+\t{ \"Laser rx power high alarm\",   SFF_A2_ALRM_FLG + 1, (1 << 7) },\n+\t{ \"Laser rx power low alarm\",    SFF_A2_ALRM_FLG + 1, (1 << 6) },\n+\t{ \"Laser rx power high warning\", SFF_A2_WARN_FLG + 1, (1 << 7) },\n+\t{ \"Laser rx power low warning\",  SFF_A2_WARN_FLG + 1, (1 << 6) },\n+\n+\t{ NULL, 0, 0 },\n+};\n+\n+/* Most common case: 16-bit unsigned integer in a certain unit */\n+#define A2_OFFSET_TO_U16(offset) \\\n+\t(data[SFF_A2_BASE + (offset)] << 8 | data[SFF_A2_BASE + (offset) + 1])\n+\n+/* Calibration slope is a number between 0.0 included and 256.0 excluded. */\n+#define A2_OFFSET_TO_SLP(offset) \\\n+\t(data[SFF_A2_BASE + (offset)] + data[SFF_A2_BASE + (offset) + 1] / 256.)\n+\n+/* Calibration offset is an integer from -32768 to 32767 */\n+#define A2_OFFSET_TO_OFF(offset) \\\n+\t((int16_t)A2_OFFSET_TO_U16(offset))\n+\n+/* RXPWR(x) are IEEE-754 floating point numbers in big-endian format */\n+#define A2_OFFSET_TO_RXPWRx(offset) \\\n+\t(befloattoh((const uint32_t *)(data + SFF_A2_BASE + (offset))))\n+\n+/*\n+ * 2-byte internal temperature conversions:\n+ * First byte is a signed 8-bit integer, which is the temp decimal part\n+ * Second byte are 1/256th of degree, which are added to the dec part.\n+ */\n+#define A2_OFFSET_TO_TEMP(offset) ((int16_t)A2_OFFSET_TO_U16(offset))\n+\n+static void sff_8472_dom_parse(const uint8_t *data, struct sff_diags *sd)\n+{\n+\tsd->bias_cur[MCURR] = A2_OFFSET_TO_U16(SFF_A2_BIAS);\n+\tsd->bias_cur[HALRM] = A2_OFFSET_TO_U16(SFF_A2_BIAS_HALRM);\n+\tsd->bias_cur[LALRM] = A2_OFFSET_TO_U16(SFF_A2_BIAS_LALRM);\n+\tsd->bias_cur[HWARN] = A2_OFFSET_TO_U16(SFF_A2_BIAS_HWARN);\n+\tsd->bias_cur[LWARN] = A2_OFFSET_TO_U16(SFF_A2_BIAS_LWARN);\n+\n+\tsd->sfp_voltage[MCURR] = A2_OFFSET_TO_U16(SFF_A2_VCC);\n+\tsd->sfp_voltage[HALRM] = A2_OFFSET_TO_U16(SFF_A2_VCC_HALRM);\n+\tsd->sfp_voltage[LALRM] = A2_OFFSET_TO_U16(SFF_A2_VCC_LALRM);\n+\tsd->sfp_voltage[HWARN] = A2_OFFSET_TO_U16(SFF_A2_VCC_HWARN);\n+\tsd->sfp_voltage[LWARN] = A2_OFFSET_TO_U16(SFF_A2_VCC_LWARN);\n+\n+\tsd->tx_power[MCURR] = A2_OFFSET_TO_U16(SFF_A2_TX_PWR);\n+\tsd->tx_power[HALRM] = A2_OFFSET_TO_U16(SFF_A2_TX_PWR_HALRM);\n+\tsd->tx_power[LALRM] = A2_OFFSET_TO_U16(SFF_A2_TX_PWR_LALRM);\n+\tsd->tx_power[HWARN] = A2_OFFSET_TO_U16(SFF_A2_TX_PWR_HWARN);\n+\tsd->tx_power[LWARN] = A2_OFFSET_TO_U16(SFF_A2_TX_PWR_LWARN);\n+\n+\tsd->rx_power[MCURR] = A2_OFFSET_TO_U16(SFF_A2_RX_PWR);\n+\tsd->rx_power[HALRM] = A2_OFFSET_TO_U16(SFF_A2_RX_PWR_HALRM);\n+\tsd->rx_power[LALRM] = A2_OFFSET_TO_U16(SFF_A2_RX_PWR_LALRM);\n+\tsd->rx_power[HWARN] = A2_OFFSET_TO_U16(SFF_A2_RX_PWR_HWARN);\n+\tsd->rx_power[LWARN] = A2_OFFSET_TO_U16(SFF_A2_RX_PWR_LWARN);\n+\n+\tsd->sfp_temp[MCURR] = A2_OFFSET_TO_TEMP(SFF_A2_TEMP);\n+\tsd->sfp_temp[HALRM] = A2_OFFSET_TO_TEMP(SFF_A2_TEMP_HALRM);\n+\tsd->sfp_temp[LALRM] = A2_OFFSET_TO_TEMP(SFF_A2_TEMP_LALRM);\n+\tsd->sfp_temp[HWARN] = A2_OFFSET_TO_TEMP(SFF_A2_TEMP_HWARN);\n+\tsd->sfp_temp[LWARN] = A2_OFFSET_TO_TEMP(SFF_A2_TEMP_LWARN);\n+}\n+\n+/* Converts to a float from a big-endian 4-byte source buffer. */\n+static float befloattoh(const uint32_t *source)\n+{\n+\tunion {\n+\t\tuint32_t src;\n+\t\tfloat dst;\n+\t} converter;\n+\n+\tconverter.src = ntohl(*source);\n+\treturn converter.dst;\n+}\n+\n+static void sff_8472_calibration(const uint8_t *data, struct sff_diags *sd)\n+{\n+\tunsigned long i;\n+\tuint16_t rx_reading;\n+\n+\t/* Calibration should occur for all values (threshold and current) */\n+\tfor (i = 0; i < ARRAY_SIZE(sd->bias_cur); ++i) {\n+\t\t/*\n+\t\t * Apply calibration formula 1 (Temp., Voltage, Bias, Tx Power)\n+\t\t */\n+\t\tsd->bias_cur[i]    *= A2_OFFSET_TO_SLP(SFF_A2_CAL_TXI_SLP);\n+\t\tsd->tx_power[i]    *= A2_OFFSET_TO_SLP(SFF_A2_CAL_TXPWR_SLP);\n+\t\tsd->sfp_voltage[i] *= A2_OFFSET_TO_SLP(SFF_A2_CAL_V_SLP);\n+\t\tsd->sfp_temp[i]    *= A2_OFFSET_TO_SLP(SFF_A2_CAL_T_SLP);\n+\n+\t\tsd->bias_cur[i]    += A2_OFFSET_TO_OFF(SFF_A2_CAL_TXI_OFF);\n+\t\tsd->tx_power[i]    += A2_OFFSET_TO_OFF(SFF_A2_CAL_TXPWR_OFF);\n+\t\tsd->sfp_voltage[i] += A2_OFFSET_TO_OFF(SFF_A2_CAL_V_OFF);\n+\t\tsd->sfp_temp[i]    += A2_OFFSET_TO_OFF(SFF_A2_CAL_T_OFF);\n+\n+\t\t/*\n+\t\t * Apply calibration formula 2 (Rx Power only)\n+\t\t */\n+\t\trx_reading = sd->rx_power[i];\n+\t\tsd->rx_power[i]    = A2_OFFSET_TO_RXPWRx(SFF_A2_CAL_RXPWR0);\n+\t\tsd->rx_power[i]    += rx_reading *\n+\t\t\tA2_OFFSET_TO_RXPWRx(SFF_A2_CAL_RXPWR1);\n+\t\tsd->rx_power[i]    += rx_reading *\n+\t\t\tA2_OFFSET_TO_RXPWRx(SFF_A2_CAL_RXPWR2);\n+\t\tsd->rx_power[i]    += rx_reading *\n+\t\t\tA2_OFFSET_TO_RXPWRx(SFF_A2_CAL_RXPWR3);\n+\t}\n+}\n+\n+static void sff_8472_parse_eeprom(const uint8_t *data, struct sff_diags *sd)\n+{\n+\tsd->supports_dom = data[SFF_A0_DOM] & SFF_A0_DOM_IMPL;\n+\tsd->supports_alarms = data[SFF_A0_OPTIONS] & SFF_A0_OPTIONS_AW;\n+\tsd->calibrated_ext = data[SFF_A0_DOM] & SFF_A0_DOM_EXTCAL;\n+\tsd->rx_power_type = data[SFF_A0_DOM] & SFF_A0_DOM_PWRT;\n+\n+\tsff_8472_dom_parse(data, sd);\n+\n+\t/*\n+\t * If the SFP is externally calibrated, we need to read calibration data\n+\t * and compensate the already stored readings.\n+\t */\n+\tif (sd->calibrated_ext)\n+\t\tsff_8472_calibration(data, sd);\n+}\n+\n+void sff_8472_show_all(const uint8_t *data, struct sff_item *items)\n+{\n+\tstruct sff_diags sd = {0};\n+\tconst char *rx_power_string = NULL;\n+\tchar val_string[SFF_ITEM_VAL_COMPOSE_SIZE];\n+\tint i;\n+\n+\tsff_8472_parse_eeprom(data, &sd);\n+\n+\tif (!sd.supports_dom) {\n+\t\tadd_item_string(items, \"Optical diagnostics support\", \"No\");\n+\t\treturn;\n+\t}\n+\tadd_item_string(items, \"Optical diagnostics support\", \"Yes\");\n+\n+\tSPRINT_BIAS(val_string, sd.bias_cur[MCURR]);\n+\tadd_item_string(items, \"Laser bias current\", val_string);\n+\n+\tSPRINT_xX_PWR(val_string, sd.tx_power[MCURR]);\n+\tadd_item_string(items, \"Laser output power\", val_string);\n+\n+\tif (!sd.rx_power_type)\n+\t\trx_power_string = \"Receiver signal OMA\";\n+\telse\n+\t\trx_power_string = \"Receiver signal average optical power\";\n+\n+\tSPRINT_xX_PWR(val_string, sd.rx_power[MCURR]);\n+\tadd_item_string(items, rx_power_string, val_string);\n+\n+\tSPRINT_TEMP(val_string, sd.sfp_temp[MCURR]);\n+\tadd_item_string(items, \"Module temperature\", val_string);\n+\n+\tSPRINT_VCC(val_string, sd.sfp_voltage[MCURR]);\n+\tadd_item_string(items, \"Module voltage\", val_string);\n+\n+\tadd_item_string(items, \"Alarm/warning flags implemented\",\n+\t\t\t(sd.supports_alarms ? \"Yes\" : \"No\"));\n+\n+\tif (sd.supports_alarms) {\n+\t\tfor (i = 0; sff_8472_aw_flags[i].str; ++i) {\n+\t\t\tadd_item_string(items, sff_8472_aw_flags[i].str,\n+\t\t\t\t\tdata[SFF_A2_BASE + sff_8472_aw_flags[i].offset]\n+\t\t\t\t\t& sff_8472_aw_flags[i].value ? \"On\" : \"Off\");\n+\t\t}\n+\t\tsff_show_thresholds(sd, items);\n+\t}\n+}\n",
    "prefixes": [
        "v4",
        "4/5"
    ]
}