aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/drm_crtc.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2014-12-15 18:52:01 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2014-12-15 18:52:01 -0500
commit988adfdffdd43cfd841df734664727993076d7cb (patch)
tree6794f7bba8f595500c2b7d33376ad6614adcfaf2 /drivers/gpu/drm/drm_crtc.c
parent26178ec11ef3c6c814bf16a0a2b9c2f7242e3c64 (diff)
parent4e0cd68115620bc3236ff4e58e4c073948629b41 (diff)
Merge branch 'drm-next' of git://people.freedesktop.org/~airlied/linux
Pull drm updates from Dave Airlie: "Highlights: - AMD KFD driver merge This is the AMD HSA interface for exposing a lowlevel interface for GPGPU use. They have an open source userspace built on top of this interface, and the code looks as good as it was going to get out of tree. - Initial atomic modesetting work The need for an atomic modesetting interface to allow userspace to try and send a complete set of modesetting state to the driver has arisen, and been suffering from neglect this past year. No more, the start of the common code and changes for msm driver to use it are in this tree. Ongoing work to get the userspace ioctl finished and the code clean will probably wait until next kernel. - DisplayID 1.3 and tiled monitor exposed to userspace. Tiled monitor property is now exposed for userspace to make use of. - Rockchip drm driver merged. - imx gpu driver moved out of staging Other stuff: - core: panel - MIPI DSI + new panels. expose suggested x/y properties for virtual GPUs - i915: Initial Skylake (SKL) support gen3/4 reset work start of dri1/ums removal infoframe tracking fixes for lots of things. - nouveau: tegra k1 voltage support GM204 modesetting support GT21x memory reclocking work - radeon: CI dpm fixes GPUVM improvements Initial DPM fan control - rcar-du: HDMI support added removed some support for old boards slave encoder driver for Analog Devices adv7511 - exynos: Exynos4415 SoC support - msm: a4xx gpu support atomic helper conversion - tegra: iommu support universal plane support ganged-mode DSI support - sti: HDMI i2c improvements - vmwgfx: some late fixes. - qxl: use suggested x/y properties" * 'drm-next' of git://people.freedesktop.org/~airlied/linux: (969 commits) drm: sti: fix module compilation issue drm/i915: save/restore GMBUS freq across suspend/resume on gen4 drm: sti: correctly cleanup CRTC and planes drm: sti: add HQVDP plane drm: sti: add cursor plane drm: sti: enable auxiliary CRTC drm: sti: fix delay in VTG programming drm: sti: prepare sti_tvout to support auxiliary crtc drm: sti: use drm_crtc_vblank_{on/off} instead of drm_vblank_{on/off} drm: sti: fix hdmi avi infoframe drm: sti: remove event lock while disabling vblank drm: sti: simplify gdp code drm: sti: clear all mixer control drm: sti: remove gpio for HDMI hot plug detection drm: sti: allow to change hdmi ddc i2c adapter drm/doc: Document drm_add_modes_noedid() usage drm/i915: Remove '& 0xffff' from the mask given to WA_REG() drm/i915: Invert the mask and val arguments in wa_add() and WA_REG() drm: Zero out DRM object memory upon cleanup drm/i915/bdw: Fix the write setting up the WIZ hashing mode ...
Diffstat (limited to 'drivers/gpu/drm/drm_crtc.c')
-rw-r--r--drivers/gpu/drm/drm_crtc.c581
1 files changed, 400 insertions, 181 deletions
diff --git a/drivers/gpu/drm/drm_crtc.c b/drivers/gpu/drm/drm_crtc.c
index e79c8d3700d8..5213da499d39 100644
--- a/drivers/gpu/drm/drm_crtc.c
+++ b/drivers/gpu/drm/drm_crtc.c
@@ -683,7 +683,7 @@ int drm_crtc_init_with_planes(struct drm_device *dev, struct drm_crtc *crtc,
683 drm_modeset_lock_init(&crtc->mutex); 683 drm_modeset_lock_init(&crtc->mutex);
684 ret = drm_mode_object_get(dev, &crtc->base, DRM_MODE_OBJECT_CRTC); 684 ret = drm_mode_object_get(dev, &crtc->base, DRM_MODE_OBJECT_CRTC);
685 if (ret) 685 if (ret)
686 goto out; 686 return ret;
687 687
688 crtc->base.properties = &crtc->properties; 688 crtc->base.properties = &crtc->properties;
689 689
@@ -697,9 +697,7 @@ int drm_crtc_init_with_planes(struct drm_device *dev, struct drm_crtc *crtc,
697 if (cursor) 697 if (cursor)
698 cursor->possible_crtcs = 1 << drm_crtc_index(crtc); 698 cursor->possible_crtcs = 1 << drm_crtc_index(crtc);
699 699
700 out: 700 return 0;
701
702 return ret;
703} 701}
704EXPORT_SYMBOL(drm_crtc_init_with_planes); 702EXPORT_SYMBOL(drm_crtc_init_with_planes);
705 703
@@ -723,6 +721,12 @@ void drm_crtc_cleanup(struct drm_crtc *crtc)
723 drm_mode_object_put(dev, &crtc->base); 721 drm_mode_object_put(dev, &crtc->base);
724 list_del(&crtc->head); 722 list_del(&crtc->head);
725 dev->mode_config.num_crtc--; 723 dev->mode_config.num_crtc--;
724
725 WARN_ON(crtc->state && !crtc->funcs->atomic_destroy_state);
726 if (crtc->state && crtc->funcs->atomic_destroy_state)
727 crtc->funcs->atomic_destroy_state(crtc, crtc->state);
728
729 memset(crtc, 0, sizeof(*crtc));
726} 730}
727EXPORT_SYMBOL(drm_crtc_cleanup); 731EXPORT_SYMBOL(drm_crtc_cleanup);
728 732
@@ -766,7 +770,6 @@ static void drm_mode_remove(struct drm_connector *connector,
766/** 770/**
767 * drm_connector_get_cmdline_mode - reads the user's cmdline mode 771 * drm_connector_get_cmdline_mode - reads the user's cmdline mode
768 * @connector: connector to quwery 772 * @connector: connector to quwery
769 * @mode: returned mode
770 * 773 *
771 * The kernel supports per-connector configration of its consoles through 774 * The kernel supports per-connector configration of its consoles through
772 * use of the video= parameter. This function parses that option and 775 * use of the video= parameter. This function parses that option and
@@ -870,6 +873,8 @@ int drm_connector_init(struct drm_device *dev,
870 873
871 drm_connector_get_cmdline_mode(connector); 874 drm_connector_get_cmdline_mode(connector);
872 875
876 /* We should add connectors at the end to avoid upsetting the connector
877 * index too much. */
873 list_add_tail(&connector->head, &dev->mode_config.connector_list); 878 list_add_tail(&connector->head, &dev->mode_config.connector_list);
874 dev->mode_config.num_connector++; 879 dev->mode_config.num_connector++;
875 880
@@ -905,6 +910,11 @@ void drm_connector_cleanup(struct drm_connector *connector)
905 struct drm_device *dev = connector->dev; 910 struct drm_device *dev = connector->dev;
906 struct drm_display_mode *mode, *t; 911 struct drm_display_mode *mode, *t;
907 912
913 if (connector->tile_group) {
914 drm_mode_put_tile_group(dev, connector->tile_group);
915 connector->tile_group = NULL;
916 }
917
908 list_for_each_entry_safe(mode, t, &connector->probed_modes, head) 918 list_for_each_entry_safe(mode, t, &connector->probed_modes, head)
909 drm_mode_remove(connector, mode); 919 drm_mode_remove(connector, mode);
910 920
@@ -919,6 +929,13 @@ void drm_connector_cleanup(struct drm_connector *connector)
919 connector->name = NULL; 929 connector->name = NULL;
920 list_del(&connector->head); 930 list_del(&connector->head);
921 dev->mode_config.num_connector--; 931 dev->mode_config.num_connector--;
932
933 WARN_ON(connector->state && !connector->funcs->atomic_destroy_state);
934 if (connector->state && connector->funcs->atomic_destroy_state)
935 connector->funcs->atomic_destroy_state(connector,
936 connector->state);
937
938 memset(connector, 0, sizeof(*connector));
922} 939}
923EXPORT_SYMBOL(drm_connector_cleanup); 940EXPORT_SYMBOL(drm_connector_cleanup);
924 941
@@ -933,6 +950,9 @@ unsigned int drm_connector_index(struct drm_connector *connector)
933{ 950{
934 unsigned int index = 0; 951 unsigned int index = 0;
935 struct drm_connector *tmp; 952 struct drm_connector *tmp;
953 struct drm_mode_config *config = &connector->dev->mode_config;
954
955 WARN_ON(!drm_modeset_is_locked(&config->connection_mutex));
936 956
937 list_for_each_entry(tmp, &connector->dev->mode_config.connector_list, head) { 957 list_for_each_entry(tmp, &connector->dev->mode_config.connector_list, head) {
938 if (tmp == connector) 958 if (tmp == connector)
@@ -1057,6 +1077,8 @@ void drm_bridge_cleanup(struct drm_bridge *bridge)
1057 list_del(&bridge->head); 1077 list_del(&bridge->head);
1058 dev->mode_config.num_bridge--; 1078 dev->mode_config.num_bridge--;
1059 drm_modeset_unlock_all(dev); 1079 drm_modeset_unlock_all(dev);
1080
1081 memset(bridge, 0, sizeof(*bridge));
1060} 1082}
1061EXPORT_SYMBOL(drm_bridge_cleanup); 1083EXPORT_SYMBOL(drm_bridge_cleanup);
1062 1084
@@ -1123,10 +1145,11 @@ void drm_encoder_cleanup(struct drm_encoder *encoder)
1123 drm_modeset_lock_all(dev); 1145 drm_modeset_lock_all(dev);
1124 drm_mode_object_put(dev, &encoder->base); 1146 drm_mode_object_put(dev, &encoder->base);
1125 kfree(encoder->name); 1147 kfree(encoder->name);
1126 encoder->name = NULL;
1127 list_del(&encoder->head); 1148 list_del(&encoder->head);
1128 dev->mode_config.num_encoder--; 1149 dev->mode_config.num_encoder--;
1129 drm_modeset_unlock_all(dev); 1150 drm_modeset_unlock_all(dev);
1151
1152 memset(encoder, 0, sizeof(*encoder));
1130} 1153}
1131EXPORT_SYMBOL(drm_encoder_cleanup); 1154EXPORT_SYMBOL(drm_encoder_cleanup);
1132 1155
@@ -1153,11 +1176,11 @@ int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
1153{ 1176{
1154 int ret; 1177 int ret;
1155 1178
1156 drm_modeset_lock_all(dev);
1157
1158 ret = drm_mode_object_get(dev, &plane->base, DRM_MODE_OBJECT_PLANE); 1179 ret = drm_mode_object_get(dev, &plane->base, DRM_MODE_OBJECT_PLANE);
1159 if (ret) 1180 if (ret)
1160 goto out; 1181 return ret;
1182
1183 drm_modeset_lock_init(&plane->mutex);
1161 1184
1162 plane->base.properties = &plane->properties; 1185 plane->base.properties = &plane->properties;
1163 plane->dev = dev; 1186 plane->dev = dev;
@@ -1167,8 +1190,7 @@ int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
1167 if (!plane->format_types) { 1190 if (!plane->format_types) {
1168 DRM_DEBUG_KMS("out of memory when allocating plane\n"); 1191 DRM_DEBUG_KMS("out of memory when allocating plane\n");
1169 drm_mode_object_put(dev, &plane->base); 1192 drm_mode_object_put(dev, &plane->base);
1170 ret = -ENOMEM; 1193 return -ENOMEM;
1171 goto out;
1172 } 1194 }
1173 1195
1174 memcpy(plane->format_types, formats, format_count * sizeof(uint32_t)); 1196 memcpy(plane->format_types, formats, format_count * sizeof(uint32_t));
@@ -1185,10 +1207,7 @@ int drm_universal_plane_init(struct drm_device *dev, struct drm_plane *plane,
1185 dev->mode_config.plane_type_property, 1207 dev->mode_config.plane_type_property,
1186 plane->type); 1208 plane->type);
1187 1209
1188 out: 1210 return 0;
1189 drm_modeset_unlock_all(dev);
1190
1191 return ret;
1192} 1211}
1193EXPORT_SYMBOL(drm_universal_plane_init); 1212EXPORT_SYMBOL(drm_universal_plane_init);
1194 1213
@@ -1246,6 +1265,12 @@ void drm_plane_cleanup(struct drm_plane *plane)
1246 if (plane->type == DRM_PLANE_TYPE_OVERLAY) 1265 if (plane->type == DRM_PLANE_TYPE_OVERLAY)
1247 dev->mode_config.num_overlay_plane--; 1266 dev->mode_config.num_overlay_plane--;
1248 drm_modeset_unlock_all(dev); 1267 drm_modeset_unlock_all(dev);
1268
1269 WARN_ON(plane->state && !plane->funcs->atomic_destroy_state);
1270 if (plane->state && plane->funcs->atomic_destroy_state)
1271 plane->funcs->atomic_destroy_state(plane, plane->state);
1272
1273 memset(plane, 0, sizeof(*plane));
1249} 1274}
1250EXPORT_SYMBOL(drm_plane_cleanup); 1275EXPORT_SYMBOL(drm_plane_cleanup);
1251 1276
@@ -1328,6 +1353,11 @@ static int drm_mode_create_standard_connector_properties(struct drm_device *dev)
1328 "PATH", 0); 1353 "PATH", 0);
1329 dev->mode_config.path_property = dev_path; 1354 dev->mode_config.path_property = dev_path;
1330 1355
1356 dev->mode_config.tile_property = drm_property_create(dev,
1357 DRM_MODE_PROP_BLOB |
1358 DRM_MODE_PROP_IMMUTABLE,
1359 "TILE", 0);
1360
1331 return 0; 1361 return 0;
1332} 1362}
1333 1363
@@ -1388,12 +1418,13 @@ EXPORT_SYMBOL(drm_mode_create_dvi_i_properties);
1388 * responsible for allocating a list of format names and passing them to 1418 * responsible for allocating a list of format names and passing them to
1389 * this routine. 1419 * this routine.
1390 */ 1420 */
1391int drm_mode_create_tv_properties(struct drm_device *dev, int num_modes, 1421int drm_mode_create_tv_properties(struct drm_device *dev,
1422 unsigned int num_modes,
1392 char *modes[]) 1423 char *modes[])
1393{ 1424{
1394 struct drm_property *tv_selector; 1425 struct drm_property *tv_selector;
1395 struct drm_property *tv_subconnector; 1426 struct drm_property *tv_subconnector;
1396 int i; 1427 unsigned int i;
1397 1428
1398 if (dev->mode_config.tv_select_subconnector_property) 1429 if (dev->mode_config.tv_select_subconnector_property)
1399 return 0; 1430 return 0;
@@ -1491,7 +1522,7 @@ EXPORT_SYMBOL(drm_mode_create_scaling_mode_property);
1491 * connectors. 1522 * connectors.
1492 * 1523 *
1493 * Returns: 1524 * Returns:
1494 * Zero on success, errno on failure. 1525 * Zero on success, negative errno on failure.
1495 */ 1526 */
1496int drm_mode_create_aspect_ratio_property(struct drm_device *dev) 1527int drm_mode_create_aspect_ratio_property(struct drm_device *dev)
1497{ 1528{
@@ -1535,6 +1566,30 @@ int drm_mode_create_dirty_info_property(struct drm_device *dev)
1535} 1566}
1536EXPORT_SYMBOL(drm_mode_create_dirty_info_property); 1567EXPORT_SYMBOL(drm_mode_create_dirty_info_property);
1537 1568
1569/**
1570 * drm_mode_create_suggested_offset_properties - create suggests offset properties
1571 * @dev: DRM device
1572 *
1573 * Create the the suggested x/y offset property for connectors.
1574 */
1575int drm_mode_create_suggested_offset_properties(struct drm_device *dev)
1576{
1577 if (dev->mode_config.suggested_x_property && dev->mode_config.suggested_y_property)
1578 return 0;
1579
1580 dev->mode_config.suggested_x_property =
1581 drm_property_create_range(dev, DRM_MODE_PROP_IMMUTABLE, "suggested X", 0, 0xffffffff);
1582
1583 dev->mode_config.suggested_y_property =
1584 drm_property_create_range(dev, DRM_MODE_PROP_IMMUTABLE, "suggested Y", 0, 0xffffffff);
1585
1586 if (dev->mode_config.suggested_x_property == NULL ||
1587 dev->mode_config.suggested_y_property == NULL)
1588 return -ENOMEM;
1589 return 0;
1590}
1591EXPORT_SYMBOL(drm_mode_create_suggested_offset_properties);
1592
1538static int drm_mode_group_init(struct drm_device *dev, struct drm_mode_group *group) 1593static int drm_mode_group_init(struct drm_device *dev, struct drm_mode_group *group)
1539{ 1594{
1540 uint32_t total_objects = 0; 1595 uint32_t total_objects = 0;
@@ -1651,7 +1706,7 @@ static void drm_crtc_convert_to_umode(struct drm_mode_modeinfo *out,
1651 * the caller. 1706 * the caller.
1652 * 1707 *
1653 * Returns: 1708 * Returns:
1654 * Zero on success, errno on failure. 1709 * Zero on success, negative errno on failure.
1655 */ 1710 */
1656static int drm_crtc_convert_umode(struct drm_display_mode *out, 1711static int drm_crtc_convert_umode(struct drm_display_mode *out,
1657 const struct drm_mode_modeinfo *in) 1712 const struct drm_mode_modeinfo *in)
@@ -1694,7 +1749,7 @@ static int drm_crtc_convert_umode(struct drm_display_mode *out,
1694 * Called by the user via ioctl. 1749 * Called by the user via ioctl.
1695 * 1750 *
1696 * Returns: 1751 * Returns:
1697 * Zero on success, errno on failure. 1752 * Zero on success, negative errno on failure.
1698 */ 1753 */
1699int drm_mode_getresources(struct drm_device *dev, void *data, 1754int drm_mode_getresources(struct drm_device *dev, void *data,
1700 struct drm_file *file_priv) 1755 struct drm_file *file_priv)
@@ -1745,7 +1800,9 @@ int drm_mode_getresources(struct drm_device *dev, void *data,
1745 card_res->count_fbs = fb_count; 1800 card_res->count_fbs = fb_count;
1746 mutex_unlock(&file_priv->fbs_lock); 1801 mutex_unlock(&file_priv->fbs_lock);
1747 1802
1748 drm_modeset_lock_all(dev); 1803 /* mode_config.mutex protects the connector list against e.g. DP MST
1804 * connector hot-adding. CRTC/Plane lists are invariant. */
1805 mutex_lock(&dev->mode_config.mutex);
1749 if (!drm_is_primary_client(file_priv)) { 1806 if (!drm_is_primary_client(file_priv)) {
1750 1807
1751 mode_group = NULL; 1808 mode_group = NULL;
@@ -1865,7 +1922,7 @@ int drm_mode_getresources(struct drm_device *dev, void *data,
1865 card_res->count_connectors, card_res->count_encoders); 1922 card_res->count_connectors, card_res->count_encoders);
1866 1923
1867out: 1924out:
1868 drm_modeset_unlock_all(dev); 1925 mutex_unlock(&dev->mode_config.mutex);
1869 return ret; 1926 return ret;
1870} 1927}
1871 1928
@@ -1880,26 +1937,22 @@ out:
1880 * Called by the user via ioctl. 1937 * Called by the user via ioctl.
1881 * 1938 *
1882 * Returns: 1939 * Returns:
1883 * Zero on success, errno on failure. 1940 * Zero on success, negative errno on failure.
1884 */ 1941 */
1885int drm_mode_getcrtc(struct drm_device *dev, 1942int drm_mode_getcrtc(struct drm_device *dev,
1886 void *data, struct drm_file *file_priv) 1943 void *data, struct drm_file *file_priv)
1887{ 1944{
1888 struct drm_mode_crtc *crtc_resp = data; 1945 struct drm_mode_crtc *crtc_resp = data;
1889 struct drm_crtc *crtc; 1946 struct drm_crtc *crtc;
1890 int ret = 0;
1891 1947
1892 if (!drm_core_check_feature(dev, DRIVER_MODESET)) 1948 if (!drm_core_check_feature(dev, DRIVER_MODESET))
1893 return -EINVAL; 1949 return -EINVAL;
1894 1950
1895 drm_modeset_lock_all(dev);
1896
1897 crtc = drm_crtc_find(dev, crtc_resp->crtc_id); 1951 crtc = drm_crtc_find(dev, crtc_resp->crtc_id);
1898 if (!crtc) { 1952 if (!crtc)
1899 ret = -ENOENT; 1953 return -ENOENT;
1900 goto out;
1901 }
1902 1954
1955 drm_modeset_lock_crtc(crtc, crtc->primary);
1903 crtc_resp->x = crtc->x; 1956 crtc_resp->x = crtc->x;
1904 crtc_resp->y = crtc->y; 1957 crtc_resp->y = crtc->y;
1905 crtc_resp->gamma_size = crtc->gamma_size; 1958 crtc_resp->gamma_size = crtc->gamma_size;
@@ -1916,10 +1969,9 @@ int drm_mode_getcrtc(struct drm_device *dev,
1916 } else { 1969 } else {
1917 crtc_resp->mode_valid = 0; 1970 crtc_resp->mode_valid = 0;
1918 } 1971 }
1972 drm_modeset_unlock_crtc(crtc);
1919 1973
1920out: 1974 return 0;
1921 drm_modeset_unlock_all(dev);
1922 return ret;
1923} 1975}
1924 1976
1925static bool drm_mode_expose_to_userspace(const struct drm_display_mode *mode, 1977static bool drm_mode_expose_to_userspace(const struct drm_display_mode *mode,
@@ -1935,6 +1987,15 @@ static bool drm_mode_expose_to_userspace(const struct drm_display_mode *mode,
1935 return true; 1987 return true;
1936} 1988}
1937 1989
1990static struct drm_encoder *drm_connector_get_encoder(struct drm_connector *connector)
1991{
1992 /* For atomic drivers only state objects are synchronously updated and
1993 * protected by modeset locks, so check those first. */
1994 if (connector->state)
1995 return connector->state->best_encoder;
1996 return connector->encoder;
1997}
1998
1938/** 1999/**
1939 * drm_mode_getconnector - get connector configuration 2000 * drm_mode_getconnector - get connector configuration
1940 * @dev: drm device for the ioctl 2001 * @dev: drm device for the ioctl
@@ -1946,13 +2007,14 @@ static bool drm_mode_expose_to_userspace(const struct drm_display_mode *mode,
1946 * Called by the user via ioctl. 2007 * Called by the user via ioctl.
1947 * 2008 *
1948 * Returns: 2009 * Returns:
1949 * Zero on success, errno on failure. 2010 * Zero on success, negative errno on failure.
1950 */ 2011 */
1951int drm_mode_getconnector(struct drm_device *dev, void *data, 2012int drm_mode_getconnector(struct drm_device *dev, void *data,
1952 struct drm_file *file_priv) 2013 struct drm_file *file_priv)
1953{ 2014{
1954 struct drm_mode_get_connector *out_resp = data; 2015 struct drm_mode_get_connector *out_resp = data;
1955 struct drm_connector *connector; 2016 struct drm_connector *connector;
2017 struct drm_encoder *encoder;
1956 struct drm_display_mode *mode; 2018 struct drm_display_mode *mode;
1957 int mode_count = 0; 2019 int mode_count = 0;
1958 int props_count = 0; 2020 int props_count = 0;
@@ -2008,8 +2070,10 @@ int drm_mode_getconnector(struct drm_device *dev, void *data,
2008 out_resp->subpixel = connector->display_info.subpixel_order; 2070 out_resp->subpixel = connector->display_info.subpixel_order;
2009 out_resp->connection = connector->status; 2071 out_resp->connection = connector->status;
2010 drm_modeset_lock(&dev->mode_config.connection_mutex, NULL); 2072 drm_modeset_lock(&dev->mode_config.connection_mutex, NULL);
2011 if (connector->encoder) 2073
2012 out_resp->encoder_id = connector->encoder->base.id; 2074 encoder = drm_connector_get_encoder(connector);
2075 if (encoder)
2076 out_resp->encoder_id = encoder->base.id;
2013 else 2077 else
2014 out_resp->encoder_id = 0; 2078 out_resp->encoder_id = 0;
2015 drm_modeset_unlock(&dev->mode_config.connection_mutex); 2079 drm_modeset_unlock(&dev->mode_config.connection_mutex);
@@ -2079,6 +2143,33 @@ out:
2079 return ret; 2143 return ret;
2080} 2144}
2081 2145
2146static struct drm_crtc *drm_encoder_get_crtc(struct drm_encoder *encoder)
2147{
2148 struct drm_connector *connector;
2149 struct drm_device *dev = encoder->dev;
2150 bool uses_atomic = false;
2151
2152 /* For atomic drivers only state objects are synchronously updated and
2153 * protected by modeset locks, so check those first. */
2154 list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
2155 if (!connector->state)
2156 continue;
2157
2158 uses_atomic = true;
2159
2160 if (connector->state->best_encoder != encoder)
2161 continue;
2162
2163 return connector->state->crtc;
2164 }
2165
2166 /* Don't return stale data (e.g. pending async disable). */
2167 if (uses_atomic)
2168 return NULL;
2169
2170 return encoder->crtc;
2171}
2172
2082/** 2173/**
2083 * drm_mode_getencoder - get encoder configuration 2174 * drm_mode_getencoder - get encoder configuration
2084 * @dev: drm device for the ioctl 2175 * @dev: drm device for the ioctl
@@ -2090,37 +2181,38 @@ out:
2090 * Called by the user via ioctl. 2181 * Called by the user via ioctl.
2091 * 2182 *
2092 * Returns: 2183 * Returns:
2093 * Zero on success, errno on failure. 2184 * Zero on success, negative errno on failure.
2094 */ 2185 */
2095int drm_mode_getencoder(struct drm_device *dev, void *data, 2186int drm_mode_getencoder(struct drm_device *dev, void *data,
2096 struct drm_file *file_priv) 2187 struct drm_file *file_priv)
2097{ 2188{
2098 struct drm_mode_get_encoder *enc_resp = data; 2189 struct drm_mode_get_encoder *enc_resp = data;
2099 struct drm_encoder *encoder; 2190 struct drm_encoder *encoder;
2100 int ret = 0; 2191 struct drm_crtc *crtc;
2101 2192
2102 if (!drm_core_check_feature(dev, DRIVER_MODESET)) 2193 if (!drm_core_check_feature(dev, DRIVER_MODESET))
2103 return -EINVAL; 2194 return -EINVAL;
2104 2195
2105 drm_modeset_lock_all(dev);
2106 encoder = drm_encoder_find(dev, enc_resp->encoder_id); 2196 encoder = drm_encoder_find(dev, enc_resp->encoder_id);
2107 if (!encoder) { 2197 if (!encoder)
2108 ret = -ENOENT; 2198 return -ENOENT;
2109 goto out;
2110 }
2111 2199
2112 if (encoder->crtc) 2200 drm_modeset_lock(&dev->mode_config.connection_mutex, NULL);
2201 crtc = drm_encoder_get_crtc(encoder);
2202 if (crtc)
2203 enc_resp->crtc_id = crtc->base.id;
2204 else if (encoder->crtc)
2113 enc_resp->crtc_id = encoder->crtc->base.id; 2205 enc_resp->crtc_id = encoder->crtc->base.id;
2114 else 2206 else
2115 enc_resp->crtc_id = 0; 2207 enc_resp->crtc_id = 0;
2208 drm_modeset_unlock(&dev->mode_config.connection_mutex);
2209
2116 enc_resp->encoder_type = encoder->encoder_type; 2210 enc_resp->encoder_type = encoder->encoder_type;
2117 enc_resp->encoder_id = encoder->base.id; 2211 enc_resp->encoder_id = encoder->base.id;
2118 enc_resp->possible_crtcs = encoder->possible_crtcs; 2212 enc_resp->possible_crtcs = encoder->possible_crtcs;
2119 enc_resp->possible_clones = encoder->possible_clones; 2213 enc_resp->possible_clones = encoder->possible_clones;
2120 2214
2121out: 2215 return 0;
2122 drm_modeset_unlock_all(dev);
2123 return ret;
2124} 2216}
2125 2217
2126/** 2218/**
@@ -2134,7 +2226,7 @@ out:
2134 * Called by the user via ioctl. 2226 * Called by the user via ioctl.
2135 * 2227 *
2136 * Returns: 2228 * Returns:
2137 * Zero on success, errno on failure. 2229 * Zero on success, negative errno on failure.
2138 */ 2230 */
2139int drm_mode_getplane_res(struct drm_device *dev, void *data, 2231int drm_mode_getplane_res(struct drm_device *dev, void *data,
2140 struct drm_file *file_priv) 2232 struct drm_file *file_priv)
@@ -2143,13 +2235,12 @@ int drm_mode_getplane_res(struct drm_device *dev, void *data,
2143 struct drm_mode_config *config; 2235 struct drm_mode_config *config;
2144 struct drm_plane *plane; 2236 struct drm_plane *plane;
2145 uint32_t __user *plane_ptr; 2237 uint32_t __user *plane_ptr;
2146 int copied = 0, ret = 0; 2238 int copied = 0;
2147 unsigned num_planes; 2239 unsigned num_planes;
2148 2240
2149 if (!drm_core_check_feature(dev, DRIVER_MODESET)) 2241 if (!drm_core_check_feature(dev, DRIVER_MODESET))
2150 return -EINVAL; 2242 return -EINVAL;
2151 2243
2152 drm_modeset_lock_all(dev);
2153 config = &dev->mode_config; 2244 config = &dev->mode_config;
2154 2245
2155 if (file_priv->universal_planes) 2246 if (file_priv->universal_planes)
@@ -2165,6 +2256,7 @@ int drm_mode_getplane_res(struct drm_device *dev, void *data,
2165 (plane_resp->count_planes >= num_planes)) { 2256 (plane_resp->count_planes >= num_planes)) {
2166 plane_ptr = (uint32_t __user *)(unsigned long)plane_resp->plane_id_ptr; 2257 plane_ptr = (uint32_t __user *)(unsigned long)plane_resp->plane_id_ptr;
2167 2258
2259 /* Plane lists are invariant, no locking needed. */
2168 list_for_each_entry(plane, &config->plane_list, head) { 2260 list_for_each_entry(plane, &config->plane_list, head) {
2169 /* 2261 /*
2170 * Unless userspace set the 'universal planes' 2262 * Unless userspace set the 'universal planes'
@@ -2174,18 +2266,14 @@ int drm_mode_getplane_res(struct drm_device *dev, void *data,
2174 !file_priv->universal_planes) 2266 !file_priv->universal_planes)
2175 continue; 2267 continue;
2176 2268
2177 if (put_user(plane->base.id, plane_ptr + copied)) { 2269 if (put_user(plane->base.id, plane_ptr + copied))
2178 ret = -EFAULT; 2270 return -EFAULT;
2179 goto out;
2180 }
2181 copied++; 2271 copied++;
2182 } 2272 }
2183 } 2273 }
2184 plane_resp->count_planes = num_planes; 2274 plane_resp->count_planes = num_planes;
2185 2275
2186out: 2276 return 0;
2187 drm_modeset_unlock_all(dev);
2188 return ret;
2189} 2277}
2190 2278
2191/** 2279/**
@@ -2199,7 +2287,7 @@ out:
2199 * Called by the user via ioctl. 2287 * Called by the user via ioctl.
2200 * 2288 *
2201 * Returns: 2289 * Returns:
2202 * Zero on success, errno on failure. 2290 * Zero on success, negative errno on failure.
2203 */ 2291 */
2204int drm_mode_getplane(struct drm_device *dev, void *data, 2292int drm_mode_getplane(struct drm_device *dev, void *data,
2205 struct drm_file *file_priv) 2293 struct drm_file *file_priv)
@@ -2207,18 +2295,15 @@ int drm_mode_getplane(struct drm_device *dev, void *data,
2207 struct drm_mode_get_plane *plane_resp = data; 2295 struct drm_mode_get_plane *plane_resp = data;
2208 struct drm_plane *plane; 2296 struct drm_plane *plane;
2209 uint32_t __user *format_ptr; 2297 uint32_t __user *format_ptr;
2210 int ret = 0;
2211 2298
2212 if (!drm_core_check_feature(dev, DRIVER_MODESET)) 2299 if (!drm_core_check_feature(dev, DRIVER_MODESET))
2213 return -EINVAL; 2300 return -EINVAL;
2214 2301
2215 drm_modeset_lock_all(dev);
2216 plane = drm_plane_find(dev, plane_resp->plane_id); 2302 plane = drm_plane_find(dev, plane_resp->plane_id);
2217 if (!plane) { 2303 if (!plane)
2218 ret = -ENOENT; 2304 return -ENOENT;
2219 goto out;
2220 }
2221 2305
2306 drm_modeset_lock(&plane->mutex, NULL);
2222 if (plane->crtc) 2307 if (plane->crtc)
2223 plane_resp->crtc_id = plane->crtc->base.id; 2308 plane_resp->crtc_id = plane->crtc->base.id;
2224 else 2309 else
@@ -2228,6 +2313,7 @@ int drm_mode_getplane(struct drm_device *dev, void *data,
2228 plane_resp->fb_id = plane->fb->base.id; 2313 plane_resp->fb_id = plane->fb->base.id;
2229 else 2314 else
2230 plane_resp->fb_id = 0; 2315 plane_resp->fb_id = 0;
2316 drm_modeset_unlock(&plane->mutex);
2231 2317
2232 plane_resp->plane_id = plane->base.id; 2318 plane_resp->plane_id = plane->base.id;
2233 plane_resp->possible_crtcs = plane->possible_crtcs; 2319 plane_resp->possible_crtcs = plane->possible_crtcs;
@@ -2243,15 +2329,12 @@ int drm_mode_getplane(struct drm_device *dev, void *data,
2243 if (copy_to_user(format_ptr, 2329 if (copy_to_user(format_ptr,
2244 plane->format_types, 2330 plane->format_types,
2245 sizeof(uint32_t) * plane->format_count)) { 2331 sizeof(uint32_t) * plane->format_count)) {
2246 ret = -EFAULT; 2332 return -EFAULT;
2247 goto out;
2248 } 2333 }
2249 } 2334 }
2250 plane_resp->count_format_types = plane->format_count; 2335 plane_resp->count_format_types = plane->format_count;
2251 2336
2252out: 2337 return 0;
2253 drm_modeset_unlock_all(dev);
2254 return ret;
2255} 2338}
2256 2339
2257/* 2340/*
@@ -2274,7 +2357,7 @@ static int __setplane_internal(struct drm_plane *plane,
2274{ 2357{
2275 int ret = 0; 2358 int ret = 0;
2276 unsigned int fb_width, fb_height; 2359 unsigned int fb_width, fb_height;
2277 int i; 2360 unsigned int i;
2278 2361
2279 /* No fb means shut it down */ 2362 /* No fb means shut it down */
2280 if (!fb) { 2363 if (!fb) {
@@ -2378,13 +2461,12 @@ static int setplane_internal(struct drm_plane *plane,
2378 * valid crtc). 2461 * valid crtc).
2379 * 2462 *
2380 * Returns: 2463 * Returns:
2381 * Zero on success, errno on failure. 2464 * Zero on success, negative errno on failure.
2382 */ 2465 */
2383int drm_mode_setplane(struct drm_device *dev, void *data, 2466int drm_mode_setplane(struct drm_device *dev, void *data,
2384 struct drm_file *file_priv) 2467 struct drm_file *file_priv)
2385{ 2468{
2386 struct drm_mode_set_plane *plane_req = data; 2469 struct drm_mode_set_plane *plane_req = data;
2387 struct drm_mode_object *obj;
2388 struct drm_plane *plane; 2470 struct drm_plane *plane;
2389 struct drm_crtc *crtc = NULL; 2471 struct drm_crtc *crtc = NULL;
2390 struct drm_framebuffer *fb = NULL; 2472 struct drm_framebuffer *fb = NULL;
@@ -2407,14 +2489,12 @@ int drm_mode_setplane(struct drm_device *dev, void *data,
2407 * First, find the plane, crtc, and fb objects. If not available, 2489 * First, find the plane, crtc, and fb objects. If not available,
2408 * we don't bother to call the driver. 2490 * we don't bother to call the driver.
2409 */ 2491 */
2410 obj = drm_mode_object_find(dev, plane_req->plane_id, 2492 plane = drm_plane_find(dev, plane_req->plane_id);
2411 DRM_MODE_OBJECT_PLANE); 2493 if (!plane) {
2412 if (!obj) {
2413 DRM_DEBUG_KMS("Unknown plane ID %d\n", 2494 DRM_DEBUG_KMS("Unknown plane ID %d\n",
2414 plane_req->plane_id); 2495 plane_req->plane_id);
2415 return -ENOENT; 2496 return -ENOENT;
2416 } 2497 }
2417 plane = obj_to_plane(obj);
2418 2498
2419 if (plane_req->fb_id) { 2499 if (plane_req->fb_id) {
2420 fb = drm_framebuffer_lookup(dev, plane_req->fb_id); 2500 fb = drm_framebuffer_lookup(dev, plane_req->fb_id);
@@ -2424,14 +2504,12 @@ int drm_mode_setplane(struct drm_device *dev, void *data,
2424 return -ENOENT; 2504 return -ENOENT;
2425 } 2505 }
2426 2506
2427 obj = drm_mode_object_find(dev, plane_req->crtc_id, 2507 crtc = drm_crtc_find(dev, plane_req->crtc_id);
2428 DRM_MODE_OBJECT_CRTC); 2508 if (!crtc) {
2429 if (!obj) {
2430 DRM_DEBUG_KMS("Unknown crtc ID %d\n", 2509 DRM_DEBUG_KMS("Unknown crtc ID %d\n",
2431 plane_req->crtc_id); 2510 plane_req->crtc_id);
2432 return -ENOENT; 2511 return -ENOENT;
2433 } 2512 }
2434 crtc = obj_to_crtc(obj);
2435 } 2513 }
2436 2514
2437 /* 2515 /*
@@ -2453,7 +2531,7 @@ int drm_mode_setplane(struct drm_device *dev, void *data,
2453 * interface. The only thing it adds is correct refcounting dance. 2531 * interface. The only thing it adds is correct refcounting dance.
2454 * 2532 *
2455 * Returns: 2533 * Returns:
2456 * Zero on success, errno on failure. 2534 * Zero on success, negative errno on failure.
2457 */ 2535 */
2458int drm_mode_set_config_internal(struct drm_mode_set *set) 2536int drm_mode_set_config_internal(struct drm_mode_set *set)
2459{ 2537{
@@ -2546,7 +2624,7 @@ EXPORT_SYMBOL(drm_crtc_check_viewport);
2546 * Called by the user via ioctl. 2624 * Called by the user via ioctl.
2547 * 2625 *
2548 * Returns: 2626 * Returns:
2549 * Zero on success, errno on failure. 2627 * Zero on success, negative errno on failure.
2550 */ 2628 */
2551int drm_mode_setcrtc(struct drm_device *dev, void *data, 2629int drm_mode_setcrtc(struct drm_device *dev, void *data,
2552 struct drm_file *file_priv) 2630 struct drm_file *file_priv)
@@ -2709,7 +2787,7 @@ out:
2709 * userspace wants to make use of these capabilities. 2787 * userspace wants to make use of these capabilities.
2710 * 2788 *
2711 * Returns: 2789 * Returns:
2712 * Zero on success, errno on failure. 2790 * Zero on success, negative errno on failure.
2713 */ 2791 */
2714static int drm_mode_cursor_universal(struct drm_crtc *crtc, 2792static int drm_mode_cursor_universal(struct drm_crtc *crtc,
2715 struct drm_mode_cursor2 *req, 2793 struct drm_mode_cursor2 *req,
@@ -2810,7 +2888,7 @@ static int drm_mode_cursor_common(struct drm_device *dev,
2810 * If this crtc has a universal cursor plane, call that plane's update 2888 * If this crtc has a universal cursor plane, call that plane's update
2811 * handler rather than using legacy cursor handlers. 2889 * handler rather than using legacy cursor handlers.
2812 */ 2890 */
2813 drm_modeset_lock_crtc(crtc); 2891 drm_modeset_lock_crtc(crtc, crtc->cursor);
2814 if (crtc->cursor) { 2892 if (crtc->cursor) {
2815 ret = drm_mode_cursor_universal(crtc, req, file_priv); 2893 ret = drm_mode_cursor_universal(crtc, req, file_priv);
2816 goto out; 2894 goto out;
@@ -2857,7 +2935,7 @@ out:
2857 * Called by the user via ioctl. 2935 * Called by the user via ioctl.
2858 * 2936 *
2859 * Returns: 2937 * Returns:
2860 * Zero on success, errno on failure. 2938 * Zero on success, negative errno on failure.
2861 */ 2939 */
2862int drm_mode_cursor_ioctl(struct drm_device *dev, 2940int drm_mode_cursor_ioctl(struct drm_device *dev,
2863 void *data, struct drm_file *file_priv) 2941 void *data, struct drm_file *file_priv)
@@ -2884,7 +2962,7 @@ int drm_mode_cursor_ioctl(struct drm_device *dev,
2884 * Called by the user via ioctl. 2962 * Called by the user via ioctl.
2885 * 2963 *
2886 * Returns: 2964 * Returns:
2887 * Zero on success, errno on failure. 2965 * Zero on success, negative errno on failure.
2888 */ 2966 */
2889int drm_mode_cursor2_ioctl(struct drm_device *dev, 2967int drm_mode_cursor2_ioctl(struct drm_device *dev,
2890 void *data, struct drm_file *file_priv) 2968 void *data, struct drm_file *file_priv)
@@ -2943,23 +3021,21 @@ EXPORT_SYMBOL(drm_mode_legacy_fb_format);
2943 * @file_priv: drm file for the ioctl call 3021 * @file_priv: drm file for the ioctl call
2944 * 3022 *
2945 * Add a new FB to the specified CRTC, given a user request. This is the 3023 * Add a new FB to the specified CRTC, given a user request. This is the
2946 * original addfb ioclt which only supported RGB formats. 3024 * original addfb ioctl which only supported RGB formats.
2947 * 3025 *
2948 * Called by the user via ioctl. 3026 * Called by the user via ioctl.
2949 * 3027 *
2950 * Returns: 3028 * Returns:
2951 * Zero on success, errno on failure. 3029 * Zero on success, negative errno on failure.
2952 */ 3030 */
2953int drm_mode_addfb(struct drm_device *dev, 3031int drm_mode_addfb(struct drm_device *dev,
2954 void *data, struct drm_file *file_priv) 3032 void *data, struct drm_file *file_priv)
2955{ 3033{
2956 struct drm_mode_fb_cmd *or = data; 3034 struct drm_mode_fb_cmd *or = data;
2957 struct drm_mode_fb_cmd2 r = {}; 3035 struct drm_mode_fb_cmd2 r = {};
2958 struct drm_mode_config *config = &dev->mode_config; 3036 int ret;
2959 struct drm_framebuffer *fb;
2960 int ret = 0;
2961 3037
2962 /* Use new struct with format internally */ 3038 /* convert to new format and call new ioctl */
2963 r.fb_id = or->fb_id; 3039 r.fb_id = or->fb_id;
2964 r.width = or->width; 3040 r.width = or->width;
2965 r.height = or->height; 3041 r.height = or->height;
@@ -2967,28 +3043,13 @@ int drm_mode_addfb(struct drm_device *dev,
2967 r.pixel_format = drm_mode_legacy_fb_format(or->bpp, or->depth); 3043 r.pixel_format = drm_mode_legacy_fb_format(or->bpp, or->depth);
2968 r.handles[0] = or->handle; 3044 r.handles[0] = or->handle;
2969 3045
2970 if (!drm_core_check_feature(dev, DRIVER_MODESET)) 3046 ret = drm_mode_addfb2(dev, &r, file_priv);
2971 return -EINVAL; 3047 if (ret)
2972 3048 return ret;
2973 if ((config->min_width > r.width) || (r.width > config->max_width))
2974 return -EINVAL;
2975
2976 if ((config->min_height > r.height) || (r.height > config->max_height))
2977 return -EINVAL;
2978 3049
2979 fb = dev->mode_config.funcs->fb_create(dev, file_priv, &r); 3050 or->fb_id = r.fb_id;
2980 if (IS_ERR(fb)) {
2981 DRM_DEBUG_KMS("could not create framebuffer\n");
2982 return PTR_ERR(fb);
2983 }
2984 3051
2985 mutex_lock(&file_priv->fbs_lock); 3052 return 0;
2986 or->fb_id = fb->base.id;
2987 list_add(&fb->filp_head, &file_priv->fbs);
2988 DRM_DEBUG_KMS("[FB:%d]\n", fb->base.id);
2989 mutex_unlock(&file_priv->fbs_lock);
2990
2991 return ret;
2992} 3053}
2993 3054
2994static int format_check(const struct drm_mode_fb_cmd2 *r) 3055static int format_check(const struct drm_mode_fb_cmd2 *r)
@@ -3080,7 +3141,7 @@ static int framebuffer_check(const struct drm_mode_fb_cmd2 *r)
3080 num_planes = drm_format_num_planes(r->pixel_format); 3141 num_planes = drm_format_num_planes(r->pixel_format);
3081 3142
3082 if (r->width == 0 || r->width % hsub) { 3143 if (r->width == 0 || r->width % hsub) {
3083 DRM_DEBUG_KMS("bad framebuffer width %u\n", r->height); 3144 DRM_DEBUG_KMS("bad framebuffer width %u\n", r->width);
3084 return -EINVAL; 3145 return -EINVAL;
3085 } 3146 }
3086 3147
@@ -3170,7 +3231,7 @@ static struct drm_framebuffer *add_framebuffer_internal(struct drm_device *dev,
3170 * Called by the user via ioctl. 3231 * Called by the user via ioctl.
3171 * 3232 *
3172 * Returns: 3233 * Returns:
3173 * Zero on success, errno on failure. 3234 * Zero on success, negative errno on failure.
3174 */ 3235 */
3175int drm_mode_addfb2(struct drm_device *dev, 3236int drm_mode_addfb2(struct drm_device *dev,
3176 void *data, struct drm_file *file_priv) 3237 void *data, struct drm_file *file_priv)
@@ -3198,7 +3259,7 @@ int drm_mode_addfb2(struct drm_device *dev,
3198 * Called by the user via ioctl. 3259 * Called by the user via ioctl.
3199 * 3260 *
3200 * Returns: 3261 * Returns:
3201 * Zero on success, errno on failure. 3262 * Zero on success, negative errno on failure.
3202 */ 3263 */
3203int drm_mode_rmfb(struct drm_device *dev, 3264int drm_mode_rmfb(struct drm_device *dev,
3204 void *data, struct drm_file *file_priv) 3265 void *data, struct drm_file *file_priv)
@@ -3252,7 +3313,7 @@ fail_lookup:
3252 * Called by the user via ioctl. 3313 * Called by the user via ioctl.
3253 * 3314 *
3254 * Returns: 3315 * Returns:
3255 * Zero on success, errno on failure. 3316 * Zero on success, negative errno on failure.
3256 */ 3317 */
3257int drm_mode_getfb(struct drm_device *dev, 3318int drm_mode_getfb(struct drm_device *dev,
3258 void *data, struct drm_file *file_priv) 3319 void *data, struct drm_file *file_priv)
@@ -3313,7 +3374,7 @@ int drm_mode_getfb(struct drm_device *dev,
3313 * Called by the user via ioctl. 3374 * Called by the user via ioctl.
3314 * 3375 *
3315 * Returns: 3376 * Returns:
3316 * Zero on success, errno on failure. 3377 * Zero on success, negative errno on failure.
3317 */ 3378 */
3318int drm_mode_dirtyfb_ioctl(struct drm_device *dev, 3379int drm_mode_dirtyfb_ioctl(struct drm_device *dev,
3319 void *data, struct drm_file *file_priv) 3380 void *data, struct drm_file *file_priv)
@@ -3393,7 +3454,7 @@ out_err1:
3393 * Called by the user via ioctl. 3454 * Called by the user via ioctl.
3394 * 3455 *
3395 * Returns: 3456 * Returns:
3396 * Zero on success, errno on failure. 3457 * Zero on success, negative errno on failure.
3397 */ 3458 */
3398void drm_fb_release(struct drm_file *priv) 3459void drm_fb_release(struct drm_file *priv)
3399{ 3460{
@@ -3402,7 +3463,7 @@ void drm_fb_release(struct drm_file *priv)
3402 3463
3403 /* 3464 /*
3404 * When the file gets released that means no one else can access the fb 3465 * When the file gets released that means no one else can access the fb
3405 * list any more, so no need to grab fpriv->fbs_lock. And we need to to 3466 * list any more, so no need to grab fpriv->fbs_lock. And we need to
3406 * avoid upsetting lockdep since the universal cursor code adds a 3467 * avoid upsetting lockdep since the universal cursor code adds a
3407 * framebuffer while holding mutex locks. 3468 * framebuffer while holding mutex locks.
3408 * 3469 *
@@ -3435,6 +3496,10 @@ void drm_fb_release(struct drm_file *priv)
3435 * object with drm_object_attach_property. The returned property object must be 3496 * object with drm_object_attach_property. The returned property object must be
3436 * freed with drm_property_destroy. 3497 * freed with drm_property_destroy.
3437 * 3498 *
3499 * Note that the DRM core keeps a per-device list of properties and that, if
3500 * drm_mode_config_cleanup() is called, it will destroy all properties created
3501 * by the driver.
3502 *
3438 * Returns: 3503 * Returns:
3439 * A pointer to the newly created property on success, NULL on failure. 3504 * A pointer to the newly created property on success, NULL on failure.
3440 */ 3505 */
@@ -3462,7 +3527,7 @@ struct drm_property *drm_property_create(struct drm_device *dev, int flags,
3462 3527
3463 property->flags = flags; 3528 property->flags = flags;
3464 property->num_values = num_values; 3529 property->num_values = num_values;
3465 INIT_LIST_HEAD(&property->enum_blob_list); 3530 INIT_LIST_HEAD(&property->enum_list);
3466 3531
3467 if (name) { 3532 if (name) {
3468 strncpy(property->name, name, DRM_PROP_NAME_LEN); 3533 strncpy(property->name, name, DRM_PROP_NAME_LEN);
@@ -3611,7 +3676,7 @@ static struct drm_property *property_create_range(struct drm_device *dev,
3611 * object with drm_object_attach_property. The returned property object must be 3676 * object with drm_object_attach_property. The returned property object must be
3612 * freed with drm_property_destroy. 3677 * freed with drm_property_destroy.
3613 * 3678 *
3614 * Userspace is allowed to set any interger value in the (min, max) range 3679 * Userspace is allowed to set any integer value in the (min, max) range
3615 * inclusive. 3680 * inclusive.
3616 * 3681 *
3617 * Returns: 3682 * Returns:
@@ -3684,8 +3749,8 @@ int drm_property_add_enum(struct drm_property *property, int index,
3684 (value > 63)) 3749 (value > 63))
3685 return -EINVAL; 3750 return -EINVAL;
3686 3751
3687 if (!list_empty(&property->enum_blob_list)) { 3752 if (!list_empty(&property->enum_list)) {
3688 list_for_each_entry(prop_enum, &property->enum_blob_list, head) { 3753 list_for_each_entry(prop_enum, &property->enum_list, head) {
3689 if (prop_enum->value == value) { 3754 if (prop_enum->value == value) {
3690 strncpy(prop_enum->name, name, DRM_PROP_NAME_LEN); 3755 strncpy(prop_enum->name, name, DRM_PROP_NAME_LEN);
3691 prop_enum->name[DRM_PROP_NAME_LEN-1] = '\0'; 3756 prop_enum->name[DRM_PROP_NAME_LEN-1] = '\0';
@@ -3703,7 +3768,7 @@ int drm_property_add_enum(struct drm_property *property, int index,
3703 prop_enum->value = value; 3768 prop_enum->value = value;
3704 3769
3705 property->values[index] = value; 3770 property->values[index] = value;
3706 list_add_tail(&prop_enum->head, &property->enum_blob_list); 3771 list_add_tail(&prop_enum->head, &property->enum_list);
3707 return 0; 3772 return 0;
3708} 3773}
3709EXPORT_SYMBOL(drm_property_add_enum); 3774EXPORT_SYMBOL(drm_property_add_enum);
@@ -3720,7 +3785,7 @@ void drm_property_destroy(struct drm_device *dev, struct drm_property *property)
3720{ 3785{
3721 struct drm_property_enum *prop_enum, *pt; 3786 struct drm_property_enum *prop_enum, *pt;
3722 3787
3723 list_for_each_entry_safe(prop_enum, pt, &property->enum_blob_list, head) { 3788 list_for_each_entry_safe(prop_enum, pt, &property->enum_list, head) {
3724 list_del(&prop_enum->head); 3789 list_del(&prop_enum->head);
3725 kfree(prop_enum); 3790 kfree(prop_enum);
3726 } 3791 }
@@ -3823,17 +3888,20 @@ int drm_object_property_get_value(struct drm_mode_object *obj,
3823EXPORT_SYMBOL(drm_object_property_get_value); 3888EXPORT_SYMBOL(drm_object_property_get_value);
3824 3889
3825/** 3890/**
3826 * drm_mode_getproperty_ioctl - get the current value of a connector's property 3891 * drm_mode_getproperty_ioctl - get the property metadata
3827 * @dev: DRM device 3892 * @dev: DRM device
3828 * @data: ioctl data 3893 * @data: ioctl data
3829 * @file_priv: DRM file info 3894 * @file_priv: DRM file info
3830 * 3895 *
3831 * This function retrieves the current value for an connectors's property. 3896 * This function retrieves the metadata for a given property, like the different
3897 * possible values for an enum property or the limits for a range property.
3898 *
3899 * Blob properties are special
3832 * 3900 *
3833 * Called by the user via ioctl. 3901 * Called by the user via ioctl.
3834 * 3902 *
3835 * Returns: 3903 * Returns:
3836 * Zero on success, errno on failure. 3904 * Zero on success, negative errno on failure.
3837 */ 3905 */
3838int drm_mode_getproperty_ioctl(struct drm_device *dev, 3906int drm_mode_getproperty_ioctl(struct drm_device *dev,
3839 void *data, struct drm_file *file_priv) 3907 void *data, struct drm_file *file_priv)
@@ -3841,16 +3909,12 @@ int drm_mode_getproperty_ioctl(struct drm_device *dev,
3841 struct drm_mode_get_property *out_resp = data; 3909 struct drm_mode_get_property *out_resp = data;
3842 struct drm_property *property; 3910 struct drm_property *property;
3843 int enum_count = 0; 3911 int enum_count = 0;
3844 int blob_count = 0;
3845 int value_count = 0; 3912 int value_count = 0;
3846 int ret = 0, i; 3913 int ret = 0, i;
3847 int copied; 3914 int copied;
3848 struct drm_property_enum *prop_enum; 3915 struct drm_property_enum *prop_enum;
3849 struct drm_mode_property_enum __user *enum_ptr; 3916 struct drm_mode_property_enum __user *enum_ptr;
3850 struct drm_property_blob *prop_blob;
3851 uint32_t __user *blob_id_ptr;
3852 uint64_t __user *values_ptr; 3917 uint64_t __user *values_ptr;
3853 uint32_t __user *blob_length_ptr;
3854 3918
3855 if (!drm_core_check_feature(dev, DRIVER_MODESET)) 3919 if (!drm_core_check_feature(dev, DRIVER_MODESET))
3856 return -EINVAL; 3920 return -EINVAL;
@@ -3864,11 +3928,8 @@ int drm_mode_getproperty_ioctl(struct drm_device *dev,
3864 3928
3865 if (drm_property_type_is(property, DRM_MODE_PROP_ENUM) || 3929 if (drm_property_type_is(property, DRM_MODE_PROP_ENUM) ||
3866 drm_property_type_is(property, DRM_MODE_PROP_BITMASK)) { 3930 drm_property_type_is(property, DRM_MODE_PROP_BITMASK)) {
3867 list_for_each_entry(prop_enum, &property->enum_blob_list, head) 3931 list_for_each_entry(prop_enum, &property->enum_list, head)
3868 enum_count++; 3932 enum_count++;
3869 } else if (drm_property_type_is(property, DRM_MODE_PROP_BLOB)) {
3870 list_for_each_entry(prop_blob, &property->enum_blob_list, head)
3871 blob_count++;
3872 } 3933 }
3873 3934
3874 value_count = property->num_values; 3935 value_count = property->num_values;
@@ -3893,7 +3954,7 @@ int drm_mode_getproperty_ioctl(struct drm_device *dev,
3893 if ((out_resp->count_enum_blobs >= enum_count) && enum_count) { 3954 if ((out_resp->count_enum_blobs >= enum_count) && enum_count) {
3894 copied = 0; 3955 copied = 0;
3895 enum_ptr = (struct drm_mode_property_enum __user *)(unsigned long)out_resp->enum_blob_ptr; 3956 enum_ptr = (struct drm_mode_property_enum __user *)(unsigned long)out_resp->enum_blob_ptr;
3896 list_for_each_entry(prop_enum, &property->enum_blob_list, head) { 3957 list_for_each_entry(prop_enum, &property->enum_list, head) {
3897 3958
3898 if (copy_to_user(&enum_ptr[copied].value, &prop_enum->value, sizeof(uint64_t))) { 3959 if (copy_to_user(&enum_ptr[copied].value, &prop_enum->value, sizeof(uint64_t))) {
3899 ret = -EFAULT; 3960 ret = -EFAULT;
@@ -3911,35 +3972,24 @@ int drm_mode_getproperty_ioctl(struct drm_device *dev,
3911 out_resp->count_enum_blobs = enum_count; 3972 out_resp->count_enum_blobs = enum_count;
3912 } 3973 }
3913 3974
3914 if (drm_property_type_is(property, DRM_MODE_PROP_BLOB)) { 3975 /*
3915 if ((out_resp->count_enum_blobs >= blob_count) && blob_count) { 3976 * NOTE: The idea seems to have been to use this to read all the blob
3916 copied = 0; 3977 * property values. But nothing ever added them to the corresponding
3917 blob_id_ptr = (uint32_t __user *)(unsigned long)out_resp->enum_blob_ptr; 3978 * list, userspace always used the special-purpose get_blob ioctl to
3918 blob_length_ptr = (uint32_t __user *)(unsigned long)out_resp->values_ptr; 3979 * read the value for a blob property. It also doesn't make a lot of
3919 3980 * sense to return values here when everything else is just metadata for
3920 list_for_each_entry(prop_blob, &property->enum_blob_list, head) { 3981 * the property itself.
3921 if (put_user(prop_blob->base.id, blob_id_ptr + copied)) { 3982 */
3922 ret = -EFAULT; 3983 if (drm_property_type_is(property, DRM_MODE_PROP_BLOB))
3923 goto done; 3984 out_resp->count_enum_blobs = 0;
3924 }
3925
3926 if (put_user(prop_blob->length, blob_length_ptr + copied)) {
3927 ret = -EFAULT;
3928 goto done;
3929 }
3930
3931 copied++;
3932 }
3933 }
3934 out_resp->count_enum_blobs = blob_count;
3935 }
3936done: 3985done:
3937 drm_modeset_unlock_all(dev); 3986 drm_modeset_unlock_all(dev);
3938 return ret; 3987 return ret;
3939} 3988}
3940 3989
3941static struct drm_property_blob *drm_property_create_blob(struct drm_device *dev, int length, 3990static struct drm_property_blob *
3942 void *data) 3991drm_property_create_blob(struct drm_device *dev, size_t length,
3992 const void *data)
3943{ 3993{
3944 struct drm_property_blob *blob; 3994 struct drm_property_blob *blob;
3945 int ret; 3995 int ret;
@@ -3985,7 +4035,7 @@ static void drm_property_destroy_blob(struct drm_device *dev,
3985 * Called by the user via ioctl. 4035 * Called by the user via ioctl.
3986 * 4036 *
3987 * Returns: 4037 * Returns:
3988 * Zero on success, errno on failure. 4038 * Zero on success, negative errno on failure.
3989 */ 4039 */
3990int drm_mode_getblob_ioctl(struct drm_device *dev, 4040int drm_mode_getblob_ioctl(struct drm_device *dev,
3991 void *data, struct drm_file *file_priv) 4041 void *data, struct drm_file *file_priv)
@@ -4019,12 +4069,25 @@ done:
4019 return ret; 4069 return ret;
4020} 4070}
4021 4071
4072/**
4073 * drm_mode_connector_set_path_property - set tile property on connector
4074 * @connector: connector to set property on.
4075 * @path: path to use for property.
4076 *
4077 * This creates a property to expose to userspace to specify a
4078 * connector path. This is mainly used for DisplayPort MST where
4079 * connectors have a topology and we want to allow userspace to give
4080 * them more meaningful names.
4081 *
4082 * Returns:
4083 * Zero on success, negative errno on failure.
4084 */
4022int drm_mode_connector_set_path_property(struct drm_connector *connector, 4085int drm_mode_connector_set_path_property(struct drm_connector *connector,
4023 char *path) 4086 const char *path)
4024{ 4087{
4025 struct drm_device *dev = connector->dev; 4088 struct drm_device *dev = connector->dev;
4026 int ret, size; 4089 size_t size = strlen(path) + 1;
4027 size = strlen(path) + 1; 4090 int ret;
4028 4091
4029 connector->path_blob_ptr = drm_property_create_blob(connector->dev, 4092 connector->path_blob_ptr = drm_property_create_blob(connector->dev,
4030 size, path); 4093 size, path);
@@ -4039,6 +4102,52 @@ int drm_mode_connector_set_path_property(struct drm_connector *connector,
4039EXPORT_SYMBOL(drm_mode_connector_set_path_property); 4102EXPORT_SYMBOL(drm_mode_connector_set_path_property);
4040 4103
4041/** 4104/**
4105 * drm_mode_connector_set_tile_property - set tile property on connector
4106 * @connector: connector to set property on.
4107 *
4108 * This looks up the tile information for a connector, and creates a
4109 * property for userspace to parse if it exists. The property is of
4110 * the form of 8 integers using ':' as a separator.
4111 *
4112 * Returns:
4113 * Zero on success, errno on failure.
4114 */
4115int drm_mode_connector_set_tile_property(struct drm_connector *connector)
4116{
4117 struct drm_device *dev = connector->dev;
4118 int ret, size;
4119 char tile[256];
4120
4121 if (connector->tile_blob_ptr)
4122 drm_property_destroy_blob(dev, connector->tile_blob_ptr);
4123
4124 if (!connector->has_tile) {
4125 connector->tile_blob_ptr = NULL;
4126 ret = drm_object_property_set_value(&connector->base,
4127 dev->mode_config.tile_property, 0);
4128 return ret;
4129 }
4130
4131 snprintf(tile, 256, "%d:%d:%d:%d:%d:%d:%d:%d",
4132 connector->tile_group->id, connector->tile_is_single_monitor,
4133 connector->num_h_tile, connector->num_v_tile,
4134 connector->tile_h_loc, connector->tile_v_loc,
4135 connector->tile_h_size, connector->tile_v_size);
4136 size = strlen(tile) + 1;
4137
4138 connector->tile_blob_ptr = drm_property_create_blob(connector->dev,
4139 size, tile);
4140 if (!connector->tile_blob_ptr)
4141 return -EINVAL;
4142
4143 ret = drm_object_property_set_value(&connector->base,
4144 dev->mode_config.tile_property,
4145 connector->tile_blob_ptr->base.id);
4146 return ret;
4147}
4148EXPORT_SYMBOL(drm_mode_connector_set_tile_property);
4149
4150/**
4042 * drm_mode_connector_update_edid_property - update the edid property of a connector 4151 * drm_mode_connector_update_edid_property - update the edid property of a connector
4043 * @connector: drm connector 4152 * @connector: drm connector
4044 * @edid: new value of the edid property 4153 * @edid: new value of the edid property
@@ -4047,13 +4156,14 @@ EXPORT_SYMBOL(drm_mode_connector_set_path_property);
4047 * connector's edid property. 4156 * connector's edid property.
4048 * 4157 *
4049 * Returns: 4158 * Returns:
4050 * Zero on success, errno on failure. 4159 * Zero on success, negative errno on failure.
4051 */ 4160 */
4052int drm_mode_connector_update_edid_property(struct drm_connector *connector, 4161int drm_mode_connector_update_edid_property(struct drm_connector *connector,
4053 struct edid *edid) 4162 const struct edid *edid)
4054{ 4163{
4055 struct drm_device *dev = connector->dev; 4164 struct drm_device *dev = connector->dev;
4056 int ret, size; 4165 size_t size;
4166 int ret;
4057 4167
4058 /* ignore requests to set edid when overridden */ 4168 /* ignore requests to set edid when overridden */
4059 if (connector->override_edid) 4169 if (connector->override_edid)
@@ -4143,7 +4253,7 @@ static bool drm_property_change_is_valid(struct drm_property *property,
4143 * Called by the user via ioctl. 4253 * Called by the user via ioctl.
4144 * 4254 *
4145 * Returns: 4255 * Returns:
4146 * Zero on success, errno on failure. 4256 * Zero on success, negative errno on failure.
4147 */ 4257 */
4148int drm_mode_connector_property_set_ioctl(struct drm_device *dev, 4258int drm_mode_connector_property_set_ioctl(struct drm_device *dev,
4149 void *data, struct drm_file *file_priv) 4259 void *data, struct drm_file *file_priv)
@@ -4226,7 +4336,7 @@ int drm_mode_plane_set_obj_prop(struct drm_plane *plane,
4226EXPORT_SYMBOL(drm_mode_plane_set_obj_prop); 4336EXPORT_SYMBOL(drm_mode_plane_set_obj_prop);
4227 4337
4228/** 4338/**
4229 * drm_mode_getproperty_ioctl - get the current value of a object's property 4339 * drm_mode_obj_get_properties_ioctl - get the current value of a object's property
4230 * @dev: DRM device 4340 * @dev: DRM device
4231 * @data: ioctl data 4341 * @data: ioctl data
4232 * @file_priv: DRM file info 4342 * @file_priv: DRM file info
@@ -4238,7 +4348,7 @@ EXPORT_SYMBOL(drm_mode_plane_set_obj_prop);
4238 * Called by the user via ioctl. 4348 * Called by the user via ioctl.
4239 * 4349 *
4240 * Returns: 4350 * Returns:
4241 * Zero on success, errno on failure. 4351 * Zero on success, negative errno on failure.
4242 */ 4352 */
4243int drm_mode_obj_get_properties_ioctl(struct drm_device *dev, void *data, 4353int drm_mode_obj_get_properties_ioctl(struct drm_device *dev, void *data,
4244 struct drm_file *file_priv) 4354 struct drm_file *file_priv)
@@ -4310,7 +4420,7 @@ out:
4310 * Called by the user via ioctl. 4420 * Called by the user via ioctl.
4311 * 4421 *
4312 * Returns: 4422 * Returns:
4313 * Zero on success, errno on failure. 4423 * Zero on success, negative errno on failure.
4314 */ 4424 */
4315int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data, 4425int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
4316 struct drm_file *file_priv) 4426 struct drm_file *file_priv)
@@ -4382,7 +4492,7 @@ out:
4382 * possible_clones and possible_crtcs bitmasks. 4492 * possible_clones and possible_crtcs bitmasks.
4383 * 4493 *
4384 * Returns: 4494 * Returns:
4385 * Zero on success, errno on failure. 4495 * Zero on success, negative errno on failure.
4386 */ 4496 */
4387int drm_mode_connector_attach_encoder(struct drm_connector *connector, 4497int drm_mode_connector_attach_encoder(struct drm_connector *connector,
4388 struct drm_encoder *encoder) 4498 struct drm_encoder *encoder)
@@ -4409,7 +4519,7 @@ EXPORT_SYMBOL(drm_mode_connector_attach_encoder);
4409 * fixed gamma table size. 4519 * fixed gamma table size.
4410 * 4520 *
4411 * Returns: 4521 * Returns:
4412 * Zero on success, errno on failure. 4522 * Zero on success, negative errno on failure.
4413 */ 4523 */
4414int drm_mode_crtc_set_gamma_size(struct drm_crtc *crtc, 4524int drm_mode_crtc_set_gamma_size(struct drm_crtc *crtc,
4415 int gamma_size) 4525 int gamma_size)
@@ -4438,7 +4548,7 @@ EXPORT_SYMBOL(drm_mode_crtc_set_gamma_size);
4438 * Called by the user via ioctl. 4548 * Called by the user via ioctl.
4439 * 4549 *
4440 * Returns: 4550 * Returns:
4441 * Zero on success, errno on failure. 4551 * Zero on success, negative errno on failure.
4442 */ 4552 */
4443int drm_mode_gamma_set_ioctl(struct drm_device *dev, 4553int drm_mode_gamma_set_ioctl(struct drm_device *dev,
4444 void *data, struct drm_file *file_priv) 4554 void *data, struct drm_file *file_priv)
@@ -4510,7 +4620,7 @@ out:
4510 * Called by the user via ioctl. 4620 * Called by the user via ioctl.
4511 * 4621 *
4512 * Returns: 4622 * Returns:
4513 * Zero on success, errno on failure. 4623 * Zero on success, negative errno on failure.
4514 */ 4624 */
4515int drm_mode_gamma_get_ioctl(struct drm_device *dev, 4625int drm_mode_gamma_get_ioctl(struct drm_device *dev,
4516 void *data, struct drm_file *file_priv) 4626 void *data, struct drm_file *file_priv)
@@ -4576,7 +4686,7 @@ out:
4576 * Called by the user via ioctl. 4686 * Called by the user via ioctl.
4577 * 4687 *
4578 * Returns: 4688 * Returns:
4579 * Zero on success, errno on failure. 4689 * Zero on success, negative errno on failure.
4580 */ 4690 */
4581int drm_mode_page_flip_ioctl(struct drm_device *dev, 4691int drm_mode_page_flip_ioctl(struct drm_device *dev,
4582 void *data, struct drm_file *file_priv) 4692 void *data, struct drm_file *file_priv)
@@ -4599,7 +4709,7 @@ int drm_mode_page_flip_ioctl(struct drm_device *dev,
4599 if (!crtc) 4709 if (!crtc)
4600 return -ENOENT; 4710 return -ENOENT;
4601 4711
4602 drm_modeset_lock_crtc(crtc); 4712 drm_modeset_lock_crtc(crtc, crtc->primary);
4603 if (crtc->primary->fb == NULL) { 4713 if (crtc->primary->fb == NULL) {
4604 /* The framebuffer is currently unbound, presumably 4714 /* The framebuffer is currently unbound, presumably
4605 * due to a hotplug event, that userspace has not 4715 * due to a hotplug event, that userspace has not
@@ -4742,7 +4852,7 @@ EXPORT_SYMBOL(drm_mode_config_reset);
4742 * Called by the user via ioctl. 4852 * Called by the user via ioctl.
4743 * 4853 *
4744 * Returns: 4854 * Returns:
4745 * Zero on success, errno on failure. 4855 * Zero on success, negative errno on failure.
4746 */ 4856 */
4747int drm_mode_create_dumb_ioctl(struct drm_device *dev, 4857int drm_mode_create_dumb_ioctl(struct drm_device *dev,
4748 void *data, struct drm_file *file_priv) 4858 void *data, struct drm_file *file_priv)
@@ -4769,6 +4879,16 @@ int drm_mode_create_dumb_ioctl(struct drm_device *dev,
4769 if (PAGE_ALIGN(size) == 0) 4879 if (PAGE_ALIGN(size) == 0)
4770 return -EINVAL; 4880 return -EINVAL;
4771 4881
4882 /*
4883 * handle, pitch and size are output parameters. Zero them out to
4884 * prevent drivers from accidentally using uninitialized data. Since
4885 * not all existing userspace is clearing these fields properly we
4886 * cannot reject IOCTL with garbage in them.
4887 */
4888 args->handle = 0;
4889 args->pitch = 0;
4890 args->size = 0;
4891
4772 return dev->driver->dumb_create(file_priv, dev, args); 4892 return dev->driver->dumb_create(file_priv, dev, args);
4773} 4893}
4774 4894
@@ -4784,7 +4904,7 @@ int drm_mode_create_dumb_ioctl(struct drm_device *dev,
4784 * Called by the user via ioctl. 4904 * Called by the user via ioctl.
4785 * 4905 *
4786 * Returns: 4906 * Returns:
4787 * Zero on success, errno on failure. 4907 * Zero on success, negative errno on failure.
4788 */ 4908 */
4789int drm_mode_mmap_dumb_ioctl(struct drm_device *dev, 4909int drm_mode_mmap_dumb_ioctl(struct drm_device *dev,
4790 void *data, struct drm_file *file_priv) 4910 void *data, struct drm_file *file_priv)
@@ -4811,7 +4931,7 @@ int drm_mode_mmap_dumb_ioctl(struct drm_device *dev,
4811 * Called by the user via ioctl. 4931 * Called by the user via ioctl.
4812 * 4932 *
4813 * Returns: 4933 * Returns:
4814 * Zero on success, errno on failure. 4934 * Zero on success, negative errno on failure.
4815 */ 4935 */
4816int drm_mode_destroy_dumb_ioctl(struct drm_device *dev, 4936int drm_mode_destroy_dumb_ioctl(struct drm_device *dev,
4817 void *data, struct drm_file *file_priv) 4937 void *data, struct drm_file *file_priv)
@@ -5097,6 +5217,7 @@ void drm_mode_config_init(struct drm_device *dev)
5097 INIT_LIST_HEAD(&dev->mode_config.property_blob_list); 5217 INIT_LIST_HEAD(&dev->mode_config.property_blob_list);
5098 INIT_LIST_HEAD(&dev->mode_config.plane_list); 5218 INIT_LIST_HEAD(&dev->mode_config.plane_list);
5099 idr_init(&dev->mode_config.crtc_idr); 5219 idr_init(&dev->mode_config.crtc_idr);
5220 idr_init(&dev->mode_config.tile_idr);
5100 5221
5101 drm_modeset_lock_all(dev); 5222 drm_modeset_lock_all(dev);
5102 drm_mode_create_standard_connector_properties(dev); 5223 drm_mode_create_standard_connector_properties(dev);
@@ -5184,6 +5305,7 @@ void drm_mode_config_cleanup(struct drm_device *dev)
5184 crtc->funcs->destroy(crtc); 5305 crtc->funcs->destroy(crtc);
5185 } 5306 }
5186 5307
5308 idr_destroy(&dev->mode_config.tile_idr);
5187 idr_destroy(&dev->mode_config.crtc_idr); 5309 idr_destroy(&dev->mode_config.crtc_idr);
5188 drm_modeset_lock_fini(&dev->mode_config.connection_mutex); 5310 drm_modeset_lock_fini(&dev->mode_config.connection_mutex);
5189} 5311}
@@ -5206,3 +5328,100 @@ struct drm_property *drm_mode_create_rotation_property(struct drm_device *dev,
5206 supported_rotations); 5328 supported_rotations);
5207} 5329}
5208EXPORT_SYMBOL(drm_mode_create_rotation_property); 5330EXPORT_SYMBOL(drm_mode_create_rotation_property);
5331
5332/**
5333 * DOC: Tile group
5334 *
5335 * Tile groups are used to represent tiled monitors with a unique
5336 * integer identifier. Tiled monitors using DisplayID v1.3 have
5337 * a unique 8-byte handle, we store this in a tile group, so we
5338 * have a common identifier for all tiles in a monitor group.
5339 */
5340static void drm_tile_group_free(struct kref *kref)
5341{
5342 struct drm_tile_group *tg = container_of(kref, struct drm_tile_group, refcount);
5343 struct drm_device *dev = tg->dev;
5344 mutex_lock(&dev->mode_config.idr_mutex);
5345 idr_remove(&dev->mode_config.tile_idr, tg->id);
5346 mutex_unlock(&dev->mode_config.idr_mutex);
5347 kfree(tg);
5348}
5349
5350/**
5351 * drm_mode_put_tile_group - drop a reference to a tile group.
5352 * @dev: DRM device
5353 * @tg: tile group to drop reference to.
5354 *
5355 * drop reference to tile group and free if 0.
5356 */
5357void drm_mode_put_tile_group(struct drm_device *dev,
5358 struct drm_tile_group *tg)
5359{
5360 kref_put(&tg->refcount, drm_tile_group_free);
5361}
5362
5363/**
5364 * drm_mode_get_tile_group - get a reference to an existing tile group
5365 * @dev: DRM device
5366 * @topology: 8-bytes unique per monitor.
5367 *
5368 * Use the unique bytes to get a reference to an existing tile group.
5369 *
5370 * RETURNS:
5371 * tile group or NULL if not found.
5372 */
5373struct drm_tile_group *drm_mode_get_tile_group(struct drm_device *dev,
5374 char topology[8])
5375{
5376 struct drm_tile_group *tg;
5377 int id;
5378 mutex_lock(&dev->mode_config.idr_mutex);
5379 idr_for_each_entry(&dev->mode_config.tile_idr, tg, id) {
5380 if (!memcmp(tg->group_data, topology, 8)) {
5381 if (!kref_get_unless_zero(&tg->refcount))
5382 tg = NULL;
5383 mutex_unlock(&dev->mode_config.idr_mutex);
5384 return tg;
5385 }
5386 }
5387 mutex_unlock(&dev->mode_config.idr_mutex);
5388 return NULL;
5389}
5390
5391/**
5392 * drm_mode_create_tile_group - create a tile group from a displayid description
5393 * @dev: DRM device
5394 * @topology: 8-bytes unique per monitor.
5395 *
5396 * Create a tile group for the unique monitor, and get a unique
5397 * identifier for the tile group.
5398 *
5399 * RETURNS:
5400 * new tile group or error.
5401 */
5402struct drm_tile_group *drm_mode_create_tile_group(struct drm_device *dev,
5403 char topology[8])
5404{
5405 struct drm_tile_group *tg;
5406 int ret;
5407
5408 tg = kzalloc(sizeof(*tg), GFP_KERNEL);
5409 if (!tg)
5410 return ERR_PTR(-ENOMEM);
5411
5412 kref_init(&tg->refcount);
5413 memcpy(tg->group_data, topology, 8);
5414 tg->dev = dev;
5415
5416 mutex_lock(&dev->mode_config.idr_mutex);
5417 ret = idr_alloc(&dev->mode_config.tile_idr, tg, 1, 0, GFP_KERNEL);
5418 if (ret >= 0) {
5419 tg->id = ret;
5420 } else {
5421 kfree(tg);
5422 tg = ERR_PTR(ret);
5423 }
5424
5425 mutex_unlock(&dev->mode_config.idr_mutex);
5426 return tg;
5427}