diff mbox series

[RFC,net-next,23/28] net: ethernet: ti: cpsw-proxy-client: add sw tx/rx irq coalescing

Message ID 20240518124234.2671651-24-s-vadapalli@ti.com (mailing list archive)
State RFC
Delegated to: Netdev Maintainers
Headers show
Series Add CPSW Proxy Client driver | expand

Checks

Context Check Description
netdev/series_format fail Series longer than 15 patches
netdev/tree_selection success Clearly marked for net-next
netdev/ynl success Generated files up to date; no warnings/errors; no diff in generated;
netdev/fixes_present success Fixes tag not required for -next series
netdev/header_inline success No static functions without inline keyword in header files
netdev/build_32bit fail Errors and warnings before: 24 this patch: 24
netdev/build_tools success No tools touched, skip
netdev/cc_maintainers warning 1 maintainers not CCed: linux-omap@vger.kernel.org
netdev/build_clang success Errors and warnings before: 8 this patch: 8
netdev/verify_signedoff success Signed-off-by tag matches author and committer
netdev/deprecated_api success None detected
netdev/check_selftest success No net selftest shell script
netdev/verify_fixes success No Fixes tag
netdev/build_allmodconfig_warn fail Errors and warnings before: 23 this patch: 23
netdev/checkpatch warning WARNING: line length of 83 exceeds 80 columns WARNING: line length of 89 exceeds 80 columns WARNING: line length of 92 exceeds 80 columns
netdev/build_clang_rust success No Rust files in patch. Skipping build
netdev/kdoc success Errors and warnings before: 0 this patch: 0
netdev/source_inline success Was 0 now: 0

Commit Message

s-vadapalli May 18, 2024, 12:42 p.m. UTC
Add coalescing support for the interrupts corresponding to the TX and RX
DMA Channels using hrtimer.

Signed-off-by: Siddharth Vadapalli <s-vadapalli@ti.com>
---
 drivers/net/ethernet/ti/cpsw-proxy-client.c | 57 +++++++++++++++++++--
 1 file changed, 53 insertions(+), 4 deletions(-)

Comments

Markus Elfring May 19, 2024, 2:12 p.m. UTC | #1
> +++ b/drivers/net/ethernet/ti/cpsw-proxy-client.c> @@ -996,8 +1001,15 @@ static int vport_tx_poll(struct napi_struct *napi_tx, int budget)> +		if (unlikely(tx_chn->tx_pace_timeout && !tdown)) {
> +			hrtimer_start(&tx_chn->tx_hrtimer,
> +				      ns_to_ktime(tx_chn->tx_pace_timeout),
> +				      HRTIMER_MODE_REL_PINNED);
> +		} else {
> +			enable_irq(tx_chn->irq);
> +		}> @@ -1179,12 +1191,38 @@ static int vport_rx_poll(struct napi_struct *napi_rx, int budget)> +			if (unlikely(rx_chn->rx_pace_timeout)) {
> +				hrtimer_start(&rx_chn->rx_hrtimer,
> +					      ns_to_ktime(rx_chn->rx_pace_timeout),
> +					      HRTIMER_MODE_REL_PINNED);
> +			} else {
> +				enable_irq(rx_chn->irq);
> +			}
…

Would you like to omit curly brackets at a few source code places?
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/Documentation/process/coding-style.rst?h=v6.9#n197

Regards,
Markus
diff mbox series

Patch

diff --git a/drivers/net/ethernet/ti/cpsw-proxy-client.c b/drivers/net/ethernet/ti/cpsw-proxy-client.c
index 450fc183eaac..408c9f78c059 100644
--- a/drivers/net/ethernet/ti/cpsw-proxy-client.c
+++ b/drivers/net/ethernet/ti/cpsw-proxy-client.c
@@ -58,13 +58,16 @@  struct rx_dma_chan {
 	struct k3_cppi_desc_pool	*desc_pool;
 	struct k3_udma_glue_rx_channel	*rx_chan;
 	struct napi_struct		napi_rx;
+	struct hrtimer			rx_hrtimer;
 	u32				rel_chan_idx;
 	u32				flow_base;
 	u32				flow_offset;
 	u32				thread_id;
 	u32				num_descs;
 	unsigned int			irq;
+	unsigned long			rx_pace_timeout;
 	char				rx_chan_name[CHAN_NAME_LEN];
+	bool				rx_irq_disabled;
 	bool				in_use;
 };
 
@@ -74,10 +77,12 @@  struct tx_dma_chan {
 	struct k3_cppi_desc_pool	*desc_pool;
 	struct k3_udma_glue_tx_channel	*tx_chan;
 	struct napi_struct		napi_tx;
+	struct hrtimer			tx_hrtimer;
 	u32				rel_chan_idx;
 	u32				thread_id;
 	u32				num_descs;
 	unsigned int			irq;
+	unsigned long			tx_pace_timeout;
 	char				tx_chan_name[CHAN_NAME_LEN];
 	bool				in_use;
 };
