Thread (11 messages) 11 messages, 2 authors, 2025-12-23

Re: [PATCH v7 2/2] drm/mediatek: Add isolation to edp

From: LIANKUN YANG (杨连坤) <hidden>
Date: 2025-12-23 06:34:46
Also in: dri-devel, linux-mediatek, lkml

On Wed, 2025-12-17 at 10:08 +0000, CK Hu (胡俊光) wrote:
On Tue, 2025-11-04 at 16:55 +0800, Liankun Yang wrote:
quoted
Because edp doesn't expect any (un)plug events during runtime and
its process differs from DP. Therefore, it is necessary to isolate
the parsing capability, panel power, training state and enable
state.

And DP related behaviors are adjusted to execute in the second half
of the interrupt.
For DP details, see drm/mediatek: Adjust bandwidth limit for DP

Signed-off-by: Liankun Yang <redacted>
---
 drivers/gpu/drm/mediatek/mtk_dp.c | 37 +++++++++++++++----------
------
 1 file changed, 18 insertions(+), 19 deletions(-)
diff --git a/drivers/gpu/drm/mediatek/mtk_dp.c
b/drivers/gpu/drm/mediatek/mtk_dp.c
index 0ba2c208811c..efd4c45985ca 100644
--- a/drivers/gpu/drm/mediatek/mtk_dp.c
+++ b/drivers/gpu/drm/mediatek/mtk_dp.c
@@ -2187,7 +2187,8 @@ static const struct drm_edid
*mtk_dp_edid_read(struct drm_bridge *bridge,
 	 * Parse capability here to let atomic_get_input_bus_fmts and
 	 * mode_valid use the capability to calculate sink bitrates.
 	 */
-	if (mtk_dp_parse_capabilities(mtk_dp)) {
+	if (mtk_dp->bridge.type == DRM_MODE_CONNECTOR_eDP &&
+	    mtk_dp_parse_capabilities(mtk_dp)) {
This is not related to dp training.
If dp does not need to parse edid, describe WHY and do not mix edid
modification with dp training modification.
`mtk_dp_parse_capabilities` is related to DP training, it is
used in `mtk_dp_hpd_event_thread` before DP training, and then only
used by eDP when read edid.

Read edid continued according to its original logic and was unaffected.
	...
	drm_edid = drm_edid_read_ddc(connector, &mtk_dp->aux.ddc);

	/*
	 * Parse capability here to let atomic_get_input_bus_fmts and
	 * mode_valid use the capability to calculate sink bitrates.
	 */
	if (mtk_dp_parse_capabilities(mtk_dp)) {
		drm_err(mtk_dp->drm_dev, "Can't parse capabilities\n");
		drm_edid_free(drm_edid);
		drm_edid = NULL;
	}

	if (drm_edid) {
	...
quoted
 		drm_err(mtk_dp->drm_dev, "Can't parse capabilities\n");
 		drm_edid_free(drm_edid);
 		drm_edid = NULL;
@@ -2385,13 +2386,15 @@ static void
mtk_dp_bridge_atomic_enable(struct drm_bridge *bridge,
 		return;
 	}
 
-	mtk_dp_aux_panel_poweron(mtk_dp, true);
+	if (mtk_dp->data->bridge_type == DRM_MODE_CONNECTOR_eDP) {
+		mtk_dp_aux_panel_poweron(mtk_dp, true);
 
-	/* Training */
-	ret = mtk_dp_training(mtk_dp);
-	if (ret) {
-		drm_err(mtk_dp->drm_dev, "Training failed, %d\n", ret);
-		goto power_off_aux;
+		/* Training */
+		ret = mtk_dp_training(mtk_dp);
+		if (ret) {
+			drm_err(mtk_dp->drm_dev, "Training failed,
%d\n", ret);
+			goto power_off_aux;
+		}
Merge this to previous patch.
quoted
 	}
 
 	ret = mtk_dp_video_config(mtk_dp);
@@ -2411,7 +2414,9 @@ static void
mtk_dp_bridge_atomic_enable(struct drm_bridge *bridge,
 		       sizeof(mtk_dp->info.audio_cur_cfg));
 	}
 
-	mtk_dp->enabled = true;
+	if (mtk_dp->data->bridge_type == DRM_MODE_CONNECTOR_eDP)
+		mtk_dp->enabled = true;
Merge this to previous patch.
quoted
+
 	mtk_dp_update_plugged_status(mtk_dp);
 
 	return;
@@ -2426,21 +2431,15 @@ static void
mtk_dp_bridge_atomic_disable(struct drm_bridge *bridge,
 {
 	struct mtk_dp *mtk_dp = mtk_dp_from_bridge(bridge);
 
-	mtk_dp->enabled = false;
+	if (mtk_dp->data->bridge_type == DRM_MODE_CONNECTOR_eDP) {
+		mtk_dp->enabled = false;
Merge this to previous patch.
quoted
+		mtk_dp_aux_panel_poweron(mtk_dp, false);
You change the code flow of DRM_MODE_CONNECTOR_eDP.
I think you should not change this.
quoted
+	}
+
 	mtk_dp_update_plugged_status(mtk_dp);
 	mtk_dp_video_enable(mtk_dp, false);
 	mtk_dp_audio_mute(mtk_dp, true);
 
-	if (mtk_dp->train_info.cable_plugged_in) {
-		drm_dp_dpcd_writeb(&mtk_dp->aux, DP_SET_POWER,
DP_SET_POWER_D3);
-		usleep_range(2000, 3000);
For DRM_MODE_CONNECTOR_DP, you remove this usleep. This may cause
side effect.
Doesn't it?
The modification to `mtk_dp_bridge_atomic_disable` here is base on
the same logic as `mtk_dp_aux_panel_poweron(mtk_dp, false);`.

Modify part of in `mtk_dp_bridge_atomic_disable`
  if (mtk_dp->train_info.cable_plugged_in) {
    drm_dp_dpcd_writeb(&mtk_dp->aux, DP_SET_POWER, DP_SET_POWER_D3);
    usleep_range(2000, 3000);
  }

  /* power off aux */
  mtk_dp_update_bits(mtk_dp, MTK_DP_TOP_PWR_STATE,
		DP_PWR_STATE_BANDGAP_TPLL,
		DP_PWR_STATE_MASK);

Modify part of in `mtk_dp_aux_panel_poweron(mtk_dp, false);`
  if (pwron) {
    ....
  } else {
    /* power off panel */
    drm_dp_dpcd_writeb(&mtk_dp->aux, DP_SET_POWER, DP_SET_POWER_D3);
    usleep_range(2000, 3000);

    /* power off aux */
    mtk_dp_update_bits(mtk_dp, MTK_DP_TOP_PWR_STATE,
			DP_PWR_STATE_BANDGAP_TPLL,
			DP_PWR_STATE_MASK);
  }

The `mtk_dp_aux_panel_poweron` function fails to align.
Within the `mtk_dp_hpd_event_thread`, if DP is disconnected,
the `mtk_dp_aux_panel_poweron` function will write from `aux`
to `DPRX`, causing a failure and thus preventing symmetry.
quoted
-	}
-
-	/* power off aux */
-	mtk_dp_update_bits(mtk_dp, MTK_DP_TOP_PWR_STATE,
-			   DP_PWR_STATE_BANDGAP_TPLL,
-			   DP_PWR_STATE_MASK);
if (mtk_dp->data->bridge_type == DRM_MODE_CONNECTOR_eDP) {
	/* power off aux */
	mtk_dp_update_bits(mtk_dp, MTK_DP_TOP_PWR_STATE,
			   DP_PWR_STATE_BANDGAP_TPLL,
			   DP_PWR_STATE_MASK);
}

Regards,
CK
quoted
-
 	/* SDP path reset sw*/
 	mtk_dp_sdp_path_reset(mtk_dp);
 
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help