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
16 #include <algorithm>
17
18 #include "ability_death_recipient.h"
19 #include "datetime_ex.h"
20 #include "ipc_skeleton.h"
21 #include "memory_guard.h"
22 #ifdef RESSCHED_ENABLE
23 #include "res_sched_client.h"
24 #endif
25 #include "sam_log.h"
26 #include "string_ex.h"
27 #include "system_ability_manager.h"
28 #include "schedule/system_ability_state_scheduler.h"
29
30 namespace OHOS {
31 namespace {
32 constexpr int64_t RESTART_TIME_INTERVAL_LIMIT = 20 * 1000;
33 constexpr int32_t RESTART_TIMES_LIMIT = 4;
34 constexpr int32_t MAX_SUBSCRIBE_COUNT = 256;
35 constexpr int32_t UNLOAD_TIMEOUT_TIME = 5 * 1000;
36 const std::string LOCAL_DEVICE = "local";
37 constexpr int32_t MAX_DELAY_TIME = 5 * 60 * 1000;
38 constexpr const char* CANCEL_UNLOAD = "cancelUnload";
39 const std::string KEY_EVENT_ID = "eventId";
40 const std::string KEY_NAME = "name";
41 const std::string KEY_VALUE = "value";
42 const std::string KEY_EXTRA_DATA_ID = "extraDataId";
43 const std::string KEY_UNLOAD_TIMEOUT = "unloadTimeout";
44 }
Init(const std::list<SaProfile> & saProfiles)45 void SystemAbilityStateScheduler::Init(const std::list<SaProfile>& saProfiles)
46 {
47 HILOGI("[SA Scheduler] init start");
48 InitStateContext(saProfiles);
49 processListenerDeath_ = sptr<IRemoteObject::DeathRecipient>(new SystemProcessListenerDeathRecipient());
50 auto unloadRunner = AppExecFwk::EventRunner::Create("UnloadHandler");
51 unloadEventHandler_ = std::make_shared<UnloadEventHandler>(unloadRunner, weak_from_this());
52 unloadEventHandler_->PostTask([]() { Samgr::MemoryGuard cacheGuard; });
53
54 auto listener = std::dynamic_pointer_cast<SystemAbilityStateListener>(shared_from_this());
55 stateMachine_ = std::make_shared<SystemAbilityStateMachine>(listener);
56 stateEventHandler_ = std::make_shared<SystemAbilityEventHandler>(stateMachine_);
57
58 auto processRunner = AppExecFwk::EventRunner::Create("ProcessHandler");
59 processHandler_ = std::make_shared<AppExecFwk::EventHandler>(processRunner);
60 processHandler_->PostTask([]() { Samgr::MemoryGuard cacheGuard; });
61 HILOGI("[SA Scheduler] init end");
62 }
63
InitStateContext(const std::list<SaProfile> & saProfiles)64 void SystemAbilityStateScheduler::InitStateContext(const std::list<SaProfile>& saProfiles)
65 {
66 for (auto& saProfile : saProfiles) {
67 if (saProfile.process.empty()) {
68 continue;
69 }
70 std::unique_lock<std::shared_mutex> processWriteLock(processMapLock_);
71 if (processContextMap_.count(saProfile.process) == 0) {
72 auto processContext = std::make_shared<SystemProcessContext>();
73 processContext->processName = saProfile.process;
74 processContext->abilityStateCountMap[SystemAbilityState::NOT_LOADED] = 0;
75 processContext->abilityStateCountMap[SystemAbilityState::LOADING] = 0;
76 processContext->abilityStateCountMap[SystemAbilityState::LOADED] = 0;
77 processContext->abilityStateCountMap[SystemAbilityState::UNLOADABLE] = 0;
78 processContext->abilityStateCountMap[SystemAbilityState::UNLOADING] = 0;
79 processContextMap_[saProfile.process] = processContext;
80 }
81 processContextMap_[saProfile.process]->saList.push_back(saProfile.saId);
82 processContextMap_[saProfile.process]->abilityStateCountMap[SystemAbilityState::NOT_LOADED]++;
83 auto abilityContext = std::make_shared<SystemAbilityContext>();
84 abilityContext->systemAbilityId = saProfile.saId;
85 abilityContext->isAutoRestart = saProfile.autoRestart;
86 int32_t delayUnloadTime = LimitDelayUnloadTime(saProfile.stopOnDemand.delayTime);
87 abilityContext->delayUnloadTime = delayUnloadTime;
88 abilityContext->ownProcessContext = processContextMap_[saProfile.process];
89 std::unique_lock<std::shared_mutex> abiltyWriteLock(abiltyMapLock_);
90 abilityContextMap_[saProfile.saId] = abilityContext;
91 }
92 }
93
LimitDelayUnloadTime(int32_t delayUnloadTime)94 int32_t SystemAbilityStateScheduler::LimitDelayUnloadTime(int32_t delayUnloadTime)
95 {
96 if (delayUnloadTime < 0) {
97 return 0;
98 }
99 if (delayUnloadTime > MAX_DELAY_TIME) {
100 return MAX_DELAY_TIME;
101 }
102 return delayUnloadTime;
103 }
104
GetSystemAbilityContext(int32_t systemAbilityId,std::shared_ptr<SystemAbilityContext> & abilityContext)105 bool SystemAbilityStateScheduler::GetSystemAbilityContext(int32_t systemAbilityId,
106 std::shared_ptr<SystemAbilityContext>& abilityContext)
107 {
108 std::shared_lock<std::shared_mutex> readLock(abiltyMapLock_);
109 if (abilityContextMap_.count(systemAbilityId) == 0) {
110 HILOGE("[SA Scheduler][SA: %{public}d] not in SA profiles", systemAbilityId);
111 return false;
112 }
113 abilityContext = abilityContextMap_[systemAbilityId];
114 if (abilityContext == nullptr) {
115 HILOGE("[SA Scheduler][SA: %{public}d] context is nullptr", systemAbilityId);
116 return false;
117 }
118 if (abilityContext->ownProcessContext == nullptr) {
119 HILOGE("[SA Scheduler][SA: %{public}d] not in any process", systemAbilityId);
120 return false;
121 }
122 return true;
123 }
124
GetSystemProcessContext(const std::u16string & processName,std::shared_ptr<SystemProcessContext> & processContext)125 bool SystemAbilityStateScheduler::GetSystemProcessContext(const std::u16string& processName,
126 std::shared_ptr<SystemProcessContext>& processContext)
127 {
128 std::shared_lock<std::shared_mutex> readLock(processMapLock_);
129 if (processContextMap_.count(processName) == 0) {
130 HILOGE("[SA Scheduler][processName: %{public}s] invalid", Str16ToStr8(processName).c_str());
131 return false;
132 }
133 processContext = processContextMap_[processName];
134 if (processContext == nullptr) {
135 HILOGE("[SA Scheduler][processName: %{public}s] context is nullptr", Str16ToStr8(processName).c_str());
136 return false;
137 }
138 return true;
139 }
140
IsSystemAbilityUnloading(int32_t systemAbilityId)141 bool SystemAbilityStateScheduler::IsSystemAbilityUnloading(int32_t systemAbilityId)
142 {
143 std::shared_ptr<SystemAbilityContext> abilityContext;
144 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
145 return false;
146 }
147 std::lock_guard<std::recursive_mutex> autoLock(abilityContext->ownProcessContext->processLock);
148 if (abilityContext->state ==SystemAbilityState::UNLOADING
149 || abilityContext->ownProcessContext->state == SystemProcessState::STOPPING) {
150 return true;
151 }
152 return false;
153 }
154
HandleLoadAbilityEvent(int32_t systemAbilityId,bool & isExist)155 int32_t SystemAbilityStateScheduler::HandleLoadAbilityEvent(int32_t systemAbilityId, bool& isExist)
156 {
157 HILOGI("[SA Scheduler][SA: %{public}d] handle load event by check start",
158 systemAbilityId);
159 std::shared_ptr<SystemAbilityContext> abilityContext;
160 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
161 isExist = false;
162 return ERR_INVALID_VALUE;
163 }
164 std::lock_guard<std::recursive_mutex> autoLock(abilityContext->ownProcessContext->processLock);
165 if (abilityContext->ownProcessContext->state == SystemProcessState::NOT_STARTED) {
166 isExist = false;
167 return ERR_INVALID_VALUE;
168 }
169 if (abilityContext->ownProcessContext->state == SystemProcessState::STARTED
170 && abilityContext->state ==SystemAbilityState::NOT_LOADED) {
171 bool result = SystemAbilityManager::GetInstance()->DoLoadOnDemandAbility(systemAbilityId, isExist);
172 if (result) {
173 return stateMachine_->AbilityStateTransitionLocked(abilityContext, SystemAbilityState::LOADING);
174 }
175 return ERR_INVALID_VALUE;
176 }
177 isExist = true;
178 return ERR_OK;
179 }
180
HandleLoadAbilityEvent(const LoadRequestInfo & loadRequestInfo)181 int32_t SystemAbilityStateScheduler::HandleLoadAbilityEvent(const LoadRequestInfo& loadRequestInfo)
182 {
183 HILOGI("[SA Scheduler][SA: %{public}d] handle load event start, callingpid: %{public}d",
184 loadRequestInfo.systemAbilityId, loadRequestInfo.callingPid);
185 std::shared_ptr<SystemAbilityContext> abilityContext;
186 if (!GetSystemAbilityContext(loadRequestInfo.systemAbilityId, abilityContext)) {
187 return ERR_INVALID_VALUE;
188 }
189 std::lock_guard<std::recursive_mutex> autoLock(abilityContext->ownProcessContext->processLock);
190 return HandleLoadAbilityEventLocked(abilityContext, loadRequestInfo);
191 }
192
HandleLoadAbilityEventLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext,const LoadRequestInfo & loadRequestInfo)193 int32_t SystemAbilityStateScheduler::HandleLoadAbilityEventLocked(
194 const std::shared_ptr<SystemAbilityContext>& abilityContext, const LoadRequestInfo& loadRequestInfo)
195 {
196 if (abilityContext->state ==SystemAbilityState::UNLOADING
197 || abilityContext->ownProcessContext->state == SystemProcessState::STOPPING) {
198 return PendLoadEventLocked(abilityContext, loadRequestInfo);
199 }
200 nlohmann::json activeReason;
201 activeReason[KEY_EVENT_ID] = loadRequestInfo.loadEvent.eventId;
202 activeReason[KEY_NAME] = loadRequestInfo.loadEvent.name;
203 activeReason[KEY_VALUE] = loadRequestInfo.loadEvent.value;
204 activeReason[KEY_EXTRA_DATA_ID] = loadRequestInfo.loadEvent.extraDataId;
205 int32_t result = ERR_INVALID_VALUE;
206 switch (abilityContext->state) {
207 case SystemAbilityState::LOADING:
208 result = RemovePendingUnloadEventLocked(abilityContext);
209 break;
210 case SystemAbilityState::LOADED:
211 result = RemoveDelayUnloadEventLocked(abilityContext->systemAbilityId);
212 break;
213 case SystemAbilityState::UNLOADABLE:
214 result = ActiveSystemAbilityLocked(abilityContext, activeReason);
215 break;
216 case SystemAbilityState::NOT_LOADED:
217 result = ERR_OK;
218 break;
219 default:
220 result = ERR_INVALID_VALUE;
221 HILOGI("[SA Scheduler][SA: %{public}d] in state %{public}d, cannot load ability",
222 loadRequestInfo.systemAbilityId, abilityContext->state);
223 break;
224 }
225 if (result == ERR_OK) {
226 return DoLoadSystemAbilityLocked(abilityContext, loadRequestInfo);
227 }
228 return result;
229 }
230
HandleUnloadAbilityEvent(const UnloadRequestInfo & unloadRequestInfo)231 int32_t SystemAbilityStateScheduler::HandleUnloadAbilityEvent(const UnloadRequestInfo& unloadRequestInfo)
232 {
233 HILOGI("[SA Scheduler][SA: %{public}d] handle unload event start", unloadRequestInfo.systemAbilityId);
234 std::shared_ptr<SystemAbilityContext> abilityContext;
235 if (!GetSystemAbilityContext(unloadRequestInfo.systemAbilityId, abilityContext)) {
236 return ERR_INVALID_VALUE;
237 }
238 std::lock_guard<std::recursive_mutex> autoLock(abilityContext->ownProcessContext->processLock);
239 return HandleUnloadAbilityEventLocked(abilityContext, unloadRequestInfo);
240 }
241
HandleUnloadAbilityEventLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext,const UnloadRequestInfo & unloadRequestInfo)242 int32_t SystemAbilityStateScheduler::HandleUnloadAbilityEventLocked(
243 const std::shared_ptr<SystemAbilityContext>& abilityContext, const UnloadRequestInfo& unloadRequestInfo)
244 {
245 abilityContext->unloadRequest = unloadRequestInfo;
246 int32_t result = ERR_INVALID_VALUE;
247 switch (abilityContext->state) {
248 case SystemAbilityState::LOADING:
249 result = PendUnloadEventLocked(abilityContext, unloadRequestInfo);
250 break;
251 case SystemAbilityState::LOADED:
252 if (unloadRequestInfo.unloadEvent.eventId == INTERFACE_CALL) {
253 result = ProcessDelayUnloadEvent(abilityContext->systemAbilityId);
254 } else {
255 result = SendDelayUnloadEventLocked(abilityContext->systemAbilityId, abilityContext->delayUnloadTime);
256 }
257 break;
258 default:
259 result = ERR_OK;
260 HILOGI("[SA Scheduler][SA: %{public}d] in state %{public}d, not need unload ability",
261 abilityContext->systemAbilityId, abilityContext->state);
262 break;
263 }
264 return result;
265 }
266
HandleCancelUnloadAbilityEvent(int32_t systemAbilityId)267 int32_t SystemAbilityStateScheduler::HandleCancelUnloadAbilityEvent(int32_t systemAbilityId)
268 {
269 HILOGI("[SA Scheduler][SA: %{public}d] cancel unload start", systemAbilityId);
270 std::shared_ptr<SystemAbilityContext> abilityContext;
271 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
272 return ERR_INVALID_VALUE;
273 }
274 nlohmann::json activeReason;
275 activeReason[KEY_EVENT_ID] = INTERFACE_CALL;
276 activeReason[KEY_NAME] = CANCEL_UNLOAD;
277 activeReason[KEY_VALUE] = "";
278 activeReason[KEY_EXTRA_DATA_ID] = -1;
279 int32_t result = ERR_INVALID_VALUE;
280 std::lock_guard<std::recursive_mutex> autoLock(abilityContext->ownProcessContext->processLock);
281 switch (abilityContext->state) {
282 case SystemAbilityState::UNLOADABLE:
283 result = ActiveSystemAbilityLocked(abilityContext, activeReason);
284 break;
285 default:
286 result = ERR_OK;
287 HILOGI("[SA Scheduler][SA: %{public}d] in state %{public}d, not need cancel unload",
288 systemAbilityId, abilityContext->state);
289 break;
290 }
291 return result;
292 }
293
ActiveSystemAbilityLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext,const nlohmann::json & activeReason)294 int32_t SystemAbilityStateScheduler::ActiveSystemAbilityLocked(
295 const std::shared_ptr<SystemAbilityContext>& abilityContext,
296 const nlohmann::json& activeReason)
297 {
298 bool result = SystemAbilityManager::GetInstance()->ActiveSystemAbility(abilityContext->systemAbilityId,
299 abilityContext->ownProcessContext->processName, activeReason);
300 if (!result) {
301 HILOGE("[SA Scheduler][SA: %{public}d] active ability failed", abilityContext->systemAbilityId);
302 return ERR_INVALID_VALUE;
303 }
304 return stateMachine_->AbilityStateTransitionLocked(abilityContext, SystemAbilityState::LOADED);
305 }
306
SendAbilityStateEvent(int32_t systemAbilityId,AbilityStateEvent event)307 int32_t SystemAbilityStateScheduler::SendAbilityStateEvent(int32_t systemAbilityId, AbilityStateEvent event)
308 {
309 HILOGD("[SA Scheduler][SA: %{public}d] receive state event", systemAbilityId);
310 std::shared_ptr<SystemAbilityContext> abilityContext;
311 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
312 return ERR_INVALID_VALUE;
313 }
314 std::lock_guard<std::recursive_mutex> autoLock(abilityContext->ownProcessContext->processLock);
315 return stateEventHandler_->HandleAbilityEventLocked(abilityContext, event);
316 }
317
SendProcessStateEvent(const ProcessInfo & processInfo,ProcessStateEvent event)318 int32_t SystemAbilityStateScheduler::SendProcessStateEvent(const ProcessInfo& processInfo, ProcessStateEvent event)
319 {
320 HILOGD("[SA Scheduler][process: %{public}s] receive state event",
321 Str16ToStr8(processInfo.processName).c_str());
322 std::shared_ptr<SystemProcessContext> processContext;
323 if (!GetSystemProcessContext(processInfo.processName, processContext)) {
324 return ERR_INVALID_VALUE;
325 }
326 std::lock_guard<std::recursive_mutex> autoLock(processContext->processLock);
327 return stateEventHandler_->HandleProcessEventLocked(processContext, processInfo, event);
328 }
329
SendDelayUnloadEventLocked(uint32_t systemAbilityId,int32_t delayTime)330 int32_t SystemAbilityStateScheduler::SendDelayUnloadEventLocked(uint32_t systemAbilityId, int32_t delayTime)
331 {
332 if (unloadEventHandler_ == nullptr) {
333 HILOGE("[SA Scheduler] unload handler not initialized!");
334 return ERR_INVALID_VALUE;
335 }
336 if (unloadEventHandler_->HasInnerEvent(systemAbilityId)) {
337 return ERR_OK;
338 }
339 HILOGI("[SA Scheduler][SA: %{public}d] send delay unload event", systemAbilityId);
340 bool ret = unloadEventHandler_->SendEvent(systemAbilityId, 0, delayTime);
341 if (!ret) {
342 HILOGE("[SA Scheduler] send event failed!");
343 return ERR_INVALID_VALUE;
344 }
345 return ERR_OK;
346 }
347
RemoveDelayUnloadEventLocked(uint32_t systemAbilityId)348 int32_t SystemAbilityStateScheduler::RemoveDelayUnloadEventLocked(uint32_t systemAbilityId)
349 {
350 if (unloadEventHandler_ == nullptr) {
351 HILOGE("[SA Scheduler] unload handler not initialized!");
352 return ERR_INVALID_VALUE;
353 }
354 if (!unloadEventHandler_->HasInnerEvent(systemAbilityId)) {
355 return ERR_OK;
356 }
357 HILOGI("[SA Scheduler][SA: %{public}d] remove delay unload event", systemAbilityId);
358 unloadEventHandler_->RemoveEvent(systemAbilityId);
359 return ERR_OK;
360 }
361
PendLoadEventLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext,const LoadRequestInfo & loadRequestInfo)362 int32_t SystemAbilityStateScheduler::PendLoadEventLocked(const std::shared_ptr<SystemAbilityContext>& abilityContext,
363 const LoadRequestInfo& loadRequestInfo)
364 {
365 HILOGI("[SA Scheduler][SA: %{public}d] save load event", abilityContext->systemAbilityId);
366 if (loadRequestInfo.callback == nullptr) {
367 HILOGW("[SA Scheduler] callback invalid!");
368 return ERR_INVALID_VALUE;
369 }
370 bool isExist = std::any_of(abilityContext->pendingLoadEventList.begin(),
371 abilityContext->pendingLoadEventList.end(), [&loadRequestInfo](const auto& loadEventItem) {
372 return loadRequestInfo.callback->AsObject() == loadEventItem.callback->AsObject();
373 });
374 if (isExist) {
375 HILOGI("[SA Scheduler][SA: %{public}d] already existed callback object", abilityContext->systemAbilityId);
376 return ERR_OK;
377 }
378 auto& count = abilityContext->pendingLoadEventCountMap[loadRequestInfo.callingPid];
379 if (count >= MAX_SUBSCRIBE_COUNT) {
380 HILOGE("[SA Scheduler][SA: %{public}d] pid:%{public}d overflow max callback count!",
381 abilityContext->systemAbilityId, loadRequestInfo.callingPid);
382 return ERR_PERMISSION_DENIED;
383 }
384 ++count;
385 abilityContext->pendingLoadEventList.emplace_back(loadRequestInfo);
386 abilityContext->pendingEvent = PendingEvent::LOAD_ABILITY_EVENT;
387 return ERR_OK;
388 }
389
PendUnloadEventLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext,const UnloadRequestInfo & unloadRequestInfo)390 int32_t SystemAbilityStateScheduler::PendUnloadEventLocked(
391 const std::shared_ptr<SystemAbilityContext>& abilityContext, const UnloadRequestInfo& unloadRequestInfo)
392 {
393 HILOGI("[SA Scheduler][SA: %{public}d] save unload event", abilityContext->systemAbilityId);
394 abilityContext->pendingEvent = PendingEvent::UNLOAD_ABILITY_EVENT;
395 abilityContext->pendingUnloadEvent = unloadRequestInfo;
396 return ERR_OK;
397 }
398
RemovePendingUnloadEventLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext)399 int32_t SystemAbilityStateScheduler::RemovePendingUnloadEventLocked(
400 const std::shared_ptr<SystemAbilityContext>& abilityContext)
401 {
402 if (abilityContext->pendingEvent == PendingEvent::UNLOAD_ABILITY_EVENT) {
403 HILOGI("[SA Scheduler][SA: %{public}d] remove pending unload event", abilityContext->systemAbilityId);
404 abilityContext->pendingEvent = PendingEvent::NO_EVENT;
405 }
406 return ERR_OK;
407 }
408
HandlePendingLoadEventLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext)409 int32_t SystemAbilityStateScheduler::HandlePendingLoadEventLocked(
410 const std::shared_ptr<SystemAbilityContext>& abilityContext)
411 {
412 if (abilityContext->pendingEvent != PendingEvent::LOAD_ABILITY_EVENT) {
413 HILOGD("[SA Scheduler][SA: %{public}d] no pending load event", abilityContext->systemAbilityId);
414 return ERR_OK;
415 }
416 HILOGI("[SA Scheduler][SA: %{public}d] handle pending load event start", abilityContext->systemAbilityId);
417 abilityContext->pendingEvent = PendingEvent::NO_EVENT;
418 for (auto& loadRequestInfo : abilityContext->pendingLoadEventList) {
419 int32_t result = HandleLoadAbilityEventLocked(abilityContext, loadRequestInfo);
420 if (result != ERR_OK) {
421 HILOGE("[SA Scheduler][SA: %{public}d] handle pending load event failed, callingPid: %{public}d",
422 abilityContext->systemAbilityId, loadRequestInfo.callingPid);
423 }
424 }
425 abilityContext->pendingLoadEventList.clear();
426 abilityContext->pendingLoadEventCountMap.clear();
427 return ERR_OK;
428 }
429
HandlePendingUnloadEventLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext)430 int32_t SystemAbilityStateScheduler::HandlePendingUnloadEventLocked(
431 const std::shared_ptr<SystemAbilityContext>& abilityContext)
432 {
433 if (abilityContext->pendingEvent != PendingEvent::UNLOAD_ABILITY_EVENT) {
434 HILOGD("[SA Scheduler][SA: %{public}d] no pending unload event", abilityContext->systemAbilityId);
435 return ERR_OK;
436 }
437 HILOGI("[SA Scheduler][SA: %{public}d] handle pending unload event start", abilityContext->systemAbilityId);
438 abilityContext->pendingEvent = PendingEvent::NO_EVENT;
439 return HandleUnloadAbilityEventLocked(abilityContext, abilityContext->pendingUnloadEvent);
440 }
441
DoLoadSystemAbilityLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext,const LoadRequestInfo & loadRequestInfo)442 int32_t SystemAbilityStateScheduler::DoLoadSystemAbilityLocked(
443 const std::shared_ptr<SystemAbilityContext>& abilityContext, const LoadRequestInfo& loadRequestInfo)
444 {
445 int32_t result = ERR_OK;
446 if (loadRequestInfo.deviceId == LOCAL_DEVICE) {
447 HILOGD("[SA Scheduler][SA: %{public}d] load ability from local start", abilityContext->systemAbilityId);
448 result = SystemAbilityManager::GetInstance()->DoLoadSystemAbility(abilityContext->systemAbilityId,
449 abilityContext->ownProcessContext->processName, loadRequestInfo.callback, loadRequestInfo.callingPid,
450 loadRequestInfo.loadEvent);
451 } else {
452 HILOGD("[SA Scheduler][SA: %{public}d] load ability from remote start", abilityContext->systemAbilityId);
453 result = SystemAbilityManager::GetInstance()->DoLoadSystemAbilityFromRpc(loadRequestInfo.deviceId,
454 abilityContext->systemAbilityId, abilityContext->ownProcessContext->processName, loadRequestInfo.callback,
455 loadRequestInfo.loadEvent);
456 }
457 if (result == ERR_OK && abilityContext->state == SystemAbilityState::NOT_LOADED) {
458 return stateMachine_->AbilityStateTransitionLocked(abilityContext, SystemAbilityState::LOADING);
459 }
460 return result;
461 }
462
TryUnloadAllSystemAbility(const std::shared_ptr<SystemProcessContext> & processContext)463 int32_t SystemAbilityStateScheduler::TryUnloadAllSystemAbility(
464 const std::shared_ptr<SystemProcessContext>& processContext)
465 {
466 if (processContext == nullptr) {
467 HILOGE("[SA Scheduler] process context is nullptr");
468 return ERR_INVALID_VALUE;
469 }
470 std::lock_guard<std::recursive_mutex> autoLock(processContext->processLock);
471 if (CanUnloadAllSystemAbility(processContext)) {
472 return UnloadAllSystemAbilityLocked(processContext);
473 }
474 return ERR_OK;
475 }
476
CanUnloadAllSystemAbility(const std::shared_ptr<SystemProcessContext> & processContext)477 bool SystemAbilityStateScheduler::CanUnloadAllSystemAbility(
478 const std::shared_ptr<SystemProcessContext>& processContext)
479 {
480 std::shared_lock<std::shared_mutex> sharedLock(processContext->stateCountLock);
481 uint32_t notLoadAbilityCount = processContext->abilityStateCountMap[SystemAbilityState::NOT_LOADED];
482 uint32_t unloadableAbilityCount = processContext->abilityStateCountMap[SystemAbilityState::UNLOADABLE];
483 HILOGI("[SA Scheduler][process: %{public}s] SA num: %{public}zu, notloaded: %{public}d, unloadable: %{public}d",
484 Str16ToStr8(processContext->processName).c_str(), processContext->saList.size(), notLoadAbilityCount,
485 unloadableAbilityCount);
486 if (unloadableAbilityCount == 0) {
487 return false;
488 }
489 if (notLoadAbilityCount + unloadableAbilityCount == processContext->saList.size()) {
490 return true;
491 }
492 return false;
493 }
494
PostTryUnloadAllAbilityTask(const std::shared_ptr<SystemProcessContext> & processContext)495 int32_t SystemAbilityStateScheduler::PostTryUnloadAllAbilityTask(
496 const std::shared_ptr<SystemProcessContext>& processContext)
497 {
498 bool result = processHandler_->PostTask([this, processContext] () {
499 int32_t ret = TryUnloadAllSystemAbility(processContext);
500 if (ret != ERR_OK) {
501 HILOGE("[SA Scheduler][process: %{public}s] unload all SA failed",
502 Str16ToStr8(processContext->processName).c_str());
503 }
504 });
505 if (!result) {
506 HILOGW("[SA Scheduler][process: %{public}s] post task failed",
507 Str16ToStr8(processContext->processName).c_str());
508 return ERR_INVALID_VALUE;
509 }
510 return ERR_OK;
511 }
512
PostUnloadTimeoutTask(const std::shared_ptr<SystemProcessContext> & processContext)513 int32_t SystemAbilityStateScheduler::PostUnloadTimeoutTask(const std::shared_ptr<SystemProcessContext>& processContext)
514 {
515 auto timeoutTask = [this, processContext] () {
516 std::lock_guard<std::recursive_mutex> autoLock(processContext->processLock);
517 if (processContext->state == SystemProcessState::STOPPING) {
518 HILOGW("[SA Scheduler][process: %{public}s] unload SA timeout",
519 Str16ToStr8(processContext->processName).c_str());
520 int32_t result = KillSystemProcessLocked(processContext);
521 HILOGI("[SA Scheduler][process: %{public}s] kill timeout process ret: %{public}d",
522 Str16ToStr8(processContext->processName).c_str(), result);
523 }
524 };
525 bool ret = processHandler_->PostTask(timeoutTask, KEY_UNLOAD_TIMEOUT + Str16ToStr8(processContext->processName),
526 UNLOAD_TIMEOUT_TIME);
527 if (!ret) {
528 HILOGW("[SA Scheduler][process: %{public}s] post timeout task failed",
529 Str16ToStr8(processContext->processName).c_str());
530 return ERR_INVALID_VALUE;
531 }
532 return ERR_OK;
533 }
534
RemoveUnloadTimeoutTask(const std::shared_ptr<SystemProcessContext> & processContext)535 void SystemAbilityStateScheduler::RemoveUnloadTimeoutTask(const std::shared_ptr<SystemProcessContext>& processContext)
536 {
537 processHandler_->RemoveTask(KEY_UNLOAD_TIMEOUT + Str16ToStr8(processContext->processName));
538 }
539
PostTryKillProcessTask(const std::shared_ptr<SystemProcessContext> & processContext)540 int32_t SystemAbilityStateScheduler::PostTryKillProcessTask(
541 const std::shared_ptr<SystemProcessContext>& processContext)
542 {
543 bool result = processHandler_->PostTask([this, processContext] () {
544 int32_t ret = TryKillSystemProcess(processContext);
545 if (ret != ERR_OK) {
546 HILOGE("[SA Scheduler][process: %{public}s] kill process failed",
547 Str16ToStr8(processContext->processName).c_str());
548 }
549 });
550 if (!result) {
551 HILOGW("[SA Scheduler][process: %{public}s] post task failed",
552 Str16ToStr8(processContext->processName).c_str());
553 return ERR_INVALID_VALUE;
554 }
555 return ERR_OK;
556 }
557
UnloadAllSystemAbilityLocked(const std::shared_ptr<SystemProcessContext> & processContext)558 int32_t SystemAbilityStateScheduler::UnloadAllSystemAbilityLocked(
559 const std::shared_ptr<SystemProcessContext>& processContext)
560 {
561 HILOGI("[SA Scheduler][process: %{public}s] unload all SA", Str16ToStr8(processContext->processName).c_str());
562 for (auto& saId : processContext->saList) {
563 std::shared_ptr<SystemAbilityContext> abilityContext;
564 if (!GetSystemAbilityContext(saId, abilityContext)) {
565 continue;
566 }
567 int32_t result = ERR_OK;
568 if (abilityContext->state == SystemAbilityState::UNLOADABLE) {
569 result = DoUnloadSystemAbilityLocked(abilityContext);
570 }
571 if (result != ERR_OK) {
572 HILOGE("[SA Scheduler][SA: %{public}d] unload failed", saId);
573 }
574 }
575 PostUnloadTimeoutTask(processContext);
576 return stateMachine_->ProcessStateTransitionLocked(processContext, SystemProcessState::STOPPING);
577 }
578
DoUnloadSystemAbilityLocked(const std::shared_ptr<SystemAbilityContext> & abilityContext)579 int32_t SystemAbilityStateScheduler::DoUnloadSystemAbilityLocked(
580 const std::shared_ptr<SystemAbilityContext>& abilityContext)
581 {
582 int32_t result = ERR_OK;
583 HILOGI("[SA Scheduler][SA: %{public}d] unload ability start", abilityContext->systemAbilityId);
584 result = SystemAbilityManager::GetInstance()->DoUnloadSystemAbility(abilityContext->systemAbilityId,
585 abilityContext->ownProcessContext->processName, abilityContext->unloadRequest.unloadEvent);
586 if (result == ERR_OK) {
587 return stateMachine_->AbilityStateTransitionLocked(abilityContext, SystemAbilityState::UNLOADING);
588 }
589 return result;
590 }
591
TryKillSystemProcess(const std::shared_ptr<SystemProcessContext> & processContext)592 int32_t SystemAbilityStateScheduler::TryKillSystemProcess(
593 const std::shared_ptr<SystemProcessContext>& processContext)
594 {
595 if (processContext == nullptr) {
596 HILOGE("[SA Scheduler] process context is nullptr");
597 return ERR_INVALID_VALUE;
598 }
599 std::lock_guard<std::recursive_mutex> autoLock(processContext->processLock);
600 if (CanKillSystemProcess(processContext)) {
601 return KillSystemProcessLocked(processContext);
602 }
603 return ERR_OK;
604 }
605
CanKillSystemProcess(const std::shared_ptr<SystemProcessContext> & processContext)606 bool SystemAbilityStateScheduler::CanKillSystemProcess(
607 const std::shared_ptr<SystemProcessContext>& processContext)
608 {
609 std::shared_lock<std::shared_mutex> sharedLock(processContext->stateCountLock);
610 uint32_t notLoadAbilityCount = processContext->abilityStateCountMap[SystemAbilityState::NOT_LOADED];
611 HILOGI("[SA Scheduler][process: %{public}s] SA num: %{public}zu, not loaded num: %{public}d",
612 Str16ToStr8(processContext->processName).c_str(), processContext->saList.size(), notLoadAbilityCount);
613 if (notLoadAbilityCount == processContext->saList.size()) {
614 return true;
615 }
616 return false;
617 }
618
KillSystemProcessLocked(const std::shared_ptr<SystemProcessContext> & processContext)619 int32_t SystemAbilityStateScheduler::KillSystemProcessLocked(
620 const std::shared_ptr<SystemProcessContext>& processContext)
621 {
622 int32_t result = ERR_OK;
623 #ifdef RESSCHED_ENABLE
624 std::unordered_map<std::string, std::string> payload;
625 payload["pid"] = std::to_string(processContext->pid);
626 payload["uid"] = std::to_string(processContext->uid);
627 payload["processName"] = Str16ToStr8(processContext->processName);
628 result = ResourceSchedule::ResSchedClient::GetInstance().KillProcess(payload);
629 HILOGI("[SA Scheduler][process: %{public}s] kill process, pid: %{public}d, uid: %{public}d, result: %{public}d",
630 Str16ToStr8(processContext->processName).c_str(), processContext->pid, processContext->uid, result);
631 #endif
632 return result;
633 }
634
CanRestartProcessLocked(const std::shared_ptr<SystemProcessContext> & processContext)635 bool SystemAbilityStateScheduler::CanRestartProcessLocked(const std::shared_ptr<SystemProcessContext>& processContext)
636 {
637 if (!processContext->enableRestart) {
638 return false;
639 }
640 int64_t curtime = GetTickCount();
641 if (processContext->restartCountsCtrl.size() < RESTART_TIMES_LIMIT) {
642 processContext->restartCountsCtrl.push_back(curtime);
643 return true;
644 } else if (processContext->restartCountsCtrl.size() == RESTART_TIMES_LIMIT) {
645 if (curtime - processContext->restartCountsCtrl.front() < RESTART_TIME_INTERVAL_LIMIT) {
646 processContext->enableRestart = false;
647 return false;
648 }
649 processContext->restartCountsCtrl.push_back(curtime);
650 processContext->restartCountsCtrl.pop_front();
651 return true;
652 } else {
653 HILOGE("[SA Scheduler][process: %{public}s] unkown error",
654 Str16ToStr8(processContext->processName).c_str());
655 }
656 return false;
657 }
658
GetAbnormallyDiedAbilityLocked(std::shared_ptr<SystemProcessContext> & processContext,std::list<std::shared_ptr<SystemAbilityContext>> & abnormallyDiedAbilityList)659 int32_t SystemAbilityStateScheduler::GetAbnormallyDiedAbilityLocked(
660 std::shared_ptr<SystemProcessContext>& processContext,
661 std::list<std::shared_ptr<SystemAbilityContext>>& abnormallyDiedAbilityList)
662 {
663 for (auto& saId : processContext->saList) {
664 std::shared_ptr<SystemAbilityContext> abilityContext;
665 if (!GetSystemAbilityContext(saId, abilityContext)) {
666 continue;
667 }
668 if (abilityContext->state == SystemAbilityState::LOADED
669 || abilityContext->state == SystemAbilityState::LOADING) {
670 HILOGI("[SA Scheduler][SA: %{public}d] abnormally died", abilityContext->systemAbilityId);
671 if (abilityContext->isAutoRestart) {
672 HILOGI("[SA Scheduler][SA: %{public}d] is auto restart", abilityContext->systemAbilityId);
673 abnormallyDiedAbilityList.emplace_back(abilityContext);
674 }
675 }
676 }
677 return ERR_OK;
678 }
679
680
HandleAbnormallyDiedAbilityLocked(std::shared_ptr<SystemProcessContext> & processContext,std::list<std::shared_ptr<SystemAbilityContext>> & abnormallyDiedAbilityList)681 int32_t SystemAbilityStateScheduler::HandleAbnormallyDiedAbilityLocked(
682 std::shared_ptr<SystemProcessContext>& processContext,
683 std::list<std::shared_ptr<SystemAbilityContext>>& abnormallyDiedAbilityList)
684 {
685 if (abnormallyDiedAbilityList.empty()) {
686 return ERR_OK;
687 }
688 if (!CanRestartProcessLocked(processContext)) {
689 HILOGW("[SA Scheduler][process: %{public}s] can't restart: More than 4 restarts in 20 seconds",
690 Str16ToStr8(processContext->processName).c_str());
691 return ERR_OK;
692 }
693 OnDemandEvent onDemandEvent = {INTERFACE_CALL, "restart"};
694 sptr<ISystemAbilityLoadCallback> callback(new SystemAbilityLoadCallbackStub());
695 for (auto& abilityContext : abnormallyDiedAbilityList) {
696 LoadRequestInfo loadRequestInfo = {abilityContext->systemAbilityId,
697 LOCAL_DEVICE, callback, -1, onDemandEvent};
698 HandleLoadAbilityEventLocked(abilityContext, loadRequestInfo);
699 }
700 return ERR_OK;
701 }
702
NotifyProcessStarted(const std::shared_ptr<SystemProcessContext> & processContext)703 void SystemAbilityStateScheduler::NotifyProcessStarted(const std::shared_ptr<SystemProcessContext>& processContext)
704 {
705 std::shared_lock<std::shared_mutex> readLock(listenerSetLock_);
706 for (auto& listener : processListeners_) {
707 if (listener->AsObject() != nullptr) {
708 SystemProcessInfo systemProcessInfo = {Str16ToStr8(processContext->processName), processContext->pid,
709 processContext->uid};
710 listener->OnSystemProcessStarted(systemProcessInfo);
711 }
712 }
713 }
714
NotifyProcessStopped(const std::shared_ptr<SystemProcessContext> & processContext)715 void SystemAbilityStateScheduler::NotifyProcessStopped(const std::shared_ptr<SystemProcessContext>& processContext)
716 {
717 std::shared_lock<std::shared_mutex> readLock(listenerSetLock_);
718 for (auto& listener : processListeners_) {
719 if (listener->AsObject() != nullptr) {
720 SystemProcessInfo systemProcessInfo = {Str16ToStr8(processContext->processName), processContext->pid,
721 processContext->uid};
722 listener->OnSystemProcessStopped(systemProcessInfo);
723 }
724 }
725 }
726
OnProcessStartedLocked(const std::u16string & processName)727 void SystemAbilityStateScheduler::OnProcessStartedLocked(const std::u16string& processName)
728 {
729 HILOGI("[SA Scheduler][process: %{public}s] started", Str16ToStr8(processName).c_str());
730 std::shared_ptr<SystemProcessContext> processContext;
731 if (!GetSystemProcessContext(processName, processContext)) {
732 return;
733 }
734 NotifyProcessStarted(processContext);
735 }
736
OnProcessNotStartedLocked(const std::u16string & processName)737 void SystemAbilityStateScheduler::OnProcessNotStartedLocked(const std::u16string& processName)
738 {
739 HILOGI("[SA Scheduler][process: %{public}s] stopped", Str16ToStr8(processName).c_str());
740 std::shared_ptr<SystemProcessContext> processContext;
741 if (!GetSystemProcessContext(processName, processContext)) {
742 return;
743 }
744 NotifyProcessStopped(processContext);
745 RemoveUnloadTimeoutTask(processContext);
746
747 std::list<std::shared_ptr<SystemAbilityContext>> abnormallyDiedAbilityList;
748 GetAbnormallyDiedAbilityLocked(processContext, abnormallyDiedAbilityList);
749 for (auto& saId : processContext->saList) {
750 std::shared_ptr<SystemAbilityContext> abilityContext;
751 if (!GetSystemAbilityContext(saId, abilityContext)) {
752 continue;
753 }
754 int32_t result = stateMachine_->AbilityStateTransitionLocked(abilityContext, SystemAbilityState::NOT_LOADED);
755 if (result != ERR_OK) {
756 continue;
757 }
758 HandlePendingLoadEventLocked(abilityContext);
759 }
760 HandleAbnormallyDiedAbilityLocked(processContext, abnormallyDiedAbilityList);
761 }
762
HandleAbilityDiedEvent(int32_t systemAbilityId)763 int32_t SystemAbilityStateScheduler::HandleAbilityDiedEvent(int32_t systemAbilityId)
764 {
765 HILOGD("[SA Scheduler][SA: %{public}d] handle ability died event", systemAbilityId);
766 return ERR_OK;
767 }
768
OnAbilityNotLoadedLocked(int32_t systemAbilityId)769 void SystemAbilityStateScheduler::OnAbilityNotLoadedLocked(int32_t systemAbilityId)
770 {
771 HILOGI("[SA Scheduler][SA: %{public}d] not loaded", systemAbilityId);
772 std::shared_ptr<SystemAbilityContext> abilityContext;
773 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
774 return;
775 }
776 RemoveDelayUnloadEventLocked(abilityContext->systemAbilityId);
777 RemovePendingUnloadEventLocked(abilityContext);
778 if (abilityContext->ownProcessContext->state == SystemProcessState::STOPPING) {
779 PostTryKillProcessTask(abilityContext->ownProcessContext);
780 } else if (abilityContext->ownProcessContext->state == SystemProcessState::STARTED) {
781 PostTryUnloadAllAbilityTask(abilityContext->ownProcessContext);
782 }
783 }
784
OnAbilityLoadedLocked(int32_t systemAbilityId)785 void SystemAbilityStateScheduler::OnAbilityLoadedLocked(int32_t systemAbilityId)
786 {
787 HILOGI("[SA Scheduler][SA: %{public}d] loaded", systemAbilityId);
788 std::shared_ptr<SystemAbilityContext> abilityContext;
789 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
790 return;
791 }
792 HandlePendingUnloadEventLocked(abilityContext);
793 }
794
OnAbilityUnloadableLocked(int32_t systemAbilityId)795 void SystemAbilityStateScheduler::OnAbilityUnloadableLocked(int32_t systemAbilityId)
796 {
797 HILOGI("[SA Scheduler][SA: %{public}d] unloadable", systemAbilityId);
798 std::shared_ptr<SystemAbilityContext> abilityContext;
799 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
800 return;
801 }
802 PostTryUnloadAllAbilityTask(abilityContext->ownProcessContext);
803 }
804
GetRunningSystemProcess(std::list<SystemProcessInfo> & systemProcessInfos)805 int32_t SystemAbilityStateScheduler::GetRunningSystemProcess(std::list<SystemProcessInfo>& systemProcessInfos)
806 {
807 HILOGI("[SA Scheduler] get running process");
808 std::shared_lock<std::shared_mutex> readLock(processMapLock_);
809 for (auto it : processContextMap_) {
810 auto& processContext = it.second;
811 if (processContext == nullptr) {
812 continue;
813 }
814 std::lock_guard<std::recursive_mutex> autoLock(processContext->processLock);
815 if (processContext->state == SystemProcessState::STARTED) {
816 SystemProcessInfo systemProcessInfo = {Str16ToStr8(processContext->processName), processContext->pid,
817 processContext->uid};
818 systemProcessInfos.emplace_back(systemProcessInfo);
819 }
820 }
821 return ERR_OK;
822 }
823
SubscribeSystemProcess(const sptr<ISystemProcessStatusChange> & listener)824 int32_t SystemAbilityStateScheduler::SubscribeSystemProcess(const sptr<ISystemProcessStatusChange>& listener)
825 {
826 std::unique_lock<std::shared_mutex> writeLock(listenerSetLock_);
827 auto iter = std::find_if(processListeners_.begin(), processListeners_.end(),
828 [listener](sptr<ISystemProcessStatusChange>& item) {
829 return item->AsObject() == listener->AsObject();
830 });
831 if (iter == processListeners_.end()) {
832 if (processListenerDeath_ != nullptr) {
833 bool ret = listener->AsObject()->AddDeathRecipient(processListenerDeath_);
834 HILOGI("SubscribeSystemProcess AddDeathRecipient %{public}s", ret ? "succeed" : "failed");
835 }
836 processListeners_.emplace_back(listener);
837 } else {
838 HILOGI("SubscribeSystemProcess listener already exists");
839 }
840 return ERR_OK;
841 }
842
UnSubscribeSystemProcess(const sptr<ISystemProcessStatusChange> & listener)843 int32_t SystemAbilityStateScheduler::UnSubscribeSystemProcess(const sptr<ISystemProcessStatusChange>& listener)
844 {
845 std::unique_lock<std::shared_mutex> writeLock(listenerSetLock_);
846 auto iter = std::find_if(processListeners_.begin(), processListeners_.end(),
847 [listener](sptr<ISystemProcessStatusChange>& item) {
848 return item->AsObject() == listener->AsObject();
849 });
850 if (iter != processListeners_.end()) {
851 if (processListenerDeath_ != nullptr) {
852 listener->AsObject()->RemoveDeathRecipient(processListenerDeath_);
853 }
854 processListeners_.erase(iter);
855 HILOGI("UnSubscribeSystemProcess listener remove success");
856 } else {
857 HILOGI("UnSubscribeSystemProcess listener not exists");
858 }
859 return ERR_OK;
860 }
861
ProcessDelayUnloadEvent(int32_t systemAbilityId)862 int32_t SystemAbilityStateScheduler::ProcessDelayUnloadEvent(int32_t systemAbilityId)
863 {
864 std::shared_ptr<SystemAbilityContext> abilityContext;
865 if (!GetSystemAbilityContext(systemAbilityId, abilityContext)) {
866 return ERR_INVALID_VALUE;
867 }
868 std::lock_guard<std::recursive_mutex> autoLock(abilityContext->ownProcessContext->processLock);
869 if (abilityContext->state != SystemAbilityState::LOADED) {
870 HILOGW("[SA Scheduler][SA: %{public}d] cannot process delay unload event", systemAbilityId);
871 return ERR_OK;
872 }
873 HILOGI("[SA Scheduler][SA: %{public}d] process delay unload event", systemAbilityId);
874 int32_t delayTime = 0;
875 nlohmann::json idleReason;
876 idleReason[KEY_EVENT_ID] = abilityContext->unloadRequest.unloadEvent.eventId;
877 idleReason[KEY_NAME] = abilityContext->unloadRequest.unloadEvent.name;
878 idleReason[KEY_VALUE] = abilityContext->unloadRequest.unloadEvent.value;
879 idleReason[KEY_EXTRA_DATA_ID] = abilityContext->unloadRequest.unloadEvent.extraDataId;
880 bool result = SystemAbilityManager::GetInstance()->IdleSystemAbility(abilityContext->systemAbilityId,
881 abilityContext->ownProcessContext->processName, idleReason, delayTime);
882 if (!result) {
883 HILOGE("[SA Scheduler][SA: %{public}d] idle system ability failed", systemAbilityId);
884 return ERR_INVALID_VALUE;
885 }
886 if (delayTime < 0) {
887 HILOGI("[SA Scheduler][SA: %{public}d] reject unload", systemAbilityId);
888 return ERR_OK;
889 } else if (delayTime == 0) {
890 HILOGI("[SA Scheduler][SA: %{public}d] agree unload", systemAbilityId);
891 return stateMachine_->AbilityStateTransitionLocked(abilityContext, SystemAbilityState::UNLOADABLE);
892 } else {
893 HILOGI("[SA Scheduler][SA: %{public}d] choose delay unload", systemAbilityId);
894 return SendDelayUnloadEventLocked(abilityContext->systemAbilityId, fmin(delayTime, MAX_DELAY_TIME));
895 }
896 }
897
ProcessEvent(const OHOS::AppExecFwk::InnerEvent::Pointer & event)898 void SystemAbilityStateScheduler::UnloadEventHandler::ProcessEvent(const OHOS::AppExecFwk::InnerEvent::Pointer& event)
899 {
900 if (event == nullptr) {
901 HILOGE("[SA Scheduler] ProcessEvent event is nullptr!");
902 return;
903 }
904 auto eventId = event->GetInnerEventId();
905 int32_t systemAbilityId = static_cast<int32_t>(eventId);
906 auto stateScheduler = stateScheduler_.lock();
907 int32_t result = ERR_OK;
908 if (stateScheduler != nullptr) {
909 result = stateScheduler->ProcessDelayUnloadEvent(systemAbilityId);
910 }
911 if (result != ERR_OK) {
912 HILOGE("[SA Scheduler][SA: %{public}d] process delay unload event failed", systemAbilityId);
913 }
914 }
915 } // namespace OHOS