14514f5e3Sopenharmony_ci/* 24514f5e3Sopenharmony_ci * Copyright (c) 2021-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#include <semaphore.h> 174514f5e3Sopenharmony_ci#include "ecmascript/napi/include/dfx_jsnapi.h" 184514f5e3Sopenharmony_ci 194514f5e3Sopenharmony_ci#include "ecmascript/base/block_hook_scope.h" 204514f5e3Sopenharmony_ci#include "ecmascript/builtins/builtins_ark_tools.h" 214514f5e3Sopenharmony_ci#include "ecmascript/checkpoint/thread_state_transition.h" 224514f5e3Sopenharmony_ci#include "ecmascript/debugger/debugger_api.h" 234514f5e3Sopenharmony_ci#include "ecmascript/debugger/js_debugger_manager.h" 244514f5e3Sopenharmony_ci#include "ecmascript/dfx/stackinfo/js_stackinfo.h" 254514f5e3Sopenharmony_ci#include "ecmascript/dfx/tracing/tracing.h" 264514f5e3Sopenharmony_ci#include "ecmascript/mem/heap-inl.h" 274514f5e3Sopenharmony_ci#include "ecmascript/jit/jit.h" 284514f5e3Sopenharmony_ci#include "ecmascript/dfx/vm_thread_control.h" 294514f5e3Sopenharmony_ci 304514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 314514f5e3Sopenharmony_ci#include "ecmascript/dfx/cpu_profiler/cpu_profiler.h" 324514f5e3Sopenharmony_ci#include "ecmascript/dfx/cpu_profiler/samples_record.h" 334514f5e3Sopenharmony_ci#endif 344514f5e3Sopenharmony_ci#if defined(ENABLE_DUMP_IN_FAULTLOG) 354514f5e3Sopenharmony_ci#include "faultloggerd_client.h" 364514f5e3Sopenharmony_ci#include "uv.h" 374514f5e3Sopenharmony_ci#endif 384514f5e3Sopenharmony_ci 394514f5e3Sopenharmony_cinamespace panda { 404514f5e3Sopenharmony_ciusing ecmascript::CString; 414514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 424514f5e3Sopenharmony_ciusing BuiltinsArkTools = ecmascript::builtins::BuiltinsArkTools; 434514f5e3Sopenharmony_ciusing ecmascript::CpuProfiler; 444514f5e3Sopenharmony_ci#endif 454514f5e3Sopenharmony_ciusing ecmascript::EcmaString; 464514f5e3Sopenharmony_ciusing ecmascript::JSTaggedValue; 474514f5e3Sopenharmony_ciusing ecmascript::GCStats; 484514f5e3Sopenharmony_citemplate<typename T> 494514f5e3Sopenharmony_ciusing JSHandle = ecmascript::JSHandle<T>; 504514f5e3Sopenharmony_ciusing ecmascript::FileStream; 514514f5e3Sopenharmony_ciusing ecmascript::FileDescriptorStream; 524514f5e3Sopenharmony_ciusing ecmascript::CMap; 534514f5e3Sopenharmony_ciusing ecmascript::Tracing; 544514f5e3Sopenharmony_ciusing ecmascript::DumpSnapShotOption; 554514f5e3Sopenharmony_cisem_t g_heapdumpCnt; 564514f5e3Sopenharmony_ci 574514f5e3Sopenharmony_civoid DFXJSNApi::DumpHeapSnapshot([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] const std::string &path, 584514f5e3Sopenharmony_ci [[maybe_unused]] const DumpSnapShotOption &dumpOption) 594514f5e3Sopenharmony_ci{ 604514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 614514f5e3Sopenharmony_ci FileStream stream(path); 624514f5e3Sopenharmony_ci DumpHeapSnapshot(vm, &stream, dumpOption); 634514f5e3Sopenharmony_ci#else 644514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap snapshot"; 654514f5e3Sopenharmony_ci#endif 664514f5e3Sopenharmony_ci} 674514f5e3Sopenharmony_ci 684514f5e3Sopenharmony_ci// IDE interface. 694514f5e3Sopenharmony_civoid DFXJSNApi::DumpHeapSnapshot([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] Stream *stream, 704514f5e3Sopenharmony_ci [[maybe_unused]] const DumpSnapShotOption &dumpOption, 714514f5e3Sopenharmony_ci [[maybe_unused]] Progress *progress) 724514f5e3Sopenharmony_ci{ 734514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 744514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 754514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 764514f5e3Sopenharmony_ci heapProfile->DumpHeapSnapshot(stream, dumpOption, progress); 774514f5e3Sopenharmony_ci#else 784514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap snapshot"; 794514f5e3Sopenharmony_ci#endif 804514f5e3Sopenharmony_ci} 814514f5e3Sopenharmony_ci 824514f5e3Sopenharmony_ci[[maybe_unused]] static uint8_t killCount = 0; 834514f5e3Sopenharmony_ci 844514f5e3Sopenharmony_civoid DFXJSNApi::DumpCpuProfile([[maybe_unused]] const EcmaVM *vm) 854514f5e3Sopenharmony_ci{ 864514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 874514f5e3Sopenharmony_ci#if defined(ENABLE_DUMP_IN_FAULTLOG) 884514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 894514f5e3Sopenharmony_ci // for CpuProfiler kill contral 904514f5e3Sopenharmony_ci if (DFXJSNApi::StopCpuProfilerForColdStart(vm)) { 914514f5e3Sopenharmony_ci return; 924514f5e3Sopenharmony_ci } 934514f5e3Sopenharmony_ci 944514f5e3Sopenharmony_ci (void)killCount; 954514f5e3Sopenharmony_ci if (DFXJSNApi::CpuProfilerSamplingAnyTime(vm)) { 964514f5e3Sopenharmony_ci killCount++; 974514f5e3Sopenharmony_ci return; 984514f5e3Sopenharmony_ci } 994514f5e3Sopenharmony_ci#endif // ECMASCRIPT_SUPPORT_CPUPROFILER 1004514f5e3Sopenharmony_ci#endif // ENABLE_DUMP_IN_FAULTLOG 1014514f5e3Sopenharmony_ci#endif // ECMASCRIPT_SUPPORT_SNAPSHOT 1024514f5e3Sopenharmony_ci} 1034514f5e3Sopenharmony_ci 1044514f5e3Sopenharmony_ci// kill -39. 1054514f5e3Sopenharmony_civoid DFXJSNApi::DumpHeapSnapshot([[maybe_unused]] const EcmaVM *vm, 1064514f5e3Sopenharmony_ci [[maybe_unused]] const DumpSnapShotOption &dumpOption) 1074514f5e3Sopenharmony_ci{ 1084514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 1094514f5e3Sopenharmony_ci#if defined(ENABLE_DUMP_IN_FAULTLOG) 1104514f5e3Sopenharmony_ci sem_wait(&g_heapdumpCnt); 1114514f5e3Sopenharmony_ci auto &options = const_cast<EcmaVM *>(vm)->GetJSOptions(); 1124514f5e3Sopenharmony_ci options.SwitchStartGlobalLeakCheck(); 1134514f5e3Sopenharmony_ci if (options.EnableGlobalLeakCheck() && options.IsStartGlobalLeakCheck()) { 1144514f5e3Sopenharmony_ci int32_t stackTraceFd = RequestFileDescriptor(static_cast<int32_t>(FaultLoggerType::JS_STACKTRACE)); 1154514f5e3Sopenharmony_ci if (stackTraceFd < 0) { 1164514f5e3Sopenharmony_ci options.SwitchStartGlobalLeakCheck(); 1174514f5e3Sopenharmony_ci } else { 1184514f5e3Sopenharmony_ci vm->GetJSThread()->SetStackTraceFd(stackTraceFd); 1194514f5e3Sopenharmony_ci } 1204514f5e3Sopenharmony_ci } 1214514f5e3Sopenharmony_ci 1224514f5e3Sopenharmony_ci // Write in faultlog for heap leak. 1234514f5e3Sopenharmony_ci int32_t fd; 1244514f5e3Sopenharmony_ci if (dumpOption.isDumpOOM && dumpOption.dumpFormat == DumpFormat::BINARY) { 1254514f5e3Sopenharmony_ci fd = RequestFileDescriptor(static_cast<int32_t>(FaultLoggerType::JS_RAW_SNAPSHOT)); 1264514f5e3Sopenharmony_ci } else { 1274514f5e3Sopenharmony_ci fd = RequestFileDescriptor(static_cast<int32_t>(FaultLoggerType::JS_HEAP_SNAPSHOT)); 1284514f5e3Sopenharmony_ci } 1294514f5e3Sopenharmony_ci if (fd < 0) { 1304514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Write FD failed, fd" << fd; 1314514f5e3Sopenharmony_ci return; 1324514f5e3Sopenharmony_ci } 1334514f5e3Sopenharmony_ci FileDescriptorStream stream(fd); 1344514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 1354514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 1364514f5e3Sopenharmony_ci heapProfile->DumpHeapSnapshot(&stream, dumpOption); 1374514f5e3Sopenharmony_ci 1384514f5e3Sopenharmony_ci sem_post(&g_heapdumpCnt); 1394514f5e3Sopenharmony_ci#endif // ENABLE_DUMP_IN_FAULTLOG 1404514f5e3Sopenharmony_ci#else 1414514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap snapshot"; 1424514f5e3Sopenharmony_ci#endif // ECMASCRIPT_SUPPORT_SNAPSHOT 1434514f5e3Sopenharmony_ci} 1444514f5e3Sopenharmony_ci 1454514f5e3Sopenharmony_ci// tid = 0: dump all vm; tid != 0: dump tid vm, hidumper. 1464514f5e3Sopenharmony_civoid DFXJSNApi::DumpHeapSnapshot([[maybe_unused]] const EcmaVM *vm, 1474514f5e3Sopenharmony_ci [[maybe_unused]] const DumpSnapShotOption &dumpOption, [[maybe_unused]] uint32_t tid) 1484514f5e3Sopenharmony_ci{ 1494514f5e3Sopenharmony_ci const int THREAD_COUNT = 1; 1504514f5e3Sopenharmony_ci if (vm->IsWorkerThread()) { 1514514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "this is a workthread!"; 1524514f5e3Sopenharmony_ci return; 1534514f5e3Sopenharmony_ci } 1544514f5e3Sopenharmony_ci sem_init(&g_heapdumpCnt, 0, THREAD_COUNT); 1554514f5e3Sopenharmony_ci uint32_t curTid = vm->GetTid(); 1564514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "DumpHeapSnapshot tid " << tid << " curTid " << curTid; 1574514f5e3Sopenharmony_ci DumpHeapSnapshotWithVm(vm, dumpOption, tid); 1584514f5e3Sopenharmony_ci} 1594514f5e3Sopenharmony_ci 1604514f5e3Sopenharmony_civoid DFXJSNApi::DumpHeapSnapshotWithVm([[maybe_unused]] const EcmaVM *vm, 1614514f5e3Sopenharmony_ci [[maybe_unused]] const DumpSnapShotOption &dumpOption, 1624514f5e3Sopenharmony_ci [[maybe_unused]] uint32_t tid) 1634514f5e3Sopenharmony_ci{ 1644514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 1654514f5e3Sopenharmony_ci#if defined(ENABLE_DUMP_IN_FAULTLOG) 1664514f5e3Sopenharmony_ci uv_loop_t *loop = reinterpret_cast<uv_loop_t *>(vm->GetLoop()); 1674514f5e3Sopenharmony_ci if (loop == nullptr || uv_loop_alive(loop) == 0) { 1684514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "loop nullptr or uv_loop_alive dead"; 1694514f5e3Sopenharmony_ci return; 1704514f5e3Sopenharmony_ci } 1714514f5e3Sopenharmony_ci struct DumpForSnapShotStruct *dumpStruct = new DumpForSnapShotStruct(); 1724514f5e3Sopenharmony_ci dumpStruct->vm = vm; 1734514f5e3Sopenharmony_ci dumpStruct->dumpOption = dumpOption; 1744514f5e3Sopenharmony_ci uv_work_t *work = new(std::nothrow) uv_work_t; 1754514f5e3Sopenharmony_ci if (work == nullptr) { 1764514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "work nullptr"; 1774514f5e3Sopenharmony_ci delete dumpStruct; 1784514f5e3Sopenharmony_ci return; 1794514f5e3Sopenharmony_ci } 1804514f5e3Sopenharmony_ci work->data = static_cast<void *>(dumpStruct); 1814514f5e3Sopenharmony_ci 1824514f5e3Sopenharmony_ci uint32_t curTid = vm->GetTid(); 1834514f5e3Sopenharmony_ci int ret = 0; 1844514f5e3Sopenharmony_ci if (tid == 0 || tid == curTid) { 1854514f5e3Sopenharmony_ci ret = uv_queue_work(loop, work, [](uv_work_t *) {}, [](uv_work_t *work, int32_t) { 1864514f5e3Sopenharmony_ci struct DumpForSnapShotStruct *dump = static_cast<struct DumpForSnapShotStruct *>(work->data); 1874514f5e3Sopenharmony_ci DFXJSNApi::GetHeapPrepare(dump->vm); 1884514f5e3Sopenharmony_ci DumpSnapShotOption dumpOption = dump->dumpOption; 1894514f5e3Sopenharmony_ci DumpHeapSnapshot(dump->vm, dumpOption); 1904514f5e3Sopenharmony_ci delete dump; 1914514f5e3Sopenharmony_ci delete work; 1924514f5e3Sopenharmony_ci }); 1934514f5e3Sopenharmony_ci } else { 1944514f5e3Sopenharmony_ci delete dumpStruct; 1954514f5e3Sopenharmony_ci delete work; 1964514f5e3Sopenharmony_ci } 1974514f5e3Sopenharmony_ci 1984514f5e3Sopenharmony_ci // dump worker vm 1994514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->EnumerateWorkerVm([&](const EcmaVM *workerVm) -> void { 2004514f5e3Sopenharmony_ci uint32_t curTid = workerVm->GetTid(); 2014514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "DumpHeapSnapshot workthread curTid " << curTid; 2024514f5e3Sopenharmony_ci DumpHeapSnapshotWithVm(workerVm, dumpOption, tid); 2034514f5e3Sopenharmony_ci return; 2044514f5e3Sopenharmony_ci }); 2054514f5e3Sopenharmony_ci 2064514f5e3Sopenharmony_ci if (ret != 0) { 2074514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "uv_queue_work fail ret " << ret; 2084514f5e3Sopenharmony_ci delete dumpStruct; 2094514f5e3Sopenharmony_ci delete work; 2104514f5e3Sopenharmony_ci } 2114514f5e3Sopenharmony_ci#endif 2124514f5e3Sopenharmony_ci#endif 2134514f5e3Sopenharmony_ci} 2144514f5e3Sopenharmony_ci 2154514f5e3Sopenharmony_civoid DFXJSNApi::GenerateHeapSnapshotByBinFile([[maybe_unused]] const EcmaVM *vm, 2164514f5e3Sopenharmony_ci [[maybe_unused]] std::string &inputFilePath, 2174514f5e3Sopenharmony_ci [[maybe_unused]] std::string &outputPath) 2184514f5e3Sopenharmony_ci{ 2194514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 2204514f5e3Sopenharmony_ci auto *heapProfile = ecmascript::HeapProfilerInterface::GetInstance(const_cast<EcmaVM *>(vm)); 2214514f5e3Sopenharmony_ci heapProfile->GenerateHeapSnapshot(inputFilePath, outputPath); 2224514f5e3Sopenharmony_ci#else 2234514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support GenerateHeapSnapshotByBinFile"; 2244514f5e3Sopenharmony_ci#endif // ECMASCRIPT_SUPPORT_SNAPSHOT 2254514f5e3Sopenharmony_ci} 2264514f5e3Sopenharmony_ci 2274514f5e3Sopenharmony_ci// tid = 0: TriggerGC all vm; tid != 0: TriggerGC tid vm 2284514f5e3Sopenharmony_civoid DFXJSNApi::TriggerGC([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] uint32_t tid) 2294514f5e3Sopenharmony_ci{ 2304514f5e3Sopenharmony_ci if (vm->IsWorkerThread()) { 2314514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "this is a workthread!"; 2324514f5e3Sopenharmony_ci return; 2334514f5e3Sopenharmony_ci } 2344514f5e3Sopenharmony_ci // triggerGC host vm 2354514f5e3Sopenharmony_ci uint32_t curTid = vm->GetTid(); 2364514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "TriggerGC tid " << tid << " curTid " << curTid; 2374514f5e3Sopenharmony_ci if (tid == 0 || tid == curTid) { 2384514f5e3Sopenharmony_ci TriggerGCWithVm(vm); 2394514f5e3Sopenharmony_ci } 2404514f5e3Sopenharmony_ci // triggerGC worker vm 2414514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->EnumerateWorkerVm([&](const EcmaVM *workerVm) -> void { 2424514f5e3Sopenharmony_ci curTid = workerVm->GetTid(); 2434514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "TriggerGC tid " << tid << " curTid " << curTid; 2444514f5e3Sopenharmony_ci if (tid == 0 || tid == curTid) { 2454514f5e3Sopenharmony_ci TriggerGCWithVm(workerVm); 2464514f5e3Sopenharmony_ci return; 2474514f5e3Sopenharmony_ci } 2484514f5e3Sopenharmony_ci }); 2494514f5e3Sopenharmony_ci // triggerSharedFullGC 2504514f5e3Sopenharmony_ci TriggerSharedGCWithVm(vm); 2514514f5e3Sopenharmony_ci} 2524514f5e3Sopenharmony_ci 2534514f5e3Sopenharmony_civoid DFXJSNApi::TriggerSharedGCWithVm([[maybe_unused]] const EcmaVM *vm) 2544514f5e3Sopenharmony_ci{ 2554514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 2564514f5e3Sopenharmony_ci#if defined(ENABLE_DUMP_IN_FAULTLOG) 2574514f5e3Sopenharmony_ci uv_loop_t *loop = reinterpret_cast<uv_loop_t *>(vm->GetLoop()); 2584514f5e3Sopenharmony_ci if (loop == nullptr) { 2594514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "loop nullptr"; 2604514f5e3Sopenharmony_ci return; 2614514f5e3Sopenharmony_ci } 2624514f5e3Sopenharmony_ci if (uv_loop_alive(loop) == 0) { 2634514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "uv_loop_alive dead"; 2644514f5e3Sopenharmony_ci return; 2654514f5e3Sopenharmony_ci } 2664514f5e3Sopenharmony_ci uv_work_t *work = new(std::nothrow) uv_work_t; 2674514f5e3Sopenharmony_ci if (work == nullptr) { 2684514f5e3Sopenharmony_ci LOG_ECMA(FATAL) << "DFXJSNApi::TriggerGCWithVm:work is nullptr"; 2694514f5e3Sopenharmony_ci return; 2704514f5e3Sopenharmony_ci } 2714514f5e3Sopenharmony_ci work->data = static_cast<void *>(const_cast<EcmaVM *>(vm)); 2724514f5e3Sopenharmony_ci int ret = uv_queue_work(loop, work, [](uv_work_t *) {}, [](uv_work_t *work, int32_t) { 2734514f5e3Sopenharmony_ci EcmaVM *vm = static_cast<EcmaVM *>(work->data); 2744514f5e3Sopenharmony_ci ecmascript::SharedHeap* sHeap = ecmascript::SharedHeap::GetInstance(); 2754514f5e3Sopenharmony_ci JSThread *thread = vm->GetJSThread(); 2764514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(thread); 2774514f5e3Sopenharmony_ci sHeap->CollectGarbage<ecmascript::TriggerGCType::SHARED_FULL_GC, 2784514f5e3Sopenharmony_ci ecmascript::GCReason::TRIGGER_BY_MEM_TOOLS>(thread); 2794514f5e3Sopenharmony_ci delete work; 2804514f5e3Sopenharmony_ci }); 2814514f5e3Sopenharmony_ci if (ret != 0) { 2824514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "uv_queue_work fail ret " << ret; 2834514f5e3Sopenharmony_ci delete work; 2844514f5e3Sopenharmony_ci } 2854514f5e3Sopenharmony_ci#endif 2864514f5e3Sopenharmony_ci#endif 2874514f5e3Sopenharmony_ci} 2884514f5e3Sopenharmony_ci 2894514f5e3Sopenharmony_civoid DFXJSNApi::TriggerGCWithVm([[maybe_unused]] const EcmaVM *vm) 2904514f5e3Sopenharmony_ci{ 2914514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 2924514f5e3Sopenharmony_ci#if defined(ENABLE_DUMP_IN_FAULTLOG) 2934514f5e3Sopenharmony_ci uv_loop_t *loop = reinterpret_cast<uv_loop_t *>(vm->GetLoop()); 2944514f5e3Sopenharmony_ci if (loop == nullptr) { 2954514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "loop nullptr"; 2964514f5e3Sopenharmony_ci return; 2974514f5e3Sopenharmony_ci } 2984514f5e3Sopenharmony_ci if (uv_loop_alive(loop) == 0) { 2994514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "uv_loop_alive dead"; 3004514f5e3Sopenharmony_ci return; 3014514f5e3Sopenharmony_ci } 3024514f5e3Sopenharmony_ci uv_work_t *work = new(std::nothrow) uv_work_t; 3034514f5e3Sopenharmony_ci if (work == nullptr) { 3044514f5e3Sopenharmony_ci LOG_ECMA(FATAL) << "DFXJSNApi::TriggerGCWithVm:work is nullptr"; 3054514f5e3Sopenharmony_ci return; 3064514f5e3Sopenharmony_ci } 3074514f5e3Sopenharmony_ci work->data = static_cast<void *>(const_cast<EcmaVM *>(vm)); 3084514f5e3Sopenharmony_ci int ret = uv_queue_work(loop, work, [](uv_work_t *) {}, [](uv_work_t *work, int32_t) { 3094514f5e3Sopenharmony_ci EcmaVM *vm = static_cast<EcmaVM *>(work->data); 3104514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 3114514f5e3Sopenharmony_ci vm->CollectGarbage(ecmascript::TriggerGCType::FULL_GC, ecmascript::GCReason::TRIGGER_BY_MEM_TOOLS); 3124514f5e3Sopenharmony_ci delete work; 3134514f5e3Sopenharmony_ci }); 3144514f5e3Sopenharmony_ci if (ret != 0) { 3154514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "uv_queue_work fail ret " << ret; 3164514f5e3Sopenharmony_ci delete work; 3174514f5e3Sopenharmony_ci } 3184514f5e3Sopenharmony_ci#endif 3194514f5e3Sopenharmony_ci#endif 3204514f5e3Sopenharmony_ci} 3214514f5e3Sopenharmony_ci 3224514f5e3Sopenharmony_civoid DFXJSNApi::DestroyHeapProfiler([[maybe_unused]] const EcmaVM *vm) 3234514f5e3Sopenharmony_ci{ 3244514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 3254514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 3264514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface::Destroy(const_cast<EcmaVM *>(vm)); 3274514f5e3Sopenharmony_ci#else 3284514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap snapshot"; 3294514f5e3Sopenharmony_ci#endif 3304514f5e3Sopenharmony_ci} 3314514f5e3Sopenharmony_ci 3324514f5e3Sopenharmony_cibool DFXJSNApi::BuildNativeAndJsStackTrace(const EcmaVM *vm, std::string &stackTraceStr) 3334514f5e3Sopenharmony_ci{ 3344514f5e3Sopenharmony_ci stackTraceStr = ecmascript::JsStackInfo::BuildJsStackTrace(vm->GetAssociatedJSThread(), true); 3354514f5e3Sopenharmony_ci if (stackTraceStr.empty()) { 3364514f5e3Sopenharmony_ci return false; 3374514f5e3Sopenharmony_ci } 3384514f5e3Sopenharmony_ci return true; 3394514f5e3Sopenharmony_ci} 3404514f5e3Sopenharmony_ci 3414514f5e3Sopenharmony_cibool DFXJSNApi::BuildJsStackTrace(const EcmaVM *vm, std::string &stackTraceStr) 3424514f5e3Sopenharmony_ci{ 3434514f5e3Sopenharmony_ci stackTraceStr = ecmascript::JsStackInfo::BuildJsStackTrace(vm->GetAssociatedJSThread(), false); 3444514f5e3Sopenharmony_ci if (stackTraceStr.empty()) { 3454514f5e3Sopenharmony_ci return false; 3464514f5e3Sopenharmony_ci } 3474514f5e3Sopenharmony_ci return true; 3484514f5e3Sopenharmony_ci} 3494514f5e3Sopenharmony_ci 3504514f5e3Sopenharmony_cibool DFXJSNApi::StartHeapTracking([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] double timeInterval, 3514514f5e3Sopenharmony_ci [[maybe_unused]] bool isVmMode, [[maybe_unused]] Stream *stream, 3524514f5e3Sopenharmony_ci [[maybe_unused]] bool traceAllocation, [[maybe_unused]] bool newThread) 3534514f5e3Sopenharmony_ci{ 3544514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 3554514f5e3Sopenharmony_ci ecmascript::base::BlockHookScope blockScope; 3564514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 3574514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 3584514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 3594514f5e3Sopenharmony_ci return heapProfile->StartHeapTracking(timeInterval, isVmMode, stream, traceAllocation, newThread); 3604514f5e3Sopenharmony_ci#else 3614514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap tracking"; 3624514f5e3Sopenharmony_ci return false; 3634514f5e3Sopenharmony_ci#endif 3644514f5e3Sopenharmony_ci} 3654514f5e3Sopenharmony_ci 3664514f5e3Sopenharmony_cibool DFXJSNApi::UpdateHeapTracking([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] Stream *stream) 3674514f5e3Sopenharmony_ci{ 3684514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 3694514f5e3Sopenharmony_ci ecmascript::base::BlockHookScope blockScope; 3704514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 3714514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 3724514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 3734514f5e3Sopenharmony_ci return heapProfile->UpdateHeapTracking(stream); 3744514f5e3Sopenharmony_ci#else 3754514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap tracking"; 3764514f5e3Sopenharmony_ci return false; 3774514f5e3Sopenharmony_ci#endif 3784514f5e3Sopenharmony_ci} 3794514f5e3Sopenharmony_ci 3804514f5e3Sopenharmony_cibool DFXJSNApi::StopHeapTracking([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] const std::string &filePath, 3814514f5e3Sopenharmony_ci [[maybe_unused]] bool newThread) 3824514f5e3Sopenharmony_ci{ 3834514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 3844514f5e3Sopenharmony_ci FileStream stream(filePath); 3854514f5e3Sopenharmony_ci return StopHeapTracking(vm, &stream, nullptr, newThread); 3864514f5e3Sopenharmony_ci#else 3874514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap tracking"; 3884514f5e3Sopenharmony_ci return false; 3894514f5e3Sopenharmony_ci#endif 3904514f5e3Sopenharmony_ci} 3914514f5e3Sopenharmony_ci 3924514f5e3Sopenharmony_cibool DFXJSNApi::StopHeapTracking([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] Stream* stream, 3934514f5e3Sopenharmony_ci [[maybe_unused]] Progress *progress, [[maybe_unused]] bool newThread) 3944514f5e3Sopenharmony_ci{ 3954514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 3964514f5e3Sopenharmony_ci ecmascript::base::BlockHookScope blockScope; 3974514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 3984514f5e3Sopenharmony_ci bool result = false; 3994514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 4004514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 4014514f5e3Sopenharmony_ci result = heapProfile->StopHeapTracking(stream, progress, newThread); 4024514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface::Destroy(const_cast<EcmaVM *>(vm)); 4034514f5e3Sopenharmony_ci return result; 4044514f5e3Sopenharmony_ci#else 4054514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap tracking"; 4064514f5e3Sopenharmony_ci return false; 4074514f5e3Sopenharmony_ci#endif 4084514f5e3Sopenharmony_ci} 4094514f5e3Sopenharmony_ci 4104514f5e3Sopenharmony_civoid DFXJSNApi::PrintStatisticResult(const EcmaVM *vm) 4114514f5e3Sopenharmony_ci{ 4124514f5e3Sopenharmony_ci ecmascript::GCStats gcstats(vm->GetHeap()); 4134514f5e3Sopenharmony_ci gcstats.PrintStatisticResult(); 4144514f5e3Sopenharmony_ci} 4154514f5e3Sopenharmony_ci 4164514f5e3Sopenharmony_civoid DFXJSNApi::StartRuntimeStat(EcmaVM *vm) 4174514f5e3Sopenharmony_ci{ 4184514f5e3Sopenharmony_ci vm->GetJSThread()->GetCurrentEcmaContext()->SetRuntimeStatEnable(true); 4194514f5e3Sopenharmony_ci} 4204514f5e3Sopenharmony_ci 4214514f5e3Sopenharmony_civoid DFXJSNApi::StopRuntimeStat(EcmaVM *vm) 4224514f5e3Sopenharmony_ci{ 4234514f5e3Sopenharmony_ci vm->GetJSThread()->GetCurrentEcmaContext()->SetRuntimeStatEnable(false); 4244514f5e3Sopenharmony_ci} 4254514f5e3Sopenharmony_ci 4264514f5e3Sopenharmony_cisize_t DFXJSNApi::GetArrayBufferSize(const EcmaVM *vm) 4274514f5e3Sopenharmony_ci{ 4284514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 4294514f5e3Sopenharmony_ci return vm->GetHeap()->GetArrayBufferSize(); 4304514f5e3Sopenharmony_ci} 4314514f5e3Sopenharmony_ci 4324514f5e3Sopenharmony_cisize_t DFXJSNApi::GetHeapTotalSize(const EcmaVM *vm) 4334514f5e3Sopenharmony_ci{ 4344514f5e3Sopenharmony_ci return vm->GetHeap()->GetCommittedSize(); 4354514f5e3Sopenharmony_ci} 4364514f5e3Sopenharmony_ci 4374514f5e3Sopenharmony_cisize_t DFXJSNApi::GetHeapUsedSize(const EcmaVM *vm) 4384514f5e3Sopenharmony_ci{ 4394514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 4404514f5e3Sopenharmony_ci return vm->GetHeap()->GetLiveObjectSize(); 4414514f5e3Sopenharmony_ci} 4424514f5e3Sopenharmony_ci 4434514f5e3Sopenharmony_cisize_t DFXJSNApi::GetHeapObjectSize(const EcmaVM *vm) 4444514f5e3Sopenharmony_ci{ 4454514f5e3Sopenharmony_ci return vm->GetHeap()->GetHeapObjectSize(); 4464514f5e3Sopenharmony_ci} 4474514f5e3Sopenharmony_ci 4484514f5e3Sopenharmony_cisize_t DFXJSNApi::GetHeapLimitSize(const EcmaVM *vm) 4494514f5e3Sopenharmony_ci{ 4504514f5e3Sopenharmony_ci return vm->GetHeap()->GetHeapLimitSize(); 4514514f5e3Sopenharmony_ci} 4524514f5e3Sopenharmony_ci 4534514f5e3Sopenharmony_cisize_t DFXJSNApi::GetProcessHeapLimitSize() 4544514f5e3Sopenharmony_ci{ 4554514f5e3Sopenharmony_ci return ecmascript::MemMapAllocator::GetInstance()->GetCapacity(); 4564514f5e3Sopenharmony_ci} 4574514f5e3Sopenharmony_ci 4584514f5e3Sopenharmony_cisize_t DFXJSNApi::GetGCCount(const EcmaVM *vm) 4594514f5e3Sopenharmony_ci{ 4604514f5e3Sopenharmony_ci if (vm->IsWorkerThread()) { 4614514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetGCCount(); 4624514f5e3Sopenharmony_ci } 4634514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetGCCount() + 4644514f5e3Sopenharmony_ci ecmascript::SharedHeap::GetInstance()->GetEcmaGCStats()->GetGCCount(); 4654514f5e3Sopenharmony_ci} 4664514f5e3Sopenharmony_ci 4674514f5e3Sopenharmony_cisize_t DFXJSNApi::GetGCDuration(const EcmaVM *vm) 4684514f5e3Sopenharmony_ci{ 4694514f5e3Sopenharmony_ci if (vm->IsWorkerThread()) { 4704514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetGCDuration(); 4714514f5e3Sopenharmony_ci } 4724514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetGCDuration() + 4734514f5e3Sopenharmony_ci ecmascript::SharedHeap::GetInstance()->GetEcmaGCStats()->GetGCDuration(); 4744514f5e3Sopenharmony_ci} 4754514f5e3Sopenharmony_ci 4764514f5e3Sopenharmony_cisize_t DFXJSNApi::GetAccumulatedAllocateSize(const EcmaVM *vm) 4774514f5e3Sopenharmony_ci{ 4784514f5e3Sopenharmony_ci if (vm->IsWorkerThread()) { 4794514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetAccumulatedAllocateSize(); 4804514f5e3Sopenharmony_ci } 4814514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetAccumulatedAllocateSize() + 4824514f5e3Sopenharmony_ci ecmascript::SharedHeap::GetInstance()->GetEcmaGCStats()->GetAccumulatedAllocateSize(); 4834514f5e3Sopenharmony_ci} 4844514f5e3Sopenharmony_ci 4854514f5e3Sopenharmony_cisize_t DFXJSNApi::GetAccumulatedFreeSize(const EcmaVM *vm) 4864514f5e3Sopenharmony_ci{ 4874514f5e3Sopenharmony_ci if (vm->IsWorkerThread()) { 4884514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetAccumulatedFreeSize(); 4894514f5e3Sopenharmony_ci } 4904514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetAccumulatedFreeSize() + 4914514f5e3Sopenharmony_ci ecmascript::SharedHeap::GetInstance()->GetEcmaGCStats()->GetAccumulatedFreeSize(); 4924514f5e3Sopenharmony_ci} 4934514f5e3Sopenharmony_ci 4944514f5e3Sopenharmony_cisize_t DFXJSNApi::GetFullGCLongTimeCount(const EcmaVM *vm) 4954514f5e3Sopenharmony_ci{ 4964514f5e3Sopenharmony_ci return vm->GetEcmaGCStats()->GetFullGCLongTimeCount(); 4974514f5e3Sopenharmony_ci} 4984514f5e3Sopenharmony_ci 4994514f5e3Sopenharmony_civoid DFXJSNApi::GetHeapPrepare(const EcmaVM *vm) 5004514f5e3Sopenharmony_ci{ 5014514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 5024514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->GetHeapPrepare(); 5034514f5e3Sopenharmony_ci} 5044514f5e3Sopenharmony_ci 5054514f5e3Sopenharmony_civoid DFXJSNApi::SetJsDumpThresholds([[maybe_unused]] EcmaVM *vm, [[maybe_unused]] size_t thresholds) 5064514f5e3Sopenharmony_ci{ 5074514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) && defined(PANDA_TARGET_OHOS) && defined(ENABLE_HISYSEVENT) 5084514f5e3Sopenharmony_ci vm->GetHeap()->SetJsDumpThresholds(thresholds); 5094514f5e3Sopenharmony_ci#else 5104514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support set jsdump thresholds"; 5114514f5e3Sopenharmony_ci#endif 5124514f5e3Sopenharmony_ci} 5134514f5e3Sopenharmony_ci 5144514f5e3Sopenharmony_civoid DFXJSNApi::SetAppFreezeFilterCallback(const EcmaVM *vm, AppFreezeFilterCallback cb) 5154514f5e3Sopenharmony_ci{ 5164514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->SetAppFreezeFilterCallback(cb); 5174514f5e3Sopenharmony_ci ecmascript::SharedHeap* sHeap = ecmascript::SharedHeap::GetInstance(); 5184514f5e3Sopenharmony_ci sHeap->SetAppFreezeFilterCallback(cb); 5194514f5e3Sopenharmony_ci} 5204514f5e3Sopenharmony_ci 5214514f5e3Sopenharmony_civoid DFXJSNApi::NotifyApplicationState(EcmaVM *vm, bool inBackground) 5224514f5e3Sopenharmony_ci{ 5234514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 5244514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->ChangeGCParams(inBackground); 5254514f5e3Sopenharmony_ci ecmascript::Jit::GetInstance()->ChangeTaskPoolState(inBackground); 5264514f5e3Sopenharmony_ci} 5274514f5e3Sopenharmony_ci 5284514f5e3Sopenharmony_civoid DFXJSNApi::NotifyIdleStatusControl(const EcmaVM *vm, std::function<void(bool)> callback) 5294514f5e3Sopenharmony_ci{ 5304514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->InitializeIdleStatusControl(callback); 5314514f5e3Sopenharmony_ci} 5324514f5e3Sopenharmony_ci 5334514f5e3Sopenharmony_civoid DFXJSNApi::NotifyIdleTime(const EcmaVM *vm, int idleMicroSec) 5344514f5e3Sopenharmony_ci{ 5354514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 5364514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->TriggerIdleCollection(idleMicroSec); 5374514f5e3Sopenharmony_ci} 5384514f5e3Sopenharmony_ci 5394514f5e3Sopenharmony_civoid DFXJSNApi::NotifyMemoryPressure(EcmaVM *vm, bool inHighMemoryPressure) 5404514f5e3Sopenharmony_ci{ 5414514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->NotifyMemoryPressure(inHighMemoryPressure); 5424514f5e3Sopenharmony_ci} 5434514f5e3Sopenharmony_ci 5444514f5e3Sopenharmony_civoid DFXJSNApi::NotifyFinishColdStart(EcmaVM *vm, bool isConvinced) 5454514f5e3Sopenharmony_ci{ 5464514f5e3Sopenharmony_ci ecmascript::ThreadManagedScope managedScope(vm->GetJSThread()); 5474514f5e3Sopenharmony_ci if (isConvinced) { 5484514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->NotifyFinishColdStart(); 5494514f5e3Sopenharmony_ci } else { 5504514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->NotifyFinishColdStartSoon(); 5514514f5e3Sopenharmony_ci } 5524514f5e3Sopenharmony_ci} 5534514f5e3Sopenharmony_ci 5544514f5e3Sopenharmony_civoid DFXJSNApi::NotifyHighSensitive(EcmaVM *vm, bool isStart) 5554514f5e3Sopenharmony_ci{ 5564514f5e3Sopenharmony_ci const_cast<ecmascript::Heap *>(vm->GetHeap())->NotifyHighSensitive(isStart); 5574514f5e3Sopenharmony_ci} 5584514f5e3Sopenharmony_ci 5594514f5e3Sopenharmony_cibool DFXJSNApi::StopCpuProfilerForColdStart([[maybe_unused]] const EcmaVM *vm) 5604514f5e3Sopenharmony_ci{ 5614514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 5624514f5e3Sopenharmony_ci bool success = false; 5634514f5e3Sopenharmony_ci auto &options = const_cast<EcmaVM *>(vm)->GetJSOptions(); 5644514f5e3Sopenharmony_ci if (options.EnableCpuProfilerColdStartMainThread()) { 5654514f5e3Sopenharmony_ci success = true; 5664514f5e3Sopenharmony_ci DFXJSNApi::StopCpuProfilerForFile(vm); 5674514f5e3Sopenharmony_ci } 5684514f5e3Sopenharmony_ci 5694514f5e3Sopenharmony_ci if (options.EnableCpuProfilerColdStartWorkerThread()) { 5704514f5e3Sopenharmony_ci success = true; 5714514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->EnumerateWorkerVm([&](const EcmaVM *workerVm) -> void { 5724514f5e3Sopenharmony_ci if (workerVm->GetJSThread()->GetIsProfiling()) { 5734514f5e3Sopenharmony_ci DFXJSNApi::StopCpuProfilerForFile(workerVm); 5744514f5e3Sopenharmony_ci } 5754514f5e3Sopenharmony_ci }); 5764514f5e3Sopenharmony_ci } 5774514f5e3Sopenharmony_ci 5784514f5e3Sopenharmony_ci return success; 5794514f5e3Sopenharmony_ci#else 5804514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler cpu profiler"; 5814514f5e3Sopenharmony_ci return false; 5824514f5e3Sopenharmony_ci#endif 5834514f5e3Sopenharmony_ci} 5844514f5e3Sopenharmony_ci 5854514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 5864514f5e3Sopenharmony_civoid DFXJSNApi::CpuProfilerAnyTimeMainThread(const EcmaVM *vm) 5874514f5e3Sopenharmony_ci{ 5884514f5e3Sopenharmony_ci const uint8_t KILL_COUNT_FACTOR = 2; 5894514f5e3Sopenharmony_ci if (killCount % KILL_COUNT_FACTOR == 0) { 5904514f5e3Sopenharmony_ci uint8_t fileCount = killCount / KILL_COUNT_FACTOR + 1; 5914514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "Start CpuProfiler Any Time Main Thread, killCount = " << killCount; 5924514f5e3Sopenharmony_ci std::string fileName = ConvertToStdString(const_cast<EcmaVM *>(vm)->GetBundleName()) 5934514f5e3Sopenharmony_ci + "_" + std::to_string(fileCount) + ".cpuprofile"; 5944514f5e3Sopenharmony_ci if (!BuiltinsArkTools::CreateFile(fileName)) { 5954514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "createFile failed " << fileName; 5964514f5e3Sopenharmony_ci } else { 5974514f5e3Sopenharmony_ci DFXJSNApi::StartCpuProfilerForFile(vm, fileName, CpuProfiler::INTERVAL_OF_INNER_START); 5984514f5e3Sopenharmony_ci } 5994514f5e3Sopenharmony_ci } else { 6004514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "Stop CpuProfiler Any Time Main Thread, killCount = " << killCount; 6014514f5e3Sopenharmony_ci if (vm->GetJSThread()->GetIsProfiling()) { 6024514f5e3Sopenharmony_ci DFXJSNApi::StopCpuProfilerForFile(vm); 6034514f5e3Sopenharmony_ci } 6044514f5e3Sopenharmony_ci } 6054514f5e3Sopenharmony_ci} 6064514f5e3Sopenharmony_ci#endif 6074514f5e3Sopenharmony_ci 6084514f5e3Sopenharmony_cibool DFXJSNApi::CpuProfilerSamplingAnyTime([[maybe_unused]] const EcmaVM *vm) 6094514f5e3Sopenharmony_ci{ 6104514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 6114514f5e3Sopenharmony_ci (void)killCount; 6124514f5e3Sopenharmony_ci bool success = false; 6134514f5e3Sopenharmony_ci const uint8_t KILL_COUNT_FACTOR = 2; 6144514f5e3Sopenharmony_ci auto &options = const_cast<EcmaVM *>(vm)->GetJSOptions(); 6154514f5e3Sopenharmony_ci if (options.EnableCpuProfilerAnyTimeMainThread()) { 6164514f5e3Sopenharmony_ci success = true; 6174514f5e3Sopenharmony_ci CpuProfilerAnyTimeMainThread(vm); 6184514f5e3Sopenharmony_ci } 6194514f5e3Sopenharmony_ci 6204514f5e3Sopenharmony_ci if (options.EnableCpuProfilerAnyTimeWorkerThread()) { 6214514f5e3Sopenharmony_ci success = true; 6224514f5e3Sopenharmony_ci if (killCount % KILL_COUNT_FACTOR == 0) { 6234514f5e3Sopenharmony_ci uint8_t fileCount = killCount / KILL_COUNT_FACTOR + 1; 6244514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "Start CpuProfiler Any Time Worker Thread, killCount = " << killCount; 6254514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->EnumerateWorkerVm([&](const EcmaVM *workerVm) -> void { 6264514f5e3Sopenharmony_ci auto *thread = workerVm->GetAssociatedJSThread(); 6274514f5e3Sopenharmony_ci std::string fileName = ConvertToStdString(workerVm->GetBundleName()) + "_" 6284514f5e3Sopenharmony_ci + std::to_string(thread->GetThreadId()) + "_" 6294514f5e3Sopenharmony_ci + std::to_string(fileCount) + ".cpuprofile"; 6304514f5e3Sopenharmony_ci if (!BuiltinsArkTools::CreateFile(fileName)) { 6314514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "createFile failed " << fileName; 6324514f5e3Sopenharmony_ci } else { 6334514f5e3Sopenharmony_ci thread->SetCpuProfileName(fileName); 6344514f5e3Sopenharmony_ci thread->SetNeedProfiling(true); 6354514f5e3Sopenharmony_ci } 6364514f5e3Sopenharmony_ci }); 6374514f5e3Sopenharmony_ci } else { 6384514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "Stop CpuProfiler Any Time Worker Thread, killCount = " << killCount; 6394514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->EnumerateWorkerVm([&](const EcmaVM *workerVm) -> void { 6404514f5e3Sopenharmony_ci auto *thread = workerVm->GetAssociatedJSThread(); 6414514f5e3Sopenharmony_ci if (thread->GetIsProfiling()) { 6424514f5e3Sopenharmony_ci DFXJSNApi::StopCpuProfilerForFile(workerVm); 6434514f5e3Sopenharmony_ci } 6444514f5e3Sopenharmony_ci thread->SetNeedProfiling(false); 6454514f5e3Sopenharmony_ci }); 6464514f5e3Sopenharmony_ci } 6474514f5e3Sopenharmony_ci } 6484514f5e3Sopenharmony_ci 6494514f5e3Sopenharmony_ci return success; 6504514f5e3Sopenharmony_ci#else 6514514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler cpu profiler"; 6524514f5e3Sopenharmony_ci return false; 6534514f5e3Sopenharmony_ci#endif 6544514f5e3Sopenharmony_ci} 6554514f5e3Sopenharmony_ci 6564514f5e3Sopenharmony_cibool DFXJSNApi::StartCpuProfilerForFile([[maybe_unused]] const EcmaVM *vm, 6574514f5e3Sopenharmony_ci [[maybe_unused]] const std::string &fileName, 6584514f5e3Sopenharmony_ci [[maybe_unused]] int interval) 6594514f5e3Sopenharmony_ci{ 6604514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 6614514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "DFXJSNApi::StartCpuProfilerForFile, vm = " << vm; 6624514f5e3Sopenharmony_ci if (interval <= 0) { 6634514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StartCpuProfilerForFile, interval <= 0"; 6644514f5e3Sopenharmony_ci return false; 6654514f5e3Sopenharmony_ci } 6664514f5e3Sopenharmony_ci if (vm == nullptr) { 6674514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StartCpuProfilerForFile, vm == nullptr"; 6684514f5e3Sopenharmony_ci return false; 6694514f5e3Sopenharmony_ci } 6704514f5e3Sopenharmony_ci CpuProfiler *profiler = vm->GetProfiler(); 6714514f5e3Sopenharmony_ci if (profiler == nullptr) { 6724514f5e3Sopenharmony_ci profiler = new CpuProfiler(vm, interval); 6734514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->SetProfiler(profiler); 6744514f5e3Sopenharmony_ci } 6754514f5e3Sopenharmony_ci return profiler->StartCpuProfilerForFile(fileName); 6764514f5e3Sopenharmony_ci#else 6774514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StartCpuProfilerForFile, not support cpu profiler"; 6784514f5e3Sopenharmony_ci return false; 6794514f5e3Sopenharmony_ci#endif 6804514f5e3Sopenharmony_ci} 6814514f5e3Sopenharmony_ci 6824514f5e3Sopenharmony_civoid DFXJSNApi::StopCpuProfilerForFile([[maybe_unused]] const EcmaVM *vm) 6834514f5e3Sopenharmony_ci{ 6844514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 6854514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "DFXJSNApi::StopCpuProfilerForFile, vm = " << vm; 6864514f5e3Sopenharmony_ci if (vm == nullptr) { 6874514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StopCpuProfilerForFile, vm == nullptr"; 6884514f5e3Sopenharmony_ci return; 6894514f5e3Sopenharmony_ci } 6904514f5e3Sopenharmony_ci CpuProfiler *profiler = vm->GetProfiler(); 6914514f5e3Sopenharmony_ci if (profiler == nullptr) { 6924514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StopCpuProfilerForFile, profiler == nullptr"; 6934514f5e3Sopenharmony_ci return; 6944514f5e3Sopenharmony_ci } 6954514f5e3Sopenharmony_ci bool result = profiler->StopCpuProfilerForFile(); 6964514f5e3Sopenharmony_ci if (!result) { 6974514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StopCpuProfilerForFile failed"; 6984514f5e3Sopenharmony_ci return; 6994514f5e3Sopenharmony_ci } 7004514f5e3Sopenharmony_ci delete profiler; 7014514f5e3Sopenharmony_ci profiler = nullptr; 7024514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->SetProfiler(nullptr); 7034514f5e3Sopenharmony_ci#else 7044514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler cpu profiler"; 7054514f5e3Sopenharmony_ci#endif 7064514f5e3Sopenharmony_ci} 7074514f5e3Sopenharmony_ci 7084514f5e3Sopenharmony_cibool DFXJSNApi::StartCpuProfilerForInfo([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] int interval) 7094514f5e3Sopenharmony_ci{ 7104514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 7114514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "DFXJSNApi::StartCpuProfilerForInfo, vm = " << vm; 7124514f5e3Sopenharmony_ci if (interval <= 0) { 7134514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StartCpuProfilerForInfo, interval <= 0"; 7144514f5e3Sopenharmony_ci return false; 7154514f5e3Sopenharmony_ci } 7164514f5e3Sopenharmony_ci if (vm == nullptr) { 7174514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StartCpuProfilerForInfo, vm == nullptr"; 7184514f5e3Sopenharmony_ci return false; 7194514f5e3Sopenharmony_ci } 7204514f5e3Sopenharmony_ci CpuProfiler *profiler = vm->GetProfiler(); 7214514f5e3Sopenharmony_ci if (profiler == nullptr) { 7224514f5e3Sopenharmony_ci profiler = new CpuProfiler(vm, interval); 7234514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->SetProfiler(profiler); 7244514f5e3Sopenharmony_ci } 7254514f5e3Sopenharmony_ci return profiler->StartCpuProfilerForInfo(); 7264514f5e3Sopenharmony_ci#else 7274514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StartCpuProfilerForInfo, not support cpu profiler"; 7284514f5e3Sopenharmony_ci return false; 7294514f5e3Sopenharmony_ci#endif 7304514f5e3Sopenharmony_ci} 7314514f5e3Sopenharmony_ci 7324514f5e3Sopenharmony_cistd::unique_ptr<ProfileInfo> DFXJSNApi::StopCpuProfilerForInfo([[maybe_unused]] const EcmaVM *vm) 7334514f5e3Sopenharmony_ci{ 7344514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 7354514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "DFXJSNApi::StopCpuProfilerForInfo, vm = " << vm; 7364514f5e3Sopenharmony_ci if (vm == nullptr) { 7374514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StopCpuProfilerForInfo, vm == nullptr"; 7384514f5e3Sopenharmony_ci return nullptr; 7394514f5e3Sopenharmony_ci } 7404514f5e3Sopenharmony_ci CpuProfiler *profiler = vm->GetProfiler(); 7414514f5e3Sopenharmony_ci if (profiler == nullptr) { 7424514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StopCpuProfilerForInfo, profiler == nullptr"; 7434514f5e3Sopenharmony_ci return nullptr; 7444514f5e3Sopenharmony_ci } 7454514f5e3Sopenharmony_ci std::unique_ptr<ProfileInfo> profileInfo; 7464514f5e3Sopenharmony_ci bool result = profiler->StopCpuProfilerForInfo(profileInfo); 7474514f5e3Sopenharmony_ci if (!result) { 7484514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StopCpuProfilerForInfo failed"; 7494514f5e3Sopenharmony_ci return nullptr; 7504514f5e3Sopenharmony_ci } 7514514f5e3Sopenharmony_ci delete profiler; 7524514f5e3Sopenharmony_ci profiler = nullptr; 7534514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->SetProfiler(nullptr); 7544514f5e3Sopenharmony_ci return profileInfo; 7554514f5e3Sopenharmony_ci#else 7564514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler cpu profiler"; 7574514f5e3Sopenharmony_ci return nullptr; 7584514f5e3Sopenharmony_ci#endif 7594514f5e3Sopenharmony_ci} 7604514f5e3Sopenharmony_ci 7614514f5e3Sopenharmony_civoid DFXJSNApi::SetCpuSamplingInterval([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] int interval) 7624514f5e3Sopenharmony_ci{ 7634514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_CPUPROFILER) 7644514f5e3Sopenharmony_ci if (interval < 0) { 7654514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Sampling interval is illegal"; 7664514f5e3Sopenharmony_ci return; 7674514f5e3Sopenharmony_ci } 7684514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "SetCpuProfilerSamplingInterval, Sampling interval is: " << interval; 7694514f5e3Sopenharmony_ci if (vm == nullptr) { 7704514f5e3Sopenharmony_ci return; 7714514f5e3Sopenharmony_ci } 7724514f5e3Sopenharmony_ci CpuProfiler *profiler = vm->GetProfiler(); 7734514f5e3Sopenharmony_ci if (profiler == nullptr) { 7744514f5e3Sopenharmony_ci profiler = new CpuProfiler(vm, interval); 7754514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->SetProfiler(profiler); 7764514f5e3Sopenharmony_ci return; 7774514f5e3Sopenharmony_ci } 7784514f5e3Sopenharmony_ci profiler->SetCpuSamplingInterval(interval); 7794514f5e3Sopenharmony_ci#else 7804514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler cpu profiler"; 7814514f5e3Sopenharmony_ci#endif 7824514f5e3Sopenharmony_ci} 7834514f5e3Sopenharmony_ci 7844514f5e3Sopenharmony_civoid DFXJSNApi::EnableSeriliazationTimeoutCheck(const EcmaVM *ecmaVM, int32_t threshold) 7854514f5e3Sopenharmony_ci{ 7864514f5e3Sopenharmony_ci ecmaVM->GetJsDebuggerManager()->EnableSerializationTimeoutCheck(); 7874514f5e3Sopenharmony_ci ecmaVM->GetJsDebuggerManager()->SetSerializationCheckThreshold(threshold); 7884514f5e3Sopenharmony_ci} 7894514f5e3Sopenharmony_ci 7904514f5e3Sopenharmony_civoid DFXJSNApi::DisableSeriliazationTimeoutCheck(const EcmaVM *ecmaVM) 7914514f5e3Sopenharmony_ci{ 7924514f5e3Sopenharmony_ci ecmaVM->GetJsDebuggerManager()->DisableSerializationTimeoutCheck(); 7934514f5e3Sopenharmony_ci} 7944514f5e3Sopenharmony_ci 7954514f5e3Sopenharmony_cibool DFXJSNApi::SuspendVM([[maybe_unused]] const EcmaVM *vm) 7964514f5e3Sopenharmony_ci{ 7974514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 7984514f5e3Sopenharmony_ci ecmascript::VmThreadControl* vmThreadControl = vm->GetAssociatedJSThread()->GetVmThreadControl(); 7994514f5e3Sopenharmony_ci return vmThreadControl->NotifyVMThreadSuspension(); 8004514f5e3Sopenharmony_ci#else 8014514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler snapshot"; 8024514f5e3Sopenharmony_ci return false; 8034514f5e3Sopenharmony_ci#endif 8044514f5e3Sopenharmony_ci} 8054514f5e3Sopenharmony_ci 8064514f5e3Sopenharmony_civoid DFXJSNApi::ResumeVM([[maybe_unused]] const EcmaVM *vm) 8074514f5e3Sopenharmony_ci{ 8084514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 8094514f5e3Sopenharmony_ci ecmascript::VmThreadControl* vmThreadControl = vm->GetAssociatedJSThread()->GetVmThreadControl(); 8104514f5e3Sopenharmony_ci vmThreadControl->ResumeVM(); 8114514f5e3Sopenharmony_ci#else 8124514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler snapshot"; 8134514f5e3Sopenharmony_ci#endif 8144514f5e3Sopenharmony_ci} 8154514f5e3Sopenharmony_ci 8164514f5e3Sopenharmony_cibool DFXJSNApi::IsSuspended([[maybe_unused]] const EcmaVM *vm) 8174514f5e3Sopenharmony_ci{ 8184514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 8194514f5e3Sopenharmony_ci ecmascript::VmThreadControl* vmThreadControl = vm->GetAssociatedJSThread()->GetVmThreadControl(); 8204514f5e3Sopenharmony_ci return vmThreadControl->IsSuspended(); 8214514f5e3Sopenharmony_ci#else 8224514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler snapshot"; 8234514f5e3Sopenharmony_ci return false; 8244514f5e3Sopenharmony_ci#endif 8254514f5e3Sopenharmony_ci} 8264514f5e3Sopenharmony_ci 8274514f5e3Sopenharmony_civoid DFXJSNApi::TerminateExecution(const EcmaVM *vm) 8284514f5e3Sopenharmony_ci{ 8294514f5e3Sopenharmony_ci ecmascript::VmThreadControl* vmThreadControl = vm->GetAssociatedJSThread()->GetVmThreadControl(); 8304514f5e3Sopenharmony_ci vmThreadControl->RequestTerminateExecution(); 8314514f5e3Sopenharmony_ci} 8324514f5e3Sopenharmony_ci 8334514f5e3Sopenharmony_cibool DFXJSNApi::CheckSafepoint([[maybe_unused]] const EcmaVM *vm) 8344514f5e3Sopenharmony_ci{ 8354514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_SNAPSHOT) 8364514f5e3Sopenharmony_ci ecmascript::JSThread* thread = vm->GetJSThread(); 8374514f5e3Sopenharmony_ci return thread->CheckSafepoint(); 8384514f5e3Sopenharmony_ci#else 8394514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler snapshot"; 8404514f5e3Sopenharmony_ci return false; 8414514f5e3Sopenharmony_ci#endif 8424514f5e3Sopenharmony_ci} 8434514f5e3Sopenharmony_ci 8444514f5e3Sopenharmony_cibool DFXJSNApi::BuildJsStackInfoList(const EcmaVM *hostVm, uint32_t tid, std::vector<JsFrameInfo>& jsFrames) 8454514f5e3Sopenharmony_ci{ 8464514f5e3Sopenharmony_ci EcmaVM *vm; 8474514f5e3Sopenharmony_ci if (hostVm->GetAssociatedJSThread()->GetThreadId() == tid) { 8484514f5e3Sopenharmony_ci vm = const_cast<EcmaVM*>(hostVm); 8494514f5e3Sopenharmony_ci } else { 8504514f5e3Sopenharmony_ci vm = const_cast<EcmaVM*>(hostVm)->GetWorkerVm(tid); 8514514f5e3Sopenharmony_ci if (vm == nullptr) { 8524514f5e3Sopenharmony_ci return false; 8534514f5e3Sopenharmony_ci } 8544514f5e3Sopenharmony_ci } 8554514f5e3Sopenharmony_ci jsFrames = ecmascript::JsStackInfo::BuildJsStackInfo(vm->GetAssociatedJSThread()); 8564514f5e3Sopenharmony_ci if (jsFrames.size() > 0) { 8574514f5e3Sopenharmony_ci return true; 8584514f5e3Sopenharmony_ci } 8594514f5e3Sopenharmony_ci return false; 8604514f5e3Sopenharmony_ci} 8614514f5e3Sopenharmony_ci 8624514f5e3Sopenharmony_ciint32_t DFXJSNApi::GetObjectHash(const EcmaVM *vm, Local<JSValueRef> nativeObject) 8634514f5e3Sopenharmony_ci{ 8644514f5e3Sopenharmony_ci JSHandle<JSTaggedValue> obj = JSNApiHelper::ToJSHandle(nativeObject); 8654514f5e3Sopenharmony_ci return ecmascript::tooling::DebuggerApi::GetObjectHash(vm, obj); 8664514f5e3Sopenharmony_ci} 8674514f5e3Sopenharmony_ci 8684514f5e3Sopenharmony_cibool DFXJSNApi::StartSampling([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] uint64_t samplingInterval) 8694514f5e3Sopenharmony_ci{ 8704514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_HEAPSAMPLING) 8714514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 8724514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 8734514f5e3Sopenharmony_ci return heapProfile->StartHeapSampling(samplingInterval); 8744514f5e3Sopenharmony_ci#else 8754514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap sampling"; 8764514f5e3Sopenharmony_ci return false; 8774514f5e3Sopenharmony_ci#endif 8784514f5e3Sopenharmony_ci} 8794514f5e3Sopenharmony_ci 8804514f5e3Sopenharmony_ciconst SamplingInfo *DFXJSNApi::GetAllocationProfile([[maybe_unused]] const EcmaVM *vm) 8814514f5e3Sopenharmony_ci{ 8824514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_HEAPSAMPLING) 8834514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 8844514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 8854514f5e3Sopenharmony_ci return heapProfile->GetAllocationProfile(); 8864514f5e3Sopenharmony_ci#else 8874514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap sampling"; 8884514f5e3Sopenharmony_ci return nullptr; 8894514f5e3Sopenharmony_ci#endif 8904514f5e3Sopenharmony_ci} 8914514f5e3Sopenharmony_ci 8924514f5e3Sopenharmony_civoid DFXJSNApi::StopSampling([[maybe_unused]] const EcmaVM *vm) 8934514f5e3Sopenharmony_ci{ 8944514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_HEAPSAMPLING) 8954514f5e3Sopenharmony_ci ecmascript::HeapProfilerInterface *heapProfile = ecmascript::HeapProfilerInterface::GetInstance( 8964514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)); 8974514f5e3Sopenharmony_ci heapProfile->StopHeapSampling(); 8984514f5e3Sopenharmony_ci#else 8994514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler heap sampling"; 9004514f5e3Sopenharmony_ci#endif 9014514f5e3Sopenharmony_ci} 9024514f5e3Sopenharmony_ci 9034514f5e3Sopenharmony_ci// release or debug hap : aa start -p 'dumpheap' 9044514f5e3Sopenharmony_ci// aa start -p 'profile' 9054514f5e3Sopenharmony_cibool DFXJSNApi::StartProfiler(EcmaVM *vm, const ProfilerOption &option, int tid, 9064514f5e3Sopenharmony_ci int32_t instanceId, const DebuggerPostTask &debuggerPostTask, bool isDebugApp) 9074514f5e3Sopenharmony_ci{ 9084514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "DFXJSNApi::StartProfiler, type = " << (int)option.profilerType 9094514f5e3Sopenharmony_ci << ", tid = " << tid << ", isDebugApp = " << isDebugApp; 9104514f5e3Sopenharmony_ci JSNApi::DebugOption debugOption; 9114514f5e3Sopenharmony_ci debugOption.libraryPath = option.libraryPath; 9124514f5e3Sopenharmony_ci if (option.profilerType == ProfilerType::CPU_PROFILER) { 9134514f5e3Sopenharmony_ci debugOption.isDebugMode = false; 9144514f5e3Sopenharmony_ci if (JSNApi::NotifyDebugMode(tid, vm, debugOption, instanceId, debuggerPostTask, isDebugApp)) { 9154514f5e3Sopenharmony_ci return StartCpuProfilerForInfo(vm, option.interval); 9164514f5e3Sopenharmony_ci } else { 9174514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "DFXJSNApi::StartProfiler, NotifyDebugMode failed"; 9184514f5e3Sopenharmony_ci return false; 9194514f5e3Sopenharmony_ci } 9204514f5e3Sopenharmony_ci } else { 9214514f5e3Sopenharmony_ci debugOption.isDebugMode = true; 9224514f5e3Sopenharmony_ci return JSNApi::NotifyDebugMode(tid, vm, debugOption, instanceId, debuggerPostTask, isDebugApp); 9234514f5e3Sopenharmony_ci } 9244514f5e3Sopenharmony_ci} 9254514f5e3Sopenharmony_ci 9264514f5e3Sopenharmony_civoid DFXJSNApi::ResumeVMById(EcmaVM *hostVm, uint32_t tid) 9274514f5e3Sopenharmony_ci{ 9284514f5e3Sopenharmony_ci if (hostVm->GetAssociatedJSThread()->GetThreadId() == tid) { 9294514f5e3Sopenharmony_ci ResumeVM(hostVm); 9304514f5e3Sopenharmony_ci } else { 9314514f5e3Sopenharmony_ci hostVm->ResumeWorkerVm(tid); 9324514f5e3Sopenharmony_ci } 9334514f5e3Sopenharmony_ci} 9344514f5e3Sopenharmony_ci 9354514f5e3Sopenharmony_cibool DFXJSNApi::SuspendVMById(EcmaVM *hostVm, uint32_t tid) 9364514f5e3Sopenharmony_ci{ 9374514f5e3Sopenharmony_ci bool success = false; 9384514f5e3Sopenharmony_ci if (hostVm->GetAssociatedJSThread()->GetThreadId() == tid) { 9394514f5e3Sopenharmony_ci success = SuspendVM(hostVm); 9404514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "The main thread, SuspendVMById succeeded: " << success; 9414514f5e3Sopenharmony_ci return success; 9424514f5e3Sopenharmony_ci } else { 9434514f5e3Sopenharmony_ci success = hostVm->SuspendWorkerVm(tid); 9444514f5e3Sopenharmony_ci LOG_ECMA(INFO) << "The worker thread, SuspendVMById succeeded: " << success; 9454514f5e3Sopenharmony_ci return success; 9464514f5e3Sopenharmony_ci } 9474514f5e3Sopenharmony_ci} 9484514f5e3Sopenharmony_ci 9494514f5e3Sopenharmony_cibool DFXJSNApi::StartTracing([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] std::string &categories) 9504514f5e3Sopenharmony_ci{ 9514514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_TRACING) 9524514f5e3Sopenharmony_ci if (vm == nullptr) { 9534514f5e3Sopenharmony_ci return false; 9544514f5e3Sopenharmony_ci } 9554514f5e3Sopenharmony_ci Tracing *tracing = vm->GetTracing(); 9564514f5e3Sopenharmony_ci if (tracing == nullptr) { 9574514f5e3Sopenharmony_ci tracing = new Tracing(vm); 9584514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->SetTracing(tracing); 9594514f5e3Sopenharmony_ci } 9604514f5e3Sopenharmony_ci tracing->StartTracing(categories); 9614514f5e3Sopenharmony_ci return true; 9624514f5e3Sopenharmony_ci#else 9634514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler tracing"; 9644514f5e3Sopenharmony_ci return false; 9654514f5e3Sopenharmony_ci#endif 9664514f5e3Sopenharmony_ci} 9674514f5e3Sopenharmony_ci 9684514f5e3Sopenharmony_cistd::unique_ptr<std::vector<TraceEvent>> DFXJSNApi::StopTracing([[maybe_unused]] const EcmaVM *vm) 9694514f5e3Sopenharmony_ci{ 9704514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_TRACING) 9714514f5e3Sopenharmony_ci if (vm == nullptr) { 9724514f5e3Sopenharmony_ci return nullptr; 9734514f5e3Sopenharmony_ci } 9744514f5e3Sopenharmony_ci Tracing *tracing = vm->GetTracing(); 9754514f5e3Sopenharmony_ci if (tracing == nullptr) { 9764514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "StopTracing tracing is nullptr"; 9774514f5e3Sopenharmony_ci return nullptr; 9784514f5e3Sopenharmony_ci } 9794514f5e3Sopenharmony_ci auto traceEvents = tracing->StopTracing(); 9804514f5e3Sopenharmony_ci if (traceEvents == nullptr) { 9814514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "trace events is nullptr"; 9824514f5e3Sopenharmony_ci } 9834514f5e3Sopenharmony_ci delete tracing; 9844514f5e3Sopenharmony_ci tracing = nullptr; 9854514f5e3Sopenharmony_ci const_cast<EcmaVM *>(vm)->SetTracing(nullptr); 9864514f5e3Sopenharmony_ci return traceEvents; 9874514f5e3Sopenharmony_ci#else 9884514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler tracing"; 9894514f5e3Sopenharmony_ci return nullptr; 9904514f5e3Sopenharmony_ci#endif 9914514f5e3Sopenharmony_ci} 9924514f5e3Sopenharmony_ci 9934514f5e3Sopenharmony_civoid DFXJSNApi::GetTracingBufferUseage([[maybe_unused]] const EcmaVM *vm, [[maybe_unused]] double &percentFull, 9944514f5e3Sopenharmony_ci [[maybe_unused]] uint32_t &eventCount, [[maybe_unused]] double &value) 9954514f5e3Sopenharmony_ci{ 9964514f5e3Sopenharmony_ci#if defined(ECMASCRIPT_SUPPORT_TRACING) 9974514f5e3Sopenharmony_ci if (vm == nullptr) { 9984514f5e3Sopenharmony_ci return; 9994514f5e3Sopenharmony_ci } 10004514f5e3Sopenharmony_ci ecmascript::Tracing *tracing = vm->GetTracing(); 10014514f5e3Sopenharmony_ci if (tracing == nullptr) { 10024514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "GetTracingBufferUseage tracing is nullptr"; 10034514f5e3Sopenharmony_ci } else { 10044514f5e3Sopenharmony_ci tracing->GetBufferUseage(percentFull, eventCount, value); 10054514f5e3Sopenharmony_ci } 10064514f5e3Sopenharmony_ci#else 10074514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Not support arkcompiler tracing"; 10084514f5e3Sopenharmony_ci#endif 10094514f5e3Sopenharmony_ci} 10104514f5e3Sopenharmony_ci 10114514f5e3Sopenharmony_civoid DFXJSNApi::TranslateJSStackInfo(const EcmaVM *vm, std::string &url, int32_t &line, int32_t &column) 10124514f5e3Sopenharmony_ci{ 10134514f5e3Sopenharmony_ci auto cb = vm->GetSourceMapTranslateCallback(); 10144514f5e3Sopenharmony_ci if (cb == nullptr) { 10154514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Translate failed, callback function is nullptr."; 10164514f5e3Sopenharmony_ci } else if (!cb(url, line, column)) { 10174514f5e3Sopenharmony_ci LOG_ECMA(ERROR) << "Translate failed, url: " << url; 10184514f5e3Sopenharmony_ci } 10194514f5e3Sopenharmony_ci} 10204514f5e3Sopenharmony_ci 10214514f5e3Sopenharmony_ciuint32_t DFXJSNApi::GetCurrentThreadId() 10224514f5e3Sopenharmony_ci{ 10234514f5e3Sopenharmony_ci return JSThread::GetCurrentThreadId(); 10244514f5e3Sopenharmony_ci} 10254514f5e3Sopenharmony_ci} // namespace panda 1026