net:wireless:Support eswin usb wifi ECR6600U
[platform/kernel/linux-starfive.git] / drivers / net / wireless / eswin / usb / ecrnx_usb.c
1 /**
2  ******************************************************************************
3  *
4  * @file ecrnx_usb.c
5  *
6  * @brief ECRNX usb init and management function
7  *
8  * Copyright (C) ESWIN 2015-2020
9  *
10  ******************************************************************************
11  */
12
13 #include <linux/module.h>
14 #include <linux/kthread.h>
15
16 #include "core.h"
17 //#include "debug.h"
18 #include "ecrnx_utils.h"
19 #include "ecrnx_cmds.h"
20 #include "ecrnx_defs.h"
21 #include "ecrnx_msg_rx.h"
22 #include "ipc_host.h"
23 #include "ipc_shared.h"
24 #include "ecrnx_events.h"
25 #include "ecrnx_usb.h"
26 #ifdef CONFIG_TEST_ESWIN_USB
27 #include "debug.h"
28 #endif
29 #ifdef CONFIG_ECRNX_WIFO_CAIL
30 #include "ecrnx_amt.h"
31 #endif
32
33
34 #define USB_ADDR_DATA                   (unsigned int)(0x200)
35
36 #ifdef CONFIG_ECRNX_SOFTMAC
37 #define FW_STR  "lmac"
38 #elif defined CONFIG_ECRNX_FULLMAC
39 #define FW_STR  "fmac"
40 #endif
41
42 #if defined(CONFIG_ECRNX_DEBUGFS_CUSTOM)
43 #include "ecrnx_debugfs_func.h"
44 #endif
45
46 extern const int nx_txdesc_cnt_msk[];
47
48 struct vendor_radiotap_hdr {
49     u8 oui[3];
50     u8 subns;
51     u16 len;
52     u8 data[];
53 };
54
55 #ifdef CONFIG_WEXT_PRIV
56 extern void priv_copy_data_wakeup(struct ecrnx_hw *ecrnx_hw, struct sk_buff *skb);
57 #endif
58
59 /**
60  * @brief: ipc_host_rxdesc_handler: Handle the reception of a Rx Descriptor
61  *  Called from general IRQ handler when status %IPC_IRQ_E2A_RXDESC is set
62  * @param {env} pointer to the usb Host environment
63  * @param {skb} received skb data
64  * @return: none
65  */
66 static int usb_host_rxdesc_handler(struct ipc_host_env_tag *env, struct sk_buff *skb)
67 {
68         u8 ret = 0;
69     // LMAC has triggered an IT saying that a reception has occurred.
70     // Then we first need to check the validity of the current hostbuf, and the validity
71     // of the next hostbufs too, because it is likely that several hostbufs have been
72     // filled within the time needed for this irq handling
73 #ifdef CONFIG_ECRNX_FULLMAC
74     // call the external function to indicate that a RX descriptor is received
75     ret = env->cb.recv_data_ind(env->pthis, skb);
76 #else
77     // call the external function to indicate that a RX packet is received
78     ret = env->cb.recv_data_ind(env->pthis, skb);
79 #endif //(CONFIG_ECRNX_FULLMAC)
80     //ECRNX_DBG("%s exit!!", __func__);
81         return ret;
82 }
83
84 /**
85  * @brief: usb_host_radar_handler  Handle the reception of radar events
86  * @param {env} pointer to the usb Host environment
87  * @param {skb} received skb data
88  * @return: none
89  */
90 static int usb_host_radar_handler(struct ipc_host_env_tag *env, struct sk_buff *skb)
91 {
92     int ret = 0;
93     
94 #ifdef CONFIG_ECRNX_RADAR
95     // LMAC has triggered an IT saying that a radar event has been sent to upper layer.
96     // Then we first need to check the validity of the current msg buf, and the validity
97     // of the next buffers too, because it is likely that several buffers have been
98     // filled within the time needed for this irq handling
99     // call the external function to indicate that a RX packet is received
100     spin_lock(&((struct ecrnx_hw *)env->pthis)->radar.lock);
101     ret = env->cb.recv_radar_ind(env->pthis, skb);
102     spin_unlock(&((struct ecrnx_hw *)env->pthis)->radar.lock);
103 #endif /* CONFIG_ECRNX_RADAR */
104     return ret;
105 }
106
107 /**
108  * @brief: usb_host_unsup_rx_vec_handler  Handle the reception of unsupported rx vector
109  * @param {env} pointer to the usb Host environment
110  * @param {skb} received skb data
111  * @return: none
112  */
113 static int usb_host_unsup_rx_vec_handler(struct ipc_host_env_tag *env, struct sk_buff *skb)
114 {
115     return env->cb.recv_unsup_rx_vec_ind(env->pthis, skb);
116 }
117
118 /**
119  * @brief: usb_host_msg_handler  Handler for firmware message
120  * @param {env} pointer to the usb Host environment
121  * @param {skb} received skb data
122  * @return: none
123  */
124 static int usb_host_msg_handler(struct ipc_host_env_tag *env, struct sk_buff *skb)
125 {
126     // LMAC has triggered an IT saying that a message has been sent to upper layer.
127     // Then we first need to check the validity of the current msg buf, and the validity
128     // of the next buffers too, because it is likely that several buffers have been
129     // filled within the time needed for this irq handling
130     // call the external function to indicate that a RX packet is received
131     return env->cb.recv_msg_ind(env->pthis, skb->data);
132 }
133
134 /**
135  * @brief: usb_host_msgack_handler  Handle the reception of message acknowledgement
136  * @param {env} pointer to the usb Host environment
137  * @param {skb} received skb data
138  * @return: none
139  */
140 static int usb_host_msgack_handler(struct ipc_host_env_tag *env, struct sk_buff *skb)
141 {
142     ptr_addr hostid = *(ptr_addr *)skb->data;
143
144     ASSERT_ERR(hostid);
145
146     env->msga2e_hostid = NULL;
147     env->cb.recv_msgack_ind(env->pthis, (void*)hostid);
148
149     return 0;
150 }
151
152 /**
153  * @brief: usb_host_dbg_handler  Handle the reception of Debug event
154  * @param {env} pointer to the usb Host environment
155  * @param {skb} received skb data
156  * @return: none
157  */
158 static int usb_host_dbg_handler(struct ipc_host_env_tag *env, struct sk_buff *skb)
159 {
160     // LMAC has triggered an IT saying that a DBG message has been sent to upper layer.
161     // Then we first need to check the validity of the current buffer, and the validity
162     // of the next buffers too, because it is likely that several buffers have been
163     // filled within the time needed for this irq handling
164     // call the external function to indicate that a RX packet is received
165     return env->cb.recv_dbg_ind(env->pthis, skb);
166 }
167
168 /**
169  * @brief: usb_host_tx_cfm_handler  Handle the reception of TX confirmation
170  * @param {env} pointer to the usb Host environment
171  * @param {queue_idx} index of the hardware on which the confirmation has been received
172  * @param {user_pos} index of the user position
173  * @return: none
174  */
175 static int usb_host_tx_cfm_handler(struct ipc_host_env_tag *env, struct sk_buff *skb)
176 {
177     ptr_addr host_id;
178     struct sk_buff *skb_cfm;
179     struct ecrnx_txhdr *txhdr;
180
181 #ifdef CONFIG_ECRNX_FULLMAC
182     struct tx_cfm_tag *cfm;
183
184     cfm = (struct tx_cfm_tag *)skb->data;
185     //host_id = cfm->hostid;
186     memcpy((uint8_t *)&host_id, (uint8_t *)cfm->hostid, sizeof(ptr_addr));
187     if (host_id == 0) {
188         return 0;
189     }
190
191     ECRNX_DBG("%s:hostid(tx_skb):0x%08x, rx_skb: 0x%x \n", __func__, host_id, skb);
192     skb_cfm = (struct sk_buff *)host_id;
193     txhdr = (struct ecrnx_txhdr *)(*((ptr_addr*)skb_cfm->data - 1));
194     memcpy(&txhdr->hw_hdr.cfm, cfm, sizeof(*cfm));
195 #elif defined CONFIG_ECRNX_SOFTMAC
196     //TODO:
197 #endif
198
199     return env->cb.send_data_cfm(env->pthis, (void*)txhdr);
200 }
201
202 #ifdef CONFIG_ECRNX_WIFO_CAIL
203 /**
204  * @brief: usb_host_amt_rx_handler  Handle the reception of rx frame
205  * @param {frm_type} received frame type
206  * @param {skb} received skb data
207  * @return: none
208  */
209 void usb_host_amt_rx_handler(uint32_t frm_type, struct sk_buff *skb)
210 {
211     int need_free = 0;
212
213     ECRNX_DBG("%s enter, frame type: %d!!", __func__, frm_type);
214     if(!skb)
215     {
216         ECRNX_ERR("usb_host_amt_rx_handler input param error!! \n!");
217         return;
218     }
219
220     if (frm_type != USB_FRM_TYPE_RXDESC)
221     {
222         skb_pull(skb, SKB_DATA_COM_HD_OFFSET); //delete the frame common header
223     }
224
225     ECRNX_DBG("skb:0x%08x, skb_len:%d, frame type: %d!!", skb->data,skb->len, frm_type);
226
227     switch (frm_type)
228     {
229         case USB_FRM_TYPE_IWPRIV:
230         {
231                 /*printk("vif_start:%d, vif_monitor:%d \n", ecrnx_hw->vif_started, ecrnx_hw->monitor_vif);
232                         print_hex_dump(KERN_INFO, "iwpriv-cfm:", DUMP_PREFIX_ADDRESS, 32, 1,
233                         skb->data, skb->len, false);*/
234             amt_vif.rxlen = skb->len;
235                         memset(amt_vif.rxdata, 0, ECRNX_RXSIZE);
236             memcpy(amt_vif.rxdata, skb->data, skb->len);
237             amt_vif.rxdatas = 1;
238             wake_up(&amt_vif.rxdataq);
239                         need_free = 1;
240             break;
241         }
242         default:
243                 need_free = 1;
244             break;
245     }
246
247     if (need_free && skb) { // free the skb
248         ECRNX_DBG("skb free: 0x%x !! \n", skb);
249         dev_kfree_skb(skb);
250     }
251     ECRNX_DBG("%s exit!!", __func__);
252     return;
253 }
254 #endif
255
256
257 /**
258  * @brief: usb_host_rx_handler  Handle the reception of rx frame
259  * @param {frm_type} received frame type
260  * @param {env} pointer to the usb Host environment
261  * @param {skb} received skb data
262  * @return: none
263  */
264 void usb_host_rx_handler(uint32_t frm_type, struct ipc_host_env_tag *env, struct sk_buff *skb)
265 {
266     int ret = 1;
267
268     //ECRNX_DBG("%s enter, frame type: %d!!", __func__, frm_type);
269     if(!env || !skb)
270     {
271         ECRNX_ERR("usb_host_rx_handler input param error!! \n!");
272         return;
273     }
274
275     ((struct ecrnx_hw *)env->pthis)->usb_rx++;
276
277     if (frm_type != USB_FRM_TYPE_RXDESC)
278     {
279         skb_pull(skb, SKB_DATA_COM_HD_OFFSET); //delete the frame common header
280     }
281
282     //ECRNX_DBG("skb:0x%08x, skb_len:%d, frame type: %d!!", skb->data,skb->len, frm_type);
283
284     switch (frm_type)
285     {
286         case USB_FRM_TYPE_RXDESC:
287         {
288             // handle the RX descriptor reception
289                         usb_host_rxdesc_handler(env, skb); //just for current only one endpoint test
290             break;
291         }
292
293         case USB_FRM_TYPE_MSG_ACK:
294         {
295             if(1 == skb->len)
296             {
297                 ECRNX_PRINT("MSG_ACK len: 1");
298                 break;
299             }
300             ret = usb_host_msgack_handler(env, skb);
301             break;
302         }
303
304         case USB_FRM_TYPE_MSG:
305         {
306             ret = usb_host_msg_handler(env, skb);
307             break;
308         }
309
310         case USB_FRM_TYPE_TXCFM:
311         {
312             if(!env->pthis)
313             {
314                 ECRNX_ERR("env->pthis ptr error!! \n!");
315                 break;
316             }
317
318             /* add the spinlock which was missed during porting.
319                when skb->len more than 24 and skb contans more than one data cfm.
320                data cfm structure length is 24 byte.
321             */
322             spin_lock_bh(&((struct ecrnx_hw *)env->pthis)->tx_lock);
323             while(skb->len > sizeof(struct tx_cfm_tag))
324             {
325                 ret = usb_host_tx_cfm_handler(env, skb);
326                 skb_pull(skb, sizeof(struct tx_cfm_tag));
327             }
328             ret = usb_host_tx_cfm_handler(env, skb);
329             spin_unlock_bh(&((struct ecrnx_hw *)env->pthis)->tx_lock);
330             break;
331         }
332
333         case USB_FRM_TYPE_UNSUP_RX_VEC:
334         {
335             // handle the unsupported rx vector reception
336             ret = usb_host_unsup_rx_vec_handler(env, skb);
337             break;
338         }
339
340         case USB_FRM_TYPE_RADAR:
341         {
342             // handle the radar event reception
343             ret = usb_host_radar_handler(env, skb);
344             break;
345         }
346
347         case USB_FRM_TYPE_TBTT_SEC:
348         {
349             env->cb.sec_tbtt_ind(env->pthis);
350             break;
351         }
352
353         case USB_FRM_TYPE_TBTT_PRIM:
354         {
355             env->cb.prim_tbtt_ind(env->pthis);
356             break;
357         }
358
359         case USB_FRM_TYPE_DBG:
360         {
361             ECRNX_DBG("--%s:USB_FRM_TYPE_DBG, len:%d, slave:%s \n", __func__, skb->len, skb->data);
362             ret = usb_host_dbg_handler(env, skb);
363             break;
364         }
365         case USB_FRM_TYPE_IWPRIV:
366         {
367 #ifdef CONFIG_WEXT_PRIV
368 #if 0
369             struct ecrnx_hw *ecrnx_hw = (struct ecrnx_hw *)env->pthis;
370             struct ecrnx_vif* ecrnx_vif = ecrnx_hw->vif_table[0];
371
372             printk("vif_start:%d, vif_monitor:%d \n", ecrnx_hw->vif_started, ecrnx_hw->monitor_vif);
373             print_hex_dump(KERN_INFO, "iwpriv-cfm:", DUMP_PREFIX_ADDRESS, 32, 1,
374                         skb->data, skb->len, false);
375             ecrnx_vif->rxlen = skb->len;
376             memcpy(ecrnx_vif->rxdata, skb->data, skb->len);
377             ecrnx_vif->rxdatas = 1;
378             wake_up(&ecrnx_vif->rxdataq);
379 #else
380             priv_copy_data_wakeup((struct ecrnx_hw *)env->pthis, skb);
381 #endif
382
383 #endif
384                         ret = 0;
385             break;
386         }
387
388 #if defined(CONFIG_ECRNX_DEBUGFS_CUSTOM)
389         case USB_FRM_DEBUG_FS:
390         {
391             uint32_t debugfs_type = ((uint32_t*)skb->data)[0];
392             debugfs_resp.debugfs_type = debugfs_type;
393
394
395             if((debugfs_type != SLAVE_LOG_LEVEL) && \
396             (debugfs_type < SLAVE_DEBUGFS_MAX)){
397
398                 debugfs_resp.rxlen = skb->len-4;
399                 memcpy(debugfs_resp.rxdata, skb->data+4, debugfs_resp.rxlen);
400
401                 ECRNX_DBG("%s - wake_up()\n", __func__);
402                 debugfs_resp.rxdatas = 1;
403                 wake_up(&debugfs_resp.rxdataq);
404             }
405
406             break;
407         }
408 #endif
409         default:
410                 ret = 0;
411             break;
412     }
413
414     if (!ret && skb) { // free the skb
415         ECRNX_DBG("skb free: 0x%x, ret: %d!! \n", skb, ret);
416         dev_kfree_skb(skb);
417     }
418     //ECRNX_DBG("%s exit!!", __func__);
419     return;
420 }
421
422 /**
423  * @brief: ecrnx_usb_init  Initialize usb interface.
424  * @param {ecrnx_hw} Main driver data
425  * @return: u8
426  */
427 u8 ecrnx_usb_init(struct ecrnx_hw *ecrnx_hw)
428 {
429     ECRNX_DBG("%s entry!!", __func__);
430     // Save the pointer to the register base
431     ecrnx_hw->ipc_env->pthis = (void*)ecrnx_hw;
432
433     ECRNX_DBG("%s exit!!", __func__);
434     return 0;
435 }
436
437 /**
438  * @brief: ecrnx_usb_deinit  DeInitialize usb interface.
439  * @param {ecrnx_hw} Main driver data
440  * @return: none
441  */
442 void ecrnx_usb_deinit(struct ecrnx_hw *ecrnx_hw)
443 {
444     ECRNX_DBG(ECRNX_FN_ENTRY_STR);
445
446     memset(ecrnx_hw, 0, sizeof(struct ecrnx_hw));
447 }