Changeset View
Changeset View
Standalone View
Standalone View
sys/net/if.c
| Show First 20 Lines • Show All 473 Lines • ▼ Show 20 Lines | |||||
| { | { | ||||
| struct ifnet *ifp, *nifp; | struct ifnet *ifp, *nifp; | ||||
| struct ifnet **pending; | struct ifnet **pending; | ||||
| int found __diagused; | int found __diagused; | ||||
| int i; | int i; | ||||
| i = 0; | i = 0; | ||||
| /* The lock has already been aquired in vnet_destroy() */ | |||||
| sx_assert(&ifnet_detach_sxlock, SX_XLOCKED); | |||||
| /* | /* | ||||
| * We need to protect our access to the V_ifnet tailq. Ordinarily we'd | * We need to protect our access to the V_ifnet tailq. Ordinarily we'd | ||||
| * enter NET_EPOCH, but that's not possible, because if_vmove() calls | * enter NET_EPOCH, but that's not possible, because if_vmove() calls | ||||
| * if_detach_internal(), which waits for NET_EPOCH callbacks to | * if_detach_internal(), which waits for NET_EPOCH callbacks to | ||||
| * complete. We can't do that from within NET_EPOCH. | * complete. We can't do that from within NET_EPOCH. | ||||
| * | * | ||||
| * However, we can also use the IFNET_xLOCK, which is the V_ifnet | * However, we can also use the IFNET_xLOCK, which is the V_ifnet | ||||
| * read/write lock. We cannot hold the lock as we call if_vmove() | * read/write lock. We cannot hold the lock as we call if_vmove() | ||||
| Show All 12 Lines | if (ifp->if_home_vnet != ifp->if_vnet) { | ||||
| MPASS(found); | MPASS(found); | ||||
| pending[i++] = ifp; | pending[i++] = ifp; | ||||
| } | } | ||||
| } | } | ||||
| IFNET_WUNLOCK(); | IFNET_WUNLOCK(); | ||||
| for (int j = 0; j < i; j++) { | for (int j = 0; j < i; j++) { | ||||
| sx_xlock(&ifnet_detach_sxlock); | |||||
| if_vmove(pending[j], pending[j]->if_home_vnet); | if_vmove(pending[j], pending[j]->if_home_vnet); | ||||
| sx_xunlock(&ifnet_detach_sxlock); | |||||
| } | } | ||||
| free(pending, M_IFNET); | free(pending, M_IFNET); | ||||
| } | } | ||||
| VNET_SYSUNINIT(vnet_if_return, SI_SUB_VNET_DONE, SI_ORDER_ANY, | VNET_SYSUNINIT(vnet_if_return, SI_SUB_VNET_DONE, SI_ORDER_ANY, | ||||
| vnet_if_return, NULL); | vnet_if_return, NULL); | ||||
| #endif | #endif | ||||
| ▲ Show 20 Lines • Show All 4,592 Lines • Show Last 20 Lines | |||||