aboutsummaryrefslogtreecommitdiffstats
path: root/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.14.71/0558-drm-amd-display-add-hyst-frames-for-fixed-refresh.patch
blob: f6936ba8fcf27353b4b945c4bef6d00f6e4c6cb3 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
From fdd381953a0a247c7917c8243310cc9b58cb9657 Mon Sep 17 00:00:00 2001
From: Anthony Koo <Anthony.Koo@amd.com>
Date: Tue, 27 Jun 2017 13:27:00 -0400
Subject: [PATCH 0558/4131] drm/amd/display: add hyst frames for fixed refresh

Signed-off-by: Anthony Koo <anthony.koo@amd.com>
Reviewed-by: Anthony Koo <Anthony.Koo@amd.com>
Acked-by: Harry Wentland <Harry.Wentland@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
---
 .../drm/amd/display/modules/freesync/freesync.c    | 56 ++++++++++++++--------
 1 file changed, 36 insertions(+), 20 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/modules/freesync/freesync.c b/drivers/gpu/drm/amd/display/modules/freesync/freesync.c
index 7109742..c7da90f 100644
--- a/drivers/gpu/drm/amd/display/modules/freesync/freesync.c
+++ b/drivers/gpu/drm/amd/display/modules/freesync/freesync.c
@@ -37,6 +37,9 @@
 #define RENDER_TIMES_MAX_COUNT 20
 /* Threshold to exit BTR (to avoid frequent enter-exits at the lower limit) */
 #define BTR_EXIT_MARGIN 2000
+/* Number of consecutive frames to check before entering/exiting fixed refresh*/
+#define FIXED_REFRESH_ENTER_FRAME_COUNT 5
+#define FIXED_REFRESH_EXIT_FRAME_COUNT 5
 
 #define FREESYNC_REGISTRY_NAME "freesync_v1"
 
@@ -72,8 +75,9 @@ struct below_the_range {
 };
 
 struct fixed_refresh {
-	bool fixed_refresh_active;
-	bool program_fixed_refresh;
+	bool fixed_active;
+	bool program_fixed;
+	unsigned int frame_counter;
 };
 
 struct freesync_range {
@@ -168,8 +172,8 @@ struct mod_freesync *mod_freesync_create(struct dc *dc)
 	/* Create initial module folder in registry for freesync enable data */
 	flag.save_per_edid = true;
 	flag.save_per_link = false;
-	dm_write_persistent_data(core_dc->ctx, NULL, FREESYNC_REGISTRY_NAME, NULL, NULL,
-					0, &flag);
+	dm_write_persistent_data(core_dc->ctx, NULL, FREESYNC_REGISTRY_NAME,
+			NULL, NULL, 0, &flag);
 	flag.save_per_edid = false;
 	flag.save_per_link = false;
 	if (dm_read_persistent_data(core_dc->ctx, NULL, NULL,
@@ -422,7 +426,7 @@ static void calc_freesync_range(struct core_freesync *core_freesync,
 		min_frame_duration_in_ns) * stream->timing.pix_clk_khz),
 		stream->timing.h_total), 1000000);
 
-	/* In case of 4k free sync monitor, vmin or vmax cannot be less than vtotal */
+	/* vmin/vmax cannot be less than vtotal */
 	if (state->freesync_range.vmin < vtotal) {
 		/* Error of 1 is permissible */
 		ASSERT((state->freesync_range.vmin + 1) >= vtotal);
@@ -553,8 +557,8 @@ static void reset_freesync_state_variables(struct freesync_state* state)
 	state->btr.inserted_frame_duration_in_us = 0;
 	state->btr.program_btr = false;
 
-	state->fixed_refresh.fixed_refresh_active = false;
-	state->fixed_refresh.program_fixed_refresh = false;
+	state->fixed_refresh.fixed_active = false;
+	state->fixed_refresh.program_fixed = false;
 }
 /*
  * Sets freesync mode on a stream depending on current freesync state.
@@ -594,7 +598,7 @@ static bool set_freesync_on_streams(struct core_freesync *core_freesync,
 			if (core_freesync->map[map_index].user_enable.
 				enable_for_gaming == true &&
 				state->fullscreen == true &&
-				state->fixed_refresh.fixed_refresh_active == false) {
+				state->fixed_refresh.fixed_active == false) {
 				/* Enable freesync */
 
 				v_total_min = state->freesync_range.vmin;
