diff options
author | Laurent Pinchart <laurent.pinchart@ideasonboard.com> | 2018-09-13 00:17:01 +0300 |
---|---|---|
committer | Tomi Valkeinen <tomi.valkeinen@ti.com> | 2019-03-18 11:42:12 +0200 |
commit | 870e19d59f8a2e13750861d8f8f49e93188634ec (patch) | |
tree | f7729f94cc9ca45f2a4c2797c7ddadc651a44a53 /drivers/gpu/drm/omapdrm | |
parent | d17eb4537a7eb16da9eafbfd5717e12b45b77251 (diff) | |
download | linux-stable-870e19d59f8a2e13750861d8f8f49e93188634ec.tar.gz linux-stable-870e19d59f8a2e13750861d8f8f49e93188634ec.tar.bz2 linux-stable-870e19d59f8a2e13750861d8f8f49e93188634ec.zip |
drm/omap: Expose DRM modes instead of timings in display devices
omap_dss_device operations expose fixed video timings through a
.get_timings() operation that return a single timing for the device. To
prepare for the move to drm_bridge, modify the API to instead add DRM
modes directly to the connector.
As this puts more burden on display devices, we also create a helper
function for panels to add a single DRM mode from the panel video
timings.
Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Reviewed-by: Sebastian Reichel <sebastian.reichel@collabora.com>
Tested-by: Sebastian Reichel <sebastian.reichel@collabora.com>
Signed-off-by: Tomi Valkeinen <tomi.valkeinen@ti.com>
Diffstat (limited to 'drivers/gpu/drm/omapdrm')
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-dpi.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-dsi-cm.c | 10 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-lgphilips-lb035q02.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-nec-nl8048hl11.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-sharp-ls037v7dw01.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-sony-acx565akm.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-tpo-td028ttec1.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/displays/panel-tpo-td043mtea1.c | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/dss/display.c | 22 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/dss/omapdss.h | 8 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/dss/venc.c | 12 | ||||
-rw-r--r-- | drivers/gpu/drm/omapdrm/omap_connector.c | 33 |
12 files changed, 80 insertions, 61 deletions
diff --git a/drivers/gpu/drm/omapdrm/displays/panel-dpi.c b/drivers/gpu/drm/omapdrm/displays/panel-dpi.c index eee44d9ea0c3..d6a584292e91 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-dpi.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-dpi.c @@ -68,12 +68,12 @@ static void panel_dpi_disable(struct omap_dss_device *dssdev) regulator_disable(ddata->vcc_supply); } -static void panel_dpi_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int panel_dpi_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static const struct omap_dss_device_ops panel_dpi_ops = { @@ -83,7 +83,7 @@ static const struct omap_dss_device_ops panel_dpi_ops = { .enable = panel_dpi_enable, .disable = panel_dpi_disable, - .get_timings = panel_dpi_get_timings, + .get_modes = panel_dpi_get_modes, }; static int panel_dpi_probe_of(struct platform_device *pdev) diff --git a/drivers/gpu/drm/omapdrm/displays/panel-dsi-cm.c b/drivers/gpu/drm/omapdrm/displays/panel-dsi-cm.c index ffbf20e6ebe9..9cd9ab487a24 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-dsi-cm.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-dsi-cm.c @@ -24,6 +24,8 @@ #include <linux/of_device.h> #include <linux/regulator/consumer.h> +#include <drm/drm_connector.h> + #include <video/mipi_display.h> #include <video/of_display_timing.h> @@ -1110,12 +1112,12 @@ static void dsicm_ulps_work(struct work_struct *work) mutex_unlock(&ddata->lock); } -static void dsicm_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int dsicm_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static int dsicm_check_timings(struct omap_dss_device *dssdev, @@ -1156,7 +1158,7 @@ static const struct omap_dss_device_ops dsicm_ops = { .enable = dsicm_enable, .disable = dsicm_disable, - .get_timings = dsicm_get_timings, + .get_modes = dsicm_get_modes, .check_timings = dsicm_check_timings, }; diff --git a/drivers/gpu/drm/omapdrm/displays/panel-lgphilips-lb035q02.c b/drivers/gpu/drm/omapdrm/displays/panel-lgphilips-lb035q02.c index e043cab0a0c9..e05b7f80416e 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-lgphilips-lb035q02.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-lgphilips-lb035q02.c @@ -139,12 +139,12 @@ static void lb035q02_disable(struct omap_dss_device *dssdev) gpiod_set_value_cansleep(ddata->enable_gpio, 0); } -static void lb035q02_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int lb035q02_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static const struct omap_dss_device_ops lb035q02_ops = { @@ -154,7 +154,7 @@ static const struct omap_dss_device_ops lb035q02_ops = { .enable = lb035q02_enable, .disable = lb035q02_disable, - .get_timings = lb035q02_get_timings, + .get_modes = lb035q02_get_modes, }; static int lb035q02_probe_of(struct spi_device *spi) diff --git a/drivers/gpu/drm/omapdrm/displays/panel-nec-nl8048hl11.c b/drivers/gpu/drm/omapdrm/displays/panel-nec-nl8048hl11.c index 44fd6134317d..cf2127837e67 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-nec-nl8048hl11.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-nec-nl8048hl11.c @@ -132,12 +132,12 @@ static void nec_8048_disable(struct omap_dss_device *dssdev) gpiod_set_value_cansleep(ddata->res_gpio, 0); } -static void nec_8048_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int nec_8048_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static const struct omap_dss_device_ops nec_8048_ops = { @@ -147,7 +147,7 @@ static const struct omap_dss_device_ops nec_8048_ops = { .enable = nec_8048_enable, .disable = nec_8048_disable, - .get_timings = nec_8048_get_timings, + .get_modes = nec_8048_get_modes, }; static int nec_8048_probe(struct spi_device *spi) diff --git a/drivers/gpu/drm/omapdrm/displays/panel-sharp-ls037v7dw01.c b/drivers/gpu/drm/omapdrm/displays/panel-sharp-ls037v7dw01.c index 907abf8ef4e6..30320cee1e56 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-sharp-ls037v7dw01.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-sharp-ls037v7dw01.c @@ -111,12 +111,12 @@ static void sharp_ls_post_disable(struct omap_dss_device *dssdev) regulator_disable(ddata->vcc); } -static void sharp_ls_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int sharp_ls_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static const struct omap_dss_device_ops sharp_ls_ops = { @@ -128,7 +128,7 @@ static const struct omap_dss_device_ops sharp_ls_ops = { .disable = sharp_ls_disable, .post_disable = sharp_ls_post_disable, - .get_timings = sharp_ls_get_timings, + .get_modes = sharp_ls_get_modes, }; static int sharp_ls_get_gpio_of(struct device *dev, int index, int val, diff --git a/drivers/gpu/drm/omapdrm/displays/panel-sony-acx565akm.c b/drivers/gpu/drm/omapdrm/displays/panel-sony-acx565akm.c index eeaea752f171..8debe77f92ff 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-sony-acx565akm.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-sony-acx565akm.c @@ -596,12 +596,12 @@ static void acx565akm_disable(struct omap_dss_device *dssdev) mutex_unlock(&ddata->mutex); } -static void acx565akm_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int acx565akm_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static const struct omap_dss_device_ops acx565akm_ops = { @@ -611,7 +611,7 @@ static const struct omap_dss_device_ops acx565akm_ops = { .enable = acx565akm_enable, .disable = acx565akm_disable, - .get_timings = acx565akm_get_timings, + .get_modes = acx565akm_get_modes, }; static int acx565akm_probe(struct spi_device *spi) diff --git a/drivers/gpu/drm/omapdrm/displays/panel-tpo-td028ttec1.c b/drivers/gpu/drm/omapdrm/displays/panel-tpo-td028ttec1.c index f1a5c14407a4..c8b15f19a166 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-tpo-td028ttec1.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-tpo-td028ttec1.c @@ -272,12 +272,12 @@ static void td028ttec1_panel_disable(struct omap_dss_device *dssdev) jbt_reg_write_1(ddata, JBT_REG_POWER_ON_OFF, 0x00); } -static void td028ttec1_panel_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int td028ttec1_panel_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static const struct omap_dss_device_ops td028ttec1_ops = { @@ -287,7 +287,7 @@ static const struct omap_dss_device_ops td028ttec1_ops = { .enable = td028ttec1_panel_enable, .disable = td028ttec1_panel_disable, - .get_timings = td028ttec1_panel_get_timings, + .get_modes = td028ttec1_panel_get_modes, }; static int td028ttec1_panel_probe(struct spi_device *spi) diff --git a/drivers/gpu/drm/omapdrm/displays/panel-tpo-td043mtea1.c b/drivers/gpu/drm/omapdrm/displays/panel-tpo-td043mtea1.c index 996a16736d10..9ecc4c7bee67 100644 --- a/drivers/gpu/drm/omapdrm/displays/panel-tpo-td043mtea1.c +++ b/drivers/gpu/drm/omapdrm/displays/panel-tpo-td043mtea1.c @@ -347,12 +347,12 @@ static void tpo_td043_disable(struct omap_dss_device *dssdev) tpo_td043_power_off(ddata); } -static void tpo_td043_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int tpo_td043_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct panel_drv_data *ddata = to_panel_data(dssdev); - *vm = ddata->vm; + return omapdss_display_get_modes(connector, &ddata->vm); } static const struct omap_dss_device_ops tpo_td043_ops = { @@ -362,7 +362,7 @@ static const struct omap_dss_device_ops tpo_td043_ops = { .enable = tpo_td043_enable, .disable = tpo_td043_disable, - .get_timings = tpo_td043_get_timings, + .get_modes = tpo_td043_get_modes, }; static int tpo_td043_probe(struct spi_device *spi) diff --git a/drivers/gpu/drm/omapdrm/dss/display.c b/drivers/gpu/drm/omapdrm/dss/display.c index 34b2a4ef63a4..398964358386 100644 --- a/drivers/gpu/drm/omapdrm/dss/display.c +++ b/drivers/gpu/drm/omapdrm/dss/display.c @@ -23,6 +23,9 @@ #include <linux/kernel.h> #include <linux/of.h> +#include <drm/drm_connector.h> +#include <drm/drm_modes.h> + #include "omapdss.h" static int disp_num_counter; @@ -58,3 +61,22 @@ struct omap_dss_device *omapdss_display_get(struct omap_dss_device *output) return omapdss_device_get(output); } EXPORT_SYMBOL_GPL(omapdss_display_get); + +int omapdss_display_get_modes(struct drm_connector *connector, + const struct videomode *vm) +{ + struct drm_display_mode *mode; + + mode = drm_mode_create(connector->dev); + if (!mode) + return 0; + + drm_display_mode_from_videomode(vm, mode); + + mode->type = DRM_MODE_TYPE_DRIVER | DRM_MODE_TYPE_PREFERRED; + drm_mode_set_name(mode); + drm_mode_probed_add(connector, mode); + + return 1; +} +EXPORT_SYMBOL_GPL(omapdss_display_get_modes); diff --git a/drivers/gpu/drm/omapdrm/dss/omapdss.h b/drivers/gpu/drm/omapdrm/dss/omapdss.h index fbdeeaa521d6..88fa61ddc959 100644 --- a/drivers/gpu/drm/omapdrm/dss/omapdss.h +++ b/drivers/gpu/drm/omapdrm/dss/omapdss.h @@ -67,6 +67,7 @@ struct dss_lcd_mgr_config; struct snd_aes_iec958; struct snd_cea_861_aud_if; struct hdmi_avi_infoframe; +struct drm_connector; enum omap_display_type { OMAP_DISPLAY_TYPE_NONE = 0, @@ -366,8 +367,6 @@ struct omap_dss_device_ops { int (*check_timings)(struct omap_dss_device *dssdev, struct videomode *vm); - void (*get_timings)(struct omap_dss_device *dssdev, - struct videomode *vm); void (*set_timings)(struct omap_dss_device *dssdev, const struct videomode *vm); @@ -381,6 +380,9 @@ struct omap_dss_device_ops { int (*read_edid)(struct omap_dss_device *dssdev, u8 *buf, int len); + int (*get_modes)(struct omap_dss_device *dssdev, + struct drm_connector *connector); + union { const struct omapdss_hdmi_ops hdmi; const struct omapdss_dsi_ops dsi; @@ -469,6 +471,8 @@ static inline bool omapdss_is_initialized(void) void omapdss_display_init(struct omap_dss_device *dssdev); struct omap_dss_device *omapdss_display_get(struct omap_dss_device *output); +int omapdss_display_get_modes(struct drm_connector *connector, + const struct videomode *vm); void omapdss_device_register(struct omap_dss_device *dssdev); void omapdss_device_unregister(struct omap_dss_device *dssdev); diff --git a/drivers/gpu/drm/omapdrm/dss/venc.c b/drivers/gpu/drm/omapdrm/dss/venc.c index 3fc776c45c4f..cefefe6d6fcb 100644 --- a/drivers/gpu/drm/omapdrm/dss/venc.c +++ b/drivers/gpu/drm/omapdrm/dss/venc.c @@ -548,14 +548,17 @@ static void venc_display_disable(struct omap_dss_device *dssdev) mutex_unlock(&venc->venc_lock); } -static void venc_get_timings(struct omap_dss_device *dssdev, - struct videomode *vm) +static int venc_get_modes(struct omap_dss_device *dssdev, + struct drm_connector *connector) { struct venc_device *venc = dssdev_to_venc(dssdev); + int r; mutex_lock(&venc->venc_lock); - *vm = venc->vm; + r = omapdss_display_get_modes(connector, &venc->vm); mutex_unlock(&venc->venc_lock); + + return r; } static void venc_set_timings(struct omap_dss_device *dssdev, @@ -690,8 +693,9 @@ static const struct omap_dss_device_ops venc_ops = { .disable = venc_display_disable, .check_timings = venc_check_timings, - .get_timings = venc_get_timings, .set_timings = venc_set_timings, + + .get_modes = venc_get_modes, }; /* ----------------------------------------------------------------------------- diff --git a/drivers/gpu/drm/omapdrm/omap_connector.c b/drivers/gpu/drm/omapdrm/omap_connector.c index 9da94d10782a..8d9197eebb53 100644 --- a/drivers/gpu/drm/omapdrm/omap_connector.c +++ b/drivers/gpu/drm/omapdrm/omap_connector.c @@ -212,8 +212,6 @@ static int omap_connector_get_modes(struct drm_connector *connector) { struct omap_connector *omap_connector = to_omap_connector(connector); struct omap_dss_device *dssdev; - struct drm_display_mode *mode; - struct videomode vm = {0}; DBG("%s", omap_connector->display->name); @@ -238,31 +236,20 @@ static int omap_connector_get_modes(struct drm_connector *connector) &connector->display_info.height_mm); /* - * Iterate over the pipeline to find the first device that can provide - * timing information. If we can't find any, we just let the KMS core - * add the default modes. + * If the display pipeline reports modes (e.g. with a fixed resolution + * panel or an analog TV output), query it. */ for (dssdev = omap_connector->display; dssdev; dssdev = dssdev->src) { - if (dssdev->ops->get_timings) - break; + if (dssdev->ops->get_modes) + return dssdev->ops->get_modes(dssdev, connector); } - if (!dssdev) - return 0; - - /* Add a single mode corresponding to the fixed panel timings. */ - mode = drm_mode_create(connector->dev); - if (!mode) - return 0; - - dssdev->ops->get_timings(dssdev, &vm); - - drm_display_mode_from_videomode(&vm, mode); - mode->type = DRM_MODE_TYPE_DRIVER | DRM_MODE_TYPE_PREFERRED; - drm_mode_set_name(mode); - drm_mode_probed_add(connector, mode); - - return 1; + /* + * We can't retrieve modes, which can happen for instance for a DVI or + * VGA output with the DDC bus unconnected. The KMS core will add the + * default modes. + */ + return 0; } static int omap_connector_mode_valid(struct drm_connector *connector, |