1 /*
2 * Copyright (c) 2021-2022 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 "ability_connect_manager.h"
17
18 #include <algorithm>
19
20 #include "ability_connect_callback_stub.h"
21 #include "ability_manager_errors.h"
22 #include "ability_manager_service.h"
23 #include "ability_util.h"
24 #include "hitrace_meter.h"
25 #include "hilog_wrapper.h"
26 #include "in_process_call_wrapper.h"
27 #include "parameter.h"
28
29 namespace OHOS {
30 namespace AAFwk {
AbilityConnectManager(int userId)31 AbilityConnectManager::AbilityConnectManager(int userId) : userId_(userId)
32 {}
33
~AbilityConnectManager()34 AbilityConnectManager::~AbilityConnectManager()
35 {}
36
StartAbility(const AbilityRequest & abilityRequest)37 int AbilityConnectManager::StartAbility(const AbilityRequest &abilityRequest)
38 {
39 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
40 std::lock_guard<std::recursive_mutex> guard(Lock_);
41 return StartAbilityLocked(abilityRequest);
42 }
43
TerminateAbility(const sptr<IRemoteObject> & token)44 int AbilityConnectManager::TerminateAbility(const sptr<IRemoteObject> &token)
45 {
46 std::lock_guard<std::recursive_mutex> guard(Lock_);
47 auto abilityRecord = GetExtensionByTokenFromSeriveMap(token);
48 MoveToTerminatingMap(abilityRecord);
49 return TerminateAbilityLocked(token);
50 }
51
TerminateAbility(const std::shared_ptr<AbilityRecord> & caller,int requestCode)52 int AbilityConnectManager::TerminateAbility(const std::shared_ptr<AbilityRecord> &caller, int requestCode)
53 {
54 HILOG_INFO("Terminate ability.");
55 std::lock_guard<std::recursive_mutex> guard(Lock_);
56
57 std::shared_ptr<AbilityRecord> targetAbility = nullptr;
58 int result = static_cast<int>(ABILITY_VISIBLE_FALSE_DENY_REQUEST);
59 std::for_each(serviceMap_.begin(),
60 serviceMap_.end(),
61 [&targetAbility, &caller, requestCode, &result](ServiceMapType::reference service) {
62 auto callerList = service.second->GetCallerRecordList();
63 for (auto &it : callerList) {
64 if (it->GetCaller() == caller && it->GetRequestCode() == requestCode) {
65 targetAbility = service.second;
66 if (targetAbility) {
67 auto abilityMs = DelayedSingleton<AbilityManagerService>::GetInstance();
68 CHECK_POINTER(abilityMs);
69 result = abilityMs->JudgeAbilityVisibleControl(targetAbility->GetAbilityInfo());
70 }
71 break;
72 }
73 }
74 });
75
76 if (!targetAbility) {
77 HILOG_ERROR("targetAbility error.");
78 return NO_FOUND_ABILITY_BY_CALLER;
79 }
80 if (result != ERR_OK) {
81 HILOG_ERROR("%{public}s JudgeAbilityVisibleControl error.", __func__);
82 return result;
83 }
84
85 MoveToTerminatingMap(targetAbility);
86 return TerminateAbilityLocked(targetAbility->GetToken());
87 }
88
StopServiceAbility(const AbilityRequest & abilityRequest)89 int AbilityConnectManager::StopServiceAbility(const AbilityRequest &abilityRequest)
90 {
91 HILOG_INFO("Stop Service ability.");
92 std::lock_guard<std::recursive_mutex> guard(Lock_);
93 return StopServiceAbilityLocked(abilityRequest);
94 }
95
TerminateAbilityResult(const sptr<IRemoteObject> & token,int startId)96 int AbilityConnectManager::TerminateAbilityResult(const sptr<IRemoteObject> &token, int startId)
97 {
98 HILOG_INFO("Terminate ability result.");
99 std::lock_guard<std::recursive_mutex> guard(Lock_);
100 return TerminateAbilityResultLocked(token, startId);
101 }
102
StartAbilityLocked(const AbilityRequest & abilityRequest)103 int AbilityConnectManager::StartAbilityLocked(const AbilityRequest &abilityRequest)
104 {
105 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
106 HILOG_INFO("Start ability locked, ability_name: %{public}s",
107 abilityRequest.want.GetElement().GetURI().c_str());
108
109 std::shared_ptr<AbilityRecord> targetService;
110 bool isLoadedAbility = false;
111 GetOrCreateServiceRecord(abilityRequest, false, targetService, isLoadedAbility);
112 CHECK_POINTER_AND_RETURN(targetService, ERR_INVALID_VALUE);
113
114 targetService->AddCallerRecord(abilityRequest.callerToken, abilityRequest.requestCode);
115
116 if (!isLoadedAbility) {
117 LoadAbility(targetService);
118 } else if (targetService->IsAbilityState(AbilityState::ACTIVE)) {
119 // It may have been started through connect
120 CommandAbility(targetService);
121 } else {
122 HILOG_ERROR("Target service is already activating.");
123 return START_SERVICE_ABILITY_ACTIVATING;
124 }
125
126 sptr<Token> token = targetService->GetToken();
127 sptr<Token> preToken = nullptr;
128 if (targetService->GetPreAbilityRecord()) {
129 preToken = targetService->GetPreAbilityRecord()->GetToken();
130 }
131 DelayedSingleton<AppScheduler>::GetInstance()->AbilityBehaviorAnalysis(token, preToken, 0, 1, 1);
132 return ERR_OK;
133 }
134
TerminateAbilityLocked(const sptr<IRemoteObject> & token)135 int AbilityConnectManager::TerminateAbilityLocked(const sptr<IRemoteObject> &token)
136 {
137 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
138 HILOG_INFO("Terminate ability locked.");
139 auto abilityRecord = GetExtensionByTokenFromTerminatingMap(token);
140 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
141
142 if (abilityRecord->IsTerminating()) {
143 HILOG_INFO("Ability is on terminating.");
144 return ERR_OK;
145 }
146
147 if (!abilityRecord->GetConnectRecordList().empty()) {
148 HILOG_INFO("Target service has been connected. Post disconnect task.");
149 auto connectRecordList = abilityRecord->GetConnectRecordList();
150 HandleTerminateDisconnectTask(connectRecordList);
151 }
152
153 auto timeoutTask = [abilityRecord, connectManager = shared_from_this()]() {
154 HILOG_WARN("Disconnect ability terminate timeout.");
155 connectManager->HandleStopTimeoutTask(abilityRecord);
156 };
157 abilityRecord->Terminate(timeoutTask);
158
159 return ERR_OK;
160 }
161
TerminateAbilityResultLocked(const sptr<IRemoteObject> & token,int startId)162 int AbilityConnectManager::TerminateAbilityResultLocked(const sptr<IRemoteObject> &token, int startId)
163 {
164 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
165 HILOG_INFO("Terminate ability result locked, startId: %{public}d", startId);
166 CHECK_POINTER_AND_RETURN(token, ERR_INVALID_VALUE);
167
168 auto abilityRecord = GetExtensionByTokenFromSeriveMap(token);
169 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
170
171 if (abilityRecord->GetStartId() != startId) {
172 HILOG_ERROR("Start id not equal.");
173 return TERMINATE_ABILITY_RESULT_FAILED;
174 }
175
176 MoveToTerminatingMap(abilityRecord);
177 return TerminateAbilityLocked(token);
178 }
179
StopServiceAbilityLocked(const AbilityRequest & abilityRequest)180 int AbilityConnectManager::StopServiceAbilityLocked(const AbilityRequest &abilityRequest)
181 {
182 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
183 HILOG_INFO("Stop service ability locked.");
184 AppExecFwk::ElementName element(abilityRequest.abilityInfo.deviceId, abilityRequest.abilityInfo.bundleName,
185 abilityRequest.abilityInfo.name, abilityRequest.abilityInfo.moduleName);
186 auto abilityRecord = GetServiceRecordByElementName(element.GetURI());
187 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
188
189 if (abilityRecord->IsTerminating()) {
190 HILOG_INFO("Ability is on terminating.");
191 return ERR_OK;
192 }
193
194 if (!abilityRecord->GetConnectRecordList().empty()) {
195 HILOG_INFO("Target service has been connected. Post disconnect task.");
196 auto connectRecordList = abilityRecord->GetConnectRecordList();
197 HandleTerminateDisconnectTask(connectRecordList);
198 }
199
200 auto timeoutTask = [abilityRecord, connectManager = shared_from_this()]() {
201 HILOG_WARN("Disconnect ability terminate timeout.");
202 connectManager->HandleStopTimeoutTask(abilityRecord);
203 };
204
205 MoveToTerminatingMap(abilityRecord);
206 abilityRecord->Terminate(timeoutTask);
207
208 return ERR_OK;
209 }
210
GetOrCreateServiceRecord(const AbilityRequest & abilityRequest,const bool isCreatedByConnect,std::shared_ptr<AbilityRecord> & targetService,bool & isLoadedAbility)211 void AbilityConnectManager::GetOrCreateServiceRecord(const AbilityRequest &abilityRequest,
212 const bool isCreatedByConnect, std::shared_ptr<AbilityRecord> &targetService, bool &isLoadedAbility)
213 {
214 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
215 AppExecFwk::ElementName element(abilityRequest.abilityInfo.deviceId, abilityRequest.abilityInfo.bundleName,
216 abilityRequest.abilityInfo.name, abilityRequest.abilityInfo.moduleName);
217 auto serviceMapIter = serviceMap_.find(element.GetURI());
218 if (serviceMapIter == serviceMap_.end()) {
219 targetService = AbilityRecord::CreateAbilityRecord(abilityRequest);
220 if (targetService) {
221 targetService->SetOwnerMissionUserId(userId_);
222 }
223
224 if (isCreatedByConnect && targetService != nullptr) {
225 targetService->SetCreateByConnectMode();
226 }
227 if (targetService && abilityRequest.abilityInfo.name == AbilityConfig::LAUNCHER_ABILITY_NAME) {
228 targetService->SetLauncherRoot();
229 targetService->SetKeepAlive();
230 targetService->SetRestartTime(abilityRequest.restartTime);
231 targetService->SetRestartCount(abilityRequest.restartCount);
232 } else if (IsAbilityNeedKeepAlive(targetService)) {
233 targetService->SetKeepAlive();
234 targetService->SetRestartTime(abilityRequest.restartTime);
235 targetService->SetRestartCount(abilityRequest.restartCount);
236 }
237 serviceMap_.emplace(element.GetURI(), targetService);
238 isLoadedAbility = false;
239 } else {
240 targetService = serviceMapIter->second;
241 if (targetService != nullptr) {
242 // want may be changed for the same ability.
243 targetService->SetWant(abilityRequest.want);
244 }
245 isLoadedAbility = true;
246 }
247 }
248
GetConnectRecordListFromMap(const sptr<IAbilityConnection> & connect,std::list<std::shared_ptr<ConnectionRecord>> & connectRecordList)249 void AbilityConnectManager::GetConnectRecordListFromMap(
250 const sptr<IAbilityConnection> &connect, std::list<std::shared_ptr<ConnectionRecord>> &connectRecordList)
251 {
252 auto connectMapIter = connectMap_.find(connect->AsObject());
253 if (connectMapIter != connectMap_.end()) {
254 connectRecordList = connectMapIter->second;
255 }
256 }
257
ConnectAbilityLocked(const AbilityRequest & abilityRequest,const sptr<IAbilityConnection> & connect,const sptr<IRemoteObject> & callerToken)258 int AbilityConnectManager::ConnectAbilityLocked(const AbilityRequest &abilityRequest,
259 const sptr<IAbilityConnection> &connect, const sptr<IRemoteObject> &callerToken)
260 {
261 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
262 HILOG_DEBUG("Connect ability called, callee:%{public}s.", abilityRequest.want.GetElement().GetURI().c_str());
263 std::lock_guard<std::recursive_mutex> guard(Lock_);
264
265 // 1. get target service ability record, and check whether it has been loaded.
266 std::shared_ptr<AbilityRecord> targetService;
267 bool isLoadedAbility = false;
268 GetOrCreateServiceRecord(abilityRequest, true, targetService, isLoadedAbility);
269 CHECK_POINTER_AND_RETURN(targetService, ERR_INVALID_VALUE);
270 // 2. get target connectRecordList, and check whether this callback has been connected.
271 ConnectListType connectRecordList;
272 GetConnectRecordListFromMap(connect, connectRecordList);
273 bool isCallbackConnected = !connectRecordList.empty();
274 // 3. If this service ability and callback has been connected, There is no need to connect repeatedly
275 if (isLoadedAbility && (isCallbackConnected) && IsAbilityConnected(targetService, connectRecordList)) {
276 HILOG_INFO("Service and callback was connected.");
277 return ERR_OK;
278 }
279
280 // 4. Other cases , need to connect the service ability
281 auto connectRecord = ConnectionRecord::CreateConnectionRecord(callerToken, targetService, connect);
282 CHECK_POINTER_AND_RETURN(connectRecord, ERR_INVALID_VALUE);
283 connectRecord->AttachCallerInfo();
284 connectRecord->SetConnectState(ConnectionState::CONNECTING);
285 targetService->AddConnectRecordToList(connectRecord);
286 connectRecordList.push_back(connectRecord);
287 if (isCallbackConnected) {
288 RemoveConnectDeathRecipient(connect);
289 connectMap_.erase(connectMap_.find(connect->AsObject()));
290 }
291 AddConnectDeathRecipient(connect);
292 connectMap_.emplace(connect->AsObject(), connectRecordList);
293
294 // 5. load or connect ability
295 int ret = ERR_OK;
296 if (!isLoadedAbility) {
297 LoadAbility(targetService);
298 } else if (targetService->IsAbilityState(AbilityState::ACTIVE)) {
299 // this service ability has not first connect
300 if (targetService->GetConnectRecordList().size() > 1) {
301 if (eventHandler_ != nullptr) {
302 auto task = [connectRecord]() { connectRecord->CompleteConnect(ERR_OK); };
303 eventHandler_->PostTask(task);
304 }
305 } else {
306 ConnectAbility(targetService);
307 }
308 } else {
309 HILOG_INFO("Target service ability is activating, just wait for callback");
310 }
311
312 auto token = targetService->GetToken();
313 auto preToken = iface_cast<Token>(connectRecord->GetToken());
314 DelayedSingleton<AppScheduler>::GetInstance()->AbilityBehaviorAnalysis(token, preToken, 0, 1, 1);
315 return ret;
316 }
317
DisconnectAbilityLocked(const sptr<IAbilityConnection> & connect)318 int AbilityConnectManager::DisconnectAbilityLocked(const sptr<IAbilityConnection> &connect)
319 {
320 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
321 HILOG_INFO("Disconnect ability begin.");
322 std::lock_guard<std::recursive_mutex> guard(Lock_);
323
324 // 1. check whether callback was connected.
325 ConnectListType connectRecordList;
326 GetConnectRecordListFromMap(connect, connectRecordList);
327 if (connectRecordList.empty()) {
328 HILOG_ERROR("Can't find the connect list from connect map by callback.");
329 return CONNECTION_NOT_EXIST;
330 }
331
332 // 2. schedule disconnect to target service
333 for (auto &connectRecord : connectRecordList) {
334 if (connectRecord) {
335 auto abilityRecord = connectRecord->GetAbilityRecord();
336 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
337 HILOG_INFO("Disconnect ability, caller:%{public}s.", abilityRecord->GetAbilityInfo().name.c_str());
338 auto abilityMs = DelayedSingleton<AbilityManagerService>::GetInstance();
339 CHECK_POINTER_AND_RETURN(abilityMs, GET_ABILITY_SERVICE_FAILED);
340 int result = abilityMs->JudgeAbilityVisibleControl(abilityRecord->GetAbilityInfo());
341 if (result != ERR_OK) {
342 HILOG_ERROR("Judge ability visible error.");
343 return result;
344 }
345 int ret = connectRecord->DisconnectAbility();
346 if (ret != ERR_OK) {
347 HILOG_ERROR("Disconnect ability fail , ret = %{public}d.", ret);
348 return ret;
349 }
350
351 if (connectRecord->GetConnectState() == ConnectionState::DISCONNECTED) {
352 HILOG_WARN("This record: %{public}d complete disconnect directly.", connectRecord->GetRecordId());
353 connectRecord->CompleteDisconnect(ERR_OK, false);
354 RemoveConnectionRecordFromMap(connectRecord);
355 }
356 }
357 }
358
359 return ERR_OK;
360 }
361
AttachAbilityThreadLocked(const sptr<IAbilityScheduler> & scheduler,const sptr<IRemoteObject> & token)362 int AbilityConnectManager::AttachAbilityThreadLocked(
363 const sptr<IAbilityScheduler> &scheduler, const sptr<IRemoteObject> &token)
364 {
365 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
366 std::lock_guard<std::recursive_mutex> guard(Lock_);
367 auto abilityRecord = GetExtensionByTokenFromSeriveMap(token);
368 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
369 if (eventHandler_ != nullptr) {
370 int recordId = abilityRecord->GetRecordId();
371 std::string taskName = std::string("LoadTimeout_") + std::to_string(recordId);
372 eventHandler_->RemoveTask(taskName);
373 eventHandler_->RemoveEvent(AbilityManagerService::LOAD_TIMEOUT_MSG, abilityRecord->GetEventId());
374 }
375 std::string element = abilityRecord->GetWant().GetElement().GetURI();
376 HILOG_DEBUG("Ability: %{public}s", element.c_str());
377 abilityRecord->SetScheduler(scheduler);
378 abilityRecord->Inactivate();
379
380 return ERR_OK;
381 }
382
OnAppStateChanged(const AppInfo & info)383 void AbilityConnectManager::OnAppStateChanged(const AppInfo &info)
384 {
385 std::lock_guard<std::recursive_mutex> guard(Lock_);
386 std::for_each(serviceMap_.begin(), serviceMap_.end(), [&info](ServiceMapType::reference service) {
387 if (service.second && (info.processName == service.second->GetAbilityInfo().process ||
388 info.processName == service.second->GetApplicationInfo().bundleName)) {
389 auto appName = service.second->GetApplicationInfo().name;
390 auto uid = service.second->GetAbilityInfo().applicationInfo.uid;
391 auto isExist = [&appName, &uid](
392 const AppData &appData) { return appData.appName == appName && appData.uid == uid; };
393 auto iter = std::find_if(info.appData.begin(), info.appData.end(), isExist);
394 if (iter != info.appData.end()) {
395 service.second->SetAppState(info.state);
396 }
397 }
398 });
399 }
400
AbilityTransitionDone(const sptr<IRemoteObject> & token,int state)401 int AbilityConnectManager::AbilityTransitionDone(const sptr<IRemoteObject> &token, int state)
402 {
403 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
404 std::lock_guard<std::recursive_mutex> guard(Lock_);
405 int targetState = AbilityRecord::ConvertLifeCycleToAbilityState(static_cast<AbilityLifeCycleState>(state));
406 std::string abilityState = AbilityRecord::ConvertAbilityState(static_cast<AbilityState>(targetState));
407 std::shared_ptr<AbilityRecord> abilityRecord;
408 if (static_cast<AbilityState>(targetState) == AbilityState::INACTIVE) {
409 abilityRecord = GetExtensionByTokenFromSeriveMap(token);
410 } else if (static_cast<AbilityState>(targetState) == AbilityState::INITIAL) {
411 abilityRecord = GetExtensionByTokenFromTerminatingMap(token);
412 } else {
413 abilityRecord = nullptr;
414 }
415 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
416 std::string element = abilityRecord->GetWant().GetElement().GetURI();
417 HILOG_DEBUG("Ability: %{public}s, state: %{public}s", element.c_str(), abilityState.c_str());
418
419 switch (state) {
420 case AbilityState::INACTIVE: {
421 if (abilityRecord->GetAbilityInfo().type == AbilityType::SERVICE) {
422 DelayedSingleton<AppScheduler>::GetInstance()->UpdateAbilityState(
423 token, AppExecFwk::AbilityState::ABILITY_STATE_CREATE);
424 } else {
425 DelayedSingleton<AppScheduler>::GetInstance()->UpdateExtensionState(
426 token, AppExecFwk::ExtensionState::EXTENSION_STATE_CREATE);
427 auto preloadTask = [owner = weak_from_this(), abilityRecord] {
428 auto acm = owner.lock();
429 if (acm == nullptr) {
430 HILOG_ERROR("AbilityConnectManager is nullptr.");
431 return;
432 }
433 acm->ProcessPreload(abilityRecord);
434 };
435 if (eventHandler_ != nullptr) {
436 eventHandler_->PostTask(preloadTask);
437 }
438 }
439 return DispatchInactive(abilityRecord, state);
440 }
441 case AbilityState::INITIAL: {
442 if (abilityRecord->GetAbilityInfo().type == AbilityType::SERVICE) {
443 DelayedSingleton<AppScheduler>::GetInstance()->UpdateAbilityState(
444 token, AppExecFwk::AbilityState::ABILITY_STATE_TERMINATED);
445 } else {
446 DelayedSingleton<AppScheduler>::GetInstance()->UpdateExtensionState(
447 token, AppExecFwk::ExtensionState::EXTENSION_STATE_TERMINATED);
448 }
449 return DispatchTerminate(abilityRecord);
450 }
451 default: {
452 HILOG_WARN("Don't support transiting state: %{public}d", state);
453 return ERR_INVALID_VALUE;
454 }
455 }
456 }
457
ProcessPreload(const std::shared_ptr<AbilityRecord> & record) const458 void AbilityConnectManager::ProcessPreload(const std::shared_ptr<AbilityRecord> &record) const
459 {
460 auto bms = AbilityUtil::GetBundleManager();
461 CHECK_POINTER(bms);
462 auto abilityInfo = record->GetAbilityInfo();
463 Want want;
464 want.SetElementName(abilityInfo.deviceId, abilityInfo.bundleName, abilityInfo.name, abilityInfo.moduleName);
465 auto uid = record->GetUid();
466 want.SetParam("uid", uid);
467 bms->ProcessPreload(want);
468 }
469
ScheduleConnectAbilityDoneLocked(const sptr<IRemoteObject> & token,const sptr<IRemoteObject> & remoteObject)470 int AbilityConnectManager::ScheduleConnectAbilityDoneLocked(
471 const sptr<IRemoteObject> &token, const sptr<IRemoteObject> &remoteObject)
472 {
473 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
474 std::lock_guard<std::recursive_mutex> guard(Lock_);
475 CHECK_POINTER_AND_RETURN(token, ERR_INVALID_VALUE);
476
477 auto abilityRecord = Token::GetAbilityRecordByToken(token);
478 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
479
480 std::string element = abilityRecord->GetWant().GetElement().GetURI();
481 HILOG_DEBUG("Connect ability done, ability: %{public}s.", element.c_str());
482
483 if ((!abilityRecord->IsAbilityState(AbilityState::INACTIVE)) &&
484 (!abilityRecord->IsAbilityState(AbilityState::ACTIVE))) {
485 HILOG_ERROR("Ability record state is not inactive ,state: %{public}d", abilityRecord->GetAbilityState());
486 return INVALID_CONNECTION_STATE;
487 }
488
489 if (abilityRecord->GetAbilityInfo().type == AbilityType::SERVICE) {
490 DelayedSingleton<AppScheduler>::GetInstance()->UpdateAbilityState(
491 token, AppExecFwk::AbilityState::ABILITY_STATE_CONNECTED);
492 } else {
493 DelayedSingleton<AppScheduler>::GetInstance()->UpdateExtensionState(
494 token, AppExecFwk::ExtensionState::EXTENSION_STATE_CONNECTED);
495 }
496
497 abilityRecord->SetConnRemoteObject(remoteObject);
498 // There may be multiple callers waiting for the connection result
499 auto connectRecordList = abilityRecord->GetConnectRecordList();
500 for (auto &connectRecord : connectRecordList) {
501 connectRecord->ScheduleConnectAbilityDone();
502 }
503
504 return ERR_OK;
505 }
506
ScheduleDisconnectAbilityDoneLocked(const sptr<IRemoteObject> & token)507 int AbilityConnectManager::ScheduleDisconnectAbilityDoneLocked(const sptr<IRemoteObject> &token)
508 {
509 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
510 std::lock_guard<std::recursive_mutex> guard(Lock_);
511 auto abilityRecord = GetExtensionByTokenFromSeriveMap(token);
512 CHECK_POINTER_AND_RETURN(abilityRecord, CONNECTION_NOT_EXIST);
513
514 auto connect = abilityRecord->GetDisconnectingRecord();
515 CHECK_POINTER_AND_RETURN(connect, CONNECTION_NOT_EXIST);
516
517 if (!abilityRecord->IsAbilityState(AbilityState::ACTIVE)) {
518 HILOG_ERROR("The service ability state is not active ,state: %{public}d", abilityRecord->GetAbilityState());
519 return INVALID_CONNECTION_STATE;
520 }
521
522 if (abilityRecord->GetAbilityInfo().type == AbilityType::SERVICE) {
523 DelayedSingleton<AppScheduler>::GetInstance()->UpdateAbilityState(
524 token, AppExecFwk::AbilityState::ABILITY_STATE_DISCONNECTED);
525 } else {
526 DelayedSingleton<AppScheduler>::GetInstance()->UpdateExtensionState(
527 token, AppExecFwk::ExtensionState::EXTENSION_STATE_DISCONNECTED);
528 }
529
530 std::string element = abilityRecord->GetWant().GetElement().GetURI();
531 HILOG_DEBUG("Disconnect ability done, service:%{public}s.", element.c_str());
532
533 // complete disconnect and remove record from conn map
534 connect->ScheduleDisconnectAbilityDone();
535 abilityRecord->RemoveConnectRecordFromList(connect);
536 if (abilityRecord->IsConnectListEmpty() && abilityRecord->GetStartId() == 0) {
537 HILOG_INFO("Service ability has no any connection, and not started , need terminate.");
538 auto timeoutTask = [abilityRecord, connectManager = shared_from_this()]() {
539 HILOG_WARN("Disconnect ability terminate timeout.");
540 connectManager->HandleStopTimeoutTask(abilityRecord);
541 };
542 MoveToTerminatingMap(abilityRecord);
543 abilityRecord->Terminate(timeoutTask);
544 }
545 RemoveConnectionRecordFromMap(connect);
546
547 return ERR_OK;
548 }
549
ScheduleCommandAbilityDoneLocked(const sptr<IRemoteObject> & token)550 int AbilityConnectManager::ScheduleCommandAbilityDoneLocked(const sptr<IRemoteObject> &token)
551 {
552 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
553 std::lock_guard<std::recursive_mutex> guard(Lock_);
554 CHECK_POINTER_AND_RETURN(token, ERR_INVALID_VALUE);
555 auto abilityRecord = Token::GetAbilityRecordByToken(token);
556 CHECK_POINTER_AND_RETURN(abilityRecord, ERR_INVALID_VALUE);
557 std::string element = abilityRecord->GetWant().GetElement().GetURI();
558 HILOG_DEBUG("Ability: %{public}s", element.c_str());
559
560 if ((!abilityRecord->IsAbilityState(AbilityState::INACTIVE)) &&
561 (!abilityRecord->IsAbilityState(AbilityState::ACTIVE))) {
562 HILOG_ERROR("Ability record state is not inactive ,state: %{public}d", abilityRecord->GetAbilityState());
563 return INVALID_CONNECTION_STATE;
564 }
565 // complete command and pop waiting start ability from queue.
566 CompleteCommandAbility(abilityRecord);
567
568 return ERR_OK;
569 }
570
CompleteCommandAbility(std::shared_ptr<AbilityRecord> abilityRecord)571 void AbilityConnectManager::CompleteCommandAbility(std::shared_ptr<AbilityRecord> abilityRecord)
572 {
573 CHECK_POINTER(abilityRecord);
574
575 if (eventHandler_) {
576 int recordId = abilityRecord->GetRecordId();
577 std::string taskName = std::string("CommandTimeout_") + std::to_string(recordId) + std::string("_") +
578 std::to_string(abilityRecord->GetStartId());
579 eventHandler_->RemoveTask(taskName);
580 }
581
582 abilityRecord->SetAbilityState(AbilityState::ACTIVE);
583 }
584
GetServiceRecordByElementName(const std::string & element)585 std::shared_ptr<AbilityRecord> AbilityConnectManager::GetServiceRecordByElementName(const std::string &element)
586 {
587 std::lock_guard<std::recursive_mutex> guard(Lock_);
588 auto mapIter = serviceMap_.find(element);
589 if (mapIter != serviceMap_.end()) {
590 return mapIter->second;
591 }
592 return nullptr;
593 }
594
GetExtensionByTokenFromSeriveMap(const sptr<IRemoteObject> & token)595 std::shared_ptr<AbilityRecord> AbilityConnectManager::GetExtensionByTokenFromSeriveMap(const sptr<IRemoteObject> &token)
596 {
597 std::lock_guard<std::recursive_mutex> guard(Lock_);
598 auto IsMatch = [token](auto service) {
599 if (!service.second) {
600 return false;
601 }
602 sptr<IRemoteObject> srcToken = service.second->GetToken();
603 return srcToken == token;
604 };
605 auto serviceRecord = std::find_if(serviceMap_.begin(), serviceMap_.end(), IsMatch);
606 if (serviceRecord != serviceMap_.end()) {
607 return serviceRecord->second;
608 }
609 return nullptr;
610 }
611
GetExtensionByTokenFromTerminatingMap(const sptr<IRemoteObject> & token)612 std::shared_ptr<AbilityRecord> AbilityConnectManager::GetExtensionByTokenFromTerminatingMap(
613 const sptr<IRemoteObject> &token)
614 {
615 std::lock_guard<std::recursive_mutex> guard(Lock_);
616 auto IsMatch = [token](auto& extension) {
617 if (extension.second == nullptr) {
618 return false;
619 }
620 auto&& terminatingToken = extension.second->GetToken();
621 if (terminatingToken != nullptr) {
622 return terminatingToken->AsObject() == token;
623 }
624 return false;
625 };
626
627 auto terminatingExtensionRecord =
628 std::find_if(terminatingExtensionMap_.begin(), terminatingExtensionMap_.end(), IsMatch);
629 if (terminatingExtensionRecord != terminatingExtensionMap_.end()) {
630 return terminatingExtensionRecord->second;
631 }
632 return nullptr;
633 }
634
GetConnectRecordListByCallback(sptr<IAbilityConnection> callback)635 std::list<std::shared_ptr<ConnectionRecord>> AbilityConnectManager::GetConnectRecordListByCallback(
636 sptr<IAbilityConnection> callback)
637 {
638 std::lock_guard<std::recursive_mutex> guard(Lock_);
639 std::list<std::shared_ptr<ConnectionRecord>> connectList;
640 auto connectMapIter = connectMap_.find(callback->AsObject());
641 if (connectMapIter != connectMap_.end()) {
642 connectList = connectMapIter->second;
643 }
644 return connectList;
645 }
646
GetAbilityRecordByEventId(int64_t eventId)647 std::shared_ptr<AbilityRecord> AbilityConnectManager::GetAbilityRecordByEventId(int64_t eventId)
648 {
649 std::lock_guard<std::recursive_mutex> guard(Lock_);
650 auto IsMatch = [eventId](auto service) {
651 if (!service.second) {
652 return false;
653 }
654 return eventId == service.second->GetEventId();
655 };
656 auto serviceRecord = std::find_if(serviceMap_.begin(), serviceMap_.end(), IsMatch);
657 if (serviceRecord != serviceMap_.end()) {
658 return serviceRecord->second;
659 }
660 return nullptr;
661 }
662
LoadAbility(const std::shared_ptr<AbilityRecord> & abilityRecord)663 void AbilityConnectManager::LoadAbility(const std::shared_ptr<AbilityRecord> &abilityRecord)
664 {
665 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
666 CHECK_POINTER(abilityRecord);
667 abilityRecord->SetStartTime();
668
669 if (!abilityRecord->CanRestartRootLauncher()) {
670 HILOG_ERROR("Root launcher restart is out of max count.");
671 RemoveServiceAbility(abilityRecord);
672 return;
673 }
674
675 PostTimeOutTask(abilityRecord, AbilityManagerService::LOAD_TIMEOUT_MSG);
676
677 sptr<Token> token = abilityRecord->GetToken();
678 sptr<Token> perToken = nullptr;
679 if (abilityRecord->IsCreateByConnect()) {
680 perToken = iface_cast<Token>(abilityRecord->GetConnectingRecord()->GetToken());
681 } else {
682 auto callerList = abilityRecord->GetCallerRecordList();
683 if (!callerList.empty() && callerList.back()) {
684 auto caller = callerList.back()->GetCaller();
685 if (caller) {
686 perToken = caller->GetToken();
687 }
688 }
689 }
690 DelayedSingleton<AppScheduler>::GetInstance()->LoadAbility(
691 token, perToken, abilityRecord->GetAbilityInfo(), abilityRecord->GetApplicationInfo(),
692 abilityRecord->GetWant());
693 }
694
PostRestartResidentTask(const AbilityRequest & abilityRequest)695 void AbilityConnectManager::PostRestartResidentTask(const AbilityRequest &abilityRequest)
696 {
697 HILOG_INFO("PostRestartResidentTask start.");
698 CHECK_POINTER(eventHandler_);
699 std::string taskName = std::string("RestartResident_") + std::string(abilityRequest.abilityInfo.name);
700 auto task = [abilityRequest, connectManager = shared_from_this()]() {
701 CHECK_POINTER(connectManager);
702 connectManager->HandleRestartResidentTask(abilityRequest);
703 };
704 int restartIntervalTime = 0;
705 auto abilityMgr = DelayedSingleton<AbilityManagerService>::GetInstance();
706 if (abilityMgr) {
707 abilityMgr->GetRestartIntervalTime(restartIntervalTime);
708 }
709 HILOG_DEBUG("PostRestartResidentTask, time:%{public}d", restartIntervalTime);
710 eventHandler_->PostTask(task, taskName, restartIntervalTime);
711 HILOG_INFO("PostRestartResidentTask end.");
712 }
713
HandleRestartResidentTask(const AbilityRequest & abilityRequest)714 void AbilityConnectManager::HandleRestartResidentTask(const AbilityRequest &abilityRequest)
715 {
716 HILOG_INFO("HandleRestartResidentTask start.");
717 auto findRestartResidentTask = [abilityRequest](const AbilityRequest &requestInfo) {
718 return (requestInfo.want.GetElement().GetBundleName() == abilityRequest.want.GetElement().GetBundleName() &&
719 requestInfo.want.GetElement().GetModuleName() == abilityRequest.want.GetElement().GetModuleName() &&
720 requestInfo.want.GetElement().GetAbilityName() == abilityRequest.want.GetElement().GetAbilityName());
721 };
722 auto findIter = find_if(restartResidentTaskList_.begin(), restartResidentTaskList_.end(), findRestartResidentTask);
723 if (findIter != restartResidentTaskList_.end()) {
724 restartResidentTaskList_.erase(findIter);
725 }
726 StartAbilityLocked(abilityRequest);
727 }
728
PostTimeOutTask(const std::shared_ptr<AbilityRecord> & abilityRecord,uint32_t messageId)729 void AbilityConnectManager::PostTimeOutTask(const std::shared_ptr<AbilityRecord> &abilityRecord, uint32_t messageId)
730 {
731 CHECK_POINTER(abilityRecord);
732 CHECK_POINTER(eventHandler_);
733 if (messageId != AbilityConnectManager::LOAD_TIMEOUT_MSG &&
734 messageId != AbilityConnectManager::CONNECT_TIMEOUT_MSG) {
735 HILOG_ERROR("Timeout task messageId is error.");
736 return;
737 }
738
739 int recordId;
740 std::string taskName;
741 int resultCode;
742 uint32_t delayTime;
743 if (abilityRecord->GetApplicationInfo().asanEnabled) {
744 recordId = abilityRecord->GetRecordId();
745 taskName = std::string("LoadTimeout_") + std::to_string(recordId);
746 resultCode = LOAD_ABILITY_TIMEOUT;
747 delayTime = AbilityManagerService::LOAD_TIMEOUT_ASANENABLED;
748 } else if (messageId == AbilityManagerService::LOAD_TIMEOUT_MSG) {
749 // first load ability, There is at most one connect record.
750 recordId = abilityRecord->GetRecordId();
751 taskName = std::string("LoadTimeout_") + std::to_string(recordId);
752 resultCode = LOAD_ABILITY_TIMEOUT;
753 delayTime = AbilityManagerService::LOAD_TIMEOUT;
754 } else {
755 auto connectRecord = abilityRecord->GetConnectingRecord();
756 CHECK_POINTER(connectRecord);
757 recordId = connectRecord->GetRecordId();
758 taskName = std::string("ConnectTimeout_") + std::to_string(recordId);
759 resultCode = CONNECTION_TIMEOUT;
760 delayTime = AbilityManagerService::CONNECT_TIMEOUT;
761 }
762
763 // check libc.hook_mode
764 const int bufferLen = 128;
765 char paramOutBuf[bufferLen] = {0};
766 const char *hook_mode = "startup:";
767 int ret = GetParameter("libc.hook_mode", "", paramOutBuf, bufferLen - 1);
768 if (ret > 0 && strncmp(paramOutBuf, hook_mode, strlen(hook_mode)) == 0) {
769 HILOG_DEBUG("Hook_mode: no timeoutTask");
770 return;
771 }
772
773 auto timeoutTask = [abilityRecord, connectManager = shared_from_this(), resultCode]() {
774 HILOG_WARN("Connect or load ability timeout.");
775 connectManager->HandleStartTimeoutTask(abilityRecord, resultCode);
776 };
777
778 eventHandler_->PostTask(timeoutTask, taskName, delayTime);
779 }
780
HandleStartTimeoutTask(const std::shared_ptr<AbilityRecord> & abilityRecord,int resultCode)781 void AbilityConnectManager::HandleStartTimeoutTask(const std::shared_ptr<AbilityRecord> &abilityRecord, int resultCode)
782 {
783 HILOG_DEBUG("Complete connect or load ability timeout.");
784 std::lock_guard<std::recursive_mutex> guard(Lock_);
785 CHECK_POINTER(abilityRecord);
786 auto connectingList = abilityRecord->GetConnectingRecordList();
787 for (auto &connectRecord : connectingList) {
788 if (connectRecord == nullptr) {
789 HILOG_WARN("ConnectRecord is nullptr.");
790 continue;
791 }
792 connectRecord->CompleteDisconnect(ERR_OK, true);
793 abilityRecord->RemoveConnectRecordFromList(connectRecord);
794 RemoveConnectionRecordFromMap(connectRecord);
795 }
796
797 if (GetExtensionByTokenFromSeriveMap(abilityRecord->GetToken()) == nullptr) {
798 HILOG_ERROR("Timeojut ability record is not exist in service map.");
799 return;
800 }
801 MoveToTerminatingMap(abilityRecord);
802
803 if (resultCode == LOAD_ABILITY_TIMEOUT) {
804 HILOG_WARN("Load time out , remove target service record from services map.");
805 RemoveServiceAbility(abilityRecord);
806 if (abilityRecord->GetAbilityInfo().name != AbilityConfig::LAUNCHER_ABILITY_NAME) {
807 DelayedSingleton<AppScheduler>::GetInstance()->AttachTimeOut(abilityRecord->GetToken());
808 if (IsAbilityNeedKeepAlive(abilityRecord)) {
809 HILOG_WARN("Load time out , try to restart.");
810 RestartAbility(abilityRecord, userId_);
811 }
812 }
813 }
814
815 if (abilityRecord->GetAbilityInfo().name == AbilityConfig::LAUNCHER_ABILITY_NAME) {
816 // terminate the timeout root launcher.
817 DelayedSingleton<AppScheduler>::GetInstance()->AttachTimeOut(abilityRecord->GetToken());
818 if (resultCode == LOAD_ABILITY_TIMEOUT) {
819 StartRootLauncher(abilityRecord);
820 }
821 }
822 }
823
HandleCommandTimeoutTask(const std::shared_ptr<AbilityRecord> & abilityRecord)824 void AbilityConnectManager::HandleCommandTimeoutTask(const std::shared_ptr<AbilityRecord> &abilityRecord)
825 {
826 HILOG_DEBUG("HandleCommandTimeoutTask start");
827 std::lock_guard<std::recursive_mutex> guard(Lock_);
828 CHECK_POINTER(abilityRecord);
829 if (abilityRecord->GetAbilityInfo().name == AbilityConfig::LAUNCHER_ABILITY_NAME) {
830 HILOG_DEBUG("Handle root launcher command timeout.");
831 // terminate the timeout root launcher.
832 DelayedSingleton<AppScheduler>::GetInstance()->AttachTimeOut(abilityRecord->GetToken());
833 }
834 HILOG_DEBUG("HandleCommandTimeoutTask end");
835 }
836
StartRootLauncher(const std::shared_ptr<AbilityRecord> & abilityRecord)837 void AbilityConnectManager::StartRootLauncher(const std::shared_ptr<AbilityRecord> &abilityRecord)
838 {
839 CHECK_POINTER(abilityRecord);
840 AbilityRequest requestInfo;
841 requestInfo.want = abilityRecord->GetWant();
842 requestInfo.abilityInfo = abilityRecord->GetAbilityInfo();
843 requestInfo.appInfo = abilityRecord->GetApplicationInfo();
844 requestInfo.restartTime = abilityRecord->GetRestartTime();
845 requestInfo.restart = true;
846 requestInfo.restartCount = abilityRecord->GetRestartCount() - 1;
847
848 HILOG_DEBUG("restart root launcher, number:%{public}d", requestInfo.restartCount);
849 StartAbilityLocked(requestInfo);
850 }
851
HandleStopTimeoutTask(const std::shared_ptr<AbilityRecord> & abilityRecord)852 void AbilityConnectManager::HandleStopTimeoutTask(const std::shared_ptr<AbilityRecord> &abilityRecord)
853 {
854 HILOG_DEBUG("Complete stop ability timeout start.");
855 std::lock_guard<std::recursive_mutex> guard(Lock_);
856 CHECK_POINTER(abilityRecord);
857 TerminateDone(abilityRecord);
858 }
859
HandleTerminateDisconnectTask(const ConnectListType & connectlist)860 void AbilityConnectManager::HandleTerminateDisconnectTask(const ConnectListType& connectlist)
861 {
862 HILOG_DEBUG("Disconnect ability when terminate.");
863 std::lock_guard<std::recursive_mutex> guard(Lock_);
864 for (auto& connectRecord : connectlist) {
865 if (!connectRecord) {
866 continue;
867 }
868 auto targetService = connectRecord->GetAbilityRecord();
869 if (targetService) {
870 HILOG_WARN("This record complete disconnect directly. recordId:%{public}d", connectRecord->GetRecordId());
871 connectRecord->CompleteDisconnect(ERR_OK, true);
872 targetService->RemoveConnectRecordFromList(connectRecord);
873 RemoveConnectionRecordFromMap(connectRecord);
874 };
875 }
876 }
877
DispatchInactive(const std::shared_ptr<AbilityRecord> & abilityRecord,int state)878 int AbilityConnectManager::DispatchInactive(const std::shared_ptr<AbilityRecord> &abilityRecord, int state)
879 {
880 CHECK_POINTER_AND_RETURN(eventHandler_, ERR_INVALID_VALUE);
881 if (!abilityRecord->IsAbilityState(AbilityState::INACTIVATING)) {
882 HILOG_ERROR("Ability transition life state error. expect %{public}d, actual %{public}d callback %{public}d",
883 AbilityState::INACTIVATING,
884 abilityRecord->GetAbilityState(),
885 state);
886 return ERR_INVALID_VALUE;
887 }
888 eventHandler_->RemoveEvent(AbilityManagerService::INACTIVE_TIMEOUT_MSG, abilityRecord->GetEventId());
889
890 // complete inactive
891 abilityRecord->SetAbilityState(AbilityState::INACTIVE);
892 if (abilityRecord->IsCreateByConnect()) {
893 ConnectAbility(abilityRecord);
894 } else {
895 CommandAbility(abilityRecord);
896 }
897
898 return ERR_OK;
899 }
900
DispatchTerminate(const std::shared_ptr<AbilityRecord> & abilityRecord)901 int AbilityConnectManager::DispatchTerminate(const std::shared_ptr<AbilityRecord> &abilityRecord)
902 {
903 // remove terminate timeout task
904 if (eventHandler_ != nullptr) {
905 eventHandler_->RemoveTask(std::to_string(abilityRecord->GetEventId()));
906 }
907 // complete terminate
908 TerminateDone(abilityRecord);
909 return ERR_OK;
910 }
911
ConnectAbility(const std::shared_ptr<AbilityRecord> & abilityRecord)912 void AbilityConnectManager::ConnectAbility(const std::shared_ptr<AbilityRecord> &abilityRecord)
913 {
914 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
915 CHECK_POINTER(abilityRecord);
916 PostTimeOutTask(abilityRecord, AbilityConnectManager::CONNECT_TIMEOUT_MSG);
917 abilityRecord->ConnectAbility();
918 }
919
CommandAbility(const std::shared_ptr<AbilityRecord> & abilityRecord)920 void AbilityConnectManager::CommandAbility(const std::shared_ptr<AbilityRecord> &abilityRecord)
921 {
922 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
923 if (eventHandler_ != nullptr) {
924 // first connect ability, There is at most one connect record.
925 int recordId = abilityRecord->GetRecordId();
926 abilityRecord->AddStartId();
927 std::string taskName = std::string("CommandTimeout_") + std::to_string(recordId) + std::string("_") +
928 std::to_string(abilityRecord->GetStartId());
929 auto timeoutTask = [abilityRecord, connectManager = shared_from_this()]() {
930 HILOG_ERROR("Command ability timeout. %{public}s", abilityRecord->GetAbilityInfo().name.c_str());
931 connectManager->HandleCommandTimeoutTask(abilityRecord);
932 };
933 eventHandler_->PostTask(timeoutTask, taskName, AbilityManagerService::COMMAND_TIMEOUT);
934 // scheduling command ability
935 abilityRecord->CommandAbility();
936 }
937 }
938
TerminateDone(const std::shared_ptr<AbilityRecord> & abilityRecord)939 void AbilityConnectManager::TerminateDone(const std::shared_ptr<AbilityRecord> &abilityRecord)
940 {
941 HITRACE_METER_NAME(HITRACE_TAG_ABILITY_MANAGER, __PRETTY_FUNCTION__);
942 if (!abilityRecord->IsAbilityState(AbilityState::TERMINATING)) {
943 std::string expect = AbilityRecord::ConvertAbilityState(AbilityState::TERMINATING);
944 std::string actual = AbilityRecord::ConvertAbilityState(abilityRecord->GetAbilityState());
945 HILOG_ERROR(
946 "Transition life state error. expect %{public}s, actual %{public}s", expect.c_str(), actual.c_str());
947 return;
948 }
949 DelayedSingleton<AppScheduler>::GetInstance()->TerminateAbility(abilityRecord->GetToken(), false);
950 RemoveServiceAbility(abilityRecord);
951 }
952
IsAbilityConnected(const std::shared_ptr<AbilityRecord> & abilityRecord,const std::list<std::shared_ptr<ConnectionRecord>> & connectRecordList)953 bool AbilityConnectManager::IsAbilityConnected(const std::shared_ptr<AbilityRecord> &abilityRecord,
954 const std::list<std::shared_ptr<ConnectionRecord>> &connectRecordList)
955 {
956 auto isMatch = [abilityRecord](auto connectRecord) -> bool {
957 if (abilityRecord == nullptr || connectRecord == nullptr) {
958 return false;
959 }
960 if (abilityRecord != connectRecord->GetAbilityRecord()) {
961 return false;
962 }
963 return true;
964 };
965 return std::any_of(connectRecordList.begin(), connectRecordList.end(), isMatch);
966 }
967
RemoveConnectionRecordFromMap(const std::shared_ptr<ConnectionRecord> & connection)968 void AbilityConnectManager::RemoveConnectionRecordFromMap(const std::shared_ptr<ConnectionRecord> &connection)
969 {
970 for (auto &connectCallback : connectMap_) {
971 auto &connectList = connectCallback.second;
972 auto connectRecord = std::find(connectList.begin(), connectList.end(), connection);
973 if (connectRecord != connectList.end()) {
974 HILOG_INFO("Remove connrecord(%{public}d) from maplist.", (*connectRecord)->GetRecordId());
975 connectList.remove(connection);
976 if (connectList.empty()) {
977 HILOG_INFO("Remove connlist from map.");
978 sptr<IAbilityConnection> connect = iface_cast<IAbilityConnection>(connectCallback.first);
979 RemoveConnectDeathRecipient(connect);
980 connectMap_.erase(connectCallback.first);
981 }
982 return;
983 }
984 }
985 }
986
RemoveServiceAbility(const std::shared_ptr<AbilityRecord> & abilityRecord)987 void AbilityConnectManager::RemoveServiceAbility(const std::shared_ptr<AbilityRecord> &abilityRecord)
988 {
989 CHECK_POINTER(abilityRecord);
990 auto& abilityInfo = abilityRecord->GetAbilityInfo();
991 AppExecFwk::ElementName element(abilityInfo.deviceId, abilityInfo.bundleName, abilityInfo.name,
992 abilityInfo.moduleName);
993 HILOG_DEBUG("Remove service(%{public}s) from terminating map.", element.GetURI().c_str());
994 terminatingExtensionMap_.erase(element.GetURI());
995 }
996
AddConnectDeathRecipient(const sptr<IAbilityConnection> & connect)997 void AbilityConnectManager::AddConnectDeathRecipient(const sptr<IAbilityConnection> &connect)
998 {
999 CHECK_POINTER(connect);
1000 CHECK_POINTER(connect->AsObject());
1001 auto it = recipientMap_.find(connect->AsObject());
1002 if (it != recipientMap_.end()) {
1003 HILOG_ERROR("This death recipient has been added.");
1004 return;
1005 } else {
1006 std::weak_ptr<AbilityConnectManager> thisWeakPtr(shared_from_this());
1007 sptr<IRemoteObject::DeathRecipient> deathRecipient =
1008 new AbilityConnectCallbackRecipient([thisWeakPtr](const wptr<IRemoteObject> &remote) {
1009 auto abilityConnectManager = thisWeakPtr.lock();
1010 if (abilityConnectManager) {
1011 abilityConnectManager->OnCallBackDied(remote);
1012 }
1013 });
1014 connect->AsObject()->AddDeathRecipient(deathRecipient);
1015 recipientMap_.emplace(connect->AsObject(), deathRecipient);
1016 }
1017 }
1018
RemoveConnectDeathRecipient(const sptr<IAbilityConnection> & connect)1019 void AbilityConnectManager::RemoveConnectDeathRecipient(const sptr<IAbilityConnection> &connect)
1020 {
1021 CHECK_POINTER(connect);
1022 CHECK_POINTER(connect->AsObject());
1023 auto it = recipientMap_.find(connect->AsObject());
1024 if (it != recipientMap_.end()) {
1025 it->first->RemoveDeathRecipient(it->second);
1026 recipientMap_.erase(it);
1027 return;
1028 }
1029 }
1030
OnCallBackDied(const wptr<IRemoteObject> & remote)1031 void AbilityConnectManager::OnCallBackDied(const wptr<IRemoteObject> &remote)
1032 {
1033 auto object = remote.promote();
1034 CHECK_POINTER(object);
1035 if (eventHandler_) {
1036 auto task = [object, connectManager = shared_from_this()]() { connectManager->HandleCallBackDiedTask(object); };
1037 eventHandler_->PostTask(task, TASK_ON_CALLBACK_DIED);
1038 }
1039 }
1040
HandleCallBackDiedTask(const sptr<IRemoteObject> & connect)1041 void AbilityConnectManager::HandleCallBackDiedTask(const sptr<IRemoteObject> &connect)
1042 {
1043 HILOG_INFO("Handle call back died task.");
1044 std::lock_guard<std::recursive_mutex> guard(Lock_);
1045 CHECK_POINTER(connect);
1046 auto it = connectMap_.find(connect);
1047 if (it != connectMap_.end()) {
1048 ConnectListType connectRecordList = it->second;
1049 for (auto &connRecord : connectRecordList) {
1050 connRecord->ClearConnCallBack();
1051 }
1052 } else {
1053 HILOG_INFO("Died object can't find from conn map.");
1054 return;
1055 }
1056 sptr<IAbilityConnection> object = iface_cast<IAbilityConnection>(connect);
1057 DisconnectAbilityLocked(object);
1058 }
1059
OnAbilityDied(const std::shared_ptr<AbilityRecord> & abilityRecord,int32_t currentUserId)1060 void AbilityConnectManager::OnAbilityDied(const std::shared_ptr<AbilityRecord> &abilityRecord, int32_t currentUserId)
1061 {
1062 HILOG_INFO("On ability died.");
1063 CHECK_POINTER(abilityRecord);
1064 if (abilityRecord->GetAbilityInfo().type != AbilityType::SERVICE &&
1065 abilityRecord->GetAbilityInfo().type != AbilityType::EXTENSION) {
1066 HILOG_DEBUG("Ability type is not service.");
1067 return;
1068 }
1069 if (eventHandler_) {
1070 auto task = [abilityRecord, connectManager = shared_from_this(), currentUserId]() {
1071 connectManager->HandleAbilityDiedTask(abilityRecord, currentUserId);
1072 };
1073 eventHandler_->PostTask(task, TASK_ON_ABILITY_DIED);
1074 }
1075 }
1076
OnTimeOut(uint32_t msgId,int64_t eventId)1077 void AbilityConnectManager::OnTimeOut(uint32_t msgId, int64_t eventId)
1078 {
1079 HILOG_DEBUG("On timeout, msgId is %{public}d", msgId);
1080 std::lock_guard<std::recursive_mutex> guard(Lock_);
1081 auto abilityRecord = GetAbilityRecordByEventId(eventId);
1082 if (abilityRecord == nullptr) {
1083 HILOG_ERROR("AbilityConnectManager on time out event: ability record is nullptr.");
1084 return;
1085 }
1086 HILOG_DEBUG("Ability timeout ,msg:%{public}d,name:%{public}s", msgId, abilityRecord->GetAbilityInfo().name.c_str());
1087
1088 switch (msgId) {
1089 case AbilityManagerService::INACTIVE_TIMEOUT_MSG:
1090 HandleInactiveTimeout(abilityRecord);
1091 break;
1092 default:
1093 break;
1094 }
1095 }
1096
HandleInactiveTimeout(const std::shared_ptr<AbilityRecord> & ability)1097 void AbilityConnectManager::HandleInactiveTimeout(const std::shared_ptr<AbilityRecord> &ability)
1098 {
1099 HILOG_DEBUG("HandleInactiveTimeout start");
1100 std::lock_guard<std::recursive_mutex> guard(Lock_);
1101 CHECK_POINTER(ability);
1102 if (ability->GetAbilityInfo().name == AbilityConfig::LAUNCHER_ABILITY_NAME) {
1103 HILOG_DEBUG("Handle root launcher inactive timeout.");
1104 // terminate the timeout root launcher.
1105 DelayedSingleton<AppScheduler>::GetInstance()->AttachTimeOut(ability->GetToken());
1106 }
1107
1108 HILOG_DEBUG("HandleInactiveTimeout end");
1109 }
1110
IsAbilityNeedKeepAlive(const std::shared_ptr<AbilityRecord> & abilityRecord)1111 bool AbilityConnectManager::IsAbilityNeedKeepAlive(const std::shared_ptr<AbilityRecord> &abilityRecord)
1112 {
1113 auto bms = AbilityUtil::GetBundleManager();
1114 CHECK_POINTER_AND_RETURN(bms, false);
1115 std::vector<AppExecFwk::BundleInfo> bundleInfos;
1116 bool getBundleInfos = bms->GetBundleInfos(OHOS::AppExecFwk::GET_BUNDLE_DEFAULT, bundleInfos, USER_ID_NO_HEAD);
1117 if (!getBundleInfos) {
1118 HILOG_ERROR("Handle ability died task, get bundle infos failed");
1119 return false;
1120 }
1121
1122 auto CheckIsAbilityNeedKeepAlive = [](const AppExecFwk::HapModuleInfo &hapModuleInfo,
1123 const std::string processName, std::string &mainElement) {
1124 if (!hapModuleInfo.isModuleJson) {
1125 // old application model
1126 mainElement = hapModuleInfo.mainAbility;
1127 for (auto abilityInfo : hapModuleInfo.abilityInfos) {
1128 if (abilityInfo.process == processName && abilityInfo.name == mainElement) {
1129 return true;
1130 }
1131 }
1132 return false;
1133 }
1134
1135 // new application model
1136 if (hapModuleInfo.process == processName) {
1137 mainElement = hapModuleInfo.mainElementName;
1138 return true;
1139 }
1140 return false;
1141 };
1142
1143 auto GetKeepAliveAbilities = [&](std::vector<std::pair<std::string, std::string>> &keepAliveAbilities) {
1144 for (size_t i = 0; i < bundleInfos.size(); i++) {
1145 std::string processName = bundleInfos[i].applicationInfo.process;
1146 if (!bundleInfos[i].isKeepAlive || processName.empty()) {
1147 continue;
1148 }
1149 std::string bundleName = bundleInfos[i].name;
1150 for (auto hapModuleInfo : bundleInfos[i].hapModuleInfos) {
1151 std::string mainElement;
1152 if (CheckIsAbilityNeedKeepAlive(hapModuleInfo, processName, mainElement) && !mainElement.empty()) {
1153 keepAliveAbilities.push_back(std::make_pair(bundleName, mainElement));
1154 }
1155 }
1156 }
1157 };
1158
1159 auto findKeepAliveAbility = [abilityRecord](const std::pair<std::string, std::string> &keepAlivePair) {
1160 return ((abilityRecord->GetAbilityInfo().bundleName == keepAlivePair.first &&
1161 abilityRecord->GetAbilityInfo().name == keepAlivePair.second) ||
1162 abilityRecord->GetAbilityInfo().name == AbilityConfig::SYSTEM_UI_ABILITY_NAME ||
1163 abilityRecord->GetAbilityInfo().name == AbilityConfig::LAUNCHER_ABILITY_NAME);
1164 };
1165
1166 std::vector<std::pair<std::string, std::string>> keepAliveAbilities;
1167 GetKeepAliveAbilities(keepAliveAbilities);
1168 auto findIter = find_if(keepAliveAbilities.begin(), keepAliveAbilities.end(), findKeepAliveAbility);
1169 if (findIter != keepAliveAbilities.end()) {
1170 abilityRecord->SetKeepAlive();
1171 return true;
1172 }
1173 return false;
1174 }
1175
HandleAbilityDiedTask(const std::shared_ptr<AbilityRecord> & abilityRecord,int32_t currentUserId)1176 void AbilityConnectManager::HandleAbilityDiedTask(
1177 const std::shared_ptr<AbilityRecord> &abilityRecord, int32_t currentUserId)
1178 {
1179 HILOG_INFO("Handle ability died task.");
1180 std::lock_guard<std::recursive_mutex> guard(Lock_);
1181 CHECK_POINTER(abilityRecord);
1182 ConnectListType connlist = abilityRecord->GetConnectRecordList();
1183 for (auto &connectRecord : connlist) {
1184 HILOG_WARN("This record complete disconnect directly. recordId:%{public}d", connectRecord->GetRecordId());
1185 connectRecord->CompleteDisconnect(ERR_OK, true);
1186 abilityRecord->RemoveConnectRecordFromList(connectRecord);
1187 RemoveConnectionRecordFromMap(connectRecord);
1188 }
1189
1190 if (abilityRecord->IsTerminating()) {
1191 HILOG_INFO("Handle extension DiedByTerminating.");
1192 RemoveServiceAbility(abilityRecord);
1193 if (IsAbilityNeedKeepAlive(abilityRecord)) {
1194 HILOG_INFO("restart ability: %{public}s", abilityRecord->GetAbilityInfo().name.c_str());
1195 RestartAbility(abilityRecord, currentUserId);
1196 }
1197 return;
1198 }
1199
1200 if (GetExtensionByTokenFromSeriveMap(abilityRecord->GetToken()) == nullptr) {
1201 HILOG_ERROR("Died ability record is not exist in service map.");
1202 return;
1203 }
1204
1205 MoveToTerminatingMap(abilityRecord);
1206 RemoveServiceAbility(abilityRecord);
1207 if (IsAbilityNeedKeepAlive(abilityRecord)) {
1208 HILOG_INFO("restart ability: %{public}s", abilityRecord->GetAbilityInfo().name.c_str());
1209 RestartAbility(abilityRecord, currentUserId);
1210 }
1211 }
1212
RestartAbility(const std::shared_ptr<AbilityRecord> & abilityRecord,int32_t currentUserId)1213 void AbilityConnectManager::RestartAbility(const std::shared_ptr<AbilityRecord> &abilityRecord, int32_t currentUserId)
1214 {
1215 HILOG_INFO("Restart ability");
1216 AbilityRequest requestInfo;
1217 requestInfo.want = abilityRecord->GetWant();
1218 requestInfo.abilityInfo = abilityRecord->GetAbilityInfo();
1219 requestInfo.appInfo = abilityRecord->GetApplicationInfo();
1220 requestInfo.restartTime = abilityRecord->GetRestartTime();
1221 requestInfo.restart = true;
1222 abilityRecord->SetRestarting(true);
1223
1224 if (currentUserId != userId_ &&
1225 abilityRecord->GetAbilityInfo().name == AbilityConfig::LAUNCHER_ABILITY_NAME) {
1226 HILOG_WARN("delay restart root launcher until switch user.");
1227 return;
1228 }
1229
1230 if (abilityRecord->GetAbilityInfo().name == AbilityConfig::LAUNCHER_ABILITY_NAME) {
1231 requestInfo.restartCount = abilityRecord->GetRestartCount();
1232 HILOG_DEBUG("restart root launcher, number:%{public}d", requestInfo.restartCount);
1233 StartAbilityLocked(requestInfo);
1234 return;
1235 }
1236
1237 // restart other resident ability
1238 if (abilityRecord->CanRestartResident()) {
1239 requestInfo.restartCount = abilityRecord->GetRestartCount();
1240 requestInfo.restartTime = AbilityUtil::SystemTimeMillis();
1241 StartAbilityLocked(requestInfo);
1242 } else {
1243 auto findRestartResidentTask = [requestInfo](const AbilityRequest &abilityRequest) {
1244 return (requestInfo.want.GetElement().GetBundleName() == abilityRequest.want.GetElement().GetBundleName() &&
1245 requestInfo.want.GetElement().GetModuleName() == abilityRequest.want.GetElement().GetModuleName() &&
1246 requestInfo.want.GetElement().GetAbilityName() == abilityRequest.want.GetElement().GetAbilityName());
1247 };
1248 auto findIter = find_if(restartResidentTaskList_.begin(), restartResidentTaskList_.end(),
1249 findRestartResidentTask);
1250 if (findIter != restartResidentTaskList_.end()) {
1251 HILOG_WARN("The restart task has been registered.");
1252 return;
1253 }
1254 restartResidentTaskList_.emplace_back(requestInfo);
1255 PostRestartResidentTask(requestInfo);
1256 }
1257 }
1258
DumpState(std::vector<std::string> & info,bool isClient,const std::string & args) const1259 void AbilityConnectManager::DumpState(std::vector<std::string> &info, bool isClient, const std::string &args) const
1260 {
1261 HILOG_INFO("DumpState args:%{public}s.", args.c_str());
1262 if (!args.empty()) {
1263 auto it = std::find_if(serviceMap_.begin(), serviceMap_.end(), [&args](const auto &service) {
1264 return service.first.compare(args) == 0;
1265 });
1266 if (it != serviceMap_.end()) {
1267 info.emplace_back("uri [ " + it->first + " ]");
1268 it->second->DumpService(info, isClient);
1269 } else {
1270 info.emplace_back(args + ": Nothing to dump.");
1271 }
1272 } else {
1273 auto abilityMgr = DelayedSingleton<AbilityManagerService>::GetInstance();
1274 info.emplace_back(" ExtensionRecords:");
1275 for (auto &&service : serviceMap_) {
1276 info.emplace_back(" uri [" + service.first + "]");
1277 service.second->DumpService(info, isClient);
1278 }
1279 }
1280 }
1281
DumpStateByUri(std::vector<std::string> & info,bool isClient,const std::string & args,std::vector<std::string> & params) const1282 void AbilityConnectManager::DumpStateByUri(std::vector<std::string> &info, bool isClient, const std::string &args,
1283 std::vector<std::string> ¶ms) const
1284 {
1285 HILOG_INFO("DumpState args:%{public}s, params size: %{public}zu", args.c_str(), params.size());
1286 auto it = std::find_if(serviceMap_.begin(), serviceMap_.end(), [&args](const auto &service) {
1287 return service.first.compare(args) == 0;
1288 });
1289 if (it != serviceMap_.end()) {
1290 info.emplace_back("uri [ " + it->first + " ]");
1291 it->second->DumpService(info, params, isClient);
1292 } else {
1293 info.emplace_back(args + ": Nothing to dump.");
1294 }
1295 }
1296
GetExtensionRunningInfos(int upperLimit,std::vector<ExtensionRunningInfo> & info,const int32_t userId,bool isPerm)1297 void AbilityConnectManager::GetExtensionRunningInfos(int upperLimit, std::vector<ExtensionRunningInfo> &info,
1298 const int32_t userId, bool isPerm)
1299 {
1300 HILOG_INFO("Get extension running info.");
1301 std::lock_guard<std::recursive_mutex> guard(Lock_);
1302 auto mgr = shared_from_this();
1303 auto queryInfo = [&info, upperLimit, userId, isPerm, mgr](ServiceMapType::reference service) {
1304 if (static_cast<int>(info.size()) >= upperLimit) {
1305 return;
1306 }
1307 auto abilityRecord = service.second;
1308 CHECK_POINTER(abilityRecord);
1309
1310 if (isPerm) {
1311 mgr->GetExtensionRunningInfo(abilityRecord, userId, info);
1312 } else {
1313 auto callingTokenId = IPCSkeleton::GetCallingTokenID();
1314 auto tokenID = abilityRecord->GetApplicationInfo().accessTokenId;
1315 if (callingTokenId == tokenID) {
1316 mgr->GetExtensionRunningInfo(abilityRecord, userId, info);
1317 }
1318 }
1319 };
1320 std::for_each(serviceMap_.begin(), serviceMap_.end(), queryInfo);
1321 }
1322
GetAbilityRunningInfos(std::vector<AbilityRunningInfo> & info,bool isPerm)1323 void AbilityConnectManager::GetAbilityRunningInfos(std::vector<AbilityRunningInfo> &info, bool isPerm)
1324 {
1325 HILOG_INFO("Query running ability infos.");
1326 std::lock_guard<std::recursive_mutex> guard(Lock_);
1327
1328 auto queryInfo = [&info, isPerm](ServiceMapType::reference service) {
1329 auto abilityRecord = service.second;
1330 CHECK_POINTER(abilityRecord);
1331
1332 if (isPerm) {
1333 DelayedSingleton<AbilityManagerService>::GetInstance()->GetAbilityRunningInfo(info, abilityRecord);
1334 } else {
1335 auto callingTokenId = IPCSkeleton::GetCallingTokenID();
1336 auto tokenID = abilityRecord->GetApplicationInfo().accessTokenId;
1337 if (callingTokenId == tokenID) {
1338 DelayedSingleton<AbilityManagerService>::GetInstance()->GetAbilityRunningInfo(info, abilityRecord);
1339 }
1340 }
1341 };
1342
1343 std::for_each(serviceMap_.begin(), serviceMap_.end(), queryInfo);
1344 }
1345
GetExtensionRunningInfo(std::shared_ptr<AbilityRecord> & abilityRecord,const int32_t userId,std::vector<ExtensionRunningInfo> & info)1346 void AbilityConnectManager::GetExtensionRunningInfo(std::shared_ptr<AbilityRecord> &abilityRecord, const int32_t userId,
1347 std::vector<ExtensionRunningInfo> &info)
1348 {
1349 ExtensionRunningInfo extensionInfo;
1350 AppExecFwk::RunningProcessInfo processInfo;
1351 extensionInfo.extension = abilityRecord->GetWant().GetElement();
1352 auto bms = AbilityUtil::GetBundleManager();
1353 CHECK_POINTER(bms);
1354 std::vector<AppExecFwk::ExtensionAbilityInfo> extensionInfos;
1355 bool queryResult = IN_PROCESS_CALL(bms->QueryExtensionAbilityInfos(abilityRecord->GetWant(),
1356 AppExecFwk::AbilityInfoFlag::GET_ABILITY_INFO_WITH_APPLICATION, userId, extensionInfos));
1357 if (queryResult) {
1358 HILOG_INFO("Query Extension Ability Infos Success.");
1359 auto abilityInfo = abilityRecord->GetAbilityInfo();
1360 auto isExist = [&abilityInfo](const AppExecFwk::ExtensionAbilityInfo &extensionInfo) {
1361 HILOG_INFO("%{public}s, %{public}s", extensionInfo.bundleName.c_str(), extensionInfo.name.c_str());
1362 return extensionInfo.bundleName == abilityInfo.bundleName && extensionInfo.name == abilityInfo.name
1363 && extensionInfo.applicationInfo.uid == abilityInfo.applicationInfo.uid;
1364 };
1365 auto infoIter = std::find_if(extensionInfos.begin(), extensionInfos.end(), isExist);
1366 if (infoIter != extensionInfos.end()) {
1367 HILOG_INFO("Get target success.");
1368 extensionInfo.type = (*infoIter).type;
1369 }
1370 }
1371 DelayedSingleton<AppScheduler>::GetInstance()->
1372 GetRunningProcessInfoByToken(abilityRecord->GetToken(), processInfo);
1373 extensionInfo.pid = processInfo.pid_;
1374 extensionInfo.uid = processInfo.uid_;
1375 extensionInfo.processName = processInfo.processName_;
1376 extensionInfo.startTime = abilityRecord->GetStartTime();
1377 ConnectListType connectRecordList = abilityRecord->GetConnectRecordList();
1378 for (auto &connectRecord : connectRecordList) {
1379 if (connectRecord == nullptr) {
1380 HILOG_DEBUG("connectRecord is nullptr.");
1381 continue;
1382 }
1383 auto callerAbilityRecord = Token::GetAbilityRecordByToken(connectRecord->GetToken());
1384 if (callerAbilityRecord == nullptr) {
1385 HILOG_DEBUG("callerAbilityRecord is nullptr.");
1386 continue;
1387 }
1388 std::string package = callerAbilityRecord->GetAbilityInfo().bundleName;
1389 extensionInfo.clientPackage.emplace_back(package);
1390 }
1391 info.emplace_back(extensionInfo);
1392 }
1393
StopAllExtensions()1394 void AbilityConnectManager::StopAllExtensions()
1395 {
1396 HILOG_INFO("StopAllExtensions begin.");
1397 std::lock_guard<std::recursive_mutex> guard(Lock_);
1398 for (auto it = serviceMap_.begin(); it != serviceMap_.end();) {
1399 auto targetExtension = it->second;
1400 if (targetExtension != nullptr && targetExtension->GetAbilityInfo().type == AbilityType::EXTENSION) {
1401 terminatingExtensionMap_.emplace(it->first, it->second);
1402 serviceMap_.erase(it++);
1403 TerminateAbilityLocked(targetExtension->GetToken());
1404 } else {
1405 it++;
1406 }
1407 }
1408 HILOG_INFO("StopAllExtensions end.");
1409 }
1410
MoveToTerminatingMap(const std::shared_ptr<AbilityRecord> & abilityRecord)1411 void AbilityConnectManager::MoveToTerminatingMap(const std::shared_ptr<AbilityRecord>& abilityRecord)
1412 {
1413 CHECK_POINTER(abilityRecord);
1414 auto& abilityInfo = abilityRecord->GetAbilityInfo();
1415 AppExecFwk::ElementName element(abilityInfo.deviceId, abilityInfo.bundleName, abilityInfo.name,
1416 abilityInfo.moduleName);
1417 terminatingExtensionMap_.emplace(element.GetURI(), abilityRecord);
1418 serviceMap_.erase(element.GetURI());
1419 }
1420 } // namespace AAFwk
1421 } // namespace OHOS
1422