]> git.baikalelectronics.ru Git - kernel.git/commitdiff
drm/amd/display: workaround for HDMI hotplug in DPMSOFF state
authorYongqiang Sun <yongqiang.sun@amd.com>
Thu, 27 Feb 2020 20:36:00 +0000 (15:36 -0500)
committerAlex Deucher <alexander.deucher@amd.com>
Thu, 19 Mar 2020 04:03:04 +0000 (00:03 -0400)
[Why]
When hotplug a HDMI monitor during entering S0i3 or DPMSOFF state due to
entering infinite loop when calling vbios to program pixel clocks. In
this scenario, pll is enabled but phy is not, and there is not a
programing guide for this case.

[How]
Before we having the proper programing guide, before disable pll, doing
a phy enable and disable to avoid the issue.

Signed-off-by: Yongqiang Sun <yongqiang.sun@amd.com>
Reviewed-by: Tony Cheng <Tony.Cheng@amd.com>
Acked-by: Rodrigo Siqueira <Rodrigo.Siqueira@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c
drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c
drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.h
drivers/gpu/drm/amd/display/dc/dcn21/dcn21_init.c
drivers/gpu/drm/amd/display/dc/inc/hw_sequencer_private.h

index 03f0c9914520e9f328b00e243bf22c6a2367d159..69eb7b3697d267949eb69de69c05820202990641 100644 (file)
@@ -654,6 +654,9 @@ enum dc_status dcn20_enable_stream_timing(
                return DC_ERROR_UNEXPECTED;
        }
 
+       if (dc->hwseq->funcs.PLAT_58856_wa && (!dc_is_dp_signal(stream->signal)))
+               dc->hwseq->funcs.PLAT_58856_wa(context, pipe_ctx);
+
        pipe_ctx->stream_res.tg->funcs->program_timing(
                        pipe_ctx->stream_res.tg,
                        &stream->timing,
index 081ad8e43d581519a0be5ed86aafd67c40eb6ad0..ada65b1a7eb19c5453008685343386285546baec 100644 (file)
@@ -112,3 +112,25 @@ void dcn21_optimize_pwr_state(
                        true);
 }
 
+/* If user hotplug a HDMI monitor while in monitor off,
+ * OS will do a mode set (with output timing) but keep output off.
+ * In this case DAL will ask vbios to power up the pll in the PHY.
+ * If user unplug the monitor (while we are on monitor off) or
+ * system attempt to enter modern standby (which we will disable PLL),
+ * PHY will hang on the next mode set attempt.
+ * if enable PLL follow by disable PLL (without executing lane enable/disable),
+ * RDPCS_PHY_DP_MPLLB_STATE remains 1,
+ * which indicate that PLL disable attempt actually didn\92t go through.
+ * As a workaround, insert PHY lane enable/disable before PLL disable.
+ */
+void dcn21_PLAT_58856_wa(struct dc_state *context, struct pipe_ctx *pipe_ctx)
+{
+       if (!pipe_ctx->stream->dpms_off)
+               return;
+
+       pipe_ctx->stream->dpms_off = false;
+       core_link_enable_stream(context, pipe_ctx);
+       core_link_disable_stream(pipe_ctx);
+       pipe_ctx->stream->dpms_off = true;
+}
+
index 18273609612316308f41c31116b8a95e2e698908..26bf24d3b59f20c1cdc80f04f6005f9be64573d0 100644 (file)
@@ -44,4 +44,7 @@ void dcn21_optimize_pwr_state(
                const struct dc *dc,
                struct dc_state *context);
 
+void dcn21_PLAT_58856_wa(struct dc_state *context,
+               struct pipe_ctx *pipe_ctx);
+
 #endif /* __DC_HWSS_DCN21_H__ */
index 32ed36c3306a77e4697e6eb30b70411b4e85dee5..b9ff9767e08fd4680f5f8fb512b81dc5fb7936d8 100644 (file)
@@ -130,6 +130,7 @@ static const struct hwseq_private_funcs dcn21_private_funcs = {
        .dccg_init = dcn20_dccg_init,
        .set_blend_lut = dcn20_set_blend_lut,
        .set_shaper_3dlut = dcn20_set_shaper_3dlut,
+       .PLAT_58856_wa = dcn21_PLAT_58856_wa,
 };
 
 void dcn21_hw_sequencer_construct(struct dc *dc)
index b1d736cbcd5acc7918f2445574398a57c014b9de..52a26e6be066b4ff978237d0feb76fb1c33e8e12 100644 (file)
@@ -145,6 +145,8 @@ struct hwseq_private_funcs {
                        const struct dc_plane_state *plane_state);
        bool (*set_shaper_3dlut)(struct pipe_ctx *pipe_ctx,
                        const struct dc_plane_state *plane_state);
+       void (*PLAT_58856_wa)(struct dc_state *context,
+                       struct pipe_ctx *pipe_ctx);
 };
 
 struct dce_hwseq {