]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
drm/xe/sysctrl: Add system controller interrupt handler
authorRaag Jadav <raag.jadav@intel.com>
Tue, 28 Apr 2026 05:48:24 +0000 (11:18 +0530)
committerRiana Tauro <riana.tauro@intel.com>
Thu, 30 Apr 2026 06:01:45 +0000 (11:31 +0530)
Add system controller interrupt handler which is denoted by 11th bit in
GFX master interrupt register. While at it, add worker for scheduling
system controller work.

Co-developed-by: Soham Purkait <soham.purkait@intel.com>
Signed-off-by: Soham Purkait <soham.purkait@intel.com>
Signed-off-by: Raag Jadav <raag.jadav@intel.com>
Reviewed-by: Mallesh Koujalagi <mallesh.koujalagi@intel.com>
Reviewed-by: Riana Tauro <riana.tauro@intel.com>
Link: https://patch.msgid.link/20260428054826.1202076-2-raag.jadav@intel.com
Signed-off-by: Riana Tauro <riana.tauro@intel.com>
drivers/gpu/drm/xe/regs/xe_irq_regs.h
drivers/gpu/drm/xe/xe_irq.c
drivers/gpu/drm/xe/xe_sysctrl.c
drivers/gpu/drm/xe/xe_sysctrl.h
drivers/gpu/drm/xe/xe_sysctrl_types.h

index 9d74f454d3ffd543fbe60a0eb18c7eb839085d68..1d6b976c4de0644af9b4804c39ef75d42adeeeea 100644 (file)
@@ -22,6 +22,7 @@
 #define   DISPLAY_IRQ                          REG_BIT(16)
 #define   SOC_H2DMEMINT_IRQ                    REG_BIT(13)
 #define   I2C_IRQ                              REG_BIT(12)
+#define   SYSCTRL_IRQ                          REG_BIT(11)
 #define   GT_DW_IRQ(x)                         REG_BIT(x)
 
 /*
index 7560a45f7f64ee043be8aa78d9a4beaa1f21e668..9e49e2241da41f1429e5467a0ef01470bcce0a26 100644 (file)
@@ -24,6 +24,7 @@
 #include "xe_mmio.h"
 #include "xe_pxp.h"
 #include "xe_sriov.h"
+#include "xe_sysctrl.h"
 #include "xe_tile.h"
 
 /*
@@ -525,6 +526,7 @@ static irqreturn_t dg1_irq_handler(int irq, void *arg)
                                xe_heci_csc_irq_handler(xe, master_ctl);
                        xe_display_irq_handler(xe, master_ctl);
                        xe_i2c_irq_handler(xe, master_ctl);
+                       xe_sysctrl_irq_handler(xe, master_ctl);
                        xe_mert_irq_handler(xe, master_ctl);
                        gu_misc_iir = gu_misc_irq_ack(xe, master_ctl);
                }
index 2bcef304eb9ac8371db3710d22e9929759f05e43..7de3e73bd8e032b96e231215b1264ca1b2f77bb4 100644 (file)
@@ -8,6 +8,7 @@
 
 #include <drm/drm_managed.h>
 
+#include "regs/xe_irq_regs.h"
 #include "regs/xe_sysctrl_regs.h"
 #include "xe_device.h"
 #include "xe_mmio.h"
 static void sysctrl_fini(void *arg)
 {
        struct xe_device *xe = arg;
+       struct xe_sysctrl *sc = &xe->sc;
 
+       disable_work_sync(&sc->work);
        xe->soc_remapper.set_sysctrl_region(xe, 0);
 }
 
+static void xe_sysctrl_work(struct work_struct *work)
+{
+}
+
 /**
  * xe_sysctrl_init() - Initialize System Controller subsystem
  * @xe: xe device instance
@@ -55,12 +62,6 @@ int xe_sysctrl_init(struct xe_device *xe)
        if (!xe->info.has_sysctrl)
                return 0;
 
-       xe->soc_remapper.set_sysctrl_region(xe, SYSCTRL_MAILBOX_INDEX);
-
-       ret = devm_add_action_or_reset(xe->drm.dev, sysctrl_fini, xe);
-       if (ret)
-               return ret;
-
        sc->mmio = devm_kzalloc(xe->drm.dev, sizeof(*sc->mmio), GFP_KERNEL);
        if (!sc->mmio)
                return -ENOMEM;
@@ -73,9 +74,29 @@ int xe_sysctrl_init(struct xe_device *xe)
        if (ret)
                return ret;
 
+       xe->soc_remapper.set_sysctrl_region(xe, SYSCTRL_MAILBOX_INDEX);
        xe_sysctrl_mailbox_init(sc);
+       INIT_WORK(&sc->work, xe_sysctrl_work);
+
+       return devm_add_action_or_reset(xe->drm.dev, sysctrl_fini, xe);
+}
+
+/**
+ * xe_sysctrl_irq_handler() - Handler for System Controller interrupts
+ * @xe: xe device instance
+ * @master_ctl: interrupt register
+ *
+ * Handle interrupts generated by System Controller.
+ */
+void xe_sysctrl_irq_handler(struct xe_device *xe, u32 master_ctl)
+{
+       struct xe_sysctrl *sc = &xe->sc;
+
+       if (!xe->info.has_sysctrl || !sc->work.func)
+               return;
 
-       return 0;
+       if (master_ctl & SYSCTRL_IRQ)
+               schedule_work(&sc->work);
 }
 
 /**
index f3b0f3716b2f7c8ff042014c9a40116e9a9ed8be..f7469bfc9324b7a093fe20f539171efe65820066 100644 (file)
@@ -17,6 +17,7 @@ static inline struct xe_device *sc_to_xe(struct xe_sysctrl *sc)
 }
 
 int xe_sysctrl_init(struct xe_device *xe);
+void xe_sysctrl_irq_handler(struct xe_device *xe, u32 master_ctl);
 void xe_sysctrl_pm_resume(struct xe_device *xe);
 
 #endif
index 8217f6befe702e542c9bae0912f7ee3ce233ac9a..5f408d6491ef4a0428c562aca618c912236358ef 100644 (file)
@@ -8,6 +8,7 @@
 
 #include <linux/mutex.h>
 #include <linux/types.h>
+#include <linux/workqueue_types.h>
 
 struct xe_mmio;
 
@@ -27,6 +28,9 @@ struct xe_sysctrl {
 
        /** @phase_bit: Message boundary phase toggle bit (0 or 1) */
        bool phase_bit;
+
+       /** @work: Pending events worker */
+       struct work_struct work;
 };
 
 #endif