In the latest v4 version I submitted on December 18th,
when I opened the -Wanalyzer-out-of-bounds and compiled it on the gcc14.2 environment,
''''''
C compiler for the host machine: cc (gcc 14.2.1 "cc (GCC) 14.2.1 20241104 (Red Hat 14.2.1-6)")
Compiler for C supports arguments -Wanalyzer-out-of-bounds: YES
''''''
this issue did not occur;
And [PATCH v4] net/zxdh: Provided zxdh basic init, this patch was submitted three months ago on September 9th;
So, I am confused;
Is this issue also present in the latest v4 submission version and do we need to solved it
>Overall this looks good, one test checklist item for me was to build
>with Gcc 14 and analyzer option. This finds bugs but can generate false
>positives. The output is quite verbose.
>It complains about this which may or may not be a real problem.
>If memcpy() is used instead of rte_memcpy() then the problem goes away.
>The issue is that inlined version rte_memcpy() will reference past the arguments
>as an internal optimization for small values.
>[1564/3222] Compiling C object drivers/libtmp_rte_net_zxdh.a.p/net_zxdh_zxdh_common.c.o
>In file included from ../lib/mempool/rte_mempool.h:50,
> from ../lib/mbuf/rte_mbuf.h:38,
> from ../lib/net/rte_ether.h:20,
> from ../lib/ethdev/rte_eth_ctrl.h:10,
> from ../lib/ethdev/rte_ethdev.h:1472,
> from ../lib/ethdev/ethdev_driver.h:21,
> from ../drivers/net/zxdh/zxdh_common.c:8:
>In function ‘rte_mov15_or_less’,
> inlined from ‘rte_memcpy_generic’ at ../lib/eal/x86/include/rte_memcpy.h:395:10,
> inlined from ‘rte_memcpy’ at ../lib/eal/x86/include/rte_memcpy.h:757:10,
> inlined from ‘zxdh_get_res_info’ at ../drivers/net/zxdh/zxdh_common.c:231:2:
>.../lib/eal/x86/include/rte_memcpy.h:82:55: warning: stack-based buffer overflow [CWE-121] [-Wanalyzer-out-of-bounds]
> 82 | ((struct rte_uint64_alias *)dst)->val =
> | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^
> 83 | ((const struct rte_uint64_alias *)src)->val;
> | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> ‘zxdh_panelid_get’: events 1-3
> |
> |../drivers/net/zxdh/zxdh_common.c:250:1:
> | 239 | uint8_t reps = 0;
> | | ~~~~
> | | |
> | | (2) capacity: 1 byte
> |......
> | 250 | zxdh_panelid_get(struct rte_eth_dev *dev, uint8_t *panelid)
> | | ^~~~~~~~~~~~~~~~
> | | |
> | | (1) entry to ‘zxdh_panelid_get’
> |......
> | 255 | int32_t ret = zxdh_get_res_panel_id(¶m, panelid);
> | | ~
> | | |
> | | (3) inlined call to ‘zxdh_get_res_panel_id’ from ‘zxdh_panelid_get’
> |
> |
> | 242 | if (zxdh_get_res_info(in, ZXDH_TBL_FIELD_PNLID, &reps, &reps_len) != ZXDH_BAR_MSG_OK)
> | | ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> | | |
> | | (4) calling ‘zxdh_get_res_info’ from ‘zxdh_panelid_get’
> |
> ‘zxdh_get_res_info’: events 5-12
> |
> | 186 | zxdh_get_res_info(struct zxdh_res_para *dev, uint8_t field, uint8_t *res, uint16_t *len)
> | | ^~~~~~~~~~~~~~~~~
> | | |
> | | (5) entry to ‘zxdh_get_res_info’
> |......
> | 192 | if (!res || !dev)
> | | ~
> | | |
> | | (6) following ‘false’ branch....
> |......
> | 195 | struct zxdh_tbl_msg_header tbl_msg = {
> | | ~~~~~~~
> | | |
> | | (7) ...to here
> |......
> | 217 | if (ret != ZXDH_BAR_MSG_OK) {
> | | ~
> | | |
> | | (8) following ‘false’ branch (when ‘ret == 0’)...
> |......
> | 225 | if (tbl_reps->check != ZXDH_TBL_MSG_PRO_SUCCESS) {
> | | ~~~~~~~~~~~~~~~~
> | | | |
> | | | (9) ...to here
> | | (10) following ‘false’ branch...
> |......
> | 230 | *len = tbl_reps->len;
> | | ~~~~~~~~~~~~~
> | | |
> | | (11) ...to here
> | 231 | rte_memcpy(res, (recv_buf + ZXDH_REPS_HEADER_OFFSET +
> | | ~
> | | |
> | | (12) inlined call to ‘rte_memcpy’ from ‘zxdh_get_res_info’
> |
> +--> ‘rte_memcpy’: events 13-14
> |
> |../lib/eal/x86/include/rte_memcpy.h:754:12:
> | 754 | if (!(((uintptr_t)dst | (uintptr_t)src) & ALIGNMENT_MASK))
> | | ^
> | | |
> | | (13) following ‘false’ branch...
> |......
> | 757 | return rte_memcpy_generic(dst, src, n);
> | | ~
> | | |
> | | (14) inlined call to ‘rte_memcpy_generic’ from ‘rte_memcpy’
> |
> +--> ‘rte_memcpy_generic’: events 15-17
> |
> | 394 | if (n < 16) {
> | | ^
> | | |
> | | (15) ...to here
> | | (16) following ‘true’ branch...
> | 395 | return rte_mov15_or_less(dst, src, n);
> | | ~
> | | |
> | | (17) inlined call to ‘rte_mov15_or_less’ from ‘rte_memcpy_generic’
> |
> +--> ‘rte_mov15_or_less’: events 18-21
> |
> | 81 | if (n & 8) {
> | | ^
> | | |
> | | (18) ...to here
> | | (19) following ‘true’ branch...
> | 82 | ((struct rte_uint64_alias *)dst)->val =
> | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> | | |
> | | (21) out-of-bounds write from byte 1 till byte 7 but ‘reps’ ends at byte 1
> | 83 | ((const struct rte_uint64_alias *)src)->val;
> | | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
> | | |
> | | (20) ...to here
> |
>.../lib/eal/x86/include/rte_memcpy.h:82:55: note: write of 7 bytes to beyond the end of ‘reps’
> 82 | ((struct rte_uint64_alias *)dst)->val =
> | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^
> 83 | ((const struct rte_uint64_alias *)src)->val;
> | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>
> ┌──────────────────────────────────────────────────────────────────────┐
> │ write of ‘uint64_t’ (8 bytes) │
> └──────────────────────────────────────────────────────────────────────┘
> │ │
> │ │
> v v
> ┌────────────────────────┐┌────────────────────────────────────────────┐
> │‘reps’ (type: ‘uint8_t’)││ after valid range │
> └────────────────────────┘└────────────────────────────────────────────┘
> ├───────────┬────────────┤├─────────────────────┬──────────────────────┤
> │ │
> ╭────────┴───────╮ ╭───────────┴──────────╮
> │capacity: 1 byte│ │⚠️ overflow of 7 bytes│
> ╰────────────────╯ ╰──────────────────────╯