xref: /linux/tools/testing/selftests/net/mptcp/mptcp_join.sh (revision 6015fb905d89063231ed33bc15be19ef0fc339b8)
1#!/bin/bash
2# SPDX-License-Identifier: GPL-2.0
3
4ret=0
5sin=""
6sinfail=""
7sout=""
8cin=""
9cinfail=""
10cinsent=""
11cout=""
12ksft_skip=4
13timeout_poll=30
14timeout_test=$((timeout_poll * 2 + 1))
15mptcp_connect=""
16capture=0
17checksum=0
18ip_mptcp=0
19do_all_tests=1
20init=0
21
22TEST_COUNT=0
23
24# generated using "nfbpf_compile '(ip && (ip[54] & 0xf0) == 0x30) ||
25#				  (ip6 && (ip6[74] & 0xf0) == 0x30)'"
26CBPF_MPTCP_SUBOPTION_ADD_ADDR="14,
27			       48 0 0 0,
28			       84 0 0 240,
29			       21 0 3 64,
30			       48 0 0 54,
31			       84 0 0 240,
32			       21 6 7 48,
33			       48 0 0 0,
34			       84 0 0 240,
35			       21 0 4 96,
36			       48 0 0 74,
37			       84 0 0 240,
38			       21 0 1 48,
39			       6 0 0 65535,
40			       6 0 0 0"
41
42init_partial()
43{
44	capout=$(mktemp)
45
46	rndh=$(mktemp -u XXXXXX)
47
48	ns1="ns1-$rndh"
49	ns2="ns2-$rndh"
50
51	for netns in "$ns1" "$ns2";do
52		ip netns add $netns || exit $ksft_skip
53		ip -net $netns link set lo up
54		ip netns exec $netns sysctl -q net.mptcp.enabled=1
55		ip netns exec $netns sysctl -q net.ipv4.conf.all.rp_filter=0
56		ip netns exec $netns sysctl -q net.ipv4.conf.default.rp_filter=0
57		if [ $checksum -eq 1 ]; then
58			ip netns exec $netns sysctl -q net.mptcp.checksum_enabled=1
59		fi
60	done
61
62	#  ns1              ns2
63	# ns1eth1    ns2eth1
64	# ns1eth2    ns2eth2
65	# ns1eth3    ns2eth3
66	# ns1eth4    ns2eth4
67
68	for i in `seq 1 4`; do
69		ip link add ns1eth$i netns "$ns1" type veth peer name ns2eth$i netns "$ns2"
70		ip -net "$ns1" addr add 10.0.$i.1/24 dev ns1eth$i
71		ip -net "$ns1" addr add dead:beef:$i::1/64 dev ns1eth$i nodad
72		ip -net "$ns1" link set ns1eth$i up
73
74		ip -net "$ns2" addr add 10.0.$i.2/24 dev ns2eth$i
75		ip -net "$ns2" addr add dead:beef:$i::2/64 dev ns2eth$i nodad
76		ip -net "$ns2" link set ns2eth$i up
77
78		# let $ns2 reach any $ns1 address from any interface
79		ip -net "$ns2" route add default via 10.0.$i.1 dev ns2eth$i metric 10$i
80		ip -net "$ns2" route add default via dead:beef:$i::1 dev ns2eth$i metric 10$i
81	done
82}
83
84init_shapers()
85{
86	for i in `seq 1 4`; do
87		tc -n $ns1 qdisc add dev ns1eth$i root netem rate 20mbit delay 1
88		tc -n $ns2 qdisc add dev ns2eth$i root netem rate 20mbit delay 1
89	done
90}
91
92cleanup_partial()
93{
94	rm -f "$capout"
95
96	for netns in "$ns1" "$ns2"; do
97		ip netns del $netns
98		rm -f /tmp/$netns.{nstat,out}
99	done
100}
101
102check_tools()
103{
104	if ! ip -Version &> /dev/null; then
105		echo "SKIP: Could not run test without ip tool"
106		exit $ksft_skip
107	fi
108
109	if ! iptables -V &> /dev/null; then
110		echo "SKIP: Could not run all tests without iptables tool"
111		exit $ksft_skip
112	fi
113
114	if ! ip6tables -V &> /dev/null; then
115		echo "SKIP: Could not run all tests without ip6tables tool"
116		exit $ksft_skip
117	fi
118}
119
120init() {
121	init=1
122
123	check_tools
124
125	sin=$(mktemp)
126	sout=$(mktemp)
127	cin=$(mktemp)
128	cinsent=$(mktemp)
129	cout=$(mktemp)
130
131	trap cleanup EXIT
132
133	make_file "$cin" "client" 1
134	make_file "$sin" "server" 1
135}
136
137cleanup()
138{
139	rm -f "$cin" "$cout" "$sinfail"
140	rm -f "$sin" "$sout" "$cinsent" "$cinfail"
141	cleanup_partial
142}
143
144reset()
145{
146	if [ "${init}" != "1" ]; then
147		init
148	else
149		cleanup_partial
150	fi
151
152	init_partial
153}
154
155reset_with_cookies()
156{
157	reset
158
159	for netns in "$ns1" "$ns2";do
160		ip netns exec $netns sysctl -q net.ipv4.tcp_syncookies=2
161	done
162}
163
164reset_with_add_addr_timeout()
165{
166	local ip="${1:-4}"
167	local tables
168
169	tables="iptables"
170	if [ $ip -eq 6 ]; then
171		tables="ip6tables"
172	fi
173
174	reset
175
176	ip netns exec $ns1 sysctl -q net.mptcp.add_addr_timeout=1
177	ip netns exec $ns2 $tables -A OUTPUT -p tcp \
178		-m tcp --tcp-option 30 \
179		-m bpf --bytecode \
180		"$CBPF_MPTCP_SUBOPTION_ADD_ADDR" \
181		-j DROP
182}
183
184reset_with_checksum()
185{
186	local ns1_enable=$1
187	local ns2_enable=$2
188
189	reset
190
191	ip netns exec $ns1 sysctl -q net.mptcp.checksum_enabled=$ns1_enable
192	ip netns exec $ns2 sysctl -q net.mptcp.checksum_enabled=$ns2_enable
193}
194
195reset_with_allow_join_id0()
196{
197	local ns1_enable=$1
198	local ns2_enable=$2
199
200	reset
201
202	ip netns exec $ns1 sysctl -q net.mptcp.allow_join_initial_addr_port=$ns1_enable
203	ip netns exec $ns2 sysctl -q net.mptcp.allow_join_initial_addr_port=$ns2_enable
204}
205
206print_file_err()
207{
208	ls -l "$1" 1>&2
209	echo "Trailing bytes are: "
210	tail -c 27 "$1"
211}
212
213check_transfer()
214{
215	in=$1
216	out=$2
217	what=$3
218
219	cmp "$in" "$out" > /dev/null 2>&1
220	if [ $? -ne 0 ] ;then
221		echo "[ FAIL ] $what does not match (in, out):"
222		print_file_err "$in"
223		print_file_err "$out"
224		ret=1
225
226		return 1
227	fi
228
229	return 0
230}
231
232do_ping()
233{
234	listener_ns="$1"
235	connector_ns="$2"
236	connect_addr="$3"
237
238	ip netns exec ${connector_ns} ping -q -c 1 $connect_addr >/dev/null
239	if [ $? -ne 0 ] ; then
240		echo "$listener_ns -> $connect_addr connectivity [ FAIL ]" 1>&2
241		ret=1
242	fi
243}
244
245link_failure()
246{
247	ns="$1"
248
249	if [ -z "$FAILING_LINKS" ]; then
250		l=$((RANDOM%4))
251		FAILING_LINKS=$((l+1))
252	fi
253
254	for l in $FAILING_LINKS; do
255		veth="ns1eth$l"
256		ip -net "$ns" link set "$veth" down
257	done
258}
259
260# $1: IP address
261is_v6()
262{
263	[ -z "${1##*:*}" ]
264}
265
266# $1: ns, $2: port
267wait_local_port_listen()
268{
269	local listener_ns="${1}"
270	local port="${2}"
271
272	local port_hex i
273
274	port_hex="$(printf "%04X" "${port}")"
275	for i in $(seq 10); do
276		ip netns exec "${listener_ns}" cat /proc/net/tcp* | \
277			awk "BEGIN {rc=1} {if (\$2 ~ /:${port_hex}\$/ && \$4 ~ /0A/) {rc=0; exit}} END {exit rc}" &&
278			break
279		sleep 0.1
280	done
281}
282
283rm_addr_count()
284{
285	ns=${1}
286
287	ip netns exec ${ns} nstat -as | grep MPTcpExtRmAddr | awk '{print $2}'
288}
289
290# $1: ns, $2: old rm_addr counter in $ns
291wait_rm_addr()
292{
293	local ns="${1}"
294	local old_cnt="${2}"
295	local cnt
296	local i
297
298	for i in $(seq 10); do
299		cnt=$(rm_addr_count ${ns})
300		[ "$cnt" = "${old_cnt}" ] || break
301		sleep 0.1
302	done
303}
304
305pm_nl_set_limits()
306{
307	local ns=$1
308	local addrs=$2
309	local subflows=$3
310
311	if [ $ip_mptcp -eq 1 ]; then
312		ip -n $ns mptcp limits set add_addr_accepted $addrs subflows $subflows
313	else
314		ip netns exec $ns ./pm_nl_ctl limits $addrs $subflows
315	fi
316}
317
318pm_nl_add_endpoint()
319{
320	local ns=$1
321	local addr=$2
322	local flags
323	local port
324	local dev
325	local id
326	local nr=2
327
328	for p in $@
329	do
330		if [ $p = "flags" ]; then
331			eval _flags=\$"$nr"
332			[ ! -z $_flags ]; flags="flags $_flags"
333		fi
334		if [ $p = "dev" ]; then
335			eval _dev=\$"$nr"
336			[ ! -z $_dev ]; dev="dev $_dev"
337		fi
338		if [ $p = "id" ]; then
339			eval _id=\$"$nr"
340			[ ! -z $_id ]; id="id $_id"
341		fi
342		if [ $p = "port" ]; then
343			eval _port=\$"$nr"
344			[ ! -z $_port ]; port="port $_port"
345		fi
346
347		let nr+=1
348	done
349
350	if [ $ip_mptcp -eq 1 ]; then
351		ip -n $ns mptcp endpoint add $addr ${_flags//","/" "} $dev $id $port
352	else
353		ip netns exec $ns ./pm_nl_ctl add $addr $flags $dev $id $port
354	fi
355}
356
357pm_nl_del_endpoint()
358{
359	local ns=$1
360	local id=$2
361	local addr=$3
362
363	if [ $ip_mptcp -eq 1 ]; then
364		ip -n $ns mptcp endpoint delete id $id $addr
365	else
366		ip netns exec $ns ./pm_nl_ctl del $id $addr
367	fi
368}
369
370pm_nl_flush_endpoint()
371{
372	local ns=$1
373
374	if [ $ip_mptcp -eq 1 ]; then
375		ip -n $ns mptcp endpoint flush
376	else
377		ip netns exec $ns ./pm_nl_ctl flush
378	fi
379}
380
381pm_nl_show_endpoints()
382{
383	local ns=$1
384
385	if [ $ip_mptcp -eq 1 ]; then
386		ip -n $ns mptcp endpoint show
387	else
388		ip netns exec $ns ./pm_nl_ctl dump
389	fi
390}
391
392pm_nl_change_endpoint()
393{
394	local ns=$1
395	local id=$2
396	local flags=$3
397
398	if [ $ip_mptcp -eq 1 ]; then
399		ip -n $ns mptcp endpoint change id $id ${flags//","/" "}
400	else
401		ip netns exec $ns ./pm_nl_ctl set id $id flags $flags
402	fi
403}
404
405do_transfer()
406{
407	listener_ns="$1"
408	connector_ns="$2"
409	cl_proto="$3"
410	srv_proto="$4"
411	connect_addr="$5"
412	test_link_fail="$6"
413	addr_nr_ns1="$7"
414	addr_nr_ns2="$8"
415	speed="$9"
416	sflags="${10}"
417
418	port=$((10000+$TEST_COUNT))
419	TEST_COUNT=$((TEST_COUNT+1))
420
421	:> "$cout"
422	:> "$sout"
423	:> "$capout"
424
425	if [ $capture -eq 1 ]; then
426		if [ -z $SUDO_USER ] ; then
427			capuser=""
428		else
429			capuser="-Z $SUDO_USER"
430		fi
431
432		capfile=$(printf "mp_join-%02u-%s.pcap" "$TEST_COUNT" "${listener_ns}")
433
434		echo "Capturing traffic for test $TEST_COUNT into $capfile"
435		ip netns exec ${listener_ns} tcpdump -i any -s 65535 -B 32768 $capuser -w $capfile > "$capout" 2>&1 &
436		cappid=$!
437
438		sleep 1
439	fi
440
441	NSTAT_HISTORY=/tmp/${listener_ns}.nstat ip netns exec ${listener_ns} \
442		nstat -n
443	NSTAT_HISTORY=/tmp/${connector_ns}.nstat ip netns exec ${connector_ns} \
444		nstat -n
445
446	if [ $speed = "fast" ]; then
447		mptcp_connect="./mptcp_connect -j"
448	elif [ $speed = "slow" ]; then
449		mptcp_connect="./mptcp_connect -r 50"
450	elif [ $speed = "least" ]; then
451		mptcp_connect="./mptcp_connect -r 10"
452	fi
453
454	local local_addr
455	if is_v6 "${connect_addr}"; then
456		local_addr="::"
457	else
458		local_addr="0.0.0.0"
459	fi
460
461	if [ "$test_link_fail" -eq 2 ];then
462		timeout ${timeout_test} \
463			ip netns exec ${listener_ns} \
464				$mptcp_connect -t ${timeout_poll} -l -p $port -s ${srv_proto} \
465					${local_addr} < "$sinfail" > "$sout" &
466	else
467		timeout ${timeout_test} \
468			ip netns exec ${listener_ns} \
469				$mptcp_connect -t ${timeout_poll} -l -p $port -s ${srv_proto} \
470					${local_addr} < "$sin" > "$sout" &
471	fi
472	spid=$!
473
474	wait_local_port_listen "${listener_ns}" "${port}"
475
476	if [ "$test_link_fail" -eq 0 ];then
477		timeout ${timeout_test} \
478			ip netns exec ${connector_ns} \
479				$mptcp_connect -t ${timeout_poll} -p $port -s ${cl_proto} \
480					$connect_addr < "$cin" > "$cout" &
481	else
482		( cat "$cinfail" ; sleep 2; link_failure $listener_ns ; cat "$cinfail" ) | \
483			tee "$cinsent" | \
484			timeout ${timeout_test} \
485				ip netns exec ${connector_ns} \
486					$mptcp_connect -t ${timeout_poll} -p $port -s ${cl_proto} \
487						$connect_addr > "$cout" &
488	fi
489	cpid=$!
490
491	# let the mptcp subflow be established in background before
492	# do endpoint manipulation
493	[ $addr_nr_ns1 = "0" -a $addr_nr_ns2 = "0" ] || sleep 1
494
495	if [ $addr_nr_ns1 -gt 0 ]; then
496		let add_nr_ns1=addr_nr_ns1
497		counter=2
498		while [ $add_nr_ns1 -gt 0 ]; do
499			local addr
500			if is_v6 "${connect_addr}"; then
501				addr="dead:beef:$counter::1"
502			else
503				addr="10.0.$counter.1"
504			fi
505			pm_nl_add_endpoint $ns1 $addr flags signal
506			let counter+=1
507			let add_nr_ns1-=1
508		done
509	elif [ $addr_nr_ns1 -lt 0 ]; then
510		let rm_nr_ns1=-addr_nr_ns1
511		if [ $rm_nr_ns1 -lt 8 ]; then
512			counter=0
513			pm_nl_show_endpoints ${listener_ns} | while read line; do
514				local arr=($line)
515				local nr=0
516
517				for i in ${arr[@]}; do
518					if [ $i = "id" ]; then
519						if [ $counter -eq $rm_nr_ns1 ]; then
520							break
521						fi
522						id=${arr[$nr+1]}
523						rm_addr=$(rm_addr_count ${connector_ns})
524						pm_nl_del_endpoint ${listener_ns} $id
525						wait_rm_addr ${connector_ns} ${rm_addr}
526						let counter+=1
527					fi
528					let nr+=1
529				done
530			done
531		elif [ $rm_nr_ns1 -eq 8 ]; then
532			pm_nl_flush_endpoint ${listener_ns}
533		elif [ $rm_nr_ns1 -eq 9 ]; then
534			pm_nl_del_endpoint ${listener_ns} 0 ${connect_addr}
535		fi
536	fi
537
538	flags="subflow"
539	if [[ "${addr_nr_ns2}" = "fullmesh_"* ]]; then
540		flags="${flags},fullmesh"
541		addr_nr_ns2=${addr_nr_ns2:9}
542	fi
543
544	# if newly added endpoints must be deleted, give the background msk
545	# some time to created them
546	[ $addr_nr_ns1 -gt 0 -a $addr_nr_ns2 -lt 0 ] && sleep 1
547
548	if [ $addr_nr_ns2 -gt 0 ]; then
549		let add_nr_ns2=addr_nr_ns2
550		counter=3
551		while [ $add_nr_ns2 -gt 0 ]; do
552			local addr
553			if is_v6 "${connect_addr}"; then
554				addr="dead:beef:$counter::2"
555			else
556				addr="10.0.$counter.2"
557			fi
558			pm_nl_add_endpoint $ns2 $addr flags $flags
559			let counter+=1
560			let add_nr_ns2-=1
561		done
562	elif [ $addr_nr_ns2 -lt 0 ]; then
563		let rm_nr_ns2=-addr_nr_ns2
564		if [ $rm_nr_ns2 -lt 8 ]; then
565			counter=0
566			pm_nl_show_endpoints ${connector_ns} | while read line; do
567				local arr=($line)
568				local nr=0
569
570				for i in ${arr[@]}; do
571					if [ $i = "id" ]; then
572						if [ $counter -eq $rm_nr_ns2 ]; then
573							break
574						fi
575						# rm_addr are serialized, allow the previous one to
576						# complete
577						id=${arr[$nr+1]}
578						rm_addr=$(rm_addr_count ${listener_ns})
579						pm_nl_del_endpoint ${connector_ns} $id
580						wait_rm_addr ${listener_ns} ${rm_addr}
581						let counter+=1
582					fi
583					let nr+=1
584				done
585			done
586		elif [ $rm_nr_ns2 -eq 8 ]; then
587			pm_nl_flush_endpoint ${connector_ns}
588		elif [ $rm_nr_ns2 -eq 9 ]; then
589			local addr
590			if is_v6 "${connect_addr}"; then
591				addr="dead:beef:1::2"
592			else
593				addr="10.0.1.2"
594			fi
595			pm_nl_del_endpoint ${connector_ns} 0 $addr
596		fi
597	fi
598
599	if [ ! -z $sflags ]; then
600		sleep 1
601		for netns in "$ns1" "$ns2"; do
602			pm_nl_show_endpoints $netns | while read line; do
603				local arr=($line)
604				local nr=0
605				local id
606
607				for i in ${arr[@]}; do
608					if [ $i = "id" ]; then
609						id=${arr[$nr+1]}
610					fi
611					let nr+=1
612				done
613				pm_nl_change_endpoint $netns $id $sflags
614			done
615		done
616	fi
617
618	wait $cpid
619	retc=$?
620	wait $spid
621	rets=$?
622
623	if [ $capture -eq 1 ]; then
624	    sleep 1
625	    kill $cappid
626	fi
627
628	NSTAT_HISTORY=/tmp/${listener_ns}.nstat ip netns exec ${listener_ns} \
629		nstat | grep Tcp > /tmp/${listener_ns}.out
630	NSTAT_HISTORY=/tmp/${connector_ns}.nstat ip netns exec ${connector_ns} \
631		nstat | grep Tcp > /tmp/${connector_ns}.out
632
633	if [ ${rets} -ne 0 ] || [ ${retc} -ne 0 ]; then
634		echo " client exit code $retc, server $rets" 1>&2
635		echo -e "\nnetns ${listener_ns} socket stat for ${port}:" 1>&2
636		ip netns exec ${listener_ns} ss -Menita 1>&2 -o "sport = :$port"
637		cat /tmp/${listener_ns}.out
638		echo -e "\nnetns ${connector_ns} socket stat for ${port}:" 1>&2
639		ip netns exec ${connector_ns} ss -Menita 1>&2 -o "dport = :$port"
640		cat /tmp/${connector_ns}.out
641
642		cat "$capout"
643		ret=1
644		return 1
645	fi
646
647	if [ "$test_link_fail" -eq 2 ];then
648		check_transfer $sinfail $cout "file received by client"
649	else
650		check_transfer $sin $cout "file received by client"
651	fi
652	retc=$?
653	if [ "$test_link_fail" -eq 0 ];then
654		check_transfer $cin $sout "file received by server"
655	else
656		check_transfer $cinsent $sout "file received by server"
657	fi
658	rets=$?
659
660	if [ $retc -eq 0 ] && [ $rets -eq 0 ];then
661		cat "$capout"
662		return 0
663	fi
664
665	cat "$capout"
666	return 1
667}
668
669make_file()
670{
671	name=$1
672	who=$2
673	size=$3
674
675	dd if=/dev/urandom of="$name" bs=1024 count=$size 2> /dev/null
676	echo -e "\nMPTCP_TEST_FILE_END_MARKER" >> "$name"
677
678	echo "Created $name (size $size KB) containing data sent by $who"
679}
680
681run_tests()
682{
683	listener_ns="$1"
684	connector_ns="$2"
685	connect_addr="$3"
686	test_linkfail="${4:-0}"
687	addr_nr_ns1="${5:-0}"
688	addr_nr_ns2="${6:-0}"
689	speed="${7:-fast}"
690	sflags="${8:-""}"
691
692	# create the input file for the failure test when
693	# the first failure test run
694	if [ "$test_linkfail" -ne 0 -a -z "$cinfail" ]; then
695		# the client file must be considerably larger
696		# of the maximum expected cwin value, or the
697		# link utilization will be not predicable
698		size=$((RANDOM%2))
699		size=$((size+1))
700		size=$((size*8192))
701		size=$((size + ( $RANDOM % 8192) ))
702
703		cinfail=$(mktemp)
704		make_file "$cinfail" "client" $size
705	fi
706
707	if [ "$test_linkfail" -eq 2 -a -z "$sinfail" ]; then
708		size=$((RANDOM%16))
709		size=$((size+1))
710		size=$((size*2048))
711
712		sinfail=$(mktemp)
713		make_file "$sinfail" "server" $size
714	fi
715
716	do_transfer ${listener_ns} ${connector_ns} MPTCP MPTCP ${connect_addr} \
717		${test_linkfail} ${addr_nr_ns1} ${addr_nr_ns2} ${speed} ${sflags}
718}
719
720dump_stats()
721{
722	echo Server ns stats
723	ip netns exec $ns1 nstat -as | grep Tcp
724	echo Client ns stats
725	ip netns exec $ns2 nstat -as | grep Tcp
726}
727
728chk_csum_nr()
729{
730	local msg=${1:-""}
731	local count
732	local dump_stats
733
734	if [ ! -z "$msg" ]; then
735		printf "%02u" "$TEST_COUNT"
736	else
737		echo -n "  "
738	fi
739	printf " %-36s %s" "$msg" "sum"
740	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtDataCsumErr | awk '{print $2}'`
741	[ -z "$count" ] && count=0
742	if [ "$count" != 0 ]; then
743		echo "[fail] got $count data checksum error[s] expected 0"
744		ret=1
745		dump_stats=1
746	else
747		echo -n "[ ok ]"
748	fi
749	echo -n " - csum  "
750	count=`ip netns exec $ns2 nstat -as | grep MPTcpExtDataCsumErr | awk '{print $2}'`
751	[ -z "$count" ] && count=0
752	if [ "$count" != 0 ]; then
753		echo "[fail] got $count data checksum error[s] expected 0"
754		ret=1
755		dump_stats=1
756	else
757		echo "[ ok ]"
758	fi
759	[ "${dump_stats}" = 1 ] && dump_stats
760}
761
762chk_fail_nr()
763{
764	local mp_fail_nr_tx=$1
765	local mp_fail_nr_rx=$2
766	local count
767	local dump_stats
768
769	printf "%-39s %s" " " "ftx"
770	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPFailTx | awk '{print $2}'`
771	[ -z "$count" ] && count=0
772	if [ "$count" != "$mp_fail_nr_tx" ]; then
773		echo "[fail] got $count MP_FAIL[s] TX expected $mp_fail_nr_tx"
774		ret=1
775		dump_stats=1
776	else
777		echo -n "[ ok ]"
778	fi
779
780	echo -n " - frx   "
781	count=`ip netns exec $ns2 nstat -as | grep MPTcpExtMPFailRx | awk '{print $2}'`
782	[ -z "$count" ] && count=0
783	if [ "$count" != "$mp_fail_nr_rx" ]; then
784		echo "[fail] got $count MP_FAIL[s] RX expected $mp_fail_nr_rx"
785		ret=1
786		dump_stats=1
787	else
788		echo "[ ok ]"
789	fi
790
791	[ "${dump_stats}" = 1 ] && dump_stats
792}
793
794chk_join_nr()
795{
796	local msg="$1"
797	local syn_nr=$2
798	local syn_ack_nr=$3
799	local ack_nr=$4
800	local count
801	local dump_stats
802	local with_cookie
803
804	printf "%02u %-36s %s" "$TEST_COUNT" "$msg" "syn"
805	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinSynRx | awk '{print $2}'`
806	[ -z "$count" ] && count=0
807	if [ "$count" != "$syn_nr" ]; then
808		echo "[fail] got $count JOIN[s] syn expected $syn_nr"
809		ret=1
810		dump_stats=1
811	else
812		echo -n "[ ok ]"
813	fi
814
815	echo -n " - synack"
816	with_cookie=`ip netns exec $ns2 sysctl -n net.ipv4.tcp_syncookies`
817	count=`ip netns exec $ns2 nstat -as | grep MPTcpExtMPJoinSynAckRx | awk '{print $2}'`
818	[ -z "$count" ] && count=0
819	if [ "$count" != "$syn_ack_nr" ]; then
820		# simult connections exceeding the limit with cookie enabled could go up to
821		# synack validation as the conn limit can be enforced reliably only after
822		# the subflow creation
823		if [ "$with_cookie" = 2 ] && [ "$count" -gt "$syn_ack_nr" ] && [ "$count" -le "$syn_nr" ]; then
824			echo -n "[ ok ]"
825		else
826			echo "[fail] got $count JOIN[s] synack expected $syn_ack_nr"
827			ret=1
828			dump_stats=1
829		fi
830	else
831		echo -n "[ ok ]"
832	fi
833
834	echo -n " - ack"
835	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinAckRx | awk '{print $2}'`
836	[ -z "$count" ] && count=0
837	if [ "$count" != "$ack_nr" ]; then
838		echo "[fail] got $count JOIN[s] ack expected $ack_nr"
839		ret=1
840		dump_stats=1
841	else
842		echo "[ ok ]"
843	fi
844	[ "${dump_stats}" = 1 ] && dump_stats
845	if [ $checksum -eq 1 ]; then
846		chk_csum_nr
847		chk_fail_nr 0 0
848	fi
849}
850
851# a negative value for 'stale_max' means no upper bound:
852# for bidirectional transfer, if one peer sleep for a while
853# - as these tests do - we can have a quite high number of
854# stale/recover conversions, proportional to
855# sleep duration/ MPTCP-level RTX interval.
856chk_stale_nr()
857{
858	local ns=$1
859	local stale_min=$2
860	local stale_max=$3
861	local stale_delta=$4
862	local dump_stats
863	local stale_nr
864	local recover_nr
865
866	printf "%-39s %-18s" " " "stale"
867	stale_nr=`ip netns exec $ns nstat -as | grep MPTcpExtSubflowStale | awk '{print $2}'`
868	[ -z "$stale_nr" ] && stale_nr=0
869	recover_nr=`ip netns exec $ns nstat -as | grep MPTcpExtSubflowRecover | awk '{print $2}'`
870	[ -z "$recover_nr" ] && recover_nr=0
871
872	if [ $stale_nr -lt $stale_min ] ||
873	   [ $stale_max -gt 0 -a $stale_nr -gt $stale_max ] ||
874	   [ $((stale_nr - $recover_nr)) -ne $stale_delta ]; then
875		echo "[fail] got $stale_nr stale[s] $recover_nr recover[s], " \
876		     " expected stale in range [$stale_min..$stale_max]," \
877		     " stale-recover delta $stale_delta "
878		ret=1
879		dump_stats=1
880	else
881		echo "[ ok ]"
882	fi
883
884	if [ "${dump_stats}" = 1 ]; then
885		echo $ns stats
886		ip netns exec $ns ip -s link show
887		ip netns exec $ns nstat -as | grep MPTcp
888	fi
889}
890
891chk_add_nr()
892{
893	local add_nr=$1
894	local echo_nr=$2
895	local port_nr=${3:-0}
896	local syn_nr=${4:-$port_nr}
897	local syn_ack_nr=${5:-$port_nr}
898	local ack_nr=${6:-$port_nr}
899	local mis_syn_nr=${7:-0}
900	local mis_ack_nr=${8:-0}
901	local count
902	local dump_stats
903	local timeout
904
905	timeout=`ip netns exec $ns1 sysctl -n net.mptcp.add_addr_timeout`
906
907	printf "%-39s %s" " " "add"
908	count=`ip netns exec $ns2 nstat -as MPTcpExtAddAddr | grep MPTcpExtAddAddr | awk '{print $2}'`
909	[ -z "$count" ] && count=0
910
911	# if the test configured a short timeout tolerate greater then expected
912	# add addrs options, due to retransmissions
913	if [ "$count" != "$add_nr" ] && [ "$timeout" -gt 1 -o "$count" -lt "$add_nr" ]; then
914		echo "[fail] got $count ADD_ADDR[s] expected $add_nr"
915		ret=1
916		dump_stats=1
917	else
918		echo -n "[ ok ]"
919	fi
920
921	echo -n " - echo  "
922	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtEchoAdd | awk '{print $2}'`
923	[ -z "$count" ] && count=0
924	if [ "$count" != "$echo_nr" ]; then
925		echo "[fail] got $count ADD_ADDR echo[s] expected $echo_nr"
926		ret=1
927		dump_stats=1
928	else
929		echo -n "[ ok ]"
930	fi
931
932	if [ $port_nr -gt 0 ]; then
933		echo -n " - pt "
934		count=`ip netns exec $ns2 nstat -as | grep MPTcpExtPortAdd | awk '{print $2}'`
935		[ -z "$count" ] && count=0
936		if [ "$count" != "$port_nr" ]; then
937			echo "[fail] got $count ADD_ADDR[s] with a port-number expected $port_nr"
938			ret=1
939			dump_stats=1
940		else
941			echo "[ ok ]"
942		fi
943
944		printf "%-39s %s" " " "syn"
945		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinPortSynRx |
946			awk '{print $2}'`
947		[ -z "$count" ] && count=0
948		if [ "$count" != "$syn_nr" ]; then
949			echo "[fail] got $count JOIN[s] syn with a different \
950				port-number expected $syn_nr"
951			ret=1
952			dump_stats=1
953		else
954			echo -n "[ ok ]"
955		fi
956
957		echo -n " - synack"
958		count=`ip netns exec $ns2 nstat -as | grep MPTcpExtMPJoinPortSynAckRx |
959			awk '{print $2}'`
960		[ -z "$count" ] && count=0
961		if [ "$count" != "$syn_ack_nr" ]; then
962			echo "[fail] got $count JOIN[s] synack with a different \
963				port-number expected $syn_ack_nr"
964			ret=1
965			dump_stats=1
966		else
967			echo -n "[ ok ]"
968		fi
969
970		echo -n " - ack"
971		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinPortAckRx |
972			awk '{print $2}'`
973		[ -z "$count" ] && count=0
974		if [ "$count" != "$ack_nr" ]; then
975			echo "[fail] got $count JOIN[s] ack with a different \
976				port-number expected $ack_nr"
977			ret=1
978			dump_stats=1
979		else
980			echo "[ ok ]"
981		fi
982
983		printf "%-39s %s" " " "syn"
984		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMismatchPortSynRx |
985			awk '{print $2}'`
986		[ -z "$count" ] && count=0
987		if [ "$count" != "$mis_syn_nr" ]; then
988			echo "[fail] got $count JOIN[s] syn with a mismatched \
989				port-number expected $mis_syn_nr"
990			ret=1
991			dump_stats=1
992		else
993			echo -n "[ ok ]"
994		fi
995
996		echo -n " - ack   "
997		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMismatchPortAckRx |
998			awk '{print $2}'`
999		[ -z "$count" ] && count=0
1000		if [ "$count" != "$mis_ack_nr" ]; then
1001			echo "[fail] got $count JOIN[s] ack with a mismatched \
1002				port-number expected $mis_ack_nr"
1003			ret=1
1004			dump_stats=1
1005		else
1006			echo "[ ok ]"
1007		fi
1008	else
1009		echo ""
1010	fi
1011
1012	[ "${dump_stats}" = 1 ] && dump_stats
1013}
1014
1015chk_rm_nr()
1016{
1017	local rm_addr_nr=$1
1018	local rm_subflow_nr=$2
1019	local invert=${3:-""}
1020	local count
1021	local dump_stats
1022	local addr_ns
1023	local subflow_ns
1024
1025	if [ -z $invert ]; then
1026		addr_ns=$ns1
1027		subflow_ns=$ns2
1028	elif [ $invert = "invert" ]; then
1029		addr_ns=$ns2
1030		subflow_ns=$ns1
1031	fi
1032
1033	printf "%-39s %s" " " "rm "
1034	count=`ip netns exec $addr_ns nstat -as | grep MPTcpExtRmAddr | awk '{print $2}'`
1035	[ -z "$count" ] && count=0
1036	if [ "$count" != "$rm_addr_nr" ]; then
1037		echo "[fail] got $count RM_ADDR[s] expected $rm_addr_nr"
1038		ret=1
1039		dump_stats=1
1040	else
1041		echo -n "[ ok ]"
1042	fi
1043
1044	echo -n " - sf    "
1045	count=`ip netns exec $subflow_ns nstat -as | grep MPTcpExtRmSubflow | awk '{print $2}'`
1046	[ -z "$count" ] && count=0
1047	if [ "$count" != "$rm_subflow_nr" ]; then
1048		echo "[fail] got $count RM_SUBFLOW[s] expected $rm_subflow_nr"
1049		ret=1
1050		dump_stats=1
1051	else
1052		echo "[ ok ]"
1053	fi
1054
1055	[ "${dump_stats}" = 1 ] && dump_stats
1056}
1057
1058chk_prio_nr()
1059{
1060	local mp_prio_nr_tx=$1
1061	local mp_prio_nr_rx=$2
1062	local count
1063	local dump_stats
1064
1065	printf "%-39s %s" " " "ptx"
1066	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPPrioTx | awk '{print $2}'`
1067	[ -z "$count" ] && count=0
1068	if [ "$count" != "$mp_prio_nr_tx" ]; then
1069		echo "[fail] got $count MP_PRIO[s] TX expected $mp_prio_nr_tx"
1070		ret=1
1071		dump_stats=1
1072	else
1073		echo -n "[ ok ]"
1074	fi
1075
1076	echo -n " - prx   "
1077	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPPrioRx | awk '{print $2}'`
1078	[ -z "$count" ] && count=0
1079	if [ "$count" != "$mp_prio_nr_rx" ]; then
1080		echo "[fail] got $count MP_PRIO[s] RX expected $mp_prio_nr_rx"
1081		ret=1
1082		dump_stats=1
1083	else
1084		echo "[ ok ]"
1085	fi
1086
1087	[ "${dump_stats}" = 1 ] && dump_stats
1088}
1089
1090chk_link_usage()
1091{
1092	local ns=$1
1093	local link=$2
1094	local out=$3
1095	local expected_rate=$4
1096	local tx_link=`ip netns exec $ns cat /sys/class/net/$link/statistics/tx_bytes`
1097	local tx_total=`ls -l $out | awk '{print $5}'`
1098	local tx_rate=$((tx_link * 100 / $tx_total))
1099	local tolerance=5
1100
1101	printf "%-39s %-18s" " " "link usage"
1102	if [ $tx_rate -lt $((expected_rate - $tolerance)) -o \
1103	     $tx_rate -gt $((expected_rate + $tolerance)) ]; then
1104		echo "[fail] got $tx_rate% usage, expected $expected_rate%"
1105		ret=1
1106	else
1107		echo "[ ok ]"
1108	fi
1109}
1110
1111wait_for_tw()
1112{
1113	local timeout_ms=$((timeout_poll * 1000))
1114	local time=0
1115	local ns=$1
1116
1117	while [ $time -lt $timeout_ms ]; do
1118		local cnt=$(ip netns exec $ns nstat -as TcpAttemptFails | grep TcpAttemptFails | awk '{print $2}')
1119
1120		[ "$cnt" = 1 ] && return 1
1121		time=$((time + 100))
1122		sleep 0.1
1123	done
1124	return 1
1125}
1126
1127subflows_tests()
1128{
1129	reset
1130	run_tests $ns1 $ns2 10.0.1.1
1131	chk_join_nr "no JOIN" "0" "0" "0"
1132
1133	# subflow limited by client
1134	reset
1135	pm_nl_set_limits $ns1 0 0
1136	pm_nl_set_limits $ns2 0 0
1137	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1138	run_tests $ns1 $ns2 10.0.1.1
1139	chk_join_nr "single subflow, limited by client" 0 0 0
1140
1141	# subflow limited by server
1142	reset
1143	pm_nl_set_limits $ns1 0 0
1144	pm_nl_set_limits $ns2 0 1
1145	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1146	run_tests $ns1 $ns2 10.0.1.1
1147	chk_join_nr "single subflow, limited by server" 1 1 0
1148
1149	# subflow
1150	reset
1151	pm_nl_set_limits $ns1 0 1
1152	pm_nl_set_limits $ns2 0 1
1153	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1154	run_tests $ns1 $ns2 10.0.1.1
1155	chk_join_nr "single subflow" 1 1 1
1156
1157	# multiple subflows
1158	reset
1159	pm_nl_set_limits $ns1 0 2
1160	pm_nl_set_limits $ns2 0 2
1161	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1162	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1163	run_tests $ns1 $ns2 10.0.1.1
1164	chk_join_nr "multiple subflows" 2 2 2
1165
1166	# multiple subflows limited by server
1167	reset
1168	pm_nl_set_limits $ns1 0 1
1169	pm_nl_set_limits $ns2 0 2
1170	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1171	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1172	run_tests $ns1 $ns2 10.0.1.1
1173	chk_join_nr "multiple subflows, limited by server" 2 2 1
1174
1175	# single subflow, dev
1176	reset
1177	pm_nl_set_limits $ns1 0 1
1178	pm_nl_set_limits $ns2 0 1
1179	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow dev ns2eth3
1180	run_tests $ns1 $ns2 10.0.1.1
1181	chk_join_nr "single subflow, dev" 1 1 1
1182}
1183
1184subflows_error_tests()
1185{
1186	# If a single subflow is configured, and matches the MPC src
1187	# address, no additional subflow should be created
1188	reset
1189	pm_nl_set_limits $ns1 0 1
1190	pm_nl_set_limits $ns2 0 1
1191	pm_nl_add_endpoint $ns2 10.0.1.2 flags subflow
1192	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
1193	chk_join_nr "no MPC reuse with single endpoint" 0 0 0
1194
1195	# multiple subflows, with subflow creation error
1196	reset
1197	pm_nl_set_limits $ns1 0 2
1198	pm_nl_set_limits $ns2 0 2
1199	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1200	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1201	ip netns exec $ns1 iptables -A INPUT -s 10.0.3.2 -p tcp -j REJECT
1202	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
1203	chk_join_nr "multi subflows, with failing subflow" 1 1 1
1204
1205	# multiple subflows, with subflow timeout on MPJ
1206	reset
1207	pm_nl_set_limits $ns1 0 2
1208	pm_nl_set_limits $ns2 0 2
1209	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1210	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1211	ip netns exec $ns1 iptables -A INPUT -s 10.0.3.2 -p tcp -j DROP
1212	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
1213	chk_join_nr "multi subflows, with subflow timeout" 1 1 1
1214
1215	# multiple subflows, check that the endpoint corresponding to
1216	# closed subflow (due to reset) is not reused if additional
1217	# subflows are added later
1218	reset
1219	pm_nl_set_limits $ns1 0 1
1220	pm_nl_set_limits $ns2 0 1
1221	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1222	ip netns exec $ns1 iptables -A INPUT -s 10.0.3.2 -p tcp -j REJECT
1223	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow &
1224
1225	# updates in the child shell do not have any effect here, we
1226	# need to bump the test counter for the above case
1227	TEST_COUNT=$((TEST_COUNT+1))
1228
1229	# mpj subflow will be in TW after the reset
1230	wait_for_tw $ns2
1231	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1232	wait
1233
1234	# additional subflow could be created only if the PM select
1235	# the later endpoint, skipping the already used one
1236	chk_join_nr "multi subflows, fair usage on close" 1 1 1
1237}
1238
1239signal_address_tests()
1240{
1241	# add_address, unused
1242	reset
1243	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1244	run_tests $ns1 $ns2 10.0.1.1
1245	chk_join_nr "unused signal address" 0 0 0
1246	chk_add_nr 1 1
1247
1248	# accept and use add_addr
1249	reset
1250	pm_nl_set_limits $ns1 0 1
1251	pm_nl_set_limits $ns2 1 1
1252	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1253	run_tests $ns1 $ns2 10.0.1.1
1254	chk_join_nr "signal address" 1 1 1
1255	chk_add_nr 1 1
1256
1257	# accept and use add_addr with an additional subflow
1258	# note: signal address in server ns and local addresses in client ns must
1259	# belong to different subnets or one of the listed local address could be
1260	# used for 'add_addr' subflow
1261	reset
1262	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1263	pm_nl_set_limits $ns1 0 2
1264	pm_nl_set_limits $ns2 1 2
1265	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1266	run_tests $ns1 $ns2 10.0.1.1
1267	chk_join_nr "subflow and signal" 2 2 2
1268	chk_add_nr 1 1
1269
1270	# accept and use add_addr with additional subflows
1271	reset
1272	pm_nl_set_limits $ns1 0 3
1273	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1274	pm_nl_set_limits $ns2 1 3
1275	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1276	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1277	run_tests $ns1 $ns2 10.0.1.1
1278	chk_join_nr "multiple subflows and signal" 3 3 3
1279	chk_add_nr 1 1
1280
1281	# signal addresses
1282	reset
1283	pm_nl_set_limits $ns1 3 3
1284	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1285	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1286	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
1287	pm_nl_set_limits $ns2 3 3
1288	run_tests $ns1 $ns2 10.0.1.1
1289	chk_join_nr "signal addresses" 3 3 3
1290	chk_add_nr 3 3
1291
1292	# signal invalid addresses
1293	reset
1294	pm_nl_set_limits $ns1 3 3
1295	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
1296	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1297	pm_nl_add_endpoint $ns1 10.0.14.1 flags signal
1298	pm_nl_set_limits $ns2 3 3
1299	run_tests $ns1 $ns2 10.0.1.1
1300	chk_join_nr "signal invalid addresses" 1 1 1
1301	chk_add_nr 3 3
1302
1303	# signal addresses race test
1304	reset
1305	pm_nl_set_limits $ns1 4 4
1306	pm_nl_set_limits $ns2 4 4
1307	pm_nl_add_endpoint $ns1 10.0.1.1 flags signal
1308	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1309	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1310	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
1311	pm_nl_add_endpoint $ns2 10.0.1.2 flags signal
1312	pm_nl_add_endpoint $ns2 10.0.2.2 flags signal
1313	pm_nl_add_endpoint $ns2 10.0.3.2 flags signal
1314	pm_nl_add_endpoint $ns2 10.0.4.2 flags signal
1315
1316	# the peer could possibly miss some addr notification, allow retransmission
1317	ip netns exec $ns1 sysctl -q net.mptcp.add_addr_timeout=1
1318	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
1319	chk_join_nr "signal addresses race test" 3 3 3
1320
1321	# the server will not signal the address terminating
1322	# the MPC subflow
1323	chk_add_nr 3 3
1324}
1325
1326link_failure_tests()
1327{
1328	# accept and use add_addr with additional subflows and link loss
1329	reset
1330
1331	# without any b/w limit each veth could spool the packets and get
1332	# them acked at xmit time, so that the corresponding subflow will
1333	# have almost always no outstanding pkts, the scheduler will pick
1334	# always the first subflow and we will have hard time testing
1335	# active backup and link switch-over.
1336	# Let's set some arbitrary (low) virtual link limits.
1337	init_shapers
1338	pm_nl_set_limits $ns1 0 3
1339	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
1340	pm_nl_set_limits $ns2 1 3
1341	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow
1342	pm_nl_add_endpoint $ns2 10.0.4.2 dev ns2eth4 flags subflow
1343	run_tests $ns1 $ns2 10.0.1.1 1
1344	chk_join_nr "multiple flows, signal, link failure" 3 3 3
1345	chk_add_nr 1 1
1346	chk_stale_nr $ns2 1 5 1
1347
1348	# accept and use add_addr with additional subflows and link loss
1349	# for bidirectional transfer
1350	reset
1351	init_shapers
1352	pm_nl_set_limits $ns1 0 3
1353	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
1354	pm_nl_set_limits $ns2 1 3
1355	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow
1356	pm_nl_add_endpoint $ns2 10.0.4.2 dev ns2eth4 flags subflow
1357	run_tests $ns1 $ns2 10.0.1.1 2
1358	chk_join_nr "multi flows, signal, bidi, link fail" 3 3 3
1359	chk_add_nr 1 1
1360	chk_stale_nr $ns2 1 -1 1
1361
1362	# 2 subflows plus 1 backup subflow with a lossy link, backup
1363	# will never be used
1364	reset
1365	init_shapers
1366	pm_nl_set_limits $ns1 0 2
1367	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
1368	pm_nl_set_limits $ns2 1 2
1369	export FAILING_LINKS="1"
1370	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow,backup
1371	run_tests $ns1 $ns2 10.0.1.1 1
1372	chk_join_nr "backup subflow unused, link failure" 2 2 2
1373	chk_add_nr 1 1
1374	chk_link_usage $ns2 ns2eth3 $cinsent 0
1375
1376	# 2 lossy links after half transfer, backup will get half of
1377	# the traffic
1378	reset
1379	init_shapers
1380	pm_nl_set_limits $ns1 0 2
1381	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
1382	pm_nl_set_limits $ns2 1 2
1383	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow,backup
1384	export FAILING_LINKS="1 2"
1385	run_tests $ns1 $ns2 10.0.1.1 1
1386	chk_join_nr "backup flow used, multi links fail" 2 2 2
1387	chk_add_nr 1 1
1388	chk_stale_nr $ns2 2 4 2
1389	chk_link_usage $ns2 ns2eth3 $cinsent 50
1390
1391	# use a backup subflow with the first subflow on a lossy link
1392	# for bidirectional transfer
1393	reset
1394	init_shapers
1395	pm_nl_set_limits $ns1 0 2
1396	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
1397	pm_nl_set_limits $ns2 1 3
1398	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow,backup
1399	run_tests $ns1 $ns2 10.0.1.1 2
1400	chk_join_nr "backup flow used, bidi, link failure" 2 2 2
1401	chk_add_nr 1 1
1402	chk_stale_nr $ns2 1 -1 2
1403	chk_link_usage $ns2 ns2eth3 $cinsent 50
1404}
1405
1406add_addr_timeout_tests()
1407{
1408	# add_addr timeout
1409	reset_with_add_addr_timeout
1410	pm_nl_set_limits $ns1 0 1
1411	pm_nl_set_limits $ns2 1 1
1412	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1413	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
1414	chk_join_nr "signal address, ADD_ADDR timeout" 1 1 1
1415	chk_add_nr 4 0
1416
1417	# add_addr timeout IPv6
1418	reset_with_add_addr_timeout 6
1419	pm_nl_set_limits $ns1 0 1
1420	pm_nl_set_limits $ns2 1 1
1421	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
1422	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
1423	chk_join_nr "signal address, ADD_ADDR6 timeout" 1 1 1
1424	chk_add_nr 4 0
1425
1426	# signal addresses timeout
1427	reset_with_add_addr_timeout
1428	pm_nl_set_limits $ns1 2 2
1429	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1430	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1431	pm_nl_set_limits $ns2 2 2
1432	run_tests $ns1 $ns2 10.0.1.1 0 0 0 least
1433	chk_join_nr "signal addresses, ADD_ADDR timeout" 2 2 2
1434	chk_add_nr 8 0
1435
1436	# signal invalid addresses timeout
1437	reset_with_add_addr_timeout
1438	pm_nl_set_limits $ns1 2 2
1439	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
1440	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1441	pm_nl_set_limits $ns2 2 2
1442	run_tests $ns1 $ns2 10.0.1.1 0 0 0 least
1443	chk_join_nr "invalid address, ADD_ADDR timeout" 1 1 1
1444	chk_add_nr 8 0
1445}
1446
1447remove_tests()
1448{
1449	# single subflow, remove
1450	reset
1451	pm_nl_set_limits $ns1 0 1
1452	pm_nl_set_limits $ns2 0 1
1453	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1454	run_tests $ns1 $ns2 10.0.1.1 0 0 -1 slow
1455	chk_join_nr "remove single subflow" 1 1 1
1456	chk_rm_nr 1 1
1457
1458	# multiple subflows, remove
1459	reset
1460	pm_nl_set_limits $ns1 0 2
1461	pm_nl_set_limits $ns2 0 2
1462	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1463	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1464	run_tests $ns1 $ns2 10.0.1.1 0 0 -2 slow
1465	chk_join_nr "remove multiple subflows" 2 2 2
1466	chk_rm_nr 2 2
1467
1468	# single address, remove
1469	reset
1470	pm_nl_set_limits $ns1 0 1
1471	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1472	pm_nl_set_limits $ns2 1 1
1473	run_tests $ns1 $ns2 10.0.1.1 0 -1 0 slow
1474	chk_join_nr "remove single address" 1 1 1
1475	chk_add_nr 1 1
1476	chk_rm_nr 1 1 invert
1477
1478	# subflow and signal, remove
1479	reset
1480	pm_nl_set_limits $ns1 0 2
1481	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1482	pm_nl_set_limits $ns2 1 2
1483	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1484	run_tests $ns1 $ns2 10.0.1.1 0 -1 -1 slow
1485	chk_join_nr "remove subflow and signal" 2 2 2
1486	chk_add_nr 1 1
1487	chk_rm_nr 1 1
1488
1489	# subflows and signal, remove
1490	reset
1491	pm_nl_set_limits $ns1 0 3
1492	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1493	pm_nl_set_limits $ns2 1 3
1494	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1495	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1496	run_tests $ns1 $ns2 10.0.1.1 0 -1 -2 slow
1497	chk_join_nr "remove subflows and signal" 3 3 3
1498	chk_add_nr 1 1
1499	chk_rm_nr 2 2
1500
1501	# addresses remove
1502	reset
1503	pm_nl_set_limits $ns1 3 3
1504	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal id 250
1505	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1506	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
1507	pm_nl_set_limits $ns2 3 3
1508	run_tests $ns1 $ns2 10.0.1.1 0 -3 0 slow
1509	chk_join_nr "remove addresses" 3 3 3
1510	chk_add_nr 3 3
1511	chk_rm_nr 3 3 invert
1512
1513	# invalid addresses remove
1514	reset
1515	pm_nl_set_limits $ns1 3 3
1516	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
1517	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1518	pm_nl_add_endpoint $ns1 10.0.14.1 flags signal
1519	pm_nl_set_limits $ns2 3 3
1520	run_tests $ns1 $ns2 10.0.1.1 0 -3 0 slow
1521	chk_join_nr "remove invalid addresses" 1 1 1
1522	chk_add_nr 3 3
1523	chk_rm_nr 3 1 invert
1524
1525	# subflows and signal, flush
1526	reset
1527	pm_nl_set_limits $ns1 0 3
1528	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1529	pm_nl_set_limits $ns2 1 3
1530	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1531	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1532	run_tests $ns1 $ns2 10.0.1.1 0 -8 -8 slow
1533	chk_join_nr "flush subflows and signal" 3 3 3
1534	chk_add_nr 1 1
1535	chk_rm_nr 2 2
1536
1537	# subflows flush
1538	reset
1539	pm_nl_set_limits $ns1 3 3
1540	pm_nl_set_limits $ns2 3 3
1541	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow id 150
1542	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1543	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1544	run_tests $ns1 $ns2 10.0.1.1 0 -8 -8 slow
1545	chk_join_nr "flush subflows" 3 3 3
1546	chk_rm_nr 3 3
1547
1548	# addresses flush
1549	reset
1550	pm_nl_set_limits $ns1 3 3
1551	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal id 250
1552	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1553	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
1554	pm_nl_set_limits $ns2 3 3
1555	run_tests $ns1 $ns2 10.0.1.1 0 -8 -8 slow
1556	chk_join_nr "flush addresses" 3 3 3
1557	chk_add_nr 3 3
1558	chk_rm_nr 3 3 invert
1559
1560	# invalid addresses flush
1561	reset
1562	pm_nl_set_limits $ns1 3 3
1563	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
1564	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
1565	pm_nl_add_endpoint $ns1 10.0.14.1 flags signal
1566	pm_nl_set_limits $ns2 3 3
1567	run_tests $ns1 $ns2 10.0.1.1 0 -8 0 slow
1568	chk_join_nr "flush invalid addresses" 1 1 1
1569	chk_add_nr 3 3
1570	chk_rm_nr 3 1 invert
1571
1572	# remove id 0 subflow
1573	reset
1574	pm_nl_set_limits $ns1 0 1
1575	pm_nl_set_limits $ns2 0 1
1576	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1577	run_tests $ns1 $ns2 10.0.1.1 0 0 -9 slow
1578	chk_join_nr "remove id 0 subflow" 1 1 1
1579	chk_rm_nr 1 1
1580
1581	# remove id 0 address
1582	reset
1583	pm_nl_set_limits $ns1 0 1
1584	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1585	pm_nl_set_limits $ns2 1 1
1586	run_tests $ns1 $ns2 10.0.1.1 0 -9 0 slow
1587	chk_join_nr "remove id 0 address" 1 1 1
1588	chk_add_nr 1 1
1589	chk_rm_nr 1 1 invert
1590}
1591
1592add_tests()
1593{
1594	# add single subflow
1595	reset
1596	pm_nl_set_limits $ns1 0 1
1597	pm_nl_set_limits $ns2 0 1
1598	run_tests $ns1 $ns2 10.0.1.1 0 0 1 slow
1599	chk_join_nr "add single subflow" 1 1 1
1600
1601	# add signal address
1602	reset
1603	pm_nl_set_limits $ns1 0 1
1604	pm_nl_set_limits $ns2 1 1
1605	run_tests $ns1 $ns2 10.0.1.1 0 1 0 slow
1606	chk_join_nr "add signal address" 1 1 1
1607	chk_add_nr 1 1
1608
1609	# add multiple subflows
1610	reset
1611	pm_nl_set_limits $ns1 0 2
1612	pm_nl_set_limits $ns2 0 2
1613	run_tests $ns1 $ns2 10.0.1.1 0 0 2 slow
1614	chk_join_nr "add multiple subflows" 2 2 2
1615
1616	# add multiple subflows IPv6
1617	reset
1618	pm_nl_set_limits $ns1 0 2
1619	pm_nl_set_limits $ns2 0 2
1620	run_tests $ns1 $ns2 dead:beef:1::1 0 0 2 slow
1621	chk_join_nr "add multiple subflows IPv6" 2 2 2
1622
1623	# add multiple addresses IPv6
1624	reset
1625	pm_nl_set_limits $ns1 0 2
1626	pm_nl_set_limits $ns2 2 2
1627	run_tests $ns1 $ns2 dead:beef:1::1 0 2 0 slow
1628	chk_join_nr "add multiple addresses IPv6" 2 2 2
1629	chk_add_nr 2 2
1630}
1631
1632ipv6_tests()
1633{
1634	# subflow IPv6
1635	reset
1636	pm_nl_set_limits $ns1 0 1
1637	pm_nl_set_limits $ns2 0 1
1638	pm_nl_add_endpoint $ns2 dead:beef:3::2 dev ns2eth3 flags subflow
1639	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
1640	chk_join_nr "single subflow IPv6" 1 1 1
1641
1642	# add_address, unused IPv6
1643	reset
1644	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
1645	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
1646	chk_join_nr "unused signal address IPv6" 0 0 0
1647	chk_add_nr 1 1
1648
1649	# signal address IPv6
1650	reset
1651	pm_nl_set_limits $ns1 0 1
1652	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
1653	pm_nl_set_limits $ns2 1 1
1654	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
1655	chk_join_nr "single address IPv6" 1 1 1
1656	chk_add_nr 1 1
1657
1658	# single address IPv6, remove
1659	reset
1660	pm_nl_set_limits $ns1 0 1
1661	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
1662	pm_nl_set_limits $ns2 1 1
1663	run_tests $ns1 $ns2 dead:beef:1::1 0 -1 0 slow
1664	chk_join_nr "remove single address IPv6" 1 1 1
1665	chk_add_nr 1 1
1666	chk_rm_nr 1 1 invert
1667
1668	# subflow and signal IPv6, remove
1669	reset
1670	pm_nl_set_limits $ns1 0 2
1671	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
1672	pm_nl_set_limits $ns2 1 2
1673	pm_nl_add_endpoint $ns2 dead:beef:3::2 dev ns2eth3 flags subflow
1674	run_tests $ns1 $ns2 dead:beef:1::1 0 -1 -1 slow
1675	chk_join_nr "remove subflow and signal IPv6" 2 2 2
1676	chk_add_nr 1 1
1677	chk_rm_nr 1 1
1678}
1679
1680v4mapped_tests()
1681{
1682	# subflow IPv4-mapped to IPv4-mapped
1683	reset
1684	pm_nl_set_limits $ns1 0 1
1685	pm_nl_set_limits $ns2 0 1
1686	pm_nl_add_endpoint $ns2 "::ffff:10.0.3.2" flags subflow
1687	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1688	chk_join_nr "single subflow IPv4-mapped" 1 1 1
1689
1690	# signal address IPv4-mapped with IPv4-mapped sk
1691	reset
1692	pm_nl_set_limits $ns1 0 1
1693	pm_nl_set_limits $ns2 1 1
1694	pm_nl_add_endpoint $ns1 "::ffff:10.0.2.1" flags signal
1695	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1696	chk_join_nr "signal address IPv4-mapped" 1 1 1
1697	chk_add_nr 1 1
1698
1699	# subflow v4-map-v6
1700	reset
1701	pm_nl_set_limits $ns1 0 1
1702	pm_nl_set_limits $ns2 0 1
1703	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1704	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1705	chk_join_nr "single subflow v4-map-v6" 1 1 1
1706
1707	# signal address v4-map-v6
1708	reset
1709	pm_nl_set_limits $ns1 0 1
1710	pm_nl_set_limits $ns2 1 1
1711	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1712	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1713	chk_join_nr "signal address v4-map-v6" 1 1 1
1714	chk_add_nr 1 1
1715
1716	# subflow v6-map-v4
1717	reset
1718	pm_nl_set_limits $ns1 0 1
1719	pm_nl_set_limits $ns2 0 1
1720	pm_nl_add_endpoint $ns2 "::ffff:10.0.3.2" flags subflow
1721	run_tests $ns1 $ns2 10.0.1.1
1722	chk_join_nr "single subflow v6-map-v4" 1 1 1
1723
1724	# signal address v6-map-v4
1725	reset
1726	pm_nl_set_limits $ns1 0 1
1727	pm_nl_set_limits $ns2 1 1
1728	pm_nl_add_endpoint $ns1 "::ffff:10.0.2.1" flags signal
1729	run_tests $ns1 $ns2 10.0.1.1
1730	chk_join_nr "signal address v6-map-v4" 1 1 1
1731	chk_add_nr 1 1
1732
1733	# no subflow IPv6 to v4 address
1734	reset
1735	pm_nl_set_limits $ns1 0 1
1736	pm_nl_set_limits $ns2 0 1
1737	pm_nl_add_endpoint $ns2 dead:beef:2::2 flags subflow
1738	run_tests $ns1 $ns2 10.0.1.1
1739	chk_join_nr "no JOIN with diff families v4-v6" 0 0 0
1740
1741	# no subflow IPv6 to v4 address even if v6 has a valid v4 at the end
1742	reset
1743	pm_nl_set_limits $ns1 0 1
1744	pm_nl_set_limits $ns2 0 1
1745	pm_nl_add_endpoint $ns2 dead:beef:2::10.0.3.2 flags subflow
1746	run_tests $ns1 $ns2 10.0.1.1
1747	chk_join_nr "no JOIN with diff families v4-v6-2" 0 0 0
1748
1749	# no subflow IPv4 to v6 address, no need to slow down too then
1750	reset
1751	pm_nl_set_limits $ns1 0 1
1752	pm_nl_set_limits $ns2 0 1
1753	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1754	run_tests $ns1 $ns2 dead:beef:1::1
1755	chk_join_nr "no JOIN with diff families v6-v4" 0 0 0
1756}
1757
1758backup_tests()
1759{
1760	# single subflow, backup
1761	reset
1762	pm_nl_set_limits $ns1 0 1
1763	pm_nl_set_limits $ns2 0 1
1764	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow,backup
1765	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow nobackup
1766	chk_join_nr "single subflow, backup" 1 1 1
1767	chk_prio_nr 0 1
1768
1769	# single address, backup
1770	reset
1771	pm_nl_set_limits $ns1 0 1
1772	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1773	pm_nl_set_limits $ns2 1 1
1774	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow backup
1775	chk_join_nr "single address, backup" 1 1 1
1776	chk_add_nr 1 1
1777	chk_prio_nr 1 0
1778
1779	# single address with port, backup
1780	reset
1781	pm_nl_set_limits $ns1 0 1
1782	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1783	pm_nl_set_limits $ns2 1 1
1784	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow backup
1785	chk_join_nr "single address with port, backup" 1 1 1
1786	chk_add_nr 1 1
1787	chk_prio_nr 1 0
1788}
1789
1790add_addr_ports_tests()
1791{
1792	# signal address with port
1793	reset
1794	pm_nl_set_limits $ns1 0 1
1795	pm_nl_set_limits $ns2 1 1
1796	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1797	run_tests $ns1 $ns2 10.0.1.1
1798	chk_join_nr "signal address with port" 1 1 1
1799	chk_add_nr 1 1 1
1800
1801	# subflow and signal with port
1802	reset
1803	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1804	pm_nl_set_limits $ns1 0 2
1805	pm_nl_set_limits $ns2 1 2
1806	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1807	run_tests $ns1 $ns2 10.0.1.1
1808	chk_join_nr "subflow and signal with port" 2 2 2
1809	chk_add_nr 1 1 1
1810
1811	# single address with port, remove
1812	reset
1813	pm_nl_set_limits $ns1 0 1
1814	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1815	pm_nl_set_limits $ns2 1 1
1816	run_tests $ns1 $ns2 10.0.1.1 0 -1 0 slow
1817	chk_join_nr "remove single address with port" 1 1 1
1818	chk_add_nr 1 1 1
1819	chk_rm_nr 1 1 invert
1820
1821	# subflow and signal with port, remove
1822	reset
1823	pm_nl_set_limits $ns1 0 2
1824	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1825	pm_nl_set_limits $ns2 1 2
1826	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1827	run_tests $ns1 $ns2 10.0.1.1 0 -1 -1 slow
1828	chk_join_nr "remove subflow and signal with port" 2 2 2
1829	chk_add_nr 1 1 1
1830	chk_rm_nr 1 1
1831
1832	# subflows and signal with port, flush
1833	reset
1834	pm_nl_set_limits $ns1 0 3
1835	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1836	pm_nl_set_limits $ns2 1 3
1837	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1838	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1839	run_tests $ns1 $ns2 10.0.1.1 0 -8 -2 slow
1840	chk_join_nr "flush subflows and signal with port" 3 3 3
1841	chk_add_nr 1 1
1842	chk_rm_nr 2 2
1843
1844	# multiple addresses with port
1845	reset
1846	pm_nl_set_limits $ns1 2 2
1847	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1848	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal port 10100
1849	pm_nl_set_limits $ns2 2 2
1850	run_tests $ns1 $ns2 10.0.1.1
1851	chk_join_nr "multiple addresses with port" 2 2 2
1852	chk_add_nr 2 2 2
1853
1854	# multiple addresses with ports
1855	reset
1856	pm_nl_set_limits $ns1 2 2
1857	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
1858	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal port 10101
1859	pm_nl_set_limits $ns2 2 2
1860	run_tests $ns1 $ns2 10.0.1.1
1861	chk_join_nr "multiple addresses with ports" 2 2 2
1862	chk_add_nr 2 2 2
1863}
1864
1865syncookies_tests()
1866{
1867	# single subflow, syncookies
1868	reset_with_cookies
1869	pm_nl_set_limits $ns1 0 1
1870	pm_nl_set_limits $ns2 0 1
1871	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1872	run_tests $ns1 $ns2 10.0.1.1
1873	chk_join_nr "single subflow with syn cookies" 1 1 1
1874
1875	# multiple subflows with syn cookies
1876	reset_with_cookies
1877	pm_nl_set_limits $ns1 0 2
1878	pm_nl_set_limits $ns2 0 2
1879	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1880	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1881	run_tests $ns1 $ns2 10.0.1.1
1882	chk_join_nr "multiple subflows with syn cookies" 2 2 2
1883
1884	# multiple subflows limited by server
1885	reset_with_cookies
1886	pm_nl_set_limits $ns1 0 1
1887	pm_nl_set_limits $ns2 0 2
1888	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1889	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1890	run_tests $ns1 $ns2 10.0.1.1
1891	chk_join_nr "subflows limited by server w cookies" 2 1 1
1892
1893	# test signal address with cookies
1894	reset_with_cookies
1895	pm_nl_set_limits $ns1 0 1
1896	pm_nl_set_limits $ns2 1 1
1897	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1898	run_tests $ns1 $ns2 10.0.1.1
1899	chk_join_nr "signal address with syn cookies" 1 1 1
1900	chk_add_nr 1 1
1901
1902	# test cookie with subflow and signal
1903	reset_with_cookies
1904	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1905	pm_nl_set_limits $ns1 0 2
1906	pm_nl_set_limits $ns2 1 2
1907	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1908	run_tests $ns1 $ns2 10.0.1.1
1909	chk_join_nr "subflow and signal w cookies" 2 2 2
1910	chk_add_nr 1 1
1911
1912	# accept and use add_addr with additional subflows
1913	reset_with_cookies
1914	pm_nl_set_limits $ns1 0 3
1915	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1916	pm_nl_set_limits $ns2 1 3
1917	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1918	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1919	run_tests $ns1 $ns2 10.0.1.1
1920	chk_join_nr "subflows and signal w. cookies" 3 3 3
1921	chk_add_nr 1 1
1922}
1923
1924checksum_tests()
1925{
1926	# checksum test 0 0
1927	reset_with_checksum 0 0
1928	pm_nl_set_limits $ns1 0 1
1929	pm_nl_set_limits $ns2 0 1
1930	run_tests $ns1 $ns2 10.0.1.1
1931	chk_csum_nr "checksum test 0 0"
1932
1933	# checksum test 1 1
1934	reset_with_checksum 1 1
1935	pm_nl_set_limits $ns1 0 1
1936	pm_nl_set_limits $ns2 0 1
1937	run_tests $ns1 $ns2 10.0.1.1
1938	chk_csum_nr "checksum test 1 1"
1939
1940	# checksum test 0 1
1941	reset_with_checksum 0 1
1942	pm_nl_set_limits $ns1 0 1
1943	pm_nl_set_limits $ns2 0 1
1944	run_tests $ns1 $ns2 10.0.1.1
1945	chk_csum_nr "checksum test 0 1"
1946
1947	# checksum test 1 0
1948	reset_with_checksum 1 0
1949	pm_nl_set_limits $ns1 0 1
1950	pm_nl_set_limits $ns2 0 1
1951	run_tests $ns1 $ns2 10.0.1.1
1952	chk_csum_nr "checksum test 1 0"
1953}
1954
1955deny_join_id0_tests()
1956{
1957	# subflow allow join id0 ns1
1958	reset_with_allow_join_id0 1 0
1959	pm_nl_set_limits $ns1 1 1
1960	pm_nl_set_limits $ns2 1 1
1961	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1962	run_tests $ns1 $ns2 10.0.1.1
1963	chk_join_nr "single subflow allow join id0 ns1" 1 1 1
1964
1965	# subflow allow join id0 ns2
1966	reset_with_allow_join_id0 0 1
1967	pm_nl_set_limits $ns1 1 1
1968	pm_nl_set_limits $ns2 1 1
1969	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1970	run_tests $ns1 $ns2 10.0.1.1
1971	chk_join_nr "single subflow allow join id0 ns2" 0 0 0
1972
1973	# signal address allow join id0 ns1
1974	# ADD_ADDRs are not affected by allow_join_id0 value.
1975	reset_with_allow_join_id0 1 0
1976	pm_nl_set_limits $ns1 1 1
1977	pm_nl_set_limits $ns2 1 1
1978	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1979	run_tests $ns1 $ns2 10.0.1.1
1980	chk_join_nr "signal address allow join id0 ns1" 1 1 1
1981	chk_add_nr 1 1
1982
1983	# signal address allow join id0 ns2
1984	# ADD_ADDRs are not affected by allow_join_id0 value.
1985	reset_with_allow_join_id0 0 1
1986	pm_nl_set_limits $ns1 1 1
1987	pm_nl_set_limits $ns2 1 1
1988	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1989	run_tests $ns1 $ns2 10.0.1.1
1990	chk_join_nr "signal address allow join id0 ns2" 1 1 1
1991	chk_add_nr 1 1
1992
1993	# subflow and address allow join id0 ns1
1994	reset_with_allow_join_id0 1 0
1995	pm_nl_set_limits $ns1 2 2
1996	pm_nl_set_limits $ns2 2 2
1997	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1998	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1999	run_tests $ns1 $ns2 10.0.1.1
2000	chk_join_nr "subflow and address allow join id0 1" 2 2 2
2001
2002	# subflow and address allow join id0 ns2
2003	reset_with_allow_join_id0 0 1
2004	pm_nl_set_limits $ns1 2 2
2005	pm_nl_set_limits $ns2 2 2
2006	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
2007	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
2008	run_tests $ns1 $ns2 10.0.1.1
2009	chk_join_nr "subflow and address allow join id0 2" 1 1 1
2010}
2011
2012fullmesh_tests()
2013{
2014	# fullmesh 1
2015	# 2 fullmesh addrs in ns2, added before the connection,
2016	# 1 non-fullmesh addr in ns1, added during the connection.
2017	reset
2018	pm_nl_set_limits $ns1 0 4
2019	pm_nl_set_limits $ns2 1 4
2020	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow,fullmesh
2021	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow,fullmesh
2022	run_tests $ns1 $ns2 10.0.1.1 0 1 0 slow
2023	chk_join_nr "fullmesh test 2x1" 4 4 4
2024	chk_add_nr 1 1
2025
2026	# fullmesh 2
2027	# 1 non-fullmesh addr in ns1, added before the connection,
2028	# 1 fullmesh addr in ns2, added during the connection.
2029	reset
2030	pm_nl_set_limits $ns1 1 3
2031	pm_nl_set_limits $ns2 1 3
2032	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
2033	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_1 slow
2034	chk_join_nr "fullmesh test 1x1" 3 3 3
2035	chk_add_nr 1 1
2036
2037	# fullmesh 3
2038	# 1 non-fullmesh addr in ns1, added before the connection,
2039	# 2 fullmesh addrs in ns2, added during the connection.
2040	reset
2041	pm_nl_set_limits $ns1 2 5
2042	pm_nl_set_limits $ns2 1 5
2043	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
2044	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_2 slow
2045	chk_join_nr "fullmesh test 1x2" 5 5 5
2046	chk_add_nr 1 1
2047
2048	# fullmesh 4
2049	# 1 non-fullmesh addr in ns1, added before the connection,
2050	# 2 fullmesh addrs in ns2, added during the connection,
2051	# limit max_subflows to 4.
2052	reset
2053	pm_nl_set_limits $ns1 2 4
2054	pm_nl_set_limits $ns2 1 4
2055	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
2056	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_2 slow
2057	chk_join_nr "fullmesh test 1x2, limited" 4 4 4
2058	chk_add_nr 1 1
2059
2060	# set fullmesh flag
2061	reset
2062	pm_nl_set_limits $ns1 4 4
2063	pm_nl_add_endpoint $ns1 10.0.2.1 flags subflow
2064	pm_nl_set_limits $ns2 4 4
2065	run_tests $ns1 $ns2 10.0.1.1 0 0 1 slow fullmesh
2066	chk_join_nr "set fullmesh flag test" 2 2 2
2067	chk_rm_nr 0 1
2068
2069	# set nofullmesh flag
2070	reset
2071	pm_nl_set_limits $ns1 4 4
2072	pm_nl_add_endpoint $ns1 10.0.2.1 flags subflow,fullmesh
2073	pm_nl_set_limits $ns2 4 4
2074	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_1 slow nofullmesh
2075	chk_join_nr "set nofullmesh flag test" 2 2 2
2076	chk_rm_nr 0 1
2077
2078	# set backup,fullmesh flags
2079	reset
2080	pm_nl_set_limits $ns1 4 4
2081	pm_nl_add_endpoint $ns1 10.0.2.1 flags subflow
2082	pm_nl_set_limits $ns2 4 4
2083	run_tests $ns1 $ns2 10.0.1.1 0 0 1 slow backup,fullmesh
2084	chk_join_nr "set backup,fullmesh flags test" 2 2 2
2085	chk_prio_nr 0 1
2086	chk_rm_nr 0 1
2087
2088	# set nobackup,nofullmesh flags
2089	reset
2090	pm_nl_set_limits $ns1 4 4
2091	pm_nl_set_limits $ns2 4 4
2092	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow,backup,fullmesh
2093	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow nobackup,nofullmesh
2094	chk_join_nr "set nobackup,nofullmesh flags test" 2 2 2
2095	chk_prio_nr 0 1
2096	chk_rm_nr 0 1
2097}
2098
2099all_tests()
2100{
2101	subflows_tests
2102	subflows_error_tests
2103	signal_address_tests
2104	link_failure_tests
2105	add_addr_timeout_tests
2106	remove_tests
2107	add_tests
2108	ipv6_tests
2109	v4mapped_tests
2110	backup_tests
2111	add_addr_ports_tests
2112	syncookies_tests
2113	checksum_tests
2114	deny_join_id0_tests
2115	fullmesh_tests
2116}
2117
2118# [$1: error message]
2119usage()
2120{
2121	if [ -n "${1}" ]; then
2122		echo "${1}"
2123		ret=1
2124	fi
2125
2126	echo "mptcp_join usage:"
2127	echo "  -f subflows_tests"
2128	echo "  -e subflows_error_tests"
2129	echo "  -s signal_address_tests"
2130	echo "  -l link_failure_tests"
2131	echo "  -t add_addr_timeout_tests"
2132	echo "  -r remove_tests"
2133	echo "  -a add_tests"
2134	echo "  -6 ipv6_tests"
2135	echo "  -4 v4mapped_tests"
2136	echo "  -b backup_tests"
2137	echo "  -p add_addr_ports_tests"
2138	echo "  -k syncookies_tests"
2139	echo "  -S checksum_tests"
2140	echo "  -d deny_join_id0_tests"
2141	echo "  -m fullmesh_tests"
2142	echo "  -c capture pcap files"
2143	echo "  -C enable data checksum"
2144	echo "  -i use ip mptcp"
2145	echo "  -h help"
2146
2147	exit ${ret}
2148}
2149
2150for arg in "$@"; do
2151	# check for "capture/checksum" args before launching tests
2152	if [[ "${arg}" =~ ^"-"[0-9a-zA-Z]*"c"[0-9a-zA-Z]*$ ]]; then
2153		capture=1
2154	fi
2155	if [[ "${arg}" =~ ^"-"[0-9a-zA-Z]*"C"[0-9a-zA-Z]*$ ]]; then
2156		checksum=1
2157	fi
2158	if [[ "${arg}" =~ ^"-"[0-9a-zA-Z]*"i"[0-9a-zA-Z]*$ ]]; then
2159		ip_mptcp=1
2160	fi
2161
2162	# exception for the capture/checksum/ip_mptcp options, the rest means: a part of the tests
2163	if [ "${arg}" != "-c" ] && [ "${arg}" != "-C" ] && [ "${arg}" != "-i" ]; then
2164		do_all_tests=0
2165	fi
2166done
2167
2168if [ $do_all_tests -eq 1 ]; then
2169	all_tests
2170	exit $ret
2171fi
2172
2173while getopts 'fesltra64bpkdmchCSi' opt; do
2174	case $opt in
2175		f)
2176			subflows_tests
2177			;;
2178		e)
2179			subflows_error_tests
2180			;;
2181		s)
2182			signal_address_tests
2183			;;
2184		l)
2185			link_failure_tests
2186			;;
2187		t)
2188			add_addr_timeout_tests
2189			;;
2190		r)
2191			remove_tests
2192			;;
2193		a)
2194			add_tests
2195			;;
2196		6)
2197			ipv6_tests
2198			;;
2199		4)
2200			v4mapped_tests
2201			;;
2202		b)
2203			backup_tests
2204			;;
2205		p)
2206			add_addr_ports_tests
2207			;;
2208		k)
2209			syncookies_tests
2210			;;
2211		S)
2212			checksum_tests
2213			;;
2214		d)
2215			deny_join_id0_tests
2216			;;
2217		m)
2218			fullmesh_tests
2219			;;
2220		c)
2221			;;
2222		C)
2223			;;
2224		i)
2225			;;
2226		h)
2227			usage
2228			;;
2229		*)
2230			usage "Unknown option: -${opt}"
2231			;;
2232	esac
2233done
2234
2235exit $ret
2236