Linux-ARM-Kernel Archive on lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH] drm/rockchip: vop2: add COLOR_ENCODING and COLOR_RANGE plane properties
@ 2026-07-16 11:30 Igor Paunovic
  0 siblings, 0 replies; only message in thread
From: Igor Paunovic @ 2026-07-16 11:30 UTC (permalink / raw)
  To: Sandy Huang, Heiko Stübner, Andy Yan
  Cc: Maarten Lankhorst, Maxime Ripard, Thomas Zimmermann, dri-devel,
	linux-rockchip, linux-arm-kernel, linux-kernel, Igor Paunovic

The VOP2 windows have a YCbCr to RGB conversion block whose coefficient
matrix is selected by a per-window CSC mode field, with hardware support
for BT.601, BT.709 (both limited range) and BT.2020, plus a BT.601 full
range mode. So far the driver hardcodes this to BT.709 limited range for
every YUV plane, so BT.601 (SD) and BT.2020 content is converted with
the wrong matrix.

Expose the standard COLOR_ENCODING and COLOR_RANGE plane properties and
program the window CSC mode from them, so userspace can request the
matrix matching the framebuffer. The default stays BT.709 limited range,
which matches the previous behaviour. The hardware has no full range
mode for the BT.709 and BT.2020 encodings, so that combination is
rejected in the plane atomic check.

Signed-off-by: Igor Paunovic <royalnet026@gmail.com>
---
 drivers/gpu/drm/rockchip/rockchip_drm_vop2.c | 40 +++++++++++++++++++-
 1 file changed, 38 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c
index 4cce3e3..22e056b 100644
--- a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c
+++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c
@@ -667,6 +667,22 @@ static int vop2_convert_csc_mode(int csc_mode)
 	}
 }
 
+static int vop2_convert_color_encoding(enum drm_color_encoding color_encoding,
+				       enum drm_color_range color_range)
+{
+	bool full_range = color_range == DRM_COLOR_YCBCR_FULL_RANGE;
+
+	switch (color_encoding) {
+	case DRM_COLOR_YCBCR_BT601:
+		return full_range ? CSC_BT601F : CSC_BT601L;
+	case DRM_COLOR_YCBCR_BT2020:
+		return CSC_BT2020L;
+	case DRM_COLOR_YCBCR_BT709:
+	default:
+		return CSC_BT709L;
+	}
+}
+
 /*
  * colorspace path:
  *      Input        Win csc                     Output
@@ -707,7 +723,6 @@ static void vop2_setup_csc_mode(struct vop2_video_port *vp,
 	struct rockchip_crtc_state *vcstate = to_rockchip_crtc_state(vp->crtc.state);
 	int is_input_yuv = pstate->fb->format->is_yuv;
 	int is_output_yuv = is_yuv_output(vcstate->bus_format);
-	int input_csc = V4L2_COLORSPACE_DEFAULT;
 	int output_csc = vcstate->color_space;
 	bool r2y_en, y2r_en;
 	int csc_mode;
@@ -715,7 +730,8 @@ static void vop2_setup_csc_mode(struct vop2_video_port *vp,
 	if (is_input_yuv && !is_output_yuv) {
 		y2r_en = true;
 		r2y_en = false;
-		csc_mode = vop2_convert_csc_mode(input_csc);
+		csc_mode = vop2_convert_color_encoding(pstate->color_encoding,
+						       pstate->color_range);
 	} else if (!is_input_yuv && is_output_yuv) {
 		y2r_en = false;
 		r2y_en = true;
@@ -1109,6 +1125,18 @@ static int vop2_plane_atomic_check(struct drm_plane *plane,
 	if (WARN_ON(format < 0))
 		return format;
 
+	/*
+	 * The window CSC hardware has no full range mode for the BT.709 and
+	 * BT.2020 encodings, so reject that combination.
+	 */
+	if (fb->format->is_yuv &&
+	    pstate->color_range == DRM_COLOR_YCBCR_FULL_RANGE &&
+	    pstate->color_encoding != DRM_COLOR_YCBCR_BT601) {
+		drm_dbg_kms(vop2->drm,
+			    "Full range is only supported with BT.601 encoding\n");
+		return -EINVAL;
+	}
+
 	/* Co-ordinates have now been clipped */
 	src_x = src->x1 >> 16;
 	src_w = drm_rect_width(src) >> 16;
@@ -2472,6 +2500,14 @@ static int vop2_plane_init(struct vop2 *vop2, struct vop2_win *win,
 	drm_plane_create_blend_mode_property(&win->base, blend_caps);
 	drm_plane_create_zpos_property(&win->base, win->win_id, 0,
 				       vop2->registered_num_wins - 1);
+	drm_plane_create_color_properties(&win->base,
+					  BIT(DRM_COLOR_YCBCR_BT601) |
+					  BIT(DRM_COLOR_YCBCR_BT709) |
+					  BIT(DRM_COLOR_YCBCR_BT2020),
+					  BIT(DRM_COLOR_YCBCR_LIMITED_RANGE) |
+					  BIT(DRM_COLOR_YCBCR_FULL_RANGE),
+					  DRM_COLOR_YCBCR_BT709,
+					  DRM_COLOR_YCBCR_LIMITED_RANGE);
 
 	return 0;
 }
-- 
2.53.0



^ permalink raw reply related	[flat|nested] only message in thread

only message in thread, other threads:[~2026-07-16 11:31 UTC | newest]

Thread overview: (only message) (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-07-16 11:30 [PATCH] drm/rockchip: vop2: add COLOR_ENCODING and COLOR_RANGE plane properties Igor Paunovic

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox