diff options
author | Robert Hancock <robert.hancock@calian.com> | 2023-01-16 23:08:34 +0100 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2023-01-18 15:26:37 +0100 |
commit | 8e7610e686d0943d0c340e0dc4425c44f6470074 (patch) | |
tree | 32de00b66fb0de731d9bd22a2c58bcbf6ceb13fd /drivers/net/ethernet/cadence/macb_ptp.c | |
parent | virtio_net: Reuse buffer free function (diff) | |
download | linux-8e7610e686d0943d0c340e0dc4425c44f6470074.tar.xz linux-8e7610e686d0943d0c340e0dc4425c44f6470074.zip |
net: macb: simplify TX timestamp handling
This driver was capturing the TX timestamp values from the TX ring
during the TX completion path, but deferring the actual packet TX
timestamp updating to a workqueue. There does not seem to be much of a
reason for this with the current state of the driver. Simplify this to
just do the TX timestamping as part of the TX completion path, to avoid
the need for the extra timestamp buffer and workqueue.
Signed-off-by: Robert Hancock <robert.hancock@calian.com>
Reviewed-by: Jacob Keller <jacob.e.keller@intel.com>
Reviewed-by: Claudiu Beznea <claudiu.beznea@microchip.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/ethernet/cadence/macb_ptp.c')
-rw-r--r-- | drivers/net/ethernet/cadence/macb_ptp.c | 83 |
1 files changed, 19 insertions, 64 deletions
diff --git a/drivers/net/ethernet/cadence/macb_ptp.c b/drivers/net/ethernet/cadence/macb_ptp.c index e6cb20aaa76a..f962a95068a0 100644 --- a/drivers/net/ethernet/cadence/macb_ptp.c +++ b/drivers/net/ethernet/cadence/macb_ptp.c @@ -292,79 +292,39 @@ void gem_ptp_rxstamp(struct macb *bp, struct sk_buff *skb, } } -static void gem_tstamp_tx(struct macb *bp, struct sk_buff *skb, - struct macb_dma_desc_ptp *desc_ptp) +void gem_ptp_txstamp(struct macb *bp, struct sk_buff *skb, + struct macb_dma_desc *desc) { struct skb_shared_hwtstamps shhwtstamps; - struct timespec64 ts; - - gem_hw_timestamp(bp, desc_ptp->ts_1, desc_ptp->ts_2, &ts); - memset(&shhwtstamps, 0, sizeof(shhwtstamps)); - shhwtstamps.hwtstamp = ktime_set(ts.tv_sec, ts.tv_nsec); - skb_tstamp_tx(skb, &shhwtstamps); -} - -int gem_ptp_txstamp(struct macb_queue *queue, struct sk_buff *skb, - struct macb_dma_desc *desc) -{ - unsigned long tail = READ_ONCE(queue->tx_ts_tail); - unsigned long head = queue->tx_ts_head; struct macb_dma_desc_ptp *desc_ptp; - struct gem_tx_ts *tx_timestamp; - - if (!GEM_BFEXT(DMA_TXVALID, desc->ctrl)) - return -EINVAL; + struct timespec64 ts; - if (CIRC_SPACE(head, tail, PTP_TS_BUFFER_SIZE) == 0) - return -ENOMEM; + if (!GEM_BFEXT(DMA_TXVALID, desc->ctrl)) { + dev_warn_ratelimited(&bp->pdev->dev, + "Timestamp not set in TX BD as expected\n"); + return; + } - desc_ptp = macb_ptp_desc(queue->bp, desc); + desc_ptp = macb_ptp_desc(bp, desc); /* Unlikely but check */ - if (!desc_ptp) - return -EINVAL; - skb_shinfo(skb)->tx_flags |= SKBTX_IN_PROGRESS; - tx_timestamp = &queue->tx_timestamps[head]; - tx_timestamp->skb = skb; + if (!desc_ptp) { + dev_warn_ratelimited(&bp->pdev->dev, + "Timestamp not supported in BD\n"); + return; + } + /* ensure ts_1/ts_2 is loaded after ctrl (TX_USED check) */ dma_rmb(); - tx_timestamp->desc_ptp.ts_1 = desc_ptp->ts_1; - tx_timestamp->desc_ptp.ts_2 = desc_ptp->ts_2; - /* move head */ - smp_store_release(&queue->tx_ts_head, - (head + 1) & (PTP_TS_BUFFER_SIZE - 1)); - - schedule_work(&queue->tx_ts_task); - return 0; -} + gem_hw_timestamp(bp, desc_ptp->ts_1, desc_ptp->ts_2, &ts); -static void gem_tx_timestamp_flush(struct work_struct *work) -{ - struct macb_queue *queue = - container_of(work, struct macb_queue, tx_ts_task); - unsigned long head, tail; - struct gem_tx_ts *tx_ts; - - /* take current head */ - head = smp_load_acquire(&queue->tx_ts_head); - tail = queue->tx_ts_tail; - - while (CIRC_CNT(head, tail, PTP_TS_BUFFER_SIZE)) { - tx_ts = &queue->tx_timestamps[tail]; - gem_tstamp_tx(queue->bp, tx_ts->skb, &tx_ts->desc_ptp); - /* cleanup */ - dev_kfree_skb_any(tx_ts->skb); - /* remove old tail */ - smp_store_release(&queue->tx_ts_tail, - (tail + 1) & (PTP_TS_BUFFER_SIZE - 1)); - tail = queue->tx_ts_tail; - } + memset(&shhwtstamps, 0, sizeof(shhwtstamps)); + shhwtstamps.hwtstamp = ktime_set(ts.tv_sec, ts.tv_nsec); + skb_tstamp_tx(skb, &shhwtstamps); } void gem_ptp_init(struct net_device *dev) { struct macb *bp = netdev_priv(dev); - struct macb_queue *queue; - unsigned int q; bp->ptp_clock_info = gem_ptp_caps_template; @@ -384,11 +344,6 @@ void gem_ptp_init(struct net_device *dev) } spin_lock_init(&bp->tsu_clk_lock); - for (q = 0, queue = bp->queues; q < bp->num_queues; ++q, ++queue) { - queue->tx_ts_head = 0; - queue->tx_ts_tail = 0; - INIT_WORK(&queue->tx_ts_task, gem_tx_timestamp_flush); - } gem_ptp_init_tsu(bp); |