[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

Re: [Libevent-users] Re: [Levent-commits] [Libevent/master 3/4] Add doxygen for event_base_dump_events



Am 06.09.2012 17:44, schrieb Nick Mathewson:
On Thu, Sep 6, 2012 at 8:40 AM, Roman Puls <puls@xxxxxxxxxxxx> wrote:
Hi Nick,

excellent - it would be even greater to specify a callback procedure
receiving the struct event tokens (I currently write language bindings for
tcl, and it would be great to generate the textual representation myself)
Hm. This would probably be a matter of turning
"event_base_foreach_event_()" into a public, supported API.  My main
obstacle for that is that I'm not sure entirely what the documentation
should say about what functions the callback would be allowed to
invoke.  Still, that's not insurmountable if somebody's interested in
writing a patch (targetting 2.1, of course) -- 2.0 doesn't have
event_base_foreach_event_() internally.

But why I write:

shouldn't that stuff (event_base_dump_events) be mutex-protected?
It probably should!  A patch would be welcome.


event-dump-lock.patch for the latter
event-foreach-fully.patch for the first topic (public API). However, I generally changed the signature of the callback to const (struct event_base|event).

Cheers,
  Roman


diff --git a/event.c b/event.c
index 79664d4..0925bb5 100644
--- a/event.c
+++ b/event.c
@@ -3311,11 +3311,13 @@ dump_active_event_fn(struct event_base *base, struct event *e, void *arg)
 void
 event_base_dump_events(struct event_base *base, FILE *output)
 {
+	EVBASE_ACQUIRE_LOCK(base, th_base_lock);
 	fprintf(output, "Inserted events:\n");
 	event_base_foreach_event_(base, dump_inserted_event_fn, output);
 
 	fprintf(output, "Active events:\n");
 	event_base_foreach_event_(base, dump_active_event_fn, output);
+	EVBASE_RELEASE_LOCK(base, th_base_lock);
 }
 
 void
diff --git a/event-internal.h b/event-internal.h
index 112821d..5372af8 100644
--- a/event-internal.h
+++ b/event-internal.h
@@ -401,7 +401,7 @@ void event_base_assert_ok_nolock_(struct event_base *base);
 
 
 /* Callback type for event_base_foreach_event. */
-typedef int (*event_base_foreach_event_cb)(struct event_base *base, struct event *, void *);
+//typedef int (*event_base_foreach_event_cb)(struct event_base *base, struct event *, void *);
 
 /* Helper function: Call 'fn' exactly once every inserted or active event in
  * the event_base 'base'.
diff --git a/event.c b/event.c
index 79664d4..2e1676c 100644
--- a/event.c
+++ b/event.c
@@ -3194,7 +3194,7 @@ evthread_make_base_notifiable_nolock_(struct event_base *base)
 
 int
 event_base_foreach_event_(struct event_base *base,
-    int (*fn)(struct event_base *, struct event *, void *), void *arg)
+    event_base_foreach_event_cb fn, void *arg)
 {
 	int r, i;
 	unsigned u;
@@ -3255,7 +3255,7 @@ event_base_foreach_event_(struct event_base *base,
 /* Helper for event_base_dump_events: called on each event in the event base;
  * dumps only the inserted events. */
 static int
-dump_inserted_event_fn(struct event_base *base, struct event *e, void *arg)
+dump_inserted_event_fn(const struct event_base *base, const struct event *e, void *arg)
 {
 	FILE *output = arg;
 	const char *gloss = (e->ev_events & EV_SIGNAL) ?
@@ -3287,7 +3287,7 @@ dump_inserted_event_fn(struct event_base *base, struct event *e, void *arg)
 /* Helper for event_base_dump_events: called on each event in the event base;
  * dumps only the active events. */
 static int
-dump_active_event_fn(struct event_base *base, struct event *e, void *arg)
+dump_active_event_fn(const struct event_base *base, const struct event *e, void *arg)
 {
 	FILE *output = arg;
 	const char *gloss = (e->ev_events & EV_SIGNAL) ?
@@ -3308,14 +3308,29 @@ dump_active_event_fn(struct event_base *base, struct event *e, void *arg)
 	return 0;
 }
 
+void 
+event_base_foreach_event(struct event_base *base, 
+    event_base_foreach_event_cb fn, void *arg)
+{
+	if ((!fn) || (!base)) {
+		return;
+	}
+	EVBASE_ACQUIRE_LOCK(base, th_base_lock);
+	event_base_foreach_event_(base, fn, arg);
+	EVBASE_RELEASE_LOCK(base, th_base_lock);
+}
+
+
 void
 event_base_dump_events(struct event_base *base, FILE *output)
 {
+	EVBASE_ACQUIRE_LOCK(base, th_base_lock);
 	fprintf(output, "Inserted events:\n");
 	event_base_foreach_event_(base, dump_inserted_event_fn, output);
 
 	fprintf(output, "Active events:\n");
 	event_base_foreach_event_(base, dump_active_event_fn, output);
+	EVBASE_RELEASE_LOCK(base, th_base_lock);
 }
 
 void
diff --git a/evmap.c b/evmap.c
index 62ecb7b..e02e4e9 100644
--- a/evmap.c
+++ b/evmap.c
@@ -963,7 +963,7 @@ evmap_check_integrity_(struct event_base *base)
 /* Helper type for evmap_foreach_event_: Bundles a function to call on every
  * event, and the user-provided void* to use as its third argument. */
 struct evmap_foreach_event_helper {
-	int (*fn)(struct event_base *, struct event *, void *);
+	int (*fn)(const struct event_base *, const struct event *, void *);
 	void *arg;
 };
 
@@ -1001,7 +1001,7 @@ evmap_signal_foreach_event_fn(struct event_base *base, int signum,
 
 int
 evmap_foreach_event_(struct event_base *base,
-    int (*fn)(struct event_base *, struct event *, void *), void *arg)
+    int (*fn)(const struct event_base *, const struct event *, void *), void *arg)
 {
 	struct evmap_foreach_event_helper h;
 	int r;
diff --git a/include/event2/event.h b/include/event2/event.h
index c2f65c9..503b9de 100644
--- a/include/event2/event.h
+++ b/include/event2/event.h
@@ -1325,6 +1325,27 @@ void event_set_mem_functions(
  */
 void event_base_dump_events(struct event_base *, FILE *);
 
+
+/**
+ * callback for iterating events in an event base via event_base_foreach_event
+ */
+typedef int (*event_base_foreach_event_cb)(const struct event_base *, const struct event *, void *);
+
+/**
+   Iterate all current events in a given event loop. The method is an
+   alternative to event_base_dump_events, but provides a native interface
+   towards the events. 
+
+   Modification of events during iteration is an invalid operation
+   and may lead to unexpected behaviour
+
+   @param base An event_base on which to scan the events.
+   @param fn   A callback function to receive the events.
+*/
+void event_base_foreach_event(struct event_base *base, event_base_foreach_event_cb fn, void *arg);
+
+
+
 /** Sets 'tv' to the current time (as returned by gettimeofday()),
     looking at the cached value in 'base' if possible, and calling
     gettimeofday() or clock_gettime() as appropriate if there is no