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