Patch Detail
get:
Show a patch.
patch:
Update a patch.
put:
Update a patch.
GET /api/patches/1199189/?format=api
{ "id": 1199189, "url": "http://patchwork.ozlabs.org/api/patches/1199189/?format=api", "web_url": "http://patchwork.ozlabs.org/project/intel-wired-lan/patch/20191122020224.1102649-4-vinicius.gomes@intel.com/", "project": { "id": 46, "url": "http://patchwork.ozlabs.org/api/projects/46/?format=api", "name": "Intel Wired Ethernet development", "link_name": "intel-wired-lan", "list_id": "intel-wired-lan.osuosl.org", "list_email": "intel-wired-lan@osuosl.org", "web_url": "", "scm_url": "", "webscm_url": "", "list_archive_url": "", "list_archive_url_format": "", "commit_url_format": "" }, "msgid": "<20191122020224.1102649-4-vinicius.gomes@intel.com>", "list_archive_url": null, "date": "2019-11-22T02:02:23", "name": "[next-queue,v1,3/4] igc: Add support for TX timestamping", "commit_ref": null, "pull_url": null, "state": "superseded", "archived": false, "hash": "9d0cc607e07cbaf9e525caaa0d13b937a60b9bc8", "submitter": { "id": 72272, "url": "http://patchwork.ozlabs.org/api/people/72272/?format=api", "name": "Vinicius Costa Gomes", "email": "vinicius.gomes@intel.com" }, "delegate": { "id": 68, "url": "http://patchwork.ozlabs.org/api/users/68/?format=api", "username": "jtkirshe", "first_name": "Jeff", "last_name": "Kirsher", "email": "jeffrey.t.kirsher@intel.com" }, "mbox": "http://patchwork.ozlabs.org/project/intel-wired-lan/patch/20191122020224.1102649-4-vinicius.gomes@intel.com/mbox/", "series": [ { "id": 144449, "url": "http://patchwork.ozlabs.org/api/series/144449/?format=api", "web_url": "http://patchwork.ozlabs.org/project/intel-wired-lan/list/?series=144449", "date": "2019-11-22T02:02:20", "name": "igc: Add basic support for Timestamping/PTP", "version": 1, "mbox": "http://patchwork.ozlabs.org/series/144449/mbox/" } ], "comments": "http://patchwork.ozlabs.org/api/patches/1199189/comments/", "check": "pending", "checks": "http://patchwork.ozlabs.org/api/patches/1199189/checks/", "tags": {}, "related": [], "headers": { "Return-Path": "<intel-wired-lan-bounces@osuosl.org>", "X-Original-To": [ "incoming@patchwork.ozlabs.org", "intel-wired-lan@lists.osuosl.org" ], "Delivered-To": [ "patchwork-incoming@bilbo.ozlabs.org", "intel-wired-lan@lists.osuosl.org" ], "Authentication-Results": [ "ozlabs.org; spf=pass (sender SPF authorized)\n\tsmtp.mailfrom=osuosl.org (client-ip=140.211.166.133;\n\thelo=hemlock.osuosl.org;\n\tenvelope-from=intel-wired-lan-bounces@osuosl.org;\n\treceiver=<UNKNOWN>)", "ozlabs.org;\n\tdmarc=fail (p=none dis=none) header.from=intel.com" ], "Received": [ "from hemlock.osuosl.org (smtp2.osuosl.org [140.211.166.133])\n\t(using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256\n\tbits)) (No client certificate requested)\n\tby ozlabs.org (Postfix) with ESMTPS id 47K07K5dDLz9sPT\n\tfor <incoming@patchwork.ozlabs.org>;\n\tFri, 22 Nov 2019 13:02:37 +1100 (AEDT)", "from localhost (localhost [127.0.0.1])\n\tby hemlock.osuosl.org (Postfix) with ESMTP id 22703889FE;\n\tFri, 22 Nov 2019 02:02:36 +0000 (UTC)", "from hemlock.osuosl.org ([127.0.0.1])\n\tby localhost (.osuosl.org [127.0.0.1]) (amavisd-new, port 10024)\n\twith ESMTP id Yu2RPGwlGrCE; Fri, 22 Nov 2019 02:02:34 +0000 (UTC)", "from ash.osuosl.org (ash.osuosl.org [140.211.166.34])\n\tby hemlock.osuosl.org (Postfix) with ESMTP id 4D3BA889B5;\n\tFri, 22 Nov 2019 02:02:34 +0000 (UTC)", "from fraxinus.osuosl.org (smtp4.osuosl.org [140.211.166.137])\n\tby ash.osuosl.org (Postfix) with ESMTP id 5B0C21BF33D\n\tfor <intel-wired-lan@lists.osuosl.org>;\n\tFri, 22 Nov 2019 02:02:32 +0000 (UTC)", "from localhost (localhost [127.0.0.1])\n\tby fraxinus.osuosl.org (Postfix) with ESMTP id 57C158723E\n\tfor <intel-wired-lan@lists.osuosl.org>;\n\tFri, 22 Nov 2019 02:02:32 +0000 (UTC)", "from fraxinus.osuosl.org ([127.0.0.1])\n\tby localhost (.osuosl.org [127.0.0.1]) (amavisd-new, port 10024)\n\twith ESMTP id 9Enf065Xz9im for <intel-wired-lan@lists.osuosl.org>;\n\tFri, 22 Nov 2019 02:02:31 +0000 (UTC)", "from mga05.intel.com (mga05.intel.com [192.55.52.43])\n\tby fraxinus.osuosl.org (Postfix) with ESMTPS id 5C16987249\n\tfor <intel-wired-lan@lists.osuosl.org>;\n\tFri, 22 Nov 2019 02:02:31 +0000 (UTC)", "from fmsmga008.fm.intel.com ([10.253.24.58])\n\tby fmsmga105.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384;\n\t21 Nov 2019 18:02:30 -0800", "from vcostago-desk1.jf.intel.com ([10.54.70.26])\n\tby fmsmga008.fm.intel.com with ESMTP; 21 Nov 2019 18:02:30 -0800" ], "X-Virus-Scanned": [ "amavisd-new at osuosl.org", "amavisd-new at osuosl.org" ], "X-Greylist": "domain auto-whitelisted by SQLgrey-1.7.6", "X-Amp-Result": "SKIPPED(no attachment in message)", "X-Amp-File-Uploaded": "False", "X-ExtLoop1": "1", "X-IronPort-AV": "E=Sophos;i=\"5.69,228,1571727600\"; d=\"scan'208\";a=\"205264940\"", "From": "Vinicius Costa Gomes <vinicius.gomes@intel.com>", "To": "intel-wired-lan@lists.osuosl.org", "Date": "Thu, 21 Nov 2019 18:02:23 -0800", "Message-Id": "<20191122020224.1102649-4-vinicius.gomes@intel.com>", "X-Mailer": "git-send-email 2.24.0", "In-Reply-To": "<20191122020224.1102649-1-vinicius.gomes@intel.com>", "References": "<20191122020224.1102649-1-vinicius.gomes@intel.com>", "MIME-Version": "1.0", "Subject": "[Intel-wired-lan] [next-queue PATCH v1 3/4] igc: Add support for TX\n\ttimestamping", "X-BeenThere": "intel-wired-lan@osuosl.org", "X-Mailman-Version": "2.1.29", "Precedence": "list", "List-Id": "Intel Wired Ethernet Linux Kernel Driver Development\n\t<intel-wired-lan.osuosl.org>", "List-Unsubscribe": "<https://lists.osuosl.org/mailman/options/intel-wired-lan>, \n\t<mailto:intel-wired-lan-request@osuosl.org?subject=unsubscribe>", "List-Archive": "<http://lists.osuosl.org/pipermail/intel-wired-lan/>", "List-Post": "<mailto:intel-wired-lan@osuosl.org>", "List-Help": "<mailto:intel-wired-lan-request@osuosl.org?subject=help>", "List-Subscribe": "<https://lists.osuosl.org/mailman/listinfo/intel-wired-lan>, \n\t<mailto:intel-wired-lan-request@osuosl.org?subject=subscribe>", "Content-Type": "text/plain; charset=\"us-ascii\"", "Content-Transfer-Encoding": "7bit", "Errors-To": "intel-wired-lan-bounces@osuosl.org", "Sender": "\"Intel-wired-lan\" <intel-wired-lan-bounces@osuosl.org>" }, "content": "This adds support for timestamping packets being transmitted.\n\nBased on the code from i210. The basic differences is that i225 has 4\nregisters to store the transmit timestamps (i210 has one). Right now,\nwe only support retrieving from one register, support for using the\nother registers will be added later.\n\nSigned-off-by: Vinicius Costa Gomes <vinicius.gomes@intel.com>\n---\n drivers/net/ethernet/intel/igc/igc.h | 2 +\n drivers/net/ethernet/intel/igc/igc_defines.h | 14 +++\n drivers/net/ethernet/intel/igc/igc_main.c | 49 +++++++++++\n drivers/net/ethernet/intel/igc/igc_ptp.c | 92 ++++++++++++++++++++\n 4 files changed, 157 insertions(+)", "diff": "diff --git a/drivers/net/ethernet/intel/igc/igc.h b/drivers/net/ethernet/intel/igc/igc.h\nindex 686fe6d9dae6..228a9179fd06 100644\n--- a/drivers/net/ethernet/intel/igc/igc.h\n+++ b/drivers/net/ethernet/intel/igc/igc.h\n@@ -556,6 +556,8 @@ void igc_ptp_rx_pktstamp(struct igc_q_vector *q_vector, void *va,\n \t\t\t struct sk_buff *skb);\n int igc_ptp_set_ts_config(struct net_device *netdev, struct ifreq *ifr);\n int igc_ptp_get_ts_config(struct net_device *netdev, struct ifreq *ifr);\n+void igc_ptp_tx_hang(struct igc_adapter *adapter);\n+\n #define igc_rx_pg_size(_ring) (PAGE_SIZE << igc_rx_pg_order(_ring))\n \n #define IGC_TXD_DCMD\t(IGC_ADVTXD_DCMD_EOP | IGC_ADVTXD_DCMD_RS)\ndiff --git a/drivers/net/ethernet/intel/igc/igc_defines.h b/drivers/net/ethernet/intel/igc/igc_defines.h\nindex a5b7e5e05a89..09ce7dc40553 100644\n--- a/drivers/net/ethernet/intel/igc/igc_defines.h\n+++ b/drivers/net/ethernet/intel/igc/igc_defines.h\n@@ -370,10 +370,24 @@\n #define IGC_TSYNCRXCFG_PTP_V1_SYNC_MESSAGE\t0x00\n #define IGC_TSYNCRXCFG_PTP_V1_DELAY_REQ_MESSAGE\t0x01\n \n+/* Immediate Interrupt Receive */\n+#define IGC_IMIR_CLEAR_MASK\t0xF001FFFF /* IMIR Reg Clear Mask */\n+#define IGC_IMIR_PORT_BYPASS\t0x20000 /* IMIR Port Bypass Bit */\n+#define IGC_IMIR_PRIORITY_SHIFT\t29 /* IMIR Priority Shift */\n+#define IGC_IMIREXT_CLEAR_MASK\t0x7FFFF /* IMIREXT Reg Clear Mask */\n+\n /* Immediate Interrupt Receive Extended */\n #define IGC_IMIREXT_CTRL_BP\t0x00080000 /* Bypass check of ctrl bits */\n #define IGC_IMIREXT_SIZE_BP\t0x00001000 /* Packet size bypass */\n \n+/* Time Sync Transmit Control bit definitions */\n+#define IGC_TSYNCTXCTL_VALID\t\t\t0x00000001 /* Tx timestamp valid */\n+#define IGC_TSYNCTXCTL_ENABLED\t\t\t0x00000010 /* enable Tx timestamping */\n+#define IGC_TSYNCTXCTL_MAX_ALLOWED_DLY_MASK\t0x0000F000 /* max delay */\n+#define IGC_TSYNCTXCTL_SYNC_COMP_ERR\t\t0x20000000 /* sync err */\n+#define IGC_TSYNCTXCTL_SYNC_COMP\t\t0x40000000 /* sync complete */\n+#define IGC_TSYNCTXCTL_START_SYNC\t\t0x80000000 /* initiate sync */\n+\n /* Receive Checksum Control */\n #define IGC_RXCSUM_CRCOFL\t0x00000800 /* CRC32 offload enable */\n #define IGC_RXCSUM_PCSD\t\t0x00002000 /* packet checksum disabled */\ndiff --git a/drivers/net/ethernet/intel/igc/igc_main.c b/drivers/net/ethernet/intel/igc/igc_main.c\nindex f6319cb6b5ca..26ca3cfd5af2 100644\n--- a/drivers/net/ethernet/intel/igc/igc_main.c\n+++ b/drivers/net/ethernet/intel/igc/igc_main.c\n@@ -960,6 +960,11 @@ static inline int igc_maybe_stop_tx(struct igc_ring *tx_ring, const u16 size)\n \treturn __igc_maybe_stop_tx(tx_ring, size);\n }\n \n+#define IGC_SET_FLAG(_input, _flag, _result) \\\n+\t(((_flag) <= (_result)) ?\t\t\t\t\\\n+\t ((u32)((_input) & (_flag)) * ((_result) / (_flag))) :\t\\\n+\t ((u32)((_input) & (_flag)) / ((_flag) / (_result))))\n+\n static u32 igc_tx_cmd_type(struct sk_buff *skb, u32 tx_flags)\n {\n \t/* set type for advanced descriptor with frame checksum insertion */\n@@ -967,6 +972,10 @@ static u32 igc_tx_cmd_type(struct sk_buff *skb, u32 tx_flags)\n \t\t IGC_ADVTXD_DCMD_DEXT |\n \t\t IGC_ADVTXD_DCMD_IFCS;\n \n+\t/* set timestamp bit if present */\n+\tcmd_type |= IGC_SET_FLAG(tx_flags, IGC_TX_FLAGS_TSTAMP,\n+\t\t\t\t (IGC_ADVTXD_MAC_TSTAMP));\n+\n \treturn cmd_type;\n }\n \n@@ -1165,6 +1174,26 @@ static netdev_tx_t igc_xmit_frame_ring(struct sk_buff *skb,\n \tfirst->bytecount = skb->len;\n \tfirst->gso_segs = 1;\n \n+\tif (unlikely(skb_shinfo(skb)->tx_flags & SKBTX_HW_TSTAMP)) {\n+\t\tstruct igc_adapter *adapter = netdev_priv(tx_ring->netdev);\n+\n+\t\t/* FIXME: add support for retrieving timestamps from\n+\t\t * the other timer registers before skipping the\n+\t\t * timestamping request.\n+\t\t */\n+\t\tif (adapter->tstamp_config.tx_type == HWTSTAMP_TX_ON &&\n+\t\t !test_and_set_bit_lock(__IGC_PTP_TX_IN_PROGRESS,\n+\t\t\t\t\t &adapter->state)) {\n+\t\t\tskb_shinfo(skb)->tx_flags |= SKBTX_IN_PROGRESS;\n+\t\t\ttx_flags |= IGC_TX_FLAGS_TSTAMP;\n+\n+\t\t\tadapter->ptp_tx_skb = skb_get(skb);\n+\t\t\tadapter->ptp_tx_start = jiffies;\n+\t\t} else {\n+\t\t\tadapter->tx_hwtstamp_skipped++;\n+\t\t}\n+\t}\n+\n \t/* record initial flags and protocol */\n \tfirst->tx_flags = tx_flags;\n \tfirst->protocol = protocol;\n@@ -2765,6 +2794,21 @@ static void igc_set_rx_mode(struct net_device *netdev)\n \twr32(IGC_RLPML, rlpml);\n }\n \n+static void igc_tsync_interrupt(struct igc_adapter *adapter)\n+{\n+\tstruct igc_hw *hw = &adapter->hw;\n+\tu32 ack = 0, tsicr = rd32(IGC_TSICR);\n+\n+\tif (tsicr & IGC_TSICR_TXTS) {\n+\t\t/* retrieve hardware timestamp */\n+\t\tschedule_work(&adapter->ptp_tx_work);\n+\t\tack |= IGC_TSICR_TXTS;\n+\t}\n+\n+\t/* acknowledge the interrupts */\n+\twr32(IGC_TSICR, ack);\n+}\n+\n /**\n * igc_msix_other - msix other interrupt handler\n * @irq: interrupt number\n@@ -2792,6 +2836,9 @@ static irqreturn_t igc_msix_other(int irq, void *data)\n \t\t\tmod_timer(&adapter->watchdog_timer, jiffies + 1);\n \t}\n \n+\tif (icr & IGC_ICR_TS)\n+\t\tigc_tsync_interrupt(adapter);\n+\n \twr32(IGC_EIMS, adapter->eims_other);\n \n \treturn IRQ_HANDLED;\n@@ -3295,6 +3342,8 @@ static void igc_watchdog_task(struct work_struct *work)\n \t\twr32(IGC_ICS, IGC_ICS_RXDMT0);\n \t}\n \n+\tigc_ptp_tx_hang(adapter);\n+\n \t/* Reset the timer */\n \tif (!test_bit(__IGC_DOWN, &adapter->state)) {\n \t\tif (adapter->flags & IGC_FLAG_NEED_LINK_UPDATE)\ndiff --git a/drivers/net/ethernet/intel/igc/igc_ptp.c b/drivers/net/ethernet/intel/igc/igc_ptp.c\nindex b39d14d40ec9..b63a03157ec1 100644\n--- a/drivers/net/ethernet/intel/igc/igc_ptp.c\n+++ b/drivers/net/ethernet/intel/igc/igc_ptp.c\n@@ -284,6 +284,12 @@ static void igc_ptp_enable_tstamp_all_rxqueues(struct igc_adapter *adapter,\n * @adapter: networking device structure\n * @config: hwtstamp configuration\n *\n+ * Outgoing time stamping can be enabled and disabled. Play nice and\n+ * disable it when requested, although it shouldn't case any overhead\n+ * when no packet needs it. At most one packet in the queue may be\n+ * marked for time stamping, otherwise it would be impossible to tell\n+ * for sure to which packet the hardware time stamp belongs.\n+ *\n * Incoming time stamping has to be configured via the hardware\n * filters. Not all combinations are supported, in particular event\n * type has to be specified. Matching the kind of event packet is\n@@ -295,6 +301,7 @@ static int igc_ptp_set_timestamp_mode(struct igc_adapter *adapter,\n \t\t\t\t struct hwtstamp_config *config)\n {\n \tstruct igc_hw *hw = &adapter->hw;\n+\tu32 tsync_tx_ctl = IGC_TSYNCTXCTL_ENABLED;\n \tu32 tsync_rx_ctl = IGC_TSYNCRXCTL_ENABLED;\n \tu32 tsync_rx_cfg = 0;\n \tbool is_l4 = false;\n@@ -305,6 +312,15 @@ static int igc_ptp_set_timestamp_mode(struct igc_adapter *adapter,\n \tif (config->flags)\n \t\treturn -EINVAL;\n \n+\tswitch (config->tx_type) {\n+\tcase HWTSTAMP_TX_OFF:\n+\t\ttsync_tx_ctl = 0;\n+\tcase HWTSTAMP_TX_ON:\n+\t\tbreak;\n+\tdefault:\n+\t\treturn -ERANGE;\n+\t}\n+\n \tswitch (config->rx_filter) {\n \tcase HWTSTAMP_FILTER_NONE:\n \t\ttsync_rx_ctl = 0;\n@@ -368,6 +384,15 @@ static int igc_ptp_set_timestamp_mode(struct igc_adapter *adapter,\n \t\t}\n \t}\n \n+\tif (tsync_tx_ctl)\n+\t\ttsync_tx_ctl = IGC_TSYNCTXCTL_ENABLED;\n+\n+\t/* enable/disable TX */\n+\tregval = rd32(IGC_TSYNCTXCTL);\n+\tregval &= ~IGC_TSYNCTXCTL_ENABLED;\n+\tregval |= tsync_tx_ctl;\n+\twr32(IGC_TSYNCTXCTL, regval);\n+\n \t/* enable/disable RX */\n \tregval = rd32(IGC_TSYNCRXCTL);\n \tregval &= ~(IGC_TSYNCRXCTL_ENABLED | IGC_TSYNCRXCTL_TYPE_MASK);\n@@ -442,8 +467,75 @@ void igc_ptp_tx_hang(struct igc_adapter *adapter)\n \t}\n }\n \n+/**\n+ * igc_ptp_tx_hwtstamp - utility function which checks for TX time stamp\n+ * @adapter: Board private structure.\n+ *\n+ * If we were asked to do hardware stamping and such a time stamp is\n+ * available, then it must have been for this skb here because we only\n+ * allow only one such packet into the queue.\n+ */\n+static void igc_ptp_tx_hwtstamp(struct igc_adapter *adapter)\n+{\n+\tstruct sk_buff *skb = adapter->ptp_tx_skb;\n+\tstruct skb_shared_hwtstamps shhwtstamps;\n+\tstruct igc_hw *hw = &adapter->hw;\n+\tu64 regval;\n+\n+\tregval = rd32(IGC_TXSTMPL);\n+\tregval |= (u64)rd32(IGC_TXSTMPH) << 32;\n+\tigc_ptp_systim_to_hwtstamp(adapter, &shhwtstamps, regval);\n+\n+\t/* Clear the lock early before calling skb_tstamp_tx so that\n+\t * applications are not woken up before the lock bit is clear. We use\n+\t * a copy of the skb pointer to ensure other threads can't change it\n+\t * while we're notifying the stack.\n+\t */\n+\tadapter->ptp_tx_skb = NULL;\n+\tclear_bit_unlock(__IGC_PTP_TX_IN_PROGRESS, &adapter->state);\n+\n+\t/* Notify the stack and free the skb after we've unlocked */\n+\tskb_tstamp_tx(skb, &shhwtstamps);\n+\tdev_kfree_skb_any(skb);\n+}\n+\n+/**\n+ * igc_ptp_tx_work\n+ * @work: pointer to work struct\n+ *\n+ * This work function polls the TSYNCTXCTL valid bit to determine when a\n+ * timestamp has been taken for the current stored skb.\n+ */\n void igc_ptp_tx_work(struct work_struct *work)\n {\n+\tstruct igc_adapter *adapter = container_of(work, struct igc_adapter,\n+\t\t\t\t\t\t ptp_tx_work);\n+\tstruct igc_hw *hw = &adapter->hw;\n+\tu32 tsynctxctl;\n+\n+\tif (!adapter->ptp_tx_skb)\n+\t\treturn;\n+\n+\tif (time_is_before_jiffies(adapter->ptp_tx_start +\n+\t\t\t\t IGC_PTP_TX_TIMEOUT)) {\n+\t\tdev_kfree_skb_any(adapter->ptp_tx_skb);\n+\t\tadapter->ptp_tx_skb = NULL;\n+\t\tclear_bit_unlock(__IGC_PTP_TX_IN_PROGRESS, &adapter->state);\n+\t\tadapter->tx_hwtstamp_timeouts++;\n+\t\t/* Clear the tx valid bit in TSYNCTXCTL register to enable\n+\t\t * interrupt\n+\t\t */\n+\t\trd32(IGC_TXSTMPH);\n+\t\tdev_warn(&adapter->pdev->dev, \"clearing Tx timestamp hang\\n\");\n+\t\treturn;\n+\t}\n+\n+\ttsynctxctl = rd32(IGC_TSYNCTXCTL);\n+\tif (tsynctxctl & IGC_TSYNCTXCTL_VALID)\n+\t\tigc_ptp_tx_hwtstamp(adapter);\n+\telse\n+\t\t/* reschedule to check later */\n+\t\tschedule_work(&adapter->ptp_tx_work);\n }\n \n /**\n", "prefixes": [ "next-queue", "v1", "3/4" ] }