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 "wifi_common_util.h"
17 #include <fstream>
18 #include <sstream>
19 #include <iterator>
20 #include <regex>
21
22 #ifndef OHOS_ARCH_LITE
23 #include <vector>
24 #include <openssl/bio.h>
25 #include <openssl/evp.h>
26 #include <openssl/pem.h>
27 #include <openssl/x509.h>
28 #include "app_mgr_client.h"
29 #include "bundle_mgr_interface.h"
30 #include "if_system_ability_manager.h"
31 #include "ipc_skeleton.h"
32 #include "iservice_registry.h"
33 #include "system_ability_definition.h"
34 #include "common_timer_errors.h"
35 #endif
36 #include "wifi_logger.h"
37 #include <ifaddrs.h>
38 #include <net/if.h>
39 #include <netdb.h>
40 #include <cerrno>
41
42 namespace OHOS {
43 namespace Wifi {
44 DEFINE_WIFILOG_LABEL("WifiCommonUtil");
45
46 constexpr int PRIFIX_IP_LEN = 3;
47 constexpr int PRIFIX_P2P_LEN = 3;
48 constexpr int PRIFIX_CHBA_LEN = 4;
49 constexpr int PRIFIX_WLAN1_LEN = 5;
50 constexpr int FREQ_2G_MIN = 2412;
51 constexpr int FREQ_2G_MAX = 2472;
52 constexpr int FREQ_5G_MIN = 5170;
53 constexpr int FREQ_5G_MAX = 5825;
54 constexpr int CHANNEL_14_FREQ = 2484;
55 constexpr int CHANNEL_14 = 14;
56 constexpr int CENTER_FREQ_DIFF = 5;
57 constexpr int CHANNEL_2G_MIN = 1;
58 constexpr int CHANNEL_5G_MIN = 34;
59 constexpr int MIN_24G_CHANNEL = 1;
60 constexpr int MAX_24G_CHANNEL = 13;
61 constexpr int MIN_5G_CHANNEL = 36;
62 constexpr int MAX_5G_CHANNEL = 165;
63 constexpr int FREQ_CHANNEL_1 = 2412;
64 constexpr int FREQ_CHANNEL_36 = 5180;
65 constexpr int SECOND_TO_MICROSECOND = 1000 * 1000;
66 constexpr int MICROSECOND_TO_NANOSECOND = 1000;
67 constexpr char HIDDEN_CHAR_SHOW_AS = '*';
68 constexpr int PASSWORD_MIN_LEN = 8;
69 constexpr int PASSWORD_NO_HIDDEN_LEN = 2;
70
71 constexpr uint32_t BASE_HEX = 16;
72 constexpr uint32_t MAX_INT32_LENGTH = 11; // -2147483648 ~ 2147483647
73 constexpr uint32_t MAX_INT64_LENGTH = 20; // -9223372036854775808 ~ 9223372036854775807
74 constexpr uint32_t MAX_UINT32_LENGTH = 10; // 0 ~ 4294967295
75 constexpr uint32_t MAX_INT32_LENGTH_HEX = 8;
76
77 const uint32_t BASE64_UNIT_ONE_PADDING = 1;
78 const uint32_t BASE64_UNIT_TWO_PADDING = 2;
79 const uint32_t BASE64_SRC_UNIT_SIZE = 3;
80 const uint32_t BASE64_DEST_UNIT_SIZE = 4;
81
82 static std::pair<std::string, int> g_brokerProcessInfo;
83 static constexpr uint8_t STEP_2BIT = 2;
84 static constexpr uint8_t HEX_OFFSET = 4;
85 static constexpr char HEX_TABLE[] = "0123456789ABCDEF";
86
DataAnonymize(const std::string str,const char delim,const char hiddenCh,const int startIdx=0)87 static std::string DataAnonymize(const std::string str, const char delim,
88 const char hiddenCh, const int startIdx = 0)
89 {
90 std::string s = str;
91 constexpr auto minDelimSize = 2;
92 constexpr auto minKeepSize = 6;
93 if (std::count(s.begin(), s.end(), delim) < minDelimSize) {
94 if (s.size() <= minKeepSize) {
95 return std::string(s.size(), hiddenCh);
96 }
97 auto idx1 = 2;
98 const auto idx2 = static_cast<int>(s.size() - 4);
99 while (idx1++ < idx2) {
100 s[idx1] = hiddenCh;
101 }
102 return s;
103 }
104
105 std::string::size_type begin = s.find_first_of(delim);
106 std::string::size_type end = s.find_last_of(delim);
107 int idx = 0;
108 while (idx++ < startIdx && begin < end) {
109 begin = s.find_first_of(delim, begin + 1);
110 }
111 while (begin++ != end) {
112 if (s[begin] != delim) {
113 s[begin] = hiddenCh;
114 }
115 }
116 return s;
117 }
118
MacAnonymize(const std::string str)119 std::string MacAnonymize(const std::string str)
120 {
121 return DataAnonymize(str, ':', '*', 1);
122 }
123
IpAnonymize(const std::string str)124 std::string IpAnonymize(const std::string str)
125 {
126 return DataAnonymize(str, '.', '*');
127 }
128
SsidAnonymize(const std::string str)129 std::string SsidAnonymize(const std::string str)
130 {
131 if (str.empty()) {
132 return str;
133 }
134
135 std::string s = str;
136 constexpr char hiddenChar = '*';
137 constexpr size_t minHiddenSize = 3;
138 constexpr size_t headKeepSize = 3;
139 constexpr size_t tailKeepSize = 3;
140 auto func = [hiddenChar](char& c) { c = hiddenChar; };
141 if (s.size() < minHiddenSize) {
142 std::for_each(s.begin(), s.end(), func);
143 return s;
144 }
145
146 if (s.size() < (minHiddenSize + headKeepSize + tailKeepSize)) {
147 size_t beginIndex = 1;
148 size_t hiddenSize = s.size() - minHiddenSize + 1;
149 hiddenSize = hiddenSize > minHiddenSize ? minHiddenSize : hiddenSize;
150 std::for_each(s.begin() + beginIndex, s.begin() + beginIndex + hiddenSize, func);
151 return s;
152 }
153 std::for_each(s.begin() + headKeepSize, s.begin() + s.size() - tailKeepSize, func);
154 return s;
155 }
156
PassWordAnonymize(const std::string str)157 std::string PassWordAnonymize(const std::string str)
158 {
159 if (str.size() < PASSWORD_MIN_LEN) {
160 WIFI_LOGE("Password should not shorter than 8");
161 return "";
162 }
163 std::string s = str;
164 auto func = [](char& c) { c = HIDDEN_CHAR_SHOW_AS; };
165 std::for_each(s.begin() + PASSWORD_NO_HIDDEN_LEN, s.end() - PASSWORD_NO_HIDDEN_LEN, func);
166 return s;
167 }
168
ConvertStrChar(char ch)169 static unsigned char ConvertStrChar(char ch)
170 {
171 constexpr int numDiffForHexAlphabet = 10;
172 if (ch >= '0' && ch <= '9') {
173 return (ch - '0');
174 }
175 if (ch >= 'A' && ch <= 'F') {
176 return (ch - 'A' + numDiffForHexAlphabet);
177 }
178 if (ch >= 'a' && ch <= 'f') {
179 return (ch - 'a' + numDiffForHexAlphabet);
180 }
181 return 0;
182 }
183
MacStrToArray(const std::string & strMac,unsigned char mac[WIFI_MAC_LEN])184 errno_t MacStrToArray(const std::string& strMac, unsigned char mac[WIFI_MAC_LEN])
185 {
186 constexpr int strMacLen = 18;
187 char tempArray[strMacLen] = { 0 };
188 errno_t ret = memcpy_s(tempArray, strMacLen, strMac.c_str(), strMac.size() + 1);
189 if (ret != EOK) {
190 return ret;
191 }
192
193 int idx = 0;
194 constexpr int bitWidth = 4;
195 char *ptr = nullptr;
196 char *p = strtok_s(tempArray, ":", &ptr);
197 while ((p != nullptr) && (idx < WIFI_MAC_LEN)) {
198 mac[idx++] = (ConvertStrChar(*p) << bitWidth) | ConvertStrChar(*(p + 1));
199 p = strtok_s(nullptr, ":", &ptr);
200 }
201 return EOK;
202 }
203
ConvertArrayChar(unsigned char ch)204 static char ConvertArrayChar(unsigned char ch)
205 {
206 constexpr int maxDecNum = 9;
207 constexpr int numDiffForHexAlphabet = 10;
208 if (ch <= maxDecNum) {
209 return '0' + ch;
210 }
211 if (ch <= 0xf) {
212 return ch + 'a' - numDiffForHexAlphabet;
213 }
214 return '0';
215 }
216
MacArrayToStr(const unsigned char mac[WIFI_MAC_LEN])217 std::string MacArrayToStr(const unsigned char mac[WIFI_MAC_LEN])
218 {
219 constexpr int bitWidth = 4;
220 constexpr int noColonBit = 5;
221 std::stringstream ss;
222 for (int i = 0; i != WIFI_MAC_LEN; ++i) {
223 ss << ConvertArrayChar(mac[i] >> bitWidth) << ConvertArrayChar(mac[i] & 0xf);
224 if (i != noColonBit) {
225 ss << ":";
226 }
227 }
228 return ss.str();
229 }
230
IsMacArrayEmpty(const unsigned char mac[WIFI_MAC_LEN])231 bool IsMacArrayEmpty(const unsigned char mac[WIFI_MAC_LEN])
232 {
233 for (int i = 0; i != WIFI_MAC_LEN; ++i) {
234 if (mac[i] != 0) {
235 return false;
236 }
237 }
238 return true;
239 }
240
Ip2Number(const std::string & strIp)241 unsigned int Ip2Number(const std::string& strIp)
242 {
243 std::string::size_type front = 0;
244 std::string::size_type back = 0;
245 unsigned int number = 0;
246 int size = 32;
247 constexpr int sectionSize = 8;
248
249 std::string ip(strIp + '.');
250 while ((back = ip.find_first_of('.', back)) != (std::string::size_type)std::string::npos) {
251 number |= static_cast<unsigned long>(std::stol(ip.substr(front, back - front).c_str()) <<
252 (size -= sectionSize));
253 front = ++back;
254 }
255 return number;
256 }
257
Number2Ip(unsigned int intIp)258 std::string Number2Ip(unsigned int intIp)
259 {
260 constexpr int fourthPartMoveLen = 24;
261 constexpr int thirdPartMoveLen = 16;
262 constexpr int secondPartMoveLen = 8;
263
264 std::string ip;
265 ip.append(std::to_string((intIp & 0xff000000) >> fourthPartMoveLen));
266 ip.push_back('.');
267 ip.append(std::to_string((intIp & 0x00ff0000) >> thirdPartMoveLen));
268 ip.push_back('.');
269 ip.append(std::to_string((intIp & 0x0000ff00) >> secondPartMoveLen));
270 ip.push_back('.');
271 ip.append(std::to_string(intIp & 0x000000ff));
272 return ip;
273 }
274
StrSplit(const std::string & str,const std::string & delim)275 std::vector<std::string> StrSplit(const std::string& str, const std::string& delim) {
276 std::regex re(delim);
277 std::sregex_token_iterator
278 first{ str.begin(), str.end(), re, -1 },
279 last;
280 return { first, last };
281 }
282
GetElapsedMicrosecondsSinceBoot()283 int64_t GetElapsedMicrosecondsSinceBoot()
284 {
285 struct timespec times = {0, 0};
286 clock_gettime(CLOCK_BOOTTIME, ×);
287 return static_cast<int64_t>(times.tv_sec) * SECOND_TO_MICROSECOND + times.tv_nsec / MICROSECOND_TO_NANOSECOND;
288 }
289
290 #ifndef OHOS_ARCH_LITE
GetBundleManager()291 sptr<AppExecFwk::IBundleMgr> GetBundleManager()
292 {
293 sptr<ISystemAbilityManager> systemManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
294 if (systemManager == nullptr) {
295 WIFI_LOGE("Get system ability manager failed!");
296 return nullptr;
297 }
298 return iface_cast<AppExecFwk::IBundleMgr>(systemManager->GetSystemAbility(BUNDLE_MGR_SERVICE_SYS_ABILITY_ID));
299 }
300
GetBundleName()301 std::string GetBundleName()
302 {
303 sptr<AppExecFwk::IBundleMgr> bundleInstance = GetBundleManager();
304 if (bundleInstance == nullptr) {
305 WIFI_LOGE("bundle instance is null!");
306 return "";
307 }
308
309 AppExecFwk::BundleInfo bundleInfo;
310 auto ret = bundleInstance->GetBundleInfoForSelf(0, bundleInfo);
311 if (ret != OHOS::ERR_OK) {
312 return "";
313 }
314
315 WIFI_LOGI("Get bundle name uid[%{public}d]: %{public}s", bundleInfo.uid, bundleInfo.name.c_str());
316 return bundleInfo.name;
317 }
318
GetBundleAppIdByBundleName(const int userId,const std::string & bundleName)319 std::string GetBundleAppIdByBundleName(const int userId, const std::string &bundleName)
320 {
321 sptr<AppExecFwk::IBundleMgr> bundleInstance = GetBundleManager();
322 if (bundleInstance == nullptr) {
323 WIFI_LOGE("bundle instance is null!");
324 return "";
325 }
326
327 AppExecFwk::BundleInfo bundleInfo;
328 AppExecFwk::GetBundleInfoFlag bundleInfoFlag = AppExecFwk::GetBundleInfoFlag::GET_BUNDLE_INFO_WITH_SIGNATURE_INFO;
329 auto ret = bundleInstance->GetBundleInfoV9(bundleName, static_cast<int32_t>(bundleInfoFlag), bundleInfo, userId);
330 if (ret != OHOS::ERR_OK) {
331 return "";
332 }
333 return bundleInfo.signatureInfo.appIdentifier;
334 }
335
GetBundleNameByUid(const int uid,std::string & bundleName)336 ErrCode GetBundleNameByUid(const int uid, std::string &bundleName)
337 {
338 sptr<AppExecFwk::IBundleMgr> bundleInstance = GetBundleManager();
339 if (bundleInstance == nullptr) {
340 WIFI_LOGE("%{public}s bundle instance is null!", __FUNCTION__);
341 return WIFI_OPT_FAILED;
342 }
343 if (!bundleInstance->GetBundleNameForUid(uid, bundleName)) {
344 WIFI_LOGD("%{public}s get bundleName failed", __FUNCTION__);
345 return WIFI_OPT_FAILED;
346 }
347 return WIFI_OPT_SUCCESS;
348 }
349
GetCallingPid()350 int GetCallingPid()
351 {
352 return IPCSkeleton::GetCallingPid();
353 }
354
GetCallingUid()355 int GetCallingUid()
356 {
357 return IPCSkeleton::GetCallingUid();
358 }
359
GetCallingTokenId()360 int GetCallingTokenId()
361 {
362 return IPCSkeleton::GetCallingTokenID();
363 }
364
GetBrokerProcessNameByPid(const int uid,const int pid)365 std::string GetBrokerProcessNameByPid(const int uid, const int pid)
366 {
367 std::string processName = "";
368 if (g_brokerProcessInfo.second == pid) {
369 processName = g_brokerProcessInfo.first;
370 }
371 return processName;
372 }
373
SetWifiBrokerProcess(int pid,std::string processName)374 void SetWifiBrokerProcess(int pid, std::string processName)
375 {
376 WIFI_LOGD("enter SetWifiBrokerProcess");
377 g_brokerProcessInfo = make_pair(processName, pid);
378 }
379
TimeStats(const std::string desc)380 TimeStats::TimeStats(const std::string desc): m_desc(desc)
381 {
382 m_startTime = std::chrono::steady_clock::now();
383 WIFI_LOGI("[Time stats][start] %{public}s.", m_desc.c_str());
384 }
385
~TimeStats()386 TimeStats::~TimeStats()
387 {
388 auto us = std::chrono::duration_cast<std::chrono::microseconds>
389 (std::chrono::steady_clock::now() - m_startTime).count();
390 constexpr int TIME_BASE = 1000;
391 WIFI_LOGI("[Time stats][end] %{public}s, time cost:%{public}lldus, %{public}lldms, %{public}llds",
392 m_desc.c_str(), us, us / TIME_BASE, us / TIME_BASE / TIME_BASE);
393 }
394 #endif
395
FrequencyToChannel(int freq)396 int FrequencyToChannel(int freq)
397 {
398 WIFI_LOGD("FrequencyToChannel: %{public}d", freq);
399 int channel = INVALID_FREQ_OR_CHANNEL;
400 if (freq >= FREQ_2G_MIN && freq <= FREQ_2G_MAX) {
401 channel = (freq - FREQ_2G_MIN) / CENTER_FREQ_DIFF + CHANNEL_2G_MIN;
402 } else if (freq == CHANNEL_14_FREQ) {
403 channel = CHANNEL_14;
404 } else if (freq >= FREQ_5G_MIN && freq <= FREQ_5G_MAX) {
405 channel = (freq - FREQ_5G_MIN) / CENTER_FREQ_DIFF + CHANNEL_5G_MIN;
406 }
407 return channel;
408 }
409
ChannelToFrequency(int channel)410 int ChannelToFrequency(int channel)
411 {
412 WIFI_LOGI("ChannelToFrequency: %{public}d", channel);
413 if (channel >= MIN_24G_CHANNEL && channel <= MAX_24G_CHANNEL) {
414 return ((channel - MIN_24G_CHANNEL) * CENTER_FREQ_DIFF + FREQ_CHANNEL_1);
415 }
416 if (MIN_5G_CHANNEL <= channel && channel <= MAX_5G_CHANNEL) {
417 return ((channel - MIN_5G_CHANNEL) * CENTER_FREQ_DIFF + FREQ_CHANNEL_36);
418 }
419 return INVALID_FREQ_OR_CHANNEL;
420 }
421
IsOtherVapConnect()422 bool IsOtherVapConnect()
423 {
424 WIFI_LOGD("Enter IsOtherVapConnect");
425 int n;
426 int ret;
427 struct ifaddrs *ifaddr = nullptr;
428 struct ifaddrs *ifa = nullptr;
429 bool p2pOrHmlConnected = false;
430 bool hotspotEnable = false;
431 if (getifaddrs(&ifaddr) == -1) {
432 WIFI_LOGE("getifaddrs failed, error is %{public}d", errno);
433 return false;
434 }
435 for (ifa = ifaddr, n = 0; ifa != nullptr; ifa = ifa->ifa_next, n++) {
436 if (ifa->ifa_addr == nullptr) {
437 continue;
438 }
439 /* For an AF_INET interface address, display the address */
440 int family = ifa->ifa_addr->sa_family;
441 char ipAddress[NI_MAXHOST] = {0}; /* IP address storage */
442 if (family == AF_INET) {
443 ret = getnameinfo(ifa->ifa_addr,
444 sizeof(struct sockaddr_in),
445 ipAddress,
446 NI_MAXHOST,
447 nullptr,
448 0,
449 NI_NUMERICHOST);
450 if (ret != 0) {
451 WIFI_LOGE("getnameinfo() failed: %{public}s\n", gai_strerror(ret));
452 return false;
453 }
454 }
455 if (strncmp("192", ipAddress, PRIFIX_IP_LEN) != 0 && strncmp("172", ipAddress, PRIFIX_IP_LEN) != 0) {
456 continue;
457 }
458 if ((strncmp("p2p", ifa->ifa_name, PRIFIX_P2P_LEN) == 0 ||
459 strncmp("chba", ifa->ifa_name, PRIFIX_CHBA_LEN) == 0)) {
460 p2pOrHmlConnected = true;
461 }
462 if (strncmp("wlan1", ifa->ifa_name, PRIFIX_WLAN1_LEN) == 0) {
463 hotspotEnable = true;
464 }
465 }
466 freeifaddrs(ifaddr);
467 return p2pOrHmlConnected && hotspotEnable;
468 }
469
Hex2num(char c)470 static int Hex2num(char c)
471 {
472 if (c >= '0' && c <= '9') {
473 return c - '0';
474 }
475 if (c >= 'a' && c <= 'f') {
476 return c - 'a' + 10; // convert to decimal
477 }
478 if (c >= 'A' && c <= 'F') {
479 return c - 'A' + 10; // convert to decimal
480 }
481 return -1;
482 }
483
Hex2byte(const char * hex)484 int Hex2byte(const char *hex)
485 {
486 int a = Hex2num(*hex++);
487 if (a < 0) {
488 return -1;
489 }
490 int b = Hex2num(*hex++);
491 if (b < 0) {
492 return -1;
493 }
494 return (a << 4) | b; // convert to binary
495 }
496
HexString2Byte(const char * hex,uint8_t * buf,size_t len)497 int HexString2Byte(const char *hex, uint8_t *buf, size_t len)
498 {
499 size_t i;
500 int a;
501 const char *ipos = hex;
502 uint8_t *opos = buf;
503
504 for (i = 0; i < len; i++) {
505 a = Hex2byte(ipos);
506 if (a < 0) {
507 return -1;
508 }
509 *opos++ = a;
510 ipos += 2; // convert to binary
511 }
512 return 0;
513 }
514
Byte2HexString(const uint8_t * byte,uint8_t bytesLen,char * hexstr,uint8_t hexstrLen)515 void Byte2HexString(const uint8_t* byte, uint8_t bytesLen, char* hexstr, uint8_t hexstrLen)
516 {
517 if ((byte == nullptr) || (hexstr == nullptr)) {
518 WIFI_LOGE("%{public}s: invalid parameter", __func__);
519 return;
520 }
521
522 if (hexstrLen < bytesLen * 2) { // verify length
523 WIFI_LOGE("%{public}s: invalid byteLen:%{public}d or hexStrLen:%{public}d",
524 __func__, bytesLen, hexstrLen);
525 return;
526 }
527
528 WIFI_LOGI("%{public}s byteLen:%{public}d, hexStrLen:%{public}d", __func__, bytesLen, hexstrLen);
529 uint8_t hexstrIndex = 0;
530 for (uint8_t i = 0; i < bytesLen; i++) {
531 if (snprintf_s(hexstr + hexstrIndex, hexstrLen - hexstrIndex, hexstrLen - hexstrIndex - 1,
532 "%02x", byte[i]) <= 0) {
533 WIFI_LOGI("%{public}s: failed to snprintf_s", __func__);
534 }
535 hexstrIndex += 2; // offset
536 if (hexstrIndex >= hexstrLen) {
537 break;
538 }
539 }
540 }
541
DecodeBase64(const std::string & input,std::vector<uint8_t> & output)542 bool DecodeBase64(const std::string &input, std::vector<uint8_t> &output)
543 {
544 #ifndef OHOS_ARCH_LITE
545 WIFI_LOGD("%{public}s input:%{private}s, length:%{public}zu", __func__, input.c_str(), input.length());
546 if (input.length() % BASE64_DEST_UNIT_SIZE != 0) {
547 WIFI_LOGE("%{public}s: wrong data length for base64 encode string", __func__);
548 return false;
549 }
550 uint32_t decodedLen = input.length() * BASE64_SRC_UNIT_SIZE / BASE64_DEST_UNIT_SIZE;
551 if (input.at(input.length() - BASE64_UNIT_ONE_PADDING) == '=') {
552 decodedLen--;
553 if (input.at(input.length() - BASE64_UNIT_TWO_PADDING) == '=') {
554 decodedLen--;
555 }
556 }
557 output.resize(decodedLen);
558
559 BIO *b64 = BIO_new(BIO_f_base64());
560 BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
561 BIO *bio = BIO_new_mem_buf(input.c_str(), input.length());
562 bio = BIO_push(b64, bio);
563 if (BIO_read(bio, &output[0], input.length()) != static_cast<int32_t>(decodedLen)) {
564 WIFI_LOGE("%{public}s: wrong data length for decoded buffer", __func__);
565 return false;
566 }
567 BIO_free_all(bio);
568 #endif
569 return true;
570 }
571
EncodeBase64(const std::vector<uint8_t> & input)572 std::string EncodeBase64(const std::vector<uint8_t> &input)
573 {
574 #ifndef OHOS_ARCH_LITE
575 WIFI_LOGD("%{public}s: size:%{public}zu", __func__, input.size());
576 if (input.empty()) {
577 WIFI_LOGE("%{public}s: wrong data length for string to encode.", __func__);
578 return "";
579 }
580 BIO *b64 = BIO_new(BIO_f_base64());
581 BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
582 BIO *bio = BIO_new(BIO_s_mem());
583 bio = BIO_push(b64, bio);
584 BIO_write(bio, &input[0], input.size());
585 BIO_flush(bio);
586
587 BUF_MEM *bptr = nullptr;
588 BIO_get_mem_ptr(bio, &bptr);
589 std::string output = "";
590 if (bptr != nullptr) {
591 std::vector<char> outputBuffer {};
592 WIFI_LOGI("%{public}s: length is %{public}zu", __func__, bptr->length);
593 outputBuffer.insert(outputBuffer.end(), bptr->data, bptr->data + bptr->length);
594 outputBuffer[bptr->length] = 0;
595 output = static_cast<char*>(&outputBuffer[0]);
596 }
597 BIO_free_all(bio);
598 return output;
599 #else
600 return "";
601 #endif
602 }
603
getAuthInfo(const std::string & input,const std::string & delimiter)604 std::vector<std::string> getAuthInfo(const std::string &input, const std::string &delimiter)
605 {
606 size_t pos = 0;
607 std::string token;
608 std::vector<std::string> results;
609
610 std::string splitStr = input;
611 WIFI_LOGD("%{public}s input:%{private}s, delimiter:%{public}s", __func__, input.c_str(), delimiter.c_str());
612 while ((pos = splitStr.find(delimiter)) != std::string::npos) {
613 token = splitStr.substr(0, pos);
614 if (token.length() > 0) {
615 results.push_back(token);
616 splitStr.erase(0, pos + delimiter.length());
617 WIFI_LOGD("%{public}s token:%{private}s, splitStr:%{public}s", __func__, token.c_str(), splitStr.c_str());
618 }
619 }
620 results.push_back(splitStr);
621 WIFI_LOGD("%{public}s size:%{public}zu", __func__, results.size());
622 return results;
623 }
624
HexToString(const std::string & str)625 std::string HexToString(const std::string &str)
626 {
627 std::string result;
628 uint8_t hexDecimal = 16;
629 uint8_t hexStep = 2;
630 if (str.length() <= 0) {
631 return result;
632 }
633 for (size_t i = 0; i < str.length() - 1; i += STEP_2BIT) {
634 std::string byte = str.substr(i, hexStep);
635 char chr = 0;
636 long strTemp = strtol(byte.c_str(), nullptr, hexDecimal);
637 if (strTemp > 0) {
638 chr = static_cast<char>(strTemp);
639 }
640 result.push_back(chr);
641 }
642 return result;
643 }
644
StringToHex(const std::string & data)645 std::string StringToHex(const std::string &data)
646 {
647 std::stringstream ss;
648 for (std::string::size_type i = 0; i < data.size(); ++i) {
649 unsigned char temp = static_cast<unsigned char>(data[i]) >> HEX_OFFSET;
650 ss << HEX_TABLE[temp] << HEX_TABLE[static_cast<unsigned char>(data[i]) & 0xf];
651 }
652 return ss.str();
653 }
654
CheckDataLegalBin(const std::string & data)655 int CheckDataLegalBin(const std::string &data)
656 {
657 if (data.empty() || data.size() > MAX_INT32_LENGTH_HEX) {
658 WIFI_LOGE("CheckDataLegalBin: invalid data:%{private}s", data.c_str());
659 return 0;
660 }
661
662 std::regex pattern("[0-1]+");
663 if (!std::regex_match(data, pattern)) {
664 return 0;
665 }
666 errno = 0;
667 char *endptr = nullptr;
668 long int num = std::strtol(data.c_str(), &endptr, BASE_HEX);
669 if (errno == ERANGE) {
670 WIFI_LOGE("CheckDataLegalBin errno == ERANGE, data:%{private}s", data.c_str());
671 return 0;
672 }
673
674 return static_cast<int>(num);
675 }
676
CheckDataLegalHex(const std::string & data)677 int CheckDataLegalHex(const std::string &data)
678 {
679 if (data.empty() || data.size() > MAX_INT32_LENGTH_HEX) {
680 WIFI_LOGE("CheckDataLegalHex: invalid data:%{private}s", data.c_str());
681 return 0;
682 }
683
684 std::regex pattern("[0-9|a-f|A-F]+");
685 if (!std::regex_match(data, pattern)) {
686 return 0;
687 }
688 errno = 0;
689 char *endptr = nullptr;
690 long int num = std::strtol(data.c_str(), &endptr, BASE_HEX);
691 if (errno == ERANGE) {
692 WIFI_LOGE("CheckDataLegalHex errno == ERANGE, data:%{private}s", data.c_str());
693 return 0;
694 }
695
696 return static_cast<int>(num);
697 }
698
CheckDataLegal(std::string & data,int base)699 int CheckDataLegal(std::string &data, int base)
700 {
701 if (data.empty() || data.size() > MAX_INT32_LENGTH) {
702 WIFI_LOGE("CheckDataLegal: invalid data:%{private}s", data.c_str());
703 return 0;
704 }
705
706 std::regex pattern("-?\\d+");
707 if (!std::regex_match(data, pattern)) {
708 return 0;
709 }
710 errno = 0;
711 char *endptr = nullptr;
712 long int num = std::strtol(data.c_str(), &endptr, base);
713 if (errno == ERANGE) {
714 WIFI_LOGE("CheckDataLegal errno == ERANGE, data:%{private}s", data.c_str());
715 return 0;
716 }
717
718 return static_cast<int>(num);
719 }
720
CheckDataToUint(std::string & data,int base)721 unsigned int CheckDataToUint(std::string &data, int base)
722 {
723 if (data.empty() || data.size() > MAX_UINT32_LENGTH) {
724 WIFI_LOGE("CheckDataToUint: invalid data:%{private}s", data.c_str());
725 return 0;
726 }
727 std::regex pattern("\\d+");
728 if (!std::regex_match(data, pattern)) {
729 WIFI_LOGE("CheckDataToUint regex unsigned int value fail, data:%{private}s", data.c_str());
730 return 0;
731 }
732
733 errno = 0;
734 char *endptr = nullptr;
735 unsigned long int num = std::strtoul(data.c_str(), &endptr, base);
736 if (errno == ERANGE) {
737 WIFI_LOGE("CheckDataToUint errno == ERANGE, data:%{private}s", data.c_str());
738 return 0;
739 }
740
741 return static_cast<unsigned int>(num);
742 }
743
CheckDataTolonglong(std::string & data,int base)744 long long CheckDataTolonglong(std::string &data, int base)
745 {
746 if (data.empty() || data.size() > MAX_INT64_LENGTH) {
747 WIFI_LOGE("CheckDataTolonglong: invalid data:%{private}s", data.c_str());
748 return 0;
749 }
750
751 std::regex pattern("-?\\d+");
752 if (!std::regex_match(data, pattern)) {
753 return 0;
754 }
755 errno = 0;
756 char *endptr = nullptr;
757 long long int num = std::strtoll(data.c_str(), &endptr, base);
758 if (errno == ERANGE) {
759 WIFI_LOGE("CheckDataTolonglong errno == ERANGE, data:%{private}s", data.c_str());
760 return 0;
761 }
762 return num;
763 }
764 } // namespace Wifi
765 } // namespace OHOS
766