Re: [PATCH] workqueue: Use raise_softirq() in bh_pool_kick_.*()

From: Bradley Morgan

Date: Wed Aug 19 2026 - 10:34:13 EST


On 19 August 2026 15:19:09 BST, Sebastian Andrzej Siewior
<bigeasy@xxxxxxxxxxxxx> wrote:
>bh_pool_kick_normal() is used as irq_work callback to schedule softirq
>on a remote CPU.
>On PREEMPT_RT the default irq_work item is initialized as IRQ_WORK_LAZY
>and is invoked in a thread with enabled interrupts (!RT would use
>softirq but interrupts would remain enabled). This triggers the warning
>in raise_softirq_irqoff() which expects interrupts to off while the
>softirq irq mask is modified.
>
>The kick function triggers an IPI and the remote CPU
>wakes of irq_work/ and the callback wakes ksoftirqd/.
>
>By initialising the irq_work as IRQ_WORK_INIT_HARD via
>| *bh_pool_irq_work(pool) = IRQ_WORK_INIT_HARD(irq_work_fns[i]);
>we get the IPI and either (directly) a wake of ksoftirqd or "injected"
>the softirq into the current context if it is already in BH-disabled
>context which is in general undesired.
>Even if ksoftirqd is woken up, the softirq work could be picked up by
>random task which decided to do softirqs and then "drains" the pending
>queue.
>
>Scheduling a remote BH-work is undesired because of the possible context
>stealing. Using raise_softirq() here avoids the warning. As of today I
>did not see any users.
>
>Use raise_softirq() in bh_pool_kick_.*() to avoid a warning in
>PREEMPT_RT.
>

Well, sure, me personally don't see any issues in this code, makes life
easier

Reviewed-by: Bradley Morgan <include@xxxxxxxxx>



>Signed-off-by: Sebastian Andrzej Siewior <bigeasy@xxxxxxxxxxxxx>
>---
> kernel/workqueue.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
>diff --git a/kernel/workqueue.c b/kernel/workqueue.c
>index 78068ae8f28a6..0bb978df02005 100644
>--- a/kernel/workqueue.c
>+++ b/kernel/workqueue.c
>@@ -7923,12 +7923,12 @@ static inline void wq_watchdog_init(void) { }
>
> static void bh_pool_kick_normal(struct irq_work *irq_work)
> {
>- raise_softirq_irqoff(TASKLET_SOFTIRQ);
>+ raise_softirq(TASKLET_SOFTIRQ);
> }
>
> static void bh_pool_kick_highpri(struct irq_work *irq_work)
> {
>- raise_softirq_irqoff(HI_SOFTIRQ);
>+ raise_softirq(HI_SOFTIRQ);
> }
>
> static void __init restrict_unbound_cpumask(const char *name, const
> struct cpumask *mask)
>

Thanks!