Skip to content

Commit

Permalink
async_hooks: minor cleanup and improvements
Browse files Browse the repository at this point in the history
Cleanup some code and make the emit hooks very slightly faster.

PR-URL: #27034
Reviewed-By: Yongsheng Zhang <zyszys98@gmail.com>
Reviewed-By: Ruben Bridgewater <ruben@bridgewater.de>
Reviewed-By: James M Snell <jasnell@gmail.com>
  • Loading branch information
apapirovski authored and BridgeAR committed Apr 4, 2019
1 parent b2bb6c2 commit 04355ef
Showing 1 changed file with 32 additions and 31 deletions.
63 changes: 32 additions & 31 deletions lib/internal/async_hooks.js
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,8 @@ const { kInit, kBefore, kAfter, kDestroy, kTotals, kPromiseResolve,
kCheck, kExecutionAsyncId, kAsyncIdCounter, kTriggerAsyncId,
kDefaultTriggerAsyncId, kStackLength } = async_wrap.constants;

const FunctionBind = Function.call.bind(Function.prototype.bind);

// Used in AsyncHook and AsyncResource.
const async_id_symbol = Symbol('asyncId');
const trigger_async_id_symbol = Symbol('triggerAsyncId');
Expand Down Expand Up @@ -151,38 +153,37 @@ function emitInitNative(asyncId, type, triggerAsyncId, resource) {
}
}


function emitHookFactory(symbol, name) {
// Called from native. The asyncId stack handling is taken care of there
// before this is called.
// eslint-disable-next-line func-style
const fn = function(asyncId) {
active_hooks.call_depth += 1;
// Use a single try/catch for all hook to avoid setting up one per
// iteration.
try {
for (var i = 0; i < active_hooks.array.length; i++) {
if (typeof active_hooks.array[i][symbol] === 'function') {
active_hooks.array[i][symbol](asyncId);
}
// Called from native. The asyncId stack handling is taken care of there
// before this is called.
function emitHook(symbol, asyncId) {
active_hooks.call_depth += 1;
// Use a single try/catch for all hook to avoid setting up one per
// iteration.
try {
for (var i = 0; i < active_hooks.array.length; i++) {
if (typeof active_hooks.array[i][symbol] === 'function') {
active_hooks.array[i][symbol](asyncId);
}
} catch (e) {
fatalError(e);
} finally {
active_hooks.call_depth -= 1;
}
} catch (e) {
fatalError(e);
} finally {
active_hooks.call_depth -= 1;
}

// Hooks can only be restored if there have been no recursive hook calls.
// Also the active hooks do not need to be restored if enable()/disable()
// weren't called during hook execution, in which case
// active_hooks.tmp_array will be null.
if (active_hooks.call_depth === 0 && active_hooks.tmp_array !== null) {
restoreActiveHooks();
}
};
// Hooks can only be restored if there have been no recursive hook calls.
// Also the active hooks do not need to be restored if enable()/disable()
// weren't called during hook execution, in which case
// active_hooks.tmp_array will be null.
if (active_hooks.call_depth === 0 && active_hooks.tmp_array !== null) {
restoreActiveHooks();
}
}

function emitHookFactory(symbol, name) {
const fn = FunctionBind(emitHook, undefined, symbol);

// Set the name property of the anonymous function as it looks good in the
// stack trace.
// Set the name property of the function as it looks good in the stack trace.
Object.defineProperty(fn, 'name', {
value: name
});
Expand Down Expand Up @@ -264,10 +265,10 @@ function getOrSetAsyncId(object) {
// the user to safeguard this call and make sure it's zero'd out when the
// constructor is complete.
function getDefaultTriggerAsyncId() {
let defaultTriggerAsyncId = async_id_fields[kDefaultTriggerAsyncId];
const defaultTriggerAsyncId = async_id_fields[kDefaultTriggerAsyncId];
// If defaultTriggerAsyncId isn't set, use the executionAsyncId
if (defaultTriggerAsyncId < 0)
defaultTriggerAsyncId = async_id_fields[kExecutionAsyncId];
return async_id_fields[kExecutionAsyncId];
return defaultTriggerAsyncId;
}

Expand Down Expand Up @@ -396,8 +397,8 @@ function pushAsyncIds(asyncId, triggerAsyncId) {

// This is the equivalent of the native pop_async_ids() call.
function popAsyncIds(asyncId) {
if (async_hook_fields[kStackLength] === 0) return false;
const stackLength = async_hook_fields[kStackLength];
if (stackLength === 0) return false;

if (async_hook_fields[kCheck] > 0 &&
async_id_fields[kExecutionAsyncId] !== asyncId) {
Expand Down

1 comment on commit 04355ef

@vvo
Copy link

@vvo vvo commented on 04355ef May 28, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

hey @apapirovski, on Node 12.3.1, I am getting weird errors like:

TypeError: Cannot read property 'enter' of undefined
  at AsyncHook.before (domain.js:76:20)
  at emitHook (internal/async_hooks.js:164:38)

And since this pull request seems to be updating the context of some functions I am wondering if this could be linked to this commit? Sorry this is very vague but I haven't found any other reference online about those errors. Thanks!

Also using https://github.com/getsentry/sentry-javascript if this has any impact.

Please sign in to comment.