!7584 Optimized UnsharedConstPool

Merge pull request !7584 from 许杰/unsharedconstpool
This commit is contained in:
openharmony_ci 2024-06-03 08:23:11 +00:00 committed by Gitee
commit 184c7a3df4
No known key found for this signature in database
GPG Key ID: 173E9B9CA92EEF8F
22 changed files with 228 additions and 175 deletions

View File

@ -45,7 +45,8 @@ enum class FrameArgIdx : uint8_t {
THIS_OBJECT,
ACTUAL_ARGC,
ACTUAL_ARGV,
CONST_POOL,
SHARED_CONST_POOL,
UNSHARED_CONST_POOL,
NUM_OF_ARGS,
};

View File

@ -417,7 +417,11 @@ void BytecodeCircuitBuilder::BuildFrameArgs()
args[idx++] = argAcc_.GetCommonArgGate(CommonArgIdx::THIS_OBJECT);
args[idx++] = argAcc_.GetCommonArgGate(CommonArgIdx::ACTUAL_ARGC);
args[idx++] = argAcc_.GetCommonArgGate(CommonArgIdx::ACTUAL_ARGV);
args[idx++] = GetCurrentConstpool(argAcc_.GetCommonArgGate(CommonArgIdx::FUNC));
GateRef sharedConstpool = Circuit::NullGate();
GateRef unSharedConstpool = Circuit::NullGate();
GetCurrentConstpool(argAcc_.GetCommonArgGate(CommonArgIdx::FUNC), sharedConstpool, unSharedConstpool);
args[idx++] = sharedConstpool;
args[idx++] = unSharedConstpool;
args[idx++] = GetPreFrameArgs();
GateRef frameArgs = circuit_->NewGate(metaData, args);
argAcc_.SetFrameArgs(frameArgs);

View File

