Received: by 2002:a05:6a10:413:0:0:0:0 with SMTP id 19csp558551pxp; Wed, 9 Mar 2022 08:09:43 -0800 (PST) X-Google-Smtp-Source: ABdhPJyTSerTiRwGD69melPwqcjQbct5xAivC5KrLL6DECfkgd/wbpl/GOGeMTGP+YJ7Uk+uW8PW X-Received: by 2002:a54:4502:0:b0:2d9:a01a:4c01 with SMTP id l2-20020a544502000000b002d9a01a4c01mr176291oil.296.1646842183645; Wed, 09 Mar 2022 08:09:43 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1646842183; cv=none; d=google.com; s=arc-20160816; b=b7abXb7HHiMloTDUIjF+Z3VKe9AX665n8+pNlzuglD7G4Wdw2nmfpjIMUkPpOiGyWS E/ld007KGAlKvP8r9AklRaRoOH4IvpCM6bGJs/cZ+oGBWQ5YIZgqq4jNgHKt2Jhk7cne aXBlELHFAr3M3fVqKUQ33no1fURSDA9CDjgdsNdX307r3Mv7xN354TMikvHUTdxaU4PY npCPgdDn2a+yVjyiT1WDjEjrUFx25beaAZAUjRAJPDKpzVmBvOwHUvgo2xOSjmmh9J5t jiAafJ2HespbH1CZi2Kd046rJ/VAX+U/mAKhi40w0DdrdA3+Y8Awmh+CRuDAy4Z3IHtJ M+Ng== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :message-id:date:subject:cc:to:from:dkim-signature; bh=4yNE8unHQFaK7qSnkWkqczTG141cySTJ7pfi48d6wGI=; b=TcnJSoWzbbCilrWjDfQZJO0k+q4vqMS+3k343VEwnJQOHAOtnBGJ0BF/CLbYcYg8iI I1XbvZvyUfEsWRXyMb5Llyw/JFkYCpnkmYVqihPfB+pcx/V1Ei9/g31zUiTJuLrLuM3U vm1vro4qp+iImObFThWswCzx4B9odztoGsB/FrKAVaTFCFRfF/L2uYAIs2bUPhz0D0JO Gar36d9GA1MXDYAOCwiJFuwyup2n28P/lqRInojg/hZc4Sj0+EpwOhAdIr2kXi2otIZK nMFkCZgrJb8oZFtibDzSQUpRIBMmWNnXl7FhknVCEAd17pnhZxp2nt+lPBAt/2nbAm68 v3xA== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@bootlin.com header.s=gm1 header.b=JSLpwvLw; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=bootlin.com Return-Path: Received: from out1.vger.email (out1.vger.email. [2620:137:e000::1:20]) by mx.google.com with ESMTP id 62-20020a9d0644000000b005b26b3bae5asi895235otn.108.2022.03.09.08.09.05; Wed, 09 Mar 2022 08:09:43 -0800 (PST) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) client-ip=2620:137:e000::1:20; Authentication-Results: mx.google.com; dkim=pass header.i=@bootlin.com header.s=gm1 header.b=JSLpwvLw; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 2620:137:e000::1:20 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=REJECT sp=REJECT dis=NONE) header.from=bootlin.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S233544AbiCIOdN (ORCPT + 99 others); Wed, 9 Mar 2022 09:33:13 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59954 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229703AbiCIOdL (ORCPT ); Wed, 9 Mar 2022 09:33:11 -0500 Received: from relay9-d.mail.gandi.net (relay9-d.mail.gandi.net [IPv6:2001:4b98:dc4:8::229]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 77BE81520FE for ; Wed, 9 Mar 2022 06:32:11 -0800 (PST) Received: (Authenticated sender: paul.kocialkowski@bootlin.com) by mail.gandi.net (Postfix) with ESMTPSA id F3C35FF810; Wed, 9 Mar 2022 14:32:08 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=bootlin.com; s=gm1; t=1646836330; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:cc:mime-version:mime-version: content-transfer-encoding:content-transfer-encoding; bh=4yNE8unHQFaK7qSnkWkqczTG141cySTJ7pfi48d6wGI=; b=JSLpwvLwjh4zr2SARMq3/4EKIuKAzfnLT6dtVBbpVJSI9lfj+AdtHbu3lQ0KqXdK1Zdm7r p3uRrHJFghTZBLI/FfjKZ8hO3w2S0jk1ihjRUlmgNn9hk7bg0gHvreyBuAkaVfHfF9b/qm rP8UJm+DJpbSKqfyQqmgyyl4ocFMel5r+g3QXrsm7SyIknIa2SsJd0S/pGcVp+oMH+/j2g Ke/ycL7pqtg2h+6Ka51h1fmJySwkg6Evvn6qBnsdwIEgRn2iE2HZceYW3mv0MKwXIMD8nb fpQIKa5Ttw95A+dtOJR6mPicRQheMthKZsGHEKuwSg0JxDDuXNyVnEKgZveTkQ== From: Paul Kocialkowski To: dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org Cc: Maarten Lankhorst , Maxime Ripard , Thomas Zimmermann , David Airlie , Daniel Vetter , Linus Walleij , Jagan Teki , Paul Kocialkowski Subject: [PATCH] drm: of: Properly try all possible cases for bridge/panel detection Date: Wed, 9 Mar 2022 15:32:00 +0100 Message-Id: <20220309143200.111292-1-paul.kocialkowski@bootlin.com> X-Mailer: git-send-email 2.35.1 MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Spam-Status: No, score=-2.8 required=5.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,DKIM_VALID_EF,RCVD_IN_DNSWL_LOW,SPF_HELO_NONE, SPF_PASS,T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on lindbergh.monkeyblade.net Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org While bridge/panel detection was initially relying on the usual port/ports-based of graph detection, it was recently changed to perform the lookup on any child node that is not port/ports instead when such a node is available, with no fallback on the usual way. This results in breaking detection when a child node is present but does not contain any panel or bridge node, even when the usual port/ports-based of graph is there. In order to support both situations properly, this commit reworks the logic to try both options and not just one of the two: it will only return -EPROBE_DEFER when both have failed. Signed-off-by: Paul Kocialkowski Fixes: 80253168dbfd ("drm: of: Lookup if child node has panel or bridge") --- drivers/gpu/drm/drm_of.c | 93 +++++++++++++++++++++------------------- 1 file changed, 49 insertions(+), 44 deletions(-) diff --git a/drivers/gpu/drm/drm_of.c b/drivers/gpu/drm/drm_of.c index 9d90cd75c457..67f1b7dfc892 100644 --- a/drivers/gpu/drm/drm_of.c +++ b/drivers/gpu/drm/drm_of.c @@ -219,6 +219,35 @@ int drm_of_encoder_active_endpoint(struct device_node *node, } EXPORT_SYMBOL_GPL(drm_of_encoder_active_endpoint); +static int drm_of_find_remote_panel_or_bridge(struct device_node *remote, + struct drm_panel **panel, + struct drm_bridge **bridge) +{ + int ret = -EPROBE_DEFER; + + if (panel) { + *panel = of_drm_find_panel(remote); + if (!IS_ERR(*panel)) + ret = 0; + else + *panel = NULL; + } + + /* No panel found yet, check for a bridge next. */ + if (bridge) { + if (ret) { + *bridge = of_drm_find_bridge(remote); + if (*bridge) + ret = 0; + } else { + *bridge = NULL; + } + + } + + return ret; +} + /** * drm_of_find_panel_or_bridge - return connected panel or bridge device * @np: device tree node containing encoder output ports @@ -249,57 +278,33 @@ int drm_of_find_panel_or_bridge(const struct device_node *np, if (panel) *panel = NULL; - /** - * Devices can also be child nodes when we also control that device - * through the upstream device (ie, MIPI-DCS for a MIPI-DSI device). - * - * Lookup for a child node of the given parent that isn't either port - * or ports. - */ - for_each_available_child_of_node(np, remote) { - if (of_node_name_eq(remote, "port") || - of_node_name_eq(remote, "ports")) - continue; - - goto of_find_panel_or_bridge; + /* Check for a graph on the device node first. */ + if (of_graph_is_present(np)) { + remote = of_graph_get_remote_node(np, port, endpoint); + if (remote) { + ret = drm_of_find_remote_panel_or_bridge(remote, panel, + bridge); + of_node_put(remote); + } } - /* - * of_graph_get_remote_node() produces a noisy error message if port - * node isn't found and the absence of the port is a legit case here, - * so at first we silently check whether graph presents in the - * device-tree node. - */ - if (!of_graph_is_present(np)) - return -ENODEV; - - remote = of_graph_get_remote_node(np, port, endpoint); - -of_find_panel_or_bridge: - if (!remote) - return -ENODEV; + /* Otherwise check for any child node other than port/ports. */ + if (ret) { + for_each_available_child_of_node(np, remote) { + if (of_node_name_eq(remote, "port") || + of_node_name_eq(remote, "ports")) + continue; - if (panel) { - *panel = of_drm_find_panel(remote); - if (!IS_ERR(*panel)) - ret = 0; - else - *panel = NULL; - } + ret = drm_of_find_remote_panel_or_bridge(remote, panel, + bridge); + of_node_put(remote); - /* No panel found yet, check for a bridge next. */ - if (bridge) { - if (ret) { - *bridge = of_drm_find_bridge(remote); - if (*bridge) - ret = 0; - } else { - *bridge = NULL; + /* Stop at the first found occurrence. */ + if (!ret) + break; } - } - of_node_put(remote); return ret; } EXPORT_SYMBOL_GPL(drm_of_find_panel_or_bridge); -- 2.35.1