diff options
author | Martin Pieuchot <mpi@cvs.openbsd.org> | 2015-09-11 19:23:01 +0000 |
---|---|---|
committer | Martin Pieuchot <mpi@cvs.openbsd.org> | 2015-09-11 19:23:01 +0000 |
commit | 8cb12af7abe545546c2692ce0731ea72c887947b (patch) | |
tree | f4a12a9a0d91ece24374dfd92301b4b7ad005fcc /sys/netinet6 | |
parent | 478f3dae60533b42e512287c9e40fb04e6118ce0 (diff) |
Rewrite in6_selectroute() to no longer return an ifp.
The returned "struct rtentry" is either the cached one or the one passed
in options.
ok claudio@
Diffstat (limited to 'sys/netinet6')
-rw-r--r-- | sys/netinet6/in6_src.c | 83 | ||||
-rw-r--r-- | sys/netinet6/ip6_output.c | 17 | ||||
-rw-r--r-- | sys/netinet6/ip6_var.h | 7 |
3 files changed, 28 insertions, 79 deletions
diff --git a/sys/netinet6/in6_src.c b/sys/netinet6/in6_src.c index 46858a1dc2a..4977868e96e 100644 --- a/sys/netinet6/in6_src.c +++ b/sys/netinet6/in6_src.c @@ -1,4 +1,4 @@ -/* $OpenBSD: in6_src.c,v 1.59 2015/09/11 13:53:04 mpi Exp $ */ +/* $OpenBSD: in6_src.c,v 1.60 2015/09/11 19:23:00 mpi Exp $ */ /* $KAME: in6_src.c,v 1.36 2001/02/06 04:08:17 itojun Exp $ */ /* @@ -293,14 +293,10 @@ in6_selectsrc(struct in6_addr **in6src, struct sockaddr_in6 *dstsock, return (EADDRNOTAVAIL); } -int +struct rtentry * in6_selectroute(struct sockaddr_in6 *dstsock, struct ip6_pktopts *opts, - struct route_in6 *ro, struct ifnet **retifp, - struct rtentry **retrt, unsigned int rtableid) + struct route_in6 *ro, unsigned int rtableid) { - int error = 0; - struct ifnet *ifp = NULL; - struct rtentry *rt = NULL; struct sockaddr_in6 *sin6_next; struct in6_addr *dst; @@ -315,11 +311,9 @@ in6_selectroute(struct sockaddr_in6 *dstsock, struct ip6_pktopts *opts, sin6_next = satosin6(opts->ip6po_nexthop); - /* at this moment, we only support AF_INET6 next hops */ - if (sin6_next->sin6_family != AF_INET6) { - error = EAFNOSUPPORT; /* or should we proceed? */ - goto done; - } + /* We only support AF_INET6 next hops */ + if (sin6_next->sin6_family != AF_INET6) + return (NULL); /* * If the next hop is an IPv6 address, then the node identified @@ -348,25 +342,16 @@ in6_selectroute(struct sockaddr_in6 *dstsock, struct ip6_pktopts *opts, rtfree(ron->ro_rt); ron->ro_rt = NULL; } - error = EHOSTUNREACH; - goto done; + return (NULL); } } if (!nd6_is_addr_neighbor(sin6_next, ron->ro_rt->rt_ifp)) { rtfree(ron->ro_rt); ron->ro_rt = NULL; - error = EHOSTUNREACH; - goto done; + return (NULL); } - rt = ron->ro_rt; - ifp = rt->rt_ifp; - /* - * When cloning is required, try to allocate a route to the - * destination so that the caller can store path MTU - * information. - */ - goto done; + return (ron->ro_rt); } /* @@ -397,25 +382,6 @@ in6_selectroute(struct sockaddr_in6 *dstsock, struct ip6_pktopts *opts, } /* - * do not care about the result if we have the nexthop - * explicitly specified. - */ - if (opts && opts->ip6po_nexthop) - goto done; - - if (ro->ro_rt) { - ifp = ro->ro_rt->rt_ifp; - - if (ifp == NULL) { /* can this really happen? */ - rtfree(ro->ro_rt); - ro->ro_rt = NULL; - } - } - if (ro->ro_rt == NULL) - error = EHOSTUNREACH; - rt = ro->ro_rt; - - /* * Check if the outgoing interface conflicts with * the interface specified by ipi6_ifindex (if specified). * Note that loopback interface is always okay. @@ -424,30 +390,18 @@ in6_selectroute(struct sockaddr_in6 *dstsock, struct ip6_pktopts *opts, */ if (opts && opts->ip6po_pktinfo && opts->ip6po_pktinfo->ipi6_ifindex) { - if (!(ifp->if_flags & IFF_LOOPBACK) && - ifp->if_index != + if (ro->ro_rt != NULL && + (ro->ro_rt->rt_ifp->if_flags & IFF_LOOPBACK) == 0 && + ro->ro_rt->rt_ifp->if_index != opts->ip6po_pktinfo->ipi6_ifindex) { - error = EHOSTUNREACH; - goto done; + return (NULL); } } - } - done: - if (ifp == NULL && rt == NULL) { - /* - * This can happen if the caller did not pass a cached route - * nor any other hints. We treat this case an error. - */ - error = EHOSTUNREACH; + return (ro->ro_rt); } - if (retifp != NULL) - *retifp = ifp; - if (retrt != NULL) - *retrt = rt; /* rt may be NULL */ - - return (error); + return (NULL); } int @@ -457,7 +411,6 @@ in6_selectif(struct sockaddr_in6 *dstsock, struct ip6_pktopts *opts, { struct rtentry *rt = NULL; struct in6_pktinfo *pi = NULL; - int error; /* If the caller specify the outgoing interface explicitly, use it. */ if (opts && (pi = opts->ip6po_pktinfo) != NULL && pi->ipi6_ifindex) { @@ -474,9 +427,9 @@ in6_selectif(struct sockaddr_in6 *dstsock, struct ip6_pktopts *opts, mopts != NULL && (*retifp = if_get(mopts->im6o_ifidx)) != NULL) return (0); - if ((error = in6_selectroute(dstsock, opts, ro, retifp, - &rt, rtableid)) != 0) - return (error); + rt = in6_selectroute(dstsock, opts, ro, rtableid); + if (rt == NULL) + return (EHOSTUNREACH); /* * do not use a rejected or black hole route. diff --git a/sys/netinet6/ip6_output.c b/sys/netinet6/ip6_output.c index 44167d3ac22..2d25636bd04 100644 --- a/sys/netinet6/ip6_output.c +++ b/sys/netinet6/ip6_output.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ip6_output.c,v 1.183 2015/09/11 13:53:04 mpi Exp $ */ +/* $OpenBSD: ip6_output.c,v 1.184 2015/09/11 19:23:00 mpi Exp $ */ /* $KAME: ip6_output.c,v 1.172 2001/03/25 09:55:56 itojun Exp $ */ /* @@ -544,18 +544,15 @@ reroute: } if (ifp == NULL) { - if ((error = in6_selectroute(&dstsock, opt, ro, &ifp, - &rt, m->m_pkthdr.ph_rtableid)) != 0) { + rt = in6_selectroute(&dstsock, opt, ro, ro->ro_tableid); + if (rt == NULL) { ip6stat.ip6s_noroute++; + error = EHOSTUNREACH; goto bad; } - } - if (rt == NULL) { - /* - * If in6_selectroute() does not return a route entry, - * dst may not have been updated. - */ - *dst = dstsock; /* XXX */ + ifp = rt->rt_ifp; + } else { + *dst = dstsock; } /* diff --git a/sys/netinet6/ip6_var.h b/sys/netinet6/ip6_var.h index 26b3930e1b3..08a20b63f8c 100644 --- a/sys/netinet6/ip6_var.h +++ b/sys/netinet6/ip6_var.h @@ -1,4 +1,4 @@ -/* $OpenBSD: ip6_var.h,v 1.54 2015/09/11 13:53:04 mpi Exp $ */ +/* $OpenBSD: ip6_var.h,v 1.55 2015/09/11 19:23:00 mpi Exp $ */ /* $KAME: ip6_var.h,v 1.33 2000/06/11 14:59:20 jinmei Exp $ */ /* @@ -310,9 +310,8 @@ int none_input(struct mbuf **, int *, int); int in6_selectsrc(struct in6_addr **, struct sockaddr_in6 *, struct ip6_pktopts *, struct ip6_moptions *, struct route_in6 *, struct in6_addr *, u_int); -int in6_selectroute(struct sockaddr_in6 *, struct ip6_pktopts *, - struct route_in6 *, struct ifnet **, - struct rtentry **, unsigned int rtableid); +struct rtentry *in6_selectroute(struct sockaddr_in6 *, struct ip6_pktopts *, + struct route_in6 *, unsigned int rtableid); u_int32_t ip6_randomflowlabel(void); #endif /* _KERNEL */ |