1 /*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15 #include "dump_manager_cpu_service.h"
16 #include <file_ex.h>
17 #include <if_system_ability_manager.h>
18 #include <ipc_skeleton.h>
19 #include <iservice_registry.h>
20 #include <string_ex.h>
21 #include <system_ability_definition.h>
22 #include <thread>
23 #include <unistd.h>
24 #include "securec.h"
25
26 #include "common/dumper_constant.h"
27 #include "dump_log_manager.h"
28 #include "hilog_wrapper.h"
29 #include "inner/dump_service_id.h"
30 #include "manager/dump_implement.h"
31 #include "dump_utils.h"
32 #include "util/string_utils.h"
33 #include "util/file_utils.h"
34 #ifdef HIDUMPER_ABILITY_BASE_ENABLE
35 #include "dump_app_state_observer.h"
36 #endif
37 #ifdef HIDUMPER_BATTERY_ENABLE
38 #include "common_event_data.h"
39 #include "common_event_manager.h"
40 #include "common_event_support.h"
41 #include "dump_battery_stats_subscriber.h"
42 #endif
43
44 using namespace std;
45 namespace OHOS {
46 namespace HiviewDFX {
47 namespace {
48 const std::string DUMPMGR_CPU_SERVICE_NAME = "HiDumperCpuService";
49 static const std::string LOAD_AVG_FILE_PATH = "/proc/loadavg";
50 static constexpr size_t LOAD_AVG_INFO_COUNT = 3;
51 static constexpr int PROC_CPU_LENGTH = 256;
52 static constexpr long unsigned HUNDRED_PERCENT_VALUE = 100;
53 static constexpr long unsigned DELAY_VALUE = 100000;
54 static constexpr int INVALID_PID = -1;
55 }
DumpManagerCpuService()56 DumpManagerCpuService::DumpManagerCpuService() : SystemAbility(DFX_SYS_HIDUMPER_CPU_ABILITY_ID, true)
57 {
58 }
59
~DumpManagerCpuService()60 DumpManagerCpuService::~DumpManagerCpuService()
61 {
62 delete sysAbilityListener_;
63 }
64
OnStart()65 void DumpManagerCpuService::OnStart()
66 {
67 DUMPER_HILOGI(MODULE_CPU_SERVICE, "on start");
68 if (started_) {
69 DUMPER_HILOGE(MODULE_CPU_SERVICE, "it's ready, nothing to do.");
70 return;
71 }
72
73 DUMPER_HILOGI(MODULE_CPU_SERVICE, "cpu service OnStart");
74 if (!Init()) {
75 DUMPER_HILOGE(MODULE_CPU_SERVICE, "init fail, nothing to do.");
76 return;
77 }
78
79 started_ = true;
80 }
81
Request(DumpCpuData & dumpCpuData)82 int32_t DumpManagerCpuService::Request(DumpCpuData &dumpCpuData)
83 {
84 DUMPER_HILOGI(MODULE_CPU_SERVICE, "enter");
85 static std::mutex mutex_;
86 unique_lock<mutex> lock(mutex_);
87 InitParam(dumpCpuData);
88 int32_t ret = DumpCpuUsageData();
89 dumpCpuData.dumpCPUDatas_ = *dumpCPUDatas_;
90 ResetParam();
91 return ret;
92 }
93
GetHandler()94 std::shared_ptr<DumpEventHandler> DumpManagerCpuService::GetHandler()
95 {
96 if (handler_ == nullptr) {
97 DUMPER_HILOGI(MODULE_CPU_SERVICE, "init handler at get handler");
98 auto dumpManagerCpuService = DumpDelayedSpSingleton<DumpManagerCpuService>::GetInstance();
99 handler_ = std::make_shared<DumpEventHandler>(eventRunner_, dumpManagerCpuService);
100 }
101 return handler_;
102 }
103
Init()104 bool DumpManagerCpuService::Init()
105 {
106 DUMPER_HILOGI(MODULE_CPU_SERVICE, "init");
107 if (sysAbilityListener_ != nullptr) {
108 return false;
109 }
110
111 sysAbilityListener_ = new (std::nothrow) SystemAbilityStatusChangeListener();
112 if (sysAbilityListener_ == nullptr) {
113 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Failed to create statusChangeListener due to no memory");
114 return false;
115 }
116
117 sptr<ISystemAbilityManager> systemAbilityManager
118 = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
119 if (systemAbilityManager == nullptr) {
120 DUMPER_HILOGE(MODULE_CPU_SERVICE, "systemAbilityManager is null");
121 return false;
122 }
123 #ifdef HIDUMPER_ABILITY_BASE_ENABLE
124 if (systemAbilityManager->SubscribeSystemAbility(APP_MGR_SERVICE_ID, sysAbilityListener_) != ERR_OK) {
125 DUMPER_HILOGE(MODULE_CPU_SERVICE, "subscribe system ability id: %{public}d failed", APP_MGR_SERVICE_ID);
126 }
127 #endif
128 #ifdef HIDUMPER_BATTERY_ENABLE
129 if (systemAbilityManager->SubscribeSystemAbility(COMMON_EVENT_SERVICE_ID, sysAbilityListener_) != ERR_OK) {
130 DUMPER_HILOGE(MODULE_CPU_SERVICE, "subscribe system ability id: %{public}d failed",
131 COMMON_EVENT_SERVICE_ID);
132 }
133 #endif
134
135 return true;
136 }
137
EventHandlerInit()138 void DumpManagerCpuService::EventHandlerInit()
139 {
140 if (registered_) {
141 return;
142 }
143 if (eventRunner_ == nullptr) {
144 eventRunner_ = AppExecFwk::EventRunner::Create(DUMPMGR_CPU_SERVICE_NAME);
145 if (eventRunner_ == nullptr) {
146 DUMPER_HILOGE(MODULE_CPU_SERVICE, "create EventRunner");
147 return;
148 }
149 }
150 eventRunner_->Run();
151
152 if (handler_ == nullptr) {
153 DUMPER_HILOGI(MODULE_CPU_SERVICE, "init handler at init");
154 auto dumpManagerCpuService = DumpDelayedSpSingleton<DumpManagerCpuService>::GetInstance();
155 handler_ = std::make_shared<DumpEventHandler>(eventRunner_, dumpManagerCpuService);
156 }
157 handler_->SendEvent(DumpEventHandler::MSG_GET_CPU_INFO_ID, DumpEventHandler::GET_CPU_INFO_DELAY_TIME_INIT);
158
159 registered_ = true;
160 }
161
SendImmediateEvent()162 bool DumpManagerCpuService::SendImmediateEvent()
163 {
164 DUMPER_HILOGI(MODULE_CPU_SERVICE, "send immediate event");
165 if (DumpCpuInfoUtil::GetInstance().IsNeedRefreshCpu()) {
166 return false;
167 }
168 if (eventRunner_ == nullptr) {
169 eventRunner_ = AppExecFwk::EventRunner::Create(DUMPMGR_CPU_SERVICE_NAME);
170 if (eventRunner_ == nullptr) {
171 DUMPER_HILOGE(MODULE_CPU_SERVICE, "create EventRunner");
172 return false;
173 }
174 }
175
176 if (handler_ == nullptr) {
177 auto dumpManagerCpuService = DumpDelayedSpSingleton<DumpManagerCpuService>::GetInstance();
178 handler_ = std::make_shared<DumpEventHandler>(eventRunner_, dumpManagerCpuService);
179 }
180
181 handler_->SendImmediateEvent(DumpEventHandler::MSG_GET_CPU_INFO_ID);
182 return true;
183 }
184
OnAddSystemAbility(int32_t systemAbilityId,const std::string & deviceId)185 void DumpManagerCpuService::SystemAbilityStatusChangeListener::OnAddSystemAbility(
186 int32_t systemAbilityId, const std::string& deviceId)
187 {
188 DUMPER_HILOGI(MODULE_CPU_SERVICE, "systemAbilityId=%{public}d, deviceId=%{private}s", systemAbilityId,
189 deviceId.c_str());
190 auto dumpManagerCpuService = DumpDelayedSpSingleton<DumpManagerCpuService>::GetInstance();
191
192 #ifdef HIDUMPER_ABILITY_BASE_ENABLE
193 if (systemAbilityId == APP_MGR_SERVICE_ID) {
194 dumpManagerCpuService->SubscribeAppStateEvent();
195 }
196 #endif
197 #ifdef HIDUMPER_BATTERY_ENABLE
198 if (systemAbilityId == COMMON_EVENT_SERVICE_ID) {
199 dumpManagerCpuService->SubscribeCommonEvent();
200 }
201 #endif
202
203 dumpManagerCpuService->EventHandlerInit();
204 }
205
OnRemoveSystemAbility(int32_t systemAbilityId,const std::string & deviceId)206 void DumpManagerCpuService::SystemAbilityStatusChangeListener::OnRemoveSystemAbility(
207 int32_t systemAbilityId, const std::string& deviceId)
208 {
209 DUMPER_HILOGI(MODULE_CPU_SERVICE, "Remove system ability, system ability id");
210 }
211
212 #ifdef HIDUMPER_ABILITY_BASE_ENABLE
SubscribeAppStateEvent()213 bool DumpManagerCpuService::SubscribeAppStateEvent()
214 {
215 return DumpAppStateObserver::GetInstance().SubscribeAppState();
216 }
217 #endif
218
219 #ifdef HIDUMPER_BATTERY_ENABLE
SubscribeCommonEvent()220 bool DumpManagerCpuService::SubscribeCommonEvent()
221 {
222 DUMPER_HILOGI(MODULE_CPU_SERVICE, "Subscribe CommonEvent enter");
223 bool result = false;
224 OHOS::EventFwk::MatchingSkills matchingSkills;
225 matchingSkills.AddEvent(OHOS::EventFwk::CommonEventSupport::COMMON_EVENT_BATTERY_CHANGED);
226 OHOS::EventFwk::CommonEventSubscribeInfo subscribeInfo(matchingSkills);
227 std::shared_ptr<EventFwk::CommonEventSubscriber> subscriberPtr =
228 std::make_shared<DumpBatteryStatsSubscriber>(subscribeInfo);
229 result = OHOS::EventFwk::CommonEventManager::SubscribeCommonEvent(subscriberPtr);
230 if (!result) {
231 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Subscribe CommonEvent failed");
232 } else {
233 DUMPER_HILOGI(MODULE_CPU_SERVICE, "Subscribe CommonEvent success");
234 }
235 return result;
236 }
237 #endif
238
InitParam(DumpCpuData & dumpCpuData)239 void DumpManagerCpuService::InitParam(DumpCpuData &dumpCpuData)
240 {
241 cpuUsagePid_ = dumpCpuData.cpuUsagePid_;
242 if (cpuUsagePid_ != INVALID_PID) {
243 curSpecProc_ = std::make_shared<ProcInfo>();
244 oldSpecProc_ = std::make_shared<ProcInfo>();
245 }
246 curCPUInfo_ = std::make_shared<CPUInfo>();
247 oldCPUInfo_ = std::make_shared<CPUInfo>();
248 dumpCPUDatas_ = std::make_shared<std::vector<std::vector<std::string>>>(dumpCpuData.dumpCPUDatas_);
249 }
250
ResetParam()251 void DumpManagerCpuService::ResetParam()
252 {
253 curCPUInfo_.reset();
254 oldCPUInfo_.reset();
255 curProcs_.clear();
256 oldProcs_.clear();
257 if (cpuUsagePid_ != INVALID_PID) {
258 curSpecProc_.reset();
259 oldSpecProc_.reset();
260 }
261 }
262
DumpCpuUsageData()263 int DumpManagerCpuService::DumpCpuUsageData()
264 {
265 if (!DumpCpuInfoUtil::GetInstance().GetCurCPUInfo(curCPUInfo_)) {
266 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Get current cpu info failed!.");
267 return DumpStatus::DUMP_FAIL;
268 }
269 if (!DumpCpuInfoUtil::GetInstance().GetOldCPUInfo(oldCPUInfo_)) {
270 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Get old cpu info failed!.");
271 return DumpStatus::DUMP_FAIL;
272 }
273
274 if (cpuUsagePid_ != INVALID_PID) {
275 if (!GetProcCPUInfo()) {
276 return DumpStatus::DUMP_FAIL;
277 }
278 } else {
279 if (!DumpCpuInfoUtil::GetInstance().GetCurProcInfo(curProcs_)) {
280 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Get current process info failed!.");
281 return DumpStatus::DUMP_FAIL;
282 }
283 if (!DumpCpuInfoUtil::GetInstance().GetOldProcInfo(oldProcs_)) {
284 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Get old process info failed!.");
285 return DumpStatus::DUMP_FAIL;
286 }
287 }
288 std::string avgInfo;
289 DumpStatus ret = ReadLoadAvgInfo(LOAD_AVG_FILE_PATH, avgInfo);
290 if (ret != DumpStatus::DUMP_OK) {
291 DUMPER_HILOGD(MODULE_CPU_SERVICE, "Get LoadAvgInfo failed!");
292 return DumpStatus::DUMP_FAIL;
293 }
294 AddStrLineToDumpInfo(avgInfo);
295
296 DumpCpuInfoUtil::GetInstance().GetUpdateCpuStartTime(startTime_);
297 DumpCpuInfoUtil::GetInstance().GetDateAndTime(endTime_);
298 std::string dumpTimeStr;
299 CreateDumpTimeString(startTime_, endTime_, dumpTimeStr);
300 AddStrLineToDumpInfo(dumpTimeStr);
301
302 std::string cpuStatStr;
303 CreateCPUStatString(cpuStatStr);
304 AddStrLineToDumpInfo(cpuStatStr);
305
306 DumpProcInfo();
307 SendImmediateEvent();
308 return DumpStatus::DUMP_OK;
309 }
310
GetProcCPUInfo()311 bool DumpManagerCpuService::GetProcCPUInfo()
312 {
313 bool ret = false;
314 if (!DumpCpuInfoUtil::GetInstance().GetOldSpecProcInfo(cpuUsagePid_, oldSpecProc_)) {
315 DumpCpuInfoUtil::GetInstance().UpdateCpuInfo();
316 if (!DumpCpuInfoUtil::GetInstance().GetOldSpecProcInfo(cpuUsagePid_, oldSpecProc_)) {
317 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Get old process %{public}d info failed!.", cpuUsagePid_);
318 return ret;
319 }
320
321 DumpCpuInfoUtil::GetInstance().CopyCpuInfo(oldCPUInfo_, curCPUInfo_);
322 usleep(DELAY_VALUE);
323 if (!DumpCpuInfoUtil::GetInstance().GetCurCPUInfo(curCPUInfo_)) {
324 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Get current cpu info failed!.");
325 return ret;
326 }
327 }
328
329 if (!DumpCpuInfoUtil::GetInstance().GetCurSpecProcInfo(cpuUsagePid_, curSpecProc_)) {
330 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Get current process %{public}d info failed!.", cpuUsagePid_);
331 return ret;
332 }
333 ret = true;
334 return ret;
335 }
336
ReadLoadAvgInfo(const std::string & filePath,std::string & info)337 DumpStatus DumpManagerCpuService::ReadLoadAvgInfo(const std::string &filePath, std::string &info)
338 {
339 if (!FileExists(filePath)) {
340 return DumpStatus::DUMP_FAIL;
341 }
342
343 std::string rawData;
344 bool ret = FileUtils::GetInstance().LoadStringFromProcCb(filePath, false, false, [&](const string& line) -> void {
345 rawData += line;
346 });
347 if (!ret) {
348 return DumpStatus::DUMP_FAIL;
349 }
350 DUMPER_HILOGD(MODULE_CPU_SERVICE, "rawData is %{public}s", rawData.c_str());
351 std::vector<std::string> vec;
352 SplitStr(rawData, DumpUtils::SPACE, vec);
353 info = "Load average:";
354 for (size_t i = 0; i < LOAD_AVG_INFO_COUNT; i++) {
355 info.append(" ");
356 info.append(vec[i]);
357 if (i == LOAD_AVG_INFO_COUNT - 1) {
358 info.append(";");
359 } else {
360 info.append(" /");
361 }
362 }
363 info.append(" the cpu load average in 1 min, 5 min and 15 min");
364 DUMPER_HILOGD(MODULE_CPU_SERVICE, "info is %{public}s", info.c_str());
365 return DumpStatus::DUMP_OK;
366 }
367
CreateDumpTimeString(const std::string & startTime,const std::string & endTime,std::string & timeStr)368 void DumpManagerCpuService::CreateDumpTimeString(const std::string &startTime,
369 const std::string &endTime, std::string &timeStr)
370 {
371 DUMPER_HILOGD(MODULE_CPU_SERVICE, "start:%{public}s, end:%{public}s", startTime.c_str(), endTime.c_str());
372 timeStr = "CPU usage from";
373 timeStr.append(startTime);
374 timeStr.append(" to");
375 timeStr.append(endTime);
376 }
377
AddStrLineToDumpInfo(const std::string & strLine)378 void DumpManagerCpuService::AddStrLineToDumpInfo(const std::string &strLine)
379 {
380 std::vector<std::string> vec;
381 vec.push_back(strLine);
382 dumpCPUDatas_->push_back(vec);
383 }
384
CreateCPUStatString(std::string & str)385 void DumpManagerCpuService::CreateCPUStatString(std::string &str)
386 {
387 long unsigned totalDeltaTime = (curCPUInfo_->uTime + curCPUInfo_->nTime + curCPUInfo_->sTime + curCPUInfo_->iTime
388 + curCPUInfo_->iowTime + curCPUInfo_->irqTime + curCPUInfo_->sirqTime)
389 - (oldCPUInfo_->uTime + oldCPUInfo_->nTime + oldCPUInfo_->sTime + oldCPUInfo_->iTime
390 + oldCPUInfo_->iowTime + oldCPUInfo_->irqTime + oldCPUInfo_->sirqTime);
391 if (cpuUsagePid_ != INVALID_PID) {
392 curSpecProc_->userSpaceUsage =
393 (curSpecProc_->uTime - oldSpecProc_->uTime) * HUNDRED_PERCENT_VALUE / totalDeltaTime;
394 curSpecProc_->sysSpaceUsage =
395 (curSpecProc_->sTime - oldSpecProc_->sTime) * HUNDRED_PERCENT_VALUE / totalDeltaTime;
396 curSpecProc_->totalUsage = curSpecProc_->userSpaceUsage + curSpecProc_->sysSpaceUsage;
397 } else {
398 for (size_t i = 0; i < curProcs_.size(); i++) {
399 if (curProcs_[i] == nullptr) {
400 continue;
401 }
402 std::shared_ptr<ProcInfo> oldProc = GetOldProc(curProcs_[i]->pid);
403 if (oldProc) {
404 curProcs_[i]->userSpaceUsage =
405 (curProcs_[i]->uTime - oldProc->uTime) * HUNDRED_PERCENT_VALUE / totalDeltaTime;
406 curProcs_[i]->sysSpaceUsage =
407 (curProcs_[i]->sTime - oldProc->sTime) * HUNDRED_PERCENT_VALUE / totalDeltaTime;
408 curProcs_[i]->totalUsage = curProcs_[i]->userSpaceUsage + curProcs_[i]->sysSpaceUsage;
409 } else {
410 curProcs_[i]->userSpaceUsage = 0;
411 curProcs_[i]->sysSpaceUsage = 0;
412 curProcs_[i]->totalUsage = 0;
413 }
414 }
415 }
416
417 long unsigned userSpaceUsage =
418 ((curCPUInfo_->uTime + curCPUInfo_->nTime) - (oldCPUInfo_->uTime + oldCPUInfo_->nTime)) * HUNDRED_PERCENT_VALUE
419 / totalDeltaTime;
420 long unsigned sysSpaceUsage = (curCPUInfo_->sTime - oldCPUInfo_->sTime) * HUNDRED_PERCENT_VALUE / totalDeltaTime;
421 long unsigned iowUsage = (curCPUInfo_->iowTime - oldCPUInfo_->iowTime) * HUNDRED_PERCENT_VALUE / totalDeltaTime;
422 long unsigned irqUsage =
423 ((curCPUInfo_->irqTime + curCPUInfo_->sirqTime) - (oldCPUInfo_->irqTime + oldCPUInfo_->sirqTime))
424 * HUNDRED_PERCENT_VALUE / totalDeltaTime;
425 long unsigned idleUsage = (curCPUInfo_->iTime - oldCPUInfo_->iTime) * HUNDRED_PERCENT_VALUE / totalDeltaTime;
426 long unsigned totalUsage = userSpaceUsage + sysSpaceUsage;
427
428 str = "Total: ";
429 str.append(std::to_string(totalUsage)).append("%; ");
430 str.append("User Space: ").append(std::to_string(userSpaceUsage)).append("%; ");
431 str.append("Kernel Space: ").append(std::to_string(sysSpaceUsage)).append("%; ");
432 str.append("iowait: ").append(std::to_string(iowUsage)).append("%; ");
433 str.append("irq: ").append(std::to_string(irqUsage)).append("%; ");
434 str.append("idle: ").append(std::to_string(idleUsage)).append("%");
435 }
436
GetOldProc(const std::string & pid)437 std::shared_ptr<ProcInfo> DumpManagerCpuService::GetOldProc(const std::string &pid)
438 {
439 for (size_t i = 0; i < oldProcs_.size(); i++) {
440 if (StringUtils::GetInstance().IsSameStr(oldProcs_[i]->pid, pid)) {
441 return oldProcs_[i];
442 }
443 }
444 return nullptr;
445 }
446
DumpProcInfo()447 void DumpManagerCpuService::DumpProcInfo()
448 {
449 std::vector<std::shared_ptr<ProcInfo>> sortedInfos;
450 sortedInfos.assign(curProcs_.begin(), curProcs_.end());
451 std::sort(sortedInfos.begin(), sortedInfos.end(), SortProcInfo);
452
453 AddStrLineToDumpInfo("Details of Processes:");
454 AddStrLineToDumpInfo(" PID Total Usage User Space Kernel Space Page Fault Minor"
455 " Page Fault Major Name");
456 if (cpuUsagePid_ != INVALID_PID) {
457 char format[PROC_CPU_LENGTH] = {0};
458 int ret = sprintf_s(format, PROC_CPU_LENGTH,
459 " %-5s %3lu%% %3lu%%"
460 " %3lu%% %8s %8s %-15s",
461 (curSpecProc_->pid).c_str(), curSpecProc_->totalUsage,
462 curSpecProc_->userSpaceUsage, curSpecProc_->sysSpaceUsage,
463 (curSpecProc_->minflt).c_str(), (curSpecProc_->majflt).c_str(),
464 (curSpecProc_->comm).c_str());
465 AddStrLineToDumpInfo(std::string(format));
466 if (ret < 0) {
467 DUMPER_HILOGE(MODULE_CPU_SERVICE, "Dump process %{public}d cpu info failed!.", cpuUsagePid_);
468 }
469 return;
470 }
471 for (size_t i = 0; i < sortedInfos.size(); i++) {
472 char format[PROC_CPU_LENGTH] = {0};
473 int ret = sprintf_s(format, PROC_CPU_LENGTH,
474 " %-5s %3lu%% %3lu%%"
475 " %3lu%% %8s %8s %-15s",
476 (sortedInfos[i]->pid).c_str(), sortedInfos[i]->totalUsage,
477 sortedInfos[i]->userSpaceUsage, sortedInfos[i]->sysSpaceUsage,
478 (sortedInfos[i]->minflt).c_str(), (sortedInfos[i]->majflt).c_str(),
479 (sortedInfos[i]->comm).c_str());
480 if (ret < 0) {
481 continue;
482 }
483 AddStrLineToDumpInfo(std::string(format));
484 }
485 }
486
SortProcInfo(std::shared_ptr<ProcInfo> & left,std::shared_ptr<ProcInfo> & right)487 bool DumpManagerCpuService::SortProcInfo(std::shared_ptr<ProcInfo> &left, std::shared_ptr<ProcInfo> &right)
488 {
489 if (right->totalUsage != left->totalUsage) {
490 return right->totalUsage < left->totalUsage;
491 }
492 if (right->userSpaceUsage != left->userSpaceUsage) {
493 return right->userSpaceUsage < left->userSpaceUsage;
494 }
495 if (right->sysSpaceUsage != left->sysSpaceUsage) {
496 return right->sysSpaceUsage < left->sysSpaceUsage;
497 }
498 if (right->pid.length() != left->pid.length()) {
499 return right->pid.length() < left->pid.length();
500 }
501 return (right->pid.compare(left->pid) < 0);
502 }
503
StartService()504 void DumpManagerCpuService::StartService()
505 {
506 DUMPER_HILOGI(MODULE_CPU_SERVICE, "dumper StartService");
507 sptr<ISystemAbilityManager> samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
508 if (samgr == nullptr) {
509 DUMPER_HILOGE(MODULE_CPU_SERVICE, "failed to find SystemAbilityManager.");
510 return;
511 }
512 auto dumpManagerCpuService = DumpDelayedSpSingleton<DumpManagerCpuService>::GetInstance();
513 int ret = samgr->AddSystemAbility(DFX_SYS_HIDUMPER_CPU_ABILITY_ID, dumpManagerCpuService);
514 if (ret != 0) {
515 DUMPER_HILOGE(MODULE_CPU_SERVICE, "failed to add sys dump cpu service ability.");
516 return;
517 }
518 OnStart();
519 }
520 } // namespace HiviewDFX
521 } // namespace OHOS
522