From patchwork Thu Jun 16 09:03:21 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Dmitry Baryshkov X-Patchwork-Id: 12883619 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 vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id DB04DC43334 for ; Thu, 16 Jun 2022 09:03:33 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1359454AbiFPJDc (ORCPT ); Thu, 16 Jun 2022 05:03:32 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:59002 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1376534AbiFPJD2 (ORCPT ); Thu, 16 Jun 2022 05:03:28 -0400 Received: from mail-lf1-x129.google.com (mail-lf1-x129.google.com [IPv6:2a00:1450:4864:20::129]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 04A622F027 for ; Thu, 16 Jun 2022 02:03:27 -0700 (PDT) Received: by mail-lf1-x129.google.com with SMTP id y32so1227731lfa.6 for ; Thu, 16 Jun 2022 02:03:26 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references :mime-version:content-transfer-encoding; bh=xFxbtir+yx3bkT7Nfr3pjUYhJCe5yYonGxiU09T4Cq8=; b=da+ZcR2V6FQe9mxSclf2WnRaQ8tgrqMrNadgdzDmprNx2lmwa9F8xJNX9tqigCO2fW SCMuauxUZAk5ThWj7S+wOkYT1LwrkT/Elv5z+OKi+bK34Gnc7tzgHpO2TXExN7yOx4dC w2crqcGtlbGXDVHNlVwV1NhDqNcMY4S6p25xdzjUA9PC64ErxFEaXR5KeM9KlxgsBA7x iTUSLrpApedlMLzYn/8dAiRwVoYCAJRHSmWJP+RXR+ch746h69yKFDX5s1+5hrzz3L7F Xn2PLSr80U0SpZpxuT+/ivKwQPz4rqVgBZc9GAUpBVfjOYH7lNAJCAS/zriKdS4/s5lE nf4w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=xFxbtir+yx3bkT7Nfr3pjUYhJCe5yYonGxiU09T4Cq8=; b=53wviLko2gCquKq8uVXaen2Ne3AqWJ8OJNAa/KzZH3ukVAaRDvOX+83PA+BkU7oMv3 7cobJFqtLrVduVra5ymr+Fospb4AhxaECKLP+ynZkO2asIvrmSmBSwfbFi6vq5NO5P8w T/9Bg8NRpJWsXbPboj1/o3PzyJMPV7siwFQ0Ob3j9Pg77/8CLH0NOVFn0s5zhgI5yFro oa3Rdkitb9B9QnCdmeohEppA5ct3gJ3cnniUw6jlzy7cgR0H6mtiyTRfrAGBvzumhd5P h4rX62gFfkgFwl3nMYBNIMt/opOlrCV1fUWfpSpVTWVA5gstb96v5PJfemV1sc9m2Wdt xpjA== X-Gm-Message-State: AJIora+b5j1Djq3xbJulKu6qX41in02fKpJ9xPL0FjAaMKiiIbDhmjUD jRUIRkhY61Xa7cVOI4XIYfpkuA== X-Google-Smtp-Source: AGRyM1tOP8zrJP1knC84OK++AOGrKy1Ek0dDGga8Bf9kQf5cVGjrBzOW9AndwYeCQaA2EErGg6q42A== X-Received: by 2002:a05:6512:314b:b0:47f:40e4:d9a with SMTP id s11-20020a056512314b00b0047f40e40d9amr2124440lfi.278.1655370205008; Thu, 16 Jun 2022 02:03:25 -0700 (PDT) Received: from eriador.lan ([37.153.55.125]) by smtp.gmail.com with ESMTPSA id j9-20020a2e8009000000b0025575338c41sm172573ljg.127.2022.06.16.02.03.23 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 16 Jun 2022 02:03:24 -0700 (PDT) From: Dmitry Baryshkov To: Rob Clark , Sean Paul , Abhinav Kumar Cc: Stephen Boyd , David Airlie , Daniel Vetter , Bjorn Andersson , linux-arm-msm@vger.kernel.org, dri-devel@lists.freedesktop.org, freedreno@lists.freedesktop.org Subject: [RFC PATCH 2/2] drm/msm/mdp4: switch LVDS to use drm_bridge/_connector Date: Thu, 16 Jun 2022 12:03:21 +0300 Message-Id: <20220616090321.433249-3-dmitry.baryshkov@linaro.org> X-Mailer: git-send-email 2.35.1 In-Reply-To: <20220616090321.433249-1-dmitry.baryshkov@linaro.org> References: <20220616090321.433249-1-dmitry.baryshkov@linaro.org> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-arm-msm@vger.kernel.org LVDS support in MDP4 driver makes use of drm_connector directly. However LCDC encoder and LVDS connector are wrappers around drm_panel. Switch them to use drm_panel_bridge/drm_bridge_connector. This allows using standard interface for the drm_panel and also inserting additional bridges between encoder and panel. Signed-off-by: Dmitry Baryshkov --- drivers/gpu/drm/msm/Makefile | 1 - drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c | 32 ++++-- drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.h | 6 +- .../gpu/drm/msm/disp/mdp4/mdp4_lcdc_encoder.c | 20 +--- .../drm/msm/disp/mdp4/mdp4_lvds_connector.c | 100 ------------------ 5 files changed, 28 insertions(+), 131 deletions(-) delete mode 100644 drivers/gpu/drm/msm/disp/mdp4/mdp4_lvds_connector.c diff --git a/drivers/gpu/drm/msm/Makefile b/drivers/gpu/drm/msm/Makefile index 66395ee0862a..709952c998e0 100644 --- a/drivers/gpu/drm/msm/Makefile +++ b/drivers/gpu/drm/msm/Makefile @@ -35,7 +35,6 @@ msm-$(CONFIG_DRM_MSM_MDP4) += \ disp/mdp4/mdp4_dsi_encoder.o \ disp/mdp4/mdp4_dtv_encoder.o \ disp/mdp4/mdp4_lcdc_encoder.o \ - disp/mdp4/mdp4_lvds_connector.o \ disp/mdp4/mdp4_lvds_pll.o \ disp/mdp4/mdp4_irq.o \ disp/mdp4/mdp4_kms.o \ diff --git a/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c b/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c index fb48c8c19ec3..77ef3114a919 100644 --- a/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c +++ b/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c @@ -6,6 +6,8 @@ #include +#include +#include #include #include "msm_drv.h" @@ -199,7 +201,7 @@ static int mdp4_modeset_init_intf(struct mdp4_kms *mdp4_kms, struct msm_drm_private *priv = dev->dev_private; struct drm_encoder *encoder; struct drm_connector *connector; - struct device_node *panel_node; + struct drm_bridge *next_bridge; int dsi_id; int ret; @@ -209,11 +211,15 @@ static int mdp4_modeset_init_intf(struct mdp4_kms *mdp4_kms, * bail out early if there is no panel node (no need to * initialize LCDC encoder and LVDS connector) */ - panel_node = of_graph_get_remote_node(dev->dev->of_node, 0, 0); - if (!panel_node) - return 0; + next_bridge = devm_drm_of_get_bridge(dev->dev, dev->dev->of_node, 0, 0); + if (IS_ERR(next_bridge)) { + ret = PTR_ERR(next_bridge); + if (ret == -ENODEV) + return 0; + return ret; + } - encoder = mdp4_lcdc_encoder_init(dev, panel_node); + encoder = mdp4_lcdc_encoder_init(dev); if (IS_ERR(encoder)) { DRM_DEV_ERROR(dev->dev, "failed to construct LCDC encoder\n"); return PTR_ERR(encoder); @@ -222,12 +228,26 @@ static int mdp4_modeset_init_intf(struct mdp4_kms *mdp4_kms, /* LCDC can be hooked to DMA_P (TODO: Add DMA_S later?) */ encoder->possible_crtcs = 1 << DMA_P; - connector = mdp4_lvds_connector_init(dev, panel_node, encoder); + ret = drm_bridge_attach(encoder, next_bridge, NULL, DRM_BRIDGE_ATTACH_NO_CONNECTOR); + if (ret) { + DRM_DEV_ERROR(dev->dev, "failed to attach LVDS panel/bridge: %d\n", ret); + + return ret; + } + + connector = drm_bridge_connector_init(dev, encoder); if (IS_ERR(connector)) { DRM_DEV_ERROR(dev->dev, "failed to initialize LVDS connector\n"); return PTR_ERR(connector); } + ret = drm_connector_attach_encoder(connector, encoder); + if (ret) { + DRM_DEV_ERROR(dev->dev, "failed to attach LVDS connector: %d\n", ret); + + return ret; + } + break; case DRM_MODE_ENCODER_TMDS: encoder = mdp4_dtv_encoder_init(dev); diff --git a/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.h b/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.h index d27fa761bfc2..7535dc343b64 100644 --- a/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.h +++ b/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.h @@ -197,11 +197,7 @@ struct drm_crtc *mdp4_crtc_init(struct drm_device *dev, long mdp4_dtv_round_pixclk(struct drm_encoder *encoder, unsigned long rate); struct drm_encoder *mdp4_dtv_encoder_init(struct drm_device *dev); -struct drm_encoder *mdp4_lcdc_encoder_init(struct drm_device *dev, - struct device_node *panel_node); - -struct drm_connector *mdp4_lvds_connector_init(struct drm_device *dev, - struct device_node *panel_node, struct drm_encoder *encoder); +struct drm_encoder *mdp4_lcdc_encoder_init(struct drm_device *dev); #ifdef CONFIG_DRM_MSM_DSI struct drm_encoder *mdp4_dsi_encoder_init(struct drm_device *dev); diff --git a/drivers/gpu/drm/msm/disp/mdp4/mdp4_lcdc_encoder.c b/drivers/gpu/drm/msm/disp/mdp4/mdp4_lcdc_encoder.c index 341dcd5087da..46d901fa0da0 100644 --- a/drivers/gpu/drm/msm/disp/mdp4/mdp4_lcdc_encoder.c +++ b/drivers/gpu/drm/msm/disp/mdp4/mdp4_lcdc_encoder.c @@ -14,7 +14,6 @@ struct mdp4_lcdc_encoder { struct drm_encoder base; - struct device_node *panel_node; struct drm_panel *panel; struct clk *lcdc_clk; unsigned long int pixclock; @@ -275,7 +274,6 @@ static void mdp4_lcdc_encoder_disable(struct drm_encoder *encoder) struct mdp4_lcdc_encoder *mdp4_lcdc_encoder = to_mdp4_lcdc_encoder(encoder); struct mdp4_kms *mdp4_kms = get_kms(encoder); - struct drm_panel *panel; int i, ret; if (WARN_ON(!mdp4_lcdc_encoder->enabled)) @@ -283,12 +281,6 @@ static void mdp4_lcdc_encoder_disable(struct drm_encoder *encoder) mdp4_write(mdp4_kms, REG_MDP4_LCDC_ENABLE, 0); - panel = of_drm_find_panel(mdp4_lcdc_encoder->panel_node); - if (!IS_ERR(panel)) { - drm_panel_disable(panel); - drm_panel_unprepare(panel); - } - /* * Wait for a vsync so we know the ENABLE=0 latched before * the (connector) source of the vsync's gets disabled, @@ -317,7 +309,6 @@ static void mdp4_lcdc_encoder_enable(struct drm_encoder *encoder) to_mdp4_lcdc_encoder(encoder); unsigned long pc = mdp4_lcdc_encoder->pixclock; struct mdp4_kms *mdp4_kms = get_kms(encoder); - struct drm_panel *panel; uint32_t config; int i, ret; @@ -353,12 +344,6 @@ static void mdp4_lcdc_encoder_enable(struct drm_encoder *encoder) if (ret) DRM_DEV_ERROR(dev->dev, "failed to enable lcdc_clk: %d\n", ret); - panel = of_drm_find_panel(mdp4_lcdc_encoder->panel_node); - if (!IS_ERR(panel)) { - drm_panel_prepare(panel); - drm_panel_enable(panel); - } - setup_phy(encoder); mdp4_write(mdp4_kms, REG_MDP4_LCDC_ENABLE, 1); @@ -392,8 +377,7 @@ static const struct drm_encoder_helper_funcs mdp4_lcdc_encoder_helper_funcs = { }; /* initialize encoder */ -struct drm_encoder *mdp4_lcdc_encoder_init(struct drm_device *dev, - struct device_node *panel_node) +struct drm_encoder *mdp4_lcdc_encoder_init(struct drm_device *dev) { struct drm_encoder *encoder = NULL; struct mdp4_lcdc_encoder *mdp4_lcdc_encoder; @@ -406,8 +390,6 @@ struct drm_encoder *mdp4_lcdc_encoder_init(struct drm_device *dev, goto fail; } - mdp4_lcdc_encoder->panel_node = panel_node; - encoder = &mdp4_lcdc_encoder->base; drm_encoder_init(dev, encoder, &mdp4_lcdc_encoder_funcs, diff --git a/drivers/gpu/drm/msm/disp/mdp4/mdp4_lvds_connector.c b/drivers/gpu/drm/msm/disp/mdp4/mdp4_lvds_connector.c deleted file mode 100644 index 4755eb13ef79..000000000000 --- a/drivers/gpu/drm/msm/disp/mdp4/mdp4_lvds_connector.c +++ /dev/null @@ -1,100 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0-only -/* - * Copyright (C) 2014 Red Hat - * Author: Rob Clark - * Author: Vinay Simha - */ - -#include "mdp4_kms.h" - -struct mdp4_lvds_connector { - struct drm_connector base; - struct drm_encoder *encoder; - struct device_node *panel_node; - struct drm_panel *panel; -}; -#define to_mdp4_lvds_connector(x) container_of(x, struct mdp4_lvds_connector, base) - -static enum drm_connector_status mdp4_lvds_connector_detect( - struct drm_connector *connector, bool force) -{ - struct mdp4_lvds_connector *mdp4_lvds_connector = - to_mdp4_lvds_connector(connector); - - if (!mdp4_lvds_connector->panel) { - mdp4_lvds_connector->panel = - of_drm_find_panel(mdp4_lvds_connector->panel_node); - if (IS_ERR(mdp4_lvds_connector->panel)) - mdp4_lvds_connector->panel = NULL; - } - - return mdp4_lvds_connector->panel ? - connector_status_connected : - connector_status_disconnected; -} - -static void mdp4_lvds_connector_destroy(struct drm_connector *connector) -{ - struct mdp4_lvds_connector *mdp4_lvds_connector = - to_mdp4_lvds_connector(connector); - - drm_connector_cleanup(connector); - - kfree(mdp4_lvds_connector); -} - -static int mdp4_lvds_connector_get_modes(struct drm_connector *connector) -{ - struct mdp4_lvds_connector *mdp4_lvds_connector = - to_mdp4_lvds_connector(connector); - struct drm_panel *panel = mdp4_lvds_connector->panel; - int ret = 0; - - if (panel) - ret = drm_panel_get_modes(panel, connector); - - return ret; -} - -static const struct drm_connector_funcs mdp4_lvds_connector_funcs = { - .detect = mdp4_lvds_connector_detect, - .fill_modes = drm_helper_probe_single_connector_modes, - .destroy = mdp4_lvds_connector_destroy, - .reset = drm_atomic_helper_connector_reset, - .atomic_duplicate_state = drm_atomic_helper_connector_duplicate_state, - .atomic_destroy_state = drm_atomic_helper_connector_destroy_state, -}; - -static const struct drm_connector_helper_funcs mdp4_lvds_connector_helper_funcs = { - .get_modes = mdp4_lvds_connector_get_modes, -}; - -/* initialize connector */ -struct drm_connector *mdp4_lvds_connector_init(struct drm_device *dev, - struct device_node *panel_node, struct drm_encoder *encoder) -{ - struct drm_connector *connector = NULL; - struct mdp4_lvds_connector *mdp4_lvds_connector; - - mdp4_lvds_connector = kzalloc(sizeof(*mdp4_lvds_connector), GFP_KERNEL); - if (!mdp4_lvds_connector) - return ERR_PTR(-ENOMEM); - - mdp4_lvds_connector->encoder = encoder; - mdp4_lvds_connector->panel_node = panel_node; - - connector = &mdp4_lvds_connector->base; - - drm_connector_init(dev, connector, &mdp4_lvds_connector_funcs, - DRM_MODE_CONNECTOR_LVDS); - drm_connector_helper_add(connector, &mdp4_lvds_connector_helper_funcs); - - connector->polled = 0; - - connector->interlace_allowed = 0; - connector->doublescan_allowed = 0; - - drm_connector_attach_encoder(connector, encoder); - - return connector; -}