]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
OPTIM: epoll: make use of EPOLLRDHUP
authorWilly Tarreau <w@1wt.eu>
Mon, 7 Jan 2013 15:19:18 +0000 (16:19 +0100)
committerWilly Tarreau <w@1wt.eu>
Mon, 7 Jan 2013 15:39:47 +0000 (16:39 +0100)
epoll may report pending shutdowns using EPOLLRDHUP. Since this
flag is missing from a number of libcs despite being available
since kernel 2.6.17, let's define it ourselves.

Doing so saves one syscall by allow us to avoid the read()==0 when
the server closes with the respose.

src/ev_epoll.c

index 90efaee054e0b2965880b2aad252bef98263dc58..034ec4c7d2f8c7b3abdb92af17f0d16797e08629 100644 (file)
@@ -40,6 +40,11 @@ static int epoll_fd;
  */
 static struct epoll_event ev;
 
+#ifndef EPOLLRDHUP
+/* EPOLLRDHUP was defined late in libc, and it appeared in kernel 2.6.17 */
+#define EPOLLRDHUP 0x2000
+#endif
+
 /*
  * speculative epoll() poller
  */
@@ -76,7 +81,7 @@ REGPRM2 static void _do_poll(struct poller *p, int exp)
                                /* construct the epoll events based on new state */
                                ev.events = 0;
                                if (en & FD_EV_POLLED_R)
-                                       ev.events |= EPOLLIN;
+                                       ev.events |= EPOLLIN | EPOLLRDHUP;
 
                                if (en & FD_EV_POLLED_W)
                                        ev.events |= EPOLLOUT;
@@ -137,8 +142,8 @@ REGPRM2 static void _do_poll(struct poller *p, int exp)
        /* process polled events */
 
        for (count = 0; count < status; count++) {
-               unsigned char n;
-               unsigned char e = epoll_events[count].events;
+               unsigned int n;
+               unsigned int e = epoll_events[count].events;
                fd = epoll_events[count].data.fd;
 
                if (!fdtab[fd].owner)
@@ -161,6 +166,10 @@ REGPRM2 static void _do_poll(struct poller *p, int exp)
                                ((e & EPOLLHUP) ? FD_POLL_HUP : 0);
                }
 
+               /* always remap RDHUP to HUP as they're used similarly */
+               if (e & EPOLLRDHUP)
+                       n |= FD_POLL_HUP;
+
                if (!n)
                        continue;