1 /*
2 * Copyright 2018 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 #include "../display_mode_lib.h"
27 #include "display_mode_vba_20.h"
28 #include "../dml_inline_defs.h"
29
30 /*
31 * NOTE:
32 * This file is gcc-parseable HW gospel, coming straight from HW engineers.
33 *
34 * It doesn't adhere to Linux kernel style and sometimes will do things in odd
35 * ways. Unless there is something clearly wrong with it the code should
36 * remain as-is as it provides us with a guarantee from HW that it is correct.
37 */
38
39 #define BPP_INVALID 0
40 #define BPP_BLENDED_PIPE 0xffffffff
41 #define DCN20_MAX_420_IMAGE_WIDTH 4096
42
43 static double adjust_ReturnBW(
44 struct display_mode_lib *mode_lib,
45 double ReturnBW,
46 bool DCCEnabledAnyPlane,
47 double ReturnBandwidthToDCN);
48 static unsigned int dscceComputeDelay(
49 unsigned int bpc,
50 double bpp,
51 unsigned int sliceWidth,
52 unsigned int numSlices,
53 enum output_format_class pixelFormat);
54 static unsigned int dscComputeDelay(enum output_format_class pixelFormat);
55 // Super monster function with some 45 argument
56 static bool CalculatePrefetchSchedule(
57 struct display_mode_lib *mode_lib,
58 double DPPCLK,
59 double DISPCLK,
60 double PixelClock,
61 double DCFCLKDeepSleep,
62 unsigned int DSCDelay,
63 unsigned int DPPPerPlane,
64 bool ScalerEnabled,
65 unsigned int NumberOfCursors,
66 double DPPCLKDelaySubtotal,
67 double DPPCLKDelaySCL,
68 double DPPCLKDelaySCLLBOnly,
69 double DPPCLKDelayCNVCFormater,
70 double DPPCLKDelayCNVCCursor,
71 double DISPCLKDelaySubtotal,
72 unsigned int ScalerRecoutWidth,
73 enum output_format_class OutputFormat,
74 unsigned int VBlank,
75 unsigned int HTotal,
76 unsigned int MaxInterDCNTileRepeaters,
77 unsigned int VStartup,
78 unsigned int PageTableLevels,
79 bool GPUVMEnable,
80 bool DynamicMetadataEnable,
81 unsigned int DynamicMetadataLinesBeforeActiveRequired,
82 unsigned int DynamicMetadataTransmittedBytes,
83 bool DCCEnable,
84 double UrgentLatencyPixelDataOnly,
85 double UrgentExtraLatency,
86 double TCalc,
87 unsigned int PDEAndMetaPTEBytesFrame,
88 unsigned int MetaRowByte,
89 unsigned int PixelPTEBytesPerRow,
90 double PrefetchSourceLinesY,
91 unsigned int SwathWidthY,
92 double BytePerPixelDETY,
93 double VInitPreFillY,
94 unsigned int MaxNumSwathY,
95 double PrefetchSourceLinesC,
96 double BytePerPixelDETC,
97 double VInitPreFillC,
98 unsigned int MaxNumSwathC,
99 unsigned int SwathHeightY,
100 unsigned int SwathHeightC,
101 double TWait,
102 bool XFCEnabled,
103 double XFCRemoteSurfaceFlipDelay,
104 bool InterlaceEnable,
105 bool ProgressiveToInterlaceUnitInOPP,
106 double *DSTXAfterScaler,
107 double *DSTYAfterScaler,
108 double *DestinationLinesForPrefetch,
109 double *PrefetchBandwidth,
110 double *DestinationLinesToRequestVMInVBlank,
111 double *DestinationLinesToRequestRowInVBlank,
112 double *VRatioPrefetchY,
113 double *VRatioPrefetchC,
114 double *RequiredPrefetchPixDataBW,
115 unsigned int *VStartupRequiredWhenNotEnoughTimeForDynamicMetadata,
116 double *Tno_bw,
117 unsigned int *VUpdateOffsetPix,
118 double *VUpdateWidthPix,
119 double *VReadyOffsetPix);
120 static double RoundToDFSGranularityUp(double Clock, double VCOSpeed);
121 static double RoundToDFSGranularityDown(double Clock, double VCOSpeed);
122 static double CalculatePrefetchSourceLines(
123 struct display_mode_lib *mode_lib,
124 double VRatio,
125 double vtaps,
126 bool Interlace,
127 bool ProgressiveToInterlaceUnitInOPP,
128 unsigned int SwathHeight,
129 unsigned int ViewportYStart,
130 double *VInitPreFill,
131 unsigned int *MaxNumSwath);
132 static unsigned int CalculateVMAndRowBytes(
133 struct display_mode_lib *mode_lib,
134 bool DCCEnable,
135 unsigned int BlockHeight256Bytes,
136 unsigned int BlockWidth256Bytes,
137 enum source_format_class SourcePixelFormat,
138 unsigned int SurfaceTiling,
139 unsigned int BytePerPixel,
140 enum scan_direction_class ScanDirection,
141 unsigned int ViewportWidth,
142 unsigned int ViewportHeight,
143 unsigned int SwathWidthY,
144 bool GPUVMEnable,
145 unsigned int VMMPageSize,
146 unsigned int PTEBufferSizeInRequestsLuma,
147 unsigned int PDEProcessingBufIn64KBReqs,
148 unsigned int Pitch,
149 unsigned int DCCMetaPitch,
150 unsigned int *MacroTileWidth,
151 unsigned int *MetaRowByte,
152 unsigned int *PixelPTEBytesPerRow,
153 bool *PTEBufferSizeNotExceeded,
154 unsigned int *dpte_row_height,
155 unsigned int *meta_row_height);
156 static double CalculateTWait(
157 unsigned int PrefetchMode,
158 double DRAMClockChangeLatency,
159 double UrgentLatencyPixelDataOnly,
160 double SREnterPlusExitTime);
161 static double CalculateRemoteSurfaceFlipDelay(
162 struct display_mode_lib *mode_lib,
163 double VRatio,
164 double SwathWidth,
165 double Bpp,
166 double LineTime,
167 double XFCTSlvVupdateOffset,
168 double XFCTSlvVupdateWidth,
169 double XFCTSlvVreadyOffset,
170 double XFCXBUFLatencyTolerance,
171 double XFCFillBWOverhead,
172 double XFCSlvChunkSize,
173 double XFCBusTransportTime,
174 double TCalc,
175 double TWait,
176 double *SrcActiveDrainRate,
177 double *TInitXFill,
178 double *TslvChk);
179 static void CalculateActiveRowBandwidth(
180 bool GPUVMEnable,
181 enum source_format_class SourcePixelFormat,
182 double VRatio,
183 bool DCCEnable,
184 double LineTime,
185 unsigned int MetaRowByteLuma,
186 unsigned int MetaRowByteChroma,
187 unsigned int meta_row_height_luma,
188 unsigned int meta_row_height_chroma,
189 unsigned int PixelPTEBytesPerRowLuma,
190 unsigned int PixelPTEBytesPerRowChroma,
191 unsigned int dpte_row_height_luma,
192 unsigned int dpte_row_height_chroma,
193 double *meta_row_bw,
194 double *dpte_row_bw,
195 double *qual_row_bw);
196 static void CalculateFlipSchedule(
197 struct display_mode_lib *mode_lib,
198 double UrgentExtraLatency,
199 double UrgentLatencyPixelDataOnly,
200 unsigned int GPUVMMaxPageTableLevels,
201 bool GPUVMEnable,
202 double BandwidthAvailableForImmediateFlip,
203 unsigned int TotImmediateFlipBytes,
204 enum source_format_class SourcePixelFormat,
205 unsigned int ImmediateFlipBytes,
206 double LineTime,
207 double VRatio,
208 double Tno_bw,
209 double PDEAndMetaPTEBytesFrame,
210 unsigned int MetaRowByte,
211 unsigned int PixelPTEBytesPerRow,
212 bool DCCEnable,
213 unsigned int dpte_row_height,
214 unsigned int meta_row_height,
215 double qual_row_bw,
216 double *DestinationLinesToRequestVMInImmediateFlip,
217 double *DestinationLinesToRequestRowInImmediateFlip,
218 double *final_flip_bw,
219 bool *ImmediateFlipSupportedForPipe);
220 static double CalculateWriteBackDelay(
221 enum source_format_class WritebackPixelFormat,
222 double WritebackHRatio,
223 double WritebackVRatio,
224 unsigned int WritebackLumaHTaps,
225 unsigned int WritebackLumaVTaps,
226 unsigned int WritebackChromaHTaps,
227 unsigned int WritebackChromaVTaps,
228 unsigned int WritebackDestinationWidth);
229
230 static void dml20_DisplayPipeConfiguration(struct display_mode_lib *mode_lib);
231 static void dml20_DISPCLKDPPCLKDCFCLKDeepSleepPrefetchParametersWatermarksAndPerformanceCalculation(
232 struct display_mode_lib *mode_lib);
233
dml20_recalculate(struct display_mode_lib * mode_lib)234 void dml20_recalculate(struct display_mode_lib *mode_lib)
235 {
236 ModeSupportAndSystemConfiguration(mode_lib);
237 mode_lib->vba.FabricAndDRAMBandwidth = dml_min(
238 mode_lib->vba.DRAMSpeed * mode_lib->vba.NumberOfChannels * mode_lib->vba.DRAMChannelWidth,
239 mode_lib->vba.FabricClock * mode_lib->vba.FabricDatapathToDCNDataReturn) / 1000.0;
240 PixelClockAdjustmentForProgressiveToInterlaceUnit(mode_lib);
241 dml20_DisplayPipeConfiguration(mode_lib);
242 dml20_DISPCLKDPPCLKDCFCLKDeepSleepPrefetchParametersWatermarksAndPerformanceCalculation(mode_lib);
243 }
244
adjust_ReturnBW(struct display_mode_lib * mode_lib,double ReturnBW,bool DCCEnabledAnyPlane,double ReturnBandwidthToDCN)245 static double adjust_ReturnBW(
246 struct display_mode_lib *mode_lib,
247 double ReturnBW,
248 bool DCCEnabledAnyPlane,
249 double ReturnBandwidthToDCN)
250 {
251 double CriticalCompression;
252
253 if (DCCEnabledAnyPlane
254 && ReturnBandwidthToDCN
255 > mode_lib->vba.DCFCLK * mode_lib->vba.ReturnBusWidth / 4.0)
256 ReturnBW =
257 dml_min(
258 ReturnBW,
259 ReturnBandwidthToDCN * 4
260 * (1.0
261 - mode_lib->vba.UrgentLatencyPixelDataOnly
262 / ((mode_lib->vba.ROBBufferSizeInKByte
263 - mode_lib->vba.PixelChunkSizeInKByte)
264 * 1024
265 / ReturnBandwidthToDCN
266 - mode_lib->vba.DCFCLK
267 * mode_lib->vba.ReturnBusWidth
268 / 4)
269 + mode_lib->vba.UrgentLatencyPixelDataOnly));
270
271 CriticalCompression = 2.0 * mode_lib->vba.ReturnBusWidth * mode_lib->vba.DCFCLK
272 * mode_lib->vba.UrgentLatencyPixelDataOnly
273 / (ReturnBandwidthToDCN * mode_lib->vba.UrgentLatencyPixelDataOnly
274 + (mode_lib->vba.ROBBufferSizeInKByte
275 - mode_lib->vba.PixelChunkSizeInKByte)
276 * 1024);
277
278 if (DCCEnabledAnyPlane && CriticalCompression > 1.0 && CriticalCompression < 4.0)
279 ReturnBW =
280 dml_min(
281 ReturnBW,
282 4.0 * ReturnBandwidthToDCN
283 * (mode_lib->vba.ROBBufferSizeInKByte
284 - mode_lib->vba.PixelChunkSizeInKByte)
285 * 1024
286 * mode_lib->vba.ReturnBusWidth
287 * mode_lib->vba.DCFCLK
288 * mode_lib->vba.UrgentLatencyPixelDataOnly
289 / dml_pow(
290 (ReturnBandwidthToDCN
291 * mode_lib->vba.UrgentLatencyPixelDataOnly
292 + (mode_lib->vba.ROBBufferSizeInKByte
293 - mode_lib->vba.PixelChunkSizeInKByte)
294 * 1024),
295 2));
296
297 return ReturnBW;
298 }
299
dscceComputeDelay(unsigned int bpc,double bpp,unsigned int sliceWidth,unsigned int numSlices,enum output_format_class pixelFormat)300 static unsigned int dscceComputeDelay(
301 unsigned int bpc,
302 double bpp,
303 unsigned int sliceWidth,
304 unsigned int numSlices,
305 enum output_format_class pixelFormat)
306 {
307 // valid bpc = source bits per component in the set of {8, 10, 12}
308 // valid bpp = increments of 1/16 of a bit
309 // min = 6/7/8 in N420/N422/444, respectively
310 // max = such that compression is 1:1
311 //valid sliceWidth = number of pixels per slice line, must be less than or equal to 5184/numSlices (or 4096/numSlices in 420 mode)
312 //valid numSlices = number of slices in the horiziontal direction per DSC engine in the set of {1, 2, 3, 4}
313 //valid pixelFormat = pixel/color format in the set of {:N444_RGB, :S422, :N422, :N420}
314
315 // fixed value
316 unsigned int rcModelSize = 8192;
317
318 // N422/N420 operate at 2 pixels per clock
319 unsigned int pixelsPerClock, lstall, D, initalXmitDelay, w, s, ix, wx, p, l0, a, ax, l,
320 Delay, pixels;
321
322 if (pixelFormat == dm_n422 || pixelFormat == dm_420)
323 pixelsPerClock = 2;
324 // #all other modes operate at 1 pixel per clock
325 else
326 pixelsPerClock = 1;
327
328 //initial transmit delay as per PPS
329 initalXmitDelay = dml_round(rcModelSize / 2.0 / bpp / pixelsPerClock);
330
331 //compute ssm delay
332 if (bpc == 8)
333 D = 81;
334 else if (bpc == 10)
335 D = 89;
336 else
337 D = 113;
338
339 //divide by pixel per cycle to compute slice width as seen by DSC
340 w = sliceWidth / pixelsPerClock;
341
342 //422 mode has an additional cycle of delay
343 if (pixelFormat == dm_s422)
344 s = 1;
345 else
346 s = 0;
347
348 //main calculation for the dscce
349 ix = initalXmitDelay + 45;
350 wx = (w + 2) / 3;
351 p = 3 * wx - w;
352 l0 = ix / w;
353 a = ix + p * l0;
354 ax = (a + 2) / 3 + D + 6 + 1;
355 l = (ax + wx - 1) / wx;
356 if ((ix % w) == 0 && p != 0)
357 lstall = 1;
358 else
359 lstall = 0;
360 Delay = l * wx * (numSlices - 1) + ax + s + lstall + 22;
361
362 //dsc processes 3 pixel containers per cycle and a container can contain 1 or 2 pixels
363 pixels = Delay * 3 * pixelsPerClock;
364 return pixels;
365 }
366
dscComputeDelay(enum output_format_class pixelFormat)367 static unsigned int dscComputeDelay(enum output_format_class pixelFormat)
368 {
369 unsigned int Delay = 0;
370
371 if (pixelFormat == dm_420) {
372 // sfr
373 Delay = Delay + 2;
374 // dsccif
375 Delay = Delay + 0;
376 // dscc - input deserializer
377 Delay = Delay + 3;
378 // dscc gets pixels every other cycle
379 Delay = Delay + 2;
380 // dscc - input cdc fifo
381 Delay = Delay + 12;
382 // dscc gets pixels every other cycle
383 Delay = Delay + 13;
384 // dscc - cdc uncertainty
385 Delay = Delay + 2;
386 // dscc - output cdc fifo
387 Delay = Delay + 7;
388 // dscc gets pixels every other cycle
389 Delay = Delay + 3;
390 // dscc - cdc uncertainty
391 Delay = Delay + 2;
392 // dscc - output serializer
393 Delay = Delay + 1;
394 // sft
395 Delay = Delay + 1;
396 } else if (pixelFormat == dm_n422) {
397 // sfr
398 Delay = Delay + 2;
399 // dsccif
400 Delay = Delay + 1;
401 // dscc - input deserializer
402 Delay = Delay + 5;
403 // dscc - input cdc fifo
404 Delay = Delay + 25;
405 // dscc - cdc uncertainty
406 Delay = Delay + 2;
407 // dscc - output cdc fifo
408 Delay = Delay + 10;
409 // dscc - cdc uncertainty
410 Delay = Delay + 2;
411 // dscc - output serializer
412 Delay = Delay + 1;
413 // sft
414 Delay = Delay + 1;
415 } else {
416 // sfr
417 Delay = Delay + 2;
418 // dsccif
419 Delay = Delay + 0;
420 // dscc - input deserializer
421 Delay = Delay + 3;
422 // dscc - input cdc fifo
423 Delay = Delay + 12;
424 // dscc - cdc uncertainty
425 Delay = Delay + 2;
426 // dscc - output cdc fifo
427 Delay = Delay + 7;
428 // dscc - output serializer
429 Delay = Delay + 1;
430 // dscc - cdc uncertainty
431 Delay = Delay + 2;
432 // sft
433 Delay = Delay + 1;
434 }
435
436 return Delay;
437 }
438
CalculatePrefetchSchedule(struct display_mode_lib * mode_lib,double DPPCLK,double DISPCLK,double PixelClock,double DCFCLKDeepSleep,unsigned int DSCDelay,unsigned int DPPPerPlane,bool ScalerEnabled,unsigned int NumberOfCursors,double DPPCLKDelaySubtotal,double DPPCLKDelaySCL,double DPPCLKDelaySCLLBOnly,double DPPCLKDelayCNVCFormater,double DPPCLKDelayCNVCCursor,double DISPCLKDelaySubtotal,unsigned int ScalerRecoutWidth,enum output_format_class OutputFormat,unsigned int VBlank,unsigned int HTotal,unsigned int MaxInterDCNTileRepeaters,unsigned int VStartup,unsigned int PageTableLevels,bool GPUVMEnable,bool DynamicMetadataEnable,unsigned int DynamicMetadataLinesBeforeActiveRequired,unsigned int DynamicMetadataTransmittedBytes,bool DCCEnable,double UrgentLatencyPixelDataOnly,double UrgentExtraLatency,double TCalc,unsigned int PDEAndMetaPTEBytesFrame,unsigned int MetaRowByte,unsigned int PixelPTEBytesPerRow,double PrefetchSourceLinesY,unsigned int SwathWidthY,double BytePerPixelDETY,double VInitPreFillY,unsigned int MaxNumSwathY,double PrefetchSourceLinesC,double BytePerPixelDETC,double VInitPreFillC,unsigned int MaxNumSwathC,unsigned int SwathHeightY,unsigned int SwathHeightC,double TWait,bool XFCEnabled,double XFCRemoteSurfaceFlipDelay,bool InterlaceEnable,bool ProgressiveToInterlaceUnitInOPP,double * DSTXAfterScaler,double * DSTYAfterScaler,double * DestinationLinesForPrefetch,double * PrefetchBandwidth,double * DestinationLinesToRequestVMInVBlank,double * DestinationLinesToRequestRowInVBlank,double * VRatioPrefetchY,double * VRatioPrefetchC,double * RequiredPrefetchPixDataBW,unsigned int * VStartupRequiredWhenNotEnoughTimeForDynamicMetadata,double * Tno_bw,unsigned int * VUpdateOffsetPix,double * VUpdateWidthPix,double * VReadyOffsetPix)439 static bool CalculatePrefetchSchedule(
440 struct display_mode_lib *mode_lib,
441 double DPPCLK,
442 double DISPCLK,
443 double PixelClock,
444 double DCFCLKDeepSleep,
445 unsigned int DSCDelay,
446 unsigned int DPPPerPlane,
447 bool ScalerEnabled,
448 unsigned int NumberOfCursors,
449 double DPPCLKDelaySubtotal,
450 double DPPCLKDelaySCL,
451 double DPPCLKDelaySCLLBOnly,
452 double DPPCLKDelayCNVCFormater,
453 double DPPCLKDelayCNVCCursor,
454 double DISPCLKDelaySubtotal,
455 unsigned int ScalerRecoutWidth,
456 enum output_format_class OutputFormat,
457 unsigned int VBlank,
458 unsigned int HTotal,
459 unsigned int MaxInterDCNTileRepeaters,
460 unsigned int VStartup,
461 unsigned int PageTableLevels,
462 bool GPUVMEnable,
463 bool DynamicMetadataEnable,
464 unsigned int DynamicMetadataLinesBeforeActiveRequired,
465 unsigned int DynamicMetadataTransmittedBytes,
466 bool DCCEnable,
467 double UrgentLatencyPixelDataOnly,
468 double UrgentExtraLatency,
469 double TCalc,
470 unsigned int PDEAndMetaPTEBytesFrame,
471 unsigned int MetaRowByte,
472 unsigned int PixelPTEBytesPerRow,
473 double PrefetchSourceLinesY,
474 unsigned int SwathWidthY,
475 double BytePerPixelDETY,
476 double VInitPreFillY,
477 unsigned int MaxNumSwathY,
478 double PrefetchSourceLinesC,
479 double BytePerPixelDETC,
480 double VInitPreFillC,
481 unsigned int MaxNumSwathC,
482 unsigned int SwathHeightY,
483 unsigned int SwathHeightC,
484 double TWait,
485 bool XFCEnabled,
486 double XFCRemoteSurfaceFlipDelay,
487 bool InterlaceEnable,
488 bool ProgressiveToInterlaceUnitInOPP,
489 double *DSTXAfterScaler,
490 double *DSTYAfterScaler,
491 double *DestinationLinesForPrefetch,
492 double *PrefetchBandwidth,
493 double *DestinationLinesToRequestVMInVBlank,
494 double *DestinationLinesToRequestRowInVBlank,
495 double *VRatioPrefetchY,
496 double *VRatioPrefetchC,
497 double *RequiredPrefetchPixDataBW,
498 unsigned int *VStartupRequiredWhenNotEnoughTimeForDynamicMetadata,
499 double *Tno_bw,
500 unsigned int *VUpdateOffsetPix,
501 double *VUpdateWidthPix,
502 double *VReadyOffsetPix)
503 {
504 bool MyError = false;
505 unsigned int DPPCycles, DISPCLKCycles;
506 double DSTTotalPixelsAfterScaler, TotalRepeaterDelayTime;
507 double Tdm, LineTime, Tsetup;
508 double dst_y_prefetch_equ;
509 double Tsw_oto;
510 double prefetch_bw_oto;
511 double Tvm_oto;
512 double Tr0_oto;
513 double Tpre_oto;
514 double dst_y_prefetch_oto;
515 double TimeForFetchingMetaPTE = 0;
516 double TimeForFetchingRowInVBlank = 0;
517 double LinesToRequestPrefetchPixelData = 0;
518
519 if (ScalerEnabled)
520 DPPCycles = DPPCLKDelaySubtotal + DPPCLKDelaySCL;
521 else
522 DPPCycles = DPPCLKDelaySubtotal + DPPCLKDelaySCLLBOnly;
523
524 DPPCycles = DPPCycles + DPPCLKDelayCNVCFormater + NumberOfCursors * DPPCLKDelayCNVCCursor;
525
526 DISPCLKCycles = DISPCLKDelaySubtotal;
527
528 if (DPPCLK == 0.0 || DISPCLK == 0.0)
529 return true;
530
531 *DSTXAfterScaler = DPPCycles * PixelClock / DPPCLK + DISPCLKCycles * PixelClock / DISPCLK
532 + DSCDelay;
533
534 if (DPPPerPlane > 1)
535 *DSTXAfterScaler = *DSTXAfterScaler + ScalerRecoutWidth;
536
537 if (OutputFormat == dm_420 || (InterlaceEnable && ProgressiveToInterlaceUnitInOPP))
538 *DSTYAfterScaler = 1;
539 else
540 *DSTYAfterScaler = 0;
541
542 DSTTotalPixelsAfterScaler = ((double) (*DSTYAfterScaler * HTotal)) + *DSTXAfterScaler;
543 *DSTYAfterScaler = dml_floor(DSTTotalPixelsAfterScaler / HTotal, 1);
544 *DSTXAfterScaler = DSTTotalPixelsAfterScaler - ((double) (*DSTYAfterScaler * HTotal));
545
546 *VUpdateOffsetPix = dml_ceil(HTotal / 4.0, 1);
547 TotalRepeaterDelayTime = MaxInterDCNTileRepeaters * (2.0 / DPPCLK + 3.0 / DISPCLK);
548 *VUpdateWidthPix = (14.0 / DCFCLKDeepSleep + 12.0 / DPPCLK + TotalRepeaterDelayTime)
549 * PixelClock;
550
551 *VReadyOffsetPix = dml_max(
552 150.0 / DPPCLK,
553 TotalRepeaterDelayTime + 20.0 / DCFCLKDeepSleep + 10.0 / DPPCLK)
554 * PixelClock;
555
556 Tsetup = (double) (*VUpdateOffsetPix + *VUpdateWidthPix + *VReadyOffsetPix) / PixelClock;
557
558 LineTime = (double) HTotal / PixelClock;
559
560 if (DynamicMetadataEnable) {
561 double Tdmbf, Tdmec, Tdmsks;
562
563 Tdm = dml_max(0.0, UrgentExtraLatency - TCalc);
564 Tdmbf = DynamicMetadataTransmittedBytes / 4.0 / DISPCLK;
565 Tdmec = LineTime;
566 if (DynamicMetadataLinesBeforeActiveRequired == 0)
567 Tdmsks = VBlank * LineTime / 2.0;
568 else
569 Tdmsks = DynamicMetadataLinesBeforeActiveRequired * LineTime;
570 if (InterlaceEnable && !ProgressiveToInterlaceUnitInOPP)
571 Tdmsks = Tdmsks / 2;
572 if (VStartup * LineTime
573 < Tsetup + TWait + UrgentExtraLatency + Tdmbf + Tdmec + Tdmsks) {
574 MyError = true;
575 *VStartupRequiredWhenNotEnoughTimeForDynamicMetadata = (Tsetup + TWait
576 + UrgentExtraLatency + Tdmbf + Tdmec + Tdmsks) / LineTime;
577 } else
578 *VStartupRequiredWhenNotEnoughTimeForDynamicMetadata = 0.0;
579 } else
580 Tdm = 0;
581
582 if (GPUVMEnable) {
583 if (PageTableLevels == 4)
584 *Tno_bw = UrgentExtraLatency + UrgentLatencyPixelDataOnly;
585 else if (PageTableLevels == 3)
586 *Tno_bw = UrgentExtraLatency;
587 else
588 *Tno_bw = 0;
589 } else if (DCCEnable)
590 *Tno_bw = LineTime;
591 else
592 *Tno_bw = LineTime / 4;
593
594 dst_y_prefetch_equ = VStartup - dml_max(TCalc + TWait, XFCRemoteSurfaceFlipDelay) / LineTime
595 - (Tsetup + Tdm) / LineTime
596 - (*DSTYAfterScaler + *DSTXAfterScaler / HTotal);
597
598 Tsw_oto = dml_max(PrefetchSourceLinesY, PrefetchSourceLinesC) * LineTime;
599
600 prefetch_bw_oto = (MetaRowByte + PixelPTEBytesPerRow
601 + PrefetchSourceLinesY * SwathWidthY * dml_ceil(BytePerPixelDETY, 1)
602 + PrefetchSourceLinesC * SwathWidthY / 2 * dml_ceil(BytePerPixelDETC, 2))
603 / Tsw_oto;
604
605 if (GPUVMEnable == true) {
606 Tvm_oto =
607 dml_max(
608 *Tno_bw + PDEAndMetaPTEBytesFrame / prefetch_bw_oto,
609 dml_max(
610 UrgentExtraLatency
611 + UrgentLatencyPixelDataOnly
612 * (PageTableLevels
613 - 1),
614 LineTime / 4.0));
615 } else
616 Tvm_oto = LineTime / 4.0;
617
618 if ((GPUVMEnable == true || DCCEnable == true)) {
619 Tr0_oto = dml_max(
620 (MetaRowByte + PixelPTEBytesPerRow) / prefetch_bw_oto,
621 dml_max(UrgentLatencyPixelDataOnly, dml_max(LineTime - Tvm_oto, LineTime / 4)));
622 } else
623 Tr0_oto = LineTime - Tvm_oto;
624
625 Tpre_oto = Tvm_oto + Tr0_oto + Tsw_oto;
626
627 dst_y_prefetch_oto = Tpre_oto / LineTime;
628
629 if (dst_y_prefetch_oto < dst_y_prefetch_equ)
630 *DestinationLinesForPrefetch = dst_y_prefetch_oto;
631 else
632 *DestinationLinesForPrefetch = dst_y_prefetch_equ;
633
634 *DestinationLinesForPrefetch = dml_floor(4.0 * (*DestinationLinesForPrefetch + 0.125), 1)
635 / 4;
636
637 dml_print("DML: VStartup: %d\n", VStartup);
638 dml_print("DML: TCalc: %f\n", TCalc);
639 dml_print("DML: TWait: %f\n", TWait);
640 dml_print("DML: XFCRemoteSurfaceFlipDelay: %f\n", XFCRemoteSurfaceFlipDelay);
641 dml_print("DML: LineTime: %f\n", LineTime);
642 dml_print("DML: Tsetup: %f\n", Tsetup);
643 dml_print("DML: Tdm: %f\n", Tdm);
644 dml_print("DML: DSTYAfterScaler: %f\n", *DSTYAfterScaler);
645 dml_print("DML: DSTXAfterScaler: %f\n", *DSTXAfterScaler);
646 dml_print("DML: HTotal: %d\n", HTotal);
647
648 *PrefetchBandwidth = 0;
649 *DestinationLinesToRequestVMInVBlank = 0;
650 *DestinationLinesToRequestRowInVBlank = 0;
651 *VRatioPrefetchY = 0;
652 *VRatioPrefetchC = 0;
653 *RequiredPrefetchPixDataBW = 0;
654 if (*DestinationLinesForPrefetch > 1) {
655 *PrefetchBandwidth = (PDEAndMetaPTEBytesFrame + 2 * MetaRowByte
656 + 2 * PixelPTEBytesPerRow
657 + PrefetchSourceLinesY * SwathWidthY * dml_ceil(BytePerPixelDETY, 1)
658 + PrefetchSourceLinesC * SwathWidthY / 2
659 * dml_ceil(BytePerPixelDETC, 2))
660 / (*DestinationLinesForPrefetch * LineTime - *Tno_bw);
661 if (GPUVMEnable) {
662 TimeForFetchingMetaPTE =
663 dml_max(
664 *Tno_bw
665 + (double) PDEAndMetaPTEBytesFrame
666 / *PrefetchBandwidth,
667 dml_max(
668 UrgentExtraLatency
669 + UrgentLatencyPixelDataOnly
670 * (PageTableLevels
671 - 1),
672 LineTime / 4));
673 } else {
674 if (NumberOfCursors > 0 || XFCEnabled)
675 TimeForFetchingMetaPTE = LineTime / 4;
676 else
677 TimeForFetchingMetaPTE = 0.0;
678 }
679
680 if ((GPUVMEnable == true || DCCEnable == true)) {
681 TimeForFetchingRowInVBlank =
682 dml_max(
683 (MetaRowByte + PixelPTEBytesPerRow)
684 / *PrefetchBandwidth,
685 dml_max(
686 UrgentLatencyPixelDataOnly,
687 dml_max(
688 LineTime
689 - TimeForFetchingMetaPTE,
690 LineTime
691 / 4.0)));
692 } else {
693 if (NumberOfCursors > 0 || XFCEnabled)
694 TimeForFetchingRowInVBlank = LineTime - TimeForFetchingMetaPTE;
695 else
696 TimeForFetchingRowInVBlank = 0.0;
697 }
698
699 *DestinationLinesToRequestVMInVBlank = dml_floor(
700 4.0 * (TimeForFetchingMetaPTE / LineTime + 0.125),
701 1) / 4.0;
702
703 *DestinationLinesToRequestRowInVBlank = dml_floor(
704 4.0 * (TimeForFetchingRowInVBlank / LineTime + 0.125),
705 1) / 4.0;
706
707 LinesToRequestPrefetchPixelData =
708 *DestinationLinesForPrefetch
709 - ((NumberOfCursors > 0 || GPUVMEnable
710 || DCCEnable) ?
711 (*DestinationLinesToRequestVMInVBlank
712 + *DestinationLinesToRequestRowInVBlank) :
713 0.0);
714
715 if (LinesToRequestPrefetchPixelData > 0) {
716
717 *VRatioPrefetchY = (double) PrefetchSourceLinesY
718 / LinesToRequestPrefetchPixelData;
719 *VRatioPrefetchY = dml_max(*VRatioPrefetchY, 1.0);
720 if ((SwathHeightY > 4) && (VInitPreFillY > 3)) {
721 if (LinesToRequestPrefetchPixelData > (VInitPreFillY - 3.0) / 2.0) {
722 *VRatioPrefetchY =
723 dml_max(
724 (double) PrefetchSourceLinesY
725 / LinesToRequestPrefetchPixelData,
726 (double) MaxNumSwathY
727 * SwathHeightY
728 / (LinesToRequestPrefetchPixelData
729 - (VInitPreFillY
730 - 3.0)
731 / 2.0));
732 *VRatioPrefetchY = dml_max(*VRatioPrefetchY, 1.0);
733 } else {
734 MyError = true;
735 *VRatioPrefetchY = 0;
736 }
737 }
738
739 *VRatioPrefetchC = (double) PrefetchSourceLinesC
740 / LinesToRequestPrefetchPixelData;
741 *VRatioPrefetchC = dml_max(*VRatioPrefetchC, 1.0);
742
743 if ((SwathHeightC > 4)) {
744 if (LinesToRequestPrefetchPixelData > (VInitPreFillC - 3.0) / 2.0) {
745 *VRatioPrefetchC =
746 dml_max(
747 *VRatioPrefetchC,
748 (double) MaxNumSwathC
749 * SwathHeightC
750 / (LinesToRequestPrefetchPixelData
751 - (VInitPreFillC
752 - 3.0)
753 / 2.0));
754 *VRatioPrefetchC = dml_max(*VRatioPrefetchC, 1.0);
755 } else {
756 MyError = true;
757 *VRatioPrefetchC = 0;
758 }
759 }
760
761 *RequiredPrefetchPixDataBW =
762 DPPPerPlane
763 * ((double) PrefetchSourceLinesY
764 / LinesToRequestPrefetchPixelData
765 * dml_ceil(
766 BytePerPixelDETY,
767 1)
768 + (double) PrefetchSourceLinesC
769 / LinesToRequestPrefetchPixelData
770 * dml_ceil(
771 BytePerPixelDETC,
772 2)
773 / 2)
774 * SwathWidthY / LineTime;
775 } else {
776 MyError = true;
777 *VRatioPrefetchY = 0;
778 *VRatioPrefetchC = 0;
779 *RequiredPrefetchPixDataBW = 0;
780 }
781
782 } else {
783 MyError = true;
784 }
785
786 if (MyError) {
787 *PrefetchBandwidth = 0;
788 TimeForFetchingMetaPTE = 0;
789 TimeForFetchingRowInVBlank = 0;
790 *DestinationLinesToRequestVMInVBlank = 0;
791 *DestinationLinesToRequestRowInVBlank = 0;
792 *DestinationLinesForPrefetch = 0;
793 LinesToRequestPrefetchPixelData = 0;
794 *VRatioPrefetchY = 0;
795 *VRatioPrefetchC = 0;
796 *RequiredPrefetchPixDataBW = 0;
797 }
798
799 return MyError;
800 }
801
RoundToDFSGranularityUp(double Clock,double VCOSpeed)802 static double RoundToDFSGranularityUp(double Clock, double VCOSpeed)
803 {
804 return VCOSpeed * 4 / dml_floor(VCOSpeed * 4 / Clock, 1);
805 }
806
RoundToDFSGranularityDown(double Clock,double VCOSpeed)807 static double RoundToDFSGranularityDown(double Clock, double VCOSpeed)
808 {
809 return VCOSpeed * 4 / dml_ceil(VCOSpeed * 4 / Clock, 1);
810 }
811
CalculatePrefetchSourceLines(struct display_mode_lib * mode_lib,double VRatio,double vtaps,bool Interlace,bool ProgressiveToInterlaceUnitInOPP,unsigned int SwathHeight,unsigned int ViewportYStart,double * VInitPreFill,unsigned int * MaxNumSwath)812 static double CalculatePrefetchSourceLines(
813 struct display_mode_lib *mode_lib,
814 double VRatio,
815 double vtaps,
816 bool Interlace,
817 bool ProgressiveToInterlaceUnitInOPP,
818 unsigned int SwathHeight,
819 unsigned int ViewportYStart,
820 double *VInitPreFill,
821 unsigned int *MaxNumSwath)
822 {
823 unsigned int MaxPartialSwath;
824
825 if (ProgressiveToInterlaceUnitInOPP)
826 *VInitPreFill = dml_floor((VRatio + vtaps + 1) / 2.0, 1);
827 else
828 *VInitPreFill = dml_floor((VRatio + vtaps + 1 + Interlace * 0.5 * VRatio) / 2.0, 1);
829
830 if (!mode_lib->vba.IgnoreViewportPositioning) {
831
832 *MaxNumSwath = dml_ceil((*VInitPreFill - 1.0) / SwathHeight, 1) + 1.0;
833
834 if (*VInitPreFill > 1.0)
835 MaxPartialSwath = (unsigned int) (*VInitPreFill - 2) % SwathHeight;
836 else
837 MaxPartialSwath = (unsigned int) (*VInitPreFill + SwathHeight - 2)
838 % SwathHeight;
839 MaxPartialSwath = dml_max(1U, MaxPartialSwath);
840
841 } else {
842
843 if (ViewportYStart != 0)
844 dml_print(
845 "WARNING DML: using viewport y position of 0 even though actual viewport y position is non-zero in prefetch source lines calculation\n");
846
847 *MaxNumSwath = dml_ceil(*VInitPreFill / SwathHeight, 1);
848
849 if (*VInitPreFill > 1.0)
850 MaxPartialSwath = (unsigned int) (*VInitPreFill - 1) % SwathHeight;
851 else
852 MaxPartialSwath = (unsigned int) (*VInitPreFill + SwathHeight - 1)
853 % SwathHeight;
854 }
855
856 return *MaxNumSwath * SwathHeight + MaxPartialSwath;
857 }
858
CalculateVMAndRowBytes(struct display_mode_lib * mode_lib,bool DCCEnable,unsigned int BlockHeight256Bytes,unsigned int BlockWidth256Bytes,enum source_format_class SourcePixelFormat,unsigned int SurfaceTiling,unsigned int BytePerPixel,enum scan_direction_class ScanDirection,unsigned int ViewportWidth,unsigned int ViewportHeight,unsigned int SwathWidth,bool GPUVMEnable,unsigned int VMMPageSize,unsigned int PTEBufferSizeInRequestsLuma,unsigned int PDEProcessingBufIn64KBReqs,unsigned int Pitch,unsigned int DCCMetaPitch,unsigned int * MacroTileWidth,unsigned int * MetaRowByte,unsigned int * PixelPTEBytesPerRow,bool * PTEBufferSizeNotExceeded,unsigned int * dpte_row_height,unsigned int * meta_row_height)859 static unsigned int CalculateVMAndRowBytes(
860 struct display_mode_lib *mode_lib,
861 bool DCCEnable,
862 unsigned int BlockHeight256Bytes,
863 unsigned int BlockWidth256Bytes,
864 enum source_format_class SourcePixelFormat,
865 unsigned int SurfaceTiling,
866 unsigned int BytePerPixel,
867 enum scan_direction_class ScanDirection,
868 unsigned int ViewportWidth,
869 unsigned int ViewportHeight,
870 unsigned int SwathWidth,
871 bool GPUVMEnable,
872 unsigned int VMMPageSize,
873 unsigned int PTEBufferSizeInRequestsLuma,
874 unsigned int PDEProcessingBufIn64KBReqs,
875 unsigned int Pitch,
876 unsigned int DCCMetaPitch,
877 unsigned int *MacroTileWidth,
878 unsigned int *MetaRowByte,
879 unsigned int *PixelPTEBytesPerRow,
880 bool *PTEBufferSizeNotExceeded,
881 unsigned int *dpte_row_height,
882 unsigned int *meta_row_height)
883 {
884 unsigned int MetaRequestHeight;
885 unsigned int MetaRequestWidth;
886 unsigned int MetaSurfWidth;
887 unsigned int MetaSurfHeight;
888 unsigned int MPDEBytesFrame;
889 unsigned int MetaPTEBytesFrame;
890 unsigned int DCCMetaSurfaceBytes;
891
892 unsigned int MacroTileSizeBytes;
893 unsigned int MacroTileHeight;
894 unsigned int DPDE0BytesFrame;
895 unsigned int ExtraDPDEBytesFrame;
896 unsigned int PDEAndMetaPTEBytesFrame;
897
898 if (DCCEnable == true) {
899 MetaRequestHeight = 8 * BlockHeight256Bytes;
900 MetaRequestWidth = 8 * BlockWidth256Bytes;
901 if (ScanDirection == dm_horz) {
902 *meta_row_height = MetaRequestHeight;
903 MetaSurfWidth = dml_ceil((double) SwathWidth - 1, MetaRequestWidth)
904 + MetaRequestWidth;
905 *MetaRowByte = MetaSurfWidth * MetaRequestHeight * BytePerPixel / 256.0;
906 } else {
907 *meta_row_height = MetaRequestWidth;
908 MetaSurfHeight = dml_ceil((double) SwathWidth - 1, MetaRequestHeight)
909 + MetaRequestHeight;
910 *MetaRowByte = MetaSurfHeight * MetaRequestWidth * BytePerPixel / 256.0;
911 }
912 if (ScanDirection == dm_horz) {
913 DCCMetaSurfaceBytes = DCCMetaPitch
914 * (dml_ceil(ViewportHeight - 1, 64 * BlockHeight256Bytes)
915 + 64 * BlockHeight256Bytes) * BytePerPixel
916 / 256;
917 } else {
918 DCCMetaSurfaceBytes = DCCMetaPitch
919 * (dml_ceil(
920 (double) ViewportHeight - 1,
921 64 * BlockHeight256Bytes)
922 + 64 * BlockHeight256Bytes) * BytePerPixel
923 / 256;
924 }
925 if (GPUVMEnable == true) {
926 MetaPTEBytesFrame = (dml_ceil(
927 (double) (DCCMetaSurfaceBytes - VMMPageSize)
928 / (8 * VMMPageSize),
929 1) + 1) * 64;
930 MPDEBytesFrame = 128 * (mode_lib->vba.GPUVMMaxPageTableLevels - 1);
931 } else {
932 MetaPTEBytesFrame = 0;
933 MPDEBytesFrame = 0;
934 }
935 } else {
936 MetaPTEBytesFrame = 0;
937 MPDEBytesFrame = 0;
938 *MetaRowByte = 0;
939 }
940
941 if (SurfaceTiling == dm_sw_linear || SurfaceTiling == dm_sw_gfx7_2d_thin_gl || SurfaceTiling == dm_sw_gfx7_2d_thin_l_vp) {
942 MacroTileSizeBytes = 256;
943 MacroTileHeight = BlockHeight256Bytes;
944 } else if (SurfaceTiling == dm_sw_4kb_s || SurfaceTiling == dm_sw_4kb_s_x
945 || SurfaceTiling == dm_sw_4kb_d || SurfaceTiling == dm_sw_4kb_d_x) {
946 MacroTileSizeBytes = 4096;
947 MacroTileHeight = 4 * BlockHeight256Bytes;
948 } else if (SurfaceTiling == dm_sw_64kb_s || SurfaceTiling == dm_sw_64kb_s_t
949 || SurfaceTiling == dm_sw_64kb_s_x || SurfaceTiling == dm_sw_64kb_d
950 || SurfaceTiling == dm_sw_64kb_d_t || SurfaceTiling == dm_sw_64kb_d_x
951 || SurfaceTiling == dm_sw_64kb_r_x) {
952 MacroTileSizeBytes = 65536;
953 MacroTileHeight = 16 * BlockHeight256Bytes;
954 } else {
955 MacroTileSizeBytes = 262144;
956 MacroTileHeight = 32 * BlockHeight256Bytes;
957 }
958 *MacroTileWidth = MacroTileSizeBytes / BytePerPixel / MacroTileHeight;
959
960 if (GPUVMEnable == true && mode_lib->vba.GPUVMMaxPageTableLevels > 1) {
961 if (ScanDirection == dm_horz) {
962 DPDE0BytesFrame =
963 64
964 * (dml_ceil(
965 ((Pitch
966 * (dml_ceil(
967 ViewportHeight
968 - 1,
969 MacroTileHeight)
970 + MacroTileHeight)
971 * BytePerPixel)
972 - MacroTileSizeBytes)
973 / (8
974 * 2097152),
975 1) + 1);
976 } else {
977 DPDE0BytesFrame =
978 64
979 * (dml_ceil(
980 ((Pitch
981 * (dml_ceil(
982 (double) SwathWidth
983 - 1,
984 MacroTileHeight)
985 + MacroTileHeight)
986 * BytePerPixel)
987 - MacroTileSizeBytes)
988 / (8
989 * 2097152),
990 1) + 1);
991 }
992 ExtraDPDEBytesFrame = 128 * (mode_lib->vba.GPUVMMaxPageTableLevels - 2);
993 } else {
994 DPDE0BytesFrame = 0;
995 ExtraDPDEBytesFrame = 0;
996 }
997
998 PDEAndMetaPTEBytesFrame = MetaPTEBytesFrame + MPDEBytesFrame + DPDE0BytesFrame
999 + ExtraDPDEBytesFrame;
1000
1001 if (GPUVMEnable == true) {
1002 unsigned int PTERequestSize;
1003 unsigned int PixelPTEReqHeight;
1004 unsigned int PixelPTEReqWidth;
1005 double FractionOfPTEReturnDrop;
1006 unsigned int EffectivePDEProcessingBufIn64KBReqs;
1007
1008 if (SurfaceTiling == dm_sw_linear) {
1009 PixelPTEReqHeight = 1;
1010 PixelPTEReqWidth = 8.0 * VMMPageSize / BytePerPixel;
1011 PTERequestSize = 64;
1012 FractionOfPTEReturnDrop = 0;
1013 } else if (MacroTileSizeBytes == 4096) {
1014 PixelPTEReqHeight = MacroTileHeight;
1015 PixelPTEReqWidth = 8 * *MacroTileWidth;
1016 PTERequestSize = 64;
1017 if (ScanDirection == dm_horz)
1018 FractionOfPTEReturnDrop = 0;
1019 else
1020 FractionOfPTEReturnDrop = 7 / 8;
1021 } else if (VMMPageSize == 4096 && MacroTileSizeBytes > 4096) {
1022 PixelPTEReqHeight = 16 * BlockHeight256Bytes;
1023 PixelPTEReqWidth = 16 * BlockWidth256Bytes;
1024 PTERequestSize = 128;
1025 FractionOfPTEReturnDrop = 0;
1026 } else {
1027 PixelPTEReqHeight = MacroTileHeight;
1028 PixelPTEReqWidth = 8 * *MacroTileWidth;
1029 PTERequestSize = 64;
1030 FractionOfPTEReturnDrop = 0;
1031 }
1032
1033 if (SourcePixelFormat == dm_420_8 || SourcePixelFormat == dm_420_10)
1034 EffectivePDEProcessingBufIn64KBReqs = PDEProcessingBufIn64KBReqs / 2;
1035 else
1036 EffectivePDEProcessingBufIn64KBReqs = PDEProcessingBufIn64KBReqs;
1037
1038 if (SurfaceTiling == dm_sw_linear) {
1039 *dpte_row_height =
1040 dml_min(
1041 128,
1042 1
1043 << (unsigned int) dml_floor(
1044 dml_log2(
1045 dml_min(
1046 (double) PTEBufferSizeInRequestsLuma
1047 * PixelPTEReqWidth,
1048 EffectivePDEProcessingBufIn64KBReqs
1049 * 65536.0
1050 / BytePerPixel)
1051 / Pitch),
1052 1));
1053 *PixelPTEBytesPerRow = PTERequestSize
1054 * (dml_ceil(
1055 (double) (Pitch * *dpte_row_height - 1)
1056 / PixelPTEReqWidth,
1057 1) + 1);
1058 } else if (ScanDirection == dm_horz) {
1059 *dpte_row_height = PixelPTEReqHeight;
1060 *PixelPTEBytesPerRow = PTERequestSize
1061 * (dml_ceil(((double) SwathWidth - 1) / PixelPTEReqWidth, 1)
1062 + 1);
1063 } else {
1064 *dpte_row_height = dml_min(PixelPTEReqWidth, *MacroTileWidth);
1065 *PixelPTEBytesPerRow = PTERequestSize
1066 * (dml_ceil(
1067 ((double) SwathWidth - 1)
1068 / PixelPTEReqHeight,
1069 1) + 1);
1070 }
1071 if (*PixelPTEBytesPerRow * (1 - FractionOfPTEReturnDrop)
1072 <= 64 * PTEBufferSizeInRequestsLuma) {
1073 *PTEBufferSizeNotExceeded = true;
1074 } else {
1075 *PTEBufferSizeNotExceeded = false;
1076 }
1077 } else {
1078 *PixelPTEBytesPerRow = 0;
1079 *PTEBufferSizeNotExceeded = true;
1080 }
1081
1082 return PDEAndMetaPTEBytesFrame;
1083 }
1084
dml20_DISPCLKDPPCLKDCFCLKDeepSleepPrefetchParametersWatermarksAndPerformanceCalculation(struct display_mode_lib * mode_lib)1085 static void dml20_DISPCLKDPPCLKDCFCLKDeepSleepPrefetchParametersWatermarksAndPerformanceCalculation(
1086 struct display_mode_lib *mode_lib)
1087 {
1088 unsigned int j, k;
1089
1090 mode_lib->vba.WritebackDISPCLK = 0.0;
1091 mode_lib->vba.DISPCLKWithRamping = 0;
1092 mode_lib->vba.DISPCLKWithoutRamping = 0;
1093 mode_lib->vba.GlobalDPPCLK = 0.0;
1094
1095 // dml_ml->vba.DISPCLK and dml_ml->vba.DPPCLK Calculation
1096 //
1097 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1098 if (mode_lib->vba.WritebackEnable[k]) {
1099 mode_lib->vba.WritebackDISPCLK =
1100 dml_max(
1101 mode_lib->vba.WritebackDISPCLK,
1102 CalculateWriteBackDISPCLK(
1103 mode_lib->vba.WritebackPixelFormat[k],
1104 mode_lib->vba.PixelClock[k],
1105 mode_lib->vba.WritebackHRatio[k],
1106 mode_lib->vba.WritebackVRatio[k],
1107 mode_lib->vba.WritebackLumaHTaps[k],
1108 mode_lib->vba.WritebackLumaVTaps[k],
1109 mode_lib->vba.WritebackChromaHTaps[k],
1110 mode_lib->vba.WritebackChromaVTaps[k],
1111 mode_lib->vba.WritebackDestinationWidth[k],
1112 mode_lib->vba.HTotal[k],
1113 mode_lib->vba.WritebackChromaLineBufferWidth));
1114 }
1115 }
1116
1117 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1118 if (mode_lib->vba.HRatio[k] > 1) {
1119 mode_lib->vba.PSCL_THROUGHPUT_LUMA[k] = dml_min(
1120 mode_lib->vba.MaxDCHUBToPSCLThroughput,
1121 mode_lib->vba.MaxPSCLToLBThroughput
1122 * mode_lib->vba.HRatio[k]
1123 / dml_ceil(
1124 mode_lib->vba.htaps[k]
1125 / 6.0,
1126 1));
1127 } else {
1128 mode_lib->vba.PSCL_THROUGHPUT_LUMA[k] = dml_min(
1129 mode_lib->vba.MaxDCHUBToPSCLThroughput,
1130 mode_lib->vba.MaxPSCLToLBThroughput);
1131 }
1132
1133 mode_lib->vba.DPPCLKUsingSingleDPPLuma =
1134 mode_lib->vba.PixelClock[k]
1135 * dml_max(
1136 mode_lib->vba.vtaps[k] / 6.0
1137 * dml_min(
1138 1.0,
1139 mode_lib->vba.HRatio[k]),
1140 dml_max(
1141 mode_lib->vba.HRatio[k]
1142 * mode_lib->vba.VRatio[k]
1143 / mode_lib->vba.PSCL_THROUGHPUT_LUMA[k],
1144 1.0));
1145
1146 if ((mode_lib->vba.htaps[k] > 6 || mode_lib->vba.vtaps[k] > 6)
1147 && mode_lib->vba.DPPCLKUsingSingleDPPLuma
1148 < 2 * mode_lib->vba.PixelClock[k]) {
1149 mode_lib->vba.DPPCLKUsingSingleDPPLuma = 2 * mode_lib->vba.PixelClock[k];
1150 }
1151
1152 if ((mode_lib->vba.SourcePixelFormat[k] != dm_420_8
1153 && mode_lib->vba.SourcePixelFormat[k] != dm_420_10)) {
1154 mode_lib->vba.PSCL_THROUGHPUT_CHROMA[k] = 0.0;
1155 mode_lib->vba.DPPCLKUsingSingleDPP[k] =
1156 mode_lib->vba.DPPCLKUsingSingleDPPLuma;
1157 } else {
1158 if (mode_lib->vba.HRatio[k] > 1) {
1159 mode_lib->vba.PSCL_THROUGHPUT_CHROMA[k] =
1160 dml_min(
1161 mode_lib->vba.MaxDCHUBToPSCLThroughput,
1162 mode_lib->vba.MaxPSCLToLBThroughput
1163 * mode_lib->vba.HRatio[k]
1164 / 2
1165 / dml_ceil(
1166 mode_lib->vba.HTAPsChroma[k]
1167 / 6.0,
1168 1.0));
1169 } else {
1170 mode_lib->vba.PSCL_THROUGHPUT_CHROMA[k] = dml_min(
1171 mode_lib->vba.MaxDCHUBToPSCLThroughput,
1172 mode_lib->vba.MaxPSCLToLBThroughput);
1173 }
1174 mode_lib->vba.DPPCLKUsingSingleDPPChroma =
1175 mode_lib->vba.PixelClock[k]
1176 * dml_max(
1177 mode_lib->vba.VTAPsChroma[k]
1178 / 6.0
1179 * dml_min(
1180 1.0,
1181 mode_lib->vba.HRatio[k]
1182 / 2),
1183 dml_max(
1184 mode_lib->vba.HRatio[k]
1185 * mode_lib->vba.VRatio[k]
1186 / 4
1187 / mode_lib->vba.PSCL_THROUGHPUT_CHROMA[k],
1188 1.0));
1189
1190 if ((mode_lib->vba.HTAPsChroma[k] > 6 || mode_lib->vba.VTAPsChroma[k] > 6)
1191 && mode_lib->vba.DPPCLKUsingSingleDPPChroma
1192 < 2 * mode_lib->vba.PixelClock[k]) {
1193 mode_lib->vba.DPPCLKUsingSingleDPPChroma = 2
1194 * mode_lib->vba.PixelClock[k];
1195 }
1196
1197 mode_lib->vba.DPPCLKUsingSingleDPP[k] = dml_max(
1198 mode_lib->vba.DPPCLKUsingSingleDPPLuma,
1199 mode_lib->vba.DPPCLKUsingSingleDPPChroma);
1200 }
1201 }
1202
1203 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1204 if (mode_lib->vba.BlendingAndTiming[k] != k)
1205 continue;
1206 if (mode_lib->vba.ODMCombineEnabled[k]) {
1207 mode_lib->vba.DISPCLKWithRamping =
1208 dml_max(
1209 mode_lib->vba.DISPCLKWithRamping,
1210 mode_lib->vba.PixelClock[k] / 2
1211 * (1
1212 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading
1213 / 100)
1214 * (1
1215 + mode_lib->vba.DISPCLKRampingMargin
1216 / 100));
1217 mode_lib->vba.DISPCLKWithoutRamping =
1218 dml_max(
1219 mode_lib->vba.DISPCLKWithoutRamping,
1220 mode_lib->vba.PixelClock[k] / 2
1221 * (1
1222 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading
1223 / 100));
1224 } else if (!mode_lib->vba.ODMCombineEnabled[k]) {
1225 mode_lib->vba.DISPCLKWithRamping =
1226 dml_max(
1227 mode_lib->vba.DISPCLKWithRamping,
1228 mode_lib->vba.PixelClock[k]
1229 * (1
1230 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading
1231 / 100)
1232 * (1
1233 + mode_lib->vba.DISPCLKRampingMargin
1234 / 100));
1235 mode_lib->vba.DISPCLKWithoutRamping =
1236 dml_max(
1237 mode_lib->vba.DISPCLKWithoutRamping,
1238 mode_lib->vba.PixelClock[k]
1239 * (1
1240 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading
1241 / 100));
1242 }
1243 }
1244
1245 mode_lib->vba.DISPCLKWithRamping = dml_max(
1246 mode_lib->vba.DISPCLKWithRamping,
1247 mode_lib->vba.WritebackDISPCLK);
1248 mode_lib->vba.DISPCLKWithoutRamping = dml_max(
1249 mode_lib->vba.DISPCLKWithoutRamping,
1250 mode_lib->vba.WritebackDISPCLK);
1251
1252 ASSERT(mode_lib->vba.DISPCLKDPPCLKVCOSpeed != 0);
1253 mode_lib->vba.DISPCLKWithRampingRoundedToDFSGranularity = RoundToDFSGranularityUp(
1254 mode_lib->vba.DISPCLKWithRamping,
1255 mode_lib->vba.DISPCLKDPPCLKVCOSpeed);
1256 mode_lib->vba.DISPCLKWithoutRampingRoundedToDFSGranularity = RoundToDFSGranularityUp(
1257 mode_lib->vba.DISPCLKWithoutRamping,
1258 mode_lib->vba.DISPCLKDPPCLKVCOSpeed);
1259 mode_lib->vba.MaxDispclkRoundedToDFSGranularity = RoundToDFSGranularityDown(
1260 mode_lib->vba.soc.clock_limits[mode_lib->vba.soc.num_states].dispclk_mhz,
1261 mode_lib->vba.DISPCLKDPPCLKVCOSpeed);
1262 if (mode_lib->vba.DISPCLKWithoutRampingRoundedToDFSGranularity
1263 > mode_lib->vba.MaxDispclkRoundedToDFSGranularity) {
1264 mode_lib->vba.DISPCLK_calculated =
1265 mode_lib->vba.DISPCLKWithoutRampingRoundedToDFSGranularity;
1266 } else if (mode_lib->vba.DISPCLKWithRampingRoundedToDFSGranularity
1267 > mode_lib->vba.MaxDispclkRoundedToDFSGranularity) {
1268 mode_lib->vba.DISPCLK_calculated = mode_lib->vba.MaxDispclkRoundedToDFSGranularity;
1269 } else {
1270 mode_lib->vba.DISPCLK_calculated =
1271 mode_lib->vba.DISPCLKWithRampingRoundedToDFSGranularity;
1272 }
1273 DTRACE(" dispclk_mhz (calculated) = %f", mode_lib->vba.DISPCLK_calculated);
1274
1275 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1276 if (mode_lib->vba.DPPPerPlane[k] == 0) {
1277 mode_lib->vba.DPPCLK_calculated[k] = 0;
1278 } else {
1279 mode_lib->vba.DPPCLK_calculated[k] = mode_lib->vba.DPPCLKUsingSingleDPP[k]
1280 / mode_lib->vba.DPPPerPlane[k]
1281 * (1 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100);
1282 }
1283 mode_lib->vba.GlobalDPPCLK = dml_max(
1284 mode_lib->vba.GlobalDPPCLK,
1285 mode_lib->vba.DPPCLK_calculated[k]);
1286 }
1287 mode_lib->vba.GlobalDPPCLK = RoundToDFSGranularityUp(
1288 mode_lib->vba.GlobalDPPCLK,
1289 mode_lib->vba.DISPCLKDPPCLKVCOSpeed);
1290 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1291 mode_lib->vba.DPPCLK_calculated[k] = mode_lib->vba.GlobalDPPCLK / 255
1292 * dml_ceil(
1293 mode_lib->vba.DPPCLK_calculated[k] * 255
1294 / mode_lib->vba.GlobalDPPCLK,
1295 1);
1296 DTRACE(" dppclk_mhz[%i] (calculated) = %f", k, mode_lib->vba.DPPCLK_calculated[k]);
1297 }
1298
1299 // Urgent Watermark
1300 mode_lib->vba.DCCEnabledAnyPlane = false;
1301 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k)
1302 if (mode_lib->vba.DCCEnable[k])
1303 mode_lib->vba.DCCEnabledAnyPlane = true;
1304
1305 mode_lib->vba.ReturnBandwidthToDCN = dml_min(
1306 mode_lib->vba.ReturnBusWidth * mode_lib->vba.DCFCLK,
1307 mode_lib->vba.FabricAndDRAMBandwidth * 1000)
1308 * mode_lib->vba.PercentOfIdealDRAMFabricAndSDPPortBWReceivedAfterUrgLatencyPixelDataOnly / 100;
1309
1310 mode_lib->vba.ReturnBW = mode_lib->vba.ReturnBandwidthToDCN;
1311 mode_lib->vba.ReturnBW = adjust_ReturnBW(
1312 mode_lib,
1313 mode_lib->vba.ReturnBW,
1314 mode_lib->vba.DCCEnabledAnyPlane,
1315 mode_lib->vba.ReturnBandwidthToDCN);
1316
1317 // Let's do this calculation again??
1318 mode_lib->vba.ReturnBandwidthToDCN = dml_min(
1319 mode_lib->vba.ReturnBusWidth * mode_lib->vba.DCFCLK,
1320 mode_lib->vba.FabricAndDRAMBandwidth * 1000);
1321 mode_lib->vba.ReturnBW = adjust_ReturnBW(
1322 mode_lib,
1323 mode_lib->vba.ReturnBW,
1324 mode_lib->vba.DCCEnabledAnyPlane,
1325 mode_lib->vba.ReturnBandwidthToDCN);
1326
1327 DTRACE(" dcfclk_mhz = %f", mode_lib->vba.DCFCLK);
1328 DTRACE(" return_bw_to_dcn = %f", mode_lib->vba.ReturnBandwidthToDCN);
1329 DTRACE(" return_bus_bw = %f", mode_lib->vba.ReturnBW);
1330
1331 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1332 bool MainPlaneDoesODMCombine = false;
1333
1334 if (mode_lib->vba.SourceScan[k] == dm_horz)
1335 mode_lib->vba.SwathWidthSingleDPPY[k] = mode_lib->vba.ViewportWidth[k];
1336 else
1337 mode_lib->vba.SwathWidthSingleDPPY[k] = mode_lib->vba.ViewportHeight[k];
1338
1339 if (mode_lib->vba.ODMCombineEnabled[k] == dm_odm_combine_mode_2to1)
1340 MainPlaneDoesODMCombine = true;
1341 for (j = 0; j < mode_lib->vba.NumberOfActivePlanes; ++j)
1342 if (mode_lib->vba.BlendingAndTiming[k] == j
1343 && mode_lib->vba.ODMCombineEnabled[k] == dm_odm_combine_mode_2to1)
1344 MainPlaneDoesODMCombine = true;
1345
1346 if (MainPlaneDoesODMCombine == true)
1347 mode_lib->vba.SwathWidthY[k] = dml_min(
1348 (double) mode_lib->vba.SwathWidthSingleDPPY[k],
1349 dml_round(
1350 mode_lib->vba.HActive[k] / 2.0
1351 * mode_lib->vba.HRatio[k]));
1352 else {
1353 if (mode_lib->vba.DPPPerPlane[k] == 0) {
1354 mode_lib->vba.SwathWidthY[k] = 0;
1355 } else {
1356 mode_lib->vba.SwathWidthY[k] = mode_lib->vba.SwathWidthSingleDPPY[k]
1357 / mode_lib->vba.DPPPerPlane[k];
1358 }
1359 }
1360 }
1361
1362 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1363 if (mode_lib->vba.SourcePixelFormat[k] == dm_444_64) {
1364 mode_lib->vba.BytePerPixelDETY[k] = 8;
1365 mode_lib->vba.BytePerPixelDETC[k] = 0;
1366 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_32) {
1367 mode_lib->vba.BytePerPixelDETY[k] = 4;
1368 mode_lib->vba.BytePerPixelDETC[k] = 0;
1369 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_16) {
1370 mode_lib->vba.BytePerPixelDETY[k] = 2;
1371 mode_lib->vba.BytePerPixelDETC[k] = 0;
1372 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_8) {
1373 mode_lib->vba.BytePerPixelDETY[k] = 1;
1374 mode_lib->vba.BytePerPixelDETC[k] = 0;
1375 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_8) {
1376 mode_lib->vba.BytePerPixelDETY[k] = 1;
1377 mode_lib->vba.BytePerPixelDETC[k] = 2;
1378 } else { // dm_420_10
1379 mode_lib->vba.BytePerPixelDETY[k] = 4.0 / 3.0;
1380 mode_lib->vba.BytePerPixelDETC[k] = 8.0 / 3.0;
1381 }
1382 }
1383
1384 mode_lib->vba.TotalDataReadBandwidth = 0.0;
1385 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1386 mode_lib->vba.ReadBandwidthPlaneLuma[k] = mode_lib->vba.SwathWidthSingleDPPY[k]
1387 * dml_ceil(mode_lib->vba.BytePerPixelDETY[k], 1)
1388 / (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k])
1389 * mode_lib->vba.VRatio[k];
1390 mode_lib->vba.ReadBandwidthPlaneChroma[k] = mode_lib->vba.SwathWidthSingleDPPY[k]
1391 / 2 * dml_ceil(mode_lib->vba.BytePerPixelDETC[k], 2)
1392 / (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k])
1393 * mode_lib->vba.VRatio[k] / 2;
1394 DTRACE(
1395 " read_bw[%i] = %fBps",
1396 k,
1397 mode_lib->vba.ReadBandwidthPlaneLuma[k]
1398 + mode_lib->vba.ReadBandwidthPlaneChroma[k]);
1399 mode_lib->vba.TotalDataReadBandwidth += mode_lib->vba.ReadBandwidthPlaneLuma[k]
1400 + mode_lib->vba.ReadBandwidthPlaneChroma[k];
1401 }
1402
1403 mode_lib->vba.TotalDCCActiveDPP = 0;
1404 mode_lib->vba.TotalActiveDPP = 0;
1405 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1406 mode_lib->vba.TotalActiveDPP = mode_lib->vba.TotalActiveDPP
1407 + mode_lib->vba.DPPPerPlane[k];
1408 if (mode_lib->vba.DCCEnable[k])
1409 mode_lib->vba.TotalDCCActiveDPP = mode_lib->vba.TotalDCCActiveDPP
1410 + mode_lib->vba.DPPPerPlane[k];
1411 }
1412
1413 mode_lib->vba.UrgentRoundTripAndOutOfOrderLatency =
1414 (mode_lib->vba.RoundTripPingLatencyCycles + 32) / mode_lib->vba.DCFCLK
1415 + mode_lib->vba.UrgentOutOfOrderReturnPerChannelPixelDataOnly
1416 * mode_lib->vba.NumberOfChannels
1417 / mode_lib->vba.ReturnBW;
1418
1419 mode_lib->vba.LastPixelOfLineExtraWatermark = 0;
1420 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1421 double DataFabricLineDeliveryTimeLuma, DataFabricLineDeliveryTimeChroma;
1422
1423 if (mode_lib->vba.VRatio[k] <= 1.0)
1424 mode_lib->vba.DisplayPipeLineDeliveryTimeLuma[k] =
1425 (double) mode_lib->vba.SwathWidthY[k]
1426 * mode_lib->vba.DPPPerPlane[k]
1427 / mode_lib->vba.HRatio[k]
1428 / mode_lib->vba.PixelClock[k];
1429 else
1430 mode_lib->vba.DisplayPipeLineDeliveryTimeLuma[k] =
1431 (double) mode_lib->vba.SwathWidthY[k]
1432 / mode_lib->vba.PSCL_THROUGHPUT_LUMA[k]
1433 / mode_lib->vba.DPPCLK[k];
1434
1435 DataFabricLineDeliveryTimeLuma = mode_lib->vba.SwathWidthSingleDPPY[k]
1436 * mode_lib->vba.SwathHeightY[k]
1437 * dml_ceil(mode_lib->vba.BytePerPixelDETY[k], 1)
1438 / (mode_lib->vba.ReturnBW * mode_lib->vba.ReadBandwidthPlaneLuma[k]
1439 / mode_lib->vba.TotalDataReadBandwidth);
1440 mode_lib->vba.LastPixelOfLineExtraWatermark = dml_max(
1441 mode_lib->vba.LastPixelOfLineExtraWatermark,
1442 DataFabricLineDeliveryTimeLuma
1443 - mode_lib->vba.DisplayPipeLineDeliveryTimeLuma[k]);
1444
1445 if (mode_lib->vba.BytePerPixelDETC[k] == 0)
1446 mode_lib->vba.DisplayPipeLineDeliveryTimeChroma[k] = 0.0;
1447 else if (mode_lib->vba.VRatio[k] / 2.0 <= 1.0)
1448 mode_lib->vba.DisplayPipeLineDeliveryTimeChroma[k] =
1449 mode_lib->vba.SwathWidthY[k] / 2.0
1450 * mode_lib->vba.DPPPerPlane[k]
1451 / (mode_lib->vba.HRatio[k] / 2.0)
1452 / mode_lib->vba.PixelClock[k];
1453 else
1454 mode_lib->vba.DisplayPipeLineDeliveryTimeChroma[k] =
1455 mode_lib->vba.SwathWidthY[k] / 2.0
1456 / mode_lib->vba.PSCL_THROUGHPUT_CHROMA[k]
1457 / mode_lib->vba.DPPCLK[k];
1458
1459 DataFabricLineDeliveryTimeChroma = mode_lib->vba.SwathWidthSingleDPPY[k] / 2.0
1460 * mode_lib->vba.SwathHeightC[k]
1461 * dml_ceil(mode_lib->vba.BytePerPixelDETC[k], 2)
1462 / (mode_lib->vba.ReturnBW
1463 * mode_lib->vba.ReadBandwidthPlaneChroma[k]
1464 / mode_lib->vba.TotalDataReadBandwidth);
1465 mode_lib->vba.LastPixelOfLineExtraWatermark =
1466 dml_max(
1467 mode_lib->vba.LastPixelOfLineExtraWatermark,
1468 DataFabricLineDeliveryTimeChroma
1469 - mode_lib->vba.DisplayPipeLineDeliveryTimeChroma[k]);
1470 }
1471
1472 mode_lib->vba.UrgentExtraLatency = mode_lib->vba.UrgentRoundTripAndOutOfOrderLatency
1473 + (mode_lib->vba.TotalActiveDPP * mode_lib->vba.PixelChunkSizeInKByte
1474 + mode_lib->vba.TotalDCCActiveDPP
1475 * mode_lib->vba.MetaChunkSize) * 1024.0
1476 / mode_lib->vba.ReturnBW;
1477
1478 if (mode_lib->vba.GPUVMEnable)
1479 mode_lib->vba.UrgentExtraLatency += mode_lib->vba.TotalActiveDPP
1480 * mode_lib->vba.PTEGroupSize / mode_lib->vba.ReturnBW;
1481
1482 mode_lib->vba.UrgentWatermark = mode_lib->vba.UrgentLatencyPixelDataOnly
1483 + mode_lib->vba.LastPixelOfLineExtraWatermark
1484 + mode_lib->vba.UrgentExtraLatency;
1485
1486 DTRACE(" urgent_extra_latency = %fus", mode_lib->vba.UrgentExtraLatency);
1487 DTRACE(" wm_urgent = %fus", mode_lib->vba.UrgentWatermark);
1488
1489 mode_lib->vba.UrgentLatency = mode_lib->vba.UrgentLatencyPixelDataOnly;
1490
1491 mode_lib->vba.TotalActiveWriteback = 0;
1492 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1493 if (mode_lib->vba.WritebackEnable[k])
1494 mode_lib->vba.TotalActiveWriteback = mode_lib->vba.TotalActiveWriteback + mode_lib->vba.ActiveWritebacksPerPlane[k];
1495 }
1496
1497 if (mode_lib->vba.TotalActiveWriteback <= 1)
1498 mode_lib->vba.WritebackUrgentWatermark = mode_lib->vba.WritebackLatency;
1499 else
1500 mode_lib->vba.WritebackUrgentWatermark = mode_lib->vba.WritebackLatency
1501 + mode_lib->vba.WritebackChunkSize * 1024.0 / 32
1502 / mode_lib->vba.SOCCLK;
1503
1504 DTRACE(" wm_wb_urgent = %fus", mode_lib->vba.WritebackUrgentWatermark);
1505
1506 // NB P-State/DRAM Clock Change Watermark
1507 mode_lib->vba.DRAMClockChangeWatermark = mode_lib->vba.DRAMClockChangeLatency
1508 + mode_lib->vba.UrgentWatermark;
1509
1510 DTRACE(" wm_pstate_change = %fus", mode_lib->vba.DRAMClockChangeWatermark);
1511
1512 DTRACE(" calculating wb pstate watermark");
1513 DTRACE(" total wb outputs %d", mode_lib->vba.TotalActiveWriteback);
1514 DTRACE(" socclk frequency %f Mhz", mode_lib->vba.SOCCLK);
1515
1516 if (mode_lib->vba.TotalActiveWriteback <= 1)
1517 mode_lib->vba.WritebackDRAMClockChangeWatermark =
1518 mode_lib->vba.DRAMClockChangeLatency
1519 + mode_lib->vba.WritebackLatency;
1520 else
1521 mode_lib->vba.WritebackDRAMClockChangeWatermark =
1522 mode_lib->vba.DRAMClockChangeLatency
1523 + mode_lib->vba.WritebackLatency
1524 + mode_lib->vba.WritebackChunkSize * 1024.0 / 32
1525 / mode_lib->vba.SOCCLK;
1526
1527 DTRACE(" wm_wb_pstate %fus", mode_lib->vba.WritebackDRAMClockChangeWatermark);
1528
1529 // Stutter Efficiency
1530 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1531 mode_lib->vba.LinesInDETY[k] = mode_lib->vba.DETBufferSizeY[k]
1532 / mode_lib->vba.BytePerPixelDETY[k] / mode_lib->vba.SwathWidthY[k];
1533 mode_lib->vba.LinesInDETYRoundedDownToSwath[k] = dml_floor(
1534 mode_lib->vba.LinesInDETY[k],
1535 mode_lib->vba.SwathHeightY[k]);
1536 mode_lib->vba.FullDETBufferingTimeY[k] =
1537 mode_lib->vba.LinesInDETYRoundedDownToSwath[k]
1538 * (mode_lib->vba.HTotal[k]
1539 / mode_lib->vba.PixelClock[k])
1540 / mode_lib->vba.VRatio[k];
1541 if (mode_lib->vba.BytePerPixelDETC[k] > 0) {
1542 mode_lib->vba.LinesInDETC[k] = mode_lib->vba.DETBufferSizeC[k]
1543 / mode_lib->vba.BytePerPixelDETC[k]
1544 / (mode_lib->vba.SwathWidthY[k] / 2);
1545 mode_lib->vba.LinesInDETCRoundedDownToSwath[k] = dml_floor(
1546 mode_lib->vba.LinesInDETC[k],
1547 mode_lib->vba.SwathHeightC[k]);
1548 mode_lib->vba.FullDETBufferingTimeC[k] =
1549 mode_lib->vba.LinesInDETCRoundedDownToSwath[k]
1550 * (mode_lib->vba.HTotal[k]
1551 / mode_lib->vba.PixelClock[k])
1552 / (mode_lib->vba.VRatio[k] / 2);
1553 } else {
1554 mode_lib->vba.LinesInDETC[k] = 0;
1555 mode_lib->vba.LinesInDETCRoundedDownToSwath[k] = 0;
1556 mode_lib->vba.FullDETBufferingTimeC[k] = 999999;
1557 }
1558 }
1559
1560 mode_lib->vba.MinFullDETBufferingTime = 999999.0;
1561 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1562 if (mode_lib->vba.FullDETBufferingTimeY[k]
1563 < mode_lib->vba.MinFullDETBufferingTime) {
1564 mode_lib->vba.MinFullDETBufferingTime =
1565 mode_lib->vba.FullDETBufferingTimeY[k];
1566 mode_lib->vba.FrameTimeForMinFullDETBufferingTime =
1567 (double) mode_lib->vba.VTotal[k] * mode_lib->vba.HTotal[k]
1568 / mode_lib->vba.PixelClock[k];
1569 }
1570 if (mode_lib->vba.FullDETBufferingTimeC[k]
1571 < mode_lib->vba.MinFullDETBufferingTime) {
1572 mode_lib->vba.MinFullDETBufferingTime =
1573 mode_lib->vba.FullDETBufferingTimeC[k];
1574 mode_lib->vba.FrameTimeForMinFullDETBufferingTime =
1575 (double) mode_lib->vba.VTotal[k] * mode_lib->vba.HTotal[k]
1576 / mode_lib->vba.PixelClock[k];
1577 }
1578 }
1579
1580 mode_lib->vba.AverageReadBandwidthGBytePerSecond = 0.0;
1581 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1582 if (mode_lib->vba.DCCEnable[k]) {
1583 mode_lib->vba.AverageReadBandwidthGBytePerSecond =
1584 mode_lib->vba.AverageReadBandwidthGBytePerSecond
1585 + mode_lib->vba.ReadBandwidthPlaneLuma[k]
1586 / mode_lib->vba.DCCRate[k]
1587 / 1000
1588 + mode_lib->vba.ReadBandwidthPlaneChroma[k]
1589 / mode_lib->vba.DCCRate[k]
1590 / 1000;
1591 } else {
1592 mode_lib->vba.AverageReadBandwidthGBytePerSecond =
1593 mode_lib->vba.AverageReadBandwidthGBytePerSecond
1594 + mode_lib->vba.ReadBandwidthPlaneLuma[k]
1595 / 1000
1596 + mode_lib->vba.ReadBandwidthPlaneChroma[k]
1597 / 1000;
1598 }
1599 if (mode_lib->vba.DCCEnable[k]) {
1600 mode_lib->vba.AverageReadBandwidthGBytePerSecond =
1601 mode_lib->vba.AverageReadBandwidthGBytePerSecond
1602 + mode_lib->vba.ReadBandwidthPlaneLuma[k]
1603 / 1000 / 256
1604 + mode_lib->vba.ReadBandwidthPlaneChroma[k]
1605 / 1000 / 256;
1606 }
1607 if (mode_lib->vba.GPUVMEnable) {
1608 mode_lib->vba.AverageReadBandwidthGBytePerSecond =
1609 mode_lib->vba.AverageReadBandwidthGBytePerSecond
1610 + mode_lib->vba.ReadBandwidthPlaneLuma[k]
1611 / 1000 / 512
1612 + mode_lib->vba.ReadBandwidthPlaneChroma[k]
1613 / 1000 / 512;
1614 }
1615 }
1616
1617 mode_lib->vba.PartOfBurstThatFitsInROB =
1618 dml_min(
1619 mode_lib->vba.MinFullDETBufferingTime
1620 * mode_lib->vba.TotalDataReadBandwidth,
1621 mode_lib->vba.ROBBufferSizeInKByte * 1024
1622 * mode_lib->vba.TotalDataReadBandwidth
1623 / (mode_lib->vba.AverageReadBandwidthGBytePerSecond
1624 * 1000));
1625 mode_lib->vba.StutterBurstTime = mode_lib->vba.PartOfBurstThatFitsInROB
1626 * (mode_lib->vba.AverageReadBandwidthGBytePerSecond * 1000)
1627 / mode_lib->vba.TotalDataReadBandwidth / mode_lib->vba.ReturnBW
1628 + (mode_lib->vba.MinFullDETBufferingTime
1629 * mode_lib->vba.TotalDataReadBandwidth
1630 - mode_lib->vba.PartOfBurstThatFitsInROB)
1631 / (mode_lib->vba.DCFCLK * 64);
1632 if (mode_lib->vba.TotalActiveWriteback == 0) {
1633 mode_lib->vba.StutterEfficiencyNotIncludingVBlank = (1
1634 - (mode_lib->vba.SRExitTime + mode_lib->vba.StutterBurstTime)
1635 / mode_lib->vba.MinFullDETBufferingTime) * 100;
1636 } else {
1637 mode_lib->vba.StutterEfficiencyNotIncludingVBlank = 0;
1638 }
1639
1640 mode_lib->vba.SmallestVBlank = 999999;
1641 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1642 if (mode_lib->vba.SynchronizedVBlank || mode_lib->vba.NumberOfActivePlanes == 1) {
1643 mode_lib->vba.VBlankTime = (double) (mode_lib->vba.VTotal[k]
1644 - mode_lib->vba.VActive[k]) * mode_lib->vba.HTotal[k]
1645 / mode_lib->vba.PixelClock[k];
1646 } else {
1647 mode_lib->vba.VBlankTime = 0;
1648 }
1649 mode_lib->vba.SmallestVBlank = dml_min(
1650 mode_lib->vba.SmallestVBlank,
1651 mode_lib->vba.VBlankTime);
1652 }
1653
1654 mode_lib->vba.StutterEfficiency = (mode_lib->vba.StutterEfficiencyNotIncludingVBlank / 100
1655 * (mode_lib->vba.FrameTimeForMinFullDETBufferingTime
1656 - mode_lib->vba.SmallestVBlank)
1657 + mode_lib->vba.SmallestVBlank)
1658 / mode_lib->vba.FrameTimeForMinFullDETBufferingTime * 100;
1659
1660 // dml_ml->vba.DCFCLK Deep Sleep
1661 mode_lib->vba.DCFCLKDeepSleep = 8.0;
1662
1663 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; k++) {
1664 if (mode_lib->vba.BytePerPixelDETC[k] > 0) {
1665 mode_lib->vba.DCFCLKDeepSleepPerPlane[k] =
1666 dml_max(
1667 1.1 * mode_lib->vba.SwathWidthY[k]
1668 * dml_ceil(
1669 mode_lib->vba.BytePerPixelDETY[k],
1670 1) / 32
1671 / mode_lib->vba.DisplayPipeLineDeliveryTimeLuma[k],
1672 1.1 * mode_lib->vba.SwathWidthY[k] / 2.0
1673 * dml_ceil(
1674 mode_lib->vba.BytePerPixelDETC[k],
1675 2) / 32
1676 / mode_lib->vba.DisplayPipeLineDeliveryTimeChroma[k]);
1677 } else
1678 mode_lib->vba.DCFCLKDeepSleepPerPlane[k] = 1.1 * mode_lib->vba.SwathWidthY[k]
1679 * dml_ceil(mode_lib->vba.BytePerPixelDETY[k], 1) / 64.0
1680 / mode_lib->vba.DisplayPipeLineDeliveryTimeLuma[k];
1681 mode_lib->vba.DCFCLKDeepSleepPerPlane[k] = dml_max(
1682 mode_lib->vba.DCFCLKDeepSleepPerPlane[k],
1683 mode_lib->vba.PixelClock[k] / 16.0);
1684 mode_lib->vba.DCFCLKDeepSleep = dml_max(
1685 mode_lib->vba.DCFCLKDeepSleep,
1686 mode_lib->vba.DCFCLKDeepSleepPerPlane[k]);
1687
1688 DTRACE(
1689 " dcfclk_deepsleep_per_plane[%i] = %fMHz",
1690 k,
1691 mode_lib->vba.DCFCLKDeepSleepPerPlane[k]);
1692 }
1693
1694 DTRACE(" dcfclk_deepsleep_mhz = %fMHz", mode_lib->vba.DCFCLKDeepSleep);
1695
1696 // Stutter Watermark
1697 mode_lib->vba.StutterExitWatermark = mode_lib->vba.SRExitTime
1698 + mode_lib->vba.LastPixelOfLineExtraWatermark
1699 + mode_lib->vba.UrgentExtraLatency + 10 / mode_lib->vba.DCFCLKDeepSleep;
1700 mode_lib->vba.StutterEnterPlusExitWatermark = mode_lib->vba.SREnterPlusExitTime
1701 + mode_lib->vba.LastPixelOfLineExtraWatermark
1702 + mode_lib->vba.UrgentExtraLatency;
1703
1704 DTRACE(" wm_cstate_exit = %fus", mode_lib->vba.StutterExitWatermark);
1705 DTRACE(" wm_cstate_enter_exit = %fus", mode_lib->vba.StutterEnterPlusExitWatermark);
1706
1707 // Urgent Latency Supported
1708 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1709 mode_lib->vba.EffectiveDETPlusLBLinesLuma =
1710 dml_floor(
1711 mode_lib->vba.LinesInDETY[k]
1712 + dml_min(
1713 mode_lib->vba.LinesInDETY[k]
1714 * mode_lib->vba.DPPCLK[k]
1715 * mode_lib->vba.BytePerPixelDETY[k]
1716 * mode_lib->vba.PSCL_THROUGHPUT_LUMA[k]
1717 / (mode_lib->vba.ReturnBW
1718 / mode_lib->vba.DPPPerPlane[k]),
1719 (double) mode_lib->vba.EffectiveLBLatencyHidingSourceLinesLuma),
1720 mode_lib->vba.SwathHeightY[k]);
1721
1722 mode_lib->vba.UrgentLatencySupportUsLuma = mode_lib->vba.EffectiveDETPlusLBLinesLuma
1723 * (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k])
1724 / mode_lib->vba.VRatio[k]
1725 - mode_lib->vba.EffectiveDETPlusLBLinesLuma
1726 * mode_lib->vba.SwathWidthY[k]
1727 * mode_lib->vba.BytePerPixelDETY[k]
1728 / (mode_lib->vba.ReturnBW
1729 / mode_lib->vba.DPPPerPlane[k]);
1730
1731 if (mode_lib->vba.BytePerPixelDETC[k] > 0) {
1732 mode_lib->vba.EffectiveDETPlusLBLinesChroma =
1733 dml_floor(
1734 mode_lib->vba.LinesInDETC[k]
1735 + dml_min(
1736 mode_lib->vba.LinesInDETC[k]
1737 * mode_lib->vba.DPPCLK[k]
1738 * mode_lib->vba.BytePerPixelDETC[k]
1739 * mode_lib->vba.PSCL_THROUGHPUT_CHROMA[k]
1740 / (mode_lib->vba.ReturnBW
1741 / mode_lib->vba.DPPPerPlane[k]),
1742 (double) mode_lib->vba.EffectiveLBLatencyHidingSourceLinesChroma),
1743 mode_lib->vba.SwathHeightC[k]);
1744 mode_lib->vba.UrgentLatencySupportUsChroma =
1745 mode_lib->vba.EffectiveDETPlusLBLinesChroma
1746 * (mode_lib->vba.HTotal[k]
1747 / mode_lib->vba.PixelClock[k])
1748 / (mode_lib->vba.VRatio[k] / 2)
1749 - mode_lib->vba.EffectiveDETPlusLBLinesChroma
1750 * (mode_lib->vba.SwathWidthY[k]
1751 / 2)
1752 * mode_lib->vba.BytePerPixelDETC[k]
1753 / (mode_lib->vba.ReturnBW
1754 / mode_lib->vba.DPPPerPlane[k]);
1755 mode_lib->vba.UrgentLatencySupportUs[k] = dml_min(
1756 mode_lib->vba.UrgentLatencySupportUsLuma,
1757 mode_lib->vba.UrgentLatencySupportUsChroma);
1758 } else {
1759 mode_lib->vba.UrgentLatencySupportUs[k] =
1760 mode_lib->vba.UrgentLatencySupportUsLuma;
1761 }
1762 }
1763
1764 mode_lib->vba.MinUrgentLatencySupportUs = 999999;
1765 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1766 mode_lib->vba.MinUrgentLatencySupportUs = dml_min(
1767 mode_lib->vba.MinUrgentLatencySupportUs,
1768 mode_lib->vba.UrgentLatencySupportUs[k]);
1769 }
1770
1771 // Non-Urgent Latency Tolerance
1772 mode_lib->vba.NonUrgentLatencyTolerance = mode_lib->vba.MinUrgentLatencySupportUs
1773 - mode_lib->vba.UrgentWatermark;
1774
1775 // DSCCLK
1776 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1777 if ((mode_lib->vba.BlendingAndTiming[k] != k) || !mode_lib->vba.DSCEnabled[k]) {
1778 mode_lib->vba.DSCCLK_calculated[k] = 0.0;
1779 } else {
1780 if (mode_lib->vba.OutputFormat[k] == dm_420
1781 || mode_lib->vba.OutputFormat[k] == dm_n422)
1782 mode_lib->vba.DSCFormatFactor = 2;
1783 else
1784 mode_lib->vba.DSCFormatFactor = 1;
1785 if (mode_lib->vba.ODMCombineEnabled[k])
1786 mode_lib->vba.DSCCLK_calculated[k] =
1787 mode_lib->vba.PixelClockBackEnd[k] / 6
1788 / mode_lib->vba.DSCFormatFactor
1789 / (1
1790 - mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading
1791 / 100);
1792 else
1793 mode_lib->vba.DSCCLK_calculated[k] =
1794 mode_lib->vba.PixelClockBackEnd[k] / 3
1795 / mode_lib->vba.DSCFormatFactor
1796 / (1
1797 - mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading
1798 / 100);
1799 }
1800 }
1801
1802 // DSC Delay
1803 // TODO
1804 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1805 double bpp = mode_lib->vba.OutputBpp[k];
1806 unsigned int slices = mode_lib->vba.NumberOfDSCSlices[k];
1807
1808 if (mode_lib->vba.DSCEnabled[k] && bpp != 0) {
1809 if (!mode_lib->vba.ODMCombineEnabled[k]) {
1810 mode_lib->vba.DSCDelay[k] =
1811 dscceComputeDelay(
1812 mode_lib->vba.DSCInputBitPerComponent[k],
1813 bpp,
1814 dml_ceil(
1815 (double) mode_lib->vba.HActive[k]
1816 / mode_lib->vba.NumberOfDSCSlices[k],
1817 1),
1818 slices,
1819 mode_lib->vba.OutputFormat[k])
1820 + dscComputeDelay(
1821 mode_lib->vba.OutputFormat[k]);
1822 } else {
1823 mode_lib->vba.DSCDelay[k] =
1824 2
1825 * (dscceComputeDelay(
1826 mode_lib->vba.DSCInputBitPerComponent[k],
1827 bpp,
1828 dml_ceil(
1829 (double) mode_lib->vba.HActive[k]
1830 / mode_lib->vba.NumberOfDSCSlices[k],
1831 1),
1832 slices / 2.0,
1833 mode_lib->vba.OutputFormat[k])
1834 + dscComputeDelay(
1835 mode_lib->vba.OutputFormat[k]));
1836 }
1837 mode_lib->vba.DSCDelay[k] = mode_lib->vba.DSCDelay[k]
1838 * mode_lib->vba.PixelClock[k]
1839 / mode_lib->vba.PixelClockBackEnd[k];
1840 } else {
1841 mode_lib->vba.DSCDelay[k] = 0;
1842 }
1843 }
1844
1845 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k)
1846 for (j = 0; j < mode_lib->vba.NumberOfActivePlanes; ++j) // NumberOfPlanes
1847 if (j != k && mode_lib->vba.BlendingAndTiming[k] == j
1848 && mode_lib->vba.DSCEnabled[j])
1849 mode_lib->vba.DSCDelay[k] = mode_lib->vba.DSCDelay[j];
1850
1851 // Prefetch
1852 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1853 unsigned int PDEAndMetaPTEBytesFrameY;
1854 unsigned int PixelPTEBytesPerRowY;
1855 unsigned int MetaRowByteY;
1856 unsigned int MetaRowByteC;
1857 unsigned int PDEAndMetaPTEBytesFrameC;
1858 unsigned int PixelPTEBytesPerRowC;
1859
1860 Calculate256BBlockSizes(
1861 mode_lib->vba.SourcePixelFormat[k],
1862 mode_lib->vba.SurfaceTiling[k],
1863 dml_ceil(mode_lib->vba.BytePerPixelDETY[k], 1),
1864 dml_ceil(mode_lib->vba.BytePerPixelDETC[k], 2),
1865 &mode_lib->vba.BlockHeight256BytesY[k],
1866 &mode_lib->vba.BlockHeight256BytesC[k],
1867 &mode_lib->vba.BlockWidth256BytesY[k],
1868 &mode_lib->vba.BlockWidth256BytesC[k]);
1869 PDEAndMetaPTEBytesFrameY = CalculateVMAndRowBytes(
1870 mode_lib,
1871 mode_lib->vba.DCCEnable[k],
1872 mode_lib->vba.BlockHeight256BytesY[k],
1873 mode_lib->vba.BlockWidth256BytesY[k],
1874 mode_lib->vba.SourcePixelFormat[k],
1875 mode_lib->vba.SurfaceTiling[k],
1876 dml_ceil(mode_lib->vba.BytePerPixelDETY[k], 1),
1877 mode_lib->vba.SourceScan[k],
1878 mode_lib->vba.ViewportWidth[k],
1879 mode_lib->vba.ViewportHeight[k],
1880 mode_lib->vba.SwathWidthY[k],
1881 mode_lib->vba.GPUVMEnable,
1882 mode_lib->vba.VMMPageSize,
1883 mode_lib->vba.PTEBufferSizeInRequestsLuma,
1884 mode_lib->vba.PDEProcessingBufIn64KBReqs,
1885 mode_lib->vba.PitchY[k],
1886 mode_lib->vba.DCCMetaPitchY[k],
1887 &mode_lib->vba.MacroTileWidthY[k],
1888 &MetaRowByteY,
1889 &PixelPTEBytesPerRowY,
1890 &mode_lib->vba.PTEBufferSizeNotExceeded[mode_lib->vba.VoltageLevel][0],
1891 &mode_lib->vba.dpte_row_height[k],
1892 &mode_lib->vba.meta_row_height[k]);
1893 mode_lib->vba.PrefetchSourceLinesY[k] = CalculatePrefetchSourceLines(
1894 mode_lib,
1895 mode_lib->vba.VRatio[k],
1896 mode_lib->vba.vtaps[k],
1897 mode_lib->vba.Interlace[k],
1898 mode_lib->vba.ProgressiveToInterlaceUnitInOPP,
1899 mode_lib->vba.SwathHeightY[k],
1900 mode_lib->vba.ViewportYStartY[k],
1901 &mode_lib->vba.VInitPreFillY[k],
1902 &mode_lib->vba.MaxNumSwathY[k]);
1903
1904 if ((mode_lib->vba.SourcePixelFormat[k] != dm_444_64
1905 && mode_lib->vba.SourcePixelFormat[k] != dm_444_32
1906 && mode_lib->vba.SourcePixelFormat[k] != dm_444_16
1907 && mode_lib->vba.SourcePixelFormat[k] != dm_444_8)) {
1908 PDEAndMetaPTEBytesFrameC =
1909 CalculateVMAndRowBytes(
1910 mode_lib,
1911 mode_lib->vba.DCCEnable[k],
1912 mode_lib->vba.BlockHeight256BytesC[k],
1913 mode_lib->vba.BlockWidth256BytesC[k],
1914 mode_lib->vba.SourcePixelFormat[k],
1915 mode_lib->vba.SurfaceTiling[k],
1916 dml_ceil(
1917 mode_lib->vba.BytePerPixelDETC[k],
1918 2),
1919 mode_lib->vba.SourceScan[k],
1920 mode_lib->vba.ViewportWidth[k] / 2,
1921 mode_lib->vba.ViewportHeight[k] / 2,
1922 mode_lib->vba.SwathWidthY[k] / 2,
1923 mode_lib->vba.GPUVMEnable,
1924 mode_lib->vba.VMMPageSize,
1925 mode_lib->vba.PTEBufferSizeInRequestsLuma,
1926 mode_lib->vba.PDEProcessingBufIn64KBReqs,
1927 mode_lib->vba.PitchC[k],
1928 0,
1929 &mode_lib->vba.MacroTileWidthC[k],
1930 &MetaRowByteC,
1931 &PixelPTEBytesPerRowC,
1932 &mode_lib->vba.PTEBufferSizeNotExceeded[mode_lib->vba.VoltageLevel][0],
1933 &mode_lib->vba.dpte_row_height_chroma[k],
1934 &mode_lib->vba.meta_row_height_chroma[k]);
1935 mode_lib->vba.PrefetchSourceLinesC[k] = CalculatePrefetchSourceLines(
1936 mode_lib,
1937 mode_lib->vba.VRatio[k] / 2,
1938 mode_lib->vba.VTAPsChroma[k],
1939 mode_lib->vba.Interlace[k],
1940 mode_lib->vba.ProgressiveToInterlaceUnitInOPP,
1941 mode_lib->vba.SwathHeightC[k],
1942 mode_lib->vba.ViewportYStartC[k],
1943 &mode_lib->vba.VInitPreFillC[k],
1944 &mode_lib->vba.MaxNumSwathC[k]);
1945 } else {
1946 PixelPTEBytesPerRowC = 0;
1947 PDEAndMetaPTEBytesFrameC = 0;
1948 MetaRowByteC = 0;
1949 mode_lib->vba.MaxNumSwathC[k] = 0;
1950 mode_lib->vba.PrefetchSourceLinesC[k] = 0;
1951 }
1952
1953 mode_lib->vba.PixelPTEBytesPerRow[k] = PixelPTEBytesPerRowY + PixelPTEBytesPerRowC;
1954 mode_lib->vba.PDEAndMetaPTEBytesFrame[k] = PDEAndMetaPTEBytesFrameY
1955 + PDEAndMetaPTEBytesFrameC;
1956 mode_lib->vba.MetaRowByte[k] = MetaRowByteY + MetaRowByteC;
1957
1958 CalculateActiveRowBandwidth(
1959 mode_lib->vba.GPUVMEnable,
1960 mode_lib->vba.SourcePixelFormat[k],
1961 mode_lib->vba.VRatio[k],
1962 mode_lib->vba.DCCEnable[k],
1963 mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k],
1964 MetaRowByteY,
1965 MetaRowByteC,
1966 mode_lib->vba.meta_row_height[k],
1967 mode_lib->vba.meta_row_height_chroma[k],
1968 PixelPTEBytesPerRowY,
1969 PixelPTEBytesPerRowC,
1970 mode_lib->vba.dpte_row_height[k],
1971 mode_lib->vba.dpte_row_height_chroma[k],
1972 &mode_lib->vba.meta_row_bw[k],
1973 &mode_lib->vba.dpte_row_bw[k],
1974 &mode_lib->vba.qual_row_bw[k]);
1975 }
1976
1977 mode_lib->vba.TCalc = 24.0 / mode_lib->vba.DCFCLKDeepSleep;
1978
1979 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
1980 if (mode_lib->vba.BlendingAndTiming[k] == k) {
1981 if (mode_lib->vba.WritebackEnable[k] == true) {
1982 mode_lib->vba.WritebackDelay[mode_lib->vba.VoltageLevel][k] =
1983 mode_lib->vba.WritebackLatency
1984 + CalculateWriteBackDelay(
1985 mode_lib->vba.WritebackPixelFormat[k],
1986 mode_lib->vba.WritebackHRatio[k],
1987 mode_lib->vba.WritebackVRatio[k],
1988 mode_lib->vba.WritebackLumaHTaps[k],
1989 mode_lib->vba.WritebackLumaVTaps[k],
1990 mode_lib->vba.WritebackChromaHTaps[k],
1991 mode_lib->vba.WritebackChromaVTaps[k],
1992 mode_lib->vba.WritebackDestinationWidth[k])
1993 / mode_lib->vba.DISPCLK;
1994 } else
1995 mode_lib->vba.WritebackDelay[mode_lib->vba.VoltageLevel][k] = 0;
1996 for (j = 0; j < mode_lib->vba.NumberOfActivePlanes; ++j) {
1997 if (mode_lib->vba.BlendingAndTiming[j] == k
1998 && mode_lib->vba.WritebackEnable[j] == true) {
1999 mode_lib->vba.WritebackDelay[mode_lib->vba.VoltageLevel][k] =
2000 dml_max(
2001 mode_lib->vba.WritebackDelay[mode_lib->vba.VoltageLevel][k],
2002 mode_lib->vba.WritebackLatency
2003 + CalculateWriteBackDelay(
2004 mode_lib->vba.WritebackPixelFormat[j],
2005 mode_lib->vba.WritebackHRatio[j],
2006 mode_lib->vba.WritebackVRatio[j],
2007 mode_lib->vba.WritebackLumaHTaps[j],
2008 mode_lib->vba.WritebackLumaVTaps[j],
2009 mode_lib->vba.WritebackChromaHTaps[j],
2010 mode_lib->vba.WritebackChromaVTaps[j],
2011 mode_lib->vba.WritebackDestinationWidth[j])
2012 / mode_lib->vba.DISPCLK);
2013 }
2014 }
2015 }
2016 }
2017
2018 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k)
2019 for (j = 0; j < mode_lib->vba.NumberOfActivePlanes; ++j)
2020 if (mode_lib->vba.BlendingAndTiming[k] == j)
2021 mode_lib->vba.WritebackDelay[mode_lib->vba.VoltageLevel][k] =
2022 mode_lib->vba.WritebackDelay[mode_lib->vba.VoltageLevel][j];
2023
2024 mode_lib->vba.VStartupLines = 13;
2025 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2026 mode_lib->vba.MaxVStartupLines[k] =
2027 mode_lib->vba.VTotal[k] - mode_lib->vba.VActive[k]
2028 - dml_max(
2029 1.0,
2030 dml_ceil(
2031 mode_lib->vba.WritebackDelay[mode_lib->vba.VoltageLevel][k]
2032 / (mode_lib->vba.HTotal[k]
2033 / mode_lib->vba.PixelClock[k]),
2034 1));
2035 }
2036
2037 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k)
2038 mode_lib->vba.MaximumMaxVStartupLines = dml_max(
2039 mode_lib->vba.MaximumMaxVStartupLines,
2040 mode_lib->vba.MaxVStartupLines[k]);
2041
2042 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2043 mode_lib->vba.cursor_bw[k] = 0.0;
2044 for (j = 0; j < mode_lib->vba.NumberOfCursors[k]; ++j)
2045 mode_lib->vba.cursor_bw[k] += mode_lib->vba.CursorWidth[k][j]
2046 * mode_lib->vba.CursorBPP[k][j] / 8.0
2047 / (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k])
2048 * mode_lib->vba.VRatio[k];
2049 }
2050
2051 do {
2052 double MaxTotalRDBandwidth = 0;
2053 bool DestinationLineTimesForPrefetchLessThan2 = false;
2054 bool VRatioPrefetchMoreThan4 = false;
2055 bool prefetch_vm_bw_valid = true;
2056 bool prefetch_row_bw_valid = true;
2057 double TWait = CalculateTWait(
2058 mode_lib->vba.PrefetchMode[mode_lib->vba.VoltageLevel][mode_lib->vba.maxMpcComb],
2059 mode_lib->vba.DRAMClockChangeLatency,
2060 mode_lib->vba.UrgentLatencyPixelDataOnly,
2061 mode_lib->vba.SREnterPlusExitTime);
2062
2063 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2064 if (mode_lib->vba.XFCEnabled[k] == true) {
2065 mode_lib->vba.XFCRemoteSurfaceFlipDelay =
2066 CalculateRemoteSurfaceFlipDelay(
2067 mode_lib,
2068 mode_lib->vba.VRatio[k],
2069 mode_lib->vba.SwathWidthY[k],
2070 dml_ceil(
2071 mode_lib->vba.BytePerPixelDETY[k],
2072 1),
2073 mode_lib->vba.HTotal[k]
2074 / mode_lib->vba.PixelClock[k],
2075 mode_lib->vba.XFCTSlvVupdateOffset,
2076 mode_lib->vba.XFCTSlvVupdateWidth,
2077 mode_lib->vba.XFCTSlvVreadyOffset,
2078 mode_lib->vba.XFCXBUFLatencyTolerance,
2079 mode_lib->vba.XFCFillBWOverhead,
2080 mode_lib->vba.XFCSlvChunkSize,
2081 mode_lib->vba.XFCBusTransportTime,
2082 mode_lib->vba.TCalc,
2083 TWait,
2084 &mode_lib->vba.SrcActiveDrainRate,
2085 &mode_lib->vba.TInitXFill,
2086 &mode_lib->vba.TslvChk);
2087 } else {
2088 mode_lib->vba.XFCRemoteSurfaceFlipDelay = 0;
2089 }
2090 mode_lib->vba.ErrorResult[k] =
2091 CalculatePrefetchSchedule(
2092 mode_lib,
2093 mode_lib->vba.DPPCLK[k],
2094 mode_lib->vba.DISPCLK,
2095 mode_lib->vba.PixelClock[k],
2096 mode_lib->vba.DCFCLKDeepSleep,
2097 mode_lib->vba.DSCDelay[k],
2098 mode_lib->vba.DPPPerPlane[k],
2099 mode_lib->vba.ScalerEnabled[k],
2100 mode_lib->vba.NumberOfCursors[k],
2101 mode_lib->vba.DPPCLKDelaySubtotal,
2102 mode_lib->vba.DPPCLKDelaySCL,
2103 mode_lib->vba.DPPCLKDelaySCLLBOnly,
2104 mode_lib->vba.DPPCLKDelayCNVCFormater,
2105 mode_lib->vba.DPPCLKDelayCNVCCursor,
2106 mode_lib->vba.DISPCLKDelaySubtotal,
2107 (unsigned int) (mode_lib->vba.SwathWidthY[k]
2108 / mode_lib->vba.HRatio[k]),
2109 mode_lib->vba.OutputFormat[k],
2110 mode_lib->vba.VTotal[k]
2111 - mode_lib->vba.VActive[k],
2112 mode_lib->vba.HTotal[k],
2113 mode_lib->vba.MaxInterDCNTileRepeaters,
2114 dml_min(
2115 mode_lib->vba.VStartupLines,
2116 mode_lib->vba.MaxVStartupLines[k]),
2117 mode_lib->vba.GPUVMMaxPageTableLevels,
2118 mode_lib->vba.GPUVMEnable,
2119 mode_lib->vba.DynamicMetadataEnable[k],
2120 mode_lib->vba.DynamicMetadataLinesBeforeActiveRequired[k],
2121 mode_lib->vba.DynamicMetadataTransmittedBytes[k],
2122 mode_lib->vba.DCCEnable[k],
2123 mode_lib->vba.UrgentLatencyPixelDataOnly,
2124 mode_lib->vba.UrgentExtraLatency,
2125 mode_lib->vba.TCalc,
2126 mode_lib->vba.PDEAndMetaPTEBytesFrame[k],
2127 mode_lib->vba.MetaRowByte[k],
2128 mode_lib->vba.PixelPTEBytesPerRow[k],
2129 mode_lib->vba.PrefetchSourceLinesY[k],
2130 mode_lib->vba.SwathWidthY[k],
2131 mode_lib->vba.BytePerPixelDETY[k],
2132 mode_lib->vba.VInitPreFillY[k],
2133 mode_lib->vba.MaxNumSwathY[k],
2134 mode_lib->vba.PrefetchSourceLinesC[k],
2135 mode_lib->vba.BytePerPixelDETC[k],
2136 mode_lib->vba.VInitPreFillC[k],
2137 mode_lib->vba.MaxNumSwathC[k],
2138 mode_lib->vba.SwathHeightY[k],
2139 mode_lib->vba.SwathHeightC[k],
2140 TWait,
2141 mode_lib->vba.XFCEnabled[k],
2142 mode_lib->vba.XFCRemoteSurfaceFlipDelay,
2143 mode_lib->vba.Interlace[k],
2144 mode_lib->vba.ProgressiveToInterlaceUnitInOPP,
2145 &mode_lib->vba.DSTXAfterScaler[k],
2146 &mode_lib->vba.DSTYAfterScaler[k],
2147 &mode_lib->vba.DestinationLinesForPrefetch[k],
2148 &mode_lib->vba.PrefetchBandwidth[k],
2149 &mode_lib->vba.DestinationLinesToRequestVMInVBlank[k],
2150 &mode_lib->vba.DestinationLinesToRequestRowInVBlank[k],
2151 &mode_lib->vba.VRatioPrefetchY[k],
2152 &mode_lib->vba.VRatioPrefetchC[k],
2153 &mode_lib->vba.RequiredPrefetchPixDataBWLuma[k],
2154 &mode_lib->vba.VStartupRequiredWhenNotEnoughTimeForDynamicMetadata,
2155 &mode_lib->vba.Tno_bw[k],
2156 &mode_lib->vba.VUpdateOffsetPix[k],
2157 &mode_lib->vba.VUpdateWidthPix[k],
2158 &mode_lib->vba.VReadyOffsetPix[k]);
2159 if (mode_lib->vba.BlendingAndTiming[k] == k) {
2160 mode_lib->vba.VStartup[k] = dml_min(
2161 mode_lib->vba.VStartupLines,
2162 mode_lib->vba.MaxVStartupLines[k]);
2163 if (mode_lib->vba.VStartupRequiredWhenNotEnoughTimeForDynamicMetadata
2164 != 0) {
2165 mode_lib->vba.VStartup[k] =
2166 mode_lib->vba.VStartupRequiredWhenNotEnoughTimeForDynamicMetadata;
2167 }
2168 } else {
2169 mode_lib->vba.VStartup[k] =
2170 dml_min(
2171 mode_lib->vba.VStartupLines,
2172 mode_lib->vba.MaxVStartupLines[mode_lib->vba.BlendingAndTiming[k]]);
2173 }
2174 }
2175
2176 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2177
2178 if (mode_lib->vba.PDEAndMetaPTEBytesFrame[k] == 0)
2179 mode_lib->vba.prefetch_vm_bw[k] = 0;
2180 else if (mode_lib->vba.DestinationLinesToRequestVMInVBlank[k] > 0) {
2181 mode_lib->vba.prefetch_vm_bw[k] =
2182 (double) mode_lib->vba.PDEAndMetaPTEBytesFrame[k]
2183 / (mode_lib->vba.DestinationLinesToRequestVMInVBlank[k]
2184 * mode_lib->vba.HTotal[k]
2185 / mode_lib->vba.PixelClock[k]);
2186 } else {
2187 mode_lib->vba.prefetch_vm_bw[k] = 0;
2188 prefetch_vm_bw_valid = false;
2189 }
2190 if (mode_lib->vba.MetaRowByte[k] + mode_lib->vba.PixelPTEBytesPerRow[k]
2191 == 0)
2192 mode_lib->vba.prefetch_row_bw[k] = 0;
2193 else if (mode_lib->vba.DestinationLinesToRequestRowInVBlank[k] > 0) {
2194 mode_lib->vba.prefetch_row_bw[k] =
2195 (double) (mode_lib->vba.MetaRowByte[k]
2196 + mode_lib->vba.PixelPTEBytesPerRow[k])
2197 / (mode_lib->vba.DestinationLinesToRequestRowInVBlank[k]
2198 * mode_lib->vba.HTotal[k]
2199 / mode_lib->vba.PixelClock[k]);
2200 } else {
2201 mode_lib->vba.prefetch_row_bw[k] = 0;
2202 prefetch_row_bw_valid = false;
2203 }
2204
2205 MaxTotalRDBandwidth =
2206 MaxTotalRDBandwidth + mode_lib->vba.cursor_bw[k]
2207 + dml_max(
2208 mode_lib->vba.prefetch_vm_bw[k],
2209 dml_max(
2210 mode_lib->vba.prefetch_row_bw[k],
2211 dml_max(
2212 mode_lib->vba.ReadBandwidthPlaneLuma[k]
2213 + mode_lib->vba.ReadBandwidthPlaneChroma[k],
2214 mode_lib->vba.RequiredPrefetchPixDataBWLuma[k])
2215 + mode_lib->vba.meta_row_bw[k]
2216 + mode_lib->vba.dpte_row_bw[k]));
2217
2218 if (mode_lib->vba.DestinationLinesForPrefetch[k] < 2)
2219 DestinationLineTimesForPrefetchLessThan2 = true;
2220 if (mode_lib->vba.VRatioPrefetchY[k] > 4
2221 || mode_lib->vba.VRatioPrefetchC[k] > 4)
2222 VRatioPrefetchMoreThan4 = true;
2223 }
2224
2225 if (MaxTotalRDBandwidth <= mode_lib->vba.ReturnBW && prefetch_vm_bw_valid
2226 && prefetch_row_bw_valid && !VRatioPrefetchMoreThan4
2227 && !DestinationLineTimesForPrefetchLessThan2)
2228 mode_lib->vba.PrefetchModeSupported = true;
2229 else {
2230 mode_lib->vba.PrefetchModeSupported = false;
2231 dml_print(
2232 "DML: CalculatePrefetchSchedule ***failed***. Bandwidth violation. Results are NOT valid\n");
2233 }
2234
2235 if (mode_lib->vba.PrefetchModeSupported == true) {
2236 double final_flip_bw[DC__NUM_DPP__MAX];
2237 unsigned int ImmediateFlipBytes[DC__NUM_DPP__MAX];
2238 double total_dcn_read_bw_with_flip = 0;
2239
2240 mode_lib->vba.BandwidthAvailableForImmediateFlip = mode_lib->vba.ReturnBW;
2241 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2242 mode_lib->vba.BandwidthAvailableForImmediateFlip =
2243 mode_lib->vba.BandwidthAvailableForImmediateFlip
2244 - mode_lib->vba.cursor_bw[k]
2245 - dml_max(
2246 mode_lib->vba.ReadBandwidthPlaneLuma[k]
2247 + mode_lib->vba.ReadBandwidthPlaneChroma[k]
2248 + mode_lib->vba.qual_row_bw[k],
2249 mode_lib->vba.PrefetchBandwidth[k]);
2250 }
2251
2252 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2253 ImmediateFlipBytes[k] = 0;
2254 if ((mode_lib->vba.SourcePixelFormat[k] != dm_420_8
2255 && mode_lib->vba.SourcePixelFormat[k] != dm_420_10)) {
2256 ImmediateFlipBytes[k] =
2257 mode_lib->vba.PDEAndMetaPTEBytesFrame[k]
2258 + mode_lib->vba.MetaRowByte[k]
2259 + mode_lib->vba.PixelPTEBytesPerRow[k];
2260 }
2261 }
2262 mode_lib->vba.TotImmediateFlipBytes = 0;
2263 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2264 if ((mode_lib->vba.SourcePixelFormat[k] != dm_420_8
2265 && mode_lib->vba.SourcePixelFormat[k] != dm_420_10)) {
2266 mode_lib->vba.TotImmediateFlipBytes =
2267 mode_lib->vba.TotImmediateFlipBytes
2268 + ImmediateFlipBytes[k];
2269 }
2270 }
2271 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2272 CalculateFlipSchedule(
2273 mode_lib,
2274 mode_lib->vba.UrgentExtraLatency,
2275 mode_lib->vba.UrgentLatencyPixelDataOnly,
2276 mode_lib->vba.GPUVMMaxPageTableLevels,
2277 mode_lib->vba.GPUVMEnable,
2278 mode_lib->vba.BandwidthAvailableForImmediateFlip,
2279 mode_lib->vba.TotImmediateFlipBytes,
2280 mode_lib->vba.SourcePixelFormat[k],
2281 ImmediateFlipBytes[k],
2282 mode_lib->vba.HTotal[k]
2283 / mode_lib->vba.PixelClock[k],
2284 mode_lib->vba.VRatio[k],
2285 mode_lib->vba.Tno_bw[k],
2286 mode_lib->vba.PDEAndMetaPTEBytesFrame[k],
2287 mode_lib->vba.MetaRowByte[k],
2288 mode_lib->vba.PixelPTEBytesPerRow[k],
2289 mode_lib->vba.DCCEnable[k],
2290 mode_lib->vba.dpte_row_height[k],
2291 mode_lib->vba.meta_row_height[k],
2292 mode_lib->vba.qual_row_bw[k],
2293 &mode_lib->vba.DestinationLinesToRequestVMInImmediateFlip[k],
2294 &mode_lib->vba.DestinationLinesToRequestRowInImmediateFlip[k],
2295 &final_flip_bw[k],
2296 &mode_lib->vba.ImmediateFlipSupportedForPipe[k]);
2297 }
2298 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2299 total_dcn_read_bw_with_flip =
2300 total_dcn_read_bw_with_flip
2301 + mode_lib->vba.cursor_bw[k]
2302 + dml_max(
2303 mode_lib->vba.prefetch_vm_bw[k],
2304 dml_max(
2305 mode_lib->vba.prefetch_row_bw[k],
2306 final_flip_bw[k]
2307 + dml_max(
2308 mode_lib->vba.ReadBandwidthPlaneLuma[k]
2309 + mode_lib->vba.ReadBandwidthPlaneChroma[k],
2310 mode_lib->vba.RequiredPrefetchPixDataBWLuma[k])));
2311 }
2312 mode_lib->vba.ImmediateFlipSupported = true;
2313 if (total_dcn_read_bw_with_flip > mode_lib->vba.ReturnBW) {
2314 mode_lib->vba.ImmediateFlipSupported = false;
2315 }
2316 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2317 if (mode_lib->vba.ImmediateFlipSupportedForPipe[k] == false) {
2318 mode_lib->vba.ImmediateFlipSupported = false;
2319 }
2320 }
2321 } else {
2322 mode_lib->vba.ImmediateFlipSupported = false;
2323 }
2324
2325 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2326 if (mode_lib->vba.ErrorResult[k]) {
2327 mode_lib->vba.PrefetchModeSupported = false;
2328 dml_print(
2329 "DML: CalculatePrefetchSchedule ***failed***. Prefetch schedule violation. Results are NOT valid\n");
2330 }
2331 }
2332
2333 mode_lib->vba.VStartupLines = mode_lib->vba.VStartupLines + 1;
2334 } while (!((mode_lib->vba.PrefetchModeSupported
2335 && (!mode_lib->vba.ImmediateFlipSupport
2336 || mode_lib->vba.ImmediateFlipSupported))
2337 || mode_lib->vba.MaximumMaxVStartupLines < mode_lib->vba.VStartupLines));
2338
2339 //Display Pipeline Delivery Time in Prefetch
2340 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2341 if (mode_lib->vba.VRatioPrefetchY[k] <= 1) {
2342 mode_lib->vba.DisplayPipeLineDeliveryTimeLumaPrefetch[k] =
2343 mode_lib->vba.SwathWidthY[k] * mode_lib->vba.DPPPerPlane[k]
2344 / mode_lib->vba.HRatio[k]
2345 / mode_lib->vba.PixelClock[k];
2346 } else {
2347 mode_lib->vba.DisplayPipeLineDeliveryTimeLumaPrefetch[k] =
2348 mode_lib->vba.SwathWidthY[k]
2349 / mode_lib->vba.PSCL_THROUGHPUT_LUMA[k]
2350 / mode_lib->vba.DPPCLK[k];
2351 }
2352 if (mode_lib->vba.BytePerPixelDETC[k] == 0) {
2353 mode_lib->vba.DisplayPipeLineDeliveryTimeChromaPrefetch[k] = 0;
2354 } else {
2355 if (mode_lib->vba.VRatioPrefetchC[k] <= 1) {
2356 mode_lib->vba.DisplayPipeLineDeliveryTimeChromaPrefetch[k] =
2357 mode_lib->vba.SwathWidthY[k]
2358 * mode_lib->vba.DPPPerPlane[k]
2359 / mode_lib->vba.HRatio[k]
2360 / mode_lib->vba.PixelClock[k];
2361 } else {
2362 mode_lib->vba.DisplayPipeLineDeliveryTimeChromaPrefetch[k] =
2363 mode_lib->vba.SwathWidthY[k]
2364 / mode_lib->vba.PSCL_THROUGHPUT_LUMA[k]
2365 / mode_lib->vba.DPPCLK[k];
2366 }
2367 }
2368 }
2369
2370 // Min TTUVBlank
2371 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2372 if (mode_lib->vba.PrefetchMode[mode_lib->vba.VoltageLevel][mode_lib->vba.maxMpcComb] == 0) {
2373 mode_lib->vba.AllowDRAMClockChangeDuringVBlank[k] = true;
2374 mode_lib->vba.AllowDRAMSelfRefreshDuringVBlank[k] = true;
2375 mode_lib->vba.MinTTUVBlank[k] = dml_max(
2376 mode_lib->vba.DRAMClockChangeWatermark,
2377 dml_max(
2378 mode_lib->vba.StutterEnterPlusExitWatermark,
2379 mode_lib->vba.UrgentWatermark));
2380 } else if (mode_lib->vba.PrefetchMode[mode_lib->vba.VoltageLevel][mode_lib->vba.maxMpcComb] == 1) {
2381 mode_lib->vba.AllowDRAMClockChangeDuringVBlank[k] = false;
2382 mode_lib->vba.AllowDRAMSelfRefreshDuringVBlank[k] = true;
2383 mode_lib->vba.MinTTUVBlank[k] = dml_max(
2384 mode_lib->vba.StutterEnterPlusExitWatermark,
2385 mode_lib->vba.UrgentWatermark);
2386 } else {
2387 mode_lib->vba.AllowDRAMClockChangeDuringVBlank[k] = false;
2388 mode_lib->vba.AllowDRAMSelfRefreshDuringVBlank[k] = false;
2389 mode_lib->vba.MinTTUVBlank[k] = mode_lib->vba.UrgentWatermark;
2390 }
2391 if (!mode_lib->vba.DynamicMetadataEnable[k])
2392 mode_lib->vba.MinTTUVBlank[k] = mode_lib->vba.TCalc
2393 + mode_lib->vba.MinTTUVBlank[k];
2394 }
2395
2396 // DCC Configuration
2397 mode_lib->vba.ActiveDPPs = 0;
2398 // NB P-State/DRAM Clock Change Support
2399 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2400 mode_lib->vba.ActiveDPPs = mode_lib->vba.ActiveDPPs + mode_lib->vba.DPPPerPlane[k];
2401 }
2402
2403 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2404 double EffectiveLBLatencyHidingY;
2405 double EffectiveLBLatencyHidingC;
2406 double DPPOutputBufferLinesY;
2407 double DPPOutputBufferLinesC;
2408 double DPPOPPBufferingY;
2409 double MaxDETBufferingTimeY;
2410 double ActiveDRAMClockChangeLatencyMarginY;
2411
2412 mode_lib->vba.LBLatencyHidingSourceLinesY =
2413 dml_min(
2414 mode_lib->vba.MaxLineBufferLines,
2415 (unsigned int) dml_floor(
2416 (double) mode_lib->vba.LineBufferSize
2417 / mode_lib->vba.LBBitPerPixel[k]
2418 / (mode_lib->vba.SwathWidthY[k]
2419 / dml_max(
2420 mode_lib->vba.HRatio[k],
2421 1.0)),
2422 1)) - (mode_lib->vba.vtaps[k] - 1);
2423
2424 mode_lib->vba.LBLatencyHidingSourceLinesC =
2425 dml_min(
2426 mode_lib->vba.MaxLineBufferLines,
2427 (unsigned int) dml_floor(
2428 (double) mode_lib->vba.LineBufferSize
2429 / mode_lib->vba.LBBitPerPixel[k]
2430 / (mode_lib->vba.SwathWidthY[k]
2431 / 2.0
2432 / dml_max(
2433 mode_lib->vba.HRatio[k]
2434 / 2,
2435 1.0)),
2436 1))
2437 - (mode_lib->vba.VTAPsChroma[k] - 1);
2438
2439 EffectiveLBLatencyHidingY = mode_lib->vba.LBLatencyHidingSourceLinesY
2440 / mode_lib->vba.VRatio[k]
2441 * (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k]);
2442
2443 EffectiveLBLatencyHidingC = mode_lib->vba.LBLatencyHidingSourceLinesC
2444 / (mode_lib->vba.VRatio[k] / 2)
2445 * (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k]);
2446
2447 if (mode_lib->vba.SwathWidthY[k] > 2 * mode_lib->vba.DPPOutputBufferPixels) {
2448 DPPOutputBufferLinesY = mode_lib->vba.DPPOutputBufferPixels
2449 / mode_lib->vba.SwathWidthY[k];
2450 } else if (mode_lib->vba.SwathWidthY[k] > mode_lib->vba.DPPOutputBufferPixels) {
2451 DPPOutputBufferLinesY = 0.5;
2452 } else {
2453 DPPOutputBufferLinesY = 1;
2454 }
2455
2456 if (mode_lib->vba.SwathWidthY[k] / 2 > 2 * mode_lib->vba.DPPOutputBufferPixels) {
2457 DPPOutputBufferLinesC = mode_lib->vba.DPPOutputBufferPixels
2458 / (mode_lib->vba.SwathWidthY[k] / 2);
2459 } else if (mode_lib->vba.SwathWidthY[k] / 2 > mode_lib->vba.DPPOutputBufferPixels) {
2460 DPPOutputBufferLinesC = 0.5;
2461 } else {
2462 DPPOutputBufferLinesC = 1;
2463 }
2464
2465 DPPOPPBufferingY = (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k])
2466 * (DPPOutputBufferLinesY + mode_lib->vba.OPPOutputBufferLines);
2467 MaxDETBufferingTimeY = mode_lib->vba.FullDETBufferingTimeY[k]
2468 + (mode_lib->vba.LinesInDETY[k]
2469 - mode_lib->vba.LinesInDETYRoundedDownToSwath[k])
2470 / mode_lib->vba.SwathHeightY[k]
2471 * (mode_lib->vba.HTotal[k]
2472 / mode_lib->vba.PixelClock[k]);
2473
2474 ActiveDRAMClockChangeLatencyMarginY = DPPOPPBufferingY + EffectiveLBLatencyHidingY
2475 + MaxDETBufferingTimeY - mode_lib->vba.DRAMClockChangeWatermark;
2476
2477 if (mode_lib->vba.ActiveDPPs > 1) {
2478 ActiveDRAMClockChangeLatencyMarginY =
2479 ActiveDRAMClockChangeLatencyMarginY
2480 - (1 - 1 / (mode_lib->vba.ActiveDPPs - 1))
2481 * mode_lib->vba.SwathHeightY[k]
2482 * (mode_lib->vba.HTotal[k]
2483 / mode_lib->vba.PixelClock[k]);
2484 }
2485
2486 if (mode_lib->vba.BytePerPixelDETC[k] > 0) {
2487 double DPPOPPBufferingC = (mode_lib->vba.HTotal[k]
2488 / mode_lib->vba.PixelClock[k])
2489 * (DPPOutputBufferLinesC
2490 + mode_lib->vba.OPPOutputBufferLines);
2491 double MaxDETBufferingTimeC =
2492 mode_lib->vba.FullDETBufferingTimeC[k]
2493 + (mode_lib->vba.LinesInDETC[k]
2494 - mode_lib->vba.LinesInDETCRoundedDownToSwath[k])
2495 / mode_lib->vba.SwathHeightC[k]
2496 * (mode_lib->vba.HTotal[k]
2497 / mode_lib->vba.PixelClock[k]);
2498 double ActiveDRAMClockChangeLatencyMarginC = DPPOPPBufferingC
2499 + EffectiveLBLatencyHidingC + MaxDETBufferingTimeC
2500 - mode_lib->vba.DRAMClockChangeWatermark;
2501
2502 if (mode_lib->vba.ActiveDPPs > 1) {
2503 ActiveDRAMClockChangeLatencyMarginC =
2504 ActiveDRAMClockChangeLatencyMarginC
2505 - (1
2506 - 1
2507 / (mode_lib->vba.ActiveDPPs
2508 - 1))
2509 * mode_lib->vba.SwathHeightC[k]
2510 * (mode_lib->vba.HTotal[k]
2511 / mode_lib->vba.PixelClock[k]);
2512 }
2513 mode_lib->vba.ActiveDRAMClockChangeLatencyMargin[k] = dml_min(
2514 ActiveDRAMClockChangeLatencyMarginY,
2515 ActiveDRAMClockChangeLatencyMarginC);
2516 } else {
2517 mode_lib->vba.ActiveDRAMClockChangeLatencyMargin[k] =
2518 ActiveDRAMClockChangeLatencyMarginY;
2519 }
2520
2521 if (mode_lib->vba.WritebackEnable[k]) {
2522 double WritebackDRAMClockChangeLatencyMargin;
2523
2524 if (mode_lib->vba.WritebackPixelFormat[k] == dm_444_32) {
2525 WritebackDRAMClockChangeLatencyMargin =
2526 (double) (mode_lib->vba.WritebackInterfaceLumaBufferSize
2527 + mode_lib->vba.WritebackInterfaceChromaBufferSize)
2528 / (mode_lib->vba.WritebackDestinationWidth[k]
2529 * mode_lib->vba.WritebackDestinationHeight[k]
2530 / (mode_lib->vba.WritebackSourceHeight[k]
2531 * mode_lib->vba.HTotal[k]
2532 / mode_lib->vba.PixelClock[k])
2533 * 4)
2534 - mode_lib->vba.WritebackDRAMClockChangeWatermark;
2535 } else if (mode_lib->vba.WritebackPixelFormat[k] == dm_420_10) {
2536 WritebackDRAMClockChangeLatencyMargin =
2537 dml_min(
2538 (double) mode_lib->vba.WritebackInterfaceLumaBufferSize
2539 * 8.0 / 10,
2540 2.0
2541 * mode_lib->vba.WritebackInterfaceChromaBufferSize
2542 * 8 / 10)
2543 / (mode_lib->vba.WritebackDestinationWidth[k]
2544 * mode_lib->vba.WritebackDestinationHeight[k]
2545 / (mode_lib->vba.WritebackSourceHeight[k]
2546 * mode_lib->vba.HTotal[k]
2547 / mode_lib->vba.PixelClock[k]))
2548 - mode_lib->vba.WritebackDRAMClockChangeWatermark;
2549 } else {
2550 WritebackDRAMClockChangeLatencyMargin =
2551 dml_min(
2552 (double) mode_lib->vba.WritebackInterfaceLumaBufferSize,
2553 2.0
2554 * mode_lib->vba.WritebackInterfaceChromaBufferSize)
2555 / (mode_lib->vba.WritebackDestinationWidth[k]
2556 * mode_lib->vba.WritebackDestinationHeight[k]
2557 / (mode_lib->vba.WritebackSourceHeight[k]
2558 * mode_lib->vba.HTotal[k]
2559 / mode_lib->vba.PixelClock[k]))
2560 - mode_lib->vba.WritebackDRAMClockChangeWatermark;
2561 }
2562 mode_lib->vba.ActiveDRAMClockChangeLatencyMargin[k] = dml_min(
2563 mode_lib->vba.ActiveDRAMClockChangeLatencyMargin[k],
2564 WritebackDRAMClockChangeLatencyMargin);
2565 }
2566 }
2567
2568 mode_lib->vba.MinActiveDRAMClockChangeMargin = 999999;
2569 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2570 if (mode_lib->vba.ActiveDRAMClockChangeLatencyMargin[k]
2571 < mode_lib->vba.MinActiveDRAMClockChangeMargin) {
2572 mode_lib->vba.MinActiveDRAMClockChangeMargin =
2573 mode_lib->vba.ActiveDRAMClockChangeLatencyMargin[k];
2574 }
2575 }
2576
2577 mode_lib->vba.MinActiveDRAMClockChangeLatencySupported =
2578 mode_lib->vba.MinActiveDRAMClockChangeMargin
2579 + mode_lib->vba.DRAMClockChangeLatency;
2580
2581 if (mode_lib->vba.DRAMClockChangeSupportsVActive &&
2582 mode_lib->vba.MinActiveDRAMClockChangeMargin > 60) {
2583 mode_lib->vba.DRAMClockChangeWatermark += 25;
2584 mode_lib->vba.DRAMClockChangeSupport[0][0] = dm_dram_clock_change_vactive;
2585 } else {
2586 if (mode_lib->vba.SynchronizedVBlank || mode_lib->vba.NumberOfActivePlanes == 1) {
2587 mode_lib->vba.DRAMClockChangeSupport[0][0] = dm_dram_clock_change_vblank;
2588 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2589 if (!mode_lib->vba.AllowDRAMClockChangeDuringVBlank[k]) {
2590 mode_lib->vba.DRAMClockChangeSupport[0][0] =
2591 dm_dram_clock_change_unsupported;
2592 }
2593 }
2594 } else {
2595 mode_lib->vba.DRAMClockChangeSupport[0][0] = dm_dram_clock_change_unsupported;
2596 }
2597 }
2598 for (k = 0; k <= mode_lib->vba.soc.num_states; k++)
2599 for (j = 0; j < 2; j++)
2600 mode_lib->vba.DRAMClockChangeSupport[k][j] = mode_lib->vba.DRAMClockChangeSupport[0][0];
2601
2602 //XFC Parameters:
2603 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2604 if (mode_lib->vba.XFCEnabled[k] == true) {
2605 double TWait;
2606
2607 mode_lib->vba.XFCSlaveVUpdateOffset[k] = mode_lib->vba.XFCTSlvVupdateOffset;
2608 mode_lib->vba.XFCSlaveVupdateWidth[k] = mode_lib->vba.XFCTSlvVupdateWidth;
2609 mode_lib->vba.XFCSlaveVReadyOffset[k] = mode_lib->vba.XFCTSlvVreadyOffset;
2610 TWait = CalculateTWait(
2611 mode_lib->vba.PrefetchMode[mode_lib->vba.VoltageLevel][mode_lib->vba.maxMpcComb],
2612 mode_lib->vba.DRAMClockChangeLatency,
2613 mode_lib->vba.UrgentLatencyPixelDataOnly,
2614 mode_lib->vba.SREnterPlusExitTime);
2615 mode_lib->vba.XFCRemoteSurfaceFlipDelay = CalculateRemoteSurfaceFlipDelay(
2616 mode_lib,
2617 mode_lib->vba.VRatio[k],
2618 mode_lib->vba.SwathWidthY[k],
2619 dml_ceil(mode_lib->vba.BytePerPixelDETY[k], 1),
2620 mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k],
2621 mode_lib->vba.XFCTSlvVupdateOffset,
2622 mode_lib->vba.XFCTSlvVupdateWidth,
2623 mode_lib->vba.XFCTSlvVreadyOffset,
2624 mode_lib->vba.XFCXBUFLatencyTolerance,
2625 mode_lib->vba.XFCFillBWOverhead,
2626 mode_lib->vba.XFCSlvChunkSize,
2627 mode_lib->vba.XFCBusTransportTime,
2628 mode_lib->vba.TCalc,
2629 TWait,
2630 &mode_lib->vba.SrcActiveDrainRate,
2631 &mode_lib->vba.TInitXFill,
2632 &mode_lib->vba.TslvChk);
2633 mode_lib->vba.XFCRemoteSurfaceFlipLatency[k] =
2634 dml_floor(
2635 mode_lib->vba.XFCRemoteSurfaceFlipDelay
2636 / (mode_lib->vba.HTotal[k]
2637 / mode_lib->vba.PixelClock[k]),
2638 1);
2639 mode_lib->vba.XFCTransferDelay[k] =
2640 dml_ceil(
2641 mode_lib->vba.XFCBusTransportTime
2642 / (mode_lib->vba.HTotal[k]
2643 / mode_lib->vba.PixelClock[k]),
2644 1);
2645 mode_lib->vba.XFCPrechargeDelay[k] =
2646 dml_ceil(
2647 (mode_lib->vba.XFCBusTransportTime
2648 + mode_lib->vba.TInitXFill
2649 + mode_lib->vba.TslvChk)
2650 / (mode_lib->vba.HTotal[k]
2651 / mode_lib->vba.PixelClock[k]),
2652 1);
2653 mode_lib->vba.InitFillLevel = mode_lib->vba.XFCXBUFLatencyTolerance
2654 * mode_lib->vba.SrcActiveDrainRate;
2655 mode_lib->vba.FinalFillMargin =
2656 (mode_lib->vba.DestinationLinesToRequestVMInVBlank[k]
2657 + mode_lib->vba.DestinationLinesToRequestRowInVBlank[k])
2658 * mode_lib->vba.HTotal[k]
2659 / mode_lib->vba.PixelClock[k]
2660 * mode_lib->vba.SrcActiveDrainRate
2661 + mode_lib->vba.XFCFillConstant;
2662 mode_lib->vba.FinalFillLevel = mode_lib->vba.XFCRemoteSurfaceFlipDelay
2663 * mode_lib->vba.SrcActiveDrainRate
2664 + mode_lib->vba.FinalFillMargin;
2665 mode_lib->vba.RemainingFillLevel = dml_max(
2666 0.0,
2667 mode_lib->vba.FinalFillLevel - mode_lib->vba.InitFillLevel);
2668 mode_lib->vba.TFinalxFill = mode_lib->vba.RemainingFillLevel
2669 / (mode_lib->vba.SrcActiveDrainRate
2670 * mode_lib->vba.XFCFillBWOverhead / 100);
2671 mode_lib->vba.XFCPrefetchMargin[k] =
2672 mode_lib->vba.XFCRemoteSurfaceFlipDelay
2673 + mode_lib->vba.TFinalxFill
2674 + (mode_lib->vba.DestinationLinesToRequestVMInVBlank[k]
2675 + mode_lib->vba.DestinationLinesToRequestRowInVBlank[k])
2676 * mode_lib->vba.HTotal[k]
2677 / mode_lib->vba.PixelClock[k];
2678 } else {
2679 mode_lib->vba.XFCSlaveVUpdateOffset[k] = 0;
2680 mode_lib->vba.XFCSlaveVupdateWidth[k] = 0;
2681 mode_lib->vba.XFCSlaveVReadyOffset[k] = 0;
2682 mode_lib->vba.XFCRemoteSurfaceFlipLatency[k] = 0;
2683 mode_lib->vba.XFCPrechargeDelay[k] = 0;
2684 mode_lib->vba.XFCTransferDelay[k] = 0;
2685 mode_lib->vba.XFCPrefetchMargin[k] = 0;
2686 }
2687 }
2688 {
2689 unsigned int VStartupMargin = 0;
2690 bool FirstMainPlane = true;
2691
2692 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2693 if (mode_lib->vba.BlendingAndTiming[k] == k) {
2694 unsigned int Margin = (mode_lib->vba.MaxVStartupLines[k] - mode_lib->vba.VStartup[k])
2695 * mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k];
2696
2697 if (FirstMainPlane) {
2698 VStartupMargin = Margin;
2699 FirstMainPlane = false;
2700 } else
2701 VStartupMargin = dml_min(VStartupMargin, Margin);
2702 }
2703
2704 if (mode_lib->vba.UseMaximumVStartup) {
2705 if (mode_lib->vba.VTotal_Max[k] == mode_lib->vba.VTotal[k]) {
2706 //only use max vstart if it is not drr or lateflip.
2707 mode_lib->vba.VStartup[k] = mode_lib->vba.MaxVStartupLines[mode_lib->vba.BlendingAndTiming[k]];
2708 }
2709 }
2710 }
2711 }
2712 }
2713
dml20_DisplayPipeConfiguration(struct display_mode_lib * mode_lib)2714 static void dml20_DisplayPipeConfiguration(struct display_mode_lib *mode_lib)
2715 {
2716 double BytePerPixDETY;
2717 double BytePerPixDETC;
2718 double Read256BytesBlockHeightY;
2719 double Read256BytesBlockHeightC;
2720 double Read256BytesBlockWidthY;
2721 double Read256BytesBlockWidthC;
2722 double MaximumSwathHeightY;
2723 double MaximumSwathHeightC;
2724 double MinimumSwathHeightY;
2725 double MinimumSwathHeightC;
2726 double SwathWidth;
2727 double SwathWidthGranularityY;
2728 double SwathWidthGranularityC;
2729 double RoundedUpMaxSwathSizeBytesY;
2730 double RoundedUpMaxSwathSizeBytesC;
2731 unsigned int j, k;
2732
2733 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
2734 bool MainPlaneDoesODMCombine = false;
2735
2736 if (mode_lib->vba.SourcePixelFormat[k] == dm_444_64) {
2737 BytePerPixDETY = 8;
2738 BytePerPixDETC = 0;
2739 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_32) {
2740 BytePerPixDETY = 4;
2741 BytePerPixDETC = 0;
2742 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_16) {
2743 BytePerPixDETY = 2;
2744 BytePerPixDETC = 0;
2745 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_8) {
2746 BytePerPixDETY = 1;
2747 BytePerPixDETC = 0;
2748 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_8) {
2749 BytePerPixDETY = 1;
2750 BytePerPixDETC = 2;
2751 } else {
2752 BytePerPixDETY = 4.0 / 3.0;
2753 BytePerPixDETC = 8.0 / 3.0;
2754 }
2755
2756 if ((mode_lib->vba.SourcePixelFormat[k] == dm_444_64
2757 || mode_lib->vba.SourcePixelFormat[k] == dm_444_32
2758 || mode_lib->vba.SourcePixelFormat[k] == dm_444_16
2759 || mode_lib->vba.SourcePixelFormat[k] == dm_444_8)) {
2760 if (mode_lib->vba.SurfaceTiling[k] == dm_sw_linear) {
2761 Read256BytesBlockHeightY = 1;
2762 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_64) {
2763 Read256BytesBlockHeightY = 4;
2764 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_32
2765 || mode_lib->vba.SourcePixelFormat[k] == dm_444_16) {
2766 Read256BytesBlockHeightY = 8;
2767 } else {
2768 Read256BytesBlockHeightY = 16;
2769 }
2770 Read256BytesBlockWidthY = 256 / dml_ceil(BytePerPixDETY, 1)
2771 / Read256BytesBlockHeightY;
2772 Read256BytesBlockHeightC = 0;
2773 Read256BytesBlockWidthC = 0;
2774 } else {
2775 if (mode_lib->vba.SurfaceTiling[k] == dm_sw_linear) {
2776 Read256BytesBlockHeightY = 1;
2777 Read256BytesBlockHeightC = 1;
2778 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_8) {
2779 Read256BytesBlockHeightY = 16;
2780 Read256BytesBlockHeightC = 8;
2781 } else {
2782 Read256BytesBlockHeightY = 8;
2783 Read256BytesBlockHeightC = 8;
2784 }
2785 Read256BytesBlockWidthY = 256 / dml_ceil(BytePerPixDETY, 1)
2786 / Read256BytesBlockHeightY;
2787 Read256BytesBlockWidthC = 256 / dml_ceil(BytePerPixDETC, 2)
2788 / Read256BytesBlockHeightC;
2789 }
2790
2791 if (mode_lib->vba.SourceScan[k] == dm_horz) {
2792 MaximumSwathHeightY = Read256BytesBlockHeightY;
2793 MaximumSwathHeightC = Read256BytesBlockHeightC;
2794 } else {
2795 MaximumSwathHeightY = Read256BytesBlockWidthY;
2796 MaximumSwathHeightC = Read256BytesBlockWidthC;
2797 }
2798
2799 if ((mode_lib->vba.SourcePixelFormat[k] == dm_444_64
2800 || mode_lib->vba.SourcePixelFormat[k] == dm_444_32
2801 || mode_lib->vba.SourcePixelFormat[k] == dm_444_16
2802 || mode_lib->vba.SourcePixelFormat[k] == dm_444_8)) {
2803 if (mode_lib->vba.SurfaceTiling[k] == dm_sw_linear
2804 || (mode_lib->vba.SourcePixelFormat[k] == dm_444_64
2805 && (mode_lib->vba.SurfaceTiling[k]
2806 == dm_sw_4kb_s
2807 || mode_lib->vba.SurfaceTiling[k]
2808 == dm_sw_4kb_s_x
2809 || mode_lib->vba.SurfaceTiling[k]
2810 == dm_sw_64kb_s
2811 || mode_lib->vba.SurfaceTiling[k]
2812 == dm_sw_64kb_s_t
2813 || mode_lib->vba.SurfaceTiling[k]
2814 == dm_sw_64kb_s_x
2815 || mode_lib->vba.SurfaceTiling[k]
2816 == dm_sw_var_s
2817 || mode_lib->vba.SurfaceTiling[k]
2818 == dm_sw_var_s_x)
2819 && mode_lib->vba.SourceScan[k] == dm_horz)) {
2820 MinimumSwathHeightY = MaximumSwathHeightY;
2821 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_8
2822 && mode_lib->vba.SourceScan[k] != dm_horz) {
2823 MinimumSwathHeightY = MaximumSwathHeightY;
2824 } else {
2825 MinimumSwathHeightY = MaximumSwathHeightY / 2.0;
2826 }
2827 MinimumSwathHeightC = MaximumSwathHeightC;
2828 } else {
2829 if (mode_lib->vba.SurfaceTiling[k] == dm_sw_linear) {
2830 MinimumSwathHeightY = MaximumSwathHeightY;
2831 MinimumSwathHeightC = MaximumSwathHeightC;
2832 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_8
2833 && mode_lib->vba.SourceScan[k] == dm_horz) {
2834 MinimumSwathHeightY = MaximumSwathHeightY / 2.0;
2835 MinimumSwathHeightC = MaximumSwathHeightC;
2836 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_10
2837 && mode_lib->vba.SourceScan[k] == dm_horz) {
2838 MinimumSwathHeightC = MaximumSwathHeightC / 2.0;
2839 MinimumSwathHeightY = MaximumSwathHeightY;
2840 } else {
2841 MinimumSwathHeightY = MaximumSwathHeightY;
2842 MinimumSwathHeightC = MaximumSwathHeightC;
2843 }
2844 }
2845
2846 if (mode_lib->vba.SourceScan[k] == dm_horz) {
2847 SwathWidth = mode_lib->vba.ViewportWidth[k];
2848 } else {
2849 SwathWidth = mode_lib->vba.ViewportHeight[k];
2850 }
2851
2852 if (mode_lib->vba.ODMCombineEnabled[k] == dm_odm_combine_mode_2to1) {
2853 MainPlaneDoesODMCombine = true;
2854 }
2855 for (j = 0; j < mode_lib->vba.NumberOfActivePlanes; ++j) {
2856 if (mode_lib->vba.BlendingAndTiming[k] == j
2857 && mode_lib->vba.ODMCombineEnabled[k] == dm_odm_combine_mode_2to1) {
2858 MainPlaneDoesODMCombine = true;
2859 }
2860 }
2861
2862 if (MainPlaneDoesODMCombine == true) {
2863 SwathWidth = dml_min(
2864 SwathWidth,
2865 mode_lib->vba.HActive[k] / 2.0 * mode_lib->vba.HRatio[k]);
2866 } else {
2867 if (mode_lib->vba.DPPPerPlane[k] == 0)
2868 SwathWidth = 0;
2869 else
2870 SwathWidth = SwathWidth / mode_lib->vba.DPPPerPlane[k];
2871 }
2872
2873 SwathWidthGranularityY = 256 / dml_ceil(BytePerPixDETY, 1) / MaximumSwathHeightY;
2874 RoundedUpMaxSwathSizeBytesY = (dml_ceil(
2875 (double) (SwathWidth - 1),
2876 SwathWidthGranularityY) + SwathWidthGranularityY) * BytePerPixDETY
2877 * MaximumSwathHeightY;
2878 if (mode_lib->vba.SourcePixelFormat[k] == dm_420_10) {
2879 RoundedUpMaxSwathSizeBytesY = dml_ceil(RoundedUpMaxSwathSizeBytesY, 256)
2880 + 256;
2881 }
2882 if (MaximumSwathHeightC > 0) {
2883 SwathWidthGranularityC = 256.0 / dml_ceil(BytePerPixDETC, 2)
2884 / MaximumSwathHeightC;
2885 RoundedUpMaxSwathSizeBytesC = (dml_ceil(
2886 (double) (SwathWidth / 2.0 - 1),
2887 SwathWidthGranularityC) + SwathWidthGranularityC)
2888 * BytePerPixDETC * MaximumSwathHeightC;
2889 if (mode_lib->vba.SourcePixelFormat[k] == dm_420_10) {
2890 RoundedUpMaxSwathSizeBytesC = dml_ceil(
2891 RoundedUpMaxSwathSizeBytesC,
2892 256) + 256;
2893 }
2894 } else
2895 RoundedUpMaxSwathSizeBytesC = 0.0;
2896
2897 if (RoundedUpMaxSwathSizeBytesY + RoundedUpMaxSwathSizeBytesC
2898 <= mode_lib->vba.DETBufferSizeInKByte[0] * 1024.0 / 2.0) {
2899 mode_lib->vba.SwathHeightY[k] = MaximumSwathHeightY;
2900 mode_lib->vba.SwathHeightC[k] = MaximumSwathHeightC;
2901 } else {
2902 mode_lib->vba.SwathHeightY[k] = MinimumSwathHeightY;
2903 mode_lib->vba.SwathHeightC[k] = MinimumSwathHeightC;
2904 }
2905
2906 if (mode_lib->vba.SwathHeightC[k] == 0) {
2907 mode_lib->vba.DETBufferSizeY[k] = mode_lib->vba.DETBufferSizeInKByte[0] * 1024;
2908 mode_lib->vba.DETBufferSizeC[k] = 0;
2909 } else if (mode_lib->vba.SwathHeightY[k] <= mode_lib->vba.SwathHeightC[k]) {
2910 mode_lib->vba.DETBufferSizeY[k] = mode_lib->vba.DETBufferSizeInKByte[0]
2911 * 1024.0 / 2;
2912 mode_lib->vba.DETBufferSizeC[k] = mode_lib->vba.DETBufferSizeInKByte[0]
2913 * 1024.0 / 2;
2914 } else {
2915 mode_lib->vba.DETBufferSizeY[k] = mode_lib->vba.DETBufferSizeInKByte[0]
2916 * 1024.0 * 2 / 3;
2917 mode_lib->vba.DETBufferSizeC[k] = mode_lib->vba.DETBufferSizeInKByte[0]
2918 * 1024.0 / 3;
2919 }
2920 }
2921 }
2922
CalculateTWait(unsigned int PrefetchMode,double DRAMClockChangeLatency,double UrgentLatencyPixelDataOnly,double SREnterPlusExitTime)2923 static double CalculateTWait(
2924 unsigned int PrefetchMode,
2925 double DRAMClockChangeLatency,
2926 double UrgentLatencyPixelDataOnly,
2927 double SREnterPlusExitTime)
2928 {
2929 if (PrefetchMode == 0) {
2930 return dml_max(
2931 DRAMClockChangeLatency + UrgentLatencyPixelDataOnly,
2932 dml_max(SREnterPlusExitTime, UrgentLatencyPixelDataOnly));
2933 } else if (PrefetchMode == 1) {
2934 return dml_max(SREnterPlusExitTime, UrgentLatencyPixelDataOnly);
2935 } else {
2936 return UrgentLatencyPixelDataOnly;
2937 }
2938 }
2939
CalculateRemoteSurfaceFlipDelay(struct display_mode_lib * mode_lib,double VRatio,double SwathWidth,double Bpp,double LineTime,double XFCTSlvVupdateOffset,double XFCTSlvVupdateWidth,double XFCTSlvVreadyOffset,double XFCXBUFLatencyTolerance,double XFCFillBWOverhead,double XFCSlvChunkSize,double XFCBusTransportTime,double TCalc,double TWait,double * SrcActiveDrainRate,double * TInitXFill,double * TslvChk)2940 static double CalculateRemoteSurfaceFlipDelay(
2941 struct display_mode_lib *mode_lib,
2942 double VRatio,
2943 double SwathWidth,
2944 double Bpp,
2945 double LineTime,
2946 double XFCTSlvVupdateOffset,
2947 double XFCTSlvVupdateWidth,
2948 double XFCTSlvVreadyOffset,
2949 double XFCXBUFLatencyTolerance,
2950 double XFCFillBWOverhead,
2951 double XFCSlvChunkSize,
2952 double XFCBusTransportTime,
2953 double TCalc,
2954 double TWait,
2955 double *SrcActiveDrainRate,
2956 double *TInitXFill,
2957 double *TslvChk)
2958 {
2959 double TSlvSetup, AvgfillRate, result;
2960
2961 *SrcActiveDrainRate = VRatio * SwathWidth * Bpp / LineTime;
2962 TSlvSetup = XFCTSlvVupdateOffset + XFCTSlvVupdateWidth + XFCTSlvVreadyOffset;
2963 *TInitXFill = XFCXBUFLatencyTolerance / (1 + XFCFillBWOverhead / 100);
2964 AvgfillRate = *SrcActiveDrainRate * (1 + XFCFillBWOverhead / 100);
2965 *TslvChk = XFCSlvChunkSize / AvgfillRate;
2966 dml_print(
2967 "DML::CalculateRemoteSurfaceFlipDelay: SrcActiveDrainRate: %f\n",
2968 *SrcActiveDrainRate);
2969 dml_print("DML::CalculateRemoteSurfaceFlipDelay: TSlvSetup: %f\n", TSlvSetup);
2970 dml_print("DML::CalculateRemoteSurfaceFlipDelay: TInitXFill: %f\n", *TInitXFill);
2971 dml_print("DML::CalculateRemoteSurfaceFlipDelay: AvgfillRate: %f\n", AvgfillRate);
2972 dml_print("DML::CalculateRemoteSurfaceFlipDelay: TslvChk: %f\n", *TslvChk);
2973 result = 2 * XFCBusTransportTime + TSlvSetup + TCalc + TWait + *TslvChk + *TInitXFill; // TODO: This doesn't seem to match programming guide
2974 dml_print("DML::CalculateRemoteSurfaceFlipDelay: RemoteSurfaceFlipDelay: %f\n", result);
2975 return result;
2976 }
2977
CalculateWriteBackDelay(enum source_format_class WritebackPixelFormat,double WritebackHRatio,double WritebackVRatio,unsigned int WritebackLumaHTaps,unsigned int WritebackLumaVTaps,unsigned int WritebackChromaHTaps,unsigned int WritebackChromaVTaps,unsigned int WritebackDestinationWidth)2978 static double CalculateWriteBackDelay(
2979 enum source_format_class WritebackPixelFormat,
2980 double WritebackHRatio,
2981 double WritebackVRatio,
2982 unsigned int WritebackLumaHTaps,
2983 unsigned int WritebackLumaVTaps,
2984 unsigned int WritebackChromaHTaps,
2985 unsigned int WritebackChromaVTaps,
2986 unsigned int WritebackDestinationWidth)
2987 {
2988 double CalculateWriteBackDelay =
2989 dml_max(
2990 dml_ceil(WritebackLumaHTaps / 4.0, 1) / WritebackHRatio,
2991 WritebackLumaVTaps * dml_ceil(1.0 / WritebackVRatio, 1)
2992 * dml_ceil(
2993 WritebackDestinationWidth
2994 / 4.0,
2995 1)
2996 + dml_ceil(1.0 / WritebackVRatio, 1)
2997 * (dml_ceil(
2998 WritebackLumaVTaps
2999 / 4.0,
3000 1) + 4));
3001
3002 if (WritebackPixelFormat != dm_444_32) {
3003 CalculateWriteBackDelay =
3004 dml_max(
3005 CalculateWriteBackDelay,
3006 dml_max(
3007 dml_ceil(
3008 WritebackChromaHTaps
3009 / 2.0,
3010 1)
3011 / (2
3012 * WritebackHRatio),
3013 WritebackChromaVTaps
3014 * dml_ceil(
3015 1
3016 / (2
3017 * WritebackVRatio),
3018 1)
3019 * dml_ceil(
3020 WritebackDestinationWidth
3021 / 2.0
3022 / 2.0,
3023 1)
3024 + dml_ceil(
3025 1
3026 / (2
3027 * WritebackVRatio),
3028 1)
3029 * (dml_ceil(
3030 WritebackChromaVTaps
3031 / 4.0,
3032 1)
3033 + 4)));
3034 }
3035 return CalculateWriteBackDelay;
3036 }
3037
CalculateActiveRowBandwidth(bool GPUVMEnable,enum source_format_class SourcePixelFormat,double VRatio,bool DCCEnable,double LineTime,unsigned int MetaRowByteLuma,unsigned int MetaRowByteChroma,unsigned int meta_row_height_luma,unsigned int meta_row_height_chroma,unsigned int PixelPTEBytesPerRowLuma,unsigned int PixelPTEBytesPerRowChroma,unsigned int dpte_row_height_luma,unsigned int dpte_row_height_chroma,double * meta_row_bw,double * dpte_row_bw,double * qual_row_bw)3038 static void CalculateActiveRowBandwidth(
3039 bool GPUVMEnable,
3040 enum source_format_class SourcePixelFormat,
3041 double VRatio,
3042 bool DCCEnable,
3043 double LineTime,
3044 unsigned int MetaRowByteLuma,
3045 unsigned int MetaRowByteChroma,
3046 unsigned int meta_row_height_luma,
3047 unsigned int meta_row_height_chroma,
3048 unsigned int PixelPTEBytesPerRowLuma,
3049 unsigned int PixelPTEBytesPerRowChroma,
3050 unsigned int dpte_row_height_luma,
3051 unsigned int dpte_row_height_chroma,
3052 double *meta_row_bw,
3053 double *dpte_row_bw,
3054 double *qual_row_bw)
3055 {
3056 if (DCCEnable != true) {
3057 *meta_row_bw = 0;
3058 } else if (SourcePixelFormat == dm_420_8 || SourcePixelFormat == dm_420_10) {
3059 *meta_row_bw = VRatio * MetaRowByteLuma / (meta_row_height_luma * LineTime)
3060 + VRatio / 2 * MetaRowByteChroma
3061 / (meta_row_height_chroma * LineTime);
3062 } else {
3063 *meta_row_bw = VRatio * MetaRowByteLuma / (meta_row_height_luma * LineTime);
3064 }
3065
3066 if (GPUVMEnable != true) {
3067 *dpte_row_bw = 0;
3068 } else if (SourcePixelFormat == dm_420_8 || SourcePixelFormat == dm_420_10) {
3069 *dpte_row_bw = VRatio * PixelPTEBytesPerRowLuma / (dpte_row_height_luma * LineTime)
3070 + VRatio / 2 * PixelPTEBytesPerRowChroma
3071 / (dpte_row_height_chroma * LineTime);
3072 } else {
3073 *dpte_row_bw = VRatio * PixelPTEBytesPerRowLuma / (dpte_row_height_luma * LineTime);
3074 }
3075
3076 if ((SourcePixelFormat == dm_420_8 || SourcePixelFormat == dm_420_10)) {
3077 *qual_row_bw = *meta_row_bw + *dpte_row_bw;
3078 } else {
3079 *qual_row_bw = 0;
3080 }
3081 }
3082
CalculateFlipSchedule(struct display_mode_lib * mode_lib,double UrgentExtraLatency,double UrgentLatencyPixelDataOnly,unsigned int GPUVMMaxPageTableLevels,bool GPUVMEnable,double BandwidthAvailableForImmediateFlip,unsigned int TotImmediateFlipBytes,enum source_format_class SourcePixelFormat,unsigned int ImmediateFlipBytes,double LineTime,double VRatio,double Tno_bw,double PDEAndMetaPTEBytesFrame,unsigned int MetaRowByte,unsigned int PixelPTEBytesPerRow,bool DCCEnable,unsigned int dpte_row_height,unsigned int meta_row_height,double qual_row_bw,double * DestinationLinesToRequestVMInImmediateFlip,double * DestinationLinesToRequestRowInImmediateFlip,double * final_flip_bw,bool * ImmediateFlipSupportedForPipe)3083 static void CalculateFlipSchedule(
3084 struct display_mode_lib *mode_lib,
3085 double UrgentExtraLatency,
3086 double UrgentLatencyPixelDataOnly,
3087 unsigned int GPUVMMaxPageTableLevels,
3088 bool GPUVMEnable,
3089 double BandwidthAvailableForImmediateFlip,
3090 unsigned int TotImmediateFlipBytes,
3091 enum source_format_class SourcePixelFormat,
3092 unsigned int ImmediateFlipBytes,
3093 double LineTime,
3094 double VRatio,
3095 double Tno_bw,
3096 double PDEAndMetaPTEBytesFrame,
3097 unsigned int MetaRowByte,
3098 unsigned int PixelPTEBytesPerRow,
3099 bool DCCEnable,
3100 unsigned int dpte_row_height,
3101 unsigned int meta_row_height,
3102 double qual_row_bw,
3103 double *DestinationLinesToRequestVMInImmediateFlip,
3104 double *DestinationLinesToRequestRowInImmediateFlip,
3105 double *final_flip_bw,
3106 bool *ImmediateFlipSupportedForPipe)
3107 {
3108 double min_row_time = 0.0;
3109
3110 if (SourcePixelFormat == dm_420_8 || SourcePixelFormat == dm_420_10) {
3111 *DestinationLinesToRequestVMInImmediateFlip = 0.0;
3112 *DestinationLinesToRequestRowInImmediateFlip = 0.0;
3113 *final_flip_bw = qual_row_bw;
3114 *ImmediateFlipSupportedForPipe = true;
3115 } else {
3116 double TimeForFetchingMetaPTEImmediateFlip;
3117 double TimeForFetchingRowInVBlankImmediateFlip;
3118
3119 if (GPUVMEnable == true) {
3120 mode_lib->vba.ImmediateFlipBW[0] = BandwidthAvailableForImmediateFlip
3121 * ImmediateFlipBytes / TotImmediateFlipBytes;
3122 TimeForFetchingMetaPTEImmediateFlip =
3123 dml_max(
3124 Tno_bw
3125 + PDEAndMetaPTEBytesFrame
3126 / mode_lib->vba.ImmediateFlipBW[0],
3127 dml_max(
3128 UrgentExtraLatency
3129 + UrgentLatencyPixelDataOnly
3130 * (GPUVMMaxPageTableLevels
3131 - 1),
3132 LineTime / 4.0));
3133 } else {
3134 TimeForFetchingMetaPTEImmediateFlip = 0;
3135 }
3136
3137 *DestinationLinesToRequestVMInImmediateFlip = dml_floor(
3138 4.0 * (TimeForFetchingMetaPTEImmediateFlip / LineTime + 0.125),
3139 1) / 4.0;
3140
3141 if ((GPUVMEnable || DCCEnable)) {
3142 mode_lib->vba.ImmediateFlipBW[0] = BandwidthAvailableForImmediateFlip
3143 * ImmediateFlipBytes / TotImmediateFlipBytes;
3144 TimeForFetchingRowInVBlankImmediateFlip = dml_max(
3145 (MetaRowByte + PixelPTEBytesPerRow)
3146 / mode_lib->vba.ImmediateFlipBW[0],
3147 dml_max(UrgentLatencyPixelDataOnly, LineTime / 4.0));
3148 } else {
3149 TimeForFetchingRowInVBlankImmediateFlip = 0;
3150 }
3151
3152 *DestinationLinesToRequestRowInImmediateFlip = dml_floor(
3153 4.0 * (TimeForFetchingRowInVBlankImmediateFlip / LineTime + 0.125),
3154 1) / 4.0;
3155
3156 if (GPUVMEnable == true) {
3157 *final_flip_bw =
3158 dml_max(
3159 PDEAndMetaPTEBytesFrame
3160 / (*DestinationLinesToRequestVMInImmediateFlip
3161 * LineTime),
3162 (MetaRowByte + PixelPTEBytesPerRow)
3163 / (TimeForFetchingRowInVBlankImmediateFlip
3164 * LineTime));
3165 } else if (MetaRowByte + PixelPTEBytesPerRow > 0) {
3166 *final_flip_bw = (MetaRowByte + PixelPTEBytesPerRow)
3167 / (TimeForFetchingRowInVBlankImmediateFlip * LineTime);
3168 } else {
3169 *final_flip_bw = 0;
3170 }
3171
3172 if (GPUVMEnable && !DCCEnable)
3173 min_row_time = dpte_row_height * LineTime / VRatio;
3174 else if (!GPUVMEnable && DCCEnable)
3175 min_row_time = meta_row_height * LineTime / VRatio;
3176 else
3177 min_row_time = dml_min(dpte_row_height, meta_row_height) * LineTime
3178 / VRatio;
3179
3180 if (*DestinationLinesToRequestVMInImmediateFlip >= 8
3181 || *DestinationLinesToRequestRowInImmediateFlip >= 16
3182 || TimeForFetchingMetaPTEImmediateFlip
3183 + 2 * TimeForFetchingRowInVBlankImmediateFlip
3184 > min_row_time)
3185 *ImmediateFlipSupportedForPipe = false;
3186 else
3187 *ImmediateFlipSupportedForPipe = true;
3188 }
3189 }
3190
TruncToValidBPP(double DecimalBPP,bool DSCEnabled,enum output_encoder_class Output,enum output_format_class Format,unsigned int DSCInputBitPerComponent)3191 static unsigned int TruncToValidBPP(
3192 double DecimalBPP,
3193 bool DSCEnabled,
3194 enum output_encoder_class Output,
3195 enum output_format_class Format,
3196 unsigned int DSCInputBitPerComponent)
3197 {
3198 if (Output == dm_hdmi) {
3199 if (Format == dm_420) {
3200 if (DecimalBPP >= 18)
3201 return 18;
3202 else if (DecimalBPP >= 15)
3203 return 15;
3204 else if (DecimalBPP >= 12)
3205 return 12;
3206 else
3207 return BPP_INVALID;
3208 } else if (Format == dm_444) {
3209 if (DecimalBPP >= 36)
3210 return 36;
3211 else if (DecimalBPP >= 30)
3212 return 30;
3213 else if (DecimalBPP >= 24)
3214 return 24;
3215 else if (DecimalBPP >= 18)
3216 return 18;
3217 else
3218 return BPP_INVALID;
3219 } else {
3220 if (DecimalBPP / 1.5 >= 24)
3221 return 24;
3222 else if (DecimalBPP / 1.5 >= 20)
3223 return 20;
3224 else if (DecimalBPP / 1.5 >= 16)
3225 return 16;
3226 else
3227 return BPP_INVALID;
3228 }
3229 } else {
3230 if (DSCEnabled) {
3231 if (Format == dm_420) {
3232 if (DecimalBPP < 6)
3233 return BPP_INVALID;
3234 else if (DecimalBPP >= 1.5 * DSCInputBitPerComponent - 1 / 16)
3235 return 1.5 * DSCInputBitPerComponent - 1 / 16;
3236 else
3237 return dml_floor(16 * DecimalBPP, 1) / 16;
3238 } else if (Format == dm_n422) {
3239 if (DecimalBPP < 7)
3240 return BPP_INVALID;
3241 else if (DecimalBPP >= 2 * DSCInputBitPerComponent - 1 / 16)
3242 return 2 * DSCInputBitPerComponent - 1 / 16;
3243 else
3244 return dml_floor(16 * DecimalBPP, 1) / 16;
3245 } else {
3246 if (DecimalBPP < 8)
3247 return BPP_INVALID;
3248 else if (DecimalBPP >= 3 * DSCInputBitPerComponent - 1 / 16)
3249 return 3 * DSCInputBitPerComponent - 1 / 16;
3250 else
3251 return dml_floor(16 * DecimalBPP, 1) / 16;
3252 }
3253 } else if (Format == dm_420) {
3254 if (DecimalBPP >= 18)
3255 return 18;
3256 else if (DecimalBPP >= 15)
3257 return 15;
3258 else if (DecimalBPP >= 12)
3259 return 12;
3260 else
3261 return BPP_INVALID;
3262 } else if (Format == dm_s422 || Format == dm_n422) {
3263 if (DecimalBPP >= 24)
3264 return 24;
3265 else if (DecimalBPP >= 20)
3266 return 20;
3267 else if (DecimalBPP >= 16)
3268 return 16;
3269 else
3270 return BPP_INVALID;
3271 } else {
3272 if (DecimalBPP >= 36)
3273 return 36;
3274 else if (DecimalBPP >= 30)
3275 return 30;
3276 else if (DecimalBPP >= 24)
3277 return 24;
3278 else if (DecimalBPP >= 18)
3279 return 18;
3280 else
3281 return BPP_INVALID;
3282 }
3283 }
3284 }
3285
dml20_ModeSupportAndSystemConfigurationFull(struct display_mode_lib * mode_lib)3286 void dml20_ModeSupportAndSystemConfigurationFull(struct display_mode_lib *mode_lib)
3287 {
3288 struct vba_vars_st *locals = &mode_lib->vba;
3289
3290 int i;
3291 unsigned int j, k, m;
3292
3293 /*MODE SUPPORT, VOLTAGE STATE AND SOC CONFIGURATION*/
3294
3295 /*Scale Ratio, taps Support Check*/
3296
3297 mode_lib->vba.ScaleRatioAndTapsSupport = true;
3298 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3299 if (mode_lib->vba.ScalerEnabled[k] == false
3300 && ((mode_lib->vba.SourcePixelFormat[k] != dm_444_64
3301 && mode_lib->vba.SourcePixelFormat[k] != dm_444_32
3302 && mode_lib->vba.SourcePixelFormat[k] != dm_444_16
3303 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_16
3304 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_8)
3305 || mode_lib->vba.HRatio[k] != 1.0
3306 || mode_lib->vba.htaps[k] != 1.0
3307 || mode_lib->vba.VRatio[k] != 1.0
3308 || mode_lib->vba.vtaps[k] != 1.0)) {
3309 mode_lib->vba.ScaleRatioAndTapsSupport = false;
3310 } else if (mode_lib->vba.vtaps[k] < 1.0 || mode_lib->vba.vtaps[k] > 8.0
3311 || mode_lib->vba.htaps[k] < 1.0 || mode_lib->vba.htaps[k] > 8.0
3312 || (mode_lib->vba.htaps[k] > 1.0
3313 && (mode_lib->vba.htaps[k] % 2) == 1)
3314 || mode_lib->vba.HRatio[k] > mode_lib->vba.MaxHSCLRatio
3315 || mode_lib->vba.VRatio[k] > mode_lib->vba.MaxVSCLRatio
3316 || mode_lib->vba.HRatio[k] > mode_lib->vba.htaps[k]
3317 || mode_lib->vba.VRatio[k] > mode_lib->vba.vtaps[k]
3318 || (mode_lib->vba.SourcePixelFormat[k] != dm_444_64
3319 && mode_lib->vba.SourcePixelFormat[k] != dm_444_32
3320 && mode_lib->vba.SourcePixelFormat[k] != dm_444_16
3321 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_16
3322 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_8
3323 && (mode_lib->vba.HRatio[k] / 2.0
3324 > mode_lib->vba.HTAPsChroma[k]
3325 || mode_lib->vba.VRatio[k] / 2.0
3326 > mode_lib->vba.VTAPsChroma[k]))) {
3327 mode_lib->vba.ScaleRatioAndTapsSupport = false;
3328 }
3329 }
3330 /*Source Format, Pixel Format and Scan Support Check*/
3331
3332 mode_lib->vba.SourceFormatPixelAndScanSupport = true;
3333 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3334 if ((mode_lib->vba.SurfaceTiling[k] == dm_sw_linear
3335 && mode_lib->vba.SourceScan[k] != dm_horz)
3336 || ((mode_lib->vba.SurfaceTiling[k] == dm_sw_4kb_d
3337 || mode_lib->vba.SurfaceTiling[k] == dm_sw_4kb_d_x
3338 || mode_lib->vba.SurfaceTiling[k] == dm_sw_64kb_d
3339 || mode_lib->vba.SurfaceTiling[k] == dm_sw_64kb_d_t
3340 || mode_lib->vba.SurfaceTiling[k] == dm_sw_64kb_d_x
3341 || mode_lib->vba.SurfaceTiling[k] == dm_sw_var_d
3342 || mode_lib->vba.SurfaceTiling[k] == dm_sw_var_d_x)
3343 && mode_lib->vba.SourcePixelFormat[k] != dm_444_64)
3344 || (mode_lib->vba.SurfaceTiling[k] == dm_sw_64kb_r_x
3345 && (mode_lib->vba.SourcePixelFormat[k] == dm_mono_8
3346 || mode_lib->vba.SourcePixelFormat[k]
3347 == dm_420_8
3348 || mode_lib->vba.SourcePixelFormat[k]
3349 == dm_420_10))
3350 || (((mode_lib->vba.SurfaceTiling[k] == dm_sw_gfx7_2d_thin_gl
3351 || mode_lib->vba.SurfaceTiling[k]
3352 == dm_sw_gfx7_2d_thin_l_vp)
3353 && !((mode_lib->vba.SourcePixelFormat[k]
3354 == dm_444_64
3355 || mode_lib->vba.SourcePixelFormat[k]
3356 == dm_444_32)
3357 && mode_lib->vba.SourceScan[k]
3358 == dm_horz
3359 && mode_lib->vba.SupportGFX7CompatibleTilingIn32bppAnd64bpp
3360 == true
3361 && mode_lib->vba.DCCEnable[k]
3362 == false))
3363 || (mode_lib->vba.DCCEnable[k] == true
3364 && (mode_lib->vba.SurfaceTiling[k]
3365 == dm_sw_linear
3366 || mode_lib->vba.SourcePixelFormat[k]
3367 == dm_420_8
3368 || mode_lib->vba.SourcePixelFormat[k]
3369 == dm_420_10)))) {
3370 mode_lib->vba.SourceFormatPixelAndScanSupport = false;
3371 }
3372 }
3373 /*Bandwidth Support Check*/
3374
3375 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3376 if (mode_lib->vba.SourcePixelFormat[k] == dm_444_64) {
3377 locals->BytePerPixelInDETY[k] = 8.0;
3378 locals->BytePerPixelInDETC[k] = 0.0;
3379 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_32) {
3380 locals->BytePerPixelInDETY[k] = 4.0;
3381 locals->BytePerPixelInDETC[k] = 0.0;
3382 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_444_16
3383 || mode_lib->vba.SourcePixelFormat[k] == dm_mono_16) {
3384 locals->BytePerPixelInDETY[k] = 2.0;
3385 locals->BytePerPixelInDETC[k] = 0.0;
3386 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_mono_8) {
3387 locals->BytePerPixelInDETY[k] = 1.0;
3388 locals->BytePerPixelInDETC[k] = 0.0;
3389 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_8) {
3390 locals->BytePerPixelInDETY[k] = 1.0;
3391 locals->BytePerPixelInDETC[k] = 2.0;
3392 } else {
3393 locals->BytePerPixelInDETY[k] = 4.0 / 3;
3394 locals->BytePerPixelInDETC[k] = 8.0 / 3;
3395 }
3396 if (mode_lib->vba.SourceScan[k] == dm_horz) {
3397 locals->SwathWidthYSingleDPP[k] = mode_lib->vba.ViewportWidth[k];
3398 } else {
3399 locals->SwathWidthYSingleDPP[k] = mode_lib->vba.ViewportHeight[k];
3400 }
3401 }
3402 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3403 locals->ReadBandwidthLuma[k] = locals->SwathWidthYSingleDPP[k] * dml_ceil(locals->BytePerPixelInDETY[k], 1.0)
3404 / (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k]) * mode_lib->vba.VRatio[k];
3405 locals->ReadBandwidthChroma[k] = locals->SwathWidthYSingleDPP[k] / 2 * dml_ceil(locals->BytePerPixelInDETC[k], 2.0)
3406 / (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k]) * mode_lib->vba.VRatio[k] / 2.0;
3407 locals->ReadBandwidth[k] = locals->ReadBandwidthLuma[k] + locals->ReadBandwidthChroma[k];
3408 }
3409 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3410 if (mode_lib->vba.WritebackEnable[k] == true
3411 && mode_lib->vba.WritebackPixelFormat[k] == dm_444_32) {
3412 locals->WriteBandwidth[k] = mode_lib->vba.WritebackDestinationWidth[k]
3413 * mode_lib->vba.WritebackDestinationHeight[k]
3414 / (mode_lib->vba.WritebackSourceHeight[k]
3415 * mode_lib->vba.HTotal[k]
3416 / mode_lib->vba.PixelClock[k]) * 4.0;
3417 } else if (mode_lib->vba.WritebackEnable[k] == true
3418 && mode_lib->vba.WritebackPixelFormat[k] == dm_420_10) {
3419 locals->WriteBandwidth[k] = mode_lib->vba.WritebackDestinationWidth[k]
3420 * mode_lib->vba.WritebackDestinationHeight[k]
3421 / (mode_lib->vba.WritebackSourceHeight[k]
3422 * mode_lib->vba.HTotal[k]
3423 / mode_lib->vba.PixelClock[k]) * 3.0;
3424 } else if (mode_lib->vba.WritebackEnable[k] == true) {
3425 locals->WriteBandwidth[k] = mode_lib->vba.WritebackDestinationWidth[k]
3426 * mode_lib->vba.WritebackDestinationHeight[k]
3427 / (mode_lib->vba.WritebackSourceHeight[k]
3428 * mode_lib->vba.HTotal[k]
3429 / mode_lib->vba.PixelClock[k]) * 1.5;
3430 } else {
3431 locals->WriteBandwidth[k] = 0.0;
3432 }
3433 }
3434 mode_lib->vba.DCCEnabledInAnyPlane = false;
3435 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3436 if (mode_lib->vba.DCCEnable[k] == true) {
3437 mode_lib->vba.DCCEnabledInAnyPlane = true;
3438 }
3439 }
3440 mode_lib->vba.UrgentLatency = mode_lib->vba.UrgentLatencyPixelDataOnly;
3441 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
3442 locals->FabricAndDRAMBandwidthPerState[i] = dml_min(
3443 mode_lib->vba.DRAMSpeedPerState[i] * mode_lib->vba.NumberOfChannels
3444 * mode_lib->vba.DRAMChannelWidth,
3445 mode_lib->vba.FabricClockPerState[i]
3446 * mode_lib->vba.FabricDatapathToDCNDataReturn) / 1000;
3447 locals->ReturnBWToDCNPerState = dml_min(locals->ReturnBusWidth * locals->DCFCLKPerState[i],
3448 locals->FabricAndDRAMBandwidthPerState[i] * 1000)
3449 * locals->PercentOfIdealDRAMFabricAndSDPPortBWReceivedAfterUrgLatencyPixelDataOnly / 100;
3450
3451 locals->ReturnBWPerState[i][0] = locals->ReturnBWToDCNPerState;
3452
3453 if (locals->DCCEnabledInAnyPlane == true && locals->ReturnBWToDCNPerState > locals->DCFCLKPerState[i] * locals->ReturnBusWidth / 4) {
3454 locals->ReturnBWPerState[i][0] = dml_min(locals->ReturnBWPerState[i][0],
3455 locals->ReturnBWToDCNPerState * 4 * (1 - locals->UrgentLatency /
3456 ((locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024
3457 / (locals->ReturnBWToDCNPerState - locals->DCFCLKPerState[i]
3458 * locals->ReturnBusWidth / 4) + locals->UrgentLatency)));
3459 }
3460 locals->CriticalPoint = 2 * locals->ReturnBusWidth * locals->DCFCLKPerState[i] *
3461 locals->UrgentLatency / (locals->ReturnBWToDCNPerState * locals->UrgentLatency
3462 + (locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024);
3463
3464 if (locals->DCCEnabledInAnyPlane && locals->CriticalPoint > 1 && locals->CriticalPoint < 4) {
3465 locals->ReturnBWPerState[i][0] = dml_min(locals->ReturnBWPerState[i][0],
3466 4 * locals->ReturnBWToDCNPerState *
3467 (locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024
3468 * locals->ReturnBusWidth * locals->DCFCLKPerState[i] * locals->UrgentLatency /
3469 dml_pow((locals->ReturnBWToDCNPerState * locals->UrgentLatency
3470 + (locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024), 2));
3471 }
3472
3473 locals->ReturnBWToDCNPerState = dml_min(locals->ReturnBusWidth *
3474 locals->DCFCLKPerState[i], locals->FabricAndDRAMBandwidthPerState[i] * 1000);
3475
3476 if (locals->DCCEnabledInAnyPlane == true && locals->ReturnBWToDCNPerState > locals->DCFCLKPerState[i] * locals->ReturnBusWidth / 4) {
3477 locals->ReturnBWPerState[i][0] = dml_min(locals->ReturnBWPerState[i][0],
3478 locals->ReturnBWToDCNPerState * 4 * (1 - locals->UrgentLatency /
3479 ((locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024
3480 / (locals->ReturnBWToDCNPerState - locals->DCFCLKPerState[i]
3481 * locals->ReturnBusWidth / 4) + locals->UrgentLatency)));
3482 }
3483 locals->CriticalPoint = 2 * locals->ReturnBusWidth * locals->DCFCLKPerState[i] *
3484 locals->UrgentLatency / (locals->ReturnBWToDCNPerState * locals->UrgentLatency
3485 + (locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024);
3486
3487 if (locals->DCCEnabledInAnyPlane && locals->CriticalPoint > 1 && locals->CriticalPoint < 4) {
3488 locals->ReturnBWPerState[i][0] = dml_min(locals->ReturnBWPerState[i][0],
3489 4 * locals->ReturnBWToDCNPerState *
3490 (locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024
3491 * locals->ReturnBusWidth * locals->DCFCLKPerState[i] * locals->UrgentLatency /
3492 dml_pow((locals->ReturnBWToDCNPerState * locals->UrgentLatency
3493 + (locals->ROBBufferSizeInKByte - locals->PixelChunkSizeInKByte) * 1024), 2));
3494 }
3495 }
3496 /*Writeback Latency support check*/
3497
3498 mode_lib->vba.WritebackLatencySupport = true;
3499 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3500 if (mode_lib->vba.WritebackEnable[k] == true) {
3501 if (mode_lib->vba.WritebackPixelFormat[k] == dm_444_32) {
3502 if (locals->WriteBandwidth[k]
3503 > (mode_lib->vba.WritebackInterfaceLumaBufferSize
3504 + mode_lib->vba.WritebackInterfaceChromaBufferSize)
3505 / mode_lib->vba.WritebackLatency) {
3506 mode_lib->vba.WritebackLatencySupport = false;
3507 }
3508 } else {
3509 if (locals->WriteBandwidth[k]
3510 > 1.5
3511 * dml_min(
3512 mode_lib->vba.WritebackInterfaceLumaBufferSize,
3513 2.0
3514 * mode_lib->vba.WritebackInterfaceChromaBufferSize)
3515 / mode_lib->vba.WritebackLatency) {
3516 mode_lib->vba.WritebackLatencySupport = false;
3517 }
3518 }
3519 }
3520 }
3521 /*Re-ordering Buffer Support Check*/
3522
3523 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
3524 locals->UrgentRoundTripAndOutOfOrderLatencyPerState[i] =
3525 (mode_lib->vba.RoundTripPingLatencyCycles + 32.0) / mode_lib->vba.DCFCLKPerState[i]
3526 + locals->UrgentOutOfOrderReturnPerChannel * mode_lib->vba.NumberOfChannels / locals->ReturnBWPerState[i][0];
3527 if ((mode_lib->vba.ROBBufferSizeInKByte - mode_lib->vba.PixelChunkSizeInKByte) * 1024.0 / locals->ReturnBWPerState[i][0]
3528 > locals->UrgentRoundTripAndOutOfOrderLatencyPerState[i]) {
3529 locals->ROBSupport[i][0] = true;
3530 } else {
3531 locals->ROBSupport[i][0] = false;
3532 }
3533 }
3534 /*Writeback Mode Support Check*/
3535
3536 mode_lib->vba.TotalNumberOfActiveWriteback = 0;
3537 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3538 if (mode_lib->vba.WritebackEnable[k] == true) {
3539 if (mode_lib->vba.ActiveWritebacksPerPlane[k] == 0)
3540 mode_lib->vba.ActiveWritebacksPerPlane[k] = 1;
3541 mode_lib->vba.TotalNumberOfActiveWriteback =
3542 mode_lib->vba.TotalNumberOfActiveWriteback
3543 + mode_lib->vba.ActiveWritebacksPerPlane[k];
3544 }
3545 }
3546 mode_lib->vba.WritebackModeSupport = true;
3547 if (mode_lib->vba.TotalNumberOfActiveWriteback > mode_lib->vba.MaxNumWriteback) {
3548 mode_lib->vba.WritebackModeSupport = false;
3549 }
3550 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3551 if (mode_lib->vba.WritebackEnable[k] == true
3552 && mode_lib->vba.Writeback10bpc420Supported != true
3553 && mode_lib->vba.WritebackPixelFormat[k] == dm_420_10) {
3554 mode_lib->vba.WritebackModeSupport = false;
3555 }
3556 }
3557 /*Writeback Scale Ratio and Taps Support Check*/
3558
3559 mode_lib->vba.WritebackScaleRatioAndTapsSupport = true;
3560 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3561 if (mode_lib->vba.WritebackEnable[k] == true) {
3562 if (mode_lib->vba.WritebackLumaAndChromaScalingSupported == false
3563 && (mode_lib->vba.WritebackHRatio[k] != 1.0
3564 || mode_lib->vba.WritebackVRatio[k] != 1.0)) {
3565 mode_lib->vba.WritebackScaleRatioAndTapsSupport = false;
3566 }
3567 if (mode_lib->vba.WritebackHRatio[k] > mode_lib->vba.WritebackMaxHSCLRatio
3568 || mode_lib->vba.WritebackVRatio[k]
3569 > mode_lib->vba.WritebackMaxVSCLRatio
3570 || mode_lib->vba.WritebackHRatio[k]
3571 < mode_lib->vba.WritebackMinHSCLRatio
3572 || mode_lib->vba.WritebackVRatio[k]
3573 < mode_lib->vba.WritebackMinVSCLRatio
3574 || mode_lib->vba.WritebackLumaHTaps[k]
3575 > mode_lib->vba.WritebackMaxHSCLTaps
3576 || mode_lib->vba.WritebackLumaVTaps[k]
3577 > mode_lib->vba.WritebackMaxVSCLTaps
3578 || mode_lib->vba.WritebackHRatio[k]
3579 > mode_lib->vba.WritebackLumaHTaps[k]
3580 || mode_lib->vba.WritebackVRatio[k]
3581 > mode_lib->vba.WritebackLumaVTaps[k]
3582 || (mode_lib->vba.WritebackLumaHTaps[k] > 2.0
3583 && ((mode_lib->vba.WritebackLumaHTaps[k] % 2)
3584 == 1))
3585 || (mode_lib->vba.WritebackPixelFormat[k] != dm_444_32
3586 && (mode_lib->vba.WritebackChromaHTaps[k]
3587 > mode_lib->vba.WritebackMaxHSCLTaps
3588 || mode_lib->vba.WritebackChromaVTaps[k]
3589 > mode_lib->vba.WritebackMaxVSCLTaps
3590 || 2.0
3591 * mode_lib->vba.WritebackHRatio[k]
3592 > mode_lib->vba.WritebackChromaHTaps[k]
3593 || 2.0
3594 * mode_lib->vba.WritebackVRatio[k]
3595 > mode_lib->vba.WritebackChromaVTaps[k]
3596 || (mode_lib->vba.WritebackChromaHTaps[k] > 2.0
3597 && ((mode_lib->vba.WritebackChromaHTaps[k] % 2) == 1))))) {
3598 mode_lib->vba.WritebackScaleRatioAndTapsSupport = false;
3599 }
3600 if (mode_lib->vba.WritebackVRatio[k] < 1.0) {
3601 mode_lib->vba.WritebackLumaVExtra =
3602 dml_max(1.0 - 2.0 / dml_ceil(1.0 / mode_lib->vba.WritebackVRatio[k], 1.0), 0.0);
3603 } else {
3604 mode_lib->vba.WritebackLumaVExtra = -1;
3605 }
3606 if ((mode_lib->vba.WritebackPixelFormat[k] == dm_444_32
3607 && mode_lib->vba.WritebackLumaVTaps[k]
3608 > (mode_lib->vba.WritebackLineBufferLumaBufferSize
3609 + mode_lib->vba.WritebackLineBufferChromaBufferSize)
3610 / 3.0
3611 / mode_lib->vba.WritebackDestinationWidth[k]
3612 - mode_lib->vba.WritebackLumaVExtra)
3613 || (mode_lib->vba.WritebackPixelFormat[k] == dm_420_8
3614 && mode_lib->vba.WritebackLumaVTaps[k]
3615 > mode_lib->vba.WritebackLineBufferLumaBufferSize
3616 * 8.0 / 10.0 / mode_lib->vba.WritebackDestinationWidth[k]
3617 - mode_lib->vba.WritebackLumaVExtra)
3618 || (mode_lib->vba.WritebackPixelFormat[k] == dm_420_10
3619 && mode_lib->vba.WritebackLumaVTaps[k]
3620 > mode_lib->vba.WritebackLineBufferLumaBufferSize
3621 * 8.0 / 10.0
3622 / mode_lib->vba.WritebackDestinationWidth[k]
3623 - mode_lib->vba.WritebackLumaVExtra)) {
3624 mode_lib->vba.WritebackScaleRatioAndTapsSupport = false;
3625 }
3626 if (2.0 * mode_lib->vba.WritebackVRatio[k] < 1) {
3627 mode_lib->vba.WritebackChromaVExtra = 0.0;
3628 } else {
3629 mode_lib->vba.WritebackChromaVExtra = -1;
3630 }
3631 if ((mode_lib->vba.WritebackPixelFormat[k] == dm_420_8
3632 && mode_lib->vba.WritebackChromaVTaps[k]
3633 > mode_lib->vba.WritebackLineBufferChromaBufferSize
3634 * 8.0 / 10.0 / mode_lib->vba.WritebackDestinationWidth[k]
3635 - mode_lib->vba.WritebackChromaVExtra)
3636 || (mode_lib->vba.WritebackPixelFormat[k] == dm_420_10
3637 && mode_lib->vba.WritebackChromaVTaps[k]
3638 > mode_lib->vba.WritebackLineBufferChromaBufferSize
3639 * 8.0 / 10.0
3640 / mode_lib->vba.WritebackDestinationWidth[k]
3641 - mode_lib->vba.WritebackChromaVExtra)) {
3642 mode_lib->vba.WritebackScaleRatioAndTapsSupport = false;
3643 }
3644 }
3645 }
3646 /*Maximum DISPCLK/DPPCLK Support check*/
3647
3648 mode_lib->vba.WritebackRequiredDISPCLK = 0.0;
3649 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3650 if (mode_lib->vba.WritebackEnable[k] == true) {
3651 mode_lib->vba.WritebackRequiredDISPCLK =
3652 dml_max(
3653 mode_lib->vba.WritebackRequiredDISPCLK,
3654 CalculateWriteBackDISPCLK(
3655 mode_lib->vba.WritebackPixelFormat[k],
3656 mode_lib->vba.PixelClock[k],
3657 mode_lib->vba.WritebackHRatio[k],
3658 mode_lib->vba.WritebackVRatio[k],
3659 mode_lib->vba.WritebackLumaHTaps[k],
3660 mode_lib->vba.WritebackLumaVTaps[k],
3661 mode_lib->vba.WritebackChromaHTaps[k],
3662 mode_lib->vba.WritebackChromaVTaps[k],
3663 mode_lib->vba.WritebackDestinationWidth[k],
3664 mode_lib->vba.HTotal[k],
3665 mode_lib->vba.WritebackChromaLineBufferWidth));
3666 }
3667 }
3668 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3669 if (mode_lib->vba.HRatio[k] > 1.0) {
3670 locals->PSCL_FACTOR[k] = dml_min(
3671 mode_lib->vba.MaxDCHUBToPSCLThroughput,
3672 mode_lib->vba.MaxPSCLToLBThroughput
3673 * mode_lib->vba.HRatio[k]
3674 / dml_ceil(
3675 mode_lib->vba.htaps[k]
3676 / 6.0,
3677 1.0));
3678 } else {
3679 locals->PSCL_FACTOR[k] = dml_min(
3680 mode_lib->vba.MaxDCHUBToPSCLThroughput,
3681 mode_lib->vba.MaxPSCLToLBThroughput);
3682 }
3683 if (locals->BytePerPixelInDETC[k] == 0.0) {
3684 locals->PSCL_FACTOR_CHROMA[k] = 0.0;
3685 locals->MinDPPCLKUsingSingleDPP[k] =
3686 mode_lib->vba.PixelClock[k]
3687 * dml_max3(
3688 mode_lib->vba.vtaps[k] / 6.0
3689 * dml_min(
3690 1.0,
3691 mode_lib->vba.HRatio[k]),
3692 mode_lib->vba.HRatio[k]
3693 * mode_lib->vba.VRatio[k]
3694 / locals->PSCL_FACTOR[k],
3695 1.0);
3696 if ((mode_lib->vba.htaps[k] > 6.0 || mode_lib->vba.vtaps[k] > 6.0)
3697 && locals->MinDPPCLKUsingSingleDPP[k]
3698 < 2.0 * mode_lib->vba.PixelClock[k]) {
3699 locals->MinDPPCLKUsingSingleDPP[k] = 2.0
3700 * mode_lib->vba.PixelClock[k];
3701 }
3702 } else {
3703 if (mode_lib->vba.HRatio[k] / 2.0 > 1.0) {
3704 locals->PSCL_FACTOR_CHROMA[k] =
3705 dml_min(
3706 mode_lib->vba.MaxDCHUBToPSCLThroughput,
3707 mode_lib->vba.MaxPSCLToLBThroughput
3708 * mode_lib->vba.HRatio[k]
3709 / 2.0
3710 / dml_ceil(
3711 mode_lib->vba.HTAPsChroma[k]
3712 / 6.0,
3713 1.0));
3714 } else {
3715 locals->PSCL_FACTOR_CHROMA[k] = dml_min(
3716 mode_lib->vba.MaxDCHUBToPSCLThroughput,
3717 mode_lib->vba.MaxPSCLToLBThroughput);
3718 }
3719 locals->MinDPPCLKUsingSingleDPP[k] =
3720 mode_lib->vba.PixelClock[k]
3721 * dml_max5(
3722 mode_lib->vba.vtaps[k] / 6.0
3723 * dml_min(
3724 1.0,
3725 mode_lib->vba.HRatio[k]),
3726 mode_lib->vba.HRatio[k]
3727 * mode_lib->vba.VRatio[k]
3728 / locals->PSCL_FACTOR[k],
3729 mode_lib->vba.VTAPsChroma[k]
3730 / 6.0
3731 * dml_min(
3732 1.0,
3733 mode_lib->vba.HRatio[k]
3734 / 2.0),
3735 mode_lib->vba.HRatio[k]
3736 * mode_lib->vba.VRatio[k]
3737 / 4.0
3738 / locals->PSCL_FACTOR_CHROMA[k],
3739 1.0);
3740 if ((mode_lib->vba.htaps[k] > 6.0 || mode_lib->vba.vtaps[k] > 6.0
3741 || mode_lib->vba.HTAPsChroma[k] > 6.0
3742 || mode_lib->vba.VTAPsChroma[k] > 6.0)
3743 && locals->MinDPPCLKUsingSingleDPP[k]
3744 < 2.0 * mode_lib->vba.PixelClock[k]) {
3745 locals->MinDPPCLKUsingSingleDPP[k] = 2.0
3746 * mode_lib->vba.PixelClock[k];
3747 }
3748 }
3749 }
3750 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3751 Calculate256BBlockSizes(
3752 mode_lib->vba.SourcePixelFormat[k],
3753 mode_lib->vba.SurfaceTiling[k],
3754 dml_ceil(locals->BytePerPixelInDETY[k], 1.0),
3755 dml_ceil(locals->BytePerPixelInDETC[k], 2.0),
3756 &locals->Read256BlockHeightY[k],
3757 &locals->Read256BlockHeightC[k],
3758 &locals->Read256BlockWidthY[k],
3759 &locals->Read256BlockWidthC[k]);
3760 if (mode_lib->vba.SourceScan[k] == dm_horz) {
3761 locals->MaxSwathHeightY[k] = locals->Read256BlockHeightY[k];
3762 locals->MaxSwathHeightC[k] = locals->Read256BlockHeightC[k];
3763 } else {
3764 locals->MaxSwathHeightY[k] = locals->Read256BlockWidthY[k];
3765 locals->MaxSwathHeightC[k] = locals->Read256BlockWidthC[k];
3766 }
3767 if ((mode_lib->vba.SourcePixelFormat[k] == dm_444_64
3768 || mode_lib->vba.SourcePixelFormat[k] == dm_444_32
3769 || mode_lib->vba.SourcePixelFormat[k] == dm_444_16
3770 || mode_lib->vba.SourcePixelFormat[k] == dm_mono_16
3771 || mode_lib->vba.SourcePixelFormat[k] == dm_mono_8)) {
3772 if (mode_lib->vba.SurfaceTiling[k] == dm_sw_linear
3773 || (mode_lib->vba.SourcePixelFormat[k] == dm_444_64
3774 && (mode_lib->vba.SurfaceTiling[k]
3775 == dm_sw_4kb_s
3776 || mode_lib->vba.SurfaceTiling[k]
3777 == dm_sw_4kb_s_x
3778 || mode_lib->vba.SurfaceTiling[k]
3779 == dm_sw_64kb_s
3780 || mode_lib->vba.SurfaceTiling[k]
3781 == dm_sw_64kb_s_t
3782 || mode_lib->vba.SurfaceTiling[k]
3783 == dm_sw_64kb_s_x
3784 || mode_lib->vba.SurfaceTiling[k]
3785 == dm_sw_var_s
3786 || mode_lib->vba.SurfaceTiling[k]
3787 == dm_sw_var_s_x)
3788 && mode_lib->vba.SourceScan[k] == dm_horz)) {
3789 locals->MinSwathHeightY[k] = locals->MaxSwathHeightY[k];
3790 } else {
3791 locals->MinSwathHeightY[k] = locals->MaxSwathHeightY[k]
3792 / 2.0;
3793 }
3794 locals->MinSwathHeightC[k] = locals->MaxSwathHeightC[k];
3795 } else {
3796 if (mode_lib->vba.SurfaceTiling[k] == dm_sw_linear) {
3797 locals->MinSwathHeightY[k] = locals->MaxSwathHeightY[k];
3798 locals->MinSwathHeightC[k] = locals->MaxSwathHeightC[k];
3799 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_8
3800 && mode_lib->vba.SourceScan[k] == dm_horz) {
3801 locals->MinSwathHeightY[k] = locals->MaxSwathHeightY[k]
3802 / 2.0;
3803 locals->MinSwathHeightC[k] = locals->MaxSwathHeightC[k];
3804 } else if (mode_lib->vba.SourcePixelFormat[k] == dm_420_10
3805 && mode_lib->vba.SourceScan[k] == dm_horz) {
3806 locals->MinSwathHeightC[k] = locals->MaxSwathHeightC[k]
3807 / 2.0;
3808 locals->MinSwathHeightY[k] = locals->MaxSwathHeightY[k];
3809 } else {
3810 locals->MinSwathHeightY[k] = locals->MaxSwathHeightY[k];
3811 locals->MinSwathHeightC[k] = locals->MaxSwathHeightC[k];
3812 }
3813 }
3814 if (mode_lib->vba.SurfaceTiling[k] == dm_sw_linear) {
3815 mode_lib->vba.MaximumSwathWidthSupport = 8192.0;
3816 } else {
3817 mode_lib->vba.MaximumSwathWidthSupport = 5120.0;
3818 }
3819 mode_lib->vba.MaximumSwathWidthInDETBuffer =
3820 dml_min(
3821 mode_lib->vba.MaximumSwathWidthSupport,
3822 mode_lib->vba.DETBufferSizeInKByte[0] * 1024.0 / 2.0
3823 / (locals->BytePerPixelInDETY[k]
3824 * locals->MinSwathHeightY[k]
3825 + locals->BytePerPixelInDETC[k]
3826 / 2.0
3827 * locals->MinSwathHeightC[k]));
3828 if (locals->BytePerPixelInDETC[k] == 0.0) {
3829 mode_lib->vba.MaximumSwathWidthInLineBuffer =
3830 mode_lib->vba.LineBufferSize
3831 * dml_max(mode_lib->vba.HRatio[k], 1.0)
3832 / mode_lib->vba.LBBitPerPixel[k]
3833 / (mode_lib->vba.vtaps[k]
3834 + dml_max(
3835 dml_ceil(
3836 mode_lib->vba.VRatio[k],
3837 1.0)
3838 - 2,
3839 0.0));
3840 } else {
3841 mode_lib->vba.MaximumSwathWidthInLineBuffer =
3842 dml_min(
3843 mode_lib->vba.LineBufferSize
3844 * dml_max(
3845 mode_lib->vba.HRatio[k],
3846 1.0)
3847 / mode_lib->vba.LBBitPerPixel[k]
3848 / (mode_lib->vba.vtaps[k]
3849 + dml_max(
3850 dml_ceil(
3851 mode_lib->vba.VRatio[k],
3852 1.0)
3853 - 2,
3854 0.0)),
3855 2.0 * mode_lib->vba.LineBufferSize
3856 * dml_max(
3857 mode_lib->vba.HRatio[k]
3858 / 2.0,
3859 1.0)
3860 / mode_lib->vba.LBBitPerPixel[k]
3861 / (mode_lib->vba.VTAPsChroma[k]
3862 + dml_max(
3863 dml_ceil(
3864 mode_lib->vba.VRatio[k]
3865 / 2.0,
3866 1.0)
3867 - 2,
3868 0.0)));
3869 }
3870 locals->MaximumSwathWidth[k] = dml_min(
3871 mode_lib->vba.MaximumSwathWidthInDETBuffer,
3872 mode_lib->vba.MaximumSwathWidthInLineBuffer);
3873 }
3874 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
3875 for (j = 0; j < 2; j++) {
3876 mode_lib->vba.MaxDispclkRoundedDownToDFSGranularity = RoundToDFSGranularityDown(
3877 mode_lib->vba.MaxDispclk[i],
3878 mode_lib->vba.DISPCLKDPPCLKVCOSpeed);
3879 mode_lib->vba.MaxDppclkRoundedDownToDFSGranularity = RoundToDFSGranularityDown(
3880 mode_lib->vba.MaxDppclk[i],
3881 mode_lib->vba.DISPCLKDPPCLKVCOSpeed);
3882 locals->RequiredDISPCLK[i][j] = 0.0;
3883 locals->DISPCLK_DPPCLK_Support[i][j] = true;
3884 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3885 mode_lib->vba.PlaneRequiredDISPCLKWithoutODMCombine =
3886 mode_lib->vba.PixelClock[k] * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0)
3887 * (1.0 + mode_lib->vba.DISPCLKRampingMargin / 100.0);
3888 if (mode_lib->vba.PlaneRequiredDISPCLKWithoutODMCombine >= mode_lib->vba.MaxDispclk[i]
3889 && i == mode_lib->vba.soc.num_states)
3890 mode_lib->vba.PlaneRequiredDISPCLKWithoutODMCombine = mode_lib->vba.PixelClock[k]
3891 * (1 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0);
3892
3893 mode_lib->vba.PlaneRequiredDISPCLKWithODMCombine = mode_lib->vba.PixelClock[k] / 2
3894 * (1 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0) * (1 + mode_lib->vba.DISPCLKRampingMargin / 100.0);
3895 if (mode_lib->vba.PlaneRequiredDISPCLKWithODMCombine >= mode_lib->vba.MaxDispclk[i]
3896 && i == mode_lib->vba.soc.num_states)
3897 mode_lib->vba.PlaneRequiredDISPCLKWithODMCombine = mode_lib->vba.PixelClock[k] / 2
3898 * (1 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0);
3899
3900 locals->ODMCombineEnablePerState[i][k] = dm_odm_combine_mode_disabled;
3901 mode_lib->vba.PlaneRequiredDISPCLK = mode_lib->vba.PlaneRequiredDISPCLKWithoutODMCombine;
3902 if (mode_lib->vba.ODMCapability) {
3903 if (locals->PlaneRequiredDISPCLKWithoutODMCombine > mode_lib->vba.MaxDispclkRoundedDownToDFSGranularity) {
3904 locals->ODMCombineEnablePerState[i][k] = dm_odm_combine_mode_2to1;
3905 mode_lib->vba.PlaneRequiredDISPCLK = mode_lib->vba.PlaneRequiredDISPCLKWithODMCombine;
3906 } else if (locals->HActive[k] > DCN20_MAX_420_IMAGE_WIDTH && locals->OutputFormat[k] == dm_420) {
3907 locals->ODMCombineEnablePerState[i][k] = dm_odm_combine_mode_2to1;
3908 mode_lib->vba.PlaneRequiredDISPCLK = mode_lib->vba.PlaneRequiredDISPCLKWithODMCombine;
3909 }
3910 }
3911
3912 if (locals->MinDPPCLKUsingSingleDPP[k] * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0) <= mode_lib->vba.MaxDppclkRoundedDownToDFSGranularity
3913 && locals->SwathWidthYSingleDPP[k] <= locals->MaximumSwathWidth[k]
3914 && locals->ODMCombineEnablePerState[i][k] == dm_odm_combine_mode_disabled) {
3915 locals->NoOfDPP[i][j][k] = 1;
3916 locals->RequiredDPPCLK[i][j][k] =
3917 locals->MinDPPCLKUsingSingleDPP[k] * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0);
3918 } else {
3919 locals->NoOfDPP[i][j][k] = 2;
3920 locals->RequiredDPPCLK[i][j][k] =
3921 locals->MinDPPCLKUsingSingleDPP[k] * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0) / 2.0;
3922 }
3923 locals->RequiredDISPCLK[i][j] = dml_max(
3924 locals->RequiredDISPCLK[i][j],
3925 mode_lib->vba.PlaneRequiredDISPCLK);
3926 if ((locals->MinDPPCLKUsingSingleDPP[k] / locals->NoOfDPP[i][j][k] * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0)
3927 > mode_lib->vba.MaxDppclkRoundedDownToDFSGranularity)
3928 || (mode_lib->vba.PlaneRequiredDISPCLK > mode_lib->vba.MaxDispclkRoundedDownToDFSGranularity)) {
3929 locals->DISPCLK_DPPCLK_Support[i][j] = false;
3930 }
3931 }
3932 locals->TotalNumberOfActiveDPP[i][j] = 0.0;
3933 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++)
3934 locals->TotalNumberOfActiveDPP[i][j] = locals->TotalNumberOfActiveDPP[i][j] + locals->NoOfDPP[i][j][k];
3935 if (j == 1) {
3936 while (locals->TotalNumberOfActiveDPP[i][j] < mode_lib->vba.MaxNumDPP
3937 && locals->TotalNumberOfActiveDPP[i][j] < 2 * mode_lib->vba.NumberOfActivePlanes) {
3938 double BWOfNonSplitPlaneOfMaximumBandwidth;
3939 unsigned int NumberOfNonSplitPlaneOfMaximumBandwidth;
3940
3941 BWOfNonSplitPlaneOfMaximumBandwidth = 0;
3942 NumberOfNonSplitPlaneOfMaximumBandwidth = 0;
3943 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; ++k) {
3944 if (locals->ReadBandwidth[k] > BWOfNonSplitPlaneOfMaximumBandwidth && locals->NoOfDPP[i][j][k] == 1) {
3945 BWOfNonSplitPlaneOfMaximumBandwidth = locals->ReadBandwidth[k];
3946 NumberOfNonSplitPlaneOfMaximumBandwidth = k;
3947 }
3948 }
3949 locals->NoOfDPP[i][j][NumberOfNonSplitPlaneOfMaximumBandwidth] = 2;
3950 locals->RequiredDPPCLK[i][j][NumberOfNonSplitPlaneOfMaximumBandwidth] =
3951 locals->MinDPPCLKUsingSingleDPP[NumberOfNonSplitPlaneOfMaximumBandwidth]
3952 * (1 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100) / 2;
3953 locals->TotalNumberOfActiveDPP[i][j] = locals->TotalNumberOfActiveDPP[i][j] + 1;
3954 }
3955 }
3956 if (locals->TotalNumberOfActiveDPP[i][j] > mode_lib->vba.MaxNumDPP) {
3957 locals->RequiredDISPCLK[i][j] = 0.0;
3958 locals->DISPCLK_DPPCLK_Support[i][j] = true;
3959 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
3960 locals->ODMCombineEnablePerState[i][k] = dm_odm_combine_mode_disabled;
3961 if (locals->SwathWidthYSingleDPP[k] <= locals->MaximumSwathWidth[k]) {
3962 locals->NoOfDPP[i][j][k] = 1;
3963 locals->RequiredDPPCLK[i][j][k] = locals->MinDPPCLKUsingSingleDPP[k]
3964 * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0);
3965 } else {
3966 locals->NoOfDPP[i][j][k] = 2;
3967 locals->RequiredDPPCLK[i][j][k] = locals->MinDPPCLKUsingSingleDPP[k]
3968 * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0) / 2.0;
3969 }
3970 if (i != mode_lib->vba.soc.num_states) {
3971 mode_lib->vba.PlaneRequiredDISPCLK =
3972 mode_lib->vba.PixelClock[k]
3973 * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0)
3974 * (1.0 + mode_lib->vba.DISPCLKRampingMargin / 100.0);
3975 } else {
3976 mode_lib->vba.PlaneRequiredDISPCLK = mode_lib->vba.PixelClock[k]
3977 * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0);
3978 }
3979 locals->RequiredDISPCLK[i][j] = dml_max(
3980 locals->RequiredDISPCLK[i][j],
3981 mode_lib->vba.PlaneRequiredDISPCLK);
3982 if (locals->MinDPPCLKUsingSingleDPP[k] / locals->NoOfDPP[i][j][k] * (1.0 + mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0)
3983 > mode_lib->vba.MaxDppclkRoundedDownToDFSGranularity
3984 || mode_lib->vba.PlaneRequiredDISPCLK > mode_lib->vba.MaxDispclkRoundedDownToDFSGranularity)
3985 locals->DISPCLK_DPPCLK_Support[i][j] = false;
3986 }
3987 locals->TotalNumberOfActiveDPP[i][j] = 0.0;
3988 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++)
3989 locals->TotalNumberOfActiveDPP[i][j] = locals->TotalNumberOfActiveDPP[i][j] + locals->NoOfDPP[i][j][k];
3990 }
3991 locals->RequiredDISPCLK[i][j] = dml_max(
3992 locals->RequiredDISPCLK[i][j],
3993 mode_lib->vba.WritebackRequiredDISPCLK);
3994 if (mode_lib->vba.MaxDispclkRoundedDownToDFSGranularity
3995 < mode_lib->vba.WritebackRequiredDISPCLK) {
3996 locals->DISPCLK_DPPCLK_Support[i][j] = false;
3997 }
3998 }
3999 }
4000 /*Viewport Size Check*/
4001
4002 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4003 locals->ViewportSizeSupport[i][0] = true;
4004 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4005 if (locals->ODMCombineEnablePerState[i][k] == dm_odm_combine_mode_2to1) {
4006 if (dml_min(locals->SwathWidthYSingleDPP[k], dml_round(mode_lib->vba.HActive[k] / 2.0 * mode_lib->vba.HRatio[k]))
4007 > locals->MaximumSwathWidth[k]) {
4008 locals->ViewportSizeSupport[i][0] = false;
4009 }
4010 } else {
4011 if (locals->SwathWidthYSingleDPP[k] / 2.0 > locals->MaximumSwathWidth[k]) {
4012 locals->ViewportSizeSupport[i][0] = false;
4013 }
4014 }
4015 }
4016 }
4017 /*Total Available Pipes Support Check*/
4018
4019 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4020 for (j = 0; j < 2; j++) {
4021 if (locals->TotalNumberOfActiveDPP[i][j] <= mode_lib->vba.MaxNumDPP)
4022 locals->TotalAvailablePipesSupport[i][j] = true;
4023 else
4024 locals->TotalAvailablePipesSupport[i][j] = false;
4025 }
4026 }
4027 /*Total Available OTG Support Check*/
4028
4029 mode_lib->vba.TotalNumberOfActiveOTG = 0.0;
4030 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4031 if (mode_lib->vba.BlendingAndTiming[k] == k) {
4032 mode_lib->vba.TotalNumberOfActiveOTG = mode_lib->vba.TotalNumberOfActiveOTG
4033 + 1.0;
4034 }
4035 }
4036 if (mode_lib->vba.TotalNumberOfActiveOTG <= mode_lib->vba.MaxNumOTG) {
4037 mode_lib->vba.NumberOfOTGSupport = true;
4038 } else {
4039 mode_lib->vba.NumberOfOTGSupport = false;
4040 }
4041 /*Display IO and DSC Support Check*/
4042
4043 mode_lib->vba.NonsupportedDSCInputBPC = false;
4044 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4045 if (!(mode_lib->vba.DSCInputBitPerComponent[k] == 12.0
4046 || mode_lib->vba.DSCInputBitPerComponent[k] == 10.0
4047 || mode_lib->vba.DSCInputBitPerComponent[k] == 8.0)) {
4048 mode_lib->vba.NonsupportedDSCInputBPC = true;
4049 }
4050 }
4051 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4052 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4053 locals->RequiresDSC[i][k] = 0;
4054 locals->RequiresFEC[i][k] = 0;
4055 if (mode_lib->vba.BlendingAndTiming[k] == k) {
4056 if (mode_lib->vba.Output[k] == dm_hdmi) {
4057 locals->RequiresDSC[i][k] = 0;
4058 locals->RequiresFEC[i][k] = 0;
4059 locals->OutputBppPerState[i][k] = TruncToValidBPP(
4060 dml_min(600.0, mode_lib->vba.PHYCLKPerState[i]) / mode_lib->vba.PixelClockBackEnd[k] * 24,
4061 false,
4062 mode_lib->vba.Output[k],
4063 mode_lib->vba.OutputFormat[k],
4064 mode_lib->vba.DSCInputBitPerComponent[k]);
4065 } else if (mode_lib->vba.Output[k] == dm_dp
4066 || mode_lib->vba.Output[k] == dm_edp) {
4067 if (mode_lib->vba.Output[k] == dm_edp) {
4068 mode_lib->vba.EffectiveFECOverhead = 0.0;
4069 } else {
4070 mode_lib->vba.EffectiveFECOverhead =
4071 mode_lib->vba.FECOverhead;
4072 }
4073 if (mode_lib->vba.PHYCLKPerState[i] >= 270.0) {
4074 mode_lib->vba.Outbpp = TruncToValidBPP(
4075 (1.0 - mode_lib->vba.Downspreading / 100.0) * 270.0
4076 * mode_lib->vba.OutputLinkDPLanes[k] / mode_lib->vba.PixelClockBackEnd[k] * 8.0,
4077 false,
4078 mode_lib->vba.Output[k],
4079 mode_lib->vba.OutputFormat[k],
4080 mode_lib->vba.DSCInputBitPerComponent[k]);
4081 mode_lib->vba.OutbppDSC = TruncToValidBPP(
4082 (1.0 - mode_lib->vba.Downspreading / 100.0) * (1.0 - mode_lib->vba.EffectiveFECOverhead / 100.0) * 270.0
4083 * mode_lib->vba.OutputLinkDPLanes[k] / mode_lib->vba.PixelClockBackEnd[k] * 8.0,
4084 true,
4085 mode_lib->vba.Output[k],
4086 mode_lib->vba.OutputFormat[k],
4087 mode_lib->vba.DSCInputBitPerComponent[k]);
4088 if (mode_lib->vba.DSCEnabled[k] == true) {
4089 locals->RequiresDSC[i][k] = true;
4090 if (mode_lib->vba.Output[k] == dm_dp) {
4091 locals->RequiresFEC[i][k] = true;
4092 } else {
4093 locals->RequiresFEC[i][k] = false;
4094 }
4095 mode_lib->vba.Outbpp = mode_lib->vba.OutbppDSC;
4096 } else {
4097 locals->RequiresDSC[i][k] = false;
4098 locals->RequiresFEC[i][k] = false;
4099 }
4100 locals->OutputBppPerState[i][k] = mode_lib->vba.Outbpp;
4101 }
4102 if (mode_lib->vba.Outbpp == BPP_INVALID && mode_lib->vba.PHYCLKPerState[i] >= 540.0) {
4103 mode_lib->vba.Outbpp = TruncToValidBPP(
4104 (1.0 - mode_lib->vba.Downspreading / 100.0) * 540.0
4105 * mode_lib->vba.OutputLinkDPLanes[k] / mode_lib->vba.PixelClockBackEnd[k] * 8.0,
4106 false,
4107 mode_lib->vba.Output[k],
4108 mode_lib->vba.OutputFormat[k],
4109 mode_lib->vba.DSCInputBitPerComponent[k]);
4110 mode_lib->vba.OutbppDSC = TruncToValidBPP(
4111 (1.0 - mode_lib->vba.Downspreading / 100.0) * (1.0 - mode_lib->vba.EffectiveFECOverhead / 100.0) * 540.0
4112 * mode_lib->vba.OutputLinkDPLanes[k] / mode_lib->vba.PixelClockBackEnd[k] * 8.0,
4113 true,
4114 mode_lib->vba.Output[k],
4115 mode_lib->vba.OutputFormat[k],
4116 mode_lib->vba.DSCInputBitPerComponent[k]);
4117 if (mode_lib->vba.DSCEnabled[k] == true) {
4118 locals->RequiresDSC[i][k] = true;
4119 if (mode_lib->vba.Output[k] == dm_dp) {
4120 locals->RequiresFEC[i][k] = true;
4121 } else {
4122 locals->RequiresFEC[i][k] = false;
4123 }
4124 mode_lib->vba.Outbpp = mode_lib->vba.OutbppDSC;
4125 } else {
4126 locals->RequiresDSC[i][k] = false;
4127 locals->RequiresFEC[i][k] = false;
4128 }
4129 locals->OutputBppPerState[i][k] = mode_lib->vba.Outbpp;
4130 }
4131 if (mode_lib->vba.Outbpp == BPP_INVALID
4132 && mode_lib->vba.PHYCLKPerState[i]
4133 >= 810.0) {
4134 mode_lib->vba.Outbpp = TruncToValidBPP(
4135 (1.0 - mode_lib->vba.Downspreading / 100.0) * 810.0
4136 * mode_lib->vba.OutputLinkDPLanes[k] / mode_lib->vba.PixelClockBackEnd[k] * 8.0,
4137 false,
4138 mode_lib->vba.Output[k],
4139 mode_lib->vba.OutputFormat[k],
4140 mode_lib->vba.DSCInputBitPerComponent[k]);
4141 mode_lib->vba.OutbppDSC = TruncToValidBPP(
4142 (1.0 - mode_lib->vba.Downspreading / 100.0) * (1.0 - mode_lib->vba.EffectiveFECOverhead / 100.0) * 810.0
4143 * mode_lib->vba.OutputLinkDPLanes[k] / mode_lib->vba.PixelClockBackEnd[k] * 8.0,
4144 true,
4145 mode_lib->vba.Output[k],
4146 mode_lib->vba.OutputFormat[k],
4147 mode_lib->vba.DSCInputBitPerComponent[k]);
4148 if (mode_lib->vba.DSCEnabled[k] == true || mode_lib->vba.Outbpp == BPP_INVALID) {
4149 locals->RequiresDSC[i][k] = true;
4150 if (mode_lib->vba.Output[k] == dm_dp) {
4151 locals->RequiresFEC[i][k] = true;
4152 } else {
4153 locals->RequiresFEC[i][k] = false;
4154 }
4155 mode_lib->vba.Outbpp = mode_lib->vba.OutbppDSC;
4156 } else {
4157 locals->RequiresDSC[i][k] = false;
4158 locals->RequiresFEC[i][k] = false;
4159 }
4160 locals->OutputBppPerState[i][k] =
4161 mode_lib->vba.Outbpp;
4162 }
4163 }
4164 } else {
4165 locals->OutputBppPerState[i][k] = BPP_BLENDED_PIPE;
4166 }
4167 }
4168 }
4169 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4170 locals->DIOSupport[i] = true;
4171 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4172 if (!mode_lib->vba.skip_dio_check[k]
4173 && (locals->OutputBppPerState[i][k] == BPP_INVALID
4174 || (mode_lib->vba.OutputFormat[k] == dm_420
4175 && mode_lib->vba.Interlace[k] == true
4176 && mode_lib->vba.ProgressiveToInterlaceUnitInOPP == true))) {
4177 locals->DIOSupport[i] = false;
4178 }
4179 }
4180 }
4181 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4182 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4183 locals->DSCCLKRequiredMoreThanSupported[i] = false;
4184 if (mode_lib->vba.BlendingAndTiming[k] == k) {
4185 if ((mode_lib->vba.Output[k] == dm_dp
4186 || mode_lib->vba.Output[k] == dm_edp)) {
4187 if (mode_lib->vba.OutputFormat[k] == dm_420
4188 || mode_lib->vba.OutputFormat[k]
4189 == dm_n422) {
4190 mode_lib->vba.DSCFormatFactor = 2;
4191 } else {
4192 mode_lib->vba.DSCFormatFactor = 1;
4193 }
4194 if (locals->RequiresDSC[i][k] == true) {
4195 if (locals->ODMCombineEnablePerState[i][k] == dm_odm_combine_mode_2to1) {
4196 if (mode_lib->vba.PixelClockBackEnd[k] / 6.0 / mode_lib->vba.DSCFormatFactor
4197 > (1.0 - mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0) * mode_lib->vba.MaxDSCCLK[i]) {
4198 locals->DSCCLKRequiredMoreThanSupported[i] =
4199 true;
4200 }
4201 } else {
4202 if (mode_lib->vba.PixelClockBackEnd[k] / 3.0 / mode_lib->vba.DSCFormatFactor
4203 > (1.0 - mode_lib->vba.DISPCLKDPPCLKDSCCLKDownSpreading / 100.0) * mode_lib->vba.MaxDSCCLK[i]) {
4204 locals->DSCCLKRequiredMoreThanSupported[i] =
4205 true;
4206 }
4207 }
4208 }
4209 }
4210 }
4211 }
4212 }
4213 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4214 locals->NotEnoughDSCUnits[i] = false;
4215 mode_lib->vba.TotalDSCUnitsRequired = 0.0;
4216 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4217 if (locals->RequiresDSC[i][k] == true) {
4218 if (locals->ODMCombineEnablePerState[i][k] == dm_odm_combine_mode_2to1) {
4219 mode_lib->vba.TotalDSCUnitsRequired =
4220 mode_lib->vba.TotalDSCUnitsRequired + 2.0;
4221 } else {
4222 mode_lib->vba.TotalDSCUnitsRequired =
4223 mode_lib->vba.TotalDSCUnitsRequired + 1.0;
4224 }
4225 }
4226 }
4227 if (mode_lib->vba.TotalDSCUnitsRequired > mode_lib->vba.NumberOfDSC) {
4228 locals->NotEnoughDSCUnits[i] = true;
4229 }
4230 }
4231 /*DSC Delay per state*/
4232
4233 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4234 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4235 if (mode_lib->vba.BlendingAndTiming[k] != k) {
4236 mode_lib->vba.slices = 0;
4237 } else if (locals->RequiresDSC[i][k] == 0
4238 || locals->RequiresDSC[i][k] == false) {
4239 mode_lib->vba.slices = 0;
4240 } else if (mode_lib->vba.PixelClockBackEnd[k] > 3200.0) {
4241 mode_lib->vba.slices = dml_ceil(
4242 mode_lib->vba.PixelClockBackEnd[k] / 400.0,
4243 4.0);
4244 } else if (mode_lib->vba.PixelClockBackEnd[k] > 1360.0) {
4245 mode_lib->vba.slices = 8.0;
4246 } else if (mode_lib->vba.PixelClockBackEnd[k] > 680.0) {
4247 mode_lib->vba.slices = 4.0;
4248 } else if (mode_lib->vba.PixelClockBackEnd[k] > 340.0) {
4249 mode_lib->vba.slices = 2.0;
4250 } else {
4251 mode_lib->vba.slices = 1.0;
4252 }
4253 if (locals->OutputBppPerState[i][k] == BPP_BLENDED_PIPE
4254 || locals->OutputBppPerState[i][k] == BPP_INVALID) {
4255 mode_lib->vba.bpp = 0.0;
4256 } else {
4257 mode_lib->vba.bpp = locals->OutputBppPerState[i][k];
4258 }
4259 if (locals->RequiresDSC[i][k] == true && mode_lib->vba.bpp != 0.0) {
4260 if (locals->ODMCombineEnablePerState[i][k] == dm_odm_combine_mode_disabled) {
4261 locals->DSCDelayPerState[i][k] =
4262 dscceComputeDelay(
4263 mode_lib->vba.DSCInputBitPerComponent[k],
4264 mode_lib->vba.bpp,
4265 dml_ceil(
4266 mode_lib->vba.HActive[k]
4267 / mode_lib->vba.slices,
4268 1.0),
4269 mode_lib->vba.slices,
4270 mode_lib->vba.OutputFormat[k])
4271 + dscComputeDelay(
4272 mode_lib->vba.OutputFormat[k]);
4273 } else {
4274 locals->DSCDelayPerState[i][k] =
4275 2.0 * (dscceComputeDelay(
4276 mode_lib->vba.DSCInputBitPerComponent[k],
4277 mode_lib->vba.bpp,
4278 dml_ceil(mode_lib->vba.HActive[k] / mode_lib->vba.slices, 1.0),
4279 mode_lib->vba.slices / 2,
4280 mode_lib->vba.OutputFormat[k])
4281 + dscComputeDelay(mode_lib->vba.OutputFormat[k]));
4282 }
4283 locals->DSCDelayPerState[i][k] =
4284 locals->DSCDelayPerState[i][k] * mode_lib->vba.PixelClock[k] / mode_lib->vba.PixelClockBackEnd[k];
4285 } else {
4286 locals->DSCDelayPerState[i][k] = 0.0;
4287 }
4288 }
4289 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4290 for (m = 0; m <= mode_lib->vba.NumberOfActivePlanes - 1; m++) {
4291 for (j = 0; j <= mode_lib->vba.NumberOfActivePlanes - 1; j++) {
4292 if (mode_lib->vba.BlendingAndTiming[k] == m && locals->RequiresDSC[i][m] == true)
4293 locals->DSCDelayPerState[i][k] = locals->DSCDelayPerState[i][m];
4294 }
4295 }
4296 }
4297 }
4298
4299 //Prefetch Check
4300 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4301 for (j = 0; j < 2; j++) {
4302 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4303 if (locals->ODMCombineEnablePerState[i][k] == dm_odm_combine_mode_2to1)
4304 locals->SwathWidthYPerState[i][j][k] = dml_min(locals->SwathWidthYSingleDPP[k], dml_round(locals->HActive[k] / 2 * locals->HRatio[k]));
4305 else
4306 locals->SwathWidthYPerState[i][j][k] = locals->SwathWidthYSingleDPP[k] / locals->NoOfDPP[i][j][k];
4307 locals->SwathWidthGranularityY = 256 / dml_ceil(locals->BytePerPixelInDETY[k], 1) / locals->MaxSwathHeightY[k];
4308 locals->RoundedUpMaxSwathSizeBytesY = (dml_ceil(locals->SwathWidthYPerState[i][j][k] - 1, locals->SwathWidthGranularityY)
4309 + locals->SwathWidthGranularityY) * locals->BytePerPixelInDETY[k] * locals->MaxSwathHeightY[k];
4310 if (locals->SourcePixelFormat[k] == dm_420_10) {
4311 locals->RoundedUpMaxSwathSizeBytesY = dml_ceil(locals->RoundedUpMaxSwathSizeBytesY, 256) + 256;
4312 }
4313 if (locals->MaxSwathHeightC[k] > 0) {
4314 locals->SwathWidthGranularityC = 256 / dml_ceil(locals->BytePerPixelInDETC[k], 2) / locals->MaxSwathHeightC[k];
4315
4316 locals->RoundedUpMaxSwathSizeBytesC = (dml_ceil(locals->SwathWidthYPerState[i][j][k] / 2 - 1, locals->SwathWidthGranularityC)
4317 + locals->SwathWidthGranularityC) * locals->BytePerPixelInDETC[k] * locals->MaxSwathHeightC[k];
4318 }
4319 if (locals->SourcePixelFormat[k] == dm_420_10) {
4320 locals->RoundedUpMaxSwathSizeBytesC = dml_ceil(locals->RoundedUpMaxSwathSizeBytesC, 256) + 256;
4321 } else {
4322 locals->RoundedUpMaxSwathSizeBytesC = 0;
4323 }
4324
4325 if (locals->RoundedUpMaxSwathSizeBytesY + locals->RoundedUpMaxSwathSizeBytesC <= locals->DETBufferSizeInKByte[0] * 1024 / 2) {
4326 locals->SwathHeightYPerState[i][j][k] = locals->MaxSwathHeightY[k];
4327 locals->SwathHeightCPerState[i][j][k] = locals->MaxSwathHeightC[k];
4328 } else {
4329 locals->SwathHeightYPerState[i][j][k] = locals->MinSwathHeightY[k];
4330 locals->SwathHeightCPerState[i][j][k] = locals->MinSwathHeightC[k];
4331 }
4332
4333 if (locals->BytePerPixelInDETC[k] == 0) {
4334 locals->LinesInDETLuma = locals->DETBufferSizeInKByte[0] * 1024 / locals->BytePerPixelInDETY[k] / locals->SwathWidthYPerState[i][j][k];
4335 locals->LinesInDETChroma = 0;
4336 } else if (locals->SwathHeightYPerState[i][j][k] <= locals->SwathHeightCPerState[i][j][k]) {
4337 locals->LinesInDETLuma = locals->DETBufferSizeInKByte[0] * 1024 / 2 / locals->BytePerPixelInDETY[k] /
4338 locals->SwathWidthYPerState[i][j][k];
4339 locals->LinesInDETChroma = locals->DETBufferSizeInKByte[0] * 1024 / 2 / locals->BytePerPixelInDETC[k] / (locals->SwathWidthYPerState[i][j][k] / 2);
4340 } else {
4341 locals->LinesInDETLuma = locals->DETBufferSizeInKByte[0] * 1024 * 2 / 3 / locals->BytePerPixelInDETY[k] / locals->SwathWidthYPerState[i][j][k];
4342 locals->LinesInDETChroma = locals->DETBufferSizeInKByte[0] * 1024 / 3 / locals->BytePerPixelInDETY[k] / (locals->SwathWidthYPerState[i][j][k] / 2);
4343 }
4344
4345 locals->EffectiveLBLatencyHidingSourceLinesLuma = dml_min(locals->MaxLineBufferLines,
4346 dml_floor(locals->LineBufferSize / locals->LBBitPerPixel[k] / (locals->SwathWidthYPerState[i][j][k]
4347 / dml_max(locals->HRatio[k], 1)), 1)) - (locals->vtaps[k] - 1);
4348
4349 locals->EffectiveLBLatencyHidingSourceLinesChroma = dml_min(locals->MaxLineBufferLines,
4350 dml_floor(locals->LineBufferSize / locals->LBBitPerPixel[k]
4351 / (locals->SwathWidthYPerState[i][j][k] / 2
4352 / dml_max(locals->HRatio[k] / 2, 1)), 1)) - (locals->VTAPsChroma[k] - 1);
4353
4354 locals->EffectiveDETLBLinesLuma = dml_floor(locals->LinesInDETLuma + dml_min(
4355 locals->LinesInDETLuma * locals->RequiredDISPCLK[i][j] * locals->BytePerPixelInDETY[k] *
4356 locals->PSCL_FACTOR[k] / locals->ReturnBWPerState[i][0],
4357 locals->EffectiveLBLatencyHidingSourceLinesLuma),
4358 locals->SwathHeightYPerState[i][j][k]);
4359
4360 locals->EffectiveDETLBLinesChroma = dml_floor(locals->LinesInDETChroma + dml_min(
4361 locals->LinesInDETChroma * locals->RequiredDISPCLK[i][j] * locals->BytePerPixelInDETC[k] *
4362 locals->PSCL_FACTOR_CHROMA[k] / locals->ReturnBWPerState[i][0],
4363 locals->EffectiveLBLatencyHidingSourceLinesChroma),
4364 locals->SwathHeightCPerState[i][j][k]);
4365
4366 if (locals->BytePerPixelInDETC[k] == 0) {
4367 locals->UrgentLatencySupportUsPerState[i][j][k] = locals->EffectiveDETLBLinesLuma * (locals->HTotal[k] / locals->PixelClock[k])
4368 / locals->VRatio[k] - locals->EffectiveDETLBLinesLuma * locals->SwathWidthYPerState[i][j][k] *
4369 dml_ceil(locals->BytePerPixelInDETY[k], 1) / (locals->ReturnBWPerState[i][0] / locals->NoOfDPP[i][j][k]);
4370 } else {
4371 locals->UrgentLatencySupportUsPerState[i][j][k] = dml_min(
4372 locals->EffectiveDETLBLinesLuma * (locals->HTotal[k] / locals->PixelClock[k])
4373 / locals->VRatio[k] - locals->EffectiveDETLBLinesLuma * locals->SwathWidthYPerState[i][j][k] *
4374 dml_ceil(locals->BytePerPixelInDETY[k], 1) / (locals->ReturnBWPerState[i][0] / locals->NoOfDPP[i][j][k]),
4375 locals->EffectiveDETLBLinesChroma * (locals->HTotal[k] / locals->PixelClock[k]) / (locals->VRatio[k] / 2) -
4376 locals->EffectiveDETLBLinesChroma * locals->SwathWidthYPerState[i][j][k] / 2 *
4377 dml_ceil(locals->BytePerPixelInDETC[k], 2) / (locals->ReturnBWPerState[i][0] / locals->NoOfDPP[i][j][k]));
4378 }
4379 }
4380 }
4381 }
4382
4383 for (i = 0; i <= locals->soc.num_states; i++) {
4384 for (j = 0; j < 2; j++) {
4385 locals->UrgentLatencySupport[i][j] = true;
4386 for (k = 0; k < locals->NumberOfActivePlanes; k++) {
4387 if (locals->UrgentLatencySupportUsPerState[i][j][k] < locals->UrgentLatency)
4388 locals->UrgentLatencySupport[i][j] = false;
4389 }
4390 }
4391 }
4392
4393
4394 /*Prefetch Check*/
4395 for (i = 0; i <= locals->soc.num_states; i++) {
4396 for (j = 0; j < 2; j++) {
4397 locals->TotalNumberOfDCCActiveDPP[i][j] = 0;
4398 for (k = 0; k < locals->NumberOfActivePlanes; k++) {
4399 if (locals->DCCEnable[k] == true) {
4400 locals->TotalNumberOfDCCActiveDPP[i][j] =
4401 locals->TotalNumberOfDCCActiveDPP[i][j] + locals->NoOfDPP[i][j][k];
4402 }
4403 }
4404 }
4405 }
4406
4407 CalculateMinAndMaxPrefetchMode(locals->AllowDRAMSelfRefreshOrDRAMClockChangeInVblank, &locals->MinPrefetchMode, &locals->MaxPrefetchMode);
4408
4409 for (i = 0; i <= locals->soc.num_states; i++) {
4410 for (j = 0; j < 2; j++) {
4411 for (k = 0; k < locals->NumberOfActivePlanes; k++) {
4412 locals->NoOfDPPThisState[k] = locals->NoOfDPP[i][j][k];
4413 locals->RequiredDPPCLKThisState[k] = locals->RequiredDPPCLK[i][j][k];
4414 locals->SwathHeightYThisState[k] = locals->SwathHeightYPerState[i][j][k];
4415 locals->SwathHeightCThisState[k] = locals->SwathHeightCPerState[i][j][k];
4416 locals->SwathWidthYThisState[k] = locals->SwathWidthYPerState[i][j][k];
4417 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0] = dml_max(
4418 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4419 mode_lib->vba.PixelClock[k] / 16.0);
4420 if (mode_lib->vba.BytePerPixelInDETC[k] == 0.0) {
4421 if (mode_lib->vba.VRatio[k] <= 1.0) {
4422 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0] =
4423 dml_max(
4424 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4425 1.1
4426 * dml_ceil(
4427 mode_lib->vba.BytePerPixelInDETY[k],
4428 1.0)
4429 / 64.0
4430 * mode_lib->vba.HRatio[k]
4431 * mode_lib->vba.PixelClock[k]
4432 / mode_lib->vba.NoOfDPP[i][j][k]);
4433 } else {
4434 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0] =
4435 dml_max(
4436 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4437 1.1
4438 * dml_ceil(
4439 mode_lib->vba.BytePerPixelInDETY[k],
4440 1.0)
4441 / 64.0
4442 * mode_lib->vba.PSCL_FACTOR[k]
4443 * mode_lib->vba.RequiredDPPCLK[i][j][k]);
4444 }
4445 } else {
4446 if (mode_lib->vba.VRatio[k] <= 1.0) {
4447 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0] =
4448 dml_max(
4449 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4450 1.1
4451 * dml_ceil(
4452 mode_lib->vba.BytePerPixelInDETY[k],
4453 1.0)
4454 / 32.0
4455 * mode_lib->vba.HRatio[k]
4456 * mode_lib->vba.PixelClock[k]
4457 / mode_lib->vba.NoOfDPP[i][j][k]);
4458 } else {
4459 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0] =
4460 dml_max(
4461 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4462 1.1
4463 * dml_ceil(
4464 mode_lib->vba.BytePerPixelInDETY[k],
4465 1.0)
4466 / 32.0
4467 * mode_lib->vba.PSCL_FACTOR[k]
4468 * mode_lib->vba.RequiredDPPCLK[i][j][k]);
4469 }
4470 if (mode_lib->vba.VRatio[k] / 2.0 <= 1.0) {
4471 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0] =
4472 dml_max(
4473 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4474 1.1
4475 * dml_ceil(
4476 mode_lib->vba.BytePerPixelInDETC[k],
4477 2.0)
4478 / 32.0
4479 * mode_lib->vba.HRatio[k]
4480 / 2.0
4481 * mode_lib->vba.PixelClock[k]
4482 / mode_lib->vba.NoOfDPP[i][j][k]);
4483 } else {
4484 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0] =
4485 dml_max(
4486 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4487 1.1
4488 * dml_ceil(
4489 mode_lib->vba.BytePerPixelInDETC[k],
4490 2.0)
4491 / 32.0
4492 * mode_lib->vba.PSCL_FACTOR_CHROMA[k]
4493 * mode_lib->vba.RequiredDPPCLK[i][j][k]);
4494 }
4495 }
4496 }
4497 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4498 mode_lib->vba.PDEAndMetaPTEBytesPerFrameY = CalculateVMAndRowBytes(
4499 mode_lib,
4500 mode_lib->vba.DCCEnable[k],
4501 mode_lib->vba.Read256BlockHeightY[k],
4502 mode_lib->vba.Read256BlockWidthY[k],
4503 mode_lib->vba.SourcePixelFormat[k],
4504 mode_lib->vba.SurfaceTiling[k],
4505 dml_ceil(mode_lib->vba.BytePerPixelInDETY[k], 1.0),
4506 mode_lib->vba.SourceScan[k],
4507 mode_lib->vba.ViewportWidth[k],
4508 mode_lib->vba.ViewportHeight[k],
4509 mode_lib->vba.SwathWidthYPerState[i][j][k],
4510 mode_lib->vba.GPUVMEnable,
4511 mode_lib->vba.VMMPageSize,
4512 mode_lib->vba.PTEBufferSizeInRequestsLuma,
4513 mode_lib->vba.PDEProcessingBufIn64KBReqs,
4514 mode_lib->vba.PitchY[k],
4515 mode_lib->vba.DCCMetaPitchY[k],
4516 &mode_lib->vba.MacroTileWidthY[k],
4517 &mode_lib->vba.MetaRowBytesY,
4518 &mode_lib->vba.DPTEBytesPerRowY,
4519 &mode_lib->vba.PTEBufferSizeNotExceededY[i][j][k],
4520 &mode_lib->vba.dpte_row_height[k],
4521 &mode_lib->vba.meta_row_height[k]);
4522 mode_lib->vba.PrefetchLinesY[0][0][k] = CalculatePrefetchSourceLines(
4523 mode_lib,
4524 mode_lib->vba.VRatio[k],
4525 mode_lib->vba.vtaps[k],
4526 mode_lib->vba.Interlace[k],
4527 mode_lib->vba.ProgressiveToInterlaceUnitInOPP,
4528 mode_lib->vba.SwathHeightYPerState[i][j][k],
4529 mode_lib->vba.ViewportYStartY[k],
4530 &mode_lib->vba.PrefillY[k],
4531 &mode_lib->vba.MaxNumSwY[k]);
4532 if ((mode_lib->vba.SourcePixelFormat[k] != dm_444_64
4533 && mode_lib->vba.SourcePixelFormat[k] != dm_444_32
4534 && mode_lib->vba.SourcePixelFormat[k] != dm_444_16
4535 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_16
4536 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_8)) {
4537 mode_lib->vba.PDEAndMetaPTEBytesPerFrameC = CalculateVMAndRowBytes(
4538 mode_lib,
4539 mode_lib->vba.DCCEnable[k],
4540 mode_lib->vba.Read256BlockHeightY[k],
4541 mode_lib->vba.Read256BlockWidthY[k],
4542 mode_lib->vba.SourcePixelFormat[k],
4543 mode_lib->vba.SurfaceTiling[k],
4544 dml_ceil(mode_lib->vba.BytePerPixelInDETC[k], 2.0),
4545 mode_lib->vba.SourceScan[k],
4546 mode_lib->vba.ViewportWidth[k] / 2.0,
4547 mode_lib->vba.ViewportHeight[k] / 2.0,
4548 mode_lib->vba.SwathWidthYPerState[i][j][k] / 2.0,
4549 mode_lib->vba.GPUVMEnable,
4550 mode_lib->vba.VMMPageSize,
4551 mode_lib->vba.PTEBufferSizeInRequestsLuma,
4552 mode_lib->vba.PDEProcessingBufIn64KBReqs,
4553 mode_lib->vba.PitchC[k],
4554 0.0,
4555 &mode_lib->vba.MacroTileWidthC[k],
4556 &mode_lib->vba.MetaRowBytesC,
4557 &mode_lib->vba.DPTEBytesPerRowC,
4558 &mode_lib->vba.PTEBufferSizeNotExceededC[i][j][k],
4559 &mode_lib->vba.dpte_row_height_chroma[k],
4560 &mode_lib->vba.meta_row_height_chroma[k]);
4561 mode_lib->vba.PrefetchLinesC[0][0][k] = CalculatePrefetchSourceLines(
4562 mode_lib,
4563 mode_lib->vba.VRatio[k] / 2.0,
4564 mode_lib->vba.VTAPsChroma[k],
4565 mode_lib->vba.Interlace[k],
4566 mode_lib->vba.ProgressiveToInterlaceUnitInOPP,
4567 mode_lib->vba.SwathHeightCPerState[i][j][k],
4568 mode_lib->vba.ViewportYStartC[k],
4569 &mode_lib->vba.PrefillC[k],
4570 &mode_lib->vba.MaxNumSwC[k]);
4571 } else {
4572 mode_lib->vba.PDEAndMetaPTEBytesPerFrameC = 0.0;
4573 mode_lib->vba.MetaRowBytesC = 0.0;
4574 mode_lib->vba.DPTEBytesPerRowC = 0.0;
4575 locals->PrefetchLinesC[0][0][k] = 0.0;
4576 locals->PTEBufferSizeNotExceededC[i][j][k] = true;
4577 locals->PTEBufferSizeInRequestsForLuma = mode_lib->vba.PTEBufferSizeInRequestsLuma + mode_lib->vba.PTEBufferSizeInRequestsChroma;
4578 }
4579 locals->PDEAndMetaPTEBytesPerFrame[0][0][k] =
4580 mode_lib->vba.PDEAndMetaPTEBytesPerFrameY + mode_lib->vba.PDEAndMetaPTEBytesPerFrameC;
4581 locals->MetaRowBytes[0][0][k] = mode_lib->vba.MetaRowBytesY + mode_lib->vba.MetaRowBytesC;
4582 locals->DPTEBytesPerRow[0][0][k] = mode_lib->vba.DPTEBytesPerRowY + mode_lib->vba.DPTEBytesPerRowC;
4583
4584 CalculateActiveRowBandwidth(
4585 mode_lib->vba.GPUVMEnable,
4586 mode_lib->vba.SourcePixelFormat[k],
4587 mode_lib->vba.VRatio[k],
4588 mode_lib->vba.DCCEnable[k],
4589 mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k],
4590 mode_lib->vba.MetaRowBytesY,
4591 mode_lib->vba.MetaRowBytesC,
4592 mode_lib->vba.meta_row_height[k],
4593 mode_lib->vba.meta_row_height_chroma[k],
4594 mode_lib->vba.DPTEBytesPerRowY,
4595 mode_lib->vba.DPTEBytesPerRowC,
4596 mode_lib->vba.dpte_row_height[k],
4597 mode_lib->vba.dpte_row_height_chroma[k],
4598 &mode_lib->vba.meta_row_bw[k],
4599 &mode_lib->vba.dpte_row_bw[k],
4600 &mode_lib->vba.qual_row_bw[k]);
4601 }
4602 mode_lib->vba.ExtraLatency =
4603 mode_lib->vba.UrgentRoundTripAndOutOfOrderLatencyPerState[i]
4604 + (mode_lib->vba.TotalNumberOfActiveDPP[i][j]
4605 * mode_lib->vba.PixelChunkSizeInKByte
4606 + mode_lib->vba.TotalNumberOfDCCActiveDPP[i][j]
4607 * mode_lib->vba.MetaChunkSize)
4608 * 1024.0
4609 / mode_lib->vba.ReturnBWPerState[i][0];
4610 if (mode_lib->vba.GPUVMEnable == true) {
4611 mode_lib->vba.ExtraLatency = mode_lib->vba.ExtraLatency
4612 + mode_lib->vba.TotalNumberOfActiveDPP[i][j]
4613 * mode_lib->vba.PTEGroupSize
4614 / mode_lib->vba.ReturnBWPerState[i][0];
4615 }
4616 mode_lib->vba.TimeCalc = 24.0 / mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0];
4617
4618 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4619 if (mode_lib->vba.BlendingAndTiming[k] == k) {
4620 if (mode_lib->vba.WritebackEnable[k] == true) {
4621 locals->WritebackDelay[i][k] = mode_lib->vba.WritebackLatency
4622 + CalculateWriteBackDelay(
4623 mode_lib->vba.WritebackPixelFormat[k],
4624 mode_lib->vba.WritebackHRatio[k],
4625 mode_lib->vba.WritebackVRatio[k],
4626 mode_lib->vba.WritebackLumaHTaps[k],
4627 mode_lib->vba.WritebackLumaVTaps[k],
4628 mode_lib->vba.WritebackChromaHTaps[k],
4629 mode_lib->vba.WritebackChromaVTaps[k],
4630 mode_lib->vba.WritebackDestinationWidth[k]) / locals->RequiredDISPCLK[i][j];
4631 } else {
4632 locals->WritebackDelay[i][k] = 0.0;
4633 }
4634 for (m = 0; m <= mode_lib->vba.NumberOfActivePlanes - 1; m++) {
4635 if (mode_lib->vba.BlendingAndTiming[m] == k
4636 && mode_lib->vba.WritebackEnable[m]
4637 == true) {
4638 locals->WritebackDelay[i][k] = dml_max(locals->WritebackDelay[i][k],
4639 mode_lib->vba.WritebackLatency + CalculateWriteBackDelay(
4640 mode_lib->vba.WritebackPixelFormat[m],
4641 mode_lib->vba.WritebackHRatio[m],
4642 mode_lib->vba.WritebackVRatio[m],
4643 mode_lib->vba.WritebackLumaHTaps[m],
4644 mode_lib->vba.WritebackLumaVTaps[m],
4645 mode_lib->vba.WritebackChromaHTaps[m],
4646 mode_lib->vba.WritebackChromaVTaps[m],
4647 mode_lib->vba.WritebackDestinationWidth[m]) / locals->RequiredDISPCLK[i][j]);
4648 }
4649 }
4650 }
4651 }
4652 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4653 for (m = 0; m <= mode_lib->vba.NumberOfActivePlanes - 1; m++) {
4654 if (mode_lib->vba.BlendingAndTiming[k] == m) {
4655 locals->WritebackDelay[i][k] = locals->WritebackDelay[i][m];
4656 }
4657 }
4658 }
4659 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4660 for (m = 0; m < locals->NumberOfCursors[k]; m++)
4661 locals->cursor_bw[k] = locals->NumberOfCursors[k] * locals->CursorWidth[k][m] * locals->CursorBPP[k][m]
4662 / 8 / (locals->HTotal[k] / locals->PixelClock[k]) * locals->VRatio[k];
4663 }
4664
4665 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4666 locals->MaximumVStartup[0][0][k] = mode_lib->vba.VTotal[k] - mode_lib->vba.VActive[k]
4667 - dml_max(1.0, dml_ceil(locals->WritebackDelay[i][k] / (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k]), 1.0));
4668 }
4669
4670 mode_lib->vba.NextPrefetchMode = mode_lib->vba.MinPrefetchMode;
4671 do {
4672 mode_lib->vba.PrefetchMode[i][j] = mode_lib->vba.NextPrefetchMode;
4673 mode_lib->vba.NextPrefetchMode = mode_lib->vba.NextPrefetchMode + 1;
4674
4675 mode_lib->vba.TWait = CalculateTWait(
4676 mode_lib->vba.PrefetchMode[i][j],
4677 mode_lib->vba.DRAMClockChangeLatency,
4678 mode_lib->vba.UrgentLatency,
4679 mode_lib->vba.SREnterPlusExitTime);
4680 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4681
4682 if (mode_lib->vba.XFCEnabled[k] == true) {
4683 mode_lib->vba.XFCRemoteSurfaceFlipDelay =
4684 CalculateRemoteSurfaceFlipDelay(
4685 mode_lib,
4686 mode_lib->vba.VRatio[k],
4687 locals->SwathWidthYPerState[i][j][k],
4688 dml_ceil(locals->BytePerPixelInDETY[k], 1.0),
4689 mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k],
4690 mode_lib->vba.XFCTSlvVupdateOffset,
4691 mode_lib->vba.XFCTSlvVupdateWidth,
4692 mode_lib->vba.XFCTSlvVreadyOffset,
4693 mode_lib->vba.XFCXBUFLatencyTolerance,
4694 mode_lib->vba.XFCFillBWOverhead,
4695 mode_lib->vba.XFCSlvChunkSize,
4696 mode_lib->vba.XFCBusTransportTime,
4697 mode_lib->vba.TimeCalc,
4698 mode_lib->vba.TWait,
4699 &mode_lib->vba.SrcActiveDrainRate,
4700 &mode_lib->vba.TInitXFill,
4701 &mode_lib->vba.TslvChk);
4702 } else {
4703 mode_lib->vba.XFCRemoteSurfaceFlipDelay = 0.0;
4704 }
4705 mode_lib->vba.IsErrorResult[i][j][k] =
4706 CalculatePrefetchSchedule(
4707 mode_lib,
4708 mode_lib->vba.RequiredDPPCLK[i][j][k],
4709 mode_lib->vba.RequiredDISPCLK[i][j],
4710 mode_lib->vba.PixelClock[k],
4711 mode_lib->vba.ProjectedDCFCLKDeepSleep[0][0],
4712 mode_lib->vba.DSCDelayPerState[i][k],
4713 mode_lib->vba.NoOfDPP[i][j][k],
4714 mode_lib->vba.ScalerEnabled[k],
4715 mode_lib->vba.NumberOfCursors[k],
4716 mode_lib->vba.DPPCLKDelaySubtotal,
4717 mode_lib->vba.DPPCLKDelaySCL,
4718 mode_lib->vba.DPPCLKDelaySCLLBOnly,
4719 mode_lib->vba.DPPCLKDelayCNVCFormater,
4720 mode_lib->vba.DPPCLKDelayCNVCCursor,
4721 mode_lib->vba.DISPCLKDelaySubtotal,
4722 mode_lib->vba.SwathWidthYPerState[i][j][k]
4723 / mode_lib->vba.HRatio[k],
4724 mode_lib->vba.OutputFormat[k],
4725 mode_lib->vba.VTotal[k]
4726 - mode_lib->vba.VActive[k],
4727 mode_lib->vba.HTotal[k],
4728 mode_lib->vba.MaxInterDCNTileRepeaters,
4729 mode_lib->vba.MaximumVStartup[0][0][k],
4730 mode_lib->vba.GPUVMMaxPageTableLevels,
4731 mode_lib->vba.GPUVMEnable,
4732 mode_lib->vba.DynamicMetadataEnable[k],
4733 mode_lib->vba.DynamicMetadataLinesBeforeActiveRequired[k],
4734 mode_lib->vba.DynamicMetadataTransmittedBytes[k],
4735 mode_lib->vba.DCCEnable[k],
4736 mode_lib->vba.UrgentLatencyPixelDataOnly,
4737 mode_lib->vba.ExtraLatency,
4738 mode_lib->vba.TimeCalc,
4739 mode_lib->vba.PDEAndMetaPTEBytesPerFrame[0][0][k],
4740 mode_lib->vba.MetaRowBytes[0][0][k],
4741 mode_lib->vba.DPTEBytesPerRow[0][0][k],
4742 mode_lib->vba.PrefetchLinesY[0][0][k],
4743 mode_lib->vba.SwathWidthYPerState[i][j][k],
4744 mode_lib->vba.BytePerPixelInDETY[k],
4745 mode_lib->vba.PrefillY[k],
4746 mode_lib->vba.MaxNumSwY[k],
4747 mode_lib->vba.PrefetchLinesC[0][0][k],
4748 mode_lib->vba.BytePerPixelInDETC[k],
4749 mode_lib->vba.PrefillC[k],
4750 mode_lib->vba.MaxNumSwC[k],
4751 mode_lib->vba.SwathHeightYPerState[i][j][k],
4752 mode_lib->vba.SwathHeightCPerState[i][j][k],
4753 mode_lib->vba.TWait,
4754 mode_lib->vba.XFCEnabled[k],
4755 mode_lib->vba.XFCRemoteSurfaceFlipDelay,
4756 mode_lib->vba.Interlace[k],
4757 mode_lib->vba.ProgressiveToInterlaceUnitInOPP,
4758 mode_lib->vba.DSTXAfterScaler,
4759 mode_lib->vba.DSTYAfterScaler,
4760 &mode_lib->vba.LineTimesForPrefetch[k],
4761 &mode_lib->vba.PrefetchBW[k],
4762 &mode_lib->vba.LinesForMetaPTE[k],
4763 &mode_lib->vba.LinesForMetaAndDPTERow[k],
4764 &mode_lib->vba.VRatioPreY[i][j][k],
4765 &mode_lib->vba.VRatioPreC[i][j][k],
4766 &mode_lib->vba.RequiredPrefetchPixelDataBWLuma[i][j][k],
4767 &mode_lib->vba.VStartupRequiredWhenNotEnoughTimeForDynamicMetadata,
4768 &mode_lib->vba.Tno_bw[k],
4769 &mode_lib->vba.VUpdateOffsetPix[k],
4770 &mode_lib->vba.VUpdateWidthPix[k],
4771 &mode_lib->vba.VReadyOffsetPix[k]);
4772 }
4773 mode_lib->vba.MaximumReadBandwidthWithoutPrefetch = 0.0;
4774 mode_lib->vba.MaximumReadBandwidthWithPrefetch = 0.0;
4775 locals->prefetch_vm_bw_valid = true;
4776 locals->prefetch_row_bw_valid = true;
4777 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4778 if (locals->PDEAndMetaPTEBytesPerFrame[0][0][k] == 0)
4779 locals->prefetch_vm_bw[k] = 0;
4780 else if (locals->LinesForMetaPTE[k] > 0)
4781 locals->prefetch_vm_bw[k] = locals->PDEAndMetaPTEBytesPerFrame[0][0][k]
4782 / (locals->LinesForMetaPTE[k] * locals->HTotal[k] / locals->PixelClock[k]);
4783 else {
4784 locals->prefetch_vm_bw[k] = 0;
4785 locals->prefetch_vm_bw_valid = false;
4786 }
4787 if (locals->MetaRowBytes[0][0][k] + locals->DPTEBytesPerRow[0][0][k] == 0)
4788 locals->prefetch_row_bw[k] = 0;
4789 else if (locals->LinesForMetaAndDPTERow[k] > 0)
4790 locals->prefetch_row_bw[k] = (locals->MetaRowBytes[0][0][k] + locals->DPTEBytesPerRow[0][0][k])
4791 / (locals->LinesForMetaAndDPTERow[k] * locals->HTotal[k] / locals->PixelClock[k]);
4792 else {
4793 locals->prefetch_row_bw[k] = 0;
4794 locals->prefetch_row_bw_valid = false;
4795 }
4796
4797 mode_lib->vba.MaximumReadBandwidthWithoutPrefetch = mode_lib->vba.MaximumReadBandwidthWithPrefetch
4798 + mode_lib->vba.cursor_bw[k] + mode_lib->vba.ReadBandwidth[k] + mode_lib->vba.meta_row_bw[k] + mode_lib->vba.dpte_row_bw[k];
4799 mode_lib->vba.MaximumReadBandwidthWithPrefetch =
4800 mode_lib->vba.MaximumReadBandwidthWithPrefetch
4801 + mode_lib->vba.cursor_bw[k]
4802 + dml_max3(
4803 mode_lib->vba.prefetch_vm_bw[k],
4804 mode_lib->vba.prefetch_row_bw[k],
4805 dml_max(mode_lib->vba.ReadBandwidth[k],
4806 mode_lib->vba.RequiredPrefetchPixelDataBWLuma[i][j][k])
4807 + mode_lib->vba.meta_row_bw[k] + mode_lib->vba.dpte_row_bw[k]);
4808 }
4809 locals->BandwidthWithoutPrefetchSupported[i][0] = true;
4810 if (mode_lib->vba.MaximumReadBandwidthWithoutPrefetch > locals->ReturnBWPerState[i][0]) {
4811 locals->BandwidthWithoutPrefetchSupported[i][0] = false;
4812 }
4813
4814 locals->PrefetchSupported[i][j] = true;
4815 if (mode_lib->vba.MaximumReadBandwidthWithPrefetch > locals->ReturnBWPerState[i][0]) {
4816 locals->PrefetchSupported[i][j] = false;
4817 }
4818 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4819 if (locals->LineTimesForPrefetch[k] < 2.0
4820 || locals->LinesForMetaPTE[k] >= 8.0
4821 || locals->LinesForMetaAndDPTERow[k] >= 16.0
4822 || mode_lib->vba.IsErrorResult[i][j][k] == true) {
4823 locals->PrefetchSupported[i][j] = false;
4824 }
4825 }
4826 locals->VRatioInPrefetchSupported[i][j] = true;
4827 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4828 if (locals->VRatioPreY[i][j][k] > 4.0
4829 || locals->VRatioPreC[i][j][k] > 4.0
4830 || mode_lib->vba.IsErrorResult[i][j][k] == true) {
4831 locals->VRatioInPrefetchSupported[i][j] = false;
4832 }
4833 }
4834 } while ((locals->PrefetchSupported[i][j] != true || locals->VRatioInPrefetchSupported[i][j] != true)
4835 && mode_lib->vba.NextPrefetchMode < mode_lib->vba.MaxPrefetchMode);
4836
4837 if (mode_lib->vba.PrefetchSupported[i][j] == true
4838 && mode_lib->vba.VRatioInPrefetchSupported[i][j] == true) {
4839 mode_lib->vba.BandwidthAvailableForImmediateFlip =
4840 mode_lib->vba.ReturnBWPerState[i][0];
4841 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4842 mode_lib->vba.BandwidthAvailableForImmediateFlip =
4843 mode_lib->vba.BandwidthAvailableForImmediateFlip
4844 - mode_lib->vba.cursor_bw[k]
4845 - dml_max(
4846 mode_lib->vba.ReadBandwidth[k] + mode_lib->vba.qual_row_bw[k],
4847 mode_lib->vba.PrefetchBW[k]);
4848 }
4849 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4850 mode_lib->vba.ImmediateFlipBytes[k] = 0.0;
4851 if ((mode_lib->vba.SourcePixelFormat[k] != dm_420_8
4852 && mode_lib->vba.SourcePixelFormat[k] != dm_420_10)) {
4853 mode_lib->vba.ImmediateFlipBytes[k] =
4854 mode_lib->vba.PDEAndMetaPTEBytesPerFrame[0][0][k]
4855 + mode_lib->vba.MetaRowBytes[0][0][k]
4856 + mode_lib->vba.DPTEBytesPerRow[0][0][k];
4857 }
4858 }
4859 mode_lib->vba.TotImmediateFlipBytes = 0.0;
4860 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4861 if ((mode_lib->vba.SourcePixelFormat[k] != dm_420_8
4862 && mode_lib->vba.SourcePixelFormat[k] != dm_420_10)) {
4863 mode_lib->vba.TotImmediateFlipBytes =
4864 mode_lib->vba.TotImmediateFlipBytes
4865 + mode_lib->vba.ImmediateFlipBytes[k];
4866 }
4867 }
4868
4869 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4870 CalculateFlipSchedule(
4871 mode_lib,
4872 mode_lib->vba.ExtraLatency,
4873 mode_lib->vba.UrgentLatencyPixelDataOnly,
4874 mode_lib->vba.GPUVMMaxPageTableLevels,
4875 mode_lib->vba.GPUVMEnable,
4876 mode_lib->vba.BandwidthAvailableForImmediateFlip,
4877 mode_lib->vba.TotImmediateFlipBytes,
4878 mode_lib->vba.SourcePixelFormat[k],
4879 mode_lib->vba.ImmediateFlipBytes[k],
4880 mode_lib->vba.HTotal[k]
4881 / mode_lib->vba.PixelClock[k],
4882 mode_lib->vba.VRatio[k],
4883 mode_lib->vba.Tno_bw[k],
4884 mode_lib->vba.PDEAndMetaPTEBytesPerFrame[0][0][k],
4885 mode_lib->vba.MetaRowBytes[0][0][k],
4886 mode_lib->vba.DPTEBytesPerRow[0][0][k],
4887 mode_lib->vba.DCCEnable[k],
4888 mode_lib->vba.dpte_row_height[k],
4889 mode_lib->vba.meta_row_height[k],
4890 mode_lib->vba.qual_row_bw[k],
4891 &mode_lib->vba.DestinationLinesToRequestVMInImmediateFlip[k],
4892 &mode_lib->vba.DestinationLinesToRequestRowInImmediateFlip[k],
4893 &mode_lib->vba.final_flip_bw[k],
4894 &mode_lib->vba.ImmediateFlipSupportedForPipe[k]);
4895 }
4896 mode_lib->vba.total_dcn_read_bw_with_flip = 0.0;
4897 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4898 mode_lib->vba.total_dcn_read_bw_with_flip =
4899 mode_lib->vba.total_dcn_read_bw_with_flip
4900 + mode_lib->vba.cursor_bw[k]
4901 + dml_max3(
4902 mode_lib->vba.prefetch_vm_bw[k],
4903 mode_lib->vba.prefetch_row_bw[k],
4904 mode_lib->vba.final_flip_bw[k]
4905 + dml_max(
4906 mode_lib->vba.ReadBandwidth[k],
4907 mode_lib->vba.RequiredPrefetchPixelDataBWLuma[i][j][k]));
4908 }
4909 mode_lib->vba.ImmediateFlipSupportedForState[i][j] = true;
4910 if (mode_lib->vba.total_dcn_read_bw_with_flip
4911 > mode_lib->vba.ReturnBWPerState[i][0]) {
4912 mode_lib->vba.ImmediateFlipSupportedForState[i][j] = false;
4913 }
4914 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4915 if (mode_lib->vba.ImmediateFlipSupportedForPipe[k] == false) {
4916 mode_lib->vba.ImmediateFlipSupportedForState[i][j] = false;
4917 }
4918 }
4919 } else {
4920 mode_lib->vba.ImmediateFlipSupportedForState[i][j] = false;
4921 }
4922 }
4923 }
4924
4925 /*Vertical Active BW support*/
4926 mode_lib->vba.MaxTotalVActiveRDBandwidth = 0;
4927 for (k = 0; k < mode_lib->vba.NumberOfActivePlanes; k++)
4928 mode_lib->vba.MaxTotalVActiveRDBandwidth = mode_lib->vba.MaxTotalVActiveRDBandwidth + mode_lib->vba.ReadBandwidth[k];
4929 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4930 mode_lib->vba.MaxTotalVerticalActiveAvailableBandwidth[i][0] = dml_min(mode_lib->vba.ReturnBusWidth *
4931 mode_lib->vba.DCFCLKPerState[i], mode_lib->vba.FabricAndDRAMBandwidthPerState[i] * 1000) *
4932 mode_lib->vba.MaxAveragePercentOfIdealDRAMBWDisplayCanUseInNormalSystemOperation / 100;
4933 if (mode_lib->vba.MaxTotalVActiveRDBandwidth <= mode_lib->vba.MaxTotalVerticalActiveAvailableBandwidth[i][0])
4934 mode_lib->vba.TotalVerticalActiveBandwidthSupport[i][0] = true;
4935 else
4936 mode_lib->vba.TotalVerticalActiveBandwidthSupport[i][0] = false;
4937 }
4938
4939 /*PTE Buffer Size Check*/
4940
4941 for (i = 0; i <= mode_lib->vba.soc.num_states; i++) {
4942 for (j = 0; j < 2; j++) {
4943 locals->PTEBufferSizeNotExceeded[i][j] = true;
4944 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4945 if (locals->PTEBufferSizeNotExceededY[i][j][k] == false
4946 || locals->PTEBufferSizeNotExceededC[i][j][k] == false) {
4947 locals->PTEBufferSizeNotExceeded[i][j] = false;
4948 }
4949 }
4950 }
4951 }
4952 /*Cursor Support Check*/
4953 mode_lib->vba.CursorSupport = true;
4954 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4955 for (j = 0; j < 2; j++) {
4956 if (mode_lib->vba.CursorWidth[k][j] > 0.0) {
4957 if (dml_floor(
4958 dml_floor(
4959 mode_lib->vba.CursorBufferSize
4960 - mode_lib->vba.CursorChunkSize,
4961 mode_lib->vba.CursorChunkSize) * 1024.0
4962 / (mode_lib->vba.CursorWidth[k][j]
4963 * mode_lib->vba.CursorBPP[k][j]
4964 / 8.0),
4965 1.0)
4966 * (mode_lib->vba.HTotal[k] / mode_lib->vba.PixelClock[k])
4967 / mode_lib->vba.VRatio[k] < mode_lib->vba.UrgentLatencyPixelDataOnly
4968 || (mode_lib->vba.CursorBPP[k][j] == 64.0
4969 && mode_lib->vba.Cursor64BppSupport == false)) {
4970 mode_lib->vba.CursorSupport = false;
4971 }
4972 }
4973 }
4974 }
4975 /*Valid Pitch Check*/
4976
4977 mode_lib->vba.PitchSupport = true;
4978 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
4979 locals->AlignedYPitch[k] = dml_ceil(
4980 dml_max(mode_lib->vba.PitchY[k], mode_lib->vba.ViewportWidth[k]),
4981 locals->MacroTileWidthY[k]);
4982 if (locals->AlignedYPitch[k] > mode_lib->vba.PitchY[k]) {
4983 mode_lib->vba.PitchSupport = false;
4984 }
4985 if (mode_lib->vba.DCCEnable[k] == true) {
4986 locals->AlignedDCCMetaPitch[k] = dml_ceil(
4987 dml_max(
4988 mode_lib->vba.DCCMetaPitchY[k],
4989 mode_lib->vba.ViewportWidth[k]),
4990 64.0 * locals->Read256BlockWidthY[k]);
4991 } else {
4992 locals->AlignedDCCMetaPitch[k] = mode_lib->vba.DCCMetaPitchY[k];
4993 }
4994 if (locals->AlignedDCCMetaPitch[k] > mode_lib->vba.DCCMetaPitchY[k]) {
4995 mode_lib->vba.PitchSupport = false;
4996 }
4997 if (mode_lib->vba.SourcePixelFormat[k] != dm_444_64
4998 && mode_lib->vba.SourcePixelFormat[k] != dm_444_32
4999 && mode_lib->vba.SourcePixelFormat[k] != dm_444_16
5000 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_16
5001 && mode_lib->vba.SourcePixelFormat[k] != dm_mono_8) {
5002 locals->AlignedCPitch[k] = dml_ceil(
5003 dml_max(
5004 mode_lib->vba.PitchC[k],
5005 mode_lib->vba.ViewportWidth[k] / 2.0),
5006 locals->MacroTileWidthC[k]);
5007 } else {
5008 locals->AlignedCPitch[k] = mode_lib->vba.PitchC[k];
5009 }
5010 if (locals->AlignedCPitch[k] > mode_lib->vba.PitchC[k]) {
5011 mode_lib->vba.PitchSupport = false;
5012 }
5013 }
5014 /*Mode Support, Voltage State and SOC Configuration*/
5015
5016 for (i = mode_lib->vba.soc.num_states; i >= 0; i--) {
5017 for (j = 0; j < 2; j++) {
5018 enum dm_validation_status status = DML_VALIDATION_OK;
5019
5020 if (mode_lib->vba.ScaleRatioAndTapsSupport != true) {
5021 status = DML_FAIL_SCALE_RATIO_TAP;
5022 } else if (mode_lib->vba.SourceFormatPixelAndScanSupport != true) {
5023 status = DML_FAIL_SOURCE_PIXEL_FORMAT;
5024 } else if (locals->ViewportSizeSupport[i][0] != true) {
5025 status = DML_FAIL_VIEWPORT_SIZE;
5026 } else if (locals->DIOSupport[i] != true) {
5027 status = DML_FAIL_DIO_SUPPORT;
5028 } else if (locals->NotEnoughDSCUnits[i] != false) {
5029 status = DML_FAIL_NOT_ENOUGH_DSC;
5030 } else if (locals->DSCCLKRequiredMoreThanSupported[i] != false) {
5031 status = DML_FAIL_DSC_CLK_REQUIRED;
5032 } else if (locals->UrgentLatencySupport[i][j] != true) {
5033 status = DML_FAIL_URGENT_LATENCY;
5034 } else if (locals->ROBSupport[i][0] != true) {
5035 status = DML_FAIL_REORDERING_BUFFER;
5036 } else if (locals->DISPCLK_DPPCLK_Support[i][j] != true) {
5037 status = DML_FAIL_DISPCLK_DPPCLK;
5038 } else if (locals->TotalAvailablePipesSupport[i][j] != true) {
5039 status = DML_FAIL_TOTAL_AVAILABLE_PIPES;
5040 } else if (mode_lib->vba.NumberOfOTGSupport != true) {
5041 status = DML_FAIL_NUM_OTG;
5042 } else if (mode_lib->vba.WritebackModeSupport != true) {
5043 status = DML_FAIL_WRITEBACK_MODE;
5044 } else if (mode_lib->vba.WritebackLatencySupport != true) {
5045 status = DML_FAIL_WRITEBACK_LATENCY;
5046 } else if (mode_lib->vba.WritebackScaleRatioAndTapsSupport != true) {
5047 status = DML_FAIL_WRITEBACK_SCALE_RATIO_TAP;
5048 } else if (mode_lib->vba.CursorSupport != true) {
5049 status = DML_FAIL_CURSOR_SUPPORT;
5050 } else if (mode_lib->vba.PitchSupport != true) {
5051 status = DML_FAIL_PITCH_SUPPORT;
5052 } else if (locals->PrefetchSupported[i][j] != true) {
5053 status = DML_FAIL_PREFETCH_SUPPORT;
5054 } else if (locals->TotalVerticalActiveBandwidthSupport[i][0] != true) {
5055 status = DML_FAIL_TOTAL_V_ACTIVE_BW;
5056 } else if (locals->VRatioInPrefetchSupported[i][j] != true) {
5057 status = DML_FAIL_V_RATIO_PREFETCH;
5058 } else if (locals->PTEBufferSizeNotExceeded[i][j] != true) {
5059 status = DML_FAIL_PTE_BUFFER_SIZE;
5060 } else if (mode_lib->vba.NonsupportedDSCInputBPC != false) {
5061 status = DML_FAIL_DSC_INPUT_BPC;
5062 }
5063
5064 if (status == DML_VALIDATION_OK) {
5065 locals->ModeSupport[i][j] = true;
5066 } else {
5067 locals->ModeSupport[i][j] = false;
5068 }
5069 locals->ValidationStatus[i] = status;
5070 }
5071 }
5072 {
5073 unsigned int MaximumMPCCombine = 0;
5074 mode_lib->vba.VoltageLevel = mode_lib->vba.soc.num_states + 1;
5075 for (i = mode_lib->vba.VoltageOverrideLevel; i <= mode_lib->vba.soc.num_states; i++) {
5076 if (locals->ModeSupport[i][0] == true || locals->ModeSupport[i][1] == true) {
5077 mode_lib->vba.VoltageLevel = i;
5078 if (locals->ModeSupport[i][1] == true && (locals->ModeSupport[i][0] == false
5079 || mode_lib->vba.WhenToDoMPCCombine == dm_mpc_always_when_possible)) {
5080 MaximumMPCCombine = 1;
5081 } else {
5082 MaximumMPCCombine = 0;
5083 }
5084 break;
5085 }
5086 }
5087 mode_lib->vba.ImmediateFlipSupport =
5088 locals->ImmediateFlipSupportedForState[mode_lib->vba.VoltageLevel][MaximumMPCCombine];
5089 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
5090 mode_lib->vba.DPPPerPlane[k] = locals->NoOfDPP[mode_lib->vba.VoltageLevel][MaximumMPCCombine][k];
5091 locals->DPPCLK[k] = locals->RequiredDPPCLK[mode_lib->vba.VoltageLevel][MaximumMPCCombine][k];
5092 }
5093 mode_lib->vba.DISPCLK = locals->RequiredDISPCLK[mode_lib->vba.VoltageLevel][MaximumMPCCombine];
5094 mode_lib->vba.maxMpcComb = MaximumMPCCombine;
5095 }
5096 mode_lib->vba.DCFCLK = mode_lib->vba.DCFCLKPerState[mode_lib->vba.VoltageLevel];
5097 mode_lib->vba.DRAMSpeed = mode_lib->vba.DRAMSpeedPerState[mode_lib->vba.VoltageLevel];
5098 mode_lib->vba.FabricClock = mode_lib->vba.FabricClockPerState[mode_lib->vba.VoltageLevel];
5099 mode_lib->vba.SOCCLK = mode_lib->vba.SOCCLKPerState[mode_lib->vba.VoltageLevel];
5100 mode_lib->vba.ReturnBW = locals->ReturnBWPerState[mode_lib->vba.VoltageLevel][0];
5101 mode_lib->vba.FabricAndDRAMBandwidth = locals->FabricAndDRAMBandwidthPerState[mode_lib->vba.VoltageLevel];
5102 for (k = 0; k <= mode_lib->vba.NumberOfActivePlanes - 1; k++) {
5103 if (mode_lib->vba.BlendingAndTiming[k] == k) {
5104 mode_lib->vba.ODMCombineEnabled[k] =
5105 locals->ODMCombineEnablePerState[mode_lib->vba.VoltageLevel][k];
5106 } else {
5107 mode_lib->vba.ODMCombineEnabled[k] = 0;
5108 }
5109 mode_lib->vba.DSCEnabled[k] =
5110 locals->RequiresDSC[mode_lib->vba.VoltageLevel][k];
5111 mode_lib->vba.OutputBpp[k] =
5112 locals->OutputBppPerState[mode_lib->vba.VoltageLevel][k];
5113 }
5114 }
5115