From c8fea9273fd1be308668496badfcbd55183e0dd3 Mon Sep 17 00:00:00 2001 From: Guchun Chen Date: Wed, 24 Aug 2022 23:00:02 +0800 Subject: [PATCH 01/21] drm/amdgpu: disable FRU access on special SIENNA CICHLID card Below driver load error will be printed, not friendly to end user. amdgpu: ATOM BIOS: 113-D603GLXE-077 [drm] FRU: Failed to get size field [drm:amdgpu_fru_get_product_info [amdgpu]] *ERROR* Failed to read FRU Manufacturer, ret:-5 Signed-off-by: Guchun Chen Reviewed-by: Kent Russell Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_fru_eeprom.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_fru_eeprom.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_fru_eeprom.c index ecada5eadfe3..e325150879df 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_fru_eeprom.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_fru_eeprom.c @@ -66,10 +66,15 @@ static bool is_fru_eeprom_supported(struct amdgpu_device *adev) return true; case CHIP_SIENNA_CICHLID: if (strnstr(atom_ctx->vbios_version, "D603", + sizeof(atom_ctx->vbios_version))) { + if (strnstr(atom_ctx->vbios_version, "D603GLXE", sizeof(atom_ctx->vbios_version))) - return true; - else + return false; + else + return true; + } else { return false; + } default: return false; } From 47e04eed84bb07cc5b54462752a4bc7286ab8197 Mon Sep 17 00:00:00 2001 From: Graham Sider Date: Mon, 15 Aug 2022 13:28:19 -0400 Subject: [PATCH 02/21] drm/amdgpu: Update mes_v11_api_def.h New GFX11 MES FW adds the trap_en bit. For now hardcode to 1 (traps enabled). Signed-off-by: Graham Sider Acked-by: Felix Kuehling Reviewed-by: Harish Kasiviswanathan Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/mes_v11_0.c | 1 + drivers/gpu/drm/amd/include/mes_v11_api_def.h | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c b/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c index 120ea294abef..cc3fdbbcd314 100644 --- a/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c +++ b/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c @@ -183,6 +183,7 @@ static int mes_v11_0_add_hw_queue(struct amdgpu_mes *mes, mes_add_queue_pkt.trap_handler_addr = input->tba_addr; mes_add_queue_pkt.tma_addr = input->tma_addr; mes_add_queue_pkt.is_kfd_process = input->is_kfd_process; + mes_add_queue_pkt.trap_en = 1; return mes_v11_0_submit_pkt_and_poll_completion(mes, &mes_add_queue_pkt, sizeof(mes_add_queue_pkt), diff --git a/drivers/gpu/drm/amd/include/mes_v11_api_def.h b/drivers/gpu/drm/amd/include/mes_v11_api_def.h index 80dab1146439..50bfa513cb35 100644 --- a/drivers/gpu/drm/amd/include/mes_v11_api_def.h +++ b/drivers/gpu/drm/amd/include/mes_v11_api_def.h @@ -268,7 +268,8 @@ union MESAPI__ADD_QUEUE { uint32_t is_tmz_queue : 1; uint32_t map_kiq_utility_queue : 1; uint32_t is_kfd_process : 1; - uint32_t reserved : 22; + uint32_t trap_en : 1; + uint32_t reserved : 21; }; struct MES_API_STATUS api_status; uint64_t tma_addr; From 507fd7c400032b126747a5ae8cca2816d73f009a Mon Sep 17 00:00:00 2001 From: George Shen Date: Wed, 10 Aug 2022 22:06:17 -0400 Subject: [PATCH 03/21] drm/amd/display: Fix DCN32 DPSTREAMCLK_CNTL programming [Why] Each index in the DPSTREAMCLK_CNTL register phyiscally maps 1-to-1 with HPO stream encoder instance. On the other hand, each index in DTBCLK_P_CNTL physically maps 1-to-1 with OTG instance. Current DCN32 DPSTREAMCLK_CLK programing assumes that OTG instance always maps 1-to-1 with HPO stream encoder instance. This is not always guaranteed and can result in blackscreen. [How] Program the correct dpstreamclk instance with the correct dtbclk_p source. Reviewed-by: Ariel Bernstein Acked-by: Brian Chang Signed-off-by: George Shen Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c | 8 ++++---- drivers/gpu/drm/amd/display/dc/link/link_hwss_hpo_dp.c | 4 ++-- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c index a31c64b50410..0d5e8a441512 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c +++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dccg.c @@ -225,19 +225,19 @@ void dccg32_set_dpstreamclk( case 0: REG_UPDATE_2(DPSTREAMCLK_CNTL, DPSTREAMCLK0_EN, - (src == REFCLK) ? 0 : 1, DPSTREAMCLK0_SRC_SEL, 0); + (src == REFCLK) ? 0 : 1, DPSTREAMCLK0_SRC_SEL, otg_inst); break; case 1: REG_UPDATE_2(DPSTREAMCLK_CNTL, DPSTREAMCLK1_EN, - (src == REFCLK) ? 0 : 1, DPSTREAMCLK1_SRC_SEL, 1); + (src == REFCLK) ? 0 : 1, DPSTREAMCLK1_SRC_SEL, otg_inst); break; case 2: REG_UPDATE_2(DPSTREAMCLK_CNTL, DPSTREAMCLK2_EN, - (src == REFCLK) ? 0 : 1, DPSTREAMCLK2_SRC_SEL, 2); + (src == REFCLK) ? 0 : 1, DPSTREAMCLK2_SRC_SEL, otg_inst); break; case 3: REG_UPDATE_2(DPSTREAMCLK_CNTL, DPSTREAMCLK3_EN, - (src == REFCLK) ? 0 : 1, DPSTREAMCLK3_SRC_SEL, 3); + (src == REFCLK) ? 0 : 1, DPSTREAMCLK3_SRC_SEL, otg_inst); break; default: BREAK_TO_DEBUGGER(); diff --git a/drivers/gpu/drm/amd/display/dc/link/link_hwss_hpo_dp.c b/drivers/gpu/drm/amd/display/dc/link/link_hwss_hpo_dp.c index db7b0b155374..226af06278ce 100644 --- a/drivers/gpu/drm/amd/display/dc/link/link_hwss_hpo_dp.c +++ b/drivers/gpu/drm/amd/display/dc/link/link_hwss_hpo_dp.c @@ -116,7 +116,7 @@ static void setup_hpo_dp_stream_encoder(struct pipe_ctx *pipe_ctx) dto_params.timing = &pipe_ctx->stream->timing; dto_params.ref_dtbclk_khz = dc->clk_mgr->funcs->get_dtb_ref_clk_frequency(dc->clk_mgr); - dccg->funcs->set_dpstreamclk(dccg, DTBCLK0, tg->inst, link_enc->inst); + dccg->funcs->set_dpstreamclk(dccg, DTBCLK0, tg->inst, stream_enc->inst); dccg->funcs->enable_symclk32_se(dccg, stream_enc->inst, phyd32clk); dccg->funcs->set_dtbclk_dto(dccg, &dto_params); stream_enc->funcs->enable_stream(stream_enc); @@ -137,7 +137,7 @@ static void reset_hpo_dp_stream_encoder(struct pipe_ctx *pipe_ctx) stream_enc->funcs->disable(stream_enc); dccg->funcs->set_dtbclk_dto(dccg, &dto_params); dccg->funcs->disable_symclk32_se(dccg, stream_enc->inst); - dccg->funcs->set_dpstreamclk(dccg, REFCLK, tg->inst, pipe_ctx->link_res.hpo_dp_link_enc->inst); + dccg->funcs->set_dpstreamclk(dccg, REFCLK, tg->inst, stream_enc->inst); } static void setup_hpo_dp_stream_attribute(struct pipe_ctx *pipe_ctx) From d1b4a51a4ca8954f30cf4671b25c4f8637c45600 Mon Sep 17 00:00:00 2001 From: Duncan Ma Date: Mon, 15 Aug 2022 17:37:32 -0400 Subject: [PATCH 04/21] drm/amd/display: Fix OTG H timing reset for dcn314 [Why] When ODM is enabled, H timing control register reset to 0. Div mode manual field get overwritten causing no display on certain modes for dcn314. [How] Use REG_UPDATE instead of REG_SET to set div_mode field. Reviewed-by: Charlene Liu Reviewed-by: Nicholas Kazlauskas Acked-by: Brian Chang Signed-off-by: Duncan Ma Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn314/dcn314_optc.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_optc.c b/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_optc.c index 0c7980266b85..38aa28ec6b13 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_optc.c +++ b/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_optc.c @@ -98,7 +98,8 @@ static void optc314_set_odm_combine(struct timing_generator *optc, int *opp_id, REG_UPDATE(OPTC_WIDTH_CONTROL, OPTC_SEGMENT_WIDTH, mpcc_hactive); - REG_SET(OTG_H_TIMING_CNTL, 0, OTG_H_TIMING_DIV_MODE, opp_cnt - 1); + REG_UPDATE(OTG_H_TIMING_CNTL, + OTG_H_TIMING_DIV_MODE, opp_cnt - 1); optc1->opp_count = opp_cnt; } From 3c93603d9568c7c4b20ff1712ddc60e997d78df7 Mon Sep 17 00:00:00 2001 From: YuBiao Wang Date: Wed, 24 Aug 2022 15:56:04 +0800 Subject: [PATCH 05/21] drm/amdgpu: Fix use-after-free in amdgpu_cs_ioctl [Why] In amdgpu_cs_ioctl, amdgpu_job_free could be performed ealier if there is -ERESTARTSYS error. In this case, job->hw_fence could be not initialized yet. Putting hw_fence during amdgpu_job_free could lead to a use-after-free warning. [How] Check if drm_sched_job_init is performed before job_free by checking s_fence. v2: Check hw_fence.ops instead since it could be NULL if fence is not initialized. Reverse the condition since !=NULL check is discouraged in kernel. Signed-off-by: YuBiao Wang Reviewed-by: Andrey Grodzovsky Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_job.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c index b1099ee79c50..c2fd6f3076a6 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_job.c @@ -159,7 +159,10 @@ void amdgpu_job_free(struct amdgpu_job *job) amdgpu_sync_free(&job->sync); amdgpu_sync_free(&job->sched_sync); - dma_fence_put(&job->hw_fence); + if (!job->hw_fence.ops) + kfree(job); + else + dma_fence_put(&job->hw_fence); } int amdgpu_job_submit(struct amdgpu_job *job, struct drm_sched_entity *entity, From 3e834a17a22cb8e9169c0b018d1a2df126977db3 Mon Sep 17 00:00:00 2001 From: Wang Fudong Date: Wed, 17 Aug 2022 17:47:50 +0800 Subject: [PATCH 06/21] drm/amd/display: set dig fifo read start level to 7 before dig fifo reset [Why] DIG_FIFO_ERROR = 1 caused mst daisy chain 2nd monitor black. [How] We need to set dig fifo read start level = 7 before dig fifo reset during dig fifo enable according to hardware designer's suggestion. If it is zero, it will cause underflow or overflow and DIG_FIFO_ERROR = 1. Reviewed-by: Alvin Lee Reviewed-by: Aric Cyr Acked-by: Brian Chang Signed-off-by: Wang Fudong Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- .../gpu/drm/amd/display/dc/dcn32/dcn32_dio_stream_encoder.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dio_stream_encoder.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dio_stream_encoder.c index 26648ce772da..38a48983f663 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dio_stream_encoder.c +++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_dio_stream_encoder.c @@ -310,6 +310,11 @@ static void enc32_stream_encoder_dp_unblank( // TODO: Confirm if we need to wait for DIG_SYMCLK_FE_ON REG_WAIT(DIG_FE_CNTL, DIG_SYMCLK_FE_ON, 1, 10, 5000); + /* read start level = 0 will bring underflow / overflow and DIG_FIFO_ERROR = 1 + * so set it to 1/2 full = 7 before reset as suggested by hardware team. + */ + REG_UPDATE(DIG_FIFO_CTRL0, DIG_FIFO_READ_START_LEVEL, 0x7); + REG_UPDATE(DIG_FIFO_CTRL0, DIG_FIFO_RESET, 1); REG_WAIT(DIG_FIFO_CTRL0, DIG_FIFO_RESET_DONE, 1, 10, 5000); From 6783e6bbc2457dbed351fb0d2477aa6060a7d32b Mon Sep 17 00:00:00 2001 From: Leo Chen Date: Thu, 18 Aug 2022 13:21:37 -0400 Subject: [PATCH 07/21] drm/amd/display: Missing HPO instance added [Why & How] Number of encoder is set to 4 but only 3 instances are created. Reviewed-by: Charlene Liu Acked-by: Brian Chang Signed-off-by: Leo Chen Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn314/dcn314_resource.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_resource.c b/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_resource.c index 3a9e3870b3a9..2a2a4a9cc117 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_resource.c +++ b/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_resource.c @@ -454,6 +454,7 @@ static const struct dcn31_hpo_dp_stream_encoder_registers hpo_dp_stream_enc_regs hpo_dp_stream_encoder_reg_list(0), hpo_dp_stream_encoder_reg_list(1), hpo_dp_stream_encoder_reg_list(2), + hpo_dp_stream_encoder_reg_list(3) }; static const struct dcn31_hpo_dp_stream_encoder_shift hpo_dp_se_shift = { From 4fd7f14b56b2e727dd66a62e217e57015da4e9fd Mon Sep 17 00:00:00 2001 From: Aurabindo Pillai Date: Thu, 18 Aug 2022 17:25:05 -0400 Subject: [PATCH 08/21] drm/amd/display: Fix CAB cursor size allocation for DCN32/321 For calculating cursor size allocation, surface size was used, resulting in over allocation Reviewed-by: Alvin Lee Reviewed-by: Nicholas Kazlauskas Acked-by: Brian Chang Signed-off-by: Aurabindo Pillai Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c index ebd3945c71f1..a3e8648a319f 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c @@ -312,7 +312,7 @@ static uint32_t dcn32_calculate_cab_allocation(struct dc *dc, struct dc_state *c cursor_size *= 8; break; } - cache_lines_used += dcn32_cache_lines_for_surface(dc, surface_size, + cache_lines_used += dcn32_cache_lines_for_surface(dc, cursor_size, plane->address.grph.cursor_cache_addr.quad_part); } } From 94a82c9e3dffb88182a4ed0464dc0266ad0d7b45 Mon Sep 17 00:00:00 2001 From: Aurabindo Pillai Date: Thu, 18 Aug 2022 12:34:06 -0400 Subject: [PATCH 09/21] drm/amd/display: disable display fresh from MALL on an edge case for DCN321 [Why&How] When using a 4k monitor when cursor caching is not supported due to framebuffer being on an uncacheable address, enabling display refresh from MALL would trigger corruption if SS is enabled. Prevent entering SS if we are on the edge case and cursor caching is not possible. Do this only if cursor size larger than a 64x64@4bpp. Pull the cursor size calculation out of if condition since cursor address may not be set on all platforms Reviewed-by: Alvin Lee Reviewed-by: Nicholas Kazlauskas Acked-by: Brian Chang Signed-off-by: Aurabindo Pillai Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/dcn32/dcn32_hwseq.c | 43 ++++++++++++------- 1 file changed, 27 insertions(+), 16 deletions(-) diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c index a3e8648a319f..dc296aac89f4 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c @@ -295,23 +295,24 @@ static uint32_t dcn32_calculate_cab_allocation(struct dc *dc, struct dc_state *c } // Include cursor size for CAB allocation - if (stream->cursor_position.enable && plane->address.grph.cursor_cache_addr.quad_part) { - cursor_size = dc->caps.max_cursor_size * dc->caps.max_cursor_size; - switch (stream->cursor_attributes.color_format) { - case CURSOR_MODE_MONO: - cursor_size /= 2; - break; - case CURSOR_MODE_COLOR_1BIT_AND: - case CURSOR_MODE_COLOR_PRE_MULTIPLIED_ALPHA: - case CURSOR_MODE_COLOR_UN_PRE_MULTIPLIED_ALPHA: - cursor_size *= 4; - break; + cursor_size = dc->caps.max_cursor_size * dc->caps.max_cursor_size; + switch (stream->cursor_attributes.color_format) { + case CURSOR_MODE_MONO: + cursor_size /= 2; + break; + case CURSOR_MODE_COLOR_1BIT_AND: + case CURSOR_MODE_COLOR_PRE_MULTIPLIED_ALPHA: + case CURSOR_MODE_COLOR_UN_PRE_MULTIPLIED_ALPHA: + cursor_size *= 4; + break; - case CURSOR_MODE_COLOR_64BIT_FP_PRE_MULTIPLIED: - case CURSOR_MODE_COLOR_64BIT_FP_UN_PRE_MULTIPLIED: - cursor_size *= 8; - break; - } + case CURSOR_MODE_COLOR_64BIT_FP_PRE_MULTIPLIED: + case CURSOR_MODE_COLOR_64BIT_FP_UN_PRE_MULTIPLIED: + cursor_size *= 8; + break; + } + + if (stream->cursor_position.enable && plane->address.grph.cursor_cache_addr.quad_part) { cache_lines_used += dcn32_cache_lines_for_surface(dc, cursor_size, plane->address.grph.cursor_cache_addr.quad_part); } @@ -325,6 +326,16 @@ static uint32_t dcn32_calculate_cab_allocation(struct dc *dc, struct dc_state *c if (cache_lines_used % lines_per_way > 0) num_ways++; + if (stream->cursor_position.enable && + !plane->address.grph.cursor_cache_addr.quad_part && + cursor_size > 16384) + /* Cursor caching is not supported since it won't be on the same line. + * So we need an extra line to accommodate it. With large cursors and a single 4k monitor + * this case triggers corruption. If we're at the edge, then dont trigger display refresh + * from MALL. We only need to cache cursor if its greater that 64x64 at 4 bpp. + */ + num_ways++; + return num_ways; } From 595091c6ba35ba48c1f8186116bbbae2b208dce6 Mon Sep 17 00:00:00 2001 From: Aurabindo Pillai Date: Thu, 18 Aug 2022 17:55:01 -0400 Subject: [PATCH 10/21] drm/amd/display: use actual cursor size instead of max for CAB allocation [Why&How] When calculating allocation for cursor size, get the real cursor through the HUBP instead of using the maximum cursor size for more optimal allocation Reviewed-by: Alvin Lee Reviewed-by: Nicholas Kazlauskas Acked-by: Brian Chang Signed-off-by: Aurabindo Pillai Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- .../gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c index dc296aac89f4..18287743add5 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c @@ -295,7 +295,20 @@ static uint32_t dcn32_calculate_cab_allocation(struct dc *dc, struct dc_state *c } // Include cursor size for CAB allocation - cursor_size = dc->caps.max_cursor_size * dc->caps.max_cursor_size; + for (i = 0; i < dc->res_pool->pipe_count; i++) { + struct pipe_ctx *pipe = &ctx->res_ctx.pipe_ctx[i]; + struct hubp *hubp = pipe->plane_res.hubp; + + if (pipe->stream && pipe->plane_state && hubp) + /* Find the cursor plane and use the exact size instead of + * using the max for calculation + */ + if (hubp->curs_attr.width > 0) { + cursor_size = hubp->curs_attr.width * hubp->curs_attr.height; + break; + } + } + switch (stream->cursor_attributes.color_format) { case CURSOR_MODE_MONO: cursor_size /= 2; From d0629cea1f97acc5e8d95ca2a42ddc72ed4ffa3b Mon Sep 17 00:00:00 2001 From: Charlene Liu Date: Thu, 18 Aug 2022 20:24:26 -0400 Subject: [PATCH 11/21] drm/amd/display: fix wrong register access [why] fw version check was for release branch. for staging, it has a chance to enter wrong code path. Reviewed-by: Hansen Dsouza Acked-by: Brian Chang Signed-off-by: Charlene Liu Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn31/dcn31_dio_link_encoder.c | 3 +++ .../gpu/drm/amd/display/dc/dcn314/dcn314_dio_stream_encoder.c | 1 + 2 files changed, 4 insertions(+) diff --git a/drivers/gpu/drm/amd/display/dc/dcn31/dcn31_dio_link_encoder.c b/drivers/gpu/drm/amd/display/dc/dcn31/dcn31_dio_link_encoder.c index a788d160953b..ab70ebd8f223 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn31/dcn31_dio_link_encoder.c +++ b/drivers/gpu/drm/amd/display/dc/dcn31/dcn31_dio_link_encoder.c @@ -104,6 +104,9 @@ static bool has_query_dp_alt(struct link_encoder *enc) { struct dc_dmub_srv *dc_dmub_srv = enc->ctx->dmub_srv; + if (enc->ctx->dce_version >= DCN_VERSION_3_15) + return true; + /* Supports development firmware and firmware >= 4.0.11 */ return dc_dmub_srv && !(dc_dmub_srv->dmub->fw_version >= DMUB_FW_VERSION(4, 0, 0) && diff --git a/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_dio_stream_encoder.c b/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_dio_stream_encoder.c index b384f30395d3..e3351ddc566c 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_dio_stream_encoder.c +++ b/drivers/gpu/drm/amd/display/dc/dcn314/dcn314_dio_stream_encoder.c @@ -317,6 +317,7 @@ static void enc314_stream_encoder_dp_unblank( /* switch DP encoder to CRTC data, but reset it the fifo first. It may happen * that it overflows during mode transition, and sometimes doesn't recover. */ + REG_UPDATE(DIG_FIFO_CTRL0, DIG_FIFO_READ_START_LEVEL, 0x7); REG_UPDATE(DP_STEER_FIFO, DP_STEER_FIFO_RESET, 1); udelay(10); From d7e7546886eebf626569e38ff06d0a67b8b82757 Mon Sep 17 00:00:00 2001 From: Evan Quan Date: Tue, 23 Aug 2022 15:45:36 +0800 Subject: [PATCH 12/21] drm/amd/pm: use vbios carried pptable for those supported SKUs For some SMU13.0.0 SKUs, the vbios carried pptable is ready to go. Use that one instead of hardcoded softpptable. Signed-off-by: Evan Quan Reviewed-by: Kenneth Feng Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h | 6 ++ .../gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c | 23 +++--- .../drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c | 72 ++++++++++++++++--- 3 files changed, 77 insertions(+), 24 deletions(-) diff --git a/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h b/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h index ac308e72241a..cf28af9ee0cb 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h +++ b/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h @@ -291,5 +291,11 @@ int smu_v13_0_set_default_dpm_tables(struct smu_context *smu); void smu_v13_0_set_smu_mailbox_registers(struct smu_context *smu); int smu_v13_0_mode1_reset(struct smu_context *smu); + +int smu_v13_0_get_pptable_from_firmware(struct smu_context *smu, + void **table, + uint32_t *size, + uint32_t pptable_id); + #endif #endif diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c index 18ee3b5e64c5..24488f4cb78c 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c +++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c @@ -84,9 +84,6 @@ MODULE_FIRMWARE("amdgpu/smu_13_0_7.bin"); static const int link_width[] = {0, 1, 2, 4, 8, 12, 16}; static const int link_speed[] = {25, 50, 80, 160}; -static int smu_v13_0_get_pptable_from_firmware(struct smu_context *smu, void **table, uint32_t *size, - uint32_t pptable_id); - int smu_v13_0_init_microcode(struct smu_context *smu) { struct amdgpu_device *adev = smu->adev; @@ -224,23 +221,19 @@ int smu_v13_0_init_pptable_microcode(struct smu_context *smu) /* * Temporary solution for SMU V13.0.0 with SCPM enabled: - * - use 36831 signed pptable when pp_table_id is 3683 - * - use 37151 signed pptable when pp_table_id is 3715 - * - use 36641 signed pptable when pp_table_id is 3664 or 0 - * TODO: drop these when the pptable carried in vbios is ready. + * - use vbios carried pptable when pptable_id is 3664, 3715 or 3795 + * - use 36831 soft pptable when pptable_id is 3683 */ if (adev->ip_versions[MP1_HWIP][0] == IP_VERSION(13, 0, 0)) { switch (pptable_id) { - case 0: case 3664: - pptable_id = 36641; + case 3715: + case 3795: + pptable_id = 0; break; case 3683: pptable_id = 36831; break; - case 3715: - pptable_id = 37151; - break; default: dev_err(adev->dev, "Unsupported pptable id %d\n", pptable_id); return -EINVAL; @@ -425,8 +418,10 @@ static int smu_v13_0_get_pptable_from_vbios(struct smu_context *smu, void **tabl return 0; } -static int smu_v13_0_get_pptable_from_firmware(struct smu_context *smu, void **table, uint32_t *size, - uint32_t pptable_id) +int smu_v13_0_get_pptable_from_firmware(struct smu_context *smu, + void **table, + uint32_t *size, + uint32_t pptable_id) { const struct smc_firmware_header_v1_0 *hdr; struct amdgpu_device *adev = smu->adev; diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c index df4a47acd724..7db2fd9ea74a 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c +++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c @@ -388,11 +388,29 @@ static int smu_v13_0_0_append_powerplay_table(struct smu_context *smu) return 0; } -static int smu_v13_0_0_setup_pptable(struct smu_context *smu) +static int smu_v13_0_0_get_pptable_from_pmfw(struct smu_context *smu, + void **table, + uint32_t *size) { struct smu_table_context *smu_table = &smu->smu_table; void *combo_pptable = smu_table->combo_pptable; + int ret = 0; + + ret = smu_cmn_get_combo_pptable(smu); + if (ret) + return ret; + + *table = combo_pptable; + *size = sizeof(struct smu_13_0_0_powerplay_table); + + return 0; +} + +static int smu_v13_0_0_setup_pptable(struct smu_context *smu) +{ + struct smu_table_context *smu_table = &smu->smu_table; struct amdgpu_device *adev = smu->adev; + uint32_t pptable_id; int ret = 0; /* @@ -401,17 +419,51 @@ static int smu_v13_0_0_setup_pptable(struct smu_context *smu) * rely on the combo pptable(and its revelant SMU message). */ if (adev->scpm_enabled) { - ret = smu_cmn_get_combo_pptable(smu); - if (ret) - return ret; - - smu->smu_table.power_play_table = combo_pptable; - smu->smu_table.power_play_table_size = sizeof(struct smu_13_0_0_powerplay_table); + ret = smu_v13_0_0_get_pptable_from_pmfw(smu, + &smu_table->power_play_table, + &smu_table->power_play_table_size); } else { - ret = smu_v13_0_setup_pptable(smu); - if (ret) - return ret; + /* override pptable_id from driver parameter */ + if (amdgpu_smu_pptable_id >= 0) { + pptable_id = amdgpu_smu_pptable_id; + dev_info(adev->dev, "override pptable id %d\n", pptable_id); + } else { + pptable_id = smu_table->boot_values.pp_table_id; + } + + /* + * Temporary solution for SMU V13.0.0 with SCPM disabled: + * - use vbios carried pptable when pptable_id is 3664, 3715 or 3795 + * - use soft pptable when pptable_id is 3683 + */ + if (adev->ip_versions[MP1_HWIP][0] == IP_VERSION(13, 0, 0)) { + switch (pptable_id) { + case 3664: + case 3715: + case 3795: + pptable_id = 0; + break; + case 3683: + break; + default: + dev_err(adev->dev, "Unsupported pptable id %d\n", pptable_id); + return -EINVAL; + } + } + + /* force using vbios pptable in sriov mode */ + if ((amdgpu_sriov_vf(adev) || !pptable_id) && (amdgpu_emu_mode != 1)) + ret = smu_v13_0_0_get_pptable_from_pmfw(smu, + &smu_table->power_play_table, + &smu_table->power_play_table_size); + else + ret = smu_v13_0_get_pptable_from_firmware(smu, + &smu_table->power_play_table, + &smu_table->power_play_table_size, + pptable_id); } + if (ret) + return ret; ret = smu_v13_0_0_store_powerplay_table(smu); if (ret) From b023053592646b1da9477b0b598f2cdd5d3f89d8 Mon Sep 17 00:00:00 2001 From: Evan Quan Date: Tue, 23 Aug 2022 16:07:18 +0800 Subject: [PATCH 13/21] drm/amd/pm: use vbios carried pptable for all SMU13.0.7 SKUs For those SMU13.0.7 unsecure SKUs, the vbios carried pptable is ready to go. Use that one instead of hardcoded softpptable. Signed-off-by: Evan Quan Reviewed-by: Kenneth Feng Signed-off-by: Alex Deucher --- .../drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c | 35 ++++++++++++------- 1 file changed, 22 insertions(+), 13 deletions(-) diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c index 1016d1c216d8..fcf24c540859 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c +++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c @@ -400,11 +400,27 @@ static int smu_v13_0_7_append_powerplay_table(struct smu_context *smu) return 0; } +static int smu_v13_0_7_get_pptable_from_pmfw(struct smu_context *smu, + void **table, + uint32_t *size) +{ + struct smu_table_context *smu_table = &smu->smu_table; + void *combo_pptable = smu_table->combo_pptable; + int ret = 0; + + ret = smu_cmn_get_combo_pptable(smu); + if (ret) + return ret; + + *table = combo_pptable; + *size = sizeof(struct smu_13_0_7_powerplay_table); + + return 0; +} static int smu_v13_0_7_setup_pptable(struct smu_context *smu) { struct smu_table_context *smu_table = &smu->smu_table; - void *combo_pptable = smu_table->combo_pptable; struct amdgpu_device *adev = smu->adev; int ret = 0; @@ -413,18 +429,11 @@ static int smu_v13_0_7_setup_pptable(struct smu_context *smu) * be used directly by driver. To get the raw pptable, we need to * rely on the combo pptable(and its revelant SMU message). */ - if (adev->scpm_enabled) { - ret = smu_cmn_get_combo_pptable(smu); - if (ret) - return ret; - - smu->smu_table.power_play_table = combo_pptable; - smu->smu_table.power_play_table_size = sizeof(struct smu_13_0_7_powerplay_table); - } else { - ret = smu_v13_0_setup_pptable(smu); - if (ret) - return ret; - } + ret = smu_v13_0_7_get_pptable_from_pmfw(smu, + &smu_table->power_play_table, + &smu_table->power_play_table_size); + if (ret) + return ret; ret = smu_v13_0_7_store_powerplay_table(smu); if (ret) From 2640174f4a139502f603f7bedf3a7011db714e1d Mon Sep 17 00:00:00 2001 From: Evan Quan Date: Tue, 23 Aug 2022 17:37:26 +0800 Subject: [PATCH 14/21] drm/amd/pm: bump SMU 13.0.0 driver_if header version To suppress the warning about version mismatch with the latest 78.54.0 PMFW. Signed-off-by: Evan Quan Reviewed-by: Kenneth Feng Signed-off-by: Alex Deucher --- .../gpu/drm/amd/pm/swsmu/inc/pmfw_if/smu13_driver_if_v13_0_0.h | 2 +- drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/amd/pm/swsmu/inc/pmfw_if/smu13_driver_if_v13_0_0.h b/drivers/gpu/drm/amd/pm/swsmu/inc/pmfw_if/smu13_driver_if_v13_0_0.h index f745cd8f1ab7..063f4a737605 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/inc/pmfw_if/smu13_driver_if_v13_0_0.h +++ b/drivers/gpu/drm/amd/pm/swsmu/inc/pmfw_if/smu13_driver_if_v13_0_0.h @@ -25,7 +25,7 @@ #define SMU13_DRIVER_IF_V13_0_0_H //Increment this version if SkuTable_t or BoardTable_t change -#define PPTABLE_VERSION 0x22 +#define PPTABLE_VERSION 0x24 #define NUM_GFXCLK_DPM_LEVELS 16 #define NUM_SOCCLK_DPM_LEVELS 8 diff --git a/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h b/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h index cf28af9ee0cb..f442bf085a31 100644 --- a/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h +++ b/drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h @@ -30,7 +30,7 @@ #define SMU13_DRIVER_IF_VERSION_ALDE 0x08 #define SMU13_DRIVER_IF_VERSION_SMU_V13_0_4 0x05 #define SMU13_DRIVER_IF_VERSION_SMU_V13_0_5 0x04 -#define SMU13_DRIVER_IF_VERSION_SMU_V13_0_0 0x2E +#define SMU13_DRIVER_IF_VERSION_SMU_V13_0_0 0x30 #define SMU13_DRIVER_IF_VERSION_SMU_V13_0_7 0x2C #define SMU13_MODE1_RESET_WAIT_TIME_IN_MS 500 //500ms From b97e914552c3fcea71ce03f899e285f2178ec38b Mon Sep 17 00:00:00 2001 From: Alex Sierra Date: Thu, 25 Aug 2022 15:42:08 -0500 Subject: [PATCH 15/21] drm/amdgpu: ensure no PCIe peer access for CPU XGMI iolinks [Why] Devices with CPU XGMI iolink do not support PCIe peer access. Signed-off-by: Alex Sierra Acked-by: Alex Deucher Reviewed-by: Felix Kuehling Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c index f095a2513aff..1400abee9f40 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c @@ -5524,7 +5524,8 @@ bool amdgpu_device_is_peer_accessible(struct amdgpu_device *adev, ~*peer_adev->dev->dma_mask : ~((1ULL << 32) - 1); resource_size_t aper_limit = adev->gmc.aper_base + adev->gmc.aper_size - 1; - bool p2p_access = !(pci_p2pdma_distance_many(adev->pdev, + bool p2p_access = !adev->gmc.xgmi.connected_to_cpu && + !(pci_p2pdma_distance_many(adev->pdev, &peer_adev->dev, 1, true) < 0); return pcie_p2p && p2p_access && (adev->gmc.visible_vram_size && From 6ffc967c36b42f864955cb2c5e8b3fded0baa918 Mon Sep 17 00:00:00 2001 From: Aurabindo Pillai Date: Fri, 19 Aug 2022 15:11:19 -0400 Subject: [PATCH 16/21] drm/amd/display: Use correct plane for CAB cursor size allocation [Why&How] plane and stream variables used for cursor size allocation calculation were stale from previous iteration. Redo the iteration to find the correct cursor plane for the calculation. Reviewed-by: Alvin Lee Acked-by: Brian Chang Signed-off-by: Aurabindo Pillai Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- .../drm/amd/display/dc/dcn32/dcn32_hwseq.c | 32 ++++++++++++------- 1 file changed, 21 insertions(+), 11 deletions(-) diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c index 18287743add5..8d9d96c39808 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c +++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c @@ -295,8 +295,8 @@ static uint32_t dcn32_calculate_cab_allocation(struct dc *dc, struct dc_state *c } // Include cursor size for CAB allocation - for (i = 0; i < dc->res_pool->pipe_count; i++) { - struct pipe_ctx *pipe = &ctx->res_ctx.pipe_ctx[i]; + for (j = 0; j < dc->res_pool->pipe_count; j++) { + struct pipe_ctx *pipe = &ctx->res_ctx.pipe_ctx[j]; struct hubp *hubp = pipe->plane_res.hubp; if (pipe->stream && pipe->plane_state && hubp) @@ -339,15 +339,25 @@ static uint32_t dcn32_calculate_cab_allocation(struct dc *dc, struct dc_state *c if (cache_lines_used % lines_per_way > 0) num_ways++; - if (stream->cursor_position.enable && - !plane->address.grph.cursor_cache_addr.quad_part && - cursor_size > 16384) - /* Cursor caching is not supported since it won't be on the same line. - * So we need an extra line to accommodate it. With large cursors and a single 4k monitor - * this case triggers corruption. If we're at the edge, then dont trigger display refresh - * from MALL. We only need to cache cursor if its greater that 64x64 at 4 bpp. - */ - num_ways++; + for (i = 0; i < ctx->stream_count; i++) { + stream = ctx->streams[i]; + for (j = 0; j < ctx->stream_status[i].plane_count; j++) { + plane = ctx->stream_status[i].plane_states[j]; + + if (stream->cursor_position.enable && plane && + !plane->address.grph.cursor_cache_addr.quad_part && + cursor_size > 16384) { + /* Cursor caching is not supported since it won't be on the same line. + * So we need an extra line to accommodate it. With large cursors and a single 4k monitor + * this case triggers corruption. If we're at the edge, then dont trigger display refresh + * from MALL. We only need to cache cursor if its greater that 64x64 at 4 bpp. + */ + num_ways++; + /* We only expect one cursor plane */ + break; + } + } + } return num_ways; } From f5b9c1ffabce5f4acbeabd3a03fd57b3970a13fe Mon Sep 17 00:00:00 2001 From: Ethan Wellenreiter Date: Mon, 22 Aug 2022 14:33:23 -0400 Subject: [PATCH 17/21] drm/amd/display: Re-initialize viewport after pipe merge [Why] Pipes get merged in preparation for SubVP but if they don't get used, and are in ODM or some other multi pipe config, it would calculate the voltage level with a viewport of just one pipe from when they were split resulting in too low of a voltage level. [How] Made it so that the viewport and other timing settings get rebuilt and re- initialized after the pipe merge, before calculating the voltage level so it would calculate it correctly. Reviewed-by: Alvin Lee Reviewed-by: Jun Lei Acked-by: Brian Chang Signed-off-by: Ethan Wellenreiter Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dml/dcn32/dcn32_fpu.c | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/drivers/gpu/drm/amd/display/dc/dml/dcn32/dcn32_fpu.c b/drivers/gpu/drm/amd/display/dc/dml/dcn32/dcn32_fpu.c index 8118cfc5b405..8e4c9d0887ce 100644 --- a/drivers/gpu/drm/amd/display/dc/dml/dcn32/dcn32_fpu.c +++ b/drivers/gpu/drm/amd/display/dc/dml/dcn32/dcn32_fpu.c @@ -1014,6 +1014,15 @@ static void dcn32_full_validate_bw_helper(struct dc *dc, dc->debug.force_subvp_mclk_switch)) { dcn32_merge_pipes_for_subvp(dc, context); + // to re-initialize viewport after the pipe merge + for (int i = 0; i < dc->res_pool->pipe_count; i++) { + struct pipe_ctx *pipe_ctx = &context->res_ctx.pipe_ctx[i]; + + if (!pipe_ctx->plane_state || !pipe_ctx->stream) + continue; + + resource_build_scaling_params(pipe_ctx); + } while (!found_supported_config && dcn32_enough_pipes_for_subvp(dc, context) && dcn32_assign_subvp_pipe(dc, context, &dc_pipe_idx)) { From d6f84bab48745ea68814d596eb476a9c11ce76ae Mon Sep 17 00:00:00 2001 From: Ethan Wellenreiter Date: Fri, 19 Aug 2022 18:30:44 -0400 Subject: [PATCH 18/21] drm/amd/display: Fix check for stream and plane [WHY] Function wasn't returning false when it had a no stream [HOW] Made it return false when it had no stream. Reviewed-by: Alvin Lee Acked-by: Brian Chang Signed-off-by: Ethan Wellenreiter Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource_helpers.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource_helpers.c b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource_helpers.c index 955f52e6064d..ab918fe38f6a 100644 --- a/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource_helpers.c +++ b/drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource_helpers.c @@ -144,7 +144,7 @@ bool dcn32_all_pipes_have_stream_and_plane(struct dc *dc, struct pipe_ctx *pipe = &context->res_ctx.pipe_ctx[i]; if (!pipe->stream) - continue; + return false; if (!pipe->plane_state) return false; From 7b471c32e4cbfdd7a673b79321f6a26abecbf33b Mon Sep 17 00:00:00 2001 From: Vladimir Stempen Date: Fri, 19 Aug 2022 18:32:01 -0400 Subject: [PATCH 19/21] drm/amd/display: Fix black flash when switching from ODM2to1 to ODMBypass [Why] On secondary display hotplug we switch primary stream from ODM2to1 to ODMBypass mode. Current logic will trigger disabling front end for this stream. [How] We need to check if prev_odm_pipe is equal to NULL in order to disable dangling planes in this scenario. Reviewed-by: Ariel Bernstein Acked-by: Brian Chang Signed-off-by: Vladimir Stempen Tested-by: Daniel Wheeler Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/display/dc/core/dc.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c index aeecca68dea7..fb22c3d70528 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc.c @@ -1094,7 +1094,8 @@ static void disable_dangling_plane(struct dc *dc, struct dc_state *context) dc->current_state->stream_count != context->stream_count) should_disable = true; - if (old_stream && !dc->current_state->res_ctx.pipe_ctx[i].top_pipe) { + if (old_stream && !dc->current_state->res_ctx.pipe_ctx[i].top_pipe && + !dc->current_state->res_ctx.pipe_ctx[i].prev_odm_pipe) { struct pipe_ctx *old_pipe, *new_pipe; old_pipe = &dc->current_state->res_ctx.pipe_ctx[i]; From 910ab9eee0f61a243126d70e932e1301b5437583 Mon Sep 17 00:00:00 2001 From: Hawking Zhang Date: Tue, 30 Aug 2022 15:47:47 +0800 Subject: [PATCH 20/21] drm/amdgpu: only init tap_delay ucode when it's included in ucode binary Not all the gfx10 variants need to integrate global tap_delay and per se tap_delay firmwares Only init tap_delay ucode when it does include in rlc ucode binary so driver doesn't send a null buffer to psp for firmware loading Signed-off-by: Hawking Zhang Reviewed-by: Jack Gui Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c | 60 +++++++++++++++----------- 1 file changed, 35 insertions(+), 25 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c b/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c index a2a4dc1844c0..a3cd5c1e8529 100644 --- a/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c +++ b/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c @@ -4274,35 +4274,45 @@ static int gfx_v10_0_init_microcode(struct amdgpu_device *adev) } - info = &adev->firmware.ucode[AMDGPU_UCODE_ID_GLOBAL_TAP_DELAYS]; - info->ucode_id = AMDGPU_UCODE_ID_GLOBAL_TAP_DELAYS; - info->fw = adev->gfx.rlc_fw; - adev->firmware.fw_size += - ALIGN(adev->gfx.rlc.global_tap_delays_ucode_size_bytes, PAGE_SIZE); + if (adev->gfx.rlc.global_tap_delays_ucode_size_bytes) { + info = &adev->firmware.ucode[AMDGPU_UCODE_ID_GLOBAL_TAP_DELAYS]; + info->ucode_id = AMDGPU_UCODE_ID_GLOBAL_TAP_DELAYS; + info->fw = adev->gfx.rlc_fw; + adev->firmware.fw_size += + ALIGN(adev->gfx.rlc.global_tap_delays_ucode_size_bytes, PAGE_SIZE); + } - info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE0_TAP_DELAYS]; - info->ucode_id = AMDGPU_UCODE_ID_SE0_TAP_DELAYS; - info->fw = adev->gfx.rlc_fw; - adev->firmware.fw_size += - ALIGN(adev->gfx.rlc.se0_tap_delays_ucode_size_bytes, PAGE_SIZE); + if (adev->gfx.rlc.se0_tap_delays_ucode_size_bytes) { + info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE0_TAP_DELAYS]; + info->ucode_id = AMDGPU_UCODE_ID_SE0_TAP_DELAYS; + info->fw = adev->gfx.rlc_fw; + adev->firmware.fw_size += + ALIGN(adev->gfx.rlc.se0_tap_delays_ucode_size_bytes, PAGE_SIZE); + } - info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE1_TAP_DELAYS]; - info->ucode_id = AMDGPU_UCODE_ID_SE1_TAP_DELAYS; - info->fw = adev->gfx.rlc_fw; - adev->firmware.fw_size += - ALIGN(adev->gfx.rlc.se1_tap_delays_ucode_size_bytes, PAGE_SIZE); + if (adev->gfx.rlc.se1_tap_delays_ucode_size_bytes) { + info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE1_TAP_DELAYS]; + info->ucode_id = AMDGPU_UCODE_ID_SE1_TAP_DELAYS; + info->fw = adev->gfx.rlc_fw; + adev->firmware.fw_size += + ALIGN(adev->gfx.rlc.se1_tap_delays_ucode_size_bytes, PAGE_SIZE); + } - info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE2_TAP_DELAYS]; - info->ucode_id = AMDGPU_UCODE_ID_SE2_TAP_DELAYS; - info->fw = adev->gfx.rlc_fw; - adev->firmware.fw_size += - ALIGN(adev->gfx.rlc.se2_tap_delays_ucode_size_bytes, PAGE_SIZE); + if (adev->gfx.rlc.se2_tap_delays_ucode_size_bytes) { + info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE2_TAP_DELAYS]; + info->ucode_id = AMDGPU_UCODE_ID_SE2_TAP_DELAYS; + info->fw = adev->gfx.rlc_fw; + adev->firmware.fw_size += + ALIGN(adev->gfx.rlc.se2_tap_delays_ucode_size_bytes, PAGE_SIZE); + } - info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE3_TAP_DELAYS]; - info->ucode_id = AMDGPU_UCODE_ID_SE3_TAP_DELAYS; - info->fw = adev->gfx.rlc_fw; - adev->firmware.fw_size += - ALIGN(adev->gfx.rlc.se3_tap_delays_ucode_size_bytes, PAGE_SIZE); + if (adev->gfx.rlc.se3_tap_delays_ucode_size_bytes) { + info = &adev->firmware.ucode[AMDGPU_UCODE_ID_SE3_TAP_DELAYS]; + info->ucode_id = AMDGPU_UCODE_ID_SE3_TAP_DELAYS; + info->fw = adev->gfx.rlc_fw; + adev->firmware.fw_size += + ALIGN(adev->gfx.rlc.se3_tap_delays_ucode_size_bytes, PAGE_SIZE); + } info = &adev->firmware.ucode[AMDGPU_UCODE_ID_CP_MEC1]; info->ucode_id = AMDGPU_UCODE_ID_CP_MEC1; From 39c84b8e929dbd4f63be7e04bf1a2bcd92b44177 Mon Sep 17 00:00:00 2001 From: Chengming Gui Date: Tue, 30 Aug 2022 16:33:01 +0800 Subject: [PATCH 21/21] drm/amd/amdgpu: skip ucode loading if ucode_size == 0 Restrict the ucode loading check to avoid frontdoor loading error. Signed-off-by: Chengming Gui Reviewed-by: Hawking Zhang Signed-off-by: Alex Deucher --- drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c index 1036446abc30..9f7a5e393f85 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c @@ -2401,7 +2401,7 @@ static int psp_load_smu_fw(struct psp_context *psp) static bool fw_load_skip_check(struct psp_context *psp, struct amdgpu_firmware_info *ucode) { - if (!ucode->fw) + if (!ucode->fw || !ucode->ucode_size) return true; if (ucode->ucode_id == AMDGPU_UCODE_ID_SMC &&