Index: /trunk/src/VBox/Runtime/r0drv/nt/initterm-r0drv-nt.cpp
===================================================================
--- /trunk/src/VBox/Runtime/r0drv/nt/initterm-r0drv-nt.cpp	(revision 24033)
+++ /trunk/src/VBox/Runtime/r0drv/nt/initterm-r0drv-nt.cpp	(revision 24034)
@@ -54,10 +54,15 @@
 
 /** ExSetTimerResolution, introduced in W2K. */
-PFNMYEXSETTIMERRESOLUTION       g_pfnrtNtExSetTimerResolution;
+PFNMYEXSETTIMERRESOLUTION   g_pfnrtNtExSetTimerResolution;
 /** KeFlushQueuedDpcs, introduced in XP. */
-PFNMYKEFLUSHQUEUEDDPCS          g_pfnrtNtKeFlushQueuedDpcs;
-/** KeSetSystemAffinityThread - Windows 2000+ */
-PFNRTKESETSYSTEMAFFINITYTHREAD  g_pfnrtKeSetSystemAffinityThread;
-
+PFNMYKEFLUSHQUEUEDDPCS      g_pfnrtNtKeFlushQueuedDpcs;
+/** HalRequestIpi, introduced in ??. */
+PFNHALREQUESTIPI            g_pfnrtNtHalRequestIpi;
+/** HalSendSoftwareInterrupt */
+PFNHALSENDSOFTWAREINTERRUPT g_pfnrtNtHalSendSoftwareInterrupt;
+/** SendIpi handler based on Windows version */
+PFNRTSENDIPI                g_pfnrtSendIpi;
+/** KeIpiGenericCall - Windows Server 2003+ only */
+PFNRTKEIPIGENERICCALL       g_pfnrtKeIpiGenericCall;
 
 /** Offset of the _KPRCB::QuantumEnd field. 0 if not found. */
@@ -86,5 +91,7 @@
     g_pfnrtNtExSetTimerResolution = NULL;
     g_pfnrtNtKeFlushQueuedDpcs = NULL;
-	g_pfnrtKeSetSystemAffinityThread = NULL;
+    g_pfnrtNtHalRequestIpi = NULL;
+    g_pfnrtNtHalSendSoftwareInterrupt = NULL;
+    g_pfnrtKeIpiGenericCall = NULL;
 #else
     /*
@@ -98,6 +105,12 @@
     g_pfnrtNtKeFlushQueuedDpcs = (PFNMYKEFLUSHQUEUEDDPCS)MmGetSystemRoutineAddress(&RoutineName);
 
-    RtlInitUnicodeString(&RoutineName, L"KeSetSystemAffinityThread");
-    g_pfnrtKeSetSystemAffinityThread = (PFNRTKESETSYSTEMAFFINITYTHREAD)MmGetSystemRoutineAddress(&RoutineName);
+    RtlInitUnicodeString(&RoutineName, L"HalRequestIpi");
+    g_pfnrtNtHalRequestIpi = (PFNHALREQUESTIPI)MmGetSystemRoutineAddress(&RoutineName);
+
+    RtlInitUnicodeString(&RoutineName, L"HalSendSoftwareInterrupt");
+    g_pfnrtNtHalSendSoftwareInterrupt = (PFNHALSENDSOFTWAREINTERRUPT)MmGetSystemRoutineAddress(&RoutineName);
+
+    RtlInitUnicodeString(&RoutineName, L"KeIpiGenericCall");
+    g_pfnrtKeIpiGenericCall = (PFNRTKEIPIGENERICCALL)MmGetSystemRoutineAddress(&RoutineName);
 #endif
 
@@ -110,4 +123,23 @@
     BOOLEAN fChecked = PsGetVersion(&MajorVersion, &MinorVersion, &BuildNumber, NULL);
 
+    g_pfnrtSendIpi = rtMpSendIpiDummy;
+#ifndef IPRT_TARGET_NT4
+    if (    g_pfnrtNtHalRequestIpi
+        &&  MajorVersion == 6
+        &&  MinorVersion == 0)
+    {
+        /* Vista or Windows Server 2008 */
+        g_pfnrtSendIpi = rtMpSendIpiVista;
+    }
+    else
+    if (    g_pfnrtNtHalSendSoftwareInterrupt
+        &&  MajorVersion == 6
+        &&  MinorVersion == 1)
+    {
+        /* Windows 7 or Windows Server 2008 R2 */
+        g_pfnrtSendIpi = rtMpSendIpiWin7;
+    }
+    /* Windows XP should send always send an IPI -> VERIFY */
+#endif
     KIRQL OldIrql;
     KeRaiseIrql(DISPATCH_LEVEL, &OldIrql); /* make sure we stay on the same cpu */
Index: /trunk/src/VBox/Runtime/r0drv/nt/internal-r0drv-nt.h
===================================================================
--- /trunk/src/VBox/Runtime/r0drv/nt/internal-r0drv-nt.h	(revision 24033)
+++ /trunk/src/VBox/Runtime/r0drv/nt/internal-r0drv-nt.h	(revision 24034)
@@ -41,5 +41,8 @@
 typedef ULONG (__stdcall *PFNMYEXSETTIMERRESOLUTION)(ULONG, BOOLEAN);
 typedef VOID (__stdcall *PFNMYKEFLUSHQUEUEDDPCS)(VOID);