@ -538,26 +538,31 @@ public:
return static_cast<int32_t>(indexAccessor.GetHeaderIndex());
}
GateRef GetCurrentConstpool(GateRef jsFunc) const
void GetCurrentConstpool(GateRef jsFunc, GateRef &sharedConstPool, GateRef &unSharedConstPool)
{
int32_t constpoolId = GetCurrentConstpoolId();
if (gateAcc_.GetOpCode(preFrameArgs_) == OpCode::CIRCUIT_ROOT) {
return circuit_->NewGate(circuit_->GetConstPool(constpoolId), MachineType::I64, {jsFunc},
sharedConstPool = circuit_->NewGate(circuit_->GetSharedConstPool(constpoolId), MachineType::I64, {jsFunc},
GateType::AnyType());
unSharedConstPool = circuit_->NewGate(circuit_->GetUnsharedConstPool(), MachineType::I64,
{sharedConstPool}, GateType::AnyType());
}
GateRef frameArgs = preFrameArgs_;
GateRef preConstpool = Circuit::NullGate();
GateRef preSharedConstPool = Circuit::NullGate();
GateRef preUnsharedConstPool = Circuit::NullGate();
int32_t preConstpoolId = 0;
while (gateAcc_.GetOpCode(frameArgs) != OpCode::CIRCUIT_ROOT) {
preConstpool = gateAcc_.GetValueIn(frameArgs, static_cast<size_t>(FrameArgIdx::CONST_POOL));
preConstpoolId = static_cast<int32_t>(gateAcc_.GetConstpoolId(preConstpool));
preSharedConstPool = gateAcc_.GetValueIn(frameArgs, static_cast<size_t>(FrameArgIdx::SHARED_CONST_POOL));
preUnsharedConstPool =
gateAcc_.GetValueIn(frameArgs, static_cast<size_t>(FrameArgIdx::UNSHARED_CONST_POOL));
preConstpoolId = static_cast<int32_t>(gateAcc_.GetConstpoolId(preSharedConstPool));
if (preConstpoolId == constpoolId) {
return preConstpool;
sharedConstPool = preSharedConstPool;
unSharedConstPool = preUnsharedConstPool;
break;
}
frameArgs = gateAcc_.GetFrameState(frameArgs);
}
return circuit_->NewGate(circuit_->GetConstPool(constpoolId), MachineType::I64, {jsFunc},
GateType::AnyType());
}
bool IsOSR() const

View File

@ -461,17 +461,6 @@ void CircuitBuilder::AppendFrameArgs(std::vector<GateRef> &args, GateRef hirGate
}
}
GateRef CircuitBuilder::GetUnsharedConstpool(GateRef constpool)
{
auto currentLabel = env_->GetCurrentLabel();
auto currentDepend = currentLabel->GetDepend();
auto newGate = GetCircuit()->NewGate(circuit_->GetUnsharedConstpool(), MachineType::I64,
{ currentDepend, constpool },
GateType::AnyType());
currentLabel->SetDepend(newGate);
return newGate;
}
GateRef CircuitBuilder::GetGlobalEnv()
{
auto currentLabel = env_->GetCurrentLabel();
@ -790,8 +779,9 @@ GateRef CircuitBuilder::CheckJSType(GateRef object, JSType jsType)
return ret;
}
GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, GateRef constPool, GateRef module,
GateRef index, ConstPoolType type)
GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, GateRef sharedConstPool,
GateRef unsharedConstPool, GateRef module, GateRef index,
ConstPoolType type)
{
Label entry(env_);
SubCfgEntry(&entry);
@ -808,7 +798,6 @@ GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, Ga
// Call runtime to create unshared constpool when current context's cache is hole in multi-thread.
DEFVALUE(cacheValue, env_, VariableType::JS_ANY(), Hole());
if (type == ConstPoolType::ARRAY_LITERAL || type == ConstPoolType::OBJECT_LITERAL) {
GateRef unsharedConstPool = GetUnsharedConstpoolFromGlue(glue, constPool);
BRANCH_CIR2(TaggedIsNotHole(unsharedConstPool), &unshareCpHit, &unshareCpMiss);
Bind(&unshareCpHit);
{
@ -816,7 +805,7 @@ GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, Ga
Jump(&unshareCpMiss);
}
} else {
cacheValue = GetValueFromTaggedArray(constPool, index);
cacheValue = GetValueFromTaggedArray(sharedConstPool, index);
Jump(&unshareCpMiss);
}
Bind(&unshareCpMiss);
@ -826,16 +815,16 @@ GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, Ga
{
if (type == ConstPoolType::STRING) {
result = CallRuntime(glue, RTSTUB_ID(GetStringFromCache), Gate::InvalidGateRef,
{ constPool, Int32ToTaggedInt(index) }, hirGate);
{ sharedConstPool, Int32ToTaggedInt(index) }, hirGate);
} else if (type == ConstPoolType::ARRAY_LITERAL) {
result = CallRuntime(glue, RTSTUB_ID(GetArrayLiteralFromCache), Gate::InvalidGateRef,
{ constPool, Int32ToTaggedInt(index), module }, hirGate);
{ sharedConstPool, Int32ToTaggedInt(index), module }, hirGate);
} else if (type == ConstPoolType::OBJECT_LITERAL) {
result = CallRuntime(glue, RTSTUB_ID(GetObjectLiteralFromCache), Gate::InvalidGateRef,
{ constPool, Int32ToTaggedInt(index), module }, hirGate);
{ sharedConstPool, Int32ToTaggedInt(index), module }, hirGate);
} else {
result = CallRuntime(glue, RTSTUB_ID(GetMethodFromCache), Gate::InvalidGateRef,
{ constPool, Int32ToTaggedInt(index) }, hirGate);
{ sharedConstPool, Int32ToTaggedInt(index) }, hirGate);
}
Jump(&exit);
}
@ -847,7 +836,7 @@ GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, Ga
Bind(&isAOTLiteralInfo);
{
result = CallRuntime(glue, RTSTUB_ID(GetMethodFromCache), Gate::InvalidGateRef,
{ constPool, Int32ToTaggedInt(index) }, hirGate);
{ sharedConstPool, Int32ToTaggedInt(index) }, hirGate);
Jump(&exit);
}
} else if (type == ConstPoolType::ARRAY_LITERAL) {
@ -856,7 +845,7 @@ GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, Ga
Bind(&isAOTLiteralInfo);
{
result = CallRuntime(glue, RTSTUB_ID(GetArrayLiteralFromCache), Gate::InvalidGateRef,
{ constPool, Int32ToTaggedInt(index), module }, hirGate);
{ sharedConstPool, Int32ToTaggedInt(index), module }, hirGate);
Jump(&exit);
}
} else if (type == ConstPoolType::OBJECT_LITERAL) {
@ -865,7 +854,7 @@ GateRef CircuitBuilder::GetObjectFromConstPool(GateRef glue, GateRef hirGate, Ga
Bind(&isAOTLiteralInfo);
{
result = CallRuntime(glue, RTSTUB_ID(GetObjectLiteralFromCache), Gate::InvalidGateRef,
{ constPool, Int32ToTaggedInt(index), module }, hirGate);
{ sharedConstPool, Int32ToTaggedInt(index), module }, hirGate);
Jump(&exit);
}
} else {
@ -928,9 +917,8 @@ GateRef CircuitBuilder::GetBaselineCodeAddr(GateRef baselineCode)
GateRef CircuitBuilder::GetHClassGateFromIndex(GateRef gate, int32_t index)
{
ArgumentAccessor argAcc(circuit_);
GateRef constPool = argAcc.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef unsharedConstpool = GetUnsharedConstpool(constPool);
return LoadHClassFromUnsharedConstpool(unsharedConstpool, index);
GateRef unsharedConstpool = argAcc.GetFrameArgsIn(gate, FrameArgIdx::UNSHARED_CONST_POOL);
return LoadHClassFromConstpool(unsharedConstpool, index);
}
GateRef Variable::AddPhiOperand(GateRef val)

View File

@ -277,15 +277,14 @@ public:
GateRef LoadBuiltinObject(size_t offset);
// Get
GateRef GetUnsharedConstpool(GateRef constpool);
GateRef GetConstPoolFromFunction(GateRef jsFunc);
GateRef GetUnsharedConstpoolFromGlue(GateRef glue, GateRef constpool);
GateRef GetUnsharedConstpoolIndex(GateRef constpool);
GateRef GetUnsharedConstpool(GateRef arrayAddr, GateRef index);
GateRef GetCodeAddr(GateRef jsFunc);
GateRef GetBaselineCodeAddr(GateRef baselineCode);
GateRef GetObjectFromConstPool(GateRef glue, GateRef hirGate, GateRef constPool, GateRef module, GateRef index,
ConstPoolType type);
GateRef GetObjectFromConstPool(GateRef glue, GateRef hirGate, GateRef shardConstPool, GateRef unsharedConstPool,
GateRef module, GateRef index, ConstPoolType type);
GateRef GetFunctionLexicalEnv(GateRef function);
GateRef GetGlobalEnv();
GateRef GetGlobalEnvObj(GateRef env, size_t index);
@ -641,7 +640,7 @@ public:
GateRef LoadMapSize(GateRef string);
GateRef LoadConstOffset(VariableType type, GateRef receiver, size_t offset,
MemoryOrder order = MemoryOrder::Default());
GateRef LoadHClassFromUnsharedConstpool(GateRef constpool, size_t index);
GateRef LoadHClassFromConstpool(GateRef constpool, size_t index);
GateRef TypedCall(GateRef hirGate, std::vector<GateRef> args, bool isNoGC);
GateRef TypedFastCall(GateRef hirGate, std::vector<GateRef> args, bool isNoGC);
inline void SetValueToTaggedArray(VariableType valType, GateRef glue, GateRef array, GateRef index, GateRef val);

View File

@ -1987,7 +1987,7 @@ bool GateAccessor::IsNoBarrier(GateRef gate) const
uint32_t GateAccessor::GetConstpoolId(GateRef gate) const
{
ASSERT(GetOpCode(gate) == OpCode::GET_CONSTPOOL);
ASSERT(GetOpCode(gate) == OpCode::GET_SHARED_CONSTPOOL);
Gate *gatePtr = circuit_->LoadGatePtr(gate);
return gatePtr->GetOneParameterMetaData()->GetValue();
}

View File

@ -33,7 +33,6 @@ GateRef LaterElimination::VisitGate(GateRef gate)
{
auto opcode = acc_.GetOpCode(gate);
switch (opcode) {
case OpCode::GET_UNSHARED_CONSTPOOL:
case OpCode::GET_GLOBAL_ENV:
case OpCode::GET_GLOBAL_ENV_OBJ:
case OpCode::GET_GLOBAL_ENV_OBJ_HCLASS:

View File

@ -920,11 +920,11 @@ GateRef CircuitBuilder::LoadConstOffset(VariableType type, GateRef receiver, siz
return ret;
}
GateRef CircuitBuilder::LoadHClassFromUnsharedConstpool(GateRef constpool, size_t index)
GateRef CircuitBuilder::LoadHClassFromConstpool(GateRef constpool, size_t index)
{
auto currentLabel = env_->GetCurrentLabel();
auto currentDepend = currentLabel->GetDepend();
auto ret = GetCircuit()->NewGate(circuit_->LoadHClassFromUnsharedConstpool(index), MachineType::I64,
auto ret = GetCircuit()->NewGate(circuit_->LoadHClassFromConstpool(index), MachineType::I64,
{ currentDepend, constpool }, GateType::AnyType());
currentLabel->SetDepend(ret);
return ret;
@ -1576,23 +1576,24 @@ GateRef CircuitBuilder::BooleanConstructorCheck(GateRef gate)
return ret;
}
GateRef CircuitBuilder::MonoLoadPropertyOnProto(GateRef receiver, GateRef plrGate, GateRef jsFunc, size_t hclassIndex)
GateRef CircuitBuilder::MonoLoadPropertyOnProto(GateRef receiver, GateRef plrGate, GateRef unsharedConstPool,
size_t hclassIndex)
{
auto currentLabel = env_->GetCurrentLabel();
auto currentControl = currentLabel->GetControl();
auto currentDepend = currentLabel->GetDepend();
auto frameState = acc_.FindNearestFrameState(currentDepend);
auto ret = GetCircuit()->NewGate(circuit_->MonoLoadPropertyOnProto(), MachineType::I64,
{ currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex), jsFunc,
frameState },
{ currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex),
unsharedConstPool, frameState },
GateType::AnyType());
currentLabel->SetControl(ret);
currentLabel->SetDepend(ret);
return ret;
}
GateRef CircuitBuilder::MonoCallGetterOnProto(GateRef gate, GateRef receiver, GateRef plrGate, GateRef jsFunc,
size_t hclassIndex)
GateRef CircuitBuilder::MonoCallGetterOnProto(GateRef gate, GateRef receiver, GateRef plrGate,
GateRef unsharedConstPool, size_t hclassIndex)
{
uint64_t pcOffset = acc_.TryGetPcOffset(gate);
ASSERT(pcOffset != 0);
@ -1601,8 +1602,8 @@ GateRef CircuitBuilder::MonoCallGetterOnProto(GateRef gate, GateRef receiver, Ga
auto currentControl = currentLabel->GetControl();
auto currentDepend = currentLabel->GetDepend();
auto frameState = acc_.FindNearestFrameState(currentDepend);
std::vector<GateRef> args = { currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex), jsFunc,
frameState };
std::vector<GateRef> args = { currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex),
unsharedConstPool, frameState };
auto callGate = GetCircuit()->NewGate(circuit_->MonoCallGetterOnProto(pcOffset),
MachineType::I64,
args.size(),
@ -1613,7 +1614,7 @@ GateRef CircuitBuilder::MonoCallGetterOnProto(GateRef gate, GateRef receiver, Ga
return callGate;
}
GateRef CircuitBuilder::MonoStorePropertyLookUpProto(GateRef receiver, GateRef plrGate, GateRef jsFunc,
GateRef CircuitBuilder::MonoStorePropertyLookUpProto(GateRef receiver, GateRef plrGate, GateRef unsharedConstPool,
size_t hclassIndex, GateRef value)
{
auto currentLabel = env_->GetCurrentLabel();
@ -1621,21 +1622,21 @@ GateRef CircuitBuilder::MonoStorePropertyLookUpProto(GateRef receiver, GateRef p
auto currentDepend = currentLabel->GetDepend();
auto frameState = acc_.FindNearestFrameState(currentDepend);
auto ret = GetCircuit()->NewGate(circuit_->MonoStorePropertyLookUpProto(false), MachineType::I64,
{ currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex), jsFunc, value, frameState},
{ currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex), unsharedConstPool, value, frameState},
GateType::AnyType());
currentLabel->SetControl(ret);
currentLabel->SetDepend(ret);
return ret;
}
GateRef CircuitBuilder::MonoStoreProperty(GateRef receiver, GateRef plrGate, GateRef jsFunc, size_t hclassIndex,
GateRef value, GateRef key)
GateRef CircuitBuilder::MonoStoreProperty(GateRef receiver, GateRef plrGate, GateRef unsharedConstPool,
size_t hclassIndex, GateRef value, GateRef key)
{
auto currentLabel = env_->GetCurrentLabel();
auto currentControl = currentLabel->GetControl();
auto currentDepend = currentLabel->GetDepend();
auto ret = GetCircuit()->NewGate(circuit_->MonoStoreProperty(false), MachineType::I64,
{ currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex), jsFunc, value, key },
{ currentControl, currentDepend, receiver, plrGate, Int32(hclassIndex), unsharedConstPool, value, key },
GateType::AnyType());
currentLabel->SetControl(ret);
currentLabel->SetDepend(ret);

View File

@ -31,9 +31,6 @@ GateRef MCRLowering::VisitGate(GateRef gate)
{
auto op = acc_.GetOpCode(gate);
switch (op) {
case OpCode::GET_UNSHARED_CONSTPOOL:
LowerGetUnsharedConstpool(gate);
break;
case OpCode::STATE_SPLIT:
DeleteStateSplit(gate);
break;
@ -56,7 +53,7 @@ GateRef MCRLowering::VisitGate(GateRef gate)
LowerLoadConstOffset(gate);
break;
case OpCode::LOAD_HCLASS_FROM_CONSTPOOL:
LowerLoadHClassFromUnsharedConstpool(gate);
LowerLoadHClassFromConstpool(gate);
break;
case OpCode::STORE_CONST_OFFSET:
LowerStoreConstOffset(gate);
@ -178,7 +175,7 @@ void MCRLowering::LowerLoadConstOffset(GateRef gate)
acc_.ReplaceGate(gate, Circuit::NullGate(), builder_.GetDepend(), result);
}
void MCRLowering::LowerLoadHClassFromUnsharedConstpool(GateRef gate)
void MCRLowering::LowerLoadHClassFromConstpool(GateRef gate)
{
Environment env(gate, circuit_, &builder_);
GateRef constpool = acc_.GetValueIn(gate, 0);
@ -294,18 +291,6 @@ void MCRLowering::LowerIsSpecificObjectType(GateRef gate)
acc_.ReplaceGate(gate, builder_.GetState(), builder_.GetDepend(), result);
}
void MCRLowering::LowerGetUnsharedConstpool(GateRef gate)
{
Environment env(gate, circuit_, &builder_);
GateRef constpool = acc_.GetValueIn(gate, 0); // 0: this object
GateRef newGate = builder_.GetUnsharedConstpoolFromGlue(glue_, constpool);
acc_.UpdateAllUses(gate, newGate);
// delete old gate
acc_.DeleteGate(gate);
}
void MCRLowering::DeleteStateSplit(GateRef gate)
{
auto depend = acc_.GetDep(gate);

View File

@ -48,7 +48,7 @@ private:
void LowerGetConstPool(GateRef gate);
void LowerGetUnsharedConstpool(GateRef gate);
void LowerLoadConstOffset(GateRef gate);
void LowerLoadHClassFromUnsharedConstpool(GateRef gate);
void LowerLoadHClassFromConstpool(GateRef gate);
void LowerStoreConstOffset(GateRef gate);
void LowerConvertHoleAsUndefined(GateRef gate);
void LowerCheckAndConvert(GateRef gate);

View File

@ -171,7 +171,7 @@ namespace panda::ecmascript::kungfu {
#define MCR_GATE_META_DATA_LIST_WITH_VALUE(V) \
V(LoadConstOffset, LOAD_CONST_OFFSET, GateFlags::NO_WRITE, 0, 1, 1) \
V(LoadHClassFromUnsharedConstpool, LOAD_HCLASS_FROM_CONSTPOOL, GateFlags::NO_WRITE, 0, 1, 1) \
V(LoadHClassFromConstpool, LOAD_HCLASS_FROM_CONSTPOOL, GateFlags::NO_WRITE, 0, 1, 1) \
V(StoreConstOffset, STORE_CONST_OFFSET, GateFlags::NONE_FLAG, 0, 1, 2) \
V(LoadElement, LOAD_ELEMENT, GateFlags::NO_WRITE, 1, 1, 2) \
V(StoreElement, STORE_ELEMENT, GateFlags::NONE_FLAG, 1, 1, 3) \

View File

@ -90,8 +90,8 @@ void NTypeHCRLowering::LowerCreateArrayWithBuffer(GateRef gate, GateRef glue)
uint32_t constPoolIndex = static_cast<uint32_t>(acc_.GetConstantValue(index));
ArgumentAccessor argAcc(circuit_);
GateRef frameState = GetFrameState(gate);
GateRef constpool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::CONST_POOL);
GateRef literialElements = LoadFromConstPool(constpool, elementIndex, ConstantPool::AOT_ARRAY_INFO_INDEX);
GateRef unsharedConstpool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::UNSHARED_CONST_POOL);
GateRef literialElements = LoadFromConstPool(unsharedConstpool, elementIndex, ConstantPool::AOT_ARRAY_INFO_INDEX);
uint32_t cpIdVal = static_cast<uint32_t>(acc_.GetConstantValue(cpId));
JSTaggedValue arr = GetArrayLiteralValue(cpIdVal, constPoolIndex);
if (arr.IsUndefined()) {
@ -178,12 +178,11 @@ void NTypeHCRLowering::LowerCreateArguments(GateRef gate, GateRef glue)
}
}
GateRef NTypeHCRLowering::LoadFromConstPool(GateRef constpool, size_t index, size_t valVecType)
GateRef NTypeHCRLowering::LoadFromConstPool(GateRef unsharedConstpool, size_t index, size_t valVecType)
{
GateRef constPool = builder_.GetUnsharedConstpool(constpool);
GateRef constPoolSize = builder_.GetLengthOfTaggedArray(constPool);
GateRef constPoolSize = builder_.GetLengthOfTaggedArray(unsharedConstpool);
GateRef valVecIndex = builder_.Int32Sub(constPoolSize, builder_.Int32(valVecType));
GateRef valVec = builder_.GetValueFromTaggedArray(constPool, valVecIndex);
GateRef valVec = builder_.GetValueFromTaggedArray(unsharedConstpool, valVecIndex);
return builder_.LoadFromTaggedArray(valVec, index);
}

View File

@ -51,7 +51,7 @@ private:
void LowerStoreModuleVar(GateRef gate, GateRef glue);
void LowerLdLocalModuleVar(GateRef gate);
GateRef LoadFromConstPool(GateRef constPool, size_t index, size_t valVecType);
GateRef LoadFromConstPool(GateRef unsharedConstPool, size_t index, size_t valVecType);
GateRef NewActualArgv(GateRef gate, GateRef glue);
GateRef NewJSArrayLiteral(GateRef glue, GateRef gate, GateRef elements, GateRef length, uint32_t hintLength = 0);
GateRef NewTaggedArray(size_t length, GateRef glue);

View File

@ -967,7 +967,7 @@ void NumberSpeculativeLowering::VisitLoadPropertyOnProto(GateRef gate)
GateRef receiver = acc_.GetValueIn(gate, 0);
GateRef propertyLookupResult = acc_.GetValueIn(gate, 1); // 1: propertyLookupResult
GateRef hclassIndex = acc_.GetValueIn(gate, 2); // 2: hclassIndex
GateRef constpool = acc_.GetValueIn(gate, 3); // 3: constpool
GateRef unsharedConstPool = acc_.GetValueIn(gate, 3); // 3: constpool
PropertyLookupResult plr(acc_.TryGetValue(propertyLookupResult));
GateRef result = Circuit::NullGate();
ASSERT(plr.IsLocal() || plr.IsFunction());
@ -975,8 +975,7 @@ void NumberSpeculativeLowering::VisitLoadPropertyOnProto(GateRef gate)
auto receiverHC = builder_.LoadConstOffset(VariableType::JS_POINTER(), receiver, TaggedObject::HCLASS_OFFSET);
auto prototype = builder_.LoadConstOffset(VariableType::JS_ANY(), receiverHC, JSHClass::PROTOTYPE_OFFSET);
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constpool);
auto holderHC = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool, acc_.GetConstantValue(hclassIndex));
auto holderHC = builder_.LoadHClassFromConstpool(unsharedConstPool, acc_.GetConstantValue(hclassIndex));
DEFVALUE(current, (&builder_), VariableType::JS_ANY(), prototype);
Label exit(&builder_);
Label loopHead(&builder_);

View File

@ -45,7 +45,7 @@ namespace panda::ecmascript::kungfu {
V(IfSuccess, IF_SUCCESS, GateFlags::CONTROL, 1, 0, 0) \
V(IfException, IF_EXCEPTION, GateFlags::CONTROL, 1, 1, 0) \
V(GetException, GET_EXCEPTION, GateFlags::NONE_FLAG, 1, 1, 0) \
V(GetUnsharedConstpool, GET_UNSHARED_CONSTPOOL, GateFlags::NO_WRITE, 0, 1, 1) \
V(GetUnsharedConstPool, GET_UNSHARED_CONSTPOOL, GateFlags::NO_WRITE, 0, 0, 1) \
V(GetGlobalEnv, GET_GLOBAL_ENV, GateFlags::NO_WRITE, 0, 1, 0) \
V(GetSuperConstructor, GET_SUPER_CONSTRUCTOR, GateFlags::NO_WRITE, 1, 1, 1) \
V(CheckSafePointAndStackOver, CHECK_SAFEPOINT_AND_STACKOVER, GateFlags::NO_WRITE, 1, 1, 0) \
@ -68,13 +68,13 @@ namespace panda::ecmascript::kungfu {
#define SHARE_GATE_META_DATA_LIST_WITH_VALUE(V) \
V(Constant, CONSTANT, GateFlags::NONE_FLAG, 0, 0, 0) \
V(FrameArgs, FRAME_ARGS, GateFlags::HAS_FRAME_STATE, 0, 0, 6) \
V(FrameArgs, FRAME_ARGS, GateFlags::HAS_FRAME_STATE, 0, 0, 7) \
V(FrameState, FRAME_STATE, GateFlags::HAS_FRAME_STATE, 0, 0, 2) \
V(IfBranch, IF_BRANCH, GateFlags::CONTROL, 1, 0, 1) \
V(RelocatableData, RELOCATABLE_DATA, GateFlags::NONE_FLAG, 0, 0, 0) \
V(SwitchBranch, SWITCH_BRANCH, GateFlags::CONTROL, 1, 0, 1) \
V(SwitchCase, SWITCH_CASE, GateFlags::CONTROL, 1, 0, 0) \
V(GetConstPool, GET_CONSTPOOL, GateFlags::NO_WRITE, 0, 0, 1)
V(GetSharedConstPool, GET_SHARED_CONSTPOOL, GateFlags::NO_WRITE, 0, 0, 1)
#define SHARE_GATE_OPCODE_LIST(V) \
V(CONSTSTRING)

View File

@ -83,14 +83,23 @@ void SlowPathLowering::CallRuntimeLowering()
case OpCode::LOOP_EXIT_VALUE:
DeleteLoopExitValue(gate);
break;
case OpCode::GET_CONSTPOOL:
LowerGetConstPool(gate);
case OpCode::GET_UNSHARED_CONSTPOOL:
unsharedCP_.emplace_back(gate);
break;
default:
break;
}
}
// Make sure all IRs are lowered before lowering the constpool. If constpool is not used in CIR, it will be replaced
// by undefined.
for (const auto &gate : unsharedCP_) {
GateRef sharedConstPool = acc_.GetValueIn(gate, 0);
ASSERT(acc_.GetOpCode(sharedConstPool) == OpCode::GET_SHARED_CONSTPOOL);
LowerGetUnsharedConstPool(gate);
LowerGetSharedConstPool(sharedConstPool);
}
if (IsLogEnabled()) {
LOG_COMPILER(INFO) << " ";
LOG_COMPILER(INFO) << "\033[34m" << "================="
@ -1187,7 +1196,7 @@ void SlowPathLowering::LowerThrowUndefinedIfHoleWithName(GateRef gate)
// 2: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 2);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef hole = acc_.GetValueIn(gate, 1);
Label successExit(&builder_);
Label exceptionExit(&builder_);
@ -1201,7 +1210,7 @@ void SlowPathLowering::LowerThrowUndefinedIfHoleWithName(GateRef gate)
builder_.Bind(&isHole);
{
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef obj = builder_.GetObjectFromConstPool(glue_, gate, constpool, module,
GateRef obj = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module,
builder_.ZExtInt16ToInt32(acc_.GetValueIn(gate, 0)),
ConstPoolType::STRING);
LowerCallRuntime(gate, RTSTUB_ID(ThrowUndefinedIfHole), {obj}, true);
@ -1586,11 +1595,12 @@ void SlowPathLowering::LowerCreateObjectWithBuffer(GateRef gate)
// 2: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 2);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef unsharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::UNSHARED_CONST_POOL);
GateRef index = acc_.GetValueIn(gate, 0);
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef obj = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, builder_.TruncInt64ToInt32(index),
ConstPoolType::OBJECT_LITERAL);
GateRef obj = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, unsharedConstPool, module,
builder_.TruncInt64ToInt32(index), ConstPoolType::OBJECT_LITERAL);
GateRef lexEnv = acc_.GetValueIn(gate, 1);
GateRef result = LowerCallRuntime(gate, RTSTUB_ID(CreateObjectHavingMethod), { obj, lexEnv }, true);
ReplaceHirWithValue(gate, result);
@ -1644,11 +1654,11 @@ void SlowPathLowering::LowerLdBigInt(GateRef gate)
// 1: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 1);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef numberBigInt = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId,
ConstPoolType::STRING);
GateRef numberBigInt = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module,
stringId, ConstPoolType::STRING);
GateRef result = LowerCallRuntime(gate, RTSTUB_ID(LdBigInt), {numberBigInt}, true);
ReplaceHirWithValue(gate, result);
}
@ -2112,10 +2122,11 @@ void SlowPathLowering::LowerCreateRegExpWithLiteral(GateRef gate)
// 2: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 2);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef pattern = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef pattern = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module,
stringId, ConstPoolType::STRING);
GateRef flags = acc_.GetValueIn(gate, 1);
GateRef newGate = LowerCallRuntime(gate, id, { pattern, builder_.ToTaggedInt(flags) }, true);
ReplaceHirWithValue(gate, newGate);
@ -2156,10 +2167,11 @@ void SlowPathLowering::LowerStOwnByName(GateRef gate)
// 3: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 3);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module,
stringId, ConstPoolType::STRING);
GateRef receiver = acc_.GetValueIn(gate, 1);
GateRef accValue = acc_.GetValueIn(gate, 2);
// we do not need to merge outValueGate, so using GateRef directly instead of using Variable
@ -2250,10 +2262,11 @@ void SlowPathLowering::LowerTryStGlobalByName(GateRef gate)
void SlowPathLowering::LowerStConstToGlobalRecord(GateRef gate, bool isConst)
{
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module,
stringId, ConstPoolType::STRING);
acc_.SetDep(gate, propKey);
// 2 : number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 2);
@ -2286,10 +2299,11 @@ void SlowPathLowering::LowerStOwnByNameWithNameSet(GateRef gate)
// 3: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 3);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module,
stringId, ConstPoolType::STRING);
GateRef receiver = acc_.GetValueIn(gate, 1);
GateRef accValue = acc_.GetValueIn(gate, 2);
Label successExit(&builder_);
@ -2419,10 +2433,11 @@ void SlowPathLowering::LowerLdSuperByName(GateRef gate)
// 2: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 2);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef prop = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef prop = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module, stringId,
ConstPoolType::STRING);
GateRef result =
LowerCallRuntime(gate, RTSTUB_ID(OptLdSuperByValue), {acc_.GetValueIn(gate, 1), prop, jsFunc}, true);
ReplaceHirWithValue(gate, result);
@ -2433,10 +2448,11 @@ void SlowPathLowering::LowerStSuperByName(GateRef gate)
// 3: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 3);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef prop = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef prop = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module, stringId,
ConstPoolType::STRING);
auto args2 = { acc_.GetValueIn(gate, 1), prop, acc_.GetValueIn(gate, 2), jsFunc };
GateRef result = LowerCallRuntime(gate, RTSTUB_ID(OptStSuperByValue), args2, true);
ReplaceHirWithValue(gate, result);
@ -2641,13 +2657,13 @@ void SlowPathLowering::LowerDefineClassWithBuffer(GateRef gate)
GateRef literalId = acc_.GetValueIn(gate, 1);
GateRef length = acc_.GetValueIn(gate, 2); // 2: second arg
GateRef lexicalEnv = acc_.GetValueIn(gate, 4); // 4: Get current env
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef module = builder_.GetModuleFromFunction(jsFunc);
Label isException(&builder_);
Label isNotException(&builder_);
GateRef result;
auto args = { proto, lexicalEnv, constpool,
auto args = { proto, lexicalEnv, sharedConstPool,
builder_.ToTaggedInt(methodId), builder_.ToTaggedInt(literalId), module,
builder_.ToTaggedInt(length)};
result = LowerCallRuntime(gate, RTSTUB_ID(CreateClassWithBuffer), args, true);
@ -2969,10 +2985,11 @@ void SlowPathLowering::LowerDefineMethod(GateRef gate)
// 4: number of value inputs
ASSERT(acc_.GetNumValueIn(gate) == 4);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef methodId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef module = builder_.GetModuleFromFunction(jsFunc);
auto method = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, methodId, ConstPoolType::METHOD);
auto method = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module, methodId,
ConstPoolType::METHOD);
GateRef length = acc_.GetValueIn(gate, 1);
GateRef env = acc_.GetValueIn(gate, 2); // 2: Get current env
GateRef homeObject = acc_.GetValueIn(gate, 3); // 3: second arg
@ -3588,11 +3605,12 @@ void SlowPathLowering::LowerDefineFieldByName(GateRef gate)
// 4: number of value inputs + acc
ASSERT(acc_.GetNumValueIn(gate) == 4);
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 1));
GateRef obj = acc_.GetValueIn(gate, 2);
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef propKey = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module,
stringId, ConstPoolType::STRING);
GateRef value = acc_.GetValueIn(gate, 3); // acc
GateRef newGate = LowerCallRuntime(gate, id, {obj, propKey, value}); // note that HClass may change
@ -3645,7 +3663,7 @@ void SlowPathLowering::LowerCreatePrivateProperty(GateRef gate)
GateRef count = acc_.GetValueIn(gate, 0);
GateRef literalId = acc_.GetValueIn(gate, 1);
GateRef lexicalEnv = acc_.GetValueIn(gate, 2);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef newGate = LowerCallRuntime(gate, id, {lexicalEnv,
@ -3678,7 +3696,7 @@ void SlowPathLowering::LowerDefineSendableClass(GateRef gate)
GateRef literalId = acc_.GetValueIn(gate, 1);
GateRef length = acc_.GetValueIn(gate, 2); // 2: second arg
GateRef proto = acc_.GetValueIn(gate, 3);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef module = builder_.GetModuleFromFunction(jsFunc);
auto args = { proto, constpool, builder_.ToTaggedInt(methodId), builder_.ToTaggedInt(literalId),
builder_.ToTaggedInt(length), module };
@ -3723,20 +3741,73 @@ void SlowPathLowering::LowerLdStr(GateRef gate)
{
GateRef stringId = builder_.TruncInt64ToInt32(acc_.GetValueIn(gate, 0));
GateRef jsFunc = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::FUNC);
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL);
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef res = builder_.GetObjectFromConstPool(glue_, gate, constpool, module, stringId, ConstPoolType::STRING);
GateRef res = builder_.GetObjectFromConstPool(glue_, gate, sharedConstPool, Circuit::NullGate(), module, stringId,
ConstPoolType::STRING);
ReplaceHirWithValue(gate, res);
}
void SlowPathLowering::LowerGetConstPool(GateRef gate)
void SlowPathLowering::LowerGetSharedConstPool(GateRef gate)
{
bool useConstPool = false;
auto uses = acc_.Uses(gate);
for (auto useIt = uses.begin(); useIt != uses.end(); useIt++) {
if (acc_.GetOpCode(*useIt) != OpCode::FRAME_ARGS) {
useConstPool = true;
break;
}
}
if (!useConstPool) {
acc_.UpdateAllUses(gate, builder_.Undefined());
acc_.DeleteGate(gate);
return;
}
GateRef jsFunc = acc_.GetValueIn(gate, 0);
GateRef methodOffset = builder_.IntPtr(JSFunctionBase::METHOD_OFFSET);
GateRef method = builder_.Load(VariableType::JS_POINTER(), jsFunc, methodOffset, acc_.GetDependRoot());
GateRef constpool = builder_.Load(VariableType::JS_ANY(), method, builder_.IntPtr(Method::CONSTANT_POOL_OFFSET),
method);
acc_.UpdateAllUses(gate, constpool);
GateRef sharedConstpool =
builder_.Load(VariableType::JS_ANY(), method, builder_.IntPtr(Method::CONSTANT_POOL_OFFSET), method);
acc_.UpdateAllUses(gate, sharedConstpool);
acc_.DeleteGate(gate);
}
void SlowPathLowering::LowerGetUnsharedConstPool(GateRef gate)
{
bool useConstPool = false;
auto uses = acc_.Uses(gate);
for (auto useIt = uses.begin(); useIt != uses.end(); useIt++) {
if (acc_.GetOpCode(*useIt) != OpCode::FRAME_ARGS) {
useConstPool = true;
break;
}
}
if (!useConstPool) {
acc_.UpdateAllUses(gate, builder_.Undefined());
acc_.DeleteGate(gate);
return;
}
GateRef sharedConstPool = acc_.GetValueIn(gate, 0);
GateRef constPoolSize = builder_.Load(VariableType::INT32(), sharedConstPool,
builder_.IntPtr(TaggedArray::LENGTH_OFFSET), sharedConstPool);
GateRef unshareIdx = builder_.Int32Sub(constPoolSize, builder_.Int32(ConstantPool::UNSHARED_CONSTPOOL_INDEX));
GateRef offset =
builder_.PtrMul(builder_.ZExtInt32ToPtr(unshareIdx), builder_.IntPtr(JSTaggedValue::TaggedTypeSize()));
GateRef dataOffset = builder_.PtrAdd(offset, builder_.IntPtr(TaggedArray::DATA_OFFSET));
GateRef index = builder_.Load(VariableType::JS_ANY(), sharedConstPool, dataOffset, constPoolSize);
GateRef unshareCpOffset = static_cast<int32_t>(JSThread::GlueData::GetUnSharedConstpoolsOffset(false));
GateRef unshareCpAddr =
builder_.Load(VariableType::NATIVE_POINTER(), glue_, builder_.IntPtr(unshareCpOffset), index);
GateRef unshareCpDataOffset =
builder_.PtrAdd(unshareCpAddr, builder_.PtrMul(builder_.IntPtr(JSTaggedValue::TaggedTypeSize()),
builder_.ZExtInt32ToPtr(builder_.TaggedGetInt(index))));
GateRef unsharedConstPool =
builder_.Load(VariableType::JS_ANY(), unshareCpDataOffset, builder_.IntPtr(0), unshareCpAddr);
acc_.UpdateAllUses(gate, unsharedConstPool);
// delete old gate
acc_.DeleteGate(gate);
}
} // namespace panda::ecmascript

