All of lore.kernel.org
 help / color / mirror / Atom feed
From: Maxime Ripard <maxime@cerno.tech>
To: Andrzej Hajda <a.hajda@samsung.com>,
	Laurent Pinchart <Laurent.pinchart@ideasonboard.com>,
	Daniel Vetter <daniel.vetter@intel.com>,
	David Airlie <airlied@linux.ie>,
	Jernej Skrabec <jernej.skrabec@siol.net>,
	Maarten Lankhorst <maarten.lankhorst@linux.intel.com>,
	Thomas Zimmermann <tzimmermann@suse.de>,
	Maxime Ripard <maxime@cerno.tech>,
	Neil Armstrong <narmstrong@baylibre.com>,
	Jonas Karlman <jonas@kwiboo.se>
Cc: Tim Gover <tim.gover@raspberrypi.com>,
	Dave Stevenson <dave.stevenson@raspberrypi.com>,
	dri-devel@lists.freedesktop.org,
	bcm-kernel-feedback-list@broadcom.com,
	linux-rpi-kernel@lists.infradead.org,
	Phil Elwell <phil@raspberrypi.com>
Subject: [PATCH 02/18] drm/bridge: Add HDMI output fmt helper
Date: Wed, 17 Mar 2021 16:43:36 +0100	[thread overview]
Message-ID: <20210317154352.732095-3-maxime@cerno.tech> (raw)
In-Reply-To: <20210317154352.732095-1-maxime@cerno.tech>

The atomic_get_output_bus_fmts bridge callback is there to list the
available formats for output by decreasing order of preference.

On HDMI controllers, we have a fairly static list that will depend on
what the HDMI sink is capable of and the BPC our controller can output.

The dw-hdmi driver already has that code done in a fairly generic
manner, so let's turn that code into an helper for all the HDMI
controllers to reuse.

Signed-off-by: Maxime Ripard <maxime@cerno.tech>
---
 drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 127 ----------------------
 drivers/gpu/drm/drm_bridge.c              | 118 ++++++++++++++++++++
 include/drm/drm_bridge.h                  |   6 +
 3 files changed, 124 insertions(+), 127 deletions(-)

diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
index dda4fa9a1a08..d010c9c525d9 100644
--- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
@@ -2514,133 +2514,6 @@ static int dw_hdmi_connector_create(struct dw_hdmi *hdmi)
  * DRM Bridge Operations
  */
 
