-
Notifications
You must be signed in to change notification settings - Fork 30k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
src: use object to pass Environment
to functions
#26382
Conversation
Use a `v8::Object` with an internal field, rather than a `v8::External`. On a `GetReturnValue().Set(Environment::GetCurrent(args) == nullptr)` noop function, this benchmarks as a ~60 % speedup, as calls to `obj->GetAlignedPointerFromInternalField()` can be inlined. This also makes breaking up some pieces of the `Environment` class into per-native-binding data easier, if we want to pursue that path in the future.
CI: https://ci.nodejs.org/job/node-test-pull-request/21107/ (:heavy_check_mark:) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
calls to obj->GetAlignedPointerFromInternalField() can be inlined
I suspect the reason of the performance improvement is less indirection.
A v8::External
is very similar to a v8::Object
but it boxes the pointer inside a v8::internal::Foreign
instance in order that unaligned pointers can be stored. That additional indirection comes at a cost.
I suppose V8 could optimize the box away most of the time by having two different External types internally, one for unboxed aligned pointers and one for boxed unaligned pointers. But I digress.
@bnoordhuis Yeah, that makes sense. |
Landed in 955be86 |
Use a `v8::Object` with an internal field, rather than a `v8::External`. On a `GetReturnValue().Set(Environment::GetCurrent(args) == nullptr)` noop function, this benchmarks as a ~60 % speedup, as calls to `obj->GetAlignedPointerFromInternalField()` can be inlined and the field is stored with one level of indirection less. This also makes breaking up some pieces of the `Environment` class into per-native-binding data easier, if we want to pursue that path in the future. PR-URL: #26382 Reviewed-By: James M Snell <jasnell@gmail.com> Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl>
Use a `v8::Object` with an internal field, rather than a `v8::External`. On a `GetReturnValue().Set(Environment::GetCurrent(args) == nullptr)` noop function, this benchmarks as a ~60 % speedup, as calls to `obj->GetAlignedPointerFromInternalField()` can be inlined and the field is stored with one level of indirection less. This also makes breaking up some pieces of the `Environment` class into per-native-binding data easier, if we want to pursue that path in the future. PR-URL: nodejs#26382 Reviewed-By: James M Snell <jasnell@gmail.com> Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl>
This is currently blocking the serialization of To unblock the snapshot integration, we need to go back to |
@joyeecheung So, I’m unfortunately only seeing your comment now, but I think it still deserves a reply. What you’re saying sounds like a defect in the V8 API to me. If templates are supposed to be context-independent, and the only way to associate data with C++ binding callbacks is to pass a As the commit message hints at, my main motivation here wasn’t actually the performance improvement, but rather I was trying to open up the possibility to make our internals a bit more flexible by allowing associating more than one item of data with the callback. (I’m assuming that that can also be done another way, using a |
As long as what we have in
It's difficult for me to see how allowing a I'll rebase my snapshot prototype and post it here for testing when I am back from vacation - the last time I tried, after I reverted this PR it only crashed until after the templates were traversed in the snapshot creator (due to something else I needed to fix..that I could not remember). With this PR it crashed during the traversal of the templates. So if your POC works it should once again crash at some point later. |
Use a
v8::Object
with an internal field, rather than av8::External
.On a
GetReturnValue().Set(Environment::GetCurrent(args) == nullptr)
noop function, this benchmarks as a ~60 % speedup, as calls to
obj->GetAlignedPointerFromInternalField()
can be inlined.This also makes breaking up some pieces of the
Environment
classinto per-native-binding data easier, if we want to pursue that path
in the future.
Checklist
make -j4 test
(UNIX), orvcbuild test
(Windows) passes