+static void
+fd_change (EV_P_ int fd)
+{
+ if (anfds [fd].reify || fdchangecnt < 0)
+ return;
+
+ anfds [fd].reify = 1;
+
+ ++fdchangecnt;
+ array_needsize (fdchanges, fdchangemax, fdchangecnt, );
+ fdchanges [fdchangecnt - 1] = fd;
+}
+
+static void
+fd_kill (EV_P_ int fd)
+{
+ struct ev_io *w;
+
+ while ((w = (struct ev_io *)anfds [fd].head))
+ {
+ ev_io_stop (EV_A_ w);
+ event (EV_A_ (W)w, EV_ERROR | EV_READ | EV_WRITE);
+ }
+}
+
+/* called on EBADF to verify fds */
+static void
+fd_ebadf (EV_P)
+{
+ int fd;
+
+ for (fd = 0; fd < anfdmax; ++fd)
+ if (anfds [fd].events)
+ if (fcntl (fd, F_GETFD) == -1 && errno == EBADF)
+ fd_kill (EV_A_ fd);
+}