]> git.baikalelectronics.ru Git - kernel.git/commit
dmaengine: idxd: use spin_lock_irqsave before wait_event_lock_irq
authorRex Zhang <rex.zhang@intel.com>
Sat, 16 Sep 2023 06:06:19 +0000 (14:06 +0800)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Thu, 19 Oct 2023 21:08:58 +0000 (23:08 +0200)
commit01b19fc6621d2b10d2433b1f0259f5745e403cd9
tree0c6f78a921dcf3c94f8fddcbb4249c56ea4ba6b1
parent5b784489c8158518bf7a466bb3cc045b0fb66b4b
dmaengine: idxd: use spin_lock_irqsave before wait_event_lock_irq

[ Upstream commit c0409dd3d151f661e7e57b901a81a02565df163c ]

In idxd_cmd_exec(), wait_event_lock_irq() explicitly calls
spin_unlock_irq()/spin_lock_irq(). If the interrupt is on before entering
wait_event_lock_irq(), it will become off status after
wait_event_lock_irq() is called. Later, wait_for_completion() may go to
sleep but irq is disabled. The scenario is warned in might_sleep().

Fix it by using spin_lock_irqsave() instead of the primitive spin_lock()
to save the irq status before entering wait_event_lock_irq() and using
spin_unlock_irqrestore() instead of the primitive spin_unlock() to restore
the irq status before entering wait_for_completion().

Before the change:
idxd_cmd_exec() {
interrupt is on
spin_lock()                        // interrupt is on
wait_event_lock_irq()
spin_unlock_irq()  // interrupt is enabled
...
spin_lock_irq()    // interrupt is disabled
spin_unlock()                      // interrupt is still disabled
wait_for_completion()              // report "BUG: sleeping function
   // called from invalid context...
   // in_atomic() irqs_disabled()"
}

After applying spin_lock_irqsave():
idxd_cmd_exec() {
interrupt is on
spin_lock_irqsave()                // save the on state
   // interrupt is disabled
wait_event_lock_irq()
spin_unlock_irq()  // interrupt is enabled
...
spin_lock_irq()    // interrupt is disabled
spin_unlock_irqrestore()           // interrupt is restored to on
wait_for_completion()              // No Call trace
}

Fixes: f9f4082dbc56 ("dmaengine: idxd: remove interrupt disable for cmd_lock")
Signed-off-by: Rex Zhang <rex.zhang@intel.com>
Signed-off-by: Lijun Pan <lijun.pan@intel.com>
Reviewed-by: Dave Jiang <dave.jiang@intel.com>
Reviewed-by: Fenghua Yu <fenghua.yu@intel.com>
Link: https://lore.kernel.org/r/20230916060619.3744220-1-rex.zhang@intel.com
Signed-off-by: Vinod Koul <vkoul@kernel.org>
Signed-off-by: Sasha Levin <sashal@kernel.org>
drivers/dma/idxd/device.c