View File

@ -333,7 +333,8 @@ private:
void DeleteLoopExit(GateRef gate);
void DeleteLoopExitValue(GateRef gate);
void LowerLdStr(GateRef gate);
void LowerGetConstPool(GateRef gate);
void LowerGetSharedConstPool(GateRef gate);
void LowerGetUnsharedConstPool(GateRef gate);
CompilationEnv *compilationEnv_;
const MethodLiteral *methodLiteral_ {nullptr};
@ -347,6 +348,7 @@ private:
bool stressDeopt_ {false};
std::string methodName_;
GateRef glue_ {Circuit::NullGate()};
CVector<GateRef> unsharedCP_;
};
} // panda::ecmascript::kungfu
#endif // ECMASCRIPT_COMPILER_SLOWPATH_LOWERING_H

View File

@ -6739,27 +6739,31 @@ GateRef StubBuilder::GetStringFromConstPool(GateRef glue, GateRef constpool, Gat
{
GateRef module = Circuit::NullGate();
GateRef hirGate = Circuit::NullGate();
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, module, index, ConstPoolType::STRING);
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, Circuit::NullGate(), module, index,
ConstPoolType::STRING);
}
GateRef StubBuilder::GetMethodFromConstPool(GateRef glue, GateRef constpool, GateRef index)
{
GateRef module = Circuit::NullGate();
GateRef hirGate = Circuit::NullGate();
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, module, index, ConstPoolType::METHOD);
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, Circuit::NullGate(), module, index,
ConstPoolType::METHOD);
}
GateRef StubBuilder::GetArrayLiteralFromConstPool(GateRef glue, GateRef constpool, GateRef index, GateRef module)
{
GateRef hirGate = Circuit::NullGate();
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, module, index,
GateRef unsharedConstPool = env_->GetBuilder()->GetUnsharedConstpoolFromGlue(glue, constpool);
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, unsharedConstPool, module, index,
ConstPoolType::ARRAY_LITERAL);
}
GateRef StubBuilder::GetObjectLiteralFromConstPool(GateRef glue, GateRef constpool, GateRef index, GateRef module)
{
GateRef hirGate = Circuit::NullGate();
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, module, index,
GateRef unsharedConstPool = env_->GetBuilder()->GetUnsharedConstpoolFromGlue(glue, constpool);
return env_->GetBuilder()->GetObjectFromConstPool(glue, hirGate, constpool, unsharedConstPool, module, index,
ConstPoolType::OBJECT_LITERAL);
}

