linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] net: remove local_bh_enable during busy poll
@ 2025-08-29  3:04 Longjun Tang
  2025-09-01 20:23 ` Jakub Kicinski
  0 siblings, 1 reply; 4+ messages in thread
From: Longjun Tang @ 2025-08-29  3:04 UTC (permalink / raw)
  To: davem, edumazet, kuba, pabeni
  Cc: netdev, linux-kernel, tanglongjun, lange_tang

From: Longjun Tang <tanglongjun@kylinos.cn>

When CONFIG_NET_RX_BUSY_POLL==Y and net.core.busy_read > 0,
the __napi_busy_loop function calls napi_poll to perform busy polling,
such as in the case of virtio_net's virnet_poll. If interrupts are enabled
during the busy polling process, it is possible that data has already been
received and that last_used_idx is updated before the interrupt is handled.
This can lead to the vring_interrupt returning IRQ_NONE in response to the
interrupt because used_idx == last_used_idx, which is considered a spurious
interrupt.Once certain conditions are met, this interrupt can be disabled.

The local_bh_enable during the busy polling process allows softirq to be
executed and interrupt notification to be enabled. Removing local_bh_enable
will significantly reduce the number of unhandled interrupts.

Signed-off-by: Longjun Tang <tanglongjun@kylinos.cn>
---
 net/core/dev.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/net/core/dev.c b/net/core/dev.c
index 5a3c0f40a93f..f5737c551666 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -6763,12 +6763,12 @@ static void __napi_busy_loop(unsigned int napi_id,
 					LINUX_MIB_BUSYPOLLRXPACKETS, work);
 		skb_defer_free_flush(this_cpu_ptr(&softnet_data));
 		bpf_net_ctx_clear(bpf_net_ctx);
-		local_bh_enable();
 
 		if (!loop_end || loop_end(loop_end_arg, start_time))
 			break;
 
 		if (unlikely(need_resched())) {
+			local_bh_enable();
 			if (flags & NAPI_F_END_ON_RESCHED)
 				break;
 			if (napi_poll)
@@ -6784,6 +6784,7 @@ static void __napi_busy_loop(unsigned int napi_id,
 		}
 		cpu_relax();
 	}
+	local_bh_enable();
 	if (napi_poll)
 		busy_poll_stop(napi, have_poll_lock, flags, budget);
 	if (!IS_ENABLED(CONFIG_PREEMPT_RT))
-- 
2.48.1


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* Re: [PATCH] net: remove local_bh_enable during busy poll
  2025-08-29  3:04 [PATCH] net: remove local_bh_enable during busy poll Longjun Tang
@ 2025-09-01 20:23 ` Jakub Kicinski
  2025-09-02  8:53   ` Lange Tang
  0 siblings, 1 reply; 4+ messages in thread
From: Jakub Kicinski @ 2025-09-01 20:23 UTC (permalink / raw)
  To: Longjun Tang; +Cc: davem, edumazet, pabeni, netdev, linux-kernel, tanglongjun

On Fri, 29 Aug 2025 11:04:56 +0800 Longjun Tang wrote:
> When CONFIG_NET_RX_BUSY_POLL==Y and net.core.busy_read > 0,
> the __napi_busy_loop function calls napi_poll to perform busy polling,
> such as in the case of virtio_net's virnet_poll. If interrupts are enabled
> during the busy polling process, it is possible that data has already been
> received and that last_used_idx is updated before the interrupt is handled.
> This can lead to the vring_interrupt returning IRQ_NONE in response to the
> interrupt because used_idx == last_used_idx, which is considered a spurious
> interrupt.Once certain conditions are met, this interrupt can be disabled.

I'm not sure this patch completely fixes the issue you're describing.
It just makes it less likely to happen. Really, it feels like the onus
for fixing this is on the driver that can't discern its own IRQ sources.
-- 
pw-bot: cr

^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re:Re: [PATCH] net: remove local_bh_enable during busy poll
  2025-09-01 20:23 ` Jakub Kicinski
@ 2025-09-02  8:53   ` Lange Tang
  2025-09-02 10:34     ` Eric Dumazet
  0 siblings, 1 reply; 4+ messages in thread
From: Lange Tang @ 2025-09-02  8:53 UTC (permalink / raw)
  To: Jakub Kicinski
  Cc: davem@davemloft.net, edumazet@google.com, pabeni@redhat.com,
	netdev@vger.kernel.org, linux-kernel@vger.kernel.org,
	Tang Longjun

