*** empty log message ***

master
Marc Alexander Lehmann 2008-10-23 04:56:49 +00:00
parent c1f58cdfd9
commit c02a5a6abb
4 changed files with 38 additions and 30 deletions

View File

@ -1,6 +1,13 @@
Revision history for libev, a high-performance and full-featured event loop.
WISH? monotonic clocks times/GetTickCount for coarse corrections?
- further optimise away the EPOLL_CTL_ADD/MOD combo in the epoll
backend by assuming the kernel event mask hasn't changed if
ADD fails with EEXIST.
- use memset to initialise most arrays now and do away with the
init functions.
3.45 Tue Oct 21 21:59:26 CEST 2008
- disable inotify usage on linux <2.6.25, as it is broken
(reported by Yoann Vandoorselaere).

35
ev.c
View File

@ -451,6 +451,8 @@ typedef struct
WL head;
unsigned char events;
unsigned char reify;
unsigned char emask; /* the epoll backend stores the actual kernel mask in here */
unsigned char unused; /* currently unused padding */
#if EV_SELECT_IS_WINSOCKET
SOCKET handle;
#endif
@ -613,6 +615,9 @@ array_realloc (int elem, void *base, int *cur, int cnt)
return ev_realloc (base, elem * *cur);
}
#define array_init_zero(base,count) \
memset ((void *)(base), 0, sizeof (*(base)) * (count))
#define array_needsize(type,base,cur,cnt,init) \
if (expect_false ((cnt) > (cur))) \
{ \
@ -665,19 +670,6 @@ queue_events (EV_P_ W *events, int eventcnt, int type)
/*****************************************************************************/
void inline_size
anfds_init (ANFD *base, int count)
{
while (count--)
{
base->head = 0;
base->events = EV_NONE;
base->reify = 0;
++base;
}
}
void inline_speed
fd_event (EV_P_ int fd, int revents)
{
@ -977,18 +969,6 @@ static int signalmax;
static EV_ATOMIC_T gotsig;
void inline_size
signals_init (ANSIG *base, int count)
{
while (count--)
{
base->head = 0;
base->gotsig = 0;
++base;
}
}
/*****************************************************************************/
void inline_speed
@ -2141,11 +2121,12 @@ ev_io_start (EV_P_ ev_io *w)
return;
assert (("ev_io_start called with negative fd", fd >= 0));
assert (("ev_io start called with illegal event mask", !(w->events & ~(EV_IOFDSET | EV_READ | EV_WRITE))));
EV_FREQUENT_CHECK;
ev_start (EV_A_ (W)w, 1);
array_needsize (ANFD, anfds, anfdmax, fd + 1, anfds_init);
array_needsize (ANFD, anfds, anfdmax, fd + 1, array_init_zero);
wlist_add (&anfds[fd].head, (WL)w);
fd_change (EV_A_ fd, w->events & EV_IOFDSET | 1);
@ -2347,7 +2328,7 @@ ev_signal_start (EV_P_ ev_signal *w)
sigprocmask (SIG_SETMASK, &full, &prev);
#endif
array_needsize (ANSIG, signals, signalmax, w->signum, signals_init);
array_needsize (ANSIG, signals, signalmax, w->signum, array_init_zero);
#ifndef _WIN32
sigprocmask (SIG_SETMASK, &prev, 0);

View File

@ -57,20 +57,34 @@
#include <sys/epoll.h>
void inline_size
unsigned_char_init (unsigned char *base, int count)
{
/* memset might be overkill */
while (count--)
*base++ = 0;
}
static void
epoll_modify (EV_P_ int fd, int oev, int nev)
{
struct epoll_event ev;
unsigned char oldmask;
/*
* we handle EPOLL_CTL_DEL by ignoring it here
* on the assumption that the fd is gone anyways
* if that is wrong, we have to handle the spurious
* event in epoll_poll.
* the fd is later added, we try to ADD it, and, if that
* fails, we assume it still has the same eventmask.
*/
if (!nev)
return;
oldmask = anfds [fd].emask;
anfds [fd].emask = nev;
ev.data.u64 = fd; /* use u64 to fully initialise the struct, for nicer strace etc. */
ev.events = (nev & EV_READ ? EPOLLIN : 0)
| (nev & EV_WRITE ? EPOLLOUT : 0);
@ -80,7 +94,7 @@ epoll_modify (EV_P_ int fd, int oev, int nev)
if (expect_true (errno == ENOENT))
{
/* on ENOENT the fd went away, so try to do the right thing */
/* if ENOENT then the fd went away, so try to do the right thing */
if (!nev)
return;
@ -89,8 +103,9 @@ epoll_modify (EV_P_ int fd, int oev, int nev)
}
else if (expect_true (errno == EEXIST))
{
/* on EEXIST we ignored a previous DEL */
if (!epoll_ctl (backend_fd, EPOLL_CTL_MOD, fd, &ev))
/* EEXIST means we ignored a previous DEL, but the fd is still active */
/* if the kernel mask is the same as the new mask, we assume it hasn't changed */
if (oldmask == nev || !epoll_ctl (backend_fd, EPOLL_CTL_MOD, fd, &ev))
return;
}
@ -122,7 +137,10 @@ epoll_poll (EV_P_ ev_tstamp timeout)
if (expect_false (got & ~want))
{
anfds [fd].emask = want;
/* we received an event but are not interested in it, try mod or del */
/* I don't think we ever need MOD, but let's handle it anyways */
ev->events = (want & EV_READ ? EPOLLIN : 0)
| (want & EV_WRITE ? EPOLLOUT : 0);

View File

@ -42,6 +42,8 @@
void inline_size
pollidx_init (int *base, int count)
{
/* consider using memset (.., -1, ...), which is pratically guarenteed
* to work on all systems implementing poll */
while (count--)
*base++ = -1;
}