diff options
23 files changed, 427 insertions, 283 deletions
diff --git a/source4/configure.ac b/source4/configure.ac index ca38f6add4..8ec6022d69 100644 --- a/source4/configure.ac +++ b/source4/configure.ac @@ -89,7 +89,7 @@ SMB_EXT_LIB_FROM_PKGCONFIG(LIBLDB, ldb >= 0.9.1, SMB_INCLUDE_MK(lib/ldb/python.mk) m4_include(lib/tls/config.m4) -m4_include(lib/events/config.m4) +m4_include(lib/events/libevents.m4) dnl m4_include(auth/kerberos/config.m4) m4_include(scripting/python/config.m4) diff --git a/source4/lib/events/config.m4 b/source4/lib/events/config.m4 deleted file mode 100644 index 180b58cbc6..0000000000 --- a/source4/lib/events/config.m4 +++ /dev/null @@ -1,18 +0,0 @@ -# check for EPOLL and native Linux AIO interface -SMB_ENABLE(EVENTS_EPOLL, NO) -SMB_ENABLE(EVENTS_AIO, 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 - SMB_ENABLE(EVENTS_EPOLL,YES) - AC_DEFINE(HAVE_EVENTS_EPOLL, 1, [Whether epoll is available]) - - # check for native Linux AIO interface - AC_CHECK_HEADERS(libaio.h) - AC_CHECK_LIB_EXT(aio, AIO_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 - SMB_ENABLE(EVENTS_AIO,YES) - AC_DEFINE(HAVE_LINUX_AIO, 1, [Whether Linux AIO is available]) - fi -fi -SMB_EXT_LIB(LIBAIO_LINUX, $AIO_LIBS) diff --git a/source4/lib/events/config.mk b/source4/lib/events/config.mk index 9d579807c8..8ba5af91a8 100644 --- a/source4/lib/events/config.mk +++ b/source4/lib/events/config.mk @@ -1,13 +1,3 @@ -################################################ -# Start SUBSYSTEM LIBEVENTS -[LIBRARY::LIBEVENTS] -PUBLIC_DEPENDENCIES = LIBTALLOC -OUTPUT_TYPE = STATIC_LIBRARY -CFLAGS = -Ilib/events -# -# End SUBSYSTEM LIBEVENTS -################################################ - ############################## [MODULE::EVENTS_AIO] PRIVATE_DEPENDENCIES = LIBAIO_LINUX @@ -41,19 +31,23 @@ INIT_FUNCTION = s4_events_standard_init EVENTS_STANDARD_OBJ_FILES = $(libeventssrcdir)/events_standard.o -############################## +################################################ # Start SUBSYSTEM LIBEVENTS -[SUBSYSTEM::LIBEVENTS] +[LIBRARY::LIBEVENTS] +PUBLIC_DEPENDENCIES = LIBTALLOC +OUTPUT_TYPE = STATIC_LIBRARY +CFLAGS = -Ilib/events +# # End SUBSYSTEM LIBEVENTS -############################## +################################################ -LIBEVENTS_OBJ_FILES = $(addprefix $(libeventssrcdir)/, events.o events_timed.o events_signal.o) +LIBEVENTS_OBJ_FILES = $(addprefix $(libeventssrcdir)/, events.o events_timed.o events_signal.o events_debug.o events_util.o events_s4.o) PUBLIC_HEADERS += $(addprefix $(libeventssrcdir)/, events.h events_internal.h) [PYTHON::swig_events] LIBRARY_REALNAME = samba/_events.$(SHLIBEXT) -PRIVATE_DEPENDENCIES = LIBEVENTS LIBSAMBA-HOSTCONFIG +PRIVATE_DEPENDENCIES = LIBEVENTS LIBSAMBA-HOSTCONFIG LIBSAMBA-UTIL swig_events_OBJ_FILES = $(libeventssrcdir)/events_wrap.o diff --git a/source4/lib/events/configure.ac b/source4/lib/events/configure.ac index 4eb3575aac..26efe82ba4 100644 --- a/source4/lib/events/configure.ac +++ b/source4/lib/events/configure.ac @@ -2,6 +2,7 @@ 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(events, 1.0.0) AC_CONFIG_SRCDIR([events.c]) AC_CONFIG_HEADER(config.h) diff --git a/source4/lib/events/events.c b/source4/lib/events/events.c index ccc62b4c83..1c94e3436d 100644 --- a/source4/lib/events/events.c +++ b/source4/lib/events/events.c @@ -52,14 +52,7 @@ forever. */ -#if _SAMBA_BUILD_ -#include "includes.h" -#include "lib/util/dlinklist.h" -#include "param/param.h" -#else #include "replace.h" -#include "events_util.h" -#endif #include "events.h" #include "events_internal.h" @@ -70,8 +63,7 @@ struct event_ops_list { }; /* list of registered event backends */ -static struct event_ops_list *event_backends; - +static struct event_ops_list *event_backends = NULL; static char *event_default_backend = NULL; /* @@ -80,11 +72,21 @@ static char *event_default_backend = NULL; bool event_register_backend(const char *name, const struct event_ops *ops) { struct event_ops_list *e; + + for (e = event_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); if (e == NULL) return false; + e->name = name; e->ops = ops; DLIST_ADD(event_backends, e); + return true; } @@ -102,25 +104,13 @@ void event_set_default_backend(const char *backend) */ static void event_backend_init(void) { -#if _SAMBA_BUILD_ - NTSTATUS s4_events_standard_init(void); - NTSTATUS s4_events_select_init(void); - NTSTATUS s4_events_epoll_init(void); - NTSTATUS s4_events_aio_init(void); - init_module_fn static_init[] = { STATIC_LIBEVENTS_MODULES }; - if (event_backends) return; - run_init_functions(static_init); -#else - bool events_standard_init(void); - bool events_select_init(void); events_select_init(); events_standard_init(); #if HAVE_EVENTS_EPOLL - { - bool events_epoll_init(void); - events_epoll_init(); - } + events_epoll_init(); #endif +#if HAVE_LINUX_AIO + events_aio_init(); #endif } @@ -135,7 +125,7 @@ const char **event_backend_list(TALLOC_CTX *mem_ctx) event_backend_init(); for (e=event_backends;e;e=e->next) { - list = str_list_add(list, e->name); + list = ev_str_list_add(list, e->name); } talloc_steal(mem_ctx, list); @@ -208,8 +198,6 @@ struct event_context *event_context_init_byname(TALLOC_CTX *mem_ctx, const char */ struct event_context *event_context_init(TALLOC_CTX *mem_ctx) { - DEBUG(0, ("New event context requested. Parent: [%s:%p]\n", - mem_ctx?talloc_get_name(mem_ctx):"NULL", mem_ctx)); return event_context_init_byname(mem_ctx, NULL); } diff --git a/source4/lib/events/events.h b/source4/lib/events/events.h index 2868fefc38..750cdfee05 100644 --- a/source4/lib/events/events.h +++ b/source4/lib/events/events.h @@ -42,6 +42,11 @@ typedef void (*event_signal_handler_t)(struct event_context *, struct signal_eve typedef void (*event_aio_handler_t)(struct event_context *, struct aio_event *, int, void *); +#ifdef _SAMBA_BUILD_ +struct event_context *s4_event_context_init_byname(TALLOC_CTX *mem_ctx, const char *name); +struct event_context *s4_event_context_init(TALLOC_CTX *mem_ctx); +#endif + struct event_context *event_context_init(TALLOC_CTX *mem_ctx); struct event_context *event_context_init_byname(TALLOC_CTX *mem_ctx, const char *name); const char **event_backend_list(TALLOC_CTX *mem_ctx); diff --git a/source4/lib/events/events.mk b/source4/lib/events/events.mk index 64d3fcb9fd..f4b02eae83 100644 --- a/source4/lib/events/events.mk +++ b/source4/lib/events/events.mk @@ -1,14 +1,47 @@ + +EVENTS_SONAME = libevents.$(SHLIBEXT).0 +EVENTS_SOLIB = libevents.$(SHLIBEXT).$(PACKAGE_VERSION) + +libevents.a: $(EVENTS_OBJ) + ar -rv libevents.a $(EVENTS_OBJ) + +libevents.$(SHLIBEXT): $(LIBEVENTS_SOLIB) + ln -fs $< $@ + +$(EVENTS_SONAME): $(EVENTS_SOLIB) + ln -fs $< $@ + dirs:: @mkdir -p lib -LIBEVENTS_SONAME = libevents.$(SHLIBEXT).0 -LIBEVENTS_SOLIB = libevents.$(SHLIBEXT).$(PACKAGE_VERSION) +installdirs:: + mkdir -p $(DESTDIR)$(includedir) + mkdir -p $(DESTDIR)$(libdir) + mkdir -p $(DESTDIR)$(libdir)/pkgconfig + +installheaders:: installdirs + cp $(srcdir)/events.h $(DESTDIR)$(includedir) + +installlibs:: installdirs + cp events.pc $(DESTDIR)$(libdir)/pkgconfig + cp libevents.a $(LIBEVENTS_SOLIB) $(DESTDIR)$(libdir) -LIBEVENTS = libevents.a +install:: all installdirs installheaders installlibs $(PYTHON_INSTALL_TARGET) clean:: - rm -f $(LIBEVENTS_SONAME) $(LIBEVENTS_SOLIB) libevents.a libevents.$(SHLIBEXT) + rm -f $(EVENTS_SONAME) $(EVENTS_SOLIB) libevents.a libevents.$(SHLIBEXT) rm -f events.pc + rm -f _libevents.$(SHLIBEXT) + + +#python stuff + +check-python:: build-python + $(LIB_PATH_VAR)=. PYTHONPATH=".:$(eventsdir)" $(PYTHON) $(eventsdir)/python/tests/simple.py + +install-swig:: + mkdir -p $(DESTDIR)`$(SWIG) -swiglib` + cp events.i $(DESTDIR)`$(SWIG) -swiglib` build-python:: _libevents.$(SHLIBEXT) @@ -18,42 +51,9 @@ events_wrap.o: $(eventsdir)/events_wrap.c _libevents.$(SHLIBEXT): libevents.$(SHLIBEXT) events_wrap.o $(SHLD) $(SHLD_FLAGS) -o $@ events_wrap.o -L. -levents `$(PYTHON_CONFIG) --libs` -install:: installdirs installbin installheaders installlibs \ - $(PYTHON_INSTALL_TARGET) - install-python:: build-python mkdir -p $(DESTDIR)`$(PYTHON) -c "import distutils.sysconfig; print distutils.sysconfig.get_python_lib(0, prefix='$(prefix)')"` \ $(DESTDIR)`$(PYTHON) -c "import distutils.sysconfig; print distutils.sysconfig.get_python_lib(1, prefix='$(prefix)')"` cp $(eventsdir)/events.py $(DESTDIR)`$(PYTHON) -c "import distutils.sysconfig; print distutils.sysconfig.get_python_lib(0, prefix='$(prefix)')"` cp _libevents.$(SHLIBEXT) $(DESTDIR)`$(PYTHON) -c "import distutils.sysconfig; print distutils.sysconfig.get_python_lib(1, prefix='$(prefix)')"` -check-python:: build-python - $(LIB_PATH_VAR)=. PYTHONPATH=".:$(eventsdir)" $(PYTHON) $(eventsdir)/python/tests/simple.py - -install-swig:: - mkdir -p $(DESTDIR)`$(SWIG) -swiglib` - cp events.i $(DESTDIR)`$(SWIG) -swiglib` - -clean:: - rm -f _libevents.$(SHLIBEXT) - -installdirs:: - mkdir -p $(DESTDIR)$(includedir) - mkdir -p $(DESTDIR)$(libdir) - mkdir -p $(DESTDIR)$(libdir)/pkgconfig - -installheaders:: installdirs - cp $(srcdir)/events.h $(DESTDIR)$(includedir) - -installlibs:: all installdirs - cp events.pc $(DESTDIR)$(libdir)/pkgconfig - cp libevents.a $(LIBEVENTS_SOLIB) $(DESTDIR)$(libdir) - -libevents.a: $(EVENTS_OBJ) - ar -rv libevents.a $(EVENTS_OBJ) - -libevents.$(SHLIBEXT): $(LIBEVENTS_SOLIB) - ln -fs $< $@ - -$(LIBEVENTS_SONAME): $(LIBEVENTS_SOLIB) - ln -fs $< $@ diff --git a/source4/lib/events/events.py b/source4/lib/events/events.py index 90695e3d92..f217c29d78 100644 --- a/source4/lib/events/events.py +++ b/source4/lib/events/events.py @@ -1,5 +1,5 @@ # This file was automatically generated by SWIG (http://www.swig.org). -# Version 1.3.35 +# Version 1.3.33 # # Don't modify this file, modify the SWIG interface instead. diff --git a/source4/lib/events/events_aio.c b/source4/lib/events/events_aio.c index a0417384e0..9d13ea96fd 100644 --- a/source4/lib/events/events_aio.c +++ b/source4/lib/events/events_aio.c @@ -30,12 +30,10 @@ this is _very_ experimental code */ -#include "includes.h" #include "system/filesys.h" #include "system/network.h" -#include "lib/util/dlinklist.h" -#include "lib/events/events.h" -#include "lib/events/events_internal.h" +#include "events.h" +#include "events_internal.h" #include <sys/epoll.h> #include <libaio.h> @@ -114,7 +112,7 @@ 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) { - DEBUG(0,("Failed to recreate epoll handle after fork\n")); + ev_debug(aio_ev->ev, EV_DEBUG_FATAL, "Failed to recreate epoll handle after fork\n"); return; } aio_ev->pid = getpid(); @@ -566,12 +564,3 @@ bool events_aio_init(void) return event_register_backend("aio", &aio_event_ops); } -#if _SAMBA_BUILD_ -NTSTATUS s4_events_aio_init(void) -{ - if (!events_aio_init()) { - return NT_STATUS_INTERNAL_ERROR; - } - return NT_STATUS_OK; -} -#endif diff --git a/source4/lib/events/events_debug.c b/source4/lib/events/events_debug.c new file mode 100644 index 0000000000..70b85d47e4 --- /dev/null +++ b/source4/lib/events/events_debug.c @@ -0,0 +1,78 @@ +/* + Unix SMB/CIFS implementation. + + Copyright (C) Andrew Tridgell 2005 + Copyright (C) Jelmer Vernooij 2005 + + 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 "events.h" +#include "events_internal.h" + +/******************************************************************** + * Debug wrapper functions, modeled (with lot's of code copied as is) + * after the ev debug wrapper functions + ********************************************************************/ + +/* + this allows the user to choose their own debug function +*/ +int ev_set_debug(struct event_context *ev, + void (*debug)(void *context, enum ev_debug_level level, + const char *fmt, va_list ap), + void *context) +{ + ev->debug_ops.debug = debug; + ev->debug_ops.context = context; + return 0; +} + +/* + debug function for ev_set_debug_stderr +*/ +static void ev_debug_stderr(void *context, enum ev_debug_level level, + const char *fmt, va_list ap) PRINTF_ATTRIBUTE(3,0); +static void ev_debug_stderr(void *context, enum ev_debug_level level, + const char *fmt, va_list ap) +{ + if (level <= EV_DEBUG_WARNING) { + vfprintf(stderr, fmt, ap); + } +} + +/* + convenience function to setup debug messages on stderr + messages of level EV_DEBUG_WARNING and higher are printed +*/ +int ev_set_debug_stderr(struct event_context *ev) +{ + return ev_set_debug(ev, ev_debug_stderr, ev); +} + +/* + log a message +*/ +void ev_debug(struct event_context *ev, enum ev_debug_level level, const char *fmt, ...) +{ + va_list ap; + if (ev->debug_ops.debug == NULL) { + ev_set_debug_stderr(ev); + } + va_start(ap, fmt); + ev->debug_ops.debug(ev->debug_ops.context, level, fmt, ap); + va_end(ap); +} + diff --git a/source4/lib/events/events_epoll.c b/source4/lib/events/events_epoll.c index 07e66154fc..c781bd99ae 100644 --- a/source4/lib/events/events_epoll.c +++ b/source4/lib/events/events_epoll.c @@ -20,13 +20,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ -#if _SAMBA_BUILD_ -#include "includes.h" -#include "lib/util/dlinklist.h" -#else #include "replace.h" -#include "events_util.h" -#endif #include "system/filesys.h" #include "system/network.h" #include "events.h" @@ -63,9 +57,8 @@ struct epoll_event_context { */ static void epoll_panic(struct epoll_event_context *epoll_ev, const char *reason) { -#if _SAMBA_BUILD_ - DEBUG(0,("%s (%s) - calling abort()\n", reason, strerror(errno))); -#endif + ev_debug(epoll_ev->ev, EV_DEBUG_FATAL, + "%s (%s) - calling abort()\n", reason, strerror(errno)); abort(); } @@ -122,7 +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) { - DEBUG(0,("Failed to recreate epoll handle after fork\n")); + ev_debug(epoll_ev->ev, EV_DEBUG_FATAL, + "Failed to recreate epoll handle after fork\n"); return; } epoll_ev->pid = getpid(); @@ -181,7 +175,9 @@ static void epoll_del_event(struct epoll_event_context *epoll_ev, struct fd_even 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) { - DEBUG(0,("epoll_del_event failed! probable early close bug (%s)\n", strerror(errno))); + ev_debug(epoll_ev->ev, EV_DEBUG_FATAL, + "epoll_del_event failed! probable early close bug (%s)\n", + strerror(errno)); } fde->additional_flags &= ~EPOLL_ADDITIONAL_FD_FLAG_HAS_EVENT; } @@ -443,7 +439,7 @@ static int epoll_event_loop_once(struct event_context *ev) struct timeval tval; tval = common_event_loop_timer_delay(ev); - if (timeval_is_zero(&tval)) { + if (ev_timeval_is_zero(&tval)) { return 0; } @@ -483,13 +479,3 @@ bool events_epoll_init(void) { return event_register_backend("epoll", &epoll_event_ops); } - -#if _SAMBA_BUILD_ -NTSTATUS s4_events_epoll_init(void) -{ - if (!events_epoll_init()) { - return NT_STATUS_INTERNAL_ERROR; - } - return NT_STATUS_OK; -} -#endif diff --git a/source4/lib/events/events_internal.h b/source4/lib/events/events_internal.h index d8c14ead95..78df98a1fe 100644 --- a/source4/lib/events/events_internal.h +++ b/source4/lib/events/events_internal.h @@ -91,10 +91,27 @@ struct signal_event { int sa_flags; }; +/* 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, + const char *fmt, va_list ap) PRINTF_ATTRIBUTE(3,0); + void *context; +}; + +int ev_set_debug(struct event_context *ev, + void (*debug)(void *context, enum ev_debug_level level, + const char *fmt, va_list ap), + void *context); +int ev_set_debug_stderr(struct event_context *ev); +void ev_debug(struct event_context *ev, enum ev_debug_level level, const char *fmt, ...); + /* aio event is private to the aio backend */ struct aio_event; -struct event_context { +struct event_context { /* the specific events implementation */ const struct event_ops *ops; @@ -109,11 +126,15 @@ struct event_context { /* pipe hack used with signal handlers */ struct fd_event *pipe_fde; + + /* debugging operations */ + struct ev_debug_ops debug_ops; }; bool event_register_backend(const char *name, const struct event_ops *ops); +bool ev_timeval_is_zero(const struct timeval *tv); struct timed_event *common_event_add_timed(struct event_context *, TALLOC_CTX *, struct timeval, event_timed_handler_t, void *); struct timeval common_event_loop_timer_delay(struct event_context *); @@ -126,3 +147,14 @@ struct signal_event *common_event_add_signal(struct event_context *ev, void *private_data); int common_event_check_signal(struct event_context *ev); + +bool events_standard_init(void); +bool events_select_init(void); +#if HAVE_EVENTS_EPOLL +bool events_epoll_init(void); +#endif +#if HAVE_LINUX_AIO +bool events_aio_init(void); +#endif + +#include "events_util.h" diff --git a/source4/lib/events/events_liboop.c b/source4/lib/events/events_liboop.c index 946c3888c1..339297a3cf 100644 --- a/source4/lib/events/events_liboop.c +++ b/source4/lib/events/events_liboop.c @@ -19,9 +19,8 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ -#include "includes.h" -#include "lib/events/events.h" -#include "lib/events/events_internal.h" +#include "events.h" +#include "events_internal.h" #include <oop.h> diff --git a/source4/lib/events/events_s4.c b/source4/lib/events/events_s4.c new file mode 100644 index 0000000000..edf92dba22 --- /dev/null +++ b/source4/lib/events/events_s4.c @@ -0,0 +1,57 @@ +/* + Unix SMB/CIFS implementation. + Copyright (C) Andrew Tridgell 2003 + + 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 "includes.h" +#include "events.h" +#include "events_internal.h" + +NTSTATUS s4_events_standard_init(void) +{ + if (!events_standard_init()) { + return NT_STATUS_INTERNAL_ERROR; + } + return NT_STATUS_OK; +} + +NTSTATUS s4_events_select_init(void) +{ + if (!events_select_init()) { + return NT_STATUS_INTERNAL_ERROR; + } + return NT_STATUS_OK; +} + +#if HAVE_EVENTS_EPOLL +NTSTATUS s4_events_epoll_init(void) +{ + if (!events_epoll_init()) { + return NT_STATUS_INTERNAL_ERROR; + } + return NT_STATUS_OK; +} +#endif + +#if HAVE_LINUX_AIO +NTSTATUS s4_events_aio_init(void) +{ + if (!events_aio_init()) { + return NT_STATUS_INTERNAL_ERROR; + } + return NT_STATUS_OK; +} +#endif diff --git a/source4/lib/events/events_select.c b/source4/lib/events/events_select.c index 16fff71e4a..9e97d2b39f 100644 --- a/source4/lib/events/events_select.c +++ b/source4/lib/events/events_select.c @@ -23,13 +23,7 @@ */ -#if _SAMBA_BUILD_ -#include "includes.h" -#include "lib/util/dlinklist.h" -#else #include "replace.h" -#include "events_util.h" -#endif #include "system/filesys.h" #include "system/select.h" #include "events.h" @@ -221,9 +215,8 @@ 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. */ -#if _SAMBA_BUILD_ - DEBUG(0,("ERROR: EBADF on select_event_loop_once\n")); -#endif + ev_debug(select_ev->ev, EV_DEBUG_FATAL, + "ERROR: EBADF on select_event_loop_once\n"); select_ev->exit_code = EBADF; return -1; } @@ -265,7 +258,7 @@ static int select_event_loop_once(struct event_context *ev) struct timeval tval; tval = common_event_loop_timer_delay(ev); - if (timeval_is_zero(&tval)) { + if (ev_timeval_is_zero(&tval)) { return 0; } @@ -306,12 +299,3 @@ bool events_select_init(void) return event_register_backend("select", &select_event_ops); } -#if _SAMBA_BUILD_ -_PUBLIC_ NTSTATUS s4_events_select_init(void) -{ - if (!events_select_init()) { - return NT_STATUS_INTERNAL_ERROR; - } - return NT_STATUS_OK; -} -#endif diff --git a/source4/lib/events/events_signal.c b/source4/lib/events/events_signal.c index 7128612fb0..5c74c47edd 100644 --- a/source4/lib/events/events_signal.c +++ b/source4/lib/events/events_signal.c @@ -19,14 +19,8 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ -#if _SAMBA_BUILD_ -#include "includes.h" -#include "lib/util/dlinklist.h" -#else #include <signal.h> #include "replace.h" -#include "events_util.h" -#endif #include "system/filesys.h" #include "system/select.h" #include "events.h" @@ -222,8 +216,8 @@ struct signal_event *common_event_add_signal(struct event_context *ev, if (sig_state->pipe_hack[0] == 0 && sig_state->pipe_hack[1] == 0) { pipe(sig_state->pipe_hack); - set_blocking(sig_state->pipe_hack[0], false); - set_blocking(sig_state->pipe_hack[1], false); + 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); diff --git a/source4/lib/events/events_standard.c b/source4/lib/events/events_standard.c index 4e41c42206..fbf83897c8 100644 --- a/source4/lib/events/events_standard.c +++ b/source4/lib/events/events_standard.c @@ -27,13 +27,7 @@ at runtime we fallback to select() */ -#if _SAMBA_BUILD_ -#include "includes.h" -#include "lib/util/dlinklist.h" -#else #include "replace.h" -#include "events_util.h" -#endif #include "system/filesys.h" #include "system/network.h" #include "system/select.h" /* needed for HAVE_EVENTS_EPOLL */ @@ -76,7 +70,9 @@ struct std_event_context { */ static void epoll_fallback_to_select(struct std_event_context *std_ev, const char *reason) { - DEBUG(0,("%s (%s) - falling back to select()\n", reason, strerror(errno))); + ev_debug(std_ev->ev, EV_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); @@ -133,7 +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) { - DEBUG(0,("Failed to recreate epoll handle after fork\n")); + ev_debug(std_ev->ev, EV_DEBUG_FATAL, + "Failed to recreate epoll handle after fork\n"); return; } std_ev->pid = getpid(); @@ -516,7 +513,8 @@ 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. */ - DEBUG(0,("ERROR: EBADF on std_event_loop_once\n")); + ev_debug(std_ev->ev, EV_DEBUG_FATAL, + "ERROR: EBADF on std_event_loop_once\n"); std_ev->exit_code = EBADF; return -1; } @@ -558,7 +556,7 @@ static int std_event_loop_once(struct event_context *ev) struct timeval tval; tval = common_event_loop_timer_delay(ev); - if (timeval_is_zero(&tval)) { + if (ev_timeval_is_zero(&tval)) { return 0; } @@ -606,12 +604,3 @@ bool events_standard_init(void) return event_register_backend("standard", &std_event_ops); } -#if _SAMBA_BUILD_ -_PUBLIC_ NTSTATUS s4_events_standard_init(void) -{ - if (!events_standard_init()) { - return NT_STATUS_INTERNAL_ERROR; - } - return NT_STATUS_OK; -} -#endif diff --git a/source4/lib/events/events_timed.c b/source4/lib/events/events_timed.c index 79e4cde795..c81825bf92 100644 --- a/source4/lib/events/events_timed.c +++ b/source4/lib/events/events_timed.c @@ -20,18 +20,91 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. */ -#if _SAMBA_BUILD_ -#include "includes.h" -#include "lib/util/dlinklist.h" -#else +#include <sys/time.h> +#include <time.h> #include "replace.h" -#include "events_util.h" -#endif #include "system/filesys.h" #include "system/select.h" #include "events.h" #include "events_internal.h" +/** + compare two timeval structures. + Return -1 if tv1 < tv2 + Return 0 if tv1 == tv2 + Return 1 if tv1 > tv2 +*/ +static int ev_timeval_compare(const struct timeval *tv1, const struct timeval *tv2) +{ + if (tv1->tv_sec > tv2->tv_sec) return 1; + if (tv1->tv_sec < tv2->tv_sec) return -1; + if (tv1->tv_usec > tv2->tv_usec) return 1; + if (tv1->tv_usec < tv2->tv_usec) return -1; + return 0; +} + +/** + return a zero timeval +*/ +static struct timeval ev_timeval_zero(void) +{ + struct timeval tv; + tv.tv_sec = 0; + tv.tv_usec = 0; + return tv; +} + +/** + return a timeval for the current time +*/ +static struct timeval ev_timeval_current(void) +{ + struct timeval tv; + gettimeofday(&tv, NULL); + return tv; +} + +/** + return a timeval struct with the given elements +*/ +static struct timeval ev_timeval_set(uint32_t secs, uint32_t usecs) +{ + struct timeval tv; + tv.tv_sec = secs; + tv.tv_usec = usecs; + return tv; +} + +/** + return the difference between two timevals as a timeval + if tv1 comes after tv2, then return a zero timeval + (this is *tv2 - *tv1) +*/ +static struct timeval ev_timeval_until(const struct timeval *tv1, + const struct timeval *tv2) +{ + struct timeval t; + if (ev_timeval_compare(tv1, tv2) >= 0) { + return ev_timeval_zero(); + } + t.tv_sec = tv2->tv_sec - tv1->tv_sec; + if (tv1->tv_usec > tv2->tv_usec) { + t.tv_sec--; + t.tv_usec = 1000000 - (tv1->tv_usec - tv2->tv_usec); + } else { + t.tv_usec = tv2->tv_usec - tv1->tv_usec; + } + return t; +} + +/** + return true if a timeval is zero +*/ +bool ev_timeval_is_zero(const struct timeval *tv) +{ + return tv->tv_sec == 0 && tv->tv_usec == 0; +} + /* destroy a timed event */ @@ -72,7 +145,7 @@ struct timed_event *common_event_add_timed(struct event_context *ev, TALLOC_CTX last_te = NULL; for (cur_te = ev->timed_events; cur_te; cur_te = cur_te->next) { /* if the new event comes before the current one break */ - if (timeval_compare(&te->next_event, &cur_te->next_event) < 0) { + if (ev_timeval_compare(&te->next_event, &cur_te->next_event) < 0) { break; } @@ -94,14 +167,14 @@ struct timed_event *common_event_add_timed(struct event_context *ev, TALLOC_CTX */ struct timeval common_event_loop_timer_delay(struct event_context *ev) { - struct timeval current_time = timeval_zero(); + struct timeval current_time = ev_timeval_zero(); struct timed_event *te = ev->timed_events; if (!te) { /* have a default tick time of 30 seconds. This guarantees that code that uses its own timeout checking will be able to proceeed eventually */ - return timeval_set(30, 0); + return ev_timeval_set(30, 0); } /* @@ -113,13 +186,13 @@ struct timeval common_event_loop_timer_delay(struct event_context *ev) * if there's a delay till the next timed event, we're done * with just returning the delay */ - if (!timeval_is_zero(&te->next_event)) { + if (!ev_timeval_is_zero(&te->next_event)) { struct timeval delay; - current_time = timeval_current(); + current_time = ev_timeval_current(); - delay = timeval_until(¤t_time, &te->next_event); - if (!timeval_is_zero(&delay)) { + delay = ev_timeval_until(¤t_time, &te->next_event); + if (!ev_timeval_is_zero(&delay)) { return delay; } } @@ -151,6 +224,6 @@ struct timeval common_event_loop_timer_delay(struct event_context *ev) talloc_free(te); - return timeval_zero(); + return ev_timeval_zero(); } diff --git a/source4/lib/events/events_util.c b/source4/lib/events/events_util.c index 74e11473f3..93f6492560 100644 --- a/source4/lib/events/events_util.c +++ b/source4/lib/events/events_util.c @@ -20,6 +20,9 @@ #include "replace.h" #include "talloc.h" +#include "events.h" +#include "events_internal.h" +#include <fcntl.h> /** return the number of elements in a string list @@ -34,7 +37,7 @@ static size_t str_list_length(const char **list) /** add an entry to a string list */ -const char **str_list_add(const char **list, const char *s) +const char **ev_str_list_add(const char **list, const char *s) { size_t len = str_list_length(list); const char **ret; @@ -50,80 +53,33 @@ const char **str_list_add(const char **list, const char *s) return ret; } -/** - compare two timeval structures. - Return -1 if tv1 < tv2 - Return 0 if tv1 == tv2 - Return 1 if tv1 > tv2 -*/ -static int timeval_compare(const struct timeval *tv1, const struct timeval *tv2) -{ - if (tv1->tv_sec > tv2->tv_sec) return 1; - if (tv1->tv_sec < tv2->tv_sec) return -1; - if (tv1->tv_usec > tv2->tv_usec) return 1; - if (tv1->tv_usec < tv2->tv_usec) return -1; - return 0; -} /** - return a zero timeval -*/ -struct timeval timeval_zero(void) -{ - struct timeval tv; - tv.tv_sec = 0; - tv.tv_usec = 0; - return tv; -} + Set a fd into blocking/nonblocking mode. Uses POSIX O_NONBLOCK if available, + else + if SYSV use O_NDELAY + if BSD use FNDELAY +**/ -/** - return true if a timeval is zero -*/ -bool timeval_is_zero(const struct timeval *tv) +int ev_set_blocking(int fd, bool set) { - return tv->tv_sec == 0 && tv->tv_usec == 0; + int val; +#ifdef O_NONBLOCK +#define FLAG_TO_SET O_NONBLOCK +#else +#ifdef SYSV +#define FLAG_TO_SET O_NDELAY +#else /* BSD */ +#define FLAG_TO_SET FNDELAY +#endif +#endif + + if((val = fcntl(fd, F_GETFL, 0)) == -1) + return -1; + if(set) /* Turn blocking on - ie. clear nonblock flag */ + val &= ~FLAG_TO_SET; + else + val |= FLAG_TO_SET; + return fcntl( fd, F_SETFL, val); +#undef FLAG_TO_SET } - -/** - return a timeval for the current time -*/ -struct timeval timeval_current(void) -{ - struct timeval tv; - GetTimeOfDay(&tv); - return tv; -} - -/** - return a timeval struct with the given elements -*/ -struct timeval timeval_set(uint32_t secs, uint32_t usecs) -{ - struct timeval tv; - tv.tv_sec = secs; - tv.tv_usec = usecs; - return tv; -} - -/** - return the difference between two timevals as a timeval - if tv1 comes after tv2, then return a zero timeval - (this is *tv2 - *tv1) -*/ -struct timeval timeval_until(const struct timeval *tv1, - const struct timeval *tv2) -{ - struct timeval t; - if (timeval_compare(tv1, tv2) >= 0) { - return timeval_zero(); - } - t.tv_sec = tv2->tv_sec - tv1->tv_sec; - if (tv1->tv_usec > tv2->tv_usec) { - t.tv_sec--; - t.tv_usec = 1000000 - (tv1->tv_usec - tv2->tv_usec); - } else { - t.tv_usec = tv2->tv_usec - tv1->tv_usec; - } - return t; -} - diff --git a/source4/lib/events/events_util.h b/source4/lib/events/events_util.h index 401df891a5..052b302aae 100644 --- a/source4/lib/events/events_util.h +++ b/source4/lib/events/events_util.h @@ -113,11 +113,5 @@ do { \ #endif /* _DLINKLIST_H */ -const char **str_list_add(const char **list, const char *s); -struct timeval timeval_zero(void); -bool timeval_is_zero(const struct timeval *tv); -struct timeval timeval_current(void); -struct timeval timeval_set(uint32_t secs, uint32_t usecs); -struct timeval timeval_until(const struct timeval *tv1, - const struct timeval *tv2); - +const char **ev_str_list_add(const char **list, const char *s); +int ev_set_blocking(int fd, bool set); diff --git a/source4/lib/events/libevents.m4 b/source4/lib/events/libevents.m4 index 483ab861fb..be3f1bb638 100644 --- a/source4/lib/events/libevents.m4 +++ b/source4/lib/events/libevents.m4 @@ -13,16 +13,34 @@ if test x"$eventsdir" = "x"; then AC_MSG_ERROR([cannot find libevents source in $eventspaths]) fi -EVENTS_OBJ="events.o events_select.o events_signal.o events_timed.o events_standard.o events_util.o" -AC_SUBST(LIBREPLACEOBJ) +EVENTS_OBJ="events.o events_select.o events_signal.o events_timed.o events_standard.o events_debug.o events_util.o" +SMB_ENABLE(EVENTS_EPOLL, NO) +SMB_ENABLE(EVENTS_AIO, 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 EVENTS_OBJ="$EVENTS_OBJ events_epoll.o" + SMB_ENABLE(EVENTS_EPOLL,YES) 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) + if test x"$ac_cv_header_libaio_h" = x"yes" -a x"$ac_cv_lib_ext_aio_io_getevents" = x"yes";then + EVENTS_OBJ="$EVENTS_OBJ events_aio.o" + SMB_ENABLE(EVENTS_AIO,YES) + AC_DEFINE(HAVE_LINUX_AIO, 1, [Whether Linux AIO is available]) + fi fi AC_SUBST(EVENTS_OBJ) +SMB_EXT_LIB(LIBAIO_LINUX, $AIO_LIBS) + +EVENTS_CFLAGS="-I$eventsdir" +AC_SUBST(EVENTS_CFLAGS) + +EVENTS_LIBS="" +AC_SUBST(EVENTS_LIBS) + diff --git a/source4/lib/events/rules.mk b/source4/lib/events/rules.mk new file mode 100644 index 0000000000..cfe548039b --- /dev/null +++ b/source4/lib/events/rules.mk @@ -0,0 +1,21 @@ +.SUFFIXES: .i _wrap.c + +.i_wrap.c: + $(SWIG) -O -Wall -python -keyword $< + +showflags:: + @echo 'libevents will be compiled with flags:' + @echo ' CFLAGS = $(CFLAGS)' + @echo ' CPPFLAGS = $(CPPFLAGS)' + @echo ' LDFLAGS = $(LDFLAGS)' + @echo ' LIBS = $(LIBS)' + +.SUFFIXES: .c .o + +.c.o: + @echo Compiling $*.c + @mkdir -p `dirname $@` + @$(CC) $(PICFLAG) $(CFLAGS) -c $< -o $@ + +distclean:: + rm -f *~ */*~ diff --git a/source4/lib/ldb/external/libevents.m4 b/source4/lib/ldb/external/libevents.m4 new file mode 100644 index 0000000000..f0f80e9d8e --- /dev/null +++ b/source4/lib/ldb/external/libevents.m4 @@ -0,0 +1,4 @@ +m4_include(pkg.m4) +EVENTS_OBJ="" +AC_SUBST(EVENTS_OBJ) +PKG_CHECK_MODULES(EVENTS, events) |