| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972 |
- #!/bin/bash
- # SPDX-License-Identifier: GPL-2.0
- #
- # This test is for checking bridge neighbor suppression functionality. The
- # topology consists of two bridges (VTEPs) connected using VXLAN. A single
- # host is connected to each bridge over multiple VLANs. The test checks that
- # ARP/NS messages from the first host are suppressed on the VXLAN port when
- # should.
- #
- # +-----------------------+ +------------------------+
- # | h1 | | h2 |
- # | | | |
- # | + eth0.10 | | + eth0.10 |
- # | | 192.0.2.1/28 | | | 192.0.2.2/28 |
- # | | 2001:db8:1::1/64 | | | 2001:db8:1::2/64 |
- # | | | | | |
- # | | + eth0.20 | | | + eth0.20 |
- # | \ | 192.0.2.17/28 | | \ | 192.0.2.18/28 |
- # | \ | 2001:db8:2::1/64 | | \ | 2001:db8:2::2/64 |
- # | \| | | \| |
- # | + eth0 | | + eth0 |
- # +----|------------------+ +----|-------------------+
- # | |
- # | |
- # +----|-------------------------------+ +----|-------------------------------+
- # | + swp1 + vx0 | | + swp1 + vx0 |
- # | | | | | | | |
- # | | br0 | | | | | |
- # | +------------+-----------+ | | +------------+-----------+ |
- # | | | | | |
- # | | | | | |
- # | +---+---+ | | +---+---+ |
- # | | | | | | | |
- # | | | | | | | |
- # | + + | | + + |
- # | br0.10 br0.20 | | br0.10 br0.20 |
- # | | | |
- # | 192.0.2.33 | | 192.0.2.34 |
- # | + lo | | + lo |
- # | | | |
- # | | | |
- # | 192.0.2.49/28 | | 192.0.2.50/28 |
- # | veth0 +-------+ veth0 |
- # | | | |
- # | sw1 | | sw2 |
- # +------------------------------------+ +------------------------------------+
- source lib.sh
- ret=0
- # All tests in this script. Can be overridden with -t option.
- TESTS="
- neigh_suppress_arp
- neigh_suppress_uc_arp
- neigh_suppress_ns
- neigh_suppress_uc_ns
- neigh_vlan_suppress_arp
- neigh_vlan_suppress_ns
- "
- VERBOSE=0
- PAUSE_ON_FAIL=no
- PAUSE=no
- ################################################################################
- # Utilities
- log_test()
- {
- local rc=$1
- local expected=$2
- local msg="$3"
- if [ ${rc} -eq ${expected} ]; then
- printf "TEST: %-60s [ OK ]\n" "${msg}"
- nsuccess=$((nsuccess+1))
- else
- ret=1
- nfail=$((nfail+1))
- printf "TEST: %-60s [FAIL]\n" "${msg}"
- if [ "$VERBOSE" = "1" ]; then
- echo " rc=$rc, expected $expected"
- fi
- if [ "${PAUSE_ON_FAIL}" = "yes" ]; then
- echo
- echo "hit enter to continue, 'q' to quit"
- read a
- [ "$a" = "q" ] && exit 1
- fi
- fi
- if [ "${PAUSE}" = "yes" ]; then
- echo
- echo "hit enter to continue, 'q' to quit"
- read a
- [ "$a" = "q" ] && exit 1
- fi
- [ "$VERBOSE" = "1" ] && echo
- }
- run_cmd()
- {
- local cmd="$1"
- local out
- local stderr="2>/dev/null"
- if [ "$VERBOSE" = "1" ]; then
- printf "COMMAND: $cmd\n"
- stderr=
- fi
- out=$(eval $cmd $stderr)
- rc=$?
- if [ "$VERBOSE" = "1" -a -n "$out" ]; then
- echo " $out"
- fi
- return $rc
- }
- tc_check_packets()
- {
- local ns=$1; shift
- local id=$1; shift
- local handle=$1; shift
- local count=$1; shift
- local pkts
- sleep 0.1
- pkts=$(tc -n $ns -j -s filter show $id \
- | jq ".[] | select(.options.handle == $handle) | \
- .options.actions[0].stats.packets")
- [[ $pkts == $count ]]
- }
- ################################################################################
- # Setup
- setup_topo_ns()
- {
- local ns=$1; shift
- ip netns exec $ns sysctl -qw net.ipv6.conf.all.keep_addr_on_down=1
- ip netns exec $ns sysctl -qw net.ipv6.conf.default.ignore_routes_with_linkdown=1
- ip netns exec $ns sysctl -qw net.ipv6.conf.all.accept_dad=0
- ip netns exec $ns sysctl -qw net.ipv6.conf.default.accept_dad=0
- }
- setup_topo()
- {
- local ns
- setup_ns h1 h2 sw1 sw2
- for ns in $h1 $h2 $sw1 $sw2; do
- setup_topo_ns $ns
- done
- ip -n $h1 link add name eth0 type veth peer name swp1 netns $sw1
- ip -n $sw1 link add name veth0 type veth peer name veth0 netns $sw2
- ip -n $h2 link add name eth0 type veth peer name swp1 netns $sw2
- }
- setup_host_common()
- {
- local ns=$1; shift
- local v4addr1=$1; shift
- local v4addr2=$1; shift
- local v6addr1=$1; shift
- local v6addr2=$1; shift
- ip -n $ns link set dev eth0 up
- ip -n $ns link add link eth0 name eth0.10 up type vlan id 10
- ip -n $ns link add link eth0 name eth0.20 up type vlan id 20
- ip -n $ns address add $v4addr1 dev eth0.10
- ip -n $ns address add $v4addr2 dev eth0.20
- ip -n $ns address add $v6addr1 dev eth0.10
- ip -n $ns address add $v6addr2 dev eth0.20
- }
- setup_h1()
- {
- local ns=$h1
- local v4addr1=192.0.2.1/28
- local v4addr2=192.0.2.17/28
- local v6addr1=2001:db8:1::1/64
- local v6addr2=2001:db8:2::1/64
- setup_host_common $ns $v4addr1 $v4addr2 $v6addr1 $v6addr2
- }
- setup_h2()
- {
- local ns=$h2
- local v4addr1=192.0.2.2/28
- local v4addr2=192.0.2.18/28
- local v6addr1=2001:db8:1::2/64
- local v6addr2=2001:db8:2::2/64
- setup_host_common $ns $v4addr1 $v4addr2 $v6addr1 $v6addr2
- }
- setup_sw_common()
- {
- local ns=$1; shift
- local local_addr=$1; shift
- local remote_addr=$1; shift
- local veth_addr=$1; shift
- local gw_addr=$1; shift
- ip -n $ns address add $local_addr/32 dev lo
- ip -n $ns link set dev veth0 up
- ip -n $ns address add $veth_addr/28 dev veth0
- ip -n $ns route add default via $gw_addr
- ip -n $ns link add name br0 up type bridge vlan_filtering 1 \
- vlan_default_pvid 0 mcast_snooping 0
- ip -n $ns link add link br0 name br0.10 up type vlan id 10
- bridge -n $ns vlan add vid 10 dev br0 self
- ip -n $ns link add link br0 name br0.20 up type vlan id 20
- bridge -n $ns vlan add vid 20 dev br0 self
- ip -n $ns link set dev swp1 up master br0
- bridge -n $ns vlan add vid 10 dev swp1
- bridge -n $ns vlan add vid 20 dev swp1
- ip -n $ns link add name vx0 up master br0 type vxlan \
- local $local_addr dstport 4789 nolearning external
- bridge -n $ns fdb add 00:00:00:00:00:00 dev vx0 self static \
- dst $remote_addr src_vni 10010
- bridge -n $ns fdb add 00:00:00:00:00:00 dev vx0 self static \
- dst $remote_addr src_vni 10020
- bridge -n $ns link set dev vx0 vlan_tunnel on learning off
- bridge -n $ns vlan add vid 10 dev vx0
- bridge -n $ns vlan add vid 10 dev vx0 tunnel_info id 10010
- bridge -n $ns vlan add vid 20 dev vx0
- bridge -n $ns vlan add vid 20 dev vx0 tunnel_info id 10020
- }
- setup_sw1()
- {
- local ns=$sw1
- local local_addr=192.0.2.33
- local remote_addr=192.0.2.34
- local veth_addr=192.0.2.49
- local gw_addr=192.0.2.50
- setup_sw_common $ns $local_addr $remote_addr $veth_addr $gw_addr
- }
- setup_sw2()
- {
- local ns=$sw2
- local local_addr=192.0.2.34
- local remote_addr=192.0.2.33
- local veth_addr=192.0.2.50
- local gw_addr=192.0.2.49
- setup_sw_common $ns $local_addr $remote_addr $veth_addr $gw_addr
- }
- setup()
- {
- set -e
- setup_topo
- setup_h1
- setup_h2
- setup_sw1
- setup_sw2
- sleep 5
- set +e
- }
- cleanup()
- {
- cleanup_ns $h1 $h2 $sw1 $sw2
- }
- ################################################################################
- # Tests
- neigh_suppress_arp_common()
- {
- local vid=$1; shift
- local sip=$1; shift
- local tip=$1; shift
- local h2_mac
- echo
- echo "Per-port ARP suppression - VLAN $vid"
- echo "----------------------------------"
- run_cmd "tc -n $sw1 qdisc replace dev vx0 clsact"
- run_cmd "tc -n $sw1 filter replace dev vx0 egress pref 1 handle 101 proto 0x0806 flower indev swp1 arp_tip $tip arp_sip $sip arp_op request action pass"
- # Initial state - check that ARP requests are not suppressed and that
- # ARP replies are received.
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip -I eth0.$vid $tip"
- log_test $? 0 "arping"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "ARP suppression"
- # Enable neighbor suppression and check that nothing changes compared
- # to the initial state.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip -I eth0.$vid $tip"
- log_test $? 0 "arping"
- tc_check_packets $sw1 "dev vx0 egress" 101 2
- log_test $? 0 "ARP suppression"
- # Install an FDB entry for the remote host and check that nothing
- # changes compared to the initial state.
- h2_mac=$(ip -n $h2 -j -p link show eth0.$vid | jq -r '.[]["address"]')
- run_cmd "bridge -n $sw1 fdb replace $h2_mac dev vx0 master static vlan $vid"
- log_test $? 0 "FDB entry installation"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip -I eth0.$vid $tip"
- log_test $? 0 "arping"
- tc_check_packets $sw1 "dev vx0 egress" 101 3
- log_test $? 0 "ARP suppression"
- # Install a neighbor on the matching SVI interface and check that ARP
- # requests are suppressed.
- run_cmd "ip -n $sw1 neigh replace $tip lladdr $h2_mac nud permanent dev br0.$vid"
- log_test $? 0 "Neighbor entry installation"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip -I eth0.$vid $tip"
- log_test $? 0 "arping"
- tc_check_packets $sw1 "dev vx0 egress" 101 3
- log_test $? 0 "ARP suppression"
- # Take the second host down and check that ARP requests are suppressed
- # and that ARP replies are received.
- run_cmd "ip -n $h2 link set dev eth0.$vid down"
- log_test $? 0 "H2 down"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip -I eth0.$vid $tip"
- log_test $? 0 "arping"
- tc_check_packets $sw1 "dev vx0 egress" 101 3
- log_test $? 0 "ARP suppression"
- run_cmd "ip -n $h2 link set dev eth0.$vid up"
- log_test $? 0 "H2 up"
- # Disable neighbor suppression and check that ARP requests are no
- # longer suppressed.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress off"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip -I eth0.$vid $tip"
- log_test $? 0 "arping"
- tc_check_packets $sw1 "dev vx0 egress" 101 4
- log_test $? 0 "ARP suppression"
- # Take the second host down and check that ARP requests are not
- # suppressed and that ARP replies are not received.
- run_cmd "ip -n $h2 link set dev eth0.$vid down"
- log_test $? 0 "H2 down"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip -I eth0.$vid $tip"
- log_test $? 1 "arping"
- tc_check_packets $sw1 "dev vx0 egress" 101 5
- log_test $? 0 "ARP suppression"
- }
- neigh_suppress_arp()
- {
- local vid=10
- local sip=192.0.2.1
- local tip=192.0.2.2
- neigh_suppress_arp_common $vid $sip $tip
- vid=20
- sip=192.0.2.17
- tip=192.0.2.18
- neigh_suppress_arp_common $vid $sip $tip
- }
- neigh_suppress_uc_arp_common()
- {
- local vid=$1; shift
- local sip=$1; shift
- local tip=$1; shift
- local tmac
- echo
- echo "Unicast ARP, per-port ARP suppression - VLAN $vid"
- echo "-----------------------------------------------"
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- tmac=$(ip -n $h2 -j -p link show eth0.$vid | jq -r '.[]["address"]')
- run_cmd "bridge -n $sw1 fdb replace $tmac dev vx0 master static vlan $vid"
- run_cmd "ip -n $sw1 neigh replace $tip lladdr $tmac nud permanent dev br0.$vid"
- run_cmd "tc -n $h1 qdisc replace dev eth0.$vid clsact"
- run_cmd "tc -n $h1 filter replace dev eth0.$vid ingress pref 1 handle 101 proto arp flower arp_sip $tip arp_op reply action pass"
- run_cmd "tc -n $h2 qdisc replace dev eth0.$vid clsact"
- run_cmd "tc -n $h2 filter replace dev eth0.$vid egress pref 1 handle 101 proto arp flower arp_tip $sip arp_op reply action pass"
- run_cmd "ip netns exec $h1 mausezahn eth0.$vid -c 1 -a own -b $tmac -t arp 'request sip=$sip, tip=$tip, tmac=$tmac' -q"
- tc_check_packets $h1 "dev eth0.$vid ingress" 101 1
- log_test $? 0 "Unicast ARP, suppression on, h1 filter"
- tc_check_packets $h2 "dev eth0.$vid egress" 101 1
- log_test $? 0 "Unicast ARP, suppression on, h2 filter"
- }
- neigh_suppress_uc_arp()
- {
- local vid=10
- local sip=192.0.2.1
- local tip=192.0.2.2
- neigh_suppress_uc_arp_common $vid $sip $tip
- vid=20
- sip=192.0.2.17
- tip=192.0.2.18
- neigh_suppress_uc_arp_common $vid $sip $tip
- }
- neigh_suppress_ns_common()
- {
- local vid=$1; shift
- local saddr=$1; shift
- local daddr=$1; shift
- local maddr=$1; shift
- local h2_mac
- echo
- echo "Per-port NS suppression - VLAN $vid"
- echo "---------------------------------"
- run_cmd "tc -n $sw1 qdisc replace dev vx0 clsact"
- run_cmd "tc -n $sw1 filter replace dev vx0 egress pref 1 handle 101 proto ipv6 flower indev swp1 ip_proto icmpv6 dst_ip $maddr src_ip $saddr type 135 code 0 action pass"
- # Initial state - check that NS messages are not suppressed and that ND
- # messages are received.
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr -w 5000 $daddr eth0.$vid"
- log_test $? 0 "ndisc6"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "NS suppression"
- # Enable neighbor suppression and check that nothing changes compared
- # to the initial state.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr -w 5000 $daddr eth0.$vid"
- log_test $? 0 "ndisc6"
- tc_check_packets $sw1 "dev vx0 egress" 101 2
- log_test $? 0 "NS suppression"
- # Install an FDB entry for the remote host and check that nothing
- # changes compared to the initial state.
- h2_mac=$(ip -n $h2 -j -p link show eth0.$vid | jq -r '.[]["address"]')
- run_cmd "bridge -n $sw1 fdb replace $h2_mac dev vx0 master static vlan $vid"
- log_test $? 0 "FDB entry installation"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr -w 5000 $daddr eth0.$vid"
- log_test $? 0 "ndisc6"
- tc_check_packets $sw1 "dev vx0 egress" 101 3
- log_test $? 0 "NS suppression"
- # Install a neighbor on the matching SVI interface and check that NS
- # messages are suppressed.
- run_cmd "ip -n $sw1 neigh replace $daddr lladdr $h2_mac nud permanent dev br0.$vid"
- log_test $? 0 "Neighbor entry installation"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr -w 5000 $daddr eth0.$vid"
- log_test $? 0 "ndisc6"
- tc_check_packets $sw1 "dev vx0 egress" 101 3
- log_test $? 0 "NS suppression"
- # Take the second host down and check that NS messages are suppressed
- # and that ND messages are received.
- run_cmd "ip -n $h2 link set dev eth0.$vid down"
- log_test $? 0 "H2 down"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr -w 5000 $daddr eth0.$vid"
- log_test $? 0 "ndisc6"
- tc_check_packets $sw1 "dev vx0 egress" 101 3
- log_test $? 0 "NS suppression"
- run_cmd "ip -n $h2 link set dev eth0.$vid up"
- log_test $? 0 "H2 up"
- # Disable neighbor suppression and check that NS messages are no longer
- # suppressed.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress off"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr -w 5000 $daddr eth0.$vid"
- log_test $? 0 "ndisc6"
- tc_check_packets $sw1 "dev vx0 egress" 101 4
- log_test $? 0 "NS suppression"
- # Take the second host down and check that NS messages are not
- # suppressed and that ND messages are not received.
- run_cmd "ip -n $h2 link set dev eth0.$vid down"
- log_test $? 0 "H2 down"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr -w 5000 $daddr eth0.$vid"
- log_test $? 2 "ndisc6"
- tc_check_packets $sw1 "dev vx0 egress" 101 5
- log_test $? 0 "NS suppression"
- }
- neigh_suppress_ns()
- {
- local vid=10
- local saddr=2001:db8:1::1
- local daddr=2001:db8:1::2
- local maddr=ff02::1:ff00:2
- neigh_suppress_ns_common $vid $saddr $daddr $maddr
- vid=20
- saddr=2001:db8:2::1
- daddr=2001:db8:2::2
- maddr=ff02::1:ff00:2
- neigh_suppress_ns_common $vid $saddr $daddr $maddr
- }
- icmpv6_header_get()
- {
- local csum=$1; shift
- local tip=$1; shift
- local type
- local p
- # Type 135 (Neighbor Solicitation), hex format
- type="87"
- p=$(:
- )"$type:"$( : ICMPv6.type
- )"00:"$( : ICMPv6.code
- )"$csum:"$( : ICMPv6.checksum
- )"00:00:00:00:"$( : Reserved
- )"$tip:"$( : Target Address
- )
- echo $p
- }
- neigh_suppress_uc_ns_common()
- {
- local vid=$1; shift
- local sip=$1; shift
- local dip=$1; shift
- local full_dip=$1; shift
- local csum=$1; shift
- local tmac
- echo
- echo "Unicast NS, per-port NS suppression - VLAN $vid"
- echo "---------------------------------------------"
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- tmac=$(ip -n $h2 -j -p link show eth0.$vid | jq -r '.[]["address"]')
- run_cmd "bridge -n $sw1 fdb replace $tmac dev vx0 master static vlan $vid"
- run_cmd "ip -n $sw1 -6 neigh replace $dip lladdr $tmac nud permanent dev br0.$vid"
- run_cmd "tc -n $h1 qdisc replace dev eth0.$vid clsact"
- run_cmd "tc -n $h1 filter replace dev eth0.$vid ingress pref 1 handle 101 proto ipv6 flower ip_proto icmpv6 src_ip $dip type 136 code 0 action pass"
- run_cmd "tc -n $h2 qdisc replace dev eth0.$vid clsact"
- run_cmd "tc -n $h2 filter replace dev eth0.$vid egress pref 1 handle 101 proto ipv6 flower ip_proto icmpv6 dst_ip $sip type 136 code 0 action pass"
- run_cmd "ip netns exec $h1 mausezahn -6 eth0.$vid -c 1 -a own -b $tmac -A $sip -B $dip -t ip hop=255,next=58,payload=$(icmpv6_header_get $csum $full_dip) -q"
- tc_check_packets $h1 "dev eth0.$vid ingress" 101 1
- log_test $? 0 "Unicast NS, suppression on, h1 filter"
- tc_check_packets $h2 "dev eth0.$vid egress" 101 1
- log_test $? 0 "Unicast NS, suppression on, h2 filter"
- }
- neigh_suppress_uc_ns()
- {
- local vid=10
- local saddr=2001:db8:1::1
- local daddr=2001:db8:1::2
- local full_daddr=20:01:0d:b8:00:01:00:00:00:00:00:00:00:00:00:02
- local csum="ef:79"
- neigh_suppress_uc_ns_common $vid $saddr $daddr $full_daddr $csum
- vid=20
- saddr=2001:db8:2::1
- daddr=2001:db8:2::2
- full_daddr=20:01:0d:b8:00:02:00:00:00:00:00:00:00:00:00:02
- csum="ef:76"
- neigh_suppress_uc_ns_common $vid $saddr $daddr $full_daddr $csum
- }
- neigh_vlan_suppress_arp()
- {
- local vid1=10
- local vid2=20
- local sip1=192.0.2.1
- local sip2=192.0.2.17
- local tip1=192.0.2.2
- local tip2=192.0.2.18
- local h2_mac1
- local h2_mac2
- echo
- echo "Per-{Port, VLAN} ARP suppression"
- echo "--------------------------------"
- run_cmd "tc -n $sw1 qdisc replace dev vx0 clsact"
- run_cmd "tc -n $sw1 filter replace dev vx0 egress pref 1 handle 101 proto 0x0806 flower indev swp1 arp_tip $tip1 arp_sip $sip1 arp_op request action pass"
- run_cmd "tc -n $sw1 filter replace dev vx0 egress pref 1 handle 102 proto 0x0806 flower indev swp1 arp_tip $tip2 arp_sip $sip2 arp_op request action pass"
- h2_mac1=$(ip -n $h2 -j -p link show eth0.$vid1 | jq -r '.[]["address"]')
- h2_mac2=$(ip -n $h2 -j -p link show eth0.$vid2 | jq -r '.[]["address"]')
- run_cmd "bridge -n $sw1 fdb replace $h2_mac1 dev vx0 master static vlan $vid1"
- run_cmd "bridge -n $sw1 fdb replace $h2_mac2 dev vx0 master static vlan $vid2"
- run_cmd "ip -n $sw1 neigh replace $tip1 lladdr $h2_mac1 nud permanent dev br0.$vid1"
- run_cmd "ip -n $sw1 neigh replace $tip2 lladdr $h2_mac2 nud permanent dev br0.$vid2"
- # Enable per-{Port, VLAN} neighbor suppression and check that ARP
- # requests are not suppressed and that ARP replies are received.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_vlan_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_vlan_suppress on\""
- log_test $? 0 "\"neigh_vlan_suppress\" is on"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip1 -I eth0.$vid1 $tip1"
- log_test $? 0 "arping (VLAN $vid1)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip2 -I eth0.$vid2 $tip2"
- log_test $? 0 "arping (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "ARP suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 1
- log_test $? 0 "ARP suppression (VLAN $vid2)"
- # Enable neighbor suppression on VLAN 10 and check that only on this
- # VLAN ARP requests are suppressed.
- run_cmd "bridge -n $sw1 vlan set vid $vid1 dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d vlan show dev vx0 vid $vid1 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on (VLAN $vid1)"
- run_cmd "bridge -n $sw1 -d vlan show dev vx0 vid $vid2 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off (VLAN $vid2)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip1 -I eth0.$vid1 $tip1"
- log_test $? 0 "arping (VLAN $vid1)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip2 -I eth0.$vid2 $tip2"
- log_test $? 0 "arping (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "ARP suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 2
- log_test $? 0 "ARP suppression (VLAN $vid2)"
- # Enable neighbor suppression on the port and check that it has no
- # effect compared to previous state.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip1 -I eth0.$vid1 $tip1"
- log_test $? 0 "arping (VLAN $vid1)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip2 -I eth0.$vid2 $tip2"
- log_test $? 0 "arping (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "ARP suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 3
- log_test $? 0 "ARP suppression (VLAN $vid2)"
- # Disable neighbor suppression on the port and check that it has no
- # effect compared to previous state.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress off"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip1 -I eth0.$vid1 $tip1"
- log_test $? 0 "arping (VLAN $vid1)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip2 -I eth0.$vid2 $tip2"
- log_test $? 0 "arping (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "ARP suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 4
- log_test $? 0 "ARP suppression (VLAN $vid2)"
- # Disable neighbor suppression on VLAN 10 and check that ARP requests
- # are no longer suppressed on this VLAN.
- run_cmd "bridge -n $sw1 vlan set vid $vid1 dev vx0 neigh_suppress off"
- run_cmd "bridge -n $sw1 -d vlan show dev vx0 vid $vid1 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off (VLAN $vid1)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip1 -I eth0.$vid1 $tip1"
- log_test $? 0 "arping (VLAN $vid1)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip2 -I eth0.$vid2 $tip2"
- log_test $? 0 "arping (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 2
- log_test $? 0 "ARP suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 5
- log_test $? 0 "ARP suppression (VLAN $vid2)"
- # Disable per-{Port, VLAN} neighbor suppression, enable neighbor
- # suppression on the port and check that on both VLANs ARP requests are
- # suppressed.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_vlan_suppress off"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_vlan_suppress off\""
- log_test $? 0 "\"neigh_vlan_suppress\" is off"
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip1 -I eth0.$vid1 $tip1"
- log_test $? 0 "arping (VLAN $vid1)"
- run_cmd "ip netns exec $h1 arping -q -b -c 1 -w 5 -s $sip2 -I eth0.$vid2 $tip2"
- log_test $? 0 "arping (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 2
- log_test $? 0 "ARP suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 5
- log_test $? 0 "ARP suppression (VLAN $vid2)"
- }
- neigh_vlan_suppress_ns()
- {
- local vid1=10
- local vid2=20
- local saddr1=2001:db8:1::1
- local saddr2=2001:db8:2::1
- local daddr1=2001:db8:1::2
- local daddr2=2001:db8:2::2
- local maddr=ff02::1:ff00:2
- local h2_mac1
- local h2_mac2
- echo
- echo "Per-{Port, VLAN} NS suppression"
- echo "-------------------------------"
- run_cmd "tc -n $sw1 qdisc replace dev vx0 clsact"
- run_cmd "tc -n $sw1 filter replace dev vx0 egress pref 1 handle 101 proto ipv6 flower indev swp1 ip_proto icmpv6 dst_ip $maddr src_ip $saddr1 type 135 code 0 action pass"
- run_cmd "tc -n $sw1 filter replace dev vx0 egress pref 1 handle 102 proto ipv6 flower indev swp1 ip_proto icmpv6 dst_ip $maddr src_ip $saddr2 type 135 code 0 action pass"
- h2_mac1=$(ip -n $h2 -j -p link show eth0.$vid1 | jq -r '.[]["address"]')
- h2_mac2=$(ip -n $h2 -j -p link show eth0.$vid2 | jq -r '.[]["address"]')
- run_cmd "bridge -n $sw1 fdb replace $h2_mac1 dev vx0 master static vlan $vid1"
- run_cmd "bridge -n $sw1 fdb replace $h2_mac2 dev vx0 master static vlan $vid2"
- run_cmd "ip -n $sw1 neigh replace $daddr1 lladdr $h2_mac1 nud permanent dev br0.$vid1"
- run_cmd "ip -n $sw1 neigh replace $daddr2 lladdr $h2_mac2 nud permanent dev br0.$vid2"
- # Enable per-{Port, VLAN} neighbor suppression and check that NS
- # messages are not suppressed and that ND messages are received.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_vlan_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_vlan_suppress on\""
- log_test $? 0 "\"neigh_vlan_suppress\" is on"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr1 -w 5000 $daddr1 eth0.$vid1"
- log_test $? 0 "ndisc6 (VLAN $vid1)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr2 -w 5000 $daddr2 eth0.$vid2"
- log_test $? 0 "ndisc6 (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "NS suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 1
- log_test $? 0 "NS suppression (VLAN $vid2)"
- # Enable neighbor suppression on VLAN 10 and check that only on this
- # VLAN NS messages are suppressed.
- run_cmd "bridge -n $sw1 vlan set vid $vid1 dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d vlan show dev vx0 vid $vid1 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on (VLAN $vid1)"
- run_cmd "bridge -n $sw1 -d vlan show dev vx0 vid $vid2 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off (VLAN $vid2)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr1 -w 5000 $daddr1 eth0.$vid1"
- log_test $? 0 "ndisc6 (VLAN $vid1)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr2 -w 5000 $daddr2 eth0.$vid2"
- log_test $? 0 "ndisc6 (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "NS suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 2
- log_test $? 0 "NS suppression (VLAN $vid2)"
- # Enable neighbor suppression on the port and check that it has no
- # effect compared to previous state.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr1 -w 5000 $daddr1 eth0.$vid1"
- log_test $? 0 "ndisc6 (VLAN $vid1)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr2 -w 5000 $daddr2 eth0.$vid2"
- log_test $? 0 "ndisc6 (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "NS suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 3
- log_test $? 0 "NS suppression (VLAN $vid2)"
- # Disable neighbor suppression on the port and check that it has no
- # effect compared to previous state.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress off"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr1 -w 5000 $daddr1 eth0.$vid1"
- log_test $? 0 "ndisc6 (VLAN $vid1)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr2 -w 5000 $daddr2 eth0.$vid2"
- log_test $? 0 "ndisc6 (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 1
- log_test $? 0 "NS suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 4
- log_test $? 0 "NS suppression (VLAN $vid2)"
- # Disable neighbor suppression on VLAN 10 and check that NS messages
- # are no longer suppressed on this VLAN.
- run_cmd "bridge -n $sw1 vlan set vid $vid1 dev vx0 neigh_suppress off"
- run_cmd "bridge -n $sw1 -d vlan show dev vx0 vid $vid1 | grep \"neigh_suppress off\""
- log_test $? 0 "\"neigh_suppress\" is off (VLAN $vid1)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr1 -w 5000 $daddr1 eth0.$vid1"
- log_test $? 0 "ndisc6 (VLAN $vid1)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr2 -w 5000 $daddr2 eth0.$vid2"
- log_test $? 0 "ndisc6 (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 2
- log_test $? 0 "NS suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 5
- log_test $? 0 "NS suppression (VLAN $vid2)"
- # Disable per-{Port, VLAN} neighbor suppression, enable neighbor
- # suppression on the port and check that on both VLANs NS messages are
- # suppressed.
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_vlan_suppress off"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_vlan_suppress off\""
- log_test $? 0 "\"neigh_vlan_suppress\" is off"
- run_cmd "bridge -n $sw1 link set dev vx0 neigh_suppress on"
- run_cmd "bridge -n $sw1 -d link show dev vx0 | grep \"neigh_suppress on\""
- log_test $? 0 "\"neigh_suppress\" is on"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr1 -w 5000 $daddr1 eth0.$vid1"
- log_test $? 0 "ndisc6 (VLAN $vid1)"
- run_cmd "ip netns exec $h1 ndisc6 -q -r 1 -s $saddr2 -w 5000 $daddr2 eth0.$vid2"
- log_test $? 0 "ndisc6 (VLAN $vid2)"
- tc_check_packets $sw1 "dev vx0 egress" 101 2
- log_test $? 0 "NS suppression (VLAN $vid1)"
- tc_check_packets $sw1 "dev vx0 egress" 102 5
- log_test $? 0 "NS suppression (VLAN $vid2)"
- }
- ################################################################################
- # Usage
- usage()
- {
- cat <<EOF
- usage: ${0##*/} OPTS
- -t <test> Test(s) to run (default: all)
- (options: $TESTS)
- -p Pause on fail
- -P Pause after each test before cleanup
- -v Verbose mode (show commands and output)
- EOF
- }
- ################################################################################
- # Main
- trap cleanup EXIT
- while getopts ":t:pPvh" opt; do
- case $opt in
- t) TESTS=$OPTARG;;
- p) PAUSE_ON_FAIL=yes;;
- P) PAUSE=yes;;
- v) VERBOSE=$(($VERBOSE + 1));;
- h) usage; exit 0;;
- *) usage; exit 1;;
- esac
- done
- # Make sure we don't pause twice.
- [ "${PAUSE}" = "yes" ] && PAUSE_ON_FAIL=no
- if [ "$(id -u)" -ne 0 ];then
- echo "SKIP: Need root privileges"
- exit $ksft_skip;
- fi
- if [ ! -x "$(command -v ip)" ]; then
- echo "SKIP: Could not run test without ip tool"
- exit $ksft_skip
- fi
- if [ ! -x "$(command -v bridge)" ]; then
- echo "SKIP: Could not run test without bridge tool"
- exit $ksft_skip
- fi
- if [ ! -x "$(command -v tc)" ]; then
- echo "SKIP: Could not run test without tc tool"
- exit $ksft_skip
- fi
- if [ ! -x "$(command -v arping)" ]; then
- echo "SKIP: Could not run test without arping tool"
- exit $ksft_skip
- fi
- if [ ! -x "$(command -v ndisc6)" ]; then
- echo "SKIP: Could not run test without ndisc6 tool"
- exit $ksft_skip
- fi
- if [ ! -x "$(command -v jq)" ]; then
- echo "SKIP: Could not run test without jq tool"
- exit $ksft_skip
- fi
- if [ ! -x "$(command -v mausezahn)" ]; then
- echo "SKIP: Could not run test without mausezahn tool"
- exit $ksft_skip
- fi
- bridge link help 2>&1 | grep -q "neigh_vlan_suppress"
- if [ $? -ne 0 ]; then
- echo "SKIP: iproute2 bridge too old, missing per-VLAN neighbor suppression support"
- exit $ksft_skip
- fi
- # Start clean.
- cleanup
- for t in $TESTS
- do
- setup; $t; cleanup;
- done
- if [ "$TESTS" != "none" ]; then
- printf "\nTests passed: %3d\n" ${nsuccess}
- printf "Tests failed: %3d\n" ${nfail}
- fi
- exit $ret
|