From: Alvin Lee <[email protected]>
[Description]
- Align calculation with addrlib (need to align to macro tiled
widht/height)
- Align the copy size / addr to 256KB for SW_256KB modes
Reviewed-by: Dillon Varone <[email protected]>
Signed-off-by: Alvin Lee <[email protected]>
Signed-off-by: Ivan Lipski <[email protected]>
---
.../amd/display/dc/dml2_0/dml21/dml21_utils.c | 15 +++---
.../dml2_core/dml2_core_dcn6_calcs_dchub.c | 47 +++++++++++++------
.../dml2_core_dcn6_funcs_mode_support.c | 3 ++
.../src/dml2_core/dml2_core_shared_types.h | 2 +
4 files changed, 46 insertions(+), 21 deletions(-)
diff --git a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/dml21_utils.c b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/dml21_utils.c
index 1ade48b8b621a..125ca619c8abb 100644
--- a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/dml21_utils.c
+++ b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/dml21_utils.c
@@ -375,11 +375,12 @@ void dml21_handle_phantom_streams_planes(const struct dc *dc, struct dc_state *c
dml2_map_dc_pipes(dml_ctx, context, NULL, &dml_ctx->v21.dml_to_dc_pipe_mapping, dc->current_state);
}
-static uint32_t calc_svp_size_64kb(uint32_t total_size_bytes)
+static uint32_t calc_svp_size_256kb(uint64_t addr_bytes)
{
- return (total_size_bytes + 0xFFFF) >> 16;
+ return (uint32_t)(((addr_bytes + 0x3FFFFull) >> 18) << 2); // ceil to 256KB, then return bits [47:16]
}
+
static unsigned int dml21_build_fams2_stream_programming_v3(const struct dc *dc,
struct dc_state *context,
struct dml2_context *dml_ctx)
@@ -387,7 +388,7 @@ static unsigned int dml21_build_fams2_stream_programming_v3(const struct dc *dc,
int dml_stream_idx, dc_stream_idx, dc_plane_idx, svp_idx;
unsigned int dc_pipe_idx;
unsigned int num_fams2_streams = 0;
- unsigned int svp_size_64kb[2] = {0};
+ unsigned int svp_size_256kb[2] = {0};
struct pipe_ctx *pipe;
for (dc_stream_idx = 0; dc_stream_idx < context->stream_count; dc_stream_idx++) {
@@ -477,12 +478,12 @@ static unsigned int dml21_build_fams2_stream_programming_v3(const struct dc *dc,
}
for (svp_idx = 0; svp_idx < 2; svp_idx++) {
alternate_static_state->pipe_copy_addr_47_16[svp_idx][dc_pipe_idx] =
- dml_ctx->config.alt_ch_cfg.region_base_addr_47_16[svp_idx] + svp_size_64kb[svp_idx];
- svp_size_64kb[svp_idx] += calc_svp_size_64kb(alternate_static_state->pipe_copy_max_size[svp_idx][dc_plane_idx]);
+ dml_ctx->config.alt_ch_cfg.region_base_addr_47_16[svp_idx] + svp_size_256kb[svp_idx];
+ svp_size_256kb[svp_idx] += calc_svp_size_256kb(alternate_static_state->pipe_copy_max_size[svp_idx][dc_plane_idx]);
if (alternate_static_state->config[dc_plane_idx].bits.is_multi_planar) {
alternate_static_state->pipe_copy_addr_47_16_c[svp_idx][dc_pipe_idx] =
- dml_ctx->config.alt_ch_cfg.region_base_addr_47_16[svp_idx] + svp_size_64kb[svp_idx];
- svp_size_64kb[svp_idx] += calc_svp_size_64kb(alternate_static_state->pipe_copy_max_size_c[svp_idx][dc_plane_idx]);
+ dml_ctx->config.alt_ch_cfg.region_base_addr_47_16[svp_idx] + svp_size_256kb[svp_idx];
+ svp_size_256kb[svp_idx] += calc_svp_size_256kb(alternate_static_state->pipe_copy_max_size_c[svp_idx][dc_plane_idx]);
}
}
}
diff --git a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_calcs_dchub.c b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_calcs_dchub.c
index cae6bee93fe30..83fada0608724 100644
--- a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_calcs_dchub.c
+++ b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_calcs_dchub.c
@@ -203,14 +203,32 @@ static unsigned int calculate_copy_swaths(double pre_first_hdl,
return num_swaths;
}
+/**
+ * *******************************************************************************************************************************************************
+ * calculate_tile_aligned_size: Applies tiled-surface padding / alignment rules to an unaligned copy region
+ *
+ * Given the unaligned copy region dimensions (copy_width in pixels, copy_height in lines) and the plane's macro tile
+ * (swizzle block) dimensions, this returns the number of bytes reserved for the region following addrlib sizing rules:
+ * - The pitch is padded up to the macro tile width and the height is padded up to the macro tile height.
+ * size = alignedPitch * alignedHeight * bpp, which is inherently macro-tile (block) aligned
+ * - The final ceil2 to 256 is a harmless floor for degenerate tile sizes.
+ *
+ * *******************************************************************************************************************************************************
+ */
+static unsigned int calculate_tile_aligned_size(unsigned int copy_width, unsigned int copy_height, unsigned int tile_width, unsigned int tile_height, unsigned int byte_per_pixel)
+{
+ unsigned int mem_width = (unsigned int)math_ceil2(copy_width, tile_width);
+ unsigned int mem_height = (unsigned int)math_ceil2(copy_height, tile_height);
+
+ return (unsigned int)math_ceil2(mem_width * mem_height * byte_per_pixel, 256);
+}
+
/**
* *******************************************************************************************************************************************************
* calculate_max_mem_size_per_plane_per_dpp: Calculate (loose) upper bound for total number of bytes reserved in memory for the copy given number of swaths
*
* - The copy width / height is the min of the vp_width/height and maximum number of pixels that can fit across an ODM slice
* - This is to account for recout positions that cross the ODM seam but are "mostly" within the same ODM slice
- * - For mem width assume an extra block width and tile width is required (the memory reserved must take into account pitch which must be tiled aligned)
- * - For mem height assumes two extra block heights are required
*
* *******************************************************************************************************************************************************
*/
@@ -222,12 +240,11 @@ static unsigned int calculate_max_mem_size_per_plane_per_dpp(const struct dml2_c
unsigned int copy_src_lines = copy_swaths * (chroma ? p->SwathHeightC[plane_idx] : p->SwathHeightY[plane_idx]);
unsigned int vp_width = chroma ? p->display_cfg->plane_descriptors[plane_idx].composition.viewport.plane1.width : p->display_cfg->plane_descriptors[plane_idx].composition.viewport.plane0.width;
unsigned int vp_height = chroma ? p->display_cfg->plane_descriptors[plane_idx].composition.viewport.plane1.height : p->display_cfg->plane_descriptors[plane_idx].composition.viewport.plane0.height;
- unsigned int block256_width = chroma ? p->Read256BlockWidthC[plane_idx] : p->Read256BlockWidthY[plane_idx];
- unsigned int block256_height = chroma ? p->Read256BlockHeightC[plane_idx] : p->Read256BlockHeightY[plane_idx];
unsigned int tile_width = chroma ? p->MacroTileWidthC[plane_idx] : p->MacroTileWidthY[plane_idx];
+ unsigned int tile_height = chroma ? p->MacroTileHeightC[plane_idx] : p->MacroTileHeightY[plane_idx];
unsigned int byte_per_pixel = chroma ? p->BytePerPixelC[plane_idx] : p->BytePerPixelY[plane_idx];
- unsigned int mem_width;
- unsigned int mem_height;
+ unsigned int copy_width;
+ unsigned int copy_height;
unsigned int odm_combine_factor;
double odm_slice_pixels;
@@ -241,12 +258,14 @@ static unsigned int calculate_max_mem_size_per_plane_per_dpp(const struct dml2_c
odm_combine_factor = 1;
odm_slice_pixels = (double)h_active / odm_combine_factor * h_ratio + (odm_combine_factor == 3 ? 2 : 0);
- mem_width = (vertical_access ? copy_src_lines : (unsigned int)math_ceil(math_min2(odm_slice_pixels, vp_width))) + block256_width + tile_width;
- mem_height = (vertical_access ? (unsigned int)math_ceil(math_min2(odm_slice_pixels, vp_height)) : copy_src_lines) + 2 * block256_height;
- return (unsigned int)math_ceil2(mem_width * mem_height * byte_per_pixel, 256);
-}
+ /* Unaligned copy region dimensions (in pixels / lines) prior to tile alignment.
+ * Also divide vp_widht/height by NoOfDPP for MPC combine scenarios (i.e., MPC split within an ODM slice). */
+ copy_width = vertical_access ? copy_src_lines : (unsigned int)math_ceil(math_min2(odm_slice_pixels, vp_width / p->NoOfDPP[plane_idx]));
+ copy_height = vertical_access ? (unsigned int)math_ceil(math_min2(odm_slice_pixels, vp_height / p->NoOfDPP[plane_idx])) : copy_src_lines;
+ return calculate_tile_aligned_size(copy_width, copy_height, tile_width, tile_height, byte_per_pixel);
+}
/**
* ****************************************************************************************************************************************
* calculate_ub_copy_size_per_plane_per_dpp: Calculate tight upper bound for total number of bytes required for the copy given number of swaths.
@@ -422,9 +441,9 @@ static void calculate_swath_params(const struct dml2_core_calcs_calculate_altern
out->prefetch_hdl_delta = (double)swath_height / vratio_pre;
}
-static unsigned int calc_svp_size_64kb_aligned(unsigned int total_size_bytes)
+static unsigned int calc_svp_size_256kb_aligned(unsigned int total_size_bytes)
{
- return ((total_size_bytes + 0xFFFF) >> 16) << 16; // Round up to nearest 64KB boundary
+ return ((total_size_bytes + 0x3FFFFu) >> 18) << 18; // Round up to nearest 256KB boundary
}
void dcn6_calculate_alternate_params(struct dml2_core_calcs_calculate_alternate_params *p)
@@ -471,7 +490,7 @@ void dcn6_calculate_alternate_params(struct dml2_core_calcs_calculate_alternate_
p->prefetch_hdl_delta[j] = swath_params.prefetch_hdl_delta;
for (k = 0; k < 2; k++) {
svp_max_bytes_per_dpp[k] = calculate_ub_copy_size_per_plane_per_dpp_per_svp(p, svp_dst_lines[k], j, false);
- svp_max_bytes[k] += calc_svp_size_64kb_aligned(svp_max_bytes_per_dpp[k]) * p->NoOfDPP[j];
+ svp_max_bytes[k] += calc_svp_size_256kb_aligned(svp_max_bytes_per_dpp[k]) * p->NoOfDPP[j];
}
p->svp0_max_bytes_per_dpp[j] = svp_max_bytes_per_dpp[0];
p->svp1_max_bytes_per_dpp[j] = svp_max_bytes_per_dpp[1];
@@ -485,7 +504,7 @@ void dcn6_calculate_alternate_params(struct dml2_core_calcs_calculate_alternate_
for (k = 0; k < 2; k++) {
svp_max_bytes_per_dpp[k] = calculate_ub_copy_size_per_plane_per_dpp_per_svp(p, svp_dst_lines[k], j, true);
- svp_max_bytes[k] += calc_svp_size_64kb_aligned(svp_max_bytes_per_dpp[k]) * p->NoOfDPP[j];
+ svp_max_bytes[k] += calc_svp_size_256kb_aligned(svp_max_bytes_per_dpp[k]) * p->NoOfDPP[j];
}
p->svp0_max_bytes_per_dpp_c[j] = svp_max_bytes_per_dpp[0];
p->svp1_max_bytes_per_dpp_c[j] = svp_max_bytes_per_dpp[1];
diff --git a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_funcs_mode_support.c b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_funcs_mode_support.c
index cb3cff316b0e8..01bbf4aacbe3c 100644
--- a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_funcs_mode_support.c
+++ b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_dcn6_funcs_mode_support.c
@@ -2246,6 +2246,8 @@ static void dcn6_ms_calculate_alternate_params(const struct dml2_core_calculate_
p->Read256BlockHeightC = inputs->Read256BlockHeightC;
p->MacroTileWidthY = inputs->MacroTileWidthY;
p->MacroTileWidthC = inputs->MacroTileWidthC;
+ p->MacroTileHeightY = inputs->MacroTileHeightY;
+ p->MacroTileHeightC = inputs->MacroTileHeightC;
p->VInitPrefillY = inputs->PrefillY;
p->VInitPrefillC = inputs->PrefillC;
p->VRatioPrefetchY = inputs->VRatioPreY;
@@ -2316,6 +2318,7 @@ static void dcn6_ms_calculate_alternate_svp_lines(const struct dml2_core_calcula
struct dml2_core_internal_mode_support *outputs = states;
DML_LOG_FUNC_ENTER();
+
p->display_cfg = ctx->display_cfg;
p->SwathHeightY = inputs->SwathHeightY;
p->SwathHeightC = inputs->SwathHeightC;
diff --git a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_shared_types.h b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_shared_types.h
index 55118fd484ce8..36250f3d83aaf 100644
--- a/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_shared_types.h
+++ b/drivers/gpu/drm/amd/display/dc/dml2_0/dml21/src/dml2_core/dml2_core_shared_types.h
@@ -2300,6 +2300,8 @@ struct dml2_core_calcs_calculate_alternate_params {
unsigned int *Read256BlockHeightC;
unsigned int *MacroTileWidthY;
unsigned int *MacroTileWidthC;
+ unsigned int *MacroTileHeightY;
+ unsigned int *MacroTileHeightC;
unsigned int *VInitPrefillY;
unsigned int *VInitPrefillC;
double *VRatioPrefetchY;
--
2.43.0
lmpx.com only provides a reader for public news (NNTP) servers. It is not
affiliated with the servers or forums shown here and is not responsible for
the content of articles, which is written by their respective authors.