diff options
-rw-r--r-- | source3/include/event.h | 32 | ||||
-rw-r--r-- | source3/lib/events.c | 309 |
2 files changed, 177 insertions, 164 deletions
diff --git a/source3/include/event.h b/source3/include/event.h index 3d40000cb8..93112a86fa 100644 --- a/source3/include/event.h +++ b/source3/include/event.h @@ -18,35 +18,14 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ -struct event_context; -struct fd_event; -struct timed_event; +#define TEVENT_COMPAT_DEFINES +#include <tevent.h> -/* bits for file descriptor event flags */ -#define EVENT_FD_READ 1 -#define EVENT_FD_WRITE 2 +#undef event_context_init +#define event_context_init(mem_ctx) s3_tevent_context_init(mem_ctx) /* The following definitions come from lib/events.c */ -struct timed_event *_event_add_timed(struct event_context *event_ctx, - TALLOC_CTX *mem_ctx, - struct timeval when, - const char *event_name, - void (*handler)(struct event_context *event_ctx, - struct timed_event *te, - struct timeval now, - void *private_data), - void *private_data); -#define event_add_timed(event_ctx, mem_ctx, when, handler, private_data) \ - _event_add_timed(event_ctx, mem_ctx, when, #handler, handler, private_data) -struct fd_event *event_add_fd(struct event_context *event_ctx, - TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, - void (*handler)(struct event_context *event_ctx, - struct fd_event *event, - uint16 flags, - void *private_data), - void *private_data); void event_fd_set_writeable(struct fd_event *fde); void event_fd_set_not_writeable(struct fd_event *fde); void event_fd_set_readable(struct fd_event *fde); @@ -59,8 +38,7 @@ bool run_events(struct event_context *event_ctx, int selrtn, fd_set *read_fds, fd_set *write_fds); struct timeval *get_timed_events_timeout(struct event_context *event_ctx, struct timeval *to_ret); -int event_loop_once(struct event_context *ev); void event_context_reinit(struct event_context *ev); -struct event_context *event_context_init(TALLOC_CTX *mem_ctx); void dump_event_list(struct event_context *event_ctx); +struct tevent_context *s3_tevent_context_init(TALLOC_CTX *mem_ctx); diff --git a/source3/lib/events.c b/source3/lib/events.c index 9e9d335c7b..be2fdcb68f 100644 --- a/source3/lib/events.c +++ b/source3/lib/events.c @@ -19,42 +19,19 @@ */ #include "includes.h" +#include <tevent_internal.h> -struct timed_event { - struct timed_event *next, *prev; - struct event_context *event_ctx; - struct timeval when; - const char *event_name; - void (*handler)(struct event_context *event_ctx, - struct timed_event *te, - struct timeval now, - void *private_data); - void *private_data; +struct s3_event_context { + struct tevent_context *ev; + struct tevent_fd *fd_events; }; -struct fd_event { - struct fd_event *prev, *next; - struct event_context *event_ctx; - int fd; - uint16_t flags; /* see EVENT_FD_* flags */ - void (*handler)(struct event_context *event_ctx, - struct fd_event *event, - uint16 flags, - void *private_data); - void *private_data; -}; - -struct event_context { - struct timed_event *timed_events; - struct fd_event *fd_events; -}; - -static int timed_event_destructor(struct timed_event *te) +static int s3_event_timer_destructor(struct tevent_timer *te) { - DEBUG(10, ("Destroying timed event %lx \"%s\"\n", (unsigned long)te, - te->event_name)); + DEBUG(10, ("Destroying timer event %p \"%s\"\n", + te, te->handler_name)); if (te->event_ctx != NULL) { - DLIST_REMOVE(te->event_ctx->timed_events, te); + DLIST_REMOVE(te->event_ctx->timer_events, te); } return 0; } @@ -63,23 +40,23 @@ static int timed_event_destructor(struct timed_event *te) Add te by time. ****************************************************************************/ -static void add_event_by_time(struct timed_event *te) +static void add_event_by_time(struct tevent_timer *te) { - struct event_context *ctx = te->event_ctx; - struct timed_event *last_te, *cur_te; + struct tevent_context *ctx = te->event_ctx; + struct tevent_timer *last_te, *cur_te; /* Keep the list ordered by time. We must preserve this. */ last_te = NULL; - for (cur_te = ctx->timed_events; cur_te; cur_te = cur_te->next) { + for (cur_te = ctx->timer_events; cur_te; cur_te = cur_te->next) { /* if the new event comes before the current one break */ - if (!timeval_is_zero(&cur_te->when) && - timeval_compare(&te->when, &cur_te->when) < 0) { + if (!timeval_is_zero(&cur_te->next_event) && + timeval_compare(&te->next_event, &cur_te->next_event) < 0) { break; } last_te = cur_te; } - DLIST_ADD_AFTER(ctx->timed_events, te, last_te); + DLIST_ADD_AFTER(ctx->timer_events, te, last_te); } /**************************************************************************** @@ -88,115 +65,128 @@ static void add_event_by_time(struct timed_event *te) handed to it. ****************************************************************************/ -struct timed_event *_event_add_timed(struct event_context *event_ctx, - TALLOC_CTX *mem_ctx, - struct timeval when, - const char *event_name, - void (*handler)(struct event_context *event_ctx, - struct timed_event *te, - struct timeval now, - void *private_data), - void *private_data) +static struct tevent_timer *s3_event_add_timer(struct tevent_context *event_ctx, + TALLOC_CTX *mem_ctx, + struct timeval when, + tevent_timer_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { - struct timed_event *te; + struct tevent_timer *te; - te = TALLOC_P(mem_ctx, struct timed_event); + te = TALLOC_P(mem_ctx, struct tevent_timer); if (te == NULL) { DEBUG(0, ("talloc failed\n")); return NULL; } te->event_ctx = event_ctx; - te->when = when; - te->event_name = event_name; + te->next_event = when; te->handler = handler; te->private_data = private_data; + te->handler_name = handler_name; + te->location = location; + te->additional_data = NULL; add_event_by_time(te); - talloc_set_destructor(te, timed_event_destructor); + talloc_set_destructor(te, s3_event_timer_destructor); - DEBUG(10, ("Added timed event \"%s\": %lx\n", event_name, - (unsigned long)te)); + DEBUG(10, ("Added timed event \"%s\": %p\n", handler_name, te)); return te; } -static int fd_event_destructor(struct fd_event *fde) +static int s3_event_fd_destructor(struct tevent_fd *fde) { if (fde->event_ctx != NULL) { - DLIST_REMOVE(fde->event_ctx->fd_events, fde); + struct s3_event_context *ev3; + ev3 = talloc_get_type(fde->event_ctx->additional_data, + struct s3_event_context); + DLIST_REMOVE(ev3->fd_events, fde); + } + if (fde->close_fn) { + fde->close_fn(fde->event_ctx, fde, fde->fd, fde->private_data); + fde->fd = -1; } return 0; } -struct fd_event *event_add_fd(struct event_context *event_ctx, - TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, - void (*handler)(struct event_context *event_ctx, - struct fd_event *event, - uint16 flags, - void *private_data), - void *private_data) +static struct tevent_fd *s3_event_add_fd(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + int fd, + uint16_t flags, + tevent_fd_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { - struct fd_event *fde; + struct s3_event_context *ev3 = talloc_get_type(ev->additional_data, + struct s3_event_context); + struct tevent_fd *fde; - if (!(fde = TALLOC_P(mem_ctx, struct fd_event))) { + if (!(fde = TALLOC_P(mem_ctx, struct tevent_fd))) { return NULL; } - fde->event_ctx = event_ctx; + fde->event_ctx = ev; fde->fd = fd; fde->flags = flags; fde->handler = handler; + fde->close_fn = NULL; fde->private_data = private_data; + fde->handler_name = handler_name; + fde->location = location; - DLIST_ADD(event_ctx->fd_events, fde); + DLIST_ADD(ev3->fd_events, fde); - talloc_set_destructor(fde, fd_event_destructor); + talloc_set_destructor(fde, s3_event_fd_destructor); return fde; } -void event_fd_set_writeable(struct fd_event *fde) +void event_fd_set_writeable(struct tevent_fd *fde) { - fde->flags |= EVENT_FD_WRITE; + TEVENT_FD_WRITEABLE(fde); } -void event_fd_set_not_writeable(struct fd_event *fde) +void event_fd_set_not_writeable(struct tevent_fd *fde) { - fde->flags &= ~EVENT_FD_WRITE; + TEVENT_FD_NOT_WRITEABLE(fde); } -void event_fd_set_readable(struct fd_event *fde) +void event_fd_set_readable(struct tevent_fd *fde) { - fde->flags |= EVENT_FD_READ; + TEVENT_FD_READABLE(fde); } -void event_fd_set_not_readable(struct fd_event *fde) +void event_fd_set_not_readable(struct tevent_fd *fde) { - fde->flags &= ~EVENT_FD_READ; + TEVENT_FD_NOT_READABLE(fde); } /* * Return if there's something in the queue */ -bool event_add_to_select_args(struct event_context *event_ctx, +bool event_add_to_select_args(struct tevent_context *ev, const struct timeval *now, fd_set *read_fds, fd_set *write_fds, struct timeval *timeout, int *maxfd) { - struct fd_event *fde; + struct s3_event_context *ev3 = talloc_get_type(ev->additional_data, + struct s3_event_context); + struct tevent_fd *fde; struct timeval diff; - bool ret = False; + bool ret = false; - for (fde = event_ctx->fd_events; fde; fde = fde->next) { + for (fde = ev3->fd_events; fde; fde = fde->next) { if (fde->flags & EVENT_FD_READ) { FD_SET(fde->fd, read_fds); - ret = True; + ret = true; } if (fde->flags & EVENT_FD_WRITE) { FD_SET(fde->fd, write_fds); - ret = True; + ret = true; } if ((fde->flags & (EVENT_FD_READ|EVENT_FD_WRITE)) @@ -205,46 +195,48 @@ bool event_add_to_select_args(struct event_context *event_ctx, } } - if (event_ctx->timed_events == NULL) { + if (ev->timer_events == NULL) { return ret; } - diff = timeval_until(now, &event_ctx->timed_events->when); + diff = timeval_until(now, &ev->timer_events->next_event); *timeout = timeval_min(timeout, &diff); - return True; + return true; } -bool run_events(struct event_context *event_ctx, +bool run_events(struct tevent_context *ev, int selrtn, fd_set *read_fds, fd_set *write_fds) { - bool fired = False; - struct fd_event *fde, *next; + struct s3_event_context *ev3 = talloc_get_type(ev->additional_data, + struct s3_event_context); + bool fired = false; + struct tevent_fd *fde, *next; /* Run all events that are pending, not just one (as we did previously. */ - while (event_ctx->timed_events) { + while (ev->timer_events) { struct timeval now; GetTimeOfDay(&now); if (timeval_compare( - &now, &event_ctx->timed_events->when) < 0) { + &now, &ev->timer_events->next_event) < 0) { /* Nothing to do yet */ DEBUG(11, ("run_events: Nothing to do\n")); break; } - DEBUG(10, ("Running event \"%s\" %lx\n", - event_ctx->timed_events->event_name, - (unsigned long)event_ctx->timed_events)); + DEBUG(10, ("Running event \"%s\" %p\n", + ev->timer_events->handler_name, + ev->timer_events)); - event_ctx->timed_events->handler( - event_ctx, - event_ctx->timed_events, now, - event_ctx->timed_events->private_data); + ev->timer_events->handler( + ev, + ev->timer_events, now, + ev->timer_events->private_data); - fired = True; + fired = true; } if (fired) { @@ -252,7 +244,7 @@ bool run_events(struct event_context *event_ctx, * We might have changed the socket status during the timed * events, return to run select again. */ - return True; + return true; } if (selrtn == 0) { @@ -262,7 +254,7 @@ bool run_events(struct event_context *event_ctx, return fired; } - for (fde = event_ctx->fd_events; fde; fde = next) { + for (fde = ev3->fd_events; fde; fde = next) { uint16 flags = 0; next = fde->next; @@ -270,8 +262,8 @@ bool run_events(struct event_context *event_ctx, if (FD_ISSET(fde->fd, write_fds)) flags |= EVENT_FD_WRITE; if (flags & fde->flags) { - fde->handler(event_ctx, fde, flags, fde->private_data); - fired = True; + fde->handler(ev, fde, flags, fde->private_data); + fired = true; } } @@ -279,17 +271,17 @@ bool run_events(struct event_context *event_ctx, } -struct timeval *get_timed_events_timeout(struct event_context *event_ctx, +struct timeval *get_timed_events_timeout(struct tevent_context *ev, struct timeval *to_ret) { struct timeval now; - if (event_ctx->timed_events == NULL) { + if (ev->timer_events == NULL) { return NULL; } now = timeval_current(); - *to_ret = timeval_until(&now, &event_ctx->timed_events->when); + *to_ret = timeval_until(&now, &ev->timer_events->next_event); DEBUG(10, ("timed_events_timeout: %d/%d\n", (int)to_ret->tv_sec, (int)to_ret->tv_usec)); @@ -297,7 +289,7 @@ struct timeval *get_timed_events_timeout(struct event_context *event_ctx, return to_ret; } -int event_loop_once(struct event_context *ev) +static int s3_event_loop_once(struct tevent_context *ev) { struct timeval now, to; fd_set r_fds, w_fds; @@ -331,45 +323,60 @@ int event_loop_once(struct event_context *ev) return 0; } -static int event_context_destructor(struct event_context *ev) +static int s3_event_loop_wait(struct tevent_context *ev) +{ + int ret = 0; + + while (ret == 0) { + ret = s3_event_loop_once(ev); + } + + return ret; +} + +static int s3_event_context_destructor(struct tevent_context *ev) { - while (ev->fd_events != NULL) { - ev->fd_events->event_ctx = NULL; - DLIST_REMOVE(ev->fd_events, ev->fd_events); + struct s3_event_context *ev3 = talloc_get_type(ev->additional_data, + struct s3_event_context); + while (ev3->fd_events != NULL) { + ev3->fd_events->event_ctx = NULL; + DLIST_REMOVE(ev3->fd_events, ev3->fd_events); } - while (ev->timed_events != NULL) { - ev->timed_events->event_ctx = NULL; - DLIST_REMOVE(ev->timed_events, ev->timed_events); + while (ev->timer_events != NULL) { + ev->timer_events->event_ctx = NULL; + DLIST_REMOVE(ev->timer_events, ev3->ev->timer_events); } return 0; } -void event_context_reinit(struct event_context *ev) +void event_context_reinit(struct tevent_context *ev) { - event_context_destructor(ev); + s3_event_context_destructor(ev); return; } -struct event_context *event_context_init(TALLOC_CTX *mem_ctx) +static int s3_event_context_init(struct tevent_context *ev) { - struct event_context *result; + struct s3_event_context *ev3; - result = TALLOC_ZERO_P(mem_ctx, struct event_context); - if (result == NULL) { - return NULL; - } + ev3 = talloc_zero(ev, struct s3_event_context); + if (!ev3) return -1; + ev3->ev = ev; - talloc_set_destructor(result, event_context_destructor); - return result; + ev->additional_data = ev3; + talloc_set_destructor(ev, s3_event_context_destructor); + return 0; } -void dump_event_list(struct event_context *event_ctx) +void dump_event_list(struct tevent_context *ev) { - struct timed_event *te; - struct fd_event *fe; + struct s3_event_context *ev3 = talloc_get_type(ev->additional_data, + struct s3_event_context); + struct tevent_timer *te; + struct tevent_fd *fe; struct timeval evt, now; - if (!event_ctx) { + if (!ev) { return; } @@ -377,22 +384,50 @@ void dump_event_list(struct event_context *event_ctx) DEBUG(10,("dump_event_list:\n")); - for (te = event_ctx->timed_events; te; te = te->next) { + for (te = ev->timer_events; te; te = te->next) { - evt = timeval_until(&now, &te->when); + evt = timeval_until(&now, &te->next_event); - DEBUGADD(10,("Timed Event \"%s\" %lx handled in %d seconds (at %s)\n", - te->event_name, - (unsigned long)te, + DEBUGADD(10,("Timed Event \"%s\" %p handled in %d seconds (at %s)\n", + te->handler_name, + te, (int)evt.tv_sec, - http_timestring(talloc_tos(), te->when.tv_sec))); + http_timestring(talloc_tos(), te->next_event.tv_sec))); } - for (fe = event_ctx->fd_events; fe; fe = fe->next) { + for (fe = ev3->fd_events; fe; fe = fe->next) { - DEBUGADD(10,("FD Event %d %lx, flags: 0x%04x\n", + DEBUGADD(10,("FD Event %d %p, flags: 0x%04x\n", fe->fd, - (unsigned long)fe, + fe, fe->flags)); } } + +static const struct tevent_ops s3_event_ops = { + .context_init = s3_event_context_init, + .add_fd = s3_event_add_fd, + .set_fd_close_fn= tevent_common_fd_set_close_fn, + .get_fd_flags = tevent_common_fd_get_flags, + .set_fd_flags = tevent_common_fd_set_flags, + .add_timer = s3_event_add_timer, + .loop_once = s3_event_loop_once, + .loop_wait = s3_event_loop_wait, +}; + +static bool s3_tevent_init(void) +{ + static bool initialized; + if (initialized) { + return true; + } + initialized = tevent_register_backend("s3", &s3_event_ops); + tevent_set_default_backend("s3"); + return initialized; +} + +struct tevent_context *s3_tevent_context_init(TALLOC_CTX *mem_ctx) +{ + s3_tevent_init(); + return tevent_context_init_byname(mem_ctx, "s3"); +} |