1 /* 2 * Copyright (c) 2022 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_COMPILER_BUILTINS_STUB_H 17 #define ECMASCRIPT_COMPILER_BUILTINS_STUB_H 18 19 #include "ecmascript/base/config.h" 20 #include "ecmascript/compiler/builtins/builtins_call_signature.h" 21 #include "ecmascript/compiler/interpreter_stub.h" 22 #include "ecmascript/ecma_runtime_call_info.h" 23 #include "ecmascript/ecma_string.h" 24 25 namespace panda::ecmascript::kungfu { 26 class BuiltinsStubBuilder : public StubBuilder { 27 public: BuiltinsStubBuilder(StubBuilder * parent)28 explicit BuiltinsStubBuilder(StubBuilder *parent) 29 :StubBuilder(parent) {} BuiltinsStubBuilder(CallSignature * callSignature,Environment * env)30 BuiltinsStubBuilder(CallSignature *callSignature, Environment *env) 31 : StubBuilder(callSignature, env) {} 32 ~BuiltinsStubBuilder() = default; 33 NO_MOVE_SEMANTIC(BuiltinsStubBuilder); 34 NO_COPY_SEMANTIC(BuiltinsStubBuilder); 35 virtual void GenerateCircuit() = 0; 36 GetGlue(GateRef info)37 inline GateRef GetGlue(GateRef info) 38 { 39 return Load(VariableType::NATIVE_POINTER(), info, 40 IntPtr(EcmaRuntimeCallInfo::GetThreadOffset(GetEnvironment()->IsArch32Bit()))); 41 } 42 GetNumArgs(GateRef info)43 inline GateRef GetNumArgs(GateRef info) 44 { 45 return Load(VariableType::INT64(), info, 46 IntPtr(EcmaRuntimeCallInfo::GetNumArgsOffset(GetEnvironment()->IsArch32Bit()))); 47 } 48 GetFunction(GateRef info)49 inline GateRef GetFunction(GateRef info) 50 { 51 return Load(VariableType::JS_ANY(), info, 52 IntPtr(EcmaRuntimeCallInfo::GetStackArgsOffset(GetEnvironment()->IsArch32Bit()))); 53 } 54 GetNewTarget(GateRef info)55 inline GateRef GetNewTarget(GateRef info) 56 { 57 GateRef newTargetOffset = IntPtr(EcmaRuntimeCallInfo::GetNewTargetOffset(GetEnvironment()->IsArch32Bit())); 58 return Load(VariableType::JS_ANY(), info, newTargetOffset); 59 } 60 GetThis(GateRef info)61 inline GateRef GetThis(GateRef info) 62 { 63 GateRef thisOffset = IntPtr(EcmaRuntimeCallInfo::GetThisOffset(GetEnvironment()->IsArch32Bit())); 64 return Load(VariableType::JS_ANY(), info, thisOffset); 65 } 66 GetCallArg0()67 inline GateRef GetCallArg0() 68 { 69 return TaggedArgument(static_cast<size_t>(BuiltinsArgs::ARG0_OR_ARGV)); 70 } 71 GetCallArg1()72 inline GateRef GetCallArg1() 73 { 74 return TaggedArgument(static_cast<size_t>(BuiltinsArgs::ARG1)); 75 } 76 GetCallArg2()77 inline GateRef GetCallArg2() 78 { 79 return TaggedArgument(static_cast<size_t>(BuiltinsArgs::ARG2)); 80 } 81 GetArgv()82 inline GateRef GetArgv() 83 { 84 return PtrArgument(static_cast<size_t>(BuiltinsArgs::ARG0_OR_ARGV)); 85 } 86 87 // not check whether index is valid, if not sure, invoke GetArg GetArgNCheck(GateRef index)88 inline GateRef GetArgNCheck(GateRef index) 89 { 90 GateRef argv = GetArgv(); 91 return Load(VariableType::JS_ANY(), argv, PtrMul(index, IntPtr(JSTaggedValue::TaggedTypeSize()))); 92 } 93 94 GateRef GetArg(GateRef numArgs, GateRef index); 95 96 GateRef CallSlowPath(GateRef nativeCode, GateRef glue, GateRef thisValue, GateRef numArgs, GateRef func, 97 GateRef newTarget); 98 IsNumberYearMonthDay(GateRef year,GateRef month,GateRef day)99 inline GateRef IsNumberYearMonthDay(GateRef year, GateRef month, GateRef day) 100 { 101 GateRef condition = BoolAnd(TaggedIsNumber(year), TaggedIsNumber(month)); 102 return BoolAnd(condition, TaggedIsNumber(day)); 103 } 104 }; 105 106 #define DECLARE_BUILTINS_STUB_CLASS(name) \ 107 class name##StubBuilder : public BuiltinsStubBuilder { \ 108 public: \ 109 explicit name##StubBuilder(CallSignature *callSignature, Environment *env) \ 110 : BuiltinsStubBuilder(callSignature, env) {} \ 111 ~name##StubBuilder() = default; \ 112 NO_MOVE_SEMANTIC(name##StubBuilder); \ 113 NO_COPY_SEMANTIC(name##StubBuilder); \ 114 void GenerateCircuit() override; \ 115 \ 116 private: \ 117 void GenerateCircuitImpl(GateRef glue, GateRef nativeCode, GateRef func, GateRef newTarget, \ 118 GateRef thisValue, GateRef numArgs); \ 119 }; 120 BUILTINS_STUB_LIST(DECLARE_BUILTINS_STUB_CLASS) 121 #undef DECLARE_BUILTINS_STUB_CLASS 122 } // namespace panda::ecmascript::kungfu 123 #endif // ECMASCRIPT_COMPILER_BUILTINS_STUB_H 124