Skip to content

Commit 05666a1

Browse files
Lawstorant1Naim
authored andcommitted
drm/amd/display: Enable HDMI VRR over PCON
[Why] Not all TVs support FreeSync and many TVs suffer from VRR flickering while Freesync is activated. [How] This works the same as FreeSync over PCON just without sending FreeSync info packets (we're sending standard DisplayPort info packets) + reading the VRR range from the HDMI Forum vendor specific data block. PCONs take over HDMI VRR triggering. Prefer HDMI VRR over FreeSync to reduce VRR flickering on many TVs. FreeSync over HDMI seems to be a fallback solution and not a first-class citizen. This especially helps VMM7100. Tested with VMM7100 and CH7218 based adapters on multiple HDMI 2.1 and HDMI 2.0 devices. (Samsung S95B, LG C4, Sony Bravia 8, Dell AW3423DWF) Closes: https://gitlab.freedesktop.org/drm/amd/-/issues/4805 Signed-off-by: Tomasz Pakuła <tomasz.pakula.oficjalny@gmail.com> Tested-by: Bernhard Berger <bernhard.berger@gmail.com> Reviewed-by: Harry Wentland <harry.wentland@amd.com>
1 parent 2c81389 commit 05666a1

1 file changed

Lines changed: 23 additions & 6 deletions

File tree

drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c

Lines changed: 23 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13267,6 +13267,17 @@ static void monitor_range_from_vsdb(struct drm_display_info *display,
1326713267
display->monitor_range.max_vfreq = vsdb->max_refresh_rate_hz;
1326813268
}
1326913269

13270+
/**
13271+
* Get VRR range from HDMI VRR info in EDID.
13272+
*
13273+
* @conn: drm_connector with HDMI VRR info
13274+
*/
13275+
static void monitor_range_from_hdmi(struct drm_display_info *display)
13276+
{
13277+
display->monitor_range.min_vfreq = display->hdmi.vrr_cap.vrr_min;
13278+
display->monitor_range.max_vfreq = display->hdmi.vrr_cap.vrr_max;
13279+
}
13280+
1327013281
/*
1327113282
* Returns true if connector is capable of freesync
1327213283
* Optionally, can fetch the range from AMD vsdb
@@ -13331,6 +13342,7 @@ void amdgpu_dm_update_freesync_caps(struct drm_connector *connector,
1333113342
struct amdgpu_device *adev = drm_to_adev(connector->dev);
1333213343
struct amdgpu_hdmi_vsdb_info vsdb_info = {0};
1333313344
struct amdgpu_hdmi_vsdb_info vsdb_did = {0};
13345+
struct drm_hdmi_vrr_cap hdmi_vrr = {0};
1333413346
struct dpcd_caps dpcd_caps = {0};
1333513347
const struct edid *edid;
1333613348
bool freesync_capable = false;
@@ -13366,6 +13378,7 @@ void amdgpu_dm_update_freesync_caps(struct drm_connector *connector,
1336613378
/* Gather all data */
1336713379
edid = drm_edid_raw(drm_edid); // FIXME: Get rid of drm_edid_raw()
1336813380
parse_amd_vsdb_cea(amdgpu_dm_connector, edid, &vsdb_info);
13381+
hdmi_vrr = connector->display_info.hdmi.vrr_cap;
1336913382

1337013383
if (amdgpu_dm_connector->dc_link) {
1337113384
dpcd_caps = amdgpu_dm_connector->dc_link->dpcd_caps;
@@ -13407,13 +13420,17 @@ void amdgpu_dm_update_freesync_caps(struct drm_connector *connector,
1340713420
freesync_capable = copy_range_to_amdgpu_connector(connector);
1340813421

1340913422
/* DP -> HDMI PCON */
13410-
} else if (pcon_allowed && vsdb_info.freesync_supported) {
13411-
amdgpu_dm_connector->as_type = ADAPTIVE_SYNC_TYPE_PCON_ALLOWED;
13412-
amdgpu_dm_connector->pack_sdp_v1_3 = true;
13413-
amdgpu_dm_connector->vsdb_info = vsdb_info;
13423+
} else if (pcon_allowed) {
13424+
/* Prefer HDMI VRR */
13425+
if (hdmi_vrr.supported && hdmi_vrr.vrr_max > 0)
13426+
monitor_range_from_hdmi(&connector->display_info);
13427+
else if (vsdb_info.freesync_supported) {
13428+
amdgpu_dm_connector->vsdb_info = vsdb_info;
13429+
monitor_range_from_vsdb(&connector->display_info, &vsdb_info);
13430+
}
1341413431

13415-
parse_amd_vsdb_cea(amdgpu_dm_connector, edid, &vsdb_info);
13416-
monitor_range_from_vsdb(&connector->display_info, &vsdb_info);
13432+
amdgpu_dm_connector->pack_sdp_v1_3 = true;
13433+
amdgpu_dm_connector->as_type = ADAPTIVE_SYNC_TYPE_PCON_ALLOWED;
1341713434
freesync_capable = copy_range_to_amdgpu_connector(connector);
1341813435
}
1341913436

0 commit comments

Comments
 (0)