-#ifdef IO_USE_SELECT
-static int
-io_dispatch_select(struct timeval *tv)
-{
- fd_set readers_tmp = readers;
- fd_set writers_tmp = writers;
- short what;
- int ret, i;
- int fds_ready;
- ret = select(select_maxfd + 1, &readers_tmp, &writers_tmp, NULL, tv);
- if (ret <= 0)
- return ret;
-
- fds_ready = ret;
-
- for (i = 0; i <= select_maxfd; i++) {
- what = 0;
- if (FD_ISSET(i, &readers_tmp)) {
- what = IO_WANTREAD;
- fds_ready--;
- }
-
- if (FD_ISSET(i, &writers_tmp)) {
- what |= IO_WANTWRITE;
- fds_ready--;
- }
- if (what)
- io_docallback(i, what);
- if (fds_ready <= 0)
- break;
- }
-
- return ret;
-}
-#endif
-
-
-#ifdef IO_USE_DEVPOLL
-static int
-io_dispatch_devpoll(struct timeval *tv)
-{
- struct dvpoll dvp;
- time_t sec = tv->tv_sec * 1000;
- int i, total, ret, timeout = tv->tv_usec + sec;
- short what;
- struct pollfd p[100];
-
- if (timeout < 0)
- timeout = 1000;
-
- total = 0;
- do {
- dvp.dp_timeout = timeout;
- dvp.dp_nfds = 100;
- 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)
- what |= IO_WANTWRITE;
-
- if (p[i].revents && !what) {
- /* other flag is set, probably POLLERR */
- what = IO_ERROR;
- }
- io_docallback(p[i].fd, what);
- }
- } while (ret == 100);
-
- return total;
-}
-#endif
-
-
-#ifdef IO_USE_POLL
-static int
-io_dispatch_poll(struct timeval *tv)
-{
- time_t sec = tv->tv_sec * 1000;
- int i, ret, timeout = tv->tv_usec + sec;
- int fds_ready;
- short what;
- struct pollfd *p = array_start(&pollfds);
-
- if (timeout < 0)
- timeout = 1000;
-
- ret = poll(p, poll_maxfd + 1, timeout);
- if (ret <= 0)
- return ret;
-
- fds_ready = ret;
- for (i=0; i <= poll_maxfd; i++) {
- what = 0;
- if (p[i].revents & (POLLIN|POLLPRI))
- what = IO_WANTREAD;
-
- if (p[i].revents & POLLOUT)
- what |= IO_WANTWRITE;
-
- if (p[i].revents && !what) {
- /* other flag is set, probably POLLERR */
- what = IO_ERROR;
- }
- if (what) {
- fds_ready--;
- io_docallback(i, what);
- }
- if (fds_ready <= 0)
- break;
- }
-
- return ret;
-}
-#endif
-
-
-#ifdef IO_USE_EPOLL
-static int
-io_dispatch_epoll(struct timeval *tv)
-{
- time_t sec = tv->tv_sec * 1000;
- int i, total = 0, ret, timeout = tv->tv_usec + sec;
- struct epoll_event epoll_ev[100];
- short type;
-
- if (timeout < 0)
- timeout = 1000;
-
- do {
- ret = epoll_wait(io_masterfd, epoll_ev, 100, timeout);
- total += ret;
- if (ret <= 0)
- return total;
-
- for (i = 0; i < ret; i++) {
- type = 0;
- if (epoll_ev[i].events & (EPOLLERR | EPOLLHUP))
- type = IO_ERROR;
-
- if (epoll_ev[i].events & (EPOLLIN | EPOLLPRI))
- type |= IO_WANTREAD;
-
- if (epoll_ev[i].events & EPOLLOUT)
- type |= IO_WANTWRITE;
-
- io_docallback(epoll_ev[i].data.fd, type);
- }
-
- timeout = 0;
- } while (ret == 100);
-
- return total;
-}
-#endif
-
-
-#ifdef IO_USE_KQUEUE
-static int
-io_dispatch_kqueue(struct timeval *tv)
-{
- int i, total = 0, ret;
- struct kevent kev[100];
- struct kevent *newevents;
- struct timespec ts;
- int newevents_len;
- ts.tv_sec = tv->tv_sec;
- ts.tv_nsec = tv->tv_usec * 1000;
-
- do {
- newevents_len = (int) array_length(&io_evcache, sizeof (struct kevent));
- newevents = (newevents_len > 0) ? array_start(&io_evcache) : NULL;
- assert(newevents_len >= 0);
- if (newevents_len < 0)
- newevents_len = 0;
-#ifdef DEBUG
- if (newevents_len)
- assert(newevents != NULL);
-#endif
- ret = kevent(io_masterfd, newevents, newevents_len, kev,
- 100, &ts);
- if ((newevents_len>0) && ret != -1)
- array_trunc(&io_evcache);
-
- total += ret;
- if (ret <= 0)
- return total;
-
- for (i = 0; i < ret; i++) {
- if (kev[i].flags & EV_EOF) {
-#ifdef DEBUG
- LogDebug("kev.flag has EV_EOF set, setting IO_ERROR",
- kev[i].filter, kev[i].ident);
-#endif
- 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:
-#ifdef DEBUG
- LogDebug("Unknown kev.filter number %d for fd %d",
- kev[i].filter, kev[i].ident); /* Fall through */
-#endif
- 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;
-}
-#endif
-
-