VirtualBox

Changeset 34386 in vbox


Ignore:
Timestamp:
Nov 25, 2010 5:10:52 PM (14 years ago)
Author:
vboxsync
Message:

PBMBlkCache: Bug fixes

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/PDMBlkCache.cpp

    r34347 r34386  
    10131013                    {
    10141014                        /* Arm the timer if this is the first endpoint. */
    1015                         if (   pBlkCacheGlobal->cRefs == 1
     1015                        if (   !pBlkCacheGlobal->cRefs
    10161016                            && pBlkCacheGlobal->u32CommitTimeoutMs > 0)
    10171017                            rc = TMTimerSetMillies(pBlkCacheGlobal->pTimerCommit, pBlkCacheGlobal->u32CommitTimeoutMs);
     
    12081208    PPDMBLKCACHEGLOBAL pCache = pBlkCache->pCache;
    12091209
     1210    /*
     1211     * Commit all dirty entries now (they are waited on for completion during the
     1212     * destruction of the AVL tree below).
     1213     * The exception is if the VM was paused because of an I/O error before.
     1214     */
     1215    if (!ASMAtomicReadBool(&pCache->fIoErrorVmSuspended))
     1216        pdmBlkCacheCommit(pBlkCache);
     1217
    12101218    /* Make sure nobody is accessing the cache while we delete the tree. */
    12111219    pdmBlkCacheLockEnter(pCache);
     
    13511359 * @param   pEntryAbove       Where to store the pointer to the best fit entry above the
    13521360 *                            the given offset. NULL if not required.
    1353  * @param   pEntryBelow       Where to store the pointer to the best fit entry below the
    1354  *                            the given offset. NULL if not required.
    13551361 */
    13561362static void pdmBlkCacheGetCacheBestFitEntryByOffset(PPDMBLKCACHE pBlkCache, uint64_t off,
    1357                                                     PPDMBLKCACHEENTRY *ppEntryAbove,
    1358                                                     PPDMBLKCACHEENTRY *ppEntryBelow)
     1363                                                    PPDMBLKCACHEENTRY *ppEntryAbove)
    13591364{
    13601365    PPDMBLKCACHEGLOBAL pCache = pBlkCache->pCache;
     
    13701375    }
    13711376
    1372     if (ppEntryBelow)
    1373     {
    1374         *ppEntryBelow = (PPDMBLKCACHEENTRY)RTAvlrU64GetBestFit(pBlkCache->pTree, off, false /*fAbove*/);
    1375         if (*ppEntryBelow)
    1376             pdmBlkCacheEntryRef(*ppEntryBelow);
    1377     }
    13781377    RTSemRWReleaseRead(pBlkCache->SemRWEntries);
    13791378
     
    15171516static int pdmBlkCacheEntryWaitersAdd(PPDMBLKCACHEENTRY pEntry,
    15181517                                      PPDMBLKCACHEREQ pReq,
    1519                                       PCRTSGBUF pSgBuf, uint64_t offDiff,
     1518                                      PRTSGBUF pSgBuf, uint64_t offDiff,
    15201519                                      size_t cbData, bool fWrite)
    15211520{
     
    15301529    pWaiter->fWrite        = fWrite;
    15311530    RTSgBufClone(&pWaiter->SgBuf, pSgBuf);
     1531    RTSgBufAdvance(pSgBuf, cbData);
    15321532
    15331533    pdmBlkCacheEntryAddWaiter(pEntry, pWaiter);
     
    15601560    uint64_t offAligned;
    15611561    PPDMBLKCACHEENTRY pEntryAbove = NULL;
    1562     PPDMBLKCACHEENTRY pEntryBelow = NULL;
    15631562
    15641563    /* Get the best fit entries around the offset */
    1565     pdmBlkCacheGetCacheBestFitEntryByOffset(pBlkCache, off, &pEntryAbove, &pEntryBelow);
     1564    pdmBlkCacheGetCacheBestFitEntryByOffset(pBlkCache, off, &pEntryAbove);
    15661565
    15671566    /* Log the info */
    1568     LogFlow(("%sest fit entry below off=%llu (BestFit=%llu BestFitEnd=%llu BestFitSize=%u)\n",
    1569              pEntryBelow ? "B" : "No b",
    1570              off,
    1571              pEntryBelow ? pEntryBelow->Core.Key : 0,
    1572              pEntryBelow ? pEntryBelow->Core.KeyLast : 0,
    1573              pEntryBelow ? pEntryBelow->cbData : 0));
    1574 
    15751567    LogFlow(("%sest fit entry above off=%llu (BestFit=%llu BestFitEnd=%llu BestFitSize=%u)\n",
    15761568             pEntryAbove ? "B" : "No b",
     
    15801572             pEntryAbove ? pEntryAbove->cbData : 0));
    15811573
    1582     /* Align the offset first. */
    1583     offAligned = off & ~(uint64_t)(512-1);
    1584     if (   pEntryBelow
    1585         && offAligned <= pEntryBelow->Core.KeyLast)
    1586         offAligned = pEntryBelow->Core.KeyLast;
     1574    offAligned = off;
    15871575
    15881576    if (    pEntryAbove
     
    15991587
    16001588    /* A few sanity checks */
    1601     AssertMsg(!pEntryBelow || pEntryBelow->Core.KeyLast < offAligned,
    1602               ("Aligned start offset intersects with another cache entry\n"));
    16031589    AssertMsg(!pEntryAbove || (offAligned + cbAligned) <= pEntryAbove->Core.Key,
    16041590              ("Aligned size intersects with another cache entry\n"));
    16051591    Assert(cbInEntry <= cbAligned);
    16061592
    1607     if (pEntryBelow)
    1608         pdmBlkCacheEntryRelease(pEntryBelow);
    16091593    if (pEntryAbove)
    16101594        pdmBlkCacheEntryRelease(pEntryAbove);
     
    19331917            /* Clip read size if necessary. */
    19341918            PPDMBLKCACHEENTRY pEntryAbove;
    1935             pdmBlkCacheGetCacheBestFitEntryByOffset(pBlkCache, off,
    1936                                                     &pEntryAbove, NULL);
     1919            pdmBlkCacheGetCacheBestFitEntryByOffset(pBlkCache, off, &pEntryAbove);
    19371920
    19381921            if (pEntryAbove)
     
    20192002            {
    20202003                /* Check if the entry is dirty. */
    2021                 if(pdmBlkCacheEntryFlagIsSetClearAcquireLock(pBlkCache, pEntry,
    2022                                                              PDMBLKCACHE_ENTRY_IS_DIRTY,
    2023                                                              0))
     2004                if (pdmBlkCacheEntryFlagIsSetClearAcquireLock(pBlkCache, pEntry,
     2005                                                              PDMBLKCACHE_ENTRY_IS_DIRTY,
     2006                                                              0))
    20242007                {
    20252008                    /* If it is already dirty but not in progress just update the data. */
     
    22722255         * the user fixed the problem and the next write succeeds.
    22732256         */
    2274         /** @todo r=aeichner: This solution doesn't work
    2275          * The user will get the message but the VM will hang afterwards
    2276          * VMR3Suspend() returns when the VM is suspended but suspending
    2277          * the VM will reopen the images readonly in DrvVD. They are closed first
    2278          * which will close the endpoints. This will block EMT while the
    2279          * I/O manager processes the close request but the IO manager is stuck
    2280          * in the VMR3Suspend call and can't process the request.
    2281          * Another problem is that closing the VM means flushing the cache
    2282          * but the entry failed and will probably fail again.
    2283          * No idea so far how to solve this problem... but the user gets informed
    2284          * at least.
    2285          */
    22862257        if (RT_FAILURE(rcIoXfer))
    22872258        {
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