net/ipv6: Fix route leaking between VRFs
Subsystems (3)
PATCH 1/1 net/ipv6: Fix route leaking between VRFs
Donald reported that IPv6 route leaking between VRFs is not working. The root cause is the strict argument in the call to rt6_lookup when validating the nexthop spec.
ip6_route_check_nh validates the gateway and device (if given) of a route spec. It in turn could call rt6_lookup (e.g., lookup in a given table did not succeed so it falls back to a full lookup) and if so sets the strict argument to 1. That means if the egress device is given, the route lookup needs to return a result with the same device. This strict requirement does not work with VRFs (IPv4 or IPv6) because the oif in the flow struct is overridden with the index of the VRF device to trigger a match on the l3mdev rule and force the lookup to its table.
The right long term solution is to add an l3mdev index to the flow struct such that the oif is not overridden. That solution will not backport well, so this patch aims for a simpler solution to relax the strict argument if the route spec device is an l3mdev slave. As done in other places, use the FLOWI_FLAG_SKIP_NH_OIF to know that the RT6_LOOKUP_F_IFACE flag needs to be removed.
--- net/ipv6/route.c | 3 +++ 1 file changed, 3 insertions(+)
net/ipv6/route.c +3 -0
@@ -919,6 +919,9 @@ static struct rt6_info *ip6_pol_route_lookup(struct net *net,struct rt6_info *rt, *rt_cache;struct fib6_node *fn; +if (fl6->flowi6_flags &FLOWI_FLAG_SKIP_NH_OIF ) + flags &= ~RT6_LOOKUP_F_IFACE ; +rcu_read_lock (); fn =fib6_lookup (&table->tb6_root, &fl6->daddr, &fl6->saddr); restart:
Signature · 1 line
2.11.0
Quoted 13 lines · David Ahern
Donald reported that IPv6 route leaking between VRFs is not working. The root cause is the strict argument in the call to
rt6_lookupwhen validating the nexthop spec.
ip6_route_check_nhvalidates the gateway and device (if given) of a route spec. It in turn could callrt6_lookup(e.g., lookup in a given table did not succeed so it falls back to a full lookup) and if so sets the strict argument to 1. That means if the egress device is given, the route lookup needs to return a result with the same device. This strict requirement does not work with VRFs (IPv4 or IPv6) because the oif in the flow struct is overridden with the index of the VRF device to trigger a match on the l3mdev rule and force the lookup to its table.
Quoted 7 lines
The right long term solution is to add an l3mdev index to the flow struct such that the oif is not overridden. That solution will not backport well, so this patch aims for a simpler solution to relax the strict argument if the route spec device is an l3mdev slave. As done in other places, use the
FLOWI_FLAG_SKIP_NH_OIFto know that theRT6_LOOKUP_F_IFACEflag needs to be removed.
Forgot the fixes tag:
Dave: I can resend if needed. Key backports are to 4.14 and 4.9. Those are the only LTS releases affected.
Quoted 21 lines
Reported-by Donald Sharp <[email protected]>Signed-off-by David Ahern <[email protected]>--- net/ipv6/route.c | 3 +++ 1 file changed, 3 insertions(+)net/ipv6/route.c +3
-0@@ -919,6 +919,9 @@ static struct rt6_info *ip6_pol_route_lookup(struct net *net,struct rt6_info *rt, *rt_cache;struct fib6_node *fn; +if (fl6->flowi6_flags &FLOWI_FLAG_SKIP_NH_OIF ) + flags &= ~RT6_LOOKUP_F_IFACE ; +rcu_read_lock (); fn =fib6_lookup (&table->tb6_root, &fl6->daddr, &fl6->saddr); restart:
From: David Ahern <[email protected]>
Date: Thu, 29 Mar 2018 17:44:57 -0700
Quoted 20 lines
Donald reported that IPv6 route leaking between VRFs is not working. The root cause is the strict argument in the call to
rt6_lookupwhen validating the nexthop spec.
ip6_route_check_nhvalidates the gateway and device (if given) of a route spec. It in turn could callrt6_lookup(e.g., lookup in a given table did not succeed so it falls back to a full lookup) and if so sets the strict argument to 1. That means if the egress device is given, the route lookup needs to return a result with the same device. This strict requirement does not work with VRFs (IPv4 or IPv6) because the oif in the flow struct is overridden with the index of the VRF device to trigger a match on the l3mdev rule and force the lookup to its table.The right long term solution is to add an l3mdev index to the flow struct such that the oif is not overridden. That solution will not backport well, so this patch aims for a simpler solution to relax the strict argument if the route spec device is an l3mdev slave. As done in other places, use the
FLOWI_FLAG_SKIP_NH_OIFto know that theRT6_LOOKUP_F_IFACEflag needs to be removed.
Quoted 2 lines
Reported-by Donald Sharp <[email protected]>Signed-off-by David Ahern <[email protected]>
Applied, with fixes tag added, and queued up for -stable.
Thanks.