1#!/bin/bash 2# SPDX-License-Identifier: GPL-2.0 3 4# This test is for checking IPv4 and IPv6 FIB rules API 5 6source lib.sh 7ret=0 8PAUSE_ON_FAIL=${PAUSE_ON_FAIL:=no} 9 10RTABLE=100 11RTABLE_PEER=101 12RTABLE_VRF=102 13GW_IP4=192.51.100.2 14SRC_IP=192.51.100.3 15GW_IP6=2001:db8:1::2 16SRC_IP6=2001:db8:1::3 17 18DEV_ADDR=192.51.100.1 19DEV_ADDR6=2001:db8:1::1 20DEV=dummy0 21TESTS=" 22 fib_rule6 23 fib_rule4 24 fib_rule6_connect 25 fib_rule4_connect 26 fib_rule6_vrf 27 fib_rule4_vrf 28" 29 30SELFTEST_PATH="" 31 32log_test() 33{ 34 local rc=$1 35 local expected=$2 36 local msg="$3" 37 38 if [ ${rc} -eq ${expected} ]; then 39 nsuccess=$((nsuccess+1)) 40 printf " TEST: %-60s [ OK ]\n" "${msg}" 41 else 42 ret=1 43 nfail=$((nfail+1)) 44 printf " TEST: %-60s [FAIL]\n" "${msg}" 45 if [ "${PAUSE_ON_FAIL}" = "yes" ]; then 46 echo 47 echo "hit enter to continue, 'q' to quit" 48 read a 49 [ "$a" = "q" ] && exit 1 50 fi 51 fi 52} 53 54setup() 55{ 56 set -e 57 setup_ns testns 58 IP="ip -netns $testns" 59 60 $IP link add dummy0 type dummy 61 $IP link set dev dummy0 up 62 $IP address add $DEV_ADDR/24 dev dummy0 63 $IP -6 address add $DEV_ADDR6/64 dev dummy0 64 65 set +e 66} 67 68cleanup() 69{ 70 $IP link del dev dummy0 &> /dev/null 71 cleanup_ns $testns 72} 73 74setup_peer() 75{ 76 set -e 77 78 setup_ns peerns 79 IP_PEER="ip -netns $peerns" 80 $IP_PEER link set dev lo up 81 82 ip link add name veth0 netns $testns type veth \ 83 peer name veth1 netns $peerns 84 $IP link set dev veth0 up 85 $IP_PEER link set dev veth1 up 86 87 $IP address add 192.0.2.10 peer 192.0.2.11/32 dev veth0 88 $IP_PEER address add 192.0.2.11 peer 192.0.2.10/32 dev veth1 89 90 $IP address add 2001:db8::10 peer 2001:db8::11/128 dev veth0 nodad 91 $IP_PEER address add 2001:db8::11 peer 2001:db8::10/128 dev veth1 nodad 92 93 $IP_PEER address add 198.51.100.11/32 dev lo 94 $IP route add table $RTABLE_PEER 198.51.100.11/32 via 192.0.2.11 95 96 $IP_PEER address add 2001:db8::1:11/128 dev lo 97 $IP route add table $RTABLE_PEER 2001:db8::1:11/128 via 2001:db8::11 98 99 set +e 100} 101 102cleanup_peer() 103{ 104 $IP link del dev veth0 105 ip netns del $peerns 106} 107 108setup_vrf() 109{ 110 $IP link add name vrf0 up type vrf table $RTABLE_VRF 111 $IP link set dev $DEV master vrf0 112} 113 114cleanup_vrf() 115{ 116 $IP link del dev vrf0 117} 118 119fib_check_iproute_support() 120{ 121 ip rule help 2>&1 | grep -q $1 122 if [ $? -ne 0 ]; then 123 echo "SKIP: iproute2 iprule too old, missing $1 match" 124 return 1 125 fi 126 127 ip route get help 2>&1 | grep -q $2 128 if [ $? -ne 0 ]; then 129 echo "SKIP: iproute2 get route too old, missing $2 match" 130 return 1 131 fi 132 133 return 0 134} 135 136fib_rule6_del() 137{ 138 $IP -6 rule del $1 139 log_test $? 0 "rule6 del $1" 140} 141 142fib_rule6_del_by_pref() 143{ 144 pref=$($IP -6 rule show $1 table $RTABLE | cut -d ":" -f 1) 145 $IP -6 rule del pref $pref 146} 147 148fib_rule6_test_match_n_redirect() 149{ 150 local match="$1" 151 local getmatch="$2" 152 local getnomatch="$3" 153 local description="$4" 154 local nomatch_description="$5" 155 156 $IP -6 rule add $match table $RTABLE 157 $IP -6 route get $GW_IP6 $getmatch | grep -q "table $RTABLE" 158 log_test $? 0 "rule6 check: $description" 159 160 $IP -6 route get $GW_IP6 $getnomatch 2>&1 | grep -q "table $RTABLE" 161 log_test $? 1 "rule6 check: $nomatch_description" 162 163 fib_rule6_del_by_pref "$match" 164 log_test $? 0 "rule6 del by pref: $description" 165} 166 167fib_rule6_test_reject() 168{ 169 local match="$1" 170 local rc 171 172 $IP -6 rule add $match table $RTABLE 2>/dev/null 173 rc=$? 174 log_test $rc 2 "rule6 check: $match" 175 176 if [ $rc -eq 0 ]; then 177 $IP -6 rule del $match table $RTABLE 178 fi 179} 180 181fib_rule6_test() 182{ 183 local ext_name=$1; shift 184 local getnomatch 185 local getmatch 186 local match 187 local cnt 188 189 echo 190 echo "IPv6 FIB rule tests $ext_name" 191 192 # setup the fib rule redirect route 193 $IP -6 route add table $RTABLE default via $GW_IP6 dev $DEV onlink 194 195 match="oif $DEV" 196 getnomatch="oif lo" 197 fib_rule6_test_match_n_redirect "$match" "$match" "$getnomatch" \ 198 "oif redirect to table" "oif no redirect to table" 199 200 match="from $SRC_IP6 iif $DEV" 201 getnomatch="from $SRC_IP6 iif lo" 202 fib_rule6_test_match_n_redirect "$match" "$match" "$getnomatch" \ 203 "iif redirect to table" "iif no redirect to table" 204 205 # Reject dsfield (tos) options which have ECN bits set 206 for cnt in $(seq 1 3); do 207 match="dsfield $cnt" 208 fib_rule6_test_reject "$match" 209 done 210 211 # Don't take ECN bits into account when matching on dsfield 212 match="tos 0x10" 213 for cnt in "0x10" "0x11" "0x12" "0x13"; do 214 # Using option 'tos' instead of 'dsfield' as old iproute2 215 # versions don't support 'dsfield' in ip rule show. 216 getmatch="tos $cnt" 217 getnomatch="tos 0x20" 218 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 219 "$getnomatch" "$getmatch redirect to table" \ 220 "$getnomatch no redirect to table" 221 done 222 223 # Re-test TOS matching, but with input routes since they are handled 224 # differently from output routes. 225 match="tos 0x10" 226 for cnt in "0x10" "0x11" "0x12" "0x13"; do 227 getmatch="tos $cnt" 228 getnomatch="tos 0x20" 229 fib_rule6_test_match_n_redirect "$match" \ 230 "from $SRC_IP6 iif $DEV $getmatch" \ 231 "from $SRC_IP6 iif $DEV $getnomatch" \ 232 "iif $getmatch redirect to table" \ 233 "iif $getnomatch no redirect to table" 234 done 235 236 match="fwmark 0x64" 237 getmatch="mark 0x64" 238 getnomatch="mark 0x63" 239 fib_rule6_test_match_n_redirect "$match" "$getmatch" "$getnomatch" \ 240 "fwmark redirect to table" "fwmark no redirect to table" 241 242 fib_check_iproute_support "uidrange" "uid" 243 if [ $? -eq 0 ]; then 244 match="uidrange 100-100" 245 getmatch="uid 100" 246 getnomatch="uid 101" 247 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 248 "$getnomatch" "uid redirect to table" \ 249 "uid no redirect to table" 250 fi 251 252 fib_check_iproute_support "sport" "sport" 253 if [ $? -eq 0 ]; then 254 match="sport 666 dport 777" 255 getnomatch="sport 667 dport 778" 256 fib_rule6_test_match_n_redirect "$match" "$match" \ 257 "$getnomatch" "sport and dport redirect to table" \ 258 "sport and dport no redirect to table" 259 260 match="sport 100-200 dport 300-400" 261 getmatch="sport 100 dport 400" 262 getnomatch="sport 100 dport 401" 263 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 264 "$getnomatch" \ 265 "sport and dport range redirect to table" \ 266 "sport and dport range no redirect to table" 267 fi 268 269 ip rule help 2>&1 | grep sport | grep -q MASK 270 if [ $? -eq 0 ]; then 271 match="sport 0x0f00/0xff00 dport 0x000f/0x00ff" 272 getmatch="sport 0x0f11 dport 0x220f" 273 getnomatch="sport 0x1f11 dport 0x221f" 274 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 275 "$getnomatch" "sport and dport masked redirect to table" \ 276 "sport and dport masked no redirect to table" 277 fi 278 279 fib_check_iproute_support "ipproto" "ipproto" 280 if [ $? -eq 0 ]; then 281 match="ipproto tcp" 282 getnomatch="ipproto udp" 283 fib_rule6_test_match_n_redirect "$match" "$match" \ 284 "$getnomatch" "ipproto tcp match" "ipproto udp no match" 285 fi 286 287 fib_check_iproute_support "ipproto" "ipproto" 288 if [ $? -eq 0 ]; then 289 match="ipproto ipv6-icmp" 290 getnomatch="ipproto tcp" 291 fib_rule6_test_match_n_redirect "$match" "$match" \ 292 "$getnomatch" "ipproto ipv6-icmp match" \ 293 "ipproto ipv6-tcp no match" 294 fi 295 296 fib_check_iproute_support "dscp" "tos" 297 if [ $? -eq 0 ]; then 298 match="dscp 0x3f" 299 getmatch="tos 0xfc" 300 getnomatch="tos 0xf4" 301 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 302 "$getnomatch" "dscp redirect to table" \ 303 "dscp no redirect to table" 304 305 match="dscp 0x3f" 306 getmatch="from $SRC_IP6 iif $DEV tos 0xfc" 307 getnomatch="from $SRC_IP6 iif $DEV tos 0xf4" 308 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 309 "$getnomatch" "iif dscp redirect to table" \ 310 "iif dscp no redirect to table" 311 fi 312 313 ip rule help 2>&1 | grep -q "DSCP\[/MASK\]" 314 if [ $? -eq 0 ]; then 315 match="dscp 0x0f/0x0f" 316 tosmatch=$(printf 0x"%x" $((0x1f << 2))) 317 tosnomatch=$(printf 0x"%x" $((0x1e << 2))) 318 getmatch="tos $tosmatch" 319 getnomatch="tos $tosnomatch" 320 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 321 "$getnomatch" "dscp masked redirect to table" \ 322 "dscp masked no redirect to table" 323 324 match="dscp 0x0f/0x0f" 325 getmatch="from $SRC_IP6 iif $DEV tos $tosmatch" 326 getnomatch="from $SRC_IP6 iif $DEV tos $tosnomatch" 327 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 328 "$getnomatch" "iif dscp masked redirect to table" \ 329 "iif dscp masked no redirect to table" 330 fi 331 332 fib_check_iproute_support "flowlabel" "flowlabel" 333 if [ $? -eq 0 ]; then 334 match="flowlabel 0xfffff" 335 getmatch="flowlabel 0xfffff" 336 getnomatch="flowlabel 0xf" 337 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 338 "$getnomatch" "flowlabel redirect to table" \ 339 "flowlabel no redirect to table" 340 341 match="flowlabel 0xfffff" 342 getmatch="from $SRC_IP6 iif $DEV flowlabel 0xfffff" 343 getnomatch="from $SRC_IP6 iif $DEV flowlabel 0xf" 344 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 345 "$getnomatch" "iif flowlabel redirect to table" \ 346 "iif flowlabel no redirect to table" 347 348 match="flowlabel 0x08000/0x08000" 349 getmatch="flowlabel 0xfffff" 350 getnomatch="flowlabel 0xf7fff" 351 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 352 "$getnomatch" "flowlabel masked redirect to table" \ 353 "flowlabel masked no redirect to table" 354 355 match="flowlabel 0x08000/0x08000" 356 getmatch="from $SRC_IP6 iif $DEV flowlabel 0xfffff" 357 getnomatch="from $SRC_IP6 iif $DEV flowlabel 0xf7fff" 358 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 359 "$getnomatch" "iif flowlabel masked redirect to table" \ 360 "iif flowlabel masked no redirect to table" 361 fi 362 363 $IP link show dev $DEV | grep -q vrf0 364 if [ $? -eq 0 ]; then 365 match="oif vrf0" 366 getmatch="oif $DEV" 367 getnomatch="oif lo" 368 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 369 "$getnomatch" "VRF oif redirect to table" \ 370 "VRF oif no redirect to table" 371 372 match="from $SRC_IP6 iif vrf0" 373 getmatch="from $SRC_IP6 iif $DEV" 374 getnomatch="from $SRC_IP6 iif lo" 375 fib_rule6_test_match_n_redirect "$match" "$getmatch" \ 376 "$getnomatch" "VRF iif redirect to table" \ 377 "VRF iif no redirect to table" 378 fi 379} 380 381fib_rule6_vrf_test() 382{ 383 setup_vrf 384 fib_rule6_test "- with VRF" 385 cleanup_vrf 386} 387 388# Verify that the IPV6_TCLASS option of UDPv6 and TCPv6 sockets is properly 389# taken into account when connecting the socket and when sending packets. 390fib_rule6_connect_test() 391{ 392 local dsfield 393 394 echo 395 echo "IPv6 FIB rule connect tests" 396 397 setup_peer 398 $IP -6 rule add dsfield 0x04 table $RTABLE_PEER 399 400 # Combine the base DS Field value (0x04) with all possible ECN values 401 # (Not-ECT: 0, ECT(1): 1, ECT(0): 2, CE: 3). 402 # The ECN bits shouldn't influence the result of the test. 403 for dsfield in 0x04 0x05 0x06 0x07; do 404 nettest -q -6 -B -t 5 -N $testns -O $peerns -U -D \ 405 -Q "${dsfield}" -l 2001:db8::1:11 -r 2001:db8::1:11 406 log_test $? 0 "rule6 dsfield udp connect (dsfield ${dsfield})" 407 408 nettest -q -6 -B -t 5 -N $testns -O $peerns -Q "${dsfield}" \ 409 -l 2001:db8::1:11 -r 2001:db8::1:11 410 log_test $? 0 "rule6 dsfield tcp connect (dsfield ${dsfield})" 411 done 412 413 # Check that UDP and TCP connections fail when using a DS Field that 414 # does not match the previously configured FIB rule. 415 nettest -q -6 -B -t 5 -N $testns -O $peerns -U -D \ 416 -Q 0x20 -l 2001:db8::1:11 -r 2001:db8::1:11 417 log_test $? 1 "rule6 dsfield udp no connect (dsfield 0x20)" 418 419 nettest -q -6 -B -t 5 -N $testns -O $peerns -Q 0x20 \ 420 -l 2001:db8::1:11 -r 2001:db8::1:11 421 log_test $? 1 "rule6 dsfield tcp no connect (dsfield 0x20)" 422 423 $IP -6 rule del dsfield 0x04 table $RTABLE_PEER 424 425 ip rule help 2>&1 | grep -q dscp 426 if [ $? -ne 0 ]; then 427 echo "SKIP: iproute2 iprule too old, missing dscp match" 428 cleanup_peer 429 return 430 fi 431 432 $IP -6 rule add dscp 0x3f table $RTABLE_PEER 433 434 nettest -q -6 -B -t 5 -N $testns -O $peerns -U -D -Q 0xfc \ 435 -l 2001:db8::1:11 -r 2001:db8::1:11 436 log_test $? 0 "rule6 dscp udp connect" 437 438 nettest -q -6 -B -t 5 -N $testns -O $peerns -Q 0xfc \ 439 -l 2001:db8::1:11 -r 2001:db8::1:11 440 log_test $? 0 "rule6 dscp tcp connect" 441 442 nettest -q -6 -B -t 5 -N $testns -O $peerns -U -D -Q 0xf4 \ 443 -l 2001:db8::1:11 -r 2001:db8::1:11 444 log_test $? 1 "rule6 dscp udp no connect" 445 446 nettest -q -6 -B -t 5 -N $testns -O $peerns -Q 0xf4 \ 447 -l 2001:db8::1:11 -r 2001:db8::1:11 448 log_test $? 1 "rule6 dscp tcp no connect" 449 450 $IP -6 rule del dscp 0x3f table $RTABLE_PEER 451 452 cleanup_peer 453} 454 455fib_rule4_del() 456{ 457 $IP rule del $1 458 log_test $? 0 "del $1" 459} 460 461fib_rule4_del_by_pref() 462{ 463 pref=$($IP rule show $1 table $RTABLE | cut -d ":" -f 1) 464 $IP rule del pref $pref 465} 466 467fib_rule4_test_match_n_redirect() 468{ 469 local match="$1" 470 local getmatch="$2" 471 local getnomatch="$3" 472 local description="$4" 473 local nomatch_description="$5" 474 475 $IP rule add $match table $RTABLE 476 $IP route get $GW_IP4 $getmatch | grep -q "table $RTABLE" 477 log_test $? 0 "rule4 check: $description" 478 479 $IP route get $GW_IP4 $getnomatch 2>&1 | grep -q "table $RTABLE" 480 log_test $? 1 "rule4 check: $nomatch_description" 481 482 fib_rule4_del_by_pref "$match" 483 log_test $? 0 "rule4 del by pref: $description" 484} 485 486fib_rule4_test_reject() 487{ 488 local match="$1" 489 local rc 490 491 $IP rule add $match table $RTABLE 2>/dev/null 492 rc=$? 493 log_test $rc 2 "rule4 check: $match" 494 495 if [ $rc -eq 0 ]; then 496 $IP rule del $match table $RTABLE 497 fi 498} 499 500fib_rule4_test() 501{ 502 local ext_name=$1; shift 503 local getnomatch 504 local getmatch 505 local match 506 local cnt 507 508 echo 509 echo "IPv4 FIB rule tests $ext_name" 510 511 # setup the fib rule redirect route 512 $IP route add table $RTABLE default via $GW_IP4 dev $DEV onlink 513 514 match="oif $DEV" 515 getnomatch="oif lo" 516 fib_rule4_test_match_n_redirect "$match" "$match" "$getnomatch" \ 517 "oif redirect to table" "oif no redirect to table" 518 519 ip netns exec $testns sysctl -qw net.ipv4.ip_forward=1 520 match="from $SRC_IP iif $DEV" 521 getnomatch="from $SRC_IP iif lo" 522 fib_rule4_test_match_n_redirect "$match" "$match" "$getnomatch" \ 523 "iif redirect to table" "iif no redirect to table" 524 525 # Reject dsfield (tos) options which have ECN bits set 526 for cnt in $(seq 1 3); do 527 match="dsfield $cnt" 528 fib_rule4_test_reject "$match" 529 done 530 531 # Don't take ECN bits into account when matching on dsfield 532 match="tos 0x10" 533 for cnt in "0x10" "0x11" "0x12" "0x13"; do 534 # Using option 'tos' instead of 'dsfield' as old iproute2 535 # versions don't support 'dsfield' in ip rule show. 536 getmatch="tos $cnt" 537 getnomatch="tos 0x20" 538 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 539 "$getnomatch" "$getmatch redirect to table" \ 540 "$getnomatch no redirect to table" 541 done 542 543 # Re-test TOS matching, but with input routes since they are handled 544 # differently from output routes. 545 match="tos 0x10" 546 for cnt in "0x10" "0x11" "0x12" "0x13"; do 547 getmatch="tos $cnt" 548 getnomatch="tos 0x20" 549 fib_rule4_test_match_n_redirect "$match" \ 550 "from $SRC_IP iif $DEV $getmatch" \ 551 "from $SRC_IP iif $DEV $getnomatch" \ 552 "iif $getmatch redirect to table" \ 553 "iif $getnomatch no redirect to table" 554 done 555 556 match="fwmark 0x64" 557 getmatch="mark 0x64" 558 getnomatch="mark 0x63" 559 fib_rule4_test_match_n_redirect "$match" "$getmatch" "$getnomatch" \ 560 "fwmark redirect to table" "fwmark no redirect to table" 561 562 fib_check_iproute_support "uidrange" "uid" 563 if [ $? -eq 0 ]; then 564 match="uidrange 100-100" 565 getmatch="uid 100" 566 getnomatch="uid 101" 567 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 568 "$getnomatch" "uid redirect to table" \ 569 "uid no redirect to table" 570 fi 571 572 fib_check_iproute_support "sport" "sport" 573 if [ $? -eq 0 ]; then 574 match="sport 666 dport 777" 575 getnomatch="sport 667 dport 778" 576 fib_rule4_test_match_n_redirect "$match" "$match" \ 577 "$getnomatch" "sport and dport redirect to table" \ 578 "sport and dport no redirect to table" 579 580 match="sport 100-200 dport 300-400" 581 getmatch="sport 100 dport 400" 582 getnomatch="sport 100 dport 401" 583 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 584 "$getnomatch" \ 585 "sport and dport range redirect to table" \ 586 "sport and dport range no redirect to table" 587 fi 588 589 ip rule help 2>&1 | grep sport | grep -q MASK 590 if [ $? -eq 0 ]; then 591 match="sport 0x0f00/0xff00 dport 0x000f/0x00ff" 592 getmatch="sport 0x0f11 dport 0x220f" 593 getnomatch="sport 0x1f11 dport 0x221f" 594 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 595 "$getnomatch" "sport and dport masked redirect to table" \ 596 "sport and dport masked no redirect to table" 597 fi 598 599 fib_check_iproute_support "ipproto" "ipproto" 600 if [ $? -eq 0 ]; then 601 match="ipproto tcp" 602 getnomatch="ipproto udp" 603 fib_rule4_test_match_n_redirect "$match" "$match" \ 604 "$getnomatch" "ipproto tcp match" \ 605 "ipproto udp no match" 606 fi 607 608 fib_check_iproute_support "ipproto" "ipproto" 609 if [ $? -eq 0 ]; then 610 match="ipproto icmp" 611 getnomatch="ipproto tcp" 612 fib_rule4_test_match_n_redirect "$match" "$match" \ 613 "$getnomatch" "ipproto icmp match" \ 614 "ipproto tcp no match" 615 fi 616 617 fib_check_iproute_support "dscp" "tos" 618 if [ $? -eq 0 ]; then 619 match="dscp 0x3f" 620 getmatch="tos 0xfc" 621 getnomatch="tos 0xf4" 622 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 623 "$getnomatch" "dscp redirect to table" \ 624 "dscp no redirect to table" 625 626 match="dscp 0x3f" 627 getmatch="from $SRC_IP iif $DEV tos 0xfc" 628 getnomatch="from $SRC_IP iif $DEV tos 0xf4" 629 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 630 "$getnomatch" "iif dscp redirect to table" \ 631 "iif dscp no redirect to table" 632 fi 633 634 ip rule help 2>&1 | grep -q "DSCP\[/MASK\]" 635 if [ $? -eq 0 ]; then 636 match="dscp 0x0f/0x0f" 637 tosmatch=$(printf 0x"%x" $((0x1f << 2))) 638 tosnomatch=$(printf 0x"%x" $((0x1e << 2))) 639 getmatch="tos $tosmatch" 640 getnomatch="tos $tosnomatch" 641 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 642 "$getnomatch" "dscp masked redirect to table" \ 643 "dscp masked no redirect to table" 644 645 match="dscp 0x0f/0x0f" 646 getmatch="from $SRC_IP iif $DEV tos $tosmatch" 647 getnomatch="from $SRC_IP iif $DEV tos $tosnomatch" 648 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 649 "$getnomatch" "iif dscp masked redirect to table" \ 650 "iif dscp masked no redirect to table" 651 fi 652 653 $IP link show dev $DEV | grep -q vrf0 654 if [ $? -eq 0 ]; then 655 match="oif vrf0" 656 getmatch="oif $DEV" 657 getnomatch="oif lo" 658 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 659 "$getnomatch" "VRF oif redirect to table" \ 660 "VRF oif no redirect to table" 661 662 match="from $SRC_IP iif vrf0" 663 getmatch="from $SRC_IP iif $DEV" 664 getnomatch="from $SRC_IP iif lo" 665 fib_rule4_test_match_n_redirect "$match" "$getmatch" \ 666 "$getnomatch" "VRF iif redirect to table" \ 667 "VRF iif no redirect to table" 668 fi 669} 670 671fib_rule4_vrf_test() 672{ 673 setup_vrf 674 fib_rule4_test "- with VRF" 675 cleanup_vrf 676} 677 678# Verify that the IP_TOS option of UDPv4 and TCPv4 sockets is properly taken 679# into account when connecting the socket and when sending packets. 680fib_rule4_connect_test() 681{ 682 local dsfield 683 684 echo 685 echo "IPv4 FIB rule connect tests" 686 687 setup_peer 688 $IP -4 rule add dsfield 0x04 table $RTABLE_PEER 689 690 # Combine the base DS Field value (0x04) with all possible ECN values 691 # (Not-ECT: 0, ECT(1): 1, ECT(0): 2, CE: 3). 692 # The ECN bits shouldn't influence the result of the test. 693 for dsfield in 0x04 0x05 0x06 0x07; do 694 nettest -q -B -t 5 -N $testns -O $peerns -D -U -Q "${dsfield}" \ 695 -l 198.51.100.11 -r 198.51.100.11 696 log_test $? 0 "rule4 dsfield udp connect (dsfield ${dsfield})" 697 698 nettest -q -B -t 5 -N $testns -O $peerns -Q "${dsfield}" \ 699 -l 198.51.100.11 -r 198.51.100.11 700 log_test $? 0 "rule4 dsfield tcp connect (dsfield ${dsfield})" 701 done 702 703 # Check that UDP and TCP connections fail when using a DS Field that 704 # does not match the previously configured FIB rule. 705 nettest -q -B -t 5 -N $testns -O $peerns -D -U -Q 0x20 \ 706 -l 198.51.100.11 -r 198.51.100.11 707 log_test $? 1 "rule4 dsfield udp no connect (dsfield 0x20)" 708 709 nettest -q -B -t 5 -N $testns -O $peerns -Q 0x20 \ 710 -l 198.51.100.11 -r 198.51.100.11 711 log_test $? 1 "rule4 dsfield tcp no connect (dsfield 0x20)" 712 713 $IP -4 rule del dsfield 0x04 table $RTABLE_PEER 714 715 ip rule help 2>&1 | grep -q dscp 716 if [ $? -ne 0 ]; then 717 echo "SKIP: iproute2 iprule too old, missing dscp match" 718 cleanup_peer 719 return 720 fi 721 722 $IP -4 rule add dscp 0x3f table $RTABLE_PEER 723 724 nettest -q -B -t 5 -N $testns -O $peerns -D -U -Q 0xfc \ 725 -l 198.51.100.11 -r 198.51.100.11 726 log_test $? 0 "rule4 dscp udp connect" 727 728 nettest -q -B -t 5 -N $testns -O $peerns -Q 0xfc \ 729 -l 198.51.100.11 -r 198.51.100.11 730 log_test $? 0 "rule4 dscp tcp connect" 731 732 nettest -q -B -t 5 -N $testns -O $peerns -D -U -Q 0xf4 \ 733 -l 198.51.100.11 -r 198.51.100.11 734 log_test $? 1 "rule4 dscp udp no connect" 735 736 nettest -q -B -t 5 -N $testns -O $peerns -Q 0xf4 \ 737 -l 198.51.100.11 -r 198.51.100.11 738 log_test $? 1 "rule4 dscp tcp no connect" 739 740 $IP -4 rule del dscp 0x3f table $RTABLE_PEER 741 742 cleanup_peer 743} 744################################################################################ 745# usage 746 747usage() 748{ 749 cat <<EOF 750usage: ${0##*/} OPTS 751 752 -t <test> Test(s) to run (default: all) 753 (options: $TESTS) 754EOF 755} 756 757################################################################################ 758# main 759 760while getopts ":t:h" opt; do 761 case $opt in 762 t) TESTS=$OPTARG;; 763 h) usage; exit 0;; 764 *) usage; exit 1;; 765 esac 766done 767 768if [ "$(id -u)" -ne 0 ];then 769 echo "SKIP: Need root privileges" 770 exit $ksft_skip 771fi 772 773if [ ! -x "$(command -v ip)" ]; then 774 echo "SKIP: Could not run test without ip tool" 775 exit $ksft_skip 776fi 777 778check_gen_prog "nettest" 779 780# start clean 781cleanup &> /dev/null 782setup 783for t in $TESTS 784do 785 case $t in 786 fib_rule6_test|fib_rule6) fib_rule6_test;; 787 fib_rule4_test|fib_rule4) fib_rule4_test;; 788 fib_rule6_connect_test|fib_rule6_connect) fib_rule6_connect_test;; 789 fib_rule4_connect_test|fib_rule4_connect) fib_rule4_connect_test;; 790 fib_rule6_vrf_test|fib_rule6_vrf) fib_rule6_vrf_test;; 791 fib_rule4_vrf_test|fib_rule4_vrf) fib_rule4_vrf_test;; 792 793 help) echo "Test names: $TESTS"; exit 0;; 794 795 esac 796done 797cleanup 798 799if [ "$TESTS" != "none" ]; then 800 printf "\nTests passed: %3d\n" ${nsuccess} 801 printf "Tests failed: %3d\n" ${nfail} 802fi 803 804exit $ret 805