Testing the patch a bit more thoroughly, I managed to find a case where the
buffer grows beyond the high watermark, and deadlocks - bufferevent_readcb()
has a check for high watermark that returns without allowing the user callback
to run. Simply removing the return from the end of the high watermark check
repairs this - but I am unsure whether this affects the expected behaviour
for the high watermark.
below is the total patch to date
--chris
--- evbuffer.c.orig Tue Apr 19 18:55:45 2005
+++ evbuffer.c Fri Feb 17 17:40:53 2006
@@ -92,13 +92,21 @@
int res = 0;
short what = EVBUFFER_READ;
size_t len;
+ int howmuch = -1;
if (event == EV_TIMEOUT) {
what |= EVBUFFER_TIMEOUT;
goto error;
}
- res = evbuffer_read(bufev->input, fd, -1);
+ /*
+ * If we have a high watermark configured then we don't want to
+ * read more data than would make us reach the watermark.
+ */
+ if (bufev->wm_read.high != 0)
+ howmuch = bufev->wm_read.high;
+
+ res = evbuffer_read(bufev->input, fd, howmuch);
if (res == -1) {
if (errno == EAGAIN || errno == EINTR)
goto reschedule;
@@ -124,7 +132,8 @@
/* Now schedule a callback for us */
evbuffer_setcb(buf, bufferevent_read_pressure_cb, bufev);
- return;
+
+ /* Fallthrough to allow the user callback to run */
}
/* Invoke the user callback - must always be called last */
--- buffer.c.orig Thu Jun 9 14:35:48 2005
+++ buffer.c Fri Feb 17 17:40:06 2006
@@ -332,8 +332,21 @@
#endif
#ifdef FIONREAD
- if (ioctl(fd, FIONREAD, &n) == -1 || n == 0)
+ if (ioctl(fd, FIONREAD, &n) == -1 || n == 0) {
n = EVBUFFER_MAX_READ;
+ } else if (n > EVBUFFER_MAX_READ && n > howmuch) {
+ /*
+ * It's possible that a lot of data is available for
+ * reading. We do not want to exhaust resources
+ * before the reader has a chance to do something
+ * about it. If the reader does not tell us how much
+ * data we should read, we artifically limit it.
+ */
+ if (n > buf->totallen << 2)
+ n = buf->totallen << 2;
+ if (n < EVBUFFER_MAX_READ)
+ n = EVBUFFER_MAX_READ;
+ }
#endif
if (howmuch < 0 || howmuch > n)
howmuch = n;
_______________________________________________
Libevent-users mailing list
[email protected]
http://monkey.org/mailman/listinfo/libevent-users