VirtualBox

Changeset 100792 in vbox


Ignore:
Timestamp:
Aug 4, 2023 9:36:49 AM (16 months ago)
Author:
vboxsync
Message:

VMM/IEM: Properly deal with CPUMCTX_INHIBIT_SHADOW at the start of a TB. bugref:10369

Location:
trunk/src/VBox/VMM
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMAll/IEMAllThrdRecompiler.cpp

    r100791 r100792  
    687687 * to apply fixes to them as well.
    688688 *
    689  * @param   pVCpu   The cross context virtual CPU structure of the calling
    690  *                  thread.
    691  * @param   fReInit Clear for the first call for a TB, set for subsequent calls
    692  *                  from inside the compile loop where we can skip a couple of
    693  *                  things.
    694  */
    695 DECL_FORCE_INLINE(void) iemThreadedCompileInitDecoder(PVMCPUCC pVCpu, bool const fReInit)
     689 * @param   pVCpu       The cross context virtual CPU structure of the calling
     690 *                      thread.
     691 * @param   fReInit     Clear for the first call for a TB, set for subsequent
     692 *                      calls from inside the compile loop where we can skip a
     693 *                      couple of things.
     694 * @param   fExtraFlags The extra translation block flags when @a fReInit is
     695 *                      true, otherwise ignored.  Only IEMTB_F_INHIBIT_SHADOW is
     696 *                      checked.
     697 */
     698DECL_FORCE_INLINE(void) iemThreadedCompileInitDecoder(PVMCPUCC pVCpu, bool const fReInit, uint32_t const fExtraFlags)
    696699{
    697700    /* ASSUMES: That iemInitExec was already called and that anyone changing
     
    735738        pVCpu->iem.s.fTbBranched            = IEMBRANCHED_F_NO;
    736739        pVCpu->iem.s.fTbCrossedPage         = false;
    737         pVCpu->iem.s.cInstrTillIrqCheck     = 32;
    738         pVCpu->iem.s.fTbCurInstrIsSti       = CPUMIsInInterruptShadow(&pVCpu->cpum.GstCtx); /** @todo this'll be a IEM_TB_F_XXX flag */
     740        pVCpu->iem.s.cInstrTillIrqCheck     = !(fExtraFlags & IEMTB_F_INHIBIT_SHADOW) ? 32 : 0;
     741        pVCpu->iem.s.fTbCurInstrIsSti       = false;
    739742    }
    740743    else
     
    13411344     * Now for the recomplication. (This mimicks IEMExecLots in many ways.)
    13421345     */
    1343     iemThreadedCompileInitDecoder(pVCpu, false /*fReInit*/);
     1346    iemThreadedCompileInitDecoder(pVCpu, false /*fReInit*/, fExtraFlags);
    13441347    iemThreadedCompileInitOpcodeFetching(pVCpu);
    13451348    VBOXSTRICTRC rcStrict;
     
    13931396        if (   pTb->Thrd.cCalls + 5 < pTb->Thrd.cAllocated
    13941397            && pTb->cbOpcodes + 16 <= pTb->cbOpcodesAllocated)
    1395             iemThreadedCompileInitDecoder(pVCpu, true /*fReInit*/);
     1398            iemThreadedCompileInitDecoder(pVCpu, true /*fReInit*/, 0);
    13961399        else
    13971400        {
     
    15461549DECL_FORCE_INLINE(uint32_t) iemGetTbFlagsForCurrentPc(PVMCPUCC pVCpu)
    15471550{
     1551    uint32_t fRet = IEMTB_F_TYPE_THREADED;
     1552
     1553    /*
     1554     * Determine the inhibit bits.
     1555     */
     1556    if (!(pVCpu->cpum.GstCtx.rflags.uBoth & (IEMTB_F_INHIBIT_SHADOW | IEMTB_F_INHIBIT_NMI)))
     1557    { /* typical */ }
     1558    else
     1559    {
     1560        if (CPUMIsInInterruptShadow(&pVCpu->cpum.GstCtx))
     1561            fRet |= IEMTB_F_INHIBIT_SHADOW;
     1562        if (CPUMAreInterruptsInhibitedByNmiEx(&pVCpu->cpum.GstCtx))
     1563            fRet |= IEMTB_F_INHIBIT_NMI;
     1564    }
     1565
    15481566    /*
    15491567     * Return IEMTB_F_CS_LIM_CHECKS if the current PC is invalid or if it is
    15501568     * likely to go invalid before the end of the translation block.
    15511569     */
    1552 /** @todo must take interrupt inhibiting (shadowing) into account here! */
    15531570    if (IEM_IS_64BIT_CODE(pVCpu))
    1554         return IEMTB_F_TYPE_THREADED;
    1555 
    1556     if (RT_LIKELY(   pVCpu->cpum.GstCtx.eip < pVCpu->cpum.GstCtx.cs.u32Limit
    1557                   && pVCpu->cpum.GstCtx.cs.u32Limit - pVCpu->cpum.GstCtx.eip >= X86_PAGE_SIZE))
    1558         return IEMTB_F_TYPE_THREADED;
    1559 
    1560     return IEMTB_F_TYPE_THREADED | IEMTB_F_CS_LIM_CHECKS;
     1571    { /* done */ }
     1572    else if (RT_LIKELY(   pVCpu->cpum.GstCtx.eip < pVCpu->cpum.GstCtx.cs.u32Limit
     1573                       && pVCpu->cpum.GstCtx.cs.u32Limit - pVCpu->cpum.GstCtx.eip >= X86_PAGE_SIZE))
     1574    { /* done */ }
     1575    else
     1576        fRet |= IEMTB_F_CS_LIM_CHECKS;
     1577    return fRet;
    15611578}
    15621579
  • trunk/src/VBox/VMM/include/IEMInternal.h

    r100789 r100792  
    668668#define IEMTB_F_STATE_OBSOLETE          UINT32_C(0x0c000000)
    669669
     670/** Set when we're starting the block in an "interrupt shadow".
     671 * We don't need to distingish between the two types of this mask, thus the one.
     672 * @see CPUMCTX_INHIBIT_SHADOW, CPUMIsInInterruptShadow() */
     673#define IEMTB_F_INHIBIT_SHADOW          UINT32_C(0x10000000)
     674/** Set when we're currently inhibiting NMIs
     675 * @see CPUMCTX_INHIBIT_NMI, CPUMAreInterruptsInhibitedByNmi() */
     676#define IEMTB_F_INHIBIT_NMI             UINT32_C(0x20000000)
     677
    670678/** Checks that EIP/IP is wihin CS.LIM before each instruction.  Used when
    671679 * we're close the limit before starting a TB, as determined by
    672680 * iemGetTbFlagsForCurrentPc(). */
    673 #define IEMTB_F_CS_LIM_CHECKS           UINT32_C(0x10000000)
     681#define IEMTB_F_CS_LIM_CHECKS           UINT32_C(0x40000000)
    674682
    675683/** Mask of the IEMTB_F_XXX flags that are part of the TB lookup key.
Note: See TracChangeset for help on using the changeset viewer.

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