[PATCH] drm/i915/pfit: Prevent negative coordinates in center mode

Nemesa Garg
2026-03-31T18:25:22Z

When the pipe_src width or height are greater than adjusted_mode hdisplay
and vdisplay, computed x and y offsets for center mode can be negative.
Writing negative values into the pch_fit registers result in a state error.
Add a check to clamp these values so that they are never negative.

v2: Compare in terms of pipe_src width and height.[Ville]

Signed-off-by: Nemesa Garg <nemesa.garg@intel.com>
---
drivers/gpu/drm/i915/display/intel_pfit.c | 11 +++++++++++
1 file changed, 11 insertions(+)

diff --git a/drivers/gpu/drm/i915/display/intel_pfit.c b/drivers/gpu/drm/i915/display/intel_pfit.c
index 6dda496190e0..0edd29eef6ad 100644
--- a/drivers/gpu/drm/i915/display/intel_pfit.c
+++ b/drivers/gpu/drm/i915/display/intel_pfit.c
@@ -186,6 +186,7 @@ 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);
+ struct intel_crtc *crtc = to_intel_crtc(crtc_state->uapi.crtc);
const struct drm_display_mode *adjusted_mode =
&crtc_state->hw.adjusted_mode;
int pipe_src_w = drm_rect_width(&crtc_state->pipe_src);
@@ -200,6 +201,16 @@ static int pch_panel_fitting(struct intel_crtc_state *crtc_state,

switch (conn_state->scaling_mode) {
case DRM_MODE_SCALE_CENTER:
+ if (adjusted_mode->crtc_hdisplay < pipe_src_w ||
+ adjusted_mode->crtc_vdisplay < pipe_src_h) {
+ drm_dbg_kms(display->drm,
+ "[CRTC:%d:%s] pfit center mode source (%dx%d) exceeds display (%dx%d)\n",
+ crtc->base.base.id, crtc->base.name,
+ width, height,
+ adjusted_mode->crtc_hdisplay,
+ adjusted_mode->crtc_vdisplay);
+ return -EINVAL;
+ }
width = pipe_src_w;
height = pipe_src_h;
x = (adjusted_mode->crtc_hdisplay - width + 1)/2;
--
2.25.1