From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id C416342CE8; Sat, 17 Jun 2023 23:00:01 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id B8E744021E; Sat, 17 Jun 2023 22:59:59 +0200 (CEST) Received: from mail-vs1-f42.google.com (mail-vs1-f42.google.com [209.85.217.42]) by mails.dpdk.org (Postfix) with ESMTP id 8EEE94021D for ; Sat, 17 Jun 2023 22:59:58 +0200 (CEST) Received: by mail-vs1-f42.google.com with SMTP id ada2fe7eead31-43b1cee7e65so462604137.2 for ; Sat, 17 Jun 2023 13:59:58 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=networkplumber-org.20221208.gappssmtp.com; s=20221208; t=1687035598; x=1689627598; h=cc:to:subject:message-id:date:from:in-reply-to:references :mime-version:from:to:cc:subject:date:message-id:reply-to; bh=WjsV+9EFV/tf3GanoqUwdTo5BQJ8nP3U92c8b+FOyrQ=; b=1RNhAiNikl6k1Xv2jp9WBqYmHDBI2+HWdOLOJ3b9W3zJJ3s7+9NR/0p5g+im5ECYOk duuiS1Y3NgW1EbUxZTJqxZISNKgzTeUs/K3jJvhN628E5eEu8fUAAqsH8bOiKDH6Jwk4 mFW38R2Z+fMe4xS1AfPxBYXJgyBJD43pBUVpAJCQz003kgKDLXla4AsqX3VyaQLdnS4r 8bTECMHitq3vgLoKxyk8dfFH870RFIHoZXUyqBDpvFwlU41m+WEFV99+kisy623X3Smm 2Vmv8r2CrSgVNM+/cmK9o/V/D7juKAj/yC5Uv6e90IyXdb7Wnc/vZlGeB1oDf/5ujSdx U6hQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20221208; t=1687035598; x=1689627598; h=cc:to:subject:message-id:date:from:in-reply-to:references :mime-version:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=WjsV+9EFV/tf3GanoqUwdTo5BQJ8nP3U92c8b+FOyrQ=; b=dFdTzpiwbNKHVYDoP7D3hGIUqn7Ap31JepQhlVj278BnHaY6fd7aF+gXCKS0+EBiB0 kIZkJoygSx4mzBZxKWxHlkdkUjdQ1nuR9+X++/VSy0T/o8d4vsa6vWQm5Pt3gbh+yf/3 ZzzYFRM8GQ7pivPkuNmgv2PDYobnKJdrB/hgFiv2CEdHHFBg3IMMkCpHVAh5UZHB0YFU zP99UtGyNELDHPN4huj6cfPH5e02wbOs2yj9A6X8LCkCfhzkySLApssGXcfByE6oXO3x 1zSWEqEALEcNkpKJBBpPm3iNfWWUDYw8dqM/FUirmwCPe/rpm+iTxwfHR1R2O6QY3X/i 69Hw== X-Gm-Message-State: AC+VfDyNqsMa12ndwDrjeQgzRemt5cA7Ko9Bp9YZBckXKAbD21eK5vxM fcb/tATDQe+XgdQjQOJCZqL0ic6LbsV2jJq/L8aeNg== X-Google-Smtp-Source: ACHHUZ7cDThKY4O45hN9a0YgpdjFMGXfTm8K1Zig2cjpJ8gbSchiJTC6QPT9uM9RxihANkPZrDpbPw3zCmiTi9pXPWw= X-Received: by 2002:a1f:e406:0:b0:471:348a:7b8d with SMTP id b6-20020a1fe406000000b00471348a7b8dmr589630vkh.8.1687035597847; Sat, 17 Jun 2023 13:59:57 -0700 (PDT) MIME-Version: 1.0 References: <20230215103041.3861350-1-qobilidop@gmail.com> In-Reply-To: <20230215103041.3861350-1-qobilidop@gmail.com> From: Stephen Hemminger Date: Sat, 17 Jun 2023 14:59:47 -0600 Message-ID: Subject: Re: [PATCH] hash: add XOR32 hash function To: Bili Dong Cc: Yipeng Wang , dev , Cristian Dumitrescu Content-Type: multipart/alternative; boundary="000000000000888f4105fe599588" X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org --000000000000888f4105fe599588 Content-Type: text/plain; charset="UTF-8" Does it generate same hash as NIC than do it in HW? On Wed, Feb 15, 2023, 3:31 AM Bili Dong wrote: > An XOR32 hash is needed in the Software Switch (SWX) Pipeline for its > use case in P4. We implement it in this patch so it could be easily > registered in the pipeline later. > > Signed-off-by: Bili Dong > --- > .mailmap | 1 + > app/test/test_hash_functions.c | 33 +++++++++++++++-- > lib/hash/rte_hash_xor.h | 65 ++++++++++++++++++++++++++++++++++ > 3 files changed, 96 insertions(+), 3 deletions(-) > create mode 100644 lib/hash/rte_hash_xor.h > > diff --git a/.mailmap b/.mailmap > index 5015494210..176dd93b66 100644 > --- a/.mailmap > +++ b/.mailmap > @@ -159,6 +159,7 @@ Bernard Iremonger > Bert van Leeuwen > Bhagyada Modali > Bharat Mota > +Bili Dong > Bill Hong > Billy McFall > Billy O'Mahony > diff --git a/app/test/test_hash_functions.c > b/app/test/test_hash_functions.c > index 76d51b6e71..14d69d90c4 100644 > --- a/app/test/test_hash_functions.c > +++ b/app/test/test_hash_functions.c > @@ -15,6 +15,7 @@ > #include > #include > #include > +#include > > #include "test.h" > > @@ -22,8 +23,8 @@ > * Hash values calculated for key sizes from array "hashtest_key_lens" > * and for initial values from array "hashtest_initvals. > * Each key will be formed by increasing each byte by 1: > - * e.g.: key size = 4, key = 0x03020100 > - * key size = 8, key = 0x0706050403020100 > + * e.g.: key size = 4, key = 0x00010203 > + * key size = 8, key = 0x0001020304050607 > */ > static uint32_t hash_values_jhash[2][12] = {{ > 0x8ba9414b, 0xdf0d39c9, > @@ -51,6 +52,19 @@ static uint32_t hash_values_crc[2][12] = {{ > 0x789c104f, 0x53028d3e > } > }; > +static uint32_t hash_values_xor[2][12] = {{ > + 0x00000000, 0x00010000, > + 0x00010203, 0x04040404, 0x00000000, 0x00000000, > + 0x00000000, 0x00000000, 0x0c040404, 0x000d0e0f, > + 0x04212223, 0x04040404 > +}, > +{ > + 0xdeadbeef, 0xdeacbeef, > + 0xdeacbcec, 0xdaa9baeb, 0xdeadbeef, 0xdeadbeef, > + 0xdeadbeef, 0xdeadbeef, 0xd2a9baeb, 0xdea0b0e0, > + 0xda8c9ccc, 0xdaa9baeb > +} > +}; > > > /******************************************************************************* > * Hash function performance test configuration section. Each performance > test > @@ -61,7 +75,7 @@ static uint32_t hash_values_crc[2][12] = {{ > */ > #define HASHTEST_ITERATIONS 1000000 > #define MAX_KEYSIZE 64 > -static rte_hash_function hashtest_funcs[] = {rte_jhash, rte_hash_crc}; > +static rte_hash_function hashtest_funcs[] = {rte_jhash, rte_hash_crc, > rte_hash_xor}; > static uint32_t hashtest_initvals[] = {0, 0xdeadbeef}; > static uint32_t hashtest_key_lens[] = { > 1, 2, /* Unusual key sizes */ > @@ -85,6 +99,9 @@ get_hash_name(rte_hash_function f) > if (f == rte_hash_crc) > return "rte_hash_crc"; > > + if (f == rte_hash_xor) > + return "rte_hash_xor"; > + > return "UnknownHash"; > } > > @@ -173,6 +190,16 @@ verify_precalculated_hash_func_tests(void) > hash_values_crc[j][i], hash); > return -1; > } > + > + hash = rte_hash_xor(key, hashtest_key_lens[i], > + hashtest_initvals[j]); > + if (hash != hash_values_xor[j][i]) { > + printf("XOR for %u bytes with initial > value 0x%x." > + "Expected 0x%x, but got 0x%x\n", > + hashtest_key_lens[i], > hashtest_initvals[j], > + hash_values_xor[j][i], hash); > + return -1; > + } > } > } > > diff --git a/lib/hash/rte_hash_xor.h b/lib/hash/rte_hash_xor.h > new file mode 100644 > index 0000000000..61ca8bee73 > --- /dev/null > +++ b/lib/hash/rte_hash_xor.h > @@ -0,0 +1,65 @@ > +/* SPDX-License-Identifier: BSD-3-Clause > + * Copyright(c) 2023 Intel Corporation > + */ > + > +#ifndef _RTE_HASH_XOR_H_ > +#define _RTE_HASH_XOR_H_ > + > +/** > + * @file > + * > + * RTE XOR Hash > + */ > + > +#ifdef __cplusplus > +extern "C" { > +#endif > + > +#include > + > +#include > + > +#define LEFT8b_MASK rte_cpu_to_be_32(0xff000000) > +#define LEFT16b_MASK rte_cpu_to_be_32(0xffff0000) > + > +/** > + * Calculate XOR32 hash on user-supplied byte array. > + * > + * @param data > + * Data to perform hash on. > + * @param data_len > + * How many bytes to use to calculate hash value. > + * @param init_val > + * Value to initialise hash generator. > + * @return > + * 32bit calculated hash value. > + */ > +static inline uint32_t > +rte_hash_xor(const void *data, uint32_t data_len, uint32_t init_val) > +{ > + unsigned i; > + uintptr_t pd = (uintptr_t) data; > + init_val = rte_cpu_to_be_32(init_val); > + > + for (i = 0; i < data_len / 4; i++) { > + init_val ^= *(const uint32_t *)pd; > + pd += 4; > + } > + > + if (data_len & 0x2) { > + init_val ^= *(const uint32_t *)pd & LEFT16b_MASK; > + pd += 2; > + } > + > + if (data_len & 0x1) > + init_val ^= *(const uint32_t *)pd & LEFT8b_MASK; > + > + init_val = rte_be_to_cpu_32(init_val); > + return init_val; > +} > + > +#ifdef __cplusplus > +} > +#endif > + > +#endif /* _RTE_HASH_XOR_H_ */ > -- > 2.34.1 > > --000000000000888f4105fe599588 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: quoted-printable
Does it generate same hash as NIC than do it in HW?
=
On Wed= , Feb 15, 2023, 3:31 AM Bili Dong <qobilidop@gmail.com> wrote:
qobilidop@gmail.com>
---
=C2=A0.mailmap=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0|=C2=A0 1 +
=C2=A0app/test/test_hash_functions.c | 33 +++++++++++++++--
=C2=A0lib/hash/rte_hash_xor.h=C2=A0 =C2=A0 =C2=A0 =C2=A0 | 65 +++++++++++++= +++++++++++++++++++++
=C2=A03 files changed, 96 insertions(+), 3 deletions(-)
=C2=A0create mode 100644 lib/hash/rte_hash_xor.h

