• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 "permission_policy_set.h"
17 
18 #include "accesstoken_log.h"
19 #include "access_token_error.h"
20 #include "data_storage.h"
21 #include "data_translator.h"
22 #include "token_field_const.h"
23 #include "permission_definition_cache.h"
24 #include "permission_validator.h"
25 
26 namespace OHOS {
27 namespace Security {
28 namespace AccessToken {
29 namespace {
30 static constexpr OHOS::HiviewDFX::HiLogLabel LABEL = {LOG_CORE, SECURITY_DOMAIN_ACCESSTOKEN, "PermissionPolicySet"};
31 }
32 
~PermissionPolicySet()33 PermissionPolicySet::~PermissionPolicySet()
34 {
35     ACCESSTOKEN_LOG_DEBUG(LABEL,
36         "%{public}s called, tokenID: 0x%{public}x destruction", __func__, tokenId_);
37 }
38 
BuildPermissionPolicySet(AccessTokenID tokenId,const std::vector<PermissionStateFull> & permStateList)39 std::shared_ptr<PermissionPolicySet> PermissionPolicySet::BuildPermissionPolicySet(
40     AccessTokenID tokenId, const std::vector<PermissionStateFull>& permStateList)
41 {
42     std::shared_ptr<PermissionPolicySet> policySet = std::make_shared<PermissionPolicySet>();
43     if (policySet != nullptr) {
44         PermissionValidator::FilterInvalidPermissionState(permStateList, policySet->permStateList_);
45         policySet->tokenId_ = tokenId;
46     }
47     return policySet;
48 }
49 
UpdatePermStateFull(const PermissionStateFull & permOld,PermissionStateFull & permNew)50 void PermissionPolicySet::UpdatePermStateFull(const PermissionStateFull& permOld, PermissionStateFull& permNew)
51 {
52     if (permNew.isGeneral == permOld.isGeneral) {
53         permNew.resDeviceID = permOld.resDeviceID;
54         permNew.grantStatus = permOld.grantStatus;
55         permNew.grantFlags = permOld.grantFlags;
56     }
57 }
58 
Update(const std::vector<PermissionStateFull> & permStateList)59 void PermissionPolicySet::Update(const std::vector<PermissionStateFull>& permStateList)
60 {
61     std::vector<PermissionStateFull> permStateFilterList;
62     PermissionValidator::FilterInvalidPermissionState(permStateList, permStateFilterList);
63 
64     Utils::UniqueWriteGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
65 
66     for (PermissionStateFull& permStateNew : permStateFilterList) {
67         auto iter = std::find_if(permStateList_.begin(), permStateList_.end(),
68             [permStateNew](const PermissionStateFull& permStateOld) {
69                 return permStateNew.permissionName == permStateOld.permissionName;
70             });
71         if (iter != permStateList_.end()) {
72             UpdatePermStateFull(*iter, permStateNew);
73             break;
74         }
75     }
76     permStateList_ = permStateFilterList;
77 }
78 
RestorePermissionPolicy(AccessTokenID tokenId,const std::vector<GenericValues> & permStateRes)79 std::shared_ptr<PermissionPolicySet> PermissionPolicySet::RestorePermissionPolicy(AccessTokenID tokenId,
80     const std::vector<GenericValues>& permStateRes)
81 {
82     std::shared_ptr<PermissionPolicySet> policySet = std::make_shared<PermissionPolicySet>();
83     if (policySet == nullptr) {
84         ACCESSTOKEN_LOG_ERROR(LABEL, "tokenId 0x%{public}x new failed.", tokenId);
85         return nullptr;
86     }
87     policySet->tokenId_ = tokenId;
88 
89     for (const GenericValues& stateValue : permStateRes) {
90         if ((AccessTokenID)stateValue.GetInt(TokenFiledConst::FIELD_TOKEN_ID) == tokenId) {
91             PermissionStateFull state;
92             int ret = DataTranslator::TranslationIntoPermissionStateFull(stateValue, state);
93             if (ret == RET_SUCCESS) {
94                 MergePermissionStateFull(policySet->permStateList_, state);
95             } else {
96                 ACCESSTOKEN_LOG_ERROR(LABEL, "tokenId 0x%{public}x permState is wrong.", tokenId);
97             }
98         }
99     }
100     return policySet;
101 }
102 
MergePermissionStateFull(std::vector<PermissionStateFull> & permStateList,const PermissionStateFull & state)103 void PermissionPolicySet::MergePermissionStateFull(std::vector<PermissionStateFull>& permStateList,
104     const PermissionStateFull& state)
105 {
106     for (auto iter = permStateList.begin(); iter != permStateList.end(); iter++) {
107         if (state.permissionName == iter->permissionName) {
108             iter->resDeviceID.emplace_back(state.resDeviceID[0]);
109             iter->grantStatus.emplace_back(state.grantStatus[0]);
110             iter->grantFlags.emplace_back(state.grantFlags[0]);
111             return;
112         }
113     }
114     permStateList.emplace_back(state);
115 }
116 
StorePermissionState(std::vector<GenericValues> & valueList) const117 void PermissionPolicySet::StorePermissionState(std::vector<GenericValues>& valueList) const
118 {
119     for (const auto& permissionState : permStateList_) {
120         if (permissionState.isGeneral) {
121             GenericValues genericValues;
122             genericValues.Put(TokenFiledConst::FIELD_TOKEN_ID, static_cast<int32_t>(tokenId_));
123             DataTranslator::TranslationIntoGenericValues(permissionState, 0, genericValues);
124             valueList.emplace_back(genericValues);
125             continue;
126         }
127 
128         unsigned int stateSize = permissionState.resDeviceID.size();
129         for (unsigned int i = 0; i < stateSize; i++) {
130             GenericValues genericValues;
131             genericValues.Put(TokenFiledConst::FIELD_TOKEN_ID, static_cast<int32_t>(tokenId_));
132             DataTranslator::TranslationIntoGenericValues(permissionState, i, genericValues);
133             valueList.emplace_back(genericValues);
134         }
135     }
136 }
137 
StorePermissionPolicySet(std::vector<GenericValues> & permStateValueList)138 void PermissionPolicySet::StorePermissionPolicySet(std::vector<GenericValues>& permStateValueList)
139 {
140     Utils::UniqueReadGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
141     StorePermissionState(permStateValueList);
142 }
143 
VerifyPermissStatus(const std::string & permissionName)144 int PermissionPolicySet::VerifyPermissStatus(const std::string& permissionName)
145 {
146     Utils::UniqueReadGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
147     for (const auto& perm : permStateList_) {
148         if (perm.permissionName == permissionName) {
149             if (perm.isGeneral) {
150                 return perm.grantStatus[0];
151             } else {
152                 return PERMISSION_DENIED;
153             }
154         }
155     }
156     return PERMISSION_DENIED;
157 }
158 
GetDefPermissions(std::vector<PermissionDef> & permList)159 void PermissionPolicySet::GetDefPermissions(std::vector<PermissionDef>& permList)
160 {
161     PermissionDefinitionCache::GetInstance().GetDefPermissionsByTokenId(permList, tokenId_);
162 }
163 
GetPermissionStateFulls(std::vector<PermissionStateFull> & permList)164 void PermissionPolicySet::GetPermissionStateFulls(std::vector<PermissionStateFull>& permList)
165 {
166     Utils::UniqueReadGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
167     permList.assign(permStateList_.begin(), permStateList_.end());
168 }
169 
QueryPermissionFlag(const std::string & permissionName,int & flag)170 int PermissionPolicySet::QueryPermissionFlag(const std::string& permissionName, int& flag)
171 {
172     Utils::UniqueReadGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
173     for (const auto& perm : permStateList_) {
174         if (perm.permissionName == permissionName) {
175             if (perm.isGeneral) {
176                 uint32_t oldFlag = static_cast<uint32_t>(perm.grantFlags[0]);
177                 uint32_t unmaskedFlag = (oldFlag) & (~PERMISSION_GRANTED_BY_POLICY);
178                 flag = static_cast<int32_t>(unmaskedFlag);
179                 return RET_SUCCESS;
180             } else {
181                 return AccessTokenError::ERR_PARAM_INVALID;
182             }
183         }
184     }
185     return AccessTokenError::ERR_PARAM_INVALID;
186 }
187 
UpdatePermissionStatus(const std::string & permissionName,bool isGranted,uint32_t flag,bool & isUpdated)188 int32_t PermissionPolicySet::UpdatePermissionStatus(
189     const std::string& permissionName, bool isGranted, uint32_t flag, bool& isUpdated)
190 {
191     ACCESSTOKEN_LOG_DEBUG(LABEL, "permissionName %{public}s.", permissionName.c_str());
192 
193     Utils::UniqueWriteGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
194     auto iter = std::find_if(permStateList_.begin(), permStateList_.end(),
195         [permissionName](const PermissionStateFull& permState) {
196             return permissionName == permState.permissionName;
197         });
198     if (iter != permStateList_.end()) {
199         if (iter->isGeneral) {
200             int32_t oldStatus = iter->grantStatus[0];
201             iter->grantStatus[0] = isGranted ? PERMISSION_GRANTED : PERMISSION_DENIED;
202             uint32_t currFlag = static_cast<uint32_t>(iter->grantFlags[0]);
203             uint32_t newFlag = flag | (currFlag & PERMISSION_GRANTED_BY_POLICY);
204             iter->grantFlags[0] = static_cast<int32_t>(newFlag);
205             isUpdated = (oldStatus == iter->grantStatus[0]) ? false : true;
206         } else {
207             ACCESSTOKEN_LOG_WARN(LABEL, "perm isGeneral is false.");
208         }
209     } else {
210         ACCESSTOKEN_LOG_ERROR(LABEL, "invalid params!");
211         return AccessTokenError::ERR_PARAM_INVALID;
212     }
213 
214     return RET_SUCCESS;
215 }
216 
ResetUserGrantPermissionStatus(void)217 void PermissionPolicySet::ResetUserGrantPermissionStatus(void)
218 {
219     Utils::UniqueWriteGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
220     for (auto& perm : permStateList_) {
221         if (perm.isGeneral) {
222             uint32_t oldFlag = static_cast<uint32_t>(perm.grantFlags[0]);
223             if ((oldFlag & PERMISSION_SYSTEM_FIXED) != 0) {
224                 continue;
225             }
226             if ((oldFlag & PERMISSION_GRANTED_BY_POLICY) != 0) {
227                 perm.grantStatus[0] = PERMISSION_GRANTED;
228                 perm.grantFlags[0] = PERMISSION_GRANTED_BY_POLICY;
229                 continue;
230             }
231             perm.grantStatus[0] = PERMISSION_DENIED;
232             perm.grantFlags[0] = PERMISSION_DEFAULT_FLAG;
233         } else {
234             continue;
235         }
236     }
237 }
238 
GetPermissionStateList(std::vector<PermissionStateFull> & stateList)239 void PermissionPolicySet::GetPermissionStateList(std::vector<PermissionStateFull>& stateList)
240 {
241     Utils::UniqueReadGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
242     for (const auto& state : permStateList_) {
243         stateList.emplace_back(state);
244     }
245 }
246 
PermDefToString(const PermissionDef & def,std::string & info) const247 void PermissionPolicySet::PermDefToString(const PermissionDef& def, std::string& info) const
248 {
249     info.append(R"(    {)");
250     info.append("\n");
251     info.append(R"(      "permissionName": ")" + def.permissionName + R"(")" + ",\n");
252     info.append(R"(      "bundleName": ")" + def.bundleName + R"(")" + ",\n");
253     info.append(R"(      "grantMode": )" + std::to_string(def.grantMode) + ",\n");
254     info.append(R"(      "availableLevel": )" + std::to_string(def.availableLevel) + ",\n");
255     info.append(R"(      "provisionEnable": )" + std::to_string(def.provisionEnable) + ",\n");
256     info.append(R"(      "distributedSceneEnable": )" + std::to_string(def.distributedSceneEnable) + ",\n");
257     info.append(R"(      "label": ")" + def.label + R"(")" + ",\n");
258     info.append(R"(      "labelId": )" + std::to_string(def.labelId) + ",\n");
259     info.append(R"(      "description": ")" + def.description + R"(")" + ",\n");
260     info.append(R"(      "descriptionId": )" + std::to_string(def.descriptionId) + ",\n");
261     info.append(R"(    })");
262 }
263 
PermStateFullToString(const PermissionStateFull & state,std::string & info) const264 void PermissionPolicySet::PermStateFullToString(const PermissionStateFull& state, std::string& info) const
265 {
266     info.append(R"(    {)");
267     info.append("\n");
268     info.append(R"(      "permissionName": ")" + state.permissionName + R"(")" + ",\n");
269     info.append(R"(      "isGeneral": )" + std::to_string(state.isGeneral) + ",\n");
270     info.append(R"(      "resDeviceIDList": [ )");
271     for (auto iter = state.resDeviceID.begin(); iter != state.resDeviceID.end(); iter++) {
272         info.append("\n");
273         info.append(R"(        { "resDeviceID": ")" + *iter + R"(")" + " }");
274         if (iter != (state.resDeviceID.end() - 1)) {
275             info.append(",");
276         }
277     }
278     info.append("\n      ],\n");
279 
280     info.append(R"(      "grantStatusList": [)");
281     for (auto iter = state.grantStatus.begin(); iter != state.grantStatus.end(); iter++) {
282         info.append("\n");
283         info.append(R"(        { "grantStatus": )" + std::to_string(*iter) + " }");
284         if (iter != (state.grantStatus.end() - 1)) {
285             info.append(",");
286         }
287     }
288     info.append("\n      ],\n");
289 
290     info.append(R"(      "grantFlagsList": [)");
291     for (auto iter = state.grantFlags.begin(); iter != state.grantFlags.end(); iter++) {
292         info.append("\n");
293         info.append(R"(        { "grantFlag": )" + std::to_string(*iter) + " }");
294         if (iter != (state.grantFlags.end() - 1)) {
295             info.append(",");
296         }
297     }
298     info.append("\n      ],\n");
299 
300     info.append(R"(    })");
301 }
302 
ToString(std::string & info)303 void PermissionPolicySet::ToString(std::string& info)
304 {
305     Utils::UniqueReadGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
306     info.append(R"(  "permDefList": [)");
307     info.append("\n");
308     std::vector<PermissionDef> permList;
309     PermissionDefinitionCache::GetInstance().GetDefPermissionsByTokenId(permList, tokenId_);
310     for (auto iter = permList.begin(); iter != permList.end(); iter++) {
311         PermDefToString(*iter, info);
312         if (iter != (permList.end() - 1)) {
313             info.append(",\n");
314         }
315     }
316     info.append("\n  ],\n");
317 
318     info.append(R"(  "permStateList": [)");
319     info.append("\n");
320     for (auto iter = permStateList_.begin(); iter != permStateList_.end(); iter++) {
321         PermStateFullToString(*iter, info);
322         if (iter != (permStateList_.end() - 1)) {
323             info.append(",\n");
324         }
325     }
326     info.append("\n  ]\n");
327 }
328 
IsPermissionReqValid(int32_t tokenApl,const std::string & permissionName,const std::vector<std::string> & nativeAcls)329 bool PermissionPolicySet::IsPermissionReqValid(int32_t tokenApl, const std::string& permissionName,
330     const std::vector<std::string>& nativeAcls)
331 {
332     PermissionDef permissionDef;
333     int ret = PermissionDefinitionCache::GetInstance().FindByPermissionName(
334         permissionName, permissionDef);
335     if (ret != RET_SUCCESS) {
336         return false;
337     }
338     if (tokenApl >= permissionDef.availableLevel) {
339         return true;
340     }
341 
342     auto iter = std::find(nativeAcls.begin(), nativeAcls.end(), permissionName);
343     if (iter != nativeAcls.end()) {
344         return true;
345     }
346     return false;
347 }
348 
PermStateToString(int32_t tokenApl,const std::vector<std::string> & nativeAcls,std::string & info)349 void PermissionPolicySet::PermStateToString(int32_t tokenApl,
350     const std::vector<std::string>& nativeAcls, std::string& info)
351 {
352     Utils::UniqueReadGuard<Utils::RWLock> infoGuard(this->permPolicySetLock_);
353 
354     std::vector<std::string> invalidPermList = {};
355     info.append(R"(  "permStateList": [)");
356     info.append("\n");
357     for (auto iter = permStateList_.begin(); iter != permStateList_.end(); iter++) {
358         if (!IsPermissionReqValid(tokenApl, iter->permissionName, nativeAcls)) {
359             invalidPermList.emplace_back(iter->permissionName);
360             continue;
361         }
362         PermStateFullToString(*iter, info);
363         if (iter != (permStateList_.end() - 1)) {
364             info.append(",\n");
365         }
366     }
367     info.append("\n  ]\n");
368 
369     if (invalidPermList.empty()) {
370         return;
371     }
372 
373     info.append(R"(  "invalidPermList": [)");
374     info.append("\n");
375     for (auto iter = invalidPermList.begin(); iter != invalidPermList.end(); iter++) {
376         info.append(R"(      "permissionName": ")" + *iter + R"(")" + ",\n");
377     }
378     info.append("\n  ]\n");
379 }
380 } // namespace AccessToken
381 } // namespace Security
382 } // namespace OHOS
383