@@ -996,8 +1001,15 @@  static int vport_tx_poll(struct napi_struct *napi_tx, int budget)
 	if (num_tx >= budget)
 		return budget;
 
-	if (napi_complete_done(napi_tx, num_tx))
-		enable_irq(tx_chn->irq);
+	if (napi_complete_done(napi_tx, num_tx)) {
+		if (unlikely(tx_chn->tx_pace_timeout && !tdown)) {
+			hrtimer_start(&tx_chn->tx_hrtimer,
+				      ns_to_ktime(tx_chn->tx_pace_timeout),
+				      HRTIMER_MODE_REL_PINNED);
+		} else {
+			enable_irq(tx_chn->irq);
+		}
+	}
 
 	return 0;
 }
@@ -1179,12 +1191,38 @@  static int vport_rx_poll(struct napi_struct *napi_rx, int budget)
 		num_rx++;
 	}
 
-	if (num_rx < budget && napi_complete_done(napi_rx, num_rx))
-		enable_irq(rx_chn->irq);
+	if (num_rx < budget && napi_complete_done(napi_rx, num_rx)) {
+		if (rx_chn->rx_irq_disabled) {
+			rx_chn->rx_irq_disabled = false;
+			if (unlikely(rx_chn->rx_pace_timeout)) {
+				hrtimer_start(&rx_chn->rx_hrtimer,
+					      ns_to_ktime(rx_chn->rx_pace_timeout),
+					      HRTIMER_MODE_REL_PINNED);
+			} else {
+				enable_irq(rx_chn->irq);
+			}
+		}
+	}
 
 	return num_rx;
 }
 
+static enum hrtimer_restart vport_tx_timer_cb(struct hrtimer *timer)
+{
+	struct tx_dma_chan *tx_chn = container_of(timer, struct tx_dma_chan, tx_hrtimer);
+
+	enable_irq(tx_chn->irq);
+	return HRTIMER_NORESTART;
+}
+
+static enum hrtimer_restart vport_rx_timer_cb(struct hrtimer *timer)
+{
+	struct rx_dma_chan *rx_chn = container_of(timer, struct rx_dma_chan, rx_hrtimer);
+
+	enable_irq(rx_chn->irq);
+	return HRTIMER_NORESTART;
+}
+
 static u32 vport_get_link(struct net_device *ndev)
 {
 	struct virtual_port *vport = vport_ndev_to_vport(ndev);
@@ -1326,6 +1364,7 @@  static void vport_stop(struct virtual_port *vport)
 		k3_udma_glue_reset_tx_chn(tx_chn->tx_chan, tx_chn, vport_tx_cleanup);
 		k3_udma_glue_disable_tx_chn(tx_chn->tx_chan);
 		napi_disable(&tx_chn->napi_tx);
+		hrtimer_cancel(&tx_chn->tx_hrtimer);
 	}
 
 	for (i = 0; i < vport->num_rx_chan; i++) {
@@ -1336,6 +1375,7 @@  static void vport_stop(struct virtual_port *vport)
 		k3_udma_glue_reset_rx_chn(rx_chn->rx_chan, 0, rx_chn, vport_rx_cleanup,
 					  false);
 		napi_disable(&rx_chn->napi_rx);
+		hrtimer_cancel(&rx_chn->rx_hrtimer);
 	}
 }
 
@@ -1381,6 +1421,10 @@  static int vport_open(struct virtual_port *vport, netdev_features_t features)
 	for (i = 0; i < vport->num_rx_chan; i++) {
 		rx_chn = &vport->rx_chans[i];
 		napi_enable(&rx_chn->napi_rx);
+		if (rx_chn->rx_irq_disabled) {
+			rx_chn->rx_irq_disabled = false;
+			enable_irq(rx_chn->irq);
+		}
 	}
 
 	return 0;
@@ -1708,11 +1752,15 @@  static int init_netdev(struct cpsw_proxy_priv *proxy_priv, struct virtual_port *
 	for (i = 0; i < vport->num_tx_chan; i++) {
 		tx_chn = &vport->tx_chans[i];
 		netif_napi_add_tx(vport->ndev, &tx_chn->napi_tx, vport_tx_poll);
+		hrtimer_init(&tx_chn->tx_hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL_PINNED);
+		tx_chn->tx_hrtimer.function = &vport_tx_timer_cb;
 	}
 
 	for (i = 0; i < vport->num_rx_chan; i++) {
 		rx_chn = &vport->rx_chans[i];
 		netif_napi_add(vport->ndev, &rx_chn->napi_rx, vport_rx_poll);
+		hrtimer_init(&rx_chn->rx_hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL_PINNED);
+		rx_chn->rx_hrtimer.function = &vport_rx_timer_cb;
 	}
 
 	ret = register_netdev(vport->ndev);
@@ -1771,6 +1819,7 @@  static irqreturn_t rx_irq_handler(int irq, void *dev_id)
 {
 	struct rx_dma_chan *rx_chn = dev_id;
 
+	rx_chn->rx_irq_disabled = true;
 	disable_irq_nosync(irq);
 	napi_schedule(&rx_chn->napi_rx);