From b6a2373c2c9a98594a87c54a4644f3c0e985e420 Mon Sep 17 00:00:00 2001 From: Wilmer van der Gaast Date: Wed, 28 Nov 2007 23:24:26 +0000 Subject: Fixed the epoll+ForkDaemon combination. The libevent event handling didn't work very well on Linux 2.6 (and possibly others) in ForkDaemon mode. --- lib/events_libevent.c | 49 +++++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 41 insertions(+), 8 deletions(-) (limited to 'lib') diff --git a/lib/events_libevent.c b/lib/events_libevent.c index f2b4d15c..d02ad6a6 100644 --- a/lib/events_libevent.c +++ b/lib/events_libevent.c @@ -36,7 +36,9 @@ #include #include -static guint id_next; +static void b_main_restart(); + +static guint id_next = 1; static GHashTable *id_hash; static int quitting = 0; @@ -47,6 +49,9 @@ static int quitting = 0; static GHashTable *read_hash; static GHashTable *write_hash; +struct event_base *leh; +struct event_base *old_leh; + struct b_event_data { guint id; @@ -58,9 +63,16 @@ struct b_event_data void b_main_init() { - event_init(); + if( leh != NULL ) + { + /* Clean up the hash tables? */ + + b_main_restart(); + old_leh = leh; + } + + leh = event_init(); - id_next = 1; id_hash = g_hash_table_new( g_int_hash, g_int_equal ); read_hash = g_hash_table_new( g_int_hash, g_int_equal ); write_hash = g_hash_table_new( g_int_hash, g_int_equal ); @@ -68,19 +80,40 @@ void b_main_init() void b_main_run() { - event_dispatch(); + /* This while loop is necessary to exit the event loop and start a + different one (necessary for ForkDaemon mode). */ + while( event_base_dispatch( leh ) == 0 && !quitting ) + { + if( old_leh != NULL ) + { + /* For some reason this just isn't allowed... + Possibly a bug in older versions, will see later. + event_base_free( old_leh ); */ + old_leh = NULL; + } + + printf( "New event loop.\n" ); + } } -void b_main_quit() +static void b_main_restart() { struct timeval tv; - /* libevent sometimes generates events before really quitting, + memset( &tv, 0, sizeof( struct timeval ) ); + event_base_loopexit( leh, &tv ); + + printf( "b_main_restart()\n" ); +} + +void b_main_quit() +{ + /* Tell b_main_run() that it shouldn't restart the loop. Also, + libevent sometimes generates events before really quitting, we want to stop them. */ quitting = 1; - memset( &tv, 0, sizeof( struct timeval ) ); - event_loopexit( &tv ); + b_main_restart(); } static void b_event_passthrough( int fd, short event, void *data ) -- cgit v1.2.3 From 9ff5737ec53cca2ba295b58fb74a8b97f496cd19 Mon Sep 17 00:00:00 2001 From: Wilmer van der Gaast Date: Thu, 29 Nov 2007 21:55:14 +0000 Subject: printf() in daemons considered harmful. --- lib/events.h | 4 ++-- lib/events_libevent.c | 8 +++----- 2 files changed, 5 insertions(+), 7 deletions(-) (limited to 'lib') diff --git a/lib/events.h b/lib/events.h index 0588547f..4baea7b6 100644 --- a/lib/events.h +++ b/lib/events.h @@ -44,7 +44,7 @@ #include #include -/* The conditions you can pass to gaim_input_add()/that will be passed to +/* The conditions you can pass to b_input_add()/that will be passed to the given callback function. */ typedef enum { GAIM_INPUT_READ = 1 << 1, @@ -57,7 +57,7 @@ typedef gboolean (*b_event_handler)(gpointer data, gint fd, b_input_condition co #define GAIM_WRITE_COND (G_IO_OUT | G_IO_HUP | G_IO_ERR | G_IO_NVAL) #define GAIM_ERR_COND (G_IO_HUP | G_IO_ERR | G_IO_NVAL) -// #define event_debug( x... ) printf( x ) +/* #define event_debug( x... ) printf( x ) */ #define event_debug( x... ) /* Call this once when the program starts. It'll initialize the event handler diff --git a/lib/events_libevent.c b/lib/events_libevent.c index d02ad6a6..d3403152 100644 --- a/lib/events_libevent.c +++ b/lib/events_libevent.c @@ -31,13 +31,11 @@ #include #include #include -#include "proxy.h" - #include #include +#include "proxy.h" static void b_main_restart(); - static guint id_next = 1; static GHashTable *id_hash; static int quitting = 0; @@ -92,7 +90,7 @@ void b_main_run() old_leh = NULL; } - printf( "New event loop.\n" ); + event_debug( "New event loop.\n" ); } } @@ -103,7 +101,7 @@ static void b_main_restart() memset( &tv, 0, sizeof( struct timeval ) ); event_base_loopexit( leh, &tv ); - printf( "b_main_restart()\n" ); + event_debug( "b_main_restart()\n" ); } void b_main_quit() -- cgit v1.2.3