((void)0)
#endif
+#define EVENT_BASE_ASSERT_LOCKED(base) \
+ EVLOCK_ASSERT_LOCKED((base)->th_base_lock)
+
static void
detect_monotonic(void)
{
static int
gettime(struct event_base *base, struct timeval *tp)
{
+ EVENT_BASE_ASSERT_LOCKED(base);
+
if (base->tv_cache.tv_sec) {
*tp = base->tv_cache;
return (0);
int
event_reinit(struct event_base *base)
{
- /* XXXX We need to grab a lock here! */
- const struct eventop *evsel = base->evsel;
+ const struct eventop *evsel;
int res = 0;
struct event *ev;
+ EVBASE_ACQUIRE_LOCK(base, th_base_lock);
+
+ evsel = base->evsel;
+
/* check if this event mechanism requires reinit */
if (!evsel->need_reinit)
- return (0);
+ goto done;
/* prevent internal delete */
if (base->sig.ev_signal_added) {
if (base->evbase == NULL) {
event_errx(1, "%s: could not reinitialize event mechanism",
__func__);
- return (-1);
+ res = -1;
+ goto done;
}
event_changelist_freemem(&base->changelist); /* XXX */
}
}
+done:
+ EVBASE_RELEASE_LOCK(base, th_base_lock);
return (res);
}
/* Allows deletes to work */
ncalls = ev->ev_ncalls;
ev->ev_pncalls = &ncalls;
+ EVBASE_RELEASE_LOCK(base, th_base_lock);
while (ncalls) {
ncalls--;
ev->ev_ncalls = ncalls;
(*ev->ev_callback)((int)ev->ev_fd, ev->ev_res, ev->ev_arg);
+#if 0
+ /* XXXX we can't do this without a lock on the base. */
if (base->event_break)
return;
+#endif
}
}
}
event_add_internal(ev, &run_at, 1);
}
+ EVBASE_RELEASE_LOCK(base, th_base_lock);
(*ev->ev_callback)((int)ev->ev_fd, ev->ev_res, ev->ev_arg);
}
EVBASE_ACQUIRE_LOCK(base, current_event_lock);
- EVBASE_RELEASE_LOCK(base, th_base_lock);
-
switch (ev->ev_closure) {
case EV_CLOSURE_SIGNAL:
event_signal_closure(base, ev);
break;
default:
case EV_CLOSURE_NONE:
+ EVBASE_RELEASE_LOCK(base, th_base_lock);
(*ev->ev_callback)(
(int)ev->ev_fd, ev->ev_res, ev->ev_arg);
break;
/* See if there is a timeout that we should report */
if (tv != NULL && (flags & event & EV_TIMEOUT)) {
struct timeval tmp = ev->ev_timeout;
- gettime(ev->ev_base, &now);
+ event_base_gettimeofday_cached(ev->ev_base, &now);
tmp.tv_usec &= MICROSECONDS_MASK;
evutil_timersub(&tmp, &now, &res);
/* correctly remap to real time */
int res = 0;
int notify = 0;
+ EVENT_BASE_ASSERT_LOCKED(base);
_event_debug_assert_is_setup(ev);
event_debug((
if (ev->ev_base == NULL)
return (-1);
+ EVENT_BASE_ASSERT_LOCKED(ev->ev_base);
+
/* If the main thread is currently executing this event's callback,
* and we are not the main thread, then we want to wait until the
* callback is done before we start removing the event. That way,
base = ev->ev_base;
+ EVENT_BASE_ASSERT_LOCKED(base);
+
ev->ev_res = res;
if (ev->ev_events & EV_SIGNAL) {
static void
event_queue_remove(struct event_base *base, struct event *ev, int queue)
{
+ EVENT_BASE_ASSERT_LOCKED(base);
+
if (!(ev->ev_flags & queue)) {
event_errx(1, "%s: %p(fd %d) not on queue %x", __func__,
ev, ev->ev_fd, queue);
static void
event_queue_insert(struct event_base *base, struct event *ev, int queue)
{
+ EVENT_BASE_ASSERT_LOCKED(base);
+
if (ev->ev_flags & queue) {
/* Double insertion is possible for active events */
if (queue & EVLIST_ACTIVE)