@@ -1240,29 +1244,39 @@ static void update_timestamps(struct core_freesync *core_freesync,
 			state->btr.frame_counter = 0;
 
 		/* Exit Fixed Refresh mode */
-		} else if (state->fixed_refresh.fixed_refresh_active) {
+		} else if (state->fixed_refresh.fixed_active) {
 
-			state->fixed_refresh.program_fixed_refresh = true;
-			state->fixed_refresh.fixed_refresh_active = false;
+			state->fixed_refresh.frame_counter++;
 
+			if (state->fixed_refresh.frame_counter >
+					FIXED_REFRESH_EXIT_FRAME_COUNT) {
+				state->fixed_refresh.frame_counter = 0;
+				state->fixed_refresh.program_fixed = true;
+				state->fixed_refresh.fixed_active = false;
+			}
 		}
 
 	} else if (last_render_time_in_us > state->time.max_render_time_in_us) {
 
 		/* Enter Below the Range */
 		if (!state->btr.btr_active &&
-				core_freesync->map[map_index].caps->btr_supported) {
+			core_freesync->map[map_index].caps->btr_supported) {
 
 			state->btr.program_btr = true;
 			state->btr.btr_active = true;
 
 		/* Enter Fixed Refresh mode */
-		} else if (!state->fixed_refresh.fixed_refresh_active &&
+		} else if (!state->fixed_refresh.fixed_active &&
 			!core_freesync->map[map_index].caps->btr_supported) {
 
-			state->fixed_refresh.program_fixed_refresh = true;
-			state->fixed_refresh.fixed_refresh_active = true;
+			state->fixed_refresh.frame_counter++;
 
+			if (state->fixed_refresh.frame_counter >
+					FIXED_REFRESH_ENTER_FRAME_COUNT) {
+				state->fixed_refresh.frame_counter = 0;
+				state->fixed_refresh.program_fixed = true;
+				state->fixed_refresh.fixed_active = true;
+			}
 		}
 	}
 
@@ -1316,7 +1330,8 @@ static void apply_below_the_range(struct core_freesync *core_freesync,
 
 			frame_time_in_us = last_render_time_in_us /
 				mid_point_frames_ceil;
-			delta_from_mid_point_in_us_1 = (state->btr.mid_point_in_us >
+			delta_from_mid_point_in_us_1 =
+				(state->btr.mid_point_in_us >
 				frame_time_in_us) ?
 				(state->btr.mid_point_in_us - frame_time_in_us):
 				(frame_time_in_us - state->btr.mid_point_in_us);
@@ -1332,7 +1347,8 @@ static void apply_below_the_range(struct core_freesync *core_freesync,
 
 			frame_time_in_us = last_render_time_in_us /
 				mid_point_frames_floor;
-			delta_from_mid_point_in_us_2 = (state->btr.mid_point_in_us >
+			delta_from_mid_point_in_us_2 =
+				(state->btr.mid_point_in_us >
 				frame_time_in_us) ?
 				(state->btr.mid_point_in_us - frame_time_in_us):
 				(frame_time_in_us - state->btr.mid_point_in_us);
@@ -1374,15 +1390,15 @@ static void apply_fixed_refresh(struct core_freesync *core_freesync,
 	unsigned int vmin = 0, vmax = 0;
 	struct freesync_state *state = &core_freesync->map[map_index].state;
 
-	if (!state->fixed_refresh.program_fixed_refresh)
+	if (!state->fixed_refresh.program_fixed)
 		return;
 
-	state->fixed_refresh.program_fixed_refresh = false;
+	state->fixed_refresh.program_fixed = false;
 
 	/* Program Fixed Refresh */
 
 	/* Fixed Refresh set to "not active" so disengage */
-	if (!state->fixed_refresh.fixed_refresh_active) {
+	if (!state->fixed_refresh.fixed_active) {
 		set_freesync_on_streams(core_freesync, &stream, 1);
 
 	/* Fixed Refresh set to "active" so engage (fix to max) */
-- 
2.7.4