Hi! On tuesday, I sent mail about various problems with libevent and its current API as well as implementation. Unfortunately, the mail has not yet shown up, but fortunately, it has been superseded by this one :)
In that mail, I announced that I will work on the problems I encountered in libevent (many of which have been reported and discusssed earlier on this list). After analyzing libevent I decided that it wasn't fixable except by rewriting the core parts of it (the inability to have multiple watchers for the same file descriptor event turned out to be blocking for my applications, otherwise I wouldn't have started the effort in the first place...). The results look promising so far: I additionally implemented a libevent compatibility layer and benchmarked both libraries using the benchmark program provided by libevent: http://libev.schmorp.de/bench.html Here is an incomplete list of what I changed and added (see the full list at http://cvs.schmorp.de/libev/README, or the cvs repository at http://cvs.schmorp.de/libev/): fixed or improved: * multiple watchers can wait for the same event, there is no limitation to one or two watchers for signals and io. * there is full support for fork, you can continue to use the event loop in the parent and child (or just one of them), even with quirky backends such as epoll. * there are two types of timers, based on real time differences and wall clock time (cron-like). timers can also be repeating and be reset at almost no cost (for idle timeouts used by many network servers). time jumps get detected reliably in both directions with or without a monotonic clock. * timers are managed by a priority queue (O(1) for important operations as opposed to O(log n) in libevent, also resulting in much simpler code). * event watchers can be added and removed at any time (in libevent, removing events that are pending can lead to crashes). * different types of events use different watchers, so you don't have to use an i/o event watcher for timeouts, and you can reset timers seperately from other types of watchers. Also, watchers are much smaller (even the libevent emulation watcher only has about 2/3 of the size of a libevent watcher). * I added idle watchers, pid watchers and hook watchers into the event loop, as is required for integration of other event-based libraries, without having to force the use of some construct around event_loop. * the backends use a much simpler design. unlike in libevent, the code to handle events is not duplicated for each backend, backends deal only with file descriptor events and a single timeout value, everything else is handled by the core, which also optimises state changes (the epoll backend is 100 lines in libev, as opposed to >350 lines in libevent, without suffering from its limitations). As for compatibility, the actual libev api is very different to the libevent API (although the design is similar), but there is a emulation layer with a corresponding event.h file that supports the event library (but no evbuffer, evnds, evhttp etc.). It works very well: both the testsuite as well as the benchmark program from libevent work as expected, and the evdns code compiles (and runs) without any changes, making libev a drop-in replacement for libevent users. "Porting" evbuffer and so on would be equally trivial. However: libev has not yet been released on its own (only as part of the EV perl module), meaning there is no configure script, C-level documentation etc. The "obvious" plan would be to take the evhttp etc. code from libevent and paste it in to libev, making libev a complete replacement for libevent with an optional new API. The catch is, I'd like to avoid this, because I am not prepared to maintain yet another library, and I am not keen on replicating the configure and portability work that went into libevent so far. So, would there be an interest in replacing the "core" event part of libevent with the libev code? If yes, there are a number of issues to solve, and here is how I would solve them: * libev only supports select and epoll. Adding poll would be trivial for me, and adding dev/poll and kqueue support would be easy, except that I don't want to set-up some bsd machines just for that. I would, however, opt to write kqueue and /dev/poll backends "dry" and let somebody else do the actual porting stuff to the then-existing backends. * libev only supports one "event base". The reason is that I think a leader/ follower pattern together with lazy I/O would beat any multiple event loop implementation, and the fact that each time I see some software module using its own copy of some mainloop meant that it doesn't work together with other such modules :) Still, if integration should be achieved, this is no insurmountable obstacle :-> * libev uses its own api, which potentially causes some global symbol spamming (lots of functions with ev_ prefix). This could be used as a chance to switch to a more efficient API while at the same time keeping 100% backwards compatibility. (The event emulation layer in libev is only 1.3kb of codesize on my machine, so reasonably thin). So what do you think? If you are not interested, I am prepared to maintain it on my own, too, so there is no pressure for either direction, I think. Greetings, and thanke for making me write my own event loop something I had planned to do for many years now :) Also kudos for the event_once interface, which I hadn't implemented if I hadn't seen it in libevent before. -- The choice of a Deliantra, the free code+content MORPG -----==- _GNU_ http://www.deliantra.net ----==-- _ generation ---==---(_)__ __ ____ __ Marc Lehmann --==---/ / _ \/ // /\ \/ / [EMAIL PROTECTED] -=====/_/_//_/\_,_/ /_/\_\ _______________________________________________ Libevent-users mailing list Libevent-users@monkey.org http://monkey.org/mailman/listinfo/libevent-users