@@ -981,6 +981,7 @@ int __ip_tunnel_change_mtu(struct net_device *dev, int new_mtu, bool strict)
struct ip_tunnel *tunnel = netdev_priv(dev);
int t_hlen = tunnel->hlen + sizeof(struct iphdr);
int max_mtu = IP_MAX_MTU - dev->hard_header_len - t_hlen;
+ int best_mtu = ip_tunnel_bind_dev(dev);
if (new_mtu < ETH_MIN_MTU)
return -EINVAL;
@@ -993,6 +994,7 @@ int __ip_tunnel_change_mtu(struct net_device *dev, int new_mtu, bool strict)
}
dev->mtu = new_mtu;
+ __vlan_constrain_mtu(dev, best_mtu);
return 0;
}
EXPORT_SYMBOL_GPL(__ip_tunnel_change_mtu);
@@ -1131,6 +1131,8 @@ static void ip6gre_tnl_link_config_route(struct ip6_tnl *t, int set_mtu,
if (dev->mtu < IPV6_MIN_MTU)
dev->mtu = IPV6_MIN_MTU;
+
+ dev->priv_flags |= IFF_NO_VLAN_ROOM;
}
}
ip6_rt_put(rt);
@@ -1801,7 +1803,7 @@ static int ip6gre_tap_init(struct net_device *dev)
if (ret)
return ret;
- dev->priv_flags |= IFF_LIVE_ADDR_CHANGE;
+ dev->priv_flags |= IFF_LIVE_ADDR_CHANGE | IFF_NO_VLAN_ROOM;
return 0;
}
Constrain the MTU of upper VLAN devices if the MTU of the GRE device is configured to its default optimal size, which does not leave space for a nested VLAN tag without causing fragmentation. If the underlying lower device is not known, then the worst case is assumed and any upper VLAN devices will always be adjusted to accommodate the VLAN tag. For IPv4 tunnels, the changes to support this are made in the generic ip_tunnel_change_mtu() handler and so IFF_NO_VLAN_ROOM is consequently maintained for all tunnel devices that leverage this implementation. GRE is, however, the only one of these implementations that might use an L2 overlay. At present nothing prevents VLAN devices being layered above raw IP tunnel devices, which does not make sense. This limitation will be addressed by a later patch in this series. IPv6 GRE is dependent on PMTU discovery, but the MTU of nested VLANs still need to be constrained, because non-VLAN packets will share the same path MTU. Signed-off-by: Edwin Peer <edwin.peer@broadcom.com> --- net/ipv4/ip_tunnel.c | 2 ++ net/ipv6/ip6_gre.c | 4 +++- 2 files changed, 5 insertions(+), 1 deletion(-)