aboutsummaryrefslogtreecommitdiffstats
path: root/common/recipes-kernel/linux/linux-yocto-4.19.8/0837-drm-amd-display-Fix-Scaling-RMX_-for-DC-driver.patch
diff options
context:
space:
mode:
Diffstat (limited to 'common/recipes-kernel/linux/linux-yocto-4.19.8/0837-drm-amd-display-Fix-Scaling-RMX_-for-DC-driver.patch')
-rw-r--r--common/recipes-kernel/linux/linux-yocto-4.19.8/0837-drm-amd-display-Fix-Scaling-RMX_-for-DC-driver.patch143
1 files changed, 143 insertions, 0 deletions
diff --git a/common/recipes-kernel/linux/linux-yocto-4.19.8/0837-drm-amd-display-Fix-Scaling-RMX_-for-DC-driver.patch b/common/recipes-kernel/linux/linux-yocto-4.19.8/0837-drm-amd-display-Fix-Scaling-RMX_-for-DC-driver.patch
new file mode 100644
index 00000000..86655941
--- /dev/null
+++ b/common/recipes-kernel/linux/linux-yocto-4.19.8/0837-drm-amd-display-Fix-Scaling-RMX_-for-DC-driver.patch
@@ -0,0 +1,143 @@
+From cb1113cf525ccce5e6dcbe863f2340a99a3d4a06 Mon Sep 17 00:00:00 2001
+From: Bhawanpreet Lakha <Bhawanpreet.Lakha@amd.com>
+Date: Fri, 16 Nov 2018 11:46:14 -0500
+Subject: [PATCH 0837/2940] drm/amd/display: Fix Scaling (RMX_*) for DC driver
+
+Before:
+We use drm_match_cea_mode() to get the vic for any mode we
+want to set, most of the time vic will be different for the new mode.
+
+DC uses memcmp to check if timing changed, in this case DC will
+say timing changed and we endup doing a full modeset.
+
+Current:
+Now we check if !RMX_OFF and old_refresh == new_refresh if so
+we copy the vic from old timing. In a case where we are currently on
+a lower timing and want to change to higher mode, stream->dst will be
+different and cause us to do a full modeset, which is what we want.
+
+Signed-off-by: Bhawanpreet Lakha <Bhawanpreet.Lakha@amd.com>
+Reviewed-by: Leo Li <sunpeng.li@amd.com>
+Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
+---
+ .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 49 ++++++++++++++-----
+ 1 file changed, 38 insertions(+), 11 deletions(-)
+
+diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+index cc1a6655884e..1b9030443e09 100644
+--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
++++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+@@ -2564,7 +2564,8 @@ static void adjust_colour_depth_from_display_info(struct dc_crtc_timing *timing_
+ static void
+ fill_stream_properties_from_drm_display_mode(struct dc_stream_state *stream,
+ const struct drm_display_mode *mode_in,
+- const struct drm_connector *connector)
++ const struct drm_connector *connector,
++ const struct dc_stream_state *old_stream)
+ {
+ struct dc_crtc_timing *timing_out = &stream->timing;
+ const struct drm_display_info *info = &connector->display_info;
+@@ -2590,7 +2591,18 @@ fill_stream_properties_from_drm_display_mode(struct dc_stream_state *stream,
+ connector);
+ timing_out->scan_type = SCANNING_TYPE_NODATA;
+ timing_out->hdmi_vic = 0;
+- timing_out->vic = drm_match_cea_mode(mode_in);
++
++ if(old_stream) {
++ timing_out->vic = old_stream->timing.vic;
++ timing_out->flags.HSYNC_POSITIVE_POLARITY = old_stream->timing.flags.HSYNC_POSITIVE_POLARITY;
++ timing_out->flags.VSYNC_POSITIVE_POLARITY = old_stream->timing.flags.VSYNC_POSITIVE_POLARITY;
++ } else {
++ timing_out->vic = drm_match_cea_mode(mode_in);
++ if (mode_in->flags & DRM_MODE_FLAG_PHSYNC)
++ timing_out->flags.HSYNC_POSITIVE_POLARITY = 1;
++ if (mode_in->flags & DRM_MODE_FLAG_PVSYNC)
++ timing_out->flags.VSYNC_POSITIVE_POLARITY = 1;
++ }
+
+ timing_out->h_addressable = mode_in->crtc_hdisplay;
+ timing_out->h_total = mode_in->crtc_htotal;
+@@ -2606,10 +2618,6 @@ fill_stream_properties_from_drm_display_mode(struct dc_stream_state *stream,
+ mode_in->crtc_vsync_end - mode_in->crtc_vsync_start;
+ timing_out->pix_clk_khz = mode_in->crtc_clock;
+ timing_out->aspect_ratio = get_aspect_ratio(mode_in);
+- if (mode_in->flags & DRM_MODE_FLAG_PHSYNC)
+- timing_out->flags.HSYNC_POSITIVE_POLARITY = 1;
+- if (mode_in->flags & DRM_MODE_FLAG_PVSYNC)
+- timing_out->flags.VSYNC_POSITIVE_POLARITY = 1;
+
+ stream->output_color_space = get_output_color_space(timing_out);
+
+@@ -2772,13 +2780,18 @@ static void dm_enable_per_frame_crtc_master_sync(struct dc_state *context)
+ static struct dc_stream_state *
+ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
+ const struct drm_display_mode *drm_mode,
+- const struct dm_connector_state *dm_state)
++ const struct dm_connector_state *dm_state,
++ const struct dc_stream_state *old_stream)
+ {
+ struct drm_display_mode *preferred_mode = NULL;
+ struct drm_connector *drm_connector;
+ struct dc_stream_state *stream = NULL;
+ struct drm_display_mode mode = *drm_mode;
+ bool native_mode_found = false;
++ bool scale = dm_state ? (dm_state->scaling != RMX_OFF) : false;
++ int mode_refresh;
++ int preferred_refresh;
++
+ struct dc_sink *sink = NULL;
+ if (aconnector == NULL) {
+ DRM_ERROR("aconnector is NULL!\n");
+@@ -2817,6 +2830,8 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
+ struct drm_display_mode,
+ head);
+
++ mode_refresh = drm_mode_vrefresh(&mode);
++
+ if (preferred_mode == NULL) {
+ /*
+ * This may not be an error, the use case is when we have no
+@@ -2834,8 +2849,19 @@ create_stream_for_sink(struct amdgpu_dm_connector *aconnector,
+ if (!dm_state)
+ drm_mode_set_crtcinfo(&mode, 0);
+
+- fill_stream_properties_from_drm_display_mode(stream,
+- &mode, &aconnector->base);
++ preferred_refresh = drm_mode_vrefresh(preferred_mode);
++
++ /*
++ * If scaling is enabled and refresh rate didn't change
++ * we copy the vic and polarities of the old timings
++ */
++ if (!scale || mode_refresh != preferred_refresh)
++ fill_stream_properties_from_drm_display_mode(stream,
++ &mode, &aconnector->base, NULL);
++ else
++ fill_stream_properties_from_drm_display_mode(stream,
++ &mode, &aconnector->base, old_stream);
++
+ update_stream_scaling_settings(&mode, dm_state, stream);
+
+ fill_audio_info(
+@@ -3256,7 +3282,7 @@ enum drm_mode_status amdgpu_dm_connector_mode_valid(struct drm_connector *connec
+ goto fail;
+ }
+
+- stream = create_stream_for_sink(aconnector, mode, NULL);
++ stream = create_stream_for_sink(aconnector, mode, NULL, NULL);
+ if (stream == NULL) {
+ DRM_ERROR("Failed to create stream for sink!\n");
+ goto fail;
+@@ -5118,7 +5144,8 @@ static int dm_update_crtcs_state(struct amdgpu_display_manager *dm,
+
+ new_stream = create_stream_for_sink(aconnector,
+ &new_crtc_state->mode,
+- dm_new_conn_state);
++ dm_new_conn_state,
++ dm_old_crtc_state->stream);
+
+ /*
+ * we can have no stream on ACTION_SET if a display
+--
+2.17.1
+