| From 65a21cd65316145f9302594be8e69074369e1050 Mon Sep 17 00:00:00 2001 |
| From: Jesse Barnes <jbarnes@virtuousgeek.org> |
| Date: Wed, 12 Oct 2011 11:10:21 -0700 |
| Subject: drm/i915: fix IVB cursor support |
| |
| From: Jesse Barnes <jbarnes@virtuousgeek.org> |
| |
| commit 65a21cd65316145f9302594be8e69074369e1050 upstream. |
| |
| The cursor regs have moved around, add the offsets and new macros for |
| getting at them. |
| |
| Signed-off-by: Jesse Barnes <jbarnes@virtuousgeek.org> |
| Tested-By: Eugeni Dodonov <eugeni.dodonov@intel.com> |
| Reviewed-By: Eugeni Dodonov <eugeni.dodonov@intel.com> |
| Signed-off-by: Keith Packard <keithp@keithp.com> |
| Signed-off-by: Robert Hooker <robert.hooker@canonical.com> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de> |
| |
| --- |
| drivers/gpu/drm/i915/i915_reg.h | 8 +++++++ |
| drivers/gpu/drm/i915/intel_display.c | 40 ++++++++++++++++++++++++++++++----- |
| 2 files changed, 43 insertions(+), 5 deletions(-) |
| |
| --- a/drivers/gpu/drm/i915/i915_reg.h |
| +++ b/drivers/gpu/drm/i915/i915_reg.h |
| @@ -2544,10 +2544,18 @@ |
| #define _CURBBASE 0x700c4 |
| #define _CURBPOS 0x700c8 |
| |
| +#define _CURBCNTR_IVB 0x71080 |
| +#define _CURBBASE_IVB 0x71084 |
| +#define _CURBPOS_IVB 0x71088 |
| + |
| #define CURCNTR(pipe) _PIPE(pipe, _CURACNTR, _CURBCNTR) |
| #define CURBASE(pipe) _PIPE(pipe, _CURABASE, _CURBBASE) |
| #define CURPOS(pipe) _PIPE(pipe, _CURAPOS, _CURBPOS) |
| |
| +#define CURCNTR_IVB(pipe) _PIPE(pipe, _CURACNTR, _CURBCNTR_IVB) |
| +#define CURBASE_IVB(pipe) _PIPE(pipe, _CURABASE, _CURBBASE_IVB) |
| +#define CURPOS_IVB(pipe) _PIPE(pipe, _CURAPOS, _CURBPOS_IVB) |
| + |
| /* Display A control */ |
| #define _DSPACNTR 0x70180 |
| #define DISPLAY_PLANE_ENABLE (1<<31) |
| --- a/drivers/gpu/drm/i915/intel_display.c |
| +++ b/drivers/gpu/drm/i915/intel_display.c |
| @@ -5334,6 +5334,31 @@ static void i9xx_update_cursor(struct dr |
| I915_WRITE(CURBASE(pipe), base); |
| } |
| |
| +static void ivb_update_cursor(struct drm_crtc *crtc, u32 base) |
| +{ |
| + struct drm_device *dev = crtc->dev; |
| + struct drm_i915_private *dev_priv = dev->dev_private; |
| + struct intel_crtc *intel_crtc = to_intel_crtc(crtc); |
| + int pipe = intel_crtc->pipe; |
| + bool visible = base != 0; |
| + |
| + if (intel_crtc->cursor_visible != visible) { |
| + uint32_t cntl = I915_READ(CURCNTR_IVB(pipe)); |
| + if (base) { |
| + cntl &= ~CURSOR_MODE; |
| + cntl |= CURSOR_MODE_64_ARGB_AX | MCURSOR_GAMMA_ENABLE; |
| + } else { |
| + cntl &= ~(CURSOR_MODE | MCURSOR_GAMMA_ENABLE); |
| + cntl |= CURSOR_MODE_DISABLE; |
| + } |
| + I915_WRITE(CURCNTR_IVB(pipe), cntl); |
| + |
| + intel_crtc->cursor_visible = visible; |
| + } |
| + /* and commit changes on next vblank */ |
| + I915_WRITE(CURBASE_IVB(pipe), base); |
| +} |
| + |
| /* If no-part of the cursor is visible on the framebuffer, then the GPU may hang... */ |
| static void intel_crtc_update_cursor(struct drm_crtc *crtc, |
| bool on) |
| @@ -5381,11 +5406,16 @@ static void intel_crtc_update_cursor(str |
| if (!visible && !intel_crtc->cursor_visible) |
| return; |
| |
| - I915_WRITE(CURPOS(pipe), pos); |
| - if (IS_845G(dev) || IS_I865G(dev)) |
| - i845_update_cursor(crtc, base); |
| - else |
| - i9xx_update_cursor(crtc, base); |
| + if (IS_IVYBRIDGE(dev)) { |
| + I915_WRITE(CURPOS_IVB(pipe), pos); |
| + ivb_update_cursor(crtc, base); |
| + } else { |
| + I915_WRITE(CURPOS(pipe), pos); |
| + if (IS_845G(dev) || IS_I865G(dev)) |
| + i845_update_cursor(crtc, base); |
| + else |
| + i9xx_update_cursor(crtc, base); |
| + } |
| |
| if (visible) |
| intel_mark_busy(dev, to_intel_framebuffer(crtc->fb)->obj); |