Commit cdb0e95b authored by Keith Packard's avatar Keith Packard

drm/i915: Try harder during dp pattern 1 link training

Instead of going through the sequence just once, run through the whole
set up to 5 times to see if something can work. This isn't part of the
DP spec, but the BIOS seems to do it, and given that link training
failure is so bad, it seems reasonable to follow suit.
Signed-off-by: default avatarKeith Packard <keithp@keithp.com>
Reviewed-by: default avatarJesse Barnes <jbarnes@virtuousgeek.org>
parent 21264c63
...@@ -1581,7 +1581,7 @@ intel_dp_start_link_train(struct intel_dp *intel_dp) ...@@ -1581,7 +1581,7 @@ intel_dp_start_link_train(struct intel_dp *intel_dp)
int i; int i;
uint8_t voltage; uint8_t voltage;
bool clock_recovery = false; bool clock_recovery = false;
int tries; int voltage_tries, loop_tries;
u32 reg; u32 reg;
uint32_t DP = intel_dp->DP; uint32_t DP = intel_dp->DP;
...@@ -1608,7 +1608,8 @@ intel_dp_start_link_train(struct intel_dp *intel_dp) ...@@ -1608,7 +1608,8 @@ intel_dp_start_link_train(struct intel_dp *intel_dp)
DP &= ~DP_LINK_TRAIN_MASK; DP &= ~DP_LINK_TRAIN_MASK;
memset(intel_dp->train_set, 0, 4); memset(intel_dp->train_set, 0, 4);
voltage = 0xff; voltage = 0xff;
tries = 0; voltage_tries = 0;
loop_tries = 0;
clock_recovery = false; clock_recovery = false;
for (;;) { for (;;) {
/* Use intel_dp->train_set[0] to set the voltage and pre emphasis values */ /* Use intel_dp->train_set[0] to set the voltage and pre emphasis values */
...@@ -1651,16 +1652,26 @@ intel_dp_start_link_train(struct intel_dp *intel_dp) ...@@ -1651,16 +1652,26 @@ intel_dp_start_link_train(struct intel_dp *intel_dp)
for (i = 0; i < intel_dp->lane_count; i++) for (i = 0; i < intel_dp->lane_count; i++)
if ((intel_dp->train_set[i] & DP_TRAIN_MAX_SWING_REACHED) == 0) if ((intel_dp->train_set[i] & DP_TRAIN_MAX_SWING_REACHED) == 0)
break; break;
if (i == intel_dp->lane_count) if (i == intel_dp->lane_count) {
break; ++loop_tries;
if (loop_tries == 5) {
DRM_DEBUG_KMS("too many full retries, give up\n");
break;
}
memset(intel_dp->train_set, 0, 4);
voltage_tries = 0;
continue;
}
/* Check to see if we've tried the same voltage 5 times */ /* Check to see if we've tried the same voltage 5 times */
if ((intel_dp->train_set[0] & DP_TRAIN_VOLTAGE_SWING_MASK) == voltage) { if ((intel_dp->train_set[0] & DP_TRAIN_VOLTAGE_SWING_MASK) == voltage) {
++tries; ++voltage_tries;
if (tries == 5) if (voltage_tries == 5) {
DRM_DEBUG_KMS("too many voltage retries, give up\n");
break; break;
}
} else } else
tries = 0; voltage_tries = 0;
voltage = intel_dp->train_set[0] & DP_TRAIN_VOLTAGE_SWING_MASK; voltage = intel_dp->train_set[0] & DP_TRAIN_VOLTAGE_SWING_MASK;
/* Compute new intel_dp->train_set as requested by target */ /* Compute new intel_dp->train_set as requested by target */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment