/* * Copyright (C) 2021 Huawei Device Co., Ltd. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include "include/startup_delay.h" #include "include/sp_utils.h" #include "include/sp_log.h" #include "include/common.h" namespace OHOS { namespace SmartPerf { StartUpDelay::StartUpDelay() {} StartUpDelay::~StartUpDelay() {} void StartUpDelay::GetTrace(const std::string &traceName) const { std::string result; std::string cmdString; if (SPUtils::IsHmKernel()) { cmdString = CMD_COMMAND_MAP.at(CmdCommand::HITRACE_1024); } else { cmdString = CMD_COMMAND_MAP.at(CmdCommand::HITRACE_2048); } SPUtils::LoadCmd(cmdString + traceName, result); if (result.find("OpenRecording failed") != std::string::npos) { std::string str; std::string traceFinishStr = "hitrace --trace_finish"; SPUtils::LoadCmd(traceFinishStr, str); SPUtils::LoadCmd(cmdString + traceName, result); } } void StartUpDelay::GetHisysId() const { int time = 10; sleep(time); std::string str = ""; std::string cmd = HISYSEVENT_CMD_MAP.at(HisyseventCmd::HISYSEVENT); SPUtils::LoadCmd(cmd, str); std::stringstream ss(str); std::string line = ""; getline(ss, line); std::stringstream ssLine(line); std::string word = ""; std::string secondStr; int count = 0; int num = 2; while (ssLine >> word) { count++; if (count == num) { secondStr = word; break; } } std::string killCmd = CMD_COMMAND_MAP.at(CmdCommand::KILL_CMD); SPUtils::LoadCmd(killCmd + secondStr, str); } void StartUpDelay::GetHisysIdAndKill() const { int time = 10; sleep(time); std::string str = ""; std::string cmd = HISYSEVENT_CMD_MAP.at(HisyseventCmd::HISYS_PID); SPUtils::LoadCmd(cmd, str); std::stringstream ss(str); std::vector hisysIdVec; std::string singleId; while (ss >> singleId) { hisysIdVec.push_back(singleId); } std::string killCmd = CMD_COMMAND_MAP.at(CmdCommand::KILL_CMD); for (size_t i = 0; i < hisysIdVec.size(); i++) { SPUtils::LoadCmd(killCmd + hisysIdVec[i], str); } } bool StartUpDelay::GetSpTcp() { std::string resultPid; std::string str; std::string cmd = CMD_COMMAND_MAP.at(CmdCommand::PIDOF_SP); SPUtils::LoadCmd(cmd, resultPid); std::vector vec; std::string token; size_t pos = 0; while ((pos = resultPid.find(' ')) != std::string::npos) { token = resultPid.substr(0, pos); vec.push_back(token); resultPid.erase(0, pos + 1); } if (vec.size() > 0) { std::string killCmd = CMD_COMMAND_MAP.at(CmdCommand::KILL_CMD); for (size_t i = 0; i < vec.size(); i++) { SPUtils::LoadCmd(killCmd + vec[i], str); } } return false; } bool StartUpDelay::GetSpClear() const { std::string resultPid; std::string str; std::string cmd = CMD_COMMAND_MAP.at(CmdCommand::PIDOF_SP); SPUtils::LoadCmd("pidof SP_daemon", resultPid); std::string token; std::string curPid = std::to_string(getpid()); std::stringstream ss(resultPid); std::string killCmd = CMD_COMMAND_MAP.at(CmdCommand::KILL_CMD); while (ss >> token) { if (token != curPid) { SPUtils::LoadCmd("kill " + token, str); } } return false; } void StartUpDelay::ClearOldServer() const { std::string curPid = std::to_string(getpid()); std::string commandServer = CMD_COMMAND_MAP.at(CmdCommand::SERVER_GREP); std::string resultPidServer; std::string commandEditorServer = CMD_COMMAND_MAP.at(CmdCommand::EDITOR_SERVER_GREP); std::string resultPidEditorServer; SPUtils::LoadCmdWithLinkBreak(commandServer, false, resultPidServer); SPUtils::LoadCmdWithLinkBreak(commandEditorServer, false, resultPidEditorServer); std::istringstream iss(resultPidServer + '\n' + resultPidEditorServer); std::string resultLine; std::string killResult; std::string killCmd = CMD_COMMAND_MAP.at(CmdCommand::KILL_CMD); while (std::getline(iss, resultLine)) { if (resultLine.empty() || resultLine.find("sh -c") != std::string::npos) { continue; } std::istringstream lineStream(resultLine); std::string token; int count = 0; while (lineStream >> token) { if (count == 1) { break; } count++; } if (token != curPid) { SPUtils::LoadCmd(killCmd + token, killResult); LOGI("Find old server: %s, killed.", token.c_str()); } } } std::string StartUpDelay::ExecuteCommand(const std::string &command, const std::vector &args) { std::string output = ""; int pipefd[2]; if (pipe(pipefd) == -1) { LOGE("startup_delay::Failed to create pipe: %s", strerror(errno)); return output; } pid_t pid = fork(); if (pid == -1) { LOGE("startup_delay::Failed to fork: %s", strerror(errno)); close(pipefd[0]); close(pipefd[1]); return output; } if (pid == 0) { close(pipefd[0]); dup2(pipefd[1], STDOUT_FILENO); close(pipefd[1]); std::vector argv(args.size() + 1); for (size_t i = 0; i < args.size(); ++i) { argv[i] = const_cast(args[i].c_str()); } argv[args.size()] = nullptr; execvp(command.c_str(), argv.data()); LOGE("startup_delay::Failed to execute pid: %s", strerror(errno)); _exit(EXIT_FAILURE); } close(pipefd[1]); char buf[1024]; ssize_t nread; while ((nread = read(pipefd[0], buf, sizeof(buf) - 1)) > 0) { if (nread == sizeof(buf) - 1) { LOGE("startup_delay::Buffer overflow: %s", strerror(errno)); break; } buf[nread] = '\0'; output.append(buf); } if (nread == -1) { LOGE("startup_delay::Failed to read from pipe: %s", strerror(errno)); } close(pipefd[0]); int status; if (waitpid(pid, &status, 0) == -1) { LOGE("startup_delay::Failed to wait for child process: %s", strerror(errno)); return output; } return output; } std::string StartUpDelay::GetPidByPkg(const std::string &curPkgName) { const std::string pidof = "pidof"; const std::vector args = {pidof, curPkgName}; std::string resultProcId = ExecuteCommand(pidof, args); if (!resultProcId.empty() && resultProcId.back() == '\n') { resultProcId.pop_back(); LOGI("startup_delay::output: (%s)", resultProcId.c_str()); } return resultProcId; } } }