diff --git a/tools/testing/selftests/net/pmtu.sh b/tools/testing/selftests/net/pmtu.sh index a369d616b390..33cba295ad45 100755 --- a/tools/testing/selftests/net/pmtu.sh +++ b/tools/testing/selftests/net/pmtu.sh @@ -26,6 +26,23 @@ # - pmtu_ipv6 # Same as pmtu_ipv4, except for locked PMTU tests, using IPv6 # +# - pmtu_ipv4_vxlan4_exception +# Set up the same network topology as pmtu_ipv4, create a VXLAN tunnel +# over IPv4 between A and B, routed via R1. On the link between R1 and B, +# set a MTU lower than the VXLAN MTU and the MTU on the link between A and +# R1. Send IPv4 packets, exceeding the MTU between R1 and B, over VXLAN +# from A to B and check that the PMTU exception is created with the right +# value on A +# +# - pmtu_ipv6_vxlan4_exception +# Same as pmtu_ipv4_vxlan4_exception, but send IPv6 packets from A to B +# +# - pmtu_ipv4_vxlan6_exception +# Same as pmtu_ipv4_vxlan4_exception, but use IPv6 transport from A to B +# +# - pmtu_ipv6_vxlan6_exception +# Same as pmtu_ipv4_vxlan6_exception, but send IPv6 packets from A to B +# # - pmtu_vti4_exception # Set up vti tunnel on top of veth, with xfrm states and policies, in two # namespaces with matching endpoints. Check that route exception is not @@ -72,6 +89,10 @@ which ping6 > /dev/null 2>&1 && ping6=$(which ping6) || ping6=$(which ping) tests=" pmtu_ipv4_exception ipv4: PMTU exceptions pmtu_ipv6_exception ipv6: PMTU exceptions + pmtu_ipv4_vxlan4_exception IPv4 over vxlan4: PMTU exceptions + pmtu_ipv6_vxlan4_exception IPv6 over vxlan4: PMTU exceptions + pmtu_ipv4_vxlan6_exception IPv4 over vxlan6: PMTU exceptions + pmtu_ipv6_vxlan6_exception IPv6 over vxlan6: PMTU exceptions pmtu_vti6_exception vti6: PMTU exceptions pmtu_vti4_exception vti4: PMTU exceptions pmtu_vti4_default_mtu vti4: default MTU assignment @@ -95,8 +116,8 @@ ns_r2="ip netns exec ${NS_R2}" # Addresses are: # - IPv4: PREFIX4.SEGMENT.ID (/24) # - IPv6: PREFIX6:SEGMENT::ID (/64) -prefix4="192.168" -prefix6="fd00" +prefix4="10.0" +prefix6="fc00" a_r1=1 a_r2=2 b_r1=3 @@ -129,12 +150,12 @@ veth6_a_addr="fd00:1::a" veth6_b_addr="fd00:1::b" veth6_mask="64" -vti4_a_addr="192.168.2.1" -vti4_b_addr="192.168.2.2" -vti4_mask="24" -vti6_a_addr="fd00:2::a" -vti6_b_addr="fd00:2::b" -vti6_mask="64" +tunnel4_a_addr="192.168.2.1" +tunnel4_b_addr="192.168.2.2" +tunnel4_mask="24" +tunnel6_a_addr="fd00:2::a" +tunnel6_b_addr="fd00:2::b" +tunnel6_mask="64" dummy6_0_addr="fc00:1000::0" dummy6_1_addr="fc00:1001::0" @@ -202,11 +223,39 @@ setup_vti() { } setup_vti4() { - setup_vti 4 ${veth4_a_addr} ${veth4_b_addr} ${vti4_a_addr} ${vti4_b_addr} ${vti4_mask} + setup_vti 4 ${veth4_a_addr} ${veth4_b_addr} ${tunnel4_a_addr} ${tunnel4_b_addr} ${tunnel4_mask} } setup_vti6() { - setup_vti 6 ${veth6_a_addr} ${veth6_b_addr} ${vti6_a_addr} ${vti6_b_addr} ${vti6_mask} + setup_vti 6 ${veth6_a_addr} ${veth6_b_addr} ${tunnel6_a_addr} ${tunnel6_b_addr} ${tunnel6_mask} +} + +setup_vxlan() { + a_addr="${1}" + b_addr="${2}" + opts="${3}" + + ${ns_a} ip link add vxlan_a type vxlan id 1 local ${a_addr} remote ${b_addr} ttl 64 dstport 4789 ${opts} || return 1 + ${ns_b} ip link add vxlan_b type vxlan id 1 local ${b_addr} remote ${a_addr} ttl 64 dstport 4789 ${opts} + + ${ns_a} ip addr add ${tunnel4_a_addr}/${tunnel4_mask} dev vxlan_a + ${ns_b} ip addr add ${tunnel4_b_addr}/${tunnel4_mask} dev vxlan_b + + ${ns_a} ip addr add ${tunnel6_a_addr}/${tunnel6_mask} dev vxlan_a + ${ns_b} ip addr add ${tunnel6_b_addr}/${tunnel6_mask} dev vxlan_b + + ${ns_a} ip link set vxlan_a up + ${ns_b} ip link set vxlan_b up + + sleep 1 +} + +setup_vxlan4() { + setup_vxlan ${prefix4}.${a_r1}.1 ${prefix4}.${b_r1}.1 "df set" +} + +setup_vxlan6() { + setup_vxlan ${prefix6}:${a_r1}::1 ${prefix6}:${b_r1}::1 "" } setup_xfrm() { @@ -465,6 +514,64 @@ test_pmtu_ipv6_exception() { test_pmtu_ipvX 6 } +test_pmtu_ipvX_over_vxlanY_exception() { + family=${1} + outer_family=${2} + ll_mtu=4000 + + if [ ${outer_family} -eq 4 ]; then + setup namespaces routing vxlan4 || return 2 + # IPv4 header UDP header VXLAN header Ethernet header + exp_mtu=$((${ll_mtu} - 20 - 8 - 8 - 14)) + else + setup namespaces routing vxlan6 || return 2 + # IPv6 header UDP header VXLAN header Ethernet header + exp_mtu=$((${ll_mtu} - 40 - 8 - 8 - 14)) + fi + + trace "${ns_a}" vxlan_a "${ns_b}" vxlan_b \ + "${ns_a}" veth_A-R1 "${ns_r1}" veth_R1-A \ + "${ns_b}" veth_B-R1 "${ns_r1}" veth_R1-B + + if [ ${family} -eq 4 ]; then + ping=ping + dst=${tunnel4_b_addr} + else + ping=${ping6} + dst=${tunnel6_b_addr} + fi + + # Create route exception by exceeding link layer MTU + mtu "${ns_a}" veth_A-R1 $((${ll_mtu} + 1000)) + mtu "${ns_r1}" veth_R1-A $((${ll_mtu} + 1000)) + mtu "${ns_b}" veth_B-R1 ${ll_mtu} + mtu "${ns_r1}" veth_R1-B ${ll_mtu} + + mtu "${ns_a}" vxlan_a $((${ll_mtu} + 1000)) + mtu "${ns_b}" vxlan_b $((${ll_mtu} + 1000)) + ${ns_a} ${ping} -q -M want -i 0.1 -w 2 -s $((${ll_mtu} + 500)) ${dst} > /dev/null + + # Check that exception was created + pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${dst})" + check_pmtu_value ${exp_mtu} "${pmtu}" "exceeding link layer MTU on VXLAN interface" +} + +test_pmtu_ipv4_vxlan4_exception() { + test_pmtu_ipvX_over_vxlanY_exception 4 4 +} + +test_pmtu_ipv6_vxlan4_exception() { + test_pmtu_ipvX_over_vxlanY_exception 6 4 +} + +test_pmtu_ipv4_vxlan6_exception() { + test_pmtu_ipvX_over_vxlanY_exception 4 6 +} + +test_pmtu_ipv6_vxlan6_exception() { + test_pmtu_ipvX_over_vxlanY_exception 6 6 +} + test_pmtu_vti4_exception() { setup namespaces veth vti4 xfrm4 || return 2 trace "${ns_a}" veth_a "${ns_b}" veth_b \ @@ -484,14 +591,14 @@ test_pmtu_vti4_exception() { # Send DF packet without exceeding link layer MTU, check that no # exception is created - ${ns_a} ping -q -M want -i 0.1 -w 2 -s ${ping_payload} ${vti4_b_addr} > /dev/null - pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${vti4_b_addr})" + ${ns_a} ping -q -M want -i 0.1 -w 2 -s ${ping_payload} ${tunnel4_b_addr} > /dev/null + pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${tunnel4_b_addr})" check_pmtu_value "" "${pmtu}" "sending packet smaller than PMTU (IP payload length ${esp_payload_rfc4106})" || return 1 # Now exceed link layer MTU by one byte, check that exception is created # with the right PMTU value - ${ns_a} ping -q -M want -i 0.1 -w 2 -s $((ping_payload + 1)) ${vti4_b_addr} > /dev/null - pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${vti4_b_addr})" + ${ns_a} ping -q -M want -i 0.1 -w 2 -s $((ping_payload + 1)) ${tunnel4_b_addr} > /dev/null + pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${tunnel4_b_addr})" check_pmtu_value "${esp_payload_rfc4106}" "${pmtu}" "exceeding PMTU (IP payload length $((esp_payload_rfc4106 + 1)))" } @@ -506,20 +613,20 @@ test_pmtu_vti6_exception() { mtu "${ns_b}" veth_b 4000 mtu "${ns_a}" vti6_a 5000 mtu "${ns_b}" vti6_b 5000 - ${ns_a} ${ping6} -q -i 0.1 -w 2 -s 60000 ${vti6_b_addr} > /dev/null + ${ns_a} ${ping6} -q -i 0.1 -w 2 -s 60000 ${tunnel6_b_addr} > /dev/null # Check that exception was created - pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${vti6_b_addr})" + pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${tunnel6_b_addr})" check_pmtu_value any "${pmtu}" "creating tunnel exceeding link layer MTU" || return 1 # Decrease tunnel MTU, check for PMTU decrease in route exception mtu "${ns_a}" vti6_a 3000 - pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${vti6_b_addr})" + pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${tunnel6_b_addr})" check_pmtu_value "3000" "${pmtu}" "decreasing tunnel MTU" || fail=1 # Increase tunnel MTU, check for PMTU increase in route exception mtu "${ns_a}" vti6_a 9000 - pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${vti6_b_addr})" + pmtu="$(route_get_dst_pmtu_from_exception "${ns_a}" ${tunnel6_b_addr})" check_pmtu_value "9000" "${pmtu}" "increasing tunnel MTU" || fail=1 return ${fail}