Commit 5f3401ee authored by Samson Tam's avatar Samson Tam Committed by Alex Deucher

drm/amd/display: reallocate DET for dual displays with high pixel rate ratio

[Why]
For dual displays where pixel rate is much higher on one display,
we may get underflow when DET is evenly allocated.

[How]
Allocate less DET segments for the lower pixel rate display and
more DET segments for the higher pixel rate display
Reviewed-by: default avatarAlvin Lee <Alvin.Lee2@amd.com>
Acked-by: default avatarQingqing Zhuo <qingqing.zhuo@amd.com>
Signed-off-by: default avatarSamson Tam <Samson.Tam@amd.com>
Tested-by: default avatarDaniel Wheeler <daniel.wheeler@amd.com>
Signed-off-by: default avatarAlex Deucher <alexander.deucher@amd.com>
parent 562e0822
...@@ -257,6 +257,8 @@ bool dcn32_is_psr_capable(struct pipe_ctx *pipe) ...@@ -257,6 +257,8 @@ bool dcn32_is_psr_capable(struct pipe_ctx *pipe)
return psr_capable; return psr_capable;
} }
#define DCN3_2_NEW_DET_OVERRIDE_MIN_MULTIPLIER 7
/** /**
* ******************************************************************************************* * *******************************************************************************************
* dcn32_determine_det_override: Determine DET allocation for each pipe * dcn32_determine_det_override: Determine DET allocation for each pipe
...@@ -268,7 +270,6 @@ bool dcn32_is_psr_capable(struct pipe_ctx *pipe) ...@@ -268,7 +270,6 @@ bool dcn32_is_psr_capable(struct pipe_ctx *pipe)
* If there is a plane that's driven by more than 1 pipe (i.e. pipe split), then the * If there is a plane that's driven by more than 1 pipe (i.e. pipe split), then the
* number of DET for that given plane will be split among the pipes driving that plane. * number of DET for that given plane will be split among the pipes driving that plane.
* *
*
* High level algorithm: * High level algorithm:
* 1. Split total DET among number of streams * 1. Split total DET among number of streams
* 2. For each stream, split DET among the planes * 2. For each stream, split DET among the planes
...@@ -276,6 +277,18 @@ bool dcn32_is_psr_capable(struct pipe_ctx *pipe) ...@@ -276,6 +277,18 @@ bool dcn32_is_psr_capable(struct pipe_ctx *pipe)
* among those pipes. * among those pipes.
* 4. Assign the DET override to the DML pipes. * 4. Assign the DET override to the DML pipes.
* *
* Special cases:
*
* For two displays that have a large difference in pixel rate, we may experience
* underflow on the larger display when we divide the DET equally. For this, we
* will implement a modified algorithm to assign more DET to larger display.
*
* 1. Calculate difference in pixel rates ( multiplier ) between two displays
* 2. If the multiplier exceeds DCN3_2_NEW_DET_OVERRIDE_MIN_MULTIPLIER, then
* implement the modified DET override algorithm.
* 3. Assign smaller DET size for lower pixel display and higher DET size for
* higher pixel display
*
* @param [in]: dc: Current DC state * @param [in]: dc: Current DC state
* @param [in]: context: New DC state to be programmed * @param [in]: context: New DC state to be programmed
* @param [in]: pipes: Array of DML pipes * @param [in]: pipes: Array of DML pipes
...@@ -295,18 +308,46 @@ void dcn32_determine_det_override(struct dc *dc, ...@@ -295,18 +308,46 @@ void dcn32_determine_det_override(struct dc *dc,
struct dc_plane_state *current_plane = NULL; struct dc_plane_state *current_plane = NULL;
uint8_t stream_count = 0; uint8_t stream_count = 0;
int phy_pix_clk_mult, lower_mode_stream_index;
int phy_pix_clk[MAX_PIPES] = {0};
bool use_new_det_override_algorithm = false;
for (i = 0; i < context->stream_count; i++) { for (i = 0; i < context->stream_count; i++) {
/* Don't count SubVP streams for DET allocation */ /* Don't count SubVP streams for DET allocation */
if (context->streams[i]->mall_stream_config.type != SUBVP_PHANTOM) { if (context->streams[i]->mall_stream_config.type != SUBVP_PHANTOM) {
phy_pix_clk[i] = context->streams[i]->phy_pix_clk;
stream_count++; stream_count++;
} }
} }
/* Check for special case with two displays, one with much higher pixel rate */
if (stream_count == 2) {
ASSERT(!phy_pix_clk[0] || !phy_pix_clk[1]);
if (phy_pix_clk[0] < phy_pix_clk[1]) {
lower_mode_stream_index = 0;
phy_pix_clk_mult = phy_pix_clk[1] / phy_pix_clk[0];
} else {
lower_mode_stream_index = 1;
phy_pix_clk_mult = phy_pix_clk[0] / phy_pix_clk[1];
}
if (phy_pix_clk_mult >= DCN3_2_NEW_DET_OVERRIDE_MIN_MULTIPLIER)
use_new_det_override_algorithm = true;
}
if (stream_count > 0) { if (stream_count > 0) {
stream_segments = 18 / stream_count; stream_segments = 18 / stream_count;
for (i = 0; i < context->stream_count; i++) { for (i = 0; i < context->stream_count; i++) {
if (context->streams[i]->mall_stream_config.type == SUBVP_PHANTOM) if (context->streams[i]->mall_stream_config.type == SUBVP_PHANTOM)
continue; continue;
if (use_new_det_override_algorithm) {
if (i == lower_mode_stream_index)
stream_segments = 4;
else
stream_segments = 14;
}
if (context->stream_status[i].plane_count > 0) if (context->stream_status[i].plane_count > 0)
plane_segments = stream_segments / context->stream_status[i].plane_count; plane_segments = stream_segments / context->stream_status[i].plane_count;
else else
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment