CLEANUP: polling: gcc doesn't always optimize constants away
In ev_poll and ev_epoll, we have a bit-to-bit mapping between the POLL_
constants and the FD_POLL_ constants. A comment said that gcc was able
to detect this and to automatically apply a mask. Things have possibly
changed since the output assembly doesn't always reflect this. So let's
perform an explicit assignment when bits are equal.
diff --git a/src/ev_epoll.c b/src/ev_epoll.c
index 2cd596a..8b0d684 100644
--- a/src/ev_epoll.c
+++ b/src/ev_epoll.c
@@ -144,15 +144,22 @@
continue;
/* it looks complicated but gcc can optimize it away when constants
- * have same values.
+ * have same values... In fact it depends on gcc :-(
*/
fdtab[fd].ev &= FD_POLL_STICKY;
- fdtab[fd].ev |=
- ((e & EPOLLIN ) ? FD_POLL_IN : 0) |
- ((e & EPOLLPRI) ? FD_POLL_PRI : 0) |
- ((e & EPOLLOUT) ? FD_POLL_OUT : 0) |
- ((e & EPOLLERR) ? FD_POLL_ERR : 0) |
- ((e & EPOLLHUP) ? FD_POLL_HUP : 0);
+ if (EPOLLIN == FD_POLL_IN && EPOLLOUT == FD_POLL_OUT &&
+ EPOLLPRI == FD_POLL_PRI && EPOLLERR == FD_POLL_ERR &&
+ EPOLLHUP == FD_POLL_HUP) {
+ fdtab[fd].ev |= e & (EPOLLIN|EPOLLOUT|EPOLLPRI|EPOLLERR|EPOLLHUP);
+ }
+ else {
+ fdtab[fd].ev |=
+ ((e & EPOLLIN ) ? FD_POLL_IN : 0) |
+ ((e & EPOLLPRI) ? FD_POLL_PRI : 0) |
+ ((e & EPOLLOUT) ? FD_POLL_OUT : 0) |
+ ((e & EPOLLERR) ? FD_POLL_ERR : 0) |
+ ((e & EPOLLHUP) ? FD_POLL_HUP : 0);
+ }
if (fdtab[fd].iocb && fdtab[fd].owner && fdtab[fd].ev) {
int new_updt, old_updt = fd_nbupdt; /* Save number of updates to detect creation of new FDs. */
diff --git a/src/ev_poll.c b/src/ev_poll.c
index cdc357f..2c7501d 100644
--- a/src/ev_poll.c
+++ b/src/ev_poll.c
@@ -154,12 +154,21 @@
if (!fdtab[fd].owner)
continue;
+ /* it looks complicated but gcc can optimize it away when constants
+ * have same values... In fact it depends on gcc :-(
+ */
fdtab[fd].ev &= FD_POLL_STICKY;
- fdtab[fd].ev |=
- ((e & POLLIN ) ? FD_POLL_IN : 0) |
- ((e & POLLOUT) ? FD_POLL_OUT : 0) |
- ((e & POLLERR) ? FD_POLL_ERR : 0) |
- ((e & POLLHUP) ? FD_POLL_HUP : 0);
+ if (POLLIN == FD_POLL_IN && POLLOUT == FD_POLL_OUT &&
+ POLLERR == FD_POLL_ERR && POLLHUP == FD_POLL_HUP) {
+ fdtab[fd].ev |= e & (POLLIN|POLLOUT|POLLERR|POLLHUP);
+ }
+ else {
+ fdtab[fd].ev |=
+ ((e & POLLIN ) ? FD_POLL_IN : 0) |
+ ((e & POLLOUT) ? FD_POLL_OUT : 0) |
+ ((e & POLLERR) ? FD_POLL_ERR : 0) |
+ ((e & POLLHUP) ? FD_POLL_HUP : 0);
+ }
if (fdtab[fd].iocb && fdtab[fd].owner && fdtab[fd].ev) {
/* Mark the events as speculative before processing