VirtualBox

Changeset 78577 in vbox for trunk/src/VBox


Ignore:
Timestamp:
May 18, 2019 10:53:11 AM (6 years ago)
Author:
vboxsync
Message:

winnt/vboxsf: Converted VBoxMRxWrite the new HGCM IDC interface, only keeping the page list variant. bugref:9172

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

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Additions/WINNT/SharedFolders/driver/file.cpp

    r78575 r78577  
    3131#define VBSF_MAX_IO_PAGES   RT_MIN(_16K / sizeof(RTGCPHYS64) /* => 8MB buffer */, VMMDEV_MAX_HGCM_DATA_SIZE >> PAGE_SHIFT)
    3232
    33 /* How much data to transfer in one HGCM request. */
    34 #define VBSF_MAX_READ_WRITE_PAGES 256
    35 
    36 
    37 typedef int FNVBSFTRANSFERBUFFER(PVBGLSFCLIENT pClient, PVBGLSFMAP pMap, SHFLHANDLE hFile,
    38                                  uint64_t offset, uint32_t *pcbBuffer,
    39                                  uint8_t *pBuffer, bool fLocked);
    40 typedef FNVBSFTRANSFERBUFFER *PFNVBSFTRANSFERBUFFER;
    41 
    42 typedef int FNVBSFTRANSFERPAGES(PVBGLSFCLIENT pClient, PVBGLSFMAP pMap, SHFLHANDLE hFile,
    43                                 uint64_t offset, uint32_t *pcbBuffer,
    44                                 uint16_t offFirstPage, uint16_t cPages, RTGCPHYS64 *paPages);
    45 typedef FNVBSFTRANSFERPAGES *PFNVBSFTRANSFERPAGES;
    46 
    47 
    48 static int vbsfTransferBufferWrite(PVBGLSFCLIENT pClient, PVBGLSFMAP pMap, SHFLHANDLE hFile,
    49                                    uint64_t offset, uint32_t *pcbBuffer,
    50                                    uint8_t *pBuffer, bool fLocked)
    51 {
    52     return VbglR0SfWrite(pClient, pMap, hFile, offset, pcbBuffer, pBuffer, fLocked);
    53 }
    54 
    55 static int vbsfTransferPagesWrite(PVBGLSFCLIENT pClient, PVBGLSFMAP pMap, SHFLHANDLE hFile,
    56                                   uint64_t offset, uint32_t *pcbBuffer,
    57                                   uint16_t offFirstPage, uint16_t cPages, RTGCPHYS64 *paPages)
    58 {
    59     return VbglR0SfWritePageList(pClient, pMap, hFile, offset, pcbBuffer, offFirstPage, cPages, paPages);
    60 }
    61 
    62 
    63 typedef struct VBSFTRANSFERCTX
    64 {
    65     PVBGLSFCLIENT pClient;
    66     PVBGLSFMAP pMap;
    67     SHFLHANDLE hFile;
    68     uint64_t offset;
    69     uint32_t cbData;
    70 
    71     PMDL pMdl;
    72     uint8_t *pBuffer;
    73     bool fLocked;
    74 
    75     PFNVBSFTRANSFERBUFFER pfnTransferBuffer;
    76     PFNVBSFTRANSFERPAGES pfnTransferPages;
    77 } VBSFTRANSFERCTX;
    78 
    79 
    80 static int vbsfTransferCommon(VBSFTRANSFERCTX *pCtx)
    81 {
    82     int rc = VINF_SUCCESS;
    83     BOOLEAN fProcessed = FALSE;
    84 
    85     uint32_t cbTransferred = 0;
    86 
    87     uint32_t cbToTransfer;
    88     uint32_t cbIO;
    89 
    90     /** @todo Remove the test and the fall-back path.  VbglR0CanUsePhysPageList()
    91      *        returns true for any host version after 3.0, i.e. further back than
    92      *        we support. */
    93     if (VbglR0CanUsePhysPageList())
    94     {
    95         ULONG offFirstPage = MmGetMdlByteOffset(pCtx->pMdl);
    96         ULONG cPages = ADDRESS_AND_SIZE_TO_SPAN_PAGES(MmGetMdlVirtualAddress(pCtx->pMdl), pCtx->cbData);
    97         ULONG cPagesToTransfer = RT_MIN(cPages, VBSF_MAX_READ_WRITE_PAGES);
    98         RTGCPHYS64 *paPages = (RTGCPHYS64 *)RTMemTmpAlloc(cPagesToTransfer * sizeof(RTGCPHYS64));
    99 
    100         Log(("VBOXSF: vbsfTransferCommon: using page list: %d pages, offset 0x%03X\n", cPages, offFirstPage));
    101 
    102         if (paPages)
    103         {
    104             PPFN_NUMBER paPfns = MmGetMdlPfnArray(pCtx->pMdl);
    105             ULONG cPagesTransferred = 0;
    106             cbTransferred = 0;
    107 
    108             while (cPagesToTransfer != 0)
    109             {
    110                 ULONG iPage;
    111                 cbToTransfer = cPagesToTransfer * PAGE_SIZE - offFirstPage;
    112 
    113                 if (cbToTransfer > pCtx->cbData - cbTransferred)
    114                     cbToTransfer = pCtx->cbData - cbTransferred;
    115 
    116                 if (cbToTransfer == 0)
    117                 {
    118                     /* Nothing to transfer. */
    119                     break;
    120                 }
    121 
    122                 cbIO = cbToTransfer;
    123 
    124                 Log(("VBOXSF: vbsfTransferCommon: transferring %d pages at %d; %d bytes at %d\n",
    125                      cPagesToTransfer, cPagesTransferred, cbToTransfer, cbTransferred));
    126 
    127                 for (iPage = 0; iPage < cPagesToTransfer; iPage++)
    128                     paPages[iPage] = (RTGCPHYS64)paPfns[iPage + cPagesTransferred] << PAGE_SHIFT;
    129 
    130                 rc = pCtx->pfnTransferPages(pCtx->pClient, pCtx->pMap, pCtx->hFile,
    131                                             pCtx->offset + cbTransferred, &cbIO,
    132                                             (uint16_t)offFirstPage, (uint16_t)cPagesToTransfer, paPages);
    133                 if (RT_FAILURE(rc))
    134                 {
    135                     Log(("VBOXSF: vbsfTransferCommon: pfnTransferPages %Rrc, cbTransferred %d\n", rc, cbTransferred));
    136 
    137                     /* If some data was transferred, then it is no error. */
    138                     if (cbTransferred > 0)
    139                         rc = VINF_SUCCESS;
    140 
    141                     break;
    142                 }
    143 
    144                 cbTransferred += cbIO;
    145 
    146                 if (cbToTransfer < cbIO)
    147                 {
    148                     /* Transferred less than requested, do not continue with the possibly remaining data. */
    149                     break;
    150                 }
    151 
    152                 cPagesTransferred += cPagesToTransfer;
    153                 offFirstPage = 0;
    154 
    155                 cPagesToTransfer = cPages - cPagesTransferred;
    156                 if (cPagesToTransfer > VBSF_MAX_READ_WRITE_PAGES)
    157                     cPagesToTransfer = VBSF_MAX_READ_WRITE_PAGES;
    158             }
    159 
    160             RTMemTmpFree(paPages);
    161 
    162             fProcessed = TRUE;
    163         }
    164     }
    165 
    166     if (fProcessed != TRUE)
    167     {
    168         /* Split large transfers. */
    169         cbTransferred = 0;
    170         cbToTransfer = RT_MIN(pCtx->cbData, VBSF_MAX_READ_WRITE_PAGES * PAGE_SIZE);
    171 
    172         /* Page list not supported or a fallback. */
    173         Log(("VBOXSF: vbsfTransferCommon: using linear address\n"));
    174 
    175         while (cbToTransfer != 0)
    176         {
    177             cbIO = cbToTransfer;
    178 
    179             Log(("VBOXSF: vbsfTransferCommon: transferring %d bytes at %d\n",
    180                  cbToTransfer, cbTransferred));
    181 
    182             rc = pCtx->pfnTransferBuffer(pCtx->pClient, pCtx->pMap, pCtx->hFile,
    183                                          pCtx->offset + cbTransferred, &cbIO,
    184                                          pCtx->pBuffer + cbTransferred, true /* locked */);
    185 
    186             if (RT_FAILURE(rc))
    187             {
    188                 Log(("VBOXSF: vbsfTransferCommon: pfnTransferBuffer %Rrc, cbTransferred %d\n", rc, cbTransferred));
    189 
    190                 /* If some data was transferred, then it is no error. */
    191                 if (cbTransferred > 0)
    192                     rc = VINF_SUCCESS;
    193 
    194                 break;
    195             }
    196 
    197             cbTransferred += cbIO;
    198 
    199             if (cbToTransfer < cbIO)
    200             {
    201                 /* Transferred less than requested, do not continue with the possibly remaining data. */
    202                 break;
    203             }
    204 
    205             cbToTransfer = pCtx->cbData - cbTransferred;
    206             if (cbToTransfer > VBSF_MAX_READ_WRITE_PAGES * PAGE_SIZE)
    207                 cbToTransfer = VBSF_MAX_READ_WRITE_PAGES * PAGE_SIZE;
    208         }
    209     }
    210 
    211     pCtx->cbData = cbTransferred;
    212 
    213     return rc;
    214 }
    21533
    21634/**
    21735 * Performs a read.
     36 *
     37 * @note Almost identical to vbsfNtWriteWorker.
    21838 */
    21939static NTSTATUS vbsfNtReadWorker(PRX_CONTEXT RxContext)
     
    22848    LogFlow(("vbsfNtReadWorker: hFile=%#RX64 offFile=%#RX64 cbToRead=%#x %s\n", pVBoxFobX->hFile,
    22949             RxContext->LowIoContext.ParamsFor.ReadWrite.ByteOffset, RxContext->LowIoContext.ParamsFor.ReadWrite.ByteCount,
    230              RxContext->Flags, RX_CONTEXT_FLAG_ASYNC_OPERATION ? " async" : "sync"));
     50             RxContext->Flags & RX_CONTEXT_FLAG_ASYNC_OPERATION ? " async" : "sync"));
    23151
    23252    AssertReturn(pBufferMdl,  STATUS_INTERNAL_ERROR);
     
    398218 * Wrapper for RxDispatchToWorkerThread().
    399219 */
    400 static VOID vbsfReadWorker(VOID *pv)
     220static VOID vbsfNtReadThreadWorker(VOID *pv)
    401221{
    402222    PRX_CONTEXT RxContext = (PRX_CONTEXT)pv;
    403223
    404     Log(("VBOXSF: vbsfReadWorker: calling the worker\n"));
     224    Log(("VBOXSF: vbsfNtReadThreadWorker: calling the worker\n"));
    405225
    406226    RxContext->IoStatusBlock.Status = vbsfNtReadWorker(RxContext);
    407227
    408     Log(("VBOXSF: vbsfReadWorker: Status 0x%08X\n",
     228    Log(("VBOXSF: vbsfNtReadThreadWorker: Status 0x%08X\n",
    409229         RxContext->IoStatusBlock.Status));
    410230
     
    439259        Assert(Status != STATUS_PENDING);
    440260
    441         Log(("VBOXSF: MRxRead: vbsfReadInternal: Status %#08X\n", Status));
     261        Log(("VBOXSF: VBoxMRxRead: vbsfNtReadWorker: Status %#08X\n", Status));
    442262    }
    443263    else
    444264    {
    445         Status = RxDispatchToWorkerThread(VBoxMRxDeviceObject, DelayedWorkQueue, vbsfReadWorker, RxContext);
    446 
    447         Log(("VBOXSF: MRxRead: RxDispatchToWorkerThread: Status 0x%08X\n", Status));
     265        Status = RxDispatchToWorkerThread(VBoxMRxDeviceObject, DelayedWorkQueue, vbsfNtReadThreadWorker, RxContext);
     266
     267        Log(("VBOXSF: VBoxMRxRead: RxDispatchToWorkerThread: Status 0x%08X\n", Status));
    448268
    449269        if (Status == STATUS_SUCCESS)
     
    454274}
    455275
    456 static NTSTATUS vbsfWriteInternal(IN PRX_CONTEXT RxContext)
    457 {
    458     NTSTATUS Status = STATUS_SUCCESS;
    459     VBSFTRANSFERCTX ctx;
    460 
     276/**
     277 * Performs a write.
     278 *
     279 * @note Almost identical to vbsfNtReadWorker.
     280 */
     281static NTSTATUS vbsfNtWriteWorker(PRX_CONTEXT RxContext)
     282{
    461283    RxCaptureFcb;
    462284    RxCaptureFobx;
    463 
    464     PMRX_VBOX_NETROOT_EXTENSION pNetRootExtension = VBoxMRxGetNetRootExtension(capFcb->pNetRoot);
    465     PVBSFNTFCBEXT pVBoxFcbx = VBoxMRxGetFcbExtension(capFcb);
    466     PMRX_VBOX_FOBX pVBoxFobx = VBoxMRxGetFileObjectExtension(capFobx);
    467 
    468     PLOWIO_CONTEXT LowIoContext  = &RxContext->LowIoContext;
    469 
    470     PMDL BufferMdl = LowIoContext->ParamsFor.ReadWrite.Buffer;
    471     uint32_t ByteCount = LowIoContext->ParamsFor.ReadWrite.ByteCount;
    472     RXVBO ByteOffset = LowIoContext->ParamsFor.ReadWrite.ByteOffset;
    473 
    474     PVOID pbUserBuffer = RxLowIoGetBufferAddress(RxContext);
    475 
    476     int vrc;
    477 
    478 #ifdef LOG_ENABLED
    479     BOOLEAN AsyncIo = BooleanFlagOn(RxContext->Flags, RX_CONTEXT_FLAG_ASYNC_OPERATION);
    480 #endif
    481     LONGLONG FileSize;
    482 
    483     RxGetFileSizeWithLock((PFCB)capFcb, &FileSize);
    484 
    485     Log(("VBOXSF: vbsfWriteInternal: AsyncIo = %d, Fcb->FileSize = 0x%RX64\n",
    486          AsyncIo, capFcb->Header.FileSize.QuadPart));
    487     Log(("VBOXSF: vbsfWriteInternal: UserBuffer %p, BufferMdl %p\n",
    488          pbUserBuffer, BufferMdl));
    489     Log(("VBOXSF: vbsfWriteInternal: ByteCount is 0x%X, ByteOffset is 0x%RX64, FileSize 0x%RX64\n",
    490          ByteCount, ByteOffset, FileSize));
    491 
    492     /** @todo allow to write 0 bytes. */
    493     if (   !BufferMdl
    494         || ByteCount == 0)
    495     {
    496         AssertFailed();
    497         return STATUS_INVALID_PARAMETER;
    498     }
    499 
    500     ctx.pClient = &g_SfClient;
    501     ctx.pMap    = &pNetRootExtension->map;
    502     ctx.hFile   = pVBoxFobx->hFile;
    503     ctx.offset  = (uint64_t)ByteOffset;
    504     ctx.cbData  = ByteCount;
    505     ctx.pMdl    = BufferMdl;
    506     ctx.pBuffer = (uint8_t *)pbUserBuffer;
    507     ctx.fLocked = true;
    508     ctx.pfnTransferBuffer = vbsfTransferBufferWrite;
    509     ctx.pfnTransferPages = vbsfTransferPagesWrite;
    510 
    511     vrc = vbsfTransferCommon(&ctx);
    512 
    513     ByteCount = ctx.cbData;
    514 
    515     Status = vbsfNtVBoxStatusToNt(vrc);
    516 
    517     if (Status == STATUS_SUCCESS)
    518     {
    519         pVBoxFobx->fTimestampsImplicitlyUpdated |= VBOX_FOBX_F_INFO_LASTWRITE_TIME;
    520         if (pVBoxFcbx->pFobxLastWriteTime != pVBoxFobx)
    521             pVBoxFcbx->pFobxLastWriteTime = NULL;
    522 
    523         /* Make sure our cached file size value is up to date: */
    524         if (ctx.cbData > 0)
     285    PMRX_VBOX_NETROOT_EXTENSION pNetRootX  = VBoxMRxGetNetRootExtension(capFcb->pNetRoot);
     286    PVBSFNTFCBEXT               pVBoxFcbX  = VBoxMRxGetFcbExtension(capFcb);
     287    PMRX_VBOX_FOBX              pVBoxFobX  = VBoxMRxGetFileObjectExtension(capFobx);
     288    PMDL                        pBufferMdl = RxContext->LowIoContext.ParamsFor.ReadWrite.Buffer;
     289
     290    LogFlow(("vbsfNtWriteWorker: hFile=%#RX64 offFile=%#RX64 cbToWrite=%#x %s\n", pVBoxFobX->hFile,
     291             RxContext->LowIoContext.ParamsFor.ReadWrite.ByteOffset, RxContext->LowIoContext.ParamsFor.ReadWrite.ByteCount,
     292             RxContext->Flags & RX_CONTEXT_FLAG_ASYNC_OPERATION ? " async" : "sync"));
     293
     294    AssertReturn(pBufferMdl,  STATUS_INTERNAL_ERROR);
     295
     296
     297    /*
     298     * We should never get a zero byte request (RDBSS checks), but in case we
     299     * do, it should succeed.
     300     */
     301    uint32_t cbRet  = 0;
     302    uint32_t cbLeft = RxContext->LowIoContext.ParamsFor.ReadWrite.ByteCount;
     303    AssertReturnStmt(cbLeft > 0, RxContext->InformationToReturn = 0, STATUS_SUCCESS);
     304
     305    Assert(cbLeft <= MmGetMdlByteCount(pBufferMdl));
     306
     307    /*
     308     * Allocate a request buffer.
     309     */
     310    uint32_t             cPagesLeft = ADDRESS_AND_SIZE_TO_SPAN_PAGES(MmGetMdlVirtualAddress(pBufferMdl), cbLeft);
     311    uint32_t             cMaxPages  = RT_MIN(cPagesLeft, VBSF_MAX_IO_PAGES);
     312    VBOXSFWRITEPGLSTREQ *pReq = (VBOXSFWRITEPGLSTREQ *)VbglR0PhysHeapAlloc(RT_UOFFSETOF_DYN(VBOXSFWRITEPGLSTREQ,
     313                                                                                            PgLst.aPages[cMaxPages]));
     314    while (!pReq && cMaxPages > 4)
     315    {
     316        cMaxPages /= 2;
     317        pReq = (VBOXSFWRITEPGLSTREQ *)VbglR0PhysHeapAlloc(RT_UOFFSETOF_DYN(VBOXSFWRITEPGLSTREQ, PgLst.aPages[cMaxPages]));
     318    }
     319    NTSTATUS rcNt = STATUS_SUCCESS;
     320    if (pReq)
     321    {
     322        /*
     323         * The write loop.
     324         */
     325        RTFOFF      offFile = RxContext->LowIoContext.ParamsFor.ReadWrite.ByteOffset;
     326        PPFN_NUMBER paPfns  = MmGetMdlPfnArray(pBufferMdl);
     327        uint32_t    offPage = MmGetMdlByteOffset(pBufferMdl);
     328        if (offPage < PAGE_SIZE)
     329        { /* likely */ }
     330        else
    525331        {
    526             RTFOFF offEndOfWrite = LowIoContext->ParamsFor.ReadWrite.ByteOffset + ctx.cbData;
    527             if (pVBoxFobx->Info.cbObject < offEndOfWrite)
    528                 pVBoxFobx->Info.cbObject = offEndOfWrite;
    529 
    530             if (pVBoxFobx->Info.cbAllocated < offEndOfWrite)
    531             {
    532                 pVBoxFobx->Info.cbAllocated = offEndOfWrite;
    533                 pVBoxFobx->nsUpToDate       = 0;
    534             }
     332            paPfns  += offPage >> PAGE_SHIFT;
     333            offPage &= PAGE_OFFSET_MASK;
    535334        }
     335
     336        for (;;)
     337        {
     338            /*
     339             * Figure out how much to process now and set up the page list for it.
     340             */
     341            uint32_t cPagesInChunk;
     342            uint32_t cbChunk;
     343            if (cPagesLeft <= cMaxPages)
     344            {
     345                cPagesInChunk = cPagesLeft;
     346                cbChunk       = cbLeft;
     347            }
     348            else
     349            {
     350                cPagesInChunk = cMaxPages;
     351                cbChunk       = (cMaxPages << PAGE_SHIFT) - offPage;
     352            }
     353
     354            size_t iPage = cPagesInChunk;
     355            while (iPage-- > 0)
     356                pReq->PgLst.aPages[iPage] = (RTGCPHYS)paPfns[iPage] << PAGE_SHIFT;
     357            pReq->PgLst.offFirstPage = offPage;
     358
     359            /*
     360             * Issue the request and unlock the pages.
     361             */
     362            int vrc = VbglR0SfHostReqWritePgLst(pNetRootX->map.root, pReq, pVBoxFobX->hFile, offFile, cbChunk, cPagesInChunk);
     363            if (RT_SUCCESS(vrc))
     364            {
     365                /*
     366                 * Success, advance position and buffer.
     367                 */
     368                uint32_t cbActual = pReq->Parms.cb32Write.u.value32;
     369                AssertStmt(cbActual <= cbChunk, cbActual = cbChunk);
     370                cbRet   += cbActual;
     371                offFile += cbActual;
     372                cbLeft  -= cbActual;
     373
     374                /*
     375                 * Update timestamp state (FCB is shared).
     376                 */
     377                pVBoxFobX->fTimestampsImplicitlyUpdated |= VBOX_FOBX_F_INFO_LASTWRITE_TIME;
     378                if (pVBoxFcbX->pFobxLastWriteTime != pVBoxFobX)
     379                    pVBoxFcbX->pFobxLastWriteTime = NULL;
     380
     381                /*
     382                 * Are we done already?
     383                 */
     384                if (!cbLeft || cbActual < cbChunk)
     385                {
     386                    /*
     387                     * Make sure our cached file size value is up to date (RDBSS takes care
     388                     * of the ones in the FCB as well as the cache manager).
     389                     */
     390                    if (cbRet > 0)
     391                    {
     392                        if (pVBoxFobX->Info.cbObject < offFile)
     393                            pVBoxFobX->Info.cbObject = offFile;
     394
     395                        if (pVBoxFobX->Info.cbAllocated < offFile)
     396                        {
     397                            pVBoxFobX->Info.cbAllocated = offFile;
     398                            pVBoxFobX->nsUpToDate       = 0;
     399                        }
     400                    }
     401                    break;
     402                }
     403
     404                /*
     405                 * More to write, advance page related variables and loop.
     406                 */
     407                paPfns     += cPagesInChunk;
     408                cPagesLeft -= cPagesInChunk;
     409                offPage     = 0;
     410            }
     411            else if (vrc == VERR_NO_MEMORY && cMaxPages > 4)
     412            {
     413                /*
     414                 * The host probably doesn't have enough heap to handle the
     415                 * request, reduce the page count and retry.
     416                 */
     417                cMaxPages /= 4;
     418                Assert(cMaxPages > 0);
     419            }
     420            else
     421            {
     422                /*
     423                 * If we've successfully written stuff, return it rather than
     424                 * the error.  (Not sure if this is such a great idea...)
     425                 */
     426                if (cbRet > 0)
     427                    Log(("vbsfNtWriteWorker: write at %#RX64 -> %Rrc; got cbRet=%#zx already\n", offFile, vrc, cbRet));
     428                else
     429                {
     430                    rcNt = vbsfNtVBoxStatusToNt(vrc);
     431                    Log(("vbsfNtWriteWorker: write at %#RX64 -> %Rrc (rcNt=%#x)\n", offFile, vrc, rcNt));
     432                }
     433                break;
     434            }
     435
     436        }
     437
     438        VbglR0PhysHeapFree(pReq);
    536439    }
    537440    else
    538         ByteCount = 0; /* Nothing written. */
    539 
    540     RxContext->InformationToReturn = ByteCount;
    541 
    542     Log(("VBOXSF: vbsfWriteInternal: Status = 0x%08X, ByteCount = 0x%X\n",
    543          Status, ByteCount));
    544 
    545     return Status;
    546 }
    547 
    548 static VOID vbsfWriteWorker(VOID *pv)
     441        rcNt = STATUS_INSUFFICIENT_RESOURCES;
     442    RxContext->InformationToReturn = cbRet;
     443    LogFlow(("vbsfNtWriteWorker: returns %#x cbRet=%#x @ %#RX64\n",
     444             rcNt, cbRet, RxContext->LowIoContext.ParamsFor.ReadWrite.ByteOffset));
     445    return rcNt;
     446}
     447
     448/**
     449 * Wrapper for RxDispatchToWorkerThread().
     450 */
     451static VOID vbsfNtWriteThreadWorker(VOID *pv)
    549452{
    550453    PRX_CONTEXT RxContext = (PRX_CONTEXT)pv;
    551454
    552     Log(("VBOXSF: vbsfWriteWorker: calling the worker\n"));
    553 
    554     RxContext->IoStatusBlock.Status = vbsfWriteInternal(RxContext);
    555 
    556     Log(("VBOXSF: vbsfWriteWorker: Status 0x%08X\n",
     455    Log(("VBOXSF: vbsfNtWriteThreadWorker: calling the worker\n"));
     456
     457    RxContext->IoStatusBlock.Status = vbsfNtWriteWorker(RxContext);
     458
     459    Log(("VBOXSF: vbsfNtWriteThreadWorker: Status 0x%08X\n",
    557460         RxContext->IoStatusBlock.Status));
    558461
     
    560463}
    561464
    562 
    563465NTSTATUS VBoxMRxWrite(IN PRX_CONTEXT RxContext)
    564466{
    565     NTSTATUS Status = RxDispatchToWorkerThread(VBoxMRxDeviceObject, DelayedWorkQueue,
    566                                                vbsfWriteWorker,
    567                                                RxContext);
    568 
    569     Log(("VBOXSF: MRxWrite: RxDispatchToWorkerThread: Status 0x%08X\n",
    570          Status));
    571 
    572     if (Status == STATUS_SUCCESS)
    573         Status = STATUS_PENDING;
     467    NTSTATUS Status;
     468
     469    /* If synchronous operation, keep it on this thread (RDBSS already checked
     470       if we've got enough stack before calling us).   */
     471    if (!(RxContext->Flags & RX_CONTEXT_FLAG_ASYNC_OPERATION))
     472    {
     473        RxContext->IoStatusBlock.Status = Status = vbsfNtWriteWorker(RxContext);
     474        Assert(Status != STATUS_PENDING);
     475
     476        Log(("VBOXSF: VBoxMRxWrite: vbsfNtWriteWorker: Status %#08X\n", Status));
     477    }
     478    else
     479    {
     480        Status = RxDispatchToWorkerThread(VBoxMRxDeviceObject, DelayedWorkQueue, vbsfNtWriteThreadWorker, RxContext);
     481
     482        Log(("VBOXSF: VBoxMRxWrite: RxDispatchToWorkerThread: Status 0x%08X\n", Status));
     483
     484        if (Status == STATUS_SUCCESS)
     485            Status = STATUS_PENDING;
     486    }
    574487
    575488    return Status;
  • trunk/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibSharedFolders.c

    r78576 r78577  
    393393}
    394394
    395 # endif /* !RT_OS_WINDOWS */
    396 
    397395DECLVBGL(int) VbglR0SfWrite(PVBGLSFCLIENT pClient, PVBGLSFMAP pMap, SHFLHANDLE hFile,
    398396                            uint64_t offset, uint32_t *pcbBuffer, uint8_t *pBuffer, bool fLocked)
     
    520518    return rc;
    521519}
     520
     521# endif /* !RT_OS_WINDOWS */
    522522
    523523DECLVBGL(int) VbglR0SfFlush(PVBGLSFCLIENT pClient, PVBGLSFMAP pMap, SHFLHANDLE hFile)
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