Thanks for your reply!

I've done some testing, pps=350000,net.core.busy_read=50.

Before apply this patch: unhandled ≈ 6400/s
After apply this patch: unhandled < 10/s

As you said, the driver needs to discern spurious interrupts in above describing situation, which I strongly agree with. and I also think that it's necessary to remove local_bh_enable during busy polling, as it causes interrupts to be enabled during the busy poll.

I think fix this issue requires two patches, in addition to this patch, another patch is needed from the driver side to discern spurious interrupts.






At 2025-09-02 04:23:30, "Jakub Kicinski" <kuba@kernel.org> wrote:
>On Fri, 29 Aug 2025 11:04:56 +0800 Longjun Tang wrote:
>> When CONFIG_NET_RX_BUSY_POLL==Y and net.core.busy_read > 0,
>> the __napi_busy_loop function calls napi_poll to perform busy polling,
>> such as in the case of virtio_net's virnet_poll. If interrupts are enabled
>> during the busy polling process, it is possible that data has already been
>> received and that last_used_idx is updated before the interrupt is handled.
>> This can lead to the vring_interrupt returning IRQ_NONE in response to the
>> interrupt because used_idx == last_used_idx, which is considered a spurious
>> interrupt.Once certain conditions are met, this interrupt can be disabled.
>
>I'm not sure this patch completely fixes the issue you're describing.
>It just makes it less likely to happen. Really, it feels like the onus
>for fixing this is on the driver that can't discern its own IRQ sources.
>-- 
>pw-bot: cr

^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: Re: [PATCH] net: remove local_bh_enable during busy poll
  2025-09-02  8:53   ` Lange Tang
@ 2025-09-02 10:34     ` Eric Dumazet
  0 siblings, 0 replies; 4+ messages in thread
From: Eric Dumazet @ 2025-09-02 10:34 UTC (permalink / raw)
  To: Lange Tang
  Cc: Jakub Kicinski, davem@davemloft.net, pabeni@redhat.com,
	netdev@vger.kernel.org, linux-kernel@vger.kernel.org,
	Tang Longjun

On Tue, Sep 2, 2025 at 1:53 AM Lange Tang <lange_tang@163.com> wrote:
>
> Thanks for your reply!
>
> I've done some testing, pps=350000,net.core.busy_read=50.

We can not let __napi_busy_loop() run for thousands of usec while blocking BH,
if net.core.busy_read=5000

To me, your patch is a no go.

Something is wrong in virtqueue_napi_complete() I think.


>
> Before apply this patch: unhandled ≈ 6400/s
> After apply this patch: unhandled < 10/s
>
> As you said, the driver needs to discern spurious interrupts in above describing situation, which I strongly agree with. and I also think that it's necessary to remove local_bh_enable during busy polling, as it causes interrupts to be enabled during the busy poll.
>
> I think fix this issue requires two patches, in addition to this patch, another patch is needed from the driver side to discern spurious interrupts.
>
>
>
>
>
>
> At 2025-09-02 04:23:30, "Jakub Kicinski" <kuba@kernel.org> wrote:
> >On Fri, 29 Aug 2025 11:04:56 +0800 Longjun Tang wrote:
> >> When CONFIG_NET_RX_BUSY_POLL==Y and net.core.busy_read > 0,
> >> the __napi_busy_loop function calls napi_poll to perform busy polling,
> >> such as in the case of virtio_net's virnet_poll. If interrupts are enabled
> >> during the busy polling process, it is possible that data has already been
> >> received and that last_used_idx is updated before the interrupt is handled.
> >> This can lead to the vring_interrupt returning IRQ_NONE in response to the
> >> interrupt because used_idx == last_used_idx, which is considered a spurious
> >> interrupt.Once certain conditions are met, this interrupt can be disabled.
> >
> >I'm not sure this patch completely fixes the issue you're describing.
> >It just makes it less likely to happen. Really, it feels like the onus
> >for fixing this is on the driver that can't discern its own IRQ sources.
> >--
> >pw-bot: cr

^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2025-09-02 10:34 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-08-29  3:04 [PATCH] net: remove local_bh_enable during busy poll Longjun Tang
2025-09-01 20:23 ` Jakub Kicinski
2025-09-02  8:53   ` Lange Tang
2025-09-02 10:34     ` Eric Dumazet

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).