diff options
author | Peter Oskolkov <posk@google.com> | 2019-03-04 19:27:09 -0500 |
---|---|---|
committer | Daniel Borkmann <daniel@iogearbox.net> | 2019-03-07 04:41:40 -0500 |
commit | 17a90a78847324b1a34b0de833492cbd2366361d (patch) | |
tree | faaf5c0521063b03c7d8040a992c5e0b60dc20a5 /tools | |
parent | ea0371f7879987cff70e21d808e3e9fea624c051 (diff) |
selftests/bpf: test that GSO works in lwt_ip_encap
Add a test on egress that a large TCP packet successfully goes through
the lwt+bpf encap tunnel.
Although there is no direct evidence that GSO worked, as opposed to
e.g. TCP segmentation or IP fragmentation (maybe a kernel stats counter
should be added to track the number of failed GSO attempts?), without
the previous patch in the patchset this test fails, and printk-debugging
showed that software-based GSO succeeded here (veth is not compatible with
SKB_GSO_DODGY, so GSO happens in the software stack).
Also removed an unnecessary nodad and added a missed failed flag.
Signed-off-by: Peter Oskolkov <posk@google.com>
Acked-by: Song Liu <songliubraving@fb.com>
Signed-off-by: Daniel Borkmann <daniel@iogearbox.net>
Diffstat (limited to 'tools')
-rwxr-xr-x | tools/testing/selftests/bpf/test_lwt_ip_encap.sh | 54 |
1 files changed, 52 insertions, 2 deletions
diff --git a/tools/testing/selftests/bpf/test_lwt_ip_encap.sh b/tools/testing/selftests/bpf/test_lwt_ip_encap.sh index 612632c1425f..d4d3391cc13a 100755 --- a/tools/testing/selftests/bpf/test_lwt_ip_encap.sh +++ b/tools/testing/selftests/bpf/test_lwt_ip_encap.sh | |||
@@ -78,6 +78,8 @@ TEST_STATUS=0 | |||
78 | TESTS_SUCCEEDED=0 | 78 | TESTS_SUCCEEDED=0 |
79 | TESTS_FAILED=0 | 79 | TESTS_FAILED=0 |
80 | 80 | ||
81 | TMPFILE="" | ||
82 | |||
81 | process_test_results() | 83 | process_test_results() |
82 | { | 84 | { |
83 | if [[ "${TEST_STATUS}" -eq 0 ]] ; then | 85 | if [[ "${TEST_STATUS}" -eq 0 ]] ; then |
@@ -147,7 +149,6 @@ setup() | |||
147 | ip -netns ${NS2} -6 addr add ${IPv6_7}/128 nodad dev veth7 | 149 | ip -netns ${NS2} -6 addr add ${IPv6_7}/128 nodad dev veth7 |
148 | ip -netns ${NS3} -6 addr add ${IPv6_8}/128 nodad dev veth8 | 150 | ip -netns ${NS3} -6 addr add ${IPv6_8}/128 nodad dev veth8 |
149 | 151 | ||
150 | |||
151 | ip -netns ${NS1} link set dev veth1 up | 152 | ip -netns ${NS1} link set dev veth1 up |
152 | ip -netns ${NS2} link set dev veth2 up | 153 | ip -netns ${NS2} link set dev veth2 up |
153 | ip -netns ${NS2} link set dev veth3 up | 154 | ip -netns ${NS2} link set dev veth3 up |
@@ -205,7 +206,7 @@ setup() | |||
205 | # configure IPv4 GRE device in NS3, and a route to it via the "bottom" route | 206 | # configure IPv4 GRE device in NS3, and a route to it via the "bottom" route |
206 | ip -netns ${NS3} tunnel add gre_dev mode gre remote ${IPv4_1} local ${IPv4_GRE} ttl 255 | 207 | ip -netns ${NS3} tunnel add gre_dev mode gre remote ${IPv4_1} local ${IPv4_GRE} ttl 255 |
207 | ip -netns ${NS3} link set gre_dev up | 208 | ip -netns ${NS3} link set gre_dev up |
208 | ip -netns ${NS3} addr add ${IPv4_GRE} nodad dev gre_dev | 209 | ip -netns ${NS3} addr add ${IPv4_GRE} dev gre_dev |
209 | ip -netns ${NS1} route add ${IPv4_GRE}/32 dev veth5 via ${IPv4_6} | 210 | ip -netns ${NS1} route add ${IPv4_GRE}/32 dev veth5 via ${IPv4_6} |
210 | ip -netns ${NS2} route add ${IPv4_GRE}/32 dev veth7 via ${IPv4_8} | 211 | ip -netns ${NS2} route add ${IPv4_GRE}/32 dev veth7 via ${IPv4_8} |
211 | 212 | ||
@@ -222,12 +223,18 @@ setup() | |||
222 | ip netns exec ${NS2} sysctl -wq net.ipv4.conf.all.rp_filter=0 | 223 | ip netns exec ${NS2} sysctl -wq net.ipv4.conf.all.rp_filter=0 |
223 | ip netns exec ${NS3} sysctl -wq net.ipv4.conf.all.rp_filter=0 | 224 | ip netns exec ${NS3} sysctl -wq net.ipv4.conf.all.rp_filter=0 |
224 | 225 | ||
226 | TMPFILE=$(mktemp /tmp/test_lwt_ip_encap.XXXXXX) | ||
227 | |||
225 | sleep 1 # reduce flakiness | 228 | sleep 1 # reduce flakiness |
226 | set +e | 229 | set +e |
227 | } | 230 | } |
228 | 231 | ||
229 | cleanup() | 232 | cleanup() |
230 | { | 233 | { |
234 | if [ -f ${TMPFILE} ] ; then | ||
235 | rm ${TMPFILE} | ||
236 | fi | ||
237 | |||
231 | ip netns del ${NS1} 2> /dev/null | 238 | ip netns del ${NS1} 2> /dev/null |
232 | ip netns del ${NS2} 2> /dev/null | 239 | ip netns del ${NS2} 2> /dev/null |
233 | ip netns del ${NS3} 2> /dev/null | 240 | ip netns del ${NS3} 2> /dev/null |
@@ -278,6 +285,46 @@ test_ping() | |||
278 | fi | 285 | fi |
279 | } | 286 | } |
280 | 287 | ||
288 | test_gso() | ||
289 | { | ||
290 | local readonly PROTO=$1 | ||
291 | local readonly PKT_SZ=5000 | ||
292 | local IP_DST="" | ||
293 | : > ${TMPFILE} # trim the capture file | ||
294 | |||
295 | # check that nc is present | ||
296 | command -v nc >/dev/null 2>&1 || \ | ||
297 | { echo >&2 "nc is not available: skipping TSO tests"; return; } | ||
298 | |||
299 | # listen on IPv*_DST, capture TCP into $TMPFILE | ||
300 | if [ "${PROTO}" == "IPv4" ] ; then | ||
301 | IP_DST=${IPv4_DST} | ||
302 | ip netns exec ${NS3} bash -c \ | ||
303 | "nc -4 -l -s ${IPv4_DST} -p 9000 > ${TMPFILE} &" | ||
304 | elif [ "${PROTO}" == "IPv6" ] ; then | ||
305 | IP_DST=${IPv6_DST} | ||
306 | ip netns exec ${NS3} bash -c \ | ||
307 | "nc -6 -l -s ${IPv6_DST} -p 9000 > ${TMPFILE} &" | ||
308 | RET=$? | ||
309 | else | ||
310 | echo " test_gso: unknown PROTO: ${PROTO}" | ||
311 | TEST_STATUS=1 | ||
312 | fi | ||
313 | sleep 1 # let nc start listening | ||
314 | |||
315 | # send a packet larger than MTU | ||
316 | ip netns exec ${NS1} bash -c \ | ||
317 | "dd if=/dev/zero bs=$PKT_SZ count=1 > /dev/tcp/${IP_DST}/9000 2>/dev/null" | ||
318 | sleep 2 # let the packet get delivered | ||
319 | |||
320 | # verify we received all expected bytes | ||
321 | SZ=$(stat -c %s ${TMPFILE}) | ||
322 | if [ "$SZ" != "$PKT_SZ" ] ; then | ||
323 | echo " test_gso failed: ${PROTO}" | ||
324 | TEST_STATUS=1 | ||
325 | fi | ||
326 | } | ||
327 | |||
281 | test_egress() | 328 | test_egress() |
282 | { | 329 | { |
283 | local readonly ENCAP=$1 | 330 | local readonly ENCAP=$1 |
@@ -307,6 +354,8 @@ test_egress() | |||
307 | fi | 354 | fi |
308 | test_ping IPv4 0 | 355 | test_ping IPv4 0 |
309 | test_ping IPv6 0 | 356 | test_ping IPv6 0 |
357 | test_gso IPv4 | ||
358 | test_gso IPv6 | ||
310 | 359 | ||
311 | # a negative test: remove routes to GRE devices: ping fails | 360 | # a negative test: remove routes to GRE devices: ping fails |
312 | remove_routes_to_gredev | 361 | remove_routes_to_gredev |
@@ -350,6 +399,7 @@ test_ingress() | |||
350 | ip -netns ${NS2} -6 route add ${IPv6_DST} encap bpf in obj test_lwt_ip_encap.o sec encap_gre6 dev veth2 | 399 | ip -netns ${NS2} -6 route add ${IPv6_DST} encap bpf in obj test_lwt_ip_encap.o sec encap_gre6 dev veth2 |
351 | else | 400 | else |
352 | echo "FAIL: unknown encap ${ENCAP}" | 401 | echo "FAIL: unknown encap ${ENCAP}" |
402 | TEST_STATUS=1 | ||
353 | fi | 403 | fi |
354 | test_ping IPv4 0 | 404 | test_ping IPv4 0 |
355 | test_ping IPv6 0 | 405 | test_ping IPv6 0 |