mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2026-05-08 14:02:37 -04:00
drm/i915/pfit: Check pipe source size against pfit limits on ILK-BDW
The ILK-BDW panel fitter imposes extra limits on the maximum pipe source size we can use. Check for that. Only HSW/BDW are really affected by this since on older platforms the max hdisplay/vdisplay matches the max PIPESRC. But we'll put in the limits for all the platforms just to keep things clear. Note that pch_panel_fitting() is also used on SKL+, but we'll skip the checks for those as it's all supposed to be handled in the unified scaler code. Signed-off-by: Ville Syrjälä <ville.syrjala@linux.intel.com> Link: https://patchwork.freedesktop.org/patch/msgid/20241016143134.26903-2-ville.syrjala@linux.intel.com Acked-by: Jani Nikula <jani.nikula@intel.com>
This commit is contained in:
@@ -383,15 +383,54 @@ void intel_panel_add_encoder_fixed_mode(struct intel_connector *connector,
|
||||
"current (BIOS)");
|
||||
}
|
||||
|
||||
static int intel_pch_pfit_check_src_size(const struct intel_crtc_state *crtc_state)
|
||||
{
|
||||
struct intel_display *display = to_intel_display(crtc_state);
|
||||
struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc);
|
||||
int pipe_src_w = drm_rect_width(&crtc_state->pipe_src);
|
||||
int pipe_src_h = drm_rect_height(&crtc_state->pipe_src);
|
||||
int max_src_w, max_src_h;
|
||||
|
||||
if (DISPLAY_VER(display) >= 8) {
|
||||
max_src_w = 4096;
|
||||
max_src_h = 4096;
|
||||
} else if (DISPLAY_VER(display) >= 7) {
|
||||
/*
|
||||
* PF0 7x5 capable
|
||||
* PF1 3x3 capable (could be switched to 7x5
|
||||
* mode on HSW when PF2 unused)
|
||||
* PF2 3x3 capable
|
||||
*
|
||||
* This assumes we use a 1:1 mapping between pipe and PF.
|
||||
*/
|
||||
max_src_w = crtc->pipe == PIPE_A ? 4096 : 2048;
|
||||
max_src_h = 4096;
|
||||
} else {
|
||||
max_src_w = 4096;
|
||||
max_src_h = 4096;
|
||||
}
|
||||
|
||||
if (pipe_src_w > max_src_w || pipe_src_h > max_src_h) {
|
||||
drm_dbg_kms(display->drm,
|
||||
"[CRTC:%d:%s] source size (%dx%d) exceeds pfit max (%dx%d)\n",
|
||||
crtc->base.base.id, crtc->base.name,
|
||||
pipe_src_w, pipe_src_h, max_src_w, max_src_h);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* adjusted_mode has been preset to be the panel's fixed mode */
|
||||
static int pch_panel_fitting(struct intel_crtc_state *crtc_state,
|
||||
const struct drm_connector_state *conn_state)
|
||||
{
|
||||
struct intel_display *display = to_intel_display(crtc_state);
|
||||
const struct drm_display_mode *adjusted_mode =
|
||||
&crtc_state->hw.adjusted_mode;
|
||||
int pipe_src_w = drm_rect_width(&crtc_state->pipe_src);
|
||||
int pipe_src_h = drm_rect_height(&crtc_state->pipe_src);
|
||||
int x, y, width, height;
|
||||
int ret, x, y, width, height;
|
||||
|
||||
/* Native modes don't need fitting */
|
||||
if (adjusted_mode->crtc_hdisplay == pipe_src_w &&
|
||||
@@ -453,6 +492,17 @@ static int pch_panel_fitting(struct intel_crtc_state *crtc_state,
|
||||
x, y, width, height);
|
||||
crtc_state->pch_pfit.enabled = true;
|
||||
|
||||
/*
|
||||
* SKL+ have unified scalers for pipes/planes so the
|
||||
* checks are done in a single place for all scalers.
|
||||
*/
|
||||
if (DISPLAY_VER(display) >= 9)
|
||||
return 0;
|
||||
|
||||
ret = intel_pch_pfit_check_src_size(crtc_state);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user