Index: /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.cpp
===================================================================
--- /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.cpp	(revision 61547)
+++ /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.cpp	(revision 61548)
@@ -20,4 +20,7 @@
 #include "VBoxMPVidPn.h"
 #include "common/VBoxMPCommon.h"
+
+
+static NTSTATUS vboxVidPnCheckMonitorModes(PVBOXMP_DEVEXT pDevExt, uint32_t u32Target, const CR_SORTARRAY *pSupportedTargetModes = NULL);
 
 static D3DDDIFORMAT vboxWddmCalcPixelFormat(const VIDEO_MODE_INFORMATION *pInfo)
@@ -658,9 +661,11 @@
         if (!NT_SUCCESS(Status))
         {
-            WARN(("pfnAddMode failed, Status 0x%x", Status));
+            WARN(("pfnAddMode (%d x %d) failed, Status 0x%x", size.cx, size.cy, Status));
             NTSTATUS tmpStatus = pVidPnModeSetInterface->pfnReleaseModeInfo(hVidPnModeSet, pVidPnModeInfo);
             Assert(tmpStatus == STATUS_SUCCESS);
-            return Status;
-        }
+            continue;
+        }
+
+        LOGF(("mode (%d x %d) added to monitor modeset", size.cx, size.cy));
     }
 
@@ -882,4 +887,12 @@
         return Status;
     }
+    
+    Status = vboxVidPnCheckMonitorModes(pDevExt, VidPnTargetId, &aModes[VidPnTargetId]);
+
+    if (!NT_SUCCESS(Status))
+    {
+        WARN(("vboxVidPnCheckMonitorModes failed, Status(0x%x)", Status));
+        return Status;
+    }
 
     return STATUS_SUCCESS;
@@ -1110,5 +1123,5 @@
 }
 
-static NTSTATUS vboxVidPnCheckMonitorModes(PVBOXMP_DEVEXT pDevExt, uint32_t u32Target)
+static NTSTATUS vboxVidPnCheckMonitorModes(PVBOXMP_DEVEXT pDevExt, uint32_t u32Target, const CR_SORTARRAY *pSupportedModes)
 {
     NTSTATUS Status;
@@ -1124,5 +1137,9 @@
     CONST DXGK_MONITORSOURCEMODESET_INTERFACE *pVidPnModeSetInterface;
 
-    const CR_SORTARRAY *pSupportedModes = VBoxWddmVModesGet(pDevExt, u32Target);
+    if (!pSupportedModes)
+    {
+        pSupportedModes = VBoxWddmVModesGet(pDevExt, u32Target);
+    }
+
     CR_SORTARRAY DiffModes;
     int rc = CrSaInit(&DiffModes, CrSaGetSize(pSupportedModes));
@@ -1165,4 +1182,5 @@
         size.cy = pVidPnModeInfo->VideoSignalInfo.ActiveSize.cy;
         CrSaRemove(&DiffModes, CR_RSIZE2U64(size));
+        LOG(("mode (%d x %d) is already in monitor modeset\n", size.cx, size.cy));
     }
 
@@ -1175,4 +1193,6 @@
         goto done;
     }
+
+    LOG(("Adding %d additional modes to monitor modeset\n", CrSaGetSize(&DiffModes)));
 
     Status = vboxVidPnMonitorModeSetFromArray(hVidPnModeSet, pVidPnModeSetInterface, &DiffModes);
