From f86cf0c2191f1903cd83fa3541f053ba7c3102e9 Mon Sep 17 00:00:00 2001 From: Antonin Bas Date: Tue, 20 Feb 2024 14:43:42 -0800 Subject: [PATCH] Use 65000 MTU upper bound for interfaces in encap mode (#5997) OVS configures the MTU for tunnel ports to 65000. In some cases (e.g., Kind clusters), the MTU of the transport interface can be larger than that, and so can be the calculated MTU of antrea-gw0 and of Pod interfaces. When this happens, packets can be dropped. To handle this edge case (real clusters are unlikely to use that kind of MTU), we set an upper bound of 65000 for the calculated MTU. Note that setting the tunnel port's MTU to 65535, or even to the calculated MTU, is not an option, as it may not work on all systems. An alternative would be to find the MTU for the tunnel interface dynamically and use that as an upper bound, rather than rely on this hardcoded constant (65000). However, that constant has remained unchanged for 7 years, and finding the MTU dynamically would require re-organizing the Agent initialization code, as we currently caclulate the MTU before creating the OVS tunnel port. So the current solution seems lower risk. Even if the constant is changed in OVS, it should not have any real impact on Antrea. Fixes #5940 Signed-off-by: Antonin Bas --- pkg/agent/agent.go | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/pkg/agent/agent.go b/pkg/agent/agent.go index 2f1378ab76a..3134751673b 100644 --- a/pkg/agent/agent.go +++ b/pkg/agent/agent.go @@ -68,6 +68,14 @@ const ( roundNumKey = "roundNum" // round number key in externalIDs. initialRoundNum = 1 maxRetryForRoundNumSave = 5 + // On Linux, OVS configures the MTU for tunnel interfaces to 65000. + // See https://github.com/openvswitch/ovs/blame/3e666ba000b5eff58da8abb4e8c694ac3f7b08d6/lib/dpif-netlink-rtnl.c#L348-L360 + // There are some edge cases (e.g., Kind clusters) where the transport Node's MTU may be + // larger than that (e.g., 65535), and packets may be dropped. To account for this, we use + // 65000 as an upper bound for the MTU calculated in getInterfaceMTU, when encap is + // supported. For simplicity's sake, we also use this upper bound for Windows, even if it + // does not apply. + ovsTunnelMaxMTU = 65000 ) var ( @@ -1200,6 +1208,11 @@ func (i *Initializer) getInterfaceMTU(transportInterface *net.Interface) (int, e isIPv6 := i.nodeConfig.NodeIPv6Addr != nil mtu -= i.networkConfig.CalculateMTUDeduction(isIPv6) + if i.networkConfig.TrafficEncapMode.SupportsEncap() { + // See comment for ovsTunnelMaxMTU constant above. + mtu = min(mtu, ovsTunnelMaxMTU) + } + return mtu, nil }