ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/libev/ev.c
(Generate patch)

Comparing libev/ev.c (file contents):
Revision 1.242 by root, Fri May 9 14:07:19 2008 UTC vs.
Revision 1.243 by root, Fri May 9 15:52:13 2008 UTC

235# else 235# else
236# define EV_USE_EVENTFD 0 236# define EV_USE_EVENTFD 0
237# endif 237# endif
238#endif 238#endif
239 239
240#ifndef EV_USE_4HEAP
241# define EV_USE_4HEAP !EV_MINIMAL
242#endif
243
244#ifndef EV_HEAP_CACHE_AT
245# define EV_HEAP_CACHE_AT !EV_MINIMAL
246#endif
247
240/* this block fixes any misconfiguration where we know we run into trouble otherwise */ 248/* this block fixes any misconfiguration where we know we run into trouble otherwise */
241 249
242#ifndef CLOCK_MONOTONIC 250#ifndef CLOCK_MONOTONIC
243# undef EV_USE_MONOTONIC 251# undef EV_USE_MONOTONIC
244# define EV_USE_MONOTONIC 0 252# define EV_USE_MONOTONIC 0
430 WL head; 438 WL head;
431} ANFS; 439} ANFS;
432#endif 440#endif
433 441
434/* Heap Entry */ 442/* Heap Entry */
435#define EV_HEAP_CACHE_AT 0
436#if EV_HEAP_CACHE_AT 443#if EV_HEAP_CACHE_AT
437 typedef struct { 444 typedef struct {
445 ev_tstamp at;
438 WT w; 446 WT w;
439 ev_tstamp at;
440 } ANHE; 447 } ANHE;
441 448
442 #define ANHE_w(he) (he).w /* access watcher, read-write */ 449 #define ANHE_w(he) (he).w /* access watcher, read-write */
443 #define ANHE_at(he) (he).at /* access cached at, read-only */ 450 #define ANHE_at(he) (he).at /* access cached at, read-only */
444 #define ANHE_at_set(he) (he).at = (he).w->at /* update at from watcher */ 451 #define ANHE_at_set(he) (he).at = (he).w->at /* update at from watcher */
791 * at the moment we allow libev the luxury of two heaps, 798 * at the moment we allow libev the luxury of two heaps,
792 * a small-code-size 2-heap one and a ~1.5kb larger 4-heap 799 * a small-code-size 2-heap one and a ~1.5kb larger 4-heap
793 * which is more cache-efficient. 800 * which is more cache-efficient.
794 * the difference is about 5% with 50000+ watchers. 801 * the difference is about 5% with 50000+ watchers.
795 */ 802 */
796#define EV_USE_4HEAP !EV_MINIMAL
797#if EV_USE_4HEAP 803#if EV_USE_4HEAP
798 804
799#define DHEAP 4 805#define DHEAP 4
800#define HEAP0 (DHEAP - 1) /* index of first element in heap */ 806#define HEAP0 (DHEAP - 1) /* index of first element in heap */
801 807
886 heap [k] = heap [p]; 892 heap [k] = heap [p];
887 ev_active (ANHE_w (heap [k])) = k; 893 ev_active (ANHE_w (heap [k])) = k;
888 k = p; 894 k = p;
889 } 895 }
890 896
891 heap [k] = w; 897 heap [k] = he;
892 ev_active (ANHE_w (heap [k])) = k; 898 ev_active (ANHE_w (heap [k])) = k;
893} 899}
894 900
895/* away from the root */ 901/* away from the root */
896void inline_speed 902void inline_speed
906 break; 912 break;
907 913
908 c += c + 1 < N && ANHE_at (heap [c]) > ANHE_at (heap [c + 1]) 914 c += c + 1 < N && ANHE_at (heap [c]) > ANHE_at (heap [c + 1])
909 ? 1 : 0; 915 ? 1 : 0;
910 916
911 if (w->at <= ANHE_at (heap [c])) 917 if (ANHE_at (he) <= ANHE_at (heap [c]))
912 break; 918 break;
913 919
914 heap [k] = heap [c]; 920 heap [k] = heap [c];
915 ev_active (ANHE_w (heap [k])) = k; 921 ev_active (ANHE_w (heap [k])) = k;
916 922
1604 /*assert (("inactive timer on timer heap detected", ev_is_active (w)));*/ 1610 /*assert (("inactive timer on timer heap detected", ev_is_active (w)));*/
1605 1611
1606 /* first reschedule or stop timer */ 1612 /* first reschedule or stop timer */
1607 if (w->repeat) 1613 if (w->repeat)
1608 { 1614 {
1609 assert (("negative ev_timer repeat value found while processing timers", w->repeat > 0.));
1610
1611 ev_at (w) += w->repeat; 1615 ev_at (w) += w->repeat;
1612 if (ev_at (w) < mn_now) 1616 if (ev_at (w) < mn_now)
1613 ev_at (w) = mn_now; 1617 ev_at (w) = mn_now;
1618
1619 assert (("negative ev_timer repeat value found while processing timers", w->repeat > 0.));
1614 1620
1615 ANHE_at_set (timers [HEAP0]); 1621 ANHE_at_set (timers [HEAP0]);
1616 downheap (timers, timercnt, HEAP0); 1622 downheap (timers, timercnt, HEAP0);
1617 } 1623 }
1618 else 1624 else
1634 1640
1635 /* first reschedule or stop timer */ 1641 /* first reschedule or stop timer */
1636 if (w->reschedule_cb) 1642 if (w->reschedule_cb)
1637 { 1643 {
1638 ev_at (w) = w->reschedule_cb (w, ev_rt_now + TIME_EPSILON); 1644 ev_at (w) = w->reschedule_cb (w, ev_rt_now + TIME_EPSILON);
1645
1639 assert (("ev_periodic reschedule callback returned time in the past", ev_at (w) > ev_rt_now)); 1646 assert (("ev_periodic reschedule callback returned time in the past", ev_at (w) > ev_rt_now));
1647
1640 ANHE_at_set (periodics [HEAP0]); 1648 ANHE_at_set (periodics [HEAP0]);
1641 downheap (periodics, periodiccnt, HEAP0); 1649 downheap (periodics, periodiccnt, HEAP0);
1642 } 1650 }
1643 else if (w->interval) 1651 else if (w->interval)
1644 { 1652 {
1645 ev_at (w) = w->offset + ceil ((ev_rt_now - w->offset) / w->interval) * w->interval; 1653 ev_at (w) = w->offset + ceil ((ev_rt_now - w->offset) / w->interval) * w->interval;
1646 if (ev_at (w) - ev_rt_now <= TIME_EPSILON) ev_at (w) += w->interval; 1654 if (ev_at (w) - ev_rt_now <= TIME_EPSILON) ev_at (w) += w->interval;
1655
1647 assert (("ev_periodic timeout in the past detected while processing timers, negative interval?", ev_at (w) > ev_rt_now)); 1656 assert (("ev_periodic timeout in the past detected while processing timers, negative interval?", ev_at (w) > ev_rt_now));
1657
1648 ANHE_at_set (periodics [HEAP0]); 1658 ANHE_at_set (periodics [HEAP0]);
1649 downheap (periodics, periodiccnt, HEAP0); 1659 downheap (periodics, periodiccnt, HEAP0);
1650 } 1660 }
1651 else 1661 else
1652 ev_periodic_stop (EV_A_ w); /* nonrepeating: stop timer */ 1662 ev_periodic_stop (EV_A_ w); /* nonrepeating: stop timer */
1671 ev_at (w) = w->offset + ceil ((ev_rt_now - w->offset) / w->interval) * w->interval; 1681 ev_at (w) = w->offset + ceil ((ev_rt_now - w->offset) / w->interval) * w->interval;
1672 1682
1673 ANHE_at_set (periodics [i]); 1683 ANHE_at_set (periodics [i]);
1674 } 1684 }
1675 1685
1676 /* now rebuild the heap, this for the 2-heap, inefficient for the 4-heap, but correct */ 1686 /* we don't use floyds algorithm, uphead is simpler and is more cache-efficient */
1677 for (i = periodiccnt >> 1; --i; ) 1687 /* also, this is easy and corretc for both 2-heaps and 4-heaps */
1688 for (i = 0; i < periodiccnt; ++i)
1678 downheap (periodics, periodiccnt, i + HEAP0); 1689 upheap (periodics, i + HEAP0);
1679} 1690}
1680#endif 1691#endif
1681 1692
1682void inline_speed 1693void inline_speed
1683time_update (EV_P_ ev_tstamp max_block) 1694time_update (EV_P_ ev_tstamp max_block)
2086 ev_at (w) = w->offset; 2097 ev_at (w) = w->offset;
2087 2098
2088 ev_start (EV_A_ (W)w, ++periodiccnt + HEAP0 - 1); 2099 ev_start (EV_A_ (W)w, ++periodiccnt + HEAP0 - 1);
2089 array_needsize (ANHE, periodics, periodicmax, ev_active (w) + 1, EMPTY2); 2100 array_needsize (ANHE, periodics, periodicmax, ev_active (w) + 1, EMPTY2);
2090 ANHE_w (periodics [ev_active (w)]) = (WT)w; 2101 ANHE_w (periodics [ev_active (w)]) = (WT)w;
2102 ANHE_at_set (periodics [ev_active (w)]);
2091 upheap (periodics, ev_active (w)); 2103 upheap (periodics, ev_active (w));
2092 2104
2093 /*assert (("internal periodic heap corruption", ANHE_w (periodics [ev_active (w)]) == (WT)w));*/ 2105 /*assert (("internal periodic heap corruption", ANHE_w (periodics [ev_active (w)]) == (WT)w));*/
2094} 2106}
2095 2107

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines