Skip to content
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

Type confusion bug in WriteFloatGeneric #12179

Closed
deian opened this issue Apr 3, 2017 · 8 comments
Closed

Type confusion bug in WriteFloatGeneric #12179

deian opened this issue Apr 3, 2017 · 8 comments
Labels
buffer Issues and PRs related to the buffer subsystem. c++ Issues and PRs that require attention from people who are familiar with C++. security Issues and PRs related to security.

Comments

@deian
Copy link
Member

deian commented Apr 3, 2017

The buffer writeFloatLE family functions are prone to code [remote] execution attacks via type confusion. The binding layer WriteFloatGeneric function just casts the first argument:

Local<Uint8Array> ts_obj = args[0].As<Uint8Array>();

Local<Uint8Array> ts_obj = args[0].As<Uint8Array>();

Few methods are called on the ts_obj after which if you choose a good argument means executing code with some choice.

For example, the following doesn't crash until the memcpy on my machine:

Buffer.prototype.writeFloatLE.call(0xdeadbeef, 0, 0, true);
@mscdex mscdex added buffer Issues and PRs related to the buffer subsystem. c++ Issues and PRs that require attention from people who are familiar with C++. labels Apr 3, 2017
@addaleax
Copy link
Member

addaleax commented Apr 3, 2017

See #12119 for a PR that just proposes dropping the noAssert flag.

Also, tbh it seems like a bit of a stretch to call this a security issue. If you have access to the buffer.write* methods and the ability to call them with chosen arguments, you can already perform writes to arbitrary memory anyway.

@deian
Copy link
Member Author

deian commented Apr 3, 2017

That was actually brought up by my email to [email protected] on 3/27, but I didn't want to create a redundant issue. The snippet for that the OOB write I had was:

const buf = Buffer.from('w00t');
buf.writeFloatLE(0, 4, true);

But this is a different kind of bug: it's a type confusion bug. It just so happens to be in the same code. I think dropping the noAssert flag is great. Thanks for all the great you're doing @addaleax.

@TimothyGu
Copy link
Member

TimothyGu commented Apr 3, 2017

The crash itself was fixed in #11927 (4fb9b12), with the original issue being #8724.

@deian
Copy link
Member Author

deian commented Apr 3, 2017

Saw that you're on top of these! Thanks @TimothyGu! That fixed the oob issues (didn't check, but I trust). The type confusion remains, I think.

On 2d039ff, this will segfault:

function FB() {this.x=33; this.y=44;}
require('util').inherits(FB, Buffer);
Buffer.prototype.writeFloatLE.call(new FB(), 0, 0, true);

@TimothyGu
Copy link
Member

You are right. I'm not sure how performance-heavy it would be to check for validity in all the write*() functions, though it does look necessary.

@TimothyGu TimothyGu added the security Issues and PRs related to security. label Apr 3, 2017
@DemiMarie
Copy link

@TimothyGu I think the real solution is to work with the V8 team to make these V8 compiler intrinsics. Then the JIT could eliminate the overhead.

If only V8 had a LuaJIT-style integrated FFI...

@Trott
Copy link
Member

Trott commented Aug 6, 2017

Dropping noAssert support entirely (that is, always treating noAssert as if it is false) would fix this, right?

@TimothyGu
Copy link
Member

Accidentally closed it... reopening

@TimothyGu TimothyGu reopened this Aug 7, 2017
BridgeAR added a commit to BridgeAR/node that referenced this issue Mar 2, 2018
This ports the Buffer#write(Double|Float)(B|L)E functions to JS.
This fixes a security issue concerning type confusion and fixes
another possible crash in combination with `noAssert`.
In addition to that it will also significantly improve the write
performance.

Fixes: nodejs#12179
Fixes: nodejs#8724
MayaLekova pushed a commit to MayaLekova/node that referenced this issue May 8, 2018
This ports the Buffer#write(Double|Float)(B|L)E functions to JS.
This fixes a security issue concerning type confusion and fixes
another possible crash in combination with `noAssert`.
In addition to that it will also significantly improve the write
performance.

Fixes: nodejs#12179
Fixes: nodejs#8724

PR-URL: nodejs#18395
Reviewed-By: James M Snell <[email protected]>
Reviewed-By: Matteo Collina <[email protected]>
Reviewed-By: Anatoli Papirovski <[email protected]>
Reviewed-By: Ben Noordhuis <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
buffer Issues and PRs related to the buffer subsystem. c++ Issues and PRs that require attention from people who are familiar with C++. security Issues and PRs related to security.
Projects
None yet
Development

No branches or pull requests

6 participants