1#!/bin/bash 2# SPDX-License-Identifier: GPL-2.0 3 4ALL_TESTS="vlmc_control_test vlmc_querier_test vlmc_igmp_mld_version_test \ 5 vlmc_last_member_test vlmc_startup_query_test vlmc_membership_test \ 6 vlmc_querier_intvl_test vlmc_query_intvl_test vlmc_query_response_intvl_test \ 7 vlmc_router_port_test vlmc_filtering_test vlmc_mcast_toggle_test" 8NUM_NETIFS=4 9CHECK_TC="yes" 10TEST_GROUP="239.10.10.10" 11 12source lib.sh 13 14h1_create() 15{ 16 simple_if_init $h1 192.0.2.1/24 2001:db8:1::1/64 17 ip link add l $h1 $h1.10 up type vlan id 10 18} 19 20h1_destroy() 21{ 22 ip link del $h1.10 23 simple_if_fini $h1 192.0.2.1/24 2001:db8:1::1/64 24} 25 26h2_create() 27{ 28 simple_if_init $h2 192.0.2.2/24 2001:db8:1::2/64 29 ip link add l $h2 $h2.10 up type vlan id 10 30} 31 32h2_destroy() 33{ 34 ip link del $h2.10 35 simple_if_fini $h2 192.0.2.2/24 2001:db8:1::2/64 36} 37 38switch_create() 39{ 40 ip link add dev br0 type bridge mcast_snooping 1 mcast_querier 1 vlan_filtering 1 41 42 ip link set dev $swp1 master br0 43 ip link set dev $swp2 master br0 44 45 ip link set dev br0 up 46 ip link set dev $swp1 up 47 ip link set dev $swp2 up 48 49 tc qdisc add dev $swp1 clsact 50 tc qdisc add dev $swp2 clsact 51 52 bridge vlan add vid 10-11 dev $swp1 master 53 bridge vlan add vid 10-11 dev $swp2 master 54 55 ip link set dev br0 type bridge mcast_vlan_snooping 1 56 check_err $? "Could not enable global vlan multicast snooping" 57 log_test "Vlan multicast snooping enable" 58} 59 60switch_destroy() 61{ 62 tc qdisc del dev $swp2 clsact 63 tc qdisc del dev $swp1 clsact 64 65 ip link set dev $swp2 down 66 ip link set dev $swp1 down 67 68 ip link del dev br0 69} 70 71setup_prepare() 72{ 73 h1=${NETIFS[p1]} 74 swp1=${NETIFS[p2]} 75 76 swp2=${NETIFS[p3]} 77 h2=${NETIFS[p4]} 78 79 vrf_prepare 80 81 h1_create 82 h2_create 83 84 switch_create 85} 86 87cleanup() 88{ 89 pre_cleanup 90 91 switch_destroy 92 93 h2_destroy 94 h1_destroy 95 96 vrf_cleanup 97} 98 99vlmc_v2join_test() 100{ 101 local expect=$1 102 103 RET=0 104 ip address add dev $h2.10 $TEST_GROUP/32 autojoin 105 check_err $? "Could not join $TEST_GROUP" 106 107 sleep 5 108 bridge -j mdb show dev br0 | 109 jq -e ".[].mdb[] | select(.grp == \"$TEST_GROUP\" and .vid == 10)" &>/dev/null 110 if [ $expect -eq 0 ]; then 111 check_err $? "IGMPv2 report didn't create mdb entry for $TEST_GROUP" 112 else 113 check_fail $? "IGMPv2 report shouldn't have created mdb entry for $TEST_GROUP" 114 fi 115 116 # check if we need to cleanup 117 if [ $RET -eq 0 ]; then 118 ip address del dev $h2.10 $TEST_GROUP/32 2>&1 1>/dev/null 119 sleep 5 120 bridge -j mdb show dev br0 | 121 jq -e ".[].mdb[] | select(.grp == \"$TEST_GROUP\" and \ 122 .vid == 10)" &>/dev/null 123 check_fail $? "IGMPv2 leave didn't remove mdb entry for $TEST_GROUP" 124 fi 125} 126 127vlmc_control_test() 128{ 129 RET=0 130 local goutput=`bridge -j vlan global show` 131 echo -n $goutput | 132 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 133 check_err $? "Could not find vlan 10's global options" 134 log_test "Vlan global options existence" 135 136 RET=0 137 echo -n $goutput | 138 jq -e ".[].vlans[] | select(.vlan == 10 and .mcast_snooping == 1) " &>/dev/null 139 check_err $? "Wrong default mcast_snooping global option value" 140 log_test "Vlan mcast_snooping global option default value" 141 142 RET=0 143 vlmc_v2join_test 0 144 bridge vlan global set vid 10 dev br0 mcast_snooping 0 145 check_err $? "Could not disable multicast snooping in vlan 10" 146 vlmc_v2join_test 1 147 log_test "Vlan 10 multicast snooping control" 148} 149 150# setup for general query counting 151vlmc_query_cnt_xstats() 152{ 153 local type=$1 154 local version=$2 155 local dev=$3 156 157 ip -j link xstats type bridge_slave dev $dev | \ 158 jq -e ".[].multicast.${type}_queries.tx_v${version}" 159} 160 161vlmc_query_cnt_setup() 162{ 163 local type=$1 164 local dev=$2 165 local match=($3) 166 167 if [[ $type == "igmp" ]]; then 168 # This matches: IP Protocol 2 (IGMP) 169 tc filter add dev "$dev" egress pref 10 prot 802.1Q \ 170 flower vlan_id 10 vlan_ethtype ipv4 dst_ip 224.0.0.1 ip_proto 2 \ 171 action goto chain 1 172 # AND Type 0x11 (Query) at offset 0 of IGMP header 173 # 20 bytes IPv4 header + 4 bytes Router Alert option + IGMP[offset 0] 174 tc filter add dev "$dev" egress pref 20 chain 1 prot 802.1Q u32 \ 175 match u8 0x11 0xff at 24 "${match[@]}" \ 176 action pass 177 else 178 # This matches: ICMPv6 179 tc filter add dev "$dev" egress pref 10 prot 802.1Q \ 180 flower vlan_id 10 vlan_ethtype ipv6 dst_ip ff02::1 ip_proto icmpv6 \ 181 action goto chain 1 182 # AND Type 0x82 (Query) at offset 0 of MLD header 183 # 40 bytes IPv6 header + 8 bytes Hop-by-hop option + MLD[offset 0] 184 tc filter add dev "$dev" egress pref 20 chain 1 prot 802.1Q u32 \ 185 match u8 0x82 0xff at 48 "${match[@]}" \ 186 action pass 187 fi 188 189 ip link set dev br0 type bridge mcast_stats_enabled 1 190} 191 192vlmc_query_cnt_cleanup() 193{ 194 local dev=$1 195 196 ip link set dev br0 type bridge mcast_stats_enabled 0 197 tc filter del dev "$dev" egress pref 20 chain 1 198 tc filter del dev "$dev" egress pref 10 199} 200 201vlmc_query_get_intvl_match() 202{ 203 local type=$1 204 local version=$2 205 local test=$3 206 local enc_val=$4 207 208 if [ "$test" = "qqic" ]; then 209 # QQIC is 8-bit floating point encoding for IGMPv3 and MLDv2 210 if [ "${type}v${version}" = "igmpv3" ]; then 211 # QQIC is at offset 9 of IGMP header 212 # 20 bytes IPv4 header + 4 bytes Router Alert option + IGMP[offset 9] 213 echo "match u8 $enc_val 0xff at 33" 214 elif [ "${type}v${version}" = "mldv2" ]; then 215 # QQIC is at offset 25 of MLD header 216 # 40 bytes IPv6 header + 8 bytes Hop-by-hop option + MLD[offset 25] 217 echo "match u8 $enc_val 0xff at 73" 218 fi 219 elif [ "$test" = "mrc" ]; then 220 if [ "${type}v${version}" = "igmpv3" ]; then 221 # MRC is 8-bit floating point encoding at offset 1 of IGMP header 222 # 20 bytes IPv4 header + 4 bytes Router Alert option + IGMP[offset 1] 223 echo "match u8 $enc_val 0xff at 25" 224 elif [ "${type}v${version}" = "mldv2" ]; then 225 # MRC is 16-bit floating point encoding at offset 4 of MLD header 226 # 40 bytes IPv6 header + 8 bytes Hop-by-hop option + MLD[offset 4] 227 echo "match u16 $enc_val 0xffff at 52" 228 fi 229 fi 230} 231 232vlmc_check_query() 233{ 234 local type=$1 235 local version=$2 236 local dev=$3 237 local expect=$4 238 local time=$5 239 local test=$6 240 local enc_val=$7 241 local intvl_match="" 242 local ret=0 243 244 intvl_match="$(vlmc_query_get_intvl_match "$type" "$version" "$test" "$enc_val")" 245 vlmc_query_cnt_setup "$type" "$dev" "$intvl_match" 246 247 local pre_tx_xstats=$(vlmc_query_cnt_xstats $type $version $dev) 248 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_querier 1 249 ret=$? 250 if [[ $ret -eq 0 ]]; then 251 sleep $time 252 253 local tcstats=$(tc_rule_stats_get "$dev" 20 egress) 254 local post_tx_xstats=$(vlmc_query_cnt_xstats $type $version $dev) 255 256 if [[ $tcstats != $expect || \ 257 $(($post_tx_xstats-$pre_tx_xstats)) != $expect || \ 258 $tcstats != $(($post_tx_xstats-$pre_tx_xstats)) ]]; then 259 ret=1 260 fi 261 fi 262 263 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_querier 0 264 vlmc_query_cnt_cleanup $dev 265 266 return $ret 267} 268 269vlmc_querier_test() 270{ 271 RET=0 272 local goutput=`bridge -j vlan global show` 273 echo -n $goutput | 274 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 275 check_err $? "Could not find vlan 10's global options" 276 277 echo -n $goutput | 278 jq -e ".[].vlans[] | select(.vlan == 10 and .mcast_querier == 0) " &>/dev/null 279 check_err $? "Wrong default mcast_querier global vlan option value" 280 log_test "Vlan mcast_querier global option default value" 281 282 RET=0 283 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_querier 1 284 check_err $? "Could not enable querier in vlan 10" 285 log_test "Vlan 10 multicast querier enable" 286 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_querier 0 287 288 RET=0 289 vlmc_check_query igmp 2 $swp1 1 1 290 check_err $? "No vlan tagged IGMPv2 general query packets sent" 291 log_test "Vlan 10 tagged IGMPv2 general query sent" 292 293 RET=0 294 vlmc_check_query mld 1 $swp1 1 1 295 check_err $? "No vlan tagged MLD general query packets sent" 296 log_test "Vlan 10 tagged MLD general query sent" 297} 298 299vlmc_igmp_mld_version_test() 300{ 301 RET=0 302 local goutput=`bridge -j vlan global show` 303 echo -n $goutput | 304 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 305 check_err $? "Could not find vlan 10's global options" 306 307 echo -n $goutput | 308 jq -e ".[].vlans[] | select(.vlan == 10 and .mcast_igmp_version == 2) " &>/dev/null 309 check_err $? "Wrong default mcast_igmp_version global vlan option value" 310 log_test "Vlan mcast_igmp_version global option default value" 311 312 RET=0 313 echo -n $goutput | 314 jq -e ".[].vlans[] | select(.vlan == 10 and .mcast_mld_version == 1) " &>/dev/null 315 check_err $? "Wrong default mcast_mld_version global vlan option value" 316 log_test "Vlan mcast_mld_version global option default value" 317 318 RET=0 319 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_igmp_version 3 320 check_err $? "Could not set mcast_igmp_version in vlan 10" 321 log_test "Vlan 10 mcast_igmp_version option changed to 3" 322 323 RET=0 324 vlmc_check_query igmp 3 $swp1 1 1 325 check_err $? "No vlan tagged IGMPv3 general query packets sent" 326 log_test "Vlan 10 tagged IGMPv3 general query sent" 327 328 RET=0 329 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_mld_version 2 330 check_err $? "Could not set mcast_mld_version in vlan 10" 331 log_test "Vlan 10 mcast_mld_version option changed to 2" 332 333 RET=0 334 vlmc_check_query mld 2 $swp1 1 1 335 check_err $? "No vlan tagged MLDv2 general query packets sent" 336 log_test "Vlan 10 tagged MLDv2 general query sent" 337 338 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_igmp_version 2 339 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_mld_version 1 340} 341 342vlmc_last_member_test() 343{ 344 RET=0 345 local goutput=`bridge -j vlan global show` 346 echo -n $goutput | 347 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 348 check_err $? "Could not find vlan 10's global options" 349 350 echo -n $goutput | 351 jq -e ".[].vlans[] | select(.vlan == 10 and \ 352 .mcast_last_member_count == 2) " &>/dev/null 353 check_err $? "Wrong default mcast_last_member_count global vlan option value" 354 log_test "Vlan mcast_last_member_count global option default value" 355 356 RET=0 357 echo -n $goutput | 358 jq -e ".[].vlans[] | select(.vlan == 10 and \ 359 .mcast_last_member_interval == 100) " &>/dev/null 360 check_err $? "Wrong default mcast_last_member_interval global vlan option value" 361 log_test "Vlan mcast_last_member_interval global option default value" 362 363 RET=0 364 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_last_member_count 3 365 check_err $? "Could not set mcast_last_member_count in vlan 10" 366 log_test "Vlan 10 mcast_last_member_count option changed to 3" 367 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_last_member_count 2 368 369 RET=0 370 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_last_member_interval 200 371 check_err $? "Could not set mcast_last_member_interval in vlan 10" 372 log_test "Vlan 10 mcast_last_member_interval option changed to 200" 373 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_last_member_interval 100 374} 375 376vlmc_startup_query_test() 377{ 378 RET=0 379 local goutput=`bridge -j vlan global show` 380 echo -n $goutput | 381 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 382 check_err $? "Could not find vlan 10's global options" 383 384 echo -n $goutput | 385 jq -e ".[].vlans[] | select(.vlan == 10 and \ 386 .mcast_startup_query_interval == 3125) " &>/dev/null 387 check_err $? "Wrong default mcast_startup_query_interval global vlan option value" 388 log_test "Vlan mcast_startup_query_interval global option default value" 389 390 RET=0 391 echo -n $goutput | 392 jq -e ".[].vlans[] | select(.vlan == 10 and \ 393 .mcast_startup_query_count == 2) " &>/dev/null 394 check_err $? "Wrong default mcast_startup_query_count global vlan option value" 395 log_test "Vlan mcast_startup_query_count global option default value" 396 397 RET=0 398 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_interval 100 399 check_err $? "Could not set mcast_startup_query_interval in vlan 10" 400 vlmc_check_query igmp 2 $swp1 2 3 401 check_err $? "Wrong number of tagged IGMPv2 general queries sent" 402 log_test "Vlan 10 mcast_startup_query_interval option changed to 100" 403 404 RET=0 405 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_count 3 406 check_err $? "Could not set mcast_startup_query_count in vlan 10" 407 vlmc_check_query igmp 2 $swp1 3 4 408 check_err $? "Wrong number of tagged IGMPv2 general queries sent" 409 log_test "Vlan 10 mcast_startup_query_count option changed to 3" 410 411 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_interval 3125 412 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_count 2 413} 414 415vlmc_membership_test() 416{ 417 RET=0 418 local goutput=`bridge -j vlan global show` 419 echo -n $goutput | 420 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 421 check_err $? "Could not find vlan 10's global options" 422 423 echo -n $goutput | 424 jq -e ".[].vlans[] | select(.vlan == 10 and \ 425 .mcast_membership_interval == 26000) " &>/dev/null 426 check_err $? "Wrong default mcast_membership_interval global vlan option value" 427 log_test "Vlan mcast_membership_interval global option default value" 428 429 RET=0 430 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_membership_interval 200 431 check_err $? "Could not set mcast_membership_interval in vlan 10" 432 log_test "Vlan 10 mcast_membership_interval option changed to 200" 433 434 RET=0 435 vlmc_v2join_test 1 436 log_test "Vlan 10 mcast_membership_interval mdb entry expire" 437 438 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_membership_interval 26000 439} 440 441vlmc_querier_intvl_test() 442{ 443 RET=0 444 local goutput=`bridge -j vlan global show` 445 echo -n $goutput | 446 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 447 check_err $? "Could not find vlan 10's global options" 448 449 echo -n $goutput | 450 jq -e ".[].vlans[] | select(.vlan == 10 and \ 451 .mcast_querier_interval == 25500) " &>/dev/null 452 check_err $? "Wrong default mcast_querier_interval global vlan option value" 453 log_test "Vlan mcast_querier_interval global option default value" 454 455 RET=0 456 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_querier_interval 100 457 check_err $? "Could not set mcast_querier_interval in vlan 10" 458 log_test "Vlan 10 mcast_querier_interval option changed to 100" 459 460 RET=0 461 ip link add dev br1 type bridge mcast_snooping 1 mcast_querier 1 vlan_filtering 1 \ 462 mcast_vlan_snooping 1 463 bridge vlan add vid 10 dev br1 self pvid untagged 464 ip link set dev $h1 master br1 465 ip link set dev br1 up 466 setup_wait_dev $h1 0 467 bridge vlan add vid 10 dev $h1 master 468 bridge vlan global set vid 10 dev br1 mcast_snooping 1 mcast_querier 1 469 sleep 2 470 ip link del dev br1 471 ip addr replace 2001:db8:1::1/64 dev $h1 472 vlmc_check_query igmp 2 $swp1 1 1 473 check_err $? "Wrong number of IGMPv2 general queries after querier interval" 474 log_test "Vlan 10 mcast_querier_interval expire after outside query" 475 476 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_querier_interval 25500 477} 478 479vlmc_query_intvl_test() 480{ 481 RET=0 482 local goutput=`bridge -j vlan global show` 483 echo -n $goutput | 484 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 485 check_err $? "Could not find vlan 10's global options" 486 487 echo -n $goutput | 488 jq -e ".[].vlans[] | select(.vlan == 10 and \ 489 .mcast_query_interval == 12500) " &>/dev/null 490 check_err $? "Wrong default mcast_query_interval global vlan option value" 491 log_test "Vlan mcast_query_interval global option default value" 492 493 RET=0 494 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_count 0 495 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_interval 200 496 check_err $? "Could not set mcast_query_interval in vlan 10" 497 # 1 is sent immediately, then 2 more in the next 5 seconds 498 vlmc_check_query igmp 2 $swp1 3 5 499 check_err $? "Wrong number of tagged IGMPv2 general queries sent" 500 log_test "Number of tagged IGMPv2 general query" 501 502 RET=0 503 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_igmp_version 3 504 check_err $? "Could not set mcast_igmp_version in vlan 10" 505 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_mld_version 2 506 check_err $? "Could not set mcast_mld_version in vlan 10" 507 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_interval 6000 508 check_err $? "Could not set mcast_query_interval in vlan 10" 509 # 1 is sent immediately, IGMPv3 QQIC should match with linear value 60 (0x3c) 510 # which is 8-bit encoded value of 60 [units of seconds] 511 vlmc_check_query igmp 3 $swp1 1 1 qqic 0x3c 512 check_err $? "Wrong QQIC in generated IGMPv3 general queries" 513 log_test "IGMPv3 QQIC linear value 60(s)" 514 515 RET=0 516 # 1 is sent immediately, MLDv2 QQIC should match with linear value 60 (0x3c) 517 # which is 8-bit encoded value of 60 [units of seconds] 518 vlmc_check_query mld 2 $swp1 1 1 qqic 0x3c 519 check_err $? "Wrong QQIC in generated MLDv2 general queries" 520 log_test "MLDv2 QQIC linear value 60(s)" 521 522 RET=0 523 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_interval 16000 524 check_err $? "Could not set mcast_query_interval in vlan 10" 525 # 1 is sent immediately, IGMPv3 QQIC should match with non linear value 132 (0x84) 526 # which is 8-bit encoded value of 160 [units of seconds] 527 vlmc_check_query igmp 3 $swp1 1 1 qqic 0x84 528 check_err $? "Wrong QQIC in generated IGMPv3 general queries" 529 log_test "IGMPv3 QQIC non linear value 160(s)" 530 531 RET=0 532 # 1 is sent immediately, MLDv2 QQIC should match with non linear value 132 (0x84) 533 # which is 8-bit encoded value of 160 [units of seconds] 534 vlmc_check_query mld 2 $swp1 1 1 qqic 0x84 535 check_err $? "Wrong QQIC in generated MLDv2 general queries" 536 log_test "MLDv2 QQIC non linear value 160(s)" 537 538 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_igmp_version 2 539 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_mld_version 1 540 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_count 2 541 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_interval 12500 542} 543 544vlmc_query_response_intvl_test() 545{ 546 RET=0 547 local goutput=`bridge -j vlan global show` 548 echo -n $goutput | 549 jq -e ".[].vlans[] | select(.vlan == 10)" &>/dev/null 550 check_err $? "Could not find vlan 10's global options" 551 552 echo -n $goutput | 553 jq -e ".[].vlans[] | select(.vlan == 10 and \ 554 .mcast_query_response_interval == 1000) " &>/dev/null 555 check_err $? "Wrong default mcast_query_response_interval global vlan option value" 556 log_test "Vlan mcast_query_response_interval global option default value" 557 558 RET=0 559 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_count 0 560 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_igmp_version 3 561 check_err $? "Could not set mcast_igmp_version in vlan 10" 562 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_mld_version 2 563 check_err $? "Could not set mcast_mld_version in vlan 10" 564 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_response_interval 600 565 check_err $? "Could not set mcast_query_response_interval in vlan 10" 566 # 1 is sent immediately, IGMPv3 MRC should match with linear value 60 (0x3c) 567 # which is 8-bit encoded value of 60 [units of 0.1s = 6 seconds] 568 vlmc_check_query igmp 3 $swp1 1 1 mrc 0x3c 569 check_err $? "Wrong MRC in generated IGMPv3 general queries" 570 log_test "IGMPv3 MRC linear value of 60(x0.1s)" 571 572 RET=0 573 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_response_interval 2400 574 check_err $? "Could not set mcast_query_response_interval in vlan 10" 575 # 1 is sent immediately, MLDv2 MRC should match with linear value 0x5dc0 (24000) 576 # which is 16-bit encoded value of 24000 [units of ms / 24 seconds] 577 vlmc_check_query mld 2 $swp1 1 1 mrc 0x5dc0 578 check_err $? "Wrong MRC in generated MLDv2 general queries" 579 log_test "MLDv2 MRC linear value of 24000(ms)" 580 581 RET=0 582 # 1 is sent immediately, IGMPv3 MRC should match with non linear value 142 (0x8e) 583 # which is 8-bit encoded value of 240 [units of 0.1s = 24 seconds] 584 vlmc_check_query igmp 3 $swp1 1 1 mrc 0x8e 585 check_err $? "Wrong MRC in generated IGMPv3 general queries" 586 log_test "IGMPv3 MRC non linear value of 240(x0.1s)" 587 588 RET=0 589 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_response_interval 4800 590 check_err $? "Could not set mcast_query_response_interval in vlan 10" 591 # 1 is sent immediately, MLDv2 MRC should match with non linear value 0x8770 (34672) 592 # which is 16-bit encoded value of 48000 [units of ms / 48 seconds] 593 vlmc_check_query mld 2 $swp1 1 1 mrc 0x8770 594 check_err $? "Wrong MRC in generated MLDv2 general queries" 595 log_test "MLDv2 MRC non linear value of 48000(ms)" 596 597 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_igmp_version 2 598 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_mld_version 1 599 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_startup_query_count 2 600 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_response_interval 1000 601} 602 603vlmc_router_port_test() 604{ 605 RET=0 606 local goutput=`bridge -j -d vlan show` 607 echo -n $goutput | 608 jq -e ".[] | select(.ifname == \"$swp1\" and \ 609 .vlans[].vlan == 10)" &>/dev/null 610 check_err $? "Could not find port vlan 10's options" 611 612 echo -n $goutput | 613 jq -e ".[] | select(.ifname == \"$swp1\" and \ 614 .vlans[].vlan == 10 and \ 615 .vlans[].mcast_router == 1)" &>/dev/null 616 check_err $? "Wrong default port mcast_router option value" 617 log_test "Port vlan 10 option mcast_router default value" 618 619 RET=0 620 bridge vlan set vid 10 dev $swp1 mcast_router 2 621 check_err $? "Could not set port vlan 10's mcast_router option" 622 log_test "Port vlan 10 mcast_router option changed to 2" 623 624 RET=0 625 tc filter add dev $swp1 egress pref 10 prot 802.1Q \ 626 flower vlan_id 10 vlan_ethtype ipv4 dst_ip 239.1.1.1 ip_proto udp action pass 627 tc filter add dev $swp2 egress pref 10 prot 802.1Q \ 628 flower vlan_id 10 vlan_ethtype ipv4 dst_ip 239.1.1.1 ip_proto udp action pass 629 bridge vlan set vid 10 dev $swp2 mcast_router 0 630 # we need to enable querier and disable query response interval to 631 # make sure packets are flooded only to router ports 632 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_querier 1 \ 633 mcast_query_response_interval 0 634 bridge vlan add vid 10 dev br0 self 635 sleep 1 636 mausezahn br0 -Q 10 -c 10 -p 128 -b 01:00:5e:01:01:01 -B 239.1.1.1 \ 637 -t udp "dp=1024" &>/dev/null 638 local swp1_tcstats=$(tc_rule_stats_get $swp1 10 egress) 639 if [[ $swp1_tcstats != 10 ]]; then 640 check_err 1 "Wrong number of vlan 10 multicast packets flooded" 641 fi 642 local swp2_tcstats=$(tc_rule_stats_get $swp2 10 egress) 643 check_err $swp2_tcstats "Vlan 10 multicast packets flooded to non-router port" 644 log_test "Flood unknown vlan multicast packets to router port only" 645 646 tc filter del dev $swp2 egress pref 10 647 tc filter del dev $swp1 egress pref 10 648 bridge vlan del vid 10 dev br0 self 649 bridge vlan global set vid 10 dev br0 mcast_snooping 1 mcast_query_response_interval 1000 650 bridge vlan set vid 10 dev $swp2 mcast_router 1 651 bridge vlan set vid 10 dev $swp1 mcast_router 1 652} 653 654vlmc_filtering_test() 655{ 656 RET=0 657 ip link set dev br0 type bridge vlan_filtering 0 658 ip -j -d link show dev br0 | \ 659 jq -e "select(.[0].linkinfo.info_data.mcast_vlan_snooping == 1)" &>/dev/null 660 check_fail $? "Vlan filtering is disabled but multicast vlan snooping is still enabled" 661 log_test "Disable multicast vlan snooping when vlan filtering is disabled" 662} 663 664vlmc_mcast_toggle_test() 665{ 666 RET=0 667 668 ip link add name br1-mcast up type bridge mcast_snooping 1 mcast_querier 1 vlan_filtering 1 669 ip link add name dummy1-mcast up master br1-mcast type dummy 670 671 # Enabling per-VLAN multicast snooping should disable the per-port 672 # multicast context on "dummy1-mcast". 673 ip link set dev br1-mcast type bridge mcast_vlan_snooping 1 674 675 # Toggling multicast snooping on the bridge should not affect the 676 # per-port multicast context on "dummy1-mcast" given that per-VLAN 677 # multicast snooping is enabled. 678 ip link set dev br1-mcast type bridge mcast_snooping 0 679 ip link set dev br1-mcast type bridge mcast_snooping 1 680 681 # If both the per-port and per-{port, VLAN} multicast contexts are 682 # enabled on "dummy1-mcast", removing it from the bridge will result 683 # in a splat. 684 ip link set dev dummy1-mcast nomaster 685 686 log_test "Toggling mcast snooping with per-VLAN mcast snooping enabled" 687 688 ip link del dev dummy1-mcast 689 ip link del dev br1-mcast 690} 691 692trap cleanup EXIT 693 694setup_prepare 695setup_wait 696 697tests_run 698 699exit $EXIT_STATUS 700