diff options
Diffstat (limited to 'net/ipv4/route.c')
-rw-r--r-- | net/ipv4/route.c | 36 |
1 files changed, 21 insertions, 15 deletions
diff --git a/net/ipv4/route.c b/net/ipv4/route.c index b6a6f18c3dd1..7dcce724c78b 100644 --- a/net/ipv4/route.c +++ b/net/ipv4/route.c | |||
@@ -635,6 +635,7 @@ static void fill_route_from_fnhe(struct rtable *rt, struct fib_nh_exception *fnh | |||
635 | 635 | ||
636 | if (fnhe->fnhe_gw) { | 636 | if (fnhe->fnhe_gw) { |
637 | rt->rt_flags |= RTCF_REDIRECTED; | 637 | rt->rt_flags |= RTCF_REDIRECTED; |
638 | rt->rt_uses_gateway = 1; | ||
638 | rt->rt_gw_family = AF_INET; | 639 | rt->rt_gw_family = AF_INET; |
639 | rt->rt_gw4 = fnhe->fnhe_gw; | 640 | rt->rt_gw4 = fnhe->fnhe_gw; |
640 | } | 641 | } |
@@ -1313,7 +1314,7 @@ static unsigned int ipv4_mtu(const struct dst_entry *dst) | |||
1313 | mtu = READ_ONCE(dst->dev->mtu); | 1314 | mtu = READ_ONCE(dst->dev->mtu); |
1314 | 1315 | ||
1315 | if (unlikely(ip_mtu_locked(dst))) { | 1316 | if (unlikely(ip_mtu_locked(dst))) { |
1316 | if (rt->rt_gw_family && mtu > 576) | 1317 | if (rt->rt_uses_gateway && mtu > 576) |
1317 | mtu = 576; | 1318 | mtu = 576; |
1318 | } | 1319 | } |
1319 | 1320 | ||
@@ -1569,6 +1570,7 @@ static void rt_set_nexthop(struct rtable *rt, __be32 daddr, | |||
1569 | struct fib_nh_common *nhc = FIB_RES_NHC(*res); | 1570 | struct fib_nh_common *nhc = FIB_RES_NHC(*res); |
1570 | 1571 | ||
1571 | if (nhc->nhc_gw_family && nhc->nhc_scope == RT_SCOPE_LINK) { | 1572 | if (nhc->nhc_gw_family && nhc->nhc_scope == RT_SCOPE_LINK) { |
1573 | rt->rt_uses_gateway = 1; | ||
1572 | rt->rt_gw_family = nhc->nhc_gw_family; | 1574 | rt->rt_gw_family = nhc->nhc_gw_family; |
1573 | /* only INET and INET6 are supported */ | 1575 | /* only INET and INET6 are supported */ |
1574 | if (likely(nhc->nhc_gw_family == AF_INET)) | 1576 | if (likely(nhc->nhc_gw_family == AF_INET)) |
@@ -1634,6 +1636,7 @@ struct rtable *rt_dst_alloc(struct net_device *dev, | |||
1634 | rt->rt_iif = 0; | 1636 | rt->rt_iif = 0; |
1635 | rt->rt_pmtu = 0; | 1637 | rt->rt_pmtu = 0; |
1636 | rt->rt_mtu_locked = 0; | 1638 | rt->rt_mtu_locked = 0; |
1639 | rt->rt_uses_gateway = 0; | ||
1637 | rt->rt_gw_family = 0; | 1640 | rt->rt_gw_family = 0; |
1638 | rt->rt_gw4 = 0; | 1641 | rt->rt_gw4 = 0; |
1639 | INIT_LIST_HEAD(&rt->rt_uncached); | 1642 | INIT_LIST_HEAD(&rt->rt_uncached); |
@@ -2694,6 +2697,7 @@ struct dst_entry *ipv4_blackhole_route(struct net *net, struct dst_entry *dst_or | |||
2694 | rt->rt_genid = rt_genid_ipv4(net); | 2697 | rt->rt_genid = rt_genid_ipv4(net); |
2695 | rt->rt_flags = ort->rt_flags; | 2698 | rt->rt_flags = ort->rt_flags; |
2696 | rt->rt_type = ort->rt_type; | 2699 | rt->rt_type = ort->rt_type; |
2700 | rt->rt_uses_gateway = ort->rt_uses_gateway; | ||
2697 | rt->rt_gw_family = ort->rt_gw_family; | 2701 | rt->rt_gw_family = ort->rt_gw_family; |
2698 | if (rt->rt_gw_family == AF_INET) | 2702 | if (rt->rt_gw_family == AF_INET) |
2699 | rt->rt_gw4 = ort->rt_gw4; | 2703 | rt->rt_gw4 = ort->rt_gw4; |
@@ -2778,21 +2782,23 @@ static int rt_fill_info(struct net *net, __be32 dst, __be32 src, | |||
2778 | if (nla_put_in_addr(skb, RTA_PREFSRC, fl4->saddr)) | 2782 | if (nla_put_in_addr(skb, RTA_PREFSRC, fl4->saddr)) |
2779 | goto nla_put_failure; | 2783 | goto nla_put_failure; |
2780 | } | 2784 | } |
2781 | if (rt->rt_gw_family == AF_INET && | 2785 | if (rt->rt_uses_gateway) { |
2782 | nla_put_in_addr(skb, RTA_GATEWAY, rt->rt_gw4)) { | 2786 | if (rt->rt_gw_family == AF_INET && |
2783 | goto nla_put_failure; | 2787 | nla_put_in_addr(skb, RTA_GATEWAY, rt->rt_gw4)) { |
2784 | } else if (rt->rt_gw_family == AF_INET6) { | ||
2785 | int alen = sizeof(struct in6_addr); | ||
2786 | struct nlattr *nla; | ||
2787 | struct rtvia *via; | ||
2788 | |||
2789 | nla = nla_reserve(skb, RTA_VIA, alen + 2); | ||
2790 | if (!nla) | ||
2791 | goto nla_put_failure; | 2788 | goto nla_put_failure; |
2792 | 2789 | } else if (rt->rt_gw_family == AF_INET6) { | |
2793 | via = nla_data(nla); | 2790 | int alen = sizeof(struct in6_addr); |
2794 | via->rtvia_family = AF_INET6; | 2791 | struct nlattr *nla; |
2795 | memcpy(via->rtvia_addr, &rt->rt_gw6, alen); | 2792 | struct rtvia *via; |
2793 | |||
2794 | nla = nla_reserve(skb, RTA_VIA, alen + 2); | ||
2795 | if (!nla) | ||
2796 | goto nla_put_failure; | ||
2797 | |||
2798 | via = nla_data(nla); | ||
2799 | via->rtvia_family = AF_INET6; | ||
2800 | memcpy(via->rtvia_addr, &rt->rt_gw6, alen); | ||
2801 | } | ||
2796 | } | 2802 | } |
2797 | 2803 | ||
2798 | expires = rt->dst.expires; | 2804 | expires = rt->dst.expires; |