Add support fot vsync, vblank, and delayed vlank interrupts of
CMTG which are part of DE port interrupt.

v2:
- Use consistent DC3co check as used in earlier patches. [Uma]
- Use else-if instead of separate if block. [Uma]
- Merge mask and unmask function as it is similar. [Uma]
- Modify DISPLAY_VER() check. [Uma]

Signed-off-by: Animesh Manna <[email protected]>
---
 drivers/gpu/drm/i915/display/intel_cmtg.c     | 42 +++++++++++++++++++
 drivers/gpu/drm/i915/display/intel_cmtg.h     |  2 +
 .../gpu/drm/i915/display/intel_display_irq.c  | 12 ++++++
 .../gpu/drm/i915/display/intel_display_regs.h |  6 +++
 4 files changed, 62 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_cmtg.c 
b/drivers/gpu/drm/i915/display/intel_cmtg.c
index 2ebab6f56c8b..e70e4c0941d5 100644
--- a/drivers/gpu/drm/i915/display/intel_cmtg.c
+++ b/drivers/gpu/drm/i915/display/intel_cmtg.c
@@ -13,6 +13,7 @@
 #include "intel_crtc.h"
 #include "intel_de.h"
 #include "intel_display_device.h"
+#include "intel_display_irq.h"
 #include "intel_display_power.h"
 #include "intel_display_regs.h"
 #include "intel_display_types.h"
@@ -406,3 +407,44 @@ void intel_cmtg_enable_ddi(const struct intel_crtc_state 
*crtc_state)
 
        drm_dbg_kms(display->drm, "CMTG: %s enabled\n", 
transcoder_name(cpu_transcoder));
 }
+
+static void intel_cmtg_mask_interrupt(const struct intel_crtc_state 
*crtc_state, bool mask)
+{
+       struct intel_display *display = to_intel_display(crtc_state);
+       enum transcoder cpu_transcoder = crtc_state->cpu_transcoder;
+       u32 interrupt_mask = 0;
+
+       if (!intel_cmtg_is_supported(crtc_state))
+               return;
+
+       if (cpu_transcoder == TRANSCODER_A)
+               interrupt_mask = CMTG_VBLANK_A | CMTG_DELAYED_VBLANK_A | 
CMTG_VSYNC_A;
+       else if (cpu_transcoder == TRANSCODER_B)
+               interrupt_mask = CMTG_VBLANK_B | CMTG_DELAYED_VBLANK_B | 
CMTG_VSYNC_B;
+
+       if (mask)
+               bdw_update_port_irq(display, interrupt_mask, 0);
+       else
+               bdw_update_port_irq(display, interrupt_mask, interrupt_mask);
+}
+
+void intel_cmtg_enable_interrupt(const struct intel_crtc_state *crtc_state)
+{
+       struct intel_display *display = to_intel_display(crtc_state);
+
+       if (!intel_cmtg_is_allowed(crtc_state))
+               return;
+
+       spin_lock_irq(&display->irq.lock);
+       intel_cmtg_mask_interrupt(crtc_state, false);
+       spin_unlock_irq(&display->irq.lock);
+}
+
+void intel_cmtg_disable_interrupt(const struct intel_crtc_state *crtc_state)
+{
+       struct intel_display *display = to_intel_display(crtc_state);
+
+       spin_lock_irq(&display->irq.lock);
+       intel_cmtg_mask_interrupt(crtc_state, true);
+       spin_unlock_irq(&display->irq.lock);
+}
diff --git a/drivers/gpu/drm/i915/display/intel_cmtg.h 
b/drivers/gpu/drm/i915/display/intel_cmtg.h
index 79785afccc51..8fcb44d6398f 100644
--- a/drivers/gpu/drm/i915/display/intel_cmtg.h
+++ b/drivers/gpu/drm/i915/display/intel_cmtg.h
@@ -21,5 +21,7 @@ void intel_cmtg_set_timings(const struct intel_crtc_state 
*crtc_state, bool lrr)
 void intel_cmtg_set_clk_select(const struct intel_crtc_state *crtc_state);
 void intel_cmtg_sanitize(struct intel_display *display);
 bool intel_cmtg_is_allowed(const struct intel_crtc_state *crtc_state);
+void intel_cmtg_enable_interrupt(const struct intel_crtc_state *crtc_state);
+void intel_cmtg_disable_interrupt(const struct intel_crtc_state *crtc_state);
 
 #endif /* __INTEL_CMTG_H__ */
diff --git a/drivers/gpu/drm/i915/display/intel_display_irq.c 
b/drivers/gpu/drm/i915/display/intel_display_irq.c
index b5bfdebc66ca..cf5881d96587 100644
--- a/drivers/gpu/drm/i915/display/intel_display_irq.c
+++ b/drivers/gpu/drm/i915/display/intel_display_irq.c
@@ -1467,6 +1467,18 @@ void gen8_de_irq_handler(struct intel_display *display, 
u32 master_ctl)
                                found = true;
                        }
 
+                       if (DISPLAY_VER(display) == 35) {
+                               if (iir & (CMTG_VBLANK_A | CMTG_VSYNC_A | 
CMTG_DELAYED_VBLANK_A)) {
+                                       intel_handle_vblank(display, PIPE_A);
+                                       found = true;
+                               }
+
+                               if (iir & (CMTG_VBLANK_B | CMTG_VSYNC_B | 
CMTG_DELAYED_VBLANK_B)) {
+                                       intel_handle_vblank(display, PIPE_B);
+                                       found = true;
+                               }
+                       }
+
                        if (DISPLAY_VER(display) >= 11) {
                                u32 te_trigger = iir & (DSI0_TE | DSI1_TE);
 
diff --git a/drivers/gpu/drm/i915/display/intel_display_regs.h 
b/drivers/gpu/drm/i915/display/intel_display_regs.h
index bc508995ad8b..a5ffe5420b0b 100644
--- a/drivers/gpu/drm/i915/display/intel_display_regs.h
+++ b/drivers/gpu/drm/i915/display/intel_display_regs.h
@@ -1458,6 +1458,12 @@
 #define  GEN9_AUX_CHANNEL_B            (1 << 25)
 #define  DSI1_TE                       (1 << 24)
 #define  DSI0_TE                       (1 << 23)
+#define  CMTG_VSYNC_B                  (1 << 19)
+#define  CMTG_DELAYED_VBLANK_B         (1 << 18)
+#define  CMTG_VBLANK_B                 (1 << 17)
+#define  CMTG_VSYNC_A                  (1 << 16)
+#define  CMTG_DELAYED_VBLANK_A         (1 << 15)
+#define  CMTG_VBLANK_A                 (1 << 14)
 #define  GEN8_DE_PORT_HOTPLUG(hpd_pin) REG_BIT(3 + _HPD_PIN_DDI(hpd_pin))
 #define  BXT_DE_PORT_HOTPLUG_MASK      (GEN8_DE_PORT_HOTPLUG(HPD_PORT_A) | \
                                         GEN8_DE_PORT_HOTPLUG(HPD_PORT_B) | \
-- 
2.29.0

Reply via email to