diff options
author | Jason Ginchereau <jasongin@microsoft.com> | 2017-07-18 20:22:35 -0700 |
---|---|---|
committer | Jason Ginchereau <jasongin@microsoft.com> | 2017-08-07 17:31:17 -0700 |
commit | af70c3b4781d8df928d183580b8075cd566ce0b5 (patch) | |
tree | e8aa823ca954220063269e47e35547de28e99c3c /src/node_api.cc | |
parent | a974753676536e239fbd937e6ffebb74c84d7cbb (diff) | |
download | android-node-v8-af70c3b4781d8df928d183580b8075cd566ce0b5.tar.gz android-node-v8-af70c3b4781d8df928d183580b8075cd566ce0b5.tar.bz2 android-node-v8-af70c3b4781d8df928d183580b8075cd566ce0b5.zip |
n-api: optimize number API performance
- Add separate APIs for creating different kinds of numbers,
because creating a V8 number value from an integer is faster
than creating one from a double.
- When getting number values, avoid getting the current context
because the context will not actually be used and is expensive
to obtain.
- When creating values, don't use v8::TryCatch (NAPI_PREAMBLE),
because these functions have no possibility of executing JS code.
Refs: https://github.com/nodejs/node/issues/14379
PR-URL: https://github.com/nodejs/node/pull/14573
Reviewed-By: Timothy Gu <timothygu99@gmail.com>
Reviewed-By: Anna Henningsen <anna@addaleax.net>
Reviewed-By: Colin Ihrig <cjihrig@gmail.com>
Diffstat (limited to 'src/node_api.cc')
-rw-r--r-- | src/node_api.cc | 131 |
1 files changed, 81 insertions, 50 deletions
diff --git a/src/node_api.cc b/src/node_api.cc index 6e9f9bbc07..32acced231 100644 --- a/src/node_api.cc +++ b/src/node_api.cc @@ -818,9 +818,7 @@ const char* error_messages[] = {nullptr, "The async work item was cancelled", "napi_escape_handle already called on scope"}; -static napi_status napi_clear_last_error(napi_env env) { - CHECK_ENV(env); - +static inline napi_status napi_clear_last_error(napi_env env) { env->last_error.error_code = napi_ok; // TODO(boingoing): Should this be a callback? @@ -829,13 +827,13 @@ static napi_status napi_clear_last_error(napi_env env) { return napi_ok; } -static napi_status napi_set_last_error(napi_env env, napi_status error_code, - uint32_t engine_error_code, - void* engine_reserved) { +static inline +napi_status napi_set_last_error(napi_env env, napi_status error_code, + uint32_t engine_error_code, + void* engine_reserved) { env->last_error.error_code = error_code; env->last_error.engine_error_code = engine_error_code; env->last_error.engine_reserved = engine_reserved; - return error_code; } @@ -1436,42 +1434,42 @@ napi_status napi_get_prototype(napi_env env, } napi_status napi_create_object(napi_env env, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); *result = v8impl::JsValueFromV8LocalValue( v8::Object::New(env->isolate)); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_create_array(napi_env env, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); *result = v8impl::JsValueFromV8LocalValue( v8::Array::New(env->isolate)); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_create_array_with_length(napi_env env, size_t length, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); *result = v8impl::JsValueFromV8LocalValue( v8::Array::New(env->isolate, length)); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_create_string_latin1(napi_env env, const char* str, size_t length, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); auto isolate = env->isolate; @@ -1483,28 +1481,28 @@ napi_status napi_create_string_latin1(napi_env env, CHECK_MAYBE_EMPTY(env, str_maybe, napi_generic_failure); *result = v8impl::JsValueFromV8LocalValue(str_maybe.ToLocalChecked()); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_create_string_utf8(napi_env env, const char* str, size_t length, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); v8::Local<v8::String> s; CHECK_NEW_FROM_UTF8_LEN(env, s, str, length); *result = v8impl::JsValueFromV8LocalValue(s); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_create_string_utf16(napi_env env, const char16_t* str, size_t length, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); auto isolate = env->isolate; @@ -1516,19 +1514,55 @@ napi_status napi_create_string_utf16(napi_env env, CHECK_MAYBE_EMPTY(env, str_maybe, napi_generic_failure); *result = v8impl::JsValueFromV8LocalValue(str_maybe.ToLocalChecked()); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } -napi_status napi_create_number(napi_env env, +napi_status napi_create_double(napi_env env, double value, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); *result = v8impl::JsValueFromV8LocalValue( v8::Number::New(env->isolate, value)); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); +} + +napi_status napi_create_int32(napi_env env, + int32_t value, + napi_value* result) { + CHECK_ENV(env); + CHECK_ARG(env, result); + + *result = v8impl::JsValueFromV8LocalValue( + v8::Integer::New(env->isolate, value)); + + return napi_clear_last_error(env); +} + +napi_status napi_create_uint32(napi_env env, + uint32_t value, + napi_value* result) { + CHECK_ENV(env); + CHECK_ARG(env, result); + + *result = v8impl::JsValueFromV8LocalValue( + v8::Integer::NewFromUnsigned(env->isolate, value)); + + return napi_clear_last_error(env); +} + +napi_status napi_create_int64(napi_env env, + int64_t value, + napi_value* result) { + CHECK_ENV(env); + CHECK_ARG(env, result); + + *result = v8impl::JsValueFromV8LocalValue( + v8::Number::New(env->isolate, static_cast<double>(value))); + + return napi_clear_last_error(env); } napi_status napi_get_boolean(napi_env env, bool value, napi_value* result) { @@ -1549,7 +1583,7 @@ napi_status napi_get_boolean(napi_env env, bool value, napi_value* result) { napi_status napi_create_symbol(napi_env env, napi_value description, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, result); v8::Isolate* isolate = env->isolate; @@ -1564,7 +1598,7 @@ napi_status napi_create_symbol(napi_env env, v8::Symbol::New(isolate, desc.As<v8::String>())); } - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } static napi_status set_error_code(napi_env env, @@ -1624,7 +1658,7 @@ napi_status napi_create_error(napi_env env, napi_value code, napi_value msg, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, msg); CHECK_ARG(env, result); @@ -1638,14 +1672,14 @@ napi_status napi_create_error(napi_env env, *result = v8impl::JsValueFromV8LocalValue(error_obj); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_create_type_error(napi_env env, napi_value code, napi_value msg, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, msg); CHECK_ARG(env, result); @@ -1659,14 +1693,14 @@ napi_status napi_create_type_error(napi_env env, *result = v8impl::JsValueFromV8LocalValue(error_obj); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_create_range_error(napi_env env, napi_value code, napi_value msg, napi_value* result) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, msg); CHECK_ARG(env, result); @@ -1680,7 +1714,7 @@ napi_status napi_create_range_error(napi_env env, *result = v8impl::JsValueFromV8LocalValue(error_obj); - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_typeof(napi_env env, @@ -1951,14 +1985,13 @@ napi_status napi_get_value_int32(napi_env env, if (val->IsInt32()) { *result = val.As<v8::Int32>()->Value(); - return napi_clear_last_error(env); - } - - RETURN_STATUS_IF_FALSE(env, val->IsNumber(), napi_number_expected); + } else { + RETURN_STATUS_IF_FALSE(env, val->IsNumber(), napi_number_expected); - v8::Isolate* isolate = env->isolate; - v8::Local<v8::Context> context = isolate->GetCurrentContext(); - *result = val->Int32Value(context).FromJust(); + // Empty context: https://github.com/nodejs/node/issues/14379 + v8::Local<v8::Context> context; + *result = val->Int32Value(context).FromJust(); + } return napi_clear_last_error(env); } @@ -1976,14 +2009,13 @@ napi_status napi_get_value_uint32(napi_env env, if (val->IsUint32()) { *result = val.As<v8::Uint32>()->Value(); - return napi_clear_last_error(env); - } - - RETURN_STATUS_IF_FALSE(env, val->IsNumber(), napi_number_expected); + } else { + RETURN_STATUS_IF_FALSE(env, val->IsNumber(), napi_number_expected); - v8::Isolate* isolate = env->isolate; - v8::Local<v8::Context> context = isolate->GetCurrentContext(); - *result = val->Uint32Value(context).FromJust(); + // Empty context: https://github.com/nodejs/node/issues/14379 + v8::Local<v8::Context> context; + *result = val->Uint32Value(context).FromJust(); + } return napi_clear_last_error(env); } @@ -2013,8 +2045,8 @@ napi_status napi_get_value_int64(napi_env env, if (std::isnan(doubleValue)) { *result = 0; } else { - v8::Isolate* isolate = env->isolate; - v8::Local<v8::Context> context = isolate->GetCurrentContext(); + // Empty context: https://github.com/nodejs/node/issues/14379 + v8::Local<v8::Context> context; *result = val->IntegerValue(context).FromJust(); } @@ -2793,11 +2825,10 @@ napi_status napi_get_buffer_info(napi_env env, napi_value value, void** data, size_t* length) { - NAPI_PREAMBLE(env); + CHECK_ENV(env); CHECK_ARG(env, value); - v8::Local<v8::Object> buffer = - v8impl::V8LocalValueFromJsValue(value).As<v8::Object>(); + v8::Local<v8::Value> buffer = v8impl::V8LocalValueFromJsValue(value); if (data != nullptr) { *data = node::Buffer::Data(buffer); @@ -2806,7 +2837,7 @@ napi_status napi_get_buffer_info(napi_env env, *length = node::Buffer::Length(buffer); } - return GET_RETURN_STATUS(env); + return napi_clear_last_error(env); } napi_status napi_is_arraybuffer(napi_env env, napi_value value, bool* result) { |