[PATCH v2 05/11] media: intel/ipu6: check irq_status mask before calling subdevice ISR

From: Valerii Sokolov

Date: Tue Nov 03 2026 - 16:11:23 EST


In ipu6_buttress_isr(), ipu6_buttress_call_isr(adev[i]) is called at the
start of each loop iteration, before checking whether irq_status has the
corresponding auxiliary device interrupt bit (adev_irq_mask[i]) set.

As a result, the ISYS and PSYS ISRs run on every Buttress interrupt
regardless of its source, and their return value is then discarded by
the continue statement. For the ISYS this means ipu6_isys_isr() taking a
runtime PM reference, masking and unmasking the UNISPART interrupts and
draining the firmware response queue on interrupts not meant for it.

Check irq_status against adev_irq_mask[i] before calling
ipu6_buttress_call_isr(adev[i]).

Fixes: ab29a2478e70 ("media: intel/ipu6: add IPU6 buttress interface driver")
Reviewed-by: Antti Laakso <antti.laakso@xxxxxxxxxxxxxxx>
Signed-off-by: Valerii Sokolov <valerii.sokolov@xxxxx>
---
drivers/media/pci/intel/ipu6/ipu6-buttress.c | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/media/pci/intel/ipu6/ipu6-buttress.c b/drivers/media/pci/intel/ipu6/ipu6-buttress.c
index f1d236054c..debc4ac929 100644
--- a/drivers/media/pci/intel/ipu6/ipu6-buttress.c
+++ b/drivers/media/pci/intel/ipu6/ipu6-buttress.c
@@ -364,11 +364,12 @@ irqreturn_t ipu6_buttress_isr(int irq, void *isp_ptr)
writel(irq_status, isp->base + regs->irq_clear);

for (i = 0; i < ARRAY_SIZE(adev_irq_mask); i++) {
- irqreturn_t r = ipu6_buttress_call_isr(adev[i]);
+ irqreturn_t r;

if (!(irq_status & adev_irq_mask[i]))
continue;

+ r = ipu6_buttress_call_isr(adev[i]);
if (r == IRQ_WAKE_THREAD) {
ret = IRQ_WAKE_THREAD;
disable_irqs |= adev_irq_mask[i];
--
2.56.0