@@ -1276,4 +1296,6 @@
 NTSTATUS VBoxVidPnUpdateModes(PVBOXMP_DEVEXT pDevExt, uint32_t u32TargetId, const RTRECTSIZE *pSize)
 {
+    LOGF(("ENTER u32TargetId(%d) mode(%d x %d)", u32TargetId, pSize->cx, pSize->cy));
+
     if (u32TargetId >= (uint32_t)VBoxCommonFromDeviceExt(pDevExt)->cDisplays)
     {
@@ -1283,4 +1305,6 @@
 
     int rc = VBoxWddmVModesAdd(pDevExt, u32TargetId, pSize, TRUE);
+    LOGF(("VBoxWddmVModesAdd returned (%d)", rc));
+
     if (RT_FAILURE(rc))
     {
@@ -1293,9 +1317,15 @@
         /* mode was already in list, just return */
         Assert(CrSaContains(VBoxWddmVModesGet(pDevExt, u32TargetId), CR_RSIZE2U64(*pSize)));
+        LOGF(("LEAVE mode was already in modeset, just return"));
         return STATUS_SUCCESS;
     }
 
     /* modes have changed, need to replug */
+/*  The VBOXESC_UPDATEMODES is a hint for VBoxVideoW8.sys to use new display mode as soon as VidPn manager will ask for it.
+    Probably, some new interface is required to plug/unplug displays by calling VBoxWddmChildStatusReportReconnected.
+    But it is a bad idea to mix sending a display mode hint and (un)plug displays in VBOXESC_UPDATEMODES.
+
     NTSTATUS Status = VBoxWddmChildStatusReportReconnected(pDevExt, u32TargetId);
+    LOG(("VBoxWddmChildStatusReportReconnected returned (%d)", Status));
     if (!NT_SUCCESS(Status))
     {
@@ -1303,5 +1333,6 @@
         return Status;
     }
-
+*/
+    LOGF(("LEAVE u32TargetId(%d)", u32TargetId));
     return STATUS_SUCCESS;
 }
@@ -1734,6 +1765,6 @@
 
 #ifdef VBOXWDDM_DEBUG_VIDPN
-    vboxVidPnDumpCofuncModalityArg(">>>>MODALITY Args: ", pEnumCofuncModalityArg, "\n");
-    vboxVidPnDumpVidPn(">>>>MODALITY VidPN (IN) : >>>>\n", pDevExt, pEnumCofuncModalityArg->hConstrainingVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<\n");
+    vboxVidPnDumpCofuncModalityArg(">>>>MODALITY Args: ", enmPivot, pPivot, "\n");
+    vboxVidPnDumpVidPn(">>>>MODALITY VidPN (IN) : >>>>\n", pDevExt, hVidPn, pVidPnInterface, "<<<<<<<<<<<<<<<<<<<<\n");
 #endif
 
@@ -3042,8 +3073,8 @@
 }
 
-void vboxVidPnDumpCofuncModalityArg(const char *pPrefix, CONST DXGKARG_ENUMVIDPNCOFUNCMODALITY* CONST  pEnumCofuncModalityArg, const char *pSuffix)
-{
-    LOGREL_EXACT(("%sPivotType(%s), SourceId(0x%x), TargetId(0x%x),%s", pPrefix, vboxVidPnDumpStrCFMPivotType(pEnumCofuncModalityArg->EnumPivotType),
-            pEnumCofuncModalityArg->EnumPivot.VidPnSourceId, pEnumCofuncModalityArg->EnumPivot.VidPnTargetId, pSuffix));
+void vboxVidPnDumpCofuncModalityArg(const char *pPrefix, D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmPivot, const DXGK_ENUM_PIVOT *pPivot, const char *pSuffix)
+{
+    LOGREL_EXACT(("%sPivotType(%s), SourceId(0x%x), TargetId(0x%x),%s", pPrefix, vboxVidPnDumpStrCFMPivotType(enmPivot),
+            pPivot->VidPnSourceId, pPivot->VidPnTargetId, pSuffix));
 }
 
Index: /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.h
===================================================================
--- /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.h	(revision 61547)
+++ /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPVidPn.h	(revision 61548)
@@ -103,5 +103,5 @@
 
 void vboxVidPnDumpVidPn(const char * pPrefix, PVBOXMP_DEVEXT pDevExt, D3DKMDT_HVIDPN hVidPn, const DXGK_VIDPN_INTERFACE* pVidPnInterface, const char * pSuffix);
-void vboxVidPnDumpCofuncModalityArg(const char *pPrefix, CONST DXGKARG_ENUMVIDPNCOFUNCMODALITY* CONST  pEnumCofuncModalityArg, const char *pSuffix);
+void vboxVidPnDumpCofuncModalityArg(const char *pPrefix, D3DKMDT_ENUMCOFUNCMODALITY_PIVOT_TYPE enmPivot, const DXGK_ENUM_PIVOT *pPivot, const char *pSuffix);
 DECLCALLBACK(BOOLEAN) vboxVidPnDumpSourceModeSetEnum(D3DKMDT_HVIDPNSOURCEMODESET hNewVidPnSourceModeSet, const DXGK_VIDPNSOURCEMODESET_INTERFACE *pVidPnSourceModeSetInterface,
         const D3DKMDT_VIDPN_SOURCE_MODE *pNewVidPnSourceModeInfo, PVOID pContext);
Index: /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPWddm.cpp
===================================================================
--- /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPWddm.cpp	(revision 61547)
+++ /trunk/src/VBox/Additions/WINNT/Graphics/Video/mp/wddm/VBoxMPWddm.cpp	(revision 61548)
@@ -5081,5 +5081,5 @@
     }
 
-    LOGF(("LEAVE, status(0x%x), context(0x%x)", Status, hAdapter));
+    LOGF(("LEAVE, isSupported(%d), context(0x%x)", pIsSupportedVidPnArg->IsVidPnSupported, hAdapter));
 
     return STATUS_SUCCESS;
Index: /trunk/src/VBox/Additions/WINNT/VBoxTray/VBoxDispIf.cpp
===================================================================
--- /trunk/src/VBox/Additions/WINNT/VBoxTray/VBoxDispIf.cpp	(revision 61547)
+++ /trunk/src/VBox/Additions/WINNT/VBoxTray/VBoxDispIf.cpp	(revision 61548)
@@ -1341,8 +1341,9 @@
     }
 
