Chris Wilson <chris@xxxxxxxxxxxxxxxxxx> writes: > From: Ben Widawsky <ben@xxxxxxxxxxxx> > > The docs specify this needs to be set on HSW GT1 parts. I've implemented it as > such since it should only be needed when using RC6, but it can probably go > anywhere. > > This patch fixes extremely reproducible hangs on our Jenkins setup. > > The interesting failure signature is: > IPEHR: 0x780c0000 (3DSTATE_VF) > INSTDONE_0: 0xffdfbffa (SVG + VS) > > This replaces the homebrew workaround we implemented in > > commit 2c550183476dfa25641309ae9a28d30feed14379 > Author: Chris Wilson <chris@xxxxxxxxxxxxxxxxxx> > Date: Tue Dec 16 10:02:27 2014 +0000 > > drm/i915: Disable PSMI sleep messages on all rings around context switches > > as that is coupled into HW semaphore support which is scheduled for > removal in the next patch. > > References: 2c550183476d ("drm/i915: Disable PSMI sleep messages on all rings around context switches") > Signed-off-by: Ben Widawsky <ben@xxxxxxxxxxxx> > Signed-off-by: Chris Wilson <chris@xxxxxxxxxxxxxxxxxx> > Cc: Mika Kuoppala <mika.kuoppala@xxxxxxxxxxxxxxx> Reviewed-by: Mika Kuoppala <mika.kuoppala@xxxxxxxxxxxxxxx> > --- > drivers/gpu/drm/i915/i915_drv.h | 2 + > drivers/gpu/drm/i915/i915_reg.h | 7 ++++ > drivers/gpu/drm/i915/intel_pm.c | 16 +++++++- > drivers/gpu/drm/i915/intel_ringbuffer.c | 49 ++----------------------- > 4 files changed, 27 insertions(+), 47 deletions(-) > > diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h > index d44255a8655e..24a5e63cc443 100644 > --- a/drivers/gpu/drm/i915/i915_drv.h > +++ b/drivers/gpu/drm/i915/i915_drv.h > @@ -2276,6 +2276,8 @@ intel_info(const struct drm_i915_private *dev_priv) > (dev_priv)->info.gt == 3) > #define IS_HSW_ULT(dev_priv) (IS_HASWELL(dev_priv) && \ > (INTEL_DEVID(dev_priv) & 0xFF00) == 0x0A00) > +#define IS_HSW_GT1(dev_priv) (IS_HASWELL(dev_priv) && \ > + (dev_priv)->info.gt == 1) > #define IS_HSW_GT3(dev_priv) (IS_HASWELL(dev_priv) && \ > (dev_priv)->info.gt == 3) > /* ULX machines are also considered ULT. */ > diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h > index 02af9b5add34..ca6a2e925194 100644 > --- a/drivers/gpu/drm/i915/i915_reg.h > +++ b/drivers/gpu/drm/i915/i915_reg.h > @@ -2464,6 +2464,13 @@ enum i915_power_well_id { > #define RING_DMA_FADD_UDW(base) _MMIO((base) + 0x60) /* gen8+ */ > #define RING_INSTPM(base) _MMIO((base) + 0xc0) > #define RING_MI_MODE(base) _MMIO((base) + 0x9c) > +#define RING_WAIT_FOR_RC6_EXIT(base) _MMIO((base) + 0xcc) > +#define RING_RC6_SEL_WRITE_ADDR_MASK (0x7 << 4) > +#define RING_RC6_SEL_WRITE_ADDR_MULTICAST (0x0 << 4) > +#define RING_RC6_SEL_WRITE_ADDR_UPPER_LEFT (0x4 << 4) > +#define RING_RC6_SEL_WRITE_ADDR_UPPER_RIGHT (0x5 << 4) > +#define RING_RC6_SEL_WRITE_ADDR_LOWER_LEFT (0x6 << 4) > +#define RING_RC6_SEL_WRITE_ADDR_LOWER_RIGHT (0x7 << 4) > #define INSTPS _MMIO(0x2070) /* 965+ only */ > #define GEN4_INSTDONE1 _MMIO(0x207c) /* 965+ only, aka INSTDONE_2 on SNB */ > #define ACTHD_I965 _MMIO(0x2074) > diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c > index 2a6ffb8b975a..c2e3502090c6 100644 > --- a/drivers/gpu/drm/i915/intel_pm.c > +++ b/drivers/gpu/drm/i915/intel_pm.c > @@ -7122,9 +7122,23 @@ static void gen6_enable_rc6(struct drm_i915_private *dev_priv) > I915_WRITE(GEN6_RC_EVALUATION_INTERVAL, 125000); > I915_WRITE(GEN6_RC_IDLE_HYSTERSIS, 25); > > - for_each_engine(engine, dev_priv, id) > + for_each_engine(engine, dev_priv, id) { > I915_WRITE(RING_MAX_IDLE(engine->mmio_base), 10); > > + /* > + * HSW GT1: "This field must be always [be] programmed to “100”, > + * this is required to address know [sic] HW issue." > + * > + * Failure to do so leads to a gpu hang on context load from > + * under rc6, with a characteristic IPEHR of 0x780c0000 (the > + * last command from the context image). > + */ > + if (IS_HSW_GT1(dev_priv)) > + I915_WRITE(RING_WAIT_FOR_RC6_EXIT(engine->mmio_base), > + _MASKED_FIELD(RING_RC6_SEL_WRITE_ADDR_MASK, > + RING_RC6_SEL_WRITE_ADDR_UPPER_LEFT)); > + } > + > I915_WRITE(GEN6_RC_SLEEP, 0); > I915_WRITE(GEN6_RC1e_THRESHOLD, 1000); > if (IS_IVYBRIDGE(dev_priv)) > diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c > index 65fd92eb071d..57f20033b19d 100644 > --- a/drivers/gpu/drm/i915/intel_ringbuffer.c > +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c > @@ -1602,12 +1602,6 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) > { > struct drm_i915_private *i915 = rq->i915; > struct intel_engine_cs *engine = rq->engine; > - enum intel_engine_id id; > - const int num_rings = > - /* Use an extended w/a on gen7 if signalling from other rings */ > - (HAS_LEGACY_SEMAPHORES(i915) && IS_GEN(i915, 7)) ? > - INTEL_INFO(i915)->num_rings - 1 : > - 0; > bool force_restore = false; > int len; > u32 *cs; > @@ -1621,7 +1615,7 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) > > len = 4; > if (IS_GEN(i915, 7)) > - len += 2 + (num_rings ? 4*num_rings + 6 : 0); > + len += 2; > if (flags & MI_FORCE_RESTORE) { > GEM_BUG_ON(flags & MI_RESTORE_INHIBIT); > flags &= ~MI_FORCE_RESTORE; > @@ -1634,23 +1628,8 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) > return PTR_ERR(cs); > > /* WaProgramMiArbOnOffAroundMiSetContext:ivb,vlv,hsw,bdw,chv */ > - if (IS_GEN(i915, 7)) { > + if (IS_GEN(i915, 7)) > *cs++ = MI_ARB_ON_OFF | MI_ARB_DISABLE; > - if (num_rings) { > - struct intel_engine_cs *signaller; > - > - *cs++ = MI_LOAD_REGISTER_IMM(num_rings); > - for_each_engine(signaller, i915, id) { > - if (signaller == engine) > - continue; > - > - *cs++ = i915_mmio_reg_offset( > - RING_PSMI_CTL(signaller->mmio_base)); > - *cs++ = _MASKED_BIT_ENABLE( > - GEN6_PSMI_SLEEP_MSG_DISABLE); > - } > - } > - } > > if (force_restore) { > /* > @@ -1681,30 +1660,8 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) > */ > *cs++ = MI_NOOP; > > - if (IS_GEN(i915, 7)) { > - if (num_rings) { > - struct intel_engine_cs *signaller; > - i915_reg_t last_reg = {}; /* keep gcc quiet */ > - > - *cs++ = MI_LOAD_REGISTER_IMM(num_rings); > - for_each_engine(signaller, i915, id) { > - if (signaller == engine) > - continue; > - > - last_reg = RING_PSMI_CTL(signaller->mmio_base); > - *cs++ = i915_mmio_reg_offset(last_reg); > - *cs++ = _MASKED_BIT_DISABLE( > - GEN6_PSMI_SLEEP_MSG_DISABLE); > - } > - > - /* Insert a delay before the next switch! */ > - *cs++ = MI_STORE_REGISTER_MEM | MI_SRM_LRM_GLOBAL_GTT; > - *cs++ = i915_mmio_reg_offset(last_reg); > - *cs++ = i915_scratch_offset(rq->i915); > - *cs++ = MI_NOOP; > - } > + if (IS_GEN(i915, 7)) > *cs++ = MI_ARB_ON_OFF | MI_ARB_ENABLE; > - } > > intel_ring_advance(rq, cs); > > -- > 2.20.1 _______________________________________________ Intel-gfx mailing list Intel-gfx@xxxxxxxxxxxxxxxxxxxxx https://lists.freedesktop.org/mailman/listinfo/intel-gfx