--- libev/ev.pod 2009/04/16 07:32:51 1.233 +++ libev/ev.pod 2009/07/08 04:29:31 1.249 @@ -64,12 +64,24 @@ return 0; } -=head1 DESCRIPTION +=head1 ABOUT THIS DOCUMENT + +This document documents the libev software package. The newest version of this document is also available as an html-formatted web page you might find easier to navigate when reading it for the first time: L. +While this document tries to be as complete as possible in documenting +libev, its usage and the rationale behind its design, it is not a tutorial +on event-based programming, nor will it introduce event-based programming +with libev. + +Familarity with event based programming techniques in general is assumed +throughout this document. + +=head1 ABOUT LIBEV + Libev is an event loop: you register interest in certain events (such as a file descriptor being readable or a timeout occurring), and it will manage these event sources and provide your program with events. @@ -112,12 +124,12 @@ =head2 TIME REPRESENTATION -Libev represents time as a single floating point number, representing the -(fractional) number of seconds since the (POSIX) epoch (somewhere near -the beginning of 1970, details are complicated, don't ask). This type is -called C, which is what you should use too. It usually aliases -to the C type in C, and when you need to do any calculations on -it, you should treat it as some floating point value. Unlike the name +Libev represents time as a single floating point number, representing +the (fractional) number of seconds since the (POSIX) epoch (somewhere +near the beginning of 1970, details are complicated, don't ask). This +type is called C, which is what you should use too. It usually +aliases to the C type in C. When you need to do any calculations +on it, you should treat it as some floating point value. Unlike the name component C might indicate, it is also used for time differences throughout libev. @@ -611,6 +623,18 @@ "ticks" the number of loop iterations), as it roughly corresponds with C and C calls. +=item unsigned int ev_loop_depth (loop) + +Returns the number of times C was entered minus the number of +times C was exited, in other words, the recursion depth. + +Outside C, this number is zero. In a callback, this number is +C<1>, unless C was invoked recursively (or from another thread), +in which case it is higher. + +Leaving C abnormally (setjmp/longjmp, cancelling the thread +etc.), doesn't count as exit. + =item unsigned int ev_backend (loop) Returns one of the C flags indicating the event backend in @@ -634,7 +658,7 @@ very long time without entering the event loop, updating libev's idea of the current time is a good idea. -See also "The special problem of time updates" in the C section. +See also L in the C section. =item ev_suspend (loop) @@ -801,7 +825,9 @@ time collecting I/O events, so you can handle more events per iteration, at the cost of increasing latency. Timeouts (both C and C) will be not affected. Setting this to a non-null value will -introduce an additional C call into most loop iterations. +introduce an additional C call into most loop iterations. The +sleep time ensures that libev will not poll for I/O events more often then +once per this interval, on average. Likewise, by setting a higher I you allow libev to spend more time collecting timeouts, at the expense of increased @@ -813,7 +839,11 @@ interval to a value near C<0.1> or so, which is often enough for interactive servers (of course not for games), likewise for timeouts. It usually doesn't make much sense to set it to a lower value than C<0.01>, -as this approaches the timing granularity of most systems. +as this approaches the timing granularity of most systems. Note that if +you do transactions with the outside world and you can't increase the +parallelity, then this setting will limit your transaction rate (if you +need to poll once per transaction and the I/O collect interval is 0.01, +then you can't do more than 100 transations per second). Setting the I can improve the opportunity for saving power, as the program will "bundle" timer callback invocations that @@ -822,6 +852,12 @@ reduce iterations/wake-ups is to use C watchers and make sure they fire on, say, one-second boundaries only. +Example: we only need 0.1s timeout granularity, and we wish not to poll +more often than 100 times per second: + + ev_set_timeout_collect_interval (EV_DEFAULT_UC_ 0.1); + ev_set_io_collect_interval (EV_DEFAULT_UC_ 0.01); + =item ev_loop_verify (loop) This function only does something when C support has been @@ -1098,7 +1134,7 @@ The default priority used by watchers when no priority has been set is always C<0>, which is supposed to not be too high and not be too low :). -See L, below, for a more thorough treatment of +See L, below, for a more thorough treatment of priorities. =item ev_invoke (loop, ev_TYPE *watcher, int revents) @@ -1174,14 +1210,14 @@ static void t1_cb (EV_P_ ev_timer *w, int revents) { - struct my_biggy big = (struct my_biggy * + struct my_biggy big = (struct my_biggy *) (((char *)w) - offsetof (struct my_biggy, t1)); } static void t2_cb (EV_P_ ev_timer *w, int revents) { - struct my_biggy big = (struct my_biggy * + struct my_biggy big = (struct my_biggy *) (((char *)w) - offsetof (struct my_biggy, t2)); } @@ -1267,7 +1303,7 @@ } static void - idle-cb (EV_P_ ev_idle *w, int revents) + idle_cb (EV_P_ ev_idle *w, int revents) { // actual processing read (STDIN_FILENO, ...); @@ -1322,7 +1358,9 @@ If you cannot use non-blocking mode, then force the use of a known-to-be-good backend (at the time of this writing, this includes only -C and C). +C and C). The same applies to file +descriptors for which non-blocking operation makes no sense (such as +files) - libev doesn't guarentee any specific behaviour in that case. Another thing you have to watch out for is that it is quite easy to receive "spurious" readiness notifications, that is your callback might @@ -1453,10 +1491,11 @@ monotonic clock option helps a lot here). The callback is guaranteed to be invoked only I its timeout has -passed. If multiple timers become ready during the same loop iteration -then the ones with earlier time-out values are invoked before ones with -later time-out values (but this is no longer true when a callback calls -C recursively). +passed (not I, so on systems with very low-resolution clocks this +might introduce a small delay). If multiple timers become ready during the +same loop iteration then the ones with earlier time-out values are invoked +before ones of the same priority with later time-out values (but this is +no longer true when a callback calls C recursively). =head3 Be smart about timeouts @@ -1510,7 +1549,7 @@ At start: - ev_timer_init (timer, callback); + ev_init (timer, callback); timer->repeat = 60.; ev_timer_again (loop, timer); @@ -1582,7 +1621,7 @@ to the current time (meaning we just have some activity :), then call the callback, which will "do the right thing" and start the timer: - ev_timer_init (timer, callback); + ev_init (timer, callback); last_activity = ev_now (loop); callback (loop, timer, EV_TIMEOUT); @@ -1989,12 +2028,16 @@ has been forked (which implies it might have already exited), as long as the event loop isn't entered (or is continued from a watcher), i.e., forking and then immediately registering a watcher for the child is fine, -but forking and registering a watcher a few event loop iterations later is -not. +but forking and registering a watcher a few event loop iterations later or +in the next callback invocation is not. Only the default event loop is capable of handling signals, and therefore you can only register child watchers in the default event loop. +Due to some design glitches inside libev, child watchers will always be +handled at maximum priority (their priority is set to C by +libev) + =head3 Process Interaction Libev grabs C as soon as the default event loop is @@ -2355,7 +2398,7 @@ ev_idle *idle_watcher = malloc (sizeof (ev_idle)); ev_idle_init (idle_watcher, idle_cb); - ev_idle_start (loop, idle_cb); + ev_idle_start (loop, idle_watcher); =head2 C and C - customise your event loop! @@ -2458,7 +2501,7 @@ adns_beforepoll (ads, fds, &nfd, &timeout, timeval_from (ev_time ())); /* the callback is illegal, but won't be called as we stop during check */ - ev_timer_init (&tw, 0, timeout * 1e-3); + ev_timer_init (&tw, 0, timeout * 1e-3, 0.); ev_timer_start (loop, &tw); // create one ev_io per pollfd @@ -2698,6 +2741,39 @@ C cheats and calls it in the wrong process, the fork handlers will be invoked, too, of course. +=head3 The special problem of life after fork - how is it possible? + +Most uses of C consist of forking, then some simple calls to ste +up/change the process environment, followed by a call to C. This +sequence should be handled by libev without any problems. + +This changes when the application actually wants to do event handling +in the child, or both parent in child, in effect "continuing" after the +fork. + +The default mode of operation (for libev, with application help to detect +forks) is to duplicate all the state in the child, as would be expected +when I the parent I the child process continues. + +When both processes want to continue using libev, then this is usually the +wrong result. In that case, usually one process (typically the parent) is +supposed to continue with all watchers in place as before, while the other +process typically wants to start fresh, i.e. without any active watchers. + +The cleanest and most efficient way to achieve that with libev is to +simply create a new event loop, which of course will be "empty", and +use that for new watchers. This has the advantage of not touching more +memory than necessary, and thus avoiding the copy-on-write, and the +disadvantage of having to use multiple event loops (which do not support +signal watchers). + +When this is not possible, or you want to use the default loop for +other reasons, then in the process that wants to start "fresh", call +C followed by C. Destroying +the default loop will "orphan" (not stop) all registered watchers, so you +have to be careful not to execute code that modifies those watchers. Note +also that in that case, you have to re-register any signal watchers. + =head3 Watcher-Specific Functions and Data Members =over 4 @@ -3889,6 +3965,9 @@ There is no supported compilation method available on windows except embedding it into other applications. +Sensible signal handling is officially unsupported by Microsoft - libev +tries its best, but under most conditions, signals will simply not work. + Not a libev limitation but worth mentioning: windows apparently doesn't accept large writes: instead of resulting in a partial write, windows will either accept everything or return C if the buffer is too large, @@ -3902,7 +3981,7 @@ more than a hundred or so sockets, then likely it needs to use a totally different implementation for windows, as libev offers the POSIX readiness notification model, which cannot be implemented efficiently on windows -(Microsoft monopoly games). +(due to Microsoft monopoly games). A typical way to use libev under windows is to embed it (see the embedding section for details) and use the following F header file instead @@ -3948,24 +4027,22 @@ of C<64> handles (probably owning to the fact that all windows kernels can only wait for C<64> things at the same time internally; Microsoft recommends spawning a chain of threads and wait for 63 handles and the -previous thread in each. Great). +previous thread in each. Sounds great!). Newer versions support more handles, but you need to define C to some high number (e.g. C<2048>) before compiling the winsocket select -call (which might be in libev or elsewhere, for example, perl does its own -select emulation on windows). +call (which might be in libev or elsewhere, for example, perl and many +other interpreters do their own select emulation on windows). Another limit is the number of file descriptors in the Microsoft runtime -libraries, which by default is C<64> (there must be a hidden I<64> fetish -or something like this inside Microsoft). You can increase this by calling -C<_setmaxstdio>, which can increase this limit to C<2048> (another -arbitrary limit), but is broken in many versions of the Microsoft runtime -libraries. - -This might get you to about C<512> or C<2048> sockets (depending on -windows version and/or the phase of the moon). To get more, you need to -wrap all I/O functions and provide your own fd management, but the cost of -calling select (O(n²)) will likely make this unworkable. +libraries, which by default is C<64> (there must be a hidden I<64> +fetish or something like this inside Microsoft). You can increase this +by calling C<_setmaxstdio>, which can increase this limit to C<2048> +(another arbitrary limit), but is broken in many versions of the Microsoft +runtime libraries. This might get you to about C<512> or C<2048> sockets +(depending on windows version and/or the phase of the moon). To get more, +you need to wrap all I/O functions and provide your own fd management, but +the cost of calling select (O(n²)) will likely make this unworkable. =back @@ -4018,7 +4095,9 @@ The type C is used to represent timestamps. It is required to have at least 51 bits of mantissa (and 9 bits of exponent), which is good enough for at least into the year 4000. This requirement is fulfilled by -implementations implementing IEEE 754 (basically all existing ones). +implementations implementing IEEE 754, which is basically all existing +ones. With IEEE 754 doubles, you get microsecond accuracy until at least +2200. =back @@ -4096,6 +4175,82 @@ =back +=head1 GLOSSARY + +=over 4 + +=item active + +A watcher is active as long as it has been started (has been attached to +an event loop) but not yet stopped (disassociated from the event loop). + +=item application + +In this document, an application is whatever is using libev. + +=item callback + +The address of a function that is called when some event has been +detected. Callbacks are being passed the event loop, the watcher that +received the event, and the actual event bitset. + +=item callback invocation + +The act of calling the callback associated with a watcher. + +=item event + +A change of state of some external event, such as data now being available +for reading on a file descriptor, time having passed or simply not having +any other events happening anymore. + +In libev, events are represented as single bits (such as C or +C). + +=item event library + +A software package implementing an event model and loop. + +=item event loop + +An entity that handles and processes external events and converts them +into callback invocations. + +=item event model + +The model used to describe how an event loop handles and processes +watchers and events. + +=item pending + +A watcher is pending as soon as the corresponding event has been detected, +and stops being pending as soon as the watcher will be invoked or its +pending status is explicitly cleared by the application. + +A watcher can be pending, but not active. Stopping a watcher also clears +its pending status. + +=item real time + +The physical time that is observed. It is apparently strictly monotonic :) + +=item wall-clock time + +The time and date as shown on clocks. Unlike real time, it can actually +be wrong and jump forwards and backwards, e.g. when the you adjust your +clock. + +=item watcher + +A data structure that describes interest in certain events. Watchers need +to be started (attached to an event loop) before they can receive events. + +=item watcher invocation + +The act of calling the callback associated with a watcher. + +=back + =head1 AUTHOR Marc Lehmann , with repeated corrections by Mikael Magnusson.