Changeset 17184 in vbox for trunk/src/VBox/HostDrivers/VBoxNetFlt
- Timestamp:
- Feb 27, 2009 12:37:35 AM (16 years ago)
- svn:sync-xref-src-repo-rev:
- 43470
- Location:
- trunk/src/VBox/HostDrivers/VBoxNetFlt
- Files:
-
- 5 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/VBox/HostDrivers/VBoxNetFlt/VBoxNetFlt.c
r16927 r17184 236 236 237 237 238 AssertCompileMemberSize(VBOXNETFLTINS, enmState, sizeof(uint32_t)); 239 240 /** 241 * Sets the enmState member atomically. 242 * 243 * Used for all updates. 244 * 245 * @param pThis The instance. 246 * @param enmNewState The new value. 247 */ 248 DECLINLINE(void) vboxNetFltSetState(PVBOXNETFLTINS pThis, VBOXNETFTLINSSTATE enmNewState) 249 { 250 ASMAtomicWriteU32((uint32_t volatile *)&pThis->enmState, enmNewState); 251 } 252 253 254 /** 255 * Gets the enmState member atomically. 256 * 257 * Used for all reads. 258 * 259 * @returns The enmState value. 260 * @param pThis The instance. 261 */ 262 DECLINLINE(VBOXNETFTLINSSTATE) vboxNetFltGetState(PVBOXNETFLTINS pThis) 263 { 264 return (VBOXNETFTLINSSTATE)ASMAtomicUoReadU32((uint32_t volatile *)&pThis->enmState); 265 } 266 267 238 268 /** 239 269 * Finds a instance by its name, the caller does the locking. 240 *241 270 * 242 271 * @returns Pointer to the instance by the given name. NULL if not found. … … 256 285 /** 257 286 * Finds a instance by its name, will request the mutex. 287 * 288 * No reference to the instance is retained, we're assuming the caller to 289 * already have one but just for some reason doesn't have the pointer to it. 258 290 * 259 291 * @returns Pointer to the instance by the given name. NULL if not found. … … 300 332 301 333 302 AssertCompileMemberSize(VBOXNETFLTINS, enmState, sizeof(uint32_t));303 304 /**305 * Sets the enmState member atomically.306 *307 * Used for all updates.308 *309 * @param pThis The instance.310 * @param enmNewState The new value.311 */312 DECLINLINE(void) vboxNetFltSetState(PVBOXNETFLTINS pThis, VBOXNETFTLINSSTATE enmNewState)313 {314 ASMAtomicWriteU32((uint32_t volatile *)&pThis->enmState, enmNewState);315 }316 317 318 /**319 * Gets the enmState member atomically.320 *321 * Used for all reads.322 *323 * @returns The enmState value.324 * @param pThis The instance.325 */326 DECLINLINE(VBOXNETFTLINSSTATE) vboxNetFltGetState(PVBOXNETFLTINS pThis)327 {328 return (VBOXNETFTLINSSTATE)ASMAtomicUoReadU32((uint32_t volatile *)&pThis->enmState);329 }330 331 332 334 /** 333 335 * Performs interface rediscovery if it was disconnected from the host. … … 611 613 * Destroy a device that has been disconnected from the switch. 612 614 * 613 * @return true iff the instance is destroyed, false otherwise615 * @returns true if the instance is destroyed, false otherwise. 614 616 * @param pThis The instance to be destroyed. This is 615 617 * no longer valid when this function returns. 616 618 */ 617 static bool vboxNetFlt CheckDestroyInstance(PVBOXNETFLTINS pThis)619 static bool vboxNetFltDestroyInstance(PVBOXNETFLTINS pThis) 618 620 { 619 621 PVBOXNETFLTGLOBALS pGlobals = pThis->pGlobals; 622 uint32_t cRefs = ASMAtomicUoReadU32((uint32_t volatile *)&pThis->cRefs); 620 623 int rc; 621 uint32_t cRefs = ASMAtomicUoReadU32((uint32_t volatile *)&pThis->cRefs); 622 LogFlow(("vboxNetFltCheckDestroyInstance: pThis=%p (%s)\n", pThis, pThis->szName)); 624 LogFlow(("vboxNetFltDestroyInstance: pThis=%p (%s)\n", pThis, pThis->szName)); 623 625 624 626 /* … … 638 640 639 641 /* 640 * Make sure the state is 'disconnecting' and let the OS specific code641 * do its part of the cleanup outside the mutex.642 * Make sure the state is 'disconnecting' / 'destroying' and let the OS 643 * specific code do its part of the cleanup outside the mutex. 642 644 */ 643 645 rc = RTSemFastMutexRequest(pGlobals->hFastMtx); AssertRC(rc); 644 if(cRefs != 0) 646 #ifdef VBOXNETFLT_STATIC_CONFIG 647 /** @todo r=bird: This looks kind of insane! I ASSUME this is specific to the 648 * static config and to devices in the Unconnected state only. This *looks* like 649 * a very unhealthy race between driver unloading and vboxNetFltFactoryCreateAndConnect. 650 * If I'm right, then vboxNetFltFactoryCreateAndConnect should be made to back down one 651 * way or the other, it should not the other way around. (see suggestion further down) 652 * 653 * If I'm wrong, then please explain in full. 654 */ 655 if (cRefs != 0) 645 656 { 646 657 Assert(cRefs < UINT32_MAX / 2); … … 649 660 } 650 661 vboxNetFltSetState(pThis, kVBoxNetFltInsState_Destroying); 662 #else 663 vboxNetFltSetState(pThis, kVBoxNetFltInsState_Disconnecting); 664 #endif 651 665 RTSemFastMutexRelease(pGlobals->hFastMtx); 652 666 … … 716 730 cRefs = ASMAtomicDecU32(&pThis->cRefs); 717 731 if (!cRefs) 718 vboxNetFlt CheckDestroyInstance(pThis);732 vboxNetFltDestroyInstance(pThis); 719 733 else 720 734 Assert(cRefs < UINT32_MAX / 2); … … 822 836 { 823 837 vboxNetFltSetState(pThis, kVBoxNetFltInsState_Connected); 824 #ifdef VBOXNETFLT_STATIC_CONFIG825 838 *ppIfPort = &pThis->MyPort; 826 #endif827 839 } 828 840 else … … 846 858 * @param pszName The instance name. 847 859 * @param pSwitchPort The port on the switch that we're connected with (dynamic only). 860 * @param fNoPromisc Do not attempt going into promiscuous mode. 861 * @param pvContext Context argument for vboxNetFltOsInitInstance. 848 862 * @param ppIfPort Where to store the pointer to our port interface (dynamic only). 849 * @param fNoPromisc Do not attempt going into promiscuous mode. 850 */ 851 static int vboxNetFltNewInstance(PVBOXNETFLTGLOBALS pGlobals, const char *pszName, PINTNETTRUNKSWPORT pSwitchPort, PINTNETTRUNKIFPORT *ppIfPort, bool fNoPromisc 852 #ifdef VBOXNETFLT_STATIC_CONFIG 853 , void * pContext 854 #endif 855 ) 863 */ 864 static int vboxNetFltNewInstance(PVBOXNETFLTGLOBALS pGlobals, const char *pszName, PINTNETTRUNKSWPORT pSwitchPort, 865 bool fNoPromisc, void *pvContext, PINTNETTRUNKIFPORT *ppIfPort) 856 866 { 857 867 /* … … 914 924 * Call the OS specific initialization code. 915 925 */ 916 rc = vboxNetFltOsInitInstance(pNew 917 #ifdef VBOXNETFLT_STATIC_CONFIG 918 , pContext 919 #endif 920 ); 926 rc = vboxNetFltOsInitInstance(pNew, pvContext); 921 927 RTSemFastMutexRequest(pGlobals->hFastMtx); 922 928 if (RT_SUCCESS(rc)) 923 929 { 924 930 #ifdef VBOXNETFLT_STATIC_CONFIG 931 /* 932 * Static instances are unconnected at birth. 933 */ 934 Assert(!pSwitchPort); 925 935 pNew->enmState = kVBoxNetFltInsState_Unconnected; 926 Assert(!pSwitchPort);936 RTSemFastMutexRelease(pGlobals->hFastMtx); 927 937 *ppIfPort = &pNew->MyPort; 928 RTSemFastMutexRelease(pGlobals->hFastMtx);929 938 return rc; 930 939 931 #else 940 #else /* !VBOXNETFLT_STATIC_CONFIG */ 932 941 /* 933 942 * Connect it as well, the OS specific bits has to be done outside … … 938 947 { 939 948 RTSemFastMutexRelease(pGlobals->hFastMtx); 940 *ppIfPort = &pNew->MyPort;949 Assert(*ppIfPort == &pNew->MyPort); 941 950 return rc; 942 951 } … … 944 953 /* Bail out (failed). */ 945 954 vboxNetFltOsDeleteInstance(pNew); 946 #endif 955 #endif /* !VBOXNETFLT_STATIC_CONFIG */ 947 956 } 948 957 vboxNetFltUnlinkLocked(pGlobals, pNew); … … 962 971 } 963 972 973 964 974 #ifdef VBOXNETFLT_STATIC_CONFIG 965 966 /** 967 * searches for the NetFlt instance by its name and creates the new one if not found 968 * 969 * @return VINF_SUCCESS if new instance was created, VINF_ALREADY_INITIALIZED if an instanmce already exists, 970 * VERR_xxx in case of a failure 971 */ 972 DECLHIDDEN(int) vboxNetFltSearchCreateInstance(PVBOXNETFLTGLOBALS pGlobals, const char *pszName, PVBOXNETFLTINS *ppInstance, void * pContext) 975 /** 976 * Searches for the NetFlt instance by its name and creates the new one if not found. 977 * 978 * @returns VBox status code. 979 * @retval VINF_SUCCESS and *ppInstance if a new instance was created. 980 * @retval VINF_ALREADY_INITIALIZED and *ppInstance if an instance already exists. 981 * 982 * @param pGlobal Pointer to the globals. 983 * @param pszName The instance name. 984 * @param ppInstance Where to return the instance pointer on success. 985 * @param pvContext Context which needs to be passed along to vboxNetFltOsInitInstance. 986 */ 987 DECLHIDDEN(int) vboxNetFltSearchCreateInstance(PVBOXNETFLTGLOBALS pGlobals, const char *pszName, PVBOXNETFLTINS *ppInstance, void *pvContext) 973 988 { 974 989 PINTNETTRUNKIFPORT pIfPort; … … 978 993 AssertRCReturn(rc, rc); 979 994 995 /* 996 * Look for an existing instance in the list. 997 * 998 * If found that it's being destroyed, wait for it to go away. 999 * Return instances in other states ASSUMING that it has lost the 1000 * connection. 1001 */ 980 1002 *ppInstance = vboxNetFltFindInstanceLocked(pGlobals, pszName); 981 if(*ppInstance)1003 while (*ppInstance) 982 1004 { 983 1005 VBOXNETFTLINSSTATE enmState = vboxNetFltGetState(*ppInstance); 984 if(enmState != kVBoxNetFltInsState_Destroying && enmState != kVBoxNetFltInsState_Destroyed) 1006 if ( enmState != kVBoxNetFltInsState_Destroying 1007 && enmState != kVBoxNetFltInsState_Destroyed) 985 1008 { 986 vboxNetFltRetain(*ppInstance, false); 1009 /** @todo r=bird: who is making sure this is a genuine reconnection case? */ 1010 vboxNetFltRetain(*ppInstance, false /* fBusy */); 987 1011 RTSemFastMutexRelease(pGlobals->hFastMtx); 988 1012 return VINF_ALREADY_INITIALIZED; 989 1013 } 990 1014 991 /*wait for the instance to be removed from the list */ 992 993 *ppInstance = NULL; 994 995 do 996 { 997 RTSemFastMutexRelease(pGlobals->hFastMtx); 998 999 RTSemEventWait(pGlobals->hTimerEvent, 2); 1000 1001 rc = RTSemFastMutexRequest(pGlobals->hFastMtx); 1002 AssertRCReturn(rc, rc); 1003 } while(vboxNetFltFindInstanceLocked(pGlobals, pszName)); 1015 /* wait 2 ms */ /** @todo r=bird: Doesn't RTThreadSleep() work here? If it's bust, I'd like to know it so we can fix it... */ 1016 RTSemFastMutexRelease(pGlobals->hFastMtx); 1017 RTSemEventWait(pGlobals->hBlockEvent, 2); 1018 rc = RTSemFastMutexRequest(pGlobals->hFastMtx); 1019 AssertRCReturn(rc, rc); 1020 1021 /* try again */ 1022 *ppInstance = vboxNetFltFindInstanceLocked(pGlobals, pszName); 1004 1023 } 1005 1024 1006 1025 RTSemFastMutexRelease(pGlobals->hFastMtx); 1007 1026 1008 rc = vboxNetFltNewInstance(pGlobals, pszName, NULL, &pIfPort, false, pContext); 1009 if(RT_SUCCESS(rc)) 1010 *ppInstance = IFPORT_2_VBOXNETFLTINS(pIfPort); 1027 /* 1028 * Try create a new instance. 1029 * (fNoPromisc is overridden in the vboxNetFltFactoryCreateAndConnect path, so pass true here.) 1030 */ 1031 rc = vboxNetFltNewInstance(pGlobals, pszName, NULL, true /* fNoPromisc */, pvContext, &pIfPort); 1032 if (RT_SUCCESS(rc)) 1033 *ppInstance = IFPORT_2_VBOXNETFLTINS(pIfPort); 1011 1034 else 1012 1035 *ppInstance = NULL; … … 1014 1037 return rc; 1015 1038 } 1016 1017 #endif 1039 #endif /* VBOXNETFLT_STATIC_CONFIG */ 1040 1018 1041 1019 1042 /** … … 1021 1044 */ 1022 1045 static DECLCALLBACK(int) vboxNetFltFactoryCreateAndConnect(PINTNETTRUNKFACTORY pIfFactory, const char *pszName, 1023 PINTNETTRUNKSWPORT pSwitchPort, PINTNETTRUNKIFPORT *ppIfPort, bool fNoPromisc) 1046 PINTNETTRUNKSWPORT pSwitchPort, uint32_t fFlags, 1047 PINTNETTRUNKIFPORT *ppIfPort) 1024 1048 { 1025 1049 PVBOXNETFLTGLOBALS pGlobals = (PVBOXNETFLTGLOBALS)((uint8_t *)pIfFactory - RT_OFFSETOF(VBOXNETFLTGLOBALS, TrunkFactory)); … … 1027 1051 int rc; 1028 1052 1029 LogFlow(("vboxNetFltFactoryCreateAndConnect: pszName=%p:{%s} \n", pszName, pszName));1053 LogFlow(("vboxNetFltFactoryCreateAndConnect: pszName=%p:{%s} fFlags=%#x\n", pszName, pszName, fFlags)); 1030 1054 Assert(pGlobals->cFactoryRefs > 0); 1055 AssertMsgReturn(fFlags & ~(INTNETTRUNKFACTORY_FLAG_NO_PROMISC), 1056 ("%#x\n", fFlags), VERR_INVALID_PARAMETER); 1031 1057 1032 1058 /* … … 1039 1065 #if defined(VBOX_TAPMINIPORT) && defined(RT_OS_WINDOWS) 1040 1066 /* temporary hack to pick up the first adapter */ 1041 pCur = pGlobals->pInstanceHead; 1067 pCur = pGlobals->pInstanceHead; /** @todo Don't for get to remove this temporary hack... :-) */ 1042 1068 #else 1043 1069 pCur = vboxNetFltFindInstanceLocked(pGlobals, pszName); … … 1046 1072 { 1047 1073 #ifdef VBOXNETFLT_STATIC_CONFIG 1048 switch (vboxNetFltGetState(pCur)) 1074 # if 0 /** @todo r=bird: We need to fix the race here. The race is against release+destructor, the 1075 * tell tale is a cRefs of and since cRefs is manipulated in an atomic fashion we can simply attempt 1076 * to grab a reference atomically, the worst thing that can happen is that we have to decrement it again.. 1077 * Here is my suggestion: */ 1078 /* Try grab a reference. If the count had already reached zero we're racing the 1079 destructor code and must back down. */ 1080 uint32_t cRefs = ASMAtomicIncU32(&pCur->cRefs); 1081 if (cRefs > 1) 1049 1082 { 1050 case kVBoxNetFltInsState_Unconnected: 1051 /* instance can be destroyed when it is neither used by the IntNet nor by the ndis filter driver mechanism 1052 * (i.e. the driver is not bound to the specified adapter)*/ 1053 /* Prevent setting promiscuous mode for WiFi adapters. */ 1054 pCur->fDisablePromiscuous = fNoPromisc; 1055 LogAleksey(("fNoPromisc=%d\n", pCur->fDisablePromiscuous)); 1056 vboxNetFltRetain(pCur, false /* fBusy */); /** @todo who releases this on failure? */ 1083 if (vboxNetFltGetState(pCur) == kVBoxNetFltInsState_Unconnected) 1084 { 1085 pCur->fDisablePromiscuous = !!(fFlags & INTNETTRUNKFACTORY_FLAG_NO_PROMISC); 1057 1086 rc = vboxNetFltConnectIt(pCur, pSwitchPort, ppIfPort); 1058 break; 1059 case kVBoxNetFltInsState_Connected: 1060 AssertFailed(); 1087 if (RT_SUCCESS(rc)) 1088 pCur = NULL; /* Don't release it, reference given to the caller. */ 1089 } 1090 else 1061 1091 rc = VERR_INTNET_FLT_IF_BUSY; 1062 break;1063 case kVBoxNetFltInsState_Disconnecting:1064 AssertFailed();1065 rc = VERR_INTNET_FLT_IF_BUSY;1066 break;1067 default:1068 /** @todo what? */1069 rc = VERR_INTNET_FLT_IF_BUSY;1070 break;1071 1092 } 1093 else 1094 { 1095 Assert(cRefs == 1); 1096 ASMAtomicDecU32(&pCur->cRefs); 1097 pCur = NULL; /* nothing to release */ 1098 rc = VERR_INTNET_FLT_IF_NOT_FOUND; 1099 } 1100 1101 RTSemFastMutexRelease(pGlobals->hFastMtx); 1102 if (pCur) 1103 vboxNetFltRelease(pCur, false /* fBusy */); 1104 1105 # else 1106 if (vboxNetFltGetState(pCur) == kVBoxNetFltInsState_Unconnected) 1107 { 1108 vboxNetFltRetain(pCur, false /* fBusy */); /** @todo r=bird: Who releases this on failure? */ 1109 pCur->fDisablePromiscuous = !!(fFlags & INTNETTRUNKFACTORY_FLAG_NO_PROMISC); 1110 rc = vboxNetFltConnectIt(pCur, pSwitchPort, ppIfPort); 1111 } 1112 else 1113 rc = VERR_INTNET_FLT_IF_BUSY; 1114 RTSemFastMutexRelease(pGlobals->hFastMtx); 1115 # endif 1072 1116 #else 1073 1117 rc = VERR_INTNET_FLT_IF_BUSY; 1118 RTSemFastMutexRelease(pGlobals->hFastMtx); 1074 1119 #endif 1075 RTSemFastMutexRelease(pGlobals->hFastMtx);1076 1120 LogFlow(("vboxNetFltFactoryCreateAndConnect: returns %Rrc\n", rc)); 1077 1121 return rc; … … 1086 1130 * Dynamically create a new instance. 1087 1131 */ 1088 rc = vboxNetFltNewInstance(pGlobals, pszName, pSwitchPort, ppIfPort, fNoPromisc); 1132 rc = vboxNetFltNewInstance(pGlobals, pszName, pSwitchPort, 1133 !!(fFlags & INTNETTRUNKFACTORY_FLAG_NO_PROMISC), 1134 ppIfPort); 1089 1135 #endif 1090 1136 LogFlow(("vboxNetFltFactoryCreateAndConnect: returns %Rrc\n", rc)); … … 1165 1211 } 1166 1212 1167 /** 1168 * tries to deinitialize Idc 1169 * we separate the globals settings "base" which is actually 1170 * "general" globals settings except for Idc, and idc. 1171 * This is needed for windows filter driver, which gets loaded prior to VBoxDrv, 1172 * thus it's not possible to make idc initialization from the driver startup routine for it, 1173 * though the "base is still needed for the driver to functions". 1174 * @param pGlobals 1175 * @return VINF_SUCCESS on succes, VERR_WRONG_ORDER if we're busy. 1213 1214 /** 1215 * Try to close the IDC connection to SUPDRV if established. 1216 * 1217 * @returns VBox status code. 1218 * @retval VINF_SUCCESS on success. 1219 * @retval VERR_WRONG_ORDER if we're busy. 1220 * 1221 * @param pGlobals Pointer to the globals. 1222 * 1223 * @sa vboxNetFltTryDeleteIdcAndGlobals() 1176 1224 */ 1177 1225 DECLHIDDEN(int) vboxNetFltTryDeleteIdc(PVBOXNETFLTGLOBALS pGlobals) … … 1187 1235 return VERR_WRONG_ORDER; 1188 1236 1189 /* 1190 * Disconnect from SUPDRV and check that nobody raced us, 1191 * reconnect if that should happen. 1192 */ 1193 rc = SUPR0IdcComponentDeregisterFactory(&pGlobals->SupDrvIDC, &pGlobals->SupDrvFactory); 1194 AssertRC(rc); 1195 if (!vboxNetFltCanUnload(pGlobals)) 1237 if (!pGlobals->fIDCOpen) 1238 rc = VINF_SUCCESS; 1239 else 1240 { 1241 /* 1242 * Disconnect from SUPDRV and check that nobody raced us, 1243 * reconnect if that should happen. 1244 */ 1245 rc = SUPR0IdcComponentDeregisterFactory(&pGlobals->SupDrvIDC, &pGlobals->SupDrvFactory); 1246 AssertRC(rc); 1247 if (!vboxNetFltCanUnload(pGlobals)) 1248 { 1249 rc = SUPR0IdcComponentRegisterFactory(&pGlobals->SupDrvIDC, &pGlobals->SupDrvFactory); 1250 AssertRC(rc); 1251 return VERR_WRONG_ORDER; 1252 } 1253 1254 SUPR0IdcClose(&pGlobals->SupDrvIDC); 1255 pGlobals->fIDCOpen = false; 1256 } 1257 1258 return rc; 1259 } 1260 1261 1262 /** 1263 * Establishes the IDC connection to SUPDRV and registers our component factory. 1264 * 1265 * @returns VBox status code. 1266 * @param pGlobals Pointer to the globals. 1267 * @sa vboxNetFltInitGlobalsAndIdc(). 1268 */ 1269 DECLHIDDEN(int) vboxNetFltInitIdc(PVBOXNETFLTGLOBALS pGlobals) 1270 { 1271 int rc; 1272 Assert(!pGlobals->fIDCOpen); 1273 1274 /* 1275 * Establish a connection to SUPDRV and register our component factory. 1276 */ 1277 rc = SUPR0IdcOpen(&pGlobals->SupDrvIDC, 0 /* iReqVersion = default */, 0 /* iMinVersion = default */, NULL, NULL, NULL); 1278 if (RT_SUCCESS(rc)) 1196 1279 { 1197 1280 rc = SUPR0IdcComponentRegisterFactory(&pGlobals->SupDrvIDC, &pGlobals->SupDrvFactory); 1198 AssertRC(rc); 1199 return VERR_WRONG_ORDER; 1281 if (RT_SUCCESS(rc)) 1282 { 1283 pGlobals->fIDCOpen = true; 1284 Log(("VBoxNetFlt: pSession=%p\n", SUPR0IdcGetSession(&pGlobals->SupDrvIDC))); 1285 return rc; 1286 } 1287 1288 /* bail out. */ 1289 LogRel(("VBoxNetFlt: Failed to register component factory, rc=%Rrc\n", rc)); 1290 SUPR0IdcClose(&pGlobals->SupDrvIDC); 1200 1291 } 1201 1292 1202 SUPR0IdcClose(&pGlobals->SupDrvIDC);1203 1204 1293 return rc; 1205 1294 } 1206 1295 1207 /** 1208 * performs "base" globals deinitialization 1209 * we separate the globals settings "base" which is actually 1210 * "general" globals settings except for Idc, and idc. 1211 * This is needed for windows filter driver, which gets loaded prior to VBoxDrv, 1212 * thus it's not possible to make idc initialization from the driver startup routine for it, 1213 * though the "base is still needed for the driver to functions". 1214 * @param pGlobals 1215 * @return none 1216 */ 1217 DECLHIDDEN(void) vboxNetFltDeleteGlobalsBase(PVBOXNETFLTGLOBALS pGlobals) 1218 { 1296 1297 /** 1298 * Deletes the globals. 1299 * 1300 * This must be called after the IDC connection has been closed, 1301 * see vboxNetFltTryDeleteIdc(). 1302 * 1303 * @param pGlobals Pointer to the globals. 1304 * @sa vboxNetFltTryDeleteIdcAndGlobals() 1305 */ 1306 DECLHIDDEN(void) vboxNetFltDeleteGlobals(PVBOXNETFLTGLOBALS pGlobals) 1307 { 1308 Assert(!pGlobals->fIDCOpen); 1309 1219 1310 /* 1220 1311 * Release resources. … … 1224 1315 1225 1316 #ifdef VBOXNETFLT_STATIC_CONFIG 1226 RTSemEventDestroy(pGlobals->h TimerEvent);1227 pGlobals->h TimerEvent = NIL_RTSEMEVENT;1317 RTSemEventDestroy(pGlobals->hBlockEvent); 1318 pGlobals->hBlockEvent = NIL_RTSEMEVENT; 1228 1319 #endif 1229 1320 1230 1321 } 1231 1322 1232 /** 1233 * Called by the native part when the OS wants the driver to unload. 1234 * 1235 * @returns VINF_SUCCESS on succes, VERR_WRONG_ORDER if we're busy.1236 * 1323 1324 /** 1325 * Initializes the globals. 1326 * 1327 * @returns VBox status code. 1237 1328 * @param pGlobals Pointer to the globals. 1238 */ 1239 DECLHIDDEN(int) vboxNetFltTryDeleteGlobals(PVBOXNETFLTGLOBALS pGlobals) 1240 { 1241 int rc = vboxNetFltTryDeleteIdc(pGlobals); 1242 if(RT_SUCCESS(rc)) 1243 { 1244 vboxNetFltDeleteGlobalsBase(pGlobals); 1245 } 1246 return rc; 1247 } 1248 1249 /** 1250 * performs the "base" globals initialization 1251 * we separate the globals initialization to globals "base" initialization which is actually 1252 * "general" globals initialization except for Idc not being initialized, and idc initialization. 1253 * This is needed for windows filter driver, which gets loaded prior to VBoxDrv, 1254 * thus it's not possible to make idc initialization from the driver startup routine for it. 1255 * 1256 * @returns VBox status code. 1257 * @param pGlobals Pointer to the globals. */ 1258 DECLHIDDEN(int) vboxNetFltInitGlobalsBase(PVBOXNETFLTGLOBALS pGlobals) 1329 * @sa vboxNetFltInitGlobalsAndIdc(). 1330 */ 1331 DECLHIDDEN(int) vboxNetFltInitGlobals(PVBOXNETFLTGLOBALS pGlobals) 1259 1332 { 1260 1333 /* … … 1265 1338 { 1266 1339 #ifdef VBOXNETFLT_STATIC_CONFIG 1267 rc = RTSemEventCreate(&pGlobals->h TimerEvent);1340 rc = RTSemEventCreate(&pGlobals->hBlockEvent); 1268 1341 if (RT_SUCCESS(rc)) 1269 1342 { … … 1279 1352 #endif 1280 1353 pGlobals->SupDrvFactory.pfnQueryFactoryInterface = vboxNetFltQueryFactoryInterface; 1354 pGlobals->fIDCOpen = false; 1281 1355 1282 1356 return rc; … … 1290 1364 } 1291 1365 1292 /** 1293 * performs the Idc initialization 1294 * we separate the globals initialization to globals "base" initialization which is actually 1295 * "general" globals initialization except for Idc not being initialized, and idc initialization. 1296 * This is needed for windows filter driver, which gets loaded prior to VBoxDrv, 1297 * thus it's not possible to make idc initialization from the driver startup routine for it. 1298 * 1299 * @returns VBox status code. 1300 * @param pGlobals Pointer to the globals. */ 1301 DECLHIDDEN(int) vboxNetFltInitIdc(PVBOXNETFLTGLOBALS pGlobals) 1302 { 1303 int rc; 1304 /* 1305 * Establish a connection to SUPDRV and register our component factory. 1306 */ 1307 rc = SUPR0IdcOpen(&pGlobals->SupDrvIDC, 0 /* iReqVersion = default */, 0 /* iMinVersion = default */, NULL, NULL, NULL); 1366 1367 /** 1368 * Called by the native part when the OS wants the driver to unload. 1369 * 1370 * @returns VINF_SUCCESS on success, VERR_WRONG_ORDER if we're busy. 1371 * 1372 * @param pGlobals Pointer to the globals. 1373 */ 1374 DECLHIDDEN(int) vboxNetFltTryDeleteIdcAndGlobals(PVBOXNETFLTGLOBALS pGlobals) 1375 { 1376 int rc = vboxNetFltTryDeleteIdc(pGlobals); 1308 1377 if (RT_SUCCESS(rc)) 1309 { 1310 rc = SUPR0IdcComponentRegisterFactory(&pGlobals->SupDrvIDC, &pGlobals->SupDrvFactory); 1311 if (RT_SUCCESS(rc)) 1312 { 1313 Log(("VBoxNetFlt: pSession=%p\n", SUPR0IdcGetSession(&pGlobals->SupDrvIDC))); 1314 return rc; 1315 } 1316 1317 /* bail out. */ 1318 LogRel(("VBoxNetFlt: Failed to register component factory, rc=%Rrc\n", rc)); 1319 SUPR0IdcClose(&pGlobals->SupDrvIDC); 1320 } 1321 1378 vboxNetFltDeleteGlobals(pGlobals); 1322 1379 return rc; 1323 1380 } 1324 1381 1382 1325 1383 /** 1326 1384 * Called by the native driver/kext module initialization routine. 1327 1385 * 1328 1386 * It will initialize the common parts of the globals, assuming the caller 1329 * has already taken care of the OS specific bits. 1387 * has already taken care of the OS specific bits, and establish the IDC 1388 * connection to SUPDRV. 1330 1389 * 1331 1390 * @returns VBox status code. 1332 1391 * @param pGlobals Pointer to the globals. 1333 1392 */ 1334 DECLHIDDEN(int) vboxNetFltInitGlobals (PVBOXNETFLTGLOBALS pGlobals)1393 DECLHIDDEN(int) vboxNetFltInitGlobalsAndIdc(PVBOXNETFLTGLOBALS pGlobals) 1335 1394 { 1336 1395 /* 1337 1396 * Initialize the common portions of the structure. 1338 1397 */ 1339 int rc = vboxNetFltInitGlobals Base(pGlobals);1398 int rc = vboxNetFltInitGlobals(pGlobals); 1340 1399 if (RT_SUCCESS(rc)) 1341 1400 { 1342 1401 rc = vboxNetFltInitIdc(pGlobals); 1343 1402 if (RT_SUCCESS(rc)) 1344 {1345 1403 return rc; 1346 }1347 1404 1348 1405 /* bail out. */ 1349 vboxNetFltDeleteGlobals Base(pGlobals);1406 vboxNetFltDeleteGlobals(pGlobals); 1350 1407 } 1351 1408 -
trunk/src/VBox/HostDrivers/VBoxNetFlt/VBoxNetFltInternal.h
r16183 r17184 68 68 * Partly for reasons of deadlock avoidance again. */ 69 69 kVBoxNetFltInsState_Disconnecting, 70 #ifdef VBOXNETFLT_STATIC_CONFIG 70 71 /** Destroying the instance 71 72 * Partly for reasons of deadlock avoidance again. */ 72 73 kVBoxNetFltInsState_Destroying, 74 #endif 73 75 /** The instance has been disconnected from both the host and the internal network. */ 74 76 kVBoxNetFltInsState_Destroyed, … … 255 257 /** The number of current factory references. */ 256 258 int32_t volatile cFactoryRefs; 257 #ifdef VBOXNETFLT_STATIC_CONFIG 258 /* wait timer event */ 259 RTSEMEVENT hTimerEvent; 260 #endif 259 /** Whether the IDC connection is open or not. 260 * This is only for cleaning up correctly after the separate IDC init on Windows. */ 261 bool fIDCOpen; 261 262 /** The SUPDRV IDC handle (opaque struct). */ 262 263 SUPDRVIDCHANDLE SupDrvIDC; 264 265 #ifdef VBOXNETFLT_STATIC_CONFIG 266 /** Something we can block on while waiting for an instance to be unlinked. */ 267 RTSEMEVENT hBlockEvent; 268 #endif 263 269 } VBOXNETFLTGLOBALS; 264 270 265 271 272 DECLHIDDEN(int) vboxNetFltInitGlobalsAndIdc(PVBOXNETFLTGLOBALS pGlobals); 266 273 DECLHIDDEN(int) vboxNetFltInitGlobals(PVBOXNETFLTGLOBALS pGlobals); 267 DECLHIDDEN(int) vboxNetFltTryDeleteGlobals(PVBOXNETFLTGLOBALS pGlobals); 274 DECLHIDDEN(int) vboxNetFltInitIdc(PVBOXNETFLTGLOBALS pGlobals); 275 DECLHIDDEN(int) vboxNetFltTryDeleteIdcAndGlobals(PVBOXNETFLTGLOBALS pGlobals); 276 DECLHIDDEN(void) vboxNetFltDeleteGlobals(PVBOXNETFLTGLOBALS pGlobals); 277 DECLHIDDEN(int) vboxNetFltTryDeleteIdc(PVBOXNETFLTGLOBALS pGlobals); 278 268 279 DECLHIDDEN(bool) vboxNetFltCanUnload(PVBOXNETFLTGLOBALS pGlobals); 269 280 DECLHIDDEN(PVBOXNETFLTINS) vboxNetFltFindInstance(PVBOXNETFLTGLOBALS pGlobals, const char *pszName); … … 274 285 #ifdef VBOXNETFLT_STATIC_CONFIG 275 286 DECLHIDDEN(int) vboxNetFltSearchCreateInstance(PVBOXNETFLTGLOBALS pGlobals, const char *pszName, PVBOXNETFLTINS *ppInstance, void * pContext); 276 DECLHIDDEN(int) vboxNetFltInitGlobalsBase(PVBOXNETFLTGLOBALS pGlobals); 277 DECLHIDDEN(int) vboxNetFltInitIdc(PVBOXNETFLTGLOBALS pGlobals); 278 DECLHIDDEN(void) vboxNetFltDeleteGlobalsBase(PVBOXNETFLTGLOBALS pGlobals); 279 DECLHIDDEN(int) vboxNetFltTryDeleteIdc(PVBOXNETFLTGLOBALS pGlobals); 280 #endif 287 #endif 288 281 289 282 290 -
trunk/src/VBox/HostDrivers/VBoxNetFlt/darwin/VBoxNetFlt-darwin.cpp
r16195 r17184 171 171 */ 172 172 memset(&g_VBoxNetFltGlobals, 0, sizeof(g_VBoxNetFltGlobals)); 173 rc = vboxNetFltInitGlobals (&g_VBoxNetFltGlobals);173 rc = vboxNetFltInitGlobalsAndIdc(&g_VBoxNetFltGlobals); 174 174 if (RT_SUCCESS(rc)) 175 175 { … … 204 204 * tracking for us! 205 205 */ 206 int rc = vboxNetFltTryDelete Globals(&g_VBoxNetFltGlobals);206 int rc = vboxNetFltTryDeleteIdcAndGlobals(&g_VBoxNetFltGlobals); 207 207 if (RT_FAILURE(rc)) 208 208 { -
trunk/src/VBox/HostDrivers/VBoxNetFlt/linux/VBoxNetFlt-linux.c
r17062 r17184 99 99 flags = (dev->flags & ~(IFF_PROMISC | 100 100 IFF_ALLMULTI | 101 IFF_RUNNING)) | 101 IFF_RUNNING)) | 102 102 (dev->gflags & (IFF_PROMISC | 103 103 IFF_ALLMULTI)); … … 209 209 { 210 210 Log(("vboxTapValidateAddr: %02x:%02x:%02x:%02x:%02x:%02x\n", 211 dev->dev_addr[0], dev->dev_addr[1], dev->dev_addr[2], 211 dev->dev_addr[0], dev->dev_addr[1], dev->dev_addr[2], 212 212 dev->dev_addr[3], dev->dev_addr[4], dev->dev_addr[5])); 213 213 return -EADDRNOTAVAIL; … … 221 221 /// @todo Use Sun vendor id 222 222 memcpy(pNetDev->dev_addr, "\0vbnet", ETH_ALEN); 223 Log(("vboxTapNetDevInit: pNetDev->dev_addr = %.6Rhxd\n", pNetDev->dev_addr)); 223 Log(("vboxTapNetDevInit: pNetDev->dev_addr = %.6Rhxd\n", pNetDev->dev_addr)); 224 224 pNetDev->open = vboxTapOpen; 225 225 pNetDev->stop = vboxTapStop; … … 297 297 */ 298 298 memset(&g_VBoxNetFltGlobals, 0, sizeof(g_VBoxNetFltGlobals)); 299 rc = vboxNetFltInitGlobals (&g_VBoxNetFltGlobals);299 rc = vboxNetFltInitGlobalsAndIdc(&g_VBoxNetFltGlobals); 300 300 if (RT_SUCCESS(rc)) 301 301 { … … 337 337 rc = vboxTapUnregisterNetDev(); 338 338 AssertRC(rc); 339 rc = vboxNetFltTryDelete Globals(&g_VBoxNetFltGlobals);339 rc = vboxNetFltTryDeleteIdcAndGlobals(&g_VBoxNetFltGlobals); 340 340 AssertRC(rc); NOREF(rc); 341 341 … … 598 598 if (!pBuf) 599 599 return 0; 600 600 601 601 pThis = VBOX_FLT_PT_TO_INST(pPacketType); 602 602 pDev = (struct net_device *)ASMAtomicUoReadPtr((void * volatile *)&pThis->u.s.pDev); … … 669 669 } 670 670 #endif 671 671 672 672 dev_kfree_skb(pBuf); 673 673 } … … 1088 1088 { 1089 1089 if (pThis->u.s.fPromiscuousSet) 1090 { 1090 { 1091 1091 rtnl_lock(); 1092 1092 dev_set_promiscuity(pDev, -1); -
trunk/src/VBox/HostDrivers/VBoxNetFlt/solaris/VBoxNetFlt-solaris.c
r16928 r17184 430 430 */ 431 431 memset(&g_VBoxNetFltSolarisGlobals, 0, sizeof(g_VBoxNetFltSolarisGlobals)); 432 rc = vboxNetFltInitGlobals (&g_VBoxNetFltSolarisGlobals);432 rc = vboxNetFltInitGlobalsAndIdc(&g_VBoxNetFltSolarisGlobals); 433 433 if (RT_SUCCESS(rc)) 434 434 { … … 438 438 439 439 LogRel((DEVICE_NAME ":mod_install failed. rc=%d\n", rc)); 440 vboxNetFltTryDelete Globals(&g_VBoxNetFltSolarisGlobals);440 vboxNetFltTryDeleteIdcAndGlobals(&g_VBoxNetFltSolarisGlobals); 441 441 } 442 442 else … … 465 465 * Undo the work done during start (in reverse order). 466 466 */ 467 rc = vboxNetFltTryDelete Globals(&g_VBoxNetFltSolarisGlobals);467 rc = vboxNetFltTryDeleteIdcAndGlobals(&g_VBoxNetFltSolarisGlobals); 468 468 if (RT_FAILURE(rc)) 469 469 { … … 2976 2976 int Pcp:3; 2977 2977 int Cfi:1; 2978 int Vid:12; 2978 int Vid:12; 2979 2979 } VLANHEADER; 2980 2980
Note:
See TracChangeset
for help on using the changeset viewer.