1 /*
2 * Copyright (c) 2010 Broadcom Corporation
3 *
4 * Permission to use, copy, modify, and/or distribute this software for any
5 * purpose with or without fee is hereby granted, provided that the above
6 * copyright notice and this permission notice appear in all copies.
7 *
8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
11 * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
13 * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
14 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15 */
16
17 #include <linux/kernel.h>
18 #include <linux/if_arp.h>
19
20 #include <bcmutils.h>
21
22 #include <asm/uaccess.h>
23
24 #include <dngl_stats.h>
25 #include <dhd.h>
26 #include <dhdioctl.h>
27 #include <wlioctl.h>
28
29 #include <linux/kthread.h>
30 #include <linux/netdevice.h>
31 #include <linux/sched.h>
32 #include <linux/etherdevice.h>
33 #include <linux/wireless.h>
34 #include <linux/ieee80211.h>
35 #include <net/cfg80211.h>
36
37 #include <net/rtnetlink.h>
38 #include <linux/mmc/sdio_func.h>
39 #include <linux/firmware.h>
40 #include <wl_cfg80211.h>
41
42 static struct sdio_func *cfg80211_sdio_func;
43 static struct wl_dev *wl_cfg80211_dev;
44 static const u8 ether_bcast[ETH_ALEN] = {255, 255, 255, 255, 255, 255};
45
46 u32 wl_dbg_level = WL_DBG_ERR | WL_DBG_INFO;
47
48 #define WL_4329_FW_FILE "brcm/bcm4329-fullmac-4.bin"
49 #define WL_4329_NVRAM_FILE "brcm/bcm4329-fullmac-4.txt"
50
51 /*
52 ** cfg80211_ops api/callback list
53 */
54 static s32 wl_cfg80211_change_iface(struct wiphy *wiphy,
55 struct net_device *ndev,
56 enum nl80211_iftype type, u32 *flags,
57 struct vif_params *params);
58 static s32 __wl_cfg80211_scan(struct wiphy *wiphy, struct net_device *ndev,
59 struct cfg80211_scan_request *request,
60 struct cfg80211_ssid *this_ssid);
61 static s32 wl_cfg80211_scan(struct wiphy *wiphy, struct net_device *ndev,
62 struct cfg80211_scan_request *request);
63 static s32 wl_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed);
64 static s32 wl_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev,
65 struct cfg80211_ibss_params *params);
66 static s32 wl_cfg80211_leave_ibss(struct wiphy *wiphy,
67 struct net_device *dev);
68 static s32 wl_cfg80211_get_station(struct wiphy *wiphy,
69 struct net_device *dev, u8 *mac,
70 struct station_info *sinfo);
71 static s32 wl_cfg80211_set_power_mgmt(struct wiphy *wiphy,
72 struct net_device *dev, bool enabled,
73 s32 timeout);
74 static s32 wl_cfg80211_set_bitrate_mask(struct wiphy *wiphy,
75 struct net_device *dev,
76 const u8 *addr,
77 const struct cfg80211_bitrate_mask
78 *mask);
79 static int wl_cfg80211_connect(struct wiphy *wiphy, struct net_device *dev,
80 struct cfg80211_connect_params *sme);
81 static s32 wl_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *dev,
82 u16 reason_code);
83 static s32 wl_cfg80211_set_tx_power(struct wiphy *wiphy,
84 enum nl80211_tx_power_setting type,
85 s32 dbm);
86 static s32 wl_cfg80211_get_tx_power(struct wiphy *wiphy, s32 *dbm);
87 static s32 wl_cfg80211_config_default_key(struct wiphy *wiphy,
88 struct net_device *dev, u8 key_idx,
89 bool unicast, bool multicast);
90 static s32 wl_cfg80211_add_key(struct wiphy *wiphy, struct net_device *dev,
91 u8 key_idx, bool pairwise, const u8 *mac_addr,
92 struct key_params *params);
93 static s32 wl_cfg80211_del_key(struct wiphy *wiphy, struct net_device *dev,
94 u8 key_idx, bool pairwise, const u8 *mac_addr);
95 static s32 wl_cfg80211_get_key(struct wiphy *wiphy, struct net_device *dev,
96 u8 key_idx, bool pairwise, const u8 *mac_addr,
97 void *cookie, void (*callback) (void *cookie,
98 struct
99 key_params *
100 params));
101 static s32 wl_cfg80211_config_default_mgmt_key(struct wiphy *wiphy,
102 struct net_device *dev,
103 u8 key_idx);
104 static s32 wl_cfg80211_resume(struct wiphy *wiphy);
105 static s32 wl_cfg80211_suspend(struct wiphy *wiphy);
106 static s32 wl_cfg80211_set_pmksa(struct wiphy *wiphy, struct net_device *dev,
107 struct cfg80211_pmksa *pmksa);
108 static s32 wl_cfg80211_del_pmksa(struct wiphy *wiphy, struct net_device *dev,
109 struct cfg80211_pmksa *pmksa);
110 static s32 wl_cfg80211_flush_pmksa(struct wiphy *wiphy,
111 struct net_device *dev);
112 /*
113 ** event & event Q handlers for cfg80211 interfaces
114 */
115 static s32 wl_create_event_handler(struct wl_priv *wl);
116 static void wl_destroy_event_handler(struct wl_priv *wl);
117 static s32 wl_event_handler(void *data);
118 static void wl_init_eq(struct wl_priv *wl);
119 static void wl_flush_eq(struct wl_priv *wl);
120 static void wl_lock_eq(struct wl_priv *wl);
121 static void wl_unlock_eq(struct wl_priv *wl);
122 static void wl_init_eq_lock(struct wl_priv *wl);
123 static void wl_init_eloop_handler(struct wl_event_loop *el);
124 static struct wl_event_q *wl_deq_event(struct wl_priv *wl);
125 static s32 wl_enq_event(struct wl_priv *wl, u32 type,
126 const wl_event_msg_t *msg, void *data);
127 static void wl_put_event(struct wl_event_q *e);
128 static void wl_wakeup_event(struct wl_priv *wl);
129 static s32 wl_notify_connect_status(struct wl_priv *wl,
130 struct net_device *ndev,
131 const wl_event_msg_t *e, void *data);
132 static s32 wl_notify_roaming_status(struct wl_priv *wl,
133 struct net_device *ndev,
134 const wl_event_msg_t *e, void *data);
135 static s32 wl_notify_scan_status(struct wl_priv *wl, struct net_device *ndev,
136 const wl_event_msg_t *e, void *data);
137 static s32 wl_bss_connect_done(struct wl_priv *wl, struct net_device *ndev,
138 const wl_event_msg_t *e, void *data,
139 bool completed);
140 static s32 wl_bss_roaming_done(struct wl_priv *wl, struct net_device *ndev,
141 const wl_event_msg_t *e, void *data);
142 static s32 wl_notify_mic_status(struct wl_priv *wl, struct net_device *ndev,
143 const wl_event_msg_t *e, void *data);
144
145 /*
146 ** register/deregister sdio function
147 */
148 struct sdio_func *wl_cfg80211_get_sdio_func(void);
149 static void wl_clear_sdio_func(void);
150
151 /*
152 ** ioctl utilites
153 */
154 static s32 wl_dev_bufvar_get(struct net_device *dev, s8 *name, s8 *buf,
155 s32 buf_len);
156 static __used s32 wl_dev_bufvar_set(struct net_device *dev, s8 *name,
157 s8 *buf, s32 len);
158 static s32 wl_dev_intvar_set(struct net_device *dev, s8 *name, s32 val);
159 static s32 wl_dev_intvar_get(struct net_device *dev, s8 *name,
160 s32 *retval);
161 static s32 wl_dev_ioctl(struct net_device *dev, u32 cmd, void *arg,
162 u32 len);
163
164 /*
165 ** cfg80211 set_wiphy_params utilities
166 */
167 static s32 wl_set_frag(struct net_device *dev, u32 frag_threshold);
168 static s32 wl_set_rts(struct net_device *dev, u32 frag_threshold);
169 static s32 wl_set_retry(struct net_device *dev, u32 retry, bool l);
170
171 /*
172 ** wl profile utilities
173 */
174 static s32 wl_update_prof(struct wl_priv *wl, const wl_event_msg_t *e,
175 void *data, s32 item);
176 static void *wl_read_prof(struct wl_priv *wl, s32 item);
177 static void wl_init_prof(struct wl_profile *prof);
178
179 /*
180 ** cfg80211 connect utilites
181 */
182 static s32 wl_set_wpa_version(struct net_device *dev,
183 struct cfg80211_connect_params *sme);
184 static s32 wl_set_auth_type(struct net_device *dev,
185 struct cfg80211_connect_params *sme);
186 static s32 wl_set_set_cipher(struct net_device *dev,
187 struct cfg80211_connect_params *sme);
188 static s32 wl_set_key_mgmt(struct net_device *dev,
189 struct cfg80211_connect_params *sme);
190 static s32 wl_set_set_sharedkey(struct net_device *dev,
191 struct cfg80211_connect_params *sme);
192 static s32 wl_get_assoc_ies(struct wl_priv *wl);
193 static void wl_ch_to_chanspec(int ch,
194 struct wl_join_params *join_params, size_t *join_params_size);
195
196 /*
197 ** information element utilities
198 */
199 static void wl_rst_ie(struct wl_priv *wl);
200 static __used s32 wl_add_ie(struct wl_priv *wl, u8 t, u8 l, u8 *v);
201 static s32 wl_mrg_ie(struct wl_priv *wl, u8 *ie_stream, u16 ie_size);
202 static s32 wl_cp_ie(struct wl_priv *wl, u8 *dst, u16 dst_size);
203 static u32 wl_get_ielen(struct wl_priv *wl);
204
205 static s32 wl_mode_to_nl80211_iftype(s32 mode);
206
207 static struct wireless_dev *wl_alloc_wdev(s32 sizeof_iface,
208 struct device *dev);
209 static void wl_free_wdev(struct wl_priv *wl);
210
211 static s32 wl_inform_bss(struct wl_priv *wl);
212 static s32 wl_inform_single_bss(struct wl_priv *wl, struct wl_bss_info *bi);
213 static s32 wl_update_bss_info(struct wl_priv *wl);
214
215 static s32 wl_add_keyext(struct wiphy *wiphy, struct net_device *dev,
216 u8 key_idx, const u8 *mac_addr,
217 struct key_params *params);
218
219 /*
220 ** key indianess swap utilities
221 */
222 static void swap_key_from_BE(struct wl_wsec_key *key);
223 static void swap_key_to_BE(struct wl_wsec_key *key);
224
225 /*
226 ** wl_priv memory init/deinit utilities
227 */
228 static s32 wl_init_priv_mem(struct wl_priv *wl);
229 static void wl_deinit_priv_mem(struct wl_priv *wl);
230
231 static void wl_delay(u32 ms);
232
233 /*
234 ** store/restore cfg80211 instance data
235 */
236 static void wl_set_drvdata(struct wl_dev *dev, void *data);
237 static void *wl_get_drvdata(struct wl_dev *dev);
238
239 /*
240 ** ibss mode utilities
241 */
242 static bool wl_is_ibssmode(struct wl_priv *wl);
243 static bool wl_is_ibssstarter(struct wl_priv *wl);
244
245 /*
246 ** dongle up/down , default configuration utilities
247 */
248 static bool wl_is_linkdown(struct wl_priv *wl, const wl_event_msg_t *e);
249 static bool wl_is_linkup(struct wl_priv *wl, const wl_event_msg_t *e);
250 static bool wl_is_nonetwork(struct wl_priv *wl, const wl_event_msg_t *e);
251 static void wl_link_up(struct wl_priv *wl);
252 static void wl_link_down(struct wl_priv *wl);
253 static s32 wl_dongle_mode(struct net_device *ndev, s32 iftype);
254 static s32 __wl_cfg80211_up(struct wl_priv *wl);
255 static s32 __wl_cfg80211_down(struct wl_priv *wl);
256 static s32 wl_dongle_probecap(struct wl_priv *wl);
257 static void wl_init_conf(struct wl_conf *conf);
258
259 /*
260 ** dongle configuration utilities
261 */
262 #ifndef EMBEDDED_PLATFORM
263 static s32 wl_dongle_mode(struct net_device *ndev, s32 iftype);
264 static s32 wl_dongle_country(struct net_device *ndev, u8 ccode);
265 static s32 wl_dongle_up(struct net_device *ndev, u32 up);
266 static s32 wl_dongle_power(struct net_device *ndev, u32 power_mode);
267 static s32 wl_dongle_glom(struct net_device *ndev, u32 glom,
268 u32 dongle_align);
269 static s32 wl_dongle_roam(struct net_device *ndev, u32 roamvar,
270 u32 bcn_timeout);
271 static s32 wl_dongle_eventmsg(struct net_device *ndev);
272 static s32 wl_dongle_scantime(struct net_device *ndev, s32 scan_assoc_time,
273 s32 scan_unassoc_time);
274 static s32 wl_dongle_offload(struct net_device *ndev, s32 arpoe,
275 s32 arp_ol);
276 static s32 wl_pattern_atoh(s8 *src, s8 *dst);
277 static s32 wl_dongle_filter(struct net_device *ndev, u32 filter_mode);
278 static s32 wl_update_wiphybands(struct wl_priv *wl);
279 #endif /* !EMBEDDED_PLATFORM */
280 static s32 wl_config_dongle(struct wl_priv *wl, bool need_lock);
281
282 /*
283 ** iscan handler
284 */
285 static void wl_iscan_timer(unsigned long data);
286 static void wl_term_iscan(struct wl_priv *wl);
287 static s32 wl_init_iscan(struct wl_priv *wl);
288 static s32 wl_iscan_thread(void *data);
289 static s32 wl_dev_iovar_setbuf(struct net_device *dev, s8 *iovar,
290 void *param, s32 paramlen, void *bufptr,
291 s32 buflen);
292 static s32 wl_dev_iovar_getbuf(struct net_device *dev, s8 *iovar,
293 void *param, s32 paramlen, void *bufptr,
294 s32 buflen);
295 static s32 wl_run_iscan(struct wl_iscan_ctrl *iscan, struct wlc_ssid *ssid,
296 u16 action);
297 static s32 wl_do_iscan(struct wl_priv *wl);
298 static s32 wl_wakeup_iscan(struct wl_iscan_ctrl *iscan);
299 static s32 wl_invoke_iscan(struct wl_priv *wl);
300 static s32 wl_get_iscan_results(struct wl_iscan_ctrl *iscan, u32 *status,
301 struct wl_scan_results **bss_list);
302 static void wl_notify_iscan_complete(struct wl_iscan_ctrl *iscan, bool aborted);
303 static void wl_init_iscan_eloop(struct wl_iscan_eloop *el);
304 static s32 wl_iscan_done(struct wl_priv *wl);
305 static s32 wl_iscan_pending(struct wl_priv *wl);
306 static s32 wl_iscan_inprogress(struct wl_priv *wl);
307 static s32 wl_iscan_aborted(struct wl_priv *wl);
308
309 /*
310 ** fw/nvram downloading handler
311 */
312 static void wl_init_fw(struct wl_fw_ctrl *fw);
313
314 /*
315 * find most significant bit set
316 */
317 static __used u32 wl_find_msb(u16 bit16);
318
319 /*
320 * update pmklist to dongle
321 */
322 static __used s32 wl_update_pmklist(struct net_device *dev,
323 struct wl_pmk_list *pmk_list, s32 err);
324
325 static void wl_set_mpc(struct net_device *ndev, int mpc);
326
327 /*
328 * debufs support
329 */
330 static int wl_debugfs_add_netdev_params(struct wl_priv *wl);
331 static void wl_debugfs_remove_netdev(struct wl_priv *wl);
332
333 #define WL_PRIV_GET() \
334 ({ \
335 struct wl_iface *ci; \
336 if (unlikely(!(wl_cfg80211_dev && \
337 (ci = wl_get_drvdata(wl_cfg80211_dev))))) { \
338 WL_ERR("wl_cfg80211_dev is unavailable\n"); \
339 BUG(); \
340 } \
341 ci_to_wl(ci); \
342 })
343
344 #define CHECK_SYS_UP() \
345 do { \
346 struct wl_priv *wl = wiphy_to_wl(wiphy); \
347 if (unlikely(!test_bit(WL_STATUS_READY, &wl->status))) { \
348 WL_INFO("device is not ready : status (%d)\n", \
349 (int)wl->status); \
350 return -EIO; \
351 } \
352 } while (0)
353
354 extern int dhd_wait_pend8021x(struct net_device *dev);
355
356 #if (WL_DBG_LEVEL > 0)
357 #define WL_DBG_ESTR_MAX 32
358 static s8 wl_dbg_estr[][WL_DBG_ESTR_MAX] = {
359 "SET_SSID", "JOIN", "START", "AUTH", "AUTH_IND",
360 "DEAUTH", "DEAUTH_IND", "ASSOC", "ASSOC_IND", "REASSOC",
361 "REASSOC_IND", "DISASSOC", "DISASSOC_IND", "QUIET_START", "QUIET_END",
362 "BEACON_RX", "LINK", "MIC_ERROR", "NDIS_LINK", "ROAM",
363 "TXFAIL", "PMKID_CACHE", "RETROGRADE_TSF", "PRUNE", "AUTOAUTH",
364 "EAPOL_MSG", "SCAN_COMPLETE", "ADDTS_IND", "DELTS_IND", "BCNSENT_IND",
365 "BCNRX_MSG", "BCNLOST_MSG", "ROAM_PREP", "PFN_NET_FOUND",
366 "PFN_NET_LOST",
367 "RESET_COMPLETE", "JOIN_START", "ROAM_START", "ASSOC_START",
368 "IBSS_ASSOC",
369 "RADIO", "PSM_WATCHDOG",
370 "PROBREQ_MSG",
371 "SCAN_CONFIRM_IND", "PSK_SUP", "COUNTRY_CODE_CHANGED",
372 "EXCEEDED_MEDIUM_TIME", "ICV_ERROR",
373 "UNICAST_DECODE_ERROR", "MULTICAST_DECODE_ERROR", "TRACE",
374 "IF",
375 "RSSI", "PFN_SCAN_COMPLETE", "ACTION_FRAME", "ACTION_FRAME_COMPLETE",
376 };
377 #endif /* WL_DBG_LEVEL */
378
379 #define CHAN2G(_channel, _freq, _flags) { \
380 .band = IEEE80211_BAND_2GHZ, \
381 .center_freq = (_freq), \
382 .hw_value = (_channel), \
383 .flags = (_flags), \
384 .max_antenna_gain = 0, \
385 .max_power = 30, \
386 }
387
388 #define CHAN5G(_channel, _flags) { \
389 .band = IEEE80211_BAND_5GHZ, \
390 .center_freq = 5000 + (5 * (_channel)), \
391 .hw_value = (_channel), \
392 .flags = (_flags), \
393 .max_antenna_gain = 0, \
394 .max_power = 30, \
395 }
396
397 #define RATE_TO_BASE100KBPS(rate) (((rate) * 10) / 2)
398 #define RATETAB_ENT(_rateid, _flags) \
399 { \
400 .bitrate = RATE_TO_BASE100KBPS(_rateid), \
401 .hw_value = (_rateid), \
402 .flags = (_flags), \
403 }
404
405 static struct ieee80211_rate __wl_rates[] = {
406 RATETAB_ENT(WLC_RATE_1M, 0),
407 RATETAB_ENT(WLC_RATE_2M, IEEE80211_RATE_SHORT_PREAMBLE),
408 RATETAB_ENT(WLC_RATE_5M5, IEEE80211_RATE_SHORT_PREAMBLE),
409 RATETAB_ENT(WLC_RATE_11M, IEEE80211_RATE_SHORT_PREAMBLE),
410 RATETAB_ENT(WLC_RATE_6M, 0),
411 RATETAB_ENT(WLC_RATE_9M, 0),
412 RATETAB_ENT(WLC_RATE_12M, 0),
413 RATETAB_ENT(WLC_RATE_18M, 0),
414 RATETAB_ENT(WLC_RATE_24M, 0),
415 RATETAB_ENT(WLC_RATE_36M, 0),
416 RATETAB_ENT(WLC_RATE_48M, 0),
417 RATETAB_ENT(WLC_RATE_54M, 0),
418 };
419
420 #define wl_a_rates (__wl_rates + 4)
421 #define wl_a_rates_size 8
422 #define wl_g_rates (__wl_rates + 0)
423 #define wl_g_rates_size 12
424
425 static struct ieee80211_channel __wl_2ghz_channels[] = {
426 CHAN2G(1, 2412, 0),
427 CHAN2G(2, 2417, 0),
428 CHAN2G(3, 2422, 0),
429 CHAN2G(4, 2427, 0),
430 CHAN2G(5, 2432, 0),
431 CHAN2G(6, 2437, 0),
432 CHAN2G(7, 2442, 0),
433 CHAN2G(8, 2447, 0),
434 CHAN2G(9, 2452, 0),
435 CHAN2G(10, 2457, 0),
436 CHAN2G(11, 2462, 0),
437 CHAN2G(12, 2467, 0),
438 CHAN2G(13, 2472, 0),
439 CHAN2G(14, 2484, 0),
440 };
441
442 static struct ieee80211_channel __wl_5ghz_a_channels[] = {
443 CHAN5G(34, 0), CHAN5G(36, 0),
444 CHAN5G(38, 0), CHAN5G(40, 0),
445 CHAN5G(42, 0), CHAN5G(44, 0),
446 CHAN5G(46, 0), CHAN5G(48, 0),
447 CHAN5G(52, 0), CHAN5G(56, 0),
448 CHAN5G(60, 0), CHAN5G(64, 0),
449 CHAN5G(100, 0), CHAN5G(104, 0),
450 CHAN5G(108, 0), CHAN5G(112, 0),
451 CHAN5G(116, 0), CHAN5G(120, 0),
452 CHAN5G(124, 0), CHAN5G(128, 0),
453 CHAN5G(132, 0), CHAN5G(136, 0),
454 CHAN5G(140, 0), CHAN5G(149, 0),
455 CHAN5G(153, 0), CHAN5G(157, 0),
456 CHAN5G(161, 0), CHAN5G(165, 0),
457 CHAN5G(184, 0), CHAN5G(188, 0),
458 CHAN5G(192, 0), CHAN5G(196, 0),
459 CHAN5G(200, 0), CHAN5G(204, 0),
460 CHAN5G(208, 0), CHAN5G(212, 0),
461 CHAN5G(216, 0),
462 };
463
464 static struct ieee80211_channel __wl_5ghz_n_channels[] = {
465 CHAN5G(32, 0), CHAN5G(34, 0),
466 CHAN5G(36, 0), CHAN5G(38, 0),
467 CHAN5G(40, 0), CHAN5G(42, 0),
468 CHAN5G(44, 0), CHAN5G(46, 0),
469 CHAN5G(48, 0), CHAN5G(50, 0),
470 CHAN5G(52, 0), CHAN5G(54, 0),
471 CHAN5G(56, 0), CHAN5G(58, 0),
472 CHAN5G(60, 0), CHAN5G(62, 0),
473 CHAN5G(64, 0), CHAN5G(66, 0),
474 CHAN5G(68, 0), CHAN5G(70, 0),
475 CHAN5G(72, 0), CHAN5G(74, 0),
476 CHAN5G(76, 0), CHAN5G(78, 0),
477 CHAN5G(80, 0), CHAN5G(82, 0),
478 CHAN5G(84, 0), CHAN5G(86, 0),
479 CHAN5G(88, 0), CHAN5G(90, 0),
480 CHAN5G(92, 0), CHAN5G(94, 0),
481 CHAN5G(96, 0), CHAN5G(98, 0),
482 CHAN5G(100, 0), CHAN5G(102, 0),
483 CHAN5G(104, 0), CHAN5G(106, 0),
484 CHAN5G(108, 0), CHAN5G(110, 0),
485 CHAN5G(112, 0), CHAN5G(114, 0),
486 CHAN5G(116, 0), CHAN5G(118, 0),
487 CHAN5G(120, 0), CHAN5G(122, 0),
488 CHAN5G(124, 0), CHAN5G(126, 0),
489 CHAN5G(128, 0), CHAN5G(130, 0),
490 CHAN5G(132, 0), CHAN5G(134, 0),
491 CHAN5G(136, 0), CHAN5G(138, 0),
492 CHAN5G(140, 0), CHAN5G(142, 0),
493 CHAN5G(144, 0), CHAN5G(145, 0),
494 CHAN5G(146, 0), CHAN5G(147, 0),
495 CHAN5G(148, 0), CHAN5G(149, 0),
496 CHAN5G(150, 0), CHAN5G(151, 0),
497 CHAN5G(152, 0), CHAN5G(153, 0),
498 CHAN5G(154, 0), CHAN5G(155, 0),
499 CHAN5G(156, 0), CHAN5G(157, 0),
500 CHAN5G(158, 0), CHAN5G(159, 0),
501 CHAN5G(160, 0), CHAN5G(161, 0),
502 CHAN5G(162, 0), CHAN5G(163, 0),
503 CHAN5G(164, 0), CHAN5G(165, 0),
504 CHAN5G(166, 0), CHAN5G(168, 0),
505 CHAN5G(170, 0), CHAN5G(172, 0),
506 CHAN5G(174, 0), CHAN5G(176, 0),
507 CHAN5G(178, 0), CHAN5G(180, 0),
508 CHAN5G(182, 0), CHAN5G(184, 0),
509 CHAN5G(186, 0), CHAN5G(188, 0),
510 CHAN5G(190, 0), CHAN5G(192, 0),
511 CHAN5G(194, 0), CHAN5G(196, 0),
512 CHAN5G(198, 0), CHAN5G(200, 0),
513 CHAN5G(202, 0), CHAN5G(204, 0),
514 CHAN5G(206, 0), CHAN5G(208, 0),
515 CHAN5G(210, 0), CHAN5G(212, 0),
516 CHAN5G(214, 0), CHAN5G(216, 0),
517 CHAN5G(218, 0), CHAN5G(220, 0),
518 CHAN5G(222, 0), CHAN5G(224, 0),
519 CHAN5G(226, 0), CHAN5G(228, 0),
520 };
521
522 static struct ieee80211_supported_band __wl_band_2ghz = {
523 .band = IEEE80211_BAND_2GHZ,
524 .channels = __wl_2ghz_channels,
525 .n_channels = ARRAY_SIZE(__wl_2ghz_channels),
526 .bitrates = wl_g_rates,
527 .n_bitrates = wl_g_rates_size,
528 };
529
530 static struct ieee80211_supported_band __wl_band_5ghz_a = {
531 .band = IEEE80211_BAND_5GHZ,
532 .channels = __wl_5ghz_a_channels,
533 .n_channels = ARRAY_SIZE(__wl_5ghz_a_channels),
534 .bitrates = wl_a_rates,
535 .n_bitrates = wl_a_rates_size,
536 };
537
538 static struct ieee80211_supported_band __wl_band_5ghz_n = {
539 .band = IEEE80211_BAND_5GHZ,
540 .channels = __wl_5ghz_n_channels,
541 .n_channels = ARRAY_SIZE(__wl_5ghz_n_channels),
542 .bitrates = wl_a_rates,
543 .n_bitrates = wl_a_rates_size,
544 };
545
546 static const u32 __wl_cipher_suites[] = {
547 WLAN_CIPHER_SUITE_WEP40,
548 WLAN_CIPHER_SUITE_WEP104,
549 WLAN_CIPHER_SUITE_TKIP,
550 WLAN_CIPHER_SUITE_CCMP,
551 WLAN_CIPHER_SUITE_AES_CMAC,
552 };
553
swap_key_from_BE(struct wl_wsec_key * key)554 static void swap_key_from_BE(struct wl_wsec_key *key)
555 {
556 key->index = cpu_to_le32(key->index);
557 key->len = cpu_to_le32(key->len);
558 key->algo = cpu_to_le32(key->algo);
559 key->flags = cpu_to_le32(key->flags);
560 key->rxiv.hi = cpu_to_le32(key->rxiv.hi);
561 key->rxiv.lo = cpu_to_le16(key->rxiv.lo);
562 key->iv_initialized = cpu_to_le32(key->iv_initialized);
563 }
564
swap_key_to_BE(struct wl_wsec_key * key)565 static void swap_key_to_BE(struct wl_wsec_key *key)
566 {
567 key->index = le32_to_cpu(key->index);
568 key->len = le32_to_cpu(key->len);
569 key->algo = le32_to_cpu(key->algo);
570 key->flags = le32_to_cpu(key->flags);
571 key->rxiv.hi = le32_to_cpu(key->rxiv.hi);
572 key->rxiv.lo = le16_to_cpu(key->rxiv.lo);
573 key->iv_initialized = le32_to_cpu(key->iv_initialized);
574 }
575
576 static s32
wl_dev_ioctl(struct net_device * dev,u32 cmd,void * arg,u32 len)577 wl_dev_ioctl(struct net_device *dev, u32 cmd, void *arg, u32 len)
578 {
579 struct ifreq ifr;
580 struct wl_ioctl ioc;
581 mm_segment_t fs;
582 s32 err = 0;
583
584 memset(&ioc, 0, sizeof(ioc));
585 ioc.cmd = cmd;
586 ioc.buf = arg;
587 ioc.len = len;
588 strcpy(ifr.ifr_name, dev->name);
589 ifr.ifr_data = (caddr_t)&ioc;
590
591 fs = get_fs();
592 set_fs(get_ds());
593 err = dev->netdev_ops->ndo_do_ioctl(dev, &ifr, SIOCDEVPRIVATE);
594 set_fs(fs);
595
596 return err;
597 }
598
599 static s32
wl_cfg80211_change_iface(struct wiphy * wiphy,struct net_device * ndev,enum nl80211_iftype type,u32 * flags,struct vif_params * params)600 wl_cfg80211_change_iface(struct wiphy *wiphy, struct net_device *ndev,
601 enum nl80211_iftype type, u32 *flags,
602 struct vif_params *params)
603 {
604 struct wl_priv *wl = wiphy_to_wl(wiphy);
605 struct wireless_dev *wdev;
606 s32 infra = 0;
607 s32 ap = 0;
608 s32 err = 0;
609
610 CHECK_SYS_UP();
611 switch (type) {
612 case NL80211_IFTYPE_MONITOR:
613 case NL80211_IFTYPE_WDS:
614 WL_ERR("type (%d) : currently we do not support this type\n",
615 type);
616 return -EOPNOTSUPP;
617 case NL80211_IFTYPE_ADHOC:
618 wl->conf->mode = WL_MODE_IBSS;
619 break;
620 case NL80211_IFTYPE_STATION:
621 wl->conf->mode = WL_MODE_BSS;
622 infra = 1;
623 break;
624 default:
625 return -EINVAL;
626 }
627 infra = cpu_to_le32(infra);
628 ap = cpu_to_le32(ap);
629 wdev = ndev->ieee80211_ptr;
630 wdev->iftype = type;
631 WL_DBG("%s : ap (%d), infra (%d)\n", ndev->name, ap, infra);
632 err = wl_dev_ioctl(ndev, WLC_SET_INFRA, &infra, sizeof(infra));
633 if (unlikely(err)) {
634 WL_ERR("WLC_SET_INFRA error (%d)\n", err);
635 return err;
636 }
637 err = wl_dev_ioctl(ndev, WLC_SET_AP, &ap, sizeof(ap));
638 if (unlikely(err)) {
639 WL_ERR("WLC_SET_AP error (%d)\n", err);
640 return err;
641 }
642
643 /* -EINPROGRESS: Call commit handler */
644 return -EINPROGRESS;
645 }
646
wl_iscan_prep(struct wl_scan_params * params,struct wlc_ssid * ssid)647 static void wl_iscan_prep(struct wl_scan_params *params, struct wlc_ssid *ssid)
648 {
649 memcpy(params->bssid, ether_bcast, ETH_ALEN);
650 params->bss_type = DOT11_BSSTYPE_ANY;
651 params->scan_type = 0;
652 params->nprobes = -1;
653 params->active_time = -1;
654 params->passive_time = -1;
655 params->home_time = -1;
656 params->channel_num = 0;
657
658 params->nprobes = cpu_to_le32(params->nprobes);
659 params->active_time = cpu_to_le32(params->active_time);
660 params->passive_time = cpu_to_le32(params->passive_time);
661 params->home_time = cpu_to_le32(params->home_time);
662 if (ssid && ssid->SSID_len)
663 memcpy(¶ms->ssid, ssid, sizeof(wlc_ssid_t));
664
665 }
666
667 static s32
wl_dev_iovar_setbuf(struct net_device * dev,s8 * iovar,void * param,s32 paramlen,void * bufptr,s32 buflen)668 wl_dev_iovar_setbuf(struct net_device *dev, s8 * iovar, void *param,
669 s32 paramlen, void *bufptr, s32 buflen)
670 {
671 s32 iolen;
672
673 iolen = bcm_mkiovar(iovar, param, paramlen, bufptr, buflen);
674 BUG_ON(!iolen);
675
676 return wl_dev_ioctl(dev, WLC_SET_VAR, bufptr, iolen);
677 }
678
679 static s32
wl_dev_iovar_getbuf(struct net_device * dev,s8 * iovar,void * param,s32 paramlen,void * bufptr,s32 buflen)680 wl_dev_iovar_getbuf(struct net_device *dev, s8 * iovar, void *param,
681 s32 paramlen, void *bufptr, s32 buflen)
682 {
683 s32 iolen;
684
685 iolen = bcm_mkiovar(iovar, param, paramlen, bufptr, buflen);
686 BUG_ON(!iolen);
687
688 return wl_dev_ioctl(dev, WLC_GET_VAR, bufptr, buflen);
689 }
690
691 static s32
wl_run_iscan(struct wl_iscan_ctrl * iscan,struct wlc_ssid * ssid,u16 action)692 wl_run_iscan(struct wl_iscan_ctrl *iscan, struct wlc_ssid *ssid, u16 action)
693 {
694 s32 params_size =
695 (WL_SCAN_PARAMS_FIXED_SIZE + offsetof(wl_iscan_params_t, params));
696 struct wl_iscan_params *params;
697 s32 err = 0;
698
699 if (ssid && ssid->SSID_len)
700 params_size += sizeof(struct wlc_ssid);
701 params = kzalloc(params_size, GFP_KERNEL);
702 if (unlikely(!params))
703 return -ENOMEM;
704 BUG_ON(params_size >= WLC_IOCTL_SMLEN);
705
706 wl_iscan_prep(¶ms->params, ssid);
707
708 params->version = cpu_to_le32(ISCAN_REQ_VERSION);
709 params->action = cpu_to_le16(action);
710 params->scan_duration = cpu_to_le16(0);
711
712 /* params_size += offsetof(wl_iscan_params_t, params); */
713 err = wl_dev_iovar_setbuf(iscan->dev, "iscan", params, params_size,
714 iscan->ioctl_buf, WLC_IOCTL_SMLEN);
715 if (unlikely(err)) {
716 if (err == -EBUSY) {
717 WL_INFO("system busy : iscan canceled\n");
718 } else {
719 WL_ERR("error (%d)\n", err);
720 }
721 }
722 kfree(params);
723 return err;
724 }
725
wl_do_iscan(struct wl_priv * wl)726 static s32 wl_do_iscan(struct wl_priv *wl)
727 {
728 struct wl_iscan_ctrl *iscan = wl_to_iscan(wl);
729 struct net_device *ndev = wl_to_ndev(wl);
730 struct wlc_ssid ssid;
731 s32 passive_scan;
732 s32 err = 0;
733
734 /* Broadcast scan by default */
735 memset(&ssid, 0, sizeof(ssid));
736
737 iscan->state = WL_ISCAN_STATE_SCANING;
738
739 passive_scan = wl->active_scan ? 0 : 1;
740 err = wl_dev_ioctl(wl_to_ndev(wl), WLC_SET_PASSIVE_SCAN,
741 &passive_scan, sizeof(passive_scan));
742 if (unlikely(err)) {
743 WL_DBG("error (%d)\n", err);
744 return err;
745 }
746 wl_set_mpc(ndev, 0);
747 wl->iscan_kickstart = true;
748 wl_run_iscan(iscan, &ssid, WL_SCAN_ACTION_START);
749 mod_timer(&iscan->timer, jiffies + iscan->timer_ms * HZ / 1000);
750 iscan->timer_on = 1;
751
752 return err;
753 }
754
755 static s32
__wl_cfg80211_scan(struct wiphy * wiphy,struct net_device * ndev,struct cfg80211_scan_request * request,struct cfg80211_ssid * this_ssid)756 __wl_cfg80211_scan(struct wiphy *wiphy, struct net_device *ndev,
757 struct cfg80211_scan_request *request,
758 struct cfg80211_ssid *this_ssid)
759 {
760 struct wl_priv *wl = ndev_to_wl(ndev);
761 struct cfg80211_ssid *ssids;
762 struct wl_scan_req *sr = wl_to_sr(wl);
763 s32 passive_scan;
764 bool iscan_req;
765 bool spec_scan;
766 s32 err = 0;
767
768 if (unlikely(test_bit(WL_STATUS_SCANNING, &wl->status))) {
769 WL_ERR("Scanning already : status (%d)\n", (int)wl->status);
770 return -EAGAIN;
771 }
772 if (unlikely(test_bit(WL_STATUS_SCAN_ABORTING, &wl->status))) {
773 WL_ERR("Scanning being aborted : status (%d)\n",
774 (int)wl->status);
775 return -EAGAIN;
776 }
777
778 iscan_req = false;
779 spec_scan = false;
780 if (request) { /* scan bss */
781 ssids = request->ssids;
782 if (wl->iscan_on && (!ssids || !ssids->ssid_len)) { /* for
783 * specific scan,
784 * ssids->ssid_len has
785 * non-zero(ssid string)
786 * length.
787 * Otherwise this is 0.
788 * we do not iscan for
789 * specific scan request
790 */
791 iscan_req = true;
792 }
793 } else { /* scan in ibss */
794 /* we don't do iscan in ibss */
795 ssids = this_ssid;
796 }
797 wl->scan_request = request;
798 set_bit(WL_STATUS_SCANNING, &wl->status);
799 if (iscan_req) {
800 err = wl_do_iscan(wl);
801 if (likely(!err))
802 return err;
803 else
804 goto scan_out;
805 } else {
806 WL_DBG("ssid \"%s\", ssid_len (%d)\n",
807 ssids->ssid, ssids->ssid_len);
808 memset(&sr->ssid, 0, sizeof(sr->ssid));
809 sr->ssid.SSID_len =
810 min_t(u8, sizeof(sr->ssid.SSID), ssids->ssid_len);
811 if (sr->ssid.SSID_len) {
812 memcpy(sr->ssid.SSID, ssids->ssid, sr->ssid.SSID_len);
813 sr->ssid.SSID_len = cpu_to_le32(sr->ssid.SSID_len);
814 WL_DBG("Specific scan ssid=\"%s\" len=%d\n",
815 sr->ssid.SSID, sr->ssid.SSID_len);
816 spec_scan = true;
817 } else {
818 WL_DBG("Broadcast scan\n");
819 }
820 WL_DBG("sr->ssid.SSID_len (%d)\n", sr->ssid.SSID_len);
821 passive_scan = wl->active_scan ? 0 : 1;
822 err = wl_dev_ioctl(ndev, WLC_SET_PASSIVE_SCAN,
823 &passive_scan, sizeof(passive_scan));
824 if (unlikely(err)) {
825 WL_ERR("WLC_SET_PASSIVE_SCAN error (%d)\n", err);
826 goto scan_out;
827 }
828 wl_set_mpc(ndev, 0);
829 err = wl_dev_ioctl(ndev, WLC_SCAN, &sr->ssid,
830 sizeof(sr->ssid));
831 if (err) {
832 if (err == -EBUSY) {
833 WL_INFO("system busy : scan for \"%s\" canceled\n",
834 sr->ssid.SSID);
835 } else {
836 WL_ERR("WLC_SCAN error (%d)\n", err);
837 }
838 wl_set_mpc(ndev, 1);
839 goto scan_out;
840 }
841 }
842
843 return 0;
844
845 scan_out:
846 clear_bit(WL_STATUS_SCANNING, &wl->status);
847 wl->scan_request = NULL;
848 return err;
849 }
850
851 static s32
wl_cfg80211_scan(struct wiphy * wiphy,struct net_device * ndev,struct cfg80211_scan_request * request)852 wl_cfg80211_scan(struct wiphy *wiphy, struct net_device *ndev,
853 struct cfg80211_scan_request *request)
854 {
855 s32 err = 0;
856
857 CHECK_SYS_UP();
858 err = __wl_cfg80211_scan(wiphy, ndev, request, NULL);
859 if (unlikely(err)) {
860 WL_DBG("scan error (%d)\n", err);
861 return err;
862 }
863
864 return err;
865 }
866
wl_dev_intvar_set(struct net_device * dev,s8 * name,s32 val)867 static s32 wl_dev_intvar_set(struct net_device *dev, s8 *name, s32 val)
868 {
869 s8 buf[WLC_IOCTL_SMLEN];
870 u32 len;
871 s32 err = 0;
872
873 val = cpu_to_le32(val);
874 len = bcm_mkiovar(name, (char *)(&val), sizeof(val), buf, sizeof(buf));
875 BUG_ON(!len);
876
877 err = wl_dev_ioctl(dev, WLC_SET_VAR, buf, len);
878 if (unlikely(err)) {
879 WL_ERR("error (%d)\n", err);
880 }
881
882 return err;
883 }
884
885 static s32
wl_dev_intvar_get(struct net_device * dev,s8 * name,s32 * retval)886 wl_dev_intvar_get(struct net_device *dev, s8 *name, s32 *retval)
887 {
888 union {
889 s8 buf[WLC_IOCTL_SMLEN];
890 s32 val;
891 } var;
892 u32 len;
893 u32 data_null;
894 s32 err = 0;
895
896 len =
897 bcm_mkiovar(name, (char *)(&data_null), 0, (char *)(&var),
898 sizeof(var.buf));
899 BUG_ON(!len);
900 err = wl_dev_ioctl(dev, WLC_GET_VAR, &var, len);
901 if (unlikely(err)) {
902 WL_ERR("error (%d)\n", err);
903 }
904 *retval = le32_to_cpu(var.val);
905
906 return err;
907 }
908
wl_set_rts(struct net_device * dev,u32 rts_threshold)909 static s32 wl_set_rts(struct net_device *dev, u32 rts_threshold)
910 {
911 s32 err = 0;
912
913 err = wl_dev_intvar_set(dev, "rtsthresh", rts_threshold);
914 if (unlikely(err)) {
915 WL_ERR("Error (%d)\n", err);
916 return err;
917 }
918 return err;
919 }
920
wl_set_frag(struct net_device * dev,u32 frag_threshold)921 static s32 wl_set_frag(struct net_device *dev, u32 frag_threshold)
922 {
923 s32 err = 0;
924
925 err = wl_dev_intvar_set(dev, "fragthresh", frag_threshold);
926 if (unlikely(err)) {
927 WL_ERR("Error (%d)\n", err);
928 return err;
929 }
930 return err;
931 }
932
wl_set_retry(struct net_device * dev,u32 retry,bool l)933 static s32 wl_set_retry(struct net_device *dev, u32 retry, bool l)
934 {
935 s32 err = 0;
936 u32 cmd = (l ? WLC_SET_LRL : WLC_SET_SRL);
937
938 retry = cpu_to_le32(retry);
939 err = wl_dev_ioctl(dev, cmd, &retry, sizeof(retry));
940 if (unlikely(err)) {
941 WL_ERR("cmd (%d) , error (%d)\n", cmd, err);
942 return err;
943 }
944 return err;
945 }
946
wl_cfg80211_set_wiphy_params(struct wiphy * wiphy,u32 changed)947 static s32 wl_cfg80211_set_wiphy_params(struct wiphy *wiphy, u32 changed)
948 {
949 struct wl_priv *wl = wiphy_to_wl(wiphy);
950 struct net_device *ndev = wl_to_ndev(wl);
951 s32 err = 0;
952
953 CHECK_SYS_UP();
954 if (changed & WIPHY_PARAM_RTS_THRESHOLD &&
955 (wl->conf->rts_threshold != wiphy->rts_threshold)) {
956 wl->conf->rts_threshold = wiphy->rts_threshold;
957 err = wl_set_rts(ndev, wl->conf->rts_threshold);
958 if (!err)
959 return err;
960 }
961 if (changed & WIPHY_PARAM_FRAG_THRESHOLD &&
962 (wl->conf->frag_threshold != wiphy->frag_threshold)) {
963 wl->conf->frag_threshold = wiphy->frag_threshold;
964 err = wl_set_frag(ndev, wl->conf->frag_threshold);
965 if (!err)
966 return err;
967 }
968 if (changed & WIPHY_PARAM_RETRY_LONG
969 && (wl->conf->retry_long != wiphy->retry_long)) {
970 wl->conf->retry_long = wiphy->retry_long;
971 err = wl_set_retry(ndev, wl->conf->retry_long, true);
972 if (!err)
973 return err;
974 }
975 if (changed & WIPHY_PARAM_RETRY_SHORT
976 && (wl->conf->retry_short != wiphy->retry_short)) {
977 wl->conf->retry_short = wiphy->retry_short;
978 err = wl_set_retry(ndev, wl->conf->retry_short, false);
979 if (!err) {
980 return err;
981 }
982 }
983
984 return err;
985 }
986
987 static s32
wl_cfg80211_join_ibss(struct wiphy * wiphy,struct net_device * dev,struct cfg80211_ibss_params * params)988 wl_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev,
989 struct cfg80211_ibss_params *params)
990 {
991 struct wl_priv *wl = wiphy_to_wl(wiphy);
992 struct cfg80211_bss *bss;
993 struct ieee80211_channel *chan;
994 struct wl_join_params join_params;
995 struct cfg80211_ssid ssid;
996 s32 scan_retry = 0;
997 s32 err = 0;
998
999 CHECK_SYS_UP();
1000 if (params->bssid) {
1001 WL_ERR("Invalid bssid\n");
1002 return -EOPNOTSUPP;
1003 }
1004 bss = cfg80211_get_ibss(wiphy, NULL, params->ssid, params->ssid_len);
1005 if (!bss) {
1006 memcpy(ssid.ssid, params->ssid, params->ssid_len);
1007 ssid.ssid_len = params->ssid_len;
1008 do {
1009 if (unlikely
1010 (__wl_cfg80211_scan(wiphy, dev, NULL, &ssid) ==
1011 -EBUSY)) {
1012 wl_delay(150);
1013 } else {
1014 break;
1015 }
1016 } while (++scan_retry < WL_SCAN_RETRY_MAX);
1017 rtnl_unlock(); /* to allow scan_inform to paropagate
1018 to cfg80211 plane */
1019 schedule_timeout_interruptible(4 * HZ); /* wait 4 secons
1020 till scan done.... */
1021 rtnl_lock();
1022 bss = cfg80211_get_ibss(wiphy, NULL,
1023 params->ssid, params->ssid_len);
1024 }
1025 if (bss) {
1026 wl->ibss_starter = false;
1027 WL_DBG("Found IBSS\n");
1028 } else {
1029 wl->ibss_starter = true;
1030 }
1031 chan = params->channel;
1032 if (chan)
1033 wl->channel = ieee80211_frequency_to_channel(chan->center_freq);
1034 /*
1035 ** Join with specific BSSID and cached SSID
1036 ** If SSID is zero join based on BSSID only
1037 */
1038 memset(&join_params, 0, sizeof(join_params));
1039 memcpy((void *)join_params.ssid.SSID, (void *)params->ssid,
1040 params->ssid_len);
1041 join_params.ssid.SSID_len = cpu_to_le32(params->ssid_len);
1042 if (params->bssid)
1043 memcpy(&join_params.params.bssid, params->bssid,
1044 ETH_ALEN);
1045 else
1046 memset(&join_params.params.bssid, 0, ETH_ALEN);
1047
1048 err = wl_dev_ioctl(dev, WLC_SET_SSID, &join_params,
1049 sizeof(join_params));
1050 if (unlikely(err)) {
1051 WL_ERR("Error (%d)\n", err);
1052 return err;
1053 }
1054 return err;
1055 }
1056
wl_cfg80211_leave_ibss(struct wiphy * wiphy,struct net_device * dev)1057 static s32 wl_cfg80211_leave_ibss(struct wiphy *wiphy, struct net_device *dev)
1058 {
1059 struct wl_priv *wl = wiphy_to_wl(wiphy);
1060 s32 err = 0;
1061
1062 CHECK_SYS_UP();
1063 wl_link_down(wl);
1064
1065 return err;
1066 }
1067
1068 static s32
wl_set_wpa_version(struct net_device * dev,struct cfg80211_connect_params * sme)1069 wl_set_wpa_version(struct net_device *dev, struct cfg80211_connect_params *sme)
1070 {
1071 struct wl_priv *wl = ndev_to_wl(dev);
1072 struct wl_security *sec;
1073 s32 val = 0;
1074 s32 err = 0;
1075
1076 if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_1)
1077 val = WPA_AUTH_PSK | WPA_AUTH_UNSPECIFIED;
1078 else if (sme->crypto.wpa_versions & NL80211_WPA_VERSION_2)
1079 val = WPA2_AUTH_PSK | WPA2_AUTH_UNSPECIFIED;
1080 else
1081 val = WPA_AUTH_DISABLED;
1082 WL_DBG("setting wpa_auth to 0x%0x\n", val);
1083 err = wl_dev_intvar_set(dev, "wpa_auth", val);
1084 if (unlikely(err)) {
1085 WL_ERR("set wpa_auth failed (%d)\n", err);
1086 return err;
1087 }
1088 sec = wl_read_prof(wl, WL_PROF_SEC);
1089 sec->wpa_versions = sme->crypto.wpa_versions;
1090 return err;
1091 }
1092
1093 static s32
wl_set_auth_type(struct net_device * dev,struct cfg80211_connect_params * sme)1094 wl_set_auth_type(struct net_device *dev, struct cfg80211_connect_params *sme)
1095 {
1096 struct wl_priv *wl = ndev_to_wl(dev);
1097 struct wl_security *sec;
1098 s32 val = 0;
1099 s32 err = 0;
1100
1101 switch (sme->auth_type) {
1102 case NL80211_AUTHTYPE_OPEN_SYSTEM:
1103 val = 0;
1104 WL_DBG("open system\n");
1105 break;
1106 case NL80211_AUTHTYPE_SHARED_KEY:
1107 val = 1;
1108 WL_DBG("shared key\n");
1109 break;
1110 case NL80211_AUTHTYPE_AUTOMATIC:
1111 val = 2;
1112 WL_DBG("automatic\n");
1113 break;
1114 case NL80211_AUTHTYPE_NETWORK_EAP:
1115 WL_DBG("network eap\n");
1116 default:
1117 val = 2;
1118 WL_ERR("invalid auth type (%d)\n", sme->auth_type);
1119 break;
1120 }
1121
1122 err = wl_dev_intvar_set(dev, "auth", val);
1123 if (unlikely(err)) {
1124 WL_ERR("set auth failed (%d)\n", err);
1125 return err;
1126 }
1127 sec = wl_read_prof(wl, WL_PROF_SEC);
1128 sec->auth_type = sme->auth_type;
1129 return err;
1130 }
1131
1132 static s32
wl_set_set_cipher(struct net_device * dev,struct cfg80211_connect_params * sme)1133 wl_set_set_cipher(struct net_device *dev, struct cfg80211_connect_params *sme)
1134 {
1135 struct wl_priv *wl = ndev_to_wl(dev);
1136 struct wl_security *sec;
1137 s32 pval = 0;
1138 s32 gval = 0;
1139 s32 err = 0;
1140
1141 if (sme->crypto.n_ciphers_pairwise) {
1142 switch (sme->crypto.ciphers_pairwise[0]) {
1143 case WLAN_CIPHER_SUITE_WEP40:
1144 case WLAN_CIPHER_SUITE_WEP104:
1145 pval = WEP_ENABLED;
1146 break;
1147 case WLAN_CIPHER_SUITE_TKIP:
1148 pval = TKIP_ENABLED;
1149 break;
1150 case WLAN_CIPHER_SUITE_CCMP:
1151 pval = AES_ENABLED;
1152 break;
1153 case WLAN_CIPHER_SUITE_AES_CMAC:
1154 pval = AES_ENABLED;
1155 break;
1156 default:
1157 WL_ERR("invalid cipher pairwise (%d)\n",
1158 sme->crypto.ciphers_pairwise[0]);
1159 return -EINVAL;
1160 }
1161 }
1162 if (sme->crypto.cipher_group) {
1163 switch (sme->crypto.cipher_group) {
1164 case WLAN_CIPHER_SUITE_WEP40:
1165 case WLAN_CIPHER_SUITE_WEP104:
1166 gval = WEP_ENABLED;
1167 break;
1168 case WLAN_CIPHER_SUITE_TKIP:
1169 gval = TKIP_ENABLED;
1170 break;
1171 case WLAN_CIPHER_SUITE_CCMP:
1172 gval = AES_ENABLED;
1173 break;
1174 case WLAN_CIPHER_SUITE_AES_CMAC:
1175 gval = AES_ENABLED;
1176 break;
1177 default:
1178 WL_ERR("invalid cipher group (%d)\n",
1179 sme->crypto.cipher_group);
1180 return -EINVAL;
1181 }
1182 }
1183
1184 WL_DBG("pval (%d) gval (%d)\n", pval, gval);
1185 err = wl_dev_intvar_set(dev, "wsec", pval | gval);
1186 if (unlikely(err)) {
1187 WL_ERR("error (%d)\n", err);
1188 return err;
1189 }
1190
1191 sec = wl_read_prof(wl, WL_PROF_SEC);
1192 sec->cipher_pairwise = sme->crypto.ciphers_pairwise[0];
1193 sec->cipher_group = sme->crypto.cipher_group;
1194
1195 return err;
1196 }
1197
1198 static s32
wl_set_key_mgmt(struct net_device * dev,struct cfg80211_connect_params * sme)1199 wl_set_key_mgmt(struct net_device *dev, struct cfg80211_connect_params *sme)
1200 {
1201 struct wl_priv *wl = ndev_to_wl(dev);
1202 struct wl_security *sec;
1203 s32 val = 0;
1204 s32 err = 0;
1205
1206 if (sme->crypto.n_akm_suites) {
1207 err = wl_dev_intvar_get(dev, "wpa_auth", &val);
1208 if (unlikely(err)) {
1209 WL_ERR("could not get wpa_auth (%d)\n", err);
1210 return err;
1211 }
1212 if (val & (WPA_AUTH_PSK | WPA_AUTH_UNSPECIFIED)) {
1213 switch (sme->crypto.akm_suites[0]) {
1214 case WLAN_AKM_SUITE_8021X:
1215 val = WPA_AUTH_UNSPECIFIED;
1216 break;
1217 case WLAN_AKM_SUITE_PSK:
1218 val = WPA_AUTH_PSK;
1219 break;
1220 default:
1221 WL_ERR("invalid cipher group (%d)\n",
1222 sme->crypto.cipher_group);
1223 return -EINVAL;
1224 }
1225 } else if (val & (WPA2_AUTH_PSK | WPA2_AUTH_UNSPECIFIED)) {
1226 switch (sme->crypto.akm_suites[0]) {
1227 case WLAN_AKM_SUITE_8021X:
1228 val = WPA2_AUTH_UNSPECIFIED;
1229 break;
1230 case WLAN_AKM_SUITE_PSK:
1231 val = WPA2_AUTH_PSK;
1232 break;
1233 default:
1234 WL_ERR("invalid cipher group (%d)\n",
1235 sme->crypto.cipher_group);
1236 return -EINVAL;
1237 }
1238 }
1239
1240 WL_DBG("setting wpa_auth to %d\n", val);
1241 err = wl_dev_intvar_set(dev, "wpa_auth", val);
1242 if (unlikely(err)) {
1243 WL_ERR("could not set wpa_auth (%d)\n", err);
1244 return err;
1245 }
1246 }
1247 sec = wl_read_prof(wl, WL_PROF_SEC);
1248 sec->wpa_auth = sme->crypto.akm_suites[0];
1249
1250 return err;
1251 }
1252
1253 static s32
wl_set_set_sharedkey(struct net_device * dev,struct cfg80211_connect_params * sme)1254 wl_set_set_sharedkey(struct net_device *dev,
1255 struct cfg80211_connect_params *sme)
1256 {
1257 struct wl_priv *wl = ndev_to_wl(dev);
1258 struct wl_security *sec;
1259 struct wl_wsec_key key;
1260 s32 val;
1261 s32 err = 0;
1262
1263 WL_DBG("key len (%d)\n", sme->key_len);
1264 if (sme->key_len) {
1265 sec = wl_read_prof(wl, WL_PROF_SEC);
1266 WL_DBG("wpa_versions 0x%x cipher_pairwise 0x%x\n",
1267 sec->wpa_versions, sec->cipher_pairwise);
1268 if (!
1269 (sec->wpa_versions & (NL80211_WPA_VERSION_1 |
1270 NL80211_WPA_VERSION_2))
1271 && (sec->cipher_pairwise & (WLAN_CIPHER_SUITE_WEP40 |
1272 WLAN_CIPHER_SUITE_WEP104))) {
1273 memset(&key, 0, sizeof(key));
1274 key.len = (u32) sme->key_len;
1275 key.index = (u32) sme->key_idx;
1276 if (unlikely(key.len > sizeof(key.data))) {
1277 WL_ERR("Too long key length (%u)\n", key.len);
1278 return -EINVAL;
1279 }
1280 memcpy(key.data, sme->key, key.len);
1281 key.flags = WL_PRIMARY_KEY;
1282 switch (sec->cipher_pairwise) {
1283 case WLAN_CIPHER_SUITE_WEP40:
1284 key.algo = CRYPTO_ALGO_WEP1;
1285 break;
1286 case WLAN_CIPHER_SUITE_WEP104:
1287 key.algo = CRYPTO_ALGO_WEP128;
1288 break;
1289 default:
1290 WL_ERR("Invalid algorithm (%d)\n",
1291 sme->crypto.ciphers_pairwise[0]);
1292 return -EINVAL;
1293 }
1294 /* Set the new key/index */
1295 WL_DBG("key length (%d) key index (%d) algo (%d)\n",
1296 key.len, key.index, key.algo);
1297 WL_DBG("key \"%s\"\n", key.data);
1298 swap_key_from_BE(&key);
1299 err = wl_dev_ioctl(dev, WLC_SET_KEY, &key,
1300 sizeof(key));
1301 if (unlikely(err)) {
1302 WL_ERR("WLC_SET_KEY error (%d)\n", err);
1303 return err;
1304 }
1305 if (sec->auth_type == NL80211_AUTHTYPE_OPEN_SYSTEM) {
1306 WL_DBG("set auth_type to shared key\n");
1307 val = 1; /* shared key */
1308 err = wl_dev_intvar_set(dev, "auth", val);
1309 if (unlikely(err)) {
1310 WL_ERR("set auth failed (%d)\n", err);
1311 return err;
1312 }
1313 }
1314 }
1315 }
1316 return err;
1317 }
1318
1319 static s32
wl_cfg80211_connect(struct wiphy * wiphy,struct net_device * dev,struct cfg80211_connect_params * sme)1320 wl_cfg80211_connect(struct wiphy *wiphy, struct net_device *dev,
1321 struct cfg80211_connect_params *sme)
1322 {
1323 struct wl_priv *wl = wiphy_to_wl(wiphy);
1324 struct ieee80211_channel *chan = sme->channel;
1325 struct wl_join_params join_params;
1326 size_t join_params_size;
1327
1328 s32 err = 0;
1329
1330 CHECK_SYS_UP();
1331 if (unlikely(!sme->ssid)) {
1332 WL_ERR("Invalid ssid\n");
1333 return -EOPNOTSUPP;
1334 }
1335 if (chan) {
1336 wl->channel = ieee80211_frequency_to_channel(chan->center_freq);
1337 WL_DBG("channel (%d), center_req (%d)\n",
1338 wl->channel, chan->center_freq);
1339 }
1340 WL_DBG("ie (%p), ie_len (%zd)\n", sme->ie, sme->ie_len);
1341 err = wl_set_wpa_version(dev, sme);
1342 if (unlikely(err))
1343 return err;
1344
1345 err = wl_set_auth_type(dev, sme);
1346 if (unlikely(err))
1347 return err;
1348
1349 err = wl_set_set_cipher(dev, sme);
1350 if (unlikely(err))
1351 return err;
1352
1353 err = wl_set_key_mgmt(dev, sme);
1354 if (unlikely(err))
1355 return err;
1356
1357 err = wl_set_set_sharedkey(dev, sme);
1358 if (unlikely(err))
1359 return err;
1360
1361 wl_update_prof(wl, NULL, sme->bssid, WL_PROF_BSSID);
1362 /*
1363 ** Join with specific BSSID and cached SSID
1364 ** If SSID is zero join based on BSSID only
1365 */
1366 memset(&join_params, 0, sizeof(join_params));
1367 join_params_size = sizeof(join_params.ssid);
1368
1369 join_params.ssid.SSID_len = min(sizeof(join_params.ssid.SSID), sme->ssid_len);
1370 memcpy(&join_params.ssid.SSID, sme->ssid, join_params.ssid.SSID_len);
1371 join_params.ssid.SSID_len = cpu_to_le32(join_params.ssid.SSID_len);
1372 wl_update_prof(wl, NULL, &join_params.ssid, WL_PROF_SSID);
1373 memcpy(join_params.params.bssid, ether_bcast, ETH_ALEN);
1374
1375 wl_ch_to_chanspec(wl->channel, &join_params, &join_params_size);
1376 WL_DBG("join_param_size %zu\n", join_params_size);
1377
1378 if (join_params.ssid.SSID_len < IEEE80211_MAX_SSID_LEN) {
1379 WL_DBG("ssid \"%s\", len (%d)\n",
1380 join_params.ssid.SSID, join_params.ssid.SSID_len);
1381 }
1382 err = wl_dev_ioctl(dev, WLC_SET_SSID, &join_params, join_params_size);
1383 if (unlikely(err)) {
1384 WL_ERR("error (%d)\n", err);
1385 return err;
1386 }
1387 set_bit(WL_STATUS_CONNECTING, &wl->status);
1388
1389 return err;
1390 }
1391
1392 static s32
wl_cfg80211_disconnect(struct wiphy * wiphy,struct net_device * dev,u16 reason_code)1393 wl_cfg80211_disconnect(struct wiphy *wiphy, struct net_device *dev,
1394 u16 reason_code)
1395 {
1396 struct wl_priv *wl = wiphy_to_wl(wiphy);
1397 scb_val_t scbval;
1398 bool act = false;
1399 s32 err = 0;
1400
1401 WL_DBG("Reason %d\n", reason_code);
1402 CHECK_SYS_UP();
1403 act = *(bool *) wl_read_prof(wl, WL_PROF_ACT);
1404 if (likely(act)) {
1405 scbval.val = reason_code;
1406 memcpy(&scbval.ea, &wl->bssid, ETH_ALEN);
1407 scbval.val = cpu_to_le32(scbval.val);
1408 err = wl_dev_ioctl(dev, WLC_DISASSOC, &scbval,
1409 sizeof(scb_val_t));
1410 if (unlikely(err)) {
1411 WL_ERR("error (%d)\n", err);
1412 return err;
1413 }
1414 }
1415
1416 return err;
1417 }
1418
1419 static s32
wl_cfg80211_set_tx_power(struct wiphy * wiphy,enum nl80211_tx_power_setting type,s32 dbm)1420 wl_cfg80211_set_tx_power(struct wiphy *wiphy,
1421 enum nl80211_tx_power_setting type, s32 dbm)
1422 {
1423
1424 struct wl_priv *wl = wiphy_to_wl(wiphy);
1425 struct net_device *ndev = wl_to_ndev(wl);
1426 u16 txpwrmw;
1427 s32 err = 0;
1428 s32 disable = 0;
1429
1430 CHECK_SYS_UP();
1431 switch (type) {
1432 case NL80211_TX_POWER_AUTOMATIC:
1433 break;
1434 case NL80211_TX_POWER_LIMITED:
1435 if (dbm < 0) {
1436 WL_ERR("TX_POWER_LIMITED - dbm is negative\n");
1437 return -EINVAL;
1438 }
1439 break;
1440 case NL80211_TX_POWER_FIXED:
1441 if (dbm < 0) {
1442 WL_ERR("TX_POWER_FIXED - dbm is negative\n");
1443 return -EINVAL;
1444 }
1445 break;
1446 }
1447 /* Make sure radio is off or on as far as software is concerned */
1448 disable = WL_RADIO_SW_DISABLE << 16;
1449 disable = cpu_to_le32(disable);
1450 err = wl_dev_ioctl(ndev, WLC_SET_RADIO, &disable, sizeof(disable));
1451 if (unlikely(err)) {
1452 WL_ERR("WLC_SET_RADIO error (%d)\n", err);
1453 return err;
1454 }
1455
1456 if (dbm > 0xffff)
1457 txpwrmw = 0xffff;
1458 else
1459 txpwrmw = (u16) dbm;
1460 err = wl_dev_intvar_set(ndev, "qtxpower",
1461 (s32) (bcm_mw_to_qdbm(txpwrmw)));
1462 if (unlikely(err)) {
1463 WL_ERR("qtxpower error (%d)\n", err);
1464 return err;
1465 }
1466 wl->conf->tx_power = dbm;
1467
1468 return err;
1469 }
1470
wl_cfg80211_get_tx_power(struct wiphy * wiphy,s32 * dbm)1471 static s32 wl_cfg80211_get_tx_power(struct wiphy *wiphy, s32 *dbm)
1472 {
1473 struct wl_priv *wl = wiphy_to_wl(wiphy);
1474 struct net_device *ndev = wl_to_ndev(wl);
1475 s32 txpwrdbm;
1476 u8 result;
1477 s32 err = 0;
1478
1479 CHECK_SYS_UP();
1480 err = wl_dev_intvar_get(ndev, "qtxpower", &txpwrdbm);
1481 if (unlikely(err)) {
1482 WL_ERR("error (%d)\n", err);
1483 return err;
1484 }
1485 result = (u8) (txpwrdbm & ~WL_TXPWR_OVERRIDE);
1486 *dbm = (s32) bcm_qdbm_to_mw(result);
1487
1488 return err;
1489 }
1490
1491 static s32
wl_cfg80211_config_default_key(struct wiphy * wiphy,struct net_device * dev,u8 key_idx,bool unicast,bool multicast)1492 wl_cfg80211_config_default_key(struct wiphy *wiphy, struct net_device *dev,
1493 u8 key_idx, bool unicast, bool multicast)
1494 {
1495 u32 index;
1496 s32 wsec;
1497 s32 err = 0;
1498
1499 WL_DBG("key index (%d)\n", key_idx);
1500 CHECK_SYS_UP();
1501
1502 err = wl_dev_ioctl(dev, WLC_GET_WSEC, &wsec, sizeof(wsec));
1503 if (unlikely(err)) {
1504 WL_ERR("WLC_GET_WSEC error (%d)\n", err);
1505 return err;
1506 }
1507 wsec = le32_to_cpu(wsec);
1508 if (wsec & WEP_ENABLED) {
1509 /* Just select a new current key */
1510 index = (u32) key_idx;
1511 index = cpu_to_le32(index);
1512 err = wl_dev_ioctl(dev, WLC_SET_KEY_PRIMARY, &index,
1513 sizeof(index));
1514 if (unlikely(err)) {
1515 WL_ERR("error (%d)\n", err);
1516 }
1517 }
1518 return err;
1519 }
1520
1521 static s32
wl_add_keyext(struct wiphy * wiphy,struct net_device * dev,u8 key_idx,const u8 * mac_addr,struct key_params * params)1522 wl_add_keyext(struct wiphy *wiphy, struct net_device *dev,
1523 u8 key_idx, const u8 *mac_addr, struct key_params *params)
1524 {
1525 struct wl_wsec_key key;
1526 s32 err = 0;
1527
1528 memset(&key, 0, sizeof(key));
1529 key.index = (u32) key_idx;
1530 /* Instead of bcast for ea address for default wep keys,
1531 driver needs it to be Null */
1532 if (!is_multicast_ether_addr(mac_addr))
1533 memcpy((char *)&key.ea, (void *)mac_addr, ETH_ALEN);
1534 key.len = (u32) params->key_len;
1535 /* check for key index change */
1536 if (key.len == 0) {
1537 /* key delete */
1538 swap_key_from_BE(&key);
1539 err = wl_dev_ioctl(dev, WLC_SET_KEY, &key, sizeof(key));
1540 if (unlikely(err)) {
1541 WL_ERR("key delete error (%d)\n", err);
1542 return err;
1543 }
1544 } else {
1545 if (key.len > sizeof(key.data)) {
1546 WL_ERR("Invalid key length (%d)\n", key.len);
1547 return -EINVAL;
1548 }
1549
1550 WL_DBG("Setting the key index %d\n", key.index);
1551 memcpy(key.data, params->key, key.len);
1552
1553 if (params->cipher == WLAN_CIPHER_SUITE_TKIP) {
1554 u8 keybuf[8];
1555 memcpy(keybuf, &key.data[24], sizeof(keybuf));
1556 memcpy(&key.data[24], &key.data[16], sizeof(keybuf));
1557 memcpy(&key.data[16], keybuf, sizeof(keybuf));
1558 }
1559
1560 /* if IW_ENCODE_EXT_RX_SEQ_VALID set */
1561 if (params->seq && params->seq_len == 6) {
1562 /* rx iv */
1563 u8 *ivptr;
1564 ivptr = (u8 *) params->seq;
1565 key.rxiv.hi = (ivptr[5] << 24) | (ivptr[4] << 16) |
1566 (ivptr[3] << 8) | ivptr[2];
1567 key.rxiv.lo = (ivptr[1] << 8) | ivptr[0];
1568 key.iv_initialized = true;
1569 }
1570
1571 switch (params->cipher) {
1572 case WLAN_CIPHER_SUITE_WEP40:
1573 key.algo = CRYPTO_ALGO_WEP1;
1574 WL_DBG("WLAN_CIPHER_SUITE_WEP40\n");
1575 break;
1576 case WLAN_CIPHER_SUITE_WEP104:
1577 key.algo = CRYPTO_ALGO_WEP128;
1578 WL_DBG("WLAN_CIPHER_SUITE_WEP104\n");
1579 break;
1580 case WLAN_CIPHER_SUITE_TKIP:
1581 key.algo = CRYPTO_ALGO_TKIP;
1582 WL_DBG("WLAN_CIPHER_SUITE_TKIP\n");
1583 break;
1584 case WLAN_CIPHER_SUITE_AES_CMAC:
1585 key.algo = CRYPTO_ALGO_AES_CCM;
1586 WL_DBG("WLAN_CIPHER_SUITE_AES_CMAC\n");
1587 break;
1588 case WLAN_CIPHER_SUITE_CCMP:
1589 key.algo = CRYPTO_ALGO_AES_CCM;
1590 WL_DBG("WLAN_CIPHER_SUITE_CCMP\n");
1591 break;
1592 default:
1593 WL_ERR("Invalid cipher (0x%x)\n", params->cipher);
1594 return -EINVAL;
1595 }
1596 swap_key_from_BE(&key);
1597
1598 dhd_wait_pend8021x(dev);
1599 err = wl_dev_ioctl(dev, WLC_SET_KEY, &key, sizeof(key));
1600 if (unlikely(err)) {
1601 WL_ERR("WLC_SET_KEY error (%d)\n", err);
1602 return err;
1603 }
1604 }
1605 return err;
1606 }
1607
1608 static s32
wl_cfg80211_add_key(struct wiphy * wiphy,struct net_device * dev,u8 key_idx,bool pairwise,const u8 * mac_addr,struct key_params * params)1609 wl_cfg80211_add_key(struct wiphy *wiphy, struct net_device *dev,
1610 u8 key_idx, bool pairwise, const u8 *mac_addr,
1611 struct key_params *params)
1612 {
1613 struct wl_wsec_key key;
1614 s32 val;
1615 s32 wsec;
1616 s32 err = 0;
1617
1618 WL_DBG("key index (%d)\n", key_idx);
1619 CHECK_SYS_UP();
1620
1621 if (mac_addr)
1622 return wl_add_keyext(wiphy, dev, key_idx, mac_addr, params);
1623 memset(&key, 0, sizeof(key));
1624
1625 key.len = (u32) params->key_len;
1626 key.index = (u32) key_idx;
1627
1628 if (unlikely(key.len > sizeof(key.data))) {
1629 WL_ERR("Too long key length (%u)\n", key.len);
1630 return -EINVAL;
1631 }
1632 memcpy(key.data, params->key, key.len);
1633
1634 key.flags = WL_PRIMARY_KEY;
1635 switch (params->cipher) {
1636 case WLAN_CIPHER_SUITE_WEP40:
1637 key.algo = CRYPTO_ALGO_WEP1;
1638 WL_DBG("WLAN_CIPHER_SUITE_WEP40\n");
1639 break;
1640 case WLAN_CIPHER_SUITE_WEP104:
1641 key.algo = CRYPTO_ALGO_WEP128;
1642 WL_DBG("WLAN_CIPHER_SUITE_WEP104\n");
1643 break;
1644 case WLAN_CIPHER_SUITE_TKIP:
1645 key.algo = CRYPTO_ALGO_TKIP;
1646 WL_DBG("WLAN_CIPHER_SUITE_TKIP\n");
1647 break;
1648 case WLAN_CIPHER_SUITE_AES_CMAC:
1649 key.algo = CRYPTO_ALGO_AES_CCM;
1650 WL_DBG("WLAN_CIPHER_SUITE_AES_CMAC\n");
1651 break;
1652 case WLAN_CIPHER_SUITE_CCMP:
1653 key.algo = CRYPTO_ALGO_AES_CCM;
1654 WL_DBG("WLAN_CIPHER_SUITE_CCMP\n");
1655 break;
1656 default:
1657 WL_ERR("Invalid cipher (0x%x)\n", params->cipher);
1658 return -EINVAL;
1659 }
1660
1661 /* Set the new key/index */
1662 swap_key_from_BE(&key);
1663 err = wl_dev_ioctl(dev, WLC_SET_KEY, &key, sizeof(key));
1664 if (unlikely(err)) {
1665 WL_ERR("WLC_SET_KEY error (%d)\n", err);
1666 return err;
1667 }
1668
1669 val = WEP_ENABLED;
1670 err = wl_dev_intvar_get(dev, "wsec", &wsec);
1671 if (unlikely(err)) {
1672 WL_ERR("get wsec error (%d)\n", err);
1673 return err;
1674 }
1675 wsec &= ~(WEP_ENABLED);
1676 wsec |= val;
1677 err = wl_dev_intvar_set(dev, "wsec", wsec);
1678 if (unlikely(err)) {
1679 WL_ERR("set wsec error (%d)\n", err);
1680 return err;
1681 }
1682
1683 val = 1; /* assume shared key. otherwise 0 */
1684 val = cpu_to_le32(val);
1685 err = wl_dev_ioctl(dev, WLC_SET_AUTH, &val, sizeof(val));
1686 if (unlikely(err)) {
1687 WL_ERR("WLC_SET_AUTH error (%d)\n", err);
1688 return err;
1689 }
1690 return err;
1691 }
1692
1693 static s32
wl_cfg80211_del_key(struct wiphy * wiphy,struct net_device * dev,u8 key_idx,bool pairwise,const u8 * mac_addr)1694 wl_cfg80211_del_key(struct wiphy *wiphy, struct net_device *dev,
1695 u8 key_idx, bool pairwise, const u8 *mac_addr)
1696 {
1697 struct wl_wsec_key key;
1698 s32 err = 0;
1699 s32 val;
1700 s32 wsec;
1701
1702 CHECK_SYS_UP();
1703 memset(&key, 0, sizeof(key));
1704
1705 key.index = (u32) key_idx;
1706 key.flags = WL_PRIMARY_KEY;
1707 key.algo = CRYPTO_ALGO_OFF;
1708
1709 WL_DBG("key index (%d)\n", key_idx);
1710 /* Set the new key/index */
1711 swap_key_from_BE(&key);
1712 err = wl_dev_ioctl(dev, WLC_SET_KEY, &key, sizeof(key));
1713 if (unlikely(err)) {
1714 if (err == -EINVAL) {
1715 if (key.index >= DOT11_MAX_DEFAULT_KEYS) {
1716 /* we ignore this key index in this case */
1717 WL_DBG("invalid key index (%d)\n", key_idx);
1718 }
1719 } else {
1720 WL_ERR("WLC_SET_KEY error (%d)\n", err);
1721 }
1722 return err;
1723 }
1724
1725 val = 0;
1726 err = wl_dev_intvar_get(dev, "wsec", &wsec);
1727 if (unlikely(err)) {
1728 WL_ERR("get wsec error (%d)\n", err);
1729 return err;
1730 }
1731 wsec &= ~(WEP_ENABLED);
1732 wsec |= val;
1733 err = wl_dev_intvar_set(dev, "wsec", wsec);
1734 if (unlikely(err)) {
1735 WL_ERR("set wsec error (%d)\n", err);
1736 return err;
1737 }
1738
1739 val = 0; /* assume open key. otherwise 1 */
1740 val = cpu_to_le32(val);
1741 err = wl_dev_ioctl(dev, WLC_SET_AUTH, &val, sizeof(val));
1742 if (unlikely(err)) {
1743 WL_ERR("WLC_SET_AUTH error (%d)\n", err);
1744 return err;
1745 }
1746 return err;
1747 }
1748
1749 static s32
wl_cfg80211_get_key(struct wiphy * wiphy,struct net_device * dev,u8 key_idx,bool pairwise,const u8 * mac_addr,void * cookie,void (* callback)(void * cookie,struct key_params * params))1750 wl_cfg80211_get_key(struct wiphy *wiphy, struct net_device *dev,
1751 u8 key_idx, bool pairwise, const u8 *mac_addr, void *cookie,
1752 void (*callback) (void *cookie, struct key_params * params))
1753 {
1754 struct key_params params;
1755 struct wl_wsec_key key;
1756 struct wl_priv *wl = wiphy_to_wl(wiphy);
1757 struct wl_security *sec;
1758 s32 wsec;
1759 s32 err = 0;
1760
1761 WL_DBG("key index (%d)\n", key_idx);
1762 CHECK_SYS_UP();
1763
1764 memset(&key, 0, sizeof(key));
1765 key.index = key_idx;
1766 swap_key_to_BE(&key);
1767 memset(¶ms, 0, sizeof(params));
1768 params.key_len = (u8) min_t(u8, WLAN_MAX_KEY_LEN, key.len);
1769 memcpy(params.key, key.data, params.key_len);
1770
1771 err = wl_dev_ioctl(dev, WLC_GET_WSEC, &wsec, sizeof(wsec));
1772 if (unlikely(err)) {
1773 WL_ERR("WLC_GET_WSEC error (%d)\n", err);
1774 return err;
1775 }
1776 wsec = le32_to_cpu(wsec);
1777 switch (wsec) {
1778 case WEP_ENABLED:
1779 sec = wl_read_prof(wl, WL_PROF_SEC);
1780 if (sec->cipher_pairwise & WLAN_CIPHER_SUITE_WEP40) {
1781 params.cipher = WLAN_CIPHER_SUITE_WEP40;
1782 WL_DBG("WLAN_CIPHER_SUITE_WEP40\n");
1783 } else if (sec->cipher_pairwise & WLAN_CIPHER_SUITE_WEP104) {
1784 params.cipher = WLAN_CIPHER_SUITE_WEP104;
1785 WL_DBG("WLAN_CIPHER_SUITE_WEP104\n");
1786 }
1787 break;
1788 case TKIP_ENABLED:
1789 params.cipher = WLAN_CIPHER_SUITE_TKIP;
1790 WL_DBG("WLAN_CIPHER_SUITE_TKIP\n");
1791 break;
1792 case AES_ENABLED:
1793 params.cipher = WLAN_CIPHER_SUITE_AES_CMAC;
1794 WL_DBG("WLAN_CIPHER_SUITE_AES_CMAC\n");
1795 break;
1796 default:
1797 WL_ERR("Invalid algo (0x%x)\n", wsec);
1798 return -EINVAL;
1799 }
1800
1801 callback(cookie, ¶ms);
1802 return err;
1803 }
1804
1805 static s32
wl_cfg80211_config_default_mgmt_key(struct wiphy * wiphy,struct net_device * dev,u8 key_idx)1806 wl_cfg80211_config_default_mgmt_key(struct wiphy *wiphy,
1807 struct net_device *dev, u8 key_idx)
1808 {
1809 WL_INFO("Not supported\n");
1810 CHECK_SYS_UP();
1811 return -EOPNOTSUPP;
1812 }
1813
1814 static s32
wl_cfg80211_get_station(struct wiphy * wiphy,struct net_device * dev,u8 * mac,struct station_info * sinfo)1815 wl_cfg80211_get_station(struct wiphy *wiphy, struct net_device *dev,
1816 u8 *mac, struct station_info *sinfo)
1817 {
1818 struct wl_priv *wl = wiphy_to_wl(wiphy);
1819 scb_val_t scb_val;
1820 int rssi;
1821 s32 rate;
1822 s32 err = 0;
1823
1824 CHECK_SYS_UP();
1825 if (unlikely
1826 (memcmp(mac, wl_read_prof(wl, WL_PROF_BSSID), ETH_ALEN))) {
1827 WL_ERR("Wrong Mac address\n");
1828 return -ENOENT;
1829 }
1830
1831 /* Report the current tx rate */
1832 err = wl_dev_ioctl(dev, WLC_GET_RATE, &rate, sizeof(rate));
1833 if (err) {
1834 WL_ERR("Could not get rate (%d)\n", err);
1835 } else {
1836 rate = le32_to_cpu(rate);
1837 sinfo->filled |= STATION_INFO_TX_BITRATE;
1838 sinfo->txrate.legacy = rate * 5;
1839 WL_DBG("Rate %d Mbps\n", rate / 2);
1840 }
1841
1842 if (test_bit(WL_STATUS_CONNECTED, &wl->status)) {
1843 scb_val.val = 0;
1844 err = wl_dev_ioctl(dev, WLC_GET_RSSI, &scb_val,
1845 sizeof(scb_val_t));
1846 if (unlikely(err)) {
1847 WL_ERR("Could not get rssi (%d)\n", err);
1848 return err;
1849 }
1850 rssi = le32_to_cpu(scb_val.val);
1851 sinfo->filled |= STATION_INFO_SIGNAL;
1852 sinfo->signal = rssi;
1853 WL_DBG("RSSI %d dBm\n", rssi);
1854 }
1855
1856 return err;
1857 }
1858
1859 static s32
wl_cfg80211_set_power_mgmt(struct wiphy * wiphy,struct net_device * dev,bool enabled,s32 timeout)1860 wl_cfg80211_set_power_mgmt(struct wiphy *wiphy, struct net_device *dev,
1861 bool enabled, s32 timeout)
1862 {
1863 s32 pm;
1864 s32 err = 0;
1865
1866 CHECK_SYS_UP();
1867 pm = enabled ? PM_FAST : PM_OFF;
1868 pm = cpu_to_le32(pm);
1869 WL_DBG("power save %s\n", (pm ? "enabled" : "disabled"));
1870 err = wl_dev_ioctl(dev, WLC_SET_PM, &pm, sizeof(pm));
1871 if (unlikely(err)) {
1872 if (err == -ENODEV)
1873 WL_DBG("net_device is not ready yet\n");
1874 else
1875 WL_ERR("error (%d)\n", err);
1876 return err;
1877 }
1878 return err;
1879 }
1880
wl_find_msb(u16 bit16)1881 static __used u32 wl_find_msb(u16 bit16)
1882 {
1883 u32 ret = 0;
1884
1885 if (bit16 & 0xff00) {
1886 ret += 8;
1887 bit16 >>= 8;
1888 }
1889
1890 if (bit16 & 0xf0) {
1891 ret += 4;
1892 bit16 >>= 4;
1893 }
1894
1895 if (bit16 & 0xc) {
1896 ret += 2;
1897 bit16 >>= 2;
1898 }
1899
1900 if (bit16 & 2)
1901 ret += bit16 & 2;
1902 else if (bit16)
1903 ret += bit16;
1904
1905 return ret;
1906 }
1907
1908 static s32
wl_cfg80211_set_bitrate_mask(struct wiphy * wiphy,struct net_device * dev,const u8 * addr,const struct cfg80211_bitrate_mask * mask)1909 wl_cfg80211_set_bitrate_mask(struct wiphy *wiphy, struct net_device *dev,
1910 const u8 *addr,
1911 const struct cfg80211_bitrate_mask *mask)
1912 {
1913 struct wl_rateset rateset;
1914 s32 rate;
1915 s32 val;
1916 s32 err_bg;
1917 s32 err_a;
1918 u32 legacy;
1919 s32 err = 0;
1920
1921 CHECK_SYS_UP();
1922 /* addr param is always NULL. ignore it */
1923 /* Get current rateset */
1924 err = wl_dev_ioctl(dev, WLC_GET_CURR_RATESET, &rateset,
1925 sizeof(rateset));
1926 if (unlikely(err)) {
1927 WL_ERR("could not get current rateset (%d)\n", err);
1928 return err;
1929 }
1930
1931 rateset.count = le32_to_cpu(rateset.count);
1932
1933 legacy = wl_find_msb(mask->control[IEEE80211_BAND_2GHZ].legacy);
1934 if (!legacy)
1935 legacy = wl_find_msb(mask->control[IEEE80211_BAND_5GHZ].legacy);
1936
1937 val = wl_g_rates[legacy - 1].bitrate * 100000;
1938
1939 if (val < rateset.count) {
1940 /* Select rate by rateset index */
1941 rate = rateset.rates[val] & 0x7f;
1942 } else {
1943 /* Specified rate in bps */
1944 rate = val / 500000;
1945 }
1946
1947 WL_DBG("rate %d mbps\n", rate / 2);
1948
1949 /*
1950 *
1951 * Set rate override,
1952 * Since the is a/b/g-blind, both a/bg_rate are enforced.
1953 */
1954 err_bg = wl_dev_intvar_set(dev, "bg_rate", rate);
1955 err_a = wl_dev_intvar_set(dev, "a_rate", rate);
1956 if (unlikely(err_bg && err_a)) {
1957 WL_ERR("could not set fixed rate (%d) (%d)\n", err_bg, err_a);
1958 return err_bg | err_a;
1959 }
1960
1961 return err;
1962 }
1963
wl_cfg80211_resume(struct wiphy * wiphy)1964 static s32 wl_cfg80211_resume(struct wiphy *wiphy)
1965 {
1966 s32 err = 0;
1967
1968 CHECK_SYS_UP();
1969 wl_invoke_iscan(wiphy_to_wl(wiphy));
1970
1971 return err;
1972 }
1973
wl_cfg80211_suspend(struct wiphy * wiphy)1974 static s32 wl_cfg80211_suspend(struct wiphy *wiphy)
1975 {
1976 struct wl_priv *wl = wiphy_to_wl(wiphy);
1977 struct net_device *ndev = wl_to_ndev(wl);
1978 s32 err = 0;
1979
1980 set_bit(WL_STATUS_SCAN_ABORTING, &wl->status);
1981 wl_term_iscan(wl);
1982 if (wl->scan_request) {
1983 cfg80211_scan_done(wl->scan_request, true); /* true means
1984 abort */
1985 wl_set_mpc(ndev, 1);
1986 wl->scan_request = NULL;
1987 }
1988 clear_bit(WL_STATUS_SCANNING, &wl->status);
1989 clear_bit(WL_STATUS_SCAN_ABORTING, &wl->status);
1990
1991 return err;
1992 }
1993
1994 static __used s32
wl_update_pmklist(struct net_device * dev,struct wl_pmk_list * pmk_list,s32 err)1995 wl_update_pmklist(struct net_device *dev, struct wl_pmk_list *pmk_list,
1996 s32 err)
1997 {
1998 int i, j;
1999
2000 WL_DBG("No of elements %d\n", pmk_list->pmkids.npmkid);
2001 for (i = 0; i < pmk_list->pmkids.npmkid; i++) {
2002 WL_DBG("PMKID[%d]: %pM =\n", i,
2003 &pmk_list->pmkids.pmkid[i].BSSID);
2004 for (j = 0; j < WLAN_PMKID_LEN; j++) {
2005 WL_DBG("%02x\n", pmk_list->pmkids.pmkid[i].PMKID[j]);
2006 }
2007 }
2008 if (likely(!err)) {
2009 err = wl_dev_bufvar_set(dev, "pmkid_info", (char *)pmk_list,
2010 sizeof(*pmk_list));
2011 }
2012
2013 return err;
2014 }
2015
2016 static s32
wl_cfg80211_set_pmksa(struct wiphy * wiphy,struct net_device * dev,struct cfg80211_pmksa * pmksa)2017 wl_cfg80211_set_pmksa(struct wiphy *wiphy, struct net_device *dev,
2018 struct cfg80211_pmksa *pmksa)
2019 {
2020 struct wl_priv *wl = wiphy_to_wl(wiphy);
2021 s32 err = 0;
2022 int i;
2023
2024 CHECK_SYS_UP();
2025 for (i = 0; i < wl->pmk_list->pmkids.npmkid; i++)
2026 if (!memcmp(pmksa->bssid, &wl->pmk_list->pmkids.pmkid[i].BSSID,
2027 ETH_ALEN))
2028 break;
2029 if (i < WL_NUM_PMKIDS_MAX) {
2030 memcpy(&wl->pmk_list->pmkids.pmkid[i].BSSID, pmksa->bssid,
2031 ETH_ALEN);
2032 memcpy(&wl->pmk_list->pmkids.pmkid[i].PMKID, pmksa->pmkid,
2033 WLAN_PMKID_LEN);
2034 if (i == wl->pmk_list->pmkids.npmkid)
2035 wl->pmk_list->pmkids.npmkid++;
2036 } else {
2037 err = -EINVAL;
2038 }
2039 WL_DBG("set_pmksa,IW_PMKSA_ADD - PMKID: %pM =\n",
2040 &wl->pmk_list->pmkids.pmkid[wl->pmk_list->pmkids.npmkid].BSSID);
2041 for (i = 0; i < WLAN_PMKID_LEN; i++) {
2042 WL_DBG("%02x\n",
2043 wl->pmk_list->pmkids.pmkid[wl->pmk_list->pmkids.npmkid].
2044 PMKID[i]);
2045 }
2046
2047 err = wl_update_pmklist(dev, wl->pmk_list, err);
2048
2049 return err;
2050 }
2051
2052 static s32
wl_cfg80211_del_pmksa(struct wiphy * wiphy,struct net_device * dev,struct cfg80211_pmksa * pmksa)2053 wl_cfg80211_del_pmksa(struct wiphy *wiphy, struct net_device *dev,
2054 struct cfg80211_pmksa *pmksa)
2055 {
2056 struct wl_priv *wl = wiphy_to_wl(wiphy);
2057 struct _pmkid_list pmkid;
2058 s32 err = 0;
2059 int i;
2060
2061 CHECK_SYS_UP();
2062 memcpy(&pmkid.pmkid[0].BSSID, pmksa->bssid, ETH_ALEN);
2063 memcpy(&pmkid.pmkid[0].PMKID, pmksa->pmkid, WLAN_PMKID_LEN);
2064
2065 WL_DBG("del_pmksa,IW_PMKSA_REMOVE - PMKID: %pM =\n",
2066 &pmkid.pmkid[0].BSSID);
2067 for (i = 0; i < WLAN_PMKID_LEN; i++) {
2068 WL_DBG("%02x\n", pmkid.pmkid[0].PMKID[i]);
2069 }
2070
2071 for (i = 0; i < wl->pmk_list->pmkids.npmkid; i++)
2072 if (!memcmp
2073 (pmksa->bssid, &wl->pmk_list->pmkids.pmkid[i].BSSID,
2074 ETH_ALEN))
2075 break;
2076
2077 if ((wl->pmk_list->pmkids.npmkid > 0)
2078 && (i < wl->pmk_list->pmkids.npmkid)) {
2079 memset(&wl->pmk_list->pmkids.pmkid[i], 0, sizeof(pmkid_t));
2080 for (; i < (wl->pmk_list->pmkids.npmkid - 1); i++) {
2081 memcpy(&wl->pmk_list->pmkids.pmkid[i].BSSID,
2082 &wl->pmk_list->pmkids.pmkid[i + 1].BSSID,
2083 ETH_ALEN);
2084 memcpy(&wl->pmk_list->pmkids.pmkid[i].PMKID,
2085 &wl->pmk_list->pmkids.pmkid[i + 1].PMKID,
2086 WLAN_PMKID_LEN);
2087 }
2088 wl->pmk_list->pmkids.npmkid--;
2089 } else {
2090 err = -EINVAL;
2091 }
2092
2093 err = wl_update_pmklist(dev, wl->pmk_list, err);
2094
2095 return err;
2096
2097 }
2098
2099 static s32
wl_cfg80211_flush_pmksa(struct wiphy * wiphy,struct net_device * dev)2100 wl_cfg80211_flush_pmksa(struct wiphy *wiphy, struct net_device *dev)
2101 {
2102 struct wl_priv *wl = wiphy_to_wl(wiphy);
2103 s32 err = 0;
2104
2105 CHECK_SYS_UP();
2106 memset(wl->pmk_list, 0, sizeof(*wl->pmk_list));
2107 err = wl_update_pmklist(dev, wl->pmk_list, err);
2108 return err;
2109
2110 }
2111
2112 static struct cfg80211_ops wl_cfg80211_ops = {
2113 .change_virtual_intf = wl_cfg80211_change_iface,
2114 .scan = wl_cfg80211_scan,
2115 .set_wiphy_params = wl_cfg80211_set_wiphy_params,
2116 .join_ibss = wl_cfg80211_join_ibss,
2117 .leave_ibss = wl_cfg80211_leave_ibss,
2118 .get_station = wl_cfg80211_get_station,
2119 .set_tx_power = wl_cfg80211_set_tx_power,
2120 .get_tx_power = wl_cfg80211_get_tx_power,
2121 .add_key = wl_cfg80211_add_key,
2122 .del_key = wl_cfg80211_del_key,
2123 .get_key = wl_cfg80211_get_key,
2124 .set_default_key = wl_cfg80211_config_default_key,
2125 .set_default_mgmt_key = wl_cfg80211_config_default_mgmt_key,
2126 .set_power_mgmt = wl_cfg80211_set_power_mgmt,
2127 .set_bitrate_mask = wl_cfg80211_set_bitrate_mask,
2128 .connect = wl_cfg80211_connect,
2129 .disconnect = wl_cfg80211_disconnect,
2130 .suspend = wl_cfg80211_suspend,
2131 .resume = wl_cfg80211_resume,
2132 .set_pmksa = wl_cfg80211_set_pmksa,
2133 .del_pmksa = wl_cfg80211_del_pmksa,
2134 .flush_pmksa = wl_cfg80211_flush_pmksa
2135 };
2136
wl_mode_to_nl80211_iftype(s32 mode)2137 static s32 wl_mode_to_nl80211_iftype(s32 mode)
2138 {
2139 s32 err = 0;
2140
2141 switch (mode) {
2142 case WL_MODE_BSS:
2143 return NL80211_IFTYPE_STATION;
2144 case WL_MODE_IBSS:
2145 return NL80211_IFTYPE_ADHOC;
2146 default:
2147 return NL80211_IFTYPE_UNSPECIFIED;
2148 }
2149
2150 return err;
2151 }
2152
wl_alloc_wdev(s32 sizeof_iface,struct device * dev)2153 static struct wireless_dev *wl_alloc_wdev(s32 sizeof_iface,
2154 struct device *dev)
2155 {
2156 struct wireless_dev *wdev;
2157 s32 err = 0;
2158
2159 wdev = kzalloc(sizeof(*wdev), GFP_KERNEL);
2160 if (unlikely(!wdev)) {
2161 WL_ERR("Could not allocate wireless device\n");
2162 return ERR_PTR(-ENOMEM);
2163 }
2164 wdev->wiphy =
2165 wiphy_new(&wl_cfg80211_ops, sizeof(struct wl_priv) + sizeof_iface);
2166 if (unlikely(!wdev->wiphy)) {
2167 WL_ERR("Couldn not allocate wiphy device\n");
2168 err = -ENOMEM;
2169 goto wiphy_new_out;
2170 }
2171 set_wiphy_dev(wdev->wiphy, dev);
2172 wdev->wiphy->max_scan_ssids = WL_NUM_SCAN_MAX;
2173 wdev->wiphy->max_num_pmkids = WL_NUM_PMKIDS_MAX;
2174 wdev->wiphy->interface_modes =
2175 BIT(NL80211_IFTYPE_STATION) | BIT(NL80211_IFTYPE_ADHOC);
2176 wdev->wiphy->bands[IEEE80211_BAND_2GHZ] = &__wl_band_2ghz;
2177 wdev->wiphy->bands[IEEE80211_BAND_5GHZ] = &__wl_band_5ghz_a; /* Set
2178 * it as 11a by default.
2179 * This will be updated with
2180 * 11n phy tables in
2181 * "ifconfig up"
2182 * if phy has 11n capability
2183 */
2184 wdev->wiphy->signal_type = CFG80211_SIGNAL_TYPE_MBM;
2185 wdev->wiphy->cipher_suites = __wl_cipher_suites;
2186 wdev->wiphy->n_cipher_suites = ARRAY_SIZE(__wl_cipher_suites);
2187 #ifndef WL_POWERSAVE_DISABLED
2188 wdev->wiphy->flags |= WIPHY_FLAG_PS_ON_BY_DEFAULT; /* enable power
2189 * save mode
2190 * by default
2191 */
2192 #else
2193 wdev->wiphy->flags &= ~WIPHY_FLAG_PS_ON_BY_DEFAULT;
2194 #endif /* !WL_POWERSAVE_DISABLED */
2195 err = wiphy_register(wdev->wiphy);
2196 if (unlikely(err < 0)) {
2197 WL_ERR("Couldn not register wiphy device (%d)\n", err);
2198 goto wiphy_register_out;
2199 }
2200 return wdev;
2201
2202 wiphy_register_out:
2203 wiphy_free(wdev->wiphy);
2204
2205 wiphy_new_out:
2206 kfree(wdev);
2207
2208 return ERR_PTR(err);
2209 }
2210
wl_free_wdev(struct wl_priv * wl)2211 static void wl_free_wdev(struct wl_priv *wl)
2212 {
2213 struct wireless_dev *wdev = wl_to_wdev(wl);
2214
2215 if (unlikely(!wdev)) {
2216 WL_ERR("wdev is invalid\n");
2217 return;
2218 }
2219 wiphy_unregister(wdev->wiphy);
2220 wiphy_free(wdev->wiphy);
2221 kfree(wdev);
2222 wl_to_wdev(wl) = NULL;
2223 }
2224
wl_inform_bss(struct wl_priv * wl)2225 static s32 wl_inform_bss(struct wl_priv *wl)
2226 {
2227 struct wl_scan_results *bss_list;
2228 struct wl_bss_info *bi = NULL; /* must be initialized */
2229 s32 err = 0;
2230 int i;
2231
2232 bss_list = wl->bss_list;
2233 if (unlikely(bss_list->version != WL_BSS_INFO_VERSION)) {
2234 WL_ERR("Version %d != WL_BSS_INFO_VERSION\n",
2235 bss_list->version);
2236 return -EOPNOTSUPP;
2237 }
2238 WL_DBG("scanned AP count (%d)\n", bss_list->count);
2239 bi = next_bss(bss_list, bi);
2240 for_each_bss(bss_list, bi, i) {
2241 err = wl_inform_single_bss(wl, bi);
2242 if (unlikely(err))
2243 break;
2244 }
2245 return err;
2246 }
2247
wl_inform_single_bss(struct wl_priv * wl,struct wl_bss_info * bi)2248 static s32 wl_inform_single_bss(struct wl_priv *wl, struct wl_bss_info *bi)
2249 {
2250 struct wiphy *wiphy = wl_to_wiphy(wl);
2251 struct ieee80211_mgmt *mgmt;
2252 struct ieee80211_channel *channel;
2253 struct ieee80211_supported_band *band;
2254 struct wl_cfg80211_bss_info *notif_bss_info;
2255 struct wl_scan_req *sr = wl_to_sr(wl);
2256 struct beacon_proberesp *beacon_proberesp;
2257 s32 mgmt_type;
2258 u32 signal;
2259 u32 freq;
2260 s32 err = 0;
2261
2262 if (unlikely(le32_to_cpu(bi->length) > WL_BSS_INFO_MAX)) {
2263 WL_DBG("Beacon is larger than buffer. Discarding\n");
2264 return err;
2265 }
2266 notif_bss_info =
2267 kzalloc(sizeof(*notif_bss_info) + sizeof(*mgmt) - sizeof(u8) +
2268 WL_BSS_INFO_MAX, GFP_KERNEL);
2269 if (unlikely(!notif_bss_info)) {
2270 WL_ERR("notif_bss_info alloc failed\n");
2271 return -ENOMEM;
2272 }
2273 mgmt = (struct ieee80211_mgmt *)notif_bss_info->frame_buf;
2274 notif_bss_info->channel =
2275 bi->ctl_ch ? bi->ctl_ch : CHSPEC_CHANNEL(bi->chanspec);
2276
2277 if (notif_bss_info->channel <= CH_MAX_2G_CHANNEL)
2278 band = wiphy->bands[IEEE80211_BAND_2GHZ];
2279 else
2280 band = wiphy->bands[IEEE80211_BAND_5GHZ];
2281 notif_bss_info->rssi = bi->RSSI;
2282 memcpy(mgmt->bssid, &bi->BSSID, ETH_ALEN);
2283 mgmt_type = wl->active_scan ?
2284 IEEE80211_STYPE_PROBE_RESP : IEEE80211_STYPE_BEACON;
2285 if (!memcmp(bi->SSID, sr->ssid.SSID, bi->SSID_len)) {
2286 mgmt->frame_control = cpu_to_le16(IEEE80211_FTYPE_MGMT |
2287 mgmt_type);
2288 }
2289 beacon_proberesp = wl->active_scan ?
2290 (struct beacon_proberesp *)&mgmt->u.probe_resp :
2291 (struct beacon_proberesp *)&mgmt->u.beacon;
2292 beacon_proberesp->timestamp = 0;
2293 beacon_proberesp->beacon_int = cpu_to_le16(bi->beacon_period);
2294 beacon_proberesp->capab_info = cpu_to_le16(bi->capability);
2295 wl_rst_ie(wl);
2296 /*
2297 * wl_add_ie is not necessary because it can only add duplicated
2298 * SSID, rate information to frame_buf
2299 */
2300 /*
2301 * wl_add_ie(wl, WLAN_EID_SSID, bi->SSID_len, bi->SSID);
2302 * wl_add_ie(wl, WLAN_EID_SUPP_RATES, bi->rateset.count,
2303 * bi->rateset.rates);
2304 */
2305 wl_mrg_ie(wl, ((u8 *) bi) + bi->ie_offset, bi->ie_length);
2306 wl_cp_ie(wl, beacon_proberesp->variable, WL_BSS_INFO_MAX -
2307 offsetof(struct wl_cfg80211_bss_info, frame_buf));
2308 notif_bss_info->frame_len =
2309 offsetof(struct ieee80211_mgmt,
2310 u.beacon.variable) + wl_get_ielen(wl);
2311 freq = ieee80211_channel_to_frequency(notif_bss_info->channel,
2312 band->band);
2313
2314 channel = ieee80211_get_channel(wiphy, freq);
2315
2316 WL_DBG("SSID : \"%s\", rssi %d, channel %d, capability : 0x04%x, bssid %pM\n",
2317 bi->SSID,
2318 notif_bss_info->rssi, notif_bss_info->channel,
2319 mgmt->u.beacon.capab_info, &bi->BSSID);
2320
2321 signal = notif_bss_info->rssi * 100;
2322 if (unlikely(!cfg80211_inform_bss_frame(wiphy, channel, mgmt,
2323 le16_to_cpu
2324 (notif_bss_info->frame_len),
2325 signal, GFP_KERNEL))) {
2326 WL_ERR("cfg80211_inform_bss_frame error\n");
2327 kfree(notif_bss_info);
2328 return -EINVAL;
2329 }
2330 kfree(notif_bss_info);
2331
2332 return err;
2333 }
2334
wl_is_linkup(struct wl_priv * wl,const wl_event_msg_t * e)2335 static bool wl_is_linkup(struct wl_priv *wl, const wl_event_msg_t *e)
2336 {
2337 u32 event = be32_to_cpu(e->event_type);
2338 u16 flags = be16_to_cpu(e->flags);
2339
2340 if (event == WLC_E_LINK) {
2341 if (flags & WLC_EVENT_MSG_LINK) {
2342 if (wl_is_ibssmode(wl)) {
2343 if (wl_is_ibssstarter(wl)) {
2344 }
2345 } else {
2346 return true;
2347 }
2348 }
2349 }
2350
2351 return false;
2352 }
2353
wl_is_linkdown(struct wl_priv * wl,const wl_event_msg_t * e)2354 static bool wl_is_linkdown(struct wl_priv *wl, const wl_event_msg_t *e)
2355 {
2356 u32 event = be32_to_cpu(e->event_type);
2357 u16 flags = be16_to_cpu(e->flags);
2358
2359 if (event == WLC_E_DEAUTH_IND || event == WLC_E_DISASSOC_IND) {
2360 return true;
2361 } else if (event == WLC_E_LINK) {
2362 if (!(flags & WLC_EVENT_MSG_LINK))
2363 return true;
2364 }
2365
2366 return false;
2367 }
2368
wl_is_nonetwork(struct wl_priv * wl,const wl_event_msg_t * e)2369 static bool wl_is_nonetwork(struct wl_priv *wl, const wl_event_msg_t *e)
2370 {
2371 u32 event = be32_to_cpu(e->event_type);
2372 u32 status = be32_to_cpu(e->status);
2373
2374 if (event == WLC_E_SET_SSID || event == WLC_E_LINK) {
2375 if (status == WLC_E_STATUS_NO_NETWORKS)
2376 return true;
2377 }
2378
2379 return false;
2380 }
2381
2382 static s32
wl_notify_connect_status(struct wl_priv * wl,struct net_device * ndev,const wl_event_msg_t * e,void * data)2383 wl_notify_connect_status(struct wl_priv *wl, struct net_device *ndev,
2384 const wl_event_msg_t *e, void *data)
2385 {
2386 bool act;
2387 s32 err = 0;
2388
2389 if (wl_is_linkup(wl, e)) {
2390 wl_link_up(wl);
2391 if (wl_is_ibssmode(wl)) {
2392 cfg80211_ibss_joined(ndev, (s8 *)&e->addr,
2393 GFP_KERNEL);
2394 WL_DBG("joined in IBSS network\n");
2395 } else {
2396 wl_bss_connect_done(wl, ndev, e, data, true);
2397 WL_DBG("joined in BSS network \"%s\"\n",
2398 ((struct wlc_ssid *)
2399 wl_read_prof(wl, WL_PROF_SSID))->SSID);
2400 }
2401 act = true;
2402 wl_update_prof(wl, e, &act, WL_PROF_ACT);
2403 } else if (wl_is_linkdown(wl, e)) {
2404 cfg80211_disconnected(ndev, 0, NULL, 0, GFP_KERNEL);
2405 clear_bit(WL_STATUS_CONNECTED, &wl->status);
2406 wl_link_down(wl);
2407 wl_init_prof(wl->profile);
2408 } else if (wl_is_nonetwork(wl, e)) {
2409 wl_bss_connect_done(wl, ndev, e, data, false);
2410 }
2411
2412 return err;
2413 }
2414
2415 static s32
wl_notify_roaming_status(struct wl_priv * wl,struct net_device * ndev,const wl_event_msg_t * e,void * data)2416 wl_notify_roaming_status(struct wl_priv *wl, struct net_device *ndev,
2417 const wl_event_msg_t *e, void *data)
2418 {
2419 bool act;
2420 s32 err = 0;
2421
2422 wl_bss_roaming_done(wl, ndev, e, data);
2423 act = true;
2424 wl_update_prof(wl, e, &act, WL_PROF_ACT);
2425
2426 return err;
2427 }
2428
2429 static __used s32
wl_dev_bufvar_set(struct net_device * dev,s8 * name,s8 * buf,s32 len)2430 wl_dev_bufvar_set(struct net_device *dev, s8 *name, s8 *buf, s32 len)
2431 {
2432 struct wl_priv *wl = ndev_to_wl(dev);
2433 u32 buflen;
2434
2435 buflen = bcm_mkiovar(name, buf, len, wl->ioctl_buf, WL_IOCTL_LEN_MAX);
2436 BUG_ON(!buflen);
2437
2438 return wl_dev_ioctl(dev, WLC_SET_VAR, wl->ioctl_buf, buflen);
2439 }
2440
2441 static s32
wl_dev_bufvar_get(struct net_device * dev,s8 * name,s8 * buf,s32 buf_len)2442 wl_dev_bufvar_get(struct net_device *dev, s8 *name, s8 *buf,
2443 s32 buf_len)
2444 {
2445 struct wl_priv *wl = ndev_to_wl(dev);
2446 u32 len;
2447 s32 err = 0;
2448
2449 len = bcm_mkiovar(name, NULL, 0, wl->ioctl_buf, WL_IOCTL_LEN_MAX);
2450 BUG_ON(!len);
2451 err = wl_dev_ioctl(dev, WLC_GET_VAR, (void *)wl->ioctl_buf,
2452 WL_IOCTL_LEN_MAX);
2453 if (unlikely(err)) {
2454 WL_ERR("error (%d)\n", err);
2455 return err;
2456 }
2457 memcpy(buf, wl->ioctl_buf, buf_len);
2458
2459 return err;
2460 }
2461
wl_get_assoc_ies(struct wl_priv * wl)2462 static s32 wl_get_assoc_ies(struct wl_priv *wl)
2463 {
2464 struct net_device *ndev = wl_to_ndev(wl);
2465 struct wl_assoc_ielen *assoc_info;
2466 struct wl_connect_info *conn_info = wl_to_conn(wl);
2467 u32 req_len;
2468 u32 resp_len;
2469 s32 err = 0;
2470
2471 err = wl_dev_bufvar_get(ndev, "assoc_info", wl->extra_buf,
2472 WL_ASSOC_INFO_MAX);
2473 if (unlikely(err)) {
2474 WL_ERR("could not get assoc info (%d)\n", err);
2475 return err;
2476 }
2477 assoc_info = (struct wl_assoc_ielen *)wl->extra_buf;
2478 req_len = assoc_info->req_len;
2479 resp_len = assoc_info->resp_len;
2480 if (req_len) {
2481 err = wl_dev_bufvar_get(ndev, "assoc_req_ies", wl->extra_buf,
2482 WL_ASSOC_INFO_MAX);
2483 if (unlikely(err)) {
2484 WL_ERR("could not get assoc req (%d)\n", err);
2485 return err;
2486 }
2487 conn_info->req_ie_len = req_len;
2488 conn_info->req_ie =
2489 kmemdup(wl->extra_buf, conn_info->req_ie_len, GFP_KERNEL);
2490 } else {
2491 conn_info->req_ie_len = 0;
2492 conn_info->req_ie = NULL;
2493 }
2494 if (resp_len) {
2495 err = wl_dev_bufvar_get(ndev, "assoc_resp_ies", wl->extra_buf,
2496 WL_ASSOC_INFO_MAX);
2497 if (unlikely(err)) {
2498 WL_ERR("could not get assoc resp (%d)\n", err);
2499 return err;
2500 }
2501 conn_info->resp_ie_len = resp_len;
2502 conn_info->resp_ie =
2503 kmemdup(wl->extra_buf, conn_info->resp_ie_len, GFP_KERNEL);
2504 } else {
2505 conn_info->resp_ie_len = 0;
2506 conn_info->resp_ie = NULL;
2507 }
2508 WL_DBG("req len (%d) resp len (%d)\n",
2509 conn_info->req_ie_len, conn_info->resp_ie_len);
2510
2511 return err;
2512 }
2513
wl_ch_to_chanspec(int ch,struct wl_join_params * join_params,size_t * join_params_size)2514 static void wl_ch_to_chanspec(int ch, struct wl_join_params *join_params,
2515 size_t *join_params_size)
2516 {
2517 chanspec_t chanspec = 0;
2518
2519 if (ch != 0) {
2520 join_params->params.chanspec_num = 1;
2521 join_params->params.chanspec_list[0] = ch;
2522
2523 if (join_params->params.chanspec_list[0])
2524 chanspec |= WL_CHANSPEC_BAND_2G;
2525 else
2526 chanspec |= WL_CHANSPEC_BAND_5G;
2527
2528 chanspec |= WL_CHANSPEC_BW_20;
2529 chanspec |= WL_CHANSPEC_CTL_SB_NONE;
2530
2531 *join_params_size += WL_ASSOC_PARAMS_FIXED_SIZE +
2532 join_params->params.chanspec_num * sizeof(chanspec_t);
2533
2534 join_params->params.chanspec_list[0] &= WL_CHANSPEC_CHAN_MASK;
2535 join_params->params.chanspec_list[0] |= chanspec;
2536 join_params->params.chanspec_list[0] =
2537 cpu_to_le16(join_params->params.chanspec_list[0]);
2538
2539 join_params->params.chanspec_num =
2540 cpu_to_le32(join_params->params.chanspec_num);
2541
2542 WL_DBG("join_params->params.chanspec_list[0]= %#X, channel %d, chanspec %#X\n",
2543 join_params->params.chanspec_list[0], ch, chanspec);
2544 }
2545 }
2546
wl_update_bss_info(struct wl_priv * wl)2547 static s32 wl_update_bss_info(struct wl_priv *wl)
2548 {
2549 struct cfg80211_bss *bss;
2550 struct wl_bss_info *bi;
2551 struct wlc_ssid *ssid;
2552 struct bcm_tlv *tim;
2553 u16 beacon_interval;
2554 u8 dtim_period;
2555 size_t ie_len;
2556 u8 *ie;
2557 s32 err = 0;
2558
2559 if (wl_is_ibssmode(wl))
2560 return err;
2561
2562 ssid = (struct wlc_ssid *)wl_read_prof(wl, WL_PROF_SSID);
2563 bss =
2564 cfg80211_get_bss(wl_to_wiphy(wl), NULL, (s8 *)&wl->bssid,
2565 ssid->SSID, ssid->SSID_len, WLAN_CAPABILITY_ESS,
2566 WLAN_CAPABILITY_ESS);
2567
2568 rtnl_lock();
2569 if (unlikely(!bss)) {
2570 WL_DBG("Could not find the AP\n");
2571 *(u32 *) wl->extra_buf = cpu_to_le32(WL_EXTRA_BUF_MAX);
2572 err = wl_dev_ioctl(wl_to_ndev(wl), WLC_GET_BSS_INFO,
2573 wl->extra_buf, WL_EXTRA_BUF_MAX);
2574 if (unlikely(err)) {
2575 WL_ERR("Could not get bss info %d\n", err);
2576 goto update_bss_info_out;
2577 }
2578 bi = (struct wl_bss_info *)(wl->extra_buf + 4);
2579 if (unlikely(memcmp(&bi->BSSID, &wl->bssid, ETH_ALEN))) {
2580 err = -EIO;
2581 goto update_bss_info_out;
2582 }
2583 err = wl_inform_single_bss(wl, bi);
2584 if (unlikely(err))
2585 goto update_bss_info_out;
2586
2587 ie = ((u8 *)bi) + bi->ie_offset;
2588 ie_len = bi->ie_length;
2589 beacon_interval = cpu_to_le16(bi->beacon_period);
2590 } else {
2591 WL_DBG("Found the AP in the list - BSSID %pM\n", bss->bssid);
2592 ie = bss->information_elements;
2593 ie_len = bss->len_information_elements;
2594 beacon_interval = bss->beacon_interval;
2595 cfg80211_put_bss(bss);
2596 }
2597
2598 tim = bcm_parse_tlvs(ie, ie_len, WLAN_EID_TIM);
2599 if (tim) {
2600 dtim_period = tim->data[1];
2601 } else {
2602 /*
2603 * active scan was done so we could not get dtim
2604 * information out of probe response.
2605 * so we speficially query dtim information to dongle.
2606 */
2607 err = wl_dev_ioctl(wl_to_ndev(wl), WLC_GET_DTIMPRD,
2608 &dtim_period, sizeof(dtim_period));
2609 if (unlikely(err)) {
2610 WL_ERR("WLC_GET_DTIMPRD error (%d)\n", err);
2611 goto update_bss_info_out;
2612 }
2613 }
2614
2615 wl_update_prof(wl, NULL, &beacon_interval, WL_PROF_BEACONINT);
2616 wl_update_prof(wl, NULL, &dtim_period, WL_PROF_DTIMPERIOD);
2617
2618 update_bss_info_out:
2619 rtnl_unlock();
2620 return err;
2621 }
2622
2623 static s32
wl_bss_roaming_done(struct wl_priv * wl,struct net_device * ndev,const wl_event_msg_t * e,void * data)2624 wl_bss_roaming_done(struct wl_priv *wl, struct net_device *ndev,
2625 const wl_event_msg_t *e, void *data)
2626 {
2627 struct wl_connect_info *conn_info = wl_to_conn(wl);
2628 s32 err = 0;
2629
2630 wl_get_assoc_ies(wl);
2631 memcpy(&wl->bssid, &e->addr, ETH_ALEN);
2632 wl_update_bss_info(wl);
2633 cfg80211_roamed(ndev,
2634 (u8 *)&wl->bssid,
2635 conn_info->req_ie, conn_info->req_ie_len,
2636 conn_info->resp_ie, conn_info->resp_ie_len, GFP_KERNEL);
2637 WL_DBG("Report roaming result\n");
2638
2639 set_bit(WL_STATUS_CONNECTED, &wl->status);
2640
2641 return err;
2642 }
2643
2644 static s32
wl_bss_connect_done(struct wl_priv * wl,struct net_device * ndev,const wl_event_msg_t * e,void * data,bool completed)2645 wl_bss_connect_done(struct wl_priv *wl, struct net_device *ndev,
2646 const wl_event_msg_t *e, void *data, bool completed)
2647 {
2648 struct wl_connect_info *conn_info = wl_to_conn(wl);
2649 s32 err = 0;
2650
2651 wl_get_assoc_ies(wl);
2652 memcpy(&wl->bssid, &e->addr, ETH_ALEN);
2653 wl_update_bss_info(wl);
2654 if (test_and_clear_bit(WL_STATUS_CONNECTING, &wl->status)) {
2655 cfg80211_connect_result(ndev,
2656 (u8 *)&wl->bssid,
2657 conn_info->req_ie,
2658 conn_info->req_ie_len,
2659 conn_info->resp_ie,
2660 conn_info->resp_ie_len,
2661 completed ? WLAN_STATUS_SUCCESS : WLAN_STATUS_AUTH_TIMEOUT,
2662 GFP_KERNEL);
2663 WL_DBG("Report connect result - connection %s\n",
2664 completed ? "succeeded" : "failed");
2665 } else {
2666 cfg80211_roamed(ndev,
2667 (u8 *)&wl->bssid,
2668 conn_info->req_ie, conn_info->req_ie_len,
2669 conn_info->resp_ie, conn_info->resp_ie_len,
2670 GFP_KERNEL);
2671 WL_DBG("Report roaming result\n");
2672 }
2673 set_bit(WL_STATUS_CONNECTED, &wl->status);
2674
2675 return err;
2676 }
2677
2678 static s32
wl_notify_mic_status(struct wl_priv * wl,struct net_device * ndev,const wl_event_msg_t * e,void * data)2679 wl_notify_mic_status(struct wl_priv *wl, struct net_device *ndev,
2680 const wl_event_msg_t *e, void *data)
2681 {
2682 u16 flags = be16_to_cpu(e->flags);
2683 enum nl80211_key_type key_type;
2684
2685 rtnl_lock();
2686 if (flags & WLC_EVENT_MSG_GROUP)
2687 key_type = NL80211_KEYTYPE_GROUP;
2688 else
2689 key_type = NL80211_KEYTYPE_PAIRWISE;
2690
2691 cfg80211_michael_mic_failure(ndev, (u8 *)&e->addr, key_type, -1,
2692 NULL, GFP_KERNEL);
2693 rtnl_unlock();
2694
2695 return 0;
2696 }
2697
2698 static s32
wl_notify_scan_status(struct wl_priv * wl,struct net_device * ndev,const wl_event_msg_t * e,void * data)2699 wl_notify_scan_status(struct wl_priv *wl, struct net_device *ndev,
2700 const wl_event_msg_t *e, void *data)
2701 {
2702 struct channel_info channel_inform;
2703 struct wl_scan_results *bss_list;
2704 u32 len = WL_SCAN_BUF_MAX;
2705 s32 err = 0;
2706
2707 if (wl->iscan_on && wl->iscan_kickstart)
2708 return wl_wakeup_iscan(wl_to_iscan(wl));
2709
2710 if (unlikely(!test_and_clear_bit(WL_STATUS_SCANNING, &wl->status))) {
2711 WL_ERR("Scan complete while device not scanning\n");
2712 return -EINVAL;
2713 }
2714 if (unlikely(!wl->scan_request)) {
2715 }
2716 rtnl_lock();
2717 err = wl_dev_ioctl(ndev, WLC_GET_CHANNEL, &channel_inform,
2718 sizeof(channel_inform));
2719 if (unlikely(err)) {
2720 WL_ERR("scan busy (%d)\n", err);
2721 goto scan_done_out;
2722 }
2723 channel_inform.scan_channel = le32_to_cpu(channel_inform.scan_channel);
2724 if (unlikely(channel_inform.scan_channel)) {
2725
2726 WL_DBG("channel_inform.scan_channel (%d)\n",
2727 channel_inform.scan_channel);
2728 }
2729 wl->bss_list = wl->scan_results;
2730 bss_list = wl->bss_list;
2731 memset(bss_list, 0, len);
2732 bss_list->buflen = cpu_to_le32(len);
2733 err = wl_dev_ioctl(ndev, WLC_SCAN_RESULTS, bss_list, len);
2734 if (unlikely(err)) {
2735 WL_ERR("%s Scan_results error (%d)\n", ndev->name, err);
2736 err = -EINVAL;
2737 goto scan_done_out;
2738 }
2739 bss_list->buflen = le32_to_cpu(bss_list->buflen);
2740 bss_list->version = le32_to_cpu(bss_list->version);
2741 bss_list->count = le32_to_cpu(bss_list->count);
2742
2743 err = wl_inform_bss(wl);
2744 if (err)
2745 goto scan_done_out;
2746
2747 scan_done_out:
2748 if (wl->scan_request) {
2749 cfg80211_scan_done(wl->scan_request, false);
2750 wl_set_mpc(ndev, 1);
2751 wl->scan_request = NULL;
2752 }
2753 rtnl_unlock();
2754 return err;
2755 }
2756
wl_init_conf(struct wl_conf * conf)2757 static void wl_init_conf(struct wl_conf *conf)
2758 {
2759 conf->mode = (u32)-1;
2760 conf->frag_threshold = (u32)-1;
2761 conf->rts_threshold = (u32)-1;
2762 conf->retry_short = (u32)-1;
2763 conf->retry_long = (u32)-1;
2764 conf->tx_power = -1;
2765 }
2766
wl_init_prof(struct wl_profile * prof)2767 static void wl_init_prof(struct wl_profile *prof)
2768 {
2769 memset(prof, 0, sizeof(*prof));
2770 }
2771
wl_init_eloop_handler(struct wl_event_loop * el)2772 static void wl_init_eloop_handler(struct wl_event_loop *el)
2773 {
2774 memset(el, 0, sizeof(*el));
2775 el->handler[WLC_E_SCAN_COMPLETE] = wl_notify_scan_status;
2776 el->handler[WLC_E_JOIN] = wl_notify_connect_status;
2777 el->handler[WLC_E_LINK] = wl_notify_connect_status;
2778 el->handler[WLC_E_DEAUTH_IND] = wl_notify_connect_status;
2779 el->handler[WLC_E_DISASSOC_IND] = wl_notify_connect_status;
2780 el->handler[WLC_E_ASSOC_IND] = wl_notify_connect_status;
2781 el->handler[WLC_E_REASSOC_IND] = wl_notify_connect_status;
2782 el->handler[WLC_E_ROAM] = wl_notify_roaming_status;
2783 el->handler[WLC_E_MIC_ERROR] = wl_notify_mic_status;
2784 el->handler[WLC_E_SET_SSID] = wl_notify_connect_status;
2785 }
2786
wl_init_priv_mem(struct wl_priv * wl)2787 static s32 wl_init_priv_mem(struct wl_priv *wl)
2788 {
2789 wl->scan_results = kzalloc(WL_SCAN_BUF_MAX, GFP_KERNEL);
2790 if (unlikely(!wl->scan_results)) {
2791 WL_ERR("Scan results alloc failed\n");
2792 goto init_priv_mem_out;
2793 }
2794 wl->conf = kzalloc(sizeof(*wl->conf), GFP_KERNEL);
2795 if (unlikely(!wl->conf)) {
2796 WL_ERR("wl_conf alloc failed\n");
2797 goto init_priv_mem_out;
2798 }
2799 wl->profile = kzalloc(sizeof(*wl->profile), GFP_KERNEL);
2800 if (unlikely(!wl->profile)) {
2801 WL_ERR("wl_profile alloc failed\n");
2802 goto init_priv_mem_out;
2803 }
2804 wl->bss_info = kzalloc(WL_BSS_INFO_MAX, GFP_KERNEL);
2805 if (unlikely(!wl->bss_info)) {
2806 WL_ERR("Bss information alloc failed\n");
2807 goto init_priv_mem_out;
2808 }
2809 wl->scan_req_int = kzalloc(sizeof(*wl->scan_req_int), GFP_KERNEL);
2810 if (unlikely(!wl->scan_req_int)) {
2811 WL_ERR("Scan req alloc failed\n");
2812 goto init_priv_mem_out;
2813 }
2814 wl->ioctl_buf = kzalloc(WL_IOCTL_LEN_MAX, GFP_KERNEL);
2815 if (unlikely(!wl->ioctl_buf)) {
2816 WL_ERR("Ioctl buf alloc failed\n");
2817 goto init_priv_mem_out;
2818 }
2819 wl->extra_buf = kzalloc(WL_EXTRA_BUF_MAX, GFP_KERNEL);
2820 if (unlikely(!wl->extra_buf)) {
2821 WL_ERR("Extra buf alloc failed\n");
2822 goto init_priv_mem_out;
2823 }
2824 wl->iscan = kzalloc(sizeof(*wl->iscan), GFP_KERNEL);
2825 if (unlikely(!wl->iscan)) {
2826 WL_ERR("Iscan buf alloc failed\n");
2827 goto init_priv_mem_out;
2828 }
2829 wl->fw = kzalloc(sizeof(*wl->fw), GFP_KERNEL);
2830 if (unlikely(!wl->fw)) {
2831 WL_ERR("fw object alloc failed\n");
2832 goto init_priv_mem_out;
2833 }
2834 wl->pmk_list = kzalloc(sizeof(*wl->pmk_list), GFP_KERNEL);
2835 if (unlikely(!wl->pmk_list)) {
2836 WL_ERR("pmk list alloc failed\n");
2837 goto init_priv_mem_out;
2838 }
2839
2840 return 0;
2841
2842 init_priv_mem_out:
2843 wl_deinit_priv_mem(wl);
2844
2845 return -ENOMEM;
2846 }
2847
wl_deinit_priv_mem(struct wl_priv * wl)2848 static void wl_deinit_priv_mem(struct wl_priv *wl)
2849 {
2850 kfree(wl->scan_results);
2851 wl->scan_results = NULL;
2852 kfree(wl->bss_info);
2853 wl->bss_info = NULL;
2854 kfree(wl->conf);
2855 wl->conf = NULL;
2856 kfree(wl->profile);
2857 wl->profile = NULL;
2858 kfree(wl->scan_req_int);
2859 wl->scan_req_int = NULL;
2860 kfree(wl->ioctl_buf);
2861 wl->ioctl_buf = NULL;
2862 kfree(wl->extra_buf);
2863 wl->extra_buf = NULL;
2864 kfree(wl->iscan);
2865 wl->iscan = NULL;
2866 kfree(wl->fw);
2867 wl->fw = NULL;
2868 kfree(wl->pmk_list);
2869 wl->pmk_list = NULL;
2870 }
2871
wl_create_event_handler(struct wl_priv * wl)2872 static s32 wl_create_event_handler(struct wl_priv *wl)
2873 {
2874 sema_init(&wl->event_sync, 0);
2875 wl->event_tsk = kthread_run(wl_event_handler, wl, "wl_event_handler");
2876 if (IS_ERR(wl->event_tsk)) {
2877 wl->event_tsk = NULL;
2878 WL_ERR("failed to create event thread\n");
2879 return -ENOMEM;
2880 }
2881 return 0;
2882 }
2883
wl_destroy_event_handler(struct wl_priv * wl)2884 static void wl_destroy_event_handler(struct wl_priv *wl)
2885 {
2886 if (wl->event_tsk) {
2887 send_sig(SIGTERM, wl->event_tsk, 1);
2888 kthread_stop(wl->event_tsk);
2889 wl->event_tsk = NULL;
2890 }
2891 }
2892
wl_term_iscan(struct wl_priv * wl)2893 static void wl_term_iscan(struct wl_priv *wl)
2894 {
2895 struct wl_iscan_ctrl *iscan = wl_to_iscan(wl);
2896
2897 if (wl->iscan_on && iscan->tsk) {
2898 iscan->state = WL_ISCAN_STATE_IDLE;
2899 send_sig(SIGTERM, iscan->tsk, 1);
2900 kthread_stop(iscan->tsk);
2901 iscan->tsk = NULL;
2902 }
2903 }
2904
wl_notify_iscan_complete(struct wl_iscan_ctrl * iscan,bool aborted)2905 static void wl_notify_iscan_complete(struct wl_iscan_ctrl *iscan, bool aborted)
2906 {
2907 struct wl_priv *wl = iscan_to_wl(iscan);
2908 struct net_device *ndev = wl_to_ndev(wl);
2909
2910 if (unlikely(!test_and_clear_bit(WL_STATUS_SCANNING, &wl->status))) {
2911 WL_ERR("Scan complete while device not scanning\n");
2912 return;
2913 }
2914 if (likely(wl->scan_request)) {
2915 cfg80211_scan_done(wl->scan_request, aborted);
2916 wl_set_mpc(ndev, 1);
2917 wl->scan_request = NULL;
2918 }
2919 wl->iscan_kickstart = false;
2920 }
2921
wl_wakeup_iscan(struct wl_iscan_ctrl * iscan)2922 static s32 wl_wakeup_iscan(struct wl_iscan_ctrl *iscan)
2923 {
2924 if (likely(iscan->state != WL_ISCAN_STATE_IDLE)) {
2925 WL_DBG("wake up iscan\n");
2926 up(&iscan->sync);
2927 return 0;
2928 }
2929
2930 return -EIO;
2931 }
2932
2933 static s32
wl_get_iscan_results(struct wl_iscan_ctrl * iscan,u32 * status,struct wl_scan_results ** bss_list)2934 wl_get_iscan_results(struct wl_iscan_ctrl *iscan, u32 *status,
2935 struct wl_scan_results **bss_list)
2936 {
2937 struct wl_iscan_results list;
2938 struct wl_scan_results *results;
2939 struct wl_iscan_results *list_buf;
2940 s32 err = 0;
2941
2942 memset(iscan->scan_buf, 0, WL_ISCAN_BUF_MAX);
2943 list_buf = (struct wl_iscan_results *)iscan->scan_buf;
2944 results = &list_buf->results;
2945 results->buflen = WL_ISCAN_RESULTS_FIXED_SIZE;
2946 results->version = 0;
2947 results->count = 0;
2948
2949 memset(&list, 0, sizeof(list));
2950 list.results.buflen = cpu_to_le32(WL_ISCAN_BUF_MAX);
2951 err = wl_dev_iovar_getbuf(iscan->dev, "iscanresults", &list,
2952 WL_ISCAN_RESULTS_FIXED_SIZE, iscan->scan_buf,
2953 WL_ISCAN_BUF_MAX);
2954 if (unlikely(err)) {
2955 WL_ERR("error (%d)\n", err);
2956 return err;
2957 }
2958 results->buflen = le32_to_cpu(results->buflen);
2959 results->version = le32_to_cpu(results->version);
2960 results->count = le32_to_cpu(results->count);
2961 WL_DBG("results->count = %d\n", results->count);
2962 WL_DBG("results->buflen = %d\n", results->buflen);
2963 *status = le32_to_cpu(list_buf->status);
2964 *bss_list = results;
2965
2966 return err;
2967 }
2968
wl_iscan_done(struct wl_priv * wl)2969 static s32 wl_iscan_done(struct wl_priv *wl)
2970 {
2971 struct wl_iscan_ctrl *iscan = wl->iscan;
2972 s32 err = 0;
2973
2974 iscan->state = WL_ISCAN_STATE_IDLE;
2975 rtnl_lock();
2976 wl_inform_bss(wl);
2977 wl_notify_iscan_complete(iscan, false);
2978 rtnl_unlock();
2979
2980 return err;
2981 }
2982
wl_iscan_pending(struct wl_priv * wl)2983 static s32 wl_iscan_pending(struct wl_priv *wl)
2984 {
2985 struct wl_iscan_ctrl *iscan = wl->iscan;
2986 s32 err = 0;
2987
2988 /* Reschedule the timer */
2989 mod_timer(&iscan->timer, jiffies + iscan->timer_ms * HZ / 1000);
2990 iscan->timer_on = 1;
2991
2992 return err;
2993 }
2994
wl_iscan_inprogress(struct wl_priv * wl)2995 static s32 wl_iscan_inprogress(struct wl_priv *wl)
2996 {
2997 struct wl_iscan_ctrl *iscan = wl->iscan;
2998 s32 err = 0;
2999
3000 rtnl_lock();
3001 wl_inform_bss(wl);
3002 wl_run_iscan(iscan, NULL, WL_SCAN_ACTION_CONTINUE);
3003 rtnl_unlock();
3004 /* Reschedule the timer */
3005 mod_timer(&iscan->timer, jiffies + iscan->timer_ms * HZ / 1000);
3006 iscan->timer_on = 1;
3007
3008 return err;
3009 }
3010
wl_iscan_aborted(struct wl_priv * wl)3011 static s32 wl_iscan_aborted(struct wl_priv *wl)
3012 {
3013 struct wl_iscan_ctrl *iscan = wl->iscan;
3014 s32 err = 0;
3015
3016 iscan->state = WL_ISCAN_STATE_IDLE;
3017 rtnl_lock();
3018 wl_notify_iscan_complete(iscan, true);
3019 rtnl_unlock();
3020
3021 return err;
3022 }
3023
wl_iscan_thread(void * data)3024 static s32 wl_iscan_thread(void *data)
3025 {
3026 struct sched_param param = {.sched_priority = MAX_RT_PRIO - 1 };
3027 struct wl_iscan_ctrl *iscan = (struct wl_iscan_ctrl *)data;
3028 struct wl_priv *wl = iscan_to_wl(iscan);
3029 struct wl_iscan_eloop *el = &iscan->el;
3030 u32 status;
3031 int err = 0;
3032
3033 sched_setscheduler(current, SCHED_FIFO, ¶m);
3034 allow_signal(SIGTERM);
3035 status = WL_SCAN_RESULTS_PARTIAL;
3036 while (likely(!down_interruptible(&iscan->sync))) {
3037 if (kthread_should_stop())
3038 break;
3039 if (iscan->timer_on) {
3040 del_timer_sync(&iscan->timer);
3041 iscan->timer_on = 0;
3042 }
3043 rtnl_lock();
3044 err = wl_get_iscan_results(iscan, &status, &wl->bss_list);
3045 if (unlikely(err)) {
3046 status = WL_SCAN_RESULTS_ABORTED;
3047 WL_ERR("Abort iscan\n");
3048 }
3049 rtnl_unlock();
3050 el->handler[status] (wl);
3051 }
3052 if (iscan->timer_on) {
3053 del_timer_sync(&iscan->timer);
3054 iscan->timer_on = 0;
3055 }
3056 WL_DBG("%s was terminated\n", __func__);
3057
3058 return 0;
3059 }
3060
wl_iscan_timer(unsigned long data)3061 static void wl_iscan_timer(unsigned long data)
3062 {
3063 struct wl_iscan_ctrl *iscan = (struct wl_iscan_ctrl *)data;
3064
3065 if (iscan) {
3066 iscan->timer_on = 0;
3067 WL_DBG("timer expired\n");
3068 wl_wakeup_iscan(iscan);
3069 }
3070 }
3071
wl_invoke_iscan(struct wl_priv * wl)3072 static s32 wl_invoke_iscan(struct wl_priv *wl)
3073 {
3074 struct wl_iscan_ctrl *iscan = wl_to_iscan(wl);
3075 int err = 0;
3076
3077 if (wl->iscan_on && !iscan->tsk) {
3078 iscan->state = WL_ISCAN_STATE_IDLE;
3079 sema_init(&iscan->sync, 0);
3080 iscan->tsk = kthread_run(wl_iscan_thread, iscan, "wl_iscan");
3081 if (IS_ERR(iscan->tsk)) {
3082 WL_ERR("Could not create iscan thread\n");
3083 iscan->tsk = NULL;
3084 return -ENOMEM;
3085 }
3086 }
3087
3088 return err;
3089 }
3090
wl_init_iscan_eloop(struct wl_iscan_eloop * el)3091 static void wl_init_iscan_eloop(struct wl_iscan_eloop *el)
3092 {
3093 memset(el, 0, sizeof(*el));
3094 el->handler[WL_SCAN_RESULTS_SUCCESS] = wl_iscan_done;
3095 el->handler[WL_SCAN_RESULTS_PARTIAL] = wl_iscan_inprogress;
3096 el->handler[WL_SCAN_RESULTS_PENDING] = wl_iscan_pending;
3097 el->handler[WL_SCAN_RESULTS_ABORTED] = wl_iscan_aborted;
3098 el->handler[WL_SCAN_RESULTS_NO_MEM] = wl_iscan_aborted;
3099 }
3100
wl_init_iscan(struct wl_priv * wl)3101 static s32 wl_init_iscan(struct wl_priv *wl)
3102 {
3103 struct wl_iscan_ctrl *iscan = wl_to_iscan(wl);
3104 int err = 0;
3105
3106 if (wl->iscan_on) {
3107 iscan->dev = wl_to_ndev(wl);
3108 iscan->state = WL_ISCAN_STATE_IDLE;
3109 wl_init_iscan_eloop(&iscan->el);
3110 iscan->timer_ms = WL_ISCAN_TIMER_INTERVAL_MS;
3111 init_timer(&iscan->timer);
3112 iscan->timer.data = (unsigned long) iscan;
3113 iscan->timer.function = wl_iscan_timer;
3114 sema_init(&iscan->sync, 0);
3115 iscan->tsk = kthread_run(wl_iscan_thread, iscan, "wl_iscan");
3116 if (IS_ERR(iscan->tsk)) {
3117 WL_ERR("Could not create iscan thread\n");
3118 iscan->tsk = NULL;
3119 return -ENOMEM;
3120 }
3121 iscan->data = wl;
3122 }
3123
3124 return err;
3125 }
3126
wl_init_fw(struct wl_fw_ctrl * fw)3127 static void wl_init_fw(struct wl_fw_ctrl *fw)
3128 {
3129 fw->status = 0; /* init fw loading status.
3130 0 means nothing was loaded yet */
3131 }
3132
wl_init_priv(struct wl_priv * wl)3133 static s32 wl_init_priv(struct wl_priv *wl)
3134 {
3135 struct wiphy *wiphy = wl_to_wiphy(wl);
3136 s32 err = 0;
3137
3138 wl->scan_request = NULL;
3139 wl->pwr_save = !!(wiphy->flags & WIPHY_FLAG_PS_ON_BY_DEFAULT);
3140 wl->iscan_on = true; /* iscan on & off switch.
3141 we enable iscan per default */
3142 wl->roam_on = false; /* roam on & off switch.
3143 we enable roam per default */
3144
3145 wl->iscan_kickstart = false;
3146 wl->active_scan = true; /* we do active scan for
3147 specific scan per default */
3148 wl->dongle_up = false; /* dongle is not up yet */
3149 wl_init_eq(wl);
3150 err = wl_init_priv_mem(wl);
3151 if (unlikely(err))
3152 return err;
3153 if (unlikely(wl_create_event_handler(wl)))
3154 return -ENOMEM;
3155 wl_init_eloop_handler(&wl->el);
3156 mutex_init(&wl->usr_sync);
3157 err = wl_init_iscan(wl);
3158 if (unlikely(err))
3159 return err;
3160 wl_init_fw(wl->fw);
3161 wl_init_conf(wl->conf);
3162 wl_init_prof(wl->profile);
3163 wl_link_down(wl);
3164
3165 return err;
3166 }
3167
wl_deinit_priv(struct wl_priv * wl)3168 static void wl_deinit_priv(struct wl_priv *wl)
3169 {
3170 wl_destroy_event_handler(wl);
3171 wl->dongle_up = false; /* dongle down */
3172 wl_flush_eq(wl);
3173 wl_link_down(wl);
3174 wl_term_iscan(wl);
3175 wl_deinit_priv_mem(wl);
3176 }
3177
wl_cfg80211_attach(struct net_device * ndev,void * data)3178 s32 wl_cfg80211_attach(struct net_device *ndev, void *data)
3179 {
3180 struct wireless_dev *wdev;
3181 struct wl_priv *wl;
3182 struct wl_iface *ci;
3183 s32 err = 0;
3184
3185 if (unlikely(!ndev)) {
3186 WL_ERR("ndev is invalid\n");
3187 return -ENODEV;
3188 }
3189 wl_cfg80211_dev = kzalloc(sizeof(struct wl_dev), GFP_KERNEL);
3190 if (unlikely(!wl_cfg80211_dev)) {
3191 WL_ERR("wl_cfg80211_dev is invalid\n");
3192 return -ENOMEM;
3193 }
3194 WL_DBG("func %p\n", wl_cfg80211_get_sdio_func());
3195 wdev = wl_alloc_wdev(sizeof(struct wl_iface), &wl_cfg80211_get_sdio_func()->dev);
3196 if (IS_ERR(wdev))
3197 return -ENOMEM;
3198
3199 wdev->iftype = wl_mode_to_nl80211_iftype(WL_MODE_BSS);
3200 wl = wdev_to_wl(wdev);
3201 wl->wdev = wdev;
3202 wl->pub = data;
3203 ci = (struct wl_iface *)wl_to_ci(wl);
3204 ci->wl = wl;
3205 ndev->ieee80211_ptr = wdev;
3206 SET_NETDEV_DEV(ndev, wiphy_dev(wdev->wiphy));
3207 wdev->netdev = ndev;
3208 err = wl_init_priv(wl);
3209 if (unlikely(err)) {
3210 WL_ERR("Failed to init iwm_priv (%d)\n", err);
3211 goto cfg80211_attach_out;
3212 }
3213 wl_set_drvdata(wl_cfg80211_dev, ci);
3214 set_bit(WL_STATUS_READY, &wl->status);
3215
3216 return err;
3217
3218 cfg80211_attach_out:
3219 wl_free_wdev(wl);
3220 return err;
3221 }
3222
wl_cfg80211_detach(void)3223 void wl_cfg80211_detach(void)
3224 {
3225 struct wl_priv *wl;
3226
3227 wl = WL_PRIV_GET();
3228
3229 wl_deinit_priv(wl);
3230 wl_free_wdev(wl);
3231 wl_set_drvdata(wl_cfg80211_dev, NULL);
3232 kfree(wl_cfg80211_dev);
3233 wl_cfg80211_dev = NULL;
3234 wl_clear_sdio_func();
3235 }
3236
wl_wakeup_event(struct wl_priv * wl)3237 static void wl_wakeup_event(struct wl_priv *wl)
3238 {
3239 up(&wl->event_sync);
3240 }
3241
wl_event_handler(void * data)3242 static s32 wl_event_handler(void *data)
3243 {
3244 struct wl_priv *wl = (struct wl_priv *)data;
3245 struct sched_param param = {.sched_priority = MAX_RT_PRIO - 1 };
3246 struct wl_event_q *e;
3247
3248 sched_setscheduler(current, SCHED_FIFO, ¶m);
3249 allow_signal(SIGTERM);
3250 while (likely(!down_interruptible(&wl->event_sync))) {
3251 if (kthread_should_stop())
3252 break;
3253 e = wl_deq_event(wl);
3254 if (unlikely(!e)) {
3255 WL_ERR("event queue empty...\n");
3256 BUG();
3257 }
3258 WL_DBG("event type (%d)\n", e->etype);
3259 if (wl->el.handler[e->etype]) {
3260 wl->el.handler[e->etype] (wl, wl_to_ndev(wl), &e->emsg,
3261 e->edata);
3262 } else {
3263 WL_DBG("Unknown Event (%d): ignoring\n", e->etype);
3264 }
3265 wl_put_event(e);
3266 }
3267 WL_DBG("%s was terminated\n", __func__);
3268 return 0;
3269 }
3270
3271 void
wl_cfg80211_event(struct net_device * ndev,const wl_event_msg_t * e,void * data)3272 wl_cfg80211_event(struct net_device *ndev, const wl_event_msg_t * e, void *data)
3273 {
3274 u32 event_type = be32_to_cpu(e->event_type);
3275 struct wl_priv *wl = ndev_to_wl(ndev);
3276 #if (WL_DBG_LEVEL > 0)
3277 s8 *estr = (event_type <= sizeof(wl_dbg_estr) / WL_DBG_ESTR_MAX - 1) ?
3278 wl_dbg_estr[event_type] : (s8 *) "Unknown";
3279 #endif /* (WL_DBG_LEVEL > 0) */
3280 WL_DBG("event_type (%d):" "WLC_E_" "%s\n", event_type, estr);
3281 if (likely(!wl_enq_event(wl, event_type, e, data)))
3282 wl_wakeup_event(wl);
3283 }
3284
wl_init_eq(struct wl_priv * wl)3285 static void wl_init_eq(struct wl_priv *wl)
3286 {
3287 wl_init_eq_lock(wl);
3288 INIT_LIST_HEAD(&wl->eq_list);
3289 }
3290
wl_flush_eq(struct wl_priv * wl)3291 static void wl_flush_eq(struct wl_priv *wl)
3292 {
3293 struct wl_event_q *e;
3294
3295 wl_lock_eq(wl);
3296 while (!list_empty(&wl->eq_list)) {
3297 e = list_first_entry(&wl->eq_list, struct wl_event_q, eq_list);
3298 list_del(&e->eq_list);
3299 kfree(e);
3300 }
3301 wl_unlock_eq(wl);
3302 }
3303
3304 /*
3305 * retrieve first queued event from head
3306 */
3307
wl_deq_event(struct wl_priv * wl)3308 static struct wl_event_q *wl_deq_event(struct wl_priv *wl)
3309 {
3310 struct wl_event_q *e = NULL;
3311
3312 wl_lock_eq(wl);
3313 if (likely(!list_empty(&wl->eq_list))) {
3314 e = list_first_entry(&wl->eq_list, struct wl_event_q, eq_list);
3315 list_del(&e->eq_list);
3316 }
3317 wl_unlock_eq(wl);
3318
3319 return e;
3320 }
3321
3322 /*
3323 ** push event to tail of the queue
3324 */
3325
3326 static s32
wl_enq_event(struct wl_priv * wl,u32 event,const wl_event_msg_t * msg,void * data)3327 wl_enq_event(struct wl_priv *wl, u32 event, const wl_event_msg_t *msg,
3328 void *data)
3329 {
3330 struct wl_event_q *e;
3331 s32 err = 0;
3332
3333 e = kzalloc(sizeof(struct wl_event_q), GFP_KERNEL);
3334 if (unlikely(!e)) {
3335 WL_ERR("event alloc failed\n");
3336 return -ENOMEM;
3337 }
3338
3339 e->etype = event;
3340 memcpy(&e->emsg, msg, sizeof(wl_event_msg_t));
3341 if (data) {
3342 }
3343 wl_lock_eq(wl);
3344 list_add_tail(&e->eq_list, &wl->eq_list);
3345 wl_unlock_eq(wl);
3346
3347 return err;
3348 }
3349
wl_put_event(struct wl_event_q * e)3350 static void wl_put_event(struct wl_event_q *e)
3351 {
3352 kfree(e);
3353 }
3354
wl_cfg80211_sdio_func(void * func)3355 void wl_cfg80211_sdio_func(void *func)
3356 {
3357 cfg80211_sdio_func = (struct sdio_func *)func;
3358 }
3359
wl_clear_sdio_func(void)3360 static void wl_clear_sdio_func(void)
3361 {
3362 cfg80211_sdio_func = NULL;
3363 }
3364
wl_cfg80211_get_sdio_func(void)3365 struct sdio_func *wl_cfg80211_get_sdio_func(void)
3366 {
3367 return cfg80211_sdio_func;
3368 }
3369
wl_dongle_mode(struct net_device * ndev,s32 iftype)3370 static s32 wl_dongle_mode(struct net_device *ndev, s32 iftype)
3371 {
3372 s32 infra = 0;
3373 s32 ap = 0;
3374 s32 err = 0;
3375
3376 switch (iftype) {
3377 case NL80211_IFTYPE_MONITOR:
3378 case NL80211_IFTYPE_WDS:
3379 WL_ERR("type (%d) : currently we do not support this mode\n",
3380 iftype);
3381 err = -EINVAL;
3382 return err;
3383 case NL80211_IFTYPE_ADHOC:
3384 break;
3385 case NL80211_IFTYPE_STATION:
3386 infra = 1;
3387 break;
3388 default:
3389 err = -EINVAL;
3390 WL_ERR("invalid type (%d)\n", iftype);
3391 return err;
3392 }
3393 infra = cpu_to_le32(infra);
3394 ap = cpu_to_le32(ap);
3395 WL_DBG("%s ap (%d), infra (%d)\n", ndev->name, ap, infra);
3396 err = wl_dev_ioctl(ndev, WLC_SET_INFRA, &infra, sizeof(infra));
3397 if (unlikely(err)) {
3398 WL_ERR("WLC_SET_INFRA error (%d)\n", err);
3399 return err;
3400 }
3401 err = wl_dev_ioctl(ndev, WLC_SET_AP, &ap, sizeof(ap));
3402 if (unlikely(err)) {
3403 WL_ERR("WLC_SET_AP error (%d)\n", err);
3404 return err;
3405 }
3406
3407 return -EINPROGRESS;
3408 }
3409
3410 #ifndef EMBEDDED_PLATFORM
wl_dongle_country(struct net_device * ndev,u8 ccode)3411 static s32 wl_dongle_country(struct net_device *ndev, u8 ccode)
3412 {
3413
3414 s32 err = 0;
3415
3416 return err;
3417 }
3418
wl_dongle_up(struct net_device * ndev,u32 up)3419 static s32 wl_dongle_up(struct net_device *ndev, u32 up)
3420 {
3421 s32 err = 0;
3422
3423 err = wl_dev_ioctl(ndev, WLC_UP, &up, sizeof(up));
3424 if (unlikely(err)) {
3425 WL_ERR("WLC_UP error (%d)\n", err);
3426 }
3427 return err;
3428 }
3429
wl_dongle_power(struct net_device * ndev,u32 power_mode)3430 static s32 wl_dongle_power(struct net_device *ndev, u32 power_mode)
3431 {
3432 s32 err = 0;
3433
3434 err = wl_dev_ioctl(ndev, WLC_SET_PM, &power_mode, sizeof(power_mode));
3435 if (unlikely(err)) {
3436 WL_ERR("WLC_SET_PM error (%d)\n", err);
3437 }
3438 return err;
3439 }
3440
3441 static s32
wl_dongle_glom(struct net_device * ndev,u32 glom,u32 dongle_align)3442 wl_dongle_glom(struct net_device *ndev, u32 glom, u32 dongle_align)
3443 {
3444 s8 iovbuf[WL_EVENTING_MASK_LEN + 12]; /* Room for "event_msgs" +
3445 '\0' + bitvec */
3446 s32 err = 0;
3447
3448 /* Match Host and Dongle rx alignment */
3449 bcm_mkiovar("bus:txglomalign", (char *)&dongle_align, 4, iovbuf,
3450 sizeof(iovbuf));
3451 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3452 if (unlikely(err)) {
3453 WL_ERR("txglomalign error (%d)\n", err);
3454 goto dongle_glom_out;
3455 }
3456 /* disable glom option per default */
3457 bcm_mkiovar("bus:txglom", (char *)&glom, 4, iovbuf, sizeof(iovbuf));
3458 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3459 if (unlikely(err)) {
3460 WL_ERR("txglom error (%d)\n", err);
3461 goto dongle_glom_out;
3462 }
3463 dongle_glom_out:
3464 return err;
3465 }
3466
3467 static s32
wl_dongle_roam(struct net_device * ndev,u32 roamvar,u32 bcn_timeout)3468 wl_dongle_roam(struct net_device *ndev, u32 roamvar, u32 bcn_timeout)
3469 {
3470 s8 iovbuf[WL_EVENTING_MASK_LEN + 12]; /* Room for "event_msgs" +
3471 '\0' + bitvec */
3472 s32 err = 0;
3473
3474 /* Setup timeout if Beacons are lost and roam is
3475 off to report link down */
3476 if (roamvar) {
3477 bcm_mkiovar("bcn_timeout", (char *)&bcn_timeout, 4, iovbuf,
3478 sizeof(iovbuf));
3479 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3480 if (unlikely(err)) {
3481 WL_ERR("bcn_timeout error (%d)\n", err);
3482 goto dongle_rom_out;
3483 }
3484 }
3485 /* Enable/Disable built-in roaming to allow supplicant
3486 to take care of roaming */
3487 bcm_mkiovar("roam_off", (char *)&roamvar, 4, iovbuf, sizeof(iovbuf));
3488 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3489 if (unlikely(err)) {
3490 WL_ERR("roam_off error (%d)\n", err);
3491 goto dongle_rom_out;
3492 }
3493 dongle_rom_out:
3494 return err;
3495 }
3496
wl_dongle_eventmsg(struct net_device * ndev)3497 static s32 wl_dongle_eventmsg(struct net_device *ndev)
3498 {
3499
3500 s8 iovbuf[WL_EVENTING_MASK_LEN + 12]; /* Room for "event_msgs" +
3501 '\0' + bitvec */
3502 s8 eventmask[WL_EVENTING_MASK_LEN];
3503 s32 err = 0;
3504
3505 /* Setup event_msgs */
3506 bcm_mkiovar("event_msgs", eventmask, WL_EVENTING_MASK_LEN, iovbuf,
3507 sizeof(iovbuf));
3508 err = wl_dev_ioctl(ndev, WLC_GET_VAR, iovbuf, sizeof(iovbuf));
3509 if (unlikely(err)) {
3510 WL_ERR("Get event_msgs error (%d)\n", err);
3511 goto dongle_eventmsg_out;
3512 }
3513 memcpy(eventmask, iovbuf, WL_EVENTING_MASK_LEN);
3514
3515 setbit(eventmask, WLC_E_SET_SSID);
3516 setbit(eventmask, WLC_E_PRUNE);
3517 setbit(eventmask, WLC_E_AUTH);
3518 setbit(eventmask, WLC_E_REASSOC);
3519 setbit(eventmask, WLC_E_REASSOC_IND);
3520 setbit(eventmask, WLC_E_DEAUTH_IND);
3521 setbit(eventmask, WLC_E_DISASSOC_IND);
3522 setbit(eventmask, WLC_E_DISASSOC);
3523 setbit(eventmask, WLC_E_JOIN);
3524 setbit(eventmask, WLC_E_ASSOC_IND);
3525 setbit(eventmask, WLC_E_PSK_SUP);
3526 setbit(eventmask, WLC_E_LINK);
3527 setbit(eventmask, WLC_E_NDIS_LINK);
3528 setbit(eventmask, WLC_E_MIC_ERROR);
3529 setbit(eventmask, WLC_E_PMKID_CACHE);
3530 setbit(eventmask, WLC_E_TXFAIL);
3531 setbit(eventmask, WLC_E_JOIN_START);
3532 setbit(eventmask, WLC_E_SCAN_COMPLETE);
3533
3534 bcm_mkiovar("event_msgs", eventmask, WL_EVENTING_MASK_LEN, iovbuf,
3535 sizeof(iovbuf));
3536 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3537 if (unlikely(err)) {
3538 WL_ERR("Set event_msgs error (%d)\n", err);
3539 goto dongle_eventmsg_out;
3540 }
3541
3542 dongle_eventmsg_out:
3543 return err;
3544 }
3545
3546 static s32
wl_dongle_scantime(struct net_device * ndev,s32 scan_assoc_time,s32 scan_unassoc_time)3547 wl_dongle_scantime(struct net_device *ndev, s32 scan_assoc_time,
3548 s32 scan_unassoc_time)
3549 {
3550 s32 err = 0;
3551
3552 err = wl_dev_ioctl(ndev, WLC_SET_SCAN_CHANNEL_TIME, &scan_assoc_time,
3553 sizeof(scan_assoc_time));
3554 if (err) {
3555 if (err == -EOPNOTSUPP) {
3556 WL_INFO("Scan assoc time is not supported\n");
3557 } else {
3558 WL_ERR("Scan assoc time error (%d)\n", err);
3559 }
3560 goto dongle_scantime_out;
3561 }
3562 err = wl_dev_ioctl(ndev, WLC_SET_SCAN_UNASSOC_TIME, &scan_unassoc_time,
3563 sizeof(scan_unassoc_time));
3564 if (err) {
3565 if (err == -EOPNOTSUPP) {
3566 WL_INFO("Scan unassoc time is not supported\n");
3567 } else {
3568 WL_ERR("Scan unassoc time error (%d)\n", err);
3569 }
3570 goto dongle_scantime_out;
3571 }
3572
3573 dongle_scantime_out:
3574 return err;
3575 }
3576
3577 static s32
wl_dongle_offload(struct net_device * ndev,s32 arpoe,s32 arp_ol)3578 wl_dongle_offload(struct net_device *ndev, s32 arpoe, s32 arp_ol)
3579 {
3580 s8 iovbuf[WL_EVENTING_MASK_LEN + 12]; /* Room for "event_msgs" +
3581 '\0' + bitvec */
3582 s32 err = 0;
3583
3584 /* Set ARP offload */
3585 bcm_mkiovar("arpoe", (char *)&arpoe, 4, iovbuf, sizeof(iovbuf));
3586 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3587 if (err) {
3588 if (err == -EOPNOTSUPP)
3589 WL_INFO("arpoe is not supported\n");
3590 else
3591 WL_ERR("arpoe error (%d)\n", err);
3592
3593 goto dongle_offload_out;
3594 }
3595 bcm_mkiovar("arp_ol", (char *)&arp_ol, 4, iovbuf, sizeof(iovbuf));
3596 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3597 if (err) {
3598 if (err == -EOPNOTSUPP)
3599 WL_INFO("arp_ol is not supported\n");
3600 else
3601 WL_ERR("arp_ol error (%d)\n", err);
3602
3603 goto dongle_offload_out;
3604 }
3605
3606 dongle_offload_out:
3607 return err;
3608 }
3609
wl_pattern_atoh(s8 * src,s8 * dst)3610 static s32 wl_pattern_atoh(s8 *src, s8 *dst)
3611 {
3612 int i;
3613 if (strncmp(src, "0x", 2) != 0 && strncmp(src, "0X", 2) != 0) {
3614 WL_ERR("Mask invalid format. Needs to start with 0x\n");
3615 return -1;
3616 }
3617 src = src + 2; /* Skip past 0x */
3618 if (strlen(src) % 2 != 0) {
3619 WL_ERR("Mask invalid format. Needs to be of even length\n");
3620 return -1;
3621 }
3622 for (i = 0; *src != '\0'; i++) {
3623 char num[3];
3624 strncpy(num, src, 2);
3625 num[2] = '\0';
3626 dst[i] = (u8) simple_strtoul(num, NULL, 16);
3627 src += 2;
3628 }
3629 return i;
3630 }
3631
wl_dongle_filter(struct net_device * ndev,u32 filter_mode)3632 static s32 wl_dongle_filter(struct net_device *ndev, u32 filter_mode)
3633 {
3634 s8 iovbuf[WL_EVENTING_MASK_LEN + 12]; /* Room for "event_msgs" +
3635 '\0' + bitvec */
3636 const s8 *str;
3637 struct wl_pkt_filter pkt_filter;
3638 struct wl_pkt_filter *pkt_filterp;
3639 s32 buf_len;
3640 s32 str_len;
3641 u32 mask_size;
3642 u32 pattern_size;
3643 s8 buf[256];
3644 s32 err = 0;
3645
3646 /* add a default packet filter pattern */
3647 str = "pkt_filter_add";
3648 str_len = strlen(str);
3649 strncpy(buf, str, str_len);
3650 buf[str_len] = '\0';
3651 buf_len = str_len + 1;
3652
3653 pkt_filterp = (struct wl_pkt_filter *)(buf + str_len + 1);
3654
3655 /* Parse packet filter id. */
3656 pkt_filter.id = cpu_to_le32(100);
3657
3658 /* Parse filter polarity. */
3659 pkt_filter.negate_match = cpu_to_le32(0);
3660
3661 /* Parse filter type. */
3662 pkt_filter.type = cpu_to_le32(0);
3663
3664 /* Parse pattern filter offset. */
3665 pkt_filter.u.pattern.offset = cpu_to_le32(0);
3666
3667 /* Parse pattern filter mask. */
3668 mask_size = cpu_to_le32(wl_pattern_atoh("0xff",
3669 (char *)pkt_filterp->u.pattern.
3670 mask_and_pattern));
3671
3672 /* Parse pattern filter pattern. */
3673 pattern_size = cpu_to_le32(wl_pattern_atoh("0x00",
3674 (char *)&pkt_filterp->u.
3675 pattern.
3676 mask_and_pattern
3677 [mask_size]));
3678
3679 if (mask_size != pattern_size) {
3680 WL_ERR("Mask and pattern not the same size\n");
3681 err = -EINVAL;
3682 goto dongle_filter_out;
3683 }
3684
3685 pkt_filter.u.pattern.size_bytes = mask_size;
3686 buf_len += WL_PKT_FILTER_FIXED_LEN;
3687 buf_len += (WL_PKT_FILTER_PATTERN_FIXED_LEN + 2 * mask_size);
3688
3689 /* Keep-alive attributes are set in local
3690 * variable (keep_alive_pkt), and
3691 * then memcpy'ed into buffer (keep_alive_pktp) since there is no
3692 * guarantee that the buffer is properly aligned.
3693 */
3694 memcpy((char *)pkt_filterp, &pkt_filter,
3695 WL_PKT_FILTER_FIXED_LEN + WL_PKT_FILTER_PATTERN_FIXED_LEN);
3696
3697 err = wl_dev_ioctl(ndev, WLC_SET_VAR, buf, buf_len);
3698 if (err) {
3699 if (err == -EOPNOTSUPP) {
3700 WL_INFO("filter not supported\n");
3701 } else {
3702 WL_ERR("filter (%d)\n", err);
3703 }
3704 goto dongle_filter_out;
3705 }
3706
3707 /* set mode to allow pattern */
3708 bcm_mkiovar("pkt_filter_mode", (char *)&filter_mode, 4, iovbuf,
3709 sizeof(iovbuf));
3710 err = wl_dev_ioctl(ndev, WLC_SET_VAR, iovbuf, sizeof(iovbuf));
3711 if (err) {
3712 if (err == -EOPNOTSUPP) {
3713 WL_INFO("filter_mode not supported\n");
3714 } else {
3715 WL_ERR("filter_mode (%d)\n", err);
3716 }
3717 goto dongle_filter_out;
3718 }
3719
3720 dongle_filter_out:
3721 return err;
3722 }
3723 #endif /* !EMBEDDED_PLATFORM */
3724
wl_config_dongle(struct wl_priv * wl,bool need_lock)3725 s32 wl_config_dongle(struct wl_priv *wl, bool need_lock)
3726 {
3727 #ifndef DHD_SDALIGN
3728 #define DHD_SDALIGN 32
3729 #endif
3730 struct net_device *ndev;
3731 struct wireless_dev *wdev;
3732 s32 err = 0;
3733
3734 if (wl->dongle_up)
3735 return err;
3736
3737 ndev = wl_to_ndev(wl);
3738 wdev = ndev->ieee80211_ptr;
3739 if (need_lock)
3740 rtnl_lock();
3741
3742 #ifndef EMBEDDED_PLATFORM
3743 err = wl_dongle_up(ndev, 0);
3744 if (unlikely(err))
3745 goto default_conf_out;
3746 err = wl_dongle_country(ndev, 0);
3747 if (unlikely(err))
3748 goto default_conf_out;
3749 err = wl_dongle_power(ndev, PM_FAST);
3750 if (unlikely(err))
3751 goto default_conf_out;
3752 err = wl_dongle_glom(ndev, 0, DHD_SDALIGN);
3753 if (unlikely(err))
3754 goto default_conf_out;
3755 err = wl_dongle_roam(ndev, (wl->roam_on ? 0 : 1), 3);
3756 if (unlikely(err))
3757 goto default_conf_out;
3758 err = wl_dongle_eventmsg(ndev);
3759 if (unlikely(err))
3760 goto default_conf_out;
3761
3762 wl_dongle_scantime(ndev, 40, 80);
3763 wl_dongle_offload(ndev, 1, 0xf);
3764 wl_dongle_filter(ndev, 1);
3765 #endif /* !EMBEDDED_PLATFORM */
3766
3767 err = wl_dongle_mode(ndev, wdev->iftype);
3768 if (unlikely(err && err != -EINPROGRESS))
3769 goto default_conf_out;
3770 err = wl_dongle_probecap(wl);
3771 if (unlikely(err))
3772 goto default_conf_out;
3773
3774 /* -EINPROGRESS: Call commit handler */
3775
3776 default_conf_out:
3777 if (need_lock)
3778 rtnl_unlock();
3779
3780 wl->dongle_up = true;
3781
3782 return err;
3783
3784 }
3785
wl_update_wiphybands(struct wl_priv * wl)3786 static s32 wl_update_wiphybands(struct wl_priv *wl)
3787 {
3788 struct wiphy *wiphy;
3789 s32 phy_list;
3790 s8 phy;
3791 s32 err = 0;
3792
3793 err = wl_dev_ioctl(wl_to_ndev(wl), WLC_GET_PHYLIST, &phy_list,
3794 sizeof(phy_list));
3795 if (unlikely(err)) {
3796 WL_ERR("error (%d)\n", err);
3797 return err;
3798 }
3799
3800 phy = ((char *)&phy_list)[1];
3801 WL_DBG("%c phy\n", phy);
3802 if (phy == 'n' || phy == 'a') {
3803 wiphy = wl_to_wiphy(wl);
3804 wiphy->bands[IEEE80211_BAND_5GHZ] = &__wl_band_5ghz_n;
3805 }
3806
3807 return err;
3808 }
3809
__wl_cfg80211_up(struct wl_priv * wl)3810 static s32 __wl_cfg80211_up(struct wl_priv *wl)
3811 {
3812 s32 err = 0;
3813
3814 wl_debugfs_add_netdev_params(wl);
3815
3816 err = wl_config_dongle(wl, false);
3817 if (unlikely(err))
3818 return err;
3819
3820 wl_invoke_iscan(wl);
3821 set_bit(WL_STATUS_READY, &wl->status);
3822 return err;
3823 }
3824
__wl_cfg80211_down(struct wl_priv * wl)3825 static s32 __wl_cfg80211_down(struct wl_priv *wl)
3826 {
3827 s32 err = 0;
3828
3829 /* Check if cfg80211 interface is already down */
3830 if (!test_bit(WL_STATUS_READY, &wl->status))
3831 return err; /* it is even not ready */
3832
3833 set_bit(WL_STATUS_SCAN_ABORTING, &wl->status);
3834 wl_term_iscan(wl);
3835 if (wl->scan_request) {
3836 cfg80211_scan_done(wl->scan_request, true); /* true
3837 means abort */
3838 /* wl_set_mpc(wl_to_ndev(wl), 1); */ /* BUG
3839 * this operation cannot help
3840 * but here because sdio
3841 * is already down through
3842 * rmmod process.
3843 * Need to figure out how to
3844 * address this issue
3845 */
3846 wl->scan_request = NULL;
3847 }
3848 clear_bit(WL_STATUS_READY, &wl->status);
3849 clear_bit(WL_STATUS_SCANNING, &wl->status);
3850 clear_bit(WL_STATUS_SCAN_ABORTING, &wl->status);
3851 clear_bit(WL_STATUS_CONNECTED, &wl->status);
3852
3853 wl_debugfs_remove_netdev(wl);
3854
3855 return err;
3856 }
3857
wl_cfg80211_up(void)3858 s32 wl_cfg80211_up(void)
3859 {
3860 struct wl_priv *wl;
3861 s32 err = 0;
3862
3863 wl = WL_PRIV_GET();
3864 mutex_lock(&wl->usr_sync);
3865 err = __wl_cfg80211_up(wl);
3866 mutex_unlock(&wl->usr_sync);
3867
3868 return err;
3869 }
3870
wl_cfg80211_down(void)3871 s32 wl_cfg80211_down(void)
3872 {
3873 struct wl_priv *wl;
3874 s32 err = 0;
3875
3876 wl = WL_PRIV_GET();
3877 mutex_lock(&wl->usr_sync);
3878 err = __wl_cfg80211_down(wl);
3879 mutex_unlock(&wl->usr_sync);
3880
3881 return err;
3882 }
3883
wl_dongle_probecap(struct wl_priv * wl)3884 static s32 wl_dongle_probecap(struct wl_priv *wl)
3885 {
3886 s32 err = 0;
3887
3888 err = wl_update_wiphybands(wl);
3889 if (unlikely(err))
3890 return err;
3891
3892 return err;
3893 }
3894
wl_read_prof(struct wl_priv * wl,s32 item)3895 static void *wl_read_prof(struct wl_priv *wl, s32 item)
3896 {
3897 switch (item) {
3898 case WL_PROF_SEC:
3899 return &wl->profile->sec;
3900 case WL_PROF_ACT:
3901 return &wl->profile->active;
3902 case WL_PROF_BSSID:
3903 return &wl->profile->bssid;
3904 case WL_PROF_SSID:
3905 return &wl->profile->ssid;
3906 }
3907 WL_ERR("invalid item (%d)\n", item);
3908 return NULL;
3909 }
3910
3911 static s32
wl_update_prof(struct wl_priv * wl,const wl_event_msg_t * e,void * data,s32 item)3912 wl_update_prof(struct wl_priv *wl, const wl_event_msg_t *e, void *data,
3913 s32 item)
3914 {
3915 s32 err = 0;
3916 struct wlc_ssid *ssid;
3917
3918 switch (item) {
3919 case WL_PROF_SSID:
3920 ssid = (wlc_ssid_t *) data;
3921 memset(wl->profile->ssid.SSID, 0,
3922 sizeof(wl->profile->ssid.SSID));
3923 memcpy(wl->profile->ssid.SSID, ssid->SSID, ssid->SSID_len);
3924 wl->profile->ssid.SSID_len = ssid->SSID_len;
3925 break;
3926 case WL_PROF_BSSID:
3927 if (data)
3928 memcpy(wl->profile->bssid, data, ETH_ALEN);
3929 else
3930 memset(wl->profile->bssid, 0, ETH_ALEN);
3931 break;
3932 case WL_PROF_SEC:
3933 memcpy(&wl->profile->sec, data, sizeof(wl->profile->sec));
3934 break;
3935 case WL_PROF_ACT:
3936 wl->profile->active = *(bool *)data;
3937 break;
3938 case WL_PROF_BEACONINT:
3939 wl->profile->beacon_interval = *(u16 *)data;
3940 break;
3941 case WL_PROF_DTIMPERIOD:
3942 wl->profile->dtim_period = *(u8 *)data;
3943 break;
3944 default:
3945 WL_ERR("unsupported item (%d)\n", item);
3946 err = -EOPNOTSUPP;
3947 break;
3948 }
3949
3950 return err;
3951 }
3952
wl_cfg80211_dbg_level(u32 level)3953 void wl_cfg80211_dbg_level(u32 level)
3954 {
3955 /*
3956 * prohibit to change debug level
3957 * by insmod parameter.
3958 * eventually debug level will be configured
3959 * in compile time by using CONFIG_XXX
3960 */
3961 /* wl_dbg_level = level; */
3962 }
3963
wl_is_ibssmode(struct wl_priv * wl)3964 static bool wl_is_ibssmode(struct wl_priv *wl)
3965 {
3966 return wl->conf->mode == WL_MODE_IBSS;
3967 }
3968
wl_is_ibssstarter(struct wl_priv * wl)3969 static bool wl_is_ibssstarter(struct wl_priv *wl)
3970 {
3971 return wl->ibss_starter;
3972 }
3973
wl_rst_ie(struct wl_priv * wl)3974 static void wl_rst_ie(struct wl_priv *wl)
3975 {
3976 struct wl_ie *ie = wl_to_ie(wl);
3977
3978 ie->offset = 0;
3979 }
3980
wl_add_ie(struct wl_priv * wl,u8 t,u8 l,u8 * v)3981 static __used s32 wl_add_ie(struct wl_priv *wl, u8 t, u8 l, u8 *v)
3982 {
3983 struct wl_ie *ie = wl_to_ie(wl);
3984 s32 err = 0;
3985
3986 if (unlikely(ie->offset + l + 2 > WL_TLV_INFO_MAX)) {
3987 WL_ERR("ei crosses buffer boundary\n");
3988 return -ENOSPC;
3989 }
3990 ie->buf[ie->offset] = t;
3991 ie->buf[ie->offset + 1] = l;
3992 memcpy(&ie->buf[ie->offset + 2], v, l);
3993 ie->offset += l + 2;
3994
3995 return err;
3996 }
3997
wl_mrg_ie(struct wl_priv * wl,u8 * ie_stream,u16 ie_size)3998 static s32 wl_mrg_ie(struct wl_priv *wl, u8 *ie_stream, u16 ie_size)
3999 {
4000 struct wl_ie *ie = wl_to_ie(wl);
4001 s32 err = 0;
4002
4003 if (unlikely(ie->offset + ie_size > WL_TLV_INFO_MAX)) {
4004 WL_ERR("ei_stream crosses buffer boundary\n");
4005 return -ENOSPC;
4006 }
4007 memcpy(&ie->buf[ie->offset], ie_stream, ie_size);
4008 ie->offset += ie_size;
4009
4010 return err;
4011 }
4012
wl_cp_ie(struct wl_priv * wl,u8 * dst,u16 dst_size)4013 static s32 wl_cp_ie(struct wl_priv *wl, u8 *dst, u16 dst_size)
4014 {
4015 struct wl_ie *ie = wl_to_ie(wl);
4016 s32 err = 0;
4017
4018 if (unlikely(ie->offset > dst_size)) {
4019 WL_ERR("dst_size is not enough\n");
4020 return -ENOSPC;
4021 }
4022 memcpy(dst, &ie->buf[0], ie->offset);
4023
4024 return err;
4025 }
4026
wl_get_ielen(struct wl_priv * wl)4027 static u32 wl_get_ielen(struct wl_priv *wl)
4028 {
4029 struct wl_ie *ie = wl_to_ie(wl);
4030
4031 return ie->offset;
4032 }
4033
wl_link_up(struct wl_priv * wl)4034 static void wl_link_up(struct wl_priv *wl)
4035 {
4036 wl->link_up = true;
4037 }
4038
wl_link_down(struct wl_priv * wl)4039 static void wl_link_down(struct wl_priv *wl)
4040 {
4041 struct wl_connect_info *conn_info = wl_to_conn(wl);
4042
4043 wl->link_up = false;
4044 kfree(conn_info->req_ie);
4045 conn_info->req_ie = NULL;
4046 conn_info->req_ie_len = 0;
4047 kfree(conn_info->resp_ie);
4048 conn_info->resp_ie = NULL;
4049 conn_info->resp_ie_len = 0;
4050 }
4051
wl_lock_eq(struct wl_priv * wl)4052 static void wl_lock_eq(struct wl_priv *wl)
4053 {
4054 spin_lock_irq(&wl->eq_lock);
4055 }
4056
wl_unlock_eq(struct wl_priv * wl)4057 static void wl_unlock_eq(struct wl_priv *wl)
4058 {
4059 spin_unlock_irq(&wl->eq_lock);
4060 }
4061
wl_init_eq_lock(struct wl_priv * wl)4062 static void wl_init_eq_lock(struct wl_priv *wl)
4063 {
4064 spin_lock_init(&wl->eq_lock);
4065 }
4066
wl_delay(u32 ms)4067 static void wl_delay(u32 ms)
4068 {
4069 if (ms < 1000 / HZ) {
4070 cond_resched();
4071 mdelay(ms);
4072 } else {
4073 msleep(ms);
4074 }
4075 }
4076
wl_set_drvdata(struct wl_dev * dev,void * data)4077 static void wl_set_drvdata(struct wl_dev *dev, void *data)
4078 {
4079 dev->driver_data = data;
4080 }
4081
wl_get_drvdata(struct wl_dev * dev)4082 static void *wl_get_drvdata(struct wl_dev *dev)
4083 {
4084 return dev->driver_data;
4085 }
4086
wl_cfg80211_read_fw(s8 * buf,u32 size)4087 s32 wl_cfg80211_read_fw(s8 *buf, u32 size)
4088 {
4089 const struct firmware *fw_entry;
4090 struct wl_priv *wl;
4091
4092 wl = WL_PRIV_GET();
4093
4094 fw_entry = wl->fw->fw_entry;
4095
4096 if (fw_entry->size < wl->fw->ptr + size)
4097 size = fw_entry->size - wl->fw->ptr;
4098
4099 memcpy(buf, &fw_entry->data[wl->fw->ptr], size);
4100 wl->fw->ptr += size;
4101 return size;
4102 }
4103
wl_cfg80211_release_fw(void)4104 void wl_cfg80211_release_fw(void)
4105 {
4106 struct wl_priv *wl;
4107
4108 wl = WL_PRIV_GET();
4109 release_firmware(wl->fw->fw_entry);
4110 wl->fw->ptr = 0;
4111 }
4112
wl_cfg80211_request_fw(s8 * file_name)4113 void *wl_cfg80211_request_fw(s8 *file_name)
4114 {
4115 struct wl_priv *wl;
4116 const struct firmware *fw_entry = NULL;
4117 s32 err = 0;
4118
4119 WL_DBG("file name : \"%s\"\n", file_name);
4120 wl = WL_PRIV_GET();
4121
4122 if (!test_bit(WL_FW_LOADING_DONE, &wl->fw->status)) {
4123 err = request_firmware(&wl->fw->fw_entry, file_name,
4124 &wl_cfg80211_get_sdio_func()->dev);
4125 if (unlikely(err)) {
4126 WL_ERR("Could not download fw (%d)\n", err);
4127 goto req_fw_out;
4128 }
4129 set_bit(WL_FW_LOADING_DONE, &wl->fw->status);
4130 fw_entry = wl->fw->fw_entry;
4131 if (fw_entry) {
4132 WL_DBG("fw size (%zd), data (%p)\n",
4133 fw_entry->size, fw_entry->data);
4134 }
4135 } else if (!test_bit(WL_NVRAM_LOADING_DONE, &wl->fw->status)) {
4136 err = request_firmware(&wl->fw->fw_entry, file_name,
4137 &wl_cfg80211_get_sdio_func()->dev);
4138 if (unlikely(err)) {
4139 WL_ERR("Could not download nvram (%d)\n", err);
4140 goto req_fw_out;
4141 }
4142 set_bit(WL_NVRAM_LOADING_DONE, &wl->fw->status);
4143 fw_entry = wl->fw->fw_entry;
4144 if (fw_entry) {
4145 WL_DBG("nvram size (%zd), data (%p)\n",
4146 fw_entry->size, fw_entry->data);
4147 }
4148 } else {
4149 WL_DBG("Downloading already done. Nothing to do more\n");
4150 err = -EPERM;
4151 }
4152
4153 req_fw_out:
4154 if (unlikely(err)) {
4155 return NULL;
4156 }
4157 wl->fw->ptr = 0;
4158 return (void *)fw_entry->data;
4159 }
4160
wl_cfg80211_get_fwname(void)4161 s8 *wl_cfg80211_get_fwname(void)
4162 {
4163 struct wl_priv *wl;
4164
4165 wl = WL_PRIV_GET();
4166 strcpy(wl->fw->fw_name, WL_4329_FW_FILE);
4167 return wl->fw->fw_name;
4168 }
4169
wl_cfg80211_get_nvramname(void)4170 s8 *wl_cfg80211_get_nvramname(void)
4171 {
4172 struct wl_priv *wl;
4173
4174 wl = WL_PRIV_GET();
4175 strcpy(wl->fw->nvram_name, WL_4329_NVRAM_FILE);
4176 return wl->fw->nvram_name;
4177 }
4178
wl_set_mpc(struct net_device * ndev,int mpc)4179 static void wl_set_mpc(struct net_device *ndev, int mpc)
4180 {
4181 s32 err = 0;
4182
4183 err = wl_dev_intvar_set(ndev, "mpc", mpc);
4184 if (unlikely(err)) {
4185 WL_ERR("fail to set mpc\n");
4186 return;
4187 }
4188 WL_DBG("MPC : %d\n", mpc);
4189 }
4190
wl_debugfs_add_netdev_params(struct wl_priv * wl)4191 static int wl_debugfs_add_netdev_params(struct wl_priv *wl)
4192 {
4193 char buf[10+IFNAMSIZ];
4194 struct dentry *fd;
4195 s32 err = 0;
4196
4197 sprintf(buf, "netdev:%s", wl_to_ndev(wl)->name);
4198 wl->debugfsdir = debugfs_create_dir(buf, wl_to_wiphy(wl)->debugfsdir);
4199
4200 fd = debugfs_create_u16("beacon_int", S_IRUGO, wl->debugfsdir,
4201 (u16 *)&wl->profile->beacon_interval);
4202 if (!fd) {
4203 err = -ENOMEM;
4204 goto err_out;
4205 }
4206
4207 fd = debugfs_create_u8("dtim_period", S_IRUGO, wl->debugfsdir,
4208 (u8 *)&wl->profile->dtim_period);
4209 if (!fd) {
4210 err = -ENOMEM;
4211 goto err_out;
4212 }
4213
4214 err_out:
4215 return err;
4216 }
4217
wl_debugfs_remove_netdev(struct wl_priv * wl)4218 static void wl_debugfs_remove_netdev(struct wl_priv *wl)
4219 {
4220 debugfs_remove_recursive(wl->debugfsdir);
4221 wl->debugfsdir = NULL;
4222 }
4223