@@ -1602,8 +1602,10 @@ intel_sdvo_hdmi_sink_detect(struct drm_connector *connector, u16 response)
kfree(edid);
intel_output->base.display_info.raw_edid = NULL;
- } else if (response & (SDVO_OUTPUT_TMDS0 | SDVO_OUTPUT_TMDS1))
- status = connector_status_disconnected;
+ } else {
+ status = connector_status_connected;
+ DRM_DEBUG_KMS("No EDID is obtained. But still connected.\n");
+ }
return status;
}
@@ -1634,7 +1636,55 @@ static enum drm_connector_status intel_sdvo_detect(struct drm_connector *connect
return connector_status_unknown;
sdvo_priv->attached_output = response;
}
- return intel_sdvo_hdmi_sink_detect(connector, response);
+ /*
+ * When the response doesn't belong to TMDS,it is unnecessary to check
+ * the EDID. In such case it will be detected as connected.
+ */
+ if (response & (SDVO_OUTPUT_TMDS0 | SDVO_OUTPUT_TMDS1))
+ return intel_sdvo_hdmi_sink_detect(connector, response);
+ else
+ return connector_status_connected;
+}
+
+/* the default mode list for the DVI-D device when
+ * there is no EDID
+ */
+static struct drm_display_mode sdvo_default_modes[] = {
+ /* 640x480@60Hz */
+ { DRM_MODE("640x480", DRM_MODE_TYPE_DRIVER, 25175, 640, 656,
+ 752, 800, 0, 480, 489, 492, 525, 0,
+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
+ /* 800x600@60Hz */
+ { DRM_MODE("800x600", DRM_MODE_TYPE_DRIVER, 40000, 800, 840,
+ 968, 1056, 0, 600, 601, 605, 628, 0,
+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
+ /* 1024x768@60Hz */
+ { DRM_MODE("1024x768", DRM_MODE_TYPE_DRIVER, 65000, 1024, 1048,
+ 1184, 1344, 0, 768, 771, 777, 806, 0,
+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_NVSYNC) },
+ /* 1280x960@60Hz */
+ { DRM_MODE("1280x960", DRM_MODE_TYPE_DRIVER, 108000, 1280, 1376,
+ 1488, 1800, 0, 960, 961, 964, 1000, 0,
+ DRM_MODE_FLAG_PHSYNC | DRM_MODE_FLAG_PVSYNC) },
+ /* 1680x1050@60Hz */
+ { DRM_MODE("1680x1050", DRM_MODE_TYPE_DRIVER, 146250, 1680, 1784,
+ 1960, 2240, 0, 1050, 1053, 1059, 1089, 0,
+ DRM_MODE_FLAG_NHSYNC | DRM_MODE_FLAG_PVSYNC) },
+};
+
+static void intel_sdvo_add_default_modes(struct drm_connector *connector)
+{
+ struct drm_device *dev = connector->dev;
+ struct drm_display_mode *mode, *ptr;
+ int i;
+
+ for (i = 0; i < sizeof(sdvo_default_modes) /
+ sizeof(struct drm_display_mode); i++) {
+ mode = &sdvo_default_modes[i];
+ ptr = drm_mode_duplicate(dev, mode);
+ if (ptr)
+ drm_mode_probed_add(connector, ptr);
+ }
}
static void intel_sdvo_get_ddc_modes(struct drm_connector *connector)
@@ -1662,10 +1712,17 @@ static void intel_sdvo_get_ddc_modes(struct drm_connector *connector)
digital_ddc_bus = intel_output->ddc_bus;
intel_output->ddc_bus = sdvo_priv->analog_ddc_bus;
- (void) intel_ddc_get_modes(intel_output);
+ num_modes = intel_ddc_get_modes(intel_output);
intel_output->ddc_bus = digital_ddc_bus;
}
+ /*
+ * If we can't get the EDID for DVI-D monitor, we will add some default
+ * modes for it.
+ * For example: 1680x1050@60, 1280x960@60Hz, 1024x768@60, 800x600@60Hz.
+ */
+ if (num_modes == 0)
+ intel_sdvo_add_default_modes(connector);
}
/*