+bool event_loop(void) {
+ running = true;
+
+#ifndef HAVE_MINGW
+ fd_set readable;
+ fd_set writable;
+
+ while(running) {
+ memcpy(&readable, &readfds, sizeof readable);
+ memcpy(&writable, &writefds, sizeof writable);
+ struct timeval diff;
+ struct timeval *tv = get_time_remaining(&diff);
+
+ int fds = 0;
+
+ if(io_tree.tail) {
+ io_t *last = io_tree.tail->data;
+ fds = last->fd + 1;
+ }
+
+ int n = select(fds, &readable, &writable, NULL, tv);
+
+ if(n < 0) {
+ if(sockwouldblock(sockerrno))
+ continue;
+ else
+ return false;
+ }
+
+ if(!n)
+ continue;
+
+ for splay_each(io_t, io, &io_tree) {
+ if(FD_ISSET(io->fd, &writable))
+ io->cb(io->data, IO_WRITE);
+ else if(FD_ISSET(io->fd, &readable))
+ io->cb(io->data, IO_READ);
+ }
+ }
+#else
+ while (running) {
+ struct timeval diff;
+ struct timeval *tv = get_time_remaining(&diff);
+ DWORD timeout_ms = tv ? (tv->tv_sec * 1000 + tv->tv_usec / 1000 + 1) : WSA_INFINITE;
+
+ if (!event_count) {
+ LeaveCriticalSection(&mutex);
+ Sleep(timeout_ms);
+ EnterCriticalSection(&mutex);
+ continue;
+ }