diff options
Diffstat (limited to 'sys/net')
-rw-r--r-- | sys/net/bridgestp.c | 1 | ||||
-rw-r--r-- | sys/net/flowtable.c | 143 | ||||
-rw-r--r-- | sys/net/flowtable.h | 5 | ||||
-rw-r--r-- | sys/net/if.c | 86 | ||||
-rw-r--r-- | sys/net/if_bridge.c | 6 | ||||
-rw-r--r-- | sys/net/if_clone.c | 23 | ||||
-rw-r--r-- | sys/net/if_ef.c | 1 | ||||
-rw-r--r-- | sys/net/if_enc.c | 1 | ||||
-rw-r--r-- | sys/net/if_ethersubr.c | 14 | ||||
-rw-r--r-- | sys/net/if_faith.c | 2 | ||||
-rw-r--r-- | sys/net/if_gif.c | 44 | ||||
-rw-r--r-- | sys/net/if_gif.h | 30 | ||||
-rw-r--r-- | sys/net/if_gre.c | 4 | ||||
-rw-r--r-- | sys/net/if_loop.c | 23 | ||||
-rw-r--r-- | sys/net/if_mib.c | 4 | ||||
-rw-r--r-- | sys/net/if_spppsubr.c | 2 | ||||
-rw-r--r-- | sys/net/if_stf.c | 3 | ||||
-rw-r--r-- | sys/net/if_var.h | 16 | ||||
-rw-r--r-- | sys/net/if_vlan.c | 1 | ||||
-rw-r--r-- | sys/net/raw_cb.c | 5 | ||||
-rw-r--r-- | sys/net/raw_cb.h | 6 | ||||
-rw-r--r-- | sys/net/raw_usrreq.c | 2 | ||||
-rw-r--r-- | sys/net/route.c | 70 | ||||
-rw-r--r-- | sys/net/rtsock.c | 3 | ||||
-rw-r--r-- | sys/net/vnet.c | 341 | ||||
-rw-r--r-- | sys/net/vnet.h | 161 |
26 files changed, 609 insertions, 388 deletions
diff --git a/sys/net/bridgestp.c b/sys/net/bridgestp.c index a4ec6bc..9349be4 100644 --- a/sys/net/bridgestp.c +++ b/sys/net/bridgestp.c @@ -2006,7 +2006,6 @@ bstp_same_bridgeid(uint64_t id1, uint64_t id2) void bstp_reinit(struct bstp_state *bs) { - INIT_VNET_NET(curvnet); struct bstp_port *bp; struct ifnet *ifp, *mif; u_char *e_addr; diff --git a/sys/net/flowtable.c b/sys/net/flowtable.c index fafdc0a..dd1b040 100644 --- a/sys/net/flowtable.c +++ b/sys/net/flowtable.c @@ -64,7 +64,6 @@ __FBSDID("$FreeBSD$"); #include <netinet/tcp.h> #include <netinet/udp.h> #include <netinet/sctp.h> -#include <netinet/vinet.h> #include <libkern/jenkins.h> @@ -164,29 +163,28 @@ struct flowtable { }; static struct proc *flowcleanerproc; -#ifdef VIMAGE_GLOBALS -static struct flowtable *flow_list_head; -static uint32_t flow_hashjitter; -static uma_zone_t flow_ipv4_zone; -static uma_zone_t flow_ipv6_zone; -#endif +static VNET_DEFINE(struct flowtable *, flow_list_head); +static VNET_DEFINE(uint32_t, flow_hashjitter); +static VNET_DEFINE(uma_zone_t, flow_ipv4_zone); +static VNET_DEFINE(uma_zone_t, flow_ipv6_zone); + +#define V_flow_list_head VNET_GET(flow_list_head) +#define V_flow_hashjitter VNET_GET(flow_hashjitter) +#define V_flow_ipv4_zone VNET_GET(flow_ipv4_zone) +#define V_flow_ipv6_zone VNET_GET(flow_ipv6_zone) static int flowtable_iattach(const void *); #ifdef VIMAGE static int flowtable_idetach(const void *); -#endif -#ifndef VIMAGE_GLOBALS static const vnet_modinfo_t flowtable_modinfo = { .vmi_id = VNET_MOD_FLOWTABLE, .vmi_name = "flowtable", .vmi_dependson = VNET_MOD_INET, .vmi_iattach = flowtable_iattach, -#ifdef VIMAGE .vmi_idetach = flowtable_idetach -#endif }; -#endif /* !VIMAGE_GLOBALS */ +#endif /* * TODO: @@ -205,54 +203,67 @@ static const vnet_modinfo_t flowtable_modinfo = { * - support explicit connection state (currently only ad-hoc for DSR) * - idetach() cleanup for options VIMAGE builds. */ -#ifdef VIMAGE_GLOBALS -int flowtable_enable; -static int flowtable_hits; -static int flowtable_lookups; -static int flowtable_misses; -static int flowtable_frees; -static int flowtable_free_checks; -static int flowtable_max_depth; -static int flowtable_collisions; -static int flowtable_syn_expire; -static int flowtable_udp_expire; -static int flowtable_fin_wait_expire; -static int flowtable_tcp_expire; -static int flowtable_nmbflows; -#endif +VNET_DEFINE(int, flowtable_enable) = 1; +static VNET_DEFINE(int, flowtable_hits); +static VNET_DEFINE(int, flowtable_lookups); +static VNET_DEFINE(int, flowtable_misses); +static VNET_DEFINE(int, flowtable_frees); +static VNET_DEFINE(int, flowtable_free_checks); +static VNET_DEFINE(int, flowtable_max_depth); +static VNET_DEFINE(int, flowtable_collisions); +static VNET_DEFINE(int, flowtable_syn_expire) = SYN_IDLE; +static VNET_DEFINE(int, flowtable_udp_expire) = UDP_IDLE; +static VNET_DEFINE(int, flowtable_fin_wait_expire) = FIN_WAIT_IDLE; +static VNET_DEFINE(int, flowtable_tcp_expire) = TCP_IDLE; +static VNET_DEFINE(int, flowtable_nmbflows) = 4096; + +#define V_flowtable_enable VNET_GET(flowtable_enable) +#define V_flowtable_hits VNET_GET(flowtable_hits) +#define V_flowtable_lookups VNET_GET(flowtable_lookups) +#define V_flowtable_misses VNET_GET(flowtable_misses) +#define V_flowtable_frees VNET_GET(flowtable_frees) +#define V_flowtable_free_checks VNET_GET(flowtable_free_checks) +#define V_flowtable_max_depth VNET_GET(flowtable_max_depth) +#define V_flowtable_collisions VNET_GET(flowtable_collisions) +#define V_flowtable_syn_expire VNET_GET(flowtable_syn_expire) +#define V_flowtable_udp_expire VNET_GET(flowtable_udp_expire) +#define V_flowtable_fin_wait_expire VNET_GET(flowtable_fin_wait_expire) +#define V_flowtable_tcp_expire VNET_GET(flowtable_tcp_expire) +#define V_flowtable_nmbflows VNET_GET(flowtable_nmbflows) + SYSCTL_NODE(_net_inet, OID_AUTO, flowtable, CTLFLAG_RD, NULL, "flowtable"); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, enable, - CTLFLAG_RW, flowtable_enable, 0, "enable flowtable caching."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, hits, - CTLFLAG_RD, flowtable_hits, 0, "# flowtable hits."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, lookups, - CTLFLAG_RD, flowtable_lookups, 0, "# flowtable lookups."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, misses, - CTLFLAG_RD, flowtable_misses, 0, "#flowtable misses."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, frees, - CTLFLAG_RD, flowtable_frees, 0, "#flows freed."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, free_checks, - CTLFLAG_RD, flowtable_free_checks, 0, "#flows free checks."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, max_depth, - CTLFLAG_RD, flowtable_max_depth, 0, "max collision list length."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, collisions, - CTLFLAG_RD, flowtable_collisions, 0, "#flowtable collisions."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, enable, CTLFLAG_RW, + &VNET_NAME(flowtable_enable), 0, "enable flowtable caching."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, hits, CTLFLAG_RD, + &VNET_NAME(flowtable_hits), 0, "# flowtable hits."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, lookups, CTLFLAG_RD, + &VNET_NAME(flowtable_lookups), 0, "# flowtable lookups."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, misses, CTLFLAG_RD, + &VNET_NAME(flowtable_misses), 0, "#flowtable misses."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, frees, CTLFLAG_RD, + &VNET_NAME(flowtable_frees), 0, "#flows freed."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, free_checks, CTLFLAG_RD, + &VNET_NAME(flowtable_free_checks), 0, "#flows free checks."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, max_depth, CTLFLAG_RD, + &VNET_NAME(flowtable_max_depth), 0, "max collision list length."); +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, collisions, CTLFLAG_RD, + &VNET_NAME(flowtable_collisions), 0, "#flowtable collisions."); /* * XXX This does not end up updating timeouts at runtime * and only reflects the value for the last table added :-/ */ -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, syn_expire, - CTLFLAG_RW, flowtable_syn_expire, 0, +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, syn_expire, CTLFLAG_RW, + &VNET_NAME(flowtable_syn_expire), 0, "seconds after which to remove syn allocated flow."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, udp_expire, - CTLFLAG_RW, flowtable_udp_expire, 0, +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, udp_expire, CTLFLAG_RW, + &VNET_NAME(flowtable_udp_expire), 0, "seconds after which to remove flow allocated to UDP."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, fin_wait_expire, - CTLFLAG_RW, flowtable_fin_wait_expire, 0, +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, fin_wait_expire, CTLFLAG_RW, + &VNET_NAME(flowtable_fin_wait_expire), 0, "seconds after which to remove a flow in FIN_WAIT."); -SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, tcp_expire, - CTLFLAG_RW, flowtable_tcp_expire, 0, +SYSCTL_VNET_INT(_net_inet_flowtable, OID_AUTO, tcp_expire, CTLFLAG_RW, + &VNET_NAME(flowtable_tcp_expire), 0, "seconds after which to remove flow allocated to a TCP connection."); @@ -266,7 +277,6 @@ SYSCTL_V_INT(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, tcp_expire, static int sysctl_nmbflows(SYSCTL_HANDLER_ARGS) { - INIT_VNET_INET(curvnet); int error, newnmbflows; newnmbflows = V_flowtable_nmbflows; @@ -283,8 +293,8 @@ sysctl_nmbflows(SYSCTL_HANDLER_ARGS) } return (error); } -SYSCTL_V_PROC(V_NET, vnet_inet, _net_inet_flowtable, OID_AUTO, nmbflows, - CTLTYPE_INT|CTLFLAG_RW, flowtable_nmbflows, 0, sysctl_nmbflows, "IU", +SYSCTL_VNET_PROC(_net_inet_flowtable, OID_AUTO, nmbflows, + CTLTYPE_INT|CTLFLAG_RW, 0, 0, sysctl_nmbflows, "IU", "Maximum number of flows allowed"); #ifndef RADIX_MPATH @@ -338,7 +348,6 @@ static uint32_t ipv4_flow_lookup_hash_internal(struct mbuf *m, struct route *ro, uint32_t *key, uint16_t *flags, uint8_t *protop) { - INIT_VNET_INET(curvnet); uint16_t sport = 0, dport = 0; struct ip *ip = NULL; uint8_t proto = 0; @@ -505,7 +514,6 @@ static int flowtable_insert(struct flowtable *ft, uint32_t hash, uint32_t *key, uint8_t proto, struct route *ro, uint16_t flags) { - INIT_VNET_INET(curvnet); struct flentry *fle, *fletail, *newfle, **flep; int depth; uma_zone_t flezone; @@ -596,7 +604,6 @@ flowtable_key_equal(struct flentry *fle, uint32_t *key) int flowtable_lookup(struct flowtable *ft, struct mbuf *m, struct route *ro) { - INIT_VNET_INET(curvnet); uint32_t key[9], hash; struct flentry *fle; uint16_t flags; @@ -718,7 +725,6 @@ uncached: struct flowtable * flowtable_alloc(int nentry, int flags) { - INIT_VNET_INET(curvnet); struct flowtable *ft, *fttail; int i; @@ -800,7 +806,7 @@ static void flowtable_setup(void *arg) { -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE vnet_mod_register(&flowtable_modinfo); #else flowtable_iattach(NULL); @@ -810,21 +816,6 @@ flowtable_setup(void *arg) static int flowtable_iattach(const void *unused __unused) { - INIT_VNET_INET(curvnet); - - V_flowtable_enable = 1; - V_flowtable_hits = 0; - V_flowtable_lookups = 0; - V_flowtable_misses = 0; - V_flowtable_frees = 0; - V_flowtable_free_checks = 0; - V_flowtable_max_depth = 0; - V_flowtable_collisions = 0; - V_flowtable_syn_expire = SYN_IDLE; - V_flowtable_udp_expire = UDP_IDLE; - V_flowtable_fin_wait_expire = FIN_WAIT_IDLE; - V_flowtable_tcp_expire = TCP_IDLE; - V_flowtable_nmbflows = 4096; V_flow_ipv4_zone = uma_zcreate("ip4flow", sizeof(struct flentry_v4), NULL, NULL, NULL, NULL, 64, UMA_ZONE_MAXBUCKET); @@ -839,7 +830,6 @@ flowtable_iattach(const void *unused __unused) static int flowtable_idetach(const void *unused __unused) { - INIT_VNET_INET(curvnet); uma_zdestroy(V_flow_ipv4_zone); uma_zdestroy(V_flow_ipv6_zone); @@ -858,7 +848,6 @@ SYSINIT(flowtable_setup, SI_SUB_KTHREAD_INIT, SI_ORDER_ANY, flowtable_setup, NUL static void fle_free(struct flentry *fle) { - INIT_VNET_INET(curvnet); struct rtentry *rt; struct llentry *lle; @@ -873,7 +862,6 @@ fle_free(struct flentry *fle) static void flowtable_free_stale(struct flowtable *ft) { - INIT_VNET_INET(curvnet); int curbit = 0, count; struct flentry *fle, **flehead, *fleprev; struct flentry *flefreehead, *flefreetail, *fletmp; @@ -961,7 +949,6 @@ flowtable_free_stale(struct flowtable *ft) static void flowtable_clean_vnet(void) { - INIT_VNET_INET(curvnet); struct flowtable *ft; int i; diff --git a/sys/net/flowtable.h b/sys/net/flowtable.h index 26aa11d..13fdfdb 100644 --- a/sys/net/flowtable.h +++ b/sys/net/flowtable.h @@ -38,9 +38,8 @@ $FreeBSD$ #define FL_PCPU (1<<1) /* pcpu cache */ struct flowtable; -#ifdef VIMAGE_GLOBALS -extern struct flowtable *ip_ft; -#endif +VNET_DECLARE(struct flowtable *, ip_ft); +#define V_ip_ft VNET_GET(ip_ft) struct flowtable *flowtable_alloc(int nentry, int flags); diff --git a/sys/net/if.c b/sys/net/if.c index 4803477..daab1ac 100644 --- a/sys/net/if.c +++ b/sys/net/if.c @@ -84,7 +84,6 @@ #endif #ifdef INET #include <netinet/if_ether.h> -#include <netinet/vinet.h> #endif #if defined(INET) || defined(INET6) #ifdef DEV_CARP @@ -94,12 +93,6 @@ #include <security/mac/mac_framework.h> -#ifndef VIMAGE -#ifndef VIMAGE_GLOBALS -struct vnet_net vnet_net_0; -#endif -#endif - struct ifindex_entry { struct ifnet *ife_ifnet; }; @@ -162,37 +155,30 @@ static int vnet_net_iattach(const void *); static int vnet_net_idetach(const void *); #endif -#ifdef VIMAGE_GLOBALS -struct ifnethead ifnet; /* depend on static init XXX */ -struct ifgrouphead ifg_head; -int if_index; -static int if_indexlim; +VNET_DEFINE(struct ifnethead, ifnet); /* depend on static init XXX */ +VNET_DEFINE(struct ifgrouphead, ifg_head); +VNET_DEFINE(int, if_index); +static VNET_DEFINE(int, if_indexlim) = 8; + /* Table of ifnet by index. Locked with ifnet_lock. */ -static struct ifindex_entry *ifindex_table; -#endif +static VNET_DEFINE(struct ifindex_entry *, ifindex_table); + +#define V_if_indexlim VNET_GET(if_indexlim) +#define V_ifindex_table VNET_GET(ifindex_table) int ifqmaxlen = IFQ_MAXLEN; struct rwlock ifnet_lock; static if_com_alloc_t *if_com_alloc[256]; static if_com_free_t *if_com_free[256]; -#ifndef VIMAGE_GLOBALS -static struct vnet_symmap vnet_net_symmap[] = { - VNET_SYMMAP(net, ifnet), - VNET_SYMMAP_END -}; - +#ifdef VIMAGE static const vnet_modinfo_t vnet_net_modinfo = { .vmi_id = VNET_MOD_NET, .vmi_name = "net", - .vmi_size = sizeof(struct vnet_net), - .vmi_symmap = vnet_net_symmap, .vmi_iattach = vnet_net_iattach, -#ifdef VIMAGE .vmi_idetach = vnet_net_idetach -#endif }; -#endif /* !VIMAGE_GLOBALS */ +#endif /* * System initialization @@ -207,7 +193,6 @@ MALLOC_DEFINE(M_IFMADDR, "ether_multi", "link-level multicast address"); struct ifnet * ifnet_byindex_locked(u_short idx) { - INIT_VNET_NET(curvnet); if (idx > V_if_index) return (NULL); @@ -244,7 +229,6 @@ ifnet_byindex_ref(u_short idx) static void ifnet_setbyindex(u_short idx, struct ifnet *ifp) { - INIT_VNET_NET(curvnet); IFNET_WLOCK_ASSERT(); @@ -276,7 +260,7 @@ static void if_init(void *dummy __unused) { -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE vnet_mod_register(&vnet_net_modinfo); #else vnet_net_iattach(NULL); @@ -289,11 +273,6 @@ if_init(void *dummy __unused) static int vnet_net_iattach(const void *unused __unused) { - INIT_VNET_NET(curvnet); - - V_if_index = 0; - V_ifindex_table = NULL; - V_if_indexlim = 8; TAILQ_INIT(&V_ifnet); TAILQ_INIT(&V_ifg_head); @@ -306,7 +285,6 @@ vnet_net_iattach(const void *unused __unused) static int vnet_net_idetach(const void *unused __unused) { - INIT_VNET_NET(curvnet); VNET_ASSERT(TAILQ_EMPTY(&V_ifnet)); VNET_ASSERT(TAILQ_EMPTY(&V_ifg_head)); @@ -320,7 +298,6 @@ vnet_net_idetach(const void *unused __unused) void if_grow(void) { - INIT_VNET_NET(curvnet); u_int n; struct ifindex_entry *e; @@ -354,7 +331,6 @@ if_check(void *dummy __unused) struct ifnet * if_alloc(u_char type) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; ifp = malloc(sizeof(struct ifnet), M_IFNET, M_WAITOK|M_ZERO); @@ -418,7 +394,6 @@ if_alloc(u_char type) static void if_free_internal(struct ifnet *ifp) { - INIT_VNET_NET(curvnet); /* ifp->if_vnet is already NULL here */ KASSERT((ifp->if_flags & IFF_DYING), ("if_free_internal: interface not dying")); @@ -544,7 +519,6 @@ if_attach(struct ifnet *ifp) static void if_attach_internal(struct ifnet *ifp, int vmove) { - INIT_VNET_NET(curvnet); unsigned socksize, ifasize; int namelen, masklen; struct sockaddr_dl *sdl; @@ -649,7 +623,6 @@ if_attach_internal(struct ifnet *ifp, int vmove) static void if_attachdomain(void *dummy) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; int s; @@ -769,7 +742,6 @@ if_detach(struct ifnet *ifp) static void if_detach_internal(struct ifnet *ifp, int vmove) { - INIT_VNET_NET(ifp->if_vnet); struct ifaddr *ifa; struct radix_node_head *rnh; int i, j; @@ -904,25 +876,17 @@ if_vmove(struct ifnet *ifp, struct vnet *new_vnet) /* * Unlink the ifnet from ifindex_table[] in current vnet, * and shrink the if_index for that vnet if possible. - * do / while construct below is needed to confine the scope - * of INIT_VNET_NET(). */ - { - INIT_VNET_NET(curvnet); - - IFNET_WLOCK(); - ifnet_setbyindex(ifp->if_index, NULL); - while (V_if_index > 0 && \ - ifnet_byindex_locked(V_if_index) == NULL) - V_if_index--; - IFNET_WUNLOCK(); - }; + IFNET_WLOCK(); + ifnet_setbyindex(ifp->if_index, NULL); + while (V_if_index > 0 && ifnet_byindex_locked(V_if_index) == NULL) + V_if_index--; + IFNET_WUNLOCK(); /* * Switch to the context of the target vnet. */ CURVNET_SET_QUIET(new_vnet); - INIT_VNET_NET(new_vnet); /* * Try to find an empty slot below if_index. If we fail, take @@ -956,7 +920,6 @@ if_vmove(struct ifnet *ifp, struct vnet *new_vnet) int if_addgroup(struct ifnet *ifp, const char *groupname) { - INIT_VNET_NET(ifp->if_vnet); struct ifg_list *ifgl; struct ifg_group *ifg = NULL; struct ifg_member *ifgm; @@ -1026,7 +989,6 @@ if_addgroup(struct ifnet *ifp, const char *groupname) int if_delgroup(struct ifnet *ifp, const char *groupname) { - INIT_VNET_NET(ifp->if_vnet); struct ifg_list *ifgl; struct ifg_member *ifgm; @@ -1072,7 +1034,6 @@ if_delgroup(struct ifnet *ifp, const char *groupname) static void if_delgroups(struct ifnet *ifp) { - INIT_VNET_NET(ifp->if_vnet); struct ifg_list *ifgl; struct ifg_member *ifgm; char groupname[IFNAMSIZ]; @@ -1164,7 +1125,6 @@ if_getgroup(struct ifgroupreq *data, struct ifnet *ifp) static int if_getgroupmembers(struct ifgroupreq *data) { - INIT_VNET_NET(curvnet); struct ifgroupreq *ifgr = data; struct ifg_group *ifg; struct ifg_member *ifgm; @@ -1336,7 +1296,6 @@ ifa_free(struct ifaddr *ifa) static struct ifaddr * ifa_ifwithaddr_internal(struct sockaddr *addr, int getref) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; struct ifaddr *ifa; @@ -1392,7 +1351,6 @@ ifa_ifwithaddr_check(struct sockaddr *addr) struct ifaddr * ifa_ifwithbroadaddr(struct sockaddr *addr) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; struct ifaddr *ifa; @@ -1426,7 +1384,6 @@ done: struct ifaddr * ifa_ifwithdstaddr(struct sockaddr *addr) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; struct ifaddr *ifa; @@ -1460,7 +1417,6 @@ done: struct ifaddr * ifa_ifwithnet(struct sockaddr *addr) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; struct ifaddr *ifa; struct ifaddr *ifa_maybe = NULL; @@ -1841,7 +1797,6 @@ if_slowtimo(void *arg) VNET_LIST_RLOCK(); VNET_FOREACH(vnet_iter) { CURVNET_SET(vnet_iter); - INIT_VNET_NET(vnet_iter); TAILQ_FOREACH(ifp, &V_ifnet, if_link) { if (ifp->if_timer == 0 || --ifp->if_timer) continue; @@ -1863,7 +1818,6 @@ if_slowtimo(void *arg) struct ifnet * ifunit_ref(const char *name) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; IFNET_RLOCK(); @@ -1881,7 +1835,6 @@ ifunit_ref(const char *name) struct ifnet * ifunit(const char *name) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; IFNET_RLOCK(); @@ -2478,7 +2431,6 @@ ifpromisc(struct ifnet *ifp, int pswitch) static int ifconf(u_long cmd, caddr_t data) { - INIT_VNET_NET(curvnet); struct ifconf *ifc = (struct ifconf *)data; #ifdef __amd64__ struct ifconf32 *ifc32 = (struct ifconf32 *)data; @@ -2837,7 +2789,6 @@ if_delmulti(struct ifnet *ifp, struct sockaddr *sa) int lastref; #ifdef INVARIANTS struct ifnet *oifp; - INIT_VNET_NET(ifp->if_vnet); IFNET_RLOCK(); TAILQ_FOREACH(oifp, &V_ifnet, if_link) @@ -2878,9 +2829,6 @@ if_delmulti(struct ifnet *ifp, struct sockaddr *sa) void if_delmulti_ifma(struct ifmultiaddr *ifma) { -#ifdef DIAGNOSTIC - INIT_VNET_NET(curvnet); -#endif struct ifnet *ifp; int lastref; diff --git a/sys/net/if_bridge.c b/sys/net/if_bridge.c index 08310d7..945bc5f 100644 --- a/sys/net/if_bridge.c +++ b/sys/net/if_bridge.c @@ -116,11 +116,9 @@ __FBSDID("$FreeBSD$"); #include <netinet/in_var.h> #include <netinet/ip.h> #include <netinet/ip_var.h> -#include <netinet/vinet.h> #ifdef INET6 #include <netinet/ip6.h> #include <netinet6/ip6_var.h> -#include <netinet6/vinet6.h> #endif #if defined(INET) || defined(INET6) #ifdef DEV_CARP @@ -3042,7 +3040,6 @@ bridge_pfil(struct mbuf **mp, struct ifnet *bifp, struct ifnet *ifp, int dir) } if (ip_fw_chk_ptr && pfil_ipfw != 0 && dir == PFIL_OUT && ifp != NULL) { - INIT_VNET_INET(curvnet); struct dn_pkt_tag *dn_tag; error = -1; @@ -3236,7 +3233,6 @@ bad: static int bridge_ip_checkbasic(struct mbuf **mp) { - INIT_VNET_INET(curvnet); struct mbuf *m = *mp; struct ip *ip; int len, hlen; @@ -3332,7 +3328,6 @@ bad: static int bridge_ip6_checkbasic(struct mbuf **mp) { - INIT_VNET_INET6(curvnet); struct mbuf *m = *mp; struct ip6_hdr *ip6; @@ -3387,7 +3382,6 @@ static int bridge_fragment(struct ifnet *ifp, struct mbuf *m, struct ether_header *eh, int snap, struct llc *llc) { - INIT_VNET_INET(curvnet); struct mbuf *m0; struct ip *ip; int error = -1; diff --git a/sys/net/if_clone.c b/sys/net/if_clone.c index eaa7397..9347d2c 100644 --- a/sys/net/if_clone.c +++ b/sys/net/if_clone.c @@ -58,10 +58,11 @@ static int if_clone_createif(struct if_clone *ifc, char *name, size_t len, static int vnet_clone_iattach(const void *); static struct mtx if_cloners_mtx; -#ifdef VIMAGE_GLOBALS -static int if_cloners_count; -LIST_HEAD(, if_clone) if_cloners; -#endif +static VNET_DEFINE(int, if_cloners_count); +VNET_DEFINE(LIST_HEAD(, if_clone), if_cloners); + +#define V_if_cloners_count VNET_GET(if_cloners_count) +#define V_if_cloners VNET_GET(if_cloners) #define IF_CLONERS_LOCK_INIT() \ mtx_init(&if_cloners_mtx, "if_cloners lock", NULL, MTX_DEF) @@ -115,17 +116,16 @@ LIST_HEAD(, if_clone) if_cloners; static MALLOC_DEFINE(M_CLONE, "clone", "interface cloning framework"); -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE static const vnet_modinfo_t vnet_clone_modinfo = { .vmi_id = VNET_MOD_IF_CLONE, .vmi_name = "if_clone", .vmi_iattach = vnet_clone_iattach }; -#endif /* !VIMAGE_GLOBALS */ +#endif static int vnet_clone_iattach(const void *unused __unused) { - INIT_VNET_NET(curvnet); LIST_INIT(&V_if_cloners); return (0); @@ -136,7 +136,7 @@ if_clone_init(void) { IF_CLONERS_LOCK_INIT(); -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE vnet_mod_register(&vnet_clone_modinfo); #else vnet_clone_iattach(NULL); @@ -149,7 +149,6 @@ if_clone_init(void) int if_clone_create(char *name, size_t len, caddr_t params) { - INIT_VNET_NET(curvnet); struct if_clone *ifc; /* Try to find an applicable cloner for this request */ @@ -162,7 +161,6 @@ if_clone_create(char *name, size_t len, caddr_t params) #ifdef VIMAGE if (ifc == NULL && !IS_DEFAULT_VNET(curvnet)) { CURVNET_SET_QUIET(vnet0); - INIT_VNET_NET(vnet0); LIST_FOREACH(ifc, &V_if_cloners, ifc_list) { if (ifc->ifc_match(ifc, name)) break; @@ -213,7 +211,6 @@ if_clone_createif(struct if_clone *ifc, char *name, size_t len, caddr_t params) int if_clone_destroy(const char *name) { - INIT_VNET_NET(curvnet); struct if_clone *ifc; struct ifnet *ifp; @@ -231,7 +228,6 @@ if_clone_destroy(const char *name) #ifdef VIMAGE if (ifc == NULL && !IS_DEFAULT_VNET(curvnet)) { CURVNET_SET_QUIET(vnet0); - INIT_VNET_NET(vnet0); LIST_FOREACH(ifc, &V_if_cloners, ifc_list) { if (ifc->ifc_match(ifc, name)) break; @@ -289,7 +285,6 @@ if_clone_destroyif(struct if_clone *ifc, struct ifnet *ifp) void if_clone_attach(struct if_clone *ifc) { - INIT_VNET_NET(curvnet); int len, maxclone; /* @@ -322,7 +317,6 @@ if_clone_attach(struct if_clone *ifc) void if_clone_detach(struct if_clone *ifc) { - INIT_VNET_NET(curvnet); struct ifc_simple_data *ifcs = ifc->ifc_data; IF_CLONERS_LOCK(); @@ -362,7 +356,6 @@ if_clone_free(struct if_clone *ifc) int if_clone_list(struct if_clonereq *ifcr) { - INIT_VNET_NET(curvnet); char *buf, *dst, *outbuf = NULL; struct if_clone *ifc; int buf_count, count, err = 0; diff --git a/sys/net/if_ef.c b/sys/net/if_ef.c index e5e7dd8..c0b2d67 100644 --- a/sys/net/if_ef.c +++ b/sys/net/if_ef.c @@ -493,7 +493,6 @@ ef_load(void) VNET_LIST_RLOCK(); VNET_FOREACH(vnet_iter) { CURVNET_SET(vnet_iter); - INIT_VNET_NET(vnet_iter); IFNET_RLOCK(); TAILQ_FOREACH(ifp, &V_ifnet, if_link) { if (ifp->if_type != IFT_ETHER) continue; diff --git a/sys/net/if_enc.c b/sys/net/if_enc.c index 38321ff..7b62734 100644 --- a/sys/net/if_enc.c +++ b/sys/net/if_enc.c @@ -47,6 +47,7 @@ #include <net/route.h> #include <net/netisr.h> #include <net/bpf.h> +#include <net/vnet.h> #include <netinet/in.h> #include <netinet/in_systm.h> diff --git a/sys/net/if_ethersubr.c b/sys/net/if_ethersubr.c index 5e98e53..f7c9042 100644 --- a/sys/net/if_ethersubr.c +++ b/sys/net/if_ethersubr.c @@ -73,7 +73,7 @@ #include <netinet/if_ether.h> #include <netinet/ip_fw.h> #include <netinet/ip_dummynet.h> -#include <netinet/vinet.h> +#include <netinet/ip_var.h> #endif #ifdef INET6 #include <netinet6/nd6.h> @@ -148,9 +148,8 @@ MALLOC_DEFINE(M_ARPCOM, "arpcom", "802.* interface internals"); #if defined(INET) || defined(INET6) int ether_ipfw_chk(struct mbuf **m0, struct ifnet *dst, int shared); -#ifdef VIMAGE_GLOBALS -static int ether_ipfw; -#endif +static VNET_DEFINE(int, ether_ipfw); +#define V_ether_ipfw VNET_GET(ether_ipfw) #endif @@ -434,7 +433,6 @@ int ether_output_frame(struct ifnet *ifp, struct mbuf *m) { #if defined(INET) || defined(INET6) - INIT_VNET_NET(ifp->if_vnet); if (ip_fw_chk_ptr && V_ether_ipfw != 0) { if (ether_ipfw_chk(&m, ifp, 0) == 0) { @@ -463,7 +461,6 @@ ether_output_frame(struct ifnet *ifp, struct mbuf *m) int ether_ipfw_chk(struct mbuf **m0, struct ifnet *dst, int shared) { - INIT_VNET_INET(dst->if_vnet); struct ether_header *eh; struct ether_header save_eh; struct mbuf *m; @@ -774,7 +771,6 @@ ether_demux(struct ifnet *ifp, struct mbuf *m) KASSERT(ifp != NULL, ("%s: NULL interface pointer", __func__)); #if defined(INET) || defined(INET6) - INIT_VNET_NET(ifp->if_vnet); /* * Allow dummynet and/or ipfw to claim the frame. * Do not do this for PROMISC frames in case we are re-entered. @@ -994,8 +990,8 @@ ether_ifdetach(struct ifnet *ifp) SYSCTL_DECL(_net_link); SYSCTL_NODE(_net_link, IFT_ETHER, ether, CTLFLAG_RW, 0, "Ethernet"); #if defined(INET) || defined(INET6) -SYSCTL_V_INT(V_NET, vnet_net, _net_link_ether, OID_AUTO, ipfw, CTLFLAG_RW, - ether_ipfw, 0, "Pass ether pkts through firewall"); +SYSCTL_VNET_INT(_net_link_ether, OID_AUTO, ipfw, CTLFLAG_RW, + &VNET_NAME(ether_ipfw), 0, "Pass ether pkts through firewall"); #endif #if 0 diff --git a/sys/net/if_faith.c b/sys/net/if_faith.c index 3b60d2c..cbca740 100644 --- a/sys/net/if_faith.c +++ b/sys/net/if_faith.c @@ -77,7 +77,6 @@ #include <netinet6/in6_var.h> #include <netinet/ip6.h> #include <netinet6/ip6_var.h> -#include <netinet6/vinet6.h> #endif #define FAITHNAME "faith" @@ -328,7 +327,6 @@ static int faithprefix(in6) struct in6_addr *in6; { - INIT_VNET_INET6(curvnet); struct rtentry *rt; struct sockaddr_in6 sin6; int ret; diff --git a/sys/net/if_gif.c b/sys/net/if_gif.c index 06a849a..e96cb41 100644 --- a/sys/net/if_gif.c +++ b/sys/net/if_gif.c @@ -95,22 +95,21 @@ static struct mtx gif_mtx; static MALLOC_DEFINE(M_GIF, "gif", "Generic Tunnel Interface"); -#ifndef VIMAGE -#ifndef VIMAGE_GLOBALS -struct vnet_gif vnet_gif_0; -#endif -#endif +static VNET_DEFINE(LIST_HEAD(, gif_softc), gif_softc_list); +static VNET_DEFINE(int, max_gif_nesting); +static VNET_DEFINE(int, parallel_tunnels); + +#define V_gif_softc_list VNET_GET(gif_softc_list) +#define V_max_gif_nesting VNET_GET(max_gif_nesting) +#define V_parallel_tunnels VNET_GET(parallel_tunnels) -#ifdef VIMAGE_GLOBALS -static LIST_HEAD(, gif_softc) gif_softc_list; -static int max_gif_nesting; -static int parallel_tunnels; #ifdef INET -int ip_gif_ttl; +VNET_DEFINE(int, ip_gif_ttl); +#define V_ip_gif_ttl VNET_GET(ip_gif_ttl) #endif #ifdef INET6 -int ip6_gif_hlim; -#endif +VNET_DEFINE(int, ip6_gif_hlim); +#define V_ip6_gif_hlim VNET_GET(ip6_gif_hlim) #endif void (*ng_gif_input_p)(struct ifnet *ifp, struct mbuf **mp, int af); @@ -123,11 +122,10 @@ static int gif_clone_create(struct if_clone *, int, caddr_t); static void gif_clone_destroy(struct ifnet *); static int vnet_gif_iattach(const void *); -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE static const vnet_modinfo_t vnet_gif_modinfo = { .vmi_id = VNET_MOD_GIF, .vmi_name = "gif", - .vmi_size = sizeof(struct vnet_gif), .vmi_dependson = VNET_MOD_NET, .vmi_iattach = vnet_gif_iattach }; @@ -151,13 +149,13 @@ SYSCTL_NODE(_net_link, IFT_GIF, gif, CTLFLAG_RW, 0, */ #define MAX_GIF_NEST 1 #endif -SYSCTL_V_INT(V_NET, vnet_gif, _net_link_gif, OID_AUTO, max_nesting, - CTLFLAG_RW, max_gif_nesting, 0, "Max nested tunnels"); +SYSCTL_VNET_INT(_net_link_gif, OID_AUTO, max_nesting, CTLFLAG_RW, + &VNET_NAME(max_gif_nesting), 0, "Max nested tunnels"); #ifdef INET6 SYSCTL_DECL(_net_inet6_ip6); -SYSCTL_V_INT(V_NET, vnet_gif, _net_inet6_ip6, IPV6CTL_GIF_HLIM, - gifhlim, CTLFLAG_RW, ip6_gif_hlim, 0, ""); +SYSCTL_VNET_INT(_net_inet6_ip6, IPV6CTL_GIF_HLIM, gifhlim, CTLFLAG_RW, + &VNET_NAME(ip6_gif_hlim), 0, ""); #endif /* @@ -165,8 +163,8 @@ SYSCTL_V_INT(V_NET, vnet_gif, _net_inet6_ip6, IPV6CTL_GIF_HLIM, * pair of addresses. Some applications require this functionality so * we allow control over this check here. */ -SYSCTL_V_INT(V_NET, vnet_gif, _net_link_gif, OID_AUTO, parallel_tunnels, - CTLFLAG_RW, parallel_tunnels, 0, "Allow parallel tunnels?"); +SYSCTL_VNET_INT(_net_link_gif, OID_AUTO, parallel_tunnels, CTLFLAG_RW, + &VNET_NAME(parallel_tunnels), 0, "Allow parallel tunnels?"); /* copy from src/sys/net/if_ethersubr.c */ static const u_char etherbroadcastaddr[ETHER_ADDR_LEN] = @@ -182,7 +180,6 @@ gif_clone_create(ifc, unit, params) int unit; caddr_t params; { - INIT_VNET_GIF(curvnet); struct gif_softc *sc; sc = malloc(sizeof(struct gif_softc), M_GIF, M_WAITOK | M_ZERO); @@ -265,7 +262,6 @@ gif_clone_destroy(ifp) static int vnet_gif_iattach(const void *unused __unused) { - INIT_VNET_GIF(curvnet); LIST_INIT(&V_gif_softc_list); V_max_gif_nesting = MAX_GIF_NEST; @@ -295,7 +291,7 @@ gifmodevent(mod, type, data) case MOD_LOAD: mtx_init(&gif_mtx, "gif_mtx", NULL, MTX_DEF); -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE vnet_mod_register(&vnet_gif_modinfo); #else vnet_gif_iattach(NULL); @@ -419,7 +415,6 @@ gif_output(ifp, m, dst, ro) struct sockaddr *dst; struct route *ro; { - INIT_VNET_GIF(ifp->if_vnet); struct gif_softc *sc = ifp->if_softc; struct m_tag *mtag; int error = 0; @@ -944,7 +939,6 @@ gif_set_tunnel(ifp, src, dst) struct sockaddr *src; struct sockaddr *dst; { - INIT_VNET_GIF(ifp->if_vnet); struct gif_softc *sc = ifp->if_softc; struct gif_softc *sc2; struct sockaddr *osrc, *odst, *sa; diff --git a/sys/net/if_gif.h b/sys/net/if_gif.h index c8768b5..5257837 100644 --- a/sys/net/if_gif.h +++ b/sys/net/if_gif.h @@ -119,34 +119,8 @@ int gif_set_tunnel(struct ifnet *, struct sockaddr *, struct sockaddr *); void gif_delete_tunnel(struct ifnet *); int gif_encapcheck(const struct mbuf *, int, int, void *); -/* - * Virtualization support - */ - -struct vnet_gif { - LIST_HEAD(, gif_softc) _gif_softc_list; - int _max_gif_nesting; - int _parallel_tunnels; - int _ip_gif_ttl; - int _ip6_gif_hlim; -}; - -#ifndef VIMAGE -#ifndef VIMAGE_GLOBALS -extern struct vnet_gif vnet_gif_0; -#endif -#endif - -#define INIT_VNET_GIF(vnet) \ - INIT_FROM_VNET(vnet, VNET_MOD_GIF, struct vnet_gif, vnet_gif) - -#define VNET_GIF(sym) VSYM(vnet_gif, sym) - -#define V_gif_softc_list VNET_GIF(gif_softc_list) -#define V_max_gif_nesting VNET_GIF(max_gif_nesting) -#define V_parallel_tunnels VNET_GIF(parallel_tunnels) -#define V_ip_gif_ttl VNET_GIF(ip_gif_ttl) -#define V_ip6_gif_hlim VNET_GIF(ip6_gif_hlim) +VNET_DECLARE(int, ip_gif_ttl); +#define V_ip_gif_ttl VNET_GET(ip_gif_ttl) #endif /* _KERNEL */ diff --git a/sys/net/if_gre.c b/sys/net/if_gre.c index e7eb34a..4ed2a9e 100644 --- a/sys/net/if_gre.c +++ b/sys/net/if_gre.c @@ -80,7 +80,6 @@ #include <netinet/ip_gre.h> #include <netinet/ip_var.h> #include <netinet/ip_encap.h> -#include <netinet/vinet.h> #else #error "Huh? if_gre without inet?" #endif @@ -243,9 +242,6 @@ static int gre_output(struct ifnet *ifp, struct mbuf *m, struct sockaddr *dst, struct route *ro) { -#ifdef INET6 - INIT_VNET_INET(ifp->if_vnet); -#endif int error = 0; struct gre_softc *sc = ifp->if_softc; struct greip *gh; diff --git a/sys/net/if_loop.c b/sys/net/if_loop.c index 82c68ff..c2acacd 100644 --- a/sys/net/if_loop.c +++ b/sys/net/if_loop.c @@ -108,25 +108,26 @@ static int vnet_loif_iattach(const void *); static int vnet_loif_idetach(const void *); #endif -#ifdef VIMAGE_GLOBALS -struct ifnet *loif; /* Used externally */ -#endif +VNET_DEFINE(struct ifnet *, loif); /* Used externally */ #ifdef VIMAGE +static VNET_DEFINE(struct ifc_simple_data *, lo_cloner_data); +static VNET_DEFINE(struct if_clone *, lo_cloner); +#define V_lo_cloner_data VNET_GET(lo_cloner_data) +#define V_lo_cloner VNET_GET(lo_cloner) + MALLOC_DEFINE(M_LO_CLONER, "lo_cloner", "lo_cloner"); #endif -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE static const vnet_modinfo_t vnet_loif_modinfo = { .vmi_id = VNET_MOD_LOIF, .vmi_dependson = VNET_MOD_IF_CLONE, .vmi_name = "loif", .vmi_iattach = vnet_loif_iattach, -#ifdef VIMAGE .vmi_idetach = vnet_loif_idetach -#endif }; -#endif /* !VIMAGE_GLOBALS */ +#endif IFC_SIMPLE_DECLARE(lo, 1); @@ -147,7 +148,6 @@ lo_clone_destroy(struct ifnet *ifp) static int lo_clone_create(struct if_clone *ifc, int unit, caddr_t params) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; ifp = if_alloc(IFT_LOOP); @@ -173,10 +173,7 @@ lo_clone_create(struct if_clone *ifc, int unit, caddr_t params) static int vnet_loif_iattach(const void *unused __unused) { - INIT_VNET_NET(curvnet); - V_loif = NULL; - #ifdef VIMAGE V_lo_cloner = malloc(sizeof(*V_lo_cloner), M_LO_CLONER, M_WAITOK | M_ZERO); @@ -196,7 +193,6 @@ vnet_loif_iattach(const void *unused __unused) static int vnet_loif_idetach(const void *unused __unused) { - INIT_VNET_NET(curvnet); if_clone_detach(V_lo_cloner); free(V_lo_cloner, M_LO_CLONER); @@ -213,7 +209,7 @@ loop_modevent(module_t mod, int type, void *data) switch (type) { case MOD_LOAD: -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE vnet_mod_register(&vnet_loif_modinfo); #else vnet_loif_iattach(NULL); @@ -309,7 +305,6 @@ looutput(struct ifnet *ifp, struct mbuf *m, struct sockaddr *dst, int if_simloop(struct ifnet *ifp, struct mbuf *m, int af, int hlen) { - INIT_VNET_NET(ifp->if_vnet); int isr; M_ASSERTPKTHDR(m); diff --git a/sys/net/if_mib.c b/sys/net/if_mib.c index e4c8a98..c0018ef 100644 --- a/sys/net/if_mib.c +++ b/sys/net/if_mib.c @@ -67,8 +67,8 @@ SYSCTL_DECL(_net_link_generic); SYSCTL_NODE(_net_link_generic, IFMIB_SYSTEM, system, CTLFLAG_RW, 0, "Variables global to all interfaces"); -SYSCTL_V_INT(V_NET, vnet_net, _net_link_generic_system, IFMIB_IFCOUNT, - ifcount, CTLFLAG_RD, if_index, 0, +SYSCTL_VNET_INT(_net_link_generic_system, IFMIB_IFCOUNT, ifcount, CTLFLAG_RD, + &VNET_NAME(if_index), 0, "Number of configured interfaces"); static int diff --git a/sys/net/if_spppsubr.c b/sys/net/if_spppsubr.c index 0515afc..2c325ee 100644 --- a/sys/net/if_spppsubr.c +++ b/sys/net/if_spppsubr.c @@ -56,7 +56,6 @@ #ifdef INET #include <netinet/ip.h> #include <netinet/tcp.h> -#include <netinet/vinet.h> #endif #ifdef INET6 @@ -4937,7 +4936,6 @@ sppp_get_ip_addrs(struct sppp *sp, u_long *src, u_long *dst, u_long *srcmask) static void sppp_set_ip_addr(struct sppp *sp, u_long src) { - INIT_VNET_INET(curvnet); STDDCL; struct ifaddr *ifa; struct sockaddr_in *si; diff --git a/sys/net/if_stf.c b/sys/net/if_stf.c index 24e5ca5..ddc5662 100644 --- a/sys/net/if_stf.c +++ b/sys/net/if_stf.c @@ -106,7 +106,6 @@ #include <netinet/ip.h> #include <netinet/ip_var.h> #include <netinet/in_var.h> -#include <netinet/vinet.h> #include <netinet/ip6.h> #include <netinet6/ip6_var.h> @@ -378,7 +377,6 @@ static struct in6_ifaddr * stf_getsrcifa6(ifp) struct ifnet *ifp; { - INIT_VNET_INET(ifp->if_vnet); struct ifaddr *ia; struct in_ifaddr *ia4; struct sockaddr_in6 *sin6; @@ -596,7 +594,6 @@ stf_checkaddr4(sc, in, inifp) struct in_addr *in; struct ifnet *inifp; /* incoming interface */ { - INIT_VNET_INET(curvnet); struct in_ifaddr *ia4; /* diff --git a/sys/net/if_var.h b/sys/net/if_var.h index a995dfd..07914f5 100644 --- a/sys/net/if_var.h +++ b/sys/net/if_var.h @@ -80,6 +80,7 @@ struct vnet; #include <sys/mbuf.h> #include <sys/eventhandler.h> #include <sys/buf_ring.h> +#include <net/vnet.h> #endif /* _KERNEL */ #include <sys/lock.h> /* XXX */ #include <sys/mutex.h> /* XXX */ @@ -779,11 +780,16 @@ struct ifnet *ifnet_byindex_ref(u_short idx); */ struct ifaddr *ifaddr_byindex(u_short idx); -#ifdef VIMAGE_GLOBALS -extern struct ifnethead ifnet; -extern struct ifnet *loif; /* first loopback interface */ -extern int if_index; -#endif +VNET_DECLARE(struct ifnethead, ifnet); +VNET_DECLARE(struct ifgrouphead, ifg_head); +VNET_DECLARE(int, if_index); +VNET_DECLARE(struct ifnet *, loif); /* first loopback interface */ + +#define V_ifnet VNET_GET(ifnet) +#define V_ifg_head VNET_GET(ifg_head) +#define V_if_index VNET_GET(if_index) +#define V_loif VNET_GET(loif) + extern int ifqmaxlen; int if_addgroup(struct ifnet *, const char *); diff --git a/sys/net/if_vlan.c b/sys/net/if_vlan.c index 6278396..ac72870 100644 --- a/sys/net/if_vlan.c +++ b/sys/net/if_vlan.c @@ -576,7 +576,6 @@ MODULE_VERSION(if_vlan, 3); static struct ifnet * vlan_clone_match_ethertag(struct if_clone *ifc, const char *name, int *tag) { - INIT_VNET_NET(curvnet); const char *cp; struct ifnet *ifp; int t = 0; diff --git a/sys/net/raw_cb.c b/sys/net/raw_cb.c index 1dedff8..30a526f 100644 --- a/sys/net/raw_cb.c +++ b/sys/net/raw_cb.c @@ -58,9 +58,7 @@ */ struct mtx rawcb_mtx; -#ifdef VIMAGE_GLOBALS -struct rawcb_list_head rawcb_list; -#endif +VNET_DEFINE(struct rawcb_list_head, rawcb_list); SYSCTL_NODE(_net, OID_AUTO, raw, CTLFLAG_RW, 0, "Raw socket infrastructure"); @@ -79,7 +77,6 @@ SYSCTL_ULONG(_net_raw, OID_AUTO, recvspace, CTLFLAG_RW, &raw_recvspace, 0, int raw_attach(struct socket *so, int proto) { - INIT_VNET_NET(so->so_vnet); struct rawcb *rp = sotorawcb(so); int error; diff --git a/sys/net/raw_cb.h b/sys/net/raw_cb.h index ffdf731..aa84a05 100644 --- a/sys/net/raw_cb.h +++ b/sys/net/raw_cb.h @@ -55,9 +55,9 @@ struct rawcb { #define RAWRCVQ 8192 #ifdef _KERNEL -#ifdef VIMAGE_GLOBALS -extern LIST_HEAD(rawcb_list_head, rawcb) rawcb_list; -#endif +VNET_DECLARE(LIST_HEAD(rawcb_list_head, rawcb), rawcb_list); +#define V_rawcb_list VNET_GET(rawcb_list) + extern struct mtx rawcb_mtx; /* diff --git a/sys/net/raw_usrreq.c b/sys/net/raw_usrreq.c index 79d3e30..0759e42 100644 --- a/sys/net/raw_usrreq.c +++ b/sys/net/raw_usrreq.c @@ -58,7 +58,6 @@ MTX_SYSINIT(rawcb_mtx, &rawcb_mtx, "rawcb", MTX_DEF); void raw_init(void) { - INIT_VNET_NET(curvnet); LIST_INIT(&V_rawcb_list); } @@ -73,7 +72,6 @@ raw_init(void) void raw_input(struct mbuf *m0, struct sockproto *proto, struct sockaddr *src) { - INIT_VNET_NET(curvnet); struct rawcb *rp; struct mbuf *m = m0; struct socket *last; diff --git a/sys/net/route.c b/sys/net/route.c index 750829a..59a5912 100644 --- a/sys/net/route.c +++ b/sys/net/route.c @@ -63,7 +63,6 @@ #include <netinet/in.h> #include <netinet/ip_mroute.h> -#include <netinet/vinet.h> #include <vm/uma.h> @@ -88,68 +87,29 @@ SYSCTL_INT(_net, OID_AUTO, add_addr_allfibs, CTLFLAG_RW, &rt_add_addr_allfibs, 0, ""); TUNABLE_INT("net.add_addr_allfibs", &rt_add_addr_allfibs); -#ifdef VIMAGE_GLOBALS -struct radix_node_head *rt_tables; -static uma_zone_t rtzone; /* Routing table UMA zone. */ -int rttrash; /* routes not in table but not freed */ -struct rtstat rtstat; -#endif - -#ifndef VIMAGE_GLOBALS -struct vnet_rtable { - struct radix_node_head *_rt_tables; - uma_zone_t _rtzone; - int _rttrash; - struct rtstat _rtstat; -}; - -/* Size guard. See sys/vimage.h. */ -VIMAGE_CTASSERT(SIZEOF_vnet_rtable, sizeof(struct vnet_rtable)); - -#ifndef VIMAGE -static struct vnet_rtable vnet_rtable_0; -#endif -#endif - -/* - * Symbol translation macros - */ -#define INIT_VNET_RTABLE(vnet) \ - INIT_FROM_VNET(vnet, VNET_MOD_RTABLE, struct vnet_rtable, vnet_rtable) +VNET_DEFINE(struct radix_node_head *, rt_tables); +static VNET_DEFINE(uma_zone_t, rtzone); /* Routing table UMA zone. */ +VNET_DEFINE(int, rttrash); /* routes not in table but not freed */ +VNET_DEFINE(struct rtstat, rtstat); -#define VNET_RTABLE(sym) VSYM(vnet_rtable, sym) - -#define V_rt_tables VNET_RTABLE(rt_tables) -#define V_rtstat VNET_RTABLE(rtstat) -#define V_rttrash VNET_RTABLE(rttrash) -#define V_rtzone VNET_RTABLE(rtzone) +#define V_rt_tables VNET_GET(rt_tables) +#define V_rtzone VNET_GET(rtzone) +#define V_rttrash VNET_GET(rttrash) +#define V_rtstat VNET_GET(rtstat) static void rt_maskedcopy(struct sockaddr *, struct sockaddr *, struct sockaddr *); static int vnet_route_iattach(const void *); #ifdef VIMAGE static int vnet_route_idetach(const void *); -#endif - -#ifndef VIMAGE_GLOBALS -static struct vnet_symmap vnet_rtable_symmap[] = { - VNET_SYMMAP(rtable, rt_tables), - VNET_SYMMAP(rtable, rtstat), - VNET_SYMMAP(rtable, rttrash), - VNET_SYMMAP_END -}; static const vnet_modinfo_t vnet_rtable_modinfo = { .vmi_id = VNET_MOD_RTABLE, .vmi_name = "rtable", - .vmi_size = sizeof(struct vnet_rtable), - .vmi_symmap = vnet_rtable_symmap, .vmi_iattach = vnet_route_iattach, -#ifdef VIMAGE .vmi_idetach = vnet_route_idetach -#endif }; -#endif /* !VIMAGE_GLOBALS */ +#endif /* compare two sockaddr structures */ #define sa_equal(a1, a2) (bcmp((a1), (a2), (a1)->sa_len) == 0) @@ -192,7 +152,6 @@ SYSCTL_PROC(_net, OID_AUTO, my_fibnum, CTLTYPE_INT|CTLFLAG_RD, static __inline struct radix_node_head ** rt_tables_get_rnh_ptr(int table, int fam) { - INIT_VNET_RTABLE(curvnet); struct radix_node_head **rnh; KASSERT(table >= 0 && table < rt_numfibs, ("%s: table out of bounds.", @@ -226,7 +185,7 @@ route_init(void) rt_numfibs = 1; rn_init(); /* initialize all zeroes, all ones, mask table */ -#ifndef VIMAGE_GLOBALS +#ifdef VIMAGE vnet_mod_register(&vnet_rtable_modinfo); #else vnet_route_iattach(NULL); @@ -236,7 +195,6 @@ route_init(void) static int vnet_route_iattach(const void *unused __unused) { - INIT_VNET_RTABLE(curvnet); struct domain *dom; struct radix_node_head **rnh; int table; @@ -382,7 +340,6 @@ struct rtentry * rtalloc1_fib(struct sockaddr *dst, int report, u_long ignflags, u_int fibnum) { - INIT_VNET_RTABLE(curvnet); struct radix_node_head *rnh; struct rtentry *rt; struct radix_node *rn; @@ -452,7 +409,6 @@ done: void rtfree(struct rtentry *rt) { - INIT_VNET_RTABLE(curvnet); struct radix_node_head *rnh; KASSERT(rt != NULL,("%s: NULL rt", __func__)); @@ -551,7 +507,6 @@ rtredirect_fib(struct sockaddr *dst, struct sockaddr *src, u_int fibnum) { - INIT_VNET_RTABLE(curvnet); struct rtentry *rt, *rt0 = NULL; int error = 0; short *stat = NULL; @@ -880,7 +835,6 @@ rt_getifa_fib(struct rt_addrinfo *info, u_int fibnum) int rtexpunge(struct rtentry *rt) { - INIT_VNET_RTABLE(curvnet); struct radix_node *rn; struct radix_node_head *rnh; struct ifaddr *ifa; @@ -1018,8 +972,6 @@ gwdelete: RT_LOCK(rt); RT_ADDREF(rt); if (req == RTM_DELETE) { - INIT_VNET_RTABLE(curvnet); - rt->rt_flags &= ~RTF_UP; /* * One more rtentry floating around that is not @@ -1027,7 +979,6 @@ gwdelete: * when RTFREE(rt) is eventually called. */ V_rttrash++; - } nondelete: @@ -1054,7 +1005,6 @@ int rtrequest1_fib(int req, struct rt_addrinfo *info, struct rtentry **ret_nrt, u_int fibnum) { - INIT_VNET_RTABLE(curvnet); int error = 0, needlock = 0; register struct rtentry *rt; register struct radix_node *rn; diff --git a/sys/net/rtsock.c b/sys/net/rtsock.c index 532070d..bdea325 100644 --- a/sys/net/rtsock.c +++ b/sys/net/rtsock.c @@ -1238,7 +1238,6 @@ rt_ifannouncemsg(struct ifnet *ifp, int what) static void rt_dispatch(struct mbuf *m, const struct sockaddr *sa) { - INIT_VNET_NET(curvnet); struct m_tag *tag; /* @@ -1317,7 +1316,6 @@ sysctl_dumpentry(struct radix_node *rn, void *vw) static int sysctl_iflist(int af, struct walkarg *w) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; struct ifaddr *ifa; struct rt_addrinfo info; @@ -1378,7 +1376,6 @@ done: static int sysctl_ifmalist(int af, struct walkarg *w) { - INIT_VNET_NET(curvnet); struct ifnet *ifp; struct ifmultiaddr *ifma; struct rt_addrinfo info; diff --git a/sys/net/vnet.c b/sys/net/vnet.c new file mode 100644 index 0000000..a314886 --- /dev/null +++ b/sys/net/vnet.c @@ -0,0 +1,341 @@ +/*- + * Copyright (c) 2009 Jeffrey Roberson <jeff@freebsd.org> + * Copyright (c) 2009 Robert N. M. Watson + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/param.h> +#include <sys/kernel.h> +#include <sys/systm.h> +#include <sys/sysctl.h> +#include <sys/linker_set.h> +#include <sys/lock.h> +#include <sys/malloc.h> +#include <sys/proc.h> +#include <sys/sx.h> +#include <sys/sysctl.h> +#include <sys/vimage.h> + +#include <net/vnet.h> + +/*- + * This is the virtual network stack allocator, which provides storage for + * virtualized global variables. These variables are defined/declared using + * the VNET_DEFINE()/VNET_DECLARE() macros, which place them in the + * 'set_vnet' linker set. The details of the implementation are somewhat + * subtle, but allow the majority of most network subsystems to maintain + * virtualization-agnostic. + * + * The virtual network stack allocator handles variables in the base kernel + * vs. modules in similar but different ways. In both cases, virtualized + * global variables are marked as such by being declared to be part of the + * vnet linker set. These "master" copies of global variables serve two + * functions: + * + * (1) They contain static initialization or "default" values for global + * variables which will be propagated to each virtual network stack + * instance when created. As with normal global variables, they default + * to zero-filled. + * + * (2) They act as unique global names by which the variable can be referred + * to, regardless of network stack instance. The single global symbol + * will be used to calculate the location of a per-virtual instance + * variable at run-time. + * + * Each virtual network stack instance has a complete copy of each + * virtualized global variable, stored in a malloc'd block of memory + * referred to by vnet->vnet_data_mem. Critical to the design is that each + * per-instance memory block is laid out identically to the master block so + * that the offset of each global variable is the same across all blocks. To + * optimize run-time access, a precalculated 'base' address, + * vnet->vnet_data_base, is stored in each vnet, and is the amount that can + * be added to the address of a 'master' instance of a variable to get to the + * per-vnet instance. + * + * Virtualized global variables are handled in a similar manner, but as each + * module has its own 'set_vnet' linker set, and we want to keep all + * virtualized globals togther, we reserve space in the kernel's linker set + * for potential module variables using a per-vnet character array, + * 'modspace'. The virtual network stack allocator maintains a free list to + * track what space in the array is free (all, initially) and as modules are + * linked, allocates portions of the space to specific globals. The kernel + * module linker queries the virtual network stack allocator and will + * bind references of the global to the location during linking. It also + * calls into the virtual network stack allocator, once the memory is + * initialized, in order to propagate the new static initializations to all + * existing virtual network stack instances so that the soon-to-be executing + * module will find every network stack instance with proper default values. + */ + +/* + * Location of the kernel's 'set_vnet' linker set. + */ +extern uintptr_t *__start_set_vnet; +extern uintptr_t *__stop_set_vnet; + +#define VNET_START (uintptr_t)&__start_set_vnet +#define VNET_STOP (uintptr_t)&__stop_set_vnet + +/* + * Number of bytes of data in the 'set_vnet' linker set, and hence the total + * size of all kernel virtualized global variables, and the malloc(9) type + * that will be used to allocate it. + */ +#define VNET_BYTES (VNET_STOP - VNET_START) + +MALLOC_DEFINE(M_VNET_DATA, "vnet_data", "VNET data"); + +/* + * VNET_MODMIN is the minimum number of bytes we will reserve for the sum of + * global variables across all loaded modules. As this actually sizes an + * array declared as a virtualized global variable in the kernel itself, and + * we want the virtualized global variable space to be page-sized, we may + * have more space than that in practice. + */ +#define VNET_MODMIN 8192 +#define VNET_SIZE roundup2(VNET_BYTES, PAGE_SIZE) +#define VNET_MODSIZE (VNET_SIZE - (VNET_BYTES - VNET_MODMIN)) + +/* + * Space to store virtualized global variables from loadable kernel modules, + * and the free list to manage it. + */ +static VNET_DEFINE(char, modspace[VNET_MODMIN]); + +struct vnet_data_free { + uintptr_t vnd_start; + int vnd_len; + TAILQ_ENTRY(vnet_data_free) vnd_link; +}; + +MALLOC_DEFINE(M_VNET_DATA_FREE, "vnet_data_free", "VNET resource accounting"); +static TAILQ_HEAD(, vnet_data_free) vnet_data_free_head = + TAILQ_HEAD_INITIALIZER(vnet_data_free_head); +static struct sx vnet_data_free_lock; + +/* + * Allocate storage for virtualized global variables in a new virtual network + * stack instance, and copy in initial values from our 'master' copy. + */ +void +vnet_data_init(struct vnet *vnet) +{ + + vnet->vnet_data_mem = malloc(VNET_SIZE, M_VNET_DATA, M_WAITOK); + memcpy(vnet->vnet_data_mem, (void *)VNET_START, VNET_BYTES); + + /* + * All use of vnet-specific data will immediately subtract VNET_START + * from the base memory pointer, so pre-calculate that now to avoid + * it on each use. + */ + vnet->vnet_data_base = (uintptr_t)vnet->vnet_data_mem - VNET_START; +} + +/* + * Release storage for a virtual network stack instance. + */ +void +vnet_data_destroy(struct vnet *vnet) +{ + + free(vnet->vnet_data_mem, M_VNET_DATA); + vnet->vnet_data_mem = NULL; + vnet->vnet_data_base = 0; +} + +/* + * Once on boot, initialize the modspace freelist to entirely cover modspace. + */ +static void +vnet_data_startup(void *dummy __unused) +{ + struct vnet_data_free *df; + + df = malloc(sizeof(*df), M_VNET_DATA_FREE, M_WAITOK | M_ZERO); + df->vnd_start = (uintptr_t)&VNET_NAME(modspace); + df->vnd_len = VNET_MODSIZE; + TAILQ_INSERT_HEAD(&vnet_data_free_head, df, vnd_link); + sx_init(&vnet_data_free_lock, "vnet_data alloc lock"); +} +SYSINIT(vnet_data, SI_SUB_KLD, SI_ORDER_FIRST, vnet_data_startup, 0); + +/* + * When a module is loaded and requires storage for a virtualized global + * variable, allocate space from the modspace free list. This interface + * should be used only by the kernel linker. + */ +void * +vnet_data_alloc(int size) +{ + struct vnet_data_free *df; + void *s; + + s = NULL; + size = roundup2(size, sizeof(void *)); + sx_xlock(&vnet_data_free_lock); + TAILQ_FOREACH(df, &vnet_data_free_head, vnd_link) { + if (df->vnd_len < size) + continue; + if (df->vnd_len == size) { + s = (void *)df->vnd_start; + TAILQ_REMOVE(&vnet_data_free_head, df, vnd_link); + free(df, M_VNET_DATA_FREE); + break; + } + s = (void *)df->vnd_start; + df->vnd_len -= size; + df->vnd_start = df->vnd_start + size; + break; + } + sx_xunlock(&vnet_data_free_lock); + + return (s); +} + +/* + * Free space for a virtualized global variable on module unload. + */ +void +vnet_data_free(void *start_arg, int size) +{ + struct vnet_data_free *df; + struct vnet_data_free *dn; + uintptr_t start; + uintptr_t end; + + size = roundup2(size, sizeof(void *)); + start = (uintptr_t)start_arg; + end = start + size; + /* + * Free a region of space and merge it with as many neighbors as + * possible. Keeping the list sorted simplifies this operation. + */ + sx_xlock(&vnet_data_free_lock); + TAILQ_FOREACH(df, &vnet_data_free_head, vnd_link) { + if (df->vnd_start > end) + break; + /* + * If we expand at the end of an entry we may have to + * merge it with the one following it as well. + */ + if (df->vnd_start + df->vnd_len == start) { + df->vnd_len += size; + dn = TAILQ_NEXT(df, vnd_link); + if (df->vnd_start + df->vnd_len == dn->vnd_start) { + df->vnd_len += dn->vnd_len; + TAILQ_REMOVE(&vnet_data_free_head, dn, vnd_link); + free(dn, M_VNET_DATA_FREE); + } + sx_xunlock(&vnet_data_free_lock); + return; + } + if (df->vnd_start == end) { + df->vnd_start = start; + df->vnd_len += size; + sx_xunlock(&vnet_data_free_lock); + return; + } + } + dn = malloc(sizeof(*df), M_VNET_DATA_FREE, M_WAITOK | M_ZERO); + dn->vnd_start = start; + dn->vnd_len = size; + if (df) + TAILQ_INSERT_BEFORE(df, dn, vnd_link); + else + TAILQ_INSERT_TAIL(&vnet_data_free_head, dn, vnd_link); + sx_xunlock(&vnet_data_free_lock); +} + +struct vnet_data_copy_fn_arg { + void *start; + int size; +}; + +static void +vnet_data_copy_fn(struct vnet *vnet, void *arg) +{ + struct vnet_data_copy_fn_arg *varg = arg; + + memcpy((void *)((uintptr_t)vnet->vnet_data_base + + (uintptr_t)varg->start), varg->start, varg->size); +} + +/* + * When a new virtualized global variable has been allocated, propagate its + * initial value to each already-allocated virtual network stack instance. + */ +void +vnet_data_copy(void *start, int size) +{ + struct vnet_data_copy_fn_arg varg; + + varg.start = start; + varg.size = size; + vnet_foreach(vnet_data_copy_fn, &varg); +} + +/* + * Variants on sysctl_handle_foo that know how to handle virtualized global + * variables: if 'arg1' is a pointer, then we transform it to the local vnet + * offset. + */ +int +vnet_sysctl_handle_int(SYSCTL_HANDLER_ARGS) +{ + + if (arg1 != NULL) + arg1 = (void *)(curvnet->vnet_data_base + (uintptr_t)arg1); + return (sysctl_handle_int(oidp, arg1, arg2, req)); +} + +int +vnet_sysctl_handle_opaque(SYSCTL_HANDLER_ARGS) +{ + + if (arg1 != NULL) + arg1 = (void *)(curvnet->vnet_data_base + (uintptr_t)arg1); + return (sysctl_handle_opaque(oidp, arg1, arg2, req)); +} + +int +vnet_sysctl_handle_string(SYSCTL_HANDLER_ARGS) +{ + + if (arg1 != NULL) + arg1 = (void *)(curvnet->vnet_data_base + (uintptr_t)arg1); + return (sysctl_handle_string(oidp, arg1, arg2, req)); +} + +int +vnet_sysctl_handle_uint(SYSCTL_HANDLER_ARGS) +{ + + if (arg1 != NULL) + arg1 = (void *)(curvnet->vnet_data_base + (uintptr_t)arg1); + return (sysctl_handle_int(oidp, arg1, arg2, req)); +} diff --git a/sys/net/vnet.h b/sys/net/vnet.h index b5d2fbd..4b543e6 100644 --- a/sys/net/vnet.h +++ b/sys/net/vnet.h @@ -1,10 +1,6 @@ /*- - * Copyright (c) 2006-2008 University of Zagreb - * Copyright (c) 2006-2008 FreeBSD Foundation - * - * This software was developed by the University of Zagreb and the - * FreeBSD Foundation under sponsorship by the Stichting NLnet and the - * FreeBSD Foundation. + * Copyright (c) 2009 Jeffrey Roberson <jeff@freebsd.org> + * Copyright (c) 2009 Robert N. M. Watson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -30,62 +26,131 @@ * $FreeBSD$ */ +/* + * This is the virtual network stack memory allocator, which provides support + * for virtualized global variables via a special linker set, set_vnet. When + * "options VIMAGE" isn't defined, virtualized global variables are compiled + * as normal globals. + */ + #ifndef _NET_VNET_H_ #define _NET_VNET_H_ -#include <net/if_var.h> +#ifdef _KERNEL +#ifdef VIMAGE + +#if defined(__arm__) +__asm__(".section set_vnet, \"aw\", %progbits"); +#else +__asm__(".section set_vnet, \"aw\", @progbits"); +#endif +__asm__(".previous"); + +#define VNET_NAME(n) vnet_entry_##n +#define VNET_DECLARE(t, n) extern t VNET_NAME(n) +#define VNET_DEFINE(t, n) t VNET_NAME(n) __section("set_vnet") __used +#define _VNET_PTR(b, n) (__typeof(VNET_NAME(n))*) \ + ((b) + (uintptr_t)&VNET_NAME(n)) + +#define _VNET_GET(b, n) (*_VNET_PTR(b, n)) +#define _VNET_SET(b, n, v) (*_VNET_PTR(b, n) = v) -struct ifindex_entry; +/* + * Virtualized global variable accessor macros. + */ +#define VNET_VNET_PTR(vnet, n) _VNET_PTR((vnet)->vnet_data_base, n) +#define VNET_VNET_GET(vnet, n) (*VNET_VNET_PTR((vnet), n)) +#define VNET_VNET_SET(vnet, n, v) ((*VNET_VNET_PTR((vnet), n)) = v) -struct vnet_net { - int _if_index; - struct ifindex_entry * _ifindex_table; - struct ifnethead _ifnet; - struct ifgrouphead _ifg_head; +#define VNET_PTR(n) VNET_VNET_PTR(curvnet, n) +#define VNET_GET(n) VNET_VNET_GET(curvnet, n) +#define VNET_SET(n, v) VNET_VNET_SET(curvnet, n, v) - int _if_indexlim; +/* + * Sysctl variants for vnet-virtualized global variables. Include + * <sys/sysctl.h> to expose these definitions. + * + * Note: SYSCTL_PROC() handler functions will need to resolve pointer + * arguments themselves, if required. + */ +#ifdef SYSCTL_OID +int vnet_sysctl_handle_int(SYSCTL_HANDLER_ARGS); +int vnet_sysctl_handle_opaque(SYSCTL_HANDLER_ARGS); +int vnet_sysctl_handle_string(SYSCTL_HANDLER_ARGS); +int vnet_sysctl_handle_uint(SYSCTL_HANDLER_ARGS); - struct ifnet * _loif; - struct if_clone * _lo_cloner; - struct ifc_simple_data *_lo_cloner_data; +#define SYSCTL_VNET_INT(parent, nbr, name, access, ptr, val, descr) \ + SYSCTL_OID(parent, nbr, name, CTLTYPE_INT|CTLFLAG_MPSAFE|(access), \ + ptr, val, vnet_sysctl_handle_int, "I", descr) +#define SYSCTL_VNET_PROC(parent, nbr, name, access, ptr, arg, handler, \ + fmt, descr) \ + SYSCTL_OID(parent, nbr, name, access, ptr, arg, handler, fmt, \ + descr) +#define SYSCTL_VNET_STRING(parent, nbr, name, access, arg, len, descr) \ + SYSCTL_OID(parent, nbr, name, CTLTYPE_STRING|(access), arg, \ + len, vnet_sysctl_handle_string, "A", descr) +#define SYSCTL_VNET_STRUCT(parent, nbr, name, access, ptr, type, descr) \ + SYSCTL_OID(parent, nbr, name, CTLTYPE_OPAQUE|(access), ptr, \ + sizeof(struct type), vnet_sysctl_handle_opaque, "S," #type, \ + descr) +#define SYSCTL_VNET_UINT(parent, nbr, name, access, ptr, val, descr) \ + SYSCTL_OID(parent, nbr, name, CTLTYPE_UINT|CTLFLAG_MPSAFE|(access), \ + ptr, val, vnet_sysctl_handle_uint, "IU", descr) +#endif /* SYSCTL_OID */ - LIST_HEAD(, rawcb) _rawcb_list; +/* + * Interfaces from the kernel linker. + */ +void *vnet_data_alloc(int size); +void vnet_data_copy(void *start, int size); +void vnet_data_free(void *start_arg, int size); - LIST_HEAD(, if_clone) _if_cloners; - int _if_cloners_count; +/* + * Interfaces for vnet setup/teardown. + */ +struct vnet; +void vnet_data_init(struct vnet *vnet); +void vnet_data_destroy(struct vnet *vnet); - int _ether_ipfw; -}; +#else /* !VIMAGE */ -/* Size guard. See sys/vimage.h. */ -VIMAGE_CTASSERT(SIZEOF_vnet_net, sizeof(struct vnet_net)); +/* + * Versions of the VNET macros that compile to normal global variables and + * standard sysctl definitions. + */ +#define VNET_NAME(n) n +#define VNET_DECLARE(t, n) extern t n +#define VNET_DEFINE(t, n) t n +#define _VNET_PTR(b, n) &VNET_NAME(n) -#ifndef VIMAGE -#ifndef VIMAGE_GLOBALS -extern struct vnet_net vnet_net_0; -#endif -#endif +#ifdef SYSCTL_OID +#define SYSCTL_VNET_INT(parent, nbr, name, access, ptr, val, descr) \ + SYSCTL_INT(parent, nbr, name, access, ptr, val, descr) +#define SYSCTL_VNET_PROC(parent, nbr, name, access, ptr, arg, handler, \ + fmt, descr) \ + SYSCTL_PROC(parent, nbr, name, access, ptr, arg, handler, fmt, \ + descr) +#define SYSCTL_VNET_STRING(parent, nbr, name, access, arg, len, descr) \ + SYSCTL_STRING(parent, nbr, name, access, arg, len, descr) +#define SYSCTL_VNET_STRUCT(parent, nbr, name, access, ptr, type, descr) \ + SYSCTL_STRUCT(parent, nbr, name, access, ptr, type, descr) +#define SYSCTL_VNET_UINT(parent, nbr, name, access, ptr, val, descr) \ + SYSCTL_UINT(parent, nbr, name, access, ptr, val, descr) +#endif /* SYSCTL_OID */ /* - * Symbol translation macros + * Virtualized global variable accessor macros. */ -#define INIT_VNET_NET(vnet) \ - INIT_FROM_VNET(vnet, VNET_MOD_NET, struct vnet_net, vnet_net) - -#define VNET_NET(sym) VSYM(vnet_net, sym) - -#define V_ether_ipfw VNET_NET(ether_ipfw) -#define V_if_index VNET_NET(if_index) -#define V_if_indexlim VNET_NET(if_indexlim) -#define V_if_cloners VNET_NET(if_cloners) -#define V_if_cloners_count VNET_NET(if_cloners_count) -#define V_ifg_head VNET_NET(ifg_head) -#define V_ifindex_table VNET_NET(ifindex_table) -#define V_ifklist VNET_NET(ifklist) -#define V_ifnet VNET_NET(ifnet) -#define V_lo_cloner VNET_NET(lo_cloner) -#define V_lo_cloner_data VNET_NET(lo_cloner_data) -#define V_loif VNET_NET(loif) -#define V_rawcb_list VNET_NET(rawcb_list) +#define VNET_VNET_PTR(vnet, n) (&(n)) +#define VNET_VNET_GET(vnet, n) (n) +#define VNET_VNET_SET(vnet, n, v) ((n) = (v)) + +#define VNET_PTR(n) (&(n)) +#define VNET_GET(n) (n) +#define VNET_SET(n, v) ((n) = (v)) + +#endif /* VIMAGE */ + +#endif /* _KERNEL */ #endif /* !_NET_VNET_H_ */ |