From d08b328ff9a28f73c90a460b5252a7236f6981a5 Mon Sep 17 00:00:00 2001 From: wsanchez Date: Sat, 28 May 2005 00:06:56 +0000 Subject: Backport r178340 from trunk: network_io/unix/sendrecv.c: Deal with EAGAIN after poll(). Following apr_wait_for_io_or_timeout(), we were doing I/O and not dealing with EAGAIN. It is legal for poll() to indicate that a socket is available for writing and then for write() to fail with EAGAIN if the state of the socket changed in between the poll() and write() calls. This only seems to actually happen on Mac OS 10.4 (Darwin 8). Rather than trying write() only once, if we get an EAGAIN, continue to call apr_wait_for_io_or_timeout() and try writing. git-svn-id: http://svn.apache.org/repos/asf/apr/apr/branches/1.1.x@178844 13f79535-47bb-0310-9956-ffa450edef68 --- CHANGES | 3 +++ network_io/unix/sendrecv.c | 32 ++++++++++++++++---------------- 2 files changed, 19 insertions(+), 16 deletions(-) diff --git a/CHANGES b/CHANGES index 2d1038ad6..acea4e466 100644 --- a/CHANGES +++ b/CHANGES @@ -17,6 +17,9 @@ Changes for APR 1.1.1 *) find_apr.m4: Try installed APR before bundled copy if --with-apr not passed to configure. [Justin Erenkrantz] + *) Fix issue with poll() followed by net I/O yielding EAGAIN on + Mac OS 10.4 (Darwin 8). [Wilfredo Sanchez] + Changes for APR 1.1.0 *) Added apr_procattr_user_set and apr_procattr_group_set diff --git a/network_io/unix/sendrecv.c b/network_io/unix/sendrecv.c index 03d132385..c5fc43a83 100644 --- a/network_io/unix/sendrecv.c +++ b/network_io/unix/sendrecv.c @@ -40,8 +40,8 @@ apr_status_t apr_socket_send(apr_socket_t *sock, const char *buf, rv = write(sock->socketdes, buf, (*len)); } while (rv == -1 && errno == EINTR); - if (rv == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while (rv == -1 && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { apr_status_t arv; do_select: arv = apr_wait_for_io_or_timeout(NULL, sock, 0); @@ -80,8 +80,8 @@ apr_status_t apr_socket_recv(apr_socket_t *sock, char *buf, apr_size_t *len) rv = read(sock->socketdes, buf, (*len)); } while (rv == -1 && errno == EINTR); - if ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { do_select: arv = apr_wait_for_io_or_timeout(NULL, sock, 1); if (arv != APR_SUCCESS) { @@ -120,8 +120,8 @@ apr_status_t apr_socket_sendto(apr_socket_t *sock, apr_sockaddr_t *where, where->salen); } while (rv == -1 && errno == EINTR); - if ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { apr_status_t arv = apr_wait_for_io_or_timeout(NULL, sock, 0); if (arv != APR_SUCCESS) { *len = 0; @@ -153,8 +153,8 @@ apr_status_t apr_socket_recvfrom(apr_sockaddr_t *from, apr_socket_t *sock, (struct sockaddr*)&from->sa, &from->salen); } while (rv == -1 && errno == EINTR); - if ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { apr_status_t arv = apr_wait_for_io_or_timeout(NULL, sock, 1); if (arv != APR_SUCCESS) { *len = 0; @@ -200,8 +200,8 @@ apr_status_t apr_socket_sendv(apr_socket_t * sock, const struct iovec *vec, rv = writev(sock->socketdes, vec, nvec); } while (rv == -1 && errno == EINTR); - if ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { apr_status_t arv; do_select: arv = apr_wait_for_io_or_timeout(NULL, sock, 0); @@ -316,8 +316,8 @@ apr_status_t apr_socket_sendfile(apr_socket_t *sock, apr_file_t *file, *len); /* number of bytes to send */ } while (rv == -1 && errno == EINTR); - if ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { do_select: arv = apr_wait_for_io_or_timeout(NULL, sock, 0); if (arv != APR_SUCCESS) { @@ -626,8 +626,8 @@ apr_status_t apr_socket_sendfile(apr_socket_t *sock, apr_file_t *file, } } while (rc == -1 && errno == EINTR); - if ((rc == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while ((rc == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { apr_status_t arv = apr_wait_for_io_or_timeout(NULL, sock, 0); if (arv != APR_SUCCESS) { @@ -773,8 +773,8 @@ apr_status_t apr_socket_sendfile(apr_socket_t * sock, apr_file_t * file, flags); /* flags */ } while (rv == -1 && errno == EINTR); - if ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) - && (sock->timeout > 0)) { + while ((rv == -1) && (errno == EAGAIN || errno == EWOULDBLOCK) + && (sock->timeout > 0)) { do_select: arv = apr_wait_for_io_or_timeout(NULL, sock, 0); if (arv != APR_SUCCESS) { -- cgit v1.2.1