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_GATE_META_DATA_CACHE_H 17 #define ECMASCRIPT_COMPILER_GATE_META_DATA_CACHE_H 18 19 #include <string> 20 21 #include "ecmascript/compiler/bytecodes.h" 22 #include "ecmascript/compiler/type.h" 23 #include "ecmascript/mem/chunk.h" 24 #include "ecmascript/mem/chunk_containers.h" 25 26 #include "libpandabase/macros.h" 27 28 namespace panda::ecmascript::kungfu { 29 30 #define CACHED_VALUE_LIST(V) \ 31 V(1) \ 32 V(2) \ 33 V(3) \ 34 V(4) \ 35 V(5) \ 36 37 // cached ARG list 38 #define CACHED_ARG_LIST(V) \ 39 V(0) \ 40 V(1) \ 41 V(2) \ 42 V(3) \ 43 V(4) \ 44 V(5) \ 45 V(6) \ 46 V(7) \ 47 V(8) \ 48 V(9) \ 49 V(10) \ 50 51 struct GateMetaDataChache { 52 static constexpr size_t ONE_VALUE = 1; 53 static constexpr size_t TWO_VALUE = 2; 54 static constexpr size_t THREE_VALUE = 3; 55 static constexpr size_t FOUR_VALUE = 4; 56 static constexpr size_t FIVE_VALUE = 5; 57 58 #define DECLARE_CACHED_GATE_META(NAME, OP, R, S, D, V) \ 59 GateMetaData cached##NAME##_ { OpCode::OP, R, S, D, V }; 60 IMMUTABLE_META_DATA_CACHE_LIST(DECLARE_CACHED_GATE_META) 61 #undef DECLARE_CACHED_GATE_META 62 63 #define DECLARE_CACHED_VALUE_META(VALUE) \ 64 GateMetaData cachedMerge##VALUE##_ { OpCode::MERGE, GateFlags::CONTROL, VALUE, 0, 0 }; \ 65 GateMetaData cachedDependSelector##VALUE##_ { OpCode::DEPEND_SELECTOR, GateFlags::FIXED, 1, VALUE, 0 }; 66 CACHED_VALUE_LIST(DECLARE_CACHED_VALUE_META) 67 #undef DECLARE_CACHED_VALUE_META 68 69 #define DECLARE_CACHED_VALUE_META(VALUE) \ 70 OneParameterMetaData cachedArg##VALUE##_ { OpCode::ARG, GateFlags::HAS_ROOT, 0, 0, 0, VALUE }; 71 CACHED_ARG_LIST(DECLARE_CACHED_VALUE_META) 72 #undef DECLARE_CACHED_VALUE_META 73 74 #define DECLARE_CACHED_GATE_META(NAME, OP, R, S, D, V) \ 75 GateMetaData cached##NAME##1_{ OpCode::OP, R, S, D, ONE_VALUE }; \ 76 GateMetaData cached##NAME##2_{ OpCode::OP, R, S, D, TWO_VALUE }; \ 77 GateMetaData cached##NAME##3_{ OpCode::OP, R, S, D, THREE_VALUE }; \ 78 GateMetaData cached##NAME##4_{ OpCode::OP, R, S, D, FOUR_VALUE }; \ 79 GateMetaData cached##NAME##5_{ OpCode::OP, R, S, D, FIVE_VALUE }; 80 GATE_META_DATA_LIST_WITH_VALUE_IN(DECLARE_CACHED_GATE_META) 81 #undef DECLARE_CACHED_GATE_META 82 83 #define DECLARE_CACHED_GATE_META(NAME, OP, R, S, D, V) \ 84 OneParameterMetaData cached##NAME##1_{ OpCode::OP, R, S, D, V, ONE_VALUE }; \ 85 OneParameterMetaData cached##NAME##2_{ OpCode::OP, R, S, D, V, TWO_VALUE }; \ 86 OneParameterMetaData cached##NAME##3_{ OpCode::OP, R, S, D, V, THREE_VALUE }; \ 87 OneParameterMetaData cached##NAME##4_{ OpCode::OP, R, S, D, V, FOUR_VALUE }; \ 88 OneParameterMetaData cached##NAME##5_{ OpCode::OP, R, S, D, V, FIVE_VALUE }; 89 GATE_META_DATA_LIST_WITH_VALUE(DECLARE_CACHED_GATE_META) 90 #undef DECLARE_CACHED_GATE_META 91 }; 92 93 class GateMetaBuilder { 94 public: 95 #define DECLARE_GATE_META(NAME, OP, R, S, D, V) \ 96 const GateMetaData* NAME(); 97 IMMUTABLE_META_DATA_CACHE_LIST(DECLARE_GATE_META) 98 #undef DECLARE_GATE_META 99 100 #define DECLARE_GATE_META(NAME, OP, R, S, D, V) \ 101 const GateMetaData* NAME(size_t value); 102 GATE_META_DATA_LIST_WITH_SIZE(DECLARE_GATE_META) 103 #undef DECLARE_GATE_META 104 105 #define DECLARE_GATE_META(NAME, OP, R, S, D, V) \ 106 const GateMetaData* NAME(uint64_t value); 107 GATE_META_DATA_LIST_WITH_ONE_PARAMETER(DECLARE_GATE_META) 108 #undef DECLARE_GATE_META 109 110 #define DECLARE_GATE_META(NAME, OP, R, S, D, V) \ 111 const GateMetaData* NAME(uint64_t value, uint64_t pcOffset); 112 GATE_META_DATA_LIST_WITH_PC_OFFSET(DECLARE_GATE_META) 113 #undef DECLARE_GATE_META 114 115 #define DECLARE_GATE_META_FOR_CALL(NAME, OP, R, S, D, V) \ 116 const GateMetaData* NAME(uint64_t value, uint64_t pcOffset, bool noGC); 117 GATE_META_DATA_LIST_FOR_CALL(DECLARE_GATE_META_FOR_CALL) 118 #undef DECLARE_GATE_META_FOR_CALL 119 120 #define DECLARE_GATE_META(NAME, OP, R, S, D, V) \ 121 const GateMetaData* NAME(uint64_t pcOffset) const; 122 GATE_META_DATA_LIST_WITH_PC_OFFSET_FIXED_VALUE(DECLARE_GATE_META) 123 #undef DECLARE_GATE_META 124 125 #define DECLARE_GATE_META(NAME, OP, R, S, D, V) \ 126 const GateMetaData* NAME(bool value); 127 GATE_META_DATA_LIST_WITH_BOOL(DECLARE_GATE_META) 128 #undef DECLARE_GATE_META 129 130 #define DECLARE_GATE_META_WITH_BOOL_VALUE_IN(NAME, OP, R, S, D, V) \ 131 const GateMetaData* NAME(size_t value, bool flag); 132 GATE_META_DATA_LIST_WITH_BOOL_VALUE_IN(DECLARE_GATE_META_WITH_BOOL_VALUE_IN) 133 #undef DECLARE_GATE_META_WITH_BOOL_VALUE_IN 134 135 explicit GateMetaBuilder(Chunk* chunk); 136 JSBytecode(size_t valuesIn,EcmaOpcode opcode,uint32_t pcOffset,GateFlags flags)137 const GateMetaData* JSBytecode(size_t valuesIn, EcmaOpcode opcode, uint32_t pcOffset, GateFlags flags) 138 { 139 return new (chunk_) JSBytecodeMetaData(valuesIn, opcode, pcOffset, flags); 140 } 141 TypedBinaryOp(uint64_t value,TypedBinOp binOp,PGOSampleType type)142 const GateMetaData* TypedBinaryOp(uint64_t value, TypedBinOp binOp, PGOSampleType type) 143 { 144 return new (chunk_) TypedBinaryMetaData(value, binOp, type); 145 } 146 TypedCallTargetCheckOp(uint32_t numIns,uint64_t value,TypedCallTargetCheckOp checkOp)147 const GateMetaData* TypedCallTargetCheckOp(uint32_t numIns, uint64_t value, TypedCallTargetCheckOp checkOp) 148 { 149 return new (chunk_) TypedCallTargetCheckMetaData(numIns, value, checkOp); 150 } 151 Nop()152 const GateMetaData* Nop() 153 { 154 return &cachedNop_; 155 } 156 NewGateMetaData(const GateMetaData * other)157 GateMetaData* NewGateMetaData(const GateMetaData* other) 158 { 159 auto meta = new (chunk_) GateMetaData(other->opcode_, other->GetFlags(), 160 other->statesIn_, other->dependsIn_, other->valuesIn_); 161 meta->SetKind(GateMetaData::Kind::MUTABLE_WITH_SIZE); 162 return meta; 163 } 164 ConstString(const std::string & str)165 const GateMetaData* ConstString(const std::string &str) 166 { 167 return new (chunk_) StringMetaData(chunk_, str); 168 } 169 170 private: 171 const GateMetaDataChache cache_; 172 const GateMetaData cachedNop_ { OpCode::NOP, GateFlags::NONE_FLAG, 0, 0, 0 }; 173 Chunk* chunk_; 174 }; 175 } // namespace panda::ecmascript::kungfu 176 #endif // ECMASCRIPT_COMPILER_GATE_META_DATA_CACHE_H 177