VirtualBox

Changeset 90608 in vbox


Ignore:
Timestamp:
Aug 10, 2021 9:33:32 PM (3 years ago)
Author:
vboxsync
Message:

VMM/PDMCritSecRw: Some code refactoring. bugref:6695

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

Legend:

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

    r90572 r90608  
    508508     * account when waiting on contended locks.
    509509     *
    510      * While we usually (it can be VINF_SUCCESS) have to option via the rcBusy
    511      * parameter of going to back to ring-3 and to re-start the work there, it's
    512      * almost always more efficient to try wait for the lock here.  The rcBusy
    513      * will be used if we encounter an VERR_INTERRUPTED situation though.
    514      *
    515      * We must never block if VMMRZCallRing3Disable is active.
     510     * While we usually (it can be VINF_SUCCESS) have the option of returning
     511     * rcBusy and force the caller to go back to ring-3 and to re-start the work
     512     * there, it's almost always more efficient to try wait for the lock here.
     513     * The rcBusy will be used if we encounter an VERR_INTERRUPTED situation
     514     * though.
    516515     */
    517516    PVMCPUCC pVCpu = VMMGetCpu(pVM);
  • trunk/src/VBox/VMM/VMMAll/PDMAllCritSectRw.cpp

    r90573 r90608  
    734734
    735735/**
     736 * Worker for pdmCritSectRwEnterExcl that bails out on wait failure.
     737 *
     738 * @returns @a rc unless corrupted.
     739 * @param   pVM         The cross context VM structure.
     740 * @param   rc          The status to return.
     741 */
     742DECL_NO_INLINE(static, int) pdmCritSectRwEnterExclBailOut(PPDMCRITSECTRW pThis, int rc)
     743{
     744    /*
     745     * Decrement the counts and return the error.
     746     */
     747    for (;;)
     748    {
     749        uint64_t       u64State    = ASMAtomicReadU64(&pThis->s.Core.u64State);
     750        uint64_t const u64OldState = u64State;
     751        uint64_t c                 = (u64State & RTCSRW_CNT_WR_MASK) >> RTCSRW_CNT_WR_SHIFT;
     752        AssertReturn(c > 0, pdmCritSectRwCorrupted(pThis, "Invalid write count on bailout"));
     753        c--;
     754        u64State &= ~RTCSRW_CNT_WR_MASK;
     755        u64State |= c << RTCSRW_CNT_WR_SHIFT;
     756        if (ASMAtomicCmpXchgU64(&pThis->s.Core.u64State, u64State, u64OldState))
     757            return rc;
     758
     759        ASMNopPause();
     760        AssertReturn(pThis->s.Core.u32Magic == RTCRITSECTRW_MAGIC, VERR_SEM_DESTROYED);
     761        ASMNopPause();
     762    }
     763}
     764
     765
     766/**
    736767 * Worker that enters a read/write critical section with exclusive access.
    737768 *
     
    879910           )
    880911        {
    881 
    882912            /*
    883913             * Wait for our turn.
     
    918948                }
    919949                if (RT_FAILURE(rc))
    920                 {
    921                     /* Decrement the counts and return the error. */
    922                     for (;;)
    923                     {
    924                         u64OldState = u64State = ASMAtomicReadU64(&pThis->s.Core.u64State);
    925                         uint64_t c = (u64State & RTCSRW_CNT_WR_MASK) >> RTCSRW_CNT_WR_SHIFT;
    926                         AssertReturn(c > 0, pdmCritSectRwCorrupted(pThis, "Invalid write count on bailout"));
    927                         c--;
    928                         u64State &= ~RTCSRW_CNT_WR_MASK;
    929                         u64State |= c << RTCSRW_CNT_WR_SHIFT;
    930                         if (ASMAtomicCmpXchgU64(&pThis->s.Core.u64State, u64State, u64OldState))
    931                             break;
    932                     }
    933                     return rc;
    934                 }
    935 
     950                    return pdmCritSectRwEnterExclBailOut(pThis, rc);
     951
     952                /* Try take exclusive write ownership. */
    936953                u64State = ASMAtomicReadU64(&pThis->s.Core.u64State);
    937954                if ((u64State & RTCSRW_DIR_MASK) == (RTCSRW_DIR_WRITE << RTCSRW_DIR_SHIFT))
     
    950967#ifdef IN_RING3
    951968            /* TryEnter call - decrement the number of (waiting) writers.  */
     969            return pdmCritSectRwEnterExclBailOut(pThis, VERR_SEM_BUSY);
    952970#else
    953971            /* We cannot call SUPSemEventWaitNoResume in this context. Go back to
    954972               ring-3 and do it there or return rcBusy. */
    955 #endif
    956 
    957             for (;;)
    958             {
    959                 u64OldState = u64State = ASMAtomicReadU64(&pThis->s.Core.u64State);
    960                 uint64_t c = (u64State & RTCSRW_CNT_WR_MASK) >> RTCSRW_CNT_WR_SHIFT;
    961                 AssertReturn(c > 0, pdmCritSectRwCorrupted(pThis, "Invalid write count on bailout"));
    962                 c--;
    963                 u64State &= ~RTCSRW_CNT_WR_MASK;
    964                 u64State |= c << RTCSRW_CNT_WR_SHIFT;
    965                 if (ASMAtomicCmpXchgU64(&pThis->s.Core.u64State, u64State, u64OldState))
    966                     break;
    967             }
    968 
    969 #ifdef IN_RING3
    970             return VERR_SEM_BUSY;
    971 #else
     973            rcBusy = pdmCritSectRwEnterExclBailOut(pThis, rcBusy);
    972974            if (rcBusy == VINF_SUCCESS)
    973975            {
     
    987989     */
    988990    Assert((ASMAtomicReadU64(&pThis->s.Core.u64State) & RTCSRW_DIR_MASK) == (RTCSRW_DIR_WRITE << RTCSRW_DIR_SHIFT));
     991#if 1 /** @todo consider generating less noise... */
    989992    ASMAtomicWriteU32(&pThis->s.Core.cWriteRecursions, 1);
     993#else
     994    pThis->s.Core.cWriteRecursions = 1;
     995#endif
    990996    Assert(pThis->s.Core.cWriterReads == 0);
    991997#if defined(PDMCRITSECTRW_STRICT) && defined(IN_RING3)
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