Skip to content

Commit

Permalink
napi: fix memory corruption vulnerability
Browse files Browse the repository at this point in the history
Fixes: https://hackerone.com/reports/784186
CVE-ID: CVE-2020-8174
PR-URL: nodejs-private/node-private#195
Reviewed-By: Anna Henningsen <[email protected]>
Reviewed-By: Gabriel Schulhof <[email protected]>
Reviewed-By: Michael Dawson <[email protected]>
Reviewed-By: Colin Ihrig <[email protected]>
Reviewed-By: Rich Trott <[email protected]>
  • Loading branch information
tniessen authored and targos committed Jun 2, 2020
1 parent 07a4d50 commit 290720d
Show file tree
Hide file tree
Showing 3 changed files with 31 additions and 3 deletions.
12 changes: 9 additions & 3 deletions src/js_native_api_v8.cc
Original file line number Diff line number Diff line change
Expand Up @@ -2177,7 +2177,7 @@ napi_status napi_get_value_string_latin1(napi_env env,
if (!buf) {
CHECK_ARG(env, result);
*result = val.As<v8::String>()->Length();
} else {
} else if (bufsize != 0) {
int copied =
val.As<v8::String>()->WriteOneByte(env->isolate,
reinterpret_cast<uint8_t*>(buf),
Expand All @@ -2189,6 +2189,8 @@ napi_status napi_get_value_string_latin1(napi_env env,
if (result != nullptr) {
*result = copied;
}
} else if (result != nullptr) {
*result = 0;
}

return napi_clear_last_error(env);
Expand Down Expand Up @@ -2216,7 +2218,7 @@ napi_status napi_get_value_string_utf8(napi_env env,
if (!buf) {
CHECK_ARG(env, result);
*result = val.As<v8::String>()->Utf8Length(env->isolate);
} else {
} else if (bufsize != 0) {
int copied = val.As<v8::String>()->WriteUtf8(
env->isolate,
buf,
Expand All @@ -2228,6 +2230,8 @@ napi_status napi_get_value_string_utf8(napi_env env,
if (result != nullptr) {
*result = copied;
}
} else if (result != nullptr) {
*result = 0;
}

return napi_clear_last_error(env);
Expand Down Expand Up @@ -2256,7 +2260,7 @@ napi_status napi_get_value_string_utf16(napi_env env,
CHECK_ARG(env, result);
// V8 assumes UTF-16 length is the same as the number of characters.
*result = val.As<v8::String>()->Length();
} else {
} else if (bufsize != 0) {
int copied = val.As<v8::String>()->Write(env->isolate,
reinterpret_cast<uint16_t*>(buf),
0,
Expand All @@ -2267,6 +2271,8 @@ napi_status napi_get_value_string_utf16(napi_env env,
if (result != nullptr) {
*result = copied;
}
} else if (result != nullptr) {
*result = 0;
}

return napi_clear_last_error(env);
Expand Down
2 changes: 2 additions & 0 deletions test/js-native-api/test_string/test.js
Original file line number Diff line number Diff line change
Expand Up @@ -81,3 +81,5 @@ assert.throws(() => {
assert.throws(() => {
test_string.TestLargeUtf16();
}, /^Error: Invalid argument$/);

test_string.TestMemoryCorruption(' '.repeat(64 * 1024));
20 changes: 20 additions & 0 deletions test/js-native-api/test_string/test_string.c
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
#include <limits.h> // INT_MAX
#include <string.h>
#include <js_native_api.h>
#include "../common.h"

Expand Down Expand Up @@ -244,6 +245,24 @@ static napi_value TestLargeUtf16(napi_env env, napi_callback_info info) {
return output;
}

static napi_value TestMemoryCorruption(napi_env env, napi_callback_info info) {
size_t argc = 1;
napi_value args[1];
NAPI_CALL(env, napi_get_cb_info(env, info, &argc, args, NULL, NULL));

NAPI_ASSERT(env, argc == 1, "Wrong number of arguments");

char buf[10] = { 0 };
NAPI_CALL(env, napi_get_value_string_utf8(env, args[0], buf, 0, NULL));

char zero[10] = { 0 };
if (memcmp(buf, zero, sizeof(buf)) != 0) {
NAPI_CALL(env, napi_throw_error(env, NULL, "Buffer overwritten"));
}

return NULL;
}

EXTERN_C_START
napi_value Init(napi_env env, napi_value exports) {
napi_property_descriptor properties[] = {
Expand All @@ -258,6 +277,7 @@ napi_value Init(napi_env env, napi_value exports) {
DECLARE_NAPI_PROPERTY("TestLargeUtf8", TestLargeUtf8),
DECLARE_NAPI_PROPERTY("TestLargeLatin1", TestLargeLatin1),
DECLARE_NAPI_PROPERTY("TestLargeUtf16", TestLargeUtf16),
DECLARE_NAPI_PROPERTY("TestMemoryCorruption", TestMemoryCorruption),
};

NAPI_CALL(env, napi_define_properties(
Expand Down

0 comments on commit 290720d

Please sign in to comment.