From 9713158cb2a918c3f6f5522eed23cdeb61f22e75 Mon Sep 17 00:00:00 2001 From: Bhawanpreet Lakha Date: Thu, 5 Nov 2020 13:37:35 -0500 Subject: drm/amdgpu: Add and use seperate reg headers for dcn302 Currently we are using dcn3 reg headers for dcn302. The offsets are different between the two so they need seperate headers. Add dcn302 header files and use these instead of dcn3 header Signed-off-by: Bhawanpreet Lakha Reviewed-by: Alex Deucher Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c index 2345f12ceab3..e2e792d23923 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c @@ -60,8 +60,8 @@ #include "vm_helper.h" #include "dimgrey_cavefish_ip_offset.h" -#include "dcn/dcn_3_0_0_offset.h" -#include "dcn/dcn_3_0_0_sh_mask.h" +#include "dcn/dcn_3_0_2_offset.h" +#include "dcn/dcn_3_0_2_sh_mask.h" #include "dcn/dpcs_3_0_0_offset.h" #include "dcn/dpcs_3_0_0_sh_mask.h" #include "nbio/nbio_7_4_offset.h" -- cgit v1.2.3 From 103cd0b1295c2bad29d5a6bc3ec4efc7d7fcd840 Mon Sep 17 00:00:00 2001 From: Isabel Zhang Date: Wed, 21 Oct 2020 14:01:26 -0400 Subject: drm/amd/display: Add fallback to prefetch mode 1 if 0 fails [Why] In some cases, prefetch mode 0 is unsupported but prefetch 1 is supported. Due to previous change always forcing prefetch mode to 0, we are failing bandwidth validation in cases where we should not. [How] By default try prefetch mode 0 but in the case validation fails, attempt to do prefetch mode 1 to see if it is supported. Signed-off-by: Isabel Zhang Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- .../gpu/drm/amd/display/dc/dcn21/dcn21_resource.c | 28 +++++++++++++++++----- .../amd/display/dc/dml/dcn21/display_mode_vba_21.c | 2 +- 2 files changed, 23 insertions(+), 7 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c index 5ae3419682c8..3d8b0875e905 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c @@ -301,9 +301,7 @@ struct _vcs_dpi_soc_bounding_box_st dcn2_1_soc = { .xfc_bus_transport_time_us = 4, .xfc_xbuf_latency_tolerance_us = 4, .use_urgent_burst_bw = 1, - .num_states = 8, - .allow_dram_self_refresh_or_dram_clock_change_in_vblank - = dm_allow_self_refresh_and_mclk_switch + .num_states = 8 }; #ifndef MAX @@ -1199,11 +1197,29 @@ static bool dcn21_fast_validate_bw( out = true; goto validate_out; } - + /* + * DML favors voltage over p-state, but we're more interested in + * supporting p-state over voltage. We can't support p-state in + * prefetch mode > 0 so try capping the prefetch mode to start. + */ + context->bw_ctx.dml.soc.allow_dram_self_refresh_or_dram_clock_change_in_vblank = + dm_allow_self_refresh_and_mclk_switch; vlevel = dml_get_voltage_level(&context->bw_ctx.dml, pipes, pipe_cnt); - if (vlevel > context->bw_ctx.dml.soc.num_states) - goto validate_fail; + if (vlevel > context->bw_ctx.dml.soc.num_states) { + /* + * If mode is unsupported or there's still no p-state support then + * fall back to favoring voltage. + * + * We don't actually support prefetch mode 2, so require that we + * at least support prefetch mode 1. + */ + context->bw_ctx.dml.soc.allow_dram_self_refresh_or_dram_clock_change_in_vblank = + dm_allow_self_refresh; + vlevel = dml_get_voltage_level(&context->bw_ctx.dml, pipes, pipe_cnt); + if (vlevel > context->bw_ctx.dml.soc.num_states) + goto validate_fail; + } vlevel = dcn20_validate_apply_pipe_split_flags(dc, context, vlevel, split, NULL); diff --git a/drivers/gpu/drm/amd/display/dc/dml/dcn21/display_mode_vba_21.c b/drivers/gpu/drm/amd/display/dc/dml/dcn21/display_mode_vba_21.c index 367c82b5ab4c..86ff24dffc3e 100644 --- a/drivers/gpu/drm/amd/display/dc/dml/dcn21/display_mode_vba_21.c +++ b/drivers/gpu/drm/amd/display/dc/dml/dcn21/display_mode_vba_21.c @@ -5477,7 +5477,7 @@ static void CalculateWatermarksAndDRAMSpeedChangeSupport( } } - if (mode_lib->vba.MinActiveDRAMClockChangeMargin > 0) { + if (mode_lib->vba.MinActiveDRAMClockChangeMargin > 0 && PrefetchMode == 0) { *DRAMClockChangeSupport = dm_dram_clock_change_vactive; } else if (((mode_lib->vba.SynchronizedVBlank == true || mode_lib->vba.TotalNumberOfActiveOTG == 1 -- cgit v1.2.3 From fa896813b441115545349752e15a7d66f3fa2240 Mon Sep 17 00:00:00 2001 From: Isabel Zhang Date: Fri, 23 Oct 2020 11:55:32 -0400 Subject: drm/amd/display: Prevent freesync power optimization during validation [Why] Due to the freesync power optimization increasing vtotal, the driver believes that MPO is supported. MPO is turned on. Freesync then exits, MPO can no longer be supported and immediate flip fails. This causes corruption on the panel. [How] Avoid the freesync optimization when doing validation so in the case freesync exits, driver can still support the configuration. Signed-off-by: Isabel Zhang Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- .../gpu/drm/amd/display/dc/dcn20/dcn20_resource.c | 22 ++++++++++------- .../gpu/drm/amd/display/dc/dcn20/dcn20_resource.h | 8 +++++-- .../gpu/drm/amd/display/dc/dcn21/dcn21_resource.c | 28 ++++++++++++++-------- .../gpu/drm/amd/display/dc/dcn30/dcn30_resource.c | 9 +++---- .../gpu/drm/amd/display/dc/dcn30/dcn30_resource.h | 3 ++- drivers/gpu/drm/amd/display/dc/inc/core_types.h | 3 ++- 6 files changed, 47 insertions(+), 26 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c index 3fcc31d75792..728212cca7aa 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c @@ -2012,7 +2012,10 @@ void dcn20_populate_dml_writeback_from_context( } int dcn20_populate_dml_pipes_from_context( - struct dc *dc, struct dc_state *context, display_e2e_pipe_params_st *pipes) + struct dc *dc, + struct dc_state *context, + display_e2e_pipe_params_st *pipes, + bool fast_validate) { int pipe_cnt, i; bool synchronized_vblank = true; @@ -2050,6 +2053,7 @@ int dcn20_populate_dml_pipes_from_context( v_total = timing->v_total; front_porch = timing->v_front_porch; + /* todo: pipes[pipe_cnt].pipe.src.dynamic_metadata_enable = 0; pipes[pipe_cnt].pipe.src.dcc = 0; @@ -2827,7 +2831,8 @@ bool dcn20_fast_validate_bw( display_e2e_pipe_params_st *pipes, int *pipe_cnt_out, int *pipe_split_from, - int *vlevel_out) + int *vlevel_out, + bool fast_validate) { bool out = false; int split[MAX_PIPES] = { 0 }; @@ -2839,7 +2844,7 @@ bool dcn20_fast_validate_bw( dcn20_merge_pipes_for_validate(dc, context); - pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes); + pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes, fast_validate); *pipe_cnt_out = pipe_cnt; @@ -2943,7 +2948,8 @@ static void dcn20_calculate_wm( display_e2e_pipe_params_st *pipes, int *out_pipe_cnt, int *pipe_split_from, - int vlevel) + int vlevel, + bool fast_validate) { int pipe_cnt, i, pipe_idx; @@ -2988,10 +2994,10 @@ static void dcn20_calculate_wm( if (pipe_cnt != pipe_idx) { if (dc->res_pool->funcs->populate_dml_pipes) pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, - context, pipes); + context, pipes, fast_validate); else pipe_cnt = dcn20_populate_dml_pipes_from_context(dc, - context, pipes); + context, pipes, fast_validate); } *out_pipe_cnt = pipe_cnt; @@ -3136,7 +3142,7 @@ static bool dcn20_validate_bandwidth_internal(struct dc *dc, struct dc_state *co BW_VAL_TRACE_COUNT(); - out = dcn20_fast_validate_bw(dc, context, pipes, &pipe_cnt, pipe_split_from, &vlevel); + out = dcn20_fast_validate_bw(dc, context, pipes, &pipe_cnt, pipe_split_from, &vlevel, fast_validate); if (pipe_cnt == 0) goto validate_out; @@ -3151,7 +3157,7 @@ static bool dcn20_validate_bandwidth_internal(struct dc *dc, struct dc_state *co goto validate_out; } - dcn20_calculate_wm(dc, context, pipes, &pipe_cnt, pipe_split_from, vlevel); + dcn20_calculate_wm(dc, context, pipes, &pipe_cnt, pipe_split_from, vlevel, fast_validate); dcn20_calculate_dlg_params(dc, context, pipes, pipe_cnt, vlevel); BW_VAL_TRACE_END_WATERMARKS(); diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.h b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.h index 64bce14fefa3..c8f3127bbcdf 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.h +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.h @@ -50,7 +50,10 @@ unsigned int dcn20_calc_max_scaled_time( enum mmhubbub_wbif_mode mode, unsigned int urgent_watermark); int dcn20_populate_dml_pipes_from_context( - struct dc *dc, struct dc_state *context, display_e2e_pipe_params_st *pipes); + struct dc *dc, + struct dc_state *context, + display_e2e_pipe_params_st *pipes, + bool fast_validate); struct pipe_ctx *dcn20_acquire_idle_pipe_for_layer( struct dc_state *state, const struct resource_pool *pool, @@ -155,7 +158,8 @@ bool dcn20_fast_validate_bw( display_e2e_pipe_params_st *pipes, int *pipe_cnt_out, int *pipe_split_from, - int *vlevel_out); + int *vlevel_out, + bool fast_validate); void dcn20_calculate_dlg_params( struct dc *dc, struct dc_state *context, display_e2e_pipe_params_st *pipes, diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c index 3d8b0875e905..5eedc19662a3 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c @@ -704,7 +704,10 @@ static const struct dcn10_stream_encoder_mask se_mask = { static void dcn21_pp_smu_destroy(struct pp_smu_funcs **pp_smu); static int dcn21_populate_dml_pipes_from_context( - struct dc *dc, struct dc_state *context, display_e2e_pipe_params_st *pipes); + struct dc *dc, + struct dc_state *context, + display_e2e_pipe_params_st *pipes, + bool fast_validate); static struct input_pixel_processor *dcn21_ipp_create( struct dc_context *ctx, uint32_t inst) @@ -1091,7 +1094,8 @@ void dcn21_calculate_wm( display_e2e_pipe_params_st *pipes, int *out_pipe_cnt, int *pipe_split_from, - int vlevel_req) + int vlevel_req, + bool fast_validate) { int pipe_cnt, i, pipe_idx; int vlevel, vlevel_max; @@ -1133,10 +1137,10 @@ void dcn21_calculate_wm( if (pipe_cnt != pipe_idx) { if (dc->res_pool->funcs->populate_dml_pipes) pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, - context, pipes); + context, pipes, fast_validate); else pipe_cnt = dcn21_populate_dml_pipes_from_context(dc, - context, pipes); + context, pipes, fast_validate); } *out_pipe_cnt = pipe_cnt; @@ -1177,7 +1181,8 @@ static bool dcn21_fast_validate_bw( display_e2e_pipe_params_st *pipes, int *pipe_cnt_out, int *pipe_split_from, - int *vlevel_out) + int *vlevel_out, + bool fast_validate) { bool out = false; int split[MAX_PIPES] = { 0 }; @@ -1189,7 +1194,7 @@ static bool dcn21_fast_validate_bw( dcn20_merge_pipes_for_validate(dc, context); - pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes); + pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes, fast_validate); *pipe_cnt_out = pipe_cnt; @@ -1339,7 +1344,7 @@ bool dcn21_validate_bandwidth(struct dc *dc, struct dc_state *context, /*Unsafe due to current pipe merge and split logic*/ ASSERT(context != dc->current_state); - out = dcn21_fast_validate_bw(dc, context, pipes, &pipe_cnt, pipe_split_from, &vlevel); + out = dcn21_fast_validate_bw(dc, context, pipes, &pipe_cnt, pipe_split_from, &vlevel, fast_validate); if (pipe_cnt == 0) goto validate_out; @@ -1354,7 +1359,7 @@ bool dcn21_validate_bandwidth(struct dc *dc, struct dc_state *context, goto validate_out; } - dcn21_calculate_wm(dc, context, pipes, &pipe_cnt, pipe_split_from, vlevel); + dcn21_calculate_wm(dc, context, pipes, &pipe_cnt, pipe_split_from, vlevel, fast_validate); dcn20_calculate_dlg_params(dc, context, pipes, pipe_cnt, vlevel); BW_VAL_TRACE_END_WATERMARKS(); @@ -1870,9 +1875,12 @@ static uint32_t read_pipe_fuses(struct dc_context *ctx) } static int dcn21_populate_dml_pipes_from_context( - struct dc *dc, struct dc_state *context, display_e2e_pipe_params_st *pipes) + struct dc *dc, + struct dc_state *context, + display_e2e_pipe_params_st *pipes, + bool fast_validate) { - uint32_t pipe_cnt = dcn20_populate_dml_pipes_from_context(dc, context, pipes); + uint32_t pipe_cnt = dcn20_populate_dml_pipes_from_context(dc, context, pipes, fast_validate); int i; for (i = 0; i < pipe_cnt; i++) { diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c index 01ac8b2921c6..c8851853843a 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c @@ -1451,12 +1451,13 @@ static struct clock_source *dcn30_clock_source_create( int dcn30_populate_dml_pipes_from_context( struct dc *dc, struct dc_state *context, - display_e2e_pipe_params_st *pipes) + display_e2e_pipe_params_st *pipes, + bool fast_validate) { int i, pipe_cnt; struct resource_context *res_ctx = &context->res_ctx; - dcn20_populate_dml_pipes_from_context(dc, context, pipes); + dcn20_populate_dml_pipes_from_context(dc, context, pipes, fast_validate); for (i = 0, pipe_cnt = 0; i < dc->res_pool->pipe_count; i++) { if (!res_ctx->pipe_ctx[i].stream) @@ -1996,7 +1997,7 @@ static bool dcn30_internal_validate_bw( if (!pipes) return false; - pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes); + pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes, fast_validate); if (!pipe_cnt) { out = true; @@ -2210,7 +2211,7 @@ static bool dcn30_internal_validate_bw( } if (repopulate_pipes) - pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes); + pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes, fast_validate); *vlevel_out = vlevel; *pipe_cnt_out = pipe_cnt; diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.h b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.h index d163812af858..8ce7f6d39a20 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.h +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.h @@ -65,7 +65,8 @@ void dcn30_populate_dml_writeback_from_context( int dcn30_populate_dml_pipes_from_context( struct dc *dc, struct dc_state *context, - display_e2e_pipe_params_st *pipes); + display_e2e_pipe_params_st *pipes, + bool fast_validate); bool dcn30_acquire_post_bldn_3dlut( struct resource_context *res_ctx, diff --git a/drivers/gpu/drm/amd/display/dc/inc/core_types.h b/drivers/gpu/drm/amd/display/dc/inc/core_types.h index 2ce8c39ca6f5..2d77eac66cb0 100644 --- a/drivers/gpu/drm/amd/display/dc/inc/core_types.h +++ b/drivers/gpu/drm/amd/display/dc/inc/core_types.h @@ -109,7 +109,8 @@ struct resource_funcs { int (*populate_dml_pipes)( struct dc *dc, struct dc_state *context, - display_e2e_pipe_params_st *pipes); + display_e2e_pipe_params_st *pipes, + bool fast_validate); enum dc_status (*validate_global)( struct dc *dc, -- cgit v1.2.3 From 1d496907f1c50c1c5f9617d4b7628a635fdd9cb1 Mon Sep 17 00:00:00 2001 From: Krunoslav Kovac Date: Tue, 20 Oct 2020 16:23:15 -0400 Subject: drm/amd/display: Engage PSR synchronously [Why & How] The intended use is to force PSR into active state and ignore all events until explicit EXIT. A new event force_static is added to power module. It is then sent to FW. Signed-off-by: Krunoslav Kovac Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 4 +- .../drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c | 6 +- drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c | 5 +- drivers/gpu/drm/amd/display/dc/core/dc.c | 4 +- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 18 ++-- drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | 4 +- drivers/gpu/drm/amd/display/dc/dc_link.h | 5 +- drivers/gpu/drm/amd/display/dc/dc_types.h | 19 ++++ drivers/gpu/drm/amd/display/dc/dce/dce_dmcu.c | 24 ++--- drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c | 111 +++++++++++++-------- drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h | 3 +- drivers/gpu/drm/amd/display/dc/inc/hw/dmcu.h | 2 +- 12 files changed, 129 insertions(+), 76 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 2855bb918535..152b1b1f3c07 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -9611,7 +9611,7 @@ bool amdgpu_dm_psr_enable(struct dc_stream_state *stream) &stream, 1, ¶ms); - return dc_link_set_psr_allow_active(link, true, false); + return dc_link_set_psr_allow_active(link, true, false, false); } /* @@ -9625,7 +9625,7 @@ static bool amdgpu_dm_psr_disable(struct dc_stream_state *stream) DRM_DEBUG_DRIVER("Disabling psr...\n"); - return dc_link_set_psr_allow_active(stream->link, false, true); + return dc_link_set_psr_allow_active(stream->link, false, true, false); } /* diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c index d31380ea57dc..11459fb09a37 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c @@ -2333,11 +2333,11 @@ static int psr_get(void *data, u64 *val) { struct amdgpu_dm_connector *connector = data; struct dc_link *link = connector->dc_link; - uint32_t psr_state = 0; + enum dc_psr_state state = PSR_STATE0; - dc_link_get_psr_state(link, &psr_state); + dc_link_get_psr_state(link, &state); - *val = psr_state; + *val = state; return 0; } diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c index 73c91027572b..995ffbbf64e7 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/clk_mgr.c @@ -94,7 +94,7 @@ void clk_mgr_exit_optimized_pwr_state(const struct dc *dc, struct clk_mgr *clk_m if (edp_link) { clk_mgr->psr_allow_active_cache = edp_link->psr_settings.psr_allow_active; - dc_link_set_psr_allow_active(edp_link, false, false); + dc_link_set_psr_allow_active(edp_link, false, false, false); } } @@ -104,7 +104,8 @@ void clk_mgr_optimize_pwr_state(const struct dc *dc, struct clk_mgr *clk_mgr) struct dc_link *edp_link = get_edp_link(dc); if (edp_link) - dc_link_set_psr_allow_active(edp_link, clk_mgr->psr_allow_active_cache, false); + dc_link_set_psr_allow_active(edp_link, + clk_mgr->psr_allow_active_cache, false, false); if (dc->hwss.optimize_pwr_state) dc->hwss.optimize_pwr_state(dc, dc->current_state); diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c index 5951f7d4022f..28b856e2686d 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc.c @@ -3058,9 +3058,9 @@ bool dc_set_psr_allow_active(struct dc *dc, bool enable) if (link->psr_settings.psr_feature_enabled) { if (enable && !link->psr_settings.psr_allow_active) - return dc_link_set_psr_allow_active(link, true, false); + return dc_link_set_psr_allow_active(link, true, false, false); else if (!enable && link->psr_settings.psr_allow_active) - return dc_link_set_psr_allow_active(link, false, true); + return dc_link_set_psr_allow_active(link, false, true, false); } } diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index ea9c459c9130..ee2a51b7a2ee 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -2565,17 +2565,23 @@ bool dc_link_set_backlight_level(const struct dc_link *link, return true; } -bool dc_link_set_psr_allow_active(struct dc_link *link, bool allow_active, bool wait) +bool dc_link_set_psr_allow_active(struct dc_link *link, bool allow_active, + bool wait, bool force_static) { struct dc *dc = link->ctx->dc; struct dmcu *dmcu = dc->res_pool->dmcu; struct dmub_psr *psr = dc->res_pool->psr; + if (psr == NULL && force_static) + return false; + link->psr_settings.psr_allow_active = allow_active; - if (psr != NULL && link->psr_settings.psr_feature_enabled) + if (psr != NULL && link->psr_settings.psr_feature_enabled) { + if (force_static && psr->funcs->psr_force_static) + psr->funcs->psr_force_static(psr); psr->funcs->psr_enable(psr, allow_active, wait); - else if ((dmcu != NULL && dmcu->funcs->is_dmcu_initialized(dmcu)) && link->psr_settings.psr_feature_enabled) + } else if ((dmcu != NULL && dmcu->funcs->is_dmcu_initialized(dmcu)) && link->psr_settings.psr_feature_enabled) dmcu->funcs->set_psr_enable(dmcu, allow_active, wait); else return false; @@ -2583,16 +2589,16 @@ bool dc_link_set_psr_allow_active(struct dc_link *link, bool allow_active, bool return true; } -bool dc_link_get_psr_state(const struct dc_link *link, uint32_t *psr_state) +bool dc_link_get_psr_state(const struct dc_link *link, enum dc_psr_state *state) { struct dc *dc = link->ctx->dc; struct dmcu *dmcu = dc->res_pool->dmcu; struct dmub_psr *psr = dc->res_pool->psr; if (psr != NULL && link->psr_settings.psr_feature_enabled) - psr->funcs->psr_get_state(psr, psr_state); + psr->funcs->psr_get_state(psr, state); else if (dmcu != NULL && link->psr_settings.psr_feature_enabled) - dmcu->funcs->get_psr_state(dmcu, psr_state); + dmcu->funcs->get_psr_state(dmcu, state); return true; } diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c index 8a7c4de49a4b..6c60c1fdebdc 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c @@ -2575,8 +2575,8 @@ static bool handle_hpd_irq_psr_sink(struct dc_link *link) sizeof(psr_error_status.raw)); /* PSR error, disable and re-enable PSR */ - dc_link_set_psr_allow_active(link, false, true); - dc_link_set_psr_allow_active(link, true, true); + dc_link_set_psr_allow_active(link, false, true, false); + dc_link_set_psr_allow_active(link, true, true, false); return true; } else if (psr_sink_psr_status.bits.SINK_SELF_REFRESH_STATUS == diff --git a/drivers/gpu/drm/amd/display/dc/dc_link.h b/drivers/gpu/drm/amd/display/dc/dc_link.h index 266b93a705d5..39277aaa3e62 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_link.h +++ b/drivers/gpu/drm/amd/display/dc/dc_link.h @@ -219,9 +219,10 @@ int dc_link_get_backlight_level(const struct dc_link *dc_link); int dc_link_get_target_backlight_pwm(const struct dc_link *link); -bool dc_link_set_psr_allow_active(struct dc_link *dc_link, bool enable, bool wait); +bool dc_link_set_psr_allow_active(struct dc_link *dc_link, bool enable, + bool wait, bool force_static); -bool dc_link_get_psr_state(const struct dc_link *dc_link, uint32_t *psr_state); +bool dc_link_get_psr_state(const struct dc_link *dc_link, enum dc_psr_state *state); bool dc_link_setup_psr(struct dc_link *dc_link, const struct dc_stream_state *stream, struct psr_config *psr_config, diff --git a/drivers/gpu/drm/amd/display/dc/dc_types.h b/drivers/gpu/drm/amd/display/dc/dc_types.h index 53c29d811493..86406b42572c 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_types.h +++ b/drivers/gpu/drm/amd/display/dc/dc_types.h @@ -671,6 +671,25 @@ struct dc_plane_flip_time { unsigned int prev_update_time_in_us; }; +enum dc_psr_state { + PSR_STATE0 = 0x0, + PSR_STATE1, + PSR_STATE1a, + PSR_STATE2, + PSR_STATE2a, + PSR_STATE3, + PSR_STATE3Init, + PSR_STATE4, + PSR_STATE4a, + PSR_STATE4b, + PSR_STATE4c, + PSR_STATE4d, + PSR_STATE5, + PSR_STATE5a, + PSR_STATE5b, + PSR_STATE5c +}; + struct psr_config { unsigned char psr_version; unsigned int psr_rfb_setup_time; diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_dmcu.c b/drivers/gpu/drm/amd/display/dc/dce/dce_dmcu.c index f0cebe721bcc..f3ed8b619caf 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_dmcu.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_dmcu.c @@ -99,7 +99,7 @@ bool dce_dmcu_load_iram(struct dmcu *dmcu, return true; } -static void dce_get_dmcu_psr_state(struct dmcu *dmcu, uint32_t *psr_state) +static void dce_get_dmcu_psr_state(struct dmcu *dmcu, enum dc_psr_state *state) { struct dce_dmcu *dmcu_dce = TO_DCE_DMCU(dmcu); @@ -114,7 +114,7 @@ static void dce_get_dmcu_psr_state(struct dmcu *dmcu, uint32_t *psr_state) REG_WRITE(DMCU_IRAM_RD_CTRL, psr_state_offset); /* Read data from IRAM_RD_DATA in DMCU_IRAM_RD_DATA*/ - *psr_state = REG_READ(DMCU_IRAM_RD_DATA); + *state = (enum dc_psr_state)REG_READ(DMCU_IRAM_RD_DATA); /* Disable write access to IRAM after finished using IRAM * in order to allow dynamic sleep state @@ -129,7 +129,7 @@ static void dce_dmcu_set_psr_enable(struct dmcu *dmcu, bool enable, bool wait) unsigned int dmcu_wait_reg_ready_interval = 100; unsigned int retryCount; - uint32_t psr_state = 0; + enum dc_psr_state state = PSR_STATE0; /* waitDMCUReadyForCmd */ REG_WAIT(MASTER_COMM_CNTL_REG, MASTER_COMM_INTERRUPT, 0, @@ -148,12 +148,12 @@ static void dce_dmcu_set_psr_enable(struct dmcu *dmcu, bool enable, bool wait) REG_UPDATE(MASTER_COMM_CNTL_REG, MASTER_COMM_INTERRUPT, 1); if (wait == true) { for (retryCount = 0; retryCount <= 100; retryCount++) { - dce_get_dmcu_psr_state(dmcu, &psr_state); + dce_get_dmcu_psr_state(dmcu, &state); if (enable) { - if (psr_state != 0) + if (state != PSR_STATE0) break; } else { - if (psr_state == 0) + if (state == PSR_STATE0) break; } udelay(10); @@ -513,7 +513,7 @@ static bool dcn10_dmcu_load_iram(struct dmcu *dmcu, return true; } -static void dcn10_get_dmcu_psr_state(struct dmcu *dmcu, uint32_t *psr_state) +static void dcn10_get_dmcu_psr_state(struct dmcu *dmcu, enum dc_psr_state *state) { struct dce_dmcu *dmcu_dce = TO_DCE_DMCU(dmcu); @@ -532,7 +532,7 @@ static void dcn10_get_dmcu_psr_state(struct dmcu *dmcu, uint32_t *psr_state) REG_WRITE(DMCU_IRAM_RD_CTRL, psr_state_offset); /* Read data from IRAM_RD_DATA in DMCU_IRAM_RD_DATA*/ - *psr_state = REG_READ(DMCU_IRAM_RD_DATA); + *state = (enum dc_psr_state)REG_READ(DMCU_IRAM_RD_DATA); /* Disable write access to IRAM after finished using IRAM * in order to allow dynamic sleep state @@ -547,7 +547,7 @@ static void dcn10_dmcu_set_psr_enable(struct dmcu *dmcu, bool enable, bool wait) unsigned int dmcu_wait_reg_ready_interval = 100; unsigned int retryCount; - uint32_t psr_state = 0; + enum dc_psr_state state = PSR_STATE0; /* If microcontroller is not running, do nothing */ if (dmcu->dmcu_state != DMCU_RUNNING) @@ -575,12 +575,12 @@ static void dcn10_dmcu_set_psr_enable(struct dmcu *dmcu, bool enable, bool wait) */ if (wait == true) { for (retryCount = 0; retryCount <= 1000; retryCount++) { - dcn10_get_dmcu_psr_state(dmcu, &psr_state); + dcn10_get_dmcu_psr_state(dmcu, &state); if (enable) { - if (psr_state != 0) + if (state != PSR_STATE0) break; } else { - if (psr_state == 0) + if (state == PSR_STATE0) break; } udelay(500); diff --git a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c index 67af67ef2865..df3879c713c5 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c @@ -34,55 +34,60 @@ /** * Convert dmcub psr state to dmcu psr state. */ -static void convert_psr_state(uint32_t *psr_state) +static enum dc_psr_state convert_psr_state(uint32_t raw_state) { - if (*psr_state == 0) - *psr_state = 0; - else if (*psr_state == 0x10) - *psr_state = 1; - else if (*psr_state == 0x11) - *psr_state = 2; - else if (*psr_state == 0x20) - *psr_state = 3; - else if (*psr_state == 0x21) - *psr_state = 4; - else if (*psr_state == 0x30) - *psr_state = 5; - else if (*psr_state == 0x31) - *psr_state = 6; - else if (*psr_state == 0x40) - *psr_state = 7; - else if (*psr_state == 0x41) - *psr_state = 8; - else if (*psr_state == 0x42) - *psr_state = 9; - else if (*psr_state == 0x43) - *psr_state = 10; - else if (*psr_state == 0x44) - *psr_state = 11; - else if (*psr_state == 0x50) - *psr_state = 12; - else if (*psr_state == 0x51) - *psr_state = 13; - else if (*psr_state == 0x52) - *psr_state = 14; - else if (*psr_state == 0x53) - *psr_state = 15; + enum dc_psr_state state = PSR_STATE0; + + if (raw_state == 0) + state = PSR_STATE0; + else if (raw_state == 0x10) + state = PSR_STATE1; + else if (raw_state == 0x11) + state = PSR_STATE1a; + else if (raw_state == 0x20) + state = PSR_STATE2; + else if (raw_state == 0x21) + state = PSR_STATE2a; + else if (raw_state == 0x30) + state = PSR_STATE3; + else if (raw_state == 0x31) + state = PSR_STATE3Init; + else if (raw_state == 0x40) + state = PSR_STATE4; + else if (raw_state == 0x41) + state = PSR_STATE4a; + else if (raw_state == 0x42) + state = PSR_STATE4b; + else if (raw_state == 0x43) + state = PSR_STATE4c; + else if (raw_state == 0x44) + state = PSR_STATE4d; + else if (raw_state == 0x50) + state = PSR_STATE5; + else if (raw_state == 0x51) + state = PSR_STATE5a; + else if (raw_state == 0x52) + state = PSR_STATE5b; + else if (raw_state == 0x53) + state = PSR_STATE5c; + + return state; } /** * Get PSR state from firmware. */ -static void dmub_psr_get_state(struct dmub_psr *dmub, uint32_t *psr_state) +static void dmub_psr_get_state(struct dmub_psr *dmub, enum dc_psr_state *state) { struct dmub_srv *srv = dmub->ctx->dmub_srv->dmub; + uint32_t raw_state; // Send gpint command and wait for ack dmub_srv_send_gpint_command(srv, DMUB_GPINT__GET_PSR_STATE, 0, 30); - dmub_srv_get_gpint_response(srv, psr_state); + dmub_srv_get_gpint_response(srv, &raw_state); - convert_psr_state(psr_state); + *state = convert_psr_state(raw_state); } /** @@ -123,7 +128,9 @@ static void dmub_psr_enable(struct dmub_psr *dmub, bool enable, bool wait) { union dmub_rb_cmd cmd; struct dc_context *dc = dmub->ctx; - uint32_t retry_count, psr_state = 0; + uint32_t retry_count; + enum dc_psr_state state = PSR_STATE0; + cmd.psr_enable.header.type = DMUB_CMD__PSR; @@ -144,13 +151,13 @@ static void dmub_psr_enable(struct dmub_psr *dmub, bool enable, bool wait) */ if (wait) { for (retry_count = 0; retry_count <= 1000; retry_count++) { - dmub_psr_get_state(dmub, &psr_state); + dmub_psr_get_state(dmub, &state); if (enable) { - if (psr_state != 0) + if (state != PSR_STATE0) break; } else { - if (psr_state == 0) + if (state == PSR_STATE0) break; } @@ -169,12 +176,12 @@ static void dmub_psr_enable(struct dmub_psr *dmub, bool enable, bool wait) static void dmub_psr_set_level(struct dmub_psr *dmub, uint16_t psr_level) { union dmub_rb_cmd cmd; - uint32_t psr_state = 0; + enum dc_psr_state state = PSR_STATE0; struct dc_context *dc = dmub->ctx; - dmub_psr_get_state(dmub, &psr_state); + dmub_psr_get_state(dmub, &state); - if (psr_state == 0) + if (state == PSR_STATE0) return; cmd.psr_set_level.header.type = DMUB_CMD__PSR; @@ -269,11 +276,29 @@ static bool dmub_psr_copy_settings(struct dmub_psr *dmub, return true; } +/** + * Send command to PSR to force static ENTER and ignore all state changes until exit + */ +static void dmub_psr_force_static(struct dmub_psr *dmub) +{ + union dmub_rb_cmd cmd; + struct dc_context *dc = dmub->ctx; + + cmd.psr_force_static.header.type = DMUB_CMD__PSR; + cmd.psr_force_static.header.sub_type = DMUB_CMD__PSR_FORCE_STATIC; + cmd.psr_enable.header.payload_bytes = 0; + + dc_dmub_srv_cmd_queue(dc->dmub_srv, &cmd); + dc_dmub_srv_cmd_execute(dc->dmub_srv); + dc_dmub_srv_wait_idle(dc->dmub_srv); +} + static const struct dmub_psr_funcs psr_funcs = { .psr_copy_settings = dmub_psr_copy_settings, .psr_enable = dmub_psr_enable, .psr_get_state = dmub_psr_get_state, .psr_set_level = dmub_psr_set_level, + .psr_force_static = dmub_psr_force_static, }; /** diff --git a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h index dc121ed92d2e..4e113ac5a56b 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h +++ b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h @@ -37,8 +37,9 @@ struct dmub_psr { struct dmub_psr_funcs { bool (*psr_copy_settings)(struct dmub_psr *dmub, struct dc_link *link, struct psr_context *psr_context); void (*psr_enable)(struct dmub_psr *dmub, bool enable, bool wait); - void (*psr_get_state)(struct dmub_psr *dmub, uint32_t *psr_state); + void (*psr_get_state)(struct dmub_psr *dmub, enum dc_psr_state *dc_psr_state); void (*psr_set_level)(struct dmub_psr *dmub, uint16_t psr_level); + void (*psr_force_static)(struct dmub_psr *dmub); }; struct dmub_psr *dmub_psr_create(struct dc_context *ctx); diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/dmcu.h b/drivers/gpu/drm/amd/display/dc/inc/hw/dmcu.h index 5315f1f86b21..69d9fbfb4bec 100644 --- a/drivers/gpu/drm/amd/display/dc/inc/hw/dmcu.h +++ b/drivers/gpu/drm/amd/display/dc/inc/hw/dmcu.h @@ -66,7 +66,7 @@ struct dmcu_funcs { bool (*setup_psr)(struct dmcu *dmcu, struct dc_link *link, struct psr_context *psr_context); - void (*get_psr_state)(struct dmcu *dmcu, uint32_t *psr_state); + void (*get_psr_state)(struct dmcu *dmcu, enum dc_psr_state *dc_psr_state); void (*set_psr_wait_loop)(struct dmcu *dmcu, unsigned int wait_loop_number); void (*get_psr_wait_loop)(struct dmcu *dmcu, -- cgit v1.2.3 From 74d7f445e8a1b4d81d6c511ace743482cc00cbe1 Mon Sep 17 00:00:00 2001 From: Dmytro Laktyushkin Date: Wed, 28 Oct 2020 10:05:36 -0400 Subject: drm/amd/display: correct dml dsc bpc assignment Signed-off-by: Dmytro Laktyushkin Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c b/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c index 62740d4e423d..3ae72e379402 100644 --- a/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c +++ b/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c @@ -469,8 +469,7 @@ static void fetch_pipe_params(struct display_mode_lib *mode_lib) mode_lib->vba.DSCEnable[mode_lib->vba.NumberOfActivePlanes] = dout->dsc_enable; mode_lib->vba.NumberOfDSCSlices[mode_lib->vba.NumberOfActivePlanes] = dout->dsc_slices; - mode_lib->vba.DSCInputBitPerComponent[mode_lib->vba.NumberOfActivePlanes] = - dout->output_bpc == 0 ? 12 : dout->output_bpc; + mode_lib->vba.DSCInputBitPerComponent[mode_lib->vba.NumberOfActivePlanes] = dout->output_bpc; mode_lib->vba.WritebackEnable[mode_lib->vba.NumberOfActivePlanes] = dout->wb_enable; mode_lib->vba.ActiveWritebacksPerPlane[mode_lib->vba.NumberOfActivePlanes] = dout->num_active_wb; -- cgit v1.2.3 From 06d55ffaeaea9badfee7376100759f1f86397e94 Mon Sep 17 00:00:00 2001 From: Eric Bernstein Date: Mon, 26 Oct 2020 13:33:28 -0400 Subject: drm/amd/display: Move common speakersToChannels definition to hw_shared.h Signed-off-by: Eric Bernstein Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/dce/dce_stream_encoder.c | 82 --------------------- .../amd/display/dc/dcn10/dcn10_stream_encoder.c | 82 --------------------- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.c | 1 + drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.h | 83 --------------------- drivers/gpu/drm/amd/display/dc/inc/hw/hw_shared.h | 84 ++++++++++++++++++++++ 5 files changed, 85 insertions(+), 247 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_stream_encoder.c b/drivers/gpu/drm/amd/display/dc/dce/dce_stream_encoder.c index 5054bb567b74..ada57f745fd7 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_stream_encoder.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_stream_encoder.c @@ -1062,88 +1062,6 @@ static void dce110_reset_hdmi_stream_attribute( #include "include/audio_types.h" -/** -* speakersToChannels -* -* @brief -* translate speakers to channels -* -* FL - Front Left -* FR - Front Right -* RL - Rear Left -* RR - Rear Right -* RC - Rear Center -* FC - Front Center -* FLC - Front Left Center -* FRC - Front Right Center -* RLC - Rear Left Center -* RRC - Rear Right Center -* LFE - Low Freq Effect -* -* FC -* FLC FRC -* FL FR -* -* LFE -* () -* -* -* RL RR -* RLC RRC -* RC -* -* ch 8 7 6 5 4 3 2 1 -* 0b00000011 - - - - - - FR FL -* 0b00000111 - - - - - LFE FR FL -* 0b00001011 - - - - FC - FR FL -* 0b00001111 - - - - FC LFE FR FL -* 0b00010011 - - - RC - - FR FL -* 0b00010111 - - - RC - LFE FR FL -* 0b00011011 - - - RC FC - FR FL -* 0b00011111 - - - RC FC LFE FR FL -* 0b00110011 - - RR RL - - FR FL -* 0b00110111 - - RR RL - LFE FR FL -* 0b00111011 - - RR RL FC - FR FL -* 0b00111111 - - RR RL FC LFE FR FL -* 0b01110011 - RC RR RL - - FR FL -* 0b01110111 - RC RR RL - LFE FR FL -* 0b01111011 - RC RR RL FC - FR FL -* 0b01111111 - RC RR RL FC LFE FR FL -* 0b11110011 RRC RLC RR RL - - FR FL -* 0b11110111 RRC RLC RR RL - LFE FR FL -* 0b11111011 RRC RLC RR RL FC - FR FL -* 0b11111111 RRC RLC RR RL FC LFE FR FL -* 0b11000011 FRC FLC - - - - FR FL -* 0b11000111 FRC FLC - - - LFE FR FL -* 0b11001011 FRC FLC - - FC - FR FL -* 0b11001111 FRC FLC - - FC LFE FR FL -* 0b11010011 FRC FLC - RC - - FR FL -* 0b11010111 FRC FLC - RC - LFE FR FL -* 0b11011011 FRC FLC - RC FC - FR FL -* 0b11011111 FRC FLC - RC FC LFE FR FL -* 0b11110011 FRC FLC RR RL - - FR FL -* 0b11110111 FRC FLC RR RL - LFE FR FL -* 0b11111011 FRC FLC RR RL FC - FR FL -* 0b11111111 FRC FLC RR RL FC LFE FR FL -* -* @param -* speakers - speaker information as it comes from CEA audio block -*/ -/* translate speakers to channels */ - -union audio_cea_channels { - uint8_t all; - struct audio_cea_channels_bits { - uint32_t FL:1; - uint32_t FR:1; - uint32_t LFE:1; - uint32_t FC:1; - uint32_t RL_RC:1; - uint32_t RR:1; - uint32_t RC_RLC_FLC:1; - uint32_t RRC_FRC:1; - } channels; -}; /* 25.2MHz/1.001*/ /* 25.2MHz/1.001*/ diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.c index f70fcadf1ee5..73ac78b16bd4 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.c @@ -1021,88 +1021,6 @@ void enc1_reset_hdmi_stream_attribute( #include "include/audio_types.h" -/** -* speakersToChannels -* -* @brief -* translate speakers to channels -* -* FL - Front Left -* FR - Front Right -* RL - Rear Left -* RR - Rear Right -* RC - Rear Center -* FC - Front Center -* FLC - Front Left Center -* FRC - Front Right Center -* RLC - Rear Left Center -* RRC - Rear Right Center -* LFE - Low Freq Effect -* -* FC -* FLC FRC -* FL FR -* -* LFE -* () -* -* -* RL RR -* RLC RRC -* RC -* -* ch 8 7 6 5 4 3 2 1 -* 0b00000011 - - - - - - FR FL -* 0b00000111 - - - - - LFE FR FL -* 0b00001011 - - - - FC - FR FL -* 0b00001111 - - - - FC LFE FR FL -* 0b00010011 - - - RC - - FR FL -* 0b00010111 - - - RC - LFE FR FL -* 0b00011011 - - - RC FC - FR FL -* 0b00011111 - - - RC FC LFE FR FL -* 0b00110011 - - RR RL - - FR FL -* 0b00110111 - - RR RL - LFE FR FL -* 0b00111011 - - RR RL FC - FR FL -* 0b00111111 - - RR RL FC LFE FR FL -* 0b01110011 - RC RR RL - - FR FL -* 0b01110111 - RC RR RL - LFE FR FL -* 0b01111011 - RC RR RL FC - FR FL -* 0b01111111 - RC RR RL FC LFE FR FL -* 0b11110011 RRC RLC RR RL - - FR FL -* 0b11110111 RRC RLC RR RL - LFE FR FL -* 0b11111011 RRC RLC RR RL FC - FR FL -* 0b11111111 RRC RLC RR RL FC LFE FR FL -* 0b11000011 FRC FLC - - - - FR FL -* 0b11000111 FRC FLC - - - LFE FR FL -* 0b11001011 FRC FLC - - FC - FR FL -* 0b11001111 FRC FLC - - FC LFE FR FL -* 0b11010011 FRC FLC - RC - - FR FL -* 0b11010111 FRC FLC - RC - LFE FR FL -* 0b11011011 FRC FLC - RC FC - FR FL -* 0b11011111 FRC FLC - RC FC LFE FR FL -* 0b11110011 FRC FLC RR RL - - FR FL -* 0b11110111 FRC FLC RR RL - LFE FR FL -* 0b11111011 FRC FLC RR RL FC - FR FL -* 0b11111111 FRC FLC RR RL FC LFE FR FL -* -* @param -* speakers - speaker information as it comes from CEA audio block -*/ -/* translate speakers to channels */ - -union audio_cea_channels { - uint8_t all; - struct audio_cea_channels_bits { - uint32_t FL:1; - uint32_t FR:1; - uint32_t LFE:1; - uint32_t FC:1; - uint32_t RL_RC:1; - uint32_t RR:1; - uint32_t RC_RLC_FLC:1; - uint32_t RRC_FRC:1; - } channels; -}; /* 25.2MHz/1.001*/ /* 25.2MHz/1.001*/ diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.c index 2b08b1d72177..fa981cd04dd0 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.c @@ -25,6 +25,7 @@ #include "dc_bios_types.h" +#include "hw_shared.h" #include "dcn30_afmt.h" #include "reg_helper.h" diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.h b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.h index 08b2d8a8170c..85d4619207e2 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.h +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_afmt.h @@ -100,89 +100,6 @@ struct dcn30_afmt_mask { }; -/** -* speakersToChannels -* -* @brief -* translate speakers to channels -* -* FL - Front Left -* FR - Front Right -* RL - Rear Left -* RR - Rear Right -* RC - Rear Center -* FC - Front Center -* FLC - Front Left Center -* FRC - Front Right Center -* RLC - Rear Left Center -* RRC - Rear Right Center -* LFE - Low Freq Effect -* -* FC -* FLC FRC -* FL FR -* -* LFE -* () -* -* -* RL RR -* RLC RRC -* RC -* -* ch 8 7 6 5 4 3 2 1 -* 0b00000011 - - - - - - FR FL -* 0b00000111 - - - - - LFE FR FL -* 0b00001011 - - - - FC - FR FL -* 0b00001111 - - - - FC LFE FR FL -* 0b00010011 - - - RC - - FR FL -* 0b00010111 - - - RC - LFE FR FL -* 0b00011011 - - - RC FC - FR FL -* 0b00011111 - - - RC FC LFE FR FL -* 0b00110011 - - RR RL - - FR FL -* 0b00110111 - - RR RL - LFE FR FL -* 0b00111011 - - RR RL FC - FR FL -* 0b00111111 - - RR RL FC LFE FR FL -* 0b01110011 - RC RR RL - - FR FL -* 0b01110111 - RC RR RL - LFE FR FL -* 0b01111011 - RC RR RL FC - FR FL -* 0b01111111 - RC RR RL FC LFE FR FL -* 0b11110011 RRC RLC RR RL - - FR FL -* 0b11110111 RRC RLC RR RL - LFE FR FL -* 0b11111011 RRC RLC RR RL FC - FR FL -* 0b11111111 RRC RLC RR RL FC LFE FR FL -* 0b11000011 FRC FLC - - - - FR FL -* 0b11000111 FRC FLC - - - LFE FR FL -* 0b11001011 FRC FLC - - FC - FR FL -* 0b11001111 FRC FLC - - FC LFE FR FL -* 0b11010011 FRC FLC - RC - - FR FL -* 0b11010111 FRC FLC - RC - LFE FR FL -* 0b11011011 FRC FLC - RC FC - FR FL -* 0b11011111 FRC FLC - RC FC LFE FR FL -* 0b11110011 FRC FLC RR RL - - FR FL -* 0b11110111 FRC FLC RR RL - LFE FR FL -* 0b11111011 FRC FLC RR RL FC - FR FL -* 0b11111111 FRC FLC RR RL FC LFE FR FL -* -* @param -* speakers - speaker information as it comes from CEA audio block -*/ -/* translate speakers to channels */ - -union audio_cea_channels { - uint8_t all; - struct audio_cea_channels_bits { - uint32_t FL:1; - uint32_t FR:1; - uint32_t LFE:1; - uint32_t FC:1; - uint32_t RL_RC:1; - uint32_t RR:1; - uint32_t RC_RLC_FLC:1; - uint32_t RRC_FRC:1; - } channels; -}; - struct afmt; struct afmt_funcs { diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/hw_shared.h b/drivers/gpu/drm/amd/display/dc/inc/hw/hw_shared.h index a3a27c16aa2f..43e33f47734d 100644 --- a/drivers/gpu/drm/amd/display/dc/inc/hw/hw_shared.h +++ b/drivers/gpu/drm/amd/display/dc/inc/hw/hw_shared.h @@ -264,4 +264,88 @@ enum dc_lut_mode { LUT_RAM_A, LUT_RAM_B }; + +/** + * speakersToChannels + * + * @brief + * translate speakers to channels + * + * FL - Front Left + * FR - Front Right + * RL - Rear Left + * RR - Rear Right + * RC - Rear Center + * FC - Front Center + * FLC - Front Left Center + * FRC - Front Right Center + * RLC - Rear Left Center + * RRC - Rear Right Center + * LFE - Low Freq Effect + * + * FC + * FLC FRC + * FL FR + * + * LFE + * () + * + * + * RL RR + * RLC RRC + * RC + * + * ch 8 7 6 5 4 3 2 1 + * 0b00000011 - - - - - - FR FL + * 0b00000111 - - - - - LFE FR FL + * 0b00001011 - - - - FC - FR FL + * 0b00001111 - - - - FC LFE FR FL + * 0b00010011 - - - RC - - FR FL + * 0b00010111 - - - RC - LFE FR FL + * 0b00011011 - - - RC FC - FR FL + * 0b00011111 - - - RC FC LFE FR FL + * 0b00110011 - - RR RL - - FR FL + * 0b00110111 - - RR RL - LFE FR FL + * 0b00111011 - - RR RL FC - FR FL + * 0b00111111 - - RR RL FC LFE FR FL + * 0b01110011 - RC RR RL - - FR FL + * 0b01110111 - RC RR RL - LFE FR FL + * 0b01111011 - RC RR RL FC - FR FL + * 0b01111111 - RC RR RL FC LFE FR FL + * 0b11110011 RRC RLC RR RL - - FR FL + * 0b11110111 RRC RLC RR RL - LFE FR FL + * 0b11111011 RRC RLC RR RL FC - FR FL + * 0b11111111 RRC RLC RR RL FC LFE FR FL + * 0b11000011 FRC FLC - - - - FR FL + * 0b11000111 FRC FLC - - - LFE FR FL + * 0b11001011 FRC FLC - - FC - FR FL + * 0b11001111 FRC FLC - - FC LFE FR FL + * 0b11010011 FRC FLC - RC - - FR FL + * 0b11010111 FRC FLC - RC - LFE FR FL + * 0b11011011 FRC FLC - RC FC - FR FL + * 0b11011111 FRC FLC - RC FC LFE FR FL + * 0b11110011 FRC FLC RR RL - - FR FL + * 0b11110111 FRC FLC RR RL - LFE FR FL + * 0b11111011 FRC FLC RR RL FC - FR FL + * 0b11111111 FRC FLC RR RL FC LFE FR FL + * + * @param + * speakers - speaker information as it comes from CEA audio block + */ +/* translate speakers to channels */ + +union audio_cea_channels { + uint8_t all; + struct audio_cea_channels_bits { + uint32_t FL:1; + uint32_t FR:1; + uint32_t LFE:1; + uint32_t FC:1; + uint32_t RL_RC:1; + uint32_t RR:1; + uint32_t RC_RLC_FLC:1; + uint32_t RRC_FRC:1; + } channels; +}; + #endif /* __DAL_HW_SHARED_H__ */ -- cgit v1.2.3 From e9917ef822bdfa9b881c87934f160a3e48125f00 Mon Sep 17 00:00:00 2001 From: Aric Cyr Date: Thu, 29 Oct 2020 17:40:51 -0400 Subject: drm/amd/display: Only wait for flip pending on immediate flips [Why] We want to make sure all immediate flips are completed before locking the pipes, but not pipes that are not flip immediate as they will be locked by the OTG [How] Skip non flip immediate pipes when checking for flip pending. Signed-off-by: Aric Cyr Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c | 29 +++++++++++----------- 1 file changed, 15 insertions(+), 14 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c index d8d45d860cb7..e65ec2a20fa2 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c @@ -1165,27 +1165,28 @@ void dcn20_pipe_control_lock( temp_pipe = pipe->bottom_pipe; while (!flip_immediate && temp_pipe) { - if (temp_pipe->plane_state != NULL) - flip_immediate = temp_pipe->plane_state->flip_immediate; - temp_pipe = temp_pipe->bottom_pipe; + if (temp_pipe->plane_state != NULL) + flip_immediate = temp_pipe->plane_state->flip_immediate; + temp_pipe = temp_pipe->bottom_pipe; } if (flip_immediate && lock) { const int TIMEOUT_FOR_FLIP_PENDING = 100000; int i; - for (i = 0; i < TIMEOUT_FOR_FLIP_PENDING; ++i) { - if (!pipe->plane_res.hubp->funcs->hubp_is_flip_pending(pipe->plane_res.hubp)) - break; - udelay(1); - } - - if (pipe->bottom_pipe != NULL) { - for (i = 0; i < TIMEOUT_FOR_FLIP_PENDING; ++i) { - if (!pipe->bottom_pipe->plane_res.hubp->funcs->hubp_is_flip_pending(pipe->bottom_pipe->plane_res.hubp)) - break; - udelay(1); + temp_pipe = pipe; + while (temp_pipe) { + if (temp_pipe->plane_state && temp_pipe->plane_state->flip_immediate) { + for (i = 0; i < TIMEOUT_FOR_FLIP_PENDING; ++i) { + if (!temp_pipe->plane_res.hubp->funcs->hubp_is_flip_pending(temp_pipe->plane_res.hubp)) + break; + udelay(1); + } + + /* no reason it should take this long for immediate flips */ + ASSERT(i != TIMEOUT_FOR_FLIP_PENDING); } + temp_pipe = temp_pipe->bottom_pipe; } } -- cgit v1.2.3 From c6160900239e20d32ee9025fca7d926f8744f448 Mon Sep 17 00:00:00 2001 From: Jing Zhou Date: Wed, 28 Oct 2020 15:50:53 +0800 Subject: drm/amd/display: force use sRGB for video TF is sRGB or BT709 [Why] When mpo enabled, video comes is 709. Desktop use sRGB. So color change easily noticeable especially when switch between mpo/non-mpo. [How] Force use sRGB for video TF is sRGB or BT709. DCN1/DCN2 use predefined type with YUV. DCN3 use distributed points type with YUV. Signed-off-by: Jing Zhou Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 1 + drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c | 1 + drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c | 1 + drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c | 1 + drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c | 1 + drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c | 1 + drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c | 1 + 7 files changed, 7 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 65aabf25cdec..27bcbe5fa7b0 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -125,6 +125,7 @@ struct dpp_color_caps { uint16_t hw_3d_lut : 1; uint16_t ogam_ram : 1; // blnd gam uint16_t ocsc : 1; + uint16_t dgam_rom_for_yuv : 1; struct rom_curve_caps dgam_rom_caps; struct rom_curve_caps ogam_rom_caps; }; diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c index e74bb2735885..bdc37831535e 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_resource.c @@ -1439,6 +1439,7 @@ static bool dcn10_resource_construct( dc->caps.color.dpp.dgam_rom_caps.hlg = 0; dc->caps.color.dpp.post_csc = 0; dc->caps.color.dpp.gamma_corr = 0; + dc->caps.color.dpp.dgam_rom_for_yuv = 1; dc->caps.color.dpp.hw_3d_lut = 0; dc->caps.color.dpp.ogam_ram = 1; // RGAM on DCN1 diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c index 728212cca7aa..ff36db5edf6c 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c @@ -3820,6 +3820,7 @@ static bool dcn20_resource_construct( dc->caps.color.dpp.dgam_rom_caps.hlg = 0; dc->caps.color.dpp.post_csc = 0; dc->caps.color.dpp.gamma_corr = 0; + dc->caps.color.dpp.dgam_rom_for_yuv = 1; dc->caps.color.dpp.hw_3d_lut = 1; dc->caps.color.dpp.ogam_ram = 1; diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c index 5eedc19662a3..abc8af0ef141 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c @@ -1978,6 +1978,7 @@ static bool dcn21_resource_construct( dc->caps.color.dpp.dgam_rom_caps.hlg = 0; dc->caps.color.dpp.post_csc = 0; dc->caps.color.dpp.gamma_corr = 0; + dc->caps.color.dpp.dgam_rom_for_yuv = 1; dc->caps.color.dpp.hw_3d_lut = 1; dc->caps.color.dpp.ogam_ram = 1; diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c index c8851853843a..b379057e669c 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c @@ -2681,6 +2681,7 @@ static bool dcn30_resource_construct( dc->caps.color.dpp.dgam_rom_caps.hlg = 1; dc->caps.color.dpp.post_csc = 1; dc->caps.color.dpp.gamma_corr = 1; + dc->caps.color.dpp.dgam_rom_for_yuv = 0; dc->caps.color.dpp.hw_3d_lut = 1; dc->caps.color.dpp.ogam_ram = 1; diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index 5a47b4106b7b..8824dbce6f4a 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -1748,6 +1748,7 @@ static bool dcn301_resource_construct( dc->caps.color.dpp.dgam_rom_caps.hlg = 1; dc->caps.color.dpp.post_csc = 1; dc->caps.color.dpp.gamma_corr = 1; + dc->caps.color.dpp.dgam_rom_for_yuv = 0; dc->caps.color.dpp.hw_3d_lut = 1; dc->caps.color.dpp.ogam_ram = 1; diff --git a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c index e2e792d23923..765002e0ff93 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c @@ -1327,6 +1327,7 @@ static bool dcn302_resource_construct( dc->caps.color.dpp.dgam_rom_caps.hlg = 1; dc->caps.color.dpp.post_csc = 1; dc->caps.color.dpp.gamma_corr = 1; + dc->caps.color.dpp.dgam_rom_for_yuv = 0; dc->caps.color.dpp.hw_3d_lut = 1; dc->caps.color.dpp.ogam_ram = 1; -- cgit v1.2.3 From c07cbc1f04ecba00f99e313de3190db5e7438e81 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Mon, 26 Oct 2020 12:33:24 -0400 Subject: drm/amd/display: update dpp dto phase and modulo. [Why & How] Program modulo with ref dpp clk Mhz/10. Program phase with pipe dpp clk Mhz /10. DMUB FW could use these value to determine optimization clk for PSR power saving. Signed-off-by: Yongqiang Sun Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c | 6 +- drivers/gpu/drm/amd/display/dc/dcn21/Makefile | 2 +- drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c | 125 +++++++++++++++++++++ drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h | 36 ++++++ .../gpu/drm/amd/display/dc/dcn21/dcn21_resource.c | 3 +- 5 files changed, 166 insertions(+), 6 deletions(-) create mode 100644 drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c create mode 100644 drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index c42d2f4e81e8..f30f3fdba433 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -158,10 +158,8 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, // workaround: Limit dppclk to 100Mhz to avoid lower eDP panel switch to plus 4K monitor underflow. // Do not adjust dppclk if dppclk is 0 to avoid unexpected result - if (!IS_DIAG_DC(dc->ctx->dce_environment)) { - if (new_clocks->dppclk_khz < 100000 && new_clocks->dppclk_khz > 0) - new_clocks->dppclk_khz = 100000; - } + if (new_clocks->dppclk_khz < 100000 && new_clocks->dppclk_khz > 0) + new_clocks->dppclk_khz = 100000; if (should_set_clock(safe_to_lower, new_clocks->dppclk_khz, clk_mgr->base.clks.dppclk_khz)) { if (clk_mgr->base.clks.dppclk_khz > new_clocks->dppclk_khz) diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/Makefile b/drivers/gpu/drm/amd/display/dc/dcn21/Makefile index 51a2f3d4c194..1ee5fc03b7b3 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/Makefile +++ b/drivers/gpu/drm/amd/display/dc/dcn21/Makefile @@ -3,7 +3,7 @@ # Makefile for DCN21. DCN21 = dcn21_init.o dcn21_hubp.o dcn21_hubbub.o dcn21_resource.o \ - dcn21_hwseq.o dcn21_link_encoder.o + dcn21_hwseq.o dcn21_link_encoder.o dcn21_dccg.o ifdef CONFIG_X86 CFLAGS_$(AMDDALPATH)/dc/dcn21/dcn21_resource.o := -mhard-float -msse diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c new file mode 100644 index 000000000000..f9e3a2337fbf --- /dev/null +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c @@ -0,0 +1,125 @@ +/* + * Copyright 2018 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#include "reg_helper.h" +#include "core_types.h" +#include "dcn20/dcn20_dccg.h" +#include "dcn21_dccg.h" + +#define TO_DCN_DCCG(dccg)\ + container_of(dccg, struct dcn_dccg, base) + +#define REG(reg) \ + (dccg_dcn->regs->reg) + +#undef FN +#define FN(reg_name, field_name) \ + dccg_dcn->dccg_shift->field_name, dccg_dcn->dccg_mask->field_name + +#define CTX \ + dccg_dcn->base.ctx +#define DC_LOGGER \ + dccg->ctx->logger + +void dccg21_update_dpp_dto(struct dccg *dccg, int dpp_inst, int req_dppclk) +{ + struct dcn_dccg *dccg_dcn = TO_DCN_DCCG(dccg); + + if (dccg->ref_dppclk) { + int ref_dppclk = dccg->ref_dppclk; + int modulo = ref_dppclk / 10000; + + if (req_dppclk) { + int phase; + + /* + * program DPP DTO phase and modulo as below + * phase = dpp_pipe_clk_mhz / 10 + * module = dpp_global_clk_mhz / 10 + * dmub FW will read phase value to + * determine minimum dpp clk and notify smu + * to set clks for more power saving in PSR state + */ + phase = (req_dppclk + 9999) / 10000; + + if (phase > 0xff) { + ASSERT(false); + phase = 0xff; + } + + REG_SET_2(DPPCLK_DTO_PARAM[dpp_inst], 0, + DPPCLK0_DTO_PHASE, phase, + DPPCLK0_DTO_MODULO, modulo); + REG_UPDATE(DPPCLK_DTO_CTRL, + DPPCLK_DTO_ENABLE[dpp_inst], 1); + } else { + /* + * set phase to 10 if dpp isn't used to + * prevent hard hang if access dpp register + * on unused pipe + */ + REG_SET_2(DPPCLK_DTO_PARAM[dpp_inst], 0, + DPPCLK0_DTO_PHASE, 10, + DPPCLK0_DTO_MODULO, modulo); + + REG_UPDATE(DPPCLK_DTO_CTRL, + DPPCLK_DTO_ENABLE[dpp_inst], 0); + } + } + + dccg->pipe_dppclk_khz[dpp_inst] = req_dppclk; +} + + +static const struct dccg_funcs dccg21_funcs = { + .update_dpp_dto = dccg21_update_dpp_dto, + .get_dccg_ref_freq = dccg2_get_dccg_ref_freq, + .dccg_init = dccg2_init +}; + +struct dccg *dccg21_create( + struct dc_context *ctx, + const struct dccg_registers *regs, + const struct dccg_shift *dccg_shift, + const struct dccg_mask *dccg_mask) +{ + struct dcn_dccg *dccg_dcn = kzalloc(sizeof(*dccg_dcn), GFP_KERNEL); + struct dccg *base; + + if (dccg_dcn == NULL) { + BREAK_TO_DEBUGGER(); + return NULL; + } + + base = &dccg_dcn->base; + base->ctx = ctx; + base->funcs = &dccg21_funcs; + + dccg_dcn->regs = regs; + dccg_dcn->dccg_shift = dccg_shift; + dccg_dcn->dccg_mask = dccg_mask; + + return &dccg_dcn->base; +} diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h new file mode 100644 index 000000000000..b7efa777ec73 --- /dev/null +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.h @@ -0,0 +1,36 @@ +/* + * Copyright 2018 Advanced Micro Devices, Inc. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL + * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR + * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Authors: AMD + * + */ + +#ifndef __DCN21_DCCG_H__ +#define __DCN21_DCCG_H__ + +struct dccg *dccg21_create( + struct dc_context *ctx, + const struct dccg_registers *regs, + const struct dccg_shift *dccg_shift, + const struct dccg_mask *dccg_mask); + + +#endif /* __DCN21_DCCG_H__ */ diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c index abc8af0ef141..ed3f62535301 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c @@ -58,6 +58,7 @@ #include "dce110/dce110_resource.h" #include "dml/display_mode_vba.h" #include "dcn20/dcn20_dccg.h" +#include "dcn21/dcn21_dccg.h" #include "dcn21_hubbub.h" #include "dcn10/dcn10_resource.h" #include "dce110/dce110_resource.h" @@ -2046,7 +2047,7 @@ static bool dcn21_resource_construct( } } - pool->base.dccg = dccg2_create(ctx, &dccg_regs, &dccg_shift, &dccg_mask); + pool->base.dccg = dccg21_create(ctx, &dccg_regs, &dccg_shift, &dccg_mask); if (pool->base.dccg == NULL) { dm_error("DC: failed to create dccg!\n"); BREAK_TO_DEBUGGER(); -- cgit v1.2.3 From 5c68c65295de0bc7856580e8b16d8fa0782ae2d3 Mon Sep 17 00:00:00 2001 From: Victor Lu Date: Fri, 23 Oct 2020 13:38:58 -0400 Subject: drm/amd/display: Explicitly disable cursor when disabling CRTC [why] On DCE, the cursor is not being disabled on commits where there is no CRTC or FB enabled. [how] Explicitly disable the cursor in the commit tail only if the pending commit disables the CRTC. Signed-off-by: Victor Lu Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 152b1b1f3c07..16e7eb4028e2 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8049,6 +8049,16 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) new_crtc_state->active_changed, new_crtc_state->connectors_changed); + /* Disable cursor if disabling crtc */ + if (old_crtc_state->active && !new_crtc_state->active) { + struct dc_cursor_position position; + + memset(&position, 0, sizeof(position)); + mutex_lock(&dm->dc_lock); + dc_stream_set_cursor_position(dm_old_crtc_state->stream, &position); + mutex_unlock(&dm->dc_lock); + } + /* Copy all transient state flags into dc state */ if (dm_new_crtc_state->stream) { amdgpu_dm_crtc_copy_transient_flags(&dm_new_crtc_state->base, -- cgit v1.2.3 From 4f6274b3b9a9d5395b1a5b757132a81023236808 Mon Sep 17 00:00:00 2001 From: Alvin Lee Date: Fri, 30 Oct 2020 13:49:46 -0400 Subject: drm/amd/display: Check other planes for iflip only if GSL already enabled [Why] We don't want GSL to be enabled when only updating plane address [How] Only check other pipes for immediate flip if GSL is already enabled Signed-off-by: Alvin Lee Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c index e65ec2a20fa2..b9c20e30d99d 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c @@ -1163,11 +1163,13 @@ void dcn20_pipe_control_lock( if (pipe->plane_state != NULL) flip_immediate = pipe->plane_state->flip_immediate; - temp_pipe = pipe->bottom_pipe; - while (!flip_immediate && temp_pipe) { - if (temp_pipe->plane_state != NULL) - flip_immediate = temp_pipe->plane_state->flip_immediate; - temp_pipe = temp_pipe->bottom_pipe; + if (pipe->stream_res.gsl_group > 0) { + temp_pipe = pipe->bottom_pipe; + while (!flip_immediate && temp_pipe) { + if (temp_pipe->plane_state != NULL) + flip_immediate = temp_pipe->plane_state->flip_immediate; + temp_pipe = temp_pipe->bottom_pipe; + } } if (flip_immediate && lock) { -- cgit v1.2.3 From 45b790dd8552bda5140f51bf5c85372f3c082f64 Mon Sep 17 00:00:00 2001 From: Anthony Koo Date: Sun, 1 Nov 2020 15:49:31 -0500 Subject: drm/amd/display: [FW Promotion] Release 0.0.41 Signed-off-by: Anthony Koo Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h index 81433c22fb51..b0d1347d13f0 100644 --- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h +++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h @@ -36,10 +36,10 @@ /* Firmware versioning. */ #ifdef DMUB_EXPOSE_VERSION -#define DMUB_FW_VERSION_GIT_HASH 0x9f0af34af +#define DMUB_FW_VERSION_GIT_HASH 0x821097815 #define DMUB_FW_VERSION_MAJOR 0 #define DMUB_FW_VERSION_MINOR 0 -#define DMUB_FW_VERSION_REVISION 40 +#define DMUB_FW_VERSION_REVISION 41 #define DMUB_FW_VERSION_TEST 0 #define DMUB_FW_VERSION_VBIOS 0 #define DMUB_FW_VERSION_HOTFIX 0 -- cgit v1.2.3 From b5fce050f041618cc6f9185d90c84f5d9599ce45 Mon Sep 17 00:00:00 2001 From: Aric Cyr Date: Mon, 2 Nov 2020 10:20:29 -0500 Subject: drm/amd/display: 3.2.111 Signed-off-by: Aric Cyr Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 27bcbe5fa7b0..5cf0b988c9c3 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -42,7 +42,7 @@ #include "inc/hw/dmcu.h" #include "dml/display_mode_lib.h" -#define DC_VER "3.2.110" +#define DC_VER "3.2.111" #define MAX_SURFACES 3 #define MAX_PLANES 6 -- cgit v1.2.3 From 4b0b1d05265b044472a23b76d5fda8d7fb218144 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Fri, 30 Oct 2020 09:29:07 -0400 Subject: drm/amd/display: check actual clock value. [Why] Actual dpp/disp clock PMFW set are always equal or more than requested. Need to cache the actual clock for debugging purpose. [How] Add actuall dpp/disp clk in clock manager and save it when set clocks. Add an ASSERT in case of actual clock less than requested. Signed-off-by: Yongqiang Sun Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c | 9 ++++++--- .../gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c | 8 ++++++++ drivers/gpu/drm/amd/display/dc/dc.h | 2 ++ 3 files changed, 16 insertions(+), 3 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index f30f3fdba433..ec394e3d8367 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -170,7 +170,7 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, if (should_set_clock(safe_to_lower, new_clocks->dispclk_khz, clk_mgr_base->clks.dispclk_khz)) { clk_mgr_base->clks.dispclk_khz = new_clocks->dispclk_khz; - rn_vbios_smu_set_dispclk(clk_mgr, clk_mgr_base->clks.dispclk_khz); + clk_mgr_base->clks.actual_dispclk_khz = rn_vbios_smu_set_dispclk(clk_mgr, clk_mgr_base->clks.dispclk_khz); update_dispclk = true; } @@ -178,11 +178,14 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, if (dpp_clock_lowered) { // increase per DPP DTO before lowering global dppclk dcn20_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); - rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); + clk_mgr_base->clks.actual_dppclk_khz = + rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); + } else { // increase global DPPCLK before lowering per DPP DTO if (update_dppclk || update_dispclk) - rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); + clk_mgr_base->clks.actual_dppclk_khz = + rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); // always update dtos unless clock is lowered and not safe to lower if (new_clocks->dppclk_khz >= dc->current_state->bw_ctx.bw.dcn.clk.dppclk_khz) dcn20_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c index 9a374522e963..ab2b9c61e565 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c @@ -136,6 +136,10 @@ int rn_vbios_smu_set_dispclk(struct clk_mgr_internal *clk_mgr, int requested_dis } } + // pmfw always set clock more than or equal requested clock + if (!IS_DIAG_DC(dc->ctx->dce_environment)) + ASSERT(actual_dispclk_set_mhz >= requested_dispclk_khz / 1000); + return actual_dispclk_set_mhz * 1000; } @@ -194,12 +198,16 @@ void rn_vbios_smu_set_phyclk(struct clk_mgr_internal *clk_mgr, int requested_phy int rn_vbios_smu_set_dppclk(struct clk_mgr_internal *clk_mgr, int requested_dpp_khz) { int actual_dppclk_set_mhz = -1; + struct dc *dc = clk_mgr->base.ctx->dc; actual_dppclk_set_mhz = rn_vbios_smu_send_msg_with_param( clk_mgr, VBIOSSMC_MSG_SetDppclkFreq, requested_dpp_khz / 1000); + if (!IS_DIAG_DC(dc->ctx->dce_environment)) + ASSERT(actual_dppclk_set_mhz >= requested_dpp_khz / 1000); + return actual_dppclk_set_mhz * 1000; } diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 5cf0b988c9c3..4c57cf099b5e 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -342,7 +342,9 @@ enum dcn_pwr_state { */ struct dc_clocks { int dispclk_khz; + int actual_dispclk_khz; int dppclk_khz; + int actual_dppclk_khz; int disp_dpp_voltage_level_khz; int dcfclk_khz; int socclk_khz; -- cgit v1.2.3 From 880af2eaedd3f63d413a439ef29edcc0a5fbdc73 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Sun, 1 Nov 2020 13:05:11 -0500 Subject: drm/amd/display: cap dpp dto phase not more than modulo. [Why] 4K monitor shows corruption if dpp dto phase is larger than modulo. [How] cap phase value never larger than modulo. Signed-off-by: Yongqiang Sun Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c | 46 ++++++++++++----------- 1 file changed, 25 insertions(+), 21 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c index f9e3a2337fbf..60cf3ff68cb0 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_dccg.c @@ -50,43 +50,47 @@ void dccg21_update_dpp_dto(struct dccg *dccg, int dpp_inst, int req_dppclk) if (dccg->ref_dppclk) { int ref_dppclk = dccg->ref_dppclk; int modulo = ref_dppclk / 10000; + int phase; if (req_dppclk) { - int phase; - /* * program DPP DTO phase and modulo as below - * phase = dpp_pipe_clk_mhz / 10 - * module = dpp_global_clk_mhz / 10 - * dmub FW will read phase value to - * determine minimum dpp clk and notify smu - * to set clks for more power saving in PSR state + * phase = ceiling(dpp_pipe_clk_mhz / 10) + * module = trunc(dpp_global_clk_mhz / 10) + * + * storing frequencies in registers allow dmcub fw + * to run time lower clocks when possible for power saving + * + * ceiling phase and truncate modulo guarentees the divided + * down per pipe dpp clock has high enough frequency */ phase = (req_dppclk + 9999) / 10000; - if (phase > 0xff) { - ASSERT(false); - phase = 0xff; + if (phase > modulo) { + /* phase > modulo result in screen corruption + * ie phase = 30, mod = 29 for 4k@60 HDMI + * in these case we don't want pipe clock to be divided + */ + phase = modulo; } - - REG_SET_2(DPPCLK_DTO_PARAM[dpp_inst], 0, - DPPCLK0_DTO_PHASE, phase, - DPPCLK0_DTO_MODULO, modulo); - REG_UPDATE(DPPCLK_DTO_CTRL, - DPPCLK_DTO_ENABLE[dpp_inst], 1); } else { /* * set phase to 10 if dpp isn't used to * prevent hard hang if access dpp register * on unused pipe + * + * DTO should be on to divide down un-used + * pipe clock for power saving */ - REG_SET_2(DPPCLK_DTO_PARAM[dpp_inst], 0, - DPPCLK0_DTO_PHASE, 10, + phase = 10; + } + + REG_SET_2(DPPCLK_DTO_PARAM[dpp_inst], 0, + DPPCLK0_DTO_PHASE, phase, DPPCLK0_DTO_MODULO, modulo); - REG_UPDATE(DPPCLK_DTO_CTRL, - DPPCLK_DTO_ENABLE[dpp_inst], 0); - } + REG_UPDATE(DPPCLK_DTO_CTRL, + DPPCLK_DTO_ENABLE[dpp_inst], 1); } dccg->pipe_dppclk_khz[dpp_inst] = req_dppclk; -- cgit v1.2.3 From 20b15c0ad7c5c9daf1d220ac35bd758d53154e46 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Fri, 6 Nov 2020 21:49:42 +0000 Subject: drm/amd/display/dc/basics/fixpt31_32: Move variables to where they're used MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Also rid some unused ones. This patch solves 2000 warnings! Fixes the following W=1 kernel build warning(s): In file included from drivers/gpu/drm/amd/amdgpu/../display/dc/dc_types.h:33, from drivers/gpu/drm/amd/amdgpu/../display/dc/dm_services_types.h:30, from drivers/gpu/drm/amd/amdgpu/../display/dc/dm_services.h:35, from drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_helpers.c:35: At top level: drivers/gpu/drm/amd/amdgpu/../display/include/fixed31_32.h:76:32: warning: ‘dc_fixpt_ln2_div_2’ defined but not used [-Wunused-const-variable=] 76 | static const struct fixed31_32 dc_fixpt_ln2_div_2 = { 1488522236LL }; | ^~~~~~~~~~~~~~~~~~ drivers/gpu/drm/amd/amdgpu/../display/include/fixed31_32.h:75:32: warning: ‘dc_fixpt_ln2’ defined but not used [-Wunused-const-variable=] 75 | static const struct fixed31_32 dc_fixpt_ln2 = { 2977044471LL }; | ^~~~~~~~~~~~ drivers/gpu/drm/amd/amdgpu/../display/include/fixed31_32.h:74:32: warning: ‘dc_fixpt_e’ defined but not used [-Wunused-const-variable=] 74 | static const struct fixed31_32 dc_fixpt_e = { 11674931555LL }; | ^~~~~~~~~~ drivers/gpu/drm/amd/amdgpu/../display/include/fixed31_32.h:73:32: warning: ‘dc_fixpt_two_pi’ defined but not used [-Wunused-const-variable=] 73 | static const struct fixed31_32 dc_fixpt_two_pi = { 26986075409LL }; | ^~~~~~~~~~~~~~~ drivers/gpu/drm/amd/amdgpu/../display/include/fixed31_32.h:72:32: warning: ‘dc_fixpt_pi’ defined but not used [-Wunused-const-variable=] 72 | static const struct fixed31_32 dc_fixpt_pi = { 13493037705LL }; | ^~~~~~~~~~~ Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c | 5 +++++ drivers/gpu/drm/amd/display/include/fixed31_32.h | 6 ------ 2 files changed, 5 insertions(+), 6 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c b/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c index 1e9a2d352068..59f37563704a 100644 --- a/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c +++ b/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c @@ -26,6 +26,11 @@ #include "dm_services.h" #include "include/fixed31_32.h" +static const struct fixed31_32 dc_fixpt_pi = { 13493037705LL }; +static const struct fixed31_32 dc_fixpt_two_pi = { 26986075409LL }; +static const struct fixed31_32 dc_fixpt_ln2 = { 2977044471LL }; +static const struct fixed31_32 dc_fixpt_ln2_div_2 = { 1488522236LL }; + static inline unsigned long long abs_i64( long long arg) { diff --git a/drivers/gpu/drm/amd/display/include/fixed31_32.h b/drivers/gpu/drm/amd/display/include/fixed31_32.h index 16df2a485dd0..22053d7ea6ce 100644 --- a/drivers/gpu/drm/amd/display/include/fixed31_32.h +++ b/drivers/gpu/drm/amd/display/include/fixed31_32.h @@ -69,12 +69,6 @@ static const struct fixed31_32 dc_fixpt_epsilon = { 1LL }; static const struct fixed31_32 dc_fixpt_half = { 0x80000000LL }; static const struct fixed31_32 dc_fixpt_one = { 0x100000000LL }; -static const struct fixed31_32 dc_fixpt_pi = { 13493037705LL }; -static const struct fixed31_32 dc_fixpt_two_pi = { 26986075409LL }; -static const struct fixed31_32 dc_fixpt_e = { 11674931555LL }; -static const struct fixed31_32 dc_fixpt_ln2 = { 2977044471LL }; -static const struct fixed31_32 dc_fixpt_ln2_div_2 = { 1488522236LL }; - /* * @brief * Initialization routines -- cgit v1.2.3 From 5c0e684074d573c75145d1064f92c1be615901ef Mon Sep 17 00:00:00 2001 From: Bernard Zhao Date: Tue, 10 Nov 2020 00:03:13 -0800 Subject: amd/display/amdgpu_dm: delete same check in if condition In function amdgpu_dm_connector_get_modes, drm_edid_is_valid will check weather (!edid), no need to check again in the if branch. Reviewed-by: Harry Wentland Signed-off-by: Bernard Zhao Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 16e7eb4028e2..678bd81a9bff 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -6846,7 +6846,7 @@ static int amdgpu_dm_connector_get_modes(struct drm_connector *connector) encoder = amdgpu_dm_connector_to_encoder(connector); - if (!edid || !drm_edid_is_valid(edid)) { + if (!drm_edid_is_valid(edid)) { amdgpu_dm_connector->num_modes = drm_add_modes_noedid(connector, 640, 480); } else { -- cgit v1.2.3 From 1a3089565e45af66b995d5fcfb4cca87aff68c7a Mon Sep 17 00:00:00 2001 From: Alex Deucher Date: Tue, 10 Nov 2020 18:25:01 -0500 Subject: drm/amdgpu/display: fix FP handling in DCN30 Adjust the FP handling to avoid nested calls. The nested calls cause the warning below WARNING: CPU: 3 PID: 384 at arch/x86/kernel/fpu/core.c:129 kernel_fpu_begin Fixes: 582e2ce5b4ece3 ("drm/amdgpu/display: FP fixes for DCN3.x (v4)") Signed-off-by: Alex Deucher Signed-off-by: Bhawanpreet Lakha Reviewed-by: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- .../gpu/drm/amd/display/dc/dcn30/dcn30_resource.c | 43 +++------------------- 1 file changed, 6 insertions(+), 37 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c index b379057e669c..d5c81ad55045 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c @@ -1470,20 +1470,8 @@ int dcn30_populate_dml_pipes_from_context( return pipe_cnt; } -/* - * This must be noinline to ensure anything that deals with FP registers - * is contained within this call; previously our compiling with hard-float - * would result in fp instructions being emitted outside of the boundaries - * of the DC_FP_START/END macros, which makes sense as the compiler has no - * idea about what is wrapped and what is not - * - * This is largely just a workaround to avoid breakage introduced with 5.6, - * ideally all fp-using code should be moved into its own file, only that - * should be compiled with hard-float, and all code exported from there - * should be strictly wrapped with DC_FP_START/END - */ -static noinline void dcn30_populate_dml_writeback_from_context_fp( - struct dc *dc, struct resource_context *res_ctx, display_e2e_pipe_params_st *pipes) +void dcn30_populate_dml_writeback_from_context( + struct dc *dc, struct resource_context *res_ctx, display_e2e_pipe_params_st *pipes) { int pipe_cnt, i, j; double max_calc_writeback_dispclk; @@ -1571,14 +1559,6 @@ static noinline void dcn30_populate_dml_writeback_from_context_fp( } -void dcn30_populate_dml_writeback_from_context( - struct dc *dc, struct resource_context *res_ctx, display_e2e_pipe_params_st *pipes) -{ - DC_FP_START(); - dcn30_populate_dml_writeback_from_context_fp(dc, res_ctx, pipes); - DC_FP_END(); -} - unsigned int dcn30_calc_max_scaled_time( unsigned int time_per_pixel, enum mmhubbub_wbif_mode mode, @@ -1977,7 +1957,7 @@ static struct pipe_ctx *dcn30_find_split_pipe( return pipe; } -static bool dcn30_internal_validate_bw( +static noinline bool dcn30_internal_validate_bw( struct dc *dc, struct dc_state *context, display_e2e_pipe_params_st *pipes, @@ -1999,6 +1979,7 @@ static bool dcn30_internal_validate_bw( pipe_cnt = dc->res_pool->funcs->populate_dml_pipes(dc, context, pipes, fast_validate); + DC_FP_START(); if (!pipe_cnt) { out = true; goto validate_out; @@ -2222,6 +2203,7 @@ validate_fail: out = false; validate_out: + DC_FP_END(); return out; } @@ -2404,7 +2386,7 @@ void dcn30_calculate_wm_and_dlg( DC_FP_END(); } -static noinline bool dcn30_validate_bandwidth_fp(struct dc *dc, +bool dcn30_validate_bandwidth(struct dc *dc, struct dc_state *context, bool fast_validate) { @@ -2455,19 +2437,6 @@ validate_out: return out; } -bool dcn30_validate_bandwidth(struct dc *dc, - struct dc_state *context, - bool fast_validate) -{ - bool out; - - DC_FP_START(); - out = dcn30_validate_bandwidth_fp(dc, context, fast_validate); - DC_FP_END(); - - return out; -} - static noinline void get_optimal_dcfclk_fclk_for_uclk(unsigned int uclk_mts, unsigned int *optimal_dcfclk, unsigned int *optimal_fclk) -- cgit v1.2.3 From 8dfcb24e40e4f2b2502007116e1d22294dbce026 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Fri, 13 Nov 2020 13:49:00 +0000 Subject: drm/amd/display/dc/core/dc_link_dp: Move DP_VGA_LVDS_CONVERTER_ID_{2, 3} to where they're used MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This patch fixes >200 warnings. Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/include/ddc_service_types.h:123:22: warning: ‘DP_VGA_LVDS_CONVERTER_ID_3’ defined but not used [-Wunused-const-variable=] 123 | static const uint8_t DP_VGA_LVDS_CONVERTER_ID_3[] = "dnomlA"; | ^~~~~~~~~~~~~~~~~~~~~~~~~~ drivers/gpu/drm/amd/amdgpu/../display/include/ddc_service_types.h:121:22: warning: ‘DP_VGA_LVDS_CONVERTER_ID_2’ defined but not used [-Wunused-const-variable=] 121 | static const uint8_t DP_VGA_LVDS_CONVERTER_ID_2[] = "sivarT"; NB: Repeated ~100 times - snipped for brevity Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | 5 +++++ drivers/gpu/drm/amd/display/include/ddc_service_types.h | 4 ---- 2 files changed, 5 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c index 6c60c1fdebdc..f2023d2b5323 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c @@ -15,6 +15,11 @@ #include "dc_dmub_srv.h" #include "dce/dmub_hw_lock_mgr.h" +/*Travis*/ +static const uint8_t DP_VGA_LVDS_CONVERTER_ID_2[] = "sivarT"; +/*Nutmeg*/ +static const uint8_t DP_VGA_LVDS_CONVERTER_ID_3[] = "dnomlA"; + #define DC_LOGGER \ link->ctx->logger #define DC_TRACE_LEVEL_MESSAGE(...) /* do nothing */ diff --git a/drivers/gpu/drm/amd/display/include/ddc_service_types.h b/drivers/gpu/drm/amd/display/include/ddc_service_types.h index c9be899cd25c..b453ce5a9bfd 100644 --- a/drivers/gpu/drm/amd/display/include/ddc_service_types.h +++ b/drivers/gpu/drm/amd/display/include/ddc_service_types.h @@ -117,10 +117,6 @@ struct av_sync_data { uint8_t aud_del_ins3;/* DPCD 0002Dh */ }; -/*Travis*/ -static const uint8_t DP_VGA_LVDS_CONVERTER_ID_2[] = "sivarT"; -/*Nutmeg*/ -static const uint8_t DP_VGA_LVDS_CONVERTER_ID_3[] = "dnomlA"; /*DP to Dual link DVI converter*/ static const uint8_t DP_DVI_CONVERTER_ID_4[] = "m2DVIa"; static const uint8_t DP_DVI_CONVERTER_ID_5[] = "3393N2"; -- cgit v1.2.3 From f631eae5259b86de9c0da331647a1d0905c22ce0 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Fri, 13 Nov 2020 13:49:01 +0000 Subject: drm/amd/display/dc/core/dc_link_ddc: Move DP_DVI_CONVERTER_ID_{4, 5} to where they're used MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This patch fixes >200 warnings. Fixes the following W=1 kernel build warning(s): from drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm.c:31: drivers/gpu/drm/amd/amdgpu/../display/include/ddc_service_types.h:126:22: warning: ‘DP_DVI_CONVERTER_ID_5’ defined but not used [-Wunused-const-variable=] 126 | static const uint8_t DP_DVI_CONVERTER_ID_5[] = "3393N2"; | ^~~~~~~~~~~~~~~~~~~~~ drivers/gpu/drm/amd/amdgpu/../display/include/ddc_service_types.h:125:22: warning: ‘DP_DVI_CONVERTER_ID_4’ defined but not used [-Wunused-const-variable=] 125 | static const uint8_t DP_DVI_CONVERTER_ID_4[] = "m2DVIa"; | ^~~~~~~~~~~~~~~~~~~~~ Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link_ddc.c | 4 ++++ drivers/gpu/drm/amd/display/include/ddc_service_types.h | 4 ---- 2 files changed, 4 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_ddc.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_ddc.c index 54beda4d4e85..c5936e064360 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_ddc.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_ddc.c @@ -37,6 +37,10 @@ #include "dc_link_ddc.h" #include "dce/dce_aux.h" +/*DP to Dual link DVI converter*/ +static const uint8_t DP_DVI_CONVERTER_ID_4[] = "m2DVIa"; +static const uint8_t DP_DVI_CONVERTER_ID_5[] = "3393N2"; + #define AUX_POWER_UP_WA_DELAY 500 #define I2C_OVER_AUX_DEFER_WA_DELAY 70 #define I2C_OVER_AUX_DEFER_WA_DELAY_1MS 1 diff --git a/drivers/gpu/drm/amd/display/include/ddc_service_types.h b/drivers/gpu/drm/amd/display/include/ddc_service_types.h index b453ce5a9bfd..4de59b66bb1a 100644 --- a/drivers/gpu/drm/amd/display/include/ddc_service_types.h +++ b/drivers/gpu/drm/amd/display/include/ddc_service_types.h @@ -117,8 +117,4 @@ struct av_sync_data { uint8_t aud_del_ins3;/* DPCD 0002Dh */ }; -/*DP to Dual link DVI converter*/ -static const uint8_t DP_DVI_CONVERTER_ID_4[] = "m2DVIa"; -static const uint8_t DP_DVI_CONVERTER_ID_5[] = "3393N2"; - #endif /* __DAL_DDC_SERVICE_TYPES_H__ */ -- cgit v1.2.3 From 52f6f16d4fe4dd6624c7d6555ba0bd95930e0a1a Mon Sep 17 00:00:00 2001 From: Alex Deucher Date: Fri, 13 Nov 2020 02:21:19 -0500 Subject: drm/amd/display: Add missing pflip irq for dcn2.0 If we have more than 4 displays we will run into dummy irq calls or flip timout issues. Reviewed-by: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/irq/dcn20/irq_service_dcn20.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/irq/dcn20/irq_service_dcn20.c b/drivers/gpu/drm/amd/display/dc/irq/dcn20/irq_service_dcn20.c index 2a1fea501f8c..3f1e7a196a23 100644 --- a/drivers/gpu/drm/amd/display/dc/irq/dcn20/irq_service_dcn20.c +++ b/drivers/gpu/drm/amd/display/dc/irq/dcn20/irq_service_dcn20.c @@ -299,8 +299,8 @@ irq_source_info_dcn20[DAL_IRQ_SOURCES_NUMBER] = { pflip_int_entry(1), pflip_int_entry(2), pflip_int_entry(3), - [DC_IRQ_SOURCE_PFLIP5] = dummy_irq_entry(), - [DC_IRQ_SOURCE_PFLIP6] = dummy_irq_entry(), + pflip_int_entry(4), + pflip_int_entry(5), [DC_IRQ_SOURCE_PFLIP_UNDERLAY0] = dummy_irq_entry(), gpio_pad_int_entry(0), gpio_pad_int_entry(1), -- cgit v1.2.3 From 816853f9dc4057b6c7ee3c45ca9bd5905649092e Mon Sep 17 00:00:00 2001 From: Bas Nieuwenhuizen Date: Wed, 11 Nov 2020 03:48:39 +0100 Subject: drm/amd/display: Set new format info for converted metadata. If we use DCC modifiers this can increase the number of planes from the initial 1 plane with metadata, so that we get a valid modifier from getfb2. Since the code didn't update the format_info getfb2 would only ever return 1 plane with a modifier for which userspace expects > 1. This moves the format lookup to amdgpu_display.c so we do not have issues when DC is not compiled. Reviewed-by: Alex Deucher Signed-off-by: Bas Nieuwenhuizen Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_display.c | 97 +++++++++++++++++++++++ drivers/gpu/drm/amd/amdgpu/amdgpu_display.h | 2 + drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 88 +------------------- 3 files changed, 100 insertions(+), 87 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c index e80b295f23c4..6ed81930ccc2 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.c @@ -534,6 +534,95 @@ uint32_t amdgpu_display_supported_domains(struct amdgpu_device *adev, return domain; } +static const struct drm_format_info dcc_formats[] = { + { .format = DRM_FORMAT_XRGB8888, .depth = 24, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_XBGR8888, .depth = 24, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_ARGB8888, .depth = 32, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_ABGR8888, .depth = 32, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_BGRA8888, .depth = 32, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_XRGB2101010, .depth = 30, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_XBGR2101010, .depth = 30, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_ARGB2101010, .depth = 30, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_ABGR2101010, .depth = 30, .num_planes = 2, + .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_RGB565, .depth = 16, .num_planes = 2, + .cpp = { 2, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, +}; + +static const struct drm_format_info dcc_retile_formats[] = { + { .format = DRM_FORMAT_XRGB8888, .depth = 24, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_XBGR8888, .depth = 24, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_ARGB8888, .depth = 32, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_ABGR8888, .depth = 32, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_BGRA8888, .depth = 32, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_XRGB2101010, .depth = 30, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_XBGR2101010, .depth = 30, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, + { .format = DRM_FORMAT_ARGB2101010, .depth = 30, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_ABGR2101010, .depth = 30, .num_planes = 3, + .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, + .has_alpha = true, }, + { .format = DRM_FORMAT_RGB565, .depth = 16, .num_planes = 3, + .cpp = { 2, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, +}; + +static const struct drm_format_info * +lookup_format_info(const struct drm_format_info formats[], + int num_formats, u32 format) +{ + int i; + + for (i = 0; i < num_formats; i++) { + if (formats[i].format == format) + return &formats[i]; + } + + return NULL; +} + +const struct drm_format_info * +amdgpu_lookup_format_info(u32 format, uint64_t modifier) +{ + if (!IS_AMD_FMT_MOD(modifier)) + return NULL; + + if (AMD_FMT_MOD_GET(DCC_RETILE, modifier)) + return lookup_format_info(dcc_retile_formats, + ARRAY_SIZE(dcc_retile_formats), + format); + + if (AMD_FMT_MOD_GET(DCC, modifier)) + return lookup_format_info(dcc_formats, ARRAY_SIZE(dcc_formats), + format); + + /* returning NULL will cause the default format structs to be used. */ + return NULL; +} + static int convert_tiling_flags_to_modifier(struct amdgpu_framebuffer *afb) { struct amdgpu_device *adev = drm_to_adev(afb->base.dev); @@ -623,6 +712,7 @@ static int convert_tiling_flags_to_modifier(struct amdgpu_framebuffer *afb) if (dcc_offset != 0) { bool dcc_i64b = AMDGPU_TILING_GET(afb->tiling_flags, DCC_INDEPENDENT_64B) != 0; bool dcc_i128b = version >= AMD_FMT_MOD_TILE_VER_GFX10_RBPLUS; + const struct drm_format_info *format_info; /* Enable constant encode on RAVEN2 and later. */ bool dcc_constant_encode = adev->asic_type > CHIP_RAVEN || @@ -641,6 +731,13 @@ static int convert_tiling_flags_to_modifier(struct amdgpu_framebuffer *afb) afb->base.offsets[1] = dcc_offset * 256 + afb->base.offsets[0]; afb->base.pitches[1] = AMDGPU_TILING_GET(afb->tiling_flags, DCC_PITCH_MAX) + 1; + + format_info = amdgpu_lookup_format_info(afb->base.format->format, + modifier); + if (!format_info) + return -EINVAL; + + afb->base.format = format_info; } } diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h index 3620b24785e1..dc7b7d116549 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_display.h @@ -44,5 +44,7 @@ struct drm_framebuffer * amdgpu_display_user_framebuffer_create(struct drm_device *dev, struct drm_file *file_priv, const struct drm_mode_fb_cmd2 *mode_cmd); +const struct drm_format_info * +amdgpu_lookup_format_info(u32 format, uint64_t modifier); #endif diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 678bd81a9bff..7f38a7cba76c 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -3847,96 +3847,10 @@ modifier_gfx9_swizzle_mode(uint64_t modifier) return AMD_FMT_MOD_GET(TILE, modifier); } -static const struct drm_format_info dcc_formats[] = { - { .format = DRM_FORMAT_XRGB8888, .depth = 24, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_XBGR8888, .depth = 24, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_ARGB8888, .depth = 32, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_ABGR8888, .depth = 32, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_BGRA8888, .depth = 32, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_XRGB2101010, .depth = 30, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_XBGR2101010, .depth = 30, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_ARGB2101010, .depth = 30, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_ABGR2101010, .depth = 30, .num_planes = 2, - .cpp = { 4, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_RGB565, .depth = 16, .num_planes = 2, - .cpp = { 2, 0, }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, -}; - -static const struct drm_format_info dcc_retile_formats[] = { - { .format = DRM_FORMAT_XRGB8888, .depth = 24, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_XBGR8888, .depth = 24, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_ARGB8888, .depth = 32, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_ABGR8888, .depth = 32, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_BGRA8888, .depth = 32, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_XRGB2101010, .depth = 30, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_XBGR2101010, .depth = 30, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, - { .format = DRM_FORMAT_ARGB2101010, .depth = 30, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_ABGR2101010, .depth = 30, .num_planes = 3, - .cpp = { 4, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, - .has_alpha = true, }, - { .format = DRM_FORMAT_RGB565, .depth = 16, .num_planes = 3, - .cpp = { 2, 0, 0 }, .block_w = {1, 1, 1}, .block_h = {1, 1, 1}, .hsub = 1, .vsub = 1, }, -}; - - -static const struct drm_format_info * -lookup_format_info(const struct drm_format_info formats[], - int num_formats, u32 format) -{ - int i; - - for (i = 0; i < num_formats; i++) { - if (formats[i].format == format) - return &formats[i]; - } - - return NULL; -} - static const struct drm_format_info * amd_get_format_info(const struct drm_mode_fb_cmd2 *cmd) { - uint64_t modifier = cmd->modifier[0]; - - if (!IS_AMD_FMT_MOD(modifier)) - return NULL; - - if (AMD_FMT_MOD_GET(DCC_RETILE, modifier)) - return lookup_format_info(dcc_retile_formats, - ARRAY_SIZE(dcc_retile_formats), - cmd->pixel_format); - - if (AMD_FMT_MOD_GET(DCC, modifier)) - return lookup_format_info(dcc_formats, ARRAY_SIZE(dcc_formats), - cmd->pixel_format); - - /* returning NULL will cause the default format structs to be used. */ - return NULL; + return amdgpu_lookup_format_info(cmd->pixel_format, cmd->modifier[0]); } static void -- cgit v1.2.3 From 5fe6b98ae00dc2e0ac24ef8a45d828b82a4aae90 Mon Sep 17 00:00:00 2001 From: Bhawanpreet Lakha Date: Fri, 13 Nov 2020 15:04:54 -0500 Subject: drm/amd/display: Update dmub code There is a delta in the dmub code - add boot options - add boot status - remove unused auto_load_is_done func pointer Signed-off-by: Bhawanpreet Lakha Reviewed-by: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dmub/dmub_srv.h | 20 ++++++++++++++++- drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h | 3 ++- drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.c | 23 ++++++++++++++++++++ drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.h | 6 ++++++ drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.c | 5 ----- drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.h | 2 -- drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.c | 5 ----- drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.h | 1 - drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c | 26 +++++++++++++++++------ 9 files changed, 70 insertions(+), 21 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dmub/dmub_srv.h b/drivers/gpu/drm/amd/display/dmub/dmub_srv.h index ac41ae2d261b..b82a46890846 100644 --- a/drivers/gpu/drm/amd/display/dmub/dmub_srv.h +++ b/drivers/gpu/drm/amd/display/dmub/dmub_srv.h @@ -265,8 +265,12 @@ struct dmub_srv_hw_funcs { bool (*is_hw_init)(struct dmub_srv *dmub); bool (*is_phy_init)(struct dmub_srv *dmub); + void (*enable_dmub_boot_options)(struct dmub_srv *dmub); + + void (*skip_dmub_panel_power_sequence)(struct dmub_srv *dmub, bool skip); + + union dmub_fw_boot_status (*get_fw_status)(struct dmub_srv *dmub); - bool (*is_auto_load_done)(struct dmub_srv *dmub); void (*set_gpint)(struct dmub_srv *dmub, union dmub_gpint_data_register reg); @@ -309,6 +313,7 @@ struct dmub_srv_hw_params { uint64_t fb_offset; uint32_t psp_version; bool load_inst_const; + bool skip_panel_power_sequence; }; /** @@ -590,6 +595,19 @@ enum dmub_status dmub_srv_get_gpint_response(struct dmub_srv *dmub, */ void dmub_flush_buffer_mem(const struct dmub_fb *fb); +/** + * dmub_srv_get_fw_boot_status() - Returns the DMUB boot status bits. + * + * @dmub: the dmub service + * @status: out pointer for firmware status + * + * Return: + * DMUB_STATUS_OK - success + * DMUB_STATUS_INVALID - unspecified error, unsupported + */ +enum dmub_status dmub_srv_get_fw_boot_status(struct dmub_srv *dmub, + union dmub_fw_boot_status *status); + #if defined(__cplusplus) } #endif diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h index b0d1347d13f0..9fd24f93a216 100644 --- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h +++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h @@ -191,7 +191,8 @@ union dmub_fw_boot_options { uint32_t optimized_init : 1; uint32_t skip_phy_access : 1; uint32_t disable_clk_gate: 1; - uint32_t reserved : 27; + uint32_t skip_phy_init_panel_sequence: 1; + uint32_t reserved : 26; } bits; uint32_t all; }; diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.c b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.c index 2c4a2fe9311d..cafba1d23c6a 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.c +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.c @@ -312,3 +312,26 @@ uint32_t dmub_dcn20_get_gpint_response(struct dmub_srv *dmub) { return REG_READ(DMCUB_SCRATCH7); } + +union dmub_fw_boot_status dmub_dcn20_get_fw_boot_status(struct dmub_srv *dmub) +{ + union dmub_fw_boot_status status; + + status.all = REG_READ(DMCUB_SCRATCH0); + return status; +} + +void dmub_dcn20_enable_dmub_boot_options(struct dmub_srv *dmub) +{ + union dmub_fw_boot_options boot_options = {0}; + + REG_WRITE(DMCUB_SCRATCH14, boot_options.all); +} + +void dmub_dcn20_skip_dmub_panel_power_sequence(struct dmub_srv *dmub, bool skip) +{ + union dmub_fw_boot_options boot_options; + boot_options.all = REG_READ(DMCUB_SCRATCH14); + boot_options.bits.skip_phy_init_panel_sequence = skip; + REG_WRITE(DMCUB_SCRATCH14, boot_options.all); +} diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.h b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.h index a316f260f6ac..d438f365cbb0 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.h +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn20.h @@ -192,4 +192,10 @@ bool dmub_dcn20_is_gpint_acked(struct dmub_srv *dmub, uint32_t dmub_dcn20_get_gpint_response(struct dmub_srv *dmub); +void dmub_dcn20_enable_dmub_boot_options(struct dmub_srv *dmub); + +void dmub_dcn20_skip_dmub_panel_power_sequence(struct dmub_srv *dmub, bool skip); + +union dmub_fw_boot_status dmub_dcn20_get_fw_boot_status(struct dmub_srv *dmub); + #endif /* _DMUB_DCN20_H_ */ diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.c b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.c index e8f488232e34..1cf67b3e4771 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.c +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.c @@ -53,11 +53,6 @@ const struct dmub_srv_common_regs dmub_srv_dcn21_regs = { /* Shared functions. */ -bool dmub_dcn21_is_auto_load_done(struct dmub_srv *dmub) -{ - return (REG_READ(DMCUB_SCRATCH0) == 3); -} - bool dmub_dcn21_is_phy_init(struct dmub_srv *dmub) { return REG_READ(DMCUB_SCRATCH10) == 0; diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.h b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.h index 2bbea237137b..6fd5b0cd4ef3 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.h +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn21.h @@ -34,8 +34,6 @@ extern const struct dmub_srv_common_regs dmub_srv_dcn21_regs; /* Hardware functions. */ -bool dmub_dcn21_is_auto_load_done(struct dmub_srv *dmub); - bool dmub_dcn21_is_phy_init(struct dmub_srv *dmub); #endif /* _DMUB_DCN21_H_ */ diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.c b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.c index 215178b8d415..f00df02ded81 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.c +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.c @@ -188,8 +188,3 @@ void dmub_dcn30_setup_windows(struct dmub_srv *dmub, DMCUB_REGION3_CW6_TOP_ADDRESS, cw6->region.top, DMCUB_REGION3_CW6_ENABLE, 1); } - -bool dmub_dcn30_is_auto_load_done(struct dmub_srv *dmub) -{ - return (REG_READ(DMCUB_SCRATCH0) > 0); -} diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.h b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.h index 4d8f52b8f12c..9a3afffd9b0f 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.h +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_dcn30.h @@ -45,6 +45,5 @@ void dmub_dcn30_setup_windows(struct dmub_srv *dmub, const struct dmub_window *cw5, const struct dmub_window *cw6); -bool dmub_dcn30_is_auto_load_done(struct dmub_srv *dmub); #endif /* _DMUB_DCN30_H_ */ diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c b/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c index d11b96d132ad..ba8494cf005f 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c @@ -153,17 +153,18 @@ static bool dmub_srv_hw_setup(struct dmub_srv *dmub, enum dmub_asic asic) funcs->set_gpint = dmub_dcn20_set_gpint; funcs->is_gpint_acked = dmub_dcn20_is_gpint_acked; funcs->get_gpint_response = dmub_dcn20_get_gpint_response; + funcs->get_fw_status = dmub_dcn20_get_fw_boot_status; + funcs->enable_dmub_boot_options = dmub_dcn20_enable_dmub_boot_options; + funcs->skip_dmub_panel_power_sequence = dmub_dcn20_skip_dmub_panel_power_sequence; if (asic == DMUB_ASIC_DCN21) { dmub->regs = &dmub_srv_dcn21_regs; - funcs->is_auto_load_done = dmub_dcn21_is_auto_load_done; funcs->is_phy_init = dmub_dcn21_is_phy_init; } if (asic == DMUB_ASIC_DCN30) { dmub->regs = &dmub_srv_dcn30_regs; - funcs->is_auto_load_done = dmub_dcn30_is_auto_load_done; funcs->backdoor_load = dmub_dcn30_backdoor_load; funcs->setup_windows = dmub_dcn30_setup_windows; } @@ -535,11 +536,10 @@ enum dmub_status dmub_srv_wait_for_auto_load(struct dmub_srv *dmub, if (!dmub->hw_init) return DMUB_STATUS_INVALID; - if (!dmub->hw_funcs.is_auto_load_done) - return DMUB_STATUS_OK; - for (i = 0; i <= timeout_us; i += 100) { - if (dmub->hw_funcs.is_auto_load_done(dmub)) + union dmub_fw_boot_status status = dmub->hw_funcs.get_fw_status(dmub); + + if (status.bits.dal_fw && status.bits.mailbox_rdy) return DMUB_STATUS_OK; udelay(100); @@ -634,3 +634,17 @@ enum dmub_status dmub_srv_get_gpint_response(struct dmub_srv *dmub, return DMUB_STATUS_OK; } + +enum dmub_status dmub_srv_get_fw_boot_status(struct dmub_srv *dmub, + union dmub_fw_boot_status *status) +{ + status->all = 0; + + if (!dmub->sw_init) + return DMUB_STATUS_INVALID; + + if (dmub->hw_funcs.get_fw_status) + *status = dmub->hw_funcs.get_fw_status(dmub); + + return DMUB_STATUS_OK; +} -- cgit v1.2.3 From 58cae8ac6b87c11917e58f3f4bbe4cd1c6d86352 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Mon, 2 Nov 2020 14:22:57 -0500 Subject: drm/amd/display: Program dpp dto based on actual dpp clk [Why] dpp dto phase and modulo are programmed with actual dpp global clk and pipe clk. Need to use actual dpp clk to prgoram dpp dto modulo to get more accuracy ratio. [How] assign actual dpp clk to dccg for dpp modulo programming. Signed-off-by: Yongqiang Sun Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c | 29 +++++++++++++++++++--- 1 file changed, 26 insertions(+), 3 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index ec394e3d8367..9e3d8af3895f 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -103,6 +103,30 @@ void rn_set_low_power_state(struct clk_mgr *clk_mgr_base) clk_mgr_base->clks.pwr_state = DCN_PWR_STATE_LOW_POWER; } +static void rn_update_clocks_update_dpp_dto(struct clk_mgr_internal *clk_mgr, + struct dc_state *context, bool safe_to_lower) +{ + int i; + + clk_mgr->dccg->ref_dppclk = clk_mgr->base.clks.actual_dppclk_khz; + for (i = 0; i < clk_mgr->base.ctx->dc->res_pool->pipe_count; i++) { + int dpp_inst, dppclk_khz, prev_dppclk_khz; + + /* Loop index will match dpp->inst if resource exists, + * and we want to avoid dependency on dpp object + */ + dpp_inst = i; + dppclk_khz = context->res_ctx.pipe_ctx[i].plane_res.bw.dppclk_khz; + + prev_dppclk_khz = clk_mgr->dccg->pipe_dppclk_khz[i]; + + if (safe_to_lower || prev_dppclk_khz < dppclk_khz) + clk_mgr->dccg->funcs->update_dpp_dto( + clk_mgr->dccg, dpp_inst, dppclk_khz); + } +} + + void rn_update_clocks(struct clk_mgr *clk_mgr_base, struct dc_state *context, bool safe_to_lower) @@ -177,7 +201,7 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, if (dpp_clock_lowered) { // increase per DPP DTO before lowering global dppclk - dcn20_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); + rn_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); clk_mgr_base->clks.actual_dppclk_khz = rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); @@ -188,7 +212,7 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); // always update dtos unless clock is lowered and not safe to lower if (new_clocks->dppclk_khz >= dc->current_state->bw_ctx.bw.dcn.clk.dppclk_khz) - dcn20_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); + rn_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); } if (update_dispclk && @@ -199,7 +223,6 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, } } - static int get_vco_frequency_from_reg(struct clk_mgr_internal *clk_mgr) { /* get FbMult value */ -- cgit v1.2.3 From b8e0b3d611e3388361d86a19f27bf2a6d7366111 Mon Sep 17 00:00:00 2001 From: Wyatt Wood Date: Wed, 21 Oct 2020 08:36:51 -0400 Subject: drm/amd/display: Hook up PSR residency command to DSAT [Why] Use GPINT command to get PSR residency from FW. [How] Hook up PSR residency command to DSAT. Since PSR Count Request is deprecated, we will use this. Signed-off-by: Wyatt Wood Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 12 ++++++++++++ drivers/gpu/drm/amd/display/dc/dc_link.h | 2 ++ drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c | 14 ++++++++++++++ drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h | 1 + 4 files changed, 29 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index ee2a51b7a2ee..858acd3df2bc 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -2783,6 +2783,18 @@ bool dc_link_setup_psr(struct dc_link *link, } +void dc_link_get_psr_residency(const struct dc_link *link, uint32_t *residency) +{ + struct dc *dc = link->ctx->dc; + struct dmub_psr *psr = dc->res_pool->psr; + + // PSR residency measurements only supported on DMCUB + if (psr != NULL && link->psr_settings.psr_feature_enabled) + psr->funcs->psr_get_residency(psr, residency); + else + *residency = 0; +} + const struct dc_link_status *dc_link_get_status(const struct dc_link *link) { return &link->link_status; diff --git a/drivers/gpu/drm/amd/display/dc/dc_link.h b/drivers/gpu/drm/amd/display/dc/dc_link.h index 39277aaa3e62..65b083e64131 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_link.h +++ b/drivers/gpu/drm/amd/display/dc/dc_link.h @@ -228,6 +228,8 @@ bool dc_link_setup_psr(struct dc_link *dc_link, const struct dc_stream_state *stream, struct psr_config *psr_config, struct psr_context *psr_context); +void dc_link_get_psr_residency(const struct dc_link *link, uint32_t *residency); + /* Request DC to detect if there is a Panel connected. * boot - If this call is during initial boot. * Return false for any type of detection failure or MST detection diff --git a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c index df3879c713c5..0d6fe7c29c20 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c @@ -293,12 +293,26 @@ static void dmub_psr_force_static(struct dmub_psr *dmub) dc_dmub_srv_wait_idle(dc->dmub_srv); } +/** + * Get PSR residency from firmware. + */ +static void dmub_psr_get_residency(struct dmub_psr *dmub, uint32_t *residency) +{ + struct dmub_srv *srv = dmub->ctx->dmub_srv->dmub; + + // Send gpint command and wait for ack + dmub_srv_send_gpint_command(srv, DMUB_GPINT__PSR_RESIDENCY, 0, 30); + + dmub_srv_get_gpint_response(srv, residency); +} + static const struct dmub_psr_funcs psr_funcs = { .psr_copy_settings = dmub_psr_copy_settings, .psr_enable = dmub_psr_enable, .psr_get_state = dmub_psr_get_state, .psr_set_level = dmub_psr_set_level, .psr_force_static = dmub_psr_force_static, + .psr_get_residency = dmub_psr_get_residency, }; /** diff --git a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h index 4e113ac5a56b..fe747c20a0d2 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h +++ b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.h @@ -40,6 +40,7 @@ struct dmub_psr_funcs { void (*psr_get_state)(struct dmub_psr *dmub, enum dc_psr_state *dc_psr_state); void (*psr_set_level)(struct dmub_psr *dmub, uint16_t psr_level); void (*psr_force_static)(struct dmub_psr *dmub); + void (*psr_get_residency)(struct dmub_psr *dmub, uint32_t *residency); }; struct dmub_psr *dmub_psr_create(struct dc_context *ctx); -- cgit v1.2.3 From 82df77ae4639af747adb223fb4678e3493e4a8b8 Mon Sep 17 00:00:00 2001 From: Sung Lee Date: Fri, 30 Oct 2020 19:31:51 -0400 Subject: drm/amd/display: Populate hostvm parameter before DML calculation [Why] If the system does not have hostvm enabled, disabling it for DML validation will allow more modes to pass at lower voltage levels. [How] When initializing HostVM save state to hubbub and read back when populating DML pipes from context. Signed-off-by: Sung Lee Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hubbub.c | 2 ++ drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c | 2 +- drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h | 1 + 3 files changed, 4 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hubbub.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hubbub.c index 129f0b62f751..42fbb5e6d505 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hubbub.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hubbub.c @@ -99,6 +99,8 @@ void dcn21_dchvm_init(struct hubbub *hubbub) //Poll until HOSTVM_PREFETCH_DONE = 1 REG_WAIT(DCHVM_RIOMMU_STAT0, HOSTVM_PREFETCH_DONE, 1, 5, 100); + + hubbub->riommu_active = true; } } diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c index ed3f62535301..1c88d2edd381 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c @@ -1886,7 +1886,7 @@ static int dcn21_populate_dml_pipes_from_context( for (i = 0; i < pipe_cnt; i++) { - pipes[i].pipe.src.hostvm = 1; + pipes[i].pipe.src.hostvm = dc->res_pool->hubbub->riommu_active; pipes[i].pipe.src.gpuvm = 1; } diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h b/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h index 5425e92efcb8..d9fd28b34f2a 100644 --- a/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h +++ b/drivers/gpu/drm/amd/display/dc/inc/hw/dchubbub.h @@ -157,6 +157,7 @@ struct hubbub_funcs { struct hubbub { const struct hubbub_funcs *funcs; struct dc_context *ctx; + bool riommu_active; }; #endif -- cgit v1.2.3 From 157cc88505f11bf3aa3952223cccf174067816da Mon Sep 17 00:00:00 2001 From: Sung Lee Date: Mon, 2 Nov 2020 15:38:04 -0500 Subject: drm/amd/display: Handle Unknown Result for SMU Periodic Retraining on DCN2.1 [WHY & HOW] Currently if VBIOSSMC_Result_UnknownCmd is returned as result of smu msg there is no way to know. Put 1 in param so if 1 is returned, this unknown case is handled. Signed-off-by: Sung Lee Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c index ab2b9c61e565..11a7b583d561 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr_vbios_smu.c @@ -247,5 +247,6 @@ int rn_vbios_smu_is_periodic_retraining_disabled(struct clk_mgr_internal *clk_mg return rn_vbios_smu_send_msg_with_param( clk_mgr, VBIOSSMC_MSG_IsPeriodicRetrainingDisabled, - 0); + 1); // if PMFW doesn't support this message, assume retraining is disabled + // so we only use most optimal watermark if we know retraining is enabled. } -- cgit v1.2.3 From 89c5ca3b5e50acdb0ed69d8af2cf5a9b7e253dae Mon Sep 17 00:00:00 2001 From: Dmytro Laktyushkin Date: Thu, 27 Aug 2020 15:23:53 -0400 Subject: drm/amd/display: remove unused dml variables Signed-off-by: Dmytro Laktyushkin Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dml/display_mode_structs.h | 2 -- drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c | 2 -- drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.h | 1 - 3 files changed, 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dml/display_mode_structs.h b/drivers/gpu/drm/amd/display/dc/dml/display_mode_structs.h index 162464261205..dd0c3b1780d7 100644 --- a/drivers/gpu/drm/amd/display/dc/dml/display_mode_structs.h +++ b/drivers/gpu/drm/amd/display/dc/dml/display_mode_structs.h @@ -334,7 +334,6 @@ struct _vcs_dpi_display_pipe_dest_params_st { unsigned int vblank_end; unsigned int htotal; unsigned int vtotal; - unsigned int refresh_rate; unsigned int vfront_porch; unsigned int vactive; unsigned int hactive; @@ -345,7 +344,6 @@ struct _vcs_dpi_display_pipe_dest_params_st { unsigned char interlaced; double pixel_rate_mhz; unsigned char synchronized_vblank_all_planes; - unsigned char synchronize_timing_if_single_refresh_rate; unsigned char otg_inst; unsigned int odm_combine; unsigned char use_maximum_vstartup; diff --git a/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c b/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c index 3ae72e379402..c9fbb33f05a3 100644 --- a/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c +++ b/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.c @@ -659,10 +659,8 @@ static void fetch_pipe_params(struct display_mode_lib *mode_lib) // TODO: ODMCombineEnabled => 2 * DPPPerPlane...actually maybe not since all pipes are specified // Do we want the dscclk to automatically be halved? Guess not since the value is specified - mode_lib->vba.SynchronizeTimingsIfSingleRefreshRate = pipes[0].pipe.dest.synchronize_timing_if_single_refresh_rate; mode_lib->vba.SynchronizedVBlank = pipes[0].pipe.dest.synchronized_vblank_all_planes; for (k = 1; k < mode_lib->vba.cache_num_pipes; ++k) { - ASSERT(mode_lib->vba.SynchronizeTimingsIfSingleRefreshRate == pipes[k].pipe.dest.synchronize_timing_if_single_refresh_rate); ASSERT(mode_lib->vba.SynchronizedVBlank == pipes[k].pipe.dest.synchronized_vblank_all_planes); } diff --git a/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.h b/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.h index 4d4ed1287673..3529fedc4c52 100644 --- a/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.h +++ b/drivers/gpu/drm/amd/display/dc/dml/display_mode_vba.h @@ -921,7 +921,6 @@ struct vba_vars_st { bool UseMinimumRequiredDCFCLK; bool ClampMinDCFCLK; bool AllowDramClockChangeOneDisplayVactive; - bool SynchronizeTimingsIfSingleRefreshRate; }; -- cgit v1.2.3 From aceeeea38a869845675e1a001e5915b5aaa5527a Mon Sep 17 00:00:00 2001 From: Samson Tam Date: Fri, 30 Oct 2020 12:30:09 -0400 Subject: drm/amd/display: fix cursor calculation for 1xnY rotated display groups [Why] Cursor is missing on displays 2 and up when doing rotated display groups in 1xnY setup. Calculation puts cursor out of bounds so it is not enabled. [How] In dcn10_set_cursor_position(), add in viewport.y into cursor calculations for 1xnY rotated display groups. For pipe split, check viewport.y for both pipes and use lower one to normalize cursor position before calculations. Add odm 2:1 support ( using same calculations as pipe split ). Signed-off-by: Samson Tam Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c | 64 ++++++++++++++++++++-- 1 file changed, 58 insertions(+), 6 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c index 8eb88a50af51..1e18f0bb40b6 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c @@ -3279,6 +3279,8 @@ void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx) }; bool pipe_split_on = (pipe_ctx->top_pipe != NULL) || (pipe_ctx->bottom_pipe != NULL); + bool odm_combine_on = (pipe_ctx->next_odm_pipe != NULL) || + (pipe_ctx->prev_odm_pipe != NULL); int x_plane = pipe_ctx->plane_state->dst_rect.x; int y_plane = pipe_ctx->plane_state->dst_rect.y; @@ -3362,16 +3364,56 @@ void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx) uint32_t temp_y = pos_cpy.y; int viewport_height = pipe_ctx->plane_res.scl_data.viewport.height; - - if (pipe_split_on) { + int viewport_y = + pipe_ctx->plane_res.scl_data.viewport.y; + + /** + * Display groups that are 1xnY, have pos_cpy.x > 2 * viewport.height + * For pipe split cases: + * - apply offset of viewport.y to normalize pos_cpy.x + * - calculate the pos_cpy.y as before + * - shift pos_cpy.y back by same offset to get final value + * - since we iterate through both pipes, use the lower + * viewport.y for offset + * For non pipe split cases, use the same calculation for + * pos_cpy.y as the 180 degree rotation case below, + * but use pos_cpy.x as our input because we are rotating + * 270 degrees + */ + if (pipe_split_on || odm_combine_on) { + int pos_cpy_x_offset; + int other_pipe_viewport_y; + + if (pipe_split_on) { + if (pipe_ctx->bottom_pipe) { + other_pipe_viewport_y = + pipe_ctx->bottom_pipe->plane_res.scl_data.viewport.y; + } else { + other_pipe_viewport_y = + pipe_ctx->top_pipe->plane_res.scl_data.viewport.y; + } + } else { + if (pipe_ctx->next_odm_pipe) { + other_pipe_viewport_y = + pipe_ctx->next_odm_pipe->plane_res.scl_data.viewport.y; + } else { + other_pipe_viewport_y = + pipe_ctx->prev_odm_pipe->plane_res.scl_data.viewport.y; + } + } + pos_cpy_x_offset = (viewport_y > other_pipe_viewport_y) ? + other_pipe_viewport_y : viewport_y; + pos_cpy.x -= pos_cpy_x_offset; if (pos_cpy.x > viewport_height) { pos_cpy.x = pos_cpy.x - viewport_height; pos_cpy.y = viewport_height - pos_cpy.x; } else { pos_cpy.y = 2 * viewport_height - pos_cpy.x; } - } else - pos_cpy.y = viewport_height - pos_cpy.x; + pos_cpy.y += pos_cpy_x_offset; + } else { + pos_cpy.y = (2 * viewport_y) + viewport_height - pos_cpy.x; + } pos_cpy.x = temp_y; } // Mirror horizontally and vertically @@ -3381,7 +3423,7 @@ void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx) int viewport_x = pipe_ctx->plane_res.scl_data.viewport.x; - if (pipe_split_on) { + if (pipe_split_on || odm_combine_on) { if (pos_cpy.x >= viewport_width + viewport_x) { pos_cpy.x = 2 * viewport_width - pos_cpy.x + 2 * viewport_x; @@ -3399,7 +3441,17 @@ void dcn10_set_cursor_position(struct pipe_ctx *pipe_ctx) } else { pos_cpy.x = viewport_width - pos_cpy.x + 2 * viewport_x; } - pos_cpy.y = pipe_ctx->plane_res.scl_data.viewport.height - pos_cpy.y; + + /** + * Display groups that are 1xnY, have pos_cpy.y > viewport.height + * Calculation: + * delta_from_bottom = viewport.y + viewport.height - pos_cpy.y + * pos_cpy.y_new = viewport.y + delta_from_bottom + * Simplify it as: + * pos_cpy.y = viewport.y * 2 + viewport.height - pos_cpy.y + */ + pos_cpy.y = (2 * pipe_ctx->plane_res.scl_data.viewport.y) + + pipe_ctx->plane_res.scl_data.viewport.height - pos_cpy.y; } hubp->funcs->set_cursor_position(hubp, &pos_cpy, ¶m); -- cgit v1.2.3 From 786b4061742be1b494f1ca046c385717e6aa4434 Mon Sep 17 00:00:00 2001 From: Wenjing Liu Date: Tue, 6 Oct 2020 16:22:40 -0400 Subject: drm/amd/display: minor restructuring of pbn calculation functions Signed-off-by: Wenjing Liu Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index 858acd3df2bc..165fd2f3c80b 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -2818,15 +2818,12 @@ static struct fixed31_32 get_pbn_per_slot(struct dc_stream_state *stream) return dc_fixpt_div_int(mbytes_per_sec, 54); } -static struct fixed31_32 get_pbn_from_timing(struct pipe_ctx *pipe_ctx) +static struct fixed31_32 get_pbn_from_bw_in_kbps(uint64_t kbps) { - uint64_t kbps; struct fixed31_32 peak_kbps; uint32_t numerator; uint32_t denominator; - kbps = dc_bandwidth_in_kbps_from_timing(&pipe_ctx->stream->timing); - /* * margin 5300ppm + 300ppm ~ 0.6% as per spec, factor is 1.006 * The unit of 54/64Mbytes/sec is an arbitrary unit chosen based on @@ -2846,6 +2843,14 @@ static struct fixed31_32 get_pbn_from_timing(struct pipe_ctx *pipe_ctx) return peak_kbps; } +static struct fixed31_32 get_pbn_from_timing(struct pipe_ctx *pipe_ctx) +{ + uint64_t kbps; + + kbps = dc_bandwidth_in_kbps_from_timing(&pipe_ctx->stream->timing); + return get_pbn_from_bw_in_kbps(kbps); +} + static void update_mst_stream_alloc_table( struct dc_link *link, struct stream_encoder *stream_enc, @@ -2873,6 +2878,7 @@ static void update_mst_stream_alloc_table( proposed_table->stream_allocations[i].vcp_id) { work_table[i] = *dc_alloc; + work_table[i].slot_count = proposed_table->stream_allocations[i].slot_count; break; /* exit j loop */ } } -- cgit v1.2.3 From 65e870dfa6741e0c1199946faa4a1113bfb23916 Mon Sep 17 00:00:00 2001 From: Roy Chan Date: Fri, 30 Oct 2020 18:00:02 -0400 Subject: drm/amd/display: Detect dynamic backlight support in eDP sink [Why] Check if the eDP sink supports the dynamic backlight control [How] Query the dynamic backlight capability in DPCD (eDP case only) Signed-off-by: Roy Chan Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | 7 +++++++ drivers/gpu/drm/amd/display/dc/dc.h | 1 + 2 files changed, 8 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c index f2023d2b5323..1dfcaf1acbfc 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c @@ -3745,6 +3745,7 @@ void detect_edp_sink_caps(struct dc_link *link) uint32_t entry; uint32_t link_rate_in_khz; enum dc_link_rate link_rate = LINK_RATE_UNKNOWN; + uint8_t backlight_adj_cap; retrieve_link_cap(link); link->dpcd_caps.edp_supported_link_rates_count = 0; @@ -3775,6 +3776,12 @@ void detect_edp_sink_caps(struct dc_link *link) } link->verified_link_cap = link->reported_link_cap; + core_link_read_dpcd(link, DP_EDP_BACKLIGHT_ADJUSTMENT_CAP, + &backlight_adj_cap, sizeof(backlight_adj_cap)); + + link->dpcd_caps.dynamic_backlight_capable_edp = + (backlight_adj_cap & DP_EDP_DYNAMIC_BACKLIGHT_CAP) ? true:false; + dc_link_set_default_brightness_aux(link); } diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 4c57cf099b5e..52e819678ecd 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -1091,6 +1091,7 @@ struct dpcd_caps { bool panel_mode_edp; bool dpcd_display_control_capable; bool ext_receiver_cap_field_present; + bool dynamic_backlight_capable_edp; union dpcd_fec_capability fec_cap; struct dpcd_dsc_capabilities dsc_caps; struct dc_lttpr_caps lttpr_caps; -- cgit v1.2.3 From af435e3f62525cace7d9b2a7bbfe28aee59eb1a7 Mon Sep 17 00:00:00 2001 From: Jacky Liao Date: Tue, 27 Oct 2020 10:56:18 -0400 Subject: drm/amd/display: Add I2C memory low power support [Why] The I2C memory blocks should be powered down when they are not in use. This will reduce power consumption. [How] 1. Write to I2C_LIGHT_SLEEP_FORCE to put memory in light sleep when released 2. Added a debug option to allow this behaviour to be turned off Signed-off-by: Jacky Liao Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 1 + drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.c | 12 ++++++++++++ drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.h | 16 ++++++++++++++++ drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c | 6 +++--- 4 files changed, 32 insertions(+), 3 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 52e819678ecd..e282c2211f42 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -419,6 +419,7 @@ struct dc_bw_validation_profile { union mem_low_power_enable_options { struct { + bool i2c: 1; bool mpc: 1; bool optc: 1; } bits; diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.c b/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.c index 3e34afe8c504..7fbd92fbc63a 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.c @@ -293,6 +293,14 @@ static bool setup_engine( { uint32_t i2c_setup_limit = I2C_SETUP_TIME_LIMIT_DCE; uint32_t reset_length = 0; + + if (dce_i2c_hw->ctx->dc->debug.enable_mem_low_power.bits.i2c) { + if (dce_i2c_hw->regs->DIO_MEM_PWR_CTRL) { + REG_UPDATE(DIO_MEM_PWR_CTRL, I2C_LIGHT_SLEEP_FORCE, 0); + REG_WAIT(DIO_MEM_PWR_STATUS, I2C_MEM_PWR_STATE, 0, 0, 5); + } + } + /* we have checked I2c not used by DMCU, set SW use I2C REQ to 1 to indicate SW using it*/ REG_UPDATE(DC_I2C_ARBITRATION, DC_I2C_SW_USE_I2C_REG_REQ, 1); @@ -369,6 +377,10 @@ static void release_engine( REG_UPDATE_2(DC_I2C_ARBITRATION, DC_I2C_SW_DONE_USING_I2C_REG, 1, DC_I2C_SW_USE_I2C_REG_REQ, 0); + if (dce_i2c_hw->ctx->dc->debug.enable_mem_low_power.bits.i2c) { + if (dce_i2c_hw->regs->DIO_MEM_PWR_CTRL) + REG_UPDATE(DIO_MEM_PWR_CTRL, I2C_LIGHT_SLEEP_FORCE, 1); + } } struct dce_i2c_hw *acquire_i2c_hw_engine( diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.h b/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.h index fb055e6883c0..2309f2bb162c 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.h +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_i2c_hw.h @@ -95,6 +95,11 @@ enum { SR(DC_I2C_DATA),\ SR(MICROSECOND_TIME_BASE_DIV) +#define I2C_HW_ENGINE_COMMON_REG_LIST_DCN30(id)\ + I2C_HW_ENGINE_COMMON_REG_LIST(id),\ + SR(DIO_MEM_PWR_CTRL),\ + SR(DIO_MEM_PWR_STATUS) + #define I2C_SF(reg_name, field_name, post_fix)\ .field_name = reg_name ## __ ## field_name ## post_fix @@ -179,6 +184,8 @@ struct dce_i2c_shift { uint8_t XTAL_REF_DIV; uint8_t DC_I2C_DDC1_SEND_RESET_LENGTH; uint8_t DC_I2C_REG_RW_CNTL_STATUS; + uint8_t I2C_LIGHT_SLEEP_FORCE; + uint8_t I2C_MEM_PWR_STATE; }; struct dce_i2c_mask { @@ -220,12 +227,19 @@ struct dce_i2c_mask { uint32_t XTAL_REF_DIV; uint32_t DC_I2C_DDC1_SEND_RESET_LENGTH; uint32_t DC_I2C_REG_RW_CNTL_STATUS; + uint32_t I2C_LIGHT_SLEEP_FORCE; + uint32_t I2C_MEM_PWR_STATE; }; #define I2C_COMMON_MASK_SH_LIST_DCN2(mask_sh)\ I2C_COMMON_MASK_SH_LIST_DCE110(mask_sh),\ I2C_SF(DC_I2C_DDC1_SETUP, DC_I2C_DDC1_SEND_RESET_LENGTH, mask_sh) +#define I2C_COMMON_MASK_SH_LIST_DCN30(mask_sh)\ + I2C_COMMON_MASK_SH_LIST_DCN2(mask_sh),\ + I2C_SF(DIO_MEM_PWR_CTRL, I2C_LIGHT_SLEEP_FORCE, mask_sh),\ + I2C_SF(DIO_MEM_PWR_STATUS, I2C_MEM_PWR_STATE, mask_sh) + struct dce_i2c_registers { uint32_t SETUP; uint32_t SPEED; @@ -239,6 +253,8 @@ struct dce_i2c_registers { uint32_t DC_I2C_TRANSACTION3; uint32_t DC_I2C_DATA; uint32_t MICROSECOND_TIME_BASE_DIV; + uint32_t DIO_MEM_PWR_CTRL; + uint32_t DIO_MEM_PWR_STATUS; }; enum dce_i2c_transaction_address_space { diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c index d5c81ad55045..5e126fdf6ec1 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c @@ -933,7 +933,7 @@ static struct dce_aux *dcn30_aux_engine_create( return &aux_engine->base; } -#define i2c_inst_regs(id) { I2C_HW_ENGINE_COMMON_REG_LIST(id) } +#define i2c_inst_regs(id) { I2C_HW_ENGINE_COMMON_REG_LIST_DCN30(id) } static const struct dce_i2c_registers i2c_hw_regs[] = { i2c_inst_regs(1), @@ -945,11 +945,11 @@ static const struct dce_i2c_registers i2c_hw_regs[] = { }; static const struct dce_i2c_shift i2c_shifts = { - I2C_COMMON_MASK_SH_LIST_DCN2(__SHIFT) + I2C_COMMON_MASK_SH_LIST_DCN30(__SHIFT) }; static const struct dce_i2c_mask i2c_masks = { - I2C_COMMON_MASK_SH_LIST_DCN2(_MASK) + I2C_COMMON_MASK_SH_LIST_DCN30(_MASK) }; static struct dce_i2c_hw *dcn30_i2c_hw_create( -- cgit v1.2.3 From e26c9d80b830812b0fd4dc02cb9a6ac21ddc3bb0 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Wed, 4 Nov 2020 16:35:35 -0500 Subject: drm/amd/display: set dpp dto as per requested clk for lower case. [Why] Blue screen when PNP with multiple monitor or hotplug external monitor when playing video due to dpp dto isn't programmed properly. If lower dpp clock, dpp dto need to be programmed first, and actual dpp clk not avalable yet. [How] set dpp dto as per request clk for lower case before dpp clk update, and after dpp clk updated set dpp dto again with actual dpp clk. Signed-off-by: Yongqiang Sun Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c | 28 ++++++++++++++++++---- 1 file changed, 23 insertions(+), 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index 9e3d8af3895f..8d8ee4b9fee1 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -104,11 +104,12 @@ void rn_set_low_power_state(struct clk_mgr *clk_mgr_base) } static void rn_update_clocks_update_dpp_dto(struct clk_mgr_internal *clk_mgr, - struct dc_state *context, bool safe_to_lower) + struct dc_state *context, int ref_dpp_clk, bool safe_to_lower) { int i; - clk_mgr->dccg->ref_dppclk = clk_mgr->base.clks.actual_dppclk_khz; + clk_mgr->dccg->ref_dppclk = ref_dpp_clk; + for (i = 0; i < clk_mgr->base.ctx->dc->res_pool->pipe_count; i++) { int dpp_inst, dppclk_khz, prev_dppclk_khz; @@ -200,19 +201,36 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, } if (dpp_clock_lowered) { - // increase per DPP DTO before lowering global dppclk - rn_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); + // increase per DPP DTO before lowering global dppclk with requested dppclk + rn_update_clocks_update_dpp_dto( + clk_mgr, + context, + clk_mgr_base->clks.dppclk_khz, + safe_to_lower); + clk_mgr_base->clks.actual_dppclk_khz = rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); + //update dpp dto with actual dpp clk. + rn_update_clocks_update_dpp_dto( + clk_mgr, + context, + clk_mgr_base->clks.actual_dppclk_khz, + safe_to_lower); + } else { // increase global DPPCLK before lowering per DPP DTO if (update_dppclk || update_dispclk) clk_mgr_base->clks.actual_dppclk_khz = rn_vbios_smu_set_dppclk(clk_mgr, clk_mgr_base->clks.dppclk_khz); + // always update dtos unless clock is lowered and not safe to lower if (new_clocks->dppclk_khz >= dc->current_state->bw_ctx.bw.dcn.clk.dppclk_khz) - rn_update_clocks_update_dpp_dto(clk_mgr, context, safe_to_lower); + rn_update_clocks_update_dpp_dto( + clk_mgr, + context, + clk_mgr_base->clks.actual_dppclk_khz, + safe_to_lower); } if (update_dispclk && -- cgit v1.2.3 From 175f097149177ec97d8dd4fb5de673e99516be09 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Wed, 4 Nov 2020 14:26:38 -0500 Subject: drm/amd/display: Add dual edp optimization flag. [Why & How] Add a dual edp power optimization flag, so driver will notify this flag to dmub FW to determine if apply the power optimization. Signed-off-by: Yongqiang Sun Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 1 + drivers/gpu/drm/amd/display/dc/dc_types.h | 2 ++ drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c | 1 + drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h | 3 ++- 4 files changed, 6 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index 165fd2f3c80b..f522b664d3c6 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -2757,6 +2757,7 @@ bool dc_link_setup_psr(struct dc_link *link, * (Always set for DAL2, did not check ASIC) */ psr_context->allow_smu_optimizations = psr_config->allow_smu_optimizations; + psr_context->allow_multi_disp_optimizations = psr_config->allow_multi_disp_optimizations; /* Complete PSR entry before aborting to prevent intermittent * freezes on certain eDPs diff --git a/drivers/gpu/drm/amd/display/dc/dc_types.h b/drivers/gpu/drm/amd/display/dc/dc_types.h index 86406b42572c..80757a0ea7c6 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_types.h +++ b/drivers/gpu/drm/amd/display/dc/dc_types.h @@ -697,6 +697,7 @@ struct psr_config { bool psr_frame_capture_indication_req; unsigned int psr_sdp_transmit_line_num_deadline; bool allow_smu_optimizations; + bool allow_multi_disp_optimizations; }; union dmcu_psr_level { @@ -799,6 +800,7 @@ struct psr_context { */ unsigned int frame_delay; bool allow_smu_optimizations; + bool allow_multi_disp_optimizations; }; struct colorspace_transform { diff --git a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c index 0d6fe7c29c20..17e84f34ceba 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dmub_psr.c @@ -261,6 +261,7 @@ static bool dmub_psr_copy_settings(struct dmub_psr *dmub, // Misc copy_settings_data->psr_level = psr_context->psr_level.u32all; copy_settings_data->smu_optimizations_en = psr_context->allow_smu_optimizations; + copy_settings_data->multi_disp_optimizations_en = psr_context->allow_multi_disp_optimizations; copy_settings_data->frame_delay = psr_context->frame_delay; copy_settings_data->frame_cap_ind = psr_context->psrFrameCaptureIndicationReq; copy_settings_data->init_sdp_deadline = psr_context->sdpTransmitLineNumDeadline; diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h index 9fd24f93a216..a980862f2543 100644 --- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h +++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h @@ -613,7 +613,8 @@ struct dmub_cmd_psr_copy_settings_data { uint8_t smu_optimizations_en; uint8_t frame_delay; uint8_t frame_cap_ind; - uint8_t pad[3]; + uint8_t pad[2]; + uint8_t multi_disp_optimizations_en; uint16_t init_sdp_deadline; uint16_t pad2; }; -- cgit v1.2.3 From c88840f342c985433ff9286dbb3083fdce85170f Mon Sep 17 00:00:00 2001 From: Anthony Koo Date: Sun, 8 Nov 2020 13:08:18 -0500 Subject: drm/amd/display: [FW Promotion] Release 0.0.42 Signed-off-by: Anthony Koo Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h index a980862f2543..a8d93366fa03 100644 --- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h +++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h @@ -36,10 +36,10 @@ /* Firmware versioning. */ #ifdef DMUB_EXPOSE_VERSION -#define DMUB_FW_VERSION_GIT_HASH 0x821097815 +#define DMUB_FW_VERSION_GIT_HASH 0x52d68b82f #define DMUB_FW_VERSION_MAJOR 0 #define DMUB_FW_VERSION_MINOR 0 -#define DMUB_FW_VERSION_REVISION 41 +#define DMUB_FW_VERSION_REVISION 42 #define DMUB_FW_VERSION_TEST 0 #define DMUB_FW_VERSION_VBIOS 0 #define DMUB_FW_VERSION_HOTFIX 0 -- cgit v1.2.3 From c920888c604d72799d057bbcd9e28a6c003ccfbe Mon Sep 17 00:00:00 2001 From: Wayne Lin Date: Mon, 19 Oct 2020 16:32:14 +0800 Subject: drm/amd/display: Expose new CRC window property [Why] Instead of calculating CRC on whole frame, add flexibility to calculate CRC on specific frame region. [How] Add few crc window coordinate properties. By default, CRC is calculated on whole frame unless user space specifies the CRC calculation window. Signed-off-by: Wayne Lin Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 142 +++++++++++++++++++-- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h | 19 +++ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c | 43 ++++++- .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.h | 3 + drivers/gpu/drm/amd/display/dc/core/dc_link.c | 3 + 5 files changed, 201 insertions(+), 9 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 7f38a7cba76c..9c7340cdc986 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -943,6 +943,41 @@ static void mmhub_read_system_context(struct amdgpu_device *adev, struct dc_phy_ } #endif +#ifdef CONFIG_DEBUG_FS +static int create_crtc_crc_properties(struct amdgpu_display_manager *dm) +{ + dm->crc_win_x_start_property = + drm_property_create_range(adev_to_drm(dm->adev), + DRM_MODE_PROP_ATOMIC, + "AMD_CRC_WIN_X_START", 0, U16_MAX); + if (!dm->crc_win_x_start_property) + return -ENOMEM; + + dm->crc_win_y_start_property = + drm_property_create_range(adev_to_drm(dm->adev), + DRM_MODE_PROP_ATOMIC, + "AMD_CRC_WIN_Y_START", 0, U16_MAX); + if (!dm->crc_win_y_start_property) + return -ENOMEM; + + dm->crc_win_x_end_property = + drm_property_create_range(adev_to_drm(dm->adev), + DRM_MODE_PROP_ATOMIC, + "AMD_CRC_WIN_X_END", 0, U16_MAX); + if (!dm->crc_win_x_end_property) + return -ENOMEM; + + dm->crc_win_y_end_property = + drm_property_create_range(adev_to_drm(dm->adev), + DRM_MODE_PROP_ATOMIC, + "AMD_CRC_WIN_Y_END", 0, U16_MAX); + if (!dm->crc_win_y_end_property) + return -ENOMEM; + + return 0; +} +#endif + static int amdgpu_dm_init(struct amdgpu_device *adev) { struct dc_init_data init_data; @@ -1084,6 +1119,10 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) dc_init_callbacks(adev->dm.dc, &init_params); } +#endif +#ifdef CONFIG_DEBUG_FS + if (create_crtc_crc_properties(&adev->dm)) + DRM_ERROR("amdgpu: failed to create crc property.\n"); #endif if (amdgpu_dm_initialize_drm_device(adev)) { DRM_ERROR( @@ -5250,12 +5289,64 @@ dm_crtc_duplicate_state(struct drm_crtc *crtc) state->crc_src = cur->crc_src; state->cm_has_degamma = cur->cm_has_degamma; state->cm_is_degamma_srgb = cur->cm_is_degamma_srgb; - +#ifdef CONFIG_DEBUG_FS + state->crc_window = cur->crc_window; +#endif /* TODO Duplicate dc_stream after objects are stream object is flattened */ return &state->base; } +#ifdef CONFIG_DEBUG_FS +int amdgpu_dm_crtc_atomic_set_property(struct drm_crtc *crtc, + struct drm_crtc_state *crtc_state, + struct drm_property *property, + uint64_t val) +{ + struct drm_device *dev = crtc->dev; + struct amdgpu_device *adev = drm_to_adev(dev); + struct dm_crtc_state *dm_new_state = + to_dm_crtc_state(crtc_state); + + if (property == adev->dm.crc_win_x_start_property) + dm_new_state->crc_window.x_start = val; + else if (property == adev->dm.crc_win_y_start_property) + dm_new_state->crc_window.y_start = val; + else if (property == adev->dm.crc_win_x_end_property) + dm_new_state->crc_window.x_end = val; + else if (property == adev->dm.crc_win_y_end_property) + dm_new_state->crc_window.y_end = val; + else + return -EINVAL; + + return 0; +} + +int amdgpu_dm_crtc_atomic_get_property(struct drm_crtc *crtc, + const struct drm_crtc_state *state, + struct drm_property *property, + uint64_t *val) +{ + struct drm_device *dev = crtc->dev; + struct amdgpu_device *adev = drm_to_adev(dev); + struct dm_crtc_state *dm_state = + to_dm_crtc_state(state); + + if (property == adev->dm.crc_win_x_start_property) + *val = dm_state->crc_window.x_start; + else if (property == adev->dm.crc_win_y_start_property) + *val = dm_state->crc_window.y_start; + else if (property == adev->dm.crc_win_x_end_property) + *val = dm_state->crc_window.x_end; + else if (property == adev->dm.crc_win_y_end_property) + *val = dm_state->crc_window.y_end; + else + return -EINVAL; + + return 0; +} +#endif + static inline int dm_set_vupdate_irq(struct drm_crtc *crtc, bool enable) { enum dc_irq_source irq_source; @@ -5322,6 +5413,10 @@ static const struct drm_crtc_funcs amdgpu_dm_crtc_funcs = { .enable_vblank = dm_enable_vblank, .disable_vblank = dm_disable_vblank, .get_vblank_timestamp = drm_crtc_vblank_helper_get_vblank_timestamp, +#ifdef CONFIG_DEBUG_FS + .atomic_set_property = amdgpu_dm_crtc_atomic_set_property, + .atomic_get_property = amdgpu_dm_crtc_atomic_get_property, +#endif }; static enum drm_connector_status @@ -6519,6 +6614,25 @@ static int amdgpu_dm_plane_init(struct amdgpu_display_manager *dm, return 0; } +#ifdef CONFIG_DEBUG_FS +static void attach_crtc_crc_properties(struct amdgpu_display_manager *dm, + struct amdgpu_crtc *acrtc) +{ + drm_object_attach_property(&acrtc->base.base, + dm->crc_win_x_start_property, + 0); + drm_object_attach_property(&acrtc->base.base, + dm->crc_win_y_start_property, + 0); + drm_object_attach_property(&acrtc->base.base, + dm->crc_win_x_end_property, + 0); + drm_object_attach_property(&acrtc->base.base, + dm->crc_win_y_end_property, + 0); +} +#endif + static int amdgpu_dm_crtc_init(struct amdgpu_display_manager *dm, struct drm_plane *plane, uint32_t crtc_index) @@ -6566,7 +6680,9 @@ static int amdgpu_dm_crtc_init(struct amdgpu_display_manager *dm, drm_crtc_enable_color_mgmt(&acrtc->base, MAX_COLOR_LUT_ENTRIES, true, MAX_COLOR_LUT_ENTRIES); drm_mode_crtc_set_gamma_size(&acrtc->base, MAX_COLOR_LEGACY_LUT_ENTRIES); - +#ifdef CONFIG_DEBUG_FS + attach_crtc_crc_properties(dm, acrtc); +#endif return 0; fail: @@ -8190,6 +8306,7 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) */ for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { struct amdgpu_crtc *acrtc = to_amdgpu_crtc(crtc); + bool configure_crc = false; dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); @@ -8199,21 +8316,30 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) dc_stream_retain(dm_new_crtc_state->stream); acrtc->dm_irq_params.stream = dm_new_crtc_state->stream; manage_dm_interrupts(adev, acrtc, true); - + } #ifdef CONFIG_DEBUG_FS + if (new_crtc_state->active && + amdgpu_dm_is_valid_crc_source(dm_new_crtc_state->crc_src)) { /** * Frontend may have changed so reapply the CRC capture * settings for the stream. */ dm_new_crtc_state = to_dm_crtc_state(new_crtc_state); + dm_old_crtc_state = to_dm_crtc_state(old_crtc_state); - if (amdgpu_dm_is_valid_crc_source(dm_new_crtc_state->crc_src)) { - amdgpu_dm_crtc_configure_crc_source( - crtc, dm_new_crtc_state, - dm_new_crtc_state->crc_src); + if (amdgpu_dm_crc_window_is_default(dm_new_crtc_state)) { + if (!old_crtc_state->active || drm_atomic_crtc_needs_modeset(new_crtc_state)) + configure_crc = true; + } else { + if (amdgpu_dm_crc_window_changed(dm_new_crtc_state, dm_old_crtc_state)) + configure_crc = true; } -#endif + + if (configure_crc) + amdgpu_dm_crtc_configure_crc_source( + crtc, dm_new_crtc_state, dm_new_crtc_state->crc_src); } +#endif } for_each_new_crtc_in_state(state, crtc, new_crtc_state, j) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h index 7798eb018257..9ba21f6a9842 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h @@ -336,6 +336,13 @@ struct amdgpu_display_manager { */ const struct gpu_info_soc_bounding_box_v1_0 *soc_bounding_box; +#ifdef CONFIG_DEBUG_FS + /* set the crc calculation window*/ + struct drm_property *crc_win_x_start_property; + struct drm_property *crc_win_y_start_property; + struct drm_property *crc_win_x_end_property; + struct drm_property *crc_win_y_end_property; +#endif /** * @mst_encoders: * @@ -422,6 +429,15 @@ struct dm_plane_state { struct dc_plane_state *dc_state; }; +#ifdef CONFIG_DEBUG_FS +struct crc_rec { + uint16_t x_start; + uint16_t y_start; + uint16_t x_end; + uint16_t y_end; + }; +#endif + struct dm_crtc_state { struct drm_crtc_state base; struct dc_stream_state *stream; @@ -444,6 +460,9 @@ struct dm_crtc_state { struct dc_info_packet vrr_infopacket; int abm_level; +#ifdef CONFIG_DEBUG_FS + struct crc_rec crc_window; +#endif }; #define to_dm_crtc_state(x) container_of(x, struct dm_crtc_state, base) diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c index c29dc11619f7..ff6db26626ea 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c @@ -81,6 +81,33 @@ const char *const *amdgpu_dm_crtc_get_crc_sources(struct drm_crtc *crtc, return pipe_crc_sources; } +bool amdgpu_dm_crc_window_is_default(struct dm_crtc_state *dm_crtc_state) +{ + bool ret = true; + + if ((dm_crtc_state->crc_window.x_start != 0) || + (dm_crtc_state->crc_window.y_start != 0) || + (dm_crtc_state->crc_window.x_end != 0) || + (dm_crtc_state->crc_window.y_end != 0)) + ret = false; + + return ret; +} + +bool amdgpu_dm_crc_window_changed(struct dm_crtc_state *dm_new_crtc_state, + struct dm_crtc_state *dm_old_crtc_state) +{ + bool ret = false; + + if ((dm_new_crtc_state->crc_window.x_start != dm_old_crtc_state->crc_window.x_start) || + (dm_new_crtc_state->crc_window.y_start != dm_old_crtc_state->crc_window.y_start) || + (dm_new_crtc_state->crc_window.x_end != dm_old_crtc_state->crc_window.x_end) || + (dm_new_crtc_state->crc_window.y_end != dm_old_crtc_state->crc_window.y_end)) + ret = true; + + return ret; +} + int amdgpu_dm_crtc_verify_crc_source(struct drm_crtc *crtc, const char *src_name, size_t *values_cnt) @@ -105,6 +132,7 @@ int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc, struct dc_stream_state *stream_state = dm_crtc_state->stream; bool enable = amdgpu_dm_is_valid_crc_source(source); int ret = 0; + struct crc_params *crc_window = NULL, tmp_window; /* Configuration will be deferred to stream enable. */ if (!stream_state) @@ -114,8 +142,21 @@ int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc, /* Enable CRTC CRC generation if necessary. */ if (dm_is_crc_source_crtc(source)) { + if (!amdgpu_dm_crc_window_is_default(dm_crtc_state)) { + crc_window = &tmp_window; + + tmp_window.windowa_x_start = dm_crtc_state->crc_window.x_start; + tmp_window.windowa_y_start = dm_crtc_state->crc_window.y_start; + tmp_window.windowa_x_end = dm_crtc_state->crc_window.x_end; + tmp_window.windowa_y_end = dm_crtc_state->crc_window.y_end; + tmp_window.windowb_x_start = dm_crtc_state->crc_window.x_start; + tmp_window.windowb_y_start = dm_crtc_state->crc_window.y_start; + tmp_window.windowb_x_end = dm_crtc_state->crc_window.x_end; + tmp_window.windowb_y_end = dm_crtc_state->crc_window.y_end; + } + if (!dc_stream_configure_crc(stream_state->ctx->dc, - stream_state, NULL, enable, enable)) { + stream_state, crc_window, enable, enable)) { ret = -EINVAL; goto unlock; } diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.h b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.h index f7d731797d3f..0235bfb246e5 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.h +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.h @@ -47,6 +47,9 @@ static inline bool amdgpu_dm_is_valid_crc_source(enum amdgpu_dm_pipe_crc_source /* amdgpu_dm_crc.c */ #ifdef CONFIG_DEBUG_FS +bool amdgpu_dm_crc_window_is_default(struct dm_crtc_state *dm_crtc_state); +bool amdgpu_dm_crc_window_changed(struct dm_crtc_state *dm_new_crtc_state, + struct dm_crtc_state *dm_old_crtc_state); int amdgpu_dm_crtc_configure_crc_source(struct drm_crtc *crtc, struct dm_crtc_state *dm_crtc_state, enum amdgpu_dm_pipe_crc_source source); diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index f522b664d3c6..5790affc7d61 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -3259,6 +3259,9 @@ void core_link_enable_stream( } } +#if defined(CONFIG_DRM_AMD_DC_DCN3_0) +#endif + dc->hwss.enable_audio_stream(pipe_ctx); /* turn off otg test pattern if enable */ -- cgit v1.2.3 From f1e1f272151b650528540dc41f220cb4373c5a21 Mon Sep 17 00:00:00 2001 From: Raymond Yang Date: Sat, 7 Nov 2020 04:25:45 +0800 Subject: drm/amd/display: correct data type [Why] We should use int for counting variable [How] Change type from bool to uint32_t Signed-off-by: Raymond Yang Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index e282c2211f42..96ff556e2567 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -483,7 +483,7 @@ struct dc_debug_options { bool scl_reset_length10; bool hdmi20_disable; bool skip_detection_link_training; - bool edid_read_retry_times; + uint32_t edid_read_retry_times; bool remove_disconnect_edp; unsigned int force_odm_combine; //bit vector based on otg inst #if defined(CONFIG_DRM_AMD_DC_DCN) -- cgit v1.2.3 From 9a31996081d7ee998aa789742329c3433396c90c Mon Sep 17 00:00:00 2001 From: Aric Cyr Date: Mon, 9 Nov 2020 10:50:43 -0500 Subject: drm/amd/display: 3.2.112 Signed-off-by: Aric Cyr Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 96ff556e2567..443b1f1ad546 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -42,7 +42,7 @@ #include "inc/hw/dmcu.h" #include "dml/display_mode_lib.h" -#define DC_VER "3.2.111" +#define DC_VER "3.2.112" #define MAX_SURFACES 3 #define MAX_PLANES 6 -- cgit v1.2.3 From 54e5f12ce530dd260722033ed9756fb107972a3f Mon Sep 17 00:00:00 2001 From: Wyatt Wood Date: Tue, 3 Nov 2020 15:07:33 -0500 Subject: drm/amd/display: Increase sr enter/exit in rn ddr4 watermark table [Why] After removing added latency for HostVM by default, DDR4 sr exit latencies were no longer large enough for some panels and caused underflow. [How] Add 1us to sr enter/exit watermark. Signed-off-by: Wyatt Wood Acked-by: Bindu Ramamurthy Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index 8d8ee4b9fee1..458dab9e813b 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -618,8 +618,8 @@ static struct wm_table ddr4_wm_table = { .wm_inst = WM_A, .wm_type = WM_TYPE_PSTATE_CHG, .pstate_latency_us = 11.72, - .sr_exit_time_us = 6.09, - .sr_enter_plus_exit_time_us = 7.14, + .sr_exit_time_us = 7.09, + .sr_enter_plus_exit_time_us = 8.14, .valid = true, }, { -- cgit v1.2.3 From c6ce6d1971a6dd33e7960612b774669fa0e57a5d Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Thu, 10 Sep 2020 09:01:58 -0400 Subject: drm/amd/display: update vgh bounding box [Why & How] Update bounding box as per spread sheet. Signed-off-by: Yongqiang Sun Acked-by: Roman Li Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/dcn301/dcn301_resource.c | 60 +++++++++++++++++----- 1 file changed, 47 insertions(+), 13 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index 8824dbce6f4a..0006d805b3b2 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -164,29 +164,63 @@ struct _vcs_dpi_ip_params_st dcn3_01_ip = { struct _vcs_dpi_soc_bounding_box_st dcn3_01_soc = { .clock_limits = { - /*TODO: fill out defaults once wm plociy is settled*/ { .state = 0, - .dcfclk_mhz = 810.0, - .fabricclk_mhz = 1200.0, + .dram_speed_mts = 2400.0, + .fabricclk_mhz = 600, + .socclk_mhz = 278.0, + .dcfclk_mhz = 400.0, + .dscclk_mhz = 206.0, + .dppclk_mhz = 1015.0, + .dispclk_mhz = 1015.0, + .phyclk_mhz = 600.0, + }, + { + .state = 1, + .dram_speed_mts = 2400.0, + .fabricclk_mhz = 688, + .socclk_mhz = 278.0, + .dcfclk_mhz = 400.0, + .dscclk_mhz = 206.0, + .dppclk_mhz = 1015.0, .dispclk_mhz = 1015.0, + .phyclk_mhz = 600.0, + }, + { + .state = 2, + .dram_speed_mts = 4267.0, + .fabricclk_mhz = 1067, + .socclk_mhz = 278.0, + .dcfclk_mhz = 608.0, + .dscclk_mhz = 296.0, .dppclk_mhz = 1015.0, + .dispclk_mhz = 1015.0, .phyclk_mhz = 810.0, - .socclk_mhz = 1000.0, + }, + + { + .state = 3, + .dram_speed_mts = 4267.0, + .fabricclk_mhz = 1067, + .socclk_mhz = 715.0, + .dcfclk_mhz = 676.0, .dscclk_mhz = 338.0, - .dram_speed_mts = 4266.0, + .dppclk_mhz = 1015.0, + .dispclk_mhz = 1015.0, + .phyclk_mhz = 810.0, }, + { - .state = 1, + .state = 4, + .dram_speed_mts = 4267.0, + .fabricclk_mhz = 1067, + .socclk_mhz = 953.0, .dcfclk_mhz = 810.0, - .fabricclk_mhz = 1200.0, - .dispclk_mhz = 1015.0, + .dscclk_mhz = 338.0, .dppclk_mhz = 1015.0, + .dispclk_mhz = 1015.0, .phyclk_mhz = 810.0, - .socclk_mhz = 1000.0, - .dscclk_mhz = 338.0, - .dram_speed_mts = 4266.0, - } + }, }, .sr_exit_time_us = 9.0, @@ -226,7 +260,7 @@ struct _vcs_dpi_soc_bounding_box_st dcn3_01_soc = { .xfc_bus_transport_time_us = 20, // ? .xfc_xbuf_latency_tolerance_us = 4, // ? .use_urgent_burst_bw = 1, // ? - .num_states = 2, + .num_states = 5, .do_urgent_latency_adjustment = false, .urgent_latency_adjustment_fabric_clock_component_us = 0, .urgent_latency_adjustment_fabric_clock_reference_mhz = 0, -- cgit v1.2.3 From 8976f73b676eb96d27ac1f7034fb36dd22292e21 Mon Sep 17 00:00:00 2001 From: Rodrigo Siqueira Date: Tue, 17 Nov 2020 09:33:51 -0500 Subject: drm/amd/display: Always get CRTC updated constant values inside commit tail We recently improved our display atomic commit and tail sequence to avoid some issues related to concurrency. One of the major changes consisted of moving the interrupt disable and the stream release from our atomic commit to our atomic tail (commit 6d90a208cfff ("drm/amd/display: Move disable interrupt into commit tail")) . However, the new code introduced inside our commit tail function was inserted right after the function drm_atomic_helper_update_legacy_modeset_state(), which has routines for updating internal data structs related to timestamps. As a result, in certain conditions, the display module can reach a situation where we update our constants and, after that, clean it. This situation generates the following warning: amdgpu 0000:03:00.0: drm_WARN_ON_ONCE(drm_drv_uses_atomic_modeset(dev)) WARNING: CPU: 6 PID: 1269 at drivers/gpu/drm/drm_vblank.c:722 drm_crtc_vblank_helper_get_vblank_timestamp_internal+0x32b/0x340 [drm] ... RIP: 0010:drm_crtc_vblank_helper_get_vblank_timestamp_internal+0x32b/0x340 [drm] ... Call Trace: ? dc_stream_get_vblank_counter+0x57/0x60 [amdgpu] drm_crtc_vblank_helper_get_vblank_timestamp+0x1c/0x20 [drm] drm_get_last_vbltimestamp+0xad/0xc0 [drm] drm_reset_vblank_timestamp+0x63/0xd0 [drm] drm_crtc_vblank_on+0x85/0x150 [drm] amdgpu_dm_atomic_commit_tail+0xaf1/0x2330 [amdgpu] commit_tail+0x99/0x130 [drm_kms_helper] drm_atomic_helper_commit+0x123/0x150 [drm_kms_helper] amdgpu_dm_atomic_commit+0x11/0x20 [amdgpu] drm_atomic_commit+0x4a/0x50 [drm] drm_atomic_helper_set_config+0x7c/0xc0 [drm_kms_helper] drm_mode_setcrtc+0x20b/0x7e0 [drm] ? tomoyo_path_number_perm+0x6f/0x200 ? drm_mode_getcrtc+0x190/0x190 [drm] drm_ioctl_kernel+0xae/0xf0 [drm] drm_ioctl+0x245/0x400 [drm] ? drm_mode_getcrtc+0x190/0x190 [drm] amdgpu_drm_ioctl+0x4e/0x80 [amdgpu] __x64_sys_ioctl+0x91/0xc0 do_syscall_64+0x38/0x90 entry_SYSCALL_64_after_hwframe+0x44/0xa9 ... For fixing this issue we rely upon a refactor introduced on drm_atomic_helper_update_legacy_modeset_state ("Remove the timestamping constant update from drm_atomic_helper_update_legacy_modeset_state()") which decouples constant values update from drm_atomic_helper_update_legacy_modeset_state to a new helper. Basically, this commit uses this new helper and place it right after our release module to avoid a situation where our CRTC struct gets wrong values. Bug: https://gitlab.freedesktop.org/drm/amd/-/issues/1373 Reviewed-by: Harry Wentland Signed-off-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 9c7340cdc986..3c81adac46fc 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8033,7 +8033,6 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) trace_amdgpu_dm_atomic_commit_tail_begin(state); drm_atomic_helper_update_legacy_modeset_state(dev, state); - drm_atomic_helper_calc_timestamping_constants(state); dm_state = dm_atomic_get_new_state(state); if (dm_state && dm_state->context) { @@ -8060,6 +8059,8 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) } } + drm_atomic_helper_calc_timestamping_constants(state); + /* update changed items */ for_each_oldnew_crtc_in_state(state, crtc, old_crtc_state, new_crtc_state, i) { struct amdgpu_crtc *acrtc = to_amdgpu_crtc(crtc); -- cgit v1.2.3 From 97f6c91787d9fc5c468bac398f11685179f64e8a Mon Sep 17 00:00:00 2001 From: Bhawanpreet Lakha Date: Thu, 26 Sep 2019 16:55:24 -0400 Subject: drm/amd/display: Add display only once. [Why] We call add display multiple times because DESIRED->ENABLED cannot happen instantaneously. We can't compare the new_state/old_state to avoid this because on unplug we set the state to DESIRED and on hotplug the state will still be DESIRED. [How] Add a flag to dm_connector_state to keep track of when to enable or disable HDCP Signed-off-by: Bhawanpreet Lakha Reviewed-by: Zhan Liu Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 15 +++++++++++---- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h | 3 +++ 2 files changed, 14 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 3c81adac46fc..9df92c6024c0 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -2401,6 +2401,7 @@ static void handle_hpd_irq(void *param) enum dc_connection_type new_connection_type = dc_connection_none; #ifdef CONFIG_DRM_AMD_DC_HDCP struct amdgpu_device *adev = drm_to_adev(dev); + struct dm_connector_state *dm_con_state = to_dm_connector_state(connector->state); #endif /* @@ -2410,8 +2411,10 @@ static void handle_hpd_irq(void *param) mutex_lock(&aconnector->hpd_lock); #ifdef CONFIG_DRM_AMD_DC_HDCP - if (adev->dm.hdcp_workqueue) + if (adev->dm.hdcp_workqueue) { hdcp_reset_display(adev->dm.hdcp_workqueue, aconnector->dc_link->link_index); + dm_con_state->update_hdcp = true; + } #endif if (aconnector->fake_enable) aconnector->fake_enable = false; @@ -7233,6 +7236,7 @@ static bool is_content_protection_different(struct drm_connector_state *state, const struct drm_connector *connector, struct hdcp_workqueue *hdcp_w) { struct amdgpu_dm_connector *aconnector = to_amdgpu_dm_connector(connector); + struct dm_connector_state *dm_con_state = to_dm_connector_state(connector->state); if (old_state->hdcp_content_type != state->hdcp_content_type && state->content_protection != DRM_MODE_CONTENT_PROTECTION_UNDESIRED) { @@ -7255,14 +7259,16 @@ static bool is_content_protection_different(struct drm_connector_state *state, /* Check if something is connected/enabled, otherwise we start hdcp but nothing is connected/enabled * hot-plug, headless s3, dpms */ - if (state->content_protection == DRM_MODE_CONTENT_PROTECTION_DESIRED && connector->dpms == DRM_MODE_DPMS_ON && - aconnector->dc_sink != NULL) + if (dm_con_state->update_hdcp && state->content_protection == DRM_MODE_CONTENT_PROTECTION_DESIRED && + connector->dpms == DRM_MODE_DPMS_ON && aconnector->dc_sink != NULL) { + dm_con_state->update_hdcp = false; return true; + } if (old_state->content_protection == state->content_protection) return false; - if (state->content_protection == DRM_MODE_CONTENT_PROTECTION_UNDESIRED) + if (state->content_protection != DRM_MODE_CONTENT_PROTECTION_ENABLED) return true; return false; @@ -8189,6 +8195,7 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) connector->state->content_protection == DRM_MODE_CONTENT_PROTECTION_ENABLED) { hdcp_reset_display(adev->dm.hdcp_workqueue, aconnector->dc_link->link_index); new_con_state->content_protection = DRM_MODE_CONTENT_PROTECTION_DESIRED; + dm_new_con_state->update_hdcp = true; continue; } diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h index 9ba21f6a9842..0b31779a0485 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.h @@ -483,6 +483,9 @@ struct dm_connector_state { uint8_t underscan_hborder; bool underscan_enable; bool freesync_capable; +#ifdef CONFIG_DRM_AMD_DC_HDCP + bool update_hdcp; +#endif uint8_t abm_level; int vcpi_slots; uint64_t pbn; -- cgit v1.2.3 From 31c0ed90b978f9fe99d48dc4a624ed0fe0dc21b7 Mon Sep 17 00:00:00 2001 From: Bhawanpreet Lakha Date: Thu, 26 Sep 2019 17:44:50 -0400 Subject: drm/amd/display: Add comments to hdcp property change code [Why] These comments are helpful in understanding which case each if statement handles. [How] Add comments for state transitions (9 possible cases) Signed-off-by: Bhawanpreet Lakha Reviewed-by: Zhan Liu Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 26 +++++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 9df92c6024c0..936979c52c2c 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -7238,26 +7238,35 @@ static bool is_content_protection_different(struct drm_connector_state *state, struct amdgpu_dm_connector *aconnector = to_amdgpu_dm_connector(connector); struct dm_connector_state *dm_con_state = to_dm_connector_state(connector->state); + /* Handle: Type0/1 change */ if (old_state->hdcp_content_type != state->hdcp_content_type && state->content_protection != DRM_MODE_CONTENT_PROTECTION_UNDESIRED) { state->content_protection = DRM_MODE_CONTENT_PROTECTION_DESIRED; return true; } - /* CP is being re enabled, ignore this */ + /* CP is being re enabled, ignore this + * + * Handles: ENABLED -> DESIRED + */ if (old_state->content_protection == DRM_MODE_CONTENT_PROTECTION_ENABLED && state->content_protection == DRM_MODE_CONTENT_PROTECTION_DESIRED) { state->content_protection = DRM_MODE_CONTENT_PROTECTION_ENABLED; return false; } - /* S3 resume case, since old state will always be 0 (UNDESIRED) and the restored state will be ENABLED */ + /* S3 resume case, since old state will always be 0 (UNDESIRED) and the restored state will be ENABLED + * + * Handles: UNDESIRED -> ENABLED + */ if (old_state->content_protection == DRM_MODE_CONTENT_PROTECTION_UNDESIRED && state->content_protection == DRM_MODE_CONTENT_PROTECTION_ENABLED) state->content_protection = DRM_MODE_CONTENT_PROTECTION_DESIRED; /* Check if something is connected/enabled, otherwise we start hdcp but nothing is connected/enabled * hot-plug, headless s3, dpms + * + * Handles: DESIRED -> DESIRED (Special case) */ if (dm_con_state->update_hdcp && state->content_protection == DRM_MODE_CONTENT_PROTECTION_DESIRED && connector->dpms == DRM_MODE_DPMS_ON && aconnector->dc_sink != NULL) { @@ -7265,12 +7274,25 @@ static bool is_content_protection_different(struct drm_connector_state *state, return true; } + /* + * Handles: UNDESIRED -> UNDESIRED + * DESIRED -> DESIRED + * ENABLED -> ENABLED + */ if (old_state->content_protection == state->content_protection) return false; + /* + * Handles: UNDESIRED -> DESIRED + * DESIRED -> UNDESIRED + * ENABLED -> UNDESIRED + */ if (state->content_protection != DRM_MODE_CONTENT_PROTECTION_ENABLED) return true; + /* + * Handles: DESIRED -> ENABLED + */ return false; } -- cgit v1.2.3 From 78deaf5f98acce53a805c42b6f56f15ca7958ce4 Mon Sep 17 00:00:00 2001 From: Bhawanpreet Lakha Date: Wed, 18 Nov 2020 14:10:44 -0500 Subject: drm/amd/display: Add DPCS regs for dcn302 link encoder dpcs reg are missing for dcn302 link encoder regs list, so add them. Just like dcn3 Signed-off-by: Bhawanpreet Lakha Reviewed-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c | 1 + 1 file changed, 1 insertion(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c index 765002e0ff93..08ef1428550b 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c @@ -967,6 +967,7 @@ static const struct encoder_feature_support link_enc_feature = { [id] = {\ LE_DCN3_REG_LIST(id), \ UNIPHY_DCN2_REG_LIST(phyid), \ + DPCS_DCN2_REG_LIST(id), \ SRI(DP_DPHY_INTERNAL_CTRL, DP, id) \ } -- cgit v1.2.3 From af5bbf93101dda20f5d89437ed00696704a65c51 Mon Sep 17 00:00:00 2001 From: Rodrigo Siqueira Date: Tue, 17 Nov 2020 15:25:48 -0500 Subject: drm/amd/display: Avoid HDCP initialization in devices without output The HDCP feature requires at least one connector attached to the device; however, some GPUs do not have a physical output, making the HDCP initialization irrelevant. This patch disables HDCP initialization when the graphic card does not have output. Acked-by: Alex Deucher Signed-off-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 936979c52c2c..63d9bfaa113b 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -1109,7 +1109,7 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) amdgpu_dm_init_color_mod(); #ifdef CONFIG_DRM_AMD_DC_HDCP - if (adev->asic_type >= CHIP_RAVEN) { + if (adev->dm.dc->caps.max_links > 0 && adev->asic_type >= CHIP_RAVEN) { adev->dm.hdcp_workqueue = hdcp_create_workqueue(adev, &init_params.cp_psp, adev->dm.dc); if (!adev->dm.hdcp_workqueue) -- cgit v1.2.3 From 910e834db00e40942e79226d638f0f2217eeedd6 Mon Sep 17 00:00:00 2001 From: "Gustavo A. R. Silva" Date: Fri, 20 Nov 2020 12:28:12 -0600 Subject: drm/amd/display: Fix fall-through warnings for Clang In preparation to enable -Wimplicit-fallthrough for Clang, fix multiple warnings by explicitly adding multiple break statements instead of just letting the code fall through to the next case. Link: https://github.com/KSPP/linux/issues/115 Signed-off-by: Gustavo A. R. Silva Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/bios/bios_parser.c | 1 + drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c | 2 ++ drivers/gpu/drm/amd/display/dc/core/dc_link.c | 1 + 3 files changed, 4 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/bios/bios_parser.c b/drivers/gpu/drm/amd/display/dc/bios/bios_parser.c index ad394aefa5d9..23a373ca94b5 100644 --- a/drivers/gpu/drm/amd/display/dc/bios/bios_parser.c +++ b/drivers/gpu/drm/amd/display/dc/bios/bios_parser.c @@ -1198,6 +1198,7 @@ static enum bp_result bios_parser_get_embedded_panel_info( default: break; } + break; default: break; } diff --git a/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c b/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c index 43922fa358a9..1782ff5542e9 100644 --- a/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c +++ b/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c @@ -903,6 +903,7 @@ static enum bp_result bios_parser_get_soc_bb_info( break; case 4: result = get_soc_bb_info_v4_4(bp, soc_bb_info); + break; default: break; } @@ -1019,6 +1020,7 @@ static enum bp_result bios_parser_get_embedded_panel_info( default: break; } + break; default: break; } diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index 5790affc7d61..02ba6b0a5980 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -1060,6 +1060,7 @@ static bool dc_link_detect_helper(struct dc_link *link, return false; } + break; default: break; } -- cgit v1.2.3 From e97978e8121ecc6e7d16eed55f0bb3987c2993aa Mon Sep 17 00:00:00 2001 From: Charlene Liu Date: Mon, 21 Sep 2020 14:24:09 -0400 Subject: drm/amd/display: add i2c speed arbitration for dc_i2c and hdcp_i2c [why] HDCP 1.4 failed on SL8800 SW w/a test driver use. [how] slower down the HW i2c speed when used by HW i2c. this request: each acquired_i2c_engine setup the i2c speed needed. and set the I2c engine for HDCP use at release_engine. this covers SW using HW I2c engine and HDCP using HW I2c engine. for dmcu using HW I2c engine, needs add similar logic in dmcufw. Signed-off-by: Charlene Liu Reviewed-by: Chris Park Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c | 1 + drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c | 1 + 2 files changed, 2 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index 0006d805b3b2..d15220a4eeb6 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -1759,6 +1759,7 @@ static bool dcn301_resource_construct( pool->base.mpcc_count = pool->base.res_cap->num_timing_generator; dc->caps.max_downscale_ratio = 600; dc->caps.i2c_speed_in_khz = 100; + dc->caps.i2c_speed_in_khz_hdcp = 5; /*1.4 w/a enabled by default*/ dc->caps.max_cursor_size = 256; dc->caps.dmdata_alloc_size = 2048; dc->caps.max_slave_planes = 1; diff --git a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c index 08ef1428550b..376ccdb85e30 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c @@ -1307,6 +1307,7 @@ static bool dcn302_resource_construct( pool->mpcc_count = pool->res_cap->num_timing_generator; dc->caps.max_downscale_ratio = 600; dc->caps.i2c_speed_in_khz = 100; + dc->caps.i2c_speed_in_khz_hdcp = 5; /*1.4 w/a applied by derfault*/ dc->caps.max_cursor_size = 256; dc->caps.dmdata_alloc_size = 2048; -- cgit v1.2.3 From 06722b37d1560502901ab1a6fb6e5996cae26b1f Mon Sep 17 00:00:00 2001 From: Ashley Thomas Date: Thu, 1 Oct 2020 00:16:05 -0700 Subject: drm/amd/display: Source minimum HBlank support [Why] Some sink devices wish to have access to the minimum HBlank supported by the ASIC. [How] Make the ASIC minimum HBlank available in Source Device information address 0x340. Signed-off-by: Ashley Thomas Reviewed-by: Anthony Koo Reviewed-by: Wenjing Liu Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c | 1 + drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c | 1 + 2 files changed, 2 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index d15220a4eeb6..be58134a7954 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -1761,6 +1761,7 @@ static bool dcn301_resource_construct( dc->caps.i2c_speed_in_khz = 100; dc->caps.i2c_speed_in_khz_hdcp = 5; /*1.4 w/a enabled by default*/ dc->caps.max_cursor_size = 256; + dc->caps.min_horizontal_blanking_period = 80; dc->caps.dmdata_alloc_size = 2048; dc->caps.max_slave_planes = 1; dc->caps.is_apu = true; diff --git a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c index 376ccdb85e30..808c4dcdb3ac 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c @@ -1309,6 +1309,7 @@ static bool dcn302_resource_construct( dc->caps.i2c_speed_in_khz = 100; dc->caps.i2c_speed_in_khz_hdcp = 5; /*1.4 w/a applied by derfault*/ dc->caps.max_cursor_size = 256; + dc->caps.min_horizontal_blanking_period = 80; dc->caps.dmdata_alloc_size = 2048; dc->caps.max_slave_planes = 1; -- cgit v1.2.3 From 41fd932e1a1518b6ee07f08ca99eb8b6a05e13d8 Mon Sep 17 00:00:00 2001 From: Chris Park Date: Mon, 19 Oct 2020 14:32:14 -0400 Subject: drm/amd/display: Update panel register [Why] Incorrect panel register settings are applied for power sequence because the register macro is not defined in resource. [How] Implement same register space to future resource files. Signed-off-by: Chris Park Reviewed-by: Joshua Aberback Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c | 1 + 1 file changed, 1 insertion(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index be58134a7954..9ce9d9603942 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -521,6 +521,7 @@ static const struct dcn10_link_enc_hpd_registers link_enc_hpd_regs[] = { [id] = {\ LE_DCN301_REG_LIST(id), \ UNIPHY_DCN2_REG_LIST(phyid), \ + SRI(DP_DPHY_INTERNAL_CTRL, DP, id) \ } static const struct dce110_aux_registers_shift aux_shift = { -- cgit v1.2.3 From 949c5cde3e0ffca0811ef72b8f4bcd9a483ab558 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Wed, 21 Oct 2020 13:19:44 -0400 Subject: drm/amd/display: Enable stutter for dcn3.01. [Why & How] Enable stutter for DCN3.01. Signed-off-by: Yongqiang Sun Reviewed-by: Harry Wentland Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c | 1 - 1 file changed, 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index 9ce9d9603942..5f97808bb423 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -855,7 +855,6 @@ static const struct dc_debug_options debug_defaults_drv = { .disable_clock_gate = true, .disable_pplib_clock_request = true, .disable_pplib_wm_range = true, - .disable_stutter = true, .pipe_split_policy = MPC_SPLIT_AVOID_MULT_DISP, .force_single_disp_pipe_split = false, .disable_dcc = DCC_ENABLE, -- cgit v1.2.3 From 96879ad3e4e3cf16af78de4fe9cbc9688cb26105 Mon Sep 17 00:00:00 2001 From: Jacky Liao Date: Wed, 21 Oct 2020 17:31:26 -0400 Subject: drm/amd/display: Add DMCU memory low power support [Why] On some platforms, DMCU is no longer used. In these cases, some DMCU memory should be completely powered off to save power. [How] 1. Set DMCU_ERAM_MEM_PWR_FORCE to shutdown memory when DMCU is not in use 2. Added a debug option to allow this behaviour to be turned off 3. Set all memory low power debug options to off first, to not immediately cause problems Signed-off-by: Jacky Liao Reviewed-by: Eric Yang Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 2 ++ drivers/gpu/drm/amd/display/dc/dce/dce_hwseq.h | 7 +++++-- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c | 7 +++++++ 3 files changed, 14 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 443b1f1ad546..b170e653febc 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -420,6 +420,8 @@ struct dc_bw_validation_profile { union mem_low_power_enable_options { struct { bool i2c: 1; + bool dmcu: 1; + bool cm: 1; bool mpc: 1; bool optc: 1; } bits; diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_hwseq.h b/drivers/gpu/drm/amd/display/dc/dce/dce_hwseq.h index ad0ae1f7b513..fe31abfa6c85 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_hwseq.h +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_hwseq.h @@ -597,6 +597,7 @@ struct dce_hwseq_registers { uint32_t AZALIA_CONTROLLER_CLOCK_GATING; uint32_t HPO_TOP_CLOCK_CONTROL; uint32_t ODM_MEM_PWR_CTRL3; + uint32_t DMU_MEM_PWR_CNTL; }; /* set field name */ #define HWS_SF(blk_name, reg_name, field_name, post_fix)\ @@ -836,7 +837,8 @@ struct dce_hwseq_registers { HWSEQ_DCN2_MASK_SH_LIST(mask_sh), \ HWS_SF(, AZALIA_AUDIO_DTO, AZALIA_AUDIO_DTO_MODULE, mask_sh), \ HWS_SF(, ODM_MEM_PWR_CTRL3, ODM_MEM_UNASSIGNED_PWR_MODE, mask_sh), \ - HWS_SF(, ODM_MEM_PWR_CTRL3, ODM_MEM_VBLANK_PWR_MODE, mask_sh) + HWS_SF(, ODM_MEM_PWR_CTRL3, ODM_MEM_VBLANK_PWR_MODE, mask_sh), \ + HWS_SF(, DMU_MEM_PWR_CNTL, DMCU_ERAM_MEM_PWR_FORCE, mask_sh) #define HWSEQ_DCN301_MASK_SH_LIST(mask_sh)\ HWSEQ_DCN_MASK_SH_LIST(mask_sh), \ @@ -1046,7 +1048,8 @@ struct dce_hwseq_registers { type D4VGA_MODE_ENABLE; \ type AZALIA_AUDIO_DTO_MODULE; \ type ODM_MEM_UNASSIGNED_PWR_MODE; \ - type ODM_MEM_VBLANK_PWR_MODE; + type ODM_MEM_VBLANK_PWR_MODE; \ + type DMCU_ERAM_MEM_PWR_FORCE; #define HWSEQ_DCN3_REG_FIELD_LIST(type) \ type HPO_HDMISTREAMCLK_GATE_DIS; diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c index e76d6ab8d93a..7a7efe9ea961 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c @@ -462,6 +462,13 @@ void dcn30_init_hw(struct dc *dc) hws->funcs.disable_vga(dc->hwseq); } + if (dc->debug.enable_mem_low_power.bits.dmcu) { + // Force ERAM to shutdown if DMCU is not enabled + if (dc->debug.disable_dmcu || dc->config.disable_dmcu) { + REG_UPDATE(DMU_MEM_PWR_CNTL, DMCU_ERAM_MEM_PWR_FORCE, 3); + } + } + // Set default OPTC memory power states if (dc->debug.enable_mem_low_power.bits.optc) { // Shutdown when unassigned and light sleep in VBLANK -- cgit v1.2.3 From d4930b7aaefb8050229f41d19da86d3ab5c8f04f Mon Sep 17 00:00:00 2001 From: Tashfique Abdullah Date: Wed, 4 Nov 2020 18:51:53 -0500 Subject: drm/amd/display: intermittent underflow observed when PIP is toggled in Full screen [Why] The MPCC may change and request data when the pipes are switching from 2 to 1 or 1 to 2. During the switch there is a possibility of underflow and flicker/missing data. [How] During VBlank the MPCC won't request data. The trick is to delay and wait on VBlank, ONLY when pipes are either turning on or off, right before MPCC is reset for the pipes. Signed-off-by: Tashfique Abdullah Reviewed-by: Aric Cyr Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c | 9 +++++++++ 1 file changed, 9 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c index b9c20e30d99d..abcb06044e6e 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_hwseq.c @@ -1695,6 +1695,15 @@ void dcn20_program_front_end_for_ctx( && context->res_ctx.pipe_ctx[i].stream) hws->funcs.blank_pixel_data(dc, &context->res_ctx.pipe_ctx[i], true); + /* wait for outstanding pending changes before adding or removing planes */ + for (i = 0; i < dc->res_pool->pipe_count; i++) { + if (context->res_ctx.pipe_ctx[i].update_flags.bits.disable || + context->res_ctx.pipe_ctx[i].update_flags.bits.enable) { + dc->hwss.wait_for_pending_cleared(dc, context); + break; + } + } + /* Disconnect mpcc */ for (i = 0; i < dc->res_pool->pipe_count; i++) if (context->res_ctx.pipe_ctx[i].update_flags.bits.disable -- cgit v1.2.3 From 2208f39c750972ad3796b4353ccf9f7c8636931c Mon Sep 17 00:00:00 2001 From: Eric Yang Date: Thu, 5 Nov 2020 15:44:55 -0500 Subject: drm/amd/display: expose clk_mgr functions for reuse Signed-off-by: Eric Yang Reviewed-by: Dmytro Laktyushkin Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c | 8 ++++---- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h | 10 ++++++++++ 2 files changed, 14 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c index 98cbb0ac095c..9a8e66bba9c0 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c @@ -32,9 +32,9 @@ // For dcn20_update_clocks_update_dpp_dto #include "dcn20/dcn20_clk_mgr.h" -#include "vg_clk_mgr.h" -#include "dcn301_smu.h" + +#include "vg_clk_mgr.h" #include "reg_helper.h" #include "core_types.h" #include "dm_helpers.h" @@ -631,7 +631,7 @@ static unsigned int find_dcfclk_for_voltage(const struct vg_dpm_clocks *clock_ta return 0; } -static void vg_clk_mgr_helper_populate_bw_params( +void vg_clk_mgr_helper_populate_bw_params( struct clk_mgr_internal *clk_mgr, struct integrated_info *bios_info, const struct vg_dpm_clocks *clock_table) @@ -709,7 +709,7 @@ static struct vg_dpm_clocks dummy_clocks = { static struct watermarks dummy_wms = { 0 }; -static void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, +void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, struct smu_dpm_clks *smu_dpm_clks) { struct vg_dpm_clocks *table = smu_dpm_clks->dpm_clks; diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h index 80497df20ba7..b5115b3123a1 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h @@ -39,5 +39,15 @@ void vg_clk_mgr_construct(struct dc_context *ctx, void vg_clk_mgr_destroy(struct clk_mgr_internal *clk_mgr); +#include "dcn301_smu.h" void vg_notify_wm_ranges(struct clk_mgr *clk_mgr_base); + +void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, + struct smu_dpm_clks *smu_dpm_clks); + +void vg_clk_mgr_helper_populate_bw_params( + struct clk_mgr_internal *clk_mgr, + struct integrated_info *bios_info, + const struct vg_dpm_clocks *clock_table); + #endif //__VG_CLK_MGR_H__ -- cgit v1.2.3 From 014427adc5565a0b46fd3ef6719167a31f04d764 Mon Sep 17 00:00:00 2001 From: Sherry Date: Wed, 11 Nov 2020 00:34:22 +0800 Subject: drm/amd/display: change hw sequence [Why] t9 delay func is called twice after setting power off, the unexpected action results in a doubling of the added 140ms t9 delay [How] If the backlight has been turned off, does not turn it off again Signed-off-by: Sherry Reviewed-by: Tony Cheng Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c index 9f56887029ca..90c85b3e859b 100644 --- a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c +++ b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c @@ -939,12 +939,15 @@ void dce110_edp_backlight_control( return; } - if (enable && link->panel_cntl && - link->panel_cntl->funcs->is_panel_backlight_on(link->panel_cntl)) { - DC_LOG_HW_RESUME_S3( - "%s: panel already powered up. Do nothing.\n", + if (link->panel_cntl) { + bool is_backlight_on = link->panel_cntl->funcs->is_panel_backlight_on(link->panel_cntl); + + if ((enable && is_backlight_on) || (!enable && !is_backlight_on)) { + DC_LOG_HW_RESUME_S3( + "%s: panel already powered up/off. Do nothing.\n", __func__); - return; + return; + } } /* Send VBIOS command to control eDP panel backlight */ -- cgit v1.2.3 From 63c954a1ff8b0f63dcabf8bb2d3b3c895a69ed89 Mon Sep 17 00:00:00 2001 From: Wyatt Wood Date: Wed, 4 Nov 2020 19:44:31 -0500 Subject: drm/amd/display: Clear sticky vsc sdp error bit [Why] Need to clear sticky error bits generated during hpd irq from receiver. [How] Clear sticky vsc sdp error bit. Signed-off-by: Wyatt Wood Reviewed-by: Anthony Koo Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c index 1dfcaf1acbfc..93fbc646f53b 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c @@ -2570,7 +2570,8 @@ static bool handle_hpd_irq_psr_sink(struct dc_link *link) psr_sink_psr_status.raw = dpcdbuf[2]; if (psr_error_status.bits.LINK_CRC_ERROR || - psr_error_status.bits.RFB_STORAGE_ERROR) { + psr_error_status.bits.RFB_STORAGE_ERROR || + psr_error_status.bits.VSC_SDP_ERROR) { /* Acknowledge and clear error bits */ dm_helpers_dp_write_dpcd( link->ctx, -- cgit v1.2.3 From 49d067dcf2844efd78562069574dbe25a75eb5d2 Mon Sep 17 00:00:00 2001 From: Jacky Liao Date: Wed, 11 Nov 2020 18:29:42 -0500 Subject: drm/amd/display: Add BLNDGAM memory shutdown support [Why] The BLNDGAM memory blocks should be powered down when they're not in use. This will reduce power consumption. [How] 1. Write to BLNDGAM_MEM_PWR_FORCE to put memory to shutdown when BLNDGAM is not used. 2. Added a debug option to allow this behaviour to be turned off Signed-off-by: Jacky Liao Reviewed-by: Eric Yang Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c | 13 ++++++++++--- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h | 4 +++- 2 files changed, 13 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c index 29231528f052..052bab3e5e8e 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c @@ -500,9 +500,14 @@ static void dpp3_power_on_blnd_lut( { struct dcn3_dpp *dpp = TO_DCN30_DPP(dpp_base); - REG_SET(CM_MEM_PWR_CTRL, 0, - BLNDGAM_MEM_PWR_FORCE, power_on == true ? 0:1); - + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) { + REG_UPDATE(CM_MEM_PWR_CTRL, BLNDGAM_MEM_PWR_FORCE, power_on ? 0 : 3); + if (power_on) + REG_WAIT(CM_MEM_PWR_STATUS, BLNDGAM_MEM_PWR_STATE, 0, 1, 5); + } else { + REG_SET(CM_MEM_PWR_CTRL, 0, + BLNDGAM_MEM_PWR_FORCE, power_on == true ? 0 : 1); + } } static void dpp3_configure_blnd_lut( @@ -675,6 +680,8 @@ bool dpp3_program_blnd_lut( if (params == NULL) { REG_SET(CM_BLNDGAM_CONTROL, 0, CM_BLNDGAM_MODE, 0); + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) + dpp3_power_on_blnd_lut(dpp_base, false); return false; } diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h index 81bf2ecc2831..2ae5e1f93dd4 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h @@ -343,6 +343,7 @@ TF_SF(DSCL0_DSCL_MEM_PWR_CTRL, LUT_MEM_PWR_FORCE, mask_sh) #define DPP_REG_LIST_SH_MASK_DCN30_UPDATED(mask_sh)\ + TF_SF(CM0_CM_MEM_PWR_STATUS, BLNDGAM_MEM_PWR_STATE, mask_sh), \ TF_SF(CM0_CM_BLNDGAM_CONTROL, CM_BLNDGAM_MODE, mask_sh), \ TF_SF(CM0_CM_BLNDGAM_CONTROL, CM_BLNDGAM_MODE_CURRENT, mask_sh), \ TF_SF(CM0_CM_BLNDGAM_CONTROL, CM_BLNDGAM_SELECT_CURRENT, mask_sh), \ @@ -446,7 +447,8 @@ type CM_BLNDGAM_MODE_CURRENT; \ type CM_BLNDGAM_SELECT_CURRENT; \ type CM_BLNDGAM_SELECT; \ - type GAMCOR_MEM_PWR_STATE + type GAMCOR_MEM_PWR_STATE; \ + type BLNDGAM_MEM_PWR_STATE struct dcn3_dpp_shift { DPP_REG_FIELD_LIST_DCN3(uint8_t); -- cgit v1.2.3 From c85ef99a9fa394f1cd3cc3694415f80d2c9378ec Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Wed, 11 Nov 2020 15:12:04 -0500 Subject: drm/amd/display: Add internal display info [Why & How] Get internal display info from vbios and pass it to dmub fw to determine if multiple display optmization is needed. Signed-off-by: Yongqiang Sun Reviewed-by: Tony Cheng Acked-by: Anthony Koo Acked-by: Aric Cyr Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c | 73 ++++++++++++++++++++++ drivers/gpu/drm/amd/display/dc/core/dc_link.c | 7 +++ drivers/gpu/drm/amd/display/dc/dc_bios_types.h | 5 ++ drivers/gpu/drm/amd/display/dc/dc_link.h | 1 + .../drm/amd/display/include/bios_parser_types.h | 5 ++ drivers/gpu/drm/amd/include/atomfirmware.h | 1 + 6 files changed, 92 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c b/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c index 1782ff5542e9..90d5b320f1ac 100644 --- a/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c +++ b/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c @@ -65,6 +65,11 @@ GENERIC_OBJECT_ID_BRACKET_LAYOUT << OBJECT_ID_SHIFT) #endif /* GENERICOBJECT_BRACKET_LAYOUT_ENUM_ID2 */ + +//TODO: Remove this temp define after atomfirmware.h is updated. +#define ATOM_DISP_CONNECTOR_CAPS_RECORD_TYPE 23 + + #define DC_LOGGER \ bp->base.ctx->logger @@ -1455,6 +1460,72 @@ static struct atom_encoder_caps_record *get_encoder_cap_record( return NULL; } +static struct atom_disp_connector_caps_record *get_disp_connector_caps_record( + struct bios_parser *bp, + struct atom_display_object_path_v2 *object) +{ + struct atom_common_record_header *header; + uint32_t offset; + + if (!object) { + BREAK_TO_DEBUGGER(); /* Invalid object */ + return NULL; + } + + offset = object->disp_recordoffset + bp->object_info_tbl_offset; + + for (;;) { + header = GET_IMAGE(struct atom_common_record_header, offset); + + if (!header) + return NULL; + + offset += header->record_size; + + if (header->record_type == LAST_RECORD_TYPE || + !header->record_size) + break; + + if (header->record_type != ATOM_DISP_CONNECTOR_CAPS_RECORD_TYPE) + continue; + + if (sizeof(struct atom_disp_connector_caps_record) <= + header->record_size) + return (struct atom_disp_connector_caps_record *)header; + } + + return NULL; +} + +static enum bp_result bios_parser_get_disp_connector_caps_info( + struct dc_bios *dcb, + struct graphics_object_id object_id, + struct bp_disp_connector_caps_info *info) +{ + struct bios_parser *bp = BP_FROM_DCB(dcb); + struct atom_display_object_path_v2 *object; + struct atom_disp_connector_caps_record *record = NULL; + + if (!info) + return BP_RESULT_BADINPUT; + + object = get_bios_object(bp, object_id); + + if (!object) + return BP_RESULT_BADINPUT; + + record = get_disp_connector_caps_record(bp, object); + if (!record) + return BP_RESULT_NORECORD; + + info->INTERNAL_DISPLAY = (record->connectcaps & ATOM_CONNECTOR_CAP_INTERNAL_DISPLAY) + ? 1 : 0; + info->INTERNAL_DISPLAY_BL = (record->connectcaps & ATOM_CONNECTOR_CAP_INTERNAL_DISPLAY_BL) + ? 1 : 0; + + return BP_RESULT_OK; +} + static enum bp_result get_vram_info_v23( struct bios_parser *bp, struct dc_vram_info *info) @@ -2463,6 +2534,8 @@ static const struct dc_vbios_funcs vbios_funcs = { .enable_lvtma_control = bios_parser_enable_lvtma_control, .get_soc_bb_info = bios_parser_get_soc_bb_info, + + .get_disp_connector_caps_info = bios_parser_get_disp_connector_caps_info, }; static bool bios_parser2_construct( diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index 02ba6b0a5980..4a897c326aab 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -1369,6 +1369,7 @@ static bool dc_link_construct(struct dc_link *link, struct integrated_info info = {{{ 0 }}}; struct dc_bios *bios = init_params->dc->ctx->dc_bios; const struct dc_vbios_funcs *bp_funcs = bios->funcs; + struct bp_disp_connector_caps_info disp_connect_caps_info = { 0 }; DC_LOGGER_INIT(dc_ctx->logger); @@ -1389,6 +1390,12 @@ static bool dc_link_construct(struct dc_link *link, link->link_id = bios->funcs->get_connector_id(bios, init_params->connector_index); + + if (bios->funcs->get_disp_connector_caps_info) { + bios->funcs->get_disp_connector_caps_info(bios, link->link_id, &disp_connect_caps_info); + link->is_internal_display = disp_connect_caps_info.INTERNAL_DISPLAY; + } + if (link->link_id.type != OBJECT_TYPE_CONNECTOR) { dm_output_to_console("%s: Invalid Connector ObjectID from Adapter Service for connector index:%d! type %d expected %d\n", __func__, init_params->connector_index, diff --git a/drivers/gpu/drm/amd/display/dc/dc_bios_types.h b/drivers/gpu/drm/amd/display/dc/dc_bios_types.h index e146e3cba8eb..509d23fdd3c9 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_bios_types.h +++ b/drivers/gpu/drm/amd/display/dc/dc_bios_types.h @@ -144,6 +144,11 @@ struct dc_vbios_funcs { enum bp_result (*get_soc_bb_info)( struct dc_bios *dcb, struct bp_soc_bb_info *soc_bb_info); + + enum bp_result (*get_disp_connector_caps_info)( + struct dc_bios *dcb, + struct graphics_object_id object_id, + struct bp_disp_connector_caps_info *info); }; struct bios_registers { diff --git a/drivers/gpu/drm/amd/display/dc/dc_link.h b/drivers/gpu/drm/amd/display/dc/dc_link.h index 65b083e64131..66445e34fd37 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_link.h +++ b/drivers/gpu/drm/amd/display/dc/dc_link.h @@ -101,6 +101,7 @@ struct dc_link { bool aux_access_disabled; bool sync_lt_in_progress; bool lttpr_non_transparent_mode; + bool is_internal_display; /* caps is the same as reported_link_cap. link_traing use * reported_link_cap. Will clean up. TODO diff --git a/drivers/gpu/drm/amd/display/include/bios_parser_types.h b/drivers/gpu/drm/amd/display/include/bios_parser_types.h index 7c782924c941..76a87b682883 100644 --- a/drivers/gpu/drm/amd/display/include/bios_parser_types.h +++ b/drivers/gpu/drm/amd/display/include/bios_parser_types.h @@ -309,6 +309,11 @@ struct bp_spread_spectrum_parameters { struct spread_spectrum_flags flags; }; +struct bp_disp_connector_caps_info { + uint32_t INTERNAL_DISPLAY : 1; + uint32_t INTERNAL_DISPLAY_BL : 1; +}; + struct bp_encoder_cap_info { uint32_t DP_HBR2_CAP:1; uint32_t DP_HBR2_EN:1; diff --git a/drivers/gpu/drm/amd/include/atomfirmware.h b/drivers/gpu/drm/amd/include/atomfirmware.h index 6139d10f4289..c38635992101 100644 --- a/drivers/gpu/drm/amd/include/atomfirmware.h +++ b/drivers/gpu/drm/amd/include/atomfirmware.h @@ -725,6 +725,7 @@ enum atom_object_record_type_id ATOM_ENCODER_CAP_RECORD_TYPE=20, ATOM_BRACKET_LAYOUT_RECORD_TYPE=21, ATOM_CONNECTOR_FORCED_TMDS_CAP_RECORD_TYPE=22, + ATOM_DISP_CONNECTOR_CAPS_RECORD_TYPE=23, ATOM_RECORD_END_TYPE =0xFF, }; -- cgit v1.2.3 From 30bdf50b77bd3dbc111b4aeff7018d8c58ec7d8d Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Thu, 12 Nov 2020 11:21:16 -0500 Subject: drm/amd/display: Check multiple internal displays for power optimization. [Why & How] only apply multiple display power optimization in case there are more than one internal display. Signed-off-by: Yongqiang Sun Reviewed-by: Tony Cheng Acked-by: Anthony Koo Acked-by: Aric Cyr Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc.c | 16 ++++++++++++++++ drivers/gpu/drm/amd/display/dc/dc.h | 1 + 2 files changed, 17 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c index 28b856e2686d..903353389edb 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc.c @@ -149,6 +149,20 @@ static void destroy_links(struct dc *dc) } } +static uint32_t get_num_of_internal_disp(struct dc_link **links, uint32_t num_links) +{ + int i; + uint32_t count = 0; + + for (i = 0; i < num_links; i++) { + if (links[i]->connector_signal == SIGNAL_TYPE_EDP || + links[i]->is_internal_display) + count++; + } + + return count; +} + static bool create_links( struct dc *dc, uint32_t num_virtual_links) @@ -250,6 +264,8 @@ static bool create_links( virtual_link_encoder_construct(link->link_enc, &enc_init); } + dc->caps.num_of_internal_disp = get_num_of_internal_disp(dc->links, dc->link_count); + return true; failed_alloc: diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index b170e653febc..115468d3f793 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -169,6 +169,7 @@ struct dc_caps { bool psp_setup_panel_mode; bool extended_aux_timeout_support; bool dmcub_support; + uint32_t num_of_internal_disp; enum dp_protocol_version max_dp_protocol_version; struct dc_plane_cap planes[MAX_PLANES]; struct dc_color_caps color; -- cgit v1.2.3 From fe270efa32e64283886bb92cbb029600194cc72b Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Fri, 13 Nov 2020 09:05:32 -0500 Subject: drm/amd/display: remove macro which is in header already [Why & How] Remove temp macro since the enum is in header file already. Signed-off-by: Yongqiang Sun Reviewed-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c | 5 ----- 1 file changed, 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c b/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c index 90d5b320f1ac..670c26583817 100644 --- a/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c +++ b/drivers/gpu/drm/amd/display/dc/bios/bios_parser2.c @@ -65,11 +65,6 @@ GENERIC_OBJECT_ID_BRACKET_LAYOUT << OBJECT_ID_SHIFT) #endif /* GENERICOBJECT_BRACKET_LAYOUT_ENUM_ID2 */ - -//TODO: Remove this temp define after atomfirmware.h is updated. -#define ATOM_DISP_CONNECTOR_CAPS_RECORD_TYPE 23 - - #define DC_LOGGER \ bp->base.ctx->logger -- cgit v1.2.3 From 3ba0a5f3eef92d3762495af9418b542ad861ca3a Mon Sep 17 00:00:00 2001 From: Jacky Liao Date: Thu, 12 Nov 2020 16:18:10 -0500 Subject: drm/amd/display: Add GAMCOR memory shutdown support [Why] The GAMCOR memory blocks should be powered down when they're not in use. This will reduce power consumption. [How] Write to GAMCOR_MEM_PWR_FORCE to put memory to shutdown when GAMCOR is not used. Signed-off-by: Jacky Liao Reviewed-by: Eric Yang Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp_cm.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp_cm.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp_cm.c index 9ab63c72f21c..9da66e491116 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp_cm.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp_cm.c @@ -136,9 +136,13 @@ static void dpp3_power_on_gamcor_lut( uint32_t power_status; struct dcn3_dpp *dpp = TO_DCN30_DPP(dpp_base); - - REG_SET(CM_MEM_PWR_CTRL, 0, - GAMCOR_MEM_PWR_DIS, power_on == true ? 0:1); + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) { + REG_UPDATE(CM_MEM_PWR_CTRL, GAMCOR_MEM_PWR_FORCE, power_on ? 0 : 3); + if (power_on) + REG_WAIT(CM_MEM_PWR_STATUS, GAMCOR_MEM_PWR_STATE, 0, 1, 5); + } else + REG_SET(CM_MEM_PWR_CTRL, 0, + GAMCOR_MEM_PWR_DIS, power_on == true ? 0:1); REG_GET(CM_MEM_PWR_STATUS, GAMCOR_MEM_PWR_STATE, &power_status); if (power_status != 0) @@ -229,6 +233,8 @@ bool dpp3_program_gamcor_lut( if (params == NULL) { //bypass if we have no pwl data REG_SET(CM_GAMCOR_CONTROL, 0, CM_GAMCOR_MODE, 0); + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) + dpp3_power_on_gamcor_lut(dpp_base, false); return false; } dpp3_power_on_gamcor_lut(dpp_base, true); -- cgit v1.2.3 From 823b3169fbfc23816dd575214a06864cbcb0454b Mon Sep 17 00:00:00 2001 From: Sung Joon Kim Date: Fri, 13 Nov 2020 11:01:19 -0500 Subject: drm/amd/display: enable pipe power gating by default [why] ASIC requirement. [how] Make disable_*_power_gate to false. Signed-off-by: Sung Joon Kim Reviewed-by: Charlene Liu Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index 5f97808bb423..4b029631a22c 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -850,8 +850,8 @@ static const struct dc_debug_options debug_defaults_drv = { .force_abm_enable = false, .timing_trace = false, .clock_trace = true, - .disable_dpp_power_gate = true, - .disable_hubp_power_gate = true, + .disable_dpp_power_gate = false, + .disable_hubp_power_gate = false, .disable_clock_gate = true, .disable_pplib_clock_request = true, .disable_pplib_wm_range = true, @@ -873,8 +873,8 @@ static const struct dc_debug_options debug_defaults_diags = { .force_abm_enable = false, .timing_trace = true, .clock_trace = true, - .disable_dpp_power_gate = true, - .disable_hubp_power_gate = true, + .disable_dpp_power_gate = false, + .disable_hubp_power_gate = false, .disable_clock_gate = true, .disable_pplib_clock_request = true, .disable_pplib_wm_range = true, -- cgit v1.2.3 From eaae693835770eca991f68917304c84130e993e5 Mon Sep 17 00:00:00 2001 From: Aric Cyr Date: Mon, 16 Nov 2020 10:27:57 -0500 Subject: drm/amd/display: 3.2.113 Signed-off-by: Aric Cyr Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 115468d3f793..68a192e64418 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -42,7 +42,7 @@ #include "inc/hw/dmcu.h" #include "dml/display_mode_lib.h" -#define DC_VER "3.2.112" +#define DC_VER "3.2.113" #define MAX_SURFACES 3 #define MAX_PLANES 6 -- cgit v1.2.3 From 7530d914633894ea691343e2671c88be36609776 Mon Sep 17 00:00:00 2001 From: Camille Cho Date: Thu, 12 Nov 2020 15:33:19 +0800 Subject: drm/amd/display: To update backlight restore mechanism [Why] Cached backlight is never being updated since panel_cntl specific registers were moved from abm to panel_cntl. [How] Update cached backlight in set_abm_immediate_disable as what we used to do. Also, update the priority of backlight restore mechanism so that cached backlight has the highest priority since it is always correct. Signed-off-by: Camille Cho Reviewed-by: Anthony Koo Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- .../gpu/drm/amd/display/dc/dce/dce_panel_cntl.c | 36 ++++++++++------------ drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c | 4 ++- 2 files changed, 20 insertions(+), 20 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dce/dce_panel_cntl.c b/drivers/gpu/drm/amd/display/dc/dce/dce_panel_cntl.c index 74f7619d4154..761fdfc1f5bd 100644 --- a/drivers/gpu/drm/amd/display/dc/dce/dce_panel_cntl.c +++ b/drivers/gpu/drm/amd/display/dc/dce/dce_panel_cntl.c @@ -108,25 +108,17 @@ static uint32_t dce_panel_cntl_hw_init(struct panel_cntl *panel_cntl) */ REG_GET(BL_PWM_CNTL, BL_ACTIVE_INT_FRAC_CNT, &value); - if (value == 0 || value == 1) { - if (panel_cntl->stored_backlight_registers.BL_PWM_CNTL != 0) { - REG_WRITE(BL_PWM_CNTL, - panel_cntl->stored_backlight_registers.BL_PWM_CNTL); - REG_WRITE(BL_PWM_CNTL2, - panel_cntl->stored_backlight_registers.BL_PWM_CNTL2); - REG_WRITE(BL_PWM_PERIOD_CNTL, - panel_cntl->stored_backlight_registers.BL_PWM_PERIOD_CNTL); - REG_UPDATE(PWRSEQ_REF_DIV, - BL_PWM_REF_DIV, - panel_cntl->stored_backlight_registers.LVTMA_PWRSEQ_REF_DIV_BL_PWM_REF_DIV); - } else { - /* TODO: Note: This should not really happen since VBIOS - * should have initialized PWM registers on boot. - */ - REG_WRITE(BL_PWM_CNTL, 0xC000FA00); - REG_WRITE(BL_PWM_PERIOD_CNTL, 0x000C0FA0); - } - } else { + if (panel_cntl->stored_backlight_registers.BL_PWM_CNTL != 0) { + REG_WRITE(BL_PWM_CNTL, + panel_cntl->stored_backlight_registers.BL_PWM_CNTL); + REG_WRITE(BL_PWM_CNTL2, + panel_cntl->stored_backlight_registers.BL_PWM_CNTL2); + REG_WRITE(BL_PWM_PERIOD_CNTL, + panel_cntl->stored_backlight_registers.BL_PWM_PERIOD_CNTL); + REG_UPDATE(PWRSEQ_REF_DIV, + BL_PWM_REF_DIV, + panel_cntl->stored_backlight_registers.LVTMA_PWRSEQ_REF_DIV_BL_PWM_REF_DIV); + } else if ((value != 0) && (value != 1)) { panel_cntl->stored_backlight_registers.BL_PWM_CNTL = REG_READ(BL_PWM_CNTL); panel_cntl->stored_backlight_registers.BL_PWM_CNTL2 = @@ -136,6 +128,12 @@ static uint32_t dce_panel_cntl_hw_init(struct panel_cntl *panel_cntl) REG_GET(PWRSEQ_REF_DIV, BL_PWM_REF_DIV, &panel_cntl->stored_backlight_registers.LVTMA_PWRSEQ_REF_DIV_BL_PWM_REF_DIV); + } else { + /* TODO: Note: This should not really happen since VBIOS + * should have initialized PWM registers on boot. + */ + REG_WRITE(BL_PWM_CNTL, 0x8000FA00); + REG_WRITE(BL_PWM_PERIOD_CNTL, 0x000C0FA0); } // Have driver take backlight control diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c index 1fa193078803..96ee0b82f458 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_hwseq.c @@ -171,9 +171,11 @@ void dcn21_set_abm_immediate_disable(struct pipe_ctx *pipe_ctx) return; } - if (abm && panel_cntl) + if (abm && panel_cntl) { dmub_abm_set_pipe(abm, otg_inst, SET_ABM_PIPE_IMMEDIATELY_DISABLE, panel_cntl->inst); + panel_cntl->funcs->store_backlight_level(panel_cntl); + } } void dcn21_set_pipe(struct pipe_ctx *pipe_ctx) -- cgit v1.2.3 From 9a3e698c0758ce42059e74998d27d689dadfebc8 Mon Sep 17 00:00:00 2001 From: Yongqiang Sun Date: Thu, 8 Oct 2020 11:07:57 -0400 Subject: drm/amd/display: init soc bounding box for dcn3.01. [Why & How] Update init soc bounding box and bw bounding box for DCN3.01. Remove pp smu interface which isn't used. v2: squash in removal of stable function definition (Alex) Signed-off-by: Yongqiang Sun Reviewed-by: Tony Cheng Acked-by: Rodrigo Siqueira Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/dcn301/dcn301_resource.c | 120 ++++++++++----------- 1 file changed, 60 insertions(+), 60 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index 4b029631a22c..7e95bd1e9e53 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -1223,8 +1223,6 @@ static const struct resource_create_funcs res_create_maximus_funcs = { .create_hwseq = dcn301_hwseq_create, }; -static void dcn301_pp_smu_destroy(struct pp_smu_funcs **pp_smu); - static void dcn301_destruct(struct dcn301_resource_pool *pool) { unsigned int i; @@ -1345,9 +1343,6 @@ static void dcn301_destruct(struct dcn301_resource_pool *pool) if (pool->base.dccg != NULL) dcn_dccg_destroy(&pool->base.dccg); - - if (pool->base.pp_smu != NULL) - dcn301_pp_smu_destroy(&pool->base.pp_smu); } struct hubp *dcn301_hubp_create( @@ -1600,41 +1595,25 @@ static bool init_soc_bounding_box(struct dc *dc, } } - if (pool->base.pp_smu) { - struct pp_smu_nv_clock_table max_clocks = {0}; - unsigned int uclk_states[8] = {0}; - unsigned int num_states = 0; - enum pp_smu_status status; - bool clock_limits_available = false; - bool uclk_states_available = false; + loaded_ip->max_num_otg = pool->base.res_cap->num_timing_generator; + loaded_ip->max_num_dpp = pool->base.pipe_count; + dcn20_patch_bounding_box(dc, loaded_bb); + + if (!bb && dc->ctx->dc_bios->funcs->get_soc_bb_info) { + struct bp_soc_bb_info bb_info = {0}; - if (pool->base.pp_smu->nv_funcs.get_uclk_dpm_states) { - status = (pool->base.pp_smu->nv_funcs.get_uclk_dpm_states) - (&pool->base.pp_smu->nv_funcs.pp_smu, uclk_states, &num_states); + if (dc->ctx->dc_bios->funcs->get_soc_bb_info(dc->ctx->dc_bios, &bb_info) == BP_RESULT_OK) { + if (bb_info.dram_clock_change_latency_100ns > 0) + dcn3_01_soc.dram_clock_change_latency_us = bb_info.dram_clock_change_latency_100ns * 10; - uclk_states_available = (status == PP_SMU_RESULT_OK); - } + if (bb_info.dram_sr_enter_exit_latency_100ns > 0) + dcn3_01_soc.sr_enter_plus_exit_time_us = bb_info.dram_sr_enter_exit_latency_100ns * 10; - if (pool->base.pp_smu->nv_funcs.get_maximum_sustainable_clocks) { - status = (*pool->base.pp_smu->nv_funcs.get_maximum_sustainable_clocks) - (&pool->base.pp_smu->nv_funcs.pp_smu, &max_clocks); - /* SMU cannot set DCF clock to anything equal to or higher than SOC clock - */ - if (max_clocks.dcfClockInKhz >= max_clocks.socClockInKhz) - max_clocks.dcfClockInKhz = max_clocks.socClockInKhz - 1000; - clock_limits_available = (status == PP_SMU_RESULT_OK); + if (bb_info.dram_sr_exit_latency_100ns > 0) + dcn3_01_soc.sr_exit_time_us = bb_info.dram_sr_exit_latency_100ns * 10; } - - if (clock_limits_available && uclk_states_available && num_states) - dcn20_update_bounding_box(dc, loaded_bb, &max_clocks, uclk_states, num_states); - else if (clock_limits_available) - dcn20_cap_soc_clocks(loaded_bb, max_clocks); } - loaded_ip->max_num_otg = pool->base.res_cap->num_timing_generator; - loaded_ip->max_num_dpp = pool->base.pipe_count; - dcn20_patch_bounding_box(dc, loaded_bb); - return true; } @@ -1682,36 +1661,58 @@ static void set_wm_ranges( pp_smu->nv_funcs.set_wm_ranges(&pp_smu->nv_funcs.pp_smu, &ranges); } -static struct pp_smu_funcs *dcn301_pp_smu_create(struct dc_context *ctx) +static void dcn301_update_bw_bounding_box(struct dc *dc, struct clk_bw_params *bw_params) { - struct pp_smu_funcs *pp_smu = kzalloc(sizeof(*pp_smu), GFP_KERNEL); - - if (!pp_smu) - return pp_smu; - - if (!IS_FPGA_MAXIMUS_DC(ctx->dce_environment) && !IS_DIAG_DC(ctx->dce_environment)) { - dm_pp_get_funcs(ctx, pp_smu); - - /* TODO: update once we have n21 smu*/ - if (pp_smu->ctx.ver != PP_SMU_VER_NV) - pp_smu = memset(pp_smu, 0, sizeof(struct pp_smu_funcs)); - } - - return pp_smu; -} + struct dcn301_resource_pool *pool = TO_DCN301_RES_POOL(dc->res_pool); + struct clk_limit_table *clk_table = &bw_params->clk_table; + struct _vcs_dpi_voltage_scaling_st clock_limits[DC__VOLTAGE_STATES]; + unsigned int i, closest_clk_lvl; + int j; + + // Default clock levels are used for diags, which may lead to overclocking. + if (!IS_DIAG_DC(dc->ctx->dce_environment)) { + dcn3_01_ip.max_num_otg = pool->base.res_cap->num_timing_generator; + dcn3_01_ip.max_num_dpp = pool->base.pipe_count; + dcn3_01_soc.num_chans = bw_params->num_channels; + + ASSERT(clk_table->num_entries); + for (i = 0; i < clk_table->num_entries; i++) { + /* loop backwards*/ + for (closest_clk_lvl = 0, j = dcn3_01_soc.num_states - 1; j >= 0; j--) { + if ((unsigned int) dcn3_01_soc.clock_limits[j].dcfclk_mhz <= clk_table->entries[i].dcfclk_mhz) { + closest_clk_lvl = j; + break; + } + } -static void dcn301_pp_smu_destroy(struct pp_smu_funcs **pp_smu) -{ - if (pp_smu && *pp_smu) { - kfree(*pp_smu); - *pp_smu = NULL; + clock_limits[i].state = i; + clock_limits[i].dcfclk_mhz = clk_table->entries[i].dcfclk_mhz; + clock_limits[i].fabricclk_mhz = clk_table->entries[i].fclk_mhz; + clock_limits[i].socclk_mhz = clk_table->entries[i].socclk_mhz; + clock_limits[i].dram_speed_mts = clk_table->entries[i].memclk_mhz * 2; + + clock_limits[i].dispclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].dispclk_mhz; + clock_limits[i].dppclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].dppclk_mhz; + clock_limits[i].dram_bw_per_chan_gbps = dcn3_01_soc.clock_limits[closest_clk_lvl].dram_bw_per_chan_gbps; + clock_limits[i].dscclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].dscclk_mhz; + clock_limits[i].dtbclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].dtbclk_mhz; + clock_limits[i].phyclk_d18_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].phyclk_d18_mhz; + clock_limits[i].phyclk_mhz = dcn3_01_soc.clock_limits[closest_clk_lvl].phyclk_mhz; + } + for (i = 0; i < clk_table->num_entries; i++) + dcn3_01_soc.clock_limits[i] = clock_limits[i]; + if (clk_table->num_entries) { + dcn3_01_soc.num_states = clk_table->num_entries; + /* duplicate last level */ + dcn3_01_soc.clock_limits[dcn3_01_soc.num_states] = dcn3_01_soc.clock_limits[dcn3_01_soc.num_states - 1]; + dcn3_01_soc.clock_limits[dcn3_01_soc.num_states].state = dcn3_01_soc.num_states; + } } -} -static void dcn301_update_bw_bounding_box(struct dc *dc, struct clk_bw_params *bw_params) -{ dcn3_01_soc.dispclk_dppclk_vco_speed_mhz = dc->clk_mgr->dentist_vco_freq_khz / 1000.0; dc->dml.soc.dispclk_dppclk_vco_speed_mhz = dc->clk_mgr->dentist_vco_freq_khz / 1000.0; + + dml_init_instance(&dc->dml, &dcn3_01_soc, &dcn3_01_ip, DML_PROJECT_DCN30); } static struct resource_funcs dcn301_res_pool_funcs = { @@ -1862,9 +1863,8 @@ static bool dcn301_resource_construct( goto create_fail; } - /* PP Lib and SMU interfaces */ - pool->base.pp_smu = dcn301_pp_smu_create(ctx); init_soc_bounding_box(dc, pool); + if (!dc->debug.disable_pplib_wm_range && pool->base.pp_smu->nv_funcs.set_wm_ranges) set_wm_ranges(pool->base.pp_smu, &dcn3_01_soc); -- cgit v1.2.3 From 24f99d2b21db3be1da2800470fecfa583a181929 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Fri, 20 Nov 2020 20:18:55 +0000 Subject: drm/amd/display: add cursor FB size check This patch expands the cursor checks added in "drm/amd/display: add basic atomic check for cursor plane" to also include a FB size check. Without this patch, setting a FB smaller than max_cursor_size with an invalid width would result in amdgpu error messages and a fallback to a 64-byte width: [drm:hubp1_cursor_set_attributes [amdgpu]] *ERROR* Invalid cursor pitch of 100. Only 64/128/256 is supported on DCN. Note that DC uses the word "pitch" when actually checking the FB width. Indeed, the function handle_cursor_update does this: attributes.pitch = attributes.width; In my tests, the cursor FB actually had a pitch of 512 bytes. Reviewed-by: Alex Deucher Signed-off-by: Simon Ser Reported-by: Pierre-Loup A. Griffais Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 63d9bfaa113b..c7322d3e0b0a 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8982,6 +8982,28 @@ static int dm_update_plane_state(struct dc *dc, return -EINVAL; } + if (new_plane_state->fb) { + if (new_plane_state->fb->width > new_acrtc->max_cursor_width || + new_plane_state->fb->height > new_acrtc->max_cursor_height) { + DRM_DEBUG_ATOMIC("Bad cursor FB size %dx%d\n", + new_plane_state->fb->width, + new_plane_state->fb->height); + return -EINVAL; + } + + switch (new_plane_state->fb->width) { + case 64: + case 128: + case 256: + /* FB width is supported by cursor plane */ + break; + default: + DRM_DEBUG_ATOMIC("Bad cursor FB width %d\n", + new_plane_state->fb->width); + return -EINVAL; + } + } + return 0; } -- cgit v1.2.3 From 5f581248159a005f194ef27aa44ad82d00ba7622 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Fri, 20 Nov 2020 20:18:57 +0000 Subject: drm/amd/display: disallow cropping for cursor plane Looking at handle_cursor_update, it doesn't seem like src_{x,y,w,h} are picked up by DC. I also tried to change these parameters via a test KMS client, and amdgpu ignored them. Instead of displaying the wrong result, reject the atomic commit. Reviewed-by: Alex Deucher Signed-off-by: Simon Ser Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index c7322d3e0b0a..a886761b3280 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8982,6 +8982,11 @@ static int dm_update_plane_state(struct dc *dc, return -EINVAL; } + if (new_plane_state->src_x != 0 || new_plane_state->src_y != 0) { + DRM_DEBUG_ATOMIC("Cropping not supported for cursor plane\n"); + return -EINVAL; + } + if (new_plane_state->fb) { if (new_plane_state->fb->width > new_acrtc->max_cursor_width || new_plane_state->fb->height > new_acrtc->max_cursor_height) { @@ -8990,6 +8995,11 @@ static int dm_update_plane_state(struct dc *dc, new_plane_state->fb->height); return -EINVAL; } + if (new_plane_state->src_w != new_plane_state->fb->width << 16 || + new_plane_state->src_h != new_plane_state->fb->height << 16) { + DRM_DEBUG_ATOMIC("Cropping not supported for cursor plane\n"); + return -EINVAL; + } switch (new_plane_state->fb->width) { case 64: -- cgit v1.2.3 From 12f4849a1cfd69f3c37cca042f2e9c512f923741 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Fri, 20 Nov 2020 20:18:59 +0000 Subject: drm/amd/display: check cursor scaling Don't allow user-space to set different scaling parameters for the cursor plane and for the primary plane. Because of DCE/DCN design, it's not possible to have a mismatch. The old check in dm_update_plane_state is superseded by this new check. Reviewed-by: Alex Deucher Signed-off-by: Simon Ser Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 51 +++++++++++++++++++---- 1 file changed, 44 insertions(+), 7 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index a886761b3280..b27d17714ebd 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8975,13 +8975,6 @@ static int dm_update_plane_state(struct dc *dc, new_acrtc = to_amdgpu_crtc(new_plane_crtc); - if ((new_plane_state->crtc_w > new_acrtc->max_cursor_width) || - (new_plane_state->crtc_h > new_acrtc->max_cursor_height)) { - DRM_DEBUG_ATOMIC("Bad cursor size %d x %d\n", - new_plane_state->crtc_w, new_plane_state->crtc_h); - return -EINVAL; - } - if (new_plane_state->src_x != 0 || new_plane_state->src_y != 0) { DRM_DEBUG_ATOMIC("Cropping not supported for cursor plane\n"); return -EINVAL; @@ -9135,6 +9128,43 @@ static int dm_update_plane_state(struct dc *dc, return ret; } +static int dm_check_crtc_cursor(struct drm_atomic_state *state, + struct drm_crtc *crtc, + struct drm_crtc_state *new_crtc_state) +{ + struct drm_plane_state *new_cursor_state, *new_primary_state; + int cursor_scale_w, cursor_scale_h, primary_scale_w, primary_scale_h; + + /* On DCE and DCN there is no dedicated hardware cursor plane. We get a + * cursor per pipe but it's going to inherit the scaling and + * positioning from the underlying pipe. Check the cursor plane's + * blending properties match the primary plane's. */ + + new_cursor_state = drm_atomic_get_new_plane_state(state, crtc->cursor); + new_primary_state = drm_atomic_get_new_plane_state(state, crtc->primary); + if (!new_cursor_state || !new_primary_state || !new_cursor_state->fb) { + return 0; + } + + cursor_scale_w = new_cursor_state->crtc_w * 1000 / + (new_cursor_state->src_w >> 16); + cursor_scale_h = new_cursor_state->crtc_h * 1000 / + (new_cursor_state->src_h >> 16); + + primary_scale_w = new_primary_state->crtc_w * 1000 / + (new_primary_state->src_w >> 16); + primary_scale_h = new_primary_state->crtc_h * 1000 / + (new_primary_state->src_h >> 16); + + if (cursor_scale_w != primary_scale_w || + cursor_scale_h != primary_scale_h) { + DRM_DEBUG_ATOMIC("Cursor plane scaling doesn't match primary plane\n"); + return -EINVAL; + } + + return 0; +} + #if defined(CONFIG_DRM_AMD_DC_DCN) static int add_affected_mst_dsc_crtcs(struct drm_atomic_state *state, struct drm_crtc *crtc) { @@ -9347,6 +9377,13 @@ static int amdgpu_dm_atomic_check(struct drm_device *dev, if (ret) goto fail; + /* Check cursor planes scaling */ + for_each_new_crtc_in_state(state, crtc, new_crtc_state, i) { + ret = dm_check_crtc_cursor(state, crtc, new_crtc_state); + if (ret) + goto fail; + } + if (state->legacy_cursor_update) { /* * This is a fast cursor update coming from the plane update -- cgit v1.2.3 From 1347385fe18753b3eb8ee76fdaebea392b88b323 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Fri, 20 Nov 2020 20:19:00 +0000 Subject: drm/amd/display: don't expose rotation prop for cursor plane Setting any rotation on the cursor plane is ignored by amdgpu. Because of DCE/DCN design, it's not possible to rotate the cursor. Instead of displaying the wrong result, stop advertising the rotation property for the cursor plane. Now that we check all cursor plane properties in amdgpu_dm_atomic_check, remove the TODO. Reviewed-by: Alex Deucher Signed-off-by: Simon Ser Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index b27d17714ebd..08539f431586 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -6604,7 +6604,8 @@ static int amdgpu_dm_plane_init(struct amdgpu_display_manager *dm, DRM_MODE_ROTATE_0 | DRM_MODE_ROTATE_90 | DRM_MODE_ROTATE_180 | DRM_MODE_ROTATE_270; - if (dm->adev->asic_type >= CHIP_BONAIRE) + if (dm->adev->asic_type >= CHIP_BONAIRE && + plane->type != DRM_PLANE_TYPE_CURSOR) drm_plane_create_rotation_property(plane, DRM_MODE_ROTATE_0, supported_rotations); @@ -8967,7 +8968,6 @@ static int dm_update_plane_state(struct dc *dc, dm_new_plane_state = to_dm_plane_state(new_plane_state); dm_old_plane_state = to_dm_plane_state(old_plane_state); - /*TODO Implement better atomic check for cursor plane */ if (plane->type == DRM_PLANE_TYPE_CURSOR) { if (!enable || !new_plane_crtc || drm_atomic_plane_disabling(plane->state, new_plane_state)) -- cgit v1.2.3 From 3f16ae825697fe317c14e97f80c2ad487b55b3e9 Mon Sep 17 00:00:00 2001 From: Aurabindo Pillai Date: Thu, 26 Nov 2020 09:31:05 -0500 Subject: drm/amd/display: Clear dc remote sinks on MST disconnect [Why&How] Recent changes to upstream mst code remove the callback which cleared the internal state for mst. Move the missing functionality that was previously called through the destroy call back for mst connector destroy Signed-off-by: Aurabindo Pillai Signed-off-by: Eryk Brol Reviewed-by: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- .../drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c | 22 ++++++++++++++++++++-- drivers/gpu/drm/amd/display/dc/dm_helpers.h | 2 +- 2 files changed, 21 insertions(+), 3 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c index b7d7ec3ba00d..d8b0f07deaf2 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c @@ -418,9 +418,10 @@ bool dm_helpers_dp_mst_start_top_mgr( void dm_helpers_dp_mst_stop_top_mgr( struct dc_context *ctx, - const struct dc_link *link) + struct dc_link *link) { struct amdgpu_dm_connector *aconnector = link->priv; + uint8_t i; if (!aconnector) { DRM_ERROR("Failed to find connector for link!"); @@ -430,8 +431,25 @@ void dm_helpers_dp_mst_stop_top_mgr( DRM_INFO("DM_MST: stopping TM on aconnector: %p [id: %d]\n", aconnector, aconnector->base.base.id); - if (aconnector->mst_mgr.mst_state == true) + if (aconnector->mst_mgr.mst_state == true) { drm_dp_mst_topology_mgr_set_mst(&aconnector->mst_mgr, false); + + for (i = 0; i < MAX_SINKS_PER_LINK; i++) { + if (link->remote_sinks[i] == NULL) + continue; + + if (link->remote_sinks[i]->sink_signal == + SIGNAL_TYPE_DISPLAY_PORT_MST) { + dc_link_remove_remote_sink(link, link->remote_sinks[i]); + + if (aconnector->dc_sink) { + dc_sink_release(aconnector->dc_sink); + aconnector->dc_sink = NULL; + aconnector->dc_link->cur_link_settings.lane_count = 0; + } + } + } + } } bool dm_helpers_dp_read_dpcd( diff --git a/drivers/gpu/drm/amd/display/dc/dm_helpers.h b/drivers/gpu/drm/amd/display/dc/dm_helpers.h index b2cd8491c707..07e349b1067b 100644 --- a/drivers/gpu/drm/amd/display/dc/dm_helpers.h +++ b/drivers/gpu/drm/amd/display/dc/dm_helpers.h @@ -113,7 +113,7 @@ bool dm_helpers_dp_mst_start_top_mgr( void dm_helpers_dp_mst_stop_top_mgr( struct dc_context *ctx, - const struct dc_link *link); + struct dc_link *link); /** * OS specific aux read callback. */ -- cgit v1.2.3 From 3c4d55c9b9becedd8d31a7c96783a364533713ab Mon Sep 17 00:00:00 2001 From: Aurabindo Pillai Date: Thu, 26 Nov 2020 16:45:59 -0500 Subject: drm/amd/display: turn DPMS off on connector unplug [Why&How] Set dpms off on the connector that was unplugged, for the side effect of releasing some references held through deallocation of MST payload. This is the expected behaviour for non MST devices as well. Signed-off-by: Aurabindo Pillai Signed-off-by: Eryk Brol Reviewed-by: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 32 ++++++++++++++++++++++- drivers/gpu/drm/amd/display/dc/core/dc.c | 13 +++++++++ drivers/gpu/drm/amd/display/dc/dc_stream.h | 1 + 3 files changed, 45 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 08539f431586..f20432c2c4d7 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -1984,6 +1984,33 @@ cleanup: return; } +static void dm_set_dpms_off(struct dc_link *link) +{ + struct dc_stream_state *stream_state; + struct amdgpu_dm_connector *aconnector = link->priv; + struct amdgpu_device *adev = drm_to_adev(aconnector->base.dev); + struct dc_stream_update stream_update; + bool dpms_off = true; + + memset(&stream_update, 0, sizeof(stream_update)); + stream_update.dpms_off = &dpms_off; + + mutex_lock(&adev->dm.dc_lock); + stream_state = dc_stream_find_from_link(link); + + if (stream_state == NULL) { + DRM_DEBUG_DRIVER("Error finding stream state associated with link!\n"); + mutex_unlock(&adev->dm.dc_lock); + return; + } + + stream_update.stream = stream_state; + dc_commit_updates_for_stream(stream_state->ctx->dc, NULL, 0, + stream_state, &stream_update, + stream_state->ctx->dc->current_state); + mutex_unlock(&adev->dm.dc_lock); +} + static int dm_resume(void *handle) { struct amdgpu_device *adev = handle; @@ -2434,8 +2461,11 @@ static void handle_hpd_irq(void *param) drm_kms_helper_hotplug_event(dev); } else if (dc_link_detect(aconnector->dc_link, DETECT_REASON_HPD)) { - amdgpu_dm_update_connector_after_detect(aconnector); + if (new_connection_type == dc_connection_none && + aconnector->dc_link->type == dc_connection_none) + dm_set_dpms_off(aconnector->dc_link); + amdgpu_dm_update_connector_after_detect(aconnector); drm_modeset_lock_all(dev); dm_restore_drm_connector_state(dev, connector); diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c index 903353389edb..58eb0d69873a 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc.c @@ -2798,6 +2798,19 @@ struct dc_stream_state *dc_get_stream_at_index(struct dc *dc, uint8_t i) return NULL; } +struct dc_stream_state *dc_stream_find_from_link(const struct dc_link *link) +{ + uint8_t i; + struct dc_context *ctx = link->ctx; + + for (i = 0; i < ctx->dc->current_state->stream_count; i++) { + if (ctx->dc->current_state->streams[i]->link == link) + return ctx->dc->current_state->streams[i]; + } + + return NULL; +} + enum dc_irq_source dc_interrupt_to_irq_source( struct dc *dc, uint32_t src_id, diff --git a/drivers/gpu/drm/amd/display/dc/dc_stream.h b/drivers/gpu/drm/amd/display/dc/dc_stream.h index bf090afc2f70..b7910976b81a 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_stream.h +++ b/drivers/gpu/drm/amd/display/dc/dc_stream.h @@ -292,6 +292,7 @@ void dc_stream_log(const struct dc *dc, const struct dc_stream_state *stream); uint8_t dc_get_current_stream_count(struct dc *dc); struct dc_stream_state *dc_get_stream_at_index(struct dc *dc, uint8_t i); +struct dc_stream_state *dc_stream_find_from_link(const struct dc_link *link); /* * Return the current frame counter. -- cgit v1.2.3 From bc1e089476dcad26a27a2714baa7169774f89d51 Mon Sep 17 00:00:00 2001 From: Eric Bernstein Date: Thu, 12 Nov 2020 16:18:48 -0500 Subject: drm/amd/display: Revert update clk_mgr for vg This reverts commit 2208f39c750972ad3796b4353ccf9f7c8636931c. It caused a regression in internal FPGA tests. Signed-off-by: Eric Bernstein Reviewed-by: Eric Yang Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c | 8 ++++---- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h | 10 ---------- 2 files changed, 4 insertions(+), 14 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c index 9a8e66bba9c0..98cbb0ac095c 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c @@ -32,9 +32,9 @@ // For dcn20_update_clocks_update_dpp_dto #include "dcn20/dcn20_clk_mgr.h" - - #include "vg_clk_mgr.h" + +#include "dcn301_smu.h" #include "reg_helper.h" #include "core_types.h" #include "dm_helpers.h" @@ -631,7 +631,7 @@ static unsigned int find_dcfclk_for_voltage(const struct vg_dpm_clocks *clock_ta return 0; } -void vg_clk_mgr_helper_populate_bw_params( +static void vg_clk_mgr_helper_populate_bw_params( struct clk_mgr_internal *clk_mgr, struct integrated_info *bios_info, const struct vg_dpm_clocks *clock_table) @@ -709,7 +709,7 @@ static struct vg_dpm_clocks dummy_clocks = { static struct watermarks dummy_wms = { 0 }; -void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, +static void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, struct smu_dpm_clks *smu_dpm_clks) { struct vg_dpm_clocks *table = smu_dpm_clks->dpm_clks; diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h index b5115b3123a1..80497df20ba7 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h @@ -39,15 +39,5 @@ void vg_clk_mgr_construct(struct dc_context *ctx, void vg_clk_mgr_destroy(struct clk_mgr_internal *clk_mgr); -#include "dcn301_smu.h" void vg_notify_wm_ranges(struct clk_mgr *clk_mgr_base); - -void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, - struct smu_dpm_clks *smu_dpm_clks); - -void vg_clk_mgr_helper_populate_bw_params( - struct clk_mgr_internal *clk_mgr, - struct integrated_info *bios_info, - const struct vg_dpm_clocks *clock_table); - #endif //__VG_CLK_MGR_H__ -- cgit v1.2.3 From 00b0ac67811b96d32940fa705fb1405139bb3aab Mon Sep 17 00:00:00 2001 From: Jacky Liao Date: Fri, 13 Nov 2020 13:13:27 -0500 Subject: drm/amd/display: Add HDR3DLUT and SHAPER memory shutdown support [Why] The HDR3DLUT and SHAPER memory blocks should be powered down when they're not in use. This will reduce power consumption. [How] 1. Write to HDR3DLUT_MEM_PWR_FORCE to put memory to shutdown when HDR3DLUT is not used. 2. Write to SHAPER_MEM_PWR_FORCE to put memory to shutdown when SHAPER is not used. Signed-off-by: Jacky Liao Reviewed-by: Eric Yang Acked-by: Yongqiang Sun Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c | 38 ++++++++++++++++++++++++ drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h | 14 ++++++++- 2 files changed, 51 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c index 052bab3e5e8e..6e864b1a95c4 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.c @@ -510,6 +510,32 @@ static void dpp3_power_on_blnd_lut( } } +static void dpp3_power_on_hdr3dlut( + struct dpp *dpp_base, + bool power_on) +{ + struct dcn3_dpp *dpp = TO_DCN30_DPP(dpp_base); + + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) { + REG_UPDATE(CM_MEM_PWR_CTRL2, HDR3DLUT_MEM_PWR_FORCE, power_on ? 0 : 3); + if (power_on) + REG_WAIT(CM_MEM_PWR_STATUS2, HDR3DLUT_MEM_PWR_STATE, 0, 1, 5); + } +} + +static void dpp3_power_on_shaper( + struct dpp *dpp_base, + bool power_on) +{ + struct dcn3_dpp *dpp = TO_DCN30_DPP(dpp_base); + + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) { + REG_UPDATE(CM_MEM_PWR_CTRL2, SHAPER_MEM_PWR_FORCE, power_on ? 0 : 3); + if (power_on) + REG_WAIT(CM_MEM_PWR_STATUS2, SHAPER_MEM_PWR_STATE, 0, 1, 5); + } +} + static void dpp3_configure_blnd_lut( struct dpp *dpp_base, bool is_ram_a) @@ -1095,8 +1121,14 @@ bool dpp3_program_shaper( if (params == NULL) { REG_SET(CM_SHAPER_CONTROL, 0, CM_SHAPER_LUT_MODE, 0); + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) + dpp3_power_on_shaper(dpp_base, false); return false; } + + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) + dpp3_power_on_shaper(dpp_base, true); + current_mode = dpp3_get_shaper_current(dpp_base); if (current_mode == LUT_BYPASS || current_mode == LUT_RAM_A) @@ -1285,8 +1317,14 @@ bool dpp3_program_3dlut( if (params == NULL) { dpp3_set_3dlut_mode(dpp_base, LUT_BYPASS, false, false); + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) + dpp3_power_on_hdr3dlut(dpp_base, false); return false; } + + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.cm) + dpp3_power_on_hdr3dlut(dpp_base, true); + mode = get3dlut_config(dpp_base, &is_17x17x17, &is_12bits_color_channel); if (mode == LUT_BYPASS || mode == LUT_RAM_B) diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h index 2ae5e1f93dd4..6415aaa01d24 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h @@ -161,6 +161,8 @@ TF_REG_LIST_DCN20_COMMON(id), \ SRI(CM_BLNDGAM_CONTROL, CM, id), \ SRI(CM_SHAPER_LUT_DATA, CM, id),\ + SRI(CM_MEM_PWR_CTRL2, CM, id), \ + SRI(CM_MEM_PWR_STATUS2, CM, id), \ SRI(CM_BLNDGAM_RAMA_START_SLOPE_CNTL_B, CM, id),\ SRI(CM_BLNDGAM_RAMA_START_SLOPE_CNTL_G, CM, id),\ SRI(CM_BLNDGAM_RAMA_START_SLOPE_CNTL_R, CM, id),\ @@ -344,6 +346,10 @@ #define DPP_REG_LIST_SH_MASK_DCN30_UPDATED(mask_sh)\ TF_SF(CM0_CM_MEM_PWR_STATUS, BLNDGAM_MEM_PWR_STATE, mask_sh), \ + TF_SF(CM0_CM_MEM_PWR_CTRL2, HDR3DLUT_MEM_PWR_FORCE, mask_sh),\ + TF_SF(CM0_CM_MEM_PWR_CTRL2, SHAPER_MEM_PWR_FORCE, mask_sh),\ + TF_SF(CM0_CM_MEM_PWR_STATUS2, HDR3DLUT_MEM_PWR_STATE, mask_sh),\ + TF_SF(CM0_CM_MEM_PWR_STATUS2, SHAPER_MEM_PWR_STATE, mask_sh),\ TF_SF(CM0_CM_BLNDGAM_CONTROL, CM_BLNDGAM_MODE, mask_sh), \ TF_SF(CM0_CM_BLNDGAM_CONTROL, CM_BLNDGAM_MODE_CURRENT, mask_sh), \ TF_SF(CM0_CM_BLNDGAM_CONTROL, CM_BLNDGAM_SELECT_CURRENT, mask_sh), \ @@ -387,6 +393,8 @@ type CM_BIAS_CR_R;\ type GAMCOR_MEM_PWR_DIS; \ type GAMCOR_MEM_PWR_FORCE; \ + type HDR3DLUT_MEM_PWR_FORCE; \ + type SHAPER_MEM_PWR_FORCE; \ type PRE_DEGAM_MODE;\ type PRE_DEGAM_SELECT;\ type CNVC_ALPHA_PLANE_ENABLE; \ @@ -448,7 +456,9 @@ type CM_BLNDGAM_SELECT_CURRENT; \ type CM_BLNDGAM_SELECT; \ type GAMCOR_MEM_PWR_STATE; \ - type BLNDGAM_MEM_PWR_STATE + type BLNDGAM_MEM_PWR_STATE; \ + type HDR3DLUT_MEM_PWR_STATE; \ + type SHAPER_MEM_PWR_STATE struct dcn3_dpp_shift { DPP_REG_FIELD_LIST_DCN3(uint8_t); @@ -461,6 +471,8 @@ struct dcn3_dpp_mask { #define DPP_DCN3_REG_VARIABLE_LIST_COMMON \ DPP_DCN2_REG_VARIABLE_LIST; \ uint32_t CM_MEM_PWR_STATUS;\ + uint32_t CM_MEM_PWR_STATUS2;\ + uint32_t CM_MEM_PWR_CTRL2;\ uint32_t CM_DEALPHA;\ uint32_t CM_BIAS_CR_R;\ uint32_t CM_BIAS_Y_G_CB_B;\ -- cgit v1.2.3 From 901c1ec05ef277ce9d43cb806a225b28b3efe89a Mon Sep 17 00:00:00 2001 From: Sung Lee Date: Fri, 13 Nov 2020 13:34:55 -0500 Subject: drm/amd/display: Update dram_clock_change_latency for DCN2.1 [WHY] dram clock change latencies get updated using ddr4 latency table, but does that update does not happen before validation. This value should not be the default and should be number received from df for better mode support. This may cause a PState hang on high refresh panels with short vblanks such as on 1080p 360hz or 300hz panels. [HOW] Update latency from 23.84 to 11.72. Signed-off-by: Sung Lee Reviewed-by: Tony Cheng Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c index 1c88d2edd381..b000b43a820d 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c @@ -296,7 +296,7 @@ struct _vcs_dpi_soc_bounding_box_st dcn2_1_soc = { .num_banks = 8, .num_chans = 4, .vmm_page_size_bytes = 4096, - .dram_clock_change_latency_us = 23.84, + .dram_clock_change_latency_us = 11.72, .return_bus_width_bytes = 64, .dispclk_dppclk_vco_speed_mhz = 3600, .xfc_bus_transport_time_us = 4, -- cgit v1.2.3 From 079204508ec0cd32a66c5ca8b9f977383355b181 Mon Sep 17 00:00:00 2001 From: Joshua Aberback Date: Tue, 17 Nov 2020 11:27:33 -0500 Subject: drm/amd/display: Check link_active instead of lane_settings != unknown [Why] enable_link_dp_mst checks that cur_link_settings != unknown to determine that the link is already enabled, to skip redundant enablement calls for multiple streams on the same link. During dc_reinitialize_hardware, cur_link_settings on previously-active links is not cleared, which blocks MST links from being re-enabled after a reinitialization. [How] - check for link_status->link_active instead, as it's the real intent - clear cur_link_settings when we clear link_active Signed-off-by: Joshua Aberback Reviewed-by: Wenjing Liu Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 2 +- drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index 4a897c326aab..a9c52657eb4b 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -1738,7 +1738,7 @@ static enum dc_status enable_link_dp_mst( /* sink signal type after MST branch is MST. Multiple MST sinks * share one link. Link DP PHY is enable or training only once. */ - if (link->cur_link_settings.lane_count != LANE_COUNT_UNKNOWN) + if (link->link_status.link_active) return DC_OK; /* clear payload table */ diff --git a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c index 90c85b3e859b..4c230f1de9a3 100644 --- a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c +++ b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c @@ -1530,6 +1530,8 @@ static void power_down_encoders(struct dc *dc) dc->links[i]->link_enc, signal); dc->links[i]->link_status.link_active = false; + memset(&dc->links[i]->cur_link_settings, 0, + sizeof(dc->links[i]->cur_link_settings)); } } -- cgit v1.2.3 From 99349a8aeda7a044fc5850924bc3b57c306a1553 Mon Sep 17 00:00:00 2001 From: Brandon Syu Date: Thu, 12 Nov 2020 15:35:52 +0800 Subject: drm/amd/display: Init clock value by current vbios CLKs [Why] While booting into OS, driver updates DPP/DISP CLKs. But init clock value is zero which is invalid. [How] Get current clocks value to update init clocks. To avoid underflow. Signed-off-by: Brandon Syu Reviewed-by: Tony Cheng Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index 458dab9e813b..fe6dc1e68e60 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -186,8 +186,17 @@ void rn_update_clocks(struct clk_mgr *clk_mgr_base, if (new_clocks->dppclk_khz < 100000 && new_clocks->dppclk_khz > 0) new_clocks->dppclk_khz = 100000; - if (should_set_clock(safe_to_lower, new_clocks->dppclk_khz, clk_mgr->base.clks.dppclk_khz)) { - if (clk_mgr->base.clks.dppclk_khz > new_clocks->dppclk_khz) + /* + * Temporally ignore thew 0 cases for disp and dpp clks. + * We may have a new feature that requires 0 clks in the future. + */ + if (new_clocks->dppclk_khz == 0 || new_clocks->dispclk_khz == 0) { + new_clocks->dppclk_khz = clk_mgr_base->clks.dppclk_khz; + new_clocks->dispclk_khz = clk_mgr_base->clks.dispclk_khz; + } + + if (should_set_clock(safe_to_lower, new_clocks->dppclk_khz, clk_mgr_base->clks.dppclk_khz)) { + if (clk_mgr_base->clks.dppclk_khz > new_clocks->dppclk_khz) dpp_clock_lowered = true; clk_mgr_base->clks.dppclk_khz = new_clocks->dppclk_khz; update_dppclk = true; -- cgit v1.2.3 From d0274aba24bf98aad04beb917dea4fbe45659a79 Mon Sep 17 00:00:00 2001 From: Jacky Liao Date: Mon, 16 Nov 2020 17:04:35 -0500 Subject: drm/amd/display: Add DSCL memory low power support [Why] The DSCL memory blocks should be powered down when they're not in use. This will reduce power consumption. [How] 1. Write to DSCL_MEM_PWR_FORCE to put memory to shutdown when DSCL is not used. 2. Added a debug option to allow this behaviour to be turned off Signed-off-by: Jacky Liao Reviewed-by: Eric Yang Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 1 + drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp.h | 8 ++++++++ .../gpu/drm/amd/display/dc/dcn10/dcn10_dpp_dscl.c | 24 +++++++++++++++++++++- drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dpp.h | 6 ++---- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h | 5 ++++- 5 files changed, 38 insertions(+), 6 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 68a192e64418..7400b0b449eb 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -422,6 +422,7 @@ union mem_low_power_enable_options { struct { bool i2c: 1; bool dmcu: 1; + bool dscl: 1; bool cm: 1; bool mpc: 1; bool optc: 1; diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp.h b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp.h index 2edf566b3a72..9a1f40eb5c47 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp.h +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp.h @@ -51,6 +51,8 @@ SRI(CM_GAMUT_REMAP_C33_C34, CM, id),\ SRI(DSCL_EXT_OVERSCAN_LEFT_RIGHT, DSCL, id), \ SRI(DSCL_EXT_OVERSCAN_TOP_BOTTOM, DSCL, id), \ + SRI(DSCL_MEM_PWR_STATUS, DSCL, id), \ + SRI(DSCL_MEM_PWR_CTRL, DSCL, id), \ SRI(OTG_H_BLANK, DSCL, id), \ SRI(OTG_V_BLANK, DSCL, id), \ SRI(SCL_MODE, DSCL, id), \ @@ -252,6 +254,8 @@ TF_SF(DSCL0_SCL_VERT_FILTER_INIT_BOT_C, SCL_V_INIT_INT_BOT_C, mask_sh),\ TF_SF(DSCL0_SCL_MODE, SCL_CHROMA_COEF_MODE, mask_sh),\ TF_SF(DSCL0_SCL_MODE, SCL_COEF_RAM_SELECT_CURRENT, mask_sh), \ + TF_SF(DSCL0_DSCL_MEM_PWR_CTRL, LUT_MEM_PWR_FORCE, mask_sh), \ + TF_SF(DSCL0_DSCL_MEM_PWR_STATUS, LUT_MEM_PWR_STATE, mask_sh), \ TF_SF(CM0_CM_ICSC_CONTROL, CM_ICSC_MODE, mask_sh), \ TF_SF(CM0_CM_ICSC_C11_C12, CM_ICSC_C11, mask_sh), \ TF_SF(CM0_CM_ICSC_C11_C12, CM_ICSC_C12, mask_sh), \ @@ -536,6 +540,8 @@ type SCL_V_INIT_INT_BOT_C; \ type SCL_CHROMA_COEF_MODE; \ type SCL_COEF_RAM_SELECT_CURRENT; \ + type LUT_MEM_PWR_FORCE; \ + type LUT_MEM_PWR_STATE; \ type CM_GAMUT_REMAP_MODE; \ type CM_GAMUT_REMAP_C11; \ type CM_GAMUT_REMAP_C12; \ @@ -1096,6 +1102,8 @@ struct dcn_dpp_mask { uint32_t DSCL_EXT_OVERSCAN_TOP_BOTTOM; \ uint32_t OTG_H_BLANK; \ uint32_t OTG_V_BLANK; \ + uint32_t DSCL_MEM_PWR_CTRL; \ + uint32_t DSCL_MEM_PWR_STATUS; \ uint32_t SCL_MODE; \ uint32_t LB_DATA_FORMAT; \ uint32_t LB_MEMORY_CTRL; \ diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp_dscl.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp_dscl.c index 878b53d85694..efa86d5c6847 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp_dscl.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_dpp_dscl.c @@ -198,6 +198,20 @@ static enum dscl_mode_sel dpp1_dscl_get_dscl_mode( return DSCL_MODE_SCALING_420_YCBCR_ENABLE; } +static void dpp1_power_on_dscl( + struct dpp *dpp_base, + bool power_on) +{ + struct dcn10_dpp *dpp = TO_DCN10_DPP(dpp_base); + + if (dpp->tf_regs->DSCL_MEM_PWR_CTRL) { + REG_UPDATE(DSCL_MEM_PWR_CTRL, LUT_MEM_PWR_FORCE, power_on ? 0 : 3); + if (power_on) + REG_WAIT(DSCL_MEM_PWR_STATUS, LUT_MEM_PWR_STATE, 0, 1, 5); + } +} + + static void dpp1_dscl_set_lb( struct dcn10_dpp *dpp, const struct line_buffer_params *lb_params, @@ -678,6 +692,11 @@ void dpp1_dscl_set_scaler_manual_scale( dpp->scl_data = *scl_data; + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.dscl) { + if (dscl_mode != DSCL_MODE_DSCL_BYPASS) + dpp1_power_on_dscl(dpp_base, true); + } + /* Autocal off */ REG_SET_3(DSCL_AUTOCAL, 0, AUTOCAL_MODE, AUTOCAL_MODE_OFF, @@ -697,8 +716,11 @@ void dpp1_dscl_set_scaler_manual_scale( /* SCL mode */ REG_UPDATE(SCL_MODE, DSCL_MODE, dscl_mode); - if (dscl_mode == DSCL_MODE_DSCL_BYPASS) + if (dscl_mode == DSCL_MODE_DSCL_BYPASS) { + if (dpp_base->ctx->dc->debug.enable_mem_low_power.bits.dscl) + dpp1_power_on_dscl(dpp_base, false); return; + } /* LB */ lb_config = dpp1_dscl_find_lb_memory_config(dpp, scl_data); diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dpp.h b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dpp.h index 27610251c57f..e735363d0051 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dpp.h +++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dpp.h @@ -632,8 +632,7 @@ type CUR0_PIX_INV_MODE; \ type CUR0_PIXEL_ALPHA_MOD_EN; \ type CUR0_ROM_EN;\ - type OBUF_MEM_PWR_FORCE;\ - type LUT_MEM_PWR_FORCE + type OBUF_MEM_PWR_FORCE struct dcn2_dpp_shift { @@ -659,8 +658,7 @@ struct dcn2_dpp_mask { uint32_t COLOR_KEYER_RED; \ uint32_t COLOR_KEYER_GREEN; \ uint32_t COLOR_KEYER_BLUE; \ - uint32_t OBUF_MEM_PWR_CTRL; \ - uint32_t DSCL_MEM_PWR_CTRL + uint32_t OBUF_MEM_PWR_CTRL #define DPP_DCN2_REG_VARIABLE_LIST_CM_APPEND \ uint32_t CM_GAMUT_REMAP_B_C11_C12; \ diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h index 6415aaa01d24..3fa86cd090a0 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_dpp.h @@ -163,6 +163,8 @@ SRI(CM_SHAPER_LUT_DATA, CM, id),\ SRI(CM_MEM_PWR_CTRL2, CM, id), \ SRI(CM_MEM_PWR_STATUS2, CM, id), \ + SRI(DSCL_MEM_PWR_STATUS, DSCL, id), \ + SRI(DSCL_MEM_PWR_CTRL, DSCL, id), \ SRI(CM_BLNDGAM_RAMA_START_SLOPE_CNTL_B, CM, id),\ SRI(CM_BLNDGAM_RAMA_START_SLOPE_CNTL_G, CM, id),\ SRI(CM_BLNDGAM_RAMA_START_SLOPE_CNTL_R, CM, id),\ @@ -342,7 +344,8 @@ TF_SF(CNVC_CUR0_CURSOR0_CONTROL, CUR0_PIXEL_ALPHA_MOD_EN, mask_sh), \ TF_SF(CNVC_CUR0_CURSOR0_CONTROL, CUR0_ROM_EN, mask_sh),\ TF_SF(DSCL0_OBUF_MEM_PWR_CTRL, OBUF_MEM_PWR_FORCE, mask_sh),\ - TF_SF(DSCL0_DSCL_MEM_PWR_CTRL, LUT_MEM_PWR_FORCE, mask_sh) + TF_SF(DSCL0_DSCL_MEM_PWR_CTRL, LUT_MEM_PWR_FORCE, mask_sh),\ + TF_SF(DSCL0_DSCL_MEM_PWR_STATUS, LUT_MEM_PWR_STATE, mask_sh) #define DPP_REG_LIST_SH_MASK_DCN30_UPDATED(mask_sh)\ TF_SF(CM0_CM_MEM_PWR_STATUS, BLNDGAM_MEM_PWR_STATE, mask_sh), \ -- cgit v1.2.3 From 115a385c08d8d1874b3496d134cba0cc218f0fda Mon Sep 17 00:00:00 2001 From: Eryk Brol Date: Thu, 19 Nov 2020 16:48:57 -0500 Subject: drm/amd/display: Do full modeset when DSC debugfs is changed [Why] Whenever DSC parameters are changed we need to perform full modeset to commit DSC changes to DC. [How] If dsc_force_changed is set, need to set mode_changed on new CRTC state Signed-off-by: Eryk Brol Signed-off-by: Mikita Lipski Reviewed-by: Mikita Lipski Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 3 +++ 1 file changed, 3 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index f20432c2c4d7..7201af1f077a 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -9320,6 +9320,9 @@ static int amdgpu_dm_atomic_check(struct drm_device *dev, ret = drm_atomic_add_affected_planes(state, crtc); if (ret) goto fail; + + if (dm_old_crtc_state->dsc_force_changed && new_crtc_state) + new_crtc_state->mode_changed = true; } /* -- cgit v1.2.3 From f5041bc1fcc3c476e08a28cb393a6869536e33c8 Mon Sep 17 00:00:00 2001 From: Zhan Liu Date: Thu, 19 Nov 2020 22:48:29 -0500 Subject: drm/amd/display: Properly define DPCS related info for DCN301 [Why] DPCS related info needs to be properly defined within code. [How] Add missing DPCS related info to code. Signed-off-by: Zhan Liu Reviewed-by: Nikola Cornij Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c index 7e95bd1e9e53..4825c5c1c6ed 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn301/dcn301_resource.c @@ -73,6 +73,9 @@ #include "nbio/nbio_7_2_0_offset.h" +#include "dcn/dpcs_3_0_0_offset.h" +#include "dcn/dpcs_3_0_0_sh_mask.h" + #include "reg_helper.h" #include "dce/dmub_abm.h" #include "dce/dce_aux.h" @@ -517,10 +520,12 @@ static const struct dcn10_link_enc_hpd_registers link_enc_hpd_regs[] = { hpd_regs(3), }; + #define link_regs(id, phyid)\ [id] = {\ LE_DCN301_REG_LIST(id), \ UNIPHY_DCN2_REG_LIST(phyid), \ + DPCS_DCN2_REG_LIST(id), \ SRI(DP_DPHY_INTERNAL_CTRL, DP, id) \ } @@ -540,11 +545,13 @@ static const struct dcn10_link_enc_registers link_enc_regs[] = { }; static const struct dcn10_link_enc_shift le_shift = { - LINK_ENCODER_MASK_SH_LIST_DCN301(__SHIFT) + LINK_ENCODER_MASK_SH_LIST_DCN301(__SHIFT),\ + DPCS_DCN2_MASK_SH_LIST(__SHIFT) }; static const struct dcn10_link_enc_mask le_mask = { - LINK_ENCODER_MASK_SH_LIST_DCN301(_MASK) + LINK_ENCODER_MASK_SH_LIST_DCN301(_MASK),\ + DPCS_DCN2_MASK_SH_LIST(_MASK) }; #define panel_cntl_regs(id)\ -- cgit v1.2.3 From 34ba432c946dfcd205813b1047790aedc562140e Mon Sep 17 00:00:00 2001 From: Anthony Koo Date: Sun, 22 Nov 2020 20:31:45 -0500 Subject: drm/amd/display: [FW Promotion] Release 0.0.44 Add feature caps to allow way for driver to query what features FW supports Signed-off-by: Anthony Koo Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h | 54 +++++++++++++++++++------ 1 file changed, 42 insertions(+), 12 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h index a8d93366fa03..4b7a1b8ad9e0 100644 --- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h +++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h @@ -36,10 +36,10 @@ /* Firmware versioning. */ #ifdef DMUB_EXPOSE_VERSION -#define DMUB_FW_VERSION_GIT_HASH 0x52d68b82f +#define DMUB_FW_VERSION_GIT_HASH 0x685065427 #define DMUB_FW_VERSION_MAJOR 0 #define DMUB_FW_VERSION_MINOR 0 -#define DMUB_FW_VERSION_REVISION 42 +#define DMUB_FW_VERSION_REVISION 44 #define DMUB_FW_VERSION_TEST 0 #define DMUB_FW_VERSION_VBIOS 0 #define DMUB_FW_VERSION_HOTFIX 0 @@ -104,12 +104,15 @@ union dmub_psr_debug_flags { uint32_t u32All; }; +struct dmub_feature_caps { + uint8_t psr; + uint8_t reserved[7]; +}; + #if defined(__cplusplus) } #endif - - //============================================================================== //================================================================= //============================================================================== @@ -301,6 +304,7 @@ enum dmub_cmd_type { DMUB_CMD__REG_SEQ_BURST_WRITE = 3, DMUB_CMD__REG_REG_WAIT = 4, DMUB_CMD__PLAT_54186_WA = 5, + DMUB_CMD__QUERY_FEATURE_CAPS = 6, DMUB_CMD__PSR = 64, DMUB_CMD__MALL = 65, DMUB_CMD__ABM = 66, @@ -321,7 +325,8 @@ enum dmub_out_cmd_type { struct dmub_cmd_header { unsigned int type : 8; unsigned int sub_type : 8; - unsigned int reserved0 : 8; + unsigned int ret_status : 1; + unsigned int reserved0 : 7; unsigned int payload_bytes : 6; /* up to 60 bytes */ unsigned int reserved1 : 2; }; @@ -603,8 +608,12 @@ struct dmub_cmd_psr_copy_settings_data { union dmub_psr_debug_flags debug; uint16_t psr_level; uint8_t dpp_inst; + /* opp_inst and mpcc_inst will not be used in dmub fw, + * dmub fw will get active opp by reading odm registers. + */ uint8_t mpcc_inst; uint8_t opp_inst; + uint8_t otg_inst; uint8_t digfe_inst; uint8_t digbe_inst; @@ -792,7 +801,16 @@ struct dmub_rb_cmd_abm_init_config { struct dmub_cmd_abm_init_config_data abm_init_config_data; }; -union dmub_rb_cmd { +struct dmub_cmd_query_feature_caps_data { + struct dmub_feature_caps feature_caps; +}; + +struct dmub_rb_cmd_query_feature_caps { + struct dmub_cmd_header header; + struct dmub_cmd_query_feature_caps_data query_feature_caps_data; +}; + + union dmub_rb_cmd { struct dmub_rb_cmd_lock_hw lock_hw; struct dmub_rb_cmd_read_modify_write read_modify_write; struct dmub_rb_cmd_reg_field_update_sequence reg_field_update_seq; @@ -819,6 +837,7 @@ union dmub_rb_cmd { struct dmub_rb_cmd_abm_init_config abm_init_config; struct dmub_rb_cmd_dp_aux_access dp_aux_access; struct dmub_rb_cmd_outbox1_enable outbox1_enable; + struct dmub_rb_cmd_query_feature_caps query_feature_caps; }; union dmub_rb_out_cmd { @@ -881,7 +900,7 @@ static inline bool dmub_rb_push_front(struct dmub_rb *rb, { uint64_t volatile *dst = (uint64_t volatile *)(rb->base_address) + rb->wrpt / sizeof(uint64_t); const uint64_t *src = (const uint64_t *)cmd; - int i; + uint8_t i; if (dmub_rb_full(rb)) return false; @@ -918,14 +937,14 @@ static inline bool dmub_rb_out_push_front(struct dmub_rb *rb, } static inline bool dmub_rb_front(struct dmub_rb *rb, - union dmub_rb_cmd *cmd) + union dmub_rb_cmd **cmd) { - uint8_t *rd_ptr = (uint8_t *)rb->base_address + rb->rptr; + uint8_t *rb_cmd = (uint8_t *)(rb->base_address) + rb->rptr; if (dmub_rb_empty(rb)) return false; - dmub_memcpy(cmd, rd_ptr, DMUB_RB_CMD_SIZE); + *cmd = (union dmub_rb_cmd *)rb_cmd; return true; } @@ -935,7 +954,7 @@ static inline bool dmub_rb_out_front(struct dmub_rb *rb, { const uint64_t volatile *src = (const uint64_t volatile *)(rb->base_address) + rb->rptr / sizeof(uint64_t); uint64_t *dst = (uint64_t *)cmd; - int i; + uint8_t i; if (dmub_rb_empty(rb)) return false; @@ -967,7 +986,7 @@ static inline void dmub_rb_flush_pending(const struct dmub_rb *rb) while (rptr != wptr) { uint64_t volatile *data = (uint64_t volatile *)rb->base_address + rptr / sizeof(uint64_t); - int i; + uint8_t i; for (i = 0; i < DMUB_RB_CMD_SIZE / sizeof(uint64_t); i++) *data++; @@ -987,6 +1006,17 @@ static inline void dmub_rb_init(struct dmub_rb *rb, rb->wrpt = init_params->write_ptr; } +static inline void dmub_rb_get_return_data(struct dmub_rb *rb, + union dmub_rb_cmd *cmd) +{ + // Copy rb entry back into command + uint8_t *rd_ptr = (rb->rptr == 0) ? + (uint8_t *)rb->base_address + rb->capacity - DMUB_RB_CMD_SIZE : + (uint8_t *)rb->base_address + rb->rptr - DMUB_RB_CMD_SIZE; + + dmub_memcpy(cmd, rd_ptr, DMUB_RB_CMD_SIZE); +} + #if defined(__cplusplus) } #endif -- cgit v1.2.3 From c529b685e1c05440ad6af10673e00c4a49b926aa Mon Sep 17 00:00:00 2001 From: Aric Cyr Date: Mon, 23 Nov 2020 09:56:00 -0500 Subject: drm/amd/display: DC Release 3.2.114 Signed-off-by: Aric Cyr Acked-by: Aurabindo Pillai Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 7400b0b449eb..54a829f95346 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -42,7 +42,7 @@ #include "inc/hw/dmcu.h" #include "dml/display_mode_lib.h" -#define DC_VER "3.2.113" +#define DC_VER "3.2.114" #define MAX_SURFACES 3 #define MAX_PLANES 6 -- cgit v1.2.3 From 50fe434196dafae18099adcc69687abb431b6e8a Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:33 +0000 Subject: drm/amd/display/dc/inc/hw/dpp: Mark 'dpp_input_csc_matrix' as __maybe_unused MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 'dpp_input_csc_matrix' is used by some, but not all source files which include dpp.h. Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/dc/inc/hw/dpp.h:50:42: warning: ‘dpp_input_csc_matrix’ defined but not used [-Wunused-const-variable=] NB: Snipped lots of these for brevity Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/inc/hw/dpp.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/inc/hw/dpp.h b/drivers/gpu/drm/amd/display/dc/inc/hw/dpp.h index 6751186f6f90..ddbe4bb52724 100644 --- a/drivers/gpu/drm/amd/display/dc/inc/hw/dpp.h +++ b/drivers/gpu/drm/amd/display/dc/inc/hw/dpp.h @@ -47,7 +47,7 @@ struct dpp_input_csc_matrix { uint16_t regval[12]; }; -static const struct dpp_input_csc_matrix dpp_input_csc_matrix[] = { +static const struct dpp_input_csc_matrix __maybe_unused dpp_input_csc_matrix[] = { {COLOR_SPACE_SRGB, {0x2000, 0, 0, 0, 0, 0x2000, 0, 0, 0, 0, 0x2000, 0} }, {COLOR_SPACE_SRGB_LIMITED, -- cgit v1.2.3 From 15e480371b74e0993652f8558b6d936c965e1964 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:35 +0000 Subject: drm/amd/display/amdgpu_dm/amdgpu_dm_color: Demote a misuse and fix another kernel-doc header MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_color.c:128: warning: Function parameter or member 'lut' not described in '__drm_lut_to_dc_gamma' drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_color.c:128: warning: Function parameter or member 'gamma' not described in '__drm_lut_to_dc_gamma' drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_color.c:128: warning: Function parameter or member 'is_legacy' not described in '__drm_lut_to_dc_gamma' drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_color.c:426: warning: Function parameter or member 'dc_plane_state' not described in 'amdgpu_dm_update_plane_color_mgmt' Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c index 5df05f0d18bc..157fe4efbb59 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c @@ -119,7 +119,7 @@ static bool __is_lut_linear(const struct drm_color_lut *lut, uint32_t size) return true; } -/** +/* * Convert the drm_color_lut to dc_gamma. The conversion depends on the size * of the lut - whether or not it's legacy. */ @@ -413,7 +413,7 @@ int amdgpu_dm_update_crtc_color_mgmt(struct dm_crtc_state *crtc) /** * amdgpu_dm_update_plane_color_mgmt: Maps DRM color management to DC plane. * @crtc: amdgpu_dm crtc state - * @ dc_plane_state: target DC surface + * @dc_plane_state: target DC surface * * Update the underlying dc_stream_state's input transfer function (ITF) in * preparation for hardware commit. The transfer function used depends on -- cgit v1.2.3 From 3d3e9cddd7471b250aed6530bc186515d75021de Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:36 +0000 Subject: drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu: Mark local functions invoked by reference as static MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_pp_smu.c:538:6: warning: no previous prototype for ‘pp_rv_set_wm_ranges’ [-Wmissing-prototypes] drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_pp_smu.c:590:6: warning: no previous prototype for ‘pp_rv_set_pme_wa_enable’ [-Wmissing-prototypes] drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_pp_smu.c:601:6: warning: no previous prototype for ‘pp_rv_set_active_display_count’ [-Wmissing-prototypes] drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_pp_smu.c:614:6: warning: no previous prototype for ‘pp_rv_set_min_deep_sleep_dcfclk’ [-Wmissing-prototypes] drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_pp_smu.c:627:6: warning: no previous prototype for ‘pp_rv_set_hard_min_dcefclk_by_freq’ [-Wmissing-prototypes] drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_pp_smu.c:640:6: warning: no previous prototype for ‘pp_rv_set_hard_min_fclk_by_freq’ [-Wmissing-prototypes] Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c index 84065c12d4b8..ac0a0539854e 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c @@ -535,7 +535,7 @@ bool dm_pp_get_static_clocks( return true; } -void pp_rv_set_wm_ranges(struct pp_smu *pp, +static void pp_rv_set_wm_ranges(struct pp_smu *pp, struct pp_smu_wm_range_sets *ranges) { const struct dc_context *ctx = pp->dm; @@ -587,7 +587,7 @@ void pp_rv_set_wm_ranges(struct pp_smu *pp, &wm_with_clock_ranges); } -void pp_rv_set_pme_wa_enable(struct pp_smu *pp) +static void pp_rv_set_pme_wa_enable(struct pp_smu *pp) { const struct dc_context *ctx = pp->dm; struct amdgpu_device *adev = ctx->driver_context; @@ -598,7 +598,7 @@ void pp_rv_set_pme_wa_enable(struct pp_smu *pp) pp_funcs->notify_smu_enable_pwe(pp_handle); } -void pp_rv_set_active_display_count(struct pp_smu *pp, int count) +static void pp_rv_set_active_display_count(struct pp_smu *pp, int count) { const struct dc_context *ctx = pp->dm; struct amdgpu_device *adev = ctx->driver_context; @@ -611,7 +611,7 @@ void pp_rv_set_active_display_count(struct pp_smu *pp, int count) pp_funcs->set_active_display_count(pp_handle, count); } -void pp_rv_set_min_deep_sleep_dcfclk(struct pp_smu *pp, int clock) +static void pp_rv_set_min_deep_sleep_dcfclk(struct pp_smu *pp, int clock) { const struct dc_context *ctx = pp->dm; struct amdgpu_device *adev = ctx->driver_context; @@ -624,7 +624,7 @@ void pp_rv_set_min_deep_sleep_dcfclk(struct pp_smu *pp, int clock) pp_funcs->set_min_deep_sleep_dcefclk(pp_handle, clock); } -void pp_rv_set_hard_min_dcefclk_by_freq(struct pp_smu *pp, int clock) +static void pp_rv_set_hard_min_dcefclk_by_freq(struct pp_smu *pp, int clock) { const struct dc_context *ctx = pp->dm; struct amdgpu_device *adev = ctx->driver_context; @@ -637,7 +637,7 @@ void pp_rv_set_hard_min_dcefclk_by_freq(struct pp_smu *pp, int clock) pp_funcs->set_hard_min_dcefclk_by_freq(pp_handle, clock); } -void pp_rv_set_hard_min_fclk_by_freq(struct pp_smu *pp, int mhz) +static void pp_rv_set_hard_min_fclk_by_freq(struct pp_smu *pp, int mhz) { const struct dc_context *ctx = pp->dm; struct amdgpu_device *adev = ctx->driver_context; @@ -661,7 +661,7 @@ static enum pp_smu_status pp_nv_set_wm_ranges(struct pp_smu *pp, return PP_SMU_RESULT_OK; } -enum pp_smu_status pp_nv_set_pme_wa_enable(struct pp_smu *pp) +static enum pp_smu_status pp_nv_set_pme_wa_enable(struct pp_smu *pp) { const struct dc_context *ctx = pp->dm; struct amdgpu_device *adev = ctx->driver_context; -- cgit v1.2.3 From 679c6771b6c85fd8a127719c7363171f380817c3 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:37 +0000 Subject: drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu: Remove unused function 'pp_nv_set_pme_wa_enable()' MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_pp_smu.c:664:20: warning: no previous prototype for ‘pp_nv_set_pme_wa_enable’ [-Wmissing-prototypes] Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c | 16 ---------------- 1 file changed, 16 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c index ac0a0539854e..607ec0999445 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_pp_smu.c @@ -661,22 +661,6 @@ static enum pp_smu_status pp_nv_set_wm_ranges(struct pp_smu *pp, return PP_SMU_RESULT_OK; } -static enum pp_smu_status pp_nv_set_pme_wa_enable(struct pp_smu *pp) -{ - const struct dc_context *ctx = pp->dm; - struct amdgpu_device *adev = ctx->driver_context; - struct smu_context *smu = &adev->smu; - - if (!smu->ppt_funcs) - return PP_SMU_RESULT_UNSUPPORTED; - - /* 0: successful or smu.ppt_funcs->set_azalia_d3_pme = NULL; 1: fail */ - if (smu_set_azalia_d3_pme(smu)) - return PP_SMU_RESULT_FAIL; - - return PP_SMU_RESULT_OK; -} - static enum pp_smu_status pp_nv_set_display_count(struct pp_smu *pp, int count) { const struct dc_context *ctx = pp->dm; -- cgit v1.2.3 From ef80cb02d5f1041f10f7e7406a5b77b9ccfb810d Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:38 +0000 Subject: drm/amd/display/dc/basics/conversion: Include header containing our prototypes MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/dc/basics/conversion.c:34:10: warning: no previous prototype for ‘fixed_point_to_int_frac’ [-Wmissing-prototypes] drivers/gpu/drm/amd/amdgpu/../display/dc/basics/conversion.c:81:6: warning: no previous prototype for ‘convert_float_matrix’ [-Wmissing-prototypes] Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/basics/conversion.c | 1 + 1 file changed, 1 insertion(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/basics/conversion.c b/drivers/gpu/drm/amd/display/dc/basics/conversion.c index 50b47f11875c..24ed03d8cda7 100644 --- a/drivers/gpu/drm/amd/display/dc/basics/conversion.c +++ b/drivers/gpu/drm/amd/display/dc/basics/conversion.c @@ -24,6 +24,7 @@ */ #include "dm_services.h" +#include "conversion.h" #define DIVIDER 10000 -- cgit v1.2.3 From 3dcd202599d3be80976a1dc7ff29f87e252c8d59 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:39 +0000 Subject: drm/amd/display/dc/basics/fixpt31_32: Remove unused variable 'dc_fixpt_pi' MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/dc/basics/fixpt31_32.c:29:32: warning: ‘dc_fixpt_pi’ defined but not used [-Wunused-const-variable=] Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: Lee Jones Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c | 1 - 1 file changed, 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c b/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c index 59f37563704a..1726bdf89bae 100644 --- a/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c +++ b/drivers/gpu/drm/amd/display/dc/basics/fixpt31_32.c @@ -26,7 +26,6 @@ #include "dm_services.h" #include "include/fixed31_32.h" -static const struct fixed31_32 dc_fixpt_pi = { 13493037705LL }; static const struct fixed31_32 dc_fixpt_two_pi = { 26986075409LL }; static const struct fixed31_32 dc_fixpt_ln2 = { 2977044471LL }; static const struct fixed31_32 dc_fixpt_ln2_div_2 = { 1488522236LL }; -- cgit v1.2.3 From 6ee5a7957aceef415419ab5a557932290759b350 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:40 +0000 Subject: drm/amd/display/dc/basics/vector: Make local function 'dal_vector_presized_costruct' static MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/dc/basics/vector.c:55:6: warning: no previous prototype for ‘dal_vector_presized_costruct’ [-Wmissing-prototypes] Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/basics/vector.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/basics/vector.c b/drivers/gpu/drm/amd/display/dc/basics/vector.c index 8f93d25f91ee..706c803c4d3b 100644 --- a/drivers/gpu/drm/amd/display/dc/basics/vector.c +++ b/drivers/gpu/drm/amd/display/dc/basics/vector.c @@ -52,7 +52,7 @@ bool dal_vector_construct( return true; } -bool dal_vector_presized_costruct( +static bool dal_vector_presized_costruct( struct vector *vector, struct dc_context *ctx, uint32_t count, -- cgit v1.2.3 From fb8284a50e9f7c5506f55bc2ab8762a0f1b855ab Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Thu, 26 Nov 2020 13:42:34 +0000 Subject: drm/amd/display/amdgpu_dm/amdgpu_dm_helpers: Use 'gnu_printf' format notation MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes the following W=1 kernel build warning(s): drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_helpers.c: In function ‘dm_dtn_log_append_v’: drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_helpers.c:345:2: warning: function ‘dm_dtn_log_append_v’ might be a candidate for ‘gnu_printf’ format attribute [-Wsuggest-attribute=format] drivers/gpu/drm/amd/amdgpu/../display/amdgpu_dm/amdgpu_dm_helpers.c:375:3: warning: function ‘dm_dtn_log_append_v’ might be a candidate for ‘gnu_printf’ format attribute [-Wsuggest-attribute=format] Cc: Harry Wentland Cc: Leo Li Cc: Alex Deucher Cc: "Christian König" Cc: David Airlie Cc: Daniel Vetter Cc: amd-gfx@lists.freedesktop.org Cc: dri-devel@lists.freedesktop.org Signed-off-by: Lee Jones Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c | 1 + 1 file changed, 1 insertion(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c index d8b0f07deaf2..f6f487e9fe2d 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c @@ -318,6 +318,7 @@ void dm_dtn_log_begin(struct dc_context *ctx, dm_dtn_log_append_v(ctx, log_ctx, "%s", msg); } +__printf(3, 4) void dm_dtn_log_append_v(struct dc_context *ctx, struct dc_log_buffer_ctx *log_ctx, const char *msg, ...) -- cgit v1.2.3 From ea9522f5e59d35a8774a6c68e98fc9d1f240a8f8 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Wed, 2 Dec 2020 17:38:46 -0500 Subject: drm/amd/display: add debug logs for dm_crtc_helper_atomic_check Instead of silently failing the atomic check, explain what happened via a debug log. This makes it easier for user-space to figure out why something failed. Signed-off-by: Simon Ser Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 7201af1f077a..49d1d947af72 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -6071,8 +6071,10 @@ static int dm_crtc_helper_atomic_check(struct drm_crtc *crtc, * userspace which stops using the HW cursor altogether in response to the resulting EINVAL. */ if (crtc_state->enable && - !(crtc_state->plane_mask & drm_plane_mask(crtc->primary))) + !(crtc_state->plane_mask & drm_plane_mask(crtc->primary))) { + DRM_DEBUG_ATOMIC("Can't enable a CRTC without enabling the primary plane\n"); return -EINVAL; + } /* In some use cases, like reset, no stream is attached */ if (!dm_crtc_state->stream) @@ -6081,6 +6083,7 @@ static int dm_crtc_helper_atomic_check(struct drm_crtc *crtc, if (dc_validate_stream(dc, dm_crtc_state->stream) == DC_OK) return 0; + DRM_DEBUG_ATOMIC("Failed DC stream validation\n"); return ret; } -- cgit v1.2.3 From 03a663673063d04c2358be754a08e62a465bb8f0 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Wed, 2 Dec 2020 21:09:07 +0000 Subject: drm/amd/display: use FB pitch to fill dc_cursor_attributes Instead of relying on pitch (in pixels) == width, use the FB pitch. This is less confusing to readers, and works correctly if we ever support FBs with a pitch (in pixels) != width. This also makes the code symmetrical with fill_plane_buffer_attributes. Reviewed-by: Nicholas Kazlauskas Signed-off-by: Simon Ser Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 49d1d947af72..1c998337656e 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -7438,7 +7438,7 @@ static void handle_cursor_update(struct drm_plane *plane, attributes.rotation_angle = 0; attributes.attribute_flags.value = 0; - attributes.pitch = attributes.width; + attributes.pitch = afb->base.pitches[0] / afb->base.format->cpp[0]; if (crtc_state->stream) { mutex_lock(&adev->dm.dc_lock); -- cgit v1.2.3 From 9bf1019c5f3f11ab615c2d531868d1fe9887e560 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Wed, 2 Dec 2020 21:09:13 +0000 Subject: drm/amd/display: add cursor pitch check Replace the width check with a pitch check, which matches DM internals. Add a new check to make sure the pitch (in pixels) matches the width. Reviewed-by: Nicholas Kazlauskas Signed-off-by: Simon Ser Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 1c998337656e..9f12fabcc33a 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8994,6 +8994,7 @@ static int dm_update_plane_state(struct dc *dc, struct amdgpu_crtc *new_acrtc; bool needs_reset; int ret = 0; + unsigned int pitch; new_plane_crtc = new_plane_state->crtc; @@ -9027,15 +9028,25 @@ static int dm_update_plane_state(struct dc *dc, return -EINVAL; } - switch (new_plane_state->fb->width) { + /* Pitch in pixels */ + pitch = new_plane_state->fb->pitches[0] / new_plane_state->fb->format->cpp[0]; + + if (new_plane_state->fb->width != pitch) { + DRM_DEBUG_ATOMIC("Cursor FB width %d doesn't match pitch %d", + new_plane_state->fb->width, + pitch); + return -EINVAL; + } + + switch (pitch) { case 64: case 128: case 256: - /* FB width is supported by cursor plane */ + /* FB pitch is supported by cursor plane */ break; default: - DRM_DEBUG_ATOMIC("Bad cursor FB width %d\n", - new_plane_state->fb->width); + DRM_DEBUG_ATOMIC("Bad cursor FB pitch %d px\n", + pitch); return -EINVAL; } } -- cgit v1.2.3 From d58159de57437806035d9f331c42d66cd31aedfa Mon Sep 17 00:00:00 2001 From: Alex Deucher Date: Thu, 3 Dec 2020 16:06:26 -0500 Subject: drm/amdgpu/disply: set num_crtc earlier To avoid a recently added warning: Bogus possible_crtcs: [ENCODER:65:TMDS-65] possible_crtcs=0xf (full crtc mask=0x7) WARNING: CPU: 3 PID: 439 at drivers/gpu/drm/drm_mode_config.c:617 drm_mode_config_validate+0x178/0x200 [drm] In this case the warning is harmless, but confusing to users. Bug: https://bugzilla.kernel.org/show_bug.cgi?id=209123 Reviewed-by: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 9f12fabcc33a..4ac0a67f816c 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -1130,9 +1130,6 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) goto error; } - /* Update the actual used number of crtc */ - adev->mode_info.num_crtc = adev->dm.display_indexes_num; - /* create fake encoders for MST */ dm_dp_create_fake_mst_encoders(adev); @@ -3364,6 +3361,10 @@ static int amdgpu_dm_initialize_drm_device(struct amdgpu_device *adev) enum dc_connection_type new_connection_type = dc_connection_none; const struct dc_plane_cap *plane; + dm->display_indexes_num = dm->dc->caps.max_streams; + /* Update the actual used number of crtc */ + adev->mode_info.num_crtc = adev->dm.display_indexes_num; + link_cnt = dm->dc->caps.max_links; if (amdgpu_dm_mode_config_init(dm->adev)) { DRM_ERROR("DM: Failed to initialize mode config\n"); @@ -3425,8 +3426,6 @@ static int amdgpu_dm_initialize_drm_device(struct amdgpu_device *adev) goto fail; } - dm->display_indexes_num = dm->dc->caps.max_streams; - /* loops over all connectors on the board */ for (i = 0; i < link_cnt; i++) { struct dc_link *link = NULL; -- cgit v1.2.3 From b0455fda6dd4e8d31f4ffa198a7ae77b831ac8e7 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Thu, 3 Dec 2020 20:19:35 +0000 Subject: drm/amd/display: extract cursor FB checks into a function As more checks are added, the indentation makes the code harder to read. Reviewed-by: Nicholas Kazlauskas Signed-off-by: Simon Ser Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 81 +++++++++++++---------- 1 file changed, 46 insertions(+), 35 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 4ac0a67f816c..fe16df881fae 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8976,6 +8976,48 @@ static bool should_reset_plane(struct drm_atomic_state *state, return false; } +static int dm_check_cursor_fb(struct amdgpu_crtc *new_acrtc, + struct drm_plane_state *new_plane_state, + struct drm_framebuffer *fb) +{ + unsigned int pitch; + + if (fb->width > new_acrtc->max_cursor_width || + fb->height > new_acrtc->max_cursor_height) { + DRM_DEBUG_ATOMIC("Bad cursor FB size %dx%d\n", + new_plane_state->fb->width, + new_plane_state->fb->height); + return -EINVAL; + } + if (new_plane_state->src_w != fb->width << 16 || + new_plane_state->src_h != fb->height << 16) { + DRM_DEBUG_ATOMIC("Cropping not supported for cursor plane\n"); + return -EINVAL; + } + + /* Pitch in pixels */ + pitch = fb->pitches[0] / fb->format->cpp[0]; + + if (fb->width != pitch) { + DRM_DEBUG_ATOMIC("Cursor FB width %d doesn't match pitch %d", + fb->width, pitch); + return -EINVAL; + } + + switch (pitch) { + case 64: + case 128: + case 256: + /* FB pitch is supported by cursor plane */ + break; + default: + DRM_DEBUG_ATOMIC("Bad cursor FB pitch %d px\n", pitch); + return -EINVAL; + } + + return 0; +} + static int dm_update_plane_state(struct dc *dc, struct drm_atomic_state *state, struct drm_plane *plane, @@ -8993,7 +9035,6 @@ static int dm_update_plane_state(struct dc *dc, struct amdgpu_crtc *new_acrtc; bool needs_reset; int ret = 0; - unsigned int pitch; new_plane_crtc = new_plane_state->crtc; @@ -9014,40 +9055,10 @@ static int dm_update_plane_state(struct dc *dc, } if (new_plane_state->fb) { - if (new_plane_state->fb->width > new_acrtc->max_cursor_width || - new_plane_state->fb->height > new_acrtc->max_cursor_height) { - DRM_DEBUG_ATOMIC("Bad cursor FB size %dx%d\n", - new_plane_state->fb->width, - new_plane_state->fb->height); - return -EINVAL; - } - if (new_plane_state->src_w != new_plane_state->fb->width << 16 || - new_plane_state->src_h != new_plane_state->fb->height << 16) { - DRM_DEBUG_ATOMIC("Cropping not supported for cursor plane\n"); - return -EINVAL; - } - - /* Pitch in pixels */ - pitch = new_plane_state->fb->pitches[0] / new_plane_state->fb->format->cpp[0]; - - if (new_plane_state->fb->width != pitch) { - DRM_DEBUG_ATOMIC("Cursor FB width %d doesn't match pitch %d", - new_plane_state->fb->width, - pitch); - return -EINVAL; - } - - switch (pitch) { - case 64: - case 128: - case 256: - /* FB pitch is supported by cursor plane */ - break; - default: - DRM_DEBUG_ATOMIC("Bad cursor FB pitch %d px\n", - pitch); - return -EINVAL; - } + ret = dm_check_cursor_fb(new_acrtc, new_plane_state, + new_plane_state->fb); + if (ret) + return ret; } return 0; -- cgit v1.2.3 From e72868c4eacf435d9c6cdf47359a058c38223e46 Mon Sep 17 00:00:00 2001 From: Simon Ser Date: Thu, 3 Dec 2020 20:19:41 +0000 Subject: drm/amd/display: check cursor FB is linear Previously we accepted non-linear buffers for the cursor plane. This results in bad output, DC validation failures and oops. Make sure the FB uses a linear layout in the atomic check function. The GFX8- check is inspired from ac_surface_set_bo_metadata in Mesa. The GFX9+ check comes from convert_tiling_flags_to_modifier. Reviewed-by: Nicholas Kazlauskas Signed-off-by: Simon Ser References: https://gitlab.freedesktop.org/drm/amd/-/issues/1390 Cc: Bas Nieuwenhuizen Cc: Alex Deucher Cc: Harry Wentland Cc: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index fe16df881fae..0da49d20396a 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8980,7 +8980,10 @@ static int dm_check_cursor_fb(struct amdgpu_crtc *new_acrtc, struct drm_plane_state *new_plane_state, struct drm_framebuffer *fb) { + struct amdgpu_device *adev = drm_to_adev(new_acrtc->base.dev); + struct amdgpu_framebuffer *afb = to_amdgpu_framebuffer(fb); unsigned int pitch; + bool linear; if (fb->width > new_acrtc->max_cursor_width || fb->height > new_acrtc->max_cursor_height) { @@ -9015,6 +9018,22 @@ static int dm_check_cursor_fb(struct amdgpu_crtc *new_acrtc, return -EINVAL; } + /* Core DRM takes care of checking FB modifiers, so we only need to + * check tiling flags when the FB doesn't have a modifier. */ + if (!(fb->flags & DRM_MODE_FB_MODIFIERS)) { + if (adev->family < AMDGPU_FAMILY_AI) { + linear = AMDGPU_TILING_GET(afb->tiling_flags, ARRAY_MODE) != DC_ARRAY_2D_TILED_THIN1 && + AMDGPU_TILING_GET(afb->tiling_flags, ARRAY_MODE) != DC_ARRAY_1D_TILED_THIN1 && + AMDGPU_TILING_GET(afb->tiling_flags, MICRO_TILE_MODE) == 0; + } else { + linear = AMDGPU_TILING_GET(afb->tiling_flags, SWIZZLE_MODE) == 0; + } + if (!linear) { + DRM_DEBUG_ATOMIC("Cursor FB not linear"); + return -EINVAL; + } + } + return 0; } -- cgit v1.2.3 From 9bc41626658271de26cd9086c6e82811ca334dd2 Mon Sep 17 00:00:00 2001 From: Reza Amini Date: Thu, 9 Jul 2020 18:01:22 -0400 Subject: drm/amd/display: Implement VSIF V3 extended refresh rate feature [Why] Implement feature of VSIF V3 [How] Set refresh rate MSB for extended range Signed-off-by: Reza Amini Reviewed-by: Anthony Koo Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- .../drm/amd/display/modules/freesync/freesync.c | 100 +++++++++++++++++---- 1 file changed, 82 insertions(+), 18 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/modules/freesync/freesync.c b/drivers/gpu/drm/amd/display/modules/freesync/freesync.c index 52c3cb6b439a..2decdd8a5e20 100644 --- a/drivers/gpu/drm/amd/display/modules/freesync/freesync.c +++ b/drivers/gpu/drm/amd/display/modules/freesync/freesync.c @@ -569,6 +569,12 @@ static void build_vrr_infopacket_data_v1(const struct mod_vrr_params *vrr, static void build_vrr_infopacket_data_v3(const struct mod_vrr_params *vrr, struct dc_info_packet *infopacket) { + unsigned int min_refresh; + unsigned int max_refresh; + unsigned int fixed_refresh; + unsigned int min_programmed; + unsigned int max_programmed; + /* PB1 = 0x1A (24bit AMD IEEE OUI (0x00001A) - Byte 0) */ infopacket->sb[1] = 0x1A; @@ -598,23 +604,29 @@ static void build_vrr_infopacket_data_v3(const struct mod_vrr_params *vrr, vrr->state == VRR_STATE_ACTIVE_FIXED) infopacket->sb[6] |= 0x04; - if (vrr->state == VRR_STATE_ACTIVE_FIXED) { - /* PB7 = FreeSync Minimum refresh rate (Hz) */ - infopacket->sb[7] = (unsigned char)((vrr->fixed_refresh_in_uhz + 500000) / 1000000); - /* PB8 = FreeSync Maximum refresh rate (Hz) */ - infopacket->sb[8] = (unsigned char)((vrr->fixed_refresh_in_uhz + 500000) / 1000000); - } else if (vrr->state == VRR_STATE_ACTIVE_VARIABLE) { - /* PB7 = FreeSync Minimum refresh rate (Hz) */ - infopacket->sb[7] = (unsigned char)((vrr->min_refresh_in_uhz + 500000) / 1000000); - /* PB8 = FreeSync Maximum refresh rate (Hz) */ - infopacket->sb[8] = (unsigned char)((vrr->max_refresh_in_uhz + 500000) / 1000000); - } else { - // Non-fs case, program nominal range - /* PB7 = FreeSync Minimum refresh rate (Hz) */ - infopacket->sb[7] = (unsigned char)((vrr->max_refresh_in_uhz + 500000) / 1000000); - /* PB8 = FreeSync Maximum refresh rate (Hz) */ - infopacket->sb[8] = (unsigned char)((vrr->max_refresh_in_uhz + 500000) / 1000000); - } + min_refresh = (vrr->min_refresh_in_uhz + 500000) / 1000000; + max_refresh = (vrr->max_refresh_in_uhz + 500000) / 1000000; + fixed_refresh = (vrr->fixed_refresh_in_uhz + 500000) / 1000000; + + min_programmed = (vrr->state == VRR_STATE_ACTIVE_FIXED) ? fixed_refresh : + (vrr->state == VRR_STATE_ACTIVE_VARIABLE) ? min_refresh : + max_refresh; // Non-fs case, program nominal range + + max_programmed = (vrr->state == VRR_STATE_ACTIVE_FIXED) ? fixed_refresh : + (vrr->state == VRR_STATE_ACTIVE_VARIABLE) ? max_refresh : + max_refresh;// Non-fs case, program nominal range + + /* PB7 = FreeSync Minimum refresh rate (Hz) */ + infopacket->sb[7] = min_programmed & 0xFF; + + /* PB8 = FreeSync Maximum refresh rate (Hz) */ + infopacket->sb[8] = max_programmed & 0xFF; + + /* PB11 : MSB FreeSync Minimum refresh rate [Hz] - bits 15:8 */ + infopacket->sb[11] = (min_programmed >> 8) & 0xFF; + + /* PB12 : MSB FreeSync Maximum refresh rate [Hz] - bits 15:8 */ + infopacket->sb[12] = (max_programmed >> 8) & 0xFF; //FreeSync HDR infopacket->sb[9] = 0; @@ -733,6 +745,58 @@ static void build_vrr_infopacket_header_v2(enum signal_type signal, } } +static void build_vrr_infopacket_header_v3(enum signal_type signal, + struct dc_info_packet *infopacket, + unsigned int *payload_size) +{ + unsigned char version; + + version = 3; + if (dc_is_hdmi_signal(signal)) { + + /* HEADER */ + + /* HB0 = Packet Type = 0x83 (Source Product + * Descriptor InfoFrame) + */ + infopacket->hb0 = DC_HDMI_INFOFRAME_TYPE_SPD; + + /* HB1 = Version = 0x03 */ + infopacket->hb1 = version; + + /* HB2 = [Bits 7:5 = 0] [Bits 4:0 = Length] */ + *payload_size = 0x10; + infopacket->hb2 = *payload_size - 1; //-1 for checksum + + } else if (dc_is_dp_signal(signal)) { + + /* HEADER */ + + /* HB0 = Secondary-data Packet ID = 0 - Only non-zero + * when used to associate audio related info packets + */ + infopacket->hb0 = 0x00; + + /* HB1 = Packet Type = 0x83 (Source Product + * Descriptor InfoFrame) + */ + infopacket->hb1 = DC_HDMI_INFOFRAME_TYPE_SPD; + + /* HB2 = [Bits 7:0 = Least significant eight bits - + * For INFOFRAME, the value must be 1Bh] + */ + infopacket->hb2 = 0x1B; + + /* HB3 = [Bits 7:2 = INFOFRAME SDP Version Number = 0x2] + * [Bits 1:0 = Most significant two bits = 0x00] + */ + + infopacket->hb3 = (version & 0x3F) << 2; + + *payload_size = 0x1B; + } +} + static void build_vrr_infopacket_checksum(unsigned int *payload_size, struct dc_info_packet *infopacket) { @@ -818,7 +882,7 @@ static void build_vrr_infopacket_v3(enum signal_type signal, { unsigned int payload_size = 0; - build_vrr_infopacket_header_v2(signal, infopacket, &payload_size); + build_vrr_infopacket_header_v3(signal, infopacket, &payload_size); build_vrr_infopacket_data_v3(vrr, infopacket); build_vrr_infopacket_fs2_data(app_tf, infopacket); -- cgit v1.2.3 From 983bcb4cbe259ca6b2e03a6133364681aff1b88b Mon Sep 17 00:00:00 2001 From: "AMD\\ramini" Date: Tue, 24 Nov 2020 17:08:44 -0500 Subject: drm/amd/display: Set FixRate bit in VSIF V3 [Why] Signal FreeSync display that we are in Fixed Rate mode, and expand the FreeSync range to 1024. [How] Set the new bit in SB16:bit0, and augment the min and max refresh rate with 2 extra bits. Signed-off-by: AMD\ramini Reviewed-by: Anthony Koo Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/modules/freesync/freesync.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/modules/freesync/freesync.c b/drivers/gpu/drm/amd/display/modules/freesync/freesync.c index 2decdd8a5e20..4762273b5bb9 100644 --- a/drivers/gpu/drm/amd/display/modules/freesync/freesync.c +++ b/drivers/gpu/drm/amd/display/modules/freesync/freesync.c @@ -610,6 +610,7 @@ static void build_vrr_infopacket_data_v3(const struct mod_vrr_params *vrr, min_programmed = (vrr->state == VRR_STATE_ACTIVE_FIXED) ? fixed_refresh : (vrr->state == VRR_STATE_ACTIVE_VARIABLE) ? min_refresh : + (vrr->state == VRR_STATE_INACTIVE) ? min_refresh : max_refresh; // Non-fs case, program nominal range max_programmed = (vrr->state == VRR_STATE_ACTIVE_FIXED) ? fixed_refresh : @@ -622,11 +623,14 @@ static void build_vrr_infopacket_data_v3(const struct mod_vrr_params *vrr, /* PB8 = FreeSync Maximum refresh rate (Hz) */ infopacket->sb[8] = max_programmed & 0xFF; - /* PB11 : MSB FreeSync Minimum refresh rate [Hz] - bits 15:8 */ - infopacket->sb[11] = (min_programmed >> 8) & 0xFF; + /* PB11 : MSB FreeSync Minimum refresh rate [Hz] - bits 9:8 */ + infopacket->sb[11] = (min_programmed >> 8) & 0x03; - /* PB12 : MSB FreeSync Maximum refresh rate [Hz] - bits 15:8 */ - infopacket->sb[12] = (max_programmed >> 8) & 0xFF; + /* PB12 : MSB FreeSync Maximum refresh rate [Hz] - bits 9:8 */ + infopacket->sb[12] = (max_programmed >> 8) & 0x03; + + /* PB16 : Reserved bits 7:1, FixedRate bit 0 */ + infopacket->sb[16] = (vrr->state == VRR_STATE_ACTIVE_FIXED) ? 1 : 0; //FreeSync HDR infopacket->sb[9] = 0; -- cgit v1.2.3 From c8ea79a8a2767e7948c778237be655a109366eb9 Mon Sep 17 00:00:00 2001 From: Qingqing Zhuo Date: Thu, 1 Oct 2020 15:56:28 -0400 Subject: drm/amd/display: NULL pointer error during compliance test [Why] Calls to disable/enable stream should be guarded with dc_lock. [How] Add dc_lock before calling into dc_link_handle_hpd_rx_irq. Signed-off-by: Qingqing Zhuo Reviewed-by: Nicholas Kazlauskas Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 0da49d20396a..c8e279f05c72 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -2560,10 +2560,11 @@ static void handle_hpd_rx_irq(void *param) struct drm_device *dev = connector->dev; struct dc_link *dc_link = aconnector->dc_link; bool is_mst_root_connector = aconnector->mst_mgr.mst_state; + bool result = false; enum dc_connection_type new_connection_type = dc_connection_none; + struct amdgpu_device *adev = drm_to_adev(dev); #ifdef CONFIG_DRM_AMD_DC_HDCP union hpd_irq_data hpd_irq_data; - struct amdgpu_device *adev = drm_to_adev(dev); memset(&hpd_irq_data, 0, sizeof(hpd_irq_data)); #endif @@ -2576,13 +2577,15 @@ static void handle_hpd_rx_irq(void *param) if (dc_link->type != dc_connection_mst_branch) mutex_lock(&aconnector->hpd_lock); - + mutex_lock(&adev->dm.dc_lock); #ifdef CONFIG_DRM_AMD_DC_HDCP - if (dc_link_handle_hpd_rx_irq(dc_link, &hpd_irq_data, NULL) && + result = dc_link_handle_hpd_rx_irq(dc_link, &hpd_irq_data, NULL); #else - if (dc_link_handle_hpd_rx_irq(dc_link, NULL, NULL) && + result = dc_link_handle_hpd_rx_irq(dc_link, NULL, NULL); #endif - !is_mst_root_connector) { + mutex_unlock(&adev->dm.dc_lock); + + if (result && !is_mst_root_connector) { /* Downstream Port status changed. */ if (!dc_link_detect_sink(dc_link, &new_connection_type)) DRM_ERROR("KMS: Failed to detect connector\n"); -- cgit v1.2.3 From 42ddf36e6720fc26dafd9cbd41322706eacf87d5 Mon Sep 17 00:00:00 2001 From: Dmytro Laktyushkin Date: Mon, 23 Nov 2020 11:39:27 -0500 Subject: drm/amd/display: Expose clk_mgr functions for reuse [How & Why] Allow clk_mgr functions to be reused by making then non-static Signed-off-by: Dmytro Laktyushkin Reviewed-by: Eric Yang Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn30/dcn30_clk_mgr.c | 2 +- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c | 8 ++++---- drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h | 10 ++++++++++ 3 files changed, 15 insertions(+), 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn30/dcn30_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn30/dcn30_clk_mgr.c index 82cb688ba5e0..5b466f440d67 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn30/dcn30_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn30/dcn30_clk_mgr.c @@ -499,7 +499,7 @@ static void dcn3_init_clocks_fpga(struct clk_mgr *clk_mgr) /* TODO: Implement the functions and remove the ifndef guard */ } -static struct clk_mgr_funcs dcn3_fpga_funcs = { +struct clk_mgr_funcs dcn3_fpga_funcs = { .get_dp_ref_clk_frequency = dce12_get_dp_ref_freq_khz, .update_clocks = dcn2_update_clocks_fpga, .init_clocks = dcn3_init_clocks_fpga, diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c index 98cbb0ac095c..9a8e66bba9c0 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.c @@ -32,9 +32,9 @@ // For dcn20_update_clocks_update_dpp_dto #include "dcn20/dcn20_clk_mgr.h" -#include "vg_clk_mgr.h" -#include "dcn301_smu.h" + +#include "vg_clk_mgr.h" #include "reg_helper.h" #include "core_types.h" #include "dm_helpers.h" @@ -631,7 +631,7 @@ static unsigned int find_dcfclk_for_voltage(const struct vg_dpm_clocks *clock_ta return 0; } -static void vg_clk_mgr_helper_populate_bw_params( +void vg_clk_mgr_helper_populate_bw_params( struct clk_mgr_internal *clk_mgr, struct integrated_info *bios_info, const struct vg_dpm_clocks *clock_table) @@ -709,7 +709,7 @@ static struct vg_dpm_clocks dummy_clocks = { static struct watermarks dummy_wms = { 0 }; -static void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, +void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, struct smu_dpm_clks *smu_dpm_clks) { struct vg_dpm_clocks *table = smu_dpm_clks->dpm_clks; diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h index 80497df20ba7..b5115b3123a1 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn301/vg_clk_mgr.h @@ -39,5 +39,15 @@ void vg_clk_mgr_construct(struct dc_context *ctx, void vg_clk_mgr_destroy(struct clk_mgr_internal *clk_mgr); +#include "dcn301_smu.h" void vg_notify_wm_ranges(struct clk_mgr *clk_mgr_base); + +void vg_get_dpm_table_from_smu(struct clk_mgr_internal *clk_mgr, + struct smu_dpm_clks *smu_dpm_clks); + +void vg_clk_mgr_helper_populate_bw_params( + struct clk_mgr_internal *clk_mgr, + struct integrated_info *bios_info, + const struct vg_dpm_clocks *clock_table); + #endif //__VG_CLK_MGR_H__ -- cgit v1.2.3 From 92f1fa0d67a88d5c3992f1ddd7bab30a42f43eb8 Mon Sep 17 00:00:00 2001 From: Wyatt Wood Date: Wed, 21 Oct 2020 13:13:41 -0400 Subject: drm/amd/display: Add support for runtime feature detection command [Why] Add support for new fw command for runtime feature detection. [How] Driver sends command through ring buffer, and fw returns data back through this command. Signed-off-by: Wyatt Wood Reviewed-by: Jun Lei Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dmub/dmub_srv.h | 6 +++++ drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c | 29 +++++++++++++++++++++++++ 2 files changed, 35 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dmub/dmub_srv.h b/drivers/gpu/drm/amd/display/dmub/dmub_srv.h index b82a46890846..863cd9cc93ff 100644 --- a/drivers/gpu/drm/amd/display/dmub/dmub_srv.h +++ b/drivers/gpu/drm/amd/display/dmub/dmub_srv.h @@ -345,6 +345,9 @@ struct dmub_srv { uint64_t fb_base; uint64_t fb_offset; uint32_t psp_version; + + /* Feature capabilities reported by fw */ + struct dmub_feature_caps feature_caps; }; /** @@ -608,6 +611,9 @@ void dmub_flush_buffer_mem(const struct dmub_fb *fb); enum dmub_status dmub_srv_get_fw_boot_status(struct dmub_srv *dmub, union dmub_fw_boot_status *status); +enum dmub_status dmub_srv_cmd_with_reply_data(struct dmub_srv *dmub, + union dmub_rb_cmd *cmd); + #if defined(__cplusplus) } #endif diff --git a/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c b/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c index ba8494cf005f..f388d36af0b6 100644 --- a/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c +++ b/drivers/gpu/drm/amd/display/dmub/src/dmub_srv.c @@ -648,3 +648,32 @@ enum dmub_status dmub_srv_get_fw_boot_status(struct dmub_srv *dmub, return DMUB_STATUS_OK; } + +enum dmub_status dmub_srv_cmd_with_reply_data(struct dmub_srv *dmub, + union dmub_rb_cmd *cmd) +{ + enum dmub_status status = DMUB_STATUS_OK; + + // Queue command + status = dmub_srv_cmd_queue(dmub, cmd); + + if (status != DMUB_STATUS_OK) + return status; + + // Execute command + status = dmub_srv_cmd_execute(dmub); + + if (status != DMUB_STATUS_OK) + return status; + + // Wait for DMUB to process command + status = dmub_srv_wait_for_idle(dmub, 100000); + + if (status != DMUB_STATUS_OK) + return status; + + // Copy data back from ring buffer into command + dmub_rb_get_return_data(&dmub->inbox1_rb, cmd); + + return status; +} -- cgit v1.2.3 From 5c8a6c71d72021c0d62d8904997495c93b962eec Mon Sep 17 00:00:00 2001 From: Jing Zhou Date: Mon, 16 Nov 2020 18:11:08 +0800 Subject: drm/amd/display: Set default bits per channel [Why] Bump into calcReducedBlankingTiming because of mode query failed. In this function, timing.displayColorDepth == DISPLAY_COLOR_DEPTH_UNDEFINED. Then req_bw == 0 because of bits_per_channel == 0. So decide edp link settings, use default RBRx1 for special timing. [How] Set default bits_per_channel is 8. Signed-off-by: Jing Zhou Reviewed-by: Aric Cyr Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 4 ++-- drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | 15 ++++++++++++--- 2 files changed, 14 insertions(+), 5 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index a9c52657eb4b..bd004de107b7 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -3471,11 +3471,11 @@ uint32_t dc_bandwidth_in_kbps_from_timing( bits_per_channel = 16; break; default: + ASSERT(bits_per_channel != 0); + bits_per_channel = 8; break; } - ASSERT(bits_per_channel != 0); - kbps = timing->pix_clk_100hz / 10; kbps *= bits_per_channel; diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c index 93fbc646f53b..dbbc0ec0b699 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c @@ -1410,15 +1410,24 @@ static void print_status_message( case LINK_RATE_LOW: link_rate = "RBR"; break; + case LINK_RATE_RATE_2: + link_rate = "R2"; + break; + case LINK_RATE_RATE_3: + link_rate = "R3"; + break; case LINK_RATE_HIGH: link_rate = "HBR"; break; - case LINK_RATE_HIGH2: - link_rate = "HBR2"; - break; case LINK_RATE_RBR2: link_rate = "RBR2"; break; + case LINK_RATE_RATE_6: + link_rate = "R6"; + break; + case LINK_RATE_HIGH2: + link_rate = "HBR2"; + break; case LINK_RATE_HIGH3: link_rate = "HBR3"; break; -- cgit v1.2.3 From 25331a18f45cdc9d872c3badd1de93c6f0f4fe64 Mon Sep 17 00:00:00 2001 From: John Wu Date: Mon, 23 Nov 2020 15:49:15 +0800 Subject: drm/amd/display: Don't check seamless boot in power down HW by timeout [Why] power_down_on_boot is designed to power down HW when set mode is not called before timeout. It can happen in headless system or booting with the display is output by non-AMD GPU only. The function will be executed only if it's not seamless boot. So in seamless boot, the HW is still on. It's not necessary to check this since there's no display data in both cases. [How] Remove seamless boot checking in power_down_on_boot. Signed-off-by: John Wu Reviewed-by: Anthony Koo Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c index 1e18f0bb40b6..9f7d6b087553 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c +++ b/drivers/gpu/drm/amd/display/dc/dcn10/dcn10_hw_sequencer.c @@ -1442,16 +1442,13 @@ void dcn10_init_hw(struct dc *dc) /* In headless boot cases, DIG may be turned * on which causes HW/SW discrepancies. * To avoid this, power down hardware on boot - * if DIG is turned on and seamless boot not enabled + * if DIG is turned on */ void dcn10_power_down_on_boot(struct dc *dc) { int i = 0; struct dc_link *edp_link; - if (!dc->config.power_down_display_on_boot) - return; - edp_link = get_edp_link(dc); if (edp_link && edp_link->link_enc->funcs->is_dig_enabled && -- cgit v1.2.3 From a013dd15d470b9ace50cb7a152b1eddabf9c36ad Mon Sep 17 00:00:00 2001 From: Judy Cai Date: Mon, 2 Nov 2020 18:49:19 -0500 Subject: drm/amd/display: Change to IMMEDIATE mode from FRAME mode [Why] Change in DCN10 to use IMMEDIATE_UPDATE mode for AFMT is not reflected in DCN30 as it uses VPG. [How] Use IMMEDIATE_UPDATE mode for DCN30 in VPG. Signed-off-by: Judy Cai Reviewed-by: Anthony Koo Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.c | 62 ++++++++++++------------ drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.h | 38 +++++++++++++-- 2 files changed, 66 insertions(+), 34 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.c index 9c0020c8a730..8cfd181b4d5f 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.c @@ -103,69 +103,69 @@ static void vpg3_update_generic_info_packet( } } - /* atomically update double-buffered GENERIC0 registers in frame mode + /* atomically update double-buffered GENERIC0 registers in immediate mode * (update at next block_update when block_update_lock == 0). */ switch (packet_index) { case 0: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC0_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC0_IMMEDIATE_UPDATE, 1); break; case 1: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC1_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC1_IMMEDIATE_UPDATE, 1); break; case 2: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC2_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC2_IMMEDIATE_UPDATE, 1); break; case 3: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC3_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC3_IMMEDIATE_UPDATE, 1); break; case 4: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC4_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC4_IMMEDIATE_UPDATE, 1); break; case 5: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC5_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC5_IMMEDIATE_UPDATE, 1); break; case 6: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC6_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC6_IMMEDIATE_UPDATE, 1); break; case 7: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC7_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC7_IMMEDIATE_UPDATE, 1); break; case 8: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC8_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC8_IMMEDIATE_UPDATE, 1); break; case 9: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC9_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC9_IMMEDIATE_UPDATE, 1); break; case 10: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC10_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC10_IMMEDIATE_UPDATE, 1); break; case 11: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC11_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC11_IMMEDIATE_UPDATE, 1); break; case 12: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC12_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC12_IMMEDIATE_UPDATE, 1); break; case 13: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC13_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC13_IMMEDIATE_UPDATE, 1); break; case 14: - REG_UPDATE(VPG_GSP_FRAME_UPDATE_CTRL, - VPG_GENERIC14_FRAME_UPDATE, 1); + REG_UPDATE(VPG_GSP_IMMEDIATE_UPDATE_CTRL, + VPG_GENERIC14_IMMEDIATE_UPDATE, 1); break; default: break; diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.h b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.h index 0284092630f1..6161e9e66355 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.h +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_vpg.h @@ -34,13 +34,15 @@ SRI(VPG_GENERIC_STATUS, VPG, id), \ SRI(VPG_GENERIC_PACKET_ACCESS_CTRL, VPG, id), \ SRI(VPG_GENERIC_PACKET_DATA, VPG, id), \ - SRI(VPG_GSP_FRAME_UPDATE_CTRL, VPG, id) + SRI(VPG_GSP_FRAME_UPDATE_CTRL, VPG, id), \ + SRI(VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG, id) struct dcn30_vpg_registers { uint32_t VPG_GENERIC_STATUS; uint32_t VPG_GENERIC_PACKET_ACCESS_CTRL; uint32_t VPG_GENERIC_PACKET_DATA; uint32_t VPG_GSP_FRAME_UPDATE_CTRL; + uint32_t VPG_GSP_IMMEDIATE_UPDATE_CTRL; }; #define DCN3_VPG_MASK_SH_LIST(mask_sh)\ @@ -65,7 +67,22 @@ struct dcn30_vpg_registers { SE_SF(VPG0_VPG_GSP_FRAME_UPDATE_CTRL, VPG_GENERIC11_FRAME_UPDATE, mask_sh),\ SE_SF(VPG0_VPG_GSP_FRAME_UPDATE_CTRL, VPG_GENERIC12_FRAME_UPDATE, mask_sh),\ SE_SF(VPG0_VPG_GSP_FRAME_UPDATE_CTRL, VPG_GENERIC13_FRAME_UPDATE, mask_sh),\ - SE_SF(VPG0_VPG_GSP_FRAME_UPDATE_CTRL, VPG_GENERIC14_FRAME_UPDATE, mask_sh) + SE_SF(VPG0_VPG_GSP_FRAME_UPDATE_CTRL, VPG_GENERIC14_FRAME_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC0_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC1_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC2_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC3_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC4_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC5_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC6_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC7_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC8_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC9_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC10_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC11_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC12_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC13_IMMEDIATE_UPDATE, mask_sh),\ + SE_SF(VPG0_VPG_GSP_IMMEDIATE_UPDATE_CTRL, VPG_GENERIC14_IMMEDIATE_UPDATE, mask_sh) #define VPG_DCN3_REG_FIELD_LIST(type) \ type VPG_GENERIC_CONFLICT_OCCURED;\ @@ -89,7 +106,22 @@ struct dcn30_vpg_registers { type VPG_GENERIC11_FRAME_UPDATE;\ type VPG_GENERIC12_FRAME_UPDATE;\ type VPG_GENERIC13_FRAME_UPDATE;\ - type VPG_GENERIC14_FRAME_UPDATE + type VPG_GENERIC14_FRAME_UPDATE;\ + type VPG_GENERIC0_IMMEDIATE_UPDATE;\ + type VPG_GENERIC1_IMMEDIATE_UPDATE;\ + type VPG_GENERIC2_IMMEDIATE_UPDATE;\ + type VPG_GENERIC3_IMMEDIATE_UPDATE;\ + type VPG_GENERIC4_IMMEDIATE_UPDATE;\ + type VPG_GENERIC5_IMMEDIATE_UPDATE;\ + type VPG_GENERIC6_IMMEDIATE_UPDATE;\ + type VPG_GENERIC7_IMMEDIATE_UPDATE;\ + type VPG_GENERIC8_IMMEDIATE_UPDATE;\ + type VPG_GENERIC9_IMMEDIATE_UPDATE;\ + type VPG_GENERIC10_IMMEDIATE_UPDATE;\ + type VPG_GENERIC11_IMMEDIATE_UPDATE;\ + type VPG_GENERIC12_IMMEDIATE_UPDATE;\ + type VPG_GENERIC13_IMMEDIATE_UPDATE;\ + type VPG_GENERIC14_IMMEDIATE_UPDATE struct dcn30_vpg_shift { -- cgit v1.2.3 From 5a83bf80723dbc18d2f4d3949466bab216225c30 Mon Sep 17 00:00:00 2001 From: Wesley Chalmers Date: Mon, 23 Nov 2020 19:04:23 -0500 Subject: drm/amd/display: Use provided offset for DPG generation [Why] Currently, the offset provided to dcn30_set_disp_pattern_generator is not forwarded to OPP for display pattern generation, resulting in misaligned patterns and test failures. [How] Use the provided offset. Signed-off-by: Wesley Chalmers Reviewed-by: Samson Tam Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c index 7a7efe9ea961..283995ab9eeb 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn30/dcn30_hwseq.c @@ -832,5 +832,5 @@ void dcn30_set_disp_pattern_generator(const struct dc *dc, int width, int height, int offset) { pipe_ctx->stream_res.opp->funcs->opp_set_disp_pattern_generator(pipe_ctx->stream_res.opp, test_pattern, - color_space, color_depth, solid_color, width, height, 0); + color_space, color_depth, solid_color, width, height, offset); } -- cgit v1.2.3 From 3083a9845e1258ee8c2126d37f7b41897fad02e5 Mon Sep 17 00:00:00 2001 From: Qingqing Zhuo Date: Mon, 23 Nov 2020 17:56:35 -0500 Subject: drm/amd/display: Only one display lights up while using MST hub [Why] With the addition of dc_lock acquire before dc_link_handle_hpd_rx_irq, there will be a deadlock situation where commit state sends a request for payload allocation on MST and wait for HPD to process DOWN_REP. [How] Move forward the MST message handling in handle_hpd_rx_irq so that it will not rely on call to dc_link_handle_hpd_rx_irq. Signed-off-by: Qingqing Zhuo Reviewed-by: Harry Wentland Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 21 ++++++++++++++++----- drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | 2 +- drivers/gpu/drm/amd/display/dc/dc_link.h | 4 ++++ 3 files changed, 21 insertions(+), 6 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index c8e279f05c72..508457cca343 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -2563,11 +2563,9 @@ static void handle_hpd_rx_irq(void *param) bool result = false; enum dc_connection_type new_connection_type = dc_connection_none; struct amdgpu_device *adev = drm_to_adev(dev); -#ifdef CONFIG_DRM_AMD_DC_HDCP union hpd_irq_data hpd_irq_data; memset(&hpd_irq_data, 0, sizeof(hpd_irq_data)); -#endif /* * TODO:Temporary add mutex to protect hpd interrupt not have a gpio @@ -2577,6 +2575,21 @@ static void handle_hpd_rx_irq(void *param) if (dc_link->type != dc_connection_mst_branch) mutex_lock(&aconnector->hpd_lock); + read_hpd_rx_irq_data(dc_link, &hpd_irq_data); + + if ((dc_link->cur_link_settings.lane_count != LANE_COUNT_UNKNOWN) || + (dc_link->type == dc_connection_mst_branch)) { + if (hpd_irq_data.bytes.device_service_irq.bits.UP_REQ_MSG_RDY) { + result = true; + dm_handle_hpd_rx_irq(aconnector); + goto out; + } else if (hpd_irq_data.bytes.device_service_irq.bits.DOWN_REP_MSG_RDY) { + result = false; + dm_handle_hpd_rx_irq(aconnector); + goto out; + } + } + mutex_lock(&adev->dm.dc_lock); #ifdef CONFIG_DRM_AMD_DC_HDCP result = dc_link_handle_hpd_rx_irq(dc_link, &hpd_irq_data, NULL); @@ -2585,6 +2598,7 @@ static void handle_hpd_rx_irq(void *param) #endif mutex_unlock(&adev->dm.dc_lock); +out: if (result && !is_mst_root_connector) { /* Downstream Port status changed. */ if (!dc_link_detect_sink(dc_link, &new_connection_type)) @@ -2625,9 +2639,6 @@ static void handle_hpd_rx_irq(void *param) hdcp_handle_cpirq(adev->dm.hdcp_workqueue, aconnector->base.index); } #endif - if ((dc_link->cur_link_settings.lane_count != LANE_COUNT_UNKNOWN) || - (dc_link->type == dc_connection_mst_branch)) - dm_handle_hpd_rx_irq(aconnector); if (dc_link->type != dc_connection_mst_branch) { drm_dp_cec_irq(&aconnector->dm_dp_aux.aux); diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c index dbbc0ec0b699..6b11d4af54af 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c @@ -1874,7 +1874,7 @@ static struct dc_link_settings get_max_link_cap(struct dc_link *link) return max_link_cap; } -static enum dc_status read_hpd_rx_irq_data( +enum dc_status read_hpd_rx_irq_data( struct dc_link *link, union hpd_irq_data *irq_data) { diff --git a/drivers/gpu/drm/amd/display/dc/dc_link.h b/drivers/gpu/drm/amd/display/dc/dc_link.h index 66445e34fd37..6d9a60c9dcc0 100644 --- a/drivers/gpu/drm/amd/display/dc/dc_link.h +++ b/drivers/gpu/drm/amd/display/dc/dc_link.h @@ -259,6 +259,10 @@ enum dc_status dc_link_reallocate_mst_payload(struct dc_link *link); bool dc_link_handle_hpd_rx_irq(struct dc_link *dc_link, union hpd_irq_data *hpd_irq_dpcd_data, bool *out_link_loss); +enum dc_status read_hpd_rx_irq_data( + struct dc_link *link, + union hpd_irq_data *irq_data); + struct dc_sink_init_data; struct dc_sink *dc_link_add_remote_sink( -- cgit v1.2.3 From 80089dd8410f356d5104496d5ab71a66a4f4646b Mon Sep 17 00:00:00 2001 From: Chris Park Date: Tue, 24 Nov 2020 20:11:25 -0500 Subject: drm/amd/display: Prevent bandwidth overflow [Why] At very high pixel clock, bandwidth calculation exceeds 32 bit size and overflow value. This causes the resulting selection of link rate to be inaccurate. [How] Change order of operation and use fixed point to deal with integer accuracy. Also address bug found when forcing link rate. Signed-off-by: Chris Park Reviewed-by: Wenjing Liu Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index bd004de107b7..0052247b4b20 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -3444,10 +3444,13 @@ uint32_t dc_bandwidth_in_kbps_from_timing( { uint32_t bits_per_channel = 0; uint32_t kbps; + struct fixed31_32 link_bw_kbps; if (timing->flags.DSC) { - kbps = (timing->pix_clk_100hz * timing->dsc_cfg.bits_per_pixel); - kbps = kbps / 160 + ((kbps % 160) ? 1 : 0); + link_bw_kbps = dc_fixpt_from_int(timing->pix_clk_100hz); + link_bw_kbps = dc_fixpt_div_int(link_bw_kbps, 160); + link_bw_kbps = dc_fixpt_mul_int(link_bw_kbps, timing->dsc_cfg.bits_per_pixel); + kbps = dc_fixpt_ceil(link_bw_kbps); return kbps; } -- cgit v1.2.3 From 4bbfae00ac22810de9e539258f27ab5993619493 Mon Sep 17 00:00:00 2001 From: Sung Lee Date: Mon, 23 Nov 2020 15:38:54 -0500 Subject: drm/amd/display: Add wm table for Renoir [Why] Without additional HostVM Latency, Renoir takes 2us longer to exit self-refresh. This causes underflow in certain cases. [How] Add table for Renoir with updated sr exit latencies for WM set A. Signed-off-by: Sung Lee Reviewed-by: Yongqiang Sun Reviewed-by: Roman Li Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c | 93 +++++++++++++++++++++- 1 file changed, 89 insertions(+), 4 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c index fe6dc1e68e60..6f4fe8fce6b7 100644 --- a/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c +++ b/drivers/gpu/drm/amd/display/dc/clk_mgr/dcn21/rn_clk_mgr.c @@ -621,7 +621,7 @@ static struct clk_bw_params rn_bw_params = { }; -static struct wm_table ddr4_wm_table = { +static struct wm_table ddr4_wm_table_gs = { .entries = { { .wm_inst = WM_A, @@ -658,7 +658,7 @@ static struct wm_table ddr4_wm_table = { } }; -static struct wm_table lpddr4_wm_table = { +static struct wm_table lpddr4_wm_table_gs = { .entries = { { .wm_inst = WM_A, @@ -732,6 +732,80 @@ static struct wm_table lpddr4_wm_table_with_disabled_ppt = { } }; +static struct wm_table ddr4_wm_table_rn = { + .entries = { + { + .wm_inst = WM_A, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.72, + .sr_exit_time_us = 9.09, + .sr_enter_plus_exit_time_us = 10.14, + .valid = true, + }, + { + .wm_inst = WM_B, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.72, + .sr_exit_time_us = 10.12, + .sr_enter_plus_exit_time_us = 11.48, + .valid = true, + }, + { + .wm_inst = WM_C, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.72, + .sr_exit_time_us = 10.12, + .sr_enter_plus_exit_time_us = 11.48, + .valid = true, + }, + { + .wm_inst = WM_D, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.72, + .sr_exit_time_us = 10.12, + .sr_enter_plus_exit_time_us = 11.48, + .valid = true, + }, + } +}; + +static struct wm_table lpddr4_wm_table_rn = { + .entries = { + { + .wm_inst = WM_A, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.65333, + .sr_exit_time_us = 7.32, + .sr_enter_plus_exit_time_us = 8.38, + .valid = true, + }, + { + .wm_inst = WM_B, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.65333, + .sr_exit_time_us = 9.82, + .sr_enter_plus_exit_time_us = 11.196, + .valid = true, + }, + { + .wm_inst = WM_C, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.65333, + .sr_exit_time_us = 9.89, + .sr_enter_plus_exit_time_us = 11.24, + .valid = true, + }, + { + .wm_inst = WM_D, + .wm_type = WM_TYPE_PSTATE_CHG, + .pstate_latency_us = 11.65333, + .sr_exit_time_us = 9.748, + .sr_enter_plus_exit_time_us = 11.102, + .valid = true, + }, + } +}; + static unsigned int find_dcfclk_for_voltage(struct dpm_clocks *clock_table, unsigned int voltage) { int i; @@ -813,6 +887,11 @@ void rn_clk_mgr_construct( struct dc_debug_options *debug = &ctx->dc->debug; struct dpm_clocks clock_table = { 0 }; enum pp_smu_status status = 0; + int is_green_sardine = 0; + +#if defined(CONFIG_DRM_AMD_DC_DCN) + is_green_sardine = ASICREV_IS_GREEN_SARDINE(ctx->asic_id.hw_internal_rev); +#endif clk_mgr->base.ctx = ctx; clk_mgr->base.funcs = &dcn21_funcs; @@ -853,10 +932,16 @@ void rn_clk_mgr_construct( if (clk_mgr->periodic_retraining_disabled) { rn_bw_params.wm_table = lpddr4_wm_table_with_disabled_ppt; } else { - rn_bw_params.wm_table = lpddr4_wm_table; + if (is_green_sardine) + rn_bw_params.wm_table = lpddr4_wm_table_gs; + else + rn_bw_params.wm_table = lpddr4_wm_table_rn; } } else { - rn_bw_params.wm_table = ddr4_wm_table; + if (is_green_sardine) + rn_bw_params.wm_table = ddr4_wm_table_gs; + else + rn_bw_params.wm_table = ddr4_wm_table_rn; } /* Saved clocks configured at boot for debug purposes */ rn_dump_clk_registers(&clk_mgr->base.boot_snapshot, &clk_mgr->base, &log_info); -- cgit v1.2.3 From c0794a3b5999d612c396a66875ccaf93cf396631 Mon Sep 17 00:00:00 2001 From: Roy Chan Date: Tue, 24 Nov 2020 18:20:13 -0500 Subject: drm/amd/display: Fixed the audio noise during mode switching with HDCP mode on [Why] When HDCP is on, some display would introduce audio noise during HDCP handling. [How] Mute before HDCP handling when disabling core link. Unmute after HDCP when enabling core link. Signed-off-by: Roy Chan Reviewed-by: Martin Leung Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc_link.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link.c b/drivers/gpu/drm/amd/display/dc/core/dc_link.c index 0052247b4b20..a901baf2aaef 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link.c @@ -3270,8 +3270,6 @@ void core_link_enable_stream( #if defined(CONFIG_DRM_AMD_DC_DCN3_0) #endif - dc->hwss.enable_audio_stream(pipe_ctx); - /* turn off otg test pattern if enable */ if (pipe_ctx->stream_res.tg->funcs->set_test_pattern) pipe_ctx->stream_res.tg->funcs->set_test_pattern(pipe_ctx->stream_res.tg, @@ -3310,6 +3308,9 @@ void core_link_enable_stream( #if defined(CONFIG_DRM_AMD_DC_HDCP) update_psp_stream_config(pipe_ctx, false); #endif + + dc->hwss.enable_audio_stream(pipe_ctx); + } else { // if (IS_FPGA_MAXIMUS_DC(dc->ctx->dce_environment)) if (dc_is_dp_signal(pipe_ctx->stream->signal) || dc_is_virtual_signal(pipe_ctx->stream->signal)) @@ -3337,6 +3338,8 @@ void core_link_disable_stream(struct pipe_ctx *pipe_ctx) core_link_set_avmute(pipe_ctx, true); } + dc->hwss.disable_audio_stream(pipe_ctx); + #if defined(CONFIG_DRM_AMD_DC_HDCP) update_psp_stream_config(pipe_ctx, true); #endif -- cgit v1.2.3 From 6df9218a22a9c572ca0abb793eb4577bcb019654 Mon Sep 17 00:00:00 2001 From: Charlene Liu Date: Fri, 27 Nov 2020 19:08:41 -0500 Subject: drm/amd/display: Enable gpu_vm_support for dcn3.01 [Why] dcn3_01 supports gpu_vm, but this is not enabled in amdgpu_dm Signed-off-by: Charlene Liu Reviewed-by: Yongqiang Sun Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 508457cca343..ee3947c6521e 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -1035,6 +1035,11 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) if (ASICREV_IS_GREEN_SARDINE(adev->external_rev_id)) init_data.flags.disable_dmcu = true; break; +#if defined(CONFIG_DRM_AMD_DC_DCN) + case CHIP_VANGOGH: + init_data.flags.gpu_vm_support = true; + break; +#endif default: break; } -- cgit v1.2.3 From 3abad347c432b9f5904cfad40f417d5cff90300c Mon Sep 17 00:00:00 2001 From: Michael Strauss Date: Fri, 27 Nov 2020 14:21:37 -0500 Subject: drm/amd/display: Revert DCN2.1 dram_clock_change_latency update [Why] New value breaks VSR on high refresh panels, reverting until a fix is developed Signed-off-by: Michael Strauss Signed-off-by: Sung Lee Reviewed-by: Yongqiang Sun Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c index b000b43a820d..1c88d2edd381 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c @@ -296,7 +296,7 @@ struct _vcs_dpi_soc_bounding_box_st dcn2_1_soc = { .num_banks = 8, .num_chans = 4, .vmm_page_size_bytes = 4096, - .dram_clock_change_latency_us = 11.72, + .dram_clock_change_latency_us = 23.84, .return_bus_width_bytes = 64, .dispclk_dppclk_vco_speed_mhz = 3600, .xfc_bus_transport_time_us = 4, -- cgit v1.2.3 From 8b19a4e351e2d453e4a9a69ff6098ef60b1eaa12 Mon Sep 17 00:00:00 2001 From: Anthony Koo Date: Sun, 29 Nov 2020 20:16:33 -0500 Subject: drm/amd/display: [FW Promotion] Release 0.0.45 - Add define for __forceinline Signed-off-by: Anthony Koo Reviewed-by: Aric Cyr Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h index 4b7a1b8ad9e0..b20a39f488ae 100644 --- a/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h +++ b/drivers/gpu/drm/amd/display/dmub/inc/dmub_cmd.h @@ -26,6 +26,15 @@ #ifndef _DMUB_CMD_H_ #define _DMUB_CMD_H_ +#if defined(_TEST_HARNESS) || defined(FPGA_USB4) +#include "dmub_fw_types.h" +#include "include_legacy/atomfirmware.h" + +#if defined(_TEST_HARNESS) +#include +#endif +#else + #include #include #include @@ -34,12 +43,14 @@ #include "atomfirmware.h" +#endif // defined(_TEST_HARNESS) || defined(FPGA_USB4) + /* Firmware versioning. */ #ifdef DMUB_EXPOSE_VERSION -#define DMUB_FW_VERSION_GIT_HASH 0x685065427 +#define DMUB_FW_VERSION_GIT_HASH 0x931573111 #define DMUB_FW_VERSION_MAJOR 0 #define DMUB_FW_VERSION_MINOR 0 -#define DMUB_FW_VERSION_REVISION 44 +#define DMUB_FW_VERSION_REVISION 45 #define DMUB_FW_VERSION_TEST 0 #define DMUB_FW_VERSION_VBIOS 0 #define DMUB_FW_VERSION_HOTFIX 0 @@ -55,6 +66,8 @@ //================================================================== /* Basic type definitions. */ +#define __forceinline inline + #define SET_ABM_PIPE_GRADUALLY_DISABLE 0 #define SET_ABM_PIPE_IMMEDIATELY_DISABLE 255 #define SET_ABM_PIPE_IMMEDIATE_KEEP_GAIN_DISABLE 254 -- cgit v1.2.3 From aec0ebd651a69e3c52b3946514f3cf3b67b7467c Mon Sep 17 00:00:00 2001 From: Aric Cyr Date: Mon, 30 Nov 2020 11:22:20 -0500 Subject: drm/amd/display: 3.2.115 Signed-off-by: Aric Cyr Acked-by: Eryk Brol Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dc.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h index 54a829f95346..b8f1e2d33423 100644 --- a/drivers/gpu/drm/amd/display/dc/dc.h +++ b/drivers/gpu/drm/amd/display/dc/dc.h @@ -42,7 +42,7 @@ #include "inc/hw/dmcu.h" #include "dml/display_mode_lib.h" -#define DC_VER "3.2.114" +#define DC_VER "3.2.115" #define MAX_SURFACES 3 #define MAX_PLANES 6 -- cgit v1.2.3 From 13524856336dfd055a8c7c5b4e5524553a12e938 Mon Sep 17 00:00:00 2001 From: Roman Li Date: Tue, 1 Dec 2020 13:57:25 -0500 Subject: drm/amd/display: setup system context for APUs [Why] Scatter/gather is APU feature. But in dm it is limited only to Renoir. Now we need it for Vangogh. [How] Apply system context setup in dm_init to all APUs. Signed-off-by: Roman Li Reviewed-by: Nicholas Kazlauskas Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index ee3947c6521e..20e448e8a5a3 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -1093,7 +1093,7 @@ static int amdgpu_dm_init(struct amdgpu_device *adev) dc_hardware_init(adev->dm.dc); #if defined(CONFIG_DRM_AMD_DC_DCN) - if (adev->asic_type == CHIP_RENOIR) { + if (adev->apu_flags) { struct dc_phy_addr_space_config pa_config; mmhub_read_system_context(adev, &pa_config); -- cgit v1.2.3 From 5f6fab247c7f206731df8bbb096b7624facf9d90 Mon Sep 17 00:00:00 2001 From: Alex Deucher Date: Fri, 4 Dec 2020 11:52:00 -0500 Subject: drm/amdgpu: free the pre-OS console framebuffer after the first modeset MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Rather than in late_init to avoid race conditions between freeing the buffers and the initial modeset. Reviewed-by: Christian König Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c | 8 ++------ drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 5 +++++ 2 files changed, 7 insertions(+), 6 deletions(-) (limited to 'drivers/gpu/drm/amd/display') diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c index e49b519aab80..6be131df21f5 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c @@ -2026,10 +2026,6 @@ int amdgpu_ttm_init(struct amdgpu_device *adev) */ void amdgpu_ttm_late_init(struct amdgpu_device *adev) { - /* return the VGA stolen memory (if any) back to VRAM */ - if (!adev->mman.keep_stolen_vga_memory) - amdgpu_bo_free_kernel(&adev->mman.stolen_vga_memory, NULL, NULL); - amdgpu_bo_free_kernel(&adev->mman.stolen_extended_memory, NULL, NULL); } /* @@ -2042,8 +2038,8 @@ void amdgpu_ttm_fini(struct amdgpu_device *adev) amdgpu_ttm_training_reserve_vram_fini(adev); /* return the stolen vga memory back to VRAM */ - if (adev->mman.keep_stolen_vga_memory) - amdgpu_bo_free_kernel(&adev->mman.stolen_vga_memory, NULL, NULL); + amdgpu_bo_free_kernel(&adev->mman.stolen_vga_memory, NULL, NULL); + amdgpu_bo_free_kernel(&adev->mman.stolen_extended_memory, NULL, NULL); /* return the IP Discovery TMR memory back to VRAM */ amdgpu_bo_free_kernel(&adev->mman.discovery_memory, NULL, NULL); amdgpu_ttm_fw_reserve_vram_fini(adev); diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c index 20e448e8a5a3..c23896207e9d 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c @@ -8462,6 +8462,11 @@ static void amdgpu_dm_atomic_commit_tail(struct drm_atomic_state *state) drm_atomic_helper_cleanup_planes(dev, state); + /* return the stolen vga memory back to VRAM */ + if (!adev->mman.keep_stolen_vga_memory) + amdgpu_bo_free_kernel(&adev->mman.stolen_vga_memory, NULL, NULL); + amdgpu_bo_free_kernel(&adev->mman.stolen_extended_memory, NULL, NULL); + /* * Finally, drop a runtime PM reference for each newly disabled CRTC, * so we can put the GPU into runtime suspend if we're not driving any -- cgit v1.2.3