aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKeith Burns <alagalah@gmail.com>2017-10-05 17:39:27 +0000
committerGerrit Code Review <gerrit@fd.io>2017-10-05 17:39:27 +0000
commit98cd49a6fee2f82cb06ecb1851f326a02f070437 (patch)
treeba32f10a637632b7637d7783839986978739b6c8
parent574e4afced9f264302a48b1fb8bb4c70be0dfbd1 (diff)
parentdc217c26c9c950dd3849ae24f7e28ffcb6dce21e (diff)
Merge "LDPRELOAD: Implement readv and writev"
-rw-r--r--vcl-ldpreload/src/libvcl-ldpreload/vcom.c94
-rw-r--r--vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.c16
-rw-r--r--vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.h4
3 files changed, 106 insertions, 8 deletions
diff --git a/vcl-ldpreload/src/libvcl-ldpreload/vcom.c b/vcl-ldpreload/src/libvcl-ldpreload/vcom.c
index f997d4d..d292b27 100644
--- a/vcl-ldpreload/src/libvcl-ldpreload/vcom.c
+++ b/vcl-ldpreload/src/libvcl-ldpreload/vcom.c
@@ -18,7 +18,10 @@
#include <dlfcn.h>
#include <pthread.h>
#include <time.h>
-
+#include <sys/uio.h>
+#include <limits.h>
+#define __need_IOV_MAX
+#include <bits/stdio_lim.h>
#include <stdarg.h>
#include <libvcl-ldpreload/vcom_socket_wrapper.h>
@@ -28,8 +31,6 @@
#include <uri/vppcom.h>
#include <libvcl-ldpreload/vcom_socket.h>
-
-
/* GCC have printf type attribute check. */
#ifdef HAVE_FUNCTION_ATTRIBUTE_FORMAT
#define PRINTF_ATTRIBUTE(a,b) \
@@ -62,11 +63,6 @@
#define DO_NOT_SANITIZE_ADDRESS_ATTRIBUTE
#endif
-
-
-
-
-
#define VCOM_SOCKET_FD_MAX 0x10000
static char vcom_app_name[MAX_VCOM_APP_NAME];
@@ -267,6 +263,47 @@ read (int __fd, void *__buf, size_t __nbytes)
return libc_read (__fd, __buf, __nbytes);
}
+ssize_t
+readv (int __fd, const struct iovec * __iov, int __iovcnt)
+{
+ size_t len = 0;
+ ssize_t total = 0;
+
+ if (is_vcom_socket_fd (__fd))
+ {
+ if (__iov == 0 || __iovcnt == 0 || __iovcnt > IOV_MAX)
+ return -EINVAL;
+
+ /* Sanity check */
+ for (int i = 0; i < __iovcnt; ++i)
+ {
+ if (SSIZE_MAX - len < __iov[i].iov_len)
+ return -EINVAL;
+ len += __iov[i].iov_len;
+ }
+
+ for (int i = 0; i < __iovcnt; ++i)
+ {
+ len = vcom_read (__fd, __iov[i].iov_base, __iov[i].iov_len);
+ if (len < 0)
+ {
+ if (total > 0)
+ return total;
+ else
+ {
+ errno = len;;
+ return -1;
+ }
+ }
+ else
+ total += len;
+ }
+ return (total);
+ }
+ else
+ return libc_readv (__fd, __iov, __iovcnt);
+}
+
/* Write N bytes of BUF to FD. Return the number written, or -1.
This function is a cancellation point and therefore
@@ -314,6 +351,47 @@ write (int __fd, const void *__buf, size_t __n)
return libc_write (__fd, __buf, __n);
}
+ssize_t
+writev (int __fd, const struct iovec * __iov, int __iovcnt)
+{
+ size_t len = 0;
+ ssize_t total = 0;
+
+ if (is_vcom_socket_fd (__fd))
+ {
+ if (__iov == 0 || __iovcnt == 0 || __iovcnt > IOV_MAX)
+ return -EINVAL;
+
+ /* Sanity check */
+ for (int i = 0; i < __iovcnt; ++i)
+ {
+ if (SSIZE_MAX - len < __iov[i].iov_len)
+ return -EINVAL;
+ len += __iov[i].iov_len;
+ }
+
+ for (int i = 0; i < __iovcnt; ++i)
+ {
+ len = vcom_write (__fd, __iov[i].iov_base, __iov[i].iov_len);
+ if (len < 0)
+ {
+ if (total > 0)
+ return total;
+ else
+ {
+ errno = len;;
+ return -1;
+ }
+ }
+ else
+ total += len;
+ }
+ return (total);
+ }
+ else
+ return libc_writev (__fd, __iov, __iovcnt);
+}
+
/* Do the file control operation described by CMD on FD.
The remaining arguments are interpreted depending on CMD.
diff --git a/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.c b/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.c
index cadac92..2e2d794 100644
--- a/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.c
+++ b/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.c
@@ -598,6 +598,14 @@ libc_read (int fd, void *buf, size_t count)
return swrap.libc.symbols._libc_read.f (fd, buf, count);
}
+ssize_t
+libc_readv (int fd, const struct iovec *iov, int iovcnt)
+{
+ swrap_bind_symbol_libc (readv);
+
+ return swrap.libc.symbols._libc_readv.f (fd, iov, iovcnt);
+}
+
int
libc_recv (int sockfd, void *buf, size_t len, int flags)
{
@@ -691,6 +699,14 @@ libc_write (int fd, const void *buf, size_t count)
return swrap.libc.symbols._libc_write.f (fd, buf, count);
}
+ssize_t
+libc_writev (int fd, const struct iovec *iov, int iovcnt)
+{
+ swrap_bind_symbol_libc (writev);
+
+ return swrap.libc.symbols._libc_writev.f (fd, iov, iovcnt);
+}
+
int
libc_shutdown (int fd, int how)
{
diff --git a/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.h b/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.h
index 8ca8bb6..66a7bc1 100644
--- a/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.h
+++ b/vcl-ldpreload/src/libvcl-ldpreload/vcom_socket_wrapper.h
@@ -143,6 +143,8 @@ int libc_listen (int sockfd, int backlog);
int libc_read (int fd, void *buf, size_t count);
+ssize_t libc_readv (int fd, const struct iovec *iov, int iovcnt);
+
int libc_recv (int sockfd, void *buf, size_t len, int flags);
int
@@ -174,6 +176,8 @@ int libc_socketpair (int domain, int type, int protocol, int sv[2]);
ssize_t libc_write (int fd, const void *buf, size_t count);
+ssize_t libc_writev (int fd, const struct iovec *iov, int iovcnt);
+
int libc_shutdown (int fd, int how);
int