--- libev/ev.pod 2011/12/20 16:32:21 1.391 +++ libev/ev.pod 2012/04/18 06:06:04 1.401 @@ -249,7 +249,7 @@ See the description of C watchers for more info. -=item ev_set_allocator (void *(*cb)(void *ptr, long size)) +=item ev_set_allocator (void *(*cb)(void *ptr, long size) throw ()) Sets the allocation function to use (the prototype is similar - the semantics are identical to the C C89/SuS/POSIX function). It is @@ -285,7 +285,7 @@ ... ev_set_allocator (persistent_realloc); -=item ev_set_syserr_cb (void (*cb)(const char *msg)) +=item ev_set_syserr_cb (void (*cb)(const char *msg) throw ()) Set the callback function to call on a retryable system call error (such as failed select, poll, epoll_wait). The message is a printable string @@ -569,9 +569,9 @@ kernel is more efficient (which says nothing about its actual speed, of course). While stopping, setting and starting an I/O watcher does never cause an extra system call as with C, it still adds up to -two event changes per incident. Support for C is very bad (but -sane, unlike epoll) and it drops fds silently in similarly hard-to-detect -cases +two event changes per incident. Support for C is very bad (you +might have to leak fd's on fork, but it's more sane than epoll) and it +drops fds silently in similarly hard-to-detect cases This backend usually performs well under most conditions. @@ -794,18 +794,22 @@ Calling C/C has the side effect of updating the event loop time (see C). -=item ev_run (loop, int flags) +=item bool ev_run (loop, int flags) Finally, this is it, the event handler. This function usually is called after you have initialised all your watchers and you want to start handling events. It will ask the operating system for any new events, call -the watcher callbacks, an then repeat the whole process indefinitely: This +the watcher callbacks, and then repeat the whole process indefinitely: This is why event loops are called I. If the flags argument is specified as C<0>, it will keep handling events until either no event watchers are active anymore or C was called. +The return value is false if there are no more active watchers (which +usually means "all jobs done" or "deadlock"), and true in all other cases +(which usually means " you should call C again"). + Please note that an explicit C is usually better than relying on all watchers to be stopped when deciding when a program has finished (especially in interactive programs), but having a program @@ -813,8 +817,8 @@ of relying on its watchers stopping correctly, that is truly a thing of beauty. -This function is also I exception-safe - you can break out of -a C call by calling C in a callback, throwing a C++ +This function is I exception-safe - you can break out of a +C call by calling C in a callback, throwing a C++ exception and so on. This does not decrement the C value, nor will it clear any outstanding C breaks. @@ -1014,7 +1018,7 @@ If you want to reset the callback, use C as new callback. -=item ev_set_loop_release_cb (loop, void (*release)(EV_P), void (*acquire)(EV_P)) +=item ev_set_loop_release_cb (loop, void (*release)(EV_P) throw (), void (*acquire)(EV_P) throw ()) Sometimes you want to share the same loop between multiple threads. This can be done relatively simply by putting mutex_lock/unlock calls around @@ -1880,7 +1884,7 @@ else { // callback was invoked, but there was some recent - // activity. simply restart the timer to time out + // activity. simply restart the timer to time out // after "after" seconds, which is the earliest time // the timeout can occur. ev_timer_set (w, after, 0.); @@ -2110,15 +2114,24 @@ =item ev_timer_again (loop, ev_timer *) -This will act as if the timer timed out and restarts it again if it is -repeating. The exact semantics are: +This will act as if the timer timed out, and restarts it again if it is +repeating. It basically works like calling C, updating the +timeout to the C value and calling C. + +The exact semantics are as in the following rules, all of which will be +applied to the watcher: + +=over 4 -If the timer is pending, its pending status is cleared. +=item If the timer is pending, the pending status is always cleared. -If the timer is started but non-repeating, stop it (as if it timed out). +=item If the timer is started but non-repeating, stop it (as if it timed +out, without invoking it). -If the timer is repeating, either start it if necessary (with the -C value), or reset the running timer to the C value. +=item If the timer is repeating, make the C value the new timeout +and start the timer, if necessary. + +=back This sounds a bit complicated, see L, above, for a usage example. @@ -3886,6 +3899,38 @@ =head1 C++ SUPPORT +=head2 C API + +The normal C API should work fine when used from C++: both ev.h and the +libev sources can be compiled as C++. Therefore, code that uses the C API +will work fine. + +Proper exception specifications might have to be added to callbacks passed +to libev: exceptions may be thrown only from watcher callbacks, all +other callbacks (allocator, syserr, loop acquire/release and periodioc +reschedule callbacks) must not throw exceptions, and might need a C specification. If you have code that needs to be compiled as both C +and C++ you can use the C macro for this: + + static void + fatal_error (const char *msg) EV_THROW + { + perror (msg); + abort (); + } + + ... + ev_set_syserr_cb (fatal_error); + +The only API functions that can currently throw exceptions are C, +C and C. + +Throwing exceptions in watcher callbacks is only supported if libev itself +is compiled with a C++ compiler or your C and C++ environments allow +throwing exceptions through C libraries (most do). + +=head2 C++ API + Libev comes with some simplistic wrapper classes for C++ that mainly allow you to use some convenience methods to start/stop watchers and also change the callback model to a model using method callbacks on objects. @@ -3910,6 +3955,10 @@ you need support for other types of functors please contact the author (preferably after implementing it). +For all this to work, your C++ compiler either has to use the same calling +conventions as your C compiler (for static member functions), or you have +to embed libev and compile libev itself as C++. + Here is a list of things available in the C namespace: =over 4 @@ -4497,6 +4546,19 @@ be detected at runtime. If undefined, it will be enabled if the headers indicate GNU/Linux + Glibc 2.4 or newer, otherwise disabled. +=item EV_NO_SMP + +If defined to be C<1>, libev will assume that memory is always coherent +between threads, that is, threads can be used, but threads never run on +different cpus (or different cpu cores). This reduces dependencies +and makes libev faster. + +=item EV_NO_THREADS + +If defined to be C<1>, libev will assume that it will never be called +from different threads, which is a stronger assumption than C, +above. This reduces dependencies and makes libev faster. + =item EV_ATOMIC_T Libev requires an integer type (suitable for storing C<0> or C<1>) whose @@ -4592,7 +4654,7 @@ #define EV_ASYNC_ENABLE 1 The actual value is a bitset, it can be a combination of the following -values: +values (by default, all of these are enabled): =over 4 @@ -4607,6 +4669,9 @@ gcc is recommended, as well as C<-DNDEBUG>, as libev contains a number of assertions. +The default is off when C<__OPTIMIZE_SIZE__> is defined by your compiler +(e.g. gcc with C<-Os>). + =item C<2> - faster/larger data structures Replaces the small 2-heap for timer management by a faster 4-heap, larger @@ -4614,6 +4679,9 @@ and can additionally have an effect on the size of data structures at runtime. +The default is off when C<__OPTIMIZE_SIZE__> is defined by your compiler +(e.g. gcc with C<-Os>). + =item C<4> - full API configuration This enables priorities (sets C=2 and C=-2), and @@ -4665,6 +4733,9 @@ To use this, define C and include F in the file that wants to use libev. +This option only works when libev is compiled with a C compiler, as C++ +doesn't support the required declaration syntax. + =item EV_AVOID_STDIO If this is set to C<1> at compiletime, then libev will avoid using stdio