diff --git a/services/flow_update/update_bin/bin_process.cpp b/services/flow_update/update_bin/bin_process.cpp index 18cbf402b3adb52e1f0d15736ab5fc0de2652e3d..78526993197c608865fd584d5824d6fec90f1bbd 100644 --- a/services/flow_update/update_bin/bin_process.cpp +++ b/services/flow_update/update_bin/bin_process.cpp @@ -31,6 +31,7 @@ using namespace std; using namespace Hpackage; using namespace Uscript; +using namespace Updater::Utils; namespace Updater { constexpr uint32_t STASH_BUFFER_SIZE = 4 * 1024 * 1024; @@ -232,7 +233,9 @@ int32_t UScriptInstructionBinFlowWrite::ProcessBinFile(Uscript::UScriptEnv &env, LOG(ERROR) << "Error to load flow data stream"; return USCRIPT_ERROR_EXECUTE; } - + LOG(INFO) << "Get binary tids"; + std::vector tids = GetAllTids(getpid()); + env.PostMessage("set_binary_tids", VectorToString(tids)); for (const auto &iter : innerFileNames) { // 根据镜像名称获取分区名称和大小 std::string partitionName = iter; diff --git a/services/include/updater/updater.h b/services/include/updater/updater.h index 0e8f4f669da236da139c88b271aea9efb9d453cc..8af7dd5298e6180d18944460799a3439504c1476 100644 --- a/services/include/updater/updater.h +++ b/services/include/updater/updater.h @@ -73,6 +73,7 @@ struct UpdaterParams { std::vector updatePackage {}; std::vector> installTime {}; std::function callbackProgress {}; + std::vector binaryTids {}; }; using CondFunc = std::function; @@ -146,10 +147,8 @@ std::vector &GetBootModes(void); std::optional SelectMode(const UpdateMessage &boot); -std::vector GetAllTids(pid_t pid); +bool SetCpuAffinityByPid(const UpdaterParams &upParams, unsigned int reservedCores); -bool SetCpuAffinityByPid(pid_t binaryPid, unsigned int reservedCores); - -void ReduceLoad(const UpdaterParams &upParams); +void UpdateBinaryTids(const std::vector &output, UpdaterParams &upParams); } // Updater #endif /* UPDATER_UPDATER_H */ diff --git a/services/updater.cpp b/services/updater.cpp index 11f710178c046746a029dd4ef22c90e829c41668..f7c7d97cb819654ea520c947488c2becf180900a 100644 --- a/services/updater.cpp +++ b/services/updater.cpp @@ -551,6 +551,8 @@ void HandleChildOutput(const std::string &buffer, int32_t bufferLen, bool &retry } } else if (outputHeader == "set_progress") { SetProgress(output, upParams); + } else if (outputHeader == "set_binary_tids") { + UpdateBinaryTids(output, upParams); } else { LOG(WARNING) << "Child process returns unexpected message."; } @@ -736,7 +738,6 @@ UpdaterStatus StartUpdaterProc(PkgManager::PkgManagerPtr pkgManager, UpdaterPara } upParams.binaryPid = pid; - ReduceLoad(upParams); close(pipeWrite); // close write endpoint bool retryUpdate = false; if (HandlePipeMsg(upParams, pipeRead, retryUpdate) != UPDATE_SUCCESS) { diff --git a/services/updater_binary/update_image_block.cpp b/services/updater_binary/update_image_block.cpp index a37187bf24502677ddd7f589c4d303ef426fc44c..4f09e7c25d54f70c8ffefa0c358c09f3cdf36b0f 100644 --- a/services/updater_binary/update_image_block.cpp +++ b/services/updater_binary/update_image_block.cpp @@ -35,6 +35,7 @@ using namespace Uscript; using namespace Hpackage; using namespace Updater; +using namespace Updater::Utils; namespace Updater { constexpr int32_t SHA_CHECK_SECOND = 2; @@ -426,7 +427,8 @@ static int32_t ExecuteUpdateBlock(Uscript::UScriptEnv &env, Uscript::UScriptCont env.GetPkgManager()->ClosePkgStream(outStream); return USCRIPT_ERROR_EXECUTE; } - + std::vector tids = GetAllTids(getpid()); + env.PostMessage("set_binary_tids", VectorToString(tids)); return DoExecuteUpdateBlock(infos, tm.get(), outStream, lines, context); } diff --git a/services/updater_utils.cpp b/services/updater_utils.cpp index ec17c43d352a711e0af0a924395bf587cc0c0a61..f23e8ef3aa1e09f5e3773e092a682d6432cddea2 100755 --- a/services/updater_utils.cpp +++ b/services/updater_utils.cpp @@ -13,8 +13,6 @@ * limitations under the License. */ #include -#include -#include #include #include #include @@ -293,44 +291,14 @@ std::optional SelectMode(const UpdateMessage &boot) return *it; } -std::vector GetAllTids(pid_t pid) +bool SetCpuAffinityByPid(const UpdaterParams &upParams, unsigned int reservedCores) { - std::vector tids; - std::string pathName = std::string("/proc/").append(std::to_string(pid)).append("/task"); - char tmpPath[PATH_MAX + 1] = {0}; - if (realpath(pathName.c_str(), tmpPath) == nullptr || tmpPath[0] == '\0') { - LOG(ERROR) << "realpath fail pathName:" << pathName; - return tids; - } - DIR *dir = opendir(tmpPath); - if (dir == nullptr) { - LOG(ERROR) << "opendir fail pathName:" << pathName; - return tids; - } - struct dirent *de = nullptr; - while ((de = readdir(dir)) != nullptr) { - if (!(de->d_type & DT_DIR) || !isdigit(de->d_name[0])) { - continue; - } - int32_t temp = -1; - if (!Utils::ConvertToLong(de->d_name, temp)) { - LOG(ERROR) << "ConvertToLong failed"; - continue; - } - pid_t tid = static_cast(temp); - if (tid > 0) { - tids.push_back(tid); - } - } - closedir(dir); - return tids; -} - -bool SetCpuAffinityByPid(pid_t binaryPid, unsigned int reservedCores) -{ - LOG(INFO) << "SetCpuAffinityByPid binaryPid:" << binaryPid; - if (binaryPid == -1) { - LOG(WARNING) << "invalid binaryPid:" << binaryPid; + static std::mutex setAffinityLock; + std::lock_guard lock(setAffinityLock); + std::vector binaryTids = upParams.binaryTids; + if (upParams.binaryPid == -1 || std::find( + binaryTids.begin(), binaryTids.end(), std::to_string(upParams.binaryPid)) == binaryTids.end()) { + LOG(WARNING) << "invalid binaryPid:" << upParams.binaryPid; return false; } unsigned int coreCount = std::thread::hardware_concurrency(); @@ -344,13 +312,14 @@ bool SetCpuAffinityByPid(pid_t binaryPid, unsigned int reservedCores) for (unsigned int i = 0; i < coreCount - reservedCores; i++) { CPU_SET(i, &mask); } - std::vector tids = GetAllTids(binaryPid); - if (tids.empty()) { - LOG(WARNING) << "set affinity faild, tids is null"; - return false; - } int syscallRes; - for (auto& tid : tids) { + for (auto &str : binaryTids) { + int32_t temp = -1; + if (!Utils::ConvertToLong(str, temp)) { + LOG(ERROR) << "ConvertToLong failed:" << str; + continue; + } + pid_t tid = static_cast(temp); syscallRes = syscall(__NR_sched_setaffinity, tid, sizeof(mask), &mask); LOG(INFO) << "setaffinity tid:" << tid; if (syscallRes != 0) { @@ -360,12 +329,19 @@ bool SetCpuAffinityByPid(pid_t binaryPid, unsigned int reservedCores) return true; } -void ReduceLoad(const UpdaterParams &upParams) +void UpdateBinaryTids(const std::vector &output, UpdaterParams &upParams) { + if (output.size() < DEFAULT_PROCESS_NUM) { + LOG(ERROR) << "check output fail"; + return; + } + auto outputInfo = Trim(output[1]); + LOG(INFO) << "binary tids:" << outputInfo; + upParams.binaryTids = SplitString(outputInfo, ","); if (upParams.isLoadReduction) { unsigned int coreCount = std::thread::hardware_concurrency(); unsigned int reservedCores = coreCount - LITTLE_CPU_CORES; - SetCpuAffinityByPid(upParams.binaryPid, reservedCores); + SetCpuAffinityByPid(upParams, reservedCores); } } } // namespace Updater diff --git a/utils/include/utils.h b/utils/include/utils.h index c8f93d68d2ccc912d8161fd1817b81282efd9df2..07fe7578f46c666372e733dddd07a8a424a93350 100644 --- a/utils/include/utils.h +++ b/utils/include/utils.h @@ -121,6 +121,8 @@ bool SetUpdateSuffix(std::string stringsuffix); int GetUpdateSlot(); std::string GetUpdateSuffix(); std::string GetUpdateActiveSuffix(); +std::vector GetAllTids(pid_t pid); +std::string VectorToString(const std::vector &pids); #ifndef __WIN32 void SetFileAttributes(const std::string& file, uid_t owner, gid_t group, mode_t mode); #endif diff --git a/utils/utils.cpp b/utils/utils.cpp index da4a4167427e255808f110bd5e6d7644da00446c..981ad9bf81be94b41b9f78a6f8befa24f39d5a10 100644 --- a/utils/utils.cpp +++ b/utils/utils.cpp @@ -1179,6 +1179,54 @@ std::string GetUpdateActiveSuffix() return std::string(paramValue); } +std::vector GetAllTids(pid_t pid) +{ + std::vector tids; + tids.push_back(pid); + std::string pathName = std::string("/proc/").append(std::to_string(pid)).append("/task"); + char tmpPath[PATH_MAX + 1] = {0}; + if (realpath(pathName.c_str(), tmpPath) == nullptr || tmpPath[0] == '\0') { + LOG(ERROR) << "realpath fail pathName:" << pathName; + return tids; + } + DIR *dir = opendir(tmpPath); + if (dir == nullptr) { + LOG(ERROR) << "opendir fail pathName:" << pathName; + return tids; + } + struct dirent *de = nullptr; + while ((de = readdir(dir)) != nullptr) { + if (!(de->d_type & DT_DIR) || !isdigit(de->d_name[0])) { + continue; + } + int32_t temp = -1; + if (!Utils::ConvertToLong(de->d_name, temp)) { + LOG(ERROR) << "ConvertToLong failed"; + continue; + } + pid_t tid = static_cast(temp); + if (tid > 0) { + tids.push_back(tid); + } + } + closedir(dir); + return tids; +} + +std::string VectorToString(const std::vector &pids) +{ + if (pids.empty()) { + return ""; + } + std::ostringstream oss; + auto it = pids.begin(); + oss << *it++; + while (it != pids.end()) { + oss << "," << *it++; + } + return oss.str(); +} + #ifndef __WIN32 void SetFileAttributes(const std::string& file, uid_t owner, gid_t group, mode_t mode) {