Browse Source

Call Tick() after coming out of select()

Previously we would only call it before going into select(). This is needed
to fix test/simple/test-next-tick-ordering2.js.
v0.7.4-release
Ryan Dahl 14 years ago
parent
commit
17f3ffa633
  1. 35
      src/node.cc
  2. 8
      test/simple/test-next-tick-ordering2.js

35
src/node.cc

@ -73,7 +73,8 @@ static bool use_debug_agent = false;
static bool debug_wait_connect = false;
static int debug_port=5858;
static ev_prepare next_tick_watcher;
static ev_check check_tick_watcher;
static ev_prepare prepare_tick_watcher;
static ev_idle tick_spinner;
static bool need_tick_cb;
static Persistent<String> tick_callback_sym;
@ -164,6 +165,11 @@ static void Check(EV_P_ ev_check *watcher, int revents) {
static Handle<Value> NeedTickCallback(const Arguments& args) {
HandleScope scope;
need_tick_cb = true;
// TODO: this tick_spinner shouldn't be necessary. An ev_prepare should be
// sufficent, the problem is only in the case of the very last "tick" -
// there is nothing left to do in the event loop and libev will exit. The
// ev_prepare callback isn't called before exiting. Thus we start this
// tick_spinner to keep the event loop alive long enough to handle it.
ev_idle_start(EV_DEFAULT_UC_ &tick_spinner);
return Undefined();
}
@ -175,10 +181,7 @@ static void Spin(EV_P_ ev_idle *watcher, int revents) {
}
static void Tick(EV_P_ ev_prepare *watcher, int revents) {
assert(watcher == &next_tick_watcher);
assert(revents == EV_PREPARE);
static void Tick(void) {
// Avoid entering a V8 scope.
if (!need_tick_cb) return;
@ -207,6 +210,20 @@ static void Tick(EV_P_ ev_prepare *watcher, int revents) {
}
static void PrepareTick(EV_P_ ev_prepare *watcher, int revents) {
assert(watcher == &prepare_tick_watcher);
assert(revents == EV_PREPARE);
Tick();
}
static void CheckTick(EV_P_ ev_check *watcher, int revents) {
assert(watcher == &check_tick_watcher);
assert(revents == EV_CHECK);
Tick();
}
static void DoPoll(EV_P_ ev_idle *watcher, int revents) {
assert(watcher == &eio_poller);
assert(revents == EV_IDLE);
@ -1808,8 +1825,12 @@ int main(int argc, char *argv[]) {
ev_default_loop(EVFLAG_AUTO);
#endif
ev_prepare_init(&node::next_tick_watcher, node::Tick);
ev_prepare_start(EV_DEFAULT_UC_ &node::next_tick_watcher);
ev_prepare_init(&node::prepare_tick_watcher, node::PrepareTick);
ev_prepare_start(EV_DEFAULT_UC_ &node::prepare_tick_watcher);
ev_unref(EV_DEFAULT_UC);
ev_check_init(&node::check_tick_watcher, node::CheckTick);
ev_check_start(EV_DEFAULT_UC_ &node::check_tick_watcher);
ev_unref(EV_DEFAULT_UC);
ev_idle_init(&node::tick_spinner, node::Spin);

8
test/simple/test-next-tick-ordering2.js

@ -3,13 +3,13 @@ assert = common.assert
var order = [];
process.nextTick(function () {
process.nextTick(function() {
order.push('nextTick');
});
setTimeout(function() {
order.push('setTimeout');
}, 0);
process.nextTick(function() {
order.push('nextTick');
});
})
process.addListener('exit', function () {

Loading…
Cancel
Save