From 66660d4cf21b7dfcb258d8a51734963802693796 Mon Sep 17 00:00:00 2001 From: Dave Airlie Date: Mon, 16 Oct 2017 05:08:09 +0100 Subject: [PATCH] drm: add connector info/property for non-desktop displays [v2] This adds the infrastructure needed to quirk displays using edid and to mark them a non-desktop. A non-desktop display is one which shouldn't normally be included as a part of a desktop environment. This is meant to cover head mounted devices like HTC Vive. v2: Change description from non-standard to non-desktop, add docs Reviewed-by: Keith Packard Signed-off-by: Dave Airlie fixup docs --- drivers/gpu/drm/drm_connector.c | 17 +++++++++++++++++ drivers/gpu/drm/drm_edid.c | 8 ++++++-- include/drm/drm_connector.h | 5 +++++ include/drm/drm_mode_config.h | 7 +++++++ 4 files changed, 35 insertions(+), 2 deletions(-) diff --git a/drivers/gpu/drm/drm_connector.c b/drivers/gpu/drm/drm_connector.c index 704fc8934616..25f4b2e9a44f 100644 --- a/drivers/gpu/drm/drm_connector.c +++ b/drivers/gpu/drm/drm_connector.c @@ -234,6 +234,10 @@ int drm_connector_init(struct drm_device *dev, config->link_status_property, 0); + drm_object_attach_property(&connector->base, + config->non_desktop_property, + 0); + if (drm_core_check_feature(dev, DRIVER_ATOMIC)) { drm_object_attach_property(&connector->base, config->prop_crtc_id, 0); } @@ -763,6 +767,10 @@ DRM_ENUM_NAME_FN(drm_get_tv_subconnector_name, * value of link-status is "GOOD". If something fails during or after modeset, * the kernel driver may set this to "BAD" and issue a hotplug uevent. Drivers * should update this value using drm_mode_connector_set_link_status_property(). + * non_desktop: + * Indicates the output should be ignored for purposes of displaying a + * standard desktop environment or console. This is most likely because + * the output device is not rectilinear. * * Connectors also have one standardized atomic property: * @@ -811,6 +819,11 @@ int drm_connector_create_standard_properties(struct drm_device *dev) return -ENOMEM; dev->mode_config.link_status_property = prop; + prop = drm_property_create_bool(dev, DRM_MODE_PROP_IMMUTABLE, "non-desktop"); + if (!prop) + return -ENOMEM; + dev->mode_config.non_desktop_property = prop; + return 0; } @@ -1194,6 +1207,10 @@ int drm_mode_connector_update_edid_property(struct drm_connector *connector, if (edid) size = EDID_LENGTH * (1 + edid->extensions); + drm_object_property_set_value(&connector->base, + dev->mode_config.non_desktop_property, + connector->display_info.non_desktop); + ret = drm_property_replace_global_blob(dev, &connector->edid_blob_ptr, size, diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c index 00ddabfbf980..1e24d5d9d659 100644 --- a/drivers/gpu/drm/drm_edid.c +++ b/drivers/gpu/drm/drm_edid.c @@ -82,6 +82,8 @@ #define EDID_QUIRK_FORCE_6BPC (1 << 10) /* Force 10bpc */ #define EDID_QUIRK_FORCE_10BPC (1 << 11) +/* Non desktop display (i.e. HMD) */ +#define EDID_QUIRK_NON_DESKTOP (1 << 12) struct detailed_mode_closure { struct drm_connector *connector; @@ -4393,7 +4395,7 @@ static void drm_parse_cea_ext(struct drm_connector *connector, } static void drm_add_display_info(struct drm_connector *connector, - struct edid *edid) + struct edid *edid, u32 quirks) { struct drm_display_info *info = &connector->display_info; @@ -4407,6 +4409,8 @@ static void drm_add_display_info(struct drm_connector *connector, info->max_tmds_clock = 0; info->dvi_dual = false; + info->non_desktop = !!(quirks & EDID_QUIRK_NON_DESKTOP); + if (edid->revision < 3) return; @@ -4627,7 +4631,7 @@ int drm_add_edid_modes(struct drm_connector *connector, struct edid *edid) * To avoid multiple parsing of same block, lets parse that map * from sink info, before parsing CEA modes. */ - drm_add_display_info(connector, edid); + drm_add_display_info(connector, edid, quirks); /* * EDID spec says modes should be preferred in this order: diff --git a/include/drm/drm_connector.h b/include/drm/drm_connector.h index 7a7140543012..df9807a3caae 100644 --- a/include/drm/drm_connector.h +++ b/include/drm/drm_connector.h @@ -284,6 +284,11 @@ struct drm_display_info { * @hdmi: advance features of a HDMI sink. */ struct drm_hdmi_info hdmi; + + /** + * @non_desktop: Non desktop display (HMD). + */ + bool non_desktop; }; int drm_display_info_set_bus_formats(struct drm_display_info *info, diff --git a/include/drm/drm_mode_config.h b/include/drm/drm_mode_config.h index 0b4ac2ebc610..b21e827c5c78 100644 --- a/include/drm/drm_mode_config.h +++ b/include/drm/drm_mode_config.h @@ -728,6 +728,13 @@ struct drm_mode_config { */ struct drm_property *suggested_y_property; + /** + * @non_desktop_property: Optional connector property with a hint + * that device isn't a standard display, and the console/desktop, + * should not be displayed on it. + */ + struct drm_property *non_desktop_property; + /* dumb ioctl parameters */ uint32_t preferred_depth, prefer_shadow; -- GitLab