Index: trunk/src/VBox/VMM/VMMR0/HMSVMR0.cpp
===================================================================
--- trunk/src/VBox/VMM/VMMR0/HMSVMR0.cpp	(revision 72786)
+++ trunk/src/VBox/VMM/VMMR0/HMSVMR0.cpp	(revision 72805)
@@ -73,5 +73,4 @@
 # endif
 #endif /* !VBOX_WITH_STATISTICS */
-
 
 /** If we decide to use a function table approach this can be useful to
@@ -528,5 +527,5 @@
  *
  * @returns VBox status code.
- * @param   pCpu            Pointer to the CPU info struct.
+ * @param   pHostCpu        Pointer to the CPU info struct.
  * @param   pVM             The cross context VM structure. Can be
  *                          NULL after a resume!
@@ -536,5 +535,5 @@
  * @param   pvArg           Unused on AMD-V.
  */
-VMMR0DECL(int) SVMR0EnableCpu(PHMGLOBALCPUINFO pCpu, PVM pVM, void *pvCpuPage, RTHCPHYS HCPhysCpuPage, bool fEnabledByHost,
+VMMR0DECL(int) SVMR0EnableCpu(PHMGLOBALCPUINFO pHostCpu, PVM pVM, void *pvCpuPage, RTHCPHYS HCPhysCpuPage, bool fEnabledByHost,
                               void *pvArg)
 {
@@ -560,7 +559,7 @@
         if (   pVM
             && pVM->hm.s.svm.fIgnoreInUseError)
-            pCpu->fIgnoreAMDVInUseError = true;
-
-        if (!pCpu->fIgnoreAMDVInUseError)
+            pHostCpu->fIgnoreAMDVInUseError = true;
+
+        if (!pHostCpu->fIgnoreAMDVInUseError)
         {
             ASMSetFlags(fEFlags);
@@ -584,10 +583,10 @@
      * entirely with before executing any guest code.
      */
-    pCpu->fFlushAsidBeforeUse = true;
+    pHostCpu->fFlushAsidBeforeUse = true;
 
     /*
      * Ensure each VCPU scheduled on this CPU gets a new ASID on resume. See @bugref{6255}.
      */
-    ++pCpu->cTlbFlushes;
+    ++pHostCpu->cTlbFlushes;
 
     return VINF_SUCCESS;
@@ -599,9 +598,9 @@
  *
  * @returns VBox status code.
- * @param   pCpu            Pointer to the CPU info struct.
+ * @param   pHostCpu        Pointer to the CPU info struct.
  * @param   pvCpuPage       Pointer to the global CPU page.
  * @param   HCPhysCpuPage   Physical address of the global CPU page.
  */
-VMMR0DECL(int) SVMR0DisableCpu(PHMGLOBALCPUINFO pCpu, void *pvCpuPage, RTHCPHYS HCPhysCpuPage)
+VMMR0DECL(int) SVMR0DisableCpu(PHMGLOBALCPUINFO pHostCpu, void *pvCpuPage, RTHCPHYS HCPhysCpuPage)
 {
     Assert(!RTThreadPreemptIsEnabled(NIL_RTTHREAD));
@@ -609,5 +608,5 @@
                  && HCPhysCpuPage != NIL_RTHCPHYS, VERR_INVALID_PARAMETER);
     AssertReturn(pvCpuPage, VERR_INVALID_PARAMETER);
-    NOREF(pCpu);
+    RT_NOREF(pHostCpu);
 
     /* Paranoid: Disable interrupts as, in theory, interrupt handlers might mess with EFER. */
@@ -1169,14 +1168,12 @@
  *
  * @returns VBox status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   GCVirt      Guest virtual address of the page to invalidate.
  */
-VMMR0DECL(int) SVMR0InvalidatePage(PVM pVM, PVMCPU pVCpu, RTGCPTR GCVirt)
-{
-    AssertReturn(pVM, VERR_INVALID_PARAMETER);
-    Assert(pVM->hm.s.svm.fSupported);
-
-    bool fFlushPending = pVM->hm.s.svm.fAlwaysFlushTLB || VMCPU_FF_IS_PENDING(pVCpu, VMCPU_FF_TLB_FLUSH);
+VMMR0DECL(int) SVMR0InvalidatePage(PVMCPU pVCpu, RTGCPTR GCVirt)
+{
+    Assert(pVCpu->CTX_SUFF(pVM)->hm.s.svm.fSupported);
+
+    bool const fFlushPending = pVCpu->CTX_SUFF(pVM)->hm.s.svm.fAlwaysFlushTLB || VMCPU_FF_IS_PENDING(pVCpu, VMCPU_FF_TLB_FLUSH);
 
     /* Skip it if a TLB flush is already pending. */
@@ -1610,5 +1607,5 @@
     pVmcb->ctrl.u32VmcbCleanBits &= ~HMSVM_VMCB_CLEAN_INTERCEPTS;
 
-    Assert(RT_HI_U32(uShadowCr0) == 0);
+    Assert(!RT_HI_U32(uShadowCr0));
     if (pVmcb->guest.u64CR0 != uShadowCr0)
     {
@@ -1723,5 +1720,5 @@
 
     /* Update VMCB with the shadow CR4 the appropriate VMCB clean bits. */
-    Assert(RT_HI_U32(uShadowCr4) == 0);
+    Assert(!RT_HI_U32(uShadowCr4));
     pVmcb->guest.u64CR4 = uShadowCr4;
     pVmcb->ctrl.u32VmcbCleanBits &= ~(HMSVM_VMCB_CLEAN_CRX_EFER | HMSVM_VMCB_CLEAN_INTERCEPTS);
@@ -2337,17 +2334,15 @@
  *
  * @returns VBox status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
- * @param   pCpu        Pointer to the CPU info struct.
- */
-VMMR0DECL(int) SVMR0Enter(PVM pVM, PVMCPU pVCpu, PHMGLOBALCPUINFO pCpu)
-{
-    AssertPtr(pVM);
+ * @param   pHostCpu    Pointer to the CPU info struct.
+ */
+VMMR0DECL(int) SVMR0Enter(PVMCPU pVCpu, PHMGLOBALCPUINFO pHostCpu)
+{
     AssertPtr(pVCpu);
-    Assert(pVM->hm.s.svm.fSupported);
+    Assert(pVCpu->CTX_SUFF(pVM)->hm.s.svm.fSupported);
     Assert(!RTThreadPreemptIsEnabled(NIL_RTTHREAD));
-    NOREF(pVM); NOREF(pCpu);
-
-    LogFlowFunc(("pVM=%p pVCpu=%p\n", pVM, pVCpu));
+    RT_NOREF(pHostCpu);
+
+    LogFlowFunc(("pVCpu=%p\n", pVCpu));
     Assert((pVCpu->hm.s.fCtxChanged & (HM_CHANGED_HOST_CONTEXT | HM_CHANGED_SVM_HOST_GUEST_SHARED_STATE))
                                    == (HM_CHANGED_HOST_CONTEXT | HM_CHANGED_SVM_HOST_GUEST_SHARED_STATE));
@@ -2410,5 +2405,5 @@
              * initializing AMD-V if necessary (onlined CPUs, local init etc.)
              */
-            int rc = HMR0EnterCpu(pVCpu);
+            int rc = hmR0EnterCpu(pVCpu);
             AssertRC(rc); NOREF(rc);
             Assert((pVCpu->hm.s.fCtxChanged & (HM_CHANGED_HOST_CONTEXT | HM_CHANGED_SVM_HOST_GUEST_SHARED_STATE))
@@ -3126,6 +3121,6 @@
     STAM_PROFILE_ADV_SET_STOPPED(&pVCpu->hm.s.StatImportGuestState);
     STAM_PROFILE_ADV_SET_STOPPED(&pVCpu->hm.s.StatExportGuestState);
-    STAM_PROFILE_ADV_SET_STOPPED(&pVCpu->hm.s.StatExit1);
-    STAM_PROFILE_ADV_SET_STOPPED(&pVCpu->hm.s.StatExit2);
+    STAM_PROFILE_ADV_SET_STOPPED(&pVCpu->hm.s.StatPreExit);
+    STAM_PROFILE_ADV_SET_STOPPED(&pVCpu->hm.s.StatExitHandling);
     STAM_COUNTER_INC(&pVCpu->hm.s.StatSwitchLongJmpToR3);
 
@@ -3255,5 +3250,4 @@
  *
  * @returns VBox status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU context.
@@ -3261,7 +3255,6 @@
  *                      VINF_VMM_UNKNOWN_RING3_CALL.
  */
-static int hmR0SvmExitToRing3(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx, int rcExit)
-{
-    Assert(pVM);
+static int hmR0SvmExitToRing3(PVMCPU pVCpu, PCPUMCTX pCtx, int rcExit)
+{
     Assert(pVCpu);
     Assert(pCtx);
@@ -3270,5 +3263,6 @@
     /* Please, no longjumps here (any logging shouldn't flush jump back to ring-3). NO LOGGING BEFORE THIS POINT! */
     VMMRZCallRing3Disable(pVCpu);
-    Log4Func(("rcExit=%d LocalFF=%#RX32 GlobalFF=%#RX32\n", rcExit, pVCpu->fLocalForcedActions, pVM->fGlobalForcedActions));
+    Log4Func(("rcExit=%d LocalFF=%#RX32 GlobalFF=%#RX32\n", rcExit, pVCpu->fLocalForcedActions,
+              pVCpu->CTX_SUFF(pVM)->fGlobalForcedActions));
 
     /* We need to do this only while truly exiting the "inner loop" back to ring-3 and -not- for any longjmp to ring3. */
@@ -3290,5 +3284,5 @@
                                | CPUM_CHANGED_TR
                                | CPUM_CHANGED_HIDDEN_SEL_REGS);
-    if (   pVM->hm.s.fNestedPaging
+    if (   pVCpu->CTX_SUFF(pVM)->hm.s.fNestedPaging
         && CPUMIsGuestPagingEnabledEx(pCtx))
     {
@@ -3331,6 +3325,4 @@
  * intercepts.
  *
- * @param   pVM         The cross context VM structure.
- * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU or nested-guest-CPU context.
  * @param   pVmcb       Pointer to the VM control block.
@@ -3338,5 +3330,5 @@
  * @remarks No-long-jump zone!!!
  */
-static void hmR0SvmUpdateTscOffsetting(PVM pVM, PVMCPU pVCpu, PCCPUMCTX pCtx, PSVMVMCB pVmcb)
+static void hmR0SvmUpdateTscOffsetting(PVMCPU pVCpu, PCCPUMCTX pCtx, PSVMVMCB pVmcb)
 {
     /*
@@ -3347,5 +3339,5 @@
     bool       fParavirtTsc;
     uint64_t   uTscOffset;
-    bool const fCanUseRealTsc = TMCpuTickCanUseRealTSC(pVM, pVCpu, &uTscOffset, &fParavirtTsc);
+    bool const fCanUseRealTsc = TMCpuTickCanUseRealTSC(pVCpu->CTX_SUFF(pVM), pVCpu, &uTscOffset, &fParavirtTsc);
 
     bool fIntercept;
@@ -4079,5 +4071,4 @@
  * Reports world-switch error and dumps some useful debug info.
  *
- * @param   pVM             The cross context VM structure.
  * @param   pVCpu           The cross context virtual CPU structure.
  * @param   rcVMRun         The return code from VMRUN (or
@@ -4086,18 +4077,15 @@
  * @param   pCtx            Pointer to the guest-CPU context.
  */
-static void hmR0SvmReportWorldSwitchError(PVM pVM, PVMCPU pVCpu, int rcVMRun, PCPUMCTX pCtx)
-{
-    NOREF(pCtx);
+static void hmR0SvmReportWorldSwitchError(PVMCPU pVCpu, int rcVMRun, PCPUMCTX pCtx)
+{
     HMSVM_ASSERT_PREEMPT_SAFE();
     HMSVM_ASSERT_NOT_IN_NESTED_GUEST(pCtx);
     HMSVM_CPUMCTX_IMPORT_STATE(pVCpu, HMSVM_CPUMCTX_EXTRN_ALL);
 
-    PCSVMVMCB pVmcb = pVCpu->hm.s.svm.pVmcb;
     if (rcVMRun == VERR_SVM_INVALID_GUEST_STATE)
     {
-        hmR0DumpRegs(pVM, pVCpu, pCtx); NOREF(pVM);
-        /** @todo We probably don't need to dump this anymore or we can expand
-         *        hmR0DumpRegs()? */
 #ifdef VBOX_STRICT
+        hmR0DumpRegs(pVCpu, pCtx);
+        PCSVMVMCB pVmcb = hmR0SvmGetCurrentVmcb(pVCpu, pCtx);
         Log4(("ctrl.u32VmcbCleanBits                 %#RX32\n",   pVmcb->ctrl.u32VmcbCleanBits));
         Log4(("ctrl.u16InterceptRdCRx                %#x\n",      pVmcb->ctrl.u16InterceptRdCRx));
@@ -4225,5 +4213,5 @@
         Log4Func(("rcVMRun=%d\n", rcVMRun));
 
-    NOREF(pVmcb);
+    NOREF(pCtx);
 }
 
@@ -4245,9 +4233,8 @@
  *         to the EM loop.
  *
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU context.
  */
-static int hmR0SvmCheckForceFlags(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx)
+static int hmR0SvmCheckForceFlags(PVMCPU pVCpu, PCPUMCTX pCtx)
 {
     Assert(VMMRZCallRing3IsEnabled(pVCpu));
@@ -4262,4 +4249,5 @@
         APICUpdatePendingInterrupts(pVCpu);
 
+    PVM pVM = pVCpu->CTX_SUFF(pVM);
     if (   VM_FF_IS_PENDING(pVM, !pVCpu->hm.s.fSingleInstruction
                             ? VM_FF_HP_R0_PRE_HM_MASK : VM_FF_HP_R0_PRE_HM_STEP_MASK)
@@ -4324,5 +4312,4 @@
  * @retval VINF_* scheduling changes, we have to go back to ring-3.
  *
- * @param   pVM             The cross context VM structure.
  * @param   pVCpu           The cross context virtual CPU structure.
  * @param   pCtx            Pointer to the nested-guest-CPU context.
@@ -4332,5 +4319,5 @@
  * @sa      hmR0SvmPreRunGuest.
  */
-static int hmR0SvmPreRunGuestNested(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx, PSVMTRANSIENT pSvmTransient)
+static int hmR0SvmPreRunGuestNested(PVMCPU pVCpu, PCPUMCTX pCtx, PSVMTRANSIENT pSvmTransient)
 {
     HMSVM_ASSERT_PREEMPT_SAFE();
@@ -4343,5 +4330,5 @@
 
     /* Check force flag actions that might require us to go back to ring-3. */
-    int rc = hmR0SvmCheckForceFlags(pVM, pVCpu, pCtx);
+    int rc = hmR0SvmCheckForceFlags(pVCpu, pCtx);
     if (rc != VINF_SUCCESS)
         return rc;
@@ -4364,4 +4351,5 @@
      * NB: If we could continue a task switch exit we wouldn't need to do this.
      */
+    PVM pVM = pVCpu->CTX_SUFF(pVM);
     if (RT_UNLIKELY(   !pVM->hm.s.svm.u32Features
                     &&  pVCpu->hm.s.Event.fPending
@@ -4446,10 +4434,9 @@
  * @retval VINF_* scheduling changes, we have to go back to ring-3.
  *
- * @param   pVM             The cross context VM structure.
  * @param   pVCpu           The cross context virtual CPU structure.
  * @param   pCtx            Pointer to the guest-CPU context.
  * @param   pSvmTransient   Pointer to the SVM transient structure.
  */
-static int hmR0SvmPreRunGuest(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx, PSVMTRANSIENT pSvmTransient)
+static int hmR0SvmPreRunGuest(PVMCPU pVCpu, PCPUMCTX pCtx, PSVMTRANSIENT pSvmTransient)
 {
     HMSVM_ASSERT_PREEMPT_SAFE();
@@ -4457,5 +4444,5 @@
 
     /* Check force flag actions that might require us to go back to ring-3. */
-    int rc = hmR0SvmCheckForceFlags(pVM, pVCpu, pCtx);
+    int rc = hmR0SvmCheckForceFlags(pVCpu, pCtx);
     if (rc != VINF_SUCCESS)
         return rc;
@@ -4471,4 +4458,5 @@
      * NB: If we could continue a task switch exit we wouldn't need to do this.
      */
+    PVM pVM = pVCpu->CTX_SUFF(pVM);
     if (RT_UNLIKELY(pVCpu->hm.s.Event.fPending && (((pVCpu->hm.s.Event.u64IntInfo >> 8) & 7) == SVM_EVENT_NMI)))
         if (RT_UNLIKELY(!pVM->hm.s.svm.u32Features))
@@ -4604,5 +4592,5 @@
         || fMigratedHostCpu)
     {
-        hmR0SvmUpdateTscOffsetting(pVM, pVCpu, pCtx, pVmcb);
+        hmR0SvmUpdateTscOffsetting(pVCpu, pCtx, pVmcb);
         pSvmTransient->fUpdateTscOffsetting = false;
     }
@@ -4687,14 +4675,14 @@
 
 /**
- * Wrapper for running the guest code in AMD-V.
+ * Wrapper for running the guest (or nested-guest) code in AMD-V.
  *
  * @returns VBox strict status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU context.
+ * @param   HCPhysVmcb  The host physical address of the VMCB.
  *
  * @remarks No-long-jump zone!!!
  */
-DECLINLINE(int) hmR0SvmRunGuest(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx)
+DECLINLINE(int) hmR0SvmRunGuest(PVMCPU pVCpu, PCPUMCTX pCtx, RTHCPHYS HCPhysVmcb)
 {
     /* Mark that HM is the keeper of all guest-CPU registers now that we're going to execute guest code. */
@@ -4708,41 +4696,9 @@
      * Refer MSDN "Configuring Programs for 64-bit/x64 Software Conventions / Register Usage".
      */
+    PVM pVM = pVCpu->CTX_SUFF(pVM);
 #ifdef VBOX_WITH_KERNEL_USING_XMM
-    return hmR0SVMRunWrapXMM(pVCpu->hm.s.svm.HCPhysVmcbHost, pVCpu->hm.s.svm.HCPhysVmcb, pCtx, pVM, pVCpu,
-                             pVCpu->hm.s.svm.pfnVMRun);
+    return hmR0SVMRunWrapXMM(pVCpu->hm.s.svm.HCPhysVmcbHost, HCPhysVmcb, pCtx, pVM, pVCpu, pVCpu->hm.s.svm.pfnVMRun);
 #else
-    return pVCpu->hm.s.svm.pfnVMRun(pVCpu->hm.s.svm.HCPhysVmcbHost, pVCpu->hm.s.svm.HCPhysVmcb, pCtx, pVM, pVCpu);
-#endif
-}
-
-
-#ifdef VBOX_WITH_NESTED_HWVIRT_SVM
-/**
- * Wrapper for running the nested-guest code in AMD-V.
- *
- * @returns VBox strict status code.
- * @param   pVM         The cross context VM structure.
- * @param   pVCpu       The cross context virtual CPU structure.
- * @param   pCtx        Pointer to the guest-CPU context.
- *
- * @remarks No-long-jump zone!!!
- */
-DECLINLINE(int) hmR0SvmRunGuestNested(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx)
-{
-    /* Mark that HM is the keeper of all guest-CPU registers now that we're going to execute guest code. */
-    pCtx->fExtrn |= HMSVM_CPUMCTX_EXTRN_ALL | CPUMCTX_EXTRN_KEEPER_HM;
-
-    /*
-     * 64-bit Windows uses XMM registers in the kernel as the Microsoft compiler expresses
-     * floating-point operations using SSE instructions. Some XMM registers (XMM6-XMM15) are
-     * callee-saved and thus the need for this XMM wrapper.
-     *
-     * Refer MSDN "Configuring Programs for 64-bit/x64 Software Conventions / Register Usage".
-     */
-#ifdef VBOX_WITH_KERNEL_USING_XMM
-    return hmR0SVMRunWrapXMM(pVCpu->hm.s.svm.HCPhysVmcbHost, pCtx->hwvirt.svm.HCPhysVmcb, pCtx, pVM, pVCpu,
-                             pVCpu->hm.s.svm.pfnVMRun);
-#else
-    return pVCpu->hm.s.svm.pfnVMRun(pVCpu->hm.s.svm.HCPhysVmcbHost, pCtx->hwvirt.svm.HCPhysVmcb, pCtx, pVM, pVCpu);
+    return pVCpu->hm.s.svm.pfnVMRun(pVCpu->hm.s.svm.HCPhysVmcbHost, HCPhysVmcb, pCtx, pVM, pVCpu);
 #endif
 }
@@ -4768,5 +4724,5 @@
     return uTicks - pVmcbNstGstCache->u64TSCOffset;
 }
-#endif
+
 
 /**
@@ -4819,5 +4775,5 @@
     }
 
-    STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatInGC, &pVCpu->hm.s.StatExit1, x);
+    STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatInGC, &pVCpu->hm.s.StatPreExit, x);
     TMNotifyEndOfExecution(pVCpu);                              /* Notify TM that the guest is no longer running. */
     VMCPU_SET_STATE(pVCpu, VMCPUSTATE_STARTED_HM);
@@ -4908,12 +4864,11 @@
  *
  * @returns VBox status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU context.
  * @param   pcLoops     Pointer to the number of executed loops.
  */
-static int hmR0SvmRunGuestCodeNormal(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx, uint32_t *pcLoops)
-{
-    uint32_t const cMaxResumeLoops = pVM->hm.s.cMaxResumeLoops;
+static int hmR0SvmRunGuestCodeNormal(PVMCPU pVCpu, PCPUMCTX pCtx, uint32_t *pcLoops)
+{
+    uint32_t const cMaxResumeLoops = pVCpu->CTX_SUFF(pVM)->hm.s.cMaxResumeLoops;
     Assert(pcLoops);
     Assert(*pcLoops <= cMaxResumeLoops);
@@ -4933,5 +4888,5 @@
            ring-3.  This bugger disables interrupts on VINF_SUCCESS! */
         STAM_PROFILE_ADV_START(&pVCpu->hm.s.StatEntry, x);
-        rc = hmR0SvmPreRunGuest(pVM, pVCpu, pCtx, &SvmTransient);
+        rc = hmR0SvmPreRunGuest(pVCpu, pCtx, &SvmTransient);
         if (rc != VINF_SUCCESS)
             break;
@@ -4944,5 +4899,5 @@
          */
         hmR0SvmPreRunGuestCommitted(pVCpu, pCtx, &SvmTransient);
-        rc = hmR0SvmRunGuest(pVM, pVCpu, pCtx);
+        rc = hmR0SvmRunGuest(pVCpu, pCtx, pVCpu->hm.s.svm.HCPhysVmcb);
 
         /* Restore any residual host-state and save any bits shared between host and guest
@@ -4955,6 +4910,6 @@
             if (rc == VINF_SUCCESS)
                 rc = VERR_SVM_INVALID_GUEST_STATE;
-            STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExit1, x);
-            hmR0SvmReportWorldSwitchError(pVM, pVCpu, rc, pCtx);
+            STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatPreExit, x);
+            hmR0SvmReportWorldSwitchError(pVCpu, rc, pCtx);
             break;
         }
@@ -4962,8 +4917,8 @@
         /* Handle the #VMEXIT. */
         HMSVM_EXITCODE_STAM_COUNTER_INC(SvmTransient.u64ExitCode);
-        STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatExit1, &pVCpu->hm.s.StatExit2, x);
+        STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatPreExit, &pVCpu->hm.s.StatExitHandling, x);
         VBOXVMM_R0_HMSVM_VMEXIT(pVCpu, pCtx, SvmTransient.u64ExitCode, pVCpu->hm.s.svm.pVmcb);
         rc = hmR0SvmHandleExit(pVCpu, pCtx, &SvmTransient);
-        STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExit2, x);
+        STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExitHandling, x);
         if (rc != VINF_SUCCESS)
             break;
@@ -4985,12 +4940,11 @@
  *
  * @returns VBox status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU context.
  * @param   pcLoops     Pointer to the number of executed loops.
  */
-static int hmR0SvmRunGuestCodeStep(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx, uint32_t *pcLoops)
-{
-    uint32_t const cMaxResumeLoops = pVM->hm.s.cMaxResumeLoops;
+static int hmR0SvmRunGuestCodeStep(PVMCPU pVCpu, PCPUMCTX pCtx, uint32_t *pcLoops)
+{
+    uint32_t const cMaxResumeLoops = pVCpu->CTX_SUFF(pVM)->hm.s.cMaxResumeLoops;
     Assert(pcLoops);
     Assert(*pcLoops <= cMaxResumeLoops);
@@ -5015,5 +4969,5 @@
            ring-3.  This bugger disables interrupts on VINF_SUCCESS! */
         STAM_PROFILE_ADV_START(&pVCpu->hm.s.StatEntry, x);
-        rc = hmR0SvmPreRunGuest(pVM, pVCpu, pCtx, &SvmTransient);
+        rc = hmR0SvmPreRunGuest(pVCpu, pCtx, &SvmTransient);
         if (rc != VINF_SUCCESS)
             break;
@@ -5029,5 +4983,5 @@
         hmR0SvmPreRunGuestCommitted(pVCpu, pCtx, &SvmTransient);
 
-        rc = hmR0SvmRunGuest(pVM, pVCpu, pCtx);
+        rc = hmR0SvmRunGuest(pVCpu, pCtx, pVCpu->hm.s.svm.HCPhysVmcb);
 
         /* Restore any residual host-state and save any bits shared between host and guest
@@ -5040,6 +4994,6 @@
             if (rc == VINF_SUCCESS)
                 rc = VERR_SVM_INVALID_GUEST_STATE;
-            STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExit1, x);
-            hmR0SvmReportWorldSwitchError(pVM, pVCpu, rc, pCtx);
+            STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatPreExit, x);
+            hmR0SvmReportWorldSwitchError(pVCpu, rc, pCtx);
             return rc;
         }
@@ -5047,8 +5001,8 @@
         /* Handle the #VMEXIT. */
         HMSVM_EXITCODE_STAM_COUNTER_INC(SvmTransient.u64ExitCode);
-        STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatExit1, &pVCpu->hm.s.StatExit2, x);
+        STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatPreExit, &pVCpu->hm.s.StatExitHandling, x);
         VBOXVMM_R0_HMSVM_VMEXIT(pVCpu, pCtx, SvmTransient.u64ExitCode, pVCpu->hm.s.svm.pVmcb);
         rc = hmR0SvmHandleExit(pVCpu, pCtx, &SvmTransient);
-        STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExit2, x);
+        STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExitHandling, x);
         if (rc != VINF_SUCCESS)
             break;
@@ -5091,5 +5045,4 @@
  *
  * @returns VBox status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU context.
@@ -5098,9 +5051,9 @@
  *                      execution loop pass the remainder value, else pass 0.
  */
-static int hmR0SvmRunGuestCodeNested(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx, uint32_t *pcLoops)
+static int hmR0SvmRunGuestCodeNested(PVMCPU pVCpu, PCPUMCTX pCtx, uint32_t *pcLoops)
 {
     HMSVM_ASSERT_IN_NESTED_GUEST(pCtx);
     Assert(pcLoops);
-    Assert(*pcLoops <= pVM->hm.s.cMaxResumeLoops);
+    Assert(*pcLoops <= pVCpu->CTX_SUFF(pVM)->hm.s.cMaxResumeLoops);
 
     SVMTRANSIENT SvmTransient;
@@ -5119,5 +5072,5 @@
            ring-3.  This bugger disables interrupts on VINF_SUCCESS! */
         STAM_PROFILE_ADV_START(&pVCpu->hm.s.StatEntry, x);
-        rc = hmR0SvmPreRunGuestNested(pVM, pVCpu, pCtx, &SvmTransient);
+        rc = hmR0SvmPreRunGuestNested(pVCpu, pCtx, &SvmTransient);
         if (    rc != VINF_SUCCESS
             || !CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
@@ -5134,5 +5087,5 @@
         hmR0SvmPreRunGuestCommitted(pVCpu, pCtx, &SvmTransient);
 
-        rc = hmR0SvmRunGuestNested(pVM, pVCpu, pCtx);
+        rc = hmR0SvmRunGuest(pVCpu, pCtx, pCtx->hwvirt.svm.HCPhysVmcb);
 
         /* Restore any residual host-state and save any bits shared between host and guest
@@ -5158,12 +5111,12 @@
         /* Handle the #VMEXIT. */
         HMSVM_NESTED_EXITCODE_STAM_COUNTER_INC(SvmTransient.u64ExitCode);
-        STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatExit1, &pVCpu->hm.s.StatExit2, x);
+        STAM_PROFILE_ADV_STOP_START(&pVCpu->hm.s.StatPreExit, &pVCpu->hm.s.StatExitHandling, x);
         VBOXVMM_R0_HMSVM_VMEXIT(pVCpu, pCtx, SvmTransient.u64ExitCode, pCtx->hwvirt.svm.CTX_SUFF(pVmcb));
         rc = hmR0SvmHandleExitNested(pVCpu, pCtx, &SvmTransient);
-        STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExit2, x);
+        STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExitHandling, x);
         if (    rc != VINF_SUCCESS
             || !CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
             break;
-        if (++(*pcLoops) >= pVM->hm.s.cMaxResumeLoops)
+        if (++(*pcLoops) >= pVCpu->CTX_SUFF(pVM)->hm.s.cMaxResumeLoops)
         {
             STAM_COUNTER_INC(&pVCpu->hm.s.StatSwitchMaxResumeLoops);
@@ -5185,9 +5138,8 @@
  *
  * @returns Strict VBox status code.
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        Pointer to the guest-CPU context.
  */
-VMMR0DECL(VBOXSTRICTRC) SVMR0RunGuestCode(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx)
+VMMR0DECL(VBOXSTRICTRC) SVMR0RunGuestCode(PVMCPU pVCpu, PCPUMCTX pCtx)
 {
     Assert(VMMRZCallRing3IsEnabled(pVCpu));
@@ -5202,7 +5154,7 @@
     {
         if (!pVCpu->hm.s.fSingleInstruction)
-            rc = hmR0SvmRunGuestCodeNormal(pVM, pVCpu, pCtx, &cLoops);
+            rc = hmR0SvmRunGuestCodeNormal(pVCpu, pCtx, &cLoops);
         else
-            rc = hmR0SvmRunGuestCodeStep(pVM, pVCpu, pCtx, &cLoops);
+            rc = hmR0SvmRunGuestCodeStep(pVCpu, pCtx, &cLoops);
     }
 #ifdef VBOX_WITH_NESTED_HWVIRT_SVM
@@ -5216,5 +5168,5 @@
     if (rc == VINF_SVM_VMRUN)
     {
-        rc = hmR0SvmRunGuestCodeNested(pVM, pVCpu, pCtx, &cLoops);
+        rc = hmR0SvmRunGuestCodeNested(pVCpu, pCtx, &cLoops);
         if (rc == VINF_SVM_VMEXIT)
             rc = VINF_SUCCESS;
@@ -5229,5 +5181,5 @@
 
     /* Prepare to return to ring-3. This will remove longjmp notifications. */
-    rc = hmR0SvmExitToRing3(pVM, pVCpu, pCtx, rc);
+    rc = hmR0SvmExitToRing3(pVCpu, pCtx, rc);
     Assert(!VMMRZCallRing3IsNotificationSet(pVCpu));
     return rc;
@@ -5954,5 +5906,4 @@
  * @retval  VERR_*                  Fatal errors.
  *
- * @param   pVM         The cross context VM structure.
  * @param   pVCpu       The cross context virtual CPU structure.
  * @param   pCtx        The guest CPU context.
@@ -5960,5 +5911,5 @@
  * @remarks Updates the RIP if the instruction was executed successfully.
  */
-static int hmR0SvmInterpretInvlpg(PVM pVM, PVMCPU pVCpu, PCPUMCTX pCtx)
+static int hmR0SvmInterpretInvlpg(PVMCPU pVCpu, PCPUMCTX pCtx)
 {
     /* Only allow 32 & 64 bit code. */
@@ -5966,5 +5917,5 @@
     {
         PDISSTATE pDis = &pVCpu->hm.s.DisState;
-        int rc = EMInterpretDisasCurrent(pVM, pVCpu, pDis, NULL /* pcbInstr */);
+        int rc = EMInterpretDisasCurrent(pVCpu->CTX_SUFF(pVM), pVCpu, pDis, NULL /* pcbInstr */);
         if (   RT_SUCCESS(rc)
             && pDis->pCurInstr->uOpcode == OP_INVLPG)
@@ -6447,6 +6398,5 @@
 {
     HMSVM_VALIDATE_EXIT_HANDLER_PARAMS();
-    PVM pVM = pVCpu->CTX_SUFF(pVM);
-    Assert(!pVM->hm.s.fNestedPaging);
+    Assert(!pVCpu->CTX_SUFF(pVM)->hm.s.fNestedPaging);
 
     bool const fSupportsDecodeAssists = hmR0SvmSupportsDecodeAssists(pVCpu, pCtx);
@@ -6465,5 +6415,5 @@
 
     HMSVM_CPUMCTX_IMPORT_STATE(pVCpu, HMSVM_CPUMCTX_EXTRN_ALL);
-    int rc = hmR0SvmInterpretInvlpg(pVM, pVCpu, pCtx);    /* Updates RIP if successful. */
+    int rc = hmR0SvmInterpretInvlpg(pVCpu, pCtx);    /* Updates RIP if successful. */
     Assert(rc == VINF_SUCCESS || rc == VERR_EM_INTERPRETER);
     HMSVM_CHECK_SINGLE_STEP(pVCpu, rc);
@@ -6997,5 +6947,5 @@
     static uint32_t const s_aIOSize[8]  = { 0, 1, 2, 0, 4, 0, 0, 0 };                   /* Size of the I/O accesses in bytes. */
     static uint32_t const s_aIOOpAnd[8] = { 0, 0xff, 0xffff, 0, 0xffffffff, 0, 0, 0 };  /* AND masks for saving
-                                                                                            the result (in AL/AX/EAX). */
+                                                                                           the result (in AL/AX/EAX). */
     Log4Func(("CS:RIP=%04x:%#RX64\n", pCtx->cs.Sel, pCtx->rip));
 
@@ -7243,8 +7193,8 @@
      */
     if (   pVM->hm.s.fTprPatchingAllowed
-        && !CPUMIsGuestInSvmNestedHwVirtMode(pCtx)
         && (GCPhysFaultAddr & PAGE_OFFSET_MASK) == XAPIC_OFF_TPR
         && (   !(u32ErrCode & X86_TRAP_PF_P)                                                             /* Not present */
             || (u32ErrCode & (X86_TRAP_PF_P | X86_TRAP_PF_RSVD)) == (X86_TRAP_PF_P | X86_TRAP_PF_RSVD))  /* MMIO page. */
+        && !CPUMIsGuestInSvmNestedHwVirtMode(pCtx)
         && !CPUMIsGuestInLongModeEx(pCtx)
         && !CPUMGetGuestCPL(pVCpu)
@@ -8049,8 +7999,6 @@
     return VINF_SUCCESS;
 }
-
 #endif /* VBOX_WITH_NESTED_HWVIRT_SVM */
 
-
 /** @} */
 
