| Index: bin/timer_impl.dart
|
| ===================================================================
|
| --- bin/timer_impl.dart (revision 2499)
|
| +++ bin/timer_impl.dart (working copy)
|
| @@ -75,10 +75,6 @@
|
| if (_callback !== null) {
|
|
|
| DoubleLinkedQueueEntry<_Timer> entry = _timers.firstEntry();
|
| - if (entry === null) {
|
| - _createTimerHandler();
|
| - }
|
| -
|
| while (entry !== null) {
|
| if (_wakeupTime < entry.element._wakeupTime) {
|
| entry.prepend(this);
|
| @@ -92,12 +88,26 @@
|
|
|
|
|
| void _notifyEventHandler() {
|
| + if (_handling_callbacks) {
|
| + // While we are already handling callbacks we will not notify the event
|
| + // handler. _handleTimeout will call _notifyEventHandler once all pending
|
| + // timers are processed.
|
| + return;
|
| + }
|
| +
|
| if (_timers.firstEntry() === null) {
|
| + // No pending timers: Close the receive port and let the event handler
|
| + // know.
|
| if (_receivePort !== null) {
|
| EventHandler._sendData(-1, _receivePort, _NO_TIMER);
|
| _shutdownTimerHandler();
|
| }
|
| } else {
|
| + if (_receivePort === null) {
|
| + // Create a receive port and register a message handler for the timer
|
| + // events.
|
| + _createTimerHandler();
|
| + }
|
| EventHandler._sendData(-1,
|
| _receivePort,
|
| _timers.firstEntry().element._wakeupTime);
|
| @@ -114,22 +124,34 @@
|
| void _handleTimeout() {
|
| int currentTime = (new Date.now()).value + _TIMER_JITTER;
|
|
|
| + // Collect all pending timers.
|
| DoubleLinkedQueueEntry<_Timer> entry = _timers.firstEntry();
|
| + var pending_timers = new List();
|
| while (entry !== null) {
|
| _Timer timer = entry.element;
|
| if (timer._wakeupTime <= currentTime) {
|
| entry.remove();
|
| + pending_timers.addLast(timer);
|
| + entry = _timers.firstEntry();
|
| + } else {
|
| + break;
|
| + }
|
| + }
|
| +
|
| + // Trigger all of the pending timers. New timers added as part of the
|
| + // callbacks will be enqueued now and notified in the next spin at the
|
| + // earliest.
|
| + _handling_callbacks = true;
|
| + try {
|
| + for (var timer in pending_timers) {
|
| timer._callback(timer);
|
| - // Always process the event with the earliest wakeupTime first.
|
| - entry = _timers.firstEntry();
|
| if (timer._repeating) {
|
| timer._advanceWakeupTime();
|
| timer._addTimerToList();
|
| - _notifyEventHandler();
|
| }
|
| - } else {
|
| - break;
|
| }
|
| + } finally {
|
| + _handling_callbacks = false;
|
| }
|
| _notifyEventHandler();
|
| }
|
| @@ -154,6 +176,7 @@
|
| static DoubleLinkedQueue<_Timer> _timers;
|
|
|
| static ReceivePort _receivePort;
|
| + static bool _handling_callbacks = false;
|
|
|
| var _callback;
|
| int _milliSeconds;
|
|
|