1cc290419Sopenharmony_ci/* 2cc290419Sopenharmony_ci * Copyright (C) 2021 Huawei Device Co., Ltd. 3cc290419Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License"); 4cc290419Sopenharmony_ci * you may not use this file except in compliance with the License. 5cc290419Sopenharmony_ci * You may obtain a copy of the License at 6cc290419Sopenharmony_ci * 7cc290419Sopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0 8cc290419Sopenharmony_ci * 9cc290419Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software 10cc290419Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS, 11cc290419Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12cc290419Sopenharmony_ci * See the License for the specific language governing permissions and 13cc290419Sopenharmony_ci * limitations under the License. 14cc290419Sopenharmony_ci * 15cc290419Sopenharmony_ci */ 16cc290419Sopenharmony_ci// The process is used to test jdwp. 17cc290419Sopenharmony_ci// jpid List pids of processes hosting a JDWP transport 18cc290419Sopenharmony_ci#include "define.h" 19cc290419Sopenharmony_ci#include "HdcJdwpSimulator.h" 20cc290419Sopenharmony_ciusing namespace OHOS::HiviewDFX; 21cc290419Sopenharmony_cistatic constexpr HiLogLabel LABEL = {LOG_CORE, 0, "JDWP_TEST"}; 22cc290419Sopenharmony_cistatic uv_loop_t loopMain; 23cc290419Sopenharmony_cistatic HdcJdwpSimulator *clsHdcJdwpSimulator = nullptr; 24cc290419Sopenharmony_ci 25cc290419Sopenharmony_cistatic void PrintMessage(const char *fmt, ...) 26cc290419Sopenharmony_ci{ 27cc290419Sopenharmony_ci int ret = 0; 28cc290419Sopenharmony_ci va_list ap; 29cc290419Sopenharmony_ci va_start(ap, fmt); 30cc290419Sopenharmony_ci vfprintf(stdout, fmt, ap); 31cc290419Sopenharmony_ci ret = fprintf(stdout, "\n"); 32cc290419Sopenharmony_ci va_end(ap); 33cc290419Sopenharmony_ci} 34cc290419Sopenharmony_ci 35cc290419Sopenharmony_cistatic void TryCloseHandle(const uv_handle_t *handle, bool alwaysCallback, 36cc290419Sopenharmony_ci uv_close_cb closeCallBack) 37cc290419Sopenharmony_ci{ 38cc290419Sopenharmony_ci bool hasCallClose = false; 39cc290419Sopenharmony_ci if (handle->loop && !uv_is_closing(handle)) { 40cc290419Sopenharmony_ci uv_close((uv_handle_t *)handle, closeCallBack); 41cc290419Sopenharmony_ci hasCallClose = true; 42cc290419Sopenharmony_ci } 43cc290419Sopenharmony_ci if (!hasCallClose && alwaysCallback) { 44cc290419Sopenharmony_ci closeCallBack((uv_handle_t *)handle); 45cc290419Sopenharmony_ci } 46cc290419Sopenharmony_ci} 47cc290419Sopenharmony_ci 48cc290419Sopenharmony_cistatic void TryCloseHandle(const uv_handle_t *handle, uv_close_cb closeCallBack) 49cc290419Sopenharmony_ci{ 50cc290419Sopenharmony_ci TryCloseHandle(handle, false, closeCallBack); 51cc290419Sopenharmony_ci} 52cc290419Sopenharmony_ci 53cc290419Sopenharmony_cistatic void TryCloseHandle(const uv_handle_t *handle) 54cc290419Sopenharmony_ci{ 55cc290419Sopenharmony_ci TryCloseHandle(handle, nullptr); 56cc290419Sopenharmony_ci} 57cc290419Sopenharmony_ci 58cc290419Sopenharmony_cistatic bool TryCloseLoop(uv_loop_t *ptrLoop, const char *callerName) 59cc290419Sopenharmony_ci{ 60cc290419Sopenharmony_ci uint8_t closeRetry = 0; 61cc290419Sopenharmony_ci bool ret = false; 62cc290419Sopenharmony_ci constexpr int maxRetry = 3; 63cc290419Sopenharmony_ci constexpr int maxHandle = 2; 64cc290419Sopenharmony_ci for (closeRetry = 0; closeRetry < maxRetry; ++closeRetry) { 65cc290419Sopenharmony_ci if (uv_loop_close(ptrLoop) == UV_EBUSY) { 66cc290419Sopenharmony_ci if (closeRetry > maxRetry) { 67cc290419Sopenharmony_ci PrintMessage("%s close busy,try:%d", callerName, closeRetry); 68cc290419Sopenharmony_ci } 69cc290419Sopenharmony_ci 70cc290419Sopenharmony_ci if (ptrLoop->active_handles >= maxHandle) { 71cc290419Sopenharmony_ci PrintMessage("TryCloseLoop issue"); 72cc290419Sopenharmony_ci } 73cc290419Sopenharmony_ci auto clearLoopTask = [](uv_handle_t *handle, void *arg) -> void { 74cc290419Sopenharmony_ci TryCloseHandle(handle); 75cc290419Sopenharmony_ci }; 76cc290419Sopenharmony_ci uv_walk(ptrLoop, clearLoopTask, nullptr); 77cc290419Sopenharmony_ci // If all processing ends, Then return0,this call will block 78cc290419Sopenharmony_ci if (!ptrLoop->active_handles) { 79cc290419Sopenharmony_ci ret = true; 80cc290419Sopenharmony_ci break; 81cc290419Sopenharmony_ci } 82cc290419Sopenharmony_ci if (!uv_run(ptrLoop, UV_RUN_ONCE)) { 83cc290419Sopenharmony_ci ret = true; 84cc290419Sopenharmony_ci break; 85cc290419Sopenharmony_ci } 86cc290419Sopenharmony_ci } else { 87cc290419Sopenharmony_ci ret = true; 88cc290419Sopenharmony_ci break; 89cc290419Sopenharmony_ci } 90cc290419Sopenharmony_ci } 91cc290419Sopenharmony_ci return ret; 92cc290419Sopenharmony_ci} 93cc290419Sopenharmony_ci 94cc290419Sopenharmony_cistatic void FreeInstance() 95cc290419Sopenharmony_ci{ 96cc290419Sopenharmony_ci if (clsHdcJdwpSimulator) { 97cc290419Sopenharmony_ci clsHdcJdwpSimulator->stop(); 98cc290419Sopenharmony_ci delete clsHdcJdwpSimulator; 99cc290419Sopenharmony_ci clsHdcJdwpSimulator = nullptr; 100cc290419Sopenharmony_ci } 101cc290419Sopenharmony_ci uv_stop(&loopMain); 102cc290419Sopenharmony_ci TryCloseLoop(&loopMain, "Hdcjdwp test exit"); 103cc290419Sopenharmony_ci HiLog::Info(LABEL, "jdwp_test_process exit."); 104cc290419Sopenharmony_ci PrintMessage("jdwp_test_process exit."); 105cc290419Sopenharmony_ci} 106cc290419Sopenharmony_ci 107cc290419Sopenharmony_cistatic void Stop(int signo) 108cc290419Sopenharmony_ci{ 109cc290419Sopenharmony_ci FreeInstance(); 110cc290419Sopenharmony_ci _exit(0); 111cc290419Sopenharmony_ci} 112cc290419Sopenharmony_ci 113cc290419Sopenharmony_ciint main(int argc, const char *argv[]) 114cc290419Sopenharmony_ci{ 115cc290419Sopenharmony_ci uv_loop_init(&loopMain); 116cc290419Sopenharmony_ci 117cc290419Sopenharmony_ci HiLog::Info(LABEL, "jdwp_test_process start."); 118cc290419Sopenharmony_ci PrintMessage("jdwp_test_process start."); 119cc290419Sopenharmony_ci if (signal(SIGINT, Stop) == SIG_ERR) { 120cc290419Sopenharmony_ci PrintMessage("jdwp_test_process signal fail."); 121cc290419Sopenharmony_ci } 122cc290419Sopenharmony_ci clsHdcJdwpSimulator = new HdcJdwpSimulator(&loopMain, "com.example.myapplication"); 123cc290419Sopenharmony_ci if (!clsHdcJdwpSimulator->Connect()) { 124cc290419Sopenharmony_ci PrintMessage("Connect fail."); 125cc290419Sopenharmony_ci return -1; 126cc290419Sopenharmony_ci } 127cc290419Sopenharmony_ci uv_run(&loopMain, UV_RUN_DEFAULT); 128cc290419Sopenharmony_ci 129cc290419Sopenharmony_ci#ifdef JS_JDWP_CONNECT 130cc290419Sopenharmony_ci PrintMessage("Enter 'exit' will stop the test."); 131cc290419Sopenharmony_ci std::string line; 132cc290419Sopenharmony_ci while (std::getline(std::cin, line)) { 133cc290419Sopenharmony_ci if (!strcmp(line.c_str(), "exit")) { 134cc290419Sopenharmony_ci PrintMessage("Exit current process."); 135cc290419Sopenharmony_ci break; 136cc290419Sopenharmony_ci } 137cc290419Sopenharmony_ci } 138cc290419Sopenharmony_ci FreeInstance(); 139cc290419Sopenharmony_ci#endif // JS_JDWP_CONNECT 140cc290419Sopenharmony_ci return 0; 141cc290419Sopenharmony_ci}