-
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
build: allow easier checking of permanent deoptimizations #12456
Conversation
The changes in |
Also, I'm not sure if the vcbuild.bat changes are absolutely correct or done the best way, batch files are not my forte. For *nix though all you need to do is |
9585e11
to
0481405
Compare
Great work! I think this is a good step and I'd love to see this as part of our build.
It depends on whether or not they're actually in the tests or are caused by code calling code outside of the tests and would happen in user code when calling Node modules too necessarily. I'd like to see how this looks on TF+Ignition. Will review actual code soon. |
lib/fs.js
Outdated
for (const key in source) | ||
var target = {}; | ||
var key; | ||
for (key in source) |
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.
Does for (var key in source)
really deopt here?
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.
No, just the const
usage. I thought there was an issue with using var
in a for-in at one time, but I could be remembering wrong. I will change those.
@@ -320,7 +321,7 @@ fs.existsSync = function(path) { | |||
}; | |||
|
|||
fs.readFile = function(path, options, callback) { | |||
callback = maybeCallback(arguments[arguments.length - 1]); | |||
callback = maybeCallback(callback || options); |
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.
I see why this might indeed be "semver-major-y" but it looks fine to me. The only difference is in the case callback is passed but not as a function at which point options
would be passed and would be rethrown if real options passed.
I think a CITGM run would be sufficient here and if that passes I don't think we need to change it or semver-major it.
Also I'm very surprised arguments use only indexed access and length check is performed deopts.
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.
I think it's also because arguments
was being used in a function where the named arguments were being overwritten. This could be a Crankshaft-specific limitation though, I'm not sure.
@@ -1248,7 +1247,7 @@ function writeAll(fd, isUserFd, buffer, offset, length, position, callback_) { | |||
} | |||
|
|||
fs.writeFile = function(path, data, options, callback) { | |||
callback = maybeCallback(arguments[arguments.length - 1]); | |||
callback = maybeCallback(callback || options); |
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.
ditto for comment above.
@@ -99,7 +99,7 @@ function shared(message, handle, indexesKey, cb) { | |||
delete handles[key]; | |||
delete indexes[indexesKey]; | |||
return close.apply(this, arguments); | |||
}; | |||
}.bind(handle); |
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.
Mind explaining this one? Typically bind
isn't that great at not causing deopts :D
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.
Bad value context for arguments value
See: https://gist.github.com/Hypercubed/89808f3051101a1a97f3
Actual changes LGTM but I'd like to check it out and test it first. I'd also land this in two parts - fixing the deopts and adding the flag, but I'd prefer defer that choice to you and the CTC. |
0481405
to
17e5d49
Compare
For the most part the deopts in tests are clearly labeled with absolute paths to the test file in the deopt message line, so that was how I knew the deopt was not actually happening in node core. However for some special cases, such as the |
How about for all the places you replaced |
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.
Add /** @const */ where replacing const
with var
@refack Here are some issues I see with doing such things:
My intention with this PR was to have something so that in case someone does change a |
Apart from automatic tools, there's also the future human reader.
Comments? will add noise for Crankshaft? (sincere question, could you point me to more info?)
Not be a thing as in; not be deopts? so we'd revert this change?
I just don't want the intention to be lost (some of your changes superficially seem syntactical, while other are semantic [reusing the vars]) |
One way to cause a function to not be inlineable in Crankshaft is to exceed the maximum source length (default is 600 characters).
Fixes for other deopts could be viewed just as unclear (e.g. the
What I mean is that TurboFan + Ignition may not cause these deopts (they may be Crankshaft-specific), so it may/may not matter for the master branch (and node v8.x) after future V8 upgrades. If they are Crankshaft-specific, then they could be reverted if necessary.
Any reuse of variables is due to duplicate |
I thought that adding comments will be the perfect balance of gaining performance, and keeping readability/maintainability. If I'm so off target, I'll remove my objection.
Including comments?
👍
Ok. but, they are sill "loss of intention" cases. |
In second thought that's actually even worse, as a future dev (or a current dev like me) will get confused and might want to remove it. IMHO non-intuitive changes should be commented. |
@hashseed do you know if comments hinder inlining? |
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
PR-URL: #12456 Reviewed-By: Benjamin Gruenbaum <[email protected]> Reviewed-By: James M Snell <[email protected]>
@mscdex should this be backported to v6.x? |
@gibfahn Sure. |
As the title says, this adds a build target to allow for checking for permanent deoptimizations in node core simply by running the parallel and sequential tests. This is not a "complete" solution per-se because it currently creates (and ignores) the issues it causes with tests that fork processes due to the extra output on stdout, which some tests check. However, aside from that it should work correctly everywhere else.
There are a few deoptimization fixes I've left out in this PR:
domain.js
runBound()
andrunIntercepted()
have deopts that do not seem straight-forward to fix AFAICT because of the API we are exposing. The deopt reason for both is:I was able to fix this same issue in another spot by
bind()
ing the function (this makes it monomorphic), but I'm not sure we can do that in these two functions becausethis
is being utilized and I am not sure how much of userland calls the created bound/intercept functions with customthis
values.internal/process.js
v8BreakIterator()
also has I'm ignoring it since it's deprecated.punycode.js
adapt()
anddecode()
both have: I'm ignoring these because it's third party code and the module is deprecated.repl.js
There are a bunch of other permanent deopts, but they lie in the actual tests themselves and not in lib/. Currently this build target shows all deopts, no matter where they occur as it does not seem that we can always reliably detect whether a deopt is from a test or not. I am not sure if deopts in tests are worth going after, perhaps it could be a possibility for code-and-learn or similar events (although the deopt reasons may be too confusing for some audiences)?
CI: https://ci.nodejs.org/job/node-test-pull-request/7436/
Checklist
make -j4 test
(UNIX), orvcbuild test
(Windows) passesAffected core subsystem(s)