diff options
Diffstat (limited to 'drivers/gpu/drm/i915/intel_sprite.c')
| -rw-r--r-- | drivers/gpu/drm/i915/intel_sprite.c | 46 |
1 files changed, 27 insertions, 19 deletions
diff --git a/drivers/gpu/drm/i915/intel_sprite.c b/drivers/gpu/drm/i915/intel_sprite.c index d7b060e0a231..1b6eb76beb7c 100644 --- a/drivers/gpu/drm/i915/intel_sprite.c +++ b/drivers/gpu/drm/i915/intel_sprite.c | |||
| @@ -50,6 +50,7 @@ ivb_update_plane(struct drm_plane *plane, struct drm_framebuffer *fb, | |||
| 50 | u32 sprctl, sprscale = 0; | 50 | u32 sprctl, sprscale = 0; |
| 51 | unsigned long sprsurf_offset, linear_offset; | 51 | unsigned long sprsurf_offset, linear_offset; |
| 52 | int pixel_size = drm_format_plane_cpp(fb->pixel_format, 0); | 52 | int pixel_size = drm_format_plane_cpp(fb->pixel_format, 0); |
| 53 | bool scaling_was_enabled = dev_priv->sprite_scaling_enabled; | ||
| 53 | 54 | ||
| 54 | sprctl = I915_READ(SPRCTL(pipe)); | 55 | sprctl = I915_READ(SPRCTL(pipe)); |
| 55 | 56 | ||
| @@ -89,6 +90,9 @@ ivb_update_plane(struct drm_plane *plane, struct drm_framebuffer *fb, | |||
| 89 | sprctl |= SPRITE_TRICKLE_FEED_DISABLE; | 90 | sprctl |= SPRITE_TRICKLE_FEED_DISABLE; |
| 90 | sprctl |= SPRITE_ENABLE; | 91 | sprctl |= SPRITE_ENABLE; |
| 91 | 92 | ||
| 93 | if (IS_HASWELL(dev)) | ||
| 94 | sprctl |= SPRITE_PIPE_CSC_ENABLE; | ||
| 95 | |||
| 92 | /* Sizes are 0 based */ | 96 | /* Sizes are 0 based */ |
| 93 | src_w--; | 97 | src_w--; |
| 94 | src_h--; | 98 | src_h--; |
| @@ -103,27 +107,23 @@ ivb_update_plane(struct drm_plane *plane, struct drm_framebuffer *fb, | |||
| 103 | * when scaling is disabled. | 107 | * when scaling is disabled. |
| 104 | */ | 108 | */ |
| 105 | if (crtc_w != src_w || crtc_h != src_h) { | 109 | if (crtc_w != src_w || crtc_h != src_h) { |
| 106 | if (!dev_priv->sprite_scaling_enabled) { | 110 | dev_priv->sprite_scaling_enabled |= 1 << pipe; |
| 107 | dev_priv->sprite_scaling_enabled = true; | 111 | |
| 112 | if (!scaling_was_enabled) { | ||
| 108 | intel_update_watermarks(dev); | 113 | intel_update_watermarks(dev); |
| 109 | intel_wait_for_vblank(dev, pipe); | 114 | intel_wait_for_vblank(dev, pipe); |
| 110 | } | 115 | } |
| 111 | sprscale = SPRITE_SCALE_ENABLE | (src_w << 16) | src_h; | 116 | sprscale = SPRITE_SCALE_ENABLE | (src_w << 16) | src_h; |
| 112 | } else { | 117 | } else |
| 113 | if (dev_priv->sprite_scaling_enabled) { | 118 | dev_priv->sprite_scaling_enabled &= ~(1 << pipe); |
| 114 | dev_priv->sprite_scaling_enabled = false; | ||
| 115 | /* potentially re-enable LP watermarks */ | ||
| 116 | intel_update_watermarks(dev); | ||
| 117 | } | ||
| 118 | } | ||
| 119 | 119 | ||
| 120 | I915_WRITE(SPRSTRIDE(pipe), fb->pitches[0]); | 120 | I915_WRITE(SPRSTRIDE(pipe), fb->pitches[0]); |
| 121 | I915_WRITE(SPRPOS(pipe), (crtc_y << 16) | crtc_x); | 121 | I915_WRITE(SPRPOS(pipe), (crtc_y << 16) | crtc_x); |
| 122 | 122 | ||
| 123 | linear_offset = y * fb->pitches[0] + x * pixel_size; | 123 | linear_offset = y * fb->pitches[0] + x * pixel_size; |
| 124 | sprsurf_offset = | 124 | sprsurf_offset = |
| 125 | intel_gen4_compute_offset_xtiled(&x, &y, | 125 | intel_gen4_compute_page_offset(&x, &y, obj->tiling_mode, |
| 126 | pixel_size, fb->pitches[0]); | 126 | pixel_size, fb->pitches[0]); |
| 127 | linear_offset -= sprsurf_offset; | 127 | linear_offset -= sprsurf_offset; |
| 128 | 128 | ||
| 129 | /* HSW consolidates SPRTILEOFF and SPRLINOFF into a single SPROFFSET | 129 | /* HSW consolidates SPRTILEOFF and SPRLINOFF into a single SPROFFSET |
| @@ -141,6 +141,10 @@ ivb_update_plane(struct drm_plane *plane, struct drm_framebuffer *fb, | |||
| 141 | I915_WRITE(SPRCTL(pipe), sprctl); | 141 | I915_WRITE(SPRCTL(pipe), sprctl); |
| 142 | I915_MODIFY_DISPBASE(SPRSURF(pipe), obj->gtt_offset + sprsurf_offset); | 142 | I915_MODIFY_DISPBASE(SPRSURF(pipe), obj->gtt_offset + sprsurf_offset); |
| 143 | POSTING_READ(SPRSURF(pipe)); | 143 | POSTING_READ(SPRSURF(pipe)); |
| 144 | |||
| 145 | /* potentially re-enable LP watermarks */ | ||
| 146 | if (scaling_was_enabled && !dev_priv->sprite_scaling_enabled) | ||
| 147 | intel_update_watermarks(dev); | ||
| 144 | } | 148 | } |
| 145 | 149 | ||
| 146 | static void | 150 | static void |
| @@ -150,6 +154,7 @@ ivb_disable_plane(struct drm_plane *plane) | |||
| 150 | struct drm_i915_private *dev_priv = dev->dev_private; | 154 | struct drm_i915_private *dev_priv = dev->dev_private; |
| 151 | struct intel_plane *intel_plane = to_intel_plane(plane); | 155 | struct intel_plane *intel_plane = to_intel_plane(plane); |
| 152 | int pipe = intel_plane->pipe; | 156 | int pipe = intel_plane->pipe; |
| 157 | bool scaling_was_enabled = dev_priv->sprite_scaling_enabled; | ||
| 153 | 158 | ||
| 154 | I915_WRITE(SPRCTL(pipe), I915_READ(SPRCTL(pipe)) & ~SPRITE_ENABLE); | 159 | I915_WRITE(SPRCTL(pipe), I915_READ(SPRCTL(pipe)) & ~SPRITE_ENABLE); |
| 155 | /* Can't leave the scaler enabled... */ | 160 | /* Can't leave the scaler enabled... */ |
| @@ -159,8 +164,11 @@ ivb_disable_plane(struct drm_plane *plane) | |||
| 159 | I915_MODIFY_DISPBASE(SPRSURF(pipe), 0); | 164 | I915_MODIFY_DISPBASE(SPRSURF(pipe), 0); |
| 160 | POSTING_READ(SPRSURF(pipe)); | 165 | POSTING_READ(SPRSURF(pipe)); |
| 161 | 166 | ||
| 162 | dev_priv->sprite_scaling_enabled = false; | 167 | dev_priv->sprite_scaling_enabled &= ~(1 << pipe); |
| 163 | intel_update_watermarks(dev); | 168 | |
| 169 | /* potentially re-enable LP watermarks */ | ||
| 170 | if (scaling_was_enabled && !dev_priv->sprite_scaling_enabled) | ||
| 171 | intel_update_watermarks(dev); | ||
| 164 | } | 172 | } |
| 165 | 173 | ||
| 166 | static int | 174 | static int |
| @@ -287,8 +295,8 @@ ilk_update_plane(struct drm_plane *plane, struct drm_framebuffer *fb, | |||
| 287 | 295 | ||
| 288 | linear_offset = y * fb->pitches[0] + x * pixel_size; | 296 | linear_offset = y * fb->pitches[0] + x * pixel_size; |
| 289 | dvssurf_offset = | 297 | dvssurf_offset = |
| 290 | intel_gen4_compute_offset_xtiled(&x, &y, | 298 | intel_gen4_compute_page_offset(&x, &y, obj->tiling_mode, |
| 291 | pixel_size, fb->pitches[0]); | 299 | pixel_size, fb->pitches[0]); |
| 292 | linear_offset -= dvssurf_offset; | 300 | linear_offset -= dvssurf_offset; |
| 293 | 301 | ||
| 294 | if (obj->tiling_mode != I915_TILING_NONE) | 302 | if (obj->tiling_mode != I915_TILING_NONE) |
| @@ -593,7 +601,7 @@ int intel_sprite_set_colorkey(struct drm_device *dev, void *data, | |||
| 593 | if ((set->flags & (I915_SET_COLORKEY_DESTINATION | I915_SET_COLORKEY_SOURCE)) == (I915_SET_COLORKEY_DESTINATION | I915_SET_COLORKEY_SOURCE)) | 601 | if ((set->flags & (I915_SET_COLORKEY_DESTINATION | I915_SET_COLORKEY_SOURCE)) == (I915_SET_COLORKEY_DESTINATION | I915_SET_COLORKEY_SOURCE)) |
| 594 | return -EINVAL; | 602 | return -EINVAL; |
| 595 | 603 | ||
| 596 | mutex_lock(&dev->mode_config.mutex); | 604 | drm_modeset_lock_all(dev); |
| 597 | 605 | ||
| 598 | obj = drm_mode_object_find(dev, set->plane_id, DRM_MODE_OBJECT_PLANE); | 606 | obj = drm_mode_object_find(dev, set->plane_id, DRM_MODE_OBJECT_PLANE); |
| 599 | if (!obj) { | 607 | if (!obj) { |
| @@ -606,7 +614,7 @@ int intel_sprite_set_colorkey(struct drm_device *dev, void *data, | |||
| 606 | ret = intel_plane->update_colorkey(plane, set); | 614 | ret = intel_plane->update_colorkey(plane, set); |
| 607 | 615 | ||
| 608 | out_unlock: | 616 | out_unlock: |
| 609 | mutex_unlock(&dev->mode_config.mutex); | 617 | drm_modeset_unlock_all(dev); |
| 610 | return ret; | 618 | return ret; |
| 611 | } | 619 | } |
| 612 | 620 | ||
| @@ -622,7 +630,7 @@ int intel_sprite_get_colorkey(struct drm_device *dev, void *data, | |||
| 622 | if (!drm_core_check_feature(dev, DRIVER_MODESET)) | 630 | if (!drm_core_check_feature(dev, DRIVER_MODESET)) |
| 623 | return -ENODEV; | 631 | return -ENODEV; |
| 624 | 632 | ||
| 625 | mutex_lock(&dev->mode_config.mutex); | 633 | drm_modeset_lock_all(dev); |
| 626 | 634 | ||
| 627 | obj = drm_mode_object_find(dev, get->plane_id, DRM_MODE_OBJECT_PLANE); | 635 | obj = drm_mode_object_find(dev, get->plane_id, DRM_MODE_OBJECT_PLANE); |
| 628 | if (!obj) { | 636 | if (!obj) { |
| @@ -635,7 +643,7 @@ int intel_sprite_get_colorkey(struct drm_device *dev, void *data, | |||
| 635 | intel_plane->get_colorkey(plane, get); | 643 | intel_plane->get_colorkey(plane, get); |
| 636 | 644 | ||
| 637 | out_unlock: | 645 | out_unlock: |
| 638 | mutex_unlock(&dev->mode_config.mutex); | 646 | drm_modeset_unlock_all(dev); |
| 639 | return ret; | 647 | return ret; |
| 640 | } | 648 | } |
| 641 | 649 | ||
