1 /*
2 * Copyright (c) 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 #include "config_policy_loader.h"
16
17 #ifdef CUSTOMIZATION_CONFIG_POLICY_ENABLE
18 #include "accesstoken_log.h"
19 #include "config_policy_utils.h"
20 #include "json_parser.h"
21 #endif
22
23 namespace OHOS {
24 namespace Security {
25 namespace AccessToken {
26 namespace {
27 #ifdef CUSTOMIZATION_CONFIG_POLICY_ENABLE
28 static constexpr OHOS::HiviewDFX::HiLogLabel LABEL = {LOG_CORE, SECURITY_DOMAIN_ACCESSTOKEN, "ConfigPolicLoader"};
29 static const std::string ACCESSTOKEN_CONFIG_FILE = "/etc/access_token/accesstoken_config.json";
30
31 static const std::string PERMISSION_MANAGER_BUNDLE_NAME_KEY = "permission_manager_bundle_name";
32 static const std::string GRANT_ABILITY_NAME_KEY = "grant_ability_name";
33 static const std::string PERMISSION_STATE_SHEET_ABILITY_NAME_KEY = "permission_state_sheet_ability_name";
34 static const std::string GLOBAL_SWITCH_SHEET_ABILITY_NAME_KEY = "global_switch_sheet_ability_name";
35 static const std::string TEMP_PERM_CANCLE_TIME_KEY = "temp_perm_cencle_time";
36
37 static const std::string RECORD_SIZE_MAXIMUM_KEY = "permission_used_record_size_maximum";
38 static const std::string RECORD_AGING_TIME_KEY = "permission_used_record_aging_time";
39 static const std::string GLOBAL_DIALOG_BUNDLE_NAME_KEY = "global_dialog_bundle_name";
40 static const std::string GLOBAL_DIALOG_ABILITY_NAME_KEY = "global_dialog_ability_name";
41
42 static const std::string SEND_REQUEST_REPEAT_TIMES_KEY = "send_request_repeat_times";
43 #endif // CUSTOMIZATION_CONFIG_POLICY_ENABLE
44 }
45
46 #ifdef CUSTOMIZATION_CONFIG_POLICY_ENABLE
GetConfigFilePathList(std::vector<std::string> & pathList)47 void ConfigPolicLoader::GetConfigFilePathList(std::vector<std::string>& pathList)
48 {
49 CfgDir *dirs = GetCfgDirList(); // malloc a CfgDir point, need to free later
50 if (dirs == nullptr) {
51 ACCESSTOKEN_LOG_ERROR(LABEL, "Can't get cfg file path.");
52 return;
53 }
54
55 for (const auto& path : dirs->paths) {
56 if ((path == nullptr) || (!JsonParser::IsDirExsit(path))) {
57 continue;
58 }
59
60 ACCESSTOKEN_LOG_INFO(LABEL, "Accesstoken cfg dir: %{public}s.", path);
61 pathList.emplace_back(path);
62 }
63
64 FreeCfgDirList(dirs); // free
65 }
66
from_json(const nlohmann::json & j,AccessTokenServiceConfig & a)67 void from_json(const nlohmann::json& j, AccessTokenServiceConfig& a)
68 {
69 if (!JsonParser::GetStringFromJson(j, PERMISSION_MANAGER_BUNDLE_NAME_KEY, a.grantBundleName)) {
70 return;
71 }
72
73 if (!JsonParser::GetStringFromJson(j, GRANT_ABILITY_NAME_KEY, a.grantAbilityName)) {
74 return;
75 }
76
77 if (!JsonParser::GetStringFromJson(j, PERMISSION_STATE_SHEET_ABILITY_NAME_KEY, a.permStateAbilityName)) {
78 return;
79 }
80
81 if (!JsonParser::GetStringFromJson(j, GLOBAL_SWITCH_SHEET_ABILITY_NAME_KEY, a.globalSwitchAbilityName)) {
82 return;
83 }
84
85 if (!JsonParser::GetIntFromJson(j, TEMP_PERM_CANCLE_TIME_KEY, a.cancleTime)) {
86 return;
87 }
88 }
89
from_json(const nlohmann::json & j,PrivacyServiceConfig & p)90 void from_json(const nlohmann::json& j, PrivacyServiceConfig& p)
91 {
92 if (!JsonParser::GetIntFromJson(j, RECORD_SIZE_MAXIMUM_KEY, p.sizeMaxImum)) {
93 return;
94 }
95
96 if (!JsonParser::GetIntFromJson(j, RECORD_AGING_TIME_KEY, p.agingTime)) {
97 return;
98 }
99
100 if (!JsonParser::GetStringFromJson(j, GLOBAL_DIALOG_BUNDLE_NAME_KEY, p.globalDialogBundleName)) {
101 return;
102 }
103
104 if (!JsonParser::GetStringFromJson(j, GLOBAL_DIALOG_ABILITY_NAME_KEY, p.globalDialogAbilityName)) {
105 return;
106 }
107 }
108
from_json(const nlohmann::json & j,TokenSyncServiceConfig & t)109 void from_json(const nlohmann::json& j, TokenSyncServiceConfig& t)
110 {
111 if (!JsonParser::GetIntFromJson(j, SEND_REQUEST_REPEAT_TIMES_KEY, t.sendRequestRepeatTimes)) {
112 return;
113 }
114 }
115
GetConfigValueFromFile(const ServiceType & type,const std::string & fileContent,AccessTokenConfigValue & config)116 bool ConfigPolicLoader::GetConfigValueFromFile(const ServiceType& type, const std::string& fileContent,
117 AccessTokenConfigValue& config)
118 {
119 nlohmann::json jsonRes = nlohmann::json::parse(fileContent, nullptr, false);
120 if (jsonRes.is_discarded()) {
121 ACCESSTOKEN_LOG_ERROR(LABEL, "JsonRes is invalid.");
122 return false;
123 }
124
125 if (type == ServiceType::ACCESSTOKEN_SERVICE) {
126 if ((jsonRes.find("accesstoken") != jsonRes.end()) && (jsonRes.at("accesstoken").is_object())) {
127 config.atConfig = jsonRes.at("accesstoken").get<nlohmann::json>();
128 return true;
129 } else {
130 return false;
131 }
132 } else if (type == ServiceType::PRIVACY_SERVICE) {
133 if ((jsonRes.find("privacy") != jsonRes.end()) && (jsonRes.at("privacy").is_object())) {
134 config.pConfig = jsonRes.at("privacy").get<nlohmann::json>();
135 return true;
136 } else {
137 return false;
138 }
139 }
140
141 if ((jsonRes.find("tokensync") != jsonRes.end()) && (jsonRes.at("tokensync").is_object())) {
142 config.tsConfig = jsonRes.at("tokensync").get<nlohmann::json>();
143 return true;
144 } else {
145 return false;
146 }
147 }
148 #endif // CUSTOMIZATION_CONFIG_POLICY_ENABLE
149
GetConfigValue(const ServiceType & type,AccessTokenConfigValue & config)150 bool ConfigPolicLoader::GetConfigValue(const ServiceType& type, AccessTokenConfigValue& config)
151 {
152 bool successFlag = false;
153 #ifdef CUSTOMIZATION_CONFIG_POLICY_ENABLE
154 std::vector<std::string> pathList;
155 GetConfigFilePathList(pathList);
156
157 for (const auto& path : pathList) {
158 std::string filePath = path + ACCESSTOKEN_CONFIG_FILE;
159 std::string fileContent;
160 int32_t res = JsonParser::ReadCfgFile(filePath, fileContent);
161 if (res != 0) {
162 ACCESSTOKEN_LOG_ERROR(LABEL, "Read Cfg file [%{public}s] failed, error(%{public}d).",
163 filePath.c_str(), res);
164 continue;
165 }
166
167 if (GetConfigValueFromFile(type, fileContent, config)) {
168 ACCESSTOKEN_LOG_INFO(LABEL, "Get valid config value!");
169 successFlag = true;
170 break; // once get the config value, break the loop
171 }
172 }
173 #endif // CUSTOMIZATION_CONFIG_POLICY_ENABLE
174 return successFlag;
175 }
176
177 extern "C" {
Create()178 void* Create()
179 {
180 return reinterpret_cast<void*>(new ConfigPolicLoader);
181 }
182
Destroy(void * loaderPtr)183 void Destroy(void* loaderPtr)
184 {
185 ConfigPolicyLoaderInterface* loader = reinterpret_cast<ConfigPolicyLoaderInterface*>(loaderPtr);
186 if (loader != nullptr) {
187 delete loader;
188 }
189 }
190 }
191 } // namespace AccessToken
192 } // namespace Security
193 } // namespace OHOS
194