From ea497bb92064875497554ee7cdf10df7fb7393fc Mon Sep 17 00:00:00 2001 From: Daniel Vetter Date: Wed, 13 Dec 2017 13:49:36 +0100 Subject: drm: rework delayed connector cleanup in connector_iter PROBE_DEFER also uses system_wq to reprobe drivers, which means when that again fails, and we try to flush the overall system_wq (to get all the delayed connectore cleanup work_struct completed), we deadlock. Fix this by using just a single cleanup work, so that we can only flush that one and don't block on anything else. That means a free list plus locking, a standard pattern. v2: - Correctly free connectors only on last ref. Oops (Chris). - use llist_head/node (Chris). v3 - Add init_llist_head (Chris). Fixes: a703c55004e1 ("drm: safely free connectors from connector_iter") Fixes: 613051dac40d ("drm: locking&new iterators for connector_list") Cc: Ben Widawsky Cc: Dave Airlie Cc: Chris Wilson Cc: Sean Paul Cc: # v4.11+: 613051dac40d ("drm: locking&new iterators for connector_list" Cc: # v4.11+ Cc: Daniel Vetter Cc: Jani Nikula Cc: Gustavo Padovan Cc: David Airlie Cc: Javier Martinez Canillas Cc: Shuah Khan Cc: Guillaume Tucker Cc: Mark Brown Cc: Kevin Hilman Cc: Matt Hart Cc: Thierry Escande Cc: Tomeu Vizoso Cc: Enric Balletbo i Serra Tested-by: Marek Szyprowski Reviewed-by: Chris Wilson Signed-off-by: Daniel Vetter Link: https://patchwork.freedesktop.org/patch/msgid/20171213124936.17914-1-daniel.vetter@ffwll.ch --- include/drm/drm_connector.h | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) (limited to 'include/drm/drm_connector.h') diff --git a/include/drm/drm_connector.h b/include/drm/drm_connector.h index a4649c56ca2f..5971577016a2 100644 --- a/include/drm/drm_connector.h +++ b/include/drm/drm_connector.h @@ -24,6 +24,7 @@ #define __DRM_CONNECTOR_H__ #include +#include #include #include #include @@ -918,12 +919,13 @@ struct drm_connector { uint16_t tile_h_size, tile_v_size; /** - * @free_work: + * @free_node: * - * Work used only by &drm_connector_iter to be able to clean up a - * connector from any context. + * List used only by &drm_connector_iter to be able to clean up a + * connector from any context, in conjunction with + * &drm_mode_config.connector_free_work. */ - struct work_struct free_work; + struct llist_node free_node; }; #define obj_to_connector(x) container_of(x, struct drm_connector, base) -- cgit