• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021 HiSilicon (Shanghai) Technologies CO., LIMITED.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
17  */
18 
19 /* ****************************************************************************
20   1 头文件包含
21 **************************************************************************** */
22 #include "oal_ext_if.h"
23 #include "oam_ext_if.h"
24 #include "hmac_ext_if.h"
25 #include "wal_cfg80211.h"
26 #include "wal_scan.h"
27 #include "wal_main.h"
28 #include "wal_regdb.h"
29 #include "wal_ioctl.h"
30 #include "wal_hipriv.h"
31 #include "net_adpater.h"
32 #include "wal_customize.h"
33 #include "mac_ie.h"
34 #include "wal_event_msg.h"
35 #include "wal_cfg80211_apt.h"
36 #include "hdf_wifi_event.h"
37 #include "plat_pm_wlan.h"
38 #include "hi_config.h"
39 #include "net_device.h"
40 
41 #ifdef __cplusplus
42 #if __cplusplus
43 extern "C" {
44 #endif
45 #endif
46 
47 extern hi_u32 hi_get_tick(hi_void);
48 
49 /* ****************************************************************************
50   2 全局变量定义
51 **************************************************************************** */
52 #define WIFI_G_RATES           (g_wifi_rates + 0)
53 #define WIFI_G_RATES_SIZE      12
54 #define WIFI_ROC_TIMEOUT       200
55 
56 /* 设备支持的速率 */
57 static oal_ieee80211_rate g_wifi_rates[] = {
58     ratetab_ent(10,  0x1,   0),
59     ratetab_ent(20,  0x2,   0),
60     ratetab_ent(55,  0x4,   0),
61     ratetab_ent(110, 0x8,   0),
62     ratetab_ent(60,  0x10,  0),
63     ratetab_ent(90,  0x20,  0),
64     ratetab_ent(120, 0x40,  0),
65     ratetab_ent(180, 0x80,  0),
66     ratetab_ent(240, 0x100, 0),
67     ratetab_ent(360, 0x200, 0),
68     ratetab_ent(480, 0x400, 0),
69     ratetab_ent(540, 0x800, 0),
70 };
71 
72 /* 2.4G 频段 */
73 oal_ieee80211_channel g_wifi_2ghz_channels[] = {
74     chan2g(1, 2412, 0),
75     chan2g(2, 2417, 0),
76     chan2g(3, 2422, 0),
77     chan2g(4, 2427, 0),
78     chan2g(5, 2432, 0),
79     chan2g(6, 2437, 0),
80     chan2g(7, 2442, 0),
81     chan2g(8, 2447, 0),
82     chan2g(9, 2452, 0),
83     chan2g(10, 2457, 0),
84     chan2g(11, 2462, 0),
85     chan2g(12, 2467, 0),
86     chan2g(13, 2472, 0),
87     chan2g(14, 2484, 0),
88 };
89 
90 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
91 /* 设备支持的加密套件 */
92 static const hi_u32 g_wifi_cipher_suites[] = {
93     WLAN_CIPHER_SUITE_WEP40,
94     WLAN_CIPHER_SUITE_WEP104,
95     WLAN_CIPHER_SUITE_TKIP,
96     WLAN_CIPHER_SUITE_CCMP,
97     WLAN_CIPHER_SUITE_AES_CMAC,
98     WLAN_CIPHER_SUITE_SMS4,
99 };
100 #endif
101 
102 /* 2.4G 频段信息 */
103 static oal_ieee80211_supported_band g_wifi_band_2ghz = {
104     .channels   = g_wifi_2ghz_channels,
105     .n_channels = sizeof(g_wifi_2ghz_channels) / sizeof(oal_ieee80211_channel),
106     .bitrates   = WIFI_G_RATES,
107     .n_bitrates = WIFI_G_RATES_SIZE,
108     .ht_cap = {
109         .ht_supported = HI_TRUE,
110         .cap = IEEE80211_HT_CAP_SUP_WIDTH_20_40 | IEEE80211_HT_CAP_SGI_20 | IEEE80211_HT_CAP_SGI_40,
111     },
112 };
113 
114 #ifdef _PRE_WLAN_FEATURE_P2P
115 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
116 oal_workqueue_stru *g_del_virtual_inf_workqueue = HI_NULL;
117 
118 static oal_ieee80211_iface_limit g_sta_p2p_limits[] = {
119     {
120         .max = 2,
121         .types = bit(NL80211_IFTYPE_STATION),
122     },
123     /* 1131添加一个AP类型接口 */
124     {
125         .max = 1,
126         .types = bit(NL80211_IFTYPE_AP),
127     },
128     {
129         .max = 2,
130         .types = bit(NL80211_IFTYPE_P2P_GO) | BIT(NL80211_IFTYPE_P2P_CLIENT),
131     },
132 #ifdef _PRE_WLAN_FEATURE_MESH
133     {
134         .max = 1,
135         .types = bit(NL80211_IFTYPE_MESH_POINT),
136     },
137 #endif
138 };
139 
140 static oal_ieee80211_iface_combination
141 g_sta_p2p_iface_combinations[] = {
142     {
143         .num_different_channels = 2,
144         .max_interfaces = 3,
145         .limits = g_sta_p2p_limits,
146         .n_limits = hi_array_size(g_sta_p2p_limits),
147     },
148 };
149 
150 /* There isn't a lot of sense in it, but you can transmit anything you like */
151 static const struct ieee80211_txrx_stypes
152 g_wal_cfg80211_default_mgmt_stypes[NUM_NL80211_IFTYPES] = {
153     [NL80211_IFTYPE_ADHOC] = {
154         .tx = 0xffff,
155         .rx = bit(IEEE80211_STYPE_ACTION >> 4)
156     },
157     [NL80211_IFTYPE_STATION] = {
158         .tx = 0xffff,
159         .rx = bit(IEEE80211_STYPE_ACTION >> 4) |
160         bit(IEEE80211_STYPE_PROBE_REQ >> 4)
161     },
162     [NL80211_IFTYPE_AP] = {
163         .tx = 0xffff,
164         .rx = bit(IEEE80211_STYPE_ASSOC_REQ >> 4) |
165         bit(IEEE80211_STYPE_REASSOC_REQ >> 4) |
166         bit(IEEE80211_STYPE_PROBE_REQ >> 4) |
167         bit(IEEE80211_STYPE_DISASSOC >> 4) |
168         bit(IEEE80211_STYPE_AUTH >> 4) |
169         bit(IEEE80211_STYPE_DEAUTH >> 4) |
170         bit(IEEE80211_STYPE_ACTION >> 4)
171     },
172     [NL80211_IFTYPE_AP_VLAN] = {
173         /* copy AP */
174         .tx = 0xffff,
175         .rx = bit(IEEE80211_STYPE_ASSOC_REQ >> 4) |
176         bit(IEEE80211_STYPE_REASSOC_REQ >> 4) |
177         bit(IEEE80211_STYPE_PROBE_REQ >> 4) |
178         bit(IEEE80211_STYPE_DISASSOC >> 4) |
179         bit(IEEE80211_STYPE_AUTH >> 4) |
180         bit(IEEE80211_STYPE_DEAUTH >> 4) |
181         bit(IEEE80211_STYPE_ACTION >> 4)
182     },
183 #if defined(_PRE_WLAN_FEATURE_P2P)
184     [NL80211_IFTYPE_P2P_CLIENT] = {
185         .tx = 0xffff,
186         .rx = bit(IEEE80211_STYPE_ACTION >> 4) |
187         bit(IEEE80211_STYPE_PROBE_REQ >> 4)
188     },
189     [NL80211_IFTYPE_P2P_GO] = {
190         .tx = 0xffff,
191         .rx = bit(IEEE80211_STYPE_ASSOC_REQ >> 4) |
192         bit(IEEE80211_STYPE_REASSOC_REQ >> 4) |
193         bit(IEEE80211_STYPE_PROBE_REQ >> 4) |
194         bit(IEEE80211_STYPE_DISASSOC >> 4) |
195         bit(IEEE80211_STYPE_AUTH >> 4) |
196         bit(IEEE80211_STYPE_DEAUTH >> 4) |
197         bit(IEEE80211_STYPE_ACTION >> 4)
198     },
199     [NL80211_IFTYPE_P2P_DEVICE] = {
200         .tx = 0xffff,
201         .rx = bit(IEEE80211_STYPE_ACTION >> 4) |
202         bit(IEEE80211_STYPE_PROBE_REQ >> 4)
203     },
204 #endif /* WL_CFG80211_P2P_DEV_IF */
205 #ifdef _PRE_WLAN_FEATURE_MESH
206     [NL80211_IFTYPE_MESH_POINT] = {
207         .tx = 0xffff,
208         .rx = bit(IEEE80211_STYPE_ASSOC_REQ >> 4) |
209         bit(IEEE80211_STYPE_REASSOC_REQ >> 4) |
210         bit(IEEE80211_STYPE_PROBE_REQ >> 4) |
211         bit(IEEE80211_STYPE_DISASSOC >> 4) |
212         bit(IEEE80211_STYPE_AUTH >> 4) |
213         bit(IEEE80211_STYPE_DEAUTH >> 4) |
214         bit(IEEE80211_STYPE_ACTION >> 4)
215     },
216 #endif
217 };
218 #endif
219 #endif
220 
221 hi_u8               g_cookie_array_bitmap = 0;   /* 每个bit 表示cookie array 中是否使用,1 - 已使用;0 - 未使用 */
222 cookie_arry_stru    g_cookie_array[WAL_COOKIE_ARRAY_SIZE];
223 
224 /* insmod 设置vap mode */
225 int g_mode = WAL_WIFI_MODE_STA; /* wifi 默认STA_AP 共存模式 */
226 module_param(g_mode, int, 0644);
227 /* insmod 设置vap bandwith */
228 int g_bw = WAL_WIFI_BW_LEGACY_20M;
229 module_param(g_bw, int, 0644);
230 /* insmod 设置vap protocol */
231 int g_proto = WAL_PHY_MODE_11N;
232 module_param(g_proto, int, 0644);
233 
234 /* ****************************************************************************
235   3 函数实现
236 **************************************************************************** */
wal_get_g_wifi_2ghz_channels(hi_void)237 oal_ieee80211_channel *wal_get_g_wifi_2ghz_channels(hi_void)
238 {
239     return g_wifi_2ghz_channels;
240 }
241 
242 #ifdef _PRE_WLAN_FEATURE_P2P
243 /* ****************************************************************************
244  函 数 名  : wal_is_p2p_group_exist
245  功能描述  : 检查是否存在P2P group
246  输入参数  : mac_device_stru *pst_mac_device
247  输出参数  : 无
248  返 回 值  : static hi_u32 HI_TRUE    存在P2P group
249                            HI_FALSE   不存在P2P group
250  调用函数  :
251  被调函数  :
252 
253  修改历史      :
254   1.日    期   : 2015年9月28日
255     作    者   : HiSilicon
256     修改内容   : 新生成函数
257 
258 **************************************************************************** */
wal_is_p2p_group_exist(mac_device_stru * mac_dev)259 static hi_u32 wal_is_p2p_group_exist(mac_device_stru *mac_dev)
260 {
261     if (hmac_p2p_check_vap_num(mac_dev, WLAN_P2P_GO_MODE) != HI_SUCCESS ||
262         hmac_p2p_check_vap_num(mac_dev, WLAN_P2P_CL_MODE) != HI_SUCCESS) {
263         return HI_TRUE;
264     } else {
265         return HI_FALSE;
266     }
267 }
268 /* ****************************************************************************
269  函 数 名  : wal_del_p2p_group
270  功能描述  : 删除P2P group
271  输入参数  : mac_device_stru *pst_mac_device
272  输出参数  : 无
273  返 回 值  : static hi_void
274  调用函数  :
275  被调函数  :
276 
277  修改历史      :
278   1.日    期   : 2015年9月28日
279     作    者   : HiSilicon
280     修改内容   : 新生成函数
281 
282 **************************************************************************** */
wal_del_p2p_group(const mac_device_stru * mac_dev)283 hi_u32 wal_del_p2p_group(const mac_device_stru *mac_dev)
284 {
285     mac_vap_stru        *mac_vap  = HI_NULL;
286     hmac_vap_stru       *hmac_vap = HI_NULL;
287     oal_net_device_stru *netdev   = HI_NULL;
288 
289     for (hi_u8 vap_idx = 0; vap_idx < mac_dev->vap_num; vap_idx++) {
290         mac_vap = mac_vap_get_vap_stru(mac_dev->auc_vap_id[vap_idx]);
291         if (oal_unlikely(mac_vap == HI_NULL)) {
292             oam_warning_log1(0, OAM_SF_P2P, "{wal_del_p2p_group::mac vap Err! vapId = %u}",
293                 mac_dev->auc_vap_id[vap_idx]);
294             continue;
295         }
296 
297         hmac_vap = hmac_vap_get_vap_stru(mac_dev->auc_vap_id[vap_idx]);
298         if (oal_unlikely(hmac_vap == HI_NULL)) {
299             oam_warning_log1(0, OAM_SF_P2P, "{wal_del_p2p_group::get hmac vap resource failed! vap id is %u}",
300                 mac_dev->auc_vap_id[vap_idx]);
301             continue;
302         }
303 
304         netdev = hmac_vap->net_device;
305         if (oal_unlikely(netdev == HI_NULL)) {
306             oam_warning_log1(0, OAM_SF_P2P, "{wal_del_p2p_group::netdev Err! vap id = %u}",
307                 mac_dev->auc_vap_id[vap_idx]);
308             continue;
309         }
310 
311         if (is_p2p_go(mac_vap) || is_p2p_cl(mac_vap)) {
312 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
313             mac_cfg_del_vap_param_stru del_vap_param;
314 
315             /* 规则6.6:禁止使用内存操作类危险函数 例外(1)对固定长度的数组进行初始化 */
316             memset_s(&del_vap_param, sizeof(del_vap_param), 0, sizeof(del_vap_param));
317 
318             del_vap_param.net_dev = netdev;
319             del_vap_param.vap_mode = mac_vap->vap_mode;
320             del_vap_param.p2p_mode = mac_get_p2p_mode(mac_vap);
321 #endif
322             oam_warning_log2(mac_vap->vap_id, OAM_SF_P2P, "{wal_del_p2p_group:: vap mode[%d], p2p mode[%d]}\r\n",
323                 mac_vap->vap_mode, mac_get_p2p_mode(mac_vap));
324             /* 删除已经存在的P2P group */
325             wal_force_scan_complete(netdev);
326             wal_stop_vap(netdev);
327 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
328             if (wal_cfg80211_del_vap(&del_vap_param) == HI_SUCCESS) {
329                 wal_cfg80211_unregister_netdev(netdev);
330             }
331 #else
332             if (wal_deinit_wlan_vap(netdev) == HI_SUCCESS) {
333                 /* 去注册netdev */
334                 oal_net_unregister_netdev(netdev);
335                 oal_net_free_netdev(netdev);
336             }
337 #endif
338         }
339     }
340 
341     return HI_SUCCESS;
342 }
343 
344 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
345 /* ****************************************************************************
346  函 数 名  : wal_set_p2p_status
347  功能描述  :设置p2p 为对应状态
348  输入参数  : oal_net_device_stru *net_dev, wlan_p2p_status_enum_uint32 en_status
349  输出参数  : 无
350  返 回 值  :
351  调用函数  :
352  被调函数  :
353 
354  修改历史      :
355   1.日    期   :
356     作    者   : HiSilicon
357     修改内容   : 新生成函数
358 
359 **************************************************************************** */
wal_set_p2p_status(oal_net_device_stru * netdev,wlan_p2p_status_enum_uint32 status)360 hi_u32 wal_set_p2p_status(oal_net_device_stru *netdev, wlan_p2p_status_enum_uint32 status)
361 {
362     hi_u32 ret;
363     wal_msg_write_stru write_msg;
364 
365     /* 填写消息头 */
366     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_SET_P2P_STATUS, sizeof(wlan_p2p_status_enum_uint32));
367     /* 填写消息体 */
368     if (memcpy_s(write_msg.auc_value, sizeof(write_msg.auc_value),
369                  &status, sizeof(wlan_p2p_status_enum_uint32)) != EOK) {
370         oam_error_log0(0, OAM_SF_ANY, "{wal_set_p2p_status::mem safe function err!}");
371         return HI_FAIL;
372     }
373     ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE,
374         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(wlan_p2p_status_enum_uint32), (hi_u8 *)&write_msg, HI_FALSE, HI_NULL);
375     if (oal_unlikely(ret != HI_SUCCESS)) {
376         oam_warning_log1(0, OAM_SF_ANY, "{wal_set_p2p_status::return err code [%u]!}\r\n", ret);
377         return HI_FAIL;
378     }
379 
380     return HI_SUCCESS;
381 }
382 #endif
383 
wal_cfg80211_add_virtual_intf_p2p_proc(mac_device_stru * mac_device)384 hi_u32 wal_cfg80211_add_virtual_intf_p2p_proc(mac_device_stru *mac_device)
385 {
386     /* 添加net_device 前先判断当前是否正在删除net_device 状态,
387         如果正在删除net_device,则等待删除完成,再添加 */
388     hmac_device_stru *hmac_dev = hmac_get_device_stru();
389     if (hmac_dev->p2p_intf_status & bit(P2P_STATUS_IF_DELETING)) {
390         oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf:Released lock, wait till IF_DEL is complete}");
391         hi_s32 l_timeout = hi_wait_event_timeout(hmac_dev->netif_change_event,
392             ((hmac_dev->p2p_intf_status & bit(P2P_STATUS_IF_DELETING)) == HI_FALSE),
393             WAL_MAX_WAIT_TIME / HI_MILLISECOND_PER_TICK);
394         if (l_timeout > 0) {
395             oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::IF DEL is success!}\r\n");
396         } else {
397             oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::timeount < 0, return -EAGAIN!}\r\n");
398             return HI_FAIL;
399         }
400     }
401 
402     /* 检查wifi 驱动中,P2P group 是否已经创建,如果P2P group 已经创建,
403         则将该P2P group 删除,并且重新创建P2P group */
404     if (wal_is_p2p_group_exist(mac_device) == HI_TRUE) {
405         oam_warning_log0(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf::found exist p2p group, delet it first!}");
406         if (wal_del_p2p_group(mac_device) != HI_SUCCESS) {
407             return HI_FAIL;
408         }
409     }
410 
411     return HI_SUCCESS;
412 }
413 
414 /* ****************************************************************************
415  函 数 名  : wal_cfg80211_remain_on_channel
416  功能描述  : 保持在指定信道
417  输入参数  : [1]wiphy
418              [2]wdev
419              [3]chan
420              [4]duration
421              [5]pull_cookie
422  输出参数  : 无
423  返 回 值  : static hi_s32
424 **************************************************************************** */
wal_p2p_stop_roc(mac_vap_stru * mac_vap,oal_net_device_stru * netdev)425 hi_u32 wal_p2p_stop_roc(mac_vap_stru *mac_vap, oal_net_device_stru *netdev)
426 {
427 #ifdef _PRE_WLAN_FEATURE_P2P
428     if (mac_vap->vap_state == MAC_VAP_STATE_STA_LISTEN) {
429         hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
430         if (hmac_vap == HI_NULL) {
431             oam_error_log0(0, OAM_SF_P2P, "{wal_p2p_stop_roc:: pst_hmac_vap null!}\r\n");
432             return HI_FAIL;
433         }
434         hmac_vap->en_wait_roc_end = HI_TRUE;
435         OAL_INIT_COMPLETION(&(hmac_vap->st_roc_end_ready));
436         wal_force_scan_complete(netdev);
437         if (oal_wait_for_completion_timeout(&(hmac_vap->st_roc_end_ready),
438             (hi_u32)OAL_MSECS_TO_JIFFIES(WIFI_ROC_TIMEOUT)) == 0) {
439             oam_error_log0(0, OAM_SF_P2P, "{wal_p2p_stop_roc::cancel old roc timeout!}");
440             return HI_FAIL;
441         }
442     }
443 #endif
444     return HI_SUCCESS;
445 }
446 
447 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_drv_remain_on_channel(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev,oal_ieee80211_channel * chan,hi_u32 duration,hi_u64 * pull_cookie,wlan_ieee80211_roc_type_uint8 en_roc_type)448 hi_u32 wal_drv_remain_on_channel(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, oal_ieee80211_channel *chan,
449     hi_u32 duration, hi_u64 *pull_cookie, wlan_ieee80211_roc_type_uint8 en_roc_type)
450 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
451 hi_s32 wal_drv_remain_on_channel(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, oal_ieee80211_channel *chan,
452     hi_u32 duration, hi_u64 *pull_cookie, wlan_ieee80211_roc_type_uint8 en_roc_type)
453 #endif
454 {
455     /* 1.1 入参检查 */
456     if ((wiphy == HI_NULL) || (wdev == HI_NULL) || (chan == HI_NULL) || (pull_cookie == HI_NULL)) {
457         oam_error_log0(0, OAM_SF_P2P, "{wal_drv_remain_on_channel::wiphy or wdev or chan or pull_cookie is NULL}");
458         goto fail;
459     }
460 
461     oal_net_device_stru *netdev = wdev->netdev;
462     if (netdev == HI_NULL) {
463         oam_error_log0(0, OAM_SF_P2P, "{wal_drv_remain_on_channel::pst_netdev ptr is NULL!}\r\n");
464         goto fail;
465     }
466 
467     mac_device_stru *mac_device     = (mac_device_stru *)mac_res_get_dev();
468     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
469 #ifdef _PRE_WLAN_FEATURE_WAPI
470     if (hmac_user_is_wapi_connected() == HI_TRUE) {
471         oam_warning_log0(0, OAM_SF_CFG, "{stop p2p remaining under wapi!}");
472         goto fail;
473     }
474 #endif /* #ifdef _PRE_WLAN_FEATURE_WAPI */
475     if (mac_vap->vap_state == MAC_VAP_STATE_STA_LISTEN) {
476         oam_warning_log1(mac_vap->vap_id, OAM_SF_P2P, "{wal_drv_remain_on_channel::new roc type[%d],cancel old roc!}",
477             en_roc_type);
478         if (wal_p2p_stop_roc(mac_vap, netdev) != HI_SUCCESS) {
479             oam_warning_log0(0, OAM_SF_CFG, "{wal_p2p_stop_roc fail!}");
480             goto fail;
481         }
482     }
483 
484     /* 2.1 消息参数准备 */
485     hi_u16 us_center_freq = chan->center_freq;
486     hi_s32 l_channel = (hi_s32)oal_ieee80211_frequency_to_channel((hi_s32)us_center_freq);
487     mac_remain_on_channel_param_stru remain_on_channel = {0};
488     remain_on_channel.uc_listen_channel = (hi_u8)l_channel;
489     remain_on_channel.listen_duration = duration;
490     remain_on_channel.st_listen_channel = *chan;
491     remain_on_channel.listen_channel_type = WLAN_BAND_WIDTH_20M;
492 
493     if ((hi_u8)chan->band == IEEE80211_BAND_2GHZ) {
494         remain_on_channel.band = WLAN_BAND_2G;
495     } else {
496         oam_warning_log1(0, OAM_SF_P2P, "{wal_drv_remain_on_channel::wrong band type[%d]!}\r\n", chan->band);
497         goto fail;
498     }
499     if (en_roc_type == IEEE80211_ROC_TYPE_NORMAL) {
500         *pull_cookie = ++mac_device->p2p_info.ull_last_roc_id;
501         if (*pull_cookie == 0) {
502             *pull_cookie = ++mac_device->p2p_info.ull_last_roc_id;
503         }
504 
505     /* 保存cookie 值,下发给HMAC 和DMAC */
506     remain_on_channel.ull_cookie = mac_device->p2p_info.ull_last_roc_id;
507     }
508     /* 抛事件给驱动 */
509     hi_u32 ret = wal_cfg80211_start_req(netdev, &remain_on_channel, sizeof(mac_remain_on_channel_param_stru),
510         WLAN_CFGID_CFG80211_REMAIN_ON_CHANNEL, HI_TRUE);
511     if (ret != HI_SUCCESS) {
512         oam_error_log1(0, OAM_SF_P2P, "{wal_drv_remain_on_channel::wal_send_cfg_event return err code:[%d]}", ret);
513         goto fail;
514     }
515 
516 if (en_roc_type == IEEE80211_ROC_TYPE_NORMAL) {
517     /* 上报暂停在指定信道成功 */
518 #if (_PRE_OS_VERSION == _PRE_OS_VERSION_LINUX) && !defined(_PRE_HDF_LINUX)
519     cfg80211_ready_on_channel(wdev, *pull_cookie, chan, duration, GFP_KERNEL);
520 #else
521     ret = HdfWifiEventRemainOnChannel(netdev, chan->center_freq, duration);
522     if (ret != HI_SUCCESS) {
523         oam_error_log1(0, OAM_SF_P2P, "{wal_drv_remain_on_channel::cfg80211_remain_on_channel failed[%u]}\r\n",
524             ret);
525         goto fail;
526     }
527 #endif
528 }
529     oam_warning_log4(0, OAM_SF_P2P,
530         "{wal_drv_remain_on_channel::SUCC! l_channel = %d, ul_duration = %d, cookie 0x%x, band = %u!}\r\n",
531         l_channel, duration, *pull_cookie, remain_on_channel.band);
532 
533     return HI_SUCCESS;
534 
535 fail:
536 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
537     return HI_FAIL;
538 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
539     return -HI_FAIL;
540 #endif
541 }
542 
543 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_cfg80211_remain_on_channel(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev,oal_ieee80211_channel * chan,hi_u32 duration,hi_u64 * pull_cookie)544 hi_s32 wal_cfg80211_remain_on_channel(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, oal_ieee80211_channel *chan,
545     hi_u32 duration, hi_u64 *pull_cookie)
546 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
547 hi_s32 wal_cfg80211_remain_on_channel(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, oal_ieee80211_channel *chan,
548     hi_u32 duration, hi_u64 *pull_cookie)
549 #endif
550 {
551     return wal_drv_remain_on_channel(wiphy, wdev, chan, duration, pull_cookie, IEEE80211_ROC_TYPE_NORMAL);
552 }
553 /* ****************************************************************************
554  函 数 名  : wal_cfg80211_cancel_remain_on_channel
555  功能描述  : 停止保持在指定信道
556  输入参数  : [1]wiphy
557              [2]wdev
558              [3]ull_cookie
559  输出参数  : 无
560  返 回 值  : static hi_s32
561 **************************************************************************** */
562 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_cfg80211_cancel_remain_on_channel(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev,hi_u64 ull_cookie)563 hi_s32 wal_cfg80211_cancel_remain_on_channel(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, hi_u64 ull_cookie)
564 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
565 hi_s32 wal_cfg80211_cancel_remain_on_channel(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, hi_u64 ull_cookie)
566 #endif
567 {
568     oal_net_device_stru             *netdev                   = HI_NULL;
569     mac_remain_on_channel_param_stru cancel_remain_on_channel = {0};
570     hi_u32                           ret;
571 
572     hi_unref_param(wiphy);
573     hi_unref_param(ull_cookie);
574     netdev = wdev->netdev;
575 
576     /* 抛事件给驱动 */
577     ret = wal_cfg80211_start_req(netdev, &cancel_remain_on_channel, sizeof(mac_remain_on_channel_param_stru),
578         WLAN_CFGID_CFG80211_CANCEL_REMAIN_ON_CHANNEL, HI_TRUE);
579     if (ret != HI_SUCCESS) {
580         oam_error_log1(0, OAM_SF_P2P,
581             "{wal_cfg80211_cancel_remain_on_channel::wal_send_cfg_event return err code:[%u]!}", ret);
582         goto fail;
583     }
584 
585     return HI_SUCCESS;
586 
587 fail:
588 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
589     return HI_FAIL;
590 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
591     return -HI_FAIL;
592 #endif
593 }
594 #endif /* #ifdef _PRE_WLAN_FEATURE_P2P */
595 
596 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
597 /* ****************************************************************************
598  函 数 名  : wal_cfg80211_register_netdev
599  功能描述  : 内核注册指定类型的net_device,用于需要解mutex lock的应用
600  输入参数  : mac_device_stru *pst_hmac_device
601              oal_net_device_stru *pst_net_dev
602  输出参数  : 无
603  返 回 值  : 无
604  调用函数  :
605  被调函数  :
606 
607  修改历史      :
608   1.日    期   : 2015年7月24日
609     作    者   : HiSilicon
610     修改内容   : 新生成函数
611 
612 **************************************************************************** */
613 #ifndef _PRE_HDF_LINUX
wal_cfg80211_register_netdev(oal_net_device_stru * netdev)614 hi_u32 wal_cfg80211_register_netdev(oal_net_device_stru *netdev)
615 {
616     hi_u8 rollback_lock = HI_FALSE;
617 
618     /* nl80211 netlink pre diot 中会获取rntl_lock互斥锁,注册net_device 会获取rntl_lock互斥锁,造成了死锁 */
619     if (rtnl_is_locked()) {
620         rtnl_unlock();
621         rollback_lock = HI_TRUE;
622     }
623 
624     /* 内核注册net_device, 只返回0 */
625     hi_u32 ret = (hi_u32)oal_net_register_netdev(netdev);
626     if (rollback_lock) {
627         rtnl_lock();
628     }
629     return ret;
630 }
631 
wal_cfg80211_unregister_netdev(oal_net_device_stru * netdev)632 hi_void wal_cfg80211_unregister_netdev(oal_net_device_stru *netdev)
633 {
634     hi_u8 rollback_lock = HI_FALSE;
635 
636     if (rtnl_is_locked()) {
637         rtnl_unlock();
638         rollback_lock = HI_TRUE;
639     }
640     /* 去注册netdev */
641     oal_net_unregister_netdev(netdev);
642 
643     if (rollback_lock) {
644         rtnl_lock();
645     }
646 }
647 #endif
648 
649 /* ****************************************************************************
650  函 数 名  : wal_find_wmm_uapsd
651  功能描述  : 查找内核下发的beacon_info中的wmm ie中wmm uapsd是否使能
652  输入参数  : hi_u8 *puc_frame_body, hi_s32 l_len
653 
654  输出参数  : 无
655  返 回 值  : uapsd使能,返回HI_TRUE,否则,返回HI_FALSE
656  调用函数  :
657  被调函数  :
658 
659  修改历史      :
660   1.日    期   : 2015年8月24日
661     作    者   : HiSilicon
662     修改内容   : 新生成函数
663 
664 **************************************************************************** */
wal_find_wmm_uapsd(hi_u8 * puc_frame_body,hi_s32 l_len)665 hi_u32 wal_find_wmm_uapsd(hi_u8 *puc_frame_body, hi_s32 l_len)
666 {
667     hi_s32    l_index = 0;
668     hi_u8     auc_oui[MAC_OUI_LEN];
669 
670     auc_oui[0] = (hi_u8)MAC_WLAN_OUI_MICRO0;
671     auc_oui[1] = (hi_u8)MAC_WLAN_OUI_MICRO1;
672     auc_oui[2] = (hi_u8)MAC_WLAN_OUI_MICRO2; /* 2: 数组第3位 */
673     /* 判断 WMM UAPSD 是否使能 */
674     while (l_index < l_len) {
675         if ((puc_frame_body[l_index] == MAC_EID_WMM) &&
676             (memcmp(puc_frame_body + l_index + 2, auc_oui, MAC_OUI_LEN) == 0) && /* 2:偏移位 */
677             (puc_frame_body[l_index + 2 + MAC_OUI_LEN] == MAC_OUITYPE_WMM) && /* 2:偏移位 */
678             (puc_frame_body[l_index + MAC_WMM_QOS_INFO_POS] & BIT7)) {
679             return HI_TRUE;
680         } else {
681             l_index += (MAC_IE_HDR_LEN + puc_frame_body[l_index + 1]);
682         }
683     }
684 
685     return HI_FALSE;
686 }
687 
wal_cfg80211_open_wmm(oal_net_device_stru * netdev,hi_u16 us_len,hi_u8 * puc_param)688 hi_u32 wal_cfg80211_open_wmm(oal_net_device_stru *netdev, hi_u16 us_len, hi_u8 *puc_param)
689 {
690     mac_vap_stru *mac_vap = HI_NULL;
691     wal_msg_write_stru write_msg;
692     hi_u32 ret;
693     mac_vap = oal_net_dev_priv(netdev);
694     if (oal_unlikely(mac_vap == HI_NULL || puc_param == HI_NULL)) {
695         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_open_wmm::pst_mac_vap/puc_param is NULL!}\r\n");
696         return HI_ERR_CODE_PTR_NULL;
697     }
698 
699     /* 针对配置vap做保护 */
700     if (mac_vap->vap_mode == WLAN_VAP_MODE_CONFIG) {
701         oam_warning_log0(mac_vap->vap_id, OAM_SF_CFG, "{wal_cfg80211_open_wmm::this is config vap! can't get info.}");
702         return HI_FAIL;
703     }
704 
705     /* 填写事件头 */
706     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_WMM_SWITCH, sizeof(hi_u8));
707     /* 填写消息体 */
708     if (memcpy_s(write_msg.auc_value, sizeof(write_msg.auc_value), puc_param, sizeof(hi_u8)) != EOK) {
709         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_open_wmm::mem safe function err!}");
710         return HI_FAIL;
711     }
712 
713     ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE, WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(hi_u8),
714         (hi_u8 *)&write_msg, HI_FALSE, HI_NULL);
715     if (oal_unlikely(ret != HI_SUCCESS)) {
716         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_open_wmm:return err code %d!}\r\n", ret);
717         return HI_FAIL;
718     }
719 
720     return ret;
721 }
722 
723 /* ****************************************************************************
724  函 数 名  : wal_parse_wmm_ie
725  功能描述  : 解析内核传递过来beacon信息中的Wmm信息元素
726  输入参数  : oal_beacon_parameters *pst_beacon_info
727 
728  输出参数  : 无
729  返 回 值  : hi_u32
730  调用函数  :
731  被调函数  :
732 
733  修改历史      :
734   1.日    期   : 2015年7月16日
735     作    者   : HiSilicon
736     修改内容   : 新生成函数
737 
738 **************************************************************************** */
wal_parse_wmm_ie(oal_net_device_stru * netdev,mac_vap_stru * mac_vap,oal_beacon_parameters * beacon_info)739 hi_u32 wal_parse_wmm_ie(oal_net_device_stru *netdev, mac_vap_stru *mac_vap, oal_beacon_parameters *beacon_info)
740 {
741     hi_u8               *puc_wmm_ie = HI_NULL;
742     hi_u16               us_len = sizeof(hi_u8);
743     hi_u8                wmm = HI_TRUE;
744     hi_u32               ret = HI_SUCCESS;
745 
746     hi_u8                uapsd;
747     wal_msg_write_stru   write_msg;
748 
749     /*  查找wmm_ie  */
750     puc_wmm_ie = mac_find_vendor_ie(MAC_WLAN_OUI_MICROSOFT, MAC_WLAN_OUI_TYPE_MICROSOFT_WMM, beacon_info->tail,
751         beacon_info->tail_len);
752     if (puc_wmm_ie == HI_NULL) {
753         /* wmm ie未找到,则说明wmm 关 */
754         wmm = HI_FALSE;
755     } else { /*  找到wmm ie,顺便判断下uapsd是否使能 */
756         if (HI_FALSE == wal_find_wmm_uapsd(beacon_info->tail, beacon_info->tail_len)) {
757             /* 对应UAPSD 关 */
758             uapsd = HI_FALSE;
759             oam_warning_log0(mac_vap->vap_id, OAM_SF_CFG, "{wal_parse_wmm_ie::uapsd is disabled!!}");
760         }
761 
762         /* 填写 msg 消息头 */
763         wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_UAPSD_EN, sizeof(hi_u32));
764         /* 填写 msg 消息体 */
765         uapsd = HI_FALSE;
766 
767         if (memcpy_s(write_msg.auc_value, sizeof(write_msg.auc_value), &uapsd, sizeof(hi_u32)) != EOK) {
768             oam_error_log0(0, OAM_SF_CFG, "{wal_parse_wmm_ie::mem safe function err!}");
769             return HI_FAIL;
770         }
771 
772         /* 发送消息 */
773         ret = (hi_u32)wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE, WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(hi_u32),
774             (hi_u8 *)&write_msg, HI_FALSE, HI_NULL);
775         if (oal_unlikely(ret != HI_SUCCESS)) {
776             ret = HI_FAIL;
777             oam_warning_log1(mac_vap->vap_id, OAM_SF_CFG, "{wal_parse_wmm_ie::uapsd switch set failed[%u].}", ret);
778         }
779     }
780 
781     /*  wmm 开启/关闭 标记  */
782     ret = wal_cfg80211_open_wmm(netdev, us_len, &wmm);
783     if (ret != HI_SUCCESS) {
784         ret = HI_FAIL;
785         oam_warning_log0(0, OAM_SF_TX, "{wal_parse_wmm_ie::can not open wmm!}\r\n");
786     }
787 
788     return ret;
789 }
790 
791 /* ****************************************************************************
792  功能描述  : 从已保存信息里获取ptk,gtk等密钥
793  输入参数  : [1]wiphy
794              [2]netdev
795              [3]p_cfg80211_get_key_info
796              [4]cookie
797              [5]callback
798  输出参数  : hi_u32
799  返 回 值  : 0:成功,其他:失败
800 **************************************************************************** */
wal_cfg80211_get_key(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,hi_u8 key_index,bool pairwise,const hi_u8 * puc_mac_addr,hi_void * cookie,hi_void (* callback)(hi_void * cookie,oal_key_params_stru *))801 static hi_s32 wal_cfg80211_get_key(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, hi_u8 key_index, bool pairwise,
802     const hi_u8 *puc_mac_addr, hi_void *cookie, hi_void (*callback)(hi_void *cookie, oal_key_params_stru *))
803 {
804     wal_msg_write_stru    write_msg;
805     mac_getkey_param_stru payload  = {0};
806     hi_u8                 mac_addr[WLAN_MAC_ADDR_LEN];
807     wal_msg_stru         *rsp_msg = HI_NULL;
808 
809     /* 1.1 入参检查 */
810     if ((wiphy == HI_NULL) || (netdev == HI_NULL) || (cookie == HI_NULL) || (callback == HI_NULL)) {
811         oam_error_log4(0, OAM_SF_ANY,
812             "{wal_cfg80211_get_key::Param ERR, wiphy, netdev, cookie, callback %d, %d, %d, %d}", wiphy, netdev, cookie,
813             callback);
814         goto fail;
815     }
816 
817     /* 2.1 消息参数准备 */
818     payload.netdev    = netdev;
819     payload.key_index = key_index;
820 
821     if (puc_mac_addr != HI_NULL) {
822         /* 不能使用内核下发的mac指针,可能被释放,需要拷贝到本地再使用 */
823         if (memcpy_s(mac_addr, WLAN_MAC_ADDR_LEN, puc_mac_addr, WLAN_MAC_ADDR_LEN) != EOK) {
824             oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_get_key::mem safe function err!}");
825             goto fail;
826         }
827         payload.puc_mac_addr = mac_addr;
828     } else {
829         payload.puc_mac_addr = HI_NULL;
830     }
831 
832     payload.pairwise = pairwise;
833     payload.cookie = cookie;
834     payload.callback = callback;
835 
836     oam_info_log2(0, OAM_SF_ANY, "{wal_cfg80211_get_key::key_idx:%d,en_pairwise:%d}", key_index, payload.pairwise);
837     if (puc_mac_addr != HI_NULL) {
838         oam_info_log3(0, OAM_SF_ANY, "{wal_cfg80211_get_key::MAC ADDR: XX:XX:XX:%02X:%02X:%02X!}\r\n", puc_mac_addr[3],
839             puc_mac_addr[4], puc_mac_addr[5]); /* mac addr 0:1:2:3:4:5 */
840     } else {
841         oam_info_log0(0, OAM_SF_ANY, "{wal_cfg80211_get_key::MAC ADDR IS NULL!}\r\n");
842     }
843     /* **************************************************************************
844         抛事件到wal层处理
845     ************************************************************************** */
846     /* 3.1 填写 msg 消息头 */
847     write_msg.wid = WLAN_CFGID_GET_KEY;
848     write_msg.us_len = sizeof(mac_getkey_param_stru);
849 
850     /* 3.2 填写 msg 消息体 */
851     if (memcpy_s(write_msg.auc_value, sizeof(write_msg.auc_value), &payload, sizeof(mac_getkey_param_stru)) != EOK) {
852         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_get_key::mem safe function err!}");
853         goto fail;
854     }
855 
856     /* 由于消息中使用了局部变量指针,因此需要将发送该函数设置为同步,否则hmac处理时会使用野指针 */
857     hi_u32 ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE,
858         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(mac_getkey_param_stru), (hi_u8 *)&write_msg, HI_TRUE, &rsp_msg);
859     if (ret != HI_SUCCESS) {
860         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_get_key::return err code [%u]!}", ret);
861         goto fail;
862     }
863 
864     if (wal_check_and_release_msg_resp(rsp_msg) != HI_SUCCESS) {
865         oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_get_key::wal_check_and_release_msg_resp failed.}");
866         goto fail;
867     }
868 
869     return HI_SUCCESS;
870 fail:
871 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
872     return HI_FAIL;
873 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
874     return -HI_FAIL;
875 #endif
876 }
877 
878 /* ****************************************************************************
879  功能描述  : 使配置的密钥生效.PMF 特性使用,配置管理密钥
880  输入参数  : [1]wiphy
881              [2]netdev
882              [3]key_index
883  输出参数  : hi_u32
884  返 回 值  : 0:成功,其他:失败
885 **************************************************************************** */
wal_cfg80211_set_default_mgmt_key(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,hi_u8 key_index)886 hi_s32 wal_cfg80211_set_default_mgmt_key(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, hi_u8 key_index)
887 {
888     /* 设置管理密钥 */
889     return -HI_FAIL;
890 }
891 
892 /* ****************************************************************************
893  功能描述  : 设置wiphy设备的 参数,RTS 门限阈值,分片门限阈值
894  输入参数  : oal_wiphy_stru *pst_wiphy
895              hi_u32 ul_changed
896  返 回 值  : static hi_s32
897  修改历史      :
898   1.日    期   : 2013年10月28日
899     作    者   : HiSilicon
900     修改内容   : 新生成函数
901 
902 **************************************************************************** */
wal_cfg80211_set_wiphy_params(oal_wiphy_stru * wiphy,hi_u32 changed)903 static hi_s32 wal_cfg80211_set_wiphy_params(oal_wiphy_stru *wiphy, hi_u32 changed)
904 {
905     /* 通过HOSTAPD 设置RTS 门限,分片门限 采用接口wal_ioctl_set_frag, wal_ioctl_set_rts */
906     oam_warning_log0(0, OAM_SF_CFG,
907         "{wal_cfg80211_set_wiphy_params::should not call this function. call wal_ioctl_set_frag/wal_ioctl_set_rts!}\r\n");
908     return HI_SUCCESS;
909 }
910 
911 /* ****************************************************************************
912  功能描述  : 修改bss参数信息
913  输入参数  : oal_wiphy_stru        *pst_wiphy
914              oal_net_device_stru   *pst_netdev
915              oal_bss_parameters    *pst_bss_params
916  修改历史      :
917   1.日    期   : 2014年12月31日
918     作    者   : HiSilicon
919     修改内容   : 新生成函数
920 
921 **************************************************************************** */
922 #ifndef _PRE_HDF_LINUX
wal_cfg80211_change_bss(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,oal_bss_parameters * bss_params)923 static hi_s32 wal_cfg80211_change_bss(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev,
924     oal_bss_parameters *bss_params)
925 {
926     return HI_SUCCESS;
927 }
928 #endif
929 
930 /* ****************************************************************************
931  功能描述  : 打印上层下发的调度扫描请求信息
932  修改历史      :
933   1.日    期   : 2015年6月19日
934     作    者   : HiSilicon
935     修改内容   : 新生成函数
936 
937 **************************************************************************** */
wal_cfg80211_print_sched_scan_req_info(oal_cfg80211_sched_scan_request_stru * request)938 static hi_void wal_cfg80211_print_sched_scan_req_info(oal_cfg80211_sched_scan_request_stru *request)
939 {
940     hi_char    ac_tmp_buff[200]; /* 200 buffer元素个数 */
941     hi_s32     l_loop = 0;
942 
943     /* 打印基本参数 */
944 /* HI1131C modify begin */
945 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
946     oam_warning_log3(0, OAM_SF_SCAN, "wal_cfg80211_print_sched_scan_req_info::channels[%d], flags[%d], rssi_thold[%d]",
947         request->n_channels, request->flags, request->min_rssi_thold);
948 #endif
949     /* HI1131C modify end */
950     /* 打印ssid集合的信息 */
951     for (l_loop = 0; l_loop < request->n_match_sets; l_loop++) {
952         if (memset_s(ac_tmp_buff, sizeof(ac_tmp_buff), 0, sizeof(ac_tmp_buff)) != EOK) {
953             continue;
954         }
955         if (snprintf_s(ac_tmp_buff, sizeof(ac_tmp_buff), sizeof(ac_tmp_buff) - 1,
956             "mactch_sets[%d] info, ssid_len[%d], ssid: %s.\n", l_loop, request->match_sets[l_loop].ssid.ssid_len,
957             request->match_sets[l_loop].ssid.ssid) == -1) {
958             oam_error_log0(0, OAM_SF_CFG, "wal_cfg80211_print_sched_scan_req_info:: l_loop snprintf_s fail.");
959             continue;
960         }
961     }
962 
963     for (l_loop = 0; l_loop < request->n_ssids; l_loop++) {
964         if (memset_s(ac_tmp_buff, sizeof(ac_tmp_buff), 0, sizeof(ac_tmp_buff)) != EOK) {
965             continue;
966         }
967         if (snprintf_s(ac_tmp_buff, sizeof(ac_tmp_buff), sizeof(ac_tmp_buff) - 1,
968             "ssids[%d] info, ssid_len[%d], ssid: %s.\n", l_loop, request->ssids[l_loop].ssid_len,
969             request->ssids[l_loop].ssid) == -1) {
970             oam_error_log0(0, OAM_SF_CFG, "wal_cfg80211_print_sched_scan_req_info:: snprintf_s failed.");
971             continue;
972         }
973     }
974 
975     return;
976 }
977 
978 /* ****************************************************************************
979  功能描述  : 调度扫描启动
980  输入参数  : oal_wiphy_stru                         *pst_wiphy
981              oal_net_device_stru                    *pst_netdev
982              oal_cfg80211_sched_scan_request_stru   *pst_request
983  修改历史      :
984   1.日    期   : 2015年6月9日
985     作    者   : HiSilicon
986     修改内容   : 新生成函数
987 
988 **************************************************************************** */
989 #ifndef _PRE_HDF_LINUX
wal_cfg80211_sched_scan_start(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,oal_cfg80211_sched_scan_request_stru * request)990 static hi_s32 wal_cfg80211_sched_scan_start(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev,
991     oal_cfg80211_sched_scan_request_stru *request)
992 {
993     oal_cfg80211_ssid_stru *ssid_tmp = HI_NULL;
994     mac_pno_scan_stru pno_scan_info;
995 
996     /* 参数合法性检查 */
997     if ((wiphy == HI_NULL) || (netdev == HI_NULL) || (request == HI_NULL)) {
998         oam_error_log3(0, OAM_SF_CFG,
999             "{wal_cfg80211_sched_scan_start::input param pointer is NULL, pst_wiphy[%p], pst_netdev[%p], "
1000             "pst_request[%p]}",
1001             wiphy, netdev, request);
1002         goto fail;
1003     }
1004 
1005     /* 通过net_device 找到对应的mac_device_stru 结构 */
1006     mac_vap_stru     *mac_vap   = oal_net_dev_priv(netdev);
1007     hmac_device_stru *hmac_dev  = hmac_get_device_stru();
1008     hmac_scan_stru   *scan_mgmt = &(hmac_dev->scan_mgmt);
1009 
1010     /* 如果当前设备处于扫描状态,不启动调度扫描 */
1011     if (scan_mgmt->request != HI_NULL) {
1012         oam_warning_log0(0, OAM_SF_CFG, "{wal_cfg80211_sched_scan_start:: device is busy, don't start sched scan!}");
1013         goto fail;
1014     }
1015 
1016     /* 检测内核下发的需要匹配的ssid集合的个数是否合法 */
1017     if (request->n_match_sets <= 0) {
1018         oam_warning_log1(mac_vap->vap_id, OAM_SF_SCAN, "{wal_cfg80211_sched_scan_start::match_sets = %d!}",
1019             request->n_match_sets);
1020         goto fail;
1021     }
1022 
1023     /* 初始化pno扫描的结构体信息
1024        安全编程规则6.6例外(1) 固定长度的结构体进行内存初始化 */
1025     memset_s(&pno_scan_info, sizeof(mac_pno_scan_stru), 0, sizeof(mac_pno_scan_stru));
1026 
1027     /* 将内核下发的匹配的ssid集合复制到本地 */
1028     for (hi_s32 l_loop = 0; l_loop < request->n_match_sets; l_loop++) {
1029         ssid_tmp = (oal_cfg80211_ssid_stru *)&(request->match_sets[l_loop].ssid);
1030         if (memcpy_s(pno_scan_info.ac_match_ssid_set[l_loop], WLAN_SSID_MAX_LEN,
1031                      ssid_tmp->ssid, ssid_tmp->ssid_len) != EOK) {
1032             oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_sched_scan_start::mem safe function err!}");
1033             continue;
1034         }
1035         pno_scan_info.ac_match_ssid_set[l_loop][ssid_tmp->ssid_len] = '\0';
1036         pno_scan_info.l_ssid_count++;
1037     }
1038 
1039     /* 其它参数赋值 */
1040 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1041     pno_scan_info.l_rssi_thold = request->min_rssi_thold;
1042 #endif
1043 
1044     pno_scan_info.pno_scan_interval = PNO_SCHED_SCAN_INTERVAL;        /* 驱动自己定义为30s */
1045     pno_scan_info.pno_scan_repeat   = MAX_PNO_REPEAT_TIMES;
1046 
1047     /* 保存当前的PNO调度扫描请求指针 */
1048     scan_mgmt->sched_scan_req = request;
1049     scan_mgmt->sched_scan_complete = HI_FALSE;
1050 
1051     /* 维测打印上层下发的调度扫描请求参数信息 */
1052     wal_cfg80211_print_sched_scan_req_info(request);
1053 
1054     /* 下发pno扫描请求到hmac */
1055     hi_u32 ret = wal_cfg80211_start_sched_scan(netdev, &pno_scan_info);
1056     if (ret != HI_SUCCESS) {
1057         oam_warning_log1(0, OAM_SF_SCAN, "{wal_cfg80211_sched_scan_start::wal_cfg80211_start_sched_scan err[%u]}", ret);
1058         goto fail;
1059     }
1060 
1061     return HI_SUCCESS;
1062 
1063 fail:
1064 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
1065     return HI_FAIL;
1066 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1067     return -HI_FAIL;
1068 #endif
1069 }
1070 #endif
1071 
1072 /* ****************************************************************************
1073  函 数 名  : wal_cfg80211_add_station
1074  功能描述  : 增加用户
1075  输入参数  : oal_wiphy_stru *pst_wiphy
1076              oal_net_device *pst_dev
1077              hi_u8 *puc_mac         用户mac 地址
1078              oal_station_parameters_stru *pst_sta_parms 用户参数
1079  输出参数  : 无
1080  返 回 值  : static hi_s32
1081  调用函数  :
1082  被调函数  :
1083 
1084  修改历史      :
1085   1.日    期   : 2013年11月13日
1086     作    者   : HiSilicon
1087     修改内容   : 新生成函数
1088 
1089 **************************************************************************** */
1090 #ifndef _PRE_HDF_LINUX
wal_cfg80211_add_station(oal_wiphy_stru * wiphy,oal_net_device_stru * dev,const hi_u8 * puc_mac,oal_station_parameters_stru * pst_sta_parms)1091 static hi_s32 wal_cfg80211_add_station(oal_wiphy_stru *wiphy, oal_net_device_stru *dev, const hi_u8 *puc_mac,
1092     oal_station_parameters_stru *pst_sta_parms)
1093 {
1094     return HI_SUCCESS;
1095 }
1096 #endif
1097 
1098 /* ****************************************************************************
1099  函 数 名  : wal_cfg80211_change_station
1100  功能描述  : 删除用户
1101  输入参数  : oal_wiphy_stru *pst_wiphy
1102              oal_net_device *pst_dev
1103              hi_u8 *puc_mac         用户mac 地址
1104              oal_station_parameters_stru *pst_sta_parms 用户参数
1105  输出参数  : 无
1106  返 回 值  : static hi_s32
1107  调用函数  :
1108  被调函数  :
1109 
1110  修改历史      :
1111   1.日    期   : 2013年11月13日
1112     作    者   : HiSilicon
1113     修改内容   : 新生成函数
1114 
1115 **************************************************************************** */
1116 #ifndef _PRE_HDF_LINUX
wal_cfg80211_change_station(oal_wiphy_stru * wiphy,oal_net_device_stru * dev,const hi_u8 * puc_mac,oal_station_parameters_stru * sta_parms)1117 static hi_s32 wal_cfg80211_change_station(oal_wiphy_stru *wiphy, oal_net_device_stru *dev, const hi_u8 *puc_mac,
1118     oal_station_parameters_stru *sta_parms)
1119 {
1120     return HI_SUCCESS;
1121 }
1122 #endif
1123 
1124 #define QUERY_STATION_INFO_TIME (5 * HZ)
1125 /* ****************************************************************************
1126  函 数 名  : wal_cfg80211_fill_station_info
1127  功能描述  : station_info结构赋值
1128  输入参数  : oal_station_info_stru  *pst_sta_info,
1129              oal_station_info_stru *pst_stats
1130  输出参数  : 无
1131  返 回 值  : 无
1132  调用函数  :
1133  被调函数  :
1134 
1135  修改历史      :
1136   1.日    期   : 2014年12月4日
1137     作    者   : HiSilicon
1138     修改内容   : 新生成函数
1139 
1140 **************************************************************************** */
wal_cfg80211_fill_station_info(oal_station_info_stru * sta_info,oal_station_info_stru * stats)1141 static hi_void wal_cfg80211_fill_station_info(oal_station_info_stru *sta_info, oal_station_info_stru *stats)
1142 {
1143     sta_info->filled |= STATION_INFO_SIGNAL;
1144 
1145     sta_info->signal = stats->signal;
1146 
1147     sta_info->filled |= STATION_INFO_RX_PACKETS;
1148     sta_info->filled |= STATION_INFO_TX_PACKETS;
1149 
1150     sta_info->rx_packets = stats->rx_packets;
1151     sta_info->tx_packets = stats->tx_packets;
1152 
1153     sta_info->filled   |= STATION_INFO_RX_BYTES;
1154     sta_info->filled   |= STATION_INFO_TX_BYTES;
1155     sta_info->rx_bytes  = stats->rx_bytes;
1156     sta_info->tx_bytes  = stats->tx_bytes;
1157 
1158     sta_info->filled |= STATION_INFO_TX_RETRIES;
1159     sta_info->filled |= STATION_INFO_TX_FAILED;
1160     sta_info->filled |= STATION_INFO_RX_DROP_MISC;
1161 
1162     sta_info->tx_retries       = stats->tx_retries;
1163     sta_info->tx_failed        = stats->tx_failed;
1164     sta_info->rx_dropped_misc  = stats->rx_dropped_misc;
1165 
1166     sta_info->filled |= STATION_INFO_TX_BITRATE;
1167     sta_info->txrate.legacy = (hi_u16)(stats->txrate.legacy * 10); /* 内核中单位为100kbps */
1168     sta_info->txrate.flags  = stats->txrate.flags;
1169     sta_info->txrate.mcs    = stats->txrate.mcs;
1170     sta_info->txrate.nss    = stats->txrate.nss;
1171 
1172     oam_info_log4(0, OAM_SF_CFG, "{wal_cfg80211_fill_station_info::legacy[%d],mcs[%d],flags[%d],nss[%d].}",
1173         sta_info->txrate.legacy / 10, sta_info->txrate.mcs, /* 10: 单位转换 */
1174         sta_info->txrate.flags, sta_info->txrate.nss);
1175 }
1176 
1177 /* ****************************************************************************
1178  功能描述  : update rssi once a second
1179  修改历史      :
1180   1.日    期   : 2015年8月20日
1181     作    者   : HiSilicon
1182     修改内容   : 新生成函数
1183 **************************************************************************** */
wal_cfg80211_get_station_filter(mac_vap_stru * mac_vap,hi_u8 * mac_addr)1184 hi_u8 wal_cfg80211_get_station_filter(mac_vap_stru *mac_vap, hi_u8 *mac_addr)
1185 {
1186     hmac_user_stru *hmac_user = HI_NULL;
1187     hi_u32      current_time = hi_get_milli_seconds();
1188     hi_u32      runtime;
1189 
1190     hmac_user = mac_vap_get_hmac_user_by_addr(mac_vap, mac_addr, WLAN_MAC_ADDR_LEN);
1191     if (hmac_user == HI_NULL) {
1192         oam_warning_log0(mac_vap->vap_id, OAM_SF_CFG, "{wal_cfg80211_get_station_filter::user %d is null.}");
1193         return HI_FALSE;
1194     }
1195 
1196     if (current_time >= hmac_user->rssi_last_timestamp) {
1197         runtime = current_time - hmac_user->rssi_last_timestamp;
1198     } else {
1199         runtime = (hi_u32)(HI_U32_MAX - (hmac_user->rssi_last_timestamp - current_time) / HI_MILLISECOND_PER_TICK) *
1200             HI_MILLISECOND_PER_TICK;
1201     }
1202 
1203     if (runtime < WAL_GET_STATION_THRESHOLD) {
1204         return HI_FALSE;
1205     }
1206 
1207     hmac_user->rssi_last_timestamp = current_time;
1208     return HI_TRUE;
1209 }
1210 
wal_cfg80211_send_query_station_event(oal_net_device_stru * netdev,mac_vap_stru * mac_vap,dmac_query_request_event * query_request,oal_station_info_stru * sta_info)1211 hi_u32 wal_cfg80211_send_query_station_event(oal_net_device_stru *netdev, mac_vap_stru *mac_vap,
1212     dmac_query_request_event *query_request, oal_station_info_stru *sta_info)
1213 {
1214     wal_msg_write_stru write_msg;
1215     write_msg.wid = WLAN_CFGID_QUERY_STATION_STATS;
1216     write_msg.us_len = sizeof(dmac_query_request_event);
1217 
1218     hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
1219     if (hmac_vap == HI_NULL) {
1220         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_send_query_station_event::hmac_vap_get_vap_stru fail.vap_id[%u]}",
1221             mac_vap->vap_id);
1222         return HI_ERR_CODE_PTR_NULL;
1223     }
1224 
1225     /* 3.2 填写 msg 消息体 */
1226     if (memcpy_s(write_msg.auc_value, sizeof(write_msg.auc_value),
1227         query_request, sizeof(dmac_query_request_event)) != EOK) {
1228         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_get_station::mem safe function err!}");
1229         return HI_FAIL;
1230     }
1231 
1232     hi_u32 ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE,
1233         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(dmac_query_request_event), (hi_u8 *)&write_msg, HI_FALSE, HI_NULL);
1234     if (oal_unlikely(ret != HI_SUCCESS)) {
1235         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_get_station::wal_send_cfg_event Err=%d}", ret);
1236         return ret;
1237     }
1238 
1239     /* info, boolean argument to function */
1240     hi_s32 i_leftime = hi_wait_event_timeout(hmac_vap->query_wait_q, (hmac_vap->query_wait_q_flag == HI_TRUE),
1241         QUERY_STATION_INFO_TIME);
1242     if (i_leftime == 0) {
1243         /* 超时还没有上报扫描结束 */
1244         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_get_station::query info wait for %ld ms timeout!}",
1245             ((QUERY_STATION_INFO_TIME * 1000) / HZ)); /* 1000: 时间转换为ms */
1246         return HI_FAIL;
1247     } else if (i_leftime < 0) {
1248         /* 定时器内部错误 */
1249         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_get_station::query info wait for %ld ms error!}",
1250             ((QUERY_STATION_INFO_TIME * 1000) / HZ)); /* 1000: 时间转换为ms */
1251         return HI_FAIL;
1252     } else {
1253         /* 正常结束  */
1254         wal_cfg80211_fill_station_info(sta_info, &hmac_vap->station_info);
1255         oam_info_log1(0, OAM_SF_CFG, "{wal_cfg80211_get_station::rssi %d.}", hmac_vap->station_info.signal);
1256         return HI_SUCCESS;
1257     }
1258 }
1259 
1260 /* ****************************************************************************
1261  功能描述  : 获取station信息
1262  输入参数  : [1]wiphy,
1263              [2]dev,
1264              [3]puc_mac,
1265              [4]sta_info
1266  返 回 值  : static hi_s32
1267 
1268 **************************************************************************** */
wal_cfg80211_get_station(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,const hi_u8 * mac_addr,oal_station_info_stru * sta_info)1269 hi_s32 wal_cfg80211_get_station(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, const hi_u8 *mac_addr,
1270     oal_station_info_stru *sta_info)
1271 {
1272     dmac_query_request_event query_request;
1273 
1274     if ((wiphy == HI_NULL) || (netdev == HI_NULL) || (mac_addr == HI_NULL) || (sta_info == HI_NULL)) {
1275         oam_error_log4(0, OAM_SF_ANY, "{wal_cfg80211_get_station::wiphy[0x%p],dev[0x%p],mac[0x%p],sta_info[0x%p]}",
1276             wiphy, netdev, mac_addr, sta_info);
1277         goto fail;
1278     }
1279 
1280     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
1281     if (mac_vap == HI_NULL) {
1282         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_get_station::oal_net_dev_priv, return null!}");
1283         goto fail;
1284     }
1285 
1286     query_request.query_event = OAL_QUERY_STATION_INFO_EVENT;
1287     if (memcpy_s(query_request.auc_query_sta_addr, WLAN_MAC_ADDR_LEN, mac_addr, WLAN_MAC_ADDR_LEN) != EOK) {
1288         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_get_station::mem safe function err!}");
1289         goto fail;
1290     }
1291 
1292     hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
1293     if (hmac_vap == HI_NULL) {
1294         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_get_station:vap_get_vap_stru Err.vap_id=%u}", mac_vap->vap_id);
1295         goto fail;
1296     }
1297 
1298     /* 固定时间内最多更新一次RSSI */
1299     if (wal_cfg80211_get_station_filter(hmac_vap->base_vap, (hi_u8 *)mac_addr) == HI_FALSE) {
1300         wal_cfg80211_fill_station_info(sta_info, &hmac_vap->station_info);
1301         return HI_SUCCESS;
1302     }
1303 
1304     hmac_vap->query_wait_q_flag = HI_FALSE;
1305 
1306     /* *******************************************************************************
1307         抛事件到wal层处理 ,对于低功耗需要做额外处理,不能像下层抛事件,直接起定时器
1308         低功耗会在接收beacon帧的时候主动上报信息。
1309     ******************************************************************************* */
1310     if (wal_cfg80211_send_query_station_event(netdev, mac_vap, &query_request, sta_info) != HI_SUCCESS) {
1311         goto fail;
1312     }
1313     return HI_SUCCESS;
1314 
1315 fail:
1316 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
1317     return HI_FAIL;
1318 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1319     return -HI_FAIL;
1320 #endif
1321 }
1322 
1323 /* ****************************************************************************
1324  函 数 名  : wal_cfg80211_dump_station
1325  功能描述  : 删除用户
1326  输入参数  : oal_wiphy_stru *pst_wiphy
1327              oal_net_device *pst_dev
1328              hi_u8 *puc_mac         用户mac 地址
1329              oal_station_parameters_stru *pst_sta_parms 用户参数
1330  输出参数  : 无
1331  返 回 值  : static hi_s32
1332  调用函数  :
1333  被调函数  :
1334 
1335  修改历史      :
1336   1.日    期   : 2013年11月13日
1337     作    者   : HiSilicon
1338     修改内容   : 新生成函数
1339 
1340 **************************************************************************** */
wal_cfg80211_dump_station(oal_wiphy_stru * wiphy,oal_net_device_stru * dev,hi_s32 int_index,hi_u8 * mac_addr,oal_station_info_stru * sta_info)1341 static hi_s32 wal_cfg80211_dump_station(oal_wiphy_stru *wiphy, oal_net_device_stru *dev, hi_s32 int_index,
1342     hi_u8 *mac_addr, oal_station_info_stru *sta_info)
1343 {
1344     return HI_SUCCESS;
1345 }
1346 
1347 /* ****************************************************************************
1348  函 数 名  : wal_cfg80211_mgmt_tx_cancel_wait
1349  功能描述  : 取消发送管理帧等待
1350  输入参数  : [1]wiphy
1351              [2]wdev
1352              [3]ull_cookie
1353  输出参数  : 无
1354  返 回 值  : static hi_s32
1355 **************************************************************************** */
wal_cfg80211_mgmt_tx_cancel_wait(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev,hi_u64 ull_cookie)1356 static hi_s32 wal_cfg80211_mgmt_tx_cancel_wait(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, hi_u64 ull_cookie)
1357 {
1358     return -HI_FAIL;
1359 }
1360 
wal_cfg80211_get_vap_p2p_mode(nl80211_iftype_uint8 type,wlan_p2p_mode_enum_uint8 * p2p_mode,wlan_vap_mode_enum_uint8 * vap_mode)1361 hi_u32 wal_cfg80211_get_vap_p2p_mode(nl80211_iftype_uint8 type, wlan_p2p_mode_enum_uint8 *p2p_mode,
1362     wlan_vap_mode_enum_uint8 *vap_mode)
1363 {
1364     switch (type) {
1365         case NL80211_IFTYPE_P2P_DEVICE: /* P2P DEVICE在前面就返回,不应该走到这里 */
1366             oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf:: p2p0 need create before this!}");
1367             return HI_FAIL;
1368         case NL80211_IFTYPE_P2P_CLIENT:
1369             *vap_mode = WLAN_VAP_MODE_BSS_STA;
1370             *p2p_mode = WLAN_P2P_CL_MODE;
1371             break;
1372         case NL80211_IFTYPE_STATION:
1373             *vap_mode = WLAN_VAP_MODE_BSS_STA;
1374             *p2p_mode = WLAN_LEGACY_VAP_MODE;
1375             break;
1376         case NL80211_IFTYPE_P2P_GO:
1377             *vap_mode = WLAN_VAP_MODE_BSS_AP;
1378             *p2p_mode = WLAN_P2P_GO_MODE;
1379             break;
1380         case NL80211_IFTYPE_AP:
1381             *vap_mode = WLAN_VAP_MODE_BSS_AP;
1382             *p2p_mode = WLAN_LEGACY_VAP_MODE;
1383             break;
1384 #ifdef _PRE_WLAN_FEATURE_MESH
1385         case NL80211_IFTYPE_MESH_POINT:
1386             *vap_mode = WLAN_VAP_MODE_MESH;
1387             *p2p_mode = WLAN_LEGACY_VAP_MODE;
1388             break;
1389 #endif
1390         default:
1391             oam_error_log1(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf::Unsupported interface type[%d]!}", type);
1392             return HI_FAIL;
1393     }
1394 
1395     return HI_SUCCESS;
1396 }
1397 
wal_cfg80211_add_virtual_intf_get_netdev(const hi_char * puc_name,oal_net_device_stru ** netdev)1398 hi_u32 wal_cfg80211_add_virtual_intf_get_netdev(const hi_char *puc_name, oal_net_device_stru **netdev)
1399 {
1400     hi_char auc_name[OAL_IF_NAME_SIZE] = {0};
1401 
1402     oal_net_device_stru *netdev_cfg = oal_get_netdev_by_name(WLAN_CFG_VAP_NAME);
1403     if (netdev_cfg == HI_NULL) {
1404         oam_error_log0(WLAN_CFG_VAP_ID, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::pst_cfg_net_dev null!}");
1405         return HI_FAIL;
1406     }
1407 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1408     oal_dev_put(netdev_cfg);
1409 #endif
1410     if (memcpy_s(auc_name, OAL_IF_NAME_SIZE, puc_name, strlen(puc_name)) != EOK) {
1411         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf::mem safe function err!}");
1412         return HI_CONTINUE;
1413     }
1414 
1415 #if defined(_PRE_WLAN_FEATURE_FLOWCTL)
1416     /* 此函数第一个入参代表私有长度,此处不涉及为0 */
1417     *netdev = oal_net_alloc_netdev_mqs(auc_name);
1418 #elif defined(_PRE_WLAN_FEATURE_OFFLOAD_FLOWCTL)
1419     /* 此函数第一个入参代表私有长度,此处不涉及为0 */
1420     *netdev = oal_net_alloc_netdev_mqs(auc_name);
1421 #else
1422     /* 此函数第一个入参代表私有长度,此处不涉及为0 */
1423 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
1424     *netdev = oal_net_alloc_netdev(auc_name);
1425 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1426     *netdev = oal_net_alloc_netdev(0, auc_name, oal_ether_setup);
1427 #endif
1428 #endif
1429     if (oal_unlikely((*netdev) == HI_NULL)) {
1430         oam_error_log0(WLAN_CFG_VAP_ID, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::pst_net_dev null ptr error!}");
1431         return HI_FAIL;
1432     }
1433 
1434     return HI_SUCCESS;
1435 }
1436 
1437 #ifndef _PRE_HDF_LINUX
wal_cfg80211_add_virtual_intf_set_wireless_dev(oal_wireless_dev * wdev,mac_device_stru * mac_device,oal_net_device_stru * netdev,nl80211_iftype_uint8 type)1438 hi_u32 wal_cfg80211_add_virtual_intf_set_wireless_dev(oal_wireless_dev *wdev, mac_device_stru *mac_device,
1439     oal_net_device_stru *netdev, nl80211_iftype_uint8 type)
1440 {
1441     /* 对netdevice进行赋值 */
1442     /* 对新创建的net_device 初始化对应参数 */
1443 #if (_PRE_OS_VERSION == _PRE_OS_VERSION_LINUX)
1444     netdev->wireless_handlers = wal_get_g_iw_handler_def();
1445 #endif
1446     netdev->netdev_ops = wal_get_net_dev_ops();
1447 
1448 #if (_PRE_MULTI_CORE_MODE == _PRE_MULTI_CORE_MODE_OFFLOAD_DMAC) && (_PRE_OS_VERSION == _PRE_OS_VERSION_LINUX)
1449     netdev->ethtool_ops = &g_wal_ethtool_ops;
1450 #endif
1451 
1452     oal_netdevice_destructor(netdev)     = oal_net_free_netdev;
1453     oal_netdevice_ifalias(netdev)        = HI_NULL;
1454     oal_netdevice_watchdog_timeo(netdev) = 5; /* 固定设置为 5 */
1455     oal_netdevice_wdev(netdev)           = wdev;
1456     oal_netdevice_qdisc(netdev, HI_NULL);
1457 
1458     wdev->iftype = type;
1459     wdev->wiphy  = mac_device->wiphy;
1460     wdev->netdev = netdev;    /* 给wdev 中的net_device 赋值 */
1461     oal_netdevice_flags(netdev) &= ~OAL_IFF_RUNNING;    /* 将net device的flag设为down */
1462 
1463     if (wal_cfg80211_register_netdev(netdev) != HI_SUCCESS) {
1464         /* 注册不成功,释放资源 */
1465         oal_mem_free(wdev);
1466         oal_net_free_netdev(netdev);
1467         return HI_FAIL;
1468     }
1469 
1470     return HI_SUCCESS;
1471 }
1472 
wal_cfg80211_add_virtual_intf_send_event(oal_net_device_stru * netdev,oal_wireless_dev * wdev,wlan_p2p_mode_enum_uint8 p2p_mode,wlan_vap_mode_enum_uint8 vap_mode)1473 oal_wireless_dev *wal_cfg80211_add_virtual_intf_send_event(oal_net_device_stru *netdev, oal_wireless_dev *wdev,
1474     wlan_p2p_mode_enum_uint8 p2p_mode, wlan_vap_mode_enum_uint8 vap_mode)
1475 {
1476     wal_msg_write_stru   write_msg;
1477     wal_msg_stru        *rsp_msg    = HI_NULL;
1478     oal_net_device_stru *netdev_cfg = oal_get_netdev_by_name(WLAN_CFG_VAP_NAME);
1479     if (netdev_cfg == HI_NULL) {
1480         oam_error_log0(WLAN_CFG_VAP_ID, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::pst_cfg_net_dev null!}");
1481         goto ERR_STEP;
1482     }
1483 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1484     oal_dev_put(netdev_cfg);
1485 #endif
1486     /* 填写消息 */
1487     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_ADD_VAP, sizeof(mac_cfg_add_vap_param_stru));
1488 
1489     mac_cfg_add_vap_param_stru *add_vap_param = (mac_cfg_add_vap_param_stru *)(write_msg.auc_value);
1490     add_vap_param->net_dev  = netdev;
1491     add_vap_param->vap_mode = vap_mode;
1492     add_vap_param->cfg_vap_indx = WLAN_CFG_VAP_ID;
1493 #ifdef _PRE_WLAN_FEATURE_P2P
1494     add_vap_param->p2p_mode = p2p_mode;
1495 #endif
1496 
1497     /* 发送消息 */
1498     hi_u32 ret = wal_send_cfg_event(netdev_cfg, WAL_MSG_TYPE_WRITE,
1499         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(mac_cfg_add_vap_param_stru), (hi_u8 *)&write_msg, HI_TRUE, &rsp_msg);
1500     if (ret != HI_SUCCESS) {
1501         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::wal_send_cfg_event return err code=%u}", ret);
1502         goto ERR_STEP;
1503     }
1504 
1505     /* 读取返回的错误码 */
1506     if (wal_check_and_release_msg_resp(rsp_msg) != HI_SUCCESS) {
1507         oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::check_and_release_msg_resp fail:err_code}");
1508         goto ERR_STEP;
1509     }
1510 
1511     /* 设置netdevice的MAC地址,MAC地址在HMAC层被初始化到MIB中 */
1512     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
1513     if (oal_unlikely(mac_vap == HI_NULL)) {
1514         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::oal_net_dev_priv(pst_net_dev) is null ptr.}");
1515         goto ERR_STEP;
1516     }
1517 
1518     /* 设置VAP UP */
1519     wal_netdev_open(netdev);
1520 
1521     oam_warning_log1(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf:succ.vap_id[%d]}", mac_vap->vap_id);
1522 
1523     return wdev;
1524 
1525 /* 异常处理 */
1526 ERR_STEP: // 操作失败之后,进行内存释放等操作,属于例外,lint_t e801告警屏蔽
1527     wal_cfg80211_unregister_netdev(netdev);
1528     /* 先去注册,后释放 */
1529     oal_mem_free(wdev);
1530     return ERR_PTR(-EAGAIN);
1531 }
1532 #endif
1533 
1534 /* ****************************************************************************
1535  函 数 名  : wal_cfg80211_add_virtual_intf
1536  功能描述  : 添加指定类型的net_device
1537  输入参数  : [1]wiphy
1538              [2]puc_name
1539              [3]type
1540              [4]pul_flags
1541              [5]params
1542  输出参数  : 无
1543  返 回 值  : static oal_wireless_dev
1544 **************************************************************************** */
1545 #ifndef _PRE_HDF_LINUX
wal_cfg80211_add_virtual_intf(oal_wiphy_stru * wiphy,const hi_char * puc_name,nl80211_iftype_uint8 name_assign_type,enum_nl80211_iftype type,hi_u32 * pul_flags,oal_vif_params_stru * params)1546 static oal_wireless_dev *wal_cfg80211_add_virtual_intf(oal_wiphy_stru *wiphy, const hi_char *puc_name,
1547     nl80211_iftype_uint8 name_assign_type, enum_nl80211_iftype type, hi_u32 *pul_flags, oal_vif_params_stru *params)
1548 {
1549     oal_wireless_dev *wdev = HI_NULL;
1550     wlan_p2p_mode_enum_uint8 p2p_mode;
1551     wlan_vap_mode_enum_uint8 vap_mode;
1552 
1553     hi_unref_param(pul_flags);
1554 
1555     /* 1.1 入参检查 */
1556     if ((wiphy == HI_NULL) || (puc_name == HI_NULL) || (params == HI_NULL)) {
1557         oam_error_log3(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf:: ptr is null,wiphy %p,name %p,params %p!}",
1558             (uintptr_t)wiphy, (uintptr_t)puc_name, (uintptr_t)params);
1559         return ERR_PTR(-EINVAL);
1560     }
1561 
1562     /* 入参检查无异常后赋值,并调用OAL统一接口 */
1563     mac_wiphy_priv_stru *wiphy_priv = oal_wiphy_priv(wiphy);
1564     mac_device_stru     *mac_device = wiphy_priv->mac_device;
1565 
1566     oam_warning_log1(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf::en_type[%d]!}", type);
1567 #ifdef _PRE_WLAN_FEATURE_P2P
1568     hi_u8 p2p0_vap_idx = mac_device->p2p_info.p2p0_vap_idx;
1569     hmac_vap_stru *p2p0_hmac_vap = (hmac_vap_stru *)hmac_vap_get_vap_stru(p2p0_vap_idx);
1570     if (p2p0_hmac_vap == HI_NULL) {
1571         oam_error_log1(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf::p2p0_hmac_vap[id=%d] null!}", p2p0_vap_idx);
1572         return ERR_PTR(-ENODEV);
1573     }
1574 #endif
1575 
1576     /* 如果创建的net device已经存在,直接返回 */
1577     oal_net_device_stru *netdev = oal_get_netdev_by_name(puc_name);
1578     if (netdev != HI_NULL) {
1579         /* 调用oal_dev_get_by_name后,必须调用oal_dev_put使net_dev的引用计数减一 */
1580         oal_dev_put(netdev);
1581         oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::the net_device is already exist!}");
1582         wdev = GET_NET_DEV_CFG80211_WIRELESS(netdev);
1583         return wdev;
1584     }
1585 
1586     if (wal_cfg80211_get_vap_p2p_mode(type, &p2p_mode, &vap_mode) != HI_SUCCESS) {
1587         return ERR_PTR(-EINVAL);
1588     }
1589 
1590 #ifdef _PRE_WLAN_FEATURE_P2P
1591     if (wal_cfg80211_add_virtual_intf_p2p_proc(mac_device) != HI_SUCCESS) {
1592         return ERR_PTR(-EAGAIN);
1593     }
1594 #endif
1595 
1596     hi_u32 ret = wal_cfg80211_add_virtual_intf_get_netdev(puc_name, &netdev);
1597     if (ret == HI_FAIL) {
1598         return ERR_PTR(-ENOMEM);
1599     } else if (ret == HI_CONTINUE) {
1600         return HI_NULL;
1601     }
1602 
1603     wdev = (oal_wireless_dev *)oal_mem_alloc(OAL_MEM_POOL_ID_LOCAL, sizeof(oal_wireless_dev));
1604     if (oal_unlikely(wdev == HI_NULL)) {
1605         oam_error_log0(WLAN_CFG_VAP_ID, OAM_SF_ANY, "{wal_cfg80211_add_virtual_intf::alloc mem, pst_wdev is null ptr}");
1606         /* 异常处理,释放内存 */
1607         oal_net_free_netdev(netdev);
1608         return ERR_PTR(-ENOMEM);
1609     }
1610 
1611     /* 安全编程规则6.6例外(3)从堆中分配内存后,赋予初值 */
1612     memset_s(wdev, sizeof(oal_wireless_dev), 0, sizeof(oal_wireless_dev));
1613 
1614     if (memcpy_s((hi_u8 *)oal_netdevice_mac_addr(netdev), WLAN_MAC_ADDR_LEN,
1615         (hi_u8 *)oal_netdevice_mac_addr(p2p0_hmac_vap->net_device), WLAN_MAC_ADDR_LEN) != EOK) {
1616         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_add_virtual_intf::mem safe function err!}");
1617         oal_mem_free(wdev);
1618         return ERR_PTR(-ENOMEM);
1619     }
1620     if (p2p_mode == WLAN_P2P_CL_MODE) {
1621         ((hi_u8 *)oal_netdevice_mac_addr(netdev))[0] |= 0x02;
1622     }
1623     if (wal_cfg80211_add_virtual_intf_set_wireless_dev(wdev, mac_device, netdev, type) != HI_SUCCESS) {
1624         return ERR_PTR(-EBUSY);
1625     }
1626 
1627     /* **************************************************************************
1628         抛事件到wal层处理
1629     ************************************************************************** */
1630     return wal_cfg80211_add_virtual_intf_send_event(netdev, wdev, p2p_mode, vap_mode);
1631 }
1632 #endif
1633 
wal_cfg80211_del_p2p_proc(wal_msg_write_stru * write_msg,oal_net_device_stru * netdev,mac_vap_stru * mac_vap)1634 hi_u32 wal_cfg80211_del_p2p_proc(wal_msg_write_stru *write_msg, oal_net_device_stru *netdev, mac_vap_stru *mac_vap)
1635 {
1636 #ifdef _PRE_WLAN_FEATURE_P2P
1637     wlan_p2p_mode_enum_uint8 p2p_mode =
1638         wal_wireless_iftype_to_mac_p2p_mode(GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype);
1639     if (p2p_mode == WLAN_P2P_BUTT) {
1640         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_del_virtual_intf::get p2p mode err}");
1641         return HI_ERR_CODE_PTR_NULL;
1642     }
1643 
1644     ((mac_cfg_del_vap_param_stru *)write_msg->auc_value)->p2p_mode = mac_get_p2p_mode(mac_vap);
1645 
1646     hi_u32 ret = wal_set_p2p_status(netdev, P2P_STATUS_IF_DELETING);
1647     if (ret != HI_SUCCESS) {
1648         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_del_virtual_intf::wal_set_p2p_status return %u}.", ret);
1649         return ret;
1650     }
1651 #endif
1652 
1653     return HI_SUCCESS;
1654 }
1655 
1656 /* ****************************************************************************
1657  函 数 名  : wal_cfg80211_del_virtual_intf
1658  功能描述  : 删除对应VAP
1659  输入参数  : oal_wiphy_stru            *pst_wiphy
1660              oal_wireless_dev     *pst_wdev
1661              hi_s32                  l_ifindex
1662  输出参数  : 无
1663  返 回 值  : hi_s32
1664  调用函数  :
1665  被调函数  :
1666 
1667  修改历史      :
1668   1.日    期   : 2014年11月21日
1669     作    者   : HiSilicon
1670     修改内容   : 新生成函数
1671 
1672 **************************************************************************** */
wal_cfg80211_del_virtual_intf(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev)1673 hi_s32 wal_cfg80211_del_virtual_intf(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev)
1674 {
1675     wal_msg_stru       *rsp_msg = HI_NULL;
1676     wal_msg_write_stru  write_msg;
1677 
1678     if (oal_unlikely((wiphy == HI_NULL) || (wdev == HI_NULL))) {
1679         oam_error_log2(0, OAM_SF_ANY, "{wal_cfg80211_del_virtual_intf::pst_wiphy or pst_wdev null ptr error %p, %p}",
1680             (uintptr_t)wiphy, (uintptr_t)wdev);
1681         return -HI_ERR_CODE_PTR_NULL;
1682     }
1683 
1684     oal_net_device_stru *netdev  = wdev->netdev;
1685     mac_vap_stru        *mac_vap = oal_net_dev_priv(netdev);
1686     if (mac_vap == HI_NULL) {
1687         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_del_virtual_intf::mac_vap is null by netdev, mode[%d]}",
1688             GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype);
1689         return -HI_ERR_CODE_PTR_NULL;
1690     }
1691 
1692     hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
1693     if (hmac_vap == HI_NULL) {
1694         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_del_virtual_intf::get_vap_stru fail.vap_id[%u]}", mac_vap->vap_id);
1695         return -HI_ERR_CODE_PTR_NULL;
1696     }
1697 
1698     oal_net_tx_stop_all_queues();
1699     wal_netdev_stop(netdev);
1700 
1701     /* **************************************************************************
1702                                 抛事件到wal层处理
1703     ************************************************************************** */
1704     /* 初始化删除vap 参数 */
1705     ((mac_cfg_del_vap_param_stru *)write_msg.auc_value)->net_dev = netdev;
1706 
1707     hi_u32 ret = wal_cfg80211_del_p2p_proc(&write_msg, netdev, mac_vap);
1708     if (ret != HI_SUCCESS) {
1709         return -HI_FAIL;
1710     }
1711 
1712     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_DEL_VAP, sizeof(mac_cfg_del_vap_param_stru));
1713 
1714     /* 启动linux work 删除net_device */
1715 #ifdef _PRE_WLAN_FEATURE_P2P
1716     hmac_vap->del_net_device = netdev;
1717 #endif
1718 
1719     ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE,
1720         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(mac_cfg_del_vap_param_stru), (hi_u8 *)&write_msg, HI_TRUE, &rsp_msg);
1721 
1722     if (wal_check_and_release_msg_resp(rsp_msg) != HI_SUCCESS) {
1723         oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_del_virtual_intf::wal_check_and_release_msg_resp fail}");
1724     }
1725 
1726     if (oal_unlikely(ret != HI_SUCCESS)) {
1727         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_del_virtual_intf::return err code %d}", ret);
1728         return -HI_FAIL;
1729     }
1730 
1731     return HI_SUCCESS;
1732 }
1733 
1734 /* P2P 补充缺失的CFG80211接口 */
wal_cfg80211_mgmt_frame_register(struct wiphy * wiphy,struct wireless_dev * wdev,hi_u16 frame_type,bool reg)1735 hi_void wal_cfg80211_mgmt_frame_register(struct wiphy *wiphy, struct wireless_dev *wdev, hi_u16 frame_type, bool reg)
1736 {
1737     return;
1738 }
1739 
wal_cfg80211_set_bitrate_mask(struct wiphy * wiphy,oal_net_device_stru * netdev,const hi_u8 * peer,const struct cfg80211_bitrate_mask * mask)1740 hi_s32 wal_cfg80211_set_bitrate_mask(struct wiphy *wiphy, oal_net_device_stru *netdev, const hi_u8 *peer,
1741     const struct cfg80211_bitrate_mask *mask)
1742 {
1743     return HI_SUCCESS;
1744 }
1745 
1746 /* ****************************************************************************
1747  函 数 名  : wal_cfg80211_start_p2p_device
1748  功能描述  : 启动P2P_DEV
1749  输入参数  : oal_wiphy_stru       *pst_wiphy
1750              oal_wireless_dev   *pst_wdev
1751  输出参数  : 无
1752  返 回 值  : static hi_s32
1753  调用函数  :
1754  被调函数  :
1755 
1756  修改历史      :
1757   1.日    期   : 2014年11月22日
1758     作    者   : HiSilicon
1759     修改内容   : 新生成函数
1760 
1761 **************************************************************************** */
wal_cfg80211_start_p2p_device(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev)1762 static hi_s32 wal_cfg80211_start_p2p_device(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev)
1763 {
1764     return -HI_FAIL;
1765 }
1766 
1767 /* ****************************************************************************
1768  函 数 名  : wal_cfg80211_stop_p2p_device
1769  功能描述  : 停止P2P_DEV
1770  输入参数  : oal_wiphy_stru       *pst_wiphy
1771              oal_wireless_dev   *pst_wdev
1772  输出参数  : 无
1773  返 回 值  : static hi_s32
1774  调用函数  :
1775  被调函数  :
1776 
1777  修改历史      :
1778   1.日    期   : 2014年11月22日
1779     作    者   : HiSilicon
1780     修改内容   : 新生成函数
1781 
1782 **************************************************************************** */
wal_cfg80211_stop_p2p_device(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev)1783 static hi_void wal_cfg80211_stop_p2p_device(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev)
1784 {
1785 }
1786 
1787 /* ****************************************************************************
1788  函 数 名  : wal_cfg80211_set_power_mgmt
1789  功能描述  : 开关低功耗
1790  输入参数  : oal_wiphy_stru       *pst_wiphy
1791              oal_wireless_dev   *pst_wdev
1792  输出参数  : 无
1793  返 回 值  : static hi_s32
1794  调用函数  :
1795  被调函数  :
1796 
1797  修改历史      :
1798   1.日    期   : 2015年07月22日
1799     作    者   : HiSilicon
1800     修改内容   : 新生成函数
1801 
1802 **************************************************************************** */
wal_cfg80211_set_power_mgmt(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,bool enabled,hi_s32 timeout)1803 static hi_s32 wal_cfg80211_set_power_mgmt(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, bool enabled,
1804     hi_s32 timeout)
1805 {
1806     wal_msg_write_stru           write_msg;
1807     mac_cfg_ps_open_stru        *sta_pm_open = HI_NULL;
1808     hi_u32                       ret;
1809     mac_vap_stru                *mac_vap = HI_NULL;
1810 
1811     /* host低功耗没有开,此时不开device的低功耗 */
1812     if (!hmac_get_wlan_pm_switch()) {
1813         return HI_SUCCESS;
1814     }
1815 
1816     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_SET_STA_PM_ON, sizeof(mac_cfg_ps_open_stru));
1817     mac_vap = oal_net_dev_priv(netdev);
1818     if (oal_unlikely(mac_vap == NULL)) {
1819         oam_warning_log0(0, OAM_SF_PWR, "{wal_cfg80211_set_power_mgmt::get mac vap failed.}");
1820         return HI_SUCCESS;
1821     }
1822 
1823     /* P2P dev不下发 */
1824     if (is_p2p_dev(mac_vap)) {
1825         oam_warning_log0(0, OAM_SF_PWR, "wal_cfg80211_set_power_mgmt:vap is p2p dev return");
1826         return HI_SUCCESS;
1827     }
1828 
1829     oam_warning_log3(0, OAM_SF_PWR, "{wal_cfg80211_set_power_mgmt::vap mode[%d]p2p mode[%d]set pm:[%d]}",
1830         mac_vap->vap_mode, mac_vap->p2p_mode, enabled);
1831 
1832     sta_pm_open = (mac_cfg_ps_open_stru *)(write_msg.auc_value);
1833     /* MAC_STA_PM_SWITCH_ON / MAC_STA_PM_SWITCH_OFF */
1834     sta_pm_open->pm_enable = enabled;
1835     sta_pm_open->pm_ctrl_type = MAC_STA_PM_CTRL_TYPE_HOST;
1836 
1837     ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE, WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(mac_cfg_ps_open_stru),
1838         (hi_u8 *)&write_msg, HI_FALSE, HI_NULL);
1839     if (ret != HI_SUCCESS) {
1840         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_set_power_mgmt::fail to send pm cfg msg, error[%u]}", ret);
1841         return -HI_FAIL;
1842     }
1843 
1844     return HI_SUCCESS;
1845 }
1846 
1847 /* ****************************************************************************
1848  函 数 名  : wal_cfg80211_start_sched_scan
1849  功能描述  :
1850  输入参数  : 无
1851  输出参数  : 无
1852  返 回 值  :
1853  调用函数  :
1854  被调函数  :
1855 
1856  修改历史      :
1857   1.日    期   : 2015年6月9日
1858     作    者   : HiSilicon
1859     修改内容   : 新生成函数
1860 
1861 **************************************************************************** */
wal_cfg80211_start_sched_scan(oal_net_device_stru * netdev,mac_pno_scan_stru * pno_scan_info)1862 hi_u32 wal_cfg80211_start_sched_scan(oal_net_device_stru *netdev, mac_pno_scan_stru *pno_scan_info)
1863 {
1864     mac_pno_scan_stru      *pno_scan_params = HI_NULL;
1865     hi_u32                  ret;
1866 
1867     /* 申请pno调度扫描参数,此处申请hmac层释放 */
1868     pno_scan_params = (mac_pno_scan_stru *)oal_mem_alloc(OAL_MEM_POOL_ID_LOCAL, sizeof(mac_pno_scan_stru));
1869     if (pno_scan_params == HI_NULL) {
1870         oam_warning_log0(0, OAM_SF_SCAN, "{wal_cfg80211_start_sched_scan::alloc pno scan param memory failed!}\r\n");
1871         return HI_ERR_CODE_PTR_NULL;
1872     }
1873 
1874     if (memcpy_s(pno_scan_params, sizeof(mac_pno_scan_stru), pno_scan_info, sizeof(mac_pno_scan_stru)) != EOK) {
1875         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_start_sched_scan::mem safe function err!}");
1876         oal_mem_free(pno_scan_params);
1877         return HI_FAIL;
1878     }
1879 
1880     ret = (hi_u32)wal_cfg80211_start_req(netdev, &pno_scan_params, sizeof(mac_pno_scan_stru),
1881         WLAN_CFGID_CFG80211_START_SCHED_SCAN, HI_TRUE);
1882     if (ret != HI_SUCCESS) {
1883         oal_mem_free(pno_scan_params);
1884         return ret;
1885     }
1886 
1887     return HI_SUCCESS;
1888 }
1889 
1890 /* ****************************************************************************
1891  函 数 名  : wal_cfg80211_sched_scan_stop
1892  功能描述  : 调度扫描关闭
1893  输入参数  : oal_wiphy_stru                       *pst_wiphy
1894              oal_net_device_stru                  *pst_netdev
1895  输出参数  : 无
1896  返 回 值  : static hi_s32
1897  调用函数  :
1898  被调函数  :
1899 
1900  修改历史      :
1901   1.日    期   : 2015年6月9日
1902     作    者   : HiSilicon
1903     修改内容   : 新生成函数
1904 
1905 **************************************************************************** */
wal_cfg80211_sched_scan_stop(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev)1906 static hi_s32 wal_cfg80211_sched_scan_stop(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev)
1907 {
1908     hmac_device_stru               *hmac_dev = HI_NULL;
1909     mac_device_stru                *mac_device = HI_NULL;
1910     hmac_scan_stru                 *scan_mgmt = HI_NULL;
1911     wal_msg_write_stru              write_msg;
1912     hi_u32                          pedding_data = 0;       /* 填充数据,不使用,只是为了复用接口 */
1913     hi_u32                          ret;
1914 
1915     /* 参数合法性检查 */
1916     if ((wiphy == HI_NULL) || (netdev == HI_NULL)) {
1917         oam_error_log2(0, OAM_SF_CFG,
1918             "{wal_cfg80211_sched_scan_stop::input param pointer is null, pst_wiphy[%p], pst_netdev[%p]!}",
1919             (uintptr_t)wiphy, (uintptr_t)netdev);
1920         goto fail;
1921     }
1922 
1923     /* 通过net_device 找到对应的mac_device_stru 结构 */
1924     hmac_dev = (hmac_device_stru *)hmac_get_device_stru();
1925     scan_mgmt = &(hmac_dev->scan_mgmt);
1926 
1927     oam_warning_log2(0, OAM_SF_SCAN, "{wal_cfg80211_sched_scan_stop::sched scan req[%p],sched scan complete[%d]}",
1928         (uintptr_t)scan_mgmt->sched_scan_req, scan_mgmt->sched_scan_complete);
1929 
1930     if ((scan_mgmt->sched_scan_req != HI_NULL) && (scan_mgmt->sched_scan_complete != HI_TRUE)) {
1931 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1932         /* 如果正常扫描请求未执行,则上报调度扫描结果 */
1933         if (scan_mgmt->request == HI_NULL) {
1934             mac_device = mac_res_get_dev();
1935             oal_cfg80211_sched_scan_result(mac_device->wiphy);
1936         }
1937 #endif
1938         scan_mgmt->sched_scan_req = HI_NULL;
1939         scan_mgmt->sched_scan_complete = HI_TRUE;
1940 
1941         /* 拋事件通知device侧停止PNO调度扫描 */
1942         wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_CFG80211_STOP_SCHED_SCAN, sizeof(pedding_data));
1943         if (memcpy_s(write_msg.auc_value, sizeof(write_msg.auc_value),
1944             (hi_s8 *)&pedding_data, sizeof(pedding_data)) != EOK) {
1945             oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_sched_scan_stop::mem safe function err!}");
1946             goto fail;
1947         }
1948 
1949         ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE, WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(pedding_data),
1950             (hi_u8 *)&write_msg, HI_FALSE, HI_NULL);
1951         if (ret != HI_SUCCESS) {
1952             oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_sched_scan_stop::fail to stop pno sched scan, error[%u]}",
1953                 ret);
1954             goto fail;
1955         }
1956     }
1957 
1958     return HI_SUCCESS;
1959 fail:
1960 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
1961     return HI_FAIL;
1962 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1963     return -HI_FAIL;
1964 #endif
1965 }
1966 
1967 /* ****************************************************************************
1968  函 数 名  : wal_cfg80211_stop_ap
1969  功能描述  : 停止AP
1970  输入参数  : oal_wiphy_stru        *pst_wiphy
1971              oal_net_device_stru *pst_netdev
1972  输出参数  : 无
1973  返 回 值  : static hi_s32
1974  调用函数  :
1975  被调函数  :
1976 
1977  修改历史      :
1978   1.日    期   : 2014年12月31日
1979     作    者   : HiSilicon
1980     修改内容   : 新生成函数
1981 
1982 **************************************************************************** */
wal_cfg80211_stop_ap(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev)1983 hi_s32 wal_cfg80211_stop_ap(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev)
1984 {
1985     wal_msg_write_stru write_msg;
1986 
1987     hi_unref_param(wiphy);
1988 
1989 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
1990     /* 参数合法性检查 */
1991     if (netdev == HI_NULL) {
1992         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_stop_ap::pst_netdev is null!}");
1993         goto fail;
1994     }
1995 #endif
1996     /* 获取vap id */
1997     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
1998     if (mac_vap == HI_NULL) {
1999         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_stop_ap::can't get mac vap from netdevice priv data!}");
2000         goto fail;
2001     }
2002 
2003     /* 判断是否为非ap模式 */
2004     if ((mac_vap->vap_mode != WLAN_VAP_MODE_BSS_AP)
2005 #ifdef _PRE_WLAN_FEATURE_MESH
2006         && (mac_vap->vap_mode != WLAN_VAP_MODE_MESH)
2007 #endif
2008     ) {
2009         oam_error_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_stop_ap::vap is not in ap mode!}");
2010         goto fail;
2011     }
2012 
2013     /* 如果netdev不是running状态,则不需要down */
2014     if ((oal_netdevice_flags(netdev) & OAL_IFF_RUNNING) == 0) {
2015         oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_stop_ap::vap is already down!}\r\n");
2016         return HI_SUCCESS;
2017     }
2018 
2019     /* ****************************************************************************
2020         发送消息,停用ap
2021     **************************************************************************** */
2022     /* 填写消息 */
2023     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_DOWN_VAP, sizeof(mac_cfg_start_vap_param_stru));
2024 
2025 #ifdef _PRE_WLAN_FEATURE_P2P
2026     oal_wireless_dev *wdev = GET_NET_DEV_CFG80211_WIRELESS(netdev);
2027     wlan_p2p_mode_enum_uint8 p2p_mode = wal_wireless_iftype_to_mac_p2p_mode(wdev->iftype);
2028     if (WLAN_P2P_BUTT == p2p_mode) {
2029         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_stop_ap::wal_wireless_iftype_to_mac_p2p_mode return BUFF}\r\n");
2030         goto fail;
2031     }
2032     oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_stop_ap::en_p2p_mode=%u}\r\n", p2p_mode);
2033 
2034     ((mac_cfg_start_vap_param_stru *)write_msg.auc_value)->p2p_mode = p2p_mode;
2035 #endif
2036 
2037     ((mac_cfg_start_vap_param_stru *)write_msg.auc_value)->net_dev = netdev;
2038 
2039     /* 发送消息 */
2040     hi_u32 ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE,
2041         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(mac_cfg_start_vap_param_stru), (hi_u8 *)&write_msg, HI_FALSE, HI_NULL);
2042     if (oal_unlikely(ret != HI_SUCCESS)) {
2043         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_stop_ap::failed to stop ap, error[%u]}", ret);
2044         goto fail;
2045     }
2046 
2047     return HI_SUCCESS;
2048 
2049 fail:
2050 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
2051     return HI_FAIL;
2052 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
2053     return -HI_FAIL;
2054 #endif
2055 }
2056 
wal_cfg80211_set_iftype(const mac_cfg_add_vap_param_stru * add_vap_param,oal_wireless_dev * wdev)2057 hi_void wal_cfg80211_set_iftype(const mac_cfg_add_vap_param_stru *add_vap_param, oal_wireless_dev *wdev)
2058 {
2059     if (add_vap_param->vap_mode == WLAN_VAP_MODE_BSS_AP) {
2060         wdev->iftype = NL80211_IFTYPE_AP;
2061     } else if (add_vap_param->vap_mode == WLAN_VAP_MODE_BSS_STA) {
2062         wdev->iftype = NL80211_IFTYPE_STATION;
2063 #ifdef _PRE_WLAN_FEATURE_MESH
2064     } else if (add_vap_param->vap_mode == WLAN_VAP_MODE_MESH) {
2065         wdev->iftype = NL80211_IFTYPE_MESH_POINT;
2066 #endif
2067     }
2068 
2069 #ifdef _PRE_WLAN_FEATURE_P2P
2070     if (add_vap_param->p2p_mode == WLAN_P2P_DEV_MODE) {
2071         wdev->iftype = NL80211_IFTYPE_P2P_DEVICE;
2072     } else if (add_vap_param->p2p_mode == WLAN_P2P_CL_MODE) {
2073         wdev->iftype = NL80211_IFTYPE_P2P_CLIENT;
2074     } else if (add_vap_param->p2p_mode == WLAN_P2P_GO_MODE) {
2075         wdev->iftype = NL80211_IFTYPE_P2P_GO;
2076     }
2077 #endif
2078 }
2079 
2080 /* ****************************************************************************
2081  函 数 名  : wal_cfg80211_add_vap
2082  功能描述  : CFG80211 接口添加网络设备
2083  输入参数  : mac_cfg_add_vap_param_stru *pst_add_vap_param
2084  输出参数  : 无
2085  返 回 值  : hi_u32
2086  调用函数  :
2087  被调函数  :
2088 
2089  修改历史      :
2090   1.日    期   : 2015年1月3日
2091     作    者   : HiSilicon
2092     修改内容   : 新生成函数
2093 
2094 **************************************************************************** */
2095 #ifndef _PRE_HDF_LINUX
wal_cfg80211_add_vap(const mac_cfg_add_vap_param_stru * add_vap_param)2096 hi_u32 wal_cfg80211_add_vap(const mac_cfg_add_vap_param_stru *add_vap_param)
2097 {
2098     wal_msg_write_stru     write_msg;
2099     wal_msg_stru          *rsp_msg    = HI_NULL;
2100     oal_net_device_stru   *netdev     = add_vap_param->net_dev;
2101     oal_wireless_dev      *wdev       = GET_NET_DEV_CFG80211_WIRELESS(netdev);
2102     oal_net_device_stru   *netdev_cfg = oal_get_netdev_by_name(WLAN_CFG_VAP_NAME);
2103 
2104     if (netdev_cfg == HI_NULL) {
2105         oal_mem_free(wdev);
2106         oal_net_free_netdev(netdev);
2107         oam_warning_log0(WLAN_CFG_VAP_ID, OAM_SF_ANY, "{wal_cfg80211_add_vap::pst_cfg_net_dev is null!}");
2108         return HI_FAIL;
2109     }
2110 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
2111     oal_dev_put(netdev_cfg);
2112 #endif
2113     wal_cfg80211_set_iftype(add_vap_param, wdev);
2114 
2115     oal_netdevice_flags(netdev) &= ~OAL_IFF_RUNNING; /* 将net device的flag设为down */
2116 
2117     /* **************************************************************************
2118         抛事件到wal层处理
2119     ************************************************************************** */
2120     /* 填写消息 */
2121     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_ADD_VAP, sizeof(mac_cfg_add_vap_param_stru));
2122     ((mac_cfg_add_vap_param_stru *)write_msg.auc_value)->net_dev      = netdev;
2123     ((mac_cfg_add_vap_param_stru *)write_msg.auc_value)->vap_mode     = add_vap_param->vap_mode;
2124     ((mac_cfg_add_vap_param_stru *)write_msg.auc_value)->cfg_vap_indx = WLAN_CFG_VAP_ID;
2125 #ifdef _PRE_WLAN_FEATURE_P2P
2126     ((mac_cfg_add_vap_param_stru *)write_msg.auc_value)->p2p_mode     = add_vap_param->p2p_mode;
2127 #endif
2128 
2129     /* 发送消息 */
2130     hi_u32 ret = wal_send_cfg_event(netdev_cfg, WAL_MSG_TYPE_WRITE,
2131         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(mac_cfg_add_vap_param_stru), (hi_u8 *)&write_msg, HI_TRUE, &rsp_msg);
2132     if (oal_unlikely(ret != HI_SUCCESS)) {
2133         oal_mem_free(wdev);
2134         oal_net_free_netdev(netdev);
2135         oam_warning_log1(WLAN_CFG_VAP_ID, OAM_SF_ANY, "{wal_cfg80211_add_vap::return err code [%u]}", ret);
2136         return ret;
2137     }
2138 
2139     /* 读取返回的错误码 */
2140     ret = wal_check_and_release_msg_resp(rsp_msg);
2141     if (ret != HI_SUCCESS) {
2142         oam_warning_log1(WLAN_CFG_VAP_ID, OAM_SF_ANY, "{wal_cfg80211_add_vap::hmac add vap Err=%u}", ret);
2143         /* 异常处理,释放内存 */
2144         oal_mem_free(wdev);
2145         oal_net_free_netdev(netdev);
2146         return ret;
2147     }
2148 
2149     wal_set_mac_to_mib(add_vap_param->net_dev); /* by lixu tmp */
2150 
2151     return HI_SUCCESS;
2152 }
2153 #endif
2154 
2155 /* ****************************************************************************
2156  函 数 名  : wal_cfg80211_del_vap
2157  功能描述  : CFG80211 接口删除网络设备
2158  输入参数  : mac_cfg_del_vap_param_stru *pst_del_vap_param
2159  输出参数  : 无
2160  返 回 值  : hi_u32
2161  调用函数  :
2162  被调函数  :
2163 
2164  修改历史      :
2165   1.日    期   : 2015年1月3日
2166     作    者   : HiSilicon
2167     修改内容   : 新生成函数
2168 
2169 **************************************************************************** */
wal_cfg80211_del_vap(const mac_cfg_del_vap_param_stru * del_vap_param)2170 hi_u32 wal_cfg80211_del_vap(const mac_cfg_del_vap_param_stru *del_vap_param)
2171 {
2172     hi_u32                       ret;
2173     wal_msg_write_stru           write_msg;
2174     wal_msg_stru                *rsp_msg = HI_NULL;
2175     oal_net_device_stru         *netdev = HI_NULL;
2176 
2177     if (oal_unlikely(del_vap_param == HI_NULL)) {
2178         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_del_vap::pst_del_vap_param null ptr !}\r\n");
2179         return HI_ERR_CODE_PTR_NULL;
2180     }
2181 
2182     netdev = del_vap_param->net_dev;
2183     /* 设备在up状态不允许删除,必须先down */
2184     if (oal_unlikely((OAL_IFF_RUNNING & oal_netdevice_flags(netdev)) != 0)) {
2185         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_del_vap::device is busy, please down it first %d!}\r\n",
2186             oal_netdevice_flags(netdev));
2187         return HI_ERR_CODE_CONFIG_BUSY;
2188     }
2189 
2190     /* **************************************************************************
2191                                 抛事件到wal层处理
2192     ************************************************************************** */
2193     /* 初始化删除vap 参数 */
2194     ((mac_cfg_del_vap_param_stru *)write_msg.auc_value)->net_dev = netdev;
2195 #ifdef _PRE_WLAN_FEATURE_P2P
2196     ((mac_cfg_del_vap_param_stru *)write_msg.auc_value)->p2p_mode = del_vap_param->p2p_mode;
2197 #endif
2198     wal_write_msg_hdr_init(&write_msg, WLAN_CFGID_DEL_VAP, sizeof(mac_cfg_del_vap_param_stru));
2199 
2200     ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE,
2201         WAL_MSG_WRITE_MSG_HDR_LENGTH + sizeof(mac_cfg_del_vap_param_stru), (hi_u8 *)&write_msg, HI_TRUE, &rsp_msg);
2202     if (ret != HI_SUCCESS) {
2203         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_del_vap::return err code [%u]!}\r\n", ret);
2204         return ret;
2205     }
2206 
2207     if (HI_SUCCESS != wal_check_and_release_msg_resp(rsp_msg)) {
2208         oam_warning_log0(0, OAM_SF_ANY, "{wal_cfg80211_del_vap::wal_check_and_release_msg_resp fail!}");
2209         return HI_FAIL;
2210     }
2211 
2212     return HI_SUCCESS;
2213 }
2214 
2215 /* ****************************************************************************
2216  函 数 名  : wal_cfg80211_start_connect
2217  功能描述  :
2218  输入参数  : 无
2219  输出参数  : 无
2220  返 回 值  :
2221  调用函数  :
2222  被调函数  :
2223 
2224  修改历史      :
2225   1.日    期   : 2013年8月30日
2226     作    者   : HiSilicon
2227     修改内容   : 新生成函数
2228 
2229 **************************************************************************** */
wal_cfg80211_start_connect(oal_net_device_stru * netdev,const mac_cfg80211_connect_param_stru * mac_cfg80211_connect_param)2230 hi_u32 wal_cfg80211_start_connect(oal_net_device_stru *netdev,
2231     const mac_cfg80211_connect_param_stru *mac_cfg80211_connect_param)
2232 {
2233     return wal_cfg80211_start_req(netdev, mac_cfg80211_connect_param, sizeof(mac_cfg80211_connect_param_stru),
2234         WLAN_CFGID_CFG80211_START_CONNECT, HI_TRUE);
2235 }
2236 
2237 /* ****************************************************************************
2238  函 数 名  : wal_cfg80211_start_disconnect
2239  功能描述  :
2240  输入参数  : 无
2241  输出参数  : 无
2242  返 回 值  :
2243  调用函数  :
2244  被调函数  :
2245 
2246  修改历史      :
2247   1.日    期   : 2013年8月30日
2248     作    者   : HiSilicon
2249     修改内容   : 新生成函数
2250 
2251 **************************************************************************** */
wal_cfg80211_start_disconnect(oal_net_device_stru * netdev,const mac_cfg_kick_user_param_stru * disconnect_param)2252 hi_u32 wal_cfg80211_start_disconnect(oal_net_device_stru *netdev, const mac_cfg_kick_user_param_stru *disconnect_param)
2253 {
2254     /* 注意 由于消息未真正处理就直接返回,导致WPA_SUPPLICANT继续下发消息,在驱动侧等到处理时被异常唤醒,
2255        导致后续下发的消息误以为操作失败,目前将去关联事件修改为等待消息处理结束后再上报,
2256        最后一个入参由HI_FALSE改为HI_TRUE */
2257     return wal_cfg80211_start_req(netdev, disconnect_param, sizeof(mac_cfg_kick_user_param_stru), WLAN_CFGID_KICK_USER,
2258         HI_TRUE);
2259 }
2260 
2261 /* ****************************************************************************
2262  函 数 名  : wal_cfg80211_unregister_netdev
2263  功能描述  : 内核去注册指定类型的net_device,用于需要解mutex lock的应用
2264  输入参数  : mac_device_stru *pst_hmac_device
2265              oal_net_device_stru *pst_net_dev
2266  输出参数  : 无
2267  返 回 值  : 无
2268  调用函数  :
2269  被调函数  :
2270 
2271  修改历史      :
2272   1.日    期   : 2015年7月24日
2273     作    者   : HiSilicon
2274     修改内容   : 新生成函数
2275 
2276 **************************************************************************** */
wal_cfg80211_unregister_netdev(oal_net_device_stru * netdev)2277 hi_void wal_cfg80211_unregister_netdev(oal_net_device_stru *netdev)
2278 {
2279     /* 去注册netdev */
2280     oal_net_unregister_netdev(netdev);
2281     oal_net_free_netdev(netdev);
2282 }
2283 
2284 #if (LINUX_VERSION_CODE >= kernel_version(4, 1, 0))
wal_cfg80211_abort_scan(oal_wiphy_stru * wiphy,oal_wireless_dev * wdev)2285 static hi_void wal_cfg80211_abort_scan(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev)
2286 {
2287     oal_net_device_stru *netdev = HI_NULL;
2288 
2289     /* 1.1 入参检查 */
2290     if ((wiphy == HI_NULL) || (wdev == HI_NULL)) {
2291         oam_error_log2(0, OAM_SF_CFG, "{wal_cfg80211_abort_scan::wiphy or wdev is null, %p, %p!}", wiphy, wdev);
2292         return;
2293     }
2294     netdev = wdev->netdev;
2295     if (netdev == HI_NULL) {
2296         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_abort_scan::netdev is null!}\r\n");
2297         return;
2298     }
2299     oam_warning_log0(0, OAM_SF_CFG, "{wal_cfg80211_abort_scan::enter!}\r\n");
2300     wal_force_scan_complete(netdev);
2301     return;
2302 }
2303 #endif
2304 #endif /* #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) */
2305 
2306 /* ****************************************************************************
2307  函 数 名  : wal_parse_rsn_ie
2308  功能描述  : 解析beacon帧中的 RSN 信息元素
2309  输入参数  : [1]puc_ie
2310              [2]beacon_param
2311  输出参数  : 无
2312  返 回 值  : hi_u32
2313 **************************************************************************** */
wal_parse_rsn_ie(const hi_u8 * puc_ie,mac_beacon_param_stru * beacon_param)2314 hi_u32 wal_parse_rsn_ie(const hi_u8 *puc_ie, mac_beacon_param_stru *beacon_param)
2315 {
2316     hi_u16 us_temp, auth_temp;
2317 
2318     /* *********************************************************************** */
2319     /*                  RSN Element Format                                   */
2320     /* --------------------------------------------------------------------- */
2321     /* |Element ID | Length | Version | Group Cipher Suite | Pairwise Cipher */
2322     /* --------------------------------------------------------------------- */
2323     /* |     1     |    1   |    2    |         4          |       2         */
2324     /* --------------------------------------------------------------------- */
2325     /* --------------------------------------------------------------------- */
2326     /* Suite Count| Pairwise Cipher Suite List | AKM Suite Count | AKM Suite List */
2327     /* ---------------------------------------------------------------------  */
2328     /*            |         4*m                |     2           |   4*n      */
2329     /* ---------------------------------------------------------------------  */
2330     /* ---------------------------------------------------------------------  */
2331     /* |RSN Capabilities|PMKID Count|PMKID List|Group Management Cipher Suite */
2332     /* ---------------------------------------------------------------------  */
2333     /* |        2       |    2      |   16 *s  |               4           |  */
2334     /* ---------------------------------------------------------------------  */
2335     /*                                                                        */
2336     /* ************************************************************************ */
2337     hi_u8 auc_oui[MAC_OUI_LEN] = {MAC_WLAN_OUI_RSN0, MAC_WLAN_OUI_RSN1, MAC_WLAN_OUI_RSN2};
2338     hi_u8 index = 2; /* 2: 忽略 RSN IE 和 IE 长度 */
2339 
2340     /* 长度若小于2,取后面的值都会异常 */
2341     if (puc_ie[1] < MAC_MIN_RSN_LEN) {
2342         oam_warning_log1(0, OAM_SF_ANY, "{wal_parse_rsn_ie::invalid RSN IE len[%d]!}\r\n", puc_ie[1]);
2343         return HI_FAIL;
2344     }
2345 
2346     /* 获取RSN 版本号 */
2347     if (hi_makeu16(puc_ie[index], puc_ie[index + 1]) != MAC_RSN_IE_VERSION) {
2348         oam_error_log0(0, OAM_SF_ANY, "{wal_parse_rsn_ie::RSN version illegal!}\r\n");
2349         return HI_FAIL;
2350     }
2351 
2352     index += 2; /* 2: 忽略 RSN 版本号长度 */
2353 
2354     /* 获取组播密钥套件 */
2355     if (memcmp(auc_oui, puc_ie + index, MAC_OUI_LEN) != 0) {
2356         oam_error_log0(0, OAM_SF_ANY, "{wal_parse_rsn_ie::RSN group OUI illegal!}\r\n");
2357         return HI_FAIL;
2358     }
2359     beacon_param->group_crypto = puc_ie[index + MAC_OUI_LEN];
2360 
2361     index += 4; /* 4: 忽略组播密钥套件长度 */
2362 
2363     /* 获取成对密钥套件 */
2364     hi_u16 us_pcip_num = hi_makeu16(puc_ie[index], puc_ie[index + 1]);
2365     if (us_pcip_num > MAC_PAIRWISE_CIPHER_SUITES_NUM) {
2366         oam_error_log1(0, OAM_SF_ANY, "{wal_parse_rsn_ie::pairwise chiper num illegal!}\r\n", us_pcip_num);
2367         return HI_FAIL;
2368     }
2369 
2370     /* 将加密套件初始化为0xff */ /* 安全编程规则6.6例外(1) 固定长度的结构体进行内存初始化 */
2371     memset_s(beacon_param->auc_pairwise_crypto_wpa2, MAC_PAIRWISE_CIPHER_SUITES_NUM, 0xff,
2372         MAC_PAIRWISE_CIPHER_SUITES_NUM);
2373 
2374     index += 2; /* 2: 获取加密套件 */
2375     for (us_temp = 0; us_temp < us_pcip_num; us_temp++) {
2376         if (memcmp(auc_oui, puc_ie + index, MAC_OUI_LEN) != 0) {
2377             oam_error_log0(0, OAM_SF_ANY, "{wal_parse_rsn_ie::RSN paerwise OUI illegal!}\r\n");
2378             return HI_FAIL;
2379         }
2380         beacon_param->auc_pairwise_crypto_wpa2[us_temp] = puc_ie[index + MAC_OUI_LEN];
2381 
2382         index += 4; /* 4: 套件长度 */
2383     }
2384 
2385     /* 获取认证套件计数 */
2386     hi_u16 us_auth_num = hi_makeu16(puc_ie[index], puc_ie[index + 1]);
2387     us_auth_num = oal_min(us_auth_num, WLAN_AUTHENTICATION_SUITES);
2388     index += 2; /* 2: 获取认证类型 */
2389 
2390     /* 将认证套件初始化为0xff */ /* 安全编程规则6.6例外(1) 固定长度的结构体进行内存初始化 */
2391     memset_s(beacon_param->auc_auth_type, us_auth_num, 0xff, us_auth_num);
2392 
2393     /* 获取认证类型 */
2394     for (auth_temp = 0; auth_temp < us_auth_num; auth_temp++) {
2395         if (memcmp(auc_oui, puc_ie + index, MAC_OUI_LEN) != 0) {
2396             oam_error_log0(0, OAM_SF_ANY, "{wal_parse_rsn_ie::RSN auth OUI illegal!}\r\n");
2397             return HI_FAIL;
2398         }
2399         beacon_param->auc_auth_type[auth_temp] = puc_ie[index + MAC_OUI_LEN];
2400         index += 4; /* 4: 类型长度 */
2401     }
2402 
2403     /* 获取RSN 能力信息 */
2404     beacon_param->us_rsn_capability = hi_makeu16(puc_ie[index], puc_ie[index + 1]);
2405 
2406     /* 设置加密模式 */
2407     beacon_param->crypto_mode |= WLAN_WPA2_BIT;
2408 
2409     return HI_SUCCESS;
2410 }
2411 
2412 /* ****************************************************************************
2413  函 数 名  : wal_parse_wpa_ie
2414  功能描述  : 解析beacon帧中的 WPA 信息元素
2415  输入参数  : [1]puc_ie
2416              [2]beacon_param
2417  输出参数  : 无
2418  返 回 值  : hi_u32
2419 **************************************************************************** */
wal_parse_wpa_ie(const hi_u8 * puc_ie,mac_beacon_param_stru * beacon_param)2420 hi_u32 wal_parse_wpa_ie(const hi_u8 *puc_ie, mac_beacon_param_stru *beacon_param)
2421 {
2422     hi_u8  auc_oui[MAC_OUI_LEN] = {MAC_WLAN_OUI_MICRO0, MAC_WLAN_OUI_MICRO1, MAC_WLAN_OUI_MICRO2};
2423     hi_u16 us_temp, auth_temp;
2424 
2425     /* ************************************************************************ */
2426     /*                  WPA Element Format                                    */
2427     /* ---------------------------------------------------------------------  */
2428     /* |Element ID | Length |    WPA OUI    |  Version |  Group Cipher Suite  */
2429     /* ---------------------------------------------------------------------  */
2430     /* |     1     |   1    |        4      |     2    |         4            */
2431     /* ---------------------------------------------------------------------  */
2432     /* ---------------------------------------------------------------------  */
2433     /* Pairwise Cipher |  Pairwise Cipher   |                 |               */
2434     /* Suite Count     |    Suite List      | AKM Suite Count |AKM Suite List */
2435     /* ---------------------------------------------------------------------  */
2436     /*        2        |          4*m       |         2       |     4*n       */
2437     /* ---------------------------------------------------------------------  */
2438     /*                                                                        */
2439     /* ************************************************************************ */
2440     hi_u8 index = 2 + 4; /* 2 4: 忽略 WPA IE(1 字节) ,IE 长度(1 字节) ,WPA OUI(4 字节) */
2441 
2442     hi_u16 us_ver = hi_makeu16(puc_ie[index], puc_ie[index + 1]);
2443     /* 对比WPA 版本信息 */
2444     if (us_ver != MAC_WPA_IE_VERSION) {
2445         oam_error_log0(0, OAM_SF_WPA, "{wal_parse_wpa_ie::WPA version illegal!}\r\n");
2446         return HI_FAIL;
2447     }
2448 
2449     index += 2; /* 2: 忽略 版本号 长度 */
2450 
2451     hi_u8 *puc_pcip_policy = beacon_param->auc_pairwise_crypto_wpa;
2452     hi_u8 *puc_auth_policy = beacon_param->auc_auth_type;
2453 
2454     /* 获取组播密钥套件 */
2455     if (memcmp(auc_oui, puc_ie + index, MAC_OUI_LEN) != 0) {
2456         oam_error_log0(0, OAM_SF_WPA, "{wal_parse_wpa_ie::WPA group OUI illegal!}\r\n");
2457         return HI_FAIL;
2458     }
2459     beacon_param->group_crypto = puc_ie[index + MAC_OUI_LEN];
2460 
2461     index += 4; /* 4: 忽略组播密钥套件长度 */
2462 
2463     /* 获取成对密钥套件 */
2464     hi_u16 us_pcip_num = hi_makeu16(puc_ie[index], puc_ie[index + 1]);
2465     if (us_pcip_num > MAC_PAIRWISE_CIPHER_SUITES_NUM) {
2466         oam_error_log1(0, OAM_SF_WPA, "{wal_parse_wpa_ie::pairwise chiper num illegal %d!}\r\n", us_pcip_num);
2467         return HI_FAIL;
2468     }
2469 
2470     /* 将加密套件初始化为0xff */ /* 安全编程规则6.6例外(1) 对固定长度的数组进行初始化 */
2471     memset_s(beacon_param->auc_pairwise_crypto_wpa, MAC_PAIRWISE_CIPHER_SUITES_NUM, 0xff,
2472         MAC_PAIRWISE_CIPHER_SUITES_NUM);
2473 
2474     index += 2; /* 2: 获取套件 */
2475     for (us_temp = 0; us_temp < us_pcip_num; us_temp++) {
2476         if (memcmp(auc_oui, puc_ie + index, MAC_OUI_LEN) != 0) {
2477             oam_error_log0(0, OAM_SF_WPA, "{wal_parse_wpa_ie::WPA pairwise OUI illegal!}\r\n");
2478             return HI_FAIL;
2479         }
2480         puc_pcip_policy[us_temp] = puc_ie[index + MAC_OUI_LEN];
2481         index += 4; /* 4: 套件长度 */
2482     }
2483 
2484     /* 获取认证套件计数 */
2485     hi_u16 us_auth_num = hi_makeu16(puc_ie[index], puc_ie[index + 1]);
2486     us_auth_num = oal_min(us_auth_num, MAC_AUTHENTICATION_SUITE_NUM);
2487     index += 2; /* 2 获取认证类型 */
2488 
2489     /* 将认证套件初始化为0xff */
2490     if (memset_s(puc_auth_policy, us_auth_num, 0xff, us_auth_num) != EOK) {
2491         return HI_FAIL;
2492     }
2493     /* 获取认证类型 */
2494     for (auth_temp = 0; auth_temp < us_auth_num; auth_temp++) {
2495         if (memcmp(auc_oui, puc_ie + index, MAC_OUI_LEN) != 0) {
2496             oam_error_log0(0, OAM_SF_WPA, "{wal_parse_wpa_ie::WPA auth OUI illegal!}\r\n");
2497             return HI_FAIL;
2498         }
2499         puc_auth_policy[auth_temp] = puc_ie[index + MAC_OUI_LEN];
2500         index += 4; /* 4: 类型长度 */
2501     }
2502 
2503     /* 设置加密模式 */
2504     beacon_param->crypto_mode |= WLAN_WPA_BIT;
2505 
2506     return HI_SUCCESS;
2507 }
2508 
2509 /* ****************************************************************************
2510  函 数 名  : wal_parse_wpa_wpa2_ie
2511  功能描述  : 解析内核传递过来的beacon信息中的WPA/WPA2 信息元素
2512  输入参数  : oal_beacon_parameters *pst_beacon_info
2513              mac_beacon_param_stru *pst_beacon_param
2514  输出参数  : 无
2515  返 回 值  : hi_u32
2516  调用函数  :
2517  被调函数  :
2518 
2519  修改历史      :
2520   1.日    期   : 2013年12月11日
2521     作    者   : HiSilicon
2522     修改内容   : 新生成函数
2523 
2524 **************************************************************************** */
wal_parse_wpa_wpa2_ie(const oal_beacon_parameters * beacon_info,mac_beacon_param_stru * beacon_param)2525 hi_u32 wal_parse_wpa_wpa2_ie(const oal_beacon_parameters *beacon_info, mac_beacon_param_stru *beacon_param)
2526 {
2527     const hi_u8         *puc_rsn_ie = HI_NULL;
2528     hi_u8               *puc_wpa_ie = HI_NULL;
2529     hi_u32               ret;
2530     oal_ieee80211_mgmt  *mgmt   = HI_NULL;
2531     hi_u16               us_capability_info;
2532 
2533     /* 判断是否加密 */
2534     mgmt = (oal_ieee80211_mgmt *)beacon_info->head;
2535     us_capability_info = mgmt->u.beacon.capab_info;
2536     beacon_param->privacy = HI_FALSE;
2537     if (WLAN_WITP_CAPABILITY_PRIVACY & us_capability_info) {
2538         beacon_param->privacy = HI_TRUE;
2539 
2540         /* 查找 RSN 信息元素 */
2541         puc_rsn_ie = mac_find_ie(MAC_EID_RSN, beacon_info->tail, beacon_info->tail_len);
2542         if (puc_rsn_ie != HI_NULL) {
2543             /* 根据RSN 信息元素解析出认证类型 */
2544             ret = wal_parse_rsn_ie(puc_rsn_ie, beacon_param);
2545             if (ret != HI_SUCCESS) {
2546                 oam_warning_log0(0, OAM_SF_WPA, "{wal_parse_wpa_wpa2_ie::Failed to parse RSN ie!}\r\n");
2547                 return HI_FAIL;
2548             }
2549         }
2550 
2551         /* 查找 WPA 信息元素,并解析出认证类型 */
2552         puc_wpa_ie = mac_find_vendor_ie(MAC_WLAN_OUI_MICROSOFT, MAC_OUITYPE_WPA, beacon_info->tail,
2553             (hi_s32)beacon_info->tail_len);
2554         if (puc_wpa_ie != HI_NULL) {
2555             ret = wal_parse_wpa_ie(puc_wpa_ie, beacon_param);
2556             if (ret != HI_SUCCESS) {
2557                 oam_warning_log0(0, OAM_SF_WPA, "{wal_parse_wpa_wpa2_ie::Failed to parse WPA ie!}\r\n");
2558                 return HI_FAIL;
2559             }
2560         }
2561     }
2562 
2563     return HI_SUCCESS;
2564 }
2565 
2566 #ifdef _PRE_WLAN_FEATURE_MESH
2567 /* ****************************************************************************
2568  功能描述  : 解析内核传递过来beacon信息中的mesh configuration信息元素
2569  输入参数  : oal_beacon_parameters *pst_beacon_info
2570  返 回 值  : hi_u32
2571  修改历史      :
2572   1.日    期   : 2019年3月19日
2573     作    者   : HiSilicon
2574     修改内容   : 新生成函数
2575 
2576 **************************************************************************** */
wal_parse_mesh_conf_ie(const oal_beacon_parameters * beacon_info,mac_beacon_param_stru * beacon_param)2577 hi_u32 wal_parse_mesh_conf_ie(const oal_beacon_parameters *beacon_info, mac_beacon_param_stru *beacon_param)
2578 {
2579     const hi_u8 *puc_mesh_conf_ie = HI_NULL;
2580     hi_u8 index = 0;
2581 
2582     /* 查找 mesh conf信息元素 */
2583     puc_mesh_conf_ie = mac_find_ie(MAC_EID_MESH_CONF, beacon_info->tail, beacon_info->tail_len);
2584     if (puc_mesh_conf_ie != HI_NULL) {
2585         /* 根据Mesh Conf信息元素解析出mesh配置项 */
2586         /* 长度若小于2,取后面的值都会异常 */
2587         if (puc_mesh_conf_ie[1] < MAC_MIN_MESH_CONF_LEN) {
2588             oam_warning_log1(0, OAM_SF_ANY, "{wal_parse_mesh_conf_ie::invalid mesh conf IE len[%d]!}\r\n",
2589                 puc_mesh_conf_ie[1]);
2590             return HI_FAIL;
2591         }
2592 
2593         index += 6; /* 6: 忽略 Mesh conf IE 和 IE 长度 ,选路算法及用塞控制 */
2594         beacon_param->mesh_auth_protocol = puc_mesh_conf_ie[index++];
2595         beacon_param->mesh_formation_info = puc_mesh_conf_ie[index++];
2596         beacon_param->mesh_capability = puc_mesh_conf_ie[index];
2597         oam_warning_log3(0, OAM_SF_ANY,
2598             "{wal_parse_mesh_conf_ie::auth_protocol = %d, formation_info = %d, capability = %d!}",
2599             beacon_param->mesh_auth_protocol, beacon_param->mesh_formation_info, beacon_param->mesh_capability);
2600     } else {
2601         oam_warning_log0(0, OAM_SF_ANY, "{wal_parse_mesh_conf_ie::mesh vap can't find mesh conf ie!}");
2602         return HI_FAIL;
2603     }
2604 
2605     return HI_SUCCESS;
2606 }
2607 #endif
2608 
2609 /* ****************************************************************************
2610  函 数 名  : wal_check_support_basic_rate_6M
2611  功能描述  : 判断指数速率集和扩展速率集中是否包含6M速率作为基本速率
2612  输入参数  : [1]puc_supported_rates_ie
2613              [2]supported_rates_num
2614              [3]puc_extended_supported_rates_ie
2615              [4]extended_supported_rates_num
2616  输出参数  : 无
2617  返 回 值  : static hi_bool : HI_TRUE    支持
2618                               HI_FALSE   不支持
2619 **************************************************************************** */
wal_check_support_basic_rate_6m(const hi_u8 * puc_supported_rates_ie,hi_u8 supported_rates_num,const hi_u8 * puc_extended_supported_rates_ie,hi_u8 extended_supported_rates_num)2620 static hi_bool wal_check_support_basic_rate_6m(const hi_u8 *puc_supported_rates_ie, hi_u8 supported_rates_num,
2621     const hi_u8 *puc_extended_supported_rates_ie, hi_u8 extended_supported_rates_num)
2622 {
2623     hi_u8 loop;
2624     hi_bool support = HI_FALSE;
2625     for (loop = 0; loop < supported_rates_num; loop++) {
2626         if (puc_supported_rates_ie == HI_NULL) {
2627             break;
2628         }
2629         if (puc_supported_rates_ie[2 + loop] == 0x8c) { /* 2:偏移位 */
2630             support = HI_TRUE;
2631         }
2632     }
2633 
2634     for (loop = 0; loop < extended_supported_rates_num; loop++) {
2635         if (puc_extended_supported_rates_ie == HI_NULL) {
2636             break;
2637         }
2638         if (puc_extended_supported_rates_ie[2 + loop] == 0x8c) { /* 2:偏移位 */
2639             support = HI_TRUE;
2640         }
2641     }
2642 
2643     return support;
2644 }
2645 
2646 /* ****************************************************************************
2647  函 数 名  : wal_parse_protocol_mode
2648  功能描述  : 解析协议模式
2649  输入参数  : 无
2650  输出参数  : 无
2651  返 回 值  :
2652  调用函数  :
2653  被调函数  :
2654 
2655  修改历史      :
2656   1.日    期   : 2014年6月12日
2657     作    者   : HiSilicon
2658     修改内容   : 新生成函数
2659 
2660 **************************************************************************** */
wal_parse_protocol_mode(wlan_channel_band_enum_uint8 band,const oal_beacon_parameters * beacon_info,const hi_u8 * puc_ht_ie,const hi_u8 * puc_vht_ie,wlan_protocol_enum_uint8 * pen_protocol)2661 static hi_u32 wal_parse_protocol_mode(wlan_channel_band_enum_uint8 band, const oal_beacon_parameters *beacon_info,
2662     const hi_u8 *puc_ht_ie, const hi_u8 *puc_vht_ie, wlan_protocol_enum_uint8 *pen_protocol)
2663 {
2664     hi_u8   *puc_supported_rates_ie             = HI_NULL;
2665     hi_u8   *puc_extended_supported_rates_ie    = HI_NULL;
2666     hi_u8    supported_rates_num             = 0;
2667     hi_u8    extended_supported_rates_num    = 0;
2668     hi_u16   us_offset;
2669 
2670     if (puc_vht_ie != HI_NULL) {
2671         /* 设置AP 为11ac 模式 */
2672         *pen_protocol = WLAN_VHT_MODE;
2673         return HI_SUCCESS;
2674     }
2675     if (puc_ht_ie != HI_NULL) {
2676         /* 设置AP 为11n 模式 */
2677         *pen_protocol = WLAN_HT_MODE;
2678         return HI_SUCCESS;
2679     }
2680 
2681     if (WLAN_BAND_2G == band) {
2682         us_offset = MAC_TIME_STAMP_LEN + MAC_BEACON_INTERVAL_LEN + MAC_CAP_INFO_LEN;
2683         if (beacon_info->head_len > us_offset) {
2684             puc_supported_rates_ie = mac_find_ie(MAC_EID_RATES, beacon_info->head + 24 + us_offset,
2685                 beacon_info->head_len - us_offset); /* mac header长度24 */
2686             if (puc_supported_rates_ie != HI_NULL) {
2687                 supported_rates_num = puc_supported_rates_ie[1];
2688             }
2689         }
2690         puc_extended_supported_rates_ie = mac_find_ie(MAC_EID_XRATES, beacon_info->tail, beacon_info->tail_len);
2691         if (puc_extended_supported_rates_ie != HI_NULL) {
2692             extended_supported_rates_num = puc_extended_supported_rates_ie[1];
2693         }
2694 
2695         if (supported_rates_num + extended_supported_rates_num == 4) { /* 判断总IE长度是否为4,选择模式 */
2696             *pen_protocol = WLAN_LEGACY_11B_MODE;
2697             return HI_SUCCESS;
2698         }
2699         if (supported_rates_num + extended_supported_rates_num == 8) { /* 判断总IE长度是否为8,选择模式 */
2700             *pen_protocol = WLAN_LEGACY_11G_MODE;
2701             return HI_SUCCESS;
2702         }
2703         if (supported_rates_num + extended_supported_rates_num == 12) { /* 判断总IE长度是否为12,选择模式 */
2704             /* 根据基本速率区分为 11gmix1 还是 11gmix2 */
2705             /* 如果基本速率集支持 6M , 则判断为 11gmix2 */
2706             *pen_protocol = WLAN_MIXED_ONE_11G_MODE;
2707             if (wal_check_support_basic_rate_6m(puc_supported_rates_ie, supported_rates_num,
2708                 puc_extended_supported_rates_ie, extended_supported_rates_num) == HI_TRUE) {
2709                 *pen_protocol = WLAN_MIXED_TWO_11G_MODE;
2710             }
2711             return HI_SUCCESS;
2712         }
2713     }
2714 
2715     /* 其他情况,认为配置不合理 */
2716     *pen_protocol = WLAN_PROTOCOL_BUTT;
2717 
2718     return HI_FAIL;
2719 }
2720 
2721 /* ****************************************************************************
2722  函 数 名  : wal_parse_ht_vht_ie
2723  功能描述  : 解析内核传递过来的beacon信息中的ht_vht 信息元素
2724  输入参数  : oal_beacon_parameters *pst_beacon_info
2725              mac_beacon_param_stru *pst_beacon_param
2726  输出参数  : 无
2727  返 回 值  : hi_u32
2728  调用函数  :
2729  被调函数  :
2730 
2731  修改历史      :
2732   1.日    期   : 2014年4月4日
2733     作    者   : HiSilicon
2734     修改内容   : 新生成函数
2735 
2736 **************************************************************************** */
wal_parse_ht_vht_ie(const mac_vap_stru * mac_vap,const oal_beacon_parameters * beacon_info,mac_beacon_param_stru * beacon_param)2737 static hi_u32 wal_parse_ht_vht_ie(const mac_vap_stru *mac_vap, const oal_beacon_parameters *beacon_info,
2738     mac_beacon_param_stru *beacon_param)
2739 {
2740     hi_u8 *puc_ht_ie  = mac_find_ie(MAC_EID_HT_CAP, beacon_info->tail, beacon_info->tail_len);
2741     hi_u8 *puc_vht_ie = mac_find_ie(MAC_EID_VHT_CAP, beacon_info->tail, beacon_info->tail_len);
2742 
2743     /* 解析协议模式 */
2744     hi_u32 ret = wal_parse_protocol_mode(mac_vap->channel.band, beacon_info, puc_ht_ie,
2745         puc_vht_ie, &beacon_param->protocol);
2746     if (ret != HI_SUCCESS) {
2747         oam_error_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_parse_ht_vht_ie::return err code!}\r\n", ret);
2748         return ret;
2749     }
2750 
2751 #ifdef _PRE_WLAN_FEATURE_P2P
2752     /* 定制化实现P2P GO 2.4G下默认支持11ac 协议模式 */
2753     if (is_p2p_go(mac_vap) && (WLAN_BAND_2G == mac_vap->channel.band)) {
2754         beacon_param->protocol = ((HI_TRUE == mac_vap->cap_flag.ac2g) ? WLAN_VHT_MODE : WLAN_HT_MODE);
2755     }
2756 #endif /* _PRE_WLAN_FEATURE_P2P */
2757 
2758     /* 解析short gi能力 */
2759     if (puc_ht_ie == HI_NULL) {
2760         return HI_SUCCESS;
2761     }
2762 
2763     /* 使用ht cap ie中数据域的2个字节 */
2764     if (puc_ht_ie[1] < sizeof(mac_frame_ht_cap_stru)) {
2765         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_parse_ht_vht_ie::invalid htcap ie len %d}\n", puc_ht_ie[1]);
2766         return HI_SUCCESS;
2767     }
2768 
2769     mac_frame_ht_cap_stru *ht_cap = (mac_frame_ht_cap_stru *)(puc_ht_ie + MAC_IE_HDR_LEN);
2770 
2771     beacon_param->shortgi_20 = (hi_u8)ht_cap->short_gi_20mhz;
2772     beacon_param->shortgi_40 = 0;
2773 
2774     if ((mac_vap->channel.en_bandwidth > WLAN_BAND_WIDTH_20M) &&
2775         (mac_vap->channel.en_bandwidth != WLAN_BAND_WIDTH_BUTT)) {
2776         beacon_param->shortgi_40 = (hi_u8)ht_cap->short_gi_40mhz;
2777     }
2778 
2779     beacon_param->smps_mode = (hi_u8)ht_cap->sm_power_save;
2780 
2781     if (puc_vht_ie == HI_NULL) {
2782         return HI_SUCCESS;
2783     }
2784 
2785     /* 使用vht cap ie中数据域的4个字节 */
2786     if (puc_vht_ie[1] < sizeof(mac_vht_cap_info_stru)) {
2787         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_parse_ht_vht_ie::invalid ht cap ie len[%d]!}\r\n",
2788             puc_vht_ie[1]);
2789         return HI_SUCCESS;
2790     }
2791 
2792     mac_vht_cap_info_stru *vht_cap = (mac_vht_cap_info_stru *)(puc_vht_ie + MAC_IE_HDR_LEN);
2793 
2794     beacon_param->shortgi_80 = 0;
2795 
2796     if ((mac_vap->channel.en_bandwidth > WLAN_BAND_WIDTH_40MINUS) &&
2797         (mac_vap->channel.en_bandwidth != WLAN_BAND_WIDTH_BUTT)) {
2798         beacon_param->shortgi_80 = vht_cap->short_gi_80mhz;
2799     }
2800 
2801     return HI_SUCCESS;
2802 }
2803 
2804 #ifdef _PRE_WLAN_FEATURE_QUICK_START
2805 hi_u32 g_l_scan_enable = HI_FALSE;
hisi_quick_set_scan_enable(hi_s32 l_enable_flag)2806 hi_u32 hisi_quick_set_scan_enable(hi_s32 l_enable_flag)
2807 {
2808     return g_l_scan_enable = l_enable_flag;
2809 }
hisi_quick_get_scan_enable(hi_void)2810 hi_u32 hisi_quick_get_scan_enable(hi_void)
2811 {
2812     return g_l_scan_enable;
2813 }
2814 #endif
2815 
2816 /* ****************************************************************************
2817  函 数 名  : wal_cfg80211_scan
2818  功能描述  : 内核调用启动扫描的接口函数
2819  输入参数  : 无
2820  输出参数  : 无
2821  返 回 值  :
2822  调用函数  :
2823  被调函数  :
2824 
2825  修改历史      :
2826   1.日    期   : 2013年8月27日
2827     作    者   : HiSilicon
2828     修改内容   : 新生成函数
2829 
2830 **************************************************************************** */
2831 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION) || defined(_PRE_HDF_LINUX)
wal_cfg80211_scan(oal_wiphy_stru * wiphy,oal_cfg80211_scan_request_stru * request)2832 hi_u32 wal_cfg80211_scan(oal_wiphy_stru *wiphy, oal_cfg80211_scan_request_stru *request)
2833 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
2834 hi_s32 wal_cfg80211_scan(oal_wiphy_stru *wiphy, oal_cfg80211_scan_request_stru *request)
2835 #endif
2836 {
2837     hmac_device_stru           *hmac_dev = HI_NULL;
2838     mac_vap_stru               *mac_vap = HI_NULL;
2839     hmac_scan_stru             *scan_mgmt = HI_NULL;
2840     oal_net_device_stru        *netdev = HI_NULL;
2841 
2842     if ((wiphy == HI_NULL) || (request == HI_NULL)) {
2843         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_scan::parameter is wrong, return fail!}");
2844         goto fail;
2845     }
2846 
2847     oam_info_log2(0, OAM_SF_SCAN, "{wal_cfg80211_scan::request to scan, channel:%d, ssid:%d}", request->n_channels,
2848         request->n_ssids);
2849 
2850     netdev = (request->wdev == HI_NULL ? HI_NULL : request->wdev->netdev);
2851     if (netdev == HI_NULL) {
2852         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_scan::acquire netdev fail, return fail!}");
2853         goto fail;
2854     }
2855 
2856     /* 通过net_device 找到对应的mac_vap_stru 结构 */
2857     mac_vap = oal_net_dev_priv(netdev);
2858     if (mac_vap == NULL) {
2859         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_scan::cann't acquire mac_vap from netdev, return fail!}");
2860         goto fail;
2861     }
2862 
2863 #ifdef _PRE_WLAN_FEATURE_WAPI
2864     if (is_p2p_scan_req(request) && (HI_TRUE == hmac_user_is_wapi_connected())) {
2865         oam_warning_log0(0, OAM_SF_SCAN, "{wal_cfg80211_scan::cann't execute p2p scan under wapi mode, return!}");
2866         goto fail;
2867     }
2868 #endif /* #ifdef _PRE_WLAN_FEATURE_WAPI */
2869 
2870     hmac_dev = hmac_get_device_stru();
2871     scan_mgmt = &(hmac_dev->scan_mgmt);
2872 
2873     /* 如果扫描未完成,则直接返回 */
2874     if (scan_mgmt->complete == HI_FALSE) {
2875         oam_warning_log0(0, OAM_SF_SCAN,
2876             "{wal_cfg80211_scan::the last scan is still running, refuse this scan request.}");
2877         goto fail;
2878     }
2879 
2880 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
2881     /* 如果当前调度扫描在运行,先暂停调度扫描 */
2882     if (scan_mgmt->sched_scan_req != HI_NULL) {
2883         wal_cfg80211_sched_scan_stop(wiphy, netdev);
2884     }
2885 #endif
2886 
2887     /* 保存当前下发的扫描请求到本地 */
2888     scan_mgmt->request = request;
2889 
2890     /* 进入扫描 */
2891     if (HI_SUCCESS != wal_start_scan_req(netdev, scan_mgmt)) {
2892         scan_mgmt->request = HI_NULL;
2893         goto fail;
2894     }
2895 
2896     return HI_SUCCESS;
2897 
2898 fail:
2899 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
2900     return HI_FAIL;
2901 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
2902     return -HI_FAIL;
2903 #endif
2904 }
2905 
2906 /* ****************************************************************************
2907  函 数 名  : wal_set_wep_key
2908  功能描述  : 配置wep加密信息
2909  输入参数  : 无
2910  输出参数  : 无
2911  返 回 值  :
2912  调用函数  :
2913  被调函数  :
2914 
2915  修改历史      :
2916   1.日    期   : 2013年11月22日
2917     作    者   : HiSilicon
2918     修改内容   : 新生成函数
2919   1.日    期   : 2014年01月24日
2920     作    者   : HiSilicon
2921     修改内容   : 修改函数, 从内核拷贝wep 加密信息到驱动
2922 
2923 **************************************************************************** */
wal_set_wep_key(mac_cfg80211_connect_param_stru * connect_param,const oal_cfg80211_connect_params_stru * sme)2924 static hi_u32 wal_set_wep_key(mac_cfg80211_connect_param_stru *connect_param,
2925     const oal_cfg80211_connect_params_stru *sme)
2926 {
2927     connect_param->puc_wep_key         = sme->key;
2928     connect_param->wep_key_len         = sme->key_len;
2929     connect_param->wep_key_index       = sme->key_idx;
2930     connect_param->crypto.cipher_group = (hi_u8)sme->crypto.cipher_group;
2931 
2932     return HI_SUCCESS;
2933 }
2934 
2935 /* ****************************************************************************
2936  功能描述  : 处理使能PMF STAUT下发n_akm_suites==0的RSN特殊情况
2937  输入参数  : mac_cfg80211_connect_param_stru   *pst_connect_param
2938              oal_cfg80211_connect_params_stru    *pst_sme
2939  返 回 值  : static hi_u32
2940 **************************************************************************** */
wal_set_crypto_pmf(mac_cfg80211_connect_param_stru * connect,const oal_cfg80211_connect_params_stru * sme,const hi_u8 * puc_ie)2941 static hi_u32 wal_set_crypto_pmf(mac_cfg80211_connect_param_stru *connect, const oal_cfg80211_connect_params_stru *sme,
2942     const hi_u8 *puc_ie)
2943 {
2944     hi_u8 loop2, loop3;
2945 
2946     /* 设置WPA/WPA2 加密信息 */
2947     connect->crypto.control_port = (hi_u8)sme->crypto.control_port;
2948     connect->crypto.wpa_versions = (hi_u8)sme->crypto.wpa_versions;
2949 
2950     /* puc_ie[1] 为IE字段的长度 */
2951     if (MAC_RSN_VERSION_LEN + MAC_OUI_LEN + MAC_OUITYPE_WPA + MAC_RSN_CIPHER_COUNT_LEN < puc_ie[1]) {
2952         return HI_FAIL;
2953     }
2954 
2955     /* 获取group cipher type */
2956     connect->crypto.cipher_group = puc_ie[MAC_IE_HDR_LEN + MAC_RSN_VERSION_LEN + MAC_OUI_LEN];
2957 
2958     /* 获取pairwise cipher cout */
2959     hi_u32 offset = MAC_IE_HDR_LEN + MAC_RSN_VERSION_LEN + MAC_OUI_LEN + MAC_OUITYPE_WPA;
2960     connect->crypto.n_ciphers_pairwise = puc_ie[offset];
2961     connect->crypto.n_ciphers_pairwise += (hi_u8)(puc_ie[offset + 1] << 8); /* 左移8位 */
2962     if (connect->crypto.n_ciphers_pairwise > OAL_NL80211_MAX_NR_CIPHER_SUITES) {
2963         oam_warning_log1(0, 0, "{wal_set_crypto_pmf:invalid ciphers len:%d!}", connect->crypto.n_ciphers_pairwise);
2964         return HI_FAIL;
2965     }
2966     /* 获取pairwise cipher type */
2967     offset += MAC_RSN_CIPHER_COUNT_LEN;
2968     if (connect->crypto.n_ciphers_pairwise) {
2969         for (loop2 = 0; loop2 < connect->crypto.n_ciphers_pairwise; loop2++) {
2970             connect->crypto.ciphers_pairwise[loop2] = (hi_u8)puc_ie[offset + MAC_OUI_LEN];
2971             offset += (MAC_OUITYPE_WPA + MAC_OUI_LEN);
2972             if (offset - MAC_IE_HDR_LEN < puc_ie[1]) {
2973                 return HI_FAIL;
2974             }
2975         }
2976     }
2977 
2978     if (offset + MAC_RSN_CIPHER_COUNT_LEN - MAC_IE_HDR_LEN < puc_ie[1]) {
2979         return HI_FAIL;
2980     }
2981 
2982     /* 获取AKM cout */
2983     connect->crypto.n_akm_suites = puc_ie[offset];
2984     connect->crypto.n_akm_suites += (hi_u8)(puc_ie[offset + 1] << 8); /* 左移8位 */
2985     if (connect->crypto.n_akm_suites > OAL_NL80211_MAX_NR_AKM_SUITES) {
2986         oam_warning_log1(0, 0, "{wal_set_crypto_pmf:invalid akm len:%d!}", connect->crypto.n_akm_suites);
2987         return HI_FAIL;
2988     }
2989     /* 获取AKM type */
2990     offset += MAC_RSN_CIPHER_COUNT_LEN;
2991     if (connect->crypto.n_akm_suites) {
2992         for (loop3 = 0; loop3 < connect->crypto.n_akm_suites; loop3++) {
2993             connect->crypto.akm_suites[loop3] = (hi_u8)puc_ie[offset + MAC_OUI_LEN];
2994             offset += (MAC_OUITYPE_WPA + MAC_OUI_LEN);
2995             if (offset - MAC_IE_HDR_LEN < puc_ie[1]) {
2996                 return HI_FAIL;
2997             }
2998         }
2999     }
3000 
3001     return HI_SUCCESS;
3002 }
3003 
3004 
3005 /* ****************************************************************************
3006  功能描述  : 设置STA connect 加密信息
3007  输入参数  : mac_cfg80211_connect_param_stru   *pst_connect_param
3008              oal_cfg80211_connect_params_stru    *pst_sme
3009  返 回 值  : static hi_u32
3010 **************************************************************************** */
wal_set_crypto_info(mac_cfg80211_connect_param_stru * connect_param,const oal_cfg80211_connect_params_stru * sme)3011 hi_u32 wal_set_crypto_info(mac_cfg80211_connect_param_stru *connect_param, const oal_cfg80211_connect_params_stru *sme)
3012 {
3013     hi_u8 *puc_ie = mac_find_ie(MAC_EID_RSN, (hi_u8 *)sme->ie, sme->ie_len);
3014     hi_u8 loop, loop1;
3015 
3016     if ((sme->key_len != 0) && (sme->crypto.n_akm_suites == 0)) {
3017         /* 设置wep加密信息 */
3018         return wal_set_wep_key(connect_param, sme);
3019     } else if (sme->crypto.n_akm_suites != 0) {
3020         if ((sme->crypto.n_akm_suites > OAL_NL80211_MAX_NR_AKM_SUITES) ||
3021             (sme->crypto.n_ciphers_pairwise > OAL_NL80211_MAX_NR_CIPHER_SUITES)) {
3022             oam_warning_log0(0, OAM_SF_CFG, "{wal_set_crypto_info:invalid suites len!}");
3023             return HI_FAIL;
3024         }
3025         /* 设置WPA/WPA2 加密信息 */
3026         connect_param->crypto.wpa_versions       = (hi_u8)sme->crypto.wpa_versions;
3027         connect_param->crypto.cipher_group       = (hi_u8)sme->crypto.cipher_group;
3028         connect_param->crypto.n_ciphers_pairwise = (hi_u8)sme->crypto.n_ciphers_pairwise;
3029         connect_param->crypto.n_akm_suites       = (hi_u8)sme->crypto.n_akm_suites;
3030         connect_param->crypto.control_port       = (hi_u8)sme->crypto.control_port;
3031 
3032         for (loop = 0; loop < connect_param->crypto.n_ciphers_pairwise; loop++) {
3033             connect_param->crypto.ciphers_pairwise[loop] = (hi_u8)sme->crypto.ciphers_pairwise[loop];
3034         }
3035 
3036         for (loop1 = 0; loop1 < connect_param->crypto.n_akm_suites; loop1++) {
3037             connect_param->crypto.akm_suites[loop1] = (hi_u8)sme->crypto.akm_suites[loop1];
3038         }
3039 
3040         return HI_SUCCESS;
3041     } else if (puc_ie != HI_NULL) {
3042         /* 处理使能PMF STAUT下发n_akm_suites==0的RSN特殊情况 */
3043         return wal_set_crypto_pmf(connect_param, sme, puc_ie);
3044     } else if (mac_find_vendor_ie(MAC_WLAN_OUI_MICROSOFT, MAC_WLAN_OUI_TYPE_MICROSOFT_WPS, (hi_u8 *)sme->ie,
3045         (hi_s32)(sme->ie_len))) {
3046         oam_warning_log0(0, OAM_SF_CFG, "{wal_set_crypto_info:connect use wps method!}");
3047 
3048         return HI_SUCCESS;
3049     }
3050 
3051     return HI_FAIL;
3052 }
3053 
3054 #ifdef _PRE_WLAN_FEATURE_P2P
3055 /* ****************************************************************************
3056  功能描述  : 判断是否为P2P DEVICE .如果是P2P device,则不允许关联。
3057  输入参数  : oal_net_device_stru *pst_net_device
3058  返 回 值  : hi_u8 HI_TRUE:P2P DEVICE 设备,
3059                                  HI_FALSE:非P2P DEVICE 设备
3060  修改历史      :
3061   1.日    期   : 2019年5月20日
3062     作    者   : HiSilicon
3063     修改内容   : 通过iftype识别p2p dev
3064 **************************************************************************** */
wal_is_p2p_device(const oal_net_device_stru * netdev)3065 static hi_u8 wal_is_p2p_device(const oal_net_device_stru *netdev)
3066 {
3067     oal_wireless_dev *wdev = HI_NULL;
3068 
3069     /* 获取mac device */
3070     wdev = GET_NET_DEV_CFG80211_WIRELESS(netdev);
3071     return (wdev->iftype == NL80211_IFTYPE_P2P_DEVICE);
3072 }
3073 #endif
3074 
wal_cfg80211_start_connect_or_req(oal_net_device_stru * netdev,const mac_cfg80211_connect_param_stru * mac_cfg80211_connect_param)3075 hi_u32 wal_cfg80211_start_connect_or_req(oal_net_device_stru *netdev,
3076     const mac_cfg80211_connect_param_stru *mac_cfg80211_connect_param)
3077 {
3078     hi_u32 ret;
3079 
3080 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3081     ret = wal_cfg80211_start_connect(netdev, mac_cfg80211_connect_param);
3082 #else
3083     ret = wal_cfg80211_start_req(netdev, mac_cfg80211_connect_param, sizeof(mac_cfg80211_connect_param_stru),
3084         WLAN_CFGID_CFG80211_START_CONNECT, HI_TRUE);
3085 #endif
3086     if (ret != HI_SUCCESS) {
3087         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_start_connect_or_req::wal_cfg80211_start_connect fail %u}", ret);
3088     }
3089 
3090     return ret;
3091 }
3092 
3093 /* ****************************************************************************
3094  函 数 名  : wal_cfg80211_connect
3095  功能描述  : 解析内核下发的关联命令,sta启动关联
3096  输入参数  : 无
3097  输出参数  : 无
3098  返 回 值  :
3099  调用函数  :
3100  被调函数  :
3101 
3102  修改历史      :
3103   1.日    期   : 2013年8月27日
3104     作    者   : HiSilicon
3105     修改内容   : 新生成函数
3106   2.日    期   : 2013年10月24日
3107     作    者   : HiSilicon
3108     修改内容   : 增加加密认证相关的处理
3109 
3110 **************************************************************************** */
3111 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_cfg80211_connect(oal_wiphy_stru * wiphy,oal_net_device_stru * net_device,oal_cfg80211_connect_params_stru * sme)3112 hi_u32 wal_cfg80211_connect(oal_wiphy_stru *wiphy, oal_net_device_stru *net_device,
3113     oal_cfg80211_connect_params_stru *sme)
3114 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3115 hi_s32 wal_cfg80211_connect(oal_wiphy_stru *wiphy, oal_net_device_stru *net_device,
3116     oal_cfg80211_connect_params_stru *sme)
3117 #endif
3118 {
3119     mac_cfg80211_connect_param_stru mac_cfg80211_connect_param = { 0 };
3120 
3121     if ((wiphy == HI_NULL) || (net_device == HI_NULL) || (sme == HI_NULL)) {
3122         oam_error_log3(0, OAM_SF_ANY, "{wal_cfg80211_connect::connect failed,wiphy=%p,netdev=%p,sme=%p}",
3123             (uintptr_t)wiphy, (uintptr_t)net_device, (uintptr_t)sme);
3124         goto fail;
3125     }
3126 
3127 #ifdef _PRE_WLAN_FEATURE_P2P
3128     if (wal_is_p2p_device(net_device)) {
3129         oam_warning_log0(0, OAM_SF_ANY, "wal_cfg80211_connect:connect stop, p2p device should not connect.");
3130         goto fail;
3131     }
3132 #endif
3133 
3134     /* iw接口下发的关联请求,有可能无信道信息,此时会访问空指针,并且此处获取信道号,在入网过程中,并没有用到 */
3135     /* 解析内核下发的 ssid */
3136     mac_cfg80211_connect_param.puc_ssid = (hi_u8 *)sme->ssid;
3137     mac_cfg80211_connect_param.ssid_len = (hi_u8)sme->ssid_len;
3138 
3139     /* 解析内核下发的 bssid */
3140     mac_cfg80211_connect_param.puc_bssid = (hi_u8 *)sme->bssid;
3141 
3142     /* 解析内核下发的安全相关参数 */
3143     /* 设置认证类型 */
3144     mac_cfg80211_connect_param.auth_type = sme->auth_type;
3145 
3146     /* 设置加密能力 */
3147     mac_cfg80211_connect_param.privacy = sme->privacy;
3148 
3149     /* 获取内核下发的pmf是使能的结果 */
3150     mac_cfg80211_connect_param.mfp = sme->mfp;
3151 
3152     oam_warning_log4(0, OAM_SF_ANY, "{wal_cfg80211_connect::start new conn,ssid_len=%d,auth_type=%d,privacy=%d,mfp=%d}",
3153         sme->ssid_len, sme->auth_type, sme->privacy, sme->mfp);
3154 
3155     /* 设置加密参数 */
3156 #ifdef _PRE_WLAN_FEATURE_WAPI
3157     if (sme->crypto.wpa_versions == WITP_WAPI_VERSION) {
3158         oam_warning_log0(0, OAM_SF_ANY, "wal_cfg80211_connect::crypt ver is wapi!");
3159         mac_cfg80211_connect_param.wapi = HI_TRUE;
3160     } else {
3161         mac_cfg80211_connect_param.wapi = HI_FALSE;
3162     }
3163 #endif
3164 
3165     if (sme->privacy) {
3166         hi_u32 ret = wal_set_crypto_info(&mac_cfg80211_connect_param, sme);
3167         if (ret != HI_SUCCESS) {
3168             oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_connect::connect failed, wal_set_wep_key fail:%d!}\r\n", ret);
3169             goto fail;
3170         }
3171     }
3172 
3173     /* 设置关联P2P/WPS ie */
3174     mac_cfg80211_connect_param.puc_ie = (hi_u8 *)sme->ie;
3175     mac_cfg80211_connect_param.ie_len = (hi_u32)(sme->ie_len);
3176 
3177 #if (_PRE_MULTI_CORE_MODE_OFFLOAD_DMAC == _PRE_MULTI_CORE_MODE) && \
3178     ((_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) || (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION))
3179     wlan_pm_set_timeout(WLAN_SLEEP_LONG_CHECK_CNT);
3180 #endif
3181 
3182     if (wal_cfg80211_start_connect_or_req(net_device, &mac_cfg80211_connect_param) != HI_SUCCESS) {
3183         goto fail;
3184     }
3185     return HI_SUCCESS;
3186 
3187 fail:
3188 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
3189     return HI_FAIL;
3190 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3191     return -HI_FAIL;
3192 #endif
3193 }
3194 
3195 /* ****************************************************************************
3196  函 数 名  : wal_cfg80211_disconnect
3197  功能描述  :
3198  输入参数  : 无
3199  输出参数  : 无
3200  返 回 值  :
3201  调用函数  :
3202  被调函数  :
3203 
3204  修改历史      :
3205   1.日    期   : 2013年8月27日
3206     作    者   : HiSilicon
3207     修改内容   : 新生成函数
3208 
3209 **************************************************************************** */
3210 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_cfg80211_disconnect(oal_wiphy_stru * wiphy,oal_net_device_stru * net_device,hi_u16 us_reason_code)3211 hi_u32 wal_cfg80211_disconnect(oal_wiphy_stru *wiphy, oal_net_device_stru *net_device, hi_u16 us_reason_code)
3212 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3213 hi_s32 wal_cfg80211_disconnect(oal_wiphy_stru *wiphy, oal_net_device_stru *net_device, hi_u16 us_reason_code)
3214 #endif
3215 {
3216     mac_cfg_kick_user_param_stru    mac_cfg_kick_user_param;
3217     hi_u32                          ret;
3218     mac_user_stru                   *mac_user = HI_NULL;
3219     mac_vap_stru                    *mac_vap = HI_NULL;
3220     hi_unref_param(wiphy);
3221 
3222     if (net_device == HI_NULL) {
3223         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_disconnect::input netdev pointer is null!}\r\n");
3224         goto fail;
3225     }
3226 
3227     /* 解析内核下发的connect参数 */
3228     if (memset_s(&mac_cfg_kick_user_param, sizeof(mac_cfg_kick_user_param_stru), 0,
3229         sizeof(mac_cfg_kick_user_param_stru)) != EOK) {
3230         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_disconnect::mem safe function err!}");
3231         goto fail;
3232     }
3233 
3234     /* 解析内核下发的去关联原因  */
3235     mac_cfg_kick_user_param.us_reason_code = us_reason_code;
3236 
3237     /* 填写和sta关联的ap mac 地址 */
3238     mac_vap = oal_net_dev_priv(net_device);
3239     if (mac_vap == HI_NULL) {
3240         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_disconnect::get mac vap ptr is null!}\r\n");
3241         goto fail;
3242     }
3243 
3244     mac_user = mac_user_get_user_stru(mac_vap->assoc_vap_id);
3245     if (mac_user == HI_NULL) {
3246         oam_warning_log1(0, OAM_SF_ANY,
3247             "{wal_cfg80211_disconnect::mac_user_get_user_stru pst_mac_user is null, user idx[%d]!}\r\n",
3248             mac_vap->assoc_vap_id);
3249         goto fail;
3250     }
3251 
3252     if (memcpy_s(mac_cfg_kick_user_param.auc_mac_addr, WLAN_MAC_ADDR_LEN,
3253                  mac_user->user_mac_addr, WLAN_MAC_ADDR_LEN) != EOK) {
3254         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_disconnect::mem safe function err!}");
3255         goto fail;
3256     }
3257 
3258 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3259     ret = wal_cfg80211_start_disconnect(net_device, &mac_cfg_kick_user_param);
3260 #else
3261     ret = wal_cfg80211_start_req(net_device, &mac_cfg_kick_user_param, sizeof(mac_cfg_kick_user_param_stru),
3262         WLAN_CFGID_KICK_USER, HI_TRUE);
3263 #endif
3264     if (ret != HI_SUCCESS) {
3265         goto fail;
3266     }
3267 
3268     return HI_SUCCESS;
3269 
3270 fail:
3271 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
3272     return HI_FAIL;
3273 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3274     return -HI_FAIL;
3275 #endif
3276 }
3277 
3278 /* ****************************************************************************
3279  函 数 名  : wal_cfg80211_add_key
3280  功能描述  : 配置ptk,gtk等密钥到物理层
3281  输入参数  : [1]wiphy
3282              [2]netdev
3283              [3]p_cfg80211_add_key_info
3284              [4]mac_addr
3285              [5]params
3286  输出参数  : hi_u32
3287  返 回 值  : 0:成功,其他:失败
3288 **************************************************************************** */
wal_cfg80211_add_key(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,hi_u8 key_index,bool pairwise,const hi_u8 * puc_mac_addr,oal_key_params_stru * params)3289 hi_u32 wal_cfg80211_add_key(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, hi_u8 key_index, bool pairwise,
3290     const hi_u8 *puc_mac_addr, oal_key_params_stru *params)
3291 {
3292     mac_addkey_param_stru payload_params;
3293     hi_u32 ret;
3294 
3295     hi_unref_param(wiphy);
3296     /* 1.1 入参检查 */
3297     if ((netdev == HI_NULL) || (params == HI_NULL)) {
3298         oam_error_log2(0, OAM_SF_ANY, "{wal_cfg80211_add_key::Param Check ERROR,pst_netdev, pst_params %p, %p, %p!}",
3299             (uintptr_t)netdev, (uintptr_t)params);
3300         goto fail;
3301     }
3302 
3303     /* 1.2 key长度检查,防止拷贝越界 */
3304     if ((params->key_len > OAL_WPA_KEY_LEN) || (params->seq_len > OAL_WPA_SEQ_LEN)) {
3305         oam_error_log2(0, OAM_SF_ANY, "{wal_cfg80211_add_key::Param Check ERROR! key_len[%x]  seq_len[%x]!}",
3306             (hi_s32)params->key_len, (hi_s32)params->seq_len);
3307         goto fail;
3308     }
3309 
3310     /* 2.1 消息参数准备 */
3311     if (memset_s(&payload_params, sizeof(payload_params), 0, sizeof(payload_params)) != EOK) {
3312         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_key::mem safe function err!}");
3313         goto fail;
3314     }
3315     payload_params.key_index = key_index;
3316 
3317     if (puc_mac_addr != HI_NULL) {
3318         /* 不能使用内核下发的mac指针,可能被释放,需要拷贝到本地再使用 */
3319         if (memcpy_s(payload_params.auc_mac_addr, WLAN_MAC_ADDR_LEN, puc_mac_addr, WLAN_MAC_ADDR_LEN) != EOK) {
3320             oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_key::mem safe function err!}");
3321             goto fail;
3322         }
3323     }
3324     payload_params.pairwise = pairwise;
3325 
3326     /* 2.2 获取相关密钥值 */
3327     payload_params.key.key_len = params->key_len;
3328     payload_params.key.seq_len = params->seq_len;
3329     payload_params.key.cipher  = params->cipher;
3330     if (memcpy_s(payload_params.key.auc_key, OAL_WPA_KEY_LEN, params->key, (hi_u32)params->key_len) != EOK) {
3331         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_key::mem safe function err!}");
3332         goto fail;
3333     }
3334 
3335     if (params->seq != HI_NULL && params->seq_len != 0) {
3336         if (memcpy_s(payload_params.key.auc_seq, OAL_WPA_SEQ_LEN, params->seq, (hi_u32)params->seq_len) != EOK) {
3337             oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_add_key::mem safe function err!}");
3338             goto fail;
3339         }
3340     }
3341     oam_info_log3(0, OAM_SF_ANY, "{wal_cfg80211_add_key::key_len:%d, seq_len:%d, cipher:0x%08x!}", params->key_len,
3342         params->seq_len, params->cipher);
3343 
3344     /* 抛事件给驱动 */
3345     ret = wal_cfg80211_start_req(netdev, &payload_params, sizeof(mac_addkey_param_stru), WLAN_CFGID_ADD_KEY, HI_TRUE);
3346     if (ret != HI_SUCCESS) {
3347         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_add_key::return err code [%u]!}", ret);
3348         goto fail;
3349     }
3350     return HI_SUCCESS;
3351 
3352 fail:
3353     return HI_FAIL;
3354 }
3355 
3356 /* ****************************************************************************
3357  函 数 名  : wal_cfg80211_remove_key
3358  功能描述  : 把ptk,gtk等密钥从物理层删除
3359  输入参数  : [1]wiphy
3360              [2]netdev
3361              [3]key_index
3362              [4]pairwise
3363              [5]puc_mac_addr
3364  输出参数  : hi_u32
3365  返 回 值  : 0:成功,其他:失败
3366 **************************************************************************** */
3367 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION) || defined(_PRE_HDF_LINUX)
wal_cfg80211_remove_key(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,hi_u8 key_index,hi_bool pairwise,const hi_u8 * mac_addr)3368 hi_u32 wal_cfg80211_remove_key(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, hi_u8 key_index, hi_bool pairwise,
3369     const hi_u8 *mac_addr)
3370 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3371 hi_s32 wal_cfg80211_remove_key(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, hi_u8 key_index, bool pairwise,
3372     const hi_u8 *mac_addr)
3373 #endif
3374 {
3375     mac_removekey_param_stru payload_params = { 0 };
3376     hi_u32 ret;
3377 
3378     hi_unref_param(wiphy);
3379     /* 1.1 入参检查 */
3380     if (oal_unlikely(netdev == HI_NULL)) {
3381         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_remove_key::pst_netdev is null!}");
3382         goto fail;
3383     }
3384 
3385     /* 2.1 消息参数准备 */
3386     payload_params.key_index = key_index;
3387 
3388     if (mac_addr != HI_NULL) {
3389         /* 不能使用内核下发的mac指针,可能被释放,需要拷贝到本地再使用 */
3390         if (memcpy_s(payload_params.auc_mac_addr, OAL_MAC_ADDR_LEN, mac_addr, WLAN_MAC_ADDR_LEN) != EOK) {
3391             oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_remove_key::mem safe function err!}");
3392             goto fail;
3393         }
3394     }
3395     payload_params.pairwise = pairwise;
3396 
3397     oam_info_log2(0, OAM_SF_ANY, "{wal_cfg80211_remove_key::index:%d, pairwise:%d!}", key_index,
3398         payload_params.pairwise);
3399 
3400     /* 抛事件给驱动 */
3401     ret = wal_cfg80211_start_req(netdev, &payload_params, sizeof(mac_removekey_param_stru), WLAN_CFGID_REMOVE_KEY,
3402         HI_TRUE);
3403     if (ret != HI_SUCCESS) {
3404         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_remove_key::return err code [%u]!}", ret);
3405         goto fail;
3406     }
3407     return HI_SUCCESS;
3408 
3409 fail:
3410 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION) || defined(_PRE_HDF_LINUX)
3411     return HI_FAIL;
3412 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3413     return -HI_FAIL;
3414 #endif
3415 }
3416 
3417 /* ****************************************************************************
3418  函 数 名  : wal_cfg80211_set_default_key
3419  功能描述  : 使配置的密钥生效
3420  输入参数  : [1]wiphy
3421              [2]netdev
3422              [3]key_index
3423              [4]unicast
3424              [5]multicast
3425  返 回 值  : 0:成功,其他:失败
3426  修改内容  : 合并设置数据帧默认密钥和设置管理帧默认密钥函数
3427 **************************************************************************** */
3428 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_cfg80211_set_default_key(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,hi_u8 key_index,hi_bool unicast,hi_bool multicast)3429 hi_u32 wal_cfg80211_set_default_key(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, hi_u8 key_index,
3430     hi_bool unicast, hi_bool multicast)
3431 #else
3432 hi_s32 wal_cfg80211_set_default_key(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, hi_u8 key_index, bool unicast,
3433     bool multicast)
3434 #endif
3435 {
3436     mac_setdefaultkey_param_stru payload_params = { 0 };
3437     hi_u32 ret;
3438 
3439     hi_unref_param(wiphy);
3440     /* 1.1 入参检查 */
3441     if (oal_unlikely(netdev == HI_NULL)) {
3442         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_set_default_key::pst_netdev ptr is null!}\r\n");
3443         goto fail;
3444     }
3445 
3446     /* 2.1 消息参数准备 */
3447     payload_params.key_index = key_index;
3448     payload_params.unicast = unicast;
3449     payload_params.multicast = multicast;
3450 
3451     oam_info_log3(0, OAM_SF_ANY, "{wal_cfg80211_set_default_key::key_index:%d, unicast:%d, multicast:%d!}\r\n",
3452         key_index, payload_params.unicast, payload_params.multicast);
3453 
3454     /* 抛事件给驱动 */
3455     ret = wal_cfg80211_start_req(netdev, &payload_params, sizeof(mac_setdefaultkey_param_stru), WLAN_CFGID_DEFAULT_KEY,
3456         HI_FALSE);
3457     if (ret != HI_SUCCESS) {
3458         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_set_default_key::return err code [%u]!}", ret);
3459         goto fail;
3460     }
3461 
3462     return HI_SUCCESS;
3463 
3464 fail:
3465 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
3466     return HI_FAIL;
3467 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3468     return -HI_FAIL;
3469 #endif
3470 }
3471 
3472 /* ****************************************************************************
3473  函 数 名  : wal_cfg80211_set_ssid
3474  功能描述  : 启动ap
3475  输入参数  : oal_net_device_stru   *pst_netdev
3476  输出参数  : 无
3477  返 回 值  : static hi_s32
3478  调用函数  :
3479  被调函数  :
3480 
3481  修改历史      :
3482   1.日    期   : 2014年12月31日
3483     作    者   : HiSilicon
3484     修改内容   : 新生成函数
3485 
3486 **************************************************************************** */
wal_cfg80211_set_ssid(oal_net_device_stru * netdev,const hi_u8 * puc_ssid_ie,hi_u8 ssid_len)3487 static hi_u32 wal_cfg80211_set_ssid(oal_net_device_stru *netdev, const hi_u8 *puc_ssid_ie, hi_u8 ssid_len)
3488 {
3489     mac_cfg_ssid_param_stru      ssid_param = {0};
3490     hi_u32                       ret;
3491 
3492     /* 2.1 消息参数准备 */
3493     ssid_param.ssid_len = ssid_len;
3494     if (memcpy_s(ssid_param.ac_ssid, WLAN_SSID_MAX_LEN, (hi_s8 *)puc_ssid_ie, ssid_len) != EOK) {
3495         oam_error_log0(0, 0, "{wal_cfg80211_set_ssid::mem safe function err!}");
3496         return HI_FAIL;
3497     }
3498 
3499     /* 抛事件给驱动 */
3500     ret = wal_cfg80211_start_req(netdev, &ssid_param, sizeof(mac_cfg_ssid_param_stru), WLAN_CFGID_SSID, HI_FALSE);
3501     if (ret != HI_SUCCESS) {
3502         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_set_ssid::return err code [%u]!}", ret);
3503         return ret;
3504     }
3505 
3506     return HI_SUCCESS;
3507 }
3508 
3509 #ifdef _PRE_WLAN_FEATURE_MESH
3510 /* ****************************************************************************
3511  功能描述  :设置meshid
3512  输入参数  : oal_net_device_stru   *pst_netdev
3513                             hi_u8 *puc_ssid_ie
3514                             hi_u8 uc_ssid_len
3515  返 回 值  : static hi_s32
3516  修改历史      :
3517   1.日    期   : 2019年3月19日
3518     作    者   : HiSilicon
3519     修改内容   : 新生成函数
3520 
3521 **************************************************************************** */
wal_cfg80211_set_meshid(oal_net_device_stru * netdev,const hi_u8 * puc_meshid_ie,hi_u8 meshid_len)3522 static hi_u32 wal_cfg80211_set_meshid(oal_net_device_stru *netdev, const hi_u8 *puc_meshid_ie, hi_u8 meshid_len)
3523 {
3524     mac_cfg_ssid_param_stru      ssid_param = {0};
3525     hi_u32                       ret;
3526 
3527     /* 2.1 消息参数准备 */
3528     ssid_param.ssid_len = meshid_len;
3529     if (memcpy_s(ssid_param.ac_ssid, WLAN_SSID_MAX_LEN, (hi_s8 *)puc_meshid_ie, meshid_len) != EOK) {
3530         oam_error_log0(0, 0, "{wal_cfg80211_set_meshid::mem safe function err!}");
3531         return HI_FAIL;
3532     }
3533 
3534     /* 抛事件给驱动 */
3535     ret = wal_cfg80211_start_req(netdev, &ssid_param, sizeof(mac_cfg_ssid_param_stru), WLAN_CFGID_MESHID, HI_FALSE);
3536     if (ret != HI_SUCCESS) {
3537         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_set_meshid::return err code [%u]!}", ret);
3538         return ret;
3539     }
3540 
3541     return HI_SUCCESS;
3542 }
3543 #endif
3544 
wal_cfg80211_configuration_beacon(const mac_vap_stru * mac_vap,const oal_beacon_data_stru * beacon_info,mac_beacon_param_stru * beacon_param)3545 hi_u32 wal_cfg80211_configuration_beacon(const mac_vap_stru *mac_vap, const oal_beacon_data_stru *beacon_info,
3546     mac_beacon_param_stru *beacon_param)
3547 {
3548     oal_beacon_parameters beacon_info_tmp = { 0 };
3549     hi_u32 ret;
3550 
3551     /* ****************************************************************************
3552         1.安全配置ie消息等
3553     **************************************************************************** */
3554     hi_u16 beacon_head_len = (hi_u16)beacon_info->head_len;
3555     hi_u16 beacon_tail_len = (hi_u16)beacon_info->tail_len;
3556     hi_u32 beacon_len = (hi_u32)beacon_head_len + (hi_u32)beacon_tail_len;
3557     hi_u8 *puc_beacon_info_tmp = (hi_u8 *)(oal_memalloc(beacon_len));
3558     if (puc_beacon_info_tmp == HI_NULL) {
3559         oam_error_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::memalloc failed.}");
3560         return HI_ERR_CODE_PTR_NULL;
3561     } else {
3562         /* 复制beacon内容 (11b模式下,beacon_tail_len为0) */
3563         if (beacon_tail_len != 0) {
3564             ret = (hi_u32)memcpy_s(puc_beacon_info_tmp, beacon_head_len, beacon_info->head, beacon_head_len);
3565             ret |= (hi_u32)memcpy_s(puc_beacon_info_tmp + beacon_head_len, beacon_tail_len, beacon_info->tail,
3566                 beacon_tail_len);
3567         } else {
3568             ret = (hi_u32)memcpy_s(puc_beacon_info_tmp, beacon_head_len, beacon_info->head, beacon_head_len);
3569         }
3570         if (ret != EOK) {
3571             oam_error_log0(0, 0, "{wal_cfg80211_fill_beacon_param::mem safe function err!}");
3572             oal_free(puc_beacon_info_tmp);
3573             return HI_FAIL;
3574         }
3575     }
3576 
3577     beacon_info_tmp.head     = puc_beacon_info_tmp;
3578     beacon_info_tmp.head_len = (hi_u32)beacon_head_len;
3579     beacon_info_tmp.tail     = puc_beacon_info_tmp + (hi_u32)beacon_head_len;
3580     beacon_info_tmp.tail_len = (hi_u32)beacon_tail_len;
3581 
3582     /* 获取 WPA/WPA2 信息元素 */
3583     ret = wal_parse_wpa_wpa2_ie(&beacon_info_tmp, beacon_param);
3584     if (ret != HI_SUCCESS) {
3585         oam_warning_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::failed to parse WPA/WPA2 ie!}");
3586         oal_free(puc_beacon_info_tmp);
3587         return ret;
3588     }
3589 
3590     ret = wal_parse_ht_vht_ie(mac_vap, &beacon_info_tmp, beacon_param);
3591     if (ret != HI_SUCCESS) {
3592         oam_warning_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::failed to parse HT/VHT ie!}");
3593         oal_free(puc_beacon_info_tmp);
3594         return ret;
3595     }
3596 
3597 #ifdef _PRE_WLAN_FEATURE_MESH
3598     /* 获取mesh conf信息元素 */
3599     if (mac_vap->vap_mode == WLAN_VAP_MODE_MESH) {
3600         ret = wal_parse_mesh_conf_ie(&beacon_info_tmp, beacon_param);
3601         if (ret != HI_SUCCESS) {
3602             oam_warning_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::Mesh VAP fail parse ie!}");
3603             oal_free(puc_beacon_info_tmp);
3604             return ret;
3605         }
3606     }
3607 #endif
3608     /* 释放临时申请的内存 */
3609     oal_free(puc_beacon_info_tmp);
3610 
3611     return HI_SUCCESS;
3612 }
3613 
3614 /* ****************************************************************************
3615  函 数 名  : wal_cfg80211_fill_beacon_param
3616  功能描述  : 将要下发的修改的beacon帧参数填入到入参结构体中
3617  输入参数  : mac_vap_stru                *pst_mac_vap,
3618              struct cfg80211_beacon_data *pst_beacon_info,
3619              mac_beacon_param_stru       *pst_beacon_param
3620  输出参数  : 无
3621  返 回 值  : static hi_s32
3622  调用函数  :
3623  被调函数  :
3624 
3625  修改历史      :
3626   1.日    期   : 2014年12月31日
3627     作    者   : HiSilicon
3628     修改内容   : 新生成函数
3629 
3630 **************************************************************************** */
wal_cfg80211_fill_beacon_param(mac_vap_stru * mac_vap,oal_beacon_data_stru * beacon_info,mac_beacon_param_stru * beacon_param)3631 hi_u32 wal_cfg80211_fill_beacon_param(mac_vap_stru *mac_vap, oal_beacon_data_stru *beacon_info,
3632     mac_beacon_param_stru *beacon_param)
3633 {
3634     hi_u32 loop, loop1;
3635 
3636     if (mac_vap == HI_NULL || beacon_info == HI_NULL || beacon_param == HI_NULL) {
3637         oam_error_log3(0, OAM_SF_ANY,
3638             "{wal_cfg80211_fill_beacon_param::param is NULL. pst_mac_vap=%p, pst_beacon_info=%p, pst_beacon_param=%p",
3639             (uintptr_t)mac_vap, (uintptr_t)beacon_info, (uintptr_t)beacon_param);
3640         return HI_ERR_CODE_PTR_NULL;
3641     }
3642     if (beacon_info->tail == HI_NULL || beacon_info->head == HI_NULL) {
3643         oam_error_log2(mac_vap->vap_id, OAM_SF_ANY,
3644             "{wal_cfg80211_fill_beacon_param::beacon frame error tail = %p, head = %p!}", (uintptr_t)beacon_info->tail,
3645             (uintptr_t)beacon_info->head);
3646         return HI_ERR_CODE_PTR_NULL;
3647     }
3648 
3649     hi_u32 ret = wal_cfg80211_configuration_beacon(mac_vap, beacon_info, beacon_param);
3650     if (ret != HI_SUCCESS) {
3651         return ret;
3652     }
3653 
3654     oam_warning_log3(mac_vap->vap_id, OAM_SF_ANY,
3655         "{wal_cfg80211_fill_beacon_param::crypto_mode=%d, group_crypt=%d, en_protocol=%d!}", beacon_param->crypto_mode,
3656         beacon_param->group_crypto, beacon_param->protocol);
3657 
3658     oam_warning_log2(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::auth_type[0]=%d, auth_type[1]=%d}",
3659         beacon_param->auc_auth_type[0], beacon_param->auc_auth_type[1]);
3660 
3661 #ifdef _PRE_WLAN_FEATURE_MESH
3662     /* 打印调试使用 */
3663     if (mac_vap->vap_mode == WLAN_VAP_MODE_MESH) {
3664         oam_warning_log2(mac_vap->vap_id, OAM_SF_ANY,
3665             "{wal_cfg80211_fill_beacon_param::mesh formation info = %d, mesh capability = %d}",
3666             beacon_param->mesh_formation_info, beacon_param->mesh_capability);
3667     }
3668 #endif
3669 
3670     /* 对日本14信道作特殊判断,只在11b模式下才能启用14,非11b模式 降为11b */
3671     if ((mac_vap->channel.chan_number == 14) && (beacon_param->protocol != WLAN_LEGACY_11B_MODE)) { /* 14:代表信道号 */
3672         oam_error_log1(mac_vap->vap_id, OAM_SF_ANY,
3673                        "{wal_cfg80211_fill_beacon_param::ch 14 should in 11b, but is %d!}", beacon_param->protocol);
3674         oam_error_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::change protocol to 11b!}");
3675         beacon_param->protocol = WLAN_LEGACY_11B_MODE;
3676     }
3677 
3678     for (loop = 0; loop < MAC_PAIRWISE_CIPHER_SUITES_NUM; loop++) {
3679         oam_warning_log2(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::wpa pariwise[%d] = %d!}",
3680                          loop, beacon_param->auc_pairwise_crypto_wpa[loop]);
3681     }
3682 
3683     for (loop1 = 0; loop1 < MAC_PAIRWISE_CIPHER_SUITES_NUM; loop1++) {
3684         oam_warning_log2(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param::wpa2 pariwise[%d] = %d!}",
3685             loop1, beacon_param->auc_pairwise_crypto_wpa2[loop1]);
3686     }
3687 
3688     return HI_SUCCESS;
3689 }
3690 
3691 /* ****************************************************************************
3692  函 数 名  : wal_cfg80211_change_beacon
3693  功能描述  : 修改ap beacon帧配置参数
3694  输入参数  : oal_wiphy_stru          *pst_wiphy
3695              oal_net_device_stru     *pst_netdev
3696              struct cfg80211_beacon_data *info
3697  输出参数  : 无
3698  返 回 值  : static hi_s32
3699  调用函数  :
3700  被调函数  :
3701 
3702  修改历史      :
3703   1.日    期   : 2014年12月31日
3704     作    者   : HiSilicon
3705     修改内容   : 新生成函数
3706 
3707 **************************************************************************** */
3708 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_cfg80211_change_beacon(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,oal_beacon_data_stru * beacon_info)3709 hi_u32 wal_cfg80211_change_beacon(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, oal_beacon_data_stru *beacon_info)
3710 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3711 hi_s32 wal_cfg80211_change_beacon(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, oal_beacon_data_stru *beacon_info)
3712 #endif
3713 {
3714     mac_beacon_param_stru        beacon_param;  /* beacon info struct */
3715     mac_vap_stru                *mac_vap = HI_NULL;
3716     hi_u32                       ret;
3717 
3718     hi_unref_param(wiphy);
3719 
3720     /* 参数合法性检查 */
3721     if ((netdev == HI_NULL) || (beacon_info == HI_NULL)) {
3722         oam_error_log2(0, OAM_SF_ANY, "{wal_cfg80211_change_beacon::pst_netdev = %p, pst_beacon_info = %p!}",
3723             (uintptr_t)netdev, (uintptr_t)beacon_info);
3724         goto fail;
3725     }
3726 
3727     /* 获取vap id */
3728     mac_vap = oal_net_dev_priv(netdev);
3729     if (mac_vap == HI_NULL) {
3730         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_change_beacon::pst_mac_vap = %p}", (uintptr_t)mac_vap);
3731         goto fail;
3732     }
3733 
3734     /* 初始化beacon interval 和DTIM_PERIOD 参数 */
3735     if (memset_s(&beacon_param, sizeof(mac_beacon_param_stru), 0, sizeof(mac_beacon_param_stru)) != EOK) {
3736         oam_error_log0(0, 0, "{wal_cfg80211_change_beacon::mem safe function err!}");
3737         goto fail;
3738     }
3739     ret = wal_cfg80211_fill_beacon_param(mac_vap, beacon_info, &beacon_param);
3740     if (ret != HI_SUCCESS) {
3741         oam_error_log1(mac_vap->vap_id, OAM_SF_ANY,
3742             "{wal_cfg80211_change_beacon::failed to fill beacon param, error[%d]}", ret);
3743         goto fail;
3744     }
3745 
3746     /* 设置操作类型 */
3747     beacon_param.operation_type = MAC_SET_BEACON;
3748 
3749     /* 抛事件给驱动 */
3750     ret = wal_cfg80211_start_req(netdev, &beacon_param, sizeof(mac_beacon_param_stru),
3751         WLAN_CFGID_CFG80211_CONFIG_BEACON, HI_FALSE);
3752     if (ret != HI_SUCCESS) {
3753         oam_warning_log1(0, OAM_SF_ANY, "{wal_cfg80211_change_beacon::Failed to start addset beacon, error[%d]!}", ret);
3754         goto fail;
3755     }
3756 
3757     return HI_SUCCESS;
3758 
3759 fail:
3760 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
3761     return HI_FAIL;
3762 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3763     return -HI_FAIL;
3764 #endif
3765 }
3766 
3767 /* ****************************************************************************
3768  函 数 名  : wal_cfg80211_convert_width_to_value
3769  功能描述  : 将内核下发的带宽枚举转换成真实的带宽宽度值
3770  输入参数  : [1]l_channel_width
3771  输出参数  : 无
3772  返 回 值  : static hi_s32
3773 **************************************************************************** */
wal_cfg80211_convert_width_to_value(hi_s32 l_channel_width)3774 static hi_u32 wal_cfg80211_convert_width_to_value(hi_s32 l_channel_width)
3775 {
3776     hi_u32 l_channel_width_value = 0;
3777 
3778     switch (l_channel_width) {
3779         case 0: /* 0 内核带宽 */
3780         case 1: /* 1 内核带宽 */
3781             l_channel_width_value = 20; /* 20 真实的带宽值 */
3782             break;
3783         case 2: /* 2 内核带宽 */
3784             l_channel_width_value = 40; /* 40 真实的带宽值 */
3785             break;
3786         case 3: /* 3 内核带宽 */
3787         case 4: /* 4 内核带宽 */
3788             l_channel_width_value = 80; /* 80 真实的带宽值 */
3789             break;
3790         case 5: /* 5 内核带宽 */
3791             l_channel_width_value = 160; /* 160 真实的带宽值 */
3792             break;
3793         default:
3794             break;
3795     }
3796 
3797     return l_channel_width_value;
3798 }
3799 
3800 /* ****************************************************************************
3801  函 数 名  : wal_cfg80211_set_channel_info
3802  功能描述  : 设置信道
3803  输入参数  : oal_wiphy_stru           *pst_wiphy
3804              oal_net_device_stru      *pst_netdev
3805  输出参数  : 无
3806  返 回 值  : static hi_s32
3807  调用函数  :
3808  被调函数  :
3809 
3810  修改历史      :
3811   1.日    期   : 2014年12月30日
3812     作    者   : HiSilicon
3813     修改内容   : 新生成函数
3814 
3815 **************************************************************************** */
wal_cfg80211_set_channel_info(oal_net_device_stru * netdev)3816 hi_u32 wal_cfg80211_set_channel_info(oal_net_device_stru *netdev)
3817 {
3818     mac_cfg_channel_param_stru channel_param = { 0 };
3819     wlan_channel_bandwidth_enum_uint8 bandwidth;
3820 
3821     oal_ieee80211_channel *channel = (oal_ieee80211_channel *)GET_NET_DEV_CFG80211_WIRELESS(netdev)->preset_chandef.chan;
3822     hi_s32 l_bandwidth = GET_NET_DEV_CFG80211_WIRELESS(netdev)->preset_chandef.width;
3823     hi_s32 l_center_freq1 = GET_NET_DEV_CFG80211_WIRELESS(netdev)->preset_chandef.center_freq1;
3824     hi_s32 l_channel      = channel->hw_value;
3825 
3826     /* 判断信道在不在管制域内 */
3827     hi_u32 ret = mac_is_channel_num_valid(channel->band, (hi_u8)l_channel);
3828     if (ret != HI_SUCCESS) {
3829         oam_warning_log3(0, OAM_SF_ANY, "{wal_cfg80211_set_channel::channel Err.band=%d,ch=%d,ErrCode=%u}",
3830             channel->band, l_channel, ret);
3831         return ret;
3832     }
3833 
3834     /* 进行内核带宽值和WITP 带宽值转换 */
3835     hi_s32 l_channel_center_freq = oal_ieee80211_frequency_to_channel(l_center_freq1);
3836     hi_u32 l_bandwidth_value     = wal_cfg80211_convert_width_to_value(l_bandwidth);
3837     if (l_bandwidth_value == 0) {
3838         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_set_channel::channelWidth Err,l_bandwidth=%d", l_bandwidth);
3839         return HI_FAIL;
3840     }
3841 
3842     if (l_bandwidth_value == 80) { /* 80:代表带宽值 */
3843         bandwidth = mac_get_bandwith_from_center_freq_seg0((hi_u8)l_channel, (hi_u8)l_channel_center_freq);
3844     } else if (l_bandwidth_value == 40) { /* 40:代表带宽值 */
3845         switch (l_channel_center_freq - l_channel) {
3846             case -2: /* -2: 内核带宽 */
3847                 bandwidth = WLAN_BAND_WIDTH_40MINUS;
3848                 break;
3849             case 2: /* 2: 内核带宽 */
3850                 bandwidth = WLAN_BAND_WIDTH_40PLUS;
3851                 break;
3852             default:
3853                 bandwidth = WLAN_BAND_WIDTH_20M;
3854                 break;
3855         }
3856     } else {
3857         bandwidth = WLAN_BAND_WIDTH_20M;
3858     }
3859 
3860     /* 2.1 消息参数准备 */
3861     channel_param.channel      = (hi_u8)channel->hw_value;
3862     channel_param.band         = channel->band;
3863     channel_param.en_bandwidth = bandwidth;
3864 
3865     oam_warning_log3(0, OAM_SF_ANY, "{wal_cfg80211_set_channel::channel=%d,band=%d,bandwidth=%d}",
3866         channel_param.channel, channel_param.band, channel_param.en_bandwidth);
3867 
3868     /* 抛事件给驱动 */
3869     ret = wal_cfg80211_start_req(netdev, &channel_param, sizeof(mac_cfg_channel_param_stru),
3870         WLAN_CFGID_CFG80211_SET_CHANNEL, HI_TRUE);
3871     if (ret != HI_SUCCESS) {
3872         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_set_channel_info::return err code [%u]!}", ret);
3873         return ret;
3874     }
3875 
3876     return HI_SUCCESS;
3877 }
3878 
wal_wifi_set_bw(oal_net_device_stru * netdev,wal_wifi_bw_enum_int bw)3879 hi_u32 wal_wifi_set_bw(oal_net_device_stru *netdev, wal_wifi_bw_enum_int bw)
3880 {
3881     hi_char ac_bw[WAL_BW_STR_MAX_LEN] = {0};
3882     if ((bw > WAL_WIFI_BW_HIEX_5M) || (bw < WAL_WIFI_BW_LEGACY_20M)) {
3883         oam_error_log0(0, 0, "hi_wifi_set_bandwidth invalid bw.");
3884         return HI_FAIL;
3885     }
3886 
3887     strcpy_s(ac_bw, WAL_BW_STR_MAX_LEN, "20");
3888     if (bw == WAL_WIFI_BW_HIEX_5M) {
3889         strcpy_s(ac_bw, WAL_BW_STR_MAX_LEN, "5");
3890     } else if (bw == WAL_WIFI_BW_HIEX_10M) {
3891         strcpy_s(ac_bw, WAL_BW_STR_MAX_LEN, "10");
3892     }
3893 
3894     if (wal_hipriv_set_bw(netdev, (hi_char *)ac_bw) != HI_SUCCESS) {
3895         oam_error_log0(0, 0, "wal_hipriv_set_bw failed.");
3896         return HI_FAIL;
3897     }
3898 
3899     return HI_SUCCESS;
3900 }
3901 
3902 /* ****************************************************************************
3903  函 数 名  : wal_cfg80211_start_ap
3904  功能描述  : 启动AP,配置AP 参数。
3905  输入参数  : oal_wiphy_stru              *pst_wiphy
3906              oal_net_device_stru         *pst_netdev
3907              struct cfg80211_ap_settings *settings
3908  输出参数  : 无
3909  返 回 值  : static hi_s32
3910  调用函数  :
3911  被调函数  :
3912 
3913  修改历史      :
3914   1.日    期   : 2014年12月30日
3915     作    者   : HiSilicon
3916     修改内容   : 新生成函数
3917 
3918 **************************************************************************** */
3919 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
wal_cfg80211_start_ap(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,oal_ap_settings_stru * ap_settings)3920 hi_u32 wal_cfg80211_start_ap(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, oal_ap_settings_stru *ap_settings)
3921 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
3922 hi_s32 wal_cfg80211_start_ap(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, oal_ap_settings_stru *ap_settings)
3923 #endif
3924 {
3925     mac_beacon_param_stru beacon_param = { 0 }; /* beacon info struct */
3926 
3927     hi_unref_param(wiphy);
3928 
3929     /* 参数合法性检查 */
3930     if ((netdev == HI_NULL) || (ap_settings == HI_NULL)) {
3931         oam_error_log2(0, OAM_SF_ANY, "{wal_cfg80211_start_ap:: %p, %p!}", (uintptr_t)netdev, (uintptr_t)ap_settings);
3932         goto fail;
3933     }
3934 
3935     /* 获取vap id */
3936     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
3937     if (mac_vap == HI_NULL) {
3938         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_start_ap::pst_mac_vap = %p}", (uintptr_t)mac_vap);
3939         goto fail;
3940     }
3941 
3942     /* ****************************************************************************
3943         1.设置信道
3944     **************************************************************************** */
3945     if (wal_cfg80211_set_channel_info(netdev) != HI_SUCCESS) {
3946         goto fail;
3947     }
3948 
3949     /* ****************************************************************************
3950         2.设置ssid等信息
3951     **************************************************************************** */
3952     if ((ap_settings->ssid_len > 32) || (ap_settings->ssid_len == 0)) { /* 32: 长度上界 */
3953         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_start_ap: len[%d].}", ap_settings->ssid_len);
3954         goto fail;
3955     }
3956 
3957     if (wal_cfg80211_set_ssid(netdev, ap_settings->ssid, (hi_u8)ap_settings->ssid_len) != HI_SUCCESS) {
3958         goto fail;
3959     }
3960 
3961 #ifdef _PRE_WLAN_FEATURE_MESH
3962     /* ****************************************************************************
3963         2.Mesh设置meshid等信息,与ssid一致
3964     **************************************************************************** */
3965     if (mac_vap->vap_mode == WLAN_VAP_MODE_MESH) {
3966         if (wal_cfg80211_set_meshid(netdev, ap_settings->ssid, (hi_u8)ap_settings->ssid_len) != HI_SUCCESS) {
3967             goto fail;
3968         }
3969     }
3970 #endif
3971 
3972     /* ****************************************************************************
3973         3.设置beacon时间间隔、tim period以及安全配置消息等
3974     **************************************************************************** */
3975     /* 初始化beacon interval 和DTIM_PERIOD 参数 */
3976     beacon_param.l_interval = ap_settings->beacon_interval;
3977     beacon_param.l_dtim_period = ap_settings->dtim_period;
3978     beacon_param.hidden_ssid = (ap_settings->hidden_ssid == 1);
3979 
3980     oam_warning_log3(0, OAM_SF_ANY, "{wal_cfg80211_fill_beacon_param:beacon_interval=%d,dtim_period=%d,hidden_ssid=%d}",
3981         ap_settings->beacon_interval, ap_settings->dtim_period, ap_settings->hidden_ssid);
3982 
3983     if (wal_cfg80211_fill_beacon_param(mac_vap, &(ap_settings->beacon), &beacon_param) != HI_SUCCESS) {
3984         goto fail;
3985     }
3986 
3987     /* 设置操作类型 */
3988     beacon_param.operation_type = MAC_ADD_BEACON;
3989 
3990     /* 抛事件给驱动 */
3991     if (wal_cfg80211_start_req(netdev, &beacon_param, sizeof(mac_beacon_param_stru), WLAN_CFGID_CFG80211_CONFIG_BEACON,
3992         HI_FALSE) != HI_SUCCESS) {
3993         goto fail;
3994     }
3995 
3996     /* ****************************************************************************
3997         4.启动ap
3998     **************************************************************************** */
3999     hi_u32 ret = wal_start_vap(netdev);
4000     if (oal_unlikely(ret != HI_SUCCESS)) {
4001         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_start_ap::failed to start ap, error[%u]}", ret);
4002         goto fail;
4003     }
4004     /* 设置net_device里flags标志 */
4005     if ((oal_netdevice_flags(netdev) & OAL_IFF_RUNNING) != 0) {
4006         oal_netdevice_flags(netdev) &= (~OAL_IFF_RUNNING);
4007     }
4008     if (wal_wifi_set_bw(netdev, g_bw) != HI_SUCCESS) {
4009         oam_warning_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_start_ap::failed to set bw}");
4010         goto fail;
4011     }
4012     if ((oal_netdevice_flags(netdev) & OAL_IFF_RUNNING) == 0) {
4013         oal_netdevice_flags(netdev) |= OAL_IFF_RUNNING;
4014     }
4015 
4016     return HI_SUCCESS;
4017 
4018 fail:
4019 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
4020     return HI_FAIL;
4021 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
4022     return -HI_FAIL;
4023 #endif
4024 }
4025 
4026 /* ****************************************************************************
4027  函 数 名  : wal_cfg80211_change_virtual_intf
4028  功能描述  : 转换AP,STA 状态
4029  输入参数  : [1]wiphy
4030              [2]net_dev
4031              [3]type        下一个状态
4032              [4]pul_flags
4033              [5]params
4034  输出参数  : 无
4035  返 回 值  : static hi_s32
4036 **************************************************************************** */
4037 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
wal_cfg80211_change_virtual_intf(oal_wiphy_stru * wiphy,oal_net_device_stru * net_dev,enum_nl80211_iftype type,hi_u32 * pul_flags,oal_vif_params_stru * params)4038 hi_s32 wal_cfg80211_change_virtual_intf(oal_wiphy_stru *wiphy, oal_net_device_stru *net_dev, enum_nl80211_iftype type,
4039     hi_u32 *pul_flags, oal_vif_params_stru *params)
4040 {
4041     wlan_p2p_mode_enum_uint8 p2p_mode;
4042     wlan_vap_mode_enum_uint8 vap_mode;
4043 #ifdef _PRE_WLAN_FEATURE_P2P
4044     mac_cfg_del_vap_param_stru del_vap_param;
4045     mac_cfg_add_vap_param_stru add_vap_param;
4046     mac_vap_stru *mac_vap = HI_NULL;
4047 #endif
4048     hi_unref_param(wiphy);
4049 
4050     /* 1.1 入参检查 */
4051     if (net_dev == HI_NULL) {
4052         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::pst_dev is null!}\r\n");
4053         return -HI_ERR_CODE_PTR_NULL;
4054     }
4055 
4056     if (params == HI_NULL) {
4057         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::pst_params ptr is null!}\r\n");
4058         return -HI_ERR_CODE_PTR_NULL;
4059     }
4060 
4061     /* 检查VAP 当前模式和目的模式是否相同,如果相同则直接返回 */
4062     if (net_dev->ieee80211Ptr->iftype == type) {
4063         oam_warning_log1(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::same iftype[%d],do not need change !}\r\n",
4064             type);
4065         return HI_SUCCESS;
4066     }
4067 
4068     oam_warning_log2(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::[%d][%d]}\r\n",
4069                      (net_dev->ieee80211Ptr->iftype), type);
4070 
4071     switch (type) {
4072         case NL80211_IFTYPE_MONITOR:
4073         case NL80211_IFTYPE_WDS:
4074         case NL80211_IFTYPE_ADHOC:
4075             oam_error_log1(0, OAM_SF_CFG,
4076                 "{wal_cfg80211_change_virtual_intf::currently we do not support this type[%d]}\r\n", type);
4077             return -HI_ERR_WIFI_WAL_INVALID_PARAMETER;
4078 #ifdef _PRE_WLAN_FEATURE_MESH
4079         case NL80211_IFTYPE_MESH_POINT:
4080             vap_mode = WLAN_VAP_MODE_MESH;
4081             p2p_mode = WLAN_LEGACY_VAP_MODE;
4082             break;
4083 #endif
4084         case NL80211_IFTYPE_STATION:
4085             if (net_dev->ieee80211Ptr->iftype == NL80211_IFTYPE_AP) {
4086                 /* 结束扫描,以防在20/40M扫描过程中关闭AP */
4087                 wal_force_scan_complete(net_dev);
4088 
4089                 /* AP关闭切换到STA模式,删除相关vap */
4090                 if (HI_SUCCESS != wal_stop_vap(net_dev)) {
4091                     oam_warning_log0(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::wal_stop_vap enter an error.}");
4092                 }
4093                 if (HI_SUCCESS != wal_deinit_wlan_vap(net_dev)) {
4094                     oam_warning_log0(0, OAM_SF_CFG,
4095                         "{wal_cfg80211_change_virtual_intf::wal_deinit_wlan_vap enter an error.}");
4096                 }
4097 
4098                 net_dev->ieee80211Ptr->iftype = type;
4099 
4100                 return HI_SUCCESS;
4101             }
4102             {
4103                 net_dev->ieee80211Ptr->iftype = type; /* P2P BUG P2P_DEVICE 提前创建,不需要通过wpa_supplicant 创建 */
4104                 oam_warning_log0(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::change to station}\r\n");
4105             }
4106             return HI_SUCCESS;
4107         case NL80211_IFTYPE_P2P_CLIENT:
4108             vap_mode = WLAN_VAP_MODE_BSS_STA;
4109             p2p_mode = WLAN_P2P_CL_MODE;
4110             break;
4111         case NL80211_IFTYPE_AP:
4112         case NL80211_IFTYPE_AP_VLAN:
4113             vap_mode = WLAN_VAP_MODE_BSS_AP;
4114             p2p_mode = WLAN_LEGACY_VAP_MODE;
4115             break;
4116         case NL80211_IFTYPE_P2P_GO:
4117             vap_mode = WLAN_VAP_MODE_BSS_AP;
4118             p2p_mode = WLAN_P2P_GO_MODE;
4119             break;
4120         default:
4121             oam_error_log1(0, OAM_SF_CFG,
4122                 "{wal_cfg80211_change_virtual_intf::currently we do not support this type[%d]}\r\n", type);
4123             return -HI_ERR_CODE_PTR_NULL;
4124     }
4125 
4126     if ((type == NL80211_IFTYPE_AP) || (type == NL80211_IFTYPE_MESH_POINT)) {
4127         net_dev->ieee80211Ptr->iftype = type;
4128         if (wal_setup_vap(net_dev) != HI_SUCCESS) {
4129             return -HI_FAIL;
4130         }
4131         return HI_SUCCESS;
4132     }
4133 #ifdef _PRE_WLAN_FEATURE_P2P
4134     /* 设备为P2P 设备才需要进行change virtual interface */
4135     mac_vap = oal_net_dev_priv(net_dev);
4136     if (mac_vap == HI_NULL) {
4137         oam_error_log0(0, OAM_SF_CFG,
4138             "{wal_cfg80211_change_virtual_intf::can't get mac vap from netdevice priv data.}\r\n");
4139         return -HI_ERR_CODE_PTR_NULL;
4140     }
4141 
4142     if (is_legacy_vap(mac_vap)) {
4143         net_dev->ieee80211Ptr->iftype = type;
4144         return HI_SUCCESS;
4145     }
4146 
4147     if ((strcmp("p2p0", (const hi_char *)net_dev->name)) == 0) {
4148         /* 解决异常情况下,wpa_supplicant下发p2p0设备切换到p2p go/cli模式导致fastboot的问题 */
4149         oam_warning_log0(0, OAM_SF_CFG,
4150             "{wal_cfg80211_change_virtual_intf::p2p0 netdevice can not change to P2P CLI/GO.}\r\n");
4151         return -HI_FAIL;
4152     }
4153 
4154     /* 如果当前模式和目的模式不同,则需要:
4155        1. 停止 VAP
4156        2. 删除 VAP
4157        3. 重新创建对应模式VAP
4158        4. 启动VAP
4159     */
4160     /* 停止VAP */
4161     wal_netdev_stop(net_dev);
4162     if (memset_s(&del_vap_param, sizeof(del_vap_param), 0, sizeof(del_vap_param)) != EOK) {
4163         return -HI_FAIL;
4164     }
4165     /* 删除VAP */
4166     del_vap_param.net_dev = net_dev;
4167     /* 设备p2p 模式需要从net_device 中获取 */
4168     del_vap_param.p2p_mode = wal_wireless_iftype_to_mac_p2p_mode(net_dev->ieee80211Ptr->iftype);
4169     if (wal_cfg80211_del_vap(&del_vap_param)) {
4170         return -HI_FAIL;
4171     }
4172 
4173     if (memset_s(&add_vap_param, sizeof(add_vap_param), 0, sizeof(add_vap_param)) != EOK) {
4174         return -HI_FAIL;
4175     }
4176     /* 重新创建对应模式VAP */
4177     add_vap_param.net_dev = net_dev;
4178     add_vap_param.vap_mode = vap_mode;
4179     add_vap_param.p2p_mode = p2p_mode;
4180     if (wal_cfg80211_add_vap(&add_vap_param) != HI_SUCCESS) {
4181         return -HI_FAIL;
4182     }
4183     /* 启动VAP */
4184     wal_netdev_open(net_dev);
4185 
4186     net_dev->ieee80211Ptr->iftype = type;
4187 #endif
4188     return HI_SUCCESS;
4189 }
4190 #else
wal_cfg80211_intf_mode_check(oal_net_device_stru * netdev,nl80211_iftype_uint8 type)4191 hi_u32 wal_cfg80211_intf_mode_check(oal_net_device_stru *netdev, nl80211_iftype_uint8 type)
4192 {
4193     switch (type) {
4194         case NL80211_IFTYPE_MONITOR:
4195         case NL80211_IFTYPE_WDS:
4196         case NL80211_IFTYPE_ADHOC:
4197             oam_error_log1(0, OAM_SF_CFG,
4198                 "{wal_cfg80211_change_virtual_intf::currently we do not support this type[%d]}\r\n", type);
4199             return HI_ERR_WIFI_WAL_INVALID_PARAMETER;
4200         case NL80211_IFTYPE_STATION:
4201             if (GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype == NL80211_IFTYPE_AP) {
4202                 /* 结束扫描,以防在20/40M扫描过程中关闭AP */
4203                 wal_force_scan_complete(netdev);
4204 
4205                 /* AP关闭切换到STA模式,删除相关vap */
4206                 if (wal_stop_vap(netdev) != HI_SUCCESS) {
4207                     oam_warning_log0(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::wal_stop_vap enter an error.}");
4208                 }
4209                 if (wal_deinit_wlan_vap(netdev) != HI_SUCCESS) {
4210                     oam_warning_log0(0, OAM_SF_CFG,
4211                         "{wal_cfg80211_change_virtual_intf::wal_deinit_wlan_vap enter an error.}");
4212                 }
4213 
4214                 GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype = type;
4215 
4216                 return HI_SUCCESS;
4217             }
4218             GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype = type; /* P2P BUG P2P_DEVICE 提前创建,不需要通过wpa_supplicant 创建 */
4219             oam_warning_log0(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::change to station}\r\n");
4220             return HI_SUCCESS;
4221 #ifdef _PRE_WLAN_FEATURE_MESH
4222         case NL80211_IFTYPE_MESH_POINT:
4223 #endif
4224         case NL80211_IFTYPE_P2P_CLIENT:
4225         case NL80211_IFTYPE_AP:
4226         case NL80211_IFTYPE_AP_VLAN:
4227         case NL80211_IFTYPE_P2P_GO:
4228             break;
4229         default:
4230             oam_error_log1(0, OAM_SF_CFG,
4231                 "{wal_cfg80211_change_virtual_intf::currently we do not support this type[%d]}\r\n", type);
4232             return HI_ERR_CODE_PTR_NULL;
4233     }
4234 
4235     return HI_CONTINUE;
4236 }
4237 
wal_cfg80211_change_virtual_intf(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,nl80211_iftype_uint8 type,hi_u32 * pul_flags,oal_vif_params_stru * params)4238 hi_u32 wal_cfg80211_change_virtual_intf(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev, nl80211_iftype_uint8 type,
4239     hi_u32 *pul_flags, oal_vif_params_stru *params)
4240 {
4241     mac_vap_stru *mac_vap = HI_NULL;
4242     hi_u32 ret;
4243     hi_unref_param(wiphy);
4244 
4245     /* 1.1 入参检查 */
4246     if (netdev == HI_NULL || params == HI_NULL) {
4247         oam_error_log2(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::params null! netdev=%p, params=%p",
4248             (uintptr_t)netdev, (uintptr_t)params);
4249         return HI_ERR_CODE_PTR_NULL;
4250     }
4251     oam_warning_log1(0, OAM_SF_CFG, "wal_cfg80211_change_virtual_intf::iftype[%d],enter", type);
4252 
4253     if (GET_NET_DEV_CFG80211_WIRELESS(netdev) == NULL)
4254     {
4255         oam_warning_log0(0, OAM_SF_CFG, "wal_cfg80211_change_virtual_intf:: null");
4256     }
4257 
4258     /* 检查VAP 当前模式和目的模式是否相同,如果相同则直接返回 */
4259     if (GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype == type) {
4260         oam_warning_log1(0, OAM_SF_CFG, "wal_cfg80211_change_virtual_intf::same iftype[%d],do not need change!", type);
4261         return HI_SUCCESS;
4262     }
4263 
4264     oam_warning_log2(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::[%d][%d]}\r\n",
4265         (GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype), type);
4266     *pul_flags = 0;
4267 
4268     ret = wal_cfg80211_intf_mode_check(netdev, type);
4269     if (ret != HI_CONTINUE) {
4270         return ret;
4271     }
4272 
4273     if ((type == NL80211_IFTYPE_AP) || (type == NL80211_IFTYPE_MESH_POINT)) {
4274         GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype = type;
4275         return wal_setup_vap(netdev);
4276     }
4277 
4278     /* 设备为P2P 设备才需要进行change virtual interface */
4279     mac_vap = oal_net_dev_priv(netdev);
4280     if (mac_vap == HI_NULL) {
4281         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_change_virtual_intf::oal_net_dev_priv fail!}\r\n");
4282         return HI_ERR_CODE_PTR_NULL;
4283     }
4284 
4285     if (is_legacy_vap(mac_vap)) {
4286         GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype = type;
4287         return HI_SUCCESS;
4288     }
4289 
4290     if ((strcmp("p2p0", (const hi_char *)netdev->name)) == 0) {
4291         /* 解决异常情况下,wpa_supplicant下发p2p0设备切换到p2p go/cli模式导致fastboot的问题 */
4292         oam_warning_log0(0, OAM_SF_CFG,
4293             "{wal_cfg80211_change_virtual_intf::p2p0 netdevice can not change to P2P CLI/GO.}\r\n");
4294         return HI_FAIL;
4295     }
4296 
4297     /* 如果当前模式和目的模式不同,则需要:
4298        1. 停止 VAP
4299        2. 删除 VAP
4300        3. 重新创建对应模式VAP
4301        4. 启动VAP
4302     */
4303     /* 停止VAP */
4304     wal_netdev_stop(netdev);
4305     if (wal_deinit_wlan_vap(netdev) != HI_SUCCESS) {
4306         return HI_FAIL;
4307     }
4308 
4309     GET_NET_DEV_CFG80211_WIRELESS(netdev)->iftype = type;
4310     if (wal_init_wlan_vap(netdev) != HI_SUCCESS) {
4311         return HI_FAIL;
4312     }
4313     /* 启动VAP */
4314     wal_netdev_open(netdev);
4315 
4316     return HI_SUCCESS;
4317 }
4318 #endif
4319 
wal_cfg80211_del_send_event(oal_net_device_stru * netdev,const hi_u8 * mac_addr,mac_vap_stru * mac_vap)4320 hi_u32 wal_cfg80211_del_send_event(oal_net_device_stru *netdev, const hi_u8 *mac_addr, mac_vap_stru *mac_vap)
4321 {
4322     mac_cfg_kick_user_param_stru kick_user_param;
4323     hi_s32                       user_count_ok   = 0;
4324     hi_s32                       user_count_fail = 0;
4325     hi_u32                       ret;
4326 
4327     hi_unref_param(mac_vap);
4328 
4329     kick_user_param.us_reason_code = MAC_INACTIVITY;
4330 #ifdef _PRE_WLAN_FEATURE_MESH
4331     kick_user_param.us_reason_code =
4332         (mac_vap->vap_mode == WLAN_VAP_MODE_MESH) ? MAC_WPA_KICK_MESH_USER : kick_user_param.us_reason_code;
4333 #endif
4334 
4335     if (memcpy_s(kick_user_param.auc_mac_addr, OAL_MAC_ADDR_LEN, mac_addr, OAL_MAC_ADDR_LEN) != EOK) {
4336         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_del_send_event::mem safe function err!}");
4337         return HI_FAIL;
4338     }
4339 
4340 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
4341     ret = wal_cfg80211_start_disconnect(netdev, &kick_user_param);
4342 #else
4343     ret = wal_cfg80211_start_req(netdev, &kick_user_param, sizeof(mac_cfg_kick_user_param_stru), WLAN_CFGID_KICK_USER,
4344         HI_TRUE);
4345 #endif
4346     if (ret != HI_SUCCESS) {
4347         /* 由于删除的时候可能用户已经删除,此时再进行用户查找,会返回错误,输出ERROR打印,修改为warning */
4348         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_del_send_event::kick_user Err=%d}", ret);
4349         user_count_fail++;
4350     } else {
4351         user_count_ok++;
4352     }
4353 
4354     if (user_count_fail > 0) {
4355         oam_info_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_del_send_event::%d user deleteErr}", user_count_fail);
4356         return HI_ERR_CODE_PTR_NULL;
4357     }
4358 
4359     oam_info_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_del_send_event::%d user delete OK}", user_count_ok);
4360 
4361     return HI_SUCCESS;
4362 }
4363 
4364 /* ****************************************************************************
4365  函 数 名  : wal_cfg80211_del_station
4366  功能描述  : 删除用户
4367  输入参数  : oal_wiphy_stru *pst_wiphy
4368              oal_net_device *pst_dev
4369              hi_u8 *puc_mac         用户mac 地址。如果mac = NULL,删除所有用户
4370  输出参数  : 无
4371  返 回 值  : static hi_s32
4372  调用函数  :
4373  被调函数  :
4374 
4375  修改历史      :
4376   1.日    期   : 2013年11月13日
4377     作    者   : HiSilicon
4378     修改内容   : 新生成函数
4379 
4380 **************************************************************************** */
wal_cfg80211_del_station(oal_wiphy_stru * wiphy,oal_net_device_stru * netdev,oal_station_del_parameters_stru * params)4381 hi_u32 wal_cfg80211_del_station(oal_wiphy_stru *wiphy, oal_net_device_stru *netdev,
4382     oal_station_del_parameters_stru *params)
4383 {
4384     hi_u8 bcast_mac_addr[OAL_MAC_ADDR_LEN];
4385     hi_u8 user_idx;
4386 
4387     hi_unref_param(wiphy);
4388     if (netdev == HI_NULL) {
4389         goto fail;
4390     }
4391 
4392     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
4393     if (mac_vap == HI_NULL) {
4394         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_del_station::can't get mac vap from netdevice priv data!}\r\n");
4395         goto fail;
4396     }
4397 
4398     /* 判断是否是AP模式 */
4399     if ((mac_vap->vap_mode != WLAN_VAP_MODE_BSS_AP)
4400 #ifdef _PRE_WLAN_FEATURE_MESH
4401         && (mac_vap->vap_mode != WLAN_VAP_MODE_MESH)
4402 #endif
4403     ) {
4404         oam_error_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_del_station::vap_mode=%d Err}", mac_vap->vap_mode);
4405         goto fail;
4406     }
4407 
4408     if (params->mac == HI_NULL) {
4409         /* 安全编程规则6.6例外(1) 固定长度的结构体进行内存初始化 */
4410         memset_s(bcast_mac_addr, OAL_MAC_ADDR_LEN, 0xff, OAL_MAC_ADDR_LEN);
4411 
4412         params->mac = bcast_mac_addr;
4413         oam_info_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_del_station::deleting all user!}\r\n");
4414     } else {
4415         oam_info_log3(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_del_station::delete user:XX:XX:XX:%02X:%02X:%02X}",
4416             params->mac[3], params->mac[4], params->mac[5]); /* 3, 4, 5: 数组下标 */
4417     }
4418 
4419     hi_u32 ret = mac_vap_find_user_by_macaddr(mac_vap, (hi_u8 *)params->mac, OAL_MAC_ADDR_LEN, &user_idx);
4420 
4421     if (ret != HI_SUCCESS) {
4422         oam_warning_log0(mac_vap->vap_id, OAM_SF_UM, "{wal_cfg80211_del_station::user has been deleted}\r\n");
4423         goto fail;
4424     }
4425     ret = wal_cfg80211_del_send_event(netdev, params->mac, mac_vap);
4426 
4427     if (ret != HI_SUCCESS) {
4428         goto fail;
4429     }
4430 
4431     return HI_SUCCESS;
4432 
4433 fail:
4434     return HI_FAIL;
4435 }
4436 
4437 /* ****************************************************************************
4438  函 数 名  : wal_check_cookie_timeout
4439  功能描述  : 删除cookie 列表中超时的cookie
4440  输入参数  : cookie_arry_stru *pst_cookie_array
4441              hi_u32 ul_current_time
4442  输出参数  : 无
4443  返 回 值  : hi_void
4444  调用函数  :
4445  被调函数  :
4446 
4447  修改历史      :
4448   1.日    期   : 2015年1月6日
4449     作    者   : HiSilicon
4450     修改内容   : 新生成函数
4451 
4452 **************************************************************************** */
wal_check_cookie_timeout(cookie_arry_stru * cookie_array,hi_u8 * puc_cookie_bitmap)4453 hi_void wal_check_cookie_timeout(cookie_arry_stru *cookie_array, hi_u8 *puc_cookie_bitmap)
4454 {
4455     hi_u8               loops = 0;
4456     cookie_arry_stru   *tmp_cookie = HI_NULL;
4457 
4458     oam_warning_log0(0, OAM_SF_CFG, "{wal_check_cookie_timeout::time_out!}\r\n");
4459     for (loops = 0; loops < WAL_COOKIE_ARRAY_SIZE; loops++) {
4460         tmp_cookie = &cookie_array[loops];
4461 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
4462         if (hi_get_tick() > tmp_cookie->record_time + WAL_MGMT_TX_TIMEOUT_MSEC / HI_MILLISECOND_PER_TICK) {
4463 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
4464         if (oal_time_is_before(tmp_cookie->record_time + OAL_MSECS_TO_JIFFIES(WAL_MGMT_TX_TIMEOUT_MSEC))) {
4465 #endif
4466 
4467             /* cookie array 中保存的cookie 值超时 */
4468             /* 清空cookie array 中超时的cookie */
4469             tmp_cookie->record_time = 0;
4470             tmp_cookie->ull_cookie = 0;
4471             /* 清除占用的cookie bitmap位 */
4472             oal_bit_clear_bit_one_byte(puc_cookie_bitmap, loops);
4473         }
4474     }
4475 }
4476 
4477 /* ****************************************************************************
4478  函 数 名  : wal_del_cookie_from_array
4479  功能描述  : 删除指定idx 的cookie
4480  输入参数  : [1]cookie_array
4481              [2]puc_cookie_bitmap
4482              [3]cookie_idx
4483  输出参数  : 无
4484  返 回 值  : hi_u32
4485 **************************************************************************** */
4486 hi_u32 wal_del_cookie_from_array(cookie_arry_stru *cookie_array, hi_u8 *puc_cookie_bitmap, hi_u8 cookie_idx)
4487 {
4488     cookie_arry_stru *tmp_cookie = HI_NULL;
4489 
4490     /* 清除对应cookie bitmap 位 */
4491     oal_bit_clear_bit_one_byte(puc_cookie_bitmap, cookie_idx);
4492 
4493     /* 清空cookie array 中超时的cookie */
4494     tmp_cookie = &cookie_array[cookie_idx];
4495     tmp_cookie->ull_cookie = 0;
4496     tmp_cookie->record_time = 0;
4497     return HI_SUCCESS;
4498 }
4499 
4500 /* ****************************************************************************
4501  函 数 名  : wal_add_cookie_to_array
4502  功能描述  : 添加cookie 到cookie array 中
4503  输入参数  : [1]cookie_array
4504              [2]puc_cookie_bitmap
4505              [3]puc_cookie_idx
4506              [4]pull_cookie
4507  输出参数  : 无
4508  返 回 值  : hi_u32
4509 **************************************************************************** */
4510 hi_u32 wal_add_cookie_to_array(cookie_arry_stru *cookie_array, hi_u8 *puc_cookie_bitmap, const hi_u64 *pull_cookie,
4511     hi_u8 *puc_cookie_idx)
4512 {
4513     hi_u8 idx;
4514     cookie_arry_stru *tmp_cookie = HI_NULL;
4515 
4516     if (*puc_cookie_bitmap == 0xFF) {
4517         /* cookie array 满,返回错误 */
4518         oam_warning_log0(0, OAM_SF_CFG, "{wal_add_cookie_to_array::array full!}\r\n");
4519         return HI_FAIL;
4520     }
4521 
4522     /* 将cookie 添加到array 中 */
4523     idx = oal_bit_get_num_one_byte(*puc_cookie_bitmap);
4524     oal_bit_set_bit_one_byte(puc_cookie_bitmap, idx);
4525 
4526     tmp_cookie = &cookie_array[idx];
4527     tmp_cookie->ull_cookie = *pull_cookie;
4528 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
4529     tmp_cookie->record_time = hi_get_tick();
4530 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
4531     tmp_cookie->record_time = OAL_TIME_JIFFY;
4532 #endif
4533 
4534     *puc_cookie_idx = idx;
4535     return HI_SUCCESS;
4536 }
4537 
4538 /* ****************************************************************************
4539  函 数 名  : wal_check_cookie_from_array
4540  功能描述  : 从cookie array 中查找相应cookie index
4541  输入参数  : [1]puc_cookie_bitmap
4542              [2]cookie_idx
4543  输出参数  : 无
4544  返 回 值  : status hi_u32
4545 **************************************************************************** */
4546 static hi_u32 wal_check_cookie_from_array(const hi_u8 *puc_cookie_bitmap, hi_u8 cookie_idx)
4547 {
4548     /* 从cookie bitmap中查找相应的cookie index,如果位图为0,表示已经被del */
4549     if (*puc_cookie_bitmap & (bit(cookie_idx))) {
4550         return HI_SUCCESS;
4551     }
4552     /* 找不到则返回FAIL */
4553     return HI_FAIL;
4554 }
4555 
4556 /* ****************************************************************************
4557  函 数 名  : wal_mgmt_do_tx
4558  功能描述  : WAL 层发送从wpa_supplicant  接收到的管理帧
4559  输入参数  : oal_net_device_stru    *pst_netdev        发送管理帧设备
4560              mac_mgmt_frame_stru    *pst_mgmt_tx_param 发送管理帧参数
4561  输出参数  : 无
4562  返 回 值  : static hi_u32 HI_SUCCESS 发送成功
4563                                    HI_FAIL 发送失败
4564  调用函数  :
4565  被调函数  :
4566 
4567  修改历史      :
4568   1.日    期   : 2015年8月29日
4569     作    者   : HiSilicon
4570     修改内容   : 新生成函数
4571 
4572 **************************************************************************** */
4573 static hi_u32 wal_mgmt_do_tx(oal_net_device_stru *netdev, const mac_mgmt_frame_stru *mgmt_tx_param,
4574     hi_bool en_offchan, hi_u32 wait)
4575 {
4576     mac_vap_stru                    *mac_vap = HI_NULL;
4577     hmac_vap_stru                   *hmac_vap = HI_NULL;
4578     oal_mgmt_tx_stru                *mgmt_tx = HI_NULL;
4579     hi_u32                           wal_ret;
4580     hi_s32                           i_leftime;
4581 
4582     mac_vap = oal_net_dev_priv(netdev);
4583     if (mac_vap == HI_NULL) {
4584         oam_error_log0(0, OAM_SF_CFG, "{wal_mgmt_do_tx::can't get mac vap from netdevice priv data.}\r\n");
4585         return HI_FAIL;
4586     }
4587 
4588     if (en_offchan == HI_TRUE) {
4589         if (mac_vap->vap_state != MAC_VAP_STATE_STA_LISTEN) {
4590             oam_warning_log1(mac_vap->vap_id, OAM_SF_CFG, "{wal_mgmt_do_tx::pst_mac_vap state[%d]not in listen!}\r\n",
4591                 mac_vap->vap_state);
4592             return HI_INVALID;
4593         }
4594     }
4595 
4596     hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
4597     if (hmac_vap == HI_NULL) {
4598         oam_error_log0(mac_vap->vap_id, OAM_SF_CFG, "{wal_mgmt_do_tx::pst_hmac_vap ptr is null!}\r\n");
4599         return HI_FAIL;
4600     }
4601 
4602     mgmt_tx = &(hmac_vap->mgmt_tx);
4603     mgmt_tx->mgmt_tx_complete = HI_FALSE;
4604     mgmt_tx->mgmt_tx_status = HI_FALSE;
4605 
4606     /* 抛事件给驱动 */
4607     wal_ret = wal_cfg80211_start_req(netdev, mgmt_tx_param, sizeof(mac_mgmt_frame_stru), WLAN_CFGID_CFG80211_MGMT_TX,
4608         HI_FALSE);
4609     if (wal_ret != HI_SUCCESS) {
4610         oam_error_log1(0, OAM_SF_ANY, "{wal_mgmt_do_tx::wal_send_cfg_event return err code:[%d]!}", wal_ret);
4611         return wal_ret;
4612     }
4613 
4614     i_leftime = hi_wait_event_timeout(mgmt_tx->wait_queue, HI_TRUE == mgmt_tx->mgmt_tx_complete,
4615         OAL_MSECS_TO_JIFFIES(wait)); // 使用非wifi目录定义宏函数,误报告警,lin_t e26告警屏蔽
4616     if (i_leftime == 0) {
4617         /* 定时器超时 */
4618         oam_warning_log0(0, OAM_SF_ANY, "{wal_mgmt_do_tx::mgmt tx timeout!}\r\n");
4619         return HI_FAIL;
4620     } else if (i_leftime < 0) {
4621         /* 定时器内部错误 */
4622         oam_warning_log0(0, OAM_SF_ANY, "{wal_mgmt_do_tx::mgmt tx timer error!}\r\n");
4623         return HI_FAIL;
4624     } else {
4625         /* 正常结束  */
4626         oam_info_log0(0, OAM_SF_ANY, "{wal_mgmt_do_tx::mgmt tx commpleted!}\r\n");
4627         return (hi_u32)((mgmt_tx->mgmt_tx_status == HI_FALSE) ? HI_FAIL : HI_SUCCESS);
4628     }
4629 }
4630 
4631 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION)
4632 #ifndef _PRE_HDF_LINUX
4633 static hi_u32 wal_cfg80211_mgmt_tx_parameter_check(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev,
4634     struct cfg80211_mgmt_tx_params *pst_params, hi_u64 *pull_cookie)
4635 {
4636     oal_net_device_stru         *netdev;
4637     oal_ieee80211_channel       *chan = HI_NULL;
4638     const hi_u8                 *puc_buf = HI_NULL;
4639     hi_unref_param(wiphy);
4640 
4641     if (pst_params == HI_NULL) {
4642         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_mgmt_tx_parameter_check::pst_params is null!}\r\n");
4643         return HI_ERR_CODE_PTR_NULL;
4644     }
4645 
4646     chan = pst_params->chan;
4647     puc_buf = pst_params->buf;
4648 
4649     if ((wdev == HI_NULL) || (chan == HI_NULL) || (pull_cookie == HI_NULL) || (puc_buf == HI_NULL)) {
4650         oam_error_log3(0, OAM_SF_CFG,
4651             "{wal_cfg80211_mgmt_tx_parameter_check::wdev or chan or cookie or buf ptr is null, error %p, %p, %p!}\r\n",
4652             (uintptr_t)wdev, (uintptr_t)chan, (uintptr_t)pull_cookie);
4653         return HI_ERR_CODE_PTR_NULL;
4654     }
4655 
4656     netdev = wdev->netdev;
4657     if (netdev == HI_NULL) {
4658         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_mgmt_tx_parameter_check::pst_netdev ptr is null!}\r\n");
4659         return HI_ERR_CODE_PTR_NULL;
4660     }
4661 
4662     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
4663     if (mac_vap == HI_NULL) {
4664         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_mgmt_tx_parameter_check::can't get mac vap fail!}\r\n");
4665         return HI_ERR_CODE_PTR_NULL;
4666     }
4667 
4668     hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
4669     if (hmac_vap == HI_NULL) {
4670         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_mgmt_tx_parameter_check::pst_hmac_vap ptr is null!}\r\n");
4671         return HI_ERR_CODE_PTR_NULL;
4672     }
4673 
4674     return HI_SUCCESS;
4675 }
4676 
4677 /* ****************************************************************************
4678  函 数 名  : wal_cfg80211_mgmt_tx
4679  功能描述  : 发送管理帧
4680 **************************************************************************** */
4681 hi_s32 wal_cfg80211_mgmt_tx(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, oal_cfg80211_mgmt_tx_params_stru *params,
4682     hi_u64 *pull_cookie)
4683 {
4684     mac_device_stru                 *mac_dev = (mac_device_stru *)mac_res_get_dev();
4685     mac_mgmt_frame_stru              mgmt_tx = {0};
4686     hi_u8                            cookie_idx;
4687     hi_u32                           ret;
4688     bool                             en_need_offchan = HI_FALSE;
4689 
4690     if (wal_cfg80211_mgmt_tx_parameter_check(wiphy, wdev, params, pull_cookie) != HI_SUCCESS) {
4691         return -HI_ERR_CODE_PTR_NULL;
4692     }
4693 
4694     oal_wireless_dev *pst_roc_wireless_dev = wdev;
4695     const hi_u8 *puc_buf = params->buf;
4696     hi_u32 len = params->len;
4697     hi_bool en_offchan = params->offchan;
4698     hi_u32 wait = params->wait;
4699 
4700     mac_vap_stru *mac_vap = oal_net_dev_priv(wdev->netdev);
4701 
4702     hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
4703 
4704     mac_p2p_info_stru *p2p_info = &mac_dev->p2p_info;
4705     *pull_cookie = p2p_info->ull_send_action_id++; /* cookie值上层调用需要判断是否是这次的发送导致的callback */
4706     if (*pull_cookie == 0) {
4707         *pull_cookie = p2p_info->ull_send_action_id++;
4708     }
4709     const oal_ieee80211_mgmt *mgmt = (const struct ieee80211_mgmt *)puc_buf;
4710     if (oal_ieee80211_is_probe_resp(mgmt->frame_control)) {
4711         *pull_cookie = 0; /* set cookie default value */
4712         /* host should not send PROE RESPONSE,
4713            device will send immediately when receive probe request packet */
4714 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
4715         HdfWifiEventMgmtTxStatus(wdev->netdev, puc_buf, len, HI_TRUE);
4716 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
4717         oal_cfg80211_mgmt_tx_status(wdev, *pull_cookie, puc_buf, params->len, HI_TRUE, GFP_KERNEL);
4718 #endif
4719         return HI_SUCCESS;
4720     }
4721 
4722     /* 2.1 消息参数准备 */
4723     mgmt_tx.channel = oal_ieee80211_frequency_to_channel(params->chan->center_freq);
4724     if (wal_add_cookie_to_array(g_cookie_array, &g_cookie_array_bitmap, pull_cookie, &cookie_idx) != HI_SUCCESS) {
4725         oam_warning_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_mgmt_tx::Failed to add cookies!}");
4726         return -HI_FAIL;
4727     }
4728     mgmt_tx.mgmt_frame_id = cookie_idx;
4729     mgmt_tx.us_len        = (hi_u16)len;
4730     mgmt_tx.puc_frame     = puc_buf;
4731 
4732     hmac_vap->mgmt_tx.mgmt_tx_complete = HI_FALSE;
4733     hmac_vap->mgmt_tx.mgmt_tx_status   = HI_FALSE;
4734 
4735     switch (mac_vap->vap_mode) {
4736         case WLAN_VAP_MODE_BSS_AP:
4737             oam_info_log3(mac_vap->vap_id, OAM_SF_ANY,
4738                 "{wal_cfg80211_mgmt_tx::p2p mode[%d] (0=Legacy,1=GO,2=Dev,3=Gc), vap ch[%d], mgmt ch [%d]}",
4739                 mac_vap->p2p_mode, mac_vap->channel.idx, mgmt_tx.channel);
4740             if ((mac_vap->channel.idx != mgmt_tx.channel) && is_p2p_go(mac_vap)) {
4741                 if (mac_dev->p2p_info.pst_p2p_net_device == HI_NULL) {
4742                     oam_error_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_mgmt_tx::go mode but p2p dev is null}");
4743                     return -HI_FAIL;
4744                 }
4745                 pst_roc_wireless_dev = oal_netdevice_wdev(mac_dev->p2p_info.pst_p2p_net_device);
4746                 en_need_offchan = HI_TRUE;
4747             }
4748             break;
4749         case WLAN_VAP_MODE_BSS_STA:
4750             if ((en_offchan == HI_TRUE) && (wiphy->flags & WIPHY_FLAG_OFFCHAN_TX)) {
4751                 en_need_offchan = HI_TRUE;
4752             }
4753             if ((mac_vap->p2p_mode == WLAN_LEGACY_VAP_MODE) && (mac_vap->vap_state == MAC_VAP_STATE_UP)) {
4754                 en_need_offchan = HI_FALSE;
4755             }
4756             break;
4757         default:
4758             break;
4759     }
4760 
4761     if ((en_need_offchan == HI_TRUE) && !chan) {
4762         oam_error_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_mgmt_tx::channel is null}\r\n");
4763         return -HI_FAIL;
4764     }
4765 
4766     if (wait == 0) {
4767         wait = WAL_MGMT_TX_TIMEOUT_MSEC;
4768         oam_warning_log1(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_mgmt_tx::wait is 0, set it to %d ms}", wait);
4769     }
4770 
4771     oam_info_log4(mac_vap->vap_id, OAM_SF_CFG,
4772         "{wal_cfg80211_mgmt_tx::offchannel[%d].channel[%d]vap state[%d],wait[%d]}\r\n",
4773         en_need_offchan, mgmt_tx.channel, mac_vap->vap_state, wait);
4774 #ifdef _PRE_WLAN_FEATURE_P2P
4775 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 6, 0))
4776     if (en_need_offchan == HI_TRUE) {
4777         ret = wal_drv_remain_on_channel(wiphy, pst_roc_wireless_dev, chan, wait, pull_cookie,
4778             IEEE80211_ROC_TYPE_MGMT_TX);
4779         if (ret != HI_SUCCESS) {
4780             oam_warning_log4(mac_vap->vap_id, OAM_SF_CFG,
4781                 "{wal_cfg80211_mgmt_tx::wal_drv_remain_on_channel[%d]!!!offchannel[%d].channel[%d],vap state[%d]}\r\n",
4782                 ret, en_need_offchan, mgmt_tx.channel, mac_vap->vap_state);
4783             return -OAL_EBUSY;
4784         }
4785     }
4786 #endif
4787 #endif /* #ifdef _PRE_WLAN_FEATURE_P2P */
4788 
4789     hi_u32 start_time_stamp = OAL_TIME_JIFFY;
4790     hi_u8 retry = 0;
4791     /* 发送失败,则尝试重传 */
4792     do {
4793         ret = wal_mgmt_do_tx(netdev, &mgmt_tx, en_need_offchan, wait);
4794         retry++;
4795     } while ((ret != HI_SUCCESS) && (ret != HI_INVALID) && (retry < = WAL_MGMT_TX_RETRY_CNT) &&
4796         (oal_time_before(start_time_stamp, start_time_stamp + OAL_MSECS_TO_JIFFIES(wait))));
4797 
4798     if (ret != HI_SUCCESS) {
4799         /* 发送失败,处理超时帧的bitmap */
4800         wal_check_cookie_timeout(g_cookie_array, &g_cookie_array_bitmap);
4801 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
4802         HdfWifiEventMgmtTxStatus(wdev->netdev, puc_buf, len, HI_FALSE);
4803 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
4804         oal_cfg80211_mgmt_tx_status(wdev, *pull_cookie, puc_buf, params->len, HI_FALSE, GFP_KERNEL);
4805 #endif
4806     } else {
4807         /* 正常结束  */
4808         *pull_cookie = g_cookie_array[hmac_vap->mgmt_tx.mgmt_frame_id].ull_cookie;
4809         wal_del_cookie_from_array(g_cookie_array, &g_cookie_array_bitmap, hmac_vap->mgmt_tx.mgmt_frame_id);
4810 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION)
4811         HdfWifiEventMgmtTxStatus(wdev->netdev, puc_buf, len, HI_FALSE);
4812 #elif (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
4813         oal_cfg80211_mgmt_tx_status(wdev, *pull_cookie, puc_buf, params->len, HI_FALSE, GFP_KERNEL);
4814 #endif
4815     }
4816 
4817     return HI_SUCCESS;
4818 }
4819 #endif /* ifndef _PRE_HDF_LINUX */
4820 
4821 #else
4822 static hi_u32 wal_cfg80211_mgmt_tx_parameter_check(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev,
4823     oal_ieee80211_channel *chan, const hi_u8 *puc_buf, hi_u64 *pull_cookie)
4824 {
4825     oal_net_device_stru *netdev;
4826     hi_unref_param(wiphy);
4827     if ((wdev == HI_NULL) || (chan == HI_NULL) || (pull_cookie == HI_NULL) || (puc_buf == HI_NULL)) {
4828         oam_error_log3(0, OAM_SF_CFG,
4829             "{wal_cfg80211_mgmt_tx_parameter_check::wdev or chan or cookie or buf ptr is null, error %p, %p, %p!}\r\n",
4830             (uintptr_t)wdev, (uintptr_t)chan, (uintptr_t)pull_cookie);
4831         return HI_ERR_CODE_PTR_NULL;
4832     }
4833 
4834     netdev = wdev->netdev;
4835     if (netdev == HI_NULL) {
4836         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_mgmt_tx_parameter_check::pst_netdev ptr is null!}\r\n");
4837         return HI_ERR_CODE_PTR_NULL;
4838     }
4839 
4840     mac_vap_stru *mac_vap = oal_net_dev_priv(netdev);
4841     if (mac_vap == HI_NULL) {
4842         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_mgmt_tx_parameter_check::can't get mac vap fail!}\r\n");
4843         return HI_ERR_CODE_PTR_NULL;
4844     }
4845 
4846     hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
4847     if (hmac_vap == HI_NULL) {
4848         oam_error_log0(0, OAM_SF_CFG, "{wal_cfg80211_mgmt_tx_parameter_check::pst_hmac_vap ptr is null!}\r\n");
4849         return HI_ERR_CODE_PTR_NULL;
4850     }
4851 
4852     return HI_SUCCESS;
4853 }
4854 
4855 /* ****************************************************************************
4856  函 数 名  : wal_cfg80211_mgmt_tx
4857  功能描述  : 发送管理帧
4858 **************************************************************************** */
4859 hi_u32 wal_cfg80211_mgmt_tx(oal_wiphy_stru *wiphy, oal_wireless_dev *wdev, oal_ieee80211_channel *chan,
4860     const hi_u8 *puc_buf, hi_u32 len, hi_u64 *pull_cookie)
4861 {
4862     mac_device_stru                 *mac_dev = (mac_device_stru *)mac_res_get_dev();
4863     mac_mgmt_frame_stru              mgmt_tx = {0};
4864     hi_u8                            cookie_idx;
4865     hi_u32                           ret;
4866 
4867     if (wal_cfg80211_mgmt_tx_parameter_check(wiphy, wdev, chan, puc_buf, pull_cookie) != HI_SUCCESS) {
4868         return HI_ERR_CODE_PTR_NULL;
4869     }
4870 
4871     mac_vap_stru *mac_vap = oal_net_dev_priv(wdev->netdev);
4872     hmac_vap_stru *hmac_vap = hmac_vap_get_vap_stru(mac_vap->vap_id);
4873     if (hmac_vap == HI_NULL) {
4874         return HI_ERR_CODE_PTR_NULL;
4875     }
4876 
4877     mac_p2p_info_stru *p2p_info = &mac_dev->p2p_info;
4878     *pull_cookie = p2p_info->ull_send_action_id++; /* cookie值上层调用需要判断是否是这次的发送导致的callback */
4879     if (*pull_cookie == 0) {
4880         *pull_cookie = p2p_info->ull_send_action_id++;
4881     }
4882     const oal_ieee80211_mgmt *mgmt = (const struct ieee80211_mgmt *)puc_buf;
4883     if (oal_ieee80211_is_probe_resp(mgmt->frame_control) == HI_TRUE) {
4884         *pull_cookie = 0; /* set cookie default value */
4885         /* host should not send PROE RESPONSE,
4886            device will send immediately when receive probe request packet */
4887         HdfWifiEventMgmtTxStatus(wdev->netdev, puc_buf, len, HI_TRUE);
4888         return HI_SUCCESS;
4889     }
4890 
4891     /* 2.1 消息参数准备 */
4892     mgmt_tx.channel = oal_ieee80211_frequency_to_channel(chan->center_freq);
4893     if (wal_add_cookie_to_array(g_cookie_array, &g_cookie_array_bitmap, pull_cookie, &cookie_idx) != HI_SUCCESS) {
4894         oam_warning_log0(mac_vap->vap_id, OAM_SF_ANY, "{wal_cfg80211_mgmt_tx::Failed to add cookies!}\r\n");
4895         return HI_FAIL;
4896     }
4897     mgmt_tx.mgmt_frame_id = cookie_idx;
4898     mgmt_tx.us_len        = (hi_u16)len;
4899     mgmt_tx.puc_frame     = puc_buf;
4900 
4901     hmac_vap->mgmt_tx.mgmt_tx_complete = HI_FALSE;
4902     hmac_vap->mgmt_tx.mgmt_tx_status = HI_FALSE;
4903 
4904     hi_u32 start_time_stamp = hi_get_tick();
4905 
4906     hi_u32 end_time_stamp = start_time_stamp + 2 * WAL_MGMT_TX_TIMEOUT_MSEC / HI_MILLISECOND_PER_TICK; /* 2: 比例系数 */
4907     /* 发送失败,则尝试重传 */
4908     do {
4909         ret = wal_mgmt_do_tx(wdev->netdev, &mgmt_tx, 0, WAL_MGMT_TX_TIMEOUT_MSEC / HI_MILLISECOND_PER_TICK);
4910     } while ((ret != HI_SUCCESS) && (hi_get_tick() < end_time_stamp));
4911 
4912     if (ret != HI_SUCCESS) {
4913         /* 发送失败,处理超时帧的bitmap */
4914         wal_check_cookie_timeout(g_cookie_array, &g_cookie_array_bitmap);
4915     } else {
4916         /* 正常结束  */
4917         *pull_cookie = g_cookie_array[hmac_vap->mgmt_tx.mgmt_frame_id].ull_cookie;
4918         wal_del_cookie_from_array(g_cookie_array, &g_cookie_array_bitmap, hmac_vap->mgmt_tx.mgmt_frame_id);
4919     }
4920     HdfWifiEventMgmtTxStatus(wdev->netdev, puc_buf, len, ((ret != HI_SUCCESS) ? HI_FALSE : HI_TRUE));
4921 
4922     return HI_SUCCESS;
4923 }
4924 #endif
4925 
4926 /* ****************************************************************************
4927  函 数 名  : wal_cfg80211_mgmt_tx_status
4928  功能描述  : HMAC抛mgmt tx status到WAL, 唤醒wait queue
4929 **************************************************************************** */
4930 /* g_ast_wal_host_ctx_table数组成员,需要修改结构体frw_event_sub_table_item_stru进而需要修改
4931    g_ast_dmac_host_crx_table数组的成员,其中dmac_cfg_vap_init_event对变量进行了修改,lint_t e818告警屏蔽 */
4932 hi_u32 wal_cfg80211_mgmt_tx_status(frw_event_mem_stru *event_mem)
4933 {
4934     frw_event_stru                  *event = HI_NULL;
4935     dmac_crx_mgmt_tx_status_stru    *mgmt_tx_status_param = HI_NULL;
4936     hmac_vap_stru                   *hmac_vap = HI_NULL;
4937     oal_mgmt_tx_stru                *mgmt_tx = HI_NULL;
4938 
4939     if (oal_unlikely(event_mem == HI_NULL)) {
4940         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_mgmt_tx_status::event_mem is null!}\r\n");
4941         return HI_ERR_CODE_PTR_NULL;
4942     }
4943 
4944     event = (frw_event_stru *)event_mem->puc_data;
4945     hmac_vap = hmac_vap_get_vap_stru(event->event_hdr.vap_id);
4946     if (hmac_vap == HI_NULL) {
4947         oam_error_log1(0, OAM_SF_TX, "{wal_cfg80211_mgmt_tx_status::pst_hmac_vap null.vap_id[%d]}",
4948             event->event_hdr.vap_id);
4949         return HI_ERR_CODE_PTR_NULL;
4950     }
4951 
4952     mgmt_tx_status_param = (dmac_crx_mgmt_tx_status_stru *)(event->auc_event_data);
4953     mgmt_tx = &(hmac_vap->mgmt_tx);
4954     mgmt_tx->mgmt_tx_complete = HI_TRUE;
4955     mgmt_tx->mgmt_tx_status   = mgmt_tx_status_param->tx_status;
4956     mgmt_tx->mgmt_frame_id    = mgmt_tx_status_param->mgmt_frame_id;
4957 
4958     /* 找不到相应的cookie值,说明已经超时被处理,不需要再唤醒 */
4959     if (HI_SUCCESS == wal_check_cookie_from_array(&g_cookie_array_bitmap, mgmt_tx->mgmt_frame_id)) {
4960         /* 让编译器优化时保证HI_WAIT_QUEUE_WAKE_UP在最后执行 */
4961         oal_smp_mb();
4962         hi_wait_queue_wake_up(&mgmt_tx->wait_queue);
4963     }
4964 
4965     return HI_SUCCESS;
4966 }
4967 
4968 /* ****************************************************************************
4969  函 数 名  : wal_cfg80211_start_req
4970  功能描述  : 向wal抛事件
4971  输入参数  : 无
4972  输出参数  : 无
4973  返 回 值  :
4974  调用函数  :
4975  被调函数  :
4976 
4977  修改历史      :
4978   1.日    期   : 2014年1月4日
4979     作    者   : HiSilicon
4980     修改内容   : 新生成函数
4981 
4982 **************************************************************************** */
4983 hi_u32 wal_cfg80211_start_req(oal_net_device_stru *netdev, const hi_void *ps_param, hi_u16 us_len,
4984     wlan_cfgid_enum_uint16 wid, hi_u8 need_rsp)
4985 {
4986     wal_msg_write_stru              write_msg;
4987     wal_msg_stru                   *rsp_msg = HI_NULL;
4988     hi_u32                          ret;
4989 
4990     if (ps_param == HI_NULL) {
4991         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_start_req::param is null!}\r\n");
4992         return HI_ERR_CODE_PTR_NULL;
4993     }
4994 
4995     /* 填写 msg 消息头 */
4996     write_msg.wid = wid;
4997     write_msg.us_len = us_len;
4998 
4999     /* 填写 msg 消息体 */
5000     if (us_len > WAL_MSG_WRITE_MAX_LEN) {
5001         oam_error_log2(0, OAM_SF_SCAN, "{wal_cfg80211_start_req::us_len %d > WAL_MSG_WRITE_MAX_LEN %d err!}\r\n",
5002             us_len, WAL_MSG_WRITE_MAX_LEN);
5003         return HI_ERR_CODE_INVALID_CONFIG;
5004     }
5005 
5006     if (memcpy_s(write_msg.auc_value, sizeof(write_msg.auc_value), ps_param, us_len) != EOK) {
5007         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_start_req::mem safe function err!}");
5008         return HI_FAIL;
5009     }
5010     /* **************************************************************************
5011            抛事件到wal层处理
5012     ************************************************************************** */
5013     ret = wal_send_cfg_event(netdev, WAL_MSG_TYPE_WRITE, WAL_MSG_WRITE_MSG_HDR_LENGTH + us_len, (hi_u8 *)&write_msg,
5014         need_rsp, need_rsp ? &rsp_msg : HI_NULL);
5015     if (oal_unlikely(ret != HI_SUCCESS)) {
5016         oam_warning_log1(0, OAM_SF_SCAN, "{wal_cfg80211_start_req::wal_send_cfg_event return err code %u!}\r\n", ret);
5017         return ret;
5018     }
5019     if (need_rsp && (rsp_msg != HI_NULL)) {
5020         /* 读取返回的错误码 */
5021         ret = wal_check_and_release_msg_resp(rsp_msg);
5022         if (ret != HI_SUCCESS) {
5023             oam_warning_log1(0, OAM_SF_SCAN, "{wal_cfg80211_start_req::wal_send_cfg_event return err code:[%u]}", ret);
5024             return ret;
5025         }
5026     }
5027 
5028     return HI_SUCCESS;
5029 }
5030 
5031 /* ****************************************************************************
5032  函 数 名  : wal_cfg80211_start_scan
5033  功能描述  :
5034  输入参数  : 无
5035  输出参数  : 无
5036  返 回 值  :
5037  调用函数  :
5038  被调函数  :
5039 
5040  修改历史      :
5041   1.日    期   : 2013年8月30日
5042     作    者   : HiSilicon
5043     修改内容   : 新生成函数
5044 
5045   2.日    期   : 2014年1月4日
5046     作    者   : HiSilicon
5047     修改内容   : 重构
5048 
5049 **************************************************************************** */
5050 hi_u32 wal_cfg80211_start_scan(oal_net_device_stru *netdev, const mac_cfg80211_scan_param_stru *scan_param)
5051 {
5052     mac_cfg80211_scan_param_stru    *mac_cfg80211_scan_param = HI_NULL;
5053     hi_u32                           ret;
5054 
5055     if (scan_param == HI_NULL) {
5056         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_start_scan::scan failed, null ptr, pst_scan_param = null.}\r\n");
5057         return HI_ERR_CODE_PTR_NULL;
5058     }
5059 
5060     /* 此处申请hmac层释放 */
5061     mac_cfg80211_scan_param =
5062         (mac_cfg80211_scan_param_stru *)oal_mem_alloc(OAL_MEM_POOL_ID_LOCAL, sizeof(mac_cfg80211_scan_param_stru));
5063     if (mac_cfg80211_scan_param == NULL) {
5064         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_start_scan::scan failed, alloc scan param memory failed!}\r\n");
5065         return HI_ERR_CODE_PTR_NULL;
5066     }
5067 
5068     if (memcpy_s(mac_cfg80211_scan_param, sizeof(mac_cfg80211_scan_param_stru), scan_param,
5069         sizeof(mac_cfg80211_scan_param_stru)) != EOK) {
5070         oal_mem_free(mac_cfg80211_scan_param);
5071         oam_error_log0(0, OAM_SF_SCAN, "{wal_cfg80211_start_scan::mem safe function err!}");
5072         return HI_FAIL;
5073     }
5074 
5075     /* 1.传的是指针的指针, 2.sizeof指针  */
5076     ret = wal_cfg80211_start_req(netdev, &mac_cfg80211_scan_param, sizeof(uintptr_t), WLAN_CFGID_CFG80211_START_SCAN,
5077         HI_FALSE);
5078     if (ret != HI_SUCCESS) {
5079         /* 下发扫描失败,释放 */
5080         oal_mem_free(mac_cfg80211_scan_param);
5081         return ret;
5082     }
5083 
5084     return HI_SUCCESS;
5085 }
5086 
5087 /* ****************************************************************************
5088  函 数 名  : wal_cfg80211_reset_bands
5089  功能描述  : 重新初始化wifi wiphy的bands
5090  输入参数  : 无
5091  输出参数  : 无
5092  返 回 值  :
5093  调用函数  :
5094  被调函数  :
5095 
5096  修改历史      :
5097   1.日    期   : 2015年12月25日
5098     作    者   : HiSilicon
5099     修改内容   : 新生成函数
5100 
5101 **************************************************************************** */
5102 hi_void wal_cfg80211_reset_bands(hi_void)
5103 {
5104     hi_s32 i;
5105 
5106     /* 每次更新国家码,flags都会被修改,且上次修改的值不会被清除,相当于每次修改的国家码都会生效,
5107        因此更新国家需要清除flag标志 */
5108     for (i = 0; i < g_wifi_band_2ghz.n_channels; i++) {
5109         g_wifi_band_2ghz.channels[i].flags = 0;
5110     }
5111 }
5112 
5113 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
5114 /* 不同操作系统函数指针结构体方式不同 */
5115 static oal_cfg80211_ops_stru g_wal_cfg80211_ops =
5116 {
5117     .scan                     = wal_cfg80211_scan,
5118     .connect                  = wal_cfg80211_connect,
5119     .disconnect               = wal_cfg80211_disconnect,
5120     .add_key                  = wal_cfg80211_add_key,
5121     .get_key                  = wal_cfg80211_get_key,
5122     .del_key                  = wal_cfg80211_remove_key,
5123     .set_default_key          = wal_cfg80211_set_default_key,
5124     .set_default_mgmt_key     = wal_cfg80211_set_default_mgmt_key,
5125     .set_wiphy_params         = wal_cfg80211_set_wiphy_params,
5126 /* Hi1131 修改AP 配置接口 */
5127     .change_beacon            = wal_cfg80211_change_beacon,
5128     .start_ap                 = wal_cfg80211_start_ap,
5129     .stop_ap                  = wal_cfg80211_stop_ap,
5130     .change_bss               = wal_cfg80211_change_bss,
5131     .sched_scan_start         = wal_cfg80211_sched_scan_start,
5132     .sched_scan_stop          = wal_cfg80211_sched_scan_stop,
5133     .change_virtual_intf      = wal_cfg80211_change_virtual_intf,
5134     .add_station              = wal_cfg80211_add_station,
5135     .del_station              = wal_cfg80211_del_station,
5136     .change_station           = wal_cfg80211_change_station,
5137     .get_station              = wal_cfg80211_get_station,
5138     .dump_station             = wal_cfg80211_dump_station,
5139 #ifdef _PRE_WLAN_FEATURE_P2P
5140     .remain_on_channel        = wal_cfg80211_remain_on_channel,
5141     .cancel_remain_on_channel = wal_cfg80211_cancel_remain_on_channel,
5142 #endif
5143     .mgmt_tx                  = wal_cfg80211_mgmt_tx,
5144     .mgmt_frame_register      = wal_cfg80211_mgmt_frame_register,
5145     .set_bitrate_mask         = wal_cfg80211_set_bitrate_mask,
5146     .add_virtual_intf         = wal_cfg80211_add_virtual_intf,
5147     .del_virtual_intf         = wal_cfg80211_del_virtual_intf,
5148     .mgmt_tx_cancel_wait      = wal_cfg80211_mgmt_tx_cancel_wait,
5149     .start_p2p_device         = wal_cfg80211_start_p2p_device,
5150     .stop_p2p_device          = wal_cfg80211_stop_p2p_device,
5151     .set_power_mgmt           = wal_cfg80211_set_power_mgmt,
5152 #if (LINUX_VERSION_CODE >= kernel_version(4,1,0))
5153     .abort_scan               = wal_cfg80211_abort_scan,
5154 #endif /* (LINUX_VERSION_CODE >= kernel_version(4,1,0)) */
5155 };
5156 #endif /* #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX) */
5157 
5158 wal_wifi_mode_enum_int wal_get_vap_mode(hi_void)
5159 {
5160     return g_mode;
5161 }
5162 
5163 wal_wifi_bw_enum_int wal_get_bw_type(hi_void)
5164 {
5165     return g_bw;
5166 }
5167 
5168 wal_phy_mode wal_get_protocol_type(hi_void)
5169 {
5170     return g_proto;
5171 }
5172 
5173 /* ****************************************************************************
5174  功能描述  : wal_linux_cfg80211加载初始化
5175  修改历史      :
5176   1.日    期   : 2013年8月28日
5177     作    者   : HiSilicon
5178     修改内容   : 新生成函数
5179 **************************************************************************** */
5180 hi_u32 wal_cfg80211_init(hi_void)
5181 {
5182     /* 单device下直接获取dev进行初始化 */
5183     mac_device_stru *mac_dev = mac_res_get_dev();
5184 #if (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION) || defined(_PRE_HDF_LINUX)
5185     mac_dev->wiphy = oal_wiphy_new(sizeof(mac_wiphy_priv_stru));
5186 #else
5187     mac_dev->wiphy = oal_wiphy_new(&g_wal_cfg80211_ops, sizeof(mac_wiphy_priv_stru));
5188 #endif
5189     if (mac_dev->wiphy == HI_NULL) {
5190         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_init::oal_wiphy_new failed!}");
5191         return HI_FAIL;
5192     }
5193 
5194     /* 初始化wiphy 结构体内容 */
5195     oal_wiphy_stru *wiphy = mac_dev->wiphy;
5196 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
5197 #ifdef _PRE_WLAN_FEATURE_P2P
5198     wiphy->iface_combinations   = g_sta_p2p_iface_combinations;
5199     wiphy->n_iface_combinations = hi_array_size(g_sta_p2p_iface_combinations);
5200     wiphy->mgmt_stypes          = g_wal_cfg80211_default_mgmt_stypes;
5201     wiphy->max_remain_on_channel_duration = 5000; /* 5000: 最大的时间间隔 */
5202     /* 使能驱动监听 */
5203     wiphy->flags |= WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL | WIPHY_FLAG_OFFCHAN_TX;
5204     wiphy->flags |= WIPHY_FLAG_HAVE_AP_SME;
5205     /* 1131注册支持pno调度扫描能力相关信息 */
5206     wiphy->max_sched_scan_ssids  = MAX_PNO_SSID_COUNT;
5207     wiphy->max_match_sets        = MAX_PNO_SSID_COUNT;
5208     wiphy->max_sched_scan_ie_len = WAL_MAX_SCAN_IE_LEN;
5209     wiphy->flags |= WIPHY_FLAG_SUPPORTS_SCHED_SCAN;
5210 #endif
5211 #ifdef _PRE_WLAN_FEATURE_P2P
5212     wiphy->interface_modes = bit(NL80211_IFTYPE_STATION) | bit(NL80211_IFTYPE_AP) | bit(NL80211_IFTYPE_P2P_CLIENT) |
5213         bit(NL80211_IFTYPE_P2P_GO);
5214 #else
5215     wiphy->interface_modes = bit(NL80211_IFTYPE_STATION) | bit(NL80211_IFTYPE_AP);
5216 #endif
5217 
5218 #ifdef _PRE_WLAN_FEATURE_MESH
5219     wiphy->interface_modes |= bit(NL80211_IFTYPE_MESH_POINT);
5220 #endif
5221     wiphy->max_scan_ssids = WLAN_SCAN_REQ_MAX_BSS;
5222     wiphy->max_scan_ie_len = WAL_MAX_SCAN_IE_LEN;
5223     wiphy->cipher_suites = g_wifi_cipher_suites;
5224     wiphy->n_cipher_suites = sizeof(g_wifi_cipher_suites) / sizeof(hi_u32);
5225 
5226     /* 不使能节能 */
5227     wiphy->flags &= ~WIPHY_FLAG_PS_ON_BY_DEFAULT;
5228     /* linux 3.14 版本升级,管制域重新修改 */
5229     wiphy->regulatory_flags |= REGULATORY_CUSTOM_REG;
5230     wiphy->signal_type       = CFG80211_SIGNAL_TYPE_MBM;
5231 #endif
5232     wiphy->bands[IEEE80211_BAND_2GHZ] = &g_wifi_band_2ghz; /* 支持的频带信息 2.4G */
5233 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
5234     oal_wiphy_apply_custom_regulatory(wiphy, wal_get_cfg_regdb());
5235     err_code = oal_wiphy_register(wiphy);
5236     if (err_code != 0) {
5237         oal_wiphy_free(mac_dev->wiphy);
5238         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_init::oal_wiphy_register failed!}\r\n");
5239         return (hi_u32)err_code;
5240     }
5241 #elif (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION) || defined(_PRE_HDF_LINUX)
5242     oal_wiphy_apply_custom_regulatory();
5243     oal_wiphy_register(wiphy);
5244 #endif
5245 
5246     /* P2P add_virtual_intf 传入wiphy 参数,在wiphy priv 指针保存wifi 驱动mac_devie_stru 结构指针 */
5247     mac_wiphy_priv_stru *wiphy_priv = (mac_wiphy_priv_stru *)(oal_wiphy_priv(wiphy));
5248     wiphy_priv->mac_device = mac_dev;
5249 
5250     return HI_SUCCESS;
5251 }
5252 
5253 /* ****************************************************************************
5254  功能描述  : 卸载wihpy
5255  修改历史      :
5256   1.日    期   : 2013年9月5日
5257     作    者   : HiSilicon
5258     修改内容   : 新生成函数
5259 **************************************************************************** */
5260 hi_void wal_cfg80211_exit(hi_void)
5261 {
5262     mac_device_stru *mac_dev = HI_NULL;
5263 
5264     /* 单device下直接获取dev进行去初始化 */
5265     mac_dev = mac_res_get_dev();
5266     /* 注销注册 wiphy device */
5267 #if (_PRE_OS_VERSION_LINUX == _PRE_OS_VERSION) && !defined(_PRE_HDF_LINUX)
5268     oal_wiphy_unregister(mac_dev->wiphy);
5269 #elif (_PRE_OS_VERSION_LITEOS == _PRE_OS_VERSION) || defined(_PRE_HDF_LINUX)
5270     oal_wiphy_unregister();
5271 #endif
5272     /* 卸载wiphy device */
5273     oal_wiphy_free(mac_dev->wiphy);
5274     return;
5275 }
5276 
5277 #ifdef _PRE_WLAN_FEATURE_REKEY_OFFLOAD
5278 /* ****************************************************************************
5279  函 数 名  : wal_cfg80211_set_rekey_info
5280  功能描述  : 上层下发的rekey info,抛给wal层处理
5281  输入参数  : oal_net_device_stru      *pst_net_dev,
5282              mac_rekey_offload_stru   *pst_rekey_offload
5283  输出参数  : 无
5284  返 回 值  : HI_SUCCESS或其它错误码
5285  调用函数  :
5286  被调函数  :
5287 
5288  修改历史      :
5289   1.日    期   : 2016年8月2日
5290     作    者   : HiSilicon
5291     修改内容   : 新生成函数
5292 
5293 **************************************************************************** */
5294 hi_u32 wal_cfg80211_set_rekey_info(oal_net_device_stru *netdev, mac_rekey_offload_stru *rekey_offload)
5295 {
5296     mac_rekey_offload_stru rekey_params;
5297     hi_u32 ret;
5298 
5299     /* 1 参数合法性检查 */
5300     if ((netdev == HI_NULL) || (rekey_offload == HI_NULL)) {
5301         oam_error_log2(0, OAM_SF_ANY, "{wal_cfg80211_set_rekey_info::pst_net_dev = %p, pst_rekey_offload = %p!}",
5302             (uintptr_t)netdev, (uintptr_t)rekey_offload);
5303         return HI_ERR_CODE_PTR_NULL;
5304     }
5305 
5306     /* 2 消息参数准备 */
5307     if (memcpy_s(&rekey_params, sizeof(mac_rekey_offload_stru),
5308         rekey_offload, sizeof(mac_rekey_offload_stru)) != EOK) {
5309         oam_error_log0(0, OAM_SF_ANY, "{wal_cfg80211_set_rekey_info::mem safe function err!}");
5310         return HI_FAIL;
5311     }
5312 
5313     /* 抛事件给驱动 */
5314     ret = wal_cfg80211_start_req(netdev, &rekey_params, sizeof(mac_rekey_offload_stru), WLAN_CFGID_SET_REKEY, HI_TRUE);
5315     if (ret != HI_SUCCESS) {
5316         oam_error_log1(0, OAM_SF_ANY, "{wal_cfg80211_set_rekey_info::wal_send_cfg_event return err code:[%d]!}", ret);
5317         return HI_FAIL;
5318     }
5319 
5320     return HI_SUCCESS;
5321 }
5322 #endif /* _PRE_WLAN_FEATURE_REKEY_OFFLOAD */
5323 
5324 #ifdef __cplusplus
5325 #if __cplusplus
5326 }
5327 #endif
5328 #endif
5329