VirtualBox

Changeset 106090 in vbox for trunk/src/VBox/VMM/VMMAll


Ignore:
Timestamp:
Sep 19, 2024 9:13:54 AM (8 months ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
164865
Message:

VMM/IEM: More liveness work for delayed eflags updating. bugref:10720 bugref:10372

Location:
trunk/src/VBox/VMM/VMMAll
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMAll/IEMAllN8veLiveness.h

    r106078 r106090  
    6565        IEMLIVENESSENTRY LiveState       = { { 0, 0, 0, 0 } }; \
    6666        IEMLIVENESSBIT   LiveMask        = { 0 }; \
    67         bool             fDoneXpctOrCall = false
     67        bool             fNoInherit      = false
    6868#endif
    6969
     
    8585#else
    8686# define IEM_LIVENESS_MARK_POTENTIAL_CALL() do { \
    87             if (!fDoneXpctOrCall) \
    88             { \
    89                 LiveState.aBits[IEMLIVENESS_BIT_READ].bm64 |= pIncoming->aBits[IEMLIVENESS_BIT_READ].bm64 & ~LiveMask.bm64; \
    90                 LiveMask.bm64   |= IEMLIVENESSBIT_MASK; \
    91                 fDoneXpctOrCall  = true; \
    92             } \
    9387            LiveState.aBits[IEMLIVENESS_BIT_POTENTIAL_CALL].bm64 |= IEMLIVENESSBIT_MASK; \
    9488        } while (0)
    9589# define IEM_LIVENESS_MARK_CALL() do { \
    96             if (!fDoneXpctOrCall) \
    97             { \
    98                 LiveState.aBits[IEMLIVENESS_BIT_READ].bm64 |= pIncoming->aBits[IEMLIVENESS_BIT_READ].bm64 & ~LiveMask.bm64; \
    99                 LiveMask.bm64   |= IEMLIVENESSBIT_MASK; \
    100                 fDoneXpctOrCall  = true; \
    101             } \
    10290            LiveState.aBits[IEMLIVENESS_BIT_CALL].bm64 |= IEMLIVENESSBIT_MASK; \
     91            LiveMask.bm64                              |= IEMLIVENESSBIT_MASK; \
     92            fNoInherit                                  = true; /* full mask */ \
    10393        } while (0)
    10494#endif
     
    285275#else
    286276# define IEM_MC_END() \
    287         /* Combine the incoming state with what we've accumulated in this block. */ \
    288         /* We can help the compiler by skipping OR'ing when having applied XPCT_OR_CALL, */ \
    289         /* since that already imports all the incoming state. Saves a lot with cl.exe. */ \
    290         if (!fDoneXpctOrCall) \
     277        /* Use the mask to effect inheriting. */ \
     278        if (!fNoInherit) \
    291279        { \
     280            uint64_t const fInhMask = ~LiveMask.bm64; \
    292281            pOutgoing->aBits[IEMLIVENESS_BIT_POTENTIAL_CALL].bm64 = LiveState.aBits[IEMLIVENESS_BIT_POTENTIAL_CALL].bm64 \
    293                                                          | (~LiveMask.bm64 & pIncoming->aBits[IEMLIVENESS_BIT_POTENTIAL_CALL].bm64); \
    294             pOutgoing->aBits[IEMLIVENESS_BIT_READ].bm64  = LiveState.aBits[IEMLIVENESS_BIT_READ].bm64 \
    295                                                          | (~LiveMask.bm64 & pIncoming->aBits[IEMLIVENESS_BIT_READ].bm64); \
     282                                                                | (pIncoming->aBits[IEMLIVENESS_BIT_POTENTIAL_CALL].bm64 & fInhMask); \
     283            pOutgoing->aBits[IEMLIVENESS_BIT_READ ].bm64 = LiveState.aBits[IEMLIVENESS_BIT_READ ].bm64 \
     284                                                       | (pIncoming->aBits[IEMLIVENESS_BIT_READ ].bm64 & fInhMask); \
    296285            pOutgoing->aBits[IEMLIVENESS_BIT_WRITE].bm64 = LiveState.aBits[IEMLIVENESS_BIT_WRITE].bm64 \
    297                                                          | (~LiveMask.bm64 & pIncoming->aBits[IEMLIVENESS_BIT_WRITE].bm64); \
    298             pOutgoing->aBits[IEMLIVENESS_BIT_CALL].bm64  = LiveState.aBits[IEMLIVENESS_BIT_CALL].bm64 \
    299                                                          | (~LiveMask.bm64 & pIncoming->aBits[IEMLIVENESS_BIT_CALL].bm64); \
     286                                                       | (pIncoming->aBits[IEMLIVENESS_BIT_WRITE].bm64 & fInhMask); \
     287            pOutgoing->aBits[IEMLIVENESS_BIT_CALL ].bm64 = LiveState.aBits[IEMLIVENESS_BIT_CALL ].bm64 \
     288                                                       | (pIncoming->aBits[IEMLIVENESS_BIT_CALL ].bm64 & fInhMask); \
    300289        } \
    301290        else \
  • trunk/src/VBox/VMM/VMMAll/IEMAllN8veRecompBltIn.cpp

    r106078 r106090  
    190190IEM_DECL_IEMNATIVELIVENESSFUNC_DEF(iemNativeLivenessFunc_BltIn_DeferToCImpl0)
    191191{
    192     IEM_LIVENESS_RAW_INIT_WITH_CALL_AND_POTENTIAL_CALL(pOutgoing, pIncoming);
     192    IEM_LIVENESS_RAW_INIT_WITH_CALL(pOutgoing, pIncoming);
    193193    RT_NOREF(pCallEntry);
    194194}
     
    393393    IEM_LIVENESS_RAW_INIT_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    394394    IEM_LIVENESS_RAW_EFLAGS_ONE_INPUT(pOutgoing, fEflOther);
     395    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    395396    RT_NOREF(pCallEntry);
    396397}
     
    411412{
    412413    IEM_LIVENESS_RAW_INIT_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
     414    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    413415    RT_NOREF(pCallEntry);
    414416}
     
    429431    IEM_LIVENESS_RAW_INIT_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    430432    IEM_LIVENESS_RAW_EFLAGS_ONE_INPUT(pOutgoing, fEflOther);
     433    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    431434    RT_NOREF(pCallEntry);
    432435}
     
    455458{
    456459    IEM_LIVENESS_RAW_INIT_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
     460    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    457461    RT_NOREF(pCallEntry);
    458462}
     
    17911795    IEM_LIVENESS_RAW_INIT_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    17921796    LIVENESS_CHECK_CS_LIM(pOutgoing);
     1797    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    17931798    RT_NOREF(pCallEntry);
    17941799}
     
    18191824    LIVENESS_CHECK_CS_LIM(pOutgoing);
    18201825    LIVENESS_CHECK_OPCODES(pOutgoing);
     1826    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    18211827    RT_NOREF(pCallEntry);
    18221828}
     
    18451851    IEM_LIVENESS_RAW_INIT_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    18461852    LIVENESS_CHECK_OPCODES(pOutgoing);
     1853    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    18471854    RT_NOREF(pCallEntry);
    18481855}
     
    18731880    LIVENESS_CONSIDER_CS_LIM_CHECKING(pOutgoing);
    18741881    LIVENESS_CHECK_OPCODES(pOutgoing);
     1882    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    18751883    RT_NOREF(pCallEntry);
    18761884}
     
    19111919    LIVENESS_CHECK_PC_AFTER_BRANCH(pOutgoing, pCallEntry);
    19121920    LIVENESS_CHECK_OPCODES(pOutgoing);
     1921    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    19131922    RT_NOREF(pCallEntry);
    19141923}
     
    19431952    LIVENESS_CHECK_PC_AFTER_BRANCH(pOutgoing, pCallEntry);
    19441953    LIVENESS_CHECK_OPCODES(pOutgoing);
     1954    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    19451955    RT_NOREF(pCallEntry);
    19461956}
     
    19781988    LIVENESS_CHECK_PC_AFTER_BRANCH(pOutgoing, pCallEntry);
    19791989    LIVENESS_CHECK_OPCODES(pOutgoing);
     1990    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    19801991    RT_NOREF(pCallEntry);
    19811992}
     
    20162027    LIVENESS_LOAD_TLB_AFTER_BRANCH(pOutgoing, pCallEntry);
    20172028    LIVENESS_CHECK_OPCODES(pOutgoing);
     2029    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    20182030    RT_NOREF(pCallEntry);
    20192031}
     
    20522064    LIVENESS_LOAD_TLB_AFTER_BRANCH(pOutgoing, pCallEntry);
    20532065    LIVENESS_CHECK_OPCODES(pOutgoing);
     2066    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    20542067    RT_NOREF(pCallEntry);
    20552068}
     
    20902103    LIVENESS_LOAD_TLB_AFTER_BRANCH(pOutgoing, pCallEntry);
    20912104    LIVENESS_CHECK_OPCODES(pOutgoing);
     2105    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    20922106    RT_NOREF(pCallEntry);
    20932107}
     
    21342148    LIVENESS_CHECK_OPCODES(pOutgoing);
    21352149    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
     2150    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    21362151    RT_NOREF(pCallEntry);
    21372152}
     
    21712186    LIVENESS_CHECK_OPCODES(pOutgoing);
    21722187    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
     2188    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    21732189    RT_NOREF(pCallEntry);
    21742190}
     
    22112227    LIVENESS_CHECK_OPCODES(pOutgoing);
    22122228    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
     2229    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    22132230    RT_NOREF(pCallEntry);
    22142231}
     
    22472264    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
    22482265    LIVENESS_CHECK_OPCODES(pOutgoing);
     2266    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    22492267    RT_NOREF(pCallEntry);
    22502268}
     
    22812299    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
    22822300    LIVENESS_CHECK_OPCODES(pOutgoing);
     2301    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    22832302    RT_NOREF(pCallEntry);
    22842303}
     
    23172336    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
    23182337    LIVENESS_CHECK_OPCODES(pOutgoing);
     2338    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    23192339    RT_NOREF(pCallEntry);
    23202340}
     
    23492369    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
    23502370    LIVENESS_CHECK_OPCODES(pOutgoing);
     2371    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    23512372    RT_NOREF(pCallEntry);
    23522373}
     
    23792400    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
    23802401    LIVENESS_CHECK_OPCODES(pOutgoing);
     2402    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    23812403    RT_NOREF(pCallEntry);
    23822404}
     
    24122434    LIVENESS_LOAD_TLB_FOR_NEW_PAGE(pOutgoing, pCallEntry);
    24132435    LIVENESS_CHECK_OPCODES(pOutgoing);
     2436    IEM_LIVENESS_RAW_FINISH_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    24142437    RT_NOREF(pCallEntry);
    24152438}
     
    24592482IEM_DECL_IEMNATIVELIVENESSFUNC_DEF(iemNativeLivenessFunc_BltIn_Jump)
    24602483{
    2461     /** @todo This isn't right:    */
    2462     IEM_LIVENESS_RAW_INIT_WITH_POTENTIAL_CALL(pOutgoing, pIncoming);
    2463     RT_NOREF(pCallEntry);
    2464 }
    2465 
     2484    /* We could also use UNUSED here, but this'll is equivialent (at the moment). */
     2485    IEM_LIVENESS_RAW_INIT_WITH_CALL(pOutgoing, pIncoming);
     2486    RT_NOREF(pCallEntry);
     2487}
     2488
  • trunk/src/VBox/VMM/VMMAll/IEMAllN8veRecompFuncs.h

    r106078 r106090  
    58125812        {
    58135813              pLivenessEntry->aBits[IEMLIVENESS_BIT_POTENTIAL_CALL].bm64
     5814            & pLivenessEntry->aBits[IEMLIVENESS_BIT_WRITE].bm64
    58145815            & ~(  pLivenessEntry->aBits[IEMLIVENESS_BIT_READ].bm64
    58155816                | pLivenessEntry->aBits[IEMLIVENESS_BIT_CALL].bm64)
  • trunk/src/VBox/VMM/VMMAll/IEMAllN8veRecompiler.cpp

    r106078 r106090  
    31733173#ifdef IEMNATIVE_WITH_LIVENESS_ANALYSIS
    31743174        /*
    3175          * When we have livness information, we use it to kick out all shadowed
     3175         * When we have liveness information, we use it to kick out all shadowed
    31763176         * guest register that will not be needed any more in this TB.  If we're
    31773177         * lucky, this may prevent us from ending up here again.
     
    31853185        {
    31863186            PCIEMLIVENESSENTRY const pLivenessEntry = &pReNative->paLivenessEntries[idxCurCall - 1];
    3187 
    3188 # ifndef IEMLIVENESS_EXTENDED_LAYOUT
    3189             /* Construct a mask of the guest registers in the UNUSED and XCPT_OR_CALL state. */
    3190             AssertCompile(IEMLIVENESS_STATE_UNUSED == 1 && IEMLIVENESS_STATE_XCPT_OR_CALL == 2);
    3191             uint64_t fToFreeMask = pLivenessEntry->Bit0.bm64 ^ pLivenessEntry->Bit1.bm64; /* mask of regs in either UNUSED */
    3192 #else
    3193             /* Construct a mask of the registers not in the read or write state.
    3194                Note! We could skips writes, if they aren't from us, as this is just
    3195                      a hack to prevent trashing registers that have just been written
    3196                      or will be written when we retire the current instruction. */
    3197             uint64_t fToFreeMask = ~pLivenessEntry->aBits[IEMLIVENESS_BIT_READ].bm64
    3198                                  & ~pLivenessEntry->aBits[IEMLIVENESS_BIT_WRITE].bm64
    3199                                  & IEMLIVENESSBIT_MASK;
    3200 #endif
     3187            uint64_t                 fToFreeMask    = IEMLIVENESS_STATE_GET_CAN_BE_FREED_SET(pLivenessEntry);
     3188
    32013189            /* Merge EFLAGS. */
    32023190            uint64_t fTmp = fToFreeMask & (fToFreeMask >> 3);   /* AF2,PF2,CF2,Other2 = AF,PF,CF,Other & OF,SF,ZF,AF */
     
    49444932        {
    49454933            PCIEMLIVENESSENTRY const pLivenessEntry = &pReNative->paLivenessEntries[idxCurCall - 1];
    4946 
    4947 # ifndef IEMLIVENESS_EXTENDED_LAYOUT
    4948             /* Construct a mask of the guest registers in the UNUSED and XCPT_OR_CALL state. */
    4949             AssertCompile(IEMLIVENESS_STATE_UNUSED == 1 && IEMLIVENESS_STATE_XCPT_OR_CALL == 2);
    4950             uint64_t fToFreeMask = pLivenessEntry->Bit0.bm64 ^ pLivenessEntry->Bit1.bm64; /* mask of regs in either UNUSED */
    4951 #else
    4952             /* Construct a mask of the registers not in the read or write state.
    4953                Note! We could skips writes, if they aren't from us, as this is just
    4954                      a hack to prevent trashing registers that have just been written
    4955                      or will be written when we retire the current instruction. */
    4956             uint64_t fToFreeMask = ~pLivenessEntry->aBits[IEMLIVENESS_BIT_READ].bm64
    4957                                  & ~pLivenessEntry->aBits[IEMLIVENESS_BIT_WRITE].bm64
    4958                                  & IEMLIVENESSBIT_MASK;
    4959 #endif
     4934            uint64_t const           fToFreeMask    = IEMLIVENESS_STATE_GET_CAN_BE_FREED_SET(pLivenessEntry);
     4935
    49604936            /* If it matches any shadowed registers. */
    49614937            if (pReNative->Core.bmGstRegShadows & fToFreeMask)
     
    65376513
    65386514    return off;
     6515}
     6516
     6517
     6518/**
     6519 * The default liveness function, matching iemNativeEmitThreadedCall.
     6520 */
     6521IEM_DECL_IEMNATIVELIVENESSFUNC_DEF(iemNativeLivenessFunc_ThreadedCall)
     6522{
     6523    IEM_LIVENESS_RAW_INIT_WITH_CALL(pOutgoing, pIncoming);
     6524    RT_NOREF(pCallEntry);
    65396525}
    65406526
     
    100129998        {
    100139999            PFNIEMNATIVELIVENESSFUNC const pfnLiveness = g_apfnIemNativeLivenessFunctions[pCallEntry->enmFunction];
    10014             if (pfnLiveness)
    10015                 pfnLiveness(pCallEntry, &paLivenessEntries[idxCall], &paLivenessEntries[idxCall - 1]);
    10016             else
    10017                 IEM_LIVENESS_RAW_INIT_WITH_CALL_AND_POTENTIAL_CALL(&paLivenessEntries[idxCall - 1], &paLivenessEntries[idxCall]);
     10000            Assert(pfnLiveness);
     10001            pfnLiveness(pCallEntry, &paLivenessEntries[idxCall], &paLivenessEntries[idxCall - 1]);
    1001810002            pCallEntry--;
    1001910003            idxCall--;
    1002010004        }
    10021 
    10022 # ifdef VBOX_WITH_STATISTICS
    10023         /* Check if there are any EFLAGS optimization to be had here.  This requires someone settings them
    10024            to 'clobbered' rather that 'input'.  */
    10025         /** @todo */
    10026 # endif
    1002710005    }
    1002810006#endif
     
    1014310121                static const char s_achState[] = "CUXI";
    1014410122# else
    10145                 static const char s_achState[] = "UxRrWwMmCcQqKkNn";
     10123                /*                                0123   4567   89ab   cdef */
     10124                /*                                              CCCC   CCCC */
     10125                /*                                       WWWW          WWWW */
     10126                /*                                  RR     RR     RR     RR */
     10127                /*                                 P P    P P    P P    P P */
     10128                static const char s_achState[] = "UxRr" "WwMm" "CcQq" "KkNn";
    1014610129# endif
    1014710130
  • trunk/src/VBox/VMM/VMMAll/IEMAllThrdPython.py

    r106061 r106090  
    35873587                    oOut.write('    iemNativeLivenessFunc_BltIn_%s,\n' % (sFuncNm,))
    35883588                else:
    3589                     oOut.write('    NULL, /*BltIn_%s*/\n' % (sFuncNm,))
     3589                    oOut.write('    iemNativeLivenessFunc_ThreadedCall, /*BltIn_%s*/\n' % (sFuncNm,))
    35903590
    35913591            iThreadedFunction = 1 + len(self.katBltIns);
     
    36033603                            oOut.write('    /*%4u*/ %s,\n' % (iThreadedFunction, sName,));
    36043604                        else:
    3605                             oOut.write('    /*%4u*/ NULL /*%s*/,\n' % (iThreadedFunction, sName,));
     3605                            oOut.write('    /*%4u*/ iemNativeLivenessFunc_ThreadedCall /*%s*/,\n' % (iThreadedFunction, sName,));
    36063606
    36073607            oOut.write(  '};\n'
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