1 #include "wilc_wfi_cfgoperations.h"
2 #include "linux_wlan_common.h"
3 #include "wilc_wlan_if.h"
6 #include <linux/slab.h>
7 #include <linux/sched.h>
8 #include <linux/delay.h>
9 #include <linux/workqueue.h>
10 #include <linux/interrupt.h>
11 #include <linux/irq.h>
12 #include <linux/gpio.h>
14 #include <linux/kthread.h>
15 #include <linux/firmware.h>
16 #include <linux/delay.h>
18 #include <linux/init.h>
19 #include <linux/netdevice.h>
20 #include <linux/inetdevice.h>
21 #include <linux/etherdevice.h>
22 #include <linux/module.h>
23 #include <linux/kernel.h>
24 #include <linux/skbuff.h>
26 #include <linux/semaphore.h>
28 static int dev_state_ev_handler(struct notifier_block
*this,
29 unsigned long event
, void *ptr
);
31 static struct notifier_block g_dev_notifier
= {
32 .notifier_call
= dev_state_ev_handler
37 static struct semaphore close_exit_sync
;
39 static int wlan_deinit_locks(struct net_device
*dev
);
40 static void wlan_deinitialize_threads(struct net_device
*dev
);
42 static void linux_wlan_tx_complete(void *priv
, int status
);
43 static int mac_init_fn(struct net_device
*ndev
);
44 static struct net_device_stats
*mac_stats(struct net_device
*dev
);
45 static int mac_ioctl(struct net_device
*ndev
, struct ifreq
*req
, int cmd
);
46 static void wilc_set_multicast_list(struct net_device
*dev
);
48 bool wilc_enable_ps
= true;
50 static const struct net_device_ops wilc_netdev_ops
= {
51 .ndo_init
= mac_init_fn
,
52 .ndo_open
= wilc_mac_open
,
53 .ndo_stop
= wilc_mac_close
,
54 .ndo_start_xmit
= wilc_mac_xmit
,
55 .ndo_do_ioctl
= mac_ioctl
,
56 .ndo_get_stats
= mac_stats
,
57 .ndo_set_rx_mode
= wilc_set_multicast_list
,
61 static int dev_state_ev_handler(struct notifier_block
*this,
62 unsigned long event
, void *ptr
)
64 struct in_ifaddr
*dev_iface
= ptr
;
65 struct wilc_priv
*priv
;
66 struct host_if_drv
*hif_drv
;
67 struct net_device
*dev
;
71 char wlan_dev_name
[5] = "wlan0";
73 if (!dev_iface
|| !dev_iface
->ifa_dev
|| !dev_iface
->ifa_dev
->dev
)
76 if (memcmp(dev_iface
->ifa_label
, "wlan0", 5) &&
77 memcmp(dev_iface
->ifa_label
, "p2p0", 4))
80 dev
= (struct net_device
*)dev_iface
->ifa_dev
->dev
;
81 if (!dev
->ieee80211_ptr
|| !dev
->ieee80211_ptr
->wiphy
)
84 priv
= wiphy_priv(dev
->ieee80211_ptr
->wiphy
);
88 hif_drv
= (struct host_if_drv
*)priv
->hif_drv
;
89 vif
= netdev_priv(dev
);
95 if (vif
->iftype
== STATION_MODE
|| vif
->iftype
== CLIENT_MODE
) {
97 wilc_optaining_ip
= false;
98 del_timer(&wilc_during_ip_timer
);
102 wilc_set_power_mgmt(vif
, 1, 0);
104 netdev_dbg(dev
, "[%s] Up IP\n", dev_iface
->ifa_label
);
106 ip_addr_buf
= (char *)&dev_iface
->ifa_address
;
107 netdev_dbg(dev
, "IP add=%d:%d:%d:%d\n",
108 ip_addr_buf
[0], ip_addr_buf
[1],
109 ip_addr_buf
[2], ip_addr_buf
[3]);
110 wilc_setup_ipaddress(vif
, ip_addr_buf
, vif
->idx
);
115 if (vif
->iftype
== STATION_MODE
|| vif
->iftype
== CLIENT_MODE
) {
117 wilc_optaining_ip
= false;
120 if (memcmp(dev_iface
->ifa_label
, wlan_dev_name
, 5) == 0)
121 wilc_set_power_mgmt(vif
, 0, 0);
123 wilc_resolve_disconnect_aberration(vif
);
125 netdev_dbg(dev
, "[%s] Down IP\n", dev_iface
->ifa_label
);
127 ip_addr_buf
= null_ip
;
128 netdev_dbg(dev
, "IP add=%d:%d:%d:%d\n",
129 ip_addr_buf
[0], ip_addr_buf
[1],
130 ip_addr_buf
[2], ip_addr_buf
[3]);
132 wilc_setup_ipaddress(vif
, ip_addr_buf
, vif
->idx
);
143 static irqreturn_t
isr_uh_routine(int irq
, void *user_data
)
145 struct wilc_vif
*vif
;
147 struct net_device
*dev
= user_data
;
149 vif
= netdev_priv(dev
);
153 netdev_err(dev
, "Can't handle UH interrupt\n");
156 return IRQ_WAKE_THREAD
;
159 static irqreturn_t
isr_bh_routine(int irq
, void *userdata
)
161 struct wilc_vif
*vif
;
163 struct net_device
*dev
= userdata
;
165 vif
= netdev_priv(userdata
);
169 netdev_err(dev
, "Can't handle BH interrupt\n");
173 wilc_handle_isr(wilc
);
178 static int init_irq(struct net_device
*dev
)
181 struct wilc_vif
*vif
;
184 vif
= netdev_priv(dev
);
187 if ((gpio_request(wl
->gpio
, "WILC_INTR") == 0) &&
188 (gpio_direction_input(wl
->gpio
) == 0)) {
189 wl
->dev_irq_num
= gpio_to_irq(wl
->gpio
);
192 netdev_err(dev
, "could not obtain gpio for WILC_INTR\n");
195 if (ret
!= -1 && request_threaded_irq(wl
->dev_irq_num
,
198 IRQF_TRIGGER_LOW
| IRQF_ONESHOT
,
199 "WILC_IRQ", dev
) < 0) {
200 netdev_err(dev
, "Failed to request IRQ GPIO: %d\n", wl
->gpio
);
205 "IRQ request succeeded IRQ-NUM= %d on GPIO: %d\n",
206 wl
->dev_irq_num
, wl
->gpio
);
212 static void deinit_irq(struct net_device
*dev
)
214 struct wilc_vif
*vif
;
217 vif
= netdev_priv(dev
);
220 /* Deintialize IRQ */
221 if (wilc
->dev_irq_num
) {
222 free_irq(wilc
->dev_irq_num
, wilc
);
223 gpio_free(wilc
->gpio
);
227 void wilc_dbg(u8
*buff
)
229 PRINT_D(INIT_DBG
, "%d\n", *buff
);
232 int wilc_lock_timeout(struct wilc
*nic
, void *vp
, u32 timeout
)
234 /* FIXME: replace with mutex_lock or wait_for_completion */
238 error
= down_timeout(vp
,
239 msecs_to_jiffies(timeout
));
243 void wilc_mac_indicate(struct wilc
*wilc
, int flag
)
247 if (flag
== WILC_MAC_INDICATE_STATUS
) {
248 wilc_wlan_cfg_get_val(WID_STATUS
,
249 (unsigned char *)&status
, 4);
250 if (wilc
->mac_status
== WILC_MAC_STATUS_INIT
) {
251 wilc
->mac_status
= status
;
252 up(&wilc
->sync_event
);
254 wilc
->mac_status
= status
;
259 static struct net_device
*get_if_handler(struct wilc
*wilc
, u8
*mac_header
)
264 bssid
= mac_header
+ 10;
265 bssid1
= mac_header
+ 4;
267 for (i
= 0; i
< wilc
->vif_num
; i
++) {
268 if (wilc
->vif
[i
]->mode
== STATION_MODE
)
269 if (!memcmp(bssid
, wilc
->vif
[i
]->bssid
, ETH_ALEN
))
270 return wilc
->vif
[i
]->ndev
;
271 if (wilc
->vif
[i
]->mode
== AP_MODE
)
272 if (!memcmp(bssid1
, wilc
->vif
[i
]->bssid
, ETH_ALEN
))
273 return wilc
->vif
[i
]->ndev
;
279 int wilc_wlan_set_bssid(struct net_device
*wilc_netdev
, u8
*bssid
, u8 mode
)
283 struct wilc_vif
*vif
;
286 vif
= netdev_priv(wilc_netdev
);
289 for (i
= 0; i
< wilc
->vif_num
; i
++)
290 if (wilc
->vif
[i
]->ndev
== wilc_netdev
) {
291 memcpy(wilc
->vif
[i
]->bssid
, bssid
, 6);
292 wilc
->vif
[i
]->mode
= mode
;
300 int wilc_wlan_get_num_conn_ifcs(struct wilc
*wilc
)
303 u8 null_bssid
[6] = {0};
306 for (i
= 0; i
< wilc
->vif_num
; i
++)
307 if (memcmp(wilc
->vif
[i
]->bssid
, null_bssid
, 6))
313 #define USE_TX_BACKOFF_DELAY_IF_NO_BUFFERS
315 static int linux_wlan_txq_task(void *vp
)
318 struct wilc_vif
*vif
;
320 struct net_device
*dev
= vp
;
321 #if defined USE_TX_BACKOFF_DELAY_IF_NO_BUFFERS
322 #define TX_BACKOFF_WEIGHT_INCR_STEP (1)
323 #define TX_BACKOFF_WEIGHT_DECR_STEP (1)
324 #define TX_BACKOFF_WEIGHT_MAX (7)
325 #define TX_BACKOFF_WEIGHT_MIN (0)
326 #define TX_BACKOFF_WEIGHT_UNIT_MS (10)
327 int backoff_weight
= TX_BACKOFF_WEIGHT_MIN
;
330 vif
= netdev_priv(dev
);
333 up(&wl
->txq_thread_started
);
335 down(&wl
->txq_event
);
338 up(&wl
->txq_thread_started
);
340 while (!kthread_should_stop())
344 #if !defined USE_TX_BACKOFF_DELAY_IF_NO_BUFFERS
345 ret
= wilc_wlan_handle_txq(dev
, &txq_count
);
348 ret
= wilc_wlan_handle_txq(dev
, &txq_count
);
349 if (txq_count
< FLOW_CONTROL_LOWER_THRESHOLD
) {
350 if (netif_queue_stopped(wl
->vif
[0]->ndev
))
351 netif_wake_queue(wl
->vif
[0]->ndev
);
352 if (netif_queue_stopped(wl
->vif
[1]->ndev
))
353 netif_wake_queue(wl
->vif
[1]->ndev
);
356 if (ret
== WILC_TX_ERR_NO_BUF
) {
357 backoff_weight
+= TX_BACKOFF_WEIGHT_INCR_STEP
;
358 if (backoff_weight
> TX_BACKOFF_WEIGHT_MAX
)
359 backoff_weight
= TX_BACKOFF_WEIGHT_MAX
;
361 if (backoff_weight
> TX_BACKOFF_WEIGHT_MIN
) {
362 backoff_weight
-= TX_BACKOFF_WEIGHT_DECR_STEP
;
363 if (backoff_weight
< TX_BACKOFF_WEIGHT_MIN
)
364 backoff_weight
= TX_BACKOFF_WEIGHT_MIN
;
367 } while (ret
== WILC_TX_ERR_NO_BUF
&& !wl
->close
);
373 int wilc_wlan_get_firmware(struct net_device
*dev
)
375 struct wilc_vif
*vif
;
377 int chip_id
, ret
= 0;
378 const struct firmware
*wilc_firmware
;
381 vif
= netdev_priv(dev
);
384 chip_id
= wilc_get_chipid(wilc
, false);
386 if (chip_id
< 0x1003a0)
387 firmware
= FIRMWARE_1002
;
389 firmware
= FIRMWARE_1003
;
391 netdev_info(dev
, "loading firmware %s\n", firmware
);
393 if (!(&vif
->ndev
->dev
))
396 if (request_firmware(&wilc_firmware
, firmware
, wilc
->dev
) != 0) {
397 netdev_err(dev
, "%s - firmare not available\n", firmware
);
401 wilc
->firmware
= wilc_firmware
;
408 static int linux_wlan_start_firmware(struct net_device
*dev
)
410 struct wilc_vif
*vif
;
414 vif
= netdev_priv(dev
);
417 ret
= wilc_wlan_start(wilc
);
421 ret
= wilc_lock_timeout(wilc
, &wilc
->sync_event
, 5000);
428 static int wilc1000_firmware_download(struct net_device
*dev
)
430 struct wilc_vif
*vif
;
434 vif
= netdev_priv(dev
);
437 if (!wilc
->firmware
) {
438 netdev_err(dev
, "Firmware buffer is NULL\n");
442 ret
= wilc_wlan_firmware_download(wilc
, wilc
->firmware
->data
,
443 wilc
->firmware
->size
);
447 release_firmware(wilc
->firmware
);
448 wilc
->firmware
= NULL
;
450 netdev_dbg(dev
, "Download Succeeded\n");
455 static int linux_wlan_init_test_config(struct net_device
*dev
,
456 struct wilc_vif
*vif
)
458 unsigned char c_val
[64];
459 unsigned char mac_add
[] = {0x00, 0x80, 0xC2, 0x5E, 0xa2, 0xff};
460 struct wilc
*wilc
= vif
->wilc
;
461 struct wilc_priv
*priv
;
462 struct host_if_drv
*hif_drv
;
464 netdev_dbg(dev
, "Start configuring Firmware\n");
465 priv
= wiphy_priv(dev
->ieee80211_ptr
->wiphy
);
466 hif_drv
= (struct host_if_drv
*)priv
->hif_drv
;
467 netdev_dbg(dev
, "Host = %p\n", hif_drv
);
468 wilc_get_mac_address(vif
, mac_add
);
470 netdev_dbg(dev
, "MAC address is : %pM\n", mac_add
);
471 wilc_get_chipid(wilc
, false);
475 if (!wilc_wlan_cfg_set(vif
, 1, WID_SET_DRV_HANDLER
, c_val
, 4, 0, 0))
479 if (!wilc_wlan_cfg_set(vif
, 0, WID_PC_TEST_MODE
, c_val
, 1, 0, 0))
482 c_val
[0] = INFRASTRUCTURE
;
483 if (!wilc_wlan_cfg_set(vif
, 0, WID_BSS_TYPE
, c_val
, 1, 0, 0))
486 c_val
[0] = RATE_AUTO
;
487 if (!wilc_wlan_cfg_set(vif
, 0, WID_CURRENT_TX_RATE
, c_val
, 1, 0, 0))
490 c_val
[0] = G_MIXED_11B_2_MODE
;
491 if (!wilc_wlan_cfg_set(vif
, 0, WID_11G_OPERATING_MODE
, c_val
, 1, 0,
496 if (!wilc_wlan_cfg_set(vif
, 0, WID_CURRENT_CHANNEL
, c_val
, 1, 0, 0))
499 c_val
[0] = G_SHORT_PREAMBLE
;
500 if (!wilc_wlan_cfg_set(vif
, 0, WID_PREAMBLE
, c_val
, 1, 0, 0))
503 c_val
[0] = AUTO_PROT
;
504 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_PROT_MECH
, c_val
, 1, 0, 0))
507 c_val
[0] = ACTIVE_SCAN
;
508 if (!wilc_wlan_cfg_set(vif
, 0, WID_SCAN_TYPE
, c_val
, 1, 0, 0))
511 c_val
[0] = SITE_SURVEY_OFF
;
512 if (!wilc_wlan_cfg_set(vif
, 0, WID_SITE_SURVEY
, c_val
, 1, 0, 0))
515 *((int *)c_val
) = 0xffff;
516 if (!wilc_wlan_cfg_set(vif
, 0, WID_RTS_THRESHOLD
, c_val
, 2, 0, 0))
519 *((int *)c_val
) = 2346;
520 if (!wilc_wlan_cfg_set(vif
, 0, WID_FRAG_THRESHOLD
, c_val
, 2, 0, 0))
524 if (!wilc_wlan_cfg_set(vif
, 0, WID_BCAST_SSID
, c_val
, 1, 0, 0))
528 if (!wilc_wlan_cfg_set(vif
, 0, WID_QOS_ENABLE
, c_val
, 1, 0, 0))
531 c_val
[0] = NO_POWERSAVE
;
532 if (!wilc_wlan_cfg_set(vif
, 0, WID_POWER_MANAGEMENT
, c_val
, 1, 0, 0))
535 c_val
[0] = NO_SECURITY
; /* NO_ENCRYPT, 0x79 */
536 if (!wilc_wlan_cfg_set(vif
, 0, WID_11I_MODE
, c_val
, 1, 0, 0))
539 c_val
[0] = OPEN_SYSTEM
;
540 if (!wilc_wlan_cfg_set(vif
, 0, WID_AUTH_TYPE
, c_val
, 1, 0, 0))
543 strcpy(c_val
, "123456790abcdef1234567890");
544 if (!wilc_wlan_cfg_set(vif
, 0, WID_WEP_KEY_VALUE
, c_val
,
545 (strlen(c_val
) + 1), 0, 0))
548 strcpy(c_val
, "12345678");
549 if (!wilc_wlan_cfg_set(vif
, 0, WID_11I_PSK
, c_val
, (strlen(c_val
)), 0,
553 strcpy(c_val
, "password");
554 if (!wilc_wlan_cfg_set(vif
, 0, WID_1X_KEY
, c_val
, (strlen(c_val
) + 1),
562 if (!wilc_wlan_cfg_set(vif
, 0, WID_1X_SERV_ADDR
, c_val
, 4, 0, 0))
566 if (!wilc_wlan_cfg_set(vif
, 0, WID_LISTEN_INTERVAL
, c_val
, 1, 0, 0))
570 if (!wilc_wlan_cfg_set(vif
, 0, WID_DTIM_PERIOD
, c_val
, 1, 0, 0))
573 c_val
[0] = NORMAL_ACK
;
574 if (!wilc_wlan_cfg_set(vif
, 0, WID_ACK_POLICY
, c_val
, 1, 0, 0))
578 if (!wilc_wlan_cfg_set(vif
, 0, WID_USER_CONTROL_ON_TX_POWER
, c_val
, 1,
583 if (!wilc_wlan_cfg_set(vif
, 0, WID_TX_POWER_LEVEL_11A
, c_val
, 1, 0,
588 if (!wilc_wlan_cfg_set(vif
, 0, WID_TX_POWER_LEVEL_11B
, c_val
, 1, 0,
592 *((int *)c_val
) = 100;
593 if (!wilc_wlan_cfg_set(vif
, 0, WID_BEACON_INTERVAL
, c_val
, 2, 0, 0))
596 c_val
[0] = REKEY_DISABLE
;
597 if (!wilc_wlan_cfg_set(vif
, 0, WID_REKEY_POLICY
, c_val
, 1, 0, 0))
600 *((int *)c_val
) = 84600;
601 if (!wilc_wlan_cfg_set(vif
, 0, WID_REKEY_PERIOD
, c_val
, 4, 0, 0))
604 *((int *)c_val
) = 500;
605 if (!wilc_wlan_cfg_set(vif
, 0, WID_REKEY_PACKET_COUNT
, c_val
, 4, 0,
610 if (!wilc_wlan_cfg_set(vif
, 0, WID_SHORT_SLOT_ALLOWED
, c_val
, 1, 0,
614 c_val
[0] = G_SELF_CTS_PROT
;
615 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_ERP_PROT_TYPE
, c_val
, 1, 0, 0))
619 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_ENABLE
, c_val
, 1, 0, 0))
622 c_val
[0] = HT_MIXED_MODE
;
623 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_OPERATING_MODE
, c_val
, 1, 0,
628 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_TXOP_PROT_DISABLE
, c_val
, 1, 0,
632 memcpy(c_val
, mac_add
, 6);
634 if (!wilc_wlan_cfg_set(vif
, 0, WID_MAC_ADDR
, c_val
, 6, 0, 0))
637 c_val
[0] = DETECT_PROTECT_REPORT
;
638 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_OBSS_NONHT_DETECTION
, c_val
, 1,
642 c_val
[0] = RTS_CTS_NONHT_PROT
;
643 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_HT_PROT_TYPE
, c_val
, 1, 0, 0))
647 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_RIFS_PROT_ENABLE
, c_val
, 1, 0,
651 c_val
[0] = MIMO_MODE
;
652 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_SMPS_MODE
, c_val
, 1, 0, 0))
656 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_CURRENT_TX_MCS
, c_val
, 1, 0,
661 if (!wilc_wlan_cfg_set(vif
, 0, WID_11N_IMMEDIATE_BA_ENABLED
, c_val
, 1,
671 void wilc1000_wlan_deinit(struct net_device
*dev
)
673 struct wilc_vif
*vif
;
676 vif
= netdev_priv(dev
);
680 netdev_err(dev
, "wl is NULL\n");
684 if (wl
->initialized
) {
685 netdev_info(dev
, "Deinitializing wilc1000...\n");
687 if (!wl
->dev_irq_num
&&
688 wl
->hif_func
->disable_interrupt
) {
689 mutex_lock(&wl
->hif_cs
);
690 wl
->hif_func
->disable_interrupt(wl
);
691 mutex_unlock(&wl
->hif_cs
);
696 wlan_deinitialize_threads(dev
);
700 wilc_wlan_cleanup(dev
);
701 #if defined(PLAT_ALLWINNER_A20) || defined(PLAT_ALLWINNER_A23) || defined(PLAT_ALLWINNER_A31)
702 if (!wl
->dev_irq_num
&&
703 wl
->hif_func
->disable_interrupt
) {
704 mutex_lock(&wl
->hif_cs
);
705 wl
->hif_func
->disable_interrupt(wl
);
706 mutex_unlock(&wl
->hif_cs
);
709 wlan_deinit_locks(dev
);
711 wl
->initialized
= false;
713 netdev_dbg(dev
, "wilc1000 deinitialization Done\n");
715 netdev_dbg(dev
, "wilc1000 is not initialized\n");
719 static int wlan_init_locks(struct net_device
*dev
)
721 struct wilc_vif
*vif
;
724 vif
= netdev_priv(dev
);
727 mutex_init(&wl
->hif_cs
);
728 mutex_init(&wl
->rxq_cs
);
730 spin_lock_init(&wl
->txq_spinlock
);
731 sema_init(&wl
->txq_add_to_head_cs
, 1);
733 sema_init(&wl
->txq_event
, 0);
735 sema_init(&wl
->cfg_event
, 0);
736 sema_init(&wl
->sync_event
, 0);
738 sema_init(&wl
->txq_thread_started
, 0);
743 static int wlan_deinit_locks(struct net_device
*dev
)
745 struct wilc_vif
*vif
;
748 vif
= netdev_priv(dev
);
752 mutex_destroy(&wilc
->hif_cs
);
755 mutex_destroy(&wilc
->rxq_cs
);
760 static int wlan_initialize_threads(struct net_device
*dev
)
762 struct wilc_vif
*vif
;
765 vif
= netdev_priv(dev
);
768 wilc
->txq_thread
= kthread_run(linux_wlan_txq_task
, (void *)dev
,
770 if (!wilc
->txq_thread
) {
771 netdev_err(dev
, "couldn't create TXQ thread\n");
775 down(&wilc
->txq_thread_started
);
780 static void wlan_deinitialize_threads(struct net_device
*dev
)
782 struct wilc_vif
*vif
;
785 vif
= netdev_priv(dev
);
793 if (wl
->txq_thread
) {
794 kthread_stop(wl
->txq_thread
);
795 wl
->txq_thread
= NULL
;
799 int wilc1000_wlan_init(struct net_device
*dev
, struct wilc_vif
*vif
)
802 struct wilc
*wl
= vif
->wilc
;
804 if (!wl
->initialized
) {
805 wl
->mac_status
= WILC_MAC_STATUS_INIT
;
808 wlan_init_locks(dev
);
810 ret
= wilc_wlan_init(dev
);
816 if (wl
->gpio
>= 0 && init_irq(dev
)) {
821 ret
= wlan_initialize_threads(dev
);
824 goto _fail_wilc_wlan_
;
827 if (!wl
->dev_irq_num
&&
828 wl
->hif_func
->enable_interrupt
&&
829 wl
->hif_func
->enable_interrupt(wl
)) {
831 goto _fail_irq_init_
;
834 if (wilc_wlan_get_firmware(dev
)) {
836 goto _fail_irq_enable_
;
839 ret
= wilc1000_firmware_download(dev
);
842 goto _fail_irq_enable_
;
845 ret
= linux_wlan_start_firmware(dev
);
848 goto _fail_irq_enable_
;
851 if (wilc_wlan_cfg_get(vif
, 1, WID_FIRMWARE_VERSION
, 1, 0)) {
853 char firmware_ver
[20];
855 size
= wilc_wlan_cfg_get_val(WID_FIRMWARE_VERSION
,
857 sizeof(firmware_ver
));
858 firmware_ver
[size
] = '\0';
859 netdev_dbg(dev
, "Firmware Ver = %s\n", firmware_ver
);
861 ret
= linux_wlan_init_test_config(dev
, vif
);
864 netdev_err(dev
, "Failed to configure firmware\n");
866 goto _fail_fw_start_
;
869 wl
->initialized
= true;
876 if (!wl
->dev_irq_num
&&
877 wl
->hif_func
->disable_interrupt
)
878 wl
->hif_func
->disable_interrupt(wl
);
883 wlan_deinitialize_threads(dev
);
885 wilc_wlan_cleanup(dev
);
887 wlan_deinit_locks(dev
);
888 netdev_err(dev
, "WLAN Iinitialization FAILED\n");
890 netdev_dbg(dev
, "wilc1000 already initialized\n");
895 static int mac_init_fn(struct net_device
*ndev
)
897 netif_start_queue(ndev
);
898 netif_stop_queue(ndev
);
903 int wilc_mac_open(struct net_device
*ndev
)
905 struct wilc_vif
*vif
;
908 unsigned char mac_add
[ETH_ALEN
] = {0};
911 struct wilc_priv
*priv
;
914 vif
= netdev_priv(ndev
);
917 if (!wl
|| !wl
->dev
) {
918 netdev_err(ndev
, "wilc1000: SPI device not ready\n");
922 vif
= netdev_priv(ndev
);
924 priv
= wiphy_priv(vif
->ndev
->ieee80211_ptr
->wiphy
);
925 netdev_dbg(ndev
, "MAC OPEN[%p]\n", ndev
);
927 ret
= wilc_init_host_int(ndev
);
931 ret
= wilc1000_wlan_init(ndev
, vif
);
933 wilc_deinit_host_int(ndev
);
937 for (i
= 0; i
< wl
->vif_num
; i
++) {
938 if (ndev
== wl
->vif
[i
]->ndev
) {
939 if (vif
->iftype
== AP_MODE
) {
940 wilc_set_wfi_drv_handler(vif
,
941 wilc_get_vif_idx(vif
),
943 } else if (!wilc_wlan_get_num_conn_ifcs(wilc
)) {
944 wilc_set_wfi_drv_handler(vif
,
945 wilc_get_vif_idx(vif
),
948 if (memcmp(wilc
->vif
[i
^ 1]->bssid
,
949 wilc
->vif
[i
^ 1]->src_addr
, 6))
950 wilc_set_wfi_drv_handler(vif
,
951 wilc_get_vif_idx(vif
),
954 wilc_set_wfi_drv_handler(vif
,
955 wilc_get_vif_idx(vif
),
958 wilc_set_operation_mode(vif
, vif
->iftype
);
960 wilc_get_mac_address(vif
, mac_add
);
961 netdev_dbg(ndev
, "Mac address: %pM\n", mac_add
);
962 memcpy(wl
->vif
[i
]->src_addr
, mac_add
, ETH_ALEN
);
968 memcpy(ndev
->dev_addr
, wl
->vif
[i
]->src_addr
, ETH_ALEN
);
970 if (!is_valid_ether_addr(ndev
->dev_addr
)) {
971 netdev_err(ndev
, "Wrong MAC address\n");
972 wilc_deinit_host_int(ndev
);
973 wilc1000_wlan_deinit(ndev
);
977 wilc_mgmt_frame_register(vif
->ndev
->ieee80211_ptr
->wiphy
,
978 vif
->ndev
->ieee80211_ptr
,
979 vif
->g_struct_frame_reg
[0].frame_type
,
980 vif
->g_struct_frame_reg
[0].reg
);
981 wilc_mgmt_frame_register(vif
->ndev
->ieee80211_ptr
->wiphy
,
982 vif
->ndev
->ieee80211_ptr
,
983 vif
->g_struct_frame_reg
[1].frame_type
,
984 vif
->g_struct_frame_reg
[1].reg
);
985 netif_wake_queue(ndev
);
991 static struct net_device_stats
*mac_stats(struct net_device
*dev
)
993 struct wilc_vif
*vif
= netdev_priv(dev
);
995 return &vif
->netstats
;
998 static void wilc_set_multicast_list(struct net_device
*dev
)
1000 struct netdev_hw_addr
*ha
;
1001 struct wilc_priv
*priv
;
1002 struct host_if_drv
*hif_drv
;
1003 struct wilc_vif
*vif
;
1006 priv
= wiphy_priv(dev
->ieee80211_ptr
->wiphy
);
1007 vif
= netdev_priv(dev
);
1008 hif_drv
= (struct host_if_drv
*)priv
->hif_drv
;
1010 if (dev
->flags
& IFF_PROMISC
)
1013 if ((dev
->flags
& IFF_ALLMULTI
) ||
1014 (dev
->mc
.count
) > WILC_MULTICAST_TABLE_SIZE
) {
1015 wilc_setup_multicast_filter(vif
, false, 0);
1019 if ((dev
->mc
.count
) == 0) {
1020 wilc_setup_multicast_filter(vif
, true, 0);
1024 netdev_for_each_mc_addr(ha
, dev
) {
1025 memcpy(wilc_multicast_mac_addr_list
[i
], ha
->addr
, ETH_ALEN
);
1026 netdev_dbg(dev
, "Entry[%d]: %x:%x:%x:%x:%x:%x\n", i
,
1027 wilc_multicast_mac_addr_list
[i
][0],
1028 wilc_multicast_mac_addr_list
[i
][1],
1029 wilc_multicast_mac_addr_list
[i
][2],
1030 wilc_multicast_mac_addr_list
[i
][3],
1031 wilc_multicast_mac_addr_list
[i
][4],
1032 wilc_multicast_mac_addr_list
[i
][5]);
1036 wilc_setup_multicast_filter(vif
, true, (dev
->mc
.count
));
1039 static void linux_wlan_tx_complete(void *priv
, int status
)
1041 struct tx_complete_data
*pv_data
= priv
;
1043 dev_kfree_skb(pv_data
->skb
);
1047 int wilc_mac_xmit(struct sk_buff
*skb
, struct net_device
*ndev
)
1049 struct wilc_vif
*vif
;
1050 struct tx_complete_data
*tx_data
= NULL
;
1054 struct ethhdr
*eth_h
;
1057 vif
= netdev_priv(ndev
);
1060 if (skb
->dev
!= ndev
) {
1061 netdev_err(ndev
, "Packet not destined to this device\n");
1065 tx_data
= kmalloc(sizeof(*tx_data
), GFP_ATOMIC
);
1068 netif_wake_queue(ndev
);
1072 tx_data
->buff
= skb
->data
;
1073 tx_data
->size
= skb
->len
;
1076 eth_h
= (struct ethhdr
*)(skb
->data
);
1077 if (eth_h
->h_proto
== 0x8e88)
1078 netdev_dbg(ndev
, "EAPOL transmitted\n");
1080 ih
= (struct iphdr
*)(skb
->data
+ sizeof(struct ethhdr
));
1082 udp_buf
= (char *)ih
+ sizeof(struct iphdr
);
1083 if ((udp_buf
[1] == 68 && udp_buf
[3] == 67) ||
1084 (udp_buf
[1] == 67 && udp_buf
[3] == 68))
1085 netdev_dbg(ndev
, "DHCP Message transmitted, type:%x %x %x\n",
1086 udp_buf
[248], udp_buf
[249], udp_buf
[250]);
1088 vif
->netstats
.tx_packets
++;
1089 vif
->netstats
.tx_bytes
+= tx_data
->size
;
1090 tx_data
->bssid
= wilc
->vif
[vif
->idx
]->bssid
;
1091 queue_count
= wilc_wlan_txq_add_net_pkt(ndev
, (void *)tx_data
,
1092 tx_data
->buff
, tx_data
->size
,
1093 linux_wlan_tx_complete
);
1095 if (queue_count
> FLOW_CONTROL_UPPER_THRESHOLD
) {
1096 netif_stop_queue(wilc
->vif
[0]->ndev
);
1097 netif_stop_queue(wilc
->vif
[1]->ndev
);
1103 int wilc_mac_close(struct net_device
*ndev
)
1105 struct wilc_priv
*priv
;
1106 struct wilc_vif
*vif
;
1107 struct host_if_drv
*hif_drv
;
1110 vif
= netdev_priv(ndev
);
1112 if (!vif
|| !vif
->ndev
|| !vif
->ndev
->ieee80211_ptr
||
1113 !vif
->ndev
->ieee80211_ptr
->wiphy
)
1116 priv
= wiphy_priv(vif
->ndev
->ieee80211_ptr
->wiphy
);
1122 hif_drv
= (struct host_if_drv
*)priv
->hif_drv
;
1124 netdev_dbg(ndev
, "Mac close\n");
1132 if ((wl
->open_ifcs
) > 0)
1138 netif_stop_queue(vif
->ndev
);
1140 wilc_deinit_host_int(vif
->ndev
);
1143 if (wl
->open_ifcs
== 0) {
1144 netdev_dbg(ndev
, "Deinitializing wilc1000\n");
1146 wilc1000_wlan_deinit(ndev
);
1147 WILC_WFI_deinit_mon_interface();
1150 up(&close_exit_sync
);
1151 vif
->mac_opened
= 0;
1156 static int mac_ioctl(struct net_device
*ndev
, struct ifreq
*req
, int cmd
)
1160 u32 size
= 0, length
= 0;
1161 struct wilc_vif
*vif
;
1162 struct wilc_priv
*priv
;
1166 vif
= netdev_priv(ndev
);
1169 if (!wilc
->initialized
)
1175 struct iwreq
*wrq
= (struct iwreq
*)req
;
1177 size
= wrq
->u
.data
.length
;
1179 if (size
&& wrq
->u
.data
.pointer
) {
1180 buff
= memdup_user(wrq
->u
.data
.pointer
,
1181 wrq
->u
.data
.length
);
1183 return PTR_ERR(buff
);
1185 if (strncasecmp(buff
, "RSSI", length
) == 0) {
1186 priv
= wiphy_priv(vif
->ndev
->ieee80211_ptr
->wiphy
);
1187 ret
= wilc_get_rssi(vif
, &rssi
);
1188 netdev_info(ndev
, "RSSI :%d\n", rssi
);
1192 snprintf(buff
, size
, "rssi %d", rssi
);
1194 if (copy_to_user(wrq
->u
.data
.pointer
, buff
, size
)) {
1195 netdev_err(ndev
, "failed to copy\n");
1206 netdev_info(ndev
, "Command - %d - has been received\n", cmd
);
1219 void wilc_frmw_to_linux(struct wilc
*wilc
, u8
*buff
, u32 size
, u32 pkt_offset
)
1221 unsigned int frame_len
= 0;
1223 unsigned char *buff_to_send
= NULL
;
1224 struct sk_buff
*skb
;
1225 struct net_device
*wilc_netdev
;
1226 struct wilc_vif
*vif
;
1231 wilc_netdev
= get_if_handler(wilc
, buff
);
1236 vif
= netdev_priv(wilc_netdev
);
1240 buff_to_send
= buff
;
1242 skb
= dev_alloc_skb(frame_len
);
1246 skb
->dev
= wilc_netdev
;
1248 memcpy(skb_put(skb
, frame_len
), buff_to_send
, frame_len
);
1250 skb
->protocol
= eth_type_trans(skb
, wilc_netdev
);
1251 vif
->netstats
.rx_packets
++;
1252 vif
->netstats
.rx_bytes
+= frame_len
;
1253 skb
->ip_summed
= CHECKSUM_UNNECESSARY
;
1254 stats
= netif_rx(skb
);
1255 netdev_dbg(wilc_netdev
, "netif_rx ret value is: %d\n", stats
);
1259 void WILC_WFI_mgmt_rx(struct wilc
*wilc
, u8
*buff
, u32 size
)
1262 struct wilc_vif
*vif
;
1264 for (i
= 0; i
< wilc
->vif_num
; i
++) {
1265 vif
= netdev_priv(wilc
->vif
[i
]->ndev
);
1266 if (vif
->monitor_flag
) {
1267 WILC_WFI_monitor_rx(buff
, size
);
1272 vif
= netdev_priv(wilc
->vif
[1]->ndev
);
1273 if ((buff
[0] == vif
->g_struct_frame_reg
[0].frame_type
&& vif
->g_struct_frame_reg
[0].reg
) ||
1274 (buff
[0] == vif
->g_struct_frame_reg
[1].frame_type
&& vif
->g_struct_frame_reg
[1].reg
))
1275 WILC_WFI_p2p_rx(wilc
->vif
[1]->ndev
, buff
, size
);
1278 void wilc_netdev_cleanup(struct wilc
*wilc
)
1281 struct wilc_vif
*vif
[NUM_CONCURRENT_IFC
];
1283 if (wilc
&& (wilc
->vif
[0]->ndev
|| wilc
->vif
[1]->ndev
)) {
1284 unregister_inetaddr_notifier(&g_dev_notifier
);
1286 for (i
= 0; i
< NUM_CONCURRENT_IFC
; i
++)
1287 vif
[i
] = netdev_priv(wilc
->vif
[i
]->ndev
);
1290 if (wilc
&& wilc
->firmware
)
1291 release_firmware(wilc
->firmware
);
1293 if (wilc
&& (wilc
->vif
[0]->ndev
|| wilc
->vif
[1]->ndev
)) {
1294 wilc_lock_timeout(wilc
, &close_exit_sync
, 5 * 1000);
1296 for (i
= 0; i
< NUM_CONCURRENT_IFC
; i
++)
1297 if (wilc
->vif
[i
]->ndev
)
1298 if (vif
[i
]->mac_opened
)
1299 wilc_mac_close(wilc
->vif
[i
]->ndev
);
1301 for (i
= 0; i
< NUM_CONCURRENT_IFC
; i
++) {
1302 unregister_netdev(wilc
->vif
[i
]->ndev
);
1303 wilc_free_wiphy(wilc
->vif
[i
]->ndev
);
1304 free_netdev(wilc
->vif
[i
]->ndev
);
1310 EXPORT_SYMBOL_GPL(wilc_netdev_cleanup
);
1312 int wilc_netdev_init(struct wilc
**wilc
, struct device
*dev
, int io_type
,
1313 int gpio
, const struct wilc_hif_func
*ops
)
1316 struct wilc_vif
*vif
;
1317 struct net_device
*ndev
;
1320 sema_init(&close_exit_sync
, 0);
1322 wl
= kzalloc(sizeof(*wl
), GFP_KERNEL
);
1327 wl
->io_type
= io_type
;
1331 register_inetaddr_notifier(&g_dev_notifier
);
1333 for (i
= 0; i
< NUM_CONCURRENT_IFC
; i
++) {
1334 ndev
= alloc_etherdev(sizeof(struct wilc_vif
));
1338 vif
= netdev_priv(ndev
);
1339 memset(vif
, 0, sizeof(struct wilc_vif
));
1342 strcpy(ndev
->name
, "wlan%d");
1344 strcpy(ndev
->name
, "p2p%d");
1346 vif
->idx
= wl
->vif_num
;
1349 wl
->vif
[wl
->vif_num
]->ndev
= ndev
;
1351 ndev
->netdev_ops
= &wilc_netdev_ops
;
1354 struct wireless_dev
*wdev
;
1356 wdev
= wilc_create_wiphy(ndev
, dev
);
1359 SET_NETDEV_DEV(ndev
, dev
);
1362 netdev_err(ndev
, "Can't register WILC Wiphy\n");
1366 vif
->ndev
->ieee80211_ptr
= wdev
;
1367 vif
->ndev
->ml_priv
= vif
;
1368 wdev
->netdev
= vif
->ndev
;
1369 vif
->netstats
.rx_packets
= 0;
1370 vif
->netstats
.tx_packets
= 0;
1371 vif
->netstats
.rx_bytes
= 0;
1372 vif
->netstats
.tx_bytes
= 0;
1375 if (register_netdev(ndev
))
1378 vif
->iftype
= STATION_MODE
;
1379 vif
->mac_opened
= 0;
1384 EXPORT_SYMBOL_GPL(wilc_netdev_init
);
1386 MODULE_LICENSE("GPL");