[PATCH 6/8] drm: rcar-du: rcar-lvds: Add bridge format support
Jacopo Mondi
jacopo+renesas at jmondi.org
Thu Apr 19 09:31:07 UTC 2018
With the introduction of static input image format enumeration in DRM
bridges, add support to retrieve the format in rcar-lvds LVDS encoder
from both panel or bridge, to set the desired LVDS mode.
Do not rely on 'DRM_BUS_FLAG_DATA_LSB_TO_MSB' flag to mirror the LVDS
format, as it is only defined for drm connectors, but use the newly
introduced _LE version of LVDS mbus image formats.
Signed-off-by: Jacopo Mondi <jacopo+renesas at jmondi.org>
---
drivers/gpu/drm/rcar-du/rcar_lvds.c | 64 +++++++++++++++++++++++++------------
1 file changed, 44 insertions(+), 20 deletions(-)
diff --git a/drivers/gpu/drm/rcar-du/rcar_lvds.c b/drivers/gpu/drm/rcar-du/rcar_lvds.c
index 3d2d3bb..2fa875f 100644
--- a/drivers/gpu/drm/rcar-du/rcar_lvds.c
+++ b/drivers/gpu/drm/rcar-du/rcar_lvds.c
@@ -280,41 +280,65 @@ static bool rcar_lvds_mode_fixup(struct drm_bridge *bridge,
return true;
}
-static void rcar_lvds_get_lvds_mode(struct rcar_lvds *lvds)
+static int rcar_lvds_get_lvds_mode_from_connector(struct rcar_lvds *lvds,
+ unsigned int *bus_fmt)
{
struct drm_display_info *info = &lvds->connector.display_info;
- enum rcar_lvds_mode mode;
-
- /*
- * There is no API yet to retrieve LVDS mode from a bridge, only panels
- * are supported.
- */
- if (!lvds->panel)
- return;
if (!info->num_bus_formats || !info->bus_formats) {
dev_err(lvds->dev, "no LVDS bus format reported\n");
- return;
+ return -EINVAL;
+ }
+
+ *bus_fmt = info->bus_formats[0];
+
+ return 0;
+}
+
+static int rcar_lvds_get_lvds_mode_from_bridge(struct rcar_lvds *lvds,
+ unsigned int *bus_fmt)
+{
+ if (!lvds->next_bridge->num_bus_formats ||
+ !lvds->next_bridge->bus_formats) {
+ dev_err(lvds->dev, "no LVDS bus format reported\n");
+ return -EINVAL;
}
- switch (info->bus_formats[0]) {
+ *bus_fmt = lvds->next_bridge->bus_formats[0];
+
+ return 0;
+}
+
+static void rcar_lvds_get_lvds_mode(struct rcar_lvds *lvds)
+{
+ unsigned int bus_fmt;
+ int ret;
+
+ if (lvds->panel)
+ ret = rcar_lvds_get_lvds_mode_from_connector(lvds, &bus_fmt);
+ else
+ ret = rcar_lvds_get_lvds_mode_from_bridge(lvds, &bus_fmt);
+ if (ret)
+ return;
+
+ switch (bus_fmt) {
+ case MEDIA_BUS_FMT_RGB666_1X7X3_SPWG_LE:
+ case MEDIA_BUS_FMT_RGB888_1X7X4_JEIDA_LE:
+ lvds->mode |= RCAR_LVDS_MODE_MIRROR;
case MEDIA_BUS_FMT_RGB666_1X7X3_SPWG:
case MEDIA_BUS_FMT_RGB888_1X7X4_JEIDA:
- mode = RCAR_LVDS_MODE_JEIDA;
+ lvds->mode = RCAR_LVDS_MODE_JEIDA;
break;
+
+ case MEDIA_BUS_FMT_RGB888_1X7X4_SPWG_LE:
+ lvds->mode |= RCAR_LVDS_MODE_MIRROR;
case MEDIA_BUS_FMT_RGB888_1X7X4_SPWG:
- mode = RCAR_LVDS_MODE_VESA;
+ lvds->mode = RCAR_LVDS_MODE_VESA;
break;
default:
dev_err(lvds->dev, "unsupported LVDS bus format 0x%04x\n",
- info->bus_formats[0]);
- return;
+ bus_fmt);
}
-
- if (info->bus_flags & DRM_BUS_FLAG_DATA_LSB_TO_MSB)
- mode |= RCAR_LVDS_MODE_MIRROR;
-
- lvds->mode = mode;
}
static void rcar_lvds_mode_set(struct drm_bridge *bridge,
--
2.7.4
More information about the dri-devel
mailing list