[vlc-devel] [PATCH 1/5] network: add convenience wrappers for send/sendto/sendmsg

RĂ©mi Denis-Courmont remi at remlab.net
Sat Mar 28 08:20:49 CET 2020


---
 include/vlc_network.h  | 54 ++++++++++++++++++++++++++++++++++++++++++
 src/libvlccore.sym     |  3 +++
 src/posix/filesystem.c | 27 +++++++++++++++++++++
 src/win32/filesystem.c | 24 +++++++++++++++++++
 4 files changed, 108 insertions(+)

diff --git a/include/vlc_network.h b/include/vlc_network.h
index 88dcfefbca..c403e9a638 100644
--- a/include/vlc_network.h
+++ b/include/vlc_network.h
@@ -113,6 +113,60 @@ struct sockaddr;
 VLC_API int vlc_accept(int lfd, struct sockaddr *addr, socklen_t *alen,
                        bool nonblock) VLC_USED;
 
+/**
+ * Sends data.
+ *
+ * Like @c send(), this function sends raw data to the peer of a
+ * connection-mode socket, or to the predefined peer of a connection-less
+ * socket.
+ * Unlike @c send(), this function never triggers a signal; if the peer hung
+ * up, it returns an error.
+ *
+ * @param fd socket to send data through
+ * @param buf start address of data
+ * @param buflen byte size of data
+ * @param flags socket send flags (see @c send() documentation)
+ * @return number of bytes actually sent, or -1 on error (@c errno is set)
+ */
+VLC_API ssize_t vlc_send(int fd, const void *buf, size_t buflen, int flags);
+
+/**
+ * Sends data to a peer.
+ *
+ * This function operates like @c sendto() with the exception that it never
+ * triggers a signal.
+ *
+ * This function mainly exists for the sakes of completeness and consistency:
+ * - To send data on a connection-mode socket, using \ref vlc_send() is
+ *   simpler.
+ * - To send data on a connection-less socket, @c sendto() and/or @c send() can
+ *   be used directly.
+ *
+ * @param fd socket to send data through
+ * @param buf start address of data
+ * @param buflen byte size of data
+ * @param flags socket send flags (see @c send() documentation)
+ * @param dst destination address (ignored for connection-mode sockets)
+ * @param dstlen byte size of destination address
+ * @return number of bytes actually sent, or -1 on error (@c errno is set)
+ */
+VLC_API ssize_t vlc_sendto(int fd, const void *buf, size_t buflen, int flags,
+                           const struct sockaddr *dst, socklen_t dstlen);
+
+/**
+ * Sends a socket message.
+ *
+ * Like @c sendmsg(), this function sends a message through a socket.
+ * Unlike @c sendmsg(), this function never triggers a signal; if the peer hung
+ * up, it returns an error.
+ *
+ * @param fd socket to send data through
+ * @param msg message to send (see @c sendmsg() documentation)
+ * @param flags socket send flags (see @c sendmsg() documentation)
+ * @return number of bytes actually sent, or -1 on error (@c errno is set)
+ */
+VLC_API ssize_t vlc_sendmsg(int fd, const struct msghdr *msg, int flags);
+
 # ifdef __cplusplus
 extern "C" {
 # endif
diff --git a/src/libvlccore.sym b/src/libvlccore.sym
index 66ae6f3ecd..9effd1246e 100644
--- a/src/libvlccore.sym
+++ b/src/libvlccore.sym
@@ -446,6 +446,9 @@ vlc_writev
 vlc_socket
 vlc_socketpair
 vlc_accept
+vlc_send
+vlc_sendto
+vlc_sendmsg
 utf8_vfprintf
 var_AddCallback
 var_AddListCallback
diff --git a/src/posix/filesystem.c b/src/posix/filesystem.c
index 3f94b76f92..89782a4bc2 100644
--- a/src/posix/filesystem.c
+++ b/src/posix/filesystem.c
@@ -315,3 +315,30 @@ int vlc_accept (int lfd, struct sockaddr *addr, socklen_t *alen, bool nonblock)
 #endif
     return fd;
 }
+
+ssize_t vlc_send(int fd, const void *buf, size_t len, int flags)
+{
+    return vlc_sendto(fd, buf, len, flags, NULL, 0);
+}
+
+ssize_t vlc_sendto(int fd, const void *buf, size_t len, int flags,
+                   const struct sockaddr *dst, socklen_t dstlen)
+{
+    struct iovec iov = {
+        .iov_base = (void *)buf,
+        .iov_len = len,
+    };
+    struct msghdr msg = {
+        .msg_name = (struct sockaddr *)dst,
+        .msg_namelen = dstlen,
+        .msg_iov = &iov,
+        .msg_iovlen = 1,
+    };
+
+    return vlc_sendmsg(fd, &msg, flags);
+}
+
+ssize_t vlc_sendmsg(int fd, const struct msghdr *msg, int flags)
+{
+    return sendmsg(fd, msg, flags | MSG_NOSIGNAL);
+}
diff --git a/src/win32/filesystem.c b/src/win32/filesystem.c
index e2df866b28..0a0656dbba 100644
--- a/src/win32/filesystem.c
+++ b/src/win32/filesystem.c
@@ -353,6 +353,30 @@ int vlc_accept (int lfd, struct sockaddr *addr, socklen_t *alen, bool nonblock)
     return fd;
 }
 
+ssize_t vlc_send(int fd, const void *buf, size_t len, int flags)
+{
+    WSABUF wsabuf = { .buf = (char *)buf, .len = len };
+    DWORD sent;
+
+    return WSASend(fd, &wsabuf, 1, &sent, flags,
+                   NULL, NULL) ? -1 : (ssize_t)sent;
+}
+
+ssize_t vlc_sendto(int fd, const void *buf, size_t len, int flags,
+                   const struct sockaddr *dst, socklen_t dstlen)
+{
+    WSABUF wsabuf = { .buf = (char *)buf, .len = len };
+    DWORD sent;
+
+    return WSASendTo(fd, &wsabuf, 1, &sent, flags, dst, dstlen,
+                     NULL, NULL) ? -1 : (ssize_t)sent;
+}
+
+ssize_t vlc_sendmsg(int fd, const struct msghdr *msg, int flags)
+{
+    return sendmsg(fd, msg, flags);
+}
+
 #if !VLC_WINSTORE_APP
 FILE *vlc_win32_tmpfile(void)
 {
-- 
2.26.0



More information about the vlc-devel mailing list