From 6af7ee74cf8baca069ae948e70e62eae24c1f93b Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 24 Nov 2022 19:54:18 +1100 Subject: udp: Fix incorrect use of IPv6 mh buffers in IPv4 path udp_sock_handler() incorrectly uses udp6_l2_mh_tap[] on the IPv4 path. In fact this is harmless because this assignment is redundant (the 0th entry msg_hdr will always point to the 0th iov entry for both IPv4 and IPv6 and won't change). There is also an incorrect usage of udp6_l2_mh_tap[] in udp_sock_fill_data_v4. This one can cause real problems, because we'll use stale iov_len values if we send multiple messages to the qemu socket. Most of the time that will be relatively harmless - we're likely to either drop UDP packets, or send duplicates. However, if the stale iov_len we use ends up referencing an uninitialized buffer we could desynchronize the qemu stream socket. Correct both these bugs. The UDP6 path appears to be correct, but it does have some comments that incorrectly reference the IPv4 versions, so fix those as well. Signed-off-by: David Gibson Signed-off-by: Stefano Brivio --- udp.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/udp.c b/udp.c index 598c793..2810462 100644 --- a/udp.c +++ b/udp.c @@ -647,7 +647,7 @@ static void udp_sock_fill_data_v4(const struct ctx *c, int n, int *msg_idx, int *msg_bufs, ssize_t *msg_len, const struct timespec *now) { - struct msghdr *mh = &udp6_l2_mh_tap[*msg_idx].msg_hdr; + struct msghdr *mh = &udp4_l2_mh_tap[*msg_idx].msg_hdr; struct udp4_l2_buf_t *b = &udp4_l2_buf[n]; size_t ip_len, buf_len; in_port_t src_port; @@ -721,9 +721,9 @@ static void udp_sock_fill_data_v4(const struct ctx *c, int n, } /** - * udp_sock_fill_data_v4() - Fill and queue one buffer. In pasta mode, write it + * udp_sock_fill_data_v6() - Fill and queue one buffer. In pasta mode, write it * @c: Execution context - * @n: Index of buffer in udp4_l2_buf pool + * @n: Index of buffer in udp6_l2_buf pool * @ref: epoll reference from socket * @msg_idx: Index within message being prepared (spans multiple buffers) * @msg_len: Length of current message being prepared for sending @@ -869,7 +869,7 @@ void udp_sock_handler(const struct ctx *c, union epoll_ref ref, uint32_t events, if (n <= 0) return; - udp6_l2_mh_tap[0].msg_hdr.msg_iov = &udp6_l2_iov_tap[0]; + udp4_l2_mh_tap[0].msg_hdr.msg_iov = &udp4_l2_iov_tap[0]; for (i = 0; i < (unsigned)n; i++) { udp_sock_fill_data_v4(c, i, ref, -- cgit v1.2.3