xref: /aosp_15_r20/external/linux-kselftest/tools/testing/selftests/net/fib-onlink-tests.sh (revision 053f45be4e351dfd5e965df293cd45b779f579ee)
1*053f45beSAndroid Build Coastguard Worker#!/bin/bash
2*053f45beSAndroid Build Coastguard Worker# SPDX-License-Identifier: GPL-2.0
3*053f45beSAndroid Build Coastguard Worker
4*053f45beSAndroid Build Coastguard Worker# IPv4 and IPv6 onlink tests
5*053f45beSAndroid Build Coastguard Worker
6*053f45beSAndroid Build Coastguard WorkerPAUSE_ON_FAIL=${PAUSE_ON_FAIL:=no}
7*053f45beSAndroid Build Coastguard WorkerVERBOSE=0
8*053f45beSAndroid Build Coastguard Worker
9*053f45beSAndroid Build Coastguard Worker# Network interfaces
10*053f45beSAndroid Build Coastguard Worker# - odd in current namespace; even in peer ns
11*053f45beSAndroid Build Coastguard Workerdeclare -A NETIFS
12*053f45beSAndroid Build Coastguard Worker# default VRF
13*053f45beSAndroid Build Coastguard WorkerNETIFS[p1]=veth1
14*053f45beSAndroid Build Coastguard WorkerNETIFS[p2]=veth2
15*053f45beSAndroid Build Coastguard WorkerNETIFS[p3]=veth3
16*053f45beSAndroid Build Coastguard WorkerNETIFS[p4]=veth4
17*053f45beSAndroid Build Coastguard Worker# VRF
18*053f45beSAndroid Build Coastguard WorkerNETIFS[p5]=veth5
19*053f45beSAndroid Build Coastguard WorkerNETIFS[p6]=veth6
20*053f45beSAndroid Build Coastguard WorkerNETIFS[p7]=veth7
21*053f45beSAndroid Build Coastguard WorkerNETIFS[p8]=veth8
22*053f45beSAndroid Build Coastguard Worker
23*053f45beSAndroid Build Coastguard Worker# /24 network
24*053f45beSAndroid Build Coastguard Workerdeclare -A V4ADDRS
25*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p1]=169.254.1.1
26*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p2]=169.254.1.2
27*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p3]=169.254.3.1
28*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p4]=169.254.3.2
29*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p5]=169.254.5.1
30*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p6]=169.254.5.2
31*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p7]=169.254.7.1
32*053f45beSAndroid Build Coastguard WorkerV4ADDRS[p8]=169.254.7.2
33*053f45beSAndroid Build Coastguard Worker
34*053f45beSAndroid Build Coastguard Worker# /64 network
35*053f45beSAndroid Build Coastguard Workerdeclare -A V6ADDRS
36*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p1]=2001:db8:101::1
37*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p2]=2001:db8:101::2
38*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p3]=2001:db8:301::1
39*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p4]=2001:db8:301::2
40*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p5]=2001:db8:501::1
41*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p6]=2001:db8:501::2
42*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p7]=2001:db8:701::1
43*053f45beSAndroid Build Coastguard WorkerV6ADDRS[p8]=2001:db8:701::2
44*053f45beSAndroid Build Coastguard Worker
45*053f45beSAndroid Build Coastguard Worker# Test networks:
46*053f45beSAndroid Build Coastguard Worker# [1] = default table
47*053f45beSAndroid Build Coastguard Worker# [2] = VRF
48*053f45beSAndroid Build Coastguard Worker#
49*053f45beSAndroid Build Coastguard Worker# /32 host routes
50*053f45beSAndroid Build Coastguard Workerdeclare -A TEST_NET4
51*053f45beSAndroid Build Coastguard WorkerTEST_NET4[1]=169.254.101
52*053f45beSAndroid Build Coastguard WorkerTEST_NET4[2]=169.254.102
53*053f45beSAndroid Build Coastguard Worker# /128 host routes
54*053f45beSAndroid Build Coastguard Workerdeclare -A TEST_NET6
55*053f45beSAndroid Build Coastguard WorkerTEST_NET6[1]=2001:db8:101
56*053f45beSAndroid Build Coastguard WorkerTEST_NET6[2]=2001:db8:102
57*053f45beSAndroid Build Coastguard Worker
58*053f45beSAndroid Build Coastguard Worker# connected gateway
59*053f45beSAndroid Build Coastguard WorkerCONGW[1]=169.254.1.254
60*053f45beSAndroid Build Coastguard WorkerCONGW[2]=169.254.3.254
61*053f45beSAndroid Build Coastguard WorkerCONGW[3]=169.254.5.254
62*053f45beSAndroid Build Coastguard Worker
63*053f45beSAndroid Build Coastguard Worker# recursive gateway
64*053f45beSAndroid Build Coastguard WorkerRECGW4[1]=169.254.11.254
65*053f45beSAndroid Build Coastguard WorkerRECGW4[2]=169.254.12.254
66*053f45beSAndroid Build Coastguard WorkerRECGW6[1]=2001:db8:11::64
67*053f45beSAndroid Build Coastguard WorkerRECGW6[2]=2001:db8:12::64
68*053f45beSAndroid Build Coastguard Worker
69*053f45beSAndroid Build Coastguard Worker# for v4 mapped to v6
70*053f45beSAndroid Build Coastguard Workerdeclare -A TEST_NET4IN6IN6
71*053f45beSAndroid Build Coastguard WorkerTEST_NET4IN6[1]=10.1.1.254
72*053f45beSAndroid Build Coastguard WorkerTEST_NET4IN6[2]=10.2.1.254
73*053f45beSAndroid Build Coastguard Worker
74*053f45beSAndroid Build Coastguard Worker# mcast address
75*053f45beSAndroid Build Coastguard WorkerMCAST6=ff02::1
76*053f45beSAndroid Build Coastguard Worker
77*053f45beSAndroid Build Coastguard Worker
78*053f45beSAndroid Build Coastguard WorkerPEER_NS=bart
79*053f45beSAndroid Build Coastguard WorkerPEER_CMD="ip netns exec ${PEER_NS}"
80*053f45beSAndroid Build Coastguard WorkerVRF=lisa
81*053f45beSAndroid Build Coastguard WorkerVRF_TABLE=1101
82*053f45beSAndroid Build Coastguard WorkerPBR_TABLE=101
83*053f45beSAndroid Build Coastguard Worker
84*053f45beSAndroid Build Coastguard Worker################################################################################
85*053f45beSAndroid Build Coastguard Worker# utilities
86*053f45beSAndroid Build Coastguard Worker
87*053f45beSAndroid Build Coastguard Workerlog_test()
88*053f45beSAndroid Build Coastguard Worker{
89*053f45beSAndroid Build Coastguard Worker	local rc=$1
90*053f45beSAndroid Build Coastguard Worker	local expected=$2
91*053f45beSAndroid Build Coastguard Worker	local msg="$3"
92*053f45beSAndroid Build Coastguard Worker
93*053f45beSAndroid Build Coastguard Worker	if [ ${rc} -eq ${expected} ]; then
94*053f45beSAndroid Build Coastguard Worker		nsuccess=$((nsuccess+1))
95*053f45beSAndroid Build Coastguard Worker		printf "    TEST: %-50s  [ OK ]\n" "${msg}"
96*053f45beSAndroid Build Coastguard Worker	else
97*053f45beSAndroid Build Coastguard Worker		nfail=$((nfail+1))
98*053f45beSAndroid Build Coastguard Worker		printf "    TEST: %-50s  [FAIL]\n" "${msg}"
99*053f45beSAndroid Build Coastguard Worker		if [ "${PAUSE_ON_FAIL}" = "yes" ]; then
100*053f45beSAndroid Build Coastguard Worker			echo
101*053f45beSAndroid Build Coastguard Worker			echo "hit enter to continue, 'q' to quit"
102*053f45beSAndroid Build Coastguard Worker			read a
103*053f45beSAndroid Build Coastguard Worker			[ "$a" = "q" ] && exit 1
104*053f45beSAndroid Build Coastguard Worker		fi
105*053f45beSAndroid Build Coastguard Worker	fi
106*053f45beSAndroid Build Coastguard Worker}
107*053f45beSAndroid Build Coastguard Worker
108*053f45beSAndroid Build Coastguard Workerlog_section()
109*053f45beSAndroid Build Coastguard Worker{
110*053f45beSAndroid Build Coastguard Worker	echo
111*053f45beSAndroid Build Coastguard Worker	echo "######################################################################"
112*053f45beSAndroid Build Coastguard Worker	echo "TEST SECTION: $*"
113*053f45beSAndroid Build Coastguard Worker	echo "######################################################################"
114*053f45beSAndroid Build Coastguard Worker}
115*053f45beSAndroid Build Coastguard Worker
116*053f45beSAndroid Build Coastguard Workerlog_subsection()
117*053f45beSAndroid Build Coastguard Worker{
118*053f45beSAndroid Build Coastguard Worker	echo
119*053f45beSAndroid Build Coastguard Worker	echo "#########################################"
120*053f45beSAndroid Build Coastguard Worker	echo "TEST SUBSECTION: $*"
121*053f45beSAndroid Build Coastguard Worker}
122*053f45beSAndroid Build Coastguard Worker
123*053f45beSAndroid Build Coastguard Workerrun_cmd()
124*053f45beSAndroid Build Coastguard Worker{
125*053f45beSAndroid Build Coastguard Worker	local cmd="$*"
126*053f45beSAndroid Build Coastguard Worker	local out
127*053f45beSAndroid Build Coastguard Worker	local rc
128*053f45beSAndroid Build Coastguard Worker
129*053f45beSAndroid Build Coastguard Worker	if [ "$VERBOSE" = "1" ]; then
130*053f45beSAndroid Build Coastguard Worker		printf "    COMMAND: $cmd\n"
131*053f45beSAndroid Build Coastguard Worker	fi
132*053f45beSAndroid Build Coastguard Worker
133*053f45beSAndroid Build Coastguard Worker	out=$(eval $cmd 2>&1)
134*053f45beSAndroid Build Coastguard Worker	rc=$?
135*053f45beSAndroid Build Coastguard Worker	if [ "$VERBOSE" = "1" -a -n "$out" ]; then
136*053f45beSAndroid Build Coastguard Worker		echo "    $out"
137*053f45beSAndroid Build Coastguard Worker	fi
138*053f45beSAndroid Build Coastguard Worker
139*053f45beSAndroid Build Coastguard Worker	[ "$VERBOSE" = "1" ] && echo
140*053f45beSAndroid Build Coastguard Worker
141*053f45beSAndroid Build Coastguard Worker	return $rc
142*053f45beSAndroid Build Coastguard Worker}
143*053f45beSAndroid Build Coastguard Worker
144*053f45beSAndroid Build Coastguard Workerget_linklocal()
145*053f45beSAndroid Build Coastguard Worker{
146*053f45beSAndroid Build Coastguard Worker	local dev=$1
147*053f45beSAndroid Build Coastguard Worker	local pfx
148*053f45beSAndroid Build Coastguard Worker	local addr
149*053f45beSAndroid Build Coastguard Worker
150*053f45beSAndroid Build Coastguard Worker	addr=$(${pfx} ip -6 -br addr show dev ${dev} | \
151*053f45beSAndroid Build Coastguard Worker	awk '{
152*053f45beSAndroid Build Coastguard Worker		for (i = 3; i <= NF; ++i) {
153*053f45beSAndroid Build Coastguard Worker			if ($i ~ /^fe80/)
154*053f45beSAndroid Build Coastguard Worker				print $i
155*053f45beSAndroid Build Coastguard Worker		}
156*053f45beSAndroid Build Coastguard Worker	}'
157*053f45beSAndroid Build Coastguard Worker	)
158*053f45beSAndroid Build Coastguard Worker	addr=${addr/\/*}
159*053f45beSAndroid Build Coastguard Worker
160*053f45beSAndroid Build Coastguard Worker	[ -z "$addr" ] && return 1
161*053f45beSAndroid Build Coastguard Worker
162*053f45beSAndroid Build Coastguard Worker	echo $addr
163*053f45beSAndroid Build Coastguard Worker
164*053f45beSAndroid Build Coastguard Worker	return 0
165*053f45beSAndroid Build Coastguard Worker}
166*053f45beSAndroid Build Coastguard Worker
167*053f45beSAndroid Build Coastguard Worker################################################################################
168*053f45beSAndroid Build Coastguard Worker#
169*053f45beSAndroid Build Coastguard Worker
170*053f45beSAndroid Build Coastguard Workersetup()
171*053f45beSAndroid Build Coastguard Worker{
172*053f45beSAndroid Build Coastguard Worker	echo
173*053f45beSAndroid Build Coastguard Worker	echo "########################################"
174*053f45beSAndroid Build Coastguard Worker	echo "Configuring interfaces"
175*053f45beSAndroid Build Coastguard Worker
176*053f45beSAndroid Build Coastguard Worker	set -e
177*053f45beSAndroid Build Coastguard Worker
178*053f45beSAndroid Build Coastguard Worker	# create namespace
179*053f45beSAndroid Build Coastguard Worker	ip netns add ${PEER_NS}
180*053f45beSAndroid Build Coastguard Worker	ip -netns ${PEER_NS} li set lo up
181*053f45beSAndroid Build Coastguard Worker
182*053f45beSAndroid Build Coastguard Worker	# add vrf table
183*053f45beSAndroid Build Coastguard Worker	ip li add ${VRF} type vrf table ${VRF_TABLE}
184*053f45beSAndroid Build Coastguard Worker	ip li set ${VRF} up
185*053f45beSAndroid Build Coastguard Worker	ip ro add table ${VRF_TABLE} unreachable default metric 8192
186*053f45beSAndroid Build Coastguard Worker	ip -6 ro add table ${VRF_TABLE} unreachable default metric 8192
187*053f45beSAndroid Build Coastguard Worker
188*053f45beSAndroid Build Coastguard Worker	# create test interfaces
189*053f45beSAndroid Build Coastguard Worker	ip li add ${NETIFS[p1]} type veth peer name ${NETIFS[p2]}
190*053f45beSAndroid Build Coastguard Worker	ip li add ${NETIFS[p3]} type veth peer name ${NETIFS[p4]}
191*053f45beSAndroid Build Coastguard Worker	ip li add ${NETIFS[p5]} type veth peer name ${NETIFS[p6]}
192*053f45beSAndroid Build Coastguard Worker	ip li add ${NETIFS[p7]} type veth peer name ${NETIFS[p8]}
193*053f45beSAndroid Build Coastguard Worker
194*053f45beSAndroid Build Coastguard Worker	# enslave vrf interfaces
195*053f45beSAndroid Build Coastguard Worker	for n in 5 7; do
196*053f45beSAndroid Build Coastguard Worker		ip li set ${NETIFS[p${n}]} vrf ${VRF}
197*053f45beSAndroid Build Coastguard Worker	done
198*053f45beSAndroid Build Coastguard Worker
199*053f45beSAndroid Build Coastguard Worker	# add addresses
200*053f45beSAndroid Build Coastguard Worker	for n in 1 3 5 7; do
201*053f45beSAndroid Build Coastguard Worker		ip li set ${NETIFS[p${n}]} up
202*053f45beSAndroid Build Coastguard Worker		ip addr add ${V4ADDRS[p${n}]}/24 dev ${NETIFS[p${n}]}
203*053f45beSAndroid Build Coastguard Worker		ip addr add ${V6ADDRS[p${n}]}/64 dev ${NETIFS[p${n}]} nodad
204*053f45beSAndroid Build Coastguard Worker	done
205*053f45beSAndroid Build Coastguard Worker
206*053f45beSAndroid Build Coastguard Worker	# move peer interfaces to namespace and add addresses
207*053f45beSAndroid Build Coastguard Worker	for n in 2 4 6 8; do
208*053f45beSAndroid Build Coastguard Worker		ip li set ${NETIFS[p${n}]} netns ${PEER_NS} up
209*053f45beSAndroid Build Coastguard Worker		ip -netns ${PEER_NS} addr add ${V4ADDRS[p${n}]}/24 dev ${NETIFS[p${n}]}
210*053f45beSAndroid Build Coastguard Worker		ip -netns ${PEER_NS} addr add ${V6ADDRS[p${n}]}/64 dev ${NETIFS[p${n}]} nodad
211*053f45beSAndroid Build Coastguard Worker	done
212*053f45beSAndroid Build Coastguard Worker
213*053f45beSAndroid Build Coastguard Worker	ip -6 ro add default via ${V6ADDRS[p3]/::[0-9]/::64}
214*053f45beSAndroid Build Coastguard Worker	ip -6 ro add table ${VRF_TABLE} default via ${V6ADDRS[p7]/::[0-9]/::64}
215*053f45beSAndroid Build Coastguard Worker
216*053f45beSAndroid Build Coastguard Worker	set +e
217*053f45beSAndroid Build Coastguard Worker}
218*053f45beSAndroid Build Coastguard Worker
219*053f45beSAndroid Build Coastguard Workercleanup()
220*053f45beSAndroid Build Coastguard Worker{
221*053f45beSAndroid Build Coastguard Worker	# make sure we start from a clean slate
222*053f45beSAndroid Build Coastguard Worker	ip netns del ${PEER_NS} 2>/dev/null
223*053f45beSAndroid Build Coastguard Worker	for n in 1 3 5 7; do
224*053f45beSAndroid Build Coastguard Worker		ip link del ${NETIFS[p${n}]} 2>/dev/null
225*053f45beSAndroid Build Coastguard Worker	done
226*053f45beSAndroid Build Coastguard Worker	ip link del ${VRF} 2>/dev/null
227*053f45beSAndroid Build Coastguard Worker	ip ro flush table ${VRF_TABLE}
228*053f45beSAndroid Build Coastguard Worker	ip -6 ro flush table ${VRF_TABLE}
229*053f45beSAndroid Build Coastguard Worker}
230*053f45beSAndroid Build Coastguard Worker
231*053f45beSAndroid Build Coastguard Worker################################################################################
232*053f45beSAndroid Build Coastguard Worker# IPv4 tests
233*053f45beSAndroid Build Coastguard Worker#
234*053f45beSAndroid Build Coastguard Worker
235*053f45beSAndroid Build Coastguard Workerrun_ip()
236*053f45beSAndroid Build Coastguard Worker{
237*053f45beSAndroid Build Coastguard Worker	local table="$1"
238*053f45beSAndroid Build Coastguard Worker	local prefix="$2"
239*053f45beSAndroid Build Coastguard Worker	local gw="$3"
240*053f45beSAndroid Build Coastguard Worker	local dev="$4"
241*053f45beSAndroid Build Coastguard Worker	local exp_rc="$5"
242*053f45beSAndroid Build Coastguard Worker	local desc="$6"
243*053f45beSAndroid Build Coastguard Worker
244*053f45beSAndroid Build Coastguard Worker	# dev arg may be empty
245*053f45beSAndroid Build Coastguard Worker	[ -n "${dev}" ] && dev="dev ${dev}"
246*053f45beSAndroid Build Coastguard Worker
247*053f45beSAndroid Build Coastguard Worker	run_cmd ip ro add table "${table}" "${prefix}"/32 via "${gw}" "${dev}" onlink
248*053f45beSAndroid Build Coastguard Worker	log_test $? ${exp_rc} "${desc}"
249*053f45beSAndroid Build Coastguard Worker}
250*053f45beSAndroid Build Coastguard Worker
251*053f45beSAndroid Build Coastguard Workerrun_ip_mpath()
252*053f45beSAndroid Build Coastguard Worker{
253*053f45beSAndroid Build Coastguard Worker	local table="$1"
254*053f45beSAndroid Build Coastguard Worker	local prefix="$2"
255*053f45beSAndroid Build Coastguard Worker	local nh1="$3"
256*053f45beSAndroid Build Coastguard Worker	local nh2="$4"
257*053f45beSAndroid Build Coastguard Worker	local exp_rc="$5"
258*053f45beSAndroid Build Coastguard Worker	local desc="$6"
259*053f45beSAndroid Build Coastguard Worker
260*053f45beSAndroid Build Coastguard Worker	# dev arg may be empty
261*053f45beSAndroid Build Coastguard Worker	[ -n "${dev}" ] && dev="dev ${dev}"
262*053f45beSAndroid Build Coastguard Worker
263*053f45beSAndroid Build Coastguard Worker	run_cmd ip ro add table "${table}" "${prefix}"/32 \
264*053f45beSAndroid Build Coastguard Worker		nexthop via ${nh1} nexthop via ${nh2}
265*053f45beSAndroid Build Coastguard Worker	log_test $? ${exp_rc} "${desc}"
266*053f45beSAndroid Build Coastguard Worker}
267*053f45beSAndroid Build Coastguard Worker
268*053f45beSAndroid Build Coastguard Workervalid_onlink_ipv4()
269*053f45beSAndroid Build Coastguard Worker{
270*053f45beSAndroid Build Coastguard Worker	# - unicast connected, unicast recursive
271*053f45beSAndroid Build Coastguard Worker	#
272*053f45beSAndroid Build Coastguard Worker	log_subsection "default VRF - main table"
273*053f45beSAndroid Build Coastguard Worker
274*053f45beSAndroid Build Coastguard Worker	run_ip 254 ${TEST_NET4[1]}.1 ${CONGW[1]} ${NETIFS[p1]} 0 "unicast connected"
275*053f45beSAndroid Build Coastguard Worker	run_ip 254 ${TEST_NET4[1]}.2 ${RECGW4[1]} ${NETIFS[p1]} 0 "unicast recursive"
276*053f45beSAndroid Build Coastguard Worker
277*053f45beSAndroid Build Coastguard Worker	log_subsection "VRF ${VRF}"
278*053f45beSAndroid Build Coastguard Worker
279*053f45beSAndroid Build Coastguard Worker	run_ip ${VRF_TABLE} ${TEST_NET4[2]}.1 ${CONGW[3]} ${NETIFS[p5]} 0 "unicast connected"
280*053f45beSAndroid Build Coastguard Worker	run_ip ${VRF_TABLE} ${TEST_NET4[2]}.2 ${RECGW4[2]} ${NETIFS[p5]} 0 "unicast recursive"
281*053f45beSAndroid Build Coastguard Worker
282*053f45beSAndroid Build Coastguard Worker	log_subsection "VRF device, PBR table"
283*053f45beSAndroid Build Coastguard Worker
284*053f45beSAndroid Build Coastguard Worker	run_ip ${PBR_TABLE} ${TEST_NET4[2]}.3 ${CONGW[3]} ${NETIFS[p5]} 0 "unicast connected"
285*053f45beSAndroid Build Coastguard Worker	run_ip ${PBR_TABLE} ${TEST_NET4[2]}.4 ${RECGW4[2]} ${NETIFS[p5]} 0 "unicast recursive"
286*053f45beSAndroid Build Coastguard Worker
287*053f45beSAndroid Build Coastguard Worker	# multipath version
288*053f45beSAndroid Build Coastguard Worker	#
289*053f45beSAndroid Build Coastguard Worker	log_subsection "default VRF - main table - multipath"
290*053f45beSAndroid Build Coastguard Worker
291*053f45beSAndroid Build Coastguard Worker	run_ip_mpath 254 ${TEST_NET4[1]}.5 \
292*053f45beSAndroid Build Coastguard Worker		"${CONGW[1]} dev ${NETIFS[p1]} onlink" \
293*053f45beSAndroid Build Coastguard Worker		"${CONGW[2]} dev ${NETIFS[p3]} onlink" \
294*053f45beSAndroid Build Coastguard Worker		0 "unicast connected - multipath"
295*053f45beSAndroid Build Coastguard Worker
296*053f45beSAndroid Build Coastguard Worker	run_ip_mpath 254 ${TEST_NET4[1]}.6 \
297*053f45beSAndroid Build Coastguard Worker		"${RECGW4[1]} dev ${NETIFS[p1]} onlink" \
298*053f45beSAndroid Build Coastguard Worker		"${RECGW4[2]} dev ${NETIFS[p3]} onlink" \
299*053f45beSAndroid Build Coastguard Worker		0 "unicast recursive - multipath"
300*053f45beSAndroid Build Coastguard Worker
301*053f45beSAndroid Build Coastguard Worker	run_ip_mpath 254 ${TEST_NET4[1]}.7 \
302*053f45beSAndroid Build Coastguard Worker		"${CONGW[1]} dev ${NETIFS[p1]}"        \
303*053f45beSAndroid Build Coastguard Worker		"${CONGW[2]} dev ${NETIFS[p3]} onlink" \
304*053f45beSAndroid Build Coastguard Worker		0 "unicast connected - multipath onlink first only"
305*053f45beSAndroid Build Coastguard Worker
306*053f45beSAndroid Build Coastguard Worker	run_ip_mpath 254 ${TEST_NET4[1]}.8 \
307*053f45beSAndroid Build Coastguard Worker		"${CONGW[1]} dev ${NETIFS[p1]} onlink" \
308*053f45beSAndroid Build Coastguard Worker		"${CONGW[2]} dev ${NETIFS[p3]}"        \
309*053f45beSAndroid Build Coastguard Worker		0 "unicast connected - multipath onlink second only"
310*053f45beSAndroid Build Coastguard Worker}
311*053f45beSAndroid Build Coastguard Worker
312*053f45beSAndroid Build Coastguard Workerinvalid_onlink_ipv4()
313*053f45beSAndroid Build Coastguard Worker{
314*053f45beSAndroid Build Coastguard Worker	run_ip 254 ${TEST_NET4[1]}.11 ${V4ADDRS[p1]} ${NETIFS[p1]} 2 \
315*053f45beSAndroid Build Coastguard Worker		"Invalid gw - local unicast address"
316*053f45beSAndroid Build Coastguard Worker
317*053f45beSAndroid Build Coastguard Worker	run_ip ${VRF_TABLE} ${TEST_NET4[2]}.11 ${V4ADDRS[p5]} ${NETIFS[p5]} 2 \
318*053f45beSAndroid Build Coastguard Worker		"Invalid gw - local unicast address, VRF"
319*053f45beSAndroid Build Coastguard Worker
320*053f45beSAndroid Build Coastguard Worker	run_ip 254 ${TEST_NET4[1]}.101 ${V4ADDRS[p1]} "" 2 "No nexthop device given"
321*053f45beSAndroid Build Coastguard Worker
322*053f45beSAndroid Build Coastguard Worker	run_ip 254 ${TEST_NET4[1]}.102 ${V4ADDRS[p3]} ${NETIFS[p1]} 2 \
323*053f45beSAndroid Build Coastguard Worker		"Gateway resolves to wrong nexthop device"
324*053f45beSAndroid Build Coastguard Worker
325*053f45beSAndroid Build Coastguard Worker	run_ip ${VRF_TABLE} ${TEST_NET4[2]}.103 ${V4ADDRS[p7]} ${NETIFS[p5]} 2 \
326*053f45beSAndroid Build Coastguard Worker		"Gateway resolves to wrong nexthop device - VRF"
327*053f45beSAndroid Build Coastguard Worker}
328*053f45beSAndroid Build Coastguard Worker
329*053f45beSAndroid Build Coastguard Worker################################################################################
330*053f45beSAndroid Build Coastguard Worker# IPv6 tests
331*053f45beSAndroid Build Coastguard Worker#
332*053f45beSAndroid Build Coastguard Worker
333*053f45beSAndroid Build Coastguard Workerrun_ip6()
334*053f45beSAndroid Build Coastguard Worker{
335*053f45beSAndroid Build Coastguard Worker	local table="$1"
336*053f45beSAndroid Build Coastguard Worker	local prefix="$2"
337*053f45beSAndroid Build Coastguard Worker	local gw="$3"
338*053f45beSAndroid Build Coastguard Worker	local dev="$4"
339*053f45beSAndroid Build Coastguard Worker	local exp_rc="$5"
340*053f45beSAndroid Build Coastguard Worker	local desc="$6"
341*053f45beSAndroid Build Coastguard Worker
342*053f45beSAndroid Build Coastguard Worker	# dev arg may be empty
343*053f45beSAndroid Build Coastguard Worker	[ -n "${dev}" ] && dev="dev ${dev}"
344*053f45beSAndroid Build Coastguard Worker
345*053f45beSAndroid Build Coastguard Worker	run_cmd ip -6 ro add table "${table}" "${prefix}"/128 via "${gw}" "${dev}" onlink
346*053f45beSAndroid Build Coastguard Worker	log_test $? ${exp_rc} "${desc}"
347*053f45beSAndroid Build Coastguard Worker}
348*053f45beSAndroid Build Coastguard Worker
349*053f45beSAndroid Build Coastguard Workerrun_ip6_mpath()
350*053f45beSAndroid Build Coastguard Worker{
351*053f45beSAndroid Build Coastguard Worker	local table="$1"
352*053f45beSAndroid Build Coastguard Worker	local prefix="$2"
353*053f45beSAndroid Build Coastguard Worker	local opts="$3"
354*053f45beSAndroid Build Coastguard Worker	local nh1="$4"
355*053f45beSAndroid Build Coastguard Worker	local nh2="$5"
356*053f45beSAndroid Build Coastguard Worker	local exp_rc="$6"
357*053f45beSAndroid Build Coastguard Worker	local desc="$7"
358*053f45beSAndroid Build Coastguard Worker
359*053f45beSAndroid Build Coastguard Worker	run_cmd ip -6 ro add table "${table}" "${prefix}"/128 "${opts}" \
360*053f45beSAndroid Build Coastguard Worker		nexthop via ${nh1} nexthop via ${nh2}
361*053f45beSAndroid Build Coastguard Worker	log_test $? ${exp_rc} "${desc}"
362*053f45beSAndroid Build Coastguard Worker}
363*053f45beSAndroid Build Coastguard Worker
364*053f45beSAndroid Build Coastguard Workervalid_onlink_ipv6()
365*053f45beSAndroid Build Coastguard Worker{
366*053f45beSAndroid Build Coastguard Worker	# - unicast connected, unicast recursive, v4-mapped
367*053f45beSAndroid Build Coastguard Worker	#
368*053f45beSAndroid Build Coastguard Worker	log_subsection "default VRF - main table"
369*053f45beSAndroid Build Coastguard Worker
370*053f45beSAndroid Build Coastguard Worker	run_ip6 254 ${TEST_NET6[1]}::1 ${V6ADDRS[p1]/::*}::64 ${NETIFS[p1]} 0 "unicast connected"
371*053f45beSAndroid Build Coastguard Worker	run_ip6 254 ${TEST_NET6[1]}::2 ${RECGW6[1]} ${NETIFS[p1]} 0 "unicast recursive"
372*053f45beSAndroid Build Coastguard Worker	run_ip6 254 ${TEST_NET6[1]}::3 ::ffff:${TEST_NET4IN6[1]} ${NETIFS[p1]} 0 "v4-mapped"
373*053f45beSAndroid Build Coastguard Worker
374*053f45beSAndroid Build Coastguard Worker	log_subsection "VRF ${VRF}"
375*053f45beSAndroid Build Coastguard Worker
376*053f45beSAndroid Build Coastguard Worker	run_ip6 ${VRF_TABLE} ${TEST_NET6[2]}::1 ${V6ADDRS[p5]/::*}::64 ${NETIFS[p5]} 0 "unicast connected"
377*053f45beSAndroid Build Coastguard Worker	run_ip6 ${VRF_TABLE} ${TEST_NET6[2]}::2 ${RECGW6[2]} ${NETIFS[p5]} 0 "unicast recursive"
378*053f45beSAndroid Build Coastguard Worker	run_ip6 ${VRF_TABLE} ${TEST_NET6[2]}::3 ::ffff:${TEST_NET4IN6[2]} ${NETIFS[p5]} 0 "v4-mapped"
379*053f45beSAndroid Build Coastguard Worker
380*053f45beSAndroid Build Coastguard Worker	log_subsection "VRF device, PBR table"
381*053f45beSAndroid Build Coastguard Worker
382*053f45beSAndroid Build Coastguard Worker	run_ip6 ${PBR_TABLE} ${TEST_NET6[2]}::4 ${V6ADDRS[p5]/::*}::64 ${NETIFS[p5]} 0 "unicast connected"
383*053f45beSAndroid Build Coastguard Worker	run_ip6 ${PBR_TABLE} ${TEST_NET6[2]}::5 ${RECGW6[2]} ${NETIFS[p5]} 0 "unicast recursive"
384*053f45beSAndroid Build Coastguard Worker	run_ip6 ${PBR_TABLE} ${TEST_NET6[2]}::6 ::ffff:${TEST_NET4IN6[2]} ${NETIFS[p5]} 0 "v4-mapped"
385*053f45beSAndroid Build Coastguard Worker
386*053f45beSAndroid Build Coastguard Worker	# multipath version
387*053f45beSAndroid Build Coastguard Worker	#
388*053f45beSAndroid Build Coastguard Worker	log_subsection "default VRF - main table - multipath"
389*053f45beSAndroid Build Coastguard Worker
390*053f45beSAndroid Build Coastguard Worker	run_ip6_mpath 254 ${TEST_NET6[1]}::4 "onlink" \
391*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p1]/::*}::64 dev ${NETIFS[p1]}" \
392*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p3]/::*}::64 dev ${NETIFS[p3]}" \
393*053f45beSAndroid Build Coastguard Worker		0 "unicast connected - multipath onlink"
394*053f45beSAndroid Build Coastguard Worker
395*053f45beSAndroid Build Coastguard Worker	run_ip6_mpath 254 ${TEST_NET6[1]}::5 "onlink" \
396*053f45beSAndroid Build Coastguard Worker		"${RECGW6[1]} dev ${NETIFS[p1]}" \
397*053f45beSAndroid Build Coastguard Worker		"${RECGW6[2]} dev ${NETIFS[p3]}" \
398*053f45beSAndroid Build Coastguard Worker		0 "unicast recursive - multipath onlink"
399*053f45beSAndroid Build Coastguard Worker
400*053f45beSAndroid Build Coastguard Worker	run_ip6_mpath 254 ${TEST_NET6[1]}::6 "onlink" \
401*053f45beSAndroid Build Coastguard Worker		"::ffff:${TEST_NET4IN6[1]} dev ${NETIFS[p1]}" \
402*053f45beSAndroid Build Coastguard Worker		"::ffff:${TEST_NET4IN6[2]} dev ${NETIFS[p3]}" \
403*053f45beSAndroid Build Coastguard Worker		0 "v4-mapped - multipath onlink"
404*053f45beSAndroid Build Coastguard Worker
405*053f45beSAndroid Build Coastguard Worker	run_ip6_mpath 254 ${TEST_NET6[1]}::7 "" \
406*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p1]/::*}::64 dev ${NETIFS[p1]} onlink" \
407*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p3]/::*}::64 dev ${NETIFS[p3]} onlink" \
408*053f45beSAndroid Build Coastguard Worker		0 "unicast connected - multipath onlink both nexthops"
409*053f45beSAndroid Build Coastguard Worker
410*053f45beSAndroid Build Coastguard Worker	run_ip6_mpath 254 ${TEST_NET6[1]}::8 "" \
411*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p1]/::*}::64 dev ${NETIFS[p1]} onlink" \
412*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p3]/::*}::64 dev ${NETIFS[p3]}" \
413*053f45beSAndroid Build Coastguard Worker		0 "unicast connected - multipath onlink first only"
414*053f45beSAndroid Build Coastguard Worker
415*053f45beSAndroid Build Coastguard Worker	run_ip6_mpath 254 ${TEST_NET6[1]}::9 "" \
416*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p1]/::*}::64 dev ${NETIFS[p1]}"        \
417*053f45beSAndroid Build Coastguard Worker		"${V6ADDRS[p3]/::*}::64 dev ${NETIFS[p3]} onlink" \
418*053f45beSAndroid Build Coastguard Worker		0 "unicast connected - multipath onlink second only"
419*053f45beSAndroid Build Coastguard Worker}
420*053f45beSAndroid Build Coastguard Worker
421*053f45beSAndroid Build Coastguard Workerinvalid_onlink_ipv6()
422*053f45beSAndroid Build Coastguard Worker{
423*053f45beSAndroid Build Coastguard Worker	local lladdr
424*053f45beSAndroid Build Coastguard Worker
425*053f45beSAndroid Build Coastguard Worker	lladdr=$(get_linklocal ${NETIFS[p1]}) || return 1
426*053f45beSAndroid Build Coastguard Worker
427*053f45beSAndroid Build Coastguard Worker	run_ip6 254 ${TEST_NET6[1]}::11 ${V6ADDRS[p1]} ${NETIFS[p1]} 2 \
428*053f45beSAndroid Build Coastguard Worker		"Invalid gw - local unicast address"
429*053f45beSAndroid Build Coastguard Worker	run_ip6 254 ${TEST_NET6[1]}::12 ${lladdr} ${NETIFS[p1]} 2 \
430*053f45beSAndroid Build Coastguard Worker		"Invalid gw - local linklocal address"
431*053f45beSAndroid Build Coastguard Worker	run_ip6 254 ${TEST_NET6[1]}::12 ${MCAST6} ${NETIFS[p1]} 2 \
432*053f45beSAndroid Build Coastguard Worker		"Invalid gw - multicast address"
433*053f45beSAndroid Build Coastguard Worker
434*053f45beSAndroid Build Coastguard Worker	lladdr=$(get_linklocal ${NETIFS[p5]}) || return 1
435*053f45beSAndroid Build Coastguard Worker	run_ip6 ${VRF_TABLE} ${TEST_NET6[2]}::11 ${V6ADDRS[p5]} ${NETIFS[p5]} 2 \
436*053f45beSAndroid Build Coastguard Worker		"Invalid gw - local unicast address, VRF"
437*053f45beSAndroid Build Coastguard Worker	run_ip6 ${VRF_TABLE} ${TEST_NET6[2]}::12 ${lladdr} ${NETIFS[p5]} 2 \
438*053f45beSAndroid Build Coastguard Worker		"Invalid gw - local linklocal address, VRF"
439*053f45beSAndroid Build Coastguard Worker	run_ip6 ${VRF_TABLE} ${TEST_NET6[2]}::12 ${MCAST6} ${NETIFS[p5]} 2 \
440*053f45beSAndroid Build Coastguard Worker		"Invalid gw - multicast address, VRF"
441*053f45beSAndroid Build Coastguard Worker
442*053f45beSAndroid Build Coastguard Worker	run_ip6 254 ${TEST_NET6[1]}::101 ${V6ADDRS[p1]} "" 2 \
443*053f45beSAndroid Build Coastguard Worker		"No nexthop device given"
444*053f45beSAndroid Build Coastguard Worker
445*053f45beSAndroid Build Coastguard Worker	# default VRF validation is done against LOCAL table
446*053f45beSAndroid Build Coastguard Worker	# run_ip6 254 ${TEST_NET6[1]}::102 ${V6ADDRS[p3]/::[0-9]/::64} ${NETIFS[p1]} 2 \
447*053f45beSAndroid Build Coastguard Worker	#	"Gateway resolves to wrong nexthop device"
448*053f45beSAndroid Build Coastguard Worker
449*053f45beSAndroid Build Coastguard Worker	run_ip6 ${VRF_TABLE} ${TEST_NET6[2]}::103 ${V6ADDRS[p7]/::[0-9]/::64} ${NETIFS[p5]} 2 \
450*053f45beSAndroid Build Coastguard Worker		"Gateway resolves to wrong nexthop device - VRF"
451*053f45beSAndroid Build Coastguard Worker}
452*053f45beSAndroid Build Coastguard Worker
453*053f45beSAndroid Build Coastguard Workerrun_onlink_tests()
454*053f45beSAndroid Build Coastguard Worker{
455*053f45beSAndroid Build Coastguard Worker	log_section "IPv4 onlink"
456*053f45beSAndroid Build Coastguard Worker	log_subsection "Valid onlink commands"
457*053f45beSAndroid Build Coastguard Worker	valid_onlink_ipv4
458*053f45beSAndroid Build Coastguard Worker	log_subsection "Invalid onlink commands"
459*053f45beSAndroid Build Coastguard Worker	invalid_onlink_ipv4
460*053f45beSAndroid Build Coastguard Worker
461*053f45beSAndroid Build Coastguard Worker	log_section "IPv6 onlink"
462*053f45beSAndroid Build Coastguard Worker	log_subsection "Valid onlink commands"
463*053f45beSAndroid Build Coastguard Worker	valid_onlink_ipv6
464*053f45beSAndroid Build Coastguard Worker	log_subsection "Invalid onlink commands"
465*053f45beSAndroid Build Coastguard Worker	invalid_onlink_ipv6
466*053f45beSAndroid Build Coastguard Worker}
467*053f45beSAndroid Build Coastguard Worker
468*053f45beSAndroid Build Coastguard Worker################################################################################
469*053f45beSAndroid Build Coastguard Worker# usage
470*053f45beSAndroid Build Coastguard Worker
471*053f45beSAndroid Build Coastguard Workerusage()
472*053f45beSAndroid Build Coastguard Worker{
473*053f45beSAndroid Build Coastguard Worker	cat <<EOF
474*053f45beSAndroid Build Coastguard Workerusage: ${0##*/} OPTS
475*053f45beSAndroid Build Coastguard Worker
476*053f45beSAndroid Build Coastguard Worker        -p          Pause on fail
477*053f45beSAndroid Build Coastguard Worker        -v          verbose mode (show commands and output)
478*053f45beSAndroid Build Coastguard WorkerEOF
479*053f45beSAndroid Build Coastguard Worker}
480*053f45beSAndroid Build Coastguard Worker
481*053f45beSAndroid Build Coastguard Worker################################################################################
482*053f45beSAndroid Build Coastguard Worker# main
483*053f45beSAndroid Build Coastguard Worker
484*053f45beSAndroid Build Coastguard Workernsuccess=0
485*053f45beSAndroid Build Coastguard Workernfail=0
486*053f45beSAndroid Build Coastguard Worker
487*053f45beSAndroid Build Coastguard Workerwhile getopts :t:pPhv o
488*053f45beSAndroid Build Coastguard Workerdo
489*053f45beSAndroid Build Coastguard Worker	case $o in
490*053f45beSAndroid Build Coastguard Worker		p) PAUSE_ON_FAIL=yes;;
491*053f45beSAndroid Build Coastguard Worker		v) VERBOSE=$(($VERBOSE + 1));;
492*053f45beSAndroid Build Coastguard Worker		h) usage; exit 0;;
493*053f45beSAndroid Build Coastguard Worker		*) usage; exit 1;;
494*053f45beSAndroid Build Coastguard Worker	esac
495*053f45beSAndroid Build Coastguard Workerdone
496*053f45beSAndroid Build Coastguard Worker
497*053f45beSAndroid Build Coastguard Workercleanup
498*053f45beSAndroid Build Coastguard Workersetup
499*053f45beSAndroid Build Coastguard Workerrun_onlink_tests
500*053f45beSAndroid Build Coastguard Workercleanup
501*053f45beSAndroid Build Coastguard Worker
502*053f45beSAndroid Build Coastguard Workerif [ "$TESTS" != "none" ]; then
503*053f45beSAndroid Build Coastguard Worker	printf "\nTests passed: %3d\n" ${nsuccess}
504*053f45beSAndroid Build Coastguard Worker	printf "Tests failed: %3d\n"   ${nfail}
505*053f45beSAndroid Build Coastguard Workerfi
506