1#!/bin/bash 2# 3# This test is for bridge 'brouting', i.e. make some packets being routed 4# rather than getting bridged even though they arrive on interface that is 5# part of a bridge. 6 7# eth0 br0 eth0 8# setup is: ns1 <-> nsbr <-> ns2 9 10source lib.sh 11 12if ! ebtables -V > /dev/null 2>&1;then 13 echo "SKIP: Could not run test without ebtables" 14 exit $ksft_skip 15fi 16 17cleanup() { 18 cleanup_all_ns 19} 20 21trap cleanup EXIT 22 23setup_ns nsbr ns1 ns2 24 25if ! ip link add veth0 netns "$nsbr" type veth peer name eth0 netns "$ns1"; then 26 echo "SKIP: Can't create veth device" 27 exit $ksft_skip 28fi 29ip link add veth1 netns "$nsbr" type veth peer name eth0 netns "$ns2" 30 31if ! ip -net "$nsbr" link add br0 type bridge; then 32 echo "SKIP: Can't create bridge br0" 33 exit $ksft_skip 34fi 35 36ip -net "$nsbr" link set veth0 up 37ip -net "$nsbr" link set veth1 up 38 39ip -net "$nsbr" link set veth0 master br0 40ip -net "$nsbr" link set veth1 master br0 41ip -net "$nsbr" link set br0 up 42ip -net "$nsbr" addr add 10.0.0.1/24 dev br0 43 44# place both in same subnet, ${ns1} and ${ns2} connected via ${nsbr}:br0 45ip -net "$ns1" link set eth0 up 46ip -net "$ns2" link set eth0 up 47ip -net "$ns1" addr add 10.0.0.11/24 dev eth0 48ip -net "$ns2" addr add 10.0.0.12/24 dev eth0 49 50test_ebtables_broute() 51{ 52 # redirect is needed so the dstmac is rewritten to the bridge itself, 53 # ip stack won't process OTHERHOST (foreign unicast mac) packets. 54 if ! ip netns exec "$nsbr" ebtables -t broute -A BROUTING -p ipv4 --ip-protocol icmp -j redirect --redirect-target=DROP; then 55 echo "SKIP: Could not add ebtables broute redirect rule" 56 return $ksft_skip 57 fi 58 59 ip netns exec "$nsbr" sysctl -q net.ipv4.conf.veth0.forwarding=0 60 61 # ping net${ns1}, expected to not work (ip forwarding is off) 62 if ip netns exec "$ns1" ping -q -c 1 10.0.0.12 -W 0.5 > /dev/null 2>&1; then 63 echo "ERROR: ping works, should have failed" 1>&2 64 return 1 65 fi 66 67 # enable forwarding on both interfaces. 68 # neither needs an ip address, but at least the bridge needs 69 # an ip address in same network segment as ${ns1} and ${ns2} (${nsbr} 70 # needs to be able to determine route for to-be-forwarded packet). 71 ip netns exec "$nsbr" sysctl -q net.ipv4.conf.veth0.forwarding=1 72 ip netns exec "$nsbr" sysctl -q net.ipv4.conf.veth1.forwarding=1 73 74 if ! ip netns exec "$ns1" ping -q -c 1 10.0.0.12 > /dev/null; then 75 echo "ERROR: ping did not work, but it should (broute+forward)" 1>&2 76 return 1 77 fi 78 79 echo "PASS: ${ns1}/${ns2} connectivity with active broute rule" 80 ip netns exec "$nsbr" ebtables -t broute -F 81 82 # ping net${ns1}, expected to work (frames are bridged) 83 if ! ip netns exec "$ns1" ping -q -c 1 10.0.0.12 > /dev/null; then 84 echo "ERROR: ping did not work, but it should (bridged)" 1>&2 85 return 1 86 fi 87 88 ip netns exec "$nsbr" ebtables -t filter -A FORWARD -p ipv4 --ip-protocol icmp -j DROP 89 90 # ping net${ns1}, expected to not work (DROP in bridge forward) 91 if ip netns exec "$ns1" ping -q -c 1 10.0.0.12 -W 0.5 > /dev/null 2>&1; then 92 echo "ERROR: ping works, should have failed (icmp forward drop)" 1>&2 93 return 1 94 fi 95 96 # re-activate brouter 97 ip netns exec "$nsbr" ebtables -t broute -A BROUTING -p ipv4 --ip-protocol icmp -j redirect --redirect-target=DROP 98 99 if ! ip netns exec "$ns2" ping -q -c 1 10.0.0.11 > /dev/null; then 100 echo "ERROR: ping did not work, but it should (broute+forward 2)" 1>&2 101 return 1 102 fi 103 104 echo "PASS: ${ns1}/${ns2} connectivity with active broute rule and bridge forward drop" 105 return 0 106} 107 108# test basic connectivity 109if ! ip netns exec "$ns1" ping -c 1 -q 10.0.0.12 > /dev/null; then 110 echo "ERROR: Could not reach ${ns2} from ${ns1}" 1>&2 111 exit 1 112fi 113 114if ! ip netns exec "$ns2" ping -c 1 -q 10.0.0.11 > /dev/null; then 115 echo "ERROR: Could not reach ${ns1} from ${ns2}" 1>&2 116 exit 1 117fi 118 119test_ebtables_broute 120exit $? 121