aboutsummaryrefslogtreecommitdiffstats
path: root/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.19.8/3586-drm-amd-display-fix-odm-validation.patch
blob: 2830a6c2333addc03946e6c83b5b473959af073a (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
From bf139b37f2d0b90b5601d03d6cc41fbdefdde746 Mon Sep 17 00:00:00 2001
From: Dmytro Laktyushkin <Dmytro.Laktyushkin@amd.com>
Date: Tue, 6 Aug 2019 12:17:57 -0400
Subject: [PATCH 3586/4256] drm/amd/display: fix odm validation

Update bw validation to use prev and next odm pipe pointers
for populating dml inputs.

Signed-off-by: Dmytro Laktyushkin <Dmytro.Laktyushkin@amd.com>
Reviewed-by: Charlene Liu <Charlene.Liu@amd.com>
Acked-by: Bhawanpreet Lakha <Bhawanpreet.Lakha@amd.com>
---
 .../drm/amd/display/dc/dcn20/dcn20_resource.c | 40 +++++++++----------
 1 file changed, 19 insertions(+), 21 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c
index aa1342ccf8b4..477885816854 100644
--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c
+++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_resource.c
@@ -1600,12 +1600,8 @@ static bool dcn20_split_stream_for_odm(
 		struct pipe_ctx *next_odm_pipe)
 {
 	int pipe_idx = next_odm_pipe->pipe_idx;
-	struct scaler_data *sd = &prev_odm_pipe->plane_res.scl_data;
-	struct pipe_ctx *sec_next_pipe = next_odm_pipe->next_odm_pipe;
-	int new_width;
 
 	*next_odm_pipe = *prev_odm_pipe;
-	next_odm_pipe->next_odm_pipe = sec_next_pipe;
 
 	next_odm_pipe->pipe_idx = pipe_idx;
 	next_odm_pipe->plane_res.mi = pool->mis[next_odm_pipe->pipe_idx];
@@ -1627,11 +1623,11 @@ static bool dcn20_split_stream_for_odm(
 	ASSERT(next_odm_pipe->top_pipe == NULL);
 
 	if (prev_odm_pipe->plane_state) {
+		struct scaler_data *sd = &prev_odm_pipe->plane_res.scl_data;
+		int new_width;
+
 		/* HACTIVE halved for odm combine */
 		sd->h_active /= 2;
-		/* Copy scl_data to secondary pipe */
-		next_odm_pipe->plane_res.scl_data = *sd;
-
 		/* Calculate new vp and recout for left pipe */
 		/* Need at least 16 pixels width per side */
 		if (sd->recout.x + 16 >= sd->h_active)
@@ -1645,10 +1641,12 @@ static bool dcn20_split_stream_for_odm(
 
 		/* Calculate new vp and recout for right pipe */
 		sd = &next_odm_pipe->plane_res.scl_data;
-		new_width = sd->recout.width + sd->recout.x - sd->h_active;
+		/* HACTIVE halved for odm combine */
+		sd->h_active /= 2;
 		/* Need at least 16 pixels width per side */
 		if (new_width <= 16)
 			return false;
+		new_width = sd->recout.width + sd->recout.x - sd->h_active;
 		sd->viewport.width -= dc_fixpt_floor(dc_fixpt_mul_int(
 				sd->ratios.horz, sd->recout.width - new_width));
 		sd->viewport_c.width -= dc_fixpt_floor(dc_fixpt_mul_int(
@@ -1818,6 +1816,19 @@ int dcn20_populate_dml_pipes_from_context(
 		pipes[pipe_cnt].dout.dp_lanes = 4;
 		pipes[pipe_cnt].pipe.dest.vtotal_min = res_ctx->pipe_ctx[i].stream->adjust.v_total_min;
 		pipes[pipe_cnt].pipe.dest.vtotal_max = res_ctx->pipe_ctx[i].stream->adjust.v_total_max;
+		pipes[pipe_cnt].pipe.dest.odm_combine = res_ctx->pipe_ctx[i].prev_odm_pipe
+							|| res_ctx->pipe_ctx[i].next_odm_pipe;
+		pipes[pipe_cnt].pipe.src.hsplit_grp = res_ctx->pipe_ctx[i].pipe_idx;
+		if (res_ctx->pipe_ctx[i].top_pipe && res_ctx->pipe_ctx[i].top_pipe->plane_state
+				== res_ctx->pipe_ctx[i].plane_state)
+			pipes[pipe_cnt].pipe.src.hsplit_grp = res_ctx->pipe_ctx[i].top_pipe->pipe_idx;
+		else if (res_ctx->pipe_ctx[i].prev_odm_pipe) {
+			struct pipe_ctx *first_pipe = res_ctx->pipe_ctx[i].prev_odm_pipe;
+
+			while (first_pipe->prev_odm_pipe)
+				first_pipe = first_pipe->prev_odm_pipe;
+			pipes[pipe_cnt].pipe.src.hsplit_grp = first_pipe->pipe_idx;
+		}
 
 		switch (res_ctx->pipe_ctx[i].stream->signal) {
 		case SIGNAL_TYPE_DISPLAY_PORT_MST:
@@ -1870,7 +1881,6 @@ int dcn20_populate_dml_pipes_from_context(
 			break;
 		}
 
-
 		switch (res_ctx->pipe_ctx[i].stream->timing.pixel_encoding) {
 		case PIXEL_ENCODING_RGB:
 		case PIXEL_ENCODING_YCBCR444:
@@ -1892,10 +1902,6 @@ int dcn20_populate_dml_pipes_from_context(
 			pipes[pipe_cnt].dout.output_format = dm_444;
 			pipes[pipe_cnt].dout.output_bpp = output_bpc * 3;
 		}
-		pipes[pipe_cnt].pipe.src.hsplit_grp = res_ctx->pipe_ctx[i].pipe_idx;
-		if (res_ctx->pipe_ctx[i].top_pipe && res_ctx->pipe_ctx[i].top_pipe->plane_state
-				== res_ctx->pipe_ctx[i].plane_state)
-			pipes[pipe_cnt].pipe.src.hsplit_grp = res_ctx->pipe_ctx[i].top_pipe->pipe_idx;
 
 		/* todo: default max for now, until there is logic reflecting this in dc*/
 		pipes[pipe_cnt].dout.output_bpc = 12;
@@ -1944,14 +1950,6 @@ int dcn20_populate_dml_pipes_from_context(
 					&& res_ctx->pipe_ctx[i].bottom_pipe->plane_state == pln)
 					|| (res_ctx->pipe_ctx[i].top_pipe
 					&& res_ctx->pipe_ctx[i].top_pipe->plane_state == pln);
-			pipes[pipe_cnt].pipe.dest.odm_combine = (res_ctx->pipe_ctx[i].bottom_pipe
-					&& res_ctx->pipe_ctx[i].bottom_pipe->plane_state == pln
-					&& res_ctx->pipe_ctx[i].bottom_pipe->stream_res.opp
-						!= res_ctx->pipe_ctx[i].stream_res.opp)
-				|| (res_ctx->pipe_ctx[i].top_pipe
-					&& res_ctx->pipe_ctx[i].top_pipe->plane_state == pln
-					&& res_ctx->pipe_ctx[i].top_pipe->stream_res.opp
-						!= res_ctx->pipe_ctx[i].stream_res.opp);
 			pipes[pipe_cnt].pipe.src.source_scan = pln->rotation == ROTATION_ANGLE_90
 					|| pln->rotation == ROTATION_ANGLE_270 ? dm_vert : dm_horz;
 			pipes[pipe_cnt].pipe.src.viewport_y_y = scl->viewport.y;
-- 
2.17.1