Commit 5654a162 authored by Praveen Paneri's avatar Praveen Paneri Committed by Paulo Zanoni
Browse files

drm/i915: Fix FBC cfb stride programming for non X-tiled FB



When FBC is enabled for linear, legacy Y-tiled and Yf-tiled
surfaces on gen9, the cfb stride must be programmed by SW as

cfb_stride = ceiling[(at least plane width in pixels)/
		     (32 * compression limit factor)] * 8

v2: Minor fix for a build error
v3: Fixed subject, register name and platform check (Ville)
v4: Added WA details in comment (Paulo)
v5:
 - Read modified reg write to preserve other bit values (Paulo)
 - Store modified stride value in reg_params (Paulo)
 - Keep GLK out of the WA (Paulo)
v6:
 - added additional field in reg_params for gen9_wa_cfb_stride (Paulo)
 - Used appropriate bit mask while writing the register (Paulo)
v7 (from Paulo):
 - Fix coding style and spacing issues.
 - Mask the old values before writing.
 - Bikeshed comments and unnecessary checks.

Signed-off-by: default avatarPraveen Paneri <praveen.paneri@intel.com>
Signed-off-by: default avatarPaulo Zanoni <paulo.r.zanoni@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/1502389833-32621-1-git-send-email-praveen.paneri@intel.com
parent dfbd4508
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -1107,6 +1107,7 @@ struct intel_fbc {
		} fb;

		int cfb_size;
		unsigned int gen9_wa_cfb_stride;
	} params;

	struct intel_fbc_work {
+4 −0
Original line number Diff line number Diff line
@@ -6923,6 +6923,10 @@ enum {
#define  GLK_CL1_PWR_DOWN	(1 << 11)
#define  GLK_CL0_PWR_DOWN	(1 << 10)

#define CHICKEN_MISC_4		_MMIO(0x4208c)
#define   FBC_STRIDE_OVERRIDE	(1 << 13)
#define   FBC_STRIDE_MASK	0x1FFF

#define _CHICKEN_PIPESL_1_A	0x420b0
#define _CHICKEN_PIPESL_1_B	0x420b4
#define  HSW_FBCQ_DIS			(1 << 22)
+17 −0
Original line number Diff line number Diff line
@@ -291,6 +291,19 @@ static void gen7_fbc_activate(struct drm_i915_private *dev_priv)
	u32 dpfc_ctl;
	int threshold = dev_priv->fbc.threshold;

	/* Display WA #0529: skl, kbl, bxt. */
	if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv)) {
		u32 val = I915_READ(CHICKEN_MISC_4);

		val &= ~(FBC_STRIDE_OVERRIDE | FBC_STRIDE_MASK);

		if (i915_gem_object_get_tiling(params->vma->obj) !=
		    I915_TILING_X)
			val |= FBC_STRIDE_OVERRIDE | params->gen9_wa_cfb_stride;

		I915_WRITE(CHICKEN_MISC_4, val);
	}

	dpfc_ctl = 0;
	if (IS_IVYBRIDGE(dev_priv))
		dpfc_ctl |= IVB_DPFC_CTL_PLANE(params->crtc.plane);
@@ -883,6 +896,10 @@ static void intel_fbc_get_reg_params(struct intel_crtc *crtc,
	params->fb.stride = cache->fb.stride;

	params->cfb_size = intel_fbc_calculate_cfb_size(dev_priv, cache);

	if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv))
		params->gen9_wa_cfb_stride = DIV_ROUND_UP(cache->plane.src_w,
						32 * fbc->threshold) * 8;
}

static bool intel_fbc_reg_params_equal(struct intel_fbc_reg_params *params1,