Commit a8a388c2 authored by Florian Westphal's avatar Florian Westphal Committed by Pablo Neira Ayuso
Browse files

selftests: netfilter: add packetdrill based conntrack tests



Add a new test script that uses packetdrill tool to exercise conntrack
state machine.

Needs ip/ip6tables and conntrack tool (to check if we have an entry in
the expected state).

Test cases added here cover following scenarios:
1. already-acked (retransmitted) packets are not tagged as INVALID
2. RST packet coming when conntrack is already closing (FIN/CLOSE_WAIT)
  transitions conntrack to CLOSE even if the RST is not an exact match
3. RST packets with out-of-window sequence numbers are marked as INVALID
4. SYN+Challenge ACK: check that challenge ack is allowed to pass
5. Old SYN/ACK: check conntrack handles the case where SYN is answered
  with SYN/ACK for an old, previous connection attempt
6. Check SYN reception while in ESTABLISHED state generates a challenge
   ack, RST response clears 'outdated' state + next SYN retransmit gets
   us into 'SYN_RECV' conntrack state.

Tests get run twice, once with ipv4 and once with ipv6.

Signed-off-by: default avatarFlorian Westphal <fw@strlen.de>
Signed-off-by: default avatarPablo Neira Ayuso <pablo@netfilter.org>
parent 532aec7e
Loading
Loading
Loading
Loading
+2 −0
Original line number Diff line number Diff line
@@ -13,6 +13,7 @@ TEST_PROGS += conntrack_tcp_unreplied.sh
TEST_PROGS += conntrack_sctp_collision.sh
TEST_PROGS += conntrack_vrf.sh
TEST_PROGS += ipvs.sh
TEST_PROGS += nf_conntrack_packetdrill.sh
TEST_PROGS += nf_nat_edemux.sh
TEST_PROGS += nft_audit.sh
TEST_PROGS += nft_concat_range.sh
@@ -45,6 +46,7 @@ $(OUTPUT)/conntrack_dump_flush: CFLAGS += $(MNL_CFLAGS)
$(OUTPUT)/conntrack_dump_flush: LDLIBS += $(MNL_LDLIBS)

TEST_FILES := lib.sh
TEST_FILES += packetdrill

TEST_INCLUDES := \
	../lib.sh
+1 −0
Original line number Diff line number Diff line
@@ -86,3 +86,4 @@ CONFIG_VLAN_8021Q=m
CONFIG_XFRM_USER=m
CONFIG_XFRM_STATISTICS=y
CONFIG_NET_PKTGEN=m
CONFIG_TUN=m
+71 −0
Original line number Diff line number Diff line
#!/bin/bash
# SPDX-License-Identifier: GPL-2.0

source lib.sh

checktool "conntrack --version" "run test without conntrack"
checktool "iptables --version" "run test without iptables"
checktool "ip6tables --version" "run test without ip6tables"

modprobe -q tun
modprobe -q nf_conntrack
# echo 1 > /proc/sys/net/netfilter/nf_log_all_netns

PDRILL_TIMEOUT=10

files="
conntrack_ack_loss_stall.pkt
conntrack_inexact_rst.pkt
conntrack_syn_challenge_ack.pkt
conntrack_synack_old.pkt
conntrack_synack_reuse.pkt
conntrack_rst_invalid.pkt
"

if ! packetdrill --dry_run --verbose "packetdrill/conntrack_ack_loss_stall.pkt";then
	echo "SKIP: packetdrill not installed"
	exit ${ksft_skip}
fi

ret=0

run_packetdrill()
{
	filename="$1"
	ipver="$2"
	local mtu=1500

	export NFCT_IP_VERSION="$ipver"

	if [ "$ipver" = "ipv4" ];then
		export xtables="iptables"
	elif [ "$ipver" = "ipv6" ];then
		export xtables="ip6tables"
		mtu=1520
	fi

	timeout "$PDRILL_TIMEOUT" unshare -n packetdrill --ip_version="$ipver" --mtu=$mtu \
		--tolerance_usecs=1000000 --non_fatal packet "$filename"
}

run_one_test_file()
{
	filename="$1"

	for v in ipv4 ipv6;do
		printf "%-50s(%s)%-20s" "$filename" "$v" ""
		if run_packetdrill packetdrill/"$f" "$v";then
			echo OK
		else
			echo FAIL
			ret=1
		fi
	done
}

echo "Replaying packetdrill test cases:"
for f in $files;do
	run_one_test_file packetdrill/"$f"
