Home | History | Annotate | Line # | Download | only in arp
t_arp.sh revision 1.33
      1 #	$NetBSD: t_arp.sh,v 1.33 2017/06/28 08:17:50 ozaki-r Exp $
      2 #
      3 # Copyright (c) 2015 The NetBSD Foundation, Inc.
      4 # All rights reserved.
      5 #
      6 # Redistribution and use in source and binary forms, with or without
      7 # modification, are permitted provided that the following conditions
      8 # are met:
      9 # 1. Redistributions of source code must retain the above copyright
     10 #    notice, this list of conditions and the following disclaimer.
     11 # 2. Redistributions in binary form must reproduce the above copyright
     12 #    notice, this list of conditions and the following disclaimer in the
     13 #    documentation and/or other materials provided with the distribution.
     14 #
     15 # THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
     16 # ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
     17 # TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
     18 # PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
     19 # BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     20 # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     21 # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
     22 # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
     23 # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
     24 # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     25 # POSSIBILITY OF SUCH DAMAGE.
     26 #
     27 
     28 SOCKSRC=unix://commsock1
     29 SOCKDST=unix://commsock2
     30 IP4SRC=10.0.1.1
     31 IP4SRC2=10.0.1.5
     32 IP4NET=10.0.1.0
     33 IP4DST=10.0.1.2
     34 IP4DST_PROXYARP1=10.0.1.3
     35 IP4DST_PROXYARP2=10.0.1.4
     36 
     37 DEBUG=${DEBUG:-false}
     38 TIMEOUT=1
     39 
     40 atf_test_case arp_cache_expiration_5s cleanup
     41 atf_test_case arp_cache_expiration_10s cleanup
     42 atf_test_case arp_command cleanup
     43 atf_test_case arp_garp cleanup
     44 atf_test_case arp_cache_overwriting cleanup
     45 atf_test_case arp_proxy_arp_pub cleanup
     46 atf_test_case arp_proxy_arp_pubproxy cleanup
     47 atf_test_case arp_link_activation cleanup
     48 atf_test_case arp_static cleanup
     49 
     50 arp_cache_expiration_5s_head()
     51 {
     52 	atf_set "descr" "Tests for ARP cache expiration (5s)"
     53 	atf_set "require.progs" "rump_server"
     54 }
     55 
     56 arp_cache_expiration_10s_head()
     57 {
     58 	atf_set "descr" "Tests for ARP cache expiration (10s)"
     59 	atf_set "require.progs" "rump_server"
     60 }
     61 
     62 arp_command_head()
     63 {
     64 	atf_set "descr" "Tests for arp_commands of arp(8)"
     65 	atf_set "require.progs" "rump_server"
     66 }
     67 
     68 arp_garp_head()
     69 {
     70 	atf_set "descr" "Tests for GARP"
     71 	atf_set "require.progs" "rump_server"
     72 }
     73 
     74 arp_cache_overwriting_head()
     75 {
     76 	atf_set "descr" "Tests for behavior of overwriting ARP caches"
     77 	atf_set "require.progs" "rump_server"
     78 }
     79 
     80 arp_proxy_arp_pub_head()
     81 {
     82 	atf_set "descr" "Tests for Proxy ARP (pub)"
     83 	atf_set "require.progs" "rump_server"
     84 }
     85 
     86 arp_proxy_arp_pubproxy_head()
     87 {
     88 	atf_set "descr" "Tests for Proxy ARP (pub proxy)"
     89 	atf_set "require.progs" "rump_server"
     90 }
     91 
     92 arp_link_activation_head()
     93 {
     94 	atf_set "descr" "Tests for activating a new MAC address"
     95 	atf_set "require.progs" "rump_server"
     96 }
     97 
     98 arp_static_head()
     99 {
    100 
    101 	atf_set "descr" "Tests for static ARP entries"
    102 	atf_set "require.progs" "rump_server"
    103 }
    104 
    105 setup_dst_server()
    106 {
    107 
    108 	rump_server_add_iface $SOCKDST shmif0 bus1
    109 	export RUMP_SERVER=$SOCKDST
    110 	atf_check -s exit:0 rump.ifconfig shmif0 inet $IP4DST/24
    111 	atf_check -s exit:0 rump.ifconfig shmif0 up
    112 	atf_check -s exit:0 rump.ifconfig -w 10
    113 
    114 	$DEBUG && rump.ifconfig shmif0
    115 	$DEBUG && rump.arp -n -a
    116 	$DEBUG && rump.netstat -nr -f inet
    117 }
    118 
    119 setup_src_server()
    120 {
    121 	local keep=${1:-0}
    122 
    123 	export RUMP_SERVER=$SOCKSRC
    124 
    125 	# Adjust ARP parameters
    126 	if [ $keep != 0 ]; then
    127 		atf_check -s exit:0 -o ignore \
    128 		    rump.sysctl -w net.inet.arp.keep=$keep
    129 	fi
    130 
    131 	# Setup an interface
    132 	rump_server_add_iface $SOCKSRC shmif0 bus1
    133 	atf_check -s exit:0 rump.ifconfig shmif0 inet $IP4SRC/24
    134 	atf_check -s exit:0 rump.ifconfig shmif0 up
    135 	atf_check -s exit:0 rump.ifconfig -w 10
    136 
    137 	# Sanity check
    138 	$DEBUG && rump.ifconfig shmif0
    139 	$DEBUG && rump.arp -n -a
    140 	$DEBUG && rump.netstat -nr -f inet
    141 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4SRC
    142 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    143 }
    144 
    145 test_cache_expiration()
    146 {
    147 	local arp_keep=$1
    148 	local bonus=2
    149 
    150 	rump_server_start $SOCKSRC
    151 	rump_server_start $SOCKDST
    152 
    153 	setup_dst_server
    154 	setup_src_server $arp_keep
    155 
    156 	#
    157 	# Check if a cache is expired expectedly
    158 	#
    159 	export RUMP_SERVER=$SOCKSRC
    160 	atf_check -s exit:0 -o ignore rump.ping -n -w $TIMEOUT -c 1 $IP4DST
    161 
    162 	$DEBUG && rump.arp -n -a
    163 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4SRC
    164 	# Should be cached
    165 	atf_check -s exit:0 -o ignore rump.arp -n $IP4DST
    166 	$DEBUG && rump.netstat -nr -f inet
    167 	atf_check -s exit:0 -o match:"$IP4DST" rump.netstat -nr -f inet
    168 
    169 	atf_check -s exit:0 sleep $(($arp_keep + $bonus))
    170 
    171 	$DEBUG && rump.arp -n -a
    172 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4SRC
    173 	# Should be expired
    174 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    175 }
    176 
    177 arp_cache_expiration_5s_body()
    178 {
    179 
    180 	test_cache_expiration 5
    181 	rump_server_destroy_ifaces
    182 }
    183 
    184 arp_cache_expiration_10s_body()
    185 {
    186 
    187 	test_cache_expiration 10
    188 	rump_server_destroy_ifaces
    189 }
    190 
    191 check_arp_static_entry()
    192 {
    193 	local ip=$1
    194 	local mac=$2
    195 	local type=$3
    196 	local flags=
    197 
    198 	atf_check -s exit:0 -o match:"$mac" rump.arp -n $ip
    199 	if [ $type = 'permanent' ]; then
    200 		atf_check -s exit:0 -o match:'permanent' rump.arp -n $ip
    201 		check_route $ip "$mac" UHLS shmif0
    202 	else
    203 		atf_check -s exit:0 -o not-match:'permanent' rump.arp -n $ip
    204 		check_route $ip "$mac" UHL shmif0
    205 	fi
    206 }
    207 
    208 arp_command_body()
    209 {
    210 	local arp_keep=5
    211 	local bonus=2
    212 
    213 	rump_server_start $SOCKSRC
    214 	rump_server_start $SOCKDST
    215 
    216 	setup_dst_server
    217 	setup_src_server $arp_keep
    218 
    219 	export RUMP_SERVER=$SOCKSRC
    220 
    221 	# Add and delete a static entry
    222 	$DEBUG && rump.arp -n -a
    223 	atf_check -s exit:0 -o ignore rump.arp -s 10.0.1.10 b2:a0:20:00:00:10
    224 	$DEBUG && rump.arp -n -a
    225 	$DEBUG && rump.netstat -nr -f inet
    226 	check_arp_static_entry 10.0.1.10 'b2:a0:20:00:00:10' permanent
    227 	atf_check -s exit:0 -o ignore rump.arp -d 10.0.1.10
    228 	$DEBUG && rump.arp -n -a
    229 	$DEBUG && rump.netstat -nr -f inet
    230 	atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.10
    231 	check_route_no_entry 10.0.1.10
    232 
    233 	# Add multiple entries via a file
    234 	cat - > ./list <<-EOF
    235 	10.0.1.11 b2:a0:20:00:00:11
    236 	10.0.1.12 b2:a0:20:00:00:12
    237 	10.0.1.13 b2:a0:20:00:00:13
    238 	10.0.1.14 b2:a0:20:00:00:14
    239 	10.0.1.15 b2:a0:20:00:00:15
    240 	EOF
    241 	$DEBUG && rump.arp -n -a
    242 	$DEBUG && rump.netstat -nr -f inet
    243 	atf_check -s exit:0 -o ignore rump.arp -f ./list
    244 	$DEBUG && rump.arp -n -a
    245 	$DEBUG && rump.netstat -nr -f inet
    246 	check_arp_static_entry 10.0.1.11 'b2:a0:20:00:00:11' permanent
    247 	check_arp_static_entry 10.0.1.12 'b2:a0:20:00:00:12' permanent
    248 	check_arp_static_entry 10.0.1.13 'b2:a0:20:00:00:13' permanent
    249 	check_arp_static_entry 10.0.1.14 'b2:a0:20:00:00:14' permanent
    250 	check_arp_static_entry 10.0.1.15 'b2:a0:20:00:00:15' permanent
    251 
    252 	# Test arp -a
    253 	atf_check -s exit:0 -o match:'10.0.1.11' rump.arp -n -a
    254 	atf_check -s exit:0 -o match:'10.0.1.12' rump.arp -n -a
    255 	atf_check -s exit:0 -o match:'10.0.1.13' rump.arp -n -a
    256 	atf_check -s exit:0 -o match:'10.0.1.14' rump.arp -n -a
    257 	atf_check -s exit:0 -o match:'10.0.1.15' rump.arp -n -a
    258 
    259 	# Flush all entries
    260 	$DEBUG && rump.arp -n -a
    261 	$DEBUG && rump.netstat -nr -f inet
    262 	atf_check -s exit:0 -o ignore rump.arp -d -a
    263 	atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.11
    264 	atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.12
    265 	atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.13
    266 	atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.14
    267 	atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.15
    268 	atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.1
    269 	check_route_no_entry 10.0.1.11
    270 	check_route_no_entry 10.0.1.12
    271 	check_route_no_entry 10.0.1.13
    272 	check_route_no_entry 10.0.1.14
    273 	check_route_no_entry 10.0.1.15
    274 
    275 	# Test temp option
    276 	$DEBUG && rump.arp -n -a
    277 	atf_check -s exit:0 -o ignore rump.arp -s 10.0.1.10 b2:a0:20:00:00:10 temp
    278 	$DEBUG && rump.arp -n -a
    279 	$DEBUG && rump.netstat -nr -f inet
    280 	check_arp_static_entry 10.0.1.10 'b2:a0:20:00:00:10' temp
    281 
    282 	# Hm? the cache doesn't expire...
    283 	atf_check -s exit:0 sleep $(($arp_keep + $bonus))
    284 	$DEBUG && rump.arp -n -a
    285 	$DEBUG && rump.netstat -nr -f inet
    286 	#atf_check -s not-exit:0 -e ignore rump.arp -n 10.0.1.10
    287 
    288 	rump_server_destroy_ifaces
    289 }
    290 
    291 make_pkt_str_arpreq()
    292 {
    293 	local target=$1
    294 	local sender=$2
    295 	pkt="> ff:ff:ff:ff:ff:ff, ethertype ARP (0x0806), length 42:"
    296 	pkt="$pkt Request who-has $target tell $sender, length 28"
    297 	echo $pkt
    298 }
    299 
    300 arp_garp_body()
    301 {
    302 	local pkt=
    303 
    304 	rump_server_start $SOCKSRC
    305 
    306 	export RUMP_SERVER=$SOCKSRC
    307 
    308 	# Setup an interface
    309 	rump_server_add_iface $SOCKSRC shmif0 bus1
    310 	atf_check -s exit:0 rump.ifconfig shmif0 inet 10.0.0.1/24
    311 	atf_check -s exit:0 rump.ifconfig shmif0 inet 10.0.0.2/24 alias
    312 	atf_check -s exit:0 rump.ifconfig shmif0 up
    313 	$DEBUG && rump.ifconfig shmif0
    314 
    315 	atf_check -s exit:0 sleep 1
    316 	shmif_dumpbus -p - bus1 2>/dev/null| tcpdump -n -e -r - > ./out
    317 
    318 	# A GARP packet is sent for the primary address
    319 	pkt=$(make_pkt_str_arpreq 10.0.0.1 10.0.0.1)
    320 	atf_check -s exit:0 -x "cat ./out |grep -q '$pkt'"
    321 	# No GARP packet is sent for the alias address
    322 	pkt=$(make_pkt_str_arpreq 10.0.0.2 10.0.0.2)
    323 	atf_check -s not-exit:0 -x "cat ./out |grep -q '$pkt'"
    324 
    325 	atf_check -s exit:0 rump.ifconfig -w 10
    326 	atf_check -s exit:0 rump.ifconfig shmif0 inet 10.0.0.3/24
    327 	atf_check -s exit:0 rump.ifconfig shmif0 inet 10.0.0.4/24 alias
    328 
    329 	# No GARP packets are sent during IFF_UP
    330 	shmif_dumpbus -p - bus1 2>/dev/null| tcpdump -n -e -r - > ./out
    331 	pkt=$(make_pkt_str_arpreq 10.0.0.3 10.0.0.3)
    332 	atf_check -s not-exit:0 -x "cat ./out |grep -q '$pkt'"
    333 	pkt=$(make_pkt_str_arpreq 10.0.0.4 10.0.0.4)
    334 	atf_check -s not-exit:0 -x "cat ./out |grep -q '$pkt'"
    335 
    336 	rump_server_destroy_ifaces
    337 }
    338 
    339 arp_cache_overwriting_body()
    340 {
    341 	local bonus=2
    342 
    343 	rump_server_start $SOCKSRC
    344 	rump_server_start $SOCKDST
    345 
    346 	setup_dst_server
    347 	setup_src_server
    348 
    349 	export RUMP_SERVER=$SOCKSRC
    350 
    351 	# Cannot overwrite a permanent cache
    352 	atf_check -s exit:0 rump.arp -s $IP4DST b2:a0:20:00:00:ff
    353 	$DEBUG && rump.arp -n -a
    354 	atf_check -s not-exit:0 -e match:'File exists' \
    355 	    rump.arp -s $IP4DST b2:a0:20:00:00:fe
    356 	# cleanup
    357 	atf_check -s exit:0 rump.arp -d $IP4DST
    358 
    359 	atf_check -s exit:0 -o ignore rump.ping -n -w $TIMEOUT -c 1 $IP4DST
    360 	$DEBUG && rump.arp -n -a
    361 	# Can overwrite a dynamic cache
    362 	atf_check -s exit:0 -o ignore rump.arp -s $IP4DST b2:a0:20:00:00:00
    363 	$DEBUG && rump.arp -n -a
    364 	atf_check -s exit:0 -o match:'b2:a0:20:00:00:00' rump.arp -n $IP4DST
    365 	atf_check -s exit:0 -o match:'permanent' rump.arp -n $IP4DST
    366 
    367 	atf_check -s exit:0 -o ignore rump.arp -s 10.0.1.10 b2:a0:20:00:00:10 temp
    368 	$DEBUG && rump.arp -n -a
    369 	atf_check -s exit:0 -o match:'b2:a0:20:00:00:10' rump.arp -n 10.0.1.10
    370 	atf_check -s exit:0 -o not-match:'permanent' rump.arp -n 10.0.1.10
    371 	# Can overwrite a temp cache
    372 	atf_check -s exit:0 -o ignore rump.arp -s 10.0.1.10 b2:a0:20:00:00:ff
    373 	atf_check -s exit:0 -o match:'b2:a0:20:00:00:ff' rump.arp -n 10.0.1.10
    374 	$DEBUG && rump.arp -n -a
    375 
    376 	rump_server_destroy_ifaces
    377 }
    378 
    379 make_pkt_str_arprep()
    380 {
    381 	local ip=$1
    382 	local mac=$2
    383 	pkt="ethertype ARP (0x0806), length 42: "
    384 	pkt="Reply $ip is-at $mac, length 28"
    385 	echo $pkt
    386 }
    387 
    388 make_pkt_str_garp()
    389 {
    390 	local ip=$1
    391 	local mac=$2
    392 	local pkt=
    393 	pkt="$mac > ff:ff:ff:ff:ff:ff, ethertype ARP (0x0806),"
    394 	pkt="$pkt length 42: Request who-has $ip tell $ip, length 28"
    395 	echo $pkt
    396 }
    397 
    398 test_proxy_arp()
    399 {
    400 	local opts= title= flags=
    401 	local type=$1
    402 
    403 	rump_server_start $SOCKSRC
    404 	rump_server_start $SOCKDST tap
    405 
    406 	setup_dst_server
    407 	setup_src_server
    408 
    409 	export RUMP_SERVER=$SOCKDST
    410 	atf_check -s exit:0 -o ignore rump.sysctl -w net.inet.ip.forwarding=1
    411 	macaddr_dst=$(get_macaddr $SOCKDST shmif0)
    412 
    413 	if [ "$type" = "pub" ]; then
    414 		opts="pub"
    415 	else
    416 		opts="pub proxy"
    417 	fi
    418 	# Always proxy only since migrating to lltable/llentry
    419 	title='permanent published \(proxy only\)'
    420 
    421 	#
    422 	# Test#1: First setup an endpoint then create proxy arp entry
    423 	#
    424 	export RUMP_SERVER=$SOCKDST
    425 	atf_check -s exit:0 rump.ifconfig tap1 create
    426 	atf_check -s exit:0 rump.ifconfig tap1 $IP4DST_PROXYARP1/24 up
    427 	atf_check -s exit:0 rump.ifconfig -w 10
    428 
    429 	# Try to ping (should fail w/o proxy arp)
    430 	export RUMP_SERVER=$SOCKSRC
    431 	atf_check -s not-exit:0 -o ignore -e ignore \
    432 	    rump.ping -n -w 1 -c 1 $IP4DST_PROXYARP1
    433 
    434 	# Flushing
    435 	extract_new_packets bus1 > ./out
    436 
    437 	# Set up proxy ARP entry
    438 	export RUMP_SERVER=$SOCKDST
    439 	atf_check -s exit:0 -o ignore \
    440 	    rump.arp -s $IP4DST_PROXYARP1 $macaddr_dst $opts
    441 	atf_check -s exit:0 -o match:"$title" rump.arp -n $IP4DST_PROXYARP1
    442 
    443 	# Try to ping
    444 	export RUMP_SERVER=$SOCKSRC
    445 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST_PROXYARP1
    446 
    447 	extract_new_packets bus1 > ./out
    448 	$DEBUG && cat ./out
    449 
    450 	pkt1=$(make_pkt_str_arprep $IP4DST_PROXYARP1 $macaddr_dst)
    451 	pkt2=$(make_pkt_str_garp $IP4DST_PROXYARP1 $macaddr_dst)
    452 	atf_check -s exit:0 -x "cat ./out |grep -q -e '$pkt1' -e '$pkt2'"
    453 
    454 	#
    455 	# Test#2: Create proxy arp entry then set up an endpoint
    456 	#
    457 	export RUMP_SERVER=$SOCKDST
    458 	atf_check -s exit:0 -o ignore \
    459 	    rump.arp -s $IP4DST_PROXYARP2 $macaddr_dst $opts
    460 	atf_check -s exit:0 -o match:"$title" rump.arp -n $IP4DST_PROXYARP2
    461 	$DEBUG && rump.netstat -nr -f inet
    462 
    463 	# Try to ping (should fail because no endpoint exists)
    464 	export RUMP_SERVER=$SOCKSRC
    465 	atf_check -s not-exit:0 -o ignore -e ignore \
    466 	    rump.ping -n -w 1 -c 1 $IP4DST_PROXYARP2
    467 
    468 	extract_new_packets bus1 > ./out
    469 	$DEBUG && cat ./out
    470 
    471 	# ARP reply should be sent
    472 	pkt=$(make_pkt_str_arprep $IP4DST_PROXYARP2 $macaddr_dst)
    473 	atf_check -s exit:0 -x "cat ./out |grep -q '$pkt'"
    474 
    475 	export RUMP_SERVER=$SOCKDST
    476 	atf_check -s exit:0 rump.ifconfig tap2 create
    477 	atf_check -s exit:0 rump.ifconfig tap2 $IP4DST_PROXYARP2/24 up
    478 	atf_check -s exit:0 rump.ifconfig -w 10
    479 
    480 	# Try to ping
    481 	export RUMP_SERVER=$SOCKSRC
    482 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST_PROXYARP2
    483 }
    484 
    485 arp_proxy_arp_pub_body()
    486 {
    487 
    488 	test_proxy_arp pub
    489 	rump_server_destroy_ifaces
    490 }
    491 
    492 arp_proxy_arp_pubproxy_body()
    493 {
    494 
    495 	test_proxy_arp pubproxy
    496 	rump_server_destroy_ifaces
    497 }
    498 
    499 arp_link_activation_body()
    500 {
    501 	local bonus=2
    502 
    503 	rump_server_start $SOCKSRC
    504 	rump_server_start $SOCKDST
    505 
    506 	setup_dst_server
    507 	setup_src_server
    508 
    509 	# flush old packets
    510 	extract_new_packets bus1 > ./out
    511 
    512 	export RUMP_SERVER=$SOCKSRC
    513 
    514 	atf_check -s exit:0 -o ignore rump.ifconfig shmif0 link \
    515 	    b2:a1:00:00:00:01
    516 
    517 	atf_check -s exit:0 sleep 1
    518 	extract_new_packets bus1 > ./out
    519 	$DEBUG && cat ./out
    520 
    521 	pkt=$(make_pkt_str_arpreq $IP4SRC $IP4SRC)
    522 	atf_check -s not-exit:0 -x "cat ./out |grep -q '$pkt'"
    523 
    524 	atf_check -s exit:0 -o ignore rump.ifconfig shmif0 link \
    525 	    b2:a1:00:00:00:02 active
    526 
    527 	atf_check -s exit:0 sleep 1
    528 	extract_new_packets bus1 > ./out
    529 	$DEBUG && cat ./out
    530 
    531 	pkt=$(make_pkt_str_arpreq $IP4SRC $IP4SRC)
    532 	atf_check -s exit:0 -x \
    533 	    "cat ./out |grep '$pkt' |grep -q 'b2:a1:00:00:00:02'"
    534 
    535 	rump_server_destroy_ifaces
    536 }
    537 
    538 arp_static_body()
    539 {
    540 	local macaddr_src=
    541 
    542 	rump_server_start $SOCKSRC
    543 	rump_server_start $SOCKDST
    544 
    545 	setup_dst_server
    546 	setup_src_server
    547 
    548 	macaddr_src=$(get_macaddr $SOCKSRC shmif0)
    549 
    550 	# Set a (valid) static ARP entry for the src server
    551 	export RUMP_SERVER=$SOCKDST
    552 	$DEBUG && rump.arp -n -a
    553 	atf_check -s exit:0 -o ignore rump.arp -s $IP4SRC $macaddr_src
    554 	$DEBUG && rump.arp -n -a
    555 
    556 	# Test receiving an ARP request with the static ARP entry (as spa/sha)
    557 	export RUMP_SERVER=$SOCKSRC
    558 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST
    559 
    560 	rump_server_destroy_ifaces
    561 }
    562 
    563 arp_cache_expiration_5s_cleanup()
    564 {
    565 	$DEBUG && dump
    566 	cleanup
    567 }
    568 
    569 arp_cache_expiration_10s_cleanup()
    570 {
    571 	$DEBUG && dump
    572 	cleanup
    573 }
    574 
    575 arp_command_cleanup()
    576 {
    577 	$DEBUG && dump
    578 	cleanup
    579 }
    580 
    581 arp_garp_cleanup()
    582 {
    583 	$DEBUG && dump
    584 	cleanup
    585 }
    586 
    587 arp_cache_overwriting_cleanup()
    588 {
    589 	$DEBUG && dump
    590 	cleanup
    591 }
    592 
    593 arp_proxy_arp_pub_cleanup()
    594 {
    595 	$DEBUG && dump
    596 	cleanup
    597 }
    598 
    599 arp_proxy_arp_pubproxy_cleanup()
    600 {
    601 	$DEBUG && dump
    602 	cleanup
    603 }
    604 
    605 arp_link_activation_cleanup()
    606 {
    607 	$DEBUG && dump
    608 	cleanup
    609 }
    610 
    611 arp_static_cleanup()
    612 {
    613 	$DEBUG && dump
    614 	cleanup
    615 }
    616 
    617 atf_test_case arp_rtm cleanup
    618 arp_rtm_head()
    619 {
    620 
    621 	atf_set "descr" "Tests for routing messages on operations of ARP entries"
    622 	atf_set "require.progs" "rump_server"
    623 }
    624 
    625 arp_rtm_body()
    626 {
    627 	local macaddr_src= macaddr_dst=
    628 	local file=./tmp
    629 	local pid= str=
    630 
    631 	rump_server_start $SOCKSRC
    632 	rump_server_start $SOCKDST
    633 
    634 	setup_dst_server
    635 	setup_src_server
    636 
    637 	macaddr_src=$(get_macaddr $SOCKSRC shmif0)
    638 	macaddr_dst=$(get_macaddr $SOCKDST shmif0)
    639 
    640 	export RUMP_SERVER=$SOCKSRC
    641 
    642 	# Test ping and a resulting routing message (RTM_ADD)
    643 	rump.route -n monitor -c 1 > $file &
    644 	pid=$?
    645 	sleep 1
    646 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST
    647 	wait $pid
    648 	$DEBUG && cat $file
    649 
    650 	str="RTM_ADD.+<UP,HOST,DONE,LLINFO,CLONED>"
    651 	atf_check -s exit:0 -o match:"$str" cat $file
    652 	str="<DST,GATEWAY>"
    653 	atf_check -s exit:0 -o match:"$str" cat $file
    654 	str="$IP4DST link#2"
    655 	atf_check -s exit:0 -o match:"$str" cat $file
    656 
    657 	# Test arp -d and resulting routing messages (RTM_DELETE)
    658 	rump.route -n monitor -c 2 > $file &
    659 	pid=$?
    660 	sleep 1
    661 	atf_check -s exit:0 -o ignore rump.arp -d $IP4DST
    662 	wait $pid
    663 	$DEBUG && cat $file
    664 
    665 	str="RTM_DELETE.+<HOST,DONE,LLINFO,CLONED>"
    666 	atf_check -s exit:0 -o match:"$str" grep -A 3 RTM_DELETE $file
    667 	str="<DST,GATEWAY>"
    668 	atf_check -s exit:0 -o match:"$str" grep -A 3 RTM_DELETE $file
    669 	str="$IP4DST $macaddr_dst"
    670 	atf_check -s exit:0 -o match:"$str" grep -A 3 RTM_DELETE $file
    671 
    672 	rump_server_destroy_ifaces
    673 }
    674 
    675 arp_rtm_cleanup()
    676 {
    677 
    678 	$DEBUG && dump
    679 	cleanup
    680 }
    681 
    682 atf_test_case arp_purge_on_route_change cleanup
    683 arp_purge_on_route_change_head()
    684 {
    685 
    686 	atf_set "descr" "Tests if ARP entries are removed on route change"
    687 	atf_set "require.progs" "rump_server"
    688 }
    689 
    690 arp_purge_on_route_change_body()
    691 {
    692 
    693 	rump_server_start $SOCKSRC
    694 	rump_server_start $SOCKDST
    695 
    696 	setup_dst_server
    697 	setup_src_server
    698 
    699 	rump_server_add_iface $SOCKSRC shmif1 bus1
    700 	export RUMP_SERVER=$SOCKSRC
    701 	atf_check -s exit:0 rump.ifconfig shmif1 inet $IP4SRC2/24
    702 	atf_check -s exit:0 rump.ifconfig -w 10
    703 
    704 	$DEBUG && rump.netstat -nr -f inet
    705 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST
    706 	$DEBUG && rump.arp -na
    707 	atf_check -s exit:0 -o ignore \
    708 	    rump.route change -net $IP4NET -ifp shmif1
    709 	$DEBUG && rump.netstat -nr -f inet
    710 	$DEBUG && rump.arp -na
    711 	# The entry was already removed on route change
    712 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    713 
    714 	rump_server_destroy_ifaces
    715 }
    716 
    717 arp_purge_on_route_change_cleanup()
    718 {
    719 
    720 	$DEBUG && dump
    721 	cleanup
    722 }
    723 
    724 atf_test_case arp_purge_on_route_delete cleanup
    725 arp_purge_on_route_delete_head()
    726 {
    727 
    728 	atf_set "descr" "Tests if ARP entries are removed on route delete"
    729 	atf_set "require.progs" "rump_server"
    730 }
    731 
    732 arp_purge_on_route_delete_body()
    733 {
    734 
    735 	rump_server_start $SOCKSRC
    736 	rump_server_start $SOCKDST
    737 
    738 	setup_dst_server
    739 	setup_src_server
    740 
    741 	$DEBUG && rump.netstat -nr -f inet
    742 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST
    743 	$DEBUG && rump.arp -na
    744 
    745 	atf_check -s exit:0 -o ignore rump.route delete -net $IP4NET
    746 	$DEBUG && rump.netstat -nr -f inet
    747 	$DEBUG && rump.arp -na
    748 
    749 	# The entry was already removed on route delete
    750 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    751 
    752 	rump_server_destroy_ifaces
    753 }
    754 
    755 arp_purge_on_route_delete_cleanup()
    756 {
    757 
    758 	$DEBUG && dump
    759 	cleanup
    760 }
    761 
    762 atf_test_case arp_purge_on_ifdown cleanup
    763 arp_purge_on_ifdown_head()
    764 {
    765 
    766 	atf_set "descr" "Tests if ARP entries are removed on interface down"
    767 	atf_set "require.progs" "rump_server"
    768 }
    769 
    770 arp_purge_on_ifdown_body()
    771 {
    772 
    773 	rump_server_start $SOCKSRC
    774 	rump_server_start $SOCKDST
    775 
    776 	setup_dst_server
    777 	setup_src_server
    778 
    779 	$DEBUG && rump.netstat -nr -f inet
    780 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST
    781 	atf_check -s exit:0 -o match:'shmif0' rump.arp -n $IP4DST
    782 
    783 	# Shutdown the interface
    784 	atf_check -s exit:0 rump.ifconfig shmif0 down
    785 	$DEBUG && rump.netstat -nr -f inet
    786 	$DEBUG && rump.arp -na
    787 
    788 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    789 
    790 	rump_server_destroy_ifaces
    791 }
    792 
    793 arp_purge_on_ifdown_cleanup()
    794 {
    795 
    796 	$DEBUG && dump
    797 	cleanup
    798 }
    799 
    800 atf_test_case arp_stray_entries cleanup
    801 arp_stray_entries_head()
    802 {
    803 
    804 	atf_set "descr" "Tests if ARP entries are removed on route change"
    805 	atf_set "require.progs" "rump_server"
    806 }
    807 
    808 arp_stray_entries_body()
    809 {
    810 
    811 	rump_server_start $SOCKSRC
    812 	rump_server_start $SOCKDST
    813 
    814 	setup_dst_server
    815 	setup_src_server
    816 
    817 	rump_server_add_iface $SOCKSRC shmif1 bus1
    818 
    819 	export RUMP_SERVER=$SOCKSRC
    820 	atf_check -s exit:0 rump.ifconfig shmif1 inet $IP4SRC2/24
    821 	atf_check -s exit:0 rump.ifconfig -w 10
    822 
    823 	$DEBUG && rump.netstat -nr -f inet
    824 	atf_check -s exit:0 -o ignore rump.ping -n -w 1 -c 1 $IP4DST
    825 	$DEBUG && rump.arp -na
    826 	atf_check -s exit:0 -o match:'shmif0' rump.arp -n $IP4DST
    827 	atf_check -s exit:0 -o not-match:'shmif1' rump.arp -n $IP4DST
    828 
    829 	# Clean up
    830 	atf_check -s exit:0 -o ignore rump.arp -da
    831 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    832 
    833 	# ping from a different source address
    834 	atf_check -s exit:0 -o ignore \
    835 	    rump.ping -n -w 1 -c 1 -I $IP4SRC2 $IP4DST
    836 	$DEBUG && rump.arp -na
    837 	atf_check -s exit:0 -o match:'shmif0' rump.arp -n $IP4DST
    838 	# ARP reply goes back via shmif1, so a cache is created on shmif1
    839 	atf_check -s exit:0 -o match:'shmif1' rump.arp -n $IP4DST
    840 
    841 	# Clean up by arp -da
    842 	atf_check -s exit:0 -o ignore rump.arp -da
    843 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    844 
    845 	# ping from a different source address again
    846 	atf_check -s exit:0 -o ignore \
    847 	    rump.ping -n -w 1 -c 1 -I $IP4SRC2 $IP4DST
    848 	atf_check -s exit:0 -o match:'shmif0' rump.arp -n $IP4DST
    849 	# ARP reply doen't come
    850 	atf_check -s exit:0 -o not-match:'shmif1' rump.arp -n $IP4DST
    851 
    852 	# Cleanup caches on the destination
    853 	export RUMP_SERVER=$SOCKDST
    854 	atf_check -s exit:0 -o ignore rump.arp -da
    855 	export RUMP_SERVER=$SOCKSRC
    856 
    857 	# ping from a different source address again
    858 	atf_check -s exit:0 -o ignore \
    859 	    rump.ping -n -w 1 -c 1 -I $IP4SRC2 $IP4DST
    860 	atf_check -s exit:0 -o match:'shmif0' rump.arp -n $IP4DST
    861 	# ARP reply goes back via shmif1
    862 	atf_check -s exit:0 -o match:'shmif1' rump.arp -n $IP4DST
    863 
    864 	# Clean up by arp -d <ip>
    865 	atf_check -s exit:0 -o ignore rump.arp -d $IP4DST
    866 	# Both entries should be deleted
    867 	atf_check -s not-exit:0 -e match:'no entry' rump.arp -n $IP4DST
    868 
    869 	rump_server_destroy_ifaces
    870 }
    871 
    872 arp_stray_entries_cleanup()
    873 {
    874 
    875 	$DEBUG && dump
    876 	cleanup
    877 }
    878 
    879 atf_init_test_cases()
    880 {
    881 	atf_add_test_case arp_cache_expiration_5s
    882 	atf_add_test_case arp_cache_expiration_10s
    883 	atf_add_test_case arp_command
    884 	atf_add_test_case arp_garp
    885 	atf_add_test_case arp_cache_overwriting
    886 	atf_add_test_case arp_proxy_arp_pub
    887 	atf_add_test_case arp_proxy_arp_pubproxy
    888 	atf_add_test_case arp_link_activation
    889 	atf_add_test_case arp_static
    890 	atf_add_test_case arp_rtm
    891 	atf_add_test_case arp_purge_on_route_change
    892 	atf_add_test_case arp_purge_on_route_delete
    893 	atf_add_test_case arp_purge_on_ifdown
    894 	atf_add_test_case arp_stray_entries
    895 }
    896