drm/i915: Extend skl+ crc sources with more planes
authorVille Syrjälä <ville.syrjala@linux.intel.com>
Thu, 14 Feb 2019 19:22:19 +0000 (21:22 +0200)
committerVille Syrjälä <ville.syrjala@linux.intel.com>
Wed, 20 Feb 2019 20:52:31 +0000 (22:52 +0200)
On skl the crc registers were extended to provide plane crcs
for up to 7 planes. Add the new crc sources.

The current code uses the ivb+ register definitions for skl+
which does happen to work as the plane1, plane2, and dmux/pf
bits happen the match what ivb+ had. So no bug in the current
code.

v2: Drop the unused set_wa parameter (DK)

Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20190214192219.3858-4-ville.syrjala@linux.intel.com
Reviewed-by: Rodrigo Vivi <rodrigo.vivi@intel.com>
drivers/gpu/drm/i915/i915_drv.h
drivers/gpu/drm/i915/i915_reg.h
drivers/gpu/drm/i915/intel_pipe_crc.c

index a5a2f5b86b60deff19756604d3ca2608f29918db..bb0e75e439874d4a20f23ad63e727f79db151274 100644 (file)
@@ -1198,6 +1198,11 @@ enum intel_pipe_crc_source {
        INTEL_PIPE_CRC_SOURCE_NONE,
        INTEL_PIPE_CRC_SOURCE_PLANE1,
        INTEL_PIPE_CRC_SOURCE_PLANE2,
+       INTEL_PIPE_CRC_SOURCE_PLANE3,
+       INTEL_PIPE_CRC_SOURCE_PLANE4,
+       INTEL_PIPE_CRC_SOURCE_PLANE5,
+       INTEL_PIPE_CRC_SOURCE_PLANE6,
+       INTEL_PIPE_CRC_SOURCE_PLANE7,
        INTEL_PIPE_CRC_SOURCE_PIPE,
        /* TV/DP on pre-gen5/vlv can't use the pipe source. */
        INTEL_PIPE_CRC_SOURCE_TV,
index a5a47369cbd521bfde8188cc56e2cfa0e088e009..a44a9f8ab76d0d15c57905e195bec8a47319ac5d 100644 (file)
@@ -4017,6 +4017,15 @@ enum {
 /* Pipe A CRC regs */
 #define _PIPE_CRC_CTL_A                        0x60050
 #define   PIPE_CRC_ENABLE              (1 << 31)
+/* skl+ source selection */
+#define   PIPE_CRC_SOURCE_PLANE_1_SKL  (0 << 28)
+#define   PIPE_CRC_SOURCE_PLANE_2_SKL  (2 << 28)
+#define   PIPE_CRC_SOURCE_DMUX_SKL     (4 << 28)
+#define   PIPE_CRC_SOURCE_PLANE_3_SKL  (6 << 28)
+#define   PIPE_CRC_SOURCE_PLANE_4_SKL  (7 << 28)
+#define   PIPE_CRC_SOURCE_PLANE_5_SKL  (5 << 28)
+#define   PIPE_CRC_SOURCE_PLANE_6_SKL  (3 << 28)
+#define   PIPE_CRC_SOURCE_PLANE_7_SKL  (1 << 28)
 /* ivb+ source selection */
 #define   PIPE_CRC_SOURCE_PRIMARY_IVB  (0 << 29)
 #define   PIPE_CRC_SOURCE_SPRITE_IVB   (1 << 29)
index 66bb7b031537119a87cc850a6f16d06ffe7585e9..53d4ec68d3c455c42a01670448766175ded8a3fd 100644 (file)
@@ -34,6 +34,11 @@ static const char * const pipe_crc_sources[] = {
        [INTEL_PIPE_CRC_SOURCE_NONE] = "none",
        [INTEL_PIPE_CRC_SOURCE_PLANE1] = "plane1",
        [INTEL_PIPE_CRC_SOURCE_PLANE2] = "plane2",
+       [INTEL_PIPE_CRC_SOURCE_PLANE3] = "plane3",
+       [INTEL_PIPE_CRC_SOURCE_PLANE4] = "plane4",
+       [INTEL_PIPE_CRC_SOURCE_PLANE5] = "plane5",
+       [INTEL_PIPE_CRC_SOURCE_PLANE6] = "plane6",
+       [INTEL_PIPE_CRC_SOURCE_PLANE7] = "plane7",
        [INTEL_PIPE_CRC_SOURCE_PIPE] = "pipe",
        [INTEL_PIPE_CRC_SOURCE_TV] = "TV",
        [INTEL_PIPE_CRC_SOURCE_DP_B] = "DP-B",
@@ -368,6 +373,49 @@ static int ivb_pipe_crc_ctl_reg(struct drm_i915_private *dev_priv,
        return 0;
 }
 
+static int skl_pipe_crc_ctl_reg(struct drm_i915_private *dev_priv,
+                               enum pipe pipe,
+                               enum intel_pipe_crc_source *source,
+                               uint32_t *val)
+{
+       if (*source == INTEL_PIPE_CRC_SOURCE_AUTO)
+               *source = INTEL_PIPE_CRC_SOURCE_PIPE;
+
+       switch (*source) {
+       case INTEL_PIPE_CRC_SOURCE_PLANE1:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_PLANE_1_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_PLANE2:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_PLANE_2_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_PLANE3:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_PLANE_3_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_PLANE4:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_PLANE_4_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_PLANE5:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_PLANE_5_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_PLANE6:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_PLANE_6_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_PLANE7:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_PLANE_7_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_PIPE:
+               *val = PIPE_CRC_ENABLE | PIPE_CRC_SOURCE_DMUX_SKL;
+               break;
+       case INTEL_PIPE_CRC_SOURCE_NONE:
+               *val = 0;
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
 static int get_new_crc_ctl_reg(struct drm_i915_private *dev_priv,
                               enum pipe pipe,
                               enum intel_pipe_crc_source *source, u32 *val,
@@ -381,8 +429,10 @@ static int get_new_crc_ctl_reg(struct drm_i915_private *dev_priv,
                return vlv_pipe_crc_ctl_reg(dev_priv, pipe, source, val);
        else if (IS_GEN_RANGE(dev_priv, 5, 6))
                return ilk_pipe_crc_ctl_reg(source, val);
-       else
+       else if (INTEL_GEN(dev_priv) < 9)
                return ivb_pipe_crc_ctl_reg(dev_priv, pipe, source, val, set_wa);
+       else
+               return skl_pipe_crc_ctl_reg(dev_priv, pipe, source, val);
 }
 
 static int
@@ -482,6 +532,25 @@ static int ivb_crc_source_valid(struct drm_i915_private *dev_priv,
        }
 }
 
+static int skl_crc_source_valid(struct drm_i915_private *dev_priv,
+                               const enum intel_pipe_crc_source source)
+{
+       switch (source) {
+       case INTEL_PIPE_CRC_SOURCE_PIPE:
+       case INTEL_PIPE_CRC_SOURCE_PLANE1:
+       case INTEL_PIPE_CRC_SOURCE_PLANE2:
+       case INTEL_PIPE_CRC_SOURCE_PLANE3:
+       case INTEL_PIPE_CRC_SOURCE_PLANE4:
+       case INTEL_PIPE_CRC_SOURCE_PLANE5:
+       case INTEL_PIPE_CRC_SOURCE_PLANE6:
+       case INTEL_PIPE_CRC_SOURCE_PLANE7:
+       case INTEL_PIPE_CRC_SOURCE_NONE:
+               return 0;
+       default:
+               return -EINVAL;
+       }
+}
+
 static int
 intel_is_valid_crc_source(struct drm_i915_private *dev_priv,
                          const enum intel_pipe_crc_source source)
@@ -494,8 +563,10 @@ intel_is_valid_crc_source(struct drm_i915_private *dev_priv,
                return vlv_crc_source_valid(dev_priv, source);
        else if (IS_GEN_RANGE(dev_priv, 5, 6))
                return ilk_crc_source_valid(dev_priv, source);
-       else
+       else if (INTEL_GEN(dev_priv) < 9)
                return ivb_crc_source_valid(dev_priv, source);
+       else
+               return skl_crc_source_valid(dev_priv, source);
 }
 
 const char *const *intel_crtc_get_crc_sources(struct drm_crtc *crtc,