mirror of
https://github.com/torvalds/linux.git
synced 2026-09-14 16:10:02 +02:00
selftests/net/openvswitch: add SCTP flow key support and test
The ovskey flow-string parser has no OVS_KEY_ATTR_SCTP entry, so a flow string containing sctp(src=.../dst=...) parses without error but silently drops the L4 key. The resulting flow carries only ipv4(proto=132), and the kernel rejects it: match_validate() in flow_netlink.c requires OVS_KEY_ATTR_SCTP when the IP protocol is IPPROTO_SCTP and returns -EINVAL for the missing key. Register OVS_KEY_ATTR_SCTP in the parse table and add a matching selftest that verifies SCTP flow key matching (sctp src/dst port). One listener serves the whole test. socat's fork option handles each association in a child, so the flow rules are the only thing that changes between the three phases and the listener is never restarted underneath them. -t 1 bounds how long a forked child lingers after its association closes, and the existing kill -TERM of the captured pid on teardown removes the listener itself. Also enable CONFIG_IP_SCTP in the selftest kernel config. The config checker strips underscores before comparing keys, so the entry sorts before CONFIG_IPV6 rather than after it. Signed-off-by: Minxi Hou <houminxi@gmail.com> Reviewed-by: Aaron Conole <aconole@redhat.com> Link: https://patch.msgid.link/20260811181645.1918420-1-houminxi@gmail.com Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
parent
5ba017f9ef
commit
07a9e39750
|
|
@ -1,5 +1,6 @@
|
|||
CONFIG_GENEVE=m
|
||||
CONFIG_INET_DIAG=y
|
||||
CONFIG_IP_SCTP=y
|
||||
CONFIG_IPV6=y
|
||||
CONFIG_NETFILTER=y
|
||||
CONFIG_NET_IPGRE=m
|
||||
|
|
|
|||
|
|
@ -33,6 +33,7 @@ tests="
|
|||
action_set set: SET action rewrites fields
|
||||
trunc trunc: output truncation
|
||||
icmpv6 icmpv6: ICMPv6 echo type match
|
||||
sctp_connect_v4 sctp: SCTP flow key matching
|
||||
psample psample: Sampling packets with psample"
|
||||
|
||||
info() {
|
||||
|
|
@ -610,6 +611,95 @@ test_icmpv6() {
|
|||
return 0
|
||||
}
|
||||
|
||||
# Check for an SCTP endpoint via /proc, which works without sctp_diag.
|
||||
sctp_eps_has() {
|
||||
ip netns exec "$1" awk -v p="$2" '$6==p' /proc/net/sctp/eps | grep -q .
|
||||
}
|
||||
|
||||
# sctp_connect_v4 test
|
||||
# - sctp(dst=4443) matches client-to-server INIT
|
||||
# - sctp(src=4443) matches server-to-client INIT-ACK
|
||||
# - remove flows and verify connection fails, reinstall and recover
|
||||
test_sctp_connect_v4() {
|
||||
local t="test_sctp_connect_v4"
|
||||
local srv_ip=172.31.110.20
|
||||
|
||||
modprobe -q sctp 2>/dev/null || return "$ksft_skip"
|
||||
socat -V 2>&1 | grep -q "define WITH_SCTP" || return "$ksft_skip"
|
||||
|
||||
sbx_add "$t" || return $?
|
||||
ovs_add_dp "$t" sctp4 || return 1
|
||||
|
||||
info "create namespaces"
|
||||
for ns in client server; do
|
||||
ovs_add_netns_and_veths "$t" "sctp4" "$ns" \
|
||||
"${ns:0:1}0" "${ns:0:1}1" || return 1
|
||||
done
|
||||
|
||||
ip netns exec client ip addr add 172.31.110.10/24 dev c1
|
||||
ip netns exec client ip link set c1 up
|
||||
ip netns exec server ip addr add "${srv_ip}/24" dev s1
|
||||
ip netns exec server ip link set s1 up
|
||||
|
||||
# ARP forwarding
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(1),eth(),eth_type(0x0806),arp()' \
|
||||
'2' || return 1
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(2),eth(),eth_type(0x0806),arp()' \
|
||||
'1' || return 1
|
||||
|
||||
# SCTP port matching: dst for request, src for reply
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(1),eth(),eth_type(0x0800),ipv4(proto=132),sctp(dst=4443)' \
|
||||
'2' || return 1
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(2),eth(),eth_type(0x0800),ipv4(proto=132),sctp(src=4443)' \
|
||||
'1' || return 1
|
||||
|
||||
# The listener forks a child per association, so one instance serves
|
||||
# the whole test and the flows stay the only variable. -t 1 bounds
|
||||
# how long a child lingers after its association closes.
|
||||
ovs_netns_spawn_daemon "$t" "server" \
|
||||
socat -u -t 1 SCTP4-LISTEN:4443,fork STDOUT
|
||||
ovs_wait sctp_eps_has server 4443 || return 1
|
||||
|
||||
info "verify SCTP association with port-keyed flows"
|
||||
ovs_sbx "$t" ip netns exec client \
|
||||
timeout 3 socat -u STDIN "SCTP4-CONNECT:${srv_ip}:4443" </dev/null \
|
||||
|| return 1
|
||||
|
||||
ovs_del_flows "$t" sctp4
|
||||
|
||||
info "verify connection fails without flows"
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(1),eth(),eth_type(0x0806),arp()' \
|
||||
'2' || return 1
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(2),eth(),eth_type(0x0806),arp()' \
|
||||
'1' || return 1
|
||||
|
||||
ovs_sbx "$t" ip netns exec client \
|
||||
timeout 3 socat -u STDIN "SCTP4-CONNECT:${srv_ip}:4443" </dev/null \
|
||||
>/dev/null 2>&1 \
|
||||
&& { info "connection should fail without flows"
|
||||
return 1; }
|
||||
|
||||
info "reinstall flows and verify recovery"
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(1),eth(),eth_type(0x0800),ipv4(proto=132),sctp(dst=4443)' \
|
||||
'2' || return 1
|
||||
ovs_add_flow "$t" sctp4 \
|
||||
'in_port(2),eth(),eth_type(0x0800),ipv4(proto=132),sctp(src=4443)' \
|
||||
'1' || return 1
|
||||
|
||||
ovs_sbx "$t" ip netns exec client \
|
||||
timeout 3 socat -u STDIN "SCTP4-CONNECT:${srv_ip}:4443" </dev/null \
|
||||
|| return 1
|
||||
|
||||
return 0
|
||||
}
|
||||
|
||||
# psample test
|
||||
# - use psample to observe packets
|
||||
test_psample() {
|
||||
|
|
|
|||
|
|
@ -1984,6 +1984,11 @@ class ovskey(nla):
|
|||
"udp",
|
||||
ovskey.ovs_key_udp,
|
||||
),
|
||||
(
|
||||
"OVS_KEY_ATTR_SCTP",
|
||||
"sctp",
|
||||
ovskey.ovs_key_sctp,
|
||||
),
|
||||
(
|
||||
"OVS_KEY_ATTR_ICMP",
|
||||
"icmp",
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user