VirtualBox

Changeset 64407 in vbox for trunk/src/VBox


Ignore:
Timestamp:
Oct 25, 2016 11:53:00 AM (8 years ago)
Author:
vboxsync
Message:

Devices/Storage: Add callback to query the actual transfer size of an I/O request if PDMIMEDIAEX is used, useful to calculate the amount of data transferred for requests where the transfer size can be different from the guest buffer size (e.g. SCSI)

Location:
trunk/src/VBox/Devices/Storage
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/Storage/DrvHostBase.cpp

    r64320 r64407  
    394394    if (RT_LIKELY(pReq))
    395395    {
     396        pReq->cbReq      = 0;
     397        pReq->cbResidual = 0;
    396398        *phIoReq = (PDMMEDIAEXIOREQ)pReq;
    397399        *ppvIoReqAlloc = &pReq->abAlloc[0];
     
    416418static DECLCALLBACK(int) drvHostBaseIoReqQueryResidual(PPDMIMEDIAEX pInterface, PDMMEDIAEXIOREQ hIoReq, size_t *pcbResidual)
    417419{
    418     RT_NOREF2(pInterface, hIoReq);
    419 
    420     *pcbResidual = 0; /** @todo: Implement. */
     420    RT_NOREF1(pInterface);
     421    PDRVHOSTBASEREQ pReq = (PDRVHOSTBASEREQ)hIoReq;
     422
     423    *pcbResidual = pReq->cbResidual;
     424    return VINF_SUCCESS;
     425}
     426
     427/** @interface_method_impl{PDMIMEDIAEX,pfnIoReqQueryXferSize} */
     428static DECLCALLBACK(int) drvHostBaseIoReqQueryXferSize(PPDMIMEDIAEX pInterface, PDMMEDIAEXIOREQ hIoReq, size_t *pcbXfer)
     429{
     430    RT_NOREF1(pInterface);
     431    PDRVHOSTBASEREQ pReq = (PDRVHOSTBASEREQ)hIoReq;
     432
     433    *pcbXfer = pReq->cbReq;
    421434    return VINF_SUCCESS;
    422435}
     
    444457             pThis->pDrvIns->pReg->szName, pThis->pDrvIns->iInstance, off, cbRead, pThis->pszDevice));
    445458    RTCritSectEnter(&pThis->CritSect);
     459
     460    pReq->cbReq = cbRead;
     461    pReq->cbResidual = cbRead;
    446462
    447463    /*
     
    464480                      "%16.*Rhxd\n",
    465481                      pThis->pDrvIns->pReg->szName, pThis->pDrvIns->iInstance, off, cbRead, cbRead, pvBuf));
     482
     483                pReq->cbResidual = 0;
    466484            }
    467485            else
     
    493511             pThis->pDrvIns->pReg->szName, pThis->pDrvIns->iInstance, off, cbWrite, pThis->pszDevice));
    494512    RTCritSectEnter(&pThis->CritSect);
     513
     514    pReq->cbReq = cbWrite;
     515    pReq->cbResidual = cbWrite;
    495516
    496517    /*
     
    517538                         pThis->pDrvIns->pReg->szName, pThis->pDrvIns->iInstance,
    518539                         off, pvBuf, cbWrite, rc, pThis->pszDevice));
     540                else
     541                    pReq->cbResidual = 0;
    519542
    520543                rc = drvHostBaseBufferRelease(pThis, pReq, cbWrite, true, pvBuf);
     
    10521075    pThis->IMediaEx.pfnIoReqFree                = drvHostBaseIoReqFree;
    10531076    pThis->IMediaEx.pfnIoReqQueryResidual       = drvHostBaseIoReqQueryResidual;
     1077    pThis->IMediaEx.pfnIoReqQueryXferSize       = drvHostBaseIoReqQueryXferSize;
    10541078    pThis->IMediaEx.pfnIoReqCancelAll           = drvHostBaseIoReqCancelAll;
    10551079    pThis->IMediaEx.pfnIoReqCancel              = drvHostBaseIoReqCancel;
  • trunk/src/VBox/Devices/Storage/DrvHostBase.h

    r64320 r64407  
    133133typedef struct DRVHOSTBASEREQ
    134134{
     135    /** Transfer size. */
     136    size_t                   cbReq;
     137    /** Amount of residual data. */
     138    size_t                   cbResidual;
    135139    /** Start of the request data for the device above us. */
    136140    uint8_t                  abAlloc[1];
  • trunk/src/VBox/Devices/Storage/DrvHostDVD.cpp

    r64362 r64407  
    565565        void *pvBuf = NULL;
    566566        size_t cbXferCur = cbXfer;
     567
     568        pReq->cbReq = cbXfer;
     569        pReq->cbResidual = cbXfer;
    567570
    568571        if (cbXfer)
     
    645648                if (rc != VINF_SUCCESS)
    646649                    break;
     650
     651                pReq->cbResidual -= cbCurrTX;
    647652                iATAPILBA += cReqSectors;
    648653                pbBuf += cbSector * cReqSectors;
     
    654659            rc = drvHostBaseScsiCmdOs(&pThis->Core, pbCdb, cbCdb, enmXferDir, pvBuf, &cbXferTmp,
    655660                                      &pThis->abATAPISense[0], sizeof(pThis->abATAPISense), cTimeoutMillies);
     661            if (RT_SUCCESS(rc))
     662                pReq->cbResidual -= cbXferTmp;
    656663        }
    657664
  • trunk/src/VBox/Devices/Storage/DrvSCSI.cpp

    r64226 r64407  
    789789}
    790790
     791/** @interface_method_impl{PDMIMEDIAEX,pfnIoReqQueryXferSize} */
     792static DECLCALLBACK(int) drvscsiIoReqQueryXferSize(PPDMIMEDIAEX pInterface, PDMMEDIAEXIOREQ hIoReq, size_t *pcbXfer)
     793{
     794    RT_NOREF1(pInterface);
     795    PDRVSCSIREQ pReq = (PDRVSCSIREQ)hIoReq;
     796
     797    *pcbXfer = pReq->cbBuf; /** @todo: Implement properly. */
     798    return VINF_SUCCESS;
     799}
     800
    791801/** @interface_method_impl{PDMIMEDIAEX,pfnIoReqCancelAll} */
    792802static DECLCALLBACK(int) drvscsiIoReqCancelAll(PPDMIMEDIAEX pInterface)
     
    12881298    pThis->IMediaEx.pfnIoReqFree                = drvscsiIoReqFree;
    12891299    pThis->IMediaEx.pfnIoReqQueryResidual       = drvscsiIoReqQueryResidual;
     1300    pThis->IMediaEx.pfnIoReqQueryXferSize       = drvscsiIoReqQueryXferSize;
    12901301    pThis->IMediaEx.pfnIoReqCancelAll           = drvscsiIoReqCancelAll;
    12911302    pThis->IMediaEx.pfnIoReqCancel              = drvscsiIoReqCancel;
  • trunk/src/VBox/Devices/Storage/DrvVD.cpp

    r64274 r64407  
    34023402
    34033403    if (   pIoReq->enmType != PDMMEDIAEXIOREQTYPE_READ
    3404         && pIoReq->enmType != PDMMEDIAEXIOREQTYPE_WRITE)
     3404        && pIoReq->enmType != PDMMEDIAEXIOREQTYPE_WRITE
     3405        && pIoReq->enmType != PDMMEDIAEXIOREQTYPE_FLUSH)
    34053406        return VERR_PDM_MEDIAEX_IOREQ_INVALID_STATE;
    34063407
    34073408    *pcbResidual = 0; /* No data left to transfer always. */
    34083409    return VINF_SUCCESS;
     3410}
     3411
     3412/**
     3413 * @interface_method_impl{PDMIMEDIAEX,pfnIoReqQueryXferSize}
     3414 */
     3415static DECLCALLBACK(int) drvvdIoReqQueryXferSize(PPDMIMEDIAEX pInterface, PDMMEDIAEXIOREQ hIoReq, size_t *pcbXfer)
     3416{
     3417    int rc = VINF_SUCCESS;
     3418    RT_NOREF1(pInterface);
     3419
     3420    PPDMMEDIAEXIOREQINT pIoReq = hIoReq;
     3421
     3422    if (pIoReq->enmState != VDIOREQSTATE_COMPLETED)
     3423        return VERR_PDM_MEDIAEX_IOREQ_INVALID_STATE;
     3424
     3425    if (   pIoReq->enmType == PDMMEDIAEXIOREQTYPE_READ
     3426        || pIoReq->enmType == PDMMEDIAEXIOREQTYPE_WRITE)
     3427        *pcbXfer = pIoReq->ReadWrite.cbReq;
     3428    else if (pIoReq->enmType == PDMMEDIAEXIOREQTYPE_FLUSH)
     3429        *pcbXfer = 0;
     3430    else
     3431        rc = VERR_PDM_MEDIAEX_IOREQ_INVALID_STATE;
     3432
     3433    return rc;
    34093434}
    34103435
     
    43894414    pThis->IMediaEx.pfnIoReqFree                = drvvdIoReqFree;
    43904415    pThis->IMediaEx.pfnIoReqQueryResidual       = drvvdIoReqQueryResidual;
     4416    pThis->IMediaEx.pfnIoReqQueryXferSize       = drvvdIoReqQueryXferSize;
    43914417    pThis->IMediaEx.pfnIoReqCancelAll           = drvvdIoReqCancelAll;
    43924418    pThis->IMediaEx.pfnIoReqCancel              = drvvdIoReqCancel;
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