*
* srvx is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
+ * the Free Software Foundation; either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
extern int clock_skew;
static struct io_fd **fds;
static unsigned int fds_size;
-static fd_set read_fds, write_fds;
+static fd_set read_fds;
+static fd_set write_fds;
+static fd_set except_fds;
static int
ioset_select_init(void)
{
FD_CLR(fd->fd, &read_fds);
FD_CLR(fd->fd, &write_fds);
+ FD_CLR(fd->fd, &except_fds);
+ fds[fd->fd] = NULL;
(void)closed;
}
free(fds);
}
-#if 0
-#define debug_fdsets(MSG, NFDS, READ_FDS, WRITE_FDS, EXCEPT_FDS, SELECT_TIMEOUT) (void)0
-#else
+#if DEBUG_FDSETS
static void
debug_fdsets(const char *msg, int nfds, fd_set *read_fds, fd_set *write_fds, fd_set *except_fds, struct timeval *select_timeout) {
static const char *flag_text[8] = { "---", "r", "w", "rw", "e", "er", "ew", "erw" };
struct timeval now;
for (pos=ii=0; ii<nfds; ++ii) {
- flags = (read_fds && FD_ISSET(ii, read_fds)) ? 1 : 0;
- flags |= (write_fds && FD_ISSET(ii, write_fds)) ? 2 : 0;
- flags |= (except_fds && FD_ISSET(ii, except_fds)) ? 4 : 0;
- if (!flags)
- continue;
- pos += sprintf(buf+pos, " %d%s", ii, flag_text[flags]);
+ flags = FD_ISSET(ii, read_fds) ? 1 : 0;
+ flags |= FD_ISSET(ii, write_fds) ? 2 : 0;
+ flags |= FD_ISSET(ii, except_fds) ? 4 : 0;
+ if (flags)
+ pos += sprintf(buf+pos, " %d%s", ii, flag_text[flags]);
}
gettimeofday(&now, NULL);
if (select_timeout) {
- log_module(MAIN_LOG, LOG_DEBUG, "%s, at "FMT_TIME_T".%06ld:%s (timeout "FMT_TIME_T".%06ld)", msg, now.tv_sec, now.tv_usec, buf, select_timeout->tv_sec, select_timeout->tv_usec);
+ log_module(MAIN_LOG, LOG_DEBUG, "%s, at %lu.%06lu:%s (timeout %lu.%06lu)", msg, (unsigned long)now.tv_sec, (unsigned long)now.tv_usec, buf, (unsigned long)select_timeout->tv_sec, (unsigned long)select_timeout->tv_usec);
} else {
- log_module(MAIN_LOG, LOG_DEBUG, "%s, at "FMT_TIME_T".%06ld:%s (no timeout)", msg, now.tv_sec, now.tv_usec, buf);
+ log_module(MAIN_LOG, LOG_DEBUG, "%s, at %lu.%06lu:%s (no timeout)", msg, (unsigned long)now.tv_sec, (unsigned long)now.tv_usec, buf);
}
}
+#else
+# define debug_fdsets(MSG, NFDS, READ_FDS, WRITE_FDS, EXCEPT_FDS, SELECT_TIMEOUT) (void)0
#endif
static int
/* Set up read_fds and write_fds fdsets. */
FD_ZERO(&read_fds);
FD_ZERO(&write_fds);
+ FD_ZERO(&except_fds);
max_fd = -1;
for (nn=0; nn<fds_size; nn++) {
if (!(fd = fds[nn]))
continue;
max_fd = nn;
FD_SET(nn, &read_fds);
+ FD_SET(nn, &except_fds);
if (fd_wants_writes(fd))
FD_SET(nn, &write_fds);
}
/* Check for activity, update time. */
- debug_fdsets("Entering select", max_fd+1, &read_fds, &write_fds, NULL, timeout);
+ debug_fdsets("Entering select", max_fd+1, &read_fds, &write_fds, &except_fds, timeout);
select_result = select(max_fd + 1, &read_fds, &write_fds, NULL, timeout);
- debug_fdsets("After select", max_fd+1, &read_fds, &write_fds, NULL, timeout);
+ debug_fdsets("After select", max_fd+1, &read_fds, &write_fds, &except_fds, timeout);
now = time(NULL) + clock_skew;
if (select_result < 0) {
if (errno != EINTR) {
/* Call back anybody that has connect or read activity and wants to know. */
for (nn=0; nn<fds_size; nn++) {
- ioset_events(fds[nn], FD_ISSET(nn, &read_fds), FD_ISSET(nn, &write_fds));
+ ioset_events(fds[nn], FD_ISSET(nn, &read_fds) | FD_ISSET(nn, &except_fds), FD_ISSET(nn, &write_fds));
}
return 0;
}