• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 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_hid2d_cfg.h"
17 #include <random>
18 #include <sstream>
19 #include "wifi_logger.h"
20 
21 DEFINE_WIFILOG_P2P_LABEL("WifiHid2dCfg");
22 namespace OHOS {
23 namespace Wifi {
24 static constexpr int INVALID_VALUE_OR_TYPE = -1;
25 static constexpr int INDEX_START = 0;
26 static constexpr int INDEX_LENGTH = 1;
27 static constexpr int INDEX_VALUE = 2;
28 static constexpr int TYPE_VERSION = 1;
29 static constexpr int TYPE_P2P_CHANNEL_OPT = 2;
30 static constexpr int TYPE_DBDC = 3;
31 static constexpr int TYPE_CSA = 4;
32 static constexpr int TYPE_RADAR_DETECT = 5;
33 static constexpr int TYPE_CREATE_DFS_CHANNEL = 6;
34 static constexpr int TYPE_CREATE_INDOOR_CHANNEL = 7;
35 static constexpr int TYPE_CURRENT_STA_CHANNEL = 8;
36 static constexpr int TYPE_CURRENT_AP_IS_PORTAL = 9;
37 static constexpr int TYPE_CURRENT_AP_SSID = 10;
38 static constexpr int TYPE_CURRENT_AP_BSSID = 11;
39 static constexpr int TYPE_CURRENT_STA_HAS_INTERNET = 12;
40 static constexpr int TYPE_P2P_SUPPORT_CHANNEL = 13;
41 static constexpr int TYPE_CURRENT_AP_PASSWORD = 14;
42 static constexpr int TYPE_CURRENT_AP_SECURITY_TYPE = 15;
43 static constexpr int TYPE_CURRENT_AP_ROUTE_TYPE = 16;
44 static constexpr int TYPE_DEVICE_TYPE = 17;
45 static constexpr int TYPE_CURRENT_SESSION_ID_TYPE = 18;
46 static constexpr int TYPE_STA_STATE_FOR_CALLBACK = 1;
47 static constexpr int TYPE_STA_CHANNEL_FOR_CALLBACK = 2;
48 static constexpr int TYPE_AP_SSID_FOR_CALLBACK = 3;
49 static constexpr int TYPE_AP_BSSID_FOR_CALLBACK = 4;
50 static constexpr int LENGTH_OFFSET = 1;
51 static constexpr int VALUE_OFFSET = 2;
52 static constexpr int NORMAL_TYPE_LENGTH = 1; // Most scenes of length(length) in Tlv is 1
53 static constexpr int TYPE_AND_LENGTH = 2;    // Most scenes of length(type + length) is 2
54 static constexpr int TYPICAL_TLV_LENGTH = 3; // Most scenes of length(tpye + length +value) is 3
55 static constexpr int MAX_SSID_LENGTH = 32;
56 static constexpr int MAX_PASSWORD_LENGTH = 64;
57 static constexpr int BSSID_LENGTH = 6;
58 static constexpr int BYTE_MASK = 0xFF;
59 static constexpr int MAX_BYTES = 255;
60 static constexpr int THE_NUM_FROM_CH1_TO_CH11 = 11;
61 static constexpr int DBAC_VERSION = 2;
62 static constexpr int SESSION_ID_LENGTH = 20;
63 static constexpr int CHANNEL_12 = 12;
64 
DeviceWifiInfo()65 DeviceWifiInfo::DeviceWifiInfo()
66 {
67     m_version = DBAC_VERSION;
68     m_isChooseP2pChannelOpt = false;
69     m_isSupportDbdc = false;
70     m_isSupportCsa = false;
71     m_isP2pSupportRadarDetect = false;
72     m_isP2pSupportDfsChannel = false;
73     m_isP2pSupportIndoorChannel = false;
74     m_isPortalAp = false;
75     m_staChannel = 0;
76     m_currentApSsid = "";
77     m_currentApBssid = "";
78     m_isCurrentApHasInternet = false;
79     m_pwd = "";
80     m_sessionId = "";
81     m_securityType = INVALID_VALUE_OR_TYPE;
82     m_routerType = INVALID_VALUE_OR_TYPE;
83     m_deviceType = DeviceClass::Default;
84 }
85 
~DeviceWifiInfo()86 DeviceWifiInfo::~DeviceWifiInfo()
87 {
88 }
89 
GetDeviceClass()90 DeviceClass DeviceWifiInfo::GetDeviceClass()
91 {
92     /* Read from configuration items */
93     return DeviceClass::Default;
94 }
95 
UpdateDeviceCapability()96 void DeviceWifiInfo::UpdateDeviceCapability()
97 {
98     m_isChooseP2pChannelOpt = false;
99     m_isSupportDbdc = false;
100     m_isSupportCsa = false;
101     m_isP2pSupportRadarDetect = false;
102     m_isP2pSupportDfsChannel = false;
103     m_isP2pSupportIndoorChannel = false;
104     m_deviceType = GetDeviceClass();
105 }
106 
ResetWifiDeviceCfg()107 void DeviceWifiInfo::ResetWifiDeviceCfg()
108 {
109     m_staChannel = 0;
110     m_currentApSsid = "";
111     m_currentApBssid = "";
112     m_isCurrentApHasInternet = false;
113     m_pwd = "";
114     m_isPortalAp = false;
115     m_securityType = INVALID_VALUE_OR_TYPE;
116     m_routerType = INVALID_VALUE_OR_TYPE;
117 }
118 
GetVersion()119 int DeviceWifiInfo::GetVersion()
120 {
121     WIFI_LOGI("GetVersion :  %{public}d ", m_version);
122     return m_version;
123 }
124 
SetVerison(int version)125 void DeviceWifiInfo::SetVerison(int version)
126 {
127     if (version <= 0) {
128         return;
129     }
130     m_version = version;
131 }
132 
GetCapsOfChooseP2pChannelOpt()133 bool DeviceWifiInfo::GetCapsOfChooseP2pChannelOpt()
134 {
135     return m_isChooseP2pChannelOpt;
136 }
137 
SetCapsOfChooseP2pChannelOpt(bool isEnabled)138 void DeviceWifiInfo::SetCapsOfChooseP2pChannelOpt(bool isEnabled)
139 {
140     m_isChooseP2pChannelOpt = isEnabled;
141 }
142 
GetCapsOfDbdc()143 bool DeviceWifiInfo::GetCapsOfDbdc()
144 {
145     return m_isSupportDbdc;
146 }
147 
SetCapsOfDbdc(bool isSupportDbdc)148 void DeviceWifiInfo::SetCapsOfDbdc(bool isSupportDbdc)
149 {
150     m_isSupportDbdc = isSupportDbdc;
151 }
152 
GetCapsOfCsa()153 bool DeviceWifiInfo::GetCapsOfCsa()
154 {
155     return m_isSupportCsa;
156 }
157 
SetCapsOfCsa(bool isSupportCsa)158 void DeviceWifiInfo::SetCapsOfCsa(bool isSupportCsa)
159 {
160     m_isSupportCsa = isSupportCsa;
161 }
162 
GetCapsOfP2pRadarDetect()163 bool DeviceWifiInfo::GetCapsOfP2pRadarDetect()
164 {
165     return m_isP2pSupportRadarDetect;
166 }
167 
SetCapsOfP2pRadarDetect(bool isP2pSupportRadarDetect)168 void DeviceWifiInfo::SetCapsOfP2pRadarDetect(bool isP2pSupportRadarDetect)
169 {
170     m_isP2pSupportRadarDetect = isP2pSupportRadarDetect;
171 }
172 
GetCapsOfP2pDfsChannel()173 bool DeviceWifiInfo::GetCapsOfP2pDfsChannel() {
174     return m_isP2pSupportDfsChannel;
175 }
176 
SetCapsOfP2pDfsChannel(bool isP2pSupportDfsChannel)177 void DeviceWifiInfo::SetCapsOfP2pDfsChannel(bool isP2pSupportDfsChannel)
178 {
179     m_isP2pSupportDfsChannel = isP2pSupportDfsChannel;
180 }
181 
GetCapsOfP2pIndoorChannel()182 bool DeviceWifiInfo::GetCapsOfP2pIndoorChannel()
183 {
184     return m_isP2pSupportIndoorChannel;
185 }
186 
SetCapsOfP2pIndoorChannel(bool isP2pSupportIndoorChannel)187 void DeviceWifiInfo::SetCapsOfP2pIndoorChannel(bool isP2pSupportIndoorChannel)
188 {
189     m_isP2pSupportIndoorChannel = isP2pSupportIndoorChannel;
190 }
191 
SetStaChannel(int channel)192 void DeviceWifiInfo::SetStaChannel(int channel)
193 {
194     WIFI_LOGI("Set sta channel: %{public}d ", channel);
195     if (channel < 0) {
196         return;
197     }
198     m_staChannel = channel;
199 }
200 
GetStaChannel()201 int DeviceWifiInfo::GetStaChannel()
202 {
203     return m_staChannel;
204 }
205 
GetApType()206 bool DeviceWifiInfo::GetApType()
207 {
208     return m_isPortalAp;
209 }
210 
SetApType(bool isPortalAp)211 void DeviceWifiInfo::SetApType(bool isPortalAp)
212 {
213     m_isPortalAp = isPortalAp;
214 }
215 
GetCurrentApSsid()216 std::string DeviceWifiInfo::GetCurrentApSsid()
217 {
218     return m_currentApSsid;
219 }
220 
SetCurrentApSsid(const std::string & ssid)221 void DeviceWifiInfo::SetCurrentApSsid(const std::string& ssid)
222 {
223     m_currentApSsid = ssid;
224 }
225 
GetCurrentApBssid()226 std::string DeviceWifiInfo::GetCurrentApBssid() {
227     return m_currentApBssid;
228 }
229 
SetCurrentApBssid(const std::string & bssid)230 void DeviceWifiInfo::SetCurrentApBssid(const std::string& bssid)
231 {
232     m_currentApBssid = bssid;
233 }
234 
SetCurrentApHasInternet(bool hasInternet)235 void DeviceWifiInfo::SetCurrentApHasInternet(bool hasInternet)
236 {
237     m_isCurrentApHasInternet = hasInternet;
238 }
239 
GetCurrentApHasInternet()240 bool DeviceWifiInfo::GetCurrentApHasInternet()
241 {
242     return m_isCurrentApHasInternet;
243 }
244 
GetP2pSupportChannel()245 std::vector<int> DeviceWifiInfo::GetP2pSupportChannel()
246 {
247     return m_P2pSupportChannelList;
248 }
249 
SetP2pSupportChannel(std::vector<int> & channels)250 void DeviceWifiInfo::SetP2pSupportChannel(std::vector<int>& channels)
251 {
252     if (channels.empty()) {
253         return;
254     }
255     m_P2pSupportChannelList = channels;
256 }
257 
GetApPwd()258 std::string DeviceWifiInfo::GetApPwd()
259 {
260     return m_pwd;
261 }
262 
SetApPwd(const std::string & pwd)263 void DeviceWifiInfo::SetApPwd(const std::string& pwd)
264 {
265     m_pwd = pwd;
266 }
267 
GetApSecurityType()268 int DeviceWifiInfo::GetApSecurityType()
269 {
270     return m_securityType;
271 }
272 
SetApSecurityType(int securityType)273 void DeviceWifiInfo::SetApSecurityType(int securityType)
274 {
275     m_securityType = securityType;
276 }
277 
GetRouterType()278 int DeviceWifiInfo::GetRouterType()
279 {
280     return m_routerType;
281 }
282 
GenerateSessionId()283 std::string DeviceWifiInfo::GenerateSessionId()
284 {
285     constexpr int sessionIdSize = 20;
286     constexpr int hexMaxNum = 15;
287     std::random_device rd;
288     std::mt19937 gen(rd());
289     std::uniform_int_distribution<> dis(0, hexMaxNum);
290 
291     std::stringstream ss;
292     ss << std::hex;
293     for (int i = 0; i != sessionIdSize; ++i) {
294         ss << dis(gen);
295     }
296     m_sessionId = ss.str();
297     return m_sessionId;
298 }
299 
GetSessionId()300 std::string DeviceWifiInfo::GetSessionId()
301 {
302     return m_sessionId;
303 }
304 
SetSessionId(std::string sessionId)305 void DeviceWifiInfo::SetSessionId(std::string sessionId)
306 {
307     m_sessionId = sessionId;
308 }
309 
ClearSessionId()310 void DeviceWifiInfo::ClearSessionId()
311 {
312     m_sessionId = "";
313 }
314 
SetRouteType(int routerType)315 void DeviceWifiInfo::SetRouteType(int routerType)
316 {
317     m_routerType = routerType;
318 }
319 
GetDeviceType()320 DeviceClass DeviceWifiInfo::GetDeviceType()
321 {
322     return m_deviceType;
323 }
324 
SetDeviceType(DeviceClass deviceType)325 void DeviceWifiInfo::SetDeviceType(DeviceClass deviceType)
326 {
327     m_deviceType = deviceType;
328 }
329 
GetValueFromType(int type)330 int DeviceWifiInfo::GetValueFromType(int type)
331 {
332     int value = INVALID_VALUE_OR_TYPE;
333     switch (type) {
334         case TYPE_VERSION:
335             value = GetVersion();
336             break;
337         case TYPE_P2P_CHANNEL_OPT:
338             value = GetCapsOfChooseP2pChannelOpt() ? 1 : 0;
339             break;
340         case TYPE_DBDC:
341             value = GetCapsOfDbdc() ? 1 : 0;
342             break;
343         case TYPE_CSA:
344             value = GetCapsOfCsa() ? 1 : 0;
345             break;
346         case TYPE_RADAR_DETECT:
347             value = GetCapsOfP2pRadarDetect() ? 1 : 0;
348             break;
349         case TYPE_CREATE_DFS_CHANNEL:
350             value = GetCapsOfP2pDfsChannel() ? 1 : 0;
351             break;
352         case TYPE_CREATE_INDOOR_CHANNEL:
353             value = GetCapsOfP2pIndoorChannel() ? 1 : 0;
354             break;
355         case TYPE_CURRENT_STA_CHANNEL:
356             value = GetStaChannel();
357             break;
358         case TYPE_CURRENT_AP_IS_PORTAL:
359             value = GetApType() ? 1 : 0;
360             break;
361         default:
362             WIFI_LOGI("GetValueFromType invalid type = %{public}d", type);
363             break;
364     }
365     return value;
366 }
367 
SetDeviceCfg(int type,int inputValue)368 void DeviceWifiInfo::SetDeviceCfg(int type, int inputValue)
369 {
370     switch (type) {
371         case TYPE_VERSION:
372             SetVerison(inputValue);
373             break;
374         case TYPE_P2P_CHANNEL_OPT:
375             SetCapsOfChooseP2pChannelOpt(inputValue == 1);
376             break;
377         case TYPE_DBDC:
378             SetCapsOfDbdc(inputValue == 1);
379             break;
380         case TYPE_CSA:
381             SetCapsOfCsa(inputValue == 1);
382             break;
383         case TYPE_RADAR_DETECT:
384             SetCapsOfP2pRadarDetect(inputValue == 1);
385             break;
386         case TYPE_CREATE_DFS_CHANNEL:
387             SetCapsOfP2pDfsChannel(inputValue == 1);
388             break;
389         case TYPE_CREATE_INDOOR_CHANNEL:
390             SetCapsOfP2pIndoorChannel(inputValue == 1);
391             break;
392         case TYPE_CURRENT_STA_CHANNEL:
393             SetStaChannel(inputValue);
394             break;
395         case TYPE_CURRENT_AP_IS_PORTAL:
396             SetApType(inputValue == 1);
397             break;
398         default:
399             WIFI_LOGI("SetDeviceCfg invalid type = %{public}d", type);
400             break;
401     }
402 }
403 
WifiHid2dCfg()404 WifiHid2dCfg::WifiHid2dCfg()
405 {
406 }
407 
~WifiHid2dCfg()408 WifiHid2dCfg::~WifiHid2dCfg()
409 {
410 }
411 
GetInstance()412 WifiHid2dCfg& WifiHid2dCfg::GetInstance()
413 {
414     static WifiHid2dCfg inst;
415     return inst;
416 }
417 
418 DeviceWifiInfo WifiHid2dCfg::m_selfDeviceInfo;
419 DeviceWifiInfo WifiHid2dCfg::m_peerDeviceInfo;
420 
GetSelfDeviceCfgInfo()421 DeviceWifiInfo& WifiHid2dCfg::GetSelfDeviceCfgInfo()
422 {
423     return m_selfDeviceInfo;
424 }
425 
GetPeerDeviceCfgInfo()426 DeviceWifiInfo& WifiHid2dCfg::GetPeerDeviceCfgInfo()
427 {
428     return m_peerDeviceInfo;
429 }
430 
ParseStringFromByteArray(char * data,int dataLen,int index,int maxLength)431 std::string WifiHid2dCfg::ParseStringFromByteArray(char* data, int dataLen, int index, int maxLength)
432 {
433     if (data == nullptr || dataLen < index + INDEX_VALUE) {
434         return "";
435     }
436     int length = data[index + INDEX_LENGTH] & BYTE_MASK;
437     if (length > maxLength + 1) { /* +1 for the end character '\0' of the C-style string */
438         WIFI_LOGE("invalid length = %{public}d", length);
439         return "";
440     }
441 
442     char* ssidArray = new char[maxLength + 1]; /* +1 for the end character '\0' of the C-style string */
443     if (ssidArray == nullptr) {
444         return "";
445     }
446     if (memcpy_s(ssidArray, maxLength + 1, data + index + INDEX_VALUE, length) != EOK) {
447         WIFI_LOGE("parse string from byte array memcpy_s failed!");
448         delete[] ssidArray;
449         return "";
450     }
451 
452     int needCopylen = FindIndexFromByteArray(ssidArray, maxLength + 1, 0);
453     std::string s(needCopylen + 1, '\0');
454     for (int i = 0; i <= needCopylen && i < maxLength + 1; ++i) {
455         s[i] = ssidArray[i];
456     }
457     delete[] ssidArray;
458     return s;
459 }
460 
461 /** 2.4g channel count from channel 1 to channel 11 */
ParseP2pSupportChannelFromByteArray(char * data,int dataLen,int index,std::vector<int> & p2pSupportChannels)462 void WifiHid2dCfg::ParseP2pSupportChannelFromByteArray(char* data, int dataLen,
463     int index, std::vector<int>& p2pSupportChannels)
464 {
465     if (data == nullptr || dataLen < (index + INDEX_VALUE)) {
466         return;
467     }
468 
469     int length = data[index + LENGTH_OFFSET] & BYTE_MASK;
470     if (dataLen < (index + length)) {
471         return;
472     }
473     // To save space, channels 1 to 11 are not carried when the peer information is obtained.
474     // channels 1 to 11 are supported by all countries, p2pSupportChannels should include it
475     int i = 0;
476     for (i = 0; i < THE_NUM_FROM_CH1_TO_CH11; i++) {
477         p2pSupportChannels.emplace_back(i + 1);
478     }
479     for (int j = 0; j < data[index + LENGTH_OFFSET]; j++) {
480         p2pSupportChannels.emplace_back(data[index + VALUE_OFFSET + j] & BYTE_MASK);
481     }
482     std::sort(p2pSupportChannels.begin(), p2pSupportChannels.end());
483 }
484 
HandlePeerApPassword()485 void WifiHid2dCfg::HandlePeerApPassword()
486 {
487 }
488 
HandleTlvData(int type,char * cfgData,int cfgDataLen,int index)489 void WifiHid2dCfg::HandleTlvData(int type, char* cfgData, int cfgDataLen, int index)
490 {
491     std::vector<int> p2pSupportChannels;
492     switch (type) {
493         case TYPE_CURRENT_AP_SSID:
494             m_peerDeviceInfo.SetCurrentApSsid(ParseStringFromByteArray(cfgData, cfgDataLen, index, MAX_SSID_LENGTH));
495             break;
496         case TYPE_CURRENT_AP_BSSID:
497             unsigned char macAddr[BSSID_LENGTH];
498             if (memcpy_s(macAddr, BSSID_LENGTH, cfgData + index + INDEX_VALUE, BSSID_LENGTH) != EOK) {
499                 return;
500             }
501             m_peerDeviceInfo.SetCurrentApBssid(MacArrayToStr(macAddr));
502             break;
503         case TYPE_CURRENT_STA_HAS_INTERNET:
504             m_peerDeviceInfo.SetCurrentApHasInternet((cfgData[index + VALUE_OFFSET] & BYTE_MASK) == 0x01);
505             break;
506         case TYPE_P2P_SUPPORT_CHANNEL:
507             ParseP2pSupportChannelFromByteArray(cfgData, cfgDataLen, index, p2pSupportChannels);
508             m_peerDeviceInfo.SetP2pSupportChannel(p2pSupportChannels);
509             break;
510         case TYPE_CURRENT_AP_PASSWORD:
511             m_peerDeviceInfo.SetApPwd(ParseStringFromByteArray(cfgData, cfgDataLen, index, MAX_PASSWORD_LENGTH));
512             break;
513         case TYPE_CURRENT_AP_SECURITY_TYPE:
514             m_peerDeviceInfo.SetApSecurityType(cfgData[index + VALUE_OFFSET] & BYTE_MASK);
515             break;
516         case TYPE_CURRENT_AP_ROUTE_TYPE:
517             m_peerDeviceInfo.SetRouteType(cfgData[index + VALUE_OFFSET] & BYTE_MASK);
518             break;
519         case TYPE_DEVICE_TYPE:
520             m_peerDeviceInfo.SetDeviceType(DeviceClass(cfgData[index + VALUE_OFFSET] & BYTE_MASK));
521             break;
522         case TYPE_CURRENT_SESSION_ID_TYPE:
523             m_peerDeviceInfo.SetSessionId(ParseStringFromByteArray(cfgData, cfgDataLen, index, SESSION_ID_LENGTH));
524             break;
525         default:
526             WIFI_LOGE("handle tlv data invalid type = %{public}d", type);
527             return;
528     }
529 }
530 
ParsePeerDeviceCfgInfo(PeerCfgType cfgType,char * cfgData,int cfgDataLen)531 int WifiHid2dCfg::ParsePeerDeviceCfgInfo(PeerCfgType cfgType, char* cfgData, int cfgDataLen)
532 {
533     if (cfgData == nullptr || cfgDataLen == 0) {
534         return INVALID_VALUE_OR_TYPE;
535     }
536     if (cfgType != PeerCfgType::TYPE_OF_SET_PEER_CONFIG) {
537         return INVALID_VALUE_OR_TYPE;
538     }
539     m_peerDeviceInfo.ResetWifiDeviceCfg();
540     int length = cfgData[INDEX_START] & BYTE_MASK;
541     if (cfgDataLen != length) {
542         return INVALID_VALUE_OR_TYPE;
543     }
544 
545     WIFI_LOGI("parse peer device cfg length = %{public}d", length);
546     for (int i = 1; i < length;) {
547         if ((i + LENGTH_OFFSET) >= length) {
548             break;
549         }
550         int valueLength = cfgData[i + LENGTH_OFFSET] & BYTE_MASK;
551         if ((i + valueLength + TYPE_AND_LENGTH) > length) {
552             break;
553         }
554         int type = cfgData[i];
555         int valueIndex = i + VALUE_OFFSET;
556         if (type > 0 && type <= TYPE_CURRENT_AP_IS_PORTAL && valueIndex < length) {
557             m_peerDeviceInfo.SetDeviceCfg(type, cfgData[valueIndex] & BYTE_MASK);
558             i += valueLength + TYPE_AND_LENGTH;
559             continue;
560         }
561         HandleTlvData(type, cfgData, cfgDataLen, i);
562         i += valueLength + TYPE_AND_LENGTH;
563     }
564 
565     if (m_peerDeviceInfo.GetApSecurityType() != INVALID_VALUE_OR_TYPE) {
566         HandlePeerApPassword();
567     }
568     return 0;
569 }
570 
ParsePeerDeviceStaChanngeInfo(PeerCfgType cfgType,char * cfgData,int cfgDataLen)571 int WifiHid2dCfg::ParsePeerDeviceStaChanngeInfo(PeerCfgType cfgType, char* cfgData, int cfgDataLen)
572 {
573     if (cfgData == nullptr || cfgDataLen == 0) {
574         return INVALID_VALUE_OR_TYPE;
575     }
576     if (cfgType != PeerCfgType::TYPE_OF_SET_PEER_STATE_CHANGE) {
577         return INVALID_VALUE_OR_TYPE;
578     }
579     if (cfgDataLen != cfgData[0]) {
580         return INVALID_VALUE_OR_TYPE;
581     }
582     for (int i = 1; i < cfgDataLen;) {
583         int type = cfgData[i];
584         switch (type) {
585             case TYPE_STA_STATE_FOR_CALLBACK:
586             case TYPE_STA_CHANNEL_FOR_CALLBACK:
587             case TYPE_AP_SSID_FOR_CALLBACK:
588             case TYPE_AP_BSSID_FOR_CALLBACK:
589             default:
590                 break;
591         }
592         i += (cfgData[i + LENGTH_OFFSET] & BYTE_MASK) + TYPE_AND_LENGTH;
593     }
594     return 0;
595 }
596 
FindIndexFromByteArray(char * data,int dataLen,int value)597 int WifiHid2dCfg::FindIndexFromByteArray(char* data, int dataLen, int value)
598 {
599     if (data == nullptr) {
600         return 0;
601     }
602     int i = 0;
603     for (i = 0; i < dataLen; i++) {
604         if (data[i] == value) {
605             return i;
606         }
607     }
608     return i;
609 }
610 
SetBssidByte(int typeBssidValue,char * dataArray,int dataArrayLen,int offset)611 int WifiHid2dCfg::SetBssidByte(int typeBssidValue, char* dataArray, int dataArrayLen, int offset)
612 {
613     if (dataArray == nullptr) {
614         return 0;
615     }
616     int length = INDEX_VALUE + BSSID_LENGTH;
617     if (dataArrayLen < (offset + length)) {
618         return 0;
619     }
620     dataArray[offset] = (char)typeBssidValue;
621     std::string bssid = m_selfDeviceInfo.GetCurrentApBssid();
622     dataArray[offset + INDEX_LENGTH] = BSSID_LENGTH;
623 
624     unsigned char macByteAddr[BSSID_LENGTH] = { 0 };
625     if (!bssid.empty()) {
626         if (MacStrToArray(bssid, macByteAddr) != EOK) {
627             return 0;
628         }
629     }
630 
631     if (memcpy_s(dataArray + offset + INDEX_VALUE, dataArrayLen - (offset + INDEX_VALUE),
632         macByteAddr, BSSID_LENGTH) != EOK) {
633         return 0;
634     }
635     return length;
636 }
637 
SetP2pSupportChannelByte(char * dataArray,int dataArrayLen,int offset)638 int WifiHid2dCfg::SetP2pSupportChannelByte(char* dataArray, int dataArrayLen, int offset)
639 {
640     if (dataArray == nullptr || dataArrayLen < (offset + INDEX_LENGTH)) {
641         return 0;
642     }
643     std::vector<int> p2pSupportChannelList = m_selfDeviceInfo.GetP2pSupportChannel();
644     if (p2pSupportChannelList.empty() || (p2pSupportChannelList.size() - THE_NUM_FROM_CH1_TO_CH11 <= 0)) {
645         WIFI_LOGI("Channel list is invalid.");
646         return 0;
647     }
648     dataArray[offset] = TYPE_P2P_SUPPORT_CHANNEL;
649     int length = p2pSupportChannelList.size() - THE_NUM_FROM_CH1_TO_CH11;
650     dataArray[offset + INDEX_LENGTH] = (char)length;
651     if (dataArrayLen < (offset + length + INDEX_VALUE)) {
652         return 0;
653     }
654     int index = 0;
655     for (int channel : p2pSupportChannelList) {
656         // To save space, channels 1 to 11 are not carried when exchanging information with the peer device for
657         // Channels 1 to 11 are supported by all countries and dataArray should not contains channel 1 to 11
658         if (channel >= CHANNEL_12) {
659             dataArray[offset + INDEX_VALUE + index] = (char)channel;
660             index++;
661         }
662     }
663     return length + VALUE_OFFSET;
664 }
665 
BuildTlvForIntVal(int type,int Value,char * tlvData,int tlvDataLen,int offset)666 int WifiHid2dCfg::BuildTlvForIntVal(int type, int Value, char* tlvData, int tlvDataLen, int offset)
667 {
668     if (tlvData == nullptr) {
669         return 0;
670     }
671     if (tlvDataLen <= (offset + INDEX_VALUE)) {
672         return 0;
673     }
674     tlvData[offset] = (char)type;
675     tlvData[offset + INDEX_LENGTH] = NORMAL_TYPE_LENGTH;
676     tlvData[offset + INDEX_VALUE] = (char)Value;
677     return TYPICAL_TLV_LENGTH;
678 }
679 
BuildTlvForStrVal(int type,std::string value,char * tlvData,int tlvDataLen,int offset)680 int WifiHid2dCfg::BuildTlvForStrVal(int type, std::string value, char* tlvData, int tlvDataLen, int offset)
681 {
682     if (tlvData == nullptr) {
683         return 0;
684     }
685     if (value.empty() || (type == TYPE_CURRENT_AP_PASSWORD && value.length() > MAX_PASSWORD_LENGTH) ||
686         (type == TYPE_CURRENT_AP_SSID && value.length() > MAX_SSID_LENGTH)) {
687         tlvData[offset] = (char)type;
688         tlvData[offset + LENGTH_OFFSET] = (char)NORMAL_TYPE_LENGTH;
689         tlvData[offset + VALUE_OFFSET] = 0;
690         return TYPICAL_TLV_LENGTH;
691     }
692 
693     /* +1 for the end character '\0' of the C-style string */
694     if (tlvDataLen < offset + value.length() + 1) {
695         return 0;
696     }
697     tlvData[offset] = (char)type;
698     /* +1 for the end character '\0' of the C-style string */
699     tlvData[offset + LENGTH_OFFSET] = (char)value.length() + 1;
700     if (memcpy_s(tlvData + offset + VALUE_OFFSET, tlvDataLen - (offset + VALUE_OFFSET),
701         value.c_str(), value.length() + 1) != EOK) {
702         return 0;
703     }
704     return tlvData[offset + LENGTH_OFFSET] + TYPE_AND_LENGTH;
705 }
706 
HandlePeerStaStateChange(char * data,int dataLen,int index)707 void WifiHid2dCfg::HandlePeerStaStateChange(char* data, int dataLen, int index)
708 {
709     if (data == nullptr || dataLen <= (index + INDEX_VALUE)) {
710         return;
711     }
712     if (data[index + INDEX_VALUE] == 0) { // 0 : disconnect
713         m_peerDeviceInfo.ResetWifiDeviceCfg();
714     }
715 }
716 
GetSelfDeviceCfg(SelfCfgType cfgType,char cfgInfo[CFG_DATA_MAX_BYTES],int & getDatValidLen)717 void WifiHid2dCfg::GetSelfDeviceCfg(SelfCfgType cfgType, char cfgInfo[CFG_DATA_MAX_BYTES], int& getDatValidLen)
718 {
719     getDatValidLen = 0;
720     if ((cfgType != SelfCfgType::TYPE_OF_GET_SELF_CONFIG &&
721         cfgType != SelfCfgType::TYPE_OF_GET_SELF_CONFIG_WITH_PASSWORD)) {
722         return;
723     }
724 
725     char* totalCfgInfo = new char[MAX_BYTES];
726     if (totalCfgInfo == nullptr) {
727         return;
728     }
729     if (memset_s(totalCfgInfo, MAX_BYTES, 0, MAX_BYTES) != EOK) {
730         delete[] totalCfgInfo;
731         return;
732     }
733 
734     int i = 1;
735     int position = 1;
736     for (i = 1; i <= TYPE_CURRENT_AP_IS_PORTAL; i++) {
737         position += BuildTlvForIntVal(i, m_selfDeviceInfo.GetValueFromType(i), totalCfgInfo, MAX_BYTES, position);
738     }
739 
740     std::string ssid = m_selfDeviceInfo.GetCurrentApSsid();
741     position += BuildTlvForStrVal(TYPE_CURRENT_AP_SSID, ssid, totalCfgInfo, MAX_BYTES, position);
742 
743     position += SetBssidByte(TYPE_CURRENT_AP_BSSID, totalCfgInfo, MAX_BYTES, position);
744 
745     position += BuildTlvForIntVal(TYPE_CURRENT_STA_HAS_INTERNET, m_selfDeviceInfo.GetCurrentApHasInternet() ? 1 : 0,
746         totalCfgInfo, MAX_BYTES, position);
747 
748     position += SetP2pSupportChannelByte(totalCfgInfo, MAX_BYTES, position);
749     if (cfgType == SelfCfgType::TYPE_OF_GET_SELF_CONFIG_WITH_PASSWORD) {
750         std::string pwd = m_selfDeviceInfo.GetApPwd();
751         position += BuildTlvForStrVal(TYPE_CURRENT_AP_PASSWORD, pwd, totalCfgInfo, MAX_BYTES, position);
752         position += BuildTlvForIntVal(TYPE_CURRENT_AP_SECURITY_TYPE, m_selfDeviceInfo.GetApSecurityType(),
753             totalCfgInfo, MAX_BYTES, position);
754     }
755 
756     position += BuildTlvForIntVal(TYPE_CURRENT_AP_ROUTE_TYPE, m_selfDeviceInfo.GetRouterType(),
757         totalCfgInfo, MAX_BYTES, position);
758 
759     position += BuildTlvForIntVal(TYPE_DEVICE_TYPE, static_cast<int>(m_selfDeviceInfo.GetDeviceType()),
760         totalCfgInfo, MAX_BYTES, position);
761 
762     std::string sessionID = m_selfDeviceInfo.GenerateSessionId();
763     position += BuildTlvForStrVal(TYPE_CURRENT_SESSION_ID_TYPE, sessionID, totalCfgInfo, MAX_BYTES, position);
764 
765     totalCfgInfo[INDEX_START] = (char)position;
766     getDatValidLen = totalCfgInfo[INDEX_START] & BYTE_MASK;
767     WIFI_LOGI("self device cfg length = %{public}d", getDatValidLen);
768     if (getDatValidLen <= 0) {
769         getDatValidLen = 0;
770         delete[] totalCfgInfo;
771         return;
772     }
773     if (memcpy_s(cfgInfo, CFG_DATA_MAX_BYTES, totalCfgInfo, getDatValidLen) != EOK) {
774         WIFI_LOGI("GetSelfDeviceCfg  memcpy_s failed!");
775         getDatValidLen = 0;
776     }
777     delete[] totalCfgInfo;
778 }
779 
Hid2dSetPeerWifiCfgInfo(PeerCfgType cfgType,char cfgInfo[CFG_DATA_MAX_BYTES],int setDataValidLen)780 int WifiHid2dCfg::Hid2dSetPeerWifiCfgInfo(PeerCfgType cfgType, char cfgInfo[CFG_DATA_MAX_BYTES], int setDataValidLen)
781 {
782     WIFI_LOGI("Hid2dSetPeerWifiCfgInfo  cfgType = %{public}d", cfgType);
783     if (cfgType == PeerCfgType::TYPE_OF_SET_PEER_CONFIG) {
784         return ParsePeerDeviceCfgInfo(cfgType, cfgInfo, setDataValidLen);
785     }
786     else if (cfgType == PeerCfgType::TYPE_OF_SET_PEER_STATE_CHANGE) {
787         return ParsePeerDeviceStaChanngeInfo(cfgType, cfgInfo, setDataValidLen);
788     } else {
789         return INVALID_VALUE_OR_TYPE;
790     }
791 }
792 }  // namespace Wifi
793 }  // namespace OHOS