TCP checksum offloading on virtio-net paravirtualized interfaces
2
votes
1
answer
207
views
Consider the topology where 2 QEMU VMs running Linux Ubuntu
16.04
kernel version 4.4.0-210
have both virtio-net
interfaces with TAP
backends connected to the same (host) Linux bridge
and an SSH
connection between them.
ubuntu@VM1:~$ uname -a
Linux VM1 4.4.0-210-generic #242-Ubuntu SMP Fri Apr 16 09:57:56 UTC 2021 x86_64 x86_64 x8x
ubuntu@VM1:~$
Both VMs use paravirtualized virtio-net
interfaces defaulting to TX and RX checksum
offloading.
ubuntu@VM1:~$ ethtool -i eth0
driver: virtio_net
version: 1.0.0
firmware-version:
expansion-rom-version:
bus-info: 0000:00:03.0
supports-statistics: no
supports-test: no
supports-eeprom-access: no
supports-register-dump: no
supports-priv-flags: no
ubuntu@VM1:~$
ubuntu@VM1:~$ ethtool -k eth0 | grep -i sum
rx-checksumming: on [fixed]
tx-checksumming: on
tx-checksum-ipv4: off [fixed]
tx-checksum-ip-generic: on
tx-checksum-ipv6: off [fixed]
tx-checksum-fcoe-crc: off [fixed]
tx-checksum-sctp: off [fixed]
ubuntu@VM1:~$
ubuntu@VM2:~$ ethtool -k eth0 | grep -i sum
rx-checksumming: on [fixed]
tx-checksumming: on
tx-checksum-ipv4: off [fixed]
tx-checksum-ip-generic: on
tx-checksum-ipv6: off [fixed]
tx-checksum-fcoe-crc: off [fixed]
tx-checksum-sctp: off [fixed]
ubuntu@VM2:~$
That actually means:
- kernel network stack sends out SSH/TCP
packets without computing & filling the relevant TCP checksum
field inside them (i.e. basically the TCP checksum
inside the packets sent is either zeroed out or incorrect)
- kernel network stack assumes the virtio-net
interface has already checked/verified the TCP checksum
for SSH/TCP
received packets and is therefore allowed to skip it
Hence the SSH
connection works even though traveling SSH/TCP
packets have an *incorrect* TCP
checksum (tcpdump
run inside both VM confirms this).
Later, changing the topology by connecting each VM to a different linux bridge with a virtual router
in the middle, suddenly the SSH
connection stop working. I double checked that virtual router actually forwards TCP/SSH
packets *as-is* from a bridge to the the other (in both directions), so I don't understand why the SSH
connection stopped working this time.
What is going on in the latter case ? Thanks.
Asked by CarloC
(385 rep)
Jul 7, 2025, 05:59 AM
Last activity: Jul 7, 2025, 09:09 AM
Last activity: Jul 7, 2025, 09:09 AM