From 8f98d4baf0ddd4b4efdd9db69467bad482ff59ab Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Tue, 4 Dec 2018 14:15:18 +0000 Subject: [PATCH 001/118] drm/i915/selftests: Reorder request allocation vs vma pinning Impose a restraint that we have all vma pinned for a request prior to its allocation. This is to simplify request construction, and should facilitate unravelling the lock interdependencies later. Signed-off-by: Chris Wilson Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181204141522.13640-3-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/selftests/huge_pages.c | 33 ++-- drivers/gpu/drm/i915/selftests/igt_spinner.c | 106 ++++++------- .../gpu/drm/i915/selftests/intel_hangcheck.c | 149 +++++++++--------- 3 files changed, 143 insertions(+), 145 deletions(-) diff --git a/drivers/gpu/drm/i915/selftests/huge_pages.c b/drivers/gpu/drm/i915/selftests/huge_pages.c index 26c065c8d2c0..a0c7cbc212ba 100644 --- a/drivers/gpu/drm/i915/selftests/huge_pages.c +++ b/drivers/gpu/drm/i915/selftests/huge_pages.c @@ -972,7 +972,6 @@ static int gpu_write(struct i915_vma *vma, { struct i915_request *rq; struct i915_vma *batch; - int flags = 0; int err; GEM_BUG_ON(!intel_engine_can_store_dword(engine)); @@ -981,14 +980,14 @@ static int gpu_write(struct i915_vma *vma, if (err) return err; - rq = i915_request_alloc(engine, ctx); - if (IS_ERR(rq)) - return PTR_ERR(rq); - batch = gpu_write_dw(vma, dword * sizeof(u32), value); - if (IS_ERR(batch)) { - err = PTR_ERR(batch); - goto err_request; + if (IS_ERR(batch)) + return PTR_ERR(batch); + + rq = i915_request_alloc(engine, ctx); + if (IS_ERR(rq)) { + err = PTR_ERR(rq); + goto err_batch; } err = i915_vma_move_to_active(batch, rq, 0); @@ -996,21 +995,21 @@ static int gpu_write(struct i915_vma *vma, goto err_request; i915_gem_object_set_active_reference(batch->obj); - i915_vma_unpin(batch); - i915_vma_close(batch); - - err = engine->emit_bb_start(rq, - batch->node.start, batch->node.size, - flags); - if (err) - goto err_request; err = i915_vma_move_to_active(vma, rq, EXEC_OBJECT_WRITE); if (err) - i915_request_skip(rq, err); + goto err_request; + err = engine->emit_bb_start(rq, + batch->node.start, batch->node.size, + 0); err_request: + if (err) + i915_request_skip(rq, err); i915_request_add(rq); +err_batch: + i915_vma_unpin(batch); + i915_vma_close(batch); return err; } diff --git a/drivers/gpu/drm/i915/selftests/igt_spinner.c b/drivers/gpu/drm/i915/selftests/igt_spinner.c index 8cd34f6e6859..0e70df0230b8 100644 --- a/drivers/gpu/drm/i915/selftests/igt_spinner.c +++ b/drivers/gpu/drm/i915/selftests/igt_spinner.c @@ -68,49 +68,66 @@ static u64 hws_address(const struct i915_vma *hws, return hws->node.start + seqno_offset(rq->fence.context); } -static int emit_recurse_batch(struct igt_spinner *spin, - struct i915_request *rq, - u32 arbitration_command) +static int move_to_active(struct i915_vma *vma, + struct i915_request *rq, + unsigned int flags) { - struct i915_address_space *vm = &rq->gem_context->ppgtt->vm; - struct i915_vma *hws, *vma; - u32 *batch; int err; - vma = i915_vma_instance(spin->obj, vm, NULL); - if (IS_ERR(vma)) - return PTR_ERR(vma); - - hws = i915_vma_instance(spin->hws, vm, NULL); - if (IS_ERR(hws)) - return PTR_ERR(hws); - - err = i915_vma_pin(vma, 0, 0, PIN_USER); + err = i915_vma_move_to_active(vma, rq, flags); if (err) return err; - err = i915_vma_pin(hws, 0, 0, PIN_USER); - if (err) - goto unpin_vma; - - err = i915_vma_move_to_active(vma, rq, 0); - if (err) - goto unpin_hws; - if (!i915_gem_object_has_active_reference(vma->obj)) { i915_gem_object_get(vma->obj); i915_gem_object_set_active_reference(vma->obj); } - err = i915_vma_move_to_active(hws, rq, 0); - if (err) - goto unpin_hws; + return 0; +} - if (!i915_gem_object_has_active_reference(hws->obj)) { - i915_gem_object_get(hws->obj); - i915_gem_object_set_active_reference(hws->obj); +struct i915_request * +igt_spinner_create_request(struct igt_spinner *spin, + struct i915_gem_context *ctx, + struct intel_engine_cs *engine, + u32 arbitration_command) +{ + struct i915_address_space *vm = &ctx->ppgtt->vm; + struct i915_request *rq = NULL; + struct i915_vma *hws, *vma; + u32 *batch; + int err; + + vma = i915_vma_instance(spin->obj, vm, NULL); + if (IS_ERR(vma)) + return ERR_CAST(vma); + + hws = i915_vma_instance(spin->hws, vm, NULL); + if (IS_ERR(hws)) + return ERR_CAST(hws); + + err = i915_vma_pin(vma, 0, 0, PIN_USER); + if (err) + return ERR_PTR(err); + + err = i915_vma_pin(hws, 0, 0, PIN_USER); + if (err) + goto unpin_vma; + + rq = i915_request_alloc(engine, ctx); + if (IS_ERR(rq)) { + err = PTR_ERR(rq); + goto unpin_hws; } + err = move_to_active(vma, rq, 0); + if (err) + goto cancel_rq; + + err = move_to_active(hws, rq, 0); + if (err) + goto cancel_rq; + batch = spin->batch; *batch++ = MI_STORE_DWORD_IMM_GEN4; @@ -127,35 +144,18 @@ static int emit_recurse_batch(struct igt_spinner *spin, i915_gem_chipset_flush(spin->i915); - err = rq->engine->emit_bb_start(rq, vma->node.start, PAGE_SIZE, 0); + err = engine->emit_bb_start(rq, vma->node.start, PAGE_SIZE, 0); +cancel_rq: + if (err) { + i915_request_skip(rq, err); + i915_request_add(rq); + } unpin_hws: i915_vma_unpin(hws); unpin_vma: i915_vma_unpin(vma); - return err; -} - -struct i915_request * -igt_spinner_create_request(struct igt_spinner *spin, - struct i915_gem_context *ctx, - struct intel_engine_cs *engine, - u32 arbitration_command) -{ - struct i915_request *rq; - int err; - - rq = i915_request_alloc(engine, ctx); - if (IS_ERR(rq)) - return rq; - - err = emit_recurse_batch(spin, rq, arbitration_command); - if (err) { - i915_request_add(rq); - return ERR_PTR(err); - } - - return rq; + return err ? ERR_PTR(err) : rq; } static u32 diff --git a/drivers/gpu/drm/i915/selftests/intel_hangcheck.c b/drivers/gpu/drm/i915/selftests/intel_hangcheck.c index 40efbed611de..60a4bd9405be 100644 --- a/drivers/gpu/drm/i915/selftests/intel_hangcheck.c +++ b/drivers/gpu/drm/i915/selftests/intel_hangcheck.c @@ -103,53 +103,88 @@ static u64 hws_address(const struct i915_vma *hws, return hws->node.start + offset_in_page(sizeof(u32)*rq->fence.context); } -static int emit_recurse_batch(struct hang *h, - struct i915_request *rq) +static int move_to_active(struct i915_vma *vma, + struct i915_request *rq, + unsigned int flags) { - struct drm_i915_private *i915 = h->i915; - struct i915_address_space *vm = - rq->gem_context->ppgtt ? - &rq->gem_context->ppgtt->vm : - &i915->ggtt.vm; - struct i915_vma *hws, *vma; - unsigned int flags; - u32 *batch; int err; - vma = i915_vma_instance(h->obj, vm, NULL); - if (IS_ERR(vma)) - return PTR_ERR(vma); - - hws = i915_vma_instance(h->hws, vm, NULL); - if (IS_ERR(hws)) - return PTR_ERR(hws); - - err = i915_vma_pin(vma, 0, 0, PIN_USER); + err = i915_vma_move_to_active(vma, rq, flags); if (err) return err; - err = i915_vma_pin(hws, 0, 0, PIN_USER); - if (err) - goto unpin_vma; - - err = i915_vma_move_to_active(vma, rq, 0); - if (err) - goto unpin_hws; - if (!i915_gem_object_has_active_reference(vma->obj)) { i915_gem_object_get(vma->obj); i915_gem_object_set_active_reference(vma->obj); } - err = i915_vma_move_to_active(hws, rq, 0); - if (err) - goto unpin_hws; + return 0; +} - if (!i915_gem_object_has_active_reference(hws->obj)) { - i915_gem_object_get(hws->obj); - i915_gem_object_set_active_reference(hws->obj); +static struct i915_request * +hang_create_request(struct hang *h, struct intel_engine_cs *engine) +{ + struct drm_i915_private *i915 = h->i915; + struct i915_address_space *vm = + h->ctx->ppgtt ? &h->ctx->ppgtt->vm : &i915->ggtt.vm; + struct i915_request *rq = NULL; + struct i915_vma *hws, *vma; + unsigned int flags; + u32 *batch; + int err; + + if (i915_gem_object_is_active(h->obj)) { + struct drm_i915_gem_object *obj; + void *vaddr; + + obj = i915_gem_object_create_internal(h->i915, PAGE_SIZE); + if (IS_ERR(obj)) + return ERR_CAST(obj); + + vaddr = i915_gem_object_pin_map(obj, + i915_coherent_map_type(h->i915)); + if (IS_ERR(vaddr)) { + i915_gem_object_put(obj); + return ERR_CAST(vaddr); + } + + i915_gem_object_unpin_map(h->obj); + i915_gem_object_put(h->obj); + + h->obj = obj; + h->batch = vaddr; } + vma = i915_vma_instance(h->obj, vm, NULL); + if (IS_ERR(vma)) + return ERR_CAST(vma); + + hws = i915_vma_instance(h->hws, vm, NULL); + if (IS_ERR(hws)) + return ERR_CAST(hws); + + err = i915_vma_pin(vma, 0, 0, PIN_USER); + if (err) + return ERR_PTR(err); + + err = i915_vma_pin(hws, 0, 0, PIN_USER); + if (err) + goto unpin_vma; + + rq = i915_request_alloc(engine, h->ctx); + if (IS_ERR(rq)) { + err = PTR_ERR(rq); + goto unpin_hws; + } + + err = move_to_active(vma, rq, 0); + if (err) + goto cancel_rq; + + err = move_to_active(hws, rq, 0); + if (err) + goto cancel_rq; + batch = h->batch; if (INTEL_GEN(i915) >= 8) { *batch++ = MI_STORE_DWORD_IMM_GEN4; @@ -213,52 +248,16 @@ static int emit_recurse_batch(struct hang *h, err = rq->engine->emit_bb_start(rq, vma->node.start, PAGE_SIZE, flags); +cancel_rq: + if (err) { + i915_request_skip(rq, err); + i915_request_add(rq); + } unpin_hws: i915_vma_unpin(hws); unpin_vma: i915_vma_unpin(vma); - return err; -} - -static struct i915_request * -hang_create_request(struct hang *h, struct intel_engine_cs *engine) -{ - struct i915_request *rq; - int err; - - if (i915_gem_object_is_active(h->obj)) { - struct drm_i915_gem_object *obj; - void *vaddr; - - obj = i915_gem_object_create_internal(h->i915, PAGE_SIZE); - if (IS_ERR(obj)) - return ERR_CAST(obj); - - vaddr = i915_gem_object_pin_map(obj, - i915_coherent_map_type(h->i915)); - if (IS_ERR(vaddr)) { - i915_gem_object_put(obj); - return ERR_CAST(vaddr); - } - - i915_gem_object_unpin_map(h->obj); - i915_gem_object_put(h->obj); - - h->obj = obj; - h->batch = vaddr; - } - - rq = i915_request_alloc(engine, h->ctx); - if (IS_ERR(rq)) - return rq; - - err = emit_recurse_batch(h, rq); - if (err) { - i915_request_add(rq); - return ERR_PTR(err); - } - - return rq; + return err ? ERR_PTR(err) : rq; } static u32 hws_seqno(const struct hang *h, const struct i915_request *rq) From 0819936247c5133593c971e7121661cc32477990 Mon Sep 17 00:00:00 2001 From: Tvrtko Ursulin Date: Tue, 4 Dec 2018 17:15:30 +0000 Subject: [PATCH 002/118] drm/i915: Dial down workaround debug messages For selftests like live_hangcheck, which does thousands of reset per second, it is too verbose to log every time we re-apply the workarounds. Remove those messages since, coupled with the dedicated selftest, it is sufficient to only log the number of recorded workarounds at init time. Signed-off-by: Tvrtko Ursulin Suggested-by: Chris Wilson Reviewed-by: Chris Wilson Signed-off-by: Chris Wilson Link: https://patchwork.freedesktop.org/patch/msgid/20181204171530.28583-1-tvrtko.ursulin@linux.intel.com --- drivers/gpu/drm/i915/intel_workarounds.c | 4 ---- 1 file changed, 4 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_workarounds.c b/drivers/gpu/drm/i915/intel_workarounds.c index 4f41e326f3f3..6bcac78a9c36 100644 --- a/drivers/gpu/drm/i915/intel_workarounds.c +++ b/drivers/gpu/drm/i915/intel_workarounds.c @@ -955,8 +955,6 @@ wa_list_apply(struct drm_i915_private *dev_priv, const struct i915_wa_list *wal) intel_uncore_forcewake_put__locked(dev_priv, fw); spin_unlock_irqrestore(&dev_priv->uncore.lock, flags); - - DRM_DEBUG_DRIVER("Applied %u %s workarounds\n", wal->count, wal->name); } void intel_gt_apply_workarounds(struct drm_i915_private *dev_priv) @@ -1126,8 +1124,6 @@ void intel_engine_apply_whitelist(struct intel_engine_cs *engine) for (; i < RING_MAX_NONPRIV_SLOTS; i++) I915_WRITE(RING_FORCE_TO_NONPRIV(base, i), i915_mmio_reg_offset(RING_NOPID(base))); - - DRM_DEBUG_DRIVER("Applied %u %s workarounds\n", wal->count, wal->name); } static void rcs_engine_wa_init(struct intel_engine_cs *engine) From 7c5c641a930ed06ca317ee39faee7d5824266348 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:33:55 -0800 Subject: [PATCH 003/118] drm/i915: Disable PSR in Apple panels MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit i915 yet don't support PSR in Apple panels, so lets keep it disabled while we work on that. v2: Renamed DP_DPCD_QUIRK_PSR_NOT_CURRENTLY_SUPPORTED to DP_DPCD_QUIRK_NO_PSR (Ville) v3: Adding documentation to DP_DPCD_QUIRK_NO_PSR(Dhinakaran and Jani) Fixed typo in comment of the new quirk entry(Jani) Fixes: 598c6cfe0690 (drm/i915/psr: Enable PSR1 on gen-9+ HW) Cc: Jani Nikula Cc: Ville Syrjälä Cc: Rodrigo Vivi Cc: Dhinakaran Pandiyan Reviewed-by: Dhinakaran Pandiyan Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-1-jose.souza@intel.com --- drivers/gpu/drm/drm_dp_helper.c | 2 ++ drivers/gpu/drm/i915/intel_psr.c | 6 ++++++ include/drm/drm_dp_helper.h | 7 +++++++ 3 files changed, 15 insertions(+) diff --git a/drivers/gpu/drm/drm_dp_helper.c b/drivers/gpu/drm/drm_dp_helper.c index 2d6c491a0542..516e82d0ed50 100644 --- a/drivers/gpu/drm/drm_dp_helper.c +++ b/drivers/gpu/drm/drm_dp_helper.c @@ -1273,6 +1273,8 @@ static const struct dpcd_quirk dpcd_quirk_list[] = { { OUI(0x00, 0x22, 0xb9), DEVICE_ID_ANY, true, BIT(DP_DPCD_QUIRK_CONSTANT_N) }, /* LG LP140WF6-SPM1 eDP panel */ { OUI(0x00, 0x22, 0xb9), DEVICE_ID('s', 'i', 'v', 'a', 'r', 'T'), false, BIT(DP_DPCD_QUIRK_CONSTANT_N) }, + /* Apple panels need some additional handling to support PSR */ + { OUI(0x00, 0x10, 0xfa), DEVICE_ID_ANY, false, BIT(DP_DPCD_QUIRK_NO_PSR) } }; #undef OUI diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index 419e56342523..f71970df9936 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -274,10 +274,16 @@ void intel_psr_init_dpcd(struct intel_dp *intel_dp) DRM_DEBUG_KMS("eDP panel supports PSR version %x\n", intel_dp->psr_dpcd[0]); + if (drm_dp_has_quirk(&intel_dp->desc, DP_DPCD_QUIRK_NO_PSR)) { + DRM_DEBUG_KMS("PSR support not currently available for this panel\n"); + return; + } + if (!(intel_dp->edp_dpcd[1] & DP_EDP_SET_POWER_CAP)) { DRM_DEBUG_KMS("Panel lacks power state control, PSR cannot be enabled\n"); return; } + dev_priv->psr.sink_support = true; dev_priv->psr.sink_sync_latency = intel_dp_get_sink_sync_latency(intel_dp); diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h index 5736c942c85b..c33e89c51d9f 100644 --- a/include/drm/drm_dp_helper.h +++ b/include/drm/drm_dp_helper.h @@ -1365,6 +1365,13 @@ enum drm_dp_quirk { * to 16 bits. So will give a constant value (0x8000) for compatability. */ DP_DPCD_QUIRK_CONSTANT_N, + /** + * @DP_DPCD_QUIRK_NO_PSR + * + * The device does not support PSR even if reports that it supports or + * driver still need to implement proper handling for such device. + */ + DP_DPCD_QUIRK_NO_PSR, }; /** From 60cae44251e8f312381c82322ab6f68e3a481113 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:33:56 -0800 Subject: [PATCH 004/118] drm/i915/psr: Don't tell sink that main link will be active while is active PSR2 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit For PSR2 there is no register to tell HW to keep main link enabled while PSR2 is active, so don't configure sink DPCD with a misleading value. v2: Moving the set of DP_PSR_CRC_VERIFICATION to the else block of 'if (dev_priv->psr.psr2_enabled)' to another patch. (Rodrigo) Cc: Dhinakaran Pandiyan Cc: Rodrigo Vivi Reviewed-by: Dhinakaran Pandiyan Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-2-jose.souza@intel.com --- drivers/gpu/drm/i915/intel_psr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index f71970df9936..90759f754952 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -395,10 +395,11 @@ static void intel_psr_enable_sink(struct intel_dp *intel_dp) drm_dp_dpcd_writeb(&intel_dp->aux, DP_RECEIVER_ALPM_CONFIG, DP_ALPM_ENABLE); dpcd_val |= DP_PSR_ENABLE_PSR2; + } else { + if (dev_priv->psr.link_standby) + dpcd_val |= DP_PSR_MAIN_LINK_ACTIVE; } - if (dev_priv->psr.link_standby) - dpcd_val |= DP_PSR_MAIN_LINK_ACTIVE; if (!dev_priv->psr.psr2_enabled && INTEL_GEN(dev_priv) >= 8) dpcd_val |= DP_PSR_CRC_VERIFICATION; drm_dp_dpcd_writeb(&intel_dp->aux, DP_PSR_EN_CFG, dpcd_val); From de570946c0e5a44568c4d40d52042100936f93fd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:33:57 -0800 Subject: [PATCH 005/118] drm/i915/psr: Set PSR CRC verification bit in sink inside PSR1 block MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit As we have a else block for the 'if (dev_priv->psr.psr2_enabled) {' and this bit is only set for PSR1 move it to that block to make it more easy to read. Cc: Dhinakaran Pandiyan Cc: Rodrigo Vivi Reviewed-by: Dhinakaran Pandiyan Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-3-jose.souza@intel.com --- drivers/gpu/drm/i915/intel_psr.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index 90759f754952..8342c33ede04 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -398,10 +398,11 @@ static void intel_psr_enable_sink(struct intel_dp *intel_dp) } else { if (dev_priv->psr.link_standby) dpcd_val |= DP_PSR_MAIN_LINK_ACTIVE; + + if (INTEL_GEN(dev_priv) >= 8) + dpcd_val |= DP_PSR_CRC_VERIFICATION; } - if (!dev_priv->psr.psr2_enabled && INTEL_GEN(dev_priv) >= 8) - dpcd_val |= DP_PSR_CRC_VERIFICATION; drm_dp_dpcd_writeb(&intel_dp->aux, DP_PSR_EN_CFG, dpcd_val); drm_dp_dpcd_writeb(&intel_dp->aux, DP_SET_POWER, DP_SET_POWER_D0); From 98751b8cd608a38f810e190c58c94906923ff668 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:33:58 -0800 Subject: [PATCH 006/118] drm/i915/psr: Enable sink to trigger a interruption on PSR2 CRC mismatch MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit eDP spec states 2 different bits to enable sink to trigger a interruption when there is a CRC mismatch. DP_PSR_CRC_VERIFICATION is for PSR only and DP_PSR_IRQ_HPD_WITH_CRC_ERRORS is for PSR2 only. Cc: Dhinakaran Pandiyan Reviewed-by: Dhinakaran Pandiyan Reviewed-by: Rodrigo Vivi Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-4-jose.souza@intel.com --- drivers/gpu/drm/i915/intel_psr.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index 8342c33ede04..e463bef3c804 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -394,7 +394,7 @@ static void intel_psr_enable_sink(struct intel_dp *intel_dp) if (dev_priv->psr.psr2_enabled) { drm_dp_dpcd_writeb(&intel_dp->aux, DP_RECEIVER_ALPM_CONFIG, DP_ALPM_ENABLE); - dpcd_val |= DP_PSR_ENABLE_PSR2; + dpcd_val |= DP_PSR_ENABLE_PSR2 | DP_PSR_IRQ_HPD_WITH_CRC_ERRORS; } else { if (dev_priv->psr.link_standby) dpcd_val |= DP_PSR_MAIN_LINK_ACTIVE; From d15f9cdd59bab73e7edadee794efdd47bcbc1a7a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:33:59 -0800 Subject: [PATCH 007/118] drm/i915/icl: Do not change reserved registers related to PSR2 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit For ICL the bit 12 of CHICKEN_TRANS is reserved so we should not touch it and as by default VSC_DATA_SEL_SOFTWARE_CONTROL is already unset in gen10 + GLK we can just drop it and fix for both gens. Cc: Dhinakaran Pandiyan Reviewed-by: Rodrigo Vivi Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-5-jose.souza@intel.com --- drivers/gpu/drm/i915/intel_psr.c | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index e463bef3c804..b513a15d60e1 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -649,17 +649,14 @@ static void intel_psr_enable_source(struct intel_dp *intel_dp, if (IS_HASWELL(dev_priv) || IS_BROADWELL(dev_priv)) hsw_psr_setup_aux(intel_dp); - if (dev_priv->psr.psr2_enabled) { + if (dev_priv->psr.psr2_enabled && (IS_GEN9(dev_priv) && + !IS_GEMINILAKE(dev_priv))) { i915_reg_t reg = gen9_chicken_trans_reg(dev_priv, cpu_transcoder); u32 chicken = I915_READ(reg); - if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv)) - chicken |= (PSR2_VSC_ENABLE_PROG_HEADER - | PSR2_ADD_VERTICAL_LINE_COUNT); - - else - chicken &= ~VSC_DATA_SEL_SOFTWARE_CONTROL; + chicken |= PSR2_VSC_ENABLE_PROG_HEADER | + PSR2_ADD_VERTICAL_LINE_COUNT; I915_WRITE(reg, chicken); } From 227939a1c46db1b3dab52b621d7e6621ad269f84 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:34:00 -0800 Subject: [PATCH 008/118] drm/i915: Remove old PSR2 FIXME about frontbuffer tracking MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Our frontbuffer tracking improved over the years + the WA #0884 helped us keep PSR2 enabled while triggering screen updates when necessary so this FIXME is not valid anymore. Acked-by: Dhinakaran Pandiyan Reviewed-by: Rodrigo Vivi Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-6-jose.souza@intel.com --- drivers/gpu/drm/i915/intel_psr.c | 3 --- 1 file changed, 3 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index b513a15d60e1..11b038ba96ec 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -476,9 +476,6 @@ static void hsw_activate_psr2(struct intel_dp *intel_dp) idle_frames = max(idle_frames, dev_priv->psr.sink_sync_latency + 1); val = idle_frames << EDP_PSR2_IDLE_FRAME_SHIFT; - /* FIXME: selective update is probably totally broken because it doesn't - * mesh at all with our frontbuffer tracking. And the hw alone isn't - * good enough. */ val |= EDP_PSR2_ENABLE | EDP_SU_TRACK_ENABLE; if (INTEL_GEN(dev_priv) >= 10 || IS_GEMINILAKE(dev_priv)) val |= EDP_Y_COORDINATE_ENABLE; From 71b15621f0972aac3512848691285663c66c8203 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:34:01 -0800 Subject: [PATCH 009/118] drm: Add the PSR SU granularity registers offsets MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Source is required to comply to sink SU granularity when DP_PSR2_SU_GRANULARITY_REQUIRED is set in DP_PSR_CAPS, so adding the registers offsets. v2: Also adding DP_PSR2_SU_Y_GRANULARITY(Rodrigo) Cc: Dhinakaran Pandiyan Cc: Rodrigo Vivi Reviewed-by: Dhinakaran Pandiyan Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-7-jose.souza@intel.com --- include/drm/drm_dp_helper.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h index c33e89c51d9f..18cfde45b8ed 100644 --- a/include/drm/drm_dp_helper.h +++ b/include/drm/drm_dp_helper.h @@ -314,6 +314,10 @@ # define DP_PSR_SETUP_TIME_SHIFT 1 # define DP_PSR2_SU_Y_COORDINATE_REQUIRED (1 << 4) /* eDP 1.4a */ # define DP_PSR2_SU_GRANULARITY_REQUIRED (1 << 5) /* eDP 1.4b */ + +#define DP_PSR2_SU_X_GRANULARITY 0x072 /* eDP 1.4b */ +#define DP_PSR2_SU_Y_GRANULARITY 0x074 /* eDP 1.4b */ + /* * 0x80-0x8f describe downstream port capabilities, but there are two layouts * based on whether DP_DETAILED_CAP_INFO_AVAILABLE was set. If it was not, From bef5e5b3bee41c6a0706f4a4f66bc9422e6933a1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:34:02 -0800 Subject: [PATCH 010/118] drm/i915/psr: Check if resolution is supported by default SU granularity MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Selective updates have a default granularity requirements as stated by eDP spec(PSR2 SELECTIVE UPDATE X GRANULARITY CAPABILITY register definition), so check if HW can match those requirements before enabling PSR2. v3: - Changes in the comments and commit message(Dhinakaran) - Printing the hdisplay that do not match with default granularity Cc: Dhinakaran Pandiyan Cc: Rodrigo Vivi Reviewed-by: Dhinakaran Pandiyan Signed-off-by: José Roberto de Souza Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-8-jose.souza@intel.com --- drivers/gpu/drm/i915/intel_psr.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index 11b038ba96ec..298c3145212d 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -536,6 +536,17 @@ static bool intel_psr2_config_valid(struct intel_dp *intel_dp, return false; } + /* + * HW sends SU blocks of size four scan lines, which means the starting + * X coordinate and Y granularity requirements will always be met. We + * only need to validate the SU block width is a multiple of 4. + */ + if (crtc_hdisplay % 4) { + DRM_DEBUG_KMS("PSR2 not enabled, hdisplay(%d) not multiple of 4\n", + crtc_hdisplay); + return false; + } + return true; } From 8c0d2c29083d689685c0ecccb82217c732490b50 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Mon, 3 Dec 2018 16:34:03 -0800 Subject: [PATCH 011/118] drm/i915/psr: Check if source supports sink specific SU granularity MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit According to eDP spec, sink can required specific selective update granularity that source must comply. Here caching the value if required and checking if source supports it. v3: - Returning the default granularity in case DPCD read fails(Dhinakaran) - Changed DPCD error message level(Dhinakaran) v4: - Setting granularity to defaul when granularity read is equal to 0(Dhinakaran) Cc: Rodrigo Vivi Cc: Dhinakaran Pandiyan Signed-off-by: José Roberto de Souza Reviewed-by: Dhinakaran Pandiyan Link: https://patchwork.freedesktop.org/patch/msgid/20181204003403.23361-9-jose.souza@intel.com --- drivers/gpu/drm/i915/i915_drv.h | 1 + drivers/gpu/drm/i915/intel_psr.c | 37 ++++++++++++++++++++++++++++---- 2 files changed, 34 insertions(+), 4 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index b1c31967194b..0689e67c966e 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -509,6 +509,7 @@ struct i915_psr { ktime_t last_exit; bool sink_not_reliable; bool irq_aux_error; + u16 su_x_granularity; }; enum intel_pch { diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index 298c3145212d..4c4dd1c310ce 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -261,6 +261,32 @@ static u8 intel_dp_get_sink_sync_latency(struct intel_dp *intel_dp) return val; } +static u16 intel_dp_get_su_x_granulartiy(struct intel_dp *intel_dp) +{ + u16 val; + ssize_t r; + + /* + * Returning the default X granularity if granularity not required or + * if DPCD read fails + */ + if (!(intel_dp->psr_dpcd[1] & DP_PSR2_SU_GRANULARITY_REQUIRED)) + return 4; + + r = drm_dp_dpcd_read(&intel_dp->aux, DP_PSR2_SU_X_GRANULARITY, &val, 2); + if (r != 2) + DRM_DEBUG_KMS("Unable to read DP_PSR2_SU_X_GRANULARITY\n"); + + /* + * Spec says that if the value read is 0 the default granularity should + * be used instead. + */ + if (r != 2 || val == 0) + val = 4; + + return val; +} + void intel_psr_init_dpcd(struct intel_dp *intel_dp) { struct drm_i915_private *dev_priv = @@ -315,6 +341,8 @@ void intel_psr_init_dpcd(struct intel_dp *intel_dp) if (dev_priv->psr.sink_psr2_support) { dev_priv->psr.colorimetry_support = intel_dp_get_colorimetry_status(intel_dp); + dev_priv->psr.su_x_granularity = + intel_dp_get_su_x_granulartiy(intel_dp); } } } @@ -539,11 +567,12 @@ static bool intel_psr2_config_valid(struct intel_dp *intel_dp, /* * HW sends SU blocks of size four scan lines, which means the starting * X coordinate and Y granularity requirements will always be met. We - * only need to validate the SU block width is a multiple of 4. + * only need to validate the SU block width is a multiple of + * x granularity. */ - if (crtc_hdisplay % 4) { - DRM_DEBUG_KMS("PSR2 not enabled, hdisplay(%d) not multiple of 4\n", - crtc_hdisplay); + if (crtc_hdisplay % dev_priv->psr.su_x_granularity) { + DRM_DEBUG_KMS("PSR2 not enabled, hdisplay(%d) not multiple of %d\n", + crtc_hdisplay, dev_priv->psr.su_x_granularity); return false; } From 79960227d93b81496365c35f5df162216f94d8e4 Mon Sep 17 00:00:00 2001 From: Pedro Tammela Date: Wed, 5 Dec 2018 09:06:08 -0200 Subject: [PATCH 012/118] Makefile: fix mixed tab and spaces Fixes a comestic issue where spaces were being used instead of mixed tab and spaces. Signed-off-by: Pedro Tammela Reviewed-by: Chris Wilson Signed-off-by: Chris Wilson Link: https://patchwork.freedesktop.org/patch/msgid/20181205110608.5513-1-pctammela@gmail.com --- drivers/gpu/drm/i915/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/Makefile b/drivers/gpu/drm/i915/Makefile index 19b5fe5016bf..c34bee16730d 100644 --- a/drivers/gpu/drm/i915/Makefile +++ b/drivers/gpu/drm/i915/Makefile @@ -40,7 +40,7 @@ i915-y := i915_drv.o \ i915_mm.o \ i915_params.o \ i915_pci.o \ - i915_suspend.o \ + i915_suspend.o \ i915_syncmap.o \ i915_sw_fence.o \ i915_sysfs.o \ From a1d926527b79576615839db39e3a5c7a7845f31c Mon Sep 17 00:00:00 2001 From: Matt Atwood Date: Thu, 29 Nov 2018 14:00:58 -0800 Subject: [PATCH 013/118] drm/i915: implement EXTENDED_RECEIVER_CAPABILITY_FIELD_PRESENT According to DP spec (2.9.3.1 of DP 1.4) if EXTENDED_RECEIVER_CAPABILITY_FIELD_PRESENT is set the addresses in DPCD 02200h through 0220Fh shall contain the DPRX's true capability. These values will match 00000h through 0000Fh, except for DPCD_REV, MAX_LINK_RATE, DOWN_STREAM_PORT_PRESENT. Read from DPCD once for all 3 values as this is an expensive operation. Spec mentions that all of address space 02200h through 0220Fh should contain the right information however currently only 3 values can differ. There is no address space in the intel_dp->dpcd struct for addresses 02200h through 0220Fh, and since so much of the data is a identical, simply overwrite the values stored in 00000h through 0000Fh with the values that can be overwritten from addresses 02200h through 0220Fh. This patch helps with backward compatibility for devices pre DP1.3. v2: read only dpcd values which can be affected, remove incorrect check, split into drm include changes into separate patch, commit message, verbose debugging statements during overwrite. v3: white space fixes v4: make path dependent on DPCD revision > 1.2 v5: split into function, removed DPCD rev check v6: add debugging prints for early exit conditions v7 (From Manasi): * Memcpy, memcmp and debig logging based on sizeof(dpcd_ext) (Jani N) * Exit early (Jani N) v8 (From Manasi): * Get rid of superfluous debug prints (Jani N) * Print entire base DPCD before memcpy (Jani N) v9 (From Manasi): * Add uniform newlines (Rodrigo) Cc: Jani Nikula Cc: Ville Syrjala Signed-off-by: Matt Atwood Signed-off-by: Manasi Navare Tested-by: Manasi Navare Acked-by: Manasi Navare Reviewed-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181129220058.19636-1-manasi.d.navare@intel.com --- drivers/gpu/drm/i915/intel_dp.c | 38 +++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index fdd2cbc56fa3..de4219721cbc 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -3991,6 +3991,42 @@ intel_dp_link_down(struct intel_encoder *encoder, } } +static void +intel_dp_extended_receiver_capabilities(struct intel_dp *intel_dp) +{ + u8 dpcd_ext[6]; + + /* + * Prior to DP1.3 the bit represented by + * DP_EXTENDED_RECEIVER_CAP_FIELD_PRESENT was reserved. + * if it is set DP_DPCD_REV at 0000h could be at a value less than + * the true capability of the panel. The only way to check is to + * then compare 0000h and 2200h. + */ + if (!(intel_dp->dpcd[DP_TRAINING_AUX_RD_INTERVAL] & + DP_EXTENDED_RECEIVER_CAP_FIELD_PRESENT)) + return; + + if (drm_dp_dpcd_read(&intel_dp->aux, DP_DP13_DPCD_REV, + &dpcd_ext, sizeof(dpcd_ext)) != sizeof(dpcd_ext)) { + DRM_ERROR("DPCD failed read at extended capabilities\n"); + return; + } + + if (intel_dp->dpcd[DP_DPCD_REV] > dpcd_ext[DP_DPCD_REV]) { + DRM_DEBUG_KMS("DPCD extended DPCD rev less than base DPCD rev\n"); + return; + } + + if (!memcmp(intel_dp->dpcd, dpcd_ext, sizeof(dpcd_ext))) + return; + + DRM_DEBUG_KMS("Base DPCD: %*ph\n", + (int)sizeof(intel_dp->dpcd), intel_dp->dpcd); + + memcpy(intel_dp->dpcd, dpcd_ext, sizeof(dpcd_ext)); +} + bool intel_dp_read_dpcd(struct intel_dp *intel_dp) { @@ -3998,6 +4034,8 @@ intel_dp_read_dpcd(struct intel_dp *intel_dp) sizeof(intel_dp->dpcd)) < 0) return false; /* aux transfer failed */ + intel_dp_extended_receiver_capabilities(intel_dp); + DRM_DEBUG_KMS("DPCD: %*ph\n", (int) sizeof(intel_dp->dpcd), intel_dp->dpcd); return intel_dp->dpcd[DP_DPCD_REV] != 0; From ed17b555303c74a35f226268523b1695dbd4617d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Wed, 5 Dec 2018 10:48:50 -0800 Subject: [PATCH 014/118] drm: Fix documentation generation for DP_DPCD_QUIRK_NO_PSR MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The DP_DPCD_QUIRK_NO_PSR comment is missing colon causing this warning when generating kernel documentation. ./include/drm/drm_dp_helper.h:1374: warning: Incorrect use of kernel-doc format: * @DP_DPCD_QUIRK_NO_PSR Fixes: 7c5c641a930e (drm/i915: Disable PSR in Apple panels) Cc: Dhinakaran Pandiyan Signed-off-by: José Roberto de Souza Reviewed-by: Dhinakaran Pandiyan Link: https://patchwork.freedesktop.org/patch/msgid/20181205184850.13218-1-jose.souza@intel.com --- include/drm/drm_dp_helper.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h index 18cfde45b8ed..c223c87ef119 100644 --- a/include/drm/drm_dp_helper.h +++ b/include/drm/drm_dp_helper.h @@ -1370,7 +1370,7 @@ enum drm_dp_quirk { */ DP_DPCD_QUIRK_CONSTANT_N, /** - * @DP_DPCD_QUIRK_NO_PSR + * @DP_DPCD_QUIRK_NO_PSR: * * The device does not support PSR even if reports that it supports or * driver still need to implement proper handling for such device. From 8d9d005d38bada06604545f815fcbb69c1d08e63 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jos=C3=A9=20Roberto=20de=20Souza?= Date: Tue, 4 Dec 2018 16:48:23 -0800 Subject: [PATCH 015/118] drm/i915/fbc/cnl: Add GLK and CNL+ hardware tracking area MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit GLK and CNL+ supports a bigger FBC tracking area. Signed-off-by: José Roberto de Souza Reviewed-by: Dhinakaran Pandiyan Link: https://patchwork.freedesktop.org/patch/msgid/20181205004823.30823-1-jose.souza@intel.com --- drivers/gpu/drm/i915/intel_fbc.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_fbc.c b/drivers/gpu/drm/i915/intel_fbc.c index f23570c44323..78dbacdeaece 100644 --- a/drivers/gpu/drm/i915/intel_fbc.c +++ b/drivers/gpu/drm/i915/intel_fbc.c @@ -626,7 +626,10 @@ static bool intel_fbc_hw_tracking_covers_screen(struct intel_crtc *crtc) struct intel_fbc *fbc = &dev_priv->fbc; unsigned int effective_w, effective_h, max_w, max_h; - if (INTEL_GEN(dev_priv) >= 8 || IS_HASWELL(dev_priv)) { + if (INTEL_GEN(dev_priv) >= 10 || IS_GEMINILAKE(dev_priv)) { + max_w = 5120; + max_h = 4096; + } else if (INTEL_GEN(dev_priv) >= 8 || IS_HASWELL(dev_priv)) { max_w = 4096; max_h = 4096; } else if (IS_G4X(dev_priv) || INTEL_GEN(dev_priv) >= 5) { From 083d2a07ee0ef09c6116f058d1c6e41bafca6a19 Mon Sep 17 00:00:00 2001 From: Ramalingam C Date: Wed, 5 Dec 2018 17:14:40 +0530 Subject: [PATCH 016/118] drm/i915: Fix GEN9 HDCP1.4 key load process HDCP1.4 key load process varies between Intel platform to platform. For Gen9 platforms except BXT and GLK, HDCP1.4 key is loaded using the GT Driver Mailbox interface. So all GEN9_BC platforms will use the GT Driver Mailbox interface for HDCP1.4 key load. v2: Using the IS_GEN9_BC for filtering the platforms [Ville] Signed-off-by: Ramalingam C Reviewed-by: Sean Paul Signed-off-by: Daniel Vetter Link: https://patchwork.freedesktop.org/patch/msgid/1544010283-20223-2-git-send-email-ramalingam.c@intel.com --- drivers/gpu/drm/i915/intel_hdcp.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_hdcp.c b/drivers/gpu/drm/i915/intel_hdcp.c index 1bf487f94254..c16bffcce3b0 100644 --- a/drivers/gpu/drm/i915/intel_hdcp.c +++ b/drivers/gpu/drm/i915/intel_hdcp.c @@ -157,10 +157,11 @@ static int intel_hdcp_load_keys(struct drm_i915_private *dev_priv) /* * Initiate loading the HDCP key from fuses. * - * BXT+ platforms, HDCP key needs to be loaded by SW. Only SKL and KBL - * differ in the key load trigger process from other platforms. + * BXT+ platforms, HDCP key needs to be loaded by SW. Only Gen 9 + * platforms except BXT and GLK, differ in the key load trigger process + * from other platforms. So GEN9_BC uses the GT Driver Mailbox i/f. */ - if (IS_SKYLAKE(dev_priv) || IS_KABYLAKE(dev_priv)) { + if (IS_GEN9_BC(dev_priv)) { mutex_lock(&dev_priv->pcu_lock); ret = sandybridge_pcode_write(dev_priv, SKL_PCODE_LOAD_HDCP_KEYS, 1); From a0ea697a66497d68acbffb84d7bdaf2c92a89fe1 Mon Sep 17 00:00:00 2001 From: Ramalingam C Date: Wed, 5 Dec 2018 17:14:41 +0530 Subject: [PATCH 017/118] drm/i915: Fix platform coverage for HDCP1.4 HDCP1.4 is enabled and validated only on GEN9+ platforms. v2: Removed the unnecessary parens [Ville] Signed-off-by: Ramalingam C Reviewed-by: Sean Paul Signed-off-by: Daniel Vetter Link: https://patchwork.freedesktop.org/patch/msgid/1544010283-20223-3-git-send-email-ramalingam.c@intel.com --- drivers/gpu/drm/i915/intel_hdcp.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_hdcp.c b/drivers/gpu/drm/i915/intel_hdcp.c index c16bffcce3b0..1e5a1e07e343 100644 --- a/drivers/gpu/drm/i915/intel_hdcp.c +++ b/drivers/gpu/drm/i915/intel_hdcp.c @@ -769,8 +769,7 @@ static void intel_hdcp_prop_work(struct work_struct *work) bool is_hdcp_supported(struct drm_i915_private *dev_priv, enum port port) { /* PORT E doesn't have HDCP, and PORT F is disabled */ - return ((INTEL_GEN(dev_priv) >= 8 || IS_HASWELL(dev_priv)) && - !IS_CHERRYVIEW(dev_priv) && port < PORT_E); + return INTEL_GEN(dev_priv) >= 9 && port < PORT_E; } int intel_hdcp_init(struct intel_connector *connector, From 4cf74aafc55bef8725d1d30f7d3449fb86c1710f Mon Sep 17 00:00:00 2001 From: Ramalingam C Date: Wed, 5 Dec 2018 17:14:42 +0530 Subject: [PATCH 018/118] drm/i915: debug log for REPLY_ACK missing Adding a debug log when the DP_AUX_NATIVE_REPLY_ACK is missing for aksv write. This helps to locate the possible non responding DP HDCP sinks. v2: Rewritten for readability [Sean Paul] Signed-off-by: Ramalingam C Reviewed-by: Sean Paul Signed-off-by: Daniel Vetter Link: https://patchwork.freedesktop.org/patch/msgid/1544010283-20223-4-git-send-email-ramalingam.c@intel.com --- drivers/gpu/drm/i915/intel_dp.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index de4219721cbc..e94faa0a42eb 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -5616,7 +5616,12 @@ int intel_dp_hdcp_write_an_aksv(struct intel_digital_port *intel_dig_port, } reply = (rxbuf[0] >> 4) & DP_AUX_NATIVE_REPLY_MASK; - return reply == DP_AUX_NATIVE_REPLY_ACK ? 0 : -EIO; + if (reply != DP_AUX_NATIVE_REPLY_ACK) { + DRM_DEBUG_KMS("Aksv write: no DP_AUX_NATIVE_REPLY_ACK %x\n", + reply); + return -EIO; + } + return 0; } static int intel_dp_hdcp_read_bksv(struct intel_digital_port *intel_dig_port, From 7e90e8d0c0ea211241ba42390bc7602debdff90e Mon Sep 17 00:00:00 2001 From: Ramalingam C Date: Wed, 5 Dec 2018 17:14:43 +0530 Subject: [PATCH 019/118] drm/i915: Increase timeout for Encrypt status change At enable/disable of the HDCP encryption, for encryption status change we need minimum one frame duration. And we might program this bit any point(start/End) in the previous frame. With 20mSec, observed the timeout for change in encryption status. Since this is not time critical operation and we need to hold on until the status is changed, fixing the timeout to 50mSec. (Based on trial and error method!) v2: %s/TIME_FOR_ENCRYPT_STATUS_CHANGE/ENCRYPT_STATUS_CHANGE_TIMEOUT_MS [Sean Paul] Signed-off-by: Ramalingam C Reviewed-by: Sean Paul Signed-off-by: Daniel Vetter Link: https://patchwork.freedesktop.org/patch/msgid/1544010283-20223-5-git-send-email-ramalingam.c@intel.com --- drivers/gpu/drm/i915/intel_hdcp.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_hdcp.c b/drivers/gpu/drm/i915/intel_hdcp.c index 1e5a1e07e343..e000e54ad569 100644 --- a/drivers/gpu/drm/i915/intel_hdcp.c +++ b/drivers/gpu/drm/i915/intel_hdcp.c @@ -15,6 +15,7 @@ #include "i915_reg.h" #define KEY_LOAD_TRIES 5 +#define ENCRYPT_STATUS_CHANGE_TIMEOUT_MS 50 static bool intel_hdcp_is_ksv_valid(u8 *ksv) @@ -637,7 +638,8 @@ static int intel_hdcp_auth(struct intel_digital_port *intel_dig_port, /* Wait for encryption confirmation */ if (intel_wait_for_register(dev_priv, PORT_HDCP_STATUS(port), - HDCP_STATUS_ENC, HDCP_STATUS_ENC, 20)) { + HDCP_STATUS_ENC, HDCP_STATUS_ENC, + ENCRYPT_STATUS_CHANGE_TIMEOUT_MS)) { DRM_ERROR("Timed out waiting for encryption\n"); return -ETIMEDOUT; } @@ -667,7 +669,7 @@ static int _intel_hdcp_disable(struct intel_connector *connector) I915_WRITE(PORT_HDCP_CONF(port), 0); if (intel_wait_for_register(dev_priv, PORT_HDCP_STATUS(port), ~0, 0, - 20)) { + ENCRYPT_STATUS_CHANGE_TIMEOUT_MS)) { DRM_ERROR("Failed to disable HDCP, timeout clearing status\n"); return -ETIMEDOUT; } From 3abd6143f97114360118b43f6465abb207be905a Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 6 Dec 2018 18:07:12 +0000 Subject: [PATCH 020/118] drm/i915/selftests: verify_gt_engine_wa() needs rpm wakeref The mmio readback for verify_gt_engine_wa() also needs a runtime-pm wakeref, so effectively do the entirety of both engine workarounds tests. As such simplify the rpm behaviour here by acquiring the wakeref for the whole of each subtest. It would be still useful to later verify the registers retain their magic values across rpm suspend/resume. Signed-off-by: Chris Wilson Cc: Tvrtko Ursulin Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181206180713.6827-1-chris@chris-wilson.co.uk --- .../gpu/drm/i915/selftests/intel_workarounds.c | 15 ++++----------- 1 file changed, 4 insertions(+), 11 deletions(-) diff --git a/drivers/gpu/drm/i915/selftests/intel_workarounds.c b/drivers/gpu/drm/i915/selftests/intel_workarounds.c index 67017d5175b8..c2b3cd8fcc34 100644 --- a/drivers/gpu/drm/i915/selftests/intel_workarounds.c +++ b/drivers/gpu/drm/i915/selftests/intel_workarounds.c @@ -333,7 +333,6 @@ static bool verify_gt_engine_wa(struct drm_i915_private *i915, const char *str) bool ok = true; ok &= intel_gt_verify_workarounds(i915, str); - for_each_engine(engine, i915, id) ok &= intel_engine_verify_workarounds(engine, str); @@ -353,19 +352,19 @@ live_gpu_reset_gt_engine_workarounds(void *arg) pr_info("Verifying after GPU reset...\n"); igt_global_reset_lock(i915); + intel_runtime_pm_get(i915); ok = verify_gt_engine_wa(i915, "before reset"); if (!ok) goto out; - intel_runtime_pm_get(i915); set_bit(I915_RESET_HANDOFF, &error->flags); i915_reset(i915, ALL_ENGINES, "live_workarounds"); - intel_runtime_pm_put(i915); ok = verify_gt_engine_wa(i915, "after reset"); out: + intel_runtime_pm_put(i915); igt_global_reset_unlock(i915); return ok ? 0 : -ESRCH; @@ -390,6 +389,7 @@ live_engine_reset_gt_engine_workarounds(void *arg) return PTR_ERR(ctx); igt_global_reset_lock(i915); + intel_runtime_pm_get(i915); for_each_engine(engine, i915, id) { bool ok; @@ -402,9 +402,7 @@ live_engine_reset_gt_engine_workarounds(void *arg) goto err; } - intel_runtime_pm_get(i915); i915_reset_engine(engine, "live_workarounds"); - intel_runtime_pm_put(i915); ok = verify_gt_engine_wa(i915, "after idle reset"); if (!ok) { @@ -416,13 +414,10 @@ live_engine_reset_gt_engine_workarounds(void *arg) if (ret) goto err; - intel_runtime_pm_get(i915); - rq = igt_spinner_create_request(&spin, ctx, engine, MI_NOOP); if (IS_ERR(rq)) { ret = PTR_ERR(rq); igt_spinner_fini(&spin); - intel_runtime_pm_put(i915); goto err; } @@ -431,15 +426,12 @@ live_engine_reset_gt_engine_workarounds(void *arg) if (!igt_wait_for_spinner(&spin, rq)) { pr_err("Spinner failed to start\n"); igt_spinner_fini(&spin); - intel_runtime_pm_put(i915); ret = -ETIMEDOUT; goto err; } i915_reset_engine(engine, "live_workarounds"); - intel_runtime_pm_put(i915); - igt_spinner_end(&spin); igt_spinner_fini(&spin); @@ -451,6 +443,7 @@ live_engine_reset_gt_engine_workarounds(void *arg) } err: + intel_runtime_pm_put(i915); igt_global_reset_unlock(i915); kernel_context_close(ctx); From 5a688ee3a224a9042627441fe6e82bae130be098 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 6 Dec 2018 18:07:13 +0000 Subject: [PATCH 021/118] drm/i915/execlists: Move RCS mmio workaround to new common wa_list We can move the remaining RCS workarounds applied to only gen8 to the engine->wa_list, and then reduce all engine->init_hw callbacks to common code. The benefit of using the new wa_list is that we verify that the registers are indeed restored and keep their magic values. v2: INSTPM_FORCE_ORDERING is already part of gen8_ctx_workarounds, and as confirmed by the mmio verification is a part of the context image! v3: MI_MODE is already part of gen8_ctx_workarounds... Signed-off-by: Chris Wilson Cc: Tvrtko Ursulin Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181206180713.6827-2-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/intel_lrc.c | 42 +------------------------------- 1 file changed, 1 insertion(+), 41 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index d7fa301b5ec7..dc8981be22cf 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -1628,6 +1628,7 @@ static bool unexpected_starting_state(struct intel_engine_cs *engine) static int gen8_init_common_ring(struct intel_engine_cs *engine) { intel_engine_apply_workarounds(engine); + intel_engine_apply_whitelist(engine); intel_mocs_init_engine(engine); @@ -1644,43 +1645,6 @@ static int gen8_init_common_ring(struct intel_engine_cs *engine) return 0; } -static int gen8_init_render_ring(struct intel_engine_cs *engine) -{ - struct drm_i915_private *dev_priv = engine->i915; - int ret; - - ret = gen8_init_common_ring(engine); - if (ret) - return ret; - - intel_engine_apply_whitelist(engine); - - /* We need to disable the AsyncFlip performance optimisations in order - * to use MI_WAIT_FOR_EVENT within the CS. It should already be - * programmed to '1' on all products. - * - * WaDisableAsyncFlipPerfMode:snb,ivb,hsw,vlv,bdw,chv - */ - I915_WRITE(MI_MODE, _MASKED_BIT_ENABLE(ASYNC_FLIP_PERF_DISABLE)); - - I915_WRITE(INSTPM, _MASKED_BIT_ENABLE(INSTPM_FORCE_ORDERING)); - - return 0; -} - -static int gen9_init_render_ring(struct intel_engine_cs *engine) -{ - int ret; - - ret = gen8_init_common_ring(engine); - if (ret) - return ret; - - intel_engine_apply_whitelist(engine); - - return 0; -} - static struct i915_request * execlists_reset_prepare(struct intel_engine_cs *engine) { @@ -2280,10 +2244,6 @@ int logical_render_ring_init(struct intel_engine_cs *engine) engine->irq_keep_mask |= GT_RENDER_L3_PARITY_ERROR_INTERRUPT; /* Override some for render ring. */ - if (INTEL_GEN(dev_priv) >= 9) - engine->init_hw = gen9_init_render_ring; - else - engine->init_hw = gen8_init_render_ring; engine->init_context = gen8_init_rcs_context; engine->emit_flush = gen8_emit_flush_render; engine->emit_breadcrumb = gen8_emit_breadcrumb_rcs; From 490b8c65b9db45896769e1095e78725775f47b3e Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 6 Dec 2018 08:44:31 +0000 Subject: [PATCH 022/118] drm/i915/execlists: Apply a full mb before execution for Braswell Braswell is really picky about having our writes posted to memory before we execute or else the GPU may see stale values. A wmb() is insufficient as it only ensures the writes are visible to other cores, we need a full mb() to ensure the writes are in memory and visible to the GPU. The most frequent failure in flushing before execution is that we see stale PTE values and execute the wrong pages. References: 987abd5c62f9 ("drm/i915/execlists: Force write serialisation into context image vs execution") Signed-off-by: Chris Wilson Cc: Mika Kuoppala Cc: Tvrtko Ursulin Cc: Joonas Lahtinen Cc: stable@vger.kernel.org Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181206084431.9805-3-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/intel_lrc.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index dc8981be22cf..27d3a780611a 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -398,8 +398,13 @@ static u64 execlists_update_context(struct i915_request *rq) * may not be visible to the HW prior to the completion of the UC * register write and that we may begin execution from the context * before its image is complete leading to invalid PD chasing. + * + * Furthermore, Braswell, at least, wants a full mb to be sure that + * the writes are coherent in memory (visible to the GPU) prior to + * execution, and not just visible to other CPUs (as is the result of + * wmb). */ - wmb(); + mb(); return ce->lrc_desc; } From d8f505311717cfc2033c44a8b26ba96c66187303 Mon Sep 17 00:00:00 2001 From: Mika Kuoppala Date: Wed, 5 Dec 2018 15:46:12 +0200 Subject: [PATCH 023/118] drm/i915/icl: Forcibly evict stale csb entries Gen11 fails to deliver wrt global observation point on tail/entry updates and we sometimes see old entry. Use clflush to forcibly evict our possibly stale copy of the cacheline in hopes that we get fresh one from gpu. Obviously there is something amiss in the coherency protocol so this can be consired as a workaround until real cause is found. The working hardware will do the evict without our cue anyways, so the cost in there should be ameliorated by that fact. v2: for next pass, s/flush/evict, add reset (Chris) References: https://bugzilla.freedesktop.org/show_bug.cgi?id=108315 Cc: Chris Wilson Signed-off-by: Mika Kuoppala Reviewed-by: Chris Wilson Link: https://patchwork.freedesktop.org/patch/msgid/20181205134612.24822-1-mika.kuoppala@linux.intel.com --- drivers/gpu/drm/i915/intel_lrc.c | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index 27d3a780611a..3a47a4732fae 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -770,6 +770,13 @@ execlists_cancel_port_requests(struct intel_engine_execlists * const execlists) execlists_clear_all_active(execlists); } +static inline void +invalidate_csb_entries(const u32 *first, const u32 *last) +{ + clflush((void *)first); + clflush((void *)last); +} + static void reset_csb_pointers(struct intel_engine_execlists *execlists) { const unsigned int reset_value = GEN8_CSB_ENTRIES - 1; @@ -785,6 +792,9 @@ static void reset_csb_pointers(struct intel_engine_execlists *execlists) */ execlists->csb_head = reset_value; WRITE_ONCE(*execlists->csb_write, reset_value); + + invalidate_csb_entries(&execlists->csb_status[0], + &execlists->csb_status[GEN8_CSB_ENTRIES - 1]); } static void nop_submission_tasklet(unsigned long data) @@ -1020,6 +1030,19 @@ static void process_csb(struct intel_engine_cs *engine) } while (head != tail); execlists->csb_head = head; + + /* + * Gen11 has proven to fail wrt global observation point between + * entry and tail update, failing on the ordering and thus + * we see an old entry in the context status buffer. + * + * Forcibly evict out entries for the next gpu csb update, + * to increase the odds that we get a fresh entries with non + * working hardware. The cost for doing so comes out mostly with + * the wash as hardware, working or not, will need to do the + * invalidation before. + */ + invalidate_csb_entries(&buf[0], &buf[GEN8_CSB_ENTRIES - 1]); } static void __execlists_submission_tasklet(struct intel_engine_cs *const engine) From 5f5800a765de8414f6fb213c4ad4a1cf529e131d Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Fri, 7 Dec 2018 09:02:11 +0000 Subject: [PATCH 024/118] drm/i915: Push EMIT_INVALIDATE at request start to backends Move the common engine->emit_flush(EMIT_INVALIDATE) back to the backends (where it was once previously) as we seek to specialise it in future patches. Signed-off-by: Chris Wilson Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181207090213.14352-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_request.c | 5 ----- drivers/gpu/drm/i915/intel_lrc.c | 9 ++++++--- drivers/gpu/drm/i915/intel_ringbuffer.c | 6 ++++-- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_request.c b/drivers/gpu/drm/i915/i915_request.c index ca95ab2f4cfa..8ab8e8e6a086 100644 --- a/drivers/gpu/drm/i915/i915_request.c +++ b/drivers/gpu/drm/i915/i915_request.c @@ -719,11 +719,6 @@ i915_request_alloc(struct intel_engine_cs *engine, struct i915_gem_context *ctx) */ rq->head = rq->ring->emit; - /* Unconditionally invalidate GPU caches and TLBs. */ - ret = engine->emit_flush(rq, EMIT_INVALIDATE); - if (ret) - goto err_unwind; - ret = engine->request_alloc(rq); if (ret) goto err_unwind; diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index 3a47a4732fae..a9084a54c0f4 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -1276,17 +1276,20 @@ static int execlists_request_alloc(struct i915_request *request) GEM_BUG_ON(!request->hw_context->pin_count); - /* Flush enough space to reduce the likelihood of waiting after + /* + * Flush enough space to reduce the likelihood of waiting after * we start building the request - in which case we will just * have to repeat work. */ request->reserved_space += EXECLISTS_REQUEST_SIZE; - ret = intel_ring_wait_for_space(request->ring, request->reserved_space); + /* Unconditionally invalidate GPU caches and TLBs. */ + ret = request->engine->emit_flush(request, EMIT_INVALIDATE); if (ret) return ret; - /* Note that after this point, we have committed to using + /* + * Note that after this point, we have committed to using * this request as it is being used to both track the * state of engine initialisation and liveness of the * golden renderstate above. Think twice before you try diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c index c5eb26a7ee79..16084749adf5 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.c +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c @@ -1820,13 +1820,15 @@ static int ring_request_alloc(struct i915_request *request) GEM_BUG_ON(!request->hw_context->pin_count); - /* Flush enough space to reduce the likelihood of waiting after + /* + * Flush enough space to reduce the likelihood of waiting after * we start building the request - in which case we will just * have to repeat work. */ request->reserved_space += LEGACY_REQUEST_SIZE; - ret = intel_ring_wait_for_space(request->ring, request->reserved_space); + /* Unconditionally invalidate GPU caches and TLBs. */ + ret = request->engine->emit_flush(request, EMIT_INVALIDATE); if (ret) return ret; From f2253bd9859bab65fdbc94bf5ce1876c403a11eb Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Fri, 7 Dec 2018 09:02:12 +0000 Subject: [PATCH 025/118] drm/i915/ringbuffer: EMIT_INVALIDATE after switch context The recommend procedure was to switch contexts (and mm) then invalidate the TLBs. Make it so. Signed-off-by: Chris Wilson Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181207090213.14352-2-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/intel_ringbuffer.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c index 16084749adf5..74a4d587c312 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.c +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c @@ -1827,12 +1827,12 @@ static int ring_request_alloc(struct i915_request *request) */ request->reserved_space += LEGACY_REQUEST_SIZE; - /* Unconditionally invalidate GPU caches and TLBs. */ - ret = request->engine->emit_flush(request, EMIT_INVALIDATE); + ret = switch_context(request); if (ret) return ret; - ret = switch_context(request); + /* Unconditionally invalidate GPU caches and TLBs. */ + ret = request->engine->emit_flush(request, EMIT_INVALIDATE); if (ret) return ret; From e8894267cc3325901073e8adf0a63e2dc53b6242 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Fri, 7 Dec 2018 09:02:13 +0000 Subject: [PATCH 026/118] drm/i915: Pipeline PDP updates for Braswell Currently we face a severe problem on Braswell that manifests as invalid ppGTT accesses. The code tries to maintain the PDP (page directory pointers) inside the context in two ways, direct write into the context and a pipelined LRI update. The direct write into the context is fundamentally racy as it is unserialised with any access (read or write) the GPU is doing. By asserting that Braswell is not used with vGPU (currently an unsupported platform) we can eliminate the dangerous direct write into the context image and solely use the pipelined update. However, the LRI of the PDP fouls up the GPU, causing it to freeze and take out the machine with "forcewake ack timeouts". This seems possible to workaround by preventing the GPU from sleeping (via means of disabling the power-state management interface, i.e. forcing each ring to remain awake) around the update. Equally, it seems an EMIT_INVALIDATE before the LRI is sufficient to prevent the forcewake errors. Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=108656 References: https://bugs.freedesktop.org/show_bug.cgi?id=108714 Signed-off-by: Chris Wilson Cc: Tvrtko Ursulin Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181207090213.14352-3-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_gem_gtt.c | 2 - drivers/gpu/drm/i915/intel_lrc.c | 140 ++++++++++++++-------------- 2 files changed, 69 insertions(+), 73 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index add1fe7aeb93..62bde517d383 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -1423,8 +1423,6 @@ static int gen8_ppgtt_alloc_pdp(struct i915_address_space *vm, gen8_initialize_pd(vm, pd); gen8_ppgtt_set_pdpe(vm, pdp, pd, pdpe); GEM_BUG_ON(pdp->used_pdpes > i915_pdpes_per_pdp(vm)); - - mark_tlbs_dirty(i915_vm_to_ppgtt(vm)); } ret = gen8_ppgtt_alloc_pd(vm, pd, start, length); diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index a9084a54c0f4..ae7e5b288ed5 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -363,31 +363,12 @@ execlists_context_schedule_out(struct i915_request *rq, unsigned long status) trace_i915_request_out(rq); } -static void -execlists_update_context_pdps(struct i915_hw_ppgtt *ppgtt, u32 *reg_state) -{ - ASSIGN_CTX_PDP(ppgtt, reg_state, 3); - ASSIGN_CTX_PDP(ppgtt, reg_state, 2); - ASSIGN_CTX_PDP(ppgtt, reg_state, 1); - ASSIGN_CTX_PDP(ppgtt, reg_state, 0); -} - static u64 execlists_update_context(struct i915_request *rq) { - struct i915_hw_ppgtt *ppgtt = rq->gem_context->ppgtt; struct intel_context *ce = rq->hw_context; - u32 *reg_state = ce->lrc_reg_state; - reg_state[CTX_RING_TAIL+1] = intel_ring_set_tail(rq->ring, rq->tail); - - /* - * True 32b PPGTT with dynamic page allocation: update PDP - * registers and point the unallocated PDPs to scratch page. - * PML4 is allocated during ppgtt init, so this is not needed - * in 48-bit mode. - */ - if (!i915_vm_is_48bit(&ppgtt->vm)) - execlists_update_context_pdps(ppgtt, reg_state); + ce->lrc_reg_state[CTX_RING_TAIL + 1] = + intel_ring_set_tail(rq->ring, rq->tail); /* * Make sure the context image is complete before we submit it to HW. @@ -1270,6 +1251,59 @@ execlists_context_pin(struct intel_engine_cs *engine, return __execlists_context_pin(engine, ctx, ce); } +static int emit_pdps(struct i915_request *rq) +{ + const struct intel_engine_cs * const engine = rq->engine; + struct i915_hw_ppgtt * const ppgtt = rq->gem_context->ppgtt; + int err, i; + u32 *cs; + + GEM_BUG_ON(intel_vgpu_active(rq->i915)); + + /* + * Beware ye of the dragons, this sequence is magic! + * + * Small changes to this sequence can cause anything from + * GPU hangs to forcewake errors and machine lockups! + */ + + /* Flush any residual operations from the context load */ + err = engine->emit_flush(rq, EMIT_FLUSH); + if (err) + return err; + + /* Magic required to prevent forcewake errors! */ + err = engine->emit_flush(rq, EMIT_INVALIDATE); + if (err) + return err; + + cs = intel_ring_begin(rq, 4 * GEN8_3LVL_PDPES + 2); + if (IS_ERR(cs)) + return PTR_ERR(cs); + + /* Ensure the LRI have landed before we invalidate & continue */ + *cs++ = MI_LOAD_REGISTER_IMM(2 * GEN8_3LVL_PDPES) | MI_LRI_FORCE_POSTED; + for (i = GEN8_3LVL_PDPES; i--; ) { + const dma_addr_t pd_daddr = i915_page_dir_dma_addr(ppgtt, i); + + *cs++ = i915_mmio_reg_offset(GEN8_RING_PDP_UDW(engine, i)); + *cs++ = upper_32_bits(pd_daddr); + *cs++ = i915_mmio_reg_offset(GEN8_RING_PDP_LDW(engine, i)); + *cs++ = lower_32_bits(pd_daddr); + } + *cs++ = MI_NOOP; + + intel_ring_advance(rq, cs); + + /* Be doubly sure the LRI have landed before proceeding */ + err = engine->emit_flush(rq, EMIT_FLUSH); + if (err) + return err; + + /* Re-invalidate the TLB for luck */ + return engine->emit_flush(rq, EMIT_INVALIDATE); +} + static int execlists_request_alloc(struct i915_request *request) { int ret; @@ -1283,11 +1317,6 @@ static int execlists_request_alloc(struct i915_request *request) */ request->reserved_space += EXECLISTS_REQUEST_SIZE; - /* Unconditionally invalidate GPU caches and TLBs. */ - ret = request->engine->emit_flush(request, EMIT_INVALIDATE); - if (ret) - return ret; - /* * Note that after this point, we have committed to using * this request as it is being used to both track the @@ -1296,6 +1325,14 @@ static int execlists_request_alloc(struct i915_request *request) * to cancel/unwind this request now. */ + /* Unconditionally invalidate GPU caches and TLBs. */ + if (i915_vm_is_48bit(&request->gem_context->ppgtt->vm)) + ret = request->engine->emit_flush(request, EMIT_INVALIDATE); + else + ret = emit_pdps(request); + if (ret) + return ret; + request->reserved_space -= EXECLISTS_REQUEST_SIZE; return 0; } @@ -1831,56 +1868,11 @@ static void execlists_reset_finish(struct intel_engine_cs *engine) atomic_read(&execlists->tasklet.count)); } -static int intel_logical_ring_emit_pdps(struct i915_request *rq) -{ - struct i915_hw_ppgtt *ppgtt = rq->gem_context->ppgtt; - struct intel_engine_cs *engine = rq->engine; - const int num_lri_cmds = GEN8_3LVL_PDPES * 2; - u32 *cs; - int i; - - cs = intel_ring_begin(rq, num_lri_cmds * 2 + 2); - if (IS_ERR(cs)) - return PTR_ERR(cs); - - *cs++ = MI_LOAD_REGISTER_IMM(num_lri_cmds); - for (i = GEN8_3LVL_PDPES - 1; i >= 0; i--) { - const dma_addr_t pd_daddr = i915_page_dir_dma_addr(ppgtt, i); - - *cs++ = i915_mmio_reg_offset(GEN8_RING_PDP_UDW(engine, i)); - *cs++ = upper_32_bits(pd_daddr); - *cs++ = i915_mmio_reg_offset(GEN8_RING_PDP_LDW(engine, i)); - *cs++ = lower_32_bits(pd_daddr); - } - - *cs++ = MI_NOOP; - intel_ring_advance(rq, cs); - - return 0; -} - static int gen8_emit_bb_start(struct i915_request *rq, u64 offset, u32 len, const unsigned int flags) { u32 *cs; - int ret; - - /* Don't rely in hw updating PDPs, specially in lite-restore. - * Ideally, we should set Force PD Restore in ctx descriptor, - * but we can't. Force Restore would be a second option, but - * it is unsafe in case of lite-restore (because the ctx is - * not idle). PML4 is allocated during ppgtt init so this is - * not needed in 48-bit.*/ - if ((intel_engine_flag(rq->engine) & rq->gem_context->ppgtt->pd_dirty_rings) && - !i915_vm_is_48bit(&rq->gem_context->ppgtt->vm) && - !intel_vgpu_active(rq->i915)) { - ret = intel_logical_ring_emit_pdps(rq); - if (ret) - return ret; - - rq->gem_context->ppgtt->pd_dirty_rings &= ~intel_engine_flag(rq->engine); - } cs = intel_ring_begin(rq, 6); if (IS_ERR(cs)) @@ -1913,6 +1905,7 @@ static int gen8_emit_bb_start(struct i915_request *rq, *cs++ = MI_ARB_ON_OFF | MI_ARB_DISABLE; *cs++ = MI_NOOP; + intel_ring_advance(rq, cs); return 0; @@ -2524,6 +2517,11 @@ static void execlists_init_reg_state(u32 *regs, * other PDP Descriptors are ignored. */ ASSIGN_CTX_PML4(ctx->ppgtt, regs); + } else { + ASSIGN_CTX_PDP(ctx->ppgtt, regs, 3); + ASSIGN_CTX_PDP(ctx->ppgtt, regs, 2); + ASSIGN_CTX_PDP(ctx->ppgtt, regs, 1); + ASSIGN_CTX_PDP(ctx->ppgtt, regs, 0); } if (rcs) { From e6154e4cb8b0d3692f84ca0d66b4e1ba0389b134 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Fri, 7 Dec 2018 11:05:54 +0000 Subject: [PATCH 027/118] drm/i915: Skip the ERR_PTR error state Although commit fb6f0b64e455 ("drm/i915: Prevent machine hang from Broxton's vtd w/a and error capture") applied cleanly after a 24 month hiatus, the code had moved on with new methods for peeking and fetching the captured gpu info. Make sure we catch all uses of the stashed error state and avoid dereferencing the error pointer. v2: Move error pointer determination into i915_gpu_capture_state v3: Restore early check to avoid capturing and then throwing away subsequent GPU error states. Fixes: fb6f0b64e455 ("drm/i915: Prevent machine hang from Broxton's vtd w/a and error capture") Signed-off-by: Chris Wilson Cc: Tvrtko Ursulin Cc: Joonas Lahtinen Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181207110554.19897-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_debugfs.c | 12 +++++++++--- drivers/gpu/drm/i915/i915_gpu_error.c | 23 ++++++++++++++--------- drivers/gpu/drm/i915/i915_sysfs.c | 4 +++- 3 files changed, 26 insertions(+), 13 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 38dcee1ca062..40a61ef9aac1 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -984,8 +984,8 @@ static int i915_gpu_info_open(struct inode *inode, struct file *file) intel_runtime_pm_get(i915); gpu = i915_capture_gpu_state(i915); intel_runtime_pm_put(i915); - if (!gpu) - return -ENOMEM; + if (IS_ERR(gpu)) + return PTR_ERR(gpu); file->private_data = gpu; return 0; @@ -1018,7 +1018,13 @@ i915_error_state_write(struct file *filp, static int i915_error_state_open(struct inode *inode, struct file *file) { - file->private_data = i915_first_error_state(inode->i_private); + struct i915_gpu_state *error; + + error = i915_first_error_state(inode->i_private); + if (IS_ERR(error)) + return PTR_ERR(error); + + file->private_data = error; return 0; } diff --git a/drivers/gpu/drm/i915/i915_gpu_error.c b/drivers/gpu/drm/i915/i915_gpu_error.c index 07465123c166..3f9ce403c755 100644 --- a/drivers/gpu/drm/i915/i915_gpu_error.c +++ b/drivers/gpu/drm/i915/i915_gpu_error.c @@ -1907,9 +1907,16 @@ i915_capture_gpu_state(struct drm_i915_private *i915) { struct i915_gpu_state *error; + /* Check if GPU capture has been disabled */ + error = READ_ONCE(i915->gpu_error.first_error); + if (IS_ERR(error)) + return error; + error = kzalloc(sizeof(*error), GFP_ATOMIC); - if (!error) - return NULL; + if (!error) { + i915_disable_error_state(i915, -ENOMEM); + return ERR_PTR(-ENOMEM); + } kref_init(&error->ref); error->i915 = i915; @@ -1945,11 +1952,8 @@ void i915_capture_error_state(struct drm_i915_private *i915, return; error = i915_capture_gpu_state(i915); - if (!error) { - DRM_DEBUG_DRIVER("out of memory, not capturing error state\n"); - i915_disable_error_state(i915, -ENOMEM); + if (IS_ERR(error)) return; - } i915_error_capture_msg(i915, error, engine_mask, error_msg); DRM_INFO("%s\n", error->error_msg); @@ -1987,7 +1991,7 @@ i915_first_error_state(struct drm_i915_private *i915) spin_lock_irq(&i915->gpu_error.lock); error = i915->gpu_error.first_error; - if (error) + if (!IS_ERR_OR_NULL(error)) i915_gpu_state_get(error); spin_unlock_irq(&i915->gpu_error.lock); @@ -2000,10 +2004,11 @@ void i915_reset_error_state(struct drm_i915_private *i915) spin_lock_irq(&i915->gpu_error.lock); error = i915->gpu_error.first_error; - i915->gpu_error.first_error = NULL; + if (error != ERR_PTR(-ENODEV)) /* if disabled, always disabled */ + i915->gpu_error.first_error = NULL; spin_unlock_irq(&i915->gpu_error.lock); - if (!IS_ERR(error)) + if (!IS_ERR_OR_NULL(error)) i915_gpu_state_put(error); } diff --git a/drivers/gpu/drm/i915/i915_sysfs.c b/drivers/gpu/drm/i915/i915_sysfs.c index 535caebd9813..c0cfe7ae2ba5 100644 --- a/drivers/gpu/drm/i915/i915_sysfs.c +++ b/drivers/gpu/drm/i915/i915_sysfs.c @@ -521,7 +521,9 @@ static ssize_t error_state_read(struct file *filp, struct kobject *kobj, ssize_t ret; gpu = i915_first_error_state(i915); - if (gpu) { + if (IS_ERR(gpu)) { + ret = PTR_ERR(gpu); + } else if (gpu) { ret = i915_gpu_state_copy_to_buffer(gpu, buf, off, count); i915_gpu_state_put(gpu); } else { From a889580c087a9cf91fddb3832ece284174214183 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Fri, 7 Dec 2018 13:40:37 +0000 Subject: [PATCH 028/118] drm/i915: Flush GPU relocs harder for gen3 Adding an extra MI_STORE_DWORD_IMM to the gpu relocation path for gen3 was good, but still not good enough. To survive 24+ hours under test we needed to perform not one, not two but three extra store-dw. Doing so for each GPU relocation was a little unsightly and since we need to worry about userspace hitting the same issues, we should apply the dummy store-dw into the EMIT_FLUSH. Fixes: 7dd4f6729f92 ("drm/i915: Async GPU relocation processing") References: 7fa28e146994 ("drm/i915: Write GPU relocs harder with gen3") Testcase: igt/gem_tiled_fence_blits # blb/pnv Signed-off-by: Chris Wilson Cc: Joonas Lahtinen Reviewed-by: Joonas Lahtinen Link: https://patchwork.freedesktop.org/patch/msgid/20181207134037.11848-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 7 +------ drivers/gpu/drm/i915/intel_ringbuffer.c | 15 ++++++++++++--- 2 files changed, 13 insertions(+), 9 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/i915_gem_execbuffer.c index 7b3ae2333dbf..1a1c04db6c80 100644 --- a/drivers/gpu/drm/i915/i915_gem_execbuffer.c +++ b/drivers/gpu/drm/i915/i915_gem_execbuffer.c @@ -1268,7 +1268,7 @@ relocate_entry(struct i915_vma *vma, else if (gen >= 4) len = 4; else - len = 6; + len = 3; batch = reloc_gpu(eb, vma, len); if (IS_ERR(batch)) @@ -1309,11 +1309,6 @@ relocate_entry(struct i915_vma *vma, *batch++ = MI_STORE_DWORD_IMM | MI_MEM_VIRTUAL; *batch++ = addr; *batch++ = target_offset; - - /* And again for good measure (blb/pnv) */ - *batch++ = MI_STORE_DWORD_IMM | MI_MEM_VIRTUAL; - *batch++ = addr; - *batch++ = target_offset; } goto out; diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c index 74a4d587c312..02f6a9b81083 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.c +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c @@ -69,19 +69,28 @@ unsigned int intel_ring_update_space(struct intel_ring *ring) static int gen2_render_ring_flush(struct i915_request *rq, u32 mode) { + unsigned int num_store_dw; u32 cmd, *cs; cmd = MI_FLUSH; - + num_store_dw = 0; if (mode & EMIT_INVALIDATE) cmd |= MI_READ_FLUSH; + if (mode & EMIT_FLUSH) + num_store_dw = 4; - cs = intel_ring_begin(rq, 2); + cs = intel_ring_begin(rq, 2 + 3 * num_store_dw); if (IS_ERR(cs)) return PTR_ERR(cs); *cs++ = cmd; - *cs++ = MI_NOOP; + while (num_store_dw--) { + *cs++ = MI_STORE_DWORD_IMM | MI_MEM_VIRTUAL; + *cs++ = i915_scratch_offset(rq->i915); + *cs++ = 0; + } + *cs++ = MI_FLUSH | MI_NO_WRITE_FLUSH; + intel_ring_advance(rq, cs); return 0; From 099a132bfb65b76f318390d66a090afbaa31518d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ville=20Syrj=C3=A4l=C3=A4?= Date: Tue, 13 Nov 2018 19:23:28 +0200 Subject: [PATCH 029/118] drm/i915: Use explicit old crtc state in skl_compute_wm() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit skl_compute_wm() wants to compare the old and new watermarks. Currently it gets at the old watermarks via crtc->state, which is confusing since it can point at either the old or the new state depending on where in the sequence we are. In this case it is correct since we have not yet swapped the states, but let's make it super clear what this is doing by using the explicit old state. Cc: Stanislav Lisovskiy Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181113172330.26069-1-ville.syrjala@linux.intel.com Reviewed-by: Rodrigo Vivi --- drivers/gpu/drm/i915/intel_pm.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index a26b4eddda25..eadcece720ce 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -5526,6 +5526,7 @@ skl_compute_wm(struct drm_atomic_state *state) { struct drm_crtc *crtc; struct drm_crtc_state *cstate; + struct drm_crtc_state *old_crtc_state; struct intel_atomic_state *intel_state = to_intel_atomic_state(state); struct skl_ddb_values *results = &intel_state->wm_results; struct skl_pipe_wm *pipe_wm; @@ -5553,11 +5554,11 @@ skl_compute_wm(struct drm_atomic_state *state) * should allow skl_update_pipe_wm() to return failure in cases where * no suitable watermark values can be found. */ - for_each_new_crtc_in_state(state, crtc, cstate, i) { + for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, cstate, i) { struct intel_crtc_state *intel_cstate = to_intel_crtc_state(cstate); const struct skl_pipe_wm *old_pipe_wm = - &to_intel_crtc_state(crtc->state)->wm.skl.optimal; + &to_intel_crtc_state(old_crtc_state)->wm.skl.optimal; pipe_wm = &intel_cstate->wm.skl.optimal; ret = skl_update_pipe_wm(cstate, old_pipe_wm, pipe_wm, &changed); From f9a954ff02dfa6c7b3cf76281ee47d7373269b1d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ville=20Syrj=C3=A4l=C3=A4?= Date: Tue, 13 Nov 2018 19:23:29 +0200 Subject: [PATCH 030/118] drm/i915: Remove bogus FIXME from SKL wm computation MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We do return an error when the watermark calculation fails, so the FIXME claiming otherwise is outdated. Remove it. Cc: Stanislav Lisovskiy Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181113172330.26069-2-ville.syrjala@linux.intel.com Reviewed-by: Rodrigo Vivi --- drivers/gpu/drm/i915/intel_pm.c | 4 ---- 1 file changed, 4 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index eadcece720ce..8ed88b4a9220 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -5549,10 +5549,6 @@ skl_compute_wm(struct drm_atomic_state *state) * Note that the DDB allocation above may have added more CRTC's that * weren't otherwise being modified (and set bits in dirty_pipes) if * pipe allocations had to change. - * - * FIXME: Now that we're doing this in the atomic check phase, we - * should allow skl_update_pipe_wm() to return failure in cases where - * no suitable watermark values can be found. */ for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, cstate, i) { struct intel_crtc_state *intel_cstate = From 0b5b45a61d3ff60b270126f1b5825654a5f9bab5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ville=20Syrj=C3=A4l=C3=A4?= Date: Tue, 13 Nov 2018 19:23:30 +0200 Subject: [PATCH 031/118] drm/i915: Remove dead update_wm_pre assignment from SKL wm code MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit SKL+ do not use crtc_state->update_wm_pre, so there is absolutely no point it setting it. crtc_state->update_wm_pre only exists as a temporary hack for pre-g4x platforms until we redo their watermarks to be be atomic. Cc: Stanislav Lisovskiy Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181113172330.26069-3-ville.syrjala@linux.intel.com Reviewed-by: Rodrigo Vivi --- drivers/gpu/drm/i915/intel_pm.c | 6 ------ 1 file changed, 6 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 8ed88b4a9220..9466c12364c4 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -5568,12 +5568,6 @@ skl_compute_wm(struct drm_atomic_state *state) if (changed) results->dirty_pipes |= drm_crtc_mask(crtc); - - if ((results->dirty_pipes & drm_crtc_mask(crtc)) == 0) - /* This pipe's WM's did not change */ - continue; - - intel_cstate->update_wm_pre = true; } skl_print_wm_changes(intel_state); From cd1d3ee90e5e5dc4da50b6c5d50bc74872288789 Mon Sep 17 00:00:00 2001 From: Matt Roper Date: Mon, 10 Dec 2018 13:54:14 -0800 Subject: [PATCH 032/118] drm/i915: Use intel_ types more consistently for watermark code (v2) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Try to be more consistent about intel_* types rather than drm_* types for lower-level driver functions. v2: - Also drop the intel_crtc parameter from compute_intermediate_wm() since we can just extract it from the crtc_state parameter. (Ville) Signed-off-by: Matt Roper Reviewed-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181210215415.19854-1-matthew.d.roper@intel.com --- drivers/gpu/drm/i915/i915_drv.h | 6 +- drivers/gpu/drm/i915/intel_display.c | 33 ++-- drivers/gpu/drm/i915/intel_drv.h | 10 +- drivers/gpu/drm/i915/intel_pm.c | 255 ++++++++++++--------------- 4 files changed, 137 insertions(+), 167 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 0689e67c966e..330fc0d39c8d 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -281,16 +281,14 @@ struct drm_i915_display_funcs { int (*get_fifo_size)(struct drm_i915_private *dev_priv, enum i9xx_plane_id i9xx_plane); int (*compute_pipe_wm)(struct intel_crtc_state *cstate); - int (*compute_intermediate_wm)(struct drm_device *dev, - struct intel_crtc *intel_crtc, - struct intel_crtc_state *newstate); + int (*compute_intermediate_wm)(struct intel_crtc_state *newstate); void (*initial_watermarks)(struct intel_atomic_state *state, struct intel_crtc_state *cstate); void (*atomic_update_watermarks)(struct intel_atomic_state *state, struct intel_crtc_state *cstate); void (*optimize_watermarks)(struct intel_atomic_state *state, struct intel_crtc_state *cstate); - int (*compute_global_watermarks)(struct drm_atomic_state *state); + int (*compute_global_watermarks)(struct intel_atomic_state *state); void (*update_wm)(struct intel_crtc *crtc); int (*modeset_calc_cdclk)(struct drm_atomic_state *state); /* Returns the active state of the crtc, and if the crtc is active, diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 07c861884c70..943d6832b05d 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -10661,12 +10661,9 @@ static void intel_crtc_destroy(struct drm_crtc *crtc) * * Returns true or false. */ -static bool intel_wm_need_update(struct drm_plane *plane, - struct drm_plane_state *state) +static bool intel_wm_need_update(struct intel_plane_state *cur, + struct intel_plane_state *new) { - struct intel_plane_state *new = to_intel_plane_state(state); - struct intel_plane_state *cur = to_intel_plane_state(plane->state); - /* Update watermarks on tiling or size changes. */ if (new->base.visible != cur->base.visible) return true; @@ -10775,7 +10772,8 @@ int intel_plane_atomic_calc_changes(const struct intel_crtc_state *old_crtc_stat /* must disable cxsr around plane enable/disable */ if (plane->id != PLANE_CURSOR) pipe_config->disable_cxsr = true; - } else if (intel_wm_need_update(&plane->base, plane_state)) { + } else if (intel_wm_need_update(to_intel_plane_state(plane->base.state), + to_intel_plane_state(plane_state))) { if (INTEL_GEN(dev_priv) < 5 && !IS_G4X(dev_priv)) { /* FIXME bollocks */ pipe_config->update_wm_pre = true; @@ -10954,8 +10952,7 @@ static int icl_check_nv12_planes(struct intel_crtc_state *crtc_state) static int intel_crtc_atomic_check(struct drm_crtc *crtc, struct drm_crtc_state *crtc_state) { - struct drm_device *dev = crtc->dev; - struct drm_i915_private *dev_priv = to_i915(dev); + struct drm_i915_private *dev_priv = to_i915(crtc->dev); struct intel_crtc *intel_crtc = to_intel_crtc(crtc); struct intel_crtc_state *pipe_config = to_intel_crtc_state(crtc_state); @@ -11004,9 +11001,7 @@ static int intel_crtc_atomic_check(struct drm_crtc *crtc, * old state and the new state. We can program these * immediately. */ - ret = dev_priv->display.compute_intermediate_wm(dev, - intel_crtc, - pipe_config); + ret = dev_priv->display.compute_intermediate_wm(pipe_config); if (ret) { DRM_DEBUG_KMS("No valid intermediate pipe watermarks are possible\n"); return ret; @@ -11964,7 +11959,7 @@ static void verify_wm_state(struct drm_crtc *crtc, if (INTEL_GEN(dev_priv) < 9 || !new_state->active) return; - skl_pipe_wm_get_hw_state(crtc, &hw_wm); + skl_pipe_wm_get_hw_state(intel_crtc, &hw_wm); sw_wm = &to_intel_crtc_state(new_state)->wm.skl.optimal; skl_pipe_ddb_get_hw_state(intel_crtc, hw_ddb_y, hw_ddb_uv); @@ -12619,9 +12614,9 @@ static int intel_modeset_checks(struct drm_atomic_state *state) * phase. The code here should be run after the per-crtc and per-plane 'check' * handlers to ensure that all derived state has been updated. */ -static int calc_watermark_data(struct drm_atomic_state *state) +static int calc_watermark_data(struct intel_atomic_state *state) { - struct drm_device *dev = state->dev; + struct drm_device *dev = state->base.dev; struct drm_i915_private *dev_priv = to_i915(dev); /* Is there platform-specific watermark information to calculate? */ @@ -12713,7 +12708,7 @@ static int intel_atomic_check(struct drm_device *dev, return ret; intel_fbc_choose_crtc(dev_priv, intel_state); - return calc_watermark_data(state); + return calc_watermark_data(intel_state); } static int intel_atomic_prepare_commit(struct drm_device *dev, @@ -15843,15 +15838,15 @@ intel_modeset_setup_hw_state(struct drm_device *dev, } if (IS_G4X(dev_priv)) { - g4x_wm_get_hw_state(dev); + g4x_wm_get_hw_state(dev_priv); g4x_wm_sanitize(dev_priv); } else if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) { - vlv_wm_get_hw_state(dev); + vlv_wm_get_hw_state(dev_priv); vlv_wm_sanitize(dev_priv); } else if (INTEL_GEN(dev_priv) >= 9) { - skl_wm_get_hw_state(dev); + skl_wm_get_hw_state(dev_priv); } else if (HAS_PCH_SPLIT(dev_priv)) { - ilk_wm_get_hw_state(dev); + ilk_wm_get_hw_state(dev_priv); } for_each_intel_crtc(dev, crtc) { diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index f94a04b4ad87..a8177ccf1d4f 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -2200,16 +2200,16 @@ void gen6_rps_busy(struct drm_i915_private *dev_priv); void gen6_rps_reset_ei(struct drm_i915_private *dev_priv); void gen6_rps_idle(struct drm_i915_private *dev_priv); void gen6_rps_boost(struct i915_request *rq, struct intel_rps_client *rps); -void g4x_wm_get_hw_state(struct drm_device *dev); -void vlv_wm_get_hw_state(struct drm_device *dev); -void ilk_wm_get_hw_state(struct drm_device *dev); -void skl_wm_get_hw_state(struct drm_device *dev); +void g4x_wm_get_hw_state(struct drm_i915_private *dev_priv); +void vlv_wm_get_hw_state(struct drm_i915_private *dev_priv); +void ilk_wm_get_hw_state(struct drm_i915_private *dev_priv); +void skl_wm_get_hw_state(struct drm_i915_private *dev_priv); void skl_pipe_ddb_get_hw_state(struct intel_crtc *crtc, struct skl_ddb_entry *ddb_y, struct skl_ddb_entry *ddb_uv); void skl_ddb_get_hw_state(struct drm_i915_private *dev_priv, struct skl_ddb_allocation *ddb /* out */); -void skl_pipe_wm_get_hw_state(struct drm_crtc *crtc, +void skl_pipe_wm_get_hw_state(struct intel_crtc *crtc, struct skl_pipe_wm *out); void g4x_wm_sanitize(struct drm_i915_private *dev_priv); void vlv_wm_sanitize(struct drm_i915_private *dev_priv); diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 9466c12364c4..2bba5315b764 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -1399,10 +1399,9 @@ static int g4x_compute_pipe_wm(struct intel_crtc_state *crtc_state) return 0; } -static int g4x_compute_intermediate_wm(struct drm_device *dev, - struct intel_crtc *crtc, - struct intel_crtc_state *new_crtc_state) +static int g4x_compute_intermediate_wm(struct intel_crtc_state *new_crtc_state) { + struct intel_crtc *crtc = to_intel_crtc(new_crtc_state->base.crtc); struct g4x_wm_state *intermediate = &new_crtc_state->wm.g4x.intermediate; const struct g4x_wm_state *optimal = &new_crtc_state->wm.g4x.optimal; struct intel_atomic_state *intel_state = @@ -2032,10 +2031,9 @@ static void vlv_atomic_update_fifo(struct intel_atomic_state *state, #undef VLV_FIFO -static int vlv_compute_intermediate_wm(struct drm_device *dev, - struct intel_crtc *crtc, - struct intel_crtc_state *new_crtc_state) +static int vlv_compute_intermediate_wm(struct intel_crtc_state *new_crtc_state) { + struct intel_crtc *crtc = to_intel_crtc(new_crtc_state->base.crtc); struct vlv_wm_state *intermediate = &new_crtc_state->wm.vlv.intermediate; const struct vlv_wm_state *optimal = &new_crtc_state->wm.vlv.optimal; struct intel_atomic_state *intel_state = @@ -2626,13 +2624,12 @@ static unsigned int ilk_fbc_wm_reg_max(const struct drm_i915_private *dev_priv) } /* Calculate the maximum primary/sprite plane watermark */ -static unsigned int ilk_plane_wm_max(const struct drm_device *dev, +static unsigned int ilk_plane_wm_max(const struct drm_i915_private *dev_priv, int level, const struct intel_wm_config *config, enum intel_ddb_partitioning ddb_partitioning, bool is_sprite) { - struct drm_i915_private *dev_priv = to_i915(dev); unsigned int fifo_size = ilk_display_fifo_size(dev_priv); /* if sprites aren't enabled, sprites get nothing */ @@ -2668,7 +2665,7 @@ static unsigned int ilk_plane_wm_max(const struct drm_device *dev, } /* Calculate the maximum cursor plane watermark */ -static unsigned int ilk_cursor_wm_max(const struct drm_device *dev, +static unsigned int ilk_cursor_wm_max(const struct drm_i915_private *dev_priv, int level, const struct intel_wm_config *config) { @@ -2677,19 +2674,19 @@ static unsigned int ilk_cursor_wm_max(const struct drm_device *dev, return 64; /* otherwise just report max that registers can hold */ - return ilk_cursor_wm_reg_max(to_i915(dev), level); + return ilk_cursor_wm_reg_max(dev_priv, level); } -static void ilk_compute_wm_maximums(const struct drm_device *dev, +static void ilk_compute_wm_maximums(const struct drm_i915_private *dev_priv, int level, const struct intel_wm_config *config, enum intel_ddb_partitioning ddb_partitioning, struct ilk_wm_maximums *max) { - max->pri = ilk_plane_wm_max(dev, level, config, ddb_partitioning, false); - max->spr = ilk_plane_wm_max(dev, level, config, ddb_partitioning, true); - max->cur = ilk_cursor_wm_max(dev, level, config); - max->fbc = ilk_fbc_wm_reg_max(to_i915(dev)); + max->pri = ilk_plane_wm_max(dev_priv, level, config, ddb_partitioning, false); + max->spr = ilk_plane_wm_max(dev_priv, level, config, ddb_partitioning, true); + max->cur = ilk_cursor_wm_max(dev_priv, level, config); + max->fbc = ilk_fbc_wm_reg_max(dev_priv); } static void ilk_compute_wm_reg_maximums(const struct drm_i915_private *dev_priv, @@ -3073,7 +3070,7 @@ static void skl_setup_wm_latency(struct drm_i915_private *dev_priv) intel_print_wm_latency(dev_priv, "Gen9 Plane", dev_priv->wm.skl_latency); } -static bool ilk_validate_pipe_wm(struct drm_device *dev, +static bool ilk_validate_pipe_wm(const struct drm_i915_private *dev_priv, struct intel_pipe_wm *pipe_wm) { /* LP0 watermark maximums depend on this pipe alone */ @@ -3085,7 +3082,7 @@ static bool ilk_validate_pipe_wm(struct drm_device *dev, struct ilk_wm_maximums max; /* LP0 watermarks always use 1/2 DDB partitioning */ - ilk_compute_wm_maximums(dev, 0, &config, INTEL_DDB_PART_1_2, &max); + ilk_compute_wm_maximums(dev_priv, 0, &config, INTEL_DDB_PART_1_2, &max); /* At least LP0 must be valid */ if (!ilk_validate_wm_level(0, &max, &pipe_wm->wm[0])) { @@ -3150,7 +3147,7 @@ static int ilk_compute_pipe_wm(struct intel_crtc_state *cstate) if (IS_HASWELL(dev_priv) || IS_BROADWELL(dev_priv)) pipe_wm->linetime = hsw_compute_linetime_wm(cstate); - if (!ilk_validate_pipe_wm(dev, pipe_wm)) + if (!ilk_validate_pipe_wm(dev_priv, pipe_wm)) return -EINVAL; ilk_compute_wm_reg_maximums(dev_priv, 1, &max); @@ -3180,17 +3177,17 @@ static int ilk_compute_pipe_wm(struct intel_crtc_state *cstate) * state and the new state. These can be programmed to the hardware * immediately. */ -static int ilk_compute_intermediate_wm(struct drm_device *dev, - struct intel_crtc *intel_crtc, - struct intel_crtc_state *newstate) +static int ilk_compute_intermediate_wm(struct intel_crtc_state *newstate) { + struct intel_crtc *intel_crtc = to_intel_crtc(newstate->base.crtc); + struct drm_i915_private *dev_priv = to_i915(intel_crtc->base.dev); struct intel_pipe_wm *a = &newstate->wm.ilk.intermediate; struct intel_atomic_state *intel_state = to_intel_atomic_state(newstate->base.state); const struct intel_crtc_state *oldstate = intel_atomic_get_old_crtc_state(intel_state, intel_crtc); const struct intel_pipe_wm *b = &oldstate->wm.ilk.optimal; - int level, max_level = ilk_wm_max_level(to_i915(dev)); + int level, max_level = ilk_wm_max_level(dev_priv); /* * Start with the final, target watermarks, then combine with the @@ -3223,7 +3220,7 @@ static int ilk_compute_intermediate_wm(struct drm_device *dev, * there's no safe way to transition from the old state to * the new state, so we need to fail the atomic transaction. */ - if (!ilk_validate_pipe_wm(dev, a)) + if (!ilk_validate_pipe_wm(dev_priv, a)) return -EINVAL; /* @@ -3239,7 +3236,7 @@ static int ilk_compute_intermediate_wm(struct drm_device *dev, /* * Merge the watermarks from all active pipes for a specific level. */ -static void ilk_merge_wm_level(struct drm_device *dev, +static void ilk_merge_wm_level(struct drm_i915_private *dev_priv, int level, struct intel_wm_level *ret_wm) { @@ -3247,7 +3244,7 @@ static void ilk_merge_wm_level(struct drm_device *dev, ret_wm->enable = true; - for_each_intel_crtc(dev, intel_crtc) { + for_each_intel_crtc(&dev_priv->drm, intel_crtc) { const struct intel_pipe_wm *active = &intel_crtc->wm.active.ilk; const struct intel_wm_level *wm = &active->wm[level]; @@ -3272,12 +3269,11 @@ static void ilk_merge_wm_level(struct drm_device *dev, /* * Merge all low power watermarks for all active pipes. */ -static void ilk_wm_merge(struct drm_device *dev, +static void ilk_wm_merge(struct drm_i915_private *dev_priv, const struct intel_wm_config *config, const struct ilk_wm_maximums *max, struct intel_pipe_wm *merged) { - struct drm_i915_private *dev_priv = to_i915(dev); int level, max_level = ilk_wm_max_level(dev_priv); int last_enabled_level = max_level; @@ -3293,7 +3289,7 @@ static void ilk_wm_merge(struct drm_device *dev, for (level = 1; level <= max_level; level++) { struct intel_wm_level *wm = &merged->wm[level]; - ilk_merge_wm_level(dev, level, wm); + ilk_merge_wm_level(dev_priv, level, wm); if (level > last_enabled_level) wm->enable = false; @@ -3335,22 +3331,20 @@ static int ilk_wm_lp_to_level(int wm_lp, const struct intel_pipe_wm *pipe_wm) } /* The value we need to program into the WM_LPx latency field */ -static unsigned int ilk_wm_lp_latency(struct drm_device *dev, int level) +static unsigned int ilk_wm_lp_latency(struct drm_i915_private *dev_priv, + int level) { - struct drm_i915_private *dev_priv = to_i915(dev); - if (IS_HASWELL(dev_priv) || IS_BROADWELL(dev_priv)) return 2 * level; else return dev_priv->wm.pri_latency[level]; } -static void ilk_compute_wm_results(struct drm_device *dev, +static void ilk_compute_wm_results(struct drm_i915_private *dev_priv, const struct intel_pipe_wm *merged, enum intel_ddb_partitioning partitioning, struct ilk_wm_values *results) { - struct drm_i915_private *dev_priv = to_i915(dev); struct intel_crtc *intel_crtc; int level, wm_lp; @@ -3370,7 +3364,7 @@ static void ilk_compute_wm_results(struct drm_device *dev, * disabled. Doing otherwise could cause underruns. */ results->wm_lp[wm_lp - 1] = - (ilk_wm_lp_latency(dev, level) << WM1_LP_LATENCY_SHIFT) | + (ilk_wm_lp_latency(dev_priv, level) << WM1_LP_LATENCY_SHIFT) | (r->pri_val << WM1_LP_SR_SHIFT) | r->cur_val; @@ -3396,7 +3390,7 @@ static void ilk_compute_wm_results(struct drm_device *dev, } /* LP0 register values */ - for_each_intel_crtc(dev, intel_crtc) { + for_each_intel_crtc(&dev_priv->drm, intel_crtc) { enum pipe pipe = intel_crtc->pipe; const struct intel_wm_level *r = &intel_crtc->wm.active.ilk.wm[0]; @@ -3415,11 +3409,12 @@ static void ilk_compute_wm_results(struct drm_device *dev, /* Find the result with the highest level enabled. Check for enable_fbc_wm in * case both are at the same level. Prefer r1 in case they're the same. */ -static struct intel_pipe_wm *ilk_find_best_result(struct drm_device *dev, - struct intel_pipe_wm *r1, - struct intel_pipe_wm *r2) +static struct intel_pipe_wm * +ilk_find_best_result(struct drm_i915_private *dev_priv, + struct intel_pipe_wm *r1, + struct intel_pipe_wm *r2) { - int level, max_level = ilk_wm_max_level(to_i915(dev)); + int level, max_level = ilk_wm_max_level(dev_priv); int level1 = 0, level2 = 0; for (level = 1; level <= max_level; level++) { @@ -4307,10 +4302,9 @@ icl_get_total_relative_data_rate(struct intel_crtc_state *intel_cstate, } static uint16_t -skl_ddb_min_alloc(const struct drm_plane_state *pstate, const int plane) +skl_ddb_min_alloc(const struct intel_plane_state *plane_state, const int plane) { - struct drm_framebuffer *fb = pstate->fb; - struct intel_plane_state *intel_pstate = to_intel_plane_state(pstate); + struct drm_framebuffer *fb = plane_state->base.fb; uint32_t src_w, src_h; uint32_t min_scanlines = 8; uint8_t plane_bpp; @@ -4334,8 +4328,8 @@ skl_ddb_min_alloc(const struct drm_plane_state *pstate, const int plane) * the 90/270 degree plane rotation cases (to match the * GTT mapping), hence no need to account for rotation here. */ - src_w = drm_rect_width(&intel_pstate->base.src) >> 16; - src_h = drm_rect_height(&intel_pstate->base.src) >> 16; + src_w = drm_rect_width(&plane_state->base.src) >> 16; + src_h = drm_rect_height(&plane_state->base.src) >> 16; /* Halve UV plane width and height for NV12 */ if (plane == 1) { @@ -4345,7 +4339,7 @@ skl_ddb_min_alloc(const struct drm_plane_state *pstate, const int plane) plane_bpp = fb->format->cpp[plane]; - if (drm_rotation_90_or_270(pstate->rotation)) { + if (drm_rotation_90_or_270(plane_state->base.rotation)) { switch (plane_bpp) { case 1: min_scanlines = 32; @@ -4388,14 +4382,15 @@ skl_ddb_calc_min(const struct intel_crtc_state *cstate, int num_active, continue; if (!plane_state->linked_plane) { - minimum[plane_id] = skl_ddb_min_alloc(pstate, 0); - uv_minimum[plane_id] = skl_ddb_min_alloc(pstate, 1); + minimum[plane_id] = skl_ddb_min_alloc(plane_state, 0); + uv_minimum[plane_id] = + skl_ddb_min_alloc(plane_state, 1); } else { enum plane_id y_plane_id = plane_state->linked_plane->id; - minimum[y_plane_id] = skl_ddb_min_alloc(pstate, 0); - minimum[plane_id] = skl_ddb_min_alloc(pstate, 1); + minimum[y_plane_id] = skl_ddb_min_alloc(plane_state, 0); + minimum[plane_id] = skl_ddb_min_alloc(plane_state, 1); } } @@ -5251,15 +5246,14 @@ bool skl_ddb_allocation_overlaps(const struct skl_ddb_entry *ddb, return false; } -static int skl_update_pipe_wm(struct drm_crtc_state *cstate, +static int skl_update_pipe_wm(struct intel_crtc_state *cstate, const struct skl_pipe_wm *old_pipe_wm, struct skl_pipe_wm *pipe_wm, /* out */ bool *changed /* out */) { - struct intel_crtc_state *intel_cstate = to_intel_crtc_state(cstate); int ret; - ret = skl_build_pipe_wm(intel_cstate, pipe_wm); + ret = skl_build_pipe_wm(cstate, pipe_wm); if (ret) return ret; @@ -5272,14 +5266,14 @@ static int skl_update_pipe_wm(struct drm_crtc_state *cstate, } static uint32_t -pipes_modified(struct drm_atomic_state *state) +pipes_modified(struct intel_atomic_state *state) { - struct drm_crtc *crtc; - struct drm_crtc_state *cstate; + struct intel_crtc *crtc; + struct intel_crtc_state *cstate; uint32_t i, ret = 0; - for_each_new_crtc_in_state(state, crtc, cstate, i) - ret |= drm_crtc_mask(crtc); + for_each_new_intel_crtc_in_state(state, crtc, cstate, i) + ret |= drm_crtc_mask(&crtc->base); return ret; } @@ -5314,11 +5308,10 @@ skl_ddb_add_affected_planes(const struct intel_crtc_state *old_crtc_state, } static int -skl_compute_ddb(struct drm_atomic_state *state) +skl_compute_ddb(struct intel_atomic_state *state) { - const struct drm_i915_private *dev_priv = to_i915(state->dev); - struct intel_atomic_state *intel_state = to_intel_atomic_state(state); - struct skl_ddb_allocation *ddb = &intel_state->wm_results.ddb; + const struct drm_i915_private *dev_priv = to_i915(state->base.dev); + struct skl_ddb_allocation *ddb = &state->wm_results.ddb; struct intel_crtc_state *old_crtc_state; struct intel_crtc_state *new_crtc_state; struct intel_crtc *crtc; @@ -5326,7 +5319,7 @@ skl_compute_ddb(struct drm_atomic_state *state) memcpy(ddb, &dev_priv->wm.skl_hw.ddb, sizeof(*ddb)); - for_each_oldnew_intel_crtc_in_state(intel_state, crtc, old_crtc_state, + for_each_oldnew_intel_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { ret = skl_allocate_pipe_ddb(new_crtc_state, ddb); if (ret) @@ -5372,14 +5365,12 @@ skl_print_wm_changes(struct intel_atomic_state *state) } static int -skl_ddb_add_affected_pipes(struct drm_atomic_state *state, bool *changed) +skl_ddb_add_affected_pipes(struct intel_atomic_state *state, bool *changed) { - struct drm_device *dev = state->dev; + struct drm_device *dev = state->base.dev; const struct drm_i915_private *dev_priv = to_i915(dev); - const struct drm_crtc *crtc; - const struct drm_crtc_state *cstate; - struct intel_crtc *intel_crtc; - struct intel_atomic_state *intel_state = to_intel_atomic_state(state); + struct intel_crtc *crtc; + struct intel_crtc_state *crtc_state; uint32_t realloc_pipes = pipes_modified(state); int ret, i; @@ -5398,7 +5389,7 @@ skl_ddb_add_affected_pipes(struct drm_atomic_state *state, bool *changed) * since any racing commits that want to update them would need to * hold _all_ CRTC state mutexes. */ - for_each_new_crtc_in_state(state, crtc, cstate, i) + for_each_new_intel_crtc_in_state(state, crtc, crtc_state, i) (*changed) = true; if (!*changed) @@ -5412,20 +5403,20 @@ skl_ddb_add_affected_pipes(struct drm_atomic_state *state, bool *changed) */ if (dev_priv->wm.distrust_bios_wm) { ret = drm_modeset_lock(&dev->mode_config.connection_mutex, - state->acquire_ctx); + state->base.acquire_ctx); if (ret) return ret; - intel_state->active_pipe_changes = ~0; + state->active_pipe_changes = ~0; /* - * We usually only initialize intel_state->active_crtcs if we + * We usually only initialize state->active_crtcs if we * we're doing a modeset; make sure this field is always * initialized during the sanitization process that happens * on the first commit too. */ - if (!intel_state->modeset) - intel_state->active_crtcs = dev_priv->active_crtcs; + if (!state->modeset) + state->active_crtcs = dev_priv->active_crtcs; } /* @@ -5441,21 +5432,19 @@ skl_ddb_add_affected_pipes(struct drm_atomic_state *state, bool *changed) * any other display updates race with this transaction, so we need * to grab the lock on *all* CRTC's. */ - if (intel_state->active_pipe_changes || intel_state->modeset) { + if (state->active_pipe_changes || state->modeset) { realloc_pipes = ~0; - intel_state->wm_results.dirty_pipes = ~0; + state->wm_results.dirty_pipes = ~0; } /* * We're not recomputing for the pipes not included in the commit, so * make sure we start with the current state. */ - for_each_intel_crtc_mask(dev, intel_crtc, realloc_pipes) { - struct intel_crtc_state *cstate; - - cstate = intel_atomic_get_crtc_state(state, intel_crtc); - if (IS_ERR(cstate)) - return PTR_ERR(cstate); + for_each_intel_crtc_mask(dev, crtc, realloc_pipes) { + crtc_state = intel_atomic_get_crtc_state(&state->base, crtc); + if (IS_ERR(crtc_state)) + return PTR_ERR(crtc_state); } return 0; @@ -5522,13 +5511,12 @@ static int skl_wm_add_affected_planes(struct intel_atomic_state *state, } static int -skl_compute_wm(struct drm_atomic_state *state) +skl_compute_wm(struct intel_atomic_state *state) { - struct drm_crtc *crtc; - struct drm_crtc_state *cstate; - struct drm_crtc_state *old_crtc_state; - struct intel_atomic_state *intel_state = to_intel_atomic_state(state); - struct skl_ddb_values *results = &intel_state->wm_results; + struct intel_crtc *crtc; + struct intel_crtc_state *cstate; + struct intel_crtc_state *old_crtc_state; + struct skl_ddb_values *results = &state->wm_results; struct skl_pipe_wm *pipe_wm; bool changed = false; int ret, i; @@ -5550,27 +5538,25 @@ skl_compute_wm(struct drm_atomic_state *state) * weren't otherwise being modified (and set bits in dirty_pipes) if * pipe allocations had to change. */ - for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, cstate, i) { - struct intel_crtc_state *intel_cstate = - to_intel_crtc_state(cstate); + for_each_oldnew_intel_crtc_in_state(state, crtc, old_crtc_state, + cstate, i) { const struct skl_pipe_wm *old_pipe_wm = - &to_intel_crtc_state(old_crtc_state)->wm.skl.optimal; + &old_crtc_state->wm.skl.optimal; - pipe_wm = &intel_cstate->wm.skl.optimal; + pipe_wm = &cstate->wm.skl.optimal; ret = skl_update_pipe_wm(cstate, old_pipe_wm, pipe_wm, &changed); if (ret) return ret; - ret = skl_wm_add_affected_planes(intel_state, - to_intel_crtc(crtc)); + ret = skl_wm_add_affected_planes(state, crtc); if (ret) return ret; if (changed) - results->dirty_pipes |= drm_crtc_mask(crtc); + results->dirty_pipes |= drm_crtc_mask(&crtc->base); } - skl_print_wm_changes(intel_state); + skl_print_wm_changes(state); return 0; } @@ -5608,13 +5594,13 @@ static void skl_initial_wm(struct intel_atomic_state *state, mutex_unlock(&dev_priv->wm.wm_mutex); } -static void ilk_compute_wm_config(struct drm_device *dev, +static void ilk_compute_wm_config(struct drm_i915_private *dev_priv, struct intel_wm_config *config) { struct intel_crtc *crtc; /* Compute the currently _active_ config */ - for_each_intel_crtc(dev, crtc) { + for_each_intel_crtc(&dev_priv->drm, crtc) { const struct intel_pipe_wm *wm = &crtc->wm.active.ilk; if (!wm->pipe_enabled) @@ -5628,25 +5614,24 @@ static void ilk_compute_wm_config(struct drm_device *dev, static void ilk_program_watermarks(struct drm_i915_private *dev_priv) { - struct drm_device *dev = &dev_priv->drm; struct intel_pipe_wm lp_wm_1_2 = {}, lp_wm_5_6 = {}, *best_lp_wm; struct ilk_wm_maximums max; struct intel_wm_config config = {}; struct ilk_wm_values results = {}; enum intel_ddb_partitioning partitioning; - ilk_compute_wm_config(dev, &config); + ilk_compute_wm_config(dev_priv, &config); - ilk_compute_wm_maximums(dev, 1, &config, INTEL_DDB_PART_1_2, &max); - ilk_wm_merge(dev, &config, &max, &lp_wm_1_2); + ilk_compute_wm_maximums(dev_priv, 1, &config, INTEL_DDB_PART_1_2, &max); + ilk_wm_merge(dev_priv, &config, &max, &lp_wm_1_2); /* 5/6 split only in single pipe config on IVB+ */ if (INTEL_GEN(dev_priv) >= 7 && config.num_pipes_active == 1 && config.sprites_enabled) { - ilk_compute_wm_maximums(dev, 1, &config, INTEL_DDB_PART_5_6, &max); - ilk_wm_merge(dev, &config, &max, &lp_wm_5_6); + ilk_compute_wm_maximums(dev_priv, 1, &config, INTEL_DDB_PART_5_6, &max); + ilk_wm_merge(dev_priv, &config, &max, &lp_wm_5_6); - best_lp_wm = ilk_find_best_result(dev, &lp_wm_1_2, &lp_wm_5_6); + best_lp_wm = ilk_find_best_result(dev_priv, &lp_wm_1_2, &lp_wm_5_6); } else { best_lp_wm = &lp_wm_1_2; } @@ -5654,7 +5639,7 @@ static void ilk_program_watermarks(struct drm_i915_private *dev_priv) partitioning = (best_lp_wm == &lp_wm_1_2) ? INTEL_DDB_PART_1_2 : INTEL_DDB_PART_5_6; - ilk_compute_wm_results(dev, best_lp_wm, partitioning, &results); + ilk_compute_wm_results(dev_priv, best_lp_wm, partitioning, &results); ilk_write_wm_values(dev_priv, &results); } @@ -5694,19 +5679,18 @@ static inline void skl_wm_level_from_reg_val(uint32_t val, PLANE_WM_LINES_MASK; } -void skl_pipe_wm_get_hw_state(struct drm_crtc *crtc, +void skl_pipe_wm_get_hw_state(struct intel_crtc *crtc, struct skl_pipe_wm *out) { - struct drm_i915_private *dev_priv = to_i915(crtc->dev); - struct intel_crtc *intel_crtc = to_intel_crtc(crtc); - enum pipe pipe = intel_crtc->pipe; + struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); + enum pipe pipe = crtc->pipe; int level, max_level; enum plane_id plane_id; uint32_t val; max_level = ilk_wm_max_level(dev_priv); - for_each_plane_id_on_crtc(intel_crtc, plane_id) { + for_each_plane_id_on_crtc(crtc, plane_id) { struct skl_plane_wm *wm = &out->planes[plane_id]; for (level = 0; level <= max_level; level++) { @@ -5726,30 +5710,27 @@ void skl_pipe_wm_get_hw_state(struct drm_crtc *crtc, skl_wm_level_from_reg_val(val, &wm->trans_wm); } - if (!intel_crtc->active) + if (!crtc->active) return; out->linetime = I915_READ(PIPE_WM_LINETIME(pipe)); } -void skl_wm_get_hw_state(struct drm_device *dev) +void skl_wm_get_hw_state(struct drm_i915_private *dev_priv) { - struct drm_i915_private *dev_priv = to_i915(dev); struct skl_ddb_values *hw = &dev_priv->wm.skl_hw; struct skl_ddb_allocation *ddb = &dev_priv->wm.skl_hw.ddb; - struct drm_crtc *crtc; - struct intel_crtc *intel_crtc; + struct intel_crtc *crtc; struct intel_crtc_state *cstate; skl_ddb_get_hw_state(dev_priv, ddb); - list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) { - intel_crtc = to_intel_crtc(crtc); - cstate = to_intel_crtc_state(crtc->state); + for_each_intel_crtc(&dev_priv->drm, crtc) { + cstate = to_intel_crtc_state(crtc->base.state); skl_pipe_wm_get_hw_state(crtc, &cstate->wm.skl.optimal); - if (intel_crtc->active) - hw->dirty_pipes |= drm_crtc_mask(crtc); + if (crtc->active) + hw->dirty_pipes |= drm_crtc_mask(&crtc->base); } if (dev_priv->active_crtcs) { @@ -5758,15 +5739,14 @@ void skl_wm_get_hw_state(struct drm_device *dev) } } -static void ilk_pipe_wm_get_hw_state(struct drm_crtc *crtc) +static void ilk_pipe_wm_get_hw_state(struct intel_crtc *crtc) { - struct drm_device *dev = crtc->dev; + struct drm_device *dev = crtc->base.dev; struct drm_i915_private *dev_priv = to_i915(dev); struct ilk_wm_values *hw = &dev_priv->wm.hw; - struct intel_crtc *intel_crtc = to_intel_crtc(crtc); - struct intel_crtc_state *cstate = to_intel_crtc_state(crtc->state); + struct intel_crtc_state *cstate = to_intel_crtc_state(crtc->base.state); struct intel_pipe_wm *active = &cstate->wm.ilk.optimal; - enum pipe pipe = intel_crtc->pipe; + enum pipe pipe = crtc->pipe; static const i915_reg_t wm0_pipe_reg[] = { [PIPE_A] = WM0_PIPEA_ILK, [PIPE_B] = WM0_PIPEB_ILK, @@ -5779,7 +5759,7 @@ static void ilk_pipe_wm_get_hw_state(struct drm_crtc *crtc) memset(active, 0, sizeof(*active)); - active->pipe_enabled = intel_crtc->active; + active->pipe_enabled = crtc->active; if (active->pipe_enabled) { u32 tmp = hw->wm_pipe[pipe]; @@ -5807,7 +5787,7 @@ static void ilk_pipe_wm_get_hw_state(struct drm_crtc *crtc) active->wm[level].enable = true; } - intel_crtc->wm.active.ilk = *active; + crtc->wm.active.ilk = *active; } #define _FW_WM(value, plane) \ @@ -5917,9 +5897,8 @@ static void vlv_read_wm_values(struct drm_i915_private *dev_priv, #undef _FW_WM #undef _FW_WM_VLV -void g4x_wm_get_hw_state(struct drm_device *dev) +void g4x_wm_get_hw_state(struct drm_i915_private *dev_priv) { - struct drm_i915_private *dev_priv = to_i915(dev); struct g4x_wm_values *wm = &dev_priv->wm.g4x; struct intel_crtc *crtc; @@ -5927,7 +5906,7 @@ void g4x_wm_get_hw_state(struct drm_device *dev) wm->cxsr = I915_READ(FW_BLC_SELF) & FW_BLC_SELF_EN; - for_each_intel_crtc(dev, crtc) { + for_each_intel_crtc(&dev_priv->drm, crtc) { struct intel_crtc_state *crtc_state = to_intel_crtc_state(crtc->base.state); struct g4x_wm_state *active = &crtc->wm.active.g4x; @@ -6058,9 +6037,8 @@ void g4x_wm_sanitize(struct drm_i915_private *dev_priv) mutex_unlock(&dev_priv->wm.wm_mutex); } -void vlv_wm_get_hw_state(struct drm_device *dev) +void vlv_wm_get_hw_state(struct drm_i915_private *dev_priv) { - struct drm_i915_private *dev_priv = to_i915(dev); struct vlv_wm_values *wm = &dev_priv->wm.vlv; struct intel_crtc *crtc; u32 val; @@ -6104,7 +6082,7 @@ void vlv_wm_get_hw_state(struct drm_device *dev) mutex_unlock(&dev_priv->pcu_lock); } - for_each_intel_crtc(dev, crtc) { + for_each_intel_crtc(&dev_priv->drm, crtc) { struct intel_crtc_state *crtc_state = to_intel_crtc_state(crtc->base.state); struct vlv_wm_state *active = &crtc->wm.active.vlv; @@ -6221,15 +6199,14 @@ static void ilk_init_lp_watermarks(struct drm_i915_private *dev_priv) */ } -void ilk_wm_get_hw_state(struct drm_device *dev) +void ilk_wm_get_hw_state(struct drm_i915_private *dev_priv) { - struct drm_i915_private *dev_priv = to_i915(dev); struct ilk_wm_values *hw = &dev_priv->wm.hw; - struct drm_crtc *crtc; + struct intel_crtc *crtc; ilk_init_lp_watermarks(dev_priv); - for_each_crtc(dev, crtc) + for_each_intel_crtc(&dev_priv->drm, crtc) ilk_pipe_wm_get_hw_state(crtc); hw->wm_lp[0] = I915_READ(WM1_LP_ILK); From 302da0cdf784f2aab5e84aaa14c0132d405542f9 Mon Sep 17 00:00:00 2001 From: Matt Roper Date: Mon, 10 Dec 2018 13:54:15 -0800 Subject: [PATCH 033/118] drm/i915: Use intel_ types more consistently for color management code (v2) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Try to be more consistent about intel_* types rather than drm_* types for lower-level driver functions. While we're at it, let's also be more consistent with state variable naming (half of the platforms use the name 'state' whereas the other half used 'crtc_state'). While we're touching these variables, let's also be more consistent about always naming the intel_crtc_state's "crtc_state" rather than "state" so that different platform types aren't using different naming conventions. v2: - s/state/crtc_state/ for consistency between platform types (Ville) - Drop the crtc parameter to intel_color_check(); we can just pull that out of the state object. Signed-off-by: Matt Roper Reviewed-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181210215415.19854-2-matthew.d.roper@intel.com --- drivers/gpu/drm/i915/i915_drv.h | 4 +- drivers/gpu/drm/i915/intel_color.c | 215 +++++++++++++-------------- drivers/gpu/drm/i915/intel_display.c | 20 +-- drivers/gpu/drm/i915/intel_drv.h | 8 +- 4 files changed, 117 insertions(+), 130 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 330fc0d39c8d..e70707e79386 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -320,8 +320,8 @@ struct drm_i915_display_funcs { /* display clock increase/decrease */ /* pll clock increase/decrease */ - void (*load_csc_matrix)(struct drm_crtc_state *crtc_state); - void (*load_luts)(struct drm_crtc_state *crtc_state); + void (*load_csc_matrix)(struct intel_crtc_state *crtc_state); + void (*load_luts)(struct intel_crtc_state *crtc_state); }; #define CSR_VERSION(major, minor) ((major) << 16 | (minor)) diff --git a/drivers/gpu/drm/i915/intel_color.c b/drivers/gpu/drm/i915/intel_color.c index 5127da286a2b..1d572e83db7f 100644 --- a/drivers/gpu/drm/i915/intel_color.c +++ b/drivers/gpu/drm/i915/intel_color.c @@ -74,12 +74,14 @@ #define ILK_CSC_COEFF_1_0 \ ((7 << 12) | ILK_CSC_COEFF_FP(CTM_COEFF_1_0, 8)) -static bool crtc_state_is_legacy_gamma(struct drm_crtc_state *state) +static bool crtc_state_is_legacy_gamma(struct intel_crtc_state *crtc_state) { - return !state->degamma_lut && - !state->ctm && - state->gamma_lut && - drm_color_lut_size(state->gamma_lut) == LEGACY_LUT_LENGTH; + int lut_length = drm_color_lut_size(crtc_state->base.gamma_lut); + + return !crtc_state->base.degamma_lut && + !crtc_state->base.ctm && + crtc_state->base.gamma_lut && + lut_length == LEGACY_LUT_LENGTH; } /* @@ -108,10 +110,10 @@ static u64 *ctm_mult_by_limited(u64 *result, const u64 *input) return result; } -static void ilk_load_ycbcr_conversion_matrix(struct intel_crtc *intel_crtc) +static void ilk_load_ycbcr_conversion_matrix(struct intel_crtc *crtc) { - int pipe = intel_crtc->pipe; - struct drm_i915_private *dev_priv = to_i915(intel_crtc->base.dev); + int pipe = crtc->pipe; + struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); I915_WRITE(PIPE_CSC_PREOFF_HI(pipe), 0); I915_WRITE(PIPE_CSC_PREOFF_ME(pipe), 0); @@ -132,14 +134,12 @@ static void ilk_load_ycbcr_conversion_matrix(struct intel_crtc *intel_crtc) I915_WRITE(PIPE_CSC_MODE(pipe), 0); } -static void ilk_load_csc_matrix(struct drm_crtc_state *crtc_state) +static void ilk_load_csc_matrix(struct intel_crtc_state *crtc_state) { - struct drm_crtc *crtc = crtc_state->crtc; - struct drm_i915_private *dev_priv = to_i915(crtc->dev); - struct intel_crtc *intel_crtc = to_intel_crtc(crtc); - int i, pipe = intel_crtc->pipe; + struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc); + struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); + int i, pipe = crtc->pipe; uint16_t coeffs[9] = { 0, }; - struct intel_crtc_state *intel_crtc_state = to_intel_crtc_state(crtc_state); bool limited_color_range = false; /* @@ -147,14 +147,14 @@ static void ilk_load_csc_matrix(struct drm_crtc_state *crtc_state) * do the range compression using the gamma LUT instead. */ if (INTEL_GEN(dev_priv) >= 8 || IS_HASWELL(dev_priv)) - limited_color_range = intel_crtc_state->limited_color_range; + limited_color_range = crtc_state->limited_color_range; - if (intel_crtc_state->output_format == INTEL_OUTPUT_FORMAT_YCBCR420 || - intel_crtc_state->output_format == INTEL_OUTPUT_FORMAT_YCBCR444) { - ilk_load_ycbcr_conversion_matrix(intel_crtc); + if (crtc_state->output_format == INTEL_OUTPUT_FORMAT_YCBCR420 || + crtc_state->output_format == INTEL_OUTPUT_FORMAT_YCBCR444) { + ilk_load_ycbcr_conversion_matrix(crtc); return; - } else if (crtc_state->ctm) { - struct drm_color_ctm *ctm = crtc_state->ctm->data; + } else if (crtc_state->base.ctm) { + struct drm_color_ctm *ctm = crtc_state->base.ctm->data; const u64 *input; u64 temp[9]; @@ -253,16 +253,15 @@ static void ilk_load_csc_matrix(struct drm_crtc_state *crtc_state) /* * Set up the pipe CSC unit on CherryView. */ -static void cherryview_load_csc_matrix(struct drm_crtc_state *state) +static void cherryview_load_csc_matrix(struct intel_crtc_state *crtc_state) { - struct drm_crtc *crtc = state->crtc; - struct drm_device *dev = crtc->dev; + struct drm_device *dev = crtc_state->base.crtc->dev; struct drm_i915_private *dev_priv = to_i915(dev); - int pipe = to_intel_crtc(crtc)->pipe; + int pipe = to_intel_crtc(crtc_state->base.crtc)->pipe; uint32_t mode; - if (state->ctm) { - struct drm_color_ctm *ctm = state->ctm->data; + if (crtc_state->base.ctm) { + struct drm_color_ctm *ctm = crtc_state->base.ctm->data; uint16_t coeffs[9] = { 0, }; int i; @@ -293,17 +292,17 @@ static void cherryview_load_csc_matrix(struct drm_crtc_state *state) I915_WRITE(CGM_PIPE_CSC_COEFF8(pipe), coeffs[8]); } - mode = (state->ctm ? CGM_PIPE_MODE_CSC : 0); - if (!crtc_state_is_legacy_gamma(state)) { - mode |= (state->degamma_lut ? CGM_PIPE_MODE_DEGAMMA : 0) | - (state->gamma_lut ? CGM_PIPE_MODE_GAMMA : 0); + mode = (crtc_state->base.ctm ? CGM_PIPE_MODE_CSC : 0); + if (!crtc_state_is_legacy_gamma(crtc_state)) { + mode |= (crtc_state->base.degamma_lut ? CGM_PIPE_MODE_DEGAMMA : 0) | + (crtc_state->base.gamma_lut ? CGM_PIPE_MODE_GAMMA : 0); } I915_WRITE(CGM_PIPE_MODE(pipe), mode); } -void intel_color_set_csc(struct drm_crtc_state *crtc_state) +void intel_color_set_csc(struct intel_crtc_state *crtc_state) { - struct drm_device *dev = crtc_state->crtc->dev; + struct drm_device *dev = crtc_state->base.crtc->dev; struct drm_i915_private *dev_priv = to_i915(dev); if (dev_priv->display.load_csc_matrix) @@ -311,14 +310,12 @@ void intel_color_set_csc(struct drm_crtc_state *crtc_state) } /* Loads the legacy palette/gamma unit for the CRTC. */ -static void i9xx_load_luts_internal(struct drm_crtc *crtc, - struct drm_property_blob *blob, - struct intel_crtc_state *crtc_state) +static void i9xx_load_luts_internal(struct intel_crtc_state *crtc_state, + struct drm_property_blob *blob) { - struct drm_device *dev = crtc->dev; - struct drm_i915_private *dev_priv = to_i915(dev); - struct intel_crtc *intel_crtc = to_intel_crtc(crtc); - enum pipe pipe = intel_crtc->pipe; + struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc); + struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); + enum pipe pipe = crtc->pipe; int i; if (HAS_GMCH_DISPLAY(dev_priv)) { @@ -353,53 +350,48 @@ static void i9xx_load_luts_internal(struct drm_crtc *crtc, } } -static void i9xx_load_luts(struct drm_crtc_state *crtc_state) +static void i9xx_load_luts(struct intel_crtc_state *crtc_state) { - i9xx_load_luts_internal(crtc_state->crtc, crtc_state->gamma_lut, - to_intel_crtc_state(crtc_state)); + i9xx_load_luts_internal(crtc_state, crtc_state->base.gamma_lut); } /* Loads the legacy palette/gamma unit for the CRTC on Haswell. */ -static void haswell_load_luts(struct drm_crtc_state *crtc_state) +static void haswell_load_luts(struct intel_crtc_state *crtc_state) { - struct drm_crtc *crtc = crtc_state->crtc; - struct drm_device *dev = crtc->dev; - struct drm_i915_private *dev_priv = to_i915(dev); - struct intel_crtc *intel_crtc = to_intel_crtc(crtc); - struct intel_crtc_state *intel_crtc_state = - to_intel_crtc_state(crtc_state); + struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc); + struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); bool reenable_ips = false; /* * Workaround : Do not read or write the pipe palette/gamma data while * GAMMA_MODE is configured for split gamma and IPS_CTL has IPS enabled. */ - if (IS_HASWELL(dev_priv) && intel_crtc_state->ips_enabled && - (intel_crtc_state->gamma_mode == GAMMA_MODE_MODE_SPLIT)) { - hsw_disable_ips(intel_crtc_state); + if (IS_HASWELL(dev_priv) && crtc_state->ips_enabled && + (crtc_state->gamma_mode == GAMMA_MODE_MODE_SPLIT)) { + hsw_disable_ips(crtc_state); reenable_ips = true; } - intel_crtc_state->gamma_mode = GAMMA_MODE_MODE_8BIT; - I915_WRITE(GAMMA_MODE(intel_crtc->pipe), GAMMA_MODE_MODE_8BIT); + crtc_state->gamma_mode = GAMMA_MODE_MODE_8BIT; + I915_WRITE(GAMMA_MODE(crtc->pipe), GAMMA_MODE_MODE_8BIT); i9xx_load_luts(crtc_state); if (reenable_ips) - hsw_enable_ips(intel_crtc_state); + hsw_enable_ips(crtc_state); } -static void bdw_load_degamma_lut(struct drm_crtc_state *state) +static void bdw_load_degamma_lut(struct intel_crtc_state *crtc_state) { - struct drm_i915_private *dev_priv = to_i915(state->crtc->dev); - enum pipe pipe = to_intel_crtc(state->crtc)->pipe; + struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev); + enum pipe pipe = to_intel_crtc(crtc_state->base.crtc)->pipe; uint32_t i, lut_size = INTEL_INFO(dev_priv)->color.degamma_lut_size; I915_WRITE(PREC_PAL_INDEX(pipe), PAL_PREC_SPLIT_MODE | PAL_PREC_AUTO_INCREMENT); - if (state->degamma_lut) { - struct drm_color_lut *lut = state->degamma_lut->data; + if (crtc_state->base.degamma_lut) { + struct drm_color_lut *lut = crtc_state->base.degamma_lut->data; for (i = 0; i < lut_size; i++) { uint32_t word = @@ -419,10 +411,10 @@ static void bdw_load_degamma_lut(struct drm_crtc_state *state) } } -static void bdw_load_gamma_lut(struct drm_crtc_state *state, u32 offset) +static void bdw_load_gamma_lut(struct intel_crtc_state *crtc_state, u32 offset) { - struct drm_i915_private *dev_priv = to_i915(state->crtc->dev); - enum pipe pipe = to_intel_crtc(state->crtc)->pipe; + struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev); + enum pipe pipe = to_intel_crtc(crtc_state->base.crtc)->pipe; uint32_t i, lut_size = INTEL_INFO(dev_priv)->color.gamma_lut_size; WARN_ON(offset & ~PAL_PREC_INDEX_VALUE_MASK); @@ -432,8 +424,8 @@ static void bdw_load_gamma_lut(struct drm_crtc_state *state, u32 offset) PAL_PREC_AUTO_INCREMENT | offset); - if (state->gamma_lut) { - struct drm_color_lut *lut = state->gamma_lut->data; + if (crtc_state->base.gamma_lut) { + struct drm_color_lut *lut = crtc_state->base.gamma_lut->data; for (i = 0; i < lut_size; i++) { uint32_t word = @@ -467,22 +459,21 @@ static void bdw_load_gamma_lut(struct drm_crtc_state *state, u32 offset) } /* Loads the palette/gamma unit for the CRTC on Broadwell+. */ -static void broadwell_load_luts(struct drm_crtc_state *state) +static void broadwell_load_luts(struct intel_crtc_state *crtc_state) { - struct drm_i915_private *dev_priv = to_i915(state->crtc->dev); - struct intel_crtc_state *intel_state = to_intel_crtc_state(state); - enum pipe pipe = to_intel_crtc(state->crtc)->pipe; + struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev); + enum pipe pipe = to_intel_crtc(crtc_state->base.crtc)->pipe; - if (crtc_state_is_legacy_gamma(state)) { - haswell_load_luts(state); + if (crtc_state_is_legacy_gamma(crtc_state)) { + haswell_load_luts(crtc_state); return; } - bdw_load_degamma_lut(state); - bdw_load_gamma_lut(state, + bdw_load_degamma_lut(crtc_state); + bdw_load_gamma_lut(crtc_state, INTEL_INFO(dev_priv)->color.degamma_lut_size); - intel_state->gamma_mode = GAMMA_MODE_MODE_SPLIT; + crtc_state->gamma_mode = GAMMA_MODE_MODE_SPLIT; I915_WRITE(GAMMA_MODE(pipe), GAMMA_MODE_MODE_SPLIT); POSTING_READ(GAMMA_MODE(pipe)); @@ -493,10 +484,10 @@ static void broadwell_load_luts(struct drm_crtc_state *state) I915_WRITE(PREC_PAL_INDEX(pipe), 0); } -static void glk_load_degamma_lut(struct drm_crtc_state *state) +static void glk_load_degamma_lut(struct intel_crtc_state *crtc_state) { - struct drm_i915_private *dev_priv = to_i915(state->crtc->dev); - enum pipe pipe = to_intel_crtc(state->crtc)->pipe; + struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev); + enum pipe pipe = to_intel_crtc(crtc_state->base.crtc)->pipe; const uint32_t lut_size = 33; uint32_t i; @@ -523,49 +514,46 @@ static void glk_load_degamma_lut(struct drm_crtc_state *state) I915_WRITE(PRE_CSC_GAMC_DATA(pipe), (1 << 16)); } -static void glk_load_luts(struct drm_crtc_state *state) +static void glk_load_luts(struct intel_crtc_state *crtc_state) { - struct drm_crtc *crtc = state->crtc; - struct drm_device *dev = crtc->dev; + struct drm_device *dev = crtc_state->base.crtc->dev; struct drm_i915_private *dev_priv = to_i915(dev); - struct intel_crtc_state *intel_state = to_intel_crtc_state(state); - enum pipe pipe = to_intel_crtc(crtc)->pipe; + enum pipe pipe = to_intel_crtc(crtc_state->base.crtc)->pipe; - glk_load_degamma_lut(state); + glk_load_degamma_lut(crtc_state); - if (crtc_state_is_legacy_gamma(state)) { - haswell_load_luts(state); + if (crtc_state_is_legacy_gamma(crtc_state)) { + haswell_load_luts(crtc_state); return; } - bdw_load_gamma_lut(state, 0); + bdw_load_gamma_lut(crtc_state, 0); - intel_state->gamma_mode = GAMMA_MODE_MODE_10BIT; + crtc_state->gamma_mode = GAMMA_MODE_MODE_10BIT; I915_WRITE(GAMMA_MODE(pipe), GAMMA_MODE_MODE_10BIT); POSTING_READ(GAMMA_MODE(pipe)); } /* Loads the palette/gamma unit for the CRTC on CherryView. */ -static void cherryview_load_luts(struct drm_crtc_state *state) +static void cherryview_load_luts(struct intel_crtc_state *crtc_state) { - struct drm_crtc *crtc = state->crtc; + struct drm_crtc *crtc = crtc_state->base.crtc; struct drm_i915_private *dev_priv = to_i915(crtc->dev); enum pipe pipe = to_intel_crtc(crtc)->pipe; struct drm_color_lut *lut; uint32_t i, lut_size; uint32_t word0, word1; - if (crtc_state_is_legacy_gamma(state)) { + if (crtc_state_is_legacy_gamma(crtc_state)) { /* Turn off degamma/gamma on CGM block. */ I915_WRITE(CGM_PIPE_MODE(pipe), - (state->ctm ? CGM_PIPE_MODE_CSC : 0)); - i9xx_load_luts_internal(crtc, state->gamma_lut, - to_intel_crtc_state(state)); + (crtc_state->base.ctm ? CGM_PIPE_MODE_CSC : 0)); + i9xx_load_luts_internal(crtc_state, crtc_state->base.gamma_lut); return; } - if (state->degamma_lut) { - lut = state->degamma_lut->data; + if (crtc_state->base.degamma_lut) { + lut = crtc_state->base.degamma_lut->data; lut_size = INTEL_INFO(dev_priv)->color.degamma_lut_size; for (i = 0; i < lut_size; i++) { /* Write LUT in U0.14 format. */ @@ -579,8 +567,8 @@ static void cherryview_load_luts(struct drm_crtc_state *state) } } - if (state->gamma_lut) { - lut = state->gamma_lut->data; + if (crtc_state->base.gamma_lut) { + lut = crtc_state->base.gamma_lut->data; lut_size = INTEL_INFO(dev_priv)->color.gamma_lut_size; for (i = 0; i < lut_size; i++) { /* Write LUT in U0.10 format. */ @@ -595,29 +583,28 @@ static void cherryview_load_luts(struct drm_crtc_state *state) } I915_WRITE(CGM_PIPE_MODE(pipe), - (state->ctm ? CGM_PIPE_MODE_CSC : 0) | - (state->degamma_lut ? CGM_PIPE_MODE_DEGAMMA : 0) | - (state->gamma_lut ? CGM_PIPE_MODE_GAMMA : 0)); + (crtc_state->base.ctm ? CGM_PIPE_MODE_CSC : 0) | + (crtc_state->base.degamma_lut ? CGM_PIPE_MODE_DEGAMMA : 0) | + (crtc_state->base.gamma_lut ? CGM_PIPE_MODE_GAMMA : 0)); /* * Also program a linear LUT in the legacy block (behind the * CGM block). */ - i9xx_load_luts_internal(crtc, NULL, to_intel_crtc_state(state)); + i9xx_load_luts_internal(crtc_state, NULL); } -void intel_color_load_luts(struct drm_crtc_state *crtc_state) +void intel_color_load_luts(struct intel_crtc_state *crtc_state) { - struct drm_device *dev = crtc_state->crtc->dev; + struct drm_device *dev = crtc_state->base.crtc->dev; struct drm_i915_private *dev_priv = to_i915(dev); dev_priv->display.load_luts(crtc_state); } -int intel_color_check(struct drm_crtc *crtc, - struct drm_crtc_state *crtc_state) +int intel_color_check(struct intel_crtc_state *crtc_state) { - struct drm_i915_private *dev_priv = to_i915(crtc->dev); + struct drm_i915_private *dev_priv = to_i915(crtc_state->base.crtc->dev); size_t gamma_length, degamma_length; degamma_length = INTEL_INFO(dev_priv)->color.degamma_lut_size; @@ -627,10 +614,10 @@ int intel_color_check(struct drm_crtc *crtc, * We allow both degamma & gamma luts at the right size or * NULL. */ - if ((!crtc_state->degamma_lut || - drm_color_lut_size(crtc_state->degamma_lut) == degamma_length) && - (!crtc_state->gamma_lut || - drm_color_lut_size(crtc_state->gamma_lut) == gamma_length)) + if ((!crtc_state->base.degamma_lut || + drm_color_lut_size(crtc_state->base.degamma_lut) == degamma_length) && + (!crtc_state->base.gamma_lut || + drm_color_lut_size(crtc_state->base.gamma_lut) == gamma_length)) return 0; /* @@ -643,11 +630,11 @@ int intel_color_check(struct drm_crtc *crtc, return -EINVAL; } -void intel_color_init(struct drm_crtc *crtc) +void intel_color_init(struct intel_crtc *crtc) { - struct drm_i915_private *dev_priv = to_i915(crtc->dev); + struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); - drm_mode_crtc_set_gamma_size(crtc, 256); + drm_mode_crtc_set_gamma_size(&crtc->base, 256); if (IS_CHERRYVIEW(dev_priv)) { dev_priv->display.load_csc_matrix = cherryview_load_csc_matrix; @@ -669,7 +656,7 @@ void intel_color_init(struct drm_crtc *crtc) /* Enable color management support when we have degamma & gamma LUTs. */ if (INTEL_INFO(dev_priv)->color.degamma_lut_size != 0 && INTEL_INFO(dev_priv)->color.gamma_lut_size != 0) - drm_crtc_enable_color_mgmt(crtc, + drm_crtc_enable_color_mgmt(&crtc->base, INTEL_INFO(dev_priv)->color.degamma_lut_size, true, INTEL_INFO(dev_priv)->color.gamma_lut_size); diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 943d6832b05d..13e5650b6f31 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -5641,7 +5641,7 @@ static void ironlake_crtc_enable(struct intel_crtc_state *pipe_config, * On ILK+ LUT must be loaded before the pipe is running but with * clocks enabled */ - intel_color_load_luts(&pipe_config->base); + intel_color_load_luts(pipe_config); if (dev_priv->display.initial_watermarks != NULL) dev_priv->display.initial_watermarks(old_intel_state, pipe_config); @@ -5752,7 +5752,7 @@ static void haswell_crtc_enable(struct intel_crtc_state *pipe_config, haswell_set_pipemisc(pipe_config); - intel_color_set_csc(&pipe_config->base); + intel_color_set_csc(pipe_config); intel_crtc->active = true; @@ -5771,7 +5771,7 @@ static void haswell_crtc_enable(struct intel_crtc_state *pipe_config, * On ILK+ LUT must be loaded before the pipe is running but with * clocks enabled */ - intel_color_load_luts(&pipe_config->base); + intel_color_load_luts(pipe_config); /* * Display WA #1153: enable hardware to bypass the alpha math @@ -6117,7 +6117,7 @@ static void valleyview_crtc_enable(struct intel_crtc_state *pipe_config, i9xx_set_pipeconf(pipe_config); - intel_color_set_csc(&pipe_config->base); + intel_color_set_csc(pipe_config); intel_crtc->active = true; @@ -6137,7 +6137,7 @@ static void valleyview_crtc_enable(struct intel_crtc_state *pipe_config, i9xx_pfit_enable(pipe_config); - intel_color_load_luts(&pipe_config->base); + intel_color_load_luts(pipe_config); dev_priv->display.initial_watermarks(old_intel_state, pipe_config); @@ -6193,7 +6193,7 @@ static void i9xx_crtc_enable(struct intel_crtc_state *pipe_config, i9xx_pfit_enable(pipe_config); - intel_color_load_luts(&pipe_config->base); + intel_color_load_luts(pipe_config); if (dev_priv->display.initial_watermarks != NULL) dev_priv->display.initial_watermarks(old_intel_state, @@ -10972,7 +10972,7 @@ static int intel_crtc_atomic_check(struct drm_crtc *crtc, } if (crtc_state->color_mgmt_changed) { - ret = intel_color_check(crtc, crtc_state); + ret = intel_color_check(pipe_config); if (ret) return ret; @@ -13547,8 +13547,8 @@ static void intel_begin_crtc_commit(struct drm_crtc *crtc, if (!modeset && (intel_cstate->base.color_mgmt_changed || intel_cstate->update_pipe)) { - intel_color_set_csc(&intel_cstate->base); - intel_color_load_luts(&intel_cstate->base); + intel_color_set_csc(intel_cstate); + intel_color_load_luts(intel_cstate); } /* Perform vblank evasion around commit operation */ @@ -14121,7 +14121,7 @@ static int intel_crtc_init(struct drm_i915_private *dev_priv, enum pipe pipe) drm_crtc_helper_add(&intel_crtc->base, &intel_helper_funcs); - intel_color_init(&intel_crtc->base); + intel_color_init(intel_crtc); WARN_ON(drm_crtc_index(&intel_crtc->base) != intel_crtc->pipe); diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index a8177ccf1d4f..d08f08f607dd 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -2327,10 +2327,10 @@ int intel_plane_atomic_check_with_state(const struct intel_crtc_state *old_crtc_ struct intel_plane_state *intel_state); /* intel_color.c */ -void intel_color_init(struct drm_crtc *crtc); -int intel_color_check(struct drm_crtc *crtc, struct drm_crtc_state *state); -void intel_color_set_csc(struct drm_crtc_state *crtc_state); -void intel_color_load_luts(struct drm_crtc_state *crtc_state); +void intel_color_init(struct intel_crtc *crtc); +int intel_color_check(struct intel_crtc_state *crtc_state); +void intel_color_set_csc(struct intel_crtc_state *crtc_state); +void intel_color_load_luts(struct intel_crtc_state *crtc_state); /* intel_lspcon.c */ bool lspcon_init(struct intel_digital_port *intel_dig_port); From ab2cb2cb1a775bffa678d4b5d9695f0622157626 Mon Sep 17 00:00:00 2001 From: Clint Taylor Date: Mon, 10 Dec 2018 14:52:54 -0800 Subject: [PATCH 034/118] drm/i915/hdmi: SCDC Scrambling enable without CTS mode MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Setting the SCDC scrambling CTS mode causes HDMI Link Layer protocol tests HF1-12 and HF1-13 to fail. V2: Removed "Source Shall" entries to a new patch V3: Rebase to drm-tip Cc: Ville Syrjälä Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=107895 Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=107896 Signed-off-by: Clint Taylor Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/1544482374-26507-1-git-send-email-clinton.a.taylor@intel.com --- drivers/gpu/drm/i915/intel_ddi.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index f3e1d6a0b7dd..92c0bf70fe09 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -1880,7 +1880,7 @@ void intel_ddi_enable_transcoder_func(const struct intel_crtc_state *crtc_state) temp |= TRANS_DDI_MODE_SELECT_DVI; if (crtc_state->hdmi_scrambling) - temp |= TRANS_DDI_HDMI_SCRAMBLING_MASK; + temp |= TRANS_DDI_HDMI_SCRAMBLING; if (crtc_state->hdmi_high_tmds_clock_ratio) temp |= TRANS_DDI_HIGH_TMDS_CHAR_RATE; } else if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_ANALOG)) { @@ -3793,8 +3793,7 @@ void intel_ddi_get_config(struct intel_encoder *encoder, if (intel_dig_port->infoframe_enabled(encoder, pipe_config)) pipe_config->has_infoframe = true; - if ((temp & TRANS_DDI_HDMI_SCRAMBLING_MASK) == - TRANS_DDI_HDMI_SCRAMBLING_MASK) + if (temp & TRANS_DDI_HDMI_SCRAMBLING) pipe_config->hdmi_scrambling = true; if (temp & TRANS_DDI_HIGH_TMDS_CHAR_RATE) pipe_config->hdmi_high_tmds_clock_ratio = true; From 9343bb247bf892f7d8731da107dc9d317834bbef Mon Sep 17 00:00:00 2001 From: Matt Roper Date: Tue, 11 Dec 2018 09:31:06 -0800 Subject: [PATCH 035/118] drm/i915: Don't use DDB allocation when choosing gen9 watermark method MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The bspec gives an if/else chain for choosing whether to use "method 1" or "method 2" for calculating the watermark "Selected Result Blocks" value for a plane. One of the branches of the if chain is: "Else If ('plane buffer allocation' is known and (plane buffer allocation / plane blocks per line) >=1)" Since our driver currently calculates DDB allocations first and the actual watermark values second, the plane buffer allocation is known at this point in our code and we include this test in our driver's logic. However we plan to soon move to a "watermarks first, ddb allocation second" sequence where we won't know the DDB allocation at this point. Let's drop this arm of the if/else statement (effectively considering the DDB allocation unknown) as an independent patch so that any regressions can be more accurately bisected to either the different watermark value (in this patch) or the new DDB allocation (in the next patch). Signed-off-by: Matt Roper Reviewed-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181211173107.11068-1-matthew.d.roper@intel.com --- drivers/gpu/drm/i915/intel_pm.c | 7 ------- 1 file changed, 7 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 2bba5315b764..bf970cf7b8a5 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -4761,13 +4761,6 @@ static int skl_compute_plane_wm(const struct intel_crtc_state *cstate, wp->dbuf_block_size < 1) && (wp->plane_bytes_per_line / wp->dbuf_block_size < 1)) { selected_result = method2; - } else if (ddb_allocation >= - fixed16_to_u32_round_up(wp->plane_blocks_per_line)) { - if (IS_GEN9(dev_priv) && - !IS_GEMINILAKE(dev_priv)) - selected_result = min_fixed16(method1, method2); - else - selected_result = method2; } else if (latency >= wp->linetime_us) { if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv)) From d8e874980241dd1cee68e85c39d8e5372bbad494 Mon Sep 17 00:00:00 2001 From: Matt Roper Date: Tue, 11 Dec 2018 09:31:07 -0800 Subject: [PATCH 036/118] drm/i915: Switch to level-based DDB allocation algorithm (v5) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The DDB allocation algorithm currently used by the driver grants each plane a very small minimum allocation of DDB blocks and then divies up all of the remaining blocks based on the percentage of the total data rate that the plane makes up. It turns out that this proportional allocation approach is overly-generous with the larger planes and can leave very small planes wthout a big enough allocation to even hit their level 0 watermark requirements (especially on APL, which has a smaller DDB in general than other gen9 platforms). Or there can be situations where the smallest planes hit a lower watermark level than they should have been able to hit with a more equitable division of DDB blocks, thus limiting the overall system sleep state that can be achieved. The bspec now describes an alternate algorithm that can be used to overcome these types of issues. With the new algorithm, we calculate all plane watermark values for all wm levels first, then go back and partition a pipe's DDB space second. The DDB allocation will calculate what the highest watermark level that can be achieved on *all* active planes, and then grant the blocks necessary to hit that level to each plane. Any remaining blocks are then divided up proportionally according to data rate, similar to the old algorithm. There was a previous attempt to implement this algorithm a couple years ago in bb9d85f6e9d ("drm/i915/skl: New ddb allocation algorithm"), but some regressions were reported, the patch was reverted, and nobody ever got around to figuring out exactly where the bug was in that version. Our watermark code has evolved significantly in the meantime, but we're still getting bug reports caused by the unfair proportional algorithm, so let's give this another shot. v2: - Make sure cursor allocation stays constant and fixed at the end of the pipe allocation. - Fix some watermark level iterators that weren't handling the max level. v3: - Ensure we don't leave any DDB blocks unused by using DIV_ROUND_UP+min to calculate the extra blocks for each plane. (Ville) - Replace a while() loop with a for() loop to be more consistent with surrounding code. (Ville) - Clean unattainable watermark levels with memset rather than directly clearing the member fields. Also do the same for the transition watermark values if they can't be achieved. (Ville) - Drop min_disp_buf_needed calculations in skl_compute_plane_wm() since the results are no longer needed or used. (Ville) - Drop skl_latency[0] != 0 sanity check; both watermark methods already account for an invalid 0 latency by returning FP_16_16_MAX. (Ville) v4: - Break DDB allocation loop when total_data_rate=0 rather than alloc_size=0. If total_data_rate has dropped to 0, all remaining planes are disabled, which isn't true for alloc_size (we might just have not had any remaining blocks to hand out). Plus total_data_rate=0 is the case we need to avoid to a prevent a div-by-0. (Ville) - s/DIV_ROUND_UP/DIV64_U64_ROUND_UP/ to prevent 32-bit breakage (Ville) v5: - Don't forget to move 'start' pointer forward for UV surface when setting plane DDB boundaries. (Ville) Cc: Ville Syrjälä Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=105458 Signed-off-by: Matt Roper Reviewed-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181211173107.11068-2-matthew.d.roper@intel.com --- drivers/gpu/drm/i915/intel_pm.c | 397 ++++++++++++-------------------- 1 file changed, 147 insertions(+), 250 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index bf970cf7b8a5..6d074f2e69d3 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -4301,102 +4301,6 @@ icl_get_total_relative_data_rate(struct intel_crtc_state *intel_cstate, return total_data_rate; } -static uint16_t -skl_ddb_min_alloc(const struct intel_plane_state *plane_state, const int plane) -{ - struct drm_framebuffer *fb = plane_state->base.fb; - uint32_t src_w, src_h; - uint32_t min_scanlines = 8; - uint8_t plane_bpp; - - if (WARN_ON(!fb)) - return 0; - - /* For packed formats, and uv-plane, return 0 */ - if (plane == 1 && fb->format->format != DRM_FORMAT_NV12) - return 0; - - /* 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_Y_TILED_CCS && - fb->modifier != I915_FORMAT_MOD_Yf_TILED_CCS) - return 8; - - /* - * Src coordinates are already rotated by 270 degrees for - * the 90/270 degree plane rotation cases (to match the - * GTT mapping), hence no need to account for rotation here. - */ - src_w = drm_rect_width(&plane_state->base.src) >> 16; - src_h = drm_rect_height(&plane_state->base.src) >> 16; - - /* Halve UV plane width and height for NV12 */ - if (plane == 1) { - src_w /= 2; - src_h /= 2; - } - - plane_bpp = fb->format->cpp[plane]; - - if (drm_rotation_90_or_270(plane_state->base.rotation)) { - switch (plane_bpp) { - case 1: - min_scanlines = 32; - break; - case 2: - min_scanlines = 16; - break; - case 4: - min_scanlines = 8; - break; - case 8: - min_scanlines = 4; - break; - default: - WARN(1, "Unsupported pixel depth %u for rotation", - plane_bpp); - min_scanlines = 32; - } - } - - return DIV_ROUND_UP((4 * src_w * plane_bpp), 512) * min_scanlines/4 + 3; -} - -static void -skl_ddb_calc_min(const struct intel_crtc_state *cstate, int num_active, - uint16_t *minimum, uint16_t *uv_minimum) -{ - const struct drm_plane_state *pstate; - struct drm_plane *plane; - - drm_atomic_crtc_state_for_each_plane_state(plane, pstate, &cstate->base) { - enum plane_id plane_id = to_intel_plane(plane)->id; - struct intel_plane_state *plane_state = to_intel_plane_state(pstate); - - if (plane_id == PLANE_CURSOR) - continue; - - /* slave plane must be invisible and calculated from master */ - if (!pstate->visible || WARN_ON(plane_state->slave)) - continue; - - if (!plane_state->linked_plane) { - minimum[plane_id] = skl_ddb_min_alloc(plane_state, 0); - uv_minimum[plane_id] = - skl_ddb_min_alloc(plane_state, 1); - } else { - enum plane_id y_plane_id = - plane_state->linked_plane->id; - - minimum[y_plane_id] = skl_ddb_min_alloc(plane_state, 0); - minimum[plane_id] = skl_ddb_min_alloc(plane_state, 1); - } - } - - minimum[PLANE_CURSOR] = skl_cursor_allocation(num_active); -} - static int skl_allocate_pipe_ddb(struct intel_crtc_state *cstate, struct skl_ddb_allocation *ddb /* out */) @@ -4406,15 +4310,17 @@ skl_allocate_pipe_ddb(struct intel_crtc_state *cstate, struct drm_i915_private *dev_priv = to_i915(crtc->dev); struct intel_crtc *intel_crtc = to_intel_crtc(crtc); struct skl_ddb_entry *alloc = &cstate->wm.skl.ddb; - uint16_t alloc_size, start; - uint16_t minimum[I915_MAX_PLANES] = {}; - uint16_t uv_minimum[I915_MAX_PLANES] = {}; + struct skl_plane_wm *wm; + uint16_t alloc_size, start = 0; + uint16_t total[I915_MAX_PLANES] = {}; + uint16_t uv_total[I915_MAX_PLANES] = {}; u64 total_data_rate; enum plane_id plane_id; int num_active; u64 plane_data_rate[I915_MAX_PLANES] = {}; u64 uv_plane_data_rate[I915_MAX_PLANES] = {}; - uint16_t total_min_blocks = 0; + uint16_t blocks = 0; + int level; /* Clear the partitioning for disabled planes. */ memset(cstate->wm.skl.plane_ddb_y, 0, sizeof(cstate->wm.skl.plane_ddb_y)); @@ -4444,81 +4350,134 @@ skl_allocate_pipe_ddb(struct intel_crtc_state *cstate, if (alloc_size == 0) return 0; - skl_ddb_calc_min(cstate, num_active, minimum, uv_minimum); - - /* - * 1. Allocate the mininum required blocks for each active plane - * and allocate the cursor, it doesn't require extra allocation - * proportional to the data rate. - */ - - for_each_plane_id_on_crtc(intel_crtc, plane_id) { - total_min_blocks += minimum[plane_id]; - total_min_blocks += uv_minimum[plane_id]; - } - - if (total_min_blocks > alloc_size) { - DRM_DEBUG_KMS("Requested display configuration exceeds system DDB limitations"); - DRM_DEBUG_KMS("minimum required %d/%d\n", total_min_blocks, - alloc_size); - return -EINVAL; - } - - alloc_size -= total_min_blocks; - cstate->wm.skl.plane_ddb_y[PLANE_CURSOR].start = alloc->end - minimum[PLANE_CURSOR]; + /* Allocate fixed number of blocks for cursor. */ + total[PLANE_CURSOR] = skl_cursor_allocation(num_active); + alloc_size -= total[PLANE_CURSOR]; + cstate->wm.skl.plane_ddb_y[PLANE_CURSOR].start = + alloc->end - total[PLANE_CURSOR]; cstate->wm.skl.plane_ddb_y[PLANE_CURSOR].end = alloc->end; - /* - * 2. Distribute the remaining space in proportion to the amount of - * data each plane needs to fetch from memory. - * - * FIXME: we may not allocate every single block here. - */ if (total_data_rate == 0) return 0; - start = alloc->start; + /* + * Find the highest watermark level for which we can satisfy the block + * requirement of active planes. + */ + for (level = ilk_wm_max_level(dev_priv); level >= 0; level--) { + for_each_plane_id_on_crtc(intel_crtc, plane_id) { + if (plane_id == PLANE_CURSOR) + continue; + + wm = &cstate->wm.skl.optimal.planes[plane_id]; + blocks += wm->wm[level].plane_res_b; + blocks += wm->uv_wm[level].plane_res_b; + } + + if (blocks < alloc_size) { + alloc_size -= blocks; + break; + } + } + + if (level < 0) { + DRM_DEBUG_KMS("Requested display configuration exceeds system DDB limitations"); + DRM_DEBUG_KMS("minimum required %d/%d\n", blocks, + alloc_size); + return -EINVAL; + } + + /* + * Grant each plane the blocks it requires at the highest achievable + * watermark level, plus an extra share of the leftover blocks + * proportional to its relative data rate. + */ for_each_plane_id_on_crtc(intel_crtc, plane_id) { - u64 data_rate, uv_data_rate; - uint16_t plane_blocks, uv_plane_blocks; + u64 rate; + u16 extra; if (plane_id == PLANE_CURSOR) continue; - data_rate = plane_data_rate[plane_id]; - /* - * allocation for (packed formats) or (uv-plane part of planar format): - * promote the expression to 64 bits to avoid overflowing, the - * result is < available as data_rate / total_data_rate < 1 + * We've accounted for all active planes; remaining planes are + * all disabled. */ - plane_blocks = minimum[plane_id]; - plane_blocks += div64_u64(alloc_size * data_rate, total_data_rate); + if (total_data_rate == 0) + break; - /* Leave disabled planes at (0,0) */ - if (data_rate) { - cstate->wm.skl.plane_ddb_y[plane_id].start = start; - cstate->wm.skl.plane_ddb_y[plane_id].end = start + plane_blocks; - } + wm = &cstate->wm.skl.optimal.planes[plane_id]; - start += plane_blocks; + rate = plane_data_rate[plane_id]; + extra = min_t(u16, alloc_size, + DIV64_U64_ROUND_UP(alloc_size * rate, + total_data_rate)); + total[plane_id] = wm->wm[level].plane_res_b + extra; + alloc_size -= extra; + total_data_rate -= rate; - /* Allocate DDB for UV plane for planar format/NV12 */ - uv_data_rate = uv_plane_data_rate[plane_id]; + if (total_data_rate == 0) + break; - uv_plane_blocks = uv_minimum[plane_id]; - uv_plane_blocks += div64_u64(alloc_size * uv_data_rate, total_data_rate); + rate = uv_plane_data_rate[plane_id]; + extra = min_t(u16, alloc_size, + DIV64_U64_ROUND_UP(alloc_size * rate, + total_data_rate)); + uv_total[plane_id] = wm->uv_wm[level].plane_res_b + extra; + alloc_size -= extra; + total_data_rate -= rate; + } + WARN_ON(alloc_size != 0 || total_data_rate != 0); + + /* Set the actual DDB start/end points for each plane */ + start = alloc->start; + for_each_plane_id_on_crtc(intel_crtc, plane_id) { + struct skl_ddb_entry *plane_alloc, *uv_plane_alloc; + + if (plane_id == PLANE_CURSOR) + continue; + + plane_alloc = &cstate->wm.skl.plane_ddb_y[plane_id]; + uv_plane_alloc = &cstate->wm.skl.plane_ddb_uv[plane_id]; /* Gen11+ uses a separate plane for UV watermarks */ - WARN_ON(INTEL_GEN(dev_priv) >= 11 && uv_plane_blocks); + WARN_ON(INTEL_GEN(dev_priv) >= 11 && uv_total[plane_id]); - if (uv_data_rate) { - cstate->wm.skl.plane_ddb_uv[plane_id].start = start; - cstate->wm.skl.plane_ddb_uv[plane_id].end = - start + uv_plane_blocks; + /* Leave disabled planes at (0,0) */ + if (total[plane_id]) { + plane_alloc->start = start; + start += total[plane_id]; + plane_alloc->end = start; } - start += uv_plane_blocks; + if (uv_total[plane_id]) { + uv_plane_alloc->start = start; + start += uv_total[plane_id]; + uv_plane_alloc->end = start; + } + } + + /* + * When we calculated watermark values we didn't know how high + * of a level we'd actually be able to hit, so we just marked + * all levels as "enabled." Go back now and disable the ones + * that aren't actually possible. + */ + for (level++; level <= ilk_wm_max_level(dev_priv); level++) { + for_each_plane_id_on_crtc(intel_crtc, plane_id) { + wm = &cstate->wm.skl.optimal.planes[plane_id]; + memset(&wm->wm[level], 0, sizeof(wm->wm[level])); + } + } + + /* + * Go back and disable the transition watermark if it turns out we + * don't have enough DDB blocks for it. + */ + for_each_plane_id_on_crtc(intel_crtc, plane_id) { + wm = &cstate->wm.skl.optimal.planes[plane_id]; + if (wm->trans_wm.plane_res_b > total[plane_id]) + memset(&wm->trans_wm, 0, sizeof(wm->trans_wm)); } return 0; @@ -4715,17 +4674,15 @@ skl_compute_plane_wm_params(const struct intel_crtc_state *cstate, return 0; } -static int skl_compute_plane_wm(const struct intel_crtc_state *cstate, - const struct intel_plane_state *intel_pstate, - uint16_t ddb_allocation, - int level, - const struct skl_wm_params *wp, - const struct skl_wm_level *result_prev, - struct skl_wm_level *result /* out */) +static void skl_compute_plane_wm(const struct intel_crtc_state *cstate, + const struct intel_plane_state *intel_pstate, + int level, + const struct skl_wm_params *wp, + const struct skl_wm_level *result_prev, + struct skl_wm_level *result /* out */) { struct drm_i915_private *dev_priv = to_i915(intel_pstate->base.plane->dev); - const struct drm_plane_state *pstate = &intel_pstate->base; uint32_t latency = dev_priv->wm.skl_latency[level]; uint_fixed_16_16_t method1, method2; uint_fixed_16_16_t selected_result; @@ -4733,10 +4690,6 @@ static int skl_compute_plane_wm(const struct intel_crtc_state *cstate, struct intel_atomic_state *state = to_intel_atomic_state(cstate->base.state); bool apply_memory_bw_wa = skl_needs_memory_bw_wa(state); - uint32_t min_disp_buf_needed; - - if (latency == 0) - return level == 0 ? -EINVAL : 0; /* Display WA #1141: kbl,cfl */ if ((IS_KABYLAKE(dev_priv) || IS_COFFEELAKE(dev_priv) || @@ -4800,61 +4753,24 @@ static int skl_compute_plane_wm(const struct intel_crtc_state *cstate, res_blocks = result_prev->plane_res_b; } - if (INTEL_GEN(dev_priv) >= 11) { - if (wp->y_tiled) { - uint32_t extra_lines; - uint_fixed_16_16_t fp_min_disp_buf_needed; - - if (res_lines % wp->y_min_scanlines == 0) - extra_lines = wp->y_min_scanlines; - else - extra_lines = wp->y_min_scanlines * 2 - - res_lines % wp->y_min_scanlines; - - fp_min_disp_buf_needed = mul_u32_fixed16(res_lines + - extra_lines, - wp->plane_blocks_per_line); - min_disp_buf_needed = fixed16_to_u32_round_up( - fp_min_disp_buf_needed); - } else { - min_disp_buf_needed = DIV_ROUND_UP(res_blocks * 11, 10); - } - } else { - min_disp_buf_needed = res_blocks; - } - - if ((level > 0 && res_lines > 31) || - res_blocks >= ddb_allocation || - min_disp_buf_needed >= ddb_allocation) { - /* - * If there are no valid level 0 watermarks, then we can't - * support this display configuration. - */ - if (level) { - return 0; - } else { - struct drm_plane *plane = pstate->plane; - - DRM_DEBUG_KMS("Requested display configuration exceeds system watermark limitations\n"); - DRM_DEBUG_KMS("[PLANE:%d:%s] blocks required = %u/%u, lines required = %u/31\n", - plane->base.id, plane->name, - res_blocks, ddb_allocation, res_lines); - return -EINVAL; - } - } - /* The number of lines are ignored for the level 0 watermark. */ + if (level > 0 && res_lines > 31) + return; + + /* + * If res_lines is valid, assume we can use this watermark level + * for now. We'll come back and disable it after we calculate the + * DDB allocation if it turns out we don't actually have enough + * blocks to satisfy it. + */ result->plane_res_b = res_blocks; result->plane_res_l = res_lines; result->plane_en = true; - - return 0; } -static int +static void skl_compute_wm_levels(const struct intel_crtc_state *cstate, const struct intel_plane_state *intel_pstate, - uint16_t ddb_blocks, const struct skl_wm_params *wm_params, struct skl_wm_level *levels) { @@ -4862,25 +4778,15 @@ skl_compute_wm_levels(const struct intel_crtc_state *cstate, to_i915(intel_pstate->base.plane->dev); int level, max_level = ilk_wm_max_level(dev_priv); struct skl_wm_level *result_prev = &levels[0]; - int ret; for (level = 0; level <= max_level; level++) { struct skl_wm_level *result = &levels[level]; - ret = skl_compute_plane_wm(cstate, - intel_pstate, - ddb_blocks, - level, - wm_params, - result_prev, - result); - if (ret) - return ret; + skl_compute_plane_wm(cstate, intel_pstate, level, wm_params, + result_prev, result); result_prev = result; } - - return 0; } static uint32_t @@ -4908,8 +4814,7 @@ skl_compute_linetime_wm(const struct intel_crtc_state *cstate) static void skl_compute_transition_wm(const struct intel_crtc_state *cstate, const struct skl_wm_params *wp, - struct skl_plane_wm *wm, - uint16_t ddb_allocation) + struct skl_plane_wm *wm) { struct drm_device *dev = cstate->base.crtc->dev; const struct drm_i915_private *dev_priv = to_i915(dev); @@ -4957,12 +4862,13 @@ static void skl_compute_transition_wm(const struct intel_crtc_state *cstate, } - res_blocks += 1; - - if (res_blocks < ddb_allocation) { - wm->trans_wm.plane_res_b = res_blocks; - wm->trans_wm.plane_en = true; - } + /* + * Just assume we can enable the transition watermark. After + * computing the DDB we'll come back and disable it if that + * assumption turns out to be false. + */ + wm->trans_wm.plane_res_b = res_blocks + 1; + wm->trans_wm.plane_en = true; } static int skl_build_plane_wm_single(struct intel_crtc_state *crtc_state, @@ -4970,7 +4876,6 @@ static int skl_build_plane_wm_single(struct intel_crtc_state *crtc_state, enum plane_id plane_id, int color_plane) { struct skl_plane_wm *wm = &crtc_state->wm.skl.optimal.planes[plane_id]; - u16 ddb_blocks = skl_ddb_entry_size(&crtc_state->wm.skl.plane_ddb_y[plane_id]); struct skl_wm_params wm_params; int ret; @@ -4979,12 +4884,8 @@ static int skl_build_plane_wm_single(struct intel_crtc_state *crtc_state, if (ret) return ret; - ret = skl_compute_wm_levels(crtc_state, plane_state, - ddb_blocks, &wm_params, wm->wm); - if (ret) - return ret; - - skl_compute_transition_wm(crtc_state, &wm_params, wm, ddb_blocks); + skl_compute_wm_levels(crtc_state, plane_state, &wm_params, wm->wm); + skl_compute_transition_wm(crtc_state, &wm_params, wm); return 0; } @@ -4994,7 +4895,6 @@ static int skl_build_plane_wm_uv(struct intel_crtc_state *crtc_state, enum plane_id plane_id) { struct skl_plane_wm *wm = &crtc_state->wm.skl.optimal.planes[plane_id]; - u16 ddb_blocks = skl_ddb_entry_size(&crtc_state->wm.skl.plane_ddb_uv[plane_id]); struct skl_wm_params wm_params; int ret; @@ -5006,10 +4906,7 @@ static int skl_build_plane_wm_uv(struct intel_crtc_state *crtc_state, if (ret) return ret; - ret = skl_compute_wm_levels(crtc_state, plane_state, - ddb_blocks, &wm_params, wm->uv_wm); - if (ret) - return ret; + skl_compute_wm_levels(crtc_state, plane_state, &wm_params, wm->uv_wm); return 0; } @@ -5521,13 +5418,9 @@ skl_compute_wm(struct intel_atomic_state *state) if (ret || !changed) return ret; - ret = skl_compute_ddb(state); - if (ret) - return ret; - /* * Calculate WM's for all pipes that are part of this transaction. - * Note that the DDB allocation above may have added more CRTC's that + * Note that skl_ddb_add_affected_pipes may have added more CRTC's that * weren't otherwise being modified (and set bits in dirty_pipes) if * pipe allocations had to change. */ @@ -5549,6 +5442,10 @@ skl_compute_wm(struct intel_atomic_state *state) results->dirty_pipes |= drm_crtc_mask(&crtc->base); } + ret = skl_compute_ddb(state); + if (ret) + return ret; + skl_print_wm_changes(state); return 0; From bea68f4a5ff286a0febcb673f4c774f717d723a1 Mon Sep 17 00:00:00 2001 From: Bob Paauwe Date: Tue, 11 Dec 2018 11:25:45 -0800 Subject: [PATCH 037/118] drm/i915: DFSM pipe disable is valid from gen9 onwards (v2) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's not just GEN9 platforms that allow for pipes to be disabled via the DFSM register, but all later platforms as well. v2: drop pointless parentheses (Ville) Signed-off-by: Bob Paauwe Acked-by: Ville Syrjälä Reviewed-by: Matt Roper Signed-off-by: Matt Roper Link: https://patchwork.freedesktop.org/patch/msgid/20181211192545.140081-1-bob.j.paauwe@intel.com --- drivers/gpu/drm/i915/intel_device_info.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_device_info.c b/drivers/gpu/drm/i915/intel_device_info.c index 1e56319334f3..bd5c4d62c635 100644 --- a/drivers/gpu/drm/i915/intel_device_info.c +++ b/drivers/gpu/drm/i915/intel_device_info.c @@ -811,7 +811,7 @@ void intel_device_info_runtime_init(struct intel_device_info *info) DRM_INFO("PipeC fused off\n"); info->num_pipes -= 1; } - } else if (HAS_DISPLAY(dev_priv) && IS_GEN9(dev_priv)) { + } else if (HAS_DISPLAY(dev_priv) && INTEL_GEN(dev_priv) >= 9) { u32 dfsm = I915_READ(SKL_DFSM); u8 disabled_mask = 0; bool invalid; From 25db2eaf1097ff6b9169d288e9532072069adb7c Mon Sep 17 00:00:00 2001 From: Matt Roper Date: Wed, 12 Dec 2018 11:17:20 -0800 Subject: [PATCH 038/118] drm/i915: Don't forget to reset blocks when testing lower wm levels MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit During DDB allocation, we try to distribute enough blocks for each plane to hit the highest watermark level; if that fails, we retry each lower level (which should require fewer blocks) until we find one that's possible (or until the whole commit is rejected as impossible). We need to reset our running block count when trying each lower level, otherwise all lower levels will fail as well. Cc: Ville Syrjälä Fixes: d8e8749802 ("drm/i915: Switch to level-based DDB allocation algorithm (v5)") Signed-off-by: Matt Roper Reviewed-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181212191720.3706-1-matthew.d.roper@intel.com --- drivers/gpu/drm/i915/intel_pm.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 6d074f2e69d3..a6c7c11d2c0e 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -4365,6 +4365,7 @@ skl_allocate_pipe_ddb(struct intel_crtc_state *cstate, * requirement of active planes. */ for (level = ilk_wm_max_level(dev_priv); level >= 0; level--) { + blocks = 0; for_each_plane_id_on_crtc(intel_crtc, plane_id) { if (plane_id == PLANE_CURSOR) continue; From 006900087727f675e9367eb3c3e054912ddbffdd Mon Sep 17 00:00:00 2001 From: Lucas De Marchi Date: Wed, 12 Dec 2018 10:10:42 -0800 Subject: [PATCH 039/118] drm/i915: Rename IS_GEN to IS_GEN_RANGE RANGE makes it longer, but clearer. We are also going to add a macro to check an individual gen, so add the _RANGE prefix here. Diff generated with: sed 's/IS_GEN(/IS_GEN_RANGE(/g' drivers/gpu/drm/i915/{*/,}*.{c,h} -i v2: use IS_GEN rather than GT_GEN Signed-off-by: Lucas De Marchi Reviewed-by: Tvrtko Ursulin Reviewed-by: Jani Nikula Signed-off-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181212181044.15886-1-lucas.demarchi@intel.com --- drivers/gpu/drm/i915/i915_drv.h | 2 +- drivers/gpu/drm/i915/i915_perf.c | 4 ++-- drivers/gpu/drm/i915/intel_bios.c | 2 +- drivers/gpu/drm/i915/intel_engine_cs.c | 2 +- drivers/gpu/drm/i915/intel_fbc.c | 2 +- drivers/gpu/drm/i915/intel_hangcheck.c | 2 +- drivers/gpu/drm/i915/intel_ringbuffer.c | 8 ++++---- drivers/gpu/drm/i915/intel_uncore.c | 12 ++++++------ 8 files changed, 17 insertions(+), 17 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index e70707e79386..031738d48aad 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -2211,7 +2211,7 @@ intel_info(const struct drm_i915_private *dev_priv) GENMASK((e) - 1, (s) - 1)) /* Returns true if Gen is in inclusive range [Start, End] */ -#define IS_GEN(dev_priv, s, e) \ +#define IS_GEN_RANGE(dev_priv, s, e) \ (!!((dev_priv)->info.gen_mask & INTEL_GEN_MASK((s), (e)))) /* diff --git a/drivers/gpu/drm/i915/i915_perf.c b/drivers/gpu/drm/i915/i915_perf.c index 4529edfdcfc8..ad0095be435d 100644 --- a/drivers/gpu/drm/i915/i915_perf.c +++ b/drivers/gpu/drm/i915/i915_perf.c @@ -1796,7 +1796,7 @@ static int gen8_enable_metric_set(struct i915_perf_stream *stream) * be read back from automatically triggered reports, as part of the * RPT_ID field. */ - if (IS_GEN(dev_priv, 9, 11)) { + if (IS_GEN_RANGE(dev_priv, 9, 11)) { I915_WRITE(GEN8_OA_DEBUG, _MASKED_BIT_ENABLE(GEN9_OA_DEBUG_DISABLE_CLK_RATIO_REPORTS | GEN9_OA_DEBUG_INCLUDE_CLK_RATIO)); @@ -3442,7 +3442,7 @@ void i915_perf_init(struct drm_i915_private *dev_priv) dev_priv->perf.oa.gen8_valid_ctx_bit = (1<<16); } - } else if (IS_GEN(dev_priv, 10, 11)) { + } else if (IS_GEN_RANGE(dev_priv, 10, 11)) { dev_priv->perf.oa.ops.is_valid_b_counter_reg = gen7_is_valid_b_counter_addr; dev_priv->perf.oa.ops.is_valid_mux_reg = diff --git a/drivers/gpu/drm/i915/intel_bios.c b/drivers/gpu/drm/i915/intel_bios.c index 6d3e0260d49c..7b7e7abfa259 100644 --- a/drivers/gpu/drm/i915/intel_bios.c +++ b/drivers/gpu/drm/i915/intel_bios.c @@ -453,7 +453,7 @@ parse_sdvo_device_mapping(struct drm_i915_private *dev_priv, u8 bdb_version) * Only parse SDVO mappings on gens that could have SDVO. This isn't * accurate and doesn't have to be, as long as it's not too strict. */ - if (!IS_GEN(dev_priv, 3, 7)) { + if (!IS_GEN_RANGE(dev_priv, 3, 7)) { DRM_DEBUG_KMS("Skipping SDVO device mapping\n"); return; } diff --git a/drivers/gpu/drm/i915/intel_engine_cs.c b/drivers/gpu/drm/i915/intel_engine_cs.c index af2873403009..fe5e87b6e1af 100644 --- a/drivers/gpu/drm/i915/intel_engine_cs.c +++ b/drivers/gpu/drm/i915/intel_engine_cs.c @@ -1248,7 +1248,7 @@ static void intel_engine_print_registers(const struct intel_engine_cs *engine, &engine->execlists; u64 addr; - if (engine->id == RCS && IS_GEN(dev_priv, 4, 7)) + if (engine->id == RCS && IS_GEN_RANGE(dev_priv, 4, 7)) drm_printf(m, "\tCCID: 0x%08x\n", I915_READ(CCID)); drm_printf(m, "\tRING_START: 0x%08x\n", I915_READ(RING_START(engine->mmio_base))); diff --git a/drivers/gpu/drm/i915/intel_fbc.c b/drivers/gpu/drm/i915/intel_fbc.c index 78dbacdeaece..b57e31fc0f1e 100644 --- a/drivers/gpu/drm/i915/intel_fbc.c +++ b/drivers/gpu/drm/i915/intel_fbc.c @@ -787,7 +787,7 @@ static bool intel_fbc_can_activate(struct intel_crtc *crtc) * having a Y offset that isn't divisible by 4 causes FIFO underrun * and screen flicker. */ - if (IS_GEN(dev_priv, 9, 10) && + if (IS_GEN_RANGE(dev_priv, 9, 10) && (fbc->state_cache.plane.adjusted_y & 3)) { fbc->no_fbc_reason = "plane Y offset is misaligned"; return false; diff --git a/drivers/gpu/drm/i915/intel_hangcheck.c b/drivers/gpu/drm/i915/intel_hangcheck.c index e26d05a46451..41921a843d42 100644 --- a/drivers/gpu/drm/i915/intel_hangcheck.c +++ b/drivers/gpu/drm/i915/intel_hangcheck.c @@ -252,7 +252,7 @@ engine_stuck(struct intel_engine_cs *engine, u64 acthd) return ENGINE_WAIT_KICK; } - if (IS_GEN(dev_priv, 6, 7) && tmp & RING_WAIT_SEMAPHORE) { + if (IS_GEN_RANGE(dev_priv, 6, 7) && tmp & RING_WAIT_SEMAPHORE) { switch (semaphore_passed(engine)) { default: return ENGINE_DEAD; diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c index 02f6a9b81083..720c11e0acd1 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.c +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c @@ -445,7 +445,7 @@ static void intel_ring_setup_status_page(struct intel_engine_cs *engine) POSTING_READ(mmio); /* Flush the TLB for this page */ - if (IS_GEN(dev_priv, 6, 7)) { + if (IS_GEN_RANGE(dev_priv, 6, 7)) { i915_reg_t reg = RING_INSTPM(engine->mmio_base); /* ring should be idle before issuing a sync flush*/ @@ -679,7 +679,7 @@ static int init_render_ring(struct intel_engine_cs *engine) return ret; /* WaTimedSingleVertexDispatch:cl,bw,ctg,elk,ilk,snb */ - if (IS_GEN(dev_priv, 4, 6)) + if (IS_GEN_RANGE(dev_priv, 4, 6)) I915_WRITE(MI_MODE, _MASKED_BIT_ENABLE(VS_TIMER_DISPATCH)); /* We need to disable the AsyncFlip performance optimisations in order @@ -688,7 +688,7 @@ static int init_render_ring(struct intel_engine_cs *engine) * * WaDisableAsyncFlipPerfMode:snb,ivb,hsw,vlv */ - if (IS_GEN(dev_priv, 6, 7)) + if (IS_GEN_RANGE(dev_priv, 6, 7)) I915_WRITE(MI_MODE, _MASKED_BIT_ENABLE(ASYNC_FLIP_PERF_DISABLE)); /* Required for the hardware to program scanline values for waiting */ @@ -713,7 +713,7 @@ static int init_render_ring(struct intel_engine_cs *engine) _MASKED_BIT_DISABLE(CM0_STC_EVICT_DISABLE_LRA_SNB)); } - if (IS_GEN(dev_priv, 6, 7)) + if (IS_GEN_RANGE(dev_priv, 6, 7)) I915_WRITE(INSTPM, _MASKED_BIT_ENABLE(INSTPM_FORCE_ORDERING)); if (INTEL_GEN(dev_priv) >= 6) diff --git a/drivers/gpu/drm/i915/intel_uncore.c b/drivers/gpu/drm/i915/intel_uncore.c index 9289515108c3..631b4165fe00 100644 --- a/drivers/gpu/drm/i915/intel_uncore.c +++ b/drivers/gpu/drm/i915/intel_uncore.c @@ -1567,13 +1567,13 @@ void intel_uncore_init(struct drm_i915_private *dev_priv) dev_priv->uncore.pmic_bus_access_nb.notifier_call = i915_pmic_bus_access_notifier; - if (IS_GEN(dev_priv, 2, 4) || intel_vgpu_active(dev_priv)) { + if (IS_GEN_RANGE(dev_priv, 2, 4) || intel_vgpu_active(dev_priv)) { ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, gen2); ASSIGN_READ_MMIO_VFUNCS(dev_priv, gen2); } else if (IS_GEN5(dev_priv)) { ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, gen5); ASSIGN_READ_MMIO_VFUNCS(dev_priv, gen5); - } else if (IS_GEN(dev_priv, 6, 7)) { + } else if (IS_GEN_RANGE(dev_priv, 6, 7)) { ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, gen6); if (IS_VALLEYVIEW(dev_priv)) { @@ -1592,7 +1592,7 @@ void intel_uncore_init(struct drm_i915_private *dev_priv) ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, gen8); ASSIGN_READ_MMIO_VFUNCS(dev_priv, gen6); } - } else if (IS_GEN(dev_priv, 9, 10)) { + } else if (IS_GEN_RANGE(dev_priv, 9, 10)) { ASSIGN_FW_DOMAINS_TABLE(__gen9_fw_ranges); ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, fwtable); ASSIGN_READ_MMIO_VFUNCS(dev_priv, fwtable); @@ -2321,7 +2321,7 @@ intel_uncore_forcewake_for_read(struct drm_i915_private *dev_priv, } else if (INTEL_GEN(dev_priv) >= 6) { fw_domains = __gen6_reg_read_fw_domains(offset); } else { - WARN_ON(!IS_GEN(dev_priv, 2, 5)); + WARN_ON(!IS_GEN_RANGE(dev_priv, 2, 5)); fw_domains = 0; } @@ -2343,10 +2343,10 @@ intel_uncore_forcewake_for_write(struct drm_i915_private *dev_priv, fw_domains = __fwtable_reg_write_fw_domains(offset); } else if (IS_GEN8(dev_priv)) { fw_domains = __gen8_reg_write_fw_domains(offset); - } else if (IS_GEN(dev_priv, 6, 7)) { + } else if (IS_GEN_RANGE(dev_priv, 6, 7)) { fw_domains = FORCEWAKE_RENDER; } else { - WARN_ON(!IS_GEN(dev_priv, 2, 5)); + WARN_ON(!IS_GEN_RANGE(dev_priv, 2, 5)); fw_domains = 0; } From cf819eff907ab49205ece97c96baeb909fd36f4d Mon Sep 17 00:00:00 2001 From: Lucas De Marchi Date: Wed, 12 Dec 2018 10:10:43 -0800 Subject: [PATCH 040/118] drm/i915: replace IS_GEN with IS_GEN(..., N) Define IS_GEN() similarly to our IS_GEN_RANGE(). but use gen instead of gen_mask to do the comparison. Now callers can pass then gen as a parameter, so we don't require one macro for each gen. The following spatch was used to convert the users of these macros: @@ expression e; @@ ( - IS_GEN2(e) + IS_GEN(e, 2) | - IS_GEN3(e) + IS_GEN(e, 3) | - IS_GEN4(e) + IS_GEN(e, 4) | - IS_GEN5(e) + IS_GEN(e, 5) | - IS_GEN6(e) + IS_GEN(e, 6) | - IS_GEN7(e) + IS_GEN(e, 7) | - IS_GEN8(e) + IS_GEN(e, 8) | - IS_GEN9(e) + IS_GEN(e, 9) | - IS_GEN10(e) + IS_GEN(e, 10) | - IS_GEN11(e) + IS_GEN(e, 11) ) v2: use IS_GEN rather than GT_GEN and compare to info.gen rather than using the bitmask Signed-off-by: Lucas De Marchi Reviewed-by: Jani Nikula Signed-off-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181212181044.15886-2-lucas.demarchi@intel.com --- drivers/gpu/drm/i915/gvt/vgpu.c | 4 +- drivers/gpu/drm/i915/i915_cmd_parser.c | 2 +- drivers/gpu/drm/i915/i915_debugfs.c | 16 ++--- drivers/gpu/drm/i915/i915_drv.c | 18 +++--- drivers/gpu/drm/i915/i915_drv.h | 29 +++------ drivers/gpu/drm/i915/i915_gem.c | 14 ++-- drivers/gpu/drm/i915/i915_gem_context.c | 2 +- drivers/gpu/drm/i915/i915_gem_execbuffer.c | 4 +- drivers/gpu/drm/i915/i915_gem_fence_reg.c | 10 +-- drivers/gpu/drm/i915/i915_gem_gtt.c | 6 +- drivers/gpu/drm/i915/i915_gem_stolen.c | 7 +- drivers/gpu/drm/i915/i915_gem_tiling.c | 4 +- drivers/gpu/drm/i915/i915_gpu_error.c | 18 +++--- drivers/gpu/drm/i915/i915_irq.c | 24 +++---- drivers/gpu/drm/i915/i915_perf.c | 4 +- drivers/gpu/drm/i915/i915_suspend.c | 12 ++-- drivers/gpu/drm/i915/intel_atomic.c | 2 +- drivers/gpu/drm/i915/intel_audio.c | 2 +- drivers/gpu/drm/i915/intel_cdclk.c | 10 +-- drivers/gpu/drm/i915/intel_crt.c | 6 +- drivers/gpu/drm/i915/intel_device_info.c | 14 ++-- drivers/gpu/drm/i915/intel_display.c | 74 +++++++++++----------- drivers/gpu/drm/i915/intel_dp.c | 24 +++---- drivers/gpu/drm/i915/intel_engine_cs.c | 4 +- drivers/gpu/drm/i915/intel_fbc.c | 22 +++---- drivers/gpu/drm/i915/intel_fifo_underrun.c | 6 +- drivers/gpu/drm/i915/intel_guc_fw.c | 2 +- drivers/gpu/drm/i915/intel_hangcheck.c | 2 +- drivers/gpu/drm/i915/intel_lrc.c | 4 +- drivers/gpu/drm/i915/intel_lvds.c | 4 +- drivers/gpu/drm/i915/intel_mocs.c | 2 +- drivers/gpu/drm/i915/intel_overlay.c | 10 +-- drivers/gpu/drm/i915/intel_panel.c | 8 +-- drivers/gpu/drm/i915/intel_pipe_crc.c | 8 +-- drivers/gpu/drm/i915/intel_pm.c | 58 ++++++++--------- drivers/gpu/drm/i915/intel_psr.c | 4 +- drivers/gpu/drm/i915/intel_ringbuffer.c | 28 ++++---- drivers/gpu/drm/i915/intel_ringbuffer.h | 4 +- drivers/gpu/drm/i915/intel_runtime_pm.c | 4 +- drivers/gpu/drm/i915/intel_sprite.c | 6 +- drivers/gpu/drm/i915/intel_uc.c | 2 +- drivers/gpu/drm/i915/intel_uncore.c | 18 +++--- drivers/gpu/drm/i915/intel_wopcm.c | 4 +- drivers/gpu/drm/i915/intel_workarounds.c | 4 +- 44 files changed, 249 insertions(+), 261 deletions(-) diff --git a/drivers/gpu/drm/i915/gvt/vgpu.c b/drivers/gpu/drm/i915/gvt/vgpu.c index c628be05fbfe..e1c860f80eb0 100644 --- a/drivers/gpu/drm/i915/gvt/vgpu.c +++ b/drivers/gpu/drm/i915/gvt/vgpu.c @@ -148,10 +148,10 @@ int intel_gvt_init_vgpu_types(struct intel_gvt *gvt) gvt->types[i].avail_instance = min(low_avail / vgpu_types[i].low_mm, high_avail / vgpu_types[i].high_mm); - if (IS_GEN8(gvt->dev_priv)) + if (IS_GEN(gvt->dev_priv, 8)) sprintf(gvt->types[i].name, "GVTg_V4_%s", vgpu_types[i].name); - else if (IS_GEN9(gvt->dev_priv)) + else if (IS_GEN(gvt->dev_priv, 9)) sprintf(gvt->types[i].name, "GVTg_V5_%s", vgpu_types[i].name); diff --git a/drivers/gpu/drm/i915/i915_cmd_parser.c b/drivers/gpu/drm/i915/i915_cmd_parser.c index 95478db9998b..33e8eed64423 100644 --- a/drivers/gpu/drm/i915/i915_cmd_parser.c +++ b/drivers/gpu/drm/i915/i915_cmd_parser.c @@ -865,7 +865,7 @@ void intel_engine_init_cmd_parser(struct intel_engine_cs *engine) int cmd_table_count; int ret; - if (!IS_GEN7(engine->i915)) + if (!IS_GEN(engine->i915, 7)) return; switch (engine->id) { diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 40a61ef9aac1..2b52c91113b3 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -1070,7 +1070,7 @@ static int i915_frequency_info(struct seq_file *m, void *unused) intel_runtime_pm_get(dev_priv); - if (IS_GEN5(dev_priv)) { + if (IS_GEN(dev_priv, 5)) { u16 rgvswctl = I915_READ16(MEMSWCTL); u16 rgvstat = I915_READ16(MEMSTAT_ILK); @@ -1791,7 +1791,7 @@ static int i915_emon_status(struct seq_file *m, void *unused) unsigned long temp, chipset, gfx; int ret; - if (!IS_GEN5(dev_priv)) + if (!IS_GEN(dev_priv, 5)) return -ENODEV; intel_runtime_pm_get(dev_priv); @@ -2040,7 +2040,7 @@ static int i915_swizzle_info(struct seq_file *m, void *data) seq_printf(m, "bit6 swizzle for Y-tiling = %s\n", swizzle_string(dev_priv->mm.bit_6_swizzle_y)); - if (IS_GEN3(dev_priv) || IS_GEN4(dev_priv)) { + if (IS_GEN(dev_priv, 3) || IS_GEN(dev_priv, 4)) { seq_printf(m, "DDC = 0x%08x\n", I915_READ(DCC)); seq_printf(m, "DDC2 = 0x%08x\n", @@ -2125,12 +2125,12 @@ static void gen6_ppgtt_info(struct seq_file *m, struct intel_engine_cs *engine; enum intel_engine_id id; - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) seq_printf(m, "GFX_MODE: 0x%08x\n", I915_READ(GFX_MODE)); for_each_engine(engine, dev_priv, id) { seq_printf(m, "%s\n", engine->name); - if (IS_GEN7(dev_priv)) + if (IS_GEN(dev_priv, 7)) seq_printf(m, "GFX_MODE: 0x%08x\n", I915_READ(RING_MODE_GEN7(engine))); seq_printf(m, "PP_DIR_BASE: 0x%08x\n", @@ -4274,7 +4274,7 @@ i915_cache_sharing_get(void *data, u64 *val) struct drm_i915_private *dev_priv = data; u32 snpcr; - if (!(IS_GEN6(dev_priv) || IS_GEN7(dev_priv))) + if (!(IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7))) return -ENODEV; intel_runtime_pm_get(dev_priv); @@ -4294,7 +4294,7 @@ i915_cache_sharing_set(void *data, u64 val) struct drm_i915_private *dev_priv = data; u32 snpcr; - if (!(IS_GEN6(dev_priv) || IS_GEN7(dev_priv))) + if (!(IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7))) return -ENODEV; if (val > 3) @@ -4551,7 +4551,7 @@ static int i915_sseu_status(struct seq_file *m, void *unused) cherryview_sseu_device_status(dev_priv, &sseu); } else if (IS_BROADWELL(dev_priv)) { broadwell_sseu_device_status(dev_priv, &sseu); - } else if (IS_GEN9(dev_priv)) { + } else if (IS_GEN(dev_priv, 9)) { gen9_sseu_device_status(dev_priv, &sseu); } else if (INTEL_GEN(dev_priv) >= 10) { gen10_sseu_device_status(dev_priv, &sseu); diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index b310a897a4ad..77c0f97fe77c 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -132,15 +132,15 @@ intel_pch_type(const struct drm_i915_private *dev_priv, unsigned short id) switch (id) { case INTEL_PCH_IBX_DEVICE_ID_TYPE: DRM_DEBUG_KMS("Found Ibex Peak PCH\n"); - WARN_ON(!IS_GEN5(dev_priv)); + WARN_ON(!IS_GEN(dev_priv, 5)); return PCH_IBX; case INTEL_PCH_CPT_DEVICE_ID_TYPE: DRM_DEBUG_KMS("Found CougarPoint PCH\n"); - WARN_ON(!IS_GEN6(dev_priv) && !IS_IVYBRIDGE(dev_priv)); + WARN_ON(!IS_GEN(dev_priv, 6) && !IS_IVYBRIDGE(dev_priv)); return PCH_CPT; case INTEL_PCH_PPT_DEVICE_ID_TYPE: DRM_DEBUG_KMS("Found PantherPoint PCH\n"); - WARN_ON(!IS_GEN6(dev_priv) && !IS_IVYBRIDGE(dev_priv)); + WARN_ON(!IS_GEN(dev_priv, 6) && !IS_IVYBRIDGE(dev_priv)); /* PantherPoint is CPT compatible */ return PCH_CPT; case INTEL_PCH_LPT_DEVICE_ID_TYPE: @@ -217,9 +217,9 @@ intel_virt_detect_pch(const struct drm_i915_private *dev_priv) * make an educated guess as to which PCH is really there. */ - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) id = INTEL_PCH_IBX_DEVICE_ID_TYPE; - else if (IS_GEN6(dev_priv) || IS_IVYBRIDGE(dev_priv)) + else if (IS_GEN(dev_priv, 6) || IS_IVYBRIDGE(dev_priv)) id = INTEL_PCH_CPT_DEVICE_ID_TYPE; else if (IS_HSW_ULT(dev_priv) || IS_BDW_ULT(dev_priv)) id = INTEL_PCH_LPT_LP_DEVICE_ID_TYPE; @@ -966,7 +966,7 @@ static int i915_mmio_setup(struct drm_i915_private *dev_priv) int mmio_bar; int mmio_size; - mmio_bar = IS_GEN2(dev_priv) ? 1 : 0; + mmio_bar = IS_GEN(dev_priv, 2) ? 1 : 0; /* * Before gen4, the registers and the GTT are behind different BARs. * However, from gen4 onwards, the registers and the GTT are shared @@ -1341,7 +1341,7 @@ intel_get_dram_info(struct drm_i915_private *dev_priv) /* Need to calculate bandwidth only for Gen9 */ if (IS_BROXTON(dev_priv)) ret = bxt_get_dram_info(dev_priv); - else if (IS_GEN9(dev_priv)) + else if (IS_GEN(dev_priv, 9)) ret = skl_get_dram_info(dev_priv); else ret = skl_dram_get_channels_info(dev_priv); @@ -1436,7 +1436,7 @@ static int i915_driver_init_hw(struct drm_i915_private *dev_priv) pci_set_master(pdev); /* overlay on gen2 is broken and can't address above 1G */ - if (IS_GEN2(dev_priv)) { + if (IS_GEN(dev_priv, 2)) { ret = dma_set_coherent_mask(&pdev->dev, DMA_BIT_MASK(30)); if (ret) { DRM_ERROR("failed to set DMA mask\n"); @@ -1574,7 +1574,7 @@ static void i915_driver_register(struct drm_i915_private *dev_priv) acpi_video_register(); } - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) intel_gpu_ips_init(dev_priv); intel_audio_init(dev_priv); diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 031738d48aad..c34198f51b13 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -2214,6 +2214,10 @@ intel_info(const struct drm_i915_private *dev_priv) #define IS_GEN_RANGE(dev_priv, s, e) \ (!!((dev_priv)->info.gen_mask & INTEL_GEN_MASK((s), (e)))) +#define IS_GEN(dev_priv, n) \ + (BUILD_BUG_ON_ZERO(!__builtin_constant_p(n)) + \ + (dev_priv)->info.gen == (n)) + /* * Return true if revision is in range [since,until] inclusive. * @@ -2365,26 +2369,9 @@ intel_info(const struct drm_i915_private *dev_priv) #define IS_ICL_REVID(p, since, until) \ (IS_ICELAKE(p) && IS_REVID(p, since, until)) -/* - * The genX designation typically refers to the render engine, so render - * capability related checks should use IS_GEN, while display and other checks - * have their own (e.g. HAS_PCH_SPLIT for ILK+ display, IS_foo for particular - * chips, etc.). - */ -#define IS_GEN2(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(1))) -#define IS_GEN3(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(2))) -#define IS_GEN4(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(3))) -#define IS_GEN5(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(4))) -#define IS_GEN6(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(5))) -#define IS_GEN7(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(6))) -#define IS_GEN8(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(7))) -#define IS_GEN9(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(8))) -#define IS_GEN10(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(9))) -#define IS_GEN11(dev_priv) (!!((dev_priv)->info.gen_mask & BIT(10))) - #define IS_LP(dev_priv) (INTEL_INFO(dev_priv)->is_lp) -#define IS_GEN9_LP(dev_priv) (IS_GEN9(dev_priv) && IS_LP(dev_priv)) -#define IS_GEN9_BC(dev_priv) (IS_GEN9(dev_priv) && !IS_LP(dev_priv)) +#define IS_GEN9_LP(dev_priv) (IS_GEN(dev_priv, 9) && IS_LP(dev_priv)) +#define IS_GEN9_BC(dev_priv) (IS_GEN(dev_priv, 9) && !IS_LP(dev_priv)) #define ENGINE_MASK(id) BIT(id) #define RENDER_RING ENGINE_MASK(RCS) @@ -2405,7 +2392,7 @@ intel_info(const struct drm_i915_private *dev_priv) #define HAS_BLT(dev_priv) HAS_ENGINE(dev_priv, BCS) #define HAS_VEBOX(dev_priv) HAS_ENGINE(dev_priv, VECS) -#define HAS_LEGACY_SEMAPHORES(dev_priv) IS_GEN7(dev_priv) +#define HAS_LEGACY_SEMAPHORES(dev_priv) IS_GEN(dev_priv, 7) #define HAS_LLC(dev_priv) ((dev_priv)->info.has_llc) #define HAS_SNOOP(dev_priv) ((dev_priv)->info.has_snoop) @@ -2457,7 +2444,7 @@ intel_info(const struct drm_i915_private *dev_priv) /* With the 945 and later, Y tiling got adjusted so that it was 32 128-byte * rows, which changed the alignment requirements and fence programming. */ -#define HAS_128_BYTE_Y_TILING(dev_priv) (!IS_GEN2(dev_priv) && \ +#define HAS_128_BYTE_Y_TILING(dev_priv) (!IS_GEN(dev_priv, 2) && \ !(IS_I915G(dev_priv) || \ IS_I915GM(dev_priv))) #define SUPPORTS_TV(dev_priv) ((dev_priv)->info.display.supports_tv) diff --git a/drivers/gpu/drm/i915/i915_gem.c b/drivers/gpu/drm/i915/i915_gem.c index d36a9755ad91..39ee67e01bb7 100644 --- a/drivers/gpu/drm/i915/i915_gem.c +++ b/drivers/gpu/drm/i915/i915_gem.c @@ -5226,15 +5226,15 @@ void i915_gem_init_swizzling(struct drm_i915_private *dev_priv) I915_WRITE(DISP_ARB_CTL, I915_READ(DISP_ARB_CTL) | DISP_TILE_SURFACE_SWIZZLING); - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) return; I915_WRITE(TILECTL, I915_READ(TILECTL) | TILECTL_SWZCTL); - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) I915_WRITE(ARB_MODE, _MASKED_BIT_ENABLE(ARB_MODE_SWIZZLE_SNB)); - else if (IS_GEN7(dev_priv)) + else if (IS_GEN(dev_priv, 7)) I915_WRITE(ARB_MODE, _MASKED_BIT_ENABLE(ARB_MODE_SWIZZLE_IVB)); - else if (IS_GEN8(dev_priv)) + else if (IS_GEN(dev_priv, 8)) I915_WRITE(GAMTARBMODE, _MASKED_BIT_ENABLE(ARB_MODE_SWIZZLE_BDW)); else BUG(); @@ -5256,10 +5256,10 @@ static void init_unused_rings(struct drm_i915_private *dev_priv) init_unused_ring(dev_priv, SRB1_BASE); init_unused_ring(dev_priv, SRB2_BASE); init_unused_ring(dev_priv, SRB3_BASE); - } else if (IS_GEN2(dev_priv)) { + } else if (IS_GEN(dev_priv, 2)) { init_unused_ring(dev_priv, SRB0_BASE); init_unused_ring(dev_priv, SRB1_BASE); - } else if (IS_GEN3(dev_priv)) { + } else if (IS_GEN(dev_priv, 3)) { init_unused_ring(dev_priv, PRB1_BASE); init_unused_ring(dev_priv, PRB2_BASE); } @@ -5583,7 +5583,7 @@ int i915_gem_init(struct drm_i915_private *dev_priv) } ret = i915_gem_init_scratch(dev_priv, - IS_GEN2(dev_priv) ? SZ_256K : PAGE_SIZE); + IS_GEN(dev_priv, 2) ? SZ_256K : PAGE_SIZE); if (ret) { GEM_BUG_ON(ret == -EIO); goto err_ggtt; diff --git a/drivers/gpu/drm/i915/i915_gem_context.c b/drivers/gpu/drm/i915/i915_gem_context.c index 371c07087095..014152e2bc68 100644 --- a/drivers/gpu/drm/i915/i915_gem_context.c +++ b/drivers/gpu/drm/i915/i915_gem_context.c @@ -311,7 +311,7 @@ static u32 default_desc_template(const struct drm_i915_private *i915, address_mode = INTEL_LEGACY_64B_CONTEXT; desc |= address_mode << GEN8_CTX_ADDRESSING_MODE_SHIFT; - if (IS_GEN8(i915)) + if (IS_GEN(i915, 8)) desc |= GEN8_CTX_L3LLC_COHERENT; /* TODO: WaDisableLiteRestore when we start using semaphore diff --git a/drivers/gpu/drm/i915/i915_gem_execbuffer.c b/drivers/gpu/drm/i915/i915_gem_execbuffer.c index 1a1c04db6c80..844bd5ad87bc 100644 --- a/drivers/gpu/drm/i915/i915_gem_execbuffer.c +++ b/drivers/gpu/drm/i915/i915_gem_execbuffer.c @@ -1380,7 +1380,7 @@ eb_relocate_entry(struct i915_execbuffer *eb, * batchbuffers. */ if (reloc->write_domain == I915_GEM_DOMAIN_INSTRUCTION && - IS_GEN6(eb->i915)) { + IS_GEN(eb->i915, 6)) { err = i915_vma_bind(target, target->obj->cache_level, PIN_GLOBAL); if (WARN_ONCE(err, @@ -1893,7 +1893,7 @@ static int i915_reset_gen7_sol_offsets(struct i915_request *rq) u32 *cs; int i; - if (!IS_GEN7(rq->i915) || rq->engine->id != RCS) { + if (!IS_GEN(rq->i915, 7) || rq->engine->id != RCS) { DRM_DEBUG("sol reset is gen7/rcs only\n"); return -EINVAL; } diff --git a/drivers/gpu/drm/i915/i915_gem_fence_reg.c b/drivers/gpu/drm/i915/i915_gem_fence_reg.c index d548ac05ccd7..24df2e2a8fc1 100644 --- a/drivers/gpu/drm/i915/i915_gem_fence_reg.c +++ b/drivers/gpu/drm/i915/i915_gem_fence_reg.c @@ -193,9 +193,9 @@ static void fence_write(struct drm_i915_fence_reg *fence, * and explicitly managed for internal users. */ - if (IS_GEN2(fence->i915)) + if (IS_GEN(fence->i915, 2)) i830_write_fence_reg(fence, vma); - else if (IS_GEN3(fence->i915)) + else if (IS_GEN(fence->i915, 3)) i915_write_fence_reg(fence, vma); else i965_write_fence_reg(fence, vma); @@ -596,13 +596,13 @@ i915_gem_detect_bit_6_swizzle(struct drm_i915_private *dev_priv) swizzle_y = I915_BIT_6_SWIZZLE_NONE; } } - } else if (IS_GEN5(dev_priv)) { + } else if (IS_GEN(dev_priv, 5)) { /* On Ironlake whatever DRAM config, GPU always do * same swizzling setup. */ swizzle_x = I915_BIT_6_SWIZZLE_9_10; swizzle_y = I915_BIT_6_SWIZZLE_9; - } else if (IS_GEN2(dev_priv)) { + } else if (IS_GEN(dev_priv, 2)) { /* As far as we know, the 865 doesn't have these bit 6 * swizzling issues. */ @@ -647,7 +647,7 @@ i915_gem_detect_bit_6_swizzle(struct drm_i915_private *dev_priv) } /* check for L-shaped memory aka modified enhanced addressing */ - if (IS_GEN4(dev_priv) && + if (IS_GEN(dev_priv, 4) && !(I915_READ(DCC2) & DCC2_MODIFIED_ENHANCED_DISABLE)) { swizzle_x = I915_BIT_6_SWIZZLE_UNKNOWN; swizzle_y = I915_BIT_6_SWIZZLE_UNKNOWN; diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index 62bde517d383..6e31745f6156 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -2193,9 +2193,9 @@ int i915_ppgtt_init_hw(struct drm_i915_private *dev_priv) { gtt_write_workarounds(dev_priv); - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) gen6_ppgtt_enable(dev_priv); - else if (IS_GEN7(dev_priv)) + else if (IS_GEN(dev_priv, 7)) gen7_ppgtt_enable(dev_priv); return 0; @@ -2277,7 +2277,7 @@ static bool needs_idle_maps(struct drm_i915_private *dev_priv) /* Query intel_iommu to see if we need the workaround. Presumably that * was loaded first. */ - return IS_GEN5(dev_priv) && IS_MOBILE(dev_priv) && intel_vtd_active(); + return IS_GEN(dev_priv, 5) && IS_MOBILE(dev_priv) && intel_vtd_active(); } static void gen6_check_faults(struct drm_i915_private *dev_priv) diff --git a/drivers/gpu/drm/i915/i915_gem_stolen.c b/drivers/gpu/drm/i915/i915_gem_stolen.c index f29a7ff7c362..2f756a97689a 100644 --- a/drivers/gpu/drm/i915/i915_gem_stolen.c +++ b/drivers/gpu/drm/i915/i915_gem_stolen.c @@ -102,7 +102,7 @@ static int i915_adjust_stolen(struct drm_i915_private *dev_priv, resource_size_t ggtt_start; ggtt_start = I915_READ(PGTBL_CTL); - if (IS_GEN4(dev_priv)) + if (IS_GEN(dev_priv, 4)) ggtt_start = (ggtt_start & PGTBL_ADDRESS_LO_MASK) | (ggtt_start & PGTBL_ADDRESS_HI_MASK) << 28; else @@ -156,7 +156,7 @@ static int i915_adjust_stolen(struct drm_i915_private *dev_priv, * GEN3 firmware likes to smash pci bridges into the stolen * range. Apparently this works. */ - if (r == NULL && !IS_GEN3(dev_priv)) { + if (r == NULL && !IS_GEN(dev_priv, 3)) { DRM_ERROR("conflict detected with stolen region: %pR\n", dsm); @@ -194,7 +194,8 @@ static void g4x_get_stolen_reserved(struct drm_i915_private *dev_priv, * Whether ILK really reuses the ELK register for this is unclear. * Let's see if we catch anyone with this supposedly enabled on ILK. */ - WARN(IS_GEN5(dev_priv), "ILK stolen reserved found? 0x%08x\n", reg_val); + WARN(IS_GEN(dev_priv, 5), "ILK stolen reserved found? 0x%08x\n", + reg_val); if (!(reg_val & G4X_STOLEN_RESERVED_ADDR2_MASK)) return; diff --git a/drivers/gpu/drm/i915/i915_gem_tiling.c b/drivers/gpu/drm/i915/i915_gem_tiling.c index d9dc9df523b5..39319ff1679c 100644 --- a/drivers/gpu/drm/i915/i915_gem_tiling.c +++ b/drivers/gpu/drm/i915/i915_gem_tiling.c @@ -87,7 +87,7 @@ u32 i915_gem_fence_size(struct drm_i915_private *i915, } /* Previous chips need a power-of-two fence region when tiling */ - if (IS_GEN3(i915)) + if (IS_GEN(i915, 3)) ggtt_size = 1024*1024; else ggtt_size = 512*1024; @@ -162,7 +162,7 @@ i915_tiling_ok(struct drm_i915_gem_object *obj, return false; } - if (IS_GEN2(i915) || + if (IS_GEN(i915, 2) || (tiling == I915_TILING_Y && HAS_128_BYTE_Y_TILING(i915))) tile_width = 128; else diff --git a/drivers/gpu/drm/i915/i915_gpu_error.c b/drivers/gpu/drm/i915/i915_gpu_error.c index 3f9ce403c755..4477631d2636 100644 --- a/drivers/gpu/drm/i915/i915_gpu_error.c +++ b/drivers/gpu/drm/i915/i915_gpu_error.c @@ -735,7 +735,7 @@ static void __err_print_to_sgl(struct drm_i915_error_state_buf *m, err_printf(m, "DONE_REG: 0x%08x\n", error->done_reg); } - if (IS_GEN7(m->i915)) + if (IS_GEN(m->i915, 7)) err_printf(m, "ERR_INT: 0x%08x\n", error->err_int); for (i = 0; i < ARRAY_SIZE(error->engine); i++) { @@ -1314,7 +1314,7 @@ static void error_record_engine_registers(struct i915_gpu_state *error, if (!HWS_NEEDS_PHYSICAL(dev_priv)) { i915_reg_t mmio; - if (IS_GEN7(dev_priv)) { + if (IS_GEN(dev_priv, 7)) { switch (engine->id) { default: case RCS: @@ -1330,7 +1330,7 @@ static void error_record_engine_registers(struct i915_gpu_state *error, mmio = VEBOX_HWS_PGA_GEN7; break; } - } else if (IS_GEN6(engine->i915)) { + } else if (IS_GEN(engine->i915, 6)) { mmio = RING_HWS_PGA_GEN6(engine->mmio_base); } else { /* XXX: gen8 returns to sanity */ @@ -1352,10 +1352,10 @@ static void error_record_engine_registers(struct i915_gpu_state *error, ee->vm_info.gfx_mode = I915_READ(RING_MODE_GEN7(engine)); - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) ee->vm_info.pp_dir_base = I915_READ(RING_PP_DIR_BASE_READ(engine)); - else if (IS_GEN7(dev_priv)) + else if (IS_GEN(dev_priv, 7)) ee->vm_info.pp_dir_base = I915_READ(RING_PP_DIR_BASE(engine)); else if (INTEL_GEN(dev_priv) >= 8) @@ -1725,7 +1725,7 @@ static void capture_reg_state(struct i915_gpu_state *error) error->forcewake = I915_READ_FW(FORCEWAKE_VLV); } - if (IS_GEN7(dev_priv)) + if (IS_GEN(dev_priv, 7)) error->err_int = I915_READ(GEN7_ERR_INT); if (INTEL_GEN(dev_priv) >= 8) { @@ -1733,7 +1733,7 @@ static void capture_reg_state(struct i915_gpu_state *error) error->fault_data1 = I915_READ(GEN8_FAULT_TLB_DATA1); } - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { error->forcewake = I915_READ_FW(FORCEWAKE); error->gab_ctl = I915_READ(GAB_CTL); error->gfx_mode = I915_READ(GFX_MODE); @@ -1753,7 +1753,7 @@ static void capture_reg_state(struct i915_gpu_state *error) error->ccid = I915_READ(CCID); /* 3: Feature specific registers */ - if (IS_GEN6(dev_priv) || IS_GEN7(dev_priv)) { + if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) { error->gam_ecochk = I915_READ(GAM_ECOCHK); error->gac_eco = I915_READ(GAC_ECO_BITS); } @@ -1777,7 +1777,7 @@ static void capture_reg_state(struct i915_gpu_state *error) error->ier = I915_READ(DEIER); error->gtier[0] = I915_READ(GTIER); error->ngtier = 1; - } else if (IS_GEN2(dev_priv)) { + } else if (IS_GEN(dev_priv, 2)) { error->ier = I915_READ16(IER); } else if (!IS_VALLEYVIEW(dev_priv)) { error->ier = I915_READ(IER); diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index d447d7d508f4..e2dac9b5f4ce 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -950,7 +950,7 @@ static int __intel_get_crtc_scanline(struct intel_crtc *crtc) if (mode->flags & DRM_MODE_FLAG_INTERLACE) vtotal /= 2; - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) position = I915_READ_FW(PIPEDSL(pipe)) & DSL_LINEMASK_GEN2; else position = I915_READ_FW(PIPEDSL(pipe)) & DSL_LINEMASK_GEN3; @@ -1030,7 +1030,7 @@ static bool i915_get_crtc_scanoutpos(struct drm_device *dev, unsigned int pipe, if (stime) *stime = ktime_get(); - if (IS_GEN2(dev_priv) || IS_G4X(dev_priv) || INTEL_GEN(dev_priv) >= 5) { + if (IS_GEN(dev_priv, 2) || IS_G4X(dev_priv) || INTEL_GEN(dev_priv) >= 5) { /* No obvious pixelcount register. Only query vertical * scanout position from Display scan line register. */ @@ -1090,7 +1090,7 @@ static bool i915_get_crtc_scanoutpos(struct drm_device *dev, unsigned int pipe, else position += vtotal - vbl_end; - if (IS_GEN2(dev_priv) || IS_G4X(dev_priv) || INTEL_GEN(dev_priv) >= 5) { + if (IS_GEN(dev_priv, 2) || IS_G4X(dev_priv) || INTEL_GEN(dev_priv) >= 5) { *vpos = position; *hpos = 0; } else { @@ -2547,7 +2547,7 @@ static void ilk_display_irq_handler(struct drm_i915_private *dev_priv, I915_WRITE(SDEIIR, pch_iir); } - if (IS_GEN5(dev_priv) && de_iir & DE_PCU_EVENT) + if (IS_GEN(dev_priv, 5) && de_iir & DE_PCU_EVENT) ironlake_rps_change_irq_handler(dev_priv); } @@ -3243,7 +3243,7 @@ void i915_clear_error_registers(struct drm_i915_private *dev_priv) { u32 eir; - if (!IS_GEN2(dev_priv)) + if (!IS_GEN(dev_priv, 2)) I915_WRITE(PGTBL_ER, I915_READ(PGTBL_ER)); if (INTEL_GEN(dev_priv) < 4) @@ -3586,11 +3586,11 @@ static void ironlake_irq_reset(struct drm_device *dev) { struct drm_i915_private *dev_priv = to_i915(dev); - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) I915_WRITE(HWSTAM, 0xffffffff); GEN3_IRQ_RESET(DE); - if (IS_GEN7(dev_priv)) + if (IS_GEN(dev_priv, 7)) I915_WRITE(GEN7_ERR_INT, 0xffffffff); if (IS_HASWELL(dev_priv)) { @@ -4045,7 +4045,7 @@ static void gen5_gt_irq_postinstall(struct drm_device *dev) } gt_irqs |= GT_RENDER_USER_INTERRUPT; - if (IS_GEN5(dev_priv)) { + if (IS_GEN(dev_priv, 5)) { gt_irqs |= ILK_BSD_USER_INTERRUPT; } else { gt_irqs |= GT_BLT_USER_INTERRUPT | GT_BSD_USER_INTERRUPT; @@ -4836,7 +4836,7 @@ void intel_irq_init(struct drm_i915_private *dev_priv) if (INTEL_GEN(dev_priv) >= 8) rps->pm_intrmsk_mbz |= GEN8_PMINTR_DISABLE_REDIRECT_TO_GUC; - if (IS_GEN2(dev_priv)) { + if (IS_GEN(dev_priv, 2)) { /* Gen2 doesn't have a hardware frame counter */ dev->max_vblank_count = 0; } else if (IS_G4X(dev_priv) || INTEL_GEN(dev_priv) >= 5) { @@ -4852,7 +4852,7 @@ void intel_irq_init(struct drm_i915_private *dev_priv) * Gen2 doesn't have a hardware frame counter and so depends on * vblank interrupts to produce sane vblank seuquence numbers. */ - if (!IS_GEN2(dev_priv)) + if (!IS_GEN(dev_priv, 2)) dev->vblank_disable_immediate = true; /* Most platforms treat the display irq block as an always-on @@ -4924,14 +4924,14 @@ void intel_irq_init(struct drm_i915_private *dev_priv) dev->driver->disable_vblank = ironlake_disable_vblank; dev_priv->display.hpd_irq_setup = ilk_hpd_irq_setup; } else { - if (IS_GEN2(dev_priv)) { + if (IS_GEN(dev_priv, 2)) { dev->driver->irq_preinstall = i8xx_irq_reset; dev->driver->irq_postinstall = i8xx_irq_postinstall; dev->driver->irq_handler = i8xx_irq_handler; dev->driver->irq_uninstall = i8xx_irq_reset; dev->driver->enable_vblank = i8xx_enable_vblank; dev->driver->disable_vblank = i8xx_disable_vblank; - } else if (IS_GEN3(dev_priv)) { + } else if (IS_GEN(dev_priv, 3)) { dev->driver->irq_preinstall = i915_irq_reset; dev->driver->irq_postinstall = i915_irq_postinstall; dev->driver->irq_uninstall = i915_irq_reset; diff --git a/drivers/gpu/drm/i915/i915_perf.c b/drivers/gpu/drm/i915/i915_perf.c index ad0095be435d..6c7992320443 100644 --- a/drivers/gpu/drm/i915/i915_perf.c +++ b/drivers/gpu/drm/i915/i915_perf.c @@ -3415,7 +3415,7 @@ void i915_perf_init(struct drm_i915_private *dev_priv) dev_priv->perf.oa.ops.read = gen8_oa_read; dev_priv->perf.oa.ops.oa_hw_tail_read = gen8_oa_hw_tail_read; - if (IS_GEN8(dev_priv) || IS_GEN9(dev_priv)) { + if (IS_GEN(dev_priv, 8) || IS_GEN(dev_priv, 9)) { dev_priv->perf.oa.ops.is_valid_b_counter_reg = gen7_is_valid_b_counter_addr; dev_priv->perf.oa.ops.is_valid_mux_reg = @@ -3431,7 +3431,7 @@ void i915_perf_init(struct drm_i915_private *dev_priv) dev_priv->perf.oa.ops.enable_metric_set = gen8_enable_metric_set; dev_priv->perf.oa.ops.disable_metric_set = gen8_disable_metric_set; - if (IS_GEN8(dev_priv)) { + if (IS_GEN(dev_priv, 8)) { dev_priv->perf.oa.ctx_oactxctrl_offset = 0x120; dev_priv->perf.oa.ctx_flexeu0_offset = 0x2ce; diff --git a/drivers/gpu/drm/i915/i915_suspend.c b/drivers/gpu/drm/i915/i915_suspend.c index 8f3aa4dc0c98..f40ba5e429e0 100644 --- a/drivers/gpu/drm/i915/i915_suspend.c +++ b/drivers/gpu/drm/i915/i915_suspend.c @@ -65,7 +65,7 @@ int i915_save_state(struct drm_i915_private *dev_priv) i915_save_display(dev_priv); - if (IS_GEN4(dev_priv)) + if (IS_GEN(dev_priv, 4)) pci_read_config_word(pdev, GCDGMBUS, &dev_priv->regfile.saveGCDGMBUS); @@ -77,14 +77,14 @@ int i915_save_state(struct drm_i915_private *dev_priv) dev_priv->regfile.saveMI_ARB_STATE = I915_READ(MI_ARB_STATE); /* Scratch space */ - if (IS_GEN2(dev_priv) && IS_MOBILE(dev_priv)) { + if (IS_GEN(dev_priv, 2) && IS_MOBILE(dev_priv)) { for (i = 0; i < 7; i++) { dev_priv->regfile.saveSWF0[i] = I915_READ(SWF0(i)); dev_priv->regfile.saveSWF1[i] = I915_READ(SWF1(i)); } for (i = 0; i < 3; i++) dev_priv->regfile.saveSWF3[i] = I915_READ(SWF3(i)); - } else if (IS_GEN2(dev_priv)) { + } else if (IS_GEN(dev_priv, 2)) { for (i = 0; i < 7; i++) dev_priv->regfile.saveSWF1[i] = I915_READ(SWF1(i)); } else if (HAS_GMCH_DISPLAY(dev_priv)) { @@ -108,7 +108,7 @@ int i915_restore_state(struct drm_i915_private *dev_priv) mutex_lock(&dev_priv->drm.struct_mutex); - if (IS_GEN4(dev_priv)) + if (IS_GEN(dev_priv, 4)) pci_write_config_word(pdev, GCDGMBUS, dev_priv->regfile.saveGCDGMBUS); i915_restore_display(dev_priv); @@ -122,14 +122,14 @@ int i915_restore_state(struct drm_i915_private *dev_priv) I915_WRITE(MI_ARB_STATE, dev_priv->regfile.saveMI_ARB_STATE | 0xffff0000); /* Scratch space */ - if (IS_GEN2(dev_priv) && IS_MOBILE(dev_priv)) { + if (IS_GEN(dev_priv, 2) && IS_MOBILE(dev_priv)) { for (i = 0; i < 7; i++) { I915_WRITE(SWF0(i), dev_priv->regfile.saveSWF0[i]); I915_WRITE(SWF1(i), dev_priv->regfile.saveSWF1[i]); } for (i = 0; i < 3; i++) I915_WRITE(SWF3(i), dev_priv->regfile.saveSWF3[i]); - } else if (IS_GEN2(dev_priv)) { + } else if (IS_GEN(dev_priv, 2)) { for (i = 0; i < 7; i++) I915_WRITE(SWF1(i), dev_priv->regfile.saveSWF1[i]); } else if (HAS_GMCH_DISPLAY(dev_priv)) { diff --git a/drivers/gpu/drm/i915/intel_atomic.c b/drivers/gpu/drm/i915/intel_atomic.c index 8cb02f28d30c..fdfc7425e644 100644 --- a/drivers/gpu/drm/i915/intel_atomic.c +++ b/drivers/gpu/drm/i915/intel_atomic.c @@ -233,7 +233,7 @@ static void intel_atomic_setup_scaler(struct intel_crtc_scaler_state *scaler_sta if (plane_state && plane_state->base.fb && plane_state->base.fb->format->is_yuv && plane_state->base.fb->format->num_planes > 1) { - if (IS_GEN9(dev_priv) && + if (IS_GEN(dev_priv, 9) && !IS_GEMINILAKE(dev_priv)) { mode = SKL_PS_SCALER_MODE_NV12; } else if (icl_is_hdr_plane(to_intel_plane(plane_state->base.plane))) { diff --git a/drivers/gpu/drm/i915/intel_audio.c b/drivers/gpu/drm/i915/intel_audio.c index ae55a6865d5c..0571aa2846a7 100644 --- a/drivers/gpu/drm/i915/intel_audio.c +++ b/drivers/gpu/drm/i915/intel_audio.c @@ -758,7 +758,7 @@ static void i915_audio_component_codec_wake_override(struct device *kdev, struct drm_i915_private *dev_priv = kdev_to_i915(kdev); u32 tmp; - if (!IS_GEN9(dev_priv)) + if (!IS_GEN(dev_priv, 9)) return; i915_audio_component_get_power(kdev); diff --git a/drivers/gpu/drm/i915/intel_cdclk.c b/drivers/gpu/drm/i915/intel_cdclk.c index 25e3aba9cded..2021e484a287 100644 --- a/drivers/gpu/drm/i915/intel_cdclk.c +++ b/drivers/gpu/drm/i915/intel_cdclk.c @@ -2140,7 +2140,7 @@ static int intel_pixel_rate_to_cdclk(struct drm_i915_private *dev_priv, { if (INTEL_GEN(dev_priv) >= 10 || IS_GEMINILAKE(dev_priv)) return DIV_ROUND_UP(pixel_rate, 2); - else if (IS_GEN9(dev_priv) || + else if (IS_GEN(dev_priv, 9) || IS_BROADWELL(dev_priv) || IS_HASWELL(dev_priv)) return pixel_rate; else if (IS_CHERRYVIEW(dev_priv)) @@ -2176,7 +2176,7 @@ int intel_crtc_compute_min_cdclk(const struct intel_crtc_state *crtc_state) if (IS_CANNONLAKE(dev_priv) || IS_GEMINILAKE(dev_priv)) { /* Display WA #1145: glk,cnl */ min_cdclk = max(316800, min_cdclk); - } else if (IS_GEN9(dev_priv) || IS_BROADWELL(dev_priv)) { + } else if (IS_GEN(dev_priv, 9) || IS_BROADWELL(dev_priv)) { /* Display WA #1144: skl,bxt */ min_cdclk = max(432000, min_cdclk); } @@ -2537,7 +2537,7 @@ static int intel_compute_max_dotclk(struct drm_i915_private *dev_priv) if (INTEL_GEN(dev_priv) >= 10 || IS_GEMINILAKE(dev_priv)) return 2 * max_cdclk_freq; - else if (IS_GEN9(dev_priv) || + else if (IS_GEN(dev_priv, 9) || IS_BROADWELL(dev_priv) || IS_HASWELL(dev_priv)) return max_cdclk_freq; else if (IS_CHERRYVIEW(dev_priv)) @@ -2785,9 +2785,9 @@ void intel_init_cdclk_hooks(struct drm_i915_private *dev_priv) dev_priv->display.get_cdclk = hsw_get_cdclk; else if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) dev_priv->display.get_cdclk = vlv_get_cdclk; - else if (IS_GEN6(dev_priv) || IS_IVYBRIDGE(dev_priv)) + else if (IS_GEN(dev_priv, 6) || IS_IVYBRIDGE(dev_priv)) dev_priv->display.get_cdclk = fixed_400mhz_get_cdclk; - else if (IS_GEN5(dev_priv)) + else if (IS_GEN(dev_priv, 5)) dev_priv->display.get_cdclk = fixed_450mhz_get_cdclk; else if (IS_GM45(dev_priv)) dev_priv->display.get_cdclk = gm45_get_cdclk; diff --git a/drivers/gpu/drm/i915/intel_crt.c b/drivers/gpu/drm/i915/intel_crt.c index 68f2fb89ece3..bf4fd739b68c 100644 --- a/drivers/gpu/drm/i915/intel_crt.c +++ b/drivers/gpu/drm/i915/intel_crt.c @@ -322,7 +322,7 @@ intel_crt_mode_valid(struct drm_connector *connector, * DAC limit supposedly 355 MHz. */ max_clock = 270000; - else if (IS_GEN3(dev_priv) || IS_GEN4(dev_priv)) + else if (IS_GEN(dev_priv, 3) || IS_GEN(dev_priv, 4)) max_clock = 400000; else max_clock = 350000; @@ -666,7 +666,7 @@ intel_crt_load_detect(struct intel_crt *crt, uint32_t pipe) /* Set the border color to purple. */ I915_WRITE(bclrpat_reg, 0x500050); - if (!IS_GEN2(dev_priv)) { + if (!IS_GEN(dev_priv, 2)) { uint32_t pipeconf = I915_READ(pipeconf_reg); I915_WRITE(pipeconf_reg, pipeconf | PIPECONF_FORCE_BORDER); POSTING_READ(pipeconf_reg); @@ -981,7 +981,7 @@ void intel_crt_init(struct drm_i915_private *dev_priv) else crt->base.crtc_mask = (1 << 0) | (1 << 1) | (1 << 2); - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) connector->interlace_allowed = 0; else connector->interlace_allowed = 1; diff --git a/drivers/gpu/drm/i915/intel_device_info.c b/drivers/gpu/drm/i915/intel_device_info.c index bd5c4d62c635..8627b9a6bff4 100644 --- a/drivers/gpu/drm/i915/intel_device_info.c +++ b/drivers/gpu/drm/i915/intel_device_info.c @@ -748,7 +748,7 @@ void intel_device_info_runtime_init(struct intel_device_info *info) if (INTEL_GEN(dev_priv) >= 10) { for_each_pipe(dev_priv, pipe) info->num_scalers[pipe] = 2; - } else if (IS_GEN9(dev_priv)) { + } else if (IS_GEN(dev_priv, 9)) { info->num_scalers[PIPE_A] = 2; info->num_scalers[PIPE_B] = 2; info->num_scalers[PIPE_C] = 1; @@ -756,10 +756,10 @@ void intel_device_info_runtime_init(struct intel_device_info *info) BUILD_BUG_ON(I915_NUM_ENGINES > BITS_PER_TYPE(intel_ring_mask_t)); - if (IS_GEN11(dev_priv)) + if (IS_GEN(dev_priv, 11)) for_each_pipe(dev_priv, pipe) info->num_sprites[pipe] = 6; - else if (IS_GEN10(dev_priv) || IS_GEMINILAKE(dev_priv)) + else if (IS_GEN(dev_priv, 10) || IS_GEMINILAKE(dev_priv)) for_each_pipe(dev_priv, pipe) info->num_sprites[pipe] = 3; else if (IS_BROXTON(dev_priv)) { @@ -787,7 +787,7 @@ void intel_device_info_runtime_init(struct intel_device_info *info) DRM_INFO("Display disabled (module parameter)\n"); info->num_pipes = 0; } else if (HAS_DISPLAY(dev_priv) && - (IS_GEN7(dev_priv) || IS_GEN8(dev_priv)) && + (IS_GEN(dev_priv, 7) || IS_GEN(dev_priv, 8)) && HAS_PCH_SPLIT(dev_priv)) { u32 fuse_strap = I915_READ(FUSE_STRAP); u32 sfuse_strap = I915_READ(SFUSE_STRAP); @@ -851,14 +851,14 @@ void intel_device_info_runtime_init(struct intel_device_info *info) cherryview_sseu_info_init(dev_priv); else if (IS_BROADWELL(dev_priv)) broadwell_sseu_info_init(dev_priv); - else if (IS_GEN9(dev_priv)) + else if (IS_GEN(dev_priv, 9)) gen9_sseu_info_init(dev_priv); - else if (IS_GEN10(dev_priv)) + else if (IS_GEN(dev_priv, 10)) gen10_sseu_info_init(dev_priv); else if (INTEL_GEN(dev_priv) >= 11) gen11_sseu_info_init(dev_priv); - if (IS_GEN6(dev_priv) && intel_vtd_active()) { + if (IS_GEN(dev_priv, 6) && intel_vtd_active()) { DRM_INFO("Disabling ppGTT for VT-d support\n"); info->ppgtt = INTEL_PPGTT_NONE; } diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 13e5650b6f31..b9e8a9898983 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -984,7 +984,7 @@ static bool pipe_scanline_is_moving(struct drm_i915_private *dev_priv, u32 line1, line2; u32 line_mask; - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) line_mask = DSL_LINEMASK_GEN2; else line_mask = DSL_LINEMASK_GEN3; @@ -1110,7 +1110,7 @@ static void assert_fdi_tx_pll_enabled(struct drm_i915_private *dev_priv, u32 val; /* ILK FDI PLL is always enabled */ - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) return; /* On Haswell, DDI ports are responsible for the FDI PLL setup */ @@ -1850,7 +1850,7 @@ static void intel_disable_pipe(const struct intel_crtc_state *old_crtc_state) static unsigned int intel_tile_size(const struct drm_i915_private *dev_priv) { - return IS_GEN2(dev_priv) ? 2048 : 4096; + return IS_GEN(dev_priv, 2) ? 2048 : 4096; } static unsigned int @@ -1863,7 +1863,7 @@ intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane) case DRM_FORMAT_MOD_LINEAR: return cpp; case I915_FORMAT_MOD_X_TILED: - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) return 128; else return 512; @@ -1872,7 +1872,7 @@ intel_tile_width_bytes(const struct drm_framebuffer *fb, int color_plane) return 128; /* fall through */ case I915_FORMAT_MOD_Y_TILED: - if (IS_GEN2(dev_priv) || HAS_128_BYTE_Y_TILING(dev_priv)) + if (IS_GEN(dev_priv, 2) || HAS_128_BYTE_Y_TILING(dev_priv)) return 128; else return 512; @@ -3193,8 +3193,8 @@ static u32 i9xx_plane_ctl(const struct intel_crtc_state *crtc_state, dspcntr = DISPLAY_PLANE_ENABLE | DISPPLANE_GAMMA_ENABLE; - if (IS_G4X(dev_priv) || IS_GEN5(dev_priv) || - IS_GEN6(dev_priv) || IS_IVYBRIDGE(dev_priv)) + if (IS_G4X(dev_priv) || IS_GEN(dev_priv, 5) || + IS_GEN(dev_priv, 6) || IS_IVYBRIDGE(dev_priv)) dspcntr |= DISPPLANE_TRICKLE_FEED_DISABLE; if (IS_HASWELL(dev_priv) || IS_BROADWELL(dev_priv)) @@ -4120,7 +4120,7 @@ static void gen6_fdi_link_train(struct intel_crtc *crtc, temp = I915_READ(reg); temp &= ~FDI_LINK_TRAIN_NONE; temp |= FDI_LINK_TRAIN_PATTERN_2; - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { temp &= ~FDI_LINK_TRAIN_VOL_EMP_MASK; /* SNB-B */ temp |= FDI_LINK_TRAIN_400MV_0DB_SNB_B; @@ -4919,10 +4919,10 @@ skl_update_scaler(struct intel_crtc_state *crtc_state, bool force_detach, /* range checks */ if (src_w < SKL_MIN_SRC_W || src_h < SKL_MIN_SRC_H || dst_w < SKL_MIN_DST_W || dst_h < SKL_MIN_DST_H || - (IS_GEN11(dev_priv) && + (IS_GEN(dev_priv, 11) && (src_w > ICL_MAX_SRC_W || src_h > ICL_MAX_SRC_H || dst_w > ICL_MAX_DST_W || dst_h > ICL_MAX_DST_H)) || - (!IS_GEN11(dev_priv) && + (!IS_GEN(dev_priv, 11) && (src_w > SKL_MAX_SRC_W || src_h > SKL_MAX_SRC_H || dst_w > SKL_MAX_DST_W || dst_h > SKL_MAX_DST_H))) { DRM_DEBUG_KMS("scaler_user index %u.%u: src %ux%u dst %ux%u " @@ -5213,7 +5213,7 @@ intel_post_enable_primary(struct drm_crtc *crtc, * FIXME: Need to fix the logic to work when we turn off all planes * but leave the pipe running. */ - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) intel_set_cpu_fifo_underrun_reporting(dev_priv, pipe, true); /* Underruns don't always raise interrupts, so check manually. */ @@ -5234,7 +5234,7 @@ intel_pre_disable_primary_noatomic(struct drm_crtc *crtc) * Gen2 reports pipe underruns whenever all planes are disabled. * So disable underrun reporting before all the planes get disabled. */ - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) intel_set_cpu_fifo_underrun_reporting(dev_priv, pipe, false); hsw_disable_ips(to_intel_crtc_state(crtc->state)); @@ -5292,7 +5292,7 @@ static bool needs_nv12_wa(struct drm_i915_private *dev_priv, return false; /* WA Display #0827: Gen9:all */ - if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv)) + if (IS_GEN(dev_priv, 9) && !IS_GEMINILAKE(dev_priv)) return true; return false; @@ -5365,7 +5365,7 @@ static void intel_pre_plane_update(struct intel_crtc_state *old_crtc_state, * Gen2 reports pipe underruns whenever all planes are disabled. * So disable underrun reporting before all the planes get disabled. */ - if (IS_GEN2(dev_priv) && old_primary_state->visible && + if (IS_GEN(dev_priv, 2) && old_primary_state->visible && (modeset || !new_primary_state->base.visible)) intel_set_cpu_fifo_underrun_reporting(dev_priv, crtc->pipe, false); } @@ -6184,7 +6184,7 @@ static void i9xx_crtc_enable(struct intel_crtc_state *pipe_config, intel_crtc->active = true; - if (!IS_GEN2(dev_priv)) + if (!IS_GEN(dev_priv, 2)) intel_set_cpu_fifo_underrun_reporting(dev_priv, pipe, true); intel_encoders_pre_enable(crtc, pipe_config, old_state); @@ -6236,7 +6236,7 @@ static void i9xx_crtc_disable(struct intel_crtc_state *old_crtc_state, * On gen2 planes are double buffered but the pipe isn't, so we must * wait for planes to fully turn off before disabling the pipe. */ - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) intel_wait_for_vblank(dev_priv, pipe); intel_encoders_disable(crtc, old_crtc_state, old_state); @@ -6261,7 +6261,7 @@ static void i9xx_crtc_disable(struct intel_crtc_state *old_crtc_state, intel_encoders_post_pll_disable(crtc, old_crtc_state, old_state); - if (!IS_GEN2(dev_priv)) + if (!IS_GEN(dev_priv, 2)) intel_set_cpu_fifo_underrun_reporting(dev_priv, pipe, false); if (!dev_priv->display.initial_watermarks) @@ -6868,7 +6868,7 @@ static bool transcoder_has_m2_n2(struct drm_i915_private *dev_priv, * Strictly speaking some registers are available before * gen7, but we only support DRRS on gen7+ */ - return IS_GEN7(dev_priv) || IS_CHERRYVIEW(dev_priv); + return IS_GEN(dev_priv, 7) || IS_CHERRYVIEW(dev_priv); } static void intel_cpu_transcoder_set_m_n(const struct intel_crtc_state *crtc_state, @@ -9005,7 +9005,7 @@ static void ironlake_get_pfit_config(struct intel_crtc *crtc, /* We currently do not free assignements of panel fitters on * ivb/hsw (since we don't use the higher upscaling modes which * differentiates them) so just WARN about this case for now. */ - if (IS_GEN7(dev_priv)) { + if (IS_GEN(dev_priv, 7)) { WARN_ON((tmp & PF_PIPE_SEL_MASK_IVB) != PF_PIPE_SEL_IVB(crtc->pipe)); } @@ -9995,7 +9995,7 @@ static u32 i9xx_cursor_ctl(const struct intel_crtc_state *crtc_state, struct intel_crtc *crtc = to_intel_crtc(crtc_state->base.crtc); u32 cntl = 0; - if (IS_GEN6(dev_priv) || IS_IVYBRIDGE(dev_priv)) + if (IS_GEN(dev_priv, 6) || IS_IVYBRIDGE(dev_priv)) cntl |= MCURSOR_TRICKLE_FEED_DISABLE; if (INTEL_GEN(dev_priv) <= 10) { @@ -10468,7 +10468,7 @@ static int i9xx_pll_refclk(struct drm_device *dev, return dev_priv->vbt.lvds_ssc_freq; else if (HAS_PCH_SPLIT(dev_priv)) return 120000; - else if (!IS_GEN2(dev_priv)) + else if (!IS_GEN(dev_priv, 2)) return 96000; else return 48000; @@ -10501,7 +10501,7 @@ static void i9xx_crtc_clock_get(struct intel_crtc *crtc, clock.m2 = (fp & FP_M2_DIV_MASK) >> FP_M2_DIV_SHIFT; } - if (!IS_GEN2(dev_priv)) { + if (!IS_GEN(dev_priv, 2)) { if (IS_PINEVIEW(dev_priv)) clock.p1 = ffs((dpll & DPLL_FPA01_P1_POST_DIV_MASK_PINEVIEW) >> DPLL_FPA01_P1_POST_DIV_SHIFT_PINEVIEW); @@ -10815,7 +10815,7 @@ int intel_plane_atomic_calc_changes(const struct intel_crtc_state *old_crtc_stat * the w/a on all three platforms. */ if (plane->id == PLANE_SPRITE0 && - (IS_GEN5(dev_priv) || IS_GEN6(dev_priv) || + (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6) || IS_IVYBRIDGE(dev_priv)) && (turn_on || (!needs_scaling(old_plane_state) && needs_scaling(to_intel_plane_state(plane_state))))) @@ -12373,7 +12373,7 @@ static void update_scanline_offset(const struct intel_crtc_state *crtc_state) * However if queried just before the start of vblank we'll get an * answer that's slightly in the future. */ - if (IS_GEN2(dev_priv)) { + if (IS_GEN(dev_priv, 2)) { const struct drm_display_mode *adjusted_mode = &crtc_state->base.adjusted_mode; int vtotal; @@ -13573,7 +13573,7 @@ void intel_crtc_arm_fifo_underrun(struct intel_crtc *crtc, { struct drm_i915_private *dev_priv = to_i915(crtc->base.dev); - if (!IS_GEN2(dev_priv)) + if (!IS_GEN(dev_priv, 2)) intel_set_cpu_fifo_underrun_reporting(dev_priv, crtc->pipe, true); if (crtc_state->has_pch_encoder) { @@ -14180,7 +14180,7 @@ static bool has_edp_a(struct drm_i915_private *dev_priv) if ((I915_READ(DP_A) & DP_DETECTED) == 0) return false; - if (IS_GEN5(dev_priv) && (I915_READ(FUSE_STRAP) & ILK_eDP_A_DISABLE)) + if (IS_GEN(dev_priv, 5) && (I915_READ(FUSE_STRAP) & ILK_eDP_A_DISABLE)) return false; return true; @@ -14392,7 +14392,7 @@ static void intel_setup_outputs(struct drm_i915_private *dev_priv) } vlv_dsi_init(dev_priv); - } else if (!IS_GEN2(dev_priv) && !IS_PINEVIEW(dev_priv)) { + } else if (!IS_GEN(dev_priv, 2) && !IS_PINEVIEW(dev_priv)) { bool found = false; if (I915_READ(GEN3_SDVOB) & SDVO_DETECTED) { @@ -14426,7 +14426,7 @@ static void intel_setup_outputs(struct drm_i915_private *dev_priv) if (IS_G4X(dev_priv) && (I915_READ(DP_D) & DP_DETECTED)) intel_dp_init(dev_priv, DP_D, PORT_D); - } else if (IS_GEN2(dev_priv)) + } else if (IS_GEN(dev_priv, 2)) intel_dvo_init(dev_priv); if (SUPPORTS_TV(dev_priv)) @@ -14624,7 +14624,7 @@ static int intel_framebuffer_init(struct intel_framebuffer *intel_fb, * require the entire fb to accommodate that to avoid * potential runtime errors at plane configuration time. */ - if (IS_GEN9(dev_priv) && i == 0 && fb->width > 3840 && + if (IS_GEN(dev_priv, 9) && i == 0 && fb->width > 3840 && is_ccs_modifier(fb->modifier)) stride_alignment *= 4; @@ -14829,7 +14829,7 @@ void intel_init_display_hooks(struct drm_i915_private *dev_priv) dev_priv->display.crtc_compute_clock = pnv_crtc_compute_clock; dev_priv->display.crtc_enable = i9xx_crtc_enable; dev_priv->display.crtc_disable = i9xx_crtc_disable; - } else if (!IS_GEN2(dev_priv)) { + } else if (!IS_GEN(dev_priv, 2)) { dev_priv->display.get_pipe_config = i9xx_get_pipe_config; dev_priv->display.get_initial_plane_config = i9xx_get_initial_plane_config; @@ -14845,9 +14845,9 @@ void intel_init_display_hooks(struct drm_i915_private *dev_priv) dev_priv->display.crtc_disable = i9xx_crtc_disable; } - if (IS_GEN5(dev_priv)) { + if (IS_GEN(dev_priv, 5)) { dev_priv->display.fdi_link_train = ironlake_fdi_link_train; - } else if (IS_GEN6(dev_priv)) { + } else if (IS_GEN(dev_priv, 6)) { dev_priv->display.fdi_link_train = gen6_fdi_link_train; } else if (IS_IVYBRIDGE(dev_priv)) { /* FIXME: detect B0+ stepping and use auto training */ @@ -14979,12 +14979,12 @@ static void sanitize_watermarks(struct drm_device *dev) static void intel_update_fdi_pll_freq(struct drm_i915_private *dev_priv) { - if (IS_GEN5(dev_priv)) { + if (IS_GEN(dev_priv, 5)) { u32 fdi_pll_clk = I915_READ(FDI_PLL_BIOS_0) & FDI_PLL_FB_CLOCK_MASK; dev_priv->fdi_pll_freq = (fdi_pll_clk + 2) * 10000; - } else if (IS_GEN6(dev_priv) || IS_IVYBRIDGE(dev_priv)) { + } else if (IS_GEN(dev_priv, 6) || IS_IVYBRIDGE(dev_priv)) { dev_priv->fdi_pll_freq = 270000; } else { return; @@ -15100,10 +15100,10 @@ int intel_modeset_init(struct drm_device *dev) } /* maximum framebuffer dimensions */ - if (IS_GEN2(dev_priv)) { + if (IS_GEN(dev_priv, 2)) { dev->mode_config.max_width = 2048; dev->mode_config.max_height = 2048; - } else if (IS_GEN3(dev_priv)) { + } else if (IS_GEN(dev_priv, 3)) { dev->mode_config.max_width = 4096; dev->mode_config.max_height = 4096; } else { @@ -15114,7 +15114,7 @@ int intel_modeset_init(struct drm_device *dev) if (IS_I845G(dev_priv) || IS_I865G(dev_priv)) { dev->mode_config.cursor_width = IS_I845G(dev_priv) ? 64 : 512; dev->mode_config.cursor_height = 1023; - } else if (IS_GEN2(dev_priv)) { + } else if (IS_GEN(dev_priv, 2)) { dev->mode_config.cursor_width = 64; dev->mode_config.cursor_height = 64; } else { diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index e94faa0a42eb..b3138abd3321 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -344,7 +344,7 @@ intel_dp_set_source_rates(struct intel_dp *intel_dp) if (INTEL_GEN(dev_priv) >= 10) { source_rates = cnl_rates; size = ARRAY_SIZE(cnl_rates); - if (IS_GEN10(dev_priv)) + if (IS_GEN(dev_priv, 10)) max_rate = cnl_max_source_rate(intel_dp); else max_rate = icl_max_source_rate(intel_dp); @@ -1128,7 +1128,7 @@ static uint32_t g4x_get_aux_send_ctl(struct intel_dp *intel_dp, to_i915(intel_dig_port->base.base.dev); uint32_t precharge, timeout; - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) precharge = 3; else precharge = 5; @@ -2585,7 +2585,7 @@ static void edp_panel_on(struct intel_dp *intel_dp) pp_ctrl_reg = _pp_ctrl_reg(intel_dp); pp = ironlake_get_pp_control(intel_dp); - if (IS_GEN5(dev_priv)) { + if (IS_GEN(dev_priv, 5)) { /* ILK workaround: disable reset around power sequence */ pp &= ~PANEL_POWER_RESET; I915_WRITE(pp_ctrl_reg, pp); @@ -2593,7 +2593,7 @@ static void edp_panel_on(struct intel_dp *intel_dp) } pp |= PANEL_POWER_ON; - if (!IS_GEN5(dev_priv)) + if (!IS_GEN(dev_priv, 5)) pp |= PANEL_POWER_RESET; I915_WRITE(pp_ctrl_reg, pp); @@ -2602,7 +2602,7 @@ static void edp_panel_on(struct intel_dp *intel_dp) wait_panel_on(intel_dp); intel_dp->last_power_on = jiffies; - if (IS_GEN5(dev_priv)) { + if (IS_GEN(dev_priv, 5)) { pp |= PANEL_POWER_RESET; /* restore panel reset bit */ I915_WRITE(pp_ctrl_reg, pp); POSTING_READ(pp_ctrl_reg); @@ -2831,7 +2831,7 @@ static void ironlake_edp_pll_on(struct intel_dp *intel_dp, * 1. Wait for the start of vertical blank on the enabled pipe going to FDI * 2. Program DP PLL enable */ - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) intel_wait_for_vblank_if_active(dev_priv, !crtc->pipe); intel_dp->DP |= DP_PLL_ENABLE; @@ -3849,7 +3849,7 @@ intel_dp_set_signal_levels(struct intel_dp *intel_dp) } else if (IS_IVYBRIDGE(dev_priv) && port == PORT_A) { signal_levels = ivb_cpu_edp_signal_levels(train_set); mask = EDP_LINK_TRAIN_VOL_EMP_MASK_IVB; - } else if (IS_GEN6(dev_priv) && port == PORT_A) { + } else if (IS_GEN(dev_priv, 6) && port == PORT_A) { signal_levels = snb_cpu_edp_signal_levels(train_set); mask = EDP_LINK_TRAIN_VOL_EMP_MASK_SNB; } else { @@ -5271,17 +5271,17 @@ bool intel_digital_port_connected(struct intel_encoder *encoder) if (INTEL_GEN(dev_priv) >= 11) return icl_digital_port_connected(encoder); - else if (IS_GEN10(dev_priv) || IS_GEN9_BC(dev_priv)) + else if (IS_GEN(dev_priv, 10) || IS_GEN9_BC(dev_priv)) return spt_digital_port_connected(encoder); else if (IS_GEN9_LP(dev_priv)) return bxt_digital_port_connected(encoder); - else if (IS_GEN8(dev_priv)) + else if (IS_GEN(dev_priv, 8)) return bdw_digital_port_connected(encoder); - else if (IS_GEN7(dev_priv)) + else if (IS_GEN(dev_priv, 7)) return ivb_digital_port_connected(encoder); - else if (IS_GEN6(dev_priv)) + else if (IS_GEN(dev_priv, 6)) return snb_digital_port_connected(encoder); - else if (IS_GEN5(dev_priv)) + else if (IS_GEN(dev_priv, 5)) return ilk_digital_port_connected(encoder); MISSING_CASE(INTEL_GEN(dev_priv)); diff --git a/drivers/gpu/drm/i915/intel_engine_cs.c b/drivers/gpu/drm/i915/intel_engine_cs.c index fe5e87b6e1af..8ff794db7881 100644 --- a/drivers/gpu/drm/i915/intel_engine_cs.c +++ b/drivers/gpu/drm/i915/intel_engine_cs.c @@ -438,7 +438,7 @@ void intel_engine_init_global_seqno(struct intel_engine_cs *engine, u32 seqno) * the semaphore value, then when the seqno moves backwards all * future waits will complete instantly (causing rendering corruption). */ - if (IS_GEN6(dev_priv) || IS_GEN7(dev_priv)) { + if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) { I915_WRITE(RING_SYNC_0(engine->mmio_base), 0); I915_WRITE(RING_SYNC_1(engine->mmio_base), 0); if (HAS_VEBOX(dev_priv)) @@ -774,7 +774,7 @@ u32 intel_calculate_mcr_s_ss_select(struct drm_i915_private *dev_priv) u32 slice = fls(sseu->slice_mask); u32 subslice = fls(sseu->subslice_mask[slice]); - if (IS_GEN10(dev_priv)) + if (IS_GEN(dev_priv, 10)) mcr_s_ss_select = GEN8_MCR_SLICE(slice) | GEN8_MCR_SUBSLICE(subslice); else if (INTEL_GEN(dev_priv) >= 11) diff --git a/drivers/gpu/drm/i915/intel_fbc.c b/drivers/gpu/drm/i915/intel_fbc.c index b57e31fc0f1e..1d3ff026d1bc 100644 --- a/drivers/gpu/drm/i915/intel_fbc.c +++ b/drivers/gpu/drm/i915/intel_fbc.c @@ -84,7 +84,7 @@ static int intel_fbc_calculate_cfb_size(struct drm_i915_private *dev_priv, int lines; intel_fbc_get_plane_source_size(cache, NULL, &lines); - if (IS_GEN7(dev_priv)) + if (IS_GEN(dev_priv, 7)) lines = min(lines, 2048); else if (INTEL_GEN(dev_priv) >= 8) lines = min(lines, 2560); @@ -127,7 +127,7 @@ static void i8xx_fbc_activate(struct drm_i915_private *dev_priv) cfb_pitch = params->fb.stride; /* FBC_CTL wants 32B or 64B units */ - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) cfb_pitch = (cfb_pitch / 32) - 1; else cfb_pitch = (cfb_pitch / 64) - 1; @@ -136,7 +136,7 @@ static void i8xx_fbc_activate(struct drm_i915_private *dev_priv) for (i = 0; i < (FBC_LL_SIZE / 32) + 1; i++) I915_WRITE(FBC_TAG(i), 0); - if (IS_GEN4(dev_priv)) { + if (IS_GEN(dev_priv, 4)) { u32 fbc_ctl2; /* Set it up... */ @@ -233,9 +233,9 @@ static void ilk_fbc_activate(struct drm_i915_private *dev_priv) if (params->flags & PLANE_HAS_FENCE) { dpfc_ctl |= DPFC_CTL_FENCE_EN; - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) dpfc_ctl |= params->vma->fence->id; - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { I915_WRITE(SNB_DPFC_CTL_SA, SNB_CPU_FENCE_ENABLE | params->vma->fence->id); @@ -243,7 +243,7 @@ static void ilk_fbc_activate(struct drm_i915_private *dev_priv) params->crtc.fence_y_offset); } } else { - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { I915_WRITE(SNB_DPFC_CTL_SA, 0); I915_WRITE(DPFC_CPU_FENCE_OFFSET, 0); } @@ -282,7 +282,7 @@ static void gen7_fbc_activate(struct drm_i915_private *dev_priv) int threshold = dev_priv->fbc.threshold; /* Display WA #0529: skl, kbl, bxt. */ - if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv)) { + if (IS_GEN(dev_priv, 9) && !IS_GEMINILAKE(dev_priv)) { u32 val = I915_READ(CHICKEN_MISC_4); val &= ~(FBC_STRIDE_OVERRIDE | FBC_STRIDE_MASK); @@ -581,10 +581,10 @@ static bool stride_is_valid(struct drm_i915_private *dev_priv, if (stride < 512) return false; - if (IS_GEN2(dev_priv) || IS_GEN3(dev_priv)) + if (IS_GEN(dev_priv, 2) || IS_GEN(dev_priv, 3)) return stride == 4096 || stride == 8192; - if (IS_GEN4(dev_priv) && !IS_G4X(dev_priv) && stride < 2048) + if (IS_GEN(dev_priv, 4) && !IS_G4X(dev_priv) && stride < 2048) return false; if (stride > 16384) @@ -603,7 +603,7 @@ static bool pixel_format_is_valid(struct drm_i915_private *dev_priv, case DRM_FORMAT_XRGB1555: case DRM_FORMAT_RGB565: /* 16bpp not supported on gen2 */ - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) return false; /* WaFbcOnly1to1Ratio:ctg */ if (IS_G4X(dev_priv)) @@ -842,7 +842,7 @@ static void intel_fbc_get_reg_params(struct intel_crtc *crtc, params->cfb_size = intel_fbc_calculate_cfb_size(dev_priv, cache); - if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv)) + if (IS_GEN(dev_priv, 9) && !IS_GEMINILAKE(dev_priv)) params->gen9_wa_cfb_stride = DIV_ROUND_UP(cache->plane.src_w, 32 * fbc->threshold) * 8; } diff --git a/drivers/gpu/drm/i915/intel_fifo_underrun.c b/drivers/gpu/drm/i915/intel_fifo_underrun.c index 77c123cc8817..ff2743ccbece 100644 --- a/drivers/gpu/drm/i915/intel_fifo_underrun.c +++ b/drivers/gpu/drm/i915/intel_fifo_underrun.c @@ -260,9 +260,9 @@ static bool __intel_set_cpu_fifo_underrun_reporting(struct drm_device *dev, if (HAS_GMCH_DISPLAY(dev_priv)) i9xx_set_fifo_underrun_reporting(dev, pipe, enable, old); - else if (IS_GEN5(dev_priv) || IS_GEN6(dev_priv)) + else if (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6)) ironlake_set_fifo_underrun_reporting(dev, pipe, enable); - else if (IS_GEN7(dev_priv)) + else if (IS_GEN(dev_priv, 7)) ivybridge_set_fifo_underrun_reporting(dev, pipe, enable, old); else if (INTEL_GEN(dev_priv) >= 8) broadwell_set_fifo_underrun_reporting(dev, pipe, enable); @@ -423,7 +423,7 @@ void intel_check_cpu_fifo_underruns(struct drm_i915_private *dev_priv) if (HAS_GMCH_DISPLAY(dev_priv)) i9xx_check_fifo_underruns(crtc); - else if (IS_GEN7(dev_priv)) + else if (IS_GEN(dev_priv, 7)) ivybridge_check_fifo_underruns(crtc); } diff --git a/drivers/gpu/drm/i915/intel_guc_fw.c b/drivers/gpu/drm/i915/intel_guc_fw.c index a67144ee5ceb..4b437e05e2cd 100644 --- a/drivers/gpu/drm/i915/intel_guc_fw.c +++ b/drivers/gpu/drm/i915/intel_guc_fw.c @@ -115,7 +115,7 @@ static void guc_prepare_xfer(struct intel_guc *guc) else I915_WRITE(GEN9_GT_PM_CONFIG, GT_DOORBELL_ENABLE); - if (IS_GEN9(dev_priv)) { + if (IS_GEN(dev_priv, 9)) { /* DOP Clock Gating Enable for GuC clocks */ I915_WRITE(GEN7_MISCCPCTL, (GEN8_DOP_CLOCK_GATE_GUC_ENABLE | I915_READ(GEN7_MISCCPCTL))); diff --git a/drivers/gpu/drm/i915/intel_hangcheck.c b/drivers/gpu/drm/i915/intel_hangcheck.c index 41921a843d42..495fa145f37f 100644 --- a/drivers/gpu/drm/i915/intel_hangcheck.c +++ b/drivers/gpu/drm/i915/intel_hangcheck.c @@ -236,7 +236,7 @@ engine_stuck(struct intel_engine_cs *engine, u64 acthd) if (ha != ENGINE_DEAD) return ha; - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) return ENGINE_DEAD; /* Is the chip hanging on a WAIT_FOR_EVENT? diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index ae7e5b288ed5..f16fb30da64f 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -1990,7 +1990,7 @@ static int gen8_emit_flush_render(struct i915_request *request, * On GEN9: before VF_CACHE_INVALIDATE we need to emit a NULL * pipe control. */ - if (IS_GEN9(request->i915)) + if (IS_GEN(request->i915, 9)) vf_flush_wa = true; /* WaForGAMHang:kbl */ @@ -2341,7 +2341,7 @@ make_rpcs(struct drm_i915_private *dev_priv) * subslices are enabled, or a count between one and four on the first * slice. */ - if (IS_GEN11(dev_priv) && slices == 1 && subslices >= 4) { + if (IS_GEN(dev_priv, 11) && slices == 1 && subslices >= 4) { GEM_BUG_ON(subslices & 1); subslice_pg = false; diff --git a/drivers/gpu/drm/i915/intel_lvds.c b/drivers/gpu/drm/i915/intel_lvds.c index e6c5d985ea0a..b85e195f7c8a 100644 --- a/drivers/gpu/drm/i915/intel_lvds.c +++ b/drivers/gpu/drm/i915/intel_lvds.c @@ -279,7 +279,7 @@ static void intel_pre_enable_lvds(struct intel_encoder *encoder, * special lvds dither control bit on pch-split platforms, dithering is * only controlled through the PIPECONF reg. */ - if (IS_GEN4(dev_priv)) { + if (IS_GEN(dev_priv, 4)) { /* * Bspec wording suggests that LVDS port dithering only exists * for 18bpp panels. @@ -919,7 +919,7 @@ void intel_lvds_init(struct drm_i915_private *dev_priv) intel_encoder->cloneable = 0; if (HAS_PCH_SPLIT(dev_priv)) intel_encoder->crtc_mask = (1 << 0) | (1 << 1) | (1 << 2); - else if (IS_GEN4(dev_priv)) + else if (IS_GEN(dev_priv, 4)) intel_encoder->crtc_mask = (1 << 0) | (1 << 1); else intel_encoder->crtc_mask = (1 << 1); diff --git a/drivers/gpu/drm/i915/intel_mocs.c b/drivers/gpu/drm/i915/intel_mocs.c index 77e9871a8c9a..e976c5ce5479 100644 --- a/drivers/gpu/drm/i915/intel_mocs.c +++ b/drivers/gpu/drm/i915/intel_mocs.c @@ -193,7 +193,7 @@ static bool get_mocs_settings(struct drm_i915_private *dev_priv, } /* WaDisableSkipCaching:skl,bxt,kbl,glk */ - if (IS_GEN9(dev_priv)) { + if (IS_GEN(dev_priv, 9)) { int i; for (i = 0; i < table->size; i++) diff --git a/drivers/gpu/drm/i915/intel_overlay.c b/drivers/gpu/drm/i915/intel_overlay.c index 20ea7c99d13a..c153be043078 100644 --- a/drivers/gpu/drm/i915/intel_overlay.c +++ b/drivers/gpu/drm/i915/intel_overlay.c @@ -541,7 +541,7 @@ static u32 calc_swidthsw(struct drm_i915_private *dev_priv, u32 offset, u32 widt { u32 sw; - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) sw = ALIGN((offset & 31) + width, 32); else sw = ALIGN((offset & 63) + width, 64); @@ -778,7 +778,7 @@ static int intel_overlay_do_put_image(struct intel_overlay *overlay, u32 oconfig; oconfig = OCONF_CC_OUT_8BIT; - if (IS_GEN4(dev_priv)) + if (IS_GEN(dev_priv, 4)) oconfig |= OCONF_CSC_MODE_BT709; oconfig |= pipe == 0 ? OCONF_PIPE_A : OCONF_PIPE_B; @@ -1012,7 +1012,7 @@ static int check_overlay_src(struct drm_i915_private *dev_priv, if (rec->stride_Y & stride_mask || rec->stride_UV & stride_mask) return -EINVAL; - if (IS_GEN4(dev_priv) && rec->stride_Y < 512) + if (IS_GEN(dev_priv, 4) && rec->stride_Y < 512) return -EINVAL; tmp = (rec->flags & I915_OVERLAY_TYPE_MASK) == I915_OVERLAY_YUV_PLANAR ? @@ -1246,7 +1246,7 @@ int intel_overlay_attrs_ioctl(struct drm_device *dev, void *data, attrs->contrast = overlay->contrast; attrs->saturation = overlay->saturation; - if (!IS_GEN2(dev_priv)) { + if (!IS_GEN(dev_priv, 2)) { attrs->gamma0 = I915_READ(OGAMC0); attrs->gamma1 = I915_READ(OGAMC1); attrs->gamma2 = I915_READ(OGAMC2); @@ -1270,7 +1270,7 @@ int intel_overlay_attrs_ioctl(struct drm_device *dev, void *data, update_reg_attrs(overlay, overlay->regs); if (attrs->flags & I915_OVERLAY_UPDATE_GAMMA) { - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) goto out_unlock; if (overlay->active) { diff --git a/drivers/gpu/drm/i915/intel_panel.c b/drivers/gpu/drm/i915/intel_panel.c index e6cd7b55c018..ee3e0842d542 100644 --- a/drivers/gpu/drm/i915/intel_panel.c +++ b/drivers/gpu/drm/i915/intel_panel.c @@ -563,7 +563,7 @@ static void i9xx_set_backlight(const struct drm_connector_state *conn_state, u32 pci_write_config_byte(dev_priv->drm.pdev, LBPC, lbpc); } - if (IS_GEN4(dev_priv)) { + if (IS_GEN(dev_priv, 4)) { mask = BACKLIGHT_DUTY_CYCLE_MASK; } else { level <<= 1; @@ -929,7 +929,7 @@ static void i9xx_enable_backlight(const struct intel_crtc_state *crtc_state, * 855gm only, but checking for gen2 is safe, as 855gm is the only gen2 * that has backlight. */ - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) I915_WRITE(BLC_HIST_CTL, BLM_HISTOGRAM_ENABLE); } @@ -1557,7 +1557,7 @@ static int i9xx_setup_backlight(struct intel_connector *connector, enum pipe unu ctl = I915_READ(BLC_PWM_CTL); - if (IS_GEN2(dev_priv) || IS_I915GM(dev_priv) || IS_I945GM(dev_priv)) + if (IS_GEN(dev_priv, 2) || IS_I915GM(dev_priv) || IS_I945GM(dev_priv)) panel->backlight.combination_mode = ctl & BLM_LEGACY_MODE; if (IS_PINEVIEW(dev_priv)) @@ -1886,7 +1886,7 @@ intel_panel_init_backlight_funcs(struct intel_panel *panel) panel->backlight.get = vlv_get_backlight; panel->backlight.hz_to_pwm = vlv_hz_to_pwm; } - } else if (IS_GEN4(dev_priv)) { + } else if (IS_GEN(dev_priv, 4)) { panel->backlight.setup = i965_setup_backlight; panel->backlight.enable = i965_enable_backlight; panel->backlight.disable = i965_disable_backlight; diff --git a/drivers/gpu/drm/i915/intel_pipe_crc.c b/drivers/gpu/drm/i915/intel_pipe_crc.c index f3c9010e332a..9e870caf8104 100644 --- a/drivers/gpu/drm/i915/intel_pipe_crc.c +++ b/drivers/gpu/drm/i915/intel_pipe_crc.c @@ -427,13 +427,13 @@ static int get_new_crc_ctl_reg(struct drm_i915_private *dev_priv, enum intel_pipe_crc_source *source, u32 *val, bool set_wa) { - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) return i8xx_pipe_crc_ctl_reg(source, val); else if (INTEL_GEN(dev_priv) < 5) return i9xx_pipe_crc_ctl_reg(dev_priv, pipe, source, val); else if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) return vlv_pipe_crc_ctl_reg(dev_priv, pipe, source, val); - else if (IS_GEN5(dev_priv) || IS_GEN6(dev_priv)) + else if (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6)) return ilk_pipe_crc_ctl_reg(source, val); else return ivb_pipe_crc_ctl_reg(dev_priv, pipe, source, val, set_wa); @@ -544,13 +544,13 @@ static int intel_is_valid_crc_source(struct drm_i915_private *dev_priv, const enum intel_pipe_crc_source source) { - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) return i8xx_crc_source_valid(dev_priv, source); else if (INTEL_GEN(dev_priv) < 5) return i9xx_crc_source_valid(dev_priv, source); else if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) return vlv_crc_source_valid(dev_priv, source); - else if (IS_GEN5(dev_priv) || IS_GEN6(dev_priv)) + else if (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6)) return ilk_crc_source_valid(dev_priv, source); else return ivb_crc_source_valid(dev_priv, source); diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index a6c7c11d2c0e..b11fac679e10 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -2271,7 +2271,7 @@ static void i9xx_update_wm(struct intel_crtc *unused_crtc) if (IS_I945GM(dev_priv)) wm_info = &i945_wm_info; - else if (!IS_GEN2(dev_priv)) + else if (!IS_GEN(dev_priv, 2)) wm_info = &i915_wm_info; else wm_info = &i830_a_wm_info; @@ -2285,7 +2285,7 @@ static void i9xx_update_wm(struct intel_crtc *unused_crtc) crtc->base.primary->state->fb; int cpp; - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) cpp = 4; else cpp = fb->format->cpp[0]; @@ -2300,7 +2300,7 @@ static void i9xx_update_wm(struct intel_crtc *unused_crtc) planea_wm = wm_info->max_wm; } - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) wm_info = &i830_bc_wm_info; fifo_size = dev_priv->display.get_fifo_size(dev_priv, PLANE_B); @@ -2312,7 +2312,7 @@ static void i9xx_update_wm(struct intel_crtc *unused_crtc) crtc->base.primary->state->fb; int cpp; - if (IS_GEN2(dev_priv)) + if (IS_GEN(dev_priv, 2)) cpp = 4; else cpp = fb->format->cpp[0]; @@ -2923,7 +2923,7 @@ static void intel_fixup_spr_wm_latency(struct drm_i915_private *dev_priv, uint16_t wm[5]) { /* ILK sprite LP0 latency is 1300 ns */ - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) wm[0] = 13; } @@ -2931,7 +2931,7 @@ static void intel_fixup_cur_wm_latency(struct drm_i915_private *dev_priv, uint16_t wm[5]) { /* ILK cursor LP0 latency is 1300 ns */ - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) wm[0] = 13; } @@ -3058,7 +3058,7 @@ static void ilk_setup_wm_latency(struct drm_i915_private *dev_priv) intel_print_wm_latency(dev_priv, "Sprite", dev_priv->wm.spr_latency); intel_print_wm_latency(dev_priv, "Cursor", dev_priv->wm.cur_latency); - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { snb_wm_latency_quirk(dev_priv); snb_wm_lp3_irq_quirk(dev_priv); } @@ -3314,7 +3314,7 @@ static void ilk_wm_merge(struct drm_i915_private *dev_priv, * What we should check here is whether FBC can be * enabled sometime later. */ - if (IS_GEN5(dev_priv) && !merged->fbc_wm_enabled && + if (IS_GEN(dev_priv, 5) && !merged->fbc_wm_enabled && intel_fbc_is_active(dev_priv)) { for (level = 2; level <= max_level; level++) { struct intel_wm_level *wm = &merged->wm[level]; @@ -3751,9 +3751,9 @@ bool intel_can_enable_sagv(struct drm_atomic_state *state) if (!intel_has_sagv(dev_priv)) return false; - if (IS_GEN9(dev_priv)) + if (IS_GEN(dev_priv, 9)) sagv_block_time_us = 30; - else if (IS_GEN10(dev_priv)) + else if (IS_GEN(dev_priv, 10)) sagv_block_time_us = 20; else sagv_block_time_us = 10; @@ -4657,7 +4657,7 @@ skl_compute_plane_wm_params(const struct intel_crtc_state *cstate, wp->plane_blocks_per_line = div_fixed16(interm_pbpl, wp->y_min_scanlines); - } else if (wp->x_tiled && IS_GEN9(dev_priv)) { + } else if (wp->x_tiled && IS_GEN(dev_priv, 9)) { interm_pbpl = DIV_ROUND_UP(wp->plane_bytes_per_line, wp->dbuf_block_size); wp->plane_blocks_per_line = u32_to_fixed16(interm_pbpl); @@ -4716,7 +4716,7 @@ static void skl_compute_plane_wm(const struct intel_crtc_state *cstate, (wp->plane_bytes_per_line / wp->dbuf_block_size < 1)) { selected_result = method2; } else if (latency >= wp->linetime_us) { - if (IS_GEN9(dev_priv) && + if (IS_GEN(dev_priv, 9) && !IS_GEMINILAKE(dev_priv)) selected_result = min_fixed16(method1, method2); else @@ -6908,7 +6908,7 @@ static void gen9_enable_rps(struct drm_i915_private *dev_priv) intel_uncore_forcewake_get(dev_priv, FORCEWAKE_ALL); /* Program defaults and thresholds for RPS */ - if (IS_GEN9(dev_priv)) + if (IS_GEN(dev_priv, 9)) I915_WRITE(GEN6_RC_VIDEO_FREQ, GEN9_FREQUENCY(dev_priv->gt_pm.rps.rp1_freq)); @@ -7144,9 +7144,9 @@ static void gen6_enable_rc6(struct drm_i915_private *dev_priv) rc6vids = 0; ret = sandybridge_pcode_read(dev_priv, GEN6_PCODE_READ_RC6VIDS, &rc6vids); - if (IS_GEN6(dev_priv) && ret) { + if (IS_GEN(dev_priv, 6) && ret) { DRM_DEBUG_DRIVER("Couldn't check for BIOS workaround\n"); - } else if (IS_GEN6(dev_priv) && (GEN6_DECODE_RC6_VID(rc6vids & 0xff) < 450)) { + } else if (IS_GEN(dev_priv, 6) && (GEN6_DECODE_RC6_VID(rc6vids & 0xff) < 450)) { DRM_DEBUG_DRIVER("You should update your BIOS. Correcting minimum rc6 voltage (%dmV->%dmV)\n", GEN6_DECODE_RC6_VID(rc6vids & 0xff), 450); rc6vids &= 0xffff00; @@ -7846,7 +7846,7 @@ unsigned long i915_chipset_val(struct drm_i915_private *dev_priv) { unsigned long val; - if (!IS_GEN5(dev_priv)) + if (!IS_GEN(dev_priv, 5)) return 0; spin_lock_irq(&mchdev_lock); @@ -7930,7 +7930,7 @@ static void __i915_update_gfx_val(struct drm_i915_private *dev_priv) void i915_update_gfx_val(struct drm_i915_private *dev_priv) { - if (!IS_GEN5(dev_priv)) + if (!IS_GEN(dev_priv, 5)) return; spin_lock_irq(&mchdev_lock); @@ -7981,7 +7981,7 @@ unsigned long i915_gfx_val(struct drm_i915_private *dev_priv) { unsigned long val; - if (!IS_GEN5(dev_priv)) + if (!IS_GEN(dev_priv, 5)) return 0; spin_lock_irq(&mchdev_lock); @@ -8269,7 +8269,7 @@ void intel_init_gt_powersave(struct drm_i915_private *dev_priv) intel_freq_opcode(dev_priv, 450)); /* After setting max-softlimit, find the overclock max freq */ - if (IS_GEN6(dev_priv) || + if (IS_GEN(dev_priv, 6) || IS_IVYBRIDGE(dev_priv) || IS_HASWELL(dev_priv)) { u32 params = 0; @@ -9339,9 +9339,9 @@ void intel_init_clock_gating_hooks(struct drm_i915_private *dev_priv) dev_priv->display.init_clock_gating = ivb_init_clock_gating; else if (IS_VALLEYVIEW(dev_priv)) dev_priv->display.init_clock_gating = vlv_init_clock_gating; - else if (IS_GEN6(dev_priv)) + else if (IS_GEN(dev_priv, 6)) dev_priv->display.init_clock_gating = gen6_init_clock_gating; - else if (IS_GEN5(dev_priv)) + else if (IS_GEN(dev_priv, 5)) dev_priv->display.init_clock_gating = ilk_init_clock_gating; else if (IS_G4X(dev_priv)) dev_priv->display.init_clock_gating = g4x_init_clock_gating; @@ -9349,11 +9349,11 @@ void intel_init_clock_gating_hooks(struct drm_i915_private *dev_priv) dev_priv->display.init_clock_gating = i965gm_init_clock_gating; else if (IS_I965G(dev_priv)) dev_priv->display.init_clock_gating = i965g_init_clock_gating; - else if (IS_GEN3(dev_priv)) + else if (IS_GEN(dev_priv, 3)) dev_priv->display.init_clock_gating = gen3_init_clock_gating; else if (IS_I85X(dev_priv) || IS_I865G(dev_priv)) dev_priv->display.init_clock_gating = i85x_init_clock_gating; - else if (IS_GEN2(dev_priv)) + else if (IS_GEN(dev_priv, 2)) dev_priv->display.init_clock_gating = i830_init_clock_gating; else { MISSING_CASE(INTEL_DEVID(dev_priv)); @@ -9367,7 +9367,7 @@ void intel_init_pm(struct drm_i915_private *dev_priv) /* For cxsr */ if (IS_PINEVIEW(dev_priv)) i915_pineview_get_mem_freq(dev_priv); - else if (IS_GEN5(dev_priv)) + else if (IS_GEN(dev_priv, 5)) i915_ironlake_get_mem_freq(dev_priv); /* For FIFO watermark updates */ @@ -9379,9 +9379,9 @@ void intel_init_pm(struct drm_i915_private *dev_priv) } else if (HAS_PCH_SPLIT(dev_priv)) { ilk_setup_wm_latency(dev_priv); - if ((IS_GEN5(dev_priv) && dev_priv->wm.pri_latency[1] && + if ((IS_GEN(dev_priv, 5) && dev_priv->wm.pri_latency[1] && dev_priv->wm.spr_latency[1] && dev_priv->wm.cur_latency[1]) || - (!IS_GEN5(dev_priv) && dev_priv->wm.pri_latency[0] && + (!IS_GEN(dev_priv, 5) && dev_priv->wm.pri_latency[0] && dev_priv->wm.spr_latency[0] && dev_priv->wm.cur_latency[0])) { dev_priv->display.compute_pipe_wm = ilk_compute_pipe_wm; dev_priv->display.compute_intermediate_wm = @@ -9422,12 +9422,12 @@ void intel_init_pm(struct drm_i915_private *dev_priv) dev_priv->display.update_wm = NULL; } else dev_priv->display.update_wm = pineview_update_wm; - } else if (IS_GEN4(dev_priv)) { + } else if (IS_GEN(dev_priv, 4)) { dev_priv->display.update_wm = i965_update_wm; - } else if (IS_GEN3(dev_priv)) { + } else if (IS_GEN(dev_priv, 3)) { dev_priv->display.update_wm = i9xx_update_wm; dev_priv->display.get_fifo_size = i9xx_get_fifo_size; - } else if (IS_GEN2(dev_priv)) { + } else if (IS_GEN(dev_priv, 2)) { if (INTEL_INFO(dev_priv)->num_pipes == 1) { dev_priv->display.update_wm = i845_update_wm; dev_priv->display.get_fifo_size = i845_get_fifo_size; diff --git a/drivers/gpu/drm/i915/intel_psr.c b/drivers/gpu/drm/i915/intel_psr.c index 4c4dd1c310ce..dce39f06b682 100644 --- a/drivers/gpu/drm/i915/intel_psr.c +++ b/drivers/gpu/drm/i915/intel_psr.c @@ -552,7 +552,7 @@ static bool intel_psr2_config_valid(struct intel_dp *intel_dp, if (INTEL_GEN(dev_priv) >= 10 || IS_GEMINILAKE(dev_priv)) { psr_max_h = 4096; psr_max_v = 2304; - } else if (IS_GEN9(dev_priv)) { + } else if (IS_GEN(dev_priv, 9)) { psr_max_h = 3640; psr_max_v = 2304; } @@ -686,7 +686,7 @@ static void intel_psr_enable_source(struct intel_dp *intel_dp, if (IS_HASWELL(dev_priv) || IS_BROADWELL(dev_priv)) hsw_psr_setup_aux(intel_dp); - if (dev_priv->psr.psr2_enabled && (IS_GEN9(dev_priv) && + if (dev_priv->psr.psr2_enabled && (IS_GEN(dev_priv, 9) && !IS_GEMINILAKE(dev_priv))) { i915_reg_t reg = gen9_chicken_trans_reg(dev_priv, cpu_transcoder); diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c index 720c11e0acd1..fdeca2b877c9 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.c +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c @@ -133,7 +133,7 @@ gen4_render_ring_flush(struct i915_request *rq, u32 mode) cmd = MI_FLUSH; if (mode & EMIT_INVALIDATE) { cmd |= MI_EXE_FLUSH; - if (IS_G4X(rq->i915) || IS_GEN5(rq->i915)) + if (IS_G4X(rq->i915) || IS_GEN(rq->i915, 5)) cmd |= MI_INVALIDATE_ISP; } @@ -401,7 +401,7 @@ static void intel_ring_setup_status_page(struct intel_engine_cs *engine) /* The ring status page addresses are no longer next to the rest of * the ring registers as of gen7. */ - if (IS_GEN7(dev_priv)) { + if (IS_GEN(dev_priv, 7)) { switch (engine->id) { /* * No more rings exist on Gen7. Default case is only to shut up @@ -422,7 +422,7 @@ static void intel_ring_setup_status_page(struct intel_engine_cs *engine) mmio = VEBOX_HWS_PGA_GEN7; break; } - } else if (IS_GEN6(dev_priv)) { + } else if (IS_GEN(dev_priv, 6)) { mmio = RING_HWS_PGA_GEN6(engine->mmio_base); } else { mmio = RING_HWS_PGA(engine->mmio_base); @@ -693,17 +693,17 @@ static int init_render_ring(struct intel_engine_cs *engine) /* Required for the hardware to program scanline values for waiting */ /* WaEnableFlushTlbInvalidationMode:snb */ - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) I915_WRITE(GFX_MODE, _MASKED_BIT_ENABLE(GFX_TLB_INVALIDATE_EXPLICIT)); /* WaBCSVCSTlbInvalidationMode:ivb,vlv,hsw */ - if (IS_GEN7(dev_priv)) + if (IS_GEN(dev_priv, 7)) I915_WRITE(GFX_MODE_GEN7, _MASKED_BIT_ENABLE(GFX_TLB_INVALIDATE_EXPLICIT) | _MASKED_BIT_ENABLE(GFX_REPLAY_MODE)); - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { /* From the Sandybridge PRM, volume 1 part 3, page 24: * "If this bit is set, STCunit will have LRA as replacement * policy. [...] This bit must be reset. LRA replacement @@ -1582,7 +1582,7 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) 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_GEN7(i915)) ? + (HAS_LEGACY_SEMAPHORES(i915) && IS_GEN(i915, 7)) ? INTEL_INFO(i915)->num_rings - 1 : 0; bool force_restore = false; @@ -1597,7 +1597,7 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) flags |= MI_SAVE_EXT_STATE_EN | MI_RESTORE_EXT_STATE_EN; len = 4; - if (IS_GEN7(i915)) + if (IS_GEN(i915, 7)) len += 2 + (num_rings ? 4*num_rings + 6 : 0); if (flags & MI_FORCE_RESTORE) { GEM_BUG_ON(flags & MI_RESTORE_INHIBIT); @@ -1611,7 +1611,7 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) return PTR_ERR(cs); /* WaProgramMiArbOnOffAroundMiSetContext:ivb,vlv,hsw,bdw,chv */ - if (IS_GEN7(i915)) { + if (IS_GEN(i915, 7)) { *cs++ = MI_ARB_ON_OFF | MI_ARB_DISABLE; if (num_rings) { struct intel_engine_cs *signaller; @@ -1658,7 +1658,7 @@ static inline int mi_set_context(struct i915_request *rq, u32 flags) */ *cs++ = MI_NOOP; - if (IS_GEN7(i915)) { + if (IS_GEN(i915, 7)) { if (num_rings) { struct intel_engine_cs *signaller; i915_reg_t last_reg = {}; /* keep gcc quiet */ @@ -2283,9 +2283,9 @@ int intel_init_render_ring_buffer(struct intel_engine_cs *engine) if (INTEL_GEN(dev_priv) >= 6) { engine->init_context = intel_rcs_ctx_init; engine->emit_flush = gen7_render_ring_flush; - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) engine->emit_flush = gen6_render_ring_flush; - } else if (IS_GEN5(dev_priv)) { + } else if (IS_GEN(dev_priv, 5)) { engine->emit_flush = gen4_render_ring_flush; } else { if (INTEL_GEN(dev_priv) < 4) @@ -2315,13 +2315,13 @@ int intel_init_bsd_ring_buffer(struct intel_engine_cs *engine) if (INTEL_GEN(dev_priv) >= 6) { /* gen6 bsd needs a special wa for tail updates */ - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) engine->set_default_submission = gen6_bsd_set_default_submission; engine->emit_flush = gen6_bsd_ring_flush; engine->irq_enable_mask = GT_BSD_USER_INTERRUPT; } else { engine->emit_flush = bsd_ring_flush; - if (IS_GEN5(dev_priv)) + if (IS_GEN(dev_priv, 5)) engine->irq_enable_mask = ILK_BSD_USER_INTERRUPT; else engine->irq_enable_mask = I915_BSD_USER_INTERRUPT; diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.h b/drivers/gpu/drm/i915/intel_ringbuffer.h index 72edaa7ff411..1ae74e579386 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.h +++ b/drivers/gpu/drm/i915/intel_ringbuffer.h @@ -94,11 +94,11 @@ hangcheck_action_to_str(const enum intel_engine_hangcheck_action a) #define I915_MAX_SUBSLICES 8 #define instdone_slice_mask(dev_priv__) \ - (IS_GEN7(dev_priv__) ? \ + (IS_GEN(dev_priv__, 7) ? \ 1 : INTEL_INFO(dev_priv__)->sseu.slice_mask) #define instdone_subslice_mask(dev_priv__) \ - (IS_GEN7(dev_priv__) ? \ + (IS_GEN(dev_priv__, 7) ? \ 1 : INTEL_INFO(dev_priv__)->sseu.subslice_mask[0]) #define for_each_instdone_slice_subslice(dev_priv__, slice__, subslice__) \ diff --git a/drivers/gpu/drm/i915/intel_runtime_pm.c b/drivers/gpu/drm/i915/intel_runtime_pm.c index 4350a5270423..9e9501f82f06 100644 --- a/drivers/gpu/drm/i915/intel_runtime_pm.c +++ b/drivers/gpu/drm/i915/intel_runtime_pm.c @@ -509,7 +509,7 @@ static bool hsw_power_well_enabled(struct drm_i915_private *dev_priv, * BIOS's own request bits, which are forced-on for these power wells * when exiting DC5/6. */ - if (IS_GEN9(dev_priv) && !IS_GEN9_LP(dev_priv) && + if (IS_GEN(dev_priv, 9) && !IS_GEN9_LP(dev_priv) && (id == SKL_DISP_PW_1 || id == SKL_DISP_PW_MISC_IO)) val |= I915_READ(regs->bios); @@ -3058,7 +3058,7 @@ static uint32_t get_allowed_dc_mask(const struct drm_i915_private *dev_priv, * suspend/resume, so allow it unconditionally. */ mask = DC_STATE_EN_DC9; - } else if (IS_GEN10(dev_priv) || IS_GEN9_BC(dev_priv)) { + } else if (IS_GEN(dev_priv, 10) || IS_GEN9_BC(dev_priv)) { max_dc = 2; mask = 0; } else if (IS_GEN9_LP(dev_priv)) { diff --git a/drivers/gpu/drm/i915/intel_sprite.c b/drivers/gpu/drm/i915/intel_sprite.c index d2e003d8f3db..f70d2c607902 100644 --- a/drivers/gpu/drm/i915/intel_sprite.c +++ b/drivers/gpu/drm/i915/intel_sprite.c @@ -1087,7 +1087,7 @@ static u32 g4x_sprite_ctl(const struct intel_crtc_state *crtc_state, dvscntr = DVS_ENABLE | DVS_GAMMA_ENABLE; - if (IS_GEN6(dev_priv)) + if (IS_GEN(dev_priv, 6)) dvscntr |= DVS_TRICKLE_FEED_DISABLE; switch (fb->format->format) { @@ -1983,7 +1983,7 @@ static bool skl_plane_has_planar(struct drm_i915_private *dev_priv, if (IS_SKYLAKE(dev_priv) || IS_BROXTON(dev_priv)) return false; - if (IS_GEN9(dev_priv) && !IS_GEMINILAKE(dev_priv) && pipe == PIPE_C) + if (IS_GEN(dev_priv, 9) && !IS_GEMINILAKE(dev_priv) && pipe == PIPE_C) return false; if (plane_id != PLANE_PRIMARY && plane_id != PLANE_SPRITE0) @@ -2163,7 +2163,7 @@ intel_sprite_plane_create(struct drm_i915_private *dev_priv, plane->check_plane = g4x_sprite_check; modifiers = i9xx_plane_format_modifiers; - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { formats = snb_plane_formats; num_formats = ARRAY_SIZE(snb_plane_formats); diff --git a/drivers/gpu/drm/i915/intel_uc.c b/drivers/gpu/drm/i915/intel_uc.c index b34c318b238d..447b1de77cc7 100644 --- a/drivers/gpu/drm/i915/intel_uc.c +++ b/drivers/gpu/drm/i915/intel_uc.c @@ -354,7 +354,7 @@ int intel_uc_init_hw(struct drm_i915_private *i915) /* WaEnableuKernelHeaderValidFix:skl */ /* WaEnableGuCBootHashCheckNotSet:skl,bxt,kbl */ - if (IS_GEN9(i915)) + if (IS_GEN(i915, 9)) attempts = 3; else attempts = 1; diff --git a/drivers/gpu/drm/i915/intel_uncore.c b/drivers/gpu/drm/i915/intel_uncore.c index 631b4165fe00..c6eb053a8fad 100644 --- a/drivers/gpu/drm/i915/intel_uncore.c +++ b/drivers/gpu/drm/i915/intel_uncore.c @@ -528,7 +528,7 @@ check_for_unclaimed_mmio(struct drm_i915_private *dev_priv) if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) ret |= vlv_check_for_unclaimed_mmio(dev_priv); - if (IS_GEN6(dev_priv) || IS_GEN7(dev_priv)) + if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) ret |= gen6_check_for_fifo_debug(dev_priv); return ret; @@ -556,7 +556,7 @@ static void __intel_uncore_early_sanitize(struct drm_i915_private *dev_priv, dev_priv->uncore.funcs.force_wake_get(dev_priv, restore_forcewake); - if (IS_GEN6(dev_priv) || IS_GEN7(dev_priv)) + if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) dev_priv->uncore.fifo_count = fifo_free_entries(dev_priv); spin_unlock_irq(&dev_priv->uncore.lock); @@ -1398,7 +1398,7 @@ static void intel_uncore_fw_domains_init(struct drm_i915_private *dev_priv) if (INTEL_GEN(dev_priv) <= 5 || intel_vgpu_active(dev_priv)) return; - if (IS_GEN6(dev_priv)) { + if (IS_GEN(dev_priv, 6)) { dev_priv->uncore.fw_reset = 0; dev_priv->uncore.fw_set = FORCEWAKE_KERNEL; dev_priv->uncore.fw_clear = 0; @@ -1437,7 +1437,7 @@ static void intel_uncore_fw_domains_init(struct drm_i915_private *dev_priv) FORCEWAKE_MEDIA_VEBOX_GEN11(i), FORCEWAKE_ACK_MEDIA_VEBOX_GEN11(i)); } - } else if (IS_GEN10(dev_priv) || IS_GEN9(dev_priv)) { + } else if (IS_GEN(dev_priv, 10) || IS_GEN(dev_priv, 9)) { dev_priv->uncore.funcs.force_wake_get = fw_domains_get_with_fallback; dev_priv->uncore.funcs.force_wake_put = fw_domains_put; @@ -1503,7 +1503,7 @@ static void intel_uncore_fw_domains_init(struct drm_i915_private *dev_priv) fw_domain_init(dev_priv, FW_DOMAIN_ID_RENDER, FORCEWAKE, FORCEWAKE_ACK); } - } else if (IS_GEN6(dev_priv)) { + } else if (IS_GEN(dev_priv, 6)) { dev_priv->uncore.funcs.force_wake_get = fw_domains_get_with_thread_status; dev_priv->uncore.funcs.force_wake_put = fw_domains_put; @@ -1570,7 +1570,7 @@ void intel_uncore_init(struct drm_i915_private *dev_priv) if (IS_GEN_RANGE(dev_priv, 2, 4) || intel_vgpu_active(dev_priv)) { ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, gen2); ASSIGN_READ_MMIO_VFUNCS(dev_priv, gen2); - } else if (IS_GEN5(dev_priv)) { + } else if (IS_GEN(dev_priv, 5)) { ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, gen5); ASSIGN_READ_MMIO_VFUNCS(dev_priv, gen5); } else if (IS_GEN_RANGE(dev_priv, 6, 7)) { @@ -1582,7 +1582,7 @@ void intel_uncore_init(struct drm_i915_private *dev_priv) } else { ASSIGN_READ_MMIO_VFUNCS(dev_priv, gen6); } - } else if (IS_GEN8(dev_priv)) { + } else if (IS_GEN(dev_priv, 8)) { if (IS_CHERRYVIEW(dev_priv)) { ASSIGN_FW_DOMAINS_TABLE(__chv_fw_ranges); ASSIGN_WRITE_MMIO_VFUNCS(dev_priv, fwtable); @@ -2173,7 +2173,7 @@ static reset_func intel_get_gpu_reset(struct drm_i915_private *dev_priv) return gen8_reset_engines; else if (INTEL_GEN(dev_priv) >= 6) return gen6_reset_engines; - else if (IS_GEN5(dev_priv)) + else if (IS_GEN(dev_priv, 5)) return ironlake_do_reset; else if (IS_G4X(dev_priv)) return g4x_do_reset; @@ -2341,7 +2341,7 @@ intel_uncore_forcewake_for_write(struct drm_i915_private *dev_priv, fw_domains = __gen11_fwtable_reg_write_fw_domains(offset); } else if (HAS_FWTABLE(dev_priv) && !IS_VALLEYVIEW(dev_priv)) { fw_domains = __fwtable_reg_write_fw_domains(offset); - } else if (IS_GEN8(dev_priv)) { + } else if (IS_GEN(dev_priv, 8)) { fw_domains = __gen8_reg_write_fw_domains(offset); } else if (IS_GEN_RANGE(dev_priv, 6, 7)) { fw_domains = FORCEWAKE_RENDER; diff --git a/drivers/gpu/drm/i915/intel_wopcm.c b/drivers/gpu/drm/i915/intel_wopcm.c index 92cb82dd0c07..630c887682e8 100644 --- a/drivers/gpu/drm/i915/intel_wopcm.c +++ b/drivers/gpu/drm/i915/intel_wopcm.c @@ -130,11 +130,11 @@ static inline int check_hw_restriction(struct drm_i915_private *i915, { int err = 0; - if (IS_GEN9(i915)) + if (IS_GEN(i915, 9)) err = gen9_check_dword_gap(guc_wopcm_base, guc_wopcm_size); if (!err && - (IS_GEN9(i915) || IS_CNL_REVID(i915, CNL_REVID_A0, CNL_REVID_A0))) + (IS_GEN(i915, 9) || IS_CNL_REVID(i915, CNL_REVID_A0, CNL_REVID_A0))) err = gen9_check_huc_fw_fits(guc_wopcm_size, huc_fw_size); return err; diff --git a/drivers/gpu/drm/i915/intel_workarounds.c b/drivers/gpu/drm/i915/intel_workarounds.c index 6bcac78a9c36..7a8618065491 100644 --- a/drivers/gpu/drm/i915/intel_workarounds.c +++ b/drivers/gpu/drm/i915/intel_workarounds.c @@ -1186,7 +1186,7 @@ static void rcs_engine_wa_init(struct intel_engine_cs *engine) GEN7_DISABLE_SAMPLER_PREFETCH); } - if (IS_GEN9(i915) || IS_CANNONLAKE(i915)) { + if (IS_GEN(i915, 9) || IS_CANNONLAKE(i915)) { /* WaEnablePreemptionGranularityControlByUMD:skl,bxt,kbl,cfl,cnl */ wa_masked_en(wal, GEN7_FF_SLICE_CS_CHICKEN1, @@ -1207,7 +1207,7 @@ static void rcs_engine_wa_init(struct intel_engine_cs *engine) GEN9_POOLED_EU_LOAD_BALANCING_FIX_DISABLE); } - if (IS_GEN9(i915)) { + if (IS_GEN(i915, 9)) { /* WaContextSwitchWithConcurrentTLBInvalidate:skl,bxt,kbl,glk,cfl */ wa_masked_en(wal, GEN9_CSFE_CHICKEN1_RCS, From f3ce44a09a15848c7b3e07c9a937e0562f681489 Mon Sep 17 00:00:00 2001 From: Lucas De Marchi Date: Wed, 12 Dec 2018 10:10:44 -0800 Subject: [PATCH 041/118] drm/i915: merge gen checks to use range Instead of using IS_GEN() for consecutive gen checks, let's pass the range to IS_GEN_RANGE(). By code inspection these were the ranges deemed necessary for spatch: @@ expression e; @@ ( - IS_GEN(e, 3) || IS_GEN(e, 2) + IS_GEN_RANGE(e, 2, 3) | - IS_GEN(e, 3) || IS_GEN(e, 4) + IS_GEN_RANGE(e, 3, 4) | - IS_GEN(e, 5) || IS_GEN(e, 6) + IS_GEN_RANGE(e, 5, 6) | - IS_GEN(e, 6) || IS_GEN(e, 7) + IS_GEN_RANGE(e, 6, 7) | - IS_GEN(e, 7) || IS_GEN(e, 8) + IS_GEN_RANGE(e, 7, 8) | - IS_GEN(e, 8) || IS_GEN(e, 9) + IS_GEN_RANGE(e, 8, 9) | - IS_GEN(e, 10) || IS_GEN(e, 9) + IS_GEN_RANGE(e, 9, 10) | - IS_GEN(e, 9) || IS_GEN(e, 10) + IS_GEN_RANGE(e, 9, 10) ) After conversion, checking we don't have any missing IS_GEN_RANGE() || IS_GEN() was also done. Signed-off-by: Lucas De Marchi Reviewed-by: Jani Nikula Signed-off-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181212181044.15886-3-lucas.demarchi@intel.com --- drivers/gpu/drm/i915/i915_debugfs.c | 6 +++--- drivers/gpu/drm/i915/i915_gpu_error.c | 2 +- drivers/gpu/drm/i915/i915_perf.c | 2 +- drivers/gpu/drm/i915/intel_crt.c | 2 +- drivers/gpu/drm/i915/intel_device_info.c | 2 +- drivers/gpu/drm/i915/intel_display.c | 2 +- drivers/gpu/drm/i915/intel_engine_cs.c | 2 +- drivers/gpu/drm/i915/intel_fifo_underrun.c | 2 +- drivers/gpu/drm/i915/intel_pipe_crc.c | 4 ++-- drivers/gpu/drm/i915/intel_uncore.c | 6 +++--- 10 files changed, 15 insertions(+), 15 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 2b52c91113b3..ed44e30f875e 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -2040,7 +2040,7 @@ static int i915_swizzle_info(struct seq_file *m, void *data) seq_printf(m, "bit6 swizzle for Y-tiling = %s\n", swizzle_string(dev_priv->mm.bit_6_swizzle_y)); - if (IS_GEN(dev_priv, 3) || IS_GEN(dev_priv, 4)) { + if (IS_GEN_RANGE(dev_priv, 3, 4)) { seq_printf(m, "DDC = 0x%08x\n", I915_READ(DCC)); seq_printf(m, "DDC2 = 0x%08x\n", @@ -4274,7 +4274,7 @@ i915_cache_sharing_get(void *data, u64 *val) struct drm_i915_private *dev_priv = data; u32 snpcr; - if (!(IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7))) + if (!(IS_GEN_RANGE(dev_priv, 6, 7))) return -ENODEV; intel_runtime_pm_get(dev_priv); @@ -4294,7 +4294,7 @@ i915_cache_sharing_set(void *data, u64 val) struct drm_i915_private *dev_priv = data; u32 snpcr; - if (!(IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7))) + if (!(IS_GEN_RANGE(dev_priv, 6, 7))) return -ENODEV; if (val > 3) diff --git a/drivers/gpu/drm/i915/i915_gpu_error.c b/drivers/gpu/drm/i915/i915_gpu_error.c index 4477631d2636..63df41d93379 100644 --- a/drivers/gpu/drm/i915/i915_gpu_error.c +++ b/drivers/gpu/drm/i915/i915_gpu_error.c @@ -1753,7 +1753,7 @@ static void capture_reg_state(struct i915_gpu_state *error) error->ccid = I915_READ(CCID); /* 3: Feature specific registers */ - if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) { + if (IS_GEN_RANGE(dev_priv, 6, 7)) { error->gam_ecochk = I915_READ(GAM_ECOCHK); error->gac_eco = I915_READ(GAC_ECO_BITS); } diff --git a/drivers/gpu/drm/i915/i915_perf.c b/drivers/gpu/drm/i915/i915_perf.c index 6c7992320443..4288c0e02f0c 100644 --- a/drivers/gpu/drm/i915/i915_perf.c +++ b/drivers/gpu/drm/i915/i915_perf.c @@ -3415,7 +3415,7 @@ void i915_perf_init(struct drm_i915_private *dev_priv) dev_priv->perf.oa.ops.read = gen8_oa_read; dev_priv->perf.oa.ops.oa_hw_tail_read = gen8_oa_hw_tail_read; - if (IS_GEN(dev_priv, 8) || IS_GEN(dev_priv, 9)) { + if (IS_GEN_RANGE(dev_priv, 8, 9)) { dev_priv->perf.oa.ops.is_valid_b_counter_reg = gen7_is_valid_b_counter_addr; dev_priv->perf.oa.ops.is_valid_mux_reg = diff --git a/drivers/gpu/drm/i915/intel_crt.c b/drivers/gpu/drm/i915/intel_crt.c index bf4fd739b68c..0a41e58d61de 100644 --- a/drivers/gpu/drm/i915/intel_crt.c +++ b/drivers/gpu/drm/i915/intel_crt.c @@ -322,7 +322,7 @@ intel_crt_mode_valid(struct drm_connector *connector, * DAC limit supposedly 355 MHz. */ max_clock = 270000; - else if (IS_GEN(dev_priv, 3) || IS_GEN(dev_priv, 4)) + else if (IS_GEN_RANGE(dev_priv, 3, 4)) max_clock = 400000; else max_clock = 350000; diff --git a/drivers/gpu/drm/i915/intel_device_info.c b/drivers/gpu/drm/i915/intel_device_info.c index 8627b9a6bff4..eccb30a68b10 100644 --- a/drivers/gpu/drm/i915/intel_device_info.c +++ b/drivers/gpu/drm/i915/intel_device_info.c @@ -787,7 +787,7 @@ void intel_device_info_runtime_init(struct intel_device_info *info) DRM_INFO("Display disabled (module parameter)\n"); info->num_pipes = 0; } else if (HAS_DISPLAY(dev_priv) && - (IS_GEN(dev_priv, 7) || IS_GEN(dev_priv, 8)) && + (IS_GEN_RANGE(dev_priv, 7, 8)) && HAS_PCH_SPLIT(dev_priv)) { u32 fuse_strap = I915_READ(FUSE_STRAP); u32 sfuse_strap = I915_READ(SFUSE_STRAP); diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index b9e8a9898983..2c3f3f68d506 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -10815,7 +10815,7 @@ int intel_plane_atomic_calc_changes(const struct intel_crtc_state *old_crtc_stat * the w/a on all three platforms. */ if (plane->id == PLANE_SPRITE0 && - (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6) || + (IS_GEN_RANGE(dev_priv, 5, 6) || IS_IVYBRIDGE(dev_priv)) && (turn_on || (!needs_scaling(old_plane_state) && needs_scaling(to_intel_plane_state(plane_state))))) diff --git a/drivers/gpu/drm/i915/intel_engine_cs.c b/drivers/gpu/drm/i915/intel_engine_cs.c index 8ff794db7881..66d0ad9c36c4 100644 --- a/drivers/gpu/drm/i915/intel_engine_cs.c +++ b/drivers/gpu/drm/i915/intel_engine_cs.c @@ -438,7 +438,7 @@ void intel_engine_init_global_seqno(struct intel_engine_cs *engine, u32 seqno) * the semaphore value, then when the seqno moves backwards all * future waits will complete instantly (causing rendering corruption). */ - if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) { + if (IS_GEN_RANGE(dev_priv, 6, 7)) { I915_WRITE(RING_SYNC_0(engine->mmio_base), 0); I915_WRITE(RING_SYNC_1(engine->mmio_base), 0); if (HAS_VEBOX(dev_priv)) diff --git a/drivers/gpu/drm/i915/intel_fifo_underrun.c b/drivers/gpu/drm/i915/intel_fifo_underrun.c index ff2743ccbece..9b39975c8389 100644 --- a/drivers/gpu/drm/i915/intel_fifo_underrun.c +++ b/drivers/gpu/drm/i915/intel_fifo_underrun.c @@ -260,7 +260,7 @@ static bool __intel_set_cpu_fifo_underrun_reporting(struct drm_device *dev, if (HAS_GMCH_DISPLAY(dev_priv)) i9xx_set_fifo_underrun_reporting(dev, pipe, enable, old); - else if (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6)) + else if (IS_GEN_RANGE(dev_priv, 5, 6)) ironlake_set_fifo_underrun_reporting(dev, pipe, enable); else if (IS_GEN(dev_priv, 7)) ivybridge_set_fifo_underrun_reporting(dev, pipe, enable, old); diff --git a/drivers/gpu/drm/i915/intel_pipe_crc.c b/drivers/gpu/drm/i915/intel_pipe_crc.c index 9e870caf8104..bdabcfab8090 100644 --- a/drivers/gpu/drm/i915/intel_pipe_crc.c +++ b/drivers/gpu/drm/i915/intel_pipe_crc.c @@ -433,7 +433,7 @@ static int get_new_crc_ctl_reg(struct drm_i915_private *dev_priv, return i9xx_pipe_crc_ctl_reg(dev_priv, pipe, source, val); else if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) return vlv_pipe_crc_ctl_reg(dev_priv, pipe, source, val); - else if (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6)) + else if (IS_GEN_RANGE(dev_priv, 5, 6)) return ilk_pipe_crc_ctl_reg(source, val); else return ivb_pipe_crc_ctl_reg(dev_priv, pipe, source, val, set_wa); @@ -550,7 +550,7 @@ intel_is_valid_crc_source(struct drm_i915_private *dev_priv, return i9xx_crc_source_valid(dev_priv, source); else if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) return vlv_crc_source_valid(dev_priv, source); - else if (IS_GEN(dev_priv, 5) || IS_GEN(dev_priv, 6)) + else if (IS_GEN_RANGE(dev_priv, 5, 6)) return ilk_crc_source_valid(dev_priv, source); else return ivb_crc_source_valid(dev_priv, source); diff --git a/drivers/gpu/drm/i915/intel_uncore.c b/drivers/gpu/drm/i915/intel_uncore.c index c6eb053a8fad..ec6dde2e59eb 100644 --- a/drivers/gpu/drm/i915/intel_uncore.c +++ b/drivers/gpu/drm/i915/intel_uncore.c @@ -528,7 +528,7 @@ check_for_unclaimed_mmio(struct drm_i915_private *dev_priv) if (IS_VALLEYVIEW(dev_priv) || IS_CHERRYVIEW(dev_priv)) ret |= vlv_check_for_unclaimed_mmio(dev_priv); - if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) + if (IS_GEN_RANGE(dev_priv, 6, 7)) ret |= gen6_check_for_fifo_debug(dev_priv); return ret; @@ -556,7 +556,7 @@ static void __intel_uncore_early_sanitize(struct drm_i915_private *dev_priv, dev_priv->uncore.funcs.force_wake_get(dev_priv, restore_forcewake); - if (IS_GEN(dev_priv, 6) || IS_GEN(dev_priv, 7)) + if (IS_GEN_RANGE(dev_priv, 6, 7)) dev_priv->uncore.fifo_count = fifo_free_entries(dev_priv); spin_unlock_irq(&dev_priv->uncore.lock); @@ -1437,7 +1437,7 @@ static void intel_uncore_fw_domains_init(struct drm_i915_private *dev_priv) FORCEWAKE_MEDIA_VEBOX_GEN11(i), FORCEWAKE_ACK_MEDIA_VEBOX_GEN11(i)); } - } else if (IS_GEN(dev_priv, 10) || IS_GEN(dev_priv, 9)) { + } else if (IS_GEN_RANGE(dev_priv, 9, 10)) { dev_priv->uncore.funcs.force_wake_get = fw_domains_get_with_fallback; dev_priv->uncore.funcs.force_wake_put = fw_domains_put; From 5edd56d394dc30438cb627586eb471f5f339a603 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 13 Dec 2018 09:15:19 +0000 Subject: [PATCH 042/118] drm/i915/selftests: Check we can recover a wedged device After declaring a terminally wedged device, we allow ourselves to recover on the next GPU reset (manually triggered), or resume. Check that resetting a wedged device does work. v2: Add rpm (taken explicitly in the subtest in case we remove the outer wakeref) and early warning to i915_reset() for missed wakerefs Signed-off-by: Chris Wilson Cc: Mika Kuoppala Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181213091522.2926-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_drv.c | 1 + .../gpu/drm/i915/selftests/intel_hangcheck.c | 25 +++++++++++++++++++ 2 files changed, 26 insertions(+) diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 77c0f97fe77c..caa055ac9472 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c @@ -2226,6 +2226,7 @@ void i915_reset(struct drm_i915_private *i915, might_sleep(); lockdep_assert_held(&i915->drm.struct_mutex); + assert_rpm_wakelock_held(i915); GEM_BUG_ON(!test_bit(I915_RESET_BACKOFF, &error->flags)); if (!test_bit(I915_RESET_HANDOFF, &error->flags)) diff --git a/drivers/gpu/drm/i915/selftests/intel_hangcheck.c b/drivers/gpu/drm/i915/selftests/intel_hangcheck.c index 60a4bd9405be..9e6c9c171ed5 100644 --- a/drivers/gpu/drm/i915/selftests/intel_hangcheck.c +++ b/drivers/gpu/drm/i915/selftests/intel_hangcheck.c @@ -385,6 +385,30 @@ static int igt_global_reset(void *arg) return err; } +static int igt_wedged_reset(void *arg) +{ + struct drm_i915_private *i915 = arg; + + /* Check that we can recover a wedged device with a GPU reset */ + + igt_global_reset_lock(i915); + mutex_lock(&i915->drm.struct_mutex); + intel_runtime_pm_get(i915); + + i915_gem_set_wedged(i915); + GEM_BUG_ON(!i915_terminally_wedged(&i915->gpu_error)); + + set_bit(I915_RESET_HANDOFF, &i915->gpu_error.flags); + i915_reset(i915, ALL_ENGINES, NULL); + GEM_BUG_ON(test_bit(I915_RESET_HANDOFF, &i915->gpu_error.flags)); + + intel_runtime_pm_put(i915); + mutex_unlock(&i915->drm.struct_mutex); + igt_global_reset_unlock(i915); + + return i915_terminally_wedged(&i915->gpu_error) ? -EIO : 0; +} + static bool wait_for_idle(struct intel_engine_cs *engine) { return wait_for(intel_engine_is_idle(engine), IGT_IDLE_TIMEOUT) == 0; @@ -1452,6 +1476,7 @@ int intel_hangcheck_live_selftests(struct drm_i915_private *i915) { static const struct i915_subtest tests[] = { SUBTEST(igt_global_reset), /* attempt to recover GPU first */ + SUBTEST(igt_wedged_reset), SUBTEST(igt_hang_sanitycheck), SUBTEST(igt_reset_idle_engine), SUBTEST(igt_reset_active_engine), From 921f3a60e54e751ce1393deef6218c5900558b3d Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 13 Dec 2018 09:15:20 +0000 Subject: [PATCH 043/118] drm/i915/selftests: Verify we can perform resets from atomic context We currently require that our per-engine reset can be called from any context, even hardirq, and in the future wish to perform the device reset without holding struct_mutex (which requires some lockless shenanigans that demand the lowlevel intel_reset_gpu() be able to be used in atomic context). Test that we meet the current requirements by calling i915_reset_engine() from under various atomic contexts. Signed-off-by: Chris Wilson Cc: Mika Kuoppala Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181213091522.2926-2-chris@chris-wilson.co.uk --- .../gpu/drm/i915/selftests/intel_hangcheck.c | 172 ++++++++++++++++++ 1 file changed, 172 insertions(+) diff --git a/drivers/gpu/drm/i915/selftests/intel_hangcheck.c b/drivers/gpu/drm/i915/selftests/intel_hangcheck.c index 9e6c9c171ed5..797cf5e6d6d4 100644 --- a/drivers/gpu/drm/i915/selftests/intel_hangcheck.c +++ b/drivers/gpu/drm/i915/selftests/intel_hangcheck.c @@ -1472,6 +1472,177 @@ static int igt_handle_error(void *arg) return err; } +static void __preempt_begin(void) +{ + preempt_disable(); +} + +static void __preempt_end(void) +{ + preempt_enable(); +} + +static void __softirq_begin(void) +{ + local_bh_disable(); +} + +static void __softirq_end(void) +{ + local_bh_enable(); +} + +static void __hardirq_begin(void) +{ + local_irq_disable(); +} + +static void __hardirq_end(void) +{ + local_irq_enable(); +} + +struct atomic_section { + const char *name; + void (*critical_section_begin)(void); + void (*critical_section_end)(void); +}; + +static int __igt_atomic_reset_engine(struct intel_engine_cs *engine, + const struct atomic_section *p, + const char *mode) +{ + struct tasklet_struct * const t = &engine->execlists.tasklet; + int err; + + GEM_TRACE("i915_reset_engine(%s:%s) under %s\n", + engine->name, mode, p->name); + + tasklet_disable_nosync(t); + p->critical_section_begin(); + + err = i915_reset_engine(engine, NULL); + + p->critical_section_end(); + tasklet_enable(t); + + if (err) + pr_err("i915_reset_engine(%s:%s) failed under %s\n", + engine->name, mode, p->name); + + return err; +} + +static int igt_atomic_reset_engine(struct intel_engine_cs *engine, + const struct atomic_section *p) +{ + struct drm_i915_private *i915 = engine->i915; + struct i915_request *rq; + struct hang h; + int err; + + err = __igt_atomic_reset_engine(engine, p, "idle"); + if (err) + return err; + + err = hang_init(&h, i915); + if (err) + return err; + + rq = hang_create_request(&h, engine); + if (IS_ERR(rq)) { + err = PTR_ERR(rq); + goto out; + } + + i915_request_get(rq); + i915_request_add(rq); + + if (wait_until_running(&h, rq)) { + err = __igt_atomic_reset_engine(engine, p, "active"); + } else { + pr_err("%s(%s): Failed to start request %llx, at %x\n", + __func__, engine->name, + rq->fence.seqno, hws_seqno(&h, rq)); + err = -EIO; + } + + if (err == 0) { + struct igt_wedge_me w; + + igt_wedge_on_timeout(&w, i915, HZ / 20 /* 50ms timeout*/) + i915_request_wait(rq, + I915_WAIT_LOCKED, + MAX_SCHEDULE_TIMEOUT); + if (i915_terminally_wedged(&i915->gpu_error)) + err = -EIO; + } + + i915_request_put(rq); +out: + hang_fini(&h); + return err; +} + +static void force_reset(struct drm_i915_private *i915) +{ + i915_gem_set_wedged(i915); + set_bit(I915_RESET_HANDOFF, &i915->gpu_error.flags); + i915_reset(i915, 0, NULL); +} + +static int igt_atomic_reset(void *arg) +{ + static const struct atomic_section phases[] = { + { "preempt", __preempt_begin, __preempt_end }, + { "softirq", __softirq_begin, __softirq_end }, + { "hardirq", __hardirq_begin, __hardirq_end }, + { } + }; + struct drm_i915_private *i915 = arg; + int err = 0; + + /* Check that the resets are usable from atomic context */ + + if (USES_GUC_SUBMISSION(i915)) + return 0; /* guc is dead; long live the guc */ + + igt_global_reset_lock(i915); + mutex_lock(&i915->drm.struct_mutex); + intel_runtime_pm_get(i915); + + /* Flush any requests before we get started and check basics */ + force_reset(i915); + if (i915_terminally_wedged(&i915->gpu_error)) + goto unlock; + + if (intel_has_reset_engine(i915)) { + struct intel_engine_cs *engine; + enum intel_engine_id id; + + for_each_engine(engine, i915, id) { + const typeof(*phases) *p; + + for (p = phases; p->name; p++) { + err = igt_atomic_reset_engine(engine, p); + if (err) + goto out; + } + } + } + +out: + /* As we poke around the guts, do a full reset before continuing. */ + force_reset(i915); + +unlock: + intel_runtime_pm_put(i915); + mutex_unlock(&i915->drm.struct_mutex); + igt_global_reset_unlock(i915); + + return err; +} + int intel_hangcheck_live_selftests(struct drm_i915_private *i915) { static const struct i915_subtest tests[] = { @@ -1487,6 +1658,7 @@ int intel_hangcheck_live_selftests(struct drm_i915_private *i915) SUBTEST(igt_reset_evict_ppgtt), SUBTEST(igt_reset_evict_fence), SUBTEST(igt_handle_error), + SUBTEST(igt_atomic_reset), }; bool saved_hangcheck; int err; From 57b19d55189bacc9408519cd7ab5ade6ca2d4ac5 Mon Sep 17 00:00:00 2001 From: Oscar Mateo Date: Thu, 13 Dec 2018 09:15:21 +0000 Subject: [PATCH 044/118] drm/i915/icl: Record the valid VDBoxes with SFC capability In Gen11, only even numbered "logical" VDBoxes are hooked up to an SFC (Scaler & Format Converter) unit. We will use this information to decide when the SFC units need to be reset. BSpec: 20189 Signed-off-by: Tomasz Lis Signed-off-by: Oscar Mateo Signed-off-by: Michel Thierry Signed-off-by: Daniele Ceraolo Spurio Cc: Michel Thierry Cc: Daniele Ceraolo Spurio Cc: Joonas Lahtinen Cc: Chris Wilson Signed-off-by: Chris Wilson Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181213091522.2926-3-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/intel_device_info.c | 11 ++++++++++- drivers/gpu/drm/i915/intel_device_info.h | 3 +++ 2 files changed, 13 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_device_info.c b/drivers/gpu/drm/i915/intel_device_info.c index eccb30a68b10..a1dfb00aa16d 100644 --- a/drivers/gpu/drm/i915/intel_device_info.c +++ b/drivers/gpu/drm/i915/intel_device_info.c @@ -884,8 +884,9 @@ void intel_driver_caps_print(const struct intel_driver_caps *caps, void intel_device_info_init_mmio(struct drm_i915_private *dev_priv) { struct intel_device_info *info = mkwrite_device_info(dev_priv); - u32 media_fuse; + unsigned int logical_vdbox = 0; unsigned int i; + u32 media_fuse; if (INTEL_GEN(dev_priv) < 11) return; @@ -904,7 +905,15 @@ void intel_device_info_init_mmio(struct drm_i915_private *dev_priv) if (!(BIT(i) & info->vdbox_enable)) { info->ring_mask &= ~ENGINE_MASK(_VCS(i)); DRM_DEBUG_DRIVER("vcs%u fused off\n", i); + continue; } + + /* + * In Gen11, only even numbered logical VDBOXes are + * hooked up to an SFC (Scaler & Format Converter) unit. + */ + if (logical_vdbox++ % 2 == 0) + info->vdbox_sfc_access |= BIT(i); } DRM_DEBUG_DRIVER("vebox enable: %04x\n", info->vebox_enable); diff --git a/drivers/gpu/drm/i915/intel_device_info.h b/drivers/gpu/drm/i915/intel_device_info.h index 1caf24e2cf0b..dd34f974a857 100644 --- a/drivers/gpu/drm/i915/intel_device_info.h +++ b/drivers/gpu/drm/i915/intel_device_info.h @@ -198,6 +198,9 @@ struct intel_device_info { u8 vdbox_enable; u8 vebox_enable; + /* Media engine access to SFC per instance */ + u8 vdbox_sfc_access; + struct color_luts { u16 degamma_lut_size; u16 gamma_lut_size; From f513ac76530c2769ebf6e8954c45f39c6985cfb6 Mon Sep 17 00:00:00 2001 From: Oscar Mateo Date: Thu, 13 Dec 2018 09:15:22 +0000 Subject: [PATCH 045/118] drm/i915/icl: Mind the SFC units when resetting VD or VEBox engines SFC (Scaler & Format Converter) units are shared between VD and VEBoxes. They also happen to have separate reset bits. So, whenever we want to reset one or more of the media engines, we have to make sure the SFCs do not change owner in the process and, if this owner happens to be one of the engines being reset, we need to reset the SFC as well. This happens in 4 steps: 1) Tell the engine that a software reset is going to happen. The engine will then try to force lock the SFC (if currently locked, it will remain so; if currently unlocked, it will ignore this and all new lock requests). 2) Poll the ack bit to make sure the hardware has received the forced lock from the driver. Once this bit is set, it indicates SFC status (lock or unlock) will not change anymore (until we tell the engine it is safe to unlock again). 3) Check the usage bit to see if the SFC has ended up being locked to the engine we want to reset. If this is the case, we have to reset the SFC as well. 4) Unlock all the SFCs once the reset sequence is completed. Obviously, if we are resetting the whole GPU, we don't have to worry about all of this. BSpec: 10989 BSpec: 10990 BSpec: 10954 BSpec: 10955 BSpec: 10956 BSpec: 19212 Signed-off-by: Tomasz Lis Signed-off-by: Oscar Mateo Signed-off-by: Michel Thierry Cc: Michel Thierry Cc: Joonas Lahtinen Cc: Chris Wilson Cc: Daniele Ceraolo Spurio Signed-off-by: Chris Wilson Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181213091522.2926-4-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_reg.h | 18 +++++ drivers/gpu/drm/i915/intel_uncore.c | 115 ++++++++++++++++++++++++++-- 2 files changed, 128 insertions(+), 5 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h index 0a7d60509ca7..0796526dc10f 100644 --- a/drivers/gpu/drm/i915/i915_reg.h +++ b/drivers/gpu/drm/i915/i915_reg.h @@ -347,6 +347,24 @@ static inline bool i915_mmio_reg_valid(i915_reg_t reg) #define GEN11_GRDOM_MEDIA4 (1 << 8) #define GEN11_GRDOM_VECS (1 << 13) #define GEN11_GRDOM_VECS2 (1 << 14) +#define GEN11_GRDOM_SFC0 (1 << 17) +#define GEN11_GRDOM_SFC1 (1 << 18) + +#define GEN11_VCS_SFC_RESET_BIT(instance) (GEN11_GRDOM_SFC0 << ((instance) >> 1)) +#define GEN11_VECS_SFC_RESET_BIT(instance) (GEN11_GRDOM_SFC0 << (instance)) + +#define GEN11_VCS_SFC_FORCED_LOCK(engine) _MMIO((engine)->mmio_base + 0x88C) +#define GEN11_VCS_SFC_FORCED_LOCK_BIT (1 << 0) +#define GEN11_VCS_SFC_LOCK_STATUS(engine) _MMIO((engine)->mmio_base + 0x890) +#define GEN11_VCS_SFC_USAGE_BIT (1 << 0) +#define GEN11_VCS_SFC_LOCK_ACK_BIT (1 << 1) + +#define GEN11_VECS_SFC_FORCED_LOCK(engine) _MMIO((engine)->mmio_base + 0x201C) +#define GEN11_VECS_SFC_FORCED_LOCK_BIT (1 << 0) +#define GEN11_VECS_SFC_LOCK_ACK(engine) _MMIO((engine)->mmio_base + 0x2018) +#define GEN11_VECS_SFC_LOCK_ACK_BIT (1 << 0) +#define GEN11_VECS_SFC_USAGE(engine) _MMIO((engine)->mmio_base + 0x2014) +#define GEN11_VECS_SFC_USAGE_BIT (1 << 0) #define RING_PP_DIR_BASE(engine) _MMIO((engine)->mmio_base + 0x228) #define RING_PP_DIR_BASE_READ(engine) _MMIO((engine)->mmio_base + 0x518) diff --git a/drivers/gpu/drm/i915/intel_uncore.c b/drivers/gpu/drm/i915/intel_uncore.c index ec6dde2e59eb..5800f0ce2c57 100644 --- a/drivers/gpu/drm/i915/intel_uncore.c +++ b/drivers/gpu/drm/i915/intel_uncore.c @@ -1931,6 +1931,103 @@ static int gen6_reset_engines(struct drm_i915_private *dev_priv, return gen6_hw_domain_reset(dev_priv, hw_mask); } +static u32 gen11_lock_sfc(struct drm_i915_private *dev_priv, + struct intel_engine_cs *engine) +{ + u8 vdbox_sfc_access = INTEL_INFO(dev_priv)->vdbox_sfc_access; + i915_reg_t sfc_forced_lock, sfc_forced_lock_ack; + u32 sfc_forced_lock_bit, sfc_forced_lock_ack_bit; + i915_reg_t sfc_usage; + u32 sfc_usage_bit; + u32 sfc_reset_bit; + + switch (engine->class) { + case VIDEO_DECODE_CLASS: + if ((BIT(engine->instance) & vdbox_sfc_access) == 0) + return 0; + + sfc_forced_lock = GEN11_VCS_SFC_FORCED_LOCK(engine); + sfc_forced_lock_bit = GEN11_VCS_SFC_FORCED_LOCK_BIT; + + sfc_forced_lock_ack = GEN11_VCS_SFC_LOCK_STATUS(engine); + sfc_forced_lock_ack_bit = GEN11_VCS_SFC_LOCK_ACK_BIT; + + sfc_usage = GEN11_VCS_SFC_LOCK_STATUS(engine); + sfc_usage_bit = GEN11_VCS_SFC_USAGE_BIT; + sfc_reset_bit = GEN11_VCS_SFC_RESET_BIT(engine->instance); + break; + + case VIDEO_ENHANCEMENT_CLASS: + sfc_forced_lock = GEN11_VECS_SFC_FORCED_LOCK(engine); + sfc_forced_lock_bit = GEN11_VECS_SFC_FORCED_LOCK_BIT; + + sfc_forced_lock_ack = GEN11_VECS_SFC_LOCK_ACK(engine); + sfc_forced_lock_ack_bit = GEN11_VECS_SFC_LOCK_ACK_BIT; + + sfc_usage = GEN11_VECS_SFC_USAGE(engine); + sfc_usage_bit = GEN11_VECS_SFC_USAGE_BIT; + sfc_reset_bit = GEN11_VECS_SFC_RESET_BIT(engine->instance); + break; + + default: + return 0; + } + + /* + * Tell the engine that a software reset is going to happen. The engine + * will then try to force lock the SFC (if currently locked, it will + * remain so until we tell the engine it is safe to unlock; if currently + * unlocked, it will ignore this and all new lock requests). If SFC + * ends up being locked to the engine we want to reset, we have to reset + * it as well (we will unlock it once the reset sequence is completed). + */ + I915_WRITE_FW(sfc_forced_lock, + I915_READ_FW(sfc_forced_lock) | sfc_forced_lock_bit); + + if (__intel_wait_for_register_fw(dev_priv, + sfc_forced_lock_ack, + sfc_forced_lock_ack_bit, + sfc_forced_lock_ack_bit, + 1000, 0, NULL)) { + DRM_DEBUG_DRIVER("Wait for SFC forced lock ack failed\n"); + return 0; + } + + if (I915_READ_FW(sfc_usage) & sfc_usage_bit) + return sfc_reset_bit; + + return 0; +} + +static void gen11_unlock_sfc(struct drm_i915_private *dev_priv, + struct intel_engine_cs *engine) +{ + u8 vdbox_sfc_access = INTEL_INFO(dev_priv)->vdbox_sfc_access; + i915_reg_t sfc_forced_lock; + u32 sfc_forced_lock_bit; + + switch (engine->class) { + case VIDEO_DECODE_CLASS: + if ((BIT(engine->instance) & vdbox_sfc_access) == 0) + return; + + sfc_forced_lock = GEN11_VCS_SFC_FORCED_LOCK(engine); + sfc_forced_lock_bit = GEN11_VCS_SFC_FORCED_LOCK_BIT; + break; + + case VIDEO_ENHANCEMENT_CLASS: + sfc_forced_lock = GEN11_VECS_SFC_FORCED_LOCK(engine); + sfc_forced_lock_bit = GEN11_VECS_SFC_FORCED_LOCK_BIT; + break; + + default: + return; + } + + I915_WRITE_FW(sfc_forced_lock, + I915_READ_FW(sfc_forced_lock) & ~sfc_forced_lock_bit); +} + /** * gen11_reset_engines - reset individual engines * @dev_priv: i915 device @@ -1947,7 +2044,6 @@ static int gen6_reset_engines(struct drm_i915_private *dev_priv, static int gen11_reset_engines(struct drm_i915_private *dev_priv, unsigned int engine_mask) { - struct intel_engine_cs *engine; const u32 hw_engine_mask[I915_NUM_ENGINES] = { [RCS] = GEN11_GRDOM_RENDER, [BCS] = GEN11_GRDOM_BLT, @@ -1958,21 +2054,30 @@ static int gen11_reset_engines(struct drm_i915_private *dev_priv, [VECS] = GEN11_GRDOM_VECS, [VECS2] = GEN11_GRDOM_VECS2, }; + struct intel_engine_cs *engine; + unsigned int tmp; u32 hw_mask; + int ret; BUILD_BUG_ON(VECS2 + 1 != I915_NUM_ENGINES); if (engine_mask == ALL_ENGINES) { hw_mask = GEN11_GRDOM_FULL; } else { - unsigned int tmp; - hw_mask = 0; - for_each_engine_masked(engine, dev_priv, engine_mask, tmp) + for_each_engine_masked(engine, dev_priv, engine_mask, tmp) { hw_mask |= hw_engine_mask[engine->id]; + hw_mask |= gen11_lock_sfc(dev_priv, engine); + } } - return gen6_hw_domain_reset(dev_priv, hw_mask); + ret = gen6_hw_domain_reset(dev_priv, hw_mask); + + if (engine_mask != ALL_ENGINES) + for_each_engine_masked(engine, dev_priv, engine_mask, tmp) + gen11_unlock_sfc(dev_priv, engine); + + return ret; } /** From a489334941d450c5212ccd821fb11102e910be69 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 13 Dec 2018 16:12:41 +0000 Subject: [PATCH 046/118] drm/i915: Fix Cherryview oops on boot MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Do not dereference the LUT blob before checking whether that blob exists. Or else, <1>[ 13.978684] BUG: unable to handle kernel NULL pointer dereference at 0000000000000048 <6>[ 13.978718] PGD 0 P4D 0 <4>[ 13.978733] Oops: 0000 [#1] PREEMPT SMP PTI <4>[ 13.978750] CPU: 0 PID: 282 Comm: modprobe Not tainted 4.20.0-rc5-CI-CI_DRM_5294+ #1 <4>[ 13.978773] Hardware name: /NUC5CPYB, BIOS PYBSWCEL.86A.0058.2016.1102.1842 11/02/2016 <4>[ 13.978932] RIP: 0010:cherryview_load_csc_matrix+0x1e6/0x210 [i915] <4>[ 13.978953] Code: 41 5c 41 5d e9 7b 83 aa e1 41 c1 e4 0d 48 83 bd 00 02 00 00 00 48 8b 85 10 02 00 00 45 89 e5 74 09 ba 01 00 00 00 31 c9 eb 9d <48> 8b 50 48 48 c1 ea 03 81 fa 00 01 00 00 75 07 31 d2 48 85 c0 75 <4>[ 13.979001] RSP: 0018:ffffc9000026f840 EFLAGS: 00010246 <4>[ 13.979018] RAX: 0000000000000000 RBX: ffff888165500000 RCX: 7885fe6200000000 <4>[ 13.979039] RDX: 0000000000000020 RSI: ffff88816553a008 RDI: ffff888165464a88 <4>[ 13.979060] RBP: ffff888165464a88 R08: 000000000ed0e429 R09: 0000000000000001 <4>[ 13.979080] R10: 0000000000000000 R11: 0000000000000000 R12: 0000000000004000 <4>[ 13.979101] R13: 0000000000004000 R14: ffff888165500000 R15: ffff888165464a88 <4>[ 13.979122] FS: 00007fb69c4f3540(0000) GS:ffff88817ba00000(0000) knlGS:0000000000000000 <4>[ 13.979146] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 <4>[ 13.979163] CR2: 0000000000000048 CR3: 000000016d7fa000 CR4: 00000000001006f0 <4>[ 13.979184] Call Trace: <4>[ 13.979302] intel_update_crtc+0x18f/0x2b0 [i915] <4>[ 13.979421] intel_update_crtcs+0x49/0x60 [i915] <4>[ 13.979538] intel_atomic_commit_tail+0x1ea/0xd70 [i915] <4>[ 13.979657] ? intel_atomic_commit_ready+0x3f/0x50 [i915] <4>[ 13.979762] ? __i915_sw_fence_complete+0x1a0/0x250 [i915] <4>[ 13.979884] intel_atomic_commit+0x244/0x330 [i915] <4>[ 13.980002] intel_initial_commit+0xb6/0x140 [i915] <4>[ 13.980127] intel_modeset_init+0x7a1/0x1880 [i915] <4>[ 13.980235] i915_driver_load+0xcbb/0x15c0 [i915] <4>[ 13.980257] ? __pm_runtime_resume+0x4f/0x80 <4>[ 13.980277] ? _raw_spin_unlock_irqrestore+0x4c/0x60 <4>[ 13.980296] ? lockdep_hardirqs_on+0xe0/0x1b0 <4>[ 13.980401] i915_pci_probe+0x29/0xa0 [i915] <4>[ 13.980421] pci_device_probe+0xa1/0x130 <4>[ 13.980440] really_probe+0xf3/0x3e0 <4>[ 13.980456] driver_probe_device+0x10a/0x120 <4>[ 13.980474] __driver_attach+0xdb/0x100 <4>[ 13.980489] ? driver_probe_device+0x120/0x120 <4>[ 13.980505] ? driver_probe_device+0x120/0x120 <4>[ 13.980522] bus_for_each_dev+0x74/0xc0 <4>[ 13.980539] bus_add_driver+0x15f/0x250 <4>[ 13.980554] ? 0xffffffffa0348000 <4>[ 13.980568] driver_register+0x56/0xe0 <4>[ 13.980583] ? 0xffffffffa0348000 <4>[ 13.980597] do_one_initcall+0x58/0x2e0 <4>[ 13.980615] ? do_init_module+0x1d/0x1ea <4>[ 13.980631] ? rcu_read_lock_sched_held+0x6f/0x80 <4>[ 13.980649] ? kmem_cache_alloc_trace+0x264/0x290 <4>[ 13.980668] do_init_module+0x56/0x1ea <4>[ 13.980685] load_module+0x227a/0x29c0 <4>[ 13.980715] ? __se_sys_finit_module+0xd3/0xf0 <4>[ 13.980731] __se_sys_finit_module+0xd3/0xf0 <4>[ 13.980756] do_syscall_64+0x55/0x190 <4>[ 13.980772] entry_SYSCALL_64_after_hwframe+0x49/0xbe <4>[ 13.980789] RIP: 0033:0x7fb69c019839 <4>[ 13.980804] Code: 00 f3 c3 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 40 00 48 89 f8 48 89 f7 48 89 d6 48 89 ca 4d 89 c2 4d 89 c8 4c 8b 4c 24 08 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d 1f f6 2c 00 f7 d8 64 89 01 48 <4>[ 13.980851] RSP: 002b:00007ffdc112e3a8 EFLAGS: 00000246 ORIG_RAX: 0000000000000139 <4>[ 13.980875] RAX: ffffffffffffffda RBX: 000055c689fe0b30 RCX: 00007fb69c019839 <4>[ 13.980895] RDX: 0000000000000000 RSI: 000055c689a05d2e RDI: 0000000000000000 <4>[ 13.980916] RBP: 000055c689a05d2e R08: 0000000000000000 R09: 0000000000000000 <4>[ 13.980936] R10: 0000000000000000 R11: 0000000000000246 R12: 0000000000000000 <4>[ 13.980957] R13: 000055c689fe0c60 R14: 0000000000040000 R15: 000055c689fe0b30 <4>[ 13.980986] Modules linked in: i915(+) snd_hda_intel snd_hda_codec snd_hwdep snd_hda_core snd_pcm pinctrl_cherryview prime_numbers <4>[ 13.981027] CR2: 0000000000000048 Fixes: 302da0cdf784 ("drm/i915: Use intel_ types more consistently for color management code (v2)") Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=109054 Signed-off-by: Chris Wilson Cc: Matt Roper Cc: Ville Syrjälä Reviewed-by: Matt Roper Signed-off-by: Matt Roper Link: https://patchwork.freedesktop.org/patch/msgid/20181213161241.3461-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/intel_color.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_color.c b/drivers/gpu/drm/i915/intel_color.c index 1d572e83db7f..37fd9ddf762e 100644 --- a/drivers/gpu/drm/i915/intel_color.c +++ b/drivers/gpu/drm/i915/intel_color.c @@ -74,14 +74,17 @@ #define ILK_CSC_COEFF_1_0 \ ((7 << 12) | ILK_CSC_COEFF_FP(CTM_COEFF_1_0, 8)) +static bool lut_is_legacy(struct drm_property_blob *lut) +{ + return drm_color_lut_size(lut) == LEGACY_LUT_LENGTH; +} + static bool crtc_state_is_legacy_gamma(struct intel_crtc_state *crtc_state) { - int lut_length = drm_color_lut_size(crtc_state->base.gamma_lut); - return !crtc_state->base.degamma_lut && !crtc_state->base.ctm && crtc_state->base.gamma_lut && - lut_length == LEGACY_LUT_LENGTH; + lut_is_legacy(crtc_state->base.gamma_lut); } /* From e845f099f1c6e72c67536ee41f735f01d30d9fc7 Mon Sep 17 00:00:00 2001 From: Manasi Navare Date: Wed, 5 Dec 2018 16:54:07 -0800 Subject: [PATCH 047/118] drm/i915/dsc: Add Per connector debugfs node for DSC support/enable DSC can be supported per DP connector. This patch adds a per connector debugfs node to expose DSC support capability by the kernel. The same node can be used from userspace to force DSC enable. force_dsc_en written through this debugfs node is used to force DSC even for lower resolutions. Credits to Ville Syrjala for suggesting the proper locks to be used and to Lyude Paul for explaining how to use them in this context v8: * Add else if (ret) for drm_modeset_lock (Lyude) v7: * Get crtc, crtc_state from connector atomic state and add proper locks and backoff (Ville, Chris Wilson, Lyude) (Suggested-by: Ville Syrjala ) * Use %zu for printing size_t variable (Lyude) v6: * Read fec_capable only for non edp (Manasi) v5: * Name it dsc sink support and also add fec support in the same node (Ville) v4: * Add missed connector_status check (Manasi) * Create i915_dsc_support node only for Gen >=10 (manasi) * Access intel_dp->dsc_dpcd only if its not NULL (Manasi) v3: * Combine Force_dsc_en with this patch (Ville) v2: * Use kstrtobool_from_user to avoid explicit error checking (Lyude) * Rebase on drm-tip (Manasi) Cc: Rodrigo Vivi Cc: Ville Syrjala Cc: Anusha Srivatsa Cc: Lyude Paul Signed-off-by: Manasi Navare Reviewed-by: Lyude Paul Signed-off-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181206005407.4698-1-manasi.d.navare@intel.com --- drivers/gpu/drm/i915/i915_debugfs.c | 106 ++++++++++++++++++++++++++++ drivers/gpu/drm/i915/intel_dp.c | 3 +- drivers/gpu/drm/i915/intel_drv.h | 3 + 3 files changed, 111 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index ed44e30f875e..77486a614614 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -5094,6 +5094,105 @@ static int i915_hdcp_sink_capability_show(struct seq_file *m, void *data) } DEFINE_SHOW_ATTRIBUTE(i915_hdcp_sink_capability); +static int i915_dsc_fec_support_show(struct seq_file *m, void *data) +{ + struct drm_connector *connector = m->private; + struct drm_device *dev = connector->dev; + struct drm_crtc *crtc; + struct intel_dp *intel_dp; + struct drm_modeset_acquire_ctx ctx; + struct intel_crtc_state *crtc_state = NULL; + int ret = 0; + bool try_again = false; + + drm_modeset_acquire_init(&ctx, DRM_MODESET_ACQUIRE_INTERRUPTIBLE); + + do { + ret = drm_modeset_lock(&dev->mode_config.connection_mutex, + &ctx); + if (ret) { + ret = -EINTR; + break; + } + crtc = connector->state->crtc; + if (connector->status != connector_status_connected || !crtc) { + ret = -ENODEV; + break; + } + ret = drm_modeset_lock(&crtc->mutex, &ctx); + if (ret == -EDEADLK) { + ret = drm_modeset_backoff(&ctx); + if (!ret) { + try_again = true; + continue; + } + break; + } else if (ret) { + break; + } + intel_dp = enc_to_intel_dp(&intel_attached_encoder(connector)->base); + crtc_state = to_intel_crtc_state(crtc->state); + seq_printf(m, "DSC_Enabled: %s\n", + yesno(crtc_state->dsc_params.compression_enable)); + if (intel_dp->dsc_dpcd) + seq_printf(m, "DSC_Sink_Support: %s\n", + yesno(drm_dp_sink_supports_dsc(intel_dp->dsc_dpcd))); + if (!intel_dp_is_edp(intel_dp)) + seq_printf(m, "FEC_Sink_Support: %s\n", + yesno(drm_dp_sink_supports_fec(intel_dp->fec_capable))); + } while (try_again); + + drm_modeset_drop_locks(&ctx); + drm_modeset_acquire_fini(&ctx); + + return ret; +} + +static ssize_t i915_dsc_fec_support_write(struct file *file, + const char __user *ubuf, + size_t len, loff_t *offp) +{ + bool dsc_enable = false; + int ret; + struct drm_connector *connector = + ((struct seq_file *)file->private_data)->private; + struct intel_encoder *encoder = intel_attached_encoder(connector); + struct intel_dp *intel_dp = enc_to_intel_dp(&encoder->base); + + if (len == 0) + return 0; + + DRM_DEBUG_DRIVER("Copied %zu bytes from user to force DSC\n", + len); + + ret = kstrtobool_from_user(ubuf, len, &dsc_enable); + if (ret < 0) + return ret; + + DRM_DEBUG_DRIVER("Got %s for DSC Enable\n", + (dsc_enable) ? "true" : "false"); + intel_dp->force_dsc_en = dsc_enable; + + *offp += len; + return len; +} + +static int i915_dsc_fec_support_open(struct inode *inode, + struct file *file) +{ + return single_open(file, i915_dsc_fec_support_show, + inode->i_private); +} + +static const struct file_operations i915_dsc_fec_support_fops = { + .owner = THIS_MODULE, + .open = i915_dsc_fec_support_open, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, + .write = i915_dsc_fec_support_write +}; + /** * i915_debugfs_connector_add - add i915 specific connector debugfs files * @connector: pointer to a registered drm_connector @@ -5106,6 +5205,7 @@ DEFINE_SHOW_ATTRIBUTE(i915_hdcp_sink_capability); int i915_debugfs_connector_add(struct drm_connector *connector) { struct dentry *root = connector->debugfs_entry; + struct drm_i915_private *dev_priv = to_i915(connector->dev); /* The connector must have been registered beforehands. */ if (!root) @@ -5130,5 +5230,11 @@ int i915_debugfs_connector_add(struct drm_connector *connector) connector, &i915_hdcp_sink_capability_fops); } + if (INTEL_GEN(dev_priv) >= 10 && + (connector->connector_type == DRM_MODE_CONNECTOR_DisplayPort || + connector->connector_type == DRM_MODE_CONNECTOR_eDP)) + debugfs_create_file("i915_dsc_fec_support", S_IRUGO, root, + connector, &i915_dsc_fec_support_fops); + return 0; } diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index b3138abd3321..62484e129563 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -2051,7 +2051,8 @@ intel_dp_compute_link_config(struct intel_encoder *encoder, &limits); /* enable compression if the mode doesn't fit available BW */ - if (!ret) { + DRM_DEBUG_KMS("Force DSC en = %d\n", intel_dp->force_dsc_en); + if (!ret || intel_dp->force_dsc_en) { if (!intel_dp_dsc_compute_config(intel_dp, pipe_config, conn_state, &limits)) return false; diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index d08f08f607dd..cb3a055f18c8 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -1209,6 +1209,9 @@ struct intel_dp { /* Displayport compliance testing */ struct intel_dp_compliance compliance; + + /* Display stream compression testing */ + bool force_dsc_en; }; enum lspcon_vendor { From a49aa6508ed7d43e89d6c60224916613ad0a4458 Mon Sep 17 00:00:00 2001 From: Anusha Srivatsa Date: Fri, 7 Dec 2018 10:28:39 -0800 Subject: [PATCH 048/118] drm/i915/huc: Update the HuC version for BXT We have an update for HuC for BXT. Load the latest version. v2: Change the subject. Cc: Rodrigo Vivi Signed-off-by: Anusha Srivatsa Reviewed-by: Rodrigo Vivi Signed-off-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181207182840.9292-2-anusha.srivatsa@intel.com --- drivers/gpu/drm/i915/intel_huc_fw.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_huc_fw.c b/drivers/gpu/drm/i915/intel_huc_fw.c index f93d2384d482..9612227b3c44 100644 --- a/drivers/gpu/drm/i915/intel_huc_fw.c +++ b/drivers/gpu/drm/i915/intel_huc_fw.c @@ -23,8 +23,8 @@ */ #define BXT_HUC_FW_MAJOR 01 -#define BXT_HUC_FW_MINOR 07 -#define BXT_BLD_NUM 1398 +#define BXT_HUC_FW_MINOR 8 +#define BXT_BLD_NUM 2893 #define SKL_HUC_FW_MAJOR 01 #define SKL_HUC_FW_MINOR 07 From 2c5c415c1df6bd244496e8b93b6393ad89b2403f Mon Sep 17 00:00:00 2001 From: Hans de Goede Date: Mon, 17 Dec 2018 15:19:03 +0100 Subject: [PATCH 049/118] drm/i915: Update crtc scaler settings when update_pipe is set When the pipe_config's update_pipe flag is set we may need to update the panel fitting settings. On GEN9+ this means we need to update the crtc's scaler settings. This fixes the following WARN_ON, during i915 loading on an Asrock B150M Pro4S/D3 board with an i5-6500 CPU / graphics: [drm:pipe_config_err [i915]] *ERROR* mismatch in pch_pfit.enabled (expected no, found yes) pipe state doesn't match! WARNING: CPU: 3 PID: 305 at drivers/gpu/drm/i915/intel_display.c:12084 With line 12084 being the I915_STATE_WARN call inside the "if (!intel_pipe_config_compare())" block in verify_crtc_state(). On this board with 2 1920x1080 monitors connected over HDMI the GOP initializes both monitors at 1920x1080 and despite no scaling being necessary configures a scaler for one of them. When booting with fastboot=1 on the initial modeset needs_modeset will be false while update_pipe is true. Since we were not calling skl_update_scaler_crtc() in this case we would leave the scaler enabled causing this error. Signed-off-by: Hans de Goede Signed-off-by: Maarten Lankhorst Link: https://patchwork.freedesktop.org/patch/msgid/20181217141903.4182-1-hdegoede@redhat.com --- drivers/gpu/drm/i915/intel_display.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 2c3f3f68d506..3b7094822aa9 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -11009,7 +11009,7 @@ static int intel_crtc_atomic_check(struct drm_crtc *crtc, } if (INTEL_GEN(dev_priv) >= 9) { - if (mode_changed) + if (mode_changed || pipe_config->update_pipe) ret = skl_update_scaler_crtc(pipe_config); if (!ret) From b265a2a6255f581258ccfdccbd2efca51a142fe2 Mon Sep 17 00:00:00 2001 From: Clint Taylor Date: Mon, 17 Dec 2018 14:13:47 -0800 Subject: [PATCH 050/118] drm/i915/icl: combo port vswing programming changes per BSPEC MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit In August 2018 the BSPEC changed the ICL port programming sequence to closely resemble earlier gen programming sequence. Restrict combo phy to HBR max rate unless eDP panel is connected to port. v2: remove debug code that Imre found v3: simplify translation table if-else v4: edp translation table now based on link rate and low_swing v5: Misc review comments + r-b BSpec: 21257 Cc: Ville Syrjälä Cc: Imre Deak Cc: Rodrigo Vivi Reviewed-by: Imre Deak Signed-off-by: Clint Taylor Signed-off-by: Imre Deak Link: https://patchwork.freedesktop.org/patch/msgid/1545084827-5776-1-git-send-email-clinton.a.taylor@intel.com --- drivers/gpu/drm/i915/i915_reg.h | 4 + drivers/gpu/drm/i915/intel_ddi.c | 238 +++++++++++-------------------- drivers/gpu/drm/i915/intel_dp.c | 4 +- 3 files changed, 93 insertions(+), 153 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_reg.h b/drivers/gpu/drm/i915/i915_reg.h index 0796526dc10f..02af9b5add34 100644 --- a/drivers/gpu/drm/i915/i915_reg.h +++ b/drivers/gpu/drm/i915/i915_reg.h @@ -1884,6 +1884,10 @@ enum i915_power_well_id { #define CNL_PORT_TX_DW7_GRP(port) _MMIO(_CNL_PORT_TX_DW_GRP((port), 7)) #define CNL_PORT_TX_DW7_LN0(port) _MMIO(_CNL_PORT_TX_DW_LN0((port), 7)) +#define ICL_PORT_TX_DW7_AUX(port) _MMIO(_ICL_PORT_TX_DW_AUX(7, port)) +#define ICL_PORT_TX_DW7_GRP(port) _MMIO(_ICL_PORT_TX_DW_GRP(7, port)) +#define ICL_PORT_TX_DW7_LN0(port) _MMIO(_ICL_PORT_TX_DW_LN(7, 0, port)) +#define ICL_PORT_TX_DW7_LN(port, ln) _MMIO(_ICL_PORT_TX_DW_LN(7, ln, port)) #define N_SCALAR(x) ((x) << 24) #define N_SCALAR_MASK (0x7F << 24) diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index 92c0bf70fe09..dfd35822cdab 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -494,103 +494,58 @@ static const struct cnl_ddi_buf_trans cnl_ddi_translations_edp_1_05V[] = { { 0x2, 0x7F, 0x3F, 0x00, 0x00 }, /* 400 400 0.0 */ }; -struct icl_combo_phy_ddi_buf_trans { - u32 dw2_swing_select; - u32 dw2_swing_scalar; - u32 dw4_scaling; +/* icl_combo_phy_ddi_translations */ +static const struct cnl_ddi_buf_trans icl_combo_phy_ddi_translations_dp_hbr2[] = { + /* NT mV Trans mV db */ + { 0xA, 0x35, 0x3F, 0x00, 0x00 }, /* 350 350 0.0 */ + { 0xA, 0x4F, 0x37, 0x00, 0x08 }, /* 350 500 3.1 */ + { 0xC, 0x71, 0x2F, 0x00, 0x10 }, /* 350 700 6.0 */ + { 0x6, 0x7F, 0x2B, 0x00, 0x14 }, /* 350 900 8.2 */ + { 0xA, 0x4C, 0x3F, 0x00, 0x00 }, /* 500 500 0.0 */ + { 0xC, 0x73, 0x34, 0x00, 0x0B }, /* 500 700 2.9 */ + { 0x6, 0x7F, 0x2F, 0x00, 0x10 }, /* 500 900 5.1 */ + { 0xC, 0x6C, 0x3C, 0x00, 0x03 }, /* 650 700 0.6 */ + { 0x6, 0x7F, 0x35, 0x00, 0x0A }, /* 600 900 3.5 */ + { 0x6, 0x7F, 0x3F, 0x00, 0x00 }, /* 900 900 0.0 */ }; -/* Voltage Swing Programming for VccIO 0.85V for DP */ -static const struct icl_combo_phy_ddi_buf_trans icl_combo_phy_ddi_translations_dp_hdmi_0_85V[] = { - /* Voltage mV db */ - { 0x2, 0x98, 0x0018 }, /* 400 0.0 */ - { 0x2, 0x98, 0x3015 }, /* 400 3.5 */ - { 0x2, 0x98, 0x6012 }, /* 400 6.0 */ - { 0x2, 0x98, 0x900F }, /* 400 9.5 */ - { 0xB, 0x70, 0x0018 }, /* 600 0.0 */ - { 0xB, 0x70, 0x3015 }, /* 600 3.5 */ - { 0xB, 0x70, 0x6012 }, /* 600 6.0 */ - { 0x5, 0x00, 0x0018 }, /* 800 0.0 */ - { 0x5, 0x00, 0x3015 }, /* 800 3.5 */ - { 0x6, 0x98, 0x0018 }, /* 1200 0.0 */ +static const struct cnl_ddi_buf_trans icl_combo_phy_ddi_translations_edp_hbr2[] = { + /* NT mV Trans mV db */ + { 0x0, 0x7F, 0x3F, 0x00, 0x00 }, /* 200 200 0.0 */ + { 0x8, 0x7F, 0x38, 0x00, 0x07 }, /* 200 250 1.9 */ + { 0x1, 0x7F, 0x33, 0x00, 0x0C }, /* 200 300 3.5 */ + { 0x9, 0x7F, 0x31, 0x00, 0x0E }, /* 200 350 4.9 */ + { 0x8, 0x7F, 0x3F, 0x00, 0x00 }, /* 250 250 0.0 */ + { 0x1, 0x7F, 0x38, 0x00, 0x07 }, /* 250 300 1.6 */ + { 0x9, 0x7F, 0x35, 0x00, 0x0A }, /* 250 350 2.9 */ + { 0x1, 0x7F, 0x3F, 0x00, 0x00 }, /* 300 300 0.0 */ + { 0x9, 0x7F, 0x38, 0x00, 0x07 }, /* 300 350 1.3 */ + { 0x9, 0x7F, 0x3F, 0x00, 0x00 }, /* 350 350 0.0 */ }; -/* FIXME - After table is updated in Bspec */ -/* Voltage Swing Programming for VccIO 0.85V for eDP */ -static const struct icl_combo_phy_ddi_buf_trans icl_combo_phy_ddi_translations_edp_0_85V[] = { - /* Voltage mV db */ - { 0x0, 0x00, 0x00 }, /* 200 0.0 */ - { 0x0, 0x00, 0x00 }, /* 200 1.5 */ - { 0x0, 0x00, 0x00 }, /* 200 4.0 */ - { 0x0, 0x00, 0x00 }, /* 200 6.0 */ - { 0x0, 0x00, 0x00 }, /* 250 0.0 */ - { 0x0, 0x00, 0x00 }, /* 250 1.5 */ - { 0x0, 0x00, 0x00 }, /* 250 4.0 */ - { 0x0, 0x00, 0x00 }, /* 300 0.0 */ - { 0x0, 0x00, 0x00 }, /* 300 1.5 */ - { 0x0, 0x00, 0x00 }, /* 350 0.0 */ +static const struct cnl_ddi_buf_trans icl_combo_phy_ddi_translations_edp_hbr3[] = { + /* NT mV Trans mV db */ + { 0xA, 0x35, 0x3F, 0x00, 0x00 }, /* 350 350 0.0 */ + { 0xA, 0x4F, 0x37, 0x00, 0x08 }, /* 350 500 3.1 */ + { 0xC, 0x71, 0x2F, 0x00, 0x10 }, /* 350 700 6.0 */ + { 0x6, 0x7F, 0x2B, 0x00, 0x14 }, /* 350 900 8.2 */ + { 0xA, 0x4C, 0x3F, 0x00, 0x00 }, /* 500 500 0.0 */ + { 0xC, 0x73, 0x34, 0x00, 0x0B }, /* 500 700 2.9 */ + { 0x6, 0x7F, 0x2F, 0x00, 0x10 }, /* 500 900 5.1 */ + { 0xC, 0x6C, 0x3C, 0x00, 0x03 }, /* 650 700 0.6 */ + { 0x6, 0x7F, 0x35, 0x00, 0x0A }, /* 600 900 3.5 */ + { 0x6, 0x7F, 0x3F, 0x00, 0x00 }, /* 900 900 0.0 */ }; -/* Voltage Swing Programming for VccIO 0.95V for DP */ -static const struct icl_combo_phy_ddi_buf_trans icl_combo_phy_ddi_translations_dp_hdmi_0_95V[] = { - /* Voltage mV db */ - { 0x2, 0x98, 0x0018 }, /* 400 0.0 */ - { 0x2, 0x98, 0x3015 }, /* 400 3.5 */ - { 0x2, 0x98, 0x6012 }, /* 400 6.0 */ - { 0x2, 0x98, 0x900F }, /* 400 9.5 */ - { 0x4, 0x98, 0x0018 }, /* 600 0.0 */ - { 0x4, 0x98, 0x3015 }, /* 600 3.5 */ - { 0x4, 0x98, 0x6012 }, /* 600 6.0 */ - { 0x5, 0x76, 0x0018 }, /* 800 0.0 */ - { 0x5, 0x76, 0x3015 }, /* 800 3.5 */ - { 0x6, 0x98, 0x0018 }, /* 1200 0.0 */ -}; - -/* FIXME - After table is updated in Bspec */ -/* Voltage Swing Programming for VccIO 0.95V for eDP */ -static const struct icl_combo_phy_ddi_buf_trans icl_combo_phy_ddi_translations_edp_0_95V[] = { - /* Voltage mV db */ - { 0x0, 0x00, 0x00 }, /* 200 0.0 */ - { 0x0, 0x00, 0x00 }, /* 200 1.5 */ - { 0x0, 0x00, 0x00 }, /* 200 4.0 */ - { 0x0, 0x00, 0x00 }, /* 200 6.0 */ - { 0x0, 0x00, 0x00 }, /* 250 0.0 */ - { 0x0, 0x00, 0x00 }, /* 250 1.5 */ - { 0x0, 0x00, 0x00 }, /* 250 4.0 */ - { 0x0, 0x00, 0x00 }, /* 300 0.0 */ - { 0x0, 0x00, 0x00 }, /* 300 1.5 */ - { 0x0, 0x00, 0x00 }, /* 350 0.0 */ -}; - -/* Voltage Swing Programming for VccIO 1.05V for DP */ -static const struct icl_combo_phy_ddi_buf_trans icl_combo_phy_ddi_translations_dp_hdmi_1_05V[] = { - /* Voltage mV db */ - { 0x2, 0x98, 0x0018 }, /* 400 0.0 */ - { 0x2, 0x98, 0x3015 }, /* 400 3.5 */ - { 0x2, 0x98, 0x6012 }, /* 400 6.0 */ - { 0x2, 0x98, 0x900F }, /* 400 9.5 */ - { 0x4, 0x98, 0x0018 }, /* 600 0.0 */ - { 0x4, 0x98, 0x3015 }, /* 600 3.5 */ - { 0x4, 0x98, 0x6012 }, /* 600 6.0 */ - { 0x5, 0x71, 0x0018 }, /* 800 0.0 */ - { 0x5, 0x71, 0x3015 }, /* 800 3.5 */ - { 0x6, 0x98, 0x0018 }, /* 1200 0.0 */ -}; - -/* FIXME - After table is updated in Bspec */ -/* Voltage Swing Programming for VccIO 1.05V for eDP */ -static const struct icl_combo_phy_ddi_buf_trans icl_combo_phy_ddi_translations_edp_1_05V[] = { - /* Voltage mV db */ - { 0x0, 0x00, 0x00 }, /* 200 0.0 */ - { 0x0, 0x00, 0x00 }, /* 200 1.5 */ - { 0x0, 0x00, 0x00 }, /* 200 4.0 */ - { 0x0, 0x00, 0x00 }, /* 200 6.0 */ - { 0x0, 0x00, 0x00 }, /* 250 0.0 */ - { 0x0, 0x00, 0x00 }, /* 250 1.5 */ - { 0x0, 0x00, 0x00 }, /* 250 4.0 */ - { 0x0, 0x00, 0x00 }, /* 300 0.0 */ - { 0x0, 0x00, 0x00 }, /* 300 1.5 */ - { 0x0, 0x00, 0x00 }, /* 350 0.0 */ +static const struct cnl_ddi_buf_trans icl_combo_phy_ddi_translations_hdmi[] = { + /* NT mV Trans mV db */ + { 0xA, 0x60, 0x3F, 0x00, 0x00 }, /* 450 450 0.0 */ + { 0xB, 0x73, 0x36, 0x00, 0x09 }, /* 450 650 3.2 */ + { 0x6, 0x7F, 0x31, 0x00, 0x0E }, /* 450 850 5.5 */ + { 0xB, 0x73, 0x3F, 0x00, 0x00 }, /* 650 650 0.0 ALS */ + { 0x6, 0x7F, 0x37, 0x00, 0x08 }, /* 650 850 2.3 */ + { 0x6, 0x7F, 0x3F, 0x00, 0x00 }, /* 850 850 0.0 */ + { 0x6, 0x7F, 0x35, 0x00, 0x0A }, /* 600 850 3.0 */ }; struct icl_mg_phy_ddi_buf_trans { @@ -871,43 +826,23 @@ cnl_get_buf_trans_edp(struct drm_i915_private *dev_priv, int *n_entries) } } -static const struct icl_combo_phy_ddi_buf_trans * +static const struct cnl_ddi_buf_trans * icl_get_combo_buf_trans(struct drm_i915_private *dev_priv, enum port port, - int type, int *n_entries) + int type, int rate, int *n_entries) { - u32 voltage = I915_READ(ICL_PORT_COMP_DW3(port)) & VOLTAGE_INFO_MASK; - - if (type == INTEL_OUTPUT_EDP && dev_priv->vbt.edp.low_vswing) { - switch (voltage) { - case VOLTAGE_INFO_0_85V: - *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_edp_0_85V); - return icl_combo_phy_ddi_translations_edp_0_85V; - case VOLTAGE_INFO_0_95V: - *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_edp_0_95V); - return icl_combo_phy_ddi_translations_edp_0_95V; - case VOLTAGE_INFO_1_05V: - *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_edp_1_05V); - return icl_combo_phy_ddi_translations_edp_1_05V; - default: - MISSING_CASE(voltage); - return NULL; - } - } else { - switch (voltage) { - case VOLTAGE_INFO_0_85V: - *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_dp_hdmi_0_85V); - return icl_combo_phy_ddi_translations_dp_hdmi_0_85V; - case VOLTAGE_INFO_0_95V: - *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_dp_hdmi_0_95V); - return icl_combo_phy_ddi_translations_dp_hdmi_0_95V; - case VOLTAGE_INFO_1_05V: - *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_dp_hdmi_1_05V); - return icl_combo_phy_ddi_translations_dp_hdmi_1_05V; - default: - MISSING_CASE(voltage); - return NULL; - } + if (type == INTEL_OUTPUT_HDMI) { + *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_hdmi); + return icl_combo_phy_ddi_translations_hdmi; + } else if (rate > 540000 && type == INTEL_OUTPUT_EDP) { + *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_edp_hbr3); + return icl_combo_phy_ddi_translations_edp_hbr3; + } else if (type == INTEL_OUTPUT_EDP && dev_priv->vbt.edp.low_vswing) { + *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_edp_hbr2); + return icl_combo_phy_ddi_translations_edp_hbr2; } + + *n_entries = ARRAY_SIZE(icl_combo_phy_ddi_translations_dp_hbr2); + return icl_combo_phy_ddi_translations_dp_hbr2; } static int intel_ddi_hdmi_level(struct drm_i915_private *dev_priv, enum port port) @@ -918,8 +853,8 @@ static int intel_ddi_hdmi_level(struct drm_i915_private *dev_priv, enum port por if (IS_ICELAKE(dev_priv)) { if (intel_port_is_combophy(dev_priv, port)) - icl_get_combo_buf_trans(dev_priv, port, - INTEL_OUTPUT_HDMI, &n_entries); + icl_get_combo_buf_trans(dev_priv, port, INTEL_OUTPUT_HDMI, + 0, &n_entries); else n_entries = ARRAY_SIZE(icl_mg_phy_ddi_translations); default_entry = n_entries - 1; @@ -2275,13 +2210,14 @@ static void bxt_ddi_vswing_sequence(struct intel_encoder *encoder, u8 intel_ddi_dp_voltage_max(struct intel_encoder *encoder) { struct drm_i915_private *dev_priv = to_i915(encoder->base.dev); + struct intel_dp *intel_dp = enc_to_intel_dp(&encoder->base); enum port port = encoder->port; int n_entries; if (IS_ICELAKE(dev_priv)) { if (intel_port_is_combophy(dev_priv, port)) icl_get_combo_buf_trans(dev_priv, port, encoder->type, - &n_entries); + intel_dp->link_rate, &n_entries); else n_entries = ARRAY_SIZE(icl_mg_phy_ddi_translations); } else if (IS_CANNONLAKE(dev_priv)) { @@ -2462,14 +2398,15 @@ static void cnl_ddi_vswing_sequence(struct intel_encoder *encoder, } static void icl_ddi_combo_vswing_program(struct drm_i915_private *dev_priv, - u32 level, enum port port, int type) + u32 level, enum port port, int type, + int rate) { - const struct icl_combo_phy_ddi_buf_trans *ddi_translations = NULL; + const struct cnl_ddi_buf_trans *ddi_translations = NULL; u32 n_entries, val; int ln; ddi_translations = icl_get_combo_buf_trans(dev_priv, port, type, - &n_entries); + rate, &n_entries); if (!ddi_translations) return; @@ -2478,34 +2415,23 @@ static void icl_ddi_combo_vswing_program(struct drm_i915_private *dev_priv, level = n_entries - 1; } - /* Set PORT_TX_DW5 Rterm Sel to 110b. */ + /* Set PORT_TX_DW5 */ val = I915_READ(ICL_PORT_TX_DW5_LN0(port)); - val &= ~RTERM_SELECT_MASK; + val &= ~(SCALING_MODE_SEL_MASK | RTERM_SELECT_MASK | + TAP2_DISABLE | TAP3_DISABLE); + val |= SCALING_MODE_SEL(0x2); val |= RTERM_SELECT(0x6); - I915_WRITE(ICL_PORT_TX_DW5_GRP(port), val); - - /* Program PORT_TX_DW5 */ - val = I915_READ(ICL_PORT_TX_DW5_LN0(port)); - /* Set DisableTap2 and DisableTap3 if MIPI DSI - * Clear DisableTap2 and DisableTap3 for all other Ports - */ - if (type == INTEL_OUTPUT_DSI) { - val |= TAP2_DISABLE; - val |= TAP3_DISABLE; - } else { - val &= ~TAP2_DISABLE; - val &= ~TAP3_DISABLE; - } + val |= TAP3_DISABLE; I915_WRITE(ICL_PORT_TX_DW5_GRP(port), val); /* Program PORT_TX_DW2 */ val = I915_READ(ICL_PORT_TX_DW2_LN0(port)); val &= ~(SWING_SEL_LOWER_MASK | SWING_SEL_UPPER_MASK | RCOMP_SCALAR_MASK); - val |= SWING_SEL_UPPER(ddi_translations[level].dw2_swing_select); - val |= SWING_SEL_LOWER(ddi_translations[level].dw2_swing_select); + val |= SWING_SEL_UPPER(ddi_translations[level].dw2_swing_sel); + val |= SWING_SEL_LOWER(ddi_translations[level].dw2_swing_sel); /* Program Rcomp scalar for every table entry */ - val |= RCOMP_SCALAR(ddi_translations[level].dw2_swing_scalar); + val |= RCOMP_SCALAR(0x98); I915_WRITE(ICL_PORT_TX_DW2_GRP(port), val); /* Program PORT_TX_DW4 */ @@ -2514,9 +2440,17 @@ static void icl_ddi_combo_vswing_program(struct drm_i915_private *dev_priv, val = I915_READ(ICL_PORT_TX_DW4_LN(port, ln)); val &= ~(POST_CURSOR_1_MASK | POST_CURSOR_2_MASK | CURSOR_COEFF_MASK); - val |= ddi_translations[level].dw4_scaling; + val |= POST_CURSOR_1(ddi_translations[level].dw4_post_cursor_1); + val |= POST_CURSOR_2(ddi_translations[level].dw4_post_cursor_2); + val |= CURSOR_COEFF(ddi_translations[level].dw4_cursor_coeff); I915_WRITE(ICL_PORT_TX_DW4_LN(port, ln), val); } + + /* Program PORT_TX_DW7 */ + val = I915_READ(ICL_PORT_TX_DW7_LN0(port)); + val &= ~N_SCALAR_MASK; + val |= N_SCALAR(ddi_translations[level].dw7_n_scalar); + I915_WRITE(ICL_PORT_TX_DW7_GRP(port), val); } static void icl_combo_phy_ddi_vswing_sequence(struct intel_encoder *encoder, @@ -2581,7 +2515,7 @@ static void icl_combo_phy_ddi_vswing_sequence(struct intel_encoder *encoder, I915_WRITE(ICL_PORT_TX_DW5_GRP(port), val); /* 5. Program swing and de-emphasis */ - icl_ddi_combo_vswing_program(dev_priv, level, port, type); + icl_ddi_combo_vswing_program(dev_priv, level, port, type, rate); /* 6. Set training enable to trigger update */ val = I915_READ(ICL_PORT_TX_DW5_LN0(port)); diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 62484e129563..9b76c23226a7 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -304,9 +304,11 @@ static int cnl_max_source_rate(struct intel_dp *intel_dp) static int icl_max_source_rate(struct intel_dp *intel_dp) { struct intel_digital_port *dig_port = dp_to_dig_port(intel_dp); + struct drm_i915_private *dev_priv = to_i915(dig_port->base.base.dev); enum port port = dig_port->base.port; - if (port == PORT_B) + if (intel_port_is_combophy(dev_priv, port) && + !intel_dp_is_edp(intel_dp)) return 540000; return 810000; From 060f23225d8203b8cd9e412d984e5237e63c83dc Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Tue, 18 Dec 2018 10:27:12 +0000 Subject: [PATCH 051/118] drm/i915: Apply missed interrupt after reset w/a to all ringbuffer gen MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Having completed a test run of gem_eio across all machines in CI we also observe the phenomenon (of lost interrupts after resetting the GPU) on gen3 machines as well as the previously sighted gen6/gen7. Let's apply the same HWSTAM workaround that was effective for gen6+ for all, as although we haven't seen the same failure on gen4/5 it seems prudent to keep the code the same. As a consequence we can remove the extra setting of HWSTAM and apply the register from a single site. v2: Delazy and move the HWSTAM into its own function v3: Mask off all HWSP writes on driver unload and engine cleanup. v4: And what about the physical hwsp? v5: No, engine->init_hw() is not called from driver_init_hw(), don't be daft. Really scrub HWSTAM as early as we can in driver_init_mmio() v6: Rename set_hwsp as it was setting the mask not the hwsp register. v7: Ville pointed out that although vcs(bsd) was introduced for g4x/ilk, per-engine HWSTAM was not introduced until gen6! References: https://bugs.freedesktop.org/show_bug.cgi?id=108735 Signed-off-by: Chris Wilson Cc: Tvrtko Ursulin Cc: Ville Syrjälä Reviewed-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181218102712.11058-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_irq.c | 9 --- drivers/gpu/drm/i915/intel_engine_cs.c | 31 ++++++++ drivers/gpu/drm/i915/intel_lrc.c | 2 +- drivers/gpu/drm/i915/intel_ringbuffer.c | 101 +++++++++++++++--------- drivers/gpu/drm/i915/intel_ringbuffer.h | 2 + 5 files changed, 96 insertions(+), 49 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_irq.c b/drivers/gpu/drm/i915/i915_irq.c index e2dac9b5f4ce..0c7fc9890891 100644 --- a/drivers/gpu/drm/i915/i915_irq.c +++ b/drivers/gpu/drm/i915/i915_irq.c @@ -3586,9 +3586,6 @@ static void ironlake_irq_reset(struct drm_device *dev) { struct drm_i915_private *dev_priv = to_i915(dev); - if (IS_GEN(dev_priv, 5)) - I915_WRITE(HWSTAM, 0xffffffff); - GEN3_IRQ_RESET(DE); if (IS_GEN(dev_priv, 7)) I915_WRITE(GEN7_ERR_INT, 0xffffffff); @@ -4368,8 +4365,6 @@ static void i8xx_irq_reset(struct drm_device *dev) i9xx_pipestat_irq_reset(dev_priv); - I915_WRITE16(HWSTAM, 0xffff); - GEN2_IRQ_RESET(); } @@ -4537,8 +4532,6 @@ static void i915_irq_reset(struct drm_device *dev) i9xx_pipestat_irq_reset(dev_priv); - I915_WRITE(HWSTAM, 0xffffffff); - GEN3_IRQ_RESET(); } @@ -4648,8 +4641,6 @@ static void i965_irq_reset(struct drm_device *dev) i9xx_pipestat_irq_reset(dev_priv); - I915_WRITE(HWSTAM, 0xffffffff); - GEN3_IRQ_RESET(); } diff --git a/drivers/gpu/drm/i915/intel_engine_cs.c b/drivers/gpu/drm/i915/intel_engine_cs.c index 66d0ad9c36c4..561b474cbab1 100644 --- a/drivers/gpu/drm/i915/intel_engine_cs.c +++ b/drivers/gpu/drm/i915/intel_engine_cs.c @@ -261,6 +261,31 @@ static void __sprint_engine_name(char *name, const struct engine_info *info) info->instance) >= INTEL_ENGINE_CS_MAX_NAME); } +void intel_engine_set_hwsp_writemask(struct intel_engine_cs *engine, u32 mask) +{ + struct drm_i915_private *dev_priv = engine->i915; + i915_reg_t hwstam; + + /* + * Though they added more rings on g4x/ilk, they did not add + * per-engine HWSTAM until gen6. + */ + if (INTEL_GEN(dev_priv) < 6 && engine->class != RENDER_CLASS) + return; + + hwstam = RING_HWSTAM(engine->mmio_base); + if (INTEL_GEN(dev_priv) >= 3) + I915_WRITE(hwstam, mask); + else + I915_WRITE16(hwstam, mask); +} + +static void intel_engine_sanitize_mmio(struct intel_engine_cs *engine) +{ + /* Mask off all writes into the unknown HWSP */ + intel_engine_set_hwsp_writemask(engine, ~0u); +} + static int intel_engine_setup(struct drm_i915_private *dev_priv, enum intel_engine_id id) @@ -312,6 +337,9 @@ intel_engine_setup(struct drm_i915_private *dev_priv, ATOMIC_INIT_NOTIFIER_HEAD(&engine->context_status_notifier); + /* Scrub mmio state on takeover */ + intel_engine_sanitize_mmio(engine); + dev_priv->engine_class[info->class][info->instance] = engine; dev_priv->engine[id] = engine; return 0; @@ -495,6 +523,9 @@ void intel_engine_setup_common(struct intel_engine_cs *engine) static void cleanup_status_page(struct intel_engine_cs *engine) { + /* Prevent writes into HWSP after returning the page to the system */ + intel_engine_set_hwsp_writemask(engine, ~0u); + if (HWS_NEEDS_PHYSICAL(engine->i915)) { void *addr = fetch_and_zero(&engine->status_page.page_addr); diff --git a/drivers/gpu/drm/i915/intel_lrc.c b/drivers/gpu/drm/i915/intel_lrc.c index f16fb30da64f..4762c1e5b9e7 100644 --- a/drivers/gpu/drm/i915/intel_lrc.c +++ b/drivers/gpu/drm/i915/intel_lrc.c @@ -1655,7 +1655,7 @@ static void enable_execlists(struct intel_engine_cs *engine) { struct drm_i915_private *dev_priv = engine->i915; - I915_WRITE(RING_HWSTAM(engine->mmio_base), 0xffffffff); + intel_engine_set_hwsp_writemask(engine, ~0u); /* HWSTAM */ /* * Make sure we're not enabling the new 12-deep CSB diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.c b/drivers/gpu/drm/i915/intel_ringbuffer.c index fdeca2b877c9..65fd92eb071d 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.c +++ b/drivers/gpu/drm/i915/intel_ringbuffer.c @@ -379,11 +379,25 @@ gen7_render_ring_flush(struct i915_request *rq, u32 mode) return 0; } -static void ring_setup_phys_status_page(struct intel_engine_cs *engine) +static void set_hwstam(struct intel_engine_cs *engine, u32 mask) +{ + /* + * Keep the render interrupt unmasked as this papers over + * lost interrupts following a reset. + */ + if (engine->class == RENDER_CLASS) { + if (INTEL_GEN(engine->i915) >= 6) + mask &= ~BIT(0); + else + mask &= ~I915_USER_INTERRUPT; + } + + intel_engine_set_hwsp_writemask(engine, mask); +} + +static void set_hws_pga(struct intel_engine_cs *engine, phys_addr_t phys) { struct drm_i915_private *dev_priv = engine->i915; - struct page *page = virt_to_page(engine->status_page.page_addr); - phys_addr_t phys = PFN_PHYS(page_to_pfn(page)); u32 addr; addr = lower_32_bits(phys); @@ -393,12 +407,22 @@ static void ring_setup_phys_status_page(struct intel_engine_cs *engine) I915_WRITE(HWS_PGA, addr); } -static void intel_ring_setup_status_page(struct intel_engine_cs *engine) +static void ring_setup_phys_status_page(struct intel_engine_cs *engine) +{ + struct page *page = virt_to_page(engine->status_page.page_addr); + phys_addr_t phys = PFN_PHYS(page_to_pfn(page)); + + set_hws_pga(engine, phys); + set_hwstam(engine, ~0u); +} + +static void set_hwsp(struct intel_engine_cs *engine, u32 offset) { struct drm_i915_private *dev_priv = engine->i915; - i915_reg_t mmio; + i915_reg_t hwsp; - /* The ring status page addresses are no longer next to the rest of + /* + * The ring status page addresses are no longer next to the rest of * the ring registers as of gen7. */ if (IS_GEN(dev_priv, 7)) { @@ -410,56 +434,55 @@ static void intel_ring_setup_status_page(struct intel_engine_cs *engine) default: GEM_BUG_ON(engine->id); case RCS: - mmio = RENDER_HWS_PGA_GEN7; + hwsp = RENDER_HWS_PGA_GEN7; break; case BCS: - mmio = BLT_HWS_PGA_GEN7; + hwsp = BLT_HWS_PGA_GEN7; break; case VCS: - mmio = BSD_HWS_PGA_GEN7; + hwsp = BSD_HWS_PGA_GEN7; break; case VECS: - mmio = VEBOX_HWS_PGA_GEN7; + hwsp = VEBOX_HWS_PGA_GEN7; break; } } else if (IS_GEN(dev_priv, 6)) { - mmio = RING_HWS_PGA_GEN6(engine->mmio_base); + hwsp = RING_HWS_PGA_GEN6(engine->mmio_base); } else { - mmio = RING_HWS_PGA(engine->mmio_base); + hwsp = RING_HWS_PGA(engine->mmio_base); } - if (INTEL_GEN(dev_priv) >= 6) { - u32 mask = ~0u; + I915_WRITE(hwsp, offset); + POSTING_READ(hwsp); +} - /* - * Keep the render interrupt unmasked as this papers over - * lost interrupts following a reset. - */ - if (engine->id == RCS) - mask &= ~BIT(0); +static void flush_cs_tlb(struct intel_engine_cs *engine) +{ + struct drm_i915_private *dev_priv = engine->i915; + i915_reg_t instpm = RING_INSTPM(engine->mmio_base); - I915_WRITE(RING_HWSTAM(engine->mmio_base), mask); - } + if (!IS_GEN_RANGE(dev_priv, 6, 7)) + return; - I915_WRITE(mmio, engine->status_page.ggtt_offset); - POSTING_READ(mmio); + /* ring should be idle before issuing a sync flush*/ + WARN_ON((I915_READ_MODE(engine) & MODE_IDLE) == 0); - /* Flush the TLB for this page */ - if (IS_GEN_RANGE(dev_priv, 6, 7)) { - i915_reg_t reg = RING_INSTPM(engine->mmio_base); + I915_WRITE(instpm, + _MASKED_BIT_ENABLE(INSTPM_TLB_INVALIDATE | + INSTPM_SYNC_FLUSH)); + if (intel_wait_for_register(dev_priv, + instpm, INSTPM_SYNC_FLUSH, 0, + 1000)) + DRM_ERROR("%s: wait for SyncFlush to complete for TLB invalidation timed out\n", + engine->name); +} - /* ring should be idle before issuing a sync flush*/ - WARN_ON((I915_READ_MODE(engine) & MODE_IDLE) == 0); +static void ring_setup_status_page(struct intel_engine_cs *engine) +{ + set_hwsp(engine, engine->status_page.ggtt_offset); + set_hwstam(engine, ~0u); - I915_WRITE(reg, - _MASKED_BIT_ENABLE(INSTPM_TLB_INVALIDATE | - INSTPM_SYNC_FLUSH)); - if (intel_wait_for_register(dev_priv, - reg, INSTPM_SYNC_FLUSH, 0, - 1000)) - DRM_ERROR("%s: wait for SyncFlush to complete for TLB invalidation timed out\n", - engine->name); - } + flush_cs_tlb(engine); } static bool stop_ring(struct intel_engine_cs *engine) @@ -529,7 +552,7 @@ static int init_ring_common(struct intel_engine_cs *engine) if (HWS_NEEDS_PHYSICAL(dev_priv)) ring_setup_phys_status_page(engine); else - intel_ring_setup_status_page(engine); + ring_setup_status_page(engine); intel_engine_reset_breadcrumbs(engine); diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.h b/drivers/gpu/drm/i915/intel_ringbuffer.h index 1ae74e579386..6b41b9ce5f5b 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.h +++ b/drivers/gpu/drm/i915/intel_ringbuffer.h @@ -903,6 +903,8 @@ int intel_init_vebox_ring_buffer(struct intel_engine_cs *engine); int intel_engine_stop_cs(struct intel_engine_cs *engine); void intel_engine_cancel_stop_cs(struct intel_engine_cs *engine); +void intel_engine_set_hwsp_writemask(struct intel_engine_cs *engine, u32 mask); + u64 intel_engine_get_active_head(const struct intel_engine_cs *engine); u64 intel_engine_get_last_batch_head(const struct intel_engine_cs *engine); From f0236a852cd78b3a0ac03fd99b4c75bef778bc37 Mon Sep 17 00:00:00 2001 From: Imre Deak Date: Fri, 14 Dec 2018 20:27:00 +0200 Subject: [PATCH 052/118] drm/i915/icl: Add a debug print for TypeC port disconnection MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's useful to see at which point a TypeC port gets disconnected, so add a debug print for it. Cc: Paulo Zanoni Cc: Ville Syrjälä Cc: José Roberto de Souza Cc: Rodrigo Vivi Signed-off-by: Imre Deak Reviewed-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181214182703.18865-2-imre.deak@intel.com --- drivers/gpu/drm/i915/intel_dp.c | 34 +++++++++++++++++++++++---------- 1 file changed, 24 insertions(+), 10 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 9b76c23226a7..3afc3215692b 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -5069,28 +5069,38 @@ static bool icl_combo_port_connected(struct drm_i915_private *dev_priv, return I915_READ(SDEISR) & SDE_DDI_HOTPLUG_ICP(port); } +static const char *tc_type_name(enum tc_port_type type) +{ + static const char * const names[] = { + [TC_PORT_UNKNOWN] = "unknown", + [TC_PORT_LEGACY] = "legacy", + [TC_PORT_TYPEC] = "typec", + [TC_PORT_TBT] = "tbt", + }; + + if (WARN_ON(type >= ARRAY_SIZE(names))) + type = TC_PORT_UNKNOWN; + + return names[type]; +} + static void icl_update_tc_port_type(struct drm_i915_private *dev_priv, struct intel_digital_port *intel_dig_port, bool is_legacy, bool is_typec, bool is_tbt) { enum port port = intel_dig_port->base.port; enum tc_port_type old_type = intel_dig_port->tc_type; - const char *type_str; WARN_ON(is_legacy + is_typec + is_tbt != 1); - if (is_legacy) { + if (is_legacy) intel_dig_port->tc_type = TC_PORT_LEGACY; - type_str = "legacy"; - } else if (is_typec) { + else if (is_typec) intel_dig_port->tc_type = TC_PORT_TYPEC; - type_str = "typec"; - } else if (is_tbt) { + else if (is_tbt) intel_dig_port->tc_type = TC_PORT_TBT; - type_str = "tbt"; - } else { + else return; - } /* Types are not supposed to be changed at runtime. */ WARN_ON(old_type != TC_PORT_UNKNOWN && @@ -5098,7 +5108,7 @@ static void icl_update_tc_port_type(struct drm_i915_private *dev_priv, if (old_type != intel_dig_port->tc_type) DRM_DEBUG_KMS("Port %c has TC type %s\n", port_name(port), - type_str); + tc_type_name(intel_dig_port->tc_type)); } static void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv, @@ -5190,6 +5200,10 @@ static void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv, I915_WRITE(PORT_TX_DFLEXDPCSSS, val); } + DRM_DEBUG_KMS("Port %c TC type %s disconnected\n", + port_name(dig_port->base.port), + tc_type_name(dig_port->tc_type)); + dig_port->tc_type = TC_PORT_UNKNOWN; } From 38b3416f3c2f1dafcf84a8c54eeee9f3bc50ffaa Mon Sep 17 00:00:00 2001 From: Imre Deak Date: Fri, 14 Dec 2018 20:27:01 +0200 Subject: [PATCH 053/118] drm/i915/bios: Parse the VBT TypeC and Thunderbolt port flags MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is needed by the next patch to determine if a DDI TypeC port is physically wired to a legacy DP or legacy HDMI connector or if the port is wired to a USB-C/Thunderbolt connector. Cc: Jani Nikula Cc: Paulo Zanoni Cc: Ville Syrjälä Cc: José Roberto de Souza Cc: Rodrigo Vivi Signed-off-by: Imre Deak Reviewed-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181214182703.18865-3-imre.deak@intel.com --- drivers/gpu/drm/i915/i915_drv.h | 2 ++ drivers/gpu/drm/i915/intel_bios.c | 11 +++++++++-- 2 files changed, 11 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index c34198f51b13..815db160b966 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -935,6 +935,8 @@ struct ddi_vbt_port_info { uint8_t supports_hdmi:1; uint8_t supports_dp:1; uint8_t supports_edp:1; + uint8_t supports_typec_usb:1; + uint8_t supports_tbt:1; uint8_t alternate_aux_channel; uint8_t alternate_ddc_pin; diff --git a/drivers/gpu/drm/i915/intel_bios.c b/drivers/gpu/drm/i915/intel_bios.c index 7b7e7abfa259..764d84d4109b 100644 --- a/drivers/gpu/drm/i915/intel_bios.c +++ b/drivers/gpu/drm/i915/intel_bios.c @@ -1386,8 +1386,15 @@ static void parse_ddi_port(struct drm_i915_private *dev_priv, enum port port, info->supports_dp = is_dp; info->supports_edp = is_edp; - DRM_DEBUG_KMS("Port %c VBT info: DP:%d HDMI:%d DVI:%d EDP:%d CRT:%d\n", - port_name(port), is_dp, is_hdmi, is_dvi, is_edp, is_crt); + if (bdb_version >= 195) + info->supports_typec_usb = child->dp_usb_type_c; + + if (bdb_version >= 209) + info->supports_tbt = child->tbt; + + DRM_DEBUG_KMS("Port %c VBT info: DP:%d HDMI:%d DVI:%d EDP:%d CRT:%d TCUSB:%d TBT:%d\n", + port_name(port), is_dp, is_hdmi, is_dvi, is_edp, is_crt, + info->supports_typec_usb, info->supports_tbt); if (is_edp && is_dvi) DRM_DEBUG_KMS("Internal DP port %c is TMDS compatible\n", From f6bff60e927b2f1e2bc87a6b7f412b87bf289712 Mon Sep 17 00:00:00 2001 From: Imre Deak Date: Fri, 14 Dec 2018 20:27:02 +0200 Subject: [PATCH 054/118] drm/i915/icl: Fix HPD handling for TypeC legacy ports MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Atm HPD disconnect events on TypeC ports will break things, since we'll switch the TypeC mode (between legacy and disconnected modes as well as among USB DP alternate, Thunderbolt alternate and disconnected modes) on the fly from the HPD disconnect interrupt work while the port may be still active. Even if the port happens to be not active during the disconnect we'd still have a problem during a subsequent modeset or AUX transfer that could happen regardless of the port's connected state. For instance the system resume display mode restore code and userspace could perform a modeset on the port or userspace could start an AUX transfer even if the port is in disconnected state. To fix this keep TypeC legacy ports in legacy mode whenever we're not suspended. This mode is a static configuration as opposed to the Thunderbolt and USB DP alternate modes between which we can switch dynamically. We determine if a TypeC port is legacy (wired to a legacy HDMI or a legacy DP connector) via the VBT DDI port specific USB-TypeC and Thunderbolt flags. If both these flags are cleared then the port is configured for legacy mode. On such legacy ports we'll run the TypeC PHY connect sequence explicitly during driver loading and system resume (vs. running the sequence during HPD processing). The connect will succeed even if the display is not connected to begin with (or disappears during the suspended state) since for legacy ports the PORT_TX_DFLEXDPPMS / DP_PHY_MODE_STATUS_COMPLETED flag is always set (as opposed to the USB DP alternate mode where it gets set only when a display is connected). Correspondingly run the TypeC PHY disconnect sequence during system suspend and driver unloading. For the unloading case I had to split up intel_dp_encoder_destroy() to be able to have the 1. flush any pending encoder work, 2. disconnect TC PHY, 3. call DRM core cleanup and kfree on the encoder object. For now run the PHY disconnect during suspend only for TypeC legacy ports. We will need to disconnect even in USB DP alternate mode in the future, but atm we don't have a way to reconnect the port in this mode during resume if the display disappears while being suspended. So for now punt on this case. Note that we do not disconnect the port during runtime suspend; in legacy mode there are no shared HW resources (PHY lanes) with other HW blocks (USB), so no need to release / reacquire these resources as with USB DP alternate mode. The only reason to disconnect legacy ports during system suspend is that the PORT_TX_DFLEXDPPMS / DP_PHY_MODE_STATUS_COMPLETED flag must be rechecked and the port must be connected again during system resume. We'll also have to turn the check for this flag into a poll, after figuring out what's the proper timeout value for it. v2: - Remove the redundant special casing of legacy mode when doing a disconnect in icl_tc_port_connected(). It's guaranteed already that we won't disconnect legacy ports in that function. - Add a note about the new intel_ddi_encoder_destroy() hook. - Reword the commit message after switching to the VBT based detection. Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=108070 Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=108924 Cc: Paulo Zanoni Cc: Ville Syrjälä Cc: José Roberto de Souza Cc: Rodrigo Vivi Signed-off-by: Imre Deak Reviewed-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181214182703.18865-4-imre.deak@intel.com --- drivers/gpu/drm/i915/intel_ddi.c | 63 ++++++++++++++++++++++++++++---- drivers/gpu/drm/i915/intel_dp.c | 21 +++++++---- drivers/gpu/drm/i915/intel_drv.h | 5 ++- 3 files changed, 73 insertions(+), 16 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index dfd35822cdab..e3cc19e19199 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -3834,9 +3834,50 @@ static bool intel_ddi_compute_config(struct intel_encoder *encoder, } +static void intel_ddi_encoder_suspend(struct intel_encoder *encoder) +{ + struct intel_digital_port *dig_port = enc_to_dig_port(&encoder->base); + struct drm_i915_private *i915 = to_i915(encoder->base.dev); + + intel_dp_encoder_suspend(encoder); + + /* + * TODO: disconnect also from USB DP alternate mode once we have a + * way to handle the modeset restore in that mode during resume + * even if the sink has disappeared while being suspended. + */ + if (dig_port->tc_legacy_port) + icl_tc_phy_disconnect(i915, dig_port); +} + +static void intel_ddi_encoder_reset(struct drm_encoder *drm_encoder) +{ + struct intel_digital_port *dig_port = enc_to_dig_port(drm_encoder); + struct drm_i915_private *i915 = to_i915(drm_encoder->dev); + + if (intel_port_is_tc(i915, dig_port->base.port)) + intel_digital_port_connected(&dig_port->base); + + intel_dp_encoder_reset(drm_encoder); +} + +static void intel_ddi_encoder_destroy(struct drm_encoder *encoder) +{ + struct intel_digital_port *dig_port = enc_to_dig_port(encoder); + struct drm_i915_private *i915 = to_i915(encoder->dev); + + intel_dp_encoder_flush_work(encoder); + + if (intel_port_is_tc(i915, dig_port->base.port)) + icl_tc_phy_disconnect(i915, dig_port); + + drm_encoder_cleanup(encoder); + kfree(dig_port); +} + static const struct drm_encoder_funcs intel_ddi_funcs = { - .reset = intel_dp_encoder_reset, - .destroy = intel_dp_encoder_destroy, + .reset = intel_ddi_encoder_reset, + .destroy = intel_ddi_encoder_destroy, }; static struct intel_connector * @@ -4080,16 +4121,16 @@ intel_ddi_max_lanes(struct intel_digital_port *intel_dport) void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port) { + struct ddi_vbt_port_info *port_info = + &dev_priv->vbt.ddi_port_info[port]; struct intel_digital_port *intel_dig_port; struct intel_encoder *intel_encoder; struct drm_encoder *encoder; bool init_hdmi, init_dp, init_lspcon = false; enum pipe pipe; - - init_hdmi = (dev_priv->vbt.ddi_port_info[port].supports_dvi || - dev_priv->vbt.ddi_port_info[port].supports_hdmi); - init_dp = dev_priv->vbt.ddi_port_info[port].supports_dp; + init_hdmi = port_info->supports_dvi || port_info->supports_hdmi; + init_dp = port_info->supports_dp; if (intel_bios_is_lspcon_present(dev_priv, port)) { /* @@ -4130,7 +4171,7 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port) intel_encoder->post_disable = intel_ddi_post_disable; intel_encoder->get_hw_state = intel_ddi_get_hw_state; intel_encoder->get_config = intel_ddi_get_config; - intel_encoder->suspend = intel_dp_encoder_suspend; + intel_encoder->suspend = intel_ddi_encoder_suspend; intel_encoder->get_power_domains = intel_ddi_get_power_domains; intel_encoder->type = INTEL_OUTPUT_DDI; intel_encoder->power_domain = intel_port_to_power_domain(port); @@ -4149,6 +4190,10 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port) intel_dig_port->max_lanes = intel_ddi_max_lanes(intel_dig_port); intel_dig_port->aux_ch = intel_bios_port_aux_ch(dev_priv, port); + intel_dig_port->tc_legacy_port = intel_port_is_tc(dev_priv, port) && + !port_info->supports_typec_usb && + !port_info->supports_tbt; + switch (port) { case PORT_A: intel_dig_port->ddi_io_power_domain = @@ -4207,6 +4252,10 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port) } intel_infoframe_init(intel_dig_port); + + if (intel_port_is_tc(dev_priv, port)) + intel_digital_port_connected(intel_encoder); + return; err: diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 3afc3215692b..a9f22a366337 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -5111,9 +5111,6 @@ static void icl_update_tc_port_type(struct drm_i915_private *dev_priv, tc_type_name(intel_dig_port->tc_type)); } -static void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv, - struct intel_digital_port *dig_port); - /* * This function implements the first part of the Connect Flow described by our * specification, Gen11 TypeC Programming chapter. The rest of the flow (reading @@ -5148,6 +5145,7 @@ static bool icl_tc_phy_connect(struct drm_i915_private *dev_priv, val = I915_READ(PORT_TX_DFLEXDPPMS); if (!(val & DP_PHY_MODE_STATUS_COMPLETED(tc_port))) { DRM_DEBUG_KMS("DP PHY for TC port %d not ready\n", tc_port); + WARN_ON(dig_port->tc_legacy_port); return false; } @@ -5179,8 +5177,8 @@ static bool icl_tc_phy_connect(struct drm_i915_private *dev_priv, * See the comment at the connect function. This implements the Disconnect * Flow. */ -static void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv, - struct intel_digital_port *dig_port) +void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv, + struct intel_digital_port *dig_port) { enum tc_port tc_port = intel_port_to_tc(dev_priv, dig_port->base.port); @@ -5225,7 +5223,8 @@ static bool icl_tc_port_connected(struct drm_i915_private *dev_priv, bool is_legacy, is_typec, is_tbt; u32 dpsp; - is_legacy = I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port); + is_legacy = intel_dig_port->tc_legacy_port || + I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port); /* * The spec says we shouldn't be using the ISR bits for detecting @@ -5237,6 +5236,7 @@ static bool icl_tc_port_connected(struct drm_i915_private *dev_priv, if (!is_legacy && !is_typec && !is_tbt) { icl_tc_phy_disconnect(dev_priv, intel_dig_port); + return false; } @@ -5545,7 +5545,7 @@ intel_dp_connector_unregister(struct drm_connector *connector) intel_connector_unregister(connector); } -void intel_dp_encoder_destroy(struct drm_encoder *encoder) +void intel_dp_encoder_flush_work(struct drm_encoder *encoder) { struct intel_digital_port *intel_dig_port = enc_to_dig_port(encoder); struct intel_dp *intel_dp = &intel_dig_port->dp; @@ -5568,9 +5568,14 @@ void intel_dp_encoder_destroy(struct drm_encoder *encoder) } intel_dp_aux_fini(intel_dp); +} + +static void intel_dp_encoder_destroy(struct drm_encoder *encoder) +{ + intel_dp_encoder_flush_work(encoder); drm_encoder_cleanup(encoder); - kfree(intel_dig_port); + kfree(enc_to_dig_port(encoder)); } void intel_dp_encoder_suspend(struct intel_encoder *intel_encoder) diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index cb3a055f18c8..1028af8ec2eb 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -1237,6 +1237,7 @@ struct intel_digital_port { /* Used for DP and ICL+ TypeC/DP and TypeC/HDMI ports. */ enum aux_ch aux_ch; enum intel_display_power_domain ddi_io_power_domain; + bool tc_legacy_port:1; enum tc_port_type tc_type; void (*write_infoframe)(struct intel_encoder *encoder, @@ -1809,7 +1810,7 @@ void intel_dp_sink_set_decompression_state(struct intel_dp *intel_dp, bool enable); void intel_dp_encoder_reset(struct drm_encoder *encoder); void intel_dp_encoder_suspend(struct intel_encoder *intel_encoder); -void intel_dp_encoder_destroy(struct drm_encoder *encoder); +void intel_dp_encoder_flush_work(struct drm_encoder *encoder); bool intel_dp_compute_config(struct intel_encoder *encoder, struct intel_crtc_state *pipe_config, struct drm_connector_state *conn_state); @@ -1877,6 +1878,8 @@ bool intel_dp_read_dpcd(struct intel_dp *intel_dp); int intel_dp_link_required(int pixel_clock, int bpp); int intel_dp_max_data_rate(int max_link_clock, int max_lanes); bool intel_digital_port_connected(struct intel_encoder *encoder); +void icl_tc_phy_disconnect(struct drm_i915_private *dev_priv, + struct intel_digital_port *dig_port); /* intel_dp_aux_backlight.c */ int intel_dp_aux_init_backlight_funcs(struct intel_connector *intel_connector); From 2a041c97c3bceab8b7f133658c22659e4a81bd75 Mon Sep 17 00:00:00 2001 From: Imre Deak Date: Fri, 14 Dec 2018 20:27:03 +0200 Subject: [PATCH 055/118] drm/i915/icl: Add fallback detection method for TypeC legacy ports MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add a fallback detection method for TypeC legacy ports in case the VBT port information used to detect normally such ports is incorrect. For the fallback method we use the TypeC legacy mode specific HPD interrupt flag which should only be raised for a legacy port. WARN if the VBT port info is incorrect. In a case where we'd detect the port in a contradicting way both as a legacy and also as a USB DP and/or TBT alternate port treat the port as legacy (by also emitting a WARN from icl_update_tc_port_type). v2: - Repurpose the detection as a fallback method instead of using it only for the DP legacy case. By now we should normally use VBT to detect DP legacy ports as well. Suggested-by: Ville Syrjälä Cc: Paulo Zanoni Cc: Ville Syrjälä Cc: José Roberto de Souza Cc: Rodrigo Vivi Signed-off-by: Imre Deak Reviewed-by: Rodrigo Vivi (v1) Reviewed-by: Mika Kahola Link: https://patchwork.freedesktop.org/patch/msgid/20181214182703.18865-5-imre.deak@intel.com --- drivers/gpu/drm/i915/intel_dp.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index a9f22a366337..5b601b754707 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -5223,8 +5223,14 @@ static bool icl_tc_port_connected(struct drm_i915_private *dev_priv, bool is_legacy, is_typec, is_tbt; u32 dpsp; - is_legacy = intel_dig_port->tc_legacy_port || - I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port); + /* + * WARN if we got a legacy port HPD, but VBT didn't mark the port as + * legacy. Treat the port as legacy from now on. + */ + if (WARN_ON(!intel_dig_port->tc_legacy_port && + I915_READ(SDEISR) & SDE_TC_HOTPLUG_ICP(tc_port))) + intel_dig_port->tc_legacy_port = true; + is_legacy = intel_dig_port->tc_legacy_port; /* * The spec says we shouldn't be using the ISR bits for detecting From 6afe8925a297a0458248e5e8b13dab91e782337e Mon Sep 17 00:00:00 2001 From: Manasi Navare Date: Wed, 19 Dec 2018 15:51:20 -0800 Subject: [PATCH 056/118] drm/i915/dsc: Fix the deadlock in dsc debugfs node The DSC debugfs node causes a possible deadlock situation. This patch resets the try_again at the beginning of loop to fix this. Fixes: e845f099f1c6 ('drm/i915/dsc: Add Per connector debugfs node for DSC support/enable') Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=109097 Cc: Lyude Paul Cc: Chris Wilson Signed-off-by: Manasi Navare Reviewed-by: Lyude Paul Signed-off-by: Chris Wilson Link: https://patchwork.freedesktop.org/patch/msgid/20181219235120.21816-1-manasi.d.navare@intel.com --- drivers/gpu/drm/i915/i915_debugfs.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 77486a614614..aca26a25ed50 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -5108,6 +5108,7 @@ static int i915_dsc_fec_support_show(struct seq_file *m, void *data) drm_modeset_acquire_init(&ctx, DRM_MODESET_ACQUIRE_INTERRUPTIBLE); do { + try_again = false; ret = drm_modeset_lock(&dev->mode_config.connection_mutex, &ctx); if (ret) { From 50c42fc90b7e1f1800f2d883ef86770e9cb6251e Mon Sep 17 00:00:00 2001 From: Maarten Lankhorst Date: Thu, 20 Dec 2018 16:17:19 +0100 Subject: [PATCH 057/118] drm/i915: Disable FBC on fastset if necessary, v2. Without this, we will get a dmesg-warn when enable_fbc is cleared on a fastset: WARN_ON(!crtc_state->enable_fbc) WARNING: CPU: 0 PID: 1090 at drivers/gpu/drm/i915/intel_fbc.c:1091 intel_fbc_enable+0x2ce/0x580 [i915] RIP: 0010:intel_fbc_enable+0x2ce/0x580 [i915] Call Trace: ? __mutex_unlock_slowpath+0x46/0x2b0 intel_update_crtc+0x6f/0x2b0 [i915] skl_update_crtcs+0x1d1/0x2b0 [i915] intel_atomic_commit_tail+0x1ea/0xdb0 [i915] intel_atomic_commit+0x244/0x330 [i915] drm_mode_atomic_ioctl+0x85d/0x950 ? drm_atomic_set_property+0x970/0x970 drm_ioctl_kernel+0x81/0xf0 drm_ioctl+0x2de/0x390 ? drm_atomic_set_property+0x970/0x970 ? __handle_mm_fault+0x81b/0xfc0 do_vfs_ioctl+0xa0/0x6e0 ? __do_page_fault+0x2a5/0x550 ksys_ioctl+0x35/0x60 __x64_sys_ioctl+0x11/0x20 do_syscall_64+0x55/0x190 entry_SYSCALL_64_after_hwframe+0x49/0xbe Changes since v1: - Move intel_fbc_disable to intel_update_crtc() (Hans) Cc: Hans de Goede Signed-off-by: Maarten Lankhorst Link: https://patchwork.freedesktop.org/patch/msgid/20181220151719.30586-1-maarten.lankhorst@linux.intel.com Reviewed-by: Hans de Goede --- drivers/gpu/drm/i915/intel_display.c | 4 +++- drivers/gpu/drm/i915/intel_fbc.c | 2 -- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index 3b7094822aa9..a0ec74e1e8e1 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -12752,7 +12752,9 @@ static void intel_update_crtc(struct drm_crtc *crtc, pipe_config); } - if (new_plane_state) + if (pipe_config->update_pipe && !pipe_config->enable_fbc) + intel_fbc_disable(intel_crtc); + else if (new_plane_state) intel_fbc_enable(intel_crtc, pipe_config, new_plane_state); intel_begin_crtc_commit(crtc, old_crtc_state); diff --git a/drivers/gpu/drm/i915/intel_fbc.c b/drivers/gpu/drm/i915/intel_fbc.c index 1d3ff026d1bc..ccd5e110a19c 100644 --- a/drivers/gpu/drm/i915/intel_fbc.c +++ b/drivers/gpu/drm/i915/intel_fbc.c @@ -1129,8 +1129,6 @@ void intel_fbc_disable(struct intel_crtc *crtc) if (!fbc_supported(dev_priv)) return; - WARN_ON(crtc->active); - mutex_lock(&fbc->lock); if (fbc->crtc == crtc) __intel_fbc_disable(dev_priv); From a5b79d34000b8f32c84be19e0565187e9613e5e9 Mon Sep 17 00:00:00 2001 From: Paulo Zanoni Date: Tue, 13 Nov 2018 17:24:32 -0800 Subject: [PATCH 058/118] drm/i915: don't apply Display WAs 1125 and 1126 to GLK/CNL+ MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit BSpec does not show these WAs as applicable to GLK, and for CNL it only shows them applicable for a super early pre-production stepping we shouldn't be caring about anymore. Remove these so we can avoid them on ICL too. v2: Change how we check for gen9 display platforms (Ville). Cc: Matt Roper Reviewed-by: Ville Syrjälä Signed-off-by: Paulo Zanoni Signed-off-by: Ville Syrjälä Link: https://patchwork.freedesktop.org/patch/msgid/20181114012432.21809-1-paulo.r.zanoni@intel.com --- drivers/gpu/drm/i915/intel_pm.c | 43 ++++++++++++++++++--------------- 1 file changed, 23 insertions(+), 20 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index b11fac679e10..2a6ffb8b975a 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -4730,28 +4730,31 @@ static void skl_compute_plane_wm(const struct intel_crtc_state *cstate, res_lines = div_round_up_fixed16(selected_result, wp->plane_blocks_per_line); - /* Display WA #1125: skl,bxt,kbl,glk */ - if (level == 0 && wp->rc_surface) - res_blocks += fixed16_to_u32_round_up(wp->y_tile_minimum); + if (IS_GEN9_BC(dev_priv) || IS_BROXTON(dev_priv)) { + /* Display WA #1125: skl,bxt,kbl */ + if (level == 0 && wp->rc_surface) + res_blocks += + fixed16_to_u32_round_up(wp->y_tile_minimum); - /* Display WA #1126: skl,bxt,kbl,glk */ - if (level >= 1 && level <= 7) { - if (wp->y_tiled) { - res_blocks += fixed16_to_u32_round_up( - wp->y_tile_minimum); - res_lines += wp->y_min_scanlines; - } else { - res_blocks++; + /* Display WA #1126: skl,bxt,kbl */ + if (level >= 1 && level <= 7) { + if (wp->y_tiled) { + res_blocks += + fixed16_to_u32_round_up(wp->y_tile_minimum); + res_lines += wp->y_min_scanlines; + } else { + res_blocks++; + } + + /* + * Make sure result blocks for higher latency levels are + * atleast as high as level below the current level. + * Assumption in DDB algorithm optimization for special + * cases. Also covers Display WA #1125 for RC. + */ + if (result_prev->plane_res_b > res_blocks) + res_blocks = result_prev->plane_res_b; } - - /* - * Make sure result blocks for higher latency levels are atleast - * as high as level below the current level. - * Assumption in DDB algorithm optimization for special cases. - * Also covers Display WA #1125 for RC. - */ - if (result_prev->plane_res_b > res_blocks) - res_blocks = result_prev->plane_res_b; } /* The number of lines are ignored for the level 0 watermark. */ From ce98528b3f619825c81f66c515c9ff07eda70f48 Mon Sep 17 00:00:00 2001 From: Rodrigo Vivi Date: Fri, 21 Dec 2018 11:12:44 -0800 Subject: [PATCH 059/118] drm/i915: Update DRIVER_DATE to 20181221 Signed-off-by: Rodrigo Vivi --- drivers/gpu/drm/i915/i915_drv.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 815db160b966..436c508f1b9d 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -90,8 +90,8 @@ #define DRIVER_NAME "i915" #define DRIVER_DESC "Intel Graphics" -#define DRIVER_DATE "20181204" -#define DRIVER_TIMESTAMP 1543944377 +#define DRIVER_DATE "20181221" +#define DRIVER_TIMESTAMP 1545419564 /* Use I915_STATE_WARN(x) and I915_STATE_WARN_ON() (rather than WARN() and * WARN_ON()) for hw state sanity checks to check for unexpected conditions From 17960f35f146258a5e6e4b1dc83bd6f16aa349a5 Mon Sep 17 00:00:00 2001 From: Rodrigo Vivi Date: Fri, 21 Dec 2018 12:04:38 -0800 Subject: [PATCH 060/118] drm/i915: Update DRIVER_DATE to 20181221 Signed-off-by: Rodrigo Vivi --- drivers/gpu/drm/i915/i915_drv.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index 436c508f1b9d..d44255a8655e 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h @@ -91,7 +91,7 @@ #define DRIVER_NAME "i915" #define DRIVER_DESC "Intel Graphics" #define DRIVER_DATE "20181221" -#define DRIVER_TIMESTAMP 1545419564 +#define DRIVER_TIMESTAMP 1545422678 /* Use I915_STATE_WARN(x) and I915_STATE_WARN_ON() (rather than WARN() and * WARN_ON()) for hw state sanity checks to check for unexpected conditions From d4de753526f4d99f541f1b6ed1d963005c09700c Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Sat, 22 Dec 2018 03:06:23 +0000 Subject: [PATCH 061/118] drm/i915: Unwind failure on pinning the gen7 ppgtt If we fail to pin the ggtt vma slot for the ppgtt page tables, we need to unwind the locals before reporting the error. Or else on subsequent attempts to bind the page tables into the ggtt, we will already believe that the vma has been pinned and continue on blithely. If something else should happen to be at that location, choas ensues. Fixes: a2bbf7148342 ("drm/i915/gtt: Only keep gen6 page directories pinned while active") Signed-off-by: Chris Wilson Cc: Joonas Lahtinen Cc: Mika Kuoppala Cc: Matthew Auld Cc: # v4.19+ Reviewed-by: Matthew Auld Link: https://patchwork.freedesktop.org/patch/msgid/20181222030623.21710-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_gem_gtt.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index 6e31745f6156..4ed2f3e61347 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -2073,6 +2073,7 @@ static struct i915_vma *pd_vma_create(struct gen6_hw_ppgtt *ppgtt, int size) int gen6_ppgtt_pin(struct i915_hw_ppgtt *base) { struct gen6_hw_ppgtt *ppgtt = to_gen6_ppgtt(base); + int err; /* * Workaround the limited maximum vma->pin_count and the aliasing_ppgtt @@ -2088,9 +2089,17 @@ int gen6_ppgtt_pin(struct i915_hw_ppgtt *base) * allocator works in address space sizes, so it's multiplied by page * size. We allocate at the top of the GTT to avoid fragmentation. */ - return i915_vma_pin(ppgtt->vma, - 0, GEN6_PD_ALIGN, - PIN_GLOBAL | PIN_HIGH); + err = i915_vma_pin(ppgtt->vma, + 0, GEN6_PD_ALIGN, + PIN_GLOBAL | PIN_HIGH); + if (err) + goto unpin; + + return 0; + +unpin: + ppgtt->pin_count = 0; + return err; } void gen6_ppgtt_unpin(struct i915_hw_ppgtt *base) From 608ed4ab240f2d09f2fc1e5f8631dfe8570f9f80 Mon Sep 17 00:00:00 2001 From: Hans de Goede Date: Thu, 20 Dec 2018 14:21:18 +0100 Subject: [PATCH 062/118] drm/i915: Add an update_pipe callback to intel_encoder and call this on fastsets (v2) When we are doing a fastset (needs_modeset=false, update_pipe=true) we may need to update some encoder-level things such as checking that PSR is enabled. This commit adds an update_pipe callback to intel_encoder and a new intel_encoders_update_pipe helper which calls this for all encoders connected to a crtc. The new intel_encoders_update_pipe helper is called from intel_update_crtc when doing a fastset. Changes in v2: -Name the new encoder callback update_pipe instead of just update Reviewed-by: Maarten Lankhorst Signed-off-by: Hans de Goede Link: https://patchwork.freedesktop.org/patch/msgid/20181220132120.15318-1-hdegoede@redhat.com --- drivers/gpu/drm/i915/intel_display.c | 23 +++++++++++++++++++++++ drivers/gpu/drm/i915/intel_drv.h | 3 +++ 2 files changed, 26 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index a0ec74e1e8e1..f0b480fba980 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c @@ -5578,6 +5578,26 @@ static void intel_encoders_post_pll_disable(struct drm_crtc *crtc, } } +static void intel_encoders_update_pipe(struct drm_crtc *crtc, + struct intel_crtc_state *crtc_state, + struct drm_atomic_state *old_state) +{ + struct drm_connector_state *conn_state; + struct drm_connector *conn; + int i; + + for_each_new_connector_in_state(old_state, conn, conn_state, i) { + struct intel_encoder *encoder = + to_intel_encoder(conn_state->best_encoder); + + if (conn_state->crtc != crtc) + continue; + + if (encoder->update_pipe) + encoder->update_pipe(encoder, crtc_state, conn_state); + } +} + static void ironlake_crtc_enable(struct intel_crtc_state *pipe_config, struct drm_atomic_state *old_state) { @@ -12750,6 +12770,9 @@ static void intel_update_crtc(struct drm_crtc *crtc, } else { intel_pre_plane_update(to_intel_crtc_state(old_crtc_state), pipe_config); + + if (pipe_config->update_pipe) + intel_encoders_update_pipe(crtc, pipe_config, state); } if (pipe_config->update_pipe && !pipe_config->enable_fbc) diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h index 1028af8ec2eb..1a11c2beb7f3 100644 --- a/drivers/gpu/drm/i915/intel_drv.h +++ b/drivers/gpu/drm/i915/intel_drv.h @@ -243,6 +243,9 @@ struct intel_encoder { void (*post_pll_disable)(struct intel_encoder *, const struct intel_crtc_state *, const struct drm_connector_state *); + void (*update_pipe)(struct intel_encoder *, + const struct intel_crtc_state *, + const struct drm_connector_state *); /* Read out the current hw state of this connector, returning true if * the encoder is active. If the encoder is enabled it also set the pipe * it is connected to in the pipe parameter. */ From f69a0d71d49cbd22dab85e9654ec7a8fc7a7d057 Mon Sep 17 00:00:00 2001 From: Hans de Goede Date: Thu, 20 Dec 2018 14:21:19 +0100 Subject: [PATCH 063/118] drm/i915: Allow calling intel_edp_drrs_enable twice Do not make it an error to call intel_edp_drrs_enable while drrs has already been enabled, instead exit silently in this case. This is a preparation patch for ensuring that DRRS is enabled on fastsets. Note that the removed WARN_ON could also be triggered from userspace through the i915_drrs_ctl debugfs entry which was added by commit 35954e88bc50 ("drm/i915: Runtime disable for eDP DRRS") Reviewed-by: Maarten Lankhorst Signed-off-by: Hans de Goede Link: https://patchwork.freedesktop.org/patch/msgid/20181220132120.15318-2-hdegoede@redhat.com --- drivers/gpu/drm/i915/intel_dp.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c index 5b601b754707..62fd11540942 100644 --- a/drivers/gpu/drm/i915/intel_dp.c +++ b/drivers/gpu/drm/i915/intel_dp.c @@ -6432,8 +6432,8 @@ void intel_edp_drrs_enable(struct intel_dp *intel_dp, } mutex_lock(&dev_priv->drrs.mutex); - if (WARN_ON(dev_priv->drrs.dp)) { - DRM_ERROR("DRRS already enabled\n"); + if (dev_priv->drrs.dp) { + DRM_DEBUG_KMS("DRRS already enabled\n"); goto unlock; } From 2ef82327c2c762517caacf063766a02efc978ccf Mon Sep 17 00:00:00 2001 From: Hans de Goede Date: Thu, 20 Dec 2018 14:21:20 +0100 Subject: [PATCH 064/118] drm/i915: DDI: call intel_psr_ and _edp_drrs_enable() on pipe updates (v2) Call intel_psr_enable() and intel_edp_drrs_enable() on pipe updates to make sure that we enable PSR / DRRS (when applicable) on fastsets. Note calling these functions when PSR / DRRS has already been enabled is a no-op, so it is safe to do this on every encoder->update_pipe callback. Changes in v2: -Merge the patches adding the intel_psr_enable() and intel_edp_drrs_enable() calls into a single patch Reviewed-by: Maarten Lankhorst Signed-off-by: Hans de Goede Acked-by: Rodrigo Vivi Link: https://patchwork.freedesktop.org/patch/msgid/20181220132120.15318-3-hdegoede@redhat.com --- drivers/gpu/drm/i915/intel_ddi.c | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/drivers/gpu/drm/i915/intel_ddi.c b/drivers/gpu/drm/i915/intel_ddi.c index e3cc19e19199..fdf57f451b72 100644 --- a/drivers/gpu/drm/i915/intel_ddi.c +++ b/drivers/gpu/drm/i915/intel_ddi.c @@ -3537,6 +3537,24 @@ static void intel_disable_ddi(struct intel_encoder *encoder, intel_disable_ddi_dp(encoder, old_crtc_state, old_conn_state); } +static void intel_ddi_update_pipe_dp(struct intel_encoder *encoder, + const struct intel_crtc_state *crtc_state, + const struct drm_connector_state *conn_state) +{ + struct intel_dp *intel_dp = enc_to_intel_dp(&encoder->base); + + intel_psr_enable(intel_dp, crtc_state); + intel_edp_drrs_enable(intel_dp, crtc_state); +} + +static void intel_ddi_update_pipe(struct intel_encoder *encoder, + const struct intel_crtc_state *crtc_state, + const struct drm_connector_state *conn_state) +{ + if (!intel_crtc_has_type(crtc_state, INTEL_OUTPUT_HDMI)) + intel_ddi_update_pipe_dp(encoder, crtc_state, conn_state); +} + static void intel_ddi_set_fia_lane_count(struct intel_encoder *encoder, const struct intel_crtc_state *pipe_config, enum port port) @@ -4169,6 +4187,7 @@ void intel_ddi_init(struct drm_i915_private *dev_priv, enum port port) intel_encoder->pre_enable = intel_ddi_pre_enable; intel_encoder->disable = intel_disable_ddi; intel_encoder->post_disable = intel_ddi_post_disable; + intel_encoder->update_pipe = intel_ddi_update_pipe; intel_encoder->get_hw_state = intel_ddi_get_hw_state; intel_encoder->get_config = intel_ddi_get_config; intel_encoder->suspend = intel_ddi_encoder_suspend; From eb3e1e3383e88735e149842c0049ea8e53dea8f4 Mon Sep 17 00:00:00 2001 From: Brajeswar Ghosh Date: Tue, 25 Dec 2018 18:53:40 +0530 Subject: [PATCH 065/118] drm/i915: Remove duplicate header from i915_request.h Remove i915_scheduler.h which is included more than once Signed-off-by: Brajeswar Ghosh Signed-off-by: Chris Wilson Link: https://patchwork.freedesktop.org/patch/msgid/20181225132340.GA2584@hp-pavilion-15-notebook-pc-brajeswar --- drivers/gpu/drm/i915/i915_request.h | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/gpu/drm/i915/i915_request.h b/drivers/gpu/drm/i915/i915_request.h index 90e9d170a0cd..d014b0605445 100644 --- a/drivers/gpu/drm/i915/i915_request.h +++ b/drivers/gpu/drm/i915/i915_request.h @@ -30,7 +30,6 @@ #include "i915_gem.h" #include "i915_scheduler.h" #include "i915_sw_fence.h" -#include "i915_scheduler.h" #include From 28e52b98b98a9e2cbe9ecd4f04f4d723fd767f56 Mon Sep 17 00:00:00 2001 From: Chris Wilson Date: Thu, 27 Dec 2018 12:15:49 +0000 Subject: [PATCH 066/118] drm/i915: Remove debugfs/i915_ppgtt_info The information presented here is not relevant to current development. We can either use the context information, but more often we want to inspect the active gpu state. The ulterior motive is to eradicate dev->filelist. Signed-off-by: Chris Wilson Reviewed-by: Tvrtko Ursulin Link: https://patchwork.freedesktop.org/patch/msgid/20181227121549.29139-1-chris@chris-wilson.co.uk --- drivers/gpu/drm/i915/i915_debugfs.c | 119 ------------------------ drivers/gpu/drm/i915/i915_gem_gtt.c | 134 ---------------------------- drivers/gpu/drm/i915/i915_gem_gtt.h | 2 - 3 files changed, 255 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index aca26a25ed50..2d29ce630c0e 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -2076,124 +2076,6 @@ static int i915_swizzle_info(struct seq_file *m, void *data) return 0; } -static int per_file_ctx(int id, void *ptr, void *data) -{ - struct i915_gem_context *ctx = ptr; - struct seq_file *m = data; - struct i915_hw_ppgtt *ppgtt = ctx->ppgtt; - - if (!ppgtt) { - seq_printf(m, " no ppgtt for context %d\n", - ctx->user_handle); - return 0; - } - - if (i915_gem_context_is_default(ctx)) - seq_puts(m, " default context:\n"); - else - seq_printf(m, " context %d:\n", ctx->user_handle); - ppgtt->debug_dump(ppgtt, m); - - return 0; -} - -static void gen8_ppgtt_info(struct seq_file *m, - struct drm_i915_private *dev_priv) -{ - struct i915_hw_ppgtt *ppgtt = dev_priv->mm.aliasing_ppgtt; - struct intel_engine_cs *engine; - enum intel_engine_id id; - int i; - - if (!ppgtt) - return; - - for_each_engine(engine, dev_priv, id) { - seq_printf(m, "%s\n", engine->name); - for (i = 0; i < 4; i++) { - u64 pdp = I915_READ(GEN8_RING_PDP_UDW(engine, i)); - pdp <<= 32; - pdp |= I915_READ(GEN8_RING_PDP_LDW(engine, i)); - seq_printf(m, "\tPDP%d 0x%016llx\n", i, pdp); - } - } -} - -static void gen6_ppgtt_info(struct seq_file *m, - struct drm_i915_private *dev_priv) -{ - struct intel_engine_cs *engine; - enum intel_engine_id id; - - if (IS_GEN(dev_priv, 6)) - seq_printf(m, "GFX_MODE: 0x%08x\n", I915_READ(GFX_MODE)); - - for_each_engine(engine, dev_priv, id) { - seq_printf(m, "%s\n", engine->name); - if (IS_GEN(dev_priv, 7)) - seq_printf(m, "GFX_MODE: 0x%08x\n", - I915_READ(RING_MODE_GEN7(engine))); - seq_printf(m, "PP_DIR_BASE: 0x%08x\n", - I915_READ(RING_PP_DIR_BASE(engine))); - seq_printf(m, "PP_DIR_BASE_READ: 0x%08x\n", - I915_READ(RING_PP_DIR_BASE_READ(engine))); - seq_printf(m, "PP_DIR_DCLV: 0x%08x\n", - I915_READ(RING_PP_DIR_DCLV(engine))); - } - if (dev_priv->mm.aliasing_ppgtt) { - struct i915_hw_ppgtt *ppgtt = dev_priv->mm.aliasing_ppgtt; - - seq_puts(m, "aliasing PPGTT:\n"); - seq_printf(m, "pd gtt offset: 0x%08x\n", ppgtt->pd.base.ggtt_offset); - - ppgtt->debug_dump(ppgtt, m); - } - - seq_printf(m, "ECOCHK: 0x%08x\n", I915_READ(GAM_ECOCHK)); -} - -static int i915_ppgtt_info(struct seq_file *m, void *data) -{ - struct drm_i915_private *dev_priv = node_to_i915(m->private); - struct drm_device *dev = &dev_priv->drm; - struct drm_file *file; - int ret; - - mutex_lock(&dev->filelist_mutex); - ret = mutex_lock_interruptible(&dev->struct_mutex); - if (ret) - goto out_unlock; - - intel_runtime_pm_get(dev_priv); - - if (INTEL_GEN(dev_priv) >= 8) - gen8_ppgtt_info(m, dev_priv); - else if (INTEL_GEN(dev_priv) >= 6) - gen6_ppgtt_info(m, dev_priv); - - list_for_each_entry_reverse(file, &dev->filelist, lhead) { - struct drm_i915_file_private *file_priv = file->driver_priv; - struct task_struct *task; - - task = get_pid_task(file->pid, PIDTYPE_PID); - if (!task) { - ret = -ESRCH; - goto out_rpm; - } - seq_printf(m, "\nproc: %s\n", task->comm); - put_task_struct(task); - idr_for_each(&file_priv->context_idr, per_file_ctx, - (void *)(unsigned long)m); - } - -out_rpm: - intel_runtime_pm_put(dev_priv); - mutex_unlock(&dev->struct_mutex); -out_unlock: - mutex_unlock(&dev->filelist_mutex); - return ret; -} - static int count_irq_waiters(struct drm_i915_private *i915) { struct intel_engine_cs *engine; @@ -4912,7 +4794,6 @@ static const struct drm_info_list i915_debugfs_list[] = { {"i915_context_status", i915_context_status, 0}, {"i915_forcewake_domains", i915_forcewake_domains, 0}, {"i915_swizzle_info", i915_swizzle_info, 0}, - {"i915_ppgtt_info", i915_ppgtt_info, 0}, {"i915_llc", i915_llc, 0}, {"i915_edp_psr_status", i915_edp_psr_status, 0}, {"i915_energy_uJ", i915_energy_uJ, 0}, diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.c b/drivers/gpu/drm/i915/i915_gem_gtt.c index 4ed2f3e61347..d4c5973ea33d 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.c +++ b/drivers/gpu/drm/i915/i915_gem_gtt.c @@ -1488,84 +1488,6 @@ static int gen8_ppgtt_alloc_4lvl(struct i915_address_space *vm, return -ENOMEM; } -static void gen8_dump_pdp(struct i915_hw_ppgtt *ppgtt, - struct i915_page_directory_pointer *pdp, - u64 start, u64 length, - gen8_pte_t scratch_pte, - struct seq_file *m) -{ - struct i915_address_space *vm = &ppgtt->vm; - struct i915_page_directory *pd; - u32 pdpe; - - gen8_for_each_pdpe(pd, pdp, start, length, pdpe) { - struct i915_page_table *pt; - u64 pd_len = length; - u64 pd_start = start; - u32 pde; - - if (pdp->page_directory[pdpe] == ppgtt->vm.scratch_pd) - continue; - - seq_printf(m, "\tPDPE #%d\n", pdpe); - gen8_for_each_pde(pt, pd, pd_start, pd_len, pde) { - u32 pte; - gen8_pte_t *pt_vaddr; - - if (pd->page_table[pde] == ppgtt->vm.scratch_pt) - continue; - - pt_vaddr = kmap_atomic_px(pt); - for (pte = 0; pte < GEN8_PTES; pte += 4) { - u64 va = (pdpe << GEN8_PDPE_SHIFT | - pde << GEN8_PDE_SHIFT | - pte << GEN8_PTE_SHIFT); - int i; - bool found = false; - - for (i = 0; i < 4; i++) - if (pt_vaddr[pte + i] != scratch_pte) - found = true; - if (!found) - continue; - - seq_printf(m, "\t\t0x%llx [%03d,%03d,%04d]: =", va, pdpe, pde, pte); - for (i = 0; i < 4; i++) { - if (pt_vaddr[pte + i] != scratch_pte) - seq_printf(m, " %llx", pt_vaddr[pte + i]); - else - seq_puts(m, " SCRATCH "); - } - seq_puts(m, "\n"); - } - kunmap_atomic(pt_vaddr); - } - } -} - -static void gen8_dump_ppgtt(struct i915_hw_ppgtt *ppgtt, struct seq_file *m) -{ - struct i915_address_space *vm = &ppgtt->vm; - const gen8_pte_t scratch_pte = vm->scratch_pte; - u64 start = 0, length = ppgtt->vm.total; - - if (use_4lvl(vm)) { - u64 pml4e; - struct i915_pml4 *pml4 = &ppgtt->pml4; - struct i915_page_directory_pointer *pdp; - - gen8_for_each_pml4e(pdp, pml4, start, length, pml4e) { - if (pml4->pdps[pml4e] == ppgtt->vm.scratch_pdp) - continue; - - seq_printf(m, " PML4E #%llu\n", pml4e); - gen8_dump_pdp(ppgtt, pdp, start, length, scratch_pte, m); - } - } else { - gen8_dump_pdp(ppgtt, &ppgtt->pdp, start, length, scratch_pte, m); - } -} - static int gen8_preallocate_top_level_pdp(struct i915_hw_ppgtt *ppgtt) { struct i915_address_space *vm = &ppgtt->vm; @@ -1670,7 +1592,6 @@ static struct i915_hw_ppgtt *gen8_ppgtt_create(struct drm_i915_private *i915) gen8_ppgtt_notify_vgt(ppgtt, true); ppgtt->vm.cleanup = gen8_ppgtt_cleanup; - ppgtt->debug_dump = gen8_dump_ppgtt; ppgtt->vm.vma_ops.bind_vma = ppgtt_bind_vma; ppgtt->vm.vma_ops.unbind_vma = ppgtt_unbind_vma; @@ -1686,60 +1607,6 @@ static struct i915_hw_ppgtt *gen8_ppgtt_create(struct drm_i915_private *i915) return ERR_PTR(err); } -static void gen6_dump_ppgtt(struct i915_hw_ppgtt *base, struct seq_file *m) -{ - struct gen6_hw_ppgtt *ppgtt = to_gen6_ppgtt(base); - const gen6_pte_t scratch_pte = base->vm.scratch_pte; - struct i915_page_table *pt; - u32 pte, pde; - - gen6_for_all_pdes(pt, &base->pd, pde) { - gen6_pte_t *vaddr; - - if (pt == base->vm.scratch_pt) - continue; - - if (i915_vma_is_bound(ppgtt->vma, I915_VMA_GLOBAL_BIND)) { - u32 expected = - GEN6_PDE_ADDR_ENCODE(px_dma(pt)) | - GEN6_PDE_VALID; - u32 pd_entry = readl(ppgtt->pd_addr + pde); - - if (pd_entry != expected) - seq_printf(m, - "\tPDE #%d mismatch: Actual PDE: %x Expected PDE: %x\n", - pde, - pd_entry, - expected); - - seq_printf(m, "\tPDE: %x\n", pd_entry); - } - - vaddr = kmap_atomic_px(base->pd.page_table[pde]); - for (pte = 0; pte < GEN6_PTES; pte += 4) { - int i; - - for (i = 0; i < 4; i++) - if (vaddr[pte + i] != scratch_pte) - break; - if (i == 4) - continue; - - seq_printf(m, "\t\t(%03d, %04d) %08llx: ", - pde, pte, - (pde * GEN6_PTES + pte) * I915_GTT_PAGE_SIZE); - for (i = 0; i < 4; i++) { - if (vaddr[pte + i] != scratch_pte) - seq_printf(m, " %08x", vaddr[pte + i]); - else - seq_puts(m, " SCRATCH"); - } - seq_puts(m, "\n"); - } - kunmap_atomic(vaddr); - } -} - /* Write pde (index) from the page directory @pd to the page table @pt */ static inline void gen6_write_pde(const struct gen6_hw_ppgtt *ppgtt, const unsigned int pde, @@ -2136,7 +2003,6 @@ static struct i915_hw_ppgtt *gen6_ppgtt_create(struct drm_i915_private *i915) ppgtt->base.vm.clear_range = gen6_ppgtt_clear_range; ppgtt->base.vm.insert_entries = gen6_ppgtt_insert_entries; ppgtt->base.vm.cleanup = gen6_ppgtt_cleanup; - ppgtt->base.debug_dump = gen6_dump_ppgtt; ppgtt->base.vm.vma_ops.bind_vma = ppgtt_bind_vma; ppgtt->base.vm.vma_ops.unbind_vma = ppgtt_unbind_vma; diff --git a/drivers/gpu/drm/i915/i915_gem_gtt.h b/drivers/gpu/drm/i915/i915_gem_gtt.h index 4874da09a3c4..e2360f16427a 100644 --- a/drivers/gpu/drm/i915/i915_gem_gtt.h +++ b/drivers/gpu/drm/i915/i915_gem_gtt.h @@ -413,8 +413,6 @@ struct i915_hw_ppgtt { struct i915_page_directory_pointer pdp; /* GEN8+ */ struct i915_page_directory pd; /* GEN6-7 */ }; - - void (*debug_dump)(struct i915_hw_ppgtt *ppgtt, struct seq_file *m); }; struct gen6_hw_ppgtt { From 6879216897b7dd4cfeaaed8e80e0374f260fc594 Mon Sep 17 00:00:00 2001 From: Brajeswar Ghosh Date: Tue, 25 Dec 2018 19:00:56 +0530 Subject: [PATCH 067/118] drm/intel_dsi_vbt: Remove duplicate header Remove video/mipi_display.h which is included more than once Signed-off-by: Brajeswar Ghosh Signed-off-by: Jani Nikula Link: https://patchwork.freedesktop.org/patch/msgid/20181225133055.GA2628@hp-pavilion-15-notebook-pc-brajeswar --- drivers/gpu/drm/i915/intel_dsi_vbt.c | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/gpu/drm/i915/intel_dsi_vbt.c b/drivers/gpu/drm/i915/intel_dsi_vbt.c index a1a8b3790e61..5b7e9118d97f 100644 --- a/drivers/gpu/drm/i915/intel_dsi_vbt.c +++ b/drivers/gpu/drm/i915/intel_dsi_vbt.c @@ -32,7 +32,6 @@ #include #include