Index: head/sys/net/route.c =================================================================== --- head/sys/net/route.c +++ head/sys/net/route.c @@ -227,7 +227,7 @@ rnh = rt_tables_get_rnh_ptr(table, fam); if (rnh == NULL) panic("%s: rnh NULL", __func__); - dom->dom_rtattach((void **)rnh, 0, table); + *rnh = dom->dom_rtattach(table); } } } @@ -256,7 +256,7 @@ rnh = rt_tables_get_rnh_ptr(table, fam); if (rnh == NULL) panic("%s: rnh NULL", __func__); - dom->dom_rtdetach((void **)rnh, 0); + dom->dom_rtdetach(*rnh); } } Index: head/sys/net/route/route_ctl.h =================================================================== --- head/sys/net/route/route_ctl.h +++ head/sys/net/route/route_ctl.h @@ -79,6 +79,9 @@ struct rib_subscription *rib_subscribe(uint32_t fibnum, int family, rib_subscription_cb_t *f, void *arg, enum rib_subscription_type type, bool waitok); +struct rib_subscription *rib_subscribe_internal(struct rib_head *rnh, + rib_subscription_cb_t *f, void *arg, enum rib_subscription_type type, + bool waitok); int rib_unsibscribe(uint32_t fibnum, int family, struct rib_subscription *rs); #endif Index: head/sys/net/route/route_ctl.c =================================================================== --- head/sys/net/route/route_ctl.c +++ head/sys/net/route/route_ctl.c @@ -817,6 +817,25 @@ } } +static struct rib_subscription * +allocate_subscription(rib_subscription_cb_t *f, void *arg, + enum rib_subscription_type type, bool waitok) +{ + struct rib_subscription *rs; + int flags = M_ZERO | (waitok ? M_WAITOK : 0); + + rs = malloc(sizeof(struct rib_subscription), M_RTABLE, flags); + if (rs == NULL) + return (NULL); + + rs->func = f; + rs->arg = arg; + rs->type = type; + + return (rs); +} + + /* * Subscribe for the changes in the routing table specified by @fibnum and * @family. @@ -830,20 +849,33 @@ struct rib_head *rnh; struct rib_subscription *rs; struct epoch_tracker et; - int flags = M_ZERO | (waitok ? M_WAITOK : 0); - rs = malloc(sizeof(struct rib_subscription), M_RTABLE, flags); - if (rs == NULL) + if ((rs = allocate_subscription(f, arg, type, waitok)) == NULL) return (NULL); NET_EPOCH_ENTER(et); KASSERT((fibnum < rt_numfibs), ("%s: bad fibnum", __func__)); rnh = rt_tables_get_rnh(fibnum, family); - rs->func = f; - rs->arg = arg; - rs->type = type; + RIB_WLOCK(rnh); + CK_STAILQ_INSERT_TAIL(&rnh->rnh_subscribers, rs, next); + RIB_WUNLOCK(rnh); + NET_EPOCH_EXIT(et); + return (rs); +} + +struct rib_subscription * +rib_subscribe_internal(struct rib_head *rnh, rib_subscription_cb_t *f, void *arg, + enum rib_subscription_type type, bool waitok) +{ + struct rib_subscription *rs; + struct epoch_tracker et; + + if ((rs = allocate_subscription(f, arg, type, waitok)) == NULL) + return (NULL); + + NET_EPOCH_ENTER(et); RIB_WLOCK(rnh); CK_STAILQ_INSERT_TAIL(&rnh->rnh_subscribers, rs, next); RIB_WUNLOCK(rnh); Index: head/sys/netinet/in_proto.c =================================================================== --- head/sys/netinet/in_proto.c +++ head/sys/netinet/in_proto.c @@ -294,9 +294,6 @@ }, }; -extern int in_inithead(void **, int, u_int); -extern int in_detachhead(void **, int); - struct domain inetdomain = { .dom_family = AF_INET, .dom_name = "internet", Index: head/sys/netinet/in_rmx.c =================================================================== --- head/sys/netinet/in_rmx.c +++ head/sys/netinet/in_rmx.c @@ -54,10 +54,6 @@ #include #include -extern int in_inithead(void **head, int off, u_int fibnum); -#ifdef VIMAGE -extern int in_detachhead(void **head, int off); -#endif static int rib4_preadd(u_int fibnum, const struct sockaddr *addr, const struct sockaddr *mask, @@ -121,38 +117,32 @@ return (0); } -static int _in_rt_was_here; /* * Initialize our routing tree. */ -int -in_inithead(void **head, int off, u_int fibnum) +struct rib_head * +in_inithead(uint32_t fibnum) { struct rib_head *rh; rh = rt_table_init(32, AF_INET, fibnum); if (rh == NULL) - return (0); + return (NULL); rh->rnh_preadd = rib4_preadd; #ifdef RADIX_MPATH rt_mpath_init_rnh(rh); #endif - *head = (void *)rh; - if (_in_rt_was_here == 0 ) { - _in_rt_was_here = 1; - } - return 1; + return (rh); } #ifdef VIMAGE -int -in_detachhead(void **head, int off) +void +in_detachhead(struct rib_head *rh) { - rt_table_destroy((struct rib_head *)(*head)); - return (1); + rt_table_destroy(rh); } #endif Index: head/sys/netinet/in_var.h =================================================================== --- head/sys/netinet/in_var.h +++ head/sys/netinet/in_var.h @@ -436,8 +436,7 @@ #define MCAST_NOTSMEMBER 2 /* This host excluded source */ #define MCAST_MUTED 3 /* [deprecated] */ -struct rtentry; -struct route; +struct rib_head; struct ip_moptions; struct in_multi *inm_lookup_locked(struct ifnet *, const struct in_addr); @@ -471,6 +470,10 @@ struct mbuf *ip_tryforward(struct mbuf *); void *in_domifattach(struct ifnet *); void in_domifdetach(struct ifnet *, void *); +struct rib_head *in_inithead(uint32_t fibnum); +#ifdef VIMAGE +void in_detachhead(struct rib_head *rh); +#endif #endif /* _KERNEL */ Index: head/sys/netinet6/in6_proto.c =================================================================== --- head/sys/netinet6/in6_proto.c +++ head/sys/netinet6/in6_proto.c @@ -333,11 +333,6 @@ }, }; -extern int in6_inithead(void **, int, u_int); -#ifdef VIMAGE -extern int in6_detachhead(void **, int); -#endif - struct domain inet6domain = { .dom_family = AF_INET6, .dom_name = "internet6", Index: head/sys/netinet6/in6_rmx.c =================================================================== --- head/sys/netinet6/in6_rmx.c +++ head/sys/netinet6/in6_rmx.c @@ -101,11 +101,6 @@ #include #include -extern int in6_inithead(void **head, int off, u_int fibnum); -#ifdef VIMAGE -extern int in6_detachhead(void **head, int off); -#endif - static int rib6_preadd(u_int fibnum, const struct sockaddr *addr, const struct sockaddr *mask, struct nhop_object *nh) @@ -147,8 +142,8 @@ * Initialize our routing tree. */ -int -in6_inithead(void **head, int off, u_int fibnum) +struct rib_head * +in6_inithead(uint32_t fibnum) { struct rib_head *rh; struct rib_subscription *rs; @@ -156,29 +151,26 @@ rh = rt_table_init(offsetof(struct sockaddr_in6, sin6_addr) << 3, AF_INET6, fibnum); if (rh == NULL) - return (0); + return (NULL); rh->rnh_preadd = rib6_preadd; #ifdef RADIX_MPATH rt_mpath_init_rnh(rh); #endif - *head = (void *)rh; - rs = rib_subscribe(fibnum, AF_INET6, nd6_subscription_cb, NULL, + rs = rib_subscribe_internal(rh, nd6_subscription_cb, NULL, RIB_NOTIFY_IMMEDIATE, true); KASSERT(rs != NULL, ("Unable to subscribe to fib %u\n", fibnum)); - return (1); + return (rh); } #ifdef VIMAGE -int -in6_detachhead(void **head, int off) +void +in6_detachhead(struct rib_head *rh) { - rt_table_destroy((struct rib_head *)(*head)); - - return (1); + rt_table_destroy(rh); } #endif Index: head/sys/netinet6/in6_var.h =================================================================== --- head/sys/netinet6/in6_var.h +++ head/sys/netinet6/in6_var.h @@ -857,6 +857,7 @@ struct ip6_moptions; struct sockopt; struct inpcbinfo; +struct rib_head; /* Multicast KPIs. */ int im6o_mc_filter(const struct ip6_moptions *, const struct ifnet *, @@ -891,6 +892,8 @@ void *in6_domifattach(struct ifnet *); void in6_domifdetach(struct ifnet *, void *); int in6_domifmtu(struct ifnet *); +struct rib_head *in6_inithead(uint32_t fibnum); +void in6_detachhead(struct rib_head *rh); void in6_setmaxmtu(void); int in6_if2idlen(struct ifnet *); struct in6_ifaddr *in6ifa_ifpforlinklocal(struct ifnet *, int); Index: head/sys/sys/domain.h =================================================================== --- head/sys/sys/domain.h +++ head/sys/sys/domain.h @@ -45,6 +45,7 @@ struct mbuf; struct ifnet; struct socket; +struct rib_head; struct domain { int dom_family; /* AF_xxx */ @@ -59,10 +60,10 @@ (struct socket *); struct protosw *dom_protosw, *dom_protoswNPROTOSW; struct domain *dom_next; - int (*dom_rtattach) /* initialize routing table */ - (void **, int, u_int); - int (*dom_rtdetach) /* clean up routing table */ - (void **, int); + struct rib_head *(*dom_rtattach) /* initialize routing table */ + (uint32_t); + void (*dom_rtdetach) /* clean up routing table */ + (struct rib_head *); void *(*dom_ifattach)(struct ifnet *); void (*dom_ifdetach)(struct ifnet *, void *); int (*dom_ifmtu)(struct ifnet *);