1 /*
2 * Copyright (c) 2022-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
16 #include "cgroup_event_handler.h"
17 #include <cinttypes>
18 #include "ability_info.h"
19 #include "app_mgr_constants.h"
20 #include "cgroup_adjuster.h"
21 #include "cgroup_sched_common.h"
22 #include "cgroup_sched_log.h"
23 #include "hisysevent.h"
24 #include "ressched_utils.h"
25 #include "res_type.h"
26 #include "sched_controller.h"
27 #include "sched_policy.h"
28 #include "system_ability_definition.h"
29 #ifdef POWER_MANAGER_ENABLE
30 #include "power_mgr_client.h"
31 #endif
32 #include "window_manager_lite.h"
33
34 #undef LOG_TAG
35 #define LOG_TAG "CgroupEventHandler"
36
37 namespace OHOS {
38 namespace ResourceSchedule {
39 namespace {
40 constexpr uint32_t EVENT_ID_REG_APP_STATE_OBSERVER = 1;
41 constexpr uint32_t EVENT_ID_REG_BGTASK_OBSERVER = 2;
42 constexpr uint32_t DELAYED_RETRY_REGISTER_DURATION = 100;
43 constexpr uint32_t MAX_RETRY_TIMES = 100;
44 constexpr uint32_t MAX_SPAN_SERIAL = 99;
45
46 const std::string MMI_SERVICE_NAME = "mmi_service";
47 }
48
49 using OHOS::AppExecFwk::ApplicationState;
50 using OHOS::AppExecFwk::AbilityState;
51 using OHOS::AppExecFwk::AbilityType;
52 using OHOS::AppExecFwk::ExtensionState;
53 using OHOS::AppExecFwk::ProcessType;
54
CgroupEventHandler(const std::string & queueName)55 CgroupEventHandler::CgroupEventHandler(const std::string &queueName)
56 {
57 cgroupEventQueue_ = std::make_shared<ffrt::queue>(queueName.c_str(),
58 ffrt::queue_attr().qos(ffrt::qos_user_interactive));
59 if (!cgroupEventQueue_) {
60 CGS_LOGE("%{public}s : create cgroupEventQueue_ failed", __func__);
61 }
62 }
63
~CgroupEventHandler()64 CgroupEventHandler::~CgroupEventHandler()
65 {
66 supervisor_ = nullptr;
67 cgroupEventQueue_ = nullptr;
68 delayTaskMap_.clear();
69 }
70
ProcessEvent(uint32_t eventId,int64_t eventParam)71 void CgroupEventHandler::ProcessEvent(uint32_t eventId, int64_t eventParam)
72 {
73 CGS_LOGD("%{public}s : eventId:%{public}d param:%{public}" PRIu64,
74 __func__, eventId, eventParam);
75 switch (eventId) {
76 case EVENT_ID_REG_APP_STATE_OBSERVER: {
77 int64_t retry = eventParam;
78 if (!SchedController::GetInstance().SubscribeAppState() &&
79 retry < MAX_RETRY_TIMES) {
80 eventId = EVENT_ID_REG_APP_STATE_OBSERVER;
81 eventParam = retry + 1;
82 this->PostTask(
83 [this, eventId, eventParam] {
84 this->ProcessEvent(eventId, eventParam);
85 },
86 std::to_string(eventId), DELAYED_RETRY_REGISTER_DURATION);
87 if (retry + 1 == static_cast<int64_t>(MAX_RETRY_TIMES)) {
88 HiSysEventWrite(HiviewDFX::HiSysEvent::Domain::RSS, "INIT_FAULT",
89 HiviewDFX::HiSysEvent::EventType::FAULT,
90 "COMPONENT_NAME", "MAIN",
91 "ERR_TYPE", "register failure",
92 "ERR_MSG", "Subscribe app status change observer failed.");
93 }
94 }
95 break;
96 }
97 case EVENT_ID_REG_BGTASK_OBSERVER: {
98 int64_t retry = eventParam;
99 if (!SchedController::GetInstance().SubscribeBackgroundTask() &&
100 retry < MAX_RETRY_TIMES) {
101 eventId = EVENT_ID_REG_BGTASK_OBSERVER;
102 eventParam = retry + 1;
103 this->PostTask(
104 [this, eventId, eventParam] {
105 this->ProcessEvent(eventId, eventParam);
106 },
107 std::to_string(eventId), DELAYED_RETRY_REGISTER_DURATION);
108 if (retry + 1 == static_cast<int64_t>(MAX_RETRY_TIMES)) {
109 HiSysEventWrite(HiviewDFX::HiSysEvent::Domain::RSS, "INIT_FAULT",
110 HiviewDFX::HiSysEvent::EventType::FAULT,
111 "COMPONENT_NAME", "MAIN",
112 "ERR_TYPE", "register failure",
113 "ERR_MSG", "Subscribe background task observer failed.");
114 }
115 }
116 break;
117 }
118 default:
119 break;
120 }
121 }
122
SetSupervisor(std::shared_ptr<Supervisor> supervisor)123 void CgroupEventHandler::SetSupervisor(std::shared_ptr<Supervisor> supervisor)
124 {
125 supervisor_ = supervisor;
126 }
127
HandleAbilityAdded(int32_t saId,const std::string & deviceId)128 void CgroupEventHandler::HandleAbilityAdded(int32_t saId, const std::string& deviceId)
129 {
130 switch (saId) {
131 case APP_MGR_SERVICE_ID:
132 this->RemoveTask(std::to_string(EVENT_ID_REG_APP_STATE_OBSERVER));
133 if (!SchedController::GetInstance().SubscribeAppState()) {
134 uint32_t eventId = EVENT_ID_REG_APP_STATE_OBSERVER;
135 int64_t eventParam = 0;
136 this->PostTask(
137 [this, eventId, eventParam] {
138 this->ProcessEvent(eventId, eventParam);
139 },
140 std::to_string(eventId), DELAYED_RETRY_REGISTER_DURATION);
141 }
142 if (supervisor_ != nullptr) {
143 supervisor_->InitSuperVisorContent();
144 }
145 break;
146 case WINDOW_MANAGER_SERVICE_ID:
147 SchedController::GetInstance().SubscribeWindowState();
148 break;
149 case BACKGROUND_TASK_MANAGER_SERVICE_ID:
150 this->RemoveTask(std::to_string(EVENT_ID_REG_BGTASK_OBSERVER));
151 if (!SchedController::GetInstance().SubscribeBackgroundTask()) {
152 uint32_t eventId = EVENT_ID_REG_BGTASK_OBSERVER;
153 int64_t eventParam = 0;
154 this->PostTask(
155 [this, eventId, eventParam] {
156 this->ProcessEvent(eventId, eventParam);
157 },
158 std::to_string(eventId), DELAYED_RETRY_REGISTER_DURATION);
159 }
160 break;
161 #ifdef POWER_MANAGER_ENABLE
162 case POWER_MANAGER_SERVICE_ID:
163 SchedController::GetInstance().GetRunningLockState();
164 break;
165 #endif
166 default:
167 break;
168 }
169 }
170
HandleAbilityRemoved(int32_t saId,const std::string & deviceId)171 void CgroupEventHandler::HandleAbilityRemoved(int32_t saId, const std::string& deviceId)
172 {
173 switch (saId) {
174 case APP_MGR_SERVICE_ID:
175 this->RemoveTask(std::to_string(EVENT_ID_REG_APP_STATE_OBSERVER));
176 SchedController::GetInstance().UnsubscribeAppState();
177 break;
178 case WINDOW_MANAGER_SERVICE_ID:
179 SchedController::GetInstance().UnsubscribeWindowState();
180 break;
181 case BACKGROUND_TASK_MANAGER_SERVICE_ID:
182 this->RemoveTask(std::to_string(EVENT_ID_REG_BGTASK_OBSERVER));
183 SchedController::GetInstance().UnsubscribeBackgroundTask();
184 break;
185 default:
186 break;
187 }
188 }
189
HandleApplicationStateChanged(uid_t uid,pid_t pid,const std::string & bundleName,int32_t state)190 void CgroupEventHandler::HandleApplicationStateChanged(uid_t uid, pid_t pid,
191 const std::string& bundleName, int32_t state)
192 {
193 if (!supervisor_) {
194 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
195 return;
196 }
197 CGS_LOGD("%{public}s : %{public}d, %{public}s, %{public}d", __func__, uid, bundleName.c_str(), state);
198 ChronoScope cs("HandleApplicationStateChanged");
199 if (state == (int32_t)(ApplicationState::APP_STATE_TERMINATED)) {
200 return;
201 }
202 std::shared_ptr<Application> app = supervisor_->GetAppRecordNonNull(uid);
203 app->SetName(bundleName);
204 app->state_ = state;
205 }
206
HandleOnAppStopped(uid_t uid,const std::string & bundleName)207 void CgroupEventHandler::HandleOnAppStopped(uid_t uid, const std::string& bundleName)
208 {
209 if (!supervisor_) {
210 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
211 return;
212 }
213 CGS_LOGI("%{public}s : %{public}d, %{public}s", __func__, uid, bundleName.c_str());
214 supervisor_->RemoveApplication(uid);
215 }
216
HandleProcessStateChanged(uid_t uid,pid_t pid,const std::string & bundleName,int32_t state)217 void CgroupEventHandler::HandleProcessStateChanged(uid_t uid, pid_t pid,
218 const std::string& bundleName, int32_t state)
219 {
220 if (!supervisor_) {
221 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
222 return;
223 }
224 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}s, %{public}d", __func__, uid,
225 pid, bundleName.c_str(), state);
226 ChronoScope cs("HandleProcessStateChanged");
227 std::shared_ptr<Application> app = supervisor_->GetAppRecordNonNull(uid);
228 std::shared_ptr<ProcessRecord> procRecord = app->GetProcessRecordNonNull(pid);
229 procRecord->processState_ = state;
230 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
231 AdjustSource::ADJS_PROCESS_STATE);
232 }
233
HandleAbilityStateChanged(uid_t uid,pid_t pid,const std::string & bundleName,const std::string & abilityName,uintptr_t token,int32_t abilityState,int32_t abilityType)234 void CgroupEventHandler::HandleAbilityStateChanged(uid_t uid, pid_t pid, const std::string& bundleName,
235 const std::string& abilityName, uintptr_t token, int32_t abilityState, int32_t abilityType)
236 {
237 if (!supervisor_) {
238 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
239 return;
240 }
241 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}s, %{public}s, %{public}d, %{public}d",
242 __func__, uid, pid, bundleName.c_str(), abilityName.c_str(), abilityState, abilityType);
243 if (abilityType == (int32_t)AbilityType::EXTENSION) {
244 CGS_LOGD("%{public}s : this type of event is not dealt with here", __func__);
245 return;
246 }
247 ChronoScope cs("HandleAbilityStateChanged");
248 if (abilityState == (int32_t)(AbilityState::ABILITY_STATE_TERMINATED)) {
249 auto app = supervisor_->GetAppRecord(uid);
250 if (app) {
251 auto procRecord = app->GetProcessRecord(pid);
252 if (procRecord) {
253 procRecord->RemoveAbilityByToken(token);
254 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
255 AdjustSource::ADJS_ABILITY_STATE);
256 }
257 }
258 return;
259 }
260 auto app = supervisor_->GetAppRecordNonNull(uid);
261 app->SetName(bundleName);
262 auto procRecord = app->GetProcessRecordNonNull(pid);
263 auto abiInfo = procRecord->GetAbilityInfoNonNull(token);
264 abiInfo->name_ = abilityName;
265 abiInfo->state_ = abilityState;
266 abiInfo->type_ = abilityType;
267 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
268 AdjustSource::ADJS_ABILITY_STATE);
269 }
270
HandleExtensionStateChanged(uid_t uid,pid_t pid,const std::string & bundleName,const std::string & abilityName,uintptr_t token,int32_t extensionState,int32_t abilityType)271 void CgroupEventHandler::HandleExtensionStateChanged(uid_t uid, pid_t pid, const std::string& bundleName,
272 const std::string& abilityName, uintptr_t token, int32_t extensionState, int32_t abilityType)
273 {
274 if (!supervisor_) {
275 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
276 return;
277 }
278 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}s, %{public}s, %{public}d, %{public}d",
279 __func__, uid, pid, bundleName.c_str(), abilityName.c_str(), extensionState, abilityType);
280 ChronoScope cs("HandleExtensionStateChanged");
281 if (extensionState == (int32_t)(ExtensionState::EXTENSION_STATE_TERMINATED)) {
282 auto app = supervisor_->GetAppRecord(uid);
283 if (app) {
284 auto procRecord = app->GetProcessRecord(pid);
285 if (procRecord) {
286 procRecord->RemoveAbilityByToken(token);
287 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
288 AdjustSource::ADJS_EXTENSION_STATE);
289 }
290 }
291 return;
292 }
293 auto app = supervisor_->GetAppRecordNonNull(uid);
294 app->SetName(bundleName);
295 auto procRecord = app->GetProcessRecordNonNull(pid);
296 auto abiInfo = procRecord->GetAbilityInfoNonNull(token);
297 abiInfo->name_ = abilityName;
298 abiInfo->estate_ = extensionState;
299 abiInfo->type_ = abilityType;
300 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
301 AdjustSource::ADJS_EXTENSION_STATE);
302 }
303
HandleProcessCreated(uid_t uid,pid_t pid,int32_t hostPid,int32_t processType,const std::string & bundleName,int32_t extensionType)304 void CgroupEventHandler::HandleProcessCreated(uid_t uid, pid_t pid, int32_t hostPid, int32_t processType,
305 const std::string& bundleName, int32_t extensionType)
306 {
307 if (!supervisor_) {
308 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
309 return;
310 }
311 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}d, %{public}d, %{public}s, %{public}d",
312 __func__, uid, pid, hostPid, processType, bundleName.c_str(), extensionType);
313 ChronoScope cs("HandleProcessCreated");
314 std::shared_ptr<Application> app = supervisor_->GetAppRecordNonNull(uid);
315 std::shared_ptr<ProcessRecord> procRecord = app->GetProcessRecordNonNull(pid);
316 app->SetName(bundleName);
317 switch (processType) {
318 case static_cast<int32_t>(ProcessType::RENDER):
319 procRecord->processType_ = ProcRecordType::RENDER;
320 procRecord->hostPid_ = hostPid;
321 app->AddHostProcess(hostPid);
322 break;
323 case static_cast<int32_t>(ProcessType::EXTENSION):
324 procRecord->processType_ = ProcRecordType::EXTENSION;
325 procRecord->extensionType_ = extensionType;
326 break;
327 case static_cast<int32_t>(ProcessType::GPU):
328 procRecord->processType_ = ProcRecordType::GPU;
329 procRecord->hostPid_ = hostPid;
330 app->AddHostProcess(hostPid);
331 break;
332 case static_cast<int32_t>(ProcessType::CHILD):
333 procRecord->processType_ = ProcRecordType::CHILD;
334 procRecord->hostPid_ = hostPid;
335 app->AddHostProcess(hostPid);
336 break;
337 default:
338 break;
339 }
340 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
341 AdjustSource::ADJS_PROCESS_CREATE);
342 }
343
HandleProcessDied(uid_t uid,pid_t pid,const std::string & bundleName)344 void CgroupEventHandler::HandleProcessDied(uid_t uid, pid_t pid, const std::string& bundleName)
345 {
346 if (!supervisor_) {
347 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
348 return;
349 }
350 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}s", __func__, uid, pid, bundleName.c_str());
351 std::shared_ptr<Application> app = supervisor_->GetAppRecord(uid);
352 if (!app) {
353 CGS_LOGE("%{public}s : application %{public}s not exist!", __func__, bundleName.c_str());
354 return;
355 }
356 std::shared_ptr<ProcessRecord> procRecord = app->GetProcessRecord(pid);
357 if (procRecord) {
358 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()),
359 ResType::RES_TYPE_PROCESS_STATE_CHANGE, ResType::ProcessStatus::PROCESS_DIED);
360 }
361 app->RemoveProcessRecord(pid);
362 // if all processes died, remove current app
363 if (app->GetPidsMap().size() == 0) {
364 supervisor_->RemoveApplication(uid);
365 }
366 }
367
HandleTransientTaskStart(uid_t uid,pid_t pid,const std::string & packageName)368 void CgroupEventHandler::HandleTransientTaskStart(uid_t uid, pid_t pid, const std::string& packageName)
369 {
370 if (!supervisor_) {
371 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
372 return;
373 }
374 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}s", __func__, uid, pid, packageName.c_str());
375 auto app = supervisor_->GetAppRecordNonNull(uid);
376 app->SetName(packageName);
377 auto procRecord = app->GetProcessRecord(pid);
378 if (!procRecord) {
379 return;
380 }
381 procRecord->runningTransientTask_ = true;
382 }
383
HandleTransientTaskEnd(uid_t uid,pid_t pid,const std::string & packageName)384 void CgroupEventHandler::HandleTransientTaskEnd(uid_t uid, pid_t pid, const std::string& packageName)
385 {
386 if (!supervisor_) {
387 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
388 return;
389 }
390 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}s", __func__, uid, pid, packageName.c_str());
391 auto app = supervisor_->GetAppRecordNonNull(uid);
392 app->SetName(packageName);
393 auto procRecord = app->GetProcessRecord(pid);
394 if (!procRecord) {
395 return;
396 }
397 procRecord->runningTransientTask_ = false;
398 }
399
HandleContinuousTaskUpdate(uid_t uid,pid_t pid,const std::vector<uint32_t> & typeIds,int32_t abilityId)400 void CgroupEventHandler::HandleContinuousTaskUpdate(uid_t uid, pid_t pid,
401 const std::vector<uint32_t>& typeIds, int32_t abilityId)
402 {
403 if (!supervisor_) {
404 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
405 return;
406 }
407 ChronoScope cs("HandleContinuousTaskUpdate");
408 auto app = supervisor_->GetAppRecordNonNull(uid);
409 auto procRecord = app->GetProcessRecordNonNull(pid);
410 procRecord->continuousTaskFlag_ = 0;
411 procRecord->abilityIdAndContinuousTaskFlagMap_[abilityId] = typeIds;
412 for (const auto& typeId : typeIds) {
413 CGS_LOGI("%{public}s : %{public}d, %{public}d, %{public}d, abilityId %{public}d,",
414 __func__, uid, pid, typeId, abilityId);
415 }
416 for (const auto& ablityIdAndcontinuousTaskFlag : procRecord->abilityIdAndContinuousTaskFlagMap_) {
417 for (const auto& typeId : ablityIdAndcontinuousTaskFlag.second) {
418 procRecord->continuousTaskFlag_ |= (1U << typeId);
419 }
420 }
421 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
422 AdjustSource::ADJS_CONTINUOUS_BEGIN);
423 }
424
HandleContinuousTaskCancel(uid_t uid,pid_t pid,int32_t typeId,int32_t abilityId)425 void CgroupEventHandler::HandleContinuousTaskCancel(uid_t uid, pid_t pid, int32_t typeId,
426 int32_t abilityId)
427 {
428 if (!supervisor_) {
429 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
430 return;
431 }
432 CGS_LOGI("%{public}s : %{public}d, %{public}d, %{public}d, %{public}d",
433 __func__, uid, pid, typeId, abilityId);
434 ChronoScope cs("HandleContinuousTaskCancel");
435 auto app = supervisor_->GetAppRecordNonNull(uid);
436 auto procRecord = app->GetProcessRecord(pid);
437 if (!procRecord) {
438 return;
439 }
440 procRecord->abilityIdAndContinuousTaskFlagMap_.erase(abilityId);
441 procRecord->continuousTaskFlag_ = 0;
442 for (const auto& ablityIdAndcontinuousTaskFlag : procRecord->abilityIdAndContinuousTaskFlagMap_) {
443 for (const auto& typeId : ablityIdAndcontinuousTaskFlag.second) {
444 procRecord->continuousTaskFlag_ |= (1U << typeId);
445 }
446 }
447 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
448 AdjustSource::ADJS_CONTINUOUS_END);
449 }
450
HandleFocusedWindow(uint32_t windowId,uintptr_t abilityToken,WindowType windowType,uint64_t displayId,int32_t pid,int32_t uid)451 void CgroupEventHandler::HandleFocusedWindow(uint32_t windowId, uintptr_t abilityToken,
452 WindowType windowType, uint64_t displayId, int32_t pid, int32_t uid)
453 {
454 if (!supervisor_) {
455 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
456 return;
457 }
458 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}" PRIu64 ", %{public}d, %{public}d",
459 __func__, windowId, windowType, displayId, pid, uid);
460 if (!abilityToken) {
461 CGS_LOGW("%{public}s : abilityToken nullptr!", __func__);
462 }
463 std::shared_ptr<Application> app = nullptr;
464 std::shared_ptr<ProcessRecord> procRecord = nullptr;
465 {
466 ChronoScope cs("HandleFocusedWindow");
467 app = supervisor_->GetAppRecordNonNull(uid);
468 procRecord = app->GetProcessRecordNonNull(pid);
469 auto win = procRecord->GetWindowInfoNonNull(windowId);
470 auto abi = procRecord->GetAbilityInfo(abilityToken);
471 procRecord->linkedWindowId_ = (int32_t)(windowId);
472 win->windowType_ = (int32_t)(windowType);
473 win->isFocused_ = true;
474 win->displayId_ = displayId;
475 win->ability_ = abi;
476
477 app->focusedProcess_ = procRecord;
478 auto lastFocusApp = supervisor_->focusedApp_;
479 if (lastFocusApp && lastFocusApp != app) {
480 lastFocusApp->focusedProcess_ = nullptr;
481 CgroupAdjuster::GetInstance().AdjustAllProcessGroup(*(lastFocusApp.get()),
482 AdjustSource::ADJS_FOCUSED_WINDOW);
483 }
484 supervisor_->focusedApp_ = app;
485 CgroupAdjuster::GetInstance().AdjustAllProcessGroup(*(app.get()), AdjustSource::ADJS_FOCUSED_WINDOW);
486 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()), ResType::RES_TYPE_WINDOW_FOCUS,
487 ResType::WindowFocusStatus::WINDOW_FOCUS);
488 }
489 if (app->GetName().empty()) {
490 app->SetName(SchedController::GetInstance().GetBundleNameByUid(uid));
491 }
492 }
493
HandleUnfocusedWindow(uint32_t windowId,uintptr_t abilityToken,WindowType windowType,uint64_t displayId,int32_t pid,int32_t uid)494 void CgroupEventHandler::HandleUnfocusedWindow(uint32_t windowId, uintptr_t abilityToken,
495 WindowType windowType, uint64_t displayId, int32_t pid, int32_t uid)
496 {
497 if (!supervisor_) {
498 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
499 return;
500 }
501 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}" PRIu64 ", %{public}d, %{public}d",
502 __func__, windowId, windowType, displayId, pid, uid);
503 if (!abilityToken) {
504 CGS_LOGW("%{public}s : abilityToken nullptr!", __func__);
505 }
506 std::shared_ptr<Application> app = nullptr;
507 std::shared_ptr<ProcessRecord> procRecord = nullptr;
508 {
509 ChronoScope cs("HandleUnfocusedWindow");
510 app = supervisor_->GetAppRecord(uid);
511 procRecord = app ? app->GetProcessRecord(pid) : nullptr;
512 if (!app || !procRecord) {
513 return;
514 }
515 auto win = procRecord->GetWindowInfoNonNull(windowId);
516 auto abi = procRecord->GetAbilityInfo(abilityToken);
517 win->windowType_ = (int32_t)(windowType);
518 win->isFocused_ = false;
519 win->displayId_ = displayId;
520 win->ability_ = abi;
521
522 if (app->focusedProcess_ == procRecord) {
523 app->focusedProcess_ = nullptr;
524 }
525 CgroupAdjuster::GetInstance().AdjustAllProcessGroup(*(app.get()), AdjustSource::ADJS_UNFOCUSED_WINDOW);
526 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()), ResType::RES_TYPE_WINDOW_FOCUS,
527 ResType::WindowFocusStatus::WINDOW_UNFOCUS);
528 }
529 if (app->GetName().empty()) {
530 app->SetName(SchedController::GetInstance().GetBundleNameByUid(uid));
531 }
532 }
533
HandleWindowVisibilityChanged(uint32_t windowId,uint32_t visibilityState,WindowType windowType,int32_t pid,int32_t uid)534 void CgroupEventHandler::HandleWindowVisibilityChanged(
535 uint32_t windowId, uint32_t visibilityState, WindowType windowType, int32_t pid, int32_t uid)
536 {
537 if (!supervisor_) {
538 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
539 return;
540 }
541 bool isVisible = visibilityState < Rosen::WindowVisibilityState::WINDOW_VISIBILITY_STATE_TOTALLY_OCCUSION;
542 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}d, %{public}d, %{public}d", __func__, windowId,
543 visibilityState, (int32_t)windowType, pid, uid);
544
545 std::shared_ptr<Application> app = nullptr;
546 std::shared_ptr<ProcessRecord> procRecord = nullptr;
547 if (isVisible) {
548 app = supervisor_->GetAppRecordNonNull(uid);
549 procRecord = app->GetProcessRecordNonNull(pid);
550 } else {
551 app = supervisor_->GetAppRecord(uid);
552 if (app) {
553 procRecord = app->GetProcessRecord(pid);
554 }
555 }
556 if (!procRecord) {
557 return;
558 }
559 auto windowInfo = procRecord->GetWindowInfoNonNull(windowId);
560 bool visibleStatusNotChanged = windowInfo->isVisible_ == isVisible;
561 windowInfo->visibilityState_ = visibilityState;
562 windowInfo->isVisible_ = isVisible;
563 windowInfo->windowType_ = (int32_t)windowType;
564
565 if (visibleStatusNotChanged) {
566 return;
567 }
568 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
569 AdjustSource::ADJS_WINDOW_VISIBILITY_CHANGED);
570 }
571
HandleDrawingContentChangeWindow(uint32_t windowId,WindowType windowType,bool drawingContentState,int32_t pid,int32_t uid)572 void CgroupEventHandler::HandleDrawingContentChangeWindow(
573 uint32_t windowId, WindowType windowType, bool drawingContentState, int32_t pid, int32_t uid)
574 {
575 if (!supervisor_) {
576 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
577 return;
578 }
579 CGS_LOGD("%{public}s : %{public}d, %{public}d, %{public}d, %{public}d, %{public}d", __func__, windowId,
580 drawingContentState, (int32_t)windowType, pid, uid);
581
582 std::shared_ptr<Application> app = supervisor_->GetAppRecord(uid);
583 std::shared_ptr<ProcessRecord> procRecord = app ? app->GetProcessRecord(pid) : nullptr;
584 if (!app || !procRecord) {
585 return;
586 }
587 procRecord->processDrawingState_ = drawingContentState;
588 auto windowInfo = procRecord->GetWindowInfoNonNull(windowId);
589 if (!windowInfo) {
590 CGS_LOGE("%{public}s : windowInfo nullptr!", __func__);
591 return;
592 }
593 windowInfo->drawingContentState_ = drawingContentState;
594 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()),
595 ResType::RES_TYPE_WINDOW_DRAWING_CONTENT_CHANGE,
596 drawingContentState ? ResType::WindowDrawingStatus::Drawing : ResType::WindowDrawingStatus::NotDrawing);
597 }
598
HandleReportMMIProcess(uint32_t resType,int64_t value,const nlohmann::json & payload)599 void CgroupEventHandler::HandleReportMMIProcess(uint32_t resType, int64_t value, const nlohmann::json& payload)
600 {
601 int32_t uid = 0;
602 int32_t pid = 0;
603 int32_t mmi_service;
604
605 if (!supervisor_) {
606 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
607 return;
608 }
609
610 if (!ParsePayload(uid, pid, mmi_service, value, payload)) {
611 return;
612 }
613
614 CGS_LOGD("%{public}s : %{public}u, %{public}d, %{public}d, %{public}d",
615 __func__, resType, uid, pid, mmi_service);
616 if (uid <= 0 || pid <= 0 || mmi_service <= 0) {
617 return;
618 }
619
620 auto app = supervisor_->GetAppRecordNonNull(uid);
621 app->SetName(MMI_SERVICE_NAME);
622 auto procRecord = app->GetProcessRecordNonNull(mmi_service);
623 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
624 AdjustSource::ADJS_REPORT_MMI_SERVICE_THREAD);
625 }
626
HandleReportRenderThread(uint32_t resType,int64_t value,const nlohmann::json & payload)627 void CgroupEventHandler::HandleReportRenderThread(uint32_t resType, int64_t value, const nlohmann::json& payload)
628 {
629 int32_t uid = 0;
630 int32_t pid = 0;
631 int32_t render = 0;
632
633 if (!supervisor_) {
634 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
635 return;
636 }
637
638 if (!ParsePayload(uid, pid, render, value, payload)) {
639 return;
640 }
641
642 CGS_LOGD("%{public}s : %{public}u, %{public}d, %{public}d, %{public}d",
643 __func__, resType, uid, pid, render);
644 if (uid <= 0 || pid <= 0 || render <= 0) {
645 return;
646 }
647
648 auto app = supervisor_->GetAppRecordNonNull(uid);
649 auto procRecord = app->GetProcessRecordNonNull(pid);
650 procRecord->renderTid_ = render;
651 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
652 AdjustSource::ADJS_REPORT_RENDER_THREAD);
653 }
654
HandleReportKeyThread(uint32_t resType,int64_t value,const nlohmann::json & payload)655 void CgroupEventHandler::HandleReportKeyThread(uint32_t resType, int64_t value, const nlohmann::json& payload)
656 {
657 int32_t uid = 0;
658 int32_t pid = 0;
659 int32_t keyTid = 0;
660 int32_t role = 0;
661
662 std::shared_ptr<Application> app = nullptr;
663 std::shared_ptr<ProcessRecord> procRecord = nullptr;
664 if (!GetProcInfoByPayload(uid, pid, app, procRecord, payload)) {
665 return;
666 }
667
668 if (!ParseValue(keyTid, "tid", payload) || !ParseValue(role, "role", payload)) {
669 return;
670 }
671
672 if (!ResSchedUtils::GetInstance().CheckTidIsInPid(pid, keyTid)) {
673 return;
674 }
675
676 if (value == ResType::ReportChangeStatus::CREATE) {
677 procRecord->keyThreadRoleMap_.emplace(keyTid, role);
678 } else {
679 procRecord->keyThreadRoleMap_.erase(keyTid);
680 }
681
682 // if role of thread is important display, adjust it
683 auto hostProcRecord = app->GetProcessRecord(procRecord->hostPid_);
684 if (!hostProcRecord) {
685 return;
686 }
687 CGS_LOGI("%{public}s : appName: %{public}s, uid: %{public}d, pid: %{public}d, keyTid: %{public}d",
688 __func__, app->GetName().c_str(), uid, pid, keyTid);
689 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(hostProcRecord.get()),
690 AdjustSource::ADJS_REPORT_IMPORTANT_DISPLAY_THREAD);
691 }
692
HandleReportWindowState(uint32_t resType,int64_t value,const nlohmann::json & payload)693 void CgroupEventHandler::HandleReportWindowState(uint32_t resType, int64_t value, const nlohmann::json& payload)
694 {
695 int32_t uid = 0;
696 int32_t pid = 0;
697 int32_t windowId = -1;
698 int32_t state = 0;
699 int32_t nowSerialNum = -1;
700
701 std::shared_ptr<Application> app = nullptr;
702 std::shared_ptr<ProcessRecord> procRecord = nullptr;
703 if (!GetProcInfoByPayload(uid, pid, app, procRecord, payload)) {
704 return;
705 }
706
707 if (!ParseValue(windowId, "windowId", payload) || !ParseValue(state, "state", payload) ||
708 !ParseValue(nowSerialNum, "serialNum", payload)) {
709 CGS_LOGW("%{public}s : param is not valid or not exist", __func__);
710 return;
711 }
712 CGS_LOGI("%{public}s : render process name: %{public}s, uid: %{public}d, pid: %{public}d, state: %{public}d",
713 __func__, app->GetName().c_str(), uid, pid, state);
714 if (nowSerialNum <= procRecord->serialNum_ &&
715 (procRecord->serialNum_ - nowSerialNum <= static_cast<int32_t>(MAX_SPAN_SERIAL))) {
716 return;
717 }
718 procRecord->serialNum_ = nowSerialNum;
719
720 if (state == ResType::WindowStates::ACTIVE) {
721 procRecord->linkedWindowId_ = windowId;
722 procRecord->isActive_ = true;
723 } else {
724 procRecord->linkedWindowId_ = -1;
725 procRecord->isActive_ = false;
726 }
727 auto hostProcRecord = app->GetProcessRecord(procRecord->hostPid_);
728 if (!hostProcRecord) {
729 return;
730 }
731 CGS_LOGI("%{public}s : pid: %{public}d, winId: %{public}d, isActive_: %{public}d",
732 __func__, pid, procRecord->linkedWindowId_, procRecord->isActive_);
733 UpdateActivepWebRenderInfo(uid, pid, windowId, state, hostProcRecord);
734 if (CheckVisibilityForRenderProcess(*(procRecord.get()), *hostProcRecord)) {
735 CGS_LOGW("%{public}s : bundle name: %{public}s, uid: %{public}d, pid: %{public}d, winId: %{public}d" \
736 "is not visible but active", __func__, app->GetName().c_str(), uid, pid, procRecord->linkedWindowId_);
737 }
738 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(hostProcRecord.get()),
739 AdjustSource::ADJS_REPORT_WINDOW_STATE_CHANGED);
740 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()),
741 ResType::RES_TYPE_REPORT_WINDOW_STATE, state);
742 }
743
UpdateActivepWebRenderInfo(int32_t uid,int32_t pid,int32_t windowId,int32_t state,const std::shared_ptr<ProcessRecord> & proc)744 void CgroupEventHandler::UpdateActivepWebRenderInfo(int32_t uid, int32_t pid, int32_t windowId, int32_t state,
745 const std::shared_ptr<ProcessRecord>& proc)
746 {
747 if (state != ResType::WindowStates::ACTIVE) {
748 return;
749 }
750 auto win = proc->GetWindowInfoNonNull(windowId);
751 win->topWebviewRenderUid_ = (uint32_t)(uid);
752 }
753
HandleReportAudioState(uint32_t resType,int64_t value,const nlohmann::json & payload)754 void CgroupEventHandler::HandleReportAudioState(uint32_t resType, int64_t value, const nlohmann::json& payload)
755 {
756 int32_t uid = 0;
757 int32_t pid = 0;
758
759 if (!supervisor_) {
760 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
761 return;
762 }
763
764 if (payload.contains("uid") && payload.at("uid").is_number_integer()) {
765 uid = payload["uid"].get<std::int32_t>();
766 }
767 if (payload.contains("pid") && payload.at("pid").is_number_integer()) {
768 pid = payload["pid"].get<std::int32_t>();
769 }
770 if (uid <= 0 || pid <= 0) {
771 return;
772 }
773
774 std::shared_ptr<Application> app = supervisor_->GetAppRecord(uid);
775 std::shared_ptr<ProcessRecord> procRecord = app ? app->GetProcessRecord(pid) : nullptr;
776 if (!app || !procRecord) {
777 return;
778 }
779 procRecord->audioPlayingState_ = static_cast<int32_t>(value);
780 CGS_LOGI("%{public}s : audio process name: %{public}s, uid: %{public}d, pid: %{public}d, state: %{public}d",
781 __func__, app->GetName().c_str(), uid, pid, procRecord->audioPlayingState_);
782
783 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
784 AdjustSource::ADJS_REPORT_AUDIO_STATE_CHANGED);
785 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()),
786 resType, static_cast<int32_t>(value));
787 }
788
HandleReportWebviewAudioState(uint32_t resType,int64_t value,const nlohmann::json & payload)789 void CgroupEventHandler::HandleReportWebviewAudioState(uint32_t resType, int64_t value, const nlohmann::json& payload)
790 {
791 int32_t uid = 0;
792 int32_t pid = 0;
793
794 if (!supervisor_) {
795 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
796 return;
797 }
798
799 if (!ParseValue(uid, "uid", payload) || !ParseValue(pid, "clientPid", payload)) {
800 return;
801 }
802 if (uid <= 0 || pid <= 0) {
803 CGS_LOGW("%{public}s : uid or pid invalid, uid: %{public}d, pid: %{public}d!",
804 __func__, uid, pid);
805 return;
806 }
807
808 std::shared_ptr<ProcessRecord> procRecord = supervisor_->FindProcessRecord(pid);
809 if (!procRecord) {
810 CGS_LOGW("%{public}s : proc record is not exist, uid: %{public}d, pid: %{public}d",
811 __func__, uid, pid);
812 return;
813 }
814
815 std::shared_ptr<Application> app = supervisor_->GetAppRecordNonNull(procRecord->GetUid());
816 procRecord->audioPlayingState_ = static_cast<int32_t>(value);
817 CGS_LOGI("%{public}s : audio process name: %{public}s, uid: %{public}d, pid: %{public}d, state: %{public}d",
818 __func__, app->GetName().c_str(), uid, pid, procRecord->audioPlayingState_);
819
820 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
821 AdjustSource::ADJS_REPORT_WEBVIEW_AUDIO_STATE_CHANGED);
822 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()),
823 resType, static_cast<int32_t>(value));
824 }
825
HandleReportRunningLockEvent(uint32_t resType,int64_t value,const nlohmann::json & payload)826 void CgroupEventHandler::HandleReportRunningLockEvent(uint32_t resType, int64_t value, const nlohmann::json& payload)
827 {
828 int32_t uid = 0;
829 int32_t pid = 0;
830 uint32_t type = 0;
831 int32_t state = -1;
832
833 if (!supervisor_) {
834 CGS_LOGE("%{public}s : supervisor nullptr.", __func__);
835 return;
836 }
837
838 if (!ParseValue(uid, "uid", payload) || !ParseValue(pid, "pid", payload)) {
839 return;
840 }
841 if (uid <= 0 || pid <= 0) {
842 return;
843 }
844 if (payload.contains("type") && payload.at("type").is_string()) {
845 type = static_cast<uint32_t>(atoi(payload["type"].get<std::string>().c_str()));
846 }
847 state = static_cast<int32_t>(value);
848 CGS_LOGI("report running lock event, uid:%{public}d, pid:%{public}d, lockType:%{public}d, state:%{public}d",
849 uid, pid, type, state);
850 #ifdef POWER_MANAGER_ENABLE
851 if (type == static_cast<uint32_t>(PowerMgr::RunningLockType::RUNNINGLOCK_PROXIMITY_SCREEN_CONTROL)) {
852 return;
853 }
854 std::shared_ptr<Application> app = supervisor_->GetAppRecord(uid);
855 std::shared_ptr<ProcessRecord> procRecord = app ? app->GetProcessRecord(pid) : nullptr;
856 if (!app || !procRecord) {
857 return;
858 }
859 procRecord->runningLockState_[type] = (state == ResType::RunninglockState::RUNNINGLOCK_STATE_ENABLE);
860 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()), resType, state);
861 #endif
862 }
863
HandleReportHisysEvent(uint32_t resType,int64_t value,const nlohmann::json & payload)864 void CgroupEventHandler::HandleReportHisysEvent(uint32_t resType, int64_t value, const nlohmann::json& payload)
865 {
866 int32_t uid = 0;
867 int32_t pid = 0;
868
869 if (!supervisor_) {
870 CGS_LOGE("%{public}s : supervisor nullptr.", __func__);
871 return;
872 }
873
874 if (!ParseValue(uid, "uid", payload) || !ParseValue(pid, "pid", payload)) {
875 return;
876 }
877 if (uid <= 0 || pid <= 0) {
878 return;
879 }
880 std::shared_ptr<Application> app = supervisor_->GetAppRecord(uid);
881 std::shared_ptr<ProcessRecord> procRecord = app ? app->GetProcessRecord(pid) : nullptr;
882 if (!app || !procRecord) {
883 return;
884 }
885
886 switch (resType) {
887 case ResType::RES_TYPE_REPORT_CAMERA_STATE: {
888 procRecord->cameraState_ = static_cast<int32_t>(value);
889 break;
890 }
891 case ResType::RES_TYPE_BLUETOOTH_A2DP_CONNECT_STATE_CHANGE: {
892 procRecord->bluetoothState_ = static_cast<int32_t>(value);
893 break;
894 }
895 case ResType::RES_TYPE_WIFI_CONNECT_STATE_CHANGE: {
896 procRecord->wifiState_ = static_cast<int32_t>(value);
897 break;
898 }
899 case ResType::RES_TYPE_MMI_INPUT_STATE: {
900 if (payload.contains("syncStatus") && payload.at("syncStatus").is_string()) {
901 procRecord->mmiStatus_ = atoi(payload["syncStatus"].get<std::string>().c_str());
902 }
903 break;
904 }
905 default: {
906 break;
907 }
908 }
909 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()),
910 resType, static_cast<int32_t>(value));
911 }
912
HandleReportScreenCaptureEvent(uint32_t resType,int64_t value,const nlohmann::json & payload)913 void CgroupEventHandler::HandleReportScreenCaptureEvent(uint32_t resType, int64_t value, const nlohmann::json& payload)
914 {
915 int32_t uid = 0;
916 int32_t pid = 0;
917
918 if (!supervisor_) {
919 CGS_LOGE("%{public}s: supervisor nullptr.", __func__);
920 return;
921 }
922
923 if (!ParseValue(uid, "uid", payload) || !ParseValue(pid, "pid", payload)) {
924 CGS_LOGE("%{public}s : payload does not contain uid or pid", __func__);
925 return;
926 }
927 if (uid <= 0 || pid <= 0) {
928 return;
929 }
930 CGS_LOGI("report screen capture event, uid:%{public}d, pid:%{public}d, value:%{public}d",
931 uid, pid, static_cast<int32_t>(value));
932 std::shared_ptr<Application> app = supervisor_->GetAppRecord(uid);
933 std::shared_ptr<ProcessRecord> procRecord = app ? app->GetProcessRecord(pid) : nullptr;
934 if (!app || !procRecord) {
935 return;
936 }
937 procRecord->screenCaptureState_ = (value == ResType::ScreenCaptureStatus::START_SCREEN_CAPTURE);
938 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
939 AdjustSource::ADJS_REPORT_SCREEN_CAPTURE);
940 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()),
941 resType, static_cast<int32_t>(value));
942 }
943
HandleReportAvCodecEvent(uint32_t resType,int64_t value,const nlohmann::json & payload)944 void CgroupEventHandler::HandleReportAvCodecEvent(uint32_t resType, int64_t value, const nlohmann::json& payload)
945 {
946 int32_t uid = 0;
947 int32_t pid = 0;
948 int32_t instanceId = -1;
949 int32_t state = -1;
950
951 if (!supervisor_) {
952 CGS_LOGE("%{public}s : supervisor nullptr.", __func__);
953 return;
954 }
955
956 if (!ParseValue(uid, "uid", payload) || !ParseValue(pid, "pid", payload)) {
957 return;
958 }
959 if (uid <= 0 || pid <= 0) {
960 return;
961 }
962 if (!ParseValue(instanceId, "instanceId", payload)) {
963 return;
964 }
965 if (instanceId < 0) {
966 return;
967 }
968 state = static_cast<int32_t>(value);
969 CGS_LOGI("report av_codec event, uid:%{public}d, pid:%{public}d, instanceId:%{public}d, state:%{public}d",
970 uid, pid, instanceId, state);
971 std::shared_ptr<Application> app = supervisor_->GetAppRecord(uid);
972 std::shared_ptr<ProcessRecord> procRecord = app ? app->GetProcessRecord(pid) : nullptr;
973 if (!app || !procRecord) {
974 return;
975 }
976 procRecord->avCodecState_[instanceId] = (state == ResType::AvCodecState::CODEC_START_INFO);
977 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()), resType, state);
978 }
979
HandleSceneBoardState(uint32_t resType,int64_t value,const nlohmann::json & payload)980 void CgroupEventHandler::HandleSceneBoardState(uint32_t resType, int64_t value, const nlohmann::json& payload)
981 {
982 int32_t sceneBoardPid = 0;
983 if (!supervisor_) {
984 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
985 return;
986 }
987
988 if (!ParseValue(sceneBoardPid, "pid", payload)) {
989 return;
990 }
991 if (sceneBoardPid <= 0) {
992 return;
993 }
994
995 supervisor_->sceneBoardPid_ = sceneBoardPid;
996 CGS_LOGI("%{public}s : set sceneboard pid: %{public}d", __func__, sceneBoardPid);
997 }
998
CheckVisibilityForRenderProcess(ProcessRecord & pr,ProcessRecord & mainProc)999 bool CgroupEventHandler::CheckVisibilityForRenderProcess(ProcessRecord &pr, ProcessRecord &mainProc)
1000 {
1001 return (pr.processType_ == ProcRecordType::RENDER) && pr.isActive_ &&
1002 !mainProc.GetWindowInfoNonNull(pr.linkedWindowId_)->isVisible_;
1003 }
1004
HandleWebviewScreenCapture(uint32_t resType,int64_t value,const nlohmann::json & payload)1005 void CgroupEventHandler::HandleWebviewScreenCapture(uint32_t resType, int64_t value, const nlohmann::json& payload)
1006 {
1007 int32_t uid = 0;
1008 int32_t pid = 0;
1009 std::shared_ptr<Application> app = nullptr;
1010 std::shared_ptr<ProcessRecord> procRecord = nullptr;
1011
1012 if (!GetProcInfoByPayload(uid, pid, app, procRecord, payload)) {
1013 return;
1014 }
1015
1016 procRecord->screenCaptureState_= (value == ResType::WebScreenCapture::WEB_SCREEN_CAPTURE_START);
1017 CGS_LOGI("%{public}s : screen capture process: %{public}s, uid: %{public}d, pid: %{public}d, state: %{public}d",
1018 __func__, app->GetName().c_str(), uid, pid, procRecord->screenCaptureState_);
1019
1020 CgroupAdjuster::GetInstance().AdjustProcessGroup(*(app.get()), *(procRecord.get()),
1021 AdjustSource::ADJS_REPORT_WEBVIEW_SCREEN_CAPTURE);
1022 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()), resType,
1023 procRecord->screenCaptureState_);
1024 }
1025
HandleReportWebviewVideoState(uint32_t resType,int64_t value,const nlohmann::json & payload)1026 void CgroupEventHandler::HandleReportWebviewVideoState(uint32_t resType, int64_t value, const nlohmann::json& payload)
1027 {
1028 int32_t uid = 0;
1029 int32_t pid = 0;
1030 std::shared_ptr<Application> app = nullptr;
1031 std::shared_ptr<ProcessRecord> procRecord = nullptr;
1032
1033 if (!GetProcInfoByPayload(uid, pid, app, procRecord, payload)) {
1034 return;
1035 }
1036
1037 procRecord->videoState_ = (value == ResType::WebVideoState::WEB_VIDEO_PLAYING_START);
1038 CGS_LOGI("%{public}s : video process name: %{public}s, uid: %{public}d, pid: %{public}d, state: %{public}d",
1039 __func__, app->GetName().c_str(), uid, pid, procRecord->videoState_);
1040
1041 ResSchedUtils::GetInstance().ReportSysEvent(*(app.get()), *(procRecord.get()), resType,
1042 procRecord->videoState_);
1043 }
1044
GetProcInfoByPayload(int32_t & uid,int32_t & pid,std::shared_ptr<Application> & app,std::shared_ptr<ProcessRecord> & procRecord,const nlohmann::json & payload)1045 bool CgroupEventHandler::GetProcInfoByPayload(int32_t &uid, int32_t &pid, std::shared_ptr<Application>& app,
1046 std::shared_ptr<ProcessRecord>& procRecord, const nlohmann::json& payload)
1047 {
1048 if (!supervisor_) {
1049 CGS_LOGE("%{public}s : supervisor nullptr!", __func__);
1050 return false;
1051 }
1052
1053 if (!ParsePayload(uid, pid, payload)) {
1054 CGS_LOGW("%{public}s : uid or pid invalid, uid: %{public}d, pid: %{public}d!",
1055 __func__, uid, pid);
1056 return false;
1057 }
1058 app = supervisor_->GetAppRecord(uid);
1059 if (app) {
1060 procRecord = app->GetProcessRecordNonNull(pid);
1061 }
1062 if (!app || !procRecord) {
1063 CGS_LOGW("%{public}s : app record or proc record is not exist, uid: %{public}d, pid: %{public}d!",
1064 __func__, uid, pid);
1065 return false;
1066 }
1067 return true;
1068 }
1069
ParsePayload(int32_t & uid,int32_t & pid,const nlohmann::json & payload)1070 bool CgroupEventHandler::ParsePayload(int32_t& uid, int32_t& pid, const nlohmann::json& payload)
1071 {
1072 if (!ParseValue(uid, "uid", payload) || !ParseValue(pid, "pid", payload)) {
1073 return false;
1074 }
1075 if (uid <= 0 || pid <= 0) {
1076 return false;
1077 }
1078 return true;
1079 }
1080
ParsePayload(int32_t & uid,int32_t & pid,int32_t & tid,int64_t value,const nlohmann::json & payload)1081 bool CgroupEventHandler::ParsePayload(int32_t& uid, int32_t& pid, int32_t& tid,
1082 int64_t value, const nlohmann::json& payload)
1083 {
1084 if (payload.contains("uid") && payload.at("uid").is_string()) {
1085 uid = atoi(payload["uid"].get<std::string>().c_str());
1086 }
1087
1088 if (payload.contains("pid") && payload.at("pid").is_string()) {
1089 pid = atoi(payload["pid"].get<std::string>().c_str());
1090 }
1091 tid = static_cast<int32_t>(value);
1092 return true;
1093 }
1094
ParseValue(int32_t & value,const char * name,const nlohmann::json & payload)1095 bool CgroupEventHandler::ParseValue(int32_t& value, const char* name,
1096 const nlohmann::json& payload)
1097 {
1098 if (payload.contains(name) && payload.at(name).is_string()) {
1099 value = atoi(payload[name].get<std::string>().c_str());
1100 return true;
1101 }
1102 return false;
1103 }
1104
PostTask(const std::function<void ()> task)1105 void CgroupEventHandler::PostTask(const std::function<void()> task)
1106 {
1107 if (!cgroupEventQueue_) {
1108 CGS_LOGE("%{public}s : cgroupEventQueue_ nullptr", __func__);
1109 return;
1110 }
1111 cgroupEventQueue_->submit([task, this] {
1112 task();
1113 });
1114 }
1115
PostTask(const std::function<void ()> task,const std::string & taskName,const int32_t delayTime)1116 void CgroupEventHandler::PostTask(const std::function<void()> task, const std::string &taskName,
1117 const int32_t delayTime)
1118 {
1119 std::lock_guard<ffrt::mutex> autoLock(delayTaskMapMutex_);
1120 if (!cgroupEventQueue_) {
1121 CGS_LOGE("%{public}s : cgroupEventQueue_ nullptr", __func__);
1122 return;
1123 }
1124 delayTaskMap_[taskName] = cgroupEventQueue_->submit_h([task, this] {
1125 task();
1126 }, ffrt::task_attr().delay(delayTime * ffrtSwitch_));
1127 }
1128
RemoveTask(const std::string & taskName)1129 void CgroupEventHandler::RemoveTask(const std::string &taskName)
1130 {
1131 std::lock_guard<ffrt::mutex> autoLock(delayTaskMapMutex_);
1132 for (auto iter = delayTaskMap_.begin(); iter != delayTaskMap_.end(); iter++) {
1133 if (iter->first == taskName && iter->second != nullptr) {
1134 cgroupEventQueue_->cancel(iter->second);
1135 delayTaskMap_.erase(iter);
1136 return;
1137 }
1138 }
1139 }
1140 } // namespace ResourceSchedule
1141 } // namespace OHOS
1142