-
Notifications
You must be signed in to change notification settings - Fork 29.6k
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
buffer: auto random fill Buffer(num) and new Buffer(num) #11806
Conversation
src/node.cc
Outdated
return node::UncheckedMalloc(size); | ||
} else if (zero_fill_field_ == 3) { | ||
void* mem = node::UncheckedMalloc(size); | ||
memset(mem, random_fill_value_, size); |
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.
You’ll need a mem != nullptr
check around this ;)
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.
doh... I always forget about that.
Hm, my first intuition is that a flag specifically for the buffer constructor itself, or specific to security-related API usage, would be better than one for general “pending” deprecations? |
if (typeof arg === 'number') { | ||
if (typeof encodingOrOffset === 'string') { | ||
throw new Error( | ||
'If encoding is specified then the first argument must be a string' | ||
); | ||
} | ||
return Buffer.allocUnsafe(arg); | ||
assertSize(arg); | ||
return new FastBuffer(createRandomFillBuffer(arg)); |
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.
Part of the performance hit might be that this stops using pooled allocation. Is that intentional?
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.
Yes, but it needn't I suppose. This was largely just to keep it simple and consistent. If we happen to pull off the pooled allocation, do you imagine we would just zero fill or use the randomly selected value to fill?
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.
@jasnell The best way that comes to mind for me right now is to have separate pools for uninitialized & for random-filled Buffers … alternatively, we could just keep using Buffer.allocUnsafe()
here and fill manually.
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.
Yeah. I'm leaning in that direction to be honest (specifically, using Buffer.alloc(size, fill)
). It would be much less disruptive and wouldn't require the underlying c/c++ change. I did it this way first to see what the perf would be like and it is way too much of a hit
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'm going to open a second PR that uses this other method. I'd like us to get some comparison benchmark runs on various platforms. Definitely think going with the alloc then fill in js is going to be the better option tho.
Regarding the flag, I'd really rather not have yet another special-case buffer-specific flag but certainly not completely opposed to it. |
Command line flag that can be used to indicate that pending deprecations should be emitted.
The pending deprecation warning is off by default. Launch the node process with --pending-deprecation or NODE_PENDING_DEPRECATION=1 env var set.
It should be noted that this makes it a breaking change for performance-critical applications, and by introducing it in 8.0.0 we won't be giving people time to migrate as described in our deprecation policy. This isn't to say that this is necessarily a bad solution, but I think it's an important fact that shouldn't be overlooked. |
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'm going to close this one in favor of the alternate which is much less disruptive overall and has a better perf profile. |
@addaleax @nodejs/ctc ...
This PR does a couple things as a proposal to bring some closure to #9531
As suggested by @addaleax, a pseudo-random byte value is selected at startup and used to auto-fill
new Buffer(num)
andBuffer(num)
.A new
--pending-deprecation
command-line flag andNODE_PENDING_DEPRECATION=1
environment variable is added that allows conditional off-by-default pending deprecation warnings.A pending deprecation warning is added for
Buffer()
andnew Buffer()
. This is off by default and will only be emitted when the new command line flag is set.These are separated out into multiple commits.
There is a definite significant performance hit to
new Buffer(num)
andBuffer(num)
using this.Checklist
make -j4 test
(UNIX), orvcbuild test
(Windows) passesAffected core subsystem(s)
buffer