[Intel-gfx] [PATCH 38/89] drm/i915/skl: Implement drm_plane vfuncs

Rodrigo Vivi rodrigo.vivi at gmail.com
Thu Sep 18 00:08:33 CEST 2014


On Thu, Sep 4, 2014 at 4:27 AM, Damien Lespiau <damien.lespiau at intel.com>
wrote:

> SKL Uses the same hardware for all planes now, so called "universal"
> planes. Ie both the primary planes and sprite planes share the same
> logic. This patch implements the drm_plane vfuncs for "sprites" ie
> planes that aren't the primary plane.
>
> v2: Couple of fixes:
>   - Actually enabled the planes and fix the plane number
>
> Signed-off-by: Damien Lespiau <damien.lespiau at intel.com>
> ---
>  drivers/gpu/drm/i915/i915_reg.h     |  31 +++++-
>  drivers/gpu/drm/i915/intel_sprite.c | 206
> +++++++++++++++++++++++++++++++++++-
>  2 files changed, 235 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/gpu/drm/i915/i915_reg.h
> b/drivers/gpu/drm/i915/i915_reg.h
> index c293dab..0159f2d 100644
> --- a/drivers/gpu/drm/i915/i915_reg.h
> +++ b/drivers/gpu/drm/i915/i915_reg.h
> @@ -4513,7 +4513,9 @@ enum punit_power_well {
>  #define   PLANE_CTL_FORMAT_INDEXED             ( 12 << 24)
>  #define   PLANE_CTL_FORMAT_RGB_565             ( 14 << 24)
>  #define   PLANE_CTL_PIPE_CSC_ENABLE            (1 << 23)
> -#define   PLANE_CTL_KEY_ENABLE                 (1 << 22)
> +#define   PLANE_CTL_KEY_ENABLE_MASK            (0x3 << 21)
> +#define   PLANE_CTL_KEY_ENABLE_SOURCE          (  1 << 21)
> +#define   PLANE_CTL_KEY_ENABLE_DESTINATION     (  2 << 21)
>

Oh ignore my comments on patch 12/89 regarding these bits! ;)


