udp_vu_sock_info() uses MSG_PEEK to look ahead at the next datagram to be
received and gets its source address. Currently we only use it in the
vhost-user path, but there's nothing inherently vhost-user specific about
it. We have upcoming uses for it elsewhere so rename and move to udp.c.
While we're there, polish its error reporting a litle.
Signed-off-by: David Gibson
---
udp.c | 25 +++++++++++++++++++++++++
udp_internal.h | 1 +
udp_vu.c | 19 +------------------
3 files changed, 27 insertions(+), 18 deletions(-)
diff --git a/udp.c b/udp.c
index 8125cfcb..6b72c30f 100644
--- a/udp.c
+++ b/udp.c
@@ -629,6 +629,31 @@ static int udp_sock_errs(const struct ctx *c, union epoll_ref ref)
return n_err;
}
+/**
+ * udp_peek_addr() - Get source address for next packet
+ * @s: Socket to get information from
+ * @src: Socket address (output)
+ *
+ * Return: 0 on success, -1 otherwise
+ */
+int udp_peek_addr(int s, union sockaddr_inany *src)
+{
+ struct msghdr msg = {
+ .msg_name = src,
+ .msg_namelen = sizeof(*src),
+ };
+ int rc;
+
+ rc = recvmsg(s, &msg, MSG_PEEK | MSG_DONTWAIT);
+ if (rc < 0) {
+ if (errno != EAGAIN && errno != EWOULDBLOCK)
+ warn_perror("Error peeking at socket address");
+ return rc;
+ }
+ return 0;
+}
+
+
/**
* udp_sock_recv() - Receive datagrams from a socket
* @c: Execution context
diff --git a/udp_internal.h b/udp_internal.h
index 02724e59..43a61094 100644
--- a/udp_internal.h
+++ b/udp_internal.h
@@ -30,5 +30,6 @@ size_t udp_update_hdr4(struct iphdr *ip4h, struct udp_payload_t *bp,
size_t udp_update_hdr6(struct ipv6hdr *ip6h, struct udp_payload_t *bp,
const struct flowside *toside, size_t dlen,
bool no_udp_csum);
+int udp_peek_addr(int s, union sockaddr_inany *src);
#endif /* UDP_INTERNAL_H */
diff --git a/udp_vu.c b/udp_vu.c
index 4153b6c1..5faf1e1d 100644
--- a/udp_vu.c
+++ b/udp_vu.c
@@ -57,23 +57,6 @@ static size_t udp_vu_hdrlen(bool v6)
return hdrlen;
}
-/**
- * udp_vu_sock_info() - get socket information
- * @s: Socket to get information from
- * @s_in: Socket address (output)
- *
- * Return: 0 if socket address can be read, -1 otherwise
- */
-static int udp_vu_sock_info(int s, union sockaddr_inany *s_in)
-{
- struct msghdr msg = {
- .msg_name = s_in,
- .msg_namelen = sizeof(union sockaddr_inany),
- };
-
- return recvmsg(s, &msg, MSG_PEEK | MSG_DONTWAIT);
-}
-
/**
* udp_vu_sock_recv() - Receive datagrams from socket into vhost-user buffers
* @c: Execution context
@@ -230,7 +213,7 @@ void udp_vu_listen_sock_data(const struct ctx *c, union epoll_ref ref,
int iov_used;
bool v6;
- if (udp_vu_sock_info(ref.fd, &s_in) < 0)
+ if (udp_peek_addr(ref.fd, &s_in) < 0)
break;
sidx = udp_flow_from_sock(c, ref, &s_in, now);
--
2.49.0