+/*  The code below was commented out because VBOXESC_UPDATEMODES should not cause (un)plugging virtual displays.
     winEr =  vboxDispIfWaitDisplayDataInited(pOp);
     if (winEr != NO_ERROR)
         WARN(("VBoxTray: (WDDM) Failed vboxDispIfWaitDisplayDataInited winEr %d\n", winEr));
-
+*/
     return winEr;
 }
@@ -1379,5 +1380,7 @@
 static DWORD vboxDispIfResizePerform(PCVBOXDISPIF const pIf, UINT iChangedMode, BOOL fEnable, BOOL fExtDispSup, DISPLAY_DEVICE *paDisplayDevices, DEVMODE *paDeviceModes, UINT cDevModes)
 {
+    LogFunc((" ENTER"));
     DWORD winEr;
+
     if (pIf->enmMode > VBOXDISPIF_MODE_WDDM)
     {
@@ -1392,4 +1395,6 @@
             WARN(("VBoxTray: (WDDM) Failed vboxDispIfWddmResizeDisplayVista winEr %d\n", winEr));
     }
+
+    LogFunc((" LEAVE"));
     return winEr;
 }
@@ -1399,5 +1404,5 @@
     DWORD winEr = NO_ERROR;
 
-    Log(("VBoxTray: vboxDispIfResizeModesWDDM iChanged %d cDevModes %d\n", iChangedMode, cDevModes));
+    Log(("VBoxTray: vboxDispIfResizeModesWDDM iChanged %d cDevModes %d fEnable %d fExtDispSup %d\n", iChangedMode, cDevModes, fEnable, fExtDispSup));
     VBoxRrRetryStop();
 
@@ -1430,12 +1435,19 @@
     }
 
-    D3DKMT_INVALIDATEACTIVEVIDPN DdiData = {0};
-
-    DdiData.hAdapter = Op.Adapter.hAdapter;
-    DdiData.pPrivateDriverData = &VidPnData;
-    DdiData.PrivateDriverDataSize = sizeof (VidPnData);
-
-    NTSTATUS Status = Op.pIf->modeData.wddm.KmtCallbacks.pfnD3DKMTInvalidateActiveVidPn(&DdiData);
-    LogFunc(("InvalidateActiveVidPn 0x%08x\n", Status));
+/*  The pfnD3DKMTInvalidateActiveVidPn was deprecated since Win7 and causes deadlocks since Win10 TH2.
+    Instead, the VidPn Manager can replace an old VidPn as soon as SetDisplayConfig or ChangeDisplaySettingsEx will try to set a new display mode.
+    On Vista D3DKMTInvalidateActiveVidPn is still required. TBD: Get rid of it. */  
+    if (Op.pIf->enmMode < VBOXDISPIF_MODE_WDDM_W7)
+    {
+        D3DKMT_INVALIDATEACTIVEVIDPN DdiData = {0};
+
+        DdiData.hAdapter = Op.Adapter.hAdapter;
+        DdiData.pPrivateDriverData = &VidPnData;
+        DdiData.PrivateDriverDataSize = sizeof (VidPnData);
+
+        NTSTATUS Status;
+        Status = Op.pIf->modeData.wddm.KmtCallbacks.pfnD3DKMTInvalidateActiveVidPn(&DdiData);
+        LogFunc(("D3DKMTInvalidateActiveVidPn returned %d)\n", Status));
+    }
 
     /* Resize displays always to keep the display layout because
@@ -1451,5 +1463,8 @@
             Size.cx = paDeviceModes[iChangedMode].dmPelsWidth;
             Size.cy = paDeviceModes[iChangedMode].dmPelsHeight;
+            LogFunc(("Calling vboxDispIfUpdateModesWDDM to change target %d mode to (%d x %d)\n", iChangedMode, Size.cx, Size.cy));
             winEr = vboxDispIfUpdateModesWDDM(&Op, iChangedMode, &Size);
+            LogFunc(("vboxDispIfUpdateModesWDDM returned %d\n", winEr));
+
             if (winEr != NO_ERROR)
                 WARN(("vboxDispIfUpdateModesWDDM failed %d\n", winEr));
@@ -1460,8 +1475,10 @@
             winEr = vboxDispIfResizePerform(pIf, i, fEnable, fExtDispSup, paDisplayDevices, paDeviceModes, cDevModes);
 
+            LogFunc(("vboxDispIfResizePerform returned %d\n", winEr));
+
             if (winEr == ERROR_RETRY)
             {
                 VBoxRrRetrySchedule(pIf, i, fEnable, fExtDispSup, paDisplayDevices, paDeviceModes, cDevModes);
-                /* just pretend everything is fine so far */
+
                 winEr = NO_ERROR;
             }
