From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from gabe.freedesktop.org (gabe.freedesktop.org [131.252.210.177]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id B99E9CCD185 for ; Thu, 9 Oct 2025 11:39:37 +0000 (UTC) Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 2923B10E9D2; Thu, 9 Oct 2025 11:39:37 +0000 (UTC) Authentication-Results: gabe.freedesktop.org; dkim=pass (2048-bit key; unprotected) header.d=bootlin.com header.i=@bootlin.com header.b="N133HeLJ"; dkim-atps=neutral Received: from smtpout-03.galae.net (smtpout-03.galae.net [185.246.85.4]) by gabe.freedesktop.org (Postfix) with ESMTPS id EA37310E9D1 for ; Thu, 9 Oct 2025 11:39:35 +0000 (UTC) Received: from smtpout-01.galae.net (smtpout-01.galae.net [212.83.139.233]) by smtpout-03.galae.net (Postfix) with ESMTPS id D3B7F4E40FB3; Thu, 9 Oct 2025 11:39:34 +0000 (UTC) Received: from mail.galae.net (mail.galae.net [212.83.136.155]) by smtpout-01.galae.net (Postfix) with ESMTPS id AA1246062C; Thu, 9 Oct 2025 11:39:34 +0000 (UTC) Received: from [127.0.0.1] (localhost [127.0.0.1]) by localhost (Mailerdaemon) with ESMTPSA id D13A3102F21DF; Thu, 9 Oct 2025 13:39:31 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=bootlin.com; s=dkim; t=1760009973; h=from:subject:date:message-id:to:cc:mime-version:content-type: content-transfer-encoding:in-reply-to:references; bh=+6w2LGFkAPvd0Ovd15hto8M5BEHW4sdwoZVyfuKtfTQ=; b=N133HeLJc45ll/GgeFG7ZLBOSkhuj0RlYV8M3jsfp/2tTZK6+UixQnzoasWf21cgPNqa0/ HbAAi9W817kDHbFGAiCSup+6yBzZ/8xdbZpdYjUDkYbnVqq5PUgdRgnB/BqmGlOJNooCWp TyGnzlC6X9ZoYBmKLW4/T6sTbaH7lNasJUTcaAeE7CIXIGOcGn/NRW3trEL06uju8tVF7Y cNeUxCEr8dADPwS9zBcncey8FVNrG0XUSY/p70MIS/z4Cs2jvb+tA0qQRGFQEKph3j6Ca6 RTYwoDQrvayQdaYEfayBQVlnUXvhQ3tVtOc1vhPoxe48W0JVfIngglFGHU2VxA== From: Luca Ceresoli Date: Thu, 09 Oct 2025 13:39:02 +0200 Subject: [PATCH v3 7/7] drm/bridge: prevent encoder chain changes in pre_enable/post_disable MIME-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: 7bit Message-Id: <20251009-drm-bridge-alloc-encoder-chain-mutex-v3-7-c90ed744efec@bootlin.com> References: <20251009-drm-bridge-alloc-encoder-chain-mutex-v3-0-c90ed744efec@bootlin.com> In-Reply-To: <20251009-drm-bridge-alloc-encoder-chain-mutex-v3-0-c90ed744efec@bootlin.com> To: Maarten Lankhorst , Maxime Ripard , Thomas Zimmermann , David Airlie , Simona Vetter , Andrzej Hajda , Neil Armstrong , Robert Foss , Laurent Pinchart , Jonas Karlman , Jernej Skrabec Cc: Hui Pu , Thomas Petazzoni , dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org, Luca Ceresoli X-Mailer: b4 0.14.2 X-Last-TLS-Session-Version: TLSv1.3 X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" Take the encoder chain mutex while iterating over the encoder chain in drm_atomic_bridge_chain_pre_enable() and drm_atomic_bridge_chain_post_disable() to ensure the lists won't change while being inspected. These functions have nested list_for_each_*() loops, which makes them complicated. list_for_each_entry_from() loops could be replaced by drm_for_each_bridge_in_chain_from(), but it would not work in a nested way in its current implementation. Besides, there is no "_reverse" variant of drm_for_each_bridge_in_chain_from(). Keep code simple and readable by explicitly locking around the outer loop. Thankfully there are no break or return points inside the loops, so the change is trivial and readable. Signed-off-by: Luca Ceresoli --- Changes in v3: - Lock encoder->bridge_chain_mutex directly, no wrappers - Improved commit message Changes in v2: - Improved commit message --- drivers/gpu/drm/drm_bridge.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/drivers/gpu/drm/drm_bridge.c b/drivers/gpu/drm/drm_bridge.c index 6de9b296c0be247f861815b7f558a80fd7938fae..a84aa68064513c654d6cc908718c79179f776ee7 100644 --- a/drivers/gpu/drm/drm_bridge.c +++ b/drivers/gpu/drm/drm_bridge.c @@ -760,6 +760,7 @@ void drm_atomic_bridge_chain_post_disable(struct drm_bridge *bridge, encoder = bridge->encoder; + mutex_lock(&encoder->bridge_chain_mutex); list_for_each_entry_from(bridge, &encoder->bridge_chain, chain_node) { limit = NULL; @@ -808,6 +809,7 @@ void drm_atomic_bridge_chain_post_disable(struct drm_bridge *bridge, /* Jump all bridges that we have already post_disabled */ bridge = limit; } + mutex_unlock(&encoder->bridge_chain_mutex); } EXPORT_SYMBOL(drm_atomic_bridge_chain_post_disable); @@ -854,6 +856,7 @@ void drm_atomic_bridge_chain_pre_enable(struct drm_bridge *bridge, encoder = bridge->encoder; + mutex_lock(&encoder->bridge_chain_mutex); list_for_each_entry_reverse(iter, &encoder->bridge_chain, chain_node) { if (iter->pre_enable_prev_first) { next = iter; @@ -896,6 +899,7 @@ void drm_atomic_bridge_chain_pre_enable(struct drm_bridge *bridge, if (iter == bridge) break; } + mutex_unlock(&encoder->bridge_chain_mutex); } EXPORT_SYMBOL(drm_atomic_bridge_chain_pre_enable); -- 2.51.0