-/*
- * Possible output formats :
- * - MEDIA_BUS_FMT_UYYVYY16_0_5X48,
- * - MEDIA_BUS_FMT_UYYVYY12_0_5X36,
- * - MEDIA_BUS_FMT_UYYVYY10_0_5X30,
- * - MEDIA_BUS_FMT_UYYVYY8_0_5X24,
- * - MEDIA_BUS_FMT_YUV16_1X48,
- * - MEDIA_BUS_FMT_RGB161616_1X48,
- * - MEDIA_BUS_FMT_UYVY12_1X24,
- * - MEDIA_BUS_FMT_YUV12_1X36,
- * - MEDIA_BUS_FMT_RGB121212_1X36,
- * - MEDIA_BUS_FMT_UYVY10_1X20,
- * - MEDIA_BUS_FMT_YUV10_1X30,
- * - MEDIA_BUS_FMT_RGB101010_1X30,
- * - MEDIA_BUS_FMT_UYVY8_1X16,
- * - MEDIA_BUS_FMT_YUV8_1X24,
- * - MEDIA_BUS_FMT_RGB888_1X24,
- */
-
-/* Can return a maximum of 11 possible output formats for a mode/connector */
-#define MAX_OUTPUT_SEL_FORMATS	11
-
-static u32 *dw_hdmi_bridge_atomic_get_output_bus_fmts(struct drm_bridge *bridge,
-					struct drm_bridge_state *bridge_state,
-					struct drm_crtc_state *crtc_state,
-					struct drm_connector_state *conn_state,
-					unsigned int *num_output_fmts)
-{
-	struct drm_connector *conn = conn_state->connector;
-	struct drm_display_info *info = &conn->display_info;
-	struct drm_display_mode *mode = &crtc_state->mode;
-	u8 max_bpc = conn_state->max_requested_bpc;
-	bool is_hdmi2_sink = info->hdmi.scdc.supported ||
-			     (info->color_formats & DRM_COLOR_FORMAT_YCRCB420);
-	u32 *output_fmts;
-	unsigned int i = 0;
-
-	*num_output_fmts = 0;
-
-	output_fmts = kcalloc(MAX_OUTPUT_SEL_FORMATS, sizeof(*output_fmts),
-			      GFP_KERNEL);
-	if (!output_fmts)
-		return NULL;
-
-	/* If dw-hdmi is the only bridge, avoid negociating with ourselves */
-	if (list_is_singular(&bridge->encoder->bridge_chain)) {
-		*num_output_fmts = 1;
-		output_fmts[0] = MEDIA_BUS_FMT_FIXED;
-
-		return output_fmts;
-	}
-
-	/*
-	 * If the current mode enforces 4:2:0, force the output but format
-	 * to 4:2:0 and do not add the YUV422/444/RGB formats
-	 */
-	if (conn->ycbcr_420_allowed &&
-	    (drm_mode_is_420_only(info, mode) ||
-	     (is_hdmi2_sink && drm_mode_is_420_also(info, mode)))) {
-
-		/* Order bus formats from 16bit to 8bit if supported */
-		if (max_bpc >= 16 && info->bpc == 16 &&
-		    (info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_48))
-			output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY16_0_5X48;
-
-		if (max_bpc >= 12 && info->bpc >= 12 &&
-		    (info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_36))
-			output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY12_0_5X36;
-
-		if (max_bpc >= 10 && info->bpc >= 10 &&
-		    (info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_30))
-			output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY10_0_5X30;
-
-		/* Default 8bit fallback */
-		output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY8_0_5X24;
-
-		*num_output_fmts = i;
-
-		return output_fmts;
-	}
-
-	/*
-	 * Order bus formats from 16bit to 8bit and from YUV422 to RGB
-	 * if supported. In any case the default RGB888 format is added
-	 */
-
-	if (max_bpc >= 16 && info->bpc == 16) {
-		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
-			output_fmts[i++] = MEDIA_BUS_FMT_YUV16_1X48;
-
-		output_fmts[i++] = MEDIA_BUS_FMT_RGB161616_1X48;
-	}
-
-	if (max_bpc >= 12 && info->bpc >= 12) {
-		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB422)
-			output_fmts[i++] = MEDIA_BUS_FMT_UYVY12_1X24;
-
-		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
-			output_fmts[i++] = MEDIA_BUS_FMT_YUV12_1X36;
-
-		output_fmts[i++] = MEDIA_BUS_FMT_RGB121212_1X36;
-	}
-
-	if (max_bpc >= 10 && info->bpc >= 10) {
-		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB422)
-			output_fmts[i++] = MEDIA_BUS_FMT_UYVY10_1X20;
-
-		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
-			output_fmts[i++] = MEDIA_BUS_FMT_YUV10_1X30;
-
-		output_fmts[i++] = MEDIA_BUS_FMT_RGB101010_1X30;
-	}
-
-	if (info->color_formats & DRM_COLOR_FORMAT_YCRCB422)
-		output_fmts[i++] = MEDIA_BUS_FMT_UYVY8_1X16;
-
-	if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
-		output_fmts[i++] = MEDIA_BUS_FMT_YUV8_1X24;
-
-	/* Default 8bit RGB fallback */
-	output_fmts[i++] = MEDIA_BUS_FMT_RGB888_1X24;
-
-	*num_output_fmts = i;
-
-	return output_fmts;
-}
-
 /*
  * Possible input formats :
  * - MEDIA_BUS_FMT_RGB888_1X24
diff --git a/drivers/gpu/drm/drm_bridge.c b/drivers/gpu/drm/drm_bridge.c
index 64f0effb52ac..253cbca1c19e 100644
--- a/drivers/gpu/drm/drm_bridge.c
+++ b/drivers/gpu/drm/drm_bridge.c
@@ -1035,6 +1035,124 @@ int drm_atomic_bridge_chain_check(struct drm_bridge *bridge,
 }
 EXPORT_SYMBOL(drm_atomic_bridge_chain_check);
 
+/* Can return a maximum of 11 possible output formats for a mode/connector */
+#define MAX_OUTPUT_SEL_FORMATS	11
+
+/**
+ * drm_bridge_helper_hdmi_atomic_get_output_bus_fmts() - Lists the output formats for an HDMI sink
+ * @bridge: bridge control structure
+ * @bridge_state: bridge state
+ * @crtc_state: CRTC state
+ * @conn_state: connector state
+ * @num_output_fmts: number of formats returned
+ *
+ * Returns the supported bus formats on the output end of an HDMI
+ * bridge. The returned array is allocated with kmalloc and will thus
+ * need to be freed. Formats will be listed in decreasing preference
+ * order, the framework eventually picking the highest preference
+ * available across all the bridges.
+ *
+ * RETURNS:
+ * an array of MEDIA_FMT_* on success, NULL on failure
+ */
+u32 *drm_atomic_helper_bridge_hdmi_get_output_bus_fmts(struct drm_bridge *bridge,
+						       struct drm_bridge_state *bridge_state,
+						       struct drm_crtc_state *crtc_state,
+						       struct drm_connector_state *conn_state,
+						       unsigned int *num_output_fmts)
+{
+	struct drm_connector *conn = conn_state->connector;
+	struct drm_display_info *info = &conn->display_info;
+	struct drm_display_mode *mode = &crtc_state->mode;
+	u8 max_bpc = conn_state->max_requested_bpc;
+	bool is_hdmi2_sink = info->hdmi.scdc.supported ||
+			     (info->color_formats & DRM_COLOR_FORMAT_YCRCB420);
+	u32 *output_fmts;
+	unsigned int i = 0;
+
+	*num_output_fmts = 0;
+
+	output_fmts = kcalloc(MAX_OUTPUT_SEL_FORMATS, sizeof(*output_fmts),
+			      GFP_KERNEL);
+	if (!output_fmts)
+		return NULL;
+
+	/*
+	 * If the current mode enforces 4:2:0, force the output but format
+	 * to 4:2:0 and do not add the YUV422/444/RGB formats
+	 */
+	if (conn->ycbcr_420_allowed &&
+	    (drm_mode_is_420_only(info, mode) ||
+	     (is_hdmi2_sink && drm_mode_is_420_also(info, mode)))) {
+
+		/* Order bus formats from 16bit to 8bit if supported */
+		if (max_bpc >= 16 && info->bpc == 16 &&
+		    (info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_48))
+			output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY16_0_5X48;
+
+		if (max_bpc >= 12 && info->bpc >= 12 &&
+		    (info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_36))
+			output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY12_0_5X36;
+
+		if (max_bpc >= 10 && info->bpc >= 10 &&
+		    (info->hdmi.y420_dc_modes & DRM_EDID_YCBCR420_DC_30))
+			output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY10_0_5X30;
+
+		/* Default 8bit fallback */
+		output_fmts[i++] = MEDIA_BUS_FMT_UYYVYY8_0_5X24;
+
+		*num_output_fmts = i;
+
+		return output_fmts;
+	}
+
+	/*
+	 * Order bus formats from 16bit to 8bit and from YUV422 to RGB
+	 * if supported. In any case the default RGB888 format is added
+	 */
+
+	if (max_bpc >= 16 && info->bpc == 16) {
+		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
+			output_fmts[i++] = MEDIA_BUS_FMT_YUV16_1X48;
+
+		output_fmts[i++] = MEDIA_BUS_FMT_RGB161616_1X48;
+	}
+
+	if (max_bpc >= 12 && info->bpc >= 12) {
+		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB422)
+			output_fmts[i++] = MEDIA_BUS_FMT_UYVY12_1X24;
+
+		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
+			output_fmts[i++] = MEDIA_BUS_FMT_YUV12_1X36;
+
+		output_fmts[i++] = MEDIA_BUS_FMT_RGB121212_1X36;
+	}
+
+	if (max_bpc >= 10 && info->bpc >= 10) {
+		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB422)
+			output_fmts[i++] = MEDIA_BUS_FMT_UYVY10_1X20;
+
+		if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
+			output_fmts[i++] = MEDIA_BUS_FMT_YUV10_1X30;
+
+		output_fmts[i++] = MEDIA_BUS_FMT_RGB101010_1X30;
+	}
+
+	if (info->color_formats & DRM_COLOR_FORMAT_YCRCB422)
+		output_fmts[i++] = MEDIA_BUS_FMT_UYVY8_1X16;
+
+	if (info->color_formats & DRM_COLOR_FORMAT_YCRCB444)
+		output_fmts[i++] = MEDIA_BUS_FMT_YUV8_1X24;
+
+	/* Default 8bit RGB fallback */
+	output_fmts[i++] = MEDIA_BUS_FMT_RGB888_1X24;
+
+	*num_output_fmts = i;
+
+	return output_fmts;
+}
+EXPORT_SYMBOL_GPL(drm_atomic_helper_bridge_hdmi_get_output_bus_fmts);
+
 /**
  * drm_bridge_detect - check if anything is attached to the bridge output
  * @bridge: bridge control structure
diff --git a/include/drm/drm_bridge.h b/include/drm/drm_bridge.h
index 2195daa289d2..1d801d77e90a 100644
--- a/include/drm/drm_bridge.h
+++ b/include/drm/drm_bridge.h
@@ -868,6 +868,12 @@ drm_atomic_helper_bridge_propagate_bus_fmt(struct drm_bridge *bridge,
 					u32 output_fmt,
 					unsigned int *num_input_fmts);
 
+u32 *drm_atomic_helper_bridge_hdmi_get_output_bus_fmts(struct drm_bridge *bridge,
+						       struct drm_bridge_state *bridge_state,
+						       struct drm_crtc_state *crtc_state,
+						       struct drm_connector_state *conn_state,
+						       unsigned int *num_output_fmts);
+
 enum drm_connector_status drm_bridge_detect(struct drm_bridge *bridge);
 int drm_bridge_get_modes(struct drm_bridge *bridge,
 			 struct drm_connector *connector);
-- 
2.30.2

_______________________________________________
dri-devel mailing list
dri-devel@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/dri-devel

  parent reply	other threads:[~2021-03-17 15:44 UTC|newest]

Thread overview: 48+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-03-17 15:43 [PATCH 00/18] drm/vc4: hdmi: Add Support for the YUV output Maxime Ripard
2021-03-17 15:43 ` [PATCH 01/18] drm: Introduce new HDMI helpers Maxime Ripard
2021-04-09  7:16   ` Thomas Zimmermann
2021-03-17 15:43 ` Maxime Ripard [this message]
2021-03-17 16:08   ` [PATCH 02/18] drm/bridge: Add HDMI output fmt helper Neil Armstrong
2021-03-18 18:31     ` Jernej Škrabec
2021-03-19  9:44       ` Neil Armstrong
2021-03-19 10:09         ` Maxime Ripard
2021-04-09  8:03   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 03/18] drm/bridge: dw-hdmi: Use helpers Maxime Ripard
2021-04-09  8:05   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 04/18] drm/vc4: txp: Properly set the possible_crtcs mask Maxime Ripard
2021-04-09  8:07   ` Thomas Zimmermann
2021-04-09  8:11   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 05/18] drm/vc4: crtc: Skip the TXP Maxime Ripard
2021-04-09  8:10   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 06/18] drm/vc4: Rework the encoder retrieval code Maxime Ripard
2021-03-17 18:09   ` kernel test robot
2021-03-20  1:08   ` kernel test robot
2021-04-09  8:54   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 07/18] drm/vc4: hdmi: Add full range RGB helper Maxime Ripard
2021-04-12  9:44   ` Thomas Zimmermann
2021-04-14 13:48     ` Maxime Ripard
2021-03-17 15:43 ` [PATCH 08/18] drm/vc4: hdmi: Use full range helper in csc functions Maxime Ripard
2021-04-12  9:45   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 09/18] drm/vc4: hdmi: Remove limited_rgb_range Maxime Ripard
2021-04-12 10:19   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 10/18] drm/vc4: hdmi: Convert to bridge Maxime Ripard
2021-04-12 10:21   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 11/18] drm/vc4: hdmi: Move XBAR setup to csc_setup Maxime Ripard
2021-04-12 10:28   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 12/18] drm/vc4: hdmi: Replace CSC_CTL hardcoded value by defines Maxime Ripard
2021-04-12 10:28   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 13/18] drm/vc4: hdmi: Define colorspace matrices Maxime Ripard
2021-04-14 13:54   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 14/18] drm/vc4: hdmi: Change CSC callback prototype Maxime Ripard
2021-04-14 13:56   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 15/18] drm/vc4: hdmi: Rework the infoframe prototype Maxime Ripard
2021-04-14 13:58   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 16/18] drm/vc4: hdmi: Support HDMI YUV output Maxime Ripard
2021-04-15  6:43   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 17/18] drm/vc4: hdmi: Move the pixel rate calculation to a helper Maxime Ripard
2021-04-15  7:19   ` Thomas Zimmermann
2021-03-17 15:43 ` [PATCH 18/18] drm/vc4: hdmi: Force YUV422 if the rate is too high Maxime Ripard
2021-04-15  7:24   ` Thomas Zimmermann
2021-03-18 18:16 ` [PATCH 00/18] drm/vc4: hdmi: Add Support for the YUV output Jernej Škrabec
2021-03-19 10:13   ` Maxime Ripard
2021-04-09  9:47   ` Neil Armstrong

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20210317154352.732095-3-maxime@cerno.tech \
    --to=maxime@cerno.tech \
    --cc=Laurent.pinchart@ideasonboard.com \
    --cc=a.hajda@samsung.com \
    --cc=airlied@linux.ie \
    --cc=bcm-kernel-feedback-list@broadcom.com \
    --cc=daniel.vetter@intel.com \
    --cc=dave.stevenson@raspberrypi.com \
    --cc=dri-devel@lists.freedesktop.org \
    --cc=jernej.skrabec@siol.net \
    --cc=jonas@kwiboo.se \
    --cc=linux-rpi-kernel@lists.infradead.org \
    --cc=maarten.lankhorst@linux.intel.com \
    --cc=narmstrong@baylibre.com \
    --cc=phil@raspberrypi.com \
    --cc=tim.gover@raspberrypi.com \
    --cc=tzimmermann@suse.de \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.