Skip to content

Commit

Permalink
accel/ivpu: Clear specific interrupt status bits on C0
Browse files Browse the repository at this point in the history
MTL C0 stepping fixed issue related to butrress interrupt status clearing,
to clear an interrupt status it is required to write 1 to specific
status bit field. This allows to execute read, modify and write routine.

Writing 0 will not clear the interrupt and will cause interrupt storm.

Fixes: 35b1376 ("accel/ivpu: Introduce a new DRM driver for Intel VPU")
Cc: [email protected] # 6.3.x
Signed-off-by: Karol Wachowski <[email protected]>
Reviewed-by: Jacek Lawrynowicz <[email protected]>
Signed-off-by: Stanislaw Gruszka <[email protected]>
Link: https://patchwork.freedesktop.org/patch/msgid/[email protected]
  • Loading branch information
Karol Wachowski authored and sgruszka committed Jul 5, 2023
1 parent 020b527 commit 7f34e01
Show file tree
Hide file tree
Showing 2 changed files with 13 additions and 6 deletions.
1 change: 1 addition & 0 deletions drivers/accel/ivpu/ivpu_drv.h
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,7 @@ struct ivpu_wa_table {
bool punit_disabled;
bool clear_runtime_mem;
bool d3hot_after_power_off;
bool interrupt_clear_with_0;
};

struct ivpu_hw_info;
Expand Down
18 changes: 12 additions & 6 deletions drivers/accel/ivpu/ivpu_hw_mtl.c
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,9 @@ static void ivpu_hw_wa_init(struct ivpu_device *vdev)
vdev->wa.punit_disabled = ivpu_is_fpga(vdev);
vdev->wa.clear_runtime_mem = false;
vdev->wa.d3hot_after_power_off = true;

if (ivpu_device_id(vdev) == PCI_DEVICE_ID_MTL && ivpu_revision(vdev) < 4)
vdev->wa.interrupt_clear_with_0 = true;
}

static void ivpu_hw_timeouts_init(struct ivpu_device *vdev)
Expand Down Expand Up @@ -973,12 +976,15 @@ static u32 ivpu_hw_mtl_irqb_handler(struct ivpu_device *vdev, int irq)
schedule_recovery = true;
}

/*
* Clear local interrupt status by writing 0 to all bits.
* This must be done after interrupts are cleared at the source.
* Writing 1 triggers an interrupt, so we can't perform read update write.
*/
REGB_WR32(MTL_BUTTRESS_INTERRUPT_STAT, 0x0);
/* This must be done after interrupts are cleared at the source. */
if (IVPU_WA(interrupt_clear_with_0))
/*
* Writing 1 triggers an interrupt, so we can't perform read update write.
* Clear local interrupt status by writing 0 to all bits.
*/
REGB_WR32(MTL_BUTTRESS_INTERRUPT_STAT, 0x0);
else
REGB_WR32(MTL_BUTTRESS_INTERRUPT_STAT, status);

/* Re-enable global interrupt */
REGB_WR32(MTL_BUTTRESS_GLOBAL_INT_MASK, 0x0);
Expand Down

0 comments on commit 7f34e01

Please sign in to comment.