From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from proxy.6wind.com (host.76.145.23.62.rev.coltfrance.com [62.23.145.76]) by dpdk.org (Postfix) with ESMTP id DA6F76CB4 for ; Mon, 3 Oct 2016 11:00:58 +0200 (CEST) Received: from glumotte.dev.6wind.com (unknown [10.16.0.195]) by proxy.6wind.com (Postfix) with ESMTP id 0D16927336; Mon, 3 Oct 2016 11:00:57 +0200 (CEST) From: Olivier Matz To: dev@dpdk.org, yuanhan.liu@linux.intel.com Cc: konstantin.ananyev@intel.com, sugesh.chandran@intel.com, bruce.richardson@intel.com, jianfeng.tan@intel.com, helin.zhang@intel.com, adrien.mazarguil@6wind.com, stephen@networkplumber.org, dprovan@bivio.net, xiao.w.wang@intel.com Date: Mon, 3 Oct 2016 11:00:15 +0200 Message-Id: <1475485223-30566-5-git-send-email-olivier.matz@6wind.com> X-Mailer: git-send-email 2.8.1 In-Reply-To: <1475485223-30566-1-git-send-email-olivier.matz@6wind.com> References: <1469088510-7552-1-git-send-email-olivier.matz@6wind.com> <1475485223-30566-1-git-send-email-olivier.matz@6wind.com> Subject: [dpdk-dev] [PATCH v2 04/12] net: add function to calculate a checksum in a mbuf X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: patches and discussions about DPDK List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 03 Oct 2016 09:00:59 -0000 This function can be used to calculate the checksum of data embedded in mbuf, that can be composed of several segments. This function will be used by the virtio pmd in next commits to calculate the checksum in software in case the protocol is not recognized. Signed-off-by: Olivier Matz --- doc/guides/rel_notes/release_16_11.rst | 5 +++ lib/librte_net/rte_ip.h | 60 ++++++++++++++++++++++++++++++++++ 2 files changed, 65 insertions(+) diff --git a/doc/guides/rel_notes/release_16_11.rst b/doc/guides/rel_notes/release_16_11.rst index 3d3c417..f29b44c 100644 --- a/doc/guides/rel_notes/release_16_11.rst +++ b/doc/guides/rel_notes/release_16_11.rst @@ -55,6 +55,11 @@ New Features Added two new functions ``rte_get_rx_ol_flag_list()`` and ``rte_get_tx_ol_flag_list()`` to dump offload flags as a string. +* **Added a functions to calculate the checksum of data in a mbuf.** + + Added a new function ``rte_raw_cksum_mbuf()`` to process the checksum of + data embedded in an mbuf chain. + Resolved Issues --------------- diff --git a/lib/librte_net/rte_ip.h b/lib/librte_net/rte_ip.h index 5b7554a..8499356 100644 --- a/lib/librte_net/rte_ip.h +++ b/lib/librte_net/rte_ip.h @@ -230,6 +230,66 @@ rte_raw_cksum(const void *buf, size_t len) } /** + * Compute the raw (non complemented) checksum of a packet. + * + * @param m + * The pointer to the mbuf. + * @param off + * The offset in bytes to start the checksum. + * @param len + * The length in bytes of the data to ckecksum. + */ +static inline uint16_t +rte_raw_cksum_mbuf(const struct rte_mbuf *m, uint32_t off, uint32_t len) +{ + const struct rte_mbuf *seg; + const char *buf; + uint32_t sum, tmp; + uint32_t seglen, done; + + /* easy case: all data in the first segment */ + if (off + len <= rte_pktmbuf_data_len(m)) + return rte_raw_cksum(rte_pktmbuf_mtod_offset(m, + const char *, off), len); + + if (off + len > rte_pktmbuf_pkt_len(m)) + return 0; /* invalid params, return a dummy value */ + + /* else browse the segment to find offset */ + seglen = 0; + for (seg = m; seg != NULL; seg = seg->next) { + seglen = rte_pktmbuf_data_len(seg); + if (off < seglen) + break; + off -= seglen; + } + seglen -= off; + buf = rte_pktmbuf_mtod_offset(seg, const char *, off); + if (seglen >= len) /* all in one segment */ + return rte_raw_cksum(buf, len); + + /* hard case: process checksum of several segments */ + sum = 0; + done = 0; + for (;;) { + tmp = __rte_raw_cksum(buf, seglen, 0); + if (done & 1) + tmp = rte_bswap16(tmp); + sum += tmp; + done += seglen; + if (done == len) + break; + seg = seg->next; + buf = rte_pktmbuf_mtod(seg, const char *); + seglen = rte_pktmbuf_data_len(seg); + if (seglen > len - done) + seglen = len - done; + } + + return __rte_raw_cksum_reduce(sum); +} + +/** * Process the IPv4 checksum of an IPv4 header. * * The checksum field must be set to 0 by the caller. -- 2.8.1