mirror of
https://gitlab.torproject.org/tpo/core/tor.git
synced 2025-02-23 06:35:28 +01:00
r16171@tombo: nickm | 2008-06-11 13:47:41 -0400
Lower number of syscalls used to write data to ordinary sockets through use of writev. Disabled till I have time to test it. svn:r15133
This commit is contained in:
parent
b2fcc417d4
commit
a886e86cbd
2 changed files with 59 additions and 6 deletions
|
@ -196,7 +196,7 @@ dnl -------------------------------------------------------------------
|
|||
dnl Check for functions before libevent, since libevent-1.2 apparently
|
||||
dnl exports strlcpy without defining it in a header.
|
||||
|
||||
AC_CHECK_FUNCS(gettimeofday ftime socketpair uname inet_aton strptime getrlimit strlcat strlcpy strtoull ftello getaddrinfo localtime_r gmtime_r memmem strtok_r inet_pton inet_ntop)
|
||||
AC_CHECK_FUNCS(gettimeofday ftime socketpair uname inet_aton strptime getrlimit strlcat strlcpy strtoull ftello getaddrinfo localtime_r gmtime_r memmem strtok_r inet_pton inet_ntop writev readv)
|
||||
|
||||
using_custom_malloc=no
|
||||
if test x$enable_openbsd_malloc = xyes ; then
|
||||
|
@ -311,7 +311,7 @@ AC_SYS_LARGEFILE
|
|||
|
||||
AC_CHECK_HEADERS(unistd.h string.h signal.h ctype.h sys/stat.h sys/types.h fcntl.h sys/fcntl.h sys/time.h errno.h assert.h time.h, , AC_MSG_WARN(Some headers were not found, compilation may fail. If compilation succeeds, please send your orconfig.h to the developers so we can fix this warning.))
|
||||
|
||||
AC_CHECK_HEADERS(netdb.h sys/ioctl.h sys/socket.h arpa/inet.h netinet/in.h pwd.h grp.h sys/un.h)
|
||||
AC_CHECK_HEADERS(netdb.h sys/ioctl.h sys/socket.h arpa/inet.h netinet/in.h pwd.h grp.h sys/un.h sys/uio.h)
|
||||
|
||||
dnl These headers are not essential
|
||||
|
||||
|
|
|
@ -15,6 +15,13 @@ const char buffers_c_id[] =
|
|||
**/
|
||||
#define BUFFERS_PRIVATE
|
||||
#include "or.h"
|
||||
#ifdef HAVE_UNISTD_H
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
#ifdef HAVE_SYS_UIO_H
|
||||
#include <sys/uio.h>
|
||||
#endif
|
||||
|
||||
|
||||
//#define PARANOIA
|
||||
//#define NOINLINE
|
||||
|
@ -545,6 +552,9 @@ buf_add_chunk_with_capacity(buf_t *buf, size_t capacity, int capped)
|
|||
return chunk;
|
||||
}
|
||||
|
||||
/** DOCDOC */
|
||||
#define N_IOV 3
|
||||
|
||||
/** Read up to <b>at_most</b> bytes from the socket <b>fd</b> into
|
||||
* <b>chunk</b> (which must be on <b>buf</b>). If we get an EOF, set
|
||||
* *<b>reached_eof</b> to 1. Return -1 on error, 0 on eof or blocking,
|
||||
|
@ -554,9 +564,26 @@ read_to_chunk(buf_t *buf, chunk_t *chunk, int fd, size_t at_most,
|
|||
int *reached_eof)
|
||||
{
|
||||
ssize_t read_result;
|
||||
|
||||
tor_assert(CHUNK_REMAINING_CAPACITY(chunk) >= at_most);
|
||||
#if 0 && defined(HAVE_READV) && !defined(WIN32)
|
||||
struct iovec iov[N_IOV];
|
||||
int i;
|
||||
size_t remaining = at_most;
|
||||
for (i=0; chunk && i < N_IOV && remaining; ++i) {
|
||||
iov[i].iov_base = CHUNK_WRITE_PTR(chunk);
|
||||
if (remaining > CHUNK_REMAINING_CAPACITY(chunk))
|
||||
iov[i].iov_len = CHUNK_REMAINING_CAPACITY(chunk);
|
||||
else
|
||||
iov[i].iov_len = remaining;
|
||||
remaining -= iov[i].iov_len;
|
||||
chunk = chunk->next;
|
||||
}
|
||||
read_result = readv(fd, iov, i);
|
||||
#else
|
||||
if (at_most > CHUNK_REMAINING_CAPACITY(chunk))
|
||||
at_most = CHUNK_REMAINING_CAPACITY(chunk);
|
||||
read_result = tor_socket_recv(fd, CHUNK_WRITE_PTR(chunk), at_most, 0);
|
||||
#endif
|
||||
|
||||
if (read_result < 0) {
|
||||
int e = tor_socket_errno(fd);
|
||||
if (!ERRNO_IS_EAGAIN(e)) { /* it's a real error */
|
||||
|
@ -573,6 +600,14 @@ read_to_chunk(buf_t *buf, chunk_t *chunk, int fd, size_t at_most,
|
|||
return 0;
|
||||
} else { /* actually got bytes. */
|
||||
buf->datalen += read_result;
|
||||
#if 0 && defined(HAVE_READV) && !defined(WIN32)
|
||||
while ((size_t)read_result > CHUNK_REMAINING_CAPACITY(chunk)) {
|
||||
chunk->datalen += CHUNK_REMAINING_CAPACITY(chunk);
|
||||
read_result -= CHUNK_REMAINING_CAPACITY(chunk);
|
||||
chunk = chunk->next;
|
||||
tor_assert(chunk);
|
||||
}
|
||||
#endif
|
||||
chunk->datalen += read_result;
|
||||
log_debug(LD_NET,"Read %ld bytes. %d on inbuf.", (long)read_result,
|
||||
(int)buf->datalen);
|
||||
|
@ -707,9 +742,27 @@ flush_chunk(int s, buf_t *buf, chunk_t *chunk, size_t sz,
|
|||
size_t *buf_flushlen)
|
||||
{
|
||||
ssize_t write_result;
|
||||
|
||||
tor_assert(sz <= chunk->datalen);
|
||||
#if 0 && defined(HAVE_WRITEV) && !defined(WIN32)
|
||||
struct iovec iov[N_IOV];
|
||||
int i;
|
||||
size_t remaining = sz;
|
||||
for (i=0; chunk && i < N_IOV && remaining; ++i) {
|
||||
iov[i].iov_base = chunk->data;
|
||||
if (remaining > chunk->datalen)
|
||||
iov[i].iov_len = chunk->datalen;
|
||||
else
|
||||
iov[i].iov_len = remaining;
|
||||
remaining -= iov[i].iov_len;
|
||||
chunk = chunk->next;
|
||||
}
|
||||
write_result = writev(s, iov, i);
|
||||
#else
|
||||
if (sz > chunk->datalen)
|
||||
sz = chunk->datalen;
|
||||
write_result = tor_socket_send(s, chunk->data, sz, 0);
|
||||
#endif
|
||||
|
||||
|
||||
if (write_result < 0) {
|
||||
int e = tor_socket_errno(s);
|
||||
if (!ERRNO_IS_EAGAIN(e)) { /* it's a real error */
|
||||
|
|
Loading…
Add table
Reference in a new issue