340 lines · bash
1#!/bin/bash2# SPDX-License-Identifier: GPL-2.03#4# Test VxLAN flooding. The device stores flood records in a singly linked list5# where each record stores up to four IPv6 addresses of remote VTEPs. The test6# verifies that packets are correctly flooded in various cases such as deletion7# of a record in the middle of the list.8#9# +-----------------------+10# | H1 (vrf) |11# | + $h1 |12# | | 2001:db8:1::1/64 |13# +----|------------------+14# |15# +----|----------------------------------------------------------------------+16# | SW | |17# | +--|--------------------------------------------------------------------+ |18# | | + $swp1 BR0 (802.1d) | |19# | | | |20# | | + vxlan0 (vxlan) | |21# | | local 2001:db8:2::1 | |22# | | remote 2001:db8:2::{2..17} | |23# | | id 10 dstport 4789 | |24# | +-----------------------------------------------------------------------+ |25# | |26# | 2001:db8:2::0/64 via 2001:db8:3::2 |27# | |28# | + $rp1 |29# | | 2001:db8:3::1/64 |30# +----|----------------------------------------------------------------------+31# |32# +----|--------------------------------------------------------+33# | | R2 (vrf) |34# | + $rp2 |35# | 2001:db8:3::2/64 |36# | |37# +-------------------------------------------------------------+38 39lib_dir=$(dirname $0)/../../../../net/forwarding40 41ALL_TESTS="flooding_test"42NUM_NETIFS=443source $lib_dir/tc_common.sh44source $lib_dir/lib.sh45 46h1_create()47{48 simple_if_init $h1 2001:db8:1::1/6449}50 51h1_destroy()52{53 simple_if_fini $h1 2001:db8:1::1/6454}55 56switch_create()57{58 # Make sure the bridge uses the MAC address of the local port and59 # not that of the VxLAN's device60 ip link add dev br0 type bridge mcast_snooping 061 ip link set dev br0 address $(mac_get $swp1)62 63 ip link add name vxlan0 type vxlan id 10 nolearning \64 udp6zerocsumrx udp6zerocsumtx ttl 20 tos inherit \65 local 2001:db8:2::1 dstport 478966 67 ip address add 2001:db8:2::1/128 dev lo68 69 ip link set dev $swp1 master br070 ip link set dev vxlan0 master br071 72 ip link set dev br0 up73 ip link set dev $swp1 up74 ip link set dev vxlan0 up75}76 77switch_destroy()78{79 ip link set dev vxlan0 down80 ip link set dev $swp1 down81 ip link set dev br0 down82 83 ip link set dev vxlan0 nomaster84 ip link set dev $swp1 nomaster85 86 ip address del 2001:db8:2::1/128 dev lo87 88 ip link del dev vxlan089 90 ip link del dev br091}92 93router1_create()94{95 # This router is in the default VRF, where the VxLAN device is96 # performing the L3 lookup97 ip link set dev $rp1 up98 ip address add 2001:db8:3::1/64 dev $rp199 ip route add 2001:db8:2::0/64 via 2001:db8:3::2100}101 102router1_destroy()103{104 ip route del 2001:db8:2::0/64 via 2001:db8:3::2105 ip address del 2001:db8:3::1/64 dev $rp1106 ip link set dev $rp1 down107}108 109router2_create()110{111 # This router is not in the default VRF, so use simple_if_init()112 simple_if_init $rp2 2001:db8:3::2/64113}114 115router2_destroy()116{117 simple_if_fini $rp2 2001:db8:3::2/64118}119 120setup_prepare()121{122 h1=${NETIFS[p1]}123 swp1=${NETIFS[p2]}124 125 rp1=${NETIFS[p3]}126 rp2=${NETIFS[p4]}127 128 vrf_prepare129 130 h1_create131 132 switch_create133 134 router1_create135 router2_create136 137 forwarding_enable138}139 140cleanup()141{142 pre_cleanup143 144 forwarding_restore145 146 router2_destroy147 router1_destroy148 149 switch_destroy150 151 h1_destroy152 153 vrf_cleanup154}155 156flooding_remotes_add()157{158 local num_remotes=$1159 local lsb160 local i161 162 # Prevent unwanted packets from entering the bridge and interfering163 # with the test.164 tc qdisc add dev br0 clsact165 tc filter add dev br0 egress protocol all pref 1 handle 1 \166 matchall skip_hw action drop167 tc qdisc add dev $h1 clsact168 tc filter add dev $h1 egress protocol all pref 1 handle 1 \169 flower skip_hw dst_mac de:ad:be:ef:13:37 action pass170 tc filter add dev $h1 egress protocol all pref 2 handle 2 \171 matchall skip_hw action drop172 173 for i in $(eval echo {1..$num_remotes}); do174 lsb=$((i + 1))175 176 bridge fdb append 00:00:00:00:00:00 dev vxlan0 self \177 dst 2001:db8:2::$lsb178 done179}180 181flooding_filters_add()182{183 local num_remotes=$1184 local lsb185 local i186 187 tc qdisc add dev $rp2 clsact188 189 for i in $(eval echo {1..$num_remotes}); do190 lsb=$((i + 1))191 192 tc filter add dev $rp2 ingress protocol ipv6 pref $i handle $i \193 flower ip_proto udp dst_ip 2001:db8:2::$lsb \194 dst_port 4789 skip_sw action drop195 done196}197 198flooding_filters_del()199{200 local num_remotes=$1201 local i202 203 for i in $(eval echo {1..$num_remotes}); do204 tc filter del dev $rp2 ingress protocol ipv6 pref $i \205 handle $i flower206 done207 208 tc qdisc del dev $rp2 clsact209 210 tc filter del dev $h1 egress protocol all pref 2 handle 2 matchall211 tc filter del dev $h1 egress protocol all pref 1 handle 1 flower212 tc qdisc del dev $h1 clsact213 tc filter del dev br0 egress protocol all pref 1 handle 1 matchall214 tc qdisc del dev br0 clsact215}216 217flooding_check_packets()218{219 local packets=("$@")220 local num_remotes=${#packets[@]}221 local i222 223 for i in $(eval echo {1..$num_remotes}); do224 tc_check_packets "dev $rp2 ingress" $i ${packets[i - 1]}225 check_err $? "remote $i - did not get expected number of packets"226 done227}228 229flooding_test()230{231 # Use 16 remote VTEPs that will be stored in 4 records. The array232 # 'packets' will store how many packets are expected to be received233 # by each remote VTEP at each stage of the test234 declare -a packets=(1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1)235 local num_remotes=16236 237 RET=0238 239 # Add FDB entries for remote VTEPs and corresponding tc filters on the240 # ingress of the nexthop router. These filters will count how many241 # packets were flooded to each remote VTEP242 flooding_remotes_add $num_remotes243 flooding_filters_add $num_remotes244 245 # Send one packet and make sure it is flooded to all the remote VTEPs246 $MZ $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1247 flooding_check_packets "${packets[@]}"248 log_test "flood after 1 packet"249 250 # Delete the third record which corresponds to VTEPs with LSB 10..13251 # and check that packet is flooded correctly when we remove a record252 # from the middle of the list253 RET=0254 255 packets=(2 2 2 2 2 2 2 2 1 1 1 1 2 2 2 2)256 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::10257 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::11258 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::12259 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::13260 261 $MZ $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1262 flooding_check_packets "${packets[@]}"263 log_test "flood after 2 packets"264 265 # Delete the first record and make sure the packet is flooded correctly266 RET=0267 268 packets=(2 2 2 2 3 3 3 3 1 1 1 1 3 3 3 3)269 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::2270 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::3271 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::4272 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::5273 274 $MZ $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1275 flooding_check_packets "${packets[@]}"276 log_test "flood after 3 packets"277 278 # Delete the last record and make sure the packet is flooded correctly279 RET=0280 281 packets=(2 2 2 2 4 4 4 4 1 1 1 1 3 3 3 3)282 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::14283 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::15284 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::16285 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::17286 287 $MZ -6 $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1288 flooding_check_packets "${packets[@]}"289 log_test "flood after 4 packets"290 291 # Delete the last record, one entry at a time and make sure single292 # entries are correctly removed293 RET=0294 295 packets=(2 2 2 2 4 5 5 5 1 1 1 1 3 3 3 3)296 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::6297 298 $MZ -6 $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1299 flooding_check_packets "${packets[@]}"300 log_test "flood after 5 packets"301 302 RET=0303 304 packets=(2 2 2 2 4 5 6 6 1 1 1 1 3 3 3 3)305 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::7306 307 $MZ -6 $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1308 flooding_check_packets "${packets[@]}"309 log_test "flood after 6 packets"310 311 RET=0312 313 packets=(2 2 2 2 4 5 6 7 1 1 1 1 3 3 3 3)314 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::8315 316 $MZ -6 $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1317 flooding_check_packets "${packets[@]}"318 log_test "flood after 7 packets"319 320 RET=0321 322 packets=(2 2 2 2 4 5 6 7 1 1 1 1 3 3 3 3)323 bridge fdb del 00:00:00:00:00:00 dev vxlan0 self dst 2001:db8:2::9324 325 $MZ -6 $h1 -q -p 64 -b de:ad:be:ef:13:37 -t ip -c 1326 flooding_check_packets "${packets[@]}"327 log_test "flood after 8 packets"328 329 flooding_filters_del $num_remotes330}331 332trap cleanup EXIT333 334setup_prepare335setup_wait336 337tests_run338 339exit $EXIT_STATUS340