VirtualBox

Changeset 81092 in vbox


Ignore:
Timestamp:
Oct 1, 2019 4:53:27 AM (5 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
133698
Message:

VMM/HMSVMR0: Nested SVM: bugref:7243 Optimize run loop to avoid exits to ring-3 on every nested-guest VM-exit.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMR0/HMSVMR0.cpp

    r81002 r81092  
    26612661    PCSVMVMCBSTATESAVE pVmcbGuest = &pVmcb->guest;
    26622662    PCSVMVMCBCTRL      pVmcbCtrl  = &pVmcb->ctrl;
    2663 
    2664     Log4Func(("fExtrn=%#RX64 fWhat=%#RX64\n", pCtx->fExtrn, fWhat));
    26652663
    26662664    /*
     
    41004098    {
    41014099        /* Pending PGM C3 sync. */
    4102         if (VMCPU_FF_IS_ANY_SET(pVCpu,VMCPU_FF_PGM_SYNC_CR3 | VMCPU_FF_PGM_SYNC_CR3_NON_GLOBAL))
     4100        if (VMCPU_FF_IS_ANY_SET(pVCpu, VMCPU_FF_PGM_SYNC_CR3 | VMCPU_FF_PGM_SYNC_CR3_NON_GLOBAL))
    41034101        {
    41044102            int rc = PGMSyncCR3(pVCpu, pVCpu->cpum.GstCtx.cr0, pVCpu->cpum.GstCtx.cr3, pVCpu->cpum.GstCtx.cr4,
     
    41834181    int rc = hmR0SvmCheckForceFlags(pVCpu);
    41844182    if (rc != VINF_SUCCESS)
     4183    {
     4184        if (!CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
     4185            STAM_COUNTER_INC(&pVCpu->hm.s.StatSwitchNstGstVmexit);
    41854186        return rc;
     4187    }
    41864188
    41874189    if (TRPMHasTrap(pVCpu))
     
    41924194        if (    rcStrict != VINF_SUCCESS
    41934195            || !CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
     4196        {
     4197            if (!CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
     4198                STAM_COUNTER_INC(&pVCpu->hm.s.StatSwitchNstGstVmexit);
    41944199            return VBOXSTRICTRC_VAL(rcStrict);
     4200        }
    41954201    }
    41964202
     
    43144320
    43154321#ifdef HMSVM_SYNC_FULL_GUEST_STATE
    4316     Assert(!(pVCpu->cpum.GstCtx->fExtrn & HMSVM_CPUMCTX_EXTRN_ALL));
     4322    Assert(!(pVCpu->cpum.GstCtx.fExtrn & HMSVM_CPUMCTX_EXTRN_ALL));
    43174323    ASMAtomicUoOrU64(&pVCpu->hm.s.fCtxChanged, HM_CHANGED_ALL_GUEST);
    43184324#endif
     
    49224928        rc = hmR0SvmHandleExitNested(pVCpu, &SvmTransient);
    49234929        STAM_PROFILE_ADV_STOP(&pVCpu->hm.s.StatExitHandling, x);
    4924         if (    rc != VINF_SUCCESS
    4925             || !CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
    4926             break;
    4927         if (++(*pcLoops) >= pVCpu->CTX_SUFF(pVM)->hm.s.cMaxResumeLoops)
    4928         {
    4929             STAM_COUNTER_INC(&pVCpu->hm.s.StatSwitchMaxResumeLoops);
    4930             rc = VINF_EM_RAW_INTERRUPT;
    4931             break;
    4932         }
    4933         /** @todo NSTSVM: Add stat for StatSwitchNstGstVmexit. Re-arrange the above code to
    4934          *        be accurate when doing so, see the corresponding VT-x code. */
    4935 
    4936         /** @todo handle single-stepping   */
     4930        if (rc == VINF_SUCCESS)
     4931        {
     4932            if (!CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
     4933            {
     4934                STAM_COUNTER_INC(&pVCpu->hm.s.StatSwitchNstGstVmexit);
     4935                rc = VINF_SVM_VMEXIT;
     4936            }
     4937            else
     4938            {
     4939                if (++(*pcLoops) <= pVCpu->CTX_SUFF(pVM)->hm.s.cMaxResumeLoops)
     4940                    continue;
     4941                STAM_COUNTER_INC(&pVCpu->hm.s.StatSwitchMaxResumeLoops);
     4942                rc = VINF_EM_RAW_INTERRUPT;
     4943            }
     4944        }
     4945        else
     4946            Assert(rc != VINF_SVM_VMEXIT);
     4947        break;
     4948        /** @todo NSTSVM: handle single-stepping. */
    49374949    }
    49384950
     
    49594971    uint32_t cLoops = 0;
    49604972    int      rc;
     4973    for (;;)
     4974    {
    49614975#ifdef VBOX_WITH_NESTED_HWVIRT_SVM
    4962     if (!CPUMIsGuestInSvmNestedHwVirtMode(pCtx))
     4976        bool const fInNestedGuestMode = CPUMIsGuestInSvmNestedHwVirtMode(pCtx);
     4977#else
     4978        NOREF(pCtx);
     4979        bool const fInNestedGuestMode = false;
    49634980#endif
    4964     {
    4965         if (!pVCpu->hm.s.fSingleInstruction)
    4966             rc = hmR0SvmRunGuestCodeNormal(pVCpu, &cLoops);
     4981        if (!fInNestedGuestMode)
     4982        {
     4983            if (!pVCpu->hm.s.fSingleInstruction)
     4984                rc = hmR0SvmRunGuestCodeNormal(pVCpu, &cLoops);
     4985            else
     4986                rc = hmR0SvmRunGuestCodeStep(pVCpu, &cLoops);
     4987        }
     4988#ifdef VBOX_WITH_NESTED_HWVIRT_SVM
    49674989        else
    4968             rc = hmR0SvmRunGuestCodeStep(pVCpu, &cLoops);
    4969     }
    4970 #ifdef VBOX_WITH_NESTED_HWVIRT_SVM
    4971     else
    4972     {
    4973         rc = VINF_SVM_VMRUN;
    4974     }
    4975 
    4976     /* Re-check the nested-guest condition here as we may be transitioning from the normal
    4977        execution loop into the nested-guest, hence this is not placed in the 'else' part above. */
    4978     if (rc == VINF_SVM_VMRUN)
    4979     {
    4980         rc = hmR0SvmRunGuestCodeNested(pVCpu, &cLoops);
     4990            rc = hmR0SvmRunGuestCodeNested(pVCpu, &cLoops);
     4991
     4992        if (rc == VINF_SVM_VMRUN)
     4993        {
     4994            Assert(CPUMIsGuestInSvmNestedHwVirtMode(pCtx));
     4995            continue;
     4996        }
    49814997        if (rc == VINF_SVM_VMEXIT)
    4982             rc = VINF_SUCCESS;
    4983     }
     4998        {
     4999            Assert(!CPUMIsGuestInSvmNestedHwVirtMode(pCtx));
     5000            continue;
     5001        }
    49845002#endif
    4985 
    4986     /** @todo NSTSVM: Continue in ring-0 after nested-guest \#VMEXIT. See VT-x code for
    4987      *        reference. */
     5003        break;
     5004    }
    49885005
    49895006    /* Fixup error codes. */
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette