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 "profile_utils.h"
17 
18 #include <codecvt>
19 #include <locale>
20 #include <regex>
21 #include <unordered_set>
22 
23 #include "cJSON.h"
24 #include "device_manager.h"
25 #include "dm_constants.h"
26 #include "rdb_errno.h"
27 
28 #include "content_sensor_manager_utils.h"
29 #include "distributed_device_profile_constants.h"
30 #include "distributed_device_profile_enums.h"
31 #include "distributed_device_profile_errors.h"
32 #include "distributed_device_profile_log.h"
33 
34 namespace OHOS {
35 namespace DistributedDeviceProfile {
36 using namespace OHOS::DistributedHardware;
37 
38 namespace {
39     const std::string TAG = "ProfileUtils";
40     const std::unordered_set<std::string> NEED_ADD_OH_SUFFIX_DEV_PROFILES { OS_TYPE, OS_VERSION };
41     const std::unordered_set<std::string> NEED_ADD_OH_SUFFIX_SVR_NAMES { "DistributeModemService",
42         "multiScreenAssistantService" };
43 }
44 
GetDbKeyAnonyString(const std::string & dbKey)45 std::string ProfileUtils::GetDbKeyAnonyString(const std::string& dbKey)
46 {
47     constexpr size_t DEVICE_ID_INDEX = 1;
48     std::vector<std::string> splitKeys;
49     if (ProfileUtils::SplitString(dbKey, SEPARATOR, splitKeys) != DP_SUCCESS ||
50         splitKeys.size() <= DEVICE_ID_INDEX) {
51         return GetAnonyString(dbKey);
52     }
53     for (size_t i = DEVICE_ID_INDEX; i < splitKeys.size(); i++) {
54         splitKeys[i] = GetAnonyString(splitKeys[i]);
55     }
56     return JoinString(splitKeys, SEPARATOR);
57 }
58 
GetAnonyString(const std::string & value)59 std::string ProfileUtils::GetAnonyString(const std::string& value)
60 {
61     constexpr size_t INT32_SHORT_ID_LENGTH = 10;
62     constexpr size_t INT32_PLAINTEXT_LENGTH = 4;
63     constexpr size_t INT32_MIN_ID_LENGTH = 3;
64     std::string res;
65     std::string tmpStr("***");
66     size_t strLen = value.length();
67     if (strLen < INT32_MIN_ID_LENGTH) {
68         return tmpStr;
69     }
70 
71     if (strLen <= INT32_SHORT_ID_LENGTH) {
72         res += value[0];
73         res += tmpStr;
74         res += value[strLen - 1];
75     } else {
76         res.append(value, 0, INT32_PLAINTEXT_LENGTH);
77         res += tmpStr;
78         res.append(value, strLen - INT32_PLAINTEXT_LENGTH, INT32_PLAINTEXT_LENGTH);
79     }
80     return res;
81 }
82 
GetOnlineDevices()83 std::vector<std::string> ProfileUtils::GetOnlineDevices()
84 {
85     std::vector<std::string> targetDevices;
86     std::vector<DmDeviceInfo> allOnlineDeviceInfos;
87     int32_t result = DeviceManager::GetInstance().GetTrustedDeviceList(DP_PKG_NAME, "", allOnlineDeviceInfos);
88     if (result != DP_SUCCESS || allOnlineDeviceInfos.empty()) {
89         HILOGE("GetTrustedDeviceList Failed!");
90         return {};
91     }
92     for (const DmDeviceInfo& dmDeviceInfo : allOnlineDeviceInfos) {
93         targetDevices.push_back(dmDeviceInfo.networkId);
94     }
95     return targetDevices;
96 }
97 
GetLocalUdidFromDM()98 std::string ProfileUtils::GetLocalUdidFromDM()
99 {
100     std::string udid = "";
101     if (DeviceManager::GetInstance().GetLocalDeviceId(DP_PKG_NAME, udid) != DP_SUCCESS) {
102         HILOGE("Get local udid fail from DM!");
103         return "";
104     }
105     return udid;
106 }
107 
FilterAndGroupOnlineDevices(const std::vector<std::string> & deviceList,std::vector<std::string> & ohBasedDevices,std::vector<std::string> & notOHBasedDevices)108 bool ProfileUtils::FilterAndGroupOnlineDevices(const std::vector<std::string>& deviceList,
109     std::vector<std::string>& ohBasedDevices, std::vector<std::string>& notOHBasedDevices)
110 {
111     if (deviceList.size() == 0 || deviceList.size() > MAX_DEVICE_SIZE) {
112         HILOGE("This deviceList size is invalid, size: %{public}zu!", deviceList.size());
113         return false;
114     }
115     std::vector<DmDeviceInfo> allOnlineDeviceInfos;
116     int32_t result = DeviceManager::GetInstance().GetTrustedDeviceList(DP_PKG_NAME, "", allOnlineDeviceInfos);
117     if (result != DP_SUCCESS || allOnlineDeviceInfos.empty()) {
118         HILOGE("GetTrustedDeviceList Failed!");
119         return false;
120     }
121     for (const DmDeviceInfo& dmDeviceInfo : allOnlineDeviceInfos) {
122         if (std::find(deviceList.begin(), deviceList.end(), dmDeviceInfo.networkId) == deviceList.end()) {
123             continue;
124         }
125         if (dmDeviceInfo.extraData.empty()) {
126             HILOGW("extraData is empty! networkId:%{public}s", GetAnonyString(dmDeviceInfo.networkId).c_str());
127             continue;
128         }
129         if (IsOHBasedDevice(dmDeviceInfo.extraData)) {
130             ohBasedDevices.push_back(dmDeviceInfo.networkId);
131         } else {
132             notOHBasedDevices.push_back(dmDeviceInfo.networkId);
133         }
134     }
135     return true;
136 }
137 
IsOHBasedDevice(const std::string & extraData)138 bool ProfileUtils::IsOHBasedDevice(const std::string& extraData)
139 {
140     if (extraData.empty()) {
141         HILOGE("extraData is empty!");
142         return false;
143     }
144     cJSON* extraDataJson = cJSON_Parse(extraData.c_str());
145     if (extraDataJson == NULL) {
146         HILOGE("extraData parse failed");
147         return false;
148     }
149     int32_t osType = OHOS_TYPE_UNKNOWN;
150     cJSON* osTypeJson = cJSON_GetObjectItem(extraDataJson, DistributedHardware::PARAM_KEY_OS_TYPE);
151     if (cJSON_IsNumber(osTypeJson)) {
152         osType = static_cast<int32_t>(osTypeJson->valueint);
153     }
154     cJSON_Delete(extraDataJson);
155     return osType == OHOS_TYPE;
156 }
157 
IsP2p(const int32_t authForm)158 bool ProfileUtils::IsP2p(const int32_t authForm)
159 {
160     if (authForm == static_cast<int32_t>(DistributedHardware::DmAuthForm::INVALID_TYPE) ||
161         authForm == static_cast<int32_t>(DistributedHardware::DmAuthForm::IDENTICAL_ACCOUNT)) {
162         HILOGD("authForm: %{public}d!", authForm);
163         return false;
164     }
165     return true;
166 }
167 
GetProfileType(const std::string & key)168 ProfileType ProfileUtils::GetProfileType(const std::string& key)
169 {
170     if (key.length() == 0 || key.length() > MAX_STRING_LEN) {
171         HILOGE("This key is invalid, value: %{public}s!", GetAnonyString(key).c_str());
172         return ProfileType::PROFILE_TYPE_MIN;
173     }
174     ProfileType profileType = ProfileType::PROFILE_TYPE_MIN;
175     if (StartsWith(key, DEV_PREFIX)) {
176         profileType = ProfileType::DEVICE_PROFILE;
177     }
178     if (StartsWith(key, SVR_PREFIX)) {
179         profileType = ProfileType::SERVICE_PROFILE;
180     }
181     if (StartsWith(key, CHAR_PREFIX)) {
182         profileType = ProfileType::CHAR_PROFILE;
183     }
184     return profileType;
185 }
186 
StartsWith(const std::string & str,const std::string & prefix)187 bool ProfileUtils::StartsWith(const std::string& str, const std::string& prefix)
188 {
189     return (str.find(prefix, 0) == 0);
190 }
191 
EndsWith(const std::string & str,const std::string & suffix)192 bool ProfileUtils::EndsWith(const std::string& str, const std::string& suffix)
193 {
194     if (str.length() < suffix.length()) {
195         return false;
196     }
197     return str.substr(str.length() - suffix.length()).compare(suffix) == 0;
198 }
199 
GetProfileKey(const std::string & dbKey)200 std::string ProfileUtils::GetProfileKey(const std::string& dbKey)
201 {
202     if (dbKey.length() == 0 || dbKey.length() > MAX_STRING_LEN) {
203         return "";
204     }
205     std::size_t pos = dbKey.find_last_of("#");
206     return dbKey.substr(0, pos);
207 }
208 
GetDeviceIdByDBKey(const std::string & dbKey)209 std::string ProfileUtils::GetDeviceIdByDBKey(const std::string& dbKey)
210 {
211     if (dbKey.length() == 0 || dbKey.length() > MAX_STRING_LEN) {
212         return "";
213     }
214     std::vector<std::string> res;
215     if (SplitString(dbKey, SEPARATOR, res) != DP_SUCCESS) {
216         return "";
217     }
218     if (res.size() < NUM_1) {
219         return "";
220     }
221     return res[NUM_1];
222 }
223 
GetServiceNameByDBKey(const std::string & dbKey)224 std::string ProfileUtils::GetServiceNameByDBKey(const std::string& dbKey)
225 {
226     if (dbKey.length() == 0 || dbKey.length() > MAX_STRING_LEN) {
227         return "";
228     }
229     std::vector<std::string> res;
230     if (SplitString(dbKey, SEPARATOR, res) != DP_SUCCESS) {
231         return "";
232     }
233     if (res.size() < NUM_2) {
234         return "";
235     }
236     return res[NUM_2];
237 }
238 
GetNonOhSuffixServiceNameByDBKey(const std::string & dbKey)239 std::string ProfileUtils::GetNonOhSuffixServiceNameByDBKey(const std::string& dbKey)
240 {
241     std::string serviceName = GetServiceNameByDBKey(dbKey);
242     if (serviceName.empty()) {
243         return "";
244     }
245     return CheckAndRemoveOhSuffix(serviceName);
246 }
247 
IsNeedAddOhSuffix(const std::string & profileName,bool isSvr)248 bool ProfileUtils::IsNeedAddOhSuffix(const std::string& profileName, bool isSvr)
249 {
250     if (profileName.length() == 0 || profileName.length() > MAX_STRING_LEN) {
251         return false;
252     }
253     if (isSvr && NEED_ADD_OH_SUFFIX_SVR_NAMES.count(profileName) > 0) {
254         return true;
255     }
256     if (!isSvr && NEED_ADD_OH_SUFFIX_DEV_PROFILES.count(profileName) > 0) {
257         return true;
258     }
259     return false;
260 }
261 
CheckAndAddOhSuffix(const std::string & profileName,bool isSvr)262 std::string ProfileUtils::CheckAndAddOhSuffix(const std::string& profileName, bool isSvr)
263 {
264     std::string str = profileName;
265     if (IsNeedAddOhSuffix(str, isSvr)) {
266         str = str + OH_PROFILE_SUFFIX;
267     }
268     return str;
269 }
270 
CheckAndRemoveOhSuffix(const std::string & profileName)271 std::string ProfileUtils::CheckAndRemoveOhSuffix(const std::string& profileName)
272 {
273     std::string str = profileName;
274     if (EndsWith(str, OH_PROFILE_SUFFIX)) {
275         str = str.erase(str.length() - OH_PROFILE_SUFFIX.length());
276     }
277     return str;
278 }
279 
GetCharKeyByDBKey(const std::string & dbKey)280 std::string ProfileUtils::GetCharKeyByDBKey(const std::string& dbKey)
281 {
282     if (dbKey.length() == 0 || dbKey.length() > MAX_STRING_LEN) {
283         return "";
284     }
285     std::vector<std::string> res;
286     if (SplitString(dbKey, SEPARATOR, res) != DP_SUCCESS) {
287         return "";
288     }
289     if (res.size() < NUM_3) {
290         return "";
291     }
292     return res[NUM_3];
293 }
294 
SplitString(const std::string & str,const std::string & splits,std::vector<std::string> & res)295 int32_t ProfileUtils::SplitString(const std::string& str, const std::string& splits, std::vector<std::string>& res)
296 {
297     if (str == "") {
298         return DP_INVALID_PARAMS;
299     }
300     std::string strs = str + splits;
301     size_t pos = strs.find(splits);
302     int32_t step = splits.size();
303 
304     while (pos != strs.npos) {
305         std::string temp = strs.substr(0, pos);
306         res.push_back(temp);
307         strs = strs.substr(pos + step, strs.size());
308         pos = strs.find(splits);
309     }
310     return DP_SUCCESS;
311 }
312 
JoinString(const std::vector<std::string> & strs,const std::string & delimiter)313 std::string ProfileUtils::JoinString(const std::vector<std::string>& strs, const std::string& delimiter)
314 {
315     std::string res = EMPTY_STRING;
316     if (strs.empty()) {
317         return res;
318     }
319     for (size_t i = 0; i < strs.size(); i++) {
320         res += strs[i];
321         if (i != strs.size() - 1) {
322             res += delimiter;
323         }
324     }
325     return res;
326 }
327 
IsKeyValid(const std::string & key)328 bool ProfileUtils::IsKeyValid(const std::string& key)
329 {
330     if (key.length() == 0 || key.length() > MAX_STRING_LEN) {
331         return false;
332     }
333     size_t found = key.find(SEPARATOR);
334     if (found != std::string::npos) {
335         return false;
336     }
337     return true;
338 }
339 
IsLocalUdid(const std::string & udid)340 bool ProfileUtils::IsLocalUdid(const std::string& udid)
341 {
342     if (udid.length() == 0 || udid.length() > MAX_STRING_LEN) {
343         return false;
344     }
345     std::string localUdid = ContentSensorManagerUtils::GetInstance().ObtainLocalUdid();
346     return localUdid == udid;
347 }
348 
IsDevProfileValid(const DeviceProfile & devProfile)349 bool ProfileUtils::IsDevProfileValid(const DeviceProfile& devProfile)
350 {
351     return IsKeyValid(devProfile.GetDeviceId()) && IsLocalUdid(devProfile.GetDeviceId());
352 }
353 
IsSvrProfileValid(const ServiceProfile & svrProfile)354 bool ProfileUtils::IsSvrProfileValid(const ServiceProfile& svrProfile)
355 {
356     return IsKeyValid(svrProfile.GetDeviceId()) && IsLocalUdid(svrProfile.GetDeviceId()) &&
357         IsKeyValid(svrProfile.GetServiceName());
358 }
359 
IsCharProfileValid(const CharacteristicProfile & charProfile)360 bool ProfileUtils::IsCharProfileValid(const CharacteristicProfile& charProfile)
361 {
362     return IsKeyValid(charProfile.GetDeviceId()) && IsLocalUdid(charProfile.GetDeviceId()) &&
363         IsKeyValid(charProfile.GetServiceName()) && IsKeyValid(charProfile.GetCharacteristicKey());
364 }
365 
IsDeviceProfileValid(const DeviceProfile & devProfile)366 bool ProfileUtils::IsDeviceProfileValid(const DeviceProfile& devProfile)
367 {
368     if (devProfile.GetOsVersion().empty() || devProfile.GetOsType() == MIN_OS_TYPE) {
369         return false;
370     }
371     return true;
372 }
373 
IsServiceProfileValid(const ServiceProfile & svrProfile)374 bool ProfileUtils::IsServiceProfileValid(const ServiceProfile& svrProfile)
375 {
376     if (svrProfile.GetServiceName().empty() || svrProfile.GetServiceType().empty()) {
377         return false;
378     }
379     return true;
380 }
381 
IsCharacteristicProfileValid(const CharacteristicProfile & charProfile)382 bool ProfileUtils::IsCharacteristicProfileValid(const CharacteristicProfile& charProfile)
383 {
384     if (charProfile.GetCharacteristicKey().empty() || charProfile.GetCharacteristicValue().empty()) {
385         return false;
386     }
387     return true;
388 }
389 
GenerateDeviceProfileKey(const std::string & deviceId)390 std::string ProfileUtils::GenerateDeviceProfileKey(const std::string& deviceId)
391 {
392     return DEV_PREFIX + SEPARATOR + deviceId;
393 }
394 
GenerateServiceProfileKey(const std::string & deviceId,const std::string & serviceName)395 std::string ProfileUtils::GenerateServiceProfileKey(const std::string& deviceId, const std::string& serviceName)
396 {
397     return SVR_PREFIX + SEPARATOR + deviceId + SEPARATOR + serviceName;
398 }
399 
GenerateCharProfileKey(const std::string & deviceId,const std::string & serviceName,const std::string & charKey)400 std::string ProfileUtils::GenerateCharProfileKey(const std::string& deviceId, const std::string& serviceName,
401     const std::string& charKey)
402 {
403     return CHAR_PREFIX + SEPARATOR + deviceId + SEPARATOR + serviceName + SEPARATOR + charKey;
404 }
405 
TrustDeviceProfileToEntries(const TrustDeviceProfile & profile,ValuesBucket & values)406 int32_t ProfileUtils::TrustDeviceProfileToEntries(const TrustDeviceProfile& profile, ValuesBucket& values)
407 {
408     values.PutString(DEVICE_ID, profile.GetDeviceId());
409     values.PutInt(DEVICE_ID_TYPE, profile.GetDeviceIdType());
410     values.PutString(DEVICE_ID_HASH, profile.GetDeviceIdHash());
411     values.PutInt(STATUS, profile.GetStatus());
412     return DP_SUCCESS;
413 }
414 
AccessControlProfileToEntries(const AccessControlProfile & profile,ValuesBucket & values)415 int32_t ProfileUtils::AccessControlProfileToEntries(const AccessControlProfile& profile, ValuesBucket& values)
416 {
417     values.PutLong(ACCESS_CONTROL_ID, profile.GetAccessControlId());
418     values.PutLong(ACCESSER_ID, profile.GetAccesserId());
419     values.PutLong(ACCESSEE_ID, profile.GetAccesseeId());
420     values.PutString(TRUST_DEVICE_ID, profile.GetTrustDeviceId());
421     values.PutInt(AUTHENTICATION_TYPE, profile.GetAuthenticationType());
422     values.PutInt(DEVICE_ID_TYPE, profile.GetDeviceIdType());
423     values.PutString(DEVICE_ID_HASH, profile.GetDeviceIdHash());
424     values.PutInt(BIND_TYPE, profile.GetBindType());
425     values.PutString(SESSION_KEY, profile.GetSessionKey());
426     values.PutInt(LAST_AUTH_TIME, profile.GetLastAuthTime());
427     values.PutInt(VALID_PERIOD, profile.GetValidPeriod());
428     values.PutInt(STATUS, profile.GetStatus());
429     values.PutInt(BIND_LEVEL, profile.GetBindLevel());
430     return DP_SUCCESS;
431 }
432 
AccesserToEntries(const AccessControlProfile & aclProfile,ValuesBucket & values)433 int32_t ProfileUtils::AccesserToEntries(const AccessControlProfile& aclProfile, ValuesBucket& values)
434 {
435     Accesser accesser = aclProfile.GetAccesser();
436     values.PutLong(ACCESSER_ID, accesser.GetAccesserId());
437     values.PutString(ACCESSER_DEVICE_ID, accesser.GetAccesserDeviceId());
438     values.PutInt(ACCESSER_USER_ID, accesser.GetAccesserUserId());
439     values.PutString(ACCESSER_ACCOUNT_ID, accesser.GetAccesserAccountId());
440     values.PutLong(ACCESSER_TOKEN_ID, accesser.GetAccesserTokenId());
441     values.PutString(ACCESSER_BUNDLE_NAME, accesser.GetAccesserBundleName());
442     values.PutString(ACCESSER_HAP_SIGNATURE, accesser.GetAccesserHapSignature());
443     values.PutInt(ACCESSER_BIND_LEVEL, accesser.GetAccesserBindLevel());
444     return DP_SUCCESS;
445 }
446 
AccesseeToEntries(const AccessControlProfile & aclProfile,ValuesBucket & values)447 int32_t ProfileUtils::AccesseeToEntries(const AccessControlProfile& aclProfile, ValuesBucket& values)
448 {
449     Accessee accessee = aclProfile.GetAccessee();
450     values.PutLong(ACCESSEE_ID, accessee.GetAccesseeId());
451     values.PutString(ACCESSEE_DEVICE_ID, accessee.GetAccesseeDeviceId());
452     values.PutInt(ACCESSEE_USER_ID, accessee.GetAccesseeUserId());
453     values.PutString(ACCESSEE_ACCOUNT_ID, accessee.GetAccesseeAccountId());
454     values.PutLong(ACCESSEE_TOKEN_ID, accessee.GetAccesseeTokenId());
455     values.PutString(ACCESSEE_BUNDLE_NAME, accessee.GetAccesseeBundleName());
456     values.PutString(ACCESSEE_HAP_SIGNATURE, accessee.GetAccesseeHapSignature());
457     values.PutInt(ACCESSEE_BIND_LEVEL, accessee.GetAccesseeBindLevel());
458     return DP_SUCCESS;
459 }
460 
DeviceProfileToEntries(const DeviceProfile & profile,std::map<std::string,std::string> & values)461 int32_t ProfileUtils::DeviceProfileToEntries(const DeviceProfile& profile, std::map<std::string, std::string>& values)
462 {
463     std::string deviceProfileKey = GenerateDeviceProfileKey(profile.GetDeviceId());
464     values[GenerateDBKey(deviceProfileKey, OS_SYS_CAPACITY)] = profile.GetOsSysCap();
465     values[GenerateDBKey(deviceProfileKey, OS_VERSION)] = profile.GetOsVersion();
466     values[GenerateDBKey(deviceProfileKey, OS_TYPE)] = std::to_string(profile.GetOsType());
467     values[GenerateDBKey(deviceProfileKey, OS_VERSION + OH_PROFILE_SUFFIX)] = profile.GetOsVersion();
468     values[GenerateDBKey(deviceProfileKey, OS_TYPE + OH_PROFILE_SUFFIX)] = std::to_string(profile.GetOsType());
469     return DP_SUCCESS;
470 }
471 
ServiceProfileToEntries(const ServiceProfile & profile,std::map<std::string,std::string> & values)472 int32_t ProfileUtils::ServiceProfileToEntries(const ServiceProfile& profile, std::map<std::string, std::string>& values)
473 {
474     std::string serviceName = CheckAndAddOhSuffix(profile.GetServiceName(), true);
475     std::string serviceProfileKey = GenerateServiceProfileKey(profile.GetDeviceId(), serviceName);
476     // value not need add OH suffix
477     values[GenerateDBKey(serviceProfileKey, SERVICE_NAME)] = profile.GetServiceName();
478     values[GenerateDBKey(serviceProfileKey, SERVICE_TYPE)] = profile.GetServiceType();
479     return DP_SUCCESS;
480 }
481 
CharacteristicProfileToEntries(const CharacteristicProfile & profile,std::map<std::string,std::string> & values)482 int32_t ProfileUtils::CharacteristicProfileToEntries(const CharacteristicProfile& profile,
483                                                      std::map<std::string, std::string>& values)
484 {
485     std::string serviceName = CheckAndAddOhSuffix(profile.GetServiceName(), true);
486     std::string charProfileKey = GenerateCharProfileKey(profile.GetDeviceId(), serviceName,
487         profile.GetCharacteristicKey());
488     values[GenerateDBKey(charProfileKey, CHARACTERISTIC_KEY)] = profile.GetCharacteristicKey();
489     values[GenerateDBKey(charProfileKey, CHARACTERISTIC_VALUE)] = profile.GetCharacteristicValue();
490     return DP_SUCCESS;
491 }
492 
EntriesToTrustDeviceProfile(const ValuesBucket & values,TrustDeviceProfile & profile)493 int32_t ProfileUtils::EntriesToTrustDeviceProfile(const ValuesBucket& values, TrustDeviceProfile& profile)
494 {
495     ValueObject valueObject;
496     std::string strValue = "";
497     int32_t intValue = 0;
498     if (values.GetObject(DEVICE_ID, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
499         profile.SetDeviceId(strValue);
500     }
501     if (values.GetObject(DEVICE_ID_HASH, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
502         profile.SetDeviceIdHash(strValue);
503     }
504     if (values.GetObject(DEVICE_TYPE_ID, valueObject) && valueObject.GetInt(intValue) == NativeRdb::E_OK) {
505         profile.SetDeviceIdType(intValue);
506     }
507     if (values.GetObject(STATUS, valueObject) && valueObject.GetInt(intValue) == NativeRdb::E_OK) {
508         profile.SetStatus(intValue);
509     }
510     return DP_SUCCESS;
511 }
512 
EntriesToAccessControlProfile(const ValuesBucket & values,AccessControlProfile & profile)513 int32_t ProfileUtils::EntriesToAccessControlProfile(const ValuesBucket& values, AccessControlProfile& profile)
514 {
515     std::string strValue = "";
516     int32_t intValue = 0;
517     int64_t int64Value = 0;
518     if (GetLongValue(values, ACCESS_CONTROL_ID, int64Value)) {
519         profile.SetAccessControlId(int64Value);
520     }
521     if (GetLongValue(values, ACCESSER_ID, int64Value)) {
522         profile.SetAccesserId(int64Value);
523     }
524     if (GetLongValue(values, ACCESSEE_ID, int64Value)) {
525         profile.SetAccesseeId(int64Value);
526     }
527     if (GetStringValue(values, SESSION_KEY, strValue)) {
528         profile.SetSessionKey(strValue);
529     }
530     if (GetIntValue(values, BIND_TYPE, intValue)) {
531         profile.SetBindType(intValue);
532     }
533     if (GetIntValue(values, AUTHENTICATION_TYPE, intValue)) {
534         profile.SetAuthenticationType(intValue);
535     }
536     if (GetIntValue(values, BIND_LEVEL, intValue)) {
537         profile.SetBindLevel(intValue);
538     }
539     if (GetIntValue(values, STATUS, intValue)) {
540         profile.SetStatus(intValue);
541     }
542     if (GetIntValue(values, VALID_PERIOD, intValue)) {
543         profile.SetValidPeriod(intValue);
544     }
545     if (GetIntValue(values, LAST_AUTH_TIME, intValue)) {
546         profile.SetLastAuthTime(intValue);
547     }
548     if (GetStringValue(values, TRUST_DEVICE_ID, strValue)) {
549         profile.SetTrustDeviceId(strValue);
550     }
551     if (GetIntValue(values, DEVICE_TYPE_ID, intValue)) {
552         profile.SetDeviceIdType(intValue);
553     }
554     if (GetStringValue(values, DEVICE_ID_HASH, strValue)) {
555         profile.SetDeviceIdHash(strValue);
556     }
557     return DP_SUCCESS;
558 }
559 
EntriesToAccesser(const ValuesBucket & values,Accesser & accesser)560 int32_t ProfileUtils::EntriesToAccesser(const ValuesBucket& values, Accesser& accesser)
561 {
562     ValueObject valueObject;
563     std::string strValue = "";
564     int32_t intValue = 0;
565     int64_t int64Value = 0;
566     if (values.GetObject(ACCESSER_ID, valueObject) && valueObject.GetLong(int64Value) == NativeRdb::E_OK) {
567         accesser.SetAccesserId(int64Value);
568     }
569     if (values.GetObject(ACCESSER_DEVICE_ID, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
570         accesser.SetAccesserDeviceId(strValue);
571     }
572     if (values.GetObject(ACCESSER_USER_ID, valueObject) && valueObject.GetInt(intValue) == NativeRdb::E_OK) {
573         accesser.SetAccesserUserId(intValue);
574     }
575     if (values.GetObject(ACCESSER_ACCOUNT_ID, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
576         accesser.SetAccesserAccountId(strValue);
577     }
578     if (values.GetObject(ACCESSER_TOKEN_ID, valueObject) && valueObject.GetLong(int64Value) == NativeRdb::E_OK) {
579         accesser.SetAccesserTokenId(int64Value);
580     }
581     if (values.GetObject(ACCESSER_BUNDLE_NAME, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
582         accesser.SetAccesserBundleName(strValue);
583     }
584     if (values.GetObject(ACCESSER_BIND_LEVEL, valueObject) && valueObject.GetInt(intValue) == NativeRdb::E_OK) {
585         accesser.SetAccesserBindLevel(intValue);
586     }
587     return DP_SUCCESS;
588 }
589 
EntriesToAccessee(const ValuesBucket & values,Accessee & accessee)590 int32_t ProfileUtils::EntriesToAccessee(const ValuesBucket& values, Accessee& accessee)
591 {
592     ValueObject valueObject;
593     std::string strValue = "";
594     int32_t intValue = 0;
595     int64_t int64Value = 0;
596     if (values.GetObject(ACCESSEE_ID, valueObject) && valueObject.GetLong(int64Value) == NativeRdb::E_OK) {
597         accessee.SetAccesseeId(int64Value);
598     }
599     if (values.GetObject(ACCESSEE_DEVICE_ID, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
600         accessee.SetAccesseeDeviceId(strValue);
601     }
602     if (values.GetObject(ACCESSEE_USER_ID, valueObject) && valueObject.GetInt(intValue) == NativeRdb::E_OK) {
603         accessee.SetAccesseeUserId(intValue);
604     }
605     if (values.GetObject(ACCESSEE_ACCOUNT_ID, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
606         accessee.SetAccesseeAccountId(strValue);
607     }
608     if (values.GetObject(ACCESSEE_TOKEN_ID, valueObject) && valueObject.GetLong(int64Value) == NativeRdb::E_OK) {
609         accessee.SetAccesseeTokenId(int64Value);
610     }
611     if (values.GetObject(ACCESSEE_BUNDLE_NAME, valueObject) && valueObject.GetString(strValue) == NativeRdb::E_OK) {
612         accessee.SetAccesseeBundleName(strValue);
613     }
614     if (values.GetObject(ACCESSEE_BIND_LEVEL, valueObject) && valueObject.GetInt(intValue) == NativeRdb::E_OK) {
615         accessee.SetAccesseeBindLevel(intValue);
616     }
617     return DP_SUCCESS;
618 }
619 
EntriesToDeviceProfile(std::map<std::string,std::string> values,DeviceProfile & profile)620 int32_t ProfileUtils::EntriesToDeviceProfile(std::map<std::string, std::string> values, DeviceProfile& profile)
621 {
622     if (values.empty() || values.size() > MAX_DB_RECORD_SIZE) {
623         HILOGI("Entries size is invalid!size: %{public}zu!", values.size());
624         return DP_INVALID_PARAMS;
625     }
626     auto propertiesMap = GetProfilePropertiesMap(values);
627     if (IsPropertyValid(propertiesMap, OS_SYS_CAPACITY, MAX_STRING_LEN)) {
628         profile.SetOsSysCap(propertiesMap[OS_SYS_CAPACITY]);
629     }
630     if (IsPropertyValid(propertiesMap, OS_VERSION, MAX_STRING_LEN)) {
631         profile.SetOsVersion(propertiesMap[OS_VERSION]);
632     }
633     if (IsPropertyValid(propertiesMap, OS_VERSION + OH_PROFILE_SUFFIX, MAX_STRING_LEN)) {
634         profile.SetOsVersion(propertiesMap[OS_VERSION + OH_PROFILE_SUFFIX]);
635     }
636     if (IsPropertyValid(propertiesMap, OS_TYPE, MIN_OS_TYPE, MAX_OS_TYPE)) {
637         int32_t osType = std::atoi(propertiesMap[OS_TYPE].c_str());
638         profile.SetOsType(osType);
639     }
640     if (IsPropertyValid(propertiesMap, OS_TYPE + OH_PROFILE_SUFFIX, MIN_OS_TYPE, MAX_OS_TYPE)) {
641         int32_t osType = std::atoi(propertiesMap[OS_TYPE + OH_PROFILE_SUFFIX].c_str());
642         profile.SetOsType(osType);
643     }
644     return DP_SUCCESS;
645 }
646 
EntriesToServiceProfile(std::map<std::string,std::string> values,ServiceProfile & profile)647 int32_t ProfileUtils::EntriesToServiceProfile(std::map<std::string, std::string> values, ServiceProfile& profile)
648 {
649     if (values.empty() || values.size() > MAX_DB_RECORD_SIZE) {
650         HILOGI("Entries size is invalid!size: %{public}zu!", values.size());
651         return DP_INVALID_PARAMS;
652     }
653     auto iter = values.begin();
654     profile.SetDeviceId(GetDeviceIdByDBKey(iter->first));
655     auto propertiesMap = GetProfilePropertiesMap(values);
656     if (propertiesMap.count(SERVICE_NAME) != 0 && 0 < propertiesMap[SERVICE_NAME].length() &&
657         propertiesMap[SERVICE_NAME].length() < MAX_STRING_LEN) {
658         profile.SetServiceName(CheckAndRemoveOhSuffix(propertiesMap[SERVICE_NAME]));
659     }
660     if (propertiesMap.count(SERVICE_TYPE) != 0 && 0 < propertiesMap[SERVICE_TYPE].length() &&
661         propertiesMap[SERVICE_TYPE].length() < MAX_STRING_LEN) {
662         profile.SetServiceType(propertiesMap[SERVICE_TYPE]);
663     }
664     return DP_SUCCESS;
665 }
666 
EntriesToCharProfile(std::map<std::string,std::string> values,CharacteristicProfile & profile)667 int32_t ProfileUtils::EntriesToCharProfile(std::map<std::string, std::string> values, CharacteristicProfile& profile)
668 {
669     if (values.empty() || values.size() > MAX_DB_RECORD_SIZE) {
670         HILOGI("Entries size is invalid!size : %{public}zu", values.size());
671         return DP_INVALID_PARAMS;
672     }
673     auto iter = values.begin();
674     profile.SetDeviceId(GetDeviceIdByDBKey(iter->first));
675     profile.SetServiceName(GetNonOhSuffixServiceNameByDBKey(iter->first));
676     auto propertiesMap = GetProfilePropertiesMap(values);
677     if (propertiesMap.count(CHARACTERISTIC_KEY) != 0 && 0 < propertiesMap[CHARACTERISTIC_KEY].length() &&
678         propertiesMap[CHARACTERISTIC_KEY].length() < MAX_STRING_LEN) {
679         profile.SetCharacteristicKey(propertiesMap[CHARACTERISTIC_KEY]);
680     }
681     if (propertiesMap.count(CHARACTERISTIC_VALUE) != 0 && 0 < propertiesMap[CHARACTERISTIC_VALUE].length() &&
682         propertiesMap[CHARACTERISTIC_VALUE].length() < MAX_STRING_LEN) {
683         profile.SetCharacteristicValue(propertiesMap[CHARACTERISTIC_VALUE]);
684     }
685     return DP_SUCCESS;
686 }
687 
GenerateDBKey(const std::string & profileKey,const std::string & profileProperty)688 std::string ProfileUtils::GenerateDBKey(const std::string& profileKey, const std::string& profileProperty)
689 {
690     return profileKey + SEPARATOR + profileProperty;
691 }
692 
GetProfileProperty(const std::string & dbKey)693 std::string ProfileUtils::GetProfileProperty(const std::string& dbKey)
694 {
695     if (dbKey.length() == 0 || dbKey.length() > MAX_STRING_LEN) {
696         return "";
697     }
698     std::size_t pos = dbKey.find_last_of("#");
699     if (pos == std::string::npos) {
700         return "";
701     }
702     return dbKey.substr(pos + 1);
703 }
704 
GetProfilePropertiesMap(std::map<std::string,std::string> dbEntries)705 std::map<std::string, std::string> ProfileUtils::GetProfilePropertiesMap(std::map<std::string, std::string> dbEntries)
706 {
707     std::map<std::string, std::string> propertiesMap;
708     for (const auto& item : dbEntries) {
709         std::string profileProperty = GetProfileProperty(item.first);
710         if (profileProperty.empty()) {
711             HILOGE("GetProfileProperty fail, %{public}s!", GetDbKeyAnonyString(item.first).c_str());
712             continue;
713         }
714         propertiesMap[profileProperty] = item.second;
715     }
716     return propertiesMap;
717 }
718 
toString(const std::u16string & str16)719 std::string ProfileUtils::toString(const std::u16string& str16)
720 {
721     return std::wstring_convert< std::codecvt_utf8_utf16<char16_t>, char16_t >{}.to_bytes(str16);
722 }
723 
IsPropertyValid(const std::map<std::string,std::string> & propertyMap,const std::string & property,int32_t maxValue)724 bool ProfileUtils::IsPropertyValid(const std::map<std::string, std::string>& propertyMap, const std::string& property,
725     int32_t maxValue)
726 {
727     if (propertyMap.count(property) != 0 && 0 < propertyMap.at(property).length() &&
728         (static_cast<int32_t>(propertyMap.at(property).length())) < maxValue) {
729         return true;
730     }
731     HILOGE("property is valid, property : %{public}s", property.c_str());
732     return false;
733 }
734 
IsPropertyValid(const std::map<std::string,std::string> & propertyMap,const std::string & property,int32_t minValue,int32_t maxValue)735 bool ProfileUtils::IsPropertyValid(const std::map<std::string, std::string>& propertyMap, const std::string& property,
736     int32_t minValue, int32_t maxValue)
737 {
738     if (property.empty() || propertyMap.find(property) == propertyMap.end()) {
739         HILOGE("property is valid, property : %{public}s", property.c_str());
740         return false;
741     }
742     std::string propertyValue = propertyMap.at(property);
743     if (!IsNumStr(propertyValue)) {
744         HILOGE("%{public}s is not numeric string", GetAnonyString(propertyValue).c_str());
745         return false;
746     }
747     if (minValue < std::atoi(propertyValue.c_str()) && std::atoi(propertyValue.c_str()) < maxValue) {
748         return true;
749     }
750     return false;
751 }
752 
IsNumStr(const std::string & inString)753 bool ProfileUtils::IsNumStr(const std::string& inString)
754 {
755     if (inString.empty()) {
756         HILOGE("inString is empty");
757         return false;
758     }
759     std::regex isNumStrRule(IS_NUMSTRING_RULES);
760     return std::regex_match(inString, isNumStrRule);
761 }
762 
GetIntValue(const ValuesBucket & values,const std::string & property,int32_t & value)763 bool ProfileUtils::GetIntValue(const ValuesBucket& values, const std::string& property, int32_t& value)
764 {
765     ValueObject valueObject;
766     if (values.GetObject(property, valueObject) && valueObject.GetInt(value) == NativeRdb::E_OK) {
767         return true;
768     }
769     return false;
770 }
771 
GetStringValue(const ValuesBucket & values,const std::string & property,std::string & value)772 bool ProfileUtils::GetStringValue(const ValuesBucket& values, const std::string& property, std::string& value)
773 {
774     ValueObject valueObject;
775     if (values.GetObject(property, valueObject) && valueObject.GetString(value) == NativeRdb::E_OK) {
776         return true;
777     }
778     return false;
779 }
780 
GetLongValue(const ValuesBucket & values,const std::string & property,int64_t & value)781 bool ProfileUtils::GetLongValue(const ValuesBucket& values, const std::string& property, int64_t& value)
782 {
783     ValueObject valueObject;
784     if (values.GetObject(property, valueObject) && valueObject.GetLong(value) == NativeRdb::E_OK) {
785         return true;
786     }
787     return false;
788 }
789 
GetUdidByNetworkId(const std::string & networkId,std::string & udid)790 bool ProfileUtils::GetUdidByNetworkId(const std::string& networkId, std::string& udid)
791 {
792     return ((DeviceManager::GetInstance().GetUdidByNetworkId(DP_PKG_NAME, networkId, udid) == 0) ? true : false);
793 }
794 
GetUuidByNetworkId(const std::string & networkId,std::string & uuid)795 bool ProfileUtils::GetUuidByNetworkId(const std::string& networkId, std::string& uuid)
796 {
797     return ((DeviceManager::GetInstance().GetUuidByNetworkId(DP_PKG_NAME, networkId, uuid) == 0) ? true : false);
798 }
799 
GetDbKeyByProfile(const CharacteristicProfile & profile)800 std::string ProfileUtils::GetDbKeyByProfile(const CharacteristicProfile& profile)
801 {
802     if (profile.GetDeviceId().empty() ||
803         profile.GetServiceName().empty() ||
804         profile.GetCharacteristicKey().empty()) {
805         HILOGE("GetDbKeyByProfile fail");
806         return "";
807     }
808     std::string serviceName = CheckAndAddOhSuffix(profile.GetServiceName(), true);
809     std::string dbKey = CHAR_PREFIX + SEPARATOR + profile.GetDeviceId() + SEPARATOR + serviceName +
810         SEPARATOR + profile.GetCharacteristicKey() + SEPARATOR + CHARACTERISTIC_VALUE;
811     return dbKey;
812 }
813 } // namespace DistributedDeviceProfile
814 } // namespace OHOS
815