1 /*
2 * Copyright 2020 Advanced Micro Devices, Inc.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
21 *
22 * Authors: AMD
23 *
24 */
25
26 #ifdef CONFIG_DRM_AMD_DC_DCN3_0
27
28 #include "../display_mode_lib.h"
29 #include "../display_mode_vba.h"
30 #include "../dml_inline_defs.h"
31 #include "display_rq_dlg_calc_30.h"
32
is_dual_plane(enum source_format_class source_format)33 static bool is_dual_plane(enum source_format_class source_format)
34 {
35 bool ret_val = 0;
36
37 if ((source_format == dm_420_12) || (source_format == dm_420_8) || (source_format == dm_420_10) || (source_format == dm_rgbe_alpha))
38 ret_val = 1;
39
40 return ret_val;
41 }
42
get_refcyc_per_delivery(struct display_mode_lib * mode_lib,double refclk_freq_in_mhz,double pclk_freq_in_mhz,unsigned int odm_combine,unsigned int recout_width,unsigned int hactive,double vratio,double hscale_pixel_rate,unsigned int delivery_width,unsigned int req_per_swath_ub)43 static double get_refcyc_per_delivery(struct display_mode_lib *mode_lib,
44 double refclk_freq_in_mhz,
45 double pclk_freq_in_mhz,
46 unsigned int odm_combine,
47 unsigned int recout_width,
48 unsigned int hactive,
49 double vratio,
50 double hscale_pixel_rate,
51 unsigned int delivery_width,
52 unsigned int req_per_swath_ub)
53 {
54 double refcyc_per_delivery = 0.0;
55
56 if (vratio <= 1.0) {
57 if (odm_combine)
58 refcyc_per_delivery = (double)refclk_freq_in_mhz * (double)((unsigned int)odm_combine*2)
59 * dml_min((double)recout_width, (double)hactive / ((unsigned int)odm_combine*2))
60 / pclk_freq_in_mhz / (double)req_per_swath_ub;
61 else
62 refcyc_per_delivery = (double)refclk_freq_in_mhz * (double)recout_width
63 / pclk_freq_in_mhz / (double)req_per_swath_ub;
64 } else {
65 refcyc_per_delivery = (double)refclk_freq_in_mhz * (double)delivery_width
66 / (double)hscale_pixel_rate / (double)req_per_swath_ub;
67 }
68
69 dml_print("DML_DLG: %s: refclk_freq_in_mhz = %3.2f\n", __func__, refclk_freq_in_mhz);
70 dml_print("DML_DLG: %s: pclk_freq_in_mhz = %3.2f\n", __func__, pclk_freq_in_mhz);
71 dml_print("DML_DLG: %s: recout_width = %d\n", __func__, recout_width);
72 dml_print("DML_DLG: %s: vratio = %3.2f\n", __func__, vratio);
73 dml_print("DML_DLG: %s: req_per_swath_ub = %d\n", __func__, req_per_swath_ub);
74 dml_print("DML_DLG: %s: refcyc_per_delivery= %3.2f\n", __func__, refcyc_per_delivery);
75
76 return refcyc_per_delivery;
77
78 }
79
get_blk_size_bytes(const enum source_macro_tile_size tile_size)80 static unsigned int get_blk_size_bytes(const enum source_macro_tile_size tile_size)
81 {
82 if (tile_size == dm_256k_tile)
83 return (256 * 1024);
84 else if (tile_size == dm_64k_tile)
85 return (64 * 1024);
86 else
87 return (4 * 1024);
88 }
89
extract_rq_sizing_regs(struct display_mode_lib * mode_lib,display_data_rq_regs_st * rq_regs,const display_data_rq_sizing_params_st rq_sizing)90 static void extract_rq_sizing_regs(struct display_mode_lib *mode_lib,
91 display_data_rq_regs_st *rq_regs,
92 const display_data_rq_sizing_params_st rq_sizing)
93 {
94 dml_print("DML_DLG: %s: rq_sizing param\n", __func__);
95 print__data_rq_sizing_params_st(mode_lib, rq_sizing);
96
97 rq_regs->chunk_size = dml_log2(rq_sizing.chunk_bytes) - 10;
98
99 if (rq_sizing.min_chunk_bytes == 0)
100 rq_regs->min_chunk_size = 0;
101 else
102 rq_regs->min_chunk_size = dml_log2(rq_sizing.min_chunk_bytes) - 8 + 1;
103
104 rq_regs->meta_chunk_size = dml_log2(rq_sizing.meta_chunk_bytes) - 10;
105 if (rq_sizing.min_meta_chunk_bytes == 0)
106 rq_regs->min_meta_chunk_size = 0;
107 else
108 rq_regs->min_meta_chunk_size = dml_log2(rq_sizing.min_meta_chunk_bytes) - 6 + 1;
109
110 rq_regs->dpte_group_size = dml_log2(rq_sizing.dpte_group_bytes) - 6;
111 rq_regs->mpte_group_size = dml_log2(rq_sizing.mpte_group_bytes) - 6;
112 }
113
extract_rq_regs(struct display_mode_lib * mode_lib,display_rq_regs_st * rq_regs,const display_rq_params_st rq_param)114 static void extract_rq_regs(struct display_mode_lib *mode_lib,
115 display_rq_regs_st *rq_regs,
116 const display_rq_params_st rq_param)
117 {
118 unsigned int detile_buf_size_in_bytes = mode_lib->ip.det_buffer_size_kbytes * 1024;
119 unsigned int detile_buf_plane1_addr = 0;
120
121 extract_rq_sizing_regs(mode_lib, &(rq_regs->rq_regs_l), rq_param.sizing.rq_l);
122
123 rq_regs->rq_regs_l.pte_row_height_linear = dml_floor(dml_log2(rq_param.dlg.rq_l.dpte_row_height),
124 1) - 3;
125
126 if (rq_param.yuv420) {
127 extract_rq_sizing_regs(mode_lib, &(rq_regs->rq_regs_c), rq_param.sizing.rq_c);
128 rq_regs->rq_regs_c.pte_row_height_linear = dml_floor(dml_log2(rq_param.dlg.rq_c.dpte_row_height),
129 1) - 3;
130 }
131
132 rq_regs->rq_regs_l.swath_height = dml_log2(rq_param.dlg.rq_l.swath_height);
133 rq_regs->rq_regs_c.swath_height = dml_log2(rq_param.dlg.rq_c.swath_height);
134
135 // FIXME: take the max between luma, chroma chunk size?
136 // okay for now, as we are setting chunk_bytes to 8kb anyways
137 if (rq_param.sizing.rq_l.chunk_bytes >= 32 * 1024 || (rq_param.yuv420 && rq_param.sizing.rq_c.chunk_bytes >= 32 * 1024)) { //32kb
138 rq_regs->drq_expansion_mode = 0;
139 } else {
140 rq_regs->drq_expansion_mode = 2;
141 }
142 rq_regs->prq_expansion_mode = 1;
143 rq_regs->mrq_expansion_mode = 1;
144 rq_regs->crq_expansion_mode = 1;
145
146 if (rq_param.yuv420) {
147 if ((double)rq_param.misc.rq_l.stored_swath_bytes
148 / (double)rq_param.misc.rq_c.stored_swath_bytes <= 1.5) {
149 detile_buf_plane1_addr = (detile_buf_size_in_bytes / 2.0 / 64.0); // half to chroma
150 } else {
151 detile_buf_plane1_addr = dml_round_to_multiple((unsigned int)((2.0 * detile_buf_size_in_bytes) / 3.0),
152 256,
153 0) / 64.0; // 2/3 to chroma
154 }
155 }
156 rq_regs->plane1_base_address = detile_buf_plane1_addr;
157 }
158
handle_det_buf_split(struct display_mode_lib * mode_lib,display_rq_params_st * rq_param,const display_pipe_source_params_st pipe_src_param)159 static void handle_det_buf_split(struct display_mode_lib *mode_lib,
160 display_rq_params_st *rq_param,
161 const display_pipe_source_params_st pipe_src_param)
162 {
163 unsigned int total_swath_bytes = 0;
164 unsigned int swath_bytes_l = 0;
165 unsigned int swath_bytes_c = 0;
166 unsigned int full_swath_bytes_packed_l = 0;
167 unsigned int full_swath_bytes_packed_c = 0;
168 bool req128_l = 0;
169 bool req128_c = 0;
170 bool surf_linear = (pipe_src_param.sw_mode == dm_sw_linear);
171 bool surf_vert = (pipe_src_param.source_scan == dm_vert);
172 unsigned int log2_swath_height_l = 0;
173 unsigned int log2_swath_height_c = 0;
174 unsigned int detile_buf_size_in_bytes = mode_lib->ip.det_buffer_size_kbytes * 1024;
175
176 full_swath_bytes_packed_l = rq_param->misc.rq_l.full_swath_bytes;
177 full_swath_bytes_packed_c = rq_param->misc.rq_c.full_swath_bytes;
178
179 if (rq_param->yuv420_10bpc) {
180 full_swath_bytes_packed_l = dml_round_to_multiple(rq_param->misc.rq_l.full_swath_bytes * 2.0 / 3.0,
181 256,
182 1) + 256;
183 full_swath_bytes_packed_c = dml_round_to_multiple(rq_param->misc.rq_c.full_swath_bytes * 2.0 / 3.0,
184 256,
185 1) + 256;
186 }
187
188 if (rq_param->yuv420)
189 total_swath_bytes = 2 * full_swath_bytes_packed_l + 2 * full_swath_bytes_packed_c;
190 else
191 total_swath_bytes = 2 * full_swath_bytes_packed_l;
192
193 if (total_swath_bytes <= detile_buf_size_in_bytes) { //full 256b request
194 req128_l = 0;
195 req128_c = 0;
196 swath_bytes_l = full_swath_bytes_packed_l;
197 swath_bytes_c = full_swath_bytes_packed_c;
198 } else if (!rq_param->yuv420) {
199 req128_l = 1;
200 req128_c = 0;
201 swath_bytes_c = full_swath_bytes_packed_c;
202 swath_bytes_l = full_swath_bytes_packed_l / 2;
203 } else if ((double)full_swath_bytes_packed_l / (double)full_swath_bytes_packed_c < 1.5) {
204 req128_l = 0;
205 req128_c = 1;
206 swath_bytes_l = full_swath_bytes_packed_l;
207 swath_bytes_c = full_swath_bytes_packed_c / 2;
208
209 total_swath_bytes = 2 * swath_bytes_l + 2 * swath_bytes_c;
210
211 if (total_swath_bytes > detile_buf_size_in_bytes) {
212 req128_l = 1;
213 swath_bytes_l = full_swath_bytes_packed_l / 2;
214 }
215 } else {
216 req128_l = 1;
217 req128_c = 0;
218 swath_bytes_l = full_swath_bytes_packed_l/2;
219 swath_bytes_c = full_swath_bytes_packed_c;
220
221 total_swath_bytes = 2 * swath_bytes_l + 2 * swath_bytes_c;
222
223 if (total_swath_bytes > detile_buf_size_in_bytes) {
224 req128_c = 1;
225 swath_bytes_c = full_swath_bytes_packed_c/2;
226 }
227 }
228
229 if (rq_param->yuv420)
230 total_swath_bytes = 2 * swath_bytes_l + 2 * swath_bytes_c;
231 else
232 total_swath_bytes = 2 * swath_bytes_l;
233
234 rq_param->misc.rq_l.stored_swath_bytes = swath_bytes_l;
235 rq_param->misc.rq_c.stored_swath_bytes = swath_bytes_c;
236
237 if (surf_linear) {
238 log2_swath_height_l = 0;
239 log2_swath_height_c = 0;
240 } else if (!surf_vert) {
241 log2_swath_height_l = dml_log2(rq_param->misc.rq_l.blk256_height) - req128_l;
242 log2_swath_height_c = dml_log2(rq_param->misc.rq_c.blk256_height) - req128_c;
243 } else {
244 log2_swath_height_l = dml_log2(rq_param->misc.rq_l.blk256_width) - req128_l;
245 log2_swath_height_c = dml_log2(rq_param->misc.rq_c.blk256_width) - req128_c;
246 }
247 rq_param->dlg.rq_l.swath_height = 1 << log2_swath_height_l;
248 rq_param->dlg.rq_c.swath_height = 1 << log2_swath_height_c;
249
250 dml_print("DML_DLG: %s: req128_l = %0d\n", __func__, req128_l);
251 dml_print("DML_DLG: %s: req128_c = %0d\n", __func__, req128_c);
252 dml_print("DML_DLG: %s: full_swath_bytes_packed_l = %0d\n",
253 __func__,
254 full_swath_bytes_packed_l);
255 dml_print("DML_DLG: %s: full_swath_bytes_packed_c = %0d\n",
256 __func__,
257 full_swath_bytes_packed_c);
258 }
259
CalculateBytePerPixelAnd256BBlockSizes(enum source_format_class SourcePixelFormat,enum dm_swizzle_mode SurfaceTiling,unsigned int * BytePerPixelY,unsigned int * BytePerPixelC,double * BytePerPixelDETY,double * BytePerPixelDETC,unsigned int * BlockHeight256BytesY,unsigned int * BlockHeight256BytesC,unsigned int * BlockWidth256BytesY,unsigned int * BlockWidth256BytesC)260 static bool CalculateBytePerPixelAnd256BBlockSizes(
261 enum source_format_class SourcePixelFormat,
262 enum dm_swizzle_mode SurfaceTiling,
263 unsigned int *BytePerPixelY,
264 unsigned int *BytePerPixelC,
265 double *BytePerPixelDETY,
266 double *BytePerPixelDETC,
267 unsigned int *BlockHeight256BytesY,
268 unsigned int *BlockHeight256BytesC,
269 unsigned int *BlockWidth256BytesY,
270 unsigned int *BlockWidth256BytesC)
271 {
272 if (SourcePixelFormat == dm_444_64) {
273 *BytePerPixelDETY = 8;
274 *BytePerPixelDETC = 0;
275 *BytePerPixelY = 8;
276 *BytePerPixelC = 0;
277 } else if (SourcePixelFormat == dm_444_32 || SourcePixelFormat == dm_rgbe) {
278 *BytePerPixelDETY = 4;
279 *BytePerPixelDETC = 0;
280 *BytePerPixelY = 4;
281 *BytePerPixelC = 0;
282 } else if (SourcePixelFormat == dm_444_16) {
283 *BytePerPixelDETY = 2;
284 *BytePerPixelDETC = 0;
285 *BytePerPixelY = 2;
286 *BytePerPixelC = 0;
287 } else if (SourcePixelFormat == dm_444_8) {
288 *BytePerPixelDETY = 1;
289 *BytePerPixelDETC = 0;
290 *BytePerPixelY = 1;
291 *BytePerPixelC = 0;
292 } else if (SourcePixelFormat == dm_rgbe_alpha) {
293 *BytePerPixelDETY = 4;
294 *BytePerPixelDETC = 1;
295 *BytePerPixelY = 4;
296 *BytePerPixelC = 1;
297 } else if (SourcePixelFormat == dm_420_8) {
298 *BytePerPixelDETY = 1;
299 *BytePerPixelDETC = 2;
300 *BytePerPixelY = 1;
301 *BytePerPixelC = 2;
302 } else if (SourcePixelFormat == dm_420_12) {
303 *BytePerPixelDETY = 2;
304 *BytePerPixelDETC = 4;
305 *BytePerPixelY = 2;
306 *BytePerPixelC = 4;
307 } else {
308 *BytePerPixelDETY = 4.0 / 3;
309 *BytePerPixelDETC = 8.0 / 3;
310 *BytePerPixelY = 2;
311 *BytePerPixelC = 4;
312 }
313
314 if ((SourcePixelFormat == dm_444_64 || SourcePixelFormat == dm_444_32
315 || SourcePixelFormat == dm_444_16 || SourcePixelFormat == dm_444_8
316 || SourcePixelFormat == dm_mono_16 || SourcePixelFormat == dm_mono_8
317 || SourcePixelFormat == dm_rgbe)) {
318 if (SurfaceTiling == dm_sw_linear) {
319 *BlockHeight256BytesY = 1;
320 } else if (SourcePixelFormat == dm_444_64) {
321 *BlockHeight256BytesY = 4;
322 } else if (SourcePixelFormat == dm_444_8) {
323 *BlockHeight256BytesY = 16;
324 } else {
325 *BlockHeight256BytesY = 8;
326 }
327 *BlockWidth256BytesY = 256U / *BytePerPixelY / *BlockHeight256BytesY;
328 *BlockHeight256BytesC = 0;
329 *BlockWidth256BytesC = 0;
330 } else {
331 if (SurfaceTiling == dm_sw_linear) {
332 *BlockHeight256BytesY = 1;
333 *BlockHeight256BytesC = 1;
334 } else if (SourcePixelFormat == dm_rgbe_alpha) {
335 *BlockHeight256BytesY = 8;
336 *BlockHeight256BytesC = 16;
337 } else if (SourcePixelFormat == dm_420_8) {
338 *BlockHeight256BytesY = 16;
339 *BlockHeight256BytesC = 8;
340 } else {
341 *BlockHeight256BytesY = 8;
342 *BlockHeight256BytesC = 8;
343 }
344 *BlockWidth256BytesY = 256U / *BytePerPixelY / *BlockHeight256BytesY;
345 *BlockWidth256BytesC = 256U / *BytePerPixelC / *BlockHeight256BytesC;
346 }
347 return true;
348 }
349
get_meta_and_pte_attr(struct display_mode_lib * mode_lib,display_data_rq_dlg_params_st * rq_dlg_param,display_data_rq_misc_params_st * rq_misc_param,display_data_rq_sizing_params_st * rq_sizing_param,unsigned int vp_width,unsigned int vp_height,unsigned int data_pitch,unsigned int meta_pitch,unsigned int source_format,unsigned int tiling,unsigned int macro_tile_size,unsigned int source_scan,unsigned int hostvm_enable,unsigned int is_chroma,unsigned int surface_height)350 static void get_meta_and_pte_attr(struct display_mode_lib *mode_lib,
351 display_data_rq_dlg_params_st *rq_dlg_param,
352 display_data_rq_misc_params_st *rq_misc_param,
353 display_data_rq_sizing_params_st *rq_sizing_param,
354 unsigned int vp_width,
355 unsigned int vp_height,
356 unsigned int data_pitch,
357 unsigned int meta_pitch,
358 unsigned int source_format,
359 unsigned int tiling,
360 unsigned int macro_tile_size,
361 unsigned int source_scan,
362 unsigned int hostvm_enable,
363 unsigned int is_chroma,
364 unsigned int surface_height)
365 {
366 bool surf_linear = (tiling == dm_sw_linear);
367 bool surf_vert = (source_scan == dm_vert);
368
369 unsigned int bytes_per_element = 0;
370 unsigned int bytes_per_element_y = 0;
371 unsigned int bytes_per_element_c = 0;
372
373 unsigned int blk256_width = 0;
374 unsigned int blk256_height = 0;
375
376 unsigned int blk256_width_y = 0;
377 unsigned int blk256_height_y = 0;
378 unsigned int blk256_width_c = 0;
379 unsigned int blk256_height_c = 0;
380 unsigned int log2_bytes_per_element = 0;
381 unsigned int log2_blk256_width = 0;
382 unsigned int log2_blk256_height = 0;
383 unsigned int blk_bytes = 0;
384 unsigned int log2_blk_bytes = 0;
385 unsigned int log2_blk_height = 0;
386 unsigned int log2_blk_width = 0;
387 unsigned int log2_meta_req_bytes = 0;
388 unsigned int log2_meta_req_height = 0;
389 unsigned int log2_meta_req_width = 0;
390 unsigned int meta_req_width = 0;
391 unsigned int meta_req_height = 0;
392 unsigned int log2_meta_row_height = 0;
393 unsigned int meta_row_width_ub = 0;
394 unsigned int log2_meta_chunk_bytes = 0;
395 unsigned int log2_meta_chunk_height = 0;
396
397 //full sized meta chunk width in unit of data elements
398 unsigned int log2_meta_chunk_width = 0;
399 unsigned int log2_min_meta_chunk_bytes = 0;
400 unsigned int min_meta_chunk_width = 0;
401 unsigned int meta_chunk_width = 0;
402 unsigned int meta_chunk_per_row_int = 0;
403 unsigned int meta_row_remainder = 0;
404 unsigned int meta_chunk_threshold = 0;
405 unsigned int meta_blk_bytes = 0;
406 unsigned int meta_blk_height = 0;
407 unsigned int meta_blk_width = 0;
408 unsigned int meta_surface_bytes = 0;
409 unsigned int vmpg_bytes = 0;
410 unsigned int meta_pte_req_per_frame_ub = 0;
411 unsigned int meta_pte_bytes_per_frame_ub = 0;
412 const unsigned int log2_vmpg_bytes = dml_log2(mode_lib->soc.gpuvm_min_page_size_bytes);
413 const bool dual_plane_en = is_dual_plane((enum source_format_class)(source_format));
414 const unsigned int dpte_buf_in_pte_reqs = dual_plane_en ?
415 (is_chroma ? mode_lib->ip.dpte_buffer_size_in_pte_reqs_chroma : mode_lib->ip.dpte_buffer_size_in_pte_reqs_luma)
416 : (mode_lib->ip.dpte_buffer_size_in_pte_reqs_luma + mode_lib->ip.dpte_buffer_size_in_pte_reqs_chroma);
417
418 unsigned int log2_vmpg_height = 0;
419 unsigned int log2_vmpg_width = 0;
420 unsigned int log2_dpte_req_height_ptes = 0;
421 unsigned int log2_dpte_req_height = 0;
422 unsigned int log2_dpte_req_width = 0;
423 unsigned int log2_dpte_row_height_linear = 0;
424 unsigned int log2_dpte_row_height = 0;
425 unsigned int log2_dpte_group_width = 0;
426 unsigned int dpte_row_width_ub = 0;
427 unsigned int dpte_req_height = 0;
428 unsigned int dpte_req_width = 0;
429 unsigned int dpte_group_width = 0;
430 unsigned int log2_dpte_group_bytes = 0;
431 unsigned int log2_dpte_group_length = 0;
432 double byte_per_pixel_det_y = 0;
433 double byte_per_pixel_det_c = 0;
434
435 CalculateBytePerPixelAnd256BBlockSizes((enum source_format_class)(source_format),
436 (enum dm_swizzle_mode)(tiling),
437 &bytes_per_element_y,
438 &bytes_per_element_c,
439 &byte_per_pixel_det_y,
440 &byte_per_pixel_det_c,
441 &blk256_height_y,
442 &blk256_height_c,
443 &blk256_width_y,
444 &blk256_width_c);
445
446 if (!is_chroma) {
447 blk256_width = blk256_width_y;
448 blk256_height = blk256_height_y;
449 bytes_per_element = bytes_per_element_y;
450 } else {
451 blk256_width = blk256_width_c;
452 blk256_height = blk256_height_c;
453 bytes_per_element = bytes_per_element_c;
454 }
455
456 log2_bytes_per_element = dml_log2(bytes_per_element);
457
458 dml_print("DML_DLG: %s: surf_linear = %d\n", __func__, surf_linear);
459 dml_print("DML_DLG: %s: surf_vert = %d\n", __func__, surf_vert);
460 dml_print("DML_DLG: %s: blk256_width = %d\n", __func__, blk256_width);
461 dml_print("DML_DLG: %s: blk256_height = %d\n", __func__, blk256_height);
462
463 log2_blk256_width = dml_log2((double)blk256_width);
464 log2_blk256_height = dml_log2((double)blk256_height);
465 blk_bytes = surf_linear ?
466 256 : get_blk_size_bytes((enum source_macro_tile_size) macro_tile_size);
467 log2_blk_bytes = dml_log2((double)blk_bytes);
468 log2_blk_height = 0;
469 log2_blk_width = 0;
470
471 // remember log rule
472 // "+" in log is multiply
473 // "-" in log is divide
474 // "/2" is like square root
475 // blk is vertical biased
476 if (tiling != dm_sw_linear)
477 log2_blk_height = log2_blk256_height
478 + dml_ceil((double)(log2_blk_bytes - 8) / 2.0, 1);
479 else
480 log2_blk_height = 0; // blk height of 1
481
482 log2_blk_width = log2_blk_bytes - log2_bytes_per_element - log2_blk_height;
483
484 if (!surf_vert) {
485 int unsigned temp = 0;
486
487 temp = dml_round_to_multiple(vp_width - 1, blk256_width, 1) + blk256_width;
488 if (data_pitch < blk256_width) {
489 dml_print("WARNING: DML_DLG: %s: swath_size calculation ignoring data_pitch=%u < blk256_width=%u\n", __func__, data_pitch, blk256_width);
490 } else {
491 if (temp > data_pitch) {
492 if (data_pitch >= vp_width)
493 temp = data_pitch;
494 else
495 dml_print("WARNING: DML_DLG: %s: swath_size calculation ignoring data_pitch=%u < vp_width=%u\n", __func__, data_pitch, vp_width);
496 }
497 }
498 rq_dlg_param->swath_width_ub = temp;
499 rq_dlg_param->req_per_swath_ub = temp >> log2_blk256_width;
500 } else {
501 int unsigned temp = 0;
502
503 temp = dml_round_to_multiple(vp_height - 1, blk256_height, 1) + blk256_height;
504 if (surface_height < blk256_height) {
505 dml_print("WARNING: DML_DLG: %s swath_size calculation ignored surface_height=%u < blk256_height=%u\n", __func__, surface_height, blk256_height);
506 } else {
507 if (temp > surface_height) {
508 if (surface_height >= vp_height)
509 temp = surface_height;
510 else
511 dml_print("WARNING: DML_DLG: %s swath_size calculation ignored surface_height=%u < vp_height=%u\n", __func__, surface_height, vp_height);
512 }
513 }
514 rq_dlg_param->swath_width_ub = temp;
515 rq_dlg_param->req_per_swath_ub = temp >> log2_blk256_height;
516 }
517
518 if (!surf_vert)
519 rq_misc_param->full_swath_bytes = rq_dlg_param->swath_width_ub * blk256_height
520 * bytes_per_element;
521 else
522 rq_misc_param->full_swath_bytes = rq_dlg_param->swath_width_ub * blk256_width
523 * bytes_per_element;
524
525 rq_misc_param->blk256_height = blk256_height;
526 rq_misc_param->blk256_width = blk256_width;
527
528 // -------
529 // meta
530 // -------
531 log2_meta_req_bytes = 6; // meta request is 64b and is 8x8byte meta element
532
533 // each 64b meta request for dcn is 8x8 meta elements and
534 // a meta element covers one 256b block of the the data surface.
535 log2_meta_req_height = log2_blk256_height + 3; // meta req is 8x8 byte, each byte represent 1 blk256
536 log2_meta_req_width = log2_meta_req_bytes + 8 - log2_bytes_per_element
537 - log2_meta_req_height;
538 meta_req_width = 1 << log2_meta_req_width;
539 meta_req_height = 1 << log2_meta_req_height;
540 log2_meta_row_height = 0;
541 meta_row_width_ub = 0;
542
543 // the dimensions of a meta row are meta_row_width x meta_row_height in elements.
544 // calculate upper bound of the meta_row_width
545 if (!surf_vert) {
546 log2_meta_row_height = log2_meta_req_height;
547 meta_row_width_ub = dml_round_to_multiple(vp_width - 1, meta_req_width, 1)
548 + meta_req_width;
549 rq_dlg_param->meta_req_per_row_ub = meta_row_width_ub / meta_req_width;
550 } else {
551 log2_meta_row_height = log2_meta_req_width;
552 meta_row_width_ub = dml_round_to_multiple(vp_height - 1, meta_req_height, 1)
553 + meta_req_height;
554 rq_dlg_param->meta_req_per_row_ub = meta_row_width_ub / meta_req_height;
555 }
556 rq_dlg_param->meta_bytes_per_row_ub = rq_dlg_param->meta_req_per_row_ub * 64;
557
558 rq_dlg_param->meta_row_height = 1 << log2_meta_row_height;
559
560 log2_meta_chunk_bytes = dml_log2(rq_sizing_param->meta_chunk_bytes);
561 log2_meta_chunk_height = log2_meta_row_height;
562
563 //full sized meta chunk width in unit of data elements
564 log2_meta_chunk_width = log2_meta_chunk_bytes + 8 - log2_bytes_per_element
565 - log2_meta_chunk_height;
566 log2_min_meta_chunk_bytes = dml_log2(rq_sizing_param->min_meta_chunk_bytes);
567 min_meta_chunk_width = 1
568 << (log2_min_meta_chunk_bytes + 8 - log2_bytes_per_element
569 - log2_meta_chunk_height);
570 meta_chunk_width = 1 << log2_meta_chunk_width;
571 meta_chunk_per_row_int = (unsigned int)(meta_row_width_ub / meta_chunk_width);
572 meta_row_remainder = meta_row_width_ub % meta_chunk_width;
573 meta_chunk_threshold = 0;
574 meta_blk_bytes = 4096;
575 meta_blk_height = blk256_height * 64;
576 meta_blk_width = meta_blk_bytes * 256 / bytes_per_element / meta_blk_height;
577 meta_surface_bytes = meta_pitch
578 * (dml_round_to_multiple(vp_height - 1, meta_blk_height, 1) + meta_blk_height)
579 * bytes_per_element / 256;
580 vmpg_bytes = mode_lib->soc.gpuvm_min_page_size_bytes;
581 meta_pte_req_per_frame_ub = (dml_round_to_multiple(meta_surface_bytes - vmpg_bytes,
582 8 * vmpg_bytes,
583 1) + 8 * vmpg_bytes) / (8 * vmpg_bytes);
584 meta_pte_bytes_per_frame_ub = meta_pte_req_per_frame_ub * 64; //64B mpte request
585 rq_dlg_param->meta_pte_bytes_per_frame_ub = meta_pte_bytes_per_frame_ub;
586
587 dml_print("DML_DLG: %s: meta_blk_height = %d\n", __func__, meta_blk_height);
588 dml_print("DML_DLG: %s: meta_blk_width = %d\n", __func__, meta_blk_width);
589 dml_print("DML_DLG: %s: meta_surface_bytes = %d\n", __func__, meta_surface_bytes);
590 dml_print("DML_DLG: %s: meta_pte_req_per_frame_ub = %d\n",
591 __func__,
592 meta_pte_req_per_frame_ub);
593 dml_print("DML_DLG: %s: meta_pte_bytes_per_frame_ub = %d\n",
594 __func__,
595 meta_pte_bytes_per_frame_ub);
596
597 if (!surf_vert)
598 meta_chunk_threshold = 2 * min_meta_chunk_width - meta_req_width;
599 else
600 meta_chunk_threshold = 2 * min_meta_chunk_width - meta_req_height;
601
602 if (meta_row_remainder <= meta_chunk_threshold)
603 rq_dlg_param->meta_chunks_per_row_ub = meta_chunk_per_row_int + 1;
604 else
605 rq_dlg_param->meta_chunks_per_row_ub = meta_chunk_per_row_int + 2;
606
607 // ------
608 // dpte
609 // ------
610 if (surf_linear) {
611 log2_vmpg_height = 0; // one line high
612 } else {
613 log2_vmpg_height = (log2_vmpg_bytes - 8) / 2 + log2_blk256_height;
614 }
615 log2_vmpg_width = log2_vmpg_bytes - log2_bytes_per_element - log2_vmpg_height;
616
617 // only 3 possible shapes for dpte request in dimensions of ptes: 8x1, 4x2, 2x4.
618 if (surf_linear) { //one 64B PTE request returns 8 PTEs
619 log2_dpte_req_height_ptes = 0;
620 log2_dpte_req_width = log2_vmpg_width + 3;
621 log2_dpte_req_height = 0;
622 } else if (log2_blk_bytes == 12) { //4KB tile means 4kB page size
623 //one 64B req gives 8x1 PTEs for 4KB tile
624 log2_dpte_req_height_ptes = 0;
625 log2_dpte_req_width = log2_blk_width + 3;
626 log2_dpte_req_height = log2_blk_height + 0;
627 } else if ((log2_blk_bytes >= 16) && (log2_vmpg_bytes == 12)) { // tile block >= 64KB
628 //two 64B reqs of 2x4 PTEs give 16 PTEs to cover 64KB
629 log2_dpte_req_height_ptes = 4;
630 log2_dpte_req_width = log2_blk256_width + 4; // log2_64KB_width
631 log2_dpte_req_height = log2_blk256_height + 4; // log2_64KB_height
632 } else { //64KB page size and must 64KB tile block
633 //one 64B req gives 8x1 PTEs for 64KB tile
634 log2_dpte_req_height_ptes = 0;
635 log2_dpte_req_width = log2_blk_width + 3;
636 log2_dpte_req_height = log2_blk_height + 0;
637 }
638
639 // The dpte request dimensions in data elements is dpte_req_width x dpte_req_height
640 // log2_vmpg_width is how much 1 pte represent, now calculating how much a 64b pte req represent
641 // That depends on the pte shape (i.e. 8x1, 4x2, 2x4)
642 //log2_dpte_req_height = log2_vmpg_height + log2_dpte_req_height_ptes;
643 //log2_dpte_req_width = log2_vmpg_width + log2_dpte_req_width_ptes;
644 dpte_req_height = 1 << log2_dpte_req_height;
645 dpte_req_width = 1 << log2_dpte_req_width;
646
647 // calculate pitch dpte row buffer can hold
648 // round the result down to a power of two.
649 if (surf_linear) {
650 unsigned int dpte_row_height = 0;
651
652 log2_dpte_row_height_linear = dml_floor(dml_log2(dpte_buf_in_pte_reqs * dpte_req_width / data_pitch), 1);
653
654 dml_print("DML_DLG: %s: is_chroma = %d\n", __func__, is_chroma);
655 dml_print("DML_DLG: %s: dpte_buf_in_pte_reqs = %d\n", __func__, dpte_buf_in_pte_reqs);
656 dml_print("DML_DLG: %s: log2_dpte_row_height_linear = %d\n", __func__, log2_dpte_row_height_linear);
657
658 ASSERT(log2_dpte_row_height_linear >= 3);
659
660 if (log2_dpte_row_height_linear > 7)
661 log2_dpte_row_height_linear = 7;
662
663 log2_dpte_row_height = log2_dpte_row_height_linear;
664 // For linear, the dpte row is pitch dependent and the pte requests wrap at the pitch boundary.
665 // the dpte_row_width_ub is the upper bound of data_pitch*dpte_row_height in elements with this unique buffering.
666 dpte_row_height = 1 << log2_dpte_row_height;
667 dpte_row_width_ub = dml_round_to_multiple(data_pitch * dpte_row_height - 1,
668 dpte_req_width,
669 1) + dpte_req_width;
670 rq_dlg_param->dpte_req_per_row_ub = dpte_row_width_ub / dpte_req_width;
671 } else {
672 // the upper bound of the dpte_row_width without dependency on viewport position follows.
673 // for tiled mode, row height is the same as req height and row store up to vp size upper bound
674 if (!surf_vert) {
675 log2_dpte_row_height = log2_dpte_req_height;
676 dpte_row_width_ub = dml_round_to_multiple(vp_width - 1, dpte_req_width, 1)
677 + dpte_req_width;
678 rq_dlg_param->dpte_req_per_row_ub = dpte_row_width_ub / dpte_req_width;
679 } else {
680 log2_dpte_row_height =
681 (log2_blk_width < log2_dpte_req_width) ?
682 log2_blk_width : log2_dpte_req_width;
683 dpte_row_width_ub = dml_round_to_multiple(vp_height - 1, dpte_req_height, 1)
684 + dpte_req_height;
685 rq_dlg_param->dpte_req_per_row_ub = dpte_row_width_ub / dpte_req_height;
686 }
687 }
688 if (log2_blk_bytes >= 16 && log2_vmpg_bytes == 12) // tile block >= 64KB
689 rq_dlg_param->dpte_bytes_per_row_ub = rq_dlg_param->dpte_req_per_row_ub * 128; //2*64B dpte request
690 else
691 rq_dlg_param->dpte_bytes_per_row_ub = rq_dlg_param->dpte_req_per_row_ub * 64; //64B dpte request
692
693 rq_dlg_param->dpte_row_height = 1 << log2_dpte_row_height;
694
695 // the dpte_group_bytes is reduced for the specific case of vertical
696 // access of a tile surface that has dpte request of 8x1 ptes.
697 if (hostvm_enable)
698 rq_sizing_param->dpte_group_bytes = 512;
699 else {
700 if (!surf_linear & (log2_dpte_req_height_ptes == 0) & surf_vert) //reduced, in this case, will have page fault within a group
701 rq_sizing_param->dpte_group_bytes = 512;
702 else
703 rq_sizing_param->dpte_group_bytes = 2048;
704 }
705
706 //since pte request size is 64byte, the number of data pte requests per full sized group is as follows.
707 log2_dpte_group_bytes = dml_log2(rq_sizing_param->dpte_group_bytes);
708 log2_dpte_group_length = log2_dpte_group_bytes - 6; //length in 64b requests
709
710 // full sized data pte group width in elements
711 if (!surf_vert)
712 log2_dpte_group_width = log2_dpte_group_length + log2_dpte_req_width;
713 else
714 log2_dpte_group_width = log2_dpte_group_length + log2_dpte_req_height;
715
716 //But if the tile block >=64KB and the page size is 4KB, then each dPTE request is 2*64B
717 if ((log2_blk_bytes >= 16) && (log2_vmpg_bytes == 12)) // tile block >= 64KB
718 log2_dpte_group_width = log2_dpte_group_width - 1;
719
720 dpte_group_width = 1 << log2_dpte_group_width;
721
722 // since dpte groups are only aligned to dpte_req_width and not dpte_group_width,
723 // the upper bound for the dpte groups per row is as follows.
724 rq_dlg_param->dpte_groups_per_row_ub = dml_ceil((double)dpte_row_width_ub / dpte_group_width,
725 1);
726 }
727
get_surf_rq_param(struct display_mode_lib * mode_lib,display_data_rq_sizing_params_st * rq_sizing_param,display_data_rq_dlg_params_st * rq_dlg_param,display_data_rq_misc_params_st * rq_misc_param,const display_pipe_params_st pipe_param,bool is_chroma,bool is_alpha)728 static void get_surf_rq_param(struct display_mode_lib *mode_lib,
729 display_data_rq_sizing_params_st *rq_sizing_param,
730 display_data_rq_dlg_params_st *rq_dlg_param,
731 display_data_rq_misc_params_st *rq_misc_param,
732 const display_pipe_params_st pipe_param,
733 bool is_chroma,
734 bool is_alpha)
735 {
736 bool mode_422 = 0;
737 unsigned int vp_width = 0;
738 unsigned int vp_height = 0;
739 unsigned int data_pitch = 0;
740 unsigned int meta_pitch = 0;
741 unsigned int surface_height = 0;
742 unsigned int ppe = mode_422 ? 2 : 1;
743
744 // FIXME check if ppe apply for both luma and chroma in 422 case
745 if (is_chroma | is_alpha) {
746 vp_width = pipe_param.src.viewport_width_c / ppe;
747 vp_height = pipe_param.src.viewport_height_c;
748 data_pitch = pipe_param.src.data_pitch_c;
749 meta_pitch = pipe_param.src.meta_pitch_c;
750 surface_height = pipe_param.src.surface_height_y / 2.0;
751 } else {
752 vp_width = pipe_param.src.viewport_width / ppe;
753 vp_height = pipe_param.src.viewport_height;
754 data_pitch = pipe_param.src.data_pitch;
755 meta_pitch = pipe_param.src.meta_pitch;
756 surface_height = pipe_param.src.surface_height_y;
757 }
758
759 if (pipe_param.dest.odm_combine) {
760 unsigned int access_dir = 0;
761 unsigned int full_src_vp_width = 0;
762 unsigned int hactive_odm = 0;
763 unsigned int src_hactive_odm = 0;
764 access_dir = (pipe_param.src.source_scan == dm_vert); // vp access direction: horizontal or vertical accessed
765 hactive_odm = pipe_param.dest.hactive / ((unsigned int)pipe_param.dest.odm_combine*2);
766 if (is_chroma) {
767 full_src_vp_width = pipe_param.scale_ratio_depth.hscl_ratio_c * pipe_param.dest.full_recout_width;
768 src_hactive_odm = pipe_param.scale_ratio_depth.hscl_ratio_c * hactive_odm;
769 } else {
770 full_src_vp_width = pipe_param.scale_ratio_depth.hscl_ratio * pipe_param.dest.full_recout_width;
771 src_hactive_odm = pipe_param.scale_ratio_depth.hscl_ratio * hactive_odm;
772 }
773
774 if (access_dir == 0) {
775 vp_width = dml_min(full_src_vp_width, src_hactive_odm);
776 dml_print("DML_DLG: %s: vp_width = %d\n", __func__, vp_width);
777 } else {
778 vp_height = dml_min(full_src_vp_width, src_hactive_odm);
779 dml_print("DML_DLG: %s: vp_height = %d\n", __func__, vp_height);
780 }
781 dml_print("DML_DLG: %s: full_src_vp_width = %d\n", __func__, full_src_vp_width);
782 dml_print("DML_DLG: %s: hactive_odm = %d\n", __func__, hactive_odm);
783 dml_print("DML_DLG: %s: src_hactive_odm = %d\n", __func__, src_hactive_odm);
784 }
785
786 rq_sizing_param->chunk_bytes = 8192;
787
788 if (is_alpha) {
789 rq_sizing_param->chunk_bytes = 4096;
790 }
791
792 if (rq_sizing_param->chunk_bytes == 64 * 1024)
793 rq_sizing_param->min_chunk_bytes = 0;
794 else
795 rq_sizing_param->min_chunk_bytes = 1024;
796
797 rq_sizing_param->meta_chunk_bytes = 2048;
798 rq_sizing_param->min_meta_chunk_bytes = 256;
799
800 if (pipe_param.src.hostvm)
801 rq_sizing_param->mpte_group_bytes = 512;
802 else
803 rq_sizing_param->mpte_group_bytes = 2048;
804
805 get_meta_and_pte_attr(mode_lib,
806 rq_dlg_param,
807 rq_misc_param,
808 rq_sizing_param,
809 vp_width,
810 vp_height,
811 data_pitch,
812 meta_pitch,
813 pipe_param.src.source_format,
814 pipe_param.src.sw_mode,
815 pipe_param.src.macro_tile_size,
816 pipe_param.src.source_scan,
817 pipe_param.src.hostvm,
818 is_chroma,
819 surface_height);
820 }
821
dml_rq_dlg_get_rq_params(struct display_mode_lib * mode_lib,display_rq_params_st * rq_param,const display_pipe_params_st pipe_param)822 static void dml_rq_dlg_get_rq_params(struct display_mode_lib *mode_lib,
823 display_rq_params_st *rq_param,
824 const display_pipe_params_st pipe_param)
825 {
826 // get param for luma surface
827 rq_param->yuv420 = pipe_param.src.source_format == dm_420_8
828 || pipe_param.src.source_format == dm_420_10
829 || pipe_param.src.source_format == dm_rgbe_alpha
830 || pipe_param.src.source_format == dm_420_12;
831
832 rq_param->yuv420_10bpc = pipe_param.src.source_format == dm_420_10;
833
834 rq_param->rgbe_alpha = (pipe_param.src.source_format == dm_rgbe_alpha)?1:0;
835
836 get_surf_rq_param(mode_lib,
837 &(rq_param->sizing.rq_l),
838 &(rq_param->dlg.rq_l),
839 &(rq_param->misc.rq_l),
840 pipe_param,
841 0,
842 0);
843
844 if (is_dual_plane((enum source_format_class)(pipe_param.src.source_format))) {
845 // get param for chroma surface
846 get_surf_rq_param(mode_lib,
847 &(rq_param->sizing.rq_c),
848 &(rq_param->dlg.rq_c),
849 &(rq_param->misc.rq_c),
850 pipe_param,
851 1,
852 rq_param->rgbe_alpha);
853 }
854
855 // calculate how to split the det buffer space between luma and chroma
856 handle_det_buf_split(mode_lib, rq_param, pipe_param.src);
857 print__rq_params_st(mode_lib, *rq_param);
858 }
859
dml30_rq_dlg_get_rq_reg(struct display_mode_lib * mode_lib,display_rq_regs_st * rq_regs,const display_pipe_params_st pipe_param)860 void dml30_rq_dlg_get_rq_reg(struct display_mode_lib *mode_lib,
861 display_rq_regs_st *rq_regs,
862 const display_pipe_params_st pipe_param)
863 {
864 display_rq_params_st rq_param = { 0 };
865
866 memset(rq_regs, 0, sizeof(*rq_regs));
867 dml_rq_dlg_get_rq_params(mode_lib, &rq_param, pipe_param);
868 extract_rq_regs(mode_lib, rq_regs, rq_param);
869
870 print__rq_regs_st(mode_lib, *rq_regs);
871 }
872
calculate_ttu_cursor(struct display_mode_lib * mode_lib,double * refcyc_per_req_delivery_pre_cur,double * refcyc_per_req_delivery_cur,double refclk_freq_in_mhz,double ref_freq_to_pix_freq,double hscale_pixel_rate_l,double hscl_ratio,double vratio_pre_l,double vratio_l,unsigned int cur_width,enum cursor_bpp cur_bpp)873 static void calculate_ttu_cursor(struct display_mode_lib *mode_lib,
874 double *refcyc_per_req_delivery_pre_cur,
875 double *refcyc_per_req_delivery_cur,
876 double refclk_freq_in_mhz,
877 double ref_freq_to_pix_freq,
878 double hscale_pixel_rate_l,
879 double hscl_ratio,
880 double vratio_pre_l,
881 double vratio_l,
882 unsigned int cur_width,
883 enum cursor_bpp cur_bpp)
884 {
885 unsigned int cur_src_width = cur_width;
886 unsigned int cur_req_size = 0;
887 unsigned int cur_req_width = 0;
888 double cur_width_ub = 0.0;
889 double cur_req_per_width = 0.0;
890 double hactive_cur = 0.0;
891
892 ASSERT(cur_src_width <= 256);
893
894 *refcyc_per_req_delivery_pre_cur = 0.0;
895 *refcyc_per_req_delivery_cur = 0.0;
896 if (cur_src_width > 0) {
897 unsigned int cur_bit_per_pixel = 0;
898
899 if (cur_bpp == dm_cur_2bit) {
900 cur_req_size = 64; // byte
901 cur_bit_per_pixel = 2;
902 } else { // 32bit
903 cur_bit_per_pixel = 32;
904 if (cur_src_width >= 1 && cur_src_width <= 16)
905 cur_req_size = 64;
906 else if (cur_src_width >= 17 && cur_src_width <= 31)
907 cur_req_size = 128;
908 else
909 cur_req_size = 256;
910 }
911
912 cur_req_width = (double)cur_req_size / ((double)cur_bit_per_pixel / 8.0);
913 cur_width_ub = dml_ceil((double)cur_src_width / (double)cur_req_width, 1)
914 * (double)cur_req_width;
915 cur_req_per_width = cur_width_ub / (double)cur_req_width;
916 hactive_cur = (double)cur_src_width / hscl_ratio; // FIXME: oswin to think about what to do for cursor
917
918 if (vratio_pre_l <= 1.0) {
919 *refcyc_per_req_delivery_pre_cur = hactive_cur * ref_freq_to_pix_freq
920 / (double)cur_req_per_width;
921 } else {
922 *refcyc_per_req_delivery_pre_cur = (double)refclk_freq_in_mhz
923 * (double)cur_src_width / hscale_pixel_rate_l
924 / (double)cur_req_per_width;
925 }
926
927 ASSERT(*refcyc_per_req_delivery_pre_cur < dml_pow(2, 13));
928
929 if (vratio_l <= 1.0) {
930 *refcyc_per_req_delivery_cur = hactive_cur * ref_freq_to_pix_freq
931 / (double)cur_req_per_width;
932 } else {
933 *refcyc_per_req_delivery_cur = (double)refclk_freq_in_mhz
934 * (double)cur_src_width / hscale_pixel_rate_l
935 / (double)cur_req_per_width;
936 }
937
938 dml_print("DML_DLG: %s: cur_req_width = %d\n",
939 __func__,
940 cur_req_width);
941 dml_print("DML_DLG: %s: cur_width_ub = %3.2f\n",
942 __func__,
943 cur_width_ub);
944 dml_print("DML_DLG: %s: cur_req_per_width = %3.2f\n",
945 __func__,
946 cur_req_per_width);
947 dml_print("DML_DLG: %s: hactive_cur = %3.2f\n",
948 __func__,
949 hactive_cur);
950 dml_print("DML_DLG: %s: refcyc_per_req_delivery_pre_cur = %3.2f\n",
951 __func__,
952 *refcyc_per_req_delivery_pre_cur);
953 dml_print("DML_DLG: %s: refcyc_per_req_delivery_cur = %3.2f\n",
954 __func__,
955 *refcyc_per_req_delivery_cur);
956
957 ASSERT(*refcyc_per_req_delivery_cur < dml_pow(2, 13));
958 }
959 }
960
961 // Note: currently taken in as is.
962 // Nice to decouple code from hw register implement and extract code that are repeated for luma and chroma.
dml_rq_dlg_get_dlg_params(struct display_mode_lib * mode_lib,const display_e2e_pipe_params_st * e2e_pipe_param,const unsigned int num_pipes,const unsigned int pipe_idx,display_dlg_regs_st * disp_dlg_regs,display_ttu_regs_st * disp_ttu_regs,const display_rq_dlg_params_st rq_dlg_param,const display_dlg_sys_params_st dlg_sys_param,const bool cstate_en,const bool pstate_en,const bool vm_en,const bool ignore_viewport_pos,const bool immediate_flip_support)963 static void dml_rq_dlg_get_dlg_params(struct display_mode_lib *mode_lib,
964 const display_e2e_pipe_params_st *e2e_pipe_param,
965 const unsigned int num_pipes,
966 const unsigned int pipe_idx,
967 display_dlg_regs_st *disp_dlg_regs,
968 display_ttu_regs_st *disp_ttu_regs,
969 const display_rq_dlg_params_st rq_dlg_param,
970 const display_dlg_sys_params_st dlg_sys_param,
971 const bool cstate_en,
972 const bool pstate_en,
973 const bool vm_en,
974 const bool ignore_viewport_pos,
975 const bool immediate_flip_support)
976 {
977 const display_pipe_source_params_st *src = &e2e_pipe_param[pipe_idx].pipe.src;
978 const display_pipe_dest_params_st *dst = &e2e_pipe_param[pipe_idx].pipe.dest;
979 const display_output_params_st *dout = &e2e_pipe_param[pipe_idx].dout;
980 const display_clocks_and_cfg_st *clks = &e2e_pipe_param[pipe_idx].clks_cfg;
981 const scaler_ratio_depth_st *scl = &e2e_pipe_param[pipe_idx].pipe.scale_ratio_depth;
982 const scaler_taps_st *taps = &e2e_pipe_param[pipe_idx].pipe.scale_taps;
983
984 // -------------------------
985 // Section 1.15.2.1: OTG dependent Params
986 // -------------------------
987 // Timing
988 unsigned int htotal = dst->htotal;
989 // unsigned int hblank_start = dst.hblank_start; // TODO: Remove
990 unsigned int hblank_end = dst->hblank_end;
991 unsigned int vblank_start = dst->vblank_start;
992 unsigned int vblank_end = dst->vblank_end;
993 unsigned int min_vblank = mode_lib->ip.min_vblank_lines;
994
995 double dppclk_freq_in_mhz = clks->dppclk_mhz;
996 double dispclk_freq_in_mhz = clks->dispclk_mhz;
997 double refclk_freq_in_mhz = clks->refclk_mhz;
998 double pclk_freq_in_mhz = dst->pixel_rate_mhz;
999 bool interlaced = dst->interlaced;
1000
1001 double ref_freq_to_pix_freq = refclk_freq_in_mhz / pclk_freq_in_mhz;
1002
1003 double min_dcfclk_mhz = 0;
1004 double t_calc_us = 0;
1005 double min_ttu_vblank = 0;
1006
1007 double min_dst_y_ttu_vblank = 0;
1008 unsigned int dlg_vblank_start = 0;
1009 bool dual_plane = 0;
1010 bool mode_422 = 0;
1011 unsigned int access_dir = 0;
1012 unsigned int vp_height_l = 0;
1013 unsigned int vp_width_l = 0;
1014 unsigned int vp_height_c = 0;
1015 unsigned int vp_width_c = 0;
1016
1017 // Scaling
1018 unsigned int htaps_l = 0;
1019 unsigned int htaps_c = 0;
1020 double hratio_l = 0;
1021 double hratio_c = 0;
1022 double vratio_l = 0;
1023 double vratio_c = 0;
1024 bool scl_enable = 0;
1025
1026 double line_time_in_us = 0;
1027 // double vinit_l;
1028 // double vinit_c;
1029 // double vinit_bot_l;
1030 // double vinit_bot_c;
1031
1032 // unsigned int swath_height_l;
1033 unsigned int swath_width_ub_l = 0;
1034 // unsigned int dpte_bytes_per_row_ub_l;
1035 unsigned int dpte_groups_per_row_ub_l = 0;
1036 // unsigned int meta_pte_bytes_per_frame_ub_l;
1037 // unsigned int meta_bytes_per_row_ub_l;
1038
1039 // unsigned int swath_height_c;
1040 unsigned int swath_width_ub_c = 0;
1041 // unsigned int dpte_bytes_per_row_ub_c;
1042 unsigned int dpte_groups_per_row_ub_c = 0;
1043
1044 unsigned int meta_chunks_per_row_ub_l = 0;
1045 unsigned int meta_chunks_per_row_ub_c = 0;
1046 unsigned int vupdate_offset = 0;
1047 unsigned int vupdate_width = 0;
1048 unsigned int vready_offset = 0;
1049
1050 unsigned int dppclk_delay_subtotal = 0;
1051 unsigned int dispclk_delay_subtotal = 0;
1052 unsigned int pixel_rate_delay_subtotal = 0;
1053
1054 unsigned int vstartup_start = 0;
1055 unsigned int dst_x_after_scaler = 0;
1056 unsigned int dst_y_after_scaler = 0;
1057 double line_wait = 0;
1058 double dst_y_prefetch = 0;
1059 double dst_y_per_vm_vblank = 0;
1060 double dst_y_per_row_vblank = 0;
1061 double dst_y_per_vm_flip = 0;
1062 double dst_y_per_row_flip = 0;
1063 double max_dst_y_per_vm_vblank = 0;
1064 double max_dst_y_per_row_vblank = 0;
1065 double lsw = 0;
1066 double vratio_pre_l = 0;
1067 double vratio_pre_c = 0;
1068 unsigned int req_per_swath_ub_l = 0;
1069 unsigned int req_per_swath_ub_c = 0;
1070 unsigned int meta_row_height_l = 0;
1071 unsigned int meta_row_height_c = 0;
1072 unsigned int swath_width_pixels_ub_l = 0;
1073 unsigned int swath_width_pixels_ub_c = 0;
1074 unsigned int scaler_rec_in_width_l = 0;
1075 unsigned int scaler_rec_in_width_c = 0;
1076 unsigned int dpte_row_height_l = 0;
1077 unsigned int dpte_row_height_c = 0;
1078 double hscale_pixel_rate_l = 0;
1079 double hscale_pixel_rate_c = 0;
1080 double min_hratio_fact_l = 0;
1081 double min_hratio_fact_c = 0;
1082 double refcyc_per_line_delivery_pre_l = 0;
1083 double refcyc_per_line_delivery_pre_c = 0;
1084 double refcyc_per_line_delivery_l = 0;
1085 double refcyc_per_line_delivery_c = 0;
1086
1087 double refcyc_per_req_delivery_pre_l = 0;
1088 double refcyc_per_req_delivery_pre_c = 0;
1089 double refcyc_per_req_delivery_l = 0;
1090 double refcyc_per_req_delivery_c = 0;
1091
1092 unsigned int full_recout_width = 0;
1093 double refcyc_per_req_delivery_pre_cur0 = 0;
1094 double refcyc_per_req_delivery_cur0 = 0;
1095 double refcyc_per_req_delivery_pre_cur1 = 0;
1096 double refcyc_per_req_delivery_cur1 = 0;
1097
1098 unsigned int pipe_index_in_combine[DC__NUM_PIPES__MAX] = { 0 };
1099
1100 memset(disp_dlg_regs, 0, sizeof(*disp_dlg_regs));
1101 memset(disp_ttu_regs, 0, sizeof(*disp_ttu_regs));
1102
1103 dml_print("DML_DLG: %s: cstate_en = %d\n", __func__, cstate_en);
1104 dml_print("DML_DLG: %s: pstate_en = %d\n", __func__, pstate_en);
1105 dml_print("DML_DLG: %s: vm_en = %d\n", __func__, vm_en);
1106 dml_print("DML_DLG: %s: ignore_viewport_pos = %d\n", __func__, ignore_viewport_pos);
1107 dml_print("DML_DLG: %s: immediate_flip_support = %d\n", __func__, immediate_flip_support);
1108
1109 dml_print("DML_DLG: %s: dppclk_freq_in_mhz = %3.2f\n", __func__, dppclk_freq_in_mhz);
1110 dml_print("DML_DLG: %s: dispclk_freq_in_mhz = %3.2f\n", __func__, dispclk_freq_in_mhz);
1111 dml_print("DML_DLG: %s: refclk_freq_in_mhz = %3.2f\n", __func__, refclk_freq_in_mhz);
1112 dml_print("DML_DLG: %s: pclk_freq_in_mhz = %3.2f\n", __func__, pclk_freq_in_mhz);
1113 dml_print("DML_DLG: %s: interlaced = %d\n", __func__, interlaced);
1114 ASSERT(ref_freq_to_pix_freq < 4.0);
1115
1116 disp_dlg_regs->ref_freq_to_pix_freq =
1117 (unsigned int)(ref_freq_to_pix_freq * dml_pow(2, 19));
1118 disp_dlg_regs->refcyc_per_htotal = (unsigned int)(ref_freq_to_pix_freq * (double)htotal
1119 * dml_pow(2, 8));
1120 disp_dlg_regs->dlg_vblank_end = interlaced ? (vblank_end / 2) : vblank_end; // 15 bits
1121
1122 min_dcfclk_mhz = dlg_sys_param.deepsleep_dcfclk_mhz;
1123 t_calc_us = get_tcalc(mode_lib, e2e_pipe_param, num_pipes);
1124 min_ttu_vblank = get_min_ttu_vblank(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1125
1126 min_dst_y_ttu_vblank = min_ttu_vblank * pclk_freq_in_mhz / (double)htotal;
1127 dlg_vblank_start = interlaced ? (vblank_start / 2) : vblank_start;
1128
1129 disp_dlg_regs->min_dst_y_next_start = (unsigned int)(((double)dlg_vblank_start
1130 ) * dml_pow(2, 2));
1131 ASSERT(disp_dlg_regs->min_dst_y_next_start < (unsigned int)dml_pow(2, 18));
1132
1133 dml_print("DML_DLG: %s: min_dcfclk_mhz = %3.2f\n",
1134 __func__,
1135 min_dcfclk_mhz);
1136 dml_print("DML_DLG: %s: min_ttu_vblank = %3.2f\n",
1137 __func__,
1138 min_ttu_vblank);
1139 dml_print("DML_DLG: %s: min_dst_y_ttu_vblank = %3.2f\n",
1140 __func__,
1141 min_dst_y_ttu_vblank);
1142 dml_print("DML_DLG: %s: t_calc_us = %3.2f\n",
1143 __func__,
1144 t_calc_us);
1145 dml_print("DML_DLG: %s: disp_dlg_regs->min_dst_y_next_start = 0x%0x\n",
1146 __func__,
1147 disp_dlg_regs->min_dst_y_next_start);
1148 dml_print("DML_DLG: %s: ref_freq_to_pix_freq = %3.2f\n",
1149 __func__,
1150 ref_freq_to_pix_freq);
1151
1152 // -------------------------
1153 // Section 1.15.2.2: Prefetch, Active and TTU
1154 // -------------------------
1155 // Prefetch Calc
1156 // Source
1157 // dcc_en = src.dcc;
1158 dual_plane = is_dual_plane((enum source_format_class)(src->source_format));
1159 mode_422 = 0; // TODO
1160 access_dir = (src->source_scan == dm_vert); // vp access direction: horizontal or vertical accessed
1161 vp_height_l = src->viewport_height;
1162 vp_width_l = src->viewport_width;
1163 vp_height_c = src->viewport_height_c;
1164 vp_width_c = src->viewport_width_c;
1165
1166 // Scaling
1167 htaps_l = taps->htaps;
1168 htaps_c = taps->htaps_c;
1169 hratio_l = scl->hscl_ratio;
1170 hratio_c = scl->hscl_ratio_c;
1171 vratio_l = scl->vscl_ratio;
1172 vratio_c = scl->vscl_ratio_c;
1173 scl_enable = scl->scl_enable;
1174
1175 line_time_in_us = (htotal / pclk_freq_in_mhz);
1176 swath_width_ub_l = rq_dlg_param.rq_l.swath_width_ub;
1177 dpte_groups_per_row_ub_l = rq_dlg_param.rq_l.dpte_groups_per_row_ub;
1178 swath_width_ub_c = rq_dlg_param.rq_c.swath_width_ub;
1179 dpte_groups_per_row_ub_c = rq_dlg_param.rq_c.dpte_groups_per_row_ub;
1180
1181 meta_chunks_per_row_ub_l = rq_dlg_param.rq_l.meta_chunks_per_row_ub;
1182 meta_chunks_per_row_ub_c = rq_dlg_param.rq_c.meta_chunks_per_row_ub;
1183 vupdate_offset = dst->vupdate_offset;
1184 vupdate_width = dst->vupdate_width;
1185 vready_offset = dst->vready_offset;
1186
1187 dppclk_delay_subtotal = mode_lib->ip.dppclk_delay_subtotal;
1188 dispclk_delay_subtotal = mode_lib->ip.dispclk_delay_subtotal;
1189
1190 if (scl_enable)
1191 dppclk_delay_subtotal += mode_lib->ip.dppclk_delay_scl;
1192 else
1193 dppclk_delay_subtotal += mode_lib->ip.dppclk_delay_scl_lb_only;
1194
1195 dppclk_delay_subtotal += mode_lib->ip.dppclk_delay_cnvc_formatter
1196 + src->num_cursors * mode_lib->ip.dppclk_delay_cnvc_cursor;
1197
1198 if (dout->dsc_enable) {
1199 double dsc_delay = get_dsc_delay(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1200
1201 dispclk_delay_subtotal += dsc_delay;
1202 }
1203
1204 pixel_rate_delay_subtotal = dppclk_delay_subtotal * pclk_freq_in_mhz / dppclk_freq_in_mhz
1205 + dispclk_delay_subtotal * pclk_freq_in_mhz / dispclk_freq_in_mhz;
1206
1207 vstartup_start = dst->vstartup_start;
1208 if (interlaced) {
1209 if (vstartup_start / 2.0
1210 - (double)(vready_offset + vupdate_width + vupdate_offset) / htotal
1211 <= vblank_end / 2.0)
1212 disp_dlg_regs->vready_after_vcount0 = 1;
1213 else
1214 disp_dlg_regs->vready_after_vcount0 = 0;
1215 } else {
1216 if (vstartup_start
1217 - (double)(vready_offset + vupdate_width + vupdate_offset) / htotal
1218 <= vblank_end)
1219 disp_dlg_regs->vready_after_vcount0 = 1;
1220 else
1221 disp_dlg_regs->vready_after_vcount0 = 0;
1222 }
1223
1224 // TODO: Where is this coming from?
1225 if (interlaced)
1226 vstartup_start = vstartup_start / 2;
1227
1228 // TODO: What if this min_vblank doesn't match the value in the dml_config_settings.cpp?
1229 if (vstartup_start >= min_vblank) {
1230 dml_print("WARNING: DML_DLG: %s: vblank_start=%d vblank_end=%d\n",
1231 __func__,
1232 vblank_start,
1233 vblank_end);
1234 dml_print("WARNING: DML_DLG: %s: vstartup_start=%d should be less than min_vblank=%d\n",
1235 __func__,
1236 vstartup_start,
1237 min_vblank);
1238 min_vblank = vstartup_start + 1;
1239 dml_print("WARNING: DML_DLG: %s: vstartup_start=%d should be less than min_vblank=%d\n",
1240 __func__,
1241 vstartup_start,
1242 min_vblank);
1243 }
1244
1245 dst_x_after_scaler = get_dst_x_after_scaler(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1246 dst_y_after_scaler = get_dst_y_after_scaler(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1247
1248 // do some adjustment on the dst_after scaler to account for odm combine mode
1249 dml_print("DML_DLG: %s: input dst_x_after_scaler = %d\n",
1250 __func__,
1251 dst_x_after_scaler);
1252 dml_print("DML_DLG: %s: input dst_y_after_scaler = %d\n",
1253 __func__,
1254 dst_y_after_scaler);
1255
1256 // need to figure out which side of odm combine we're in
1257 if (dst->odm_combine) {
1258 // figure out which pipes go together
1259 bool visited[DC__NUM_PIPES__MAX] = { false };
1260 unsigned int i, j, k;
1261
1262 for (k = 0; k < num_pipes; ++k) {
1263 visited[k] = false;
1264 pipe_index_in_combine[k] = 0;
1265 }
1266
1267 for (i = 0; i < num_pipes; i++) {
1268 if (e2e_pipe_param[i].pipe.src.is_hsplit && !visited[i]) {
1269
1270 unsigned int grp = e2e_pipe_param[i].pipe.src.hsplit_grp;
1271 unsigned int grp_idx = 0;
1272
1273 for (j = i; j < num_pipes; j++) {
1274 if (e2e_pipe_param[j].pipe.src.hsplit_grp == grp
1275 && e2e_pipe_param[j].pipe.src.is_hsplit && !visited[j]) {
1276 pipe_index_in_combine[j] = grp_idx;
1277 dml_print("DML_DLG: %s: pipe[%d] is in grp %d idx %d\n", __func__, j, grp, grp_idx);
1278 grp_idx++;
1279 visited[j] = true;
1280 }
1281 }
1282 }
1283 }
1284
1285 }
1286
1287 if (dst->odm_combine == dm_odm_combine_mode_disabled) {
1288 disp_dlg_regs->refcyc_h_blank_end = (unsigned int)((double) hblank_end * ref_freq_to_pix_freq);
1289 } else {
1290 unsigned int odm_combine_factor = (dst->odm_combine == dm_odm_combine_mode_2to1 ? 2 : 4); // TODO: We should really check that 4to1 is supported before setting it to 4
1291 unsigned int odm_pipe_index = pipe_index_in_combine[pipe_idx];
1292 disp_dlg_regs->refcyc_h_blank_end = (unsigned int)(((double) hblank_end + odm_pipe_index * (double) dst->hactive / odm_combine_factor) * ref_freq_to_pix_freq);
1293 }
1294 ASSERT(disp_dlg_regs->refcyc_h_blank_end < (unsigned int)dml_pow(2, 13));
1295
1296 dml_print("DML_DLG: %s: htotal = %d\n", __func__, htotal);
1297 dml_print("DML_DLG: %s: pixel_rate_delay_subtotal = %d\n",
1298 __func__,
1299 pixel_rate_delay_subtotal);
1300 dml_print("DML_DLG: %s: dst_x_after_scaler[%d] = %d\n",
1301 __func__,
1302 pipe_idx,
1303 dst_x_after_scaler);
1304 dml_print("DML_DLG: %s: dst_y_after_scaler[%d] = %d\n",
1305 __func__,
1306 pipe_idx,
1307 dst_y_after_scaler);
1308
1309 // Lwait
1310 // TODO: Should this be urgent_latency_pixel_mixed_with_vm_data_us?
1311 line_wait = mode_lib->soc.urgent_latency_pixel_data_only_us;
1312 if (cstate_en)
1313 line_wait = dml_max(mode_lib->soc.sr_enter_plus_exit_time_us, line_wait);
1314 if (pstate_en)
1315 line_wait = dml_max(mode_lib->soc.dram_clock_change_latency_us
1316 + mode_lib->soc.urgent_latency_pixel_data_only_us, // TODO: Should this be urgent_latency_pixel_mixed_with_vm_data_us?
1317 line_wait);
1318 line_wait = line_wait / line_time_in_us;
1319
1320 dst_y_prefetch = get_dst_y_prefetch(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1321 dml_print("DML_DLG: %s: dst_y_prefetch (after rnd) = %3.2f\n", __func__, dst_y_prefetch);
1322
1323 dst_y_per_vm_vblank = get_dst_y_per_vm_vblank(mode_lib,
1324 e2e_pipe_param,
1325 num_pipes,
1326 pipe_idx);
1327 dst_y_per_row_vblank = get_dst_y_per_row_vblank(mode_lib,
1328 e2e_pipe_param,
1329 num_pipes,
1330 pipe_idx);
1331 dst_y_per_vm_flip = get_dst_y_per_vm_flip(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1332 dst_y_per_row_flip = get_dst_y_per_row_flip(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1333
1334 max_dst_y_per_vm_vblank = 32.0; //U5.2
1335 max_dst_y_per_row_vblank = 16.0; //U4.2
1336
1337 // magic!
1338 if (htotal <= 75) {
1339 min_vblank = 300;
1340 max_dst_y_per_vm_vblank = 100.0;
1341 max_dst_y_per_row_vblank = 100.0;
1342 }
1343
1344 dml_print("DML_DLG: %s: dst_y_per_vm_flip = %3.2f\n", __func__, dst_y_per_vm_flip);
1345 dml_print("DML_DLG: %s: dst_y_per_row_flip = %3.2f\n", __func__, dst_y_per_row_flip);
1346 dml_print("DML_DLG: %s: dst_y_per_vm_vblank = %3.2f\n", __func__, dst_y_per_vm_vblank);
1347 dml_print("DML_DLG: %s: dst_y_per_row_vblank = %3.2f\n", __func__, dst_y_per_row_vblank);
1348
1349 ASSERT(dst_y_per_vm_vblank < max_dst_y_per_vm_vblank);
1350 ASSERT(dst_y_per_row_vblank < max_dst_y_per_row_vblank);
1351
1352 ASSERT(dst_y_prefetch > (dst_y_per_vm_vblank + dst_y_per_row_vblank));
1353 lsw = dst_y_prefetch - (dst_y_per_vm_vblank + dst_y_per_row_vblank);
1354
1355 dml_print("DML_DLG: %s: lsw = %3.2f\n", __func__, lsw);
1356
1357 vratio_pre_l = get_vratio_prefetch_l(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1358 vratio_pre_c = get_vratio_prefetch_c(mode_lib, e2e_pipe_param, num_pipes, pipe_idx);
1359
1360 dml_print("DML_DLG: %s: vratio_pre_l=%3.2f\n", __func__, vratio_pre_l);
1361 dml_print("DML_DLG: %s: vratio_pre_c=%3.2f\n", __func__, vratio_pre_c);
1362
1363 // Active
1364 req_per_swath_ub_l = rq_dlg_param.rq_l.req_per_swath_ub;
1365 req_per_swath_ub_c = rq_dlg_param.rq_c.req_per_swath_ub;
1366 meta_row_height_l = rq_dlg_param.rq_l.meta_row_height;
1367 meta_row_height_c = rq_dlg_param.rq_c.meta_row_height;
1368 swath_width_pixels_ub_l = 0;
1369 swath_width_pixels_ub_c = 0;
1370 scaler_rec_in_width_l = 0;
1371 scaler_rec_in_width_c = 0;
1372 dpte_row_height_l = rq_dlg_param.rq_l.dpte_row_height;
1373 dpte_row_height_c = rq_dlg_param.rq_c.dpte_row_height;
1374
1375 if (mode_422) {
1376 swath_width_pixels_ub_l = swath_width_ub_l * 2; // *2 for 2 pixel per element
1377 swath_width_pixels_ub_c = swath_width_ub_c * 2;
1378 } else {
1379 swath_width_pixels_ub_l = swath_width_ub_l * 1;
1380 swath_width_pixels_ub_c = swath_width_ub_c * 1;
1381 }
1382
1383 hscale_pixel_rate_l = 0.;
1384 hscale_pixel_rate_c = 0.;
1385 min_hratio_fact_l = 1.0;
1386 min_hratio_fact_c = 1.0;
1387
1388 if (hratio_l <= 1)
1389 min_hratio_fact_l = 2.0;
1390 else if (htaps_l <= 6) {
1391 if ((hratio_l * 2.0) > 4.0)
1392 min_hratio_fact_l = 4.0;
1393 else
1394 min_hratio_fact_l = hratio_l * 2.0;
1395 } else {
1396 if (hratio_l > 4.0)
1397 min_hratio_fact_l = 4.0;
1398 else
1399 min_hratio_fact_l = hratio_l;
1400 }
1401
1402 hscale_pixel_rate_l = min_hratio_fact_l * dppclk_freq_in_mhz;
1403
1404 if (hratio_c <= 1)
1405 min_hratio_fact_c = 2.0;
1406 else if (htaps_c <= 6) {
1407 if ((hratio_c * 2.0) > 4.0)
1408 min_hratio_fact_c = 4.0;
1409 else
1410 min_hratio_fact_c = hratio_c * 2.0;
1411 } else {
1412 if (hratio_c > 4.0)
1413 min_hratio_fact_c = 4.0;
1414 else
1415 min_hratio_fact_c = hratio_c;
1416 }
1417
1418 hscale_pixel_rate_c = min_hratio_fact_c * dppclk_freq_in_mhz;
1419
1420 refcyc_per_line_delivery_pre_l = 0.;
1421 refcyc_per_line_delivery_pre_c = 0.;
1422 refcyc_per_line_delivery_l = 0.;
1423 refcyc_per_line_delivery_c = 0.;
1424
1425 refcyc_per_req_delivery_pre_l = 0.;
1426 refcyc_per_req_delivery_pre_c = 0.;
1427 refcyc_per_req_delivery_l = 0.;
1428 refcyc_per_req_delivery_c = 0.;
1429
1430 full_recout_width = 0;
1431 // In ODM
1432 if (src->is_hsplit) {
1433 // This "hack" is only allowed (and valid) for MPC combine. In ODM
1434 // combine, you MUST specify the full_recout_width...according to Oswin
1435 if (dst->full_recout_width == 0 && !dst->odm_combine) {
1436 dml_print("DML_DLG: %s: Warning: full_recout_width not set in hsplit mode\n",
1437 __func__);
1438 full_recout_width = dst->recout_width * 2; // assume half split for dcn1
1439 } else
1440 full_recout_width = dst->full_recout_width;
1441 } else
1442 full_recout_width = dst->recout_width;
1443
1444 // As of DCN2, mpc_combine and odm_combine are mutually exclusive
1445 refcyc_per_line_delivery_pre_l = get_refcyc_per_delivery(mode_lib,
1446 refclk_freq_in_mhz,
1447 pclk_freq_in_mhz,
1448 dst->odm_combine,
1449 full_recout_width,
1450 dst->hactive,
1451 vratio_pre_l,
1452 hscale_pixel_rate_l,
1453 swath_width_pixels_ub_l,
1454 1); // per line
1455
1456 refcyc_per_line_delivery_l = get_refcyc_per_delivery(mode_lib,
1457 refclk_freq_in_mhz,
1458 pclk_freq_in_mhz,
1459 dst->odm_combine,
1460 full_recout_width,
1461 dst->hactive,
1462 vratio_l,
1463 hscale_pixel_rate_l,
1464 swath_width_pixels_ub_l,
1465 1); // per line
1466
1467 dml_print("DML_DLG: %s: full_recout_width = %d\n",
1468 __func__,
1469 full_recout_width);
1470 dml_print("DML_DLG: %s: hscale_pixel_rate_l = %3.2f\n",
1471 __func__,
1472 hscale_pixel_rate_l);
1473 dml_print("DML_DLG: %s: refcyc_per_line_delivery_pre_l = %3.2f\n",
1474 __func__,
1475 refcyc_per_line_delivery_pre_l);
1476 dml_print("DML_DLG: %s: refcyc_per_line_delivery_l = %3.2f\n",
1477 __func__,
1478 refcyc_per_line_delivery_l);
1479
1480 if (dual_plane) {
1481 refcyc_per_line_delivery_pre_c = get_refcyc_per_delivery(mode_lib,
1482 refclk_freq_in_mhz,
1483 pclk_freq_in_mhz,
1484 dst->odm_combine,
1485 full_recout_width,
1486 dst->hactive,
1487 vratio_pre_c,
1488 hscale_pixel_rate_c,
1489 swath_width_pixels_ub_c,
1490 1); // per line
1491
1492 refcyc_per_line_delivery_c = get_refcyc_per_delivery(mode_lib,
1493 refclk_freq_in_mhz,
1494 pclk_freq_in_mhz,
1495 dst->odm_combine,
1496 full_recout_width,
1497 dst->hactive,
1498 vratio_c,
1499 hscale_pixel_rate_c,
1500 swath_width_pixels_ub_c,
1501 1); // per line
1502
1503 dml_print("DML_DLG: %s: refcyc_per_line_delivery_pre_c = %3.2f\n",
1504 __func__,
1505 refcyc_per_line_delivery_pre_c);
1506 dml_print("DML_DLG: %s: refcyc_per_line_delivery_c = %3.2f\n",
1507 __func__,
1508 refcyc_per_line_delivery_c);
1509 }
1510
1511 // smehta: this is a hack added until we get the real dml, sorry, need to make progress
1512 if (src->dynamic_metadata_enable && src->gpuvm) {
1513 unsigned int levels = mode_lib->ip.gpuvm_max_page_table_levels;
1514 double ref_cycles;
1515
1516 if (src->hostvm)
1517 levels = levels * (mode_lib->ip.hostvm_max_page_table_levels+1);
1518
1519 ref_cycles = (levels * mode_lib->soc.urgent_latency_vm_data_only_us) * refclk_freq_in_mhz;
1520 dml_print("BENyamin: dst_y_prefetch = %f %d %f %f \n",
1521 ref_cycles, levels, mode_lib->soc.urgent_latency_vm_data_only_us, refclk_freq_in_mhz);
1522 disp_dlg_regs->refcyc_per_vm_dmdata = (unsigned int) ref_cycles;
1523 }
1524 dml_print("BENyamin: dmdta_en vm = %d %d \n",
1525 src->dynamic_metadata_enable, src->vm);
1526 // TTU - Luma / Chroma
1527 if (access_dir) { // vertical access
1528 scaler_rec_in_width_l = vp_height_l;
1529 scaler_rec_in_width_c = vp_height_c;
1530 } else {
1531 scaler_rec_in_width_l = vp_width_l;
1532 scaler_rec_in_width_c = vp_width_c;
1533 }
1534
1535 refcyc_per_req_delivery_pre_l = get_refcyc_per_delivery(mode_lib,
1536 refclk_freq_in_mhz,
1537 pclk_freq_in_mhz,
1538 dst->odm_combine,
1539 full_recout_width,
1540 dst->hactive,
1541 vratio_pre_l,
1542 hscale_pixel_rate_l,
1543 scaler_rec_in_width_l,
1544 req_per_swath_ub_l); // per req
1545 refcyc_per_req_delivery_l = get_refcyc_per_delivery(mode_lib,
1546 refclk_freq_in_mhz,
1547 pclk_freq_in_mhz,
1548 dst->odm_combine,
1549 full_recout_width,
1550 dst->hactive,
1551 vratio_l,
1552 hscale_pixel_rate_l,
1553 scaler_rec_in_width_l,
1554 req_per_swath_ub_l); // per req
1555
1556 dml_print("DML_DLG: %s: refcyc_per_req_delivery_pre_l = %3.2f\n",
1557 __func__,
1558 refcyc_per_req_delivery_pre_l);
1559 dml_print("DML_DLG: %s: refcyc_per_req_delivery_l = %3.2f\n",
1560 __func__,
1561 refcyc_per_req_delivery_l);
1562
1563 ASSERT(refcyc_per_req_delivery_pre_l < dml_pow(2, 13));
1564 ASSERT(refcyc_per_req_delivery_l < dml_pow(2, 13));
1565
1566 if (dual_plane) {
1567 refcyc_per_req_delivery_pre_c = get_refcyc_per_delivery(mode_lib,
1568 refclk_freq_in_mhz,
1569 pclk_freq_in_mhz,
1570 dst->odm_combine,
1571 full_recout_width,
1572 dst->hactive,
1573 vratio_pre_c,
1574 hscale_pixel_rate_c,
1575 scaler_rec_in_width_c,
1576 req_per_swath_ub_c); // per req
1577 refcyc_per_req_delivery_c = get_refcyc_per_delivery(mode_lib,
1578 refclk_freq_in_mhz,
1579 pclk_freq_in_mhz,
1580 dst->odm_combine,
1581 full_recout_width,
1582 dst->hactive,
1583 vratio_c,
1584 hscale_pixel_rate_c,
1585 scaler_rec_in_width_c,
1586 req_per_swath_ub_c); // per req
1587
1588 dml_print("DML_DLG: %s: refcyc_per_req_delivery_pre_c = %3.2f\n",
1589 __func__,
1590 refcyc_per_req_delivery_pre_c);
1591 dml_print("DML_DLG: %s: refcyc_per_req_delivery_c = %3.2f\n",
1592 __func__,
1593 refcyc_per_req_delivery_c);
1594
1595 ASSERT(refcyc_per_req_delivery_pre_c < dml_pow(2, 13));
1596 ASSERT(refcyc_per_req_delivery_c < dml_pow(2, 13));
1597 }
1598
1599 // TTU - Cursor
1600 refcyc_per_req_delivery_pre_cur0 = 0.0;
1601 refcyc_per_req_delivery_cur0 = 0.0;
1602 if (src->num_cursors > 0) {
1603 calculate_ttu_cursor(mode_lib,
1604 &refcyc_per_req_delivery_pre_cur0,
1605 &refcyc_per_req_delivery_cur0,
1606 refclk_freq_in_mhz,
1607 ref_freq_to_pix_freq,
1608 hscale_pixel_rate_l,
1609 scl->hscl_ratio,
1610 vratio_pre_l,
1611 vratio_l,
1612 src->cur0_src_width,
1613 (enum cursor_bpp)(src->cur0_bpp));
1614 }
1615
1616 refcyc_per_req_delivery_pre_cur1 = 0.0;
1617 refcyc_per_req_delivery_cur1 = 0.0;
1618 if (src->num_cursors > 1) {
1619 calculate_ttu_cursor(mode_lib,
1620 &refcyc_per_req_delivery_pre_cur1,
1621 &refcyc_per_req_delivery_cur1,
1622 refclk_freq_in_mhz,
1623 ref_freq_to_pix_freq,
1624 hscale_pixel_rate_l,
1625 scl->hscl_ratio,
1626 vratio_pre_l,
1627 vratio_l,
1628 src->cur1_src_width,
1629 (enum cursor_bpp)(src->cur1_bpp));
1630 }
1631
1632 // TTU - Misc
1633 // all hard-coded
1634
1635 // Assignment to register structures
1636 disp_dlg_regs->dst_y_after_scaler = dst_y_after_scaler; // in terms of line
1637 ASSERT(disp_dlg_regs->dst_y_after_scaler < (unsigned int)8);
1638 disp_dlg_regs->refcyc_x_after_scaler = dst_x_after_scaler * ref_freq_to_pix_freq; // in terms of refclk
1639 ASSERT(disp_dlg_regs->refcyc_x_after_scaler < (unsigned int)dml_pow(2, 13));
1640 disp_dlg_regs->dst_y_prefetch = (unsigned int)(dst_y_prefetch * dml_pow(2, 2));
1641 disp_dlg_regs->dst_y_per_vm_vblank = (unsigned int)(dst_y_per_vm_vblank * dml_pow(2, 2));
1642 disp_dlg_regs->dst_y_per_row_vblank = (unsigned int)(dst_y_per_row_vblank * dml_pow(2, 2));
1643 disp_dlg_regs->dst_y_per_vm_flip = (unsigned int)(dst_y_per_vm_flip * dml_pow(2, 2));
1644 disp_dlg_regs->dst_y_per_row_flip = (unsigned int)(dst_y_per_row_flip * dml_pow(2, 2));
1645
1646 disp_dlg_regs->vratio_prefetch = (unsigned int)(vratio_pre_l * dml_pow(2, 19));
1647 disp_dlg_regs->vratio_prefetch_c = (unsigned int)(vratio_pre_c * dml_pow(2, 19));
1648
1649 dml_print("DML_DLG: %s: disp_dlg_regs->dst_y_per_vm_vblank = 0x%x\n", __func__, disp_dlg_regs->dst_y_per_vm_vblank);
1650 dml_print("DML_DLG: %s: disp_dlg_regs->dst_y_per_row_vblank = 0x%x\n", __func__, disp_dlg_regs->dst_y_per_row_vblank);
1651 dml_print("DML_DLG: %s: disp_dlg_regs->dst_y_per_vm_flip = 0x%x\n", __func__, disp_dlg_regs->dst_y_per_vm_flip);
1652 dml_print("DML_DLG: %s: disp_dlg_regs->dst_y_per_row_flip = 0x%x\n", __func__, disp_dlg_regs->dst_y_per_row_flip);
1653 disp_dlg_regs->refcyc_per_pte_group_vblank_l =
1654 (unsigned int)(dst_y_per_row_vblank * (double)htotal
1655 * ref_freq_to_pix_freq / (double)dpte_groups_per_row_ub_l);
1656 ASSERT(disp_dlg_regs->refcyc_per_pte_group_vblank_l < (unsigned int)dml_pow(2, 13));
1657
1658 if (dual_plane) {
1659 disp_dlg_regs->refcyc_per_pte_group_vblank_c = (unsigned int)(dst_y_per_row_vblank
1660 * (double)htotal * ref_freq_to_pix_freq
1661 / (double)dpte_groups_per_row_ub_c);
1662 ASSERT(disp_dlg_regs->refcyc_per_pte_group_vblank_c
1663 < (unsigned int)dml_pow(2, 13));
1664 }
1665
1666 disp_dlg_regs->refcyc_per_meta_chunk_vblank_l =
1667 (unsigned int)(dst_y_per_row_vblank * (double)htotal
1668 * ref_freq_to_pix_freq / (double)meta_chunks_per_row_ub_l);
1669 ASSERT(disp_dlg_regs->refcyc_per_meta_chunk_vblank_l < (unsigned int)dml_pow(2, 13));
1670
1671 disp_dlg_regs->refcyc_per_meta_chunk_vblank_c =
1672 disp_dlg_regs->refcyc_per_meta_chunk_vblank_l; // dcc for 4:2:0 is not supported in dcn1.0. assigned to be the same as _l for now
1673
1674 disp_dlg_regs->refcyc_per_pte_group_flip_l = (unsigned int)(dst_y_per_row_flip * htotal
1675 * ref_freq_to_pix_freq) / dpte_groups_per_row_ub_l;
1676 disp_dlg_regs->refcyc_per_meta_chunk_flip_l = (unsigned int)(dst_y_per_row_flip * htotal
1677 * ref_freq_to_pix_freq) / meta_chunks_per_row_ub_l;
1678
1679 if (dual_plane) {
1680 disp_dlg_regs->refcyc_per_pte_group_flip_c = (unsigned int)(dst_y_per_row_flip
1681 * htotal * ref_freq_to_pix_freq) / dpte_groups_per_row_ub_c;
1682 disp_dlg_regs->refcyc_per_meta_chunk_flip_c = (unsigned int)(dst_y_per_row_flip
1683 * htotal * ref_freq_to_pix_freq) / meta_chunks_per_row_ub_c;
1684 }
1685
1686 disp_dlg_regs->refcyc_per_vm_group_vblank = get_refcyc_per_vm_group_vblank(mode_lib, e2e_pipe_param, num_pipes, pipe_idx) * refclk_freq_in_mhz;
1687 disp_dlg_regs->refcyc_per_vm_group_flip = get_refcyc_per_vm_group_flip(mode_lib, e2e_pipe_param, num_pipes, pipe_idx) * refclk_freq_in_mhz;
1688 disp_dlg_regs->refcyc_per_vm_req_vblank = get_refcyc_per_vm_req_vblank(mode_lib, e2e_pipe_param, num_pipes, pipe_idx) * refclk_freq_in_mhz * dml_pow(2, 10);
1689 disp_dlg_regs->refcyc_per_vm_req_flip = get_refcyc_per_vm_req_flip(mode_lib, e2e_pipe_param, num_pipes, pipe_idx) * refclk_freq_in_mhz * dml_pow(2, 10);
1690
1691 // Clamp to max for now
1692 if (disp_dlg_regs->refcyc_per_vm_group_vblank >= (unsigned int)dml_pow(2, 23))
1693 disp_dlg_regs->refcyc_per_vm_group_vblank = dml_pow(2, 23) - 1;
1694
1695 if (disp_dlg_regs->refcyc_per_vm_group_flip >= (unsigned int)dml_pow(2, 23))
1696 disp_dlg_regs->refcyc_per_vm_group_flip = dml_pow(2, 23) - 1;
1697
1698 if (disp_dlg_regs->refcyc_per_vm_req_vblank >= (unsigned int)dml_pow(2, 23))
1699 disp_dlg_regs->refcyc_per_vm_req_vblank = dml_pow(2, 23) - 1;
1700
1701 if (disp_dlg_regs->refcyc_per_vm_req_flip >= (unsigned int)dml_pow(2, 23))
1702 disp_dlg_regs->refcyc_per_vm_req_flip = dml_pow(2, 23) - 1;
1703
1704 disp_dlg_regs->dst_y_per_pte_row_nom_l = (unsigned int)((double)dpte_row_height_l
1705 / (double)vratio_l * dml_pow(2, 2));
1706 ASSERT(disp_dlg_regs->dst_y_per_pte_row_nom_l < (unsigned int)dml_pow(2, 17));
1707
1708 if (dual_plane) {
1709 disp_dlg_regs->dst_y_per_pte_row_nom_c = (unsigned int)((double)dpte_row_height_c
1710 / (double)vratio_c * dml_pow(2, 2));
1711 if (disp_dlg_regs->dst_y_per_pte_row_nom_c >= (unsigned int)dml_pow(2, 17)) {
1712 dml_print("DML_DLG: %s: Warning dst_y_per_pte_row_nom_c %u larger than supported by register format U15.2 %u\n",
1713 __func__,
1714 disp_dlg_regs->dst_y_per_pte_row_nom_c,
1715 (unsigned int)dml_pow(2, 17) - 1);
1716 }
1717 }
1718
1719 disp_dlg_regs->dst_y_per_meta_row_nom_l = (unsigned int)((double)meta_row_height_l
1720 / (double)vratio_l * dml_pow(2, 2));
1721 ASSERT(disp_dlg_regs->dst_y_per_meta_row_nom_l < (unsigned int)dml_pow(2, 17));
1722
1723 disp_dlg_regs->dst_y_per_meta_row_nom_c = disp_dlg_regs->dst_y_per_meta_row_nom_l; // TODO: dcc for 4:2:0 is not supported in dcn1.0. assigned to be the same as _l for now
1724
1725 dml_print("DML: Trow: %fus\n", line_time_in_us * (double)dpte_row_height_l / (double)vratio_l);
1726
1727 disp_dlg_regs->refcyc_per_pte_group_nom_l = (unsigned int)((double)dpte_row_height_l
1728 / (double)vratio_l * (double)htotal * ref_freq_to_pix_freq
1729 / (double)dpte_groups_per_row_ub_l);
1730 if (disp_dlg_regs->refcyc_per_pte_group_nom_l >= (unsigned int)dml_pow(2, 23))
1731 disp_dlg_regs->refcyc_per_pte_group_nom_l = dml_pow(2, 23) - 1;
1732 disp_dlg_regs->refcyc_per_meta_chunk_nom_l = (unsigned int)((double)meta_row_height_l
1733 / (double)vratio_l * (double)htotal * ref_freq_to_pix_freq
1734 / (double)meta_chunks_per_row_ub_l);
1735 if (disp_dlg_regs->refcyc_per_meta_chunk_nom_l >= (unsigned int)dml_pow(2, 23))
1736 disp_dlg_regs->refcyc_per_meta_chunk_nom_l = dml_pow(2, 23) - 1;
1737
1738 if (dual_plane) {
1739 disp_dlg_regs->refcyc_per_pte_group_nom_c =
1740 (unsigned int)((double)dpte_row_height_c / (double)vratio_c
1741 * (double)htotal * ref_freq_to_pix_freq
1742 / (double)dpte_groups_per_row_ub_c);
1743 if (disp_dlg_regs->refcyc_per_pte_group_nom_c >= (unsigned int)dml_pow(2, 23))
1744 disp_dlg_regs->refcyc_per_pte_group_nom_c = dml_pow(2, 23) - 1;
1745
1746 // TODO: Is this the right calculation? Does htotal need to be halved?
1747 disp_dlg_regs->refcyc_per_meta_chunk_nom_c =
1748 (unsigned int)((double)meta_row_height_c / (double)vratio_c
1749 * (double)htotal * ref_freq_to_pix_freq
1750 / (double)meta_chunks_per_row_ub_c);
1751 if (disp_dlg_regs->refcyc_per_meta_chunk_nom_c >= (unsigned int)dml_pow(2, 23))
1752 disp_dlg_regs->refcyc_per_meta_chunk_nom_c = dml_pow(2, 23) - 1;
1753 }
1754
1755 disp_dlg_regs->refcyc_per_line_delivery_pre_l = (unsigned int)dml_floor(refcyc_per_line_delivery_pre_l,
1756 1);
1757 disp_dlg_regs->refcyc_per_line_delivery_l = (unsigned int)dml_floor(refcyc_per_line_delivery_l,
1758 1);
1759 ASSERT(disp_dlg_regs->refcyc_per_line_delivery_pre_l < (unsigned int)dml_pow(2, 13));
1760 ASSERT(disp_dlg_regs->refcyc_per_line_delivery_l < (unsigned int)dml_pow(2, 13));
1761
1762 disp_dlg_regs->refcyc_per_line_delivery_pre_c = (unsigned int)dml_floor(refcyc_per_line_delivery_pre_c,
1763 1);
1764 disp_dlg_regs->refcyc_per_line_delivery_c = (unsigned int)dml_floor(refcyc_per_line_delivery_c,
1765 1);
1766 ASSERT(disp_dlg_regs->refcyc_per_line_delivery_pre_c < (unsigned int)dml_pow(2, 13));
1767 ASSERT(disp_dlg_regs->refcyc_per_line_delivery_c < (unsigned int)dml_pow(2, 13));
1768
1769 disp_dlg_regs->chunk_hdl_adjust_cur0 = 3;
1770 disp_dlg_regs->dst_y_offset_cur0 = 0;
1771 disp_dlg_regs->chunk_hdl_adjust_cur1 = 3;
1772 disp_dlg_regs->dst_y_offset_cur1 = 0;
1773
1774 disp_dlg_regs->dst_y_delta_drq_limit = 0x7fff; // off
1775
1776 disp_ttu_regs->refcyc_per_req_delivery_pre_l = (unsigned int)(refcyc_per_req_delivery_pre_l
1777 * dml_pow(2, 10));
1778 disp_ttu_regs->refcyc_per_req_delivery_l = (unsigned int)(refcyc_per_req_delivery_l
1779 * dml_pow(2, 10));
1780 disp_ttu_regs->refcyc_per_req_delivery_pre_c = (unsigned int)(refcyc_per_req_delivery_pre_c
1781 * dml_pow(2, 10));
1782 disp_ttu_regs->refcyc_per_req_delivery_c = (unsigned int)(refcyc_per_req_delivery_c
1783 * dml_pow(2, 10));
1784 disp_ttu_regs->refcyc_per_req_delivery_pre_cur0 =
1785 (unsigned int)(refcyc_per_req_delivery_pre_cur0 * dml_pow(2, 10));
1786 disp_ttu_regs->refcyc_per_req_delivery_cur0 = (unsigned int)(refcyc_per_req_delivery_cur0
1787 * dml_pow(2, 10));
1788 disp_ttu_regs->refcyc_per_req_delivery_pre_cur1 =
1789 (unsigned int)(refcyc_per_req_delivery_pre_cur1 * dml_pow(2, 10));
1790 disp_ttu_regs->refcyc_per_req_delivery_cur1 = (unsigned int)(refcyc_per_req_delivery_cur1
1791 * dml_pow(2, 10));
1792 disp_ttu_regs->qos_level_low_wm = 0;
1793 ASSERT(disp_ttu_regs->qos_level_low_wm < dml_pow(2, 14));
1794 disp_ttu_regs->qos_level_high_wm = (unsigned int)(4.0 * (double)htotal
1795 * ref_freq_to_pix_freq);
1796 ASSERT(disp_ttu_regs->qos_level_high_wm < dml_pow(2, 14));
1797
1798 disp_ttu_regs->qos_level_flip = 14;
1799 disp_ttu_regs->qos_level_fixed_l = 8;
1800 disp_ttu_regs->qos_level_fixed_c = 8;
1801 disp_ttu_regs->qos_level_fixed_cur0 = 8;
1802 disp_ttu_regs->qos_ramp_disable_l = 0;
1803 disp_ttu_regs->qos_ramp_disable_c = 0;
1804 disp_ttu_regs->qos_ramp_disable_cur0 = 0;
1805
1806 disp_ttu_regs->min_ttu_vblank = min_ttu_vblank * refclk_freq_in_mhz;
1807 ASSERT(disp_ttu_regs->min_ttu_vblank < dml_pow(2, 24));
1808
1809 print__ttu_regs_st(mode_lib, *disp_ttu_regs);
1810 print__dlg_regs_st(mode_lib, *disp_dlg_regs);
1811 }
1812
dml30_rq_dlg_get_dlg_reg(struct display_mode_lib * mode_lib,display_dlg_regs_st * dlg_regs,display_ttu_regs_st * ttu_regs,display_e2e_pipe_params_st * e2e_pipe_param,const unsigned int num_pipes,const unsigned int pipe_idx,const bool cstate_en,const bool pstate_en,const bool vm_en,const bool ignore_viewport_pos,const bool immediate_flip_support)1813 void dml30_rq_dlg_get_dlg_reg(struct display_mode_lib *mode_lib,
1814 display_dlg_regs_st *dlg_regs,
1815 display_ttu_regs_st *ttu_regs,
1816 display_e2e_pipe_params_st *e2e_pipe_param,
1817 const unsigned int num_pipes,
1818 const unsigned int pipe_idx,
1819 const bool cstate_en,
1820 const bool pstate_en,
1821 const bool vm_en,
1822 const bool ignore_viewport_pos,
1823 const bool immediate_flip_support)
1824 {
1825 display_rq_params_st rq_param = { 0 };
1826 display_dlg_sys_params_st dlg_sys_param = { 0 };
1827
1828 // Get watermark and Tex.
1829 dlg_sys_param.t_urg_wm_us = get_wm_urgent(mode_lib, e2e_pipe_param, num_pipes);
1830 dlg_sys_param.deepsleep_dcfclk_mhz = get_clk_dcf_deepsleep(mode_lib,
1831 e2e_pipe_param,
1832 num_pipes);
1833 dlg_sys_param.t_extra_us = get_urgent_extra_latency(mode_lib, e2e_pipe_param, num_pipes);
1834 dlg_sys_param.mem_trip_us = get_wm_memory_trip(mode_lib, e2e_pipe_param, num_pipes);
1835 dlg_sys_param.t_mclk_wm_us = get_wm_dram_clock_change(mode_lib, e2e_pipe_param, num_pipes);
1836 dlg_sys_param.t_sr_wm_us = get_wm_stutter_enter_exit(mode_lib, e2e_pipe_param, num_pipes);
1837 dlg_sys_param.total_flip_bw = get_total_immediate_flip_bw(mode_lib,
1838 e2e_pipe_param,
1839 num_pipes);
1840 dlg_sys_param.total_flip_bytes = get_total_immediate_flip_bytes(mode_lib,
1841 e2e_pipe_param,
1842 num_pipes);
1843 dlg_sys_param.t_srx_delay_us = mode_lib->ip.dcfclk_cstate_latency
1844 / dlg_sys_param.deepsleep_dcfclk_mhz; // TODO: Deprecated
1845
1846 print__dlg_sys_params_st(mode_lib, dlg_sys_param);
1847
1848 // system parameter calculation done
1849
1850 dml_print("DML_DLG: Calculation for pipe[%d] start\n\n", pipe_idx);
1851 dml_rq_dlg_get_rq_params(mode_lib, &rq_param, e2e_pipe_param[pipe_idx].pipe);
1852 dml_rq_dlg_get_dlg_params(mode_lib,
1853 e2e_pipe_param,
1854 num_pipes,
1855 pipe_idx,
1856 dlg_regs,
1857 ttu_regs,
1858 rq_param.dlg,
1859 dlg_sys_param,
1860 cstate_en,
1861 pstate_en,
1862 vm_en,
1863 ignore_viewport_pos,
1864 immediate_flip_support);
1865 dml_print("DML_DLG: Calculation for pipe[%d] end\n", pipe_idx);
1866 }
1867
1868 #endif
1869