• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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_TS_HCR_LOWERING_H
17 #define ECMASCRIPT_COMPILER_TS_HCR_LOWERING_H
18 
19 #include "ecmascript/compiler/argument_accessor.h"
20 #include "ecmascript/compiler/builtins/builtins_call_signature.h"
21 #include "ecmascript/compiler/bytecode_circuit_builder.h"
22 #include "ecmascript/compiler/circuit_builder-inl.h"
23 #include "ecmascript/compiler/object_access_helper.h"
24 #include "ecmascript/compiler/pass_manager.h"
25 
26 namespace panda::ecmascript::kungfu {
27 class TSHCRLowering {
28 public:
TSHCRLowering(Circuit * circuit,PassContext * ctx,bool enableLog,bool enableTypeLog,const std::string & name)29     TSHCRLowering(Circuit *circuit, PassContext *ctx,
30                    bool enableLog, bool enableTypeLog,
31                    const std::string& name)
32         : circuit_(circuit),
33           acc_(circuit),
34           builder_(circuit, ctx->GetCompilerConfig()),
35           dependEntry_(circuit->GetDependRoot()),
36           tsManager_(ctx->GetTSManager()),
37           enableLog_(enableLog),
38           enableTypeLog_(enableTypeLog),
39           profiling_(ctx->GetCompilerConfig()->IsProfiling()),
40           verifyVTable_(ctx->GetCompilerConfig()->IsVerifyVTbale()),
41           traceBc_(ctx->GetCompilerConfig()->IsTraceBC()),
42           methodName_(name),
43           glue_(acc_.GetGlueFromArgList()),
44           argAcc_(circuit),
45           pgoTypeLog_(circuit),
46           noCheck_(ctx->GetEcmaVM()->GetJSOptions().IsCompilerNoCheck()),
47           thread_(ctx->GetEcmaVM()->GetJSThread()) {}
48 
49     ~TSHCRLowering() = default;
50 
51     bool RunTSHCRLowering();
52 
53 private:
IsLogEnabled()54     bool IsLogEnabled() const
55     {
56         return enableLog_;
57     }
58 
IsTypeLogEnabled()59     bool IsTypeLogEnabled() const
60     {
61         return enableTypeLog_;
62     }
63 
IsProfiling()64     bool IsProfiling() const
65     {
66         return profiling_;
67     }
68 
IsVerifyVTbale()69     bool IsVerifyVTbale() const
70     {
71         return verifyVTable_;
72     }
73 
IsTraceBC()74     bool IsTraceBC() const
75     {
76         return traceBc_;
77     }
78 
GetMethodName()79     const std::string& GetMethodName() const
80     {
81         return methodName_;
82     }
83 
84     void Lower(GateRef gate);
85     template<TypedBinOp Op>
86     void LowerTypedBinOp(GateRef gate);
87     void LowerTypedMod(GateRef gate);
88     void LowerTypedDiv(GateRef gate);
89     void LowerTypedStrictEq(GateRef gate);
90     void LowerTypedShl(GateRef gate);
91     void LowerTypedShr(GateRef gate);
92     void LowerTypedAshr(GateRef gate);
93     void LowerTypedAnd(GateRef gate);
94     void LowerTypedOr(GateRef gate);
95     void LowerTypedXor(GateRef gate);
96     void LowerTypedInc(GateRef gate);
97     void LowerTypedDec(GateRef gate);
98     void LowerTypeToNumeric(GateRef gate);
99     void LowerPrimitiveTypeToNumber(GateRef gate);
100     void LowerConditionJump(GateRef gate, bool flag);
101     void LowerTypedNeg(GateRef gate);
102     void LowerTypedNot(GateRef gate);
103 
104     void LowerTypedLdObjByName(GateRef gate);
105     void LowerTypedStObjByName(GateRef gate, bool isThis);
106     using AccessMode = ObjectAccessHelper::AccessMode;
107     void LowerNamedAccess(GateRef gate, GateRef receiver, AccessMode accessMode, JSTaggedValue key, GateRef value);
108     GateRef BuildNamedPropertyAccess(GateRef hir, ObjectAccessHelper accessHelper, PropertyLookupResult plr);
109     void BuildNamedPropertyAccessVerifier(GateRef gate, GateRef receiver, AccessMode mode, GateRef value);
110     bool TryLowerTypedLdObjByNameForArray(GateRef gate, GateType receiverType, JSTaggedValue key);
111     void LowerTypedLdArrayLength(GateRef gate);
112     void LowerTypedLdTypedArrayLength(GateRef gate);
113 
114     void LowerTypedLdObjByIndex(GateRef gate);
115     void LowerTypedStObjByIndex(GateRef gate);
116     void LowerTypedLdObjByValue(GateRef gate, bool isThis);
117     void LowerTypedStObjByValue(GateRef gate);
118     void LowerTypedIsTrueOrFalse(GateRef gate, bool flag);
119     void LowerTypedNewObjRange(GateRef gate);
120     void LowerTypedSuperCall(GateRef gate);
121 
122     void LowerTypedCallArg0(GateRef gate);
123     void LowerTypedCallArg1(GateRef gate);
124     void LowerTypedCallArg2(GateRef gate);
125     void LowerTypedCallArg3(GateRef gate);
126     void LowerTypedCallrange(GateRef gate);
127     void LowerTypedCallthis0(GateRef gate);
128     void LowerTypedCallthis1(GateRef gate);
129     void LowerTypedCallthis2(GateRef gate);
130     void LowerTypedCallthis3(GateRef gate);
131     void LowerTypedCallthisrange(GateRef gate);
132     void LowerTypedCall(GateRef gate, GateRef func, GateRef actualArgc, GateType funcType, uint32_t argc);
133     void LowerTypedThisCall(GateRef gate, GateRef func, GateRef actualArgc, uint32_t argc);
134     bool IsLoadVtable(GateRef func);
135     bool CanOptimizeAsFastCall(GateRef func);
136     void CheckCallTargetAndLowerCall(GateRef gate, GateRef func, GlobalTSTypeRef funcGt,
137         GateType funcType, const std::vector<GateRef> &args, const std::vector<GateRef> &argsFastCall);
138     void CheckCallTargetFromDefineFuncAndLowerCall(GateRef gate, GateRef func, GlobalTSTypeRef funcGt,
139         GateType funcType, const std::vector<GateRef> &args, const std::vector<GateRef> &argsFastCall, bool isNoGC);
140     void CheckThisCallTargetAndLowerCall(GateRef gate, GateRef func, GlobalTSTypeRef funcGt,
141         GateType funcType, const std::vector<GateRef> &args, const std::vector<GateRef> &argsFastCall);
142     void CheckCallThisCallTarget(GateRef gate, GateRef func, GlobalTSTypeRef funcGt,
143                                  GateType funcType, bool isNoGC);
144     void CheckFastCallThisCallTarget(GateRef gate, GateRef func, GlobalTSTypeRef funcGt,
145                                      GateType funcType, bool isNoGC);
146     void LowerFastCall(GateRef gate, GateRef func, const std::vector<GateRef> &argsFastCall, bool isNoGC);
147     void LowerCall(GateRef gate, GateRef func, const std::vector<GateRef> &args, bool isNoGC);
148     GateRef LoadJSArrayByIndex(GateRef receiver, GateRef propKey, ElementsKind kind);
149     GateRef LoadTypedArrayByIndex(GateRef receiver, GateRef propKey);
150     void StoreJSArrayByIndex(GateRef receiver, GateRef propKey, GateRef value, ElementsKind kind);
151     void StoreTypedArrayByIndex(GateRef receiver, GateRef propKey, GateRef value);
152 
153     // TypeTrusted means the type of gate is already PrimitiveTypeCheck-passed,
154     // or the gate is constant and no need to check.
155     bool IsTrustedType(GateRef gate) const;
156     bool HasNumberType(GateRef gate, GateRef value) const;
157     bool HasNumberType(GateRef gate, GateRef left, GateRef right) const;
158 
159     void AddBytecodeCount(EcmaOpcode op);
160     void DeleteBytecodeCount(EcmaOpcode op);
161     void AddHitBytecodeCount();
162 
163     template<TypedBinOp Op>
164     void SpeculateNumbers(GateRef gate);
165     template<TypedUnOp Op>
166     void SpeculateNumber(GateRef gate);
167     void SpeculateConditionJump(GateRef gate, bool flag);
168     void SpeculateCallBuiltin(GateRef gate, GateRef func, GateRef a0, BuiltinsStubCSigns::ID Op);
169     void SpeculateCallThis3Builtin(GateRef gate, BuiltinsStubCSigns::ID id);
170     BuiltinsStubCSigns::ID GetBuiltinId(BuiltinTypeId id, GateRef func);
171     void DeleteConstDataIfNoUser(GateRef gate);
172 
173     void AddProfiling(GateRef gate);
174 
Uncheck()175     bool Uncheck() const
176     {
177         return noCheck_;
178     }
179 
180     Circuit *circuit_ {nullptr};
181     GateAccessor acc_;
182     CircuitBuilder builder_;
183     GateRef dependEntry_ {Gate::InvalidGateRef};
184     TSManager *tsManager_ {nullptr};
185     bool enableLog_ {false};
186     bool enableTypeLog_ {false};
187     bool profiling_ {false};
188     bool verifyVTable_ {false};
189     bool traceBc_ {false};
190     size_t allJSBcCount_ {0};
191     size_t allNonTypedOpCount_ {0};
192     size_t hitTypedOpCount_ {0};
193     std::string methodName_;
194     GateRef glue_ {Circuit::NullGate()};
195     ArgumentAccessor argAcc_;
196     EcmaOpcode currentOp_ {static_cast<EcmaOpcode>(0xff)};
197     PGOTypeLogList pgoTypeLog_;
198     std::unordered_map<EcmaOpcode, uint32_t> bytecodeMap_;
199     std::unordered_map<EcmaOpcode, uint32_t> bytecodeHitTimeMap_;
200     bool noCheck_ {false};
201     const JSThread *thread_ {nullptr};
202 };
203 }  // panda::ecmascript::kungfu
204 #endif  // ECMASCRIPT_COMPILER_TS_HCR_LOWERING_H
205