1 /* 2 * Copyright (c) 2021 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef ECMASCRIPT_NAPI_JSNAPI_HELPER_H 17 #define ECMASCRIPT_NAPI_JSNAPI_HELPER_H 18 19 #include "ecmascript/ecma_runtime_call_info.h" 20 #include "ecmascript/js_handle.h" 21 #include "ecmascript/js_tagged_value.h" 22 #include "ecmascript/napi/include/jsnapi.h" 23 24 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 25 #define RETURN_VALUE_IF_ABRUPT(thread, value) \ 26 do { \ 27 if (thread->HasPendingException()) { \ 28 LOG_FULL(ERROR) << "occur exception need return"; \ 29 return value; \ 30 } \ 31 } while (false) 32 33 #if ECMASCRIPT_ENABLE_NAPI_SPECIAL_CHECK 34 #define LOG_IF_SPECIAL(handleValue, level) \ 35 do { \ 36 LOG_ECMA(DEBUG) << "Enable napi special check"; \ 37 if ((handleValue).GetTaggedValue().IsSpecial()) { \ 38 LOG_FULL(level) << "Special value " << (handleValue).GetTaggedType() << " checked!"; \ 39 } \ 40 } while (false) 41 #else 42 #define LOG_IF_SPECIAL(handleValue, level) static_cast<void>(0) 43 #endif 44 45 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 46 #define TYPED_ARRAY_ALL(V) \ 47 V(Int8Array) \ 48 V(Uint8Array) \ 49 V(Uint8ClampedArray) \ 50 V(Int16Array) \ 51 V(Uint16Array) \ 52 V(Int32Array) \ 53 V(Uint32Array) \ 54 V(Float32Array) \ 55 V(Float64Array) \ 56 V(BigInt64Array) \ 57 V(BigUint64Array) 58 59 // NOLINTNEXTLINE(cppcoreguidelines-macro-usage) 60 #define EXCEPTION_ERROR_ALL(V) \ 61 V(Error, ERROR) \ 62 V(RangeError, RANGE_ERROR) \ 63 V(SyntaxError, SYNTAX_ERROR) \ 64 V(ReferenceError, REFERENCE_ERROR) \ 65 V(TypeError, TYPE_ERROR) \ 66 V(AggregateError, AGGREGATE_ERROR) \ 67 V(EvalError, EVAL_ERROR) \ 68 V(OOMError, OOM_ERROR) 69 70 namespace panda { 71 using NativeFinalize = void (*)(EcmaVM *); 72 class JSNApiHelper { 73 public: 74 template<typename T> ToLocal(ecmascript::JSHandle<ecmascript::JSTaggedValue> from)75 static inline Local<T> ToLocal(ecmascript::JSHandle<ecmascript::JSTaggedValue> from) 76 { 77 return Local<T>(from.GetAddress()); 78 } 79 ToJSTaggedValue(JSValueRef * from)80 static inline ecmascript::JSTaggedValue ToJSTaggedValue(JSValueRef *from) 81 { 82 ASSERT(from != nullptr); 83 return *reinterpret_cast<ecmascript::JSTaggedValue *>(from); 84 } 85 ToJSHandle(Local<JSValueRef> from)86 static inline ecmascript::JSHandle<ecmascript::JSTaggedValue> ToJSHandle(Local<JSValueRef> from) 87 { 88 ASSERT(!from.IsEmpty()); 89 return ecmascript::JSHandle<ecmascript::JSTaggedValue>(reinterpret_cast<uintptr_t>(*from)); 90 } 91 ToJSHandle(JSValueRef * from)92 static inline ecmascript::JSHandle<ecmascript::JSTaggedValue> ToJSHandle(JSValueRef *from) 93 { 94 ASSERT(from != nullptr); 95 return ecmascript::JSHandle<ecmascript::JSTaggedValue>(reinterpret_cast<uintptr_t>(from)); 96 } 97 }; 98 99 class NativeReferenceHelper { 100 public: NativeReferenceHelper(EcmaVM * vm,Global<ObjectRef> obj,NativeFinalize callback)101 NativeReferenceHelper(EcmaVM *vm, Global<ObjectRef> obj, NativeFinalize callback) 102 : vm_(vm), obj_(obj), callback_(callback) {} ~NativeReferenceHelper()103 ~NativeReferenceHelper() 104 { 105 obj_.FreeGlobalHandleAddr(); 106 } FreeGlobalCallBack(void * ref)107 static void FreeGlobalCallBack(void* ref) 108 { 109 auto that = reinterpret_cast<NativeReferenceHelper*>(ref); 110 that->obj_.FreeGlobalHandleAddr(); 111 } 112 NativeFinalizeCallBack(void * ref)113 static void NativeFinalizeCallBack(void* ref) 114 { 115 auto that = reinterpret_cast<NativeReferenceHelper*>(ref); 116 if (that->callback_ != nullptr) { 117 that->callback_(that->vm_); 118 } 119 that->callback_ = nullptr; 120 } 121 SetWeakCallback()122 void SetWeakCallback() 123 { 124 obj_.SetWeakCallback(this, FreeGlobalCallBack, NativeFinalizeCallBack); 125 } 126 127 private: 128 EcmaVM *vm_; 129 Global<ObjectRef> obj_; 130 NativeFinalize callback_ = nullptr; 131 }; 132 133 class Callback { 134 public: 135 static ecmascript::JSTaggedValue RegisterCallback(ecmascript::EcmaRuntimeCallInfo *ecmaRuntimeCallInfo); 136 }; 137 } // namespace panda 138 #endif // ECMASCRIPT_NAPI_JSNAPI_HELPER_H 139