1
0
mirror of https://github.com/osmarks/ngircd.git synced 2025-07-01 01:22:50 +00:00

io: remove outer do {} while loops for epoll/kqueue/devpoll backends

simplifies things a bit. io_dispatch() is called repeatedly from the
main loop.
This commit is contained in:
Florian Westphal 2012-01-24 21:57:23 +01:00
parent 871760583c
commit c7dd5ea0ba

View File

@ -160,39 +160,34 @@ io_dispatch_devpoll(struct timeval *tv)
{ {
struct dvpoll dvp; struct dvpoll dvp;
time_t sec = tv->tv_sec * 1000; time_t sec = tv->tv_sec * 1000;
int i, total, ret, timeout = tv->tv_usec + sec; int i, ret, timeout = tv->tv_usec + sec;
short what; short what;
struct pollfd p[100]; struct pollfd p[100];
if (timeout < 0) if (timeout < 0)
timeout = 1000; timeout = 1000;
total = 0; dvp.dp_timeout = timeout;
do { dvp.dp_nfds = 100;
dvp.dp_timeout = timeout; dvp.dp_fds = p;
dvp.dp_nfds = 100; ret = ioctl(io_masterfd, DP_POLL, &dvp);
dvp.dp_fds = p;
ret = ioctl(io_masterfd, DP_POLL, &dvp);
total += ret;
if (ret <= 0)
return total;
for (i=0; i < ret ; i++) {
what = 0;
if (p[i].revents & (POLLIN|POLLPRI))
what = IO_WANTREAD;
if (p[i].revents & POLLOUT) for (i=0; i < ret ; i++) {
what |= IO_WANTWRITE; what = 0;
if (p[i].revents & (POLLIN|POLLPRI))
what = IO_WANTREAD;
if (p[i].revents && !what) { if (p[i].revents & POLLOUT)
/* other flag is set, probably POLLERR */ what |= IO_WANTWRITE;
what = IO_ERROR;
} if (p[i].revents && !what) {
io_docallback(p[i].fd, what); /* other flag is set, probably POLLERR */
what = IO_ERROR;
} }
} while (ret == 100); io_docallback(p[i].fd, what);
}
return total; return ret;
} }
@ -462,37 +457,30 @@ static int
io_dispatch_epoll(struct timeval *tv) io_dispatch_epoll(struct timeval *tv)
{ {
time_t sec = tv->tv_sec * 1000; time_t sec = tv->tv_sec * 1000;
int i, total = 0, ret, timeout = tv->tv_usec + sec; int i, ret, timeout = tv->tv_usec + sec;
struct epoll_event epoll_ev[100]; struct epoll_event epoll_ev[100];
short type; short type;
if (timeout < 0) if (timeout < 0)
timeout = 1000; timeout = 1000;
do { ret = epoll_wait(io_masterfd, epoll_ev, 100, timeout);
ret = epoll_wait(io_masterfd, epoll_ev, 100, timeout);
total += ret;
if (ret <= 0)
return total;
for (i = 0; i < ret; i++) { for (i = 0; i < ret; i++) {
type = 0; type = 0;
if (epoll_ev[i].events & (EPOLLERR | EPOLLHUP)) if (epoll_ev[i].events & (EPOLLERR | EPOLLHUP))
type = IO_ERROR; type = IO_ERROR;
if (epoll_ev[i].events & (EPOLLIN | EPOLLPRI)) if (epoll_ev[i].events & (EPOLLIN | EPOLLPRI))
type |= IO_WANTREAD; type |= IO_WANTREAD;
if (epoll_ev[i].events & EPOLLOUT) if (epoll_ev[i].events & EPOLLOUT)
type |= IO_WANTWRITE; type |= IO_WANTWRITE;
io_docallback(epoll_ev[i].data.fd, type); io_docallback(epoll_ev[i].data.fd, type);
} }
timeout = 0; return ret;
} while (ret == 100);
return total;
} }
static void static void
@ -576,7 +564,7 @@ io_event_change_kqueue(int fd, short what, const int action)
static int static int
io_dispatch_kqueue(struct timeval *tv) io_dispatch_kqueue(struct timeval *tv)
{ {
int i, total = 0, ret; int i, ret;
struct kevent kev[100]; struct kevent kev[100];
struct kevent *newevents; struct kevent *newevents;
struct timespec ts; struct timespec ts;
@ -584,50 +572,42 @@ io_dispatch_kqueue(struct timeval *tv)
ts.tv_sec = tv->tv_sec; ts.tv_sec = tv->tv_sec;
ts.tv_nsec = tv->tv_usec * 1000; ts.tv_nsec = tv->tv_usec * 1000;
do { newevents_len = (int) array_length(&io_evcache, sizeof (struct kevent));
newevents_len = (int) array_length(&io_evcache, sizeof (struct kevent)); newevents = (newevents_len > 0) ? array_start(&io_evcache) : NULL;
newevents = (newevents_len > 0) ? array_start(&io_evcache) : NULL; assert(newevents_len >= 0);
assert(newevents_len >= 0);
ret = kevent(io_masterfd, newevents, newevents_len, kev, 100, &ts); ret = kevent(io_masterfd, newevents, newevents_len, kev, 100, &ts);
if (newevents && ret != -1) if (newevents && ret != -1)
array_trunc(&io_evcache); array_trunc(&io_evcache);
total += ret; for (i = 0; i < ret; i++) {
if (ret <= 0) io_debug("dispatch_kqueue: fd, kev.flags", (int)kev[i].ident, kev[i].flags);
return total; if (kev[i].flags & (EV_EOF|EV_ERROR)) {
if (kev[i].flags & EV_ERROR)
for (i = 0; i < ret; i++) { Log(LOG_ERR, "kevent fd %d: EV_ERROR (%s)",
io_debug("dispatch_kqueue: fd, kev.flags", (int)kev[i].ident, kev[i].flags); (int)kev[i].ident, strerror((int)kev[i].data));
if (kev[i].flags & (EV_EOF|EV_ERROR)) { io_docallback((int)kev[i].ident, IO_ERROR);
if (kev[i].flags & EV_ERROR) continue;
Log(LOG_ERR, "kevent fd %d: EV_ERROR (%s)",
(int)kev[i].ident, strerror((int)kev[i].data));
io_docallback((int)kev[i].ident, IO_ERROR);
continue;
}
switch (kev[i].filter) {
case EVFILT_READ:
io_docallback((int)kev[i].ident, IO_WANTREAD);
break;
case EVFILT_WRITE:
io_docallback((int)kev[i].ident, IO_WANTWRITE);
break;
default:
LogDebug("Unknown kev.filter number %d for fd %d",
kev[i].filter, kev[i].ident);
/* Fall through */
case EV_ERROR:
io_docallback((int)kev[i].ident, IO_ERROR);
break;
}
} }
ts.tv_sec = 0;
ts.tv_nsec = 0;
} while (ret == 100);
return total; switch (kev[i].filter) {
case EVFILT_READ:
io_docallback((int)kev[i].ident, IO_WANTREAD);
break;
case EVFILT_WRITE:
io_docallback((int)kev[i].ident, IO_WANTWRITE);
break;
default:
LogDebug("Unknown kev.filter number %d for fd %d",
kev[i].filter, kev[i].ident);
/* Fall through */
case EV_ERROR:
io_docallback((int)kev[i].ident, IO_ERROR);
break;
}
}
return ret;
} }
static void static void