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