> From: dev [mailto:dev-boun...@dpdk.org] On Behalf Of guohongzhi (A) > Sent: Friday, May 15, 2020 3:05 AM > > Ok, later I will write a patch to solve the problem of tcpdump checksum > > -----Original Message----- > From: Morten Brørup [mailto:m...@smartsharesystems.com] > Sent: Thursday,May 14,2020 20:57 > To: guohongzhi (A) <guohongz...@huawei.com>; dev@dpdk.org > Cc: olivier.m...@6wind.com; konstantin.anan...@intel.com; > jiayu...@intel.com; ferruh.yi...@intel.com; nicolas.chau...@intel.com; > cristian.dumitre...@intel.com; Zhoujingbin (Robin, Russell Lab) > <zhoujing...@huawei.com>; chenchanghu <chenchan...@huawei.com>; Lilijun > (Jerry) <jerry.lili...@huawei.com>; Linhaifeng <haifeng....@huawei.com> > Subject: RE: [dpdk-dev] [PATCH] lib/librte_net: fix bug for ipv4 > checksumcalculating > > > From: dev [mailto:dev-boun...@dpdk.org] On Behalf Of guohongzhi > > Sent: Thursday, May 14, 2020 3:27 AM > > > > The function of rte_ipv4_cksum for calculating the checksum of IPv4 > > header is incorrect. > > This function will return checksum value like 0xffff. > > This value, however, is considered an illegal checksum on some > > switches(like Trident3). > > > > RFC 1624 specifies the IPv4 checksum as follows: > > https://tools.ietf.org/rfc/rfc1624 > > Since there is guaranteed to be at least one > > non-zero field in the IP header, and the checksum field in the > > protocol header is the complement of the sum, the checksum field > can > > never contain ~(+0), which is -0 (0xFFFF). It can, however, > contain > > ~(-0), which is +0 (0x0000). > > > > --- > > lib/librte_net/rte_ip.h | 2 +- > > 1 file changed, 1 insertion(+), 1 deletion(-) > > > > diff --git a/lib/librte_net/rte_ip.h b/lib/librte_net/rte_ip.h index > > 1ceb7b7..ece2e43 100644 > > --- a/lib/librte_net/rte_ip.h > > +++ b/lib/librte_net/rte_ip.h > > @@ -267,7 +267,7 @@ rte_ipv4_cksum(const struct rte_ipv4_hdr > > *ipv4_hdr) { > > uint16_t cksum; > > cksum = rte_raw_cksum(ipv4_hdr, sizeof(struct rte_ipv4_hdr)); > > - return (cksum == 0xffff) ? cksum : (uint16_t)~cksum; > > + return (uint16_t)~cksum; > > } > > > > /** > > -- > > 2.21.0.windows.1 > > > > > > Well spotted! > > Reviewed-By: Morten Brørup <m...@smartsharesystems.com> >
While you are at it, you could also fix a Big Endian bug in __rte_raw_cksum(): /* if length is in odd bytes */ if (len == 1) +#if RTE_BYTE_ORDER == RTE_BIG_ENDIAN + sum += *((const uint8_t *)u16_buf) << 8; +#else sum += *((const uint8_t *)u16_buf); +#endif return sum; > > Would you consider writing another patch splitting > rte_ipv4_udptcp_cksum() up into rte_ipv4_udp_cksum() and > rte_ipv4_tcp_cksum(), so the TCP checksum will be calculated correctly? > > RFC 768 for UDP specifies: > > If the computed checksum is zero, it is transmitted as all ones > (the equivalent in one's complement arithmetic). An all zero > transmitted checksum value means that the transmitter generated no > checksum (for debugging or for higher level protocols that don't > care). > > RFC 793 for TCP has no such special treatment for the checksum of zero, > but rte_ipv4_udptcp_cksum() implements the UDP special treatment > anyway.