Commit 2e2adb05 authored by Ville Syrjälä's avatar Ville Syrjälä Committed by Daniel Stone

drm/i915: Add render decompression support

SKL+ display engine can scan out certain kinds of compressed surfaces
produced by the render engine. This involved telling the display engine
the location of the color control surfae (CCS) which describes
which parts of the main surface are compressed and which are not. The
location of CCS is provided by userspace as just another plane with its
own offset.

Add the required stuff to validate the user provided AUX plane metadata
and convert the user provided linear offset into something the hardware
can consume.

Due to hardware limitations we require that the main surface and
the AUX surface (CCS) be part of the same bo. The hardware also
makes life hard by not allowing you to provide separate x/y offsets
for the main and AUX surfaces (excpet with NV12), so finding suitable
offsets for both requires a bit of work. Assuming we still want keep
playing tricks with the offsets. I've just gone with a dumb "search
backward for suitable offsets" approach, which is far from optimal,
but it works.

Also not all planes will be capable of scanning out compressed surfaces,
and eg. 90/270 degree rotation is not supported in combination with
decompression either.

This patch may contain work from at least the following people:
* Vandana Kannan <vandana.kannan@intel.com>
* Daniel Vetter <daniel@ffwll.ch>
* Ben Widawsky <ben@bwidawsk.net>

v2: Deal with display workarounds 0390, 0531, 1125 (Paulo)
v3: Pretend CCS tiles are regular 128 byte wide Y tiles (Jason)
    Put the AUX register defines to the correct place
    Fix up the slightly bogus rotation check
v4: Use I915_WRITE_FW() due to plane update locking changes
    s/return -EINVAL/goto err/ in intel_framebuffer_init()
    Eliminate a bunch hardcoded numbers in CCS code

v5: (By Ben)
conflict resolution +
-               res_blocks += fixed_16_16_to_u32_round_up(y_tile_minimum);
+               res_blocks += fixed16_to_u32_round_up(y_tile_minimum);

v6: (daniels) Fix botched commit message.

