On 2025/09/11, Marius Vlad wrote:
> From: Derek Foreman <[email protected]>
>
> This adds YUV444 and Auto, which will fallback to RGB as per
> commit "drm: Pass supported color formats straight onto drm_bridge".
>
> Signed-off-by: Derek Foreman <[email protected]>
> Signed-off-by: Marius Vlad <[email protected]>
> ---
>  .../gpu/drm/rockchip/dw_hdmi_qp-rockchip.c    | 10 +++-
>  drivers/gpu/drm/rockchip/inno_hdmi.c          |  8 ++++
>  drivers/gpu/drm/rockchip/rk3066_hdmi.c        |  8 ++++
>  drivers/gpu/drm/rockchip/rockchip_drm_vop2.c  | 46 +++++++++++++++++++
>  drivers/gpu/drm/rockchip/rockchip_drm_vop2.h  |  2 +
>  5 files changed, 73 insertions(+), 1 deletion(-)
>
> diff --git a/drivers/gpu/drm/rockchip/dw_hdmi_qp-rockchip.c 
> b/drivers/gpu/drm/rockchip/dw_hdmi_qp-rockchip.c
> index 58e24669ef34..794b8de9c9c5 100644
> --- a/drivers/gpu/drm/rockchip/dw_hdmi_qp-rockchip.c
> +++ b/drivers/gpu/drm/rockchip/dw_hdmi_qp-rockchip.c
> @@ -427,6 +427,11 @@ static const struct of_device_id 
> dw_hdmi_qp_rockchip_dt_ids[] = {
>  };
>  MODULE_DEVICE_TABLE(of, dw_hdmi_qp_rockchip_dt_ids);
>
> +static const u32 supported_colorformats =
> +       DRM_COLOR_FORMAT_AUTO |
> +       DRM_COLOR_FORMAT_RGB444 |
> +       DRM_COLOR_FORMAT_YCBCR444;
> +
>  static int dw_hdmi_qp_rockchip_bind(struct device *dev, struct device 
> *master,
>                                   void *data)
>  {
> @@ -563,13 +568,16 @@ static int dw_hdmi_qp_rockchip_bind(struct device *dev, 
> struct device *master,
>               return ret;
>       }
>
> -     connector = drm_bridge_connector_init(drm, encoder, 
> BIT(HDMI_COLORSPACE_RGB));
> +     connector = drm_bridge_connector_init(drm, encoder, 
> supported_colorformats);

The supported formats set to BIT(HDMI_COLORSPACE_RGB) initially as part
of drm_bridge_connector_init() and further moved out and passed as an
argument via "[PATCH 5/8] drm: Pass supported color formats straight
onto drm_bridge" is nothing but a default value to be used later on
drmm_connector_hdmi_init() invocation if the HDMI bridge in the display
pipeline (currently the framework allows only one bridge in a chain to
set DRM_BRIDGE_OP_HDMI) does not provide it's own supported_formats
before it gets attached to the encoder's chain.  Otherwise it will be
simply overridden:

    if (bridge->supported_formats)
        supported_formats = bridge->supported_formats;

This is precisely the case with [1] handling platform supported formats
and color depth in DW HDMI QP library.

>       if (IS_ERR(connector)) {
>               ret = PTR_ERR(connector);
>               dev_err(hdmi->dev, "failed to init bridge connector: %d\n", 
> ret);
>               return ret;
>       }
>
> +     if (!drm_mode_create_hdmi_color_format_property(connector, 
> supported_colorformats))
> +             drm_connector_attach_color_format_property(connector);
> +
>       return drm_connector_attach_encoder(connector, encoder);
>  }

[...]

> diff --git a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c 
> b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c
> index 186f6452a7d3..5634e59a6412 100644
> --- a/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c
> +++ b/drivers/gpu/drm/rockchip/rockchip_drm_vop2.c
> @@ -1543,6 +1543,50 @@ static void vop2_dither_setup(struct drm_crtc *crtc, 
> u32 *dsp_ctrl)
>                               DITHER_DOWN_ALLEGRO);
>  }
>
> +static void vop2_bcsh_config(struct drm_crtc *crtc, struct vop2_video_port 
> *vp)
> +{
> +     struct drm_connector_list_iter conn_iter;
> +     struct drm_connector *connector;
> +     u32 format = 0;
> +     enum drm_colorspace colorspace = 0;
> +     u32 val = 0;
> +
> +     drm_connector_list_iter_begin(crtc->dev, &conn_iter);
> +     drm_for_each_connector_iter(connector, &conn_iter) {
> +             if (!(crtc->state->connector_mask & 
> drm_connector_mask(connector)))
> +                     continue;
> +
> +             format = connector->state->color_format;
> +             colorspace = connector->state->colorspace;
> +             break;
> +     }
> +     drm_connector_list_iter_end(&conn_iter);
> +
> +     if (format == DRM_COLOR_FORMAT_YCBCR420 ||
> +         format == DRM_COLOR_FORMAT_YCBCR444 ||
> +         format == DRM_COLOR_FORMAT_YCBCR422) {
> +             val = RK3568_VP_BCSH_CTRL__BCSH_R2Y_EN | BIT(7);
> +
> +             switch (colorspace) {
> +             case DRM_MODE_COLORIMETRY_BT2020_RGB:
> +             case DRM_MODE_COLORIMETRY_BT2020_YCC:
> +                     val |= BIT(7) | BIT(6);
> +                     break;
> +             case DRM_MODE_COLORIMETRY_BT709_YCC:
> +                     val |= BIT(6);
> +                     break;
> +             default:
> +                     break;
> +             }
> +             if (colorspace == DRM_MODE_COLORIMETRY_BT2020_RGB ||
> +                 colorspace == DRM_MODE_COLORIMETRY_BT2020_YCC)

While working on YUV420 output format support [2] I noticed VOP2 relies
on v4l2_colorspace instead of drm_colorspace, presumably that's just a
downstream inheritance.  Moreover, it also defines a custom
vop_csc_format and provides the vop2_convert_csc_mode() helper to translate
the V4L2_COLORSPACE_* entries into the internal CSC_* representation, as
required for the actual HW programming.

I implemented the rockchip_drm_colorimetry_to_v4l_colorspace() utility
in [3] to convert drm_colorspace to v4l2_colorspace as a temporary
workaround to pass conn_state->colorspace via
dw_hdmi_qp_rockchip_encoder_atomic_check() in [2].

I think we should try first to clean this up before adding even more
colorspace related mess, i.e. if possible get rid of v4l2_colorspace and
rely exclusively on drm_colorspace while providing a conversion helper
to the internal vop_csc_format.

Alternatively, we could keep the rockchip changes in this series to the
bare minimum (i.e. RGB-only) and handle YUV separately, to avoid adding
here unnecessary and/or unrelated complexity.  It's worth noting the 
indicated YUV420 related work has been done on top of the high color 
depth support series [1] for the required platform support, while in 
turn it conflicts with the HDMI CEC series [4], hence added as a 
dependency.

[1] 
https://lore.kernel.org/all/[email protected]/
[2] 
https://gitlab.collabora.com/hardware-enablement/rockchip-3588/linux/-/commit/6d78f42a5b88cf83cff771f7cccc44c8d67b9695
[3] 
https://gitlab.collabora.com/hardware-enablement/rockchip-3588/linux/-/commit/9ce7c0c95ce024ee5799a3e5f776c98609683090
[4] 
https://lore.kernel.org/all/[email protected]/

Reply via email to