VirtualBox

Changeset 41469 in vbox for trunk/src


Ignore:
Timestamp:
May 28, 2012 10:58:48 PM (13 years ago)
Author:
vboxsync
Message:

AsyncCompletion: enhance injectdelay debugger command to delay multiple requests at once

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

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMR3/PDMAsyncCompletionFile.cpp

    r41434 r41469  
    4444#include "PDMAsyncCompletionFileInternal.h"
    4545
    46 
    4746/*******************************************************************************
    4847*   Internal Functions                                                         *
     
    7170{
    7271    /* cTimesMin,   cTimesMax,  enmCategory,            fFlags,                         pszName,        pszDescription */
    73     {  1,           1,          DBGCVAR_CAT_STRING,     0,                              "direction",    "write/read." },
     72    {  1,           1,          DBGCVAR_CAT_STRING,     0,                              "direction",    "write|read|flush|any." },
    7473    {  1,           1,          DBGCVAR_CAT_STRING,     0,                              "filename",     "Filename." },
    7574    {  1,           1,          DBGCVAR_CAT_NUMBER,     0,                              "delay",        "Delay in milliseconds." },
     75    {  1,           1,          DBGCVAR_CAT_NUMBER,     0,                              "reqs",         "Number of requests to delay." },
    7676};
    7777# endif
     
    8383    { "injecterror",        3, 3,        &g_aInjectErrorArgs[0],           3,      0, pdmacEpFileErrorInject, "",        "Inject error into I/O subsystem." }
    8484# ifdef PDM_ASYNC_COMPLETION_FILE_WITH_DELAY
    85     ,{ "injectdelay",        3, 3,        &g_aInjectDelayArgs[0],           3,      0, pdmacEpFileDelayInject, "",        "Inject a delay of a request." }
     85    ,{ "injectdelay",        4, 4,        &g_aInjectDelayArgs[0],           4,      0, pdmacEpFileDelayInject, "",        "Inject a delay of a request." }
    8686# endif
    8787};
     
    334334            /* Check if we should delay completion of the request. */
    335335            if (   ASMAtomicReadU32(&pEpFile->msDelay) > 0
    336                 && ASMAtomicCmpXchgPtr(&pEpFile->pReqDelayed, pTaskFile, NULL))
     336                && ASMAtomicReadU32(&pEpFile->cReqsDelay) > 0)
    337337            {
     338                ASMAtomicDecU32(&pEpFile->cReqsDelay);
     339
    338340                /* Arm the delay. */
    339                 pEpFile->tsDelayEnd = RTTimeProgramMilliTS() + pEpFile->msDelay;
     341                pTaskFile->tsDelayEnd = RTTimeProgramMilliTS() + pEpFile->msDelay;
     342
     343                /* Append to the list. */
     344                PPDMASYNCCOMPLETIONTASKFILE pHead = NULL;
     345                do
     346                {
     347                    pHead = ASMAtomicReadPtrT(&pEpFile->pDelayedHead, PPDMASYNCCOMPLETIONTASKFILE);
     348                    pTaskFile->pDelayedNext = pHead;
     349                } while (!ASMAtomicCmpXchgPtr(&pEpFile->pDelayedHead, pTaskFile, pHead));
     350
    340351                LogRel(("AIOMgr: Delaying request %#p for %u ms\n", pTaskFile, pEpFile->msDelay));
    341352                return;
     
    344355            pdmR3AsyncCompletionCompleteTask(&pTaskFile->Core, pTaskFile->rc, true);
    345356
    346 #if PDM_ASYNC_COMPLETION_FILE_WITH_DELAY
     357#ifdef PDM_ASYNC_COMPLETION_FILE_WITH_DELAY
    347358            /* Check for an expired delay. */
    348             if (   pEpFile->pReqDelayed != NULL
    349                 && RTTimeProgramMilliTS() >= pEpFile->tsDelayEnd)
     359            if (pEpFile->pDelayedHead != NULL)
    350360            {
    351                 pTaskFile = ASMAtomicXchgPtrT(&pEpFile->pReqDelayed, NULL, PPDMASYNCCOMPLETIONTASKFILE);
    352                 ASMAtomicXchgU32(&pEpFile->msDelay, 0);
    353                 LogRel(("AIOMgr: Delayed request %#p completed\n", pTaskFile));
    354                 pdmR3AsyncCompletionCompleteTask(&pTaskFile->Core, pTaskFile->rc, true);
     361                uint64_t tsCur = RTTimeProgramMilliTS();
     362                pTaskFile = ASMAtomicXchgPtrT(&pEpFile->pDelayedHead, NULL, PPDMASYNCCOMPLETIONTASKFILE);
     363
     364                while (pTaskFile)
     365                {
     366                    PPDMASYNCCOMPLETIONTASKFILE pTmp = pTaskFile;
     367                    pTaskFile = pTaskFile->pDelayedNext;
     368
     369                    if (tsCur >= pTmp->tsDelayEnd)
     370                    {
     371                        LogRel(("AIOMgr: Delayed request %#p completed\n", pTmp));
     372                        pdmR3AsyncCompletionCompleteTask(&pTmp->Core, pTmp->rc, true);
     373                    }
     374                    else
     375                    {
     376                        /* Prepend to the delayed list again. */
     377                        PPDMASYNCCOMPLETIONTASKFILE pHead = NULL;
     378                        do
     379                        {
     380                            pHead = ASMAtomicReadPtrT(&pEpFile->pDelayedHead, PPDMASYNCCOMPLETIONTASKFILE);
     381                            pTmp->pDelayedNext = pHead;
     382                        } while (!ASMAtomicCmpXchgPtr(&pEpFile->pDelayedHead, pTmp, pHead));
     383                    }
     384                }
    355385            }
    356386#endif
     
    671701     */
    672702    DBGC_CMDHLP_REQ_VM_RET(pCmdHlp, pCmd, pVM);
    673     DBGC_CMDHLP_ASSERT_PARSER_RET(pCmdHlp, pCmd, -1, cArgs == 3);
     703    DBGC_CMDHLP_ASSERT_PARSER_RET(pCmdHlp, pCmd, -1, cArgs >= 3);
    674704    DBGC_CMDHLP_ASSERT_PARSER_RET(pCmdHlp, pCmd, 0, pArgs[0].enmType == DBGCVAR_TYPE_STRING);
    675705    DBGC_CMDHLP_ASSERT_PARSER_RET(pCmdHlp, pCmd, 1, pArgs[1].enmType == DBGCVAR_TYPE_STRING);
     
    679709    pEpClassFile = (PPDMASYNCCOMPLETIONEPCLASSFILE)pVM->pUVM->pdm.s.apAsyncCompletionEndpointClass[PDMASYNCCOMPLETIONEPCLASSTYPE_FILE];
    680710
    681     /* Syntax is "read|write <filename> <status code>" */
    682     bool fWrite;
     711    /* Syntax is "read|write|flush|any <filename> <delay> [reqs]" */
     712    PDMACFILEREQTYPEDELAY enmDelayType = PDMACFILEREQTYPEDELAY_ANY;
    683713    if (!RTStrCmp(pArgs[0].u.pszString, "read"))
    684         fWrite = false;
     714        enmDelayType = PDMACFILEREQTYPEDELAY_READ;
    685715    else if (!RTStrCmp(pArgs[0].u.pszString, "write"))
    686         fWrite = true;
     716        enmDelayType = PDMACFILEREQTYPEDELAY_WRITE;
     717    else if (!RTStrCmp(pArgs[0].u.pszString, "flush"))
     718        enmDelayType = PDMACFILEREQTYPEDELAY_FLUSH;
     719    else if (!RTStrCmp(pArgs[0].u.pszString, "any"))
     720        enmDelayType = PDMACFILEREQTYPEDELAY_ANY;
    687721    else
    688722        return DBGCCmdHlpFail(pCmdHlp, pCmd, "invalid transfer direction '%s'", pArgs[0].u.pszString);
     
    692726        return DBGCCmdHlpFail(pCmdHlp, pCmd, "The delay '%lld' is out of range", pArgs[0].u.u64Number);
    693727
     728    uint32_t cReqsDelay = 1;
     729    if (cArgs == 4)
     730        cReqsDelay = (uint32_t)pArgs[3].u.u64Number;
    694731
    695732    /*
     
    708745    if (pEpFile)
    709746    {
    710         bool fXchg = ASMAtomicCmpXchgU32(&pEpFile->msDelay, msDelay, 0);
    711 
    712         if (fXchg)
    713             DBGCCmdHlpPrintf(pCmdHlp, "Injected delay of %u ms into '%s' for %s\n",
    714                              msDelay, pArgs[1].u.pszString, pArgs[0].u.pszString);
    715         else
    716             DBGCCmdHlpPrintf(pCmdHlp, "Another delay for '%s' is still active, ignoring\n",
    717                              pArgs[1].u.pszString);
     747        ASMAtomicWriteSize(&pEpFile->enmTypeDelay, enmDelayType);
     748        ASMAtomicWriteU32(&pEpFile->msDelay, msDelay);
     749        ASMAtomicWriteU32(&pEpFile->cReqsDelay, cReqsDelay);
     750
     751        DBGCCmdHlpPrintf(pCmdHlp, "Injected delay for the next %u requests of %u ms into '%s' for %s\n",
     752                         cReqsDelay, msDelay, pArgs[1].u.pszString, pArgs[0].u.pszString);
    718753    }
    719754
  • trunk/src/VBox/VMM/include/PDMAsyncCompletionFileInternal.h

    r39078 r41469  
    311311} PDMASYNCCOMPLETIONENDPOINTFILESTATE;
    312312
     313typedef enum PDMACFILEREQTYPEDELAY
     314{
     315    PDMACFILEREQTYPEDELAY_ANY = 0,
     316    PDMACFILEREQTYPEDELAY_READ,
     317    PDMACFILEREQTYPEDELAY_WRITE,
     318    PDMACFILEREQTYPEDELAY_FLUSH,
     319    PDMACFILEREQTYPEDELAY_32BIT_HACK = 0x7fffffff
     320} PDMACFILEREQTYPEDELAY;
     321
    313322/**
    314323 * Data for the file endpoint.
     
    371380    /** Request delay. */
    372381    volatile uint32_t                      msDelay;
     382    /** Number of requests to delay. */
     383    volatile uint32_t                      cReqsDelay;
     384    /** Task type to delay. */
     385    PDMACFILEREQTYPEDELAY                  enmTypeDelay;
    373386    /** The current task which gets delayed. */
    374     PPDMASYNCCOMPLETIONTASKFILE            pReqDelayed;
    375     /** Timestamp when the delay expires. */
    376     uint64_t                               tsDelayEnd;
     387    PPDMASYNCCOMPLETIONTASKFILE            pDelayedHead;
    377388#endif
    378389    /** Flag whether a blocking event is pending and needs
     
    498509    /** Return code. */
    499510    volatile int          rc;
     511#ifdef PDM_ASYNC_COMPLETION_FILE_WITH_DELAY
     512    volatile PPDMASYNCCOMPLETIONTASKFILE pDelayedNext;
     513    /** Timestamp when the delay expires. */
     514    uint64_t                             tsDelayEnd;
     515#endif
    500516} PDMASYNCCOMPLETIONTASKFILE;
    501517
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