Skip to content

Commit 62b7d68

Browse files
Jessica Zhanglumag
authored andcommitted
drm/msm/dpu: Filter modes based on adjusted mode clock
Filter out modes that have a clock rate greater than the max core clock rate when adjusted for the perf clock factor This is especially important for chipsets such as QCS615 that have lower limits for the MDP max core clock. Since the core CRTC clock is at least the mode clock (adjusted for the perf clock factor) [1], the modes supported by the driver should be less than the max core clock rate. [1] https://elixir.bootlin.com/linux/v6.12.4/source/drivers/gpu/drm/msm/disp/dpu1/dpu_core_perf.c#L83 Reviewed-by: Dmitry Baryshkov <dmitry.baryshkov@linaro.org> Signed-off-by: Jessica Zhang <jessica.zhang@oss.qualcomm.com> Patchwork: https://patchwork.freedesktop.org/patch/652041/ Link: https://lore.kernel.org/r/20250506-filter-modes-v2-1-c20a0b7aa241@oss.qualcomm.com Signed-off-by: Dmitry Baryshkov <dmitry.baryshkov@oss.qualcomm.com>
1 parent 12c3c6c commit 62b7d68

File tree

3 files changed

+39
-11
lines changed

3 files changed

+39
-11
lines changed

drivers/gpu/drm/msm/disp/dpu1/dpu_core_perf.c

Lines changed: 24 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,26 @@ enum dpu_perf_mode {
3131
DPU_PERF_MODE_MAX
3232
};
3333

34+
/**
35+
* dpu_core_perf_adjusted_mode_clk - Adjust given mode clock rate according to
36+
* the perf clock factor.
37+
* @crtc_clk_rate - Unadjusted mode clock rate
38+
* @perf_cfg: performance configuration
39+
*/
40+
u64 dpu_core_perf_adjusted_mode_clk(u64 mode_clk_rate,
41+
const struct dpu_perf_cfg *perf_cfg)
42+
{
43+
u32 clk_factor;
44+
45+
clk_factor = perf_cfg->clk_inefficiency_factor;
46+
if (clk_factor) {
47+
mode_clk_rate *= clk_factor;
48+
do_div(mode_clk_rate, 100);
49+
}
50+
51+
return mode_clk_rate;
52+
}
53+
3454
/**
3555
* _dpu_core_perf_calc_bw() - to calculate BW per crtc
3656
* @perf_cfg: performance configuration
@@ -75,28 +95,21 @@ static u64 _dpu_core_perf_calc_clk(const struct dpu_perf_cfg *perf_cfg,
7595
struct drm_plane *plane;
7696
struct dpu_plane_state *pstate;
7797
struct drm_display_mode *mode;
78-
u64 crtc_clk;
79-
u32 clk_factor;
98+
u64 mode_clk;
8099

81100
mode = &state->adjusted_mode;
82101

83-
crtc_clk = (u64)mode->vtotal * mode->hdisplay * drm_mode_vrefresh(mode);
102+
mode_clk = (u64)mode->vtotal * mode->hdisplay * drm_mode_vrefresh(mode);
84103

85104
drm_atomic_crtc_for_each_plane(plane, crtc) {
86105
pstate = to_dpu_plane_state(plane->state);
87106
if (!pstate)
88107
continue;
89108

90-
crtc_clk = max(pstate->plane_clk, crtc_clk);
91-
}
92-
93-
clk_factor = perf_cfg->clk_inefficiency_factor;
94-
if (clk_factor) {
95-
crtc_clk *= clk_factor;
96-
do_div(crtc_clk, 100);
109+
mode_clk = max(pstate->plane_clk, mode_clk);
97110
}
98111

99-
return crtc_clk;
112+
return dpu_core_perf_adjusted_mode_clk(mode_clk, perf_cfg);
100113
}
101114

102115
static struct dpu_kms *_dpu_crtc_get_kms(struct drm_crtc *crtc)

drivers/gpu/drm/msm/disp/dpu1/dpu_core_perf.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,9 @@ struct dpu_core_perf {
5454
u32 fix_core_ab_vote;
5555
};
5656

57+
u64 dpu_core_perf_adjusted_mode_clk(u64 clk_rate,
58+
const struct dpu_perf_cfg *perf_cfg);
59+
5760
int dpu_core_perf_crtc_check(struct drm_crtc *crtc,
5861
struct drm_crtc_state *state);
5962

drivers/gpu/drm/msm/disp/dpu1/dpu_crtc.c

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1534,13 +1534,25 @@ static enum drm_mode_status dpu_crtc_mode_valid(struct drm_crtc *crtc,
15341534
const struct drm_display_mode *mode)
15351535
{
15361536
struct dpu_kms *dpu_kms = _dpu_crtc_get_kms(crtc);
1537+
u64 adjusted_mode_clk;
15371538

15381539
/* if there is no 3d_mux block we cannot merge LMs so we cannot
15391540
* split the large layer into 2 LMs, filter out such modes
15401541
*/
15411542
if (!dpu_kms->catalog->caps->has_3d_merge &&
15421543
mode->hdisplay > dpu_kms->catalog->caps->max_mixer_width)
15431544
return MODE_BAD_HVALUE;
1545+
1546+
adjusted_mode_clk = dpu_core_perf_adjusted_mode_clk(mode->clock,
1547+
dpu_kms->perf.perf_cfg);
1548+
1549+
/*
1550+
* The given mode, adjusted for the perf clock factor, should not exceed
1551+
* the max core clock rate
1552+
*/
1553+
if (dpu_kms->perf.max_core_clk_rate < adjusted_mode_clk * 1000)
1554+
return MODE_CLOCK_HIGH;
1555+
15441556
/*
15451557
* max crtc width is equal to the max mixer width * 2 and max height is 4K
15461558
*/

0 commit comments

Comments
 (0)