diff options
author | Maarten Lankhorst <maarten.lankhorst@linux.intel.com> | 2015-07-13 10:30:29 -0400 |
---|---|---|
committer | Daniel Vetter <daniel.vetter@ffwll.ch> | 2015-07-14 12:09:56 -0400 |
commit | 70e0bd74b9a22ecaa25793bf4f461cf84a1f348a (patch) | |
tree | 93409c42e3cb3b8948b3b557a2fa62f2040e0775 /drivers/gpu/drm/i915/intel_display.c | |
parent | e694eb020f12949a3eb12d4bb4957f0237961b2d (diff) |
drm/i915: Make intel_display_suspend atomic, try 2.
Calculate all state using a normal transition, but afterwards fudge
crtc->state->active back to its old value. This should still allow
state restore in setup_hw_state to work properly.
Signed-off-by: Maarten Lankhorst <maarten.lankhorst@linux.intel.com>
Reviewed-by: Daniel Stone <daniels@collabora.com>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Diffstat (limited to 'drivers/gpu/drm/i915/intel_display.c')
-rw-r--r-- | drivers/gpu/drm/i915/intel_display.c | 52 |
1 files changed, 49 insertions, 3 deletions
diff --git a/drivers/gpu/drm/i915/intel_display.c b/drivers/gpu/drm/i915/intel_display.c index f9ed3732f95f..4e64dae78360 100644 --- a/drivers/gpu/drm/i915/intel_display.c +++ b/drivers/gpu/drm/i915/intel_display.c | |||
@@ -6225,12 +6225,58 @@ static void intel_crtc_disable_noatomic(struct drm_crtc *crtc) | |||
6225 | * turn all crtc's off, but do not adjust state | 6225 | * turn all crtc's off, but do not adjust state |
6226 | * This has to be paired with a call to intel_modeset_setup_hw_state. | 6226 | * This has to be paired with a call to intel_modeset_setup_hw_state. |
6227 | */ | 6227 | */ |
6228 | void intel_display_suspend(struct drm_device *dev) | 6228 | int intel_display_suspend(struct drm_device *dev) |
6229 | { | 6229 | { |
6230 | struct drm_mode_config *config = &dev->mode_config; | ||
6231 | struct drm_modeset_acquire_ctx *ctx = config->acquire_ctx; | ||
6232 | struct drm_atomic_state *state; | ||
6230 | struct drm_crtc *crtc; | 6233 | struct drm_crtc *crtc; |
6234 | unsigned crtc_mask = 0; | ||
6235 | int ret = 0; | ||
6236 | |||
6237 | if (WARN_ON(!ctx)) | ||
6238 | return 0; | ||
6239 | |||
6240 | lockdep_assert_held(&ctx->ww_ctx); | ||
6241 | state = drm_atomic_state_alloc(dev); | ||
6242 | if (WARN_ON(!state)) | ||
6243 | return -ENOMEM; | ||
6244 | |||
6245 | state->acquire_ctx = ctx; | ||
6246 | state->allow_modeset = true; | ||
6247 | |||
6248 | for_each_crtc(dev, crtc) { | ||
6249 | struct drm_crtc_state *crtc_state = | ||
6250 | drm_atomic_get_crtc_state(state, crtc); | ||
6231 | 6251 | ||
6232 | for_each_crtc(dev, crtc) | 6252 | ret = PTR_ERR_OR_ZERO(crtc_state); |
6233 | intel_crtc_disable_noatomic(crtc); | 6253 | if (ret) |
6254 | goto free; | ||
6255 | |||
6256 | if (!crtc_state->active) | ||
6257 | continue; | ||
6258 | |||
6259 | crtc_state->active = false; | ||
6260 | crtc_mask |= 1 << drm_crtc_index(crtc); | ||
6261 | } | ||
6262 | |||
6263 | if (crtc_mask) { | ||
6264 | ret = intel_set_mode(state); | ||
6265 | |||
6266 | if (!ret) { | ||
6267 | for_each_crtc(dev, crtc) | ||
6268 | if (crtc_mask & (1 << drm_crtc_index(crtc))) | ||
6269 | crtc->state->active = true; | ||
6270 | |||
6271 | return ret; | ||
6272 | } | ||
6273 | } | ||
6274 | |||
6275 | free: | ||
6276 | if (ret) | ||
6277 | DRM_ERROR("Suspending crtc's failed with %i\n", ret); | ||
6278 | drm_atomic_state_free(state); | ||
6279 | return ret; | ||
6234 | } | 6280 | } |
6235 | 6281 | ||
6236 | /* Master function to enable/disable CRTC and corresponding power wells */ | 6282 | /* Master function to enable/disable CRTC and corresponding power wells */ |