Subversion Repositories Kolibri OS

Rev

Rev 3192 | Rev 3746 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. /*
  2.  * Copyright (c) 2006-2008 Intel Corporation
  3.  * Copyright (c) 2007 Dave Airlie <airlied@linux.ie>
  4.  * Copyright (c) 2008 Red Hat Inc.
  5.  *
  6.  * DRM core CRTC related functions
  7.  *
  8.  * Permission to use, copy, modify, distribute, and sell this software and its
  9.  * documentation for any purpose is hereby granted without fee, provided that
  10.  * the above copyright notice appear in all copies and that both that copyright
  11.  * notice and this permission notice appear in supporting documentation, and
  12.  * that the name of the copyright holders not be used in advertising or
  13.  * publicity pertaining to distribution of the software without specific,
  14.  * written prior permission.  The copyright holders make no representations
  15.  * about the suitability of this software for any purpose.  It is provided "as
  16.  * is" without express or implied warranty.
  17.  *
  18.  * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
  19.  * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
  20.  * EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
  21.  * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
  22.  * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
  23.  * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE
  24.  * OF THIS SOFTWARE.
  25.  *
  26.  * Authors:
  27.  *      Keith Packard
  28.  *      Eric Anholt <eric@anholt.net>
  29.  *      Dave Airlie <airlied@linux.ie>
  30.  *      Jesse Barnes <jesse.barnes@intel.com>
  31.  */
  32. #include <linux/list.h>
  33. #include <linux/slab.h>
  34. #include <linux/export.h>
  35. #include <drm/drmP.h>
  36. #include <drm/drm_crtc.h>
  37. #include <drm/drm_edid.h>
  38. #include <drm/drm_fourcc.h>
  39.  
  40. /**
  41.  * drm_modeset_lock_all - take all modeset locks
  42.  * @dev: drm device
  43.  *
  44.  * This function takes all modeset locks, suitable where a more fine-grained
  45.  * scheme isn't (yet) implemented.
  46.  */
  47. void drm_modeset_lock_all(struct drm_device *dev)
  48. {
  49.         struct drm_crtc *crtc;
  50.  
  51.         mutex_lock(&dev->mode_config.mutex);
  52.  
  53.         list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
  54.                 mutex_lock_nest_lock(&crtc->mutex, &dev->mode_config.mutex);
  55. }
  56. EXPORT_SYMBOL(drm_modeset_lock_all);
  57.  
  58. /**
  59.  * drm_modeset_unlock_all - drop all modeset locks
  60.  * @dev: device
  61.  */
  62. void drm_modeset_unlock_all(struct drm_device *dev)
  63. {
  64.         struct drm_crtc *crtc;
  65.  
  66.         list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
  67.                 mutex_unlock(&crtc->mutex);
  68.  
  69.         mutex_unlock(&dev->mode_config.mutex);
  70. }
  71. EXPORT_SYMBOL(drm_modeset_unlock_all);
  72.  
  73. /**
  74.  * drm_warn_on_modeset_not_all_locked - check that all modeset locks are locked
  75.  * @dev: device
  76.  */
  77. void drm_warn_on_modeset_not_all_locked(struct drm_device *dev)
  78. {
  79.         struct drm_crtc *crtc;
  80.  
  81.         list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
  82.                 WARN_ON(!mutex_is_locked(&crtc->mutex));
  83.  
  84.         WARN_ON(!mutex_is_locked(&dev->mode_config.mutex));
  85. }
  86. EXPORT_SYMBOL(drm_warn_on_modeset_not_all_locked);
  87.  
  88. /* Avoid boilerplate.  I'm tired of typing. */
  89. #define DRM_ENUM_NAME_FN(fnname, list)                          \
  90.         char *fnname(int val)                                   \
  91.         {                                                       \
  92.                 int i;                                          \
  93.                 for (i = 0; i < ARRAY_SIZE(list); i++) {        \
  94.                         if (list[i].type == val)                \
  95.                                 return list[i].name;            \
  96.                 }                                               \
  97.                 return "(unknown)";                             \
  98.         }
  99.  
  100. /*
  101.  * Global properties
  102.  */
  103. static struct drm_prop_enum_list drm_dpms_enum_list[] =
  104. {       { DRM_MODE_DPMS_ON, "On" },
  105.         { DRM_MODE_DPMS_STANDBY, "Standby" },
  106.         { DRM_MODE_DPMS_SUSPEND, "Suspend" },
  107.         { DRM_MODE_DPMS_OFF, "Off" }
  108. };
  109.  
  110. DRM_ENUM_NAME_FN(drm_get_dpms_name, drm_dpms_enum_list)
  111.  
  112. /*
  113.  * Optional properties
  114.  */
  115. static struct drm_prop_enum_list drm_scaling_mode_enum_list[] =
  116. {
  117.         { DRM_MODE_SCALE_NONE, "None" },
  118.         { DRM_MODE_SCALE_FULLSCREEN, "Full" },
  119.         { DRM_MODE_SCALE_CENTER, "Center" },
  120.         { DRM_MODE_SCALE_ASPECT, "Full aspect" },
  121. };
  122.  
  123. static struct drm_prop_enum_list drm_dithering_mode_enum_list[] =
  124. {
  125.         { DRM_MODE_DITHERING_OFF, "Off" },
  126.         { DRM_MODE_DITHERING_ON, "On" },
  127.         { DRM_MODE_DITHERING_AUTO, "Automatic" },
  128. };
  129.  
  130. /*
  131.  * Non-global properties, but "required" for certain connectors.
  132.  */
  133. static struct drm_prop_enum_list drm_dvi_i_select_enum_list[] =
  134. {
  135.         { DRM_MODE_SUBCONNECTOR_Automatic, "Automatic" }, /* DVI-I and TV-out */
  136.         { DRM_MODE_SUBCONNECTOR_DVID,      "DVI-D"     }, /* DVI-I  */
  137.         { DRM_MODE_SUBCONNECTOR_DVIA,      "DVI-A"     }, /* DVI-I  */
  138. };
  139.  
  140. DRM_ENUM_NAME_FN(drm_get_dvi_i_select_name, drm_dvi_i_select_enum_list)
  141.  
  142. static struct drm_prop_enum_list drm_dvi_i_subconnector_enum_list[] =
  143. {
  144.         { DRM_MODE_SUBCONNECTOR_Unknown,   "Unknown"   }, /* DVI-I and TV-out */
  145.         { DRM_MODE_SUBCONNECTOR_DVID,      "DVI-D"     }, /* DVI-I  */
  146.         { DRM_MODE_SUBCONNECTOR_DVIA,      "DVI-A"     }, /* DVI-I  */
  147. };
  148.  
  149. DRM_ENUM_NAME_FN(drm_get_dvi_i_subconnector_name,
  150.                  drm_dvi_i_subconnector_enum_list)
  151.  
  152. static struct drm_prop_enum_list drm_tv_select_enum_list[] =
  153. {
  154.         { DRM_MODE_SUBCONNECTOR_Automatic, "Automatic" }, /* DVI-I and TV-out */
  155.         { DRM_MODE_SUBCONNECTOR_Composite, "Composite" }, /* TV-out */
  156.         { DRM_MODE_SUBCONNECTOR_SVIDEO,    "SVIDEO"    }, /* TV-out */
  157.         { DRM_MODE_SUBCONNECTOR_Component, "Component" }, /* TV-out */
  158.         { DRM_MODE_SUBCONNECTOR_SCART,     "SCART"     }, /* TV-out */
  159. };
  160.  
  161. DRM_ENUM_NAME_FN(drm_get_tv_select_name, drm_tv_select_enum_list)
  162.  
  163. static struct drm_prop_enum_list drm_tv_subconnector_enum_list[] =
  164. {
  165.         { DRM_MODE_SUBCONNECTOR_Unknown,   "Unknown"   }, /* DVI-I and TV-out */
  166.         { DRM_MODE_SUBCONNECTOR_Composite, "Composite" }, /* TV-out */
  167.         { DRM_MODE_SUBCONNECTOR_SVIDEO,    "SVIDEO"    }, /* TV-out */
  168.         { DRM_MODE_SUBCONNECTOR_Component, "Component" }, /* TV-out */
  169.         { DRM_MODE_SUBCONNECTOR_SCART,     "SCART"     }, /* TV-out */
  170. };
  171.  
  172. DRM_ENUM_NAME_FN(drm_get_tv_subconnector_name,
  173.                  drm_tv_subconnector_enum_list)
  174.  
  175. static struct drm_prop_enum_list drm_dirty_info_enum_list[] = {
  176.         { DRM_MODE_DIRTY_OFF,      "Off"      },
  177.         { DRM_MODE_DIRTY_ON,       "On"       },
  178.         { DRM_MODE_DIRTY_ANNOTATE, "Annotate" },
  179. };
  180.  
  181. DRM_ENUM_NAME_FN(drm_get_dirty_info_name,
  182.                  drm_dirty_info_enum_list)
  183.  
  184. struct drm_conn_prop_enum_list {
  185.         int type;
  186.         char *name;
  187.         int count;
  188. };
  189.  
  190. /*
  191.  * Connector and encoder types.
  192.  */
  193. static struct drm_conn_prop_enum_list drm_connector_enum_list[] =
  194. {       { DRM_MODE_CONNECTOR_Unknown, "Unknown", 0 },
  195.         { DRM_MODE_CONNECTOR_VGA, "VGA", 0 },
  196.         { DRM_MODE_CONNECTOR_DVII, "DVI-I", 0 },
  197.         { DRM_MODE_CONNECTOR_DVID, "DVI-D", 0 },
  198.         { DRM_MODE_CONNECTOR_DVIA, "DVI-A", 0 },
  199.         { DRM_MODE_CONNECTOR_Composite, "Composite", 0 },
  200.         { DRM_MODE_CONNECTOR_SVIDEO, "SVIDEO", 0 },
  201.         { DRM_MODE_CONNECTOR_LVDS, "LVDS", 0 },
  202.         { DRM_MODE_CONNECTOR_Component, "Component", 0 },
  203.         { DRM_MODE_CONNECTOR_9PinDIN, "DIN", 0 },
  204.         { DRM_MODE_CONNECTOR_DisplayPort, "DP", 0 },
  205.         { DRM_MODE_CONNECTOR_HDMIA, "HDMI-A", 0 },
  206.         { DRM_MODE_CONNECTOR_HDMIB, "HDMI-B", 0 },
  207.         { DRM_MODE_CONNECTOR_TV, "TV", 0 },
  208.         { DRM_MODE_CONNECTOR_eDP, "eDP", 0 },
  209.         { DRM_MODE_CONNECTOR_VIRTUAL, "Virtual", 0},
  210. };
  211.  
  212. static struct drm_prop_enum_list drm_encoder_enum_list[] =
  213. {       { DRM_MODE_ENCODER_NONE, "None" },
  214.         { DRM_MODE_ENCODER_DAC, "DAC" },
  215.         { DRM_MODE_ENCODER_TMDS, "TMDS" },
  216.         { DRM_MODE_ENCODER_LVDS, "LVDS" },
  217.         { DRM_MODE_ENCODER_TVDAC, "TV" },
  218.         { DRM_MODE_ENCODER_VIRTUAL, "Virtual" },
  219. };
  220.  
  221. char *drm_get_encoder_name(struct drm_encoder *encoder)
  222. {
  223.         static char buf[32];
  224.  
  225.         snprintf(buf, 32, "%s-%d",
  226.                  drm_encoder_enum_list[encoder->encoder_type].name,
  227.                  encoder->base.id);
  228.         return buf;
  229. }
  230. EXPORT_SYMBOL(drm_get_encoder_name);
  231.  
  232. char *drm_get_connector_name(struct drm_connector *connector)
  233. {
  234.         static char buf[32];
  235.  
  236.         snprintf(buf, 32, "%s-%d",
  237.                  drm_connector_enum_list[connector->connector_type].name,
  238.                  connector->connector_type_id);
  239.         return buf;
  240. }
  241. EXPORT_SYMBOL(drm_get_connector_name);
  242.  
  243. char *drm_get_connector_status_name(enum drm_connector_status status)
  244. {
  245.         if (status == connector_status_connected)
  246.                 return "connected";
  247.         else if (status == connector_status_disconnected)
  248.                 return "disconnected";
  249.         else
  250.                 return "unknown";
  251. }
  252.  
  253. /**
  254.  * drm_mode_object_get - allocate a new modeset identifier
  255.  * @dev: DRM device
  256.  * @obj: object pointer, used to generate unique ID
  257.  * @obj_type: object type
  258.  *
  259.  * Create a unique identifier based on @ptr in @dev's identifier space.  Used
  260.  * for tracking modes, CRTCs and connectors.
  261.  *
  262.  * RETURNS:
  263.  * New unique (relative to other objects in @dev) integer identifier for the
  264.  * object.
  265.  */
  266. static int drm_mode_object_get(struct drm_device *dev,
  267.                                struct drm_mode_object *obj, uint32_t obj_type)
  268. {
  269.         int ret;
  270.  
  271.         mutex_lock(&dev->mode_config.idr_mutex);
  272.         ret = idr_alloc(&dev->mode_config.crtc_idr, obj, 1, 0, GFP_KERNEL);
  273.         if (ret >= 0) {
  274.                 /*
  275.                  * Set up the object linking under the protection of the idr
  276.                  * lock so that other users can't see inconsistent state.
  277.                  */
  278.                 obj->id = ret;
  279.                 obj->type = obj_type;
  280.         }
  281.         mutex_unlock(&dev->mode_config.idr_mutex);
  282.  
  283.         return ret < 0 ? ret : 0;
  284. }
  285.  
  286. /**
  287.  * drm_mode_object_put - free a modeset identifer
  288.  * @dev: DRM device
  289.  * @object: object to free
  290.  *
  291.  * Free @id from @dev's unique identifier pool.
  292.  */
  293. static void drm_mode_object_put(struct drm_device *dev,
  294.                                 struct drm_mode_object *object)
  295. {
  296.         mutex_lock(&dev->mode_config.idr_mutex);
  297.         idr_remove(&dev->mode_config.crtc_idr, object->id);
  298.         mutex_unlock(&dev->mode_config.idr_mutex);
  299. }
  300.  
  301. /**
  302.  * drm_mode_object_find - look up a drm object with static lifetime
  303.  * @dev: drm device
  304.  * @id: id of the mode object
  305.  * @type: type of the mode object
  306.  *
  307.  * Note that framebuffers cannot be looked up with this functions - since those
  308.  * are reference counted, they need special treatment.
  309.  */
  310. struct drm_mode_object *drm_mode_object_find(struct drm_device *dev,
  311.                 uint32_t id, uint32_t type)
  312. {
  313.         struct drm_mode_object *obj = NULL;
  314.  
  315.         /* Framebuffers are reference counted and need their own lookup
  316.          * function.*/
  317.         WARN_ON(type == DRM_MODE_OBJECT_FB);
  318.  
  319.         mutex_lock(&dev->mode_config.idr_mutex);
  320.         obj = idr_find(&dev->mode_config.crtc_idr, id);
  321.         if (!obj || (obj->type != type) || (obj->id != id))
  322.                 obj = NULL;
  323.         mutex_unlock(&dev->mode_config.idr_mutex);
  324.  
  325.         return obj;
  326. }
  327. EXPORT_SYMBOL(drm_mode_object_find);
  328.  
  329. /**
  330.  * drm_framebuffer_init - initialize a framebuffer
  331.  * @dev: DRM device
  332.  * @fb: framebuffer to be initialized
  333.  * @funcs: ... with these functions
  334.  *
  335.  * Allocates an ID for the framebuffer's parent mode object, sets its mode
  336.  * functions & device file and adds it to the master fd list.
  337.  *
  338.  * IMPORTANT:
  339.  * This functions publishes the fb and makes it available for concurrent access
  340.  * by other users. Which means by this point the fb _must_ be fully set up -
  341.  * since all the fb attributes are invariant over its lifetime, no further
  342.  * locking but only correct reference counting is required.
  343.  *
  344.  * RETURNS:
  345.  * Zero on success, error code on failure.
  346.  */
  347. int drm_framebuffer_init(struct drm_device *dev, struct drm_framebuffer *fb,
  348.                          const struct drm_framebuffer_funcs *funcs)
  349. {
  350.         int ret;
  351.  
  352.         mutex_lock(&dev->mode_config.fb_lock);
  353.         kref_init(&fb->refcount);
  354.         INIT_LIST_HEAD(&fb->filp_head);
  355.         fb->dev = dev;
  356.         fb->funcs = funcs;
  357.  
  358.         ret = drm_mode_object_get(dev, &fb->base, DRM_MODE_OBJECT_FB);
  359.         if (ret)
  360.                 goto out;
  361.  
  362.         /* Grab the idr reference. */
  363.         drm_framebuffer_reference(fb);
  364.  
  365.         dev->mode_config.num_fb++;
  366.         list_add(&fb->head, &dev->mode_config.fb_list);
  367. out:
  368.         mutex_unlock(&dev->mode_config.fb_lock);
  369.  
  370.         return 0;
  371. }
  372. EXPORT_SYMBOL(drm_framebuffer_init);
  373.  
  374. static void drm_framebuffer_free(struct kref *kref)
  375. {
  376.         struct drm_framebuffer *fb =
  377.                         container_of(kref, struct drm_framebuffer, refcount);
  378.         fb->funcs->destroy(fb);
  379. }
  380.  
  381. static struct drm_framebuffer *__drm_framebuffer_lookup(struct drm_device *dev,
  382.                                                         uint32_t id)
  383. {
  384.         struct drm_mode_object *obj = NULL;
  385.         struct drm_framebuffer *fb;
  386.  
  387.         mutex_lock(&dev->mode_config.idr_mutex);
  388.         obj = idr_find(&dev->mode_config.crtc_idr, id);
  389.         if (!obj || (obj->type != DRM_MODE_OBJECT_FB) || (obj->id != id))
  390.                 fb = NULL;
  391.         else
  392.                 fb = obj_to_fb(obj);
  393.         mutex_unlock(&dev->mode_config.idr_mutex);
  394.  
  395.         return fb;
  396. }
  397.  
  398. /**
  399.  * drm_framebuffer_lookup - look up a drm framebuffer and grab a reference
  400.  * @dev: drm device
  401.  * @id: id of the fb object
  402.  *
  403.  * If successful, this grabs an additional reference to the framebuffer -
  404.  * callers need to make sure to eventually unreference the returned framebuffer
  405.  * again.
  406.  */
  407. struct drm_framebuffer *drm_framebuffer_lookup(struct drm_device *dev,
  408.                                                uint32_t id)
  409. {
  410.         struct drm_framebuffer *fb;
  411.  
  412.         mutex_lock(&dev->mode_config.fb_lock);
  413.         fb = __drm_framebuffer_lookup(dev, id);
  414.         if (fb)
  415.                 kref_get(&fb->refcount);
  416.         mutex_unlock(&dev->mode_config.fb_lock);
  417.  
  418.         return fb;
  419. }
  420. EXPORT_SYMBOL(drm_framebuffer_lookup);
  421.  
  422. /**
  423.  * drm_framebuffer_unreference - unref a framebuffer
  424.  * @fb: framebuffer to unref
  425.  *
  426.  * This functions decrements the fb's refcount and frees it if it drops to zero.
  427.  */
  428. void drm_framebuffer_unreference(struct drm_framebuffer *fb)
  429. {
  430.         DRM_DEBUG("FB ID: %d\n", fb->base.id);
  431.         kref_put(&fb->refcount, drm_framebuffer_free);
  432. }
  433. EXPORT_SYMBOL(drm_framebuffer_unreference);
  434.  
  435. /**
  436.  * drm_framebuffer_reference - incr the fb refcnt
  437.  * @fb: framebuffer
  438.  */
  439. void drm_framebuffer_reference(struct drm_framebuffer *fb)
  440. {
  441.         DRM_DEBUG("FB ID: %d\n", fb->base.id);
  442.         kref_get(&fb->refcount);
  443. }
  444. EXPORT_SYMBOL(drm_framebuffer_reference);
  445.  
  446. static void drm_framebuffer_free_bug(struct kref *kref)
  447. {
  448.         BUG();
  449. }
  450.  
  451. static void __drm_framebuffer_unreference(struct drm_framebuffer *fb)
  452. {
  453.         DRM_DEBUG("FB ID: %d\n", fb->base.id);
  454.         kref_put(&fb->refcount, drm_framebuffer_free_bug);
  455. }
  456.  
  457. /* dev->mode_config.fb_lock must be held! */
  458. static void __drm_framebuffer_unregister(struct drm_device *dev,
  459.                                          struct drm_framebuffer *fb)
  460. {
  461.         mutex_lock(&dev->mode_config.idr_mutex);
  462.         idr_remove(&dev->mode_config.crtc_idr, fb->base.id);
  463.         mutex_unlock(&dev->mode_config.idr_mutex);
  464.  
  465.         fb->base.id = 0;
  466.  
  467.         __drm_framebuffer_unreference(fb);
  468. }
  469.  
  470. /**
  471.  * drm_framebuffer_unregister_private - unregister a private fb from the lookup idr
  472.  * @fb: fb to unregister
  473.  *
  474.  * Drivers need to call this when cleaning up driver-private framebuffers, e.g.
  475.  * those used for fbdev. Note that the caller must hold a reference of it's own,
  476.  * i.e. the object may not be destroyed through this call (since it'll lead to a
  477.  * locking inversion).
  478.  */
  479. void drm_framebuffer_unregister_private(struct drm_framebuffer *fb)
  480. {
  481.         struct drm_device *dev = fb->dev;
  482.  
  483.         mutex_lock(&dev->mode_config.fb_lock);
  484.         /* Mark fb as reaped and drop idr ref. */
  485.         __drm_framebuffer_unregister(dev, fb);
  486.         mutex_unlock(&dev->mode_config.fb_lock);
  487. }
  488. EXPORT_SYMBOL(drm_framebuffer_unregister_private);
  489.  
  490. /**
  491.  * drm_framebuffer_cleanup - remove a framebuffer object
  492.  * @fb: framebuffer to remove
  493.  *
  494.  * Cleanup references to a user-created framebuffer. This function is intended
  495.  * to be used from the drivers ->destroy callback.
  496.  *
  497.  * Note that this function does not remove the fb from active usuage - if it is
  498.  * still used anywhere, hilarity can ensue since userspace could call getfb on
  499.  * the id and get back -EINVAL. Obviously no concern at driver unload time.
  500.  *
  501.  * Also, the framebuffer will not be removed from the lookup idr - for
  502.  * user-created framebuffers this will happen in in the rmfb ioctl. For
  503.  * driver-private objects (e.g. for fbdev) drivers need to explicitly call
  504.  * drm_framebuffer_unregister_private.
  505.  */
  506. void drm_framebuffer_cleanup(struct drm_framebuffer *fb)
  507. {
  508.         struct drm_device *dev = fb->dev;
  509.  
  510.         mutex_lock(&dev->mode_config.fb_lock);
  511.         list_del(&fb->head);
  512.         dev->mode_config.num_fb--;
  513.         mutex_unlock(&dev->mode_config.fb_lock);
  514. }
  515. EXPORT_SYMBOL(drm_framebuffer_cleanup);
  516.  
  517. /**
  518.  * drm_framebuffer_remove - remove and unreference a framebuffer object
  519.  * @fb: framebuffer to remove
  520.  *
  521.  * Scans all the CRTCs and planes in @dev's mode_config.  If they're
  522.  * using @fb, removes it, setting it to NULL. Then drops the reference to the
  523.  * passed-in framebuffer. Might take the modeset locks.
  524.  *
  525.  * Note that this function optimizes the cleanup away if the caller holds the
  526.  * last reference to the framebuffer. It is also guaranteed to not take the
  527.  * modeset locks in this case.
  528.  */
  529. void drm_framebuffer_remove(struct drm_framebuffer *fb)
  530. {
  531.         struct drm_device *dev = fb->dev;
  532.         struct drm_crtc *crtc;
  533.         struct drm_plane *plane;
  534.         struct drm_mode_set set;
  535.         int ret;
  536.  
  537.         WARN_ON(!list_empty(&fb->filp_head));
  538.  
  539.         /*
  540.          * drm ABI mandates that we remove any deleted framebuffers from active
  541.          * useage. But since most sane clients only remove framebuffers they no
  542.          * longer need, try to optimize this away.
  543.          *
  544.          * Since we're holding a reference ourselves, observing a refcount of 1
  545.          * means that we're the last holder and can skip it. Also, the refcount
  546.          * can never increase from 1 again, so we don't need any barriers or
  547.          * locks.
  548.          *
  549.          * Note that userspace could try to race with use and instate a new
  550.          * usage _after_ we've cleared all current ones. End result will be an
  551.          * in-use fb with fb-id == 0. Userspace is allowed to shoot its own foot
  552.          * in this manner.
  553.          */
  554.         if (atomic_read(&fb->refcount.refcount) > 1) {
  555.                 drm_modeset_lock_all(dev);
  556.                 /* remove from any CRTC */
  557.                 list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
  558.                         if (crtc->fb == fb) {
  559.                                 /* should turn off the crtc */
  560.                                 memset(&set, 0, sizeof(struct drm_mode_set));
  561.                                 set.crtc = crtc;
  562.                                 set.fb = NULL;
  563.                                 ret = drm_mode_set_config_internal(&set);
  564.                                 if (ret)
  565.                                         DRM_ERROR("failed to reset crtc %p when fb was deleted\n", crtc);
  566.                         }
  567.                 }
  568.  
  569.                 list_for_each_entry(plane, &dev->mode_config.plane_list, head) {
  570.                         if (plane->fb == fb) {
  571.                                 /* should turn off the crtc */
  572.                                 ret = plane->funcs->disable_plane(plane);
  573.                                 if (ret)
  574.                                         DRM_ERROR("failed to disable plane with busy fb\n");
  575.                                 /* disconnect the plane from the fb and crtc: */
  576.                                 __drm_framebuffer_unreference(plane->fb);
  577.                                 plane->fb = NULL;
  578.                                 plane->crtc = NULL;
  579.                         }
  580.                 }
  581.                 drm_modeset_unlock_all(dev);
  582.         }
  583.  
  584.         drm_framebuffer_unreference(fb);
  585. }
  586. EXPORT_SYMBOL(drm_framebuffer_remove);
  587.  
  588. /**
  589.  * drm_crtc_init - Initialise a new CRTC object
  590.  * @dev: DRM device
  591.  * @crtc: CRTC object to init
  592.  * @funcs: callbacks for the new CRTC
  593.  *
  594.  * Inits a new object created as base part of an driver crtc object.
  595.  *
  596.  * RETURNS:
  597.  * Zero on success, error code on failure.
  598.  */
  599. int drm_crtc_init(struct drm_device *dev, struct drm_crtc *crtc,
  600.                    const struct drm_crtc_funcs *funcs)
  601. {
  602.         int ret;
  603.  
  604.         crtc->dev = dev;
  605.         crtc->funcs = funcs;
  606.         crtc->invert_dimensions = false;
  607.  
  608.         drm_modeset_lock_all(dev);
  609.         mutex_init(&crtc->mutex);
  610.         mutex_lock_nest_lock(&crtc->mutex, &dev->mode_config.mutex);
  611.  
  612.         ret = drm_mode_object_get(dev, &crtc->base, DRM_MODE_OBJECT_CRTC);
  613.         if (ret)
  614.                 goto out;
  615.  
  616.         crtc->base.properties = &crtc->properties;
  617.  
  618.         list_add_tail(&crtc->head, &dev->mode_config.crtc_list);
  619.         dev->mode_config.num_crtc++;
  620.  
  621.  out:
  622.         drm_modeset_unlock_all(dev);
  623.  
  624.         return ret;
  625. }
  626. EXPORT_SYMBOL(drm_crtc_init);
  627.  
  628. /**
  629.  * drm_crtc_cleanup - Cleans up the core crtc usage.
  630.  * @crtc: CRTC to cleanup
  631.  *
  632.  * Cleanup @crtc. Removes from drm modesetting space
  633.  * does NOT free object, caller does that.
  634.  */
  635. void drm_crtc_cleanup(struct drm_crtc *crtc)
  636. {
  637.         struct drm_device *dev = crtc->dev;
  638.  
  639.                 kfree(crtc->gamma_store);
  640.                 crtc->gamma_store = NULL;
  641.  
  642.         drm_mode_object_put(dev, &crtc->base);
  643.         list_del(&crtc->head);
  644.         dev->mode_config.num_crtc--;
  645. }
  646. EXPORT_SYMBOL(drm_crtc_cleanup);
  647.  
  648. /**
  649.  * drm_mode_probed_add - add a mode to a connector's probed mode list
  650.  * @connector: connector the new mode
  651.  * @mode: mode data
  652.  *
  653.  * Add @mode to @connector's mode list for later use.
  654.  */
  655. void drm_mode_probed_add(struct drm_connector *connector,
  656.                          struct drm_display_mode *mode)
  657. {
  658.         list_add(&mode->head, &connector->probed_modes);
  659. }
  660. EXPORT_SYMBOL(drm_mode_probed_add);
  661.  
  662. /**
  663.  * drm_mode_remove - remove and free a mode
  664.  * @connector: connector list to modify
  665.  * @mode: mode to remove
  666.  *
  667.  * Remove @mode from @connector's mode list, then free it.
  668.  */
  669. void drm_mode_remove(struct drm_connector *connector,
  670.                      struct drm_display_mode *mode)
  671. {
  672.         list_del(&mode->head);
  673.         drm_mode_destroy(connector->dev, mode);
  674. }
  675. EXPORT_SYMBOL(drm_mode_remove);
  676.  
  677. /**
  678.  * drm_connector_init - Init a preallocated connector
  679.  * @dev: DRM device
  680.  * @connector: the connector to init
  681.  * @funcs: callbacks for this connector
  682.  * @connector_type: user visible type of the connector
  683.  *
  684.  * Initialises a preallocated connector. Connectors should be
  685.  * subclassed as part of driver connector objects.
  686.  *
  687.  * RETURNS:
  688.  * Zero on success, error code on failure.
  689.  */
  690. int drm_connector_init(struct drm_device *dev,
  691.                      struct drm_connector *connector,
  692.                      const struct drm_connector_funcs *funcs,
  693.                      int connector_type)
  694. {
  695.         int ret;
  696.  
  697.         drm_modeset_lock_all(dev);
  698.  
  699.         ret = drm_mode_object_get(dev, &connector->base, DRM_MODE_OBJECT_CONNECTOR);
  700.         if (ret)
  701.                 goto out;
  702.  
  703.         connector->base.properties = &connector->properties;
  704.         connector->dev = dev;
  705.         connector->funcs = funcs;
  706.         connector->connector_type = connector_type;
  707.         connector->connector_type_id =
  708.                 ++drm_connector_enum_list[connector_type].count; /* TODO */
  709.         INIT_LIST_HEAD(&connector->user_modes);
  710.         INIT_LIST_HEAD(&connector->probed_modes);
  711.         INIT_LIST_HEAD(&connector->modes);
  712.         connector->edid_blob_ptr = NULL;
  713.         connector->status = connector_status_unknown;
  714.  
  715.         list_add_tail(&connector->head, &dev->mode_config.connector_list);
  716.         dev->mode_config.num_connector++;
  717.  
  718.         if (connector_type != DRM_MODE_CONNECTOR_VIRTUAL)
  719.                 drm_object_attach_property(&connector->base,
  720.                                               dev->mode_config.edid_property,
  721.                                               0);
  722.  
  723.         drm_object_attach_property(&connector->base,
  724.                                       dev->mode_config.dpms_property, 0);
  725.  
  726.  out:
  727.         drm_modeset_unlock_all(dev);
  728.  
  729.         return ret;
  730. }
  731. EXPORT_SYMBOL(drm_connector_init);
  732.  
  733. /**
  734.  * drm_connector_cleanup - cleans up an initialised connector
  735.  * @connector: connector to cleanup
  736.  *
  737.  * Cleans up the connector but doesn't free the object.
  738.  */
  739. void drm_connector_cleanup(struct drm_connector *connector)
  740. {
  741.         struct drm_device *dev = connector->dev;
  742.         struct drm_display_mode *mode, *t;
  743.  
  744.         list_for_each_entry_safe(mode, t, &connector->probed_modes, head)
  745.                 drm_mode_remove(connector, mode);
  746.  
  747.         list_for_each_entry_safe(mode, t, &connector->modes, head)
  748.                 drm_mode_remove(connector, mode);
  749.  
  750.         list_for_each_entry_safe(mode, t, &connector->user_modes, head)
  751.                 drm_mode_remove(connector, mode);
  752.  
  753.         drm_mode_object_put(dev, &connector->base);
  754.         list_del(&connector->head);
  755.         dev->mode_config.num_connector--;
  756. }
  757. EXPORT_SYMBOL(drm_connector_cleanup);
  758.  
  759. void drm_connector_unplug_all(struct drm_device *dev)
  760. {
  761.         struct drm_connector *connector;
  762.  
  763.         /* taking the mode config mutex ends up in a clash with sysfs */
  764. //   list_for_each_entry(connector, &dev->mode_config.connector_list, head)
  765. //       drm_sysfs_connector_remove(connector);
  766.  
  767. }
  768. EXPORT_SYMBOL(drm_connector_unplug_all);
  769.  
  770. int drm_encoder_init(struct drm_device *dev,
  771.                       struct drm_encoder *encoder,
  772.                       const struct drm_encoder_funcs *funcs,
  773.                       int encoder_type)
  774. {
  775.         int ret;
  776.  
  777.         drm_modeset_lock_all(dev);
  778.  
  779.         ret = drm_mode_object_get(dev, &encoder->base, DRM_MODE_OBJECT_ENCODER);
  780.         if (ret)
  781.                 goto out;
  782.  
  783.         encoder->dev = dev;
  784.         encoder->encoder_type = encoder_type;
  785.         encoder->funcs = funcs;
  786.  
  787.         list_add_tail(&encoder->head, &dev->mode_config.encoder_list);
  788.         dev->mode_config.num_encoder++;
  789.  
  790.  out:
  791.         drm_modeset_unlock_all(dev);
  792.  
  793.         return ret;
  794. }
  795. EXPORT_SYMBOL(drm_encoder_init);
  796.  
  797. void drm_encoder_cleanup(struct drm_encoder *encoder)
  798. {
  799.         struct drm_device *dev = encoder->dev;
  800.         drm_modeset_lock_all(dev);
  801.         drm_mode_object_put(dev, &encoder->base);
  802.         list_del(&encoder->head);
  803.         dev->mode_config.num_encoder--;
  804.         drm_modeset_unlock_all(dev);
  805. }
  806. EXPORT_SYMBOL(drm_encoder_cleanup);
  807.  
  808. int drm_plane_init(struct drm_device *dev, struct drm_plane *plane,
  809.                    unsigned long possible_crtcs,
  810.                    const struct drm_plane_funcs *funcs,
  811.                    const uint32_t *formats, uint32_t format_count,
  812.                    bool priv)
  813. {
  814.         int ret;
  815.  
  816.         drm_modeset_lock_all(dev);
  817.  
  818.         ret = drm_mode_object_get(dev, &plane->base, DRM_MODE_OBJECT_PLANE);
  819.         if (ret)
  820.                 goto out;
  821.  
  822.         plane->base.properties = &plane->properties;
  823.         plane->dev = dev;
  824.         plane->funcs = funcs;
  825.         plane->format_types = kmalloc(sizeof(uint32_t) * format_count,
  826.                                       GFP_KERNEL);
  827.         if (!plane->format_types) {
  828.                 DRM_DEBUG_KMS("out of memory when allocating plane\n");
  829.                 drm_mode_object_put(dev, &plane->base);
  830.                 ret = -ENOMEM;
  831.                 goto out;
  832.         }
  833.  
  834.         memcpy(plane->format_types, formats, format_count * sizeof(uint32_t));
  835.         plane->format_count = format_count;
  836.         plane->possible_crtcs = possible_crtcs;
  837.  
  838.         /* private planes are not exposed to userspace, but depending on
  839.          * display hardware, might be convenient to allow sharing programming
  840.          * for the scanout engine with the crtc implementation.
  841.          */
  842.         if (!priv) {
  843.                 list_add_tail(&plane->head, &dev->mode_config.plane_list);
  844.                 dev->mode_config.num_plane++;
  845.         } else {
  846.                 INIT_LIST_HEAD(&plane->head);
  847.         }
  848.  
  849.  out:
  850.         drm_modeset_unlock_all(dev);
  851.  
  852.         return ret;
  853. }
  854. EXPORT_SYMBOL(drm_plane_init);
  855.  
  856. void drm_plane_cleanup(struct drm_plane *plane)
  857. {
  858.         struct drm_device *dev = plane->dev;
  859.  
  860.         drm_modeset_lock_all(dev);
  861.         kfree(plane->format_types);
  862.         drm_mode_object_put(dev, &plane->base);
  863.         /* if not added to a list, it must be a private plane */
  864.         if (!list_empty(&plane->head)) {
  865.                 list_del(&plane->head);
  866.                 dev->mode_config.num_plane--;
  867.         }
  868.         drm_modeset_unlock_all(dev);
  869. }
  870. EXPORT_SYMBOL(drm_plane_cleanup);
  871.  
  872. /**
  873.  * drm_mode_create - create a new display mode
  874.  * @dev: DRM device
  875.  *
  876.  * Create a new drm_display_mode, give it an ID, and return it.
  877.  *
  878.  * RETURNS:
  879.  * Pointer to new mode on success, NULL on error.
  880.  */
  881. struct drm_display_mode *drm_mode_create(struct drm_device *dev)
  882. {
  883.         struct drm_display_mode *nmode;
  884.  
  885.         nmode = kzalloc(sizeof(struct drm_display_mode), GFP_KERNEL);
  886.         if (!nmode)
  887.                 return NULL;
  888.  
  889.         if (drm_mode_object_get(dev, &nmode->base, DRM_MODE_OBJECT_MODE)) {
  890.                 kfree(nmode);
  891.                 return NULL;
  892.         }
  893.  
  894.         return nmode;
  895. }
  896. EXPORT_SYMBOL(drm_mode_create);
  897.  
  898. /**
  899.  * drm_mode_destroy - remove a mode
  900.  * @dev: DRM device
  901.  * @mode: mode to remove
  902.  *
  903.  * Free @mode's unique identifier, then free it.
  904.  */
  905. void drm_mode_destroy(struct drm_device *dev, struct drm_display_mode *mode)
  906. {
  907.         if (!mode)
  908.                 return;
  909.  
  910.         drm_mode_object_put(dev, &mode->base);
  911.  
  912.         kfree(mode);
  913. }
  914. EXPORT_SYMBOL(drm_mode_destroy);
  915.  
  916. static int drm_mode_create_standard_connector_properties(struct drm_device *dev)
  917. {
  918.         struct drm_property *edid;
  919.         struct drm_property *dpms;
  920.  
  921.         /*
  922.          * Standard properties (apply to all connectors)
  923.          */
  924.         edid = drm_property_create(dev, DRM_MODE_PROP_BLOB |
  925.                                    DRM_MODE_PROP_IMMUTABLE,
  926.                                    "EDID", 0);
  927.         dev->mode_config.edid_property = edid;
  928.  
  929.         dpms = drm_property_create_enum(dev, 0,
  930.                                    "DPMS", drm_dpms_enum_list,
  931.                                    ARRAY_SIZE(drm_dpms_enum_list));
  932.         dev->mode_config.dpms_property = dpms;
  933.  
  934.         return 0;
  935. }
  936.  
  937. /**
  938.  * drm_mode_create_dvi_i_properties - create DVI-I specific connector properties
  939.  * @dev: DRM device
  940.  *
  941.  * Called by a driver the first time a DVI-I connector is made.
  942.  */
  943. int drm_mode_create_dvi_i_properties(struct drm_device *dev)
  944. {
  945.         struct drm_property *dvi_i_selector;
  946.         struct drm_property *dvi_i_subconnector;
  947.  
  948.         if (dev->mode_config.dvi_i_select_subconnector_property)
  949.                 return 0;
  950.  
  951.         dvi_i_selector =
  952.                 drm_property_create_enum(dev, 0,
  953.                                     "select subconnector",
  954.                                     drm_dvi_i_select_enum_list,
  955.                                     ARRAY_SIZE(drm_dvi_i_select_enum_list));
  956.         dev->mode_config.dvi_i_select_subconnector_property = dvi_i_selector;
  957.  
  958.         dvi_i_subconnector = drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
  959.                                     "subconnector",
  960.                                     drm_dvi_i_subconnector_enum_list,
  961.                                     ARRAY_SIZE(drm_dvi_i_subconnector_enum_list));
  962.         dev->mode_config.dvi_i_subconnector_property = dvi_i_subconnector;
  963.  
  964.         return 0;
  965. }
  966. EXPORT_SYMBOL(drm_mode_create_dvi_i_properties);
  967.  
  968. /**
  969.  * drm_create_tv_properties - create TV specific connector properties
  970.  * @dev: DRM device
  971.  * @num_modes: number of different TV formats (modes) supported
  972.  * @modes: array of pointers to strings containing name of each format
  973.  *
  974.  * Called by a driver's TV initialization routine, this function creates
  975.  * the TV specific connector properties for a given device.  Caller is
  976.  * responsible for allocating a list of format names and passing them to
  977.  * this routine.
  978.  */
  979. int drm_mode_create_tv_properties(struct drm_device *dev, int num_modes,
  980.                                   char *modes[])
  981. {
  982.         struct drm_property *tv_selector;
  983.         struct drm_property *tv_subconnector;
  984.         int i;
  985.  
  986.         if (dev->mode_config.tv_select_subconnector_property)
  987.                 return 0;
  988.  
  989.         /*
  990.          * Basic connector properties
  991.          */
  992.         tv_selector = drm_property_create_enum(dev, 0,
  993.                                           "select subconnector",
  994.                                           drm_tv_select_enum_list,
  995.                                           ARRAY_SIZE(drm_tv_select_enum_list));
  996.         dev->mode_config.tv_select_subconnector_property = tv_selector;
  997.  
  998.         tv_subconnector =
  999.                 drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
  1000.                                     "subconnector",
  1001.                                     drm_tv_subconnector_enum_list,
  1002.                                     ARRAY_SIZE(drm_tv_subconnector_enum_list));
  1003.         dev->mode_config.tv_subconnector_property = tv_subconnector;
  1004.  
  1005.         /*
  1006.          * Other, TV specific properties: margins & TV modes.
  1007.          */
  1008.         dev->mode_config.tv_left_margin_property =
  1009.                 drm_property_create_range(dev, 0, "left margin", 0, 100);
  1010.  
  1011.         dev->mode_config.tv_right_margin_property =
  1012.                 drm_property_create_range(dev, 0, "right margin", 0, 100);
  1013.  
  1014.         dev->mode_config.tv_top_margin_property =
  1015.                 drm_property_create_range(dev, 0, "top margin", 0, 100);
  1016.  
  1017.         dev->mode_config.tv_bottom_margin_property =
  1018.                 drm_property_create_range(dev, 0, "bottom margin", 0, 100);
  1019.  
  1020.         dev->mode_config.tv_mode_property =
  1021.                 drm_property_create(dev, DRM_MODE_PROP_ENUM,
  1022.                                     "mode", num_modes);
  1023.         for (i = 0; i < num_modes; i++)
  1024.                 drm_property_add_enum(dev->mode_config.tv_mode_property, i,
  1025.                                       i, modes[i]);
  1026.  
  1027.         dev->mode_config.tv_brightness_property =
  1028.                 drm_property_create_range(dev, 0, "brightness", 0, 100);
  1029.  
  1030.         dev->mode_config.tv_contrast_property =
  1031.                 drm_property_create_range(dev, 0, "contrast", 0, 100);
  1032.  
  1033.         dev->mode_config.tv_flicker_reduction_property =
  1034.                 drm_property_create_range(dev, 0, "flicker reduction", 0, 100);
  1035.  
  1036.         dev->mode_config.tv_overscan_property =
  1037.                 drm_property_create_range(dev, 0, "overscan", 0, 100);
  1038.  
  1039.         dev->mode_config.tv_saturation_property =
  1040.                 drm_property_create_range(dev, 0, "saturation", 0, 100);
  1041.  
  1042.         dev->mode_config.tv_hue_property =
  1043.                 drm_property_create_range(dev, 0, "hue", 0, 100);
  1044.  
  1045.         return 0;
  1046. }
  1047. EXPORT_SYMBOL(drm_mode_create_tv_properties);
  1048.  
  1049. /**
  1050.  * drm_mode_create_scaling_mode_property - create scaling mode property
  1051.  * @dev: DRM device
  1052.  *
  1053.  * Called by a driver the first time it's needed, must be attached to desired
  1054.  * connectors.
  1055.  */
  1056. int drm_mode_create_scaling_mode_property(struct drm_device *dev)
  1057. {
  1058.         struct drm_property *scaling_mode;
  1059.  
  1060.         if (dev->mode_config.scaling_mode_property)
  1061.                 return 0;
  1062.  
  1063.         scaling_mode =
  1064.                 drm_property_create_enum(dev, 0, "scaling mode",
  1065.                                 drm_scaling_mode_enum_list,
  1066.                                     ARRAY_SIZE(drm_scaling_mode_enum_list));
  1067.  
  1068.         dev->mode_config.scaling_mode_property = scaling_mode;
  1069.  
  1070.         return 0;
  1071. }
  1072. EXPORT_SYMBOL(drm_mode_create_scaling_mode_property);
  1073.  
  1074. /**
  1075.  * drm_mode_create_dithering_property - create dithering property
  1076.  * @dev: DRM device
  1077.  *
  1078.  * Called by a driver the first time it's needed, must be attached to desired
  1079.  * connectors.
  1080.  */
  1081. int drm_mode_create_dithering_property(struct drm_device *dev)
  1082. {
  1083.         struct drm_property *dithering_mode;
  1084.  
  1085.         if (dev->mode_config.dithering_mode_property)
  1086.                 return 0;
  1087.  
  1088.         dithering_mode =
  1089.                 drm_property_create_enum(dev, 0, "dithering",
  1090.                                 drm_dithering_mode_enum_list,
  1091.                                     ARRAY_SIZE(drm_dithering_mode_enum_list));
  1092.         dev->mode_config.dithering_mode_property = dithering_mode;
  1093.  
  1094.         return 0;
  1095. }
  1096. EXPORT_SYMBOL(drm_mode_create_dithering_property);
  1097.  
  1098. /**
  1099.  * drm_mode_create_dirty_property - create dirty property
  1100.  * @dev: DRM device
  1101.  *
  1102.  * Called by a driver the first time it's needed, must be attached to desired
  1103.  * connectors.
  1104.  */
  1105. int drm_mode_create_dirty_info_property(struct drm_device *dev)
  1106. {
  1107.         struct drm_property *dirty_info;
  1108.  
  1109.         if (dev->mode_config.dirty_info_property)
  1110.                 return 0;
  1111.  
  1112.         dirty_info =
  1113.                 drm_property_create_enum(dev, DRM_MODE_PROP_IMMUTABLE,
  1114.                                     "dirty",
  1115.                                     drm_dirty_info_enum_list,
  1116.                                     ARRAY_SIZE(drm_dirty_info_enum_list));
  1117.         dev->mode_config.dirty_info_property = dirty_info;
  1118.  
  1119.         return 0;
  1120. }
  1121. EXPORT_SYMBOL(drm_mode_create_dirty_info_property);
  1122.  
  1123. /**
  1124.  * drm_mode_config_init - initialize DRM mode_configuration structure
  1125.  * @dev: DRM device
  1126.  *
  1127.  * Initialize @dev's mode_config structure, used for tracking the graphics
  1128.  * configuration of @dev.
  1129.  *
  1130.  * Since this initializes the modeset locks, no locking is possible. Which is no
  1131.  * problem, since this should happen single threaded at init time. It is the
  1132.  * driver's problem to ensure this guarantee.
  1133.  *
  1134.  */
  1135. void drm_mode_config_init(struct drm_device *dev)
  1136. {
  1137.         mutex_init(&dev->mode_config.mutex);
  1138.         mutex_init(&dev->mode_config.idr_mutex);
  1139.         mutex_init(&dev->mode_config.fb_lock);
  1140.         INIT_LIST_HEAD(&dev->mode_config.fb_list);
  1141.         INIT_LIST_HEAD(&dev->mode_config.crtc_list);
  1142.         INIT_LIST_HEAD(&dev->mode_config.connector_list);
  1143.         INIT_LIST_HEAD(&dev->mode_config.encoder_list);
  1144.         INIT_LIST_HEAD(&dev->mode_config.property_list);
  1145.         INIT_LIST_HEAD(&dev->mode_config.property_blob_list);
  1146.         INIT_LIST_HEAD(&dev->mode_config.plane_list);
  1147.         idr_init(&dev->mode_config.crtc_idr);
  1148.  
  1149.         drm_modeset_lock_all(dev);
  1150.         drm_mode_create_standard_connector_properties(dev);
  1151.         drm_modeset_unlock_all(dev);
  1152.  
  1153.         /* Just to be sure */
  1154.         dev->mode_config.num_fb = 0;
  1155.         dev->mode_config.num_connector = 0;
  1156.         dev->mode_config.num_crtc = 0;
  1157.         dev->mode_config.num_encoder = 0;
  1158. }
  1159. EXPORT_SYMBOL(drm_mode_config_init);
  1160.  
  1161. int drm_mode_group_init(struct drm_device *dev, struct drm_mode_group *group)
  1162. {
  1163.         uint32_t total_objects = 0;
  1164.  
  1165.         total_objects += dev->mode_config.num_crtc;
  1166.         total_objects += dev->mode_config.num_connector;
  1167.         total_objects += dev->mode_config.num_encoder;
  1168.  
  1169.         group->id_list = kzalloc(total_objects * sizeof(uint32_t), GFP_KERNEL);
  1170.         if (!group->id_list)
  1171.                 return -ENOMEM;
  1172.  
  1173.         group->num_crtcs = 0;
  1174.         group->num_connectors = 0;
  1175.         group->num_encoders = 0;
  1176.         return 0;
  1177. }
  1178.  
  1179. int drm_mode_group_init_legacy_group(struct drm_device *dev,
  1180.                                      struct drm_mode_group *group)
  1181. {
  1182.         struct drm_crtc *crtc;
  1183.         struct drm_encoder *encoder;
  1184.         struct drm_connector *connector;
  1185.         int ret;
  1186.  
  1187.         if ((ret = drm_mode_group_init(dev, group)))
  1188.                 return ret;
  1189.  
  1190.         list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
  1191.                 group->id_list[group->num_crtcs++] = crtc->base.id;
  1192.  
  1193.         list_for_each_entry(encoder, &dev->mode_config.encoder_list, head)
  1194.                 group->id_list[group->num_crtcs + group->num_encoders++] =
  1195.                 encoder->base.id;
  1196.  
  1197.         list_for_each_entry(connector, &dev->mode_config.connector_list, head)
  1198.                 group->id_list[group->num_crtcs + group->num_encoders +
  1199.                                group->num_connectors++] = connector->base.id;
  1200.  
  1201.         return 0;
  1202. }
  1203. EXPORT_SYMBOL(drm_mode_group_init_legacy_group);
  1204.  
  1205. /**
  1206.  * drm_mode_config_cleanup - free up DRM mode_config info
  1207.  * @dev: DRM device
  1208.  *
  1209.  * Free up all the connectors and CRTCs associated with this DRM device, then
  1210.  * free up the framebuffers and associated buffer objects.
  1211.  *
  1212.  * Note that since this /should/ happen single-threaded at driver/device
  1213.  * teardown time, no locking is required. It's the driver's job to ensure that
  1214.  * this guarantee actually holds true.
  1215.  *
  1216.  * FIXME: cleanup any dangling user buffer objects too
  1217.  */
  1218. void drm_mode_config_cleanup(struct drm_device *dev)
  1219. {
  1220.         struct drm_connector *connector, *ot;
  1221.         struct drm_crtc *crtc, *ct;
  1222.         struct drm_encoder *encoder, *enct;
  1223.         struct drm_framebuffer *fb, *fbt;
  1224.         struct drm_property *property, *pt;
  1225.         struct drm_plane *plane, *plt;
  1226.  
  1227.         list_for_each_entry_safe(encoder, enct, &dev->mode_config.encoder_list,
  1228.                                  head) {
  1229.                 encoder->funcs->destroy(encoder);
  1230.         }
  1231.  
  1232.         list_for_each_entry_safe(connector, ot,
  1233.                                  &dev->mode_config.connector_list, head) {
  1234.                 connector->funcs->destroy(connector);
  1235.         }
  1236.  
  1237.         list_for_each_entry_safe(property, pt, &dev->mode_config.property_list,
  1238.                                  head) {
  1239.                 drm_property_destroy(dev, property);
  1240.         }
  1241.  
  1242.         /*
  1243.          * Single-threaded teardown context, so it's not required to grab the
  1244.          * fb_lock to protect against concurrent fb_list access. Contrary, it
  1245.          * would actually deadlock with the drm_framebuffer_cleanup function.
  1246.          *
  1247.          * Also, if there are any framebuffers left, that's a driver leak now,
  1248.          * so politely WARN about this.
  1249.          */
  1250.         WARN_ON(!list_empty(&dev->mode_config.fb_list));
  1251.         list_for_each_entry_safe(fb, fbt, &dev->mode_config.fb_list, head) {
  1252.                 drm_framebuffer_remove(fb);
  1253.         }
  1254.  
  1255.         list_for_each_entry_safe(plane, plt, &dev->mode_config.plane_list,
  1256.                                  head) {
  1257.                 plane->funcs->destroy(plane);
  1258.         }
  1259.  
  1260.         list_for_each_entry_safe(crtc, ct, &dev->mode_config.crtc_list, head) {
  1261.                 crtc->funcs->destroy(crtc);
  1262.         }
  1263.  
  1264.         idr_destroy(&dev->mode_config.crtc_idr);
  1265. }
  1266. EXPORT_SYMBOL(drm_mode_config_cleanup);
  1267.  
  1268. /**
  1269.  * drm_crtc_convert_to_umode - convert a drm_display_mode into a modeinfo
  1270.  * @out: drm_mode_modeinfo struct to return to the user
  1271.  * @in: drm_display_mode to use
  1272.  *
  1273.  * Convert a drm_display_mode into a drm_mode_modeinfo structure to return to
  1274.  * the user.
  1275.  */
  1276. static void drm_crtc_convert_to_umode(struct drm_mode_modeinfo *out,
  1277.                                       const struct drm_display_mode *in)
  1278. {
  1279.         WARN(in->hdisplay > USHRT_MAX || in->hsync_start > USHRT_MAX ||
  1280.              in->hsync_end > USHRT_MAX || in->htotal > USHRT_MAX ||
  1281.              in->hskew > USHRT_MAX || in->vdisplay > USHRT_MAX ||
  1282.              in->vsync_start > USHRT_MAX || in->vsync_end > USHRT_MAX ||
  1283.              in->vtotal > USHRT_MAX || in->vscan > USHRT_MAX,
  1284.              "timing values too large for mode info\n");
  1285.  
  1286.         out->clock = in->clock;
  1287.         out->hdisplay = in->hdisplay;
  1288.         out->hsync_start = in->hsync_start;
  1289.         out->hsync_end = in->hsync_end;
  1290.         out->htotal = in->htotal;
  1291.         out->hskew = in->hskew;
  1292.         out->vdisplay = in->vdisplay;
  1293.         out->vsync_start = in->vsync_start;
  1294.         out->vsync_end = in->vsync_end;
  1295.         out->vtotal = in->vtotal;
  1296.         out->vscan = in->vscan;
  1297.         out->vrefresh = in->vrefresh;
  1298.         out->flags = in->flags;
  1299.         out->type = in->type;
  1300.         strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
  1301.         out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
  1302. }
  1303.  
  1304. /**
  1305.  * drm_crtc_convert_to_umode - convert a modeinfo into a drm_display_mode
  1306.  * @out: drm_display_mode to return to the user
  1307.  * @in: drm_mode_modeinfo to use
  1308.  *
  1309.  * Convert a drm_mode_modeinfo into a drm_display_mode structure to return to
  1310.  * the caller.
  1311.  *
  1312.  * RETURNS:
  1313.  * Zero on success, errno on failure.
  1314.  */
  1315. static int drm_crtc_convert_umode(struct drm_display_mode *out,
  1316.                                   const struct drm_mode_modeinfo *in)
  1317. {
  1318.         if (in->clock > INT_MAX || in->vrefresh > INT_MAX)
  1319.                 return -ERANGE;
  1320.  
  1321.         out->clock = in->clock;
  1322.         out->hdisplay = in->hdisplay;
  1323.         out->hsync_start = in->hsync_start;
  1324.         out->hsync_end = in->hsync_end;
  1325.         out->htotal = in->htotal;
  1326.         out->hskew = in->hskew;
  1327.         out->vdisplay = in->vdisplay;
  1328.         out->vsync_start = in->vsync_start;
  1329.         out->vsync_end = in->vsync_end;
  1330.         out->vtotal = in->vtotal;
  1331.         out->vscan = in->vscan;
  1332.         out->vrefresh = in->vrefresh;
  1333.         out->flags = in->flags;
  1334.         out->type = in->type;
  1335.         strncpy(out->name, in->name, DRM_DISPLAY_MODE_LEN);
  1336.         out->name[DRM_DISPLAY_MODE_LEN-1] = 0;
  1337.  
  1338.         return 0;
  1339. }
  1340.  
  1341.  
  1342. #if 0
  1343. /**
  1344.  * drm_mode_getresources - get graphics configuration
  1345.  * @dev: drm device for the ioctl
  1346.  * @data: data pointer for the ioctl
  1347.  * @file_priv: drm file for the ioctl call
  1348.  *
  1349.  * Construct a set of configuration description structures and return
  1350.  * them to the user, including CRTC, connector and framebuffer configuration.
  1351.  *
  1352.  * Called by the user via ioctl.
  1353.  *
  1354.  * RETURNS:
  1355.  * Zero on success, errno on failure.
  1356.  */
  1357. int drm_mode_getresources(struct drm_device *dev, void *data,
  1358.                           struct drm_file *file_priv)
  1359. {
  1360.         struct drm_mode_card_res *card_res = data;
  1361.         struct list_head *lh;
  1362.         struct drm_framebuffer *fb;
  1363.         struct drm_connector *connector;
  1364.         struct drm_crtc *crtc;
  1365.         struct drm_encoder *encoder;
  1366.         int ret = 0;
  1367.         int connector_count = 0;
  1368.         int crtc_count = 0;
  1369.         int fb_count = 0;
  1370.         int encoder_count = 0;
  1371.         int copied = 0, i;
  1372.         uint32_t __user *fb_id;
  1373.         uint32_t __user *crtc_id;
  1374.         uint32_t __user *connector_id;
  1375.         uint32_t __user *encoder_id;
  1376.         struct drm_mode_group *mode_group;
  1377.  
  1378.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  1379.                 return -EINVAL;
  1380.  
  1381.  
  1382.         mutex_lock(&file_priv->fbs_lock);
  1383.         /*
  1384.          * For the non-control nodes we need to limit the list of resources
  1385.          * by IDs in the group list for this node
  1386.          */
  1387.         list_for_each(lh, &file_priv->fbs)
  1388.                 fb_count++;
  1389.  
  1390.         /* handle this in 4 parts */
  1391.         /* FBs */
  1392.         if (card_res->count_fbs >= fb_count) {
  1393.                 copied = 0;
  1394.                 fb_id = (uint32_t __user *)(unsigned long)card_res->fb_id_ptr;
  1395.                 list_for_each_entry(fb, &file_priv->fbs, filp_head) {
  1396.                         if (put_user(fb->base.id, fb_id + copied)) {
  1397.                                 mutex_unlock(&file_priv->fbs_lock);
  1398.                                 return -EFAULT;
  1399.                         }
  1400.                         copied++;
  1401.                 }
  1402.         }
  1403.         card_res->count_fbs = fb_count;
  1404.         mutex_unlock(&file_priv->fbs_lock);
  1405.  
  1406.         drm_modeset_lock_all(dev);
  1407.         mode_group = &file_priv->master->minor->mode_group;
  1408.         if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
  1409.  
  1410.                 list_for_each(lh, &dev->mode_config.crtc_list)
  1411.                         crtc_count++;
  1412.  
  1413.                 list_for_each(lh, &dev->mode_config.connector_list)
  1414.                         connector_count++;
  1415.  
  1416.                 list_for_each(lh, &dev->mode_config.encoder_list)
  1417.                         encoder_count++;
  1418.         } else {
  1419.  
  1420.                 crtc_count = mode_group->num_crtcs;
  1421.                 connector_count = mode_group->num_connectors;
  1422.                 encoder_count = mode_group->num_encoders;
  1423.         }
  1424.  
  1425.         card_res->max_height = dev->mode_config.max_height;
  1426.         card_res->min_height = dev->mode_config.min_height;
  1427.         card_res->max_width = dev->mode_config.max_width;
  1428.         card_res->min_width = dev->mode_config.min_width;
  1429.  
  1430.         /* CRTCs */
  1431.         if (card_res->count_crtcs >= crtc_count) {
  1432.                 copied = 0;
  1433.                 crtc_id = (uint32_t __user *)(unsigned long)card_res->crtc_id_ptr;
  1434.                 if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
  1435.                         list_for_each_entry(crtc, &dev->mode_config.crtc_list,
  1436.                                             head) {
  1437.                                 DRM_DEBUG_KMS("[CRTC:%d]\n", crtc->base.id);
  1438.                                 if (put_user(crtc->base.id, crtc_id + copied)) {
  1439.                                         ret = -EFAULT;
  1440.                                         goto out;
  1441.                                 }
  1442.                                 copied++;
  1443.                         }
  1444.                 } else {
  1445.                         for (i = 0; i < mode_group->num_crtcs; i++) {
  1446.                                 if (put_user(mode_group->id_list[i],
  1447.                                              crtc_id + copied)) {
  1448.                                         ret = -EFAULT;
  1449.                                         goto out;
  1450.                                 }
  1451.                                 copied++;
  1452.                         }
  1453.                 }
  1454.         }
  1455.         card_res->count_crtcs = crtc_count;
  1456.  
  1457.         /* Encoders */
  1458.         if (card_res->count_encoders >= encoder_count) {
  1459.                 copied = 0;
  1460.                 encoder_id = (uint32_t __user *)(unsigned long)card_res->encoder_id_ptr;
  1461.                 if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
  1462.                         list_for_each_entry(encoder,
  1463.                                             &dev->mode_config.encoder_list,
  1464.                                             head) {
  1465.                                 DRM_DEBUG_KMS("[ENCODER:%d:%s]\n", encoder->base.id,
  1466.                                                 drm_get_encoder_name(encoder));
  1467.                                 if (put_user(encoder->base.id, encoder_id +
  1468.                                              copied)) {
  1469.                                         ret = -EFAULT;
  1470.                                         goto out;
  1471.                                 }
  1472.                                 copied++;
  1473.                         }
  1474.                 } else {
  1475.                         for (i = mode_group->num_crtcs; i < mode_group->num_crtcs + mode_group->num_encoders; i++) {
  1476.                                 if (put_user(mode_group->id_list[i],
  1477.                                              encoder_id + copied)) {
  1478.                                         ret = -EFAULT;
  1479.                                         goto out;
  1480.                                 }
  1481.                                 copied++;
  1482.                         }
  1483.  
  1484.                 }
  1485.         }
  1486.         card_res->count_encoders = encoder_count;
  1487.  
  1488.         /* Connectors */
  1489.         if (card_res->count_connectors >= connector_count) {
  1490.                 copied = 0;
  1491.                 connector_id = (uint32_t __user *)(unsigned long)card_res->connector_id_ptr;
  1492.                 if (file_priv->master->minor->type == DRM_MINOR_CONTROL) {
  1493.                         list_for_each_entry(connector,
  1494.                                             &dev->mode_config.connector_list,
  1495.                                             head) {
  1496.                                 DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n",
  1497.                                         connector->base.id,
  1498.                                         drm_get_connector_name(connector));
  1499.                                 if (put_user(connector->base.id,
  1500.                                              connector_id + copied)) {
  1501.                                         ret = -EFAULT;
  1502.                                         goto out;
  1503.                                 }
  1504.                                 copied++;
  1505.                         }
  1506.                 } else {
  1507.                         int start = mode_group->num_crtcs +
  1508.                                 mode_group->num_encoders;
  1509.                         for (i = start; i < start + mode_group->num_connectors; i++) {
  1510.                                 if (put_user(mode_group->id_list[i],
  1511.                                              connector_id + copied)) {
  1512.                                         ret = -EFAULT;
  1513.                                         goto out;
  1514.                                 }
  1515.                                 copied++;
  1516.                         }
  1517.                 }
  1518.         }
  1519.         card_res->count_connectors = connector_count;
  1520.  
  1521.         DRM_DEBUG_KMS("CRTC[%d] CONNECTORS[%d] ENCODERS[%d]\n", card_res->count_crtcs,
  1522.                   card_res->count_connectors, card_res->count_encoders);
  1523.  
  1524. out:
  1525.         drm_modeset_unlock_all(dev);
  1526.         return ret;
  1527. }
  1528.  
  1529. /**
  1530.  * drm_mode_getcrtc - get CRTC configuration
  1531.  * @dev: drm device for the ioctl
  1532.  * @data: data pointer for the ioctl
  1533.  * @file_priv: drm file for the ioctl call
  1534.  *
  1535.  * Construct a CRTC configuration structure to return to the user.
  1536.  *
  1537.  * Called by the user via ioctl.
  1538.  *
  1539.  * RETURNS:
  1540.  * Zero on success, errno on failure.
  1541.  */
  1542. int drm_mode_getcrtc(struct drm_device *dev,
  1543.                      void *data, struct drm_file *file_priv)
  1544. {
  1545.         struct drm_mode_crtc *crtc_resp = data;
  1546.         struct drm_crtc *crtc;
  1547.         struct drm_mode_object *obj;
  1548.         int ret = 0;
  1549.  
  1550.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  1551.                 return -EINVAL;
  1552.  
  1553.         drm_modeset_lock_all(dev);
  1554.  
  1555.         obj = drm_mode_object_find(dev, crtc_resp->crtc_id,
  1556.                                    DRM_MODE_OBJECT_CRTC);
  1557.         if (!obj) {
  1558.                 ret = -EINVAL;
  1559.                 goto out;
  1560.         }
  1561.         crtc = obj_to_crtc(obj);
  1562.  
  1563.         crtc_resp->x = crtc->x;
  1564.         crtc_resp->y = crtc->y;
  1565.         crtc_resp->gamma_size = crtc->gamma_size;
  1566.         if (crtc->fb)
  1567.                 crtc_resp->fb_id = crtc->fb->base.id;
  1568.         else
  1569.                 crtc_resp->fb_id = 0;
  1570.  
  1571.         if (crtc->enabled) {
  1572.  
  1573.                 drm_crtc_convert_to_umode(&crtc_resp->mode, &crtc->mode);
  1574.                 crtc_resp->mode_valid = 1;
  1575.  
  1576.         } else {
  1577.                 crtc_resp->mode_valid = 0;
  1578.         }
  1579.  
  1580. out:
  1581.         drm_modeset_unlock_all(dev);
  1582.         return ret;
  1583. }
  1584.  
  1585. /**
  1586.  * drm_mode_getconnector - get connector configuration
  1587.  * @dev: drm device for the ioctl
  1588.  * @data: data pointer for the ioctl
  1589.  * @file_priv: drm file for the ioctl call
  1590.  *
  1591.  * Construct a connector configuration structure to return to the user.
  1592.  *
  1593.  * Called by the user via ioctl.
  1594.  *
  1595.  * RETURNS:
  1596.  * Zero on success, errno on failure.
  1597.  */
  1598. int drm_mode_getconnector(struct drm_device *dev, void *data,
  1599.                           struct drm_file *file_priv)
  1600. {
  1601.         struct drm_mode_get_connector *out_resp = data;
  1602.         struct drm_mode_object *obj;
  1603.         struct drm_connector *connector;
  1604.         struct drm_display_mode *mode;
  1605.         int mode_count = 0;
  1606.         int props_count = 0;
  1607.         int encoders_count = 0;
  1608.         int ret = 0;
  1609.         int copied = 0;
  1610.         int i;
  1611.         struct drm_mode_modeinfo u_mode;
  1612.         struct drm_mode_modeinfo __user *mode_ptr;
  1613.         uint32_t __user *prop_ptr;
  1614.         uint64_t __user *prop_values;
  1615.         uint32_t __user *encoder_ptr;
  1616.  
  1617.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  1618.                 return -EINVAL;
  1619.  
  1620.         memset(&u_mode, 0, sizeof(struct drm_mode_modeinfo));
  1621.  
  1622.         DRM_DEBUG_KMS("[CONNECTOR:%d:?]\n", out_resp->connector_id);
  1623.  
  1624.         mutex_lock(&dev->mode_config.mutex);
  1625.  
  1626.         obj = drm_mode_object_find(dev, out_resp->connector_id,
  1627.                                    DRM_MODE_OBJECT_CONNECTOR);
  1628.         if (!obj) {
  1629.                 ret = -EINVAL;
  1630.                 goto out;
  1631.         }
  1632.         connector = obj_to_connector(obj);
  1633.  
  1634.         props_count = connector->properties.count;
  1635.  
  1636.         for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
  1637.                 if (connector->encoder_ids[i] != 0) {
  1638.                         encoders_count++;
  1639.                 }
  1640.         }
  1641.  
  1642.         if (out_resp->count_modes == 0) {
  1643.                 connector->funcs->fill_modes(connector,
  1644.                                              dev->mode_config.max_width,
  1645.                                              dev->mode_config.max_height);
  1646.         }
  1647.  
  1648.         /* delayed so we get modes regardless of pre-fill_modes state */
  1649.         list_for_each_entry(mode, &connector->modes, head)
  1650.                 mode_count++;
  1651.  
  1652.         out_resp->connector_id = connector->base.id;
  1653.         out_resp->connector_type = connector->connector_type;
  1654.         out_resp->connector_type_id = connector->connector_type_id;
  1655.         out_resp->mm_width = connector->display_info.width_mm;
  1656.         out_resp->mm_height = connector->display_info.height_mm;
  1657.         out_resp->subpixel = connector->display_info.subpixel_order;
  1658.         out_resp->connection = connector->status;
  1659.         if (connector->encoder)
  1660.                 out_resp->encoder_id = connector->encoder->base.id;
  1661.         else
  1662.                 out_resp->encoder_id = 0;
  1663.  
  1664.         /*
  1665.          * This ioctl is called twice, once to determine how much space is
  1666.          * needed, and the 2nd time to fill it.
  1667.          */
  1668.         if ((out_resp->count_modes >= mode_count) && mode_count) {
  1669.                 copied = 0;
  1670.                 mode_ptr = (struct drm_mode_modeinfo __user *)(unsigned long)out_resp->modes_ptr;
  1671.                 list_for_each_entry(mode, &connector->modes, head) {
  1672.                         drm_crtc_convert_to_umode(&u_mode, mode);
  1673.                         if (copy_to_user(mode_ptr + copied,
  1674.                                          &u_mode, sizeof(u_mode))) {
  1675.                                 ret = -EFAULT;
  1676.                                 goto out;
  1677.                         }
  1678.                         copied++;
  1679.                 }
  1680.         }
  1681.         out_resp->count_modes = mode_count;
  1682.  
  1683.         if ((out_resp->count_props >= props_count) && props_count) {
  1684.                 copied = 0;
  1685.                 prop_ptr = (uint32_t __user *)(unsigned long)(out_resp->props_ptr);
  1686.                 prop_values = (uint64_t __user *)(unsigned long)(out_resp->prop_values_ptr);
  1687.                 for (i = 0; i < connector->properties.count; i++) {
  1688.                         if (put_user(connector->properties.ids[i],
  1689.                                              prop_ptr + copied)) {
  1690.                                         ret = -EFAULT;
  1691.                                         goto out;
  1692.                                 }
  1693.  
  1694.                         if (put_user(connector->properties.values[i],
  1695.                                              prop_values + copied)) {
  1696.                                         ret = -EFAULT;
  1697.                                         goto out;
  1698.                                 }
  1699.                                 copied++;
  1700.                         }
  1701.                 }
  1702.         out_resp->count_props = props_count;
  1703.  
  1704.         if ((out_resp->count_encoders >= encoders_count) && encoders_count) {
  1705.                 copied = 0;
  1706.                 encoder_ptr = (uint32_t __user *)(unsigned long)(out_resp->encoders_ptr);
  1707.                 for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
  1708.                         if (connector->encoder_ids[i] != 0) {
  1709.                                 if (put_user(connector->encoder_ids[i],
  1710.                                              encoder_ptr + copied)) {
  1711.                                         ret = -EFAULT;
  1712.                                         goto out;
  1713.                                 }
  1714.                                 copied++;
  1715.                         }
  1716.                 }
  1717.         }
  1718.         out_resp->count_encoders = encoders_count;
  1719.  
  1720. out:
  1721.         mutex_unlock(&dev->mode_config.mutex);
  1722.  
  1723.         return ret;
  1724. }
  1725.  
  1726. int drm_mode_getencoder(struct drm_device *dev, void *data,
  1727.                         struct drm_file *file_priv)
  1728. {
  1729.         struct drm_mode_get_encoder *enc_resp = data;
  1730.         struct drm_mode_object *obj;
  1731.         struct drm_encoder *encoder;
  1732.         int ret = 0;
  1733.  
  1734.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  1735.                 return -EINVAL;
  1736.  
  1737.         drm_modeset_lock_all(dev);
  1738.         obj = drm_mode_object_find(dev, enc_resp->encoder_id,
  1739.                                    DRM_MODE_OBJECT_ENCODER);
  1740.         if (!obj) {
  1741.                 ret = -EINVAL;
  1742.                 goto out;
  1743.         }
  1744.         encoder = obj_to_encoder(obj);
  1745.  
  1746.         if (encoder->crtc)
  1747.                 enc_resp->crtc_id = encoder->crtc->base.id;
  1748.         else
  1749.                 enc_resp->crtc_id = 0;
  1750.         enc_resp->encoder_type = encoder->encoder_type;
  1751.         enc_resp->encoder_id = encoder->base.id;
  1752.         enc_resp->possible_crtcs = encoder->possible_crtcs;
  1753.         enc_resp->possible_clones = encoder->possible_clones;
  1754.  
  1755. out:
  1756.         drm_modeset_unlock_all(dev);
  1757.         return ret;
  1758. }
  1759.  
  1760. /**
  1761.  * drm_mode_getplane_res - get plane info
  1762.  * @dev: DRM device
  1763.  * @data: ioctl data
  1764.  * @file_priv: DRM file info
  1765.  *
  1766.  * Return an plane count and set of IDs.
  1767.  */
  1768. int drm_mode_getplane_res(struct drm_device *dev, void *data,
  1769.                             struct drm_file *file_priv)
  1770. {
  1771.         struct drm_mode_get_plane_res *plane_resp = data;
  1772.         struct drm_mode_config *config;
  1773.         struct drm_plane *plane;
  1774.         uint32_t __user *plane_ptr;
  1775.         int copied = 0, ret = 0;
  1776.  
  1777.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  1778.                 return -EINVAL;
  1779.  
  1780.         drm_modeset_lock_all(dev);
  1781.         config = &dev->mode_config;
  1782.  
  1783.         /*
  1784.          * This ioctl is called twice, once to determine how much space is
  1785.          * needed, and the 2nd time to fill it.
  1786.          */
  1787.         if (config->num_plane &&
  1788.             (plane_resp->count_planes >= config->num_plane)) {
  1789.                 plane_ptr = (uint32_t __user *)(unsigned long)plane_resp->plane_id_ptr;
  1790.  
  1791.                 list_for_each_entry(plane, &config->plane_list, head) {
  1792.                         if (put_user(plane->base.id, plane_ptr + copied)) {
  1793.                                 ret = -EFAULT;
  1794.                                 goto out;
  1795.                         }
  1796.                         copied++;
  1797.                 }
  1798.         }
  1799.         plane_resp->count_planes = config->num_plane;
  1800.  
  1801. out:
  1802.         drm_modeset_unlock_all(dev);
  1803.         return ret;
  1804. }
  1805.  
  1806. /**
  1807.  * drm_mode_getplane - get plane info
  1808.  * @dev: DRM device
  1809.  * @data: ioctl data
  1810.  * @file_priv: DRM file info
  1811.  *
  1812.  * Return plane info, including formats supported, gamma size, any
  1813.  * current fb, etc.
  1814.  */
  1815. int drm_mode_getplane(struct drm_device *dev, void *data,
  1816.                         struct drm_file *file_priv)
  1817. {
  1818.         struct drm_mode_get_plane *plane_resp = data;
  1819.         struct drm_mode_object *obj;
  1820.         struct drm_plane *plane;
  1821.         uint32_t __user *format_ptr;
  1822.         int ret = 0;
  1823.  
  1824.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  1825.                 return -EINVAL;
  1826.  
  1827.         drm_modeset_lock_all(dev);
  1828.         obj = drm_mode_object_find(dev, plane_resp->plane_id,
  1829.                                    DRM_MODE_OBJECT_PLANE);
  1830.         if (!obj) {
  1831.                 ret = -ENOENT;
  1832.                 goto out;
  1833.         }
  1834.         plane = obj_to_plane(obj);
  1835.  
  1836.         if (plane->crtc)
  1837.                 plane_resp->crtc_id = plane->crtc->base.id;
  1838.         else
  1839.                 plane_resp->crtc_id = 0;
  1840.  
  1841.         if (plane->fb)
  1842.                 plane_resp->fb_id = plane->fb->base.id;
  1843.         else
  1844.                 plane_resp->fb_id = 0;
  1845.  
  1846.         plane_resp->plane_id = plane->base.id;
  1847.         plane_resp->possible_crtcs = plane->possible_crtcs;
  1848.         plane_resp->gamma_size = plane->gamma_size;
  1849.  
  1850.         /*
  1851.          * This ioctl is called twice, once to determine how much space is
  1852.          * needed, and the 2nd time to fill it.
  1853.          */
  1854.         if (plane->format_count &&
  1855.             (plane_resp->count_format_types >= plane->format_count)) {
  1856.                 format_ptr = (uint32_t __user *)(unsigned long)plane_resp->format_type_ptr;
  1857.                 if (copy_to_user(format_ptr,
  1858.                                  plane->format_types,
  1859.                                  sizeof(uint32_t) * plane->format_count)) {
  1860.                         ret = -EFAULT;
  1861.                         goto out;
  1862.                 }
  1863.         }
  1864.         plane_resp->count_format_types = plane->format_count;
  1865.  
  1866. out:
  1867.         drm_modeset_unlock_all(dev);
  1868.         return ret;
  1869. }
  1870.  
  1871. /**
  1872.  * drm_mode_setplane - set up or tear down an plane
  1873.  * @dev: DRM device
  1874.  * @data: ioctl data*
  1875.  * @file_priv: DRM file info
  1876.  *
  1877.  * Set plane info, including placement, fb, scaling, and other factors.
  1878.  * Or pass a NULL fb to disable.
  1879.  */
  1880. int drm_mode_setplane(struct drm_device *dev, void *data,
  1881.                         struct drm_file *file_priv)
  1882. {
  1883.         struct drm_mode_set_plane *plane_req = data;
  1884.         struct drm_mode_object *obj;
  1885.         struct drm_plane *plane;
  1886.         struct drm_crtc *crtc;
  1887.         struct drm_framebuffer *fb = NULL, *old_fb = NULL;
  1888.         int ret = 0;
  1889.         unsigned int fb_width, fb_height;
  1890.         int i;
  1891.  
  1892.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  1893.                 return -EINVAL;
  1894.  
  1895.         /*
  1896.          * First, find the plane, crtc, and fb objects.  If not available,
  1897.          * we don't bother to call the driver.
  1898.          */
  1899.         obj = drm_mode_object_find(dev, plane_req->plane_id,
  1900.                                    DRM_MODE_OBJECT_PLANE);
  1901.         if (!obj) {
  1902.                 DRM_DEBUG_KMS("Unknown plane ID %d\n",
  1903.                               plane_req->plane_id);
  1904.                 return -ENOENT;
  1905.         }
  1906.         plane = obj_to_plane(obj);
  1907.  
  1908.         /* No fb means shut it down */
  1909.         if (!plane_req->fb_id) {
  1910.                 drm_modeset_lock_all(dev);
  1911.                 old_fb = plane->fb;
  1912.                 plane->funcs->disable_plane(plane);
  1913.                 plane->crtc = NULL;
  1914.                 plane->fb = NULL;
  1915.                 drm_modeset_unlock_all(dev);
  1916.                 goto out;
  1917.         }
  1918.  
  1919.         obj = drm_mode_object_find(dev, plane_req->crtc_id,
  1920.                                    DRM_MODE_OBJECT_CRTC);
  1921.         if (!obj) {
  1922.                 DRM_DEBUG_KMS("Unknown crtc ID %d\n",
  1923.                               plane_req->crtc_id);
  1924.                 ret = -ENOENT;
  1925.                 goto out;
  1926.         }
  1927.         crtc = obj_to_crtc(obj);
  1928.  
  1929.         fb = drm_framebuffer_lookup(dev, plane_req->fb_id);
  1930.         if (!fb) {
  1931.                 DRM_DEBUG_KMS("Unknown framebuffer ID %d\n",
  1932.                               plane_req->fb_id);
  1933.                 ret = -ENOENT;
  1934.                 goto out;
  1935.         }
  1936.  
  1937.         /* Check whether this plane supports the fb pixel format. */
  1938.         for (i = 0; i < plane->format_count; i++)
  1939.                 if (fb->pixel_format == plane->format_types[i])
  1940.                         break;
  1941.         if (i == plane->format_count) {
  1942.                 DRM_DEBUG_KMS("Invalid pixel format 0x%08x\n", fb->pixel_format);
  1943.                 ret = -EINVAL;
  1944.                 goto out;
  1945.         }
  1946.  
  1947.         fb_width = fb->width << 16;
  1948.         fb_height = fb->height << 16;
  1949.  
  1950.         /* Make sure source coordinates are inside the fb. */
  1951.         if (plane_req->src_w > fb_width ||
  1952.             plane_req->src_x > fb_width - plane_req->src_w ||
  1953.             plane_req->src_h > fb_height ||
  1954.             plane_req->src_y > fb_height - plane_req->src_h) {
  1955.                 DRM_DEBUG_KMS("Invalid source coordinates "
  1956.                               "%u.%06ux%u.%06u+%u.%06u+%u.%06u\n",
  1957.                               plane_req->src_w >> 16,
  1958.                               ((plane_req->src_w & 0xffff) * 15625) >> 10,
  1959.                               plane_req->src_h >> 16,
  1960.                               ((plane_req->src_h & 0xffff) * 15625) >> 10,
  1961.                               plane_req->src_x >> 16,
  1962.                               ((plane_req->src_x & 0xffff) * 15625) >> 10,
  1963.                               plane_req->src_y >> 16,
  1964.                               ((plane_req->src_y & 0xffff) * 15625) >> 10);
  1965.                 ret = -ENOSPC;
  1966.                 goto out;
  1967.         }
  1968.  
  1969.         /* Give drivers some help against integer overflows */
  1970.         if (plane_req->crtc_w > INT_MAX ||
  1971.             plane_req->crtc_x > INT_MAX - (int32_t) plane_req->crtc_w ||
  1972.             plane_req->crtc_h > INT_MAX ||
  1973.             plane_req->crtc_y > INT_MAX - (int32_t) plane_req->crtc_h) {
  1974.                 DRM_DEBUG_KMS("Invalid CRTC coordinates %ux%u+%d+%d\n",
  1975.                               plane_req->crtc_w, plane_req->crtc_h,
  1976.                               plane_req->crtc_x, plane_req->crtc_y);
  1977.                 ret = -ERANGE;
  1978.                 goto out;
  1979.         }
  1980.  
  1981.         drm_modeset_lock_all(dev);
  1982.         ret = plane->funcs->update_plane(plane, crtc, fb,
  1983.                                          plane_req->crtc_x, plane_req->crtc_y,
  1984.                                          plane_req->crtc_w, plane_req->crtc_h,
  1985.                                          plane_req->src_x, plane_req->src_y,
  1986.                                          plane_req->src_w, plane_req->src_h);
  1987.         if (!ret) {
  1988.                 old_fb = plane->fb;
  1989.                 plane->crtc = crtc;
  1990.                 plane->fb = fb;
  1991.                 fb = NULL;
  1992.         }
  1993.         drm_modeset_unlock_all(dev);
  1994.  
  1995. out:
  1996.         if (fb)
  1997.                 drm_framebuffer_unreference(fb);
  1998.         if (old_fb)
  1999.                 drm_framebuffer_unreference(old_fb);
  2000.  
  2001.         return ret;
  2002. }
  2003. #endif
  2004.  
  2005. /**
  2006.  * drm_mode_set_config_internal - helper to call ->set_config
  2007.  * @set: modeset config to set
  2008.  *
  2009.  * This is a little helper to wrap internal calls to the ->set_config driver
  2010.  * interface. The only thing it adds is correct refcounting dance.
  2011.  */
  2012. int drm_mode_set_config_internal(struct drm_mode_set *set)
  2013. {
  2014.         struct drm_crtc *crtc = set->crtc;
  2015.         struct drm_framebuffer *fb, *old_fb;
  2016.         int ret;
  2017.  
  2018.         old_fb = crtc->fb;
  2019.         fb = set->fb;
  2020.  
  2021.         ret = crtc->funcs->set_config(set);
  2022.         if (ret == 0) {
  2023.                 if (old_fb)
  2024.                         drm_framebuffer_unreference(old_fb);
  2025.                 if (fb)
  2026.                         drm_framebuffer_reference(fb);
  2027.         }
  2028.  
  2029.         return ret;
  2030. }
  2031. EXPORT_SYMBOL(drm_mode_set_config_internal);
  2032.  
  2033. #if 0
  2034. /**
  2035.  * drm_mode_setcrtc - set CRTC configuration
  2036.  * @dev: drm device for the ioctl
  2037.  * @data: data pointer for the ioctl
  2038.  * @file_priv: drm file for the ioctl call
  2039.  *
  2040.  * Build a new CRTC configuration based on user request.
  2041.  *
  2042.  * Called by the user via ioctl.
  2043.  *
  2044.  * RETURNS:
  2045.  * Zero on success, errno on failure.
  2046.  */
  2047. int drm_mode_setcrtc(struct drm_device *dev, void *data,
  2048.                      struct drm_file *file_priv)
  2049. {
  2050.         struct drm_mode_config *config = &dev->mode_config;
  2051.         struct drm_mode_crtc *crtc_req = data;
  2052.         struct drm_mode_object *obj;
  2053.         struct drm_crtc *crtc;
  2054.         struct drm_connector **connector_set = NULL, *connector;
  2055.         struct drm_framebuffer *fb = NULL;
  2056.         struct drm_display_mode *mode = NULL;
  2057.         struct drm_mode_set set;
  2058.         uint32_t __user *set_connectors_ptr;
  2059.         int ret;
  2060.         int i;
  2061.  
  2062.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2063.                 return -EINVAL;
  2064.  
  2065.         /* For some reason crtc x/y offsets are signed internally. */
  2066.         if (crtc_req->x > INT_MAX || crtc_req->y > INT_MAX)
  2067.                 return -ERANGE;
  2068.  
  2069.         drm_modeset_lock_all(dev);
  2070.         obj = drm_mode_object_find(dev, crtc_req->crtc_id,
  2071.                                    DRM_MODE_OBJECT_CRTC);
  2072.         if (!obj) {
  2073.                 DRM_DEBUG_KMS("Unknown CRTC ID %d\n", crtc_req->crtc_id);
  2074.                 ret = -EINVAL;
  2075.                 goto out;
  2076.         }
  2077.         crtc = obj_to_crtc(obj);
  2078.         DRM_DEBUG_KMS("[CRTC:%d]\n", crtc->base.id);
  2079.  
  2080.         if (crtc_req->mode_valid) {
  2081.                 int hdisplay, vdisplay;
  2082.                 /* If we have a mode we need a framebuffer. */
  2083.                 /* If we pass -1, set the mode with the currently bound fb */
  2084.                 if (crtc_req->fb_id == -1) {
  2085.                         if (!crtc->fb) {
  2086.                                 DRM_DEBUG_KMS("CRTC doesn't have current FB\n");
  2087.                                 ret = -EINVAL;
  2088.                                 goto out;
  2089.                         }
  2090.                                         fb = crtc->fb;
  2091.                         /* Make refcounting symmetric with the lookup path. */
  2092.                         drm_framebuffer_reference(fb);
  2093.                 } else {
  2094.                         fb = drm_framebuffer_lookup(dev, crtc_req->fb_id);
  2095.                         if (!fb) {
  2096.                                 DRM_DEBUG_KMS("Unknown FB ID%d\n",
  2097.                                                 crtc_req->fb_id);
  2098.                                 ret = -EINVAL;
  2099.                                 goto out;
  2100.                         }
  2101.                 }
  2102.  
  2103.                 mode = drm_mode_create(dev);
  2104.                 if (!mode) {
  2105.                         ret = -ENOMEM;
  2106.                         goto out;
  2107.                 }
  2108.  
  2109.                 ret = drm_crtc_convert_umode(mode, &crtc_req->mode);
  2110.                 if (ret) {
  2111.                         DRM_DEBUG_KMS("Invalid mode\n");
  2112.                         goto out;
  2113.                 }
  2114.  
  2115.                 drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
  2116.  
  2117.                 hdisplay = mode->hdisplay;
  2118.                 vdisplay = mode->vdisplay;
  2119.  
  2120.                 if (crtc->invert_dimensions)
  2121.                         swap(hdisplay, vdisplay);
  2122.  
  2123.                 if (hdisplay > fb->width ||
  2124.                     vdisplay > fb->height ||
  2125.                     crtc_req->x > fb->width - hdisplay ||
  2126.                     crtc_req->y > fb->height - vdisplay) {
  2127.                         DRM_DEBUG_KMS("Invalid fb size %ux%u for CRTC viewport %ux%u+%d+%d%s.\n",
  2128.                                       fb->width, fb->height,
  2129.                                       hdisplay, vdisplay, crtc_req->x, crtc_req->y,
  2130.                                       crtc->invert_dimensions ? " (inverted)" : "");
  2131.                         ret = -ENOSPC;
  2132.                         goto out;
  2133.                 }
  2134.         }
  2135.  
  2136.         if (crtc_req->count_connectors == 0 && mode) {
  2137.                 DRM_DEBUG_KMS("Count connectors is 0 but mode set\n");
  2138.                 ret = -EINVAL;
  2139.                 goto out;
  2140.         }
  2141.  
  2142.         if (crtc_req->count_connectors > 0 && (!mode || !fb)) {
  2143.                 DRM_DEBUG_KMS("Count connectors is %d but no mode or fb set\n",
  2144.                           crtc_req->count_connectors);
  2145.                 ret = -EINVAL;
  2146.                 goto out;
  2147.         }
  2148.  
  2149.         if (crtc_req->count_connectors > 0) {
  2150.                 u32 out_id;
  2151.  
  2152.                 /* Avoid unbounded kernel memory allocation */
  2153.                 if (crtc_req->count_connectors > config->num_connector) {
  2154.                         ret = -EINVAL;
  2155.                         goto out;
  2156.                 }
  2157.  
  2158.                 connector_set = kmalloc(crtc_req->count_connectors *
  2159.                                         sizeof(struct drm_connector *),
  2160.                                         GFP_KERNEL);
  2161.                 if (!connector_set) {
  2162.                         ret = -ENOMEM;
  2163.                         goto out;
  2164.                 }
  2165.  
  2166.                 for (i = 0; i < crtc_req->count_connectors; i++) {
  2167.                         set_connectors_ptr = (uint32_t __user *)(unsigned long)crtc_req->set_connectors_ptr;
  2168.                         if (get_user(out_id, &set_connectors_ptr[i])) {
  2169.                                 ret = -EFAULT;
  2170.                                 goto out;
  2171.                         }
  2172.  
  2173.                         obj = drm_mode_object_find(dev, out_id,
  2174.                                                    DRM_MODE_OBJECT_CONNECTOR);
  2175.                         if (!obj) {
  2176.                                 DRM_DEBUG_KMS("Connector id %d unknown\n",
  2177.                                                 out_id);
  2178.                                 ret = -EINVAL;
  2179.                                 goto out;
  2180.                         }
  2181.                         connector = obj_to_connector(obj);
  2182.                         DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n",
  2183.                                         connector->base.id,
  2184.                                         drm_get_connector_name(connector));
  2185.  
  2186.                         connector_set[i] = connector;
  2187.                 }
  2188.         }
  2189.  
  2190.         set.crtc = crtc;
  2191.         set.x = crtc_req->x;
  2192.         set.y = crtc_req->y;
  2193.         set.mode = mode;
  2194.         set.connectors = connector_set;
  2195.         set.num_connectors = crtc_req->count_connectors;
  2196.         set.fb = fb;
  2197.         ret = drm_mode_set_config_internal(&set);
  2198.  
  2199. out:
  2200.         if (fb)
  2201.                 drm_framebuffer_unreference(fb);
  2202.  
  2203.         kfree(connector_set);
  2204.         drm_mode_destroy(dev, mode);
  2205.         drm_modeset_unlock_all(dev);
  2206.         return ret;
  2207. }
  2208.  
  2209. int drm_mode_cursor_ioctl(struct drm_device *dev,
  2210.                         void *data, struct drm_file *file_priv)
  2211. {
  2212.         struct drm_mode_cursor *req = data;
  2213.         struct drm_mode_object *obj;
  2214.         struct drm_crtc *crtc;
  2215.         int ret = 0;
  2216.  
  2217.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2218.                 return -EINVAL;
  2219.  
  2220.         if (!req->flags || (~DRM_MODE_CURSOR_FLAGS & req->flags))
  2221.                 return -EINVAL;
  2222.  
  2223.         obj = drm_mode_object_find(dev, req->crtc_id, DRM_MODE_OBJECT_CRTC);
  2224.         if (!obj) {
  2225.                 DRM_DEBUG_KMS("Unknown CRTC ID %d\n", req->crtc_id);
  2226.                 return -EINVAL;
  2227.         }
  2228.         crtc = obj_to_crtc(obj);
  2229.  
  2230.         mutex_lock(&crtc->mutex);
  2231.         if (req->flags & DRM_MODE_CURSOR_BO) {
  2232.                 if (!crtc->funcs->cursor_set) {
  2233.                         ret = -ENXIO;
  2234.                         goto out;
  2235.                 }
  2236.                 /* Turns off the cursor if handle is 0 */
  2237.                 ret = crtc->funcs->cursor_set(crtc, file_priv, req->handle,
  2238.                                               req->width, req->height);
  2239.         }
  2240.  
  2241.         if (req->flags & DRM_MODE_CURSOR_MOVE) {
  2242.                 if (crtc->funcs->cursor_move) {
  2243.                         ret = crtc->funcs->cursor_move(crtc, req->x, req->y);
  2244.                 } else {
  2245.                         ret = -EFAULT;
  2246.                         goto out;
  2247.                 }
  2248.         }
  2249. out:
  2250.         mutex_unlock(&crtc->mutex);
  2251.  
  2252.         return ret;
  2253. }
  2254. #endif
  2255. /* Original addfb only supported RGB formats, so figure out which one */
  2256. uint32_t drm_mode_legacy_fb_format(uint32_t bpp, uint32_t depth)
  2257. {
  2258.         uint32_t fmt;
  2259.  
  2260.         switch (bpp) {
  2261.         case 8:
  2262.                 fmt = DRM_FORMAT_C8;
  2263.                 break;
  2264.         case 16:
  2265.                 if (depth == 15)
  2266.                         fmt = DRM_FORMAT_XRGB1555;
  2267.                 else
  2268.                         fmt = DRM_FORMAT_RGB565;
  2269.                 break;
  2270.         case 24:
  2271.                 fmt = DRM_FORMAT_RGB888;
  2272.                 break;
  2273.         case 32:
  2274.                 if (depth == 24)
  2275.                         fmt = DRM_FORMAT_XRGB8888;
  2276.                 else if (depth == 30)
  2277.                         fmt = DRM_FORMAT_XRGB2101010;
  2278.                 else
  2279.                         fmt = DRM_FORMAT_ARGB8888;
  2280.                 break;
  2281.         default:
  2282.                 DRM_ERROR("bad bpp, assuming x8r8g8b8 pixel format\n");
  2283.                 fmt = DRM_FORMAT_XRGB8888;
  2284.                 break;
  2285.         }
  2286.  
  2287.         return fmt;
  2288. }
  2289. EXPORT_SYMBOL(drm_mode_legacy_fb_format);
  2290. #if 0
  2291. /**
  2292.  * drm_mode_addfb - add an FB to the graphics configuration
  2293.  * @dev: drm device for the ioctl
  2294.  * @data: data pointer for the ioctl
  2295.  * @file_priv: drm file for the ioctl call
  2296.  *
  2297.  * Add a new FB to the specified CRTC, given a user request.
  2298.  *
  2299.  * Called by the user via ioctl.
  2300.  *
  2301.  * RETURNS:
  2302.  * Zero on success, errno on failure.
  2303.  */
  2304. int drm_mode_addfb(struct drm_device *dev,
  2305.                    void *data, struct drm_file *file_priv)
  2306. {
  2307.         struct drm_mode_fb_cmd *or = data;
  2308.         struct drm_mode_fb_cmd2 r = {};
  2309.         struct drm_mode_config *config = &dev->mode_config;
  2310.         struct drm_framebuffer *fb;
  2311.         int ret = 0;
  2312.  
  2313.         /* Use new struct with format internally */
  2314.         r.fb_id = or->fb_id;
  2315.         r.width = or->width;
  2316.         r.height = or->height;
  2317.         r.pitches[0] = or->pitch;
  2318.         r.pixel_format = drm_mode_legacy_fb_format(or->bpp, or->depth);
  2319.         r.handles[0] = or->handle;
  2320.  
  2321.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2322.                 return -EINVAL;
  2323.  
  2324.         if ((config->min_width > r.width) || (r.width > config->max_width))
  2325.                 return -EINVAL;
  2326.  
  2327.         if ((config->min_height > r.height) || (r.height > config->max_height))
  2328.                 return -EINVAL;
  2329.  
  2330.         fb = dev->mode_config.funcs->fb_create(dev, file_priv, &r);
  2331.         if (IS_ERR(fb)) {
  2332.                 DRM_DEBUG_KMS("could not create framebuffer\n");
  2333.                 return PTR_ERR(fb);
  2334.         }
  2335.  
  2336.         mutex_lock(&file_priv->fbs_lock);
  2337.         or->fb_id = fb->base.id;
  2338.         list_add(&fb->filp_head, &file_priv->fbs);
  2339.         DRM_DEBUG_KMS("[FB:%d]\n", fb->base.id);
  2340.         mutex_unlock(&file_priv->fbs_lock);
  2341.  
  2342.         return ret;
  2343. }
  2344.  
  2345. static int format_check(const struct drm_mode_fb_cmd2 *r)
  2346. {
  2347.         uint32_t format = r->pixel_format & ~DRM_FORMAT_BIG_ENDIAN;
  2348.  
  2349.         switch (format) {
  2350.         case DRM_FORMAT_C8:
  2351.         case DRM_FORMAT_RGB332:
  2352.         case DRM_FORMAT_BGR233:
  2353.         case DRM_FORMAT_XRGB4444:
  2354.         case DRM_FORMAT_XBGR4444:
  2355.         case DRM_FORMAT_RGBX4444:
  2356.         case DRM_FORMAT_BGRX4444:
  2357.         case DRM_FORMAT_ARGB4444:
  2358.         case DRM_FORMAT_ABGR4444:
  2359.         case DRM_FORMAT_RGBA4444:
  2360.         case DRM_FORMAT_BGRA4444:
  2361.         case DRM_FORMAT_XRGB1555:
  2362.         case DRM_FORMAT_XBGR1555:
  2363.         case DRM_FORMAT_RGBX5551:
  2364.         case DRM_FORMAT_BGRX5551:
  2365.         case DRM_FORMAT_ARGB1555:
  2366.         case DRM_FORMAT_ABGR1555:
  2367.         case DRM_FORMAT_RGBA5551:
  2368.         case DRM_FORMAT_BGRA5551:
  2369.         case DRM_FORMAT_RGB565:
  2370.         case DRM_FORMAT_BGR565:
  2371.         case DRM_FORMAT_RGB888:
  2372.         case DRM_FORMAT_BGR888:
  2373.         case DRM_FORMAT_XRGB8888:
  2374.         case DRM_FORMAT_XBGR8888:
  2375.         case DRM_FORMAT_RGBX8888:
  2376.         case DRM_FORMAT_BGRX8888:
  2377.         case DRM_FORMAT_ARGB8888:
  2378.         case DRM_FORMAT_ABGR8888:
  2379.         case DRM_FORMAT_RGBA8888:
  2380.         case DRM_FORMAT_BGRA8888:
  2381.         case DRM_FORMAT_XRGB2101010:
  2382.         case DRM_FORMAT_XBGR2101010:
  2383.         case DRM_FORMAT_RGBX1010102:
  2384.         case DRM_FORMAT_BGRX1010102:
  2385.         case DRM_FORMAT_ARGB2101010:
  2386.         case DRM_FORMAT_ABGR2101010:
  2387.         case DRM_FORMAT_RGBA1010102:
  2388.         case DRM_FORMAT_BGRA1010102:
  2389.         case DRM_FORMAT_YUYV:
  2390.         case DRM_FORMAT_YVYU:
  2391.         case DRM_FORMAT_UYVY:
  2392.         case DRM_FORMAT_VYUY:
  2393.         case DRM_FORMAT_AYUV:
  2394.         case DRM_FORMAT_NV12:
  2395.         case DRM_FORMAT_NV21:
  2396.         case DRM_FORMAT_NV16:
  2397.         case DRM_FORMAT_NV61:
  2398.         case DRM_FORMAT_NV24:
  2399.         case DRM_FORMAT_NV42:
  2400.         case DRM_FORMAT_YUV410:
  2401.         case DRM_FORMAT_YVU410:
  2402.         case DRM_FORMAT_YUV411:
  2403.         case DRM_FORMAT_YVU411:
  2404.         case DRM_FORMAT_YUV420:
  2405.         case DRM_FORMAT_YVU420:
  2406.         case DRM_FORMAT_YUV422:
  2407.         case DRM_FORMAT_YVU422:
  2408.         case DRM_FORMAT_YUV444:
  2409.         case DRM_FORMAT_YVU444:
  2410.                 return 0;
  2411.         default:
  2412.                 return -EINVAL;
  2413.         }
  2414. }
  2415.  
  2416. static int framebuffer_check(const struct drm_mode_fb_cmd2 *r)
  2417. {
  2418.         int ret, hsub, vsub, num_planes, i;
  2419.  
  2420.         ret = format_check(r);
  2421.         if (ret) {
  2422.                 DRM_DEBUG_KMS("bad framebuffer format 0x%08x\n", r->pixel_format);
  2423.                 return ret;
  2424.         }
  2425.  
  2426.         hsub = drm_format_horz_chroma_subsampling(r->pixel_format);
  2427.         vsub = drm_format_vert_chroma_subsampling(r->pixel_format);
  2428.         num_planes = drm_format_num_planes(r->pixel_format);
  2429.  
  2430.         if (r->width == 0 || r->width % hsub) {
  2431.                 DRM_DEBUG_KMS("bad framebuffer width %u\n", r->height);
  2432.                 return -EINVAL;
  2433.         }
  2434.  
  2435.         if (r->height == 0 || r->height % vsub) {
  2436.                 DRM_DEBUG_KMS("bad framebuffer height %u\n", r->height);
  2437.                 return -EINVAL;
  2438.         }
  2439.  
  2440.         for (i = 0; i < num_planes; i++) {
  2441.                 unsigned int width = r->width / (i != 0 ? hsub : 1);
  2442.                 unsigned int height = r->height / (i != 0 ? vsub : 1);
  2443.                 unsigned int cpp = drm_format_plane_cpp(r->pixel_format, i);
  2444.  
  2445.                 if (!r->handles[i]) {
  2446.                         DRM_DEBUG_KMS("no buffer object handle for plane %d\n", i);
  2447.                         return -EINVAL;
  2448.                 }
  2449.  
  2450.                 if ((uint64_t) width * cpp > UINT_MAX)
  2451.                         return -ERANGE;
  2452.  
  2453.                 if ((uint64_t) height * r->pitches[i] + r->offsets[i] > UINT_MAX)
  2454.                         return -ERANGE;
  2455.  
  2456.                 if (r->pitches[i] < width * cpp) {
  2457.                         DRM_DEBUG_KMS("bad pitch %u for plane %d\n", r->pitches[i], i);
  2458.                         return -EINVAL;
  2459.                 }
  2460.         }
  2461.  
  2462.         return 0;
  2463. }
  2464.  
  2465. /**
  2466.  * drm_mode_addfb2 - add an FB to the graphics configuration
  2467.  * @dev: drm device for the ioctl
  2468.  * @data: data pointer for the ioctl
  2469.  * @file_priv: drm file for the ioctl call
  2470.  *
  2471.  * Add a new FB to the specified CRTC, given a user request with format.
  2472.  *
  2473.  * Called by the user via ioctl.
  2474.  *
  2475.  * RETURNS:
  2476.  * Zero on success, errno on failure.
  2477.  */
  2478. int drm_mode_addfb2(struct drm_device *dev,
  2479.                     void *data, struct drm_file *file_priv)
  2480. {
  2481.         struct drm_mode_fb_cmd2 *r = data;
  2482.         struct drm_mode_config *config = &dev->mode_config;
  2483.         struct drm_framebuffer *fb;
  2484.         int ret;
  2485.  
  2486.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2487.                 return -EINVAL;
  2488.  
  2489.         if (r->flags & ~DRM_MODE_FB_INTERLACED) {
  2490.                 DRM_DEBUG_KMS("bad framebuffer flags 0x%08x\n", r->flags);
  2491.                 return -EINVAL;
  2492.         }
  2493.  
  2494.         if ((config->min_width > r->width) || (r->width > config->max_width)) {
  2495.                 DRM_DEBUG_KMS("bad framebuffer width %d, should be >= %d && <= %d\n",
  2496.                           r->width, config->min_width, config->max_width);
  2497.                 return -EINVAL;
  2498.         }
  2499.         if ((config->min_height > r->height) || (r->height > config->max_height)) {
  2500.                 DRM_DEBUG_KMS("bad framebuffer height %d, should be >= %d && <= %d\n",
  2501.                           r->height, config->min_height, config->max_height);
  2502.                 return -EINVAL;
  2503.         }
  2504.  
  2505.         ret = framebuffer_check(r);
  2506.         if (ret)
  2507.                 return ret;
  2508.  
  2509.         fb = dev->mode_config.funcs->fb_create(dev, file_priv, r);
  2510.         if (IS_ERR(fb)) {
  2511.                 DRM_DEBUG_KMS("could not create framebuffer\n");
  2512.                 return PTR_ERR(fb);
  2513.         }
  2514.  
  2515.         mutex_lock(&file_priv->fbs_lock);
  2516.         r->fb_id = fb->base.id;
  2517.         list_add(&fb->filp_head, &file_priv->fbs);
  2518.         DRM_DEBUG_KMS("[FB:%d]\n", fb->base.id);
  2519.         mutex_unlock(&file_priv->fbs_lock);
  2520.  
  2521.  
  2522.         return ret;
  2523. }
  2524.  
  2525. /**
  2526.  * drm_mode_rmfb - remove an FB from the configuration
  2527.  * @dev: drm device for the ioctl
  2528.  * @data: data pointer for the ioctl
  2529.  * @file_priv: drm file for the ioctl call
  2530.  *
  2531.  * Remove the FB specified by the user.
  2532.  *
  2533.  * Called by the user via ioctl.
  2534.  *
  2535.  * RETURNS:
  2536.  * Zero on success, errno on failure.
  2537.  */
  2538. int drm_mode_rmfb(struct drm_device *dev,
  2539.                    void *data, struct drm_file *file_priv)
  2540. {
  2541.         struct drm_framebuffer *fb = NULL;
  2542.         struct drm_framebuffer *fbl = NULL;
  2543.         uint32_t *id = data;
  2544.         int found = 0;
  2545.  
  2546.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2547.                 return -EINVAL;
  2548.  
  2549.         mutex_lock(&file_priv->fbs_lock);
  2550.         mutex_lock(&dev->mode_config.fb_lock);
  2551.         fb = __drm_framebuffer_lookup(dev, *id);
  2552.         if (!fb)
  2553.                 goto fail_lookup;
  2554.  
  2555.         list_for_each_entry(fbl, &file_priv->fbs, filp_head)
  2556.                 if (fb == fbl)
  2557.                         found = 1;
  2558.         if (!found)
  2559.                 goto fail_lookup;
  2560.  
  2561.         /* Mark fb as reaped, we still have a ref from fpriv->fbs. */
  2562.         __drm_framebuffer_unregister(dev, fb);
  2563.  
  2564.         list_del_init(&fb->filp_head);
  2565.         mutex_unlock(&dev->mode_config.fb_lock);
  2566.         mutex_unlock(&file_priv->fbs_lock);
  2567.  
  2568.         drm_framebuffer_remove(fb);
  2569.  
  2570.         return 0;
  2571.  
  2572. fail_lookup:
  2573.         mutex_unlock(&dev->mode_config.fb_lock);
  2574.         mutex_unlock(&file_priv->fbs_lock);
  2575.  
  2576.         return -EINVAL;
  2577. }
  2578.  
  2579. /**
  2580.  * drm_mode_getfb - get FB info
  2581.  * @dev: drm device for the ioctl
  2582.  * @data: data pointer for the ioctl
  2583.  * @file_priv: drm file for the ioctl call
  2584.  *
  2585.  * Lookup the FB given its ID and return info about it.
  2586.  *
  2587.  * Called by the user via ioctl.
  2588.  *
  2589.  * RETURNS:
  2590.  * Zero on success, errno on failure.
  2591.  */
  2592. int drm_mode_getfb(struct drm_device *dev,
  2593.                    void *data, struct drm_file *file_priv)
  2594. {
  2595.         struct drm_mode_fb_cmd *r = data;
  2596.         struct drm_framebuffer *fb;
  2597.         int ret;
  2598.  
  2599.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2600.                 return -EINVAL;
  2601.  
  2602.         fb = drm_framebuffer_lookup(dev, r->fb_id);
  2603.         if (!fb)
  2604.                 return -EINVAL;
  2605.  
  2606.         r->height = fb->height;
  2607.         r->width = fb->width;
  2608.         r->depth = fb->depth;
  2609.         r->bpp = fb->bits_per_pixel;
  2610.         r->pitch = fb->pitches[0];
  2611.         if (fb->funcs->create_handle)
  2612.                 ret = fb->funcs->create_handle(fb, file_priv, &r->handle);
  2613.         else
  2614.                 ret = -ENODEV;
  2615.  
  2616.         drm_framebuffer_unreference(fb);
  2617.  
  2618.         return ret;
  2619. }
  2620.  
  2621. int drm_mode_dirtyfb_ioctl(struct drm_device *dev,
  2622.                            void *data, struct drm_file *file_priv)
  2623. {
  2624.         struct drm_clip_rect __user *clips_ptr;
  2625.         struct drm_clip_rect *clips = NULL;
  2626.         struct drm_mode_fb_dirty_cmd *r = data;
  2627.         struct drm_framebuffer *fb;
  2628.         unsigned flags;
  2629.         int num_clips;
  2630.         int ret;
  2631.  
  2632.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2633.                 return -EINVAL;
  2634.  
  2635.         fb = drm_framebuffer_lookup(dev, r->fb_id);
  2636.         if (!fb)
  2637.                 return -EINVAL;
  2638.  
  2639.         num_clips = r->num_clips;
  2640.         clips_ptr = (struct drm_clip_rect __user *)(unsigned long)r->clips_ptr;
  2641.  
  2642.         if (!num_clips != !clips_ptr) {
  2643.                 ret = -EINVAL;
  2644.                 goto out_err1;
  2645.         }
  2646.  
  2647.         flags = DRM_MODE_FB_DIRTY_FLAGS & r->flags;
  2648.  
  2649.         /* If userspace annotates copy, clips must come in pairs */
  2650.         if (flags & DRM_MODE_FB_DIRTY_ANNOTATE_COPY && (num_clips % 2)) {
  2651.                 ret = -EINVAL;
  2652.                 goto out_err1;
  2653.         }
  2654.  
  2655.         if (num_clips && clips_ptr) {
  2656.                 if (num_clips < 0 || num_clips > DRM_MODE_FB_DIRTY_MAX_CLIPS) {
  2657.                         ret = -EINVAL;
  2658.                         goto out_err1;
  2659.                 }
  2660.                 clips = kzalloc(num_clips * sizeof(*clips), GFP_KERNEL);
  2661.                 if (!clips) {
  2662.                         ret = -ENOMEM;
  2663.                         goto out_err1;
  2664.                 }
  2665.  
  2666.                 ret = copy_from_user(clips, clips_ptr,
  2667.                                      num_clips * sizeof(*clips));
  2668.                 if (ret) {
  2669.                         ret = -EFAULT;
  2670.                         goto out_err2;
  2671.         }
  2672.         }
  2673.  
  2674.         if (fb->funcs->dirty) {
  2675.                 drm_modeset_lock_all(dev);
  2676.                 ret = fb->funcs->dirty(fb, file_priv, flags, r->color,
  2677.                                        clips, num_clips);
  2678.                 drm_modeset_unlock_all(dev);
  2679.         } else {
  2680.                 ret = -ENOSYS;
  2681.         }
  2682.  
  2683. out_err2:
  2684.         kfree(clips);
  2685. out_err1:
  2686.         drm_framebuffer_unreference(fb);
  2687.  
  2688.         return ret;
  2689. }
  2690.  
  2691.  
  2692. /**
  2693.  * drm_fb_release - remove and free the FBs on this file
  2694.  * @priv: drm file for the ioctl
  2695.  *
  2696.  * Destroy all the FBs associated with @filp.
  2697.  *
  2698.  * Called by the user via ioctl.
  2699.  *
  2700.  * RETURNS:
  2701.  * Zero on success, errno on failure.
  2702.  */
  2703. void drm_fb_release(struct drm_file *priv)
  2704. {
  2705.         struct drm_device *dev = priv->minor->dev;
  2706.         struct drm_framebuffer *fb, *tfb;
  2707.  
  2708.         mutex_lock(&priv->fbs_lock);
  2709.         list_for_each_entry_safe(fb, tfb, &priv->fbs, filp_head) {
  2710.  
  2711.                 mutex_lock(&dev->mode_config.fb_lock);
  2712.                 /* Mark fb as reaped, we still have a ref from fpriv->fbs. */
  2713.                 __drm_framebuffer_unregister(dev, fb);
  2714.                 mutex_unlock(&dev->mode_config.fb_lock);
  2715.  
  2716.                 list_del_init(&fb->filp_head);
  2717.  
  2718.                 /* This will also drop the fpriv->fbs reference. */
  2719.                 drm_framebuffer_remove(fb);
  2720.         }
  2721.         mutex_unlock(&priv->fbs_lock);
  2722. }
  2723. #endif
  2724.  
  2725. /**
  2726.  * drm_mode_attachmode - add a mode to the user mode list
  2727.  * @dev: DRM device
  2728.  * @connector: connector to add the mode to
  2729.  * @mode: mode to add
  2730.  *
  2731.  * Add @mode to @connector's user mode list.
  2732.  */
  2733. static void drm_mode_attachmode(struct drm_device *dev,
  2734.                                struct drm_connector *connector,
  2735.                                struct drm_display_mode *mode)
  2736. {
  2737.         list_add_tail(&mode->head, &connector->user_modes);
  2738. }
  2739.  
  2740. int drm_mode_attachmode_crtc(struct drm_device *dev, struct drm_crtc *crtc,
  2741.                              const struct drm_display_mode *mode)
  2742. {
  2743.         struct drm_connector *connector;
  2744.         int ret = 0;
  2745.         struct drm_display_mode *dup_mode, *next;
  2746.         LIST_HEAD(list);
  2747.  
  2748.         list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
  2749.                 if (!connector->encoder)
  2750.                         continue;
  2751.                 if (connector->encoder->crtc == crtc) {
  2752.                                 dup_mode = drm_mode_duplicate(dev, mode);
  2753.                         if (!dup_mode) {
  2754.                                 ret = -ENOMEM;
  2755.                                 goto out;
  2756.                 }
  2757.                         list_add_tail(&dup_mode->head, &list);
  2758.                 }
  2759.         }
  2760.  
  2761.         list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
  2762.                 if (!connector->encoder)
  2763.                         continue;
  2764.                 if (connector->encoder->crtc == crtc)
  2765.                         list_move_tail(list.next, &connector->user_modes);
  2766.         }
  2767.  
  2768.         WARN_ON(!list_empty(&list));
  2769.  
  2770.  out:
  2771.         list_for_each_entry_safe(dup_mode, next, &list, head)
  2772.                 drm_mode_destroy(dev, dup_mode);
  2773.  
  2774.         return ret;
  2775. }
  2776. EXPORT_SYMBOL(drm_mode_attachmode_crtc);
  2777.  
  2778. static int drm_mode_detachmode(struct drm_device *dev,
  2779.                                struct drm_connector *connector,
  2780.                                struct drm_display_mode *mode)
  2781. {
  2782.         int found = 0;
  2783.         int ret = 0;
  2784.         struct drm_display_mode *match_mode, *t;
  2785.  
  2786.         list_for_each_entry_safe(match_mode, t, &connector->user_modes, head) {
  2787.                 if (drm_mode_equal(match_mode, mode)) {
  2788.                         list_del(&match_mode->head);
  2789.                         drm_mode_destroy(dev, match_mode);
  2790.                         found = 1;
  2791.                         break;
  2792.                 }
  2793.         }
  2794.  
  2795.         if (!found)
  2796.                 ret = -EINVAL;
  2797.  
  2798.         return ret;
  2799. }
  2800.  
  2801. int drm_mode_detachmode_crtc(struct drm_device *dev, struct drm_display_mode *mode)
  2802. {
  2803.         struct drm_connector *connector;
  2804.  
  2805.         list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
  2806.                 drm_mode_detachmode(dev, connector, mode);
  2807.         }
  2808.         return 0;
  2809. }
  2810. EXPORT_SYMBOL(drm_mode_detachmode_crtc);
  2811.  
  2812. #if 0
  2813.  
  2814. /**
  2815.  * drm_fb_attachmode - Attach a user mode to an connector
  2816.  * @dev: drm device for the ioctl
  2817.  * @data: data pointer for the ioctl
  2818.  * @file_priv: drm file for the ioctl call
  2819.  *
  2820.  * This attaches a user specified mode to an connector.
  2821.  * Called by the user via ioctl.
  2822.  *
  2823.  * RETURNS:
  2824.  * Zero on success, errno on failure.
  2825.  */
  2826. int drm_mode_attachmode_ioctl(struct drm_device *dev,
  2827.                               void *data, struct drm_file *file_priv)
  2828. {
  2829.         struct drm_mode_mode_cmd *mode_cmd = data;
  2830.         struct drm_connector *connector;
  2831.         struct drm_display_mode *mode;
  2832.         struct drm_mode_object *obj;
  2833.         struct drm_mode_modeinfo *umode = &mode_cmd->mode;
  2834.         int ret;
  2835.  
  2836.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2837.                 return -EINVAL;
  2838.  
  2839.         drm_modeset_lock_all(dev);
  2840.  
  2841.         obj = drm_mode_object_find(dev, mode_cmd->connector_id, DRM_MODE_OBJECT_CONNECTOR);
  2842.         if (!obj) {
  2843.                 ret = -EINVAL;
  2844.                 goto out;
  2845.         }
  2846.         connector = obj_to_connector(obj);
  2847.  
  2848.         mode = drm_mode_create(dev);
  2849.         if (!mode) {
  2850.                 ret = -ENOMEM;
  2851.                 goto out;
  2852.         }
  2853.  
  2854.         ret = drm_crtc_convert_umode(mode, umode);
  2855.         if (ret) {
  2856.                 DRM_DEBUG_KMS("Invalid mode\n");
  2857.                 drm_mode_destroy(dev, mode);
  2858.                 goto out;
  2859.         }
  2860.  
  2861.         drm_mode_attachmode(dev, connector, mode);
  2862. out:
  2863.         drm_modeset_unlock_all(dev);
  2864.         return ret;
  2865. }
  2866.  
  2867.  
  2868. /**
  2869.  * drm_fb_detachmode - Detach a user specified mode from an connector
  2870.  * @dev: drm device for the ioctl
  2871.  * @data: data pointer for the ioctl
  2872.  * @file_priv: drm file for the ioctl call
  2873.  *
  2874.  * Called by the user via ioctl.
  2875.  *
  2876.  * RETURNS:
  2877.  * Zero on success, errno on failure.
  2878.  */
  2879. int drm_mode_detachmode_ioctl(struct drm_device *dev,
  2880.                               void *data, struct drm_file *file_priv)
  2881. {
  2882.         struct drm_mode_object *obj;
  2883.         struct drm_mode_mode_cmd *mode_cmd = data;
  2884.         struct drm_connector *connector;
  2885.         struct drm_display_mode mode;
  2886.         struct drm_mode_modeinfo *umode = &mode_cmd->mode;
  2887.         int ret;
  2888.  
  2889.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  2890.                 return -EINVAL;
  2891.  
  2892.         drm_modeset_lock_all(dev);
  2893.  
  2894.         obj = drm_mode_object_find(dev, mode_cmd->connector_id, DRM_MODE_OBJECT_CONNECTOR);
  2895.         if (!obj) {
  2896.                 ret = -EINVAL;
  2897.                 goto out;
  2898.         }
  2899.         connector = obj_to_connector(obj);
  2900.  
  2901.         ret = drm_crtc_convert_umode(&mode, umode);
  2902.         if (ret) {
  2903.                 DRM_DEBUG_KMS("Invalid mode\n");
  2904.                 goto out;
  2905.         }
  2906.  
  2907.         ret = drm_mode_detachmode(dev, connector, &mode);
  2908. out:
  2909.         drm_modeset_unlock_all(dev);
  2910.         return ret;
  2911. }
  2912. #endif
  2913.  
  2914. struct drm_property *drm_property_create(struct drm_device *dev, int flags,
  2915.                                          const char *name, int num_values)
  2916. {
  2917.         struct drm_property *property = NULL;
  2918.         int ret;
  2919.  
  2920.         property = kzalloc(sizeof(struct drm_property), GFP_KERNEL);
  2921.         if (!property)
  2922.                 return NULL;
  2923.  
  2924.         if (num_values) {
  2925.                 property->values = kzalloc(sizeof(uint64_t)*num_values, GFP_KERNEL);
  2926.                 if (!property->values)
  2927.                         goto fail;
  2928.         }
  2929.  
  2930.         ret = drm_mode_object_get(dev, &property->base, DRM_MODE_OBJECT_PROPERTY);
  2931.         if (ret)
  2932.                 goto fail;
  2933.  
  2934.         property->flags = flags;
  2935.         property->num_values = num_values;
  2936.         INIT_LIST_HEAD(&property->enum_blob_list);
  2937.  
  2938.         if (name) {
  2939.                 strncpy(property->name, name, DRM_PROP_NAME_LEN);
  2940.                 property->name[DRM_PROP_NAME_LEN-1] = '\0';
  2941.         }
  2942.  
  2943.         list_add_tail(&property->head, &dev->mode_config.property_list);
  2944.         return property;
  2945. fail:
  2946.         kfree(property->values);
  2947.         kfree(property);
  2948.         return NULL;
  2949. }
  2950. EXPORT_SYMBOL(drm_property_create);
  2951.  
  2952. struct drm_property *drm_property_create_enum(struct drm_device *dev, int flags,
  2953.                                          const char *name,
  2954.                                          const struct drm_prop_enum_list *props,
  2955.                                          int num_values)
  2956. {
  2957.         struct drm_property *property;
  2958.         int i, ret;
  2959.  
  2960.         flags |= DRM_MODE_PROP_ENUM;
  2961.  
  2962.         property = drm_property_create(dev, flags, name, num_values);
  2963.         if (!property)
  2964.                 return NULL;
  2965.  
  2966.         for (i = 0; i < num_values; i++) {
  2967.                 ret = drm_property_add_enum(property, i,
  2968.                                       props[i].type,
  2969.                                       props[i].name);
  2970.                 if (ret) {
  2971.                         drm_property_destroy(dev, property);
  2972.                         return NULL;
  2973.                 }
  2974.         }
  2975.  
  2976.         return property;
  2977. }
  2978. EXPORT_SYMBOL(drm_property_create_enum);
  2979.  
  2980. struct drm_property *drm_property_create_bitmask(struct drm_device *dev,
  2981.                                          int flags, const char *name,
  2982.                                          const struct drm_prop_enum_list *props,
  2983.                                          int num_values)
  2984. {
  2985.         struct drm_property *property;
  2986.         int i, ret;
  2987.  
  2988.         flags |= DRM_MODE_PROP_BITMASK;
  2989.  
  2990.         property = drm_property_create(dev, flags, name, num_values);
  2991.         if (!property)
  2992.                 return NULL;
  2993.  
  2994.         for (i = 0; i < num_values; i++) {
  2995.                 ret = drm_property_add_enum(property, i,
  2996.                                       props[i].type,
  2997.                                       props[i].name);
  2998.                 if (ret) {
  2999.                         drm_property_destroy(dev, property);
  3000.                         return NULL;
  3001.                 }
  3002.         }
  3003.  
  3004.         return property;
  3005. }
  3006. EXPORT_SYMBOL(drm_property_create_bitmask);
  3007.  
  3008. struct drm_property *drm_property_create_range(struct drm_device *dev, int flags,
  3009.                                          const char *name,
  3010.                                          uint64_t min, uint64_t max)
  3011. {
  3012.         struct drm_property *property;
  3013.  
  3014.         flags |= DRM_MODE_PROP_RANGE;
  3015.  
  3016.         property = drm_property_create(dev, flags, name, 2);
  3017.         if (!property)
  3018.                 return NULL;
  3019.  
  3020.         property->values[0] = min;
  3021.         property->values[1] = max;
  3022.  
  3023.         return property;
  3024. }
  3025. EXPORT_SYMBOL(drm_property_create_range);
  3026.  
  3027. int drm_property_add_enum(struct drm_property *property, int index,
  3028.                           uint64_t value, const char *name)
  3029. {
  3030.         struct drm_property_enum *prop_enum;
  3031.  
  3032.         if (!(property->flags & (DRM_MODE_PROP_ENUM | DRM_MODE_PROP_BITMASK)))
  3033.                 return -EINVAL;
  3034.  
  3035.         /*
  3036.          * Bitmask enum properties have the additional constraint of values
  3037.          * from 0 to 63
  3038.          */
  3039.         if ((property->flags & DRM_MODE_PROP_BITMASK) && (value > 63))
  3040.                 return -EINVAL;
  3041.  
  3042.         if (!list_empty(&property->enum_blob_list)) {
  3043.                 list_for_each_entry(prop_enum, &property->enum_blob_list, head) {
  3044.                         if (prop_enum->value == value) {
  3045.                                 strncpy(prop_enum->name, name, DRM_PROP_NAME_LEN);
  3046.                                 prop_enum->name[DRM_PROP_NAME_LEN-1] = '\0';
  3047.                                 return 0;
  3048.                         }
  3049.                 }
  3050.         }
  3051.  
  3052.         prop_enum = kzalloc(sizeof(struct drm_property_enum), GFP_KERNEL);
  3053.         if (!prop_enum)
  3054.                 return -ENOMEM;
  3055.  
  3056.         strncpy(prop_enum->name, name, DRM_PROP_NAME_LEN);
  3057.         prop_enum->name[DRM_PROP_NAME_LEN-1] = '\0';
  3058.         prop_enum->value = value;
  3059.  
  3060.         property->values[index] = value;
  3061.         list_add_tail(&prop_enum->head, &property->enum_blob_list);
  3062.         return 0;
  3063. }
  3064. EXPORT_SYMBOL(drm_property_add_enum);
  3065.  
  3066. void drm_property_destroy(struct drm_device *dev, struct drm_property *property)
  3067. {
  3068.         struct drm_property_enum *prop_enum, *pt;
  3069.  
  3070.         list_for_each_entry_safe(prop_enum, pt, &property->enum_blob_list, head) {
  3071.                 list_del(&prop_enum->head);
  3072.                 kfree(prop_enum);
  3073.         }
  3074.  
  3075.         if (property->num_values)
  3076.                 kfree(property->values);
  3077.         drm_mode_object_put(dev, &property->base);
  3078.         list_del(&property->head);
  3079.         kfree(property);
  3080. }
  3081. EXPORT_SYMBOL(drm_property_destroy);
  3082.  
  3083. void drm_object_attach_property(struct drm_mode_object *obj,
  3084.                                 struct drm_property *property,
  3085.                                 uint64_t init_val)
  3086. {
  3087.         int count = obj->properties->count;
  3088.  
  3089.         if (count == DRM_OBJECT_MAX_PROPERTY) {
  3090.                 WARN(1, "Failed to attach object property (type: 0x%x). Please "
  3091.                         "increase DRM_OBJECT_MAX_PROPERTY by 1 for each time "
  3092.                         "you see this message on the same object type.\n",
  3093.                         obj->type);
  3094.                 return;
  3095.         }
  3096.  
  3097.         obj->properties->ids[count] = property->base.id;
  3098.         obj->properties->values[count] = init_val;
  3099.         obj->properties->count++;
  3100. }
  3101. EXPORT_SYMBOL(drm_object_attach_property);
  3102.  
  3103. int drm_object_property_set_value(struct drm_mode_object *obj,
  3104.                                   struct drm_property *property, uint64_t val)
  3105. {
  3106.         int i;
  3107.  
  3108.         for (i = 0; i < obj->properties->count; i++) {
  3109.                 if (obj->properties->ids[i] == property->base.id) {
  3110.                         obj->properties->values[i] = val;
  3111.                         return 0;
  3112.                 }
  3113.         }
  3114.  
  3115.                 return -EINVAL;
  3116. }
  3117. EXPORT_SYMBOL(drm_object_property_set_value);
  3118.  
  3119. int drm_object_property_get_value(struct drm_mode_object *obj,
  3120.                                   struct drm_property *property, uint64_t *val)
  3121. {
  3122.         int i;
  3123.  
  3124.         for (i = 0; i < obj->properties->count; i++) {
  3125.                 if (obj->properties->ids[i] == property->base.id) {
  3126.                         *val = obj->properties->values[i];
  3127.                         return 0;
  3128.                 }
  3129.         }
  3130.  
  3131.                 return -EINVAL;
  3132. }
  3133. EXPORT_SYMBOL(drm_object_property_get_value);
  3134.  
  3135. #if 0
  3136. int drm_mode_getproperty_ioctl(struct drm_device *dev,
  3137.                                void *data, struct drm_file *file_priv)
  3138. {
  3139.         struct drm_mode_object *obj;
  3140.         struct drm_mode_get_property *out_resp = data;
  3141.         struct drm_property *property;
  3142.         int enum_count = 0;
  3143.         int blob_count = 0;
  3144.         int value_count = 0;
  3145.         int ret = 0, i;
  3146.         int copied;
  3147.         struct drm_property_enum *prop_enum;
  3148.         struct drm_mode_property_enum __user *enum_ptr;
  3149.         struct drm_property_blob *prop_blob;
  3150.         uint32_t __user *blob_id_ptr;
  3151.         uint64_t __user *values_ptr;
  3152.         uint32_t __user *blob_length_ptr;
  3153.  
  3154.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  3155.                 return -EINVAL;
  3156.  
  3157.         drm_modeset_lock_all(dev);
  3158.         obj = drm_mode_object_find(dev, out_resp->prop_id, DRM_MODE_OBJECT_PROPERTY);
  3159.         if (!obj) {
  3160.                 ret = -EINVAL;
  3161.                 goto done;
  3162.         }
  3163.         property = obj_to_property(obj);
  3164.  
  3165.         if (property->flags & (DRM_MODE_PROP_ENUM | DRM_MODE_PROP_BITMASK)) {
  3166.                 list_for_each_entry(prop_enum, &property->enum_blob_list, head)
  3167.                         enum_count++;
  3168.         } else if (property->flags & DRM_MODE_PROP_BLOB) {
  3169.                 list_for_each_entry(prop_blob, &property->enum_blob_list, head)
  3170.                         blob_count++;
  3171.         }
  3172.  
  3173.         value_count = property->num_values;
  3174.  
  3175.         strncpy(out_resp->name, property->name, DRM_PROP_NAME_LEN);
  3176.         out_resp->name[DRM_PROP_NAME_LEN-1] = 0;
  3177.         out_resp->flags = property->flags;
  3178.  
  3179.         if ((out_resp->count_values >= value_count) && value_count) {
  3180.                 values_ptr = (uint64_t __user *)(unsigned long)out_resp->values_ptr;
  3181.                 for (i = 0; i < value_count; i++) {
  3182.                         if (copy_to_user(values_ptr + i, &property->values[i], sizeof(uint64_t))) {
  3183.                                 ret = -EFAULT;
  3184.                                 goto done;
  3185.                         }
  3186.                 }
  3187.         }
  3188.         out_resp->count_values = value_count;
  3189.  
  3190.         if (property->flags & (DRM_MODE_PROP_ENUM | DRM_MODE_PROP_BITMASK)) {
  3191.                 if ((out_resp->count_enum_blobs >= enum_count) && enum_count) {
  3192.                         copied = 0;
  3193.                         enum_ptr = (struct drm_mode_property_enum __user *)(unsigned long)out_resp->enum_blob_ptr;
  3194.                         list_for_each_entry(prop_enum, &property->enum_blob_list, head) {
  3195.  
  3196.                                 if (copy_to_user(&enum_ptr[copied].value, &prop_enum->value, sizeof(uint64_t))) {
  3197.                                         ret = -EFAULT;
  3198.                                         goto done;
  3199.                                 }
  3200.  
  3201.                                 if (copy_to_user(&enum_ptr[copied].name,
  3202.                                                  &prop_enum->name, DRM_PROP_NAME_LEN)) {
  3203.                                         ret = -EFAULT;
  3204.                                         goto done;
  3205.                                 }
  3206.                                 copied++;
  3207.                         }
  3208.                 }
  3209.                 out_resp->count_enum_blobs = enum_count;
  3210.         }
  3211.  
  3212.         if (property->flags & DRM_MODE_PROP_BLOB) {
  3213.                 if ((out_resp->count_enum_blobs >= blob_count) && blob_count) {
  3214.                         copied = 0;
  3215.                         blob_id_ptr = (uint32_t __user *)(unsigned long)out_resp->enum_blob_ptr;
  3216.                         blob_length_ptr = (uint32_t __user *)(unsigned long)out_resp->values_ptr;
  3217.  
  3218.                         list_for_each_entry(prop_blob, &property->enum_blob_list, head) {
  3219.                                 if (put_user(prop_blob->base.id, blob_id_ptr + copied)) {
  3220.                                         ret = -EFAULT;
  3221.                                         goto done;
  3222.                                 }
  3223.  
  3224.                                 if (put_user(prop_blob->length, blob_length_ptr + copied)) {
  3225.                                         ret = -EFAULT;
  3226.                                         goto done;
  3227.                                 }
  3228.  
  3229.                                 copied++;
  3230.                         }
  3231.                 }
  3232.                 out_resp->count_enum_blobs = blob_count;
  3233.         }
  3234. done:
  3235.         drm_modeset_unlock_all(dev);
  3236.         return ret;
  3237. }
  3238. #endif
  3239.  
  3240. static struct drm_property_blob *drm_property_create_blob(struct drm_device *dev, int length,
  3241.                                                           void *data)
  3242. {
  3243.         struct drm_property_blob *blob;
  3244.         int ret;
  3245.  
  3246.         if (!length || !data)
  3247.                 return NULL;
  3248.  
  3249.         blob = kzalloc(sizeof(struct drm_property_blob)+length, GFP_KERNEL);
  3250.         if (!blob)
  3251.                 return NULL;
  3252.  
  3253.         ret = drm_mode_object_get(dev, &blob->base, DRM_MODE_OBJECT_BLOB);
  3254.         if (ret) {
  3255.                 kfree(blob);
  3256.                 return NULL;
  3257.         }
  3258.  
  3259.         blob->length = length;
  3260.  
  3261.         memcpy(blob->data, data, length);
  3262.  
  3263.         list_add_tail(&blob->head, &dev->mode_config.property_blob_list);
  3264.         return blob;
  3265. }
  3266.  
  3267. static void drm_property_destroy_blob(struct drm_device *dev,
  3268.                                struct drm_property_blob *blob)
  3269. {
  3270.         drm_mode_object_put(dev, &blob->base);
  3271.         list_del(&blob->head);
  3272.         kfree(blob);
  3273. }
  3274.  
  3275. #if 0
  3276. int drm_mode_getblob_ioctl(struct drm_device *dev,
  3277.                            void *data, struct drm_file *file_priv)
  3278. {
  3279.         struct drm_mode_object *obj;
  3280.         struct drm_mode_get_blob *out_resp = data;
  3281.         struct drm_property_blob *blob;
  3282.         int ret = 0;
  3283.         void __user *blob_ptr;
  3284.  
  3285.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  3286.                 return -EINVAL;
  3287.  
  3288.         drm_modeset_lock_all(dev);
  3289.         obj = drm_mode_object_find(dev, out_resp->blob_id, DRM_MODE_OBJECT_BLOB);
  3290.         if (!obj) {
  3291.                 ret = -EINVAL;
  3292.                 goto done;
  3293.         }
  3294.         blob = obj_to_blob(obj);
  3295.  
  3296.         if (out_resp->length == blob->length) {
  3297.                 blob_ptr = (void __user *)(unsigned long)out_resp->data;
  3298.                 if (copy_to_user(blob_ptr, blob->data, blob->length)){
  3299.                         ret = -EFAULT;
  3300.                         goto done;
  3301.                 }
  3302.         }
  3303.         out_resp->length = blob->length;
  3304.  
  3305. done:
  3306.         drm_modeset_unlock_all(dev);
  3307.         return ret;
  3308. }
  3309. #endif
  3310.  
  3311. int drm_mode_connector_update_edid_property(struct drm_connector *connector,
  3312.                                             struct edid *edid)
  3313. {
  3314.         struct drm_device *dev = connector->dev;
  3315.         int ret, size;
  3316.  
  3317.         if (connector->edid_blob_ptr)
  3318.                 drm_property_destroy_blob(dev, connector->edid_blob_ptr);
  3319.  
  3320.         /* Delete edid, when there is none. */
  3321.         if (!edid) {
  3322.                 connector->edid_blob_ptr = NULL;
  3323.                 ret = drm_object_property_set_value(&connector->base, dev->mode_config.edid_property, 0);
  3324.                 return ret;
  3325.         }
  3326.  
  3327.         size = EDID_LENGTH * (1 + edid->extensions);
  3328.         connector->edid_blob_ptr = drm_property_create_blob(connector->dev,
  3329.                                                             size, edid);
  3330.         if (!connector->edid_blob_ptr)
  3331.                 return -EINVAL;
  3332.  
  3333.         ret = drm_object_property_set_value(&connector->base,
  3334.                                                dev->mode_config.edid_property,
  3335.                                                connector->edid_blob_ptr->base.id);
  3336.  
  3337.         return ret;
  3338. }
  3339. EXPORT_SYMBOL(drm_mode_connector_update_edid_property);
  3340.  
  3341. #if 0
  3342.  
  3343. static int drm_mode_connector_set_obj_prop(struct drm_mode_object *obj,
  3344.                                            struct drm_property *property,
  3345.                                            uint64_t value)
  3346. {
  3347.         int ret = -EINVAL;
  3348.         struct drm_connector *connector = obj_to_connector(obj);
  3349.  
  3350.         /* Do DPMS ourselves */
  3351.         if (property == connector->dev->mode_config.dpms_property) {
  3352.                 if (connector->funcs->dpms)
  3353.                         (*connector->funcs->dpms)(connector, (int)value);
  3354.                 ret = 0;
  3355.         } else if (connector->funcs->set_property)
  3356.                 ret = connector->funcs->set_property(connector, property, value);
  3357.  
  3358.         /* store the property value if successful */
  3359.         if (!ret)
  3360.                 drm_object_property_set_value(&connector->base, property, value);
  3361.         return ret;
  3362. }
  3363.  
  3364. static int drm_mode_crtc_set_obj_prop(struct drm_mode_object *obj,
  3365.                                       struct drm_property *property,
  3366.                                       uint64_t value)
  3367. {
  3368.         int ret = -EINVAL;
  3369.         struct drm_crtc *crtc = obj_to_crtc(obj);
  3370.  
  3371.         if (crtc->funcs->set_property)
  3372.                 ret = crtc->funcs->set_property(crtc, property, value);
  3373.         if (!ret)
  3374.                 drm_object_property_set_value(obj, property, value);
  3375.  
  3376.         return ret;
  3377. }
  3378.  
  3379. static int drm_mode_plane_set_obj_prop(struct drm_mode_object *obj,
  3380.                                       struct drm_property *property,
  3381.                                       uint64_t value)
  3382. {
  3383.         int ret = -EINVAL;
  3384.         struct drm_plane *plane = obj_to_plane(obj);
  3385.  
  3386.         if (plane->funcs->set_property)
  3387.                 ret = plane->funcs->set_property(plane, property, value);
  3388.         if (!ret)
  3389.                 drm_object_property_set_value(obj, property, value);
  3390.  
  3391.         return ret;
  3392. }
  3393.  
  3394. int drm_mode_obj_get_properties_ioctl(struct drm_device *dev, void *data,
  3395.                                       struct drm_file *file_priv)
  3396. {
  3397.         struct drm_mode_obj_get_properties *arg = data;
  3398.         struct drm_mode_object *obj;
  3399.         int ret = 0;
  3400.         int i;
  3401.         int copied = 0;
  3402.         int props_count = 0;
  3403.         uint32_t __user *props_ptr;
  3404.         uint64_t __user *prop_values_ptr;
  3405.  
  3406.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  3407.                 return -EINVAL;
  3408.  
  3409.         drm_modeset_lock_all(dev);
  3410.  
  3411.         obj = drm_mode_object_find(dev, arg->obj_id, arg->obj_type);
  3412.         if (!obj) {
  3413.                 ret = -EINVAL;
  3414.                 goto out;
  3415.         }
  3416.         if (!obj->properties) {
  3417.                 ret = -EINVAL;
  3418.                 goto out;
  3419.         }
  3420.  
  3421.         props_count = obj->properties->count;
  3422.  
  3423.         /* This ioctl is called twice, once to determine how much space is
  3424.          * needed, and the 2nd time to fill it. */
  3425.         if ((arg->count_props >= props_count) && props_count) {
  3426.                 copied = 0;
  3427.                 props_ptr = (uint32_t __user *)(unsigned long)(arg->props_ptr);
  3428.                 prop_values_ptr = (uint64_t __user *)(unsigned long)
  3429.                                   (arg->prop_values_ptr);
  3430.                 for (i = 0; i < props_count; i++) {
  3431.                         if (put_user(obj->properties->ids[i],
  3432.                                      props_ptr + copied)) {
  3433.                                 ret = -EFAULT;
  3434.                                 goto out;
  3435.         }
  3436.                         if (put_user(obj->properties->values[i],
  3437.                                      prop_values_ptr + copied)) {
  3438.                                 ret = -EFAULT;
  3439.                 goto out;
  3440.         }
  3441.                         copied++;
  3442.                 }
  3443.         }
  3444.         arg->count_props = props_count;
  3445. out:
  3446.         drm_modeset_unlock_all(dev);
  3447.         return ret;
  3448. }
  3449.  
  3450. int drm_mode_obj_set_property_ioctl(struct drm_device *dev, void *data,
  3451.                                     struct drm_file *file_priv)
  3452. {
  3453.         struct drm_mode_obj_set_property *arg = data;
  3454.         struct drm_mode_object *arg_obj;
  3455.         struct drm_mode_object *prop_obj;
  3456.         struct drm_property *property;
  3457.         int ret = -EINVAL;
  3458.         int i;
  3459.  
  3460.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  3461.                 return -EINVAL;
  3462.  
  3463.         drm_modeset_lock_all(dev);
  3464.  
  3465.         arg_obj = drm_mode_object_find(dev, arg->obj_id, arg->obj_type);
  3466.         if (!arg_obj)
  3467.                 goto out;
  3468.         if (!arg_obj->properties)
  3469.                 goto out;
  3470.  
  3471.         for (i = 0; i < arg_obj->properties->count; i++)
  3472.                 if (arg_obj->properties->ids[i] == arg->prop_id)
  3473.                         break;
  3474.  
  3475.         if (i == arg_obj->properties->count)
  3476.                 goto out;
  3477.  
  3478.         prop_obj = drm_mode_object_find(dev, arg->prop_id,
  3479.                                         DRM_MODE_OBJECT_PROPERTY);
  3480.         if (!prop_obj)
  3481.                         goto out;
  3482.         property = obj_to_property(prop_obj);
  3483.  
  3484.         if (!drm_property_change_is_valid(property, arg->value))
  3485.                         goto out;
  3486.  
  3487.         switch (arg_obj->type) {
  3488.         case DRM_MODE_OBJECT_CONNECTOR:
  3489.                 ret = drm_mode_connector_set_obj_prop(arg_obj, property,
  3490.                                                       arg->value);
  3491.                 break;
  3492.         case DRM_MODE_OBJECT_CRTC:
  3493.                 ret = drm_mode_crtc_set_obj_prop(arg_obj, property, arg->value);
  3494.                 break;
  3495.         case DRM_MODE_OBJECT_PLANE:
  3496.                 ret = drm_mode_plane_set_obj_prop(arg_obj, property, arg->value);
  3497.                                 break;
  3498.                         }
  3499.  
  3500. out:
  3501.         drm_modeset_unlock_all(dev);
  3502.         return ret;
  3503. }
  3504. #endif
  3505.  
  3506. int drm_mode_connector_attach_encoder(struct drm_connector *connector,
  3507.                                       struct drm_encoder *encoder)
  3508. {
  3509.         int i;
  3510.  
  3511.         for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
  3512.                 if (connector->encoder_ids[i] == 0) {
  3513.                         connector->encoder_ids[i] = encoder->base.id;
  3514.                         return 0;
  3515.                 }
  3516.         }
  3517.         return -ENOMEM;
  3518. }
  3519. EXPORT_SYMBOL(drm_mode_connector_attach_encoder);
  3520.  
  3521. void drm_mode_connector_detach_encoder(struct drm_connector *connector,
  3522.                                     struct drm_encoder *encoder)
  3523. {
  3524.         int i;
  3525.         for (i = 0; i < DRM_CONNECTOR_MAX_ENCODER; i++) {
  3526.                 if (connector->encoder_ids[i] == encoder->base.id) {
  3527.                         connector->encoder_ids[i] = 0;
  3528.                         if (connector->encoder == encoder)
  3529.                                 connector->encoder = NULL;
  3530.                         break;
  3531.                 }
  3532.         }
  3533. }
  3534. EXPORT_SYMBOL(drm_mode_connector_detach_encoder);
  3535.  
  3536. int drm_mode_crtc_set_gamma_size(struct drm_crtc *crtc,
  3537.                                   int gamma_size)
  3538. {
  3539.         crtc->gamma_size = gamma_size;
  3540.  
  3541.         crtc->gamma_store = kzalloc(gamma_size * sizeof(uint16_t) * 3, GFP_KERNEL);
  3542.         if (!crtc->gamma_store) {
  3543.                 crtc->gamma_size = 0;
  3544.                 return -ENOMEM;
  3545.         }
  3546.  
  3547.         return 0;
  3548. }
  3549. EXPORT_SYMBOL(drm_mode_crtc_set_gamma_size);
  3550.  
  3551. #if 0
  3552. int drm_mode_gamma_set_ioctl(struct drm_device *dev,
  3553.                              void *data, struct drm_file *file_priv)
  3554. {
  3555.         struct drm_mode_crtc_lut *crtc_lut = data;
  3556.         struct drm_mode_object *obj;
  3557.         struct drm_crtc *crtc;
  3558.         void *r_base, *g_base, *b_base;
  3559.         int size;
  3560.         int ret = 0;
  3561.  
  3562.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  3563.                 return -EINVAL;
  3564.  
  3565.         drm_modeset_lock_all(dev);
  3566.         obj = drm_mode_object_find(dev, crtc_lut->crtc_id, DRM_MODE_OBJECT_CRTC);
  3567.         if (!obj) {
  3568.                 ret = -EINVAL;
  3569.                 goto out;
  3570.         }
  3571.         crtc = obj_to_crtc(obj);
  3572.  
  3573.         if (crtc->funcs->gamma_set == NULL) {
  3574.                 ret = -ENOSYS;
  3575.                 goto out;
  3576.         }
  3577.  
  3578.         /* memcpy into gamma store */
  3579.         if (crtc_lut->gamma_size != crtc->gamma_size) {
  3580.                 ret = -EINVAL;
  3581.                 goto out;
  3582.         }
  3583.  
  3584.         size = crtc_lut->gamma_size * (sizeof(uint16_t));
  3585.         r_base = crtc->gamma_store;
  3586.         if (copy_from_user(r_base, (void __user *)(unsigned long)crtc_lut->red, size)) {
  3587.                 ret = -EFAULT;
  3588.                 goto out;
  3589.         }
  3590.  
  3591.         g_base = r_base + size;
  3592.         if (copy_from_user(g_base, (void __user *)(unsigned long)crtc_lut->green, size)) {
  3593.                 ret = -EFAULT;
  3594.                 goto out;
  3595.         }
  3596.  
  3597.         b_base = g_base + size;
  3598.         if (copy_from_user(b_base, (void __user *)(unsigned long)crtc_lut->blue, size)) {
  3599.                 ret = -EFAULT;
  3600.                 goto out;
  3601.         }
  3602.  
  3603.         crtc->funcs->gamma_set(crtc, r_base, g_base, b_base, 0, crtc->gamma_size);
  3604.  
  3605. out:
  3606.         drm_modeset_unlock_all(dev);
  3607.         return ret;
  3608.  
  3609. }
  3610.  
  3611. int drm_mode_gamma_get_ioctl(struct drm_device *dev,
  3612.                              void *data, struct drm_file *file_priv)
  3613. {
  3614.         struct drm_mode_crtc_lut *crtc_lut = data;
  3615.         struct drm_mode_object *obj;
  3616.         struct drm_crtc *crtc;
  3617.         void *r_base, *g_base, *b_base;
  3618.         int size;
  3619.         int ret = 0;
  3620.  
  3621.         if (!drm_core_check_feature(dev, DRIVER_MODESET))
  3622.                 return -EINVAL;
  3623.  
  3624.         drm_modeset_lock_all(dev);
  3625.         obj = drm_mode_object_find(dev, crtc_lut->crtc_id, DRM_MODE_OBJECT_CRTC);
  3626.         if (!obj) {
  3627.                 ret = -EINVAL;
  3628.                 goto out;
  3629.         }
  3630.         crtc = obj_to_crtc(obj);
  3631.  
  3632.         /* memcpy into gamma store */
  3633.         if (crtc_lut->gamma_size != crtc->gamma_size) {
  3634.                 ret = -EINVAL;
  3635.                 goto out;
  3636.         }
  3637.  
  3638.         size = crtc_lut->gamma_size * (sizeof(uint16_t));
  3639.         r_base = crtc->gamma_store;
  3640.         if (copy_to_user((void __user *)(unsigned long)crtc_lut->red, r_base, size)) {
  3641.                 ret = -EFAULT;
  3642.                 goto out;
  3643.         }
  3644.  
  3645.         g_base = r_base + size;
  3646.         if (copy_to_user((void __user *)(unsigned long)crtc_lut->green, g_base, size)) {
  3647.                 ret = -EFAULT;
  3648.                 goto out;
  3649.         }
  3650.  
  3651.         b_base = g_base + size;
  3652.         if (copy_to_user((void __user *)(unsigned long)crtc_lut->blue, b_base, size)) {
  3653.                 ret = -EFAULT;
  3654.                 goto out;
  3655.         }
  3656. out:
  3657.         drm_modeset_unlock_all(dev);
  3658.         return ret;
  3659. }
  3660.  
  3661. #endif
  3662.  
  3663.  
  3664. void drm_mode_config_reset(struct drm_device *dev)
  3665. {
  3666.         struct drm_crtc *crtc;
  3667.         struct drm_encoder *encoder;
  3668.         struct drm_connector *connector;
  3669.  
  3670.         list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
  3671.                 if (crtc->funcs->reset)
  3672.                         crtc->funcs->reset(crtc);
  3673.  
  3674.         list_for_each_entry(encoder, &dev->mode_config.encoder_list, head)
  3675.                 if (encoder->funcs->reset)
  3676.                         encoder->funcs->reset(encoder);
  3677.  
  3678.         list_for_each_entry(connector, &dev->mode_config.connector_list, head) {
  3679.                 connector->status = connector_status_unknown;
  3680.  
  3681.                 if (connector->funcs->reset)
  3682.                         connector->funcs->reset(connector);
  3683.         }
  3684. }
  3685. EXPORT_SYMBOL(drm_mode_config_reset);
  3686. /*
  3687.  * Just need to support RGB formats here for compat with code that doesn't
  3688.  * use pixel formats directly yet.
  3689.  */
  3690. void drm_fb_get_bpp_depth(uint32_t format, unsigned int *depth,
  3691.                           int *bpp)
  3692. {
  3693.         switch (format) {
  3694.         case DRM_FORMAT_C8:
  3695.         case DRM_FORMAT_RGB332:
  3696.         case DRM_FORMAT_BGR233:
  3697.                 *depth = 8;
  3698.                 *bpp = 8;
  3699.                 break;
  3700.         case DRM_FORMAT_XRGB1555:
  3701.         case DRM_FORMAT_XBGR1555:
  3702.         case DRM_FORMAT_RGBX5551:
  3703.         case DRM_FORMAT_BGRX5551:
  3704.         case DRM_FORMAT_ARGB1555:
  3705.         case DRM_FORMAT_ABGR1555:
  3706.         case DRM_FORMAT_RGBA5551:
  3707.         case DRM_FORMAT_BGRA5551:
  3708.                 *depth = 15;
  3709.                 *bpp = 16;
  3710.                 break;
  3711.         case DRM_FORMAT_RGB565:
  3712.         case DRM_FORMAT_BGR565:
  3713.                 *depth = 16;
  3714.                 *bpp = 16;
  3715.                 break;
  3716.         case DRM_FORMAT_RGB888:
  3717.         case DRM_FORMAT_BGR888:
  3718.                 *depth = 24;
  3719.                 *bpp = 24;
  3720.                 break;
  3721.         case DRM_FORMAT_XRGB8888:
  3722.         case DRM_FORMAT_XBGR8888:
  3723.         case DRM_FORMAT_RGBX8888:
  3724.         case DRM_FORMAT_BGRX8888:
  3725.                 *depth = 24;
  3726.                 *bpp = 32;
  3727.                 break;
  3728.         case DRM_FORMAT_XRGB2101010:
  3729.         case DRM_FORMAT_XBGR2101010:
  3730.         case DRM_FORMAT_RGBX1010102:
  3731.         case DRM_FORMAT_BGRX1010102:
  3732.         case DRM_FORMAT_ARGB2101010:
  3733.         case DRM_FORMAT_ABGR2101010:
  3734.         case DRM_FORMAT_RGBA1010102:
  3735.         case DRM_FORMAT_BGRA1010102:
  3736.                 *depth = 30;
  3737.                 *bpp = 32;
  3738.                 break;
  3739.         case DRM_FORMAT_ARGB8888:
  3740.         case DRM_FORMAT_ABGR8888:
  3741.         case DRM_FORMAT_RGBA8888:
  3742.         case DRM_FORMAT_BGRA8888:
  3743.                 *depth = 32;
  3744.                 *bpp = 32;
  3745.                 break;
  3746.         default:
  3747.                 DRM_DEBUG_KMS("unsupported pixel format\n");
  3748.                 *depth = 0;
  3749.                 *bpp = 0;
  3750.                 break;
  3751.         }
  3752. }
  3753. EXPORT_SYMBOL(drm_fb_get_bpp_depth);
  3754.  
  3755. /**
  3756.  * drm_format_num_planes - get the number of planes for format
  3757.  * @format: pixel format (DRM_FORMAT_*)
  3758.  *
  3759.  * RETURNS:
  3760.  * The number of planes used by the specified pixel format.
  3761.  */
  3762. int drm_format_num_planes(uint32_t format)
  3763. {
  3764.         switch (format) {
  3765.         case DRM_FORMAT_YUV410:
  3766.         case DRM_FORMAT_YVU410:
  3767.         case DRM_FORMAT_YUV411:
  3768.         case DRM_FORMAT_YVU411:
  3769.         case DRM_FORMAT_YUV420:
  3770.         case DRM_FORMAT_YVU420:
  3771.         case DRM_FORMAT_YUV422:
  3772.         case DRM_FORMAT_YVU422:
  3773.         case DRM_FORMAT_YUV444:
  3774.         case DRM_FORMAT_YVU444:
  3775.                 return 3;
  3776.         case DRM_FORMAT_NV12:
  3777.         case DRM_FORMAT_NV21:
  3778.         case DRM_FORMAT_NV16:
  3779.         case DRM_FORMAT_NV61:
  3780.         case DRM_FORMAT_NV24:
  3781.         case DRM_FORMAT_NV42:
  3782.                 return 2;
  3783.         default:
  3784.                 return 1;
  3785.         }
  3786. }
  3787. EXPORT_SYMBOL(drm_format_num_planes);
  3788.  
  3789. /**
  3790.  * drm_format_plane_cpp - determine the bytes per pixel value
  3791.  * @format: pixel format (DRM_FORMAT_*)
  3792.  * @plane: plane index
  3793.  *
  3794.  * RETURNS:
  3795.  * The bytes per pixel value for the specified plane.
  3796.  */
  3797. int drm_format_plane_cpp(uint32_t format, int plane)
  3798. {
  3799.         unsigned int depth;
  3800.         int bpp;
  3801.  
  3802.         if (plane >= drm_format_num_planes(format))
  3803.                 return 0;
  3804.  
  3805.         switch (format) {
  3806.         case DRM_FORMAT_YUYV:
  3807.         case DRM_FORMAT_YVYU:
  3808.         case DRM_FORMAT_UYVY:
  3809.         case DRM_FORMAT_VYUY:
  3810.                 return 2;
  3811.         case DRM_FORMAT_NV12:
  3812.         case DRM_FORMAT_NV21:
  3813.         case DRM_FORMAT_NV16:
  3814.         case DRM_FORMAT_NV61:
  3815.         case DRM_FORMAT_NV24:
  3816.         case DRM_FORMAT_NV42:
  3817.                 return plane ? 2 : 1;
  3818.         case DRM_FORMAT_YUV410:
  3819.         case DRM_FORMAT_YVU410:
  3820.         case DRM_FORMAT_YUV411:
  3821.         case DRM_FORMAT_YVU411:
  3822.         case DRM_FORMAT_YUV420:
  3823.         case DRM_FORMAT_YVU420:
  3824.         case DRM_FORMAT_YUV422:
  3825.         case DRM_FORMAT_YVU422:
  3826.         case DRM_FORMAT_YUV444:
  3827.         case DRM_FORMAT_YVU444:
  3828.                 return 1;
  3829.         default:
  3830.                 drm_fb_get_bpp_depth(format, &depth, &bpp);
  3831.                 return bpp >> 3;
  3832.         }
  3833. }
  3834. EXPORT_SYMBOL(drm_format_plane_cpp);
  3835.  
  3836. /**
  3837.  * drm_format_horz_chroma_subsampling - get the horizontal chroma subsampling factor
  3838.  * @format: pixel format (DRM_FORMAT_*)
  3839.  *
  3840.  * RETURNS:
  3841.  * The horizontal chroma subsampling factor for the
  3842.  * specified pixel format.
  3843.  */
  3844. int drm_format_horz_chroma_subsampling(uint32_t format)
  3845. {
  3846.         switch (format) {
  3847.         case DRM_FORMAT_YUV411:
  3848.         case DRM_FORMAT_YVU411:
  3849.         case DRM_FORMAT_YUV410:
  3850.         case DRM_FORMAT_YVU410:
  3851.                 return 4;
  3852.         case DRM_FORMAT_YUYV:
  3853.         case DRM_FORMAT_YVYU:
  3854.         case DRM_FORMAT_UYVY:
  3855.         case DRM_FORMAT_VYUY:
  3856.         case DRM_FORMAT_NV12:
  3857.         case DRM_FORMAT_NV21:
  3858.         case DRM_FORMAT_NV16:
  3859.         case DRM_FORMAT_NV61:
  3860.         case DRM_FORMAT_YUV422:
  3861.         case DRM_FORMAT_YVU422:
  3862.         case DRM_FORMAT_YUV420:
  3863.         case DRM_FORMAT_YVU420:
  3864.                 return 2;
  3865.         default:
  3866.                 return 1;
  3867.         }
  3868. }
  3869. EXPORT_SYMBOL(drm_format_horz_chroma_subsampling);
  3870.  
  3871. /**
  3872.  * drm_format_vert_chroma_subsampling - get the vertical chroma subsampling factor
  3873.  * @format: pixel format (DRM_FORMAT_*)
  3874.  *
  3875.  * RETURNS:
  3876.  * The vertical chroma subsampling factor for the
  3877.  * specified pixel format.
  3878.  */
  3879. int drm_format_vert_chroma_subsampling(uint32_t format)
  3880. {
  3881.         switch (format) {
  3882.         case DRM_FORMAT_YUV410:
  3883.         case DRM_FORMAT_YVU410:
  3884.                 return 4;
  3885.         case DRM_FORMAT_YUV420:
  3886.         case DRM_FORMAT_YVU420:
  3887.         case DRM_FORMAT_NV12:
  3888.         case DRM_FORMAT_NV21:
  3889.                 return 2;
  3890.         default:
  3891.                 return 1;
  3892.         }
  3893. }
  3894. EXPORT_SYMBOL(drm_format_vert_chroma_subsampling);
  3895.