diff options
author | David Ahern <dsahern@gmail.com> | 2019-06-08 17:53:31 -0400 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2019-06-10 13:44:56 -0400 |
commit | 2d44234bf9ed45ba1b91e4bcc929ab15f8b6a901 (patch) | |
tree | c13043e078c4b9a7689e72e6d12b65b91cc09b7a /net/ipv6/route.c | |
parent | 49d5b8ef20d091d71a7fe019d71d0b2dd73a5b99 (diff) |
ipv6: Handle all fib6_nh in a nexthop in mtu updates
Use nexthop_for_each_fib6_nh to call fib6_nh_mtu_change for each
fib6_nh in a nexthop for rt6_mtu_change_route. For __ip6_rt_update_pmtu,
we need to find the nexthop that correlates to the device and gateway
in the rt6_info.
Signed-off-by: David Ahern <dsahern@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'net/ipv6/route.c')
-rw-r--r-- | net/ipv6/route.c | 29 |
1 files changed, 28 insertions, 1 deletions
diff --git a/net/ipv6/route.c b/net/ipv6/route.c index 715356e00f58..f287375fd0b2 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c | |||
@@ -2679,10 +2679,31 @@ static void __ip6_rt_update_pmtu(struct dst_entry *dst, const struct sock *sk, | |||
2679 | rcu_read_unlock(); | 2679 | rcu_read_unlock(); |
2680 | return; | 2680 | return; |
2681 | } | 2681 | } |
2682 | res.nh = res.f6i->fib6_nh; | ||
2683 | res.fib6_flags = res.f6i->fib6_flags; | 2682 | res.fib6_flags = res.f6i->fib6_flags; |
2684 | res.fib6_type = res.f6i->fib6_type; | 2683 | res.fib6_type = res.f6i->fib6_type; |
2685 | 2684 | ||
2685 | if (res.f6i->nh) { | ||
2686 | struct fib6_nh_match_arg arg = { | ||
2687 | .dev = dst->dev, | ||
2688 | .gw = &rt6->rt6i_gateway, | ||
2689 | }; | ||
2690 | |||
2691 | nexthop_for_each_fib6_nh(res.f6i->nh, | ||
2692 | fib6_nh_find_match, &arg); | ||
2693 | |||
2694 | /* fib6_info uses a nexthop that does not have fib6_nh | ||
2695 | * using the dst->dev + gw. Should be impossible. | ||
2696 | */ | ||
2697 | if (!arg.match) { | ||
2698 | rcu_read_unlock(); | ||
2699 | return; | ||
2700 | } | ||
2701 | |||
2702 | res.nh = arg.match; | ||
2703 | } else { | ||
2704 | res.nh = res.f6i->fib6_nh; | ||
2705 | } | ||
2706 | |||
2686 | nrt6 = ip6_rt_cache_alloc(&res, daddr, saddr); | 2707 | nrt6 = ip6_rt_cache_alloc(&res, daddr, saddr); |
2687 | if (nrt6) { | 2708 | if (nrt6) { |
2688 | rt6_do_update_pmtu(nrt6, mtu); | 2709 | rt6_do_update_pmtu(nrt6, mtu); |
@@ -4650,6 +4671,12 @@ static int rt6_mtu_change_route(struct fib6_info *f6i, void *p_arg) | |||
4650 | return 0; | 4671 | return 0; |
4651 | 4672 | ||
4652 | arg->f6i = f6i; | 4673 | arg->f6i = f6i; |
4674 | if (f6i->nh) { | ||
4675 | /* fib6_nh_mtu_change only returns 0, so this is safe */ | ||
4676 | return nexthop_for_each_fib6_nh(f6i->nh, fib6_nh_mtu_change, | ||
4677 | arg); | ||
4678 | } | ||
4679 | |||
4653 | return fib6_nh_mtu_change(f6i->fib6_nh, arg); | 4680 | return fib6_nh_mtu_change(f6i->fib6_nh, arg); |
4654 | } | 4681 | } |
4655 | 4682 | ||