aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorIdo Schimmel <idosch@mellanox.com>2017-12-20 05:28:25 -0500
committerDavid S. Miller <davem@davemloft.net>2017-12-21 11:51:06 -0500
commit58acfd714e6b02e8617448b431c2b64a2f1f0792 (patch)
tree2ad940bb6a9cd84c0a2286be2af6ba8f37d06bde
parent8b6ca2bf5a9b25369d7ec821ca051246558fbee0 (diff)
ipv6: Honor specified parameters in fibmatch lookup
Currently, parameters such as oif and source address are not taken into account during fibmatch lookup. Example (IPv4 for reference) before patch: $ ip -4 route show 192.0.2.0/24 dev dummy0 proto kernel scope link src 192.0.2.1 198.51.100.0/24 dev dummy1 proto kernel scope link src 198.51.100.1 $ ip -6 route show 2001:db8:1::/64 dev dummy0 proto kernel metric 256 pref medium 2001:db8:2::/64 dev dummy1 proto kernel metric 256 pref medium fe80::/64 dev dummy0 proto kernel metric 256 pref medium fe80::/64 dev dummy1 proto kernel metric 256 pref medium $ ip -4 route get fibmatch 192.0.2.2 oif dummy0 192.0.2.0/24 dev dummy0 proto kernel scope link src 192.0.2.1 $ ip -4 route get fibmatch 192.0.2.2 oif dummy1 RTNETLINK answers: No route to host $ ip -6 route get fibmatch 2001:db8:1::2 oif dummy0 2001:db8:1::/64 dev dummy0 proto kernel metric 256 pref medium $ ip -6 route get fibmatch 2001:db8:1::2 oif dummy1 2001:db8:1::/64 dev dummy0 proto kernel metric 256 pref medium After: $ ip -6 route get fibmatch 2001:db8:1::2 oif dummy0 2001:db8:1::/64 dev dummy0 proto kernel metric 256 pref medium $ ip -6 route get fibmatch 2001:db8:1::2 oif dummy1 RTNETLINK answers: Network is unreachable The problem stems from the fact that the necessary route lookup flags are not set based on these parameters. Instead of duplicating the same logic for fibmatch, we can simply resolve the original route from its copy and dump it instead. Fixes: 18c3a61c4264 ("net: ipv6: RTM_GETROUTE: return matched fib result when requested") Signed-off-by: Ido Schimmel <idosch@mellanox.com> Acked-by: David Ahern <dsahern@gmail.com> Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r--net/ipv6/route.c19
1 files changed, 11 insertions, 8 deletions
diff --git a/net/ipv6/route.c b/net/ipv6/route.c
index 2bc91c349273..0458b761f3c5 100644
--- a/net/ipv6/route.c
+++ b/net/ipv6/route.c
@@ -4298,19 +4298,13 @@ static int inet6_rtm_getroute(struct sk_buff *in_skb, struct nlmsghdr *nlh,
4298 if (!ipv6_addr_any(&fl6.saddr)) 4298 if (!ipv6_addr_any(&fl6.saddr))
4299 flags |= RT6_LOOKUP_F_HAS_SADDR; 4299 flags |= RT6_LOOKUP_F_HAS_SADDR;
4300 4300
4301 if (!fibmatch) 4301 dst = ip6_route_input_lookup(net, dev, &fl6, flags);
4302 dst = ip6_route_input_lookup(net, dev, &fl6, flags);
4303 else
4304 dst = ip6_route_lookup(net, &fl6, 0);
4305 4302
4306 rcu_read_unlock(); 4303 rcu_read_unlock();
4307 } else { 4304 } else {
4308 fl6.flowi6_oif = oif; 4305 fl6.flowi6_oif = oif;
4309 4306
4310 if (!fibmatch) 4307 dst = ip6_route_output(net, NULL, &fl6);
4311 dst = ip6_route_output(net, NULL, &fl6);
4312 else
4313 dst = ip6_route_lookup(net, &fl6, 0);
4314 } 4308 }
4315 4309
4316 4310
@@ -4327,6 +4321,15 @@ static int inet6_rtm_getroute(struct sk_buff *in_skb, struct nlmsghdr *nlh,
4327 goto errout; 4321 goto errout;
4328 } 4322 }
4329 4323
4324 if (fibmatch && rt->dst.from) {
4325 struct rt6_info *ort = container_of(rt->dst.from,
4326 struct rt6_info, dst);
4327
4328 dst_hold(&ort->dst);
4329 ip6_rt_put(rt);
4330 rt = ort;
4331 }
4332
4330 skb = alloc_skb(NLMSG_GOODSIZE, GFP_KERNEL); 4333 skb = alloc_skb(NLMSG_GOODSIZE, GFP_KERNEL);
4331 if (!skb) { 4334 if (!skb) {
4332 ip6_rt_put(rt); 4335 ip6_rt_put(rt);