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 "bms_wrapper.h"
17 #include "bundle_mgr_interface.h"
18 #include "iservice_registry.h"
19
20 #include <cstring>
21 #include "securec.h"
22
23 #include "accesstoken_kit.h"
24 #include "bundle_mgr_client.h"
25 #include "hap_token_info.h"
26 #include "ipc_skeleton.h"
27
28 #include "asset_type.h"
29 #include "asset_log.h"
30
31 using namespace OHOS;
32 using namespace AppExecFwk;
33 using namespace Security::AccessToken;
34
35 namespace {
36 constexpr int BUNDLE_MGR_SERVICE_SYS_ABILITY_ID = 401;
37
GetBundleMgr()38 sptr<IBundleMgr> GetBundleMgr()
39 {
40 auto systemAbilityManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
41 if (systemAbilityManager == nullptr) {
42 LOGE("[FATAL]systemAbilityManager is nullptr, please check.");
43 return nullptr;
44 }
45 auto bundleMgrRemoteObj = systemAbilityManager->GetSystemAbility(BUNDLE_MGR_SERVICE_SYS_ABILITY_ID);
46 if (bundleMgrRemoteObj == nullptr) {
47 LOGE("[FATAL]bundleMgrRemoteObj is nullptr, please check.");
48 return nullptr;
49 }
50 return iface_cast<IBundleMgr>(bundleMgrRemoteObj);
51 }
52
GetHapProcessInfo(int32_t userId,uint64_t uid,ProcessInfo * processInfo)53 int32_t GetHapProcessInfo(int32_t userId, uint64_t uid, ProcessInfo *processInfo)
54 {
55 auto bundleMgr = GetBundleMgr();
56 if (bundleMgr == nullptr) {
57 LOGE("[FATAL]bundleMgr is nullptr, please check.");
58 return ASSET_BMS_ERROR;
59 }
60 int32_t appIndex = 0;
61 std::string bundleName;
62 int32_t ret = bundleMgr->GetNameAndIndexForUid(uid, bundleName, appIndex);
63 if (ret != RET_SUCCESS) {
64 LOGE("[FATAL]GetNameAndIndexForUid get bundleName and appIndex failed. ret:%{public}d", ret);
65 return ASSET_BMS_ERROR;
66 }
67 processInfo->hapInfo.appIndex = appIndex;
68
69 if (memcpy_s(processInfo->processName, processInfo->processNameLen, bundleName.c_str(),
70 bundleName.size()) != EOK) {
71 LOGE("[FATAL]The processName buffer is too small. Expect size: %{public}zu, actual size: %{public}u",
72 bundleName.size(), processInfo->processNameLen);
73 return ASSET_OUT_OF_MEMORY;
74 }
75 processInfo->processNameLen = bundleName.size();
76
77 AppExecFwk::BundleMgrClient bmsClient;
78 AppExecFwk::BundleInfo bundleInfo;
79 if (!bmsClient.GetBundleInfo(bundleName, BundleFlag::GET_BUNDLE_WITH_HASH_VALUE,
80 bundleInfo, userId)) {
81 LOGE("[FATAL]Get bundle info failed!");
82 return ASSET_BMS_ERROR;
83 }
84
85 if (memcpy_s(processInfo->hapInfo.appId, processInfo->hapInfo.appIdLen, bundleInfo.appId.c_str(),
86 bundleInfo.appId.size()) != EOK) {
87 LOGE("[FATAL]The app id buffer is too small. Expect size: %{public}zu, actual size: %{public}u",
88 bundleInfo.appId.size(), processInfo->hapInfo.appIdLen);
89 return ASSET_OUT_OF_MEMORY;
90 }
91 processInfo->hapInfo.appIdLen = bundleInfo.appId.size();
92
93 return ASSET_SUCCESS;
94 }
95
GetNativeProcessInfo(uint32_t tokenId,uint64_t uid,ProcessInfo * processInfo)96 int32_t GetNativeProcessInfo(uint32_t tokenId, uint64_t uid, ProcessInfo *processInfo)
97 {
98 NativeTokenInfo nativeTokenInfo;
99 int32_t ret = AccessTokenKit::GetNativeTokenInfo(tokenId, nativeTokenInfo);
100 if (ret != RET_SUCCESS) {
101 LOGE("[FATAL]Get native token info failed, ret = %{public}d", ret);
102 return ASSET_ACCESS_TOKEN_ERROR;
103 }
104
105 if (memcpy_s(processInfo->processName, processInfo->processNameLen, nativeTokenInfo.processName.c_str(),
106 nativeTokenInfo.processName.size()) != EOK) {
107 LOGE("[FATAL]The processName buffer is too small. Expect size: %{public}zu, actual size: %{public}u",
108 nativeTokenInfo.processName.size(), processInfo->processNameLen);
109 return ASSET_OUT_OF_MEMORY;
110 }
111 processInfo->processNameLen = nativeTokenInfo.processName.size();
112 processInfo->nativeInfo.uid = uid;
113 return ASSET_SUCCESS;
114 }
115 } // namespace
116
GetCallingProcessInfo(uint32_t userId,uint64_t uid,ProcessInfo * processInfo)117 int32_t GetCallingProcessInfo(uint32_t userId, uint64_t uid, ProcessInfo *processInfo)
118 {
119 processInfo->userId = userId;
120 auto tokenId = IPCSkeleton::GetCallingTokenID();
121 ATokenTypeEnum tokenType = AccessTokenKit::GetTokenTypeFlag(tokenId);
122 int32_t res = ASSET_SUCCESS;
123 switch (tokenType) {
124 case ATokenTypeEnum::TOKEN_HAP:
125 processInfo->ownerType = HAP;
126 res = GetHapProcessInfo(userId, uid, processInfo);
127 break;
128 case ATokenTypeEnum::TOKEN_NATIVE:
129 case ATokenTypeEnum::TOKEN_SHELL:
130 processInfo->ownerType = NATIVE;
131 res = GetNativeProcessInfo(tokenId, uid, processInfo);
132 break;
133 default:
134 LOGE("[FATAL]Invalid calling type: %{public}d", tokenType);
135 res = ASSET_INVALID_ARGUMENT;
136 }
137 return res;
138 }