Skip to content

Commit 8140333

Browse files
felixgeisaacs
authored andcommitted
Fix process.nextTick throw call sites
This patch now reports the proper throw call site for exceptions triggered within process.nextTick. So instead of this: node.js:201 throw e; // process.nextTick error, or 'error' event on first tick ^ You will now see: mydir/myscript.js:15 throw new Error('My Error'); ^ From my testing this patch causes no performance regressions, but does greatly simplify processing the nextTickQueue.
1 parent ee437c0 commit 8140333

6 files changed

Lines changed: 28 additions & 32 deletions

File tree

src/node.cc

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -255,9 +255,7 @@ static void Spin(uv_idle_t* handle, int status) {
255255
Tick();
256256
}
257257

258-
259-
static Handle<Value> NeedTickCallback(const Arguments& args) {
260-
HandleScope scope;
258+
static void StartTickSpinner() {
261259
need_tick_cb = true;
262260
// TODO: this tick_spinner shouldn't be necessary. An ev_prepare should be
263261
// sufficent, the problem is only in the case of the very last "tick" -
@@ -268,9 +266,12 @@ static Handle<Value> NeedTickCallback(const Arguments& args) {
268266
uv_idle_start(&tick_spinner, Spin);
269267
uv_ref(uv_default_loop());
270268
}
271-
return Undefined();
272269
}
273270

271+
static Handle<Value> NeedTickCallback(const Arguments& args) {
272+
StartTickSpinner();
273+
return Undefined();
274+
}
274275

275276
static void PrepareTick(uv_prepare_t* handle, int status) {
276277
assert(handle == &prepare_tick_watcher);
@@ -1694,6 +1695,9 @@ void FatalException(TryCatch &try_catch) {
16941695
emit->Call(process, 2, event_argv);
16951696
// Decrement so we know if the next exception is a recursion or not
16961697
uncaught_exception_counter--;
1698+
1699+
// This makes sure uncaught exceptions don't interfere with process.nextTick
1700+
StartTickSpinner();
16971701
}
16981702

16991703

src/node.js

Lines changed: 8 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -180,26 +180,18 @@
180180

181181
startup.processNextTick = function() {
182182
var nextTickQueue = [];
183+
var nextTickIndex = 0;
183184

184185
process._tickCallback = function() {
185-
var l = nextTickQueue.length;
186-
if (l === 0) return;
186+
var nextTickLength = nextTickQueue.length;
187+
if (nextTickLength === 0) return;
187188

188-
var q = nextTickQueue;
189-
nextTickQueue = [];
190-
191-
try {
192-
for (var i = 0; i < l; i++) q[i]();
193-
}
194-
catch (e) {
195-
if (i + 1 < l) {
196-
nextTickQueue = q.slice(i + 1).concat(nextTickQueue);
197-
}
198-
if (nextTickQueue.length) {
199-
process._needTickCallback();
200-
}
201-
throw e; // process.nextTick error, or 'error' event on first tick
189+
while (nextTickIndex < nextTickLength) {
190+
nextTickQueue[nextTickIndex++]();
202191
}
192+
193+
nextTickQueue.splice(0, nextTickIndex);
194+
nextTickIndex = 0;
203195
};
204196

205197
process.nextTick = function(callback) {

test/message/stack_overflow.out

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
before
22

3-
node.js:*
4-
throw e; // process.nextTick error, or 'error' event on first tick
5-
^
3+
module.js:311
4+
throw err;
5+
^
66
RangeError: Maximum call stack size exceeded
Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
before
22

3-
node.js:*
4-
throw e; // process.nextTick error, or 'error' event on first tick
5-
^
3+
module.js:311
4+
throw err;
5+
^
66
MyCustomError: This is a custom message

test/message/throw_non_error.out

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
before
22

3-
node.js:*
4-
throw e; // process.nextTick error, or 'error' event on first tick
5-
^
3+
module.js:311
4+
throw err;
5+
^
66
[object Object]

test/message/undefined_reference_in_new_context.out

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
before
22

3-
node.js:*
4-
throw e; // process.nextTick error, or 'error' event on first tick
5-
^
3+
module.js:311
4+
throw err;
5+
^
66
ReferenceError: foo is not defined
77
at evalmachine.<anonymous>:*
88
at Object.<anonymous> (*test*message*undefined_reference_in_new_context.js:*)

0 commit comments

Comments
 (0)