]> Git Repo - esp-hosted.git/blame - esp_hosted_ng/host/main.c
Merge branch 'docfix/esp-hosted-ng-fg' into 'master'
[esp-hosted.git] / esp_hosted_ng / host / main.c
CommitLineData
774e9b2e
MM
1/*
2 * Espressif Systems Wireless LAN device driver
3 *
4 * Copyright (C) 2015-2021 Espressif Systems (Shanghai) PTE LTD
5 *
6 * This software file (the "File") is distributed by Espressif Systems (Shanghai)
7 * PTE LTD under the terms of the GNU General Public License Version 2, June 1991
8 * (the "License"). You may use, redistribute and/or modify this File in
9 * accordance with the terms and conditions of the License, a copy of which
10 * is available by writing to the Free Software Foundation, Inc.,
11 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA or on the
12 * worldwide web at http://www.gnu.org/licenses/old-licenses/gpl-2.0.txt.
13 *
14 * THE FILE IS DISTRIBUTED AS-IS, WITHOUT WARRANTY OF ANY KIND, AND THE
15 * IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE
16 * ARE EXPRESSLY DISCLAIMED. The License provides additional details about
17 * this warranty disclaimer.
18 */
19
20#include <linux/init.h>
21#include <linux/module.h>
22#include <linux/kernel.h>
23#include <linux/gpio.h>
24
25#include "esp.h"
26#include "esp_if.h"
27#include "esp_bt_api.h"
28#include "esp_api.h"
29#include "esp_cmd.h"
30
31#include "esp_cfg80211.h"
32
33#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 6, 0))
34 #define NDO_TX_TIMEOUT_PROTOTYPE() \
35 static void esp_tx_timeout(struct net_device *ndev, unsigned int txqueue)
36#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 29))
37 #define NDO_TX_TIMEOUT_PROTOTYPE() \
38 static void esp_tx_timeout(struct net_device *ndev)
39#else
40 #error "No symbol **ndo_tx_timeout** found in kernel < 2.6.29"
41#endif
42
43#define HOST_GPIO_PIN_INVALID -1
44static int resetpin = HOST_GPIO_PIN_INVALID;
45extern u8 ap_bssid[MAC_ADDR_LEN];
46
47module_param(resetpin, int, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
48MODULE_PARM_DESC(resetpin, "Host's GPIO pin number which is connected to ESP32's EN to reset ESP32 device");
49
50static void deinit_adapter(void);
51
52
53struct esp_adapter adapter;
54/*struct esp_device esp_dev;*/
55
56struct esp_adapter * esp_get_adapter(void)
57{
58 return &adapter;
59}
60
61void esp_process_new_packet_intr(struct esp_adapter *adapter)
62{
63 if(adapter)
64 queue_work(adapter->if_rx_workqueue, &adapter->if_rx_work);
65}
66
67static int process_tx_packet (struct sk_buff *skb)
68{
69 struct esp_wifi_device *priv = NULL;
70 struct esp_skb_cb *cb = NULL;
71 struct esp_payload_header *payload_header = NULL;
72 struct sk_buff *new_skb = NULL;
73 int ret = 0;
74 u8 pad_len = 0, realloc_skb = 0;
75 u16 len = 0;
76 u16 total_len = 0;
77 static u8 c = 0;
78 u8 *pos = NULL;
79
80 c++;
81 /* Get the priv */
82 cb = (struct esp_skb_cb *) skb->cb;
83 priv = cb->priv;
84
85 if (!priv) {
86 dev_kfree_skb(skb);
87 printk(KERN_INFO "%s: no priv\n", __func__);
88 return NETDEV_TX_OK;
89 }
90
91 if (netif_queue_stopped((const struct net_device *) priv->ndev)) {
92 printk(KERN_INFO "%s: Netif queue stopped\n", __func__);
93 return NETDEV_TX_BUSY;
94 }
95
96 len = skb->len;
97
98 /* Create space for payload header */
99 pad_len = sizeof(struct esp_payload_header);
100
101 total_len = len + pad_len;
102
103 /* Align buffer length */
104 pad_len += SKB_DATA_ADDR_ALIGNMENT - (total_len % SKB_DATA_ADDR_ALIGNMENT);
105
106 if (skb_headroom(skb) < pad_len) {
107 /* Headroom is not sufficient */
108 realloc_skb = 1;
109 }
110
111 if (realloc_skb || !IS_ALIGNED((unsigned long) skb->data, SKB_DATA_ADDR_ALIGNMENT)) {
112 /* Realloc SKB */
113 if (skb_linearize(skb)) {
114 priv->stats.tx_errors++;
115 dev_kfree_skb(skb);
116 printk(KERN_ERR "%s: Failed to linearize SKB", __func__);
117 return NETDEV_TX_OK;
118 }
119
120 new_skb = esp_alloc_skb(skb->len + pad_len);
121
122 if (!new_skb) {
123 printk(KERN_ERR "%s: Failed to allocate SKB", __func__);
124 priv->stats.tx_errors++;
125 dev_kfree_skb(skb);
126 return NETDEV_TX_OK;
127 }
128
129 pos = new_skb->data;
130 pos += pad_len;
131
132 /* Populate new SKB */
133 skb_copy_from_linear_data(skb, pos, skb->len);
134 skb_put(new_skb, skb->len + pad_len);
135
136 /* Replace old SKB */
137 dev_kfree_skb_any(skb);
138 skb = new_skb;
139 } else {
140 /* Realloc is not needed, Make space for interface header */
141 skb_push(skb, pad_len);
142 }
143
144 /* Set payload header */
145 payload_header = (struct esp_payload_header *) skb->data;
146 memset(payload_header, 0, pad_len);
147
148 payload_header->if_type = priv->if_type;
149 payload_header->if_num = priv->if_num;
150 payload_header->len = cpu_to_le16(len);
151 payload_header->offset = cpu_to_le16(pad_len);
152 payload_header->packet_type = PACKET_TYPE_DATA;
153
154 payload_header->checksum = cpu_to_le16(compute_checksum(skb->data, (len + pad_len)));
155
156 if (!priv->stop_data) {
157 ret = esp_send_packet(priv->adapter, skb);
158
159 if (ret) {
160/* printk(KERN_ERR "%s: Failed to send SKB", __func__);*/
161 priv->stats.tx_errors++;
162 } else {
163 priv->stats.tx_packets++;
164 priv->stats.tx_bytes += skb->len;
165 }
166 } else {
167 dev_kfree_skb_any(skb);
168 priv->stats.tx_dropped++;
169 }
170
171 return 0;
172}
173
174void esp_port_open(struct esp_wifi_device * priv)
175{
176 priv->port_open = 1;
177 priv->stop_data = 0;
178}
179
180void esp_port_close(struct esp_wifi_device * priv)
181{
182 if (!priv)
183 return;
184
185 priv->port_open = 0;
186 priv->stop_data = 1;
187}
188
189void print_capabilities(u32 cap)
190{
191 printk(KERN_INFO "Capabilities: 0x%x. Features supported are:\n", cap);
192 if (cap & ESP_WLAN_SDIO_SUPPORT)
193 printk(KERN_INFO "\t * WLAN on SDIO\n");
194 else if (cap & ESP_WLAN_SPI_SUPPORT)
195 printk(KERN_INFO "\t * WLAN on SPI\n");
196
197 if ((cap & ESP_BT_UART_SUPPORT) ||
198 (cap & ESP_BT_SDIO_SUPPORT) ||
199 (cap & ESP_BT_SPI_SUPPORT)) {
200 printk(KERN_INFO "\t * BT/BLE\n");
201 if (cap & ESP_BT_UART_SUPPORT)
202 printk(KERN_INFO "\t - HCI over UART\n");
203 if (cap & ESP_BT_SDIO_SUPPORT)
204 printk(KERN_INFO "\t - HCI over SDIO\n");
205 if (cap & ESP_BT_SPI_SUPPORT)
206 printk(KERN_INFO "\t - HCI over SPI\n");
207
208 if ((cap & ESP_BLE_ONLY_SUPPORT) && (cap & ESP_BR_EDR_ONLY_SUPPORT))
209 printk(KERN_INFO "\t - BT/BLE dual mode\n");
210 else if (cap & ESP_BLE_ONLY_SUPPORT)
211 printk(KERN_INFO "\t - BLE only\n");
212 else if (cap & ESP_BR_EDR_ONLY_SUPPORT)
213 printk(KERN_INFO "\t - BR EDR only\n");
214 }
215}
216
217void process_capabilities(struct esp_adapter *adapter)
218{
219 printk(KERN_INFO "ESP peripheral capabilities: 0x%x\n", adapter->capabilities);
220
221 /* Reset BT */
222 esp_deinit_bt(adapter);
223
224 if ((adapter->capabilities & ESP_BT_SPI_SUPPORT) ||
225 (adapter->capabilities & ESP_BT_SDIO_SUPPORT)) {
226 msleep(200);
227 printk(KERN_INFO "ESP Bluetooth init\n");
228 esp_init_bt(adapter);
229 }
230}
231
232static int check_esp_version(struct fw_version *ver)
233{
234 printk(KERN_INFO "esp32: ESP Firmware version: %u.%u.%u\n",
235 ver->major1, ver->major2, ver->minor);
236 if (!ver->major1) {
237 printk(KERN_ERR "Incompatible ESP firmware release detected, Please use correct ESP-Hosted branch/compatible release\n");
238 return -1;
239 }
240 return 0;
241}
242
243static void print_reset_reason(uint32_t reason)
244{
245 switch (reason)
246 {
247 case 1 : printk(KERN_INFO "POWERON_RESET\n");break; /**<1, Vbat power on reset*/
248 case 3 : printk(KERN_INFO "SW_RESET\n");break; /**<3, Software reset digital core*/
249 case 4 : printk(KERN_INFO "OWDT_RESET\n");break; /**<4, Legacy watch dog reset digital core*/
250 case 5 : printk(KERN_INFO "DEEPSLEEP_RESET\n");break; /**<5, Deep Sleep reset digital core*/
251 case 6 : printk(KERN_INFO "SDIO_RESET\n");break; /**<6, Reset by SLC module, reset digital core*/
252 case 7 : printk(KERN_INFO "TG0WDT_SYS_RESET\n");break; /**<7, Timer Group0 Watch dog reset digital core*/
253 case 8 : printk(KERN_INFO "TG1WDT_SYS_RESET\n");break; /**<8, Timer Group1 Watch dog reset digital core*/
254 case 9 : printk(KERN_INFO "RTCWDT_SYS_RESET\n");break; /**<9, RTC Watch dog Reset digital core*/
255 case 10 : printk(KERN_INFO "INTRUSION_RESET\n");break; /**<10, Instrusion tested to reset CPU*/
256 case 11 : printk(KERN_INFO "TGWDT_CPU_RESET\n");break; /**<11, Time Group reset CPU*/
257 case 12 : printk(KERN_INFO "SW_CPU_RESET\n");break; /**<12, Software reset CPU*/
258 case 13 : printk(KERN_INFO "RTCWDT_CPU_RESET\n");break; /**<13, RTC Watch dog Reset CPU*/
259 case 14 : printk(KERN_INFO "EXT_CPU_RESET\n");break; /**<14, for APP CPU, reseted by PRO CPU*/
260 case 15 : printk(KERN_INFO "RTCWDT_BROWN_OUT_RESET\n");break;/**<15, Reset when the vdd voltage is not stable*/
261 case 16 : printk(KERN_INFO "RTCWDT_RTC_RESET\n");break; /**<16, RTC Watch dog reset digital core and rtc module*/
262 default : printk(KERN_INFO "Unknown[%u]\n",reason);break;
263 }
264}
265
266int process_fw_data(struct fw_data *fw_p)
267{
268 if (!fw_p) {
269 printk(KERN_ERR "Incomplete/incorrect bootup event received\n");
270 return -1;
271 }
272
273 printk(KERN_INFO "esp32: %s ESP chipset's last reset cause: ", __func__);
274 print_reset_reason(le32_to_cpu(fw_p->last_reset_reason));
275 return check_esp_version(&fw_p->version);
276}
277
278static int esp_open(struct net_device *ndev)
279{
280/* netif_start_queue(ndev);*/
281 return 0;
282}
283
284static int esp_stop(struct net_device *ndev)
285{
286/* netif_stop_queue(ndev);*/
287 return 0;
288}
289
290static struct net_device_stats* esp_get_stats(struct net_device *ndev)
291{
292 struct esp_wifi_device *priv = netdev_priv(ndev);
293
294 if (!priv)
295 return NULL;
296
297 return &priv->stats;
298}
299
300static int esp_set_mac_address(struct net_device *ndev, void *data)
301{
302 struct esp_wifi_device *priv = netdev_priv(ndev);
303 //struct sockaddr *mac_addr = data;
304
305 if (!priv || !priv->adapter)
306 return -EINVAL;
307
308 printk(KERN_INFO "%s:%u %pM\n", __func__, __LINE__, priv->mac_address);
309 /* TODO Handle in correct way */
310 ether_addr_copy(ndev->dev_addr, priv->mac_address/*mac_addr->sa_data*/);
311
312 clear_bit(ESP_CLEANUP_IN_PROGRESS, &priv->adapter->state_flags);
313 return 0;
314}
315
316NDO_TX_TIMEOUT_PROTOTYPE()
317{
318}
319
320static void esp_set_rx_mode(struct net_device *ndev)
321{
322}
323
324static int esp_hard_start_xmit(struct sk_buff *skb, struct net_device *ndev)
325{
326 struct esp_wifi_device *priv = NULL;
327 struct esp_skb_cb *cb = NULL;
328
329 if (!skb || !ndev)
330 return NETDEV_TX_OK;
331
332 priv = netdev_priv(ndev);
333 if (!priv) {
334 dev_kfree_skb(skb);
335 return NETDEV_TX_OK;
336 }
337
338 if (!priv->port_open) {
339 priv->stats.tx_dropped++;
340 /*printk(KERN_ERR "esp32: %s: port not yet open\n", __func__);*/
341 dev_kfree_skb(skb);
342 return NETDEV_TX_OK;
343 }
344
345 if (!skb->len || (skb->len > ETH_FRAME_LEN)) {
346 printk(KERN_ERR "esp32: %s: Bad len %d\n", __func__, skb->len);
347 priv->stats.tx_dropped++;
348 dev_kfree_skb(skb);
349 return NETDEV_TX_OK;
350 }
351
352 cb = (struct esp_skb_cb *) skb->cb;
353 cb->priv = priv;
354
355 return process_tx_packet(skb);
356}
357
358static const struct net_device_ops esp_netdev_ops = {
359 .ndo_open = esp_open,
360 .ndo_stop = esp_stop,
361 .ndo_start_xmit = esp_hard_start_xmit,
362 .ndo_set_mac_address = esp_set_mac_address,
363 .ndo_validate_addr = eth_validate_addr,
364 .ndo_tx_timeout = esp_tx_timeout,
365 .ndo_get_stats = esp_get_stats,
366 .ndo_set_rx_mode = esp_set_rx_mode,
367};
368
369
370void esp_init_priv(struct net_device *ndev)
371{
372 ndev->netdev_ops = &esp_netdev_ops;
373 ndev->needed_headroom = roundup(sizeof(struct esp_payload_header) +
374 INTERFACE_HEADER_PADDING, 4);
375}
376
377#if 0
378void start_scan(struct esp_wifi_device *priv, char *ssid, u8 ssid_len)
379{
380 struct cmd_scan_config *scan_cmd;
381 struct sk_buff *skb;
382 struct esp_payload_header *payload_header;
383 u16 total_len;
384
385 if (!priv->adapter) {
386 printk(KERN_ERR "%s: empty adapter\n", __func__);
387 return 0;
388 }
389
390 total_len = sizeof(struct esp_payload_header) +
391 sizeof(struct cmd_scan_config);
392
393 if (ssid_len) {
394 total_len += ssid_len + 1;
395 }
396
397 skb = esp_alloc_skb(total_len);
398
399 if (!skb) {
400 printk(KERN_ERR "%s: Failed to allocate command buffer\n", __func__);
401 return;
402 }
403
404 payload_header = skb_put(skb, total_len);
405 memset(payload_header, 0, total_len);
406
407 payload_header->if_type = ESP_PRIV_IF;
408 payload_header->len = total_len - sizeof(struct esp_payload_header);
409 payload_header->offset = sizeof(struct esp_payload_header);
410
411 scan_cmd = (struct cmd_scan_config *) (skb->data + payload_header->offset);
412 scan_cmd->header.cmd_code = CONFIG_SCAN_CMD;
413 scan_cmd->header.if_type = ESP_STA_IF;
414 scan_cmd->header.action = 1;
415
416 if (ssid_len) {
417 scan_cmd->header.len = ssid_len + 1;
418 memcpy(scan_cmd->ssid, ssid, ssid_len);
419 }
420
421 esp_send_packet(priv->adapter, skb);
422}
423#endif
424
425static int add_network_iface(void)
426{
427 int ret = 0;
428 struct esp_adapter * adapter = esp_get_adapter();
429
430 if (!adapter) {
431 printk(KERN_INFO "%s: adapter not yet init\n", __func__);
432 return -EINVAL;
433 }
434
435 ret = esp_cfg80211_register(adapter);
436 if (ret) {
437 printk(KERN_ERR "Failed to register with cfg80211 (err code 0x%x)\n", ret);
438 return ret;
439 }
440
441 rtnl_lock();
442 esp_cfg80211_add_iface(adapter->wiphy, "espsta%d", 1, NL80211_IFTYPE_STATION, NULL);
443 rtnl_unlock();
444
445 return 0;
446}
447
448int esp_add_card(struct esp_adapter *adapter)
449{
450 int ret = 0;
451
452 ret = init_esp_dev(adapter);
453 if (ret) {
454 printk(KERN_ERR "Failed to init ESP device (err code 0x%x)\n", ret);
455 return ret;
456 }
457
458 ret = add_network_iface();
459
460 return ret;
461}
462
463void esp_remove_network_interfaces(struct esp_adapter *adapter)
464{
465 uint8_t iface_idx = 0;
466 struct net_device *ndev = NULL;
467 struct esp_wifi_device *priv = NULL;
468
469 for (iface_idx=0; iface_idx < ESP_MAX_INTERFACE; iface_idx++) {
470
471 priv = adapter->priv[iface_idx];
472
473 if (!priv)
474 continue;
475
476 if (!test_bit(ESP_NETWORK_UP, &priv->priv_flags))
477 continue;
478
479 /* stop and unregister network */
480 ndev = priv->ndev;
481
482 if (ndev) {
483
484 if (netif_carrier_ok(ndev))
485 netif_carrier_off(ndev);
486
487 netif_device_detach(ndev);
488
489 if (ndev->reg_state == NETREG_REGISTERED) {
490 unregister_netdev(ndev);
491 free_netdev(ndev);
492 ndev = NULL;
493 }
494 }
495 clear_bit(ESP_NETWORK_UP, &priv->priv_flags);
496 }
497
498 if (adapter->wiphy) {
499
500 wiphy_unregister(adapter->wiphy);
501 wiphy_free(adapter->wiphy);
502 adapter->wiphy = NULL;
503 }
504}
505
506int esp_remove_card(struct esp_adapter *adapter)
507{
508 uint8_t iface_idx = 0;
509
510 if (!adapter) {
511 return 0;
512 }
513
514#if 0
515 /* For SDIO, card gets removed from thread that remove hardware
516 * i.e. which does rmmod or kernel which calls esp_remove.
517 *
518 * For SPI, there is possibility that if_rx_workqueue
519 * itself call this function. to avoid deadlock, do not flush for SPI */
520 if (adapter->capabilities & ESP_WLAN_SDIO_SUPPORT)
521 if (adapter->if_rx_workqueue)
522 flush_workqueue(adapter->if_rx_workqueue);
523#endif
524
525 deinit_esp_dev(adapter);
526
527 esp_remove_network_interfaces(adapter);
528
529 for (iface_idx=0; iface_idx < ESP_MAX_INTERFACE; iface_idx++) {
530 esp_port_close(adapter->priv[iface_idx]);
531 adapter->priv[iface_idx] = NULL;
532 }
533
534 return 0;
535}
536
537struct esp_wifi_device * get_priv_from_payload_header(
538 struct esp_payload_header *header)
539{
540 struct esp_wifi_device *priv = NULL;
541 u8 i = 0;
542
543 if (!header)
544 return NULL;
545
546 for (i = 0; i < ESP_MAX_INTERFACE; i++) {
547 priv = adapter.priv[i];
548
549 if (!priv)
550 continue;
551
552 if (priv->if_type == header->if_type &&
553 priv->if_num == header->if_num) {
554 return priv;
555 }
556 }
557 return NULL;
558}
559
560static void process_esp_bootup_event(struct esp_adapter *adapter,
561 struct esp_internal_bootup_event *evt)
562{
563 if (!adapter || !evt) {
564 printk(KERN_ERR "%s: Invalid arguments\n", __func__);
565 return;
566 }
567
568 if (evt->header.status) {
569 printk(KERN_ERR "%s: Incorrect ESP bootup event\n", __func__);
570 return;
571 }
572
573 printk (KERN_INFO "\nReceived ESP bootup event\n");
574 process_event_esp_bootup(adapter, evt->data, evt->len);
575}
576
577static int process_internal_event(struct esp_adapter *adapter,
578 struct sk_buff *skb)
579{
580 struct event_header *header = NULL;
581
582 if (!skb || !adapter) {
583 printk (KERN_ERR "esp32: Incorrect event data!\n");
584 return -1;
585 }
586
587 header = (struct event_header *) (skb->data);
588
589 switch (header->event_code) {
590
591 case ESP_INTERNAL_BOOTUP_EVENT:
592 process_esp_bootup_event(adapter,
593 (struct esp_internal_bootup_event *)(skb->data));
594 break;
595
596 default:
597 printk(KERN_INFO "%s:%u unhandled internal event[%u]\n",
598 __func__, __LINE__, header->event_code);
599 break;
600 }
601
602 return 0;
603}
604
605static void process_rx_packet(struct esp_adapter *adapter, struct sk_buff *skb)
606{
607 struct esp_wifi_device *priv = NULL;
608 struct esp_payload_header *payload_header = NULL;
609 u16 len = 0, offset = 0;
610 struct hci_dev *hdev = adapter->hcidev;
611 u8 *type = NULL;
612 struct sk_buff * eap_skb = NULL;
613 struct ethhdr * eth = NULL;
614
615 if (!skb)
616 return;
617
618 /* get the paload header */
619 payload_header = (struct esp_payload_header *) skb->data;
620
621 len = le16_to_cpu(payload_header->len);
622 offset = le16_to_cpu(payload_header->offset);
623
624 /*print_hex_dump(KERN_ERR , "rx: ", DUMP_PREFIX_ADDRESS, 16, 1, skb->data, len, 1);*/
625
626 payload_header->checksum = 0;
627
628 /* chop off the header from skb */
629 skb_pull(skb, offset);
630
631 if (payload_header->if_type == ESP_STA_IF || payload_header->if_type == ESP_AP_IF) {
632
633 /* retrieve priv based on payload header contents */
634 priv = get_priv_from_payload_header(payload_header);
635
636 if (!priv) {
637 printk(KERN_ERR "%s: empty priv\n", __func__);
638 dev_kfree_skb_any(skb);
639 return;
640 }
641
642 if (payload_header->packet_type == PACKET_TYPE_EAPOL) {
643 esp_port_open(priv);
644
645 eap_skb = alloc_skb(skb->len, GFP_KERNEL);
646 if(!eap_skb) {
647 printk(KERN_INFO "%s:%u memory alloc failed\n",__func__, __LINE__);
648 return;
649 }
650 eap_skb->dev = priv->ndev;
651
652 if (!IS_ALIGNED((unsigned long) eap_skb->data, SKB_DATA_ADDR_ALIGNMENT)) {
653 printk(KERN_INFO "%s:%u eap skb unaligned\n",__func__, __LINE__);
654 }
655
656 eth = skb_put(eap_skb, ETH_HLEN);
657 ether_addr_copy(eth->h_dest, /*skb->data*/priv->ndev->dev_addr);
658 ether_addr_copy(eth->h_source, /*skb->data+6*/ ap_bssid);
659 eth->h_proto = cpu_to_be16(ETH_P_PAE);
660
661 skb_put_data(eap_skb, skb->data, skb->len);
662 eap_skb->protocol = eth_type_trans(eap_skb, eap_skb->dev);
663
664 netif_rx(eap_skb);
665
666 } else if (payload_header->packet_type == PACKET_TYPE_DATA) {
667
668 skb->dev = priv->ndev;
669 skb->protocol = eth_type_trans(skb, priv->ndev);
670 skb->ip_summed = CHECKSUM_NONE;
671
672 priv->stats.rx_bytes += skb->len;
673 /* Forward skb to kernel */
674 netif_rx_ni(skb);
675
676 priv->stats.rx_packets++;
677 } else if (payload_header->packet_type == PACKET_TYPE_COMMAND_RESPONSE) {
678 process_command_response(priv->adapter, skb);
679 } else if (payload_header->packet_type == PACKET_TYPE_EVENT) {
680 process_event(priv, skb);
681 dev_kfree_skb_any(skb);
682 }
683
684 } else if (payload_header->if_type == ESP_HCI_IF) {
685 if (hdev) {
686
687 type = skb->data;
688 hci_skb_pkt_type(skb) = *type;
689 skb_pull(skb, 1);
690
691#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 13, 0))
692 if (hci_recv_frame(hdev, skb)) {
693#else
694 if (hci_recv_frame(skb)) {
695#endif
696 hdev->stat.err_rx++;
697 } else {
698 esp_hci_update_rx_counter(hdev, *type, skb->len);
699 }
700 }
701 } else if (payload_header->if_type == ESP_INTERNAL_IF) {
702
703 /* Queue event skb for processing in events workqueue */
704 skb_queue_tail(&adapter->events_skb_q, skb);
705
706 if (adapter->events_wq)
707 queue_work(adapter->events_wq, &adapter->events_work);
708 else
709 dev_kfree_skb_any(skb);
710
711 } else {
712 dev_kfree_skb_any(skb);
713 }
714}
715
716void esp_tx_pause(struct esp_wifi_device *priv)
717{
718 if (!priv || !priv->ndev)
719 return;
720
721 if (!netif_queue_stopped((const struct net_device *)priv->ndev)) {
722 netif_stop_queue(priv->ndev);
723 }
724}
725
726void esp_tx_resume(struct esp_wifi_device *priv)
727{
728 if (!priv || !priv->ndev)
729 return;
730
731 if (netif_queue_stopped((const struct net_device *)priv->ndev)) {
732 netif_wake_queue(priv->ndev);
733 }
734}
735
736struct sk_buff * esp_alloc_skb(u32 len)
737{
738 struct sk_buff *skb = NULL;
739
740 u8 offset;
741
742 skb = netdev_alloc_skb(NULL, len + INTERFACE_HEADER_PADDING);
743
744 if (skb) {
745 /* Align SKB data pointer */
746 offset = ((unsigned long)skb->data) & (SKB_DATA_ADDR_ALIGNMENT - 1);
747
748 if (offset)
749 skb_reserve(skb, INTERFACE_HEADER_PADDING - offset);
750 }
751
752 return skb;
753}
754
755
756static int esp_get_packets(struct esp_adapter *adapter)
757{
758 struct sk_buff *skb = NULL;
759
760 if (!adapter || !adapter->if_ops || !adapter->if_ops->read)
761 return -EINVAL;
762
763 skb = adapter->if_ops->read(adapter);
764
765 if (!skb)
766 return -EFAULT;
767
768 process_rx_packet(adapter, skb);
769
770 return 0;
771}
772
773int esp_send_packet(struct esp_adapter *adapter, struct sk_buff *skb)
774{
775 if (!adapter || !adapter->if_ops || !adapter->if_ops->write)
776 return -EINVAL;
777
778 return adapter->if_ops->write(adapter, skb);
779}
780
781static void esp_if_rx_work(struct work_struct *work)
782{
783 /* read inbound packet and forward it to network/serial interface */
784 esp_get_packets(&adapter);
785}
786
787static void esp_events_work(struct work_struct *work)
788{
789 struct sk_buff *skb = NULL;
790
791 skb = skb_dequeue(&adapter.events_skb_q);
792 if (!skb)
793 return;
794
795 process_internal_event(&adapter, skb);
796 dev_kfree_skb_any(skb);
797}
798
799static struct esp_adapter * init_adapter(void)
800{
801 memset(&adapter, 0, sizeof(adapter));
802
803 /* Prepare interface RX work */
804 adapter.if_rx_workqueue = alloc_workqueue("ESP_IF_RX_WORK_QUEUE", 0, 0);
805
806 if (!adapter.if_rx_workqueue) {
807 deinit_adapter();
808 return NULL;
809 }
810
811 INIT_WORK(&adapter.if_rx_work, esp_if_rx_work);
812
813 skb_queue_head_init(&adapter.events_skb_q);
814
815 adapter.events_wq = alloc_workqueue("ESP_EVENTS_WORKQUEUE", WQ_HIGHPRI, 0);
816
817 if (!adapter.events_wq) {
818 deinit_adapter();
819 return NULL;
820 }
821
822 INIT_WORK(&adapter.events_work, esp_events_work);
823
824 return &adapter;
825}
826
827static void deinit_adapter(void)
828{
829 skb_queue_purge(&adapter.events_skb_q);
830
831 if (adapter.events_wq)
832 destroy_workqueue(adapter.events_wq);
833
834 if (adapter.if_rx_workqueue)
835 destroy_workqueue(adapter.if_rx_workqueue);
836}
837
838static void esp_reset(void)
839{
840 if (resetpin != HOST_GPIO_PIN_INVALID) {
841 /* Check valid GPIO or not */
842 if (!gpio_is_valid(resetpin)) {
843 printk(KERN_WARNING "%s, ESP32: host resetpin (%d) configured is invalid GPIO\n", __func__, resetpin);
844 resetpin = HOST_GPIO_PIN_INVALID;
845 } else {
846 gpio_request(resetpin, "sysfs");
847
848 /* HOST's resetpin set to OUTPUT, HIGH */
849 gpio_direction_output(resetpin, true);
850
851 /* HOST's resetpin set to LOW */
852 gpio_set_value(resetpin, 0);
853 udelay(200);
854
855 /* HOST's resetpin set to INPUT */
856 gpio_direction_input(resetpin);
857
858 printk(KERN_DEBUG "%s, ESP32: Triggering ESP reset.\n", __func__);
859 }
860 }
861}
862
863
864static int __init esp_init(void)
865{
866 int ret = 0;
867 struct esp_adapter *adapter = NULL;
868
869 /* Reset ESP, Clean start ESP */
870 esp_reset();
871 msleep(200);
872
873 adapter = init_adapter();
874
875 if (!adapter)
876 return -EFAULT;
877
878 /* Init transport layer */
879 ret = esp_init_interface_layer(adapter);
880
881 if (ret != 0) {
882 deinit_adapter();
883 }
884
885 return ret;
886}
887
888static void __exit esp_exit(void)
889{
890 uint8_t iface_idx = 0;
891
892 for (iface_idx=0; iface_idx<ESP_MAX_INTERFACE; iface_idx++) {
893 cmd_deinit_interface(adapter.priv[iface_idx]);
894 }
895
896 esp_deinit_interface_layer();
897 deinit_adapter();
898
899 if (resetpin != HOST_GPIO_PIN_INVALID) {
900 gpio_free(resetpin);
901 }
902}
903MODULE_LICENSE("GPL");
904MODULE_AUTHOR("Amey Inamdar <[email protected]>");
905MODULE_AUTHOR("Mangesh Malusare <[email protected]>");
906MODULE_AUTHOR("Yogesh Mantri <[email protected]>");
907MODULE_DESCRIPTION("Wifi driver for ESP-Hosted solution");
908MODULE_VERSION("0.1");
909module_init(esp_init);
910module_exit(esp_exit);
This page took 0.116322 seconds and 4 git commands to generate.