aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorImre Deak <imre.deak@intel.com>2014-03-31 08:10:44 -0400
committerDaniel Vetter <daniel.vetter@ffwll.ch>2014-04-01 16:30:01 -0400
commitae48434c2a13cf4758aaf87da21d828f6d4dbebb (patch)
tree0162c5b1cb050f28747f1558139220ed5d47f75d
parent50227e1cae118562b8b6230e31bca84870cad27e (diff)
drm/i915: vlv: reserve the GT power context only once during driver init
Atm we reserve/allocate and free the power context during GT power enable/disable time. There is no need to do this, we can reserve/allocate the buffer once during driver loading and free it during driver cleanup. The re-reservation can also fail in case the driver previously manages to allocate something on the given fixed address. The buffer isn't exepected to move even if allocated by the BIOS, for safety add an assert to check this assumption. This also fixed a bug for Ville, where re-reserving the context failed during a GPU reset (I assume because something else got allocated on its fixed address). Tested-by: Ville Syrjälä <ville.syrjala@linux.intel.com> Signed-off-by: Imre Deak <imre.deak@intel.com> Reviewed-by: Ville Syrjälä <ville.syrjala@linux.intel.com> Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
-rw-r--r--drivers/gpu/drm/i915/intel_display.c8
-rw-r--r--drivers/gpu/drm/i915/intel_drv.h2
-rw-r--r--drivers/gpu/drm/i915/intel_pm.c41
3 files changed, 44 insertions, 7 deletions
diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c
index 8bce7f00294b..c31c6203c7ca 100644
--- a/drivers/gpu/drm/i915/intel_display.c
+++ b/drivers/gpu/drm/i915/intel_display.c
@@ -11759,6 +11759,10 @@ void intel_modeset_gem_init(struct drm_device *dev)
11759 struct drm_crtc *c; 11759 struct drm_crtc *c;
11760 struct intel_framebuffer *fb; 11760 struct intel_framebuffer *fb;
11761 11761
11762 mutex_lock(&dev->struct_mutex);
11763 intel_init_gt_powersave(dev);
11764 mutex_unlock(&dev->struct_mutex);
11765
11762 intel_modeset_init_hw(dev); 11766 intel_modeset_init_hw(dev);
11763 11767
11764 intel_setup_overlay(dev); 11768 intel_setup_overlay(dev);
@@ -11845,6 +11849,10 @@ void intel_modeset_cleanup(struct drm_device *dev)
11845 drm_mode_config_cleanup(dev); 11849 drm_mode_config_cleanup(dev);
11846 11850
11847 intel_cleanup_overlay(dev); 11851 intel_cleanup_overlay(dev);
11852
11853 mutex_lock(&dev->struct_mutex);
11854 intel_cleanup_gt_powersave(dev);
11855 mutex_unlock(&dev->struct_mutex);
11848} 11856}
11849 11857
11850/* 11858/*
diff --git a/drivers/gpu/drm/i915/intel_drv.h b/drivers/gpu/drm/i915/intel_drv.h
index fa9910481ab0..0542de982260 100644
--- a/drivers/gpu/drm/i915/intel_drv.h
+++ b/drivers/gpu/drm/i915/intel_drv.h
@@ -897,6 +897,8 @@ void intel_display_power_get(struct drm_i915_private *dev_priv,
897void intel_display_power_put(struct drm_i915_private *dev_priv, 897void intel_display_power_put(struct drm_i915_private *dev_priv,
898 enum intel_display_power_domain domain); 898 enum intel_display_power_domain domain);
899void intel_power_domains_init_hw(struct drm_i915_private *dev_priv); 899void intel_power_domains_init_hw(struct drm_i915_private *dev_priv);
900void intel_init_gt_powersave(struct drm_device *dev);
901void intel_cleanup_gt_powersave(struct drm_device *dev);
900void intel_enable_gt_powersave(struct drm_device *dev); 902void intel_enable_gt_powersave(struct drm_device *dev);
901void intel_disable_gt_powersave(struct drm_device *dev); 903void intel_disable_gt_powersave(struct drm_device *dev);
902void ironlake_teardown_rc6(struct drm_device *dev); 904void ironlake_teardown_rc6(struct drm_device *dev);
diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c
index 38a68cea5ed7..453bf0cc21c0 100644
--- a/drivers/gpu/drm/i915/intel_pm.c
+++ b/drivers/gpu/drm/i915/intel_pm.c
@@ -3201,11 +3201,6 @@ static void valleyview_disable_rps(struct drm_device *dev)
3201 I915_WRITE(GEN6_RC_CONTROL, 0); 3201 I915_WRITE(GEN6_RC_CONTROL, 0);
3202 3202
3203 gen6_disable_rps_interrupts(dev); 3203 gen6_disable_rps_interrupts(dev);
3204
3205 if (dev_priv->vlv_pctx) {
3206 drm_gem_object_unreference(&dev_priv->vlv_pctx->base);
3207 dev_priv->vlv_pctx = NULL;
3208 }
3209} 3204}
3210 3205
3211static void intel_print_rc6_info(struct drm_device *dev, u32 mode) 3206static void intel_print_rc6_info(struct drm_device *dev, u32 mode)
@@ -3549,6 +3544,15 @@ int valleyview_rps_min_freq(struct drm_i915_private *dev_priv)
3549 return vlv_punit_read(dev_priv, PUNIT_REG_GPU_LFM) & 0xff; 3544 return vlv_punit_read(dev_priv, PUNIT_REG_GPU_LFM) & 0xff;
3550} 3545}
3551 3546
3547/* Check that the pctx buffer wasn't move under us. */
3548static void valleyview_check_pctx(struct drm_i915_private *dev_priv)
3549{
3550 unsigned long pctx_addr = I915_READ(VLV_PCBR) & ~4095;
3551
3552 WARN_ON(pctx_addr != dev_priv->mm.stolen_base +
3553 dev_priv->vlv_pctx->stolen->start);
3554}
3555
3552static void valleyview_setup_pctx(struct drm_device *dev) 3556static void valleyview_setup_pctx(struct drm_device *dev)
3553{ 3557{
3554 struct drm_i915_private *dev_priv = dev->dev_private; 3558 struct drm_i915_private *dev_priv = dev->dev_private;
@@ -3593,6 +3597,17 @@ out:
3593 dev_priv->vlv_pctx = pctx; 3597 dev_priv->vlv_pctx = pctx;
3594} 3598}
3595 3599
3600static void valleyview_cleanup_pctx(struct drm_device *dev)
3601{
3602 struct drm_i915_private *dev_priv = dev->dev_private;
3603
3604 if (WARN_ON(!dev_priv->vlv_pctx))
3605 return;
3606
3607 drm_gem_object_unreference(&dev_priv->vlv_pctx->base);
3608 dev_priv->vlv_pctx = NULL;
3609}
3610
3596static void valleyview_enable_rps(struct drm_device *dev) 3611static void valleyview_enable_rps(struct drm_device *dev)
3597{ 3612{
3598 struct drm_i915_private *dev_priv = dev->dev_private; 3613 struct drm_i915_private *dev_priv = dev->dev_private;
@@ -3602,6 +3617,8 @@ static void valleyview_enable_rps(struct drm_device *dev)
3602 3617
3603 WARN_ON(!mutex_is_locked(&dev_priv->rps.hw_lock)); 3618 WARN_ON(!mutex_is_locked(&dev_priv->rps.hw_lock));
3604 3619
3620 valleyview_check_pctx(dev_priv);
3621
3605 if ((gtfifodbg = I915_READ(GTFIFODBG))) { 3622 if ((gtfifodbg = I915_READ(GTFIFODBG))) {
3606 DRM_DEBUG_DRIVER("GT fifo had a previous error %x\n", 3623 DRM_DEBUG_DRIVER("GT fifo had a previous error %x\n",
3607 gtfifodbg); 3624 gtfifodbg);
@@ -4418,6 +4435,18 @@ static void intel_init_emon(struct drm_device *dev)
4418 dev_priv->ips.corr = (lcfuse & LCFUSE_HIV_MASK); 4435 dev_priv->ips.corr = (lcfuse & LCFUSE_HIV_MASK);
4419} 4436}
4420 4437
4438void intel_init_gt_powersave(struct drm_device *dev)
4439{
4440 if (IS_VALLEYVIEW(dev))
4441 valleyview_setup_pctx(dev);
4442}
4443
4444void intel_cleanup_gt_powersave(struct drm_device *dev)
4445{
4446 if (IS_VALLEYVIEW(dev))
4447 valleyview_cleanup_pctx(dev);
4448}
4449
4421void intel_disable_gt_powersave(struct drm_device *dev) 4450void intel_disable_gt_powersave(struct drm_device *dev)
4422{ 4451{
4423 struct drm_i915_private *dev_priv = dev->dev_private; 4452 struct drm_i915_private *dev_priv = dev->dev_private;
@@ -4472,8 +4501,6 @@ void intel_enable_gt_powersave(struct drm_device *dev)
4472 ironlake_enable_rc6(dev); 4501 ironlake_enable_rc6(dev);
4473 intel_init_emon(dev); 4502 intel_init_emon(dev);
4474 } else if (IS_GEN6(dev) || IS_GEN7(dev)) { 4503 } else if (IS_GEN6(dev) || IS_GEN7(dev)) {
4475 if (IS_VALLEYVIEW(dev))
4476 valleyview_setup_pctx(dev);
4477 /* 4504 /*
4478 * PCU communication is slow and this doesn't need to be 4505 * PCU communication is slow and this doesn't need to be
4479 * done at any specific time, so do this out of our fast path 4506 * done at any specific time, so do this out of our fast path