From 50f33e7037d142792855dfe0bcc947f0034d5603 Mon Sep 17 00:00:00 2001 From: Eduardo Speroni Date: Thu, 11 May 2023 12:30:41 -0300 Subject: [PATCH 1/3] feat: add node helpers for interacting with functions --- NativeScript/runtime/Helpers.h | 130 ++++++++++++++++ NativeScript/runtime/Helpers.mm | 257 ++++++++++++++++++++++++++++++++ 2 files changed, 387 insertions(+) diff --git a/NativeScript/runtime/Helpers.h b/NativeScript/runtime/Helpers.h index 55464dd7..576c173d 100644 --- a/NativeScript/runtime/Helpers.h +++ b/NativeScript/runtime/Helpers.h @@ -198,6 +198,136 @@ void Assert(bool condition, v8::Isolate* isolate = nullptr, std::string const &r void StopExecutionAndLogStackTrace(v8::Isolate* isolate); + + + +// Helpers from Node +inline v8::Local OneByteString(v8::Isolate* isolate, + const char* data, + int length) { + return v8::String::NewFromOneByte(isolate, + reinterpret_cast(data), + v8::NewStringType::kNormal, + length).ToLocalChecked(); +} +inline v8::Local OneByteString(v8::Isolate* isolate, + const signed char* data, + int length) { + return v8::String::NewFromOneByte(isolate, + reinterpret_cast(data), + v8::NewStringType::kNormal, + length).ToLocalChecked(); +} +inline v8::Local OneByteString(v8::Isolate* isolate, + const unsigned char* data, + int length) { + return v8::String::NewFromOneByte( + isolate, data, v8::NewStringType::kNormal, length) + .ToLocalChecked(); +} + +// Convenience wrapper around v8::String::NewFromOneByte(). +inline v8::Local OneByteString(v8::Isolate* isolate, + const char* data, + int length = -1); +// For the people that compile with -funsigned-char. +inline v8::Local OneByteString(v8::Isolate* isolate, + const signed char* data, + int length = -1); +inline v8::Local OneByteString(v8::Isolate* isolate, + const unsigned char* data, + int length = -1); + + + +v8::Local NewFunctionTemplate( + v8::Isolate* isolate, + v8::FunctionCallback callback, + v8::Local signature = v8::Local(), + v8::ConstructorBehavior behavior = v8::ConstructorBehavior::kAllow, + v8::SideEffectType side_effect = v8::SideEffectType::kHasSideEffect, + const v8::CFunction* c_function = nullptr); +// Convenience methods for NewFunctionTemplate(). +void SetMethod(v8::Local context, + v8::Local that, + const char* name, + v8::FunctionCallback callback); +// Similar to SetProtoMethod but without receiver signature checks. +void SetMethod(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback callback); +void SetFastMethod(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback slow_callback, + const v8::CFunction* c_function); +void SetFastMethod(v8::Local context, + v8::Local that, + const char* name, + v8::FunctionCallback slow_callback, + const v8::CFunction* c_function); +void SetFastMethodNoSideEffect(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback slow_callback, + const v8::CFunction* c_function); +void SetFastMethodNoSideEffect(v8::Local context, + v8::Local that, + const char* name, + v8::FunctionCallback slow_callback, + const v8::CFunction* c_function); +void SetProtoMethod(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback callback); +void SetInstanceMethod(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback callback); +// Safe variants denote the function has no side effects. +void SetMethodNoSideEffect(v8::Local context, + v8::Local that, + const char* name, + v8::FunctionCallback callback); +void SetProtoMethodNoSideEffect(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback callback); +void SetMethodNoSideEffect(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback callback); +enum class SetConstructorFunctionFlag { + NONE, + SET_CLASS_NAME, +}; +void SetConstructorFunction(v8::Local context, + v8::Local that, + const char* name, + v8::Local tmpl, + SetConstructorFunctionFlag flag = + SetConstructorFunctionFlag::SET_CLASS_NAME); +void SetConstructorFunction(v8::Local context, + v8::Local that, + v8::Local name, + v8::Local tmpl, + SetConstructorFunctionFlag flag = + SetConstructorFunctionFlag::SET_CLASS_NAME); +void SetConstructorFunction(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::Local tmpl, + SetConstructorFunctionFlag flag = + SetConstructorFunctionFlag::SET_CLASS_NAME); +void SetConstructorFunction(v8::Isolate* isolate, + v8::Local that, + v8::Local name, + v8::Local tmpl, + SetConstructorFunctionFlag flag = + SetConstructorFunctionFlag::SET_CLASS_NAME); + + } #endif /* Helpers_h */ diff --git a/NativeScript/runtime/Helpers.mm b/NativeScript/runtime/Helpers.mm index f98b005d..b08a25f7 100644 --- a/NativeScript/runtime/Helpers.mm +++ b/NativeScript/runtime/Helpers.mm @@ -679,3 +679,260 @@ void tns::StopExecutionAndLogStackTrace(v8::Isolate* isolate) { Assert(false, isolate); } + + +namespace tns { +Local NewFunctionTemplate( + v8::Isolate* isolate, + v8::FunctionCallback callback, + Local signature, + v8::ConstructorBehavior behavior, + v8::SideEffectType side_effect_type, + const v8::CFunction* c_function) { + return v8::FunctionTemplate::New(isolate, + callback, + Local(), + signature, + 0, + behavior, + side_effect_type, + c_function); +} +void SetMethod(Local context, + Local that, + const char* name, + v8::FunctionCallback callback) { + Isolate* isolate = context->GetIsolate(); + Local function = + NewFunctionTemplate(isolate, + callback, + Local(), + v8::ConstructorBehavior::kThrow, + v8::SideEffectType::kHasSideEffect) + ->GetFunction(context) + .ToLocalChecked(); + // kInternalized strings are created in the old space. + const v8::NewStringType type = v8::NewStringType::kInternalized; + Local name_string = + v8::String::NewFromUtf8(isolate, name, type).ToLocalChecked(); + that->Set(context, name_string, function).Check(); + function->SetName(name_string); // NODE_SET_METHOD() compatibility. +} +void SetMethod(v8::Isolate* isolate, + v8::Local that, + const char* name, + v8::FunctionCallback callback) { + Local t = + NewFunctionTemplate(isolate, + callback, + Local(), + v8::ConstructorBehavior::kThrow, + v8::SideEffectType::kHasSideEffect); + // kInternalized strings are created in the old space. + const v8::NewStringType type = v8::NewStringType::kInternalized; + Local name_string = + v8::String::NewFromUtf8(isolate, name, type).ToLocalChecked(); + that->Set(name_string, t); +} +void SetFastMethod(Isolate* isolate, + Local