Changeset 28275 in vbox for trunk/src/VBox
- Timestamp:
- Apr 13, 2010 7:40:10 PM (15 years ago)
- Location:
- trunk/src/VBox/Devices/Network
- Files:
-
- 7 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/Devices/Network/DevE1000.cpp
r28196 r28275 3736 3736 } 3737 3737 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 */ 3746 static 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 3738 3801 #ifdef VBOX_WITH_TX_THREAD_IN_NET_DEVICES 3739 3802 … … 3784 3847 if (pThread->enmState == PDMTHREADSTATE_RUNNING) 3785 3848 { 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); 3812 3851 } 3813 3852 } -
trunk/src/VBox/Devices/Network/DevPCNet.cpp
r28082 r28275 2060 2060 NOREF(pItem); 2061 2061 2062 /* Clear counter .*/2063 2062 #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 } 2070 2088 #else 2089 /* 2090 * Wake up the TX thread. 2091 */ 2071 2092 int rc = RTSemEventSignal(pThis->hSendEventSem); 2072 2093 AssertRC(rc); … … 2691 2712 /* 2692 2713 * 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. 2694 2715 */ 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 } 2695 2724 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); 2696 2737 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);2705 2738 } 2706 2739 -
trunk/src/VBox/Devices/Network/DevVirtioNet.cpp
r28213 r28275 834 834 } 835 835 836 static DECLCALLBACK(void) vnetTransmitPendingPackets(PVNETSTATE pState, PVQUEUE pQueue )836 static DECLCALLBACK(void) vnetTransmitPendingPackets(PVNETSTATE pState, PVQUEUE pQueue, bool fOnWorkerThread) 837 837 { 838 838 /* … … 849 849 INSTANCE(pState), pState->VPCI.uStatus)); 850 850 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 } 851 863 } 852 864 … … 909 921 vpciSetWriteLed(&pState->VPCI, false); 910 922 923 if (pDrv) 924 pDrv->pfnEndXmit(pDrv); 911 925 ASMAtomicWriteU32(&pState->uIsTransmitting, 0); 912 926 } … … 922 936 Log3(("%s vnetQueueTransmit: Got kicked with notification disabled, " 923 937 "re-enable notification and flush TX queue\n", INSTANCE(pState))); 924 vnetTransmitPendingPackets(pState, pQueue );938 vnetTransmitPendingPackets(pState, pQueue, false /*fOnWorkerThread*/); 925 939 if (RT_FAILURE(vnetCsEnter(pState, VERR_SEM_BUSY))) 926 940 LogRel(("vnetQueueTransmit: Failed to enter critical section!/n")); … … 970 984 971 985 // Log3(("%s vnetTxTimer: Expired\n", INSTANCE(pState))); 972 vnetTransmitPendingPackets(pState, pState->pTxQueue );986 vnetTransmitPendingPackets(pState, pState->pTxQueue, false /*fOnWorkerThread*/); 973 987 if (RT_FAILURE(vnetCsEnter(pState, VERR_SEM_BUSY))) 974 988 { … … 985 999 VNETSTATE *pState = (VNETSTATE*)pvState; 986 1000 987 vnetTransmitPendingPackets(pState, pQueue );1001 vnetTransmitPendingPackets(pState, pQueue, false /*fOnWorkerThread*/); 988 1002 } 989 1003 #endif /* !VNET_TX_DELAY */ -
trunk/src/VBox/Devices/Network/DrvIntNet.cpp
r28259 r28275 200 200 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit} 201 201 */ 202 static DECLCALLBACK(int) drvR3IntNetUp_BeginXmit(PPDMINETWORKUP pInterface )202 static DECLCALLBACK(int) drvR3IntNetUp_BeginXmit(PPDMINETWORKUP pInterface, bool fOnWorkerThread) 203 203 { 204 204 PDRVINTNET pThis = RT_FROM_MEMBER(pInterface, DRVINTNET, INetworkUpR3); … … 219 219 int rc = VINF_SUCCESS; 220 220 Assert(cbMin < UINT32_MAX / 2); 221 //Assert(PDMCritSectIsOwner(&pThis->XmitLock));221 Assert(PDMCritSectIsOwner(&pThis->XmitLock)); 222 222 223 223 /* … … 296 296 Assert( pHdr->u16Type == INTNETHDR_TYPE_FRAME 297 297 || pHdr->u16Type == INTNETHDR_TYPE_GSO); 298 //Assert(PDMCritSectIsOwner(&pThis->XmitLock));298 Assert(PDMCritSectIsOwner(&pThis->XmitLock)); 299 299 300 300 /** @todo LATER: try unalloc the frame. */ … … 318 318 Assert(pSgBuf->fFlags == (PDMSCATTERGATHER_FLAGS_MAGIC | PDMSCATTERGATHER_FLAGS_OWNER_1)); 319 319 Assert(pSgBuf->cbUsed <= pSgBuf->cbAvailable); 320 //Assert(PDMCritSectIsOwner(&pThis->XmitLock));320 Assert(PDMCritSectIsOwner(&pThis->XmitLock)); 321 321 322 322 if (pSgBuf->pvUser) -
trunk/src/VBox/Devices/Network/DrvNAT.cpp
r28258 r28275 458 458 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit} 459 459 */ 460 static DECLCALLBACK(int) drvNATNetworkUp_BeginXmit(PPDMINETWORKUP pInterface )460 static DECLCALLBACK(int) drvNATNetworkUp_BeginXmit(PPDMINETWORKUP pInterface, bool fOnWorkerThread) 461 461 { 462 462 PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp); … … 477 477 { 478 478 PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp); 479 // Assert(RTCritSectIsOwner(&pThis->XmitLock);479 Assert(RTCritSectIsOwner(&pThis->XmitLock)); 480 480 481 481 /* … … 543 543 { 544 544 PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp); 545 // Assert(RTCritSectIsOwner(&pThis->XmitLock);545 Assert(RTCritSectIsOwner(&pThis->XmitLock)); 546 546 drvNATFreeSgBuf(pThis, pSgBuf); 547 547 return VINF_SUCCESS; … … 555 555 PDRVNAT pThis = RT_FROM_MEMBER(pInterface, DRVNAT, INetworkUp); 556 556 Assert((pSgBuf->fFlags & PDMSCATTERGATHER_FLAGS_OWNER_MASK) == PDMSCATTERGATHER_FLAGS_OWNER_1); 557 // Assert(RTCritSectIsOwner(&pThis->XmitLock);557 Assert(RTCritSectIsOwner(&pThis->XmitLock)); 558 558 559 559 int rc; -
trunk/src/VBox/Devices/Network/DrvNetSniffer.cpp
r28258 r28275 87 87 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit} 88 88 */ 89 static DECLCALLBACK(int) drvNetSnifferUp_BeginXmit(PPDMINETWORKUP pInterface )89 static DECLCALLBACK(int) drvNetSnifferUp_BeginXmit(PPDMINETWORKUP pInterface, bool fOnWorkerThread) 90 90 { 91 91 PDRVNETSNIFFER pThis = RT_FROM_MEMBER(pInterface, DRVNETSNIFFER, INetworkUp); … … 97 97 return rc; 98 98 } 99 return pThis->pIBelowNet->pfnBeginXmit(pThis->pIBelowNet );99 return pThis->pIBelowNet->pfnBeginXmit(pThis->pIBelowNet, fOnWorkerThread); 100 100 } 101 101 -
trunk/src/VBox/Devices/Network/DrvTAP.cpp
r28258 r28275 124 124 PPDMTHREAD pThread; 125 125 126 /** @todo The transmit thread. */ 127 /** Transmit lock used by drvTAPNetworkUp_BeginXmit. */ 128 RTCRITSECT XmitLock; 129 126 130 #ifdef VBOX_WITH_STATISTICS 127 131 /** Number of sent packets. */ … … 165 169 166 170 171 172 /** 173 * @interface_method_impl{PDMINETWORKUP,pfnBeginXmit} 174 */ 175 static 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 167 188 /** 168 189 * @interface_method_impl{PDMINETWORKUP,pfnAllocBuf} … … 172 193 { 173 194 PDRVTAP pThis = PDMINETWORKUP_2_DRVTAP(pInterface); 195 Assert(RTCritSectIsOwner(&pThis->XmitLock)); 174 196 175 197 /* … … 216 238 { 217 239 PDRVTAP pThis = PDMINETWORKUP_2_DRVTAP(pInterface); 240 Assert(RTCritSectIsOwner(&pThis->XmitLock)); 218 241 if (pSgBuf) 219 242 { … … 238 261 AssertPtr(pSgBuf); 239 262 Assert((pSgBuf->fFlags & PDMSCATTERGATHER_FLAGS_MAGIC_MASK) == PDMSCATTERGATHER_FLAGS_MAGIC); 263 Assert(RTCritSectIsOwner(&pThis->XmitLock)); 240 264 241 265 int rc; … … 279 303 rc = rc == VERR_NO_MEMORY ? VERR_NET_NO_BUFFER_SPACE : VERR_NET_DOWN; 280 304 return rc; 305 } 306 307 308 /** 309 * @interface_method_impl{PDMINETWORKUP,pfnEndXmit} 310 */ 311 static DECLCALLBACK(void) drvTAPNetworkUp_EndXmit(PPDMINETWORKUP pInterface) 312 { 313 PDRVTAP pThis = PDMINETWORKUP_2_DRVTAP(pInterface); 314 RTCritSectLeave(&pThis->XmitLock); 281 315 } 282 316 … … 939 973 MMR3HeapFree(pThis->pszTerminateApplication); 940 974 975 /* 976 * Kill the xmit lock. 977 */ 978 if (RTCritSectIsInitialized(&pThis->XmitLock)) 979 RTCritSectDelete(&pThis->XmitLock); 980 941 981 #ifdef VBOX_WITH_STATISTICS 942 982 /* … … 983 1023 pDrvIns->IBase.pfnQueryInterface = drvTAPQueryInterface; 984 1024 /* INetwork */ 985 pThis->INetworkUp.pfn SendBuf = drvTAPNetworkUp_SendBuf;1025 pThis->INetworkUp.pfnBeginXmit = drvTAPNetworkUp_BeginXmit; 986 1026 pThis->INetworkUp.pfnAllocBuf = drvTAPNetworkUp_AllocBuf; 987 1027 pThis->INetworkUp.pfnFreeBuf = drvTAPNetworkUp_FreeBuf; 1028 pThis->INetworkUp.pfnSendBuf = drvTAPNetworkUp_SendBuf; 1029 pThis->INetworkUp.pfnEndXmit = drvTAPNetworkUp_EndXmit; 988 1030 pThis->INetworkUp.pfnSetPromiscuousMode = drvTAPNetworkUp_SetPromiscuousMode; 989 1031 pThis->INetworkUp.pfnNotifyLinkChanged = drvTAPNetworkUp_NotifyLinkChanged; … … 1053 1095 N_("Error running TAP setup application. rc=%d"), rc); 1054 1096 } 1097 1098 /* 1099 * Create the transmit lock. 1100 */ 1101 rc = RTCritSectInit(&pThis->XmitLock); 1102 AssertRCReturn(rc, rc); 1055 1103 1056 1104 /*
Note:
See TracChangeset
for help on using the changeset viewer.