Cc: Paulo Zanoni <paulo.r.zanoni@intel.com>
Cc: Daniel Vetter <daniel@ffwll.ch>
Cc: Ben Widawsky <ben@bwidawsk.net>
Cc: Jason Ekstrand <jason@jlekstrand.net>
Signed-off-by: default avatarVille Syrjä <ville.syrjala@linux.intel.com>
Reviewed-by: Ben Widawsky <ben@bwidawsk.net> (v1)
Reviewed-by: default avatarDaniel Stone <daniels@collabora.com>
Signed-off-by: default avatarBen Widawsky <ben@bwidawsk.net>
Signed-off-by: default avatarDaniel Stone <daniels@collabora.com>
Link: http://patchwork.freedesktop.org/patch/msgid/20170801165817.7063-1-ben@bwidawsk.net
parent bbfb6ce8
......@@ -6199,6 +6199,10 @@ enum {
#define _PLANE_KEYMSK_2_A 0x70298
#define _PLANE_KEYMAX_1_A 0x701a0
#define _PLANE_KEYMAX_2_A 0x702a0
#define _PLANE_AUX_DIST_1_A 0x701c0
#define _PLANE_AUX_DIST_2_A 0x702c0
#define _PLANE_AUX_OFFSET_1_A 0x701c4
#define _PLANE_AUX_OFFSET_2_A 0x702c4
#define _PLANE_COLOR_CTL_1_A 0x701CC /* GLK+ */
#define _PLANE_COLOR_CTL_2_A 0x702CC /* GLK+ */
#define _PLANE_COLOR_CTL_3_A 0x703CC /* GLK+ */
......@@ -6305,6 +6309,24 @@ enum {
#define PLANE_NV12_BUF_CFG(pipe, plane) \
_MMIO_PLANE(plane, _PLANE_NV12_BUF_CFG_1(pipe), _PLANE_NV12_BUF_CFG_2(pipe))
#define _PLANE_AUX_DIST_1_B 0x711c0
#define _PLANE_AUX_DIST_2_B 0x712c0
#define _PLANE_AUX_DIST_1(pipe) \
_PIPE(pipe, _PLANE_AUX_DIST_1_A, _PLANE_AUX_DIST_1_B)
#define _PLANE_AUX_DIST_2(pipe) \
_PIPE(pipe, _PLANE_AUX_DIST_2_A, _PLANE_AUX_DIST_2_B)
#define PLANE_AUX_DIST(pipe, plane) \
_MMIO_PLANE(plane, _PLANE_AUX_DIST_1(pipe), _PLANE_AUX_DIST_2(pipe))
#define _PLANE_AUX_OFFSET_1_B 0x711c4
#define _PLANE_AUX_OFFSET_2_B 0x712c4
#define _PLANE_AUX_OFFSET_1(pipe) \
_PIPE(pipe, _PLANE_AUX_OFFSET_1_A, _PLANE_AUX_OFFSET_1_B)
#define _PLANE_AUX_OFFSET_2(pipe) \
_PIPE(pipe, _PLANE_AUX_OFFSET_2_A, _PLANE_AUX_OFFSET_2_B)
#define PLANE_AUX_OFFSET(pipe, plane) \
_MMIO_PLANE(plane, _PLANE_AUX_OFFSET_1(pipe), _PLANE_AUX_OFFSET_2(pipe))
#define _PLANE_COLOR_CTL_1_B 0x711CC
#define _PLANE_COLOR_CTL_2_B 0x712CC
#define _PLANE_COLOR_CTL_3_B 0x713CC
......@@ -6788,6 +6810,7 @@ enum {
# define CHICKEN3_DGMG_DONE_FIX_DISABLE (1 << 2)
#define CHICKEN_PAR1_1 _MMIO(0x42080)
#define SKL_RC_HASH_OUTSIDE (1 << 15)
#define DPA_MASK_VBLANK_SRD (1 << 15)
#define FORCE_ARB_IDLE_PLANES (1 << 14)
#define SKL_EDP_PSR_FIX_RDWRAP (1 << 3)
......
This diff is collapsed.
......@@ -62,6 +62,20 @@ static void gen9_init_clock_gating(struct drm_i915_private *dev_priv)
I915_WRITE(CHICKEN_PAR1_1,
I915_READ(CHICKEN_PAR1_1) | SKL_EDP_PSR_FIX_RDWRAP);
/*
* Display WA#0390: skl,bxt,kbl,glk
*
* Must match Sampler, Pixel Back End, and Media
* (0xE194 bit 8, 0x7014 bit 13, 0x4DDC bits 27 and 31).
*
* Including bits outside the page in the hash would
* require 2 (or 4?) MiB alignment of resources. Just
* assume the defaul hashing mode which only uses bits
* within the page.
*/
I915_WRITE(CHICKEN_PAR1_1,
I915_READ(CHICKEN_PAR1_1) & ~SKL_RC_HASH_OUTSIDE);
I915_WRITE(GEN8_CONFIG0,
I915_READ(GEN8_CONFIG0) | GEN9_DEFAULT_FIXES);
......@@ -4077,7 +4091,9 @@ skl_ddb_min_alloc(const struct drm_plane_state *pstate,
/* For Non Y-tile return 8-blocks */
if (fb->modifier != I915_FORMAT_MOD_Y_TILED &&
fb->modifier != I915_FORMAT_MOD_Yf_TILED)
fb->modifier != I915_FORMAT_MOD_Yf_TILED &&
fb->modifier != I915_FORMAT_MOD_Y_TILED_CCS &&
fb->modifier != I915_FORMAT_MOD_Yf_TILED_CCS)
return 8;
/*
......@@ -4383,7 +4399,9 @@ static int skl_compute_plane_wm(const struct drm_i915_private *dev_priv,
}
y_tiled = fb->modifier == I915_FORMAT_MOD_Y_TILED ||
fb->modifier == I915_FORMAT_MOD_Yf_TILED;
fb->modifier == I915_FORMAT_MOD_Yf_TILED ||
fb->modifier == I915_FORMAT_MOD_Y_TILED_CCS ||
fb->modifier == I915_FORMAT_MOD_Yf_TILED_CCS;
x_tiled = fb->modifier == I915_FORMAT_MOD_X_TILED;
/* Display WA #1141: kbl,cfl */
......@@ -4478,6 +4496,13 @@ static int skl_compute_plane_wm(const struct drm_i915_private *dev_priv,
res_lines = div_round_up_fixed16(selected_result,
plane_blocks_per_line);
/* Display WA #1125: skl,bxt,kbl,glk */
if (level == 0 &&
(fb->modifier == I915_FORMAT_MOD_Y_TILED_CCS ||
fb->modifier == I915_FORMAT_MOD_Yf_TILED_CCS))
res_blocks += fixed16_to_u32_round_up(y_tile_minimum);
/* Display WA #1126: skl,bxt,kbl,glk */
if (level >= 1 && level <= 7) {
if (y_tiled) {
res_blocks += fixed16_to_u32_round_up(y_tile_minimum);
......
......@@ -238,6 +238,7 @@ skl_update_plane(struct intel_plane *plane,
u32 surf_addr = plane_state->main.offset;
unsigned int rotation = plane_state->base.rotation;
u32 stride = skl_plane_stride(fb, 0, rotation);
u32 aux_stride = skl_plane_stride(fb, 1, rotation);
int crtc_x = plane_state->base.dst.x1;
int crtc_y = plane_state->base.dst.y1;
uint32_t crtc_w = drm_rect_width(&plane_state->base.dst);
......@@ -272,6 +273,10 @@ skl_update_plane(struct intel_plane *plane,
I915_WRITE_FW(PLANE_OFFSET(pipe, plane_id), (y << 16) | x);
I915_WRITE_FW(PLANE_STRIDE(pipe, plane_id), stride);
I915_WRITE_FW(PLANE_SIZE(pipe, plane_id), (src_h << 16) | src_w);
I915_WRITE_FW(PLANE_AUX_DIST(pipe, plane_id),
(plane_state->aux.offset - surf_addr) | aux_stride);
I915_WRITE_FW(PLANE_AUX_OFFSET(pipe, plane_id),
(plane_state->aux.y << 16) | plane_state->aux.x);
/* program plane scaler */
if (plane_state->scaler_id >= 0) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment