hdmi_frl_perform_link_training() gives LTS:3 a single budget of 105 polls
at 2 ms (~210 ms) that starts at the FRL_Rate write and is not restarted
when the sink raises its first FLT_update with the LTP request. A sink
that needs close to 200 ms after the LTP request to report lock therefore
fails whenever its LTP request itself takes more than a few tens of ms.
Measured on an LG C2 (GSM 49352, 2022) driven by a Strix Halo DP-HDMI
FRL PCON, DPMS off/on with drm.debug=0x2, kernel 7.2.6:
6G x4 (3840x2160@60 10bpc): LTP request at poll 11 (~21 ms),
lock at poll 100 (~179 ms later): PASSED first try.
10G x4 (3840x2160@120 10bpc): LTP request at poll 22 (~44 ms),
no lock by poll 105: "FAILED - Timeout waiting for FLT_UPDATE".
Retry 200 ms later: LTP request at poll 11, lock at poll 101:
PASSED.
The sink answers FLT_READY on the first poll every time and locks in a
steady ~180 ms at both rates, so it is neither slow to wake nor
marginal; the total just does not fit 210 ms once the LTP request is
late, which happens far more often at 10G. On this system that is the
difference between reliable DPMS wakes at 4K60 and mostly dark ones at
4K120: hdmi_frl_perform_link_training_with_retries() retrains at the same
rate up to four times 200 ms apart and the output is then left dark.
"drm/amd/display: Update and revert FRL LT Timeout behaviour" already
allows 155 polls (~300 ms) for 16 Gbps and above. Use that budget at
every rate. With the change applied to 7.2.6, five consecutive DPMS
wakes at 10G x4 trained on the first attempt; three of them locked at
poll 104-105, i.e. inside the last 1-2 polls of the old budget.
Cc: Fangzhi Zuo <[email protected]>
Signed-off-by: David Janice <[email protected]>
---
.../amd/display/dc/link/protocols/link_hdmi_frl.c | 14 +++++++++++---
1 file changed, 11 insertions(+), 3 deletions(-)
diff --git a/drivers/gpu/drm/amd/display/dc/link/protocols/link_hdmi_frl.c
b/drivers/gpu/drm/amd/display/dc/link/protocols/link_hdmi_frl.c
index 7f93009..005feb9 100644
--- a/drivers/gpu/drm/amd/display/dc/link/protocols/link_hdmi_frl.c
+++ b/drivers/gpu/drm/amd/display/dc/link/protocols/link_hdmi_frl.c
@@ -528,10 +528,18 @@ static enum link_result
hdmi_frl_perform_link_training(struct ddc_service *ddc_s
FRL_INFO("FRL LINK TRAINING: Poll for FLT_UPDATE.\n");
/*LTS:3: Start Link Training*/
- /*Start FLT Timer = 200 ms, or 300ms if link rate >= 16Gbps*/
+ /*
+ * Start FLT Timer = 300 ms. HDMI 2.1 specifies FLT_TIMEOUT =
200 ms,
+ * but this budget runs from the FRL_Rate write to the final
+ * FLT_update and some sinks need more than that in total: an
LG C2
+ * (2022) at 10G x4 raises its first FLT_update (the LTP
request)
+ * ~45 ms after the rate write and reports lock a further ~180
ms
+ * later, ~225 ms in all, so it failed the 105-poll (~210 ms)
budget on
+ * most DPMS wakes at 4K120 while at 6G x4 (~20 ms + ~180 ms)
it just
+ * fit. Use the 300 ms already allowed for >= 16 Gbps at every
rate.
+ */
num_polls = 0;
- if (link_settings->frl_link_rate >= HDMI_FRL_LINK_RATE_16GBPS)
- max_polls = 155;
+ max_polls = 155;
while (num_polls < max_polls) {
flt_poll_cur_time = dm_get_timestamp(ddc_service->ctx);
--
2.55.0