-
Notifications
You must be signed in to change notification settings - Fork 223
Description
I'm opening this issue to discuss the current status of async_hooks in nodejs and how it affects node-fibers.
@AndreasMadsen I want your input here about what fibers can do going forward to ensure that what we're doing here remains possible as async_hooks matures. I've added you to this thread because of your work on async_hooks in the nodejs repository.
I'm not sure if you're familiar with node-fibers but as the name implies I've implemented fibers/coroutines in nodejs. I started this project in 2011 on node v0.2.x before async/await even had a viable specification proposal-- the value of this project is questionable now that support for single-frame continuations exists in JS natively, but the fact remains that a lot of projects still depend on node-fibers.
I managed to pull this implementation off with some hacks to thread-local storage to make v8 think it is running in multiple threads when what is actually happening behind the scenes is just setjmp/longjmp magic. Appropriate Locker/Unlocker scopes are in place and all this is expressly allowed in the v8 API. Some members of the node team have expressed disgust and outrage with this approach but it works. Additionally the same functionality can be implemented cleanly without violating any invariants via threading and conditional waits, though we would lose the lightweight nature of the current implementation.
Anyway, I find myself fighting with async_hooks in recent days because it justifiably assumes that there will be only one stack. I've put in place even more hacks to deal with this, most recently in nodejs v8.10.0 due to the changes to the undocumented APIs I was using. You can see this implementation in fibers.js#L29.
The hacks can be expressed as two simple functions: getAndClearStack()
and restoreStack()
. The first function saves the current async stack, returns it as an array, and then sets the stack to empty. The second function restores an async stack using the return value from a previous invocation to getAndClearStack
. restoreStack
assumes that it is called while the async stack is currently empty. node-fibers can then call those two functions where appropriate and nodejs is happy. It's important to note that all the RAII goodness of AsyncHooks::CallbackScope continues to work with these two functions in place since the correct async stack will always be restored before longjmp'ing back into that scope.
So what I would I like to ask is: would the nodejs team be open to supporting, or allowing me to support, these two functions in the async_hooks API?