14514f5e3Sopenharmony_ci/* 24514f5e3Sopenharmony_ci * Copyright (c) 2023-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 164514f5e3Sopenharmony_ci#ifndef ECMASCRIPT_PGO_PROFILER_INFO_H 174514f5e3Sopenharmony_ci#define ECMASCRIPT_PGO_PROFILER_INFO_H 184514f5e3Sopenharmony_ci 194514f5e3Sopenharmony_ci#include <cstdint> 204514f5e3Sopenharmony_ci#include <memory> 214514f5e3Sopenharmony_ci#include <sstream> 224514f5e3Sopenharmony_ci#include <unordered_map> 234514f5e3Sopenharmony_ci#include <unordered_set> 244514f5e3Sopenharmony_ci#include <utility> 254514f5e3Sopenharmony_ci#include <string.h> 264514f5e3Sopenharmony_ci 274514f5e3Sopenharmony_ci#include "ecmascript/common.h" 284514f5e3Sopenharmony_ci#include "ecmascript/jspandafile/method_literal.h" 294514f5e3Sopenharmony_ci#include "ecmascript/log_wrapper.h" 304514f5e3Sopenharmony_ci#include "ecmascript/mem/c_containers.h" 314514f5e3Sopenharmony_ci#include "ecmascript/mem/c_string.h" 324514f5e3Sopenharmony_ci#include "ecmascript/mem/chunk_containers.h" 334514f5e3Sopenharmony_ci#include "ecmascript/mem/native_area_allocator.h" 344514f5e3Sopenharmony_ci#include "ecmascript/mem/slots.h" 354514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/ap_file/pgo_file_info.h" 364514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/ap_file/pgo_method_type_set.h" 374514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/ap_file/pgo_profile_type_pool.h" 384514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/ap_file/pgo_proto_transition_type_pool.h" 394514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/ap_file/pgo_record_pool.h" 404514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/pgo_context.h" 414514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/pgo_profiler.h" 424514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/pgo_profiler_layout.h" 434514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/pgo_utils.h" 444514f5e3Sopenharmony_ci#include "ecmascript/pgo_profiler/types/pgo_profiler_type.h" 454514f5e3Sopenharmony_ci#include "ecmascript/property_attributes.h" 464514f5e3Sopenharmony_ci#include "ecmascript/ts_types/global_type_info.h" 474514f5e3Sopenharmony_ci#include "macros.h" 484514f5e3Sopenharmony_ci 494514f5e3Sopenharmony_cinamespace panda::ecmascript::pgo { 504514f5e3Sopenharmony_ciclass SaveTask; 514514f5e3Sopenharmony_ciclass PGOContext; 524514f5e3Sopenharmony_ci 534514f5e3Sopenharmony_ciclass PGOPandaFileInfos { 544514f5e3Sopenharmony_cipublic: 554514f5e3Sopenharmony_ci void Sample(uint32_t checksum) 564514f5e3Sopenharmony_ci { 574514f5e3Sopenharmony_ci fileInfos_.emplace(checksum); 584514f5e3Sopenharmony_ci } 594514f5e3Sopenharmony_ci 604514f5e3Sopenharmony_ci void Clear() 614514f5e3Sopenharmony_ci { 624514f5e3Sopenharmony_ci fileInfos_.clear(); 634514f5e3Sopenharmony_ci } 644514f5e3Sopenharmony_ci 654514f5e3Sopenharmony_ci void ParseFromBinary(void *buffer, SectionInfo *const info); 664514f5e3Sopenharmony_ci void ProcessToBinary(std::fstream &fileStream, SectionInfo *info) const; 674514f5e3Sopenharmony_ci void Merge(const PGOPandaFileInfos &pandaFileInfos); 684514f5e3Sopenharmony_ci bool VerifyChecksum(const PGOPandaFileInfos &pandaFileInfos, const std::string &base, 694514f5e3Sopenharmony_ci const std::string &incoming) const; 704514f5e3Sopenharmony_ci 714514f5e3Sopenharmony_ci void ProcessToText(std::ofstream &stream) const; 724514f5e3Sopenharmony_ci bool ParseFromText(std::ifstream &stream); 734514f5e3Sopenharmony_ci 744514f5e3Sopenharmony_ci bool Checksum(uint32_t checksum) const; 754514f5e3Sopenharmony_ci 764514f5e3Sopenharmony_ciprivate: 774514f5e3Sopenharmony_ci class FileInfo { 784514f5e3Sopenharmony_ci public: 794514f5e3Sopenharmony_ci FileInfo() = default; 804514f5e3Sopenharmony_ci FileInfo(uint32_t checksum) : size_(LastSize()), checksum_(checksum) {} 814514f5e3Sopenharmony_ci 824514f5e3Sopenharmony_ci static size_t LastSize() 834514f5e3Sopenharmony_ci { 844514f5e3Sopenharmony_ci return sizeof(FileInfo); 854514f5e3Sopenharmony_ci } 864514f5e3Sopenharmony_ci 874514f5e3Sopenharmony_ci size_t Size() const 884514f5e3Sopenharmony_ci { 894514f5e3Sopenharmony_ci return static_cast<size_t>(size_); 904514f5e3Sopenharmony_ci } 914514f5e3Sopenharmony_ci 924514f5e3Sopenharmony_ci bool operator<(const FileInfo &right) const 934514f5e3Sopenharmony_ci { 944514f5e3Sopenharmony_ci return checksum_ < right.checksum_; 954514f5e3Sopenharmony_ci } 964514f5e3Sopenharmony_ci 974514f5e3Sopenharmony_ci uint32_t GetChecksum() const 984514f5e3Sopenharmony_ci { 994514f5e3Sopenharmony_ci return checksum_; 1004514f5e3Sopenharmony_ci } 1014514f5e3Sopenharmony_ci 1024514f5e3Sopenharmony_ci private: 1034514f5e3Sopenharmony_ci // Support extended fields 1044514f5e3Sopenharmony_ci uint32_t size_; 1054514f5e3Sopenharmony_ci uint32_t checksum_; 1064514f5e3Sopenharmony_ci }; 1074514f5e3Sopenharmony_ci 1084514f5e3Sopenharmony_ci std::set<FileInfo> fileInfos_; 1094514f5e3Sopenharmony_ci}; 1104514f5e3Sopenharmony_ci 1114514f5e3Sopenharmony_ciclass PGOMethodInfo { 1124514f5e3Sopenharmony_cipublic: 1134514f5e3Sopenharmony_ci static constexpr int METHOD_INFO_COUNT = 4; 1144514f5e3Sopenharmony_ci static constexpr int METHOD_ID_INDEX = 0; 1154514f5e3Sopenharmony_ci static constexpr int METHOD_COUNT_INDEX = 1; 1164514f5e3Sopenharmony_ci static constexpr int METHOD_MODE_INDEX = 2; 1174514f5e3Sopenharmony_ci static constexpr int METHOD_NAME_INDEX = 3; 1184514f5e3Sopenharmony_ci static constexpr uint32_t METHOD_MAX_HIT_COUNT = 10000U; 1194514f5e3Sopenharmony_ci 1204514f5e3Sopenharmony_ci explicit PGOMethodInfo(PGOMethodId id) : id_(id) {} 1214514f5e3Sopenharmony_ci 1224514f5e3Sopenharmony_ci PGOMethodInfo(PGOMethodId id, uint32_t count, SampleMode mode, const char *methodName) 1234514f5e3Sopenharmony_ci : id_(id), count_(count), mode_(mode) 1244514f5e3Sopenharmony_ci { 1254514f5e3Sopenharmony_ci size_t len = strlen(methodName); 1264514f5e3Sopenharmony_ci size_ = static_cast<uint32_t>(Size(len)); 1274514f5e3Sopenharmony_ci if (len > 0 && memcpy_s(&methodName_, len, methodName, len) != EOK) { 1284514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "SetMethodName memcpy_s failed" << methodName << ", len = " << len; 1294514f5e3Sopenharmony_ci UNREACHABLE(); 1304514f5e3Sopenharmony_ci } 1314514f5e3Sopenharmony_ci *(&methodName_ + len) = '\0'; 1324514f5e3Sopenharmony_ci } 1334514f5e3Sopenharmony_ci 1344514f5e3Sopenharmony_ci static uint32_t PUBLIC_API CalcChecksum(const char *name, const uint8_t *byteCodeArray, uint32_t byteCodeLength); 1354514f5e3Sopenharmony_ci 1364514f5e3Sopenharmony_ci static uint32_t CalcOpCodeChecksum(const uint8_t *byteCodeArray, uint32_t byteCodeLength); 1374514f5e3Sopenharmony_ci 1384514f5e3Sopenharmony_ci static int32_t Size(uint32_t length) 1394514f5e3Sopenharmony_ci { 1404514f5e3Sopenharmony_ci return sizeof(PGOMethodInfo) + AlignUp(length, GetAlignmentInBytes(ALIGN_SIZE)); 1414514f5e3Sopenharmony_ci } 1424514f5e3Sopenharmony_ci 1434514f5e3Sopenharmony_ci int32_t Size() const 1444514f5e3Sopenharmony_ci { 1454514f5e3Sopenharmony_ci return size_; 1464514f5e3Sopenharmony_ci } 1474514f5e3Sopenharmony_ci 1484514f5e3Sopenharmony_ci static bool GetSampleMode(std::string content, SampleMode &mode) 1494514f5e3Sopenharmony_ci { 1504514f5e3Sopenharmony_ci if (content == "HOTNESS_MODE") { 1514514f5e3Sopenharmony_ci mode = SampleMode::HOTNESS_MODE; 1524514f5e3Sopenharmony_ci } else if (content == "CALL_MODE") { 1534514f5e3Sopenharmony_ci mode = SampleMode::CALL_MODE; 1544514f5e3Sopenharmony_ci } else { 1554514f5e3Sopenharmony_ci return false; 1564514f5e3Sopenharmony_ci } 1574514f5e3Sopenharmony_ci return true; 1584514f5e3Sopenharmony_ci } 1594514f5e3Sopenharmony_ci 1604514f5e3Sopenharmony_ci void IncreaseCount() 1614514f5e3Sopenharmony_ci { 1624514f5e3Sopenharmony_ci count_++; 1634514f5e3Sopenharmony_ci } 1644514f5e3Sopenharmony_ci 1654514f5e3Sopenharmony_ci void ClearCount() 1664514f5e3Sopenharmony_ci { 1674514f5e3Sopenharmony_ci count_ = 0; 1684514f5e3Sopenharmony_ci } 1694514f5e3Sopenharmony_ci 1704514f5e3Sopenharmony_ci void Merge(const PGOMethodInfo *info) 1714514f5e3Sopenharmony_ci { 1724514f5e3Sopenharmony_ci if (!(id_ == info->GetMethodId())) { 1734514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "The method id must same for merging"; 1744514f5e3Sopenharmony_ci return; 1754514f5e3Sopenharmony_ci } 1764514f5e3Sopenharmony_ci count_ = std::min(count_ + info->GetCount(), METHOD_MAX_HIT_COUNT); 1774514f5e3Sopenharmony_ci SetSampleMode(info->GetSampleMode()); 1784514f5e3Sopenharmony_ci } 1794514f5e3Sopenharmony_ci 1804514f5e3Sopenharmony_ci PGOMethodId GetMethodId() const 1814514f5e3Sopenharmony_ci { 1824514f5e3Sopenharmony_ci return id_; 1834514f5e3Sopenharmony_ci } 1844514f5e3Sopenharmony_ci 1854514f5e3Sopenharmony_ci uint32_t GetCount() const 1864514f5e3Sopenharmony_ci { 1874514f5e3Sopenharmony_ci return count_; 1884514f5e3Sopenharmony_ci } 1894514f5e3Sopenharmony_ci 1904514f5e3Sopenharmony_ci const char *GetMethodName() const 1914514f5e3Sopenharmony_ci { 1924514f5e3Sopenharmony_ci return &methodName_; 1934514f5e3Sopenharmony_ci } 1944514f5e3Sopenharmony_ci 1954514f5e3Sopenharmony_ci void SetSampleMode(SampleMode mode) 1964514f5e3Sopenharmony_ci { 1974514f5e3Sopenharmony_ci if (mode_ == SampleMode::HOTNESS_MODE) { 1984514f5e3Sopenharmony_ci return; 1994514f5e3Sopenharmony_ci } 2004514f5e3Sopenharmony_ci mode_ = mode; 2014514f5e3Sopenharmony_ci } 2024514f5e3Sopenharmony_ci 2034514f5e3Sopenharmony_ci SampleMode GetSampleMode() const 2044514f5e3Sopenharmony_ci { 2054514f5e3Sopenharmony_ci return mode_; 2064514f5e3Sopenharmony_ci } 2074514f5e3Sopenharmony_ci 2084514f5e3Sopenharmony_ci std::string GetSampleModeToString() const 2094514f5e3Sopenharmony_ci { 2104514f5e3Sopenharmony_ci std::string result; 2114514f5e3Sopenharmony_ci switch (mode_) { 2124514f5e3Sopenharmony_ci case SampleMode::HOTNESS_MODE: 2134514f5e3Sopenharmony_ci result = "HOTNESS_MODE"; 2144514f5e3Sopenharmony_ci break; 2154514f5e3Sopenharmony_ci case SampleMode::CALL_MODE: 2164514f5e3Sopenharmony_ci result = "CALL_MODE"; 2174514f5e3Sopenharmony_ci break; 2184514f5e3Sopenharmony_ci default: 2194514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "mode error"; 2204514f5e3Sopenharmony_ci } 2214514f5e3Sopenharmony_ci return result; 2224514f5e3Sopenharmony_ci } 2234514f5e3Sopenharmony_ci 2244514f5e3Sopenharmony_ci bool IsFilter(uint32_t threshold) const 2254514f5e3Sopenharmony_ci { 2264514f5e3Sopenharmony_ci if (count_ < threshold && mode_ == SampleMode::CALL_MODE) { 2274514f5e3Sopenharmony_ci return true; 2284514f5e3Sopenharmony_ci } 2294514f5e3Sopenharmony_ci return false; 2304514f5e3Sopenharmony_ci } 2314514f5e3Sopenharmony_ci 2324514f5e3Sopenharmony_ci void ParseFromBinary(void **buffer); 2334514f5e3Sopenharmony_ci void ProcessToBinary(std::ofstream &fileStream) const; 2344514f5e3Sopenharmony_ci 2354514f5e3Sopenharmony_ci static std::vector<std::string> ParseFromText(const std::string &infoString); 2364514f5e3Sopenharmony_ci void ProcessToText(std::string &text) const; 2374514f5e3Sopenharmony_ci 2384514f5e3Sopenharmony_ci void ProcessToJson(ProfileType::VariantMap &function) const; 2394514f5e3Sopenharmony_ci 2404514f5e3Sopenharmony_ci NO_COPY_SEMANTIC(PGOMethodInfo); 2414514f5e3Sopenharmony_ci NO_MOVE_SEMANTIC(PGOMethodInfo); 2424514f5e3Sopenharmony_ci 2434514f5e3Sopenharmony_ciprivate: 2444514f5e3Sopenharmony_ci uint32_t size_ {0}; 2454514f5e3Sopenharmony_ci PGOMethodId id_; 2464514f5e3Sopenharmony_ci uint32_t count_ {0}; 2474514f5e3Sopenharmony_ci SampleMode mode_ {SampleMode::CALL_MODE}; 2484514f5e3Sopenharmony_ci char methodName_ {0}; 2494514f5e3Sopenharmony_ci}; 2504514f5e3Sopenharmony_ci 2514514f5e3Sopenharmony_ciclass PGODecodeMethodInfo { 2524514f5e3Sopenharmony_cipublic: 2534514f5e3Sopenharmony_ci explicit PGODecodeMethodInfo(PGOMethodId id) : methodId_(id) {} 2544514f5e3Sopenharmony_ci 2554514f5e3Sopenharmony_ci PGOMethodId GetMethodId() const 2564514f5e3Sopenharmony_ci { 2574514f5e3Sopenharmony_ci return methodId_; 2584514f5e3Sopenharmony_ci } 2594514f5e3Sopenharmony_ci 2604514f5e3Sopenharmony_ci PGOMethodTypeSet &GetPGOMethodTypeSet() 2614514f5e3Sopenharmony_ci { 2624514f5e3Sopenharmony_ci return pgoMethodTypeSet_; 2634514f5e3Sopenharmony_ci } 2644514f5e3Sopenharmony_ci 2654514f5e3Sopenharmony_ci void Merge(const PGODecodeMethodInfo &from); 2664514f5e3Sopenharmony_ci 2674514f5e3Sopenharmony_ciprivate: 2684514f5e3Sopenharmony_ci PGOMethodId methodId_ {0}; 2694514f5e3Sopenharmony_ci PGOMethodTypeSet pgoMethodTypeSet_ {}; 2704514f5e3Sopenharmony_ci}; 2714514f5e3Sopenharmony_ci 2724514f5e3Sopenharmony_ciclass PGOMethodInfoMap { 2734514f5e3Sopenharmony_cipublic: 2744514f5e3Sopenharmony_ci PGOMethodInfoMap() = default; 2754514f5e3Sopenharmony_ci 2764514f5e3Sopenharmony_ci void Clear() 2774514f5e3Sopenharmony_ci { 2784514f5e3Sopenharmony_ci // PGOMethodInfo release by chunk 2794514f5e3Sopenharmony_ci for (auto &entry : methodTypeInfos_) { 2804514f5e3Sopenharmony_ci entry.second->Clear(); 2814514f5e3Sopenharmony_ci } 2824514f5e3Sopenharmony_ci methodInfos_.clear(); 2834514f5e3Sopenharmony_ci methodTypeInfos_.clear(); 2844514f5e3Sopenharmony_ci } 2854514f5e3Sopenharmony_ci 2864514f5e3Sopenharmony_ci bool AddMethod(Chunk *chunk, Method *jsMethod, SampleMode mode); 2874514f5e3Sopenharmony_ci bool AddType(Chunk *chunk, PGOMethodId methodId, int32_t offset, PGOSampleType type); 2884514f5e3Sopenharmony_ci bool AddCallTargetType(Chunk *chunk, PGOMethodId methodId, int32_t offset, PGOSampleType type); 2894514f5e3Sopenharmony_ci bool AddObjectInfo(Chunk *chunk, PGOMethodId methodId, int32_t offset, const PGOObjectInfo &info); 2904514f5e3Sopenharmony_ci bool AddDefine(Chunk *chunk, PGOMethodId methodId, int32_t offset, PGODefineOpType type); 2914514f5e3Sopenharmony_ci void Merge(Chunk *chunk, PGOMethodInfoMap *methodInfos); 2924514f5e3Sopenharmony_ci 2934514f5e3Sopenharmony_ci bool ParseFromBinary(Chunk *chunk, PGOContext &context, void **buffer); 2944514f5e3Sopenharmony_ci bool ProcessToBinary(PGOContext &context, ProfileTypeRef recordProfileRef, const SaveTask *task, 2954514f5e3Sopenharmony_ci std::fstream &fileStream, PGOProfilerHeader *const header) const; 2964514f5e3Sopenharmony_ci 2974514f5e3Sopenharmony_ci bool ParseFromText(Chunk *chunk, uint32_t threshold, const std::vector<std::string> &content); 2984514f5e3Sopenharmony_ci void ProcessToText(uint32_t threshold, const CString &recordName, std::ofstream &stream) const; 2994514f5e3Sopenharmony_ci 3004514f5e3Sopenharmony_ci void ProcessToJson(uint32_t threshold, ProfileType::jModuleType &jModule) const; 3014514f5e3Sopenharmony_ci 3024514f5e3Sopenharmony_ci const CMap<PGOMethodId, PGOMethodInfo *> &GetMethodInfos() const 3034514f5e3Sopenharmony_ci { 3044514f5e3Sopenharmony_ci return methodInfos_; 3054514f5e3Sopenharmony_ci } 3064514f5e3Sopenharmony_ci 3074514f5e3Sopenharmony_ci NO_COPY_SEMANTIC(PGOMethodInfoMap); 3084514f5e3Sopenharmony_ci NO_MOVE_SEMANTIC(PGOMethodInfoMap); 3094514f5e3Sopenharmony_ci 3104514f5e3Sopenharmony_ciprivate: 3114514f5e3Sopenharmony_ci PGOMethodTypeSet *GetOrInsertMethodTypeSet(Chunk *chunk, PGOMethodId methodId); 3124514f5e3Sopenharmony_ci 3134514f5e3Sopenharmony_ci CMap<PGOMethodId, PGOMethodInfo *> methodInfos_; 3144514f5e3Sopenharmony_ci CMap<PGOMethodId, PGOMethodTypeSet *> methodTypeInfos_; 3154514f5e3Sopenharmony_ci CMap<PGOMethodId, uint32_t> methodsChecksum_; 3164514f5e3Sopenharmony_ci CMap<PGOSampleType, CMap<CString, TrackType>> globalLayoutDescInfos_; 3174514f5e3Sopenharmony_ci}; 3184514f5e3Sopenharmony_ci 3194514f5e3Sopenharmony_ciclass PGOMethodIdSet { 3204514f5e3Sopenharmony_cipublic: 3214514f5e3Sopenharmony_ci explicit PGOMethodIdSet(Chunk* chunk): chunk_(chunk), methodInfoMap_(chunk) {}; 3224514f5e3Sopenharmony_ci ~PGOMethodIdSet() = default; 3234514f5e3Sopenharmony_ci 3244514f5e3Sopenharmony_ci void Clear() 3254514f5e3Sopenharmony_ci { 3264514f5e3Sopenharmony_ci candidateSet_.clear(); 3274514f5e3Sopenharmony_ci for (auto &methodNameSet : methodInfoMap_) { 3284514f5e3Sopenharmony_ci methodNameSet.second.Clear(); 3294514f5e3Sopenharmony_ci } 3304514f5e3Sopenharmony_ci methodInfoMap_.clear(); 3314514f5e3Sopenharmony_ci } 3324514f5e3Sopenharmony_ci 3334514f5e3Sopenharmony_ci bool Match(EntityId methodId) 3344514f5e3Sopenharmony_ci { 3354514f5e3Sopenharmony_ci return candidateSet_.find(methodId) != candidateSet_.end(); 3364514f5e3Sopenharmony_ci } 3374514f5e3Sopenharmony_ci 3384514f5e3Sopenharmony_ci template <typename Callback> 3394514f5e3Sopenharmony_ci bool Update(const CString &recordName, Callback callback) 3404514f5e3Sopenharmony_ci { 3414514f5e3Sopenharmony_ci std::unordered_set<EntityId> newIds = callback(recordName, candidateSet_); 3424514f5e3Sopenharmony_ci if (!newIds.empty()) { 3434514f5e3Sopenharmony_ci candidateSet_.insert(newIds.begin(), newIds.end()); 3444514f5e3Sopenharmony_ci return true; 3454514f5e3Sopenharmony_ci } 3464514f5e3Sopenharmony_ci return false; 3474514f5e3Sopenharmony_ci } 3484514f5e3Sopenharmony_ci 3494514f5e3Sopenharmony_ci template <typename Callback> 3504514f5e3Sopenharmony_ci void GetTypeInfo(const char *methodName, Callback callback) 3514514f5e3Sopenharmony_ci { 3524514f5e3Sopenharmony_ci // for no function checksum in ap file 3534514f5e3Sopenharmony_ci auto iter = methodInfoMap_.find(methodName); 3544514f5e3Sopenharmony_ci if ((iter != methodInfoMap_.end()) && (iter->second.GetFirstMethodInfo() != nullptr)) { 3554514f5e3Sopenharmony_ci iter->second.GetFirstMethodInfo()->GetPGOMethodTypeSet().GetTypeInfo(callback); 3564514f5e3Sopenharmony_ci } 3574514f5e3Sopenharmony_ci } 3584514f5e3Sopenharmony_ci 3594514f5e3Sopenharmony_ci template <typename Callback> 3604514f5e3Sopenharmony_ci void GetTypeInfo(const char *methodName, uint32_t checksum, Callback callback) 3614514f5e3Sopenharmony_ci { 3624514f5e3Sopenharmony_ci auto iter = methodInfoMap_.find(methodName); 3634514f5e3Sopenharmony_ci if ((iter != methodInfoMap_.end()) && (iter->second.GetMethodInfo(checksum) != nullptr)) { 3644514f5e3Sopenharmony_ci return iter->second.GetMethodInfo(checksum)->GetPGOMethodTypeSet().GetTypeInfo(callback); 3654514f5e3Sopenharmony_ci } 3664514f5e3Sopenharmony_ci LOG_ECMA(DEBUG) << "Method checksum mismatched, name: " << methodName; 3674514f5e3Sopenharmony_ci } 3684514f5e3Sopenharmony_ci 3694514f5e3Sopenharmony_ci void MatchAndMarkMethod(const char *methodName, EntityId methodId) 3704514f5e3Sopenharmony_ci { 3714514f5e3Sopenharmony_ci const auto &iter = methodInfoMap_.find(methodName); 3724514f5e3Sopenharmony_ci if (iter == methodInfoMap_.end()) { 3734514f5e3Sopenharmony_ci // no matching method in PGO file. 3744514f5e3Sopenharmony_ci return; 3754514f5e3Sopenharmony_ci } 3764514f5e3Sopenharmony_ci candidateSet_.emplace(methodId); 3774514f5e3Sopenharmony_ci iter->second.SetMatch(); 3784514f5e3Sopenharmony_ci } 3794514f5e3Sopenharmony_ci 3804514f5e3Sopenharmony_ci bool ParseFromBinary(PGOContext &context, void **buffer); 3814514f5e3Sopenharmony_ci 3824514f5e3Sopenharmony_ci void GetMismatchResult(const CString &recordName, uint32_t &totalMethodCount, uint32_t &mismatchMethodCount, 3834514f5e3Sopenharmony_ci std::set<std::pair<std::string, CString>> &mismatchMethodSet) const; 3844514f5e3Sopenharmony_ci 3854514f5e3Sopenharmony_ci void Merge(const PGOMethodIdSet &from); 3864514f5e3Sopenharmony_ci 3874514f5e3Sopenharmony_ci class PGOMethodNameSet { 3884514f5e3Sopenharmony_ci public: 3894514f5e3Sopenharmony_ci explicit PGOMethodNameSet(Chunk* chunk): methodMap_(chunk) {}; 3904514f5e3Sopenharmony_ci void SetMatch() 3914514f5e3Sopenharmony_ci { 3924514f5e3Sopenharmony_ci methodNameMatch_ = true; 3934514f5e3Sopenharmony_ci } 3944514f5e3Sopenharmony_ci 3954514f5e3Sopenharmony_ci bool IsMatch() const 3964514f5e3Sopenharmony_ci { 3974514f5e3Sopenharmony_ci return methodNameMatch_; 3984514f5e3Sopenharmony_ci } 3994514f5e3Sopenharmony_ci 4004514f5e3Sopenharmony_ci PGODecodeMethodInfo& GetOrCreateMethodInfo(uint32_t checksum, PGOMethodId methodId) 4014514f5e3Sopenharmony_ci { 4024514f5e3Sopenharmony_ci auto methodIter = methodMap_.find(checksum); 4034514f5e3Sopenharmony_ci if (methodIter == methodMap_.end()) { 4044514f5e3Sopenharmony_ci auto ret = methodMap_.emplace(checksum, methodId); 4054514f5e3Sopenharmony_ci ASSERT(ret.second); 4064514f5e3Sopenharmony_ci methodIter = ret.first; 4074514f5e3Sopenharmony_ci } 4084514f5e3Sopenharmony_ci return methodIter->second; 4094514f5e3Sopenharmony_ci } 4104514f5e3Sopenharmony_ci 4114514f5e3Sopenharmony_ci void Merge(const PGOMethodNameSet &from) 4124514f5e3Sopenharmony_ci { 4134514f5e3Sopenharmony_ci for (const auto &method : from.methodMap_) { 4144514f5e3Sopenharmony_ci uint32_t checksum = method.first; 4154514f5e3Sopenharmony_ci auto methodInfo = methodMap_.find(checksum); 4164514f5e3Sopenharmony_ci if (methodInfo == methodMap_.end()) { 4174514f5e3Sopenharmony_ci auto ret = methodMap_.emplace(checksum, method.second.GetMethodId()); 4184514f5e3Sopenharmony_ci ASSERT(ret.second); 4194514f5e3Sopenharmony_ci methodInfo = ret.first; 4204514f5e3Sopenharmony_ci } 4214514f5e3Sopenharmony_ci methodInfo->second.Merge(method.second); 4224514f5e3Sopenharmony_ci } 4234514f5e3Sopenharmony_ci } 4244514f5e3Sopenharmony_ci 4254514f5e3Sopenharmony_ci PGODecodeMethodInfo *GetFirstMethodInfo() 4264514f5e3Sopenharmony_ci { 4274514f5e3Sopenharmony_ci if (methodMap_.empty()) { 4284514f5e3Sopenharmony_ci return nullptr; 4294514f5e3Sopenharmony_ci } 4304514f5e3Sopenharmony_ci return &(methodMap_.begin()->second); 4314514f5e3Sopenharmony_ci } 4324514f5e3Sopenharmony_ci 4334514f5e3Sopenharmony_ci PGODecodeMethodInfo *GetMethodInfo(uint32_t checksum) 4344514f5e3Sopenharmony_ci { 4354514f5e3Sopenharmony_ci auto methodInfo = methodMap_.find(checksum); 4364514f5e3Sopenharmony_ci if (methodInfo == methodMap_.end()) { 4374514f5e3Sopenharmony_ci return nullptr; 4384514f5e3Sopenharmony_ci } 4394514f5e3Sopenharmony_ci return &(methodInfo->second); 4404514f5e3Sopenharmony_ci } 4414514f5e3Sopenharmony_ci 4424514f5e3Sopenharmony_ci void Clear() 4434514f5e3Sopenharmony_ci { 4444514f5e3Sopenharmony_ci methodMap_.clear(); 4454514f5e3Sopenharmony_ci } 4464514f5e3Sopenharmony_ci 4474514f5e3Sopenharmony_ci private: 4484514f5e3Sopenharmony_ci bool methodNameMatch_ {false}; 4494514f5e3Sopenharmony_ci ChunkUnorderedMap<uint32_t, PGODecodeMethodInfo> methodMap_; 4504514f5e3Sopenharmony_ci }; 4514514f5e3Sopenharmony_ci 4524514f5e3Sopenharmony_ci NO_COPY_SEMANTIC(PGOMethodIdSet); 4534514f5e3Sopenharmony_ci NO_MOVE_SEMANTIC(PGOMethodIdSet); 4544514f5e3Sopenharmony_ci 4554514f5e3Sopenharmony_ciprivate: 4564514f5e3Sopenharmony_ci Chunk* chunk_; 4574514f5e3Sopenharmony_ci std::unordered_set<EntityId> candidateSet_; // methodId in abc file, DO NOT for pgo internal use 4584514f5e3Sopenharmony_ci ChunkUnorderedMap<CString, PGOMethodNameSet> methodInfoMap_; 4594514f5e3Sopenharmony_ci}; 4604514f5e3Sopenharmony_ci 4614514f5e3Sopenharmony_ciclass PGORecordDetailInfos : public PGOContext { 4624514f5e3Sopenharmony_cipublic: 4634514f5e3Sopenharmony_ci explicit PGORecordDetailInfos(uint32_t hotnessThreshold); 4644514f5e3Sopenharmony_ci 4654514f5e3Sopenharmony_ci ~PGORecordDetailInfos() override; 4664514f5e3Sopenharmony_ci 4674514f5e3Sopenharmony_ci void Clear(); 4684514f5e3Sopenharmony_ci void InitSections(); 4694514f5e3Sopenharmony_ci 4704514f5e3Sopenharmony_ci // If it is a new method, return true. 4714514f5e3Sopenharmony_ci bool AddMethod(ProfileType recordProfileType, Method *jsMethod, SampleMode mode); 4724514f5e3Sopenharmony_ci bool AddType(ProfileType recordProfileType, PGOMethodId methodId, int32_t offset, PGOSampleType type); 4734514f5e3Sopenharmony_ci bool AddCallTargetType(ProfileType recordProfileType, PGOMethodId methodId, int32_t offset, PGOSampleType type); 4744514f5e3Sopenharmony_ci bool AddObjectInfo(ProfileType recordProfileType, PGOMethodId methodId, int32_t offset, const PGOObjectInfo &info); 4754514f5e3Sopenharmony_ci bool AddDefine(ProfileType recordProfileType, PGOMethodId methodId, int32_t offset, PGODefineOpType type); 4764514f5e3Sopenharmony_ci 4774514f5e3Sopenharmony_ci bool AddRwUseInfo(ProfileType rootType); 4784514f5e3Sopenharmony_ci bool AddRootLayout(JSTaggedType hclass, ProfileType rootType); 4794514f5e3Sopenharmony_ci bool UpdateTransitionLayout( 4804514f5e3Sopenharmony_ci ProfileType rootType, JSTaggedType parent, ProfileType parentType, JSTaggedType child, ProfileType childType); 4814514f5e3Sopenharmony_ci bool UpdateLayout(ProfileType rootType, JSTaggedType hclass, ProfileType curType); 4824514f5e3Sopenharmony_ci void AddRootPtType(ProfileType rootType, ProfileType ptType); 4834514f5e3Sopenharmony_ci bool IsDumped(ProfileType rootType, ProfileType curType) const; 4844514f5e3Sopenharmony_ci 4854514f5e3Sopenharmony_ci void Merge(const PGORecordDetailInfos &recordInfos); 4864514f5e3Sopenharmony_ci 4874514f5e3Sopenharmony_ci void UpdateLayout(); 4884514f5e3Sopenharmony_ci 4894514f5e3Sopenharmony_ci bool ParseFromBinary(void *buffer, PGOProfilerHeader *const header); 4904514f5e3Sopenharmony_ci void ProcessToBinary(const SaveTask *task, std::fstream &fileStream, PGOProfilerHeader *const header); 4914514f5e3Sopenharmony_ci 4924514f5e3Sopenharmony_ci bool ParseFromText(std::ifstream &stream); 4934514f5e3Sopenharmony_ci void ProcessToText(std::ofstream &stream) const; 4944514f5e3Sopenharmony_ci 4954514f5e3Sopenharmony_ci const CMap<ProfileType, PGOMethodInfoMap *> &GetRecordInfos() const 4964514f5e3Sopenharmony_ci { 4974514f5e3Sopenharmony_ci return recordInfos_; 4984514f5e3Sopenharmony_ci } 4994514f5e3Sopenharmony_ci 5004514f5e3Sopenharmony_ci std::shared_ptr<PGORecordPool> GetRecordPool() const 5014514f5e3Sopenharmony_ci { 5024514f5e3Sopenharmony_ci return recordPool_; 5034514f5e3Sopenharmony_ci } 5044514f5e3Sopenharmony_ci 5054514f5e3Sopenharmony_ci std::shared_ptr<PGOProfileTypePool> GetProfileTypePool() const override 5064514f5e3Sopenharmony_ci { 5074514f5e3Sopenharmony_ci return profileTypePool_; 5084514f5e3Sopenharmony_ci } 5094514f5e3Sopenharmony_ci 5104514f5e3Sopenharmony_ci std::shared_ptr<PGOProtoTransitionPool> GetProtoTransitionPool() const 5114514f5e3Sopenharmony_ci { 5124514f5e3Sopenharmony_ci return protoTransitionPool_; 5134514f5e3Sopenharmony_ci } 5144514f5e3Sopenharmony_ci 5154514f5e3Sopenharmony_ci uint32_t GetHotnessThreshold() const override 5164514f5e3Sopenharmony_ci { 5174514f5e3Sopenharmony_ci return hotnessThreshold_; 5184514f5e3Sopenharmony_ci } 5194514f5e3Sopenharmony_ci 5204514f5e3Sopenharmony_ci PGOProfilerHeader *GetHeader() const override 5214514f5e3Sopenharmony_ci { 5224514f5e3Sopenharmony_ci return header_; 5234514f5e3Sopenharmony_ci } 5244514f5e3Sopenharmony_ci 5254514f5e3Sopenharmony_ci bool SupportElementsKind() const override 5264514f5e3Sopenharmony_ci { 5274514f5e3Sopenharmony_ci ASSERT(header_ != nullptr); 5284514f5e3Sopenharmony_ci return header_->SupportElementsKind(); 5294514f5e3Sopenharmony_ci } 5304514f5e3Sopenharmony_ci 5314514f5e3Sopenharmony_ci bool SupportElementsTrackInfo() const override 5324514f5e3Sopenharmony_ci { 5334514f5e3Sopenharmony_ci ASSERT(header_ != nullptr); 5344514f5e3Sopenharmony_ci return header_->SupportElementsTrackInfo(); 5354514f5e3Sopenharmony_ci } 5364514f5e3Sopenharmony_ci 5374514f5e3Sopenharmony_ci void ResetAbcIdRemap() const override 5384514f5e3Sopenharmony_ci { 5394514f5e3Sopenharmony_ci abcIdRemap_.clear(); 5404514f5e3Sopenharmony_ci } 5414514f5e3Sopenharmony_ci 5424514f5e3Sopenharmony_ci void AddAbcIdRemap(ApEntityId oldId, ApEntityId newId) const override 5434514f5e3Sopenharmony_ci { 5444514f5e3Sopenharmony_ci abcIdRemap_[oldId] = newId; 5454514f5e3Sopenharmony_ci } 5464514f5e3Sopenharmony_ci 5474514f5e3Sopenharmony_ci const std::map<ApEntityId, ApEntityId> &GetAbcIdRemap() const override 5484514f5e3Sopenharmony_ci { 5494514f5e3Sopenharmony_ci return abcIdRemap_; 5504514f5e3Sopenharmony_ci } 5514514f5e3Sopenharmony_ci 5524514f5e3Sopenharmony_ci NO_COPY_SEMANTIC(PGORecordDetailInfos); 5534514f5e3Sopenharmony_ci NO_MOVE_SEMANTIC(PGORecordDetailInfos); 5544514f5e3Sopenharmony_ci 5554514f5e3Sopenharmony_ciprivate: 5564514f5e3Sopenharmony_ci PGOMethodInfoMap *GetMethodInfoMap(ProfileType recordProfileType); 5574514f5e3Sopenharmony_ci bool ParseFromBinaryForLayout(void **buffer); 5584514f5e3Sopenharmony_ci bool ProcessToBinaryForLayout(NativeAreaAllocator *allocator, const SaveTask *task, std::fstream &stream); 5594514f5e3Sopenharmony_ci 5604514f5e3Sopenharmony_ci uint32_t hotnessThreshold_ {2}; 5614514f5e3Sopenharmony_ci NativeAreaAllocator nativeAreaAllocator_; 5624514f5e3Sopenharmony_ci std::unique_ptr<Chunk> chunk_; 5634514f5e3Sopenharmony_ci CMap<ProfileType, PGOMethodInfoMap *> recordInfos_; 5644514f5e3Sopenharmony_ci std::set<PGOHClassTreeDesc> hclassTreeDescInfos_; 5654514f5e3Sopenharmony_ci PGOProfilerHeader *header_ {nullptr}; 5664514f5e3Sopenharmony_ci std::shared_ptr<PGORecordPool> recordPool_; 5674514f5e3Sopenharmony_ci std::shared_ptr<PGOProtoTransitionPool> protoTransitionPool_; 5684514f5e3Sopenharmony_ci std::shared_ptr<PGOProfileTypePool> profileTypePool_; 5694514f5e3Sopenharmony_ci mutable std::map<ApEntityId, ApEntityId> abcIdRemap_; 5704514f5e3Sopenharmony_ci}; 5714514f5e3Sopenharmony_ci 5724514f5e3Sopenharmony_ciclass PGORecordSimpleInfos : public PGOContext { 5734514f5e3Sopenharmony_cipublic: 5744514f5e3Sopenharmony_ci explicit PGORecordSimpleInfos(uint32_t threshold); 5754514f5e3Sopenharmony_ci 5764514f5e3Sopenharmony_ci ~PGORecordSimpleInfos() override; 5774514f5e3Sopenharmony_ci 5784514f5e3Sopenharmony_ci void Clear(); 5794514f5e3Sopenharmony_ci 5804514f5e3Sopenharmony_ci void InitSections(); 5814514f5e3Sopenharmony_ci 5824514f5e3Sopenharmony_ci bool Match(const CString &abcNormalizedDesc, const CString &recordName, EntityId methodId); 5834514f5e3Sopenharmony_ci 5844514f5e3Sopenharmony_ci template <typename Callback> 5854514f5e3Sopenharmony_ci void Update(const CString &abcNormalizedDesc, Callback callback) 5864514f5e3Sopenharmony_ci { 5874514f5e3Sopenharmony_ci auto abcMethodIds = methodIds_.find(abcNormalizedDesc); 5884514f5e3Sopenharmony_ci if (abcMethodIds == methodIds_.end()) { 5894514f5e3Sopenharmony_ci return; 5904514f5e3Sopenharmony_ci } 5914514f5e3Sopenharmony_ci for (auto iter = abcMethodIds->second.begin(); iter != abcMethodIds->second.end(); iter++) { 5924514f5e3Sopenharmony_ci auto recordName = iter->first; 5934514f5e3Sopenharmony_ci auto methodIds = iter->second; 5944514f5e3Sopenharmony_ci methodIds->Update(recordName, callback); 5954514f5e3Sopenharmony_ci } 5964514f5e3Sopenharmony_ci } 5974514f5e3Sopenharmony_ci 5984514f5e3Sopenharmony_ci template <typename Callback> 5994514f5e3Sopenharmony_ci void Update(const CString &abcNormalizedDesc, const CString &recordName, Callback callback) 6004514f5e3Sopenharmony_ci { 6014514f5e3Sopenharmony_ci auto abcMethodIds = methodIds_.find(abcNormalizedDesc); 6024514f5e3Sopenharmony_ci if (abcMethodIds == methodIds_.end()) { 6034514f5e3Sopenharmony_ci return; 6044514f5e3Sopenharmony_ci } 6054514f5e3Sopenharmony_ci auto iter = abcMethodIds->second.find(recordName); 6064514f5e3Sopenharmony_ci if (iter != abcMethodIds->second.end()) { 6074514f5e3Sopenharmony_ci iter->second->Update(recordName, callback); 6084514f5e3Sopenharmony_ci } else { 6094514f5e3Sopenharmony_ci PGOMethodIdSet *methodIdSet = nativeAreaAllocator_.New<PGOMethodIdSet>(chunk_.get()); 6104514f5e3Sopenharmony_ci if (methodIdSet->Update(recordName, callback)) { 6114514f5e3Sopenharmony_ci abcMethodIds->second.emplace(recordName, methodIdSet); 6124514f5e3Sopenharmony_ci } else { 6134514f5e3Sopenharmony_ci nativeAreaAllocator_.Delete(methodIdSet); 6144514f5e3Sopenharmony_ci } 6154514f5e3Sopenharmony_ci } 6164514f5e3Sopenharmony_ci } 6174514f5e3Sopenharmony_ci 6184514f5e3Sopenharmony_ci template <typename Callback> 6194514f5e3Sopenharmony_ci void GetTypeInfo(const CString &abcNormalizedDesc, const CString &recordName, const char *methodName, 6204514f5e3Sopenharmony_ci Callback callback) 6214514f5e3Sopenharmony_ci { 6224514f5e3Sopenharmony_ci auto abcMethodIds = methodIds_.find(abcNormalizedDesc); 6234514f5e3Sopenharmony_ci if (abcMethodIds == methodIds_.end()) { 6244514f5e3Sopenharmony_ci return; 6254514f5e3Sopenharmony_ci } 6264514f5e3Sopenharmony_ci auto iter = abcMethodIds->second.find(recordName); 6274514f5e3Sopenharmony_ci if (iter != abcMethodIds->second.end()) { 6284514f5e3Sopenharmony_ci iter->second->GetTypeInfo(methodName, callback); 6294514f5e3Sopenharmony_ci } 6304514f5e3Sopenharmony_ci } 6314514f5e3Sopenharmony_ci 6324514f5e3Sopenharmony_ci template <typename Callback> 6334514f5e3Sopenharmony_ci void GetTypeInfo(const CString &abcNormalizedDesc, const CString &recordName, const char *methodName, 6344514f5e3Sopenharmony_ci uint32_t checksum, Callback callback) 6354514f5e3Sopenharmony_ci { 6364514f5e3Sopenharmony_ci auto abcMethodIds = methodIds_.find(abcNormalizedDesc); 6374514f5e3Sopenharmony_ci if (abcMethodIds == methodIds_.end()) { 6384514f5e3Sopenharmony_ci return; 6394514f5e3Sopenharmony_ci } 6404514f5e3Sopenharmony_ci auto iter = abcMethodIds->second.find(recordName); 6414514f5e3Sopenharmony_ci if (iter != abcMethodIds->second.end()) { 6424514f5e3Sopenharmony_ci iter->second->GetTypeInfo(methodName, checksum, callback); 6434514f5e3Sopenharmony_ci } 6444514f5e3Sopenharmony_ci } 6454514f5e3Sopenharmony_ci 6464514f5e3Sopenharmony_ci std::shared_ptr<PGOProtoTransitionPool> GetProtoTransitionPool() const 6474514f5e3Sopenharmony_ci { 6484514f5e3Sopenharmony_ci return protoTransitionPool_; 6494514f5e3Sopenharmony_ci } 6504514f5e3Sopenharmony_ci 6514514f5e3Sopenharmony_ci bool GetHClassTreeDesc(PGOSampleType profileType, PGOHClassTreeDesc **desc) const 6524514f5e3Sopenharmony_ci { 6534514f5e3Sopenharmony_ci auto iter = hclassTreeDescInfos_.find(PGOHClassTreeDesc(profileType.GetProfileType())); 6544514f5e3Sopenharmony_ci if (iter != hclassTreeDescInfos_.end()) { 6554514f5e3Sopenharmony_ci *desc = &(const_cast<PGOHClassTreeDesc &>(*iter)); 6564514f5e3Sopenharmony_ci return true; 6574514f5e3Sopenharmony_ci } 6584514f5e3Sopenharmony_ci return false; 6594514f5e3Sopenharmony_ci } 6604514f5e3Sopenharmony_ci 6614514f5e3Sopenharmony_ci template <typename Callback> 6624514f5e3Sopenharmony_ci bool IterateHClassTreeDesc(Callback callback) const 6634514f5e3Sopenharmony_ci { 6644514f5e3Sopenharmony_ci for (auto treeDescInfo : hclassTreeDescInfos_) { 6654514f5e3Sopenharmony_ci callback(&treeDescInfo); 6664514f5e3Sopenharmony_ci } 6674514f5e3Sopenharmony_ci return true; 6684514f5e3Sopenharmony_ci } 6694514f5e3Sopenharmony_ci 6704514f5e3Sopenharmony_ci template <typename Callback> 6714514f5e3Sopenharmony_ci bool IterateProtoTransitionPool(Callback callback) const 6724514f5e3Sopenharmony_ci { 6734514f5e3Sopenharmony_ci protoTransitionPool_->Iterate(callback); 6744514f5e3Sopenharmony_ci return true; 6754514f5e3Sopenharmony_ci } 6764514f5e3Sopenharmony_ci 6774514f5e3Sopenharmony_ci void MatchAndMarkMethod(const CString &abcNormalizedDesc, const CString &recordName, const char *methodName, 6784514f5e3Sopenharmony_ci EntityId methodId) 6794514f5e3Sopenharmony_ci { 6804514f5e3Sopenharmony_ci auto abcMethodIds = methodIds_.find(abcNormalizedDesc); 6814514f5e3Sopenharmony_ci if (abcMethodIds == methodIds_.end()) { 6824514f5e3Sopenharmony_ci return; 6834514f5e3Sopenharmony_ci } 6844514f5e3Sopenharmony_ci auto iter = abcMethodIds->second.find(recordName); 6854514f5e3Sopenharmony_ci if (iter != abcMethodIds->second.end()) { 6864514f5e3Sopenharmony_ci return iter->second->MatchAndMarkMethod(methodName, methodId); 6874514f5e3Sopenharmony_ci } 6884514f5e3Sopenharmony_ci } 6894514f5e3Sopenharmony_ci 6904514f5e3Sopenharmony_ci void GetMismatchResult(const CString &abcNormalizedDesc, uint32_t &totalMethodCount, uint32_t &mismatchMethodCount, 6914514f5e3Sopenharmony_ci std::set<std::pair<std::string, CString>> &mismatchMethodSet) const 6924514f5e3Sopenharmony_ci { 6934514f5e3Sopenharmony_ci auto abcMethodIds = methodIds_.find(abcNormalizedDesc); 6944514f5e3Sopenharmony_ci if (abcMethodIds == methodIds_.end()) { 6954514f5e3Sopenharmony_ci return; 6964514f5e3Sopenharmony_ci } 6974514f5e3Sopenharmony_ci for (const auto &methodId : abcMethodIds->second) { 6984514f5e3Sopenharmony_ci methodId.second->GetMismatchResult(methodId.first, totalMethodCount, mismatchMethodCount, 6994514f5e3Sopenharmony_ci mismatchMethodSet); 7004514f5e3Sopenharmony_ci } 7014514f5e3Sopenharmony_ci } 7024514f5e3Sopenharmony_ci 7034514f5e3Sopenharmony_ci void ParseFromBinary(void *buffer, PGOProfilerHeader *const header, std::shared_ptr<PGOAbcFilePool> &abcFilePool); 7044514f5e3Sopenharmony_ci 7054514f5e3Sopenharmony_ci void Merge(const PGORecordSimpleInfos &simpleInfos); 7064514f5e3Sopenharmony_ci 7074514f5e3Sopenharmony_ci std::shared_ptr<PGOProfileTypePool> GetProfileTypePool() const override 7084514f5e3Sopenharmony_ci { 7094514f5e3Sopenharmony_ci return profileTypePool_; 7104514f5e3Sopenharmony_ci } 7114514f5e3Sopenharmony_ci 7124514f5e3Sopenharmony_ci uint32_t GetHotnessThreshold() const override 7134514f5e3Sopenharmony_ci { 7144514f5e3Sopenharmony_ci return hotnessThreshold_; 7154514f5e3Sopenharmony_ci } 7164514f5e3Sopenharmony_ci 7174514f5e3Sopenharmony_ci PGOProfilerHeader *GetHeader() const override 7184514f5e3Sopenharmony_ci { 7194514f5e3Sopenharmony_ci return header_; 7204514f5e3Sopenharmony_ci } 7214514f5e3Sopenharmony_ci 7224514f5e3Sopenharmony_ci bool SupportElementsKind() const override 7234514f5e3Sopenharmony_ci { 7244514f5e3Sopenharmony_ci ASSERT(header_ != nullptr); 7254514f5e3Sopenharmony_ci return header_->SupportElementsKind(); 7264514f5e3Sopenharmony_ci } 7274514f5e3Sopenharmony_ci 7284514f5e3Sopenharmony_ci bool SupportElementsTrackInfo() const override 7294514f5e3Sopenharmony_ci { 7304514f5e3Sopenharmony_ci ASSERT(header_ != nullptr); 7314514f5e3Sopenharmony_ci return header_->SupportElementsTrackInfo(); 7324514f5e3Sopenharmony_ci } 7334514f5e3Sopenharmony_ci 7344514f5e3Sopenharmony_ci void ResetAbcIdRemap() const override 7354514f5e3Sopenharmony_ci { 7364514f5e3Sopenharmony_ci abcIdRemap_.clear(); 7374514f5e3Sopenharmony_ci } 7384514f5e3Sopenharmony_ci 7394514f5e3Sopenharmony_ci const std::map<ApEntityId, ApEntityId> &GetAbcIdRemap() const override 7404514f5e3Sopenharmony_ci { 7414514f5e3Sopenharmony_ci return abcIdRemap_; 7424514f5e3Sopenharmony_ci } 7434514f5e3Sopenharmony_ci 7444514f5e3Sopenharmony_ci void AddAbcIdRemap(ApEntityId oldId, ApEntityId newId) const override 7454514f5e3Sopenharmony_ci { 7464514f5e3Sopenharmony_ci abcIdRemap_[oldId] = newId; 7474514f5e3Sopenharmony_ci } 7484514f5e3Sopenharmony_ci 7494514f5e3Sopenharmony_ci NO_COPY_SEMANTIC(PGORecordSimpleInfos); 7504514f5e3Sopenharmony_ci NO_MOVE_SEMANTIC(PGORecordSimpleInfos); 7514514f5e3Sopenharmony_ci 7524514f5e3Sopenharmony_ciprivate: 7534514f5e3Sopenharmony_ci bool ParseFromBinaryForLayout(void **buffer); 7544514f5e3Sopenharmony_ci 7554514f5e3Sopenharmony_ci uint32_t hotnessThreshold_ {2}; 7564514f5e3Sopenharmony_ci NativeAreaAllocator nativeAreaAllocator_; 7574514f5e3Sopenharmony_ci std::unique_ptr<Chunk> chunk_; 7584514f5e3Sopenharmony_ci CUnorderedMap<CString, CUnorderedMap<CString, PGOMethodIdSet *>> methodIds_; 7594514f5e3Sopenharmony_ci PGOProfilerHeader *header_ {nullptr}; 7604514f5e3Sopenharmony_ci // std::list<std::weak_ptr<PGOFileSectionInterface>> apSectionList_; 7614514f5e3Sopenharmony_ci std::shared_ptr<PGORecordPool> recordPool_; 7624514f5e3Sopenharmony_ci std::shared_ptr<PGOProtoTransitionPool> protoTransitionPool_; 7634514f5e3Sopenharmony_ci std::shared_ptr<PGOProfileTypePool> profileTypePool_; 7644514f5e3Sopenharmony_ci std::set<PGOHClassTreeDesc> hclassTreeDescInfos_; 7654514f5e3Sopenharmony_ci mutable std::map<ApEntityId, ApEntityId> abcIdRemap_; 7664514f5e3Sopenharmony_ci}; 7674514f5e3Sopenharmony_ci} // namespace panda::ecmascript::pgo 7684514f5e3Sopenharmony_ci#endif // ECMASCRIPT_PGO_PROFILER_INFO_H 769