diff options
Diffstat (limited to 'drivers/gpu/drm/i915/intel_pm.c')
| -rw-r--r-- | drivers/gpu/drm/i915/intel_pm.c | 40 |
1 files changed, 40 insertions, 0 deletions
diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 8bbd4f910663..d1e53abec1b5 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c | |||
| @@ -2113,6 +2113,43 @@ static void intel_print_wm_latency(struct drm_device *dev, | |||
| 2113 | } | 2113 | } |
| 2114 | } | 2114 | } |
| 2115 | 2115 | ||
| 2116 | static bool ilk_increase_wm_latency(struct drm_i915_private *dev_priv, | ||
| 2117 | uint16_t wm[5], uint16_t min) | ||
| 2118 | { | ||
| 2119 | int level, max_level = ilk_wm_max_level(dev_priv->dev); | ||
| 2120 | |||
| 2121 | if (wm[0] >= min) | ||
| 2122 | return false; | ||
| 2123 | |||
| 2124 | wm[0] = max(wm[0], min); | ||
| 2125 | for (level = 1; level <= max_level; level++) | ||
| 2126 | wm[level] = max_t(uint16_t, wm[level], DIV_ROUND_UP(min, 5)); | ||
| 2127 | |||
| 2128 | return true; | ||
| 2129 | } | ||
| 2130 | |||
| 2131 | static void snb_wm_latency_quirk(struct drm_device *dev) | ||
| 2132 | { | ||
| 2133 | struct drm_i915_private *dev_priv = dev->dev_private; | ||
| 2134 | bool changed; | ||
| 2135 | |||
| 2136 | /* | ||
| 2137 | * The BIOS provided WM memory latency values are often | ||
| 2138 | * inadequate for high resolution displays. Adjust them. | ||
| 2139 | */ | ||
| 2140 | changed = ilk_increase_wm_latency(dev_priv, dev_priv->wm.pri_latency, 12) | | ||
| 2141 | ilk_increase_wm_latency(dev_priv, dev_priv->wm.spr_latency, 12) | | ||
| 2142 | ilk_increase_wm_latency(dev_priv, dev_priv->wm.cur_latency, 12); | ||
| 2143 | |||
| 2144 | if (!changed) | ||
| 2145 | return; | ||
| 2146 | |||
| 2147 | DRM_DEBUG_KMS("WM latency values increased to avoid potential underruns\n"); | ||
| 2148 | intel_print_wm_latency(dev, "Primary", dev_priv->wm.pri_latency); | ||
| 2149 | intel_print_wm_latency(dev, "Sprite", dev_priv->wm.spr_latency); | ||
| 2150 | intel_print_wm_latency(dev, "Cursor", dev_priv->wm.cur_latency); | ||
| 2151 | } | ||
| 2152 | |||
| 2116 | static void ilk_setup_wm_latency(struct drm_device *dev) | 2153 | static void ilk_setup_wm_latency(struct drm_device *dev) |
| 2117 | { | 2154 | { |
| 2118 | struct drm_i915_private *dev_priv = dev->dev_private; | 2155 | struct drm_i915_private *dev_priv = dev->dev_private; |
| @@ -2130,6 +2167,9 @@ static void ilk_setup_wm_latency(struct drm_device *dev) | |||
| 2130 | intel_print_wm_latency(dev, "Primary", dev_priv->wm.pri_latency); | 2167 | intel_print_wm_latency(dev, "Primary", dev_priv->wm.pri_latency); |
| 2131 | intel_print_wm_latency(dev, "Sprite", dev_priv->wm.spr_latency); | 2168 | intel_print_wm_latency(dev, "Sprite", dev_priv->wm.spr_latency); |
| 2132 | intel_print_wm_latency(dev, "Cursor", dev_priv->wm.cur_latency); | 2169 | intel_print_wm_latency(dev, "Cursor", dev_priv->wm.cur_latency); |
| 2170 | |||
| 2171 | if (IS_GEN6(dev)) | ||
| 2172 | snb_wm_latency_quirk(dev); | ||
| 2133 | } | 2173 | } |
| 2134 | 2174 | ||
| 2135 | static void ilk_compute_wm_parameters(struct drm_crtc *crtc, | 2175 | static void ilk_compute_wm_parameters(struct drm_crtc *crtc, |