-typedef VOID (__stdcall *PFNRTKESETSYSTEMAFFINITYTHREAD)(KAFFINITY);
+typedef VOID (__stdcall *PFNHALREQUESTIPI)(KAFFINITY TargetSet);
+typedef VOID (__stdcall *PFNHALSENDSOFTWAREINTERRUPT)(ULONG ProcessorNumber, KIRQL Irql);
+typedef int (__stdcall *PFNRTSENDIPI)(RTCPUID idCpu);
+typedef ULONG_PTR (__stdcall *PFNRTKEIPIGENERICCALL)(PKIPI_BROADCAST_WORKER BroadcastFunction, ULONG_PTR  Context);
 
 /*******************************************************************************
@@ -49,8 +52,16 @@
 extern PFNMYEXSETTIMERRESOLUTION    g_pfnrtNtExSetTimerResolution;
 extern PFNMYKEFLUSHQUEUEDDPCS       g_pfnrtNtKeFlushQueuedDpcs;
-extern PFNRTKESETSYSTEMAFFINITYTHREAD g_pfnrtKeSetSystemAffinityThread;
+extern PFNHALREQUESTIPI             g_pfnrtNtHalRequestIpi;
+extern PFNHALSENDSOFTWAREINTERRUPT  g_pfnrtNtHalSendSoftwareInterrupt;
+extern PFNRTSENDIPI                 g_pfnrtSendIpi;
+extern PFNRTKEIPIGENERICCALL        g_pfnrtKeIpiGenericCall;
 extern uint32_t                     g_offrtNtPbQuantumEnd;
 extern uint32_t                     g_cbrtNtPbQuantumEnd;
 extern uint32_t                     g_offrtNtPbDpcQueueDepth;
+
+
+int rtMpSendIpiVista(RTCPUID idCpu);
+int rtMpSendIpiWin7(RTCPUID idCpu);
+int rtMpSendIpiDummy(RTCPUID idCpu);
 
 RT_C_DECLS_END
Index: /trunk/src/VBox/Runtime/r0drv/nt/mp-r0drv-nt.cpp
===================================================================
--- /trunk/src/VBox/Runtime/r0drv/nt/mp-r0drv-nt.cpp	(revision 24033)
+++ /trunk/src/VBox/Runtime/r0drv/nt/mp-r0drv-nt.cpp	(revision 24034)
@@ -347,4 +347,31 @@
 }
 
+#ifndef IPRT_TARGET_NT4
+
+ULONG_PTR rtMpIpiGenericCall(ULONG_PTR  Argument)
+{
+    return 0;
+}
+
+int rtMpSendIpiVista(RTCPUID idCpu)
+{
+    g_pfnrtKeIpiGenericCall(rtMpIpiGenericCall, 0);
+////    g_pfnrtNtHalRequestIpi(1 << idCpu);
+    return VINF_SUCCESS;
+}
+
+int rtMpSendIpiWin7(RTCPUID idCpu)
+{
+    g_pfnrtKeIpiGenericCall(rtMpIpiGenericCall, 0);
+////    g_pfnrtNtHalSendSoftwareInterrupt(idCpu, DISPATCH_LEVEL);
+    return VINF_SUCCESS;
+}
+#endif /* IPRT_TARGET_NT4 */
+
+int rtMpSendIpiDummy(RTCPUID idCpu)
+{
+    return VERR_NOT_IMPLEMENTED;
+}
+
 RTDECL(int) RTMpPokeCpu(RTCPUID idCpu)
 {
@@ -353,4 +380,8 @@
               ? VERR_CPU_NOT_FOUND
               : VERR_CPU_OFFLINE;
+
+    int rc = g_pfnrtSendIpi(idCpu);
+    if (rc == VINF_SUCCESS)
+        return rc;
 
     /* Fallback. */
@@ -376,5 +407,5 @@
 
     /* Assuming here that high importance DPCs will be delivered immediately; or at least an IPI will be sent immediately.
-     * @note: seems to be true on Vista
+     * @note: not true on at least Vista & Windows 7
      */
     BOOLEAN bRet = KeInsertQueueDpc(&aPokeDpcs[idCpu], 0, 0);
Index: /trunk/src/VBox/Runtime/r0drv/nt/thread-r0drv-nt.cpp
===================================================================
--- /trunk/src/VBox/Runtime/r0drv/nt/thread-r0drv-nt.cpp	(revision 24033)
+++ /trunk/src/VBox/Runtime/r0drv/nt/thread-r0drv-nt.cpp	(revision 24034)
@@ -170,10 +170,5 @@
     Assert(KeGetCurrentIrql() <= DISPATCH_LEVEL);
 
-#ifndef IPRT_TARGET_NT4
-    Assert(g_pfnrtKeSetSystemAffinityThread);
-    g_pfnrtKeSetSystemAffinityThread((KAFFINITY)1 << KeGetCurrentProcessorNumber());
-#else
     KeRaiseIrql(DISPATCH_LEVEL, &pState->uchOldIrql);
-#endif
     RT_ASSERT_PREEMPT_CPUID_DISABLE(pState);
 }
@@ -185,10 +180,5 @@
 
     RT_ASSERT_PREEMPT_CPUID_RESTORE(pState);
-#ifndef IPRT_TARGET_NT4
-    Assert(g_pfnrtKeSetSystemAffinityThread);
-    g_pfnrtKeSetSystemAffinityThread(KeQueryActiveProcessors());
-#else
     KeLowerIrql(pState->uchOldIrql);
-#endif
     pState->uchOldIrql = 255;
 }
