Commit | Line | Data |
---|---|---|
1b29df0e | 1 | #!/bin/bash |
a062260a PA |
2 | # SPDX-License-Identifier: GPL-2.0 |
3 | ||
4 | readonly BASE="ns-$(mktemp -u XXXXXX)" | |
5 | readonly SRC=2 | |
6 | readonly DST=1 | |
7 | readonly DST_NAT=100 | |
8 | readonly NS_SRC=$BASE$SRC | |
9 | readonly NS_DST=$BASE$DST | |
10 | ||
11 | # "baremetal" network used for raw UDP traffic | |
12 | readonly BM_NET_V4=192.168.1. | |
13 | readonly BM_NET_V6=2001:db8:: | |
14 | ||
15 | # "overlay" network used for UDP over UDP tunnel traffic | |
16 | readonly OL_NET_V4=172.16.1. | |
17 | readonly OL_NET_V6=2001:db8:1:: | |
18 | readonly NPROCS=`nproc` | |
19 | ||
20 | cleanup() { | |
21 | local ns | |
22 | local -r jobs="$(jobs -p)" | |
23 | [ -n "${jobs}" ] && kill -1 ${jobs} 2>/dev/null | |
24 | ||
25 | for ns in $NS_SRC $NS_DST; do | |
26 | ip netns del $ns 2>/dev/null | |
27 | done | |
28 | } | |
29 | ||
30 | trap cleanup EXIT | |
31 | ||
32 | create_ns() { | |
33 | local net | |
34 | local ns | |
35 | ||
36 | for ns in $NS_SRC $NS_DST; do | |
37 | ip netns add $ns | |
38 | ip -n $ns link set dev lo up | |
39 | done | |
40 | ||
41 | ip link add name veth$SRC type veth peer name veth$DST | |
42 | ||
43 | for ns in $SRC $DST; do | |
44 | ip link set dev veth$ns netns $BASE$ns | |
45 | ip -n $BASE$ns link set dev veth$ns up | |
46 | ip -n $BASE$ns addr add dev veth$ns $BM_NET_V4$ns/24 | |
47 | ip -n $BASE$ns addr add dev veth$ns $BM_NET_V6$ns/64 nodad | |
48 | done | |
d28b25a6 | 49 | ip -n $NS_DST link set veth$DST xdp object ../bpf/xdp_dummy.o section xdp 2>/dev/null |
a062260a PA |
50 | } |
51 | ||
52 | create_vxlan_endpoint() { | |
53 | local -r netns=$1 | |
54 | local -r bm_dev=$2 | |
55 | local -r bm_rem_addr=$3 | |
56 | local -r vxlan_dev=$4 | |
57 | local -r vxlan_id=$5 | |
58 | local -r vxlan_port=4789 | |
59 | ||
60 | ip -n $netns link set dev $bm_dev up | |
61 | ip -n $netns link add dev $vxlan_dev type vxlan id $vxlan_id \ | |
62 | dstport $vxlan_port remote $bm_rem_addr | |
63 | ip -n $netns link set dev $vxlan_dev up | |
64 | } | |
65 | ||
66 | create_vxlan_pair() { | |
67 | local ns | |
68 | ||
69 | create_ns | |
70 | ||
71 | for ns in $SRC $DST; do | |
72 | # note that 3 - $SRC == $DST and 3 - $DST == $SRC | |
73 | create_vxlan_endpoint $BASE$ns veth$ns $BM_NET_V4$((3 - $ns)) vxlan$ns 4 | |
74 | ip -n $BASE$ns addr add dev vxlan$ns $OL_NET_V4$ns/24 | |
75 | done | |
76 | for ns in $SRC $DST; do | |
77 | create_vxlan_endpoint $BASE$ns veth$ns $BM_NET_V6$((3 - $ns)) vxlan6$ns 6 | |
78 | ip -n $BASE$ns addr add dev vxlan6$ns $OL_NET_V6$ns/24 nodad | |
79 | done | |
80 | } | |
81 | ||
82 | is_ipv6() { | |
83 | if [[ $1 =~ .*:.* ]]; then | |
84 | return 0 | |
85 | fi | |
86 | return 1 | |
87 | } | |
88 | ||
89 | run_test() { | |
90 | local -r msg=$1 | |
91 | local -r dst=$2 | |
92 | local -r pkts=$3 | |
93 | local -r vxpkts=$4 | |
94 | local bind=$5 | |
95 | local rx_args="" | |
96 | local rx_family="-4" | |
97 | local family=-4 | |
98 | local filter=IpInReceives | |
99 | local ipt=iptables | |
100 | ||
101 | printf "%-40s" "$msg" | |
102 | ||
103 | if is_ipv6 $dst; then | |
104 | # rx program does not support '-6' and implies ipv6 usage by default | |
105 | rx_family="" | |
106 | family=-6 | |
107 | filter=Ip6InReceives | |
108 | ipt=ip6tables | |
109 | fi | |
110 | ||
111 | rx_args="$rx_family" | |
112 | [ -n "$bind" ] && rx_args="$rx_args -b $bind" | |
113 | ||
114 | # send a single GSO packet, segmented in 10 UDP frames. | |
115 | # Always expect 10 UDP frames on RX side as rx socket does | |
116 | # not enable GRO | |
117 | ip netns exec $NS_DST $ipt -A INPUT -p udp --dport 4789 | |
118 | ip netns exec $NS_DST $ipt -A INPUT -p udp --dport 8000 | |
119 | ip netns exec $NS_DST ./udpgso_bench_rx -C 1000 -R 10 -n 10 -l 1300 $rx_args & | |
120 | local spid=$! | |
121 | sleep 0.1 | |
122 | ip netns exec $NS_SRC ./udpgso_bench_tx $family -M 1 -s 13000 -S 1300 -D $dst | |
123 | local retc=$? | |
124 | wait $spid | |
125 | local rets=$? | |
126 | if [ ${rets} -ne 0 ] || [ ${retc} -ne 0 ]; then | |
127 | echo " fail client exit code $retc, server $rets" | |
128 | ret=1 | |
129 | return | |
130 | fi | |
131 | ||
132 | local rcv=`ip netns exec $NS_DST $ipt"-save" -c | grep 'dport 8000' | \ | |
133 | sed -e 's/\[//' -e 's/:.*//'` | |
134 | if [ $rcv != $pkts ]; then | |
add25d6d | 135 | echo " fail - received $rcv packets, expected $pkts" |
a062260a PA |
136 | ret=1 |
137 | return | |
138 | fi | |
139 | ||
140 | local vxrcv=`ip netns exec $NS_DST $ipt"-save" -c | grep 'dport 4789' | \ | |
141 | sed -e 's/\[//' -e 's/:.*//'` | |
142 | ||
143 | # upper net can generate a little noise, allow some tolerance | |
144 | if [ $vxrcv -lt $vxpkts -o $vxrcv -gt $((vxpkts + 3)) ]; then | |
145 | echo " fail - received $vxrcv vxlan packets, expected $vxpkts" | |
146 | ret=1 | |
147 | return | |
148 | fi | |
149 | echo " ok" | |
150 | } | |
151 | ||
152 | run_bench() { | |
153 | local -r msg=$1 | |
154 | local -r dst=$2 | |
155 | local family=-4 | |
156 | ||
157 | printf "%-40s" "$msg" | |
158 | if [ $NPROCS -lt 2 ]; then | |
159 | echo " skip - needed 2 CPUs found $NPROCS" | |
160 | return | |
161 | fi | |
162 | ||
163 | is_ipv6 $dst && family=-6 | |
164 | ||
165 | # bind the sender and the receiver to different CPUs to try | |
166 | # get reproducible results | |
167 | ip netns exec $NS_DST bash -c "echo 2 > /sys/class/net/veth$DST/queues/rx-0/rps_cpus" | |
168 | ip netns exec $NS_DST taskset 0x2 ./udpgso_bench_rx -C 1000 -R 10 & | |
169 | local spid=$! | |
170 | sleep 0.1 | |
171 | ip netns exec $NS_SRC taskset 0x1 ./udpgso_bench_tx $family -l 3 -S 1300 -D $dst | |
172 | local retc=$? | |
173 | wait $spid | |
174 | local rets=$? | |
175 | if [ ${rets} -ne 0 ] || [ ${retc} -ne 0 ]; then | |
176 | echo " fail client exit code $retc, server $rets" | |
177 | ret=1 | |
178 | return | |
179 | fi | |
180 | } | |
181 | ||
182 | for family in 4 6; do | |
183 | BM_NET=$BM_NET_V4 | |
184 | OL_NET=$OL_NET_V4 | |
185 | IPT=iptables | |
186 | SUFFIX=24 | |
187 | VXDEV=vxlan | |
8b3170e0 | 188 | PING=ping |
a062260a PA |
189 | |
190 | if [ $family = 6 ]; then | |
191 | BM_NET=$BM_NET_V6 | |
192 | OL_NET=$OL_NET_V6 | |
193 | SUFFIX="64 nodad" | |
194 | VXDEV=vxlan6 | |
195 | IPT=ip6tables | |
5e75d0b2 JW |
196 | # Use ping6 on systems where ping doesn't handle IPv6 |
197 | ping -w 1 -c 1 ::1 > /dev/null 2>&1 || PING="ping6" | |
a062260a PA |
198 | fi |
199 | ||
200 | echo "IPv$family" | |
201 | ||
202 | create_ns | |
203 | run_test "No GRO" $BM_NET$DST 10 0 | |
204 | cleanup | |
205 | ||
206 | create_ns | |
207 | ip netns exec $NS_DST ethtool -K veth$DST rx-gro-list on | |
208 | run_test "GRO frag list" $BM_NET$DST 1 0 | |
209 | cleanup | |
210 | ||
211 | # UDP GRO fwd skips aggregation when find an udp socket with the GRO option | |
212 | # if there is an UDP tunnel in the running system, such lookup happen | |
213 | # take place. | |
214 | # use NAT to circumvent GRO FWD check | |
215 | create_ns | |
216 | ip -n $NS_DST addr add dev veth$DST $BM_NET$DST_NAT/$SUFFIX | |
217 | ip netns exec $NS_DST ethtool -K veth$DST rx-udp-gro-forwarding on | |
218 | ip netns exec $NS_DST $IPT -t nat -I PREROUTING -d $BM_NET$DST_NAT \ | |
219 | -j DNAT --to-destination $BM_NET$DST | |
220 | run_test "GRO fwd" $BM_NET$DST_NAT 1 0 $BM_NET$DST | |
221 | cleanup | |
222 | ||
223 | create_ns | |
224 | run_bench "UDP fwd perf" $BM_NET$DST | |
225 | ip netns exec $NS_DST ethtool -K veth$DST rx-udp-gro-forwarding on | |
226 | run_bench "UDP GRO fwd perf" $BM_NET$DST | |
227 | cleanup | |
228 | ||
229 | create_vxlan_pair | |
230 | ip netns exec $NS_DST ethtool -K veth$DST rx-gro-list on | |
231 | run_test "GRO frag list over UDP tunnel" $OL_NET$DST 1 1 | |
232 | cleanup | |
233 | ||
234 | # use NAT to circumvent GRO FWD check | |
235 | create_vxlan_pair | |
236 | ip -n $NS_DST addr add dev $VXDEV$DST $OL_NET$DST_NAT/$SUFFIX | |
237 | ip netns exec $NS_DST ethtool -K veth$DST rx-udp-gro-forwarding on | |
238 | ip netns exec $NS_DST $IPT -t nat -I PREROUTING -d $OL_NET$DST_NAT \ | |
239 | -j DNAT --to-destination $OL_NET$DST | |
240 | ||
241 | # load arp cache before running the test to reduce the amount of | |
242 | # stray traffic on top of the UDP tunnel | |
8b3170e0 | 243 | ip netns exec $NS_SRC $PING -q -c 1 $OL_NET$DST_NAT >/dev/null |
a062260a PA |
244 | run_test "GRO fwd over UDP tunnel" $OL_NET$DST_NAT 1 1 $OL_NET$DST |
245 | cleanup | |
246 | ||
247 | create_vxlan_pair | |
248 | run_bench "UDP tunnel fwd perf" $OL_NET$DST | |
249 | ip netns exec $NS_DST ethtool -K veth$DST rx-udp-gro-forwarding on | |
250 | run_bench "UDP tunnel GRO fwd perf" $OL_NET$DST | |
251 | cleanup | |
252 | done | |
253 | ||
254 | exit $ret |