DPDK patches and discussions
 help / color / mirror / Atom feed
From: David Marchand <david.marchand@redhat.com>
To: Huichao Cai <chcchc88@163.com>,
	Konstantin Ananyev <konstantin.v.ananyev@yandex.ru>
Cc: dev <dev@dpdk.org>, Thomas Monjalon <thomas@monjalon.net>,
	 Stephen Hemminger <stephen@networkplumber.org>
Subject: Re: [PATCH v7] ip_frag: add IPv4 options fragment and test data
Date: Thu, 16 Jun 2022 17:10:46 +0200	[thread overview]
Message-ID: <CAJFAV8yA7VfqZfr4eBKJmtPC6z=Po9DM-0k=D-2BrejC0T9Q0Q@mail.gmail.com> (raw)
In-Reply-To: <1649993210-1854-1-git-send-email-chcchc88@163.com>

On Fri, Apr 15, 2022 at 5:27 AM Huichao Cai <chcchc88@163.com> wrote:
>
> According to RFC791,the options may appear or not in datagrams.
> They must be implemented by all IP modules (host and gateways).
> What is optional is their transmission in any particular datagram,
> not their implementation.So we have to deal with it during the
> fragmenting process.Add some test data for the IPv4 header optional
> field fragmenting.
>
> Signed-off-by: Huichao Cai <chcchc88@163.com>

gcc-12 raises warnings on both the unit test code and the library code.
See below.

