1b08fbf24SPaolo Abeni#!/bin/bash
2b08fbf24SPaolo Abeni# SPDX-License-Identifier: GPL-2.0
3b08fbf24SPaolo Abeni
4b08fbf24SPaolo Abeniret=0
5b08fbf24SPaolo Abenisin=""
67d1e6f16SPaolo Abenisinfail=""
7b08fbf24SPaolo Abenisout=""
8b08fbf24SPaolo Abenicin=""
97d1e6f16SPaolo Abenicinfail=""
108b819a84SFlorian Westphalcinsent=""
11b08fbf24SPaolo Abenicout=""
12b08fbf24SPaolo Abeniksft_skip=4
135888a61cSMatthieu Baertstimeout_poll=30
145888a61cSMatthieu Baertstimeout_test=$((timeout_poll * 2 + 1))
15b08fbf24SPaolo Abenicapture=0
16af66d3e1SGeliang Tangchecksum=0
1734aa6e3bSGeliang Tangip_mptcp=0
188117dac3SGeliang Tangcheck_invert=0
1993827ad5SMatthieu Baertsinit=0
20b08fbf24SPaolo Abeni
21b08fbf24SPaolo AbeniTEST_COUNT=0
229a0a9367SGeliang Tangnr_blank=40
23b08fbf24SPaolo Abeni
248d014eaaSGeliang Tang# generated using "nfbpf_compile '(ip && (ip[54] & 0xf0) == 0x30) ||
258d014eaaSGeliang Tang#				  (ip6 && (ip6[74] & 0xf0) == 0x30)'"
268d014eaaSGeliang TangCBPF_MPTCP_SUBOPTION_ADD_ADDR="14,
278d014eaaSGeliang Tang			       48 0 0 0,
288d014eaaSGeliang Tang			       84 0 0 240,
298d014eaaSGeliang Tang			       21 0 3 64,
308d014eaaSGeliang Tang			       48 0 0 54,
318d014eaaSGeliang Tang			       84 0 0 240,
328d014eaaSGeliang Tang			       21 6 7 48,
338d014eaaSGeliang Tang			       48 0 0 0,
348d014eaaSGeliang Tang			       84 0 0 240,
358d014eaaSGeliang Tang			       21 0 4 96,
368d014eaaSGeliang Tang			       48 0 0 74,
378d014eaaSGeliang Tang			       84 0 0 240,
388d014eaaSGeliang Tang			       21 0 1 48,
398d014eaaSGeliang Tang			       6 0 0 65535,
408d014eaaSGeliang Tang			       6 0 0 0"
418d014eaaSGeliang Tang
4293827ad5SMatthieu Baertsinit_partial()
43b08fbf24SPaolo Abeni{
44b08fbf24SPaolo Abeni	capout=$(mktemp)
45b08fbf24SPaolo Abeni
460a40e273SMatthieu Baerts	rndh=$(mktemp -u XXXXXX)
47b08fbf24SPaolo Abeni
48b08fbf24SPaolo Abeni	ns1="ns1-$rndh"
49b08fbf24SPaolo Abeni	ns2="ns2-$rndh"
50b08fbf24SPaolo Abeni
51b08fbf24SPaolo Abeni	for netns in "$ns1" "$ns2";do
52b08fbf24SPaolo Abeni		ip netns add $netns || exit $ksft_skip
53b08fbf24SPaolo Abeni		ip -net $netns link set lo up
54b08fbf24SPaolo Abeni		ip netns exec $netns sysctl -q net.mptcp.enabled=1
55b08fbf24SPaolo Abeni		ip netns exec $netns sysctl -q net.ipv4.conf.all.rp_filter=0
56b08fbf24SPaolo Abeni		ip netns exec $netns sysctl -q net.ipv4.conf.default.rp_filter=0
57af66d3e1SGeliang Tang		if [ $checksum -eq 1 ]; then
58af66d3e1SGeliang Tang			ip netns exec $netns sysctl -q net.mptcp.checksum_enabled=1
59af66d3e1SGeliang Tang		fi
60b08fbf24SPaolo Abeni	done
61b08fbf24SPaolo Abeni
628117dac3SGeliang Tang	check_invert=0
638117dac3SGeliang Tang
64b08fbf24SPaolo Abeni	#  ns1              ns2
65b08fbf24SPaolo Abeni	# ns1eth1    ns2eth1
66b08fbf24SPaolo Abeni	# ns1eth2    ns2eth2
67b08fbf24SPaolo Abeni	# ns1eth3    ns2eth3
68b08fbf24SPaolo Abeni	# ns1eth4    ns2eth4
69b08fbf24SPaolo Abeni
70b08fbf24SPaolo Abeni	for i in `seq 1 4`; do
71b08fbf24SPaolo Abeni		ip link add ns1eth$i netns "$ns1" type veth peer name ns2eth$i netns "$ns2"
72b08fbf24SPaolo Abeni		ip -net "$ns1" addr add 10.0.$i.1/24 dev ns1eth$i
73b08fbf24SPaolo Abeni		ip -net "$ns1" addr add dead:beef:$i::1/64 dev ns1eth$i nodad
74b08fbf24SPaolo Abeni		ip -net "$ns1" link set ns1eth$i up
75b08fbf24SPaolo Abeni
76b08fbf24SPaolo Abeni		ip -net "$ns2" addr add 10.0.$i.2/24 dev ns2eth$i
77b08fbf24SPaolo Abeni		ip -net "$ns2" addr add dead:beef:$i::2/64 dev ns2eth$i nodad
78b08fbf24SPaolo Abeni		ip -net "$ns2" link set ns2eth$i up
79b08fbf24SPaolo Abeni
80b08fbf24SPaolo Abeni		# let $ns2 reach any $ns1 address from any interface
81b08fbf24SPaolo Abeni		ip -net "$ns2" route add default via 10.0.$i.1 dev ns2eth$i metric 10$i
829846921dSPaolo Abeni		ip -net "$ns2" route add default via dead:beef:$i::1 dev ns2eth$i metric 10$i
83b08fbf24SPaolo Abeni	done
84b08fbf24SPaolo Abeni}
85b08fbf24SPaolo Abeni
867d1e6f16SPaolo Abeniinit_shapers()
877d1e6f16SPaolo Abeni{
887d1e6f16SPaolo Abeni	for i in `seq 1 4`; do
897d1e6f16SPaolo Abeni		tc -n $ns1 qdisc add dev ns1eth$i root netem rate 20mbit delay 1
907d1e6f16SPaolo Abeni		tc -n $ns2 qdisc add dev ns2eth$i root netem rate 20mbit delay 1
917d1e6f16SPaolo Abeni	done
927d1e6f16SPaolo Abeni}
937d1e6f16SPaolo Abeni
94b08fbf24SPaolo Abenicleanup_partial()
95b08fbf24SPaolo Abeni{
96b08fbf24SPaolo Abeni	rm -f "$capout"
97b08fbf24SPaolo Abeni
98b08fbf24SPaolo Abeni	for netns in "$ns1" "$ns2"; do
99b08fbf24SPaolo Abeni		ip netns del $netns
100c2a55e8fSMatthieu Baerts		rm -f /tmp/$netns.{nstat,out}
101b08fbf24SPaolo Abeni	done
102b08fbf24SPaolo Abeni}
103b08fbf24SPaolo Abeni
10487154755SMatthieu Baertscheck_tools()
10587154755SMatthieu Baerts{
10687154755SMatthieu Baerts	if ! ip -Version &> /dev/null; then
10787154755SMatthieu Baerts		echo "SKIP: Could not run test without ip tool"
10887154755SMatthieu Baerts		exit $ksft_skip
10987154755SMatthieu Baerts	fi
11087154755SMatthieu Baerts
11187154755SMatthieu Baerts	if ! iptables -V &> /dev/null; then
11287154755SMatthieu Baerts		echo "SKIP: Could not run all tests without iptables tool"
11387154755SMatthieu Baerts		exit $ksft_skip
11487154755SMatthieu Baerts	fi
11587154755SMatthieu Baerts
11687154755SMatthieu Baerts	if ! ip6tables -V &> /dev/null; then
11787154755SMatthieu Baerts		echo "SKIP: Could not run all tests without ip6tables tool"
11887154755SMatthieu Baerts		exit $ksft_skip
11987154755SMatthieu Baerts	fi
12087154755SMatthieu Baerts}
12187154755SMatthieu Baerts
12293827ad5SMatthieu Baertsinit() {
12393827ad5SMatthieu Baerts	init=1
12493827ad5SMatthieu Baerts
12587154755SMatthieu Baerts	check_tools
12687154755SMatthieu Baerts
12793827ad5SMatthieu Baerts	sin=$(mktemp)
12893827ad5SMatthieu Baerts	sout=$(mktemp)
12993827ad5SMatthieu Baerts	cin=$(mktemp)
13093827ad5SMatthieu Baerts	cinsent=$(mktemp)
13193827ad5SMatthieu Baerts	cout=$(mktemp)
13293827ad5SMatthieu Baerts
13393827ad5SMatthieu Baerts	trap cleanup EXIT
13493827ad5SMatthieu Baerts
13593827ad5SMatthieu Baerts	make_file "$cin" "client" 1
13693827ad5SMatthieu Baerts	make_file "$sin" "server" 1
13793827ad5SMatthieu Baerts}
13893827ad5SMatthieu Baerts
139b08fbf24SPaolo Abenicleanup()
140b08fbf24SPaolo Abeni{
1417d1e6f16SPaolo Abeni	rm -f "$cin" "$cout" "$sinfail"
1427d1e6f16SPaolo Abeni	rm -f "$sin" "$sout" "$cinsent" "$cinfail"
143b08fbf24SPaolo Abeni	cleanup_partial
144b08fbf24SPaolo Abeni}
145b08fbf24SPaolo Abeni
146b08fbf24SPaolo Abenireset()
147b08fbf24SPaolo Abeni{
14893827ad5SMatthieu Baerts	if [ "${init}" != "1" ]; then
149b08fbf24SPaolo Abeni		init
15093827ad5SMatthieu Baerts	else
15193827ad5SMatthieu Baerts		cleanup_partial
15293827ad5SMatthieu Baerts	fi
15393827ad5SMatthieu Baerts
15493827ad5SMatthieu Baerts	init_partial
155b08fbf24SPaolo Abeni}
156b08fbf24SPaolo Abeni
15700587187SFlorian Westphalreset_with_cookies()
15800587187SFlorian Westphal{
15900587187SFlorian Westphal	reset
16000587187SFlorian Westphal
16100587187SFlorian Westphal	for netns in "$ns1" "$ns2";do
16200587187SFlorian Westphal		ip netns exec $netns sysctl -q net.ipv4.tcp_syncookies=2
16300587187SFlorian Westphal	done
16400587187SFlorian Westphal}
16500587187SFlorian Westphal
1668d014eaaSGeliang Tangreset_with_add_addr_timeout()
1678d014eaaSGeliang Tang{
1688d014eaaSGeliang Tang	local ip="${1:-4}"
1698d014eaaSGeliang Tang	local tables
1708d014eaaSGeliang Tang
1718d014eaaSGeliang Tang	tables="iptables"
1728d014eaaSGeliang Tang	if [ $ip -eq 6 ]; then
1738d014eaaSGeliang Tang		tables="ip6tables"
1748d014eaaSGeliang Tang	fi
1758d014eaaSGeliang Tang
1768d014eaaSGeliang Tang	reset
1778d014eaaSGeliang Tang
1788d014eaaSGeliang Tang	ip netns exec $ns1 sysctl -q net.mptcp.add_addr_timeout=1
1798d014eaaSGeliang Tang	ip netns exec $ns2 $tables -A OUTPUT -p tcp \
1808d014eaaSGeliang Tang		-m tcp --tcp-option 30 \
1818d014eaaSGeliang Tang		-m bpf --bytecode \
1828d014eaaSGeliang Tang		"$CBPF_MPTCP_SUBOPTION_ADD_ADDR" \
1838d014eaaSGeliang Tang		-j DROP
1848d014eaaSGeliang Tang}
1858d014eaaSGeliang Tang
186af66d3e1SGeliang Tangreset_with_checksum()
187af66d3e1SGeliang Tang{
188af66d3e1SGeliang Tang	local ns1_enable=$1
189af66d3e1SGeliang Tang	local ns2_enable=$2
190af66d3e1SGeliang Tang
191af66d3e1SGeliang Tang	reset
192af66d3e1SGeliang Tang
193af66d3e1SGeliang Tang	ip netns exec $ns1 sysctl -q net.mptcp.checksum_enabled=$ns1_enable
194af66d3e1SGeliang Tang	ip netns exec $ns2 sysctl -q net.mptcp.checksum_enabled=$ns2_enable
195af66d3e1SGeliang Tang}
196af66d3e1SGeliang Tang
1970cddb4a6SGeliang Tangreset_with_allow_join_id0()
1980cddb4a6SGeliang Tang{
1990cddb4a6SGeliang Tang	local ns1_enable=$1
2000cddb4a6SGeliang Tang	local ns2_enable=$2
2010cddb4a6SGeliang Tang
2020cddb4a6SGeliang Tang	reset
2030cddb4a6SGeliang Tang
2040cddb4a6SGeliang Tang	ip netns exec $ns1 sysctl -q net.mptcp.allow_join_initial_addr_port=$ns1_enable
2050cddb4a6SGeliang Tang	ip netns exec $ns2 sysctl -q net.mptcp.allow_join_initial_addr_port=$ns2_enable
2060cddb4a6SGeliang Tang}
2070cddb4a6SGeliang Tang
2088b819a84SFlorian Westphalprint_file_err()
2098b819a84SFlorian Westphal{
2108b819a84SFlorian Westphal	ls -l "$1" 1>&2
2118b819a84SFlorian Westphal	echo "Trailing bytes are: "
2128b819a84SFlorian Westphal	tail -c 27 "$1"
2138b819a84SFlorian Westphal}
2148b819a84SFlorian Westphal
215b08fbf24SPaolo Abenicheck_transfer()
216b08fbf24SPaolo Abeni{
217b08fbf24SPaolo Abeni	in=$1
218b08fbf24SPaolo Abeni	out=$2
219b08fbf24SPaolo Abeni	what=$3
220b08fbf24SPaolo Abeni
2218117dac3SGeliang Tang	cmp -l "$in" "$out" | while read line; do
2228117dac3SGeliang Tang		local arr=($line)
2238117dac3SGeliang Tang
2248117dac3SGeliang Tang		let sum=0${arr[1]}+0${arr[2]}
2258117dac3SGeliang Tang		if [ $check_invert -eq 0 ] || [ $sum -ne $((0xff)) ]; then
226b08fbf24SPaolo Abeni			echo "[ FAIL ] $what does not match (in, out):"
227b08fbf24SPaolo Abeni			print_file_err "$in"
228b08fbf24SPaolo Abeni			print_file_err "$out"
2298b819a84SFlorian Westphal			ret=1
230b08fbf24SPaolo Abeni
231b08fbf24SPaolo Abeni			return 1
2328117dac3SGeliang Tang		else
2338117dac3SGeliang Tang			echo "$what has inverted byte at ${arr[0]}"
234b08fbf24SPaolo Abeni		fi
2358117dac3SGeliang Tang	done
236b08fbf24SPaolo Abeni
237b08fbf24SPaolo Abeni	return 0
238b08fbf24SPaolo Abeni}
239b08fbf24SPaolo Abeni
240b08fbf24SPaolo Abenido_ping()
241b08fbf24SPaolo Abeni{
242b08fbf24SPaolo Abeni	listener_ns="$1"
243b08fbf24SPaolo Abeni	connector_ns="$2"
244b08fbf24SPaolo Abeni	connect_addr="$3"
245b08fbf24SPaolo Abeni
246b08fbf24SPaolo Abeni	ip netns exec ${connector_ns} ping -q -c 1 $connect_addr >/dev/null
247b08fbf24SPaolo Abeni	if [ $? -ne 0 ] ; then
248b08fbf24SPaolo Abeni		echo "$listener_ns -> $connect_addr connectivity [ FAIL ]" 1>&2
249b08fbf24SPaolo Abeni		ret=1
250b08fbf24SPaolo Abeni	fi
251b08fbf24SPaolo Abeni}
252b08fbf24SPaolo Abeni
2538b819a84SFlorian Westphallink_failure()
2548b819a84SFlorian Westphal{
2558b819a84SFlorian Westphal	ns="$1"
2568b819a84SFlorian Westphal
2577d1e6f16SPaolo Abeni	if [ -z "$FAILING_LINKS" ]; then
2588b819a84SFlorian Westphal		l=$((RANDOM%4))
2597d1e6f16SPaolo Abeni		FAILING_LINKS=$((l+1))
2607d1e6f16SPaolo Abeni	fi
2618b819a84SFlorian Westphal
2627d1e6f16SPaolo Abeni	for l in $FAILING_LINKS; do
2638b819a84SFlorian Westphal		veth="ns1eth$l"
2648b819a84SFlorian Westphal		ip -net "$ns" link set "$veth" down
2657d1e6f16SPaolo Abeni	done
2668b819a84SFlorian Westphal}
2678b819a84SFlorian Westphal
268523514edSGeliang Tang# $1: IP address
269523514edSGeliang Tangis_v6()
270523514edSGeliang Tang{
271523514edSGeliang Tang	[ -z "${1##*:*}" ]
272523514edSGeliang Tang}
273523514edSGeliang Tang
274327b9a94SPaolo Abeni# $1: ns, $2: port
275327b9a94SPaolo Abeniwait_local_port_listen()
276327b9a94SPaolo Abeni{
277327b9a94SPaolo Abeni	local listener_ns="${1}"
278327b9a94SPaolo Abeni	local port="${2}"
279327b9a94SPaolo Abeni
280327b9a94SPaolo Abeni	local port_hex i
281327b9a94SPaolo Abeni
282327b9a94SPaolo Abeni	port_hex="$(printf "%04X" "${port}")"
283327b9a94SPaolo Abeni	for i in $(seq 10); do
284327b9a94SPaolo Abeni		ip netns exec "${listener_ns}" cat /proc/net/tcp* | \
285327b9a94SPaolo Abeni			awk "BEGIN {rc=1} {if (\$2 ~ /:${port_hex}\$/ && \$4 ~ /0A/) {rc=0; exit}} END {exit rc}" &&
286327b9a94SPaolo Abeni			break
287327b9a94SPaolo Abeni		sleep 0.1
288327b9a94SPaolo Abeni	done
289327b9a94SPaolo Abeni}
290327b9a94SPaolo Abeni
291327b9a94SPaolo Abenirm_addr_count()
292327b9a94SPaolo Abeni{
293327b9a94SPaolo Abeni	ns=${1}
294327b9a94SPaolo Abeni
295327b9a94SPaolo Abeni	ip netns exec ${ns} nstat -as | grep MPTcpExtRmAddr | awk '{print $2}'
296327b9a94SPaolo Abeni}
297327b9a94SPaolo Abeni
298327b9a94SPaolo Abeni# $1: ns, $2: old rm_addr counter in $ns
299327b9a94SPaolo Abeniwait_rm_addr()
300327b9a94SPaolo Abeni{
301327b9a94SPaolo Abeni	local ns="${1}"
302327b9a94SPaolo Abeni	local old_cnt="${2}"
303327b9a94SPaolo Abeni	local cnt
304327b9a94SPaolo Abeni	local i
305327b9a94SPaolo Abeni
306327b9a94SPaolo Abeni	for i in $(seq 10); do
307327b9a94SPaolo Abeni		cnt=$(rm_addr_count ${ns})
308327b9a94SPaolo Abeni		[ "$cnt" = "${old_cnt}" ] || break
309327b9a94SPaolo Abeni		sleep 0.1
310327b9a94SPaolo Abeni	done
311327b9a94SPaolo Abeni}
312327b9a94SPaolo Abeni
31334aa6e3bSGeliang Tangpm_nl_set_limits()
31434aa6e3bSGeliang Tang{
31534aa6e3bSGeliang Tang	local ns=$1
31634aa6e3bSGeliang Tang	local addrs=$2
31734aa6e3bSGeliang Tang	local subflows=$3
31834aa6e3bSGeliang Tang
31934aa6e3bSGeliang Tang	if [ $ip_mptcp -eq 1 ]; then
32034aa6e3bSGeliang Tang		ip -n $ns mptcp limits set add_addr_accepted $addrs subflows $subflows
32134aa6e3bSGeliang Tang	else
32234aa6e3bSGeliang Tang		ip netns exec $ns ./pm_nl_ctl limits $addrs $subflows
32334aa6e3bSGeliang Tang	fi
32434aa6e3bSGeliang Tang}
32534aa6e3bSGeliang Tang
32634aa6e3bSGeliang Tangpm_nl_add_endpoint()
32734aa6e3bSGeliang Tang{
32834aa6e3bSGeliang Tang	local ns=$1
32934aa6e3bSGeliang Tang	local addr=$2
33034aa6e3bSGeliang Tang	local flags
33134aa6e3bSGeliang Tang	local port
33234aa6e3bSGeliang Tang	local dev
33334aa6e3bSGeliang Tang	local id
33434aa6e3bSGeliang Tang	local nr=2
33534aa6e3bSGeliang Tang
33634aa6e3bSGeliang Tang	for p in $@
33734aa6e3bSGeliang Tang	do
33834aa6e3bSGeliang Tang		if [ $p = "flags" ]; then
33934aa6e3bSGeliang Tang			eval _flags=\$"$nr"
34034aa6e3bSGeliang Tang			[ ! -z $_flags ]; flags="flags $_flags"
34134aa6e3bSGeliang Tang		fi
34234aa6e3bSGeliang Tang		if [ $p = "dev" ]; then
34334aa6e3bSGeliang Tang			eval _dev=\$"$nr"
34434aa6e3bSGeliang Tang			[ ! -z $_dev ]; dev="dev $_dev"
34534aa6e3bSGeliang Tang		fi
34634aa6e3bSGeliang Tang		if [ $p = "id" ]; then
34734aa6e3bSGeliang Tang			eval _id=\$"$nr"
34834aa6e3bSGeliang Tang			[ ! -z $_id ]; id="id $_id"
34934aa6e3bSGeliang Tang		fi
35034aa6e3bSGeliang Tang		if [ $p = "port" ]; then
35134aa6e3bSGeliang Tang			eval _port=\$"$nr"
35234aa6e3bSGeliang Tang			[ ! -z $_port ]; port="port $_port"
35334aa6e3bSGeliang Tang		fi
35434aa6e3bSGeliang Tang
35534aa6e3bSGeliang Tang		let nr+=1
35634aa6e3bSGeliang Tang	done
35734aa6e3bSGeliang Tang
35834aa6e3bSGeliang Tang	if [ $ip_mptcp -eq 1 ]; then
35934aa6e3bSGeliang Tang		ip -n $ns mptcp endpoint add $addr ${_flags//","/" "} $dev $id $port
36034aa6e3bSGeliang Tang	else
36134aa6e3bSGeliang Tang		ip netns exec $ns ./pm_nl_ctl add $addr $flags $dev $id $port
36234aa6e3bSGeliang Tang	fi
36334aa6e3bSGeliang Tang}
36434aa6e3bSGeliang Tang
36534aa6e3bSGeliang Tangpm_nl_del_endpoint()
36634aa6e3bSGeliang Tang{
36734aa6e3bSGeliang Tang	local ns=$1
36834aa6e3bSGeliang Tang	local id=$2
36934aa6e3bSGeliang Tang	local addr=$3
37034aa6e3bSGeliang Tang
37134aa6e3bSGeliang Tang	if [ $ip_mptcp -eq 1 ]; then
37234aa6e3bSGeliang Tang		ip -n $ns mptcp endpoint delete id $id $addr
37334aa6e3bSGeliang Tang	else
37434aa6e3bSGeliang Tang		ip netns exec $ns ./pm_nl_ctl del $id $addr
37534aa6e3bSGeliang Tang	fi
37634aa6e3bSGeliang Tang}
37734aa6e3bSGeliang Tang
37834aa6e3bSGeliang Tangpm_nl_flush_endpoint()
37934aa6e3bSGeliang Tang{
38034aa6e3bSGeliang Tang	local ns=$1
38134aa6e3bSGeliang Tang
38234aa6e3bSGeliang Tang	if [ $ip_mptcp -eq 1 ]; then
38334aa6e3bSGeliang Tang		ip -n $ns mptcp endpoint flush
38434aa6e3bSGeliang Tang	else
38534aa6e3bSGeliang Tang		ip netns exec $ns ./pm_nl_ctl flush
38634aa6e3bSGeliang Tang	fi
38734aa6e3bSGeliang Tang}
38834aa6e3bSGeliang Tang
389dda61b3dSGeliang Tangpm_nl_show_endpoints()
390dda61b3dSGeliang Tang{
391dda61b3dSGeliang Tang	local ns=$1
392dda61b3dSGeliang Tang
393dda61b3dSGeliang Tang	if [ $ip_mptcp -eq 1 ]; then
394dda61b3dSGeliang Tang		ip -n $ns mptcp endpoint show
395dda61b3dSGeliang Tang	else
396dda61b3dSGeliang Tang		ip netns exec $ns ./pm_nl_ctl dump
397dda61b3dSGeliang Tang	fi
398dda61b3dSGeliang Tang}
399dda61b3dSGeliang Tang
400f0140386SGeliang Tangpm_nl_change_endpoint()
401f0140386SGeliang Tang{
402f0140386SGeliang Tang	local ns=$1
403bccefb76SGeliang Tang	local id=$2
404bccefb76SGeliang Tang	local flags=$3
405f0140386SGeliang Tang
406f0140386SGeliang Tang	if [ $ip_mptcp -eq 1 ]; then
407f0140386SGeliang Tang		ip -n $ns mptcp endpoint change id $id ${flags//","/" "}
408f0140386SGeliang Tang	else
409bccefb76SGeliang Tang		ip netns exec $ns ./pm_nl_ctl set id $id flags $flags
410f0140386SGeliang Tang	fi
411f0140386SGeliang Tang}
412f0140386SGeliang Tang
413b08fbf24SPaolo Abenido_transfer()
414b08fbf24SPaolo Abeni{
415b08fbf24SPaolo Abeni	listener_ns="$1"
416b08fbf24SPaolo Abeni	connector_ns="$2"
417b08fbf24SPaolo Abeni	cl_proto="$3"
418b08fbf24SPaolo Abeni	srv_proto="$4"
419b08fbf24SPaolo Abeni	connect_addr="$5"
4208b819a84SFlorian Westphal	test_link_fail="$6"
4212e8cbf45SGeliang Tang	addr_nr_ns1="$7"
4222e8cbf45SGeliang Tang	addr_nr_ns2="$8"
4238b819a84SFlorian Westphal	speed="$9"
4246a0653b9SGeliang Tang	sflags="${10}"
425b08fbf24SPaolo Abeni
426b08fbf24SPaolo Abeni	port=$((10000+$TEST_COUNT))
427b08fbf24SPaolo Abeni	TEST_COUNT=$((TEST_COUNT+1))
428b08fbf24SPaolo Abeni
429b08fbf24SPaolo Abeni	:> "$cout"
430b08fbf24SPaolo Abeni	:> "$sout"
431b08fbf24SPaolo Abeni	:> "$capout"
432b08fbf24SPaolo Abeni
433b08fbf24SPaolo Abeni	if [ $capture -eq 1 ]; then
434b08fbf24SPaolo Abeni		if [ -z $SUDO_USER ] ; then
435b08fbf24SPaolo Abeni			capuser=""
436b08fbf24SPaolo Abeni		else
437b08fbf24SPaolo Abeni			capuser="-Z $SUDO_USER"
438b08fbf24SPaolo Abeni		fi
439b08fbf24SPaolo Abeni
44000587187SFlorian Westphal		capfile=$(printf "mp_join-%02u-%s.pcap" "$TEST_COUNT" "${listener_ns}")
441b08fbf24SPaolo Abeni
442b08fbf24SPaolo Abeni		echo "Capturing traffic for test $TEST_COUNT into $capfile"
443b08fbf24SPaolo Abeni		ip netns exec ${listener_ns} tcpdump -i any -s 65535 -B 32768 $capuser -w $capfile > "$capout" 2>&1 &
444b08fbf24SPaolo Abeni		cappid=$!
445b08fbf24SPaolo Abeni
446b08fbf24SPaolo Abeni		sleep 1
447b08fbf24SPaolo Abeni	fi
448b08fbf24SPaolo Abeni
449c2a55e8fSMatthieu Baerts	NSTAT_HISTORY=/tmp/${listener_ns}.nstat ip netns exec ${listener_ns} \
450c2a55e8fSMatthieu Baerts		nstat -n
451c2a55e8fSMatthieu Baerts	NSTAT_HISTORY=/tmp/${connector_ns}.nstat ip netns exec ${connector_ns} \
452c2a55e8fSMatthieu Baerts		nstat -n
453c2a55e8fSMatthieu Baerts
454cbfafac4SGeliang Tang	local extra_args
4558d014eaaSGeliang Tang	if [ $speed = "fast" ]; then
456cbfafac4SGeliang Tang		extra_args="-j"
4578da6229bSGeliang Tang	elif [ $speed = "slow" ]; then
458cbfafac4SGeliang Tang		extra_args="-r 50"
459cbfafac4SGeliang Tang	elif [[ $speed = "speed_"* ]]; then
460cbfafac4SGeliang Tang		extra_args="-r ${speed:6}"
461dd72b0feSGeliang Tang	fi
462dd72b0feSGeliang Tang
46301542c9bSGeliang Tang	if [[ "${addr_nr_ns2}" = "fastclose_"* ]]; then
46401542c9bSGeliang Tang		# disconnect
46501542c9bSGeliang Tang		extra_args="$extra_args -I ${addr_nr_ns2:10}"
46601542c9bSGeliang Tang		addr_nr_ns2=0
46701542c9bSGeliang Tang	fi
46801542c9bSGeliang Tang
469523514edSGeliang Tang	local local_addr
470523514edSGeliang Tang	if is_v6 "${connect_addr}"; then
471523514edSGeliang Tang		local_addr="::"
472523514edSGeliang Tang	else
473523514edSGeliang Tang		local_addr="0.0.0.0"
474523514edSGeliang Tang	fi
475523514edSGeliang Tang
47634b572b7SGeliang Tang	if [ "$test_link_fail" -gt 1 ];then
4777d1e6f16SPaolo Abeni		timeout ${timeout_test} \
4787d1e6f16SPaolo Abeni			ip netns exec ${listener_ns} \
479cbfafac4SGeliang Tang				./mptcp_connect -t ${timeout_poll} -l -p $port -s ${srv_proto} \
480cbfafac4SGeliang Tang					$extra_args ${local_addr} < "$sinfail" > "$sout" &
4817d1e6f16SPaolo Abeni	else
4825888a61cSMatthieu Baerts		timeout ${timeout_test} \
4835888a61cSMatthieu Baerts			ip netns exec ${listener_ns} \
484cbfafac4SGeliang Tang				./mptcp_connect -t ${timeout_poll} -l -p $port -s ${srv_proto} \
485cbfafac4SGeliang Tang					$extra_args ${local_addr} < "$sin" > "$sout" &
4867d1e6f16SPaolo Abeni	fi
487b08fbf24SPaolo Abeni	spid=$!
488b08fbf24SPaolo Abeni
489327b9a94SPaolo Abeni	wait_local_port_listen "${listener_ns}" "${port}"
490b08fbf24SPaolo Abeni
4918b819a84SFlorian Westphal	if [ "$test_link_fail" -eq 0 ];then
4925888a61cSMatthieu Baerts		timeout ${timeout_test} \
4935888a61cSMatthieu Baerts			ip netns exec ${connector_ns} \
494cbfafac4SGeliang Tang				./mptcp_connect -t ${timeout_poll} -p $port -s ${cl_proto} \
495cbfafac4SGeliang Tang					$extra_args $connect_addr < "$cin" > "$cout" &
49634b572b7SGeliang Tang	elif [ "$test_link_fail" -eq 1 ] || [ "$test_link_fail" -eq 2 ];then
4977d1e6f16SPaolo Abeni		( cat "$cinfail" ; sleep 2; link_failure $listener_ns ; cat "$cinfail" ) | \
4985888a61cSMatthieu Baerts			tee "$cinsent" | \
4995888a61cSMatthieu Baerts			timeout ${timeout_test} \
5005888a61cSMatthieu Baerts				ip netns exec ${connector_ns} \
501cbfafac4SGeliang Tang					./mptcp_connect -t ${timeout_poll} -p $port -s ${cl_proto} \
502cbfafac4SGeliang Tang						$extra_args $connect_addr > "$cout" &
50334b572b7SGeliang Tang	else
50434b572b7SGeliang Tang		cat "$cinfail" | tee "$cinsent" | \
50534b572b7SGeliang Tang			timeout ${timeout_test} \
50634b572b7SGeliang Tang				ip netns exec ${connector_ns} \
50734b572b7SGeliang Tang					./mptcp_connect -t ${timeout_poll} -p $port -s ${cl_proto} \
50834b572b7SGeliang Tang						$extra_args $connect_addr > "$cout" &
5098b819a84SFlorian Westphal	fi
510b08fbf24SPaolo Abeni	cpid=$!
511b08fbf24SPaolo Abeni
512327b9a94SPaolo Abeni	# let the mptcp subflow be established in background before
513327b9a94SPaolo Abeni	# do endpoint manipulation
514327b9a94SPaolo Abeni	[ $addr_nr_ns1 = "0" -a $addr_nr_ns2 = "0" ] || sleep 1
515327b9a94SPaolo Abeni
5166208fd82SGeliang Tang	if [ $addr_nr_ns1 -gt 0 ]; then
5176208fd82SGeliang Tang		let add_nr_ns1=addr_nr_ns1
5186208fd82SGeliang Tang		counter=2
5196208fd82SGeliang Tang		while [ $add_nr_ns1 -gt 0 ]; do
5206208fd82SGeliang Tang			local addr
5216208fd82SGeliang Tang			if is_v6 "${connect_addr}"; then
5226208fd82SGeliang Tang				addr="dead:beef:$counter::1"
5236208fd82SGeliang Tang			else
5246208fd82SGeliang Tang				addr="10.0.$counter.1"
5256208fd82SGeliang Tang			fi
52634aa6e3bSGeliang Tang			pm_nl_add_endpoint $ns1 $addr flags signal
5276208fd82SGeliang Tang			let counter+=1
5286208fd82SGeliang Tang			let add_nr_ns1-=1
5296208fd82SGeliang Tang		done
5306208fd82SGeliang Tang	elif [ $addr_nr_ns1 -lt 0 ]; then
5312e8cbf45SGeliang Tang		let rm_nr_ns1=-addr_nr_ns1
5326fe4ccdcSGeliang Tang		if [ $rm_nr_ns1 -lt 8 ]; then
533dda61b3dSGeliang Tang			counter=0
534dda61b3dSGeliang Tang			pm_nl_show_endpoints ${listener_ns} | while read line; do
535dda61b3dSGeliang Tang				local arr=($line)
536dda61b3dSGeliang Tang				local nr=0
537dda61b3dSGeliang Tang
538dda61b3dSGeliang Tang				for i in ${arr[@]}; do
539dda61b3dSGeliang Tang					if [ $i = "id" ]; then
540dda61b3dSGeliang Tang						if [ $counter -eq $rm_nr_ns1 ]; then
541dda61b3dSGeliang Tang							break
542dda61b3dSGeliang Tang						fi
543dda61b3dSGeliang Tang						id=${arr[$nr+1]}
544327b9a94SPaolo Abeni						rm_addr=$(rm_addr_count ${connector_ns})
54534aa6e3bSGeliang Tang						pm_nl_del_endpoint ${listener_ns} $id
546327b9a94SPaolo Abeni						wait_rm_addr ${connector_ns} ${rm_addr}
547dd72b0feSGeliang Tang						let counter+=1
548f87744adSGeliang Tang					fi
549dda61b3dSGeliang Tang					let nr+=1
550dda61b3dSGeliang Tang				done
551dda61b3dSGeliang Tang			done
5525e287fe7SGeliang Tang		elif [ $rm_nr_ns1 -eq 8 ]; then
55334aa6e3bSGeliang Tang			pm_nl_flush_endpoint ${listener_ns}
5545e287fe7SGeliang Tang		elif [ $rm_nr_ns1 -eq 9 ]; then
55534aa6e3bSGeliang Tang			pm_nl_del_endpoint ${listener_ns} 0 ${connect_addr}
5566fe4ccdcSGeliang Tang		fi
557dd72b0feSGeliang Tang	fi
558dd72b0feSGeliang Tang
5594f49d633SGeliang Tang	flags="subflow"
5604f49d633SGeliang Tang	if [[ "${addr_nr_ns2}" = "fullmesh_"* ]]; then
5614f49d633SGeliang Tang		flags="${flags},fullmesh"
5624f49d633SGeliang Tang		addr_nr_ns2=${addr_nr_ns2:9}
5634f49d633SGeliang Tang	fi
5644f49d633SGeliang Tang
565327b9a94SPaolo Abeni	# if newly added endpoints must be deleted, give the background msk
566327b9a94SPaolo Abeni	# some time to created them
567327b9a94SPaolo Abeni	[ $addr_nr_ns1 -gt 0 -a $addr_nr_ns2 -lt 0 ] && sleep 1
568327b9a94SPaolo Abeni
5696208fd82SGeliang Tang	if [ $addr_nr_ns2 -gt 0 ]; then
5706208fd82SGeliang Tang		let add_nr_ns2=addr_nr_ns2
5716208fd82SGeliang Tang		counter=3
5726208fd82SGeliang Tang		while [ $add_nr_ns2 -gt 0 ]; do
5736208fd82SGeliang Tang			local addr
5746208fd82SGeliang Tang			if is_v6 "${connect_addr}"; then
5756208fd82SGeliang Tang				addr="dead:beef:$counter::2"
5766208fd82SGeliang Tang			else
5776208fd82SGeliang Tang				addr="10.0.$counter.2"
5786208fd82SGeliang Tang			fi
57934aa6e3bSGeliang Tang			pm_nl_add_endpoint $ns2 $addr flags $flags
5806208fd82SGeliang Tang			let counter+=1
5816208fd82SGeliang Tang			let add_nr_ns2-=1
5826208fd82SGeliang Tang		done
5836208fd82SGeliang Tang	elif [ $addr_nr_ns2 -lt 0 ]; then
5842e8cbf45SGeliang Tang		let rm_nr_ns2=-addr_nr_ns2
5856fe4ccdcSGeliang Tang		if [ $rm_nr_ns2 -lt 8 ]; then
586dda61b3dSGeliang Tang			counter=0
587dda61b3dSGeliang Tang			pm_nl_show_endpoints ${connector_ns} | while read line; do
588dda61b3dSGeliang Tang				local arr=($line)
589dda61b3dSGeliang Tang				local nr=0
590dda61b3dSGeliang Tang
591dda61b3dSGeliang Tang				for i in ${arr[@]}; do
592dda61b3dSGeliang Tang					if [ $i = "id" ]; then
593dda61b3dSGeliang Tang						if [ $counter -eq $rm_nr_ns2 ]; then
594dda61b3dSGeliang Tang							break
595dda61b3dSGeliang Tang						fi
596dda61b3dSGeliang Tang						# rm_addr are serialized, allow the previous one to
597dda61b3dSGeliang Tang						# complete
598dda61b3dSGeliang Tang						id=${arr[$nr+1]}
599327b9a94SPaolo Abeni						rm_addr=$(rm_addr_count ${listener_ns})
60034aa6e3bSGeliang Tang						pm_nl_del_endpoint ${connector_ns} $id
601327b9a94SPaolo Abeni						wait_rm_addr ${listener_ns} ${rm_addr}
602dd72b0feSGeliang Tang						let counter+=1
603f87744adSGeliang Tang					fi
604dda61b3dSGeliang Tang					let nr+=1
605dda61b3dSGeliang Tang				done
606dda61b3dSGeliang Tang			done
6075e287fe7SGeliang Tang		elif [ $rm_nr_ns2 -eq 8 ]; then
60834aa6e3bSGeliang Tang			pm_nl_flush_endpoint ${connector_ns}
6095e287fe7SGeliang Tang		elif [ $rm_nr_ns2 -eq 9 ]; then
6105e287fe7SGeliang Tang			local addr
6115e287fe7SGeliang Tang			if is_v6 "${connect_addr}"; then
6125e287fe7SGeliang Tang				addr="dead:beef:1::2"
6135e287fe7SGeliang Tang			else
6145e287fe7SGeliang Tang				addr="10.0.1.2"
6155e287fe7SGeliang Tang			fi
61634aa6e3bSGeliang Tang			pm_nl_del_endpoint ${connector_ns} 0 $addr
6176fe4ccdcSGeliang Tang		fi
618dd72b0feSGeliang Tang	fi
619dd72b0feSGeliang Tang
6206a0653b9SGeliang Tang	if [ ! -z $sflags ]; then
621718eb44eSGeliang Tang		sleep 1
622718eb44eSGeliang Tang		for netns in "$ns1" "$ns2"; do
623dda61b3dSGeliang Tang			pm_nl_show_endpoints $netns | while read line; do
62433397b83SGeliang Tang				local arr=($line)
625bccefb76SGeliang Tang				local nr=0
626f0140386SGeliang Tang				local id
62733397b83SGeliang Tang
62833397b83SGeliang Tang				for i in ${arr[@]}; do
629bccefb76SGeliang Tang					if [ $i = "id" ]; then
630bccefb76SGeliang Tang						id=${arr[$nr+1]}
631718eb44eSGeliang Tang					fi
632bccefb76SGeliang Tang					let nr+=1
63333397b83SGeliang Tang				done
634bccefb76SGeliang Tang				pm_nl_change_endpoint $netns $id $sflags
63533397b83SGeliang Tang			done
636718eb44eSGeliang Tang		done
637718eb44eSGeliang Tang	fi
638718eb44eSGeliang Tang
639b08fbf24SPaolo Abeni	wait $cpid
640b08fbf24SPaolo Abeni	retc=$?
641b08fbf24SPaolo Abeni	wait $spid
642b08fbf24SPaolo Abeni	rets=$?
643b08fbf24SPaolo Abeni
644b08fbf24SPaolo Abeni	if [ $capture -eq 1 ]; then
645b08fbf24SPaolo Abeni	    sleep 1
646b08fbf24SPaolo Abeni	    kill $cappid
647b08fbf24SPaolo Abeni	fi
648b08fbf24SPaolo Abeni
649c2a55e8fSMatthieu Baerts	NSTAT_HISTORY=/tmp/${listener_ns}.nstat ip netns exec ${listener_ns} \
650c2a55e8fSMatthieu Baerts		nstat | grep Tcp > /tmp/${listener_ns}.out
651c2a55e8fSMatthieu Baerts	NSTAT_HISTORY=/tmp/${connector_ns}.nstat ip netns exec ${connector_ns} \
652c2a55e8fSMatthieu Baerts		nstat | grep Tcp > /tmp/${connector_ns}.out
653c2a55e8fSMatthieu Baerts
654b08fbf24SPaolo Abeni	if [ ${rets} -ne 0 ] || [ ${retc} -ne 0 ]; then
655b08fbf24SPaolo Abeni		echo " client exit code $retc, server $rets" 1>&2
6568b974778SMatthieu Baerts		echo -e "\nnetns ${listener_ns} socket stat for ${port}:" 1>&2
657c2a55e8fSMatthieu Baerts		ip netns exec ${listener_ns} ss -Menita 1>&2 -o "sport = :$port"
658c2a55e8fSMatthieu Baerts		cat /tmp/${listener_ns}.out
6598b974778SMatthieu Baerts		echo -e "\nnetns ${connector_ns} socket stat for ${port}:" 1>&2
660c2a55e8fSMatthieu Baerts		ip netns exec ${connector_ns} ss -Menita 1>&2 -o "dport = :$port"
661c2a55e8fSMatthieu Baerts		cat /tmp/${connector_ns}.out
662b08fbf24SPaolo Abeni
663b08fbf24SPaolo Abeni		cat "$capout"
6648b819a84SFlorian Westphal		ret=1
665b08fbf24SPaolo Abeni		return 1
666b08fbf24SPaolo Abeni	fi
667b08fbf24SPaolo Abeni
66834b572b7SGeliang Tang	if [ "$test_link_fail" -gt 1 ];then
6697d1e6f16SPaolo Abeni		check_transfer $sinfail $cout "file received by client"
6707d1e6f16SPaolo Abeni	else
671b08fbf24SPaolo Abeni		check_transfer $sin $cout "file received by client"
6727d1e6f16SPaolo Abeni	fi
673b08fbf24SPaolo Abeni	retc=$?
6748b819a84SFlorian Westphal	if [ "$test_link_fail" -eq 0 ];then
675b08fbf24SPaolo Abeni		check_transfer $cin $sout "file received by server"
6768b819a84SFlorian Westphal	else
6778b819a84SFlorian Westphal		check_transfer $cinsent $sout "file received by server"
6788b819a84SFlorian Westphal	fi
679b08fbf24SPaolo Abeni	rets=$?
680b08fbf24SPaolo Abeni
681b08fbf24SPaolo Abeni	if [ $retc -eq 0 ] && [ $rets -eq 0 ];then
682b08fbf24SPaolo Abeni		cat "$capout"
683b08fbf24SPaolo Abeni		return 0
684b08fbf24SPaolo Abeni	fi
685b08fbf24SPaolo Abeni
686b08fbf24SPaolo Abeni	cat "$capout"
687b08fbf24SPaolo Abeni	return 1
688b08fbf24SPaolo Abeni}
689b08fbf24SPaolo Abeni
690b08fbf24SPaolo Abenimake_file()
691b08fbf24SPaolo Abeni{
692b08fbf24SPaolo Abeni	name=$1
693b08fbf24SPaolo Abeni	who=$2
6948b819a84SFlorian Westphal	size=$3
695b08fbf24SPaolo Abeni
6968b819a84SFlorian Westphal	dd if=/dev/urandom of="$name" bs=1024 count=$size 2> /dev/null
697b08fbf24SPaolo Abeni	echo -e "\nMPTCP_TEST_FILE_END_MARKER" >> "$name"
698b08fbf24SPaolo Abeni
6998b819a84SFlorian Westphal	echo "Created $name (size $size KB) containing data sent by $who"
700b08fbf24SPaolo Abeni}
701b08fbf24SPaolo Abeni
702b08fbf24SPaolo Abenirun_tests()
703b08fbf24SPaolo Abeni{
704b08fbf24SPaolo Abeni	listener_ns="$1"
705b08fbf24SPaolo Abeni	connector_ns="$2"
706b08fbf24SPaolo Abeni	connect_addr="$3"
7078b819a84SFlorian Westphal	test_linkfail="${4:-0}"
7082e8cbf45SGeliang Tang	addr_nr_ns1="${5:-0}"
7092e8cbf45SGeliang Tang	addr_nr_ns2="${6:-0}"
7108b819a84SFlorian Westphal	speed="${7:-fast}"
7116a0653b9SGeliang Tang	sflags="${8:-""}"
7128b819a84SFlorian Westphal
71334b572b7SGeliang Tang	# The values above 2 are reused to make test files
71434b572b7SGeliang Tang	# with the given sizes (KB)
71534b572b7SGeliang Tang	if [ "$test_linkfail" -gt 2 ]; then
71634b572b7SGeliang Tang		size=$test_linkfail
71734b572b7SGeliang Tang
71834b572b7SGeliang Tang		if [ -z "$cinfail" ]; then
71934b572b7SGeliang Tang			cinfail=$(mktemp)
72034b572b7SGeliang Tang		fi
72134b572b7SGeliang Tang		make_file "$cinfail" "client" $size
7227d1e6f16SPaolo Abeni	# create the input file for the failure test when
7237d1e6f16SPaolo Abeni	# the first failure test run
72434b572b7SGeliang Tang	elif [ "$test_linkfail" -ne 0 -a -z "$cinfail" ]; then
7257d1e6f16SPaolo Abeni		# the client file must be considerably larger
7267d1e6f16SPaolo Abeni		# of the maximum expected cwin value, or the
7277d1e6f16SPaolo Abeni		# link utilization will be not predicable
7287d1e6f16SPaolo Abeni		size=$((RANDOM%2))
7298b819a84SFlorian Westphal		size=$((size+1))
7307d1e6f16SPaolo Abeni		size=$((size*8192))
7317d1e6f16SPaolo Abeni		size=$((size + ( $RANDOM % 8192) ))
7328b819a84SFlorian Westphal
7337d1e6f16SPaolo Abeni		cinfail=$(mktemp)
7347d1e6f16SPaolo Abeni		make_file "$cinfail" "client" $size
7357d1e6f16SPaolo Abeni	fi
7367d1e6f16SPaolo Abeni
73734b572b7SGeliang Tang	if [ "$test_linkfail" -gt 2 ]; then
73834b572b7SGeliang Tang		size=$test_linkfail
73934b572b7SGeliang Tang
74034b572b7SGeliang Tang		if [ -z "$sinfail" ]; then
74134b572b7SGeliang Tang			sinfail=$(mktemp)
74234b572b7SGeliang Tang		fi
74334b572b7SGeliang Tang		make_file "$sinfail" "server" $size
74434b572b7SGeliang Tang	elif [ "$test_linkfail" -eq 2 -a -z "$sinfail" ]; then
7457d1e6f16SPaolo Abeni		size=$((RANDOM%16))
7467d1e6f16SPaolo Abeni		size=$((size+1))
7477d1e6f16SPaolo Abeni		size=$((size*2048))
7487d1e6f16SPaolo Abeni
7497d1e6f16SPaolo Abeni		sinfail=$(mktemp)
7507d1e6f16SPaolo Abeni		make_file "$sinfail" "server" $size
7518b819a84SFlorian Westphal	fi
752b08fbf24SPaolo Abeni
7538d014eaaSGeliang Tang	do_transfer ${listener_ns} ${connector_ns} MPTCP MPTCP ${connect_addr} \
7546a0653b9SGeliang Tang		${test_linkfail} ${addr_nr_ns1} ${addr_nr_ns2} ${speed} ${sflags}
755b08fbf24SPaolo Abeni}
756b08fbf24SPaolo Abeni
757327b9a94SPaolo Abenidump_stats()
758327b9a94SPaolo Abeni{
759327b9a94SPaolo Abeni	echo Server ns stats
760327b9a94SPaolo Abeni	ip netns exec $ns1 nstat -as | grep Tcp
761327b9a94SPaolo Abeni	echo Client ns stats
762327b9a94SPaolo Abeni	ip netns exec $ns2 nstat -as | grep Tcp
763327b9a94SPaolo Abeni}
764327b9a94SPaolo Abeni
765af66d3e1SGeliang Tangchk_csum_nr()
766af66d3e1SGeliang Tang{
767af66d3e1SGeliang Tang	local msg=${1:-""}
76826516e10SGeliang Tang	local csum_ns1=${2:-0}
76926516e10SGeliang Tang	local csum_ns2=${3:-0}
770af66d3e1SGeliang Tang	local count
771af66d3e1SGeliang Tang	local dump_stats
77226516e10SGeliang Tang	local allow_multi_errors_ns1=0
77326516e10SGeliang Tang	local allow_multi_errors_ns2=0
77426516e10SGeliang Tang
77526516e10SGeliang Tang	if [[ "${csum_ns1}" = "+"* ]]; then
77626516e10SGeliang Tang		allow_multi_errors_ns1=1
77726516e10SGeliang Tang		csum_ns1=${csum_ns1:1}
77826516e10SGeliang Tang	fi
77926516e10SGeliang Tang	if [[ "${csum_ns2}" = "+"* ]]; then
78026516e10SGeliang Tang		allow_multi_errors_ns2=1
78126516e10SGeliang Tang		csum_ns2=${csum_ns2:1}
78226516e10SGeliang Tang	fi
783af66d3e1SGeliang Tang
784af66d3e1SGeliang Tang	if [ ! -z "$msg" ]; then
7859a0a9367SGeliang Tang		printf "%03u" "$TEST_COUNT"
786af66d3e1SGeliang Tang	else
787af66d3e1SGeliang Tang		echo -n "   "
788af66d3e1SGeliang Tang	fi
789af66d3e1SGeliang Tang	printf " %-36s %s" "$msg" "sum"
790af66d3e1SGeliang Tang	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtDataCsumErr | awk '{print $2}'`
791af66d3e1SGeliang Tang	[ -z "$count" ] && count=0
79226516e10SGeliang Tang	if [ "$count" != $csum_ns1 -a $allow_multi_errors_ns1 -eq 0 ] ||
79326516e10SGeliang Tang	   [ "$count" -lt $csum_ns1 -a $allow_multi_errors_ns1 -eq 1 ]; then
79426516e10SGeliang Tang		echo "[fail] got $count data checksum error[s] expected $csum_ns1"
795af66d3e1SGeliang Tang		ret=1
796af66d3e1SGeliang Tang		dump_stats=1
797af66d3e1SGeliang Tang	else
798af66d3e1SGeliang Tang		echo -n "[ ok ]"
799af66d3e1SGeliang Tang	fi
800af66d3e1SGeliang Tang	echo -n " - csum  "
801af66d3e1SGeliang Tang	count=`ip netns exec $ns2 nstat -as | grep MPTcpExtDataCsumErr | awk '{print $2}'`
802af66d3e1SGeliang Tang	[ -z "$count" ] && count=0
80326516e10SGeliang Tang	if [ "$count" != $csum_ns2 -a $allow_multi_errors_ns2 -eq 0 ] ||
80426516e10SGeliang Tang	   [ "$count" -lt $csum_ns2 -a $allow_multi_errors_ns2 -eq 1 ]; then
80526516e10SGeliang Tang		echo "[fail] got $count data checksum error[s] expected $csum_ns2"
806af66d3e1SGeliang Tang		ret=1
807af66d3e1SGeliang Tang		dump_stats=1
808af66d3e1SGeliang Tang	else
809af66d3e1SGeliang Tang		echo "[ ok ]"
810af66d3e1SGeliang Tang	fi
811327b9a94SPaolo Abeni	[ "${dump_stats}" = 1 ] && dump_stats
812af66d3e1SGeliang Tang}
813af66d3e1SGeliang Tang
8146bb3ab49SGeliang Tangchk_fail_nr()
8156bb3ab49SGeliang Tang{
81626516e10SGeliang Tang	local fail_tx=$1
81726516e10SGeliang Tang	local fail_rx=$2
8186bb3ab49SGeliang Tang	local count
8196bb3ab49SGeliang Tang	local dump_stats
8206bb3ab49SGeliang Tang
8219a0a9367SGeliang Tang	printf "%-${nr_blank}s %s" " " "ftx"
8226bb3ab49SGeliang Tang	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPFailTx | awk '{print $2}'`
8236bb3ab49SGeliang Tang	[ -z "$count" ] && count=0
82426516e10SGeliang Tang	if [ "$count" != "$fail_tx" ]; then
82526516e10SGeliang Tang		echo "[fail] got $count MP_FAIL[s] TX expected $fail_tx"
8266bb3ab49SGeliang Tang		ret=1
8276bb3ab49SGeliang Tang		dump_stats=1
8286bb3ab49SGeliang Tang	else
8296bb3ab49SGeliang Tang		echo -n "[ ok ]"
8306bb3ab49SGeliang Tang	fi
8316bb3ab49SGeliang Tang
83226516e10SGeliang Tang	echo -n " - failrx"
8336bb3ab49SGeliang Tang	count=`ip netns exec $ns2 nstat -as | grep MPTcpExtMPFailRx | awk '{print $2}'`
8346bb3ab49SGeliang Tang	[ -z "$count" ] && count=0
83526516e10SGeliang Tang	if [ "$count" != "$fail_rx" ]; then
83626516e10SGeliang Tang		echo "[fail] got $count MP_FAIL[s] RX expected $fail_rx"
8376bb3ab49SGeliang Tang		ret=1
8386bb3ab49SGeliang Tang		dump_stats=1
8396bb3ab49SGeliang Tang	else
8406bb3ab49SGeliang Tang		echo "[ ok ]"
8416bb3ab49SGeliang Tang	fi
8426bb3ab49SGeliang Tang
843327b9a94SPaolo Abeni	[ "${dump_stats}" = 1 ] && dump_stats
8446bb3ab49SGeliang Tang}
8456bb3ab49SGeliang Tang
846e8e947efSGeliang Tangchk_fclose_nr()
847e8e947efSGeliang Tang{
848e8e947efSGeliang Tang	local fclose_tx=$1
849e8e947efSGeliang Tang	local fclose_rx=$2
850e8e947efSGeliang Tang	local count
851e8e947efSGeliang Tang	local dump_stats
852e8e947efSGeliang Tang
853e8e947efSGeliang Tang	printf "%-${nr_blank}s %s" " " "ctx"
854e8e947efSGeliang Tang	count=$(ip netns exec $ns2 nstat -as | grep MPTcpExtMPFastcloseTx | awk '{print $2}')
855e8e947efSGeliang Tang	[ -z "$count" ] && count=0
856e8e947efSGeliang Tang	if [ "$count" != "$fclose_tx" ]; then
857e8e947efSGeliang Tang		echo "[fail] got $count MP_FASTCLOSE[s] TX expected $fclose_tx"
858e8e947efSGeliang Tang		ret=1
859e8e947efSGeliang Tang		dump_stats=1
860e8e947efSGeliang Tang	else
861e8e947efSGeliang Tang		echo -n "[ ok ]"
862e8e947efSGeliang Tang	fi
863e8e947efSGeliang Tang
864e8e947efSGeliang Tang	echo -n " - fclzrx"
865e8e947efSGeliang Tang	count=$(ip netns exec $ns1 nstat -as | grep MPTcpExtMPFastcloseRx | awk '{print $2}')
866e8e947efSGeliang Tang	[ -z "$count" ] && count=0
867e8e947efSGeliang Tang	if [ "$count" != "$fclose_rx" ]; then
868e8e947efSGeliang Tang		echo "[fail] got $count MP_FASTCLOSE[s] RX expected $fclose_rx"
869e8e947efSGeliang Tang		ret=1
870e8e947efSGeliang Tang		dump_stats=1
871e8e947efSGeliang Tang	else
872e8e947efSGeliang Tang		echo "[ ok ]"
873e8e947efSGeliang Tang	fi
874e8e947efSGeliang Tang
875e8e947efSGeliang Tang	[ "${dump_stats}" = 1 ] && dump_stats
876e8e947efSGeliang Tang}
877e8e947efSGeliang Tang
878922fd2b3SGeliang Tangchk_rst_nr()
879922fd2b3SGeliang Tang{
880922fd2b3SGeliang Tang	local rst_tx=$1
881922fd2b3SGeliang Tang	local rst_rx=$2
882922fd2b3SGeliang Tang	local ns_invert=${3:-""}
883922fd2b3SGeliang Tang	local count
884922fd2b3SGeliang Tang	local dump_stats
885922fd2b3SGeliang Tang	local ns_tx=$ns1
886922fd2b3SGeliang Tang	local ns_rx=$ns2
887922fd2b3SGeliang Tang	local extra_msg=""
888922fd2b3SGeliang Tang
889922fd2b3SGeliang Tang	if [[ $ns_invert = "invert" ]]; then
890922fd2b3SGeliang Tang		ns_tx=$ns2
891922fd2b3SGeliang Tang		ns_rx=$ns1
892922fd2b3SGeliang Tang		extra_msg="   invert"
893922fd2b3SGeliang Tang	fi
894922fd2b3SGeliang Tang
895922fd2b3SGeliang Tang	printf "%-${nr_blank}s %s" " " "rtx"
896922fd2b3SGeliang Tang	count=$(ip netns exec $ns_tx nstat -as | grep MPTcpExtMPRstTx | awk '{print $2}')
897922fd2b3SGeliang Tang	[ -z "$count" ] && count=0
898922fd2b3SGeliang Tang	if [ "$count" != "$rst_tx" ]; then
899922fd2b3SGeliang Tang		echo "[fail] got $count MP_RST[s] TX expected $rst_tx"
900922fd2b3SGeliang Tang		ret=1
901922fd2b3SGeliang Tang		dump_stats=1
902922fd2b3SGeliang Tang	else
903922fd2b3SGeliang Tang		echo -n "[ ok ]"
904922fd2b3SGeliang Tang	fi
905922fd2b3SGeliang Tang
906922fd2b3SGeliang Tang	echo -n " - rstrx "
907922fd2b3SGeliang Tang	count=$(ip netns exec $ns_rx nstat -as | grep MPTcpExtMPRstRx | awk '{print $2}')
908922fd2b3SGeliang Tang	[ -z "$count" ] && count=0
909922fd2b3SGeliang Tang	if [ "$count" != "$rst_rx" ]; then
910922fd2b3SGeliang Tang		echo "[fail] got $count MP_RST[s] RX expected $rst_rx"
911922fd2b3SGeliang Tang		ret=1
912922fd2b3SGeliang Tang		dump_stats=1
913922fd2b3SGeliang Tang	else
914922fd2b3SGeliang Tang		echo -n "[ ok ]"
915922fd2b3SGeliang Tang	fi
916922fd2b3SGeliang Tang
917922fd2b3SGeliang Tang	[ "${dump_stats}" = 1 ] && dump_stats
918922fd2b3SGeliang Tang
919922fd2b3SGeliang Tang	echo "$extra_msg"
920922fd2b3SGeliang Tang}
921922fd2b3SGeliang Tang
922b08fbf24SPaolo Abenichk_join_nr()
923b08fbf24SPaolo Abeni{
924b08fbf24SPaolo Abeni	local msg="$1"
925b08fbf24SPaolo Abeni	local syn_nr=$2
926b08fbf24SPaolo Abeni	local syn_ack_nr=$3
927b08fbf24SPaolo Abeni	local ack_nr=$4
92826516e10SGeliang Tang	local csum_ns1=${5:-0}
92926516e10SGeliang Tang	local csum_ns2=${6:-0}
93026516e10SGeliang Tang	local fail_nr=${7:-0}
93126516e10SGeliang Tang	local rst_nr=${8:-0}
932b08fbf24SPaolo Abeni	local count
933b08fbf24SPaolo Abeni	local dump_stats
934e35f885bSPaolo Abeni	local with_cookie
935b08fbf24SPaolo Abeni
9369a0a9367SGeliang Tang	printf "%03u %-36s %s" "$TEST_COUNT" "$msg" "syn"
937b08fbf24SPaolo Abeni	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinSynRx | awk '{print $2}'`
938b08fbf24SPaolo Abeni	[ -z "$count" ] && count=0
939b08fbf24SPaolo Abeni	if [ "$count" != "$syn_nr" ]; then
940b08fbf24SPaolo Abeni		echo "[fail] got $count JOIN[s] syn expected $syn_nr"
941b08fbf24SPaolo Abeni		ret=1
942b08fbf24SPaolo Abeni		dump_stats=1
943b08fbf24SPaolo Abeni	else
944b08fbf24SPaolo Abeni		echo -n "[ ok ]"
945b08fbf24SPaolo Abeni	fi
946b08fbf24SPaolo Abeni
947b08fbf24SPaolo Abeni	echo -n " - synack"
948e35f885bSPaolo Abeni	with_cookie=`ip netns exec $ns2 sysctl -n net.ipv4.tcp_syncookies`
949b08fbf24SPaolo Abeni	count=`ip netns exec $ns2 nstat -as | grep MPTcpExtMPJoinSynAckRx | awk '{print $2}'`
950b08fbf24SPaolo Abeni	[ -z "$count" ] && count=0
951b08fbf24SPaolo Abeni	if [ "$count" != "$syn_ack_nr" ]; then
952e35f885bSPaolo Abeni		# simult connections exceeding the limit with cookie enabled could go up to
953e35f885bSPaolo Abeni		# synack validation as the conn limit can be enforced reliably only after
954e35f885bSPaolo Abeni		# the subflow creation
955e35f885bSPaolo Abeni		if [ "$with_cookie" = 2 ] && [ "$count" -gt "$syn_ack_nr" ] && [ "$count" -le "$syn_nr" ]; then
956e35f885bSPaolo Abeni			echo -n "[ ok ]"
957e35f885bSPaolo Abeni		else
958b08fbf24SPaolo Abeni			echo "[fail] got $count JOIN[s] synack expected $syn_ack_nr"
959b08fbf24SPaolo Abeni			ret=1
960b08fbf24SPaolo Abeni			dump_stats=1
961e35f885bSPaolo Abeni		fi
962b08fbf24SPaolo Abeni	else
963b08fbf24SPaolo Abeni		echo -n "[ ok ]"
964b08fbf24SPaolo Abeni	fi
965b08fbf24SPaolo Abeni
966b08fbf24SPaolo Abeni	echo -n " - ack"
967b08fbf24SPaolo Abeni	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinAckRx | awk '{print $2}'`
968b08fbf24SPaolo Abeni	[ -z "$count" ] && count=0
969b08fbf24SPaolo Abeni	if [ "$count" != "$ack_nr" ]; then
970b08fbf24SPaolo Abeni		echo "[fail] got $count JOIN[s] ack expected $ack_nr"
971b08fbf24SPaolo Abeni		ret=1
972b08fbf24SPaolo Abeni		dump_stats=1
973b08fbf24SPaolo Abeni	else
974b08fbf24SPaolo Abeni		echo "[ ok ]"
975b08fbf24SPaolo Abeni	fi
976327b9a94SPaolo Abeni	[ "${dump_stats}" = 1 ] && dump_stats
977af66d3e1SGeliang Tang	if [ $checksum -eq 1 ]; then
97826516e10SGeliang Tang		chk_csum_nr "" $csum_ns1 $csum_ns2
97926516e10SGeliang Tang		chk_fail_nr $fail_nr $fail_nr
98026516e10SGeliang Tang		chk_rst_nr $rst_nr $rst_nr
981af66d3e1SGeliang Tang	fi
982b08fbf24SPaolo Abeni}
983b08fbf24SPaolo Abeni
9847d1e6f16SPaolo Abeni# a negative value for 'stale_max' means no upper bound:
9857d1e6f16SPaolo Abeni# for bidirectional transfer, if one peer sleep for a while
9867d1e6f16SPaolo Abeni# - as these tests do - we can have a quite high number of
9877d1e6f16SPaolo Abeni# stale/recover conversions, proportional to
9887d1e6f16SPaolo Abeni# sleep duration/ MPTCP-level RTX interval.
9897d1e6f16SPaolo Abenichk_stale_nr()
9907d1e6f16SPaolo Abeni{
9917d1e6f16SPaolo Abeni	local ns=$1
9927d1e6f16SPaolo Abeni	local stale_min=$2
9937d1e6f16SPaolo Abeni	local stale_max=$3
9947d1e6f16SPaolo Abeni	local stale_delta=$4
9957d1e6f16SPaolo Abeni	local dump_stats
9967d1e6f16SPaolo Abeni	local stale_nr
9977d1e6f16SPaolo Abeni	local recover_nr
9987d1e6f16SPaolo Abeni
9999a0a9367SGeliang Tang	printf "%-${nr_blank}s %-18s" " " "stale"
10007d1e6f16SPaolo Abeni	stale_nr=`ip netns exec $ns nstat -as | grep MPTcpExtSubflowStale | awk '{print $2}'`
10017d1e6f16SPaolo Abeni	[ -z "$stale_nr" ] && stale_nr=0
10027d1e6f16SPaolo Abeni	recover_nr=`ip netns exec $ns nstat -as | grep MPTcpExtSubflowRecover | awk '{print $2}'`
10037d1e6f16SPaolo Abeni	[ -z "$recover_nr" ] && recover_nr=0
10047d1e6f16SPaolo Abeni
10057d1e6f16SPaolo Abeni	if [ $stale_nr -lt $stale_min ] ||
10067d1e6f16SPaolo Abeni	   [ $stale_max -gt 0 -a $stale_nr -gt $stale_max ] ||
10077d1e6f16SPaolo Abeni	   [ $((stale_nr - $recover_nr)) -ne $stale_delta ]; then
10087d1e6f16SPaolo Abeni		echo "[fail] got $stale_nr stale[s] $recover_nr recover[s], " \
10097d1e6f16SPaolo Abeni		     " expected stale in range [$stale_min..$stale_max]," \
10107d1e6f16SPaolo Abeni		     " stale-recover delta $stale_delta "
10117d1e6f16SPaolo Abeni		ret=1
10127d1e6f16SPaolo Abeni		dump_stats=1
10137d1e6f16SPaolo Abeni	else
10147d1e6f16SPaolo Abeni		echo "[ ok ]"
10157d1e6f16SPaolo Abeni	fi
10167d1e6f16SPaolo Abeni
10177d1e6f16SPaolo Abeni	if [ "${dump_stats}" = 1 ]; then
10187d1e6f16SPaolo Abeni		echo $ns stats
10197d1e6f16SPaolo Abeni		ip netns exec $ns ip -s link show
10207d1e6f16SPaolo Abeni		ip netns exec $ns nstat -as | grep MPTcp
10217d1e6f16SPaolo Abeni	fi
10227d1e6f16SPaolo Abeni}
10237d1e6f16SPaolo Abeni
1024be613160SGeliang Tangchk_add_nr()
1025be613160SGeliang Tang{
1026be613160SGeliang Tang	local add_nr=$1
1027be613160SGeliang Tang	local echo_nr=$2
10288a127bf6SGeliang Tang	local port_nr=${3:-0}
10298a127bf6SGeliang Tang	local syn_nr=${4:-$port_nr}
10308a127bf6SGeliang Tang	local syn_ack_nr=${5:-$port_nr}
10318a127bf6SGeliang Tang	local ack_nr=${6:-$port_nr}
10328a127bf6SGeliang Tang	local mis_syn_nr=${7:-0}
10338a127bf6SGeliang Tang	local mis_ack_nr=${8:-0}
1034be613160SGeliang Tang	local count
1035be613160SGeliang Tang	local dump_stats
10366ef84b15SPaolo Abeni	local timeout
10376ef84b15SPaolo Abeni
10386ef84b15SPaolo Abeni	timeout=`ip netns exec $ns1 sysctl -n net.mptcp.add_addr_timeout`
1039be613160SGeliang Tang
10409a0a9367SGeliang Tang	printf "%-${nr_blank}s %s" " " "add"
10416ef84b15SPaolo Abeni	count=`ip netns exec $ns2 nstat -as MPTcpExtAddAddr | grep MPTcpExtAddAddr | awk '{print $2}'`
1042be613160SGeliang Tang	[ -z "$count" ] && count=0
10436ef84b15SPaolo Abeni
10446ef84b15SPaolo Abeni	# if the test configured a short timeout tolerate greater then expected
10456ef84b15SPaolo Abeni	# add addrs options, due to retransmissions
10466ef84b15SPaolo Abeni	if [ "$count" != "$add_nr" ] && [ "$timeout" -gt 1 -o "$count" -lt "$add_nr" ]; then
1047be613160SGeliang Tang		echo "[fail] got $count ADD_ADDR[s] expected $add_nr"
1048be613160SGeliang Tang		ret=1
1049be613160SGeliang Tang		dump_stats=1
1050be613160SGeliang Tang	else
1051be613160SGeliang Tang		echo -n "[ ok ]"
1052be613160SGeliang Tang	fi
1053be613160SGeliang Tang
1054be613160SGeliang Tang	echo -n " - echo  "
1055be613160SGeliang Tang	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtEchoAdd | awk '{print $2}'`
1056be613160SGeliang Tang	[ -z "$count" ] && count=0
1057be613160SGeliang Tang	if [ "$count" != "$echo_nr" ]; then
1058be613160SGeliang Tang		echo "[fail] got $count ADD_ADDR echo[s] expected $echo_nr"
1059be613160SGeliang Tang		ret=1
1060be613160SGeliang Tang		dump_stats=1
1061be613160SGeliang Tang	else
10628a127bf6SGeliang Tang		echo -n "[ ok ]"
10638a127bf6SGeliang Tang	fi
10648a127bf6SGeliang Tang
10658a127bf6SGeliang Tang	if [ $port_nr -gt 0 ]; then
10668a127bf6SGeliang Tang		echo -n " - pt "
10678a127bf6SGeliang Tang		count=`ip netns exec $ns2 nstat -as | grep MPTcpExtPortAdd | awk '{print $2}'`
10688a127bf6SGeliang Tang		[ -z "$count" ] && count=0
10698a127bf6SGeliang Tang		if [ "$count" != "$port_nr" ]; then
10708a127bf6SGeliang Tang			echo "[fail] got $count ADD_ADDR[s] with a port-number expected $port_nr"
10718a127bf6SGeliang Tang			ret=1
10728a127bf6SGeliang Tang			dump_stats=1
10738a127bf6SGeliang Tang		else
1074be613160SGeliang Tang			echo "[ ok ]"
1075be613160SGeliang Tang		fi
1076be613160SGeliang Tang
10779a0a9367SGeliang Tang		printf "%-${nr_blank}s %s" " " "syn"
10788a127bf6SGeliang Tang		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinPortSynRx |
10798a127bf6SGeliang Tang			awk '{print $2}'`
10808a127bf6SGeliang Tang		[ -z "$count" ] && count=0
10818a127bf6SGeliang Tang		if [ "$count" != "$syn_nr" ]; then
10828a127bf6SGeliang Tang			echo "[fail] got $count JOIN[s] syn with a different \
10838a127bf6SGeliang Tang				port-number expected $syn_nr"
10848a127bf6SGeliang Tang			ret=1
10858a127bf6SGeliang Tang			dump_stats=1
10868a127bf6SGeliang Tang		else
10878a127bf6SGeliang Tang			echo -n "[ ok ]"
10888a127bf6SGeliang Tang		fi
10898a127bf6SGeliang Tang
10908a127bf6SGeliang Tang		echo -n " - synack"
10918a127bf6SGeliang Tang		count=`ip netns exec $ns2 nstat -as | grep MPTcpExtMPJoinPortSynAckRx |
10928a127bf6SGeliang Tang			awk '{print $2}'`
10938a127bf6SGeliang Tang		[ -z "$count" ] && count=0
10948a127bf6SGeliang Tang		if [ "$count" != "$syn_ack_nr" ]; then
10958a127bf6SGeliang Tang			echo "[fail] got $count JOIN[s] synack with a different \
10968a127bf6SGeliang Tang				port-number expected $syn_ack_nr"
10978a127bf6SGeliang Tang			ret=1
10988a127bf6SGeliang Tang			dump_stats=1
10998a127bf6SGeliang Tang		else
11008a127bf6SGeliang Tang			echo -n "[ ok ]"
11018a127bf6SGeliang Tang		fi
11028a127bf6SGeliang Tang
11038a127bf6SGeliang Tang		echo -n " - ack"
11048a127bf6SGeliang Tang		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPJoinPortAckRx |
11058a127bf6SGeliang Tang			awk '{print $2}'`
11068a127bf6SGeliang Tang		[ -z "$count" ] && count=0
11078a127bf6SGeliang Tang		if [ "$count" != "$ack_nr" ]; then
11088a127bf6SGeliang Tang			echo "[fail] got $count JOIN[s] ack with a different \
11098a127bf6SGeliang Tang				port-number expected $ack_nr"
11108a127bf6SGeliang Tang			ret=1
11118a127bf6SGeliang Tang			dump_stats=1
11128a127bf6SGeliang Tang		else
11138a127bf6SGeliang Tang			echo "[ ok ]"
11148a127bf6SGeliang Tang		fi
11158a127bf6SGeliang Tang
11169a0a9367SGeliang Tang		printf "%-${nr_blank}s %s" " " "syn"
11178a127bf6SGeliang Tang		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMismatchPortSynRx |
11188a127bf6SGeliang Tang			awk '{print $2}'`
11198a127bf6SGeliang Tang		[ -z "$count" ] && count=0
11208a127bf6SGeliang Tang		if [ "$count" != "$mis_syn_nr" ]; then
11218a127bf6SGeliang Tang			echo "[fail] got $count JOIN[s] syn with a mismatched \
11228a127bf6SGeliang Tang				port-number expected $mis_syn_nr"
11238a127bf6SGeliang Tang			ret=1
11248a127bf6SGeliang Tang			dump_stats=1
11258a127bf6SGeliang Tang		else
11268a127bf6SGeliang Tang			echo -n "[ ok ]"
11278a127bf6SGeliang Tang		fi
11288a127bf6SGeliang Tang
11298a127bf6SGeliang Tang		echo -n " - ack   "
11308a127bf6SGeliang Tang		count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMismatchPortAckRx |
11318a127bf6SGeliang Tang			awk '{print $2}'`
11328a127bf6SGeliang Tang		[ -z "$count" ] && count=0
11338a127bf6SGeliang Tang		if [ "$count" != "$mis_ack_nr" ]; then
11348a127bf6SGeliang Tang			echo "[fail] got $count JOIN[s] ack with a mismatched \
11358a127bf6SGeliang Tang				port-number expected $mis_ack_nr"
11368a127bf6SGeliang Tang			ret=1
11378a127bf6SGeliang Tang			dump_stats=1
11388a127bf6SGeliang Tang		else
11398a127bf6SGeliang Tang			echo "[ ok ]"
11408a127bf6SGeliang Tang		fi
11418a127bf6SGeliang Tang	else
11428a127bf6SGeliang Tang		echo ""
11438a127bf6SGeliang Tang	fi
11448a127bf6SGeliang Tang
1145327b9a94SPaolo Abeni	[ "${dump_stats}" = 1 ] && dump_stats
1146be613160SGeliang Tang}
1147be613160SGeliang Tang
1148dd72b0feSGeliang Tangchk_rm_nr()
1149dd72b0feSGeliang Tang{
1150dd72b0feSGeliang Tang	local rm_addr_nr=$1
1151dd72b0feSGeliang Tang	local rm_subflow_nr=$2
11527028ba8aSGeliang Tang	local invert=${3:-""}
1153dd72b0feSGeliang Tang	local count
1154dd72b0feSGeliang Tang	local dump_stats
11557d9bf018SGeliang Tang	local addr_ns=$ns1
11567d9bf018SGeliang Tang	local subflow_ns=$ns2
11577d9bf018SGeliang Tang	local extra_msg=""
11587028ba8aSGeliang Tang
11597d9bf018SGeliang Tang	if [[ $invert = "invert" ]]; then
11607028ba8aSGeliang Tang		addr_ns=$ns2
11617028ba8aSGeliang Tang		subflow_ns=$ns1
11627d9bf018SGeliang Tang		extra_msg="   invert"
11637028ba8aSGeliang Tang	fi
1164dd72b0feSGeliang Tang
11659a0a9367SGeliang Tang	printf "%-${nr_blank}s %s" " " "rm "
11667028ba8aSGeliang Tang	count=`ip netns exec $addr_ns nstat -as | grep MPTcpExtRmAddr | awk '{print $2}'`
1167dd72b0feSGeliang Tang	[ -z "$count" ] && count=0
1168dd72b0feSGeliang Tang	if [ "$count" != "$rm_addr_nr" ]; then
1169dd72b0feSGeliang Tang		echo "[fail] got $count RM_ADDR[s] expected $rm_addr_nr"
1170dd72b0feSGeliang Tang		ret=1
1171dd72b0feSGeliang Tang		dump_stats=1
1172dd72b0feSGeliang Tang	else
1173dd72b0feSGeliang Tang		echo -n "[ ok ]"
1174dd72b0feSGeliang Tang	fi
1175dd72b0feSGeliang Tang
11767d9bf018SGeliang Tang	echo -n " - rmsf  "
11777028ba8aSGeliang Tang	count=`ip netns exec $subflow_ns nstat -as | grep MPTcpExtRmSubflow | awk '{print $2}'`
1178dd72b0feSGeliang Tang	[ -z "$count" ] && count=0
1179dd72b0feSGeliang Tang	if [ "$count" != "$rm_subflow_nr" ]; then
1180dd72b0feSGeliang Tang		echo "[fail] got $count RM_SUBFLOW[s] expected $rm_subflow_nr"
1181dd72b0feSGeliang Tang		ret=1
1182dd72b0feSGeliang Tang		dump_stats=1
1183dd72b0feSGeliang Tang	else
11847d9bf018SGeliang Tang		echo -n "[ ok ]"
1185dd72b0feSGeliang Tang	fi
1186dd72b0feSGeliang Tang
1187327b9a94SPaolo Abeni	[ "${dump_stats}" = 1 ] && dump_stats
11887d9bf018SGeliang Tang
11897d9bf018SGeliang Tang	echo "$extra_msg"
1190dd72b0feSGeliang Tang}
1191dd72b0feSGeliang Tang
1192718eb44eSGeliang Tangchk_prio_nr()
1193718eb44eSGeliang Tang{
1194718eb44eSGeliang Tang	local mp_prio_nr_tx=$1
1195718eb44eSGeliang Tang	local mp_prio_nr_rx=$2
1196718eb44eSGeliang Tang	local count
1197718eb44eSGeliang Tang	local dump_stats
1198718eb44eSGeliang Tang
11999a0a9367SGeliang Tang	printf "%-${nr_blank}s %s" " " "ptx"
1200718eb44eSGeliang Tang	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPPrioTx | awk '{print $2}'`
1201718eb44eSGeliang Tang	[ -z "$count" ] && count=0
1202718eb44eSGeliang Tang	if [ "$count" != "$mp_prio_nr_tx" ]; then
1203718eb44eSGeliang Tang		echo "[fail] got $count MP_PRIO[s] TX expected $mp_prio_nr_tx"
1204718eb44eSGeliang Tang		ret=1
1205718eb44eSGeliang Tang		dump_stats=1
1206718eb44eSGeliang Tang	else
1207718eb44eSGeliang Tang		echo -n "[ ok ]"
1208718eb44eSGeliang Tang	fi
1209718eb44eSGeliang Tang
1210718eb44eSGeliang Tang	echo -n " - prx   "
1211718eb44eSGeliang Tang	count=`ip netns exec $ns1 nstat -as | grep MPTcpExtMPPrioRx | awk '{print $2}'`
1212718eb44eSGeliang Tang	[ -z "$count" ] && count=0
1213718eb44eSGeliang Tang	if [ "$count" != "$mp_prio_nr_rx" ]; then
1214718eb44eSGeliang Tang		echo "[fail] got $count MP_PRIO[s] RX expected $mp_prio_nr_rx"
1215718eb44eSGeliang Tang		ret=1
1216718eb44eSGeliang Tang		dump_stats=1
1217718eb44eSGeliang Tang	else
1218718eb44eSGeliang Tang		echo "[ ok ]"
1219718eb44eSGeliang Tang	fi
1220718eb44eSGeliang Tang
1221327b9a94SPaolo Abeni	[ "${dump_stats}" = 1 ] && dump_stats
1222718eb44eSGeliang Tang}
1223718eb44eSGeliang Tang
12247d1e6f16SPaolo Abenichk_link_usage()
12257d1e6f16SPaolo Abeni{
12267d1e6f16SPaolo Abeni	local ns=$1
12277d1e6f16SPaolo Abeni	local link=$2
12287d1e6f16SPaolo Abeni	local out=$3
12297d1e6f16SPaolo Abeni	local expected_rate=$4
12307d1e6f16SPaolo Abeni	local tx_link=`ip netns exec $ns cat /sys/class/net/$link/statistics/tx_bytes`
12317d1e6f16SPaolo Abeni	local tx_total=`ls -l $out | awk '{print $5}'`
12327d1e6f16SPaolo Abeni	local tx_rate=$((tx_link * 100 / $tx_total))
12337d1e6f16SPaolo Abeni	local tolerance=5
12347d1e6f16SPaolo Abeni
12359a0a9367SGeliang Tang	printf "%-${nr_blank}s %-18s" " " "link usage"
12367d1e6f16SPaolo Abeni	if [ $tx_rate -lt $((expected_rate - $tolerance)) -o \
12377d1e6f16SPaolo Abeni	     $tx_rate -gt $((expected_rate + $tolerance)) ]; then
12387d1e6f16SPaolo Abeni		echo "[fail] got $tx_rate% usage, expected $expected_rate%"
12397d1e6f16SPaolo Abeni		ret=1
12407d1e6f16SPaolo Abeni	else
12417d1e6f16SPaolo Abeni		echo "[ ok ]"
12427d1e6f16SPaolo Abeni	fi
12437d1e6f16SPaolo Abeni}
12447d1e6f16SPaolo Abeni
124546e967d1SPaolo Abeniwait_for_tw()
124646e967d1SPaolo Abeni{
124746e967d1SPaolo Abeni	local timeout_ms=$((timeout_poll * 1000))
124846e967d1SPaolo Abeni	local time=0
124946e967d1SPaolo Abeni	local ns=$1
125046e967d1SPaolo Abeni
125146e967d1SPaolo Abeni	while [ $time -lt $timeout_ms ]; do
12525b31dda7SPaolo Abeni		local cnt=$(ip netns exec $ns nstat -as TcpAttemptFails | grep TcpAttemptFails | awk '{print $2}')
125346e967d1SPaolo Abeni
125446e967d1SPaolo Abeni		[ "$cnt" = 1 ] && return 1
125546e967d1SPaolo Abeni		time=$((time + 100))
125646e967d1SPaolo Abeni		sleep 0.1
125746e967d1SPaolo Abeni	done
125846e967d1SPaolo Abeni	return 1
125946e967d1SPaolo Abeni}
126046e967d1SPaolo Abeni
12611002b89fSGeliang Tangsubflows_tests()
12621002b89fSGeliang Tang{
12631002b89fSGeliang Tang	reset
1264b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1265b08fbf24SPaolo Abeni	chk_join_nr "no JOIN" "0" "0" "0"
1266b08fbf24SPaolo Abeni
12671002b89fSGeliang Tang	# subflow limited by client
1268b08fbf24SPaolo Abeni	reset
126934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 0
127034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 0
127134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1272b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1273b08fbf24SPaolo Abeni	chk_join_nr "single subflow, limited by client" 0 0 0
1274b08fbf24SPaolo Abeni
12751002b89fSGeliang Tang	# subflow limited by server
1276b08fbf24SPaolo Abeni	reset
127734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 0
127834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
127934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1280b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1281b08fbf24SPaolo Abeni	chk_join_nr "single subflow, limited by server" 1 1 0
1282b08fbf24SPaolo Abeni
1283b08fbf24SPaolo Abeni	# subflow
1284b08fbf24SPaolo Abeni	reset
128534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
128634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
128734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1288b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1289b08fbf24SPaolo Abeni	chk_join_nr "single subflow" 1 1 1
1290b08fbf24SPaolo Abeni
1291b08fbf24SPaolo Abeni	# multiple subflows
1292b08fbf24SPaolo Abeni	reset
129334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
129434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
129534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
129634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1297b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1298b08fbf24SPaolo Abeni	chk_join_nr "multiple subflows" 2 2 2
1299b08fbf24SPaolo Abeni
130072bcbc46SPaolo Abeni	# multiple subflows limited by server
1301b08fbf24SPaolo Abeni	reset
130234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
130334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
130434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
130534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
1306b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1307b08fbf24SPaolo Abeni	chk_join_nr "multiple subflows, limited by server" 2 2 1
1308c3eaa5f6SGeliang Tang
1309c3eaa5f6SGeliang Tang	# single subflow, dev
1310c3eaa5f6SGeliang Tang	reset
131134aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
131234aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
131334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow dev ns2eth3
1314c3eaa5f6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
1315c3eaa5f6SGeliang Tang	chk_join_nr "single subflow, dev" 1 1 1
13161002b89fSGeliang Tang}
1317b08fbf24SPaolo Abeni
131846e967d1SPaolo Abenisubflows_error_tests()
131946e967d1SPaolo Abeni{
132046e967d1SPaolo Abeni	# If a single subflow is configured, and matches the MPC src
132146e967d1SPaolo Abeni	# address, no additional subflow should be created
132246e967d1SPaolo Abeni	reset
132334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
132434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
132534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.1.2 flags subflow
132646e967d1SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
132746e967d1SPaolo Abeni	chk_join_nr "no MPC reuse with single endpoint" 0 0 0
132846e967d1SPaolo Abeni
132946e967d1SPaolo Abeni	# multiple subflows, with subflow creation error
133046e967d1SPaolo Abeni	reset
133134aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
133234aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
133334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
133434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
133546e967d1SPaolo Abeni	ip netns exec $ns1 iptables -A INPUT -s 10.0.3.2 -p tcp -j REJECT
133646e967d1SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
133746e967d1SPaolo Abeni	chk_join_nr "multi subflows, with failing subflow" 1 1 1
133846e967d1SPaolo Abeni
133946e967d1SPaolo Abeni	# multiple subflows, with subflow timeout on MPJ
134046e967d1SPaolo Abeni	reset
134134aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
134234aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
134334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
134434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
134546e967d1SPaolo Abeni	ip netns exec $ns1 iptables -A INPUT -s 10.0.3.2 -p tcp -j DROP
134646e967d1SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
134746e967d1SPaolo Abeni	chk_join_nr "multi subflows, with subflow timeout" 1 1 1
134846e967d1SPaolo Abeni
134946e967d1SPaolo Abeni	# multiple subflows, check that the endpoint corresponding to
135046e967d1SPaolo Abeni	# closed subflow (due to reset) is not reused if additional
135146e967d1SPaolo Abeni	# subflows are added later
135246e967d1SPaolo Abeni	reset
135334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
135434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
135534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
135646e967d1SPaolo Abeni	ip netns exec $ns1 iptables -A INPUT -s 10.0.3.2 -p tcp -j REJECT
135746e967d1SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow &
135846e967d1SPaolo Abeni
135946e967d1SPaolo Abeni	# updates in the child shell do not have any effect here, we
136046e967d1SPaolo Abeni	# need to bump the test counter for the above case
136146e967d1SPaolo Abeni	TEST_COUNT=$((TEST_COUNT+1))
136246e967d1SPaolo Abeni
136346e967d1SPaolo Abeni	# mpj subflow will be in TW after the reset
136446e967d1SPaolo Abeni	wait_for_tw $ns2
136534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
136646e967d1SPaolo Abeni	wait
136746e967d1SPaolo Abeni
136846e967d1SPaolo Abeni	# additional subflow could be created only if the PM select
136946e967d1SPaolo Abeni	# the later endpoint, skipping the already used one
137046e967d1SPaolo Abeni	chk_join_nr "multi subflows, fair usage on close" 1 1 1
137146e967d1SPaolo Abeni}
137246e967d1SPaolo Abeni
13731002b89fSGeliang Tangsignal_address_tests()
13741002b89fSGeliang Tang{
1375b08fbf24SPaolo Abeni	# add_address, unused
1376b08fbf24SPaolo Abeni	reset
137734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1378b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1379b08fbf24SPaolo Abeni	chk_join_nr "unused signal address" 0 0 0
1380be613160SGeliang Tang	chk_add_nr 1 1
1381b08fbf24SPaolo Abeni
1382b08fbf24SPaolo Abeni	# accept and use add_addr
1383b08fbf24SPaolo Abeni	reset
138434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
138534aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
138634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1387b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1388b08fbf24SPaolo Abeni	chk_join_nr "signal address" 1 1 1
1389be613160SGeliang Tang	chk_add_nr 1 1
1390b08fbf24SPaolo Abeni
1391b08fbf24SPaolo Abeni	# accept and use add_addr with an additional subflow
1392b08fbf24SPaolo Abeni	# note: signal address in server ns and local addresses in client ns must
1393b08fbf24SPaolo Abeni	# belong to different subnets or one of the listed local address could be
1394b08fbf24SPaolo Abeni	# used for 'add_addr' subflow
1395b08fbf24SPaolo Abeni	reset
139634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
139734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
139834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
139934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1400b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1401b08fbf24SPaolo Abeni	chk_join_nr "subflow and signal" 2 2 2
1402be613160SGeliang Tang	chk_add_nr 1 1
1403b08fbf24SPaolo Abeni
1404b08fbf24SPaolo Abeni	# accept and use add_addr with additional subflows
1405b08fbf24SPaolo Abeni	reset
140634aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 3
140734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
140834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
140934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
141034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1411b08fbf24SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1
1412b08fbf24SPaolo Abeni	chk_join_nr "multiple subflows and signal" 3 3 3
1413be613160SGeliang Tang	chk_add_nr 1 1
1414ef360019SGeliang Tang
1415ef360019SGeliang Tang	# signal addresses
1416ef360019SGeliang Tang	reset
141734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 3 3
141834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
141934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
142034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
142134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 3 3
1422ef360019SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
1423ef360019SGeliang Tang	chk_join_nr "signal addresses" 3 3 3
1424ef360019SGeliang Tang	chk_add_nr 3 3
1425ef360019SGeliang Tang
1426ef360019SGeliang Tang	# signal invalid addresses
1427ef360019SGeliang Tang	reset
142834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 3 3
142934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
143034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
143134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.14.1 flags signal
143234aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 3 3
1433ef360019SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
1434ef360019SGeliang Tang	chk_join_nr "signal invalid addresses" 1 1 1
1435ef360019SGeliang Tang	chk_add_nr 3 3
143633c563adSYonglong Li
143733c563adSYonglong Li	# signal addresses race test
143833c563adSYonglong Li	reset
143934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 4 4
144034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 4 4
144134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.1.1 flags signal
144234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
144334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
144434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
144534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.1.2 flags signal
144634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags signal
144734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags signal
144834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 flags signal
14496ef84b15SPaolo Abeni
14506ef84b15SPaolo Abeni	# the peer could possibly miss some addr notification, allow retransmission
14516ef84b15SPaolo Abeni	ip netns exec $ns1 sysctl -q net.mptcp.add_addr_timeout=1
14526ef84b15SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
1453857898ebSMatthieu Baerts	chk_join_nr "signal addresses race test" 3 3 3
145486e39e04SPaolo Abeni
145586e39e04SPaolo Abeni	# the server will not signal the address terminating
145686e39e04SPaolo Abeni	# the MPC subflow
145786e39e04SPaolo Abeni	chk_add_nr 3 3
14581002b89fSGeliang Tang}
1459b08fbf24SPaolo Abeni
14601002b89fSGeliang Tanglink_failure_tests()
14611002b89fSGeliang Tang{
14628b819a84SFlorian Westphal	# accept and use add_addr with additional subflows and link loss
14638b819a84SFlorian Westphal	reset
14647d1e6f16SPaolo Abeni
14657d1e6f16SPaolo Abeni	# without any b/w limit each veth could spool the packets and get
14667d1e6f16SPaolo Abeni	# them acked at xmit time, so that the corresponding subflow will
14677d1e6f16SPaolo Abeni	# have almost always no outstanding pkts, the scheduler will pick
14687d1e6f16SPaolo Abeni	# always the first subflow and we will have hard time testing
14697d1e6f16SPaolo Abeni	# active backup and link switch-over.
14707d1e6f16SPaolo Abeni	# Let's set some arbitrary (low) virtual link limits.
14717d1e6f16SPaolo Abeni	init_shapers
147234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 3
147334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
147434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
147534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow
147634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 dev ns2eth4 flags subflow
14778b819a84SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1 1
14788b819a84SFlorian Westphal	chk_join_nr "multiple flows, signal, link failure" 3 3 3
14798b819a84SFlorian Westphal	chk_add_nr 1 1
14807d1e6f16SPaolo Abeni	chk_stale_nr $ns2 1 5 1
14817d1e6f16SPaolo Abeni
14827d1e6f16SPaolo Abeni	# accept and use add_addr with additional subflows and link loss
14837d1e6f16SPaolo Abeni	# for bidirectional transfer
14847d1e6f16SPaolo Abeni	reset
14857d1e6f16SPaolo Abeni	init_shapers
148634aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 3
148734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
148834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
148934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow
149034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 dev ns2eth4 flags subflow
14917d1e6f16SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 2
14927d1e6f16SPaolo Abeni	chk_join_nr "multi flows, signal, bidi, link fail" 3 3 3
14937d1e6f16SPaolo Abeni	chk_add_nr 1 1
14947d1e6f16SPaolo Abeni	chk_stale_nr $ns2 1 -1 1
14957d1e6f16SPaolo Abeni
14967d1e6f16SPaolo Abeni	# 2 subflows plus 1 backup subflow with a lossy link, backup
14977d1e6f16SPaolo Abeni	# will never be used
14987d1e6f16SPaolo Abeni	reset
14997d1e6f16SPaolo Abeni	init_shapers
150034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
150134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
150234aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
15037d1e6f16SPaolo Abeni	export FAILING_LINKS="1"
150434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow,backup
15057d1e6f16SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 1
15067d1e6f16SPaolo Abeni	chk_join_nr "backup subflow unused, link failure" 2 2 2
15077d1e6f16SPaolo Abeni	chk_add_nr 1 1
15087d1e6f16SPaolo Abeni	chk_link_usage $ns2 ns2eth3 $cinsent 0
15097d1e6f16SPaolo Abeni
15107d1e6f16SPaolo Abeni	# 2 lossy links after half transfer, backup will get half of
15117d1e6f16SPaolo Abeni	# the traffic
15127d1e6f16SPaolo Abeni	reset
15137d1e6f16SPaolo Abeni	init_shapers
151434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
151534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
151634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
151734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow,backup
15187d1e6f16SPaolo Abeni	export FAILING_LINKS="1 2"
15197d1e6f16SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 1
15207d1e6f16SPaolo Abeni	chk_join_nr "backup flow used, multi links fail" 2 2 2
15217d1e6f16SPaolo Abeni	chk_add_nr 1 1
15227d1e6f16SPaolo Abeni	chk_stale_nr $ns2 2 4 2
15237d1e6f16SPaolo Abeni	chk_link_usage $ns2 ns2eth3 $cinsent 50
15247d1e6f16SPaolo Abeni
15257d1e6f16SPaolo Abeni	# use a backup subflow with the first subflow on a lossy link
15267d1e6f16SPaolo Abeni	# for bidirectional transfer
15277d1e6f16SPaolo Abeni	reset
15287d1e6f16SPaolo Abeni	init_shapers
152934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
153034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 dev ns1eth2 flags signal
153134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
153234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 dev ns2eth3 flags subflow,backup
15337d1e6f16SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 2
15347d1e6f16SPaolo Abeni	chk_join_nr "backup flow used, bidi, link failure" 2 2 2
15357d1e6f16SPaolo Abeni	chk_add_nr 1 1
15367d1e6f16SPaolo Abeni	chk_stale_nr $ns2 1 -1 2
15377d1e6f16SPaolo Abeni	chk_link_usage $ns2 ns2eth3 $cinsent 50
15381002b89fSGeliang Tang}
15398b819a84SFlorian Westphal
15401002b89fSGeliang Tangadd_addr_timeout_tests()
15411002b89fSGeliang Tang{
15428d014eaaSGeliang Tang	# add_addr timeout
15438d014eaaSGeliang Tang	reset_with_add_addr_timeout
154434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
154534aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
154634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
15478b819a84SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow
15488d014eaaSGeliang Tang	chk_join_nr "signal address, ADD_ADDR timeout" 1 1 1
15498d014eaaSGeliang Tang	chk_add_nr 4 0
15508d014eaaSGeliang Tang
15511002b89fSGeliang Tang	# add_addr timeout IPv6
15521002b89fSGeliang Tang	reset_with_add_addr_timeout 6
155334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
155434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
155534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
15561002b89fSGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
15571002b89fSGeliang Tang	chk_join_nr "signal address, ADD_ADDR6 timeout" 1 1 1
15581002b89fSGeliang Tang	chk_add_nr 4 0
15598da6229bSGeliang Tang
15608da6229bSGeliang Tang	# signal addresses timeout
15618da6229bSGeliang Tang	reset_with_add_addr_timeout
156234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 2
156334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
156434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
156534aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 2 2
1566cbfafac4SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 0 speed_10
15678da6229bSGeliang Tang	chk_join_nr "signal addresses, ADD_ADDR timeout" 2 2 2
15688da6229bSGeliang Tang	chk_add_nr 8 0
15698da6229bSGeliang Tang
15708da6229bSGeliang Tang	# signal invalid addresses timeout
15718da6229bSGeliang Tang	reset_with_add_addr_timeout
157234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 2
157334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
157434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
157534aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 2 2
1576cbfafac4SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 0 speed_10
15778da6229bSGeliang Tang	chk_join_nr "invalid address, ADD_ADDR timeout" 1 1 1
15788da6229bSGeliang Tang	chk_add_nr 8 0
15791002b89fSGeliang Tang}
15801002b89fSGeliang Tang
15811002b89fSGeliang Tangremove_tests()
15821002b89fSGeliang Tang{
1583dd72b0feSGeliang Tang	# single subflow, remove
1584dd72b0feSGeliang Tang	reset
158534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
158634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
158734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
15882e8cbf45SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 -1 slow
1589dd72b0feSGeliang Tang	chk_join_nr "remove single subflow" 1 1 1
1590dd72b0feSGeliang Tang	chk_rm_nr 1 1
1591dd72b0feSGeliang Tang
1592dd72b0feSGeliang Tang	# multiple subflows, remove
1593dd72b0feSGeliang Tang	reset
159434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
159534aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
159634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
159734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
15982e8cbf45SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 -2 slow
1599dd72b0feSGeliang Tang	chk_join_nr "remove multiple subflows" 2 2 2
1600dd72b0feSGeliang Tang	chk_rm_nr 2 2
1601dd72b0feSGeliang Tang
1602dd72b0feSGeliang Tang	# single address, remove
1603dd72b0feSGeliang Tang	reset
160434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
160534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
160634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
16072e8cbf45SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -1 0 slow
1608dd72b0feSGeliang Tang	chk_join_nr "remove single address" 1 1 1
1609dd72b0feSGeliang Tang	chk_add_nr 1 1
16107028ba8aSGeliang Tang	chk_rm_nr 1 1 invert
1611dd72b0feSGeliang Tang
1612dd72b0feSGeliang Tang	# subflow and signal, remove
1613dd72b0feSGeliang Tang	reset
161434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
161534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
161634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
161734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
16182e8cbf45SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -1 -1 slow
1619dd72b0feSGeliang Tang	chk_join_nr "remove subflow and signal" 2 2 2
1620dd72b0feSGeliang Tang	chk_add_nr 1 1
1621dd72b0feSGeliang Tang	chk_rm_nr 1 1
1622dd72b0feSGeliang Tang
1623dd72b0feSGeliang Tang	# subflows and signal, remove
1624dd72b0feSGeliang Tang	reset
162534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 3
162634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
162734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
162834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
162934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
16302e8cbf45SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -1 -2 slow
1631dd72b0feSGeliang Tang	chk_join_nr "remove subflows and signal" 3 3 3
1632dd72b0feSGeliang Tang	chk_add_nr 1 1
1633dd72b0feSGeliang Tang	chk_rm_nr 2 2
1634dd72b0feSGeliang Tang
1635ef360019SGeliang Tang	# addresses remove
1636ef360019SGeliang Tang	reset
163734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 3 3
163834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal id 250
163934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
164034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
164134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 3 3
1642ef360019SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -3 0 slow
1643ef360019SGeliang Tang	chk_join_nr "remove addresses" 3 3 3
1644ef360019SGeliang Tang	chk_add_nr 3 3
1645ef360019SGeliang Tang	chk_rm_nr 3 3 invert
1646ef360019SGeliang Tang
1647ef360019SGeliang Tang	# invalid addresses remove
1648ef360019SGeliang Tang	reset
164934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 3 3
165034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
165134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
165234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.14.1 flags signal
165334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 3 3
1654ef360019SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -3 0 slow
1655ef360019SGeliang Tang	chk_join_nr "remove invalid addresses" 1 1 1
1656ef360019SGeliang Tang	chk_add_nr 3 3
1657ef360019SGeliang Tang	chk_rm_nr 3 1 invert
1658ef360019SGeliang Tang
16596fe4ccdcSGeliang Tang	# subflows and signal, flush
16606fe4ccdcSGeliang Tang	reset
166134aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 3
166234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
166334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
166434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
166534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
16662e8cbf45SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -8 -8 slow
16676fe4ccdcSGeliang Tang	chk_join_nr "flush subflows and signal" 3 3 3
16686fe4ccdcSGeliang Tang	chk_add_nr 1 1
16696fe4ccdcSGeliang Tang	chk_rm_nr 2 2
1670d2c4333aSGeliang Tang
1671d2c4333aSGeliang Tang	# subflows flush
1672d2c4333aSGeliang Tang	reset
167334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 3 3
167434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 3 3
167534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow id 150
167634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
167734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1678d2c4333aSGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -8 -8 slow
1679d2c4333aSGeliang Tang	chk_join_nr "flush subflows" 3 3 3
1680d2c4333aSGeliang Tang	chk_rm_nr 3 3
1681d2c4333aSGeliang Tang
1682d2c4333aSGeliang Tang	# addresses flush
1683d2c4333aSGeliang Tang	reset
168434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 3 3
168534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal id 250
168634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
168734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.4.1 flags signal
168834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 3 3
1689d2c4333aSGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -8 -8 slow
1690d2c4333aSGeliang Tang	chk_join_nr "flush addresses" 3 3 3
1691d2c4333aSGeliang Tang	chk_add_nr 3 3
1692d2c4333aSGeliang Tang	chk_rm_nr 3 3 invert
1693ef360019SGeliang Tang
1694ef360019SGeliang Tang	# invalid addresses flush
1695ef360019SGeliang Tang	reset
169634aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 3 3
169734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.12.1 flags signal
169834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal
169934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.14.1 flags signal
170034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 3 3
1701ef360019SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -8 0 slow
1702ef360019SGeliang Tang	chk_join_nr "flush invalid addresses" 1 1 1
1703ef360019SGeliang Tang	chk_add_nr 3 3
1704ef360019SGeliang Tang	chk_rm_nr 3 1 invert
17055e287fe7SGeliang Tang
17065e287fe7SGeliang Tang	# remove id 0 subflow
17075e287fe7SGeliang Tang	reset
170834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
170934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
171034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
17115e287fe7SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 -9 slow
17125e287fe7SGeliang Tang	chk_join_nr "remove id 0 subflow" 1 1 1
17135e287fe7SGeliang Tang	chk_rm_nr 1 1
17145e287fe7SGeliang Tang
17155e287fe7SGeliang Tang	# remove id 0 address
17165e287fe7SGeliang Tang	reset
171734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
171834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
171934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
17205e287fe7SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -9 0 slow
17215e287fe7SGeliang Tang	chk_join_nr "remove id 0 address" 1 1 1
17225e287fe7SGeliang Tang	chk_add_nr 1 1
17235e287fe7SGeliang Tang	chk_rm_nr 1 1 invert
17241002b89fSGeliang Tang}
17256fe4ccdcSGeliang Tang
17261002b89fSGeliang Tangadd_tests()
17271002b89fSGeliang Tang{
17286208fd82SGeliang Tang	# add single subflow
17296208fd82SGeliang Tang	reset
173034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
173134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
17326208fd82SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 1 slow
17336208fd82SGeliang Tang	chk_join_nr "add single subflow" 1 1 1
17346208fd82SGeliang Tang
17356208fd82SGeliang Tang	# add signal address
17366208fd82SGeliang Tang	reset
173734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
173834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
17396208fd82SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 1 0 slow
17406208fd82SGeliang Tang	chk_join_nr "add signal address" 1 1 1
17416208fd82SGeliang Tang	chk_add_nr 1 1
17426208fd82SGeliang Tang
17436208fd82SGeliang Tang	# add multiple subflows
17446208fd82SGeliang Tang	reset
174534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
174634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
17476208fd82SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 2 slow
17486208fd82SGeliang Tang	chk_join_nr "add multiple subflows" 2 2 2
17496208fd82SGeliang Tang
17506208fd82SGeliang Tang	# add multiple subflows IPv6
17516208fd82SGeliang Tang	reset
175234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
175334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
17546208fd82SGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 0 2 slow
17556208fd82SGeliang Tang	chk_join_nr "add multiple subflows IPv6" 2 2 2
17566208fd82SGeliang Tang
17576208fd82SGeliang Tang	# add multiple addresses IPv6
17586208fd82SGeliang Tang	reset
175934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
176034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 2 2
17616208fd82SGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 2 0 slow
17626208fd82SGeliang Tang	chk_join_nr "add multiple addresses IPv6" 2 2 2
17636208fd82SGeliang Tang	chk_add_nr 2 2
17641002b89fSGeliang Tang}
17656208fd82SGeliang Tang
17661002b89fSGeliang Tangipv6_tests()
17671002b89fSGeliang Tang{
1768523514edSGeliang Tang	# subflow IPv6
1769523514edSGeliang Tang	reset
177034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
177134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
177234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 dead:beef:3::2 dev ns2eth3 flags subflow
1773523514edSGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
1774523514edSGeliang Tang	chk_join_nr "single subflow IPv6" 1 1 1
1775523514edSGeliang Tang
1776523514edSGeliang Tang	# add_address, unused IPv6
1777523514edSGeliang Tang	reset
177834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
1779523514edSGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
1780523514edSGeliang Tang	chk_join_nr "unused signal address IPv6" 0 0 0
1781523514edSGeliang Tang	chk_add_nr 1 1
1782523514edSGeliang Tang
1783523514edSGeliang Tang	# signal address IPv6
1784523514edSGeliang Tang	reset
178534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
178634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
178734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
1788523514edSGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 0 0 slow
1789523514edSGeliang Tang	chk_join_nr "single address IPv6" 1 1 1
1790523514edSGeliang Tang	chk_add_nr 1 1
1791523514edSGeliang Tang
1792523514edSGeliang Tang	# single address IPv6, remove
1793523514edSGeliang Tang	reset
179434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
179534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
179634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
17972e8cbf45SGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 -1 0 slow
1798523514edSGeliang Tang	chk_join_nr "remove single address IPv6" 1 1 1
1799523514edSGeliang Tang	chk_add_nr 1 1
18007028ba8aSGeliang Tang	chk_rm_nr 1 1 invert
1801523514edSGeliang Tang
1802523514edSGeliang Tang	# subflow and signal IPv6, remove
1803523514edSGeliang Tang	reset
180434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
180534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 dead:beef:2::1 flags signal
180634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
180734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 dead:beef:3::2 dev ns2eth3 flags subflow
18082e8cbf45SGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1 0 -1 -1 slow
1809523514edSGeliang Tang	chk_join_nr "remove subflow and signal IPv6" 2 2 2
1810523514edSGeliang Tang	chk_add_nr 1 1
1811523514edSGeliang Tang	chk_rm_nr 1 1
18121002b89fSGeliang Tang}
1813523514edSGeliang Tang
18141002b89fSGeliang Tangv4mapped_tests()
18151002b89fSGeliang Tang{
1816a6094788SGeliang Tang	# subflow IPv4-mapped to IPv4-mapped
1817a6094788SGeliang Tang	reset
181834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
181934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
182034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 "::ffff:10.0.3.2" flags subflow
1821a6094788SGeliang Tang	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1822a6094788SGeliang Tang	chk_join_nr "single subflow IPv4-mapped" 1 1 1
1823a6094788SGeliang Tang
1824a6094788SGeliang Tang	# signal address IPv4-mapped with IPv4-mapped sk
1825a6094788SGeliang Tang	reset
182634aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
182734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
182834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 "::ffff:10.0.2.1" flags signal
1829a6094788SGeliang Tang	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1830a6094788SGeliang Tang	chk_join_nr "signal address IPv4-mapped" 1 1 1
1831a6094788SGeliang Tang	chk_add_nr 1 1
1832a6094788SGeliang Tang
1833a6094788SGeliang Tang	# subflow v4-map-v6
1834a6094788SGeliang Tang	reset
183534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
183634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
183734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1838a6094788SGeliang Tang	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1839a6094788SGeliang Tang	chk_join_nr "single subflow v4-map-v6" 1 1 1
1840a6094788SGeliang Tang
1841a6094788SGeliang Tang	# signal address v4-map-v6
1842a6094788SGeliang Tang	reset
184334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
184434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
184534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
1846a6094788SGeliang Tang	run_tests $ns1 $ns2 "::ffff:10.0.1.1"
1847a6094788SGeliang Tang	chk_join_nr "signal address v4-map-v6" 1 1 1
1848a6094788SGeliang Tang	chk_add_nr 1 1
1849a6094788SGeliang Tang
1850a6094788SGeliang Tang	# subflow v6-map-v4
1851a6094788SGeliang Tang	reset
185234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
185334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
185434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 "::ffff:10.0.3.2" flags subflow
1855a6094788SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
1856a6094788SGeliang Tang	chk_join_nr "single subflow v6-map-v4" 1 1 1
1857a6094788SGeliang Tang
1858a6094788SGeliang Tang	# signal address v6-map-v4
1859a6094788SGeliang Tang	reset
186034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
186134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
186234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 "::ffff:10.0.2.1" flags signal
1863a6094788SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
1864a6094788SGeliang Tang	chk_join_nr "signal address v6-map-v4" 1 1 1
1865a6094788SGeliang Tang	chk_add_nr 1 1
1866a6094788SGeliang Tang
1867a6094788SGeliang Tang	# no subflow IPv6 to v4 address
1868a6094788SGeliang Tang	reset
186934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
187034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
187134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 dead:beef:2::2 flags subflow
1872a6094788SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
1873a6094788SGeliang Tang	chk_join_nr "no JOIN with diff families v4-v6" 0 0 0
1874a6094788SGeliang Tang
1875a6094788SGeliang Tang	# no subflow IPv6 to v4 address even if v6 has a valid v4 at the end
1876a6094788SGeliang Tang	reset
187734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
187834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
187934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 dead:beef:2::10.0.3.2 flags subflow
1880a6094788SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
1881a6094788SGeliang Tang	chk_join_nr "no JOIN with diff families v4-v6-2" 0 0 0
1882a6094788SGeliang Tang
1883a6094788SGeliang Tang	# no subflow IPv4 to v6 address, no need to slow down too then
1884a6094788SGeliang Tang	reset
188534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
188634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
188734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
1888a6094788SGeliang Tang	run_tests $ns1 $ns2 dead:beef:1::1
1889a6094788SGeliang Tang	chk_join_nr "no JOIN with diff families v6-v4" 0 0 0
18901002b89fSGeliang Tang}
1891a6094788SGeliang Tang
18921002b89fSGeliang Tangbackup_tests()
18931002b89fSGeliang Tang{
1894718eb44eSGeliang Tang	# single subflow, backup
1895718eb44eSGeliang Tang	reset
189634aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
189734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
189834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow,backup
1899718eb44eSGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow nobackup
1900718eb44eSGeliang Tang	chk_join_nr "single subflow, backup" 1 1 1
1901718eb44eSGeliang Tang	chk_prio_nr 0 1
1902718eb44eSGeliang Tang
1903718eb44eSGeliang Tang	# single address, backup
1904718eb44eSGeliang Tang	reset
190534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
190634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
190734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
1908718eb44eSGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow backup
1909718eb44eSGeliang Tang	chk_join_nr "single address, backup" 1 1 1
1910718eb44eSGeliang Tang	chk_add_nr 1 1
1911718eb44eSGeliang Tang	chk_prio_nr 1 0
191233397b83SGeliang Tang
191333397b83SGeliang Tang	# single address with port, backup
191433397b83SGeliang Tang	reset
191534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
191634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
191734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
191833397b83SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow backup
191933397b83SGeliang Tang	chk_join_nr "single address with port, backup" 1 1 1
192033397b83SGeliang Tang	chk_add_nr 1 1
192133397b83SGeliang Tang	chk_prio_nr 1 0
19221002b89fSGeliang Tang}
1923718eb44eSGeliang Tang
19241002b89fSGeliang Tangadd_addr_ports_tests()
19251002b89fSGeliang Tang{
19268a127bf6SGeliang Tang	# signal address with port
19278a127bf6SGeliang Tang	reset
192834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
192934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
193034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
19318a127bf6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
19328a127bf6SGeliang Tang	chk_join_nr "signal address with port" 1 1 1
19338a127bf6SGeliang Tang	chk_add_nr 1 1 1
19348a127bf6SGeliang Tang
19358a127bf6SGeliang Tang	# subflow and signal with port
19368a127bf6SGeliang Tang	reset
193734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
193834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
193934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
194034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
19418a127bf6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
19428a127bf6SGeliang Tang	chk_join_nr "subflow and signal with port" 2 2 2
19438a127bf6SGeliang Tang	chk_add_nr 1 1 1
19448a127bf6SGeliang Tang
19458a127bf6SGeliang Tang	# single address with port, remove
19468a127bf6SGeliang Tang	reset
194734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
194834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
194934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
19508a127bf6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -1 0 slow
19518a127bf6SGeliang Tang	chk_join_nr "remove single address with port" 1 1 1
19528a127bf6SGeliang Tang	chk_add_nr 1 1 1
19537028ba8aSGeliang Tang	chk_rm_nr 1 1 invert
19548a127bf6SGeliang Tang
19558a127bf6SGeliang Tang	# subflow and signal with port, remove
19568a127bf6SGeliang Tang	reset
195734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
195834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
195934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
196034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
19618a127bf6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 -1 -1 slow
19628a127bf6SGeliang Tang	chk_join_nr "remove subflow and signal with port" 2 2 2
19638a127bf6SGeliang Tang	chk_add_nr 1 1 1
19648a127bf6SGeliang Tang	chk_rm_nr 1 1
19658a127bf6SGeliang Tang
19668a127bf6SGeliang Tang	# subflows and signal with port, flush
19678a127bf6SGeliang Tang	reset
196834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 3
196934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
197034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
197134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
197234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
1973327b9a94SPaolo Abeni	run_tests $ns1 $ns2 10.0.1.1 0 -8 -2 slow
19748a127bf6SGeliang Tang	chk_join_nr "flush subflows and signal with port" 3 3 3
19758a127bf6SGeliang Tang	chk_add_nr 1 1
19768a127bf6SGeliang Tang	chk_rm_nr 2 2
19778a127bf6SGeliang Tang
19788a127bf6SGeliang Tang	# multiple addresses with port
19798a127bf6SGeliang Tang	reset
198034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 2
198134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
198234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal port 10100
198334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 2 2
19848a127bf6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
19858a127bf6SGeliang Tang	chk_join_nr "multiple addresses with port" 2 2 2
19868a127bf6SGeliang Tang	chk_add_nr 2 2 2
19878a127bf6SGeliang Tang
19888a127bf6SGeliang Tang	# multiple addresses with ports
19898a127bf6SGeliang Tang	reset
199034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 2
199134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal port 10100
199234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.3.1 flags signal port 10101
199334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 2 2
19948a127bf6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
19958a127bf6SGeliang Tang	chk_join_nr "multiple addresses with ports" 2 2 2
19968a127bf6SGeliang Tang	chk_add_nr 2 2 2
19971002b89fSGeliang Tang}
19988a127bf6SGeliang Tang
19991002b89fSGeliang Tangsyncookies_tests()
20001002b89fSGeliang Tang{
200100587187SFlorian Westphal	# single subflow, syncookies
200200587187SFlorian Westphal	reset_with_cookies
200334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
200434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
200534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
200600587187SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1
200700587187SFlorian Westphal	chk_join_nr "single subflow with syn cookies" 1 1 1
200800587187SFlorian Westphal
200900587187SFlorian Westphal	# multiple subflows with syn cookies
201000587187SFlorian Westphal	reset_with_cookies
201134aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
201234aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
201334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
201434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
201500587187SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1
201600587187SFlorian Westphal	chk_join_nr "multiple subflows with syn cookies" 2 2 2
201700587187SFlorian Westphal
201800587187SFlorian Westphal	# multiple subflows limited by server
201900587187SFlorian Westphal	reset_with_cookies
202034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
202134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 2
202234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
202334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow
202400587187SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1
2025a7da4416SJianguo Wu	chk_join_nr "subflows limited by server w cookies" 2 1 1
202600587187SFlorian Westphal
202700587187SFlorian Westphal	# test signal address with cookies
202800587187SFlorian Westphal	reset_with_cookies
202934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
203034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
203134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
203200587187SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1
203300587187SFlorian Westphal	chk_join_nr "signal address with syn cookies" 1 1 1
2034be613160SGeliang Tang	chk_add_nr 1 1
203500587187SFlorian Westphal
203600587187SFlorian Westphal	# test cookie with subflow and signal
203700587187SFlorian Westphal	reset_with_cookies
203834aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
203934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 2
204034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 2
204134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
204200587187SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1
204300587187SFlorian Westphal	chk_join_nr "subflow and signal w cookies" 2 2 2
2044be613160SGeliang Tang	chk_add_nr 1 1
204500587187SFlorian Westphal
204600587187SFlorian Westphal	# accept and use add_addr with additional subflows
204700587187SFlorian Westphal	reset_with_cookies
204834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 3
204934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
205034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
205134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
205234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.4.2 flags subflow
205300587187SFlorian Westphal	run_tests $ns1 $ns2 10.0.1.1
205400587187SFlorian Westphal	chk_join_nr "subflows and signal w. cookies" 3 3 3
2055be613160SGeliang Tang	chk_add_nr 1 1
20561002b89fSGeliang Tang}
20571002b89fSGeliang Tang
2058af66d3e1SGeliang Tangchecksum_tests()
2059af66d3e1SGeliang Tang{
2060af66d3e1SGeliang Tang	# checksum test 0 0
2061af66d3e1SGeliang Tang	reset_with_checksum 0 0
206234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
206334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
2064af66d3e1SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
2065af66d3e1SGeliang Tang	chk_csum_nr "checksum test 0 0"
2066af66d3e1SGeliang Tang
2067af66d3e1SGeliang Tang	# checksum test 1 1
2068af66d3e1SGeliang Tang	reset_with_checksum 1 1
206934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
207034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
2071af66d3e1SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
2072af66d3e1SGeliang Tang	chk_csum_nr "checksum test 1 1"
2073af66d3e1SGeliang Tang
2074af66d3e1SGeliang Tang	# checksum test 0 1
2075af66d3e1SGeliang Tang	reset_with_checksum 0 1
207634aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
207734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
2078af66d3e1SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
2079af66d3e1SGeliang Tang	chk_csum_nr "checksum test 0 1"
2080af66d3e1SGeliang Tang
2081af66d3e1SGeliang Tang	# checksum test 1 0
2082af66d3e1SGeliang Tang	reset_with_checksum 1 0
208334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 1
208434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 0 1
2085af66d3e1SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
2086af66d3e1SGeliang Tang	chk_csum_nr "checksum test 1 0"
2087af66d3e1SGeliang Tang}
2088af66d3e1SGeliang Tang
20890cddb4a6SGeliang Tangdeny_join_id0_tests()
20900cddb4a6SGeliang Tang{
20910cddb4a6SGeliang Tang	# subflow allow join id0 ns1
20920cddb4a6SGeliang Tang	reset_with_allow_join_id0 1 0
209334aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 1 1
209434aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
209534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
20960cddb4a6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
20970cddb4a6SGeliang Tang	chk_join_nr "single subflow allow join id0 ns1" 1 1 1
20980cddb4a6SGeliang Tang
20990cddb4a6SGeliang Tang	# subflow allow join id0 ns2
21000cddb4a6SGeliang Tang	reset_with_allow_join_id0 0 1
210134aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 1 1
210234aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
210334aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
21040cddb4a6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
21050cddb4a6SGeliang Tang	chk_join_nr "single subflow allow join id0 ns2" 0 0 0
21060cddb4a6SGeliang Tang
21070cddb4a6SGeliang Tang	# signal address allow join id0 ns1
21080cddb4a6SGeliang Tang	# ADD_ADDRs are not affected by allow_join_id0 value.
21090cddb4a6SGeliang Tang	reset_with_allow_join_id0 1 0
211034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 1 1
211134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
211234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
21130cddb4a6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
21140cddb4a6SGeliang Tang	chk_join_nr "signal address allow join id0 ns1" 1 1 1
21150cddb4a6SGeliang Tang	chk_add_nr 1 1
21160cddb4a6SGeliang Tang
21170cddb4a6SGeliang Tang	# signal address allow join id0 ns2
21180cddb4a6SGeliang Tang	# ADD_ADDRs are not affected by allow_join_id0 value.
21190cddb4a6SGeliang Tang	reset_with_allow_join_id0 0 1
212034aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 1 1
212134aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 1
212234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
21230cddb4a6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
21240cddb4a6SGeliang Tang	chk_join_nr "signal address allow join id0 ns2" 1 1 1
21250cddb4a6SGeliang Tang	chk_add_nr 1 1
21260cddb4a6SGeliang Tang
21270cddb4a6SGeliang Tang	# subflow and address allow join id0 ns1
21280cddb4a6SGeliang Tang	reset_with_allow_join_id0 1 0
212934aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 2
213034aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 2 2
213134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
213234aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
21330cddb4a6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
21340cddb4a6SGeliang Tang	chk_join_nr "subflow and address allow join id0 1" 2 2 2
21350cddb4a6SGeliang Tang
21360cddb4a6SGeliang Tang	# subflow and address allow join id0 ns2
21370cddb4a6SGeliang Tang	reset_with_allow_join_id0 0 1
213834aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 2
213934aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 2 2
214034aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
214134aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow
21420cddb4a6SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1
21430cddb4a6SGeliang Tang	chk_join_nr "subflow and address allow join id0 2" 1 1 1
21440cddb4a6SGeliang Tang}
21450cddb4a6SGeliang Tang
21464f49d633SGeliang Tangfullmesh_tests()
21474f49d633SGeliang Tang{
21484f49d633SGeliang Tang	# fullmesh 1
21494f49d633SGeliang Tang	# 2 fullmesh addrs in ns2, added before the connection,
21504f49d633SGeliang Tang	# 1 non-fullmesh addr in ns1, added during the connection.
21514f49d633SGeliang Tang	reset
215234aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 0 4
215334aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 4
215434aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow,fullmesh
215534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.3.2 flags subflow,fullmesh
21564f49d633SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 1 0 slow
21574f49d633SGeliang Tang	chk_join_nr "fullmesh test 2x1" 4 4 4
21584f49d633SGeliang Tang	chk_add_nr 1 1
21594f49d633SGeliang Tang
21604f49d633SGeliang Tang	# fullmesh 2
21614f49d633SGeliang Tang	# 1 non-fullmesh addr in ns1, added before the connection,
21624f49d633SGeliang Tang	# 1 fullmesh addr in ns2, added during the connection.
21634f49d633SGeliang Tang	reset
216434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 1 3
216534aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 3
216634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
21674f49d633SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_1 slow
21684f49d633SGeliang Tang	chk_join_nr "fullmesh test 1x1" 3 3 3
21694f49d633SGeliang Tang	chk_add_nr 1 1
21704f49d633SGeliang Tang
21714f49d633SGeliang Tang	# fullmesh 3
21724f49d633SGeliang Tang	# 1 non-fullmesh addr in ns1, added before the connection,
21734f49d633SGeliang Tang	# 2 fullmesh addrs in ns2, added during the connection.
21744f49d633SGeliang Tang	reset
217534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 5
217634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 5
217734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
21784f49d633SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_2 slow
21794f49d633SGeliang Tang	chk_join_nr "fullmesh test 1x2" 5 5 5
21804f49d633SGeliang Tang	chk_add_nr 1 1
21814f49d633SGeliang Tang
21824f49d633SGeliang Tang	# fullmesh 4
21834f49d633SGeliang Tang	# 1 non-fullmesh addr in ns1, added before the connection,
21844f49d633SGeliang Tang	# 2 fullmesh addrs in ns2, added during the connection,
21854f49d633SGeliang Tang	# limit max_subflows to 4.
21864f49d633SGeliang Tang	reset
218734aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 2 4
218834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 1 4
218934aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags signal
21904f49d633SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_2 slow
21914f49d633SGeliang Tang	chk_join_nr "fullmesh test 1x2, limited" 4 4 4
21924f49d633SGeliang Tang	chk_add_nr 1 1
21936a0653b9SGeliang Tang
21946a0653b9SGeliang Tang	# set fullmesh flag
21956a0653b9SGeliang Tang	reset
219634aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 4 4
219734aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags subflow
219834aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 4 4
21996a0653b9SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 1 slow fullmesh
22006a0653b9SGeliang Tang	chk_join_nr "set fullmesh flag test" 2 2 2
22016a0653b9SGeliang Tang	chk_rm_nr 0 1
22026a0653b9SGeliang Tang
22036a0653b9SGeliang Tang	# set nofullmesh flag
22046a0653b9SGeliang Tang	reset
220534aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 4 4
220634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags subflow,fullmesh
220734aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 4 4
22086a0653b9SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 fullmesh_1 slow nofullmesh
22096a0653b9SGeliang Tang	chk_join_nr "set nofullmesh flag test" 2 2 2
22106a0653b9SGeliang Tang	chk_rm_nr 0 1
22116a0653b9SGeliang Tang
22126a0653b9SGeliang Tang	# set backup,fullmesh flags
22136a0653b9SGeliang Tang	reset
221434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 4 4
221534aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns1 10.0.2.1 flags subflow
221634aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 4 4
22176a0653b9SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 1 slow backup,fullmesh
22186a0653b9SGeliang Tang	chk_join_nr "set backup,fullmesh flags test" 2 2 2
22196a0653b9SGeliang Tang	chk_prio_nr 0 1
22206a0653b9SGeliang Tang	chk_rm_nr 0 1
22216a0653b9SGeliang Tang
22226a0653b9SGeliang Tang	# set nobackup,nofullmesh flags
22236a0653b9SGeliang Tang	reset
222434aa6e3bSGeliang Tang	pm_nl_set_limits $ns1 4 4
222534aa6e3bSGeliang Tang	pm_nl_set_limits $ns2 4 4
222634aa6e3bSGeliang Tang	pm_nl_add_endpoint $ns2 10.0.2.2 flags subflow,backup,fullmesh
22276a0653b9SGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 0 0 0 slow nobackup,nofullmesh
22286a0653b9SGeliang Tang	chk_join_nr "set nobackup,nofullmesh flags test" 2 2 2
22296a0653b9SGeliang Tang	chk_prio_nr 0 1
22306a0653b9SGeliang Tang	chk_rm_nr 0 1
22314f49d633SGeliang Tang}
22324f49d633SGeliang Tang
223301542c9bSGeliang Tangfastclose_tests()
223401542c9bSGeliang Tang{
223501542c9bSGeliang Tang	reset
223601542c9bSGeliang Tang	run_tests $ns1 $ns2 10.0.1.1 1024 0 fastclose_2
223701542c9bSGeliang Tang	chk_join_nr "fastclose test" 0 0 0
223801542c9bSGeliang Tang	chk_fclose_nr 1 1
223901542c9bSGeliang Tang	chk_rst_nr 1 1 invert
224001542c9bSGeliang Tang}
224101542c9bSGeliang Tang
22421002b89fSGeliang Tangall_tests()
22431002b89fSGeliang Tang{
22441002b89fSGeliang Tang	subflows_tests
224546e967d1SPaolo Abeni	subflows_error_tests
22461002b89fSGeliang Tang	signal_address_tests
22471002b89fSGeliang Tang	link_failure_tests
22481002b89fSGeliang Tang	add_addr_timeout_tests
22491002b89fSGeliang Tang	remove_tests
22501002b89fSGeliang Tang	add_tests
22511002b89fSGeliang Tang	ipv6_tests
22521002b89fSGeliang Tang	v4mapped_tests
22531002b89fSGeliang Tang	backup_tests
22541002b89fSGeliang Tang	add_addr_ports_tests
22551002b89fSGeliang Tang	syncookies_tests
2256af66d3e1SGeliang Tang	checksum_tests
22570cddb4a6SGeliang Tang	deny_join_id0_tests
22584f49d633SGeliang Tang	fullmesh_tests
225901542c9bSGeliang Tang	fastclose_tests
22601002b89fSGeliang Tang}
22611002b89fSGeliang Tang
226222514d52SMatthieu Baerts# [$1: error message]
22631002b89fSGeliang Tangusage()
22641002b89fSGeliang Tang{
226522514d52SMatthieu Baerts	if [ -n "${1}" ]; then
226622514d52SMatthieu Baerts		echo "${1}"
226722514d52SMatthieu Baerts		ret=1
226822514d52SMatthieu Baerts	fi
226922514d52SMatthieu Baerts
22701002b89fSGeliang Tang	echo "mptcp_join usage:"
22711002b89fSGeliang Tang	echo "  -f subflows_tests"
227246e967d1SPaolo Abeni	echo "  -e subflows_error_tests"
22731002b89fSGeliang Tang	echo "  -s signal_address_tests"
22741002b89fSGeliang Tang	echo "  -l link_failure_tests"
22751002b89fSGeliang Tang	echo "  -t add_addr_timeout_tests"
22761002b89fSGeliang Tang	echo "  -r remove_tests"
22771002b89fSGeliang Tang	echo "  -a add_tests"
22781002b89fSGeliang Tang	echo "  -6 ipv6_tests"
22791002b89fSGeliang Tang	echo "  -4 v4mapped_tests"
22801002b89fSGeliang Tang	echo "  -b backup_tests"
22811002b89fSGeliang Tang	echo "  -p add_addr_ports_tests"
2282a673321aSMat Martineau	echo "  -k syncookies_tests"
2283af66d3e1SGeliang Tang	echo "  -S checksum_tests"
22840cddb4a6SGeliang Tang	echo "  -d deny_join_id0_tests"
22854f49d633SGeliang Tang	echo "  -m fullmesh_tests"
228601542c9bSGeliang Tang	echo "  -z fastclose_tests"
2287a673321aSMat Martineau	echo "  -c capture pcap files"
2288af66d3e1SGeliang Tang	echo "  -C enable data checksum"
2289621bd393SGeliang Tang	echo "  -i use ip mptcp"
22901002b89fSGeliang Tang	echo "  -h help"
229122514d52SMatthieu Baerts
229222514d52SMatthieu Baerts	exit ${ret}
22931002b89fSGeliang Tang}
22941002b89fSGeliang Tang
2295a673321aSMat Martineau
2296*826d7bdcSMatthieu Baertstests=()
229701542c9bSGeliang Tangwhile getopts 'fesltra64bpkdmchzCSi' opt; do
22981002b89fSGeliang Tang	case $opt in
22991002b89fSGeliang Tang		f)
2300*826d7bdcSMatthieu Baerts			tests+=(subflows_tests)
23011002b89fSGeliang Tang			;;
230246e967d1SPaolo Abeni		e)
2303*826d7bdcSMatthieu Baerts			tests+=(subflows_error_tests)
230446e967d1SPaolo Abeni			;;
23051002b89fSGeliang Tang		s)
2306*826d7bdcSMatthieu Baerts			tests+=(signal_address_tests)
23071002b89fSGeliang Tang			;;
23081002b89fSGeliang Tang		l)
2309*826d7bdcSMatthieu Baerts			tests+=(link_failure_tests)
23101002b89fSGeliang Tang			;;
23111002b89fSGeliang Tang		t)
2312*826d7bdcSMatthieu Baerts			tests+=(add_addr_timeout_tests)
23131002b89fSGeliang Tang			;;
23141002b89fSGeliang Tang		r)
2315*826d7bdcSMatthieu Baerts			tests+=(remove_tests)
23161002b89fSGeliang Tang			;;
23171002b89fSGeliang Tang		a)
2318*826d7bdcSMatthieu Baerts			tests+=(add_tests)
23191002b89fSGeliang Tang			;;
23201002b89fSGeliang Tang		6)
2321*826d7bdcSMatthieu Baerts			tests+=(ipv6_tests)
23221002b89fSGeliang Tang			;;
23231002b89fSGeliang Tang		4)
2324*826d7bdcSMatthieu Baerts			tests+=(v4mapped_tests)
23251002b89fSGeliang Tang			;;
23261002b89fSGeliang Tang		b)
2327*826d7bdcSMatthieu Baerts			tests+=(backup_tests)
23281002b89fSGeliang Tang			;;
23291002b89fSGeliang Tang		p)
2330*826d7bdcSMatthieu Baerts			tests+=(add_addr_ports_tests)
23311002b89fSGeliang Tang			;;
2332a673321aSMat Martineau		k)
2333*826d7bdcSMatthieu Baerts			tests+=(syncookies_tests)
23341002b89fSGeliang Tang			;;
2335af66d3e1SGeliang Tang		S)
2336*826d7bdcSMatthieu Baerts			tests+=(checksum_tests)
2337af66d3e1SGeliang Tang			;;
23380cddb4a6SGeliang Tang		d)
2339*826d7bdcSMatthieu Baerts			tests+=(deny_join_id0_tests)
23400cddb4a6SGeliang Tang			;;
23414f49d633SGeliang Tang		m)
2342*826d7bdcSMatthieu Baerts			tests+=(fullmesh_tests)
23434f49d633SGeliang Tang			;;
234401542c9bSGeliang Tang		z)
2345*826d7bdcSMatthieu Baerts			tests+=(fastclose_tests)
234601542c9bSGeliang Tang			;;
2347a673321aSMat Martineau		c)
2348*826d7bdcSMatthieu Baerts			capture=1
2349a673321aSMat Martineau			;;
2350af66d3e1SGeliang Tang		C)
2351*826d7bdcSMatthieu Baerts			checksum=1
2352af66d3e1SGeliang Tang			;;
2353621bd393SGeliang Tang		i)
2354*826d7bdcSMatthieu Baerts			ip_mptcp=1
2355621bd393SGeliang Tang			;;
235622514d52SMatthieu Baerts		h)
23571002b89fSGeliang Tang			usage
23581002b89fSGeliang Tang			;;
235922514d52SMatthieu Baerts		*)
236022514d52SMatthieu Baerts			usage "Unknown option: -${opt}"
236122514d52SMatthieu Baerts			;;
23621002b89fSGeliang Tang	esac
23631002b89fSGeliang Tangdone
236400587187SFlorian Westphal
2365*826d7bdcSMatthieu Baertsif [ ${#tests[@]} -eq 0 ]; then
2366*826d7bdcSMatthieu Baerts	all_tests
2367*826d7bdcSMatthieu Baertselse
2368*826d7bdcSMatthieu Baerts	for subtests in "${tests[@]}"; do
2369*826d7bdcSMatthieu Baerts		"${subtests}"
2370*826d7bdcSMatthieu Baerts	done
2371*826d7bdcSMatthieu Baertsfi
2372*826d7bdcSMatthieu Baerts
2373b08fbf24SPaolo Abeniexit $ret
2374