[Intel-gfx] [PATCH] drm/i915: Init some CHV workarounds via LRIs in ring->init_context()
Chris Wilson
chris at chris-wilson.co.uk
Wed Aug 27 17:02:33 CEST 2014
On Wed, Aug 27, 2014 at 05:33:12PM +0300, ville.syrjala at linux.intel.com wrote:
> From: Ville Syrjälä <ville.syrjala at linux.intel.com>
>
> Follow the BDW example and apply the workarounds touching registers
> which are saved in the context image through LRIs in the new
> ring->init_context() hook.
>
> This makes Mesa much happier and eg. glxgears doesn't hang after
> the first frame.
>
> Cc: Arun Siluvery <arun.siluvery at linux.intel.com>
> Signed-off-by: Ville Syrjälä <ville.syrjala at linux.intel.com>
> ---
> drivers/gpu/drm/i915/intel_pm.c | 14 -------------
> drivers/gpu/drm/i915/intel_ringbuffer.c | 36 +++++++++++++++++++++++++++++++--
> 2 files changed, 34 insertions(+), 16 deletions(-)
>
> diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c
> index bbe65d5..437f25a 100644
> --- a/drivers/gpu/drm/i915/intel_pm.c
> +++ b/drivers/gpu/drm/i915/intel_pm.c
> @@ -5841,14 +5841,6 @@ static void cherryview_init_clock_gating(struct drm_device *dev)
>
> I915_WRITE(MI_ARB_VLV, MI_ARB_DISPLAY_TRICKLE_FEED_DISABLE);
>
> - /* WaDisablePartialInstShootdown:chv */
> - I915_WRITE(GEN8_ROW_CHICKEN,
> - _MASKED_BIT_ENABLE(PARTIAL_INSTRUCTION_SHOOTDOWN_DISABLE));
> -
> - /* WaDisableThreadStallDopClockGating:chv */
> - I915_WRITE(GEN8_ROW_CHICKEN,
> - _MASKED_BIT_ENABLE(STALL_DOP_GATING_DISABLE));
> -
> /* WaVSRefCountFullforceMissDisable:chv */
> /* WaDSRefCountFullforceMissDisable:chv */
> I915_WRITE(GEN7_FF_THREAD_MODE,
> @@ -5867,10 +5859,6 @@ static void cherryview_init_clock_gating(struct drm_device *dev)
> I915_WRITE(GEN8_UCGCTL6, I915_READ(GEN8_UCGCTL6) |
> GEN8_SDEUNIT_CLOCK_GATE_DISABLE);
>
> - /* WaDisableSamplerPowerBypass:chv (pre-production hw) */
> - I915_WRITE(HALF_SLICE_CHICKEN3,
> - _MASKED_BIT_ENABLE(GEN8_SAMPLER_POWER_BYPASS_DIS));
> -
> /* WaDisableGunitClockGating:chv (pre-production hw) */
> I915_WRITE(VLV_GUNIT_CLOCK_GATE, I915_READ(VLV_GUNIT_CLOCK_GATE) |
> GINT_DIS);
> @@ -5880,8 +5868,6 @@ static void cherryview_init_clock_gating(struct drm_device *dev)
> _MASKED_BIT_ENABLE(GEN8_FF_DOP_CLOCK_GATE_DISABLE));
>
> /* WaDisableDopClockGating:chv (pre-production hw) */
> - I915_WRITE(GEN7_ROW_CHICKEN2,
> - _MASKED_BIT_ENABLE(DOP_CLOCK_GATING_DISABLE));
> I915_WRITE(GEN6_UCGCTL1, I915_READ(GEN6_UCGCTL1) |
> GEN6_EU_TCUNIT_CLOCK_GATE_DISABLE);
> }
> diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c
> index cef8465..42d9b43 100644
> --- a/drivers/gpu/drm/i915/intel_ringbuffer.c
> +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c
> @@ -658,7 +658,7 @@ static inline void intel_ring_emit_wa(struct intel_engine_cs *ring,
> intel_ring_emit(ring, value);
> }
>
> -static int gen8_init_workarounds(struct intel_engine_cs *ring)
> +static int bdw_init_workarounds(struct intel_engine_cs *ring)
Sorry, these are continuing naming gripes.
*_ring_init_context so that there isn't that much disconnect between
vfunc and function.
> {
> int ret;
>
> @@ -728,6 +728,35 @@ static int gen8_init_workarounds(struct intel_engine_cs *ring)
> return 0;
> }
>
> +static int chv_init_workarounds(struct intel_engine_cs *ring)
> +{
> + int ret;
> +
> + ret = intel_ring_begin(ring, 12);
> + if (ret)
> + return ret;
> +
> + /* WaDisablePartialInstShootdown:chv */
> + intel_ring_emit_wa(ring, GEN8_ROW_CHICKEN,
> + _MASKED_BIT_ENABLE(PARTIAL_INSTRUCTION_SHOOTDOWN_DISABLE));
intel_ring_emit_lri();
However, if we get fancy, you can do these 4 in a single command
intel_ring_emit(ring, MI_LOAD_REGISTER_IMM(3));
intel_ring_emit(ring, GEN8_ROW_CHICKEN);
intel_ring_emit(ring,
_MASKED_BIT_ENABLE(PARTIAL_INSTRUCTION_SHOOTDOWN_DISABLE) |
_MASKED_BIT_ENABLE(STALL_DOP_GATING_DISABLE));
(perhaps even intel_ring_emit_pair(ring, reg, value))
intel_ring_emit(ring, GEN7_ROW_CHICKEN2);
intel_ring_emit(ring,
_MASKED_BIT_ENABLE(DOP_CLOCK_GATING_DISABLE));
intel_ring_emit(ring, HALF_SLICE_CHICKEN3,
intel_ring_emit(ring,
_MASKED_BIT_ENABLE(GEN8_SAMPLER_POWER_BYPASS_DIS));
hmm, actually if you do
int
i915_request_emit_lri(rq, int num_registers, ...)
{
struct intel_ringbuffer *ring;
va_list ap;
ring = intel_ring_begin(rq, 2*num_registers + 2);
if (IS_ERR(ring))
return PTR_ERR(ring);
va_start(ap, num_registers);
intel_ring_emit(ring, MI_LOAD_REGISTER_IMM(num_registers));
while (num_registers--) {
intel_ring_emit(ring, va_arg(ap, u32));
intel_ring_emit(ring, va_arg(ap, u32));
}
intel_ring_emit(ring, MI_NOOP);
intel_ring_advance(ring);
return 0;
}
then
static int chv_ring_init_context(struct i915_request *rq)
{
return i915_request_emit_lri(rq, 3,
/* WaDisablePartialInstShootdown:chv */
/* WaDisableThreadStallDopClockGating:chv */
GEN8_ROW_CHICKEN,
_MASKED_BIT_ENABLE(PARTIAL_INSTRUCTION_SHOOTDOWN_DISABLE) |
_MASKED_BIT_ENABLE(STALL_DOP_GATING_DISABLE)
/* WaDisableDopClockGating:chv (pre-production hw) */
GEN7_ROW_CHICKEN2,
_MASKED_BIT_ENABLE(DOP_CLOCK_GATING_DISABLE),
/* WaDisableSamplerPowerBypass:chv (pre-production hw) */
HALF_SLICE_CHICKEN3,
_MASKED_BIT_ENABLE(GEN8_SAMPLER_POWER_BYPASS_DIS));
}
Just not fond of intel_ring_emit_lri() as we the current
intel_ring_emit* style should not be calling intel_ring_begin() itself.
-Chris
--
Chris Wilson, Intel Open Source Technology Centre
More information about the Intel-gfx
mailing list