Changeset 52136 in vbox for trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm
- Timestamp:
- Jul 22, 2014 7:36:45 PM (10 years ago)
- Location:
- trunk
- Files:
-
- 2 added
- 8 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk
- Property svn:mergeinfo changed
/branches/VBox-4.3 merged: 95154,95164
- Property svn:mergeinfo changed
-
trunk/src/VBox
- Property svn:mergeinfo changed
/branches/VBox-4.3/src/VBox merged: 95154,95164
- Property svn:mergeinfo changed
-
trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPMisc.cpp
r51943 r52136 707 707 708 708 Status = vboxWddmRegOpenKey(&hKey, VBOXWDDM_REG_DISPLAYSETTINGSVIDEOKEY, GENERIC_READ); 709 Assert(Status == STATUS_SUCCESS);709 //Assert(Status == STATUS_SUCCESS); 710 710 if (Status == STATUS_SUCCESS) 711 711 { … … 734 734 memcpy(pSubBuf, VBOXWDDM_REG_DISPLAYSETTINGSVIDEOKEY_SUBKEY, sizeof (VBOXWDDM_REG_DISPLAYSETTINGSVIDEOKEY_SUBKEY)); 735 735 Status = vboxWddmRegOpenKey(&hSubKey, KeyBuf, GENERIC_READ); 736 Assert(Status == STATUS_SUCCESS);736 //Assert(Status == STATUS_SUCCESS); 737 737 if (Status == STATUS_SUCCESS) 738 738 { … … 856 856 HANDLE hKey; 857 857 NTSTATUS Status = vboxWddmRegOpenDisplaySettingsKey(pDeviceExtension, VidPnSourceId, &hKey); 858 Assert(Status == STATUS_SUCCESS);858 //Assert(Status == STATUS_SUCCESS); 859 859 if (Status == STATUS_SUCCESS) 860 860 { -
trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPMisc.h
r51943 r52136 188 188 #endif 189 189 190 NTSTATUS vboxWddmChildStatusConnect(PVBOXMP_DEVEXT pDevExt, uint32_t iChild, BOOLEAN fConnect);191 192 190 #endif /* #ifndef ___VBoxMPMisc_h__ */ -
trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPTypes.h
r51260 r52136 34 34 #include "VBoxMPVbva.h" 35 35 #include "VBoxMPCr.h" 36 #include "VBoxMPVModes.h" 36 37 37 38 #ifdef VBOX_WITH_CROGL 38 39 #include <cr_vreg.h> 39 40 #endif 41 42 #include <cr_sortarray.h> 40 43 41 44 #if 0 … … 336 339 } VBOXWDDM_OPENALLOCATION, *PVBOXWDDM_OPENALLOCATION; 337 340 338 #define VBOXWDDM_MAX_VIDEOMODES 128 339 typedef struct VBOXWDDM_VIDEOMODES_INFO 340 { 341 int32_t iPreferredMode; 342 uint32_t cModes; 343 VIDEO_MODE_INFORMATION aModes[VBOXWDDM_MAX_VIDEOMODES]; 344 int32_t iPreferredResolution; 345 uint32_t cResolutions; 346 D3DKMDT_2DREGION aResolutions[VBOXWDDM_MAX_VIDEOMODES]; 347 } VBOXWDDM_VIDEOMODES_INFO, *PVBOXWDDM_VIDEOMODES_INFO; 341 #define VBOX_VMODES_MAX_COUNT 128 342 343 typedef struct VBOX_VMODES 344 { 345 uint32_t cTargets; 346 CR_SORTARRAY aTargets[VBOX_VIDEO_MAX_SCREENS]; 347 } VBOX_VMODES; 348 349 typedef struct VBOXWDDM_VMODES 350 { 351 VBOX_VMODES Modes; 352 /* note that we not use array indices to indentify modes, because indices may change due to element removal */ 353 uint64_t aTransientResolutions[VBOX_VIDEO_MAX_SCREENS]; 354 uint64_t aPendingRemoveCurResolutions[VBOX_VIDEO_MAX_SCREENS]; 355 } VBOXWDDM_VMODES; 348 356 349 357 #endif /* #ifndef ___VBoxMPTypes_h___ */ -
trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.cpp
r51960 r52136 119 119 } 120 120 121 NTSTATUS vboxVidPnCheckSourceModeInfo(const D3DKMDT_HVIDPN hDesiredVidPn, 122 const D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo, 123 BOOLEAN *pbSupported) 124 { 125 BOOLEAN bSupported = TRUE; 126 /* we support both GRAPHICS and TEXT modes */ 127 switch (pNewVidPnSourceModeInfo->Type) 128 { 129 case D3DKMDT_RMT_GRAPHICS: 130 /* any primary surface size actually 131 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cx 132 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cy 133 */ 134 if (pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cx != pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cx 135 || pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cy != pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cy) 136 { 137 LOG(("VisibleRegionSize(%d, %d) != PrimSurfSize(%d, %d)", 138 pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cx, 139 pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cy, 140 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cx, 141 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cy)); 142 AssertBreakpoint(); 143 bSupported = FALSE; 144 break; 145 } 146 147 /* 148 pNewVidPnSourceModeInfo->Format.Graphics.Stride 149 pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat 150 pNewVidPnSourceModeInfo->Format.Graphics.ColorBasis 151 pNewVidPnSourceModeInfo->Format.Graphics.PixelValueAccessMode 152 */ 153 154 break; 155 case D3DKMDT_RMT_TEXT: 156 break; 157 default: 158 AssertBreakpoint(); 159 LOG(("Warning: Unknown Src mode Type (%d)", pNewVidPnSourceModeInfo->Type)); 160 break; 161 } 162 163 *pbSupported = bSupported; 164 return STATUS_SUCCESS; 165 } 166 167 NTSTATUS vboxVidPnCheckSourceModeSet(const D3DKMDT_HVIDPN hDesiredVidPn, 168 D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet, const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnSourceModeSetInterface, 169 BOOLEAN *pbSupported) 170 { 171 const D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo; 172 NTSTATUS Status = pVidPnSourceModeSetInterface->pfnAcquireFirstModeInfo(hNewVidPnSourceModeSet, &pNewVidPnSourceModeInfo); 173 BOOLEAN bSupported = TRUE; 174 if (Status == STATUS_SUCCESS) 175 { 176 while (1) 177 { 178 Status = vboxVidPnCheckSourceModeInfo(hDesiredVidPn, pNewVidPnSourceModeInfo, &bSupported); 179 if (Status == STATUS_SUCCESS && bSupported) 180 { 181 const D3DKMDT_VIDPN_SOURCE_MODE *pNextVidPnSourceModeInfo; 182 Status = pVidPnSourceModeSetInterface->pfnAcquireNextModeInfo(hNewVidPnSourceModeSet, pNewVidPnSourceModeInfo, &pNextVidPnSourceModeInfo); 183 pVidPnSourceModeSetInterface->pfnReleaseModeInfo(hNewVidPnSourceModeSet, pNewVidPnSourceModeInfo); 184 if (Status == STATUS_SUCCESS) 185 { 186 pNewVidPnSourceModeInfo = pNextVidPnSourceModeInfo; 187 } 188 else if (Status == STATUS_GRAPHICS_NO_MORE_ELEMENTS_IN_DATASET) 189 { 190 Status = STATUS_SUCCESS; 191 break; 192 } 193 else 194 { 195 LOGREL(("pfnAcquireNextModeInfo Failed Status(0x%x)", Status)); 196 break; 197 } 198 } 199 else 200 { 201 pVidPnSourceModeSetInterface->pfnReleaseModeInfo(hNewVidPnSourceModeSet, pNewVidPnSourceModeInfo); 202 break; 203 } 204 } 205 } 206 else if (Status == STATUS_GRAPHICS_DATASET_IS_EMPTY) 207 Status = STATUS_SUCCESS; 208 else 209 LOGREL(("pfnAcquireFirstModeInfo failed Status(0x%x)", Status)); 210 211 *pbSupported = bSupported; 212 return Status; 213 } 214 215 NTSTATUS vboxVidPnPopulateVideoSignalInfo(D3DKMDT_VIDEO_SIGNAL_INFO *pVsi, 216 D3DKMDT_2DREGION *pResolution, 121 static NTSTATUS vboxVidPnPopulateVideoSignalInfo(D3DKMDT_VIDEO_SIGNAL_INFO *pVsi, 122 const RTRECTSIZE *pResolution, 217 123 ULONG VSync) 218 124 { … … 220 126 221 127 pVsi->VideoStandard = D3DKMDT_VSS_OTHER; 222 pVsi->ActiveSize = *pResolution; 128 pVsi->ActiveSize.cx = pResolution->cx; 129 pVsi->ActiveSize.cy = pResolution->cy; 223 130 pVsi->VSyncFreq.Numerator = VSync * 1000; 224 131 pVsi->VSyncFreq.Denominator = 1000; … … 261 168 } 262 169 263 NTSTATUS vboxVidPnCheckTargetModeInfo(const D3DKMDT_HVIDPN hDesiredVidPn, 264 const D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo, 265 BOOLEAN *pbSupported) 266 { 267 BOOLEAN bSupported = TRUE; 268 D3DKMDT_VIDEO_SIGNAL_INFO CmpVsi; 269 D3DKMDT_2DREGION CmpRes; 270 CmpRes.cx = pNewVidPnTargetModeInfo->VideoSignalInfo.ActiveSize.cx; 271 CmpRes.cy = pNewVidPnTargetModeInfo->VideoSignalInfo.ActiveSize.cy; 272 NTSTATUS Status = vboxVidPnPopulateVideoSignalInfo(&CmpVsi, 273 &CmpRes, 274 pNewVidPnTargetModeInfo->VideoSignalInfo.VSyncFreq.Numerator/pNewVidPnTargetModeInfo->VideoSignalInfo.VSyncFreq.Denominator); 275 Assert(Status == STATUS_SUCCESS); 276 if (Status != STATUS_SUCCESS) 277 { 278 LOGREL(("vboxVidPnPopulateVideoSignalInfo error Status (0x%x)", Status)); 279 return Status; 280 } 281 282 if (!vboxVidPnMatchVideoSignal(&CmpVsi, &pNewVidPnTargetModeInfo->VideoSignalInfo)) 283 { 284 WARN(("VideoSignalInfos do not match!!!")); 285 AssertBreakpoint(); 286 bSupported = FALSE; 287 } 288 289 *pbSupported = bSupported; 290 return STATUS_SUCCESS; 291 } 292 293 NTSTATUS vboxVidPnCheckTargetModeSet(const D3DKMDT_HVIDPN hDesiredVidPn, 294 D3DKMDT_HVIDPNTARGETMODESET hNewVidPnTargetModeSet, const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnTargetModeSetInterface, 295 BOOLEAN *pbSupported) 296 { 297 const D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo; 298 NTSTATUS Status = pVidPnTargetModeSetInterface->pfnAcquireFirstModeInfo(hNewVidPnTargetModeSet, &pNewVidPnTargetModeInfo); 299 BOOLEAN bSupported = TRUE; 300 if (Status == STATUS_SUCCESS) 301 { 302 Assert(pNewVidPnTargetModeInfo); 303 while (1) 304 { 305 Status = vboxVidPnCheckTargetModeInfo(hDesiredVidPn, pNewVidPnTargetModeInfo, &bSupported); 306 if (Status == STATUS_SUCCESS && bSupported) 307 { 308 const D3DKMDT_VIDPN_TARGET_MODE *pNextVidPnTargetModeInfo; 309 Status = pVidPnTargetModeSetInterface->pfnAcquireNextModeInfo(hNewVidPnTargetModeSet, pNewVidPnTargetModeInfo, &pNextVidPnTargetModeInfo); 310 pVidPnTargetModeSetInterface->pfnReleaseModeInfo(hNewVidPnTargetModeSet, pNewVidPnTargetModeInfo); 311 if (Status == STATUS_SUCCESS) 312 { 313 pNewVidPnTargetModeInfo = pNextVidPnTargetModeInfo; 314 } 315 else if (Status == STATUS_GRAPHICS_NO_MORE_ELEMENTS_IN_DATASET) 316 { 317 Status = STATUS_SUCCESS; 318 break; 319 } 320 else 321 { 322 LOGREL(("pfnAcquireNextModeInfo Failed Status(0x%x)", Status)); 323 break; 324 } 325 } 326 else 327 { 328 pVidPnTargetModeSetInterface->pfnReleaseModeInfo(hNewVidPnTargetModeSet, pNewVidPnTargetModeInfo); 329 break; 330 } 331 } 332 } 333 else if (Status == STATUS_GRAPHICS_DATASET_IS_EMPTY) 334 Status = STATUS_SUCCESS; 170 static void vboxVidPnPopulateSourceModeInfo(D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo, 171 const RTRECTSIZE *pSize) 172 { 173 NTSTATUS Status = STATUS_SUCCESS; 174 /* this is a graphics mode */ 175 pNewVidPnSourceModeInfo->Type = D3DKMDT_RMT_GRAPHICS; 176 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cx = pSize->cx; 177 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cy = pSize->cy; 178 pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize = pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize; 179 pNewVidPnSourceModeInfo->Format.Graphics.Stride = pSize->cx * 4; 180 pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat = D3DDDIFMT_A8R8G8B8; 181 Assert(pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat != D3DDDIFMT_UNKNOWN); 182 pNewVidPnSourceModeInfo->Format.Graphics.ColorBasis = D3DKMDT_CB_SRGB; 183 if (pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat == D3DDDIFMT_P8) 184 pNewVidPnSourceModeInfo->Format.Graphics.PixelValueAccessMode = D3DKMDT_PVAM_SETTABLEPALETTE; 335 185 else 336 LOGREL(("pfnAcquireFirstModeInfo failed Status(0x%x)", Status)); 337 338 *pbSupported = bSupported; 339 return Status; 340 } 341 342 NTSTATUS vboxVidPnPopulateSourceModeInfoFromLegacy(D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo, 343 VIDEO_MODE_INFORMATION *pMode) 344 { 345 NTSTATUS Status = STATUS_SUCCESS; 346 if (pMode->AttributeFlags & VIDEO_MODE_GRAPHICS) 347 { 348 /* this is a graphics mode */ 349 pNewVidPnSourceModeInfo->Type = D3DKMDT_RMT_GRAPHICS; 350 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cx = pMode->VisScreenWidth; 351 pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cy = pMode->VisScreenHeight; 352 pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize = pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize; 353 pNewVidPnSourceModeInfo->Format.Graphics.Stride = pMode->ScreenStride; 354 pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat = vboxWddmCalcPixelFormat(pMode); 355 Assert(pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat != D3DDDIFMT_UNKNOWN); 356 if (pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat != D3DDDIFMT_UNKNOWN) 357 { 358 pNewVidPnSourceModeInfo->Format.Graphics.ColorBasis = D3DKMDT_CB_SRGB; 359 if (pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat == D3DDDIFMT_P8) 360 pNewVidPnSourceModeInfo->Format.Graphics.PixelValueAccessMode = D3DKMDT_PVAM_SETTABLEPALETTE; 361 else 362 pNewVidPnSourceModeInfo->Format.Graphics.PixelValueAccessMode = D3DKMDT_PVAM_DIRECT; 363 } 364 else 365 { 366 LOGREL(("vboxWddmCalcPixelFormat failed")); 367 Status = STATUS_INVALID_PARAMETER; 368 } 369 } 370 else 371 { 372 /* @todo: XPDM driver does not seem to return text modes, should we? */ 373 LOGREL(("text mode not supported currently")); 374 AssertBreakpoint(); 375 Status = STATUS_INVALID_PARAMETER; 376 } 377 378 return Status; 379 } 380 381 NTSTATUS vboxVidPnPopulateMonitorSourceModeInfoFromLegacy(PVBOXMP_DEVEXT pDevExt, 382 D3DKMDT_MONITOR_SOURCE_MODE *pMonitorSourceMode, 383 D3DKMDT_2DREGION *pResolution, 384 D3DKMDT_MONITOR_CAPABILITIES_ORIGIN enmOrigin, 385 BOOLEAN bPreferred) 386 { 387 NTSTATUS Status = vboxVidPnPopulateVideoSignalInfo(&pMonitorSourceMode->VideoSignalInfo, pResolution, 60 /* ULONG VSync */); 388 Assert(Status == STATUS_SUCCESS); 389 if (Status == STATUS_SUCCESS) 390 { 391 pMonitorSourceMode->ColorBasis = D3DKMDT_CB_SRGB; 392 pMonitorSourceMode->ColorCoeffDynamicRanges.FirstChannel = 8; 393 pMonitorSourceMode->ColorCoeffDynamicRanges.SecondChannel = 8; 394 pMonitorSourceMode->ColorCoeffDynamicRanges.ThirdChannel = 8; 395 pMonitorSourceMode->ColorCoeffDynamicRanges.FourthChannel = 0; 396 pMonitorSourceMode->Origin = enmOrigin; 397 pMonitorSourceMode->Preference = bPreferred ? D3DKMDT_MP_PREFERRED : D3DKMDT_MP_NOTPREFERRED; 398 } 399 400 return Status; 401 } 402 403 NTSTATUS vboxVidPnCreatePopulateMonitorSourceModeInfoFromLegacy(PVBOXMP_DEVEXT pDevExt, 404 CONST D3DKMDT_HMONITORSOURCEMODESET hMonitorSMS, 405 CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pMonitorSMSIf, 406 D3DKMDT_2DREGION *pResolution, 407 D3DKMDT_MONITOR_CAPABILITIES_ORIGIN enmOrigin, 408 BOOLEAN bPreferred) 409 { 410 D3DKMDT_MONITOR_SOURCE_MODE * pMonitorSMI; 411 NTSTATUS Status = pMonitorSMSIf->pfnCreateNewModeInfo(hMonitorSMS, &pMonitorSMI); 412 Assert(Status == STATUS_SUCCESS); 413 if (Status == STATUS_SUCCESS) 414 { 415 do 416 { 417 Status = vboxVidPnPopulateMonitorSourceModeInfoFromLegacy(pDevExt, 418 pMonitorSMI, 419 pResolution, 420 enmOrigin, 421 bPreferred); 422 Assert(Status == STATUS_SUCCESS); 423 if (Status == STATUS_SUCCESS) 424 { 425 Status = pMonitorSMSIf->pfnAddMode(hMonitorSMS, pMonitorSMI); 426 Assert(Status == STATUS_SUCCESS/* || Status == STATUS_GRAPHICS_MODE_ALREADY_IN_MODESET*/); 427 if (Status == STATUS_SUCCESS) 428 break; 429 LOGREL(("pfnAddMode failed, Status(0x%x)", Status)); 430 } 431 else 432 LOGREL(("vboxVidPnPopulateMonitorSourceModeInfoFromLegacy failed, Status(0x%x)", Status)); 433 434 Assert (Status != STATUS_SUCCESS); 435 /* we're here because of a failure */ 436 NTSTATUS tmpStatus = pMonitorSMSIf->pfnReleaseModeInfo(hMonitorSMS, pMonitorSMI); 437 Assert(tmpStatus == STATUS_SUCCESS); 438 if (tmpStatus != STATUS_SUCCESS) 439 LOGREL(("pfnReleaseModeInfo failed tmpStatus(0x%x)", tmpStatus)); 440 441 if (Status == STATUS_GRAPHICS_MODE_ALREADY_IN_MODESET) 442 Status = STATUS_SUCCESS; 443 } while (0); 444 } 445 else 446 LOGREL(("pfnCreateNewModeInfo failed, Status(0x%x)", Status)); 447 448 return Status; 449 } 450 451 NTSTATUS vboxVidPnPopulateTargetModeInfoFromLegacy(D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo, D3DKMDT_2DREGION *pResolution, BOOLEAN fPreferred) 452 { 453 pNewVidPnTargetModeInfo->Preference = fPreferred ? D3DKMDT_MP_PREFERRED : D3DKMDT_MP_NOTPREFERRED; 186 pNewVidPnSourceModeInfo->Format.Graphics.PixelValueAccessMode = D3DKMDT_PVAM_DIRECT; 187 } 188 189 static void vboxVidPnPopulateMonitorModeInfo(D3DKMDT_MONITOR_SOURCE_MODE *pMonitorSourceMode, 190 const RTRECTSIZE *pResolution) 191 { 192 vboxVidPnPopulateVideoSignalInfo(&pMonitorSourceMode->VideoSignalInfo, pResolution, 60 /* ULONG VSync */); 193 pMonitorSourceMode->ColorBasis = D3DKMDT_CB_SRGB; 194 pMonitorSourceMode->ColorCoeffDynamicRanges.FirstChannel = 8; 195 pMonitorSourceMode->ColorCoeffDynamicRanges.SecondChannel = 8; 196 pMonitorSourceMode->ColorCoeffDynamicRanges.ThirdChannel = 8; 197 pMonitorSourceMode->ColorCoeffDynamicRanges.FourthChannel = 0; 198 pMonitorSourceMode->Origin = D3DKMDT_MCO_DRIVER; 199 pMonitorSourceMode->Preference = D3DKMDT_MP_NOTPREFERRED; 200 } 201 202 static NTSTATUS vboxVidPnPopulateTargetModeInfo(D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo, const RTRECTSIZE *pResolution) 203 { 204 pNewVidPnTargetModeInfo->Preference = D3DKMDT_MP_NOTPREFERRED; 454 205 return vboxVidPnPopulateVideoSignalInfo(&pNewVidPnTargetModeInfo->VideoSignalInfo, pResolution, 60 /* ULONG VSync */); 455 206 } … … 598 349 } 599 350 600 typedef struct VBOXVIDPNCHECKADDMONITORMODES 601 { 351 352 static D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE vboxVidPnCofuncModalityCurrentPathPivot(D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmPivot, 353 const DXGK_ENUM_PIVOT *pPivot, 354 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 355 { 356 switch (enmPivot) 357 { 358 case D3DKMDT_EPT_VIDPNSOURCE: 359 if (pPivot->VidPnSourceId == VidPnSourceId) 360 return D3DKMDT_EPT_VIDPNSOURCE; 361 if (pPivot->VidPnSourceId == D3DDDI_ID_ALL) 362 { 363 #ifdef DEBUG_misha 364 AssertFailed(); 365 #endif 366 return D3DKMDT_EPT_VIDPNSOURCE; 367 } 368 return D3DKMDT_EPT_NOPIVOT; 369 case D3DKMDT_EPT_VIDPNTARGET: 370 if (pPivot->VidPnTargetId == VidPnTargetId) 371 return D3DKMDT_EPT_VIDPNTARGET; 372 if (pPivot->VidPnTargetId == D3DDDI_ID_ALL) 373 { 374 #ifdef DEBUG_misha 375 AssertFailed(); 376 #endif 377 return D3DKMDT_EPT_VIDPNTARGET; 378 } 379 return D3DKMDT_EPT_NOPIVOT; 380 case D3DKMDT_EPT_SCALING: 381 case D3DKMDT_EPT_ROTATION: 382 case D3DKMDT_EPT_NOPIVOT: 383 return D3DKMDT_EPT_NOPIVOT; 384 default: 385 WARN(("unexpected pivot")); 386 return D3DKMDT_EPT_NOPIVOT; 387 } 388 } 389 390 NTSTATUS vboxVidPnQueryPinnedTargetMode(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 391 D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId, RTRECTSIZE *pSize) 392 { 393 D3DKMDT_HVIDPNTARGETMODESET hCurVidPnTargetModeSet; 394 const DXGK_VIDPNTARGETMODESET_INTERFACE *pCurVidPnTargetModeSetInterface; 395 pSize->cx = 0; 396 pSize->cy = 0; 397 NTSTATUS Status = pVidPnInterface->pfnAcquireTargetModeSet(hVidPn, 398 VidPnTargetId, 399 &hCurVidPnTargetModeSet, 400 &pCurVidPnTargetModeSetInterface); 401 if (!NT_SUCCESS(Status)) 402 { 403 WARN(("pfnAcquireTargetModeSet failed Status(0x%x)", Status)); 404 return Status; 405 } 406 407 CONST D3DKMDT_VIDPN_TARGET_MODE* pPinnedVidPnTargetModeInfo; 408 Status = pCurVidPnTargetModeSetInterface->pfnAcquirePinnedModeInfo(hCurVidPnTargetModeSet, &pPinnedVidPnTargetModeInfo); 409 if (Status == STATUS_GRAPHICS_MODE_NOT_PINNED) 410 { 411 pPinnedVidPnTargetModeInfo = NULL; 412 Status = STATUS_SUCCESS; 413 } 414 else if (!NT_SUCCESS(Status)) 415 { 416 WARN(("pfnAcquirePinnedModeInfo failed Status(0x%x)", Status)); 417 } 418 else 419 { 420 Assert(pPinnedVidPnTargetModeInfo); 421 pSize->cx = pPinnedVidPnTargetModeInfo->VideoSignalInfo.ActiveSize.cx; 422 pSize->cy = pPinnedVidPnTargetModeInfo->VideoSignalInfo.ActiveSize.cy; 423 NTSTATUS tmpStatus = pCurVidPnTargetModeSetInterface->pfnReleaseModeInfo(hCurVidPnTargetModeSet, pPinnedVidPnTargetModeInfo); 424 Assert(NT_SUCCESS(tmpStatus)); 425 } 426 427 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hCurVidPnTargetModeSet); 428 Assert(tmpStatus == STATUS_SUCCESS); 429 430 return Status; 431 } 432 433 NTSTATUS vboxVidPnQueryPinnedSourceMode(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 434 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, RTRECTSIZE *pSize) 435 { 436 D3DKMDT_HVIDPNSOURCEMODESET hCurVidPnSourceModeSet; 437 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pCurVidPnSourceModeSetInterface; 438 pSize->cx = 0; 439 pSize->cy = 0; 440 NTSTATUS Status = pVidPnInterface->pfnAcquireSourceModeSet(hVidPn, 441 VidPnSourceId, 442 &hCurVidPnSourceModeSet, 443 &pCurVidPnSourceModeSetInterface); 444 if (!NT_SUCCESS(Status)) 445 { 446 WARN(("pfnAcquireSourceModeSet failed Status(0x%x)", Status)); 447 return Status; 448 } 449 450 CONST D3DKMDT_VIDPN_SOURCE_MODE* pPinnedVidPnSourceModeInfo; 451 Status = pCurVidPnSourceModeSetInterface->pfnAcquirePinnedModeInfo(hCurVidPnSourceModeSet, &pPinnedVidPnSourceModeInfo); 452 if (Status == STATUS_GRAPHICS_MODE_NOT_PINNED) 453 { 454 pPinnedVidPnSourceModeInfo = NULL; 455 Status = STATUS_SUCCESS; 456 } 457 else if (!NT_SUCCESS(Status)) 458 { 459 WARN(("pfnAcquirePinnedModeInfo failed Status(0x%x)", Status)); 460 } 461 else 462 { 463 Assert(pPinnedVidPnSourceModeInfo); 464 pSize->cx = pPinnedVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cx; 465 pSize->cy = pPinnedVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cy; 466 NTSTATUS tmpStatus = pCurVidPnSourceModeSetInterface->pfnReleaseModeInfo(hCurVidPnSourceModeSet, pPinnedVidPnSourceModeInfo); 467 Assert(NT_SUCCESS(tmpStatus)); 468 } 469 470 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hCurVidPnSourceModeSet); 471 Assert(tmpStatus == STATUS_SUCCESS); 472 473 return Status; 474 } 475 476 static NTSTATUS vboxVidPnSourceModeSetToArray(D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet, 477 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface, 478 CR_SORTARRAY *pArray) 479 { 480 VBOXVIDPN_SOURCEMODE_ITER Iter; 481 const D3DKMDT_VIDPN_SOURCE_MODE *pVidPnModeInfo; 482 483 VBoxVidPnSourceModeIterInit(&Iter, hVidPnModeSet, pVidPnModeSetInterface); 484 485 while ((pVidPnModeInfo = VBoxVidPnSourceModeIterNext(&Iter)) != NULL) 486 { 487 RTRECTSIZE size; 488 size.cx = pVidPnModeInfo->Format.Graphics.VisibleRegionSize.cx; 489 size.cy = pVidPnModeInfo->Format.Graphics.VisibleRegionSize.cy; 490 int rc = CrSaAdd(pArray, CR_RSIZE2U64(size)); 491 if (RT_FAILURE(rc)) 492 { 493 WARN(("CrSaAdd failed %d", rc)); 494 VBoxVidPnSourceModeIterTerm(&Iter); 495 return STATUS_UNSUCCESSFUL; 496 } 497 } 498 499 VBoxVidPnSourceModeIterTerm(&Iter); 500 501 return VBoxVidPnSourceModeIterStatus(&Iter); 502 } 503 504 static NTSTATUS vboxVidPnSourceModeSetFromArray(D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet, 505 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface, 506 const CR_SORTARRAY *pArray) 507 { 508 for (uint32_t i = 0; i < CrSaGetSize(pArray); ++i) 509 { 510 RTRECTSIZE size = CR_U642RSIZE(CrSaGetVal(pArray, i)); 511 512 D3DKMDT_VIDPN_SOURCE_MODE *pVidPnModeInfo; 513 NTSTATUS Status = pVidPnModeSetInterface->pfnCreateNewModeInfo(hVidPnModeSet, &pVidPnModeInfo); 514 if (!NT_SUCCESS(Status)) 515 { 516 WARN(("pfnCreateNewModeInfo failed, Status 0x%x", Status)); 517 return Status; 518 } 519 520 vboxVidPnPopulateSourceModeInfo(pVidPnModeInfo, &size); 521 522 Status = pVidPnModeSetInterface->pfnAddMode(hVidPnModeSet, pVidPnModeInfo); 523 if (!NT_SUCCESS(Status)) 524 { 525 WARN(("pfnAddMode failed, Status 0x%x", Status)); 526 NTSTATUS tmpStatus = pVidPnModeSetInterface->pfnReleaseModeInfo(hVidPnModeSet, pVidPnModeInfo); 527 Assert(tmpStatus == STATUS_SUCCESS); 528 return Status; 529 } 530 } 531 532 return STATUS_SUCCESS; 533 } 534 535 static NTSTATUS vboxVidPnTargetModeSetToArray(D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet, 536 const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface, 537 CR_SORTARRAY *pArray) 538 { 539 VBOXVIDPN_TARGETMODE_ITER Iter; 540 const D3DKMDT_VIDPN_TARGET_MODE *pVidPnModeInfo; 541 542 VBoxVidPnTargetModeIterInit(&Iter, hVidPnModeSet, pVidPnModeSetInterface); 543 544 while ((pVidPnModeInfo = VBoxVidPnTargetModeIterNext(&Iter)) != NULL) 545 { 546 RTRECTSIZE size; 547 size.cx = pVidPnModeInfo->VideoSignalInfo.ActiveSize.cx; 548 size.cy = pVidPnModeInfo->VideoSignalInfo.ActiveSize.cy; 549 int rc = CrSaAdd(pArray, CR_RSIZE2U64(size)); 550 if (RT_FAILURE(rc)) 551 { 552 WARN(("CrSaAdd failed %d", rc)); 553 VBoxVidPnTargetModeIterTerm(&Iter); 554 return STATUS_UNSUCCESSFUL; 555 } 556 } 557 558 VBoxVidPnTargetModeIterTerm(&Iter); 559 560 return VBoxVidPnTargetModeIterStatus(&Iter); 561 } 562 563 static NTSTATUS vboxVidPnTargetModeSetFromArray(D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet, 564 const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface, 565 const CR_SORTARRAY *pArray) 566 { 567 for (uint32_t i = 0; i < CrSaGetSize(pArray); ++i) 568 { 569 RTRECTSIZE size = CR_U642RSIZE(CrSaGetVal(pArray, i)); 570 571 D3DKMDT_VIDPN_TARGET_MODE *pVidPnModeInfo; 572 NTSTATUS Status = pVidPnModeSetInterface->pfnCreateNewModeInfo(hVidPnModeSet, &pVidPnModeInfo); 573 if (!NT_SUCCESS(Status)) 574 { 575 WARN(("pfnCreateNewModeInfo failed, Status 0x%x", Status)); 576 return Status; 577 } 578 579 vboxVidPnPopulateTargetModeInfo(pVidPnModeInfo, &size); 580 581 Status = pVidPnModeSetInterface->pfnAddMode(hVidPnModeSet, pVidPnModeInfo); 582 if (!NT_SUCCESS(Status)) 583 { 584 WARN(("pfnAddMode failed, Status 0x%x", Status)); 585 NTSTATUS tmpStatus = pVidPnModeSetInterface->pfnReleaseModeInfo(hVidPnModeSet, pVidPnModeInfo); 586 Assert(tmpStatus == STATUS_SUCCESS); 587 return Status; 588 } 589 } 590 591 return STATUS_SUCCESS; 592 } 593 594 static NTSTATUS vboxVidPnMonitorModeSetToArray(D3DKMDT_HMONITORSOURCEMODESET hVidPnModeSet, 595 const DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface, 596 CR_SORTARRAY *pArray) 597 { 598 VBOXVIDPN_MONITORMODE_ITER Iter; 599 const D3DKMDT_MONITOR_SOURCE_MODE *pVidPnModeInfo; 600 601 VBoxVidPnMonitorModeIterInit(&Iter, hVidPnModeSet, pVidPnModeSetInterface); 602 603 while ((pVidPnModeInfo = VBoxVidPnMonitorModeIterNext(&Iter)) != NULL) 604 { 605 RTRECTSIZE size; 606 size.cx = pVidPnModeInfo->VideoSignalInfo.ActiveSize.cx; 607 size.cy = pVidPnModeInfo->VideoSignalInfo.ActiveSize.cy; 608 int rc = CrSaAdd(pArray, CR_RSIZE2U64(size)); 609 if (RT_FAILURE(rc)) 610 { 611 WARN(("CrSaAdd failed %d", rc)); 612 VBoxVidPnMonitorModeIterTerm(&Iter); 613 return STATUS_UNSUCCESSFUL; 614 } 615 } 616 617 VBoxVidPnMonitorModeIterTerm(&Iter); 618 619 return VBoxVidPnMonitorModeIterStatus(&Iter); 620 } 621 622 static NTSTATUS vboxVidPnMonitorModeSetFromArray(D3DKMDT_HMONITORSOURCEMODESET hVidPnModeSet, 623 const DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface, 624 const CR_SORTARRAY *pArray) 625 { 626 for (uint32_t i = 0; i < CrSaGetSize(pArray); ++i) 627 { 628 RTRECTSIZE size = CR_U642RSIZE(CrSaGetVal(pArray, i)); 629 630 D3DKMDT_MONITOR_SOURCE_MODE *pVidPnModeInfo; 631 NTSTATUS Status = pVidPnModeSetInterface->pfnCreateNewModeInfo(hVidPnModeSet, &pVidPnModeInfo); 632 if (!NT_SUCCESS(Status)) 633 { 634 WARN(("pfnCreateNewModeInfo failed, Status 0x%x", Status)); 635 return Status; 636 } 637 638 vboxVidPnPopulateMonitorModeInfo(pVidPnModeInfo, &size); 639 640 Status = pVidPnModeSetInterface->pfnAddMode(hVidPnModeSet, pVidPnModeInfo); 641 if (!NT_SUCCESS(Status)) 642 { 643 WARN(("pfnAddMode failed, Status 0x%x", Status)); 644 NTSTATUS tmpStatus = pVidPnModeSetInterface->pfnReleaseModeInfo(hVidPnModeSet, pVidPnModeInfo); 645 Assert(tmpStatus == STATUS_SUCCESS); 646 return Status; 647 } 648 } 649 650 return STATUS_SUCCESS; 651 } 652 653 654 static NTSTATUS vboxVidPnCollectInfoForPathTarget(PVBOXMP_DEVEXT pDevExt, 655 D3DKMDT_HVIDPN hVidPn, 656 const DXGK_VIDPN_INTERFACE* pVidPnInterface, 657 D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmCurPivot, 658 uint32_t *aAdjustedModeMap, 659 CR_SORTARRAY *aModes, 660 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 661 { 662 const CR_SORTARRAY* pSupportedModes = VBoxWddmVModesGet(pDevExt, VidPnTargetId); 602 663 NTSTATUS Status; 603 D3DKMDT_2DREGION *pResolutions; 604 uint32_t cResolutions; 605 } VBOXVIDPNCHECKADDMONITORMODES, *PVBOXVIDPNCHECKADDMONITORMODES; 606 607 static DECLCALLBACK(BOOLEAN) vboxVidPnCheckAddMonitorModesEnum(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HMONITORSOURCEMODESET hMonitorSMS, CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pMonitorSMSIf, 608 CONST D3DKMDT_MONITOR_SOURCE_MODE *pMonitorSMI, PVOID pContext) 609 { 610 PVBOXVIDPNCHECKADDMONITORMODES pData = (PVBOXVIDPNCHECKADDMONITORMODES)pContext; 611 NTSTATUS Status = STATUS_SUCCESS; 612 613 for (uint32_t i = 0; i < pData->cResolutions; ++i) 614 { 615 D3DKMDT_VIDPN_TARGET_MODE dummyMode = {0}; 616 Status = vboxVidPnPopulateTargetModeInfoFromLegacy(&dummyMode, &pData->pResolutions[i], FALSE /* preference does not matter for now */); 617 Assert(Status == STATUS_SUCCESS); 618 if (Status == STATUS_SUCCESS) 619 { 620 if (vboxVidPnMatchVideoSignal(&dummyMode.VideoSignalInfo, &pMonitorSMI->VideoSignalInfo)) 621 { 622 /* mark it as unneeded */ 623 pData->pResolutions[i].cx = 0; 624 break; 625 } 664 if (enmCurPivot == D3DKMDT_EPT_VIDPNTARGET) 665 { 666 D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet; 667 const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface; 668 Status = pVidPnInterface->pfnAcquireTargetModeSet(hVidPn, 669 VidPnTargetId, 670 &hVidPnModeSet, 671 &pVidPnModeSetInterface); 672 if (!NT_SUCCESS(Status)) 673 { 674 WARN(("pfnAcquireTargetModeSet failed %#x", Status)); 675 return Status; 676 } 677 678 /* intersect modes from target */ 679 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 680 { 681 Status = vboxVidPnTargetModeSetToArray(hVidPnModeSet, pVidPnModeSetInterface, &aModes[VidPnTargetId]); 682 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 626 683 } 627 684 else 628 685 { 629 LOGREL(("vboxVidPnPopulateTargetModeInfoFromLegacy failed Status(0x%x)", Status)); 630 break; 631 } 632 } 633 634 pMonitorSMSIf->pfnReleaseModeInfo(hMonitorSMS, pMonitorSMI); 635 636 pData->Status = Status; 637 638 return Status == STATUS_SUCCESS; 639 } 640 641 typedef struct VBOXVIDPNCHECKMONMODESENUM 642 { 643 D3DKMDT_2DREGION Region; 644 const D3DKMDT_MONITOR_SOURCE_MODE * pMonitorSMI; 645 } VBOXVIDPNCHECKMONMODESENUM, *PVBOXVIDPNCHECKMONMODESENUM; 646 647 static DECLCALLBACK(BOOLEAN) vboxFidPnCheckMonitorModesEnum(D3DKMDT_HMONITORSOURCEMODESET hMonitorSMS, CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pMonitorSMSIf, 648 CONST D3DKMDT_MONITOR_SOURCE_MODE *pMonitorSMI, PVOID pContext) 649 { 650 PVBOXVIDPNCHECKMONMODESENUM pInfo = (PVBOXVIDPNCHECKMONMODESENUM)pContext; 651 if (pMonitorSMI->VideoSignalInfo.ActiveSize.cx == pInfo->Region.cx 652 && pMonitorSMI->VideoSignalInfo.ActiveSize.cy == pInfo->Region.cy) 653 { 654 Assert(!pInfo->pMonitorSMI); 655 if (pInfo->pMonitorSMI) 656 { 657 pMonitorSMSIf->pfnReleaseModeInfo(hMonitorSMS, pInfo->pMonitorSMI); 658 } 659 pInfo->pMonitorSMI = pMonitorSMI; 686 CR_SORTARRAY Arr; 687 CrSaInit(&Arr, 0); 688 Status = vboxVidPnTargetModeSetToArray(hVidPnModeSet, pVidPnModeSetInterface, &aModes[VidPnTargetId]); 689 CrSaIntersect(&aModes[VidPnTargetId], &Arr); 690 CrSaCleanup(&Arr); 691 } 692 693 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hVidPnModeSet); 694 Assert(tmpStatus == STATUS_SUCCESS); 695 696 if (!NT_SUCCESS(Status)) 697 { 698 WARN(("vboxVidPnTargetModeSetToArray failed %#x", Status)); 699 return Status; 700 } 701 702 return STATUS_SUCCESS; 703 } 704 705 RTRECTSIZE pinnedSize = {0}; 706 Status = vboxVidPnQueryPinnedTargetMode(hVidPn, pVidPnInterface, VidPnTargetId, &pinnedSize); 707 if (!NT_SUCCESS(Status)) 708 { 709 WARN(("vboxVidPnQueryPinnedTargetMode failed %#x", Status)); 710 return Status; 711 } 712 713 if (pinnedSize.cx) 714 { 715 Assert(CrSaContains(pSupportedModes, CR_RSIZE2U64(pinnedSize))); 716 717 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 718 { 719 Assert(CrSaGetSize(&aModes[VidPnTargetId]) == 0); 720 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 721 if (!RT_SUCCESS(rc)) 722 { 723 WARN(("CrSaAdd failed %d", rc)); 724 return STATUS_UNSUCCESSFUL; 725 } 726 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 727 } 728 else 729 { 730 CrSaClear(&aModes[VidPnTargetId]); 731 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 732 if (!RT_SUCCESS(rc)) 733 { 734 WARN(("CrSaAdd failed %d", rc)); 735 return STATUS_UNSUCCESSFUL; 736 } 737 } 738 739 return STATUS_SUCCESS; 740 } 741 742 743 Status = vboxVidPnQueryPinnedSourceMode(hVidPn, pVidPnInterface, VidPnSourceId, &pinnedSize); 744 if (!NT_SUCCESS(Status)) 745 { 746 WARN(("vboxVidPnQueryPinnedSourceMode failed %#x", Status)); 747 return Status; 748 } 749 750 if (pinnedSize.cx) 751 { 752 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 753 { 754 Assert(CrSaGetSize(&aModes[VidPnTargetId]) == 0); 755 if (CrSaContains(pSupportedModes, CR_RSIZE2U64(pinnedSize))) 756 { 757 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 758 if (!RT_SUCCESS(rc)) 759 { 760 WARN(("CrSaAdd failed %d", rc)); 761 return STATUS_UNSUCCESSFUL; 762 } 763 } 764 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 765 } 766 else 767 { 768 CrSaClear(&aModes[VidPnTargetId]); 769 if (CrSaContains(pSupportedModes, CR_RSIZE2U64(pinnedSize))) 770 { 771 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 772 if (!RT_SUCCESS(rc)) 773 { 774 WARN(("CrSaAdd failed %d", rc)); 775 return STATUS_UNSUCCESSFUL; 776 } 777 } 778 } 779 780 return STATUS_SUCCESS; 781 } 782 783 /* now we are here because no pinned info is specified, we need to populate it based on the supported info 784 * and modes already configured, 785 * this is pretty simple actually */ 786 787 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 788 { 789 Assert(CrSaGetSize(&aModes[VidPnTargetId]) == 0); 790 int rc = CrSaClone(pSupportedModes, &aModes[VidPnTargetId]); 791 if (!RT_SUCCESS(rc)) 792 { 793 WARN(("CrSaClone failed %d", rc)); 794 return STATUS_UNSUCCESSFUL; 795 } 796 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 660 797 } 661 798 else 662 799 { 663 pMonitorSMSIf->pfnReleaseModeInfo(hMonitorSMS, pMonitorSMI); 664 } 665 return TRUE; 666 } 667 668 typedef struct VBOXVIDPNMATCHMONMODESENUM 669 { 670 D3DKMDT_2DREGION *paResolutions; 671 uint32_t cResolutions; 672 BOOLEAN fMatched; 673 } VBOXVIDPNMATCHMONMODESENUM, *PVBOXVIDPNMATCHMONMODESENUM; 674 675 static DECLCALLBACK(BOOLEAN) vboxFidPnMatchMonitorModesEnum(D3DKMDT_HMONITORSOURCEMODESET hMonitorSMS, CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pMonitorSMSIf, 676 CONST D3DKMDT_MONITOR_SOURCE_MODE *pMonitorSMI, PVOID pContext) 677 { 678 PVBOXVIDPNMATCHMONMODESENUM pInfo = (PVBOXVIDPNMATCHMONMODESENUM)pContext; 679 680 Assert(pInfo->fMatched); 681 682 BOOLEAN fFound = FALSE; 683 684 for (UINT i = 0; i < pInfo->cResolutions; ++i) 685 { 686 D3DKMDT_2DREGION *pResolution = &pInfo->paResolutions[i]; 687 if (pMonitorSMI->VideoSignalInfo.ActiveSize.cx == pResolution->cx 688 && pMonitorSMI->VideoSignalInfo.ActiveSize.cy == pResolution->cy) 689 { 690 fFound = TRUE; 691 break; 692 } 693 } 694 695 if (!fFound) 696 pInfo->fMatched = FALSE; 697 698 if (!pInfo->fMatched) 699 LOG(("Found non-matching mode (%d X %d)", 700 pMonitorSMI->VideoSignalInfo.ActiveSize.cx, pMonitorSMI->VideoSignalInfo.ActiveSize.cy)); 701 702 pMonitorSMSIf->pfnReleaseModeInfo(hMonitorSMS, pMonitorSMI); 703 704 return pInfo->fMatched; 705 } 706 707 /* matches the monitor mode set for the given target id with the resolution set, and sets the pfMatch to true if they match, otherwise sets it to false */ 708 NTSTATUS vboxVidPnMatchMonitorModes(PVBOXMP_DEVEXT pDevExt, D3DDDI_VIDEO_PRESENT_TARGET_ID targetId, 709 D3DKMDT_2DREGION *pResolutions, uint32_t cResolutions, BOOLEAN *pfMatch) 710 { 711 *pfMatch = FALSE; 712 CONST DXGK_MONITOR_INTERFACE *pMonitorInterface; 713 NTSTATUS Status = pDevExt->u.primary.DxgkInterface.DxgkCbQueryMonitorInterface(pDevExt->u.primary.DxgkInterface.DeviceHandle, DXGK_MONITOR_INTERFACE_VERSION_V1, &pMonitorInterface); 714 if (!NT_SUCCESS(Status)) 715 { 716 WARN(("DxgkCbQueryMonitorInterface failed, Status (0x%x)", Status)); 800 CrSaIntersect(&aModes[VidPnTargetId], pSupportedModes); 801 } 802 803 /* we are done */ 804 return STATUS_SUCCESS; 805 } 806 807 static NTSTATUS vboxVidPnApplyInfoForPathTarget(PVBOXMP_DEVEXT pDevExt, 808 D3DKMDT_HVIDPN hVidPn, 809 const DXGK_VIDPN_INTERFACE* pVidPnInterface, 810 D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmCurPivot, 811 uint32_t *aAdjustedModeMap, 812 const CR_SORTARRAY *aModes, 813 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 814 { 815 Assert(ASMBitTest(aAdjustedModeMap, VidPnTargetId)); 816 817 if (enmCurPivot == D3DKMDT_EPT_VIDPNTARGET) 818 return STATUS_SUCCESS; 819 820 RTRECTSIZE pinnedSize = {0}; 821 NTSTATUS Status = vboxVidPnQueryPinnedTargetMode(hVidPn, pVidPnInterface, VidPnTargetId, &pinnedSize); 822 if (!NT_SUCCESS(Status)) 823 { 824 WARN(("vboxVidPnQueryPinnedTargetMode failed %#x", Status)); 717 825 return Status; 718 826 } 719 827 720 D3DKMDT_HMONITORSOURCEMODESET hMonitorSMS; 721 CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pMonitorSMSIf; 722 Status = pMonitorInterface->pfnAcquireMonitorSourceModeSet(pDevExt->u.primary.DxgkInterface.DeviceHandle, 723 targetId, 724 &hMonitorSMS, 725 &pMonitorSMSIf); 726 if (!NT_SUCCESS(Status)) 727 { 728 WARN(("pfnAcquireMonitorSourceModeSet failed, Status (0x%x)", Status)); 729 if (Status == STATUS_GRAPHICS_MONITOR_NOT_CONNECTED) 730 { 731 /* this is ok in case we replug the monitor to pick up the monitor modes properly, 732 * so pretend success */ 733 *pfMatch = TRUE; 734 Status = STATUS_SUCCESS; 735 } 828 if (pinnedSize.cx) 829 return STATUS_SUCCESS; 830 831 /* now just create the new source mode set and apply it */ 832 D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet; 833 const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface; 834 Status = pVidPnInterface->pfnCreateNewTargetModeSet(hVidPn, 835 VidPnTargetId, 836 &hVidPnModeSet, 837 &pVidPnModeSetInterface); 838 if (!NT_SUCCESS(Status)) 839 { 840 WARN(("pfnCreateNewTargetModeSet failed Status(0x%x)", Status)); 736 841 return Status; 737 842 } 738 843 739 /* we care only about monitor modes covering all needed resolutions, 740 * we do NOT care if resolutions do not cover some monitor modes */ 741 SIZE_T cModes = 0; 742 Status = pMonitorSMSIf->pfnGetNumModes(hMonitorSMS, &cModes); 743 if (NT_SUCCESS(Status)) 744 { 745 if (cModes < cResolutions) 746 { 747 *pfMatch = FALSE; 748 LOG(("num modes(%d) and resolutions(%d) do not match, treat as not matched..", cModes, cResolutions)); 844 Status = vboxVidPnTargetModeSetFromArray(hVidPnModeSet, 845 pVidPnModeSetInterface, 846 &aModes[VidPnTargetId]); 847 if (!NT_SUCCESS(Status)) 848 { 849 WARN(("vboxVidPnTargetModeSetFromArray failed Status(0x%x)", Status)); 850 return Status; 851 } 852 853 Status = pVidPnInterface->pfnAssignTargetModeSet(hVidPn, VidPnTargetId, hVidPnModeSet); 854 if (!NT_SUCCESS(Status)) 855 { 856 WARN(("\n\n!!!!!!!\n\n pfnAssignTargetModeSet failed, Status(0x%x)", Status)); 857 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hVidPnModeSet); 858 Assert(tmpStatus == STATUS_SUCCESS); 859 return Status; 860 } 861 862 return STATUS_SUCCESS; 863 } 864 865 static NTSTATUS vboxVidPnApplyInfoForPathSource(PVBOXMP_DEVEXT pDevExt, 866 D3DKMDT_HVIDPN hVidPn, 867 const DXGK_VIDPN_INTERFACE* pVidPnInterface, 868 D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmCurPivot, 869 uint32_t *aAdjustedModeMap, 870 const CR_SORTARRAY *aModes, 871 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 872 { 873 Assert(ASMBitTest(aAdjustedModeMap, VidPnTargetId)); 874 875 if (enmCurPivot == D3DKMDT_EPT_VIDPNSOURCE) 876 return STATUS_SUCCESS; 877 878 RTRECTSIZE pinnedSize = {0}; 879 NTSTATUS Status = vboxVidPnQueryPinnedSourceMode(hVidPn, pVidPnInterface, VidPnSourceId, &pinnedSize); 880 if (!NT_SUCCESS(Status)) 881 { 882 WARN(("vboxVidPnQueryPinnedSourceMode failed %#x", Status)); 883 return Status; 884 } 885 886 if (pinnedSize.cx) 887 return STATUS_SUCCESS; 888 889 /* now just create the new source mode set and apply it */ 890 D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet; 891 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface; 892 Status = pVidPnInterface->pfnCreateNewSourceModeSet(hVidPn, 893 VidPnSourceId, 894 &hVidPnModeSet, 895 &pVidPnModeSetInterface); 896 if (!NT_SUCCESS(Status)) 897 { 898 WARN(("pfnCreateNewSourceModeSet failed Status(0x%x)", Status)); 899 return Status; 900 } 901 902 Status = vboxVidPnSourceModeSetFromArray(hVidPnModeSet, 903 pVidPnModeSetInterface, 904 &aModes[VidPnTargetId]); /* <- target modes always! */ 905 if (!NT_SUCCESS(Status)) 906 { 907 WARN(("vboxVidPnSourceModeSetFromArray failed Status(0x%x)", Status)); 908 return Status; 909 } 910 911 Status = pVidPnInterface->pfnAssignSourceModeSet(hVidPn, VidPnSourceId, hVidPnModeSet); 912 if (!NT_SUCCESS(Status)) 913 { 914 WARN(("\n\n!!!!!!!\n\n pfnAssignSourceModeSet failed, Status(0x%x)", Status)); 915 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hVidPnModeSet); 916 Assert(tmpStatus == STATUS_SUCCESS); 917 return Status; 918 } 919 920 return STATUS_SUCCESS; 921 } 922 923 static NTSTATUS vboxVidPnCollectInfoForPathSource(PVBOXMP_DEVEXT pDevExt, 924 D3DKMDT_HVIDPN hVidPn, 925 const DXGK_VIDPN_INTERFACE* pVidPnInterface, 926 D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmCurPivot, 927 uint32_t *aAdjustedModeMap, 928 CR_SORTARRAY *aModes, 929 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 930 { 931 const CR_SORTARRAY* pSupportedModes = VBoxWddmVModesGet(pDevExt, VidPnTargetId); /* <- yes, modes are target-determined always */ 932 NTSTATUS Status; 933 934 if (enmCurPivot == D3DKMDT_EPT_VIDPNSOURCE) 935 { 936 D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet; 937 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface; 938 Status = pVidPnInterface->pfnAcquireSourceModeSet(hVidPn, 939 VidPnSourceId, 940 &hVidPnModeSet, 941 &pVidPnModeSetInterface); 942 if (!NT_SUCCESS(Status)) 943 { 944 WARN(("pfnAcquireSourceModeSet failed %#x", Status)); 945 return Status; 946 } 947 948 /* intersect modes from target */ 949 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 950 { 951 Status = vboxVidPnSourceModeSetToArray(hVidPnModeSet, pVidPnModeSetInterface, &aModes[VidPnTargetId]); 952 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 749 953 } 750 954 else 751 955 { 752 VBOXVIDPNMATCHMONMODESENUM Info; 753 Info.paResolutions = pResolutions; 754 Info.cResolutions = cResolutions; 755 Info.fMatched = TRUE; 756 757 Status = vboxVidPnEnumMonitorSourceModes(hMonitorSMS, pMonitorSMSIf, vboxFidPnMatchMonitorModesEnum, &Info); 758 if (NT_SUCCESS(Status)) 759 { 760 *pfMatch = Info.fMatched; 761 LOG(("modes %smatched", Info.fMatched ? "" : "NOT ")); 762 } 763 else 764 WARN(("vboxVidPnEnumMonitorSourceModes failed, Status 0x%x", Status)); 765 } 956 CR_SORTARRAY Arr; 957 CrSaInit(&Arr, 0); 958 Status = vboxVidPnSourceModeSetToArray(hVidPnModeSet, pVidPnModeSetInterface, &aModes[VidPnTargetId]); 959 CrSaIntersect(&aModes[VidPnTargetId], &Arr); 960 CrSaCleanup(&Arr); 961 } 962 963 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hVidPnModeSet); 964 Assert(tmpStatus == STATUS_SUCCESS); 965 966 if (!NT_SUCCESS(Status)) 967 { 968 WARN(("pfnReleaseSourceModeSet failed %#x", Status)); 969 return Status; 970 } 971 972 /* intersect it with supported target modes, just in case */ 973 CrSaIntersect(&aModes[VidPnTargetId], pSupportedModes); 974 975 return STATUS_SUCCESS; 976 } 977 978 RTRECTSIZE pinnedSize = {0}; 979 Status = vboxVidPnQueryPinnedSourceMode(hVidPn, pVidPnInterface, VidPnSourceId, &pinnedSize); 980 if (!NT_SUCCESS(Status)) 981 { 982 WARN(("vboxVidPnQueryPinnedSourceMode failed %#x", Status)); 983 return Status; 984 } 985 986 if (pinnedSize.cx) 987 { 988 Assert(CrSaContains(pSupportedModes, CR_RSIZE2U64(pinnedSize))); 989 990 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 991 { 992 Assert(CrSaGetSize(&aModes[VidPnTargetId]) == 0); 993 994 if (CrSaContains(pSupportedModes, CR_RSIZE2U64(pinnedSize))) 995 { 996 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 997 if (!RT_SUCCESS(rc)) 998 { 999 WARN(("CrSaAdd failed %d", rc)); 1000 return STATUS_UNSUCCESSFUL; 1001 } 1002 } 1003 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 1004 } 1005 else 1006 { 1007 CrSaClear(&aModes[VidPnTargetId]); 1008 if (CrSaContains(pSupportedModes, CR_RSIZE2U64(pinnedSize))) 1009 { 1010 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 1011 if (!RT_SUCCESS(rc)) 1012 { 1013 WARN(("CrSaAdd failed %d", rc)); 1014 return STATUS_UNSUCCESSFUL; 1015 } 1016 } 1017 } 1018 1019 return STATUS_SUCCESS; 1020 } 1021 1022 1023 Status = vboxVidPnQueryPinnedTargetMode(hVidPn, pVidPnInterface, VidPnTargetId, &pinnedSize); 1024 if (!NT_SUCCESS(Status)) 1025 { 1026 WARN(("vboxVidPnQueryPinnedTargetMode failed %#x", Status)); 1027 return Status; 1028 } 1029 1030 if (pinnedSize.cx) 1031 { 1032 Assert(CrSaContains(pSupportedModes, CR_RSIZE2U64(pinnedSize))); 1033 1034 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 1035 { 1036 Assert(CrSaGetSize(&aModes[VidPnTargetId]) == 0); 1037 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 1038 if (!RT_SUCCESS(rc)) 1039 { 1040 WARN(("CrSaAdd failed %d", rc)); 1041 return STATUS_UNSUCCESSFUL; 1042 } 1043 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 1044 } 1045 else 1046 { 1047 CrSaClear(&aModes[VidPnTargetId]); 1048 int rc = CrSaAdd(&aModes[VidPnTargetId], CR_RSIZE2U64(pinnedSize)); 1049 if (!RT_SUCCESS(rc)) 1050 { 1051 WARN(("CrSaAdd failed %d", rc)); 1052 return STATUS_UNSUCCESSFUL; 1053 } 1054 } 1055 1056 return STATUS_SUCCESS; 1057 } 1058 1059 /* now we are here because no pinned info is specified, we need to populate it based on the supported info 1060 * and modes already configured, 1061 * this is pretty simple actually */ 1062 1063 if (!ASMBitTest(aAdjustedModeMap, VidPnTargetId)) 1064 { 1065 Assert(CrSaGetSize(&aModes[VidPnTargetId]) == 0); 1066 int rc = CrSaClone(pSupportedModes, &aModes[VidPnTargetId]); 1067 if (!RT_SUCCESS(rc)) 1068 { 1069 WARN(("CrSaClone failed %d", rc)); 1070 return STATUS_UNSUCCESSFUL; 1071 } 1072 ASMBitSet(aAdjustedModeMap, VidPnTargetId); 766 1073 } 767 1074 else 768 WARN(("pfnGetNumModes failed, Status 0x%x", Status)); 769 770 NTSTATUS tmpStatus = pMonitorInterface->pfnReleaseMonitorSourceModeSet(pDevExt->u.primary.DxgkInterface.DeviceHandle, hMonitorSMS); 771 if (!NT_SUCCESS(tmpStatus)) 772 WARN(("pfnReleaseMonitorSourceModeSet failed tmpStatus(0x%x)", tmpStatus)); 773 774 return Status; 775 } 776 777 NTSTATUS vboxVidPnCheckAddMonitorModes(PVBOXMP_DEVEXT pDevExt, 778 D3DDDI_VIDEO_PRESENT_TARGET_ID targetId, D3DKMDT_MONITOR_CAPABILITIES_ORIGIN enmOrigin, 779 D3DKMDT_2DREGION *pResolutions, uint32_t cResolutions, int iPreferred) 1075 { 1076 CrSaIntersect(&aModes[VidPnTargetId], pSupportedModes); 1077 } 1078 1079 /* we are done */ 1080 return STATUS_SUCCESS; 1081 } 1082 1083 static NTSTATUS vboxVidPnCheckMonitorModes(PVBOXMP_DEVEXT pDevExt, uint32_t u32Target) 780 1084 { 781 1085 NTSTATUS Status; … … 788 1092 } 789 1093 790 D3DKMDT_HMONITORSOURCEMODESET hMonitorSMS; 791 CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pMonitorSMSIf; 1094 D3DKMDT_HMONITORSOURCEMODESET hVidPnModeSet; 1095 CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface; 1096 1097 const CR_SORTARRAY *pSupportedModes = VBoxWddmVModesGet(pDevExt, u32Target); 1098 CR_SORTARRAY DiffModes; 1099 int rc = CrSaInit(&DiffModes, CrSaGetSize(pSupportedModes)); 1100 if (!RT_SUCCESS(rc)) 1101 { 1102 WARN(("CrSaInit failed")); 1103 return STATUS_NO_MEMORY; 1104 } 1105 792 1106 793 1107 Status = pMonitorInterface->pfnAcquireMonitorSourceModeSet(pDevExt->u.primary.DxgkInterface.DeviceHandle, 794 targetId,795 &h MonitorSMS,796 &p MonitorSMSIf);1108 u32Target, 1109 &hVidPnModeSet, 1110 &pVidPnModeSetInterface); 797 1111 if (!NT_SUCCESS(Status)) 798 1112 { 799 1113 WARN(("DxgkCbQueryMonitorInterface failed, Status()0x%x", Status)); 800 if (Status == STATUS_GRAPHICS_MONITOR_NOT_CONNECTED) 801 { 802 /* this is ok in case we replug the monitor to pick up the monitor modes properly, 803 * so pretend success */ 804 Status = STATUS_SUCCESS; 805 } 1114 // if (Status == STATUS_GRAPHICS_MONITOR_NOT_CONNECTED) 1115 CrSaCleanup(&DiffModes); 806 1116 return Status; 807 1117 } 808 1118 809 for (uint32_t i = 0; i < cResolutions; ++i) 810 { 811 D3DKMDT_2DREGION *pRes = &pResolutions[i]; 812 813 Status = vboxVidPnCreatePopulateMonitorSourceModeInfoFromLegacy(pDevExt, 814 hMonitorSMS, 815 pMonitorSMSIf, 816 pRes, 817 enmOrigin, 818 iPreferred == i 819 ); 820 Assert(Status == STATUS_SUCCESS); 821 if (Status != STATUS_SUCCESS) 822 { 823 LOGREL(("vboxVidPnCreatePopulateMonitorSourceModeInfoFromLegacy failed Status(0x%x)", Status)); 824 break; 825 } 826 } 827 828 NTSTATUS tmpStatus = pMonitorInterface->pfnReleaseMonitorSourceModeSet(pDevExt->u.primary.DxgkInterface.DeviceHandle, hMonitorSMS); 1119 VBOXVIDPN_MONITORMODE_ITER Iter; 1120 const D3DKMDT_MONITOR_SOURCE_MODE *pVidPnModeInfo; 1121 1122 rc = CrSaClone(pSupportedModes, &DiffModes); 1123 if (!RT_SUCCESS(rc)) 1124 { 1125 WARN(("CrSaClone failed")); 1126 Status = STATUS_NO_MEMORY; 1127 goto done; 1128 } 1129 1130 VBoxVidPnMonitorModeIterInit(&Iter, hVidPnModeSet, pVidPnModeSetInterface); 1131 1132 while ((pVidPnModeInfo = VBoxVidPnMonitorModeIterNext(&Iter)) != NULL) 1133 { 1134 RTRECTSIZE size; 1135 size.cx = pVidPnModeInfo->VideoSignalInfo.ActiveSize.cx; 1136 size.cy = pVidPnModeInfo->VideoSignalInfo.ActiveSize.cy; 1137 CrSaRemove(&DiffModes, CR_RSIZE2U64(size)); 1138 } 1139 1140 VBoxVidPnMonitorModeIterTerm(&Iter); 1141 1142 Status = VBoxVidPnMonitorModeIterStatus(&Iter); 1143 if (!NT_SUCCESS(Status)) 1144 { 1145 WARN(("iter status failed %#x", Status)); 1146 goto done; 1147 } 1148 1149 Status = vboxVidPnMonitorModeSetFromArray(hVidPnModeSet, pVidPnModeSetInterface, &DiffModes); 1150 if (!NT_SUCCESS(Status)) 1151 { 1152 WARN(("vboxVidPnMonitorModeSetFromArray failed %#x", Status)); 1153 goto done; 1154 } 1155 1156 done: 1157 NTSTATUS tmpStatus = pMonitorInterface->pfnReleaseMonitorSourceModeSet(pDevExt->u.primary.DxgkInterface.DeviceHandle, hVidPnModeSet); 829 1158 if (!NT_SUCCESS(tmpStatus)) 830 {831 1159 WARN(("pfnReleaseMonitorSourceModeSet failed tmpStatus(0x%x)", tmpStatus)); 832 } 1160 1161 CrSaCleanup(&DiffModes); 833 1162 834 1163 return Status; 835 1164 } 836 1165 837 NTSTATUS vboxVidPnPathAdd(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 838 const D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, const D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 1166 static NTSTATUS vboxVidPnPathAdd(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 1167 const D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, const D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId, 1168 D3DKMDT_VIDPN_PRESENT_PATH_IMPORTANCE enmImportance) 839 1169 { 840 1170 D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology; … … 857 1187 pNewVidPnPresentPathInfo->VidPnSourceId = VidPnSourceId; 858 1188 pNewVidPnPresentPathInfo->VidPnTargetId = VidPnTargetId; 859 pNewVidPnPresentPathInfo->ImportanceOrdinal = D3DKMDT_VPPI_PRIMARY;1189 pNewVidPnPresentPathInfo->ImportanceOrdinal = enmImportance; 860 1190 pNewVidPnPresentPathInfo->ContentTransformation.Scaling = D3DKMDT_VPPS_IDENTITY; 861 1191 memset(&pNewVidPnPresentPathInfo->ContentTransformation.ScalingSupport, … … 895 1225 } 896 1226 1227 LOG(("Recommended Path (%d->%d)", VidPnSourceId, VidPnTargetId)); 1228 897 1229 return Status; 898 1230 } 899 1231 900 static NTSTATUS vboxVidPnCreatePopulateSourceModeInfoFromLegacy(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 901 const D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, 902 VIDEO_MODE_INFORMATION *pModes, uint32_t cModes, int iModeToPin, 903 D3DKMDT_VIDEO_PRESENT_SOURCE_MODE_ID *pModeIdToPin, 904 BOOLEAN fDoPin 905 ) 906 { 907 D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet; 908 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pNewVidPnSourceModeSetInterface; 909 910 if (pModeIdToPin) 911 *pModeIdToPin = D3DDDI_ID_UNINITIALIZED; 912 913 NTSTATUS Status = pVidPnInterface->pfnCreateNewSourceModeSet(hVidPn, 914 VidPnSourceId, 915 &hNewVidPnSourceModeSet, 916 &pNewVidPnSourceModeSetInterface); 917 if (!NT_SUCCESS(Status)) 918 { 919 AssertFailed(); 1232 NTSTATUS VBoxVidPnRecommendMonitorModes(PVBOXMP_DEVEXT pDevExt, D3DDDI_VIDEO_PRESENT_TARGET_ID VideoPresentTargetId, 1233 D3DKMDT_HMONITORSOURCEMODESET hVidPnModeSet, const DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface) 1234 { 1235 const CR_SORTARRAY *pSupportedModes = VBoxWddmVModesGet(pDevExt, VideoPresentTargetId); 1236 1237 NTSTATUS Status = vboxVidPnMonitorModeSetFromArray(hVidPnModeSet, pVidPnModeSetInterface, pSupportedModes); 1238 if (!NT_SUCCESS(Status)) 1239 { 1240 WARN(("vboxVidPnMonitorModeSetFromArray failed %d", Status)); 920 1241 return Status; 921 1242 } 922 1243 923 D3DKMDT_VIDEO_PRESENT_SOURCE_MODE_ID sourceModeId = D3DDDI_ID_UNINITIALIZED; 924 925 for (uint32_t i = 0; i < cModes; ++i) 926 { 927 VIDEO_MODE_INFORMATION *pMode = &pModes[i]; 928 D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo; 929 Status = pNewVidPnSourceModeSetInterface->pfnCreateNewModeInfo(hNewVidPnSourceModeSet, &pNewVidPnSourceModeInfo); 1244 return STATUS_SUCCESS; 1245 } 1246 1247 NTSTATUS VBoxVidPnUpdateModes(PVBOXMP_DEVEXT pDevExt, uint32_t u32TargetId, const RTRECTSIZE *pSize) 1248 { 1249 if (u32TargetId >= (uint32_t)VBoxCommonFromDeviceExt(pDevExt)->cDisplays) 1250 { 1251 WARN(("invalid target id")); 1252 return STATUS_INVALID_PARAMETER; 1253 } 1254 1255 int rc = VBoxWddmVModesAdd(pDevExt, u32TargetId, pSize, TRUE); 1256 if (RT_FAILURE(rc)) 1257 { 1258 WARN(("VBoxWddmVModesAdd failed %d", rc)); 1259 return STATUS_UNSUCCESSFUL; 1260 } 1261 1262 if (rc == VINF_ALREADY_INITIALIZED) 1263 { 1264 /* mode was already in list, just return */ 1265 Assert(CrSaContains(VBoxWddmVModesGet(pDevExt, u32TargetId), CR_RSIZE2U64(*pSize))); 1266 return STATUS_SUCCESS; 1267 } 1268 1269 /* modes have changed, need to replug */ 1270 NTSTATUS Status = VBoxWddmChildStatusReportReconnected(pDevExt, u32TargetId); 1271 if (!NT_SUCCESS(Status)) 1272 { 1273 WARN(("VBoxWddmChildStatusReportReconnected failed Status(%#x)", Status)); 1274 return Status; 1275 } 1276 1277 return STATUS_SUCCESS; 1278 } 1279 1280 NTSTATUS VBoxVidPnRecommendFunctional(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, const VBOXWDDM_RECOMMENDVIDPN *pData) 1281 { 1282 const DXGK_VIDPN_INTERFACE* pVidPnInterface = NULL; 1283 NTSTATUS Status = pDevExt->u.primary.DxgkInterface.DxgkCbQueryVidPnInterface(hVidPn, DXGK_VIDPN_INTERFACE_VERSION_V1, &pVidPnInterface); 1284 if (!NT_SUCCESS(Status)) 1285 { 1286 WARN(("DxgkCbQueryVidPnInterface failed Status(%#x)", Status)); 1287 return Status; 1288 } 1289 1290 VBOXCMDVBVA_SCREENMAP_DECL(uint32_t, aVisitedSourceMap); 1291 1292 memset(aVisitedSourceMap, 0, sizeof (aVisitedSourceMap)); 1293 1294 uint32_t Importance = (uint32_t)D3DKMDT_VPPI_PRIMARY; 1295 1296 for (uint32_t i = 0; i < (uint32_t)VBoxCommonFromDeviceExt(pDevExt)->cDisplays; ++i) 1297 { 1298 int32_t iSource = pData->aTargets[i].iSource; 1299 if (iSource < 0) 1300 continue; 1301 1302 if (iSource >= VBoxCommonFromDeviceExt(pDevExt)->cDisplays) 1303 { 1304 WARN(("invalid iSource")); 1305 return STATUS_INVALID_PARAMETER; 1306 } 1307 1308 if (!pDevExt->fComplexTopologiesEnabled && iSource != i) 1309 { 1310 WARN(("complex topologies not supported!")); 1311 return STATUS_INVALID_PARAMETER; 1312 } 1313 1314 bool fNewSource = false; 1315 1316 if (!ASMBitTest(aVisitedSourceMap, iSource)) 1317 { 1318 int rc = VBoxWddmVModesAdd(pDevExt, i, &pData->aSources[iSource].Size, TRUE); 1319 if (RT_FAILURE(rc)) 1320 { 1321 WARN(("VBoxWddmVModesAdd failed %d", rc)); 1322 return STATUS_UNSUCCESSFUL; 1323 } 1324 1325 Assert(CrSaContains(VBoxWddmVModesGet(pDevExt, i), CR_RSIZE2U64(pData->aSources[iSource].Size))); 1326 1327 Status = vboxVidPnCheckMonitorModes(pDevExt, i); 1328 if (!NT_SUCCESS(Status)) 1329 { 1330 WARN(("vboxVidPnCheckMonitorModes failed %#x", Status)); 1331 return Status; 1332 } 1333 1334 ASMBitSet(aVisitedSourceMap, iSource); 1335 fNewSource = true; 1336 } 1337 1338 Status = vboxVidPnPathAdd(hVidPn, pVidPnInterface, 1339 (const D3DDDI_VIDEO_PRESENT_SOURCE_ID)iSource, (const D3DDDI_VIDEO_PRESENT_TARGET_ID)i, 1340 (D3DKMDT_VIDPN_PRESENT_PATH_IMPORTANCE)Importance); 930 1341 if (!NT_SUCCESS(Status)) 931 1342 { 932 AssertFailed(); 933 break; 934 } 935 936 Status = vboxVidPnPopulateSourceModeInfoFromLegacy(pNewVidPnSourceModeInfo, pMode); 937 if (NT_SUCCESS(Status)) 938 { 939 if (i == iModeToPin) 940 { 941 sourceModeId = pNewVidPnSourceModeInfo->Id; 942 } 943 Status = pNewVidPnSourceModeSetInterface->pfnAddMode(hNewVidPnSourceModeSet, pNewVidPnSourceModeInfo); 1343 WARN(("vboxVidPnPathAdd failed Status()0x%x\n", Status)); 1344 return Status; 1345 } 1346 1347 Importance++; 1348 1349 do { 1350 D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet; 1351 const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface; 1352 1353 Status = pVidPnInterface->pfnCreateNewTargetModeSet(hVidPn, 1354 i, 1355 &hVidPnModeSet, 1356 &pVidPnModeSetInterface); 944 1357 if (NT_SUCCESS(Status)) 945 1358 { 946 /* success */ 947 continue; 948 } 949 AssertFailed(); 950 } 951 else 952 { 953 AssertFailed(); 954 } 955 956 NTSTATUS tmpStatus = pNewVidPnSourceModeSetInterface->pfnReleaseModeInfo(hNewVidPnSourceModeSet, pNewVidPnSourceModeInfo); 957 Assert(tmpStatus == STATUS_SUCCESS); 958 959 /* we're here because of an error */ 960 Assert(!NT_SUCCESS(Status)); 961 break; 962 } 963 964 if (!NT_SUCCESS(Status)) 965 { 966 AssertFailed(); 967 return Status; 968 } 969 970 if (sourceModeId != D3DDDI_ID_UNINITIALIZED) 971 { 972 if (pModeIdToPin) 973 { 974 *pModeIdToPin = sourceModeId; 975 } 976 Assert(iModeToPin >= 0); 977 if (fDoPin) 978 { 979 Status = pNewVidPnSourceModeSetInterface->pfnPinMode(hNewVidPnSourceModeSet, sourceModeId); 980 if (!NT_SUCCESS(Status)) 981 { 982 AssertFailed(); 983 return Status; 984 } 985 } 986 } 987 else 988 { 989 Assert(iModeToPin < 0); 990 } 991 992 Status = pVidPnInterface->pfnAssignSourceModeSet(hVidPn, VidPnSourceId, hNewVidPnSourceModeSet); 993 if (!NT_SUCCESS(Status)) 994 { 995 AssertFailed(); 996 return Status; 997 } 998 999 return Status; 1000 } 1001 1002 static NTSTATUS vboxVidPnCreatePopulateTargetModeInfoFromLegacy(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 1003 const D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId, 1004 D3DKMDT_2DREGION *pResolutions, uint32_t cResolutions, 1005 VIDEO_MODE_INFORMATION *pModeToPin, 1006 D3DKMDT_VIDEO_PRESENT_TARGET_MODE_ID *pModeIdToPin, 1007 BOOLEAN fSetPreferred, 1008 BOOLEAN fDoPin 1009 ) 1010 { 1011 D3DKMDT_HVIDPNTARGETMODESET hNewVidPnTargetModeSet; 1012 const DXGK_VIDPNTARGETMODESET_INTERFACE *pNewVidPnTargetModeSetInterface; 1013 1014 if (pModeIdToPin) 1015 *pModeIdToPin = D3DDDI_ID_UNINITIALIZED; 1016 1017 NTSTATUS Status = pVidPnInterface->pfnCreateNewTargetModeSet(hVidPn, 1018 VidPnTargetId, 1019 &hNewVidPnTargetModeSet, 1020 &pNewVidPnTargetModeSetInterface); 1021 if (!NT_SUCCESS(Status)) 1022 { 1023 AssertFailed(); 1024 return Status; 1025 } 1026 1027 D3DKMDT_VIDEO_PRESENT_TARGET_MODE_ID targetModeId = D3DDDI_ID_UNINITIALIZED; 1028 1029 for (uint32_t i = 0; i < cResolutions; ++i) 1030 { 1031 D3DKMDT_2DREGION *pResolution = &pResolutions[i]; 1032 D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo; 1033 Status = pNewVidPnTargetModeSetInterface->pfnCreateNewModeInfo(hNewVidPnTargetModeSet, &pNewVidPnTargetModeInfo); 1034 if (!NT_SUCCESS(Status)) 1035 { 1036 AssertFailed(); 1037 break; 1038 } 1039 1040 BOOLEAN fIsPinMode = pModeToPin && pModeToPin->VisScreenWidth == pResolution->cx 1041 && pModeToPin->VisScreenHeight == pResolution->cy; 1042 1043 Status = vboxVidPnPopulateTargetModeInfoFromLegacy(pNewVidPnTargetModeInfo, pResolution, fIsPinMode && fSetPreferred); 1044 if (NT_SUCCESS(Status)) 1045 { 1046 if (fIsPinMode) 1047 { 1048 targetModeId = pNewVidPnTargetModeInfo->Id; 1049 } 1050 Status = pNewVidPnTargetModeSetInterface->pfnAddMode(hNewVidPnTargetModeSet, pNewVidPnTargetModeInfo); 1051 if (NT_SUCCESS(Status)) 1052 { 1053 1054 /* success */ 1055 continue; 1056 } 1057 AssertFailed(); 1058 } 1059 else 1060 { 1061 AssertFailed(); 1062 } 1063 1064 NTSTATUS tmpStatus = pNewVidPnTargetModeSetInterface->pfnReleaseModeInfo(hNewVidPnTargetModeSet, pNewVidPnTargetModeInfo); 1065 Assert(tmpStatus == STATUS_SUCCESS); 1066 1067 /* we're here because of an error */ 1068 Assert(!NT_SUCCESS(Status)); 1069 break; 1070 } 1071 1072 if (!NT_SUCCESS(Status)) 1073 { 1074 AssertFailed(); 1075 return Status; 1076 } 1077 1078 if (targetModeId != D3DDDI_ID_UNINITIALIZED) 1079 { 1080 Assert(pModeToPin); 1081 1082 if (pModeIdToPin) 1083 { 1084 *pModeIdToPin = targetModeId; 1085 } 1086 1087 if (fDoPin) 1088 { 1089 Status = pNewVidPnTargetModeSetInterface->pfnPinMode(hNewVidPnTargetModeSet, targetModeId); 1090 if (!NT_SUCCESS(Status)) 1091 { 1092 AssertFailed(); 1093 return Status; 1094 } 1095 } 1096 } 1097 else 1098 { 1099 Assert(!pModeToPin); 1100 } 1101 1102 Status = pVidPnInterface->pfnAssignTargetModeSet(hVidPn, VidPnTargetId, hNewVidPnTargetModeSet); 1103 if (!NT_SUCCESS(Status)) 1104 { 1105 AssertFailed(); 1106 return Status; 1107 } 1108 1109 return Status; 1110 } 1111 1112 NTSTATUS vboxVidPnCreatePopulateVidPnPathFromLegacy(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 1113 VIDEO_MODE_INFORMATION *pModes, uint32_t cModes, int iModeToPin, 1114 D3DKMDT_2DREGION *pResolutions, uint32_t cResolutions, 1115 const D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, const D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 1116 { 1117 NTSTATUS Status; 1118 1119 #if 0 1120 Status = vboxVidPnPathAdd(hVidPn, pVidPnInterface, VidPnSourceId, VidPnTargetId); 1121 if (!NT_SUCCESS(Status)) 1122 { 1123 AssertFailed(); 1124 return Status; 1125 } 1126 #endif 1127 1128 VIDEO_MODE_INFORMATION *pModeToPin = iModeToPin >= 0 ? &pModes[iModeToPin] : NULL; 1129 Status = vboxVidPnCreatePopulateTargetModeInfoFromLegacy(hVidPn, pVidPnInterface, VidPnTargetId, pResolutions, cResolutions, pModeToPin, NULL, TRUE, TRUE); 1130 if (!NT_SUCCESS(Status)) 1131 { 1132 AssertFailed(); 1133 return Status; 1134 } 1135 1136 Status = vboxVidPnCreatePopulateSourceModeInfoFromLegacy(hVidPn, pVidPnInterface, VidPnSourceId, pModes, cModes, iModeToPin, NULL, TRUE); 1137 if (!NT_SUCCESS(Status)) 1138 { 1139 AssertFailed(); 1140 return Status; 1141 } 1142 1143 return Status; 1144 } 1145 1146 typedef struct VBOXVIDPNPOPRESOLUTIONENUM 1147 { 1148 NTSTATUS Status; 1149 D3DKMDT_2DREGION *pResolutions; 1150 int cResolutions; 1151 int cResultResolutions; 1152 }VBOXVIDPNPOPRESOLUTIONENUM, *PVBOXVIDPNPOPRESOLUTIONENUM; 1153 1154 static DECLCALLBACK(BOOLEAN) vboxVidPnPopulateResolutionsFromSourceModeSetEnum(D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet, const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnSourceModeSetInterface, 1155 const D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo, PVOID pContext) 1156 { 1157 NTSTATUS Status = STATUS_SUCCESS; 1158 PVBOXVIDPNPOPRESOLUTIONENUM pInfo = (PVBOXVIDPNPOPRESOLUTIONENUM)pContext; 1159 Assert(pInfo->cResolutions >= pInfo->cResultResolutions); 1160 Assert(pInfo->Status == STATUS_SUCCESS); 1161 if (vboxWddmResolutionFind(pInfo->pResolutions, pInfo->cResultResolutions, &pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize) < 0) 1162 { 1163 if (pInfo->cResultResolutions < pInfo->cResolutions) 1164 { 1165 pInfo->pResolutions[pInfo->cResultResolutions] = pNewVidPnSourceModeInfo->Format.Graphics.PrimSurfSize; 1166 ++pInfo->cResultResolutions; 1167 } 1168 else 1169 { 1170 Status = STATUS_BUFFER_OVERFLOW; 1171 } 1172 } 1173 1174 pInfo->Status = Status; 1175 1176 return Status == STATUS_SUCCESS; 1177 } 1178 1179 static DECLCALLBACK(BOOLEAN) vboxVidPnPopulateResolutionsFromTargetModeSetEnum(D3DKMDT_HVIDPNTARGETMODESET hNewVidPnTargetModeSet, const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnTargetModeSetInterface, 1180 const D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo, PVOID pContext) 1181 { 1182 NTSTATUS Status = STATUS_SUCCESS; 1183 PVBOXVIDPNPOPRESOLUTIONENUM pInfo = (PVBOXVIDPNPOPRESOLUTIONENUM)pContext; 1184 Assert(pInfo->cResolutions >= pInfo->cResultResolutions); 1185 Assert(pInfo->Status == STATUS_SUCCESS); 1186 if (vboxWddmResolutionFind(pInfo->pResolutions, pInfo->cResultResolutions, &pNewVidPnTargetModeInfo->VideoSignalInfo.ActiveSize) < 0) 1187 { 1188 if (pInfo->cResultResolutions < pInfo->cResolutions) 1189 { 1190 pInfo->pResolutions[pInfo->cResultResolutions] = pNewVidPnTargetModeInfo->VideoSignalInfo.ActiveSize; 1191 ++pInfo->cResultResolutions; 1192 } 1193 else 1194 { 1195 Status = STATUS_BUFFER_OVERFLOW; 1196 } 1197 } 1198 1199 pInfo->Status = Status; 1200 1201 return Status == STATUS_SUCCESS; 1202 } 1203 1204 typedef struct VBOXVIDPNPOPMODEENUM 1205 { 1206 NTSTATUS Status; 1207 VIDEO_MODE_INFORMATION *pModes; 1208 int cModes; 1209 int cResultModes; 1210 }VBOXVIDPNPOPMODEENUM, *PVBOXVIDPNPOPMODEENUM; 1211 1212 static DECLCALLBACK(BOOLEAN) vboxVidPnPopulateModesFromSourceModeSetEnum(D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet, const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnSourceModeSetInterface, 1213 const D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo, PVOID pContext) 1214 { 1215 NTSTATUS Status = STATUS_SUCCESS; 1216 PVBOXVIDPNPOPMODEENUM pInfo = (PVBOXVIDPNPOPMODEENUM)pContext; 1217 VIDEO_MODE_INFORMATION Mode; 1218 Assert(pInfo->cModes >= pInfo->cResultModes); 1219 Assert(pInfo->Status == STATUS_SUCCESS); 1220 if (VBoxWddmFillMode(&Mode, pNewVidPnSourceModeInfo->Format.Graphics.PixelFormat, 1221 pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cx, 1222 pNewVidPnSourceModeInfo->Format.Graphics.VisibleRegionSize.cy)) 1223 { 1224 if (vboxWddmVideoModeFind(pInfo->pModes, pInfo->cModes, &Mode) < 0) 1225 { 1226 if (pInfo->cResultModes < pInfo->cModes) 1227 { 1228 pInfo->pModes[pInfo->cResultModes] = Mode; 1229 ++pInfo->cResultModes; 1359 D3DKMDT_VIDPN_TARGET_MODE *pVidPnModeInfo; 1360 Status = pVidPnModeSetInterface->pfnCreateNewModeInfo(hVidPnModeSet, &pVidPnModeInfo); 1361 if (NT_SUCCESS(Status)) 1362 { 1363 vboxVidPnPopulateTargetModeInfo(pVidPnModeInfo, &pData->aSources[iSource].Size); 1364 1365 IN_CONST_D3DKMDT_VIDEO_PRESENT_TARGET_MODE_ID idMode = pVidPnModeInfo->Id; 1366 1367 Status = pVidPnModeSetInterface->pfnAddMode(hVidPnModeSet, pVidPnModeInfo); 1368 if (NT_SUCCESS(Status)) 1369 { 1370 pVidPnModeInfo = NULL; 1371 1372 Status = pVidPnModeSetInterface->pfnPinMode(hVidPnModeSet, idMode); 1373 if (NT_SUCCESS(Status)) 1374 { 1375 Status = pVidPnInterface->pfnAssignTargetModeSet(hVidPn, i, hVidPnModeSet); 1376 if (NT_SUCCESS(Status)) 1377 { 1378 LOG(("Recommended Target[%d] (%dx%d)", i, pData->aSources[iSource].Size.cx, pData->aSources[iSource].Size.cy)); 1379 break; 1380 } 1381 else 1382 WARN(("pfnAssignTargetModeSet failed %#x", Status)); 1383 } 1384 else 1385 WARN(("pfnPinMode failed %#x", Status)); 1386 1387 } 1388 else 1389 WARN(("pfnAddMode failed %#x", Status)); 1390 1391 if (pVidPnModeInfo) 1392 { 1393 NTSTATUS tmpStatus = pVidPnModeSetInterface->pfnReleaseModeInfo(hVidPnModeSet, pVidPnModeInfo); 1394 Assert(tmpStatus == STATUS_SUCCESS); 1395 } 1396 } 1397 else 1398 WARN(("pfnCreateNewTargetModeSet failed %#x", Status)); 1399 1400 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hVidPnModeSet); 1401 Assert(tmpStatus == STATUS_SUCCESS); 1230 1402 } 1231 1403 else 1232 { 1233 Status = STATUS_BUFFER_OVERFLOW; 1234 } 1235 } 1236 } 1237 else 1238 { 1239 Assert(0); 1240 Status = STATUS_INVALID_PARAMETER; 1241 } 1242 1243 pInfo->Status = Status; 1244 1245 return Status == STATUS_SUCCESS; 1246 } 1247 1248 typedef struct VBOXVIDPNPOPMODETARGETENUM 1249 { 1250 VBOXVIDPNPOPMODEENUM Base; 1251 VIDEO_MODE_INFORMATION *pSuperset; 1252 int cSuperset; 1253 }VBOXVIDPNPOPMODETARGETENUM, *PVBOXVIDPNPOPMODETARGETENUM; 1254 1255 static DECLCALLBACK(BOOLEAN) vboxVidPnPopulateModesFromTargetModeSetEnum(D3DKMDT_HVIDPNTARGETMODESET hNewVidPnTargetModeSet, const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnTargetModeSetInterface, 1256 const D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo, PVOID pContext) 1257 { 1258 NTSTATUS Status = STATUS_SUCCESS; 1259 PVBOXVIDPNPOPMODETARGETENUM pInfo = (PVBOXVIDPNPOPMODETARGETENUM)pContext; 1260 Assert(pInfo->Base.cModes >= pInfo->Base.cResultModes); 1261 Assert(pInfo->Base.Status == STATUS_SUCCESS); 1262 uint32_t cResult; 1263 Status = VBoxWddmGetModesForResolution(pInfo->pSuperset, pInfo->cSuperset, -1, &pNewVidPnTargetModeInfo->VideoSignalInfo.ActiveSize, 1264 pInfo->Base.pModes + pInfo->Base.cResultModes, pInfo->Base.cModes - pInfo->Base.cResultModes, &cResult, NULL); 1265 Assert(Status == STATUS_SUCCESS); 1266 if (Status == STATUS_SUCCESS) 1267 { 1268 pInfo->Base.cResultModes += cResult; 1269 } 1270 1271 pInfo->Base.Status = Status; 1272 1273 return Status == STATUS_SUCCESS; 1274 } 1275 1276 static D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE vboxVidPnCofuncModalityCurrentPathPivot(CONST DXGKARG_ENUMVIDPNCOFUNCMODALITY* pEnumCofuncModalityArg, 1277 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 1278 { 1279 switch (pEnumCofuncModalityArg->EnumPivotType) 1280 { 1281 case D3DKMDT_EPT_VIDPNSOURCE: 1282 if (pEnumCofuncModalityArg->EnumPivot.VidPnSourceId == VidPnSourceId) 1283 return D3DKMDT_EPT_VIDPNSOURCE; 1284 if (pEnumCofuncModalityArg->EnumPivot.VidPnSourceId == D3DDDI_ID_ALL) 1285 { 1286 #ifdef DEBUG_misha 1287 AssertFailed(); 1288 #endif 1289 return D3DKMDT_EPT_VIDPNSOURCE; 1290 } 1291 return D3DKMDT_EPT_NOPIVOT; 1292 case D3DKMDT_EPT_VIDPNTARGET: 1293 if (pEnumCofuncModalityArg->EnumPivot.VidPnTargetId == VidPnTargetId) 1294 return D3DKMDT_EPT_VIDPNTARGET; 1295 if (pEnumCofuncModalityArg->EnumPivot.VidPnTargetId == D3DDDI_ID_ALL) 1296 { 1297 #ifdef DEBUG_misha 1298 AssertFailed(); 1299 #endif 1300 return D3DKMDT_EPT_VIDPNTARGET; 1301 } 1302 return D3DKMDT_EPT_NOPIVOT; 1303 case D3DKMDT_EPT_SCALING: 1304 case D3DKMDT_EPT_ROTATION: 1305 case D3DKMDT_EPT_NOPIVOT: 1306 return D3DKMDT_EPT_NOPIVOT; 1307 default: 1308 AssertFailed(); 1309 return D3DKMDT_EPT_NOPIVOT; 1310 } 1311 } 1312 1313 NTSTATUS vboxVidPnHasPinnedTargetMode(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 1314 D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId, BOOLEAN *pfHas) 1315 { 1316 D3DKMDT_HVIDPNTARGETMODESET hCurVidPnTargetModeSet; 1317 const DXGK_VIDPNTARGETMODESET_INTERFACE *pCurVidPnTargetModeSetInterface; 1318 *pfHas = FALSE; 1319 NTSTATUS Status = pVidPnInterface->pfnAcquireTargetModeSet(hVidPn, 1320 VidPnTargetId, 1321 &hCurVidPnTargetModeSet, 1322 &pCurVidPnTargetModeSetInterface); 1323 if (!NT_SUCCESS(Status)) 1324 { 1325 AssertFailed(); 1326 return Status; 1327 } 1328 1329 CONST D3DKMDT_VIDPN_TARGET_MODE* pPinnedVidPnTargetModeInfo; 1330 Status = pCurVidPnTargetModeSetInterface->pfnAcquirePinnedModeInfo(hCurVidPnTargetModeSet, &pPinnedVidPnTargetModeInfo); 1331 if (Status == STATUS_GRAPHICS_MODE_NOT_PINNED) 1332 { 1333 pPinnedVidPnTargetModeInfo = NULL; 1334 Status = STATUS_SUCCESS; 1335 } 1336 else if (!NT_SUCCESS(Status)) 1337 { 1338 LOGREL(("pfnAcquirePinnedModeInfo failed Status(0x%x)", Status)); 1339 AssertFailed(); 1340 } 1341 else 1342 { 1343 Assert(pPinnedVidPnTargetModeInfo); 1344 NTSTATUS tmpStatus = pCurVidPnTargetModeSetInterface->pfnReleaseModeInfo(hCurVidPnTargetModeSet, pPinnedVidPnTargetModeInfo); 1345 Assert(NT_SUCCESS(tmpStatus)); 1346 *pfHas = TRUE; 1347 } 1348 1349 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hCurVidPnTargetModeSet); 1350 Assert(tmpStatus == STATUS_SUCCESS); 1351 1352 return Status; 1353 } 1354 1355 NTSTATUS vboxVidPnHasPinnedSourceMode(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 1356 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, BOOLEAN *pfHas) 1357 { 1358 D3DKMDT_HVIDPNSOURCEMODESET hCurVidPnSourceModeSet; 1359 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pCurVidPnSourceModeSetInterface; 1360 *pfHas = FALSE; 1361 NTSTATUS Status = pVidPnInterface->pfnAcquireSourceModeSet(hVidPn, 1362 VidPnSourceId, 1363 &hCurVidPnSourceModeSet, 1364 &pCurVidPnSourceModeSetInterface); 1365 if (!NT_SUCCESS(Status)) 1366 { 1367 AssertFailed(); 1368 return Status; 1369 } 1370 1371 CONST D3DKMDT_VIDPN_SOURCE_MODE* pPinnedVidPnSourceModeInfo; 1372 Status = pCurVidPnSourceModeSetInterface->pfnAcquirePinnedModeInfo(hCurVidPnSourceModeSet, &pPinnedVidPnSourceModeInfo); 1373 if (Status == STATUS_GRAPHICS_MODE_NOT_PINNED) 1374 { 1375 pPinnedVidPnSourceModeInfo = NULL; 1376 Status = STATUS_SUCCESS; 1377 } 1378 else if (!NT_SUCCESS(Status)) 1379 { 1380 LOGREL(("pfnAcquirePinnedModeInfo failed Status(0x%x)", Status)); 1381 AssertFailed(); 1382 } 1383 else 1384 { 1385 Assert(pPinnedVidPnSourceModeInfo); 1386 NTSTATUS tmpStatus = pCurVidPnSourceModeSetInterface->pfnReleaseModeInfo(hCurVidPnSourceModeSet, pPinnedVidPnSourceModeInfo); 1387 Assert(NT_SUCCESS(tmpStatus)); 1388 *pfHas = TRUE; 1389 } 1390 1391 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hCurVidPnSourceModeSet); 1392 Assert(tmpStatus == STATUS_SUCCESS); 1393 1394 return Status; 1395 } 1396 1397 static NTSTATUS vboxVidPnCofuncModalityForPathTarget(PVBOXVIDPNCOFUNCMODALITY pCbContext, 1398 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 1399 { 1400 PVBOXMP_DEVEXT pDevExt = pCbContext->pDevExt; 1401 D3DKMDT_HVIDPN hVidPn = pCbContext->pEnumCofuncModalityArg->hConstrainingVidPn; 1402 const DXGK_VIDPN_INTERFACE* pVidPnInterface = pCbContext->pVidPnInterface; 1403 PVBOXWDDM_VIDEOMODES_INFO pInfo = &pCbContext->pInfos[VidPnTargetId]; 1404 1405 D3DKMDT_HVIDPNTARGETMODESET hNewVidPnTargetModeSet = NULL; 1406 const DXGK_VIDPNTARGETMODESET_INTERFACE *pNewVidPnTargetModeSetInterface; 1407 1408 Assert(pDevExt->fComplexTopologiesEnabled || VidPnSourceId == VidPnTargetId); 1409 1410 D3DKMDT_HVIDPNSOURCEMODESET hCurVidPnSourceModeSet; 1411 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pCurVidPnSourceModeSetInterface; 1412 NTSTATUS Status = pVidPnInterface->pfnAcquireSourceModeSet(hVidPn, 1413 VidPnSourceId, 1414 &hCurVidPnSourceModeSet, 1415 &pCurVidPnSourceModeSetInterface); 1416 if (!NT_SUCCESS(Status)) 1417 { 1418 AssertFailed(); 1419 return Status; 1420 } 1421 1422 CONST D3DKMDT_VIDPN_SOURCE_MODE* pPinnedVidPnSourceModeInfo; 1423 Status = pCurVidPnSourceModeSetInterface->pfnAcquirePinnedModeInfo(hCurVidPnSourceModeSet, &pPinnedVidPnSourceModeInfo); 1424 if (Status == STATUS_GRAPHICS_MODE_NOT_PINNED) 1425 { 1426 pPinnedVidPnSourceModeInfo = NULL; 1427 Status = STATUS_SUCCESS; 1428 } 1429 else if (!NT_SUCCESS(Status)) 1430 { 1431 LOGREL(("pfnAcquirePinnedModeInfo failed Status(0x%x)", Status)); 1432 AssertFailed(); 1433 } 1434 else 1435 { 1436 Assert(pPinnedVidPnSourceModeInfo); 1437 } 1438 1439 if (NT_SUCCESS(Status)) 1440 { 1441 Status = pVidPnInterface->pfnCreateNewTargetModeSet(hVidPn, 1442 VidPnTargetId, 1443 &hNewVidPnTargetModeSet, 1444 &pNewVidPnTargetModeSetInterface); 1445 if (NT_SUCCESS(Status)) 1446 { 1447 Assert(hNewVidPnTargetModeSet); 1448 Assert(pDevExt->fComplexTopologiesEnabled || VidPnSourceId == VidPnTargetId); 1449 // if (VidPnSourceId == VidPnTargetId && pCbContext->apPathInfos[VidPnTargetId].enmState == VBOXVIDPNPATHITEM_STATE_PRESENT) 1450 { 1451 for (uint32_t i = 0; i < pInfo->cResolutions; ++i) 1404 WARN(("pfnCreateNewTargetModeSet failed %#x", Status)); 1405 1406 Assert(!NT_SUCCESS(Status)); 1407 1408 return Status; 1409 } while (0); 1410 1411 if (fNewSource) 1412 { 1413 do { 1414 D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet; 1415 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface; 1416 1417 Status = pVidPnInterface->pfnCreateNewSourceModeSet(hVidPn, 1418 iSource, 1419 &hVidPnModeSet, 1420 &pVidPnModeSetInterface); 1421 if (NT_SUCCESS(Status)) 1452 1422 { 1453 D3DKMDT_2DREGION *pResolution = &pInfo->aResolutions[i]; 1454 if (pPinnedVidPnSourceModeInfo) 1423 D3DKMDT_VIDPN_SOURCE_MODE *pVidPnModeInfo; 1424 Status = pVidPnModeSetInterface->pfnCreateNewModeInfo(hVidPnModeSet, &pVidPnModeInfo); 1425 if (NT_SUCCESS(Status)) 1455 1426 { 1456 if (pPinnedVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cx != pResolution->cx 1457 || pPinnedVidPnSourceModeInfo->Format.Graphics.PrimSurfSize.cy != pResolution->cy) 1427 vboxVidPnPopulateSourceModeInfo(pVidPnModeInfo, &pData->aSources[iSource].Size); 1428 1429 IN_CONST_D3DKMDT_VIDEO_PRESENT_SOURCE_MODE_ID idMode = pVidPnModeInfo->Id; 1430 1431 Status = pVidPnModeSetInterface->pfnAddMode(hVidPnModeSet, pVidPnModeInfo); 1432 if (NT_SUCCESS(Status)) 1458 1433 { 1459 continue; 1434 pVidPnModeInfo = NULL; 1435 1436 Status = pVidPnModeSetInterface->pfnPinMode(hVidPnModeSet, idMode); 1437 if (NT_SUCCESS(Status)) 1438 { 1439 Status = pVidPnInterface->pfnAssignSourceModeSet(hVidPn, iSource, hVidPnModeSet); 1440 if (NT_SUCCESS(Status)) 1441 { 1442 LOG(("Recommended Source[%d] (%dx%d)", iSource, pData->aSources[iSource].Size.cx, pData->aSources[iSource].Size.cy)); 1443 break; 1444 } 1445 else 1446 WARN(("pfnAssignSourceModeSet failed %#x", Status)); 1447 } 1448 else 1449 WARN(("pfnPinMode failed %#x", Status)); 1450 1451 } 1452 else 1453 WARN(("pfnAddMode failed %#x", Status)); 1454 1455 if (pVidPnModeInfo) 1456 { 1457 NTSTATUS tmpStatus = pVidPnModeSetInterface->pfnReleaseModeInfo(hVidPnModeSet, pVidPnModeInfo); 1458 Assert(tmpStatus == STATUS_SUCCESS); 1460 1459 } 1461 1460 } 1462 1463 D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo; 1464 Status = pNewVidPnTargetModeSetInterface->pfnCreateNewModeInfo(hNewVidPnTargetModeSet, &pNewVidPnTargetModeInfo); 1465 Assert(Status == STATUS_SUCCESS); 1466 if (NT_SUCCESS(Status)) 1467 { 1468 Status = vboxVidPnPopulateTargetModeInfoFromLegacy(pNewVidPnTargetModeInfo, pResolution, i == pInfo->iPreferredResolution); 1469 if (NT_SUCCESS(Status)) 1470 { 1471 Status = pNewVidPnTargetModeSetInterface->pfnAddMode(hNewVidPnTargetModeSet, pNewVidPnTargetModeInfo); 1472 if (NT_SUCCESS(Status)) 1473 { 1474 /* success */ 1475 continue; 1476 } 1477 else 1478 WARN(("pfnAddMode failed, Status 0x%x", Status)); 1479 } 1480 else 1481 WARN(("vboxVidPnPopulateTargetModeInfoFromLegacy failed, Status 0x%x", Status)); 1482 1483 NTSTATUS tmpStatus = pNewVidPnTargetModeSetInterface->pfnReleaseModeInfo(hNewVidPnTargetModeSet, pNewVidPnTargetModeInfo); 1484 Assert(tmpStatus == STATUS_SUCCESS); 1485 } 1486 1487 /* we're here because of an error */ 1488 Assert(!NT_SUCCESS(Status)); 1489 /* ignore mode addition failure */ 1490 Status = STATUS_SUCCESS; 1491 continue; 1461 else 1462 WARN(("pfnCreateNewSourceModeSet failed %#x", Status)); 1463 1464 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hVidPnModeSet); 1465 Assert(tmpStatus == STATUS_SUCCESS); 1492 1466 } 1493 } 1494 } 1495 else 1496 { 1497 AssertFailed(); 1498 } 1499 } 1500 else 1501 { 1502 AssertFailed(); 1503 } 1504 1505 if (pPinnedVidPnSourceModeInfo) 1506 { 1507 NTSTATUS tmpStatus = pCurVidPnSourceModeSetInterface->pfnReleaseModeInfo(hCurVidPnSourceModeSet, pPinnedVidPnSourceModeInfo); 1508 Assert(tmpStatus == STATUS_SUCCESS); 1509 } 1510 1511 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hCurVidPnSourceModeSet); 1512 Assert(tmpStatus == STATUS_SUCCESS); 1513 1514 if (NT_SUCCESS(Status)) 1515 { 1516 Assert(hNewVidPnTargetModeSet); 1517 Status = pVidPnInterface->pfnAssignTargetModeSet(hVidPn, VidPnTargetId, hNewVidPnTargetModeSet); 1518 if (!NT_SUCCESS(Status)) 1519 { 1520 WARN(("\n\n!!!!!!!\n\n pfnAssignTargetModeSet failed, Status(0x%x)", Status)); 1521 tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hNewVidPnTargetModeSet); 1522 Assert(tmpStatus == STATUS_SUCCESS); 1523 } 1524 } 1525 1526 return Status; 1527 } 1528 1529 static NTSTATUS vboxVidPnCofuncModalityForPathSource(PVBOXVIDPNCOFUNCMODALITY pCbContext, 1530 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 1531 { 1532 PVBOXMP_DEVEXT pDevExt = pCbContext->pDevExt; 1533 D3DKMDT_HVIDPN hVidPn = pCbContext->pEnumCofuncModalityArg->hConstrainingVidPn; 1534 const DXGK_VIDPN_INTERFACE* pVidPnInterface = pCbContext->pVidPnInterface; 1535 PVBOXWDDM_VIDEOMODES_INFO pInfo = &pCbContext->pInfos[VidPnTargetId]; 1536 D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet = NULL; 1537 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pNewVidPnSourceModeSetInterface; 1538 1539 Assert(pDevExt->fComplexTopologiesEnabled || VidPnSourceId == VidPnTargetId); 1540 1541 D3DKMDT_HVIDPNTARGETMODESET hCurVidPnTargetModeSet; 1542 const DXGK_VIDPNTARGETMODESET_INTERFACE *pCurVidPnTargetModeSetInterface; 1543 NTSTATUS Status = pVidPnInterface->pfnAcquireTargetModeSet(hVidPn, 1544 VidPnTargetId, 1545 &hCurVidPnTargetModeSet, 1546 &pCurVidPnTargetModeSetInterface); 1547 if (!NT_SUCCESS(Status)) 1548 { 1549 AssertFailed(); 1550 return Status; 1551 } 1552 1553 CONST D3DKMDT_VIDPN_TARGET_MODE* pPinnedVidPnTargetModeInfo; 1554 Status = pCurVidPnTargetModeSetInterface->pfnAcquirePinnedModeInfo(hCurVidPnTargetModeSet, &pPinnedVidPnTargetModeInfo); 1555 if (Status == STATUS_GRAPHICS_MODE_NOT_PINNED) 1556 { 1557 pPinnedVidPnTargetModeInfo = NULL; 1558 Status = STATUS_SUCCESS; 1559 } 1560 else if (!NT_SUCCESS(Status)) 1561 { 1562 LOGREL(("pfnAcquirePinnedModeInfo failed Status(0x%x)", Status)); 1563 AssertFailed(); 1564 } 1565 else 1566 { 1567 Assert(pPinnedVidPnTargetModeInfo); 1568 } 1569 1570 if (NT_SUCCESS(Status)) 1571 { 1572 NTSTATUS Status = pVidPnInterface->pfnCreateNewSourceModeSet(hVidPn, 1573 VidPnSourceId, 1574 &hNewVidPnSourceModeSet, 1575 &pNewVidPnSourceModeSetInterface); 1576 if (NT_SUCCESS(Status)) 1577 { 1578 Assert(hNewVidPnSourceModeSet); 1579 Assert(pDevExt->fComplexTopologiesEnabled || VidPnSourceId == VidPnTargetId); 1580 // if (VidPnSourceId == VidPnTargetId && pCbContext->apPathInfos[VidPnSourceId].enmState == VBOXVIDPNPATHITEM_STATE_PRESENT) 1581 { 1582 for (uint32_t i = 0; i < pInfo->cModes; ++i) 1583 { 1584 VIDEO_MODE_INFORMATION *pMode = &pInfo->aModes[i]; 1585 if (pPinnedVidPnTargetModeInfo) 1586 { 1587 if (pPinnedVidPnTargetModeInfo->VideoSignalInfo.ActiveSize.cx != pMode->VisScreenWidth 1588 || pPinnedVidPnTargetModeInfo->VideoSignalInfo.ActiveSize.cy != pMode->VisScreenHeight) 1589 { 1590 continue; 1591 } 1592 } 1593 1594 D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo; 1595 Status = pNewVidPnSourceModeSetInterface->pfnCreateNewModeInfo(hNewVidPnSourceModeSet, &pNewVidPnSourceModeInfo); 1596 if (NT_SUCCESS(Status)) 1597 { 1598 Status = vboxVidPnPopulateSourceModeInfoFromLegacy(pNewVidPnSourceModeInfo, pMode); 1599 Assert(Status == STATUS_SUCCESS); 1600 if (NT_SUCCESS(Status)) 1601 { 1602 Status = pNewVidPnSourceModeSetInterface->pfnAddMode(hNewVidPnSourceModeSet, pNewVidPnSourceModeInfo); 1603 if (NT_SUCCESS(Status)) 1604 { 1605 /* success */ 1606 continue; 1607 } 1608 else 1609 WARN(("pfnAddMode failed, Status 0x%x", Status)); 1610 } 1611 1612 NTSTATUS tmpStatus = pNewVidPnSourceModeSetInterface->pfnReleaseModeInfo(hNewVidPnSourceModeSet, pNewVidPnSourceModeInfo); 1613 Assert(tmpStatus == STATUS_SUCCESS); 1614 } 1615 else 1616 WARN(("pfnCreateNewModeInfo failed, Status 0x%x", Status)); 1617 /* we're here because of an error */ 1618 Assert(!NT_SUCCESS(Status)); 1619 /* ignore mode addition failure */ 1620 Status = STATUS_SUCCESS; 1621 continue; 1622 } 1623 } 1624 } 1625 else 1626 { 1627 AssertFailed(); 1628 } 1629 } 1630 else 1631 { 1632 AssertFailed(); 1633 } 1634 1635 if (pPinnedVidPnTargetModeInfo) 1636 { 1637 NTSTATUS tmpStatus = pCurVidPnTargetModeSetInterface->pfnReleaseModeInfo(hCurVidPnTargetModeSet, pPinnedVidPnTargetModeInfo); 1638 Assert(tmpStatus == STATUS_SUCCESS); 1639 } 1640 1641 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hCurVidPnTargetModeSet); 1642 Assert(tmpStatus == STATUS_SUCCESS); 1643 1644 if (NT_SUCCESS(Status)) 1645 { 1646 Assert(hNewVidPnSourceModeSet); 1647 Status = pVidPnInterface->pfnAssignSourceModeSet(hVidPn, VidPnSourceId, hNewVidPnSourceModeSet); 1648 if (!NT_SUCCESS(Status)) 1649 { 1650 WARN(("\n\n!!!!!!!\n\n pfnAssignSourceModeSet failed, Status(0x%x)", Status)); 1651 tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hNewVidPnSourceModeSet); 1652 Assert(tmpStatus == STATUS_SUCCESS); 1653 } 1654 } 1655 1656 return Status; 1657 } 1658 1659 NTSTATUS vboxVidPnCofuncModalityForPath(PVBOXVIDPNCOFUNCMODALITY pCbContext, 1660 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId) 1661 { 1662 PVBOXMP_DEVEXT pDevExt = pCbContext->pDevExt; 1663 D3DKMDT_HVIDPN hVidPn = pCbContext->pEnumCofuncModalityArg->hConstrainingVidPn; 1664 const DXGK_VIDPN_INTERFACE* pVidPnInterface = pCbContext->pVidPnInterface; 1665 NTSTATUS Status = STATUS_SUCCESS; 1666 pCbContext->Status = STATUS_SUCCESS; 1667 PVBOXWDDM_VIDEOMODES_INFO pInfo = &pCbContext->pInfos[VidPnTargetId]; 1668 1669 D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmPivot = vboxVidPnCofuncModalityCurrentPathPivot(pCbContext->pEnumCofuncModalityArg, VidPnSourceId, VidPnTargetId); 1670 BOOLEAN fHasPinnedMode = FALSE; 1671 Status = vboxVidPnHasPinnedTargetMode(hVidPn, pVidPnInterface, VidPnTargetId, &fHasPinnedMode); 1672 if (!NT_SUCCESS(Status)) 1673 { 1674 AssertFailed(); 1675 return Status; 1676 } 1677 1678 BOOLEAN fNeedUpdate = enmPivot != D3DKMDT_EPT_VIDPNTARGET && !fHasPinnedMode; 1679 if (fNeedUpdate) 1680 { 1681 Status = vboxVidPnCofuncModalityForPathTarget(pCbContext, VidPnSourceId, VidPnTargetId); 1682 } 1683 1684 if (NT_SUCCESS(Status)) 1685 { 1686 fHasPinnedMode = FALSE; 1687 Status = vboxVidPnHasPinnedSourceMode(hVidPn, pVidPnInterface, VidPnSourceId, &fHasPinnedMode); 1688 if (!NT_SUCCESS(Status)) 1689 { 1690 AssertFailed(); 1691 return Status; 1692 } 1693 1694 fNeedUpdate = enmPivot != D3DKMDT_EPT_VIDPNSOURCE && !fHasPinnedMode; 1695 if (fNeedUpdate) 1696 { 1697 Status = vboxVidPnCofuncModalityForPathSource(pCbContext, VidPnSourceId, VidPnTargetId); 1698 } 1699 } 1700 1701 return Status; 1702 } 1703 1704 DECLCALLBACK(BOOLEAN) vboxVidPnCofuncModalityPathEnum(D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface, 1705 const D3DKMDT_VIDPN_PRESENT_PATH *pNewVidPnPresentPathInfo, PVOID pContext) 1706 { 1707 PVBOXVIDPNCOFUNCMODALITY pCbContext = (PVBOXVIDPNCOFUNCMODALITY)pContext; 1708 D3DKMDT_VIDPN_PRESENT_PATH AdjustedPath = {0}; 1709 NTSTATUS Status = STATUS_SUCCESS; 1710 bool bUpdatePath = false; 1711 AdjustedPath.VidPnSourceId = pNewVidPnPresentPathInfo->VidPnSourceId; 1712 AdjustedPath.VidPnTargetId = pNewVidPnPresentPathInfo->VidPnTargetId; 1713 AdjustedPath.ContentTransformation = pNewVidPnPresentPathInfo->ContentTransformation; 1714 AdjustedPath.CopyProtection = pNewVidPnPresentPathInfo->CopyProtection; 1715 1716 if (pNewVidPnPresentPathInfo->ContentTransformation.Scaling == D3DKMDT_VPPS_UNPINNED) 1717 { 1718 AdjustedPath.ContentTransformation.ScalingSupport.Identity = TRUE; 1719 bUpdatePath = true; 1720 } 1721 1722 if (pNewVidPnPresentPathInfo->ContentTransformation.Rotation == D3DKMDT_VPPR_UNPINNED) 1723 { 1724 AdjustedPath.ContentTransformation.RotationSupport.Identity = TRUE; 1725 bUpdatePath = true; 1726 } 1727 1728 if (bUpdatePath) 1729 { 1730 Status = pVidPnTopologyInterface->pfnUpdatePathSupportInfo(hVidPnTopology, &AdjustedPath); 1731 Assert(Status == STATUS_SUCCESS); 1732 } 1733 1734 Status = vboxVidPnCofuncModalityForPath(pCbContext, pNewVidPnPresentPathInfo->VidPnSourceId, pNewVidPnPresentPathInfo->VidPnTargetId); 1735 1736 pVidPnTopologyInterface->pfnReleasePathInfo(hVidPnTopology, pNewVidPnPresentPathInfo); 1737 1738 pCbContext->Status = Status; 1739 Assert(Status == STATUS_SUCCESS); 1740 return Status == STATUS_SUCCESS; 1467 else 1468 WARN(("pfnCreateNewSourceModeSet failed %#x", Status)); 1469 1470 Assert(!NT_SUCCESS(Status)); 1471 1472 return Status; 1473 } while (0); 1474 } 1475 } 1476 1477 Assert(NT_SUCCESS(Status)); 1478 return STATUS_SUCCESS; 1741 1479 } 1742 1480 … … 1864 1602 } 1865 1603 1866 typedef struct VBOXVIDPNGETPATHSINFO 1867 { 1868 PVBOXMP_DEVEXT pDevExt; 1869 NTSTATUS Status; 1870 BOOLEAN fBreakOnDisabled; 1871 BOOLEAN fDisabledFound; 1872 } VBOXVIDPNGETPATHSINFO, *PVBOXVIDPNGETPATHSINFO; 1873 1874 static DECLCALLBACK(BOOLEAN) vboxVidPnCheckTopologyEnum(D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface, 1875 const D3DKMDT_VIDPN_PRESENT_PATH *pNewVidPnPresentPathInfo, PVOID pContext) 1876 { 1877 PVBOXVIDPNGETPATHSINFO pCbContext = (PVBOXVIDPNGETPATHSINFO)pContext; 1878 NTSTATUS Status = STATUS_SUCCESS; 1879 CONST D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId = pNewVidPnPresentPathInfo->VidPnSourceId; 1880 CONST D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId = pNewVidPnPresentPathInfo->VidPnTargetId; 1881 BOOLEAN fDisabledFound = !vboxVidPnIsPathSupported(pCbContext->pDevExt, pNewVidPnPresentPathInfo); 1882 1883 pCbContext->fDisabledFound |= fDisabledFound; 1884 pCbContext->Status = Status; 1885 if (!NT_SUCCESS(Status)) 1886 return FALSE; /* do not continue on failure */ 1887 1888 return !fDisabledFound || !pCbContext->fBreakOnDisabled; 1889 } 1890 1891 /* we currently support only 0 -> 0, 1 -> 1, 2 -> 2 paths, AND 0 -> 0 must be present 1892 * this routine disables all paths unsupported */ 1893 NTSTATUS VBoxVidPnCheckTopology(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface, BOOLEAN *pfSupported) 1894 { 1895 VBOXVIDPNGETPATHSINFO CbContext = {0}; 1896 CbContext.pDevExt = pDevExt; 1897 CbContext.Status = STATUS_SUCCESS; 1898 CbContext.fBreakOnDisabled = FALSE; 1899 CbContext.fDisabledFound = FALSE; 1900 NTSTATUS Status = vboxVidPnEnumPaths(hVidPnTopology, pVidPnTopologyInterface, vboxVidPnCheckTopologyEnum, &CbContext); 1901 if (!NT_SUCCESS(Status)) 1902 { 1903 WARN(("vboxVidPnEnumPaths failed Status()0x%x\n", Status)); 1604 NTSTATUS VBoxVidPnIsSupported(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, BOOLEAN *pfSupported) 1605 { 1606 *pfSupported = FALSE; 1607 1608 const DXGK_VIDPN_INTERFACE* pVidPnInterface = NULL; 1609 NTSTATUS Status = pDevExt->u.primary.DxgkInterface.DxgkCbQueryVidPnInterface(hVidPn, DXGK_VIDPN_INTERFACE_VERSION_V1, &pVidPnInterface); 1610 if (!NT_SUCCESS(Status)) 1611 { 1612 WARN(("DxgkCbQueryVidPnInterface failed Status()0x%x\n", Status)); 1904 1613 return Status; 1905 1614 } 1906 1615 1907 Status = CbContext.Status; 1908 if (!NT_SUCCESS(Status)) 1909 { 1910 WARN(("vboxVidPnCheckTopologyEnum returned failed Status()0x%x\n", Status)); 1616 #ifdef VBOXWDDM_DEBUG_VIDPN 1617 vboxVidPnDumpVidPn(">>>>IsSupported VidPN (IN) : >>>>\n", pDevExt, hVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<\n"); 1618 #endif 1619 1620 D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology; 1621 const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface; 1622 Status = pVidPnInterface->pfnGetTopology(hVidPn, &hVidPnTopology, &pVidPnTopologyInterface); 1623 if (!NT_SUCCESS(Status)) 1624 { 1625 WARN(("pfnGetTopology failed Status()0x%x\n", Status)); 1911 1626 return Status; 1912 1627 } 1913 1628 1914 BOOLEAN fSupported = !CbContext.fDisabledFound; 1915 1916 /* now check if 0->0 path is present and enabled, and if not, disable everything */ 1917 // if (cItems && aItems[0].enmState != VBOXVIDPNPATHITEM_STATE_PRESENT) 1918 // { 1919 // LOG(("path 0 not set to present\n")); 1920 //// for (i = 0; i < cItems; ++i) 1921 //// { 1922 //// if (aItems[i].enmState == VBOXVIDPNPATHITEM_STATE_PRESENT) 1923 //// aItems[i].enmState = VBOXVIDPNPATHITEM_STATE_DISABLED; 1924 //// } 1925 // fSupported = FALSE; 1926 // } 1927 1928 if (pfSupported) 1929 *pfSupported = fSupported; 1629 VBOXVIDPN_PATH_ITER PathIter; 1630 const D3DKMDT_VIDPN_PRESENT_PATH * pPath; 1631 VBOXCMDVBVA_SCREENMAP_DECL(uint32_t, aVisitedTargetMap); 1632 VBOXCMDVBVA_SCREENMAP_DECL(uint32_t, aModeMap); 1633 CR_SORTARRAY aModes[VBOX_VIDEO_MAX_SCREENS]; 1634 1635 memset(aVisitedTargetMap, 0, sizeof (aVisitedTargetMap)); 1636 memset(aModeMap, 0, sizeof (aModeMap)); 1637 memset(aModes, 0, sizeof (aModes)); 1638 1639 CR_SORTARRAY TargetMode = {0}; 1640 1641 BOOLEAN fSupported = TRUE; 1642 /* collect info first */ 1643 VBoxVidPnPathIterInit(&PathIter, hVidPnTopology, pVidPnTopologyInterface); 1644 while ((pPath = VBoxVidPnPathIterNext(&PathIter)) != NULL) 1645 { 1646 CrSaClear(&TargetMode); 1647 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId = pPath->VidPnSourceId; 1648 D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId = pPath->VidPnTargetId; 1649 /* actually vidpn topology should contain only one target info, right? */ 1650 Assert(!ASMBitTest(aVisitedTargetMap, VidPnTargetId)); 1651 ASMBitSet(aVisitedTargetMap, VidPnTargetId); 1652 1653 if (!vboxVidPnIsPathSupported(pDevExt, pPath)) 1654 { 1655 fSupported = FALSE; 1656 break; 1657 } 1658 1659 RTRECTSIZE TargetSize; 1660 RTRECTSIZE SourceSize; 1661 Status = vboxVidPnQueryPinnedTargetMode(hVidPn, pVidPnInterface, VidPnTargetId, &TargetSize); 1662 if (!NT_SUCCESS(Status)) 1663 { 1664 WARN(("vboxVidPnQueryPinnedTargetMode failed %#x", Status)); 1665 break; 1666 } 1667 1668 Status = vboxVidPnQueryPinnedSourceMode(hVidPn, pVidPnInterface, VidPnSourceId, &SourceSize); 1669 if (!NT_SUCCESS(Status)) 1670 { 1671 WARN(("vboxVidPnQueryPinnedSourceMode failed %#x", Status)); 1672 break; 1673 } 1674 1675 if (memcmp(&TargetSize, &SourceSize, sizeof (TargetSize)) && TargetSize.cx) 1676 { 1677 if (!SourceSize.cx) 1678 WARN(("not expected?")); 1679 1680 fSupported = FALSE; 1681 break; 1682 } 1683 1684 { 1685 D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet; 1686 const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface; 1687 Status = pVidPnInterface->pfnAcquireTargetModeSet(hVidPn, 1688 VidPnTargetId, 1689 &hVidPnModeSet, 1690 &pVidPnModeSetInterface); 1691 if (!NT_SUCCESS(Status)) 1692 { 1693 WARN(("pfnAcquireTargetModeSet failed %#x", Status)); 1694 break; 1695 } 1696 1697 Status = vboxVidPnTargetModeSetToArray(hVidPnModeSet, pVidPnModeSetInterface, &TargetMode); 1698 if (!NT_SUCCESS(Status)) 1699 { 1700 WARN(("vboxVidPnTargetModeSetToArray failed %#x", Status)); 1701 break; 1702 } 1703 1704 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseTargetModeSet(hVidPn, hVidPnModeSet); 1705 Assert(tmpStatus == STATUS_SUCCESS); 1706 } 1707 1708 if (!ASMBitTest(aModeMap, VidPnSourceId)) 1709 { 1710 D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet; 1711 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface; 1712 Status = pVidPnInterface->pfnAcquireSourceModeSet(hVidPn, 1713 VidPnSourceId, 1714 &hVidPnModeSet, 1715 &pVidPnModeSetInterface); 1716 if (!NT_SUCCESS(Status)) 1717 { 1718 WARN(("pfnAcquireSourceModeSet failed %#x", Status)); 1719 break; 1720 } 1721 1722 Status = vboxVidPnSourceModeSetToArray(hVidPnModeSet, pVidPnModeSetInterface, &aModes[VidPnSourceId]); 1723 if (!NT_SUCCESS(Status)) 1724 { 1725 WARN(("vboxVidPnSourceModeSetToArray failed %#x", Status)); 1726 break; 1727 } 1728 1729 NTSTATUS tmpStatus = pVidPnInterface->pfnReleaseSourceModeSet(hVidPn, hVidPnModeSet); 1730 Assert(tmpStatus == STATUS_SUCCESS); 1731 1732 ASMBitSet(aModeMap, VidPnSourceId); 1733 } 1734 1735 if (CrSaCmp(&aModes[VidPnSourceId], &TargetMode)) 1736 { 1737 WARN(("not expected 2?")); 1738 fSupported = FALSE; 1739 break; 1740 } 1741 1742 #if 0 1743 const CR_SORTARRAY *pSupportedModes = VBoxWddmVModesGet(pDevExt, VidPnTargetId); 1744 if (!CrSaCovers(pSupportedModes, &TargetMode)) 1745 { 1746 WARN(("not expected 3?")); 1747 fSupported = FALSE; 1748 break; 1749 } 1750 #endif 1751 } 1752 1753 VBoxVidPnPathIterTerm(&PathIter); 1754 1755 if (!NT_SUCCESS(Status)) 1756 goto done; 1757 1758 Status = VBoxVidPnPathIterStatus(&PathIter); 1759 if (!NT_SUCCESS(Status)) 1760 { 1761 WARN(("PathIter failed Status()0x%x\n", Status)); 1762 goto done; 1763 } 1764 1765 *pfSupported = fSupported; 1766 done: 1767 1768 CrSaCleanup(&TargetMode); 1769 1770 for (uint32_t i = 0; i < (uint32_t)VBoxCommonFromDeviceExt(pDevExt)->cDisplays; ++i) 1771 { 1772 CrSaCleanup(&aModes[i]); 1773 } 1774 1775 1776 return Status; 1777 } 1778 1779 NTSTATUS VBoxVidPnCofuncModality(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmPivot, const DXGK_ENUM_PIVOT *pPivot) 1780 { 1781 const DXGK_VIDPN_INTERFACE* pVidPnInterface = NULL; 1782 NTSTATUS Status = pDevExt->u.primary.DxgkInterface.DxgkCbQueryVidPnInterface(hVidPn, DXGK_VIDPN_INTERFACE_VERSION_V1, &pVidPnInterface); 1783 if (!NT_SUCCESS(Status)) 1784 { 1785 WARN(("DxgkCbQueryVidPnInterface failed Status()0x%x\n", Status)); 1786 return Status; 1787 } 1788 1789 #ifdef VBOXWDDM_DEBUG_VIDPN 1790 vboxVidPnDumpCofuncModalityArg(">>>>MODALITY Args: ", pEnumCofuncModalityArg, "\n"); 1791 vboxVidPnDumpVidPn(">>>>MODALITY VidPN (IN) : >>>>\n", pDevExt, pEnumCofuncModalityArg->hConstrainingVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<\n"); 1792 #endif 1793 1794 D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology; 1795 const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface; 1796 Status = pVidPnInterface->pfnGetTopology(hVidPn, &hVidPnTopology, &pVidPnTopologyInterface); 1797 if (!NT_SUCCESS(Status)) 1798 { 1799 WARN(("pfnGetTopology failed Status()0x%x\n", Status)); 1800 return Status; 1801 } 1802 1803 VBOXVIDPN_PATH_ITER PathIter; 1804 const D3DKMDT_VIDPN_PRESENT_PATH * pPath; 1805 VBOXCMDVBVA_SCREENMAP_DECL(uint32_t, aVisitedTargetMap); 1806 VBOXCMDVBVA_SCREENMAP_DECL(uint32_t, aAdjustedModeMap); 1807 CR_SORTARRAY aModes[VBOX_VIDEO_MAX_SCREENS]; 1808 1809 memset(aVisitedTargetMap, 0, sizeof (aVisitedTargetMap)); 1810 memset(aAdjustedModeMap, 0, sizeof (aAdjustedModeMap)); 1811 memset(aModes, 0, sizeof (aModes)); 1812 1813 /* collect info first */ 1814 VBoxVidPnPathIterInit(&PathIter, hVidPnTopology, pVidPnTopologyInterface); 1815 while ((pPath = VBoxVidPnPathIterNext(&PathIter)) != NULL) 1816 { 1817 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId = pPath->VidPnSourceId; 1818 D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId = pPath->VidPnTargetId; 1819 /* actually vidpn topology should contain only one target info, right? */ 1820 Assert(!ASMBitTest(aVisitedTargetMap, VidPnTargetId)); 1821 ASMBitSet(aVisitedTargetMap, VidPnTargetId); 1822 1823 D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmCurPivot = vboxVidPnCofuncModalityCurrentPathPivot(enmPivot, pPivot, VidPnSourceId, VidPnTargetId); 1824 1825 Status = vboxVidPnCollectInfoForPathTarget(pDevExt, 1826 hVidPn, 1827 pVidPnInterface, 1828 enmCurPivot, 1829 aAdjustedModeMap, 1830 aModes, 1831 VidPnSourceId, VidPnTargetId); 1832 if (!NT_SUCCESS(Status)) 1833 { 1834 WARN(("vboxVidPnCollectInfoForPathTarget failed Status(0x%x\n", Status)); 1835 break; 1836 } 1837 1838 Assert(CrSaCovers(VBoxWddmVModesGet(pDevExt, VidPnTargetId), &aModes[VidPnTargetId])); 1839 1840 Status = vboxVidPnCollectInfoForPathSource(pDevExt, 1841 hVidPn, 1842 pVidPnInterface, 1843 enmCurPivot, 1844 aAdjustedModeMap, 1845 aModes, 1846 VidPnSourceId, VidPnTargetId); 1847 if (!NT_SUCCESS(Status)) 1848 { 1849 WARN(("vboxVidPnCollectInfoForPathSource failed Status(0x%x\n", Status)); 1850 break; 1851 } 1852 1853 Assert(CrSaCovers(VBoxWddmVModesGet(pDevExt, VidPnTargetId), &aModes[VidPnTargetId])); 1854 } 1855 1856 VBoxVidPnPathIterTerm(&PathIter); 1857 1858 if (!NT_SUCCESS(Status)) 1859 goto done; 1860 1861 Status = VBoxVidPnPathIterStatus(&PathIter); 1862 if (!NT_SUCCESS(Status)) 1863 { 1864 WARN(("PathIter failed Status()0x%x\n", Status)); 1865 goto done; 1866 } 1867 1868 /* now we have collected all the necessary info, 1869 * go ahead and apply it */ 1870 memset(aVisitedTargetMap, 0, sizeof (aVisitedTargetMap)); 1871 VBoxVidPnPathIterInit(&PathIter, hVidPnTopology, pVidPnTopologyInterface); 1872 while ((pPath = VBoxVidPnPathIterNext(&PathIter)) != NULL) 1873 { 1874 D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId = pPath->VidPnSourceId; 1875 D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId = pPath->VidPnTargetId; 1876 /* actually vidpn topology should contain only one target info, right? */ 1877 Assert(!ASMBitTest(aVisitedTargetMap, VidPnTargetId)); 1878 ASMBitSet(aVisitedTargetMap, VidPnTargetId); 1879 1880 D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmCurPivot = vboxVidPnCofuncModalityCurrentPathPivot(enmPivot, pPivot, VidPnSourceId, VidPnTargetId); 1881 1882 bool bUpdatePath = false; 1883 D3DKMDT_VIDPN_PRESENT_PATH AdjustedPath = {0}; 1884 AdjustedPath.VidPnSourceId = pPath->VidPnSourceId; 1885 AdjustedPath.VidPnTargetId = pPath->VidPnTargetId; 1886 AdjustedPath.ContentTransformation = pPath->ContentTransformation; 1887 AdjustedPath.CopyProtection = pPath->CopyProtection; 1888 1889 if (pPath->ContentTransformation.Scaling == D3DKMDT_VPPS_UNPINNED) 1890 { 1891 AdjustedPath.ContentTransformation.ScalingSupport.Identity = TRUE; 1892 bUpdatePath = true; 1893 } 1894 1895 if (pPath->ContentTransformation.Rotation == D3DKMDT_VPPR_UNPINNED) 1896 { 1897 AdjustedPath.ContentTransformation.RotationSupport.Identity = TRUE; 1898 bUpdatePath = true; 1899 } 1900 1901 if (bUpdatePath) 1902 { 1903 Status = pVidPnTopologyInterface->pfnUpdatePathSupportInfo(hVidPnTopology, &AdjustedPath); 1904 if (!NT_SUCCESS(Status)) 1905 { 1906 WARN(("pfnUpdatePathSupportInfo failed Status()0x%x\n", Status)); 1907 goto done; 1908 } 1909 } 1910 1911 Assert(CrSaCovers(VBoxWddmVModesGet(pDevExt, VidPnTargetId), &aModes[VidPnTargetId])); 1912 1913 Status = vboxVidPnApplyInfoForPathTarget(pDevExt, 1914 hVidPn, 1915 pVidPnInterface, 1916 enmCurPivot, 1917 aAdjustedModeMap, 1918 aModes, 1919 VidPnSourceId, VidPnTargetId); 1920 if (!NT_SUCCESS(Status)) 1921 { 1922 WARN(("vboxVidPnApplyInfoForPathTarget failed Status(0x%x\n", Status)); 1923 break; 1924 } 1925 1926 Status = vboxVidPnApplyInfoForPathSource(pDevExt, 1927 hVidPn, 1928 pVidPnInterface, 1929 enmCurPivot, 1930 aAdjustedModeMap, 1931 aModes, 1932 VidPnSourceId, VidPnTargetId); 1933 if (!NT_SUCCESS(Status)) 1934 { 1935 WARN(("vboxVidPnApplyInfoForPathSource failed Status(0x%x\n", Status)); 1936 break; 1937 } 1938 } 1939 1940 VBoxVidPnPathIterTerm(&PathIter); 1941 1942 if (!NT_SUCCESS(Status)) 1943 goto done; 1944 1945 Status = VBoxVidPnPathIterStatus(&PathIter); 1946 if (!NT_SUCCESS(Status)) 1947 { 1948 WARN(("PathIter failed Status()0x%x\n", Status)); 1949 goto done; 1950 } 1951 1952 done: 1953 1954 for (uint32_t i = 0; i < (uint32_t)VBoxCommonFromDeviceExt(pDevExt)->cDisplays; ++i) 1955 { 1956 CrSaCleanup(&aModes[i]); 1957 } 1930 1958 1931 1959 return Status; … … 2399 2427 } 2400 2428 2401 typedef struct VBOXVIDPNCOMMIT2402 {2403 NTSTATUS Status;2404 PVBOXMP_DEVEXT pDevExt;2405 D3DKMDT_HVIDPN hVidPn;2406 const DXGK_VIDPN_INTERFACE* pVidPnInterface;2407 PVBOXWDDM_ALLOCATION pAllocation;2408 VBOXWDDM_SOURCE *paSources;2409 VBOXWDDM_TARGET *paTargets;2410 } VBOXVIDPNCOMMIT, *PVBOXVIDPNCOMMIT;2411 2412 DECLCALLBACK(BOOLEAN) vboxVidPnCommitPathEnum(D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface,2413 const D3DKMDT_VIDPN_PRESENT_PATH *pVidPnPresentPathInfo, PVOID pContext)2414 {2415 NTSTATUS Status = STATUS_SUCCESS;2416 PVBOXVIDPNCOMMIT pCommitInfo = (PVBOXVIDPNCOMMIT)pContext;2417 PVBOXMP_DEVEXT pDevExt = pCommitInfo->pDevExt;2418 const D3DKMDT_HVIDPN hDesiredVidPn = pCommitInfo->hVidPn;2419 const DXGK_VIDPN_INTERFACE* pVidPnInterface = pCommitInfo->pVidPnInterface;2420 2421 Status = VBoxVidPnCommitSourceModeForSrcId(pDevExt, hDesiredVidPn, pVidPnInterface, pCommitInfo->pAllocation,2422 pVidPnPresentPathInfo->VidPnSourceId, pCommitInfo->paSources, pCommitInfo->paTargets);2423 if (Status != STATUS_SUCCESS)2424 WARN(("VBoxVidPnCommitSourceModeForSrcId failed Status(0x%x)", Status));2425 2426 pCommitInfo->Status = Status;2427 pVidPnTopologyInterface->pfnReleasePathInfo(hVidPnTopology, pVidPnPresentPathInfo);2428 return Status == STATUS_SUCCESS;2429 }2430 2431 2429 NTSTATUS VBoxVidPnCommitAll(PVBOXMP_DEVEXT pDevExt, const D3DKMDT_HVIDPN hDesiredVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 2432 2430 PVBOXWDDM_ALLOCATION pAllocation, … … 2461 2459 VBoxVidPnStCleanup(paSources, paTargets, VBoxCommonFromDeviceExt(pDevExt)->cDisplays); 2462 2460 2463 VBOXVIDPNCOMMIT CbContext; 2464 memset(&CbContext, 0, sizeof (CbContext)); 2465 CbContext.pDevExt = pDevExt; 2466 CbContext.hVidPn = hDesiredVidPn; 2467 CbContext.pVidPnInterface = pVidPnInterface; 2468 CbContext.pAllocation = pAllocation; 2469 CbContext.paSources = paSources; 2470 CbContext.paTargets = paTargets; 2471 Status = vboxVidPnEnumPaths(hVidPnTopology, pVidPnTopologyInterface, 2472 vboxVidPnCommitPathEnum, &CbContext); 2473 if (!NT_SUCCESS(Status)) 2474 { 2475 WARN(("vboxVidPnEnumPaths failed Status 0x%x", Status)); 2461 VBOXVIDPN_PATH_ITER PathIter; 2462 const D3DKMDT_VIDPN_PRESENT_PATH *pPath; 2463 VBoxVidPnPathIterInit(&PathIter, hVidPnTopology, pVidPnTopologyInterface); 2464 while ((pPath = VBoxVidPnPathIterNext(&PathIter)) != NULL) 2465 { 2466 Status = VBoxVidPnCommitSourceModeForSrcId(pDevExt, hDesiredVidPn, pVidPnInterface, pAllocation, 2467 pPath->VidPnSourceId, paSources, paTargets); 2468 if (Status != STATUS_SUCCESS) 2469 { 2470 WARN(("VBoxVidPnCommitSourceModeForSrcId failed Status(0x%x)", Status)); 2471 break; 2472 } 2473 } 2474 2475 VBoxVidPnPathIterTerm(&PathIter); 2476 2477 if (!NT_SUCCESS(Status)) 2478 { 2479 WARN(("")); 2476 2480 return Status; 2477 2481 } 2478 2482 2479 Status = CbContext.Status;2480 if (!NT_SUCCESS(Status)) 2481 { 2482 WARN((" vboxVidPnCommitPathEnumfailed Status 0x%x", Status));2483 Status = VBoxVidPnPathIterStatus(&PathIter); 2484 if (!NT_SUCCESS(Status)) 2485 { 2486 WARN(("VBoxVidPnPathIterStatus failed Status 0x%x", Status)); 2483 2487 return Status; 2484 2488 } 2485 2489 2486 return S tatus;2490 return STATUS_SUCCESS; 2487 2491 } 2488 2492 -
trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.h
r51269 r52136 48 48 PVBOXWDDM_TARGET VBoxVidPnStTIterNext(VBOXWDDM_TARGET_ITER *pIter); 49 49 50 NTSTATUS vboxVidPnCheckSourceModeInfo(const D3DKMDT_HVIDPN hDesiredVidPn,51 const D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo,52 BOOLEAN *pbSupported);53 54 NTSTATUS vboxVidPnCheckSourceModeSet(const D3DKMDT_HVIDPN hDesiredVidPn,55 D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet, const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnSourceModeSetInterface,56 BOOLEAN *pbSupported);57 58 NTSTATUS vboxVidPnCheckTargetModeInfo(const D3DKMDT_HVIDPN hDesiredVidPn,59 const D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo,60 BOOLEAN *pbSupported);61 62 NTSTATUS vboxVidPnCheckTargetModeSet(const D3DKMDT_HVIDPN hDesiredVidPn,63 D3DKMDT_HVIDPNTARGETMODESET hNewVidPnTargetModeSet, const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnTargetModeSetInterface,64 BOOLEAN *pbSupported);65 66 typedef enum67 {68 VBOXVIDPNPATHITEM_STATE_NOT_EXISTS = 0,69 VBOXVIDPNPATHITEM_STATE_PRESENT,70 VBOXVIDPNPATHITEM_STATE_DISABLED71 } VBOXVIDPNPATHITEM_STATE;72 73 typedef struct VBOXVIDPNPATHITEM74 {75 VBOXVIDPNPATHITEM_STATE enmState;76 } VBOXVIDPNPATHITEM, *PVBOXVIDPNPATHITEM;77 78 typedef struct VBOXVIDPNCOFUNCMODALITY79 {80 NTSTATUS Status;81 PVBOXMP_DEVEXT pDevExt;82 const DXGK_VIDPN_INTERFACE* pVidPnInterface;83 CONST DXGKARG_ENUMVIDPNCOFUNCMODALITY* pEnumCofuncModalityArg;84 PVBOXWDDM_VIDEOMODES_INFO pInfos;85 // UINT cPathInfos;86 // PVBOXVIDPNPATHITEM apPathInfos;87 } VBOXVIDPNCOFUNCMODALITY, *PVBOXVIDPNCOFUNCMODALITY;88 89 50 /* !!!NOTE: The callback is responsible for releasing the path */ 90 51 typedef DECLCALLBACK(BOOLEAN) FNVBOXVIDPNENUMPATHS(D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface, … … 111 72 typedef FNVBOXVIDPNENUMTARGETSFORSOURCE *PFNVBOXVIDPNENUMTARGETSFORSOURCE; 112 73 113 DECLCALLBACK(BOOLEAN) vboxVidPnCofuncModalityPathEnum(D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface,114 const D3DKMDT_VIDPN_PRESENT_PATH *pNewVidPnPresentPathInfo, PVOID pContext);115 116 DECLCALLBACK(BOOLEAN) vboxVidPnCofuncModalitySourceModeEnum(PVBOXMP_DEVEXT pDevExt, const D3DKMDT_HVIDPN hDesiredVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface,117 D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet, const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnSourceModeSetInterface,118 const D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo, PVOID pContext);119 120 DECLCALLBACK(BOOLEAN) vboxVidPnCofuncModalityTargetModeEnum(PVBOXMP_DEVEXT pDevExt, const D3DKMDT_HVIDPN hDesiredVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface,121 D3DKMDT_HVIDPNTARGETMODESET hNewVidPnTargetModeSet, const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnTargetModeSetInterface,122 const D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo, PVOID pContext);123 124 74 NTSTATUS VBoxVidPnCommitSourceModeForSrcId(PVBOXMP_DEVEXT pDevExt, const D3DKMDT_HVIDPN hDesiredVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, 125 75 PVBOXWDDM_ALLOCATION pAllocation, … … 145 95 CONST D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, 146 96 PFNVBOXVIDPNENUMTARGETSFORSOURCE pfnCallback, PVOID pContext); 147 148 NTSTATUS vboxVidPnPopulateMonitorSourceModeInfoFromLegacy(PVBOXMP_DEVEXT pDevExt,149 D3DKMDT_MONITOR_SOURCE_MODE *pMonitorSourceMode,150 D3DKMDT_2DREGION *pResolution,151 D3DKMDT_MONITOR_CAPABILITIES_ORIGIN enmOrigin,152 BOOLEAN bPreferred);153 154 NTSTATUS vboxVidPnCreatePopulateVidPnPathFromLegacy(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface,155 VIDEO_MODE_INFORMATION *pModes, uint32_t cModes, int iPreferredMode,156 D3DKMDT_2DREGION *pResolutions, uint32_t cResolutions,157 const D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, const D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId);158 159 NTSTATUS vboxVidPnCheckAddMonitorModes(PVBOXMP_DEVEXT pDevExt,160 D3DDDI_VIDEO_PRESENT_TARGET_ID targetId, D3DKMDT_MONITOR_CAPABILITIES_ORIGIN enmOrigin,161 D3DKMDT_2DREGION *pResolutions, uint32_t cResolutions, int iPreferred);162 163 NTSTATUS vboxVidPnMatchMonitorModes(PVBOXMP_DEVEXT pDevExt, D3DDDI_VIDEO_PRESENT_TARGET_ID targetId,164 D3DKMDT_2DREGION *pResolutions, uint32_t cResolutions, BOOLEAN *pfMatch);165 166 NTSTATUS vboxVidPnCofuncModalityForPath(PVBOXVIDPNCOFUNCMODALITY pCbContext, D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId);167 168 NTSTATUS VBoxVidPnCheckTopology(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface, BOOLEAN *pfSupported);169 170 NTSTATUS vboxVidPnPathAdd(D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface,171 const D3DDDI_VIDEO_PRESENT_SOURCE_ID VidPnSourceId, const D3DDDI_VIDEO_PRESENT_TARGET_ID VidPnTargetId);172 97 173 98 void vboxVidPnDumpVidPn(const char * pPrefix, PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, const char * pSuffix); … … 178 103 const D3DKMDT_VIDPN_TARGET_MODE *pNewVidPnTargetModeInfo, PVOID pContext); 179 104 105 106 typedef struct VBOXVIDPN_SOURCEMODE_ITER 107 { 108 D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet; 109 const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface; 110 const D3DKMDT_VIDPN_SOURCE_MODE *pCurVidPnModeInfo; 111 NTSTATUS Status; 112 } VBOXVIDPN_SOURCEMODE_ITER; 113 114 DECLINLINE(void) VBoxVidPnSourceModeIterInit(VBOXVIDPN_SOURCEMODE_ITER *pIter, D3DKMDT_HVIDPNSOURCEMODESET hVidPnModeSet, const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnModeSetInterface) 115 { 116 pIter->hVidPnModeSet = hVidPnModeSet; 117 pIter->pVidPnModeSetInterface = pVidPnModeSetInterface; 118 pIter->pCurVidPnModeInfo = NULL; 119 pIter->Status = STATUS_SUCCESS; 120 } 121 122 DECLINLINE(void) VBoxVidPnSourceModeIterTerm(VBOXVIDPN_SOURCEMODE_ITER *pIter) 123 { 124 if (pIter->pCurVidPnModeInfo) 125 { 126 pIter->pVidPnModeSetInterface->pfnReleaseModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo); 127 pIter->pCurVidPnModeInfo = NULL; 128 } 129 } 130 131 DECLINLINE(const D3DKMDT_VIDPN_SOURCE_MODE *) VBoxVidPnSourceModeIterNext(VBOXVIDPN_SOURCEMODE_ITER *pIter) 132 { 133 NTSTATUS Status; 134 const D3DKMDT_VIDPN_SOURCE_MODE *pCurVidPnModeInfo; 135 136 if (!pIter->pCurVidPnModeInfo) 137 Status = pIter->pVidPnModeSetInterface->pfnAcquireFirstModeInfo(pIter->hVidPnModeSet, &pCurVidPnModeInfo); 138 else 139 Status = pIter->pVidPnModeSetInterface->pfnAcquireNextModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo, &pCurVidPnModeInfo); 140 141 if (Status == STATUS_SUCCESS) 142 { 143 Assert(pCurVidPnModeInfo); 144 145 if (pIter->pCurVidPnModeInfo) 146 pIter->pVidPnModeSetInterface->pfnReleaseModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo); 147 148 pIter->pCurVidPnModeInfo = pCurVidPnModeInfo; 149 return pCurVidPnModeInfo; 150 } 151 152 if (Status == STATUS_GRAPHICS_NO_MORE_ELEMENTS_IN_DATASET 153 || Status == STATUS_GRAPHICS_DATASET_IS_EMPTY) 154 return NULL; 155 156 WARN(("getting Source info failed %#x", Status)); 157 158 pIter->Status = Status; 159 return NULL; 160 } 161 162 DECLINLINE(NTSTATUS) VBoxVidPnSourceModeIterStatus(VBOXVIDPN_SOURCEMODE_ITER *pIter) 163 { 164 return pIter->Status; 165 } 166 167 typedef struct VBOXVIDPN_TARGETMODE_ITER 168 { 169 D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet; 170 const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface; 171 const D3DKMDT_VIDPN_TARGET_MODE *pCurVidPnModeInfo; 172 NTSTATUS Status; 173 } VBOXVIDPN_TARGETMODE_ITER; 174 175 DECLINLINE(void) VBoxVidPnTargetModeIterInit(VBOXVIDPN_TARGETMODE_ITER *pIter,D3DKMDT_HVIDPNTARGETMODESET hVidPnModeSet, const DXGK_VIDPNTARGETMODESET_INTERFACE *pVidPnModeSetInterface) 176 { 177 pIter->hVidPnModeSet = hVidPnModeSet; 178 pIter->pVidPnModeSetInterface = pVidPnModeSetInterface; 179 pIter->pCurVidPnModeInfo = NULL; 180 pIter->Status = STATUS_SUCCESS; 181 } 182 183 DECLINLINE(void) VBoxVidPnTargetModeIterTerm(VBOXVIDPN_TARGETMODE_ITER *pIter) 184 { 185 if (pIter->pCurVidPnModeInfo) 186 { 187 pIter->pVidPnModeSetInterface->pfnReleaseModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo); 188 pIter->pCurVidPnModeInfo = NULL; 189 } 190 } 191 192 DECLINLINE(const D3DKMDT_VIDPN_TARGET_MODE *) VBoxVidPnTargetModeIterNext(VBOXVIDPN_TARGETMODE_ITER *pIter) 193 { 194 NTSTATUS Status; 195 const D3DKMDT_VIDPN_TARGET_MODE *pCurVidPnModeInfo; 196 197 if (!pIter->pCurVidPnModeInfo) 198 Status = pIter->pVidPnModeSetInterface->pfnAcquireFirstModeInfo(pIter->hVidPnModeSet, &pCurVidPnModeInfo); 199 else 200 Status = pIter->pVidPnModeSetInterface->pfnAcquireNextModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo, &pCurVidPnModeInfo); 201 202 if (Status == STATUS_SUCCESS) 203 { 204 Assert(pCurVidPnModeInfo); 205 206 if (pIter->pCurVidPnModeInfo) 207 pIter->pVidPnModeSetInterface->pfnReleaseModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo); 208 209 pIter->pCurVidPnModeInfo = pCurVidPnModeInfo; 210 return pCurVidPnModeInfo; 211 } 212 213 if (Status == STATUS_GRAPHICS_NO_MORE_ELEMENTS_IN_DATASET 214 || Status == STATUS_GRAPHICS_DATASET_IS_EMPTY) 215 return NULL; 216 217 WARN(("getting Target info failed %#x", Status)); 218 219 pIter->Status = Status; 220 return NULL; 221 } 222 223 DECLINLINE(NTSTATUS) VBoxVidPnTargetModeIterStatus(VBOXVIDPN_TARGETMODE_ITER *pIter) 224 { 225 return pIter->Status; 226 } 227 228 229 typedef struct VBOXVIDPN_MONITORMODE_ITER 230 { 231 D3DKMDT_HMONITORSOURCEMODESET hVidPnModeSet; 232 const DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface; 233 const D3DKMDT_MONITOR_SOURCE_MODE *pCurVidPnModeInfo; 234 NTSTATUS Status; 235 } VBOXVIDPN_MONITORMODE_ITER; 236 237 238 DECLINLINE(void) VBoxVidPnMonitorModeIterInit(VBOXVIDPN_MONITORMODE_ITER *pIter, D3DKMDT_HMONITORSOURCEMODESET hVidPnModeSet, const DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface) 239 { 240 pIter->hVidPnModeSet = hVidPnModeSet; 241 pIter->pVidPnModeSetInterface = pVidPnModeSetInterface; 242 pIter->pCurVidPnModeInfo = NULL; 243 pIter->Status = STATUS_SUCCESS; 244 } 245 246 DECLINLINE(void) VBoxVidPnMonitorModeIterTerm(VBOXVIDPN_MONITORMODE_ITER *pIter) 247 { 248 if (pIter->pCurVidPnModeInfo) 249 { 250 pIter->pVidPnModeSetInterface->pfnReleaseModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo); 251 pIter->pCurVidPnModeInfo = NULL; 252 } 253 } 254 255 DECLINLINE(const D3DKMDT_MONITOR_SOURCE_MODE *) VBoxVidPnMonitorModeIterNext(VBOXVIDPN_MONITORMODE_ITER *pIter) 256 { 257 NTSTATUS Status; 258 const D3DKMDT_MONITOR_SOURCE_MODE *pCurVidPnModeInfo; 259 260 if (!pIter->pCurVidPnModeInfo) 261 Status = pIter->pVidPnModeSetInterface->pfnAcquireFirstModeInfo(pIter->hVidPnModeSet, &pCurVidPnModeInfo); 262 else 263 Status = pIter->pVidPnModeSetInterface->pfnAcquireNextModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo, &pCurVidPnModeInfo); 264 265 if (Status == STATUS_SUCCESS) 266 { 267 Assert(pCurVidPnModeInfo); 268 269 if (pIter->pCurVidPnModeInfo) 270 pIter->pVidPnModeSetInterface->pfnReleaseModeInfo(pIter->hVidPnModeSet, pIter->pCurVidPnModeInfo); 271 272 pIter->pCurVidPnModeInfo = pCurVidPnModeInfo; 273 return pCurVidPnModeInfo; 274 } 275 276 if (Status == STATUS_GRAPHICS_NO_MORE_ELEMENTS_IN_DATASET 277 || Status == STATUS_GRAPHICS_DATASET_IS_EMPTY) 278 return NULL; 279 280 WARN(("getting Monitor info failed %#x", Status)); 281 282 pIter->Status = Status; 283 return NULL; 284 } 285 286 DECLINLINE(NTSTATUS) VBoxVidPnMonitorModeIterStatus(VBOXVIDPN_MONITORMODE_ITER *pIter) 287 { 288 return pIter->Status; 289 } 290 291 292 293 typedef struct VBOXVIDPN_PATH_ITER 294 { 295 D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology; 296 const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface; 297 const D3DKMDT_VIDPN_PRESENT_PATH *pCurVidPnPathInfo; 298 NTSTATUS Status; 299 } VBOXVIDPN_PATH_ITER; 300 301 302 DECLINLINE(void) VBoxVidPnPathIterInit(VBOXVIDPN_PATH_ITER *pIter, D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology, const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface) 303 { 304 pIter->hVidPnTopology = hVidPnTopology; 305 pIter->pVidPnTopologyInterface = pVidPnTopologyInterface; 306 pIter->pCurVidPnPathInfo = NULL; 307 pIter->Status = STATUS_SUCCESS; 308 } 309 310 DECLINLINE(void) VBoxVidPnPathIterTerm(VBOXVIDPN_PATH_ITER *pIter) 311 { 312 if (pIter->pCurVidPnPathInfo) 313 { 314 pIter->pVidPnTopologyInterface->pfnReleasePathInfo(pIter->hVidPnTopology, pIter->pCurVidPnPathInfo); 315 pIter->pCurVidPnPathInfo = NULL; 316 } 317 } 318 319 DECLINLINE(const D3DKMDT_VIDPN_PRESENT_PATH *) VBoxVidPnPathIterNext(VBOXVIDPN_PATH_ITER *pIter) 320 { 321 NTSTATUS Status; 322 const D3DKMDT_VIDPN_PRESENT_PATH *pCurVidPnPathInfo; 323 324 if (!pIter->pCurVidPnPathInfo) 325 Status = pIter->pVidPnTopologyInterface->pfnAcquireFirstPathInfo(pIter->hVidPnTopology, &pCurVidPnPathInfo); 326 else 327 Status = pIter->pVidPnTopologyInterface->pfnAcquireNextPathInfo(pIter->hVidPnTopology, pIter->pCurVidPnPathInfo, &pCurVidPnPathInfo); 328 329 if (Status == STATUS_SUCCESS) 330 { 331 Assert(pCurVidPnPathInfo); 332 333 if (pIter->pCurVidPnPathInfo) 334 pIter->pVidPnTopologyInterface->pfnReleasePathInfo(pIter->hVidPnTopology, pIter->pCurVidPnPathInfo); 335 336 pIter->pCurVidPnPathInfo = pCurVidPnPathInfo; 337 return pCurVidPnPathInfo; 338 } 339 340 if (Status == STATUS_GRAPHICS_NO_MORE_ELEMENTS_IN_DATASET 341 || Status == STATUS_GRAPHICS_DATASET_IS_EMPTY) 342 return NULL; 343 344 WARN(("getting Path info failed %#x", Status)); 345 346 pIter->Status = Status; 347 return NULL; 348 } 349 350 DECLINLINE(NTSTATUS) VBoxVidPnPathIterStatus(VBOXVIDPN_PATH_ITER *pIter) 351 { 352 return pIter->Status; 353 } 354 355 NTSTATUS VBoxVidPnRecommendMonitorModes(PVBOXMP_DEVEXT pDevExt, D3DDDI_VIDEO_PRESENT_TARGET_ID VideoPresentTargetId, 356 D3DKMDT_HMONITORSOURCEMODESET hVidPnModeSet, const DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface); 357 358 NTSTATUS VBoxVidPnRecommendFunctional(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, const VBOXWDDM_RECOMMENDVIDPN *pData); 359 360 NTSTATUS VBoxVidPnCofuncModality(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmPivot, const DXGK_ENUM_PIVOT *pPivot); 361 362 NTSTATUS VBoxVidPnIsSupported(PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, BOOLEAN *pfSupported); 363 364 NTSTATUS VBoxVidPnUpdateModes(PVBOXMP_DEVEXT pDevExt, uint32_t u32TargetId, const RTRECTSIZE *pSize); 365 180 366 #endif /* #ifndef ___VBoxMPVidPn_h___ */ -
trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPWddm.cpp
r51920 r52136 532 532 bool vboxWddmGhDisplayCheckSetInfoFromSource(PVBOXMP_DEVEXT pDevExt, PVBOXWDDM_SOURCE pSource) 533 533 { 534 bool fReportTargets = !pDevExt-> cContextsDispIfResize;534 bool fReportTargets = !pDevExt->fDisableTargetUpdate; 535 535 return vboxWddmGhDisplayCheckSetInfoFromSourceEx(pDevExt, pSource, fReportTargets); 536 536 } … … 629 629 void vboxWddmGhDisplayCheckSetInfoForDisabledTargetsCheck(PVBOXMP_DEVEXT pDevExt) 630 630 { 631 bool fReportTargets = !pDevExt-> cContextsDispIfResize;631 bool fReportTargets = !pDevExt->fDisableTargetUpdate; 632 632 633 633 if (fReportTargets) … … 649 649 void vboxWddmGhDisplayCheckSetInfo(PVBOXMP_DEVEXT pDevExt) 650 650 { 651 bool fReportTargets = !pDevExt-> cContextsDispIfResize;651 bool fReportTargets = !pDevExt->fDisableTargetUpdate; 652 652 vboxWddmGhDisplayCheckSetInfoEx(pDevExt, fReportTargets); 653 653 } … … 1154 1154 pDevExt->cContextsDispIfResize = 0; 1155 1155 pDevExt->cUnlockedVBVADisabled = 0; 1156 pDevExt->fDisableTargetUpdate = 0; 1156 1157 VBOXWDDM_CTXLOCK_INIT(pDevExt); 1157 1158 KeInitializeSpinLock(&pDevExt->SynchLock); 1158 1159 VBoxMPCmnInitCustomVideoModes(pDevExt);1160 1159 1161 1160 VBoxCommonFromDeviceExt(pDevExt)->fAnyX = VBoxVideoAnyWidthAllowed(); … … 1278 1277 #endif 1279 1278 1280 VBoxWddm InitVideoModes(pDevExt);1279 VBoxWddmVModesInit(pDevExt); 1281 1280 } 1282 1281 else … … 1965 1964 PVBOXMP_DEVEXT pDevExt = (PVBOXMP_DEVEXT)MiniportDeviceContext; 1966 1965 1966 if (ChildStatus->ChildUid >= (uint32_t)VBoxCommonFromDeviceExt(pDevExt)->cDisplays) 1967 { 1968 WARN(("Invalid child id %d", ChildStatus->ChildUid)); 1969 return STATUS_INVALID_PARAMETER; 1970 } 1971 1967 1972 NTSTATUS Status = STATUS_SUCCESS; 1968 1973 switch (ChildStatus->Type) … … 1972 1977 LOGF(("StatusConnection")); 1973 1978 VBOXWDDM_TARGET *pTarget = &pDevExt->aTargets[ChildStatus->ChildUid]; 1979 BOOLEAN Connected = !!pTarget->fConnected; 1980 if (!Connected) 1981 LOGREL(("Tgt[%d] DISCONNECTED!!", ChildStatus->ChildUid)); 1974 1982 ChildStatus->HotPlug.Connected = !!pTarget->fConnected; 1975 1983 break; … … 4586 4594 } 4587 4595 #endif 4588 case VBOXESC_REINITVIDEOMODES: 4589 { 4596 case VBOXESC_CONFIGURETARGETS: 4597 { 4598 LOG(("=> VBOXESC_CONFIGURETARGETS")); 4599 4590 4600 if (!pEscape->Flags.HardwareAccess) 4591 4601 { 4592 WARN(("VBOXESC_ REINITVIDEOMODESBYMASKcalled without HardwareAccess flag set, failing"));4602 WARN(("VBOXESC_CONFIGURETARGETS called without HardwareAccess flag set, failing")); 4593 4603 Status = STATUS_INVALID_PARAMETER; 4594 4604 break; … … 4600 4610 if (!pContext) 4601 4611 { 4602 WARN(("VBOXESC_REINITVIDEOMODES no context supplied!"));4603 Status = STATUS_INVALID_PARAMETER;4604 break;4605 }4606 4607 if (pContext->enmType != VBOXWDDM_CONTEXT_TYPE_CUSTOM_DISPIF_RESIZE)4608 {4609 WARN(("VBOXESC_REINITVIDEOMODES invalid context supplied %d!", pContext->enmType));4610 Status = STATUS_INVALID_PARAMETER;4611 break;4612 }4613 #endif4614 4615 WARN(("VBOXESC_REINITVIDEOMODESBYMASK should be called instead"));4616 VBoxWddmUpdateVideoModesInfoByMask(pDevExt, NULL);4617 Status = STATUS_SUCCESS;4618 break;4619 }4620 case VBOXESC_REINITVIDEOMODESBYMASK:4621 {4622 if (!pEscape->Flags.HardwareAccess)4623 {4624 WARN(("VBOXESC_REINITVIDEOMODESBYMASK called without HardwareAccess flag set, failing"));4625 Status = STATUS_INVALID_PARAMETER;4626 break;4627 }4628 4629 #ifdef VBOX_DISPIF_WITH_OPCONTEXT4630 /* win8.1 does not allow context-based escapes for display-only mode */4631 PVBOXWDDM_CONTEXT pContext = (PVBOXWDDM_CONTEXT)pEscape->hContext;4632 if (!pContext)4633 {4634 WARN(("VBOXESC_REINITVIDEOMODESBYMASK no context supplied!"));4635 Status = STATUS_INVALID_PARAMETER;4636 break;4637 }4638 4639 if (pContext->enmType != VBOXWDDM_CONTEXT_TYPE_CUSTOM_DISPIF_RESIZE)4640 {4641 WARN(("VBOXESC_REINITVIDEOMODESBYMASK invalid context supplied %d!", pContext->enmType));4642 Status = STATUS_INVALID_PARAMETER;4643 break;4644 }4645 #endif4646 4647 if (pEscape->PrivateDriverDataSize != sizeof (VBOXDISPIFESCAPE_REINITVIDEOMODESBYMASK))4648 {4649 WARN(("invalid private driver size %d", pEscape->PrivateDriverDataSize));4650 Status = STATUS_INVALID_PARAMETER;4651 break;4652 }4653 LOG(("=> VBOXESC_REINITVIDEOMODESBYMASK"));4654 PVBOXDISPIFESCAPE_REINITVIDEOMODESBYMASK pData = (PVBOXDISPIFESCAPE_REINITVIDEOMODESBYMASK)pEscapeHdr;4655 VBoxWddmUpdateVideoModesInfoByMask(pDevExt, pData->ScreenMask);4656 Status = STATUS_SUCCESS;4657 LOG(("<= VBOXESC_REINITVIDEOMODESBYMASK"));4658 break;4659 }4660 case VBOXESC_CONFIGURETARGETS:4661 {4662 LOG(("=> VBOXESC_CONFIGURETARGETS"));4663 4664 if (!pEscape->Flags.HardwareAccess)4665 {4666 WARN(("VBOXESC_CONFIGURETARGETS called without HardwareAccess flag set, failing"));4667 Status = STATUS_INVALID_PARAMETER;4668 break;4669 }4670 4671 #ifdef VBOX_DISPIF_WITH_OPCONTEXT4672 /* win8.1 does not allow context-based escapes for display-only mode */4673 PVBOXWDDM_CONTEXT pContext = (PVBOXWDDM_CONTEXT)pEscape->hContext;4674 if (!pContext)4675 {4676 4612 WARN(("VBOXESC_CONFIGURETARGETS no context supplied!")); 4677 4613 Status = STATUS_INVALID_PARAMETER; … … 4715 4651 if (!pTarget->fConnected) 4716 4652 { 4717 Status = vboxWddmChildStatusConnect(pDevExt, (uint32_t)i, TRUE);4653 Status = VBoxWddmChildStatusConnect(pDevExt, (uint32_t)i, TRUE); 4718 4654 if (NT_SUCCESS(Status)) 4719 4655 ++cAdjusted; … … 4755 4691 break; 4756 4692 } 4757 case VBOXESC_ADJUSTVIDEOMODES:4758 {4759 if (!pEscape->Flags.HardwareAccess)4760 {4761 WARN(("VBOXESC_ADJUSTVIDEOMODES called without HardwareAccess flag set, failing"));4762 Status = STATUS_INVALID_PARAMETER;4763 break;4764 }4765 4766 uint32_t cModes = pEscapeHdr->u32CmdSpecific;4767 if (cModes > VBOXWDDM_TRAILARRAY_MAXELEMENTSU32(VBOXDISPIFESCAPE_ADJUSTVIDEOMODES, aScreenInfos)4768 || pEscape->PrivateDriverDataSize != RT_OFFSETOF(VBOXDISPIFESCAPE_ADJUSTVIDEOMODES, aScreenInfos[cModes]))4769 {4770 WARN(("invalid modes count passed"));4771 Status = STATUS_INVALID_PARAMETER;4772 break;4773 }4774 4775 PVBOXDISPIFESCAPE_ADJUSTVIDEOMODES pPodesInfo = (PVBOXDISPIFESCAPE_ADJUSTVIDEOMODES)pEscapeHdr;4776 VBoxWddmAdjustModes(pDevExt, cModes, pPodesInfo->aScreenInfos);4777 Status = STATUS_SUCCESS;4778 break;4779 }4780 4693 case VBOXESC_SETALLOCHOSTID: 4781 4694 { … … 4916 4829 pIsAnyX->u32IsAnyX = VBoxCommonFromDeviceExt(pDevExt)->fAnyX; 4917 4830 Status = STATUS_SUCCESS; 4831 break; 4832 } 4833 case VBOXESC_UPDATEMODES: 4834 { 4835 LOG(("=> VBOXESC_UPDATEMODES")); 4836 4837 if (!pEscape->Flags.HardwareAccess) 4838 { 4839 WARN(("VBOXESC_UPDATEMODES called without HardwareAccess flag set, failing")); 4840 Status = STATUS_INVALID_PARAMETER; 4841 break; 4842 } 4843 4844 #ifdef VBOX_DISPIF_WITH_OPCONTEXT 4845 /* win8.1 does not allow context-based escapes for display-only mode */ 4846 PVBOXWDDM_CONTEXT pContext = (PVBOXWDDM_CONTEXT)pEscape->hContext; 4847 if (!pContext) 4848 { 4849 WARN(("VBOXESC_UPDATEMODES no context supplied!")); 4850 Status = STATUS_INVALID_PARAMETER; 4851 break; 4852 } 4853 4854 if (pContext->enmType != VBOXWDDM_CONTEXT_TYPE_CUSTOM_DISPIF_RESIZE) 4855 { 4856 WARN(("VBOXESC_UPDATEMODES invalid context supplied %d!", pContext->enmType)); 4857 Status = STATUS_INVALID_PARAMETER; 4858 break; 4859 } 4860 #endif 4861 4862 if (pEscape->PrivateDriverDataSize != sizeof (VBOXDISPIFESCAPE_UPDATEMODES)) 4863 { 4864 WARN(("VBOXESC_UPDATEMODES invalid private driver size %d", pEscape->PrivateDriverDataSize)); 4865 Status = STATUS_INVALID_PARAMETER; 4866 break; 4867 } 4868 4869 VBOXDISPIFESCAPE_UPDATEMODES *pData = (VBOXDISPIFESCAPE_UPDATEMODES*)pEscapeHdr; 4870 Status = VBoxVidPnUpdateModes(pDevExt, pData->u32TargetId, &pData->Size); 4871 if (!NT_SUCCESS(Status)) 4872 { 4873 WARN(("VBoxVidPnUpdateModes failed Status(%#x)\n", Status)); 4874 return Status; 4875 } 4876 4918 4877 break; 4919 4878 } … … 5087 5046 vboxVDbgBreakFv(); 5088 5047 5089 NTSTATUS Status = STATUS_SUCCESS;5090 5091 5048 PVBOXMP_DEVEXT pDevExt = (PVBOXMP_DEVEXT)hAdapter; 5092 const DXGK_VIDPN_INTERFACE* pVidPnInterface = NULL; 5093 Status = pDevExt->u.primary.DxgkInterface.DxgkCbQueryVidPnInterface(pIsSupportedVidPnArg->hDesiredVidPn, DXGK_VIDPN_INTERFACE_VERSION_V1, &pVidPnInterface); 5049 NTSTATUS Status = VBoxVidPnIsSupported(pDevExt, pIsSupportedVidPnArg->hDesiredVidPn, &pIsSupportedVidPnArg->IsVidPnSupported); 5094 5050 if (!NT_SUCCESS(Status)) 5095 5051 { 5096 WARN((" DxgkCbQueryVidPnInterface failed Status()0x%x\n", Status));5052 WARN(("VBoxVidPnIsSupported failed Status(%#x)\n", Status)); 5097 5053 return Status; 5098 5054 } 5099 5055 5100 #ifdef VBOXWDDM_DEBUG_VIDPN5101 vboxVidPnDumpVidPn("\n>>>>IS SUPPORTED VidPN : >>>>", pDevExt, pIsSupportedVidPnArg->hDesiredVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<");5102 #endif5103 5104 D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology;5105 const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface;5106 Status = pVidPnInterface->pfnGetTopology(pIsSupportedVidPnArg->hDesiredVidPn, &hVidPnTopology, &pVidPnTopologyInterface);5107 if (!NT_SUCCESS(Status))5108 {5109 WARN(("pfnGetTopology failed Status()0x%x\n", Status));5110 return Status;5111 }5112 5113 BOOLEAN fSupported = FALSE;5114 Status = VBoxVidPnCheckTopology(pDevExt, hVidPnTopology, pVidPnTopologyInterface, &fSupported);5115 if (!NT_SUCCESS(Status))5116 {5117 WARN(("VBoxVidPnCheckTopology failed Status()0x%x\n", Status));5118 return Status;5119 }5120 5121 if (!fSupported)5122 LOG(("found unsupported path"));5123 5124 pIsSupportedVidPnArg->IsVidPnSupported = fSupported;5125 5126 #ifdef VBOXWDDM_DEBUG_VIDPN5127 LOGREL(("The Given VidPn is %ssupported\n", pIsSupportedVidPnArg->IsVidPnSupported ? "" : "!!NOT!! "));5128 #endif5129 5130 5056 LOGF(("LEAVE, status(0x%x), context(0x%x)", Status, hAdapter)); 5131 5057 5132 return S tatus;5058 return STATUS_SUCCESS; 5133 5059 } 5134 5060 … … 5147 5073 vboxVDbgBreakFv(); 5148 5074 5149 #ifdef DEBUG_misha5150 Assert(0);5151 #endif5152 5153 5075 PVBOXMP_DEVEXT pDevExt = (PVBOXMP_DEVEXT)hAdapter; 5154 NTSTATUS Status; 5155 PVBOXWDDM_RECOMMENDVIDPN pVidPnInfo = pRecommendFunctionalVidPnArg->PrivateDriverDataSize >= sizeof (VBOXWDDM_RECOMMENDVIDPN) ? 5156 (PVBOXWDDM_RECOMMENDVIDPN)pRecommendFunctionalVidPnArg->pPrivateDriverData : NULL; 5157 PVBOXWDDM_VIDEOMODES_INFO pInfos = VBoxWddmGetAllVideoModesInfos(pDevExt); 5158 int i; 5159 5160 for (i = 0; i < VBoxCommonFromDeviceExt(pDevExt)->cDisplays; ++i) 5161 { 5162 /* @todo: check that we actually need the current source->target */ 5163 PVBOXWDDM_VIDEOMODES_INFO pInfo = &pInfos[i]; 5164 VIDEO_MODE_INFORMATION *pModeInfo = &pInfo->aModes[pInfo->iPreferredMode]; 5165 #if 0 5166 D3DKMDT_2DREGION Resolution; 5167 Resolution.cx = pModeInfo->VisScreenWidth; 5168 Resolution.cy = pModeInfo->VisScreenHeight; 5169 Status = vboxVidPnCheckAddMonitorModes(pDevExt, i, D3DKMDT_MCO_DRIVER, &Resolution, 1, 0); 5170 #else 5171 Status = vboxVidPnCheckAddMonitorModes(pDevExt, i, D3DKMDT_MCO_DRIVER, pInfo->aResolutions, pInfo->cResolutions, pInfo->iPreferredResolution); 5172 #endif 5173 if (Status != STATUS_SUCCESS) 5174 { 5175 WARN(("vboxVidPnCheckAddMonitorModes failed Status(0x%x)", Status)); 5176 break; 5177 } 5178 } 5179 5180 const DXGK_VIDPN_INTERFACE* pVidPnInterface = NULL; 5181 Status = pDevExt->u.primary.DxgkInterface.DxgkCbQueryVidPnInterface(pRecommendFunctionalVidPnArg->hRecommendedFunctionalVidPn, DXGK_VIDPN_INTERFACE_VERSION_V1, &pVidPnInterface); 5076 5077 if (pRecommendFunctionalVidPnArg->PrivateDriverDataSize != sizeof (VBOXWDDM_RECOMMENDVIDPN)) 5078 { 5079 WARN(("invalid size")); 5080 return STATUS_INVALID_PARAMETER; 5081 } 5082 5083 VBOXWDDM_RECOMMENDVIDPN *pData = (VBOXWDDM_RECOMMENDVIDPN*)pRecommendFunctionalVidPnArg->pPrivateDriverData; 5084 Assert(pData); 5085 5086 NTSTATUS Status = VBoxVidPnRecommendFunctional(pDevExt, pRecommendFunctionalVidPnArg->hRecommendedFunctionalVidPn, pData); 5182 5087 if (!NT_SUCCESS(Status)) 5183 5088 { 5184 WARN((" DxgkCbQueryVidPnInterface failed Status(0x%x)", Status));5089 WARN(("VBoxVidPnRecommendFunctional failed %#x", Status)); 5185 5090 return Status; 5186 5091 } 5187 5092 5188 for (i = 0; i < VBoxCommonFromDeviceExt(pDevExt)->cDisplays; ++i)5189 {5190 Status = vboxVidPnPathAdd(pRecommendFunctionalVidPnArg->hRecommendedFunctionalVidPn, pVidPnInterface, i, i);5191 if (!NT_SUCCESS(Status))5192 {5193 WARN(("vboxVidPnPathAdd failed Status(0x%x)", Status));5194 return Status;5195 }5196 }5197 5198 VIDEO_MODE_INFORMATION *pResModes = NULL;5199 uint32_t cResModes = 0;5200 5201 for (i = 0; i < VBoxCommonFromDeviceExt(pDevExt)->cDisplays; ++i)5202 {5203 D3DKMDT_2DREGION Resolution;5204 PVBOXWDDM_VIDEOMODES_INFO pInfo = &pInfos[i];5205 VIDEO_MODE_INFORMATION *pModeInfo = &pInfo->aModes[pInfo->iPreferredMode];5206 Resolution.cx = pModeInfo->VisScreenWidth;5207 Resolution.cy = pModeInfo->VisScreenHeight;5208 int32_t iPreferableResMode;5209 uint32_t cActualResModes;5210 5211 Status = VBoxWddmGetModesForResolution(pInfo->aModes, pInfo->cModes, pInfo->iPreferredMode, &Resolution,5212 pResModes, cResModes, &cActualResModes, &iPreferableResMode);5213 Assert(Status == STATUS_SUCCESS || Status == STATUS_BUFFER_TOO_SMALL);5214 if (Status == STATUS_BUFFER_TOO_SMALL)5215 {5216 Assert(cResModes < cActualResModes);5217 if (pResModes)5218 {5219 vboxWddmMemFree(pResModes);5220 }5221 pResModes = (VIDEO_MODE_INFORMATION*)vboxWddmMemAllocZero(sizeof (*pResModes) * cActualResModes);5222 Assert(pResModes);5223 if (!pResModes)5224 {5225 Status = STATUS_NO_MEMORY;5226 break;5227 }5228 cResModes = cActualResModes;5229 Status = VBoxWddmGetModesForResolution(pInfo->aModes, pInfo->cModes, pInfo->iPreferredMode, &Resolution,5230 pResModes, cResModes, &cActualResModes, &iPreferableResMode);5231 Assert(Status == STATUS_SUCCESS);5232 if (Status != STATUS_SUCCESS)5233 break;5234 }5235 else if (Status != STATUS_SUCCESS)5236 break;5237 5238 Assert(iPreferableResMode >= 0);5239 Assert(cActualResModes);5240 5241 Status = vboxVidPnCreatePopulateVidPnPathFromLegacy(pDevExt, pRecommendFunctionalVidPnArg->hRecommendedFunctionalVidPn, pVidPnInterface,5242 pResModes, cActualResModes, iPreferableResMode,5243 &Resolution, 1 /* cResolutions */,5244 i, i); /* srcId, tgtId */5245 Assert(Status == STATUS_SUCCESS);5246 if (Status != STATUS_SUCCESS)5247 {5248 LOGREL(("vboxVidPnCreatePopulateVidPnFromLegacy failed Status(0x%x)", Status));5249 break;5250 }5251 }5252 5253 if(pResModes)5254 vboxWddmMemFree(pResModes);5255 5256 #ifdef VBOXWDDM_DEBUG_VIDPN5257 vboxVidPnDumpVidPn("\n>>>>Recommended VidPN: >>>>", pDevExt, pRecommendFunctionalVidPnArg->hRecommendedFunctionalVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<\n");5258 #endif5259 5260 5093 LOGF(("LEAVE, status(0x%x), context(0x%x)", Status, hAdapter)); 5261 5094 5262 return S tatus;5095 return STATUS_SUCCESS; 5263 5096 } 5264 5097 … … 5278 5111 5279 5112 PVBOXMP_DEVEXT pDevExt = (PVBOXMP_DEVEXT)hAdapter; 5280 const DXGK_VIDPN_INTERFACE* pVidPnInterface = NULL; 5281 NTSTATUS Status = pDevExt->u.primary.DxgkInterface.DxgkCbQueryVidPnInterface(pEnumCofuncModalityArg->hConstrainingVidPn, DXGK_VIDPN_INTERFACE_VERSION_V1, &pVidPnInterface);5113 5114 NTSTATUS Status = VBoxVidPnCofuncModality(pDevExt, pEnumCofuncModalityArg->hConstrainingVidPn, pEnumCofuncModalityArg->EnumPivotType, &pEnumCofuncModalityArg->EnumPivot); 5282 5115 if (!NT_SUCCESS(Status)) 5283 5116 { 5284 WARN((" DxgkCbQueryVidPnInterface failed Status()0x%x\n", Status));5117 WARN(("VBoxVidPnCofuncModality failed Status(%#x)\n", Status)); 5285 5118 return Status; 5286 5119 } 5287 #ifdef VBOXWDDM_DEBUG_VIDPN5288 vboxVidPnDumpCofuncModalityArg(">>>>MODALITY Args: ", pEnumCofuncModalityArg, "\n");5289 vboxVidPnDumpVidPn(">>>>MODALITY VidPN (IN) : >>>>\n", pDevExt, pEnumCofuncModalityArg->hConstrainingVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<\n");5290 #endif5291 5292 D3DKMDT_HVIDPNTOPOLOGY hVidPnTopology;5293 const DXGK_VIDPNTOPOLOGY_INTERFACE* pVidPnTopologyInterface;5294 Status = pVidPnInterface->pfnGetTopology(pEnumCofuncModalityArg->hConstrainingVidPn, &hVidPnTopology, &pVidPnTopologyInterface);5295 Assert(Status == STATUS_SUCCESS);5296 if (!NT_SUCCESS(Status))5297 {5298 WARN(("pfnGetTopology failed Status()0x%x\n", Status));5299 return Status;5300 }5301 5302 #ifdef DEBUG_misha5303 {5304 BOOLEAN fSupported = FALSE;5305 Status = VBoxVidPnCheckTopology(pDevExt, hVidPnTopology, pVidPnTopologyInterface, &fSupported);5306 if (!NT_SUCCESS(Status))5307 WARN(("VBoxVidPnCheckTopology failed Status()0x%x\n", Status));5308 5309 Assert(fSupported);5310 }5311 #endif5312 VBOXVIDPNCOFUNCMODALITY CbContext = {0};5313 CbContext.pDevExt = pDevExt;5314 CbContext.pVidPnInterface = pVidPnInterface;5315 CbContext.pEnumCofuncModalityArg = pEnumCofuncModalityArg;5316 CbContext.pInfos = VBoxWddmGetAllVideoModesInfos(pDevExt);5317 5318 Status = vboxVidPnEnumPaths(hVidPnTopology, pVidPnTopologyInterface,5319 vboxVidPnCofuncModalityPathEnum, &CbContext);5320 if (!NT_SUCCESS(Status))5321 {5322 WARN(("vboxVidPnEnumPaths failed Status()0x%x\n", Status));5323 return Status;5324 }5325 5326 Status = CbContext.Status;5327 if (!NT_SUCCESS(Status))5328 {5329 WARN(("vboxVidPnCofuncModalityPathEnum failed Status()0x%x\n", Status));5330 return Status;5331 }5332 5333 #ifdef VBOXWDDM_DEBUG_VIDPN5334 vboxVidPnDumpVidPn("\n>>>>MODALITY VidPN (OUT) : >>>>\n", pDevExt, pEnumCofuncModalityArg->hConstrainingVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<\n\n");5335 #endif5336 5120 5337 5121 LOGF(("LEAVE, status(0x%x), context(0x%x)", Status, hAdapter)); 5338 5122 5339 return S tatus;5123 return STATUS_SUCCESS; 5340 5124 } 5341 5125 … … 5361 5145 POINT Pos; 5362 5146 Status= vboxWddmDisplaySettingsQueryPos(pDevExt, pSetVidPnSourceAddress->VidPnSourceId, &Pos); 5363 Assert(Status == STATUS_SUCCESS);5147 //Assert(Status == STATUS_SUCCESS); 5364 5148 if (NT_SUCCESS(Status)) 5365 5149 { … … 5445 5229 POINT Pos; 5446 5230 Status= vboxWddmDisplaySettingsQueryPos(pDevExt, pSetVidPnSourceVisibility->VidPnSourceId, &Pos); 5447 Assert(Status == STATUS_SUCCESS);5231 //Assert(Status == STATUS_SUCCESS); 5448 5232 if (NT_SUCCESS(Status)) 5449 5233 { … … 5602 5386 5603 5387 PVBOXMP_DEVEXT pDevExt = (PVBOXMP_DEVEXT)hAdapter; 5604 NTSTATUS Status; 5605 PVBOXWDDM_VIDEOMODES_INFO pInfo = VBoxWddmGetVideoModesInfo(pDevExt, pRecommendMonitorModesArg->VideoPresentTargetId); 5606 PVIDEO_MODE_INFORMATION pPreferredMode = &pInfo->aModes[pInfo->iPreferredMode]; 5607 5608 5609 for (uint32_t i = 0; i < pInfo->cResolutions; i++) 5610 { 5611 D3DKMDT_MONITOR_SOURCE_MODE * pNewMonitorSourceModeInfo; 5612 Status = pRecommendMonitorModesArg->pMonitorSourceModeSetInterface->pfnCreateNewModeInfo( 5613 pRecommendMonitorModesArg->hMonitorSourceModeSet, &pNewMonitorSourceModeInfo); 5614 Assert(Status == STATUS_SUCCESS); 5615 if (Status == STATUS_SUCCESS) 5616 { 5617 Status = vboxVidPnPopulateMonitorSourceModeInfoFromLegacy(pDevExt, 5618 pNewMonitorSourceModeInfo, 5619 &pInfo->aResolutions[i], 5620 D3DKMDT_MCO_DRIVER, 5621 pPreferredMode->VisScreenWidth == pInfo->aResolutions[i].cx 5622 && pPreferredMode->VisScreenHeight == pInfo->aResolutions[i].cy); 5623 Assert(Status == STATUS_SUCCESS); 5624 if (Status == STATUS_SUCCESS) 5625 { 5626 Status = pRecommendMonitorModesArg->pMonitorSourceModeSetInterface->pfnAddMode( 5627 pRecommendMonitorModesArg->hMonitorSourceModeSet, pNewMonitorSourceModeInfo); 5628 Assert(Status == STATUS_SUCCESS); 5629 if (Status == STATUS_SUCCESS) 5630 continue; 5631 } 5632 5633 /* error has occurred, release & break */ 5634 pRecommendMonitorModesArg->pMonitorSourceModeSetInterface->pfnReleaseModeInfo( 5635 pRecommendMonitorModesArg->hMonitorSourceModeSet, pNewMonitorSourceModeInfo); 5636 break; 5637 } 5388 5389 NTSTATUS Status = VBoxVidPnRecommendMonitorModes(pDevExt, pRecommendMonitorModesArg->VideoPresentTargetId, 5390 pRecommendMonitorModesArg->hMonitorSourceModeSet, pRecommendMonitorModesArg->pMonitorSourceModeSetInterface); 5391 if (!NT_SUCCESS(Status)) 5392 { 5393 WARN(("VBoxVidPnRecommendMonitorModes failed %#x", Status)); 5394 return Status; 5638 5395 } 5639 5396 5640 5397 LOGF(("LEAVE, hAdapter(0x%x)", hAdapter)); 5641 5398 5642 return S tatus;5399 return STATUS_SUCCESS; 5643 5400 } 5644 5401 … … 5670 5427 5671 5428 #ifdef DEBUG_misha 5672 RT_BREAKPOINT();5429 // RT_BREAKPOINT(); 5673 5430 #endif 5674 5431 … … 6991 6748 pDevExt->aSources[i].u8SyncState = 0; 6992 6749 NTSTATUS tmpStatus= vboxWddmDisplaySettingsQueryPos(pDevExt, i, &pDevExt->aSources[i].VScreenPos); 6993 Assert(tmpStatus == STATUS_SUCCESS);6750 //Assert(tmpStatus == STATUS_SUCCESS); 6994 6751 } 6995 6752 #ifdef VBOX_WITH_CROGL … … 7207 6964 Assert(cContexts < UINT32_MAX/2); 7208 6965 if (!cContexts) 7209 vboxWddmGhDisplayCheckSetInfoEx(pDevExt, true); 6966 { 6967 if (pDevExt->fDisableTargetUpdate) 6968 { 6969 pDevExt->fDisableTargetUpdate = FALSE; 6970 vboxWddmGhDisplayCheckSetInfoEx(pDevExt, true); 6971 } 6972 } 7210 6973 break; 7211 6974 }
Note:
See TracChangeset
for help on using the changeset viewer.