diff mbox series

[net-next] r8169: reduce number of workaround doorbell rings

Message ID 0a15a83c-aecf-ab51-8071-b29d9dcd529a@gmail.com (mailing list archive)
State Accepted
Commit 94d8a98e6235c2ac4d188e21cab6ea4d43c98806
Delegated to: Netdev Maintainers
Headers show
Series [net-next] r8169: reduce number of workaround doorbell rings | expand

Checks

Context Check Description
netdev/cover_letter success Link
netdev/fixes_present success Link
netdev/patch_count success Link
netdev/tree_selection success Clearly marked for net-next
netdev/subject_prefix success Link
netdev/source_inline success Was 0 now: 0
netdev/verify_signedoff success Link
netdev/module_param success Was 0 now: 0
netdev/build_32bit success Errors and warnings before: 0 this patch: 0
netdev/kdoc success Errors and warnings before: 0 this patch: 0
netdev/verify_fixes success Link
netdev/checkpatch success total: 0 errors, 0 warnings, 0 checks, 31 lines checked
netdev/build_allmodconfig_warn success Errors and warnings before: 0 this patch: 0
netdev/header_inline success Link
netdev/stable success Stable not CCed

Commit Message

Heiner Kallweit Nov. 19, 2020, 8:57 p.m. UTC
Some chip versions have a hw bug resulting in lost door bell rings.
To work around this the doorbell is also rung whenever we still have
tx descriptors in flight after having cleaned up tx descriptors.
These PCI(e) writes come at a cost, therefore let's reduce the number
of extra doorbell rings.
If skb is NULL then this means:
- last cleaned-up descriptor belongs to a skb with at least one fragment
  and last fragment isn't marked as sent yet
- hw is in progress sending the skb, therefore no extra doorbell ring
  is needed for this skb
- once last fragment is marked as transmitted hw will trigger
  a tx done interrupt and we come here again (with skb != NULL)
  and ring the doorbell if needed
Therefore skip the workaround doorbell ring if skb is NULL.

Signed-off-by: Heiner Kallweit <hkallweit1@gmail.com>
---
 drivers/net/ethernet/realtek/r8169_main.c | 7 +++++--
 1 file changed, 5 insertions(+), 2 deletions(-)

Comments

patchwork-bot+netdevbpf@kernel.org Nov. 21, 2020, 2:40 a.m. UTC | #1
Hello:

This patch was applied to netdev/net-next.git (refs/heads/master):

On Thu, 19 Nov 2020 21:57:27 +0100 you wrote:
> Some chip versions have a hw bug resulting in lost door bell rings.
> To work around this the doorbell is also rung whenever we still have
> tx descriptors in flight after having cleaned up tx descriptors.
> These PCI(e) writes come at a cost, therefore let's reduce the number
> of extra doorbell rings.
> If skb is NULL then this means:
> - last cleaned-up descriptor belongs to a skb with at least one fragment
>   and last fragment isn't marked as sent yet
> - hw is in progress sending the skb, therefore no extra doorbell ring
>   is needed for this skb
> - once last fragment is marked as transmitted hw will trigger
>   a tx done interrupt and we come here again (with skb != NULL)
>   and ring the doorbell if needed
> Therefore skip the workaround doorbell ring if skb is NULL.
> 
> [...]

Here is the summary with links:
  - [net-next] r8169: reduce number of workaround doorbell rings
    https://git.kernel.org/netdev/net-next/c/94d8a98e6235

You are awesome, thank you!
--
Deet-doot-dot, I am a bot.
https://korg.docs.kernel.org/patchwork/pwbot.html
diff mbox series

Patch

diff --git a/drivers/net/ethernet/realtek/r8169_main.c b/drivers/net/ethernet/realtek/r8169_main.c
index 1acf7128c..7dd643f53 100644
--- a/drivers/net/ethernet/realtek/r8169_main.c
+++ b/drivers/net/ethernet/realtek/r8169_main.c
@@ -4356,18 +4356,19 @@  static void rtl_tx(struct net_device *dev, struct rtl8169_private *tp,
 		   int budget)
 {
 	unsigned int dirty_tx, bytes_compl = 0, pkts_compl = 0;
+	struct sk_buff *skb;
 
 	dirty_tx = tp->dirty_tx;
 
 	while (READ_ONCE(tp->cur_tx) != dirty_tx) {
 		unsigned int entry = dirty_tx % NUM_TX_DESC;
-		struct sk_buff *skb = tp->tx_skb[entry].skb;
 		u32 status;
 
 		status = le32_to_cpu(tp->TxDescArray[entry].opts1);
 		if (status & DescOwn)
 			break;
 
+		skb = tp->tx_skb[entry].skb;
 		rtl8169_unmap_tx_skb(tp, entry);
 
 		if (skb) {
@@ -4397,8 +4398,10 @@  static void rtl_tx(struct net_device *dev, struct rtl8169_private *tp,
 		 * too close. Let's kick an extra TxPoll request when a burst
 		 * of start_xmit activity is detected (if it is not detected,
 		 * it is slow enough). -- FR
+		 * If skb is NULL then we come here again once a tx irq is
+		 * triggered after the last fragment is marked transmitted.
 		 */
-		if (tp->cur_tx != dirty_tx)
+		if (tp->cur_tx != dirty_tx && skb)
 			rtl8169_doorbell(tp);
 	}
 }