diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/replace/test/os2_delete.c | 8 | ||||
-rw-r--r-- | lib/tevent/config.mk | 46 | ||||
-rw-r--r-- | lib/tevent/configure.ac | 7 | ||||
-rw-r--r-- | lib/tevent/libtevent.m4 | 37 | ||||
-rw-r--r-- | lib/tevent/pytevent.c | 39 | ||||
-rw-r--r-- | lib/tevent/samba.m4 | 16 | ||||
-rw-r--r-- | lib/tevent/tests.py | 8 | ||||
-rw-r--r-- | lib/tevent/testsuite.c | 3 | ||||
-rw-r--r-- | lib/tevent/tevent.c | 193 | ||||
-rw-r--r-- | lib/tevent/tevent.h | 136 | ||||
-rw-r--r-- | lib/tevent/tevent.mk | 11 | ||||
-rw-r--r-- | lib/tevent/tevent.pc.in | 2 | ||||
-rw-r--r-- | lib/tevent/tevent_aio.c | 94 | ||||
-rw-r--r-- | lib/tevent/tevent_debug.c | 32 | ||||
-rw-r--r-- | lib/tevent/tevent_epoll.c | 82 | ||||
-rw-r--r-- | lib/tevent/tevent_fd.c | 42 | ||||
-rw-r--r-- | lib/tevent/tevent_internal.h | 109 | ||||
-rw-r--r-- | lib/tevent/tevent_select.c | 76 | ||||
-rw-r--r-- | lib/tevent/tevent_signal.c | 44 | ||||
-rw-r--r-- | lib/tevent/tevent_standard.c | 100 | ||||
-rw-r--r-- | lib/tevent/tevent_timed.c | 27 |
21 files changed, 606 insertions, 506 deletions
diff --git a/lib/replace/test/os2_delete.c b/lib/replace/test/os2_delete.c index b45c135355..44efeea08a 100644 --- a/lib/replace/test/os2_delete.c +++ b/lib/replace/test/os2_delete.c @@ -30,7 +30,9 @@ static int test_readdir_os2_delete_ret; static void cleanup(void) { /* I'm a lazy bastard */ - system("rm -rf " TESTDIR); + if (system("rm -rf " TESTDIR)) { + FAILED("system"); + } mkdir(TESTDIR, 0700) == 0 || FAILED("mkdir"); } @@ -118,7 +120,9 @@ int test_readdir_os2_delete(void) rmdir(TESTDIR) == 0 || FAILED("rmdir"); - system("rm -rf " TESTDIR); + if (system("rm -rf " TESTDIR) == -1) { + FAILED("system"); + } return test_readdir_os2_delete_ret; } diff --git a/lib/tevent/config.mk b/lib/tevent/config.mk deleted file mode 100644 index e4fb9a8088..0000000000 --- a/lib/tevent/config.mk +++ /dev/null @@ -1,46 +0,0 @@ -############################## -[MODULE::TEVENT_AIO] -PRIVATE_DEPENDENCIES = LIBAIO_LINUX -OUTPUT_TYPE = MERGED_OBJ -SUBSYSTEM = LIBTEVENT -############################## - -TEVENT_AIO_OBJ_FILES = $(libteventsrcdir)/tevent_aio.o - -############################## -[MODULE::TEVENT_EPOLL] -OUTPUT_TYPE = MERGED_OBJ -SUBSYSTEM = LIBTEVENT -############################## - -TEVENT_EPOLL_OBJ_FILES = $(libteventsrcdir)/tevent_epoll.o - -############################## -[MODULE::TEVENT_SELECT] -OUTPUT_TYPE = MERGED_OBJ -SUBSYSTEM = LIBTEVENT -############################## - -TEVENT_SELECT_OBJ_FILES = $(libteventsrcdir)/tevent_select.o - -############################## -[MODULE::TEVENT_STANDARD] -OUTPUT_TYPE = MERGED_OBJ -SUBSYSTEM = LIBTEVENT -############################## - -TEVENT_STANDARD_OBJ_FILES = $(libteventsrcdir)/tevent_standard.o - -################################################ -# Start SUBSYSTEM LIBTEVENT -[LIBRARY::LIBTEVENT] -PUBLIC_DEPENDENCIES = LIBTALLOC -OUTPUT_TYPE = MERGED_OBJ -CFLAGS = -I../lib/tevent -# -# End SUBSYSTEM LIBTEVENT -################################################ - -LIBTEVENT_OBJ_FILES = $(addprefix $(libteventsrcdir)/, tevent.o tevent_timed.o tevent_signal.o tevent_debug.o tevent_util.o) - -PUBLIC_HEADERS += $(addprefix $(libteventsrcdir)/, tevent.h tevent_internal.h) diff --git a/lib/tevent/configure.ac b/lib/tevent/configure.ac index 22d306b0f6..3cc06a144a 100644 --- a/lib/tevent/configure.ac +++ b/lib/tevent/configure.ac @@ -1,11 +1,8 @@ AC_PREREQ(2.50) -AC_DEFUN([SMB_MODULE_DEFAULT], [echo -n ""]) -AC_DEFUN([SMB_LIBRARY_ENABLE], [echo -n ""]) -AC_DEFUN([SMB_ENABLE], [echo -n ""]) -AC_DEFUN([SMB_EXT_LIB], [echo -n ""]) -AC_INIT(tevent, 0.9.0) +AC_INIT(tevent, 0.9.2) AC_CONFIG_SRCDIR([tevent.c]) AC_CONFIG_HEADER(config.h) + AC_LIBREPLACE_ALL_CHECKS AC_LD_EXPORT_DYNAMIC diff --git a/lib/tevent/libtevent.m4 b/lib/tevent/libtevent.m4 index 30105d9bef..ec2ed9cd1f 100644 --- a/lib/tevent/libtevent.m4 +++ b/lib/tevent/libtevent.m4 @@ -1,12 +1,14 @@ dnl find the tevent sources. This is meant to work both for dnl standalone builds, and builds of packages using libtevent + +AC_SUBST(teventdir) + if test x"$teventdir" = "x"; then teventdir="" teventpaths="$srcdir $srcdir/../lib/tevent $srcdir/tevent $srcdir/../tevent" for d in $teventpaths; do if test -f "$d/tevent.c"; then teventdir="$d" - AC_SUBST(teventdir) break; fi done @@ -15,37 +17,32 @@ if test x"$teventdir" = "x"; then fi fi -TEVENT_OBJ="tevent.o tevent_select.o tevent_signal.o tevent_timed.o tevent_standard.o tevent_debug.o tevent_util.o" -AC_LIBREPLACE_NETWORK_CHECKS +TEVENT_OBJ="" +TEVENT_CFLAGS="" +TEVENT_LIBS="" +AC_SUBST(TEVENT_OBJ) +AC_SUBST(TEVENT_CFLAGS) +AC_SUBST(TEVENT_LIBS) + +TEVENT_CFLAGS="-I$teventdir" + +TEVENT_OBJ="tevent.o tevent_fd.o tevent_timed.o tevent_signal.o tevent_debug.o tevent_util.o" +TEVENT_OBJ="$TEVENT_OBJ tevent_standard.o tevent_select.o" -SMB_ENABLE(TEVENT_EPOLL, NO) -SMB_ENABLE(TEVENT_AIO, NO) +tevent_cv_aio_support=no AC_CHECK_HEADERS(sys/epoll.h) AC_CHECK_FUNCS(epoll_create) if test x"$ac_cv_header_sys_epoll_h" = x"yes" -a x"$ac_cv_func_epoll_create" = x"yes"; then TEVENT_OBJ="$TEVENT_OBJ tevent_epoll.o" - SMB_ENABLE(TEVENT_EPOLL,YES) AC_DEFINE(HAVE_EPOLL, 1, [Whether epoll available]) - #TODO: remove HAVE_EVENTS_EPOLL and use HAVE_EPOLL - AC_DEFINE(HAVE_EVENTS_EPOLL, 1, [Whether epoll available]) # check for native Linux AIO interface AC_CHECK_HEADERS(libaio.h) - AC_CHECK_LIB_EXT(aio, AIO_LIBS, io_getevents) + AC_CHECK_LIB_EXT(aio, TEVENT_LIBS, io_getevents) if test x"$ac_cv_header_libaio_h" = x"yes" -a x"$ac_cv_lib_ext_aio_io_getevents" = x"yes";then TEVENT_OBJ="$TEVENT_OBJ tevent_aio.o" - SMB_ENABLE(TEVENT_AIO,YES) + tevent_cv_aio_support=yes AC_DEFINE(HAVE_LINUX_AIO, 1, [Whether Linux AIO is available]) fi fi -AC_SUBST(TEVENT_OBJ) -SMB_EXT_LIB(LIBAIO_LINUX, $AIO_LIBS) - -TEVENT_CFLAGS="-I$teventdir" -AC_SUBST(TEVENT_CFLAGS) - -TEVENT_LIBS="$AIO_LIBS" -AC_SUBST(TEVENT_LIBS) - - diff --git a/lib/tevent/pytevent.c b/lib/tevent/pytevent.c index a969373738..3d71d78397 100644 --- a/lib/tevent/pytevent.c +++ b/lib/tevent/pytevent.c @@ -24,9 +24,9 @@ typedef struct { PyObject_HEAD struct tevent_context *ev_ctx; -} PyEventContextObject; +} PyTEventContextObject; -PyAPI_DATA(PyTypeObject) PyEventContext; +PyAPI_DATA(PyTypeObject) PyTEventContext; static PyObject *py_set_default_backend(PyObject *self, PyObject *args) { @@ -34,13 +34,13 @@ static PyObject *py_set_default_backend(PyObject *self, PyObject *args) if (!PyArg_ParseTuple(args, "s", &name)) return NULL; - event_set_default_backend(name); + tevent_set_default_backend(name); return Py_None; } static PyObject *py_backend_list(PyObject *self) { - const char **backends = event_backend_list(NULL); + const char **backends = tevent_backend_list(NULL); PyObject *ret; int i, len; @@ -66,28 +66,28 @@ static PyObject *py_event_ctx_new(PyTypeObject *type, PyObject *args, PyObject * const char *kwnames[] = { "name", NULL }; char *name = NULL; struct tevent_context *ev_ctx; - PyEventContextObject *ret; + PyTEventContextObject *ret; if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|s", (char **)kwnames, &name)) return NULL; if (name == NULL) - ev_ctx = event_context_init(NULL); + ev_ctx = tevent_context_init(NULL); else - ev_ctx = event_context_init_byname(NULL, name); + ev_ctx = tevent_context_init_byname(NULL, name); - ret = (PyEventContextObject *)type->tp_alloc(type, 0); + ret = (PyTEventContextObject *)type->tp_alloc(type, 0); ret->ev_ctx = ev_ctx; return (PyObject *)ret; } -static PyObject *py_event_ctx_loop_once(PyEventContextObject *self) +static PyObject *py_event_ctx_loop_once(PyTEventContextObject *self) { - return PyInt_FromLong(event_loop_once(self->ev_ctx)); + return PyInt_FromLong(tevent_loop_once(self->ev_ctx)); } -static PyObject *py_event_ctx_loop_wait(PyEventContextObject *self) +static PyObject *py_event_ctx_loop_wait(PyTEventContextObject *self) { - return PyInt_FromLong(event_loop_wait(self->ev_ctx)); + return PyInt_FromLong(tevent_loop_wait(self->ev_ctx)); } static PyMethodDef py_event_ctx_methods[] = { @@ -98,16 +98,17 @@ static PyMethodDef py_event_ctx_methods[] = { { NULL } }; -static void py_event_ctx_dealloc(PyEventContextObject * self) +static void py_event_ctx_dealloc(PyTEventContextObject * self) { talloc_free(self->ev_ctx); self->ob_type->tp_free(self); } -PyTypeObject PyEventContext = { - .tp_name = "EventContext", + +PyTypeObject PyTEventContext = { + .tp_name = "TEventContext", .tp_methods = py_event_ctx_methods, - .tp_basicsize = sizeof(PyEventContextObject), + .tp_basicsize = sizeof(PyTEventContextObject), .tp_dealloc = (destructor)py_event_ctx_dealloc, .tp_flags = Py_TPFLAGS_DEFAULT, .tp_new = py_event_ctx_new, @@ -117,14 +118,14 @@ void inittevent(void) { PyObject *m; - if (PyType_Ready(&PyEventContext) < 0) + if (PyType_Ready(&PyTEventContext) < 0) return; m = Py_InitModule3("tevent", tevent_methods, "Event management."); if (m == NULL) return; - Py_INCREF(&PyEventContext); - PyModule_AddObject(m, "EventContext", (PyObject *)&PyEventContext); + Py_INCREF(&PyTEventContext); + PyModule_AddObject(m, "TEventContext", (PyObject *)&PyTEventContext); } diff --git a/lib/tevent/samba.m4 b/lib/tevent/samba.m4 new file mode 100644 index 0000000000..89b0b705b4 --- /dev/null +++ b/lib/tevent/samba.m4 @@ -0,0 +1,16 @@ + +teventdir="\$(libteventsrcdir)" +m4_include(../lib/tevent/libtevent.m4) + +SMB_EXT_LIB(LIBTEVENT_EXT, [${TEVENT_LIBS}]) +SMB_ENABLE(LIBTEVENT_EXT) + +SMB_SUBSYSTEM(LIBTEVENT, + [\$(addprefix \$(libteventsrcdir)/, ${TEVENT_OBJ})], + [LIBTEVENT_EXT], + [${TEVENT_CFLAGS}]) + +SMB_MAKE_SETTINGS([ +PUBLIC_HEADERS += \$(addprefix \$(libteventsrcdir)/, tevent.h tevent_internal.h) +]) + diff --git a/lib/tevent/tests.py b/lib/tevent/tests.py index 0ec736b359..bf594a14f6 100644 --- a/lib/tevent/tests.py +++ b/lib/tevent/tests.py @@ -17,15 +17,15 @@ # along with this program. If not, see <http://www.gnu.org/licenses/>. # -import tevent as events +import tevent import unittest # Just test the bindings are there and that calling them doesn't crash # anything. -class EventTestCase(unittest.TestCase): +class TEventTestCase(unittest.TestCase): def test_create(self): - self.assertTrue(events.EventContext() is not None) + self.assertTrue(tevent.TEventContext() is not None) def test_loop_wait(self): - self.assertEquals(0, events.EventContext().loop_wait()) + self.assertEquals(0, tevent.TEventContext().loop_wait()) diff --git a/lib/tevent/testsuite.c b/lib/tevent/testsuite.c index ec57c5ad2e..1b811f5fa2 100644 --- a/lib/tevent/testsuite.c +++ b/lib/tevent/testsuite.c @@ -81,8 +81,9 @@ static bool test_event_context(struct torture_context *test, /* create a pipe */ pipe(fd); - fde = event_add_fd(ev_ctx, ev_ctx, fd[0], EVENT_FD_READ|EVENT_FD_AUTOCLOSE, + fde = event_add_fd(ev_ctx, ev_ctx, fd[0], EVENT_FD_READ, fde_handler, fd); + tevent_fd_set_auto_close(fde); event_add_timed(ev_ctx, ev_ctx, timeval_current_ofs(2,0), finished_handler, &finished); diff --git a/lib/tevent/tevent.c b/lib/tevent/tevent.c index e45a690c33..5582b583e7 100644 --- a/lib/tevent/tevent.c +++ b/lib/tevent/tevent.c @@ -41,52 +41,53 @@ handler to get another event. To setup a set of events you first need to create a event_context - structure using the function event_context_init(); This returns a + structure using the function tevent_context_init(); This returns a 'struct tevent_context' that you use in all subsequent calls. After that you can add/remove events that you are interested in - using event_add_*() and talloc_free() + using tevent_add_*() and talloc_free() - Finally, you call event_loop_wait_once() to block waiting for one of the - events to occor or event_loop_wait() which will loop + Finally, you call tevent_loop_wait_once() to block waiting for one of the + events to occor or tevent_loop_wait() which will loop forever. */ #include "replace.h" +#include "system/filesys.h" #include "tevent.h" #include "tevent_internal.h" #include "tevent_util.h" -struct event_ops_list { - struct event_ops_list *next, *prev; +struct tevent_ops_list { + struct tevent_ops_list *next, *prev; const char *name; - const struct event_ops *ops; + const struct tevent_ops *ops; }; /* list of registered event backends */ -static struct event_ops_list *event_backends = NULL; -static char *event_default_backend = NULL; +static struct tevent_ops_list *tevent_backends = NULL; +static char *tevent_default_backend = NULL; /* register an events backend */ -bool event_register_backend(const char *name, const struct event_ops *ops) +bool tevent_register_backend(const char *name, const struct tevent_ops *ops) { - struct event_ops_list *e; + struct tevent_ops_list *e; - for (e = event_backends; e != NULL; e = e->next) { + for (e = tevent_backends; e != NULL; e = e->next) { if (0 == strcmp(e->name, name)) { /* already registered, skip it */ return true; } } - e = talloc(talloc_autofree_context(), struct event_ops_list); + e = talloc(talloc_autofree_context(), struct tevent_ops_list); if (e == NULL) return false; e->name = name; e->ops = ops; - DLIST_ADD(event_backends, e); + DLIST_ADD(tevent_backends, e); return true; } @@ -94,38 +95,39 @@ bool event_register_backend(const char *name, const struct event_ops *ops) /* set the default event backend */ -void event_set_default_backend(const char *backend) +void tevent_set_default_backend(const char *backend) { - if (event_default_backend) free(event_default_backend); - event_default_backend = strdup(backend); + talloc_free(tevent_default_backend); + tevent_default_backend = talloc_strdup(talloc_autofree_context(), + backend); } /* initialise backends if not already done */ -static void event_backend_init(void) +static void tevent_backend_init(void) { - events_select_init(); - events_standard_init(); -#if HAVE_EVENTS_EPOLL - events_epoll_init(); + tevent_select_init(); + tevent_standard_init(); +#ifdef HAVE_EPOLL + tevent_epoll_init(); #endif -#if HAVE_LINUX_AIO - events_aio_init(); +#ifdef HAVE_LINUX_AIO + tevent_aio_init(); #endif } /* list available backends */ -const char **event_backend_list(TALLOC_CTX *mem_ctx) +const char **tevent_backend_list(TALLOC_CTX *mem_ctx) { const char **list = NULL; - struct event_ops_list *e; + struct tevent_ops_list *e; - event_backend_init(); + tevent_backend_init(); - for (e=event_backends;e;e=e->next) { + for (e=tevent_backends;e;e=e->next) { list = ev_str_list_add(list, e->name); } @@ -143,10 +145,10 @@ const char **event_backend_list(TALLOC_CTX *mem_ctx) This function is for allowing third-party-applications to hook in gluecode to their own event loop code, so that they can make async usage of our client libs - NOTE: use event_context_init() inside of samba! + NOTE: use tevent_context_init() inside of samba! */ -static struct tevent_context *event_context_init_ops(TALLOC_CTX *mem_ctx, - const struct event_ops *ops) +static struct tevent_context *tevent_context_init_ops(TALLOC_CTX *mem_ctx, + const struct tevent_ops *ops) { struct tevent_context *ev; int ret; @@ -170,22 +172,23 @@ static struct tevent_context *event_context_init_ops(TALLOC_CTX *mem_ctx, call, and all subsequent calls pass this event_context as the first element. Event handlers also receive this as their first argument. */ -struct tevent_context *event_context_init_byname(TALLOC_CTX *mem_ctx, const char *name) +struct tevent_context *tevent_context_init_byname(TALLOC_CTX *mem_ctx, + const char *name) { - struct event_ops_list *e; + struct tevent_ops_list *e; - event_backend_init(); + tevent_backend_init(); if (name == NULL) { - name = event_default_backend; + name = tevent_default_backend; } if (name == NULL) { name = "standard"; } - for (e=event_backends;e;e=e->next) { + for (e=tevent_backends;e;e=e->next) { if (strcmp(name, e->name) == 0) { - return event_context_init_ops(mem_ctx, e->ops); + return tevent_context_init_ops(mem_ctx, e->ops); } } return NULL; @@ -197,42 +200,74 @@ struct tevent_context *event_context_init_byname(TALLOC_CTX *mem_ctx, const char call, and all subsequent calls pass this event_context as the first element. Event handlers also receive this as their first argument. */ -struct tevent_context *event_context_init(TALLOC_CTX *mem_ctx) +struct tevent_context *tevent_context_init(TALLOC_CTX *mem_ctx) { - return event_context_init_byname(mem_ctx, NULL); + return tevent_context_init_byname(mem_ctx, NULL); } /* add a fd based event return NULL on failure (memory allocation error) - if flags contains EVENT_FD_AUTOCLOSE then the fd will be closed when + if flags contains TEVENT_FD_AUTOCLOSE then the fd will be closed when the returned fd_event context is freed */ -struct tevent_fd *event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, event_fd_handler_t handler, - void *private_data) +struct tevent_fd *_tevent_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) { - return ev->ops->add_fd(ev, mem_ctx, fd, flags, handler, private_data); + return ev->ops->add_fd(ev, mem_ctx, fd, flags, handler, private_data, + handler_name, location); } /* add a disk aio event */ -struct aio_event *event_add_aio(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - struct iocb *iocb, - event_aio_handler_t handler, - void *private_data) +struct tevent_aio *_tevent_add_aio(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + struct iocb *iocb, + tevent_aio_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { if (ev->ops->add_aio == NULL) return NULL; - return ev->ops->add_aio(ev, mem_ctx, iocb, handler, private_data); + return ev->ops->add_aio(ev, mem_ctx, iocb, handler, private_data, + handler_name, location); +} + +/* + set a close function on the fd event +*/ +void tevent_fd_set_close_fn(struct tevent_fd *fde, + tevent_fd_close_fn_t close_fn) +{ + if (!fde) return; + fde->event_ctx->ops->set_fd_close_fn(fde, close_fn); +} + +static void tevent_fd_auto_close_fn(struct tevent_context *ev, + struct tevent_fd *fde, + int fd, + void *private_data) +{ + close(fd); +} + +void tevent_fd_set_auto_close(struct tevent_fd *fde) +{ + tevent_fd_set_close_fn(fde, tevent_fd_auto_close_fn); } /* return the fd event flags */ -uint16_t event_get_fd_flags(struct tevent_fd *fde) +uint16_t tevent_fd_get_flags(struct tevent_fd *fde) { if (!fde) return 0; return fde->event_ctx->ops->get_fd_flags(fde); @@ -241,22 +276,26 @@ uint16_t event_get_fd_flags(struct tevent_fd *fde) /* set the fd event flags */ -void event_set_fd_flags(struct tevent_fd *fde, uint16_t flags) +void tevent_fd_set_flags(struct tevent_fd *fde, uint16_t flags) { if (!fde) return; fde->event_ctx->ops->set_fd_flags(fde, flags); } /* - add a timed event + add a timer event return NULL on failure */ -struct tevent_timer *event_add_timed(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - struct timeval next_event, - event_timed_handler_t handler, - void *private_data) +struct tevent_timer *_tevent_add_timer(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + struct timeval next_event, + tevent_timer_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { - return ev->ops->add_timer(ev, mem_ctx, next_event, handler, private_data); + return ev->ops->add_timer(ev, mem_ctx, next_event, handler, private_data, + handler_name, location); } /* @@ -266,19 +305,23 @@ struct tevent_timer *event_add_timed(struct tevent_context *ev, TALLOC_CTX *mem_ return NULL on failure */ -struct signal_event *event_add_signal(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - int signum, - int sa_flags, - event_signal_handler_t handler, - void *private_data) +struct tevent_signal *_tevent_add_signal(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + int signum, + int sa_flags, + tevent_signal_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { - return ev->ops->add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data); + return ev->ops->add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data, + handler_name, location); } /* do a single event loop using the events defined in ev */ -int event_loop_once(struct tevent_context *ev) +int tevent_loop_once(struct tevent_context *ev) { return ev->ops->loop_once(ev); } @@ -286,25 +329,7 @@ int event_loop_once(struct tevent_context *ev) /* return on failure or (with 0) if all fd events are removed */ -int event_loop_wait(struct tevent_context *ev) +int tevent_loop_wait(struct tevent_context *ev) { return ev->ops->loop_wait(ev); } - -/* - find an event context that is a parent of the given memory context, - or create a new event context as a child of the given context if - none is found - - This should be used in preference to event_context_init() in places - where you would prefer to use the existing event context if possible - (which is most situations) -*/ -struct tevent_context *event_context_find(TALLOC_CTX *mem_ctx) -{ - struct tevent_context *ev = talloc_find_parent_bytype(mem_ctx, struct tevent_context); - if (ev == NULL) { - ev = event_context_init(mem_ctx); - } - return ev; -} diff --git a/lib/tevent/tevent.h b/lib/tevent/tevent.h index f626de9d12..b57d96f5fb 100644 --- a/lib/tevent/tevent.h +++ b/lib/tevent/tevent.h @@ -33,59 +33,93 @@ struct tevent_aio; struct tevent_signal; /* event handler types */ -typedef void (*tevent_fd_handler_t)(struct tevent_context *, - struct tevent_fd *, - uint16_t , void *); -typedef void (*tevent_timer_handler_t)(struct tevent_context *, - struct tevent_timer *, - struct timeval , void *); -typedef void (*tevent_signal_handler_t)(struct tevent_context *, - struct tevent_signal *, - int , int, void *, void *); -typedef void (*tevent_aio_handler_t)(struct tevent_context *, - struct tevent_aio *, - int, void *); +typedef void (*tevent_fd_handler_t)(struct tevent_context *ev, + struct tevent_fd *fde, + uint16_t flags, + void *private_data); +typedef void (*tevent_fd_close_fn_t)(struct tevent_context *ev, + struct tevent_fd *fde, + int fd, + void *private_data); +typedef void (*tevent_timer_handler_t)(struct tevent_context *ev, + struct tevent_timer *te, + struct timeval current_time, + void *private_data); +typedef void (*tevent_signal_handler_t)(struct tevent_context *ev, + struct tevent_signal *se, + int signum, + int count, + void *siginfo, + void *private_data); +typedef void (*tevent_aio_handler_t)(struct tevent_context *ev, + struct tevent_aio *ae, + int ret, + void *private_data); struct tevent_context *tevent_context_init(TALLOC_CTX *mem_ctx); struct tevent_context *tevent_context_init_byname(TALLOC_CTX *mem_ctx, const char *name); const char **tevent_backend_list(TALLOC_CTX *mem_ctx); void tevent_set_default_backend(const char *backend); -struct tevent_fd *tevent_add_fd(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, - tevent_fd_handler_t handler, - void *private_data); - -struct tevent_timer *tevent_add_timer(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - struct timeval next_event, - tevent_timer_handler_t handler, - void *private_data); - -struct tevent_signal *tevent_add_signal(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - int signum, int sa_flags, - tevent_signal_handler_t handler, - void *private_data); +struct tevent_fd *_tevent_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); +#define tevent_add_fd(ev, mem_ctx, fd, flags, handler, private_data) \ + _tevent_add_fd(ev, mem_ctx, fd, flags, handler, private_data, \ + #handler, __location__) + +struct tevent_timer *_tevent_add_timer(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + struct timeval next_event, + tevent_timer_handler_t handler, + void *private_data, + const char *handler_name, + const char *location); +#define tevent_add_timer(ev, mem_ctx, next_event, handler, private_data) \ + _tevent_add_timer(ev, mem_ctx, next_event, handler, private_data, \ + #handler, __location__); + +struct tevent_signal *_tevent_add_signal(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + int signum, + int sa_flags, + tevent_signal_handler_t handler, + void *private_data, + const char *handler_name, + const char *location); +#define tevent_add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data) \ + _tevent_add_signal(ev, mem_ctx, signum, sa_flags, handler, private_data, \ + #handler, __location__) struct iocb; -struct tevent_aio *tevent_add_aio(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - struct iocb *iocb, - tevent_aio_handler_t handler, - void *private_data); +struct tevent_aio *_tevent_add_aio(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + struct iocb *iocb, + tevent_aio_handler_t handler, + void *private_data, + const char *handler_name, + const char *location); +#define tevent_add_aio(ev, mem_ctx, iocb, handler, private_data) \ + _tevent_add_aio(ev, mem_ctx, iocb, handler, private_data, \ + #handler, __location__); int tevent_loop_once(struct tevent_context *ev); int tevent_loop_wait(struct tevent_context *ev); +void tevent_fd_set_close_fn(struct tevent_fd *fde, + tevent_fd_close_fn_t close_fn); +void tevent_fd_set_auto_close(struct tevent_fd *fde); uint16_t tevent_fd_get_flags(struct tevent_fd *fde); void tevent_fd_set_flags(struct tevent_fd *fde, uint16_t flags); /* bits for file descriptor event flags */ #define TEVENT_FD_READ 1 #define TEVENT_FD_WRITE 2 -#define TEVENT_FD_AUTOCLOSE 4 #define TEVENT_FD_WRITEABLE(fde) \ tevent_fd_set_flags(fde, tevent_fd_get_flags(fde) | TEVENT_FD_WRITE) @@ -97,10 +131,21 @@ void tevent_fd_set_flags(struct tevent_fd *fde, uint16_t flags); #define TEVENT_FD_NOT_READABLE(fde) \ tevent_fd_set_flags(fde, tevent_fd_get_flags(fde) & ~TEVENT_FD_READ) -/* for now always define the compat symbols */ -#ifndef TEVENT_COMPAT_DEFINES -#define TEVENT_COMPAT_DEFINES 1 -#endif +/* DEBUG */ +enum tevent_debug_level { + TEVENT_DEBUG_FATAL, + TEVENT_DEBUG_ERROR, + TEVENT_DEBUG_WARNING, + TEVENT_DEBUG_TRACE +}; + +int tevent_set_debug(struct tevent_context *ev, + void (*debug)(void *context, + enum tevent_debug_level level, + const char *fmt, + va_list ap) PRINTF_ATTRIBUTE(3,0), + void *context); +int tevent_set_debug_stderr(struct tevent_context *ev); #ifdef TEVENT_COMPAT_DEFINES @@ -154,7 +199,6 @@ void tevent_fd_set_flags(struct tevent_fd *fde, uint16_t flags); #define EVENT_FD_READ TEVENT_FD_READ #define EVENT_FD_WRITE TEVENT_FD_WRITE -#define EVENT_FD_AUTOCLOSE TEVENT_FD_AUTOCLOSE #define EVENT_FD_WRITEABLE(fde) \ TEVENT_FD_WRITEABLE(fde) @@ -168,6 +212,18 @@ void tevent_fd_set_flags(struct tevent_fd *fde, uint16_t flags); #define EVENT_FD_NOT_READABLE(fde) \ TEVENT_FD_NOT_READABLE(fde) +#define ev_debug_level tevent_debug_level + +#define EV_DEBUG_FATAL TEVENT_DEBUG_FATAL +#define EV_DEBUG_ERROR TEVENT_DEBUG_ERROR +#define EV_DEBUG_WARNING TEVENT_DEBUG_WARNING +#define EV_DEBUG_TRACE TEVENT_DEBUG_TRACE + +#define ev_set_debug(ev, debug, context) \ + tevent_set_debug(ev, debug, context) + +#define ev_set_debug_stderr(_ev) tevent_set_debug_stderr(ev) + #endif /* TEVENT_COMPAT_DEFINES */ #endif /* __TEVENT_H__ */ diff --git a/lib/tevent/tevent.mk b/lib/tevent/tevent.mk index 6538362a06..be7e298218 100644 --- a/lib/tevent/tevent.mk +++ b/lib/tevent/tevent.mk @@ -1,11 +1,12 @@ -TEVENT_SONAME = libtevent.$(SHLIBEXT).0 -TEVENT_SOLIB = libtevent.$(SHLIBEXT).$(PACKAGE_VERSION) +TEVENT_SOBASE = libtevent.$(SHLIBEXT) +TEVENT_SONAME = $(TEVENT_SOBASE).0 +TEVENT_SOLIB = $(TEVENT_SOBASE).$(PACKAGE_VERSION) TEVENT_STLIB = libtevent.a $(TEVENT_STLIB): $(TEVENT_OBJ) ar -rv $(TEVENT_STLIB) $(TEVENT_OBJ) -libtevent.$(SHLIBEXT): $(TEVENT_SOLIB) +$(TEVENT_SOBASE): $(TEVENT_SOLIB) ln -fs $< $@ $(TEVENT_SONAME): $(TEVENT_SOLIB) @@ -31,7 +32,7 @@ installlibs:: installdirs install:: all installdirs installheaders installlibs $(PYTHON_INSTALL_TARGET) clean:: - rm -f $(TEVENT_SONAME) $(TEVENT_SOLIB) $(TEVENT_STLIB) libtevent.$(SHLIBEXT) + rm -f $(TEVENT_SOBASE) $(TEVENT_SONAME) $(TEVENT_SOLIB) $(TEVENT_STLIB) rm -f tevent.pc rm -f tevent.$(SHLIBEXT) @@ -45,7 +46,7 @@ build-python:: tevent.$(SHLIBEXT) pytevent.o: $(teventdir)/pytevent.c $(CC) $(PICFLAG) -c $(teventdir)/pytevent.c $(CFLAGS) `$(PYTHON_CONFIG) --cflags` -tevent.$(SHLIBEXT): libtevent.$(SHLIBEXT) pytevent.o +tevent.$(SHLIBEXT): $(TEVENT_SOBASE) $(TEVENT_SONAME) pytevent.o $(SHLD) $(SHLD_FLAGS) -o $@ pytevent.o -L. -ltevent `$(PYTHON_CONFIG) --libs` install-python:: build-python diff --git a/lib/tevent/tevent.pc.in b/lib/tevent/tevent.pc.in index afd9fcc279..93d0cf5d8b 100644 --- a/lib/tevent/tevent.pc.in +++ b/lib/tevent/tevent.pc.in @@ -3,7 +3,7 @@ exec_prefix=@exec_prefix@ libdir=@libdir@ includedir=@includedir@ -Name: events +Name: tevent Description: An event system library Version: @PACKAGE_VERSION@ Libs: -L${libdir} -ltevent diff --git a/lib/tevent/tevent_aio.c b/lib/tevent/tevent_aio.c index 746e96060b..b15dab3aaf 100644 --- a/lib/tevent/tevent_aio.c +++ b/lib/tevent/tevent_aio.c @@ -30,12 +30,12 @@ this is _very_ experimental code */ -#include "system/filesys.h" #include "replace.h" +#include "system/filesys.h" +#include "system/select.h" #include "tevent.h" #include "tevent_internal.h" #include "tevent_util.h" -#include <sys/epoll.h> #include <libaio.h> #define MAX_AIO_QUEUE_DEPTH 100 @@ -66,11 +66,11 @@ struct aio_event_context { pid_t pid; }; -struct aio_event { +struct tevent_aio { struct tevent_context *event_ctx; struct iocb iocb; void *private_data; - event_aio_handler_t handler; + tevent_aio_handler_t handler; }; /* @@ -79,8 +79,8 @@ struct aio_event { static uint32_t epoll_map_flags(uint16_t flags) { uint32_t ret = 0; - if (flags & EVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP); - if (flags & EVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP); + if (flags & TEVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP); + if (flags & TEVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP); return ret; } @@ -113,7 +113,8 @@ static void epoll_check_reopen(struct aio_event_context *aio_ev) close(aio_ev->epoll_fd); aio_ev->epoll_fd = epoll_create(MAX_AIO_QUEUE_DEPTH); if (aio_ev->epoll_fd == -1) { - ev_debug(aio_ev->ev, EV_DEBUG_FATAL, "Failed to recreate epoll handle after fork\n"); + tevent_debug(aio_ev->ev, TEVENT_DEBUG_FATAL, + "Failed to recreate epoll handle after fork\n"); return; } aio_ev->pid = getpid(); @@ -146,7 +147,7 @@ static void epoll_add_event(struct aio_event_context *aio_ev, struct tevent_fd * fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT; /* only if we want to read we want to tell the event handler about errors */ - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR; } } @@ -191,7 +192,7 @@ static void epoll_mod_event(struct aio_event_context *aio_ev, struct tevent_fd * epoll_ctl(aio_ev->epoll_fd, EPOLL_CTL_MOD, fde->fd, &event); /* only if we want to read we want to tell the event handler about errors */ - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR; } } @@ -199,8 +200,8 @@ static void epoll_mod_event(struct aio_event_context *aio_ev, struct tevent_fd * static void epoll_change_event(struct aio_event_context *aio_ev, struct tevent_fd *fde) { bool got_error = (fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR); - bool want_read = (fde->flags & EVENT_FD_READ); - bool want_write= (fde->flags & EVENT_FD_WRITE); + bool want_read = (fde->flags & TEVENT_FD_READ); + bool want_write= (fde->flags & TEVENT_FD_WRITE); if (aio_ev->epoll_fd == -1) return; @@ -260,7 +261,7 @@ static int aio_event_loop(struct aio_event_context *aio_ev, struct timeval *tval if (aio_ev->epoll_fd == -1) return -1; if (aio_ev->ev->num_signal_handlers && - common_event_check_signal(aio_ev->ev)) { + tevent_common_check_signal(aio_ev->ev)) { return 0; } @@ -278,14 +279,14 @@ static int aio_event_loop(struct aio_event_context *aio_ev, struct timeval *tval if (ret == -EINTR) { if (aio_ev->ev->num_signal_handlers) { - common_event_check_signal(aio_ev->ev); + tevent_common_check_signal(aio_ev->ev); } return 0; } if (ret == 0 && tvalp) { /* we don't care about a possible delay here */ - common_event_loop_timer_delay(aio_ev->ev); + tevent_common_loop_timer_delay(aio_ev->ev); return 0; } @@ -296,8 +297,8 @@ static int aio_event_loop(struct aio_event_context *aio_ev, struct timeval *tval switch (finished->aio_lio_opcode) { case IO_CMD_PWRITE: case IO_CMD_PREAD: { - struct aio_event *ae = talloc_get_type(finished->data, - struct aio_event); + struct tevent_aio *ae = talloc_get_type(finished->data, + struct tevent_aio); if (ae) { talloc_set_destructor(ae, NULL); ae->handler(ae->event_ctx, ae, @@ -326,10 +327,10 @@ static int aio_event_loop(struct aio_event_context *aio_ev, struct timeval *tval epoll_del_event(aio_ev, fde); continue; } - flags |= EVENT_FD_READ; + flags |= TEVENT_FD_READ; } - if (ep->events & EPOLLIN) flags |= EVENT_FD_READ; - if (ep->events & EPOLLOUT) flags |= EVENT_FD_WRITE; + if (ep->events & EPOLLIN) flags |= TEVENT_FD_READ; + if (ep->events & EPOLLOUT) flags |= TEVENT_FD_WRITE; if (flags) { fde->handler(aio_ev->ev, fde, flags, fde->private_data); } @@ -398,8 +399,8 @@ static int aio_event_fd_destructor(struct tevent_fd *fde) epoll_del_event(aio_ev, fde); - if (fde->flags & EVENT_FD_AUTOCLOSE) { - close(fde->fd); + if (fde->close_fn) { + fde->close_fn(ev, fde, fde->fd, fde->private_data); fde->fd = -1; } @@ -411,9 +412,11 @@ static int aio_event_fd_destructor(struct tevent_fd *fde) return NULL on failure (memory allocation error) */ static struct tevent_fd *aio_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, - event_fd_handler_t handler, - void *private_data) + int fd, uint16_t flags, + tevent_fd_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { struct aio_event_context *aio_ev = talloc_get_type(ev->additional_data, struct aio_event_context); @@ -428,7 +431,10 @@ static struct tevent_fd *aio_event_add_fd(struct tevent_context *ev, TALLOC_CTX 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; fde->additional_flags = 0; fde->additional_data = NULL; @@ -441,15 +447,6 @@ static struct tevent_fd *aio_event_add_fd(struct tevent_context *ev, TALLOC_CTX return fde; } - -/* - return the fd event flags -*/ -static uint16_t aio_event_get_fd_flags(struct tevent_fd *fde) -{ - return fde->flags; -} - /* set the fd event flags */ @@ -479,7 +476,7 @@ static int aio_event_loop_once(struct tevent_context *ev) struct aio_event_context); struct timeval tval; - tval = common_event_loop_timer_delay(ev); + tval = tevent_common_loop_timer_delay(ev); if (ev_timeval_is_zero(&tval)) { return 0; } @@ -508,7 +505,7 @@ static int aio_event_loop_wait(struct tevent_context *ev) /* called when a disk IO event needs to be cancelled */ -static int aio_destructor(struct aio_event *ae) +static int aio_destructor(struct tevent_aio *ae) { struct tevent_context *ev = ae->event_ctx; struct aio_event_context *aio_ev = talloc_get_type(ev->additional_data, @@ -520,16 +517,18 @@ static int aio_destructor(struct aio_event *ae) } /* submit an aio disk IO event */ -static struct aio_event *aio_event_add_aio(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - struct iocb *iocb, - event_aio_handler_t handler, - void *private_data) +static struct tevent_aio *aio_event_add_aio(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + struct iocb *iocb, + tevent_aio_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { struct aio_event_context *aio_ev = talloc_get_type(ev->additional_data, struct aio_event_context); struct iocb *iocbp; - struct aio_event *ae = talloc(mem_ctx?mem_ctx:ev, struct aio_event); + struct tevent_aio *ae = talloc(mem_ctx?mem_ctx:ev, struct tevent_aio); if (ae == NULL) return NULL; ae->event_ctx = ev; @@ -548,20 +547,21 @@ static struct aio_event *aio_event_add_aio(struct tevent_context *ev, return ae; } -static const struct event_ops aio_event_ops = { +static const struct tevent_ops aio_event_ops = { .context_init = aio_event_context_init, .add_fd = aio_event_add_fd, .add_aio = aio_event_add_aio, - .get_fd_flags = aio_event_get_fd_flags, + .set_fd_close_fn= tevent_common_fd_set_close_fn, + .get_fd_flags = tevent_common_fd_get_flags, .set_fd_flags = aio_event_set_fd_flags, - .add_timer = common_event_add_timed, - .add_signal = common_event_add_signal, + .add_timer = tevent_common_add_timer, + .add_signal = tevent_common_add_signal, .loop_once = aio_event_loop_once, .loop_wait = aio_event_loop_wait, }; -bool events_aio_init(void) +bool tevent_aio_init(void) { - return event_register_backend("aio", &aio_event_ops); + return tevent_register_backend("aio", &aio_event_ops); } diff --git a/lib/tevent/tevent_debug.c b/lib/tevent/tevent_debug.c index 4fa58534b4..841446bf6c 100644 --- a/lib/tevent/tevent_debug.c +++ b/lib/tevent/tevent_debug.c @@ -30,10 +30,12 @@ /* this allows the user to choose their own debug function */ -int ev_set_debug(struct tevent_context *ev, - void (*debug)(void *context, enum ev_debug_level level, - const char *fmt, va_list ap), - void *context) +int tevent_set_debug(struct tevent_context *ev, + void (*debug)(void *context, + enum tevent_debug_level level, + const char *fmt, + va_list ap) PRINTF_ATTRIBUTE(3,0), + void *context) { ev->debug_ops.debug = debug; ev->debug_ops.context = context; @@ -43,23 +45,26 @@ int ev_set_debug(struct tevent_context *ev, /* debug function for ev_set_debug_stderr */ -void ev_debug_stderr(void *context, enum ev_debug_level level, - const char *fmt, va_list ap) PRINTF_ATTRIBUTE(3,0); -void ev_debug_stderr(void *context, enum ev_debug_level level, - const char *fmt, va_list ap) +static void tevent_debug_stderr(void *private_data, + enum tevent_debug_level level, + const char *fmt, + va_list ap) PRINTF_ATTRIBUTE(3,0); +static void tevent_debug_stderr(void *private_data, + enum tevent_debug_level level, + const char *fmt, va_list ap) { - if (level <= EV_DEBUG_WARNING) { + if (level <= TEVENT_DEBUG_WARNING) { vfprintf(stderr, fmt, ap); } } /* convenience function to setup debug messages on stderr - messages of level EV_DEBUG_WARNING and higher are printed + messages of level TEVENT_DEBUG_WARNING and higher are printed */ -int ev_set_debug_stderr(struct tevent_context *ev) +int tevent_set_debug_stderr(struct tevent_context *ev) { - return ev_set_debug(ev, ev_debug_stderr, ev); + return tevent_set_debug(ev, tevent_debug_stderr, ev); } /* @@ -70,7 +75,8 @@ int ev_set_debug_stderr(struct tevent_context *ev) * Applications using the library must decide where to * redirect debugging messages */ -void ev_debug(struct tevent_context *ev, enum ev_debug_level level, const char *fmt, ...) +void tevent_debug(struct tevent_context *ev, enum tevent_debug_level level, + const char *fmt, ...) { va_list ap; if (ev->debug_ops.debug == NULL) { diff --git a/lib/tevent/tevent_epoll.c b/lib/tevent/tevent_epoll.c index 1ce666462c..3835774349 100644 --- a/lib/tevent/tevent_epoll.c +++ b/lib/tevent/tevent_epoll.c @@ -22,11 +22,10 @@ #include "replace.h" #include "system/filesys.h" -#include "system/network.h" +#include "system/select.h" #include "tevent.h" #include "tevent_internal.h" #include "tevent_util.h" -#include <sys/epoll.h> struct epoll_event_context { /* a pointer back to the generic event_context */ @@ -58,19 +57,19 @@ struct epoll_event_context { */ static void epoll_panic(struct epoll_event_context *epoll_ev, const char *reason) { - ev_debug(epoll_ev->ev, EV_DEBUG_FATAL, + tevent_debug(epoll_ev->ev, TEVENT_DEBUG_FATAL, "%s (%s) - calling abort()\n", reason, strerror(errno)); abort(); } /* - map from EVENT_FD_* to EPOLLIN/EPOLLOUT + map from TEVENT_FD_* to EPOLLIN/EPOLLOUT */ static uint32_t epoll_map_flags(uint16_t flags) { uint32_t ret = 0; - if (flags & EVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP); - if (flags & EVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP); + if (flags & TEVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP); + if (flags & TEVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP); return ret; } @@ -116,8 +115,8 @@ static void epoll_check_reopen(struct epoll_event_context *epoll_ev) close(epoll_ev->epoll_fd); epoll_ev->epoll_fd = epoll_create(64); if (epoll_ev->epoll_fd == -1) { - ev_debug(epoll_ev->ev, EV_DEBUG_FATAL, - "Failed to recreate epoll handle after fork\n"); + tevent_debug(epoll_ev->ev, TEVENT_DEBUG_FATAL, + "Failed to recreate epoll handle after fork\n"); return; } epoll_ev->pid = getpid(); @@ -153,7 +152,7 @@ static void epoll_add_event(struct epoll_event_context *epoll_ev, struct tevent_ fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT; /* only if we want to read we want to tell the event handler about errors */ - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR; } } @@ -176,9 +175,9 @@ static void epoll_del_event(struct epoll_event_context *epoll_ev, struct tevent_ event.events = epoll_map_flags(fde->flags); event.data.ptr = fde; if (epoll_ctl(epoll_ev->epoll_fd, EPOLL_CTL_DEL, fde->fd, &event) != 0) { - ev_debug(epoll_ev->ev, EV_DEBUG_FATAL, - "epoll_del_event failed! probable early close bug (%s)\n", - strerror(errno)); + tevent_debug(epoll_ev->ev, TEVENT_DEBUG_FATAL, + "epoll_del_event failed! probable early close bug (%s)\n", + strerror(errno)); } fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT; } @@ -201,7 +200,7 @@ static void epoll_mod_event(struct epoll_event_context *epoll_ev, struct tevent_ } /* only if we want to read we want to tell the event handler about errors */ - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR; } } @@ -209,8 +208,8 @@ static void epoll_mod_event(struct epoll_event_context *epoll_ev, struct tevent_ static void epoll_change_event(struct epoll_event_context *epoll_ev, struct tevent_fd *fde) { bool got_error = (fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR); - bool want_read = (fde->flags & EVENT_FD_READ); - bool want_write= (fde->flags & EVENT_FD_WRITE); + bool want_read = (fde->flags & TEVENT_FD_READ); + bool want_write= (fde->flags & TEVENT_FD_WRITE); if (epoll_ev->epoll_fd == -1) return; @@ -258,14 +257,14 @@ static int epoll_event_loop(struct epoll_event_context *epoll_ev, struct timeval } if (epoll_ev->ev->num_signal_handlers && - common_event_check_signal(epoll_ev->ev)) { + tevent_common_check_signal(epoll_ev->ev)) { return 0; } ret = epoll_wait(epoll_ev->epoll_fd, events, MAXEVENTS, timeout); if (ret == -1 && errno == EINTR && epoll_ev->ev->num_signal_handlers) { - if (common_event_check_signal(epoll_ev->ev)) { + if (tevent_common_check_signal(epoll_ev->ev)) { return 0; } } @@ -277,7 +276,7 @@ static int epoll_event_loop(struct epoll_event_context *epoll_ev, struct timeval if (ret == 0 && tvalp) { /* we don't care about a possible delay here */ - common_event_loop_timer_delay(epoll_ev->ev); + tevent_common_loop_timer_delay(epoll_ev->ev); return 0; } @@ -293,7 +292,7 @@ static int epoll_event_loop(struct epoll_event_context *epoll_ev, struct timeval if (events[i].events & (EPOLLHUP|EPOLLERR)) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR; /* - * if we only wait for EVENT_FD_WRITE, we should not tell the + * if we only wait for TEVENT_FD_WRITE, we should not tell the * event handler about it, and remove the epoll_event, * as we only report errors when waiting for read events, * to match the select() behavior @@ -302,10 +301,10 @@ static int epoll_event_loop(struct epoll_event_context *epoll_ev, struct timeval epoll_del_event(epoll_ev, fde); continue; } - flags |= EVENT_FD_READ; + flags |= TEVENT_FD_READ; } - if (events[i].events & EPOLLIN) flags |= EVENT_FD_READ; - if (events[i].events & EPOLLOUT) flags |= EVENT_FD_WRITE; + if (events[i].events & EPOLLIN) flags |= TEVENT_FD_READ; + if (events[i].events & EPOLLOUT) flags |= TEVENT_FD_WRITE; if (flags) { fde->handler(epoll_ev->ev, fde, flags, fde->private_data); if (destruction_count != epoll_ev->destruction_count) { @@ -358,8 +357,8 @@ static int epoll_event_fd_destructor(struct tevent_fd *fde) epoll_del_event(epoll_ev, fde); - if (fde->flags & EVENT_FD_AUTOCLOSE) { - close(fde->fd); + if (fde->close_fn) { + fde->close_fn(ev, fde, fde->fd, fde->private_data); fde->fd = -1; } @@ -371,9 +370,11 @@ static int epoll_event_fd_destructor(struct tevent_fd *fde) return NULL on failure (memory allocation error) */ static struct tevent_fd *epoll_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, - event_fd_handler_t handler, - void *private_data) + int fd, uint16_t flags, + tevent_fd_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { struct epoll_event_context *epoll_ev = talloc_get_type(ev->additional_data, struct epoll_event_context); @@ -388,7 +389,10 @@ static struct tevent_fd *epoll_event_add_fd(struct tevent_context *ev, TALLOC_CT 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; fde->additional_flags = 0; fde->additional_data = NULL; @@ -401,15 +405,6 @@ static struct tevent_fd *epoll_event_add_fd(struct tevent_context *ev, TALLOC_CT return fde; } - -/* - return the fd event flags -*/ -static uint16_t epoll_event_get_fd_flags(struct tevent_fd *fde) -{ - return fde->flags; -} - /* set the fd event flags */ @@ -439,7 +434,7 @@ static int epoll_event_loop_once(struct tevent_context *ev) struct epoll_event_context); struct timeval tval; - tval = common_event_loop_timer_delay(ev); + tval = tevent_common_loop_timer_delay(ev); if (ev_timeval_is_zero(&tval)) { return 0; } @@ -465,18 +460,19 @@ static int epoll_event_loop_wait(struct tevent_context *ev) return 0; } -static const struct event_ops epoll_event_ops = { +static const struct tevent_ops epoll_event_ops = { .context_init = epoll_event_context_init, .add_fd = epoll_event_add_fd, - .get_fd_flags = epoll_event_get_fd_flags, + .set_fd_close_fn= tevent_common_fd_set_close_fn, + .get_fd_flags = tevent_common_fd_get_flags, .set_fd_flags = epoll_event_set_fd_flags, - .add_timer = common_event_add_timed, - .add_signal = common_event_add_signal, + .add_timer = tevent_common_add_timer, + .add_signal = tevent_common_add_signal, .loop_once = epoll_event_loop_once, .loop_wait = epoll_event_loop_wait, }; -bool events_epoll_init(void) +bool tevent_epoll_init(void) { - return event_register_backend("epoll", &epoll_event_ops); + return tevent_register_backend("epoll", &epoll_event_ops); } diff --git a/lib/tevent/tevent_fd.c b/lib/tevent/tevent_fd.c new file mode 100644 index 0000000000..d450e2168d --- /dev/null +++ b/lib/tevent/tevent_fd.c @@ -0,0 +1,42 @@ +/* + Unix SMB/CIFS implementation. + + common events code for fd events + + Copyright (C) Stefan Metzmacher 2009 + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see <http://www.gnu.org/licenses/>. +*/ + +#include "replace.h" +#include "tevent.h" +#include "tevent_internal.h" +#include "tevent_util.h" + +uint16_t tevent_common_fd_get_flags(struct tevent_fd *fde) +{ + return fde->flags; +} + +void tevent_common_fd_set_flags(struct tevent_fd *fde, uint16_t flags) +{ + if (fde->flags == flags) return; + fde->flags = flags; +} + +void tevent_common_fd_set_close_fn(struct tevent_fd *fde, + tevent_fd_close_fn_t close_fn) +{ + fde->close_fn = close_fn; +} diff --git a/lib/tevent/tevent_internal.h b/lib/tevent/tevent_internal.h index 2d6909da36..f29e9c62f5 100644 --- a/lib/tevent/tevent_internal.h +++ b/lib/tevent/tevent_internal.h @@ -30,7 +30,11 @@ struct tevent_ops { TALLOC_CTX *mem_ctx, int fd, uint16_t flags, tevent_fd_handler_t handler, - void *private_data); + void *private_data, + const char *handler_name, + const char *location); + void (*set_fd_close_fn)(struct tevent_fd *fde, + tevent_fd_close_fn_t close_fn); uint16_t (*get_fd_flags)(struct tevent_fd *fde); void (*set_fd_flags)(struct tevent_fd *fde, uint16_t flags); @@ -39,19 +43,25 @@ struct tevent_ops { TALLOC_CTX *mem_ctx, struct timeval next_event, tevent_timer_handler_t handler, - void *private_data); + void *private_data, + const char *handler_name, + const char *location); /* disk aio event functions */ struct tevent_aio *(*add_aio)(struct tevent_context *ev, TALLOC_CTX *mem_ctx, struct iocb *iocb, tevent_aio_handler_t handler, - void *private_data); + void *private_data, + const char *handler_name, + const char *location); /* signal functions */ struct tevent_signal *(*add_signal)(struct tevent_context *ev, TALLOC_CTX *mem_ctx, int signum, int sa_flags, tevent_signal_handler_t handler, - void *private_data); + void *private_data, + const char *handler_name, + const char *location); /* loop functions */ int (*loop_once)(struct tevent_context *ev); @@ -62,10 +72,14 @@ struct tevent_fd { struct tevent_fd *prev, *next; struct tevent_context *event_ctx; int fd; - uint16_t flags; /* see EVENT_FD_* flags */ + uint16_t flags; /* see TEVENT_FD_* flags */ tevent_fd_handler_t handler; + tevent_fd_close_fn_t close_fn; /* this is private for the specific handler */ void *private_data; + /* this is for debugging only! */ + const char *handler_name; + const char *location; /* this is private for the events_ops implementation */ uint16_t additional_flags; void *additional_data; @@ -78,6 +92,9 @@ struct tevent_timer { tevent_timer_handler_t handler; /* this is private for the specific handler */ void *private_data; + /* this is for debugging only! */ + const char *handler_name; + const char *location; /* this is private for the events_ops implementation */ void *additional_data; }; @@ -85,28 +102,26 @@ struct tevent_timer { struct tevent_signal { struct tevent_signal *prev, *next; struct tevent_context *event_ctx; - tevent_signal_handler_t handler; - void *private_data; int signum; int sa_flags; + tevent_signal_handler_t handler; + /* this is private for the specific handler */ + void *private_data; + /* this is for debugging only! */ + const char *handler_name; + const char *location; + /* this is private for the events_ops implementation */ + void *additional_data; }; -/* DEBUG */ -enum ev_debug_level {EV_DEBUG_FATAL, EV_DEBUG_ERROR, - EV_DEBUG_WARNING, EV_DEBUG_TRACE}; - -struct ev_debug_ops { - void (*debug)(void *context, enum ev_debug_level level, +struct tevent_debug_ops { + void (*debug)(void *context, enum tevent_debug_level level, const char *fmt, va_list ap) PRINTF_ATTRIBUTE(3,0); void *context; }; -int ev_set_debug(struct tevent_context *ev, - void (*debug)(void *context, enum ev_debug_level level, - const char *fmt, va_list ap) PRINTF_ATTRIBUTE(3,0), - void *context); -int ev_set_debug_stderr(struct tevent_context *ev); -void ev_debug(struct tevent_context *ev, enum ev_debug_level level, const char *fmt, ...); +void tevent_debug(struct tevent_context *ev, enum tevent_debug_level level, + const char *fmt, ...) PRINTF_ATTRIBUTE(3,4); /* aio event is private to the aio backend */ struct tevent_aio; @@ -128,34 +143,42 @@ struct tevent_context { struct tevent_fd *pipe_fde; /* debugging operations */ - struct ev_debug_ops debug_ops; + struct tevent_debug_ops debug_ops; }; -bool event_register_backend(const char *name, const struct tevent_ops *ops); +bool tevent_register_backend(const char *name, const struct tevent_ops *ops); + +void tevent_common_fd_set_close_fn(struct tevent_fd *fde, + tevent_fd_close_fn_t close_fn); +uint16_t tevent_common_fd_get_flags(struct tevent_fd *fde); +void tevent_common_fd_set_flags(struct tevent_fd *fde, uint16_t flags); bool ev_timeval_is_zero(const struct timeval *tv); -struct tevent_timer *common_event_add_timed(struct tevent_context *, - TALLOC_CTX *, - struct timeval, - tevent_timer_handler_t, - void *); -struct timeval common_event_loop_timer_delay(struct tevent_context *); - -struct tevent_signal *common_event_add_signal(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - int signum, - int sa_flags, - tevent_signal_handler_t handler, - void *private_data); -int common_event_check_signal(struct tevent_context *ev); - - -bool events_standard_init(void); -bool events_select_init(void); -#if HAVE_EVENTS_EPOLL -bool events_epoll_init(void); +struct tevent_timer *tevent_common_add_timer(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + struct timeval next_event, + tevent_timer_handler_t handler, + void *private_data, + const char *handler_name, + const char *location); +struct timeval tevent_common_loop_timer_delay(struct tevent_context *); + +struct tevent_signal *tevent_common_add_signal(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + int signum, + int sa_flags, + tevent_signal_handler_t handler, + void *private_data, + const char *handler_name, + const char *location); +int tevent_common_check_signal(struct tevent_context *ev); + +bool tevent_standard_init(void); +bool tevent_select_init(void); +#ifdef HAVE_EPOLL +bool tevent_epoll_init(void); #endif -#if HAVE_LINUX_AIO -bool events_aio_init(void); +#ifdef HAVE_LINUX_AIO +bool tevent_aio_init(void); #endif diff --git a/lib/tevent/tevent_select.c b/lib/tevent/tevent_select.c index 3e72ce4943..cf4453f64f 100644 --- a/lib/tevent/tevent_select.c +++ b/lib/tevent/tevent_select.c @@ -103,8 +103,8 @@ static int select_event_fd_destructor(struct tevent_fd *fde) DLIST_REMOVE(select_ev->fd_events, fde); select_ev->destruction_count++; - if (fde->flags & EVENT_FD_AUTOCLOSE) { - close(fde->fd); + if (fde->close_fn) { + fde->close_fn(ev, fde, fde->fd, fde->private_data); fde->fd = -1; } @@ -116,9 +116,11 @@ static int select_event_fd_destructor(struct tevent_fd *fde) return NULL on failure (memory allocation error) */ static struct tevent_fd *select_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, - event_fd_handler_t handler, - void *private_data) + int fd, uint16_t flags, + tevent_fd_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { struct select_event_context *select_ev = talloc_get_type(ev->additional_data, struct select_event_context); @@ -131,7 +133,10 @@ static struct tevent_fd *select_event_add_fd(struct tevent_context *ev, TALLOC_C 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; fde->additional_flags = 0; fde->additional_data = NULL; @@ -144,31 +149,6 @@ static struct tevent_fd *select_event_add_fd(struct tevent_context *ev, TALLOC_C return fde; } - -/* - return the fd event flags -*/ -static uint16_t select_event_get_fd_flags(struct tevent_fd *fde) -{ - return fde->flags; -} - -/* - set the fd event flags -*/ -static void select_event_set_fd_flags(struct tevent_fd *fde, uint16_t flags) -{ - struct tevent_context *ev; - struct select_event_context *select_ev; - - if (fde->flags == flags) return; - - ev = fde->event_ctx; - select_ev = talloc_get_type(ev->additional_data, struct select_event_context); - - fde->flags = flags; -} - /* event loop handling using select() */ @@ -189,16 +169,16 @@ static int select_event_loop_select(struct select_event_context *select_ev, stru /* setup any fd events */ for (fde = select_ev->fd_events; fde; fde = fde->next) { - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { FD_SET(fde->fd, &r_fds); } - if (fde->flags & EVENT_FD_WRITE) { + if (fde->flags & TEVENT_FD_WRITE) { FD_SET(fde->fd, &w_fds); } } if (select_ev->ev->num_signal_handlers && - common_event_check_signal(select_ev->ev)) { + tevent_common_check_signal(select_ev->ev)) { return 0; } @@ -206,7 +186,7 @@ static int select_event_loop_select(struct select_event_context *select_ev, stru if (selrtn == -1 && errno == EINTR && select_ev->ev->num_signal_handlers) { - common_event_check_signal(select_ev->ev); + tevent_common_check_signal(select_ev->ev); return 0; } @@ -216,15 +196,15 @@ static int select_event_loop_select(struct select_event_context *select_ev, stru made readable and that should have removed the event, so this must be a bug. This is a fatal error. */ - ev_debug(select_ev->ev, EV_DEBUG_FATAL, - "ERROR: EBADF on select_event_loop_once\n"); + tevent_debug(select_ev->ev, TEVENT_DEBUG_FATAL, + "ERROR: EBADF on select_event_loop_once\n"); select_ev->exit_code = EBADF; return -1; } if (selrtn == 0 && tvalp) { /* we don't care about a possible delay here */ - common_event_loop_timer_delay(select_ev->ev); + tevent_common_loop_timer_delay(select_ev->ev); return 0; } @@ -235,8 +215,8 @@ static int select_event_loop_select(struct select_event_context *select_ev, stru for (fde = select_ev->fd_events; fde; fde = fde->next) { uint16_t flags = 0; - if (FD_ISSET(fde->fd, &r_fds)) flags |= EVENT_FD_READ; - if (FD_ISSET(fde->fd, &w_fds)) flags |= EVENT_FD_WRITE; + if (FD_ISSET(fde->fd, &r_fds)) flags |= TEVENT_FD_READ; + if (FD_ISSET(fde->fd, &w_fds)) flags |= TEVENT_FD_WRITE; if (flags) { fde->handler(select_ev->ev, fde, flags, fde->private_data); if (destruction_count != select_ev->destruction_count) { @@ -258,7 +238,7 @@ static int select_event_loop_once(struct tevent_context *ev) struct select_event_context); struct timeval tval; - tval = common_event_loop_timer_delay(ev); + tval = tevent_common_loop_timer_delay(ev); if (ev_timeval_is_zero(&tval)) { return 0; } @@ -284,19 +264,19 @@ static int select_event_loop_wait(struct tevent_context *ev) return select_ev->exit_code; } -static const struct event_ops select_event_ops = { +static const struct tevent_ops select_event_ops = { .context_init = select_event_context_init, .add_fd = select_event_add_fd, - .get_fd_flags = select_event_get_fd_flags, - .set_fd_flags = select_event_set_fd_flags, - .add_timer = common_event_add_timed, - .add_signal = common_event_add_signal, + .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 = tevent_common_add_timer, + .add_signal = tevent_common_add_signal, .loop_once = select_event_loop_once, .loop_wait = select_event_loop_wait, }; -bool events_select_init(void) +bool tevent_select_init(void) { - return event_register_backend("select", &select_event_ops); + return tevent_register_backend("select", &select_event_ops); } - diff --git a/lib/tevent/tevent_signal.c b/lib/tevent/tevent_signal.c index bb50480dd7..031845927b 100644 --- a/lib/tevent/tevent_signal.c +++ b/lib/tevent/tevent_signal.c @@ -19,10 +19,9 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ -#include <signal.h> #include "replace.h" #include "system/filesys.h" -#include "system/select.h" +#include "system/wait.h" #include "tevent.h" #include "tevent_internal.h" #include "tevent_util.h" @@ -46,7 +45,7 @@ struct sigcounter { the poor design of signals means that this table must be static global */ static struct sig_state { - struct signal_event *sig_handlers[NUM_SIGNALS+1]; + struct tevent_signal *sig_handlers[NUM_SIGNALS+1]; struct sigaction *oldact[NUM_SIGNALS+1]; struct sigcounter signal_count[NUM_SIGNALS+1]; struct sigcounter got_signal; @@ -108,7 +107,7 @@ static void signal_handler_info(int signum, siginfo_t *info, void *uctx) /* destroy a signal event */ -static int signal_event_destructor(struct signal_event *se) +static int tevent_signal_destructor(struct tevent_signal *se) { se->event_ctx->num_signal_handlers--; DLIST_REMOVE(sig_state->sig_handlers[se->signum], se); @@ -141,14 +140,16 @@ static void signal_pipe_handler(struct tevent_context *ev, struct tevent_fd *fde add a signal event return NULL on failure (memory allocation error) */ -struct signal_event *common_event_add_signal(struct tevent_context *ev, - TALLOC_CTX *mem_ctx, - int signum, - int sa_flags, - event_signal_handler_t handler, - void *private_data) +struct tevent_signal *tevent_common_add_signal(struct tevent_context *ev, + TALLOC_CTX *mem_ctx, + int signum, + int sa_flags, + tevent_signal_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { - struct signal_event *se; + struct tevent_signal *se; if (signum >= NUM_SIGNALS) { return NULL; @@ -163,15 +164,18 @@ struct signal_event *common_event_add_signal(struct tevent_context *ev, } } - se = talloc(mem_ctx?mem_ctx:ev, struct signal_event); + se = talloc(mem_ctx?mem_ctx:ev, struct tevent_signal); if (se == NULL) return NULL; se->event_ctx = ev; - se->handler = handler; - se->private_data = private_data; se->signum = signum; se->sa_flags = sa_flags; - + se->handler = handler; + se->private_data = private_data; + se->handler_name = handler_name; + se->location = location; + se->additional_data = NULL; + /* Ensure, no matter the destruction order, that we always have a handle on the global sig_state */ if (!talloc_reference(se, sig_state)) { return NULL; @@ -209,7 +213,7 @@ struct signal_event *common_event_add_signal(struct tevent_context *ev, DLIST_ADD(sig_state->sig_handlers[signum], se); - talloc_set_destructor(se, signal_event_destructor); + talloc_set_destructor(se, tevent_signal_destructor); /* we need to setup the pipe hack handler if not already setup */ @@ -220,8 +224,8 @@ struct signal_event *common_event_add_signal(struct tevent_context *ev, ev_set_blocking(sig_state->pipe_hack[0], false); ev_set_blocking(sig_state->pipe_hack[1], false); } - ev->pipe_fde = event_add_fd(ev, ev, sig_state->pipe_hack[0], - EVENT_FD_READ, signal_pipe_handler, NULL); + ev->pipe_fde = tevent_add_fd(ev, ev, sig_state->pipe_hack[0], + TEVENT_FD_READ, signal_pipe_handler, NULL); } ev->num_signal_handlers++; @@ -233,7 +237,7 @@ struct signal_event *common_event_add_signal(struct tevent_context *ev, check if a signal is pending return != 0 if a signal was pending */ -int common_event_check_signal(struct tevent_context *ev) +int tevent_common_check_signal(struct tevent_context *ev) { int i; @@ -242,7 +246,7 @@ int common_event_check_signal(struct tevent_context *ev) } for (i=0;i<NUM_SIGNALS+1;i++) { - struct signal_event *se, *next; + struct tevent_signal *se, *next; struct sigcounter counter = sig_state->signal_count[i]; uint32_t count = sig_count(counter); diff --git a/lib/tevent/tevent_standard.c b/lib/tevent/tevent_standard.c index 1c99408b8d..2a292a4c39 100644 --- a/lib/tevent/tevent_standard.c +++ b/lib/tevent/tevent_standard.c @@ -29,8 +29,7 @@ #include "replace.h" #include "system/filesys.h" -#include "system/network.h" -#include "system/select.h" /* needed for HAVE_EVENTS_EPOLL */ +#include "system/select.h" #include "tevent.h" #include "tevent_util.h" #include "tevent_internal.h" @@ -64,29 +63,29 @@ struct std_event_context { }; /* use epoll if it is available */ -#if HAVE_EVENTS_EPOLL +#if HAVE_EPOLL /* called when a epoll call fails, and we should fallback to using select */ static void epoll_fallback_to_select(struct std_event_context *std_ev, const char *reason) { - ev_debug(std_ev->ev, EV_DEBUG_FATAL, - "%s (%s) - falling back to select()\n", - reason, strerror(errno)); + tevent_debug(std_ev->ev, TEVENT_DEBUG_FATAL, + "%s (%s) - falling back to select()\n", + reason, strerror(errno)); close(std_ev->epoll_fd); std_ev->epoll_fd = -1; talloc_set_destructor(std_ev, NULL); } /* - map from EVENT_FD_* to EPOLLIN/EPOLLOUT + map from TEVENT_FD_* to EPOLLIN/EPOLLOUT */ static uint32_t epoll_map_flags(uint16_t flags) { uint32_t ret = 0; - if (flags & EVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP); - if (flags & EVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP); + if (flags & TEVENT_FD_READ) ret |= (EPOLLIN | EPOLLERR | EPOLLHUP); + if (flags & TEVENT_FD_WRITE) ret |= (EPOLLOUT | EPOLLERR | EPOLLHUP); return ret; } @@ -130,8 +129,8 @@ static void epoll_check_reopen(struct std_event_context *std_ev) close(std_ev->epoll_fd); std_ev->epoll_fd = epoll_create(64); if (std_ev->epoll_fd == -1) { - ev_debug(std_ev->ev, EV_DEBUG_FATAL, - "Failed to recreate epoll handle after fork\n"); + tevent_debug(std_ev->ev, TEVENT_DEBUG_FATAL, + "Failed to recreate epoll handle after fork\n"); return; } std_ev->pid = getpid(); @@ -166,7 +165,7 @@ static void epoll_add_event(struct std_event_context *std_ev, struct tevent_fd * fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT; /* only if we want to read we want to tell the event handler about errors */ - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR; } } @@ -209,7 +208,7 @@ static void epoll_mod_event(struct std_event_context *std_ev, struct tevent_fd * } /* only if we want to read we want to tell the event handler about errors */ - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_REPORT_ERROR; } } @@ -217,8 +216,8 @@ static void epoll_mod_event(struct std_event_context *std_ev, struct tevent_fd * static void epoll_change_event(struct std_event_context *std_ev, struct tevent_fd *fde) { bool got_error = (fde->additional_flags & EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR); - bool want_read = (fde->flags & EVENT_FD_READ); - bool want_write= (fde->flags & EVENT_FD_WRITE); + bool want_read = (fde->flags & TEVENT_FD_READ); + bool want_write= (fde->flags & TEVENT_FD_WRITE); if (std_ev->epoll_fd == -1) return; @@ -266,14 +265,14 @@ static int epoll_event_loop(struct std_event_context *std_ev, struct timeval *tv } if (std_ev->ev->num_signal_handlers && - common_event_check_signal(std_ev->ev)) { + tevent_common_check_signal(std_ev->ev)) { return 0; } ret = epoll_wait(std_ev->epoll_fd, events, MAXEVENTS, timeout); if (ret == -1 && errno == EINTR && std_ev->ev->num_signal_handlers) { - if (common_event_check_signal(std_ev->ev)) { + if (tevent_common_check_signal(std_ev->ev)) { return 0; } } @@ -285,7 +284,7 @@ static int epoll_event_loop(struct std_event_context *std_ev, struct timeval *tv if (ret == 0 && tvalp) { /* we don't care about a possible delay here */ - common_event_loop_timer_delay(std_ev->ev); + tevent_common_loop_timer_delay(std_ev->ev); return 0; } @@ -301,7 +300,7 @@ static int epoll_event_loop(struct std_event_context *std_ev, struct timeval *tv if (events[i].events & (EPOLLHUP|EPOLLERR)) { fde->additional_flags |= EPOLL_ADDITIONAL_FD_FLAG_GOT_ERROR; /* - * if we only wait for EVENT_FD_WRITE, we should not tell the + * if we only wait for TEVENT_FD_WRITE, we should not tell the * event handler about it, and remove the epoll_event, * as we only report errors when waiting for read events, * to match the select() behavior @@ -310,10 +309,10 @@ static int epoll_event_loop(struct std_event_context *std_ev, struct timeval *tv epoll_del_event(std_ev, fde); continue; } - flags |= EVENT_FD_READ; + flags |= TEVENT_FD_READ; } - if (events[i].events & EPOLLIN) flags |= EVENT_FD_READ; - if (events[i].events & EPOLLOUT) flags |= EVENT_FD_WRITE; + if (events[i].events & EPOLLIN) flags |= TEVENT_FD_READ; + if (events[i].events & EPOLLOUT) flags |= TEVENT_FD_WRITE; if (flags) { fde->handler(std_ev->ev, fde, flags, fde->private_data); if (destruction_count != std_ev->destruction_count) { @@ -392,8 +391,8 @@ static int std_event_fd_destructor(struct tevent_fd *fde) epoll_del_event(std_ev, fde); - if (fde->flags & EVENT_FD_AUTOCLOSE) { - close(fde->fd); + if (fde->close_fn) { + fde->close_fn(ev, fde, fde->fd, fde->private_data); fde->fd = -1; } @@ -405,9 +404,11 @@ static int std_event_fd_destructor(struct tevent_fd *fde) return NULL on failure (memory allocation error) */ static struct tevent_fd *std_event_add_fd(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - int fd, uint16_t flags, - event_fd_handler_t handler, - void *private_data) + int fd, uint16_t flags, + tevent_fd_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { struct std_event_context *std_ev = talloc_get_type(ev->additional_data, struct std_event_context); @@ -422,7 +423,10 @@ static struct tevent_fd *std_event_add_fd(struct tevent_context *ev, TALLOC_CTX 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; fde->additional_flags = 0; fde->additional_data = NULL; @@ -438,15 +442,6 @@ static struct tevent_fd *std_event_add_fd(struct tevent_context *ev, TALLOC_CTX return fde; } - -/* - return the fd event flags -*/ -static uint16_t std_event_get_fd_flags(struct tevent_fd *fde) -{ - return fde->flags; -} - /* set the fd event flags */ @@ -487,16 +482,16 @@ static int std_event_loop_select(struct std_event_context *std_ev, struct timeva /* setup any fd events */ for (fde = std_ev->fd_events; fde; fde = fde->next) { - if (fde->flags & EVENT_FD_READ) { + if (fde->flags & TEVENT_FD_READ) { FD_SET(fde->fd, &r_fds); } - if (fde->flags & EVENT_FD_WRITE) { + if (fde->flags & TEVENT_FD_WRITE) { FD_SET(fde->fd, &w_fds); } } if (std_ev->ev->num_signal_handlers && - common_event_check_signal(std_ev->ev)) { + tevent_common_check_signal(std_ev->ev)) { return 0; } @@ -504,7 +499,7 @@ static int std_event_loop_select(struct std_event_context *std_ev, struct timeva if (selrtn == -1 && errno == EINTR && std_ev->ev->num_signal_handlers) { - common_event_check_signal(std_ev->ev); + tevent_common_check_signal(std_ev->ev); return 0; } @@ -514,15 +509,15 @@ static int std_event_loop_select(struct std_event_context *std_ev, struct timeva made readable and that should have removed the event, so this must be a bug. This is a fatal error. */ - ev_debug(std_ev->ev, EV_DEBUG_FATAL, - "ERROR: EBADF on std_event_loop_once\n"); + tevent_debug(std_ev->ev, TEVENT_DEBUG_FATAL, + "ERROR: EBADF on std_event_loop_once\n"); std_ev->exit_code = EBADF; return -1; } if (selrtn == 0 && tvalp) { /* we don't care about a possible delay here */ - common_event_loop_timer_delay(std_ev->ev); + tevent_common_loop_timer_delay(std_ev->ev); return 0; } @@ -533,8 +528,8 @@ static int std_event_loop_select(struct std_event_context *std_ev, struct timeva for (fde = std_ev->fd_events; fde; fde = fde->next) { uint16_t flags = 0; - if (FD_ISSET(fde->fd, &r_fds)) flags |= EVENT_FD_READ; - if (FD_ISSET(fde->fd, &w_fds)) flags |= EVENT_FD_WRITE; + if (FD_ISSET(fde->fd, &r_fds)) flags |= TEVENT_FD_READ; + if (FD_ISSET(fde->fd, &w_fds)) flags |= TEVENT_FD_WRITE; if (flags) { fde->handler(std_ev->ev, fde, flags, fde->private_data); if (destruction_count != std_ev->destruction_count) { @@ -556,7 +551,7 @@ static int std_event_loop_once(struct tevent_context *ev) struct std_event_context); struct timeval tval; - tval = common_event_loop_timer_delay(ev); + tval = tevent_common_loop_timer_delay(ev); if (ev_timeval_is_zero(&tval)) { return 0; } @@ -588,20 +583,21 @@ static int std_event_loop_wait(struct tevent_context *ev) return std_ev->exit_code; } -static const struct event_ops std_event_ops = { +static const struct tevent_ops std_event_ops = { .context_init = std_event_context_init, .add_fd = std_event_add_fd, - .get_fd_flags = std_event_get_fd_flags, + .set_fd_close_fn= tevent_common_fd_set_close_fn, + .get_fd_flags = tevent_common_fd_get_flags, .set_fd_flags = std_event_set_fd_flags, - .add_timer = common_event_add_timed, - .add_signal = common_event_add_signal, + .add_timer = tevent_common_add_timer, + .add_signal = tevent_common_add_signal, .loop_once = std_event_loop_once, .loop_wait = std_event_loop_wait, }; -bool events_standard_init(void) +bool tevent_standard_init(void) { - return event_register_backend("standard", &std_event_ops); + return tevent_register_backend("standard", &std_event_ops); } diff --git a/lib/tevent/tevent_timed.c b/lib/tevent/tevent_timed.c index ce3fc8eb00..dadd360416 100644 --- a/lib/tevent/tevent_timed.c +++ b/lib/tevent/tevent_timed.c @@ -20,11 +20,8 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ -#include <sys/time.h> -#include <time.h> #include "replace.h" -#include "system/filesys.h" -#include "system/select.h" +#include "system/time.h" #include "tevent.h" #include "tevent_internal.h" #include "tevent_util.h" @@ -109,7 +106,7 @@ bool ev_timeval_is_zero(const struct timeval *tv) /* destroy a timed event */ -static int common_event_timed_destructor(struct tevent_timer *te) +static int tevent_common_timed_destructor(struct tevent_timer *te) { struct tevent_context *ev = talloc_get_type(te->event_ctx, struct tevent_context); @@ -117,7 +114,7 @@ static int common_event_timed_destructor(struct tevent_timer *te) return 0; } -static int common_event_timed_deny_destructor(struct tevent_timer *te) +static int tevent_common_timed_deny_destructor(struct tevent_timer *te) { return -1; } @@ -126,10 +123,12 @@ static int common_event_timed_deny_destructor(struct tevent_timer *te) add a timed event return NULL on failure (memory allocation error) */ -struct tevent_timer *common_event_add_timed(struct tevent_context *ev, TALLOC_CTX *mem_ctx, - struct timeval next_event, - event_timed_handler_t handler, - void *private_data) +struct tevent_timer *tevent_common_add_timer(struct tevent_context *ev, TALLOC_CTX *mem_ctx, + struct timeval next_event, + tevent_timer_handler_t handler, + void *private_data, + const char *handler_name, + const char *location) { struct tevent_timer *te, *last_te, *cur_te; @@ -140,6 +139,8 @@ struct tevent_timer *common_event_add_timed(struct tevent_context *ev, TALLOC_CT te->next_event = next_event; te->handler = handler; te->private_data = private_data; + te->handler_name = handler_name; + te->location = location; te->additional_data = NULL; /* keep the list ordered */ @@ -155,7 +156,7 @@ struct tevent_timer *common_event_add_timed(struct tevent_context *ev, TALLOC_CT DLIST_ADD_AFTER(ev->timer_events, te, last_te); - talloc_set_destructor(te, common_event_timed_destructor); + talloc_set_destructor(te, tevent_common_timed_destructor); return te; } @@ -166,7 +167,7 @@ struct tevent_timer *common_event_add_timed(struct tevent_context *ev, TALLOC_CT return the delay untill the next timed event, or zero if a timed event was triggered */ -struct timeval common_event_loop_timer_delay(struct tevent_context *ev) +struct timeval tevent_common_loop_timer_delay(struct tevent_context *ev) { struct timeval current_time = ev_timeval_zero(); struct tevent_timer *te = ev->timer_events; @@ -203,7 +204,7 @@ struct timeval common_event_loop_timer_delay(struct tevent_context *ev) */ /* deny the handler to free the event */ - talloc_set_destructor(te, common_event_timed_deny_destructor); + talloc_set_destructor(te, tevent_common_timed_deny_destructor); /* We need to remove the timer from the list before calling the * handler because in a semi-async inner event loop called from the |