done

exit $ret
+33 −0
Original line number Diff line number Diff line
#!/bin/bash
# SPDX-License-Identifier: GPL-2.0

# for debugging set net.netfilter.nf_log_all_netns=1 in init_net
# or do not use net namespaces.
modprobe -q nf_conntrack
sysctl -q net.netfilter.nf_conntrack_log_invalid=6

# Flush old cached data (fastopen cookies).
ip tcp_metrics flush all > /dev/null 2>&1

# TCP min, default, and max receive and send buffer sizes.
sysctl -q net.ipv4.tcp_rmem="4096 540000 $((15*1024*1024))"
sysctl -q net.ipv4.tcp_wmem="4096 $((256*1024)) 4194304"

# TCP congestion control.
sysctl -q net.ipv4.tcp_congestion_control=cubic

# TCP slow start after idle.
sysctl -q net.ipv4.tcp_slow_start_after_idle=0

# TCP Explicit Congestion Notification (ECN)
sysctl -q net.ipv4.tcp_ecn=0

sysctl -q net.ipv4.tcp_notsent_lowat=4294967295 > /dev/null 2>&1

# Override the default qdisc on the tun device.
# Many tests fail with timing errors if the default
# is FQ and that paces their flows.
tc qdisc add dev tun0 root pfifo

# Enable conntrack
$xtables -A INPUT -m conntrack --ctstate NEW -p tcp --syn
+118 −0
Original line number Diff line number Diff line
// check that already-acked (retransmitted) packet is let through rather
// than tagged as INVALID.

`packetdrill/common.sh`

// should set -P DROP but it disconnects VM w.o. extra netns
+0 `$xtables -A INPUT -m conntrack --ctstate INVALID -j DROP`

+0 socket(..., SOCK_STREAM, IPPROTO_TCP) = 3
+0 setsockopt(3, SOL_SOCKET, SO_REUSEADDR, [1], 4) = 0
+0 bind(3, ..., ...) = 0
+0 listen(3, 10) = 0

+0 < S 0:0(0) win 32792 <mss 1000>
+0 > S. 0:0(0) ack 1 <mss 1460>
+.01 < . 1:1(0) ack 1 win 65535
+0 accept(3, ..., ...) = 4

