diff options
author | Henning Brauer <henning@cvs.openbsd.org> | 2006-11-27 12:27:46 +0000 |
---|---|---|
committer | Henning Brauer <henning@cvs.openbsd.org> | 2006-11-27 12:27:46 +0000 |
commit | 840004135aa5ae51a122a1f689d6726b5c2e45ff (patch) | |
tree | 09b4562be58e3e35a3863d55f2e0721d902e2549 | |
parent | 260cd8ce709a413c6a5adab22ec07153aa64354a (diff) |
make use of multiple routing tables.
hook up looking up routes in alternate tables to the packet forwarding path.
alternate routing tables are mintained with route(8), table selection via pf.
mostly hacked on a train ride with ryan some time ago, ok mcbride claudio
-rw-r--r-- | sys/netinet/ip_input.c | 19 | ||||
-rw-r--r-- | sys/netinet6/ip6_forward.c | 18 | ||||
-rw-r--r-- | sys/netinet6/ip6_input.c | 17 |
3 files changed, 43 insertions, 11 deletions
diff --git a/sys/netinet/ip_input.c b/sys/netinet/ip_input.c index 366fb593b16..d49d43e8687 100644 --- a/sys/netinet/ip_input.c +++ b/sys/netinet/ip_input.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ip_input.c,v 1.144 2006/10/11 09:29:20 henning Exp $ */ +/* $OpenBSD: ip_input.c,v 1.145 2006/11/27 12:27:45 henning Exp $ */ /* $NetBSD: ip_input.c,v 1.30 1996/03/16 23:53:58 christos Exp $ */ /* @@ -239,6 +239,7 @@ ip_init() struct sockaddr_in ipaddr = { sizeof(ipaddr), AF_INET }; struct route ipforward_rt; +int ipforward_rtableid; void ipintr() @@ -1407,9 +1408,12 @@ ip_forward(m, srcrt) struct ip *ip = mtod(m, struct ip *); struct sockaddr_in *sin; struct rtentry *rt; - int error, type = 0, code = 0, destmtu = 0; + int error, type = 0, code = 0, destmtu = 0, rtableid = 0; struct mbuf *mcopy; n_long dest; +#if NPF > 0 + struct pf_mtag *pft; +#endif dest = 0; #ifdef DIAGNOSTIC @@ -1427,9 +1431,15 @@ ip_forward(m, srcrt) return; } +#if NPF > 0 + if ((pft = pf_find_mtag(m)) != NULL) + rtableid = pft->rtableid; +#endif + sin = satosin(&ipforward_rt.ro_dst); if ((rt = ipforward_rt.ro_rt) == 0 || - ip->ip_dst.s_addr != sin->sin_addr.s_addr) { + ip->ip_dst.s_addr != sin->sin_addr.s_addr || + rtableid != ipforward_rtableid) { if (ipforward_rt.ro_rt) { RTFREE(ipforward_rt.ro_rt); ipforward_rt.ro_rt = 0; @@ -1438,11 +1448,12 @@ ip_forward(m, srcrt) sin->sin_len = sizeof(*sin); sin->sin_addr = ip->ip_dst; - rtalloc_mpath(&ipforward_rt, &ip->ip_src.s_addr, 0); + rtalloc_mpath(&ipforward_rt, &ip->ip_src.s_addr, rtableid); if (ipforward_rt.ro_rt == 0) { icmp_error(m, ICMP_UNREACH, ICMP_UNREACH_HOST, dest, 0); return; } + ipforward_rtableid = rtableid; rt = ipforward_rt.ro_rt; } diff --git a/sys/netinet6/ip6_forward.c b/sys/netinet6/ip6_forward.c index 4b3ec716eef..7448d6f3f59 100644 --- a/sys/netinet6/ip6_forward.c +++ b/sys/netinet6/ip6_forward.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ip6_forward.c,v 1.36 2006/11/17 01:11:23 itojun Exp $ */ +/* $OpenBSD: ip6_forward.c,v 1.37 2006/11/27 12:27:45 henning Exp $ */ /* $KAME: ip6_forward.c,v 1.75 2001/06/29 12:42:13 jinmei Exp $ */ /* @@ -69,6 +69,7 @@ #endif struct route_in6 ip6_forward_rt; +int ip6_forward_rtableid; /* * Forward a packet. If some error occurs return the sender @@ -103,6 +104,10 @@ ip6_forward(m, srcrt) struct tdb *tdb; int s; #endif /* IPSEC */ +#if NPF > 0 + struct pf_mtag *pft; +#endif + int rtableid = 0; /* * Do not forward packets to multicast destination (should be handled @@ -214,6 +219,11 @@ ip6_forward(m, srcrt) done_spd: #endif /* IPSEC */ +#if NPF > 0 + if ((pft = pf_find_mtag(m)) != NULL) + rtableid = pft->rtableid; +#endif + /* * Save at most ICMPV6_PLD_MAXLEN (= the min IPv6 MTU - * size of IPv6 + ICMPv6 headers) bytes of the packet in case @@ -231,14 +241,16 @@ ip6_forward(m, srcrt) * ip6_forward_rt.ro_dst.sin6_addr is equal to ip6->ip6_dst */ if (ip6_forward_rt.ro_rt == 0 || - (ip6_forward_rt.ro_rt->rt_flags & RTF_UP) == 0) { + (ip6_forward_rt.ro_rt->rt_flags & RTF_UP) == 0 || + ip6_forward_rtableid != rtableid) { if (ip6_forward_rt.ro_rt) { RTFREE(ip6_forward_rt.ro_rt); ip6_forward_rt.ro_rt = 0; } /* this probably fails but give it a try again */ rtalloc_mpath((struct route *)&ip6_forward_rt, - &ip6->ip6_src.s6_addr32[0], 0); + &ip6->ip6_src.s6_addr32[0], rtableid); + ip6_forward_rtableid = rtableid; } if (ip6_forward_rt.ro_rt == 0) { diff --git a/sys/netinet6/ip6_input.c b/sys/netinet6/ip6_input.c index 3f7b5dc09be..67b01130451 100644 --- a/sys/netinet6/ip6_input.c +++ b/sys/netinet6/ip6_input.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ip6_input.c,v 1.69 2006/11/17 01:11:23 itojun Exp $ */ +/* $OpenBSD: ip6_input.c,v 1.70 2006/11/27 12:27:45 henning Exp $ */ /* $KAME: ip6_input.c,v 1.188 2001/03/29 05:34:31 itojun Exp $ */ /* @@ -185,6 +185,7 @@ ip6intr() } extern struct route_in6 ip6_forward_rt; +extern int ip6_forward_rtableid; void ip6_input(m) @@ -198,8 +199,9 @@ ip6_input(m) struct ifnet *deliverifp = NULL; #if NPF > 0 struct in6_addr odst; + struct pf_mtag *pft; #endif - int srcrt = 0; + int srcrt = 0, rtableid = 0; /* * mbuf statistics by kazu @@ -390,13 +392,19 @@ ip6_input(m) goto hbhcheck; } +#if NPF > 0 + if ((pft = pf_find_mtag(m)) != NULL) + rtableid = pft->rtableid; +#endif + /* * Unicast check */ if (ip6_forward_rt.ro_rt != NULL && (ip6_forward_rt.ro_rt->rt_flags & RTF_UP) != 0 && IN6_ARE_ADDR_EQUAL(&ip6->ip6_dst, - &ip6_forward_rt.ro_dst.sin6_addr)) + &ip6_forward_rt.ro_dst.sin6_addr) && + rtableid == ip6_forward_rtableid) ip6stat.ip6s_forward_cachehit++; else { if (ip6_forward_rt.ro_rt) { @@ -410,9 +418,10 @@ ip6_input(m) ip6_forward_rt.ro_dst.sin6_len = sizeof(struct sockaddr_in6); ip6_forward_rt.ro_dst.sin6_family = AF_INET6; ip6_forward_rt.ro_dst.sin6_addr = ip6->ip6_dst; + ip6_forward_rtableid = rtableid; rtalloc_mpath((struct route *)&ip6_forward_rt, - &ip6->ip6_src.s6_addr32[0], 0); + &ip6->ip6_src.s6_addr32[0], rtableid); } #define rt6_key(r) ((struct sockaddr_in6 *)((r)->rt_nodes->rn_key)) |