View File

@ -336,13 +336,13 @@ GateRef TSInlineLowering::BuildAccessor(InlineTypeInfoAccessor &info)
int holderHCIndex = static_cast<int>(ptManager->GetHClassIndexByProfileType(holderType));
ASSERT(ptManager->QueryHClass(holderType.first, holderType.second).IsJSHClass());
ArgumentAccessor argAcc(circuit_);
GateRef constpool = argAcc.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef unsharedConstPool = argAcc.GetFrameArgsIn(gate, FrameArgIdx::UNSHARED_CONST_POOL);
auto currentLabel = env.GetCurrentLabel();
auto state = currentLabel->GetControl();
auto depend = currentLabel->GetDepend();
GateRef holder = circuit_->NewGate(circuit_->LookUpHolder(), MachineType::I64,
{ state, depend, receiver, builder_.Int32(holderHCIndex), constpool},
{ state, depend, receiver, builder_.Int32(holderHCIndex), unsharedConstPool},
GateType::AnyType());
if (info.IsCallGetter()) {
@ -542,9 +542,9 @@ void TSInlineLowering::InlineAccessorCheck(const InlineTypeInfoAccessor &info)
auto callDepend = currentLabel->GetDepend();
auto frameState = acc_.GetFrameState(gate);
ArgumentAccessor argAcc(circuit_);
GateRef constpool = argAcc.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef unsharedConstPool = argAcc.GetFrameArgsIn(gate, FrameArgIdx::UNSHARED_CONST_POOL);
GateRef ret = circuit_->NewGate(circuit_->PrototypeCheck(receiverHCIndex), MachineType::I1,
{callState, callDepend, constpool, frameState}, GateType::NJSValue());
{callState, callDepend, unsharedConstPool, frameState}, GateType::NJSValue());
acc_.ReplaceStateIn(gate, ret);
acc_.ReplaceDependIn(gate, ret);
}

