Merge tag 'drm-intel-next-2014-12-19' of git://anongit.freedesktop.org/drm-intel...
[cascardo/linux.git] / drivers / gpu / drm / drm_crtc.c
index 46fa094..7c1786d 100644 (file)
@@ -831,6 +831,7 @@ int drm_connector_init(struct drm_device *dev,
                       const struct drm_connector_funcs *funcs,
                       int connector_type)
 {
+       struct drm_mode_config *config = &dev->mode_config;
        int ret;
        struct ida *connector_ida =
                &drm_connector_enum_list[connector_type].ida;
@@ -869,16 +870,20 @@ int drm_connector_init(struct drm_device *dev,
 
        /* We should add connectors at the end to avoid upsetting the connector
         * index too much. */
-       list_add_tail(&connector->head, &dev->mode_config.connector_list);
-       dev->mode_config.num_connector++;
+       list_add_tail(&connector->head, &config->connector_list);
+       config->num_connector++;
 
        if (connector_type != DRM_MODE_CONNECTOR_VIRTUAL)
                drm_object_attach_property(&connector->base,
-                                             dev->mode_config.edid_property,
+                                             config->edid_property,
                                              0);
 
        drm_object_attach_property(&connector->base,
-                                     dev->mode_config.dpms_property, 0);
+                                     config->dpms_property, 0);
+
+       if (drm_core_check_feature(dev, DRIVER_ATOMIC)) {
+               drm_object_attach_property(&connector->base, config->prop_crtc_id, 0);
+       }
 
        connector->debugfs_entry = NULL;
 
@@ -2653,6 +2658,27 @@ int drm_mode_set_config_internal(struct drm_mode_set *set)
 }
 EXPORT_SYMBOL(drm_mode_set_config_internal);
 
+/**
+ * drm_crtc_get_hv_timing - Fetches hdisplay/vdisplay for given mode
+ * @mode: mode to query
+ * @hdisplay: hdisplay value to fill in
+ * @vdisplay: vdisplay value to fill in
+ *
+ * The vdisplay value will be doubled if the specified mode is a stereo mode of
+ * the appropriate layout.
+ */
+void drm_crtc_get_hv_timing(const struct drm_display_mode *mode,
+                           int *hdisplay, int *vdisplay)
+{
+       struct drm_display_mode adjusted;
+
+       drm_mode_copy(&adjusted, mode);
+       drm_mode_set_crtcinfo(&adjusted, CRTC_STEREO_DOUBLE_ONLY);
+       *hdisplay = adjusted.crtc_hdisplay;
+       *vdisplay = adjusted.crtc_vdisplay;
+}
+EXPORT_SYMBOL(drm_crtc_get_hv_timing);
+
 /**
  * drm_crtc_check_viewport - Checks that a framebuffer is big enough for the
  *     CRTC viewport
@@ -2670,16 +2696,7 @@ int drm_crtc_check_viewport(const struct drm_crtc *crtc,
 {
        int hdisplay, vdisplay;
 
-       hdisplay = mode->hdisplay;
-       vdisplay = mode->vdisplay;
-
-       if (drm_mode_is_stereo(mode)) {
-               struct drm_display_mode adjusted = *mode;
-
-               drm_mode_set_crtcinfo(&adjusted, CRTC_STEREO_DOUBLE);
-               hdisplay = adjusted.crtc_hdisplay;
-               vdisplay = adjusted.crtc_vdisplay;
-       }
+       drm_crtc_get_hv_timing(mode, &hdisplay, &vdisplay);
 
        if (crtc->invert_dimensions)
                swap(hdisplay, vdisplay);
@@ -2775,6 +2792,12 @@ int drm_mode_setcrtc(struct drm_device *dev, void *data,
                        goto out;
                }
 
+               mode->status = drm_mode_validate_basic(mode);
+               if (mode->status != MODE_OK) {
+                       ret = -EINVAL;
+                       goto out;
+               }
+
                drm_mode_set_crtcinfo(mode, CRTC_INTERLACE_HALVE_V);
 
                ret = drm_crtc_check_viewport(crtc, crtc_req->x, crtc_req->y,
@@ -4298,7 +4321,7 @@ EXPORT_SYMBOL(drm_mode_connector_update_edid_property);
  * object to which the property is attached has a chance to take it's own
  * reference).
  */
-static bool drm_property_change_valid_get(struct drm_property *property,
+bool drm_property_change_valid_get(struct drm_property *property,
                                         uint64_t value, struct drm_mode_object **ref)
 {
        int i;
@@ -4360,7 +4383,7 @@ static bool drm_property_change_valid_get(struct drm_property *property,
        return false;
 }
 
-static void drm_property_change_valid_put(struct drm_property *property,
+void drm_property_change_valid_put(struct drm_property *property,
                struct drm_mode_object *ref)
 {
        if (!ref)