+0.0001 < P. 1:1461(1460) ack 1 win 257
+.0 > . 1:1(0) ack 1461 win 65535
+0.0001 < P. 1461:2921(1460) ack 1 win 257
+.0 > . 1:1(0) ack 2921 win 65535
+0.0001 < P. 2921:4381(1460) ack 1 win 257
+.0 > . 1:1(0) ack 4381 win 65535
+0.0001 < P. 4381:5841(1460) ack 1 win 257
+.0 > . 1:1(0) ack 5841 win 65535
+0.0001 < P. 5841:7301(1460) ack 1 win 257
+.0 > . 1:1(0) ack 7301 win 65535
+0.0001 < P. 7301:8761(1460) ack 1 win 257
+.0 > . 1:1(0) ack 8761 win 65535
+0.0001 < P. 8761:10221(1460) ack 1 win 257
+.0 > . 1:1(0) ack 10221 win 65535
+0.0001 < P. 10221:11681(1460) ack 1 win 257
+.0 > . 1:1(0) ack 11681 win 65535
+0.0001 < P. 11681:13141(1460) ack 1 win 257
+.0 > . 1:1(0) ack 13141 win 65535
+0.0001 < P. 13141:14601(1460) ack 1 win 257
+.0 > . 1:1(0) ack 14601 win 65535
+0.0001 < P. 14601:16061(1460) ack 1 win 257
+.0 > . 1:1(0) ack 16061 win 65535
+0.0001 < P. 16061:17521(1460) ack 1 win 257
+.0 > . 1:1(0) ack 17521 win 65535
+0.0001 < P. 17521:18981(1460) ack 1 win 257
+.0 > . 1:1(0) ack 18981 win 65535
+0.0001 < P. 18981:20441(1460) ack 1 win 257
+.0 > . 1:1(0) ack 20441 win 65535
+0.0001 < P. 20441:21901(1460) ack 1 win 257
+.0 > . 1:1(0) ack 21901 win 65535
+0.0001 < P. 21901:23361(1460) ack 1 win 257
+.0 > . 1:1(0) ack 23361 win 65535
+0.0001 < P. 23361:24821(1460) ack 1 win 257
0.055 > . 1:1(0) ack 24821 win 65535
+0.0001 < P. 24821:26281(1460) ack 1 win 257
+.0 > . 1:1(0) ack 26281 win 65535
+0.0001 < P. 26281:27741(1460) ack 1 win 257
+.0 > . 1:1(0) ack 27741 win 65535
+0.0001 < P. 27741:29201(1460) ack 1 win 257
+.0 > . 1:1(0) ack 29201 win 65535
+0.0001 < P. 29201:30661(1460) ack 1 win 257
+.0 > . 1:1(0) ack 30661 win 65535
+0.0001 < P. 30661:32121(1460) ack 1 win 257
+.0 > . 1:1(0) ack 32121 win 65535
+0.0001 < P. 32121:33581(1460) ack 1 win 257
+.0 > . 1:1(0) ack 33581 win 65535
+0.0001 < P. 33581:35041(1460) ack 1 win 257
+.0 > . 1:1(0) ack 35041 win 65535
+0.0001 < P. 35041:36501(1460) ack 1 win 257
+.0 > . 1:1(0) ack 36501 win 65535
+0.0001 < P. 36501:37961(1460) ack 1 win 257
+.0 > . 1:1(0) ack 37961 win 65535
+0.0001 < P. 37961:39421(1460) ack 1 win 257
+.0 > . 1:1(0) ack 39421 win 65535
+0.0001 < P. 39421:40881(1460) ack 1 win 257
+.0 > . 1:1(0) ack 40881 win 65535
+0.0001 < P. 40881:42341(1460) ack 1 win 257
+.0 > . 1:1(0) ack 42341 win 65535
+0.0001 < P. 42341:43801(1460) ack 1 win 257
+.0 > . 1:1(0) ack 43801 win 65535
+0.0001 < P. 43801:45261(1460) ack 1 win 257
+.0 > . 1:1(0) ack 45261 win 65535
+0.0001 < P. 45261:46721(1460) ack 1 win 257
+.0 > . 1:1(0) ack 46721 win 65535
+0.0001 < P. 46721:48181(1460) ack 1 win 257
+.0 > . 1:1(0) ack 48181 win 65535
+0.0001 < P. 48181:49641(1460) ack 1 win 257
+.0 > . 1:1(0) ack 49641 win 65535
+0.0001 < P. 49641:51101(1460) ack 1 win 257
+.0 > . 1:1(0) ack 51101 win 65535
+0.0001 < P. 51101:52561(1460) ack 1 win 257
+.0 > . 1:1(0) ack 52561 win 65535
+0.0001 < P. 52561:54021(1460) ack 1 win 257
+.0 > . 1:1(0) ack 54021 win 65535
+0.0001 < P. 54021:55481(1460) ack 1 win 257
+.0 > . 1:1(0) ack 55481 win 65535
+0.0001 < P. 55481:56941(1460) ack 1 win 257
+.0 > . 1:1(0) ack 56941 win 65535
+0.0001 < P. 56941:58401(1460) ack 1 win 257
+.0 > . 1:1(0) ack 58401 win 65535
+0.0001 < P. 58401:59861(1460) ack 1 win 257
+.0 > . 1:1(0) ack 59861 win 65535
+0.0001 < P. 59861:61321(1460) ack 1 win 257
+.0 > . 1:1(0) ack 61321 win 65535
+0.0001 < P. 61321:62781(1460) ack 1 win 257
+.0 > . 1:1(0) ack 62781 win 65535
+0.0001 < P. 62781:64241(1460) ack 1 win 257
+.0 > . 1:1(0) ack 64241 win 65535
+0.0001 < P. 64241:65701(1460) ack 1 win 257
+.0 > . 1:1(0) ack 65701 win 65535
+0.0001 < P. 65701:67161(1460) ack 1 win 257
+.0 > . 1:1(0) ack 67161 win 65535

// nf_ct_proto_6: SEQ is under the lower bound (already ACKed data retransmitted) IN=tun0 OUT= MAC= SRC=192.0.2.1 DST=192.168.24.72 LEN=1500 TOS=0x00 PREC=0x00 TTL=255 ID=0 PROTO=TCP SPT=34375 DPT=8080 SEQ=1 ACK=4162510439 WINDOW=257 RES=0x00 ACK PSH URGP=0
+0.0001 < P. 1:1461(1460) ack 1 win 257

// only sent if above packet isn't flagged as invalid
+.0 > . 1:1(0) ack 67161 win 65535

+0 `$xtables -D INPUT -m conntrack --ctstate INVALID -j DROP`
Loading