1 /*
2  * Copyright (c) 2021-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 "launcher_service.h"
17 
18 #include "bundle_mgr_proxy.h"
19 #include "bundle_mgr_service_death_recipient.h"
20 #include "common_event_subscribe_info.h"
21 #include "common_event_support.h"
22 #include "hitrace_meter.h"
23 #include "matching_skills.h"
24 #include "operation_builder.h"
25 
26 namespace OHOS {
27 namespace AppExecFwk {
28 OHOS::sptr<OHOS::AppExecFwk::IBundleMgr> LauncherService::bundleMgr_ = nullptr;
29 OHOS::sptr<IRemoteObject::DeathRecipient> LauncherService::deathRecipient_(
30     new (std::nothrow) LauncherServiceDeathRecipient());
31 std::mutex LauncherService::bundleMgrMutex_;
32 const char* EMPTY_STRING = "";
33 
34 void LauncherService::LauncherServiceDeathRecipient::OnRemoteDied([[maybe_unused]] const wptr<IRemoteObject>& remote)
35 {
36     APP_LOGD("BundleManagerService dead");
37     std::lock_guard<std::mutex> lock(bundleMgrMutex_);
38     bundleMgr_ = nullptr;
39 };
40 
LauncherService()41 LauncherService::LauncherService()
42 {
43     init();
44 }
45 
init()46 void LauncherService::init()
47 {
48     EventFwk::MatchingSkills matchingSkills;
49     matchingSkills.AddEvent(EventFwk::CommonEventSupport::COMMON_EVENT_PACKAGE_ADDED);
50     matchingSkills.AddEvent(EventFwk::CommonEventSupport::COMMON_EVENT_PACKAGE_CHANGED);
51     matchingSkills.AddEvent(EventFwk::CommonEventSupport::COMMON_EVENT_PACKAGE_REMOVED);
52     EventFwk::CommonEventSubscribeInfo subscribeInfo(matchingSkills);
53     bundleMonitor_ = std::make_shared<BundleMonitor>(subscribeInfo);
54 }
55 
~LauncherService()56 LauncherService::~LauncherService()
57 {
58     APP_LOGD("destroy LauncherService");
59     if (bundleMgr_ != nullptr && deathRecipient_ != nullptr) {
60         bundleMgr_->AsObject()->RemoveDeathRecipient(deathRecipient_);
61     }
62 }
63 
GetBundleMgr()64 OHOS::sptr<OHOS::AppExecFwk::IBundleMgr> LauncherService::GetBundleMgr()
65 {
66     if (bundleMgr_ == nullptr) {
67         std::lock_guard<std::mutex> lock(bundleMgrMutex_);
68         if (bundleMgr_ == nullptr) {
69             auto systemAbilityManager = OHOS::SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
70             if (systemAbilityManager == nullptr) {
71                 APP_LOGE("GetBundleMgr GetSystemAbilityManager is null");
72                 return nullptr;
73             }
74             auto bundleMgrSa = systemAbilityManager->GetSystemAbility(OHOS::BUNDLE_MGR_SERVICE_SYS_ABILITY_ID);
75             if (bundleMgrSa == nullptr) {
76                 APP_LOGE("GetBundleMgr GetSystemAbility is null");
77                 return nullptr;
78             }
79             auto bundleMgr = OHOS::iface_cast<IBundleMgr>(bundleMgrSa);
80             if (bundleMgr == nullptr) {
81                 APP_LOGE("GetBundleMgr iface_cast get null");
82                 return nullptr;
83             }
84             bundleMgr_ = bundleMgr;
85             bundleMgr_->AsObject()->AddDeathRecipient(deathRecipient_);
86         }
87     }
88     return bundleMgr_;
89 }
90 
RegisterCallback(const sptr<IBundleStatusCallback> & callback)91 bool LauncherService::RegisterCallback(const sptr<IBundleStatusCallback> &callback)
92 {
93     APP_LOGD("RegisterCallback called");
94     if (bundleMonitor_ == nullptr) {
95         APP_LOGE("failed to register callback, bundleMonitor is null");
96         return false;
97     }
98 
99     // check permission
100     auto iBundleMgr = GetBundleMgr();
101     if (iBundleMgr == nullptr) {
102         APP_LOGE("can not get iBundleMgr");
103         return false;
104     }
105     if (!iBundleMgr->VerifySystemApi(Constants::INVALID_API_VERSION)) {
106         APP_LOGE("non-system app calling system api");
107         return false;
108     }
109     if (!iBundleMgr->VerifyCallingPermission(Constants::LISTEN_BUNDLE_CHANGE)) {
110         APP_LOGE("register bundle status callback failed due to lack of permission");
111         return false;
112     }
113     return bundleMonitor_->Subscribe(callback);
114 }
115 
UnRegisterCallback()116 bool LauncherService::UnRegisterCallback()
117 {
118     APP_LOGD("UnRegisterCallback called");
119     if (bundleMonitor_ == nullptr) {
120         APP_LOGE("failed to unregister callback, bundleMonitor is null");
121         return false;
122     }
123 
124     // check permission
125     auto iBundleMgr = GetBundleMgr();
126     if (iBundleMgr == nullptr) {
127         APP_LOGE("can not get iBundleMgr");
128         return false;
129     }
130     if (!iBundleMgr->VerifySystemApi(Constants::INVALID_API_VERSION)) {
131         APP_LOGE("non-system app calling system api");
132         return false;
133     }
134     if (!iBundleMgr->VerifyCallingPermission(Constants::LISTEN_BUNDLE_CHANGE)) {
135         APP_LOGE("register bundle status callback failed due to lack of permission");
136         return false;
137     }
138     return bundleMonitor_->UnSubscribe();
139 }
140 
GetAbilityList(const std::string & bundleName,const int userId,std::vector<LauncherAbilityInfo> & launcherAbilityInfos)141 bool LauncherService::GetAbilityList(
142     const std::string &bundleName, const int userId, std::vector<LauncherAbilityInfo> &launcherAbilityInfos)
143 {
144     APP_LOGD("GetAbilityList called");
145     auto iBundleMgr = GetBundleMgr();
146     if ((iBundleMgr == nullptr) || (bundleName.empty())) {
147         APP_LOGE("can not get iBundleMgr");
148         return false;
149     }
150     if (!iBundleMgr->VerifySystemApi(Constants::INVALID_API_VERSION)) {
151         APP_LOGE("non-system app calling system api");
152         return false;
153     }
154     std::vector<std::string> entities;
155     entities.push_back(Want::ENTITY_HOME);
156     Want want;
157     want.SetAction(Want::ACTION_HOME);
158     want.AddEntity(Want::ENTITY_HOME);
159     ElementName elementName;
160     elementName.SetBundleName(bundleName);
161     want.SetElement(elementName);
162     std::vector<AbilityInfo> abilityInfos;
163     if (!iBundleMgr->QueryAllAbilityInfos(want, userId, abilityInfos)) {
164         APP_LOGE("Query ability info failed");
165         return false;
166     }
167 
168     for (auto &ability : abilityInfos) {
169         if (ability.bundleName != bundleName || !ability.enabled) {
170             continue;
171         }
172 
173         LauncherAbilityInfo info;
174         info.applicationInfo = ability.applicationInfo;
175         info.labelId = ability.labelId;
176         info.iconId = ability.iconId;
177         ElementName abilityElementName;
178         abilityElementName.SetBundleName(ability.bundleName);
179         abilityElementName.SetModuleName(ability.moduleName);
180         abilityElementName.SetAbilityName(ability.name);
181         abilityElementName.SetDeviceID(ability.deviceId);
182         info.elementName = abilityElementName;
183         info.userId = userId;
184         info.installTime = ability.installTime;
185         launcherAbilityInfos.emplace_back(info);
186     }
187 
188     return true;
189 }
190 
GetAllLauncherAbilityInfos(int32_t userId,std::vector<LauncherAbilityInfo> & launcherAbilityInfos)191 bool LauncherService::GetAllLauncherAbilityInfos(int32_t userId, std::vector<LauncherAbilityInfo> &launcherAbilityInfos)
192 {
193     APP_LOGI("start");
194     auto iBundleMgr = GetBundleMgr();
195     if (iBundleMgr == nullptr) {
196         APP_LOGE("can not get iBundleMgr");
197         return false;
198     }
199     if (!iBundleMgr->VerifySystemApi(Constants::INVALID_API_VERSION)) {
200         APP_LOGE("non-system app calling system api");
201         return false;
202     }
203     Want want;
204     want.SetAction(Want::ACTION_HOME);
205     want.AddEntity(Want::ENTITY_HOME);
206 
207     std::vector<AbilityInfo> abilityInfos;
208     if (!iBundleMgr->QueryAllAbilityInfos(want, userId, abilityInfos)) {
209         APP_LOGE("Query ability info failed");
210         return false;
211     }
212 
213     for (const auto& ability : abilityInfos) {
214         if (ability.applicationInfo.isLauncherApp || !ability.enabled) {
215             continue;
216         }
217 
218         if (ability.applicationInfo.hideDesktopIcon) {
219             APP_LOGD("Bundle(%{public}s) hide desktop icon", ability.bundleName.c_str());
220             continue;
221         }
222 
223         LauncherAbilityInfo info;
224         info.installTime = ability.installTime;
225         info.applicationInfo = ability.applicationInfo;
226         info.labelId = ability.labelId;
227         info.iconId = ability.iconId;
228         info.userId = userId;
229         ElementName elementName;
230         elementName.SetBundleName(ability.bundleName);
231         elementName.SetModuleName(ability.moduleName);
232         elementName.SetAbilityName(ability.name);
233         elementName.SetDeviceID(ability.deviceId);
234         info.elementName = elementName;
235         launcherAbilityInfos.emplace_back(info);
236     }
237 
238     if (launcherAbilityInfos.empty()) {
239         APP_LOGW("success, but launcherAbilityInfos is empty");
240     } else {
241         APP_LOGI("success");
242     }
243 
244     return true;
245 }
246 
GetShortcutInfos(const std::string & bundleName,std::vector<ShortcutInfo> & shortcutInfos)247 ErrCode LauncherService::GetShortcutInfos(
248     const std::string &bundleName, std::vector<ShortcutInfo> &shortcutInfos)
249 {
250     APP_LOGD("GetShortcutInfos called");
251     if (bundleName.empty()) {
252         APP_LOGE("bundleName is empty");
253         return ERR_BUNDLE_MANAGER_INVALID_PARAMETER;
254     }
255     auto iBundleMgr = GetBundleMgr();
256     if (iBundleMgr == nullptr) {
257         APP_LOGE("iBundleMgr is empty");
258         return ERR_BUNDLE_MANAGER_INTERNAL_ERROR;
259     }
260     if (!iBundleMgr->VerifySystemApi(Constants::INVALID_API_VERSION)) {
261         return ERR_BUNDLE_MANAGER_SYSTEM_API_DENIED;
262     }
263 
264     std::vector<ShortcutInfo> infos;
265     if (!iBundleMgr->GetShortcutInfos(bundleName, infos)) {
266         APP_LOGE("GetShortcutInfos is empty");
267         return ERR_BUNDLE_MANAGER_BUNDLE_NOT_EXIST;
268     }
269     if (infos.size() == 0) {
270         APP_LOGE("infos size is empty");
271         return ERR_BUNDLE_MANAGER_PROFILE_NOT_EXIST;
272     }
273 
274     for (ShortcutInfo shortcutInfo : infos) {
275         if (bundleName == shortcutInfo.bundleName) {
276             shortcutInfos.emplace_back(shortcutInfo);
277         }
278     }
279     return ERR_OK;
280 }
281 
InitWant(Want & want,const std::string & bundleName)282 void LauncherService::InitWant(Want &want, const std::string &bundleName)
283 {
284     want.SetAction(Want::ACTION_HOME);
285     want.AddEntity(Want::ENTITY_HOME);
286     if (!bundleName.empty()) {
287         ElementName elementName;
288         elementName.SetBundleName(bundleName);
289         want.SetElement(elementName);
290     }
291 }
292 
ConvertAbilityToLauncherAbility(const AbilityInfo & ability,LauncherAbilityInfo & launcherAbility,const int32_t userId)293 void LauncherService::ConvertAbilityToLauncherAbility(const AbilityInfo &ability, LauncherAbilityInfo &launcherAbility,
294     const int32_t userId)
295 {
296     launcherAbility.applicationInfo = ability.applicationInfo;
297     launcherAbility.labelId = ability.labelId;
298     launcherAbility.iconId = ability.iconId;
299     ElementName elementName;
300     elementName.SetBundleName(ability.bundleName);
301     elementName.SetModuleName(ability.moduleName);
302     elementName.SetAbilityName(ability.name);
303     elementName.SetDeviceID(ability.deviceId);
304     launcherAbility.elementName = elementName;
305     launcherAbility.userId = userId;
306     launcherAbility.installTime = ability.installTime;
307 }
308 
GetLauncherAbilityByBundleName(const std::string & bundleName,const int32_t userId,std::vector<LauncherAbilityInfo> & launcherAbilityInfos)309 ErrCode LauncherService::GetLauncherAbilityByBundleName(const std::string &bundleName, const int32_t userId,
310     std::vector<LauncherAbilityInfo> &launcherAbilityInfos)
311 {
312     HITRACE_METER_NAME(HITRACE_TAG_APP, __PRETTY_FUNCTION__);
313     APP_LOGD("GetLauncherAbilityByBundleName called");
314     if (bundleName.empty()) {
315         APP_LOGE("no bundleName %{public}s found", bundleName.c_str());
316         return ERR_BUNDLE_MANAGER_BUNDLE_NOT_EXIST;
317     }
318     auto iBundleMgr = GetBundleMgr();
319     if (iBundleMgr == nullptr) {
320         APP_LOGE("can not get iBundleMgr");
321         return ERR_APPEXECFWK_SERVICE_NOT_READY;
322     }
323 
324     Want want;
325     InitWant(want, bundleName);
326     std::vector<AbilityInfo> abilityInfos;
327     ErrCode err = iBundleMgr->QueryLauncherAbilityInfos(want, userId, abilityInfos);
328     if (err != ERR_OK) {
329         APP_LOGE("QueryLauncherAbilityInfos failed");
330         return err;
331     }
332     for (const auto &ability : abilityInfos) {
333         if (ability.bundleName != bundleName || !ability.enabled) {
334             continue;
335         }
336         LauncherAbilityInfo info;
337         ConvertAbilityToLauncherAbility(ability, info, userId);
338         launcherAbilityInfos.push_back(info);
339     }
340     return ERR_OK;
341 }
342 
GetAllLauncherAbility(const int32_t userId,std::vector<LauncherAbilityInfo> & launcherAbilityInfos)343 ErrCode LauncherService::GetAllLauncherAbility(const int32_t userId,
344     std::vector<LauncherAbilityInfo> &launcherAbilityInfos)
345 {
346     APP_LOGD("GetAllLauncherAbility called");
347     auto iBundleMgr = GetBundleMgr();
348     if (iBundleMgr == nullptr) {
349         APP_LOGE("can not get iBundleMgr");
350         return ERR_APPEXECFWK_SERVICE_NOT_READY;
351     }
352 
353     Want want;
354     InitWant(want, EMPTY_STRING);
355     std::vector<AbilityInfo> abilityInfos;
356     ErrCode err = iBundleMgr->QueryLauncherAbilityInfos(want, userId, abilityInfos);
357     if (err != ERR_OK) {
358         APP_LOGE("QueryLauncherAbilityInfos failed");
359         return err;
360     }
361     for (const auto &ability : abilityInfos) {
362         if (!ability.enabled || ability.applicationInfo.hideDesktopIcon) {
363             continue;
364         }
365         LauncherAbilityInfo info;
366         ConvertAbilityToLauncherAbility(ability, info, userId);
367         launcherAbilityInfos.push_back(info);
368     }
369     return ERR_OK;
370 }
371 
GetShortcutInfoV9(const std::string & bundleName,std::vector<ShortcutInfo> & shortcutInfos,int32_t userId)372 ErrCode LauncherService::GetShortcutInfoV9(
373     const std::string &bundleName, std::vector<ShortcutInfo> &shortcutInfos, int32_t userId)
374 {
375     auto iBundleMgr = GetBundleMgr();
376     if (iBundleMgr == nullptr) {
377         APP_LOGE("can not get iBundleMgr");
378         return ERR_APPEXECFWK_SERVICE_NOT_READY;
379     }
380     std::vector<ShortcutInfo> infos;
381     ErrCode errCode = iBundleMgr->GetShortcutInfoV9(bundleName, infos, userId);
382     if (errCode != ERR_OK) {
383         APP_LOGE("GetShortcutInfoV9 is failed");
384         return errCode;
385     }
386     if (infos.empty()) {
387         APP_LOGD("ShortcutInfo is not exist for this bundle");
388         return ERR_OK;
389     }
390 
391     for (ShortcutInfo shortcutInfo : infos) {
392         if (bundleName == shortcutInfo.bundleName) {
393             shortcutInfos.emplace_back(shortcutInfo);
394         }
395     }
396     return ERR_OK;
397 }
398 
OnDeath()399 void LauncherService::OnDeath()
400 {
401     APP_LOGD("BundleManagerService dead");
402     std::lock_guard<std::mutex> lock(bundleMgrMutex_);
403     bundleMgr_ = nullptr;
404 }
405 }  // namespace AppExecFwk
406 }  // namespace OHOS