trawick 2003/06/04 19:29:13
Modified: . CHANGES
file_io/unix readwrite.c
Log:
When writing to pipes with a timeout set, handle the situation
where the kernel says the pipe is writable but an attempt to
write <= PIPE_BUF bytes gets EAGAIN. APR will now write whatever
data will fit. APR applications that relied on the atomic nature
of relatively small pipe write requests may be affected.
PR: 20295
First patch and lots of testing from: Mark Street <[EMAIL PROTECTED]>
Revision Changes Path
1.415 +7 -0 apr/CHANGES
Index: CHANGES
===================================================================
RCS file: /home/cvs/apr/CHANGES,v
retrieving revision 1.414
retrieving revision 1.415
diff -u -r1.414 -r1.415
--- CHANGES 2 Jun 2003 15:52:28 -0000 1.414
+++ CHANGES 5 Jun 2003 02:29:12 -0000 1.415
@@ -1,5 +1,12 @@
Changes with APR 0.9.4
+ *) When writing to pipes with a timeout set, handle the situation
+ where the kernel says the pipe is writable but an attempt to
+ write <= PIPE_BUF bytes gets EAGAIN. APR will now write whatever
+ data will fit. APR applications that relied on the atomic nature
+ of relatively small pipe write requests may be affected.
+ PR 20295 [Mark Street <[EMAIL PROTECTED]>, Jeff Trawick]
+
*) Define _THREAD_SAFE for all compilations on AIX. Previously
those of us who used the vendor compiler had it defined
implicitly and others did not. The difference became obvious
1.86 +13 -2 apr/file_io/unix/readwrite.c
Index: readwrite.c
===================================================================
RCS file: /home/cvs/apr/file_io/unix/readwrite.c,v
retrieving revision 1.85
retrieving revision 1.86
diff -u -r1.85 -r1.86
--- readwrite.c 1 May 2003 03:16:29 -0000 1.85
+++ readwrite.c 5 Jun 2003 02:29:12 -0000 1.86
@@ -243,8 +243,19 @@
}
else {
do {
- rv = write(thefile->filedes, buf, *nbytes);
- } while (rv == (apr_size_t)-1 && errno == EINTR);
+ do {
+ rv = write(thefile->filedes, buf, *nbytes);
+ } while (rv == (apr_size_t)-1 && errno == EINTR);
+ if (rv == (apr_size_t)-1 &&
+ (errno == EAGAIN || errno == EWOULDBLOCK)) {
+ *nbytes /= 2; /* yes, we'll loop if kernel lied
+ * and we can't even write 1 byte
+ */
+ }
+ else {
+ break;
+ }
+ } while (1);
}
}
#endif