diff --git a/.mailmap b/.mailmap
index 5015494210..176dd93b66 100644
--- a/.mailmap
+++ b/.mailmap
@@ -159,6 +159,7 @@ Bernard Iremonger <bernard.iremonger@intel.= com>
=C2=A0Bert van Leeuwen <bert.vanleeuwen@netronome.com>=
=C2=A0Bhagyada Modali <bhagyada.modali@amd.com>
=C2=A0Bharat Mota <bmota@vmware.com>
+Bili Dong <qobilidop@gmail.com>
=C2=A0Bill Hong <bhong@brocade.com>
=C2=A0Billy McFall <bmcfall@redhat.com>
=C2=A0Billy O'Mahony <billy.o.mahony@intel.com>
diff --git a/app/test/test_hash_functions.c b/app/test/test_hash_functions.= c
index 76d51b6e71..14d69d90c4 100644
--- a/app/test/test_hash_functions.c
+++ b/app/test/test_hash_functions.c
@@ -15,6 +15,7 @@
=C2=A0#include <rte_hash.h>
=C2=A0#include <rte_jhash.h>
=C2=A0#include <rte_hash_crc.h>
+#include <rte_hash_xor.h>

=C2=A0#include "test.h"

@@ -22,8 +23,8 @@
=C2=A0 * Hash values calculated for key sizes from array "hashtest_key= _lens"
=C2=A0 * and for initial values from array "hashtest_initvals.
=C2=A0 * Each key will be formed by increasing each byte by 1:
- * e.g.: key size =3D 4, key =3D 0x03020100
- *=C2=A0 =C2=A0 =C2=A0 =C2=A0key size =3D 8, key =3D 0x0706050403020100 + * e.g.: key size =3D 4, key =3D 0x00010203
+ *=C2=A0 =C2=A0 =C2=A0 =C2=A0key size =3D 8, key =3D 0x0001020304050607 =C2=A0 */
=C2=A0static uint32_t hash_values_jhash[2][12] =3D {{
=C2=A0 =C2=A0 =C2=A0 =C2=A0 0x8ba9414b, 0xdf0d39c9,
@@ -51,6 +52,19 @@ static uint32_t hash_values_crc[2][12] =3D {{
=C2=A0 =C2=A0 =C2=A0 =C2=A0 0x789c104f, 0x53028d3e
=C2=A0}
=C2=A0};
+static uint32_t hash_values_xor[2][12] =3D {{
+=C2=A0 =C2=A0 =C2=A0 =C2=A00x00000000, 0x00010000,
+=C2=A0 =C2=A0 =C2=A0 =C2=A00x00010203, 0x04040404, 0x00000000, 0x00000000,=
+=C2=A0 =C2=A0 =C2=A0 =C2=A00x00000000, 0x00000000, 0x0c040404, 0x000d0e0f,=
+=C2=A0 =C2=A0 =C2=A0 =C2=A00x04212223, 0x04040404
+},
+{
+=C2=A0 =C2=A0 =C2=A0 =C2=A00xdeadbeef, 0xdeacbeef,
+=C2=A0 =C2=A0 =C2=A0 =C2=A00xdeacbcec, 0xdaa9baeb, 0xdeadbeef, 0xdeadbeef,=
+=C2=A0 =C2=A0 =C2=A0 =C2=A00xdeadbeef, 0xdeadbeef, 0xd2a9baeb, 0xdea0b0e0,=
+=C2=A0 =C2=A0 =C2=A0 =C2=A00xda8c9ccc, 0xdaa9baeb
+}
+};

=C2=A0/********************************************************************= ***********
=C2=A0 * Hash function performance test configuration section. Each perform= ance test
@@ -61,7 +75,7 @@ static uint32_t hash_values_crc[2][12] =3D {{
=C2=A0 */
=C2=A0#define HASHTEST_ITERATIONS 1000000
=C2=A0#define MAX_KEYSIZE 64
-static rte_hash_function hashtest_funcs[] =3D {rte_jhash, rte_hash_crc}; +static rte_hash_function hashtest_funcs[] =3D {rte_jhash, rte_hash_crc, rt= e_hash_xor};
=C2=A0static uint32_t hashtest_initvals[] =3D {0, 0xdeadbeef};
=C2=A0static uint32_t hashtest_key_lens[] =3D {
=C2=A0 =C2=A0 =C2=A0 =C2=A0 1, 2,=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 = =C2=A0 =C2=A0 =C2=A0/* Unusual key sizes */
@@ -85,6 +99,9 @@ get_hash_name(rte_hash_function f)
=C2=A0 =C2=A0 =C2=A0 =C2=A0 if (f =3D=3D rte_hash_crc)
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return "rte_ha= sh_crc";

+=C2=A0 =C2=A0 =C2=A0 =C2=A0if (f =3D=3D rte_hash_xor)
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0return "rte_ha= sh_xor";
+
=C2=A0 =C2=A0 =C2=A0 =C2=A0 return "UnknownHash";
=C2=A0}

@@ -173,6 +190,16 @@ verify_precalculated_hash_func_tests(void)
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0hash_valu= es_crc[j][i], hash);
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 return -1;
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 }
+
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0hash =3D rte_hash_xor(key, hashtest_key_lens[i],
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0hashtest_= initvals[j]);
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0if (hash !=3D hash_values_xor[j][i]) {
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0printf("XOR for %u bytes with in= itial value 0x%x."
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 "Expected = 0x%x, but got 0x%x\n",
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hashtest_key_le= ns[i], hashtest_initvals[j],
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 hash_values_xor= [j][i], hash);
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0return -1;
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0}
=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 }
=C2=A0 =C2=A0 =C2=A0 =C2=A0 }

