Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F150494168
D19248.id54460.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
4 KB
Referenced Files
None
Subscribers
None
D19248.id54460.diff
View Options
Index: sys/net/if_tun.c
===================================================================
--- sys/net/if_tun.c
+++ sys/net/if_tun.c
@@ -105,6 +105,7 @@
* which is static after setup.
*/
static struct mtx tunmtx;
+static eventhandler_tag tag;
static const char tunname[] = "tun";
static MALLOC_DEFINE(M_TUN, tunname, "Tunnel Interface");
static int tundebug = 0;
@@ -129,9 +130,12 @@
const struct sockaddr *, struct route *ro);
static void tunstart(struct ifnet *);
-static int tun_clone_create(struct if_clone *, int, caddr_t);
-static void tun_clone_destroy(struct ifnet *);
-static struct if_clone *tun_cloner;
+static int tun_clone_match(struct if_clone *ifc, const char *name);
+static int tun_clone_create(struct if_clone *, char *, size_t, caddr_t);
+static int tun_clone_destroy(struct if_clone *, struct ifnet *);
+static struct unrhdr *tun_unrhdr;
+VNET_DEFINE(struct if_clone *, tun_cloner);
+#define V_tun_cloner VNET(tun_cloner)
static d_open_t tunopen;
static d_close_t tunclose;
@@ -173,10 +177,35 @@
};
static int
-tun_clone_create(struct if_clone *ifc, int unit, caddr_t params)
+tun_clone_match(struct if_clone *ifc, const char *name)
+{
+ if (strncmp("tun", name, 3) == 0)
+ return (1);
+
+ return (0);
+}
+
+static int
+tun_clone_create(struct if_clone *ifc, char *name, size_t len, caddr_t params)
{
struct cdev *dev;
- int i;
+ int err, unit, i;
+
+ printf("KP: %s(%p, %s, %zu)\n", __FUNCTION__, ifc, name, len);
+ err = ifc_name2unit(name, &unit);
+ printf("KP: %s() unit %d, err %d\n", __FUNCTION__, unit, err);
+ if (err != 0)
+ return (err);
+
+ if (unit != -1) {
+ /* If this unit number is still available that/s okay. */
+ if (alloc_unr_specific(tun_unrhdr, unit) == -1)
+ return (EEXIST);
+ } else {
+ unit = alloc_unr(tun_unrhdr);
+ }
+
+ snprintf(name, IFNAMSIZ, "tun%d", unit);
/* find any existing device, or allocate new unit number */
i = clone_create(&tunclones, &tun_cdevsw, &unit, &dev, 0);
@@ -252,6 +281,7 @@
dev = tp->tun_dev;
bpfdetach(TUN2IFP(tp));
if_detach(TUN2IFP(tp));
+ free_unr(tun_unrhdr, TUN2IFP(tp)->if_dunit);
if_free(TUN2IFP(tp));
destroy_dev(dev);
seldrain(&tp->tun_rsel);
@@ -263,8 +293,8 @@
CURVNET_RESTORE();
}
-static void
-tun_clone_destroy(struct ifnet *ifp)
+static int
+tun_clone_destroy(struct if_clone *ifc, struct ifnet *ifp)
{
struct tun_softc *tp = ifp->if_softc;
@@ -272,39 +302,64 @@
TAILQ_REMOVE(&tunhead, tp, tun_list);
mtx_unlock(&tunmtx);
tun_destroy(tp);
+
+ return (0);
+}
+
+static void
+vnet_tun_init(const void *unused __unused)
+{
+ V_tun_cloner = if_clone_advanced(tunname, 0, tun_clone_match,
+ tun_clone_create, tun_clone_destroy);
+}
+VNET_SYSINIT(vnet_tun_init, SI_SUB_PROTO_IF, SI_ORDER_ANY,
+ vnet_tun_init, NULL);
+
+static void
+vnet_tun_uninit(const void *unused __unused)
+{
+ if_clone_detach(V_tun_cloner);
}
+VNET_SYSUNINIT(vnet_tun_uninit, SI_SUB_PROTO_IF, SI_ORDER_ANY,
+ vnet_tun_uninit, NULL);
+
+static void
+tun_uninit(const void *unused __unused)
+{
+ struct tun_softc *tp;
+
+ EVENTHANDLER_DEREGISTER(dev_clone, tag);
+ drain_dev_clone_events();
+
+ mtx_lock(&tunmtx);
+ while ((tp = TAILQ_FIRST(&tunhead)) != NULL) {
+ TAILQ_REMOVE(&tunhead, tp, tun_list);
+ mtx_unlock(&tunmtx);
+ tun_destroy(tp);
+ mtx_lock(&tunmtx);
+ }
+ mtx_unlock(&tunmtx);
+ delete_unrhdr(tun_unrhdr);
+ clone_cleanup(&tunclones);
+ mtx_destroy(&tunmtx);
+}
+SYSUNINIT(tun_uninit, SI_SUB_PROTO_IF, SI_ORDER_ANY, tun_uninit, NULL);
static int
tunmodevent(module_t mod, int type, void *data)
{
- static eventhandler_tag tag;
- struct tun_softc *tp;
switch (type) {
case MOD_LOAD:
mtx_init(&tunmtx, "tunmtx", NULL, MTX_DEF);
clone_setup(&tunclones);
+ tun_unrhdr = new_unrhdr(0, IF_MAXUNIT, &tunmtx);
tag = EVENTHANDLER_REGISTER(dev_clone, tunclone, 0, 1000);
if (tag == NULL)
return (ENOMEM);
- tun_cloner = if_clone_simple(tunname, tun_clone_create,
- tun_clone_destroy, 0);
break;
case MOD_UNLOAD:
- if_clone_detach(tun_cloner);
- EVENTHANDLER_DEREGISTER(dev_clone, tag);
- drain_dev_clone_events();
-
- mtx_lock(&tunmtx);
- while ((tp = TAILQ_FIRST(&tunhead)) != NULL) {
- TAILQ_REMOVE(&tunhead, tp, tun_list);
- mtx_unlock(&tunmtx);
- tun_destroy(tp);
- mtx_lock(&tunmtx);
- }
- mtx_unlock(&tunmtx);
- clone_cleanup(&tunclones);
- mtx_destroy(&tunmtx);
+ /* See tun_uninit, so it's done after the vnet_sysuninit() */
break;
default:
return EOPNOTSUPP;
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Thu, Apr 2, 5:04 PM (8 h, 42 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
30730738
Default Alt Text
D19248.id54460.diff (4 KB)
Attached To
Mode
D19248: tun: VIMAGE fix for if_tun cloner
Attached
Detach File
Event Timeline
Log In to Comment