View File

@ -508,12 +508,12 @@ void TypedBytecodeLowering::LowerTypedLdObjByName(GateRef gate)
builder_.ProtoChangeMarkerCheck(receiver, frameState);
PropertyLookupResult plr = tacc.GetAccessInfo(0).Plr();
GateRef plrGate = builder_.Int32(plr.GetData());
GateRef constpoool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef unsharedConstPoool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::UNSHARED_CONST_POOL);
size_t holderHClassIndex = static_cast<size_t>(tacc.GetAccessInfo(0).HClassIndex());
if (LIKELY(!plr.IsAccessor())) {
result = builder_.MonoLoadPropertyOnProto(receiver, plrGate, constpoool, holderHClassIndex);
result = builder_.MonoLoadPropertyOnProto(receiver, plrGate, unsharedConstPoool, holderHClassIndex);
} else {
result = builder_.MonoCallGetterOnProto(gate, receiver, plrGate, constpoool, holderHClassIndex);
result = builder_.MonoCallGetterOnProto(gate, receiver, plrGate, unsharedConstPoool, holderHClassIndex);
}
}
acc_.ReplaceHirAndDeleteIfException(gate, builder_.GetStateDepend(), *result);
@ -689,15 +689,17 @@ void TypedBytecodeLowering::LowerTypedStObjByName(GateRef gate)
builder_.ProtoChangeMarkerCheck(tacc.GetReceiver(), frameState);
PropertyLookupResult plr = tacc.GetAccessInfo(0).Plr();
GateRef plrGate = builder_.Int32(plr.GetData());
GateRef constpool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL);
GateRef unsharedConstPool = argAcc_.GetFrameArgsIn(gate, FrameArgIdx::UNSHARED_CONST_POOL);
size_t holderHClassIndex = static_cast<size_t>(tacc.GetAccessInfo(0).HClassIndex());
GateRef value = tacc.GetValue();
if (tacc.IsHolderEqNewHolder(0)) {
builder_.MonoStorePropertyLookUpProto(tacc.GetReceiver(), plrGate, constpool, holderHClassIndex, value);
builder_.MonoStorePropertyLookUpProto(tacc.GetReceiver(), plrGate, unsharedConstPool, holderHClassIndex,
value);
} else {
auto propKey = builder_.LoadObjectFromConstPool(argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL),
auto propKey =
builder_.LoadObjectFromConstPool(argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL),
tacc.GetKey());
builder_.MonoStoreProperty(tacc.GetReceiver(), plrGate, constpool, holderHClassIndex, value,
builder_.MonoStoreProperty(tacc.GetReceiver(), plrGate, unsharedConstPool, holderHClassIndex, value,
propKey);
}
} else if (tacc.IsReceiverEqHolder(0)) {
@ -754,7 +756,8 @@ void TypedBytecodeLowering::LowerTypedStObjByName(GateRef gate)
builder_.Branch(builder_.IsProtoTypeHClass(receiverHC), &isProto, &notProto,
BranchWeight::ONE_WEIGHT, BranchWeight::DEOPT_WEIGHT, "isProtoTypeHClass");
builder_.Bind(&isProto);
auto propKey = builder_.LoadObjectFromConstPool(argAcc_.GetFrameArgsIn(gate, FrameArgIdx::CONST_POOL),
auto propKey =
builder_.LoadObjectFromConstPool(argAcc_.GetFrameArgsIn(gate, FrameArgIdx::SHARED_CONST_POOL),
tacc.GetKey());
builder_.CallRuntime(glue_, RTSTUB_ID(UpdateAOTHClass), Gate::InvalidGateRef,
{ receiverHC, newHolderHC, propKey }, gate);

View File

@ -542,9 +542,8 @@ GateRef TypedHCRLowering::BuildCompareHClass(GateRef gate, GateRef frameState)
GateRef aotHCIndex = acc_.GetValueIn(gate, 1);
auto hclassIndex = acc_.GetConstantValue(aotHCIndex);
ArgumentAccessor argAcc(circuit_);
GateRef constpool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::CONST_POOL);
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constpool);
auto aotHCGate = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool, hclassIndex);
GateRef unsharedConstPool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::UNSHARED_CONST_POOL);
GateRef aotHCGate = LoadFromConstPool(unsharedConstPool, hclassIndex, ConstantPool::AOT_HCLASS_INFO_INDEX);
GateRef receiverHClass = builder_.LoadConstOffset(
VariableType::JS_POINTER(), receiver, TaggedObject::HCLASS_OFFSET);
return builder_.Equal(aotHCGate, receiverHClass, "checkHClass");
@ -764,12 +763,11 @@ void TypedHCRLowering::LowerPrimitiveToNumber(GateRef dst, GateRef src, ParamTyp
acc_.ReplaceGate(dst, builder_.GetState(), builder_.GetDepend(), *result);
}
GateRef TypedHCRLowering::LoadFromConstPool(GateRef constpool, size_t index, size_t valVecType)
GateRef TypedHCRLowering::LoadFromConstPool(GateRef unsharedConstPool, size_t index, size_t valVecType)
{
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constpool);
GateRef constPoolSize = builder_.GetLengthOfTaggedArray(unsharedConstpool);
GateRef constPoolSize = builder_.GetLengthOfTaggedArray(unsharedConstPool);
GateRef valVecIndex = builder_.Int32Sub(constPoolSize, builder_.Int32(valVecType));
GateRef valVec = builder_.GetValueFromTaggedArray(unsharedConstpool, valVecIndex);
GateRef valVec = builder_.GetValueFromTaggedArray(unsharedConstPool, valVecIndex);
return builder_.LoadFromTaggedArray(valVec, index);
}
@ -1462,12 +1460,12 @@ void TypedHCRLowering::LowerJSCallTargetTypeCheck(GateRef gate)
Environment env(gate, circuit_, &builder_);
ArgumentAccessor argAcc(circuit_);
GateRef frameState = GetFrameState(gate);
GateRef constpool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::SHARED_CONST_POOL);
auto func = acc_.GetValueIn(gate, 0);
auto methodIndex = acc_.GetValueIn(gate, 1);
builder_.HeapObjectCheck(func, frameState);
GateRef funcMethodTarget = builder_.GetMethodFromFunction(func);
GateRef methodTarget = builder_.GetValueFromTaggedArray(constpool, methodIndex);
GateRef methodTarget = builder_.GetValueFromTaggedArray(sharedConstPool, methodIndex);
GateRef check = builder_.Equal(funcMethodTarget, methodTarget);
builder_.DeoptCheck(check, frameState, DeoptType::NOTJSCALLTGT2);
acc_.ReplaceGate(gate, builder_.GetState(), builder_.GetDepend(), Circuit::NullGate());
@ -1478,12 +1476,12 @@ void TypedHCRLowering::LowerJSFastCallTargetTypeCheck(GateRef gate)
Environment env(gate, circuit_, &builder_);
ArgumentAccessor argAcc(circuit_);
GateRef frameState = GetFrameState(gate);
GateRef constpool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::CONST_POOL);
GateRef sharedConstPool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::SHARED_CONST_POOL);
auto func = acc_.GetValueIn(gate, 0);
auto methodIndex = acc_.GetValueIn(gate, 1);
builder_.HeapObjectCheck(func, frameState);
GateRef funcMethodTarget = builder_.GetMethodFromFunction(func);
GateRef methodTarget = builder_.GetValueFromTaggedArray(constpool, methodIndex);
GateRef methodTarget = builder_.GetValueFromTaggedArray(sharedConstPool, methodIndex);
GateRef check = builder_.Equal(funcMethodTarget, methodTarget);
builder_.DeoptCheck(check, frameState, DeoptType::NOTJSFASTCALLTGT1);
acc_.ReplaceGate(gate, builder_.GetState(), builder_.GetDepend(), Circuit::NullGate());
@ -1695,9 +1693,8 @@ void TypedHCRLowering::LowerLookupHolder(GateRef gate)
ASSERT(acc_.GetNumValueIn(gate) == 3); // 3: receiver, holderHC, jsFunc
GateRef receiver = acc_.GetValueIn(gate, 0);
GateRef holderHCIndex = acc_.GetValueIn(gate, 1);
GateRef constPool = acc_.GetValueIn(gate, 2); // 2: constpool
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constPool);
GateRef holderHC = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool,
GateRef unsharedConstPool = acc_.GetValueIn(gate, 2); // 2: constpool
GateRef holderHC = builder_.LoadHClassFromConstpool(unsharedConstPool,
acc_.GetConstantValue(holderHCIndex));
DEFVALUE(holder, (&builder_), VariableType::JS_ANY(), receiver);
Label loopHead(&builder_);
@ -1762,12 +1759,11 @@ void TypedHCRLowering::LowerLoadSetter(GateRef gate)
void TypedHCRLowering::LowerPrototypeCheck(GateRef gate)
{
Environment env(gate, circuit_, &builder_);
GateRef constPool = acc_.GetValueIn(gate, 0);
GateRef unsharedConstPool = acc_.GetValueIn(gate, 0);
GateRef frameState = acc_.GetFrameState(gate);
uint32_t hclassIndex = acc_.GetHClassIndex(gate);
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constPool);
auto expectedReceiverHC = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool, hclassIndex);
auto expectedReceiverHC = builder_.LoadHClassFromConstpool(unsharedConstPool, hclassIndex);
auto prototype = builder_.LoadConstOffset(VariableType::JS_ANY(), expectedReceiverHC, JSHClass::PROTOTYPE_OFFSET);
auto protoHClass = builder_.LoadHClass(prototype);
@ -2837,7 +2833,7 @@ void TypedHCRLowering::LowerMonoLoadPropertyOnProto(GateRef gate)
GateRef receiver = acc_.GetValueIn(gate, 0);
GateRef propertyLookupResult = acc_.GetValueIn(gate, 1); // 1: propertyLookupResult
GateRef hclassIndex = acc_.GetValueIn(gate, 2); // 2: hclassIndex
GateRef constPool = acc_.GetValueIn(gate, 3); // 3: constPool
GateRef unsharedConstPool = acc_.GetValueIn(gate, 3); // 3: constPool
PropertyLookupResult plr(acc_.TryGetValue(propertyLookupResult));
GateRef result = Circuit::NullGate();
ASSERT(plr.IsLocal() || plr.IsFunction());
@ -2846,8 +2842,7 @@ void TypedHCRLowering::LowerMonoLoadPropertyOnProto(GateRef gate)
auto prototype = builder_.LoadConstOffset(VariableType::JS_ANY(), receiverHC, JSHClass::PROTOTYPE_OFFSET);
// lookup from receiver for holder
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constPool);
auto holderHC = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool, acc_.GetConstantValue(hclassIndex));
auto holderHC = builder_.LoadHClassFromConstpool(unsharedConstPool, acc_.GetConstantValue(hclassIndex));
DEFVALUE(current, (&builder_), VariableType::JS_ANY(), prototype);
Label exit(&builder_);
Label loopHead(&builder_);
@ -2878,7 +2873,7 @@ void TypedHCRLowering::LowerMonoCallGetterOnProto(GateRef gate, GateRef glue)
GateRef receiver = acc_.GetValueIn(gate, 0);
GateRef propertyLookupResult = acc_.GetValueIn(gate, 1); // 1: propertyLookupResult
GateRef hclassIndex = acc_.GetValueIn(gate, 2); // 2: hclassIndex
GateRef constPool = acc_.GetValueIn(gate, 3); // 3: constPool
GateRef unsharedConstPool = acc_.GetValueIn(gate, 3); // 3: constPool
PropertyLookupResult plr(acc_.TryGetValue(propertyLookupResult));
GateRef accessor = Circuit::NullGate();
GateRef holder = Circuit::NullGate();
@ -2887,8 +2882,7 @@ void TypedHCRLowering::LowerMonoCallGetterOnProto(GateRef gate, GateRef glue)
auto prototype = builder_.LoadConstOffset(VariableType::JS_ANY(), receiverHC, JSHClass::PROTOTYPE_OFFSET);
// lookup from receiver for holder
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constPool);
auto holderHC = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool, acc_.GetConstantValue(hclassIndex));
auto holderHC = builder_.LoadHClassFromConstpool(unsharedConstPool, acc_.GetConstantValue(hclassIndex));
DEFVALUE(current, (&builder_), VariableType::JS_ANY(), prototype);
Label exitLoad(&builder_);
Label loopHead(&builder_);
@ -2970,7 +2964,7 @@ void TypedHCRLowering::LowerMonoStorePropertyLookUpProto(GateRef gate, GateRef g
GateRef receiver = acc_.GetValueIn(gate, 0);
GateRef propertyLookupResult = acc_.GetValueIn(gate, 1); // 1: propertyLookupResult
GateRef hclassIndex = acc_.GetValueIn(gate, 2); // 2: hclassIndex
GateRef constpool = acc_.GetValueIn(gate, 3); // 3: constpool
GateRef unsharedConstPool = acc_.GetValueIn(gate, 3); // 3: constpool
GateRef value = acc_.GetValueIn(gate, 4); // 4: value
PropertyLookupResult plr(acc_.TryGetValue(propertyLookupResult));
bool noBarrier = acc_.IsNoBarrier(gate);
@ -2978,8 +2972,7 @@ void TypedHCRLowering::LowerMonoStorePropertyLookUpProto(GateRef gate, GateRef g
auto receiverHC = builder_.LoadConstOffset(VariableType::JS_POINTER(), receiver, TaggedObject::HCLASS_OFFSET);
auto prototype = builder_.LoadConstOffset(VariableType::JS_ANY(), receiverHC, JSHClass::PROTOTYPE_OFFSET);
// lookup from receiver for holder
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constpool);
auto holderHC = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool, acc_.GetConstantValue(hclassIndex));
auto holderHC = builder_.LoadHClassFromConstpool(unsharedConstPool, acc_.GetConstantValue(hclassIndex));
DEFVALUE(current, (&builder_), VariableType::JS_ANY(), prototype);
Label exit(&builder_);
Label loopHead(&builder_);
@ -3037,7 +3030,7 @@ void TypedHCRLowering::LowerMonoStoreProperty(GateRef gate, GateRef glue)
GateRef receiver = acc_.GetValueIn(gate, 0);
GateRef propertyLookupResult = acc_.GetValueIn(gate, 1); // 1: propertyLookupResult
GateRef hclassIndex = acc_.GetValueIn(gate, 2); // 2: hclassIndex
GateRef constPool = acc_.GetValueIn(gate, 3); // 3: constPool
GateRef unsharedConstPool = acc_.GetValueIn(gate, 3); // 3: constPool
GateRef value = acc_.GetValueIn(gate, 4); // 4: value
GateRef key = acc_.GetValueIn(gate, 5); // 5: key
PropertyLookupResult plr(acc_.TryGetValue(propertyLookupResult));
@ -3048,8 +3041,7 @@ void TypedHCRLowering::LowerMonoStoreProperty(GateRef gate, GateRef glue)
Label exit(&builder_);
Label notProto(&builder_);
Label isProto(&builder_);
GateRef unsharedConstpool = builder_.GetUnsharedConstpool(constPool);
auto newHolderHC = builder_.LoadHClassFromUnsharedConstpool(unsharedConstpool, acc_.GetConstantValue(hclassIndex));
auto newHolderHC = builder_.LoadHClassFromConstpool(unsharedConstPool, acc_.GetConstantValue(hclassIndex));
builder_.StoreConstOffset(VariableType::JS_ANY(), newHolderHC, JSHClass::PROTOTYPE_OFFSET, prototype);
builder_.Branch(builder_.IsProtoTypeHClass(receiverHC), &isProto, &notProto,
BranchWeight::ONE_WEIGHT, BranchWeight::DEOPT_WEIGHT, "isProtoTypeHClass");
@ -3180,8 +3172,9 @@ void TypedHCRLowering::LowerTypedCreateObjWithBuffer(GateRef gate, GateRef glue)
GateRef frameState = acc_.GetFrameState(gate);
GateRef jsFunc = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::FUNC);
GateRef module = builder_.GetModuleFromFunction(jsFunc);
GateRef constpool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::CONST_POOL);
GateRef oldObj = builder_.GetObjectFromConstPool(glue, gate, constpool, module,
GateRef sharedConstpool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::SHARED_CONST_POOL);
GateRef unsharedConstPool = argAcc.GetFrameArgsIn(frameState, FrameArgIdx::UNSHARED_CONST_POOL);
GateRef oldObj = builder_.GetObjectFromConstPool(glue, gate, sharedConstpool, unsharedConstPool, module,
builder_.TruncInt64ToInt32(index), ConstPoolType::OBJECT_LITERAL);
GateRef hclass = builder_.LoadConstOffset(VariableType::JS_POINTER(), oldObj, JSObject::HCLASS_OFFSET);
GateRef emptyArray = builder_.GetGlobalConstantValue(ConstantIndex::EMPTY_ARRAY_OBJECT_INDEX);

View File

@ -259,7 +259,7 @@ private:
GateRef GetLengthFromSupers(GateRef supers);
GateRef GetValueFromSupers(GateRef supers, size_t index);
GateRef LoadFromTaggedArray(GateRef array, size_t index);
GateRef LoadFromConstPool(GateRef constpool, size_t index, size_t valVecType);
GateRef LoadFromConstPool(GateRef unsharedConstPool, size_t index, size_t valVecType);
GateRef LoadFromVTable(GateRef receiver, size_t index);
GateRef GetLengthFromString(GateRef gate);
GateRef LoadPropertyFromHolder(GateRef holder, PropertyLookupResult plr);