1 /*
2  * Copyright (c) 2023-2024 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_auto_startup_service.h"
17 
18 #include "ability_auto_startup_data_manager.h"
19 #include "ability_manager_service.h"
20 #include "auto_startup_interface.h"
21 #include "global_constant.h"
22 #include "hilog_tag_wrapper.h"
23 #include "in_process_call_wrapper.h"
24 #include "permission_constants.h"
25 
26 namespace OHOS {
27 namespace AbilityRuntime {
28 using namespace OHOS::AAFwk;
29 namespace {
30 constexpr char PRODUCT_APPBOOT_SETTING_ENABLED[] = "const.product.appboot.setting.enabled";
31 } // namespace
32 
AbilityAutoStartupService()33 AbilityAutoStartupService::AbilityAutoStartupService() {}
34 
~AbilityAutoStartupService()35 AbilityAutoStartupService::~AbilityAutoStartupService() {}
36 
RegisterAutoStartupSystemCallback(const sptr<IRemoteObject> & callback)37 int32_t AbilityAutoStartupService::RegisterAutoStartupSystemCallback(const sptr<IRemoteObject> &callback)
38 {
39     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
40     int32_t code = CheckPermissionForSystem();
41     if (code != ERR_OK) {
42         return code;
43     }
44 
45     {
46         std::lock_guard<std::mutex> lock(autoStartUpMutex_);
47         bool isFound = false;
48         auto item = callbackVector_.begin();
49         while (item != callbackVector_.end()) {
50             if (*item == callback) {
51                 isFound = true;
52                 break;
53             }
54             item++;
55         }
56         if (!isFound) {
57             callbackVector_.emplace_back(callback);
58             SetDeathRecipient(
59                 callback, new (std::nothrow) AbilityAutoStartupService::ClientDeathRecipient(weak_from_this()));
60         } else {
61             TAG_LOGD(AAFwkTag::AUTO_STARTUP, "Callback already exist");
62         }
63     }
64     return ERR_OK;
65 }
66 
UnregisterAutoStartupSystemCallback(const sptr<IRemoteObject> & callback)67 int32_t AbilityAutoStartupService::UnregisterAutoStartupSystemCallback(const sptr<IRemoteObject> &callback)
68 {
69     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
70     int32_t code = CheckPermissionForSystem();
71     if (code != ERR_OK) {
72         return code;
73     }
74 
75     {
76         std::lock_guard<std::mutex> lock(autoStartUpMutex_);
77         bool isFound = false;
78         auto item = callbackVector_.begin();
79         while (item != callbackVector_.end()) {
80             if (*item == callback) {
81                 item = callbackVector_.erase(item);
82                 isFound = true;
83             } else {
84                 item++;
85             }
86         }
87         if (!isFound) {
88             TAG_LOGD(AAFwkTag::AUTO_STARTUP, "Callback not exist");
89         }
90     }
91     return ERR_OK;
92 }
93 
SetApplicationAutoStartup(const AutoStartupInfo & info)94 int32_t AbilityAutoStartupService::SetApplicationAutoStartup(const AutoStartupInfo &info)
95 {
96     TAG_LOGD(AAFwkTag::AUTO_STARTUP,
97         "Called, bundleName: %{public}s, moduleName: %{public}s, abilityName: %{public}s,"
98         " accessTokenId: %{public}s, userId: %{public}d",
99         info.bundleName.c_str(), info.moduleName.c_str(),
100         info.abilityName.c_str(), info.accessTokenId.c_str(), info.userId);
101     int32_t code = CheckPermissionForSystem();
102     if (code != ERR_OK) {
103         return code;
104     }
105 
106     bool isVisible;
107     int32_t userId;
108     std::string abilityTypeName;
109     std::string accessTokenId;
110     if (!GetAbilityData(info, isVisible, abilityTypeName, accessTokenId, userId)) {
111         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Get ability data failed");
112         return INNER_ERR;
113     }
114 
115     if (!isVisible) {
116         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Current ability not visible");
117         return ABILITY_VISIBLE_FALSE_DENY_REQUEST;
118     }
119 
120     AutoStartupInfo fullInfo(info);
121     fullInfo.abilityTypeName = abilityTypeName;
122     fullInfo.userId = userId;
123     fullInfo.accessTokenId = accessTokenId;
124 
125     return InnerSetApplicationAutoStartup(fullInfo);
126 }
127 
InnerSetApplicationAutoStartup(const AutoStartupInfo & info)128 int32_t AbilityAutoStartupService::InnerSetApplicationAutoStartup(const AutoStartupInfo &info)
129 {
130     AutoStartupStatus status =
131         DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->QueryAutoStartupData(info);
132     if (status.code != ERR_OK && status.code != ERR_NAME_NOT_FOUND) {
133         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Query auto startup data failed");
134         return status.code;
135     }
136 
137     int32_t result;
138     if (status.code == ERR_NAME_NOT_FOUND) {
139         TAG_LOGI(AAFwkTag::AUTO_STARTUP, "Not found");
140         result =
141             DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->InsertAutoStartupData(info, true, false);
142         if (result == ERR_OK) {
143             ExecuteCallbacks(true, info);
144         }
145         return result;
146     }
147     if (status.isEdmForce) {
148         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Edm application abnormal");
149         return ERR_EDM_APP_CONTROLLED;
150     }
151     if (!status.isAutoStartup) {
152         result =
153             DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->UpdateAutoStartupData(info, true, false);
154         if (result == ERR_OK) {
155             ExecuteCallbacks(true, info);
156         }
157         return result;
158     }
159     return ERR_ALREADY_EXISTS;
160 }
161 
CancelApplicationAutoStartup(const AutoStartupInfo & info)162 int32_t AbilityAutoStartupService::CancelApplicationAutoStartup(const AutoStartupInfo &info)
163 {
164     TAG_LOGD(AAFwkTag::AUTO_STARTUP,
165         "Called, bundleName: %{public}s, moduleName: %{public}s, abilityName: %{public}s,"
166         " accessTokenId: %{public}s, userId: %{public}d",
167         info.bundleName.c_str(), info.moduleName.c_str(),
168         info.abilityName.c_str(), info.accessTokenId.c_str(), info.userId);
169     int32_t code = CheckPermissionForSystem();
170     if (code != ERR_OK) {
171         return code;
172     }
173 
174     bool isVisible;
175     std::string abilityTypeName;
176     std::string accessTokenId;
177     int32_t userId;
178     if (!GetAbilityData(info, isVisible, abilityTypeName, accessTokenId, userId)) {
179         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Get ability data failed");
180         return INNER_ERR;
181     }
182 
183     if (!isVisible) {
184         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Current ability not visible");
185         return ABILITY_VISIBLE_FALSE_DENY_REQUEST;
186     }
187 
188     AutoStartupInfo fullInfo(info);
189     fullInfo.abilityTypeName = abilityTypeName;
190     fullInfo.accessTokenId = accessTokenId;
191     fullInfo.userId = userId;
192 
193     return InnerCancelApplicationAutoStartup(fullInfo);
194 }
195 
InnerCancelApplicationAutoStartup(const AutoStartupInfo & info)196 int32_t AbilityAutoStartupService::InnerCancelApplicationAutoStartup(const AutoStartupInfo &info)
197 {
198     AutoStartupStatus status =
199         DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->QueryAutoStartupData(info);
200     if (status.code != ERR_OK) {
201         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Query auto startup data failed");
202         return status.code;
203     }
204 
205     if (status.isEdmForce) {
206         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Edm application abnormal");
207         return ERR_EDM_APP_CONTROLLED;
208     }
209 
210     if (status.isAutoStartup) {
211         int32_t result = DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->DeleteAutoStartupData(info);
212         if (result == ERR_OK) {
213             ExecuteCallbacks(false, info);
214         }
215         return result;
216     }
217     return ERR_OK;
218 }
219 
QueryAllAutoStartupApplications(std::vector<AutoStartupInfo> & infoList,int32_t userId)220 int32_t AbilityAutoStartupService::QueryAllAutoStartupApplications(std::vector<AutoStartupInfo> &infoList,
221     int32_t userId)
222 {
223     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
224     int32_t code = CheckPermissionForEDM();
225     code = code == ERR_OK ? code : CheckPermissionForSystem();
226     if (code != ERR_OK) {
227         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Permission verification failed");
228         return code;
229     }
230 
231     return DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->QueryAllAutoStartupApplications(infoList,
232         userId);
233 }
234 
QueryAllAutoStartupApplicationsWithoutPermission(std::vector<AutoStartupInfo> & infoList,int32_t userId)235 int32_t AbilityAutoStartupService::QueryAllAutoStartupApplicationsWithoutPermission(
236     std::vector<AutoStartupInfo> &infoList, int32_t userId)
237 {
238     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
239     if (!system::GetBoolParameter(PRODUCT_APPBOOT_SETTING_ENABLED, false)) {
240         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Disabled Product config");
241         return ERR_NOT_SUPPORTED_PRODUCT_TYPE;
242     }
243 
244     return DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->QueryAllAutoStartupApplications(infoList,
245         userId);
246 }
247 
DeleteAutoStartupData(const std::string & bundleName,const int32_t accessTokenId)248 int32_t AbilityAutoStartupService::DeleteAutoStartupData(const std::string &bundleName, const int32_t accessTokenId)
249 {
250     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
251     return DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->DeleteAutoStartupData(
252         bundleName, accessTokenId);
253 }
254 
CheckAutoStartupData(const std::string & bundleName,int32_t uid)255 int32_t AbilityAutoStartupService::CheckAutoStartupData(const std::string &bundleName, int32_t uid)
256 {
257     int32_t userId;
258     int32_t appIndex = 0;
259     AppExecFwk::BundleInfo bundleInfo;
260     if (!GetBundleInfo(bundleName, bundleInfo, uid, userId, appIndex)) {
261         return INNER_ERR;
262     }
263     auto tokenId = bundleInfo.applicationInfo.accessTokenId;
264     std::string accessTokenIdStr = std::to_string(tokenId);
265     std::vector<AutoStartupInfo> infoList;
266     int32_t result = DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->GetCurrentAppAutoStartupData(
267         bundleName, infoList, accessTokenIdStr);
268     if (result != ERR_OK) {
269         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Get auto startup data failed");
270         return result;
271     }
272     if (infoList.size() == 0) {
273         return ERR_OK;
274     }
275 
276     bool isFound = false;
277     for (auto info : infoList) {
278         for (auto abilityInfo : bundleInfo.abilityInfos) {
279             if ((abilityInfo.bundleName == info.bundleName) && (abilityInfo.name == info.abilityName) &&
280                 (info.moduleName.empty() || (abilityInfo.moduleName == info.moduleName))) {
281                 isFound = true;
282                 break;
283             }
284         }
285     }
286 
287     if (!isFound) {
288         TAG_LOGD(AAFwkTag::AUTO_STARTUP, "Current bundleName not found");
289         return DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->DeleteAutoStartupData(bundleName,
290             tokenId);
291     }
292     return ERR_OK;
293 }
294 
ExecuteCallbacks(bool isCallOn,const AutoStartupInfo & info)295 void AbilityAutoStartupService::ExecuteCallbacks(bool isCallOn, const AutoStartupInfo &info)
296 {
297     TAG_LOGD(AAFwkTag::AUTO_STARTUP,
298         "Called, bundleName: %{public}s, moduleName: %{public}s, abilityName: %{public}s,"
299         " accessTokenId: %{public}s, userId: %{public}d",
300         info.bundleName.c_str(), info.moduleName.c_str(),
301         info.abilityName.c_str(), info.accessTokenId.c_str(), info.userId);
302     for (auto item : callbackVector_) {
303         auto remoteSystemCallback = iface_cast<IAutoStartupCallBack>(item);
304         if (remoteSystemCallback != nullptr) {
305             if (isCallOn) {
306                 remoteSystemCallback->OnAutoStartupOn(info);
307             } else {
308                 remoteSystemCallback->OnAutoStartupOff(info);
309             }
310         }
311     }
312 
313     auto it = callbackMaps_.find(info.bundleName);
314     if (it != callbackMaps_.end()) {
315         auto remoteCallback = iface_cast<IAutoStartupCallBack>(it->second);
316         if (remoteCallback != nullptr) {
317             if (isCallOn) {
318                 remoteCallback->OnAutoStartupOn(info);
319             } else {
320                 remoteCallback->OnAutoStartupOff(info);
321             }
322         }
323     }
324 }
325 
SetDeathRecipient(const sptr<IRemoteObject> & callback,const sptr<IRemoteObject::DeathRecipient> & deathRecipient)326 void AbilityAutoStartupService::SetDeathRecipient(
327     const sptr<IRemoteObject> &callback, const sptr<IRemoteObject::DeathRecipient> &deathRecipient)
328 {
329     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
330     if (callback == nullptr || deathRecipient == nullptr) {
331         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "CallerToken or deathRecipient empty");
332         return;
333     }
334     std::lock_guard<std::mutex> lock(deathRecipientsMutex_);
335     auto iter = deathRecipients_.find(callback);
336     if (iter == deathRecipients_.end()) {
337         deathRecipients_.emplace(callback, deathRecipient);
338         callback->AddDeathRecipient(deathRecipient);
339         return;
340     }
341     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "DeathRecipient added");
342 }
343 
CleanResource(const wptr<IRemoteObject> & remote)344 void AbilityAutoStartupService::CleanResource(const wptr<IRemoteObject> &remote)
345 {
346     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
347     auto object = remote.promote();
348     if (object == nullptr) {
349         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "null remote obj");
350         return;
351     }
352 
353     // Clean the callbackVector_ and callbackMaps_.
354     {
355         std::lock_guard<std::mutex> lock(autoStartUpMutex_);
356         for (auto item = callbackVector_.begin(); item != callbackVector_.end();) {
357             if (*item == object) {
358                 item = callbackVector_.erase(item);
359             } else {
360                 item++;
361             }
362         }
363 
364         for (auto it = callbackMaps_.begin(); it != callbackMaps_.end();) {
365             const auto &callback = it->second;
366             if (callback == object) {
367                 it = callbackMaps_.erase(it);
368             } else {
369                 it++;
370             }
371         }
372     }
373     {
374         std::lock_guard<std::mutex> deathLock(deathRecipientsMutex_);
375         auto iter = deathRecipients_.find(object);
376         if (iter != deathRecipients_.end()) {
377             auto deathRecipient = iter->second;
378             deathRecipients_.erase(iter);
379             object->RemoveDeathRecipient(deathRecipient);
380         }
381     }
382 }
383 
ClientDeathRecipient(const std::weak_ptr<AbilityAutoStartupService> & weakPtr)384 AbilityAutoStartupService::ClientDeathRecipient::ClientDeathRecipient(
385     const std::weak_ptr<AbilityAutoStartupService> &weakPtr)
386 {
387     weakPtr_ = weakPtr;
388 }
389 
OnRemoteDied(const wptr<IRemoteObject> & remote)390 void AbilityAutoStartupService::ClientDeathRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
391 {
392     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
393     auto abilityAutoStartupService = weakPtr_.lock();
394     if (abilityAutoStartupService == nullptr) {
395         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "null abilityAutoStartupService");
396         return;
397     }
398     abilityAutoStartupService->CleanResource(remote);
399 }
400 
GetSelfApplicationBundleName()401 std::string AbilityAutoStartupService::GetSelfApplicationBundleName()
402 {
403     auto bundleMgrClient = GetBundleMgrClient();
404     if (bundleMgrClient == nullptr) {
405         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Get BundleMgrClient failed");
406         return "";
407     }
408 
409     std::string bundleName;
410     int32_t callerUid = IPCSkeleton::GetCallingUid();
411     if (IN_PROCESS_CALL(bundleMgrClient->GetNameForUid(callerUid, bundleName)) != ERR_OK) {
412         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Get Bundle Name failed");
413         return "";
414     }
415     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "Get bundle name: %{public}s", bundleName.c_str());
416     return bundleName;
417 }
418 
CheckSelfApplication(const std::string & bundleName)419 bool AbilityAutoStartupService::CheckSelfApplication(const std::string &bundleName)
420 {
421     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "Called, bundleName: %{public}s", bundleName.c_str());
422     return GetSelfApplicationBundleName() == bundleName ? true : false;
423 }
424 
GetBundleInfo(const std::string & bundleName,AppExecFwk::BundleInfo & bundleInfo,int32_t uid,int32_t & userId,int32_t appIndex)425 bool AbilityAutoStartupService::GetBundleInfo(const std::string &bundleName,
426     AppExecFwk::BundleInfo &bundleInfo, int32_t uid, int32_t &userId, int32_t appIndex)
427 {
428     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
429 
430     if (uid == -1) {
431         userId = IPCSkeleton::GetCallingUid() / AppExecFwk::Constants::BASE_USER_RANGE;
432     } else {
433         userId = uid / AppExecFwk::Constants::BASE_USER_RANGE;
434     }
435     if (userId == 0) {
436         auto abilityMgr = DelayedSingleton<AbilityManagerService>::GetInstance();
437         if (abilityMgr == nullptr) {
438             TAG_LOGE(AAFwkTag::AUTO_STARTUP, "null abilityMgr");
439             return false;
440         }
441         userId = abilityMgr->GetUserId();
442     }
443     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "userId: %{public}d", userId);
444     auto bundleMgrHelper = DelayedSingleton<AppExecFwk::BundleMgrHelper>::GetInstance();
445     if (bundleMgrHelper == nullptr) {
446         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "null bundleMgrHelper");
447         return false;
448     }
449     if (appIndex == 0) {
450         auto flags =
451             AppExecFwk::BundleFlag::GET_BUNDLE_WITH_ABILITIES | AppExecFwk::BundleFlag::GET_BUNDLE_WITH_EXTENSION_INFO;
452             if (!IN_PROCESS_CALL(bundleMgrHelper->GetBundleInfo(
453                 bundleName, static_cast<AppExecFwk::BundleFlag>(flags), bundleInfo, userId))) {
454                 TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Get bundle info failed");
455                 return false;
456             }
457     } else if (appIndex <= GlobalConstant::MAX_APP_CLONE_INDEX) {
458         auto bundleFlag = static_cast<int32_t>(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_APPLICATION) +
459             static_cast<int32_t>(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_ABILITY) +
460             static_cast<int32_t>(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_EXTENSION_ABILITY) +
461             static_cast<int32_t>(AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_HAP_MODULE);
462         auto bundleMgrResult = IN_PROCESS_CALL(
463             bundleMgrHelper->GetCloneBundleInfo(bundleName, bundleFlag, appIndex, bundleInfo, userId));
464             if (bundleMgrResult != ERR_OK) {
465                 TAG_LOGE(AAFwkTag::AUTO_STARTUP, "error bundleMgrResult");
466                 return false;
467             }
468     } else {
469             if (!IN_PROCESS_CALL(bundleMgrHelper->GetSandboxBundleInfo(bundleName, appIndex, userId, bundleInfo))) {
470                 TAG_LOGE(AAFwkTag::AUTO_STARTUP, "GetSandboxBundleInfo failed");
471                 return false;
472             }
473     }
474     return true;
475 }
476 
GetAbilityData(const AutoStartupInfo & info,bool & isVisible,std::string & abilityTypeName,std::string & accessTokenId,int32_t & userId)477 bool AbilityAutoStartupService::GetAbilityData(const AutoStartupInfo &info, bool &isVisible,
478     std::string &abilityTypeName, std::string &accessTokenId, int32_t &userId)
479 {
480     TAG_LOGD(AAFwkTag::AUTO_STARTUP,
481         "bundleName: %{public}s, moduleName: %{public}s, abilityName: %{public}s,"
482         " accessTokenId: %{public}s, userId: %{public}d",
483         info.bundleName.c_str(), info.moduleName.c_str(),
484         info.abilityName.c_str(), info.accessTokenId.c_str(), info.userId);
485     AppExecFwk::BundleInfo bundleInfo;
486     int32_t currentUserId;
487     int32_t uid = bundleInfo.applicationInfo.uid;
488     if (!GetBundleInfo(info.bundleName, bundleInfo, uid, currentUserId, info.appCloneIndex)) {
489         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Failed to GetBundleInfo.");
490         return false;
491     }
492     userId = currentUserId;
493     auto accessTokenIdStr = bundleInfo.applicationInfo.accessTokenId;
494     accessTokenId = std::to_string(accessTokenIdStr);
495     for (const auto& hapModuleInfo : bundleInfo.hapModuleInfos) {
496         for (const auto& abilityInfo : hapModuleInfo.abilityInfos) {
497             if ((abilityInfo.bundleName == info.bundleName) && (abilityInfo.name == info.abilityName) &&
498                 (info.moduleName.empty() || (abilityInfo.moduleName == info.moduleName))) {
499                 isVisible = abilityInfo.visible;
500                 abilityTypeName = GetAbilityTypeName(abilityInfo);
501                 TAG_LOGD(AAFwkTag::AUTO_STARTUP, "Get ability info success");
502                 return true;
503             }
504         }
505     }
506 
507     for (auto extensionInfo : bundleInfo.extensionInfos) {
508         if ((extensionInfo.bundleName == info.bundleName) && (extensionInfo.name == info.abilityName)) {
509             if (info.moduleName.empty() || (extensionInfo.moduleName == info.moduleName)) {
510                 isVisible = extensionInfo.visible;
511                 abilityTypeName = GetExtensionTypeName(extensionInfo);
512                 TAG_LOGD(AAFwkTag::AUTO_STARTUP, "Get extension info success");
513                 return true;
514             }
515         }
516     }
517     return false;
518 }
519 
GetAbilityTypeName(AppExecFwk::AbilityInfo abilityInfo)520 std::string AbilityAutoStartupService::GetAbilityTypeName(AppExecFwk::AbilityInfo abilityInfo)
521 {
522     std::string abilityTypeName;
523     if (abilityInfo.type == AppExecFwk::AbilityType::PAGE) {
524         abilityTypeName = "UIAbility";
525     }
526     return abilityTypeName;
527 }
528 
GetExtensionTypeName(AppExecFwk::ExtensionAbilityInfo extensionInfo)529 std::string AbilityAutoStartupService::GetExtensionTypeName(AppExecFwk::ExtensionAbilityInfo extensionInfo)
530 {
531     std::string abilityTypeName;
532     if (extensionInfo.type == AppExecFwk::ExtensionAbilityType::SERVICE) {
533         abilityTypeName = "ServiceExtension";
534     }
535     return abilityTypeName;
536 }
537 
GetBundleMgrClient()538 std::shared_ptr<AppExecFwk::BundleMgrClient> AbilityAutoStartupService::GetBundleMgrClient()
539 {
540     TAG_LOGD(AAFwkTag::AUTO_STARTUP, "called");
541     if (bundleMgrClient_ == nullptr) {
542         bundleMgrClient_ = DelayedSingleton<AppExecFwk::BundleMgrClient>::GetInstance();
543     }
544     return bundleMgrClient_;
545 }
546 
CheckPermissionForSystem()547 int32_t AbilityAutoStartupService::CheckPermissionForSystem()
548 {
549     if (!system::GetBoolParameter(PRODUCT_APPBOOT_SETTING_ENABLED, false)) {
550         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Disabled Product config");
551         return ERR_NOT_SUPPORTED_PRODUCT_TYPE;
552     }
553 
554     if (!PermissionVerification::GetInstance()->JudgeCallerIsAllowedToUseSystemAPI()) {
555         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Caller is not system-app, can not use system-api");
556         return ERR_NOT_SYSTEM_APP;
557     }
558 
559     if (!PermissionVerification::GetInstance()->VerifyCallingPermission(
560         PermissionConstants::PERMISSION_MANAGE_APP_BOOT)) {
561         TAG_LOGE(AAFwkTag::AUTO_STARTUP, " Verify PERMISSION_MANAGE_APP_BOOT failed");
562         return CHECK_PERMISSION_FAILED;
563     }
564 
565     return ERR_OK;
566 }
567 
CheckPermissionForSelf(const std::string & bundleName)568 int32_t AbilityAutoStartupService::CheckPermissionForSelf(const std::string &bundleName)
569 {
570     if (!system::GetBoolParameter(PRODUCT_APPBOOT_SETTING_ENABLED, false)) {
571         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Disabled Product config");
572         return ERR_NOT_SUPPORTED_PRODUCT_TYPE;
573     }
574 
575     if (!CheckSelfApplication(bundleName)) {
576         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Not self application");
577         return ERR_NOT_SELF_APPLICATION;
578     }
579     return ERR_OK;
580 }
581 
GetAbilityInfo(const AutoStartupInfo & info,std::string & abilityTypeName,std::string & accessTokenId,int32_t & userId)582 int32_t AbilityAutoStartupService::GetAbilityInfo(
583     const AutoStartupInfo &info, std::string &abilityTypeName, std::string &accessTokenId, int32_t &userId)
584 {
585     bool isVisible = false;
586     if (!GetAbilityData(info, isVisible, abilityTypeName, accessTokenId, userId)) {
587         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Get ability data failed");
588         return INNER_ERR;
589     }
590 
591     if (!isVisible) {
592         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Current ability not visible");
593         return ABILITY_VISIBLE_FALSE_DENY_REQUEST;
594     }
595 
596     return ERR_OK;
597 }
598 
SetApplicationAutoStartupByEDM(const AutoStartupInfo & info,bool flag)599 int32_t AbilityAutoStartupService::SetApplicationAutoStartupByEDM(const AutoStartupInfo &info, bool flag)
600 {
601     int32_t errorCode = CheckPermissionForEDM();
602     if (errorCode != ERR_OK) {
603         return errorCode;
604     }
605     int32_t userId;
606     std::string typeName;
607     std::string accessTokenId;
608 
609     errorCode = GetAbilityInfo(info, typeName, accessTokenId, userId);
610     if (errorCode != ERR_OK) {
611         return errorCode;
612     }
613     AutoStartupInfo fullInfo(info);
614     fullInfo.abilityTypeName = typeName;
615     fullInfo.accessTokenId = accessTokenId;
616     fullInfo.userId = userId;
617     return InnerApplicationAutoStartupByEDM(fullInfo, true, flag);
618 }
619 
CancelApplicationAutoStartupByEDM(const AutoStartupInfo & info,bool flag)620 int32_t AbilityAutoStartupService::CancelApplicationAutoStartupByEDM(const AutoStartupInfo &info, bool flag)
621 {
622     int32_t errorCode = CheckPermissionForEDM();
623     if (errorCode != ERR_OK) {
624         return errorCode;
625     }
626     int32_t userId;
627     std::string typeName;
628     std::string accessTokenId;
629     errorCode = GetAbilityInfo(info, typeName, accessTokenId, userId);
630     if (errorCode != ERR_OK) {
631         return errorCode;
632     }
633     AutoStartupInfo fullInfo(info);
634     fullInfo.abilityTypeName = typeName;
635     fullInfo.accessTokenId = accessTokenId;
636     fullInfo.userId = userId;
637     return InnerApplicationAutoStartupByEDM(fullInfo, false, flag);
638 }
639 
InnerApplicationAutoStartupByEDM(const AutoStartupInfo & info,bool isSet,bool flag)640 int32_t AbilityAutoStartupService::InnerApplicationAutoStartupByEDM(const AutoStartupInfo &info, bool isSet, bool flag)
641 {
642     TAG_LOGD(AAFwkTag::AUTO_STARTUP,
643         "Called, bundleName: %{public}s, moduleName: %{public}s, abilityName: %{public}s, accessTokenId: %{public}s,"
644         " userId: %{public}d, isSet: %{public}d, flag: %{public}d",
645         info.bundleName.c_str(), info.moduleName.c_str(), info.abilityName.c_str(),
646         info.accessTokenId.c_str(), info.userId, isSet, flag);
647     AutoStartupStatus status =
648         DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->QueryAutoStartupData(info);
649     if (status.code != ERR_OK && status.code != ERR_NAME_NOT_FOUND) {
650         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Query auto startup data failed");
651         return status.code;
652     }
653 
654     int32_t result = ERR_OK;
655     if (status.code == ERR_NAME_NOT_FOUND) {
656         result = DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->InsertAutoStartupData(
657             info, isSet, flag);
658         if (result == ERR_OK && isSet) {
659             ExecuteCallbacks(isSet, info);
660         }
661         return result;
662     }
663 
664     bool isFlag = isSet ? !status.isAutoStartup : status.isAutoStartup;
665     if (isFlag) {
666         result =
667             DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->UpdateAutoStartupData(info, isSet, flag);
668         if (result == ERR_OK) {
669             ExecuteCallbacks(isSet, info);
670         }
671         return result;
672     }
673     if (status.isEdmForce != flag) {
674         result =
675             DelayedSingleton<AbilityAutoStartupDataManager>::GetInstance()->UpdateAutoStartupData(info, isSet, flag);
676         return result;
677     }
678 
679     return result;
680 }
681 
CheckPermissionForEDM()682 int32_t AbilityAutoStartupService::CheckPermissionForEDM()
683 {
684     if (!PermissionVerification::GetInstance()->VerifyCallingPermission(
685         PermissionConstants::PERMISSION_MANAGE_APP_BOOT_INTERNAL)) {
686         TAG_LOGE(AAFwkTag::AUTO_STARTUP, "Verify ohos.permission.MANAGE_APP_BOOT_INTERNAL failed");
687         return CHECK_PERMISSION_FAILED;
688     }
689     return ERR_OK;
690 }
691 } // namespace AbilityRuntime
692 } // namespace OHOS
693