14514f5e3Sopenharmony_ci/*
24514f5e3Sopenharmony_ci * Copyright (c) 2024 Huawei Device Co., Ltd.
34514f5e3Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
44514f5e3Sopenharmony_ci * you may not use this file except in compliance with the License.
54514f5e3Sopenharmony_ci * You may obtain a copy of the License at
64514f5e3Sopenharmony_ci *
74514f5e3Sopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
84514f5e3Sopenharmony_ci *
94514f5e3Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
104514f5e3Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
114514f5e3Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
124514f5e3Sopenharmony_ci * See the License for the specific language governing permissions and
134514f5e3Sopenharmony_ci * limitations under the License.
144514f5e3Sopenharmony_ci */
154514f5e3Sopenharmony_ci#include "ecmascript/jit/jit_profiler.h"
164514f5e3Sopenharmony_ci
174514f5e3Sopenharmony_ci#include <chrono>
184514f5e3Sopenharmony_ci#include <cstdint>
194514f5e3Sopenharmony_ci#include <memory>
204514f5e3Sopenharmony_ci
214514f5e3Sopenharmony_ci#include "ecmascript/compiler/jit_compilation_env.h"
224514f5e3Sopenharmony_ci#include "ecmascript/compiler/pgo_type/pgo_type_manager.h"
234514f5e3Sopenharmony_ci#include "ecmascript/enum_conversion.h"
244514f5e3Sopenharmony_ci#include "ecmascript/interpreter/interpreter-inl.h"
254514f5e3Sopenharmony_ci
264514f5e3Sopenharmony_cinamespace panda::ecmascript {
274514f5e3Sopenharmony_ciusing namespace pgo;
284514f5e3Sopenharmony_ciJITProfiler::JITProfiler(EcmaVM *vm) : vm_(vm)
294514f5e3Sopenharmony_ci{
304514f5e3Sopenharmony_ci}
314514f5e3Sopenharmony_ci
324514f5e3Sopenharmony_civoid JITProfiler::ProfileBytecode(JSThread *thread, const JSHandle<ProfileTypeInfo> &profileTypeInfo,
334514f5e3Sopenharmony_ci                                  ProfileTypeInfo *rawProfileTypeInfo,
344514f5e3Sopenharmony_ci                                  EntityId methodId, ApEntityId abcId, const uint8_t *pcStart, uint32_t codeSize,
354514f5e3Sopenharmony_ci                                  [[maybe_unused]]const panda_file::File::Header *header, bool useRawProfileTypeInfo)
364514f5e3Sopenharmony_ci{
374514f5e3Sopenharmony_ci    Clear();
384514f5e3Sopenharmony_ci    if (useRawProfileTypeInfo) {
394514f5e3Sopenharmony_ci        profileTypeInfo_ = rawProfileTypeInfo;
404514f5e3Sopenharmony_ci    }
414514f5e3Sopenharmony_ci    abcId_ = abcId;
424514f5e3Sopenharmony_ci    methodId_ = methodId;
434514f5e3Sopenharmony_ci    BytecodeInstruction bcIns(pcStart);
444514f5e3Sopenharmony_ci    auto bcInsLast = bcIns.JumpTo(codeSize);
454514f5e3Sopenharmony_ci
464514f5e3Sopenharmony_ci    while (bcIns.GetAddress() != bcInsLast.GetAddress()) {
474514f5e3Sopenharmony_ci        auto opcode = bcIns.GetOpcode();
484514f5e3Sopenharmony_ci        auto bcOffset = bcIns.GetAddress() - pcStart;
494514f5e3Sopenharmony_ci        auto pc = bcIns.GetAddress();
504514f5e3Sopenharmony_ci        switch (opcode) {
514514f5e3Sopenharmony_ci            case EcmaOpcode::LDTHISBYNAME_IMM8_ID16:
524514f5e3Sopenharmony_ci            case EcmaOpcode::LDOBJBYNAME_IMM8_ID16: {
534514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
544514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
554514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
564514f5e3Sopenharmony_ci                }
574514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
584514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
594514f5e3Sopenharmony_ci                ConvertICByName(bcOffset, slotId, BCType::LOAD);
604514f5e3Sopenharmony_ci                break;
614514f5e3Sopenharmony_ci            }
624514f5e3Sopenharmony_ci            case EcmaOpcode::LDTHISBYNAME_IMM16_ID16:
634514f5e3Sopenharmony_ci            case EcmaOpcode::LDOBJBYNAME_IMM16_ID16: {
644514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
654514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
664514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
674514f5e3Sopenharmony_ci                }
684514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
694514f5e3Sopenharmony_ci                ConvertICByName(bcOffset, slotId, BCType::LOAD);
704514f5e3Sopenharmony_ci                break;
714514f5e3Sopenharmony_ci            }
724514f5e3Sopenharmony_ci            case EcmaOpcode::LDOBJBYVALUE_IMM8_V8:
734514f5e3Sopenharmony_ci            case EcmaOpcode::LDTHISBYVALUE_IMM8: {
744514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
754514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
764514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
774514f5e3Sopenharmony_ci                }
784514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
794514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
804514f5e3Sopenharmony_ci                ConvertICByValue(bcOffset, slotId, BCType::LOAD);
814514f5e3Sopenharmony_ci                break;
824514f5e3Sopenharmony_ci            }
834514f5e3Sopenharmony_ci            case EcmaOpcode::LDOBJBYVALUE_IMM16_V8:
844514f5e3Sopenharmony_ci            case EcmaOpcode::LDTHISBYVALUE_IMM16: {
854514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
864514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
874514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
884514f5e3Sopenharmony_ci                }
894514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
904514f5e3Sopenharmony_ci                ConvertICByValue(bcOffset, slotId, BCType::LOAD);
914514f5e3Sopenharmony_ci                break;
924514f5e3Sopenharmony_ci            }
934514f5e3Sopenharmony_ci            case EcmaOpcode::STOBJBYNAME_IMM8_ID16_V8:
944514f5e3Sopenharmony_ci            case EcmaOpcode::STTHISBYNAME_IMM8_ID16:
954514f5e3Sopenharmony_ci            case EcmaOpcode::DEFINEPROPERTYBYNAME_IMM8_ID16_V8:
964514f5e3Sopenharmony_ci            case EcmaOpcode::STPRIVATEPROPERTY_IMM8_IMM16_IMM16_V8: {
974514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
984514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
994514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
1004514f5e3Sopenharmony_ci                }
1014514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
1024514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
1034514f5e3Sopenharmony_ci                ConvertICByName(bcOffset, slotId, BCType::STORE);
1044514f5e3Sopenharmony_ci                break;
1054514f5e3Sopenharmony_ci            }
1064514f5e3Sopenharmony_ci            case EcmaOpcode::STOBJBYNAME_IMM16_ID16_V8:
1074514f5e3Sopenharmony_ci            case EcmaOpcode::STTHISBYNAME_IMM16_ID16: {
1084514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
1094514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
1104514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
1114514f5e3Sopenharmony_ci                }
1124514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
1134514f5e3Sopenharmony_ci                ConvertICByName(bcOffset, slotId, BCType::STORE);
1144514f5e3Sopenharmony_ci                break;
1154514f5e3Sopenharmony_ci            }
1164514f5e3Sopenharmony_ci            case EcmaOpcode::STOBJBYVALUE_IMM8_V8_V8:
1174514f5e3Sopenharmony_ci            case EcmaOpcode::STOWNBYINDEX_IMM8_V8_IMM16:
1184514f5e3Sopenharmony_ci            case EcmaOpcode::STTHISBYVALUE_IMM8_V8: {
1194514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
1204514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
1214514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
1224514f5e3Sopenharmony_ci                }
1234514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
1244514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
1254514f5e3Sopenharmony_ci                ConvertICByValue(bcOffset, slotId, BCType::STORE);
1264514f5e3Sopenharmony_ci                break;
1274514f5e3Sopenharmony_ci            }
1284514f5e3Sopenharmony_ci            case EcmaOpcode::STOBJBYVALUE_IMM16_V8_V8:
1294514f5e3Sopenharmony_ci            case EcmaOpcode::STOWNBYINDEX_IMM16_V8_IMM16:
1304514f5e3Sopenharmony_ci            case EcmaOpcode::STTHISBYVALUE_IMM16_V8: {
1314514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
1324514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
1334514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
1344514f5e3Sopenharmony_ci                }
1354514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
1364514f5e3Sopenharmony_ci                ConvertICByValue(bcOffset, slotId, BCType::STORE);
1374514f5e3Sopenharmony_ci                break;
1384514f5e3Sopenharmony_ci            }
1394514f5e3Sopenharmony_ci            // Op
1404514f5e3Sopenharmony_ci            case EcmaOpcode::ADD2_IMM8_V8:
1414514f5e3Sopenharmony_ci            case EcmaOpcode::SUB2_IMM8_V8:
1424514f5e3Sopenharmony_ci            case EcmaOpcode::MUL2_IMM8_V8:
1434514f5e3Sopenharmony_ci            case EcmaOpcode::DIV2_IMM8_V8:
1444514f5e3Sopenharmony_ci            case EcmaOpcode::MOD2_IMM8_V8:
1454514f5e3Sopenharmony_ci            case EcmaOpcode::SHL2_IMM8_V8:
1464514f5e3Sopenharmony_ci            case EcmaOpcode::SHR2_IMM8_V8:
1474514f5e3Sopenharmony_ci            case EcmaOpcode::AND2_IMM8_V8:
1484514f5e3Sopenharmony_ci            case EcmaOpcode::OR2_IMM8_V8:
1494514f5e3Sopenharmony_ci            case EcmaOpcode::XOR2_IMM8_V8:
1504514f5e3Sopenharmony_ci            case EcmaOpcode::ASHR2_IMM8_V8:
1514514f5e3Sopenharmony_ci            case EcmaOpcode::EXP_IMM8_V8:
1524514f5e3Sopenharmony_ci            case EcmaOpcode::NEG_IMM8:
1534514f5e3Sopenharmony_ci            case EcmaOpcode::NOT_IMM8:
1544514f5e3Sopenharmony_ci            case EcmaOpcode::INC_IMM8:
1554514f5e3Sopenharmony_ci            case EcmaOpcode::DEC_IMM8:
1564514f5e3Sopenharmony_ci            case EcmaOpcode::EQ_IMM8_V8:
1574514f5e3Sopenharmony_ci            case EcmaOpcode::NOTEQ_IMM8_V8:
1584514f5e3Sopenharmony_ci            case EcmaOpcode::LESS_IMM8_V8:
1594514f5e3Sopenharmony_ci            case EcmaOpcode::LESSEQ_IMM8_V8:
1604514f5e3Sopenharmony_ci            case EcmaOpcode::GREATER_IMM8_V8:
1614514f5e3Sopenharmony_ci            case EcmaOpcode::GREATEREQ_IMM8_V8:
1624514f5e3Sopenharmony_ci            case EcmaOpcode::STRICTNOTEQ_IMM8_V8:
1634514f5e3Sopenharmony_ci            case EcmaOpcode::STRICTEQ_IMM8_V8:
1644514f5e3Sopenharmony_ci            case EcmaOpcode::TONUMERIC_IMM8: {
1654514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
1664514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
1674514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
1684514f5e3Sopenharmony_ci                }
1694514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
1704514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
1714514f5e3Sopenharmony_ci                ConvertOpType(slotId, bcOffset);
1724514f5e3Sopenharmony_ci                break;
1734514f5e3Sopenharmony_ci            }
1744514f5e3Sopenharmony_ci            // Call
1754514f5e3Sopenharmony_ci            case EcmaOpcode::CALLARG0_IMM8:
1764514f5e3Sopenharmony_ci            case EcmaOpcode::CALLARG1_IMM8_V8:
1774514f5e3Sopenharmony_ci            case EcmaOpcode::CALLARGS2_IMM8_V8_V8:
1784514f5e3Sopenharmony_ci            case EcmaOpcode::CALLARGS3_IMM8_V8_V8_V8:
1794514f5e3Sopenharmony_ci            case EcmaOpcode::CALLRANGE_IMM8_IMM8_V8:
1804514f5e3Sopenharmony_ci            case EcmaOpcode::CALLTHIS0_IMM8_V8:
1814514f5e3Sopenharmony_ci            case EcmaOpcode::CALLTHIS1_IMM8_V8_V8:
1824514f5e3Sopenharmony_ci            case EcmaOpcode::CALLTHIS2_IMM8_V8_V8_V8:
1834514f5e3Sopenharmony_ci            case EcmaOpcode::CALLTHIS3_IMM8_V8_V8_V8_V8:
1844514f5e3Sopenharmony_ci            case EcmaOpcode::CALLTHISRANGE_IMM8_IMM8_V8: {
1854514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
1864514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
1874514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
1884514f5e3Sopenharmony_ci                }
1894514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
1904514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
1914514f5e3Sopenharmony_ci                ConvertCall(slotId, bcOffset);
1924514f5e3Sopenharmony_ci                break;
1934514f5e3Sopenharmony_ci            }
1944514f5e3Sopenharmony_ci            case EcmaOpcode::CALLRUNTIME_CALLINIT_PREF_IMM8_V8: {
1954514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
1964514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
1974514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
1984514f5e3Sopenharmony_ci                }
1994514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_1();
2004514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
2014514f5e3Sopenharmony_ci                ConvertCall(slotId, bcOffset);
2024514f5e3Sopenharmony_ci                break;
2034514f5e3Sopenharmony_ci            }
2044514f5e3Sopenharmony_ci            case EcmaOpcode::WIDE_CALLRANGE_PREF_IMM16_V8:
2054514f5e3Sopenharmony_ci            case EcmaOpcode::WIDE_CALLTHISRANGE_PREF_IMM16_V8: {
2064514f5e3Sopenharmony_ci                // no ic slot
2074514f5e3Sopenharmony_ci                break;
2084514f5e3Sopenharmony_ci            }
2094514f5e3Sopenharmony_ci            case EcmaOpcode::NEWOBJRANGE_IMM8_IMM8_V8: {
2104514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
2114514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
2124514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
2134514f5e3Sopenharmony_ci                }
2144514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
2154514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
2164514f5e3Sopenharmony_ci                ConvertNewObjRange(slotId, bcOffset);
2174514f5e3Sopenharmony_ci                break;
2184514f5e3Sopenharmony_ci            }
2194514f5e3Sopenharmony_ci            case EcmaOpcode::NEWOBJRANGE_IMM16_IMM8_V8: {
2204514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
2214514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
2224514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
2234514f5e3Sopenharmony_ci                }
2244514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
2254514f5e3Sopenharmony_ci                ConvertNewObjRange(slotId, bcOffset);
2264514f5e3Sopenharmony_ci                break;
2274514f5e3Sopenharmony_ci            }
2284514f5e3Sopenharmony_ci            case EcmaOpcode::WIDE_NEWOBJRANGE_PREF_IMM16_V8: {
2294514f5e3Sopenharmony_ci                break;
2304514f5e3Sopenharmony_ci            }
2314514f5e3Sopenharmony_ci            // Create object
2324514f5e3Sopenharmony_ci            case EcmaOpcode::DEFINECLASSWITHBUFFER_IMM8_ID16_ID16_IMM16_V8: {
2334514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
2344514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
2354514f5e3Sopenharmony_ci                (void) slotId;
2364514f5e3Sopenharmony_ci                break;
2374514f5e3Sopenharmony_ci            }
2384514f5e3Sopenharmony_ci            case EcmaOpcode::DEFINECLASSWITHBUFFER_IMM16_ID16_ID16_IMM16_V8: {
2394514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
2404514f5e3Sopenharmony_ci                (void) slotId;
2414514f5e3Sopenharmony_ci                break;
2424514f5e3Sopenharmony_ci            }
2434514f5e3Sopenharmony_ci            case EcmaOpcode::DEFINEFUNC_IMM8_ID16_IMM8: {
2444514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
2454514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
2464514f5e3Sopenharmony_ci                break;
2474514f5e3Sopenharmony_ci            }
2484514f5e3Sopenharmony_ci            case EcmaOpcode::DEFINEFUNC_IMM16_ID16_IMM8: {
2494514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
2504514f5e3Sopenharmony_ci                (void) slotId;
2514514f5e3Sopenharmony_ci                break;
2524514f5e3Sopenharmony_ci            }
2534514f5e3Sopenharmony_ci            case EcmaOpcode::CREATEOBJECTWITHBUFFER_IMM8_ID16:
2544514f5e3Sopenharmony_ci            case EcmaOpcode::CREATEARRAYWITHBUFFER_IMM8_ID16:
2554514f5e3Sopenharmony_ci            case EcmaOpcode::CREATEEMPTYARRAY_IMM8: {
2564514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
2574514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
2584514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
2594514f5e3Sopenharmony_ci                }
2604514f5e3Sopenharmony_ci                auto traceId =
2614514f5e3Sopenharmony_ci                    static_cast<int32_t>(reinterpret_cast<uintptr_t>(pc) - reinterpret_cast<uintptr_t>(header));
2624514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
2634514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
2644514f5e3Sopenharmony_ci                ConvertCreateObject(slotId, bcOffset, traceId);
2654514f5e3Sopenharmony_ci                break;
2664514f5e3Sopenharmony_ci            }
2674514f5e3Sopenharmony_ci            case EcmaOpcode::CREATEOBJECTWITHBUFFER_IMM16_ID16:
2684514f5e3Sopenharmony_ci            case EcmaOpcode::CREATEARRAYWITHBUFFER_IMM16_ID16:
2694514f5e3Sopenharmony_ci            case EcmaOpcode::CREATEEMPTYARRAY_IMM16: {
2704514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
2714514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
2724514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
2734514f5e3Sopenharmony_ci                }
2744514f5e3Sopenharmony_ci                auto traceId =
2754514f5e3Sopenharmony_ci                    static_cast<int32_t>(reinterpret_cast<uintptr_t>(pc) - reinterpret_cast<uintptr_t>(header));
2764514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
2774514f5e3Sopenharmony_ci                ConvertCreateObject(slotId, bcOffset, traceId);
2784514f5e3Sopenharmony_ci                break;
2794514f5e3Sopenharmony_ci            }
2804514f5e3Sopenharmony_ci            case EcmaOpcode::GETITERATOR_IMM8: {
2814514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
2824514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
2834514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
2844514f5e3Sopenharmony_ci                }
2854514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
2864514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
2874514f5e3Sopenharmony_ci                ConvertGetIterator(slotId, bcOffset);
2884514f5e3Sopenharmony_ci                break;
2894514f5e3Sopenharmony_ci            }
2904514f5e3Sopenharmony_ci            case EcmaOpcode::GETITERATOR_IMM16: {
2914514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
2924514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
2934514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
2944514f5e3Sopenharmony_ci                }
2954514f5e3Sopenharmony_ci                uint16_t slotId = READ_INST_16_0();
2964514f5e3Sopenharmony_ci                ConvertGetIterator(slotId, bcOffset);
2974514f5e3Sopenharmony_ci                break;
2984514f5e3Sopenharmony_ci            }
2994514f5e3Sopenharmony_ci            // Others
3004514f5e3Sopenharmony_ci            case EcmaOpcode::INSTANCEOF_IMM8_V8: {
3014514f5e3Sopenharmony_ci                Jit::JitLockHolder lock(thread);
3024514f5e3Sopenharmony_ci                if (!useRawProfileTypeInfo) {
3034514f5e3Sopenharmony_ci                    profileTypeInfo_ = *profileTypeInfo;
3044514f5e3Sopenharmony_ci                }
3054514f5e3Sopenharmony_ci                uint8_t slotId = READ_INST_8_0();
3064514f5e3Sopenharmony_ci                CHECK_SLOTID_BREAK(slotId);
3074514f5e3Sopenharmony_ci                ConvertInstanceof(bcOffset, slotId);
3084514f5e3Sopenharmony_ci                break;
3094514f5e3Sopenharmony_ci            }
3104514f5e3Sopenharmony_ci            case EcmaOpcode::DEFINEGETTERSETTERBYVALUE_V8_V8_V8_V8:
3114514f5e3Sopenharmony_ci            default:
3124514f5e3Sopenharmony_ci                break;
3134514f5e3Sopenharmony_ci        }
3144514f5e3Sopenharmony_ci        bcIns = bcIns.GetNext();
3154514f5e3Sopenharmony_ci    }
3164514f5e3Sopenharmony_ci}
3174514f5e3Sopenharmony_ci
3184514f5e3Sopenharmony_ci// PGOSampleType
3194514f5e3Sopenharmony_civoid JITProfiler::ConvertOpType(uint32_t slotId, long bcOffset)
3204514f5e3Sopenharmony_ci{
3214514f5e3Sopenharmony_ci    JSTaggedValue slotValue = profileTypeInfo_->Get(slotId);
3224514f5e3Sopenharmony_ci    if (slotValue.IsInt()) {
3234514f5e3Sopenharmony_ci        auto type = slotValue.GetInt();
3244514f5e3Sopenharmony_ci        UpdatePGOType(bcOffset, chunk_->New<PGOSampleType>(type));
3254514f5e3Sopenharmony_ci    }
3264514f5e3Sopenharmony_ci}
3274514f5e3Sopenharmony_ci
3284514f5e3Sopenharmony_civoid JITProfiler::ConvertCall(uint32_t slotId, long bcOffset)
3294514f5e3Sopenharmony_ci{
3304514f5e3Sopenharmony_ci    JSTaggedValue slotValue = profileTypeInfo_->Get(slotId);
3314514f5e3Sopenharmony_ci    ProfileType::Kind kind;
3324514f5e3Sopenharmony_ci    int calleeMethodId = 0;
3334514f5e3Sopenharmony_ci    ApEntityId calleeAbcId = 0;
3344514f5e3Sopenharmony_ci    if (slotValue.IsInt()) {
3354514f5e3Sopenharmony_ci        calleeMethodId = slotValue.GetInt();
3364514f5e3Sopenharmony_ci        if (calleeMethodId == 0) {
3374514f5e3Sopenharmony_ci            return;
3384514f5e3Sopenharmony_ci        }
3394514f5e3Sopenharmony_ci        calleeAbcId = abcId_;
3404514f5e3Sopenharmony_ci        ASSERT(calleeMethodId <= 0);
3414514f5e3Sopenharmony_ci        kind = ProfileType::Kind::BuiltinFunctionId;
3424514f5e3Sopenharmony_ci    }  else if (slotValue.IsJSFunction()) {
3434514f5e3Sopenharmony_ci        JSFunction *callee = JSFunction::Cast(slotValue);
3444514f5e3Sopenharmony_ci        Method *calleeMethod = Method::Cast(callee->GetMethod());
3454514f5e3Sopenharmony_ci        calleeMethodId = static_cast<int>(calleeMethod->GetMethodId().GetOffset());
3464514f5e3Sopenharmony_ci        calleeAbcId = PGOProfiler::GetMethodAbcId(callee);
3474514f5e3Sopenharmony_ci        static_cast<JitCompilationEnv *>(compilationEnv_)
3484514f5e3Sopenharmony_ci            ->UpdateFuncSlotIdMap(calleeMethodId, methodId_.GetOffset(), slotId);
3494514f5e3Sopenharmony_ci        kind = ProfileType::Kind::MethodId;
3504514f5e3Sopenharmony_ci    } else {
3514514f5e3Sopenharmony_ci        return;
3524514f5e3Sopenharmony_ci    }
3534514f5e3Sopenharmony_ci    PGOSampleType* type = chunk_->New<PGOSampleType>(ProfileType(abcId_, std::abs(calleeMethodId), kind));
3544514f5e3Sopenharmony_ci    UpdatePGOType(bcOffset, type);
3554514f5e3Sopenharmony_ci}
3564514f5e3Sopenharmony_ci
3574514f5e3Sopenharmony_civoid JITProfiler::ConvertNewObjRange(uint32_t slotId, long bcOffset)
3584514f5e3Sopenharmony_ci{
3594514f5e3Sopenharmony_ci    JSTaggedValue slotValue = profileTypeInfo_->Get(slotId);
3604514f5e3Sopenharmony_ci    int ctorMethodId = 0;
3614514f5e3Sopenharmony_ci    JSHClass* hclass = nullptr;
3624514f5e3Sopenharmony_ci    if (slotValue.IsInt()) {
3634514f5e3Sopenharmony_ci        ctorMethodId = slotValue.GetInt();
3644514f5e3Sopenharmony_ci        // JIT cannot optimize this scenario because it doesn't know the hclass
3654514f5e3Sopenharmony_ci        if (ctorMethodId > 0) {
3664514f5e3Sopenharmony_ci            return;
3674514f5e3Sopenharmony_ci        }
3684514f5e3Sopenharmony_ci    } else if (slotValue.IsJSFunction()) {
3694514f5e3Sopenharmony_ci        JSFunction *callee = JSFunction::Cast(slotValue);
3704514f5e3Sopenharmony_ci        Method *calleeMethod = Method::Cast(callee->GetMethod());
3714514f5e3Sopenharmony_ci        ctorMethodId = static_cast<int>(calleeMethod->GetMethodId().GetOffset());
3724514f5e3Sopenharmony_ci        JSTaggedValue protoOrHClass = callee->GetProtoOrHClass();
3734514f5e3Sopenharmony_ci        if (protoOrHClass.IsJSHClass()) {
3744514f5e3Sopenharmony_ci            hclass = JSHClass::Cast(protoOrHClass.GetTaggedObject());
3754514f5e3Sopenharmony_ci        } else {
3764514f5e3Sopenharmony_ci            return;
3774514f5e3Sopenharmony_ci        }
3784514f5e3Sopenharmony_ci    } else {
3794514f5e3Sopenharmony_ci        return;
3804514f5e3Sopenharmony_ci    }
3814514f5e3Sopenharmony_ci    if (ctorMethodId > 0) {
3824514f5e3Sopenharmony_ci        ptManager_->RecordAndGetHclassIndexForJIT(hclass);
3834514f5e3Sopenharmony_ci        auto pt = ProfileType(abcId_, std::abs(ctorMethodId), ProfileType::Kind::JITClassId, true);
3844514f5e3Sopenharmony_ci        PGODefineOpType* type = chunk_->New<PGODefineOpType>(pt, hclass);
3854514f5e3Sopenharmony_ci        UpdatePGOType(bcOffset, type);
3864514f5e3Sopenharmony_ci    } else {
3874514f5e3Sopenharmony_ci        auto kind = ProfileType::Kind::BuiltinFunctionId;
3884514f5e3Sopenharmony_ci        auto type = chunk_->New<PGOSampleType>(ProfileType(abcId_, std::abs(ctorMethodId), kind));
3894514f5e3Sopenharmony_ci        UpdatePGOType(bcOffset, type);
3904514f5e3Sopenharmony_ci    }
3914514f5e3Sopenharmony_ci}
3924514f5e3Sopenharmony_ci
3934514f5e3Sopenharmony_civoid JITProfiler::ConvertGetIterator(uint32_t slotId, long bcOffset)
3944514f5e3Sopenharmony_ci{
3954514f5e3Sopenharmony_ci    if (vm_->GetJSThread()->GetEnableLazyBuiltins()) {
3964514f5e3Sopenharmony_ci        return;
3974514f5e3Sopenharmony_ci    }
3984514f5e3Sopenharmony_ci    JSTaggedValue value = profileTypeInfo_->Get(slotId);
3994514f5e3Sopenharmony_ci    if (!value.IsInt()) {
4004514f5e3Sopenharmony_ci        return;
4014514f5e3Sopenharmony_ci    }
4024514f5e3Sopenharmony_ci    int iterKind = value.GetInt();
4034514f5e3Sopenharmony_ci    ASSERT(iterKind <= 0);
4044514f5e3Sopenharmony_ci    ProfileType::Kind pgoKind = ProfileType::Kind::BuiltinFunctionId;
4054514f5e3Sopenharmony_ci    auto type = chunk_->New<PGOSampleType>(ProfileType(abcId_, std::abs(iterKind), pgoKind));
4064514f5e3Sopenharmony_ci    UpdatePGOType(bcOffset, type);
4074514f5e3Sopenharmony_ci}
4084514f5e3Sopenharmony_ci
4094514f5e3Sopenharmony_civoid JITProfiler::ConvertCreateObject(uint32_t slotId, long bcOffset, [[maybe_unused]]int32_t traceId)
4104514f5e3Sopenharmony_ci{
4114514f5e3Sopenharmony_ci    JSTaggedValue slotValue = profileTypeInfo_->Get(slotId);
4124514f5e3Sopenharmony_ci    if (!slotValue.IsHeapObject()) {
4134514f5e3Sopenharmony_ci        return;
4144514f5e3Sopenharmony_ci    }
4154514f5e3Sopenharmony_ci    if (slotValue.IsWeak()) {
4164514f5e3Sopenharmony_ci        auto object = slotValue.GetWeakReferentUnChecked();
4174514f5e3Sopenharmony_ci        if (object->GetClass()->IsHClass()) {
4184514f5e3Sopenharmony_ci            auto newHClass = JSHClass::Cast(object);
4194514f5e3Sopenharmony_ci            PGODefineOpType* objDefType = chunk_->New<PGODefineOpType>(ProfileType::CreateJITType(), newHClass);
4204514f5e3Sopenharmony_ci            ptManager_->RecordAndGetHclassIndexForJIT(newHClass);
4214514f5e3Sopenharmony_ci            UpdatePGOType(bcOffset, objDefType);
4224514f5e3Sopenharmony_ci        }
4234514f5e3Sopenharmony_ci    } else if (slotValue.IsTrackInfoObject()) {
4244514f5e3Sopenharmony_ci        TrackInfo *trackInfo = TrackInfo::Cast(slotValue.GetTaggedObject());
4254514f5e3Sopenharmony_ci        auto hclass = JSHClass::Cast(trackInfo->GetCachedHClass().GetTaggedObject());
4264514f5e3Sopenharmony_ci        PGODefineOpType* objDefType = chunk_->New<PGODefineOpType>(ProfileType::CreateJITType(), hclass);
4274514f5e3Sopenharmony_ci        ptManager_->RecordAndGetHclassIndexForJIT(hclass);
4284514f5e3Sopenharmony_ci        auto elementsKind = trackInfo->GetElementsKind();
4294514f5e3Sopenharmony_ci        objDefType->SetElementsKind(elementsKind);
4304514f5e3Sopenharmony_ci        objDefType->SetElementsLength(trackInfo->GetArrayLength());
4314514f5e3Sopenharmony_ci        objDefType->SetSpaceFlag(trackInfo->GetSpaceFlag());
4324514f5e3Sopenharmony_ci        UpdatePGOType(bcOffset, objDefType);
4334514f5e3Sopenharmony_ci    }
4344514f5e3Sopenharmony_ci}
4354514f5e3Sopenharmony_ci
4364514f5e3Sopenharmony_civoid JITProfiler::ConvertICByName(int32_t bcOffset, uint32_t slotId, BCType type)
4374514f5e3Sopenharmony_ci{
4384514f5e3Sopenharmony_ci    ProfileTypeAccessorLockScope accessorLockScope(vm_->GetJSThreadNoCheck());
4394514f5e3Sopenharmony_ci    JSTaggedValue firstValue = profileTypeInfo_->Get(slotId);
4404514f5e3Sopenharmony_ci    if (!firstValue.IsHeapObject()) {
4414514f5e3Sopenharmony_ci        if (firstValue.IsHole()) {
4424514f5e3Sopenharmony_ci            // Mega state
4434514f5e3Sopenharmony_ci            AddObjectInfoWithMega(bcOffset);
4444514f5e3Sopenharmony_ci        }
4454514f5e3Sopenharmony_ci        return;
4464514f5e3Sopenharmony_ci    }
4474514f5e3Sopenharmony_ci    if (firstValue.IsWeak()) {
4484514f5e3Sopenharmony_ci        TaggedObject *object = firstValue.GetWeakReferentUnChecked();
4494514f5e3Sopenharmony_ci        if (object->GetClass()->IsHClass()) {
4504514f5e3Sopenharmony_ci            JSTaggedValue secondValue = profileTypeInfo_->Get(slotId + 1);
4514514f5e3Sopenharmony_ci            JSHClass *hclass = JSHClass::Cast(object);
4524514f5e3Sopenharmony_ci            ConvertICByNameWithHandler(abcId_, bcOffset, hclass, secondValue, type, slotId + 1);
4534514f5e3Sopenharmony_ci        }
4544514f5e3Sopenharmony_ci        return;
4554514f5e3Sopenharmony_ci    }
4564514f5e3Sopenharmony_ci    ConvertICByNameWithPoly(abcId_, bcOffset, firstValue, type, slotId);
4574514f5e3Sopenharmony_ci}
4584514f5e3Sopenharmony_ci
4594514f5e3Sopenharmony_civoid JITProfiler::ConvertICByNameWithHandler(ApEntityId abcId, int32_t bcOffset,
4604514f5e3Sopenharmony_ci                                             JSHClass *hclass,
4614514f5e3Sopenharmony_ci                                             JSTaggedValue secondValue, BCType type, uint32_t slotId)
4624514f5e3Sopenharmony_ci{
4634514f5e3Sopenharmony_ci    if (type == BCType::LOAD) {
4644514f5e3Sopenharmony_ci        HandleLoadType(abcId, bcOffset, hclass, secondValue, slotId);
4654514f5e3Sopenharmony_ci        // LoadGlobal
4664514f5e3Sopenharmony_ci        return;
4674514f5e3Sopenharmony_ci    }
4684514f5e3Sopenharmony_ci    HandleOtherTypes(abcId, bcOffset, hclass, secondValue, slotId);
4694514f5e3Sopenharmony_ci}
4704514f5e3Sopenharmony_ci
4714514f5e3Sopenharmony_civoid JITProfiler::HandleLoadType(ApEntityId &abcId, int32_t &bcOffset,
4724514f5e3Sopenharmony_ci                                 JSHClass *hclass, JSTaggedValue &secondValue, uint32_t slotId)
4734514f5e3Sopenharmony_ci{
4744514f5e3Sopenharmony_ci    if (secondValue.IsInt()) {
4754514f5e3Sopenharmony_ci        HandleLoadTypeInt(abcId, bcOffset, hclass, secondValue);
4764514f5e3Sopenharmony_ci    } else if (secondValue.IsPrototypeHandler()) {
4774514f5e3Sopenharmony_ci        HandleLoadTypePrototypeHandler(abcId, bcOffset, hclass, secondValue, slotId);
4784514f5e3Sopenharmony_ci    }
4794514f5e3Sopenharmony_ci}
4804514f5e3Sopenharmony_ci
4814514f5e3Sopenharmony_civoid JITProfiler::HandleLoadTypeInt(ApEntityId &abcId, int32_t &bcOffset,
4824514f5e3Sopenharmony_ci                                    JSHClass *hclass, JSTaggedValue &secondValue)
4834514f5e3Sopenharmony_ci{
4844514f5e3Sopenharmony_ci    auto handlerInfo = static_cast<uint32_t>(secondValue.GetInt());
4854514f5e3Sopenharmony_ci    if (HandlerBase::IsNonExist(handlerInfo)) {
4864514f5e3Sopenharmony_ci        return;
4874514f5e3Sopenharmony_ci    }
4884514f5e3Sopenharmony_ci    if (AddBuiltinsInfoByNameInInstance(abcId, bcOffset, hclass)) {
4894514f5e3Sopenharmony_ci        return;
4904514f5e3Sopenharmony_ci    }
4914514f5e3Sopenharmony_ci    if (HandlerBase::IsField(handlerInfo) || HandlerBase::IsAccessor(handlerInfo)) {
4924514f5e3Sopenharmony_ci        AddObjectInfo(abcId, bcOffset, hclass, hclass, hclass);
4934514f5e3Sopenharmony_ci    }
4944514f5e3Sopenharmony_ci}
4954514f5e3Sopenharmony_ci
4964514f5e3Sopenharmony_civoid JITProfiler::HandleLoadTypePrototypeHandler(ApEntityId &abcId, int32_t &bcOffset,
4974514f5e3Sopenharmony_ci                                                 JSHClass *hclass, JSTaggedValue &secondValue, uint32_t slotId)
4984514f5e3Sopenharmony_ci{
4994514f5e3Sopenharmony_ci    auto prototypeHandler = PrototypeHandler::Cast(secondValue.GetTaggedObject());
5004514f5e3Sopenharmony_ci    auto cellValue = prototypeHandler->GetProtoCell();
5014514f5e3Sopenharmony_ci    if (cellValue.IsUndefined()) {
5024514f5e3Sopenharmony_ci        return;
5034514f5e3Sopenharmony_ci    }
5044514f5e3Sopenharmony_ci    ProtoChangeMarker *cell = ProtoChangeMarker::Cast(cellValue.GetTaggedObject());
5054514f5e3Sopenharmony_ci    if (cell->GetHasChanged()) {
5064514f5e3Sopenharmony_ci        return;
5074514f5e3Sopenharmony_ci    }
5084514f5e3Sopenharmony_ci    auto holder = prototypeHandler->GetHolder();
5094514f5e3Sopenharmony_ci    auto holderHClass = holder.GetTaggedObject()->GetClass();
5104514f5e3Sopenharmony_ci    JSTaggedValue handlerInfoVal = prototypeHandler->GetHandlerInfo();
5114514f5e3Sopenharmony_ci    if (!handlerInfoVal.IsInt()) {
5124514f5e3Sopenharmony_ci        return;
5134514f5e3Sopenharmony_ci    }
5144514f5e3Sopenharmony_ci    auto handlerInfo = static_cast<uint32_t>(handlerInfoVal.GetInt());
5154514f5e3Sopenharmony_ci    if (HandlerBase::IsNonExist(handlerInfo)) {
5164514f5e3Sopenharmony_ci        return;
5174514f5e3Sopenharmony_ci    }
5184514f5e3Sopenharmony_ci    auto accessorMethodId = prototypeHandler->GetAccessorMethodId();
5194514f5e3Sopenharmony_ci    auto accessor = prototypeHandler->GetAccessorJSFunction();
5204514f5e3Sopenharmony_ci    if (accessor.IsJSFunction()) {
5214514f5e3Sopenharmony_ci        auto accessorFunction = JSFunction::Cast(accessor);
5224514f5e3Sopenharmony_ci        auto methodId = Method::Cast(accessorFunction->GetMethod())->GetMethodId().GetOffset();
5234514f5e3Sopenharmony_ci        ASSERT(accessorMethodId == methodId);
5244514f5e3Sopenharmony_ci        accessorMethodId = methodId;
5254514f5e3Sopenharmony_ci        static_cast<JitCompilationEnv *>(compilationEnv_)
5264514f5e3Sopenharmony_ci            ->UpdateFuncSlotIdMap(accessorMethodId, methodId_.GetOffset(), slotId);
5274514f5e3Sopenharmony_ci    }
5284514f5e3Sopenharmony_ci    if (AddBuiltinsInfoByNameInProt(abcId, bcOffset, hclass, holderHClass)) {
5294514f5e3Sopenharmony_ci        return ;
5304514f5e3Sopenharmony_ci    }
5314514f5e3Sopenharmony_ci    AddObjectInfo(abcId, bcOffset, hclass, holderHClass, holderHClass, accessorMethodId);
5324514f5e3Sopenharmony_ci}
5334514f5e3Sopenharmony_ci
5344514f5e3Sopenharmony_civoid JITProfiler::HandleOtherTypes(ApEntityId &abcId, int32_t &bcOffset,
5354514f5e3Sopenharmony_ci                                   JSHClass *hclass, JSTaggedValue &secondValue, uint32_t slotId)
5364514f5e3Sopenharmony_ci{
5374514f5e3Sopenharmony_ci    if (secondValue.IsInt()) {
5384514f5e3Sopenharmony_ci        AddObjectInfo(abcId, bcOffset, hclass, hclass, hclass);
5394514f5e3Sopenharmony_ci    } else if (secondValue.IsTransitionHandler()) {
5404514f5e3Sopenharmony_ci        HandleTransitionHandler(abcId, bcOffset, hclass, secondValue);
5414514f5e3Sopenharmony_ci    } else if (secondValue.IsTransWithProtoHandler()) {
5424514f5e3Sopenharmony_ci        HandleTransWithProtoHandler(abcId, bcOffset, hclass, secondValue);
5434514f5e3Sopenharmony_ci    } else if (secondValue.IsPrototypeHandler()) {
5444514f5e3Sopenharmony_ci        HandleOtherTypesPrototypeHandler(abcId, bcOffset, hclass, secondValue, slotId);
5454514f5e3Sopenharmony_ci    } else if (secondValue.IsPropertyBox()) {
5464514f5e3Sopenharmony_ci        // StoreGlobal
5474514f5e3Sopenharmony_ci    } else if (secondValue.IsStoreTSHandler()) {
5484514f5e3Sopenharmony_ci        HandleStoreTSHandler(abcId, bcOffset, hclass, secondValue);
5494514f5e3Sopenharmony_ci    }
5504514f5e3Sopenharmony_ci}
5514514f5e3Sopenharmony_ci
5524514f5e3Sopenharmony_civoid JITProfiler::HandleTransitionHandler(ApEntityId &abcId, int32_t &bcOffset,
5534514f5e3Sopenharmony_ci                                          JSHClass *hclass, JSTaggedValue &secondValue)
5544514f5e3Sopenharmony_ci{
5554514f5e3Sopenharmony_ci    auto transitionHandler = TransitionHandler::Cast(secondValue.GetTaggedObject());
5564514f5e3Sopenharmony_ci    auto transitionHClassVal = transitionHandler->GetTransitionHClass();
5574514f5e3Sopenharmony_ci    if (transitionHClassVal.IsJSHClass()) {
5584514f5e3Sopenharmony_ci        auto transitionHClass = JSHClass::Cast(transitionHClassVal.GetTaggedObject());
5594514f5e3Sopenharmony_ci        AddObjectInfo(abcId, bcOffset, hclass, hclass, transitionHClass);
5604514f5e3Sopenharmony_ci    }
5614514f5e3Sopenharmony_ci}
5624514f5e3Sopenharmony_ci
5634514f5e3Sopenharmony_civoid JITProfiler::HandleTransWithProtoHandler(ApEntityId &abcId, int32_t &bcOffset,
5644514f5e3Sopenharmony_ci                                              JSHClass *hclass, JSTaggedValue &secondValue)
5654514f5e3Sopenharmony_ci{
5664514f5e3Sopenharmony_ci    auto transWithProtoHandler = TransWithProtoHandler::Cast(secondValue.GetTaggedObject());
5674514f5e3Sopenharmony_ci    auto cellValue = transWithProtoHandler->GetProtoCell();
5684514f5e3Sopenharmony_ci    ASSERT(cellValue.IsProtoChangeMarker());
5694514f5e3Sopenharmony_ci    ProtoChangeMarker *cell = ProtoChangeMarker::Cast(cellValue.GetTaggedObject());
5704514f5e3Sopenharmony_ci    if (cell->GetHasChanged()) {
5714514f5e3Sopenharmony_ci        return;
5724514f5e3Sopenharmony_ci    }
5734514f5e3Sopenharmony_ci    auto transitionHClassVal = transWithProtoHandler->GetTransitionHClass();
5744514f5e3Sopenharmony_ci    if (transitionHClassVal.IsJSHClass()) {
5754514f5e3Sopenharmony_ci        auto transitionHClass = JSHClass::Cast(transitionHClassVal.GetTaggedObject());
5764514f5e3Sopenharmony_ci        AddObjectInfo(abcId, bcOffset, hclass, hclass, transitionHClass);
5774514f5e3Sopenharmony_ci    }
5784514f5e3Sopenharmony_ci}
5794514f5e3Sopenharmony_ci
5804514f5e3Sopenharmony_civoid JITProfiler::HandleOtherTypesPrototypeHandler(ApEntityId &abcId, int32_t &bcOffset,
5814514f5e3Sopenharmony_ci                                                   JSHClass *hclass, JSTaggedValue &secondValue, uint32_t slotId)
5824514f5e3Sopenharmony_ci{
5834514f5e3Sopenharmony_ci    auto prototypeHandler = PrototypeHandler::Cast(secondValue.GetTaggedObject());
5844514f5e3Sopenharmony_ci    auto cellValue = prototypeHandler->GetProtoCell();
5854514f5e3Sopenharmony_ci    if (cellValue.IsUndefined()) {
5864514f5e3Sopenharmony_ci        return;
5874514f5e3Sopenharmony_ci    }
5884514f5e3Sopenharmony_ci    ProtoChangeMarker *cell = ProtoChangeMarker::Cast(cellValue.GetTaggedObject());
5894514f5e3Sopenharmony_ci    if (cell->GetHasChanged()) {
5904514f5e3Sopenharmony_ci        return;
5914514f5e3Sopenharmony_ci    }
5924514f5e3Sopenharmony_ci    auto holder = prototypeHandler->GetHolder();
5934514f5e3Sopenharmony_ci    auto holderHClass = holder.GetTaggedObject()->GetClass();
5944514f5e3Sopenharmony_ci    auto accessorMethodId = prototypeHandler->GetAccessorMethodId();
5954514f5e3Sopenharmony_ci    auto accessor = prototypeHandler->GetAccessorJSFunction();
5964514f5e3Sopenharmony_ci    if (accessor.IsJSFunction()) {
5974514f5e3Sopenharmony_ci        auto accessorFunction = JSFunction::Cast(accessor);
5984514f5e3Sopenharmony_ci        auto methodId = Method::Cast(accessorFunction->GetMethod())->GetMethodId().GetOffset();
5994514f5e3Sopenharmony_ci        ASSERT(accessorMethodId == methodId);
6004514f5e3Sopenharmony_ci        accessorMethodId = methodId;
6014514f5e3Sopenharmony_ci        static_cast<JitCompilationEnv *>(compilationEnv_)
6024514f5e3Sopenharmony_ci            ->UpdateFuncSlotIdMap(accessorMethodId, methodId_.GetOffset(), slotId);
6034514f5e3Sopenharmony_ci    }
6044514f5e3Sopenharmony_ci    AddObjectInfo(abcId, bcOffset, hclass, holderHClass, holderHClass, accessorMethodId);
6054514f5e3Sopenharmony_ci}
6064514f5e3Sopenharmony_ci
6074514f5e3Sopenharmony_civoid JITProfiler::HandleStoreTSHandler(ApEntityId &abcId, int32_t &bcOffset,
6084514f5e3Sopenharmony_ci                                       JSHClass *hclass, JSTaggedValue &secondValue)
6094514f5e3Sopenharmony_ci{
6104514f5e3Sopenharmony_ci    StoreTSHandler *storeTSHandler = StoreTSHandler::Cast(secondValue.GetTaggedObject());
6114514f5e3Sopenharmony_ci    auto cellValue = storeTSHandler->GetProtoCell();
6124514f5e3Sopenharmony_ci    ASSERT(cellValue.IsProtoChangeMarker());
6134514f5e3Sopenharmony_ci    ProtoChangeMarker *cell = ProtoChangeMarker::Cast(cellValue.GetTaggedObject());
6144514f5e3Sopenharmony_ci    if (cell->GetHasChanged()) {
6154514f5e3Sopenharmony_ci        return;
6164514f5e3Sopenharmony_ci    }
6174514f5e3Sopenharmony_ci    auto holder = storeTSHandler->GetHolder();
6184514f5e3Sopenharmony_ci    auto holderHClass = holder.GetTaggedObject()->GetClass();
6194514f5e3Sopenharmony_ci    AddObjectInfo(abcId, bcOffset, hclass, holderHClass, holderHClass);
6204514f5e3Sopenharmony_ci}
6214514f5e3Sopenharmony_ci
6224514f5e3Sopenharmony_civoid JITProfiler::ConvertICByNameWithPoly(ApEntityId abcId, int32_t bcOffset, JSTaggedValue cacheValue, BCType type,
6234514f5e3Sopenharmony_ci                                          uint32_t slotId)
6244514f5e3Sopenharmony_ci{
6254514f5e3Sopenharmony_ci    if (cacheValue.IsWeak()) {
6264514f5e3Sopenharmony_ci        return;
6274514f5e3Sopenharmony_ci    }
6284514f5e3Sopenharmony_ci    ASSERT(cacheValue.IsTaggedArray());
6294514f5e3Sopenharmony_ci    auto array = TaggedArray::Cast(cacheValue);
6304514f5e3Sopenharmony_ci    uint32_t length = array->GetLength();
6314514f5e3Sopenharmony_ci    for (uint32_t i = 0; i < length; i += 2) { // 2 means one ic, two slot
6324514f5e3Sopenharmony_ci        auto result = array->Get(i);
6334514f5e3Sopenharmony_ci        auto handler = array->Get(i + 1);
6344514f5e3Sopenharmony_ci        if (!result.IsHeapObject() || !result.IsWeak()) {
6354514f5e3Sopenharmony_ci            continue;
6364514f5e3Sopenharmony_ci        }
6374514f5e3Sopenharmony_ci        TaggedObject *object = result.GetWeakReferentUnChecked();
6384514f5e3Sopenharmony_ci        if (!object->GetClass()->IsHClass()) {
6394514f5e3Sopenharmony_ci            continue;
6404514f5e3Sopenharmony_ci        }
6414514f5e3Sopenharmony_ci        JSHClass *hclass = JSHClass::Cast(object);
6424514f5e3Sopenharmony_ci        ConvertICByNameWithHandler(abcId, bcOffset, hclass, handler, type, slotId);
6434514f5e3Sopenharmony_ci    }
6444514f5e3Sopenharmony_ci}
6454514f5e3Sopenharmony_ci
6464514f5e3Sopenharmony_civoid JITProfiler::ConvertICByValue(int32_t bcOffset, uint32_t slotId, BCType type)
6474514f5e3Sopenharmony_ci{
6484514f5e3Sopenharmony_ci    ProfileTypeAccessorLockScope accessorLockScope(vm_->GetJSThreadNoCheck());
6494514f5e3Sopenharmony_ci    JSTaggedValue firstValue = profileTypeInfo_->Get(slotId);
6504514f5e3Sopenharmony_ci    if (!firstValue.IsHeapObject()) {
6514514f5e3Sopenharmony_ci        if (firstValue.IsHole()) {
6524514f5e3Sopenharmony_ci            // Mega state
6534514f5e3Sopenharmony_ci            AddObjectInfoWithMega(bcOffset);
6544514f5e3Sopenharmony_ci        }
6554514f5e3Sopenharmony_ci        return;
6564514f5e3Sopenharmony_ci    }
6574514f5e3Sopenharmony_ci    if (firstValue.IsWeak()) {
6584514f5e3Sopenharmony_ci        TaggedObject *object = firstValue.GetWeakReferentUnChecked();
6594514f5e3Sopenharmony_ci        if (object->GetClass()->IsHClass()) {
6604514f5e3Sopenharmony_ci            JSTaggedValue secondValue = profileTypeInfo_->Get(slotId + 1);
6614514f5e3Sopenharmony_ci            JSHClass *hclass = JSHClass::Cast(object);
6624514f5e3Sopenharmony_ci            ConvertICByValueWithHandler(abcId_, bcOffset, hclass, secondValue, type);
6634514f5e3Sopenharmony_ci        }
6644514f5e3Sopenharmony_ci        return;
6654514f5e3Sopenharmony_ci    }
6664514f5e3Sopenharmony_ci    // Check key
6674514f5e3Sopenharmony_ci    if ((firstValue.IsString() || firstValue.IsSymbol())) {
6684514f5e3Sopenharmony_ci        return;
6694514f5e3Sopenharmony_ci    }
6704514f5e3Sopenharmony_ci    // Check without key
6714514f5e3Sopenharmony_ci    ConvertICByValueWithPoly(abcId_, bcOffset, firstValue, type);
6724514f5e3Sopenharmony_ci}
6734514f5e3Sopenharmony_ci
6744514f5e3Sopenharmony_civoid JITProfiler::ConvertICByValueWithHandler(ApEntityId abcId, int32_t bcOffset,
6754514f5e3Sopenharmony_ci                                              JSHClass *hclass, JSTaggedValue secondValue,
6764514f5e3Sopenharmony_ci                                              BCType type)
6774514f5e3Sopenharmony_ci{
6784514f5e3Sopenharmony_ci    if (type == BCType::LOAD) {
6794514f5e3Sopenharmony_ci        if (secondValue.IsInt()) {
6804514f5e3Sopenharmony_ci            auto handlerInfo = static_cast<uint32_t>(secondValue.GetInt());
6814514f5e3Sopenharmony_ci            if (HandlerBase::IsNormalElement(handlerInfo) || HandlerBase::IsStringElement(handlerInfo)) {
6824514f5e3Sopenharmony_ci                if (HandlerBase::NeedSkipInPGODump(handlerInfo)) {
6834514f5e3Sopenharmony_ci                    return;
6844514f5e3Sopenharmony_ci                }
6854514f5e3Sopenharmony_ci                AddBuiltinsInfo(abcId, bcOffset, hclass, hclass);
6864514f5e3Sopenharmony_ci                return;
6874514f5e3Sopenharmony_ci            }
6884514f5e3Sopenharmony_ci            if (HandlerBase::IsTypedArrayElement(handlerInfo)) {
6894514f5e3Sopenharmony_ci                OnHeapMode onHeap =  HandlerBase::IsOnHeap(handlerInfo) ? OnHeapMode::ON_HEAP : OnHeapMode::NOT_ON_HEAP;
6904514f5e3Sopenharmony_ci                AddBuiltinsInfo(abcId, bcOffset, hclass, hclass, onHeap);
6914514f5e3Sopenharmony_ci                return;
6924514f5e3Sopenharmony_ci            }
6934514f5e3Sopenharmony_ci            AddObjectInfo(abcId, bcOffset, hclass, hclass, hclass);
6944514f5e3Sopenharmony_ci        }
6954514f5e3Sopenharmony_ci        return;
6964514f5e3Sopenharmony_ci    }
6974514f5e3Sopenharmony_ci    HandleStoreType(abcId, bcOffset, hclass, secondValue);
6984514f5e3Sopenharmony_ci}
6994514f5e3Sopenharmony_ci
7004514f5e3Sopenharmony_civoid JITProfiler::HandleStoreType(ApEntityId &abcId, int32_t &bcOffset,
7014514f5e3Sopenharmony_ci                                  JSHClass *hclass, JSTaggedValue &secondValue)
7024514f5e3Sopenharmony_ci{
7034514f5e3Sopenharmony_ci    if (secondValue.IsInt()) {
7044514f5e3Sopenharmony_ci        auto handlerInfo = static_cast<uint32_t>(secondValue.GetInt());
7054514f5e3Sopenharmony_ci        if (HandlerBase::IsNormalElement(handlerInfo) || HandlerBase::IsStringElement(handlerInfo)) {
7064514f5e3Sopenharmony_ci            AddBuiltinsInfo(abcId, bcOffset, hclass, hclass,
7074514f5e3Sopenharmony_ci                            OnHeapMode::NONE, HandlerBase::IsStoreOutOfBounds(handlerInfo));
7084514f5e3Sopenharmony_ci            return;
7094514f5e3Sopenharmony_ci        }
7104514f5e3Sopenharmony_ci        if (HandlerBase::IsTypedArrayElement(handlerInfo)) {
7114514f5e3Sopenharmony_ci            OnHeapMode onHeap = HandlerBase::IsOnHeap(handlerInfo) ? OnHeapMode::ON_HEAP : OnHeapMode::NOT_ON_HEAP;
7124514f5e3Sopenharmony_ci            AddBuiltinsInfo(abcId,  bcOffset, hclass, hclass, onHeap,
7134514f5e3Sopenharmony_ci                            HandlerBase::IsStoreOutOfBounds(handlerInfo));
7144514f5e3Sopenharmony_ci            return;
7154514f5e3Sopenharmony_ci        }
7164514f5e3Sopenharmony_ci        AddObjectInfo(abcId, bcOffset, hclass, hclass, hclass);
7174514f5e3Sopenharmony_ci    } else if (secondValue.IsTransitionHandler()) {
7184514f5e3Sopenharmony_ci        HandleTransition(abcId, bcOffset, hclass, secondValue);
7194514f5e3Sopenharmony_ci    } else if (secondValue.IsTransWithProtoHandler()) {
7204514f5e3Sopenharmony_ci        HandleTransWithProto(abcId, bcOffset, hclass, secondValue);
7214514f5e3Sopenharmony_ci    } else {
7224514f5e3Sopenharmony_ci        HandlePrototypeHandler(abcId, bcOffset, hclass, secondValue);
7234514f5e3Sopenharmony_ci    }
7244514f5e3Sopenharmony_ci}
7254514f5e3Sopenharmony_ci
7264514f5e3Sopenharmony_civoid JITProfiler::HandleTransition(ApEntityId &abcId, int32_t &bcOffset,
7274514f5e3Sopenharmony_ci                                   JSHClass *hclass, JSTaggedValue &secondValue)
7284514f5e3Sopenharmony_ci{
7294514f5e3Sopenharmony_ci    auto transitionHandler = TransitionHandler::Cast(secondValue.GetTaggedObject());
7304514f5e3Sopenharmony_ci    auto transitionHClassVal = transitionHandler->GetTransitionHClass();
7314514f5e3Sopenharmony_ci
7324514f5e3Sopenharmony_ci    auto handlerInfoValue = transitionHandler->GetHandlerInfo();
7334514f5e3Sopenharmony_ci    ASSERT(handlerInfoValue.IsInt());
7344514f5e3Sopenharmony_ci    auto handlerInfo = static_cast<uint32_t>(handlerInfoValue.GetInt());
7354514f5e3Sopenharmony_ci    if (transitionHClassVal.IsJSHClass()) {
7364514f5e3Sopenharmony_ci        auto transitionHClass = JSHClass::Cast(transitionHClassVal.GetTaggedObject());
7374514f5e3Sopenharmony_ci        if (HandlerBase::IsElement(handlerInfo)) {
7384514f5e3Sopenharmony_ci            AddBuiltinsInfo(abcId, bcOffset, hclass, transitionHClass,
7394514f5e3Sopenharmony_ci                            OnHeapMode::NONE, HandlerBase::IsStoreOutOfBounds(handlerInfo));
7404514f5e3Sopenharmony_ci        } else {
7414514f5e3Sopenharmony_ci            AddObjectInfo(abcId, bcOffset, hclass, hclass, transitionHClass);
7424514f5e3Sopenharmony_ci        }
7434514f5e3Sopenharmony_ci    }
7444514f5e3Sopenharmony_ci}
7454514f5e3Sopenharmony_ci
7464514f5e3Sopenharmony_civoid JITProfiler::HandleTransWithProto(ApEntityId &abcId, int32_t &bcOffset,
7474514f5e3Sopenharmony_ci                                       JSHClass *hclass, JSTaggedValue &secondValue)
7484514f5e3Sopenharmony_ci{
7494514f5e3Sopenharmony_ci    auto transWithProtoHandler = TransWithProtoHandler::Cast(secondValue.GetTaggedObject());
7504514f5e3Sopenharmony_ci    auto transitionHClassVal = transWithProtoHandler->GetTransitionHClass();
7514514f5e3Sopenharmony_ci    auto handlerInfoValue = transWithProtoHandler->GetHandlerInfo();
7524514f5e3Sopenharmony_ci    ASSERT(handlerInfoValue.IsInt());
7534514f5e3Sopenharmony_ci    auto handlerInfo = static_cast<uint32_t>(handlerInfoValue.GetInt());
7544514f5e3Sopenharmony_ci    if (transitionHClassVal.IsJSHClass()) {
7554514f5e3Sopenharmony_ci        auto transitionHClass = JSHClass::Cast(transitionHClassVal.GetTaggedObject());
7564514f5e3Sopenharmony_ci        if (HandlerBase::IsElement(handlerInfo)) {
7574514f5e3Sopenharmony_ci            AddBuiltinsInfo(abcId, bcOffset, hclass, transitionHClass,
7584514f5e3Sopenharmony_ci                            OnHeapMode::NONE, HandlerBase::IsStoreOutOfBounds(handlerInfo));
7594514f5e3Sopenharmony_ci        } else {
7604514f5e3Sopenharmony_ci            AddObjectInfo(abcId, bcOffset, hclass, hclass, transitionHClass);
7614514f5e3Sopenharmony_ci        }
7624514f5e3Sopenharmony_ci    }
7634514f5e3Sopenharmony_ci}
7644514f5e3Sopenharmony_ci
7654514f5e3Sopenharmony_civoid JITProfiler::HandlePrototypeHandler(ApEntityId &abcId, int32_t &bcOffset,
7664514f5e3Sopenharmony_ci                                         JSHClass *hclass, JSTaggedValue &secondValue)
7674514f5e3Sopenharmony_ci{
7684514f5e3Sopenharmony_ci    ASSERT(secondValue.IsPrototypeHandler());
7694514f5e3Sopenharmony_ci    PrototypeHandler *prototypeHandler = PrototypeHandler::Cast(secondValue.GetTaggedObject());
7704514f5e3Sopenharmony_ci    auto cellValue = prototypeHandler->GetProtoCell();
7714514f5e3Sopenharmony_ci    if (!cellValue.IsProtoChangeMarker()) {
7724514f5e3Sopenharmony_ci        return;
7734514f5e3Sopenharmony_ci    }
7744514f5e3Sopenharmony_ci    ASSERT(cellValue.IsProtoChangeMarker());
7754514f5e3Sopenharmony_ci    ProtoChangeMarker *cell = ProtoChangeMarker::Cast(cellValue.GetTaggedObject());
7764514f5e3Sopenharmony_ci    if (cell->GetHasChanged()) {
7774514f5e3Sopenharmony_ci        return;
7784514f5e3Sopenharmony_ci    }
7794514f5e3Sopenharmony_ci    JSTaggedValue handlerInfoValue = prototypeHandler->GetHandlerInfo();
7804514f5e3Sopenharmony_ci    ASSERT(handlerInfoValue.IsInt());
7814514f5e3Sopenharmony_ci    auto handlerInfo = static_cast<uint32_t>(handlerInfoValue.GetInt());
7824514f5e3Sopenharmony_ci    if (HandlerBase::IsElement(handlerInfo)) {
7834514f5e3Sopenharmony_ci        AddBuiltinsInfo(abcId, bcOffset, hclass, hclass,
7844514f5e3Sopenharmony_ci                        OnHeapMode::NONE, HandlerBase::IsStoreOutOfBounds(handlerInfo));
7854514f5e3Sopenharmony_ci        return;
7864514f5e3Sopenharmony_ci    }
7874514f5e3Sopenharmony_ci    auto holder = prototypeHandler->GetHolder();
7884514f5e3Sopenharmony_ci    auto holderHClass = holder.GetTaggedObject()->GetClass();
7894514f5e3Sopenharmony_ci    AddObjectInfo(abcId, bcOffset, hclass, holderHClass, holderHClass);
7904514f5e3Sopenharmony_ci}
7914514f5e3Sopenharmony_ci
7924514f5e3Sopenharmony_civoid JITProfiler::ConvertICByValueWithPoly(ApEntityId abcId, int32_t bcOffset, JSTaggedValue cacheValue, BCType type)
7934514f5e3Sopenharmony_ci{
7944514f5e3Sopenharmony_ci    if (cacheValue.IsWeak()) {
7954514f5e3Sopenharmony_ci        return;
7964514f5e3Sopenharmony_ci    }
7974514f5e3Sopenharmony_ci    ASSERT(cacheValue.IsTaggedArray());
7984514f5e3Sopenharmony_ci    auto array = TaggedArray::Cast(cacheValue);
7994514f5e3Sopenharmony_ci    uint32_t length = array->GetLength();
8004514f5e3Sopenharmony_ci    for (uint32_t i = 0; i < length; i += 2) { // 2 means one ic, two slot
8014514f5e3Sopenharmony_ci        auto result = array->Get(i);
8024514f5e3Sopenharmony_ci        auto handler = array->Get(i + 1);
8034514f5e3Sopenharmony_ci        if (!result.IsHeapObject() || !result.IsWeak()) {
8044514f5e3Sopenharmony_ci            continue;
8054514f5e3Sopenharmony_ci        }
8064514f5e3Sopenharmony_ci        TaggedObject *object = result.GetWeakReferentUnChecked();
8074514f5e3Sopenharmony_ci        if (!object->GetClass()->IsHClass()) {
8084514f5e3Sopenharmony_ci            continue;
8094514f5e3Sopenharmony_ci        }
8104514f5e3Sopenharmony_ci        JSHClass *hclass = JSHClass::Cast(object);
8114514f5e3Sopenharmony_ci        ConvertICByValueWithHandler(abcId, bcOffset, hclass, handler, type);
8124514f5e3Sopenharmony_ci    }
8134514f5e3Sopenharmony_ci}
8144514f5e3Sopenharmony_ci
8154514f5e3Sopenharmony_civoid JITProfiler::ConvertInstanceof(int32_t bcOffset, uint32_t slotId)
8164514f5e3Sopenharmony_ci{
8174514f5e3Sopenharmony_ci    JSTaggedValue firstValue = profileTypeInfo_->Get(slotId);
8184514f5e3Sopenharmony_ci    if (!firstValue.IsHeapObject()) {
8194514f5e3Sopenharmony_ci        if (firstValue.IsHole()) {
8204514f5e3Sopenharmony_ci            // Mega state
8214514f5e3Sopenharmony_ci            AddObjectInfoWithMega(bcOffset);
8224514f5e3Sopenharmony_ci        }
8234514f5e3Sopenharmony_ci        return;
8244514f5e3Sopenharmony_ci    }
8254514f5e3Sopenharmony_ci    if (firstValue.IsWeak()) {
8264514f5e3Sopenharmony_ci        TaggedObject *object = firstValue.GetWeakReferentUnChecked();
8274514f5e3Sopenharmony_ci        if (object->GetClass()->IsHClass()) {
8284514f5e3Sopenharmony_ci            JSHClass *hclass = JSHClass::Cast(object);
8294514f5e3Sopenharmony_ci            // Since pgo does not support symbol, we choose to return if hclass having @@hasInstance
8304514f5e3Sopenharmony_ci            JSHandle<GlobalEnv> env = vm_->GetGlobalEnv();
8314514f5e3Sopenharmony_ci            JSTaggedValue key = env->GetHasInstanceSymbol().GetTaggedValue();
8324514f5e3Sopenharmony_ci            JSHClass *functionPrototypeHC = JSObject::Cast(env->GetFunctionPrototype().GetTaggedValue())->GetClass();
8334514f5e3Sopenharmony_ci            JSTaggedValue foundHClass = TryFindKeyInPrototypeChain(object, hclass, key);
8344514f5e3Sopenharmony_ci            if (!foundHClass.IsUndefined() && JSHClass::Cast(foundHClass.GetTaggedObject()) != functionPrototypeHC) {
8354514f5e3Sopenharmony_ci                return;
8364514f5e3Sopenharmony_ci            }
8374514f5e3Sopenharmony_ci            AddObjectInfo(abcId_, bcOffset, hclass, hclass, hclass);
8384514f5e3Sopenharmony_ci        }
8394514f5e3Sopenharmony_ci        return;
8404514f5e3Sopenharmony_ci    }
8414514f5e3Sopenharmony_ci    // Poly Not Consider now
8424514f5e3Sopenharmony_ci    return;
8434514f5e3Sopenharmony_ci}
8444514f5e3Sopenharmony_ci
8454514f5e3Sopenharmony_ciJSTaggedValue JITProfiler::TryFindKeyInPrototypeChain(TaggedObject *currObj, JSHClass *currHC, JSTaggedValue key)
8464514f5e3Sopenharmony_ci{
8474514f5e3Sopenharmony_ci    // This is a temporary solution for Instanceof Only!
8484514f5e3Sopenharmony_ci    // Do NOT use this function for other purpose.
8494514f5e3Sopenharmony_ci    if (currHC->IsDictionaryMode()) {
8504514f5e3Sopenharmony_ci        return JSTaggedValue(currHC);
8514514f5e3Sopenharmony_ci    }
8524514f5e3Sopenharmony_ci    while (!JSTaggedValue(currHC).IsUndefinedOrNull()) {
8534514f5e3Sopenharmony_ci        if (LIKELY(!currHC->IsDictionaryMode())) {
8544514f5e3Sopenharmony_ci            int entry = JSHClass::FindPropertyEntry(vm_->GetJSThread(), currHC, key);
8554514f5e3Sopenharmony_ci            if (entry != -1) {
8564514f5e3Sopenharmony_ci                return JSTaggedValue(currHC);
8574514f5e3Sopenharmony_ci            }
8584514f5e3Sopenharmony_ci        } else {
8594514f5e3Sopenharmony_ci            TaggedArray *array = TaggedArray::Cast(JSObject::Cast(currObj)->GetProperties().GetTaggedObject());
8604514f5e3Sopenharmony_ci            ASSERT(array->IsDictionaryMode());
8614514f5e3Sopenharmony_ci            NameDictionary *dict = NameDictionary::Cast(array);
8624514f5e3Sopenharmony_ci            int entry = dict->FindEntry(key);
8634514f5e3Sopenharmony_ci            if (entry != -1) {
8644514f5e3Sopenharmony_ci                return JSTaggedValue(currHC);
8654514f5e3Sopenharmony_ci            }
8664514f5e3Sopenharmony_ci        }
8674514f5e3Sopenharmony_ci        currObj = currHC->GetProto().GetTaggedObject();
8684514f5e3Sopenharmony_ci        if (JSTaggedValue(currObj).IsUndefinedOrNull()) {
8694514f5e3Sopenharmony_ci            break;
8704514f5e3Sopenharmony_ci        }
8714514f5e3Sopenharmony_ci        currHC = currObj->GetClass();
8724514f5e3Sopenharmony_ci    }
8734514f5e3Sopenharmony_ci    return JSTaggedValue::Undefined();
8744514f5e3Sopenharmony_ci}
8754514f5e3Sopenharmony_ci
8764514f5e3Sopenharmony_civoid JITProfiler::AddObjectInfoWithMega(int32_t bcOffset)
8774514f5e3Sopenharmony_ci{
8784514f5e3Sopenharmony_ci    auto megaType = ProfileType::CreateMegaType();
8794514f5e3Sopenharmony_ci    PGOObjectInfo info(megaType, megaType, megaType, megaType, megaType, megaType, PGOSampleType());
8804514f5e3Sopenharmony_ci    AddObjectInfoImplement(bcOffset, info);
8814514f5e3Sopenharmony_ci}
8824514f5e3Sopenharmony_ci
8834514f5e3Sopenharmony_civoid JITProfiler::AddObjectInfoImplement(int32_t bcOffset, const PGOObjectInfo &info)
8844514f5e3Sopenharmony_ci{
8854514f5e3Sopenharmony_ci    PGORWOpType *cur = nullptr;
8864514f5e3Sopenharmony_ci    if (bcOffsetPGORwTypeMap_.find(bcOffset) == bcOffsetPGORwTypeMap_.end()) {
8874514f5e3Sopenharmony_ci        cur = chunk_->New<PGORWOpType>();
8884514f5e3Sopenharmony_ci        bcOffsetPGORwTypeMap_[bcOffset] = cur;
8894514f5e3Sopenharmony_ci    } else {
8904514f5e3Sopenharmony_ci        cur = const_cast<PGORWOpType*>(bcOffsetPGORwTypeMap_.at(bcOffset));
8914514f5e3Sopenharmony_ci    }
8924514f5e3Sopenharmony_ci    if (cur != nullptr) {
8934514f5e3Sopenharmony_ci        cur->AddObjectInfo(info);
8944514f5e3Sopenharmony_ci    }
8954514f5e3Sopenharmony_ci}
8964514f5e3Sopenharmony_ci
8974514f5e3Sopenharmony_cibool JITProfiler::AddObjectInfo(ApEntityId abcId, int32_t bcOffset,
8984514f5e3Sopenharmony_ci                                JSHClass *receiver, JSHClass *hold, JSHClass *holdTra, uint32_t accessorMethodId)
8994514f5e3Sopenharmony_ci{
9004514f5e3Sopenharmony_ci    PGOSampleType accessor = PGOSampleType::CreateProfileType(abcId, accessorMethodId, ProfileType::Kind::MethodId);
9014514f5e3Sopenharmony_ci    // case: obj = Object.create(null) => LowerProtoChangeMarkerCheck Crash
9024514f5e3Sopenharmony_ci    if (receiver->GetPrototype().IsNull()) {
9034514f5e3Sopenharmony_ci        return false;
9044514f5e3Sopenharmony_ci    }
9054514f5e3Sopenharmony_ci    return AddTranstionObjectInfo(bcOffset, receiver, hold, holdTra, accessor);
9064514f5e3Sopenharmony_ci}
9074514f5e3Sopenharmony_ci
9084514f5e3Sopenharmony_cibool JITProfiler::AddTranstionObjectInfo(
9094514f5e3Sopenharmony_ci    int32_t bcOffset, JSHClass *receiver, JSHClass *hold, JSHClass *holdTra, PGOSampleType accessorMethod)
9104514f5e3Sopenharmony_ci{
9114514f5e3Sopenharmony_ci    ptManager_->RecordAndGetHclassIndexForJIT(receiver);
9124514f5e3Sopenharmony_ci    ptManager_->RecordAndGetHclassIndexForJIT(hold);
9134514f5e3Sopenharmony_ci    ptManager_->RecordAndGetHclassIndexForJIT(holdTra);
9144514f5e3Sopenharmony_ci    PGOObjectInfo info(ProfileType::CreateJITType(), receiver, hold, holdTra, accessorMethod);
9154514f5e3Sopenharmony_ci    AddObjectInfoImplement(bcOffset, info);
9164514f5e3Sopenharmony_ci    return true;
9174514f5e3Sopenharmony_ci}
9184514f5e3Sopenharmony_ci
9194514f5e3Sopenharmony_civoid JITProfiler::AddBuiltinsInfo(ApEntityId abcId, int32_t bcOffset, JSHClass *receiver,
9204514f5e3Sopenharmony_ci    JSHClass *transitionHClass, OnHeapMode onHeap, bool everOutOfBounds)
9214514f5e3Sopenharmony_ci{
9224514f5e3Sopenharmony_ci    if (receiver->IsJSArray()) {
9234514f5e3Sopenharmony_ci        auto type = receiver->GetObjectType();
9244514f5e3Sopenharmony_ci        auto elementsKind = receiver->GetElementsKind();
9254514f5e3Sopenharmony_ci        auto transitionElementsKind = transitionHClass->GetElementsKind();
9264514f5e3Sopenharmony_ci        auto profileType = ProfileType::CreateBuiltinsArray(abcId, type, elementsKind, transitionElementsKind,
9274514f5e3Sopenharmony_ci                                                            everOutOfBounds);
9284514f5e3Sopenharmony_ci        PGOObjectInfo info(profileType);
9294514f5e3Sopenharmony_ci        AddObjectInfoImplement(bcOffset, info);
9304514f5e3Sopenharmony_ci    } else if (receiver->IsTypedArray()) {
9314514f5e3Sopenharmony_ci        JSType jsType = receiver->GetObjectType();
9324514f5e3Sopenharmony_ci        auto profileType = ProfileType::CreateBuiltinsTypedArray(abcId, jsType, onHeap, everOutOfBounds);
9334514f5e3Sopenharmony_ci        PGOObjectInfo info(profileType);
9344514f5e3Sopenharmony_ci        AddObjectInfoImplement(bcOffset, info);
9354514f5e3Sopenharmony_ci    } else {
9364514f5e3Sopenharmony_ci        auto type = receiver->GetObjectType();
9374514f5e3Sopenharmony_ci        PGOObjectInfo info(ProfileType::CreateBuiltins(abcId, type));
9384514f5e3Sopenharmony_ci        AddObjectInfoImplement(bcOffset, info);
9394514f5e3Sopenharmony_ci    }
9404514f5e3Sopenharmony_ci}
9414514f5e3Sopenharmony_ci
9424514f5e3Sopenharmony_civoid JITProfiler::AddBuiltinsGlobalInfo(ApEntityId abcId, int32_t bcOffset, GlobalIndex globalsId)
9434514f5e3Sopenharmony_ci{
9444514f5e3Sopenharmony_ci    PGOObjectInfo info(ProfileType::CreateGlobals(abcId, globalsId));
9454514f5e3Sopenharmony_ci    AddObjectInfoImplement(bcOffset, info);
9464514f5e3Sopenharmony_ci}
9474514f5e3Sopenharmony_ci
9484514f5e3Sopenharmony_cibool JITProfiler::AddBuiltinsInfoByNameInInstance(ApEntityId abcId, int32_t bcOffset, JSHClass *receiver)
9494514f5e3Sopenharmony_ci{
9504514f5e3Sopenharmony_ci    auto thread = vm_->GetJSThread();
9514514f5e3Sopenharmony_ci    auto type = receiver->GetObjectType();
9524514f5e3Sopenharmony_ci    const auto &ctorEntries = thread->GetCtorHclassEntries();
9534514f5e3Sopenharmony_ci    auto entry = ctorEntries.find(receiver);
9544514f5e3Sopenharmony_ci    if (entry != ctorEntries.end()) {
9554514f5e3Sopenharmony_ci        AddBuiltinsGlobalInfo(abcId, bcOffset, entry->second);
9564514f5e3Sopenharmony_ci        return true;
9574514f5e3Sopenharmony_ci    }
9584514f5e3Sopenharmony_ci
9594514f5e3Sopenharmony_ci    auto builtinsId = ToBuiltinsTypeId(type);
9604514f5e3Sopenharmony_ci    if (!builtinsId.has_value()) {
9614514f5e3Sopenharmony_ci        return false;
9624514f5e3Sopenharmony_ci    }
9634514f5e3Sopenharmony_ci    JSHClass *exceptRecvHClass = nullptr;
9644514f5e3Sopenharmony_ci    if (builtinsId == BuiltinTypeId::ARRAY) {
9654514f5e3Sopenharmony_ci        bool receiverIsPrototype = receiver->IsPrototype();
9664514f5e3Sopenharmony_ci        exceptRecvHClass = thread->GetArrayInstanceHClass(receiver->GetElementsKind(), receiverIsPrototype);
9674514f5e3Sopenharmony_ci    } else if (builtinsId == BuiltinTypeId::STRING) {
9684514f5e3Sopenharmony_ci        exceptRecvHClass = receiver;
9694514f5e3Sopenharmony_ci    } else {
9704514f5e3Sopenharmony_ci        exceptRecvHClass = thread->GetBuiltinInstanceHClass(builtinsId.value());
9714514f5e3Sopenharmony_ci    }
9724514f5e3Sopenharmony_ci
9734514f5e3Sopenharmony_ci    if (exceptRecvHClass != receiver) {
9744514f5e3Sopenharmony_ci        // When JSType cannot uniquely identify builtins object, it is necessary to
9754514f5e3Sopenharmony_ci        // query the receiver on the global constants.
9764514f5e3Sopenharmony_ci        if (builtinsId == BuiltinTypeId::OBJECT) {
9774514f5e3Sopenharmony_ci            exceptRecvHClass = JSHClass::Cast(thread->GlobalConstants()->GetIteratorResultClass().GetTaggedObject());
9784514f5e3Sopenharmony_ci            if (exceptRecvHClass == receiver) {
9794514f5e3Sopenharmony_ci                GlobalIndex globalsId;
9804514f5e3Sopenharmony_ci                globalsId.UpdateGlobalConstId(static_cast<size_t>(ConstantIndex::ITERATOR_RESULT_CLASS));
9814514f5e3Sopenharmony_ci                AddBuiltinsGlobalInfo(abcId, bcOffset, globalsId);
9824514f5e3Sopenharmony_ci                return true;
9834514f5e3Sopenharmony_ci            }
9844514f5e3Sopenharmony_ci            return false;
9854514f5e3Sopenharmony_ci        }
9864514f5e3Sopenharmony_ci        return true;
9874514f5e3Sopenharmony_ci    }
9884514f5e3Sopenharmony_ci    AddBuiltinsInfo(abcId, bcOffset, receiver, receiver);
9894514f5e3Sopenharmony_ci    return true;
9904514f5e3Sopenharmony_ci}
9914514f5e3Sopenharmony_ci
9924514f5e3Sopenharmony_cibool JITProfiler::AddBuiltinsInfoByNameInProt(ApEntityId abcId, int32_t bcOffset, JSHClass *receiver, JSHClass *hold)
9934514f5e3Sopenharmony_ci{
9944514f5e3Sopenharmony_ci    auto type = receiver->GetObjectType();
9954514f5e3Sopenharmony_ci    auto builtinsId = ToBuiltinsTypeId(type);
9964514f5e3Sopenharmony_ci    if (!builtinsId.has_value()) {
9974514f5e3Sopenharmony_ci        return false;
9984514f5e3Sopenharmony_ci    }
9994514f5e3Sopenharmony_ci    auto thread = vm_->GetJSThread();
10004514f5e3Sopenharmony_ci    JSHClass *exceptRecvHClass = nullptr;
10014514f5e3Sopenharmony_ci    if (builtinsId == BuiltinTypeId::ARRAY) {
10024514f5e3Sopenharmony_ci        bool receiverIsPrototype = receiver->IsPrototype();
10034514f5e3Sopenharmony_ci        exceptRecvHClass = thread->GetArrayInstanceHClass(receiver->GetElementsKind(), receiverIsPrototype);
10044514f5e3Sopenharmony_ci    } else if (builtinsId == BuiltinTypeId::STRING) {
10054514f5e3Sopenharmony_ci        exceptRecvHClass = receiver;
10064514f5e3Sopenharmony_ci    } else {
10074514f5e3Sopenharmony_ci        exceptRecvHClass = thread->GetBuiltinInstanceHClass(builtinsId.value());
10084514f5e3Sopenharmony_ci    }
10094514f5e3Sopenharmony_ci
10104514f5e3Sopenharmony_ci    auto exceptHoldHClass = thread->GetBuiltinPrototypeHClass(builtinsId.value());
10114514f5e3Sopenharmony_ci    auto exceptPrototypeOfPrototypeHClass =
10124514f5e3Sopenharmony_ci        thread->GetBuiltinPrototypeOfPrototypeHClass(builtinsId.value());
10134514f5e3Sopenharmony_ci    // iterator needs to find two layers of prototype
10144514f5e3Sopenharmony_ci    if (builtinsId == BuiltinTypeId::ARRAY_ITERATOR) {
10154514f5e3Sopenharmony_ci        if ((exceptRecvHClass != receiver) ||
10164514f5e3Sopenharmony_ci            (exceptHoldHClass != hold && exceptPrototypeOfPrototypeHClass != hold)) {
10174514f5e3Sopenharmony_ci            return true;
10184514f5e3Sopenharmony_ci        }
10194514f5e3Sopenharmony_ci    } else if (IsTypedArrayType(builtinsId.value())) {
10204514f5e3Sopenharmony_ci        auto exceptRecvHClassOnHeap = thread->GetBuiltinExtraHClass(builtinsId.value());
10214514f5e3Sopenharmony_ci        ASSERT_PRINT(exceptRecvHClassOnHeap == nullptr || exceptRecvHClassOnHeap->IsOnHeapFromBitField(),
10224514f5e3Sopenharmony_ci                     "must be on heap");
10234514f5e3Sopenharmony_ci        if (JITProfiler::IsJSHClassNotEqual(receiver, hold, exceptRecvHClass, exceptRecvHClassOnHeap, exceptHoldHClass,
10244514f5e3Sopenharmony_ci                                            exceptPrototypeOfPrototypeHClass)) {
10254514f5e3Sopenharmony_ci            return true;
10264514f5e3Sopenharmony_ci        }
10274514f5e3Sopenharmony_ci    } else if (exceptRecvHClass != receiver || exceptHoldHClass != hold) {
10284514f5e3Sopenharmony_ci        if (builtinsId == BuiltinTypeId::OBJECT) {
10294514f5e3Sopenharmony_ci            return false;
10304514f5e3Sopenharmony_ci        } else {
10314514f5e3Sopenharmony_ci            return true;
10324514f5e3Sopenharmony_ci        }
10334514f5e3Sopenharmony_ci    }
10344514f5e3Sopenharmony_ci    AddBuiltinsInfo(abcId, bcOffset, receiver, receiver);
10354514f5e3Sopenharmony_ci    return true;
10364514f5e3Sopenharmony_ci}
10374514f5e3Sopenharmony_ci
10384514f5e3Sopenharmony_cibool JITProfiler::IsJSHClassNotEqual(JSHClass *receiver, JSHClass *hold, JSHClass *exceptRecvHClass,
10394514f5e3Sopenharmony_ci                                     JSHClass *exceptRecvHClassOnHeap, JSHClass *exceptHoldHClass,
10404514f5e3Sopenharmony_ci                                     JSHClass *exceptPrototypeOfPrototypeHClass)
10414514f5e3Sopenharmony_ci{
10424514f5e3Sopenharmony_ci    //exceptRecvHClass = IHC, exceptRecvHClassOnHeap = IHC OnHeap
10434514f5e3Sopenharmony_ci    //exceptHoldHClass = PHC, exceptPrototypeOfPrototypeHClass = HClass of X.prototype.prototype
10444514f5e3Sopenharmony_ci    return ((exceptRecvHClass != receiver && exceptRecvHClassOnHeap != receiver) ||
10454514f5e3Sopenharmony_ci            (exceptHoldHClass != hold && exceptPrototypeOfPrototypeHClass != hold));
10464514f5e3Sopenharmony_ci}
10474514f5e3Sopenharmony_ci
10484514f5e3Sopenharmony_civoid JITProfiler::Clear()
10494514f5e3Sopenharmony_ci{
10504514f5e3Sopenharmony_ci    bcOffsetPGOOpTypeMap_.clear();
10514514f5e3Sopenharmony_ci    bcOffsetPGODefOpTypeMap_.clear();
10524514f5e3Sopenharmony_ci    bcOffsetPGORwTypeMap_.clear();
10534514f5e3Sopenharmony_ci    abcId_ = 0;
10544514f5e3Sopenharmony_ci    profileTypeInfo_ = nullptr;
10554514f5e3Sopenharmony_ci    methodId_ = (EntityId)0;
10564514f5e3Sopenharmony_ci}
10574514f5e3Sopenharmony_ci
10584514f5e3Sopenharmony_ci
10594514f5e3Sopenharmony_ciJITProfiler::~JITProfiler()
10604514f5e3Sopenharmony_ci{
10614514f5e3Sopenharmony_ci}
10624514f5e3Sopenharmony_ci}
1063