VirtualBox

Changeset 28275 in vbox for trunk/src/VBox


Ignore:
Timestamp:
Apr 13, 2010 7:40:10 PM (15 years ago)
Author:
vboxsync
Message:

Devices/Network: Call pfnBeginXmit and pfnEndXmit.

Location:
trunk/src/VBox/Devices/Network
Files:
7 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Devices/Network/DevE1000.cpp

    r28196 r28275  
    37363736}
    37373737
     3738
     3739/**
     3740 * Transmit pending descriptors.
     3741 *
     3742 * @returns VBox status code.  VERR_TRY_AGAIN is returned if we're busy.
     3743 *
     3744 * @param   pState              The E1000 state.
     3745 */
     3746static int e1kXmitPending(E1KSTATE *pState)
     3747{
     3748    PPDMINETWORKUP  pDrv = pState->pDrv;
     3749    int             rc;
     3750
     3751    /*
     3752     * Grab the xmit lock of the driver as well as the E1K device state.
     3753     */
     3754    if (pDrv)
     3755    {
     3756        rc = pDrv->pfnBeginXmit(pDrv, true /*fOnWorkerThread*/);
     3757        if (RT_FAILURE(rc))
     3758            return rc;
     3759    }
     3760    rc = e1kMutexAcquire(pState, VERR_TRY_AGAIN, RT_SRC_POS);
     3761    if (RT_SUCCESS(rc))
     3762    {
     3763        /*
     3764         * Process all pending descriptors.
     3765         * Note! Do not process descriptors in locked state
     3766         */
     3767        while (TDH != TDT && !pState->fLocked)
     3768        {
     3769            E1KTXDESC desc;
     3770            E1kLog3(("%s About to process new TX descriptor at %08x%08x, TDLEN=%08x, TDH=%08x, TDT=%08x\n",
     3771                     INSTANCE(pState), TDBAH, TDBAL + TDH * sizeof(desc), TDLEN, TDH, TDT));
     3772
     3773            e1kLoadDesc(pState, &desc, ((uint64_t)TDBAH << 32) + TDBAL + TDH * sizeof(desc));
     3774            e1kXmitDesc(pState, &desc, ((uint64_t)TDBAH << 32) + TDBAL + TDH * sizeof(desc));
     3775            if (++TDH * sizeof(desc) >= TDLEN)
     3776                TDH = 0;
     3777
     3778            if (e1kGetTxLen(pState) <= GET_BITS(TXDCTL, LWTHRESH)*8)
     3779            {
     3780                E1kLog2(("%s Low on transmit descriptors, raise ICR.TXD_LOW, len=%x thresh=%x\n",
     3781                         INSTANCE(pState), e1kGetTxLen(pState), GET_BITS(TXDCTL, LWTHRESH)*8));
     3782                e1kRaiseInterrupt(pState, VERR_SEM_BUSY, ICR_TXD_LOW);
     3783            }
     3784
     3785            STAM_PROFILE_ADV_STOP(&pState->StatTransmit, a);
     3786        }
     3787
     3788        /// @todo: uncomment: pState->uStatIntTXQE++;
     3789        /// @todo: uncomment: e1kRaiseInterrupt(pState, ICR_TXQE);
     3790
     3791        /*
     3792         * Release the locks.
     3793         */
     3794        e1kMutexRelease(pState);
     3795    }
     3796    if (pDrv)
     3797        pDrv->pfnEndXmit(pDrv);
     3798    return rc;
     3799}
     3800
    37383801#ifdef VBOX_WITH_TX_THREAD_IN_NET_DEVICES
    37393802
     
    37843847        if (pThread->enmState == PDMTHREADSTATE_RUNNING)
    37853848        {
    3786             E1KTXDESC desc;
    3787             rc = e1kMutexAcquire(pState, VERR_SEM_BUSY, RT_SRC_POS);
    3788             AssertRCReturn(rc, rc);
    3789             /* Do not process descriptors in locked state */
    3790             while (TDH != TDT && !pState->fLocked)
    3791             {
    3792                 E1kLog3(("%s About to process new TX descriptor at %08x%08x, TDLEN=%08x, TDH=%08x, TDT=%08x\n",
    3793                          INSTANCE(pState), TDBAH, TDBAL + TDH * sizeof(desc), TDLEN, TDH, TDT));
    3794                 //if (!e1kCsEnter(pState, RT_SRC_POS))
    3795                 //    return VERR_PERMISSION_DENIED;
    3796                 e1kLoadDesc(pState, &desc, ((uint64_t)TDBAH << 32) + TDBAL + TDH * sizeof(desc));
    3797                 e1kXmitDesc(pState, &desc, ((uint64_t)TDBAH << 32) + TDBAL + TDH * sizeof(desc));
    3798                 if (++TDH * sizeof(desc) >= TDLEN)
    3799                     TDH = 0;
    3800                 if (e1kGetTxLen(pState) <= GET_BITS(TXDCTL, LWTHRESH)*8)
    3801                 {
    3802                     E1kLog2(("%s Low on transmit descriptors, raise ICR.TXD_LOW, len=%x thresh=%x\n",
    3803                              INSTANCE(pState), e1kGetTxLen(pState), GET_BITS(TXDCTL, LWTHRESH)*8));
    3804                     e1kRaiseInterrupt(pState, VERR_SEM_BUSY, ICR_TXD_LOW);
    3805                 }
    3806                 STAM_PROFILE_ADV_STOP(&pState->StatTransmit, a);
    3807                 //e1kCsLeave(pState);
    3808             }
    3809             /// @todo: uncomment: pState->uStatIntTXQE++;
    3810             /// @todo: uncomment: e1kRaiseInterrupt(pState, ICR_TXQE);
    3811             e1kMutexRelease(pState);
     3849            rc = e1kXmitPending(pState);
     3850            AssertMsgReturn(RT_SUCCESS(rc) || rc == VERR_TRY_AGAIN, ("%Rrc\n", rc), rc);
    38123851        }
    38133852    }
  • trunk/src/VBox/Devices/Network/DevPCNet.cpp

    r28082 r28275  
    20602060    NOREF(pItem);
    20612061
    2062     /* Clear counter .*/
    20632062#ifndef VBOX_WITH_TX_THREAD_IN_NET_DEVICES
    2064     int rc = PDMCritSectEnter(&pThis->CritSect, VERR_SEM_BUSY);
    2065     AssertReleaseRC(rc);
    2066 
    2067     pcnetAsyncTransmit(pThis, false /*fOnWorkerThread*/);
    2068 
    2069     PDMCritSectLeave(&pThis->CritSect);
     2063    /*
     2064     * Process as much as we can.
     2065     */
     2066    int             rc   = VINF_SUCCESS;
     2067    PPDMINETWORKUP  pDrv = pThis->pDrvR3;
     2068    if (pDrv)
     2069    {
     2070        rc = pDrv->pfnBeginXmit(pDrv, false /*fOnWorkerThread*/);
     2071        AssertMsg(rc == VINF_SUCCESS || rc == VERR_TRY_AGAIN, ("%Rrc\n", rc));
     2072    }
     2073    if (RT_SUCCESS(rc))
     2074    {
     2075        rc = PDMCritSectEnter(&pThis->CritSect, VERR_SEM_BUSY);
     2076        if (RT_SUCCESS(rc))
     2077        {
     2078            int rc2 = pcnetAsyncTransmit(pThis, false /*fOnWorkerThread*/);
     2079            AssertReleaseRC(rc2);
     2080
     2081            PDMCritSectLeave(&pThis->CritSect);
     2082        }
     2083        else
     2084            AssertReleaseRC(rc);
     2085        if (pDrv)
     2086            pDrv->pfnEndXmit(pDrv);
     2087    }
    20702088#else
     2089    /*
     2090     * Wake up the TX thread.
     2091     */
    20712092    int rc = RTSemEventSignal(pThis->hSendEventSem);
    20722093    AssertRC(rc);
     
    26912712        /*
    26922713         * Perform async send. Mind that we might be requested to
    2693          * suspended while waiting for the critical section.
     2714         * suspended while waiting for the critical sections.
    26942715         */
     2716        PPDMINETWORKUP pDrv = pThis->pDrvR3;
     2717        if (pDrv)
     2718        {
     2719            rc = pDrv->pfnBeginXmit(pDrv, true /*fOnWorkerThread*/);
     2720            if (rc == VERR_TRY_AGAIN)
     2721                continue;
     2722            AssertReleaseRCReturn(rc, rc);
     2723        }
    26952724        rc = PDMCritSectEnter(&pThis->CritSect, VERR_SEM_BUSY);
     2725        if (RT_SUCCESS(rc))
     2726        {
     2727            if (pThread->enmState == PDMTHREADSTATE_RUNNING)
     2728            {
     2729                int rc2 = pcnetAsyncTransmit(pThis, true /*fOnWorkerThread*/);
     2730                AssertReleaseRC(rc2);
     2731            }
     2732
     2733            PDMCritSectLeave(&pThis->CritSect);
     2734        }
     2735        if (pDrv)
     2736            pDrv->pfnEndXmit(pDrv);
    26962737        AssertReleaseRCReturn(rc, rc);
    2697 
    2698         if (pThread->enmState == PDMTHREADSTATE_RUNNING)
    2699         {
    2700             rc = pcnetAsyncTransmit(pThis, true /*fOnWorkerThread*/);
    2701             AssertReleaseRC(rc);
    2702         }
    2703 
    2704         PDMCritSectLeave(&pThis->CritSect);
    27052738    }
    27062739
  • trunk/src/VBox/Devices/Network/DevVirtioNet.cpp

    r28213 r28275  
    834834}
    835835
    836 static DECLCALLBACK(void) vnetTransmitPendingPackets(PVNETSTATE pState, PVQUEUE pQueue)
     836static DECLCALLBACK(void) vnetTransmitPendingPackets(PVNETSTATE pState, PVQUEUE pQueue, bool fOnWorkerThread)
    837837{
    838838    /*
     
    849849             INSTANCE(pState), pState->VPCI.uStatus));
    850850        return;
     851    }
     852
     853    PPDMINETWORKUP pDrv = pState->pDrv;
     854    if (pDrv)
     855    {
     856        int rc = pDrv->pfnBeginXmit(pDrv, fOnWorkerThread);
     857        Assert(rc == VINF_SUCCESS || rc == VERR_TRY_AGAIN);
     858        if (rc == VERR_TRY_AGAIN)
     859        {
     860            ASMAtomicWriteU32(&pState->uIsTransmitting, 0);
     861            return;
     862        }
    851863    }
    852864
     
    909921    vpciSetWriteLed(&pState->VPCI, false);
    910922
     923    if (pDrv)
     924        pDrv->pfnEndXmit(pDrv);
    911925    ASMAtomicWriteU32(&pState->uIsTransmitting, 0);
    912926}
     
    922936        Log3(("%s vnetQueueTransmit: Got kicked with notification disabled, "
    923937              "re-enable notification and flush TX queue\n", INSTANCE(pState)));
    924         vnetTransmitPendingPackets(pState, pQueue);
     938        vnetTransmitPendingPackets(pState, pQueue, false /*fOnWorkerThread*/);
    925939        if (RT_FAILURE(vnetCsEnter(pState, VERR_SEM_BUSY)))
    926940            LogRel(("vnetQueueTransmit: Failed to enter critical section!/n"));
     
    970984
    971985//    Log3(("%s vnetTxTimer: Expired\n", INSTANCE(pState)));
    972     vnetTransmitPendingPackets(pState, pState->pTxQueue);
     986    vnetTransmitPendingPackets(pState, pState->pTxQueue, false /*fOnWorkerThread*/);
    973987    if (RT_FAILURE(vnetCsEnter(pState, VERR_SEM_BUSY)))
    974988    {
     
    985999    VNETSTATE *pState = (VNETSTATE*)pvState;
    9861000
    987     vnetTransmitPendingPackets(pState, pQueue);
     1001    vnetTransmitPendingPackets(pState, pQueue, false /*fOnWorkerThread*/);
    9881002}
    9891003#endif /* !VNET_TX_DELAY */
  • trunk/src/VBox/Devices/Network/DrvIntNet.cpp

    r28259 r28275  
    200200 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit}
    201201 */
    202 static DECLCALLBACK(int) drvR3IntNetUp_BeginXmit(PPDMINETWORKUP pInterface)
     202static DECLCALLBACK(int) drvR3IntNetUp_BeginXmit(PPDMINETWORKUP pInterface, bool fOnWorkerThread)
    203203{
    204204    PDRVINTNET pThis = RT_FROM_MEMBER(pInterface, DRVINTNET, INetworkUpR3);
     
    219219    int         rc    = VINF_SUCCESS;
    220220    Assert(cbMin < UINT32_MAX / 2);
    221 //    Assert(PDMCritSectIsOwner(&pThis->XmitLock));
     221    Assert(PDMCritSectIsOwner(&pThis->XmitLock));
    222222
    223223    /*
     
    296296    Assert(   pHdr->u16Type == INTNETHDR_TYPE_FRAME
    297297           || pHdr->u16Type == INTNETHDR_TYPE_GSO);
    298 //    Assert(PDMCritSectIsOwner(&pThis->XmitLock));
     298    Assert(PDMCritSectIsOwner(&pThis->XmitLock));
    299299
    300300    /** @todo LATER: try unalloc the frame. */
     
    318318    Assert(pSgBuf->fFlags == (PDMSCATTERGATHER_FLAGS_MAGIC | PDMSCATTERGATHER_FLAGS_OWNER_1));
    319319    Assert(pSgBuf->cbUsed <= pSgBuf->cbAvailable);
    320 //    Assert(PDMCritSectIsOwner(&pThis->XmitLock));
     320    Assert(PDMCritSectIsOwner(&pThis->XmitLock));
    321321
    322322    if (pSgBuf->pvUser)
  • trunk/src/VBox/Devices/Network/DrvNAT.cpp

    r28258 r28275  
    458458 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit}
    459459 */
    460 static DECLCALLBACK(int) drvNATNetworkUp_BeginXmit(PPDMINETWORKUP pInterface)
     460static DECLCALLBACK(int) drvNATNetworkUp_BeginXmit(PPDMINETWORKUP pInterface, bool fOnWorkerThread)
    461461{
    462462    PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp);
     
    477477{
    478478    PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp);
    479 //    Assert(RTCritSectIsOwner(&pThis->XmitLock);
     479    Assert(RTCritSectIsOwner(&pThis->XmitLock));
    480480
    481481    /*
     
    543543{
    544544    PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp);
    545 //    Assert(RTCritSectIsOwner(&pThis->XmitLock);
     545    Assert(RTCritSectIsOwner(&pThis->XmitLock));
    546546    drvNATFreeSgBuf(pThis, pSgBuf);
    547547    return VINF_SUCCESS;
     
    555555    PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp);
    556556    Assert((pSgBuf->fFlags & PDMSCATTERGATHER_FLAGS_OWNER_MASK) == PDMSCATTERGATHER_FLAGS_OWNER_1);
    557 //    Assert(RTCritSectIsOwner(&pThis->XmitLock);
     557    Assert(RTCritSectIsOwner(&pThis->XmitLock));
    558558
    559559    int rc;
  • trunk/src/VBox/Devices/Network/DrvNetSniffer.cpp

    r28258 r28275  
    8787 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit}
    8888 */
    89 static DECLCALLBACK(int) drvNetSnifferUp_BeginXmit(PPDMINETWORKUP pInterface)
     89static DECLCALLBACK(int) drvNetSnifferUp_BeginXmit(PPDMINETWORKUP pInterface, bool fOnWorkerThread)
    9090{
    9191    PDRVNETSNIFFER pThis = RT_FROM_MEMBER(pInterface, DRVNETSNIFFER, INetworkUp);
     
    9797        return rc;
    9898    }
    99     return pThis->pIBelowNet->pfnBeginXmit(pThis->pIBelowNet);
     99    return pThis->pIBelowNet->pfnBeginXmit(pThis->pIBelowNet, fOnWorkerThread);
    100100}
    101101
  • trunk/src/VBox/Devices/Network/DrvTAP.cpp

    r28258 r28275  
    124124    PPDMTHREAD              pThread;
    125125
     126    /** @todo The transmit thread. */
     127    /** Transmit lock used by drvTAPNetworkUp_BeginXmit. */
     128    RTCRITSECT              XmitLock;
     129
    126130#ifdef VBOX_WITH_STATISTICS
    127131    /** Number of sent packets. */
     
    165169
    166170
     171
     172/**
     173 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit}
     174 */
     175static DECLCALLBACK(int) drvTAPNetworkUp_BeginXmit(PPDMINETWORKUP pInterface, bool fOnWorkerThread)
     176{
     177    PDRVTAP pThis = PDMINETWORKUP_2_DRVTAP(pInterface);
     178    int rc = RTCritSectTryEnter(&pThis->XmitLock);
     179    if (RT_FAILURE(rc))
     180    {
     181        /** @todo XMIT thread */
     182        rc = VERR_TRY_AGAIN;
     183    }
     184    return rc;
     185}
     186
     187
    167188/**
    168189 * @interface_method_impl{PDMINETWORKUP,pfnAllocBuf}
     
    172193{
    173194    PDRVTAP pThis = PDMINETWORKUP_2_DRVTAP(pInterface);
     195    Assert(RTCritSectIsOwner(&pThis->XmitLock));
    174196
    175197    /*
     
    216238{
    217239    PDRVTAP pThis = PDMINETWORKUP_2_DRVTAP(pInterface);
     240    Assert(RTCritSectIsOwner(&pThis->XmitLock));
    218241    if (pSgBuf)
    219242    {
     
    238261    AssertPtr(pSgBuf);
    239262    Assert((pSgBuf->fFlags & PDMSCATTERGATHER_FLAGS_MAGIC_MASK) == PDMSCATTERGATHER_FLAGS_MAGIC);
     263    Assert(RTCritSectIsOwner(&pThis->XmitLock));
    240264
    241265    int rc;
     
    279303        rc = rc == VERR_NO_MEMORY ? VERR_NET_NO_BUFFER_SPACE : VERR_NET_DOWN;
    280304    return rc;
     305}
     306
     307
     308/**
     309 * @interface_method_impl{PDMINETWORKUP,pfnEndXmit}
     310 */
     311static DECLCALLBACK(void) drvTAPNetworkUp_EndXmit(PPDMINETWORKUP pInterface)
     312{
     313    PDRVTAP pThis = PDMINETWORKUP_2_DRVTAP(pInterface);
     314    RTCritSectLeave(&pThis->XmitLock);
    281315}
    282316
     
    939973    MMR3HeapFree(pThis->pszTerminateApplication);
    940974
     975    /*
     976     * Kill the xmit lock.
     977     */
     978    if (RTCritSectIsInitialized(&pThis->XmitLock))
     979        RTCritSectDelete(&pThis->XmitLock);
     980
    941981#ifdef VBOX_WITH_STATISTICS
    942982    /*
     
    9831023    pDrvIns->IBase.pfnQueryInterface    = drvTAPQueryInterface;
    9841024    /* INetwork */
    985     pThis->INetworkUp.pfnSendBuf                = drvTAPNetworkUp_SendBuf;
     1025    pThis->INetworkUp.pfnBeginXmit              = drvTAPNetworkUp_BeginXmit;
    9861026    pThis->INetworkUp.pfnAllocBuf               = drvTAPNetworkUp_AllocBuf;
    9871027    pThis->INetworkUp.pfnFreeBuf                = drvTAPNetworkUp_FreeBuf;
     1028    pThis->INetworkUp.pfnSendBuf                = drvTAPNetworkUp_SendBuf;
     1029    pThis->INetworkUp.pfnEndXmit                = drvTAPNetworkUp_EndXmit;
    9881030    pThis->INetworkUp.pfnSetPromiscuousMode     = drvTAPNetworkUp_SetPromiscuousMode;
    9891031    pThis->INetworkUp.pfnNotifyLinkChanged      = drvTAPNetworkUp_NotifyLinkChanged;
     
    10531095                                       N_("Error running TAP setup application. rc=%d"), rc);
    10541096    }
     1097
     1098    /*
     1099     * Create the transmit lock.
     1100     */
     1101    rc = RTCritSectInit(&pThis->XmitLock);
     1102    AssertRCReturn(rc, rc);
    10551103
    10561104    /*
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