Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

drm/amd/display: Pass the new context into disable OTG WA

[Why]
When enabling an HPO stream for the first time after having previously
enabled a DIO stream there may be lingering DIO FIFO errors even though
the DIO is no longer enabled.

These can cause display clock change to hang if we don't apply the
OTG disable workaround since the ramping logic is tied to OTG on.

[How]
The workaround wasn't being applied in the sequence of:

1 DIO stream
0 streams
1 HPO stream

because current_state has no stream or planes in its context - and
it's only swapped after optimize has finished.

We should be using the incoming context instead to determine whether
this logic is needed or not.

Reviewed-by: Dmytro Laktyushkin <Dmytro.Laktyushkin@amd.com>
Reviewed-by: Dmytro Laktyushkin <Dmytro.Laktyushkin@amd.com>
Acked-by: Jasdeep Dhillon <jdhillon@amd.com>
Tested-by: Daniel Wheeler <daniel.wheeler@amd.com>
Signed-off-by: Nicholas Kazlauskas <nicholas.kazlauskas@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>

authored by

Nicholas Kazlauskas and committed by
Alex Deucher
8440f575 0ec74408

+13 -13
+4 -4
drivers/gpu/drm/amd/display/dc/clk_mgr/dcn31/dcn31_clk_mgr.c
··· 99 99 return display_count; 100 100 } 101 101 102 - static void dcn31_disable_otg_wa(struct clk_mgr *clk_mgr_base, bool disable) 102 + static void dcn31_disable_otg_wa(struct clk_mgr *clk_mgr_base, struct dc_state *context, bool disable) 103 103 { 104 104 struct dc *dc = clk_mgr_base->ctx->dc; 105 105 int i; 106 106 107 107 for (i = 0; i < dc->res_pool->pipe_count; ++i) { 108 - struct pipe_ctx *pipe = &dc->current_state->res_ctx.pipe_ctx[i]; 108 + struct pipe_ctx *pipe = &context->res_ctx.pipe_ctx[i]; 109 109 110 110 if (pipe->top_pipe || pipe->prev_odm_pipe) 111 111 continue; ··· 211 211 } 212 212 213 213 if (should_set_clock(safe_to_lower, new_clocks->dispclk_khz, clk_mgr_base->clks.dispclk_khz)) { 214 - dcn31_disable_otg_wa(clk_mgr_base, true); 214 + dcn31_disable_otg_wa(clk_mgr_base, context, true); 215 215 216 216 clk_mgr_base->clks.dispclk_khz = new_clocks->dispclk_khz; 217 217 dcn31_smu_set_dispclk(clk_mgr, clk_mgr_base->clks.dispclk_khz); 218 - dcn31_disable_otg_wa(clk_mgr_base, false); 218 + dcn31_disable_otg_wa(clk_mgr_base, context, false); 219 219 220 220 update_dispclk = true; 221 221 }
+4 -4
drivers/gpu/drm/amd/display/dc/clk_mgr/dcn315/dcn315_clk_mgr.c
··· 81 81 return display_count; 82 82 } 83 83 84 - static void dcn315_disable_otg_wa(struct clk_mgr *clk_mgr_base, bool disable) 84 + static void dcn315_disable_otg_wa(struct clk_mgr *clk_mgr_base, struct dc_state *context, bool disable) 85 85 { 86 86 struct dc *dc = clk_mgr_base->ctx->dc; 87 87 int i; 88 88 89 89 for (i = 0; i < dc->res_pool->pipe_count; ++i) { 90 - struct pipe_ctx *pipe = &dc->current_state->res_ctx.pipe_ctx[i]; 90 + struct pipe_ctx *pipe = &context->res_ctx.pipe_ctx[i]; 91 91 92 92 if (pipe->top_pipe || pipe->prev_odm_pipe) 93 93 continue; ··· 175 175 } 176 176 177 177 if (should_set_clock(safe_to_lower, new_clocks->dispclk_khz, clk_mgr_base->clks.dispclk_khz)) { 178 - dcn315_disable_otg_wa(clk_mgr_base, true); 178 + dcn315_disable_otg_wa(clk_mgr_base, context, true); 179 179 180 180 clk_mgr_base->clks.dispclk_khz = new_clocks->dispclk_khz; 181 181 dcn315_smu_set_dispclk(clk_mgr, clk_mgr_base->clks.dispclk_khz); 182 - dcn315_disable_otg_wa(clk_mgr_base, false); 182 + dcn315_disable_otg_wa(clk_mgr_base, context, false); 183 183 184 184 update_dispclk = true; 185 185 }
+4 -4
drivers/gpu/drm/amd/display/dc/clk_mgr/dcn316/dcn316_clk_mgr.c
··· 112 112 return display_count; 113 113 } 114 114 115 - static void dcn316_disable_otg_wa(struct clk_mgr *clk_mgr_base, bool disable) 115 + static void dcn316_disable_otg_wa(struct clk_mgr *clk_mgr_base, struct dc_state *context, bool disable) 116 116 { 117 117 struct dc *dc = clk_mgr_base->ctx->dc; 118 118 int i; 119 119 120 120 for (i = 0; i < dc->res_pool->pipe_count; ++i) { 121 - struct pipe_ctx *pipe = &dc->current_state->res_ctx.pipe_ctx[i]; 121 + struct pipe_ctx *pipe = &context->res_ctx.pipe_ctx[i]; 122 122 123 123 if (pipe->top_pipe || pipe->prev_odm_pipe) 124 124 continue; ··· 221 221 } 222 222 223 223 if (should_set_clock(safe_to_lower, new_clocks->dispclk_khz, clk_mgr_base->clks.dispclk_khz)) { 224 - dcn316_disable_otg_wa(clk_mgr_base, true); 224 + dcn316_disable_otg_wa(clk_mgr_base, context, true); 225 225 226 226 clk_mgr_base->clks.dispclk_khz = new_clocks->dispclk_khz; 227 227 dcn316_smu_set_dispclk(clk_mgr, clk_mgr_base->clks.dispclk_khz); 228 - dcn316_disable_otg_wa(clk_mgr_base, false); 228 + dcn316_disable_otg_wa(clk_mgr_base, context, false); 229 229 230 230 update_dispclk = true; 231 231 }
+1 -1
drivers/gpu/drm/amd/display/dc/inc/hw/dccg.h
··· 120 120 121 121 void (*set_dtbclk_dto)( 122 122 struct dccg *dccg, 123 - const struct dtbclk_dto_params *params); 123 + struct dtbclk_dto_params *dto_params); 124 124 125 125 void (*set_audio_dtbclk_dto)( 126 126 struct dccg *dccg,