aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2012-11-23 06:57:56 -0500
committerDaniel Vetter <daniel.vetter@ffwll.ch>2012-11-29 05:42:38 -0500
commitfc37381cc8ae2c24b8ece33659e69a0605ca074c (patch)
tree9773583ec49a5b875dbde4145f048cf6f3341960 /drivers/gpu/drm
parent9a69b885e964cf93064f1a16ddd06ebb7d46ac17 (diff)
drm/i915: Increase the response time for slow SDVO devices
Some devices may respond very slowly and only flag that the reply is pending within the first 15us response window. Be kind to such devices and wait a further 15ms, before checking for the pending reply. This moves the existing special case delay of 30ms down from the detection routine into the common path and pretends to explain it... v2: Simplify the loop constructs as suggested by Jani Nikula. References: https://bugs.freedesktop.org/show_bug.cgi?id=36997 Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk> Reviewed-by: Jani Nikula <jani.nikula@intel.com> Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Diffstat (limited to 'drivers/gpu/drm')
-rw-r--r--drivers/gpu/drm/i915/intel_sdvo.c31
1 files changed, 19 insertions, 12 deletions
diff --git a/drivers/gpu/drm/i915/intel_sdvo.c b/drivers/gpu/drm/i915/intel_sdvo.c
index a4bee83df745..0e03985b0fe4 100644
--- a/drivers/gpu/drm/i915/intel_sdvo.c
+++ b/drivers/gpu/drm/i915/intel_sdvo.c
@@ -509,7 +509,7 @@ out:
509static bool intel_sdvo_read_response(struct intel_sdvo *intel_sdvo, 509static bool intel_sdvo_read_response(struct intel_sdvo *intel_sdvo,
510 void *response, int response_len) 510 void *response, int response_len)
511{ 511{
512 u8 retry = 5; 512 u8 retry = 15; /* 5 quick checks, followed by 10 long checks */
513 u8 status; 513 u8 status;
514 int i; 514 int i;
515 515
@@ -522,14 +522,27 @@ static bool intel_sdvo_read_response(struct intel_sdvo *intel_sdvo,
522 * command to be complete. 522 * command to be complete.
523 * 523 *
524 * Check 5 times in case the hardware failed to read the docs. 524 * Check 5 times in case the hardware failed to read the docs.
525 *
526 * Also beware that the first response by many devices is to
527 * reply PENDING and stall for time. TVs are notorious for
528 * requiring longer than specified to complete their replies.
529 * Originally (in the DDX long ago), the delay was only ever 15ms
530 * with an additional delay of 30ms applied for TVs added later after
531 * many experiments. To accommodate both sets of delays, we do a
532 * sequence of slow checks if the device is falling behind and fails
533 * to reply within 5*15µs.
525 */ 534 */
526 if (!intel_sdvo_read_byte(intel_sdvo, 535 if (!intel_sdvo_read_byte(intel_sdvo,
527 SDVO_I2C_CMD_STATUS, 536 SDVO_I2C_CMD_STATUS,
528 &status)) 537 &status))
529 goto log_fail; 538 goto log_fail;
530 539
531 while (status == SDVO_CMD_STATUS_PENDING && retry--) { 540 while (status == SDVO_CMD_STATUS_PENDING && --retry) {
532 udelay(15); 541 if (retry < 10)
542 msleep(15);
543 else
544 udelay(15);
545
533 if (!intel_sdvo_read_byte(intel_sdvo, 546 if (!intel_sdvo_read_byte(intel_sdvo,
534 SDVO_I2C_CMD_STATUS, 547 SDVO_I2C_CMD_STATUS,
535 &status)) 548 &status))
@@ -1535,15 +1548,9 @@ intel_sdvo_detect(struct drm_connector *connector, bool force)
1535 struct intel_sdvo_connector *intel_sdvo_connector = to_intel_sdvo_connector(connector); 1548 struct intel_sdvo_connector *intel_sdvo_connector = to_intel_sdvo_connector(connector);
1536 enum drm_connector_status ret; 1549 enum drm_connector_status ret;
1537 1550
1538 if (!intel_sdvo_write_cmd(intel_sdvo, 1551 if (!intel_sdvo_get_value(intel_sdvo,
1539 SDVO_CMD_GET_ATTACHED_DISPLAYS, NULL, 0)) 1552 SDVO_CMD_GET_ATTACHED_DISPLAYS,
1540 return connector_status_unknown; 1553 &response, 2))
1541
1542 /* add 30ms delay when the output type might be TV */
1543 if (intel_sdvo->caps.output_flags & SDVO_TV_MASK)
1544 msleep(30);
1545
1546 if (!intel_sdvo_read_response(intel_sdvo, &response, 2))
1547 return connector_status_unknown; 1554 return connector_status_unknown;
1548 1555
1549 DRM_DEBUG_KMS("SDVO response %d %d [%x]\n", 1556 DRM_DEBUG_KMS("SDVO response %d %d [%x]\n",