Permalink
Browse files

libevent 0.5

  • Loading branch information...
1 parent 384663c commit c26ec4ce115b8479c3a13a2917cc15782ef60ef0 itojun committed Jun 14, 2002
Showing with 171 additions and 17 deletions.
  1. +50 −8 kame/kame/faithd.libevent/event.c
  2. +18 −2 kame/kame/faithd.libevent/event.h
  3. +103 −7 kame/kame/faithd.libevent/select.c
@@ -81,6 +81,7 @@ void event_queue_remove(struct event *, int);
static RB_HEAD(event_tree, event) timetree;
static struct event_list activequeue;
+struct event_list signalqueue;
struct event_list eventqueue;
static struct timeval event_tv;
@@ -111,6 +112,7 @@ event_init(void)
RB_INIT(&timetree);
TAILQ_INIT(&eventqueue);
TAILQ_INIT(&activequeue);
+ TAILQ_INIT(&signalqueue);
evbase = NULL;
for (i = 0; eventops[i] && !evbase; i++) {
@@ -129,19 +131,27 @@ int
event_haveevents(void)
{
return (RB_ROOT(&timetree) || TAILQ_FIRST(&eventqueue) ||
- TAILQ_FIRST(&activequeue));
+ TAILQ_FIRST(&signalqueue) || TAILQ_FIRST(&activequeue));
}
void
event_process_active(void)
{
struct event *ev;
+ short ncalls;
for (ev = TAILQ_FIRST(&activequeue); ev;
ev = TAILQ_FIRST(&activequeue)) {
event_queue_remove(ev, EVLIST_ACTIVE);
- (*ev->ev_callback)(ev->ev_fd, ev->ev_res, ev->ev_arg);
+ /* Allows deletes to work */
+ ncalls = ev->ev_ncalls;
+ ev->ev_pncalls = &ncalls;
+ while (ncalls) {
+ ncalls--;
+ ev->ev_ncalls = ncalls;
+ (*ev->ev_callback)(ev->ev_fd, ev->ev_res, ev->ev_arg);
+ }
}
}
@@ -226,6 +236,8 @@ event_set(struct event *ev, int fd, short events,
ev->ev_fd = fd;
ev->ev_events = events;
ev->ev_flags = EVLIST_INIT;
+ ev->ev_ncalls = 0;
+ ev->ev_pncalls = NULL;
}
/*
@@ -269,14 +281,15 @@ event_add(struct event *ev, struct timeval *tv)
if (tv != NULL) {
struct timeval now;
+ if (ev->ev_flags & EVLIST_TIMEOUT)
+ event_queue_remove(ev, EVLIST_TIMEOUT);
+
gettimeofday(&now, NULL);
timeradd(&now, tv, &ev->ev_timeout);
LOG_DBG((LOG_MISC, 55,
"event_add: timeout in %d seconds, call %p",
tv->tv_sec, ev->ev_callback));
- if (ev->ev_flags & EVLIST_TIMEOUT)
- event_queue_remove(ev, EVLIST_TIMEOUT);
event_queue_insert(ev, EVLIST_TIMEOUT);
}
@@ -286,6 +299,11 @@ event_add(struct event *ev, struct timeval *tv)
event_queue_insert(ev, EVLIST_INSERTED);
return (evsel->add(evbase, ev));
+ } else if ((ev->ev_events & EV_SIGNAL) &&
+ !(ev->ev_flags & EVLIST_SIGNAL)) {
+ event_queue_insert(ev, EVLIST_SIGNAL);
+
+ return (evsel->add(evbase, ev));
}
return (0);
@@ -299,6 +317,12 @@ event_del(struct event *ev)
assert(!(ev->ev_flags & ~EVLIST_ALL));
+ /* See if we are just active executing this event in a loop */
+ if (ev->ev_ncalls && ev->ev_pncalls) {
+ /* Abort loop */
+ *ev->ev_pncalls = 0;
+ }
+
if (ev->ev_flags & EVLIST_TIMEOUT)
event_queue_remove(ev, EVLIST_TIMEOUT);
@@ -308,27 +332,39 @@ event_del(struct event *ev)
if (ev->ev_flags & EVLIST_INSERTED) {
event_queue_remove(ev, EVLIST_INSERTED);
return (evsel->del(evbase, ev));
+ } else if (ev->ev_flags & EVLIST_SIGNAL) {
+ event_queue_remove(ev, EVLIST_SIGNAL);
+ return (evsel->del(evbase, ev));
}
return (0);
}
void
-event_active(struct event *ev, int res)
+event_active(struct event *ev, int res, short ncalls)
{
+ /* We get different kinds of events, add them together */
+ if (ev->ev_flags & EVLIST_ACTIVE) {
+ ev->ev_res |= res;
+ return;
+ }
+
ev->ev_res = res;
+ ev->ev_ncalls = ncalls;
+ ev->ev_pncalls = NULL;
event_queue_insert(ev, EVLIST_ACTIVE);
}
int
timeout_next(struct timeval *tv)
{
+ struct timeval dflt = TIMEOUT_DEFAULT;
+
struct timeval now;
struct event *ev;
if ((ev = RB_MIN(event_tree, &timetree)) == NULL) {
- timerclear(tv);
- tv->tv_sec = TIMEOUT_DEFAULT;
+ *tv = dflt;
return (0);
}
@@ -378,7 +414,7 @@ timeout_process(void)
LOG_DBG((LOG_MISC, 60, "timeout_process: call %p",
ev->ev_callback));
- event_active(ev, EV_TIMEOUT);
+ event_active(ev, EV_TIMEOUT, 1);
}
}
@@ -419,6 +455,9 @@ event_queue_remove(struct event *ev, int queue)
case EVLIST_ACTIVE:
TAILQ_REMOVE(&activequeue, ev, ev_active_next);
break;
+ case EVLIST_SIGNAL:
+ TAILQ_REMOVE(&signalqueue, ev, ev_signal_next);
+ break;
case EVLIST_TIMEOUT:
RB_REMOVE(event_tree, &timetree, ev);
break;
@@ -442,6 +481,9 @@ event_queue_insert(struct event *ev, int queue)
case EVLIST_ACTIVE:
TAILQ_INSERT_TAIL(&activequeue, ev, ev_active_next);
break;
+ case EVLIST_SIGNAL:
+ TAILQ_INSERT_TAIL(&signalqueue, ev, ev_signal_next);
+ break;
case EVLIST_TIMEOUT:
timeout_insert(ev);
break;
@@ -36,6 +36,7 @@ extern "C" {
#define EVLIST_TIMEOUT 0x01
#define EVLIST_INSERTED 0x02
+#define EVLIST_SIGNAL 0x04
#define EVLIST_ACTIVE 0x08
#define EVLIST_INIT 0x80
@@ -45,6 +46,8 @@ extern "C" {
#define EV_TIMEOUT 0x01
#define EV_READ 0x02
#define EV_WRITE 0x04
+#define EV_SIGNAL 0x08
+#define EV_PERSIST 0x10 /* Persistant event */
/* Fix so that ppl dont have to run with <sys/queue.h> */
#ifndef TAILQ_ENTRY
@@ -69,10 +72,13 @@ struct { \
struct event {
TAILQ_ENTRY (event) ev_next;
TAILQ_ENTRY (event) ev_active_next;
+ TAILQ_ENTRY (event) ev_signal_next;
RB_ENTRY (event) ev_timeout_node;
int ev_fd;
short ev_events;
+ short ev_ncalls;
+ short *ev_pncalls; /* Allows deletes in callback */
struct timeval ev_timeout;
@@ -83,6 +89,9 @@ struct event {
int ev_flags;
};
+#define EVENT_SIGNAL(ev) ev->ev_fd
+#define EVENT_FD(ev) ev->ev_fd
+
#ifdef _EVENT_DEFINED_TQENTRY
#undef TAILQ_ENTRY
#undef _EVENT_DEFINED_TQENTRY
@@ -103,7 +112,7 @@ struct eventop {
int (*dispatch)(void *, struct timeval *);
};
-#define TIMEOUT_DEFAULT 5
+#define TIMEOUT_DEFAULT {5, 0}
void event_init(void);
int event_dispatch(void);
@@ -122,10 +131,17 @@ void timeout_process(void);
#define timeout_pending(ev, tv) event_pending(ev, EV_TIMEOUT, tv)
#define timeout_initialized(ev) ((ev)->ev_flags & EVLIST_INIT)
+#define signal_add(ev, tv) event_add(ev, tv)
+#define signal_set(ev, x, cb, arg) \
+ event_set(ev, x, EV_SIGNAL|EV_PERSIST, cb, arg)
+#define signal_del(ev) event_del(ev)
+#define signal_pending(ev, tv) event_pending(ev, EV_SIGNAL, tv)
+#define signal_initialized(ev) ((ev)->ev_flags & EVLIST_INIT)
+
void event_set(struct event *, int, short, void (*)(int, short, void *), void *);
int event_add(struct event *, struct timeval *);
int event_del(struct event *);
- void event_active(struct event *, int);
+void event_active(struct event *, int, short);
int event_pending(struct event *, short, struct timeval *);
Oops, something went wrong. Retry.

0 comments on commit c26ec4c

Please sign in to comment.