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