>  #define   PLANE_CTL_ORDER_BGRX                 (0 << 20)
>  #define   PLANE_CTL_ORDER_RGBX                 (1 << 20)
>  #define   PLANE_CTL_YUV422_ORDER_MASK          (0x3 << 16)
> @@ -4548,6 +4550,12 @@ enum punit_power_well {
>  #define _PLANE_OFFSET_1_A                      0x701a4
>  #define _PLANE_OFFSET_2_A                      0x702a4
>  #define _PLANE_OFFSET_3_A                      0x703a4
> +#define _PLANE_KEYVAL_1_A                      0x70194
> +#define _PLANE_KEYVAL_2_A                      0x70294
> +#define _PLANE_KEYMSK_1_A                      0x70198
> +#define _PLANE_KEYMSK_2_A                      0x70298
> +#define _PLANE_KEYMAX_1_A                      0x701a0
> +#define _PLANE_KEYMAX_2_A                      0x702a0
>
>  #define _PLANE_CTL_1_B                         0x71180
>  #define _PLANE_CTL_2_B                         0x71280
> @@ -4604,6 +4612,27 @@ enum punit_power_well {
>  #define PLANE_OFFSET(pipe, plane)      \
>         _PLANE(plane, _PLANE_OFFSET_1(pipe), _PLANE_OFFSET_2(pipe))
>
> +#define _PLANE_KEYVAL_1_B                      0x71194
> +#define _PLANE_KEYVAL_2_B                      0x71294
> +#define _PLANE_KEYVAL_1(pipe) _PIPE(pipe, _PLANE_KEYVAL_1_A,
> _PLANE_KEYVAL_1_B)
> +#define _PLANE_KEYVAL_2(pipe) _PIPE(pipe, _PLANE_KEYVAL_2_A,
> _PLANE_KEYVAL_2_B)
> +#define PLANE_KEYVAL(pipe, plane)      \
> +       _PLANE(plane, _PLANE_KEYVAL_1(pipe), _PLANE_KEYVAL_2(pipe))
> +
> +#define _PLANE_KEYMSK_1_B                      0x71198
> +#define _PLANE_KEYMSK_2_B                      0x71298
> +#define _PLANE_KEYMSK_1(pipe) _PIPE(pipe, _PLANE_KEYMSK_1_A,
> _PLANE_KEYMSK_1_B)
> +#define _PLANE_KEYMSK_2(pipe) _PIPE(pipe, _PLANE_KEYMSK_2_A,
> _PLANE_KEYMSK_2_B)
> +#define PLANE_KEYMSK(pipe, plane)      \
> +       _PLANE(plane, _PLANE_KEYMSK_1(pipe), _PLANE_KEYMSK_2(pipe))
> +
> +#define _PLANE_KEYMAX_1_B                      0x711a0
> +#define _PLANE_KEYMAX_2_B                      0x712a0
> +#define _PLANE_KEYMAX_1(pipe) _PIPE(pipe, _PLANE_KEYMAX_1_A,
> _PLANE_KEYMAX_1_B)
> +#define _PLANE_KEYMAX_2(pipe) _PIPE(pipe, _PLANE_KEYMAX_2_A,
> _PLANE_KEYMAX_2_B)
> +#define PLANE_KEYMAX(pipe, plane)      \
> +       _PLANE(plane, _PLANE_KEYMAX_1(pipe), _PLANE_KEYMAX_2(pipe))
> +
>  /* VBIOS regs */
>  #define VGACNTRL               0x71400
>  # define VGA_DISP_DISABLE                      (1 << 31)
> diff --git a/drivers/gpu/drm/i915/intel_sprite.c
> b/drivers/gpu/drm/i915/intel_sprite.c
> index 07a74ef..57e7190 100644
> --- a/drivers/gpu/drm/i915/intel_sprite.c
> +++ b/drivers/gpu/drm/i915/intel_sprite.c
> @@ -139,6 +139,184 @@ static void intel_update_primary_plane(struct
> intel_crtc *crtc)
>  }
>
>  static void
> +skl_update_plane(struct drm_plane *drm_plane, struct drm_crtc *crtc,
> +                struct drm_framebuffer *fb,
> +                struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
> +                unsigned int crtc_w, unsigned int crtc_h,
> +                uint32_t x, uint32_t y,
> +                uint32_t src_w, uint32_t src_h)
> +{
> +       struct drm_device *dev = drm_plane->dev;
> +       struct drm_i915_private *dev_priv = dev->dev_private;
> +       struct intel_plane *intel_plane = to_intel_plane(drm_plane);
> +       const int pipe = intel_plane->pipe;
> +       const int plane = intel_plane->plane + 1;


A comment above to remind skl doesn't have the primary would be good.


> +       u32 plane_ctl, stride;
> +       int pixel_size = drm_format_plane_cpp(fb->pixel_format, 0);
> +
> +       plane_ctl = I915_READ(PLANE_CTL(pipe, plane));
> +
> +       /* Mask out pixel format bits in case we change it */
> +       plane_ctl &= ~PLANE_CTL_FORMAT_MASK;
> +       plane_ctl &= ~PLANE_CTL_ORDER_RGBX;
> +       plane_ctl &= ~PLANE_CTL_YUV422_ORDER_MASK;
> +       plane_ctl &= ~PLANE_CTL_TILED_MASK;
> +       plane_ctl &= ~PLANE_CTL_ALPHA_MASK;
> +
> +       /* Trickle feed has to be enabled */
> +       plane_ctl &= ~PLANE_CTL_TRICKLE_FEED_DISABLE;
> +
> +       switch (fb->pixel_format) {
> +       case DRM_FORMAT_RGB565:
> +               plane_ctl |= PLANE_CTL_FORMAT_RGB_565;
> +               break;
> +       case DRM_FORMAT_XBGR8888:
> +               plane_ctl |= PLANE_CTL_FORMAT_XRGB_8888 |
> PLANE_CTL_ORDER_RGBX;
> +               break;
> +       case DRM_FORMAT_XRGB8888:
> +               plane_ctl |= PLANE_CTL_FORMAT_XRGB_8888;
> +               break;
> +       /*
> +        * XXX: For ARBG/ABGR formats we default to expecting scanout
> buffers
> +        * to be already pre-multiplied. We need to add a knob (or a
> different
> +        * DRM_FORMAT) for user-space to configure that.
> +        */
> +       case DRM_FORMAT_ABGR8888:
> +               plane_ctl |= PLANE_CTL_FORMAT_XRGB_8888 |
> +                            PLANE_CTL_ORDER_RGBX |
> +                            PLANE_CTL_ALPHA_SW_PREMULTIPLY;
> +               break;
> +       case DRM_FORMAT_ARGB8888:
> +               plane_ctl |= PLANE_CTL_FORMAT_XRGB_8888 |
> +                            PLANE_CTL_ALPHA_SW_PREMULTIPLY;
> +               break;
> +       case DRM_FORMAT_YUYV:
> +               plane_ctl |= PLANE_CTL_FORMAT_YUV422 |
> PLANE_CTL_YUV422_YUYV;
> +               break;
> +       case DRM_FORMAT_YVYU:
> +               plane_ctl |= PLANE_CTL_FORMAT_YUV422 |
> PLANE_CTL_YUV422_YVYU;
> +               break;
> +       case DRM_FORMAT_UYVY:
> +               plane_ctl |= PLANE_CTL_FORMAT_YUV422 |
> PLANE_CTL_YUV422_UYVY;
> +               break;
> +       case DRM_FORMAT_VYUY:
> +               plane_ctl |= PLANE_CTL_FORMAT_YUV422 |
> PLANE_CTL_YUV422_VYUY;
> +               break;
> +       default:
> +               BUG();
> +       }
> +
> +       switch (obj->tiling_mode) {
> +       case I915_TILING_NONE:
> +               stride = fb->pitches[0] >> 6;
> +               break;
> +       case I915_TILING_X:
> +               plane_ctl |= PLANE_CTL_TILED_X;
> +               stride = fb->pitches[0] >> 9;
> +               break;
> +       default:
> +               BUG();
> +       }
> +
> +       plane_ctl |= PLANE_CTL_ENABLE;
> +       plane_ctl |= PLANE_CTL_PIPE_CSC_ENABLE;
> +
> +       intel_update_sprite_watermarks(drm_plane, crtc, src_w, src_h,
> +                                      pixel_size, true,
> +                                      src_w != crtc_w || src_h != crtc_h);
> +
> +       /* Sizes are 0 based */
> +       src_w--;
> +       src_h--;
> +       crtc_w--;
> +       crtc_h--;
> +
> +       I915_WRITE(PLANE_OFFSET(pipe, plane), (y << 16) | x);
> +       I915_WRITE(PLANE_STRIDE(pipe, plane), stride);
> +       I915_WRITE(PLANE_POS(pipe, plane), (crtc_y << 16) | crtc_x);
> +       I915_WRITE(PLANE_SIZE(pipe, plane), (crtc_h << 16) | crtc_w);
> +       I915_WRITE(PLANE_CTL(pipe, plane), plane_ctl);
> +       I915_WRITE(PLANE_SURF(pipe, plane), i915_gem_obj_ggtt_offset(obj));
> +       POSTING_READ(PLANE_SURF(pipe, plane));
> +}
> +
> +static void
> +skl_disable_plane(struct drm_plane *drm_plane, struct drm_crtc *crtc)
> +{
> +       struct drm_device *dev = drm_plane->dev;
> +       struct drm_i915_private *dev_priv = dev->dev_private;
> +       struct intel_plane *intel_plane = to_intel_plane(drm_plane);
> +       const int pipe = intel_plane->pipe;
> +       const int plane = intel_plane->plane + 1;
> +
> +       I915_WRITE(PLANE_CTL(pipe, plane),
> +                  I915_READ(PLANE_CTL(pipe, plane)) & ~PLANE_CTL_ENABLE);
> +
> +       /* Activate double buffered register update */
> +       I915_WRITE(PLANE_CTL(pipe, plane), 0);
> +       POSTING_READ(PLANE_CTL(pipe, plane));
> +
> +       intel_update_sprite_watermarks(drm_plane, crtc, 0, 0, 0, false,
> false);
> +}
> +
> +static int
> +skl_update_colorkey(struct drm_plane *drm_plane,
> +                   struct drm_intel_sprite_colorkey *key)
> +{
> +       struct drm_device *dev = drm_plane->dev;
> +       struct drm_i915_private *dev_priv = dev->dev_private;
> +       struct intel_plane *intel_plane = to_intel_plane(drm_plane);
> +       const int pipe = intel_plane->pipe;
> +       const int plane = intel_plane->plane;
> +       u32 plane_ctl;
> +
> +       I915_WRITE(PLANE_KEYVAL(pipe, plane), key->min_value);
> +       I915_WRITE(PLANE_KEYMAX(pipe, plane), key->max_value);
> +       I915_WRITE(PLANE_KEYMSK(pipe, plane), key->channel_mask);
> +
> +       plane_ctl = I915_READ(PLANE_CTL(pipe, plane));
> +       plane_ctl &= ~PLANE_CTL_KEY_ENABLE_MASK;
> +       if (key->flags & I915_SET_COLORKEY_DESTINATION)
> +               plane_ctl |= PLANE_CTL_KEY_ENABLE_DESTINATION;
> +       else if (key->flags & I915_SET_COLORKEY_SOURCE)
> +               plane_ctl |= PLANE_CTL_KEY_ENABLE_SOURCE;
> +       I915_WRITE(PLANE_CTL(pipe, plane), plane_ctl);
> +
> +       POSTING_READ(PLANE_CTL(pipe, plane));
> +
> +       return 0;
> +}
> +
> +static void
> +skl_get_colorkey(struct drm_plane *drm_plane,
> +                struct drm_intel_sprite_colorkey *key)
> +{
> +       struct drm_device *dev = drm_plane->dev;
> +       struct drm_i915_private *dev_priv = dev->dev_private;
> +       struct intel_plane *intel_plane = to_intel_plane(drm_plane);
> +       const int pipe = intel_plane->pipe;
> +       const int plane = intel_plane->plane;
> +       u32 plane_ctl;
> +
> +       key->min_value = I915_READ(PLANE_KEYVAL(pipe, plane));
> +       key->max_value = I915_READ(PLANE_KEYMAX(pipe, plane));
> +       key->channel_mask = I915_READ(PLANE_KEYMSK(pipe, plane));
> +
> +       plane_ctl = I915_READ(PLANE_CTL(pipe, plane));
> +
> +       switch (plane_ctl & PLANE_CTL_KEY_ENABLE_MASK) {
> +       case PLANE_CTL_KEY_ENABLE_DESTINATION:
> +               key->flags = I915_SET_COLORKEY_DESTINATION;
> +               break;
> +       case PLANE_CTL_KEY_ENABLE_SOURCE:
> +               key->flags = I915_SET_COLORKEY_SOURCE;
> +               break;
> +       default:
> +               key->flags = I915_SET_COLORKEY_NONE;
> +       }
> +}
> +
> +static void
>  vlv_update_plane(struct drm_plane *dplane, struct drm_crtc *crtc,
>                  struct drm_framebuffer *fb,
>                  struct drm_i915_gem_object *obj, int crtc_x, int crtc_y,
> @@ -1305,6 +1483,18 @@ static uint32_t vlv_plane_formats[] = {
>         DRM_FORMAT_VYUY,
>  };
>
> +static uint32_t skl_plane_formats[] = {
> +       DRM_FORMAT_RGB565,
> +       DRM_FORMAT_ABGR8888,
> +       DRM_FORMAT_ARGB8888,
> +       DRM_FORMAT_XBGR8888,
> +       DRM_FORMAT_XRGB8888,
> +       DRM_FORMAT_YUYV,
> +       DRM_FORMAT_YVYU,
> +       DRM_FORMAT_UYVY,
> +       DRM_FORMAT_VYUY,
> +};
> +
>  int
>  intel_plane_init(struct drm_device *dev, enum pipe pipe, int plane)
>  {
> @@ -1368,7 +1558,21 @@ intel_plane_init(struct drm_device *dev, enum pipe
> pipe, int plane)
>                         num_plane_formats = ARRAY_SIZE(snb_plane_formats);
>                 }
>                 break;
> -
> +       case 9:
> +               /*
> +                * FIXME: Skylake planes can be scaled (with some
> restrictions),
> +                * but this is for another time.
> +                */
> +               intel_plane->can_scale = false;
> +               intel_plane->max_downscale = 1;
> +               intel_plane->update_plane = skl_update_plane;
> +               intel_plane->disable_plane = skl_disable_plane;
> +               intel_plane->update_colorkey = skl_update_colorkey;
> +               intel_plane->get_colorkey = skl_get_colorkey;
> +
> +               plane_formats = skl_plane_formats;
> +               num_plane_formats = ARRAY_SIZE(skl_plane_formats);
> +               break;
>         default:
>                 kfree(intel_plane);
>                 return -ENODEV;
> --
> 1.8.3.1
>
> _______________________________________________
> Intel-gfx mailing list
> Intel-gfx at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/intel-gfx
>


Reviewed-by: Rodrigo Vivi <rodrigo.vivi at intel.com>

-- 
Rodrigo Vivi
Blog: http://blog.vivi.eng.br
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.freedesktop.org/archives/intel-gfx/attachments/20140917/d2b1ff3e/attachment.html>


More information about the Intel-gfx mailing list