diff --git a/lib/hash/rte_hash_xor.h b/lib/hash/rte_hash_xor.h
new file mode 100644
index 0000000000..61ca8bee73
--- /dev/null
+++ b/lib/hash/rte_hash_xor.h
@@ -0,0 +1,65 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright(c) 2023 Intel Corporation
+ */
+
+#ifndef _RTE_HASH_XOR_H_
+#define _RTE_HASH_XOR_H_
+
+/**
+ * @file
+ *
+ * RTE XOR Hash
+ */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <stdint.h>
+
+#include <rte_byteorder.h>
+
+#define LEFT8b_MASK rte_cpu_to_be_32(0xff000000)
+#define LEFT16b_MASK rte_cpu_to_be_32(0xffff0000)
+
+/**
+ * Calculate XOR32 hash on user-supplied byte array.
+ *
+ * @param data
+ *=C2=A0 =C2=A0Data to perform hash on.
+ * @param data_len
+ *=C2=A0 =C2=A0How many bytes to use to calculate hash value.
+ * @param init_val
+ *=C2=A0 =C2=A0Value to initialise hash generator.
+ * @return
+ *=C2=A0 =C2=A032bit calculated hash value.
+ */
+static inline uint32_t
+rte_hash_xor(const void *data, uint32_t data_len, uint32_t init_val)
+{
+=C2=A0 =C2=A0 =C2=A0 =C2=A0unsigned i;
+=C2=A0 =C2=A0 =C2=A0 =C2=A0uintptr_t pd =3D (uintptr_t) data;
+=C2=A0 =C2=A0 =C2=A0 =C2=A0init_val =3D rte_cpu_to_be_32(init_val);
+
+=C2=A0 =C2=A0 =C2=A0 =C2=A0for (i =3D 0; i < data_len / 4; i++) {
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0init_val ^=3D *(con= st uint32_t *)pd;
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0pd +=3D 4;
+=C2=A0 =C2=A0 =C2=A0 =C2=A0}
+
+=C2=A0 =C2=A0 =C2=A0 =C2=A0if (data_len & 0x2) {
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0init_val ^=3D *(con= st uint32_t *)pd & LEFT16b_MASK;
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0pd +=3D 2;
+=C2=A0 =C2=A0 =C2=A0 =C2=A0}
+
+=C2=A0 =C2=A0 =C2=A0 =C2=A0if (data_len & 0x1)
+=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0init_val ^=3D *(con= st uint32_t *)pd & LEFT8b_MASK;
+
+=C2=A0 =C2=A0 =C2=A0 =C2=A0init_val =3D rte_be_to_cpu_32(init_val);
+=C2=A0 =C2=A0 =C2=A0 =C2=A0return init_val;
+}
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _RTE_HASH_XOR_H_ */
--
2.34.1

--000000000000888f4105fe599588--