On Tue, Aug 05, 2025 at 05:46:08PM +0200, Laurent Vivier wrote:
Use packet_data() and extract headers using IOV_REMOVE_HEADER() and IOV_PEEK_HEADER() rather than packet_get().
Signed-off-by: Laurent Vivier
Reviewed-by: David Gibson
--- iov.c | 1 - udp.c | 33 ++++++++++++++++++++++----------- 2 files changed, 22 insertions(+), 12 deletions(-)
diff --git a/iov.c b/iov.c index 9d99beb32532..f519eb3cfeaf 100644 --- a/iov.c +++ b/iov.c @@ -334,7 +334,6 @@ void *iov_remove_header_(struct iov_tail *tail, void *v, size_t len, size_t alig * iov array, a negative value if there is not enough room in the * destination iov array */ -/* cppcheck-suppress unusedFunction */ ssize_t iov_tail_clone(struct iovec *dst_iov, size_t dst_iov_cnt, struct iov_tail *tail) { diff --git a/udp.c b/udp.c index 75edc2054d4a..3c25f2e0ae97 100644 --- a/udp.c +++ b/udp.c @@ -978,9 +978,11 @@ int udp_tap_handler(const struct ctx *c, uint8_t pif, struct mmsghdr mm[UIO_MAXIOV]; union sockaddr_inany to_sa; struct iovec m[UIO_MAXIOV]; + struct udphdr uh_storage; const struct udphdr *uh; struct udp_flow *uflow; - int i, s, count = 0; + int i, j, s, count = 0; + struct iov_tail data; flow_sidx_t tosidx; in_port_t src, dst; uint8_t topif; @@ -988,7 +990,10 @@ int udp_tap_handler(const struct ctx *c, uint8_t pif,
ASSERT(!c->no_udp);
- uh = packet_get(p, idx, 0, sizeof(*uh), NULL); + if (!packet_data(p, idx, &data)) + return 1; + + uh = IOV_PEEK_HEADER(&data, uh_storage); if (!uh) return 1;
@@ -1025,23 +1030,29 @@ int udp_tap_handler(const struct ctx *c, uint8_t pif,
pif_sockaddr(c, &to_sa, &sl, topif, &toside->eaddr, toside->eport);
- for (i = 0; i < (int)p->count - idx; i++) { - struct udphdr *uh_send; - size_t len; + for (i = 0, j = 0; i < (int)p->count - idx && j < UIO_MAXIOV; i++) { + const struct udphdr *uh_send;
- uh_send = packet_get(p, idx + i, 0, sizeof(*uh), &len); + if (!packet_data(p, idx + i, &data)) + return p->count - idx; + + uh_send = IOV_REMOVE_HEADER(&data, uh_storage); if (!uh_send) return p->count - idx;
mm[i].msg_hdr.msg_name = &to_sa; mm[i].msg_hdr.msg_namelen = sl;
- if (len) { - m[i].iov_base = (char *)(uh_send + 1); - m[i].iov_len = len; + if (data.cnt) { + int cnt; + + cnt = iov_tail_clone(&m[j], UIO_MAXIOV - j, &data); + if (cnt < 0) + return p->count - idx;
- mm[i].msg_hdr.msg_iov = m + i; - mm[i].msg_hdr.msg_iovlen = 1; + mm[i].msg_hdr.msg_iov = &m[j]; + mm[i].msg_hdr.msg_iovlen = cnt; + j += cnt; } else { mm[i].msg_hdr.msg_iov = NULL; mm[i].msg_hdr.msg_iovlen = 0;
-- David Gibson (he or they) | I'll have my music baroque, and my code david AT gibson.dropbear.id.au | minimalist, thank you, not the other way | around. http://www.ozlabs.org/~dgibson