Configure ARP cache to react more quickly to MAC address changes
When an IP address was reused by a new container, other containers could experience delays of many seconds the first time they tried to talk to that new container before successful communication would occur. This delay came from three sources related to ARP cache behaviour: - The kernel would take a while to decide that an ARP mapping was stale due to lack of positive evidence (due to the base_reachable_time default of 30s) - Even once an ARP mapping was considered stale, the kernel would wait a few seconds before sending an ARP request, in the hope that a higher layer (e.g. TCP) would confirm the ARP entry (due to the delay_first_probe default of 5s) - When the kernel sent out an ARP request to update a stale entry, initial attempts would unicast the request to the old MAC address before resorting to broadcast (due to the ucast_solicit default of 3) This change reduces all these values, so that any delays are a few seconds. For most workloads, this should not greatly increase the amount of ARP traffic, because communication via TCP is often sufficient to confirm ARP entries. And one unicast ARP request is still sent just in case. Unfortunately, there's a fixed-but-only-recently bug in the kernel that means that changing base_reachable_time can take a while to take effect: <https://git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/commit/?id=4bf6980dd0328530783fd657c776e3719b421d30>. This means that a container will continue to use a long reachable_time delay for the first few minutes of its life.
This commit is contained in:
1 parent
e8ed9c707d
commit
11af544071
1 file changed
+14
-3
@@ -148,6 +148,12 @@ create_bridge() {
|
||||
fi
|
||||
|
||||
ip link set dev $BRIDGE up
|
||||
|
||||
# Configure the ARP cache parameters on the bridge interface for
|
||||
# the sake of 'weave expose'
|
||||
echo 5 >/proc/sys/net/ipv4/neigh/$BRIDGE/base_reachable_time
|
||||
echo 2 >/proc/sys/net/ipv4/neigh/$BRIDGE/delay_first_probe_time
|
||||
echo 1 >/proc/sys/net/ipv4/neigh/$BRIDGE/ucast_solicit
|
||||
}
|
||||
|
||||
destroy_bridge() {
|
||||
@@ -235,10 +241,15 @@ connect_container_to_bridge() {
|
||||
return 1
|
||||
fi
|
||||
|
||||
if ! ip netns exec $NETNS ip link set $GUEST_IFNAME name $CONTAINER_IFNAME ; then
|
||||
if ! ip netns exec $NETNS sh -c "\
|
||||
ip link set $GUEST_IFNAME name $CONTAINER_IFNAME &&
|
||||
echo 5 >/proc/sys/net/ipv4/neigh/$CONTAINER_IFNAME/base_reachable_time &&
|
||||
echo 2 >/proc/sys/net/ipv4/neigh/$CONTAINER_IFNAME/delay_first_probe_time &&
|
||||
echo 1 >/proc/sys/net/ipv4/neigh/$CONTAINER_IFNAME/ucast_solicit" ; then
|
||||
# failed after we assigned the veth to the container's
|
||||
# namespace
|
||||
ip netns exec $NETNS ip link del $GUEST_IFNAME type veth || true
|
||||
# namespace, and we don't know if it was renamed or not.
|
||||
ip netns exec $NETNS ip link del $GUEST_IFNAME type veth 2>/dev/null || true
|
||||
ip netns exec $NETNS ip link del $CONTAINER_IFNAME type veth 2>/dev/null || true
|
||||
return 1
|
||||
fi
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user