From 10bf0a38c4084c14c57df5d635a5ba0867a3c260 Mon Sep 17 00:00:00 2001 From: Maarten Lankhorst Date: Fri, 10 Nov 2017 12:34:58 +0100 Subject: [PATCH] drm/i915: Handle locking better in i915_sink_crc. Lock the bare minimum, instead of the entire world, and use interruptible locking because we can. Signed-off-by: Maarten Lankhorst Link: https://patchwork.freedesktop.org/patch/msgid/20171110113503.16253-6-maarten.lankhorst@linux.intel.com Reviewed-by: Daniel Vetter --- drivers/gpu/drm/i915/i915_debugfs.c | 40 +++++++++++++++++++++++------ 1 file changed, 32 insertions(+), 8 deletions(-) diff --git a/drivers/gpu/drm/i915/i915_debugfs.c b/drivers/gpu/drm/i915/i915_debugfs.c index 533ba096b9a6..cb77aeab4ee2 100644 --- a/drivers/gpu/drm/i915/i915_debugfs.c +++ b/drivers/gpu/drm/i915/i915_debugfs.c @@ -2735,39 +2735,63 @@ static int i915_sink_crc(struct seq_file *m, void *data) struct intel_connector *connector; struct drm_connector_list_iter conn_iter; struct intel_dp *intel_dp = NULL; + struct drm_modeset_acquire_ctx ctx; int ret; u8 crc[6]; - drm_modeset_lock_all(dev); + drm_modeset_acquire_init(&ctx, DRM_MODESET_ACQUIRE_INTERRUPTIBLE); + drm_connector_list_iter_begin(dev, &conn_iter); + for_each_intel_connector_iter(connector, &conn_iter) { struct drm_crtc *crtc; + struct drm_connector_state *state; - if (!connector->base.state->best_encoder) + if (connector->base.connector_type != DRM_MODE_CONNECTOR_eDP) continue; - crtc = connector->base.state->crtc; - if (!crtc->state->active) +retry: + ret = drm_modeset_lock(&dev->mode_config.connection_mutex, &ctx); + if (ret) + goto err; + + state = connector->base.state; + if (!state->best_encoder) continue; - if (connector->base.connector_type != DRM_MODE_CONNECTOR_eDP) + crtc = state->crtc; + ret = drm_modeset_lock(&crtc->mutex, &ctx); + if (ret) + goto err; + + if (!crtc->state->active) continue; - intel_dp = enc_to_intel_dp(connector->base.state->best_encoder); + intel_dp = enc_to_intel_dp(state->best_encoder); ret = intel_dp_sink_crc(intel_dp, crc); if (ret) - goto out; + goto err; seq_printf(m, "%02x%02x%02x%02x%02x%02x\n", crc[0], crc[1], crc[2], crc[3], crc[4], crc[5]); goto out; + +err: + if (ret == -EDEADLK) { + ret = drm_modeset_backoff(&ctx); + if (!ret) + goto retry; + } + goto out; } ret = -ENODEV; out: drm_connector_list_iter_end(&conn_iter); - drm_modeset_unlock_all(dev); + drm_modeset_drop_locks(&ctx); + drm_modeset_acquire_fini(&ctx); + return ret; } -- GitLab