> ---
>  app/test/test_ipfrag.c               | 219 ++++++++++++++++++++++++++++++++---
>  lib/ip_frag/rte_ipv4_fragmentation.c |  70 ++++++++++-
>  lib/net/rte_ip.h                     |   6 +
>  3 files changed, 272 insertions(+), 23 deletions(-)
>
> diff --git a/app/test/test_ipfrag.c b/app/test/test_ipfrag.c
> index 1ced25a..610a86b 100644
> --- a/app/test/test_ipfrag.c
> +++ b/app/test/test_ipfrag.c
> @@ -18,10 +18,50 @@
>  #define NUM_MBUFS 128
>  #define BURST 32
>
> +uint8_t expected_first_frag_ipv4_opts_copied[] = {
> +       0x07, 0x0b, 0x04, 0x00,
> +       0x00, 0x00, 0x00, 0x00,
> +       0x00, 0x00, 0x00, 0x83,
> +       0x07, 0x04, 0xc0, 0xa8,
> +       0xe3, 0x96, 0x00, 0x00,
> +};
> +
> +uint8_t expected_sub_frag_ipv4_opts_copied[] = {
> +       0x83, 0x07, 0x04, 0xc0,
> +       0xa8, 0xe3, 0x96, 0x00,
> +};
> +
> +uint8_t expected_first_frag_ipv4_opts_nocopied[] = {
> +       0x07, 0x0b, 0x04, 0x00,
> +       0x00, 0x00, 0x00, 0x00,
> +       0x00, 0x00, 0x00, 0x00,
> +};
> +
> +uint8_t expected_sub_frag_ipv4_opts_nocopied[0];
> +
> +struct test_opt_data {
> +       bool is_first_frag;              /**< offset is 0 */
> +       bool opt_copied;                 /**< ip option copied flag */
> +       uint16_t len;                    /**< option data len */
> +       uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
> +};
> +
>  static struct rte_mempool *pkt_pool,
>                           *direct_pool,
>                           *indirect_pool;
>
> +static inline void
> +hex_to_str(uint8_t *hex, uint16_t len, char *str)
> +{
> +       int i;
> +
> +       for (i = 0; i < len; i++) {
> +               sprintf(str, "%02x", hex[i]);
> +               str += 2;
> +       }
> +       *str = 0;
> +}
> +
>  static int
>  setup_buf_pool(void)
>  {
> @@ -88,23 +128,67 @@ static void ut_teardown(void)
>  {
>  }
>
> +static inline void
> +test_get_ipv4_opt(bool is_first_frag, bool opt_copied,
> +       struct test_opt_data *expected_opt)
> +{
> +       if (is_first_frag) {
> +               if (opt_copied) {
> +                       expected_opt->len =
> +                               sizeof(expected_first_frag_ipv4_opts_copied);
> +                       rte_memcpy(expected_opt->data,
> +                               expected_first_frag_ipv4_opts_copied,
> +                               sizeof(expected_first_frag_ipv4_opts_copied));
> +               } else {
> +                       expected_opt->len =
> +                               sizeof(expected_first_frag_ipv4_opts_nocopied);
> +                       rte_memcpy(expected_opt->data,
> +                               expected_first_frag_ipv4_opts_nocopied,
> +                               sizeof(expected_first_frag_ipv4_opts_nocopied));
> +               }
> +       } else {
> +               if (opt_copied) {
> +                       expected_opt->len =
> +                               sizeof(expected_sub_frag_ipv4_opts_copied);
> +                       rte_memcpy(expected_opt->data,
> +                               expected_sub_frag_ipv4_opts_copied,
> +                               sizeof(expected_sub_frag_ipv4_opts_copied));
> +               } else {
> +                       expected_opt->len =
> +                               sizeof(expected_sub_frag_ipv4_opts_nocopied);
> +                       rte_memcpy(expected_opt->data,
> +                               expected_sub_frag_ipv4_opts_nocopied,
> +                               sizeof(expected_sub_frag_ipv4_opts_nocopied));
> +               }
> +       }
> +}
> +
>  static void
> -v4_allocate_packet_of(struct rte_mbuf *b, int fill,
> -                     size_t s, int df, uint8_t mf, uint16_t off,
> -                     uint8_t ttl, uint8_t proto, uint16_t pktid)
> +v4_allocate_packet_of(struct rte_mbuf *b, int fill, size_t s,
> +       int df, uint8_t mf, uint16_t off, uint8_t ttl, uint8_t proto,
> +       uint16_t pktid, bool have_opt, bool is_first_frag, bool opt_copied)
>  {
>         /* Create a packet, 2k bytes long */
>         b->data_off = 0;
>         char *data = rte_pktmbuf_mtod(b, char *);
> -       rte_be16_t fragment_offset = 0; /**< fragmentation offset */
> +       rte_be16_t fragment_offset = 0; /* fragmentation offset */
> +       uint16_t iph_len;
> +       struct test_opt_data opt;
> +
> +       opt.len = 0;
> +
> +       if (have_opt)
> +               test_get_ipv4_opt(is_first_frag, opt_copied, &opt);


FAILED: app/test/dpdk-test.p/test_ipfrag.c.o
ccache gcc -Iapp/test/dpdk-test.p -Iapp/test -I../app/test -I. -I..
-Iconfig -I../config -Ilib/eal/include -I../lib/eal/include
-Ilib/eal/linux/include -I../lib/eal/linux/include
-Ilib/eal/x86/include -I../lib/eal/x86/include -Ilib/kvargs
-I../lib/kvargs -Ilib/metrics -I../lib/metrics -Ilib/telemetry
-I../lib/telemetry -Ilib/eal/common -I../lib/eal/common -Ilib/eal
-I../lib/eal -Ilib/ring -I../lib/ring -Ilib/rcu -I../lib/rcu
-Ilib/mempool -I../lib/mempool -Ilib/mbuf -I../lib/mbuf -Ilib/net
-I../lib/net -Ilib/meter -I../lib/meter -Ilib/ethdev -I../lib/ethdev
-Ilib/pci -I../lib/pci -Ilib/cmdline -I../lib/cmdline -Ilib/hash
-I../lib/hash -Ilib/timer -I../lib/timer -Ilib/acl -I../lib/acl
-Ilib/bbdev -I../lib/bbdev -Ilib/bitratestats -I../lib/bitratestats
-Ilib/bpf -I../lib/bpf -Ilib/cfgfile -I../lib/cfgfile
-Ilib/compressdev -I../lib/compressdev -Ilib/cryptodev
-I../lib/cryptodev -Ilib/distributor -I../lib/distributor -Ilib/efd
-I../lib/efd -Ilib/eventdev -I../lib/eventdev -Ilib/gpudev
-I../lib/gpudev -Ilib/gro -I../lib/gro -Ilib/gso -I../lib/gso
-Ilib/ip_frag -I../lib/ip_frag -Ilib/jobstats -I../lib/jobstats
-Ilib/kni -I../lib/kni -Ilib/latencystats -I../lib/latencystats
-Ilib/lpm -I../lib/lpm -Ilib/member -I../lib/member -Ilib/pcapng
-I../lib/pcapng -Ilib/power -I../lib/power -Ilib/rawdev
-I../lib/rawdev -Ilib/regexdev -I../lib/regexdev -Ilib/dmadev
-I../lib/dmadev -Ilib/rib -I../lib/rib -Ilib/reorder -I../lib/reorder
-Ilib/sched -I../lib/sched -Ilib/security -I../lib/security
-Ilib/stack -I../lib/stack -Ilib/vhost -I../lib/vhost -Ilib/ipsec
-I../lib/ipsec -Ilib/fib -I../lib/fib -Ilib/port -I../lib/port
-Ilib/pdump -I../lib/pdump -Ilib/table -I../lib/table -Ilib/pipeline
-I../lib/pipeline -Ilib/flow_classify -I../lib/flow_classify
-Ilib/graph -I../lib/graph -Ilib/node -I../lib/node -Idrivers/bus/pci
-I../drivers/bus/pci -I../drivers/bus/pci/linux -Idrivers/bus/vdev
-I../drivers/bus/vdev -Idrivers/mempool/ring -I../drivers/mempool/ring
-Idrivers/mempool/stack -I../drivers/mempool/stack
-Idrivers/event/skeleton -I../drivers/event/skeleton
-Idrivers/net/bonding -I../drivers/net/bonding -Idrivers/net/ring
-I../drivers/net/ring -Idrivers/net/null -I../drivers/net/null
-Idrivers/crypto/scheduler -I../drivers/crypto/scheduler
-fdiagnostics-color=always -D_FILE_OFFSET_BITS=64 -Wall -Winvalid-pch
-Wextra -Werror -O3 -include rte_config.h -Wcast-qual -Wdeprecated
-Wformat -Wformat-nonliteral -Wformat-security -Wmissing-declarations
-Wmissing-prototypes -Wnested-externs -Wold-style-definition
-Wpointer-arith -Wsign-compare -Wstrict-prototypes -Wundef
-Wwrite-strings -Wno-address-of-packed-member -Wno-packed-not-aligned
-Wno-missing-field-initializers -Wno-zero-length-bounds -D_GNU_SOURCE
-march=native -DALLOW_EXPERIMENTAL_API -Wno-format-truncation
-fno-strict-aliasing -DALLOW_INTERNAL_API -MD -MQ
app/test/dpdk-test.p/test_ipfrag.c.o -MF
app/test/dpdk-test.p/test_ipfrag.c.o.d -o
app/test/dpdk-test.p/test_ipfrag.c.o -c ../app/test/test_ipfrag.c
In file included from
/usr/lib/gcc/x86_64-redhat-linux/12/include/immintrin.h:43,
                 from
/usr/lib/gcc/x86_64-redhat-linux/12/include/x86intrin.h:32,
                 from ../lib/eal/x86/include/rte_vect.h:31,
                 from ../lib/eal/x86/include/rte_memcpy.h:17,
                 from ../lib/mempool/rte_mempool.h:46,
                 from ../lib/mbuf/rte_mbuf.h:38,
                 from ../lib/net/rte_ip.h:32,
                 from ../app/test/test_ipfrag.c:12:
In function ‘_mm256_loadu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:346:9,
    inlined from ‘rte_mov128’ at ../lib/eal/x86/include/rte_memcpy.h:369:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:445:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘v4_allocate_packet_of’ at ../app/test/test_ipfrag.c:230:2,
    inlined from ‘test_ip_frag’ at ../app/test/test_ipfrag.c:402:4:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:929:10: error:
array subscript ‘__m256i_u[1]’ is partly outside array bounds of
‘struct test_opt_data[1]’ [-Werror=array-bounds]
  929 |   return *__P;
      |          ^~~~
../app/test/test_ipfrag.c: In function ‘test_ip_frag’:
../app/test/test_ipfrag.c:187:30: note: at offset 36 into object ‘opt’
of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
In function ‘_mm256_loadu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:346:9,
    inlined from ‘rte_mov128’ at ../lib/eal/x86/include/rte_memcpy.h:370:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:445:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘v4_allocate_packet_of’ at ../app/test/test_ipfrag.c:230:2,
    inlined from ‘test_ip_frag’ at ../app/test/test_ipfrag.c:402:4:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:929:10: error:
array subscript 2 is outside array bounds of ‘struct test_opt_data[1]’
[-Werror=array-bounds]
  929 |   return *__P;
      |          ^~~~
../app/test/test_ipfrag.c: In function ‘test_ip_frag’:
../app/test/test_ipfrag.c:187:30: note: at offset 68 into object ‘opt’
of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
In function ‘_mm256_loadu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:346:9,
    inlined from ‘rte_mov128’ at ../lib/eal/x86/include/rte_memcpy.h:371:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:445:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘v4_allocate_packet_of’ at ../app/test/test_ipfrag.c:230:2,
    inlined from ‘test_ip_frag’ at ../app/test/test_ipfrag.c:402:4:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:929:10: error:
array subscript 3 is outside array bounds of ‘struct test_opt_data[1]’
[-Werror=array-bounds]
  929 |   return *__P;
      |          ^~~~
../app/test/test_ipfrag.c: In function ‘test_ip_frag’:
../app/test/test_ipfrag.c:187:30: note: at offset 100 into object
‘opt’ of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
In function ‘_mm256_loadu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:346:9,
    inlined from ‘rte_mov64’ at ../lib/eal/x86/include/rte_memcpy.h:358:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:452:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘v4_allocate_packet_of’ at ../app/test/test_ipfrag.c:230:2,
    inlined from ‘test_ip_frag’ at ../app/test/test_ipfrag.c:402:4:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:929:10: error:
array subscript ‘__m256i_u[1]’ is partly outside array bounds of
‘const void[44]’ [-Werror=array-bounds]
  929 |   return *__P;
      |          ^~~~
../app/test/test_ipfrag.c: In function ‘test_ip_frag’:
../app/test/test_ipfrag.c:57:17: note: at offset 36 into object ‘data’
of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
../app/test/test_ipfrag.c:57:17: note: at offset [37, 40] into object
‘data’ of size 40
../app/test/test_ipfrag.c:187:30: note: at offset 168 into object
‘opt’ of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
../app/test/test_ipfrag.c:57:17: note: at offset 36 into object ‘data’
of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
In function ‘_mm256_loadu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:346:9,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:457:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘v4_allocate_packet_of’ at ../app/test/test_ipfrag.c:230:2,
    inlined from ‘test_ip_frag’ at ../app/test/test_ipfrag.c:402:4:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:929:10: error:
array subscript [2, 2051] is outside array bounds of ‘const void[44]’
[-Werror=array-bounds]
  929 |   return *__P;
      |          ^~~~
../app/test/test_ipfrag.c: In function ‘test_ip_frag’:
../app/test/test_ipfrag.c:57:17: note: at offset [4, 40] into object
‘data’ of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
../app/test/test_ipfrag.c:57:17: note: at offset [5, 40] into object
‘data’ of size 40
../app/test/test_ipfrag.c:187:30: note: at offset [136, 200] into
object ‘opt’ of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
../app/test/test_ipfrag.c:57:17: note: at offset [4, 40] into object
‘data’ of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
../app/test/test_ipfrag.c:57:17: note: at offset [5, 40] into object
‘data’ of size 40
../app/test/test_ipfrag.c:187:30: note: at offset [136, 200] into
object ‘opt’ of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
../app/test/test_ipfrag.c:57:17: note: at offset [4, 40] into object
‘data’ of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
In function ‘_mm256_loadu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:346:9,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:458:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘v4_allocate_packet_of’ at ../app/test/test_ipfrag.c:230:2,
    inlined from ‘test_ip_frag’ at ../app/test/test_ipfrag.c:402:4:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:929:10: error:
array subscript [2, 2052] is outside array bounds of ‘const void[44]’
[-Werror=array-bounds]
  929 |   return *__P;
      |          ^~~~
../app/test/test_ipfrag.c: In function ‘test_ip_frag’:
../app/test/test_ipfrag.c:57:17: note: at offset [5, 40] into object
‘data’ of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
../app/test/test_ipfrag.c:57:17: note: at offset [6, 40] into object
‘data’ of size 40
../app/test/test_ipfrag.c:187:30: note: at offset [137, 201] into
object ‘opt’ of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
../app/test/test_ipfrag.c:57:17: note: at offset [5, 40] into object
‘data’ of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
../app/test/test_ipfrag.c:57:17: note: at offset [6, 40] into object
‘data’ of size 40
../app/test/test_ipfrag.c:187:30: note: at offset [137, 201] into
object ‘opt’ of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
../app/test/test_ipfrag.c:57:17: note: at offset [5, 40] into object
‘data’ of size 40
   57 |         uint8_t data[RTE_IPV4_HDR_OPT_MAX_LEN]; /**< option data */
      |                 ^~~~
In function ‘_mm256_loadu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:346:9,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:438:3,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘v4_allocate_packet_of’ at ../app/test/test_ipfrag.c:230:2,
    inlined from ‘test_ip_frag’ at ../app/test/test_ipfrag.c:402:4:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:929:10: error:
array subscript ‘__m256i_u[0]’ is partly outside array bounds of
‘struct test_opt_data[1]’ [-Werror=array-bounds]
  929 |   return *__P;
      |          ^~~~
../app/test/test_ipfrag.c: In function ‘test_ip_frag’:
../app/test/test_ipfrag.c:187:30: note: at offset [21, 36] into object
‘opt’ of size 44
  187 |         struct test_opt_data opt;
      |                              ^~~
cc1: all warnings being treated as errors
ninja: build stopped: subcommand failed.


>
> -       memset(data, fill, sizeof(struct rte_ipv4_hdr) + s);
> +       iph_len = sizeof(struct rte_ipv4_hdr) + opt.len;
> +       memset(data, fill, iph_len + s);
>
>         struct rte_ipv4_hdr *hdr = (struct rte_ipv4_hdr *)data;
>
> -       hdr->version_ihl = 0x45; /* standard IP header... */
> +       hdr->version_ihl = 0x40; /* ipv4 */
> +       hdr->version_ihl += (iph_len / 4);
>         hdr->type_of_service = 0;
> -       b->pkt_len = s + sizeof(struct rte_ipv4_hdr);
> +       b->pkt_len = s + iph_len;
>         b->data_len = b->pkt_len;
>         hdr->total_length = rte_cpu_to_be_16(b->pkt_len);
>         hdr->packet_id = rte_cpu_to_be_16(pktid);
> @@ -131,6 +215,8 @@ static void ut_teardown(void)
>         hdr->hdr_checksum = 0;
>         hdr->src_addr = rte_cpu_to_be_32(0x8080808);
>         hdr->dst_addr = rte_cpu_to_be_32(0x8080404);
> +
> +       rte_memcpy(hdr + 1, opt.data, opt.len);
>  }
>
>  static void
> @@ -187,6 +273,45 @@ static void ut_teardown(void)
>         }
>  }
>
> +static inline void
> +test_get_frag_opt(struct rte_mbuf **mb, int32_t num,
> +       struct test_opt_data *opt, int ipv, bool opt_copied)
> +{
> +       int32_t i;
> +
> +       for (i = 0; i < num; i++) {
> +               if (ipv == 4) {
> +                       struct rte_ipv4_hdr *iph =
> +                           rte_pktmbuf_mtod(mb[i], struct rte_ipv4_hdr *);
> +                       uint16_t header_len = (iph->version_ihl &
> +                               RTE_IPV4_HDR_IHL_MASK) *
> +                               RTE_IPV4_IHL_MULTIPLIER;
> +                       uint16_t opt_len = header_len -
> +                               sizeof(struct rte_ipv4_hdr);
> +
> +                       opt->opt_copied = opt_copied;
> +
> +                       if ((rte_be_to_cpu_16(iph->fragment_offset) &
> +                                   RTE_IPV4_HDR_OFFSET_MASK) == 0)
> +                               opt->is_first_frag = true;
> +                       else
> +                               opt->is_first_frag = false;
> +
> +                       if (likely(opt_len <= RTE_IPV4_HDR_OPT_MAX_LEN)) {
> +                               char *iph_opt = rte_pktmbuf_mtod_offset(mb[i],
> +                                   char *, sizeof(struct rte_ipv4_hdr));
> +                               opt->len = opt_len;
> +                               rte_memcpy(opt->data, iph_opt, opt_len);
> +                       } else {
> +                               opt->len = RTE_IPV4_HDR_OPT_MAX_LEN;
> +                               memset(opt->data, RTE_IPV4_HDR_OPT_EOL,
> +                                   sizeof(opt->data));
> +                       }
> +                       opt++;
> +               }
> +       }
> +}
> +
>  static int
>  test_ip_frag(void)
>  {
> @@ -206,32 +331,52 @@ static void ut_teardown(void)
>                 uint16_t pkt_id;
>                 int      expected_frags;
>                 uint16_t expected_fragment_offset[BURST];
> +               bool have_opt;
> +               bool is_first_frag;
> +               bool opt_copied;
>         } tests[] = {
>                  {4, 1280, 1400, 0, 0, 0, 64, IPPROTO_ICMP, RND_ID,       2,
> -                 {0x2000, 0x009D}},
> +                 {0x2000, 0x009D}, false},
>                  {4, 1280, 1400, 0, 0, 0, 64, IPPROTO_ICMP, 0,            2,
> -                 {0x2000, 0x009D}},
> +                 {0x2000, 0x009D}, false},
>                  {4,  600, 1400, 0, 0, 0, 64, IPPROTO_ICMP, RND_ID,       3,
> -                 {0x2000, 0x2048, 0x0090}},
> +                 {0x2000, 0x2048, 0x0090}, false},
>                  {4, 4, 1400, 0, 0, 0, 64, IPPROTO_ICMP, RND_ID,    -EINVAL},
>                  {4, 600, 1400, 1, 0, 0, 64, IPPROTO_ICMP, RND_ID, -ENOTSUP},
>                  {4, 600, 1400, 0, 0, 0, 0, IPPROTO_ICMP, RND_ID,         3,
> -                 {0x2000, 0x2048, 0x0090}},
> +                 {0x2000, 0x2046, 0x008C}, true, true, true},
> +                /* The first fragment */
> +                {4, 68, 104, 0, 1, 0, 0, IPPROTO_ICMP, RND_ID,           5,
> +                 {0x2000, 0x2003, 0x2006, 0x2009, 0x200C}, true, true, true},
> +                /* The middle fragment */
>                  {4, 68, 104, 0, 1, 13, 0, IPPROTO_ICMP, RND_ID,          3,
> -                 {0x200D, 0x2013, 0x2019}},
> -
> +                 {0x200D, 0x2012, 0x2017}, true, false, true},
> +                /* The last fragment */
> +                {4, 68, 104, 0, 0, 26, 0, IPPROTO_ICMP, RND_ID,          3,
> +                 {0x201A, 0x201F, 0x0024}, true, false, true},
> +                /* The first fragment */
> +                {4, 68, 104, 0, 1, 0, 0, IPPROTO_ICMP, RND_ID,           4,
> +                 {0x2000, 0x2004, 0x2008, 0x200C}, true, true, false},
> +                /* The middle fragment */
> +                {4, 68, 104, 0, 1, 13, 0, IPPROTO_ICMP, RND_ID,          3,
> +                 {0x200D, 0x2013, 0x2019}, true, false, false},
> +                /* The last fragment */
> +                {4, 68, 104, 0, 0, 26, 0, IPPROTO_ICMP, RND_ID,          3,
> +                 {0x201A, 0x2020, 0x0026}, true, false, false},
>                  {6, 1280, 1400, 0, 0, 0, 64, IPPROTO_ICMP, RND_ID,       2,
> -                 {0x0001, 0x04D0}},
> +                 {0x0001, 0x04D0}, false},
>                  {6, 1300, 1400, 0, 0, 0, 64, IPPROTO_ICMP, RND_ID,       2,
> -                 {0x0001, 0x04E0}},
> +                 {0x0001, 0x04E0}, false},
>                  {6, 4, 1400, 0, 0, 0, 64, IPPROTO_ICMP, RND_ID,    -EINVAL},
>                  {6, 1300, 1400, 0, 0, 0, 0, IPPROTO_ICMP, RND_ID,        2,
> -                 {0x0001, 0x04E0}},
> +                 {0x0001, 0x04E0}, false},
>         };
>
>         for (i = 0; i < RTE_DIM(tests); i++) {
>                 int32_t len = 0;
>                 uint16_t fragment_offset[BURST];
> +               struct test_opt_data opt_res[BURST];
> +               struct test_opt_data opt_exp;
>                 uint16_t pktid = tests[i].pkt_id;
>                 struct rte_mbuf *pkts_out[BURST];
>                 struct rte_mbuf *b = rte_pktmbuf_alloc(pkt_pool);
> @@ -250,7 +395,10 @@ static void ut_teardown(void)
>                                               tests[i].set_of,
>                                               tests[i].ttl,
>                                               tests[i].proto,
> -                                             pktid);
> +                                             pktid,
> +                                             tests[i].have_opt,
> +                                             tests[i].is_first_frag,
> +                                             tests[i].opt_copied);
>                 } else if (tests[i].ipv == 6) {
>                         v6_allocate_packet_of(b, 0x41414141,
>                                               tests[i].pkt_size,
> @@ -275,17 +423,20 @@ static void ut_teardown(void)
>                 if (len > 0) {
>                         test_get_offset(pkts_out, len,
>                             fragment_offset, tests[i].ipv);
> +                       if (tests[i].have_opt)
> +                               test_get_frag_opt(pkts_out, len, opt_res,
> +                                       tests[i].ipv, tests[i].opt_copied);
>                         test_free_fragments(pkts_out, len);
>                 }
>
> -               printf("%zd: checking %d with %d\n", i, len,
> +               printf("[check frag number]%zd: checking %d with %d\n", i, len,
>                        tests[i].expected_frags);
>                 RTE_TEST_ASSERT_EQUAL(len, tests[i].expected_frags,
>                                       "Failed case %zd.\n", i);
>
>                 if (len > 0) {
>                         for (j = 0; j < (size_t)len; j++) {
> -                               printf("%zd-%zd: checking %d with %d\n",
> +                               printf("[check offset]%zd-%zd: checking %d with %d\n",
>                                     i, j, fragment_offset[j],
>                                     rte_cpu_to_be_16(
>                                         tests[i].expected_fragment_offset[j]));
> @@ -294,6 +445,36 @@ static void ut_teardown(void)
>                                         tests[i].expected_fragment_offset[j]),
>                                     "Failed case %zd.\n", i);
>                         }
> +
> +                       if (tests[i].have_opt && (tests[i].ipv == 4)) {
> +                               for (j = 0; j < (size_t)len; j++) {
> +                                       char opt_res_str[2 *
> +                                               RTE_IPV4_HDR_OPT_MAX_LEN + 1];
> +                                       char opt_exp_str[2 *
> +                                               RTE_IPV4_HDR_OPT_MAX_LEN + 1];
> +
> +                                       test_get_ipv4_opt(
> +                                               opt_res[j].is_first_frag,
> +                                               opt_res[j].opt_copied,
> +                                               &opt_exp);
> +                                       hex_to_str(opt_res[j].data,
> +                                               opt_res[j].len,
> +                                               opt_res_str);
> +                                       hex_to_str(opt_exp.data,
> +                                               opt_exp.len,
> +                                               opt_exp_str);
> +
> +                                       printf(
> +                                               "[check ipv4 option]%zd-%zd: checking (len:%u)%s with (len:%u)%s\n",
> +                                               i, j,
> +                                               opt_res[j].len, opt_res_str,
> +                                               opt_exp.len, opt_exp_str);
> +                                               RTE_TEST_ASSERT_SUCCESS(
> +                                                       strcmp(opt_res_str,
> +                                                               opt_exp_str),
> +                                               "Failed case %zd.\n", i);
> +                               }
> +                       }
>                 }
>
>         }
> diff --git a/lib/ip_frag/rte_ipv4_fragmentation.c b/lib/ip_frag/rte_ipv4_fragmentation.c
> index 2e7739d..a562424 100644
> --- a/lib/ip_frag/rte_ipv4_fragmentation.c
> +++ b/lib/ip_frag/rte_ipv4_fragmentation.c
> @@ -22,6 +22,8 @@
>
>  #define        IPV4_HDR_FO_ALIGN                       (1 << RTE_IPV4_HDR_FO_SHIFT)
>
> +#define IPV4_HDR_MAX_LEN                       60
> +
>  static inline void __fill_ipv4hdr_frag(struct rte_ipv4_hdr *dst,
>                 const struct rte_ipv4_hdr *src, uint16_t header_len,
>                 uint16_t len, uint16_t fofs, uint16_t dofs, uint32_t mf)
> @@ -41,6 +43,49 @@ static inline void __free_fragments(struct rte_mbuf *mb[], uint32_t num)
>                 rte_pktmbuf_free(mb[i]);
>  }
>
> +static inline uint16_t __create_ipopt_frag_hdr(uint8_t *iph,
> +       uint16_t ipopt_len, uint8_t *ipopt_frag_hdr)
> +{
> +       uint16_t len = ipopt_len;
> +       struct rte_ipv4_hdr *iph_opt = (struct rte_ipv4_hdr *)ipopt_frag_hdr;
> +
> +       ipopt_len = 0;
> +       rte_memcpy(ipopt_frag_hdr, iph, sizeof(struct rte_ipv4_hdr));
> +       ipopt_frag_hdr += sizeof(struct rte_ipv4_hdr);
> +
> +       uint8_t *p_opt = iph + sizeof(struct rte_ipv4_hdr);
> +
> +       while (len > 0) {
> +               if (unlikely(*p_opt == RTE_IPV4_HDR_OPT_NOP)) {
> +                       len--;
> +                       p_opt++;
> +                       continue;
> +               } else if (unlikely(*p_opt == RTE_IPV4_HDR_OPT_EOL))
> +                       break;
> +
> +               if (unlikely(p_opt[1] < 2 || p_opt[1] > len))
> +                       break;
> +
> +               if (RTE_IPV4_HDR_OPT_COPIED(*p_opt)) {
> +                       rte_memcpy(ipopt_frag_hdr + ipopt_len,
> +                               p_opt, p_opt[1]);
> +                       ipopt_len += p_opt[1];
> +               }
> +
> +               len -= p_opt[1];
> +               p_opt += p_opt[1];
> +       }
> +
> +       len = RTE_ALIGN_CEIL(ipopt_len, RTE_IPV4_IHL_MULTIPLIER);
> +       memset(ipopt_frag_hdr + ipopt_len,
> +               RTE_IPV4_HDR_OPT_EOL, len - ipopt_len);
> +       ipopt_len = len;
> +       iph_opt->ihl = (sizeof(struct rte_ipv4_hdr) + ipopt_len) /
> +               RTE_IPV4_IHL_MULTIPLIER;
> +
> +       return ipopt_len;
> +}
> +
>  /**
>   * IPv4 fragmentation.
>   *
> @@ -76,6 +121,8 @@ static inline void __free_fragments(struct rte_mbuf *mb[], uint32_t num)
>         uint32_t more_in_segs;
>         uint16_t fragment_offset, flag_offset, frag_size, header_len;
>         uint16_t frag_bytes_remaining;
> +       uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
> +       uint16_t ipopt_len;
>
>         /*
>          * Formal parameter checking.
> @@ -118,6 +165,10 @@ static inline void __free_fragments(struct rte_mbuf *mb[], uint32_t num)
>         out_pkt_pos = 0;
>         fragment_offset = 0;
>
> +       ipopt_len = header_len - sizeof(struct rte_ipv4_hdr);
> +       if (unlikely(ipopt_len > RTE_IPV4_HDR_OPT_MAX_LEN))
> +               return -EINVAL;
> +
>         more_in_segs = 1;
>         while (likely(more_in_segs)) {
>                 struct rte_mbuf *out_pkt = NULL, *out_seg_prev = NULL;
> @@ -188,10 +239,21 @@ static inline void __free_fragments(struct rte_mbuf *mb[], uint32_t num)
>                     (uint16_t)out_pkt->pkt_len,
>                     flag_offset, fragment_offset, more_in_segs);
>
> -               fragment_offset = (uint16_t)(fragment_offset +
> -                   out_pkt->pkt_len - header_len);
> -
> -               out_pkt->l3_len = header_len;
> +               if (unlikely((fragment_offset == 0) && (ipopt_len) &&
> +                           ((flag_offset & RTE_IPV4_HDR_OFFSET_MASK) == 0))) {
> +                       ipopt_len = __create_ipopt_frag_hdr((uint8_t *)in_hdr,
> +                               ipopt_len, ipopt_frag_hdr);
> +                       fragment_offset = (uint16_t)(fragment_offset +
> +                               out_pkt->pkt_len - header_len);
> +                       out_pkt->l3_len = header_len;
> +
> +                       header_len = sizeof(struct rte_ipv4_hdr) + ipopt_len;
> +                       in_hdr = (struct rte_ipv4_hdr *)ipopt_frag_hdr;
> +               } else {
> +                       fragment_offset = (uint16_t)(fragment_offset +
> +                               out_pkt->pkt_len - header_len);
> +                       out_pkt->l3_len = header_len;
> +               }

FAILED: lib/librte_ip_frag.a.p/ip_frag_rte_ipv4_fragmentation.c.o
ccache gcc -Ilib/librte_ip_frag.a.p -Ilib -I../lib -Ilib/ip_frag
-I../lib/ip_frag -I. -I.. -Iconfig -I../config -Ilib/eal/include
-I../lib/eal/include -Ilib/eal/linux/include
-I../lib/eal/linux/include -Ilib/eal/x86/include
-I../lib/eal/x86/include -Ilib/eal/common -I../lib/eal/common
-Ilib/eal -I../lib/eal -Ilib/kvargs -I../lib/kvargs -Ilib/metrics
-I../lib/metrics -Ilib/telemetry -I../lib/telemetry -Ilib/ethdev
-I../lib/ethdev -Ilib/net -I../lib/net -Ilib/mbuf -I../lib/mbuf
-Ilib/mempool -I../lib/mempool -Ilib/ring -I../lib/ring -Ilib/meter
-I../lib/meter -Ilib/hash -I../lib/hash -Ilib/rcu -I../lib/rcu
-fdiagnostics-color=always -D_FILE_OFFSET_BITS=64 -Wall -Winvalid-pch
-Wextra -Werror -O3 -g -include rte_config.h -Wcast-qual -Wdeprecated
-Wformat -Wformat-nonliteral -Wformat-security -Wmissing-declarations
-Wmissing-prototypes -Wnested-externs -Wold-style-definition
-Wpointer-arith -Wsign-compare -Wstrict-prototypes -Wundef
-Wwrite-strings -Wno-address-of-packed-member -Wno-packed-not-aligned
-Wno-missing-field-initializers -Wno-zero-length-bounds -D_GNU_SOURCE
-fPIC -march=native -DALLOW_EXPERIMENTAL_API -DALLOW_INTERNAL_API
-Wno-format-truncation -DRTE_LOG_DEFAULT_LOGTYPE=lib.ip_frag -MD -MQ
lib/librte_ip_frag.a.p/ip_frag_rte_ipv4_fragmentation.c.o -MF
lib/librte_ip_frag.a.p/ip_frag_rte_ipv4_fragmentation.c.o.d -o
lib/librte_ip_frag.a.p/ip_frag_rte_ipv4_fragmentation.c.o -c
../lib/ip_frag/rte_ipv4_fragmentation.c
In file included from
/usr/lib/gcc/x86_64-redhat-linux/12/include/immintrin.h:43,
                 from
/usr/lib/gcc/x86_64-redhat-linux/12/include/x86intrin.h:32,
                 from ../lib/eal/x86/include/rte_vect.h:31,
                 from ../lib/eal/x86/include/rte_memcpy.h:17,
                 from ../lib/ip_frag/rte_ipv4_fragmentation.c:8:
In function ‘_mm256_storeu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:347:2,
    inlined from ‘rte_mov128’ at ../lib/eal/x86/include/rte_memcpy.h:369:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:445:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘__create_ipopt_frag_hdr’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:68:4,
    inlined from ‘rte_ipv4_fragment_packet’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:242:16:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:935:8: error:
array subscript ‘__m256i_u[1]’ is partly outside array bounds of
‘uint8_t[60]’ {aka ‘unsigned char[60]’} [-Werror=array-bounds]
  935 |   *__P = __A;
      |   ~~~~~^~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c: In function ‘rte_ipv4_fragment_packet’:
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [52,
60] into object ‘ipopt_frag_hdr’ of size 60
  122 |         uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
      |                 ^~~~~~~~~~~~~~
In function ‘_mm256_storeu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:347:2,
    inlined from ‘rte_mov128’ at ../lib/eal/x86/include/rte_memcpy.h:370:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:445:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘__create_ipopt_frag_hdr’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:68:4,
    inlined from ‘rte_ipv4_fragment_packet’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:242:16:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:935:8: error:
array subscript [2, 3] is outside array bounds of ‘uint8_t[60]’ {aka
‘unsigned char[60]’} [-Werror=array-bounds]
  935 |   *__P = __A;
      |   ~~~~~^~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c: In function ‘rte_ipv4_fragment_packet’:
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [84,
124] into object ‘ipopt_frag_hdr’ of size 60
  122 |         uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
      |                 ^~~~~~~~~~~~~~
In function ‘_mm256_storeu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:347:2,
    inlined from ‘rte_mov128’ at ../lib/eal/x86/include/rte_memcpy.h:371:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:445:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘__create_ipopt_frag_hdr’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:68:4,
    inlined from ‘rte_ipv4_fragment_packet’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:242:16:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:935:8: error:
array subscript [3, 4] is outside array bounds of ‘uint8_t[60]’ {aka
‘unsigned char[60]’} [-Werror=array-bounds]
  935 |   *__P = __A;
      |   ~~~~~^~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c: In function ‘rte_ipv4_fragment_packet’:
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [116,
156] into object ‘ipopt_frag_hdr’ of size 60
  122 |         uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
      |                 ^~~~~~~~~~~~~~
In function ‘_mm256_storeu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:347:2,
    inlined from ‘rte_mov64’ at ../lib/eal/x86/include/rte_memcpy.h:358:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:452:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘__create_ipopt_frag_hdr’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:68:4,
    inlined from ‘rte_ipv4_fragment_packet’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:242:16:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:935:8: error:
array subscript ‘__m256i_u[1]’ is partly outside array bounds of
‘void[60]’ [-Werror=array-bounds]
  935 |   *__P = __A;
      |   ~~~~~^~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c: In function ‘rte_ipv4_fragment_packet’:
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [180,
240] into object ‘ipopt_frag_hdr’ of size 60
  122 |         uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
      |                 ^~~~~~~~~~~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [52,
60] into object ‘ipopt_frag_hdr’ of size 60
In function ‘_mm256_storeu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:347:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:457:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘__create_ipopt_frag_hdr’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:68:4,
    inlined from ‘rte_ipv4_fragment_packet’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:242:16:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:935:8: error:
array subscript [2, 7] is outside array bounds of ‘void[60]’
[-Werror=array-bounds]
  935 |   *__P = __A;
      |   ~~~~~^~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c: In function ‘rte_ipv4_fragment_packet’:
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [148,
272] into object ‘ipopt_frag_hdr’ of size 60
  122 |         uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
      |                 ^~~~~~~~~~~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [148,
272] into object ‘ipopt_frag_hdr’ of size 60
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [20,
60] into object ‘ipopt_frag_hdr’ of size 60
In function ‘_mm256_storeu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:347:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:458:4,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘__create_ipopt_frag_hdr’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:68:4,
    inlined from ‘rte_ipv4_fragment_packet’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:242:16:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:935:8: error:
array subscript [2, 8] is outside array bounds of ‘void[60]’
[-Werror=array-bounds]
  935 |   *__P = __A;
      |   ~~~~~^~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c: In function ‘rte_ipv4_fragment_packet’:
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [149,
273] into object ‘ipopt_frag_hdr’ of size 60
  122 |         uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
      |                 ^~~~~~~~~~~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [149,
273] into object ‘ipopt_frag_hdr’ of size 60
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [21,
60] into object ‘ipopt_frag_hdr’ of size 60
In function ‘_mm256_storeu_si256’,
    inlined from ‘rte_mov32’ at ../lib/eal/x86/include/rte_memcpy.h:347:2,
    inlined from ‘rte_memcpy_generic’ at
../lib/eal/x86/include/rte_memcpy.h:438:3,
    inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:851:10,
    inlined from ‘__create_ipopt_frag_hdr’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:68:4,
    inlined from ‘rte_ipv4_fragment_packet’ at
../lib/ip_frag/rte_ipv4_fragmentation.c:242:16:
/usr/lib/gcc/x86_64-redhat-linux/12/include/avxintrin.h:935:8: error:
array subscript ‘__m256i_u[1]’ is partly outside array bounds of
‘uint8_t[60]’ {aka ‘unsigned char[60]’} [-Werror=array-bounds]
  935 |   *__P = __A;
      |   ~~~~~^~~~~
../lib/ip_frag/rte_ipv4_fragmentation.c: In function ‘rte_ipv4_fragment_packet’:
../lib/ip_frag/rte_ipv4_fragmentation.c:122:17: note: at offset [37,
60] into object ‘ipopt_frag_hdr’ of size 60
  122 |         uint8_t ipopt_frag_hdr[IPV4_HDR_MAX_LEN];
      |                 ^~~~~~~~~~~~~~
cc1: all warnings being treated as errors



-- 
David Marchand


  parent reply	other threads:[~2022-06-16 15:11 UTC|newest]

Thread overview: 33+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-11-24  8:47 [PATCH] ip_frag: add IPv4 options fragment and unit " Huichao Cai
2021-12-01 11:49 ` Dariusz Sosnowski
2021-12-02  2:24   ` Huichao Cai
2022-02-15  8:50 ` [PATCH v2] ip_frag: add IPv4 options fragment and " Huichao Cai
2022-02-18 19:04   ` Ananyev, Konstantin
2022-02-21  2:34     ` Huichao Cai
2022-02-21  3:17   ` [PATCH v3] " Huichao Cai
2022-02-25 14:33     ` Ananyev, Konstantin
2022-02-28 12:39       ` Huichao Cai
2022-03-15  7:22     ` [PATCH v4] " Huichao Cai
2022-03-21 14:24       ` Ananyev, Konstantin
2022-03-22  1:25         ` Huichao Cai
2022-03-22  3:09       ` [PATCH v5] " Huichao Cai
2022-03-23 12:52         ` Ananyev, Konstantin
2022-04-06  1:22           ` Huichao Cai
2022-04-06 16:47             ` Ananyev, Konstantin
2022-04-07 14:08               ` Aaron Conole
2022-04-13  2:49                 ` Huichao Cai
2022-04-11  3:55         ` [PATCH v6] " Huichao Cai
2022-04-14 13:14           ` Thomas Monjalon
2022-04-14 13:26             ` Thomas Monjalon
2022-04-15  1:52               ` Huichao Cai
2022-04-15  3:26           ` [PATCH v7] " Huichao Cai
2022-04-15  8:29             ` Ananyev, Konstantin
2022-05-29  8:50               ` Huichao Cai
2022-05-29  8:57               ` Huichao Cai
2022-05-29 10:38                 ` Konstantin Ananyev
2022-05-31 21:23               ` Thomas Monjalon
2022-06-16 15:10             ` David Marchand [this message]
2022-06-16 16:31               ` Stephen Hemminger
2022-06-17  3:52                 ` Huichao Cai
2022-06-17 16:31                   ` Stephen Hemminger
2022-06-18 11:01                     ` Huichao Cai

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to='CAJFAV8yA7VfqZfr4eBKJmtPC6z=Po9DM-0k=D-2BrejC0T9Q0Q@mail.gmail.com' \
    --to=david.marchand@redhat.com \
    --cc=chcchc88@163.com \
    --cc=dev@dpdk.org \
    --cc=konstantin.v.ananyev@yandex.ru \
    --cc=stephen@networkplumber.org \
    --cc=thomas@monjalon.net \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).