Skip to content

Commit

Permalink
selftests: net: csum: Fix checksums for packets with non-zero padding
Browse files Browse the repository at this point in the history
[ Upstream commit e8a63d4 ]

Padding is not included in UDP and TCP checksums. Therefore, reduce the
length of the checksummed data to include only the data in the IP
payload. This fixes spurious reported checksum failures like

rx: pkt: sport=33000 len=26 csum=0xc850 verify=0xf9fe
pkt: bad csum

Technically it is possible for there to be trailing bytes after the UDP
data but before the Ethernet padding (e.g. if sizeof(ip) + sizeof(udp) +
udp.len < ip.len). However, we don't generate such packets.

Fixes: 91a7de8 ("selftests/net: add csum offload test")
Signed-off-by: Sean Anderson <[email protected]>
Reviewed-by: Willem de Bruijn <[email protected]>
Link: https://patch.msgid.link/[email protected]
Signed-off-by: Jakub Kicinski <[email protected]>
Signed-off-by: Sasha Levin <[email protected]>
  • Loading branch information
Sean Anderson authored and gregkh committed Sep 18, 2024
1 parent 67b61e2 commit 176b6a0
Showing 1 changed file with 14 additions and 2 deletions.
16 changes: 14 additions & 2 deletions tools/testing/selftests/net/lib/csum.c
Original file line number Diff line number Diff line change
Expand Up @@ -654,10 +654,16 @@ static int recv_verify_packet_ipv4(void *nh, int len)
{
struct iphdr *iph = nh;
uint16_t proto = cfg_encap ? IPPROTO_UDP : cfg_proto;
uint16_t ip_len;

if (len < sizeof(*iph) || iph->protocol != proto)
return -1;

ip_len = ntohs(iph->tot_len);
if (ip_len > len || ip_len < sizeof(*iph))
return -1;

len = ip_len;
iph_addr_p = &iph->saddr;
if (proto == IPPROTO_TCP)
return recv_verify_packet_tcp(iph + 1, len - sizeof(*iph));
Expand All @@ -669,16 +675,22 @@ static int recv_verify_packet_ipv6(void *nh, int len)
{
struct ipv6hdr *ip6h = nh;
uint16_t proto = cfg_encap ? IPPROTO_UDP : cfg_proto;
uint16_t ip_len;

if (len < sizeof(*ip6h) || ip6h->nexthdr != proto)
return -1;

ip_len = ntohs(ip6h->payload_len);
if (ip_len > len - sizeof(*ip6h))
return -1;

len = ip_len;
iph_addr_p = &ip6h->saddr;

if (proto == IPPROTO_TCP)
return recv_verify_packet_tcp(ip6h + 1, len - sizeof(*ip6h));
return recv_verify_packet_tcp(ip6h + 1, len);
else
return recv_verify_packet_udp(ip6h + 1, len - sizeof(*ip6h));
return recv_verify_packet_udp(ip6h + 1, len);
}

/* return whether auxdata includes TP_STATUS_CSUM_VALID */
Expand Down

0 comments on commit 176b6a0

Please sign in to comment.