]> git.ipfire.org Git - people/pmueller/ipfire-2.x.git/blob - src/patches/suse-2.6.27.25/patches.drivers/staging-add-rt2860-wireless-driver.patch
Reenabled linux-xen and xen-image build
[people/pmueller/ipfire-2.x.git] / src / patches / suse-2.6.27.25 / patches.drivers / staging-add-rt2860-wireless-driver.patch
1 From 52076881ca20d02dd8b4b14348a08a3479715252 Mon Sep 17 00:00:00 2001
2 From: Greg Kroah-Hartman <gregkh@suse.de>
3 Date: Tue, 28 Oct 2008 14:48:09 -0700
4 Subject: Staging: add rt2860 wireless driver
5
6 From: Greg Kroah-Hartman <gregkh@suse.de>
7
8 This is the Ralink RT2860 driver from the company that does horrible
9 things like reading a config file from /etc. However, the driver that
10 is currently under development from the wireless development community
11 is not working at all yet, so distros and users are using this version
12 instead (quite common hardware on a lot of netbook machines).
13
14 So here is this driver, for now, until the wireless developers get a
15 "clean" version into the main tree, or until this version is cleaned up
16 sufficiently to move out of the staging tree.
17
18 Ported to the Linux build system and cleaned up a bit already by me.
19
20 Cc: Linux wireless <linux-wireless@vger.kernel.org>
21 Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
22
23 ---
24 drivers/staging/Kconfig | 2
25 drivers/staging/Makefile | 1
26 drivers/staging/rt2860/2860_main_dev.c | 1377 +++
27 drivers/staging/rt2860/Kconfig | 5
28 drivers/staging/rt2860/Makefile | 41
29 drivers/staging/rt2860/TODO | 17
30 drivers/staging/rt2860/aironet.h | 210
31 drivers/staging/rt2860/ap.h | 557 +
32 drivers/staging/rt2860/chlist.h | 1296 +++
33 drivers/staging/rt2860/common/2860_rtmp_init.c | 922 ++
34 drivers/staging/rt2860/common/action.c | 1031 ++
35 drivers/staging/rt2860/common/action.h | 68
36 drivers/staging/rt2860/common/ba_action.c | 1802 +++++
37 drivers/staging/rt2860/common/cmm_data.c | 3469 ++++++++++
38 drivers/staging/rt2860/common/cmm_data_2860.c | 1240 +++
39 drivers/staging/rt2860/common/cmm_info.c | 3417 +++++++++
40 drivers/staging/rt2860/common/cmm_sanity.c | 1633 ++++
41 drivers/staging/rt2860/common/cmm_sync.c | 702 ++
42 drivers/staging/rt2860/common/cmm_wpa.c | 1606 ++++
43 drivers/staging/rt2860/common/dfs.c | 453 +
44 drivers/staging/rt2860/common/eeprom.c | 244
45 drivers/staging/rt2860/common/firmware.h | 558 +
46 drivers/staging/rt2860/common/md5.c | 1427 ++++
47 drivers/staging/rt2860/common/mlme.c | 8667 +++++++++++++++++++++++++
48 drivers/staging/rt2860/common/netif_block.c | 144
49 drivers/staging/rt2860/common/netif_block.h | 58
50 drivers/staging/rt2860/common/rtmp_init.c | 3757 ++++++++++
51 drivers/staging/rt2860/common/rtmp_tkip.c | 1607 ++++
52 drivers/staging/rt2860/common/rtmp_wep.c | 499 +
53 drivers/staging/rt2860/common/spectrum.c | 1877 +++++
54 drivers/staging/rt2860/config.mk | 245
55 drivers/staging/rt2860/dfs.h | 100
56 drivers/staging/rt2860/leap.h | 215
57 drivers/staging/rt2860/link_list.h | 134
58 drivers/staging/rt2860/md4.h | 42
59 drivers/staging/rt2860/md5.h | 107
60 drivers/staging/rt2860/mlme.h | 1447 ++++
61 drivers/staging/rt2860/oid.h | 995 ++
62 drivers/staging/rt2860/rt2860.h | 349 +
63 drivers/staging/rt2860/rt28xx.h | 2714 +++++++
64 drivers/staging/rt2860/rt_ate.c | 6025 +++++++++++++++++
65 drivers/staging/rt2860/rt_ate.h | 353 +
66 drivers/staging/rt2860/rt_config.h | 101
67 drivers/staging/rt2860/rt_linux.c | 1054 +++
68 drivers/staging/rt2860/rt_linux.h | 926 ++
69 drivers/staging/rt2860/rt_main_dev.c | 1686 ++++
70 drivers/staging/rt2860/rt_profile.c | 1976 +++++
71 drivers/staging/rt2860/rtmp.h | 7177 ++++++++++++++++++++
72 drivers/staging/rt2860/rtmp_ckipmic.h | 113
73 drivers/staging/rt2860/rtmp_def.h | 1588 ++++
74 drivers/staging/rt2860/rtmp_type.h | 94
75 drivers/staging/rt2860/spectrum.h | 322
76 drivers/staging/rt2860/spectrum_def.h | 95
77 drivers/staging/rt2860/sta/aironet.c | 1312 +++
78 drivers/staging/rt2860/sta/assoc.c | 1826 +++++
79 drivers/staging/rt2860/sta/auth.c | 474 +
80 drivers/staging/rt2860/sta/auth_rsp.c | 167
81 drivers/staging/rt2860/sta/connect.c | 2751 +++++++
82 drivers/staging/rt2860/sta/dls.c | 2201 ++++++
83 drivers/staging/rt2860/sta/rtmp_data.c | 2614 +++++++
84 drivers/staging/rt2860/sta/sanity.c | 420 +
85 drivers/staging/rt2860/sta/sync.c | 1961 +++++
86 drivers/staging/rt2860/sta/wpa.c | 2086 ++++++
87 drivers/staging/rt2860/sta_ioctl.c | 6944 ++++++++++++++++++++
88 drivers/staging/rt2860/wpa.h | 356 +
89 65 files changed, 89657 insertions(+)
90
91 --- a/drivers/staging/Kconfig
92 +++ b/drivers/staging/Kconfig
93 @@ -47,4 +47,6 @@ source "drivers/staging/agnx/Kconfig"
94
95 source "drivers/staging/otus/Kconfig"
96
97 +source "drivers/staging/rt2860/Kconfig"
98 +
99 endif # STAGING
100 --- a/drivers/staging/Makefile
101 +++ b/drivers/staging/Makefile
102 @@ -15,3 +15,4 @@ obj-$(CONFIG_ECHO) += echo/
103 obj-$(CONFIG_USB_ATMEL) += at76_usb/
104 obj-$(CONFIG_AGNX) += agnx/
105 obj-$(CONFIG_OTUS) += otus/
106 +obj-$(CONFIG_RT2860) += rt2860/
107 --- /dev/null
108 +++ b/drivers/staging/rt2860/2860_main_dev.c
109 @@ -0,0 +1,1377 @@
110 +/*
111 + *************************************************************************
112 + * Ralink Tech Inc.
113 + * 5F., No.36, Taiyuan St., Jhubei City,
114 + * Hsinchu County 302,
115 + * Taiwan, R.O.C.
116 + *
117 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
118 + *
119 + * This program is free software; you can redistribute it and/or modify *
120 + * it under the terms of the GNU General Public License as published by *
121 + * the Free Software Foundation; either version 2 of the License, or *
122 + * (at your option) any later version. *
123 + * *
124 + * This program is distributed in the hope that it will be useful, *
125 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
126 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
127 + * GNU General Public License for more details. *
128 + * *
129 + * You should have received a copy of the GNU General Public License *
130 + * along with this program; if not, write to the *
131 + * Free Software Foundation, Inc., *
132 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
133 + * *
134 + *************************************************************************
135 +
136 + Module Name:
137 + 2870_main_dev.c
138 +
139 + Abstract:
140 + Create and register network interface.
141 +
142 + Revision History:
143 + Who When What
144 + -------- ---------- ----------------------------------------------
145 +*/
146 +
147 +#include "rt_config.h"
148 +
149 +
150 +#ifdef MULTIPLE_CARD_SUPPORT
151 +// record whether the card in the card list is used in the card file
152 +extern UINT8 MC_CardUsed[];
153 +#endif // MULTIPLE_CARD_SUPPORT //
154 +
155 +
156 +extern INT __devinit rt28xx_probe(IN void *_dev_p, IN void *_dev_id_p,
157 + IN UINT argc, OUT PRTMP_ADAPTER *ppAd);
158 +
159 +static void rx_done_tasklet(unsigned long data);
160 +static void mgmt_dma_done_tasklet(unsigned long data);
161 +static void ac0_dma_done_tasklet(unsigned long data);
162 +static void ac1_dma_done_tasklet(unsigned long data);
163 +static void ac2_dma_done_tasklet(unsigned long data);
164 +static void ac3_dma_done_tasklet(unsigned long data);
165 +static void hcca_dma_done_tasklet(unsigned long data);
166 +static void fifo_statistic_full_tasklet(unsigned long data);
167 +
168 +
169 +/*---------------------------------------------------------------------*/
170 +/* Symbol & Macro Definitions */
171 +/*---------------------------------------------------------------------*/
172 +#define RT2860_INT_RX_DLY (1<<0) // bit 0
173 +#define RT2860_INT_TX_DLY (1<<1) // bit 1
174 +#define RT2860_INT_RX_DONE (1<<2) // bit 2
175 +#define RT2860_INT_AC0_DMA_DONE (1<<3) // bit 3
176 +#define RT2860_INT_AC1_DMA_DONE (1<<4) // bit 4
177 +#define RT2860_INT_AC2_DMA_DONE (1<<5) // bit 5
178 +#define RT2860_INT_AC3_DMA_DONE (1<<6) // bit 6
179 +#define RT2860_INT_HCCA_DMA_DONE (1<<7) // bit 7
180 +#define RT2860_INT_MGMT_DONE (1<<8) // bit 8
181 +
182 +#define INT_RX RT2860_INT_RX_DONE
183 +
184 +#define INT_AC0_DLY (RT2860_INT_AC0_DMA_DONE) //| RT2860_INT_TX_DLY)
185 +#define INT_AC1_DLY (RT2860_INT_AC1_DMA_DONE) //| RT2860_INT_TX_DLY)
186 +#define INT_AC2_DLY (RT2860_INT_AC2_DMA_DONE) //| RT2860_INT_TX_DLY)
187 +#define INT_AC3_DLY (RT2860_INT_AC3_DMA_DONE) //| RT2860_INT_TX_DLY)
188 +#define INT_HCCA_DLY (RT2860_INT_HCCA_DMA_DONE) //| RT2860_INT_TX_DLY)
189 +#define INT_MGMT_DLY RT2860_INT_MGMT_DONE
190 +
191 +/*---------------------------------------------------------------------*/
192 +/* Prototypes of Functions Used */
193 +/*---------------------------------------------------------------------*/
194 +/* function declarations */
195 +static INT __devinit rt2860_init_one (struct pci_dev *pci_dev, const struct pci_device_id *ent);
196 +static VOID __devexit rt2860_remove_one(struct pci_dev *pci_dev);
197 +static INT __devinit rt2860_probe(struct pci_dev *pci_dev, const struct pci_device_id *ent);
198 +void init_thread_task(PRTMP_ADAPTER pAd);
199 +static void __exit rt2860_cleanup_module(void);
200 +static int __init rt2860_init_module(void);
201 +
202 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
203 +#ifdef CONFIG_PM
204 +static int rt2860_suspend(struct pci_dev *pci_dev, pm_message_t state);
205 +static int rt2860_resume(struct pci_dev *pci_dev);
206 +#endif // CONFIG_PM //
207 +#endif
208 +
209 +
210 +//
211 +// Ralink PCI device table, include all supported chipsets
212 +//
213 +static struct pci_device_id rt2860_pci_tbl[] __devinitdata =
214 +{
215 + {PCI_DEVICE(NIC_PCI_VENDOR_ID, NIC2860_PCI_DEVICE_ID)}, //RT28602.4G
216 + {PCI_DEVICE(NIC_PCI_VENDOR_ID, NIC2860_PCIe_DEVICE_ID)},
217 + {PCI_DEVICE(NIC_PCI_VENDOR_ID, NIC2760_PCI_DEVICE_ID)},
218 + {PCI_DEVICE(NIC_PCI_VENDOR_ID, NIC2790_PCIe_DEVICE_ID)},
219 + {PCI_DEVICE(VEN_AWT_PCI_VENDOR_ID, VEN_AWT_PCIe_DEVICE_ID)},
220 + {0,} // terminate list
221 +};
222 +
223 +MODULE_DEVICE_TABLE(pci, rt2860_pci_tbl);
224 +#ifdef CONFIG_STA_SUPPORT
225 +MODULE_LICENSE("GPL");
226 +#ifdef MODULE_VERSION
227 +MODULE_VERSION(STA_DRIVER_VERSION);
228 +#endif
229 +#endif // CONFIG_STA_SUPPORT //
230 +
231 +
232 +//
233 +// Our PCI driver structure
234 +//
235 +static struct pci_driver rt2860_driver =
236 +{
237 + name: "rt2860",
238 + id_table: rt2860_pci_tbl,
239 + probe: rt2860_init_one,
240 +#if LINUX_VERSION_CODE >= 0x20412
241 + remove: __devexit_p(rt2860_remove_one),
242 +#else
243 + remove: __devexit(rt2860_remove_one),
244 +#endif
245 +
246 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
247 +#ifdef CONFIG_PM
248 + suspend: rt2860_suspend,
249 + resume: rt2860_resume,
250 +#endif
251 +#endif
252 +};
253 +
254 +
255 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
256 +#ifdef CONFIG_PM
257 +
258 +VOID RT2860RejectPendingPackets(
259 + IN PRTMP_ADAPTER pAd)
260 +{
261 + // clear PS packets
262 + // clear TxSw packets
263 +}
264 +
265 +static int rt2860_suspend(
266 + struct pci_dev *pci_dev,
267 + pm_message_t state)
268 +{
269 + struct net_device *net_dev = pci_get_drvdata(pci_dev);
270 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)NULL;
271 + INT32 retval;
272 +
273 +
274 + DBGPRINT(RT_DEBUG_TRACE, ("===> rt2860_suspend()\n"));
275 +
276 + if (net_dev == NULL)
277 + {
278 + DBGPRINT(RT_DEBUG_ERROR, ("net_dev == NULL!\n"));
279 + }
280 + else
281 + {
282 + pAd = (PRTMP_ADAPTER)net_dev->priv;
283 +
284 + /* we can not use IFF_UP because ra0 down but ra1 up */
285 + /* and 1 suspend/resume function for 1 module, not for each interface */
286 + /* so Linux will call suspend/resume function once */
287 + if (VIRTUAL_IF_NUM(pAd) > 0)
288 + {
289 + // avoid users do suspend after interface is down
290 +
291 + // stop interface
292 + netif_carrier_off(net_dev);
293 + netif_stop_queue(net_dev);
294 +
295 + // mark device as removed from system and therefore no longer available
296 + netif_device_detach(net_dev);
297 +
298 + // mark halt flag
299 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS);
300 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
301 +
302 + // take down the device
303 + rt28xx_close((PNET_DEV)net_dev);
304 +
305 + RT_MOD_DEC_USE_COUNT();
306 + }
307 + }
308 +
309 + // reference to http://vovo2000.com/type-lab/linux/kernel-api/linux-kernel-api.html
310 + // enable device to generate PME# when suspended
311 + // pci_choose_state(): Choose the power state of a PCI device to be suspended
312 + retval = pci_enable_wake(pci_dev, pci_choose_state(pci_dev, state), 1);
313 + // save the PCI configuration space of a device before suspending
314 + pci_save_state(pci_dev);
315 + // disable PCI device after use
316 + pci_disable_device(pci_dev);
317 +
318 + retval = pci_set_power_state(pci_dev, pci_choose_state(pci_dev, state));
319 +
320 + DBGPRINT(RT_DEBUG_TRACE, ("<=== rt2860_suspend()\n"));
321 + return retval;
322 +}
323 +
324 +static int rt2860_resume(
325 + struct pci_dev *pci_dev)
326 +{
327 + struct net_device *net_dev = pci_get_drvdata(pci_dev);
328 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)NULL;
329 + INT32 retval;
330 +
331 +
332 + // set the power state of a PCI device
333 + // PCI has 4 power states, DO (normal) ~ D3(less power)
334 + // in include/linux/pci.h, you can find that
335 + // #define PCI_D0 ((pci_power_t __force) 0)
336 + // #define PCI_D1 ((pci_power_t __force) 1)
337 + // #define PCI_D2 ((pci_power_t __force) 2)
338 + // #define PCI_D3hot ((pci_power_t __force) 3)
339 + // #define PCI_D3cold ((pci_power_t __force) 4)
340 + // #define PCI_UNKNOWN ((pci_power_t __force) 5)
341 + // #define PCI_POWER_ERROR ((pci_power_t __force) -1)
342 + retval = pci_set_power_state(pci_dev, PCI_D0);
343 +
344 + // restore the saved state of a PCI device
345 + pci_restore_state(pci_dev);
346 +
347 + // initialize device before it's used by a driver
348 + if (pci_enable_device(pci_dev))
349 + {
350 + printk("pci enable fail!\n");
351 + return 0;
352 + }
353 +
354 + DBGPRINT(RT_DEBUG_TRACE, ("===> rt2860_resume()\n"));
355 +
356 + if (net_dev == NULL)
357 + {
358 + DBGPRINT(RT_DEBUG_ERROR, ("net_dev == NULL!\n"));
359 + }
360 + else
361 + pAd = (PRTMP_ADAPTER)net_dev->priv;
362 +
363 + if (pAd != NULL)
364 + {
365 + /* we can not use IFF_UP because ra0 down but ra1 up */
366 + /* and 1 suspend/resume function for 1 module, not for each interface */
367 + /* so Linux will call suspend/resume function once */
368 + if (VIRTUAL_IF_NUM(pAd) > 0)
369 + {
370 + // mark device as attached from system and restart if needed
371 + netif_device_attach(net_dev);
372 +
373 + if (rt28xx_open((PNET_DEV)net_dev) != 0)
374 + {
375 + // open fail
376 + DBGPRINT(RT_DEBUG_TRACE, ("<=== rt2860_resume()\n"));
377 + return 0;
378 + }
379 +
380 + // increase MODULE use count
381 + RT_MOD_INC_USE_COUNT();
382 +
383 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS);
384 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
385 +
386 + netif_start_queue(net_dev);
387 + netif_carrier_on(net_dev);
388 + netif_wake_queue(net_dev);
389 + }
390 + }
391 +
392 + DBGPRINT(RT_DEBUG_TRACE, ("<=== rt2860_resume()\n"));
393 + return 0;
394 +}
395 +#endif // CONFIG_PM //
396 +#endif
397 +
398 +
399 +static INT __init rt2860_init_module(VOID)
400 +{
401 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
402 + return pci_register_driver(&rt2860_driver);
403 +#else
404 + return pci_module_init(&rt2860_driver);
405 +#endif
406 +}
407 +
408 +
409 +//
410 +// Driver module unload function
411 +//
412 +static VOID __exit rt2860_cleanup_module(VOID)
413 +{
414 + pci_unregister_driver(&rt2860_driver);
415 +}
416 +
417 +module_init(rt2860_init_module);
418 +module_exit(rt2860_cleanup_module);
419 +
420 +
421 +static INT __devinit rt2860_init_one (
422 + IN struct pci_dev *pci_dev,
423 + IN const struct pci_device_id *ent)
424 +{
425 + INT rc;
426 +
427 + DBGPRINT(RT_DEBUG_TRACE, ("===> rt2860_init_one\n"));
428 +
429 + // wake up and enable device
430 + if (pci_enable_device (pci_dev))
431 + {
432 + rc = -EIO;
433 + }
434 + else
435 + {
436 + rc = rt2860_probe(pci_dev, ent);
437 + }
438 +
439 + DBGPRINT(RT_DEBUG_TRACE, ("<=== rt2860_init_one\n"));
440 + return rc;
441 +}
442 +
443 +
444 +static VOID __devexit rt2860_remove_one(
445 + IN struct pci_dev *pci_dev)
446 +{
447 + struct net_device *net_dev = pci_get_drvdata(pci_dev);
448 + RTMP_ADAPTER *pAd = net_dev->priv;
449 +
450 + DBGPRINT(RT_DEBUG_TRACE, ("===> rt2860_remove_one\n"));
451 +
452 + if (pAd != NULL)
453 + {
454 +#ifdef MULTIPLE_CARD_SUPPORT
455 + if ((pAd->MC_RowID >= 0) && (pAd->MC_RowID <= MAX_NUM_OF_MULTIPLE_CARD))
456 + MC_CardUsed[pAd->MC_RowID] = 0; // not clear MAC address
457 +#endif // MULTIPLE_CARD_SUPPORT //
458 +
459 +
460 +
461 +
462 + // Unregister network device
463 + unregister_netdev(net_dev);
464 +
465 + // Unmap CSR base address
466 + iounmap((char *)(net_dev->base_addr));
467 +
468 + RTMPFreeAdapter(pAd);
469 +
470 + // release memory region
471 + release_mem_region(pci_resource_start(pci_dev, 0), pci_resource_len(pci_dev, 0));
472 + }
473 + else
474 + {
475 + // Unregister network device
476 + unregister_netdev(net_dev);
477 +
478 + // Unmap CSR base address
479 + iounmap((char *)(net_dev->base_addr));
480 +
481 + // release memory region
482 + release_mem_region(pci_resource_start(pci_dev, 0), pci_resource_len(pci_dev, 0));
483 + }
484 +
485 + // Free pre-allocated net_device memory
486 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
487 + free_netdev(net_dev);
488 +#else
489 + kfree(net_dev);
490 +#endif
491 +}
492 +
493 +//
494 +// PCI device probe & initialization function
495 +//
496 +static INT __devinit rt2860_probe(
497 + IN struct pci_dev *pci_dev,
498 + IN const struct pci_device_id *ent)
499 +{
500 + PRTMP_ADAPTER pAd;
501 + INT rv = 0;
502 +
503 + rv = (INT)rt28xx_probe((void *)pci_dev, (void *)ent, 0, &pAd);
504 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE);
505 + return rv;
506 +}
507 +
508 +
509 +void init_thread_task(IN PRTMP_ADAPTER pAd)
510 +{
511 + POS_COOKIE pObj;
512 +
513 + pObj = (POS_COOKIE) pAd->OS_Cookie;
514 +
515 + tasklet_init(&pObj->rx_done_task, rx_done_tasklet, (unsigned long)pAd);
516 + tasklet_init(&pObj->mgmt_dma_done_task, mgmt_dma_done_tasklet, (unsigned long)pAd);
517 + tasklet_init(&pObj->ac0_dma_done_task, ac0_dma_done_tasklet, (unsigned long)pAd);
518 + tasklet_init(&pObj->ac1_dma_done_task, ac1_dma_done_tasklet, (unsigned long)pAd);
519 + tasklet_init(&pObj->ac2_dma_done_task, ac2_dma_done_tasklet, (unsigned long)pAd);
520 + tasklet_init(&pObj->ac3_dma_done_task, ac3_dma_done_tasklet, (unsigned long)pAd);
521 + tasklet_init(&pObj->hcca_dma_done_task, hcca_dma_done_tasklet, (unsigned long)pAd);
522 + tasklet_init(&pObj->tbtt_task, tbtt_tasklet, (unsigned long)pAd);
523 + tasklet_init(&pObj->fifo_statistic_full_task, fifo_statistic_full_tasklet, (unsigned long)pAd);
524 +}
525 +
526 +void kill_thread_task(IN PRTMP_ADAPTER pAd)
527 +{
528 + POS_COOKIE pObj;
529 +
530 + pObj = (POS_COOKIE) pAd->OS_Cookie;
531 +
532 + tasklet_kill(&pObj->rx_done_task);
533 + tasklet_kill(&pObj->mgmt_dma_done_task);
534 + tasklet_kill(&pObj->ac0_dma_done_task);
535 + tasklet_kill(&pObj->ac1_dma_done_task);
536 + tasklet_kill(&pObj->ac2_dma_done_task);
537 + tasklet_kill(&pObj->ac3_dma_done_task);
538 + tasklet_kill(&pObj->hcca_dma_done_task);
539 + tasklet_kill(&pObj->tbtt_task);
540 + tasklet_kill(&pObj->fifo_statistic_full_task);
541 +}
542 +
543 +
544 +static void rt2860_int_enable(PRTMP_ADAPTER pAd, unsigned int mode)
545 +{
546 + u32 regValue;
547 +
548 + pAd->int_disable_mask &= ~(mode);
549 + regValue = pAd->int_enable_reg & ~(pAd->int_disable_mask);
550 + RTMP_IO_WRITE32(pAd, INT_MASK_CSR, regValue); // 1:enable
551 +
552 + if (regValue != 0)
553 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE);
554 +}
555 +
556 +
557 +static void rt2860_int_disable(PRTMP_ADAPTER pAd, unsigned int mode)
558 +{
559 + u32 regValue;
560 +
561 + pAd->int_disable_mask |= mode;
562 + regValue = pAd->int_enable_reg & ~(pAd->int_disable_mask);
563 + RTMP_IO_WRITE32(pAd, INT_MASK_CSR, regValue); // 0: disable
564 +
565 + if (regValue == 0)
566 + {
567 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE);
568 + }
569 +}
570 +
571 +static void mgmt_dma_done_tasklet(unsigned long data)
572 +{
573 + unsigned long flags;
574 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
575 + INT_SOURCE_CSR_STRUC IntSource;
576 + POS_COOKIE pObj;
577 +
578 + // Do nothing if the driver is starting halt state.
579 + // This might happen when timer already been fired before cancel timer with mlmehalt
580 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
581 + return;
582 +
583 + pObj = (POS_COOKIE) pAd->OS_Cookie;
584 +
585 + IntSource.word = 0;
586 + IntSource.field.MgmtDmaDone = 1;
587 + pAd->int_pending &= ~INT_MGMT_DLY;
588 +
589 + RTMPHandleMgmtRingDmaDoneInterrupt(pAd);
590 +
591 + // if you use RTMP_SEM_LOCK, sometimes kernel will hang up, no any
592 + // bug report output
593 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
594 + /*
595 + * double check to avoid lose of interrupts
596 + */
597 + if (pAd->int_pending & INT_MGMT_DLY)
598 + {
599 + tasklet_hi_schedule(&pObj->mgmt_dma_done_task);
600 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
601 + return;
602 + }
603 +
604 + /* enable TxDataInt again */
605 + rt2860_int_enable(pAd, INT_MGMT_DLY);
606 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
607 +}
608 +
609 +static void rx_done_tasklet(unsigned long data)
610 +{
611 + unsigned long flags;
612 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
613 + BOOLEAN bReschedule = 0;
614 + POS_COOKIE pObj;
615 +
616 + // Do nothing if the driver is starting halt state.
617 + // This might happen when timer already been fired before cancel timer with mlmehalt
618 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
619 + return;
620 +
621 + pObj = (POS_COOKIE) pAd->OS_Cookie;
622 +
623 + pAd->int_pending &= ~(INT_RX);
624 +#ifdef CONFIG_STA_SUPPORT
625 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
626 + bReschedule = STARxDoneInterruptHandle(pAd, 0);
627 +#endif // CONFIG_STA_SUPPORT //
628 +
629 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
630 + /*
631 + * double check to avoid rotting packet
632 + */
633 + if (pAd->int_pending & INT_RX || bReschedule)
634 + {
635 + tasklet_hi_schedule(&pObj->rx_done_task);
636 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
637 + return;
638 + }
639 +
640 + /* enable RxINT again */
641 + rt2860_int_enable(pAd, INT_RX);
642 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
643 +
644 +}
645 +
646 +void fifo_statistic_full_tasklet(unsigned long data)
647 +{
648 + unsigned long flags;
649 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
650 + POS_COOKIE pObj;
651 +
652 + // Do nothing if the driver is starting halt state.
653 + // This might happen when timer already been fired before cancel timer with mlmehalt
654 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
655 + return;
656 +
657 + pObj = (POS_COOKIE) pAd->OS_Cookie;
658 +
659 + pAd->int_pending &= ~(FifoStaFullInt);
660 + NICUpdateFifoStaCounters(pAd);
661 +
662 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
663 + /*
664 + * double check to avoid rotting packet
665 + */
666 + if (pAd->int_pending & FifoStaFullInt)
667 + {
668 + tasklet_hi_schedule(&pObj->fifo_statistic_full_task);
669 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
670 + return;
671 + }
672 +
673 + /* enable RxINT again */
674 +
675 + rt2860_int_enable(pAd, FifoStaFullInt);
676 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
677 +
678 +}
679 +
680 +static void hcca_dma_done_tasklet(unsigned long data)
681 +{
682 + unsigned long flags;
683 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
684 + INT_SOURCE_CSR_STRUC IntSource;
685 + POS_COOKIE pObj;
686 +
687 + // Do nothing if the driver is starting halt state.
688 + // This might happen when timer already been fired before cancel timer with mlmehalt
689 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
690 + return;
691 +
692 + pObj = (POS_COOKIE) pAd->OS_Cookie;
693 +
694 +
695 + IntSource.word = 0;
696 + IntSource.field.HccaDmaDone = 1;
697 + pAd->int_pending &= ~INT_HCCA_DLY;
698 +
699 + RTMPHandleTxRingDmaDoneInterrupt(pAd, IntSource);
700 +
701 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
702 + /*
703 + * double check to avoid lose of interrupts
704 + */
705 + if (pAd->int_pending & INT_HCCA_DLY)
706 + {
707 + tasklet_hi_schedule(&pObj->hcca_dma_done_task);
708 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
709 + return;
710 + }
711 +
712 + /* enable TxDataInt again */
713 + rt2860_int_enable(pAd, INT_HCCA_DLY);
714 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
715 +}
716 +
717 +static void ac3_dma_done_tasklet(unsigned long data)
718 +{
719 + unsigned long flags;
720 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
721 + INT_SOURCE_CSR_STRUC IntSource;
722 + POS_COOKIE pObj;
723 + BOOLEAN bReschedule = 0;
724 +
725 + // Do nothing if the driver is starting halt state.
726 + // This might happen when timer already been fired before cancel timer with mlmehalt
727 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
728 + return;
729 +
730 + pObj = (POS_COOKIE) pAd->OS_Cookie;
731 +
732 + IntSource.word = 0;
733 + IntSource.field.Ac3DmaDone = 1;
734 + pAd->int_pending &= ~INT_AC3_DLY;
735 +
736 + bReschedule = RTMPHandleTxRingDmaDoneInterrupt(pAd, IntSource);
737 +
738 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
739 + /*
740 + * double check to avoid lose of interrupts
741 + */
742 + if ((pAd->int_pending & INT_AC3_DLY) || bReschedule)
743 + {
744 + tasklet_hi_schedule(&pObj->ac3_dma_done_task);
745 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
746 + return;
747 + }
748 +
749 + /* enable TxDataInt again */
750 + rt2860_int_enable(pAd, INT_AC3_DLY);
751 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
752 +}
753 +
754 +static void ac2_dma_done_tasklet(unsigned long data)
755 +{
756 + unsigned long flags;
757 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
758 + INT_SOURCE_CSR_STRUC IntSource;
759 + POS_COOKIE pObj;
760 + BOOLEAN bReschedule = 0;
761 +
762 + // Do nothing if the driver is starting halt state.
763 + // This might happen when timer already been fired before cancel timer with mlmehalt
764 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
765 + return;
766 +
767 + pObj = (POS_COOKIE) pAd->OS_Cookie;
768 +
769 + IntSource.word = 0;
770 + IntSource.field.Ac2DmaDone = 1;
771 + pAd->int_pending &= ~INT_AC2_DLY;
772 +
773 + bReschedule = RTMPHandleTxRingDmaDoneInterrupt(pAd, IntSource);
774 +
775 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
776 +
777 + /*
778 + * double check to avoid lose of interrupts
779 + */
780 + if ((pAd->int_pending & INT_AC2_DLY) || bReschedule)
781 + {
782 + tasklet_hi_schedule(&pObj->ac2_dma_done_task);
783 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
784 + return;
785 + }
786 +
787 + /* enable TxDataInt again */
788 + rt2860_int_enable(pAd, INT_AC2_DLY);
789 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
790 +}
791 +
792 +static void ac1_dma_done_tasklet(unsigned long data)
793 +{
794 + unsigned long flags;
795 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
796 + INT_SOURCE_CSR_STRUC IntSource;
797 + POS_COOKIE pObj;
798 + BOOLEAN bReschedule = 0;
799 +
800 + // Do nothing if the driver is starting halt state.
801 + // This might happen when timer already been fired before cancel timer with mlmehalt
802 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
803 + return;
804 +
805 + pObj = (POS_COOKIE) pAd->OS_Cookie;
806 +
807 + IntSource.word = 0;
808 + IntSource.field.Ac1DmaDone = 1;
809 + pAd->int_pending &= ~INT_AC1_DLY;
810 +
811 + bReschedule = RTMPHandleTxRingDmaDoneInterrupt(pAd, IntSource);
812 +
813 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
814 + /*
815 + * double check to avoid lose of interrupts
816 + */
817 + if ((pAd->int_pending & INT_AC1_DLY) || bReschedule)
818 + {
819 + tasklet_hi_schedule(&pObj->ac1_dma_done_task);
820 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
821 + return;
822 + }
823 +
824 + /* enable TxDataInt again */
825 + rt2860_int_enable(pAd, INT_AC1_DLY);
826 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
827 +}
828 +
829 +static void ac0_dma_done_tasklet(unsigned long data)
830 +{
831 + unsigned long flags;
832 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) data;
833 + INT_SOURCE_CSR_STRUC IntSource;
834 + POS_COOKIE pObj;
835 + BOOLEAN bReschedule = 0;
836 +
837 + // Do nothing if the driver is starting halt state.
838 + // This might happen when timer already been fired before cancel timer with mlmehalt
839 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
840 + return;
841 +
842 + pObj = (POS_COOKIE) pAd->OS_Cookie;
843 +
844 + IntSource.word = 0;
845 + IntSource.field.Ac0DmaDone = 1;
846 + pAd->int_pending &= ~INT_AC0_DLY;
847 +
848 + bReschedule = RTMPHandleTxRingDmaDoneInterrupt(pAd, IntSource);
849 +
850 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
851 + /*
852 + * double check to avoid lose of interrupts
853 + */
854 + if ((pAd->int_pending & INT_AC0_DLY) || bReschedule)
855 + {
856 + tasklet_hi_schedule(&pObj->ac0_dma_done_task);
857 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
858 + return;
859 + }
860 +
861 + /* enable TxDataInt again */
862 + rt2860_int_enable(pAd, INT_AC0_DLY);
863 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
864 +}
865 +
866 +
867 +int print_int_count;
868 +
869 +IRQ_HANDLE_TYPE
870 +#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,19))
871 +rt2860_interrupt(int irq, void *dev_instance)
872 +#else
873 +rt2860_interrupt(int irq, void *dev_instance, struct pt_regs *regs)
874 +#endif
875 +{
876 + struct net_device *net_dev = (struct net_device *) dev_instance;
877 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) net_dev->priv;
878 + INT_SOURCE_CSR_STRUC IntSource;
879 + POS_COOKIE pObj;
880 +
881 + pObj = (POS_COOKIE) pAd->OS_Cookie;
882 +
883 +
884 + /* Note 03312008: we can not return here before
885 + RTMP_IO_READ32(pAd, INT_SOURCE_CSR, &IntSource.word);
886 + RTMP_IO_WRITE32(pAd, INT_SOURCE_CSR, IntSource.word);
887 + Or kernel will panic after ifconfig ra0 down sometimes */
888 +
889 +
890 + //
891 + // Inital the Interrupt source.
892 + //
893 + IntSource.word = 0x00000000L;
894 +// McuIntSource.word = 0x00000000L;
895 +
896 + //
897 + // Get the interrupt sources & saved to local variable
898 + //
899 + //RTMP_IO_READ32(pAd, where, &McuIntSource.word);
900 + //RTMP_IO_WRITE32(pAd, , McuIntSource.word);
901 +
902 + //
903 + // Flag fOP_STATUS_DOZE On, means ASIC put to sleep, elase means ASICK WakeUp
904 + // And at the same time, clock maybe turned off that say there is no DMA service.
905 + // when ASIC get to sleep.
906 + // To prevent system hang on power saving.
907 + // We need to check it before handle the INT_SOURCE_CSR, ASIC must be wake up.
908 + //
909 + // RT2661 => when ASIC is sleeping, MAC register cannot be read and written.
910 + // RT2860 => when ASIC is sleeping, MAC register can be read and written.
911 +
912 + {
913 + RTMP_IO_READ32(pAd, INT_SOURCE_CSR, &IntSource.word);
914 + RTMP_IO_WRITE32(pAd, INT_SOURCE_CSR, IntSource.word); // write 1 to clear
915 + }
916 +
917 + // Do nothing if Reset in progress
918 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||
919 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS))
920 + {
921 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
922 + return IRQ_HANDLED;
923 +#else
924 + return;
925 +#endif
926 + }
927 +
928 + //
929 + // Handle interrupt, walk through all bits
930 + // Should start from highest priority interrupt
931 + // The priority can be adjust by altering processing if statement
932 + //
933 +
934 + pAd->bPCIclkOff = FALSE;
935 +
936 + // If required spinlock, each interrupt service routine has to acquire
937 + // and release itself.
938 + //
939 +
940 + // Do nothing if NIC doesn't exist
941 + if (IntSource.word == 0xffffffff)
942 + {
943 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST | fRTMP_ADAPTER_HALT_IN_PROGRESS);
944 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
945 + return IRQ_HANDLED;
946 +#else
947 + return;
948 +#endif
949 + }
950 +
951 + if (IntSource.word & TxCoherent)
952 + {
953 + DBGPRINT(RT_DEBUG_ERROR, (">>>TxCoherent<<<\n"));
954 + RTMPHandleRxCoherentInterrupt(pAd);
955 + }
956 +
957 + if (IntSource.word & RxCoherent)
958 + {
959 + DBGPRINT(RT_DEBUG_ERROR, (">>>RxCoherent<<<\n"));
960 + RTMPHandleRxCoherentInterrupt(pAd);
961 + }
962 +
963 + if (IntSource.word & FifoStaFullInt)
964 + {
965 +#if 1
966 + if ((pAd->int_disable_mask & FifoStaFullInt) == 0)
967 + {
968 + /* mask FifoStaFullInt */
969 + rt2860_int_disable(pAd, FifoStaFullInt);
970 + tasklet_hi_schedule(&pObj->fifo_statistic_full_task);
971 + }
972 + pAd->int_pending |= FifoStaFullInt;
973 +#else
974 + NICUpdateFifoStaCounters(pAd);
975 +#endif
976 + }
977 +
978 + if (IntSource.word & INT_MGMT_DLY)
979 + {
980 + if ((pAd->int_disable_mask & INT_MGMT_DLY) ==0 )
981 + {
982 + rt2860_int_disable(pAd, INT_MGMT_DLY);
983 + tasklet_hi_schedule(&pObj->mgmt_dma_done_task);
984 + }
985 + pAd->int_pending |= INT_MGMT_DLY ;
986 + }
987 +
988 + if (IntSource.word & INT_RX)
989 + {
990 + if ((pAd->int_disable_mask & INT_RX) == 0)
991 + {
992 + /* mask RxINT */
993 + rt2860_int_disable(pAd, INT_RX);
994 + tasklet_hi_schedule(&pObj->rx_done_task);
995 + }
996 + pAd->int_pending |= INT_RX;
997 + }
998 +
999 + if (IntSource.word & INT_HCCA_DLY)
1000 + {
1001 +
1002 + if ((pAd->int_disable_mask & INT_HCCA_DLY) == 0)
1003 + {
1004 + /* mask TxDataInt */
1005 + rt2860_int_disable(pAd, INT_HCCA_DLY);
1006 + tasklet_hi_schedule(&pObj->hcca_dma_done_task);
1007 + }
1008 + pAd->int_pending |= INT_HCCA_DLY;
1009 + }
1010 +
1011 + if (IntSource.word & INT_AC3_DLY)
1012 + {
1013 +
1014 + if ((pAd->int_disable_mask & INT_AC3_DLY) == 0)
1015 + {
1016 + /* mask TxDataInt */
1017 + rt2860_int_disable(pAd, INT_AC3_DLY);
1018 + tasklet_hi_schedule(&pObj->ac3_dma_done_task);
1019 + }
1020 + pAd->int_pending |= INT_AC3_DLY;
1021 + }
1022 +
1023 + if (IntSource.word & INT_AC2_DLY)
1024 + {
1025 +
1026 + if ((pAd->int_disable_mask & INT_AC2_DLY) == 0)
1027 + {
1028 + /* mask TxDataInt */
1029 + rt2860_int_disable(pAd, INT_AC2_DLY);
1030 + tasklet_hi_schedule(&pObj->ac2_dma_done_task);
1031 + }
1032 + pAd->int_pending |= INT_AC2_DLY;
1033 + }
1034 +
1035 + if (IntSource.word & INT_AC1_DLY)
1036 + {
1037 +
1038 + pAd->int_pending |= INT_AC1_DLY;
1039 +
1040 + if ((pAd->int_disable_mask & INT_AC1_DLY) == 0)
1041 + {
1042 + /* mask TxDataInt */
1043 + rt2860_int_disable(pAd, INT_AC1_DLY);
1044 + tasklet_hi_schedule(&pObj->ac1_dma_done_task);
1045 + }
1046 +
1047 + }
1048 +
1049 + if (IntSource.word & INT_AC0_DLY)
1050 + {
1051 + pAd->int_pending |= INT_AC0_DLY;
1052 +
1053 + if ((pAd->int_disable_mask & INT_AC0_DLY) == 0)
1054 + {
1055 + /* mask TxDataInt */
1056 + rt2860_int_disable(pAd, INT_AC0_DLY);
1057 + tasklet_hi_schedule(&pObj->ac0_dma_done_task);
1058 + }
1059 +
1060 + }
1061 +
1062 + if (IntSource.word & PreTBTTInt)
1063 + {
1064 + RTMPHandlePreTBTTInterrupt(pAd);
1065 + }
1066 +
1067 + if (IntSource.word & TBTTInt)
1068 + {
1069 + RTMPHandleTBTTInterrupt(pAd);
1070 + }
1071 +
1072 +
1073 +
1074 +#ifdef CONFIG_STA_SUPPORT
1075 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
1076 + {
1077 + if (IntSource.word & AutoWakeupInt)
1078 + RTMPHandleTwakeupInterrupt(pAd);
1079 + }
1080 +#endif // CONFIG_STA_SUPPORT //
1081 +
1082 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
1083 + return IRQ_HANDLED;
1084 +#endif
1085 +
1086 +}
1087 +
1088 +/*
1089 +========================================================================
1090 +Routine Description:
1091 + Check the chipset vendor/product ID.
1092 +
1093 +Arguments:
1094 + _dev_p Point to the PCI or USB device
1095 +
1096 +Return Value:
1097 + TRUE Check ok
1098 + FALSE Check fail
1099 +
1100 +Note:
1101 +========================================================================
1102 +*/
1103 +BOOLEAN RT28XXChipsetCheck(
1104 + IN void *_dev_p)
1105 +{
1106 + /* always TRUE */
1107 + return TRUE;
1108 +}
1109 +
1110 +
1111 +/*
1112 +========================================================================
1113 +Routine Description:
1114 + Init net device structure.
1115 +
1116 +Arguments:
1117 + _dev_p Point to the PCI or USB device
1118 + *net_dev Point to the net device
1119 + *pAd the raxx interface data pointer
1120 +
1121 +Return Value:
1122 + TRUE Init ok
1123 + FALSE Init fail
1124 +
1125 +Note:
1126 +========================================================================
1127 +*/
1128 +BOOLEAN RT28XXNetDevInit(
1129 + IN void *_dev_p,
1130 + IN struct net_device *net_dev,
1131 + IN RTMP_ADAPTER *pAd)
1132 +{
1133 + struct pci_dev *pci_dev = (struct pci_dev *)_dev_p;
1134 + CHAR *print_name;
1135 + ULONG csr_addr;
1136 +
1137 +
1138 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
1139 + print_name = pci_dev ? pci_name(pci_dev) : "rt2860";
1140 +#else
1141 + print_name = pci_dev ? pci_dev->slot_name : "rt2860";
1142 +#endif // LINUX_VERSION_CODE //
1143 +
1144 + net_dev->base_addr = 0;
1145 + net_dev->irq = 0;
1146 +
1147 + if (pci_request_regions(pci_dev, print_name))
1148 + goto err_out_free_netdev;
1149 +
1150 + // interrupt IRQ number
1151 + net_dev->irq = pci_dev->irq;
1152 +
1153 + // map physical address to virtual address for accessing register
1154 + csr_addr = (unsigned long) ioremap(pci_resource_start(pci_dev, 0),
1155 + pci_resource_len(pci_dev, 0));
1156 +
1157 + if (!csr_addr)
1158 + {
1159 + DBGPRINT(RT_DEBUG_ERROR,
1160 + ("ioremap failed for device %s, region 0x%lX @ 0x%lX\n",
1161 + print_name, (ULONG)pci_resource_len(pci_dev, 0),
1162 + (ULONG)pci_resource_start(pci_dev, 0)));
1163 + goto err_out_free_res;
1164 + }
1165 +
1166 + // Save CSR virtual address and irq to device structure
1167 + net_dev->base_addr = csr_addr;
1168 + pAd->CSRBaseAddress = (PUCHAR)net_dev->base_addr;
1169 +
1170 + // Set DMA master
1171 + pci_set_master(pci_dev);
1172 +
1173 + net_dev->priv_flags = INT_MAIN;
1174 +
1175 + DBGPRINT(RT_DEBUG_TRACE, ("%s: at 0x%lx, VA 0x%lx, IRQ %d. \n",
1176 + net_dev->name, (ULONG)pci_resource_start(pci_dev, 0),
1177 + (ULONG)csr_addr, pci_dev->irq));
1178 + return TRUE;
1179 +
1180 +
1181 + /* --------------------------- ERROR HANDLE --------------------------- */
1182 +err_out_free_res:
1183 + pci_release_regions(pci_dev);
1184 +err_out_free_netdev:
1185 + /* free netdev in caller, not here */
1186 + return FALSE;
1187 +}
1188 +
1189 +
1190 +/*
1191 +========================================================================
1192 +Routine Description:
1193 + Init net device structure.
1194 +
1195 +Arguments:
1196 + _dev_p Point to the PCI or USB device
1197 + *pAd the raxx interface data pointer
1198 +
1199 +Return Value:
1200 + TRUE Config ok
1201 + FALSE Config fail
1202 +
1203 +Note:
1204 +========================================================================
1205 +*/
1206 +BOOLEAN RT28XXProbePostConfig(
1207 + IN void *_dev_p,
1208 + IN RTMP_ADAPTER *pAd,
1209 + IN INT32 argc)
1210 +{
1211 + /* no use */
1212 + return TRUE;
1213 +}
1214 +
1215 +
1216 +/*
1217 +========================================================================
1218 +Routine Description:
1219 + Disable DMA.
1220 +
1221 +Arguments:
1222 + *pAd the raxx interface data pointer
1223 +
1224 +Return Value:
1225 + None
1226 +
1227 +Note:
1228 +========================================================================
1229 +*/
1230 +VOID RT28XXDMADisable(
1231 + IN RTMP_ADAPTER *pAd)
1232 +{
1233 + WPDMA_GLO_CFG_STRUC GloCfg;
1234 +
1235 +
1236 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word);
1237 + GloCfg.word &= 0xff0;
1238 + GloCfg.field.EnTXWriteBackDDONE =1;
1239 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word);
1240 +}
1241 +
1242 +
1243 +/*
1244 +========================================================================
1245 +Routine Description:
1246 + Enable DMA.
1247 +
1248 +Arguments:
1249 + *pAd the raxx interface data pointer
1250 +
1251 +Return Value:
1252 + None
1253 +
1254 +Note:
1255 +========================================================================
1256 +*/
1257 +VOID RT28XXDMAEnable(
1258 + IN RTMP_ADAPTER *pAd)
1259 +{
1260 + WPDMA_GLO_CFG_STRUC GloCfg;
1261 + int i = 0;
1262 +
1263 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x4);
1264 + do
1265 + {
1266 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word);
1267 + if ((GloCfg.field.TxDMABusy == 0) && (GloCfg.field.RxDMABusy == 0))
1268 + break;
1269 +
1270 + DBGPRINT(RT_DEBUG_TRACE, ("==> DMABusy\n"));
1271 + RTMPusecDelay(1000);
1272 + i++;
1273 + }while ( i <200);
1274 +
1275 + RTMPusecDelay(50);
1276 +
1277 + GloCfg.field.EnTXWriteBackDDONE = 1;
1278 + GloCfg.field.WPDMABurstSIZE = 2;
1279 + GloCfg.field.EnableRxDMA = 1;
1280 + GloCfg.field.EnableTxDMA = 1;
1281 +
1282 + DBGPRINT(RT_DEBUG_TRACE, ("<== WRITE DMA offset 0x208 = 0x%x\n", GloCfg.word));
1283 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word);
1284 +
1285 +}
1286 +
1287 +/*
1288 +========================================================================
1289 +Routine Description:
1290 + Write Beacon buffer to Asic.
1291 +
1292 +Arguments:
1293 + *pAd the raxx interface data pointer
1294 +
1295 +Return Value:
1296 + None
1297 +
1298 +Note:
1299 +========================================================================
1300 +*/
1301 +VOID RT28xx_UpdateBeaconToAsic(
1302 + IN RTMP_ADAPTER *pAd,
1303 + IN INT apidx,
1304 + IN ULONG FrameLen,
1305 + IN ULONG UpdatePos)
1306 +{
1307 + ULONG CapInfoPos = 0;
1308 + UCHAR *ptr, *ptr_update, *ptr_capinfo;
1309 + UINT i;
1310 + BOOLEAN bBcnReq = FALSE;
1311 + UCHAR bcn_idx = 0;
1312 +
1313 + {
1314 + DBGPRINT(RT_DEBUG_ERROR, ("%s() : No valid Interface be found.\n", __FUNCTION__));
1315 + return;
1316 + }
1317 +
1318 + if (bBcnReq == FALSE)
1319 + {
1320 + /* when the ra interface is down, do not send its beacon frame */
1321 + /* clear all zero */
1322 + for(i=0; i<TXWI_SIZE; i+=4)
1323 + RTMP_IO_WRITE32(pAd, pAd->BeaconOffset[bcn_idx] + i, 0x00);
1324 + }
1325 + else
1326 + {
1327 + ptr = (PUCHAR)&pAd->BeaconTxWI;
1328 +#ifdef RT_BIG_ENDIAN
1329 + RTMPWIEndianChange(ptr, TYPE_TXWI);
1330 +#endif
1331 + for (i=0; i<TXWI_SIZE; i+=4) // 16-byte TXWI field
1332 + {
1333 + UINT32 longptr = *ptr + (*(ptr+1)<<8) + (*(ptr+2)<<16) + (*(ptr+3)<<24);
1334 + RTMP_IO_WRITE32(pAd, pAd->BeaconOffset[bcn_idx] + i, longptr);
1335 + ptr += 4;
1336 + }
1337 +
1338 + // Update CapabilityInfo in Beacon
1339 + for (i = CapInfoPos; i < (CapInfoPos+2); i++)
1340 + {
1341 + RTMP_IO_WRITE8(pAd, pAd->BeaconOffset[bcn_idx] + TXWI_SIZE + i, *ptr_capinfo);
1342 + ptr_capinfo ++;
1343 + }
1344 +
1345 + if (FrameLen > UpdatePos)
1346 + {
1347 + for (i= UpdatePos; i< (FrameLen); i++)
1348 + {
1349 + RTMP_IO_WRITE8(pAd, pAd->BeaconOffset[bcn_idx] + TXWI_SIZE + i, *ptr_update);
1350 + ptr_update ++;
1351 + }
1352 + }
1353 +
1354 + }
1355 +
1356 +}
1357 +
1358 +#ifdef CONFIG_STA_SUPPORT
1359 +VOID RTMPInitPCIeLinkCtrlValue(
1360 + IN PRTMP_ADAPTER pAd)
1361 +{
1362 +}
1363 +
1364 +VOID RTMPFindHostPCIDev(
1365 + IN PRTMP_ADAPTER pAd)
1366 +{
1367 +}
1368 +
1369 +/*
1370 + ========================================================================
1371 +
1372 + Routine Description:
1373 +
1374 + Arguments:
1375 + Level = RESTORE_HALT : Restore PCI host and Ralink PCIe Link Control field to its default value.
1376 + Level = Other Value : Restore from dot11 power save or radio off status. And force PCI host Link Control fields to 0x1
1377 +
1378 + ========================================================================
1379 +*/
1380 +VOID RTMPPCIeLinkCtrlValueRestore(
1381 + IN PRTMP_ADAPTER pAd,
1382 + IN UCHAR Level)
1383 +{
1384 +}
1385 +
1386 +/*
1387 + ========================================================================
1388 +
1389 + Routine Description:
1390 +
1391 + Arguments:
1392 + Max : limit Host PCI and Ralink PCIe device's LINK CONTROL field's value.
1393 + Because now frequently set our device to mode 1 or mode 3 will cause problem.
1394 +
1395 + ========================================================================
1396 +*/
1397 +VOID RTMPPCIeLinkCtrlSetting(
1398 + IN PRTMP_ADAPTER pAd,
1399 + IN USHORT Max)
1400 +{
1401 +}
1402 +#endif // CONFIG_STA_SUPPORT //
1403 +
1404 +VOID rt2860_stop(struct net_device *net_dev)
1405 +{
1406 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)NULL;
1407 + if (net_dev == NULL)
1408 + {
1409 + DBGPRINT(RT_DEBUG_ERROR, ("net_dev == NULL!\n"));
1410 + }
1411 + else
1412 + pAd = (PRTMP_ADAPTER)net_dev->priv;
1413 +
1414 + if (pAd != NULL)
1415 + {
1416 + // stop interface
1417 + netif_carrier_off(net_dev);
1418 + netif_stop_queue(net_dev);
1419 +
1420 + // mark device as removed from system and therefore no longer available
1421 + netif_device_detach(net_dev);
1422 +
1423 + // mark halt flag
1424 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS);
1425 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
1426 +
1427 + // take down the device
1428 + rt28xx_close((PNET_DEV)net_dev);
1429 + RT_MOD_DEC_USE_COUNT();
1430 + }
1431 + return;
1432 +}
1433 +
1434 +/*
1435 + * invaild or writeback cache
1436 + * and convert virtual address to physical address
1437 + */
1438 +dma_addr_t linux_pci_map_single(void *handle, void *ptr, size_t size, int sd_idx, int direction)
1439 +{
1440 + PRTMP_ADAPTER pAd;
1441 + POS_COOKIE pObj;
1442 +
1443 + /*
1444 + ------ Porting Information ------
1445 + > For Tx Alloc:
1446 + mgmt packets => sd_idx = 0
1447 + SwIdx: pAd->MgmtRing.TxCpuIdx
1448 + pTxD : pAd->MgmtRing.Cell[SwIdx].AllocVa;
1449 +
1450 + data packets => sd_idx = 1
1451 + TxIdx : pAd->TxRing[pTxBlk->QueIdx].TxCpuIdx
1452 + QueIdx: pTxBlk->QueIdx
1453 + pTxD : pAd->TxRing[pTxBlk->QueIdx].Cell[TxIdx].AllocVa;
1454 +
1455 + > For Rx Alloc:
1456 + sd_idx = -1
1457 + */
1458 +
1459 + pAd = (PRTMP_ADAPTER)handle;
1460 + pObj = (POS_COOKIE)pAd->OS_Cookie;
1461 +
1462 + if (sd_idx == 1)
1463 + {
1464 + PTX_BLK pTxBlk;
1465 + pTxBlk = (PTX_BLK)ptr;
1466 + return pci_map_single(pObj->pci_dev, pTxBlk->pSrcBufData, pTxBlk->SrcBufLen, direction);
1467 + }
1468 + else
1469 + {
1470 + return pci_map_single(pObj->pci_dev, ptr, size, direction);
1471 + }
1472 +
1473 +}
1474 +
1475 +void linux_pci_unmap_single(void *handle, dma_addr_t dma_addr, size_t size, int direction)
1476 +{
1477 + PRTMP_ADAPTER pAd;
1478 + POS_COOKIE pObj;
1479 +
1480 + pAd=(PRTMP_ADAPTER)handle;
1481 + pObj = (POS_COOKIE)pAd->OS_Cookie;
1482 +
1483 + pci_unmap_single(pObj->pci_dev, dma_addr, size, direction);
1484 +
1485 +}
1486 +
1487 --- /dev/null
1488 +++ b/drivers/staging/rt2860/aironet.h
1489 @@ -0,0 +1,210 @@
1490 +/*
1491 + *************************************************************************
1492 + * Ralink Tech Inc.
1493 + * 5F., No.36, Taiyuan St., Jhubei City,
1494 + * Hsinchu County 302,
1495 + * Taiwan, R.O.C.
1496 + *
1497 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
1498 + *
1499 + * This program is free software; you can redistribute it and/or modify *
1500 + * it under the terms of the GNU General Public License as published by *
1501 + * the Free Software Foundation; either version 2 of the License, or *
1502 + * (at your option) any later version. *
1503 + * *
1504 + * This program is distributed in the hope that it will be useful, *
1505 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
1506 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
1507 + * GNU General Public License for more details. *
1508 + * *
1509 + * You should have received a copy of the GNU General Public License *
1510 + * along with this program; if not, write to the *
1511 + * Free Software Foundation, Inc., *
1512 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
1513 + * *
1514 + *************************************************************************
1515 +
1516 + Module Name:
1517 + aironet.h
1518 +
1519 + Abstract:
1520 +
1521 + Revision History:
1522 + Who When What
1523 + -------- ---------- ----------------------------------------------
1524 + Name Date Modification logs
1525 + Paul Lin 04-06-15 Initial
1526 +*/
1527 +
1528 +#ifndef __AIRONET_H__
1529 +#define __AIRONET_H__
1530 +
1531 +// Measurement Type definition
1532 +#define MSRN_TYPE_UNUSED 0
1533 +#define MSRN_TYPE_CHANNEL_LOAD_REQ 1
1534 +#define MSRN_TYPE_NOISE_HIST_REQ 2
1535 +#define MSRN_TYPE_BEACON_REQ 3
1536 +#define MSRN_TYPE_FRAME_REQ 4
1537 +
1538 +// Scan Mode in Beacon Request
1539 +#define MSRN_SCAN_MODE_PASSIVE 0
1540 +#define MSRN_SCAN_MODE_ACTIVE 1
1541 +#define MSRN_SCAN_MODE_BEACON_TABLE 2
1542 +
1543 +// PHY type definition for Aironet beacon report, CCX 2 table 36-9
1544 +#define PHY_FH 1
1545 +#define PHY_DSS 2
1546 +#define PHY_UNUSED 3
1547 +#define PHY_OFDM 4
1548 +#define PHY_HR_DSS 5
1549 +#define PHY_ERP 6
1550 +
1551 +// RPI table in dBm
1552 +#define RPI_0 0 // Power <= -87
1553 +#define RPI_1 1 // -87 < Power <= -82
1554 +#define RPI_2 2 // -82 < Power <= -77
1555 +#define RPI_3 3 // -77 < Power <= -72
1556 +#define RPI_4 4 // -72 < Power <= -67
1557 +#define RPI_5 5 // -67 < Power <= -62
1558 +#define RPI_6 6 // -62 < Power <= -57
1559 +#define RPI_7 7 // -57 < Power
1560 +
1561 +// Cisco Aironet IAPP definetions
1562 +#define AIRONET_IAPP_TYPE 0x32
1563 +#define AIRONET_IAPP_SUBTYPE_REQUEST 0x01
1564 +#define AIRONET_IAPP_SUBTYPE_REPORT 0x81
1565 +
1566 +// Measurement Request detail format
1567 +typedef struct _MEASUREMENT_REQUEST {
1568 + UCHAR Channel;
1569 + UCHAR ScanMode; // Use only in beacon request, other requests did not use this field
1570 + USHORT Duration;
1571 +} MEASUREMENT_REQUEST, *PMEASUREMENT_REQUEST;
1572 +
1573 +// Beacon Measurement Report
1574 +// All these field might change to UCHAR, because we didn't do anything to these report.
1575 +// We copy all these beacons and report to CCX 2 AP.
1576 +typedef struct _BEACON_REPORT {
1577 + UCHAR Channel;
1578 + UCHAR Spare;
1579 + USHORT Duration;
1580 + UCHAR PhyType; // Definiation is listed above table 36-9
1581 + UCHAR RxPower;
1582 + UCHAR BSSID[6];
1583 + UCHAR ParentTSF[4];
1584 + UCHAR TargetTSF[8];
1585 + USHORT BeaconInterval;
1586 + USHORT CapabilityInfo;
1587 +} BEACON_REPORT, *PBEACON_REPORT;
1588 +
1589 +// Frame Measurement Report (Optional)
1590 +typedef struct _FRAME_REPORT {
1591 + UCHAR Channel;
1592 + UCHAR Spare;
1593 + USHORT Duration;
1594 + UCHAR TA;
1595 + UCHAR BSSID[6];
1596 + UCHAR RSSI;
1597 + UCHAR Count;
1598 +} FRAME_REPORT, *PFRAME_REPORT;
1599 +
1600 +#pragma pack(1)
1601 +// Channel Load Report
1602 +typedef struct _CHANNEL_LOAD_REPORT {
1603 + UCHAR Channel;
1604 + UCHAR Spare;
1605 + USHORT Duration;
1606 + UCHAR CCABusy;
1607 +} CHANNEL_LOAD_REPORT, *PCHANNEL_LOAD_REPORT;
1608 +#pragma pack()
1609 +
1610 +// Nosie Histogram Report
1611 +typedef struct _NOISE_HIST_REPORT {
1612 + UCHAR Channel;
1613 + UCHAR Spare;
1614 + USHORT Duration;
1615 + UCHAR Density[8];
1616 +} NOISE_HIST_REPORT, *PNOISE_HIST_REPORT;
1617 +
1618 +// Radio Management Capability element
1619 +typedef struct _RADIO_MANAGEMENT_CAPABILITY {
1620 + UCHAR Eid; // TODO: Why the Eid is 1 byte, not normal 2 bytes???
1621 + UCHAR Length;
1622 + UCHAR AironetOui[3]; // AIronet OUI (00 40 96)
1623 + UCHAR Type; // Type / Version
1624 + USHORT Status; // swap16 required
1625 +} RADIO_MANAGEMENT_CAPABILITY, *PRADIO_MANAGEMENT_CAPABILITY;
1626 +
1627 +// Measurement Mode Bit definition
1628 +typedef struct _MEASUREMENT_MODE {
1629 + UCHAR Rsvd:4;
1630 + UCHAR Report:1;
1631 + UCHAR NotUsed:1;
1632 + UCHAR Enable:1;
1633 + UCHAR Parallel:1;
1634 +} MEASUREMENT_MODE, *PMEASUREMENT_MODE;
1635 +
1636 +// Measurement Request element, This is little endian mode
1637 +typedef struct _MEASUREMENT_REQUEST_ELEMENT {
1638 + USHORT Eid;
1639 + USHORT Length; // swap16 required
1640 + USHORT Token; // non-zero unique token
1641 + UCHAR Mode; // Measurement Mode
1642 + UCHAR Type; // Measurement type
1643 +} MEASUREMENT_REQUEST_ELEMENT, *PMEASUREMENT_REQUEST_ELEMENT;
1644 +
1645 +// Measurement Report element, This is little endian mode
1646 +typedef struct _MEASUREMENT_REPORT_ELEMENT {
1647 + USHORT Eid;
1648 + USHORT Length; // swap16 required
1649 + USHORT Token; // non-zero unique token
1650 + UCHAR Mode; // Measurement Mode
1651 + UCHAR Type; // Measurement type
1652 +} MEASUREMENT_REPORT_ELEMENT, *PMEASUREMENT_REPORT_ELEMENT;
1653 +
1654 +// Cisco Aironet IAPP Frame Header, Network byte order used
1655 +typedef struct _AIRONET_IAPP_HEADER {
1656 + UCHAR CiscoSnapHeader[8]; // 8 bytes Cisco snap header
1657 + USHORT Length; // IAPP ID & length, remember to swap16 in LE system
1658 + UCHAR Type; // IAPP type
1659 + UCHAR SubType; // IAPP subtype
1660 + UCHAR DA[6]; // Destination MAC address
1661 + UCHAR SA[6]; // Source MAC address
1662 + USHORT Token; // Dialog token, no need to swap16 since it is for yoken usage only
1663 +} AIRONET_IAPP_HEADER, *PAIRONET_IAPP_HEADER;
1664 +
1665 +// Radio Measurement Request frame
1666 +typedef struct _AIRONET_RM_REQUEST_FRAME {
1667 + AIRONET_IAPP_HEADER IAPP; // Common header
1668 + UCHAR Delay; // Activation Delay
1669 + UCHAR Offset; // Measurement offset
1670 +} AIRONET_RM_REQUEST_FRAME, *PAIRONET_RM_REQUEST_FRAME;
1671 +
1672 +// Radio Measurement Report frame
1673 +typedef struct _AIRONET_RM_REPORT_FRAME {
1674 + AIRONET_IAPP_HEADER IAPP; // Common header
1675 +} AIRONET_RM_REPORT_FRAME, *PAIRONET_RM_REPORT_FRAME;
1676 +
1677 +// Saved element request actions which will saved in StaCfg.
1678 +typedef struct _RM_REQUEST_ACTION {
1679 + MEASUREMENT_REQUEST_ELEMENT ReqElem; // Saved request element
1680 + MEASUREMENT_REQUEST Measurement; // Saved measurement within the request element
1681 +} RM_REQUEST_ACTION, *PRM_REQUEST_ACTION;
1682 +
1683 +// CCX administration control
1684 +typedef union _CCX_CONTROL {
1685 + struct {
1686 + UINT32 Enable:1; // Enable CCX2
1687 + UINT32 LeapEnable:1; // Enable LEAP at CCX2
1688 + UINT32 RMEnable:1; // Radio Measurement Enable
1689 + UINT32 DCRMEnable:1; // Non serving channel Radio Measurement enable
1690 + UINT32 QOSEnable:1; // Enable QOS for CCX 2.0 support
1691 + UINT32 FastRoamEnable:1; // Enable fast roaming
1692 + UINT32 Rsvd:2; // Not used
1693 + UINT32 dBmToRoam:8; // the condition to roam when receiving Rssi less than this value. It's negative value.
1694 + UINT32 TuLimit:16; // Limit for different channel scan
1695 + } field;
1696 + UINT32 word;
1697 +} CCX_CONTROL, *PCCX_CONTROL;
1698 +
1699 +#endif // __AIRONET_H__
1700 --- /dev/null
1701 +++ b/drivers/staging/rt2860/ap.h
1702 @@ -0,0 +1,557 @@
1703 +/*
1704 + *************************************************************************
1705 + * Ralink Tech Inc.
1706 + * 5F., No.36, Taiyuan St., Jhubei City,
1707 + * Hsinchu County 302,
1708 + * Taiwan, R.O.C.
1709 + *
1710 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
1711 + *
1712 + * This program is free software; you can redistribute it and/or modify *
1713 + * it under the terms of the GNU General Public License as published by *
1714 + * the Free Software Foundation; either version 2 of the License, or *
1715 + * (at your option) any later version. *
1716 + * *
1717 + * This program is distributed in the hope that it will be useful, *
1718 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
1719 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
1720 + * GNU General Public License for more details. *
1721 + * *
1722 + * You should have received a copy of the GNU General Public License *
1723 + * along with this program; if not, write to the *
1724 + * Free Software Foundation, Inc., *
1725 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
1726 + * *
1727 + *************************************************************************
1728 +
1729 + Module Name:
1730 + ap.h
1731 +
1732 + Abstract:
1733 + Miniport generic portion header file
1734 +
1735 + Revision History:
1736 + Who When What
1737 + -------- ---------- ----------------------------------------------
1738 + Paul Lin 08-01-2002 created
1739 + James Tan 09-06-2002 modified (Revise NTCRegTable)
1740 + John Chang 12-22-2004 modified for RT2561/2661. merge with STA driver
1741 +*/
1742 +#ifndef __AP_H__
1743 +#define __AP_H__
1744 +
1745 +
1746 +
1747 +// ========================= AP RTMP.h ================================
1748 +
1749 +
1750 +
1751 +// =============================================================
1752 +// Function Prototypes
1753 +// =============================================================
1754 +
1755 +// ap_data.c
1756 +
1757 +BOOLEAN APBridgeToWirelessSta(
1758 + IN PRTMP_ADAPTER pAd,
1759 + IN PUCHAR pHeader,
1760 + IN UINT HdrLen,
1761 + IN PUCHAR pData,
1762 + IN UINT DataLen,
1763 + IN ULONG fromwdsidx);
1764 +
1765 +BOOLEAN APHandleRxDoneInterrupt(
1766 + IN PRTMP_ADAPTER pAd);
1767 +
1768 +VOID APSendPackets(
1769 + IN NDIS_HANDLE MiniportAdapterContext,
1770 + IN PPNDIS_PACKET ppPacketArray,
1771 + IN UINT NumberOfPackets);
1772 +
1773 +NDIS_STATUS APSendPacket(
1774 + IN PRTMP_ADAPTER pAd,
1775 + IN PNDIS_PACKET pPacket);
1776 +
1777 +
1778 +NDIS_STATUS APHardTransmit(
1779 + IN PRTMP_ADAPTER pAd,
1780 + IN TX_BLK *pTxBlk,
1781 + IN UCHAR QueIdx);
1782 +
1783 +VOID APRxEAPOLFrameIndicate(
1784 + IN PRTMP_ADAPTER pAd,
1785 + IN MAC_TABLE_ENTRY *pEntry,
1786 + IN RX_BLK *pRxBlk,
1787 + IN UCHAR FromWhichBSSID);
1788 +
1789 +NDIS_STATUS APCheckRxError(
1790 + IN PRTMP_ADAPTER pAd,
1791 + IN PRT28XX_RXD_STRUC pRxD,
1792 + IN UCHAR Wcid);
1793 +
1794 +BOOLEAN APCheckClass2Class3Error(
1795 + IN PRTMP_ADAPTER pAd,
1796 + IN ULONG Wcid,
1797 + IN PHEADER_802_11 pHeader);
1798 +
1799 +VOID APHandleRxPsPoll(
1800 + IN PRTMP_ADAPTER pAd,
1801 + IN PUCHAR pAddr,
1802 + IN USHORT Aid,
1803 + IN BOOLEAN isActive);
1804 +
1805 +VOID RTMPDescriptorEndianChange(
1806 + IN PUCHAR pData,
1807 + IN ULONG DescriptorType);
1808 +
1809 +VOID RTMPFrameEndianChange(
1810 + IN PRTMP_ADAPTER pAd,
1811 + IN PUCHAR pData,
1812 + IN ULONG Dir,
1813 + IN BOOLEAN FromRxDoneInt);
1814 +
1815 +// ap_assoc.c
1816 +
1817 +VOID APAssocStateMachineInit(
1818 + IN PRTMP_ADAPTER pAd,
1819 + IN STATE_MACHINE *S,
1820 + OUT STATE_MACHINE_FUNC Trans[]);
1821 +
1822 +VOID APPeerAssocReqAction(
1823 + IN PRTMP_ADAPTER pAd,
1824 + IN MLME_QUEUE_ELEM *Elem);
1825 +
1826 +VOID APPeerReassocReqAction(
1827 + IN PRTMP_ADAPTER pAd,
1828 + IN MLME_QUEUE_ELEM *Elem);
1829 +
1830 +VOID APPeerDisassocReqAction(
1831 + IN PRTMP_ADAPTER pAd,
1832 + IN MLME_QUEUE_ELEM *Elem);
1833 +
1834 +VOID MbssKickOutStas(
1835 + IN PRTMP_ADAPTER pAd,
1836 + IN INT apidx,
1837 + IN USHORT Reason);
1838 +
1839 +VOID APMlmeKickOutSta(
1840 + IN PRTMP_ADAPTER pAd,
1841 + IN PUCHAR pStaAddr,
1842 + IN UCHAR Wcid,
1843 + IN USHORT Reason);
1844 +
1845 +VOID APMlmeDisassocReqAction(
1846 + IN PRTMP_ADAPTER pAd,
1847 + IN MLME_QUEUE_ELEM *Elem);
1848 +
1849 +VOID APCls3errAction(
1850 + IN PRTMP_ADAPTER pAd,
1851 + IN ULONG Wcid,
1852 + IN PHEADER_802_11 pHeader);
1853 +
1854 +
1855 +USHORT APBuildAssociation(
1856 + IN PRTMP_ADAPTER pAd,
1857 + IN MAC_TABLE_ENTRY *pEntry,
1858 + IN USHORT CapabilityInfo,
1859 + IN UCHAR MaxSupportedRateIn500Kbps,
1860 + IN UCHAR *RSN,
1861 + IN UCHAR *pRSNLen,
1862 + IN BOOLEAN bWmmCapable,
1863 + IN ULONG RalinkIe,
1864 +#ifdef DOT11N_DRAFT3
1865 + IN EXT_CAP_INFO_ELEMENT ExtCapInfo,
1866 +#endif // DOT11N_DRAFT3 //
1867 + IN HT_CAPABILITY_IE *pHtCapability,
1868 + IN UCHAR HtCapabilityLen,
1869 + OUT USHORT *pAid);
1870 +
1871 +// ap_auth.c
1872 +
1873 +void APAuthStateMachineInit(
1874 + IN PRTMP_ADAPTER pAd,
1875 + IN STATE_MACHINE *Sm,
1876 + OUT STATE_MACHINE_FUNC Trans[]);
1877 +
1878 +VOID APMlmeDeauthReqAction(
1879 + IN PRTMP_ADAPTER pAd,
1880 + IN MLME_QUEUE_ELEM *Elem);
1881 +
1882 +VOID APCls2errAction(
1883 + IN PRTMP_ADAPTER pAd,
1884 + IN ULONG Wcid,
1885 + IN PHEADER_802_11 pHeader);
1886 +
1887 +// ap_authrsp.c
1888 +
1889 +VOID APAuthRspStateMachineInit(
1890 + IN PRTMP_ADAPTER pAd,
1891 + IN PSTATE_MACHINE Sm,
1892 + IN STATE_MACHINE_FUNC Trans[]);
1893 +
1894 +VOID APPeerAuthAtAuthRspIdleAction(
1895 + IN PRTMP_ADAPTER pAd,
1896 + IN MLME_QUEUE_ELEM *Elem);
1897 +
1898 +VOID APPeerDeauthReqAction(
1899 + IN PRTMP_ADAPTER pAd,
1900 + IN MLME_QUEUE_ELEM *Elem);
1901 +
1902 +VOID APPeerAuthSimpleRspGenAndSend(
1903 + IN PRTMP_ADAPTER pAd,
1904 + IN PHEADER_802_11 pHdr80211,
1905 + IN USHORT Alg,
1906 + IN USHORT Seq,
1907 + IN USHORT StatusCode);
1908 +
1909 +// ap_connect.c
1910 +
1911 +BOOLEAN BeaconTransmitRequired(
1912 + IN PRTMP_ADAPTER pAd,
1913 + IN INT apidx);
1914 +
1915 +VOID APMakeBssBeacon(
1916 + IN PRTMP_ADAPTER pAd,
1917 + IN INT apidx);
1918 +
1919 +VOID APUpdateBeaconFrame(
1920 + IN PRTMP_ADAPTER pAd,
1921 + IN INT apidx);
1922 +
1923 +VOID APMakeAllBssBeacon(
1924 + IN PRTMP_ADAPTER pAd);
1925 +
1926 +VOID APUpdateAllBeaconFrame(
1927 + IN PRTMP_ADAPTER pAd);
1928 +
1929 +
1930 +// ap_sync.c
1931 +
1932 +VOID APSyncStateMachineInit(
1933 + IN PRTMP_ADAPTER pAd,
1934 + IN STATE_MACHINE *Sm,
1935 + OUT STATE_MACHINE_FUNC Trans[]);
1936 +
1937 +VOID APScanTimeout(
1938 + IN PVOID SystemSpecific1,
1939 + IN PVOID FunctionContext,
1940 + IN PVOID SystemSpecific2,
1941 + IN PVOID SystemSpecific3);
1942 +
1943 +VOID APInvalidStateWhenScan(
1944 + IN PRTMP_ADAPTER pAd,
1945 + IN MLME_QUEUE_ELEM *Elem);
1946 +
1947 +VOID APScanTimeoutAction(
1948 + IN PRTMP_ADAPTER pAd,
1949 + IN MLME_QUEUE_ELEM *Elem);
1950 +
1951 +VOID APPeerProbeReqAction(
1952 + IN PRTMP_ADAPTER pAd,
1953 + IN MLME_QUEUE_ELEM *Elem);
1954 +
1955 +VOID APPeerBeaconAction(
1956 + IN PRTMP_ADAPTER pAd,
1957 + IN MLME_QUEUE_ELEM *Elem);
1958 +
1959 +VOID APMlmeScanReqAction(
1960 + IN PRTMP_ADAPTER pAd,
1961 + IN MLME_QUEUE_ELEM *Elem);
1962 +
1963 +VOID APPeerBeaconAtScanAction(
1964 + IN PRTMP_ADAPTER pAd,
1965 + IN MLME_QUEUE_ELEM *Elem);
1966 +
1967 +VOID APScanCnclAction(
1968 + IN PRTMP_ADAPTER pAd,
1969 + IN MLME_QUEUE_ELEM *Elem);
1970 +
1971 +VOID ApSiteSurvey(
1972 + IN PRTMP_ADAPTER pAd);
1973 +
1974 +VOID SupportRate(
1975 + IN PUCHAR SupRate,
1976 + IN UCHAR SupRateLen,
1977 + IN PUCHAR ExtRate,
1978 + IN UCHAR ExtRateLen,
1979 + OUT PUCHAR *Rates,
1980 + OUT PUCHAR RatesLen,
1981 + OUT PUCHAR pMaxSupportRate);
1982 +
1983 +
1984 +BOOLEAN ApScanRunning(
1985 + IN PRTMP_ADAPTER pAd);
1986 +
1987 +#ifdef DOT11N_DRAFT3
1988 +VOID APOverlappingBSSScan(
1989 + IN RTMP_ADAPTER *pAd);
1990 +#endif // DOT11N_DRAFT3 //
1991 +
1992 +// ap_wpa.c
1993 +
1994 +VOID APWpaStateMachineInit(
1995 + IN PRTMP_ADAPTER pAd,
1996 + IN STATE_MACHINE *Sm,
1997 + OUT STATE_MACHINE_FUNC Trans[]);
1998 +
1999 +// ap_mlme.c
2000 +
2001 +VOID APMlmePeriodicExec(
2002 + IN PRTMP_ADAPTER pAd);
2003 +
2004 +VOID APMlmeSelectTxRateTable(
2005 + IN PRTMP_ADAPTER pAd,
2006 + IN PMAC_TABLE_ENTRY pEntry,
2007 + IN PUCHAR *ppTable,
2008 + IN PUCHAR pTableSize,
2009 + IN PUCHAR pInitTxRateIdx);
2010 +
2011 +VOID APMlmeSetTxRate(
2012 + IN PRTMP_ADAPTER pAd,
2013 + IN PMAC_TABLE_ENTRY pEntry,
2014 + IN PRTMP_TX_RATE_SWITCH pTxRate);
2015 +
2016 +VOID APMlmeDynamicTxRateSwitching(
2017 + IN PRTMP_ADAPTER pAd);
2018 +
2019 +VOID APQuickResponeForRateUpExec(
2020 + IN PVOID SystemSpecific1,
2021 + IN PVOID FunctionContext,
2022 + IN PVOID SystemSpecific2,
2023 + IN PVOID SystemSpecific3);
2024 +
2025 +BOOLEAN APMsgTypeSubst(
2026 + IN PRTMP_ADAPTER pAd,
2027 + IN PFRAME_802_11 pFrame,
2028 + OUT INT *Machine,
2029 + OUT INT *MsgType);
2030 +
2031 +VOID APQuickResponeForRateUpExec(
2032 + IN PVOID SystemSpecific1,
2033 + IN PVOID FunctionContext,
2034 + IN PVOID SystemSpecific2,
2035 + IN PVOID SystemSpecific3);
2036 +
2037 +
2038 +VOID RTMPSetPiggyBack(
2039 + IN PRTMP_ADAPTER pAd,
2040 + IN BOOLEAN bPiggyBack);
2041 +
2042 +VOID APAsicEvaluateRxAnt(
2043 + IN PRTMP_ADAPTER pAd);
2044 +
2045 +VOID APAsicRxAntEvalTimeout(
2046 + IN PRTMP_ADAPTER pAd);
2047 +
2048 +// ap.c
2049 +
2050 +VOID APSwitchChannel(
2051 + IN PRTMP_ADAPTER pAd,
2052 + IN INT Channel);
2053 +
2054 +NDIS_STATUS APInitialize(
2055 + IN PRTMP_ADAPTER pAd);
2056 +
2057 +VOID APShutdown(
2058 + IN PRTMP_ADAPTER pAd);
2059 +
2060 +VOID APStartUp(
2061 + IN PRTMP_ADAPTER pAd);
2062 +
2063 +VOID APStop(
2064 + IN PRTMP_ADAPTER pAd);
2065 +
2066 +VOID APCleanupPsQueue(
2067 + IN PRTMP_ADAPTER pAd,
2068 + IN PQUEUE_HEADER pQueue);
2069 +
2070 +VOID MacTableReset(
2071 + IN PRTMP_ADAPTER pAd);
2072 +
2073 +MAC_TABLE_ENTRY *MacTableInsertEntry(
2074 + IN PRTMP_ADAPTER pAd,
2075 + IN PUCHAR pAddr,
2076 + IN UCHAR apidx,
2077 + IN BOOLEAN CleanAll);
2078 +
2079 +BOOLEAN MacTableDeleteEntry(
2080 + IN PRTMP_ADAPTER pAd,
2081 + IN USHORT wcid,
2082 + IN PUCHAR pAddr);
2083 +
2084 +MAC_TABLE_ENTRY *MacTableLookup(
2085 + IN PRTMP_ADAPTER pAd,
2086 + IN PUCHAR pAddr);
2087 +
2088 +VOID MacTableMaintenance(
2089 + IN PRTMP_ADAPTER pAd);
2090 +
2091 +UINT32 MacTableAssocStaNumGet(
2092 + IN PRTMP_ADAPTER pAd);
2093 +
2094 +MAC_TABLE_ENTRY *APSsPsInquiry(
2095 + IN PRTMP_ADAPTER pAd,
2096 + IN PUCHAR pAddr,
2097 + OUT SST *Sst,
2098 + OUT USHORT *Aid,
2099 + OUT UCHAR *PsMode,
2100 + OUT UCHAR *Rate);
2101 +
2102 +BOOLEAN APPsIndicate(
2103 + IN PRTMP_ADAPTER pAd,
2104 + IN PUCHAR pAddr,
2105 + IN ULONG Wcid,
2106 + IN UCHAR Psm);
2107 +
2108 +VOID ApLogEvent(
2109 + IN PRTMP_ADAPTER pAd,
2110 + IN PUCHAR pAddr,
2111 + IN USHORT Event);
2112 +
2113 +#ifdef DOT11_N_SUPPORT
2114 +VOID APUpdateOperationMode(
2115 + IN PRTMP_ADAPTER pAd);
2116 +#endif // DOT11_N_SUPPORT //
2117 +
2118 +VOID APUpdateCapabilityAndErpIe(
2119 + IN PRTMP_ADAPTER pAd);
2120 +
2121 +BOOLEAN ApCheckAccessControlList(
2122 + IN PRTMP_ADAPTER pAd,
2123 + IN PUCHAR pAddr,
2124 + IN UCHAR Apidx);
2125 +
2126 +VOID ApUpdateAccessControlList(
2127 + IN PRTMP_ADAPTER pAd,
2128 + IN UCHAR Apidx);
2129 +
2130 +VOID ApEnqueueNullFrame(
2131 + IN PRTMP_ADAPTER pAd,
2132 + IN PUCHAR pAddr,
2133 + IN UCHAR TxRate,
2134 + IN UCHAR PID,
2135 + IN UCHAR apidx,
2136 + IN BOOLEAN bQosNull,
2137 + IN BOOLEAN bEOSP,
2138 + IN UCHAR OldUP);
2139 +
2140 +VOID ApSendFrame(
2141 + IN PRTMP_ADAPTER pAd,
2142 + IN PVOID pBuffer,
2143 + IN ULONG Length,
2144 + IN UCHAR TxRate,
2145 + IN UCHAR PID);
2146 +
2147 +VOID ApEnqueueAckFrame(
2148 + IN PRTMP_ADAPTER pAd,
2149 + IN PUCHAR pAddr,
2150 + IN UCHAR TxRate,
2151 + IN UCHAR apidx);
2152 +
2153 +UCHAR APAutoSelectChannel(
2154 + IN PRTMP_ADAPTER pAd,
2155 + IN BOOLEAN Optimal);
2156 +
2157 +// ap_sanity.c
2158 +
2159 +
2160 +BOOLEAN PeerAssocReqCmmSanity(
2161 + IN PRTMP_ADAPTER pAd,
2162 + IN BOOLEAN isRessoc,
2163 + IN VOID *Msg,
2164 + IN ULONG MsgLen,
2165 + OUT PUCHAR pAddr2,
2166 + OUT USHORT *pCapabilityInfo,
2167 + OUT USHORT *pListenInterval,
2168 + OUT PUCHAR pApAddr,
2169 + OUT UCHAR *pSsidLen,
2170 + OUT char *Ssid,
2171 + OUT UCHAR *pRatesLen,
2172 + OUT UCHAR Rates[],
2173 + OUT UCHAR *RSN,
2174 + OUT UCHAR *pRSNLen,
2175 + OUT BOOLEAN *pbWmmCapable,
2176 + OUT ULONG *pRalinkIe,
2177 +#ifdef DOT11N_DRAFT3
2178 + OUT EXT_CAP_INFO_ELEMENT *pExtCapInfo,
2179 +#endif // DOT11N_DRAFT3 //
2180 + OUT UCHAR *pHtCapabilityLen,
2181 + OUT HT_CAPABILITY_IE *pHtCapability);
2182 +
2183 +BOOLEAN PeerDisassocReqSanity(
2184 + IN PRTMP_ADAPTER pAd,
2185 + IN VOID *Msg,
2186 + IN ULONG MsgLen,
2187 + OUT PUCHAR pAddr2,
2188 + OUT USHORT *Reason);
2189 +
2190 +BOOLEAN PeerDeauthReqSanity(
2191 + IN PRTMP_ADAPTER pAd,
2192 + IN VOID *Msg,
2193 + IN ULONG MsgLen,
2194 + OUT PUCHAR pAddr2,
2195 + OUT USHORT *Reason);
2196 +
2197 +BOOLEAN APPeerAuthSanity(
2198 + IN PRTMP_ADAPTER pAd,
2199 + IN VOID *Msg,
2200 + IN ULONG MsgLen,
2201 + OUT PUCHAR pAddr1,
2202 + OUT PUCHAR pAddr2,
2203 + OUT USHORT *Alg,
2204 + OUT USHORT *Seq,
2205 + OUT USHORT *Status,
2206 + CHAR *ChlgText);
2207 +
2208 +BOOLEAN APPeerProbeReqSanity(
2209 + IN PRTMP_ADAPTER pAd,
2210 + IN VOID *Msg,
2211 + IN ULONG MsgLen,
2212 + OUT PUCHAR pAddr2,
2213 + OUT CHAR Ssid[],
2214 + OUT UCHAR *SsidLen);
2215 +
2216 +BOOLEAN APPeerBeaconAndProbeRspSanity(
2217 + IN PRTMP_ADAPTER pAd,
2218 + IN VOID *Msg,
2219 + IN ULONG MsgLen,
2220 + OUT PUCHAR pAddr2,
2221 + OUT PUCHAR pBssid,
2222 + OUT CHAR Ssid[],
2223 + OUT UCHAR *SsidLen,
2224 + OUT UCHAR *BssType,
2225 + OUT USHORT *BeaconPeriod,
2226 + OUT UCHAR *Channel,
2227 + OUT LARGE_INTEGER *Timestamp,
2228 + OUT USHORT *CapabilityInfo,
2229 + OUT UCHAR Rate[],
2230 + OUT UCHAR *RateLen,
2231 + OUT BOOLEAN *ExtendedRateIeExist,
2232 + OUT UCHAR *Erp);
2233 +
2234 +// ap_info.c
2235 +
2236 +#ifdef WIN_NDIS
2237 +NDIS_STATUS APQueryInformation(
2238 + IN NDIS_HANDLE MiniportAdapterContext,
2239 + IN NDIS_OID Oid,
2240 + IN PVOID pInformationBuffer,
2241 + IN ULONG InformationBufferLength,
2242 + OUT PULONG pBytesWritten,
2243 + OUT PULONG pBytesNeeded);
2244 +
2245 +NDIS_STATUS APSetInformation(
2246 + IN NDIS_HANDLE MiniportAdapterContext,
2247 + IN NDIS_OID Oid,
2248 + IN PVOID pInformationBuffer,
2249 + IN ULONG InformationBufferLength,
2250 + OUT PULONG pBytesRead,
2251 + OUT PULONG pBytesNeeded);
2252 +#endif
2253 +
2254 +
2255 +// ================== end of AP RTMP.h ========================
2256 +
2257 +
2258 +#endif // __AP_H__
2259 +
2260 --- /dev/null
2261 +++ b/drivers/staging/rt2860/chlist.h
2262 @@ -0,0 +1,1296 @@
2263 +/*
2264 + *************************************************************************
2265 + * Ralink Tech Inc.
2266 + * 5F., No.36, Taiyuan St., Jhubei City,
2267 + * Hsinchu County 302,
2268 + * Taiwan, R.O.C.
2269 + *
2270 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
2271 + *
2272 + * This program is free software; you can redistribute it and/or modify *
2273 + * it under the terms of the GNU General Public License as published by *
2274 + * the Free Software Foundation; either version 2 of the License, or *
2275 + * (at your option) any later version. *
2276 + * *
2277 + * This program is distributed in the hope that it will be useful, *
2278 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
2279 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
2280 + * GNU General Public License for more details. *
2281 + * *
2282 + * You should have received a copy of the GNU General Public License *
2283 + * along with this program; if not, write to the *
2284 + * Free Software Foundation, Inc., *
2285 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
2286 + * *
2287 + *************************************************************************
2288 +
2289 + Module Name:
2290 + chlist.c
2291 +
2292 + Abstract:
2293 +
2294 + Revision History:
2295 + Who When What
2296 + -------- ---------- ----------------------------------------------
2297 + Fonchi Wu 2007-12-19 created
2298 +*/
2299 +
2300 +#ifndef __CHLIST_H__
2301 +#define __CHLIST_H__
2302 +
2303 +#include "rtmp_type.h"
2304 +#include "rtmp_def.h"
2305 +
2306 +
2307 +#define ODOR 0
2308 +#define IDOR 1
2309 +#define BOTH 2
2310 +
2311 +#define BAND_5G 0
2312 +#define BAND_24G 1
2313 +#define BAND_BOTH 2
2314 +
2315 +typedef struct _CH_DESP {
2316 + UCHAR FirstChannel;
2317 + UCHAR NumOfCh;
2318 + CHAR MaxTxPwr; // dBm
2319 + UCHAR Geography; // 0:out door, 1:in door, 2:both
2320 + BOOLEAN DfsReq; // Dfs require, 0: No, 1: yes.
2321 +} CH_DESP, *PCH_DESP;
2322 +
2323 +typedef struct _CH_REGION {
2324 + UCHAR CountReg[3];
2325 + UCHAR DfsType; // 0: CE, 1: FCC, 2: JAP, 3:JAP_W53, JAP_W56
2326 + CH_DESP ChDesp[10];
2327 +} CH_REGION, *PCH_REGION;
2328 +
2329 +static CH_REGION ChRegion[] =
2330 +{
2331 + { // Antigua and Berbuda
2332 + "AG",
2333 + CE,
2334 + {
2335 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2336 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2337 + { 52, 4, 23, BOTH, FALSE}, // 5G, ch 52~64
2338 + { 100, 11, 30, BOTH, FALSE}, // 5G, ch 100~140
2339 + { 0}, // end
2340 + }
2341 + },
2342 +
2343 + { // Argentina
2344 + "AR",
2345 + CE,
2346 + {
2347 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2348 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2349 + { 149, 4, 30, BOTH, FALSE}, // 5G, ch 149~161
2350 + { 0}, // end
2351 + }
2352 + },
2353 +
2354 + { // Aruba
2355 + "AW",
2356 + CE,
2357 + {
2358 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2359 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2360 + { 52, 4, 23, BOTH, FALSE}, // 5G, ch 52~64
2361 + { 100, 11, 30, BOTH, FALSE}, // 5G, ch 100~140
2362 + { 0}, // end
2363 + }
2364 + },
2365 +
2366 + { // Australia
2367 + "AU",
2368 + CE,
2369 + {
2370 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2371 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2372 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2373 + { 149, 5, 30, BOTH, FALSE}, // 5G, ch 149~165
2374 + { 0}, // end
2375 + }
2376 + },
2377 +
2378 + { // Austria
2379 + "AT",
2380 + CE,
2381 + {
2382 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2383 + { 36, 4, 23, IDOR, TRUE}, // 5G, ch 36~48
2384 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2385 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2386 + { 0}, // end
2387 + }
2388 + },
2389 +
2390 + { // Bahamas
2391 + "BS",
2392 + CE,
2393 + {
2394 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2395 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2396 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2397 + { 149, 5, 30, BOTH, FALSE}, // 5G, ch 149~165
2398 + { 0}, // end
2399 + }
2400 + },
2401 +
2402 + { // Barbados
2403 + "BB",
2404 + CE,
2405 + {
2406 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2407 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2408 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2409 + { 100, 11, 30, BOTH, FALSE}, // 5G, ch 100~140
2410 + { 0}, // end
2411 + }
2412 + },
2413 +
2414 + { // Bermuda
2415 + "BM",
2416 + CE,
2417 + {
2418 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2419 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2420 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2421 + { 100, 11, 30, BOTH, FALSE}, // 5G, ch 100~140
2422 + { 0}, // end
2423 + }
2424 + },
2425 +
2426 + { // Brazil
2427 + "BR",
2428 + CE,
2429 + {
2430 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2431 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2432 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2433 + { 100, 11, 24, BOTH, FALSE}, // 5G, ch 100~140
2434 + { 149, 5, 30, BOTH, FALSE}, // 5G, ch 100~140
2435 + { 0}, // end
2436 + }
2437 + },
2438 +
2439 + { // Belgium
2440 + "BE",
2441 + CE,
2442 + {
2443 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2444 + { 36, 4, 18, IDOR, FALSE}, // 5G, ch 36~48
2445 + { 52, 4, 18, IDOR, FALSE}, // 5G, ch 52~64
2446 + { 0}, // end
2447 + }
2448 + },
2449 +
2450 + { // Bulgaria
2451 + "BG",
2452 + CE,
2453 + {
2454 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2455 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2456 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2457 + { 100, 11, 30, ODOR, TRUE}, // 5G, ch 100~140
2458 + { 0}, // end
2459 + }
2460 + },
2461 +
2462 + { // Canada
2463 + "CA",
2464 + CE,
2465 + {
2466 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2467 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2468 + { 52, 4, 23, BOTH, FALSE}, // 5G, ch 52~64
2469 + { 149, 5, 30, BOTH, FALSE}, // 5G, ch 149~165
2470 + { 0}, // end
2471 + }
2472 + },
2473 +
2474 + { // Cayman IsLands
2475 + "KY",
2476 + CE,
2477 + {
2478 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2479 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2480 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2481 + { 100, 11, 30, BOTH, FALSE}, // 5G, ch 100~140
2482 + { 0}, // end
2483 + }
2484 + },
2485 +
2486 + { // Chile
2487 + "CL",
2488 + CE,
2489 + {
2490 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2491 + { 36, 4, 20, BOTH, FALSE}, // 5G, ch 36~48
2492 + { 52, 4, 20, BOTH, FALSE}, // 5G, ch 52~64
2493 + { 149, 5, 20, BOTH, FALSE}, // 5G, ch 149~165
2494 + { 0}, // end
2495 + }
2496 + },
2497 +
2498 + { // China
2499 + "CN",
2500 + CE,
2501 + {
2502 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2503 + { 149, 4, 27, BOTH, FALSE}, // 5G, ch 149~161
2504 + { 0}, // end
2505 + }
2506 + },
2507 +
2508 + { // Colombia
2509 + "CO",
2510 + CE,
2511 + {
2512 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2513 + { 36, 4, 17, BOTH, FALSE}, // 5G, ch 36~48
2514 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2515 + { 100, 11, 30, BOTH, FALSE}, // 5G, ch 100~140
2516 + { 149, 5, 30, BOTH, FALSE}, // 5G, ch 149~165
2517 + { 0}, // end
2518 + }
2519 + },
2520 +
2521 + { // Costa Rica
2522 + "CR",
2523 + CE,
2524 + {
2525 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2526 + { 36, 4, 17, BOTH, FALSE}, // 5G, ch 36~48
2527 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2528 + { 149, 4, 30, BOTH, FALSE}, // 5G, ch 149~161
2529 + { 0}, // end
2530 + }
2531 + },
2532 +
2533 + { // Cyprus
2534 + "CY",
2535 + CE,
2536 + {
2537 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2538 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2539 + { 52, 4, 24, IDOR, TRUE}, // 5G, ch 52~64
2540 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2541 + { 0}, // end
2542 + }
2543 + },
2544 +
2545 + { // Czech_Republic
2546 + "CZ",
2547 + CE,
2548 + {
2549 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2550 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2551 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2552 + { 0}, // end
2553 + }
2554 + },
2555 +
2556 + { // Denmark
2557 + "DK",
2558 + CE,
2559 + {
2560 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2561 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2562 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2563 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2564 + { 0}, // end
2565 + }
2566 + },
2567 +
2568 + { // Dominican Republic
2569 + "DO",
2570 + CE,
2571 + {
2572 + { 1, 0, 20, BOTH, FALSE}, // 2.4 G, ch 0
2573 + { 149, 4, 20, BOTH, FALSE}, // 5G, ch 149~161
2574 + { 0}, // end
2575 + }
2576 + },
2577 +
2578 + { // Equador
2579 + "EC",
2580 + CE,
2581 + {
2582 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2583 + { 100, 11, 27, BOTH, FALSE}, // 5G, ch 100~140
2584 + { 0}, // end
2585 + }
2586 + },
2587 +
2588 + { // El Salvador
2589 + "SV",
2590 + CE,
2591 + {
2592 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2593 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2594 + { 52, 4, 30, BOTH, TRUE}, // 5G, ch 52~64
2595 + { 149, 4, 36, BOTH, TRUE}, // 5G, ch 149~165
2596 + { 0}, // end
2597 + }
2598 + },
2599 +
2600 + { // Finland
2601 + "FI",
2602 + CE,
2603 + {
2604 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2605 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2606 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2607 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2608 + { 0}, // end
2609 + }
2610 + },
2611 +
2612 + { // France
2613 + "FR",
2614 + CE,
2615 + {
2616 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2617 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2618 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2619 + { 0}, // end
2620 + }
2621 + },
2622 +
2623 + { // Germany
2624 + "DE",
2625 + CE,
2626 + {
2627 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2628 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2629 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2630 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2631 + { 0}, // end
2632 + }
2633 + },
2634 +
2635 + { // Greece
2636 + "GR",
2637 + CE,
2638 + {
2639 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2640 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2641 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2642 + { 100, 11, 30, ODOR, TRUE}, // 5G, ch 100~140
2643 + { 0}, // end
2644 + }
2645 + },
2646 +
2647 + { // Guam
2648 + "GU",
2649 + CE,
2650 + {
2651 + { 1, 11, 20, BOTH, FALSE}, // 2.4 G, ch 1~11
2652 + { 36, 4, 17, BOTH, FALSE}, // 5G, ch 36~48
2653 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2654 + { 100, 11, 30, BOTH, FALSE}, // 5G, ch 100~140
2655 + { 149, 5, 30, BOTH, FALSE}, // 5G, ch 149~165
2656 + { 0}, // end
2657 + }
2658 + },
2659 +
2660 + { // Guatemala
2661 + "GT",
2662 + CE,
2663 + {
2664 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2665 + { 36, 4, 17, BOTH, FALSE}, // 5G, ch 36~48
2666 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2667 + { 149, 4, 30, BOTH, FALSE}, // 5G, ch 149~161
2668 + { 0}, // end
2669 + }
2670 + },
2671 +
2672 + { // Haiti
2673 + "HT",
2674 + CE,
2675 + {
2676 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2677 + { 36, 4, 17, BOTH, FALSE}, // 5G, ch 36~48
2678 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2679 + { 149, 4, 30, BOTH, FALSE}, // 5G, ch 149~161
2680 + { 0}, // end
2681 + }
2682 + },
2683 +
2684 + { // Honduras
2685 + "HN",
2686 + CE,
2687 + {
2688 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2689 + { 149, 4, 27, BOTH, FALSE}, // 5G, ch 149~161
2690 + { 0}, // end
2691 + }
2692 + },
2693 +
2694 + { // Hong Kong
2695 + "HK",
2696 + CE,
2697 + {
2698 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2699 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2700 + { 52, 4, 23, IDOR, FALSE}, // 5G, ch 52~64
2701 + { 149, 4, 30, BOTH, FALSE}, // 5G, ch 149~161
2702 + { 0}, // end
2703 + }
2704 + },
2705 +
2706 + { // Hungary
2707 + "HU",
2708 + CE,
2709 + {
2710 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2711 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2712 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2713 + { 0}, // end
2714 + }
2715 + },
2716 +
2717 + { // Iceland
2718 + "IS",
2719 + CE,
2720 + {
2721 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2722 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2723 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2724 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2725 + { 0}, // end
2726 + }
2727 + },
2728 +
2729 + { // India
2730 + "IN",
2731 + CE,
2732 + {
2733 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2734 + { 149, 4, 24, IDOR, FALSE}, // 5G, ch 149~161
2735 + { 0}, // end
2736 + }
2737 + },
2738 +
2739 + { // Indonesia
2740 + "ID",
2741 + CE,
2742 + {
2743 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2744 + { 149, 4, 27, BOTH, FALSE}, // 5G, ch 149~161
2745 + { 0}, // end
2746 + }
2747 + },
2748 +
2749 + { // Ireland
2750 + "IE",
2751 + CE,
2752 + {
2753 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2754 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2755 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2756 + { 100, 11, 30, ODOR, TRUE}, // 5G, ch 100~140
2757 + { 0}, // end
2758 + }
2759 + },
2760 +
2761 + { // Israel
2762 + "IL",
2763 + CE,
2764 + {
2765 + { 1, 3, 20, IDOR, FALSE}, // 2.4 G, ch 1~3
2766 + { 4, 6, 20, BOTH, FALSE}, // 2.4 G, ch 4~9
2767 + { 10, 4, 20, IDOR, FALSE}, // 2.4 G, ch 10~13
2768 + { 0}, // end
2769 + }
2770 + },
2771 +
2772 + { // Italy
2773 + "IT",
2774 + CE,
2775 + {
2776 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2777 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2778 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2779 + { 100, 11, 30, ODOR, TRUE}, // 5G, ch 100~140
2780 + { 0}, // end
2781 + }
2782 + },
2783 +
2784 + { // Japan
2785 + "JP",
2786 + JAP,
2787 + {
2788 + { 1, 14, 20, BOTH, FALSE}, // 2.4 G, ch 1~14
2789 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2790 + { 0}, // end
2791 + }
2792 + },
2793 +
2794 + { // Jordan
2795 + "JO",
2796 + CE,
2797 + {
2798 + { 1, 13, 20, IDOR, FALSE}, // 2.4 G, ch 1~13
2799 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2800 + { 149, 4, 23, IDOR, FALSE}, // 5G, ch 149~161
2801 + { 0}, // end
2802 + }
2803 + },
2804 +
2805 + { // Latvia
2806 + "LV",
2807 + CE,
2808 + {
2809 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2810 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2811 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2812 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2813 + { 0}, // end
2814 + }
2815 + },
2816 +
2817 + { // Liechtenstein
2818 + "LI",
2819 + CE,
2820 + {
2821 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2822 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2823 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2824 + { 0}, // end
2825 + }
2826 + },
2827 +
2828 + { // Lithuania
2829 + "LT",
2830 + CE,
2831 + {
2832 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2833 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2834 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2835 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2836 + { 0}, // end
2837 + }
2838 + },
2839 +
2840 + { // Luxemburg
2841 + "LU",
2842 + CE,
2843 + {
2844 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2845 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2846 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2847 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2848 + { 0}, // end
2849 + }
2850 + },
2851 +
2852 + { // Malaysia
2853 + "MY",
2854 + CE,
2855 + {
2856 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2857 + { 52, 4, 23, BOTH, FALSE}, // 5G, ch 52~64
2858 + { 149, 5, 20, BOTH, FALSE}, // 5G, ch 149~165
2859 + { 0}, // end
2860 + }
2861 + },
2862 +
2863 + { // Malta
2864 + "MT",
2865 + CE,
2866 + {
2867 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2868 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2869 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2870 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2871 + { 0}, // end
2872 + }
2873 + },
2874 +
2875 + { // Marocco
2876 + "MA",
2877 + CE,
2878 + {
2879 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2880 + { 36, 4, 24, IDOR, FALSE}, // 5G, ch 36~48
2881 + { 0}, // end
2882 + }
2883 + },
2884 +
2885 + { // Mexico
2886 + "MX",
2887 + CE,
2888 + {
2889 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2890 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2891 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2892 + { 149, 5, 30, IDOR, FALSE}, // 5G, ch 149~165
2893 + { 0}, // end
2894 + }
2895 + },
2896 +
2897 + { // Netherlands
2898 + "NL",
2899 + CE,
2900 + {
2901 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2902 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2903 + { 52, 4, 24, IDOR, TRUE}, // 5G, ch 52~64
2904 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2905 + { 0}, // end
2906 + }
2907 + },
2908 +
2909 + { // New Zealand
2910 + "NZ",
2911 + CE,
2912 + {
2913 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2914 + { 36, 4, 24, BOTH, FALSE}, // 5G, ch 36~48
2915 + { 52, 4, 24, BOTH, FALSE}, // 5G, ch 52~64
2916 + { 149, 4, 30, BOTH, FALSE}, // 5G, ch 149~161
2917 + { 0}, // end
2918 + }
2919 + },
2920 +
2921 + { // Norway
2922 + "NO",
2923 + CE,
2924 + {
2925 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2926 + { 36, 4, 24, IDOR, FALSE}, // 5G, ch 36~48
2927 + { 52, 4, 24, IDOR, TRUE}, // 5G, ch 52~64
2928 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 149~161
2929 + { 0}, // end
2930 + }
2931 + },
2932 +
2933 + { // Peru
2934 + "PE",
2935 + CE,
2936 + {
2937 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2938 + { 149, 4, 27, BOTH, FALSE}, // 5G, ch 149~161
2939 + { 0}, // end
2940 + }
2941 + },
2942 +
2943 + { // Portugal
2944 + "PT",
2945 + CE,
2946 + {
2947 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2948 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2949 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2950 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2951 + { 0}, // end
2952 + }
2953 + },
2954 +
2955 + { // Poland
2956 + "PL",
2957 + CE,
2958 + {
2959 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2960 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2961 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2962 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2963 + { 0}, // end
2964 + }
2965 + },
2966 +
2967 + { // Romania
2968 + "RO",
2969 + CE,
2970 + {
2971 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2972 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
2973 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
2974 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
2975 + { 0}, // end
2976 + }
2977 + },
2978 +
2979 + { // Russia
2980 + "RU",
2981 + CE,
2982 + {
2983 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2984 + { 149, 4, 20, IDOR, FALSE}, // 5G, ch 149~161
2985 + { 0}, // end
2986 + }
2987 + },
2988 +
2989 + { // Saudi Arabia
2990 + "SA",
2991 + CE,
2992 + {
2993 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
2994 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
2995 + { 52, 4, 23, BOTH, FALSE}, // 5G, ch 52~64
2996 + { 149, 4, 23, BOTH, FALSE}, // 5G, ch 149~161
2997 + { 0}, // end
2998 + }
2999 + },
3000 +
3001 + { // Serbia_and_Montenegro
3002 + "CS",
3003 + CE,
3004 + {
3005 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3006 + { 0}, // end
3007 + }
3008 + },
3009 +
3010 + { // Singapore
3011 + "SG",
3012 + CE,
3013 + {
3014 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3015 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
3016 + { 52, 4, 23, BOTH, FALSE}, // 5G, ch 52~64
3017 + { 149, 4, 20, BOTH, FALSE}, // 5G, ch 149~161
3018 + { 0}, // end
3019 + }
3020 + },
3021 +
3022 + { // Slovakia
3023 + "SK",
3024 + CE,
3025 + {
3026 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3027 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
3028 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
3029 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
3030 + { 0}, // end
3031 + }
3032 + },
3033 +
3034 + { // Slovenia
3035 + "SI",
3036 + CE,
3037 + {
3038 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3039 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
3040 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
3041 + { 0}, // end
3042 + }
3043 + },
3044 +
3045 + { // South Africa
3046 + "ZA",
3047 + CE,
3048 + {
3049 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3050 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
3051 + { 52, 4, 23, IDOR, FALSE}, // 5G, ch 52~64
3052 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
3053 + { 149, 4, 30, BOTH, FALSE}, // 5G, ch 149~161
3054 + { 0}, // end
3055 + }
3056 + },
3057 +
3058 + { // South Korea
3059 + "KR",
3060 + CE,
3061 + {
3062 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3063 + { 36, 4, 20, BOTH, FALSE}, // 5G, ch 36~48
3064 + { 52, 4, 20, BOTH, FALSE}, // 5G, ch 52~64
3065 + { 100, 8, 20, BOTH, FALSE}, // 5G, ch 100~128
3066 + { 149, 4, 20, BOTH, FALSE}, // 5G, ch 149~161
3067 + { 0}, // end
3068 + }
3069 + },
3070 +
3071 + { // Spain
3072 + "ES",
3073 + CE,
3074 + {
3075 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3076 + { 36, 4, 17, IDOR, FALSE}, // 5G, ch 36~48
3077 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
3078 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
3079 + { 0}, // end
3080 + }
3081 + },
3082 +
3083 + { // Sweden
3084 + "SE",
3085 + CE,
3086 + {
3087 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3088 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 36~48
3089 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
3090 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
3091 + { 0}, // end
3092 + }
3093 + },
3094 +
3095 + { // Switzerland
3096 + "CH",
3097 + CE,
3098 + {
3099 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~13
3100 + { 36, 4, 23, IDOR, TRUE}, // 5G, ch 36~48
3101 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
3102 + { 0}, // end
3103 + }
3104 + },
3105 +
3106 + { // Taiwan
3107 + "TW",
3108 + CE,
3109 + {
3110 + { 1, 11, 30, BOTH, FALSE}, // 2.4 G, ch 1~11
3111 + { 52, 4, 23, IDOR, FALSE}, // 5G, ch 52~64
3112 + { 0}, // end
3113 + }
3114 + },
3115 +
3116 + { // Turkey
3117 + "TR",
3118 + CE,
3119 + {
3120 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~11
3121 + { 36, 4, 23, BOTH, FALSE}, // 5G, ch 36~48
3122 + { 52, 4, 23, BOTH, FALSE}, // 5G, ch 52~64
3123 + { 0}, // end
3124 + }
3125 + },
3126 +
3127 + { // UK
3128 + "GB",
3129 + CE,
3130 + {
3131 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~11
3132 + { 36, 4, 23, IDOR, FALSE}, // 5G, ch 52~64
3133 + { 52, 4, 23, IDOR, TRUE}, // 5G, ch 52~64
3134 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
3135 + { 0}, // end
3136 + }
3137 + },
3138 +
3139 + { // Ukraine
3140 + "UA",
3141 + CE,
3142 + {
3143 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~11
3144 + { 0}, // end
3145 + }
3146 + },
3147 +
3148 + { // United_Arab_Emirates
3149 + "AE",
3150 + CE,
3151 + {
3152 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~11
3153 + { 0}, // end
3154 + }
3155 + },
3156 +
3157 + { // United_States
3158 + "US",
3159 + CE,
3160 + {
3161 + { 1, 11, 30, BOTH, FALSE}, // 2.4 G, ch 1~11
3162 + { 36, 4, 17, IDOR, FALSE}, // 5G, ch 52~64
3163 + { 52, 4, 24, BOTH, TRUE}, // 5G, ch 52~64
3164 + { 100, 11, 30, BOTH, TRUE}, // 5G, ch 100~140
3165 + { 149, 5, 30, BOTH, FALSE}, // 5G, ch 149~165
3166 + { 0}, // end
3167 + }
3168 + },
3169 +
3170 + { // Venezuela
3171 + "VE",
3172 + CE,
3173 + {
3174 + { 1, 13, 20, BOTH, FALSE}, // 2.4 G, ch 1~11
3175 + { 149, 4, 27, BOTH, FALSE}, // 5G, ch 149~161
3176 + { 0}, // end
3177 + }
3178 + },
3179 +
3180 + { // Default
3181 + "",
3182 + CE,
3183 + {
3184 + { 1, 11, 20, BOTH, FALSE}, // 2.4 G, ch 1~11
3185 + { 36, 4, 20, BOTH, FALSE}, // 5G, ch 52~64
3186 + { 52, 4, 20, BOTH, FALSE}, // 5G, ch 52~64
3187 + { 100, 11, 20, BOTH, FALSE}, // 5G, ch 100~140
3188 + { 149, 5, 20, BOTH, FALSE}, // 5G, ch 149~165
3189 + { 0}, // end
3190 + }
3191 + },
3192 +};
3193 +
3194 +static inline PCH_REGION GetChRegion(
3195 + IN PUCHAR CntryCode)
3196 +{
3197 + INT loop = 0;
3198 + PCH_REGION pChRegion = NULL;
3199 +
3200 + while (strcmp(ChRegion[loop].CountReg, "") != 0)
3201 + {
3202 + if (strncmp(ChRegion[loop].CountReg, CntryCode, 2) == 0)
3203 + {
3204 + pChRegion = &ChRegion[loop];
3205 + break;
3206 + }
3207 + loop++;
3208 + }
3209 +
3210 + if (pChRegion == NULL)
3211 + pChRegion = &ChRegion[loop];
3212 + return pChRegion;
3213 +}
3214 +
3215 +static inline VOID ChBandCheck(
3216 + IN UCHAR PhyMode,
3217 + OUT PUCHAR pChType)
3218 +{
3219 + switch(PhyMode)
3220 + {
3221 + case PHY_11A:
3222 +#ifdef DOT11_N_SUPPORT
3223 + case PHY_11AN_MIXED:
3224 +#endif // DOT11_N_SUPPORT //
3225 + *pChType = BAND_5G;
3226 + break;
3227 + case PHY_11ABG_MIXED:
3228 +#ifdef DOT11_N_SUPPORT
3229 + case PHY_11AGN_MIXED:
3230 + case PHY_11ABGN_MIXED:
3231 +#endif // DOT11_N_SUPPORT //
3232 + *pChType = BAND_BOTH;
3233 + break;
3234 +
3235 + default:
3236 + *pChType = BAND_24G;
3237 + break;
3238 + }
3239 +}
3240 +
3241 +static inline UCHAR FillChList(
3242 + IN PRTMP_ADAPTER pAd,
3243 + IN PCH_DESP pChDesp,
3244 + IN UCHAR Offset,
3245 + IN UCHAR increment)
3246 +{
3247 + INT i, j, l;
3248 + UCHAR channel;
3249 +
3250 + j = Offset;
3251 + for (i = 0; i < pChDesp->NumOfCh; i++)
3252 + {
3253 + channel = pChDesp->FirstChannel + i * increment;
3254 + for (l=0; l<MAX_NUM_OF_CHANNELS; l++)
3255 + {
3256 + if (channel == pAd->TxPower[l].Channel)
3257 + {
3258 + pAd->ChannelList[j].Power = pAd->TxPower[l].Power;
3259 + pAd->ChannelList[j].Power2 = pAd->TxPower[l].Power2;
3260 + break;
3261 + }
3262 + }
3263 + if (l == MAX_NUM_OF_CHANNELS)
3264 + continue;
3265 +
3266 + pAd->ChannelList[j].Channel = pChDesp->FirstChannel + i * increment;
3267 + pAd->ChannelList[j].MaxTxPwr = pChDesp->MaxTxPwr;
3268 + pAd->ChannelList[j].DfsReq = pChDesp->DfsReq;
3269 + j++;
3270 + }
3271 + pAd->ChannelListNum = j;
3272 +
3273 + return j;
3274 +}
3275 +
3276 +static inline VOID CreateChList(
3277 + IN PRTMP_ADAPTER pAd,
3278 + IN PCH_REGION pChRegion,
3279 + IN UCHAR Geography)
3280 +{
3281 + INT i;
3282 + UCHAR offset = 0;
3283 + PCH_DESP pChDesp;
3284 + UCHAR ChType;
3285 + UCHAR increment;
3286 +
3287 + if (pChRegion == NULL)
3288 + return;
3289 +
3290 + ChBandCheck(pAd->CommonCfg.PhyMode, &ChType);
3291 +
3292 + for (i=0; i<10; i++)
3293 + {
3294 + pChDesp = &pChRegion->ChDesp[i];
3295 + if (pChDesp->FirstChannel == 0)
3296 + break;
3297 +
3298 + if (ChType == BAND_5G)
3299 + {
3300 + if (pChDesp->FirstChannel <= 14)
3301 + continue;
3302 + }
3303 + else if (ChType == BAND_24G)
3304 + {
3305 + if (pChDesp->FirstChannel > 14)
3306 + continue;
3307 + }
3308 +
3309 + if ((pChDesp->Geography == BOTH)
3310 + || (pChDesp->Geography == Geography))
3311 + {
3312 + if (pChDesp->FirstChannel > 14)
3313 + increment = 4;
3314 + else
3315 + increment = 1;
3316 + offset = FillChList(pAd, pChDesp, offset, increment);
3317 + }
3318 + }
3319 +}
3320 +
3321 +static inline VOID BuildChannelListEx(
3322 + IN PRTMP_ADAPTER pAd)
3323 +{
3324 + PCH_REGION pChReg;
3325 +
3326 + pChReg = GetChRegion(pAd->CommonCfg.CountryCode);
3327 + CreateChList(pAd, pChReg, pAd->CommonCfg.Geography);
3328 +}
3329 +
3330 +static inline VOID BuildBeaconChList(
3331 + IN PRTMP_ADAPTER pAd,
3332 + OUT PUCHAR pBuf,
3333 + OUT PULONG pBufLen)
3334 +{
3335 + INT i;
3336 + ULONG TmpLen;
3337 + PCH_REGION pChRegion;
3338 + PCH_DESP pChDesp;
3339 + UCHAR ChType;
3340 +
3341 + pChRegion = GetChRegion(pAd->CommonCfg.CountryCode);
3342 +
3343 + if (pChRegion == NULL)
3344 + return;
3345 +
3346 + ChBandCheck(pAd->CommonCfg.PhyMode, &ChType);
3347 + *pBufLen = 0;
3348 +
3349 + for (i=0; i<10; i++)
3350 + {
3351 + pChDesp = &pChRegion->ChDesp[i];
3352 + if (pChDesp->FirstChannel == 0)
3353 + break;
3354 +
3355 + if (ChType == BAND_5G)
3356 + {
3357 + if (pChDesp->FirstChannel <= 14)
3358 + continue;
3359 + }
3360 + else if (ChType == BAND_24G)
3361 + {
3362 + if (pChDesp->FirstChannel > 14)
3363 + continue;
3364 + }
3365 +
3366 + if ((pChDesp->Geography == BOTH)
3367 + || (pChDesp->Geography == pAd->CommonCfg.Geography))
3368 + {
3369 + MakeOutgoingFrame(pBuf + *pBufLen, &TmpLen,
3370 + 1, &pChDesp->FirstChannel,
3371 + 1, &pChDesp->NumOfCh,
3372 + 1, &pChDesp->MaxTxPwr,
3373 + END_OF_ARGS);
3374 + *pBufLen += TmpLen;
3375 + }
3376 + }
3377 +}
3378 +
3379 +
3380 +#ifdef DOT11_N_SUPPORT
3381 +static inline BOOLEAN IsValidChannel(
3382 + IN PRTMP_ADAPTER pAd,
3383 + IN UCHAR channel)
3384 +
3385 +{
3386 + INT i;
3387 +
3388 + for (i = 0; i < pAd->ChannelListNum; i++)
3389 + {
3390 + if (pAd->ChannelList[i].Channel == channel)
3391 + break;
3392 + }
3393 +
3394 + if (i == pAd->ChannelListNum)
3395 + return FALSE;
3396 + else
3397 + return TRUE;
3398 +}
3399 +
3400 +
3401 +static inline UCHAR GetExtCh(
3402 + IN UCHAR Channel,
3403 + IN UCHAR Direction)
3404 +{
3405 + CHAR ExtCh;
3406 +
3407 + if (Direction == EXTCHA_ABOVE)
3408 + ExtCh = Channel + 4;
3409 + else
3410 + ExtCh = (Channel - 4) > 0 ? (Channel - 4) : 0;
3411 +
3412 + return ExtCh;
3413 +}
3414 +
3415 +
3416 +static inline VOID N_ChannelCheck(
3417 + IN PRTMP_ADAPTER pAd)
3418 +{
3419 + //UCHAR ChannelNum = pAd->ChannelListNum;
3420 + UCHAR Channel = pAd->CommonCfg.Channel;
3421 +
3422 + if ((pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED) && (pAd->CommonCfg.RegTransmitSetting.field.BW == BW_40))
3423 + {
3424 + if (Channel > 14)
3425 + {
3426 + if ((Channel == 36) || (Channel == 44) || (Channel == 52) || (Channel == 60) || (Channel == 100) || (Channel == 108) ||
3427 + (Channel == 116) || (Channel == 124) || (Channel == 132) || (Channel == 149) || (Channel == 157))
3428 + {
3429 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_ABOVE;
3430 + }
3431 + else if ((Channel == 40) || (Channel == 48) || (Channel == 56) || (Channel == 64) || (Channel == 104) || (Channel == 112) ||
3432 + (Channel == 120) || (Channel == 128) || (Channel == 136) || (Channel == 153) || (Channel == 161))
3433 + {
3434 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_BELOW;
3435 + }
3436 + else
3437 + {
3438 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
3439 + }
3440 + }
3441 + else
3442 + {
3443 + do
3444 + {
3445 + UCHAR ExtCh;
3446 + UCHAR Dir = pAd->CommonCfg.RegTransmitSetting.field.EXTCHA;
3447 + ExtCh = GetExtCh(Channel, Dir);
3448 + if (IsValidChannel(pAd, ExtCh))
3449 + break;
3450 +
3451 + Dir = (Dir == EXTCHA_ABOVE) ? EXTCHA_BELOW : EXTCHA_ABOVE;
3452 + ExtCh = GetExtCh(Channel, Dir);
3453 + if (IsValidChannel(pAd, ExtCh))
3454 + {
3455 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = Dir;
3456 + break;
3457 + }
3458 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
3459 + } while(FALSE);
3460 +
3461 + if (Channel == 14)
3462 + {
3463 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
3464 + //pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_NONE; // We didn't set the ExtCh as NONE due to it'll set in RTMPSetHT()
3465 + }
3466 +#if 0
3467 + switch (pAd->CommonCfg.CountryRegion & 0x7f)
3468 + {
3469 + case REGION_0_BG_BAND: // 1 -11
3470 + case REGION_1_BG_BAND: // 1 - 13
3471 + case REGION_5_BG_BAND: // 1 - 14
3472 + if (Channel <= 4)
3473 + {
3474 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_ABOVE;
3475 + }
3476 + else if (Channel >= 8)
3477 + {
3478 + if ((ChannelNum - Channel) < 4)
3479 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_BELOW;
3480 + }
3481 + break;
3482 +
3483 + case REGION_2_BG_BAND: // 10 - 11
3484 + case REGION_3_BG_BAND: // 10 - 13
3485 + case REGION_4_BG_BAND: // 14
3486 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
3487 + break;
3488 +
3489 + case REGION_6_BG_BAND: // 3 - 9
3490 + if (Channel <= 5)
3491 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_ABOVE;
3492 + else if (Channel == 6)
3493 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
3494 + else if (Channel >= 7)
3495 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_BELOW;
3496 + break;
3497 +
3498 + case REGION_7_BG_BAND: // 5 - 13
3499 + if (Channel <= 8)
3500 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_ABOVE;
3501 + else if (Channel >= 10)
3502 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_BELOW;
3503 + break;
3504 +
3505 + default: // Error. should never happen
3506 + break;
3507 + }
3508 +#endif
3509 + }
3510 + }
3511 +
3512 +
3513 +}
3514 +
3515 +
3516 +static inline VOID N_SetCenCh(
3517 + IN PRTMP_ADAPTER pAd)
3518 +{
3519 + if (pAd->CommonCfg.RegTransmitSetting.field.BW == BW_40)
3520 + {
3521 + if (pAd->CommonCfg.RegTransmitSetting.field.EXTCHA == EXTCHA_ABOVE)
3522 + {
3523 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel + 2;
3524 + }
3525 + else
3526 + {
3527 + if (pAd->CommonCfg.Channel == 14)
3528 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel - 1;
3529 + else
3530 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel - 2;
3531 + }
3532 + }
3533 + else
3534 + {
3535 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel;
3536 + }
3537 +}
3538 +#endif // DOT11_N_SUPPORT //
3539 +
3540 +
3541 +static inline UINT8 GetCuntryMaxTxPwr(
3542 + IN PRTMP_ADAPTER pAd,
3543 + IN UINT8 channel)
3544 +{
3545 + int i;
3546 + for (i = 0; i < pAd->ChannelListNum; i++)
3547 + {
3548 + if (pAd->ChannelList[i].Channel == channel)
3549 + break;
3550 + }
3551 +
3552 + if (i == pAd->ChannelListNum)
3553 + return 0xff;
3554 + else
3555 + return pAd->ChannelList[i].MaxTxPwr;
3556 +}
3557 +#endif // __CHLIST_H__
3558 +
3559 --- /dev/null
3560 +++ b/drivers/staging/rt2860/common/2860_rtmp_init.c
3561 @@ -0,0 +1,922 @@
3562 +/*
3563 + *************************************************************************
3564 + * Ralink Tech Inc.
3565 + * 5F., No.36, Taiyuan St., Jhubei City,
3566 + * Hsinchu County 302,
3567 + * Taiwan, R.O.C.
3568 + *
3569 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
3570 + *
3571 + * This program is free software; you can redistribute it and/or modify *
3572 + * it under the terms of the GNU General Public License as published by *
3573 + * the Free Software Foundation; either version 2 of the License, or *
3574 + * (at your option) any later version. *
3575 + * *
3576 + * This program is distributed in the hope that it will be useful, *
3577 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
3578 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
3579 + * GNU General Public License for more details. *
3580 + * *
3581 + * You should have received a copy of the GNU General Public License *
3582 + * along with this program; if not, write to the *
3583 + * Free Software Foundation, Inc., *
3584 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
3585 + * *
3586 + *************************************************************************
3587 +
3588 + Module Name:
3589 + 2860_rtmp_init.c
3590 +
3591 + Abstract:
3592 + Miniport generic portion header file
3593 +
3594 + Revision History:
3595 + Who When What
3596 + -------- ---------- ----------------------------------------------
3597 + Paul Lin 2002-08-01 created
3598 + John Chang 2004-08-20 RT2561/2661 use scatter-gather scheme
3599 + Jan Lee 2006-09-15 RT2860. Change for 802.11n , EEPROM, Led, BA, HT.
3600 +*/
3601 +#include "../rt_config.h"
3602 +
3603 +
3604 +
3605 +
3606 +/*
3607 + ========================================================================
3608 +
3609 + Routine Description:
3610 + Allocate DMA memory blocks for send, receive
3611 +
3612 + Arguments:
3613 + Adapter Pointer to our adapter
3614 +
3615 + Return Value:
3616 + NDIS_STATUS_SUCCESS
3617 + NDIS_STATUS_FAILURE
3618 + NDIS_STATUS_RESOURCES
3619 +
3620 + IRQL = PASSIVE_LEVEL
3621 +
3622 + Note:
3623 +
3624 + ========================================================================
3625 +*/
3626 +NDIS_STATUS RTMPAllocTxRxRingMemory(
3627 + IN PRTMP_ADAPTER pAd)
3628 +{
3629 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
3630 + ULONG RingBasePaHigh;
3631 + ULONG RingBasePaLow;
3632 + PVOID RingBaseVa;
3633 + INT index, num;
3634 + PTXD_STRUC pTxD;
3635 + PRXD_STRUC pRxD;
3636 + ULONG ErrorValue = 0;
3637 + PRTMP_TX_RING pTxRing;
3638 + PRTMP_DMABUF pDmaBuf;
3639 + PNDIS_PACKET pPacket;
3640 +
3641 + DBGPRINT(RT_DEBUG_TRACE, ("--> RTMPAllocTxRxRingMemory\n"));
3642 + do
3643 + {
3644 + //
3645 + // Allocate all ring descriptors, include TxD, RxD, MgmtD.
3646 + // Although each size is different, to prevent cacheline and alignment
3647 + // issue, I intentional set them all to 64 bytes.
3648 + //
3649 + for (num=0; num<NUM_OF_TX_RING; num++)
3650 + {
3651 + ULONG BufBasePaHigh;
3652 + ULONG BufBasePaLow;
3653 + PVOID BufBaseVa;
3654 +
3655 + //
3656 + // Allocate Tx ring descriptor's memory (5 TX rings = 4 ACs + 1 HCCA)
3657 + //
3658 + pAd->TxDescRing[num].AllocSize = TX_RING_SIZE * TXD_SIZE;
3659 + RTMP_AllocateTxDescMemory(
3660 + pAd,
3661 + num,
3662 + pAd->TxDescRing[num].AllocSize,
3663 + FALSE,
3664 + &pAd->TxDescRing[num].AllocVa,
3665 + &pAd->TxDescRing[num].AllocPa);
3666 +
3667 + if (pAd->TxDescRing[num].AllocVa == NULL)
3668 + {
3669 + ErrorValue = ERRLOG_OUT_OF_SHARED_MEMORY;
3670 + DBGPRINT_ERR(("Failed to allocate a big buffer\n"));
3671 + Status = NDIS_STATUS_RESOURCES;
3672 + break;
3673 + }
3674 +
3675 + // Zero init this memory block
3676 + NdisZeroMemory(pAd->TxDescRing[num].AllocVa, pAd->TxDescRing[num].AllocSize);
3677 +
3678 + // Save PA & VA for further operation
3679 + RingBasePaHigh = RTMP_GetPhysicalAddressHigh(pAd->TxDescRing[num].AllocPa);
3680 + RingBasePaLow = RTMP_GetPhysicalAddressLow (pAd->TxDescRing[num].AllocPa);
3681 + RingBaseVa = pAd->TxDescRing[num].AllocVa;
3682 +
3683 + //
3684 + // Allocate all 1st TXBuf's memory for this TxRing
3685 + //
3686 + pAd->TxBufSpace[num].AllocSize = TX_RING_SIZE * TX_DMA_1ST_BUFFER_SIZE;
3687 + RTMP_AllocateFirstTxBuffer(
3688 + pAd,
3689 + num,
3690 + pAd->TxBufSpace[num].AllocSize,
3691 + FALSE,
3692 + &pAd->TxBufSpace[num].AllocVa,
3693 + &pAd->TxBufSpace[num].AllocPa);
3694 +
3695 + if (pAd->TxBufSpace[num].AllocVa == NULL)
3696 + {
3697 + ErrorValue = ERRLOG_OUT_OF_SHARED_MEMORY;
3698 + DBGPRINT_ERR(("Failed to allocate a big buffer\n"));
3699 + Status = NDIS_STATUS_RESOURCES;
3700 + break;
3701 + }
3702 +
3703 + // Zero init this memory block
3704 + NdisZeroMemory(pAd->TxBufSpace[num].AllocVa, pAd->TxBufSpace[num].AllocSize);
3705 +
3706 + // Save PA & VA for further operation
3707 + BufBasePaHigh = RTMP_GetPhysicalAddressHigh(pAd->TxBufSpace[num].AllocPa);
3708 + BufBasePaLow = RTMP_GetPhysicalAddressLow (pAd->TxBufSpace[num].AllocPa);
3709 + BufBaseVa = pAd->TxBufSpace[num].AllocVa;
3710 +
3711 + //
3712 + // Initialize Tx Ring Descriptor and associated buffer memory
3713 + //
3714 + pTxRing = &pAd->TxRing[num];
3715 + for (index = 0; index < TX_RING_SIZE; index++)
3716 + {
3717 + pTxRing->Cell[index].pNdisPacket = NULL;
3718 + pTxRing->Cell[index].pNextNdisPacket = NULL;
3719 + // Init Tx Ring Size, Va, Pa variables
3720 + pTxRing->Cell[index].AllocSize = TXD_SIZE;
3721 + pTxRing->Cell[index].AllocVa = RingBaseVa;
3722 + RTMP_SetPhysicalAddressHigh(pTxRing->Cell[index].AllocPa, RingBasePaHigh);
3723 + RTMP_SetPhysicalAddressLow (pTxRing->Cell[index].AllocPa, RingBasePaLow);
3724 +
3725 + // Setup Tx Buffer size & address. only 802.11 header will store in this space
3726 + pDmaBuf = &pTxRing->Cell[index].DmaBuf;
3727 + pDmaBuf->AllocSize = TX_DMA_1ST_BUFFER_SIZE;
3728 + pDmaBuf->AllocVa = BufBaseVa;
3729 + RTMP_SetPhysicalAddressHigh(pDmaBuf->AllocPa, BufBasePaHigh);
3730 + RTMP_SetPhysicalAddressLow(pDmaBuf->AllocPa, BufBasePaLow);
3731 +
3732 + // link the pre-allocated TxBuf to TXD
3733 + pTxD = (PTXD_STRUC) pTxRing->Cell[index].AllocVa;
3734 + pTxD->SDPtr0 = BufBasePaLow;
3735 + // advance to next ring descriptor address
3736 + pTxD->DMADONE = 1;
3737 +#ifdef RT_BIG_ENDIAN
3738 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
3739 +#endif
3740 + RingBasePaLow += TXD_SIZE;
3741 + RingBaseVa = (PUCHAR) RingBaseVa + TXD_SIZE;
3742 +
3743 + // advance to next TxBuf address
3744 + BufBasePaLow += TX_DMA_1ST_BUFFER_SIZE;
3745 + BufBaseVa = (PUCHAR) BufBaseVa + TX_DMA_1ST_BUFFER_SIZE;
3746 + }
3747 + DBGPRINT(RT_DEBUG_TRACE, ("TxRing[%d]: total %d entry allocated\n", num, index));
3748 + }
3749 + if (Status == NDIS_STATUS_RESOURCES)
3750 + break;
3751 +
3752 + //
3753 + // Allocate MGMT ring descriptor's memory except Tx ring which allocated eariler
3754 + //
3755 + pAd->MgmtDescRing.AllocSize = MGMT_RING_SIZE * TXD_SIZE;
3756 + RTMP_AllocateMgmtDescMemory(
3757 + pAd,
3758 + pAd->MgmtDescRing.AllocSize,
3759 + FALSE,
3760 + &pAd->MgmtDescRing.AllocVa,
3761 + &pAd->MgmtDescRing.AllocPa);
3762 +
3763 + if (pAd->MgmtDescRing.AllocVa == NULL)
3764 + {
3765 + ErrorValue = ERRLOG_OUT_OF_SHARED_MEMORY;
3766 + DBGPRINT_ERR(("Failed to allocate a big buffer\n"));
3767 + Status = NDIS_STATUS_RESOURCES;
3768 + break;
3769 + }
3770 +
3771 + // Zero init this memory block
3772 + NdisZeroMemory(pAd->MgmtDescRing.AllocVa, pAd->MgmtDescRing.AllocSize);
3773 +
3774 + // Save PA & VA for further operation
3775 + RingBasePaHigh = RTMP_GetPhysicalAddressHigh(pAd->MgmtDescRing.AllocPa);
3776 + RingBasePaLow = RTMP_GetPhysicalAddressLow (pAd->MgmtDescRing.AllocPa);
3777 + RingBaseVa = pAd->MgmtDescRing.AllocVa;
3778 +
3779 + //
3780 + // Initialize MGMT Ring and associated buffer memory
3781 + //
3782 + for (index = 0; index < MGMT_RING_SIZE; index++)
3783 + {
3784 + pAd->MgmtRing.Cell[index].pNdisPacket = NULL;
3785 + pAd->MgmtRing.Cell[index].pNextNdisPacket = NULL;
3786 + // Init MGMT Ring Size, Va, Pa variables
3787 + pAd->MgmtRing.Cell[index].AllocSize = TXD_SIZE;
3788 + pAd->MgmtRing.Cell[index].AllocVa = RingBaseVa;
3789 + RTMP_SetPhysicalAddressHigh(pAd->MgmtRing.Cell[index].AllocPa, RingBasePaHigh);
3790 + RTMP_SetPhysicalAddressLow (pAd->MgmtRing.Cell[index].AllocPa, RingBasePaLow);
3791 +
3792 + // Offset to next ring descriptor address
3793 + RingBasePaLow += TXD_SIZE;
3794 + RingBaseVa = (PUCHAR) RingBaseVa + TXD_SIZE;
3795 +
3796 + // link the pre-allocated TxBuf to TXD
3797 + pTxD = (PTXD_STRUC) pAd->MgmtRing.Cell[index].AllocVa;
3798 + pTxD->DMADONE = 1;
3799 +
3800 +#ifdef RT_BIG_ENDIAN
3801 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
3802 +#endif
3803 + // no pre-allocated buffer required in MgmtRing for scatter-gather case
3804 + }
3805 + DBGPRINT(RT_DEBUG_TRACE, ("MGMT Ring: total %d entry allocated\n", index));
3806 +
3807 + //
3808 + // Allocate RX ring descriptor's memory except Tx ring which allocated eariler
3809 + //
3810 + pAd->RxDescRing.AllocSize = RX_RING_SIZE * RXD_SIZE;
3811 + RTMP_AllocateRxDescMemory(
3812 + pAd,
3813 + pAd->RxDescRing.AllocSize,
3814 + FALSE,
3815 + &pAd->RxDescRing.AllocVa,
3816 + &pAd->RxDescRing.AllocPa);
3817 +
3818 + if (pAd->RxDescRing.AllocVa == NULL)
3819 + {
3820 + ErrorValue = ERRLOG_OUT_OF_SHARED_MEMORY;
3821 + DBGPRINT_ERR(("Failed to allocate a big buffer\n"));
3822 + Status = NDIS_STATUS_RESOURCES;
3823 + break;
3824 + }
3825 +
3826 + // Zero init this memory block
3827 + NdisZeroMemory(pAd->RxDescRing.AllocVa, pAd->RxDescRing.AllocSize);
3828 +
3829 +
3830 + printk("RX DESC %p size = %ld\n", pAd->RxDescRing.AllocVa,
3831 + pAd->RxDescRing.AllocSize);
3832 +
3833 + // Save PA & VA for further operation
3834 + RingBasePaHigh = RTMP_GetPhysicalAddressHigh(pAd->RxDescRing.AllocPa);
3835 + RingBasePaLow = RTMP_GetPhysicalAddressLow (pAd->RxDescRing.AllocPa);
3836 + RingBaseVa = pAd->RxDescRing.AllocVa;
3837 +
3838 + //
3839 + // Initialize Rx Ring and associated buffer memory
3840 + //
3841 + for (index = 0; index < RX_RING_SIZE; index++)
3842 + {
3843 + // Init RX Ring Size, Va, Pa variables
3844 + pAd->RxRing.Cell[index].AllocSize = RXD_SIZE;
3845 + pAd->RxRing.Cell[index].AllocVa = RingBaseVa;
3846 + RTMP_SetPhysicalAddressHigh(pAd->RxRing.Cell[index].AllocPa, RingBasePaHigh);
3847 + RTMP_SetPhysicalAddressLow (pAd->RxRing.Cell[index].AllocPa, RingBasePaLow);
3848 +
3849 + // Offset to next ring descriptor address
3850 + RingBasePaLow += RXD_SIZE;
3851 + RingBaseVa = (PUCHAR) RingBaseVa + RXD_SIZE;
3852 +
3853 + // Setup Rx associated Buffer size & allocate share memory
3854 + pDmaBuf = &pAd->RxRing.Cell[index].DmaBuf;
3855 + pDmaBuf->AllocSize = RX_BUFFER_AGGRESIZE;
3856 + pPacket = RTMP_AllocateRxPacketBuffer(
3857 + pAd,
3858 + pDmaBuf->AllocSize,
3859 + FALSE,
3860 + &pDmaBuf->AllocVa,
3861 + &pDmaBuf->AllocPa);
3862 +
3863 + /* keep allocated rx packet */
3864 + pAd->RxRing.Cell[index].pNdisPacket = pPacket;
3865 +
3866 + // Error handling
3867 + if (pDmaBuf->AllocVa == NULL)
3868 + {
3869 + ErrorValue = ERRLOG_OUT_OF_SHARED_MEMORY;
3870 + DBGPRINT_ERR(("Failed to allocate RxRing's 1st buffer\n"));
3871 + Status = NDIS_STATUS_RESOURCES;
3872 + break;
3873 + }
3874 +
3875 + // Zero init this memory block
3876 + NdisZeroMemory(pDmaBuf->AllocVa, pDmaBuf->AllocSize);
3877 +
3878 + // Write RxD buffer address & allocated buffer length
3879 + pRxD = (PRXD_STRUC) pAd->RxRing.Cell[index].AllocVa;
3880 + pRxD->SDP0 = RTMP_GetPhysicalAddressLow(pDmaBuf->AllocPa);
3881 + pRxD->DDONE = 0;
3882 +
3883 +#ifdef RT_BIG_ENDIAN
3884 + RTMPDescriptorEndianChange((PUCHAR)pRxD, TYPE_RXD);
3885 +#endif
3886 + }
3887 +
3888 + DBGPRINT(RT_DEBUG_TRACE, ("Rx Ring: total %d entry allocated\n", index));
3889 +
3890 + } while (FALSE);
3891 +
3892 +
3893 + NdisZeroMemory(&pAd->FragFrame, sizeof(FRAGMENT_FRAME));
3894 + pAd->FragFrame.pFragPacket = RTMP_AllocateFragPacketBuffer(pAd, RX_BUFFER_NORMSIZE);
3895 +
3896 + if (pAd->FragFrame.pFragPacket == NULL)
3897 + {
3898 + Status = NDIS_STATUS_RESOURCES;
3899 + }
3900 +
3901 + if (Status != NDIS_STATUS_SUCCESS)
3902 + {
3903 + // Log error inforamtion
3904 + NdisWriteErrorLogEntry(
3905 + pAd->AdapterHandle,
3906 + NDIS_ERROR_CODE_OUT_OF_RESOURCES,
3907 + 1,
3908 + ErrorValue);
3909 + }
3910 +
3911 + DBGPRINT_S(Status, ("<-- RTMPAllocTxRxRingMemory, Status=%x\n", Status));
3912 + return Status;
3913 +}
3914 +
3915 +
3916 +/*
3917 + ========================================================================
3918 +
3919 + Routine Description:
3920 + Initialize transmit data structures
3921 +
3922 + Arguments:
3923 + Adapter Pointer to our adapter
3924 +
3925 + Return Value:
3926 + None
3927 +
3928 + IRQL = PASSIVE_LEVEL
3929 +
3930 + Note:
3931 + Initialize all transmit releated private buffer, include those define
3932 + in RTMP_ADAPTER structure and all private data structures.
3933 +
3934 + ========================================================================
3935 +*/
3936 +VOID NICInitTxRxRingAndBacklogQueue(
3937 + IN PRTMP_ADAPTER pAd)
3938 +{
3939 + //WPDMA_GLO_CFG_STRUC GloCfg;
3940 + int i;
3941 +
3942 + DBGPRINT(RT_DEBUG_TRACE, ("<--> NICInitTxRxRingAndBacklogQueue\n"));
3943 +
3944 + // Initialize all transmit related software queues
3945 + InitializeQueueHeader(&pAd->TxSwQueue[QID_AC_BE]);
3946 + InitializeQueueHeader(&pAd->TxSwQueue[QID_AC_BK]);
3947 + InitializeQueueHeader(&pAd->TxSwQueue[QID_AC_VI]);
3948 + InitializeQueueHeader(&pAd->TxSwQueue[QID_AC_VO]);
3949 + InitializeQueueHeader(&pAd->TxSwQueue[QID_HCCA]);
3950 +
3951 + // Init RX Ring index pointer
3952 + pAd->RxRing.RxSwReadIdx = 0;
3953 + pAd->RxRing.RxCpuIdx = RX_RING_SIZE - 1;
3954 +
3955 + // Init TX rings index pointer
3956 + for (i=0; i<NUM_OF_TX_RING; i++)
3957 + {
3958 + pAd->TxRing[i].TxSwFreeIdx = 0;
3959 + pAd->TxRing[i].TxCpuIdx = 0;
3960 + }
3961 +
3962 + // init MGMT ring index pointer
3963 + pAd->MgmtRing.TxSwFreeIdx = 0;
3964 + pAd->MgmtRing.TxCpuIdx = 0;
3965 +
3966 + pAd->PrivateInfo.TxRingFullCnt = 0;
3967 +}
3968 +
3969 +
3970 +/*
3971 + ========================================================================
3972 +
3973 + Routine Description:
3974 + Reset NIC Asics. Call after rest DMA. So reset TX_CTX_IDX to zero.
3975 +
3976 + Arguments:
3977 + Adapter Pointer to our adapter
3978 +
3979 + Return Value:
3980 + None
3981 +
3982 + IRQL = PASSIVE_LEVEL
3983 + IRQL = DISPATCH_LEVEL
3984 +
3985 + Note:
3986 + Reset NIC to initial state AS IS system boot up time.
3987 +
3988 + ========================================================================
3989 +*/
3990 +VOID RTMPRingCleanUp(
3991 + IN PRTMP_ADAPTER pAd,
3992 + IN UCHAR RingType)
3993 +{
3994 + PTXD_STRUC pTxD;
3995 + PRXD_STRUC pRxD;
3996 + PQUEUE_ENTRY pEntry;
3997 + PNDIS_PACKET pPacket;
3998 + int i;
3999 + PRTMP_TX_RING pTxRing;
4000 + unsigned long IrqFlags;
4001 +
4002 + DBGPRINT(RT_DEBUG_TRACE,("RTMPRingCleanUp(RingIdx=%d, Pending-NDIS=%ld)\n", RingType, pAd->RalinkCounters.PendingNdisPacketCount));
4003 + switch (RingType)
4004 + {
4005 + case QID_AC_BK:
4006 + case QID_AC_BE:
4007 + case QID_AC_VI:
4008 + case QID_AC_VO:
4009 + case QID_HCCA:
4010 + RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
4011 + pTxRing = &pAd->TxRing[RingType];
4012 +
4013 + // We have to clean all descriptors in case some error happened with reset
4014 + for (i=0; i<TX_RING_SIZE; i++) // We have to scan all TX ring
4015 + {
4016 + pTxD = (PTXD_STRUC) pTxRing->Cell[i].AllocVa;
4017 +
4018 + pPacket = (PNDIS_PACKET) pTxRing->Cell[i].pNdisPacket;
4019 + // release scatter-and-gather NDIS_PACKET
4020 + if (pPacket)
4021 + {
4022 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
4023 + pTxRing->Cell[i].pNdisPacket = NULL;
4024 + }
4025 +
4026 + pPacket = (PNDIS_PACKET) pTxRing->Cell[i].pNextNdisPacket;
4027 + // release scatter-and-gather NDIS_PACKET
4028 + if (pPacket)
4029 + {
4030 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
4031 + pTxRing->Cell[i].pNextNdisPacket = NULL;
4032 + }
4033 + }
4034 +
4035 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + RingType * 0x10, &pTxRing->TxDmaIdx);
4036 + pTxRing->TxSwFreeIdx = pTxRing->TxDmaIdx;
4037 + pTxRing->TxCpuIdx = pTxRing->TxDmaIdx;
4038 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + RingType * 0x10, pTxRing->TxCpuIdx);
4039 +
4040 + RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
4041 + RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
4042 + while (pAd->TxSwQueue[RingType].Head != NULL)
4043 + {
4044 + pEntry = RemoveHeadQueue(&pAd->TxSwQueue[RingType]);
4045 + pPacket = QUEUE_ENTRY_TO_PACKET(pEntry);
4046 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
4047 + DBGPRINT(RT_DEBUG_TRACE,("Release 1 NDIS packet from s/w backlog queue\n"));
4048 + }
4049 + RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
4050 + break;
4051 +
4052 + case QID_MGMT:
4053 + // We have to clean all descriptors in case some error happened with reset
4054 + NdisAcquireSpinLock(&pAd->MgmtRingLock);
4055 +
4056 + for (i=0; i<MGMT_RING_SIZE; i++)
4057 + {
4058 + pTxD = (PTXD_STRUC) pAd->MgmtRing.Cell[i].AllocVa;
4059 +
4060 + pPacket = (PNDIS_PACKET) pAd->MgmtRing.Cell[i].pNdisPacket;
4061 + // rlease scatter-and-gather NDIS_PACKET
4062 + if (pPacket)
4063 + {
4064 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
4065 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
4066 + }
4067 + pAd->MgmtRing.Cell[i].pNdisPacket = NULL;
4068 +
4069 + pPacket = (PNDIS_PACKET) pAd->MgmtRing.Cell[i].pNextNdisPacket;
4070 + // release scatter-and-gather NDIS_PACKET
4071 + if (pPacket)
4072 + {
4073 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
4074 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
4075 + }
4076 + pAd->MgmtRing.Cell[i].pNextNdisPacket = NULL;
4077 +
4078 + }
4079 +
4080 + RTMP_IO_READ32(pAd, TX_MGMTDTX_IDX, &pAd->MgmtRing.TxDmaIdx);
4081 + pAd->MgmtRing.TxSwFreeIdx = pAd->MgmtRing.TxDmaIdx;
4082 + pAd->MgmtRing.TxCpuIdx = pAd->MgmtRing.TxDmaIdx;
4083 + RTMP_IO_WRITE32(pAd, TX_MGMTCTX_IDX, pAd->MgmtRing.TxCpuIdx);
4084 +
4085 + NdisReleaseSpinLock(&pAd->MgmtRingLock);
4086 + pAd->RalinkCounters.MgmtRingFullCount = 0;
4087 + break;
4088 +
4089 + case QID_RX:
4090 + // We have to clean all descriptors in case some error happened with reset
4091 + NdisAcquireSpinLock(&pAd->RxRingLock);
4092 +
4093 + for (i=0; i<RX_RING_SIZE; i++)
4094 + {
4095 + pRxD = (PRXD_STRUC) pAd->RxRing.Cell[i].AllocVa;
4096 + pRxD->DDONE = 0 ;
4097 + }
4098 +
4099 + RTMP_IO_READ32(pAd, RX_DRX_IDX, &pAd->RxRing.RxDmaIdx);
4100 + pAd->RxRing.RxSwReadIdx = pAd->RxRing.RxDmaIdx;
4101 + pAd->RxRing.RxCpuIdx = ((pAd->RxRing.RxDmaIdx == 0) ? (RX_RING_SIZE-1) : (pAd->RxRing.RxDmaIdx-1));
4102 + RTMP_IO_WRITE32(pAd, RX_CRX_IDX, pAd->RxRing.RxCpuIdx);
4103 +
4104 + NdisReleaseSpinLock(&pAd->RxRingLock);
4105 + break;
4106 +
4107 + default:
4108 + break;
4109 + }
4110 +}
4111 +
4112 +
4113 +NDIS_STATUS AdapterBlockAllocateMemory(
4114 + IN PVOID handle,
4115 + OUT PVOID *ppAd)
4116 +{
4117 + PPCI_DEV pci_dev;
4118 + dma_addr_t *phy_addr;
4119 + POS_COOKIE pObj = (POS_COOKIE) handle;
4120 +
4121 + pci_dev = pObj->pci_dev;
4122 + phy_addr = &pObj->pAd_pa;
4123 +
4124 + *ppAd = (PVOID)vmalloc(sizeof(RTMP_ADAPTER)); //pci_alloc_consistent(pci_dev, sizeof(RTMP_ADAPTER), phy_addr);
4125 +
4126 + if (*ppAd)
4127 + {
4128 + NdisZeroMemory(*ppAd, sizeof(RTMP_ADAPTER));
4129 + ((PRTMP_ADAPTER)*ppAd)->OS_Cookie = handle;
4130 + return (NDIS_STATUS_SUCCESS);
4131 + } else {
4132 + return (NDIS_STATUS_FAILURE);
4133 + }
4134 +}
4135 +
4136 +
4137 +void RTMP_AllocateTxDescMemory(
4138 + IN PRTMP_ADAPTER pAd,
4139 + IN UINT Index,
4140 + IN ULONG Length,
4141 + IN BOOLEAN Cached,
4142 + OUT PVOID *VirtualAddress,
4143 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress)
4144 +{
4145 + POS_COOKIE pObj = (POS_COOKIE)pAd->OS_Cookie;
4146 +
4147 + *VirtualAddress = (PVOID)PCI_ALLOC_CONSISTENT(pObj->pci_dev,sizeof(char)*Length, PhysicalAddress);
4148 +
4149 +}
4150 +
4151 +void RTMP_AllocateMgmtDescMemory(
4152 + IN PRTMP_ADAPTER pAd,
4153 + IN ULONG Length,
4154 + IN BOOLEAN Cached,
4155 + OUT PVOID *VirtualAddress,
4156 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress)
4157 +{
4158 + POS_COOKIE pObj = (POS_COOKIE)pAd->OS_Cookie;
4159 +
4160 + *VirtualAddress = (PVOID)PCI_ALLOC_CONSISTENT(pObj->pci_dev,sizeof(char)*Length, PhysicalAddress);
4161 +
4162 +}
4163 +
4164 +void RTMP_AllocateRxDescMemory(
4165 + IN PRTMP_ADAPTER pAd,
4166 + IN ULONG Length,
4167 + IN BOOLEAN Cached,
4168 + OUT PVOID *VirtualAddress,
4169 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress)
4170 +{
4171 + POS_COOKIE pObj = (POS_COOKIE)pAd->OS_Cookie;
4172 +
4173 + *VirtualAddress = (PVOID)PCI_ALLOC_CONSISTENT(pObj->pci_dev,sizeof(char)*Length, PhysicalAddress);
4174 +
4175 +}
4176 +
4177 +void RTMP_FreeRxDescMemory(
4178 + IN PRTMP_ADAPTER pAd,
4179 + IN ULONG Length,
4180 + IN PVOID VirtualAddress,
4181 + IN NDIS_PHYSICAL_ADDRESS PhysicalAddress)
4182 +{
4183 + POS_COOKIE pObj = (POS_COOKIE)pAd->OS_Cookie;
4184 +
4185 + PCI_FREE_CONSISTENT(pObj->pci_dev, Length, VirtualAddress, PhysicalAddress);
4186 +}
4187 +
4188 +
4189 +void RTMP_AllocateFirstTxBuffer(
4190 + IN PRTMP_ADAPTER pAd,
4191 + IN UINT Index,
4192 + IN ULONG Length,
4193 + IN BOOLEAN Cached,
4194 + OUT PVOID *VirtualAddress,
4195 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress)
4196 +{
4197 + POS_COOKIE pObj = (POS_COOKIE)pAd->OS_Cookie;
4198 +
4199 + *VirtualAddress = (PVOID)PCI_ALLOC_CONSISTENT(pObj->pci_dev,sizeof(char)*Length, PhysicalAddress);
4200 +}
4201 +
4202 +/*
4203 + * FUNCTION: Allocate a common buffer for DMA
4204 + * ARGUMENTS:
4205 + * AdapterHandle: AdapterHandle
4206 + * Length: Number of bytes to allocate
4207 + * Cached: Whether or not the memory can be cached
4208 + * VirtualAddress: Pointer to memory is returned here
4209 + * PhysicalAddress: Physical address corresponding to virtual address
4210 + */
4211 +
4212 +void RTMP_AllocateSharedMemory(
4213 + IN PRTMP_ADAPTER pAd,
4214 + IN ULONG Length,
4215 + IN BOOLEAN Cached,
4216 + OUT PVOID *VirtualAddress,
4217 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress)
4218 +{
4219 + POS_COOKIE pObj = (POS_COOKIE)pAd->OS_Cookie;
4220 +
4221 + *VirtualAddress = (PVOID)PCI_ALLOC_CONSISTENT(pObj->pci_dev,sizeof(char)*Length, PhysicalAddress);
4222 +}
4223 +
4224 +VOID RTMPFreeTxRxRingMemory(
4225 + IN PRTMP_ADAPTER pAd)
4226 +{
4227 + int index, num , j;
4228 + PRTMP_TX_RING pTxRing;
4229 + PTXD_STRUC pTxD;
4230 + PNDIS_PACKET pPacket;
4231 + unsigned int IrqFlags;
4232 +
4233 + POS_COOKIE pObj =(POS_COOKIE) pAd->OS_Cookie;
4234 +
4235 + DBGPRINT(RT_DEBUG_TRACE, ("--> RTMPFreeTxRxRingMemory\n"));
4236 +
4237 + // Free TxSwQueue Packet
4238 + for (index=0; index <NUM_OF_TX_RING; index++)
4239 + {
4240 + PQUEUE_ENTRY pEntry;
4241 + PNDIS_PACKET pPacket;
4242 + PQUEUE_HEADER pQueue;
4243 +
4244 + RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
4245 + pQueue = &pAd->TxSwQueue[index];
4246 + while (pQueue->Head)
4247 + {
4248 + pEntry = RemoveHeadQueue(pQueue);
4249 + pPacket = QUEUE_ENTRY_TO_PACKET(pEntry);
4250 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
4251 + }
4252 + RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
4253 + }
4254 +
4255 + // Free Tx Ring Packet
4256 + for (index=0;index< NUM_OF_TX_RING;index++)
4257 + {
4258 + pTxRing = &pAd->TxRing[index];
4259 +
4260 + for (j=0; j< TX_RING_SIZE; j++)
4261 + {
4262 + pTxD = (PTXD_STRUC) (pTxRing->Cell[j].AllocVa);
4263 + pPacket = pTxRing->Cell[j].pNdisPacket;
4264 +
4265 + if (pPacket)
4266 + {
4267 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
4268 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
4269 + }
4270 + //Always assign pNdisPacket as NULL after clear
4271 + pTxRing->Cell[j].pNdisPacket = NULL;
4272 +
4273 + pPacket = pTxRing->Cell[j].pNextNdisPacket;
4274 +
4275 + if (pPacket)
4276 + {
4277 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
4278 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
4279 + }
4280 + //Always assign pNextNdisPacket as NULL after clear
4281 + pTxRing->Cell[pTxRing->TxSwFreeIdx].pNextNdisPacket = NULL;
4282 +
4283 + }
4284 + }
4285 +
4286 + for (index = RX_RING_SIZE - 1 ; index >= 0; index--)
4287 + {
4288 + if ((pAd->RxRing.Cell[index].DmaBuf.AllocVa) && (pAd->RxRing.Cell[index].pNdisPacket))
4289 + {
4290 + PCI_UNMAP_SINGLE(pObj->pci_dev, pAd->RxRing.Cell[index].DmaBuf.AllocPa, pAd->RxRing.Cell[index].DmaBuf.AllocSize, PCI_DMA_FROMDEVICE);
4291 + RELEASE_NDIS_PACKET(pAd, pAd->RxRing.Cell[index].pNdisPacket, NDIS_STATUS_SUCCESS);
4292 + }
4293 + }
4294 + NdisZeroMemory(pAd->RxRing.Cell, RX_RING_SIZE * sizeof(RTMP_DMACB));
4295 +
4296 + if (pAd->RxDescRing.AllocVa)
4297 + {
4298 + PCI_FREE_CONSISTENT(pObj->pci_dev, pAd->RxDescRing.AllocSize, pAd->RxDescRing.AllocVa, pAd->RxDescRing.AllocPa);
4299 + }
4300 + NdisZeroMemory(&pAd->RxDescRing, sizeof(RTMP_DMABUF));
4301 +
4302 + if (pAd->MgmtDescRing.AllocVa)
4303 + {
4304 + PCI_FREE_CONSISTENT(pObj->pci_dev, pAd->MgmtDescRing.AllocSize, pAd->MgmtDescRing.AllocVa, pAd->MgmtDescRing.AllocPa);
4305 + }
4306 + NdisZeroMemory(&pAd->MgmtDescRing, sizeof(RTMP_DMABUF));
4307 +
4308 + for (num = 0; num < NUM_OF_TX_RING; num++)
4309 + {
4310 + if (pAd->TxBufSpace[num].AllocVa)
4311 + {
4312 + PCI_FREE_CONSISTENT(pObj->pci_dev, pAd->TxBufSpace[num].AllocSize, pAd->TxBufSpace[num].AllocVa, pAd->TxBufSpace[num].AllocPa);
4313 + }
4314 + NdisZeroMemory(&pAd->TxBufSpace[num], sizeof(RTMP_DMABUF));
4315 +
4316 + if (pAd->TxDescRing[num].AllocVa)
4317 + {
4318 + PCI_FREE_CONSISTENT(pObj->pci_dev, pAd->TxDescRing[num].AllocSize, pAd->TxDescRing[num].AllocVa, pAd->TxDescRing[num].AllocPa);
4319 + }
4320 + NdisZeroMemory(&pAd->TxDescRing[num], sizeof(RTMP_DMABUF));
4321 + }
4322 +
4323 + if (pAd->FragFrame.pFragPacket)
4324 + RELEASE_NDIS_PACKET(pAd, pAd->FragFrame.pFragPacket, NDIS_STATUS_SUCCESS);
4325 +
4326 + DBGPRINT(RT_DEBUG_TRACE, ("<-- RTMPFreeTxRxRingMemory\n"));
4327 +}
4328 +
4329 +
4330 +/*
4331 + * FUNCTION: Allocate a packet buffer for DMA
4332 + * ARGUMENTS:
4333 + * AdapterHandle: AdapterHandle
4334 + * Length: Number of bytes to allocate
4335 + * Cached: Whether or not the memory can be cached
4336 + * VirtualAddress: Pointer to memory is returned here
4337 + * PhysicalAddress: Physical address corresponding to virtual address
4338 + * Notes:
4339 + * Cached is ignored: always cached memory
4340 + */
4341 +PNDIS_PACKET RTMP_AllocateRxPacketBuffer(
4342 + IN PRTMP_ADAPTER pAd,
4343 + IN ULONG Length,
4344 + IN BOOLEAN Cached,
4345 + OUT PVOID *VirtualAddress,
4346 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress)
4347 +{
4348 + PNDIS_PACKET pkt;
4349 +
4350 + pkt = RTPKT_TO_OSPKT(DEV_ALLOC_SKB(Length));
4351 +
4352 + if (pkt == NULL) {
4353 + DBGPRINT(RT_DEBUG_ERROR, ("can't allocate rx %ld size packet\n",Length));
4354 + }
4355 +
4356 + if (pkt) {
4357 + RTMP_SET_PACKET_SOURCE(pkt, PKTSRC_NDIS);
4358 + *VirtualAddress = (PVOID) RTPKT_TO_OSPKT(pkt)->data;
4359 + *PhysicalAddress = PCI_MAP_SINGLE(pAd, *VirtualAddress, Length, -1, PCI_DMA_FROMDEVICE);
4360 + } else {
4361 + *VirtualAddress = (PVOID) NULL;
4362 + *PhysicalAddress = (NDIS_PHYSICAL_ADDRESS) NULL;
4363 + }
4364 +
4365 + return (PNDIS_PACKET) pkt;
4366 +}
4367 +
4368 +
4369 +VOID Invalid_Remaining_Packet(
4370 + IN PRTMP_ADAPTER pAd,
4371 + IN ULONG VirtualAddress)
4372 +{
4373 + NDIS_PHYSICAL_ADDRESS PhysicalAddress;
4374 +
4375 + PhysicalAddress = PCI_MAP_SINGLE(pAd, (void *)(VirtualAddress+1600), RX_BUFFER_NORMSIZE-1600, -1, PCI_DMA_FROMDEVICE);
4376 +}
4377 +
4378 +PNDIS_PACKET GetPacketFromRxRing(
4379 + IN PRTMP_ADAPTER pAd,
4380 + OUT PRT28XX_RXD_STRUC pSaveRxD,
4381 + OUT BOOLEAN *pbReschedule,
4382 + IN OUT UINT32 *pRxPending)
4383 +{
4384 + PRXD_STRUC pRxD;
4385 +#ifdef RT_BIG_ENDIAN
4386 + PRXD_STRUC pDestRxD;
4387 + RXD_STRUC RxD;
4388 +#endif
4389 + PNDIS_PACKET pRxPacket = NULL;
4390 + PNDIS_PACKET pNewPacket;
4391 + PVOID AllocVa;
4392 + NDIS_PHYSICAL_ADDRESS AllocPa;
4393 + BOOLEAN bReschedule = FALSE;
4394 +
4395 + RTMP_SEM_LOCK(&pAd->RxRingLock);
4396 +
4397 + if (*pRxPending == 0)
4398 + {
4399 + // Get how may packets had been received
4400 + RTMP_IO_READ32(pAd, RX_DRX_IDX , &pAd->RxRing.RxDmaIdx);
4401 +
4402 + if (pAd->RxRing.RxSwReadIdx == pAd->RxRing.RxDmaIdx)
4403 + {
4404 + // no more rx packets
4405 + bReschedule = FALSE;
4406 + goto done;
4407 + }
4408 +
4409 + // get rx pending count
4410 + if (pAd->RxRing.RxDmaIdx > pAd->RxRing.RxSwReadIdx)
4411 + *pRxPending = pAd->RxRing.RxDmaIdx - pAd->RxRing.RxSwReadIdx;
4412 + else
4413 + *pRxPending = pAd->RxRing.RxDmaIdx + RX_RING_SIZE - pAd->RxRing.RxSwReadIdx;
4414 +
4415 + }
4416 +
4417 +#ifdef RT_BIG_ENDIAN
4418 + pDestRxD = (PRXD_STRUC) pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].AllocVa;
4419 + RxD = *pDestRxD;
4420 + pRxD = &RxD;
4421 + RTMPDescriptorEndianChange((PUCHAR)pRxD, TYPE_RXD);
4422 +#else
4423 + // Point to Rx indexed rx ring descriptor
4424 + pRxD = (PRXD_STRUC) pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].AllocVa;
4425 +#endif
4426 +
4427 + if (pRxD->DDONE == 0)
4428 + {
4429 + *pRxPending = 0;
4430 + // DMAIndx had done but DDONE bit not ready
4431 + bReschedule = TRUE;
4432 + goto done;
4433 + }
4434 +
4435 +
4436 + // return rx descriptor
4437 + NdisMoveMemory(pSaveRxD, pRxD, RXD_SIZE);
4438 +
4439 + pNewPacket = RTMP_AllocateRxPacketBuffer(pAd, RX_BUFFER_AGGRESIZE, FALSE, &AllocVa, &AllocPa);
4440 +
4441 + if (pNewPacket)
4442 + {
4443 + // unmap the rx buffer
4444 + PCI_UNMAP_SINGLE(pAd, pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].DmaBuf.AllocPa,
4445 + pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].DmaBuf.AllocSize, PCI_DMA_FROMDEVICE);
4446 + pRxPacket = pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].pNdisPacket;
4447 +
4448 + pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].DmaBuf.AllocSize = RX_BUFFER_AGGRESIZE;
4449 + pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].pNdisPacket = (PNDIS_PACKET) pNewPacket;
4450 + pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].DmaBuf.AllocVa = AllocVa;
4451 + pAd->RxRing.Cell[pAd->RxRing.RxSwReadIdx].DmaBuf.AllocPa = AllocPa;
4452 + /* update SDP0 to new buffer of rx packet */
4453 + pRxD->SDP0 = AllocPa;
4454 + }
4455 + else
4456 + {
4457 + //printk("No Rx Buffer\n");
4458 + pRxPacket = NULL;
4459 + bReschedule = TRUE;
4460 + }
4461 +
4462 + pRxD->DDONE = 0;
4463 +
4464 + // had handled one rx packet
4465 + *pRxPending = *pRxPending - 1;
4466 +
4467 + // update rx descriptor and kick rx
4468 +#ifdef RT_BIG_ENDIAN
4469 + RTMPDescriptorEndianChange((PUCHAR)pRxD, TYPE_RXD);
4470 + WriteBackToDescriptor((PUCHAR)pDestRxD, (PUCHAR)pRxD, FALSE, TYPE_RXD);
4471 +#endif
4472 + INC_RING_INDEX(pAd->RxRing.RxSwReadIdx, RX_RING_SIZE);
4473 +
4474 + pAd->RxRing.RxCpuIdx = (pAd->RxRing.RxSwReadIdx == 0) ? (RX_RING_SIZE-1) : (pAd->RxRing.RxSwReadIdx-1);
4475 + RTMP_IO_WRITE32(pAd, RX_CRX_IDX, pAd->RxRing.RxCpuIdx);
4476 +
4477 +done:
4478 + RTMP_SEM_UNLOCK(&pAd->RxRingLock);
4479 + *pbReschedule = bReschedule;
4480 + return pRxPacket;
4481 +}
4482 +/* End of 2860_rtmp_init.c */
4483 +
4484 --- /dev/null
4485 +++ b/drivers/staging/rt2860/common/action.c
4486 @@ -0,0 +1,1031 @@
4487 +/*
4488 + *************************************************************************
4489 + * Ralink Tech Inc.
4490 + * 5F., No.36, Taiyuan St., Jhubei City,
4491 + * Hsinchu County 302,
4492 + * Taiwan, R.O.C.
4493 + *
4494 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
4495 + *
4496 + * This program is free software; you can redistribute it and/or modify *
4497 + * it under the terms of the GNU General Public License as published by *
4498 + * the Free Software Foundation; either version 2 of the License, or *
4499 + * (at your option) any later version. *
4500 + * *
4501 + * This program is distributed in the hope that it will be useful, *
4502 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
4503 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
4504 + * GNU General Public License for more details. *
4505 + * *
4506 + * You should have received a copy of the GNU General Public License *
4507 + * along with this program; if not, write to the *
4508 + * Free Software Foundation, Inc., *
4509 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
4510 + * *
4511 + *************************************************************************
4512 +
4513 + Module Name:
4514 + action.c
4515 +
4516 + Abstract:
4517 + Handle association related requests either from WSTA or from local MLME
4518 +
4519 + Revision History:
4520 + Who When What
4521 + -------- ---------- ----------------------------------------------
4522 + Jan Lee 2006 created for rt2860
4523 + */
4524 +
4525 +#include "../rt_config.h"
4526 +#include "action.h"
4527 +
4528 +
4529 +static VOID ReservedAction(
4530 + IN PRTMP_ADAPTER pAd,
4531 + IN MLME_QUEUE_ELEM *Elem);
4532 +
4533 +/*
4534 + ==========================================================================
4535 + Description:
4536 + association state machine init, including state transition and timer init
4537 + Parameters:
4538 + S - pointer to the association state machine
4539 + Note:
4540 + The state machine looks like the following
4541 +
4542 + ASSOC_IDLE
4543 + MT2_MLME_DISASSOC_REQ mlme_disassoc_req_action
4544 + MT2_PEER_DISASSOC_REQ peer_disassoc_action
4545 + MT2_PEER_ASSOC_REQ drop
4546 + MT2_PEER_REASSOC_REQ drop
4547 + MT2_CLS3ERR cls3err_action
4548 + ==========================================================================
4549 + */
4550 +VOID ActionStateMachineInit(
4551 + IN PRTMP_ADAPTER pAd,
4552 + IN STATE_MACHINE *S,
4553 + OUT STATE_MACHINE_FUNC Trans[])
4554 +{
4555 + StateMachineInit(S, (STATE_MACHINE_FUNC *)Trans, MAX_ACT_STATE, MAX_ACT_MSG, (STATE_MACHINE_FUNC)Drop, ACT_IDLE, ACT_MACHINE_BASE);
4556 +
4557 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_SPECTRUM_CATE, (STATE_MACHINE_FUNC)PeerSpectrumAction);
4558 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_QOS_CATE, (STATE_MACHINE_FUNC)PeerQOSAction);
4559 +
4560 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_DLS_CATE, (STATE_MACHINE_FUNC)ReservedAction);
4561 +#ifdef QOS_DLS_SUPPORT
4562 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_DLS_CATE, (STATE_MACHINE_FUNC)PeerDLSAction);
4563 +#endif // QOS_DLS_SUPPORT //
4564 +
4565 +#ifdef DOT11_N_SUPPORT
4566 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_BA_CATE, (STATE_MACHINE_FUNC)PeerBAAction);
4567 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_HT_CATE, (STATE_MACHINE_FUNC)PeerHTAction);
4568 + StateMachineSetAction(S, ACT_IDLE, MT2_MLME_ADD_BA_CATE, (STATE_MACHINE_FUNC)MlmeADDBAAction);
4569 + StateMachineSetAction(S, ACT_IDLE, MT2_MLME_ORI_DELBA_CATE, (STATE_MACHINE_FUNC)MlmeDELBAAction);
4570 + StateMachineSetAction(S, ACT_IDLE, MT2_MLME_REC_DELBA_CATE, (STATE_MACHINE_FUNC)MlmeDELBAAction);
4571 +#endif // DOT11_N_SUPPORT //
4572 +
4573 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_PUBLIC_CATE, (STATE_MACHINE_FUNC)PeerPublicAction);
4574 + StateMachineSetAction(S, ACT_IDLE, MT2_PEER_RM_CATE, (STATE_MACHINE_FUNC)PeerRMAction);
4575 +
4576 + StateMachineSetAction(S, ACT_IDLE, MT2_MLME_QOS_CATE, (STATE_MACHINE_FUNC)MlmeQOSAction);
4577 + StateMachineSetAction(S, ACT_IDLE, MT2_MLME_DLS_CATE, (STATE_MACHINE_FUNC)MlmeDLSAction);
4578 + StateMachineSetAction(S, ACT_IDLE, MT2_ACT_INVALID, (STATE_MACHINE_FUNC)MlmeInvalidAction);
4579 +}
4580 +
4581 +#ifdef DOT11_N_SUPPORT
4582 +VOID MlmeADDBAAction(
4583 + IN PRTMP_ADAPTER pAd,
4584 + IN MLME_QUEUE_ELEM *Elem)
4585 +
4586 +{
4587 + MLME_ADDBA_REQ_STRUCT *pInfo;
4588 + UCHAR Addr[6];
4589 + PUCHAR pOutBuffer = NULL;
4590 + NDIS_STATUS NStatus;
4591 + ULONG Idx;
4592 + FRAME_ADDBA_REQ Frame;
4593 + ULONG FrameLen;
4594 + BA_ORI_ENTRY *pBAEntry = NULL;
4595 +
4596 + pInfo = (MLME_ADDBA_REQ_STRUCT *)Elem->Msg;
4597 + NdisZeroMemory(&Frame, sizeof(FRAME_ADDBA_REQ));
4598 +
4599 + if(MlmeAddBAReqSanity(pAd, Elem->Msg, Elem->MsgLen, Addr))
4600 + {
4601 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
4602 + if(NStatus != NDIS_STATUS_SUCCESS)
4603 + {
4604 + DBGPRINT(RT_DEBUG_TRACE,("BA - MlmeADDBAAction() allocate memory failed \n"));
4605 + return;
4606 + }
4607 + // 1. find entry
4608 + Idx = pAd->MacTab.Content[pInfo->Wcid].BAOriWcidArray[pInfo->TID];
4609 + if (Idx == 0)
4610 + {
4611 + MlmeFreeMemory(pAd, pOutBuffer);
4612 + DBGPRINT(RT_DEBUG_ERROR,("BA - MlmeADDBAAction() can't find BAOriEntry \n"));
4613 + return;
4614 + }
4615 + else
4616 + {
4617 + pBAEntry =&pAd->BATable.BAOriEntry[Idx];
4618 + }
4619 +
4620 +#ifdef CONFIG_STA_SUPPORT
4621 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
4622 + {
4623 + if (ADHOC_ON(pAd))
4624 + ActHeaderInit(pAd, &Frame.Hdr, pInfo->pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
4625 + else
4626 +#ifdef QOS_DLS_SUPPORT
4627 + if (pAd->MacTab.Content[pInfo->Wcid].ValidAsDls)
4628 + ActHeaderInit(pAd, &Frame.Hdr, pInfo->pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
4629 + else
4630 +#endif // QOS_DLS_SUPPORT //
4631 + ActHeaderInit(pAd, &Frame.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pInfo->pAddr);
4632 +
4633 + }
4634 +#endif // CONFIG_STA_SUPPORT //
4635 +
4636 + Frame.Category = CATEGORY_BA;
4637 + Frame.Action = ADDBA_REQ;
4638 + Frame.BaParm.AMSDUSupported = 0;
4639 + Frame.BaParm.BAPolicy = IMMED_BA;
4640 + Frame.BaParm.TID = pInfo->TID;
4641 + Frame.BaParm.BufSize = pInfo->BaBufSize;
4642 + Frame.Token = pInfo->Token;
4643 + Frame.TimeOutValue = pInfo->TimeOutValue;
4644 + Frame.BaStartSeq.field.FragNum = 0;
4645 + Frame.BaStartSeq.field.StartSeq = pAd->MacTab.Content[pInfo->Wcid].TxSeq[pInfo->TID];
4646 +
4647 + *(USHORT *)(&Frame.BaParm) = cpu2le16(*(USHORT *)(&Frame.BaParm));
4648 + Frame.TimeOutValue = cpu2le16(Frame.TimeOutValue);
4649 + Frame.BaStartSeq.word = cpu2le16(Frame.BaStartSeq.word);
4650 +
4651 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
4652 + sizeof(FRAME_ADDBA_REQ), &Frame,
4653 + END_OF_ARGS);
4654 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
4655 + MlmeFreeMemory(pAd, pOutBuffer);
4656 +
4657 + DBGPRINT(RT_DEBUG_TRACE, ("BA - Send ADDBA request. StartSeq = %x, FrameLen = %ld. BufSize = %d\n", Frame.BaStartSeq.field.StartSeq, FrameLen, Frame.BaParm.BufSize));
4658 + }
4659 +}
4660 +
4661 +/*
4662 + ==========================================================================
4663 + Description:
4664 + send DELBA and delete BaEntry if any
4665 + Parametrs:
4666 + Elem - MLME message MLME_DELBA_REQ_STRUCT
4667 +
4668 + IRQL = DISPATCH_LEVEL
4669 +
4670 + ==========================================================================
4671 + */
4672 +VOID MlmeDELBAAction(
4673 + IN PRTMP_ADAPTER pAd,
4674 + IN MLME_QUEUE_ELEM *Elem)
4675 +{
4676 + MLME_DELBA_REQ_STRUCT *pInfo;
4677 + PUCHAR pOutBuffer = NULL;
4678 + PUCHAR pOutBuffer2 = NULL;
4679 + NDIS_STATUS NStatus;
4680 + ULONG Idx;
4681 + FRAME_DELBA_REQ Frame;
4682 + ULONG FrameLen;
4683 + FRAME_BAR FrameBar;
4684 +
4685 + pInfo = (MLME_DELBA_REQ_STRUCT *)Elem->Msg;
4686 + // must send back DELBA
4687 + NdisZeroMemory(&Frame, sizeof(FRAME_DELBA_REQ));
4688 + DBGPRINT(RT_DEBUG_TRACE, ("==> MlmeDELBAAction(), Initiator(%d) \n", pInfo->Initiator));
4689 +
4690 + if(MlmeDelBAReqSanity(pAd, Elem->Msg, Elem->MsgLen))
4691 + {
4692 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
4693 + if(NStatus != NDIS_STATUS_SUCCESS)
4694 + {
4695 + DBGPRINT(RT_DEBUG_ERROR,("BA - MlmeDELBAAction() allocate memory failed 1. \n"));
4696 + return;
4697 + }
4698 +
4699 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer2); //Get an unused nonpaged memory
4700 + if(NStatus != NDIS_STATUS_SUCCESS)
4701 + {
4702 + MlmeFreeMemory(pAd, pOutBuffer);
4703 + DBGPRINT(RT_DEBUG_ERROR, ("BA - MlmeDELBAAction() allocate memory failed 2. \n"));
4704 + return;
4705 + }
4706 +
4707 + // SEND BAR (Send BAR to refresh peer reordering buffer.)
4708 + Idx = pAd->MacTab.Content[pInfo->Wcid].BAOriWcidArray[pInfo->TID];
4709 +#ifdef CONFIG_STA_SUPPORT
4710 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
4711 + BarHeaderInit(pAd, &FrameBar, pAd->MacTab.Content[pInfo->Wcid].Addr, pAd->CurrentAddress);
4712 +#endif // CONFIG_STA_SUPPORT //
4713 +
4714 + FrameBar.StartingSeq.field.FragNum = 0; // make sure sequence not clear in DEL funciton.
4715 + FrameBar.StartingSeq.field.StartSeq = pAd->MacTab.Content[pInfo->Wcid].TxSeq[pInfo->TID]; // make sure sequence not clear in DEL funciton.
4716 + FrameBar.BarControl.TID = pInfo->TID; // make sure sequence not clear in DEL funciton.
4717 + FrameBar.BarControl.ACKPolicy = IMMED_BA; // make sure sequence not clear in DEL funciton.
4718 + FrameBar.BarControl.Compressed = 1; // make sure sequence not clear in DEL funciton.
4719 + FrameBar.BarControl.MTID = 0; // make sure sequence not clear in DEL funciton.
4720 +
4721 + MakeOutgoingFrame(pOutBuffer2, &FrameLen,
4722 + sizeof(FRAME_BAR), &FrameBar,
4723 + END_OF_ARGS);
4724 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer2, FrameLen);
4725 + MlmeFreeMemory(pAd, pOutBuffer2);
4726 + DBGPRINT(RT_DEBUG_TRACE,("BA - MlmeDELBAAction() . Send BAR to refresh peer reordering buffer \n"));
4727 +
4728 + // SEND DELBA FRAME
4729 + FrameLen = 0;
4730 +#ifdef CONFIG_STA_SUPPORT
4731 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
4732 + {
4733 + if (ADHOC_ON(pAd))
4734 + ActHeaderInit(pAd, &Frame.Hdr, pAd->MacTab.Content[pInfo->Wcid].Addr, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
4735 + else
4736 +#ifdef QOS_DLS_SUPPORT
4737 + if (pAd->MacTab.Content[pInfo->Wcid].ValidAsDls)
4738 + ActHeaderInit(pAd, &Frame.Hdr, pAd->MacTab.Content[pInfo->Wcid].Addr, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
4739 + else
4740 +#endif // QOS_DLS_SUPPORT //
4741 + ActHeaderInit(pAd, &Frame.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAd->MacTab.Content[pInfo->Wcid].Addr);
4742 + }
4743 +#endif // CONFIG_STA_SUPPORT //
4744 + Frame.Category = CATEGORY_BA;
4745 + Frame.Action = DELBA;
4746 + Frame.DelbaParm.Initiator = pInfo->Initiator;
4747 + Frame.DelbaParm.TID = pInfo->TID;
4748 + Frame.ReasonCode = 39; // Time Out
4749 + *(USHORT *)(&Frame.DelbaParm) = cpu2le16(*(USHORT *)(&Frame.DelbaParm));
4750 + Frame.ReasonCode = cpu2le16(Frame.ReasonCode);
4751 +
4752 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
4753 + sizeof(FRAME_DELBA_REQ), &Frame,
4754 + END_OF_ARGS);
4755 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
4756 + MlmeFreeMemory(pAd, pOutBuffer);
4757 + DBGPRINT(RT_DEBUG_TRACE, ("BA - MlmeDELBAAction() . 3 DELBA sent. Initiator(%d)\n", pInfo->Initiator));
4758 + }
4759 +}
4760 +#endif // DOT11_N_SUPPORT //
4761 +
4762 +VOID MlmeQOSAction(
4763 + IN PRTMP_ADAPTER pAd,
4764 + IN MLME_QUEUE_ELEM *Elem)
4765 +{
4766 +}
4767 +
4768 +VOID MlmeDLSAction(
4769 + IN PRTMP_ADAPTER pAd,
4770 + IN MLME_QUEUE_ELEM *Elem)
4771 +{
4772 +}
4773 +
4774 +VOID MlmeInvalidAction(
4775 + IN PRTMP_ADAPTER pAd,
4776 + IN MLME_QUEUE_ELEM *Elem)
4777 +{
4778 + //PUCHAR pOutBuffer = NULL;
4779 + //Return the receiving frame except the MSB of category filed set to 1. 7.3.1.11
4780 +}
4781 +
4782 +VOID PeerQOSAction(
4783 + IN PRTMP_ADAPTER pAd,
4784 + IN MLME_QUEUE_ELEM *Elem)
4785 +{
4786 +}
4787 +
4788 +#ifdef QOS_DLS_SUPPORT
4789 +VOID PeerDLSAction(
4790 + IN PRTMP_ADAPTER pAd,
4791 + IN MLME_QUEUE_ELEM *Elem)
4792 +{
4793 + UCHAR Action = Elem->Msg[LENGTH_802_11+1];
4794 +
4795 + switch(Action)
4796 + {
4797 + case ACTION_DLS_REQUEST:
4798 +#ifdef CONFIG_STA_SUPPORT
4799 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
4800 + PeerDlsReqAction(pAd, Elem);
4801 +#endif // CONFIG_STA_SUPPORT //
4802 + break;
4803 +
4804 + case ACTION_DLS_RESPONSE:
4805 +#ifdef CONFIG_STA_SUPPORT
4806 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
4807 + PeerDlsRspAction(pAd, Elem);
4808 +#endif // CONFIG_STA_SUPPORT //
4809 + break;
4810 +
4811 + case ACTION_DLS_TEARDOWN:
4812 +#ifdef CONFIG_STA_SUPPORT
4813 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
4814 + PeerDlsTearDownAction(pAd, Elem);
4815 +#endif // CONFIG_STA_SUPPORT //
4816 + break;
4817 + }
4818 +}
4819 +#endif // QOS_DLS_SUPPORT //
4820 +
4821 +#ifdef DOT11_N_SUPPORT
4822 +VOID PeerBAAction(
4823 + IN PRTMP_ADAPTER pAd,
4824 + IN MLME_QUEUE_ELEM *Elem)
4825 +{
4826 + UCHAR Action = Elem->Msg[LENGTH_802_11+1];
4827 +
4828 + switch(Action)
4829 + {
4830 + case ADDBA_REQ:
4831 + PeerAddBAReqAction(pAd,Elem);
4832 + break;
4833 + case ADDBA_RESP:
4834 + PeerAddBARspAction(pAd,Elem);
4835 + break;
4836 + case DELBA:
4837 + PeerDelBAAction(pAd,Elem);
4838 + break;
4839 + }
4840 +}
4841 +
4842 +
4843 +#ifdef DOT11N_DRAFT3
4844 +
4845 +#ifdef CONFIG_STA_SUPPORT
4846 +VOID StaPublicAction(
4847 + IN PRTMP_ADAPTER pAd,
4848 + IN UCHAR Bss2040Coexist)
4849 +{
4850 + BSS_2040_COEXIST_IE BssCoexist;
4851 + MLME_SCAN_REQ_STRUCT ScanReq;
4852 +
4853 + BssCoexist.word = Bss2040Coexist;
4854 + // AP asks Station to return a 20/40 BSS Coexistence mgmt frame. So we first starts a scan, then send back 20/40 BSS Coexistence mgmt frame
4855 + if ((BssCoexist.field.InfoReq == 1) && (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_SCAN_2040)))
4856 + {
4857 + // Clear record first. After scan , will update those bit and send back to transmiter.
4858 + pAd->CommonCfg.BSSCoexist2040.field.InfoReq = 1;
4859 + pAd->CommonCfg.BSSCoexist2040.field.Intolerant40 = 0;
4860 + pAd->CommonCfg.BSSCoexist2040.field.BSS20WidthReq = 0;
4861 + // Fill out stuff for scan request
4862 + ScanParmFill(pAd, &ScanReq, ZeroSsid, 0, BSS_ANY, SCAN_2040_BSS_COEXIST);
4863 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ, sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
4864 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
4865 + }
4866 +}
4867 +
4868 +
4869 +/*
4870 +Description : Build Intolerant Channel Rerpot from Trigger event table.
4871 +return : how many bytes copied.
4872 +*/
4873 +ULONG BuildIntolerantChannelRep(
4874 + IN PRTMP_ADAPTER pAd,
4875 + IN PUCHAR pDest)
4876 +{
4877 + ULONG FrameLen = 0;
4878 + ULONG ReadOffset = 0;
4879 + UCHAR i;
4880 + UCHAR LastRegClass = 0xff;
4881 + PUCHAR pLen;
4882 +
4883 + for ( i = 0;i < MAX_TRIGGER_EVENT;i++)
4884 + {
4885 + if (pAd->CommonCfg.TriggerEventTab.EventA[i].bValid == TRUE)
4886 + {
4887 + if (pAd->CommonCfg.TriggerEventTab.EventA[i].RegClass == LastRegClass)
4888 + {
4889 + *(pDest + ReadOffset) = (UCHAR)pAd->CommonCfg.TriggerEventTab.EventA[i].Channel;
4890 + *pLen++;
4891 + ReadOffset++;
4892 + FrameLen++;
4893 + }
4894 + else
4895 + {
4896 + *(pDest + ReadOffset) = IE_2040_BSS_INTOLERANT_REPORT; // IE
4897 + *(pDest + ReadOffset + 1) = 2; // Len = RegClass byte + channel byte.
4898 + pLen = pDest + ReadOffset + 1;
4899 + LastRegClass = pAd->CommonCfg.TriggerEventTab.EventA[i].RegClass;
4900 + *(pDest + ReadOffset + 2) = LastRegClass; // Len = RegClass byte + channel byte.
4901 + *(pDest + ReadOffset + 3) = (UCHAR)pAd->CommonCfg.TriggerEventTab.EventA[i].Channel;
4902 + FrameLen += 4;
4903 + ReadOffset += 4;
4904 + }
4905 +
4906 + }
4907 + }
4908 + return FrameLen;
4909 +}
4910 +
4911 +
4912 +/*
4913 +Description : Send 20/40 BSS Coexistence Action frame If one trigger event is triggered.
4914 +*/
4915 +VOID Send2040CoexistAction(
4916 + IN PRTMP_ADAPTER pAd,
4917 + IN UCHAR Wcid,
4918 + IN BOOLEAN bAddIntolerantCha)
4919 +{
4920 + PUCHAR pOutBuffer = NULL;
4921 + NDIS_STATUS NStatus;
4922 + FRAME_ACTION_HDR Frame;
4923 + ULONG FrameLen;
4924 + ULONG IntolerantChaRepLen;
4925 +
4926 + IntolerantChaRepLen = 0;
4927 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
4928 + if(NStatus != NDIS_STATUS_SUCCESS)
4929 + {
4930 + DBGPRINT(RT_DEBUG_ERROR,("ACT - Send2040CoexistAction() allocate memory failed \n"));
4931 + return;
4932 + }
4933 + ActHeaderInit(pAd, &Frame.Hdr, pAd->MacTab.Content[Wcid].Addr, pAd->CommonCfg.Bssid);
4934 + Frame.Category = CATEGORY_PUBLIC;
4935 + Frame.Action = ACTION_BSS_2040_COEXIST;
4936 +
4937 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
4938 + sizeof(FRAME_ACTION_HDR), &Frame,
4939 + END_OF_ARGS);
4940 +
4941 + *(pOutBuffer + FrameLen) = pAd->CommonCfg.BSSCoexist2040.word;
4942 + FrameLen++;
4943 +
4944 + if (bAddIntolerantCha == TRUE)
4945 + IntolerantChaRepLen = BuildIntolerantChannelRep(pAd, pOutBuffer + FrameLen);
4946 +
4947 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen + IntolerantChaRepLen);
4948 + DBGPRINT(RT_DEBUG_ERROR,("ACT - Send2040CoexistAction( BSSCoexist2040 = 0x%x ) \n", pAd->CommonCfg.BSSCoexist2040.word));
4949 +
4950 +}
4951 +
4952 +
4953 +/*
4954 + ==========================================================================
4955 + Description:
4956 + After scan, Update 20/40 BSS Coexistence IE and send out.
4957 + According to 802.11n D3.03 11.14.10
4958 +
4959 + Parameters:
4960 + ==========================================================================
4961 + */
4962 +VOID Update2040CoexistFrameAndNotify(
4963 + IN PRTMP_ADAPTER pAd,
4964 + IN UCHAR Wcid,
4965 + IN BOOLEAN bAddIntolerantCha)
4966 +{
4967 + BSS_2040_COEXIST_IE OldValue;
4968 +
4969 + OldValue.word = pAd->CommonCfg.BSSCoexist2040.word;
4970 + if ((pAd->CommonCfg.TriggerEventTab.EventANo > 0) || (pAd->CommonCfg.TriggerEventTab.EventBCountDown > 0))
4971 + pAd->CommonCfg.BSSCoexist2040.field.BSS20WidthReq = 1;
4972 +
4973 + // Need to check !!!!
4974 + // How STA will set Intolerant40 if implementation dependent. Now we don't set this bit first.!!!!!
4975 + // So Only check BSS20WidthReq change.
4976 + if (OldValue.field.BSS20WidthReq != pAd->CommonCfg.BSSCoexist2040.field.BSS20WidthReq)
4977 + {
4978 + Send2040CoexistAction(pAd, Wcid, bAddIntolerantCha);
4979 + }
4980 +}
4981 +#endif // CONFIG_STA_SUPPORT //
4982 +
4983 +
4984 +BOOLEAN ChannelSwitchSanityCheck(
4985 + IN PRTMP_ADAPTER pAd,
4986 + IN UCHAR Wcid,
4987 + IN UCHAR NewChannel,
4988 + IN UCHAR Secondary)
4989 +{
4990 + UCHAR i;
4991 +
4992 + if (Wcid >= MAX_LEN_OF_MAC_TABLE)
4993 + return FALSE;
4994 +
4995 + if ((NewChannel > 7) && (Secondary == 1))
4996 + return FALSE;
4997 +
4998 + if ((NewChannel < 5) && (Secondary == 3))
4999 + return FALSE;
5000 +
5001 + // 0. Check if new channel is in the channellist.
5002 + for (i = 0;i < pAd->ChannelListNum;i++)
5003 + {
5004 + if (pAd->ChannelList[i].Channel == NewChannel)
5005 + {
5006 + break;
5007 + }
5008 + }
5009 +
5010 + if (i == pAd->ChannelListNum)
5011 + return FALSE;
5012 +
5013 + return TRUE;
5014 +}
5015 +
5016 +
5017 +VOID ChannelSwitchAction(
5018 + IN PRTMP_ADAPTER pAd,
5019 + IN UCHAR Wcid,
5020 + IN UCHAR NewChannel,
5021 + IN UCHAR Secondary)
5022 +{
5023 + UCHAR BBPValue = 0;
5024 + ULONG MACValue;
5025 +
5026 + DBGPRINT(RT_DEBUG_TRACE,("SPECTRUM - ChannelSwitchAction(NewChannel = %d , Secondary = %d) \n", NewChannel, Secondary));
5027 +
5028 + if (ChannelSwitchSanityCheck(pAd, Wcid, NewChannel, Secondary) == FALSE)
5029 + return;
5030 +
5031 + // 1. Switches to BW = 20.
5032 + if (Secondary == 0)
5033 + {
5034 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
5035 + BBPValue&= (~0x18);
5036 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
5037 + if (pAd->MACVersion == 0x28600100)
5038 + {
5039 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, 0x16);
5040 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, 0x08);
5041 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, 0x11);
5042 + DBGPRINT(RT_DEBUG_TRACE, ("!!!rt2860C !!! \n" ));
5043 + }
5044 + pAd->CommonCfg.BBPCurrentBW = BW_20;
5045 + pAd->CommonCfg.Channel = NewChannel;
5046 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel;
5047 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel,FALSE);
5048 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
5049 + pAd->MacTab.Content[Wcid].HTPhyMode.field.BW = 0;
5050 + DBGPRINT(RT_DEBUG_TRACE, ("!!!20MHz !!! \n" ));
5051 + }
5052 + // 1. Switches to BW = 40 And Station supports BW = 40.
5053 + else if (((Secondary == 1) || (Secondary == 3)) && (pAd->CommonCfg.HtCapability.HtCapInfo.ChannelWidth == 1))
5054 + {
5055 + pAd->CommonCfg.Channel = NewChannel;
5056 +
5057 + if (Secondary == 1)
5058 + {
5059 + // Secondary above.
5060 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel + 2;
5061 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &MACValue);
5062 + MACValue &= 0xfe;
5063 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, MACValue);
5064 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
5065 + BBPValue&= (~0x18);
5066 + BBPValue|= (0x10);
5067 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
5068 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BBPValue);
5069 + BBPValue&= (~0x20);
5070 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BBPValue);
5071 + DBGPRINT(RT_DEBUG_TRACE, ("!!!40MHz Lower LINK UP !!! Control Channel at Below. Central = %d \n", pAd->CommonCfg.CentralChannel ));
5072 + }
5073 + else
5074 + {
5075 + // Secondary below.
5076 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel - 2;
5077 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &MACValue);
5078 + MACValue &= 0xfe;
5079 + MACValue |= 0x1;
5080 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, MACValue);
5081 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
5082 + BBPValue&= (~0x18);
5083 + BBPValue|= (0x10);
5084 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
5085 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BBPValue);
5086 + BBPValue&= (~0x20);
5087 + BBPValue|= (0x20);
5088 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BBPValue);
5089 + DBGPRINT(RT_DEBUG_TRACE, ("!!!40MHz Upper LINK UP !!! Control Channel at UpperCentral = %d \n", pAd->CommonCfg.CentralChannel ));
5090 + }
5091 + pAd->CommonCfg.BBPCurrentBW = BW_40;
5092 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
5093 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
5094 + pAd->MacTab.Content[Wcid].HTPhyMode.field.BW = 1;
5095 + }
5096 +}
5097 +#endif // DOT11N_DRAFT3 //
5098 +#endif // DOT11_N_SUPPORT //
5099 +
5100 +VOID PeerPublicAction(
5101 + IN PRTMP_ADAPTER pAd,
5102 + IN MLME_QUEUE_ELEM *Elem)
5103 +{
5104 +#ifdef DOT11N_DRAFT3
5105 + UCHAR Action = Elem->Msg[LENGTH_802_11+1];
5106 +#endif // DOT11N_DRAFT3 //
5107 +
5108 + if (Elem->Wcid >= MAX_LEN_OF_MAC_TABLE)
5109 + return;
5110 +
5111 +#ifdef DOT11N_DRAFT3
5112 + switch(Action)
5113 + {
5114 + case ACTION_BSS_2040_COEXIST: // Format defined in IEEE 7.4.7a.1 in 11n Draf3.03
5115 + {
5116 + //UCHAR BssCoexist;
5117 + BSS_2040_COEXIST_ELEMENT *pCoexistInfo;
5118 + BSS_2040_COEXIST_IE *pBssCoexistIe;
5119 + BSS_2040_INTOLERANT_CH_REPORT *pIntolerantReport = NULL;
5120 +
5121 + if (Elem->MsgLen <= (LENGTH_802_11 + sizeof(BSS_2040_COEXIST_ELEMENT)) )
5122 + {
5123 + DBGPRINT(RT_DEBUG_ERROR, ("ACTION - 20/40 BSS Coexistence Management Frame length too short! len = %ld!\n", Elem->MsgLen));
5124 + break;
5125 + }
5126 + DBGPRINT(RT_DEBUG_TRACE, ("ACTION - 20/40 BSS Coexistence Management action----> \n"));
5127 + hex_dump("CoexistenceMgmtFrame", Elem->Msg, Elem->MsgLen);
5128 +
5129 +
5130 + pCoexistInfo = (BSS_2040_COEXIST_ELEMENT *) &Elem->Msg[LENGTH_802_11+2];
5131 + //hex_dump("CoexistInfo", (PUCHAR)pCoexistInfo, sizeof(BSS_2040_COEXIST_ELEMENT));
5132 + if (Elem->MsgLen >= (LENGTH_802_11 + sizeof(BSS_2040_COEXIST_ELEMENT) + sizeof(BSS_2040_INTOLERANT_CH_REPORT)))
5133 + {
5134 + pIntolerantReport = (BSS_2040_INTOLERANT_CH_REPORT *)((PUCHAR)pCoexistInfo + sizeof(BSS_2040_COEXIST_ELEMENT));
5135 + }
5136 + //hex_dump("IntolerantReport ", (PUCHAR)pIntolerantReport, sizeof(BSS_2040_INTOLERANT_CH_REPORT));
5137 +
5138 + pBssCoexistIe = (BSS_2040_COEXIST_IE *)(&pCoexistInfo->BssCoexistIe);
5139 +
5140 +#ifdef CONFIG_STA_SUPPORT
5141 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
5142 + {
5143 + if (INFRA_ON(pAd))
5144 + {
5145 + StaPublicAction(pAd, pCoexistInfo);
5146 + }
5147 + }
5148 +#endif // CONFIG_STA_SUPPORT //
5149 +
5150 + }
5151 + break;
5152 + }
5153 +
5154 +#endif // DOT11N_DRAFT3 //
5155 +
5156 +}
5157 +
5158 +
5159 +static VOID ReservedAction(
5160 + IN PRTMP_ADAPTER pAd,
5161 + IN MLME_QUEUE_ELEM *Elem)
5162 +{
5163 + UCHAR Category;
5164 +
5165 + if (Elem->MsgLen <= LENGTH_802_11)
5166 + {
5167 + return;
5168 + }
5169 +
5170 + Category = Elem->Msg[LENGTH_802_11];
5171 + DBGPRINT(RT_DEBUG_TRACE,("Rcv reserved category(%d) Action Frame\n", Category));
5172 + hex_dump("Reserved Action Frame", &Elem->Msg[0], Elem->MsgLen);
5173 +}
5174 +
5175 +VOID PeerRMAction(
5176 + IN PRTMP_ADAPTER pAd,
5177 + IN MLME_QUEUE_ELEM *Elem)
5178 +
5179 +{
5180 + return;
5181 +}
5182 +
5183 +#ifdef DOT11_N_SUPPORT
5184 +static VOID respond_ht_information_exchange_action(
5185 + IN PRTMP_ADAPTER pAd,
5186 + IN MLME_QUEUE_ELEM *Elem)
5187 +{
5188 + PUCHAR pOutBuffer = NULL;
5189 + NDIS_STATUS NStatus;
5190 + ULONG FrameLen;
5191 + FRAME_HT_INFO HTINFOframe, *pFrame;
5192 + UCHAR *pAddr;
5193 +
5194 +
5195 + // 2. Always send back ADDBA Response
5196 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
5197 +
5198 + if (NStatus != NDIS_STATUS_SUCCESS)
5199 + {
5200 + DBGPRINT(RT_DEBUG_TRACE,("ACTION - respond_ht_information_exchange_action() allocate memory failed \n"));
5201 + return;
5202 + }
5203 +
5204 + // get RA
5205 + pFrame = (FRAME_HT_INFO *) &Elem->Msg[0];
5206 + pAddr = pFrame->Hdr.Addr2;
5207 +
5208 + NdisZeroMemory(&HTINFOframe, sizeof(FRAME_HT_INFO));
5209 + // 2-1. Prepare ADDBA Response frame.
5210 +#ifdef CONFIG_STA_SUPPORT
5211 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
5212 + {
5213 + if (ADHOC_ON(pAd))
5214 + ActHeaderInit(pAd, &HTINFOframe.Hdr, pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
5215 + else
5216 + ActHeaderInit(pAd, &HTINFOframe.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAddr);
5217 + }
5218 +#endif // CONFIG_STA_SUPPORT //
5219 +
5220 + HTINFOframe.Category = CATEGORY_HT;
5221 + HTINFOframe.Action = HT_INFO_EXCHANGE;
5222 + HTINFOframe.HT_Info.Request = 0;
5223 + HTINFOframe.HT_Info.Forty_MHz_Intolerant = pAd->CommonCfg.HtCapability.HtCapInfo.Forty_Mhz_Intolerant;
5224 + HTINFOframe.HT_Info.STA_Channel_Width = pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth;
5225 +
5226 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
5227 + sizeof(FRAME_HT_INFO), &HTINFOframe,
5228 + END_OF_ARGS);
5229 +
5230 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
5231 + MlmeFreeMemory(pAd, pOutBuffer);
5232 +}
5233 +
5234 +
5235 +#ifdef DOT11N_DRAFT3
5236 +VOID SendNotifyBWActionFrame(
5237 + IN PRTMP_ADAPTER pAd,
5238 + IN UCHAR Wcid,
5239 + IN UCHAR apidx)
5240 +{
5241 + PUCHAR pOutBuffer = NULL;
5242 + NDIS_STATUS NStatus;
5243 + FRAME_ACTION_HDR Frame;
5244 + ULONG FrameLen;
5245 + PUCHAR pAddr1;
5246 +
5247 +
5248 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
5249 + if(NStatus != NDIS_STATUS_SUCCESS)
5250 + {
5251 + DBGPRINT(RT_DEBUG_ERROR,("ACT - SendNotifyBWAction() allocate memory failed \n"));
5252 + return;
5253 + }
5254 +
5255 + if (Wcid == MCAST_WCID)
5256 + pAddr1 = &BROADCAST_ADDR[0];
5257 + else
5258 + pAddr1 = pAd->MacTab.Content[Wcid].Addr;
5259 + ActHeaderInit(pAd, &Frame.Hdr, pAddr1, pAd->ApCfg.MBSSID[apidx].Bssid, pAd->ApCfg.MBSSID[apidx].Bssid);
5260 +
5261 + Frame.Category = CATEGORY_HT;
5262 + Frame.Action = NOTIFY_BW_ACTION;
5263 +
5264 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
5265 + sizeof(FRAME_ACTION_HDR), &Frame,
5266 + END_OF_ARGS);
5267 +
5268 + *(pOutBuffer + FrameLen) = pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth;
5269 + FrameLen++;
5270 +
5271 +
5272 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
5273 + DBGPRINT(RT_DEBUG_TRACE,("ACT - SendNotifyBWAction(NotifyBW= %d)!\n", pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth));
5274 +
5275 +}
5276 +#endif // DOT11N_DRAFT3 //
5277 +
5278 +
5279 +VOID PeerHTAction(
5280 + IN PRTMP_ADAPTER pAd,
5281 + IN MLME_QUEUE_ELEM *Elem)
5282 +{
5283 + UCHAR Action = Elem->Msg[LENGTH_802_11+1];
5284 +
5285 + if (Elem->Wcid >= MAX_LEN_OF_MAC_TABLE)
5286 + return;
5287 +
5288 + switch(Action)
5289 + {
5290 + case NOTIFY_BW_ACTION:
5291 + DBGPRINT(RT_DEBUG_TRACE,("ACTION - HT Notify Channel bandwidth action----> \n"));
5292 +#ifdef CONFIG_STA_SUPPORT
5293 + if(pAd->StaActive.SupportedPhyInfo.bHtEnable == FALSE)
5294 + {
5295 + // Note, this is to patch DIR-1353 AP. When the AP set to Wep, it will use legacy mode. But AP still keeps
5296 + // sending BW_Notify Action frame, and cause us to linkup and linkdown.
5297 + // In legacy mode, don't need to parse HT action frame.
5298 + DBGPRINT(RT_DEBUG_TRACE,("ACTION -Ignore HT Notify Channel BW when link as legacy mode. BW = %d---> \n",
5299 + Elem->Msg[LENGTH_802_11+2] ));
5300 + break;
5301 + }
5302 +#endif // CONFIG_STA_SUPPORT //
5303 +
5304 + if (Elem->Msg[LENGTH_802_11+2] == 0) // 7.4.8.2. if value is 1, keep the same as supported channel bandwidth.
5305 + pAd->MacTab.Content[Elem->Wcid].HTPhyMode.field.BW = 0;
5306 +
5307 + break;
5308 + case SMPS_ACTION:
5309 + // 7.3.1.25
5310 + DBGPRINT(RT_DEBUG_TRACE,("ACTION - SMPS action----> \n"));
5311 + if (((Elem->Msg[LENGTH_802_11+2]&0x1) == 0))
5312 + {
5313 + pAd->MacTab.Content[Elem->Wcid].MmpsMode = MMPS_ENABLE;
5314 + }
5315 + else if (((Elem->Msg[LENGTH_802_11+2]&0x2) == 0))
5316 + {
5317 + pAd->MacTab.Content[Elem->Wcid].MmpsMode = MMPS_STATIC;
5318 + }
5319 + else
5320 + {
5321 + pAd->MacTab.Content[Elem->Wcid].MmpsMode = MMPS_DYNAMIC;
5322 + }
5323 +
5324 + DBGPRINT(RT_DEBUG_TRACE,("Aid(%d) MIMO PS = %d\n", Elem->Wcid, pAd->MacTab.Content[Elem->Wcid].MmpsMode));
5325 + // rt2860c : add something for smps change.
5326 + break;
5327 +
5328 + case SETPCO_ACTION:
5329 + break;
5330 + case MIMO_CHA_MEASURE_ACTION:
5331 + break;
5332 + case HT_INFO_EXCHANGE:
5333 + {
5334 + HT_INFORMATION_OCTET *pHT_info;
5335 +
5336 + pHT_info = (HT_INFORMATION_OCTET *) &Elem->Msg[LENGTH_802_11+2];
5337 + // 7.4.8.10
5338 + DBGPRINT(RT_DEBUG_TRACE,("ACTION - HT Information Exchange action----> \n"));
5339 + if (pHT_info->Request)
5340 + {
5341 + respond_ht_information_exchange_action(pAd, Elem);
5342 + }
5343 + }
5344 + break;
5345 + }
5346 +}
5347 +
5348 +
5349 +/*
5350 + ==========================================================================
5351 + Description:
5352 + Retry sending ADDBA Reqest.
5353 +
5354 + IRQL = DISPATCH_LEVEL
5355 +
5356 + Parametrs:
5357 + p8023Header: if this is already 802.3 format, p8023Header is NULL
5358 +
5359 + Return : TRUE if put into rx reordering buffer, shouldn't indicaterxhere.
5360 + FALSE , then continue indicaterx at this moment.
5361 + ==========================================================================
5362 + */
5363 +VOID ORIBATimerTimeout(
5364 + IN PRTMP_ADAPTER pAd)
5365 +{
5366 + MAC_TABLE_ENTRY *pEntry;
5367 + INT i, total;
5368 + UCHAR TID;
5369 +
5370 +#ifdef RALINK_ATE
5371 + if (ATE_ON(pAd))
5372 + return;
5373 +#endif // RALINK_ATE //
5374 +
5375 + total = pAd->MacTab.Size * NUM_OF_TID;
5376 +
5377 + for (i = 1; ((i <MAX_LEN_OF_BA_ORI_TABLE) && (total > 0)) ; i++)
5378 + {
5379 + if (pAd->BATable.BAOriEntry[i].ORI_BA_Status == Originator_Done)
5380 + {
5381 + pEntry = &pAd->MacTab.Content[pAd->BATable.BAOriEntry[i].Wcid];
5382 + TID = pAd->BATable.BAOriEntry[i].TID;
5383 +
5384 + ASSERT(pAd->BATable.BAOriEntry[i].Wcid < MAX_LEN_OF_MAC_TABLE);
5385 + }
5386 + total --;
5387 + }
5388 +}
5389 +
5390 +
5391 +VOID SendRefreshBAR(
5392 + IN PRTMP_ADAPTER pAd,
5393 + IN MAC_TABLE_ENTRY *pEntry)
5394 +{
5395 + FRAME_BAR FrameBar;
5396 + ULONG FrameLen;
5397 + NDIS_STATUS NStatus;
5398 + PUCHAR pOutBuffer = NULL;
5399 + USHORT Sequence;
5400 + UCHAR i, TID;
5401 + USHORT idx;
5402 + BA_ORI_ENTRY *pBAEntry;
5403 +
5404 + for (i = 0; i <NUM_OF_TID; i++)
5405 + {
5406 + idx = pEntry->BAOriWcidArray[i];
5407 + if (idx == 0)
5408 + {
5409 + continue;
5410 + }
5411 + pBAEntry = &pAd->BATable.BAOriEntry[idx];
5412 +
5413 + if (pBAEntry->ORI_BA_Status == Originator_Done)
5414 + {
5415 + TID = pBAEntry->TID;
5416 +
5417 + ASSERT(pBAEntry->Wcid < MAX_LEN_OF_MAC_TABLE);
5418 +
5419 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
5420 + if(NStatus != NDIS_STATUS_SUCCESS)
5421 + {
5422 + DBGPRINT(RT_DEBUG_ERROR,("BA - MlmeADDBAAction() allocate memory failed \n"));
5423 + return;
5424 + }
5425 +
5426 + Sequence = pEntry->TxSeq[TID];
5427 +#ifdef CONFIG_STA_SUPPORT
5428 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
5429 + BarHeaderInit(pAd, &FrameBar, pEntry->Addr, pAd->CurrentAddress);
5430 +#endif // CONFIG_STA_SUPPORT //
5431 +
5432 + FrameBar.StartingSeq.field.FragNum = 0; // make sure sequence not clear in DEL function.
5433 + FrameBar.StartingSeq.field.StartSeq = Sequence; // make sure sequence not clear in DEL funciton.
5434 + FrameBar.BarControl.TID = TID; // make sure sequence not clear in DEL funciton.
5435 +
5436 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
5437 + sizeof(FRAME_BAR), &FrameBar,
5438 + END_OF_ARGS);
5439 + if (1) // Now we always send BAR.
5440 + {
5441 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
5442 + }
5443 + MlmeFreeMemory(pAd, pOutBuffer);
5444 + }
5445 + }
5446 +}
5447 +#endif // DOT11_N_SUPPORT //
5448 +
5449 +VOID ActHeaderInit(
5450 + IN PRTMP_ADAPTER pAd,
5451 + IN OUT PHEADER_802_11 pHdr80211,
5452 + IN PUCHAR Addr1,
5453 + IN PUCHAR Addr2,
5454 + IN PUCHAR Addr3)
5455 +{
5456 + NdisZeroMemory(pHdr80211, sizeof(HEADER_802_11));
5457 + pHdr80211->FC.Type = BTYPE_MGMT;
5458 + pHdr80211->FC.SubType = SUBTYPE_ACTION;
5459 +
5460 + COPY_MAC_ADDR(pHdr80211->Addr1, Addr1);
5461 + COPY_MAC_ADDR(pHdr80211->Addr2, Addr2);
5462 + COPY_MAC_ADDR(pHdr80211->Addr3, Addr3);
5463 +}
5464 +
5465 +VOID BarHeaderInit(
5466 + IN PRTMP_ADAPTER pAd,
5467 + IN OUT PFRAME_BAR pCntlBar,
5468 + IN PUCHAR pDA,
5469 + IN PUCHAR pSA)
5470 +{
5471 + NdisZeroMemory(pCntlBar, sizeof(FRAME_BAR));
5472 + pCntlBar->FC.Type = BTYPE_CNTL;
5473 + pCntlBar->FC.SubType = SUBTYPE_BLOCK_ACK_REQ;
5474 + pCntlBar->BarControl.MTID = 0;
5475 + pCntlBar->BarControl.Compressed = 1;
5476 + pCntlBar->BarControl.ACKPolicy = 0;
5477 +
5478 +
5479 + pCntlBar->Duration = 16 + RTMPCalcDuration(pAd, RATE_1, sizeof(FRAME_BA));
5480 +
5481 + COPY_MAC_ADDR(pCntlBar->Addr1, pDA);
5482 + COPY_MAC_ADDR(pCntlBar->Addr2, pSA);
5483 +}
5484 +
5485 +
5486 +/*
5487 + ==========================================================================
5488 + Description:
5489 + Insert Category and action code into the action frame.
5490 +
5491 + Parametrs:
5492 + 1. frame buffer pointer.
5493 + 2. frame length.
5494 + 3. category code of the frame.
5495 + 4. action code of the frame.
5496 +
5497 + Return : None.
5498 + ==========================================================================
5499 + */
5500 +VOID InsertActField(
5501 + IN PRTMP_ADAPTER pAd,
5502 + OUT PUCHAR pFrameBuf,
5503 + OUT PULONG pFrameLen,
5504 + IN UINT8 Category,
5505 + IN UINT8 ActCode)
5506 +{
5507 + ULONG TempLen;
5508 +
5509 + MakeOutgoingFrame( pFrameBuf, &TempLen,
5510 + 1, &Category,
5511 + 1, &ActCode,
5512 + END_OF_ARGS);
5513 +
5514 + *pFrameLen = *pFrameLen + TempLen;
5515 +
5516 + return;
5517 +}
5518 --- /dev/null
5519 +++ b/drivers/staging/rt2860/common/action.h
5520 @@ -0,0 +1,68 @@
5521 +/*
5522 + *************************************************************************
5523 + * Ralink Tech Inc.
5524 + * 5F., No.36, Taiyuan St., Jhubei City,
5525 + * Hsinchu County 302,
5526 + * Taiwan, R.O.C.
5527 + *
5528 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
5529 + *
5530 + * This program is free software; you can redistribute it and/or modify *
5531 + * it under the terms of the GNU General Public License as published by *
5532 + * the Free Software Foundation; either version 2 of the License, or *
5533 + * (at your option) any later version. *
5534 + * *
5535 + * This program is distributed in the hope that it will be useful, *
5536 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
5537 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
5538 + * GNU General Public License for more details. *
5539 + * *
5540 + * You should have received a copy of the GNU General Public License *
5541 + * along with this program; if not, write to the *
5542 + * Free Software Foundation, Inc., *
5543 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
5544 + * *
5545 + *************************************************************************
5546 +
5547 + Module Name:
5548 + aironet.h
5549 +
5550 + Abstract:
5551 +
5552 + Revision History:
5553 + Who When What
5554 + -------- ---------- ----------------------------------------------
5555 + Name Date Modification logs
5556 + Paul Lin 04-06-15 Initial
5557 +*/
5558 +
5559 +#ifndef __ACTION_H__
5560 +#define __ACTION_H__
5561 +
5562 +typedef struct PACKED __HT_INFO_OCTET
5563 +{
5564 +#ifdef RT_BIG_ENDIAN
5565 + UCHAR Reserved:5;
5566 + UCHAR STA_Channel_Width:1;
5567 + UCHAR Forty_MHz_Intolerant:1;
5568 + UCHAR Request:1;
5569 +#else
5570 + UCHAR Request:1;
5571 + UCHAR Forty_MHz_Intolerant:1;
5572 + UCHAR STA_Channel_Width:1;
5573 + UCHAR Reserved:5;
5574 +#endif
5575 +} HT_INFORMATION_OCTET;
5576 +
5577 +
5578 +typedef struct PACKED __FRAME_HT_INFO
5579 +{
5580 + HEADER_802_11 Hdr;
5581 + UCHAR Category;
5582 + UCHAR Action;
5583 + HT_INFORMATION_OCTET HT_Info;
5584 +} FRAME_HT_INFO, *PFRAME_HT_INFO;
5585 +
5586 +#endif /* __ACTION_H__ */
5587 +
5588 +
5589 --- /dev/null
5590 +++ b/drivers/staging/rt2860/common/ba_action.c
5591 @@ -0,0 +1,1802 @@
5592 +/*
5593 + *************************************************************************
5594 + * Ralink Tech Inc.
5595 + * 5F., No.36, Taiyuan St., Jhubei City,
5596 + * Hsinchu County 302,
5597 + * Taiwan, R.O.C.
5598 + *
5599 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
5600 + *
5601 + * This program is free software; you can redistribute it and/or modify *
5602 + * it under the terms of the GNU General Public License as published by *
5603 + * the Free Software Foundation; either version 2 of the License, or *
5604 + * (at your option) any later version. *
5605 + * *
5606 + * This program is distributed in the hope that it will be useful, *
5607 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
5608 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
5609 + * GNU General Public License for more details. *
5610 + * *
5611 + * You should have received a copy of the GNU General Public License *
5612 + * along with this program; if not, write to the *
5613 + * Free Software Foundation, Inc., *
5614 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
5615 + * *
5616 + *************************************************************************
5617 + */
5618 +
5619 +#ifdef DOT11_N_SUPPORT
5620 +
5621 +#include "../rt_config.h"
5622 +
5623 +
5624 +
5625 +#define BA_ORI_INIT_SEQ (pEntry->TxSeq[TID]) //1 // inital sequence number of BA session
5626 +
5627 +#define ORI_SESSION_MAX_RETRY 8
5628 +#define ORI_BA_SESSION_TIMEOUT (2000) // ms
5629 +#define REC_BA_SESSION_IDLE_TIMEOUT (1000) // ms
5630 +
5631 +#define REORDERING_PACKET_TIMEOUT ((100 * HZ)/1000) // system ticks -- 100 ms
5632 +#define MAX_REORDERING_PACKET_TIMEOUT ((3000 * HZ)/1000) // system ticks -- 100 ms
5633 +
5634 +#define RESET_RCV_SEQ (0xFFFF)
5635 +
5636 +static void ba_mpdu_blk_free(PRTMP_ADAPTER pAd, struct reordering_mpdu *mpdu_blk);
5637 +
5638 +
5639 +BA_ORI_ENTRY *BATableAllocOriEntry(
5640 + IN PRTMP_ADAPTER pAd,
5641 + OUT USHORT *Idx);
5642 +
5643 +BA_REC_ENTRY *BATableAllocRecEntry(
5644 + IN PRTMP_ADAPTER pAd,
5645 + OUT USHORT *Idx);
5646 +
5647 +VOID BAOriSessionSetupTimeout(
5648 + IN PVOID SystemSpecific1,
5649 + IN PVOID FunctionContext,
5650 + IN PVOID SystemSpecific2,
5651 + IN PVOID SystemSpecific3);
5652 +
5653 +VOID BARecSessionIdleTimeout(
5654 + IN PVOID SystemSpecific1,
5655 + IN PVOID FunctionContext,
5656 + IN PVOID SystemSpecific2,
5657 + IN PVOID SystemSpecific3);
5658 +
5659 +
5660 +BUILD_TIMER_FUNCTION(BAOriSessionSetupTimeout);
5661 +BUILD_TIMER_FUNCTION(BARecSessionIdleTimeout);
5662 +
5663 +#define ANNOUNCE_REORDERING_PACKET(_pAd, _mpdu_blk) \
5664 + Announce_Reordering_Packet(_pAd, _mpdu_blk);
5665 +
5666 +VOID BA_MaxWinSizeReasign(
5667 + IN PRTMP_ADAPTER pAd,
5668 + IN MAC_TABLE_ENTRY *pEntryPeer,
5669 + OUT UCHAR *pWinSize)
5670 +{
5671 + UCHAR MaxSize;
5672 +
5673 +
5674 + if (pAd->MACVersion >= RALINK_2883_VERSION) // 3*3
5675 + {
5676 + if (pAd->MACVersion >= RALINK_3070_VERSION)
5677 + {
5678 + if (pEntryPeer->WepStatus != Ndis802_11EncryptionDisabled)
5679 + MaxSize = 7; // for non-open mode
5680 + else
5681 + MaxSize = 13;
5682 + }
5683 + else
5684 + MaxSize = 31;
5685 + }
5686 + else if (pAd->MACVersion >= RALINK_2880E_VERSION) // 2880 e
5687 + {
5688 + if (pEntryPeer->WepStatus != Ndis802_11EncryptionDisabled)
5689 + MaxSize = 7; // for non-open mode
5690 + else
5691 + MaxSize = 13;
5692 + }
5693 + else
5694 + MaxSize = 7;
5695 +
5696 + DBGPRINT(RT_DEBUG_TRACE, ("ba> Win Size = %d, Max Size = %d\n",
5697 + *pWinSize, MaxSize));
5698 +
5699 + if ((*pWinSize) > MaxSize)
5700 + {
5701 + DBGPRINT(RT_DEBUG_TRACE, ("ba> reassign max win size from %d to %d\n",
5702 + *pWinSize, MaxSize));
5703 +
5704 + *pWinSize = MaxSize;
5705 + }
5706 +}
5707 +
5708 +void Announce_Reordering_Packet(IN PRTMP_ADAPTER pAd,
5709 + IN struct reordering_mpdu *mpdu)
5710 +{
5711 + PNDIS_PACKET pPacket;
5712 +
5713 + pPacket = mpdu->pPacket;
5714 +
5715 + if (mpdu->bAMSDU)
5716 + {
5717 + ASSERT(0);
5718 + BA_Reorder_AMSDU_Annnounce(pAd, pPacket);
5719 + }
5720 + else
5721 + {
5722 + //
5723 + // pass this 802.3 packet to upper layer or forward this packet to WM directly
5724 + //
5725 +
5726 +#ifdef CONFIG_STA_SUPPORT
5727 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
5728 + ANNOUNCE_OR_FORWARD_802_3_PACKET(pAd, pPacket, RTMP_GET_PACKET_IF(pPacket));
5729 +#endif // CONFIG_STA_SUPPORT //
5730 + }
5731 +}
5732 +
5733 +/*
5734 + * Insert a reordering mpdu into sorted linked list by sequence no.
5735 + */
5736 +BOOLEAN ba_reordering_mpdu_insertsorted(struct reordering_list *list, struct reordering_mpdu *mpdu)
5737 +{
5738 +
5739 + struct reordering_mpdu **ppScan = &list->next;
5740 +
5741 + while (*ppScan != NULL)
5742 + {
5743 + if (SEQ_SMALLER((*ppScan)->Sequence, mpdu->Sequence, MAXSEQ))
5744 + {
5745 + ppScan = &(*ppScan)->next;
5746 + }
5747 + else if ((*ppScan)->Sequence == mpdu->Sequence)
5748 + {
5749 + /* give up this duplicated frame */
5750 + return(FALSE);
5751 + }
5752 + else
5753 + {
5754 + /* find position */
5755 + break;
5756 + }
5757 + }
5758 +
5759 + mpdu->next = *ppScan;
5760 + *ppScan = mpdu;
5761 + list->qlen++;
5762 + return TRUE;
5763 +}
5764 +
5765 +
5766 +/*
5767 + * caller lock critical section if necessary
5768 + */
5769 +static inline void ba_enqueue(struct reordering_list *list, struct reordering_mpdu *mpdu_blk)
5770 +{
5771 + list->qlen++;
5772 + mpdu_blk->next = list->next;
5773 + list->next = mpdu_blk;
5774 +}
5775 +
5776 +/*
5777 + * caller lock critical section if necessary
5778 + */
5779 +static inline struct reordering_mpdu * ba_dequeue(struct reordering_list *list)
5780 +{
5781 + struct reordering_mpdu *mpdu_blk = NULL;
5782 +
5783 + ASSERT(list);
5784 +
5785 + if (list->qlen)
5786 + {
5787 + list->qlen--;
5788 + mpdu_blk = list->next;
5789 + if (mpdu_blk)
5790 + {
5791 + list->next = mpdu_blk->next;
5792 + mpdu_blk->next = NULL;
5793 + }
5794 + }
5795 + return mpdu_blk;
5796 +}
5797 +
5798 +
5799 +static inline struct reordering_mpdu *ba_reordering_mpdu_dequeue(struct reordering_list *list)
5800 +{
5801 + return(ba_dequeue(list));
5802 +}
5803 +
5804 +
5805 +static inline struct reordering_mpdu *ba_reordering_mpdu_probe(struct reordering_list *list)
5806 + {
5807 + ASSERT(list);
5808 +
5809 + return(list->next);
5810 + }
5811 +
5812 +
5813 +/*
5814 + * free all resource for reordering mechanism
5815 + */
5816 +void ba_reordering_resource_release(PRTMP_ADAPTER pAd)
5817 +{
5818 + BA_TABLE *Tab;
5819 + PBA_REC_ENTRY pBAEntry;
5820 + struct reordering_mpdu *mpdu_blk;
5821 + int i;
5822 +
5823 + Tab = &pAd->BATable;
5824 +
5825 + /* I. release all pending reordering packet */
5826 + NdisAcquireSpinLock(&pAd->BATabLock);
5827 + for (i = 0; i < MAX_LEN_OF_BA_REC_TABLE; i++)
5828 + {
5829 + pBAEntry = &Tab->BARecEntry[i];
5830 + if (pBAEntry->REC_BA_Status != Recipient_NONE)
5831 + {
5832 + while ((mpdu_blk = ba_reordering_mpdu_dequeue(&pBAEntry->list)))
5833 + {
5834 + ASSERT(mpdu_blk->pPacket);
5835 + RELEASE_NDIS_PACKET(pAd, mpdu_blk->pPacket, NDIS_STATUS_FAILURE);
5836 + ba_mpdu_blk_free(pAd, mpdu_blk);
5837 + }
5838 + }
5839 + }
5840 + NdisReleaseSpinLock(&pAd->BATabLock);
5841 +
5842 + ASSERT(pBAEntry->list.qlen == 0);
5843 + /* II. free memory of reordering mpdu table */
5844 + NdisAcquireSpinLock(&pAd->mpdu_blk_pool.lock);
5845 + os_free_mem(pAd, pAd->mpdu_blk_pool.mem);
5846 + NdisReleaseSpinLock(&pAd->mpdu_blk_pool.lock);
5847 +}
5848 +
5849 +
5850 +
5851 +/*
5852 + * Allocate all resource for reordering mechanism
5853 + */
5854 +BOOLEAN ba_reordering_resource_init(PRTMP_ADAPTER pAd, int num)
5855 +{
5856 + int i;
5857 + PUCHAR mem;
5858 + struct reordering_mpdu *mpdu_blk;
5859 + struct reordering_list *freelist;
5860 +
5861 + /* allocate spinlock */
5862 + NdisAllocateSpinLock(&pAd->mpdu_blk_pool.lock);
5863 +
5864 + /* initialize freelist */
5865 + freelist = &pAd->mpdu_blk_pool.freelist;
5866 + freelist->next = NULL;
5867 + freelist->qlen = 0;
5868 +
5869 + DBGPRINT(RT_DEBUG_TRACE, ("Allocate %d memory for BA reordering\n", (UINT32)(num*sizeof(struct reordering_mpdu))));
5870 +
5871 + /* allocate number of mpdu_blk memory */
5872 + os_alloc_mem(pAd, (PUCHAR *)&mem, (num*sizeof(struct reordering_mpdu)));
5873 +
5874 + pAd->mpdu_blk_pool.mem = mem;
5875 +
5876 + if (mem == NULL)
5877 + {
5878 + DBGPRINT(RT_DEBUG_ERROR, ("Can't Allocate Memory for BA Reordering\n"));
5879 + return(FALSE);
5880 + }
5881 +
5882 + /* build mpdu_blk free list */
5883 + for (i=0; i<num; i++)
5884 + {
5885 + /* get mpdu_blk */
5886 + mpdu_blk = (struct reordering_mpdu *) mem;
5887 + /* initial mpdu_blk */
5888 + NdisZeroMemory(mpdu_blk, sizeof(struct reordering_mpdu));
5889 + /* next mpdu_blk */
5890 + mem += sizeof(struct reordering_mpdu);
5891 + /* insert mpdu_blk into freelist */
5892 + ba_enqueue(freelist, mpdu_blk);
5893 + }
5894 +
5895 + return(TRUE);
5896 +}
5897 +
5898 +//static int blk_count=0; // sample take off, no use
5899 +
5900 +static struct reordering_mpdu *ba_mpdu_blk_alloc(PRTMP_ADAPTER pAd)
5901 +{
5902 + struct reordering_mpdu *mpdu_blk;
5903 +
5904 + NdisAcquireSpinLock(&pAd->mpdu_blk_pool.lock);
5905 + mpdu_blk = ba_dequeue(&pAd->mpdu_blk_pool.freelist);
5906 + if (mpdu_blk)
5907 + {
5908 +// blk_count++;
5909 + /* reset mpdu_blk */
5910 + NdisZeroMemory(mpdu_blk, sizeof(struct reordering_mpdu));
5911 + }
5912 + NdisReleaseSpinLock(&pAd->mpdu_blk_pool.lock);
5913 + return mpdu_blk;
5914 +}
5915 +
5916 +static void ba_mpdu_blk_free(PRTMP_ADAPTER pAd, struct reordering_mpdu *mpdu_blk)
5917 +{
5918 + ASSERT(mpdu_blk);
5919 +
5920 + NdisAcquireSpinLock(&pAd->mpdu_blk_pool.lock);
5921 +// blk_count--;
5922 + ba_enqueue(&pAd->mpdu_blk_pool.freelist, mpdu_blk);
5923 + NdisReleaseSpinLock(&pAd->mpdu_blk_pool.lock);
5924 +}
5925 +
5926 +
5927 +static USHORT ba_indicate_reordering_mpdus_in_order(
5928 + IN PRTMP_ADAPTER pAd,
5929 + IN PBA_REC_ENTRY pBAEntry,
5930 + IN USHORT StartSeq)
5931 +{
5932 + struct reordering_mpdu *mpdu_blk;
5933 + USHORT LastIndSeq = RESET_RCV_SEQ;
5934 +
5935 + NdisAcquireSpinLock(&pBAEntry->RxReRingLock);
5936 +
5937 + while ((mpdu_blk = ba_reordering_mpdu_probe(&pBAEntry->list)))
5938 + {
5939 + /* find in-order frame */
5940 + if (!SEQ_STEPONE(mpdu_blk->Sequence, StartSeq, MAXSEQ))
5941 + {
5942 + break;
5943 + }
5944 + /* dequeue in-order frame from reodering list */
5945 + mpdu_blk = ba_reordering_mpdu_dequeue(&pBAEntry->list);
5946 + /* pass this frame up */
5947 + ANNOUNCE_REORDERING_PACKET(pAd, mpdu_blk);
5948 + /* move to next sequence */
5949 + StartSeq = mpdu_blk->Sequence;
5950 + LastIndSeq = StartSeq;
5951 + /* free mpdu_blk */
5952 + ba_mpdu_blk_free(pAd, mpdu_blk);
5953 + }
5954 +
5955 + NdisReleaseSpinLock(&pBAEntry->RxReRingLock);
5956 +
5957 + /* update last indicated sequence */
5958 + return LastIndSeq;
5959 +}
5960 +
5961 +static void ba_indicate_reordering_mpdus_le_seq(
5962 + IN PRTMP_ADAPTER pAd,
5963 + IN PBA_REC_ENTRY pBAEntry,
5964 + IN USHORT Sequence)
5965 +{
5966 + struct reordering_mpdu *mpdu_blk;
5967 +
5968 + NdisAcquireSpinLock(&pBAEntry->RxReRingLock);
5969 + while ((mpdu_blk = ba_reordering_mpdu_probe(&pBAEntry->list)))
5970 + {
5971 + /* find in-order frame */
5972 + if ((mpdu_blk->Sequence == Sequence) || SEQ_SMALLER(mpdu_blk->Sequence, Sequence, MAXSEQ))
5973 + {
5974 + /* dequeue in-order frame from reodering list */
5975 + mpdu_blk = ba_reordering_mpdu_dequeue(&pBAEntry->list);
5976 + /* pass this frame up */
5977 + ANNOUNCE_REORDERING_PACKET(pAd, mpdu_blk);
5978 + /* free mpdu_blk */
5979 + ba_mpdu_blk_free(pAd, mpdu_blk);
5980 + }
5981 + else
5982 + {
5983 + break;
5984 + }
5985 + }
5986 + NdisReleaseSpinLock(&pBAEntry->RxReRingLock);
5987 +}
5988 +
5989 +
5990 +static void ba_refresh_reordering_mpdus(
5991 + IN PRTMP_ADAPTER pAd,
5992 + PBA_REC_ENTRY pBAEntry)
5993 +{
5994 + struct reordering_mpdu *mpdu_blk;
5995 +
5996 + NdisAcquireSpinLock(&pBAEntry->RxReRingLock);
5997 +
5998 + /* dequeue in-order frame from reodering list */
5999 + while ((mpdu_blk = ba_reordering_mpdu_dequeue(&pBAEntry->list)))
6000 + {
6001 + /* pass this frame up */
6002 + ANNOUNCE_REORDERING_PACKET(pAd, mpdu_blk);
6003 +
6004 + pBAEntry->LastIndSeq = mpdu_blk->Sequence;
6005 + ba_mpdu_blk_free(pAd, mpdu_blk);
6006 +
6007 + /* update last indicated sequence */
6008 + }
6009 + ASSERT(pBAEntry->list.qlen == 0);
6010 + pBAEntry->LastIndSeq = RESET_RCV_SEQ;
6011 + NdisReleaseSpinLock(&pBAEntry->RxReRingLock);
6012 +}
6013 +
6014 +
6015 +//static
6016 +void ba_flush_reordering_timeout_mpdus(
6017 + IN PRTMP_ADAPTER pAd,
6018 + IN PBA_REC_ENTRY pBAEntry,
6019 + IN ULONG Now32)
6020 +
6021 +{
6022 + USHORT Sequence;
6023 +
6024 +// if ((RTMP_TIME_AFTER((unsigned long)Now32, (unsigned long)(pBAEntry->LastIndSeqAtTimer+REORDERING_PACKET_TIMEOUT)) &&
6025 +// (pBAEntry->list.qlen > ((pBAEntry->BAWinSize*7)/8))) //||
6026 +// (RTMP_TIME_AFTER((unsigned long)Now32, (unsigned long)(pBAEntry->LastIndSeqAtTimer+(10*REORDERING_PACKET_TIMEOUT))) &&
6027 +// (pBAEntry->list.qlen > (pBAEntry->BAWinSize/8)))
6028 + if (RTMP_TIME_AFTER((unsigned long)Now32, (unsigned long)(pBAEntry->LastIndSeqAtTimer+(MAX_REORDERING_PACKET_TIMEOUT/6)))
6029 + &&(pBAEntry->list.qlen > 1)
6030 + )
6031 + {
6032 + DBGPRINT(RT_DEBUG_TRACE,("timeout[%d] (%08lx-%08lx = %d > %d): %x, flush all!\n ", pBAEntry->list.qlen, Now32, (pBAEntry->LastIndSeqAtTimer),
6033 + (int)((long) Now32 - (long)(pBAEntry->LastIndSeqAtTimer)), MAX_REORDERING_PACKET_TIMEOUT,
6034 + pBAEntry->LastIndSeq));
6035 + ba_refresh_reordering_mpdus(pAd, pBAEntry);
6036 + pBAEntry->LastIndSeqAtTimer = Now32;
6037 + }
6038 + else
6039 + if (RTMP_TIME_AFTER((unsigned long)Now32, (unsigned long)(pBAEntry->LastIndSeqAtTimer+(REORDERING_PACKET_TIMEOUT)))
6040 + && (pBAEntry->list.qlen > 0)
6041 + )
6042 + {
6043 +// printk("timeout[%d] (%lx-%lx = %d > %d): %x, ", pBAEntry->list.qlen, Now32, (pBAEntry->LastIndSeqAtTimer),
6044 +// (int)((long) Now32 - (long)(pBAEntry->LastIndSeqAtTimer)), REORDERING_PACKET_TIMEOUT,
6045 +// pBAEntry->LastIndSeq);
6046 + //
6047 + // force LastIndSeq to shift to LastIndSeq+1
6048 + //
6049 + Sequence = (pBAEntry->LastIndSeq+1) & MAXSEQ;
6050 + ba_indicate_reordering_mpdus_le_seq(pAd, pBAEntry, Sequence);
6051 + pBAEntry->LastIndSeqAtTimer = Now32;
6052 + pBAEntry->LastIndSeq = Sequence;
6053 + //
6054 + // indicate in-order mpdus
6055 + //
6056 + Sequence = ba_indicate_reordering_mpdus_in_order(pAd, pBAEntry, Sequence);
6057 + if (Sequence != RESET_RCV_SEQ)
6058 + {
6059 + pBAEntry->LastIndSeq = Sequence;
6060 + }
6061 +
6062 + //printk("%x, flush one!\n", pBAEntry->LastIndSeq);
6063 +
6064 + }
6065 +#if 0
6066 + else if (
6067 + (RTMP_TIME_AFTER((unsigned long)Now32, (unsigned long)(pBAEntry->LastIndSeqAtTimer+(MAX_REORDERING_PACKET_TIMEOUT))) &&
6068 + (pBAEntry->list.qlen > 1))
6069 + )
6070 + {
6071 + DBGPRINT(RT_DEBUG_TRACE,("timeout[%d] (%lx-%lx = %d > %d): %x\n ", pBAEntry->list.qlen, Now32, (pBAEntry->LastIndSeqAtTimer),
6072 + (int)((long) Now32 - (long)(pBAEntry->LastIndSeqAtTimer)), MAX_REORDERING_PACKET_TIMEOUT,
6073 + pBAEntry->LastIndSeq));
6074 + ba_refresh_reordering_mpdus(pAd, pBAEntry);
6075 + pBAEntry->LastIndSeqAtTimer = Now32;
6076 + }
6077 +#endif
6078 +}
6079 +
6080 +
6081 +/*
6082 + * generate ADDBA request to
6083 + * set up BA agreement
6084 + */
6085 +VOID BAOriSessionSetUp(
6086 + IN PRTMP_ADAPTER pAd,
6087 + IN MAC_TABLE_ENTRY *pEntry,
6088 + IN UCHAR TID,
6089 + IN USHORT TimeOut,
6090 + IN ULONG DelayTime,
6091 + IN BOOLEAN isForced)
6092 +
6093 +{
6094 + //MLME_ADDBA_REQ_STRUCT AddbaReq;
6095 + BA_ORI_ENTRY *pBAEntry = NULL;
6096 + USHORT Idx;
6097 + BOOLEAN Cancelled;
6098 +
6099 + if ((pAd->CommonCfg.BACapability.field.AutoBA != TRUE) && (isForced == FALSE))
6100 + return;
6101 +
6102 + // if this entry is limited to use legacy tx mode, it doesn't generate BA.
6103 + if (RTMPStaFixedTxMode(pAd, pEntry) != FIXED_TXMODE_HT)
6104 + return;
6105 +
6106 + if ((pEntry->BADeclineBitmap & (1<<TID)) && (isForced == FALSE))
6107 + {
6108 + // try again after 3 secs
6109 + DelayTime = 3000;
6110 +// printk("DeCline BA from Peer\n");
6111 +// return;
6112 + }
6113 +
6114 +
6115 + Idx = pEntry->BAOriWcidArray[TID];
6116 + if (Idx == 0)
6117 + {
6118 + // allocate a BA session
6119 + pBAEntry = BATableAllocOriEntry(pAd, &Idx);
6120 + if (pBAEntry == NULL)
6121 + {
6122 + DBGPRINT(RT_DEBUG_TRACE,("ADDBA - MlmeADDBAAction() allocate BA session failed \n"));
6123 + return;
6124 + }
6125 + }
6126 + else
6127 + {
6128 + pBAEntry =&pAd->BATable.BAOriEntry[Idx];
6129 + }
6130 +
6131 + if (pBAEntry->ORI_BA_Status >= Originator_WaitRes)
6132 + {
6133 + return;
6134 + }
6135 +
6136 + pEntry->BAOriWcidArray[TID] = Idx;
6137 +
6138 + // Initialize BA session
6139 + pBAEntry->ORI_BA_Status = Originator_WaitRes;
6140 + pBAEntry->Wcid = pEntry->Aid;
6141 + pBAEntry->BAWinSize = pAd->CommonCfg.BACapability.field.RxBAWinLimit;
6142 + pBAEntry->Sequence = BA_ORI_INIT_SEQ;
6143 + pBAEntry->Token = 1; // (2008-01-21) Jan Lee recommends it - this token can't be 0
6144 + pBAEntry->TID = TID;
6145 + pBAEntry->TimeOutValue = TimeOut;
6146 + pBAEntry->pAdapter = pAd;
6147 +
6148 + if (!(pEntry->TXBAbitmap & (1<<TID)))
6149 + {
6150 + RTMPInitTimer(pAd, &pBAEntry->ORIBATimer, GET_TIMER_FUNCTION(BAOriSessionSetupTimeout), pBAEntry, FALSE);
6151 + }
6152 + else
6153 + RTMPCancelTimer(&pBAEntry->ORIBATimer, &Cancelled);
6154 +
6155 + // set timer to send ADDBA request
6156 + RTMPSetTimer(&pBAEntry->ORIBATimer, DelayTime);
6157 +}
6158 +
6159 +VOID BAOriSessionAdd(
6160 + IN PRTMP_ADAPTER pAd,
6161 + IN MAC_TABLE_ENTRY *pEntry,
6162 + IN PFRAME_ADDBA_RSP pFrame)
6163 +{
6164 + BA_ORI_ENTRY *pBAEntry = NULL;
6165 + BOOLEAN Cancelled;
6166 + UCHAR TID;
6167 + USHORT Idx;
6168 + PUCHAR pOutBuffer2 = NULL;
6169 + NDIS_STATUS NStatus;
6170 + ULONG FrameLen;
6171 + FRAME_BAR FrameBar;
6172 +
6173 + TID = pFrame->BaParm.TID;
6174 + Idx = pEntry->BAOriWcidArray[TID];
6175 + pBAEntry =&pAd->BATable.BAOriEntry[Idx];
6176 +
6177 + // Start fill in parameters.
6178 + if ((Idx !=0) && (pBAEntry->TID == TID) && (pBAEntry->ORI_BA_Status == Originator_WaitRes))
6179 + {
6180 + pBAEntry->BAWinSize = min(pBAEntry->BAWinSize, ((UCHAR)pFrame->BaParm.BufSize));
6181 + BA_MaxWinSizeReasign(pAd, pEntry, &pBAEntry->BAWinSize);
6182 +
6183 + pBAEntry->TimeOutValue = pFrame->TimeOutValue;
6184 + pBAEntry->ORI_BA_Status = Originator_Done;
6185 + // reset sequence number
6186 + pBAEntry->Sequence = BA_ORI_INIT_SEQ;
6187 + // Set Bitmap flag.
6188 + pEntry->TXBAbitmap |= (1<<TID);
6189 + RTMPCancelTimer(&pBAEntry->ORIBATimer, &Cancelled);
6190 +
6191 + pBAEntry->ORIBATimer.TimerValue = 0; //pFrame->TimeOutValue;
6192 +
6193 + DBGPRINT(RT_DEBUG_TRACE,("%s : TXBAbitmap = %x, BAWinSize = %d, TimeOut = %ld\n", __FUNCTION__, pEntry->TXBAbitmap,
6194 + pBAEntry->BAWinSize, pBAEntry->ORIBATimer.TimerValue));
6195 +
6196 + // SEND BAR ;
6197 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer2); //Get an unused nonpaged memory
6198 + if (NStatus != NDIS_STATUS_SUCCESS)
6199 + {
6200 + DBGPRINT(RT_DEBUG_TRACE,("BA - BAOriSessionAdd() allocate memory failed \n"));
6201 + return;
6202 + }
6203 +
6204 +
6205 +#ifdef CONFIG_STA_SUPPORT
6206 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
6207 + BarHeaderInit(pAd, &FrameBar, pAd->MacTab.Content[pBAEntry->Wcid].Addr, pAd->CurrentAddress);
6208 +#endif // CONFIG_STA_SUPPORT //
6209 +
6210 + FrameBar.StartingSeq.field.FragNum = 0; // make sure sequence not clear in DEL function.
6211 + FrameBar.StartingSeq.field.StartSeq = pBAEntry->Sequence; // make sure sequence not clear in DEL funciton.
6212 + FrameBar.BarControl.TID = pBAEntry->TID; // make sure sequence not clear in DEL funciton.
6213 + MakeOutgoingFrame(pOutBuffer2, &FrameLen,
6214 + sizeof(FRAME_BAR), &FrameBar,
6215 + END_OF_ARGS);
6216 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer2, FrameLen);
6217 + MlmeFreeMemory(pAd, pOutBuffer2);
6218 +
6219 +
6220 + if (pBAEntry->ORIBATimer.TimerValue)
6221 + RTMPSetTimer(&pBAEntry->ORIBATimer, pBAEntry->ORIBATimer.TimerValue); // in mSec
6222 + }
6223 +}
6224 +
6225 +BOOLEAN BARecSessionAdd(
6226 + IN PRTMP_ADAPTER pAd,
6227 + IN MAC_TABLE_ENTRY *pEntry,
6228 + IN PFRAME_ADDBA_REQ pFrame)
6229 +{
6230 + BA_REC_ENTRY *pBAEntry = NULL;
6231 + BOOLEAN Status = TRUE;
6232 + BOOLEAN Cancelled;
6233 + USHORT Idx;
6234 + UCHAR TID;
6235 + UCHAR BAWinSize;
6236 + //UINT32 Value;
6237 + //UINT offset;
6238 +
6239 +
6240 + ASSERT(pEntry);
6241 +
6242 + // find TID
6243 + TID = pFrame->BaParm.TID;
6244 +
6245 + BAWinSize = min(((UCHAR)pFrame->BaParm.BufSize), (UCHAR)pAd->CommonCfg.BACapability.field.RxBAWinLimit);
6246 +
6247 + // Intel patch
6248 + if (BAWinSize == 0)
6249 + {
6250 + BAWinSize = 64;
6251 + }
6252 +
6253 + Idx = pEntry->BARecWcidArray[TID];
6254 +
6255 +
6256 + if (Idx == 0)
6257 + {
6258 + pBAEntry = BATableAllocRecEntry(pAd, &Idx);
6259 + }
6260 + else
6261 + {
6262 + pBAEntry = &pAd->BATable.BARecEntry[Idx];
6263 + // flush all pending reordering mpdus
6264 + ba_refresh_reordering_mpdus(pAd, pBAEntry);
6265 + }
6266 +
6267 + DBGPRINT(RT_DEBUG_TRACE,("%s(%ld): Idx = %d, BAWinSize(req %d) = %d\n", __FUNCTION__, pAd->BATable.numAsRecipient, Idx,
6268 + pFrame->BaParm.BufSize, BAWinSize));
6269 +
6270 + // Start fill in parameters.
6271 + if (pBAEntry != NULL)
6272 + {
6273 + ASSERT(pBAEntry->list.qlen == 0);
6274 +
6275 + pBAEntry->REC_BA_Status = Recipient_HandleRes;
6276 + pBAEntry->BAWinSize = BAWinSize;
6277 + pBAEntry->Wcid = pEntry->Aid;
6278 + pBAEntry->TID = TID;
6279 + pBAEntry->TimeOutValue = pFrame->TimeOutValue;
6280 + pBAEntry->REC_BA_Status = Recipient_Accept;
6281 + // initial sequence number
6282 + pBAEntry->LastIndSeq = RESET_RCV_SEQ; //pFrame->BaStartSeq.field.StartSeq;
6283 +
6284 + printk("Start Seq = %08x\n", pFrame->BaStartSeq.field.StartSeq);
6285 +
6286 + if (pEntry->RXBAbitmap & (1<<TID))
6287 + {
6288 + RTMPCancelTimer(&pBAEntry->RECBATimer, &Cancelled);
6289 + }
6290 + else
6291 + {
6292 + RTMPInitTimer(pAd, &pBAEntry->RECBATimer, GET_TIMER_FUNCTION(BARecSessionIdleTimeout), pBAEntry, TRUE);
6293 + }
6294 +
6295 +#if 0 // for debugging
6296 + RTMPSetTimer(&pBAEntry->RECBATimer, REC_BA_SESSION_IDLE_TIMEOUT);
6297 +#endif
6298 +
6299 + // Set Bitmap flag.
6300 + pEntry->RXBAbitmap |= (1<<TID);
6301 + pEntry->BARecWcidArray[TID] = Idx;
6302 +
6303 + pEntry->BADeclineBitmap &= ~(1<<TID);
6304 +
6305 + // Set BA session mask in WCID table.
6306 + RT28XX_ADD_BA_SESSION_TO_ASIC(pAd, pEntry->Aid, TID);
6307 +
6308 + DBGPRINT(RT_DEBUG_TRACE,("MACEntry[%d]RXBAbitmap = 0x%x. BARecWcidArray=%d\n",
6309 + pEntry->Aid, pEntry->RXBAbitmap, pEntry->BARecWcidArray[TID]));
6310 + }
6311 + else
6312 + {
6313 + Status = FALSE;
6314 + DBGPRINT(RT_DEBUG_TRACE,("Can't Accept ADDBA for %02x:%02x:%02x:%02x:%02x:%02x TID = %d\n",
6315 + PRINT_MAC(pEntry->Addr), TID));
6316 + }
6317 + return(Status);
6318 +}
6319 +
6320 +
6321 +BA_REC_ENTRY *BATableAllocRecEntry(
6322 + IN PRTMP_ADAPTER pAd,
6323 + OUT USHORT *Idx)
6324 +{
6325 + int i;
6326 + BA_REC_ENTRY *pBAEntry = NULL;
6327 +
6328 +
6329 + NdisAcquireSpinLock(&pAd->BATabLock);
6330 +
6331 + if (pAd->BATable.numAsRecipient >= MAX_BARECI_SESSION)
6332 + {
6333 + printk("BA Recipeint Session (%ld) > %d\n", pAd->BATable.numAsRecipient,
6334 + MAX_BARECI_SESSION);
6335 + goto done;
6336 + }
6337 +
6338 + // reserve idx 0 to identify BAWcidArray[TID] as empty
6339 + for (i=1; i < MAX_LEN_OF_BA_REC_TABLE; i++)
6340 + {
6341 + pBAEntry =&pAd->BATable.BARecEntry[i];
6342 + if ((pBAEntry->REC_BA_Status == Recipient_NONE))
6343 + {
6344 + // get one
6345 + pAd->BATable.numAsRecipient++;
6346 + pBAEntry->REC_BA_Status = Recipient_USED;
6347 + *Idx = i;
6348 + break;
6349 + }
6350 + }
6351 +
6352 +done:
6353 + NdisReleaseSpinLock(&pAd->BATabLock);
6354 + return pBAEntry;
6355 +}
6356 +
6357 +BA_ORI_ENTRY *BATableAllocOriEntry(
6358 + IN PRTMP_ADAPTER pAd,
6359 + OUT USHORT *Idx)
6360 +{
6361 + int i;
6362 + BA_ORI_ENTRY *pBAEntry = NULL;
6363 +
6364 + NdisAcquireSpinLock(&pAd->BATabLock);
6365 +
6366 + if (pAd->BATable.numAsOriginator >= (MAX_LEN_OF_BA_ORI_TABLE))
6367 + {
6368 + goto done;
6369 + }
6370 +
6371 + // reserve idx 0 to identify BAWcidArray[TID] as empty
6372 + for (i=1; i<MAX_LEN_OF_BA_ORI_TABLE; i++)
6373 + {
6374 + pBAEntry =&pAd->BATable.BAOriEntry[i];
6375 + if ((pBAEntry->ORI_BA_Status == Originator_NONE))
6376 + {
6377 + // get one
6378 + pAd->BATable.numAsOriginator++;
6379 + pBAEntry->ORI_BA_Status = Originator_USED;
6380 + pBAEntry->pAdapter = pAd;
6381 + *Idx = i;
6382 + break;
6383 + }
6384 + }
6385 +
6386 +done:
6387 + NdisReleaseSpinLock(&pAd->BATabLock);
6388 + return pBAEntry;
6389 +}
6390 +
6391 +
6392 +VOID BATableFreeOriEntry(
6393 + IN PRTMP_ADAPTER pAd,
6394 + IN ULONG Idx)
6395 +{
6396 + BA_ORI_ENTRY *pBAEntry = NULL;
6397 + MAC_TABLE_ENTRY *pEntry;
6398 +
6399 +
6400 + if ((Idx == 0) || (Idx >= MAX_LEN_OF_BA_ORI_TABLE))
6401 + return;
6402 +
6403 + pBAEntry =&pAd->BATable.BAOriEntry[Idx];
6404 +
6405 + if (pBAEntry->ORI_BA_Status != Originator_NONE)
6406 + {
6407 + pEntry = &pAd->MacTab.Content[pBAEntry->Wcid];
6408 + pEntry->BAOriWcidArray[pBAEntry->TID] = 0;
6409 +
6410 +
6411 + NdisAcquireSpinLock(&pAd->BATabLock);
6412 + if (pBAEntry->ORI_BA_Status == Originator_Done)
6413 + {
6414 + pEntry->TXBAbitmap &= (~(1<<(pBAEntry->TID) ));
6415 + DBGPRINT(RT_DEBUG_TRACE, ("BATableFreeOriEntry numAsOriginator= %ld\n", pAd->BATable.numAsRecipient));
6416 + // Erase Bitmap flag.
6417 + }
6418 +
6419 + ASSERT(pAd->BATable.numAsOriginator != 0);
6420 +
6421 + pAd->BATable.numAsOriginator -= 1;
6422 +
6423 + pBAEntry->ORI_BA_Status = Originator_NONE;
6424 + pBAEntry->Token = 0;
6425 + NdisReleaseSpinLock(&pAd->BATabLock);
6426 + }
6427 +}
6428 +
6429 +
6430 +VOID BATableFreeRecEntry(
6431 + IN PRTMP_ADAPTER pAd,
6432 + IN ULONG Idx)
6433 +{
6434 + BA_REC_ENTRY *pBAEntry = NULL;
6435 + MAC_TABLE_ENTRY *pEntry;
6436 +
6437 +
6438 + if ((Idx == 0) || (Idx >= MAX_LEN_OF_BA_REC_TABLE))
6439 + return;
6440 +
6441 + pBAEntry =&pAd->BATable.BARecEntry[Idx];
6442 +
6443 + if (pBAEntry->REC_BA_Status != Recipient_NONE)
6444 + {
6445 + pEntry = &pAd->MacTab.Content[pBAEntry->Wcid];
6446 + pEntry->BARecWcidArray[pBAEntry->TID] = 0;
6447 +
6448 + NdisAcquireSpinLock(&pAd->BATabLock);
6449 +
6450 + ASSERT(pAd->BATable.numAsRecipient != 0);
6451 +
6452 + pAd->BATable.numAsRecipient -= 1;
6453 +
6454 + pBAEntry->REC_BA_Status = Recipient_NONE;
6455 + NdisReleaseSpinLock(&pAd->BATabLock);
6456 + }
6457 +}
6458 +
6459 +
6460 +VOID BAOriSessionTearDown(
6461 + IN OUT PRTMP_ADAPTER pAd,
6462 + IN UCHAR Wcid,
6463 + IN UCHAR TID,
6464 + IN BOOLEAN bPassive,
6465 + IN BOOLEAN bForceSend)
6466 +{
6467 + ULONG Idx = 0;
6468 + BA_ORI_ENTRY *pBAEntry;
6469 + BOOLEAN Cancelled;
6470 +
6471 + if (Wcid >= MAX_LEN_OF_MAC_TABLE)
6472 + {
6473 + return;
6474 + }
6475 +
6476 + //
6477 + // Locate corresponding BA Originator Entry in BA Table with the (pAddr,TID).
6478 + //
6479 + Idx = pAd->MacTab.Content[Wcid].BAOriWcidArray[TID];
6480 + if ((Idx == 0) || (Idx >= MAX_LEN_OF_BA_ORI_TABLE))
6481 + {
6482 + if (bForceSend == TRUE)
6483 + {
6484 + // force send specified TID DelBA
6485 + MLME_DELBA_REQ_STRUCT DelbaReq;
6486 + MLME_QUEUE_ELEM *Elem = (MLME_QUEUE_ELEM *) kmalloc(sizeof(MLME_QUEUE_ELEM), MEM_ALLOC_FLAG);
6487 +
6488 + NdisZeroMemory(&DelbaReq, sizeof(DelbaReq));
6489 + NdisZeroMemory(Elem, sizeof(MLME_QUEUE_ELEM));
6490 +
6491 + COPY_MAC_ADDR(DelbaReq.Addr, pAd->MacTab.Content[Wcid].Addr);
6492 + DelbaReq.Wcid = Wcid;
6493 + DelbaReq.TID = TID;
6494 + DelbaReq.Initiator = ORIGINATOR;
6495 +#if 1
6496 + Elem->MsgLen = sizeof(DelbaReq);
6497 + NdisMoveMemory(Elem->Msg, &DelbaReq, sizeof(DelbaReq));
6498 + MlmeDELBAAction(pAd, Elem);
6499 + kfree(Elem);
6500 +#else
6501 + MlmeEnqueue(pAd, ACTION_STATE_MACHINE, MT2_MLME_ORI_DELBA_CATE, sizeof(MLME_DELBA_REQ_STRUCT), (PVOID)&DelbaReq);
6502 + RT28XX_MLME_HANDLER(pAd);
6503 +#endif
6504 + }
6505 +
6506 + return;
6507 + }
6508 +
6509 + DBGPRINT(RT_DEBUG_TRACE,("%s===>Wcid=%d.TID=%d \n", __FUNCTION__, Wcid, TID));
6510 +
6511 + pBAEntry = &pAd->BATable.BAOriEntry[Idx];
6512 + DBGPRINT(RT_DEBUG_TRACE,("\t===>Idx = %ld, Wcid=%d.TID=%d, ORI_BA_Status = %d \n", Idx, Wcid, TID, pBAEntry->ORI_BA_Status));
6513 + //
6514 + // Prepare DelBA action frame and send to the peer.
6515 + //
6516 + if ((bPassive == FALSE) && (TID == pBAEntry->TID) && (pBAEntry->ORI_BA_Status == Originator_Done))
6517 + {
6518 + MLME_DELBA_REQ_STRUCT DelbaReq;
6519 + MLME_QUEUE_ELEM *Elem = (MLME_QUEUE_ELEM *) kmalloc(sizeof(MLME_QUEUE_ELEM), MEM_ALLOC_FLAG);
6520 +
6521 + NdisZeroMemory(&DelbaReq, sizeof(DelbaReq));
6522 + NdisZeroMemory(Elem, sizeof(MLME_QUEUE_ELEM));
6523 +
6524 + COPY_MAC_ADDR(DelbaReq.Addr, pAd->MacTab.Content[Wcid].Addr);
6525 + DelbaReq.Wcid = Wcid;
6526 + DelbaReq.TID = pBAEntry->TID;
6527 + DelbaReq.Initiator = ORIGINATOR;
6528 +#if 1
6529 + Elem->MsgLen = sizeof(DelbaReq);
6530 + NdisMoveMemory(Elem->Msg, &DelbaReq, sizeof(DelbaReq));
6531 + MlmeDELBAAction(pAd, Elem);
6532 + kfree(Elem);
6533 +#else
6534 + MlmeEnqueue(pAd, ACTION_STATE_MACHINE, MT2_MLME_ORI_DELBA_CATE, sizeof(MLME_DELBA_REQ_STRUCT), (PVOID)&DelbaReq);
6535 + RT28XX_MLME_HANDLER(pAd);
6536 +#endif
6537 + }
6538 + RTMPCancelTimer(&pBAEntry->ORIBATimer, &Cancelled);
6539 + BATableFreeOriEntry(pAd, Idx);
6540 +
6541 + if (bPassive)
6542 + {
6543 + //BAOriSessionSetUp(pAd, &pAd->MacTab.Content[Wcid], TID, 0, 10000, TRUE);
6544 + }
6545 +}
6546 +
6547 +VOID BARecSessionTearDown(
6548 + IN OUT PRTMP_ADAPTER pAd,
6549 + IN UCHAR Wcid,
6550 + IN UCHAR TID,
6551 + IN BOOLEAN bPassive)
6552 +{
6553 + ULONG Idx = 0;
6554 + BA_REC_ENTRY *pBAEntry;
6555 +
6556 + if (Wcid >= MAX_LEN_OF_MAC_TABLE)
6557 + {
6558 + return;
6559 + }
6560 +
6561 + //
6562 + // Locate corresponding BA Originator Entry in BA Table with the (pAddr,TID).
6563 + //
6564 + Idx = pAd->MacTab.Content[Wcid].BARecWcidArray[TID];
6565 + if (Idx == 0)
6566 + return;
6567 +
6568 + DBGPRINT(RT_DEBUG_TRACE,("%s===>Wcid=%d.TID=%d \n", __FUNCTION__, Wcid, TID));
6569 +
6570 +
6571 + pBAEntry = &pAd->BATable.BARecEntry[Idx];
6572 + DBGPRINT(RT_DEBUG_TRACE,("\t===>Idx = %ld, Wcid=%d.TID=%d, REC_BA_Status = %d \n", Idx, Wcid, TID, pBAEntry->REC_BA_Status));
6573 + //
6574 + // Prepare DelBA action frame and send to the peer.
6575 + //
6576 + if ((TID == pBAEntry->TID) && (pBAEntry->REC_BA_Status == Recipient_Accept))
6577 + {
6578 + MLME_DELBA_REQ_STRUCT DelbaReq;
6579 + BOOLEAN Cancelled;
6580 + MLME_QUEUE_ELEM *Elem = (MLME_QUEUE_ELEM *) kmalloc(sizeof(MLME_QUEUE_ELEM), MEM_ALLOC_FLAG);
6581 + //ULONG offset;
6582 + //UINT32 VALUE;
6583 +
6584 + RTMPCancelTimer(&pBAEntry->RECBATimer, &Cancelled);
6585 +
6586 + //
6587 + // 1. Send DELBA Action Frame
6588 + //
6589 + if (bPassive == FALSE)
6590 + {
6591 + NdisZeroMemory(&DelbaReq, sizeof(DelbaReq));
6592 + NdisZeroMemory(Elem, sizeof(MLME_QUEUE_ELEM));
6593 +
6594 + COPY_MAC_ADDR(DelbaReq.Addr, pAd->MacTab.Content[Wcid].Addr);
6595 + DelbaReq.Wcid = Wcid;
6596 + DelbaReq.TID = TID;
6597 + DelbaReq.Initiator = RECIPIENT;
6598 +#if 1
6599 + Elem->MsgLen = sizeof(DelbaReq);
6600 + NdisMoveMemory(Elem->Msg, &DelbaReq, sizeof(DelbaReq));
6601 + MlmeDELBAAction(pAd, Elem);
6602 + kfree(Elem);
6603 +#else
6604 + MlmeEnqueue(pAd, ACTION_STATE_MACHINE, MT2_MLME_ORI_DELBA_CATE, sizeof(MLME_DELBA_REQ_STRUCT), (PVOID)&DelbaReq);
6605 + RT28XX_MLME_HANDLER(pAd);
6606 +#endif
6607 + }
6608 +
6609 +
6610 + //
6611 + // 2. Free resource of BA session
6612 + //
6613 + // flush all pending reordering mpdus
6614 + ba_refresh_reordering_mpdus(pAd, pBAEntry);
6615 +
6616 + NdisAcquireSpinLock(&pAd->BATabLock);
6617 +
6618 + // Erase Bitmap flag.
6619 + pBAEntry->LastIndSeq = RESET_RCV_SEQ;
6620 + pBAEntry->BAWinSize = 0;
6621 + // Erase Bitmap flag at software mactable
6622 + pAd->MacTab.Content[Wcid].RXBAbitmap &= (~(1<<(pBAEntry->TID)));
6623 + pAd->MacTab.Content[Wcid].BARecWcidArray[TID] = 0;
6624 +
6625 + RT28XX_DEL_BA_SESSION_FROM_ASIC(pAd, Wcid, TID);
6626 +
6627 + NdisReleaseSpinLock(&pAd->BATabLock);
6628 +
6629 + }
6630 +
6631 + BATableFreeRecEntry(pAd, Idx);
6632 +}
6633 +
6634 +VOID BASessionTearDownALL(
6635 + IN OUT PRTMP_ADAPTER pAd,
6636 + IN UCHAR Wcid)
6637 +{
6638 + int i;
6639 +
6640 + for (i=0; i<NUM_OF_TID; i++)
6641 + {
6642 + BAOriSessionTearDown(pAd, Wcid, i, FALSE, FALSE);
6643 + BARecSessionTearDown(pAd, Wcid, i, FALSE);
6644 + }
6645 +}
6646 +
6647 +
6648 +/*
6649 + ==========================================================================
6650 + Description:
6651 + Retry sending ADDBA Reqest.
6652 +
6653 + IRQL = DISPATCH_LEVEL
6654 +
6655 + Parametrs:
6656 + p8023Header: if this is already 802.3 format, p8023Header is NULL
6657 +
6658 + Return : TRUE if put into rx reordering buffer, shouldn't indicaterxhere.
6659 + FALSE , then continue indicaterx at this moment.
6660 + ==========================================================================
6661 + */
6662 +VOID BAOriSessionSetupTimeout(
6663 + IN PVOID SystemSpecific1,
6664 + IN PVOID FunctionContext,
6665 + IN PVOID SystemSpecific2,
6666 + IN PVOID SystemSpecific3)
6667 +{
6668 + BA_ORI_ENTRY *pBAEntry = (BA_ORI_ENTRY *)FunctionContext;
6669 + MAC_TABLE_ENTRY *pEntry;
6670 + PRTMP_ADAPTER pAd;
6671 +
6672 + if (pBAEntry == NULL)
6673 + return;
6674 +
6675 + pAd = pBAEntry->pAdapter;
6676 +
6677 +#ifdef CONFIG_STA_SUPPORT
6678 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
6679 + {
6680 + // Do nothing if monitor mode is on
6681 + if (MONITOR_ON(pAd))
6682 + return;
6683 + }
6684 +#endif // CONFIG_STA_SUPPORT //
6685 +
6686 +#ifdef RALINK_ATE
6687 + // Nothing to do in ATE mode.
6688 + if (ATE_ON(pAd))
6689 + return;
6690 +#endif // RALINK_ATE //
6691 +
6692 + pEntry = &pAd->MacTab.Content[pBAEntry->Wcid];
6693 +
6694 + if ((pBAEntry->ORI_BA_Status == Originator_WaitRes) && (pBAEntry->Token < ORI_SESSION_MAX_RETRY))
6695 + {
6696 + MLME_ADDBA_REQ_STRUCT AddbaReq;
6697 +
6698 + NdisZeroMemory(&AddbaReq, sizeof(AddbaReq));
6699 + COPY_MAC_ADDR(AddbaReq.pAddr, pEntry->Addr);
6700 + AddbaReq.Wcid = (UCHAR)(pEntry->Aid);
6701 + AddbaReq.TID = pBAEntry->TID;
6702 + AddbaReq.BaBufSize = pAd->CommonCfg.BACapability.field.RxBAWinLimit;
6703 + AddbaReq.TimeOutValue = 0;
6704 + AddbaReq.Token = pBAEntry->Token;
6705 + MlmeEnqueue(pAd, ACTION_STATE_MACHINE, MT2_MLME_ADD_BA_CATE, sizeof(MLME_ADDBA_REQ_STRUCT), (PVOID)&AddbaReq);
6706 + RT28XX_MLME_HANDLER(pAd);
6707 + DBGPRINT(RT_DEBUG_TRACE,("BA Ori Session Timeout(%d) : Send ADD BA again\n", pBAEntry->Token));
6708 +
6709 + pBAEntry->Token++;
6710 + RTMPSetTimer(&pBAEntry->ORIBATimer, ORI_BA_SESSION_TIMEOUT);
6711 + }
6712 + else
6713 + {
6714 + BATableFreeOriEntry(pAd, pEntry->BAOriWcidArray[pBAEntry->TID]);
6715 + }
6716 +}
6717 +
6718 +/*
6719 + ==========================================================================
6720 + Description:
6721 + Retry sending ADDBA Reqest.
6722 +
6723 + IRQL = DISPATCH_LEVEL
6724 +
6725 + Parametrs:
6726 + p8023Header: if this is already 802.3 format, p8023Header is NULL
6727 +
6728 + Return : TRUE if put into rx reordering buffer, shouldn't indicaterxhere.
6729 + FALSE , then continue indicaterx at this moment.
6730 + ==========================================================================
6731 + */
6732 +VOID BARecSessionIdleTimeout(
6733 + IN PVOID SystemSpecific1,
6734 + IN PVOID FunctionContext,
6735 + IN PVOID SystemSpecific2,
6736 + IN PVOID SystemSpecific3)
6737 +{
6738 +
6739 + BA_REC_ENTRY *pBAEntry = (BA_REC_ENTRY *)FunctionContext;
6740 + PRTMP_ADAPTER pAd;
6741 + ULONG Now32;
6742 +
6743 + if (pBAEntry == NULL)
6744 + return;
6745 +
6746 + if ((pBAEntry->REC_BA_Status == Recipient_Accept))
6747 + {
6748 + NdisGetSystemUpTime(&Now32);
6749 +
6750 + if (RTMP_TIME_AFTER((unsigned long)Now32, (unsigned long)(pBAEntry->LastIndSeqAtTimer + REC_BA_SESSION_IDLE_TIMEOUT)))
6751 + {
6752 + pAd = pBAEntry->pAdapter;
6753 + // flush all pending reordering mpdus
6754 + ba_refresh_reordering_mpdus(pAd, pBAEntry);
6755 + printk("%ld: REC BA session Timeout\n", Now32);
6756 + }
6757 + }
6758 +}
6759 +
6760 +
6761 +VOID PeerAddBAReqAction(
6762 + IN PRTMP_ADAPTER pAd,
6763 + IN MLME_QUEUE_ELEM *Elem)
6764 +
6765 +{
6766 + // 7.4.4.1
6767 + //ULONG Idx;
6768 + UCHAR Status = 1;
6769 + UCHAR pAddr[6];
6770 + FRAME_ADDBA_RSP ADDframe;
6771 + PUCHAR pOutBuffer = NULL;
6772 + NDIS_STATUS NStatus;
6773 + PFRAME_ADDBA_REQ pAddreqFrame = NULL;
6774 + //UCHAR BufSize;
6775 + ULONG FrameLen;
6776 + PULONG ptemp;
6777 + PMAC_TABLE_ENTRY pMacEntry;
6778 +
6779 + DBGPRINT(RT_DEBUG_TRACE, ("%s ==> (Wcid = %d)\n", __FUNCTION__, Elem->Wcid));
6780 +
6781 + //hex_dump("AddBAReq", Elem->Msg, Elem->MsgLen);
6782 +
6783 + //ADDBA Request from unknown peer, ignore this.
6784 + if (Elem->Wcid >= MAX_LEN_OF_MAC_TABLE)
6785 + return;
6786 +
6787 + pMacEntry = &pAd->MacTab.Content[Elem->Wcid];
6788 + DBGPRINT(RT_DEBUG_TRACE,("BA - PeerAddBAReqAction----> \n"));
6789 + ptemp = (PULONG)Elem->Msg;
6790 + //DBGPRINT_RAW(RT_DEBUG_EMU, ("%08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x\n", *(ptemp), *(ptemp+1), *(ptemp+2), *(ptemp+3), *(ptemp+4), *(ptemp+5), *(ptemp+6), *(ptemp+7), *(ptemp+8)));
6791 +
6792 + if (PeerAddBAReqActionSanity(pAd, Elem->Msg, Elem->MsgLen, pAddr))
6793 + {
6794 +
6795 + if ((pAd->CommonCfg.bBADecline == FALSE) && IS_HT_STA(pMacEntry))
6796 + {
6797 + pAddreqFrame = (PFRAME_ADDBA_REQ)(&Elem->Msg[0]);
6798 + printk("Rcv Wcid(%d) AddBAReq\n", Elem->Wcid);
6799 + if (BARecSessionAdd(pAd, &pAd->MacTab.Content[Elem->Wcid], pAddreqFrame))
6800 + Status = 0;
6801 + else
6802 + Status = 38; // more parameters have invalid values
6803 + }
6804 + else
6805 + {
6806 + Status = 37; // the request has been declined.
6807 + }
6808 + }
6809 +
6810 + if (pAd->MacTab.Content[Elem->Wcid].ValidAsCLI)
6811 + ASSERT(pAd->MacTab.Content[Elem->Wcid].Sst == SST_ASSOC);
6812 +
6813 + pAddreqFrame = (PFRAME_ADDBA_REQ)(&Elem->Msg[0]);
6814 + // 2. Always send back ADDBA Response
6815 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
6816 + if (NStatus != NDIS_STATUS_SUCCESS)
6817 + {
6818 + DBGPRINT(RT_DEBUG_TRACE,("ACTION - PeerBAAction() allocate memory failed \n"));
6819 + return;
6820 + }
6821 +
6822 + NdisZeroMemory(&ADDframe, sizeof(FRAME_ADDBA_RSP));
6823 + // 2-1. Prepare ADDBA Response frame.
6824 +#ifdef CONFIG_STA_SUPPORT
6825 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
6826 + {
6827 + if (ADHOC_ON(pAd))
6828 + ActHeaderInit(pAd, &ADDframe.Hdr, pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
6829 + else
6830 +#ifdef QOS_DLS_SUPPORT
6831 + if (pAd->MacTab.Content[Elem->Wcid].ValidAsDls)
6832 + ActHeaderInit(pAd, &ADDframe.Hdr, pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
6833 + else
6834 +#endif // QOS_DLS_SUPPORT //
6835 + ActHeaderInit(pAd, &ADDframe.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAddr);
6836 + }
6837 +#endif // CONFIG_STA_SUPPORT //
6838 + ADDframe.Category = CATEGORY_BA;
6839 + ADDframe.Action = ADDBA_RESP;
6840 + ADDframe.Token = pAddreqFrame->Token;
6841 + // What is the Status code?? need to check.
6842 + ADDframe.StatusCode = Status;
6843 + ADDframe.BaParm.BAPolicy = IMMED_BA;
6844 + ADDframe.BaParm.AMSDUSupported = 0;
6845 + ADDframe.BaParm.TID = pAddreqFrame->BaParm.TID;
6846 + ADDframe.BaParm.BufSize = min(((UCHAR)pAddreqFrame->BaParm.BufSize), (UCHAR)pAd->CommonCfg.BACapability.field.RxBAWinLimit);
6847 + if (ADDframe.BaParm.BufSize == 0)
6848 + {
6849 + ADDframe.BaParm.BufSize = 64;
6850 + }
6851 + ADDframe.TimeOutValue = 0; //pAddreqFrame->TimeOutValue;
6852 +
6853 + *(USHORT *)(&ADDframe.BaParm) = cpu2le16(*(USHORT *)(&ADDframe.BaParm));
6854 + ADDframe.StatusCode = cpu2le16(ADDframe.StatusCode);
6855 + ADDframe.TimeOutValue = cpu2le16(ADDframe.TimeOutValue);
6856 +
6857 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
6858 + sizeof(FRAME_ADDBA_RSP), &ADDframe,
6859 + END_OF_ARGS);
6860 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
6861 + MlmeFreeMemory(pAd, pOutBuffer);
6862 +
6863 + DBGPRINT(RT_DEBUG_TRACE, ("%s(%d): TID(%d), BufSize(%d) <== \n", __FUNCTION__, Elem->Wcid, ADDframe.BaParm.TID,
6864 + ADDframe.BaParm.BufSize));
6865 +}
6866 +
6867 +
6868 +VOID PeerAddBARspAction(
6869 + IN PRTMP_ADAPTER pAd,
6870 + IN MLME_QUEUE_ELEM *Elem)
6871 +
6872 +{
6873 + //UCHAR Idx, i;
6874 + //PUCHAR pOutBuffer = NULL;
6875 + PFRAME_ADDBA_RSP pFrame = NULL;
6876 + //PBA_ORI_ENTRY pBAEntry;
6877 +
6878 + //ADDBA Response from unknown peer, ignore this.
6879 + if (Elem->Wcid >= MAX_LEN_OF_MAC_TABLE)
6880 + return;
6881 +
6882 + DBGPRINT(RT_DEBUG_TRACE, ("%s ==> Wcid(%d)\n", __FUNCTION__, Elem->Wcid));
6883 +
6884 + //hex_dump("PeerAddBARspAction()", Elem->Msg, Elem->MsgLen);
6885 +
6886 + if (PeerAddBARspActionSanity(pAd, Elem->Msg, Elem->MsgLen))
6887 + {
6888 + pFrame = (PFRAME_ADDBA_RSP)(&Elem->Msg[0]);
6889 +
6890 + DBGPRINT(RT_DEBUG_TRACE, ("\t\t StatusCode = %d\n", pFrame->StatusCode));
6891 + switch (pFrame->StatusCode)
6892 + {
6893 + case 0:
6894 + // I want a BAsession with this peer as an originator.
6895 + BAOriSessionAdd(pAd, &pAd->MacTab.Content[Elem->Wcid], pFrame);
6896 + break;
6897 + default:
6898 + // check status == USED ???
6899 + BAOriSessionTearDown(pAd, Elem->Wcid, pFrame->BaParm.TID, TRUE, FALSE);
6900 + break;
6901 + }
6902 + // Rcv Decline StatusCode
6903 + if ((pFrame->StatusCode == 37)
6904 +#ifdef CONFIG_STA_SUPPORT
6905 + || ((pAd->OpMode == OPMODE_STA) && STA_TGN_WIFI_ON(pAd) && (pFrame->StatusCode != 0))
6906 +#endif // CONFIG_STA_SUPPORT //
6907 + )
6908 + {
6909 + pAd->MacTab.Content[Elem->Wcid].BADeclineBitmap |= 1<<pFrame->BaParm.TID;
6910 + }
6911 + }
6912 +}
6913 +
6914 +VOID PeerDelBAAction(
6915 + IN PRTMP_ADAPTER pAd,
6916 + IN MLME_QUEUE_ELEM *Elem)
6917 +
6918 +{
6919 + //UCHAR Idx;
6920 + //PUCHAR pOutBuffer = NULL;
6921 + PFRAME_DELBA_REQ pDelFrame = NULL;
6922 +
6923 + DBGPRINT(RT_DEBUG_TRACE,("%s ==>\n", __FUNCTION__));
6924 + //DELBA Request from unknown peer, ignore this.
6925 + if (PeerDelBAActionSanity(pAd, Elem->Wcid, Elem->Msg, Elem->MsgLen))
6926 + {
6927 + pDelFrame = (PFRAME_DELBA_REQ)(&Elem->Msg[0]);
6928 + if (pDelFrame->DelbaParm.Initiator == ORIGINATOR)
6929 + {
6930 + DBGPRINT(RT_DEBUG_TRACE,("BA - PeerDelBAAction----> ORIGINATOR\n"));
6931 + BARecSessionTearDown(pAd, Elem->Wcid, pDelFrame->DelbaParm.TID, TRUE);
6932 + }
6933 + else
6934 + {
6935 + DBGPRINT(RT_DEBUG_TRACE,("BA - PeerDelBAAction----> RECIPIENT, Reason = %d\n", pDelFrame->ReasonCode));
6936 + //hex_dump("DelBA Frame", pDelFrame, Elem->MsgLen);
6937 + BAOriSessionTearDown(pAd, Elem->Wcid, pDelFrame->DelbaParm.TID, TRUE, FALSE);
6938 + }
6939 + }
6940 +}
6941 +
6942 +
6943 +BOOLEAN CntlEnqueueForRecv(
6944 + IN PRTMP_ADAPTER pAd,
6945 + IN ULONG Wcid,
6946 + IN ULONG MsgLen,
6947 + IN PFRAME_BA_REQ pMsg)
6948 +{
6949 + PFRAME_BA_REQ pFrame = pMsg;
6950 + //PRTMP_REORDERBUF pBuffer;
6951 + //PRTMP_REORDERBUF pDmaBuf;
6952 + PBA_REC_ENTRY pBAEntry;
6953 + //BOOLEAN Result;
6954 + ULONG Idx;
6955 + //UCHAR NumRxPkt;
6956 + UCHAR TID;//, i;
6957 +
6958 + TID = (UCHAR)pFrame->BARControl.TID;
6959 +
6960 + DBGPRINT(RT_DEBUG_TRACE, ("%s(): BAR-Wcid(%ld), Tid (%d)\n", __FUNCTION__, Wcid, TID));
6961 + //hex_dump("BAR", (PCHAR) pFrame, MsgLen);
6962 + // Do nothing if the driver is starting halt state.
6963 + // This might happen when timer already been fired before cancel timer with mlmehalt
6964 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
6965 + return FALSE;
6966 +
6967 + // First check the size, it MUST not exceed the mlme queue size
6968 + if (MsgLen > MGMT_DMA_BUFFER_SIZE)
6969 + {
6970 + DBGPRINT_ERR(("CntlEnqueueForRecv: frame too large, size = %ld \n", MsgLen));
6971 + return FALSE;
6972 + }
6973 + else if (MsgLen != sizeof(FRAME_BA_REQ))
6974 + {
6975 + DBGPRINT_ERR(("CntlEnqueueForRecv: BlockAck Request frame length size = %ld incorrect\n", MsgLen));
6976 + return FALSE;
6977 + }
6978 + else if (MsgLen != sizeof(FRAME_BA_REQ))
6979 + {
6980 + DBGPRINT_ERR(("CntlEnqueueForRecv: BlockAck Request frame length size = %ld incorrect\n", MsgLen));
6981 + return FALSE;
6982 + }
6983 +
6984 + if ((Wcid < MAX_LEN_OF_MAC_TABLE) && (TID < 8))
6985 + {
6986 + // if this receiving packet is from SA that is in our OriEntry. Since WCID <9 has direct mapping. no need search.
6987 + Idx = pAd->MacTab.Content[Wcid].BARecWcidArray[TID];
6988 + pBAEntry = &pAd->BATable.BARecEntry[Idx];
6989 + }
6990 + else
6991 + {
6992 + return FALSE;
6993 + }
6994 +
6995 + DBGPRINT(RT_DEBUG_TRACE, ("BAR(%ld) : Tid (%d) - %04x:%04x\n", Wcid, TID, pFrame->BAStartingSeq.field.StartSeq, pBAEntry->LastIndSeq ));
6996 +
6997 + if (SEQ_SMALLER(pBAEntry->LastIndSeq, pFrame->BAStartingSeq.field.StartSeq, MAXSEQ))
6998 + {
6999 + //printk("BAR Seq = %x, LastIndSeq = %x\n", pFrame->BAStartingSeq.field.StartSeq, pBAEntry->LastIndSeq);
7000 + ba_indicate_reordering_mpdus_le_seq(pAd, pBAEntry, pFrame->BAStartingSeq.field.StartSeq);
7001 + pBAEntry->LastIndSeq = (pFrame->BAStartingSeq.field.StartSeq == 0) ? MAXSEQ :(pFrame->BAStartingSeq.field.StartSeq -1);
7002 + }
7003 + //ba_refresh_reordering_mpdus(pAd, pBAEntry);
7004 + return TRUE;
7005 +}
7006 +
7007 +/*
7008 +Description : Send PSMP Action frame If PSMP mode switches.
7009 +*/
7010 +VOID SendPSMPAction(
7011 + IN PRTMP_ADAPTER pAd,
7012 + IN UCHAR Wcid,
7013 + IN UCHAR Psmp)
7014 +{
7015 + PUCHAR pOutBuffer = NULL;
7016 + NDIS_STATUS NStatus;
7017 + //ULONG Idx;
7018 + FRAME_PSMP_ACTION Frame;
7019 + ULONG FrameLen;
7020 +
7021 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
7022 + if (NStatus != NDIS_STATUS_SUCCESS)
7023 + {
7024 + DBGPRINT(RT_DEBUG_ERROR,("BA - MlmeADDBAAction() allocate memory failed \n"));
7025 + return;
7026 + }
7027 +#ifdef CONFIG_STA_SUPPORT
7028 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
7029 + ActHeaderInit(pAd, &Frame.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAd->MacTab.Content[Wcid].Addr);
7030 +#endif // CONFIG_STA_SUPPORT //
7031 +
7032 + Frame.Category = CATEGORY_HT;
7033 + Frame.Action = SMPS_ACTION;
7034 + switch (Psmp)
7035 + {
7036 + case MMPS_ENABLE:
7037 + Frame.Psmp = 0;
7038 + break;
7039 + case MMPS_DYNAMIC:
7040 + Frame.Psmp = 3;
7041 + break;
7042 + case MMPS_STATIC:
7043 + Frame.Psmp = 1;
7044 + break;
7045 + }
7046 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
7047 + sizeof(FRAME_PSMP_ACTION), &Frame,
7048 + END_OF_ARGS);
7049 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
7050 + MlmeFreeMemory(pAd, pOutBuffer);
7051 + DBGPRINT(RT_DEBUG_ERROR,("HT - SendPSMPAction( %d ) \n", Frame.Psmp));
7052 +}
7053 +
7054 +
7055 +#define RADIO_MEASUREMENT_REQUEST_ACTION 0
7056 +
7057 +typedef struct PACKED
7058 +{
7059 + UCHAR RegulatoryClass;
7060 + UCHAR ChannelNumber;
7061 + USHORT RandomInterval;
7062 + USHORT MeasurementDuration;
7063 + UCHAR MeasurementMode;
7064 + UCHAR BSSID[MAC_ADDR_LEN];
7065 + UCHAR ReportingCondition;
7066 + UCHAR Threshold;
7067 + UCHAR SSIDIE[2]; // 2 byte
7068 +} BEACON_REQUEST;
7069 +
7070 +typedef struct PACKED
7071 +{
7072 + UCHAR ID;
7073 + UCHAR Length;
7074 + UCHAR Token;
7075 + UCHAR RequestMode;
7076 + UCHAR Type;
7077 +} MEASUREMENT_REQ;
7078 +
7079 +
7080 +
7081 +
7082 +void convert_reordering_packet_to_preAMSDU_or_802_3_packet(
7083 + IN PRTMP_ADAPTER pAd,
7084 + IN RX_BLK *pRxBlk,
7085 + IN UCHAR FromWhichBSSID)
7086 +{
7087 + PNDIS_PACKET pRxPkt;
7088 + UCHAR Header802_3[LENGTH_802_3];
7089 +
7090 + // 1. get 802.3 Header
7091 + // 2. remove LLC
7092 + // a. pointer pRxBlk->pData to payload
7093 + // b. modify pRxBlk->DataSize
7094 +
7095 +#ifdef CONFIG_STA_SUPPORT
7096 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
7097 + RTMP_802_11_REMOVE_LLC_AND_CONVERT_TO_802_3(pRxBlk, Header802_3);
7098 +#endif // CONFIG_STA_SUPPORT //
7099 +
7100 + ASSERT(pRxBlk->pRxPacket);
7101 + pRxPkt = RTPKT_TO_OSPKT(pRxBlk->pRxPacket);
7102 +
7103 + RTPKT_TO_OSPKT(pRxPkt)->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
7104 + RTPKT_TO_OSPKT(pRxPkt)->data = pRxBlk->pData;
7105 + RTPKT_TO_OSPKT(pRxPkt)->len = pRxBlk->DataSize;
7106 + RTPKT_TO_OSPKT(pRxPkt)->tail = RTPKT_TO_OSPKT(pRxPkt)->data + RTPKT_TO_OSPKT(pRxPkt)->len;
7107 +
7108 + //
7109 + // copy 802.3 header, if necessary
7110 + //
7111 + if (!RX_BLK_TEST_FLAG(pRxBlk, fRX_AMSDU))
7112 + {
7113 +
7114 +#ifdef CONFIG_STA_SUPPORT
7115 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
7116 + {
7117 +#ifdef LINUX
7118 + NdisMoveMemory(skb_push(pRxPkt, LENGTH_802_3), Header802_3, LENGTH_802_3);
7119 +#endif
7120 +#ifdef UCOS
7121 + NdisMoveMemory(net_pkt_push(pRxPkt, LENGTH_802_3), Header802_3, LENGTH_802_3);
7122 +#endif
7123 + }
7124 +#endif // CONFIG_STA_SUPPORT //
7125 + }
7126 +}
7127 +
7128 +
7129 +#define INDICATE_LEGACY_OR_AMSDU(_pAd, _pRxBlk, _fromWhichBSSID) \
7130 + do \
7131 + { \
7132 + if (RX_BLK_TEST_FLAG(_pRxBlk, fRX_AMSDU)) \
7133 + { \
7134 + Indicate_AMSDU_Packet(_pAd, _pRxBlk, _fromWhichBSSID); \
7135 + } \
7136 + else if (RX_BLK_TEST_FLAG(_pRxBlk, fRX_EAP)) \
7137 + { \
7138 + Indicate_EAPOL_Packet(_pAd, _pRxBlk, _fromWhichBSSID); \
7139 + } \
7140 + else \
7141 + { \
7142 + Indicate_Legacy_Packet(_pAd, _pRxBlk, _fromWhichBSSID); \
7143 + } \
7144 + } while (0);
7145 +
7146 +
7147 +
7148 +static VOID ba_enqueue_reordering_packet(
7149 + IN PRTMP_ADAPTER pAd,
7150 + IN PBA_REC_ENTRY pBAEntry,
7151 + IN RX_BLK *pRxBlk,
7152 + IN UCHAR FromWhichBSSID)
7153 +{
7154 + struct reordering_mpdu *mpdu_blk;
7155 + UINT16 Sequence = (UINT16) pRxBlk->pHeader->Sequence;
7156 +
7157 + mpdu_blk = ba_mpdu_blk_alloc(pAd);
7158 + if (mpdu_blk != NULL)
7159 + {
7160 + // Write RxD buffer address & allocated buffer length
7161 + NdisAcquireSpinLock(&pBAEntry->RxReRingLock);
7162 +
7163 + mpdu_blk->Sequence = Sequence;
7164 +
7165 + mpdu_blk->bAMSDU = RX_BLK_TEST_FLAG(pRxBlk, fRX_AMSDU);
7166 +
7167 + convert_reordering_packet_to_preAMSDU_or_802_3_packet(pAd, pRxBlk, FromWhichBSSID);
7168 +
7169 + STATS_INC_RX_PACKETS(pAd, FromWhichBSSID);
7170 +
7171 + //
7172 + // it is necessary for reordering packet to record
7173 + // which BSS it come from
7174 + //
7175 + RTMP_SET_PACKET_IF(pRxBlk->pRxPacket, FromWhichBSSID);
7176 +
7177 + mpdu_blk->pPacket = pRxBlk->pRxPacket;
7178 +
7179 + if (ba_reordering_mpdu_insertsorted(&pBAEntry->list, mpdu_blk) == FALSE)
7180 + {
7181 + // had been already within reordering list
7182 + // don't indicate
7183 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_SUCCESS);
7184 + ba_mpdu_blk_free(pAd, mpdu_blk);
7185 + }
7186 +
7187 + ASSERT((0<= pBAEntry->list.qlen) && (pBAEntry->list.qlen <= pBAEntry->BAWinSize));
7188 + NdisReleaseSpinLock(&pBAEntry->RxReRingLock);
7189 + }
7190 + else
7191 + {
7192 +#if 0
7193 + DBGPRINT(RT_DEBUG_ERROR, ("!!! (%d:%d) Can't allocate reordering mpdu blk\n",
7194 + blk_count, pBAEntry->list.qlen));
7195 +#else
7196 + DBGPRINT(RT_DEBUG_ERROR, ("!!! (%d) Can't allocate reordering mpdu blk\n",
7197 + pBAEntry->list.qlen));
7198 +#endif
7199 + /*
7200 + * flush all pending reordering mpdus
7201 + * and receving mpdu to upper layer
7202 + * make tcp/ip to take care reordering mechanism
7203 + */
7204 + //ba_refresh_reordering_mpdus(pAd, pBAEntry);
7205 + ba_indicate_reordering_mpdus_le_seq(pAd, pBAEntry, Sequence);
7206 +
7207 + pBAEntry->LastIndSeq = Sequence;
7208 + INDICATE_LEGACY_OR_AMSDU(pAd, pRxBlk, FromWhichBSSID);
7209 + }
7210 +}
7211 +
7212 +
7213 +/*
7214 + ==========================================================================
7215 + Description:
7216 + Indicate this packet to upper layer or put it into reordering buffer
7217 +
7218 + Parametrs:
7219 + pRxBlk : carry necessary packet info 802.11 format
7220 + FromWhichBSSID : the packet received from which BSS
7221 +
7222 + Return :
7223 + none
7224 +
7225 + Note :
7226 + the packet queued into reordering buffer need to cover to 802.3 format
7227 + or pre_AMSDU format
7228 + ==========================================================================
7229 + */
7230 +
7231 +VOID Indicate_AMPDU_Packet(
7232 + IN PRTMP_ADAPTER pAd,
7233 + IN RX_BLK *pRxBlk,
7234 + IN UCHAR FromWhichBSSID)
7235 +{
7236 + USHORT Idx;
7237 + PBA_REC_ENTRY pBAEntry = NULL;
7238 + UINT16 Sequence = pRxBlk->pHeader->Sequence;
7239 + ULONG Now32;
7240 + UCHAR Wcid = pRxBlk->pRxWI->WirelessCliID;
7241 + UCHAR TID = pRxBlk->pRxWI->TID;
7242 +
7243 +
7244 + if (!RX_BLK_TEST_FLAG(pRxBlk, fRX_AMSDU) && (pRxBlk->DataSize > MAX_RX_PKT_LEN))
7245 + {
7246 +#if 0 // sample take off, no use
7247 + static int err_size;
7248 +
7249 + err_size++;
7250 + if (err_size > 20) {
7251 + printk("AMPDU DataSize = %d\n", pRxBlk->DataSize);
7252 + hex_dump("802.11 Header", (UCHAR *)pRxBlk->pHeader, 24);
7253 + hex_dump("Payload", pRxBlk->pData, 64);
7254 + err_size = 0;
7255 + }
7256 +#endif
7257 + // release packet
7258 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
7259 + return;
7260 + }
7261 +
7262 +
7263 +#if 0 // test
7264 + /* Rec BA Session had been torn down */
7265 + INDICATE_LEGACY_OR_AMSDU(pAd, pRxBlk, FromWhichBSSID);
7266 + return;
7267 +#endif
7268 +
7269 + if (Wcid < MAX_LEN_OF_MAC_TABLE)
7270 + {
7271 + Idx = pAd->MacTab.Content[Wcid].BARecWcidArray[TID];
7272 + if (Idx == 0)
7273 + {
7274 + /* Rec BA Session had been torn down */
7275 + INDICATE_LEGACY_OR_AMSDU(pAd, pRxBlk, FromWhichBSSID);
7276 + return;
7277 + }
7278 + pBAEntry = &pAd->BATable.BARecEntry[Idx];
7279 + }
7280 + else
7281 + {
7282 + // impossible !!!
7283 + ASSERT(0);
7284 + // release packet
7285 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
7286 + return;
7287 + }
7288 +
7289 + ASSERT(pBAEntry);
7290 +
7291 + // update last rx time
7292 + NdisGetSystemUpTime(&Now32);
7293 +
7294 + pBAEntry->rcvSeq = Sequence;
7295 +
7296 +
7297 + ba_flush_reordering_timeout_mpdus(pAd, pBAEntry, Now32);
7298 + pBAEntry->LastIndSeqAtTimer = Now32;
7299 +
7300 + //
7301 + // Reset Last Indicate Sequence
7302 + //
7303 + if (pBAEntry->LastIndSeq == RESET_RCV_SEQ)
7304 + {
7305 + ASSERT((pBAEntry->list.qlen == 0) && (pBAEntry->list.next == NULL));
7306 +
7307 + // reset rcv sequence of BA session
7308 + pBAEntry->LastIndSeq = Sequence;
7309 + pBAEntry->LastIndSeqAtTimer = Now32;
7310 + INDICATE_LEGACY_OR_AMSDU(pAd, pRxBlk, FromWhichBSSID);
7311 + return;
7312 + }
7313 +
7314 +
7315 + //
7316 + // I. Check if in order.
7317 + //
7318 + if (SEQ_STEPONE(Sequence, pBAEntry->LastIndSeq, MAXSEQ))
7319 + {
7320 + USHORT LastIndSeq;
7321 +
7322 + pBAEntry->LastIndSeq = Sequence;
7323 + INDICATE_LEGACY_OR_AMSDU(pAd, pRxBlk, FromWhichBSSID);
7324 + LastIndSeq = ba_indicate_reordering_mpdus_in_order(pAd, pBAEntry, pBAEntry->LastIndSeq);
7325 + if (LastIndSeq != RESET_RCV_SEQ)
7326 + {
7327 + pBAEntry->LastIndSeq = LastIndSeq;
7328 + }
7329 + pBAEntry->LastIndSeqAtTimer = Now32;
7330 + }
7331 + //
7332 + // II. Drop Duplicated Packet
7333 + //
7334 + else if (Sequence == pBAEntry->LastIndSeq)
7335 + {
7336 +
7337 + // drop and release packet
7338 + pBAEntry->nDropPacket++;
7339 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
7340 + }
7341 + //
7342 + // III. Drop Old Received Packet
7343 + //
7344 + else if (SEQ_SMALLER(Sequence, pBAEntry->LastIndSeq, MAXSEQ))
7345 + {
7346 +
7347 + // drop and release packet
7348 + pBAEntry->nDropPacket++;
7349 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
7350 + }
7351 + //
7352 + // IV. Receive Sequence within Window Size
7353 + //
7354 + else if (SEQ_SMALLER(Sequence, (((pBAEntry->LastIndSeq+pBAEntry->BAWinSize+1)) & MAXSEQ), MAXSEQ))
7355 + {
7356 + ba_enqueue_reordering_packet(pAd, pBAEntry, pRxBlk, FromWhichBSSID);
7357 + }
7358 + //
7359 + // V. Receive seq surpasses Win(lastseq + nMSDU). So refresh all reorder buffer
7360 + //
7361 + else
7362 + {
7363 +#if 0
7364 + ba_refresh_reordering_mpdus(pAd, pBAEntry);
7365 + INDICATE_LEGACY_OR_AMSDU(pAd, pRxBlk, FromWhichBSSID);
7366 +#else
7367 + LONG WinStartSeq, TmpSeq;
7368 +
7369 +
7370 + TmpSeq = Sequence - (pBAEntry->BAWinSize) -1;
7371 + if (TmpSeq < 0)
7372 + {
7373 + TmpSeq = (MAXSEQ+1) + TmpSeq;
7374 + }
7375 + WinStartSeq = (TmpSeq+1) & MAXSEQ;
7376 + ba_indicate_reordering_mpdus_le_seq(pAd, pBAEntry, WinStartSeq);
7377 + pBAEntry->LastIndSeq = WinStartSeq; //TmpSeq;
7378 +
7379 + pBAEntry->LastIndSeqAtTimer = Now32;
7380 +
7381 + ba_enqueue_reordering_packet(pAd, pBAEntry, pRxBlk, FromWhichBSSID);
7382 +
7383 + TmpSeq = ba_indicate_reordering_mpdus_in_order(pAd, pBAEntry, pBAEntry->LastIndSeq);
7384 + if (TmpSeq != RESET_RCV_SEQ)
7385 + {
7386 + pBAEntry->LastIndSeq = TmpSeq;
7387 + }
7388 +#endif
7389 + }
7390 +}
7391 +
7392 +#endif // DOT11_N_SUPPORT //
7393 +
7394 --- /dev/null
7395 +++ b/drivers/staging/rt2860/common/cmm_data_2860.c
7396 @@ -0,0 +1,1240 @@
7397 +/*
7398 + *************************************************************************
7399 + * Ralink Tech Inc.
7400 + * 5F., No.36, Taiyuan St., Jhubei City,
7401 + * Hsinchu County 302,
7402 + * Taiwan, R.O.C.
7403 + *
7404 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
7405 + *
7406 + * This program is free software; you can redistribute it and/or modify *
7407 + * it under the terms of the GNU General Public License as published by *
7408 + * the Free Software Foundation; either version 2 of the License, or *
7409 + * (at your option) any later version. *
7410 + * *
7411 + * This program is distributed in the hope that it will be useful, *
7412 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
7413 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
7414 + * GNU General Public License for more details. *
7415 + * *
7416 + * You should have received a copy of the GNU General Public License *
7417 + * along with this program; if not, write to the *
7418 + * Free Software Foundation, Inc., *
7419 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
7420 + * *
7421 + *************************************************************************
7422 +*/
7423 +
7424 +/*
7425 + All functions in this file must be PCI-depended, or you should out your function
7426 + in other files.
7427 +
7428 +*/
7429 +#include "../rt_config.h"
7430 +
7431 +extern RTMP_RF_REGS RF2850RegTable[];
7432 +extern UCHAR NUM_OF_2850_CHNL;
7433 +
7434 +USHORT RtmpPCI_WriteTxResource(
7435 + IN PRTMP_ADAPTER pAd,
7436 + IN TX_BLK *pTxBlk,
7437 + IN BOOLEAN bIsLast,
7438 + OUT USHORT *FreeNumber)
7439 +{
7440 +
7441 + UCHAR *pDMAHeaderBufVA;
7442 + USHORT TxIdx, RetTxIdx;
7443 + PTXD_STRUC pTxD;
7444 + UINT32 BufBasePaLow;
7445 + PRTMP_TX_RING pTxRing;
7446 + USHORT hwHeaderLen;
7447 +
7448 + //
7449 + // get Tx Ring Resource
7450 + //
7451 + pTxRing = &pAd->TxRing[pTxBlk->QueIdx];
7452 + TxIdx = pAd->TxRing[pTxBlk->QueIdx].TxCpuIdx;
7453 + pDMAHeaderBufVA = (PUCHAR) pTxRing->Cell[TxIdx].DmaBuf.AllocVa;
7454 + BufBasePaLow = RTMP_GetPhysicalAddressLow(pTxRing->Cell[TxIdx].DmaBuf.AllocPa);
7455 +
7456 + // copy TXINFO + TXWI + WLAN Header + LLC into DMA Header Buffer
7457 + if (pTxBlk->TxFrameType == TX_AMSDU_FRAME)
7458 + {
7459 + hwHeaderLen = pTxBlk->MpduHeaderLen - LENGTH_AMSDU_SUBFRAMEHEAD + pTxBlk->HdrPadLen + LENGTH_AMSDU_SUBFRAMEHEAD;
7460 + }
7461 + else
7462 + {
7463 + hwHeaderLen = pTxBlk->MpduHeaderLen + pTxBlk->HdrPadLen;
7464 + }
7465 + NdisMoveMemory(pDMAHeaderBufVA, pTxBlk->HeaderBuf, TXINFO_SIZE + TXWI_SIZE + hwHeaderLen);
7466 +
7467 + pTxRing->Cell[TxIdx].pNdisPacket = pTxBlk->pPacket;
7468 + pTxRing->Cell[TxIdx].pNextNdisPacket = NULL;
7469 +
7470 + //
7471 + // build Tx Descriptor
7472 + //
7473 +
7474 + pTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
7475 + NdisZeroMemory(pTxD, TXD_SIZE);
7476 +
7477 + pTxD->SDPtr0 = BufBasePaLow;
7478 + pTxD->SDLen0 = TXINFO_SIZE + TXWI_SIZE + hwHeaderLen; // include padding
7479 + pTxD->SDPtr1 = PCI_MAP_SINGLE(pAd, pTxBlk, 0, 1, PCI_DMA_TODEVICE);;
7480 + pTxD->SDLen1 = pTxBlk->SrcBufLen;
7481 + pTxD->LastSec0 = 0;
7482 + pTxD->LastSec1 = (bIsLast) ? 1 : 0;
7483 +
7484 + RTMPWriteTxDescriptor(pAd, pTxD, FALSE, FIFO_EDCA);
7485 +
7486 + RetTxIdx = TxIdx;
7487 + //
7488 + // Update Tx index
7489 + //
7490 + INC_RING_INDEX(TxIdx, TX_RING_SIZE);
7491 + pTxRing->TxCpuIdx = TxIdx;
7492 +
7493 + *FreeNumber -= 1;
7494 +
7495 + return RetTxIdx;
7496 +}
7497 +
7498 +
7499 +USHORT RtmpPCI_WriteSingleTxResource(
7500 + IN PRTMP_ADAPTER pAd,
7501 + IN TX_BLK *pTxBlk,
7502 + IN BOOLEAN bIsLast,
7503 + OUT USHORT *FreeNumber)
7504 +{
7505 +
7506 + UCHAR *pDMAHeaderBufVA;
7507 + USHORT TxIdx, RetTxIdx;
7508 + PTXD_STRUC pTxD;
7509 +#ifdef RT_BIG_ENDIAN
7510 + PTXD_STRUC pDestTxD;
7511 + TXD_STRUC TxD;
7512 +#endif
7513 + UINT32 BufBasePaLow;
7514 + PRTMP_TX_RING pTxRing;
7515 + USHORT hwHeaderLen;
7516 +
7517 + //
7518 + // get Tx Ring Resource
7519 + //
7520 + pTxRing = &pAd->TxRing[pTxBlk->QueIdx];
7521 + TxIdx = pAd->TxRing[pTxBlk->QueIdx].TxCpuIdx;
7522 + pDMAHeaderBufVA = (PUCHAR) pTxRing->Cell[TxIdx].DmaBuf.AllocVa;
7523 + BufBasePaLow = RTMP_GetPhysicalAddressLow(pTxRing->Cell[TxIdx].DmaBuf.AllocPa);
7524 +
7525 + // copy TXINFO + TXWI + WLAN Header + LLC into DMA Header Buffer
7526 + hwHeaderLen = pTxBlk->MpduHeaderLen + pTxBlk->HdrPadLen;
7527 +
7528 + NdisMoveMemory(pDMAHeaderBufVA, pTxBlk->HeaderBuf, TXINFO_SIZE + TXWI_SIZE + hwHeaderLen);
7529 +
7530 + pTxRing->Cell[TxIdx].pNdisPacket = pTxBlk->pPacket;
7531 + pTxRing->Cell[TxIdx].pNextNdisPacket = NULL;
7532 +
7533 + //
7534 + // build Tx Descriptor
7535 + //
7536 +#ifndef RT_BIG_ENDIAN
7537 + pTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
7538 +#else
7539 + pDestTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
7540 + TxD = *pDestTxD;
7541 + pTxD = &TxD;
7542 +#endif
7543 + NdisZeroMemory(pTxD, TXD_SIZE);
7544 +
7545 + pTxD->SDPtr0 = BufBasePaLow;
7546 + pTxD->SDLen0 = TXINFO_SIZE + TXWI_SIZE + hwHeaderLen; // include padding
7547 + pTxD->SDPtr1 = PCI_MAP_SINGLE(pAd, pTxBlk, 0, 1, PCI_DMA_TODEVICE);;
7548 + pTxD->SDLen1 = pTxBlk->SrcBufLen;
7549 + pTxD->LastSec0 = 0;
7550 + pTxD->LastSec1 = (bIsLast) ? 1 : 0;
7551 +
7552 + RTMPWriteTxDescriptor(pAd, pTxD, FALSE, FIFO_EDCA);
7553 +#ifdef RT_BIG_ENDIAN
7554 + RTMPWIEndianChange((PUCHAR)(pDMAHeaderBufVA + TXINFO_SIZE), TYPE_TXWI);
7555 + RTMPFrameEndianChange(pAd, (PUCHAR)(pDMAHeaderBufVA + TXINFO_SIZE + TXWI_SIZE), DIR_WRITE, FALSE);
7556 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
7557 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
7558 +#endif // RT_BIG_ENDIAN //
7559 +
7560 + RetTxIdx = TxIdx;
7561 + //
7562 + // Update Tx index
7563 + //
7564 + INC_RING_INDEX(TxIdx, TX_RING_SIZE);
7565 + pTxRing->TxCpuIdx = TxIdx;
7566 +
7567 + *FreeNumber -= 1;
7568 +
7569 + return RetTxIdx;
7570 +}
7571 +
7572 +
7573 +USHORT RtmpPCI_WriteMultiTxResource(
7574 + IN PRTMP_ADAPTER pAd,
7575 + IN TX_BLK *pTxBlk,
7576 + IN UCHAR frameNum,
7577 + OUT USHORT *FreeNumber)
7578 +{
7579 + BOOLEAN bIsLast;
7580 + UCHAR *pDMAHeaderBufVA;
7581 + USHORT TxIdx, RetTxIdx;
7582 + PTXD_STRUC pTxD;
7583 +#ifdef RT_BIG_ENDIAN
7584 + PTXD_STRUC pDestTxD;
7585 + TXD_STRUC TxD;
7586 +#endif
7587 + UINT32 BufBasePaLow;
7588 + PRTMP_TX_RING pTxRing;
7589 + USHORT hwHdrLen;
7590 + UINT32 firstDMALen;
7591 +
7592 + bIsLast = ((frameNum == (pTxBlk->TotalFrameNum - 1)) ? 1 : 0);
7593 +
7594 + //
7595 + // get Tx Ring Resource
7596 + //
7597 + pTxRing = &pAd->TxRing[pTxBlk->QueIdx];
7598 + TxIdx = pAd->TxRing[pTxBlk->QueIdx].TxCpuIdx;
7599 + pDMAHeaderBufVA = (PUCHAR) pTxRing->Cell[TxIdx].DmaBuf.AllocVa;
7600 + BufBasePaLow = RTMP_GetPhysicalAddressLow(pTxRing->Cell[TxIdx].DmaBuf.AllocPa);
7601 +
7602 + if (frameNum == 0)
7603 + {
7604 + // copy TXINFO + TXWI + WLAN Header + LLC into DMA Header Buffer
7605 + if (pTxBlk->TxFrameType == TX_AMSDU_FRAME)
7606 + //hwHdrLen = ROUND_UP(pTxBlk->MpduHeaderLen-LENGTH_AMSDU_SUBFRAMEHEAD, 4)+LENGTH_AMSDU_SUBFRAMEHEAD;
7607 + hwHdrLen = pTxBlk->MpduHeaderLen - LENGTH_AMSDU_SUBFRAMEHEAD + pTxBlk->HdrPadLen + LENGTH_AMSDU_SUBFRAMEHEAD;
7608 + else if (pTxBlk->TxFrameType == TX_RALINK_FRAME)
7609 + //hwHdrLen = ROUND_UP(pTxBlk->MpduHeaderLen-LENGTH_ARALINK_HEADER_FIELD, 4)+LENGTH_ARALINK_HEADER_FIELD;
7610 + hwHdrLen = pTxBlk->MpduHeaderLen - LENGTH_ARALINK_HEADER_FIELD + pTxBlk->HdrPadLen + LENGTH_ARALINK_HEADER_FIELD;
7611 + else
7612 + //hwHdrLen = ROUND_UP(pTxBlk->MpduHeaderLen, 4);
7613 + hwHdrLen = pTxBlk->MpduHeaderLen + pTxBlk->HdrPadLen;
7614 +
7615 + firstDMALen = TXINFO_SIZE + TXWI_SIZE + hwHdrLen;
7616 + }
7617 + else
7618 + {
7619 + firstDMALen = pTxBlk->MpduHeaderLen;
7620 + }
7621 +
7622 + NdisMoveMemory(pDMAHeaderBufVA, pTxBlk->HeaderBuf, firstDMALen);
7623 +
7624 + pTxRing->Cell[TxIdx].pNdisPacket = pTxBlk->pPacket;
7625 + pTxRing->Cell[TxIdx].pNextNdisPacket = NULL;
7626 +
7627 + //
7628 + // build Tx Descriptor
7629 + //
7630 +#ifndef RT_BIG_ENDIAN
7631 + pTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
7632 +#else
7633 + pDestTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
7634 + TxD = *pDestTxD;
7635 + pTxD = &TxD;
7636 +#endif
7637 + NdisZeroMemory(pTxD, TXD_SIZE);
7638 +
7639 + pTxD->SDPtr0 = BufBasePaLow;
7640 + pTxD->SDLen0 = firstDMALen; // include padding
7641 + pTxD->SDPtr1 = PCI_MAP_SINGLE(pAd, pTxBlk, 0, 1, PCI_DMA_TODEVICE);;
7642 + pTxD->SDLen1 = pTxBlk->SrcBufLen;
7643 + pTxD->LastSec0 = 0;
7644 + pTxD->LastSec1 = (bIsLast) ? 1 : 0;
7645 +
7646 + RTMPWriteTxDescriptor(pAd, pTxD, FALSE, FIFO_EDCA);
7647 +
7648 +#ifdef RT_BIG_ENDIAN
7649 + if (frameNum == 0)
7650 + RTMPFrameEndianChange(pAd, (PUCHAR)(pDMAHeaderBufVA+ TXINFO_SIZE + TXWI_SIZE), DIR_WRITE, FALSE);
7651 +
7652 + if (frameNum != 0)
7653 + RTMPWIEndianChange((PUCHAR)(pDMAHeaderBufVA + TXINFO_SIZE), TYPE_TXWI);
7654 +
7655 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
7656 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
7657 +#endif // RT_BIG_ENDIAN //
7658 +
7659 + RetTxIdx = TxIdx;
7660 + //
7661 + // Update Tx index
7662 + //
7663 + INC_RING_INDEX(TxIdx, TX_RING_SIZE);
7664 + pTxRing->TxCpuIdx = TxIdx;
7665 +
7666 + *FreeNumber -= 1;
7667 +
7668 + return RetTxIdx;
7669 +
7670 +}
7671 +
7672 +
7673 +VOID RtmpPCI_FinalWriteTxResource(
7674 + IN PRTMP_ADAPTER pAd,
7675 + IN TX_BLK *pTxBlk,
7676 + IN USHORT totalMPDUSize,
7677 + IN USHORT FirstTxIdx)
7678 +{
7679 +
7680 + PTXWI_STRUC pTxWI;
7681 + PRTMP_TX_RING pTxRing;
7682 +
7683 + //
7684 + // get Tx Ring Resource
7685 + //
7686 + pTxRing = &pAd->TxRing[pTxBlk->QueIdx];
7687 + pTxWI = (PTXWI_STRUC) pTxRing->Cell[FirstTxIdx].DmaBuf.AllocVa;
7688 + pTxWI->MPDUtotalByteCount = totalMPDUSize;
7689 +#ifdef RT_BIG_ENDIAN
7690 + RTMPWIEndianChange((PUCHAR)pTxWI, TYPE_TXWI);
7691 +#endif // RT_BIG_ENDIAN //
7692 +
7693 +}
7694 +
7695 +
7696 +VOID RtmpPCIDataLastTxIdx(
7697 + IN PRTMP_ADAPTER pAd,
7698 + IN UCHAR QueIdx,
7699 + IN USHORT LastTxIdx)
7700 +{
7701 + PTXD_STRUC pTxD;
7702 +#ifdef RT_BIG_ENDIAN
7703 + PTXD_STRUC pDestTxD;
7704 + TXD_STRUC TxD;
7705 +#endif
7706 + PRTMP_TX_RING pTxRing;
7707 +
7708 + //
7709 + // get Tx Ring Resource
7710 + //
7711 + pTxRing = &pAd->TxRing[QueIdx];
7712 +
7713 + //
7714 + // build Tx Descriptor
7715 + //
7716 +#ifndef RT_BIG_ENDIAN
7717 + pTxD = (PTXD_STRUC) pTxRing->Cell[LastTxIdx].AllocVa;
7718 +#else
7719 + pDestTxD = (PTXD_STRUC) pTxRing->Cell[LastTxIdx].AllocVa;
7720 + TxD = *pDestTxD;
7721 + pTxD = &TxD;
7722 +#endif
7723 +
7724 + pTxD->LastSec1 = 1;
7725 +
7726 +#ifdef RT_BIG_ENDIAN
7727 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
7728 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
7729 +#endif // RT_BIG_ENDIAN //
7730 +
7731 +}
7732 +
7733 +
7734 +USHORT RtmpPCI_WriteFragTxResource(
7735 + IN PRTMP_ADAPTER pAd,
7736 + IN TX_BLK *pTxBlk,
7737 + IN UCHAR fragNum,
7738 + OUT USHORT *FreeNumber)
7739 +{
7740 + UCHAR *pDMAHeaderBufVA;
7741 + USHORT TxIdx, RetTxIdx;
7742 + PTXD_STRUC pTxD;
7743 +#ifdef RT_BIG_ENDIAN
7744 + PTXD_STRUC pDestTxD;
7745 + TXD_STRUC TxD;
7746 +#endif
7747 + UINT32 BufBasePaLow;
7748 + PRTMP_TX_RING pTxRing;
7749 + USHORT hwHeaderLen;
7750 + UINT32 firstDMALen;
7751 +
7752 + //
7753 + // Get Tx Ring Resource
7754 + //
7755 + pTxRing = &pAd->TxRing[pTxBlk->QueIdx];
7756 + TxIdx = pAd->TxRing[pTxBlk->QueIdx].TxCpuIdx;
7757 + pDMAHeaderBufVA = (PUCHAR) pTxRing->Cell[TxIdx].DmaBuf.AllocVa;
7758 + BufBasePaLow = RTMP_GetPhysicalAddressLow(pTxRing->Cell[TxIdx].DmaBuf.AllocPa);
7759 +
7760 + //
7761 + // Copy TXINFO + TXWI + WLAN Header + LLC into DMA Header Buffer
7762 + //
7763 + hwHeaderLen = pTxBlk->MpduHeaderLen + pTxBlk->HdrPadLen;
7764 +
7765 + firstDMALen = TXINFO_SIZE + TXWI_SIZE + hwHeaderLen;
7766 + NdisMoveMemory(pDMAHeaderBufVA, pTxBlk->HeaderBuf, firstDMALen);
7767 +
7768 +
7769 + //
7770 + // Build Tx Descriptor
7771 + //
7772 +#ifndef RT_BIG_ENDIAN
7773 + pTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
7774 +#else
7775 + pDestTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
7776 + TxD = *pDestTxD;
7777 + pTxD = &TxD;
7778 +#endif
7779 + NdisZeroMemory(pTxD, TXD_SIZE);
7780 +
7781 + if (fragNum == pTxBlk->TotalFragNum)
7782 + {
7783 + pTxRing->Cell[TxIdx].pNdisPacket = pTxBlk->pPacket;
7784 + pTxRing->Cell[TxIdx].pNextNdisPacket = NULL;
7785 + }
7786 +
7787 + pTxD->SDPtr0 = BufBasePaLow;
7788 + pTxD->SDLen0 = firstDMALen; // include padding
7789 + pTxD->SDPtr1 = PCI_MAP_SINGLE(pAd, pTxBlk, 0, 1, PCI_DMA_TODEVICE);
7790 + pTxD->SDLen1 = pTxBlk->SrcBufLen;
7791 + pTxD->LastSec0 = 0;
7792 + pTxD->LastSec1 = 1;
7793 +
7794 + RTMPWriteTxDescriptor(pAd, pTxD, FALSE, FIFO_EDCA);
7795 +
7796 +#ifdef RT_BIG_ENDIAN
7797 + RTMPWIEndianChange((PUCHAR)(pDMAHeaderBufVA + TXINFO_SIZE), TYPE_TXWI);
7798 + RTMPFrameEndianChange(pAd, (PUCHAR)(pDMAHeaderBufVA + TXINFO_SIZE + TXWI_SIZE), DIR_WRITE, FALSE);
7799 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
7800 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
7801 +#endif // RT_BIG_ENDIAN //
7802 +
7803 + RetTxIdx = TxIdx;
7804 + pTxBlk->Priv += pTxBlk->SrcBufLen;
7805 +
7806 + //
7807 + // Update Tx index
7808 + //
7809 + INC_RING_INDEX(TxIdx, TX_RING_SIZE);
7810 + pTxRing->TxCpuIdx = TxIdx;
7811 +
7812 + *FreeNumber -= 1;
7813 +
7814 + return RetTxIdx;
7815 +
7816 +}
7817 +
7818 +/*
7819 + Must be run in Interrupt context
7820 + This function handle PCI specific TxDesc and cpu index update and kick the packet out.
7821 + */
7822 +int RtmpPCIMgmtKickOut(
7823 + IN RTMP_ADAPTER *pAd,
7824 + IN UCHAR QueIdx,
7825 + IN PNDIS_PACKET pPacket,
7826 + IN PUCHAR pSrcBufVA,
7827 + IN UINT SrcBufLen)
7828 +{
7829 + PTXD_STRUC pTxD;
7830 +#ifdef RT_BIG_ENDIAN
7831 + PTXD_STRUC pDestTxD;
7832 + TXD_STRUC TxD;
7833 +#endif
7834 + ULONG SwIdx = pAd->MgmtRing.TxCpuIdx;
7835 +
7836 +#ifdef RT_BIG_ENDIAN
7837 + pDestTxD = (PTXD_STRUC)pAd->MgmtRing.Cell[SwIdx].AllocVa;
7838 + TxD = *pDestTxD;
7839 + pTxD = &TxD;
7840 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
7841 +#else
7842 + pTxD = (PTXD_STRUC) pAd->MgmtRing.Cell[SwIdx].AllocVa;
7843 +#endif
7844 +
7845 + pAd->MgmtRing.Cell[SwIdx].pNdisPacket = pPacket;
7846 + pAd->MgmtRing.Cell[SwIdx].pNextNdisPacket = NULL;
7847 +
7848 + RTMPWriteTxDescriptor(pAd, pTxD, TRUE, FIFO_MGMT);
7849 + pTxD->LastSec0 = 1;
7850 + pTxD->LastSec1 = 1;
7851 + pTxD->DMADONE = 0;
7852 + pTxD->SDLen1 = 0;
7853 + pTxD->SDPtr0 = PCI_MAP_SINGLE(pAd, pSrcBufVA, SrcBufLen, 0, PCI_DMA_TODEVICE);;
7854 + pTxD->SDLen0 = SrcBufLen;
7855 +
7856 +#ifdef RT_BIG_ENDIAN
7857 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
7858 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
7859 +#endif
7860 +
7861 + pAd->RalinkCounters.KickTxCount++;
7862 + pAd->RalinkCounters.OneSecTxDoneCount++;
7863 +
7864 + // Increase TX_CTX_IDX, but write to register later.
7865 + INC_RING_INDEX(pAd->MgmtRing.TxCpuIdx, MGMT_RING_SIZE);
7866 +
7867 + RTMP_IO_WRITE32(pAd, TX_MGMTCTX_IDX, pAd->MgmtRing.TxCpuIdx);
7868 +
7869 + return 0;
7870 +}
7871 +
7872 +
7873 +#ifdef CONFIG_STA_SUPPORT
7874 +/*
7875 + ========================================================================
7876 +
7877 + Routine Description:
7878 + Check Rx descriptor, return NDIS_STATUS_FAILURE if any error dound
7879 +
7880 + Arguments:
7881 + pRxD Pointer to the Rx descriptor
7882 +
7883 + Return Value:
7884 + NDIS_STATUS_SUCCESS No err
7885 + NDIS_STATUS_FAILURE Error
7886 +
7887 + Note:
7888 +
7889 + ========================================================================
7890 +*/
7891 +NDIS_STATUS RTMPCheckRxError(
7892 + IN PRTMP_ADAPTER pAd,
7893 + IN PHEADER_802_11 pHeader,
7894 + IN PRXWI_STRUC pRxWI,
7895 + IN PRT28XX_RXD_STRUC pRxD)
7896 +{
7897 + PCIPHER_KEY pWpaKey;
7898 + INT dBm;
7899 +
7900 + // Phy errors & CRC errors
7901 + if (/*(pRxD->PhyErr) ||*/ (pRxD->Crc))
7902 + {
7903 + // Check RSSI for Noise Hist statistic collection.
7904 + dBm = (INT) (pRxWI->RSSI0) - pAd->BbpRssiToDbmDelta;
7905 + if (dBm <= -87)
7906 + pAd->StaCfg.RPIDensity[0] += 1;
7907 + else if (dBm <= -82)
7908 + pAd->StaCfg.RPIDensity[1] += 1;
7909 + else if (dBm <= -77)
7910 + pAd->StaCfg.RPIDensity[2] += 1;
7911 + else if (dBm <= -72)
7912 + pAd->StaCfg.RPIDensity[3] += 1;
7913 + else if (dBm <= -67)
7914 + pAd->StaCfg.RPIDensity[4] += 1;
7915 + else if (dBm <= -62)
7916 + pAd->StaCfg.RPIDensity[5] += 1;
7917 + else if (dBm <= -57)
7918 + pAd->StaCfg.RPIDensity[6] += 1;
7919 + else if (dBm > -57)
7920 + pAd->StaCfg.RPIDensity[7] += 1;
7921 +
7922 + return(NDIS_STATUS_FAILURE);
7923 + }
7924 +
7925 + // Add Rx size to channel load counter, we should ignore error counts
7926 + pAd->StaCfg.CLBusyBytes += (pRxD->SDL0 + 14);
7927 +
7928 + // Drop ToDs promiscous frame, it is opened due to CCX 2 channel load statistics
7929 + if (pHeader != NULL)
7930 + {
7931 + if (pHeader->FC.ToDs)
7932 + {
7933 + return(NDIS_STATUS_FAILURE);
7934 + }
7935 + }
7936 +
7937 + // Drop not U2M frames, cant's drop here because we will drop beacon in this case
7938 + // I am kind of doubting the U2M bit operation
7939 + // if (pRxD->U2M == 0)
7940 + // return(NDIS_STATUS_FAILURE);
7941 +
7942 + // drop decyption fail frame
7943 + if (pRxD->CipherErr)
7944 + {
7945 + if (pRxD->CipherErr == 2)
7946 + {DBGPRINT_RAW(RT_DEBUG_TRACE,("pRxD ERROR: ICV ok but MICErr "));}
7947 + else if (pRxD->CipherErr == 1)
7948 + {DBGPRINT_RAW(RT_DEBUG_TRACE,("pRxD ERROR: ICV Err "));}
7949 + else if (pRxD->CipherErr == 3)
7950 + DBGPRINT_RAW(RT_DEBUG_TRACE,("pRxD ERROR: Key not valid "));
7951 +
7952 + if (((pRxD->CipherErr & 1) == 1) && pAd->CommonCfg.bWirelessEvent && INFRA_ON(pAd))
7953 + RTMPSendWirelessEvent(pAd, IW_ICV_ERROR_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
7954 +
7955 + DBGPRINT_RAW(RT_DEBUG_TRACE,(" %d (len=%d, Mcast=%d, MyBss=%d, Wcid=%d, KeyId=%d)\n",
7956 + pRxD->CipherErr,
7957 + pRxD->SDL0,
7958 + pRxD->Mcast | pRxD->Bcast,
7959 + pRxD->MyBss,
7960 + pRxWI->WirelessCliID,
7961 + pRxWI->KeyIndex));
7962 +
7963 + //
7964 + // MIC Error
7965 + //
7966 + if (pRxD->CipherErr == 2)
7967 + {
7968 + pWpaKey = &pAd->SharedKey[BSS0][pRxWI->KeyIndex];
7969 +#ifdef WPA_SUPPLICANT_SUPPORT
7970 + if (pAd->StaCfg.WpaSupplicantUP)
7971 + WpaSendMicFailureToWpaSupplicant(pAd,
7972 + (pWpaKey->Type == PAIRWISEKEY) ? TRUE:FALSE);
7973 + else
7974 +#endif // WPA_SUPPLICANT_SUPPORT //
7975 + RTMPReportMicError(pAd, pWpaKey);
7976 +
7977 + if (((pRxD->CipherErr & 2) == 2) && pAd->CommonCfg.bWirelessEvent && INFRA_ON(pAd))
7978 + RTMPSendWirelessEvent(pAd, IW_MIC_ERROR_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
7979 +
7980 + DBGPRINT_RAW(RT_DEBUG_ERROR,("Rx MIC Value error\n"));
7981 + }
7982 +
7983 + if (pHeader == NULL)
7984 + return(NDIS_STATUS_SUCCESS);
7985 +
7986 + return(NDIS_STATUS_FAILURE);
7987 + }
7988 +
7989 + return(NDIS_STATUS_SUCCESS);
7990 +}
7991 +
7992 +/*
7993 + ==========================================================================
7994 + Description:
7995 + This routine sends command to firmware and turn our chip to power save mode.
7996 + Both RadioOff and .11 power save function needs to call this routine.
7997 + Input:
7998 + Level = GUIRADIO_OFF : GUI Radio Off mode
7999 + Level = DOT11POWERSAVE : 802.11 power save mode
8000 + Level = RTMP_HALT : When Disable device.
8001 +
8002 + ==========================================================================
8003 + */
8004 +VOID RT28xxPciAsicRadioOff(
8005 + IN PRTMP_ADAPTER pAd,
8006 + IN UCHAR Level,
8007 + IN USHORT TbttNumToNextWakeUp)
8008 +{
8009 + WPDMA_GLO_CFG_STRUC DmaCfg;
8010 + UCHAR i, tempBBP_R3 = 0;
8011 + BOOLEAN brc = FALSE, Cancelled;
8012 + UINT32 TbTTTime = 0;
8013 + UINT32 PsPollTime = 0, MACValue;
8014 + ULONG BeaconPeriodTime;
8015 + UINT32 RxDmaIdx, RxCpuIdx;
8016 + DBGPRINT(RT_DEBUG_TRACE, ("AsicRadioOff ===> TxCpuIdx = %d, TxDmaIdx = %d. RxCpuIdx = %d, RxDmaIdx = %d.\n", pAd->TxRing[0].TxCpuIdx, pAd->TxRing[0].TxDmaIdx, pAd->RxRing.RxCpuIdx, pAd->RxRing.RxDmaIdx));
8017 +
8018 + // Check Rx DMA busy status, if more than half is occupied, give up this radio off.
8019 + RTMP_IO_READ32(pAd, RX_DRX_IDX , &RxDmaIdx);
8020 + RTMP_IO_READ32(pAd, RX_CRX_IDX , &RxCpuIdx);
8021 + if ((RxDmaIdx > RxCpuIdx) && ((RxDmaIdx - RxCpuIdx) > RX_RING_SIZE/3))
8022 + {
8023 + DBGPRINT(RT_DEBUG_TRACE, ("AsicRadioOff ===> return1. RxDmaIdx = %d , RxCpuIdx = %d. \n", RxDmaIdx, RxCpuIdx));
8024 + return;
8025 + }
8026 + else if ((RxCpuIdx >= RxDmaIdx) && ((RxCpuIdx - RxDmaIdx) < RX_RING_SIZE/3))
8027 + {
8028 + DBGPRINT(RT_DEBUG_TRACE, ("AsicRadioOff ===> return2. RxCpuIdx = %d. RxDmaIdx = %d , \n", RxCpuIdx, RxDmaIdx));
8029 + return;
8030 + }
8031 +
8032 + // Once go into this function, disable tx because don't want too many packets in queue to prevent HW stops.
8033 + pAd->bPCIclkOffDisableTx = TRUE;
8034 +
8035 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
8036 + {
8037 + RTMPCancelTimer(&pAd->Mlme.RadioOnOffTimer, &Cancelled);
8038 + RTMPCancelTimer(&pAd->Mlme.PsPollTimer, &Cancelled);
8039 +
8040 + if (Level == DOT11POWERSAVE)
8041 + {
8042 + RTMP_IO_READ32(pAd, TBTT_TIMER, &TbTTTime);
8043 + TbTTTime &= 0x1ffff;
8044 + // 00. check if need to do sleep in this DTIM period. If next beacon will arrive within 30ms , ...doesn't necessarily sleep.
8045 + // TbTTTime uint = 64us, LEAD_TIME unit = 1024us, PsPollTime unit = 1ms
8046 + if (((64*TbTTTime) <((LEAD_TIME*1024) + 40000)) && (TbttNumToNextWakeUp == 0))
8047 + {
8048 + DBGPRINT(RT_DEBUG_TRACE, ("TbTTTime = 0x%x , give up this sleep. \n", TbTTTime));
8049 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
8050 + pAd->bPCIclkOffDisableTx = FALSE;
8051 + return;
8052 + }
8053 + else
8054 + {
8055 + PsPollTime = (64*TbTTTime- LEAD_TIME*1024)/1000;
8056 + PsPollTime -= 3;
8057 +
8058 + BeaconPeriodTime = pAd->CommonCfg.BeaconPeriod*102/100;
8059 + if (TbttNumToNextWakeUp > 0)
8060 + PsPollTime += ((TbttNumToNextWakeUp -1) * BeaconPeriodTime);
8061 +
8062 + pAd->Mlme.bPsPollTimerRunning = TRUE;
8063 + RTMPSetTimer(&pAd->Mlme.PsPollTimer, PsPollTime);
8064 + }
8065 + }
8066 + }
8067 +
8068 + // 0. Disable Tx DMA.
8069 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &DmaCfg.word);
8070 + DmaCfg.field.EnableTxDMA = 0;
8071 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, DmaCfg.word);
8072 +
8073 + // 1. Wait DMA not busy
8074 + i = 0;
8075 + do
8076 + {
8077 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &DmaCfg.word);
8078 + if ((DmaCfg.field.TxDMABusy == 0) && (DmaCfg.field.RxDMABusy == 0))
8079 + break;
8080 + RTMPusecDelay(20);
8081 + i++;
8082 + }while(i < 50);
8083 +
8084 + if (i >= 50)
8085 + {
8086 + DBGPRINT(RT_DEBUG_TRACE, ("DMA keeps busy. return on RT28xxPciAsicRadioOff ()\n"));
8087 + pAd->bPCIclkOffDisableTx = FALSE;
8088 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &DmaCfg.word);
8089 + DmaCfg.field.EnableTxDMA = 1;
8090 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, DmaCfg.word);
8091 + return;
8092 + }
8093 +
8094 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_IDLE_RADIO_OFF);
8095 +
8096 + // Set to 1R.
8097 + tempBBP_R3 = (pAd->StaCfg.BBPR3 & 0xE7);
8098 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, tempBBP_R3);
8099 +
8100 + // In Radio Off, we turn off RF clk, So now need to call ASICSwitchChannel again.
8101 + if (INFRA_ON(pAd) && (pAd->CommonCfg.CentralChannel != pAd->CommonCfg.Channel)
8102 + && (pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth == BW_40))
8103 + {
8104 + // Must using 40MHz.
8105 + AsicTurnOffRFClk(pAd, pAd->CommonCfg.CentralChannel);
8106 + }
8107 + else
8108 + {
8109 + // Must using 20MHz.
8110 + AsicTurnOffRFClk(pAd, pAd->CommonCfg.Channel);
8111 + }
8112 +
8113 + // When PCI clock is off, don't want to service interrupt.
8114 + RTMP_IO_WRITE32(pAd, INT_MASK_CSR, AutoWakeupInt);
8115 +
8116 + RTMP_IO_WRITE32(pAd, RX_CRX_IDX, pAd->RxRing.RxCpuIdx);
8117 + // Disable MAC Rx
8118 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL , &MACValue);
8119 + MACValue &= 0xf7;
8120 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL , MACValue);
8121 +
8122 + // 2. Send Sleep command
8123 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_STATUS, 0xffffffff);
8124 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_CID, 0xffffffff);
8125 + AsicSendCommandToMcu(pAd, 0x30, PowerSafeCID, 0xff, 0x00); // send POWER-SAVE command to MCU. Timeout unit:40us.
8126 + // 2-1. Wait command success
8127 + // Status = 1 : success, Status = 2, already sleep, Status = 3, Maybe MAC is busy so can't finish this task.
8128 + brc = AsicCheckCommanOk(pAd, PowerSafeCID);
8129 +
8130 + if (brc == FALSE)
8131 + {
8132 + // try again
8133 + AsicSendCommandToMcu(pAd, 0x30, PowerSafeCID, 0xff, 0x00); // send POWER-SAVE command to MCU. Timeout unit:40us.
8134 + //RTMPusecDelay(200);
8135 + brc = AsicCheckCommanOk(pAd, PowerSafeCID);
8136 + }
8137 +
8138 + // 3. After 0x30 command is ok, send radio off command. lowbyte = 0 for power safe.
8139 + // If 0x30 command is not ok this time, we can ignore 0x35 command. It will make sure not cause firmware'r problem.
8140 + if ((Level == DOT11POWERSAVE) && (brc == TRUE))
8141 + {
8142 + AsicSendCommandToMcu(pAd, 0x35, PowerRadioOffCID, 0, 0x00); // lowbyte = 0 means to do power safe, NOT turn off radio.
8143 + // 3-1. Wait command success
8144 + AsicCheckCommanOk(pAd, PowerRadioOffCID);
8145 + }
8146 + else if (brc == TRUE)
8147 + {
8148 + AsicSendCommandToMcu(pAd, 0x35, PowerRadioOffCID, 1, 0x00); // lowbyte = 0 means to do power safe, NOT turn off radio.
8149 + // 3-1. Wait command success
8150 + AsicCheckCommanOk(pAd, PowerRadioOffCID);
8151 + }
8152 +
8153 + // Wait DMA not busy
8154 + i = 0;
8155 + do
8156 + {
8157 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &DmaCfg.word);
8158 + if (DmaCfg.field.RxDMABusy == 0)
8159 + break;
8160 + RTMPusecDelay(20);
8161 + i++;
8162 + }while(i < 50);
8163 +
8164 + if (i >= 50)
8165 + {
8166 + DBGPRINT(RT_DEBUG_TRACE, ("DMA Rx keeps busy. on RT28xxPciAsicRadioOff ()\n"));
8167 + }
8168 + // disable DMA Rx.
8169 + {
8170 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &DmaCfg.word);
8171 + DmaCfg.field.EnableRxDMA = 0;
8172 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, DmaCfg.word);
8173 + }
8174 +
8175 + if (Level == DOT11POWERSAVE)
8176 + {
8177 + AUTO_WAKEUP_STRUC AutoWakeupCfg;
8178 + //RTMPSetTimer(&pAd->Mlme.PsPollTimer, 90);
8179 +
8180 + // we have decided to SLEEP, so at least do it for a BEACON period.
8181 + if (TbttNumToNextWakeUp == 0)
8182 + TbttNumToNextWakeUp = 1;
8183 +
8184 + AutoWakeupCfg.word = 0;
8185 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
8186 +
8187 + // 1. Set auto wake up timer.
8188 + AutoWakeupCfg.field.NumofSleepingTbtt = TbttNumToNextWakeUp - 1;
8189 + AutoWakeupCfg.field.EnableAutoWakeup = 1;
8190 + AutoWakeupCfg.field.AutoLeadTime = LEAD_TIME;
8191 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
8192 + }
8193 +
8194 + // 4-1. If it's to disable our device. Need to restore PCI Configuration Space to its original value.
8195 + if (Level == RTMP_HALT)
8196 + {
8197 + if ((brc == TRUE) && (i < 50))
8198 + RTMPPCIeLinkCtrlSetting(pAd, 1);
8199 + }
8200 + // 4. Set PCI configuration Space Link Comtrol fields. Only Radio Off needs to call this function
8201 + else
8202 + {
8203 + if ((brc == TRUE) && (i < 50))
8204 + RTMPPCIeLinkCtrlSetting(pAd, 3);
8205 + }
8206 +
8207 + pAd->bPCIclkOffDisableTx = FALSE;
8208 +}
8209 +
8210 +
8211 +/*
8212 + ==========================================================================
8213 + Description:
8214 + This routine sends command to firmware and turn our chip to wake up mode from power save mode.
8215 + Both RadioOn and .11 power save function needs to call this routine.
8216 + Input:
8217 + Level = GUIRADIO_OFF : call this function is from Radio Off to Radio On. Need to restore PCI host value.
8218 + Level = other value : normal wake up function.
8219 +
8220 + ==========================================================================
8221 + */
8222 +BOOLEAN RT28xxPciAsicRadioOn(
8223 + IN PRTMP_ADAPTER pAd,
8224 + IN UCHAR Level)
8225 +{
8226 + WPDMA_GLO_CFG_STRUC DmaCfg;
8227 + BOOLEAN Cancelled, brv = TRUE;
8228 + UINT32 MACValue;
8229 +
8230 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
8231 + {
8232 + pAd->Mlme.bPsPollTimerRunning = FALSE;
8233 + RTMPCancelTimer(&pAd->Mlme.PsPollTimer, &Cancelled);
8234 + if ((Level == GUIRADIO_OFF) || (Level == GUI_IDLE_POWER_SAVE))
8235 + {
8236 + DBGPRINT(RT_DEBUG_TRACE, ("RT28xxPciAsicRadioOn ()\n"));
8237 + // 1. Set PCI Link Control in Configuration Space.
8238 + RTMPPCIeLinkCtrlValueRestore(pAd, RESTORE_WAKEUP);
8239 + RTMPusecDelay(6000);
8240 + }
8241 + }
8242 +
8243 + pAd->bPCIclkOff = FALSE;
8244 +
8245 + // 2. Send wake up command.
8246 + AsicSendCommandToMcu(pAd, 0x31, PowerWakeCID, 0x00, 0x00);
8247 +
8248 + // 2-1. wait command ok.
8249 + brv = AsicCheckCommanOk(pAd, PowerWakeCID);
8250 + if (brv)
8251 + {
8252 + //RTMP_IO_WRITE32(pAd, INT_MASK_CSR, (DELAYINTMASK|RxINT));
8253 + NICEnableInterrupt(pAd);
8254 +
8255 + // 3. Enable Tx DMA.
8256 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &DmaCfg.word);
8257 + DmaCfg.field.EnableTxDMA = 1;
8258 + DmaCfg.field.EnableRxDMA = 1;
8259 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, DmaCfg.word);
8260 +
8261 + // Eable MAC Rx
8262 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL , &MACValue);
8263 + MACValue |= 0x8;
8264 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL , MACValue);
8265 +
8266 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_IDLE_RADIO_OFF);
8267 + if (Level == GUI_IDLE_POWER_SAVE)
8268 + {
8269 + // In Radio Off, we turn off RF clk, So now need to call ASICSwitchChannel again.
8270 + if (INFRA_ON(pAd) && (pAd->CommonCfg.CentralChannel != pAd->CommonCfg.Channel)
8271 + && (pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth == BW_40))
8272 + {
8273 + // Must using 40MHz.
8274 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
8275 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
8276 + }
8277 + else
8278 + {
8279 + // Must using 20MHz.
8280 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
8281 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
8282 + }
8283 + }
8284 + return TRUE;
8285 + }
8286 + else
8287 + return FALSE;
8288 +}
8289 +
8290 +VOID RT28xxPciStaAsicForceWakeup(
8291 + IN PRTMP_ADAPTER pAd,
8292 + IN BOOLEAN bFromTx)
8293 +{
8294 + AUTO_WAKEUP_STRUC AutoWakeupCfg;
8295 +
8296 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
8297 + return;
8298 +
8299 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WAKEUP_NOW))
8300 + {
8301 + DBGPRINT(RT_DEBUG_TRACE, ("waking up now!\n"));
8302 + return;
8303 + }
8304 +
8305 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_WAKEUP_NOW);
8306 +
8307 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
8308 + {
8309 + // Support PCIe Advance Power Save
8310 + if (bFromTx == TRUE)
8311 + {
8312 + pAd->Mlme.bPsPollTimerRunning = FALSE;
8313 + RTMPPCIeLinkCtrlValueRestore(pAd, RESTORE_WAKEUP);
8314 + RTMPusecDelay(3000);
8315 + DBGPRINT(RT_DEBUG_TRACE, ("=======AsicForceWakeup===bFromTx\n"));
8316 + }
8317 +
8318 + AutoWakeupCfg.word = 0;
8319 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
8320 +
8321 + if (RT28xxPciAsicRadioOn(pAd, DOT11POWERSAVE))
8322 + {
8323 + // In Radio Off, we turn off RF clk, So now need to call ASICSwitchChannel again.
8324 + if (INFRA_ON(pAd) && (pAd->CommonCfg.CentralChannel != pAd->CommonCfg.Channel)
8325 + && (pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth == BW_40))
8326 + {
8327 + // Must using 40MHz.
8328 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
8329 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
8330 + }
8331 + else
8332 + {
8333 + // Must using 20MHz.
8334 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
8335 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
8336 + }
8337 + }
8338 + }
8339 + else
8340 + {
8341 + // PCI, 2860-PCIe
8342 + AsicSendCommandToMcu(pAd, 0x31, 0xff, 0x00, 0x00);
8343 + AutoWakeupCfg.word = 0;
8344 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
8345 + }
8346 +
8347 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
8348 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_WAKEUP_NOW);
8349 + DBGPRINT(RT_DEBUG_TRACE, ("<=======RT28xxPciStaAsicForceWakeup\n"));
8350 +}
8351 +
8352 +VOID RT28xxPciStaAsicSleepThenAutoWakeup(
8353 + IN PRTMP_ADAPTER pAd,
8354 + IN USHORT TbttNumToNextWakeUp)
8355 +{
8356 + if (pAd->StaCfg.bRadio == FALSE)
8357 + {
8358 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
8359 + return;
8360 + }
8361 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
8362 + {
8363 + ULONG Now = 0;
8364 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WAKEUP_NOW))
8365 + {
8366 + DBGPRINT(RT_DEBUG_TRACE, ("waking up now!\n"));
8367 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
8368 + return;
8369 + }
8370 +
8371 + NdisGetSystemUpTime(&Now);
8372 + // If last send NULL fram time is too close to this receiving beacon (within 8ms), don't go to sleep for this DTM.
8373 + // Because Some AP can't queuing outgoing frames immediately.
8374 + if (((pAd->Mlme.LastSendNULLpsmTime + 8) >= Now) && (pAd->Mlme.LastSendNULLpsmTime <= Now))
8375 + {
8376 + DBGPRINT(RT_DEBUG_TRACE, ("Now = %lu, LastSendNULLpsmTime=%lu : RxCountSinceLastNULL = %lu. \n", Now, pAd->Mlme.LastSendNULLpsmTime, pAd->RalinkCounters.RxCountSinceLastNULL));
8377 + return;
8378 + }
8379 + else if ((pAd->RalinkCounters.RxCountSinceLastNULL > 0) && ((pAd->Mlme.LastSendNULLpsmTime + pAd->CommonCfg.BeaconPeriod) >= Now))
8380 + {
8381 + DBGPRINT(RT_DEBUG_TRACE, ("Now = %lu, LastSendNULLpsmTime=%lu: RxCountSinceLastNULL = %lu > 0 \n", Now, pAd->Mlme.LastSendNULLpsmTime, pAd->RalinkCounters.RxCountSinceLastNULL));
8382 + return;
8383 + }
8384 +
8385 + RT28xxPciAsicRadioOff(pAd, DOT11POWERSAVE, TbttNumToNextWakeUp);
8386 + }
8387 + else
8388 + {
8389 + AUTO_WAKEUP_STRUC AutoWakeupCfg;
8390 + // we have decided to SLEEP, so at least do it for a BEACON period.
8391 + if (TbttNumToNextWakeUp == 0)
8392 + TbttNumToNextWakeUp = 1;
8393 +
8394 + AutoWakeupCfg.word = 0;
8395 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
8396 + AutoWakeupCfg.field.NumofSleepingTbtt = TbttNumToNextWakeUp - 1;
8397 + AutoWakeupCfg.field.EnableAutoWakeup = 1;
8398 + AutoWakeupCfg.field.AutoLeadTime = 5;
8399 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
8400 + AsicSendCommandToMcu(pAd, 0x30, 0xff, 0xff, 0x00); // send POWER-SAVE command to MCU. Timeout 40us.
8401 + DBGPRINT(RT_DEBUG_TRACE, ("<-- %s, TbttNumToNextWakeUp=%d \n", __FUNCTION__, TbttNumToNextWakeUp));
8402 + }
8403 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_DOZE);
8404 +}
8405 +
8406 +VOID PsPollWakeExec(
8407 + IN PVOID SystemSpecific1,
8408 + IN PVOID FunctionContext,
8409 + IN PVOID SystemSpecific2,
8410 + IN PVOID SystemSpecific3)
8411 +{
8412 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
8413 + unsigned long flags;
8414 +
8415 + DBGPRINT(RT_DEBUG_TRACE,("-->PsPollWakeExec \n"));
8416 + RTMP_INT_LOCK(&pAd->irq_lock, flags);
8417 + if (pAd->Mlme.bPsPollTimerRunning)
8418 + {
8419 + RTMPPCIeLinkCtrlValueRestore(pAd, RESTORE_WAKEUP);
8420 + }
8421 + pAd->Mlme.bPsPollTimerRunning = FALSE;
8422 + RTMP_INT_UNLOCK(&pAd->irq_lock, flags);
8423 +}
8424 +
8425 +VOID RadioOnExec(
8426 + IN PVOID SystemSpecific1,
8427 + IN PVOID FunctionContext,
8428 + IN PVOID SystemSpecific2,
8429 + IN PVOID SystemSpecific3)
8430 +{
8431 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
8432 + WPDMA_GLO_CFG_STRUC DmaCfg;
8433 + BOOLEAN Cancelled;
8434 +
8435 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
8436 + {
8437 + DBGPRINT(RT_DEBUG_TRACE,("-->RadioOnExec() return on fOP_STATUS_DOZE == TRUE; \n"));
8438 + RTMPSetTimer(&pAd->Mlme.RadioOnOffTimer, 10);
8439 + return;
8440 + }
8441 +
8442 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
8443 + {
8444 + DBGPRINT(RT_DEBUG_TRACE,("-->RadioOnExec() return on SCAN_IN_PROGRESS; \n"));
8445 + RTMPSetTimer(&pAd->Mlme.RadioOnOffTimer, 10);
8446 + return;
8447 + }
8448 + pAd->Mlme.bPsPollTimerRunning = FALSE;
8449 + RTMPCancelTimer(&pAd->Mlme.PsPollTimer, &Cancelled);
8450 + if (pAd->StaCfg.bRadio == TRUE)
8451 + {
8452 + pAd->bPCIclkOff = FALSE;
8453 + RTMPRingCleanUp(pAd, QID_AC_BK);
8454 + RTMPRingCleanUp(pAd, QID_AC_BE);
8455 + RTMPRingCleanUp(pAd, QID_AC_VI);
8456 + RTMPRingCleanUp(pAd, QID_AC_VO);
8457 + RTMPRingCleanUp(pAd, QID_HCCA);
8458 + RTMPRingCleanUp(pAd, QID_MGMT);
8459 + RTMPRingCleanUp(pAd, QID_RX);
8460 +
8461 + // 2. Send wake up command.
8462 + AsicSendCommandToMcu(pAd, 0x31, PowerWakeCID, 0x00, 0x02);
8463 + // 2-1. wait command ok.
8464 + AsicCheckCommanOk(pAd, PowerWakeCID);
8465 +
8466 + // When PCI clock is off, don't want to service interrupt. So when back to clock on, enable interrupt.
8467 + NICEnableInterrupt(pAd);
8468 +
8469 + // 3. Enable Tx DMA.
8470 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &DmaCfg.word);
8471 + DmaCfg.field.EnableTxDMA = 1;
8472 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, DmaCfg.word);
8473 +
8474 + // In Radio Off, we turn off RF clk, So now need to call ASICSwitchChannel again.
8475 + if (INFRA_ON(pAd) && (pAd->CommonCfg.CentralChannel != pAd->CommonCfg.Channel)
8476 + && (pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth == BW_40))
8477 + {
8478 + // Must using 40MHz.
8479 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
8480 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
8481 + }
8482 + else
8483 + {
8484 + // Must using 20MHz.
8485 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
8486 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
8487 + }
8488 +
8489 + // Clear Radio off flag
8490 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
8491 +
8492 + // Set LED
8493 + RTMPSetLED(pAd, LED_RADIO_ON);
8494 +
8495 + if (pAd->StaCfg.Psm == PWR_ACTIVE)
8496 + {
8497 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, pAd->StaCfg.BBPR3);
8498 + }
8499 + }
8500 + else
8501 + {
8502 + RT28xxPciAsicRadioOff(pAd, GUIRADIO_OFF, 0);
8503 + }
8504 +}
8505 +
8506 +#endif // CONFIG_STA_SUPPORT //
8507 +
8508 +VOID RT28xxPciMlmeRadioOn(
8509 + IN PRTMP_ADAPTER pAd)
8510 +{
8511 + if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF))
8512 + return;
8513 +
8514 + DBGPRINT(RT_DEBUG_TRACE,("%s===>\n", __FUNCTION__));
8515 +
8516 + if ((pAd->OpMode == OPMODE_AP) ||
8517 + ((pAd->OpMode == OPMODE_STA) && (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))))
8518 + {
8519 + NICResetFromError(pAd);
8520 +
8521 + RTMPRingCleanUp(pAd, QID_AC_BK);
8522 + RTMPRingCleanUp(pAd, QID_AC_BE);
8523 + RTMPRingCleanUp(pAd, QID_AC_VI);
8524 + RTMPRingCleanUp(pAd, QID_AC_VO);
8525 + RTMPRingCleanUp(pAd, QID_HCCA);
8526 + RTMPRingCleanUp(pAd, QID_MGMT);
8527 + RTMPRingCleanUp(pAd, QID_RX);
8528 +
8529 + // Enable Tx/Rx
8530 + RTMPEnableRxTx(pAd);
8531 +
8532 + // Clear Radio off flag
8533 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
8534 +
8535 + // Set LED
8536 + RTMPSetLED(pAd, LED_RADIO_ON);
8537 + }
8538 +
8539 +#ifdef CONFIG_STA_SUPPORT
8540 + if ((pAd->OpMode == OPMODE_STA) &&
8541 + (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE)))
8542 + {
8543 + BOOLEAN Cancelled;
8544 +
8545 + RTMPPCIeLinkCtrlValueRestore(pAd, RESTORE_WAKEUP);
8546 +
8547 + pAd->Mlme.bPsPollTimerRunning = FALSE;
8548 + RTMPCancelTimer(&pAd->Mlme.PsPollTimer, &Cancelled);
8549 + RTMPCancelTimer(&pAd->Mlme.RadioOnOffTimer, &Cancelled);
8550 + RTMPSetTimer(&pAd->Mlme.RadioOnOffTimer, 10);
8551 + }
8552 +#endif // CONFIG_STA_SUPPORT //
8553 +}
8554 +
8555 +VOID RT28xxPciMlmeRadioOFF(
8556 + IN PRTMP_ADAPTER pAd)
8557 +{
8558 + WPDMA_GLO_CFG_STRUC GloCfg;
8559 + UINT32 i;
8560 +
8561 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF))
8562 + return;
8563 +
8564 + DBGPRINT(RT_DEBUG_TRACE,("%s===>\n", __FUNCTION__));
8565 +
8566 + // Set LED
8567 + RTMPSetLED(pAd, LED_RADIO_OFF);
8568 + // Set Radio off flag
8569 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
8570 +
8571 +#ifdef CONFIG_STA_SUPPORT
8572 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
8573 + {
8574 + BOOLEAN Cancelled;
8575 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
8576 + {
8577 + RTMPCancelTimer(&pAd->MlmeAux.ScanTimer, &Cancelled);
8578 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS);
8579 + }
8580 +
8581 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
8582 + {
8583 + BOOLEAN Cancelled;
8584 + pAd->Mlme.bPsPollTimerRunning = FALSE;
8585 + RTMPCancelTimer(&pAd->Mlme.PsPollTimer, &Cancelled);
8586 + RTMPCancelTimer(&pAd->Mlme.RadioOnOffTimer, &Cancelled);
8587 + }
8588 +
8589 + // Link down first if any association exists
8590 + if (INFRA_ON(pAd) || ADHOC_ON(pAd))
8591 + LinkDown(pAd, FALSE);
8592 + RTMPusecDelay(10000);
8593 + //==========================================
8594 + // Clean up old bss table
8595 + BssTableInit(&pAd->ScanTab);
8596 + }
8597 +#endif // CONFIG_STA_SUPPORT //
8598 +
8599 + // Disable Tx/Rx DMA
8600 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word); // disable DMA
8601 + GloCfg.field.EnableTxDMA = 0;
8602 + GloCfg.field.EnableRxDMA = 0;
8603 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word); // abort all TX rings
8604 +
8605 +
8606 + // MAC_SYS_CTRL => value = 0x0 => 40mA
8607 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0);
8608 +
8609 + // PWR_PIN_CFG => value = 0x0 => 40mA
8610 + RTMP_IO_WRITE32(pAd, PWR_PIN_CFG, 0);
8611 +
8612 + // TX_PIN_CFG => value = 0x0 => 20mA
8613 + RTMP_IO_WRITE32(pAd, TX_PIN_CFG, 0);
8614 +
8615 + if (pAd->CommonCfg.BBPCurrentBW == BW_40)
8616 + {
8617 + // Must using 40MHz.
8618 + AsicTurnOffRFClk(pAd, pAd->CommonCfg.CentralChannel);
8619 + }
8620 + else
8621 + {
8622 + // Must using 20MHz.
8623 + AsicTurnOffRFClk(pAd, pAd->CommonCfg.Channel);
8624 + }
8625 +
8626 + // Waiting for DMA idle
8627 + i = 0;
8628 + do
8629 + {
8630 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word);
8631 + if ((GloCfg.field.TxDMABusy == 0) && (GloCfg.field.RxDMABusy == 0))
8632 + break;
8633 +
8634 + RTMPusecDelay(1000);
8635 + }while (i++ < 100);
8636 +}
8637 --- /dev/null
8638 +++ b/drivers/staging/rt2860/common/cmm_data.c
8639 @@ -0,0 +1,3469 @@
8640 +/*
8641 + *************************************************************************
8642 + * Ralink Tech Inc.
8643 + * 5F., No.36, Taiyuan St., Jhubei City,
8644 + * Hsinchu County 302,
8645 + * Taiwan, R.O.C.
8646 + *
8647 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
8648 + *
8649 + * This program is free software; you can redistribute it and/or modify *
8650 + * it under the terms of the GNU General Public License as published by *
8651 + * the Free Software Foundation; either version 2 of the License, or *
8652 + * (at your option) any later version. *
8653 + * *
8654 + * This program is distributed in the hope that it will be useful, *
8655 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
8656 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
8657 + * GNU General Public License for more details. *
8658 + * *
8659 + * You should have received a copy of the GNU General Public License *
8660 + * along with this program; if not, write to the *
8661 + * Free Software Foundation, Inc., *
8662 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
8663 + * *
8664 + *************************************************************************
8665 +*/
8666 +
8667 +#include "../rt_config.h"
8668 +
8669 +#define MAX_TX_IN_TBTT (16)
8670 +
8671 +
8672 +UCHAR SNAP_802_1H[] = {0xaa, 0xaa, 0x03, 0x00, 0x00, 0x00};
8673 +UCHAR SNAP_BRIDGE_TUNNEL[] = {0xaa, 0xaa, 0x03, 0x00, 0x00, 0xf8};
8674 +// Add Cisco Aironet SNAP heade for CCX2 support
8675 +UCHAR SNAP_AIRONET[] = {0xaa, 0xaa, 0x03, 0x00, 0x40, 0x96, 0x00, 0x00};
8676 +UCHAR CKIP_LLC_SNAP[] = {0xaa, 0xaa, 0x03, 0x00, 0x40, 0x96, 0x00, 0x02};
8677 +UCHAR EAPOL_LLC_SNAP[]= {0xaa, 0xaa, 0x03, 0x00, 0x00, 0x00, 0x88, 0x8e};
8678 +UCHAR EAPOL[] = {0x88, 0x8e};
8679 +UCHAR TPID[] = {0x81, 0x00}; /* VLAN related */
8680 +
8681 +UCHAR IPX[] = {0x81, 0x37};
8682 +UCHAR APPLE_TALK[] = {0x80, 0xf3};
8683 +UCHAR RateIdToPlcpSignal[12] = {
8684 + 0, /* RATE_1 */ 1, /* RATE_2 */ 2, /* RATE_5_5 */ 3, /* RATE_11 */ // see BBP spec
8685 + 11, /* RATE_6 */ 15, /* RATE_9 */ 10, /* RATE_12 */ 14, /* RATE_18 */ // see IEEE802.11a-1999 p.14
8686 + 9, /* RATE_24 */ 13, /* RATE_36 */ 8, /* RATE_48 */ 12 /* RATE_54 */ }; // see IEEE802.11a-1999 p.14
8687 +
8688 +UCHAR OfdmSignalToRateId[16] = {
8689 + RATE_54, RATE_54, RATE_54, RATE_54, // OFDM PLCP Signal = 0, 1, 2, 3 respectively
8690 + RATE_54, RATE_54, RATE_54, RATE_54, // OFDM PLCP Signal = 4, 5, 6, 7 respectively
8691 + RATE_48, RATE_24, RATE_12, RATE_6, // OFDM PLCP Signal = 8, 9, 10, 11 respectively
8692 + RATE_54, RATE_36, RATE_18, RATE_9, // OFDM PLCP Signal = 12, 13, 14, 15 respectively
8693 +};
8694 +
8695 +UCHAR OfdmRateToRxwiMCS[12] = {
8696 + 0, 0, 0, 0,
8697 + 0, 1, 2, 3, // OFDM rate 6,9,12,18 = rxwi mcs 0,1,2,3
8698 + 4, 5, 6, 7, // OFDM rate 24,36,48,54 = rxwi mcs 4,5,6,7
8699 +};
8700 +UCHAR RxwiMCSToOfdmRate[12] = {
8701 + RATE_6, RATE_9, RATE_12, RATE_18,
8702 + RATE_24, RATE_36, RATE_48, RATE_54, // OFDM rate 6,9,12,18 = rxwi mcs 0,1,2,3
8703 + 4, 5, 6, 7, // OFDM rate 24,36,48,54 = rxwi mcs 4,5,6,7
8704 +};
8705 +
8706 +char* MCSToMbps[] = {"1Mbps","2Mbps","5.5Mbps","11Mbps","06Mbps","09Mbps","12Mbps","18Mbps","24Mbps","36Mbps","48Mbps","54Mbps","MM-0","MM-1","MM-2","MM-3","MM-4","MM-5","MM-6","MM-7","MM-8","MM-9","MM-10","MM-11","MM-12","MM-13","MM-14","MM-15","MM-32","ee1","ee2","ee3"};
8707 +
8708 +UCHAR default_cwmin[]={CW_MIN_IN_BITS, CW_MIN_IN_BITS, CW_MIN_IN_BITS-1, CW_MIN_IN_BITS-2};
8709 +UCHAR default_sta_aifsn[]={3,7,2,2};
8710 +
8711 +UCHAR MapUserPriorityToAccessCategory[8] = {QID_AC_BE, QID_AC_BK, QID_AC_BK, QID_AC_BE, QID_AC_VI, QID_AC_VI, QID_AC_VO, QID_AC_VO};
8712 +
8713 +
8714 +/*
8715 + ========================================================================
8716 +
8717 + Routine Description:
8718 + API for MLME to transmit management frame to AP (BSS Mode)
8719 + or station (IBSS Mode)
8720 +
8721 + Arguments:
8722 + pAd Pointer to our adapter
8723 + pData Pointer to the outgoing 802.11 frame
8724 + Length Size of outgoing management frame
8725 +
8726 + Return Value:
8727 + NDIS_STATUS_FAILURE
8728 + NDIS_STATUS_PENDING
8729 + NDIS_STATUS_SUCCESS
8730 +
8731 + IRQL = PASSIVE_LEVEL
8732 + IRQL = DISPATCH_LEVEL
8733 +
8734 + Note:
8735 +
8736 + ========================================================================
8737 +*/
8738 +NDIS_STATUS MiniportMMRequest(
8739 + IN PRTMP_ADAPTER pAd,
8740 + IN UCHAR QueIdx,
8741 + IN PUCHAR pData,
8742 + IN UINT Length)
8743 +{
8744 + PNDIS_PACKET pPacket;
8745 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
8746 + ULONG FreeNum;
8747 +#ifdef RT2860
8748 + unsigned long IrqFlags = 0;
8749 +#endif // RT2860 //
8750 + UCHAR IrqState;
8751 + UCHAR rtmpHwHdr[TXINFO_SIZE + TXWI_SIZE]; //RTMP_HW_HDR_LEN];
8752 +
8753 + ASSERT(Length <= MGMT_DMA_BUFFER_SIZE);
8754 +
8755 + QueIdx=3;
8756 +
8757 + // 2860C use Tx Ring
8758 +
8759 + IrqState = pAd->irq_disabled;
8760 +#ifdef RT2860
8761 + if ((pAd->MACVersion == 0x28600100) && (!IrqState))
8762 + RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
8763 +#endif // RT2860 //
8764 +
8765 + do
8766 + {
8767 + // Reset is in progress, stop immediately
8768 + if ( RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||
8769 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST)||
8770 + !RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_START_UP))
8771 + {
8772 + Status = NDIS_STATUS_FAILURE;
8773 + break;
8774 + }
8775 +
8776 + // Check Free priority queue
8777 + // Since we use PBF Queue2 for management frame. Its corresponding DMA ring should be using TxRing.
8778 +
8779 + // 2860C use Tx Ring
8780 + if (pAd->MACVersion == 0x28600100)
8781 + {
8782 + FreeNum = GET_TXRING_FREENO(pAd, QueIdx);
8783 + }
8784 + else
8785 + {
8786 + FreeNum = GET_MGMTRING_FREENO(pAd);
8787 + }
8788 +
8789 + if ((FreeNum > 0))
8790 + {
8791 + // We need to reserve space for rtmp hardware header. i.e., TxWI for RT2860 and TxInfo+TxWI for RT2870
8792 + NdisZeroMemory(&rtmpHwHdr, (TXINFO_SIZE + TXWI_SIZE));
8793 + Status = RTMPAllocateNdisPacket(pAd, &pPacket, (PUCHAR)&rtmpHwHdr, (TXINFO_SIZE + TXWI_SIZE), pData, Length);
8794 + if (Status != NDIS_STATUS_SUCCESS)
8795 + {
8796 + DBGPRINT(RT_DEBUG_WARN, ("MiniportMMRequest (error:: can't allocate NDIS PACKET)\n"));
8797 + break;
8798 + }
8799 +
8800 + //pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_CCK;
8801 + //pAd->CommonCfg.MlmeRate = RATE_2;
8802 +
8803 +
8804 + Status = MlmeHardTransmit(pAd, QueIdx, pPacket);
8805 + if (Status != NDIS_STATUS_SUCCESS)
8806 + RTMPFreeNdisPacket(pAd, pPacket);
8807 + }
8808 + else
8809 + {
8810 + pAd->RalinkCounters.MgmtRingFullCount++;
8811 + DBGPRINT(RT_DEBUG_ERROR, ("Qidx(%d), not enough space in MgmtRing, MgmtRingFullCount=%ld!\n",
8812 + QueIdx, pAd->RalinkCounters.MgmtRingFullCount));
8813 + }
8814 +
8815 + } while (FALSE);
8816 +
8817 +#ifdef RT2860
8818 + // 2860C use Tx Ring
8819 + if ((pAd->MACVersion == 0x28600100) && (!IrqState))
8820 + RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
8821 +#endif // RT2860 //
8822 +
8823 + return Status;
8824 +}
8825 +
8826 +
8827 +#ifdef RT2860
8828 +NDIS_STATUS MiniportMMRequestUnlock(
8829 + IN PRTMP_ADAPTER pAd,
8830 + IN UCHAR QueIdx,
8831 + IN PUCHAR pData,
8832 + IN UINT Length)
8833 +{
8834 + PNDIS_PACKET pPacket;
8835 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
8836 + ULONG FreeNum;
8837 + TXWI_STRUC TXWI;
8838 + ULONG SW_TX_IDX;
8839 + PTXD_STRUC pTxD;
8840 +
8841 + QueIdx = 3;
8842 + ASSERT(Length <= MGMT_DMA_BUFFER_SIZE);
8843 +
8844 + do
8845 + {
8846 + // Reset is in progress, stop immediately
8847 + if ( RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||
8848 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST)||
8849 + !RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_START_UP))
8850 + {
8851 + Status = NDIS_STATUS_FAILURE;
8852 + break;
8853 + }
8854 +
8855 + // Check Free priority queue
8856 + // Since we use PBF Queue2 for management frame. Its corresponding DMA ring should be using TxRing.
8857 + // 2860C use Tx Ring
8858 + if (pAd->MACVersion == 0x28600100)
8859 + {
8860 + FreeNum = GET_TXRING_FREENO(pAd, QueIdx);
8861 + SW_TX_IDX = pAd->TxRing[QueIdx].TxCpuIdx;
8862 + pTxD = (PTXD_STRUC) pAd->TxRing[QueIdx].Cell[SW_TX_IDX].AllocVa;
8863 + }
8864 + else
8865 + {
8866 + FreeNum = GET_MGMTRING_FREENO(pAd);
8867 + SW_TX_IDX = pAd->MgmtRing.TxCpuIdx;
8868 + pTxD = (PTXD_STRUC) pAd->MgmtRing.Cell[SW_TX_IDX].AllocVa;
8869 + }
8870 + if ((FreeNum > 0))
8871 + {
8872 + NdisZeroMemory(&TXWI, TXWI_SIZE);
8873 + Status = RTMPAllocateNdisPacket(pAd, &pPacket, (PUCHAR)&TXWI, TXWI_SIZE, pData, Length);
8874 + if (Status != NDIS_STATUS_SUCCESS)
8875 + {
8876 + DBGPRINT(RT_DEBUG_WARN, ("MiniportMMRequest (error:: can't allocate NDIS PACKET)\n"));
8877 + break;
8878 + }
8879 +
8880 + Status = MlmeHardTransmit(pAd, QueIdx, pPacket);
8881 + if (Status != NDIS_STATUS_SUCCESS)
8882 + RTMPFreeNdisPacket(pAd, pPacket);
8883 + }
8884 + else
8885 + {
8886 + pAd->RalinkCounters.MgmtRingFullCount++;
8887 + DBGPRINT(RT_DEBUG_ERROR, ("Qidx(%d), not enough space in MgmtRing\n", QueIdx));
8888 + }
8889 +
8890 + } while (FALSE);
8891 +
8892 +
8893 + return Status;
8894 +}
8895 +#endif // RT2860 //
8896 +
8897 +
8898 +/*
8899 + ========================================================================
8900 +
8901 + Routine Description:
8902 + Copy frame from waiting queue into relative ring buffer and set
8903 + appropriate ASIC register to kick hardware transmit function
8904 +
8905 + Arguments:
8906 + pAd Pointer to our adapter
8907 + pBuffer Pointer to memory of outgoing frame
8908 + Length Size of outgoing management frame
8909 +
8910 + Return Value:
8911 + NDIS_STATUS_FAILURE
8912 + NDIS_STATUS_PENDING
8913 + NDIS_STATUS_SUCCESS
8914 +
8915 + IRQL = PASSIVE_LEVEL
8916 + IRQL = DISPATCH_LEVEL
8917 +
8918 + Note:
8919 +
8920 + ========================================================================
8921 +*/
8922 +NDIS_STATUS MlmeHardTransmit(
8923 + IN PRTMP_ADAPTER pAd,
8924 + IN UCHAR QueIdx,
8925 + IN PNDIS_PACKET pPacket)
8926 +{
8927 + if (pAd->CommonCfg.RadarDetect.RDMode != RD_NORMAL_MODE)
8928 + {
8929 + return NDIS_STATUS_FAILURE;
8930 + }
8931 +
8932 +#ifdef RT2860
8933 + if ( pAd->MACVersion == 0x28600100 )
8934 + return MlmeHardTransmitTxRing(pAd,QueIdx,pPacket);
8935 + else
8936 +#endif // RT2860 //
8937 + return MlmeHardTransmitMgmtRing(pAd,QueIdx,pPacket);
8938 +
8939 +}
8940 +
8941 +
8942 +#ifdef RT2860
8943 +NDIS_STATUS MlmeHardTransmitTxRing(
8944 + IN PRTMP_ADAPTER pAd,
8945 + IN UCHAR QueIdx,
8946 + IN PNDIS_PACKET pPacket)
8947 +{
8948 + PACKET_INFO PacketInfo;
8949 + PUCHAR pSrcBufVA;
8950 + UINT SrcBufLen;
8951 + PTXD_STRUC pTxD;
8952 +#ifdef RT_BIG_ENDIAN
8953 + PTXD_STRUC pDestTxD;
8954 + TXD_STRUC TxD;
8955 +#endif
8956 + PHEADER_802_11 pHeader_802_11;
8957 + BOOLEAN bAckRequired, bInsertTimestamp;
8958 + ULONG SrcBufPA;
8959 + UCHAR MlmeRate;
8960 + ULONG SwIdx = pAd->TxRing[QueIdx].TxCpuIdx;
8961 + PTXWI_STRUC pFirstTxWI;
8962 + ULONG FreeNum;
8963 + MAC_TABLE_ENTRY *pMacEntry = NULL;
8964 +
8965 +
8966 + RTMP_QueryPacketInfo(pPacket, &PacketInfo, &pSrcBufVA, &SrcBufLen);
8967 +
8968 + if (pSrcBufVA == NULL)
8969 + {
8970 + // The buffer shouldn't be NULL
8971 + return NDIS_STATUS_FAILURE;
8972 + }
8973 +
8974 + // Make sure MGMT ring resource won't be used by other threads
8975 + //NdisAcquireSpinLock(&pAd->TxRingLock);
8976 +
8977 + FreeNum = GET_TXRING_FREENO(pAd, QueIdx);
8978 +
8979 + if (FreeNum == 0)
8980 + {
8981 + //NdisReleaseSpinLock(&pAd->TxRingLock);
8982 + return NDIS_STATUS_FAILURE;
8983 + }
8984 +
8985 + SwIdx = pAd->TxRing[QueIdx].TxCpuIdx;
8986 +
8987 +#ifndef RT_BIG_ENDIAN
8988 + pTxD = (PTXD_STRUC) pAd->TxRing[QueIdx].Cell[SwIdx].AllocVa;
8989 +#else
8990 + pDestTxD = (PTXD_STRUC)pAd->TxRing[QueIdx].Cell[SwIdx].AllocVa;
8991 + TxD = *pDestTxD;
8992 + pTxD = &TxD;
8993 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
8994 +#endif
8995 +
8996 + if (pAd->TxRing[QueIdx].Cell[SwIdx].pNdisPacket)
8997 + {
8998 + printk("MlmeHardTransmit Error\n");
8999 + return NDIS_STATUS_FAILURE;
9000 + }
9001 +
9002 +
9003 +#ifdef CONFIG_STA_SUPPORT
9004 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
9005 + {
9006 + // outgoing frame always wakeup PHY to prevent frame lost
9007 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
9008 + AsicForceWakeup(pAd, TRUE);
9009 + }
9010 +#endif // CONFIG_STA_SUPPORT //
9011 + pFirstTxWI =(PTXWI_STRUC)pSrcBufVA;
9012 +
9013 + pHeader_802_11 = (PHEADER_802_11) (pSrcBufVA + TXWI_SIZE);
9014 + if (pHeader_802_11->Addr1[0] & 0x01)
9015 + {
9016 + MlmeRate = pAd->CommonCfg.BasicMlmeRate;
9017 + }
9018 + else
9019 + {
9020 + MlmeRate = pAd->CommonCfg.MlmeRate;
9021 + }
9022 +
9023 + if ((pHeader_802_11->FC.Type == BTYPE_DATA) &&
9024 + (pHeader_802_11->FC.SubType == SUBTYPE_QOS_NULL))
9025 + {
9026 + pMacEntry = MacTableLookup(pAd, pHeader_802_11->Addr1);
9027 + }
9028 +
9029 + // Verify Mlme rate for a / g bands.
9030 + if ((pAd->LatchRfRegs.Channel > 14) && (MlmeRate < RATE_6)) // 11A band
9031 + MlmeRate = RATE_6;
9032 +
9033 + //
9034 + // Should not be hard code to set PwrMgmt to 0 (PWR_ACTIVE)
9035 + // Snice it's been set to 0 while on MgtMacHeaderInit
9036 + // By the way this will cause frame to be send on PWR_SAVE failed.
9037 + //
9038 + //
9039 + // In WMM-UAPSD, mlme frame should be set psm as power saving but probe request frame
9040 +#ifdef CONFIG_STA_SUPPORT
9041 + // Data-Null packets alse pass through MMRequest in RT2860, however, we hope control the psm bit to pass APSD
9042 + if (pHeader_802_11->FC.Type != BTYPE_DATA)
9043 + {
9044 + if ((pHeader_802_11->FC.SubType == SUBTYPE_PROBE_REQ) || !(pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable))
9045 + {
9046 + pHeader_802_11->FC.PwrMgmt = PWR_ACTIVE;
9047 + }
9048 + else
9049 + {
9050 + pHeader_802_11->FC.PwrMgmt = pAd->CommonCfg.bAPSDForcePowerSave;
9051 + }
9052 + }
9053 +#endif // CONFIG_STA_SUPPORT //
9054 +
9055 + bInsertTimestamp = FALSE;
9056 + if (pHeader_802_11->FC.Type == BTYPE_CNTL) // must be PS-POLL
9057 + {
9058 + bAckRequired = FALSE;
9059 + }
9060 + else // BTYPE_MGMT or BTYPE_DATA(must be NULL frame)
9061 + {
9062 + if (pHeader_802_11->Addr1[0] & 0x01) // MULTICAST, BROADCAST
9063 + {
9064 + bAckRequired = FALSE;
9065 + pHeader_802_11->Duration = 0;
9066 + }
9067 + else
9068 + {
9069 + bAckRequired = TRUE;
9070 + pHeader_802_11->Duration = RTMPCalcDuration(pAd, MlmeRate, 14);
9071 + if (pHeader_802_11->FC.SubType == SUBTYPE_PROBE_RSP)
9072 + {
9073 + bInsertTimestamp = TRUE;
9074 + }
9075 + }
9076 + }
9077 + pHeader_802_11->Sequence = pAd->Sequence++;
9078 + if (pAd->Sequence > 0xfff)
9079 + pAd->Sequence = 0;
9080 + // Before radar detection done, mgmt frame can not be sent but probe req
9081 + // Because we need to use probe req to trigger driver to send probe req in passive scan
9082 + if ((pHeader_802_11->FC.SubType != SUBTYPE_PROBE_REQ)
9083 + && (pAd->CommonCfg.bIEEE80211H == 1)
9084 + && (pAd->CommonCfg.RadarDetect.RDMode != RD_NORMAL_MODE))
9085 + {
9086 + DBGPRINT(RT_DEBUG_ERROR,("MlmeHardTransmit --> radar detect not in normal mode !!!\n"));
9087 + return (NDIS_STATUS_FAILURE);
9088 + }
9089 +
9090 +#ifdef RT_BIG_ENDIAN
9091 + RTMPFrameEndianChange(pAd, (PUCHAR)pHeader_802_11, DIR_WRITE, FALSE);
9092 +#endif
9093 + //
9094 + // fill scatter-and-gather buffer list into TXD. Internally created NDIS PACKET
9095 + // should always has only one ohysical buffer, and the whole frame size equals
9096 + // to the first scatter buffer size
9097 + //
9098 +
9099 + // Initialize TX Descriptor
9100 + // For inter-frame gap, the number is for this frame and next frame
9101 + // For MLME rate, we will fix as 2Mb to match other vendor's implement
9102 +
9103 +// management frame doesn't need encryption. so use RESERVED_WCID no matter u are sending to specific wcid or not.
9104 + // Only beacon use Nseq=TRUE. So here we use Nseq=FALSE.
9105 + if (pMacEntry == NULL)
9106 + {
9107 + RTMPWriteTxWI(pAd, pFirstTxWI, FALSE, FALSE, bInsertTimestamp, FALSE, bAckRequired, FALSE,
9108 + 0, RESERVED_WCID, (SrcBufLen - TXWI_SIZE), PID_MGMT, 0, (UCHAR)pAd->CommonCfg.MlmeTransmit.field.MCS, IFS_BACKOFF, FALSE, &pAd->CommonCfg.MlmeTransmit);
9109 + }
9110 + else
9111 + {
9112 + RTMPWriteTxWI(pAd, pFirstTxWI, FALSE, FALSE,
9113 + bInsertTimestamp, FALSE, bAckRequired, FALSE,
9114 + 0, pMacEntry->Aid, (SrcBufLen - TXWI_SIZE),
9115 + pMacEntry->MaxHTPhyMode.field.MCS, 0,
9116 + (UCHAR)pMacEntry->MaxHTPhyMode.field.MCS,
9117 + IFS_BACKOFF, FALSE, &pMacEntry->MaxHTPhyMode);
9118 + }
9119 +
9120 + pAd->TxRing[QueIdx].Cell[SwIdx].pNdisPacket = pPacket;
9121 + pAd->TxRing[QueIdx].Cell[SwIdx].pNextNdisPacket = NULL;
9122 +#ifdef RT_BIG_ENDIAN
9123 + RTMPWIEndianChange((PUCHAR)pFirstTxWI, TYPE_TXWI);
9124 +#endif
9125 + SrcBufPA = PCI_MAP_SINGLE(pAd, pSrcBufVA, SrcBufLen, 0, PCI_DMA_TODEVICE);
9126 +
9127 +
9128 + RTMPWriteTxDescriptor(pAd, pTxD, TRUE, FIFO_EDCA);
9129 + pTxD->LastSec0 = 1;
9130 + pTxD->LastSec1 = 1;
9131 + pTxD->SDLen0 = SrcBufLen;
9132 + pTxD->SDLen1 = 0;
9133 + pTxD->SDPtr0 = SrcBufPA;
9134 + pTxD->DMADONE = 0;
9135 +
9136 +#ifdef RT_BIG_ENDIAN
9137 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
9138 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
9139 +#endif
9140 +
9141 + pAd->RalinkCounters.KickTxCount++;
9142 + pAd->RalinkCounters.OneSecTxDoneCount++;
9143 +
9144 + // Increase TX_CTX_IDX, but write to register later.
9145 + INC_RING_INDEX(pAd->TxRing[QueIdx].TxCpuIdx, TX_RING_SIZE);
9146 +
9147 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QueIdx*0x10, pAd->TxRing[QueIdx].TxCpuIdx);
9148 +
9149 + return NDIS_STATUS_SUCCESS;
9150 +}
9151 +#endif // RT2860 //
9152 +
9153 +
9154 +NDIS_STATUS MlmeHardTransmitMgmtRing(
9155 + IN PRTMP_ADAPTER pAd,
9156 + IN UCHAR QueIdx,
9157 + IN PNDIS_PACKET pPacket)
9158 +{
9159 + PACKET_INFO PacketInfo;
9160 + PUCHAR pSrcBufVA;
9161 + UINT SrcBufLen;
9162 + PHEADER_802_11 pHeader_802_11;
9163 + BOOLEAN bAckRequired, bInsertTimestamp;
9164 + UCHAR MlmeRate;
9165 + PTXWI_STRUC pFirstTxWI;
9166 + MAC_TABLE_ENTRY *pMacEntry = NULL;
9167 +
9168 + RTMP_QueryPacketInfo(pPacket, &PacketInfo, &pSrcBufVA, &SrcBufLen);
9169 + RTMP_SEM_LOCK(&pAd->MgmtRingLock);
9170 +
9171 +
9172 + if (pSrcBufVA == NULL)
9173 + {
9174 + RTMP_SEM_UNLOCK(&pAd->MgmtRingLock);
9175 + return NDIS_STATUS_FAILURE;
9176 + }
9177 +
9178 +#ifdef CONFIG_STA_SUPPORT
9179 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
9180 + {
9181 + // outgoing frame always wakeup PHY to prevent frame lost
9182 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
9183 + AsicForceWakeup(pAd, TRUE);
9184 + }
9185 +#endif // CONFIG_STA_SUPPORT //
9186 +
9187 + pFirstTxWI = (PTXWI_STRUC)(pSrcBufVA + TXINFO_SIZE);
9188 + pHeader_802_11 = (PHEADER_802_11) (pSrcBufVA + TXINFO_SIZE + TXWI_SIZE); //TXWI_SIZE);
9189 +
9190 + if (pHeader_802_11->Addr1[0] & 0x01)
9191 + {
9192 + MlmeRate = pAd->CommonCfg.BasicMlmeRate;
9193 + }
9194 + else
9195 + {
9196 + MlmeRate = pAd->CommonCfg.MlmeRate;
9197 + }
9198 +
9199 + // Verify Mlme rate for a / g bands.
9200 + if ((pAd->LatchRfRegs.Channel > 14) && (MlmeRate < RATE_6)) // 11A band
9201 + MlmeRate = RATE_6;
9202 +
9203 + if ((pHeader_802_11->FC.Type == BTYPE_DATA) &&
9204 + (pHeader_802_11->FC.SubType == SUBTYPE_QOS_NULL))
9205 + {
9206 + pMacEntry = MacTableLookup(pAd, pHeader_802_11->Addr1);
9207 + }
9208 +
9209 +#ifdef CONFIG_STA_SUPPORT
9210 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
9211 + {
9212 + // Fixed W52 with Activity scan issue in ABG_MIXED and ABGN_MIXED mode.
9213 + if (pAd->CommonCfg.PhyMode == PHY_11ABG_MIXED
9214 +#ifdef DOT11_N_SUPPORT
9215 + || pAd->CommonCfg.PhyMode == PHY_11ABGN_MIXED
9216 +#endif // DOT11_N_SUPPORT //
9217 + )
9218 + {
9219 + if (pAd->LatchRfRegs.Channel > 14)
9220 + pAd->CommonCfg.MlmeTransmit.field.MODE = 1;
9221 + else
9222 + pAd->CommonCfg.MlmeTransmit.field.MODE = 0;
9223 + }
9224 + }
9225 +#endif // CONFIG_STA_SUPPORT //
9226 +
9227 + //
9228 + // Should not be hard code to set PwrMgmt to 0 (PWR_ACTIVE)
9229 + // Snice it's been set to 0 while on MgtMacHeaderInit
9230 + // By the way this will cause frame to be send on PWR_SAVE failed.
9231 + //
9232 + // pHeader_802_11->FC.PwrMgmt = 0; // (pAd->StaCfg.Psm == PWR_SAVE);
9233 + //
9234 + // In WMM-UAPSD, mlme frame should be set psm as power saving but probe request frame
9235 +#ifdef CONFIG_STA_SUPPORT
9236 + // Data-Null packets alse pass through MMRequest in RT2860, however, we hope control the psm bit to pass APSD
9237 + if ((pHeader_802_11->FC.Type != BTYPE_DATA) && (pHeader_802_11->FC.Type != BTYPE_CNTL))
9238 + {
9239 + if ((pAd->StaCfg.Psm == PWR_SAVE) &&
9240 + (pHeader_802_11->FC.SubType == SUBTYPE_ACTION))
9241 + pHeader_802_11->FC.PwrMgmt = PWR_SAVE;
9242 + else
9243 + pHeader_802_11->FC.PwrMgmt = PWR_ACTIVE;
9244 + }
9245 +#endif // CONFIG_STA_SUPPORT //
9246 +
9247 + bInsertTimestamp = FALSE;
9248 + if (pHeader_802_11->FC.Type == BTYPE_CNTL) // must be PS-POLL
9249 + {
9250 +#ifdef CONFIG_STA_SUPPORT
9251 + //Set PM bit in ps-poll, to fix WLK 1.2 PowerSaveMode_ext failure issue.
9252 + if ((pAd->OpMode == OPMODE_STA) && (pHeader_802_11->FC.SubType == SUBTYPE_PS_POLL))
9253 + {
9254 + pHeader_802_11->FC.PwrMgmt = PWR_SAVE;
9255 + }
9256 +#endif // CONFIG_STA_SUPPORT //
9257 + bAckRequired = FALSE;
9258 + }
9259 + else // BTYPE_MGMT or BTYPE_DATA(must be NULL frame)
9260 + {
9261 + if (pHeader_802_11->Addr1[0] & 0x01) // MULTICAST, BROADCAST
9262 + {
9263 + bAckRequired = FALSE;
9264 + pHeader_802_11->Duration = 0;
9265 + }
9266 + else
9267 + {
9268 + bAckRequired = TRUE;
9269 + pHeader_802_11->Duration = RTMPCalcDuration(pAd, MlmeRate, 14);
9270 + if (pHeader_802_11->FC.SubType == SUBTYPE_PROBE_RSP)
9271 + {
9272 + bInsertTimestamp = TRUE;
9273 + }
9274 + }
9275 + }
9276 +
9277 + pHeader_802_11->Sequence = pAd->Sequence++;
9278 + if (pAd->Sequence >0xfff)
9279 + pAd->Sequence = 0;
9280 +
9281 + // Before radar detection done, mgmt frame can not be sent but probe req
9282 + // Because we need to use probe req to trigger driver to send probe req in passive scan
9283 + if ((pHeader_802_11->FC.SubType != SUBTYPE_PROBE_REQ)
9284 + && (pAd->CommonCfg.bIEEE80211H == 1)
9285 + && (pAd->CommonCfg.RadarDetect.RDMode != RD_NORMAL_MODE))
9286 + {
9287 + DBGPRINT(RT_DEBUG_ERROR,("MlmeHardTransmit --> radar detect not in normal mode !!!\n"));
9288 + RTMP_SEM_UNLOCK(&pAd->MgmtRingLock);
9289 + return (NDIS_STATUS_FAILURE);
9290 + }
9291 +
9292 +#ifdef RT_BIG_ENDIAN
9293 + RTMPFrameEndianChange(pAd, (PUCHAR)pHeader_802_11, DIR_WRITE, FALSE);
9294 +#endif
9295 +
9296 + //
9297 + // fill scatter-and-gather buffer list into TXD. Internally created NDIS PACKET
9298 + // should always has only one ohysical buffer, and the whole frame size equals
9299 + // to the first scatter buffer size
9300 + //
9301 +
9302 + // Initialize TX Descriptor
9303 + // For inter-frame gap, the number is for this frame and next frame
9304 + // For MLME rate, we will fix as 2Mb to match other vendor's implement
9305 +
9306 +// management frame doesn't need encryption. so use RESERVED_WCID no matter u are sending to specific wcid or not.
9307 + if (pMacEntry == NULL)
9308 + {
9309 + RTMPWriteTxWI(pAd, pFirstTxWI, FALSE, FALSE, bInsertTimestamp, FALSE, bAckRequired, FALSE,
9310 + 0, RESERVED_WCID, (SrcBufLen - TXINFO_SIZE - TXWI_SIZE), PID_MGMT, 0, (UCHAR)pAd->CommonCfg.MlmeTransmit.field.MCS, IFS_BACKOFF, FALSE, &pAd->CommonCfg.MlmeTransmit);
9311 + }
9312 + else
9313 + {
9314 + RTMPWriteTxWI(pAd, pFirstTxWI, FALSE, FALSE,
9315 + bInsertTimestamp, FALSE, bAckRequired, FALSE,
9316 + 0, pMacEntry->Aid, (SrcBufLen - TXINFO_SIZE - TXWI_SIZE),
9317 + pMacEntry->MaxHTPhyMode.field.MCS, 0,
9318 + (UCHAR)pMacEntry->MaxHTPhyMode.field.MCS,
9319 + IFS_BACKOFF, FALSE, &pMacEntry->MaxHTPhyMode);
9320 + }
9321 +
9322 +#ifdef RT_BIG_ENDIAN
9323 + RTMPWIEndianChange((PUCHAR)pFirstTxWI, TYPE_TXWI);
9324 +#endif
9325 +
9326 + // Now do hardware-depened kick out.
9327 + HAL_KickOutMgmtTx(pAd, QueIdx, pPacket, pSrcBufVA, SrcBufLen);
9328 +
9329 + // Make sure to release MGMT ring resource
9330 + RTMP_SEM_UNLOCK(&pAd->MgmtRingLock);
9331 + return NDIS_STATUS_SUCCESS;
9332 +}
9333 +
9334 +
9335 +/********************************************************************************
9336 +
9337 + New DeQueue Procedures.
9338 +
9339 + ********************************************************************************/
9340 +
9341 +#define DEQUEUE_LOCK(lock, bIntContext, IrqFlags) \
9342 + do{ \
9343 + if (bIntContext == FALSE) \
9344 + RTMP_IRQ_LOCK((lock), IrqFlags); \
9345 + }while(0)
9346 +
9347 +#define DEQUEUE_UNLOCK(lock, bIntContext, IrqFlags) \
9348 + do{ \
9349 + if (bIntContext == FALSE) \
9350 + RTMP_IRQ_UNLOCK((lock), IrqFlags); \
9351 + }while(0)
9352 +
9353 +/*
9354 + ========================================================================
9355 + Tx Path design algorithm:
9356 + Basically, we divide the packets into four types, Broadcast/Multicast, 11N Rate(AMPDU, AMSDU, Normal), B/G Rate(ARALINK, Normal),
9357 + Specific Packet Type. Following show the classification rule and policy for each kinds of packets.
9358 + Classification Rule=>
9359 + Multicast: (*addr1 & 0x01) == 0x01
9360 + Specific : bDHCPFrame, bARPFrame, bEAPOLFrame, etc.
9361 + 11N Rate : If peer support HT
9362 + (1).AMPDU -- If TXBA is negotiated.
9363 + (2).AMSDU -- If AMSDU is capable for both peer and ourself.
9364 + *). AMSDU can embedded in a AMPDU, but now we didn't support it.
9365 + (3).Normal -- Other packets which send as 11n rate.
9366 +
9367 + B/G Rate : If peer is b/g only.
9368 + (1).ARALINK-- If both of peer/us supprot Ralink proprietary Aggregation and the TxRate is large than RATE_6
9369 + (2).Normal -- Other packets which send as b/g rate.
9370 + Fragment:
9371 + The packet must be unicast, NOT A-RALINK, NOT A-MSDU, NOT 11n, then can consider about fragment.
9372 +
9373 + Classified Packet Handle Rule=>
9374 + Multicast:
9375 + No ACK, //pTxBlk->bAckRequired = FALSE;
9376 + No WMM, //pTxBlk->bWMM = FALSE;
9377 + No piggyback, //pTxBlk->bPiggyBack = FALSE;
9378 + Force LowRate, //pTxBlk->bForceLowRate = TRUE;
9379 + Specific : Basically, for specific packet, we should handle it specifically, but now all specific packets are use
9380 + the same policy to handle it.
9381 + Force LowRate, //pTxBlk->bForceLowRate = TRUE;
9382 +
9383 + 11N Rate :
9384 + No piggyback, //pTxBlk->bPiggyBack = FALSE;
9385 +
9386 + (1).AMSDU
9387 + pTxBlk->bWMM = TRUE;
9388 + (2).AMPDU
9389 + pTxBlk->bWMM = TRUE;
9390 + (3).Normal
9391 +
9392 + B/G Rate :
9393 + (1).ARALINK
9394 +
9395 + (2).Normal
9396 + ========================================================================
9397 +*/
9398 +static UCHAR TxPktClassification(
9399 + IN RTMP_ADAPTER *pAd,
9400 + IN PNDIS_PACKET pPacket)
9401 +{
9402 + UCHAR TxFrameType = TX_UNKOWN_FRAME;
9403 + UCHAR Wcid;
9404 + MAC_TABLE_ENTRY *pMacEntry = NULL;
9405 +#ifdef DOT11_N_SUPPORT
9406 + BOOLEAN bHTRate = FALSE;
9407 +#endif // DOT11_N_SUPPORT //
9408 +
9409 + Wcid = RTMP_GET_PACKET_WCID(pPacket);
9410 + if (Wcid == MCAST_WCID)
9411 + { // Handle for RA is Broadcast/Multicast Address.
9412 + return TX_MCAST_FRAME;
9413 + }
9414 +
9415 + // Handle for unicast packets
9416 + pMacEntry = &pAd->MacTab.Content[Wcid];
9417 + if (RTMP_GET_PACKET_LOWRATE(pPacket))
9418 + { // It's a specific packet need to force low rate, i.e., bDHCPFrame, bEAPOLFrame, bWAIFrame
9419 + TxFrameType = TX_LEGACY_FRAME;
9420 + }
9421 +#ifdef DOT11_N_SUPPORT
9422 + else if (IS_HT_RATE(pMacEntry))
9423 + { // it's a 11n capable packet
9424 +
9425 + // Depends on HTPhyMode to check if the peer support the HTRate transmission.
9426 + // Currently didn't support A-MSDU embedded in A-MPDU
9427 + bHTRate = TRUE;
9428 + if (RTMP_GET_PACKET_MOREDATA(pPacket) || (pMacEntry->PsMode == PWR_SAVE))
9429 + TxFrameType = TX_LEGACY_FRAME;
9430 +#ifdef UAPSD_AP_SUPPORT
9431 + else if (RTMP_GET_PACKET_EOSP(pPacket))
9432 + TxFrameType = TX_LEGACY_FRAME;
9433 +#endif // UAPSD_AP_SUPPORT //
9434 + else if((pMacEntry->TXBAbitmap & (1<<(RTMP_GET_PACKET_UP(pPacket)))) != 0)
9435 + return TX_AMPDU_FRAME;
9436 + else if(CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_AMSDU_INUSED))
9437 + return TX_AMSDU_FRAME;
9438 + else
9439 + TxFrameType = TX_LEGACY_FRAME;
9440 + }
9441 +#endif // DOT11_N_SUPPORT //
9442 + else
9443 + { // it's a legacy b/g packet.
9444 + if ((CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_AGGREGATION_CAPABLE) && pAd->CommonCfg.bAggregationCapable) &&
9445 + (RTMP_GET_PACKET_TXRATE(pPacket) >= RATE_6) &&
9446 + (!(OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED) && CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_WMM_CAPABLE))))
9447 + { // if peer support Ralink Aggregation, we use it.
9448 + TxFrameType = TX_RALINK_FRAME;
9449 + }
9450 + else
9451 + {
9452 + TxFrameType = TX_LEGACY_FRAME;
9453 + }
9454 + }
9455 +
9456 + // Currently, our fragment only support when a unicast packet send as NOT-ARALINK, NOT-AMSDU and NOT-AMPDU.
9457 + if ((RTMP_GET_PACKET_FRAGMENTS(pPacket) > 1) && (TxFrameType == TX_LEGACY_FRAME))
9458 + TxFrameType = TX_FRAG_FRAME;
9459 +
9460 + return TxFrameType;
9461 +}
9462 +
9463 +
9464 +BOOLEAN RTMP_FillTxBlkInfo(
9465 + IN RTMP_ADAPTER *pAd,
9466 + IN TX_BLK *pTxBlk)
9467 +{
9468 + PACKET_INFO PacketInfo;
9469 + PNDIS_PACKET pPacket;
9470 + PMAC_TABLE_ENTRY pMacEntry = NULL;
9471 +
9472 + pPacket = pTxBlk->pPacket;
9473 + RTMP_QueryPacketInfo(pPacket, &PacketInfo, &pTxBlk->pSrcBufHeader, &pTxBlk->SrcBufLen);
9474 +
9475 + pTxBlk->Wcid = RTMP_GET_PACKET_WCID(pPacket);
9476 + pTxBlk->apidx = RTMP_GET_PACKET_IF(pPacket);
9477 + pTxBlk->UserPriority = RTMP_GET_PACKET_UP(pPacket);
9478 + pTxBlk->FrameGap = IFS_HTTXOP; // ASIC determine Frame Gap
9479 +
9480 + if (RTMP_GET_PACKET_CLEAR_EAP_FRAME(pTxBlk->pPacket))
9481 + TX_BLK_SET_FLAG(pTxBlk, fTX_bClearEAPFrame);
9482 + else
9483 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bClearEAPFrame);
9484 +
9485 + // Default to clear this flag
9486 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bForceNonQoS);
9487 +
9488 +
9489 + if (pTxBlk->Wcid == MCAST_WCID)
9490 + {
9491 + pTxBlk->pMacEntry = NULL;
9492 + {
9493 +#ifdef MCAST_RATE_SPECIFIC
9494 + PUCHAR pDA = GET_OS_PKT_DATAPTR(pPacket);
9495 + if (((*pDA & 0x01) == 0x01) && (*pDA != 0xff))
9496 + pTxBlk->pTransmit = &pAd->CommonCfg.MCastPhyMode;
9497 + else
9498 +#endif // MCAST_RATE_SPECIFIC //
9499 + pTxBlk->pTransmit = &pAd->MacTab.Content[MCAST_WCID].HTPhyMode;
9500 + }
9501 +
9502 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bAckRequired); // AckRequired = FALSE, when broadcast packet in Adhoc mode.
9503 + //TX_BLK_SET_FLAG(pTxBlk, fTX_bForceLowRate);
9504 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bAllowFrag);
9505 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bWMM);
9506 + if (RTMP_GET_PACKET_MOREDATA(pPacket))
9507 + {
9508 + TX_BLK_SET_FLAG(pTxBlk, fTX_bMoreData);
9509 + }
9510 +
9511 + }
9512 + else
9513 + {
9514 + pTxBlk->pMacEntry = &pAd->MacTab.Content[pTxBlk->Wcid];
9515 + pTxBlk->pTransmit = &pTxBlk->pMacEntry->HTPhyMode;
9516 +
9517 + pMacEntry = pTxBlk->pMacEntry;
9518 +
9519 +
9520 + // For all unicast packets, need Ack unless the Ack Policy is not set as NORMAL_ACK.
9521 + if (pAd->CommonCfg.AckPolicy[pTxBlk->QueIdx] != NORMAL_ACK)
9522 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bAckRequired);
9523 + else
9524 + TX_BLK_SET_FLAG(pTxBlk, fTX_bAckRequired);
9525 +
9526 + {
9527 +
9528 +#ifdef CONFIG_STA_SUPPORT
9529 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
9530 + {
9531 +
9532 + // If support WMM, enable it.
9533 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED))
9534 + TX_BLK_SET_FLAG(pTxBlk, fTX_bWMM);
9535 + }
9536 +#endif // CONFIG_STA_SUPPORT //
9537 + }
9538 +
9539 + if (pTxBlk->TxFrameType == TX_LEGACY_FRAME)
9540 + {
9541 + if ( (RTMP_GET_PACKET_LOWRATE(pPacket)) ||
9542 + ((pAd->OpMode == OPMODE_AP) && (pMacEntry->MaxHTPhyMode.field.MODE == MODE_CCK) && (pMacEntry->MaxHTPhyMode.field.MCS == RATE_1)))
9543 + { // Specific packet, i.e., bDHCPFrame, bEAPOLFrame, bWAIFrame, need force low rate.
9544 + pTxBlk->pTransmit = &pAd->MacTab.Content[MCAST_WCID].HTPhyMode;
9545 +#ifdef DOT11_N_SUPPORT
9546 + // Modify the WMM bit for ICV issue. If we have a packet with EOSP field need to set as 1, how to handle it???
9547 + if (IS_HT_STA(pTxBlk->pMacEntry) &&
9548 + (CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_RALINK_CHIPSET)) &&
9549 + ((pAd->CommonCfg.bRdg == TRUE) && CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_RDG_CAPABLE)))
9550 + {
9551 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bWMM);
9552 + TX_BLK_SET_FLAG(pTxBlk, fTX_bForceNonQoS);
9553 + }
9554 +#endif // DOT11_N_SUPPORT //
9555 + }
9556 +
9557 +#ifdef DOT11_N_SUPPORT
9558 + if ( (IS_HT_RATE(pMacEntry) == FALSE) &&
9559 + (CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_PIGGYBACK_CAPABLE)))
9560 + { // Currently piggy-back only support when peer is operate in b/g mode.
9561 + TX_BLK_SET_FLAG(pTxBlk, fTX_bPiggyBack);
9562 + }
9563 +#endif // DOT11_N_SUPPORT //
9564 +
9565 + if (RTMP_GET_PACKET_MOREDATA(pPacket))
9566 + {
9567 + TX_BLK_SET_FLAG(pTxBlk, fTX_bMoreData);
9568 + }
9569 +#ifdef UAPSD_AP_SUPPORT
9570 + if (RTMP_GET_PACKET_EOSP(pPacket))
9571 + {
9572 + TX_BLK_SET_FLAG(pTxBlk, fTX_bWMM_UAPSD_EOSP);
9573 + }
9574 +#endif // UAPSD_AP_SUPPORT //
9575 + }
9576 + else if (pTxBlk->TxFrameType == TX_FRAG_FRAME)
9577 + {
9578 + TX_BLK_SET_FLAG(pTxBlk, fTX_bAllowFrag);
9579 + }
9580 +
9581 + pMacEntry->DebugTxCount++;
9582 + }
9583 +
9584 + return TRUE;
9585 +
9586 +FillTxBlkErr:
9587 + return FALSE;
9588 +}
9589 +
9590 +
9591 +BOOLEAN CanDoAggregateTransmit(
9592 + IN RTMP_ADAPTER *pAd,
9593 + IN NDIS_PACKET *pPacket,
9594 + IN TX_BLK *pTxBlk)
9595 +{
9596 +
9597 + //printk("Check if can do aggregation! TxFrameType=%d!\n", pTxBlk->TxFrameType);
9598 +
9599 + if (RTMP_GET_PACKET_WCID(pPacket) == MCAST_WCID)
9600 + return FALSE;
9601 +
9602 + if (RTMP_GET_PACKET_DHCP(pPacket) ||
9603 + RTMP_GET_PACKET_EAPOL(pPacket) ||
9604 + RTMP_GET_PACKET_WAI(pPacket))
9605 + return FALSE;
9606 +
9607 + if ((pTxBlk->TxFrameType == TX_AMSDU_FRAME) &&
9608 + ((pTxBlk->TotalFrameLen + GET_OS_PKT_LEN(pPacket))> (RX_BUFFER_AGGRESIZE - 100)))
9609 + { // For AMSDU, allow the packets with total length < max-amsdu size
9610 + return FALSE;
9611 + }
9612 +
9613 + if ((pTxBlk->TxFrameType == TX_RALINK_FRAME) &&
9614 + (pTxBlk->TxPacketList.Number == 2))
9615 + { // For RALINK-Aggregation, allow two frames in one batch.
9616 + return FALSE;
9617 + }
9618 +
9619 +#ifdef CONFIG_STA_SUPPORT
9620 + if ((INFRA_ON(pAd)) && (pAd->OpMode == OPMODE_STA)) // must be unicast to AP
9621 + return TRUE;
9622 + else
9623 +#endif // CONFIG_STA_SUPPORT //
9624 + return FALSE;
9625 +
9626 +}
9627 +
9628 +
9629 +/*
9630 + ========================================================================
9631 +
9632 + Routine Description:
9633 + To do the enqueue operation and extract the first item of waiting
9634 + list. If a number of available shared memory segments could meet
9635 + the request of extracted item, the extracted item will be fragmented
9636 + into shared memory segments.
9637 +
9638 + Arguments:
9639 + pAd Pointer to our adapter
9640 + pQueue Pointer to Waiting Queue
9641 +
9642 + Return Value:
9643 + None
9644 +
9645 + IRQL = DISPATCH_LEVEL
9646 +
9647 + Note:
9648 +
9649 + ========================================================================
9650 +*/
9651 +VOID RTMPDeQueuePacket(
9652 + IN PRTMP_ADAPTER pAd,
9653 + IN BOOLEAN bIntContext,
9654 + IN UCHAR QIdx, /* BulkOutPipeId */
9655 + IN UCHAR Max_Tx_Packets)
9656 +{
9657 + PQUEUE_ENTRY pEntry = NULL;
9658 + PNDIS_PACKET pPacket;
9659 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
9660 + UCHAR Count=0;
9661 + PQUEUE_HEADER pQueue;
9662 + ULONG FreeNumber[NUM_OF_TX_RING];
9663 + UCHAR QueIdx, sQIdx, eQIdx;
9664 + unsigned long IrqFlags = 0;
9665 + BOOLEAN hasTxDesc = FALSE;
9666 + TX_BLK TxBlk;
9667 + TX_BLK *pTxBlk;
9668 +
9669 +#ifdef DBG_DIAGNOSE
9670 + BOOLEAN firstRound;
9671 + RtmpDiagStruct *pDiagStruct = &pAd->DiagStruct;
9672 +#endif
9673 +
9674 +
9675 + if (QIdx == NUM_OF_TX_RING)
9676 + {
9677 + sQIdx = 0;
9678 + eQIdx = 3; // 4 ACs, start from 0.
9679 + }
9680 + else
9681 + {
9682 + sQIdx = eQIdx = QIdx;
9683 + }
9684 +
9685 + for (QueIdx=sQIdx; QueIdx <= eQIdx; QueIdx++)
9686 + {
9687 + Count=0;
9688 +
9689 + RT28XX_START_DEQUEUE(pAd, QueIdx, IrqFlags);
9690 +
9691 +#ifdef DBG_DIAGNOSE
9692 + firstRound = ((QueIdx == 0) ? TRUE : FALSE);
9693 +#endif // DBG_DIAGNOSE //
9694 +
9695 + while (1)
9696 + {
9697 + if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS |
9698 + fRTMP_ADAPTER_RADIO_OFF |
9699 + fRTMP_ADAPTER_RESET_IN_PROGRESS |
9700 + fRTMP_ADAPTER_HALT_IN_PROGRESS |
9701 + fRTMP_ADAPTER_NIC_NOT_EXIST))))
9702 + {
9703 + RT28XX_STOP_DEQUEUE(pAd, QueIdx, IrqFlags);
9704 + return;
9705 + }
9706 +
9707 + if (Count >= Max_Tx_Packets)
9708 + break;
9709 +
9710 + DEQUEUE_LOCK(&pAd->irq_lock, bIntContext, IrqFlags);
9711 + if (&pAd->TxSwQueue[QueIdx] == NULL)
9712 + {
9713 +#ifdef DBG_DIAGNOSE
9714 + if (firstRound == TRUE)
9715 + pDiagStruct->TxSWQueCnt[pDiagStruct->ArrayCurIdx][0]++;
9716 +#endif // DBG_DIAGNOSE //
9717 + DEQUEUE_UNLOCK(&pAd->irq_lock, bIntContext, IrqFlags);
9718 + break;
9719 + }
9720 +
9721 +#ifdef RT2860
9722 + FreeNumber[QueIdx] = GET_TXRING_FREENO(pAd, QueIdx);
9723 +
9724 +#ifdef DBG_DIAGNOSE
9725 + if (firstRound == TRUE)
9726 + {
9727 + UCHAR txDescNumLevel, txSwQNumLevel;
9728 +
9729 + txDescNumLevel = (TX_RING_SIZE - FreeNumber[QueIdx]); // Number of occupied hw desc.
9730 + txDescNumLevel = ((txDescNumLevel <=15) ? txDescNumLevel : 15);
9731 + pDiagStruct->TxDescCnt[pDiagStruct->ArrayCurIdx][txDescNumLevel]++;
9732 +
9733 + txSwQNumLevel = ((pAd->TxSwQueue[QueIdx].Number <=7) ? pAd->TxSwQueue[QueIdx].Number : 8);
9734 + pDiagStruct->TxSWQueCnt[pDiagStruct->ArrayCurIdx][txSwQNumLevel]++;
9735 +
9736 + firstRound = FALSE;
9737 + }
9738 +#endif // DBG_DIAGNOSE //
9739 +
9740 + if (FreeNumber[QueIdx] <= 5)
9741 + {
9742 + // free Tx(QueIdx) resources
9743 + RTMPFreeTXDUponTxDmaDone(pAd, QueIdx);
9744 + FreeNumber[QueIdx] = GET_TXRING_FREENO(pAd, QueIdx);
9745 + }
9746 +#endif // RT2860 //
9747 +
9748 + // probe the Queue Head
9749 + pQueue = &pAd->TxSwQueue[QueIdx];
9750 + if ((pEntry = pQueue->Head) == NULL)
9751 + {
9752 + DEQUEUE_UNLOCK(&pAd->irq_lock, bIntContext, IrqFlags);
9753 + break;
9754 + }
9755 +
9756 + pTxBlk = &TxBlk;
9757 + NdisZeroMemory((PUCHAR)pTxBlk, sizeof(TX_BLK));
9758 + pTxBlk->QueIdx = QueIdx;
9759 +
9760 + pPacket = QUEUE_ENTRY_TO_PKT(pEntry);
9761 +
9762 + // Early check to make sure we have enoguh Tx Resource.
9763 + hasTxDesc = RT28XX_HAS_ENOUGH_FREE_DESC(pAd, pTxBlk, FreeNumber[QueIdx], pPacket);
9764 + if (!hasTxDesc)
9765 + {
9766 + pAd->PrivateInfo.TxRingFullCnt++;
9767 +
9768 + DEQUEUE_UNLOCK(&pAd->irq_lock, bIntContext, IrqFlags);
9769 +
9770 + break;
9771 + }
9772 +
9773 + pTxBlk->TxFrameType = TxPktClassification(pAd, pPacket);
9774 + pEntry = RemoveHeadQueue(pQueue);
9775 + pTxBlk->TotalFrameNum++;
9776 + pTxBlk->TotalFragNum += RTMP_GET_PACKET_FRAGMENTS(pPacket); // The real fragment number maybe vary
9777 + pTxBlk->TotalFrameLen += GET_OS_PKT_LEN(pPacket);
9778 + pTxBlk->pPacket = pPacket;
9779 + InsertTailQueue(&pTxBlk->TxPacketList, PACKET_TO_QUEUE_ENTRY(pPacket));
9780 +
9781 + if (pTxBlk->TxFrameType == TX_RALINK_FRAME || pTxBlk->TxFrameType == TX_AMSDU_FRAME)
9782 + {
9783 + // Enhance SW Aggregation Mechanism
9784 + if (NEED_QUEUE_BACK_FOR_AGG(pAd, QueIdx, FreeNumber[QueIdx], pTxBlk->TxFrameType))
9785 + {
9786 + InsertHeadQueue(pQueue, PACKET_TO_QUEUE_ENTRY(pPacket));
9787 + DEQUEUE_UNLOCK(&pAd->irq_lock, bIntContext, IrqFlags);
9788 + break;
9789 + }
9790 +
9791 + do{
9792 + if((pEntry = pQueue->Head) == NULL)
9793 + break;
9794 +
9795 + // For TX_AMSDU_FRAME/TX_RALINK_FRAME, Need to check if next pakcet can do aggregation.
9796 + pPacket = QUEUE_ENTRY_TO_PKT(pEntry);
9797 + FreeNumber[QueIdx] = GET_TXRING_FREENO(pAd, QueIdx);
9798 + hasTxDesc = RT28XX_HAS_ENOUGH_FREE_DESC(pAd, pTxBlk, FreeNumber[QueIdx], pPacket);
9799 + if ((hasTxDesc == FALSE) || (CanDoAggregateTransmit(pAd, pPacket, pTxBlk) == FALSE))
9800 + break;
9801 +
9802 + //Remove the packet from the TxSwQueue and insert into pTxBlk
9803 + pEntry = RemoveHeadQueue(pQueue);
9804 + ASSERT(pEntry);
9805 + pPacket = QUEUE_ENTRY_TO_PKT(pEntry);
9806 + pTxBlk->TotalFrameNum++;
9807 + pTxBlk->TotalFragNum += RTMP_GET_PACKET_FRAGMENTS(pPacket); // The real fragment number maybe vary
9808 + pTxBlk->TotalFrameLen += GET_OS_PKT_LEN(pPacket);
9809 + InsertTailQueue(&pTxBlk->TxPacketList, PACKET_TO_QUEUE_ENTRY(pPacket));
9810 + }while(1);
9811 +
9812 + if (pTxBlk->TxPacketList.Number == 1)
9813 + pTxBlk->TxFrameType = TX_LEGACY_FRAME;
9814 + }
9815 +
9816 +
9817 + Count += pTxBlk->TxPacketList.Number;
9818 +
9819 + // Do HardTransmit now.
9820 +#ifdef CONFIG_STA_SUPPORT
9821 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
9822 + Status = STAHardTransmit(pAd, pTxBlk, QueIdx);
9823 +#endif // CONFIG_STA_SUPPORT //
9824 +
9825 +#ifdef RT2860
9826 + DEQUEUE_UNLOCK(&pAd->irq_lock, bIntContext, IrqFlags);
9827 + // static rate also need NICUpdateFifoStaCounters() function.
9828 + //if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_TX_RATE_SWITCH_ENABLED))
9829 + NICUpdateFifoStaCounters(pAd);
9830 +#endif // RT2860 //
9831 + }
9832 +
9833 + RT28XX_STOP_DEQUEUE(pAd, QueIdx, IrqFlags);
9834 +
9835 +
9836 +#ifdef BLOCK_NET_IF
9837 + if ((pAd->blockQueueTab[QueIdx].SwTxQueueBlockFlag == TRUE)
9838 + && (pAd->TxSwQueue[QueIdx].Number < 1))
9839 + {
9840 + releaseNetIf(&pAd->blockQueueTab[QueIdx]);
9841 + }
9842 +#endif // BLOCK_NET_IF //
9843 +
9844 + }
9845 +
9846 +}
9847 +
9848 +
9849 +/*
9850 + ========================================================================
9851 +
9852 + Routine Description:
9853 + Calculates the duration which is required to transmit out frames
9854 + with given size and specified rate.
9855 +
9856 + Arguments:
9857 + pAd Pointer to our adapter
9858 + Rate Transmit rate
9859 + Size Frame size in units of byte
9860 +
9861 + Return Value:
9862 + Duration number in units of usec
9863 +
9864 + IRQL = PASSIVE_LEVEL
9865 + IRQL = DISPATCH_LEVEL
9866 +
9867 + Note:
9868 +
9869 + ========================================================================
9870 +*/
9871 +USHORT RTMPCalcDuration(
9872 + IN PRTMP_ADAPTER pAd,
9873 + IN UCHAR Rate,
9874 + IN ULONG Size)
9875 +{
9876 + ULONG Duration = 0;
9877 +
9878 + if (Rate < RATE_FIRST_OFDM_RATE) // CCK
9879 + {
9880 + if ((Rate > RATE_1) && OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED))
9881 + Duration = 96; // 72+24 preamble+plcp
9882 + else
9883 + Duration = 192; // 144+48 preamble+plcp
9884 +
9885 + Duration += (USHORT)((Size << 4) / RateIdTo500Kbps[Rate]);
9886 + if ((Size << 4) % RateIdTo500Kbps[Rate])
9887 + Duration ++;
9888 + }
9889 + else if (Rate <= RATE_LAST_OFDM_RATE)// OFDM rates
9890 + {
9891 + Duration = 20 + 6; // 16+4 preamble+plcp + Signal Extension
9892 + Duration += 4 * (USHORT)((11 + Size * 4) / RateIdTo500Kbps[Rate]);
9893 + if ((11 + Size * 4) % RateIdTo500Kbps[Rate])
9894 + Duration += 4;
9895 + }
9896 + else //mimo rate
9897 + {
9898 + Duration = 20 + 6; // 16+4 preamble+plcp + Signal Extension
9899 + }
9900 +
9901 + return (USHORT)Duration;
9902 +}
9903 +
9904 +
9905 +/*
9906 + ========================================================================
9907 +
9908 + Routine Description:
9909 + Calculates the duration which is required to transmit out frames
9910 + with given size and specified rate.
9911 +
9912 + Arguments:
9913 + pTxWI Pointer to head of each MPDU to HW.
9914 + Ack Setting for Ack requirement bit
9915 + Fragment Setting for Fragment bit
9916 + RetryMode Setting for retry mode
9917 + Ifs Setting for IFS gap
9918 + Rate Setting for transmit rate
9919 + Service Setting for service
9920 + Length Frame length
9921 + TxPreamble Short or Long preamble when using CCK rates
9922 + QueIdx - 0-3, according to 802.11e/d4.4 June/2003
9923 +
9924 + Return Value:
9925 + None
9926 +
9927 + IRQL = PASSIVE_LEVEL
9928 + IRQL = DISPATCH_LEVEL
9929 +
9930 + See also : BASmartHardTransmit() !!!
9931 +
9932 + ========================================================================
9933 +*/
9934 +VOID RTMPWriteTxWI(
9935 + IN PRTMP_ADAPTER pAd,
9936 + IN PTXWI_STRUC pOutTxWI,
9937 + IN BOOLEAN FRAG,
9938 + IN BOOLEAN CFACK,
9939 + IN BOOLEAN InsTimestamp,
9940 + IN BOOLEAN AMPDU,
9941 + IN BOOLEAN Ack,
9942 + IN BOOLEAN NSeq, // HW new a sequence.
9943 + IN UCHAR BASize,
9944 + IN UCHAR WCID,
9945 + IN ULONG Length,
9946 + IN UCHAR PID,
9947 + IN UCHAR TID,
9948 + IN UCHAR TxRate,
9949 + IN UCHAR Txopmode,
9950 + IN BOOLEAN CfAck,
9951 + IN HTTRANSMIT_SETTING *pTransmit)
9952 +{
9953 + PMAC_TABLE_ENTRY pMac = NULL;
9954 + TXWI_STRUC TxWI;
9955 + PTXWI_STRUC pTxWI;
9956 +
9957 + if (WCID < MAX_LEN_OF_MAC_TABLE)
9958 + pMac = &pAd->MacTab.Content[WCID];
9959 +
9960 + //
9961 + // Always use Long preamble before verifiation short preamble functionality works well.
9962 + // Todo: remove the following line if short preamble functionality works
9963 + //
9964 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED);
9965 + NdisZeroMemory(&TxWI, TXWI_SIZE);
9966 + pTxWI = &TxWI;
9967 +
9968 + pTxWI->FRAG= FRAG;
9969 +
9970 + pTxWI->CFACK = CFACK;
9971 + pTxWI->TS= InsTimestamp;
9972 + pTxWI->AMPDU = AMPDU;
9973 + pTxWI->ACK = Ack;
9974 + pTxWI->txop= Txopmode;
9975 +
9976 + pTxWI->NSEQ = NSeq;
9977 + // John tune the performace with Intel Client in 20 MHz performance
9978 +#ifdef DOT11_N_SUPPORT
9979 + BASize = pAd->CommonCfg.TxBASize;
9980 +
9981 + if( BASize >7 )
9982 + BASize =7;
9983 + pTxWI->BAWinSize = BASize;
9984 + pTxWI->ShortGI = pTransmit->field.ShortGI;
9985 + pTxWI->STBC = pTransmit->field.STBC;
9986 +#endif // DOT11_N_SUPPORT //
9987 +
9988 + pTxWI->WirelessCliID = WCID;
9989 + pTxWI->MPDUtotalByteCount = Length;
9990 + pTxWI->PacketId = PID;
9991 +
9992 + // If CCK or OFDM, BW must be 20
9993 + pTxWI->BW = (pTransmit->field.MODE <= MODE_OFDM) ? (BW_20) : (pTransmit->field.BW);
9994 +#ifdef DOT11N_DRAFT3
9995 + if (pTxWI->BW)
9996 + pTxWI->BW = (pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth == 0) ? (BW_20) : (pTransmit->field.BW);
9997 +#endif // DOT11N_DRAFT3 //
9998 +
9999 + pTxWI->MCS = pTransmit->field.MCS;
10000 + pTxWI->PHYMODE = pTransmit->field.MODE;
10001 + pTxWI->CFACK = CfAck;
10002 +
10003 +#ifdef DOT11_N_SUPPORT
10004 + if (pMac)
10005 + {
10006 + if (pAd->CommonCfg.bMIMOPSEnable)
10007 + {
10008 + if ((pMac->MmpsMode == MMPS_DYNAMIC) && (pTransmit->field.MCS > 7))
10009 + {
10010 + // Dynamic MIMO Power Save Mode
10011 + pTxWI->MIMOps = 1;
10012 + }
10013 + else if (pMac->MmpsMode == MMPS_STATIC)
10014 + {
10015 + // Static MIMO Power Save Mode
10016 + if (pTransmit->field.MODE >= MODE_HTMIX && pTransmit->field.MCS > 7)
10017 + {
10018 + pTxWI->MCS = 7;
10019 + pTxWI->MIMOps = 0;
10020 + }
10021 + }
10022 + }
10023 + //pTxWI->MIMOps = (pMac->PsMode == PWR_MMPS)? 1:0;
10024 + if (pMac->bIAmBadAtheros && (pMac->WepStatus != Ndis802_11WEPDisabled))
10025 + {
10026 + pTxWI->MpduDensity = 7;
10027 + }
10028 + else
10029 + {
10030 + pTxWI->MpduDensity = pMac->MpduDensity;
10031 + }
10032 + }
10033 +#endif // DOT11_N_SUPPORT //
10034 +
10035 + pTxWI->PacketId = pTxWI->MCS;
10036 + NdisMoveMemory(pOutTxWI, &TxWI, sizeof(TXWI_STRUC));
10037 +}
10038 +
10039 +
10040 +VOID RTMPWriteTxWI_Data(
10041 + IN PRTMP_ADAPTER pAd,
10042 + IN OUT PTXWI_STRUC pTxWI,
10043 + IN TX_BLK *pTxBlk)
10044 +{
10045 + HTTRANSMIT_SETTING *pTransmit;
10046 + PMAC_TABLE_ENTRY pMacEntry;
10047 +#ifdef DOT11_N_SUPPORT
10048 + UCHAR BASize;
10049 +#endif // DOT11_N_SUPPORT //
10050 +
10051 +
10052 + ASSERT(pTxWI);
10053 +
10054 + pTransmit = pTxBlk->pTransmit;
10055 + pMacEntry = pTxBlk->pMacEntry;
10056 +
10057 +
10058 + //
10059 + // Always use Long preamble before verifiation short preamble functionality works well.
10060 + // Todo: remove the following line if short preamble functionality works
10061 + //
10062 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED);
10063 + NdisZeroMemory(pTxWI, TXWI_SIZE);
10064 +
10065 + pTxWI->FRAG = TX_BLK_TEST_FLAG(pTxBlk, fTX_bAllowFrag);
10066 + pTxWI->ACK = TX_BLK_TEST_FLAG(pTxBlk, fTX_bAckRequired);
10067 + pTxWI->txop = pTxBlk->FrameGap;
10068 +
10069 +#ifdef CONFIG_STA_SUPPORT
10070 +#ifdef QOS_DLS_SUPPORT
10071 + if (pMacEntry &&
10072 + (pAd->StaCfg.BssType == BSS_INFRA) &&
10073 + (pMacEntry->ValidAsDls == TRUE))
10074 + pTxWI->WirelessCliID = BSSID_WCID;
10075 + else
10076 +#endif // QOS_DLS_SUPPORT //
10077 +#endif // CONFIG_STA_SUPPORT //
10078 + pTxWI->WirelessCliID = pTxBlk->Wcid;
10079 +
10080 + pTxWI->MPDUtotalByteCount = pTxBlk->MpduHeaderLen + pTxBlk->SrcBufLen;
10081 + pTxWI->CFACK = TX_BLK_TEST_FLAG(pTxBlk, fTX_bPiggyBack);
10082 +
10083 + // If CCK or OFDM, BW must be 20
10084 + pTxWI->BW = (pTransmit->field.MODE <= MODE_OFDM) ? (BW_20) : (pTransmit->field.BW);
10085 +#ifdef DOT11_N_SUPPORT
10086 +#ifdef DOT11N_DRAFT3
10087 + if (pTxWI->BW)
10088 + pTxWI->BW = (pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth == 0) ? (BW_20) : (pTransmit->field.BW);
10089 +#endif // DOT11N_DRAFT3 //
10090 + pTxWI->AMPDU = ((pTxBlk->TxFrameType == TX_AMPDU_FRAME) ? TRUE : FALSE);
10091 +
10092 + // John tune the performace with Intel Client in 20 MHz performance
10093 + BASize = pAd->CommonCfg.TxBASize;
10094 + if((pTxBlk->TxFrameType == TX_AMPDU_FRAME) && (pMacEntry))
10095 + {
10096 + UCHAR RABAOriIdx = 0; //The RA's BA Originator table index.
10097 +
10098 + RABAOriIdx = pTxBlk->pMacEntry->BAOriWcidArray[pTxBlk->UserPriority];
10099 + BASize = pAd->BATable.BAOriEntry[RABAOriIdx].BAWinSize;
10100 + }
10101 +
10102 + pTxWI->TxBF = pTransmit->field.TxBF;
10103 + pTxWI->BAWinSize = BASize;
10104 + pTxWI->ShortGI = pTransmit->field.ShortGI;
10105 + pTxWI->STBC = pTransmit->field.STBC;
10106 +#endif // DOT11_N_SUPPORT //
10107 +
10108 + pTxWI->MCS = pTransmit->field.MCS;
10109 + pTxWI->PHYMODE = pTransmit->field.MODE;
10110 +
10111 +#ifdef DOT11_N_SUPPORT
10112 + if (pMacEntry)
10113 + {
10114 + if ((pMacEntry->MmpsMode == MMPS_DYNAMIC) && (pTransmit->field.MCS > 7))
10115 + {
10116 + // Dynamic MIMO Power Save Mode
10117 + pTxWI->MIMOps = 1;
10118 + }
10119 + else if (pMacEntry->MmpsMode == MMPS_STATIC)
10120 + {
10121 + // Static MIMO Power Save Mode
10122 + if (pTransmit->field.MODE >= MODE_HTMIX && pTransmit->field.MCS > 7)
10123 + {
10124 + pTxWI->MCS = 7;
10125 + pTxWI->MIMOps = 0;
10126 + }
10127 + }
10128 +
10129 + if (pMacEntry->bIAmBadAtheros && (pMacEntry->WepStatus != Ndis802_11WEPDisabled))
10130 + {
10131 + pTxWI->MpduDensity = 7;
10132 + }
10133 + else
10134 + {
10135 + pTxWI->MpduDensity = pMacEntry->MpduDensity;
10136 + }
10137 + }
10138 +#endif // DOT11_N_SUPPORT //
10139 +
10140 +#ifdef DBG_DIAGNOSE
10141 + if (pTxBlk->QueIdx== 0)
10142 + {
10143 + pAd->DiagStruct.TxDataCnt[pAd->DiagStruct.ArrayCurIdx]++;
10144 + pAd->DiagStruct.TxMcsCnt[pAd->DiagStruct.ArrayCurIdx][pTxWI->MCS]++;
10145 + }
10146 +#endif // DBG_DIAGNOSE //
10147 +
10148 + // for rate adapation
10149 + pTxWI->PacketId = pTxWI->MCS;
10150 +}
10151 +
10152 +
10153 +VOID RTMPWriteTxWI_Cache(
10154 + IN PRTMP_ADAPTER pAd,
10155 + IN OUT PTXWI_STRUC pTxWI,
10156 + IN TX_BLK *pTxBlk)
10157 +{
10158 + PHTTRANSMIT_SETTING pTransmit;
10159 + PMAC_TABLE_ENTRY pMacEntry;
10160 +
10161 + //
10162 + // update TXWI
10163 + //
10164 + pMacEntry = pTxBlk->pMacEntry;
10165 + pTransmit = pTxBlk->pTransmit;
10166 +
10167 + if (pMacEntry->bAutoTxRateSwitch)
10168 + {
10169 + pTxWI->txop = IFS_HTTXOP;
10170 +
10171 + // If CCK or OFDM, BW must be 20
10172 + pTxWI->BW = (pTransmit->field.MODE <= MODE_OFDM) ? (BW_20) : (pTransmit->field.BW);
10173 + pTxWI->ShortGI = pTransmit->field.ShortGI;
10174 + pTxWI->STBC = pTransmit->field.STBC;
10175 +
10176 + pTxWI->MCS = pTransmit->field.MCS;
10177 + pTxWI->PHYMODE = pTransmit->field.MODE;
10178 +
10179 + // set PID for TxRateSwitching
10180 + pTxWI->PacketId = pTransmit->field.MCS;
10181 + }
10182 +
10183 +#ifdef DOT11_N_SUPPORT
10184 + pTxWI->AMPDU = ((pMacEntry->NoBADataCountDown == 0) ? TRUE: FALSE);
10185 + pTxWI->MIMOps = 0;
10186 +
10187 +#ifdef DOT11N_DRAFT3
10188 + if (pTxWI->BW)
10189 + pTxWI->BW = (pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth == 0) ? (BW_20) : (pTransmit->field.BW);
10190 +#endif // DOT11N_DRAFT3 //
10191 +
10192 + if (pAd->CommonCfg.bMIMOPSEnable)
10193 + {
10194 + // MIMO Power Save Mode
10195 + if ((pMacEntry->MmpsMode == MMPS_DYNAMIC) && (pTransmit->field.MCS > 7))
10196 + {
10197 + // Dynamic MIMO Power Save Mode
10198 + pTxWI->MIMOps = 1;
10199 + }
10200 + else if (pMacEntry->MmpsMode == MMPS_STATIC)
10201 + {
10202 + // Static MIMO Power Save Mode
10203 + if ((pTransmit->field.MODE >= MODE_HTMIX) && (pTransmit->field.MCS > 7))
10204 + {
10205 + pTxWI->MCS = 7;
10206 + pTxWI->MIMOps = 0;
10207 + }
10208 + }
10209 + }
10210 +#endif // DOT11_N_SUPPORT //
10211 +
10212 +#ifdef DBG_DIAGNOSE
10213 + if (pTxBlk->QueIdx== 0)
10214 + {
10215 + pAd->DiagStruct.TxDataCnt[pAd->DiagStruct.ArrayCurIdx]++;
10216 + pAd->DiagStruct.TxMcsCnt[pAd->DiagStruct.ArrayCurIdx][pTxWI->MCS]++;
10217 + }
10218 +#endif // DBG_DIAGNOSE //
10219 +
10220 + pTxWI->MPDUtotalByteCount = pTxBlk->MpduHeaderLen + pTxBlk->SrcBufLen;
10221 +
10222 +}
10223 +
10224 +
10225 +/*
10226 + ========================================================================
10227 +
10228 + Routine Description:
10229 + Calculates the duration which is required to transmit out frames
10230 + with given size and specified rate.
10231 +
10232 + Arguments:
10233 + pTxD Pointer to transmit descriptor
10234 + Ack Setting for Ack requirement bit
10235 + Fragment Setting for Fragment bit
10236 + RetryMode Setting for retry mode
10237 + Ifs Setting for IFS gap
10238 + Rate Setting for transmit rate
10239 + Service Setting for service
10240 + Length Frame length
10241 + TxPreamble Short or Long preamble when using CCK rates
10242 + QueIdx - 0-3, according to 802.11e/d4.4 June/2003
10243 +
10244 + Return Value:
10245 + None
10246 +
10247 + IRQL = PASSIVE_LEVEL
10248 + IRQL = DISPATCH_LEVEL
10249 +
10250 + ========================================================================
10251 +*/
10252 +VOID RTMPWriteTxDescriptor(
10253 + IN PRTMP_ADAPTER pAd,
10254 + IN PTXD_STRUC pTxD,
10255 + IN BOOLEAN bWIV,
10256 + IN UCHAR QueueSEL)
10257 +{
10258 + //
10259 + // Always use Long preamble before verifiation short preamble functionality works well.
10260 + // Todo: remove the following line if short preamble functionality works
10261 + //
10262 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED);
10263 +
10264 + pTxD->WIV = (bWIV) ? 1: 0;
10265 + pTxD->QSEL= (QueueSEL);
10266 + if (pAd->bGenOneHCCA == TRUE)
10267 + pTxD->QSEL= FIFO_HCCA;
10268 + pTxD->DMADONE = 0;
10269 +}
10270 +
10271 +
10272 +// should be called only when -
10273 +// 1. MEADIA_CONNECTED
10274 +// 2. AGGREGATION_IN_USED
10275 +// 3. Fragmentation not in used
10276 +// 4. either no previous frame (pPrevAddr1=NULL) .OR. previoud frame is aggregatible
10277 +BOOLEAN TxFrameIsAggregatible(
10278 + IN PRTMP_ADAPTER pAd,
10279 + IN PUCHAR pPrevAddr1,
10280 + IN PUCHAR p8023hdr)
10281 +{
10282 +
10283 + // can't aggregate EAPOL (802.1x) frame
10284 + if ((p8023hdr[12] == 0x88) && (p8023hdr[13] == 0x8e))
10285 + return FALSE;
10286 +
10287 + // can't aggregate multicast/broadcast frame
10288 + if (p8023hdr[0] & 0x01)
10289 + return FALSE;
10290 +
10291 + if (INFRA_ON(pAd)) // must be unicast to AP
10292 + return TRUE;
10293 + else if ((pPrevAddr1 == NULL) || MAC_ADDR_EQUAL(pPrevAddr1, p8023hdr)) // unicast to same STA
10294 + return TRUE;
10295 + else
10296 + return FALSE;
10297 +}
10298 +
10299 +
10300 +/*
10301 + ========================================================================
10302 +
10303 + Routine Description:
10304 + Check the MSDU Aggregation policy
10305 + 1.HT aggregation is A-MSDU
10306 + 2.legaacy rate aggregation is software aggregation by Ralink.
10307 +
10308 + Arguments:
10309 +
10310 + Return Value:
10311 +
10312 + Note:
10313 +
10314 + ========================================================================
10315 +*/
10316 +BOOLEAN PeerIsAggreOn(
10317 + IN PRTMP_ADAPTER pAd,
10318 + IN ULONG TxRate,
10319 + IN PMAC_TABLE_ENTRY pMacEntry)
10320 +{
10321 + ULONG AFlags = (fCLIENT_STATUS_AMSDU_INUSED | fCLIENT_STATUS_AGGREGATION_CAPABLE);
10322 +
10323 + if (pMacEntry != NULL && CLIENT_STATUS_TEST_FLAG(pMacEntry, AFlags))
10324 + {
10325 +#ifdef DOT11_N_SUPPORT
10326 + if (pMacEntry->HTPhyMode.field.MODE >= MODE_HTMIX)
10327 + {
10328 + return TRUE;
10329 + }
10330 +#endif // DOT11_N_SUPPORT //
10331 +
10332 +#ifdef AGGREGATION_SUPPORT
10333 + if (TxRate >= RATE_6 && pAd->CommonCfg.bAggregationCapable && (!(OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED) && CLIENT_STATUS_TEST_FLAG(pMacEntry, fCLIENT_STATUS_WMM_CAPABLE))))
10334 + { // legacy Ralink Aggregation support
10335 + return TRUE;
10336 + }
10337 +#endif // AGGREGATION_SUPPORT //
10338 + }
10339 +
10340 + return FALSE;
10341 +
10342 +}
10343 +
10344 +
10345 +/*
10346 + ========================================================================
10347 +
10348 + Routine Description:
10349 + Check and fine the packet waiting in SW queue with highest priority
10350 +
10351 + Arguments:
10352 + pAd Pointer to our adapter
10353 +
10354 + Return Value:
10355 + pQueue Pointer to Waiting Queue
10356 +
10357 + IRQL = DISPATCH_LEVEL
10358 +
10359 + Note:
10360 +
10361 + ========================================================================
10362 +*/
10363 +PQUEUE_HEADER RTMPCheckTxSwQueue(
10364 + IN PRTMP_ADAPTER pAd,
10365 + OUT PUCHAR pQueIdx)
10366 +{
10367 +
10368 + ULONG Number;
10369 +
10370 + Number = pAd->TxSwQueue[QID_AC_BK].Number
10371 + + pAd->TxSwQueue[QID_AC_BE].Number
10372 + + pAd->TxSwQueue[QID_AC_VI].Number
10373 + + pAd->TxSwQueue[QID_AC_VO].Number
10374 + + pAd->TxSwQueue[QID_HCCA].Number;
10375 +
10376 + if (pAd->TxSwQueue[QID_AC_VO].Head != NULL)
10377 + {
10378 + *pQueIdx = QID_AC_VO;
10379 + return (&pAd->TxSwQueue[QID_AC_VO]);
10380 + }
10381 + else if (pAd->TxSwQueue[QID_AC_VI].Head != NULL)
10382 + {
10383 + *pQueIdx = QID_AC_VI;
10384 + return (&pAd->TxSwQueue[QID_AC_VI]);
10385 + }
10386 + else if (pAd->TxSwQueue[QID_AC_BE].Head != NULL)
10387 + {
10388 + *pQueIdx = QID_AC_BE;
10389 + return (&pAd->TxSwQueue[QID_AC_BE]);
10390 + }
10391 + else if (pAd->TxSwQueue[QID_AC_BK].Head != NULL)
10392 + {
10393 + *pQueIdx = QID_AC_BK;
10394 + return (&pAd->TxSwQueue[QID_AC_BK]);
10395 + }
10396 + else if (pAd->TxSwQueue[QID_HCCA].Head != NULL)
10397 + {
10398 + *pQueIdx = QID_HCCA;
10399 + return (&pAd->TxSwQueue[QID_HCCA]);
10400 + }
10401 +
10402 + // No packet pending in Tx Sw queue
10403 + *pQueIdx = QID_AC_BK;
10404 +
10405 + return (NULL);
10406 +}
10407 +
10408 +
10409 +#ifdef RT2860
10410 +BOOLEAN RTMPFreeTXDUponTxDmaDone(
10411 + IN PRTMP_ADAPTER pAd,
10412 + IN UCHAR QueIdx)
10413 +{
10414 + PRTMP_TX_RING pTxRing;
10415 + PTXD_STRUC pTxD;
10416 +#ifdef RT_BIG_ENDIAN
10417 + PTXD_STRUC pDestTxD;
10418 +#endif
10419 + PNDIS_PACKET pPacket;
10420 + UCHAR FREE = 0;
10421 + TXD_STRUC TxD, *pOriTxD;
10422 + //ULONG IrqFlags;
10423 + BOOLEAN bReschedule = FALSE;
10424 +
10425 +
10426 + ASSERT(QueIdx < NUM_OF_TX_RING);
10427 + pTxRing = &pAd->TxRing[QueIdx];
10428 +
10429 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + QueIdx * RINGREG_DIFF, &pTxRing->TxDmaIdx);
10430 + while (pTxRing->TxSwFreeIdx != pTxRing->TxDmaIdx)
10431 + {
10432 +#ifdef RALINK_ATE
10433 +#ifdef RALINK_28xx_QA
10434 + PHEADER_802_11 pHeader80211;
10435 +
10436 + if ((ATE_ON(pAd)) && (pAd->ate.bQATxStart == TRUE))
10437 + {
10438 + if (pAd->ate.QID == QueIdx)
10439 + {
10440 + pAd->ate.TxDoneCount++;
10441 + //pAd->ate.Repeat++;
10442 + pAd->RalinkCounters.KickTxCount++;
10443 +
10444 + /* always use QID_AC_BE and FIFO_EDCA */
10445 + ASSERT(pAd->ate.QID == 0);
10446 + pAd->ate.TxAc0++;
10447 +
10448 + FREE++;
10449 +#ifndef RT_BIG_ENDIAN
10450 + pTxD = (PTXD_STRUC) (pTxRing->Cell[pTxRing->TxSwFreeIdx].AllocVa);
10451 + pOriTxD = pTxD;
10452 + NdisMoveMemory(&TxD, pTxD, sizeof(TXD_STRUC));
10453 + pTxD = &TxD;
10454 +#else
10455 + pDestTxD = (PTXD_STRUC) (pTxRing->Cell[pTxRing->TxSwFreeIdx].AllocVa);
10456 + pOriTxD = pDestTxD ;
10457 + TxD = *pDestTxD;
10458 + pTxD = &TxD;
10459 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10460 +#endif
10461 + pTxD->DMADONE = 0;
10462 +
10463 + pHeader80211 = pTxRing->Cell[pTxRing->TxSwFreeIdx].DmaBuf.AllocVa + sizeof(TXWI_STRUC);
10464 +#ifdef RT_BIG_ENDIAN
10465 + RTMPFrameEndianChange(pAd, (PUCHAR)pHeader80211, DIR_READ, FALSE);
10466 +#endif
10467 + pHeader80211->Sequence = ++pAd->ate.seq;
10468 +#ifdef RT_BIG_ENDIAN
10469 + RTMPFrameEndianChange(pAd, (PUCHAR)pHeader80211, DIR_WRITE, FALSE);
10470 +#endif
10471 +
10472 + if ((pAd->ate.bQATxStart == TRUE) && (pAd->ate.Mode & ATE_TXFRAME) && (pAd->ate.TxDoneCount < pAd->ate.TxCount))
10473 + {
10474 + pAd->RalinkCounters.TransmittedByteCount += (pTxD->SDLen1 + pTxD->SDLen0);
10475 + pAd->RalinkCounters.OneSecDmaDoneCount[QueIdx] ++;
10476 + INC_RING_INDEX(pTxRing->TxSwFreeIdx, TX_RING_SIZE);
10477 + /* get tx_tdx_idx again */
10478 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + QueIdx * RINGREG_DIFF , &pTxRing->TxDmaIdx);
10479 + goto kick_out;
10480 + }
10481 + else if ((pAd->ate.TxStatus == 1)/* or (pAd->ate.bQATxStart == TRUE) ??? */ && (pAd->ate.TxDoneCount == pAd->ate.TxCount))//<========================PETER
10482 + {
10483 + DBGPRINT(RT_DEBUG_TRACE,("all Tx is done\n"));
10484 + // Tx status enters idle mode.
10485 + pAd->ate.TxStatus = 0;
10486 + }
10487 + else if (!(pAd->ate.Mode & ATE_TXFRAME))
10488 + {
10489 + /* not complete sending yet, but someone press the Stop TX botton. */
10490 + DBGPRINT(RT_DEBUG_ERROR,("not complete sending yet, but someone pressed the Stop TX bottom\n"));
10491 + DBGPRINT(RT_DEBUG_ERROR,("pAd->ate.Mode = 0x%02x\n", pAd->ate.Mode));
10492 + }
10493 + else
10494 + {
10495 + DBGPRINT(RT_DEBUG_OFF,("pTxRing->TxSwFreeIdx = %d\n", pTxRing->TxSwFreeIdx));
10496 + }
10497 +#ifndef RT_BIG_ENDIAN
10498 + NdisMoveMemory(pOriTxD, pTxD, sizeof(TXD_STRUC));
10499 +#else
10500 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10501 + *pDestTxD = TxD;
10502 +#endif // RT_BIG_ENDIAN //
10503 +
10504 + INC_RING_INDEX(pTxRing->TxSwFreeIdx, TX_RING_SIZE);
10505 + continue;
10506 + }
10507 + }
10508 +#endif // RALINK_28xx_QA //
10509 +#endif // RALINK_ATE //
10510 +
10511 + // static rate also need NICUpdateFifoStaCounters() function.
10512 + //if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_TX_RATE_SWITCH_ENABLED))
10513 + NICUpdateFifoStaCounters(pAd);
10514 +
10515 + /* Note : If (pAd->ate.bQATxStart == TRUE), we will never reach here. */
10516 + FREE++;
10517 +#ifndef RT_BIG_ENDIAN
10518 + pTxD = (PTXD_STRUC) (pTxRing->Cell[pTxRing->TxSwFreeIdx].AllocVa);
10519 + pOriTxD = pTxD;
10520 + NdisMoveMemory(&TxD, pTxD, sizeof(TXD_STRUC));
10521 + pTxD = &TxD;
10522 +#else
10523 + pDestTxD = (PTXD_STRUC) (pTxRing->Cell[pTxRing->TxSwFreeIdx].AllocVa);
10524 + pOriTxD = pDestTxD ;
10525 + TxD = *pDestTxD;
10526 + pTxD = &TxD;
10527 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10528 +#endif
10529 +
10530 + pTxD->DMADONE = 0;
10531 +
10532 +
10533 +#ifdef RALINK_ATE
10534 + /* Execution of this block is not allowed when ATE is running. */
10535 + if (!(ATE_ON(pAd)))
10536 +#endif // RALINK_ATE //
10537 +/*====================================================================*/
10538 + {
10539 + pPacket = pTxRing->Cell[pTxRing->TxSwFreeIdx].pNdisPacket;
10540 + if (pPacket)
10541 + {
10542 +#ifdef CONFIG_5VT_ENHANCE
10543 + if (RTMP_GET_PACKET_5VT(pPacket))
10544 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, 16, PCI_DMA_TODEVICE);
10545 + else
10546 +#endif // CONFIG_5VT_ENHANCE //
10547 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
10548 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
10549 + }
10550 + //Always assign pNdisPacket as NULL after clear
10551 + pTxRing->Cell[pTxRing->TxSwFreeIdx].pNdisPacket = NULL;
10552 +
10553 + pPacket = pTxRing->Cell[pTxRing->TxSwFreeIdx].pNextNdisPacket;
10554 +
10555 + ASSERT(pPacket == NULL);
10556 + if (pPacket)
10557 + {
10558 +#ifdef CONFIG_5VT_ENHANCE
10559 + if (RTMP_GET_PACKET_5VT(pPacket))
10560 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, 16, PCI_DMA_TODEVICE);
10561 + else
10562 +#endif // CONFIG_5VT_ENHANCE //
10563 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
10564 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
10565 + }
10566 + //Always assign pNextNdisPacket as NULL after clear
10567 + pTxRing->Cell[pTxRing->TxSwFreeIdx].pNextNdisPacket = NULL;
10568 + }
10569 +/*====================================================================*/
10570 +
10571 + pAd->RalinkCounters.TransmittedByteCount += (pTxD->SDLen1 + pTxD->SDLen0);
10572 + pAd->RalinkCounters.OneSecDmaDoneCount[QueIdx] ++;
10573 + INC_RING_INDEX(pTxRing->TxSwFreeIdx, TX_RING_SIZE);
10574 + /* get tx_tdx_idx again */
10575 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + QueIdx * RINGREG_DIFF , &pTxRing->TxDmaIdx);
10576 +#ifdef RT_BIG_ENDIAN
10577 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10578 + *pDestTxD = TxD;
10579 +#else
10580 + NdisMoveMemory(pOriTxD, pTxD, sizeof(TXD_STRUC));
10581 +#endif
10582 +
10583 +#ifdef RALINK_ATE
10584 +#ifdef RALINK_28xx_QA
10585 +kick_out:
10586 +#endif // RALINK_28xx_QA //
10587 +
10588 + //
10589 + // ATE_TXCONT mode also need to send some normal frames, so let it in.
10590 + // ATE_STOP must be changed not to be 0xff
10591 + // to prevent it from running into this block.
10592 + //
10593 + if ((pAd->ate.Mode & ATE_TXFRAME) && (pAd->ate.QID == QueIdx))
10594 + {
10595 + // TxDoneCount++ has been done if QA is used.
10596 + if (pAd->ate.bQATxStart == FALSE)
10597 + {
10598 + pAd->ate.TxDoneCount++;
10599 + }
10600 + if (((pAd->ate.TxCount - pAd->ate.TxDoneCount + 1) >= TX_RING_SIZE))
10601 + {
10602 + /* Note : We increase TxCpuIdx here, not TxSwFreeIdx ! */
10603 + INC_RING_INDEX(pAd->TxRing[QueIdx].TxCpuIdx, TX_RING_SIZE);
10604 +#ifndef RT_BIG_ENDIAN//<==========================PETER
10605 + pTxD = (PTXD_STRUC) (pTxRing->Cell[pAd->TxRing[QueIdx].TxCpuIdx].AllocVa);
10606 + pOriTxD = pTxD;
10607 + NdisMoveMemory(&TxD, pTxD, sizeof(TXD_STRUC));
10608 + pTxD = &TxD;
10609 +#else
10610 + pDestTxD = (PTXD_STRUC) (pTxRing->Cell[pAd->TxRing[QueIdx].TxCpuIdx].AllocVa);
10611 + pOriTxD = pDestTxD ;
10612 + TxD = *pDestTxD;
10613 + pTxD = &TxD;
10614 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10615 +#endif
10616 + pTxD->DMADONE = 0;
10617 +#ifndef RT_BIG_ENDIAN//<==========================PETER
10618 + NdisMoveMemory(pOriTxD, pTxD, sizeof(TXD_STRUC));
10619 +#else
10620 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10621 + *pDestTxD = TxD;
10622 +#endif
10623 + // kick Tx-Ring.
10624 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QueIdx * RINGREG_DIFF, pAd->TxRing[QueIdx].TxCpuIdx);
10625 + pAd->RalinkCounters.KickTxCount++;
10626 + }
10627 + }
10628 +#endif // RALINK_ATE //
10629 + }
10630 +
10631 +
10632 + return bReschedule;
10633 +
10634 +}
10635 +
10636 +
10637 +/*
10638 + ========================================================================
10639 +
10640 + Routine Description:
10641 + Process TX Rings DMA Done interrupt, running in DPC level
10642 +
10643 + Arguments:
10644 + Adapter Pointer to our adapter
10645 +
10646 + Return Value:
10647 + None
10648 +
10649 + IRQL = DISPATCH_LEVEL
10650 +
10651 + ========================================================================
10652 +*/
10653 +BOOLEAN RTMPHandleTxRingDmaDoneInterrupt(
10654 + IN PRTMP_ADAPTER pAd,
10655 + IN INT_SOURCE_CSR_STRUC TxRingBitmap)
10656 +{
10657 + unsigned long IrqFlags;
10658 + BOOLEAN bReschedule = FALSE;
10659 +
10660 + // Make sure Tx ring resource won't be used by other threads
10661 +
10662 + RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
10663 +
10664 + if (TxRingBitmap.field.Ac0DmaDone)
10665 + bReschedule = RTMPFreeTXDUponTxDmaDone(pAd, QID_AC_BE);
10666 +
10667 + if (TxRingBitmap.field.HccaDmaDone)
10668 + bReschedule |= RTMPFreeTXDUponTxDmaDone(pAd, QID_HCCA);
10669 +
10670 + if (TxRingBitmap.field.Ac3DmaDone)
10671 + bReschedule |= RTMPFreeTXDUponTxDmaDone(pAd, QID_AC_VO);
10672 +
10673 + if (TxRingBitmap.field.Ac2DmaDone)
10674 + bReschedule |= RTMPFreeTXDUponTxDmaDone(pAd, QID_AC_VI);
10675 +
10676 + if (TxRingBitmap.field.Ac1DmaDone)
10677 + bReschedule |= RTMPFreeTXDUponTxDmaDone(pAd, QID_AC_BK);
10678 +
10679 + // Make sure to release Tx ring resource
10680 + RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
10681 +
10682 + // Dequeue outgoing frames from TxSwQueue[] and process it
10683 + RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
10684 +
10685 + return bReschedule;
10686 +}
10687 +
10688 +
10689 +/*
10690 + ========================================================================
10691 +
10692 + Routine Description:
10693 + Process MGMT ring DMA done interrupt, running in DPC level
10694 +
10695 + Arguments:
10696 + pAd Pointer to our adapter
10697 +
10698 + Return Value:
10699 + None
10700 +
10701 + IRQL = DISPATCH_LEVEL
10702 +
10703 + Note:
10704 +
10705 + ========================================================================
10706 +*/
10707 +VOID RTMPHandleMgmtRingDmaDoneInterrupt(
10708 + IN PRTMP_ADAPTER pAd)
10709 +{
10710 + PTXD_STRUC pTxD;
10711 +#ifdef RT_BIG_ENDIAN
10712 + PTXD_STRUC pDestTxD;
10713 + TXD_STRUC TxD;
10714 +#endif
10715 + PNDIS_PACKET pPacket;
10716 + UCHAR FREE = 0;
10717 + PRTMP_MGMT_RING pMgmtRing = &pAd->MgmtRing;
10718 +
10719 + NdisAcquireSpinLock(&pAd->MgmtRingLock);
10720 +
10721 + RTMP_IO_READ32(pAd, TX_MGMTDTX_IDX, &pMgmtRing->TxDmaIdx);
10722 + while (pMgmtRing->TxSwFreeIdx!= pMgmtRing->TxDmaIdx)
10723 + {
10724 + FREE++;
10725 +#ifdef RT_BIG_ENDIAN
10726 + pDestTxD = (PTXD_STRUC) (pMgmtRing->Cell[pAd->MgmtRing.TxSwFreeIdx].AllocVa);
10727 + TxD = *pDestTxD;
10728 + pTxD = &TxD;
10729 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10730 +#else
10731 + pTxD = (PTXD_STRUC) (pMgmtRing->Cell[pAd->MgmtRing.TxSwFreeIdx].AllocVa);
10732 +#endif
10733 + pTxD->DMADONE = 0;
10734 + pPacket = pMgmtRing->Cell[pMgmtRing->TxSwFreeIdx].pNdisPacket;
10735 +
10736 +
10737 + if (pPacket)
10738 + {
10739 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
10740 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
10741 + }
10742 + pMgmtRing->Cell[pMgmtRing->TxSwFreeIdx].pNdisPacket = NULL;
10743 +
10744 + pPacket = pMgmtRing->Cell[pMgmtRing->TxSwFreeIdx].pNextNdisPacket;
10745 + if (pPacket)
10746 + {
10747 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
10748 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
10749 + }
10750 + pMgmtRing->Cell[pMgmtRing->TxSwFreeIdx].pNextNdisPacket = NULL;
10751 + INC_RING_INDEX(pMgmtRing->TxSwFreeIdx, MGMT_RING_SIZE);
10752 +
10753 +#ifdef RT_BIG_ENDIAN
10754 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
10755 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, TRUE, TYPE_TXD);
10756 +#endif
10757 + }
10758 + NdisReleaseSpinLock(&pAd->MgmtRingLock);
10759 +
10760 +}
10761 +
10762 +
10763 +/*
10764 + ========================================================================
10765 +
10766 + Routine Description:
10767 + Arguments:
10768 + Adapter Pointer to our adapter. Dequeue all power safe delayed braodcast frames after beacon.
10769 +
10770 + IRQL = DISPATCH_LEVEL
10771 +
10772 + ========================================================================
10773 +*/
10774 +VOID RTMPHandleTBTTInterrupt(
10775 + IN PRTMP_ADAPTER pAd)
10776 +{
10777 + {
10778 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
10779 + {
10780 + }
10781 + }
10782 +}
10783 +
10784 +
10785 +/*
10786 + ========================================================================
10787 +
10788 + Routine Description:
10789 + Arguments:
10790 + Adapter Pointer to our adapter. Rewrite beacon content before next send-out.
10791 +
10792 + IRQL = DISPATCH_LEVEL
10793 +
10794 + ========================================================================
10795 +*/
10796 +VOID RTMPHandlePreTBTTInterrupt(
10797 + IN PRTMP_ADAPTER pAd)
10798 +{
10799 + {
10800 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
10801 + {
10802 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPHandlePreTBTTInterrupt...\n"));
10803 + }
10804 + }
10805 +
10806 +
10807 +}
10808 +
10809 +VOID RTMPHandleRxCoherentInterrupt(
10810 + IN PRTMP_ADAPTER pAd)
10811 +{
10812 + WPDMA_GLO_CFG_STRUC GloCfg;
10813 +
10814 + if (pAd == NULL)
10815 + {
10816 + DBGPRINT(RT_DEBUG_TRACE, ("====> pAd is NULL, return.\n"));
10817 + return;
10818 + }
10819 +
10820 + DBGPRINT(RT_DEBUG_TRACE, ("==> RTMPHandleRxCoherentInterrupt \n"));
10821 +
10822 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG , &GloCfg.word);
10823 +
10824 + GloCfg.field.EnTXWriteBackDDONE = 0;
10825 + GloCfg.field.EnableRxDMA = 0;
10826 + GloCfg.field.EnableTxDMA = 0;
10827 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word);
10828 +
10829 + RTMPRingCleanUp(pAd, QID_AC_BE);
10830 + RTMPRingCleanUp(pAd, QID_AC_BK);
10831 + RTMPRingCleanUp(pAd, QID_AC_VI);
10832 + RTMPRingCleanUp(pAd, QID_AC_VO);
10833 + RTMPRingCleanUp(pAd, QID_HCCA);
10834 + RTMPRingCleanUp(pAd, QID_MGMT);
10835 + RTMPRingCleanUp(pAd, QID_RX);
10836 +
10837 + RTMPEnableRxTx(pAd);
10838 +
10839 + DBGPRINT(RT_DEBUG_TRACE, ("<== RTMPHandleRxCoherentInterrupt \n"));
10840 +}
10841 +
10842 +
10843 +VOID DBGPRINT_TX_RING(
10844 + IN PRTMP_ADAPTER pAd,
10845 + IN UCHAR QueIdx)
10846 +{
10847 + UINT32 Ac0Base;
10848 + UINT32 Ac0HwIdx = 0, Ac0SwIdx = 0, AC0freeIdx;
10849 + int i;
10850 + PULONG ptemp;
10851 +
10852 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("=====================================================\n " ));
10853 + switch (QueIdx)
10854 + {
10855 + case QID_AC_BE:
10856 + RTMP_IO_READ32(pAd, TX_BASE_PTR0, &Ac0Base);
10857 + RTMP_IO_READ32(pAd, TX_CTX_IDX0, &Ac0SwIdx);
10858 + RTMP_IO_READ32(pAd, TX_DTX_IDX0, &Ac0HwIdx);
10859 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("All QID_AC_BE DESCRIPTOR \n " ));
10860 + for (i=0;i<TX_RING_SIZE;i++)
10861 + {
10862 + ptemp= (PULONG)pAd->TxRing[QID_AC_BE].Cell[i].AllocVa;
10863 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("[%02d] %08lx: %08lx: %08lx: %08lx\n " , i, *ptemp,*(ptemp+1),*(ptemp+2),*(ptemp+3)));
10864 + }
10865 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" \n " ));
10866 + break;
10867 + case QID_AC_BK:
10868 + RTMP_IO_READ32(pAd, TX_BASE_PTR1, &Ac0Base);
10869 + RTMP_IO_READ32(pAd, TX_CTX_IDX1, &Ac0SwIdx);
10870 + RTMP_IO_READ32(pAd, TX_DTX_IDX1, &Ac0HwIdx);
10871 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("All QID_AC_BK DESCRIPTOR \n " ));
10872 + for (i=0;i<TX_RING_SIZE;i++)
10873 + {
10874 + ptemp= (PULONG)pAd->TxRing[QID_AC_BK].Cell[i].AllocVa;
10875 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("[%02d] %08lx: %08lx: %08lx: %08lx\n " , i, *ptemp,*(ptemp+1),*(ptemp+2),*(ptemp+3)));
10876 + }
10877 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" \n " ));
10878 + break;
10879 + case QID_AC_VI:
10880 + RTMP_IO_READ32(pAd, TX_BASE_PTR2, &Ac0Base);
10881 + RTMP_IO_READ32(pAd, TX_CTX_IDX2, &Ac0SwIdx);
10882 + RTMP_IO_READ32(pAd, TX_DTX_IDX2, &Ac0HwIdx);
10883 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("All QID_AC_VI DESCRIPTOR \n " ));
10884 + for (i=0;i<TX_RING_SIZE;i++)
10885 + {
10886 + ptemp= (PULONG)pAd->TxRing[QID_AC_VI].Cell[i].AllocVa;
10887 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("[%02d] %08lx: %08lx: %08lx: %08lx\n " , i, *ptemp,*(ptemp+1),*(ptemp+2),*(ptemp+3)));
10888 + }
10889 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" \n " ));
10890 + break;
10891 + case QID_AC_VO:
10892 + RTMP_IO_READ32(pAd, TX_BASE_PTR3, &Ac0Base);
10893 + RTMP_IO_READ32(pAd, TX_CTX_IDX3, &Ac0SwIdx);
10894 + RTMP_IO_READ32(pAd, TX_DTX_IDX3, &Ac0HwIdx);
10895 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("All QID_AC_VO DESCRIPTOR \n " ));
10896 + for (i=0;i<TX_RING_SIZE;i++)
10897 + {
10898 + ptemp= (PULONG)pAd->TxRing[QID_AC_VO].Cell[i].AllocVa;
10899 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("[%02d] %08lx: %08lx: %08lx: %08lx\n " , i, *ptemp,*(ptemp+1),*(ptemp+2),*(ptemp+3)));
10900 + }
10901 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" \n " ));
10902 + break;
10903 + case QID_MGMT:
10904 + RTMP_IO_READ32(pAd, TX_BASE_PTR5, &Ac0Base);
10905 + RTMP_IO_READ32(pAd, TX_CTX_IDX5, &Ac0SwIdx);
10906 + RTMP_IO_READ32(pAd, TX_DTX_IDX5, &Ac0HwIdx);
10907 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" All QID_MGMT DESCRIPTOR \n " ));
10908 + for (i=0;i<MGMT_RING_SIZE;i++)
10909 + {
10910 + ptemp= (PULONG)pAd->MgmtRing.Cell[i].AllocVa;
10911 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("[%02d] %08lx: %08lx: %08lx: %08lx\n " , i, *ptemp,*(ptemp+1),*(ptemp+2),*(ptemp+3)));
10912 + }
10913 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" \n " ));
10914 + break;
10915 +
10916 + default:
10917 + DBGPRINT_ERR(("DBGPRINT_TX_RING(Ring %d) not supported\n", QueIdx));
10918 + break;
10919 + }
10920 + AC0freeIdx = pAd->TxRing[QueIdx].TxSwFreeIdx;
10921 +
10922 + DBGPRINT(RT_DEBUG_TRACE,("TxRing%d, TX_DTX_IDX=%d, TX_CTX_IDX=%d\n", QueIdx, Ac0HwIdx, Ac0SwIdx));
10923 + DBGPRINT_RAW(RT_DEBUG_TRACE,(" TxSwFreeIdx[%d]", AC0freeIdx));
10924 + DBGPRINT_RAW(RT_DEBUG_TRACE,(" pending-NDIS=%ld\n", pAd->RalinkCounters.PendingNdisPacketCount));
10925 +
10926 +
10927 +}
10928 +
10929 +
10930 +VOID DBGPRINT_RX_RING(
10931 + IN PRTMP_ADAPTER pAd)
10932 +{
10933 + UINT32 Ac0Base;
10934 + UINT32 Ac0HwIdx = 0, Ac0SwIdx = 0, AC0freeIdx;
10935 + int i;
10936 + UINT32 *ptemp;
10937 +
10938 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("=====================================================\n " ));
10939 + RTMP_IO_READ32(pAd, RX_BASE_PTR, &Ac0Base);
10940 + RTMP_IO_READ32(pAd, RX_CRX_IDX, &Ac0SwIdx);
10941 + RTMP_IO_READ32(pAd, RX_DRX_IDX, &Ac0HwIdx);
10942 + AC0freeIdx = pAd->RxRing.RxSwReadIdx;
10943 +
10944 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("All RX DSP \n " ));
10945 + for (i=0;i<RX_RING_SIZE;i++)
10946 + {
10947 + ptemp = (UINT32 *)pAd->RxRing.Cell[i].AllocVa;
10948 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("[%02d] %08x: %08x: %08x: %08x\n " , i, *ptemp,*(ptemp+1),*(ptemp+2),*(ptemp+3)));
10949 + }
10950 + DBGPRINT(RT_DEBUG_TRACE,("RxRing, RX_DRX_IDX=%d, RX_CRX_IDX=%d \n", Ac0HwIdx, Ac0SwIdx));
10951 + DBGPRINT_RAW(RT_DEBUG_TRACE,(" RxSwReadIdx [%d]=", AC0freeIdx));
10952 + DBGPRINT_RAW(RT_DEBUG_TRACE,(" pending-NDIS=%ld\n", pAd->RalinkCounters.PendingNdisPacketCount));
10953 +}
10954 +#endif // RT2860 //
10955 +
10956 +/*
10957 + ========================================================================
10958 +
10959 + Routine Description:
10960 + Suspend MSDU transmission
10961 +
10962 + Arguments:
10963 + pAd Pointer to our adapter
10964 +
10965 + Return Value:
10966 + None
10967 +
10968 + Note:
10969 +
10970 + ========================================================================
10971 +*/
10972 +VOID RTMPSuspendMsduTransmission(
10973 + IN PRTMP_ADAPTER pAd)
10974 +{
10975 + DBGPRINT(RT_DEBUG_TRACE,("SCANNING, suspend MSDU transmission ...\n"));
10976 +
10977 +
10978 + //
10979 + // Before BSS_SCAN_IN_PROGRESS, we need to keep Current R66 value and
10980 + // use Lowbound as R66 value on ScanNextChannel(...)
10981 + //
10982 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R66, &pAd->BbpTuning.R66CurrentValue);
10983 +
10984 + // set BBP_R66 to 0x30/0x40 when scanning (AsicSwitchChannel will set R66 according to channel when scanning)
10985 + RTMPSetAGCInitValue(pAd, BW_20);
10986 +
10987 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS);
10988 +}
10989 +
10990 +
10991 +/*
10992 + ========================================================================
10993 +
10994 + Routine Description:
10995 + Resume MSDU transmission
10996 +
10997 + Arguments:
10998 + pAd Pointer to our adapter
10999 +
11000 + Return Value:
11001 + None
11002 +
11003 + IRQL = DISPATCH_LEVEL
11004 +
11005 + Note:
11006 +
11007 + ========================================================================
11008 +*/
11009 +VOID RTMPResumeMsduTransmission(
11010 + IN PRTMP_ADAPTER pAd)
11011 +{
11012 + DBGPRINT(RT_DEBUG_TRACE,("SCAN done, resume MSDU transmission ...\n"));
11013 +
11014 +
11015 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, pAd->BbpTuning.R66CurrentValue);
11016 +
11017 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS);
11018 + RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
11019 +}
11020 +
11021 +
11022 +UINT deaggregate_AMSDU_announce(
11023 + IN PRTMP_ADAPTER pAd,
11024 + PNDIS_PACKET pPacket,
11025 + IN PUCHAR pData,
11026 + IN ULONG DataSize)
11027 +{
11028 + USHORT PayloadSize;
11029 + USHORT SubFrameSize;
11030 + PHEADER_802_3 pAMSDUsubheader;
11031 + UINT nMSDU;
11032 + UCHAR Header802_3[14];
11033 +
11034 + PUCHAR pPayload, pDA, pSA, pRemovedLLCSNAP;
11035 + PNDIS_PACKET pClonePacket;
11036 +
11037 +
11038 +
11039 + nMSDU = 0;
11040 +
11041 + while (DataSize > LENGTH_802_3)
11042 + {
11043 +
11044 + nMSDU++;
11045 +
11046 + pAMSDUsubheader = (PHEADER_802_3)pData;
11047 + PayloadSize = pAMSDUsubheader->Octet[1] + (pAMSDUsubheader->Octet[0]<<8);
11048 + SubFrameSize = PayloadSize + LENGTH_802_3;
11049 +
11050 +
11051 + if ((DataSize < SubFrameSize) || (PayloadSize > 1518 ))
11052 + {
11053 + break;
11054 + }
11055 +
11056 + pPayload = pData + LENGTH_802_3;
11057 + pDA = pData;
11058 + pSA = pData + MAC_ADDR_LEN;
11059 +
11060 + // convert to 802.3 header
11061 + CONVERT_TO_802_3(Header802_3, pDA, pSA, pPayload, PayloadSize, pRemovedLLCSNAP);
11062 +
11063 +#ifdef CONFIG_STA_SUPPORT
11064 + if ((Header802_3[12] == 0x88) && (Header802_3[13] == 0x8E) )
11065 + {
11066 + // avoid local heap overflow, use dyanamic allocation
11067 + MLME_QUEUE_ELEM *Elem = (MLME_QUEUE_ELEM *) kmalloc(sizeof(MLME_QUEUE_ELEM), MEM_ALLOC_FLAG);
11068 + memmove(Elem->Msg+(LENGTH_802_11 + LENGTH_802_1_H), pPayload, PayloadSize);
11069 + Elem->MsgLen = LENGTH_802_11 + LENGTH_802_1_H + PayloadSize;
11070 + WpaEAPOLKeyAction(pAd, Elem);
11071 + kfree(Elem);
11072 + }
11073 +#endif // CONFIG_STA_SUPPORT //
11074 +
11075 +#ifdef CONFIG_STA_SUPPORT
11076 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11077 + {
11078 + if (pRemovedLLCSNAP)
11079 + {
11080 + pPayload -= LENGTH_802_3;
11081 + PayloadSize += LENGTH_802_3;
11082 + NdisMoveMemory(pPayload, &Header802_3[0], LENGTH_802_3);
11083 + }
11084 + }
11085 +#endif // CONFIG_STA_SUPPORT //
11086 +
11087 + pClonePacket = ClonePacket(pAd, pPacket, pPayload, PayloadSize);
11088 + if (pClonePacket)
11089 + {
11090 +#ifdef CONFIG_STA_SUPPORT
11091 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11092 + ANNOUNCE_OR_FORWARD_802_3_PACKET(pAd, pClonePacket, RTMP_GET_PACKET_IF(pPacket));
11093 +#endif // CONFIG_STA_SUPPORT //
11094 + }
11095 +
11096 +
11097 + // A-MSDU has padding to multiple of 4 including subframe header.
11098 + // align SubFrameSize up to multiple of 4
11099 + SubFrameSize = (SubFrameSize+3)&(~0x3);
11100 +
11101 +
11102 + if (SubFrameSize > 1528 || SubFrameSize < 32)
11103 + {
11104 + break;
11105 + }
11106 +
11107 + if (DataSize > SubFrameSize)
11108 + {
11109 + pData += SubFrameSize;
11110 + DataSize -= SubFrameSize;
11111 + }
11112 + else
11113 + {
11114 + // end of A-MSDU
11115 + DataSize = 0;
11116 + }
11117 + }
11118 +
11119 + // finally release original rx packet
11120 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
11121 +
11122 + return nMSDU;
11123 +}
11124 +
11125 +
11126 +UINT BA_Reorder_AMSDU_Annnounce(
11127 + IN PRTMP_ADAPTER pAd,
11128 + IN PNDIS_PACKET pPacket)
11129 +{
11130 + PUCHAR pData;
11131 + USHORT DataSize;
11132 + UINT nMSDU = 0;
11133 +
11134 + pData = (PUCHAR) GET_OS_PKT_DATAPTR(pPacket);
11135 + DataSize = (USHORT) GET_OS_PKT_LEN(pPacket);
11136 +
11137 + nMSDU = deaggregate_AMSDU_announce(pAd, pPacket, pData, DataSize);
11138 +
11139 + return nMSDU;
11140 +}
11141 +
11142 +
11143 +/*
11144 + ==========================================================================
11145 + Description:
11146 + Look up the MAC address in the MAC table. Return NULL if not found.
11147 + Return:
11148 + pEntry - pointer to the MAC entry; NULL is not found
11149 + ==========================================================================
11150 +*/
11151 +MAC_TABLE_ENTRY *MacTableLookup(
11152 + IN PRTMP_ADAPTER pAd,
11153 + PUCHAR pAddr)
11154 +{
11155 + ULONG HashIdx;
11156 + MAC_TABLE_ENTRY *pEntry = NULL;
11157 +
11158 + HashIdx = MAC_ADDR_HASH_INDEX(pAddr);
11159 + pEntry = pAd->MacTab.Hash[HashIdx];
11160 +
11161 + while (pEntry && (pEntry->ValidAsCLI || pEntry->ValidAsWDS || pEntry->ValidAsApCli || pEntry->ValidAsMesh))
11162 + {
11163 + if (MAC_ADDR_EQUAL(pEntry->Addr, pAddr))
11164 + {
11165 + break;
11166 + }
11167 + else
11168 + pEntry = pEntry->pNext;
11169 + }
11170 +
11171 + return pEntry;
11172 +}
11173 +
11174 +MAC_TABLE_ENTRY *MacTableInsertEntry(
11175 + IN PRTMP_ADAPTER pAd,
11176 + IN PUCHAR pAddr,
11177 + IN UCHAR apidx,
11178 + IN BOOLEAN CleanAll)
11179 +{
11180 + UCHAR HashIdx;
11181 + int i, FirstWcid;
11182 + MAC_TABLE_ENTRY *pEntry = NULL, *pCurrEntry;
11183 +
11184 + // if FULL, return
11185 + if (pAd->MacTab.Size >= MAX_LEN_OF_MAC_TABLE)
11186 + return NULL;
11187 +
11188 + FirstWcid = 1;
11189 +#ifdef CONFIG_STA_SUPPORT
11190 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11191 + if (pAd->StaCfg.BssType == BSS_INFRA)
11192 + FirstWcid = 2;
11193 +#endif // CONFIG_STA_SUPPORT //
11194 +
11195 + // allocate one MAC entry
11196 + NdisAcquireSpinLock(&pAd->MacTabLock);
11197 + for (i = FirstWcid; i< MAX_LEN_OF_MAC_TABLE; i++) // skip entry#0 so that "entry index == AID" for fast lookup
11198 + {
11199 + // pick up the first available vacancy
11200 + if ((pAd->MacTab.Content[i].ValidAsCLI == FALSE) &&
11201 + (pAd->MacTab.Content[i].ValidAsWDS == FALSE) &&
11202 + (pAd->MacTab.Content[i].ValidAsApCli== FALSE) &&
11203 + (pAd->MacTab.Content[i].ValidAsMesh == FALSE)
11204 +#ifdef CONFIG_STA_SUPPORT
11205 +#ifdef QOS_DLS_SUPPORT
11206 + && (pAd->MacTab.Content[i].ValidAsDls == FALSE)
11207 +#endif // QOS_DLS_SUPPORT //
11208 +#endif // CONFIG_STA_SUPPORT //
11209 + )
11210 + {
11211 + pEntry = &pAd->MacTab.Content[i];
11212 + if (CleanAll == TRUE)
11213 + {
11214 + pEntry->MaxSupportedRate = RATE_11;
11215 + pEntry->CurrTxRate = RATE_11;
11216 + NdisZeroMemory(pEntry, sizeof(MAC_TABLE_ENTRY));
11217 + pEntry->PairwiseKey.KeyLen = 0;
11218 + pEntry->PairwiseKey.CipherAlg = CIPHER_NONE;
11219 + }
11220 +#ifdef CONFIG_STA_SUPPORT
11221 +#ifdef QOS_DLS_SUPPORT
11222 + if (apidx >= MIN_NET_DEVICE_FOR_DLS)
11223 + {
11224 + pEntry->ValidAsCLI = FALSE;
11225 + pEntry->ValidAsWDS = FALSE;
11226 + pEntry->ValidAsApCli = FALSE;
11227 + pEntry->ValidAsMesh = FALSE;
11228 + pEntry->ValidAsDls = TRUE;
11229 + pEntry->isCached = FALSE;
11230 + }
11231 + else
11232 +#endif // QOS_DLS_SUPPORT //
11233 +#endif // CONFIG_STA_SUPPORT //
11234 + {
11235 +
11236 +#ifdef CONFIG_STA_SUPPORT
11237 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11238 + {
11239 + pEntry->ValidAsCLI = TRUE;
11240 + pEntry->ValidAsWDS = FALSE;
11241 + pEntry->ValidAsApCli = FALSE;
11242 + pEntry->ValidAsMesh = FALSE;
11243 + pEntry->ValidAsDls = FALSE;
11244 + }
11245 +#endif // CONFIG_STA_SUPPORT //
11246 + }
11247 +
11248 + pEntry->bIAmBadAtheros = FALSE;
11249 + pEntry->pAd = pAd;
11250 + pEntry->CMTimerRunning = FALSE;
11251 + pEntry->EnqueueEapolStartTimerRunning = EAPOL_START_DISABLE;
11252 + pEntry->RSNIE_Len = 0;
11253 + NdisZeroMemory(pEntry->R_Counter, sizeof(pEntry->R_Counter));
11254 + pEntry->ReTryCounter = PEER_MSG1_RETRY_TIMER_CTR;
11255 +
11256 + if (pEntry->ValidAsMesh)
11257 + pEntry->apidx = (apidx - MIN_NET_DEVICE_FOR_MESH);
11258 + else if (pEntry->ValidAsApCli)
11259 + pEntry->apidx = (apidx - MIN_NET_DEVICE_FOR_APCLI);
11260 + else if (pEntry->ValidAsWDS)
11261 + pEntry->apidx = (apidx - MIN_NET_DEVICE_FOR_WDS);
11262 +#ifdef CONFIG_STA_SUPPORT
11263 +#ifdef QOS_DLS_SUPPORT
11264 + else if (pEntry->ValidAsDls)
11265 + pEntry->apidx = (apidx - MIN_NET_DEVICE_FOR_DLS);
11266 +#endif // QOS_DLS_SUPPORT //
11267 +#endif // CONFIG_STA_SUPPORT //
11268 + else
11269 + pEntry->apidx = apidx;
11270 +
11271 + {
11272 +
11273 +#ifdef CONFIG_STA_SUPPORT
11274 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11275 + {
11276 + pEntry->AuthMode = pAd->StaCfg.AuthMode;
11277 + pEntry->WepStatus = pAd->StaCfg.WepStatus;
11278 + pEntry->PrivacyFilter = Ndis802_11PrivFilterAcceptAll;
11279 +#ifdef RT2860
11280 + AsicRemovePairwiseKeyEntry(pAd, pEntry->apidx, (UCHAR)i);
11281 +#endif // RT2860 //
11282 + }
11283 +#endif // CONFIG_STA_SUPPORT //
11284 + }
11285 +
11286 + pEntry->GTKState = REKEY_NEGOTIATING;
11287 + pEntry->PairwiseKey.KeyLen = 0;
11288 + pEntry->PairwiseKey.CipherAlg = CIPHER_NONE;
11289 +#ifdef CONFIG_STA_SUPPORT
11290 + if ((pAd->OpMode == OPMODE_STA) &&
11291 + (pAd->StaCfg.BssType == BSS_ADHOC))
11292 + pEntry->PortSecured = WPA_802_1X_PORT_SECURED;
11293 + else
11294 +#ifdef QOS_DLS_SUPPORT
11295 + if (pEntry->ValidAsDls == TRUE)
11296 + pEntry->PortSecured = WPA_802_1X_PORT_SECURED;
11297 + else
11298 +#endif //QOS_DLS_SUPPORT
11299 +#endif // CONFIG_STA_SUPPORT //
11300 + pEntry->PortSecured = WPA_802_1X_PORT_NOT_SECURED;
11301 + pEntry->PMKID_CacheIdx = ENTRY_NOT_FOUND;
11302 + COPY_MAC_ADDR(pEntry->Addr, pAddr);
11303 + pEntry->Sst = SST_NOT_AUTH;
11304 + pEntry->AuthState = AS_NOT_AUTH;
11305 + pEntry->Aid = (USHORT)i; //0;
11306 + pEntry->CapabilityInfo = 0;
11307 + pEntry->PsMode = PWR_ACTIVE;
11308 + pEntry->PsQIdleCount = 0;
11309 + pEntry->NoDataIdleCount = 0;
11310 + pEntry->ContinueTxFailCnt = 0;
11311 + InitializeQueueHeader(&pEntry->PsQueue);
11312 +
11313 +
11314 + pAd->MacTab.Size ++;
11315 + // Add this entry into ASIC RX WCID search table
11316 + RT28XX_STA_ENTRY_ADD(pAd, pEntry);
11317 +
11318 +
11319 +
11320 + DBGPRINT(RT_DEBUG_TRACE, ("MacTableInsertEntry - allocate entry #%d, Total= %d\n",i, pAd->MacTab.Size));
11321 + break;
11322 + }
11323 + }
11324 +
11325 + // add this MAC entry into HASH table
11326 + if (pEntry)
11327 + {
11328 + HashIdx = MAC_ADDR_HASH_INDEX(pAddr);
11329 + if (pAd->MacTab.Hash[HashIdx] == NULL)
11330 + {
11331 + pAd->MacTab.Hash[HashIdx] = pEntry;
11332 + }
11333 + else
11334 + {
11335 + pCurrEntry = pAd->MacTab.Hash[HashIdx];
11336 + while (pCurrEntry->pNext != NULL)
11337 + pCurrEntry = pCurrEntry->pNext;
11338 + pCurrEntry->pNext = pEntry;
11339 + }
11340 + }
11341 +
11342 + NdisReleaseSpinLock(&pAd->MacTabLock);
11343 + return pEntry;
11344 +}
11345 +
11346 +/*
11347 + ==========================================================================
11348 + Description:
11349 + Delete a specified client from MAC table
11350 + ==========================================================================
11351 + */
11352 +BOOLEAN MacTableDeleteEntry(
11353 + IN PRTMP_ADAPTER pAd,
11354 + IN USHORT wcid,
11355 + IN PUCHAR pAddr)
11356 +{
11357 + USHORT HashIdx;
11358 + MAC_TABLE_ENTRY *pEntry, *pPrevEntry, *pProbeEntry;
11359 + BOOLEAN Cancelled;
11360 +
11361 + if (wcid >= MAX_LEN_OF_MAC_TABLE)
11362 + return FALSE;
11363 +
11364 + NdisAcquireSpinLock(&pAd->MacTabLock);
11365 +
11366 + HashIdx = MAC_ADDR_HASH_INDEX(pAddr);
11367 + pEntry = &pAd->MacTab.Content[wcid];
11368 +
11369 + if (pEntry && (pEntry->ValidAsCLI || pEntry->ValidAsApCli || pEntry->ValidAsWDS || pEntry->ValidAsMesh
11370 +#ifdef CONFIG_STA_SUPPORT
11371 +#ifdef QOS_DLS_SUPPORT
11372 + || pEntry->ValidAsDls
11373 +#endif // QOS_DLS_SUPPORT //
11374 +#endif // CONFIG_STA_SUPPORT //
11375 + ))
11376 + {
11377 + if (MAC_ADDR_EQUAL(pEntry->Addr, pAddr))
11378 + {
11379 +
11380 + // Delete this entry from ASIC on-chip WCID Table
11381 + RT28XX_STA_ENTRY_MAC_RESET(pAd, wcid);
11382 +
11383 +#ifdef DOT11_N_SUPPORT
11384 + // free resources of BA
11385 + BASessionTearDownALL(pAd, pEntry->Aid);
11386 +#endif // DOT11_N_SUPPORT //
11387 +
11388 +
11389 + pPrevEntry = NULL;
11390 + pProbeEntry = pAd->MacTab.Hash[HashIdx];
11391 + ASSERT(pProbeEntry);
11392 +
11393 + // update Hash list
11394 + do
11395 + {
11396 + if (pProbeEntry == pEntry)
11397 + {
11398 + if (pPrevEntry == NULL)
11399 + {
11400 + pAd->MacTab.Hash[HashIdx] = pEntry->pNext;
11401 + }
11402 + else
11403 + {
11404 + pPrevEntry->pNext = pEntry->pNext;
11405 + }
11406 + break;
11407 + }
11408 +
11409 + pPrevEntry = pProbeEntry;
11410 + pProbeEntry = pProbeEntry->pNext;
11411 + } while (pProbeEntry);
11412 +
11413 + // not found !!!
11414 + ASSERT(pProbeEntry != NULL);
11415 +
11416 + RT28XX_STA_ENTRY_KEY_DEL(pAd, BSS0, wcid);
11417 +
11418 +
11419 + if (pEntry->EnqueueEapolStartTimerRunning != EAPOL_START_DISABLE)
11420 + {
11421 + RTMPCancelTimer(&pEntry->EnqueueStartForPSKTimer, &Cancelled);
11422 + pEntry->EnqueueEapolStartTimerRunning = EAPOL_START_DISABLE;
11423 + }
11424 +
11425 +
11426 + NdisZeroMemory(pEntry, sizeof(MAC_TABLE_ENTRY));
11427 + pAd->MacTab.Size --;
11428 + DBGPRINT(RT_DEBUG_TRACE, ("MacTableDeleteEntry1 - Total= %d\n", pAd->MacTab.Size));
11429 + }
11430 + else
11431 + {
11432 + printk("\n%s: Impossible Wcid = %d !!!!!\n", __FUNCTION__, wcid);
11433 + }
11434 + }
11435 +
11436 + NdisReleaseSpinLock(&pAd->MacTabLock);
11437 +
11438 + //Reset operating mode when no Sta.
11439 + if (pAd->MacTab.Size == 0)
11440 + {
11441 +#ifdef DOT11_N_SUPPORT
11442 + pAd->CommonCfg.AddHTInfo.AddHtInfo2.OperaionMode = 0;
11443 +#endif // DOT11_N_SUPPORT //
11444 + AsicUpdateProtect(pAd, 0 /*pAd->CommonCfg.AddHTInfo.AddHtInfo2.OperaionMode*/, (ALLN_SETPROTECT), TRUE, 0 /*pAd->MacTab.fAnyStationNonGF*/);
11445 + }
11446 +
11447 + return TRUE;
11448 +}
11449 +
11450 +
11451 +/*
11452 + ==========================================================================
11453 + Description:
11454 + This routine reset the entire MAC table. All packets pending in
11455 + the power-saving queues are freed here.
11456 + ==========================================================================
11457 + */
11458 +VOID MacTableReset(
11459 + IN PRTMP_ADAPTER pAd)
11460 +{
11461 + int i;
11462 +
11463 + DBGPRINT(RT_DEBUG_TRACE, ("MacTableReset\n"));
11464 + //NdisAcquireSpinLock(&pAd->MacTabLock);
11465 +
11466 + for (i=1; i<MAX_LEN_OF_MAC_TABLE; i++)
11467 + {
11468 +#ifdef RT2860
11469 + RT28XX_STA_ENTRY_MAC_RESET(pAd, i);
11470 +#endif // RT2860 //
11471 + if (pAd->MacTab.Content[i].ValidAsCLI == TRUE)
11472 + {
11473 +
11474 +#ifdef DOT11_N_SUPPORT
11475 + // free resources of BA
11476 + BASessionTearDownALL(pAd, i);
11477 +#endif // DOT11_N_SUPPORT //
11478 +
11479 + pAd->MacTab.Content[i].ValidAsCLI = FALSE;
11480 +
11481 +
11482 +
11483 +
11484 + //AsicDelWcidTab(pAd, i);
11485 + }
11486 + }
11487 +
11488 + return;
11489 +}
11490 +
11491 +/*
11492 + ==========================================================================
11493 + Description:
11494 +
11495 + IRQL = DISPATCH_LEVEL
11496 +
11497 + ==========================================================================
11498 +*/
11499 +VOID AssocParmFill(
11500 + IN PRTMP_ADAPTER pAd,
11501 + IN OUT MLME_ASSOC_REQ_STRUCT *AssocReq,
11502 + IN PUCHAR pAddr,
11503 + IN USHORT CapabilityInfo,
11504 + IN ULONG Timeout,
11505 + IN USHORT ListenIntv)
11506 +{
11507 + COPY_MAC_ADDR(AssocReq->Addr, pAddr);
11508 + // Add mask to support 802.11b mode only
11509 + AssocReq->CapabilityInfo = CapabilityInfo & SUPPORTED_CAPABILITY_INFO; // not cf-pollable, not cf-poll-request
11510 + AssocReq->Timeout = Timeout;
11511 + AssocReq->ListenIntv = ListenIntv;
11512 +}
11513 +
11514 +
11515 +/*
11516 + ==========================================================================
11517 + Description:
11518 +
11519 + IRQL = DISPATCH_LEVEL
11520 +
11521 + ==========================================================================
11522 +*/
11523 +VOID DisassocParmFill(
11524 + IN PRTMP_ADAPTER pAd,
11525 + IN OUT MLME_DISASSOC_REQ_STRUCT *DisassocReq,
11526 + IN PUCHAR pAddr,
11527 + IN USHORT Reason)
11528 +{
11529 + COPY_MAC_ADDR(DisassocReq->Addr, pAddr);
11530 + DisassocReq->Reason = Reason;
11531 +}
11532 +
11533 +
11534 +/*
11535 + ========================================================================
11536 +
11537 + Routine Description:
11538 + Check the out going frame, if this is an DHCP or ARP datagram
11539 + will be duplicate another frame at low data rate transmit.
11540 +
11541 + Arguments:
11542 + pAd Pointer to our adapter
11543 + pPacket Pointer to outgoing Ndis frame
11544 +
11545 + Return Value:
11546 + TRUE To be duplicate at Low data rate transmit. (1mb)
11547 + FALSE Do nothing.
11548 +
11549 + IRQL = DISPATCH_LEVEL
11550 +
11551 + Note:
11552 +
11553 + MAC header + IP Header + UDP Header
11554 + 14 Bytes 20 Bytes
11555 +
11556 + UDP Header
11557 + 00|01|02|03|04|05|06|07|08|09|10|11|12|13|14|15|
11558 + Source Port
11559 + 16|17|18|19|20|21|22|23|24|25|26|27|28|29|30|31|
11560 + Destination Port
11561 +
11562 + port 0x43 means Bootstrap Protocol, server.
11563 + Port 0x44 means Bootstrap Protocol, client.
11564 +
11565 + ========================================================================
11566 +*/
11567 +
11568 +BOOLEAN RTMPCheckDHCPFrame(
11569 + IN PRTMP_ADAPTER pAd,
11570 + IN PNDIS_PACKET pPacket)
11571 +{
11572 + PACKET_INFO PacketInfo;
11573 + ULONG NumberOfBytesRead = 0;
11574 + ULONG CurrentOffset = 0;
11575 + PVOID pVirtualAddress = NULL;
11576 + UINT NdisBufferLength;
11577 + PUCHAR pSrc;
11578 + USHORT Protocol;
11579 + UCHAR ByteOffset36 = 0;
11580 + UCHAR ByteOffset38 = 0;
11581 + BOOLEAN ReadFirstParm = TRUE;
11582 +
11583 + RTMP_QueryPacketInfo(pPacket, &PacketInfo, (PUCHAR *)&pVirtualAddress, &NdisBufferLength);
11584 +
11585 + NumberOfBytesRead += NdisBufferLength;
11586 + pSrc = (PUCHAR) pVirtualAddress;
11587 + Protocol = *(pSrc + 12) * 256 + *(pSrc + 13);
11588 +
11589 + //
11590 + // Check DHCP & BOOTP protocol
11591 + //
11592 + while (NumberOfBytesRead <= PacketInfo.TotalPacketLength)
11593 + {
11594 + if ((NumberOfBytesRead >= 35) && (ReadFirstParm == TRUE))
11595 + {
11596 + CurrentOffset = 35 - (NumberOfBytesRead - NdisBufferLength);
11597 + ByteOffset36 = *(pSrc + CurrentOffset);
11598 + ReadFirstParm = FALSE;
11599 + }
11600 +
11601 + if (NumberOfBytesRead >= 37)
11602 + {
11603 + CurrentOffset = 37 - (NumberOfBytesRead - NdisBufferLength);
11604 + ByteOffset38 = *(pSrc + CurrentOffset);
11605 + //End of Read
11606 + break;
11607 + }
11608 + return FALSE;
11609 + }
11610 +
11611 + // Check for DHCP & BOOTP protocol
11612 + if ((ByteOffset36 != 0x44) || (ByteOffset38 != 0x43))
11613 + {
11614 + //
11615 + // 2054 (hex 0806) for ARP datagrams
11616 + // if this packet is not ARP datagrams, then do nothing
11617 + // ARP datagrams will also be duplicate at 1mb broadcast frames
11618 + //
11619 + if (Protocol != 0x0806 )
11620 + return FALSE;
11621 + }
11622 +
11623 + return TRUE;
11624 +}
11625 +
11626 +
11627 +BOOLEAN RTMPCheckEtherType(
11628 + IN PRTMP_ADAPTER pAd,
11629 + IN PNDIS_PACKET pPacket)
11630 +{
11631 + USHORT TypeLen;
11632 + UCHAR Byte0, Byte1;
11633 + PUCHAR pSrcBuf;
11634 + UINT32 pktLen;
11635 + UINT16 srcPort, dstPort;
11636 + BOOLEAN status = TRUE;
11637 +
11638 +
11639 + pSrcBuf = GET_OS_PKT_DATAPTR(pPacket);
11640 + pktLen = GET_OS_PKT_LEN(pPacket);
11641 +
11642 + ASSERT(pSrcBuf);
11643 +
11644 + RTMP_SET_PACKET_SPECIFIC(pPacket, 0);
11645 +
11646 + // get Ethernet protocol field
11647 + TypeLen = (pSrcBuf[12] << 8) + pSrcBuf[13];
11648 +
11649 + pSrcBuf += LENGTH_802_3; // Skip the Ethernet Header.
11650 +
11651 + if (TypeLen <= 1500)
11652 + { // 802.3, 802.3 LLC
11653 + /*
11654 + DestMAC(6) + SrcMAC(6) + Lenght(2) +
11655 + DSAP(1) + SSAP(1) + Control(1) +
11656 + if the DSAP = 0xAA, SSAP=0xAA, Contorl = 0x03, it has a 5-bytes SNAP header.
11657 + => + SNAP (5, OriginationID(3) + etherType(2))
11658 + */
11659 + if (pSrcBuf[0] == 0xAA && pSrcBuf[1] == 0xAA && pSrcBuf[2] == 0x03)
11660 + {
11661 + Sniff2BytesFromNdisBuffer(pSrcBuf, 6, &Byte0, &Byte1);
11662 + RTMP_SET_PACKET_LLCSNAP(pPacket, 1);
11663 + TypeLen = (USHORT)((Byte0 << 8) + Byte1);
11664 + pSrcBuf += 8; // Skip this LLC/SNAP header
11665 + }
11666 + else
11667 + {
11668 + //It just has 3-byte LLC header, maybe a legacy ether type frame. we didn't handle it.
11669 + }
11670 + }
11671 +
11672 + // If it's a VLAN packet, get the real Type/Length field.
11673 + if (TypeLen == 0x8100)
11674 + {
11675 + /* 0x8100 means VLAN packets */
11676 +
11677 + /* Dest. MAC Address (6-bytes) +
11678 + Source MAC Address (6-bytes) +
11679 + Length/Type = 802.1Q Tag Type (2-byte) +
11680 + Tag Control Information (2-bytes) +
11681 + Length / Type (2-bytes) +
11682 + data payload (0-n bytes) +
11683 + Pad (0-p bytes) +
11684 + Frame Check Sequence (4-bytes) */
11685 +
11686 + RTMP_SET_PACKET_VLAN(pPacket, 1);
11687 + Sniff2BytesFromNdisBuffer(pSrcBuf, 2, &Byte0, &Byte1);
11688 + TypeLen = (USHORT)((Byte0 << 8) + Byte1);
11689 +
11690 + pSrcBuf += 4; // Skip the VLAN Header.
11691 + }
11692 +
11693 + switch (TypeLen)
11694 + {
11695 + case 0x0800:
11696 + {
11697 + ASSERT((pktLen > 34));
11698 + if (*(pSrcBuf + 9) == 0x11)
11699 + { // udp packet
11700 + ASSERT((pktLen > 34)); // 14 for ethernet header, 20 for IP header
11701 +
11702 + pSrcBuf += 20; // Skip the IP header
11703 + srcPort = OS_NTOHS(*((UINT16 *)pSrcBuf));
11704 + dstPort = OS_NTOHS(*((UINT16 *)(pSrcBuf +2)));
11705 +
11706 + if ((srcPort==0x44 && dstPort==0x43) || (srcPort==0x43 && dstPort==0x44))
11707 + { //It's a BOOTP/DHCP packet
11708 + RTMP_SET_PACKET_DHCP(pPacket, 1);
11709 + }
11710 + }
11711 + }
11712 + break;
11713 + case 0x0806:
11714 + {
11715 + //ARP Packet.
11716 + RTMP_SET_PACKET_DHCP(pPacket, 1);
11717 + }
11718 + break;
11719 + case 0x888e:
11720 + {
11721 + // EAPOL Packet.
11722 + RTMP_SET_PACKET_EAPOL(pPacket, 1);
11723 + }
11724 + break;
11725 + default:
11726 + status = FALSE;
11727 + break;
11728 + }
11729 +
11730 + return status;
11731 +
11732 +}
11733 +
11734 +
11735 +
11736 +VOID Update_Rssi_Sample(
11737 + IN PRTMP_ADAPTER pAd,
11738 + IN RSSI_SAMPLE *pRssi,
11739 + IN PRXWI_STRUC pRxWI)
11740 + {
11741 + CHAR rssi0 = pRxWI->RSSI0;
11742 + CHAR rssi1 = pRxWI->RSSI1;
11743 + CHAR rssi2 = pRxWI->RSSI2;
11744 +
11745 + if (rssi0 != 0)
11746 + {
11747 + pRssi->LastRssi0 = ConvertToRssi(pAd, (CHAR)rssi0, RSSI_0);
11748 + pRssi->AvgRssi0X8 = (pRssi->AvgRssi0X8 - pRssi->AvgRssi0) + pRssi->LastRssi0;
11749 + pRssi->AvgRssi0 = pRssi->AvgRssi0X8 >> 3;
11750 + }
11751 +
11752 + if (rssi1 != 0)
11753 + {
11754 + pRssi->LastRssi1 = ConvertToRssi(pAd, (CHAR)rssi1, RSSI_1);
11755 + pRssi->AvgRssi1X8 = (pRssi->AvgRssi1X8 - pRssi->AvgRssi1) + pRssi->LastRssi1;
11756 + pRssi->AvgRssi1 = pRssi->AvgRssi1X8 >> 3;
11757 + }
11758 +
11759 + if (rssi2 != 0)
11760 + {
11761 + pRssi->LastRssi2 = ConvertToRssi(pAd, (CHAR)rssi2, RSSI_2);
11762 + pRssi->AvgRssi2X8 = (pRssi->AvgRssi2X8 - pRssi->AvgRssi2) + pRssi->LastRssi2;
11763 + pRssi->AvgRssi2 = pRssi->AvgRssi2X8 >> 3;
11764 + }
11765 +}
11766 +
11767 +
11768 +
11769 +// Normal legacy Rx packet indication
11770 +VOID Indicate_Legacy_Packet(
11771 + IN PRTMP_ADAPTER pAd,
11772 + IN RX_BLK *pRxBlk,
11773 + IN UCHAR FromWhichBSSID)
11774 +{
11775 + PNDIS_PACKET pRxPacket = pRxBlk->pRxPacket;
11776 + UCHAR Header802_3[LENGTH_802_3];
11777 +
11778 + // 1. get 802.3 Header
11779 + // 2. remove LLC
11780 + // a. pointer pRxBlk->pData to payload
11781 + // b. modify pRxBlk->DataSize
11782 +#ifdef CONFIG_STA_SUPPORT
11783 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11784 + RTMP_802_11_REMOVE_LLC_AND_CONVERT_TO_802_3(pRxBlk, Header802_3);
11785 +#endif // CONFIG_STA_SUPPORT //
11786 +
11787 + if (pRxBlk->DataSize > MAX_RX_PKT_LEN)
11788 + {
11789 +
11790 + // release packet
11791 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
11792 + return;
11793 + }
11794 +
11795 +
11796 + STATS_INC_RX_PACKETS(pAd, FromWhichBSSID);
11797 +
11798 +
11799 + wlan_802_11_to_802_3_packet(pAd, pRxBlk, Header802_3, FromWhichBSSID);
11800 +
11801 + //
11802 + // pass this 802.3 packet to upper layer or forward this packet to WM directly
11803 + //
11804 +#ifdef CONFIG_STA_SUPPORT
11805 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11806 + ANNOUNCE_OR_FORWARD_802_3_PACKET(pAd, pRxPacket, FromWhichBSSID);
11807 +#endif // CONFIG_STA_SUPPORT //
11808 +
11809 +}
11810 +
11811 +
11812 +// Normal, AMPDU or AMSDU
11813 +VOID CmmRxnonRalinkFrameIndicate(
11814 + IN PRTMP_ADAPTER pAd,
11815 + IN RX_BLK *pRxBlk,
11816 + IN UCHAR FromWhichBSSID)
11817 +{
11818 +#ifdef DOT11_N_SUPPORT
11819 + if (RX_BLK_TEST_FLAG(pRxBlk, fRX_AMPDU) && (pAd->CommonCfg.bDisableReordering == 0))
11820 + {
11821 + Indicate_AMPDU_Packet(pAd, pRxBlk, FromWhichBSSID);
11822 + }
11823 + else
11824 +#endif // DOT11_N_SUPPORT //
11825 + {
11826 +#ifdef DOT11_N_SUPPORT
11827 + if (RX_BLK_TEST_FLAG(pRxBlk, fRX_AMSDU))
11828 + {
11829 + // handle A-MSDU
11830 + Indicate_AMSDU_Packet(pAd, pRxBlk, FromWhichBSSID);
11831 + }
11832 + else
11833 +#endif // DOT11_N_SUPPORT //
11834 + {
11835 + Indicate_Legacy_Packet(pAd, pRxBlk, FromWhichBSSID);
11836 + }
11837 + }
11838 +}
11839 +
11840 +
11841 +VOID CmmRxRalinkFrameIndicate(
11842 + IN PRTMP_ADAPTER pAd,
11843 + IN MAC_TABLE_ENTRY *pEntry,
11844 + IN RX_BLK *pRxBlk,
11845 + IN UCHAR FromWhichBSSID)
11846 +{
11847 + UCHAR Header802_3[LENGTH_802_3];
11848 + UINT16 Msdu2Size;
11849 + UINT16 Payload1Size, Payload2Size;
11850 + PUCHAR pData2;
11851 + PNDIS_PACKET pPacket2 = NULL;
11852 +
11853 +
11854 +
11855 + Msdu2Size = *(pRxBlk->pData) + (*(pRxBlk->pData+1) << 8);
11856 +
11857 + if ((Msdu2Size <= 1536) && (Msdu2Size < pRxBlk->DataSize))
11858 + {
11859 + /* skip two byte MSDU2 len */
11860 + pRxBlk->pData += 2;
11861 + pRxBlk->DataSize -= 2;
11862 + }
11863 + else
11864 + {
11865 + // release packet
11866 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
11867 + return;
11868 + }
11869 +
11870 + // get 802.3 Header and remove LLC
11871 +#ifdef CONFIG_STA_SUPPORT
11872 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11873 + RTMP_802_11_REMOVE_LLC_AND_CONVERT_TO_802_3(pRxBlk, Header802_3);
11874 +#endif // CONFIG_STA_SUPPORT //
11875 +
11876 +
11877 + ASSERT(pRxBlk->pRxPacket);
11878 +
11879 + // Ralink Aggregation frame
11880 + pAd->RalinkCounters.OneSecRxAggregationCount ++;
11881 + Payload1Size = pRxBlk->DataSize - Msdu2Size;
11882 + Payload2Size = Msdu2Size - LENGTH_802_3;
11883 +
11884 + pData2 = pRxBlk->pData + Payload1Size + LENGTH_802_3;
11885 +#ifdef CONFIG_STA_SUPPORT
11886 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11887 + pPacket2 = duplicate_pkt(pAd, (pData2-LENGTH_802_3), LENGTH_802_3, pData2, Payload2Size, FromWhichBSSID);
11888 +#endif // CONFIG_STA_SUPPORT //
11889 +
11890 + if (!pPacket2)
11891 + {
11892 + // release packet
11893 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
11894 + return;
11895 + }
11896 +
11897 + // update payload size of 1st packet
11898 + pRxBlk->DataSize = Payload1Size;
11899 + wlan_802_11_to_802_3_packet(pAd, pRxBlk, Header802_3, FromWhichBSSID);
11900 +
11901 +#ifdef CONFIG_STA_SUPPORT
11902 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11903 + ANNOUNCE_OR_FORWARD_802_3_PACKET(pAd, pRxBlk->pRxPacket, FromWhichBSSID);
11904 +#endif // CONFIG_STA_SUPPORT //
11905 +
11906 + if (pPacket2)
11907 + {
11908 +#ifdef CONFIG_STA_SUPPORT
11909 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
11910 + ANNOUNCE_OR_FORWARD_802_3_PACKET(pAd, pPacket2, FromWhichBSSID);
11911 +#endif // CONFIG_STA_SUPPORT //
11912 + }
11913 +}
11914 +
11915 +
11916 +#define RESET_FRAGFRAME(_fragFrame) \
11917 + { \
11918 + _fragFrame.RxSize = 0; \
11919 + _fragFrame.Sequence = 0; \
11920 + _fragFrame.LastFrag = 0; \
11921 + _fragFrame.Flags = 0; \
11922 + }
11923 +
11924 +
11925 +PNDIS_PACKET RTMPDeFragmentDataFrame(
11926 + IN PRTMP_ADAPTER pAd,
11927 + IN RX_BLK *pRxBlk)
11928 +{
11929 + PHEADER_802_11 pHeader = pRxBlk->pHeader;
11930 + PNDIS_PACKET pRxPacket = pRxBlk->pRxPacket;
11931 + UCHAR *pData = pRxBlk->pData;
11932 + USHORT DataSize = pRxBlk->DataSize;
11933 + PNDIS_PACKET pRetPacket = NULL;
11934 + UCHAR *pFragBuffer = NULL;
11935 + BOOLEAN bReassDone = FALSE;
11936 + UCHAR HeaderRoom = 0;
11937 +
11938 +
11939 + ASSERT(pHeader);
11940 +
11941 + HeaderRoom = pData - (UCHAR *)pHeader;
11942 +
11943 + // Re-assemble the fragmented packets
11944 + if (pHeader->Frag == 0) // Frag. Number is 0 : First frag or only one pkt
11945 + {
11946 + // the first pkt of fragment, record it.
11947 + if (pHeader->FC.MoreFrag)
11948 + {
11949 + ASSERT(pAd->FragFrame.pFragPacket);
11950 + pFragBuffer = GET_OS_PKT_DATAPTR(pAd->FragFrame.pFragPacket);
11951 + pAd->FragFrame.RxSize = DataSize + HeaderRoom;
11952 + NdisMoveMemory(pFragBuffer, pHeader, pAd->FragFrame.RxSize);
11953 + pAd->FragFrame.Sequence = pHeader->Sequence;
11954 + pAd->FragFrame.LastFrag = pHeader->Frag; // Should be 0
11955 + ASSERT(pAd->FragFrame.LastFrag == 0);
11956 + goto done; // end of processing this frame
11957 + }
11958 + }
11959 + else //Middle & End of fragment
11960 + {
11961 + if ((pHeader->Sequence != pAd->FragFrame.Sequence) ||
11962 + (pHeader->Frag != (pAd->FragFrame.LastFrag + 1)))
11963 + {
11964 + // Fragment is not the same sequence or out of fragment number order
11965 + // Reset Fragment control blk
11966 + RESET_FRAGFRAME(pAd->FragFrame);
11967 + DBGPRINT(RT_DEBUG_ERROR, ("Fragment is not the same sequence or out of fragment number order.\n"));
11968 + goto done; // give up this frame
11969 + }
11970 + else if ((pAd->FragFrame.RxSize + DataSize) > MAX_FRAME_SIZE)
11971 + {
11972 + // Fragment frame is too large, it exeeds the maximum frame size.
11973 + // Reset Fragment control blk
11974 + RESET_FRAGFRAME(pAd->FragFrame);
11975 + DBGPRINT(RT_DEBUG_ERROR, ("Fragment frame is too large, it exeeds the maximum frame size.\n"));
11976 + goto done; // give up this frame
11977 + }
11978 +
11979 + //
11980 + // Broadcom AP(BCM94704AGR) will send out LLC in fragment's packet, LLC only can accpet at first fragment.
11981 + // In this case, we will dropt it.
11982 + //
11983 + if (NdisEqualMemory(pData, SNAP_802_1H, sizeof(SNAP_802_1H)))
11984 + {
11985 + DBGPRINT(RT_DEBUG_ERROR, ("Find another LLC at Middle or End fragment(SN=%d, Frag=%d)\n", pHeader->Sequence, pHeader->Frag));
11986 + goto done; // give up this frame
11987 + }
11988 +
11989 + pFragBuffer = GET_OS_PKT_DATAPTR(pAd->FragFrame.pFragPacket);
11990 +
11991 + // concatenate this fragment into the re-assembly buffer
11992 + NdisMoveMemory((pFragBuffer + pAd->FragFrame.RxSize), pData, DataSize);
11993 + pAd->FragFrame.RxSize += DataSize;
11994 + pAd->FragFrame.LastFrag = pHeader->Frag; // Update fragment number
11995 +
11996 + // Last fragment
11997 + if (pHeader->FC.MoreFrag == FALSE)
11998 + {
11999 + bReassDone = TRUE;
12000 + }
12001 + }
12002 +
12003 +done:
12004 + // always release rx fragmented packet
12005 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
12006 +
12007 + // return defragmented packet if packet is reassembled completely
12008 + // otherwise return NULL
12009 + if (bReassDone)
12010 + {
12011 + PNDIS_PACKET pNewFragPacket;
12012 +
12013 + // allocate a new packet buffer for fragment
12014 + pNewFragPacket = RTMP_AllocateFragPacketBuffer(pAd, RX_BUFFER_NORMSIZE);
12015 + if (pNewFragPacket)
12016 + {
12017 + // update RxBlk
12018 + pRetPacket = pAd->FragFrame.pFragPacket;
12019 + pAd->FragFrame.pFragPacket = pNewFragPacket;
12020 + pRxBlk->pHeader = (PHEADER_802_11) GET_OS_PKT_DATAPTR(pRetPacket);
12021 + pRxBlk->pData = (UCHAR *)pRxBlk->pHeader + HeaderRoom;
12022 + pRxBlk->DataSize = pAd->FragFrame.RxSize - HeaderRoom;
12023 + pRxBlk->pRxPacket = pRetPacket;
12024 + }
12025 + else
12026 + {
12027 + RESET_FRAGFRAME(pAd->FragFrame);
12028 + }
12029 + }
12030 +
12031 + return pRetPacket;
12032 +}
12033 +
12034 +
12035 +VOID Indicate_AMSDU_Packet(
12036 + IN PRTMP_ADAPTER pAd,
12037 + IN RX_BLK *pRxBlk,
12038 + IN UCHAR FromWhichBSSID)
12039 +{
12040 + UINT nMSDU;
12041 +
12042 + update_os_packet_info(pAd, pRxBlk, FromWhichBSSID);
12043 + RTMP_SET_PACKET_IF(pRxBlk->pRxPacket, FromWhichBSSID);
12044 + nMSDU = deaggregate_AMSDU_announce(pAd, pRxBlk->pRxPacket, pRxBlk->pData, pRxBlk->DataSize);
12045 +}
12046 +
12047 +VOID Indicate_EAPOL_Packet(
12048 + IN PRTMP_ADAPTER pAd,
12049 + IN RX_BLK *pRxBlk,
12050 + IN UCHAR FromWhichBSSID)
12051 +{
12052 + MAC_TABLE_ENTRY *pEntry = NULL;
12053 +
12054 +
12055 +#ifdef CONFIG_STA_SUPPORT
12056 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12057 + {
12058 + pEntry = &pAd->MacTab.Content[BSSID_WCID];
12059 + STARxEAPOLFrameIndicate(pAd, pEntry, pRxBlk, FromWhichBSSID);
12060 + return;
12061 + }
12062 +#endif // CONFIG_STA_SUPPORT //
12063 +
12064 + if (pEntry == NULL)
12065 + {
12066 + DBGPRINT(RT_DEBUG_WARN, ("Indicate_EAPOL_Packet: drop and release the invalid packet.\n"));
12067 + // release packet
12068 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
12069 + return;
12070 + }
12071 +}
12072 +
12073 +#define BCN_TBTT_OFFSET 64 //defer 64 us
12074 +VOID ReSyncBeaconTime(
12075 + IN PRTMP_ADAPTER pAd)
12076 +{
12077 +
12078 + UINT32 Offset;
12079 +
12080 +
12081 + Offset = (pAd->TbttTickCount) % (BCN_TBTT_OFFSET);
12082 +
12083 + pAd->TbttTickCount++;
12084 +
12085 + //
12086 + // The updated BeaconInterval Value will affect Beacon Interval after two TBTT
12087 + // beacasue the original BeaconInterval had been loaded into next TBTT_TIMER
12088 + //
12089 + if (Offset == (BCN_TBTT_OFFSET-2))
12090 + {
12091 + BCN_TIME_CFG_STRUC csr;
12092 + RTMP_IO_READ32(pAd, BCN_TIME_CFG, &csr.word);
12093 + csr.field.BeaconInterval = (pAd->CommonCfg.BeaconPeriod << 4) - 1 ; // ASIC register in units of 1/16 TU = 64us
12094 + RTMP_IO_WRITE32(pAd, BCN_TIME_CFG, csr.word);
12095 + }
12096 + else
12097 + {
12098 + if (Offset == (BCN_TBTT_OFFSET-1))
12099 + {
12100 + BCN_TIME_CFG_STRUC csr;
12101 +
12102 + RTMP_IO_READ32(pAd, BCN_TIME_CFG, &csr.word);
12103 + csr.field.BeaconInterval = (pAd->CommonCfg.BeaconPeriod) << 4; // ASIC register in units of 1/16 TU
12104 + RTMP_IO_WRITE32(pAd, BCN_TIME_CFG, csr.word);
12105 + }
12106 + }
12107 +}
12108 +
12109 --- /dev/null
12110 +++ b/drivers/staging/rt2860/common/cmm_info.c
12111 @@ -0,0 +1,3417 @@
12112 +/*
12113 + *************************************************************************
12114 + * Ralink Tech Inc.
12115 + * 5F., No.36, Taiyuan St., Jhubei City,
12116 + * Hsinchu County 302,
12117 + * Taiwan, R.O.C.
12118 + *
12119 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
12120 + *
12121 + * This program is free software; you can redistribute it and/or modify *
12122 + * it under the terms of the GNU General Public License as published by *
12123 + * the Free Software Foundation; either version 2 of the License, or *
12124 + * (at your option) any later version. *
12125 + * *
12126 + * This program is distributed in the hope that it will be useful, *
12127 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12128 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
12129 + * GNU General Public License for more details. *
12130 + * *
12131 + * You should have received a copy of the GNU General Public License *
12132 + * along with this program; if not, write to the *
12133 + * Free Software Foundation, Inc., *
12134 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
12135 + * *
12136 + *************************************************************************
12137 +*/
12138 +
12139 +#include "../rt_config.h"
12140 +
12141 +INT Show_SSID_Proc(
12142 + IN PRTMP_ADAPTER pAd,
12143 + OUT PUCHAR pBuf);
12144 +
12145 +INT Show_WirelessMode_Proc(
12146 + IN PRTMP_ADAPTER pAd,
12147 + OUT PUCHAR pBuf);
12148 +
12149 +INT Show_TxBurst_Proc(
12150 + IN PRTMP_ADAPTER pAd,
12151 + OUT PUCHAR pBuf);
12152 +
12153 +INT Show_TxPreamble_Proc(
12154 + IN PRTMP_ADAPTER pAd,
12155 + OUT PUCHAR pBuf);
12156 +
12157 +INT Show_TxPower_Proc(
12158 + IN PRTMP_ADAPTER pAd,
12159 + OUT PUCHAR pBuf);
12160 +
12161 +INT Show_Channel_Proc(
12162 + IN PRTMP_ADAPTER pAd,
12163 + OUT PUCHAR pBuf);
12164 +
12165 +INT Show_BGProtection_Proc(
12166 + IN PRTMP_ADAPTER pAd,
12167 + OUT PUCHAR pBuf);
12168 +
12169 +INT Show_RTSThreshold_Proc(
12170 + IN PRTMP_ADAPTER pAd,
12171 + OUT PUCHAR pBuf);
12172 +
12173 +INT Show_FragThreshold_Proc(
12174 + IN PRTMP_ADAPTER pAd,
12175 + OUT PUCHAR pBuf);
12176 +
12177 +#ifdef DOT11_N_SUPPORT
12178 +INT Show_HtBw_Proc(
12179 + IN PRTMP_ADAPTER pAd,
12180 + OUT PUCHAR pBuf);
12181 +
12182 +INT Show_HtMcs_Proc(
12183 + IN PRTMP_ADAPTER pAd,
12184 + OUT PUCHAR pBuf);
12185 +
12186 +INT Show_HtGi_Proc(
12187 + IN PRTMP_ADAPTER pAd,
12188 + OUT PUCHAR pBuf);
12189 +
12190 +INT Show_HtOpMode_Proc(
12191 + IN PRTMP_ADAPTER pAd,
12192 + OUT PUCHAR pBuf);
12193 +
12194 +INT Show_HtExtcha_Proc(
12195 + IN PRTMP_ADAPTER pAd,
12196 + OUT PUCHAR pBuf);
12197 +
12198 +INT Show_HtMpduDensity_Proc(
12199 + IN PRTMP_ADAPTER pAd,
12200 + OUT PUCHAR pBuf);
12201 +
12202 +INT Show_HtBaWinSize_Proc(
12203 + IN PRTMP_ADAPTER pAd,
12204 + OUT PUCHAR pBuf);
12205 +
12206 +INT Show_HtRdg_Proc(
12207 + IN PRTMP_ADAPTER pAd,
12208 + OUT PUCHAR pBuf);
12209 +
12210 +INT Show_HtAmsdu_Proc(
12211 + IN PRTMP_ADAPTER pAd,
12212 + OUT PUCHAR pBuf);
12213 +
12214 +INT Show_HtAutoBa_Proc(
12215 + IN PRTMP_ADAPTER pAd,
12216 + OUT PUCHAR pBuf);
12217 +#endif // DOT11_N_SUPPORT //
12218 +
12219 +INT Show_CountryRegion_Proc(
12220 + IN PRTMP_ADAPTER pAd,
12221 + OUT PUCHAR pBuf);
12222 +
12223 +INT Show_CountryRegionABand_Proc(
12224 + IN PRTMP_ADAPTER pAd,
12225 + OUT PUCHAR pBuf);
12226 +
12227 +INT Show_CountryCode_Proc(
12228 + IN PRTMP_ADAPTER pAd,
12229 + OUT PUCHAR pBuf);
12230 +
12231 +#ifdef AGGREGATION_SUPPORT
12232 +INT Show_PktAggregate_Proc(
12233 + IN PRTMP_ADAPTER pAd,
12234 + OUT PUCHAR pBuf);
12235 +#endif // AGGREGATION_SUPPORT //
12236 +
12237 +#ifdef WMM_SUPPORT
12238 +INT Show_WmmCapable_Proc(
12239 + IN PRTMP_ADAPTER pAd,
12240 + OUT PUCHAR pBuf);
12241 +#endif // WMM_SUPPORT //
12242 +
12243 +INT Show_IEEE80211H_Proc(
12244 + IN PRTMP_ADAPTER pAd,
12245 + OUT PUCHAR pBuf);
12246 +
12247 +#ifdef CONFIG_STA_SUPPORT
12248 +INT Show_NetworkType_Proc(
12249 + IN PRTMP_ADAPTER pAd,
12250 + OUT PUCHAR pBuf);
12251 +#endif // CONFIG_STA_SUPPORT //
12252 +
12253 +INT Show_AuthMode_Proc(
12254 + IN PRTMP_ADAPTER pAd,
12255 + OUT PUCHAR pBuf);
12256 +
12257 +INT Show_EncrypType_Proc(
12258 + IN PRTMP_ADAPTER pAd,
12259 + OUT PUCHAR pBuf);
12260 +
12261 +INT Show_DefaultKeyID_Proc(
12262 + IN PRTMP_ADAPTER pAd,
12263 + OUT PUCHAR pBuf);
12264 +
12265 +INT Show_Key1_Proc(
12266 + IN PRTMP_ADAPTER pAd,
12267 + OUT PUCHAR pBuf);
12268 +
12269 +INT Show_Key2_Proc(
12270 + IN PRTMP_ADAPTER pAd,
12271 + OUT PUCHAR pBuf);
12272 +
12273 +INT Show_Key3_Proc(
12274 + IN PRTMP_ADAPTER pAd,
12275 + OUT PUCHAR pBuf);
12276 +
12277 +INT Show_Key4_Proc(
12278 + IN PRTMP_ADAPTER pAd,
12279 + OUT PUCHAR pBuf);
12280 +
12281 +INT Show_WPAPSK_Proc(
12282 + IN PRTMP_ADAPTER pAd,
12283 + OUT PUCHAR pBuf);
12284 +
12285 +static struct {
12286 + CHAR *name;
12287 + INT (*show_proc)(PRTMP_ADAPTER pAdapter, PUCHAR arg);
12288 +} *PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC, RTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC[] = {
12289 + {"SSID", Show_SSID_Proc},
12290 + {"WirelessMode", Show_WirelessMode_Proc},
12291 + {"TxBurst", Show_TxBurst_Proc},
12292 + {"TxPreamble", Show_TxPreamble_Proc},
12293 + {"TxPower", Show_TxPower_Proc},
12294 + {"Channel", Show_Channel_Proc},
12295 + {"BGProtection", Show_BGProtection_Proc},
12296 + {"RTSThreshold", Show_RTSThreshold_Proc},
12297 + {"FragThreshold", Show_FragThreshold_Proc},
12298 +#ifdef DOT11_N_SUPPORT
12299 + {"HtBw", Show_HtBw_Proc},
12300 + {"HtMcs", Show_HtMcs_Proc},
12301 + {"HtGi", Show_HtGi_Proc},
12302 + {"HtOpMode", Show_HtOpMode_Proc},
12303 + {"HtExtcha", Show_HtExtcha_Proc},
12304 + {"HtMpduDensity", Show_HtMpduDensity_Proc},
12305 + {"HtBaWinSize", Show_HtBaWinSize_Proc},
12306 + {"HtRdg", Show_HtRdg_Proc},
12307 + {"HtAmsdu", Show_HtAmsdu_Proc},
12308 + {"HtAutoBa", Show_HtAutoBa_Proc},
12309 +#endif // DOT11_N_SUPPORT //
12310 + {"CountryRegion", Show_CountryRegion_Proc},
12311 + {"CountryRegionABand", Show_CountryRegionABand_Proc},
12312 + {"CountryCode", Show_CountryCode_Proc},
12313 +#ifdef AGGREGATION_SUPPORT
12314 + {"PktAggregate", Show_PktAggregate_Proc},
12315 +#endif
12316 +
12317 +#ifdef WMM_SUPPORT
12318 + {"WmmCapable", Show_WmmCapable_Proc},
12319 +#endif
12320 + {"IEEE80211H", Show_IEEE80211H_Proc},
12321 +#ifdef CONFIG_STA_SUPPORT
12322 + {"NetworkType", Show_NetworkType_Proc},
12323 +#endif // CONFIG_STA_SUPPORT //
12324 + {"AuthMode", Show_AuthMode_Proc},
12325 + {"EncrypType", Show_EncrypType_Proc},
12326 + {"DefaultKeyID", Show_DefaultKeyID_Proc},
12327 + {"Key1", Show_Key1_Proc},
12328 + {"Key2", Show_Key2_Proc},
12329 + {"Key3", Show_Key3_Proc},
12330 + {"Key4", Show_Key4_Proc},
12331 + {"WPAPSK", Show_WPAPSK_Proc},
12332 + {NULL, NULL}
12333 +};
12334 +
12335 +/*
12336 + ==========================================================================
12337 + Description:
12338 + Get Driver version.
12339 +
12340 + Return:
12341 + ==========================================================================
12342 +*/
12343 +INT Set_DriverVersion_Proc(
12344 + IN PRTMP_ADAPTER pAd,
12345 + IN PUCHAR arg)
12346 +{
12347 +
12348 +#ifdef CONFIG_STA_SUPPORT
12349 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12350 + DBGPRINT(RT_DEBUG_TRACE, ("Driver version-%s\n", STA_DRIVER_VERSION));
12351 +#endif // CONFIG_STA_SUPPORT //
12352 +
12353 + return TRUE;
12354 +}
12355 +
12356 +/*
12357 + ==========================================================================
12358 + Description:
12359 + Set Country Region.
12360 + This command will not work, if the field of CountryRegion in eeprom is programmed.
12361 + Return:
12362 + TRUE if all parameters are OK, FALSE otherwise
12363 + ==========================================================================
12364 +*/
12365 +INT Set_CountryRegion_Proc(
12366 + IN PRTMP_ADAPTER pAd,
12367 + IN PUCHAR arg)
12368 +{
12369 + ULONG region;
12370 +
12371 + region = simple_strtol(arg, 0, 10);
12372 +
12373 +#ifdef EXT_BUILD_CHANNEL_LIST
12374 + return -EOPNOTSUPP;
12375 +#endif // EXT_BUILD_CHANNEL_LIST //
12376 +
12377 + // Country can be set only when EEPROM not programmed
12378 + if (pAd->CommonCfg.CountryRegion & 0x80)
12379 + {
12380 + DBGPRINT(RT_DEBUG_ERROR, ("Set_CountryRegion_Proc::parameter of CountryRegion in eeprom is programmed \n"));
12381 + return FALSE;
12382 + }
12383 +
12384 + if((region >= 0) && (region <= REGION_MAXIMUM_BG_BAND))
12385 + {
12386 + pAd->CommonCfg.CountryRegion = (UCHAR) region;
12387 + }
12388 + else if (region == REGION_31_BG_BAND)
12389 + {
12390 + pAd->CommonCfg.CountryRegion = (UCHAR) region;
12391 + }
12392 + else
12393 + {
12394 + DBGPRINT(RT_DEBUG_ERROR, ("Set_CountryRegion_Proc::parameters out of range\n"));
12395 + return FALSE;
12396 + }
12397 +
12398 + // if set country region, driver needs to be reset
12399 + BuildChannelList(pAd);
12400 +
12401 + DBGPRINT(RT_DEBUG_TRACE, ("Set_CountryRegion_Proc::(CountryRegion=%d)\n", pAd->CommonCfg.CountryRegion));
12402 +
12403 + return TRUE;
12404 +}
12405 +
12406 +/*
12407 + ==========================================================================
12408 + Description:
12409 + Set Country Region for A band.
12410 + This command will not work, if the field of CountryRegion in eeprom is programmed.
12411 + Return:
12412 + TRUE if all parameters are OK, FALSE otherwise
12413 + ==========================================================================
12414 +*/
12415 +INT Set_CountryRegionABand_Proc(
12416 + IN PRTMP_ADAPTER pAd,
12417 + IN PUCHAR arg)
12418 +{
12419 + ULONG region;
12420 +
12421 + region = simple_strtol(arg, 0, 10);
12422 +
12423 +#ifdef EXT_BUILD_CHANNEL_LIST
12424 + return -EOPNOTSUPP;
12425 +#endif // EXT_BUILD_CHANNEL_LIST //
12426 +
12427 + // Country can be set only when EEPROM not programmed
12428 + if (pAd->CommonCfg.CountryRegionForABand & 0x80)
12429 + {
12430 + DBGPRINT(RT_DEBUG_ERROR, ("Set_CountryRegionABand_Proc::parameter of CountryRegion in eeprom is programmed \n"));
12431 + return FALSE;
12432 + }
12433 +
12434 + if((region >= 0) && (region <= REGION_MAXIMUM_A_BAND))
12435 + {
12436 + pAd->CommonCfg.CountryRegionForABand = (UCHAR) region;
12437 + }
12438 + else
12439 + {
12440 + DBGPRINT(RT_DEBUG_ERROR, ("Set_CountryRegionABand_Proc::parameters out of range\n"));
12441 + return FALSE;
12442 + }
12443 +
12444 + // if set country region, driver needs to be reset
12445 + BuildChannelList(pAd);
12446 +
12447 + DBGPRINT(RT_DEBUG_TRACE, ("Set_CountryRegionABand_Proc::(CountryRegion=%d)\n", pAd->CommonCfg.CountryRegionForABand));
12448 +
12449 + return TRUE;
12450 +}
12451 +
12452 +/*
12453 + ==========================================================================
12454 + Description:
12455 + Set Wireless Mode
12456 + Return:
12457 + TRUE if all parameters are OK, FALSE otherwise
12458 + ==========================================================================
12459 +*/
12460 +INT Set_WirelessMode_Proc(
12461 + IN PRTMP_ADAPTER pAd,
12462 + IN PUCHAR arg)
12463 +{
12464 + ULONG WirelessMode;
12465 + INT success = TRUE;
12466 +
12467 + WirelessMode = simple_strtol(arg, 0, 10);
12468 +
12469 +
12470 +#ifdef CONFIG_STA_SUPPORT
12471 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12472 + {
12473 + INT MaxPhyMode = PHY_11G;
12474 +
12475 +#ifdef DOT11_N_SUPPORT
12476 + MaxPhyMode = PHY_11N_5G;
12477 +#endif // DOT11_N_SUPPORT //
12478 +
12479 + if (WirelessMode <= MaxPhyMode)
12480 + {
12481 + RTMPSetPhyMode(pAd, WirelessMode);
12482 +#ifdef DOT11_N_SUPPORT
12483 + if (WirelessMode >= PHY_11ABGN_MIXED)
12484 + {
12485 + pAd->CommonCfg.BACapability.field.AutoBA = TRUE;
12486 + pAd->CommonCfg.REGBACapability.field.AutoBA = TRUE;
12487 + }
12488 + else
12489 + {
12490 + pAd->CommonCfg.BACapability.field.AutoBA = FALSE;
12491 + pAd->CommonCfg.REGBACapability.field.AutoBA = FALSE;
12492 + }
12493 +#endif // DOT11_N_SUPPORT //
12494 + // Set AdhocMode rates
12495 + if (pAd->StaCfg.BssType == BSS_ADHOC)
12496 + {
12497 + MlmeUpdateTxRates(pAd, FALSE, 0);
12498 + MakeIbssBeacon(pAd); // re-build BEACON frame
12499 + AsicEnableIbssSync(pAd); // copy to on-chip memory
12500 + }
12501 + }
12502 + else
12503 + {
12504 + success = FALSE;
12505 + }
12506 + }
12507 +#endif // CONFIG_STA_SUPPORT //
12508 +
12509 + // it is needed to set SSID to take effect
12510 + if (success == TRUE)
12511 + {
12512 +#ifdef DOT11_N_SUPPORT
12513 + SetCommonHT(pAd);
12514 +#endif // DOT11_N_SUPPORT //
12515 + DBGPRINT(RT_DEBUG_TRACE, ("Set_WirelessMode_Proc::(=%ld)\n", WirelessMode));
12516 + }
12517 + else
12518 + {
12519 + DBGPRINT(RT_DEBUG_ERROR, ("Set_WirelessMode_Proc::parameters out of range\n"));
12520 + }
12521 +
12522 + return success;
12523 +}
12524 +
12525 +/*
12526 + ==========================================================================
12527 + Description:
12528 + Set Channel
12529 + Return:
12530 + TRUE if all parameters are OK, FALSE otherwise
12531 + ==========================================================================
12532 +*/
12533 +INT Set_Channel_Proc(
12534 + IN PRTMP_ADAPTER pAd,
12535 + IN PUCHAR arg)
12536 +{
12537 + INT success = TRUE;
12538 + UCHAR Channel;
12539 +
12540 + Channel = (UCHAR) simple_strtol(arg, 0, 10);
12541 +
12542 + // check if this channel is valid
12543 + if (ChannelSanity(pAd, Channel) == TRUE)
12544 + {
12545 +#ifdef CONFIG_STA_SUPPORT
12546 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12547 + {
12548 + pAd->CommonCfg.Channel = Channel;
12549 +
12550 + if (MONITOR_ON(pAd))
12551 + {
12552 +#ifdef DOT11_N_SUPPORT
12553 + N_ChannelCheck(pAd);
12554 + if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED &&
12555 + pAd->CommonCfg.RegTransmitSetting.field.BW == BW_40)
12556 + {
12557 + N_SetCenCh(pAd);
12558 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
12559 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
12560 + DBGPRINT(RT_DEBUG_TRACE, ("BW_40, control_channel(%d), CentralChannel(%d) \n",
12561 + pAd->CommonCfg.Channel, pAd->CommonCfg.CentralChannel));
12562 + }
12563 + else
12564 +#endif // DOT11_N_SUPPORT //
12565 + {
12566 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
12567 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
12568 + DBGPRINT(RT_DEBUG_TRACE, ("BW_20, Channel(%d)\n", pAd->CommonCfg.Channel));
12569 + }
12570 + }
12571 + }
12572 +#endif // CONFIG_STA_SUPPORT //
12573 + success = TRUE;
12574 + }
12575 + else
12576 + {
12577 +
12578 +#ifdef CONFIG_STA_SUPPORT
12579 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12580 + success = FALSE;
12581 +#endif // CONFIG_STA_SUPPORT //
12582 + }
12583 +
12584 +
12585 + if (success == TRUE)
12586 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Channel_Proc::(Channel=%d)\n", pAd->CommonCfg.Channel));
12587 +
12588 + return success;
12589 +}
12590 +
12591 +/*
12592 + ==========================================================================
12593 + Description:
12594 + Set Short Slot Time Enable or Disable
12595 + Return:
12596 + TRUE if all parameters are OK, FALSE otherwise
12597 + ==========================================================================
12598 +*/
12599 +INT Set_ShortSlot_Proc(
12600 + IN PRTMP_ADAPTER pAd,
12601 + IN PUCHAR arg)
12602 +{
12603 + ULONG ShortSlot;
12604 +
12605 + ShortSlot = simple_strtol(arg, 0, 10);
12606 +
12607 + if (ShortSlot == 1)
12608 + pAd->CommonCfg.bUseShortSlotTime = TRUE;
12609 + else if (ShortSlot == 0)
12610 + pAd->CommonCfg.bUseShortSlotTime = FALSE;
12611 + else
12612 + return FALSE; //Invalid argument
12613 +
12614 + DBGPRINT(RT_DEBUG_TRACE, ("Set_ShortSlot_Proc::(ShortSlot=%d)\n", pAd->CommonCfg.bUseShortSlotTime));
12615 +
12616 + return TRUE;
12617 +}
12618 +
12619 +/*
12620 + ==========================================================================
12621 + Description:
12622 + Set Tx power
12623 + Return:
12624 + TRUE if all parameters are OK, FALSE otherwise
12625 + ==========================================================================
12626 +*/
12627 +INT Set_TxPower_Proc(
12628 + IN PRTMP_ADAPTER pAd,
12629 + IN PUCHAR arg)
12630 +{
12631 + ULONG TxPower;
12632 + INT success = FALSE;
12633 +
12634 + TxPower = (ULONG) simple_strtol(arg, 0, 10);
12635 + if (TxPower <= 100)
12636 + {
12637 +
12638 +#ifdef CONFIG_STA_SUPPORT
12639 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12640 + {
12641 + pAd->CommonCfg.TxPowerDefault = TxPower;
12642 + pAd->CommonCfg.TxPowerPercentage = pAd->CommonCfg.TxPowerDefault;
12643 + }
12644 +#endif // CONFIG_STA_SUPPORT //
12645 + success = TRUE;
12646 + }
12647 + else
12648 + success = FALSE;
12649 +
12650 + DBGPRINT(RT_DEBUG_TRACE, ("Set_TxPower_Proc::(TxPowerPercentage=%ld)\n", pAd->CommonCfg.TxPowerPercentage));
12651 +
12652 + return success;
12653 +}
12654 +
12655 +/*
12656 + ==========================================================================
12657 + Description:
12658 + Set 11B/11G Protection
12659 + Return:
12660 + TRUE if all parameters are OK, FALSE otherwise
12661 + ==========================================================================
12662 +*/
12663 +INT Set_BGProtection_Proc(
12664 + IN PRTMP_ADAPTER pAd,
12665 + IN PUCHAR arg)
12666 +{
12667 + switch (simple_strtol(arg, 0, 10))
12668 + {
12669 + case 0: //AUTO
12670 + pAd->CommonCfg.UseBGProtection = 0;
12671 + break;
12672 + case 1: //Always On
12673 + pAd->CommonCfg.UseBGProtection = 1;
12674 + break;
12675 + case 2: //Always OFF
12676 + pAd->CommonCfg.UseBGProtection = 2;
12677 + break;
12678 + default: //Invalid argument
12679 + return FALSE;
12680 + }
12681 +
12682 +
12683 + DBGPRINT(RT_DEBUG_TRACE, ("Set_BGProtection_Proc::(BGProtection=%ld)\n", pAd->CommonCfg.UseBGProtection));
12684 +
12685 + return TRUE;
12686 +}
12687 +
12688 +/*
12689 + ==========================================================================
12690 + Description:
12691 + Set TxPreamble
12692 + Return:
12693 + TRUE if all parameters are OK, FALSE otherwise
12694 + ==========================================================================
12695 +*/
12696 +INT Set_TxPreamble_Proc(
12697 + IN PRTMP_ADAPTER pAd,
12698 + IN PUCHAR arg)
12699 +{
12700 + RT_802_11_PREAMBLE Preamble;
12701 +
12702 + Preamble = simple_strtol(arg, 0, 10);
12703 +
12704 +
12705 + switch (Preamble)
12706 + {
12707 + case Rt802_11PreambleShort:
12708 + pAd->CommonCfg.TxPreamble = Preamble;
12709 +#ifdef CONFIG_STA_SUPPORT
12710 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12711 + MlmeSetTxPreamble(pAd, Rt802_11PreambleShort);
12712 +#endif // CONFIG_STA_SUPPORT //
12713 + break;
12714 + case Rt802_11PreambleLong:
12715 +#ifdef CONFIG_STA_SUPPORT
12716 + case Rt802_11PreambleAuto:
12717 + // if user wants AUTO, initialize to LONG here, then change according to AP's
12718 + // capability upon association.
12719 +#endif // CONFIG_STA_SUPPORT //
12720 + pAd->CommonCfg.TxPreamble = Preamble;
12721 +#ifdef CONFIG_STA_SUPPORT
12722 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12723 + MlmeSetTxPreamble(pAd, Rt802_11PreambleLong);
12724 +#endif // CONFIG_STA_SUPPORT //
12725 + break;
12726 + default: //Invalid argument
12727 + return FALSE;
12728 + }
12729 +
12730 + DBGPRINT(RT_DEBUG_TRACE, ("Set_TxPreamble_Proc::(TxPreamble=%ld)\n", pAd->CommonCfg.TxPreamble));
12731 +
12732 + return TRUE;
12733 +}
12734 +
12735 +/*
12736 + ==========================================================================
12737 + Description:
12738 + Set RTS Threshold
12739 + Return:
12740 + TRUE if all parameters are OK, FALSE otherwise
12741 + ==========================================================================
12742 +*/
12743 +INT Set_RTSThreshold_Proc(
12744 + IN PRTMP_ADAPTER pAd,
12745 + IN PUCHAR arg)
12746 +{
12747 + NDIS_802_11_RTS_THRESHOLD RtsThresh;
12748 +
12749 + RtsThresh = simple_strtol(arg, 0, 10);
12750 +
12751 + if((RtsThresh > 0) && (RtsThresh <= MAX_RTS_THRESHOLD))
12752 + pAd->CommonCfg.RtsThreshold = (USHORT)RtsThresh;
12753 +#ifdef CONFIG_STA_SUPPORT
12754 + else if (RtsThresh == 0)
12755 + pAd->CommonCfg.RtsThreshold = MAX_RTS_THRESHOLD;
12756 +#endif // CONFIG_STA_SUPPORT //
12757 + else
12758 + return FALSE; //Invalid argument
12759 +
12760 + DBGPRINT(RT_DEBUG_TRACE, ("Set_RTSThreshold_Proc::(RTSThreshold=%d)\n", pAd->CommonCfg.RtsThreshold));
12761 +
12762 + return TRUE;
12763 +}
12764 +
12765 +/*
12766 + ==========================================================================
12767 + Description:
12768 + Set Fragment Threshold
12769 + Return:
12770 + TRUE if all parameters are OK, FALSE otherwise
12771 + ==========================================================================
12772 +*/
12773 +INT Set_FragThreshold_Proc(
12774 + IN PRTMP_ADAPTER pAd,
12775 + IN PUCHAR arg)
12776 +{
12777 + NDIS_802_11_FRAGMENTATION_THRESHOLD FragThresh;
12778 +
12779 + FragThresh = simple_strtol(arg, 0, 10);
12780 +
12781 + if (FragThresh > MAX_FRAG_THRESHOLD || FragThresh < MIN_FRAG_THRESHOLD)
12782 + {
12783 + //Illegal FragThresh so we set it to default
12784 + pAd->CommonCfg.FragmentThreshold = MAX_FRAG_THRESHOLD;
12785 + }
12786 + else if (FragThresh % 2 == 1)
12787 + {
12788 + // The length of each fragment shall always be an even number of octets, except for the last fragment
12789 + // of an MSDU or MMPDU, which may be either an even or an odd number of octets.
12790 + pAd->CommonCfg.FragmentThreshold = (USHORT)(FragThresh - 1);
12791 + }
12792 + else
12793 + {
12794 + pAd->CommonCfg.FragmentThreshold = (USHORT)FragThresh;
12795 + }
12796 +
12797 +#ifdef CONFIG_STA_SUPPORT
12798 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
12799 + {
12800 + if (pAd->CommonCfg.FragmentThreshold == MAX_FRAG_THRESHOLD)
12801 + pAd->CommonCfg.bUseZeroToDisableFragment = TRUE;
12802 + else
12803 + pAd->CommonCfg.bUseZeroToDisableFragment = FALSE;
12804 + }
12805 +#endif // CONFIG_STA_SUPPORT //
12806 +
12807 + DBGPRINT(RT_DEBUG_TRACE, ("Set_FragThreshold_Proc::(FragThreshold=%d)\n", pAd->CommonCfg.FragmentThreshold));
12808 +
12809 + return TRUE;
12810 +}
12811 +
12812 +/*
12813 + ==========================================================================
12814 + Description:
12815 + Set TxBurst
12816 + Return:
12817 + TRUE if all parameters are OK, FALSE otherwise
12818 + ==========================================================================
12819 +*/
12820 +INT Set_TxBurst_Proc(
12821 + IN PRTMP_ADAPTER pAd,
12822 + IN PUCHAR arg)
12823 +{
12824 + ULONG TxBurst;
12825 +
12826 + TxBurst = simple_strtol(arg, 0, 10);
12827 + if (TxBurst == 1)
12828 + pAd->CommonCfg.bEnableTxBurst = TRUE;
12829 + else if (TxBurst == 0)
12830 + pAd->CommonCfg.bEnableTxBurst = FALSE;
12831 + else
12832 + return FALSE; //Invalid argument
12833 +
12834 + DBGPRINT(RT_DEBUG_TRACE, ("Set_TxBurst_Proc::(TxBurst=%d)\n", pAd->CommonCfg.bEnableTxBurst));
12835 +
12836 + return TRUE;
12837 +}
12838 +
12839 +#ifdef AGGREGATION_SUPPORT
12840 +/*
12841 + ==========================================================================
12842 + Description:
12843 + Set TxBurst
12844 + Return:
12845 + TRUE if all parameters are OK, FALSE otherwise
12846 + ==========================================================================
12847 +*/
12848 +INT Set_PktAggregate_Proc(
12849 + IN PRTMP_ADAPTER pAd,
12850 + IN PUCHAR arg)
12851 +{
12852 + ULONG aggre;
12853 +
12854 + aggre = simple_strtol(arg, 0, 10);
12855 +
12856 + if (aggre == 1)
12857 + pAd->CommonCfg.bAggregationCapable = TRUE;
12858 + else if (aggre == 0)
12859 + pAd->CommonCfg.bAggregationCapable = FALSE;
12860 + else
12861 + return FALSE; //Invalid argument
12862 +
12863 +
12864 + DBGPRINT(RT_DEBUG_TRACE, ("Set_PktAggregate_Proc::(AGGRE=%d)\n", pAd->CommonCfg.bAggregationCapable));
12865 +
12866 + return TRUE;
12867 +}
12868 +#endif
12869 +
12870 +/*
12871 + ==========================================================================
12872 + Description:
12873 + Set IEEE80211H.
12874 + This parameter is 1 when needs radar detection, otherwise 0
12875 + Return:
12876 + TRUE if all parameters are OK, FALSE otherwise
12877 + ==========================================================================
12878 +*/
12879 +INT Set_IEEE80211H_Proc(
12880 + IN PRTMP_ADAPTER pAd,
12881 + IN PUCHAR arg)
12882 +{
12883 + ULONG ieee80211h;
12884 +
12885 + ieee80211h = simple_strtol(arg, 0, 10);
12886 +
12887 + if (ieee80211h == 1)
12888 + pAd->CommonCfg.bIEEE80211H = TRUE;
12889 + else if (ieee80211h == 0)
12890 + pAd->CommonCfg.bIEEE80211H = FALSE;
12891 + else
12892 + return FALSE; //Invalid argument
12893 +
12894 + DBGPRINT(RT_DEBUG_TRACE, ("Set_IEEE80211H_Proc::(IEEE80211H=%d)\n", pAd->CommonCfg.bIEEE80211H));
12895 +
12896 + return TRUE;
12897 +}
12898 +
12899 +
12900 +#ifdef DBG
12901 +/*
12902 + ==========================================================================
12903 + Description:
12904 + For Debug information
12905 + Return:
12906 + TRUE if all parameters are OK, FALSE otherwise
12907 + ==========================================================================
12908 +*/
12909 +INT Set_Debug_Proc(
12910 + IN PRTMP_ADAPTER pAd,
12911 + IN PUCHAR arg)
12912 +{
12913 + DBGPRINT(RT_DEBUG_TRACE, ("==> Set_Debug_Proc *******************\n"));
12914 +
12915 + if(simple_strtol(arg, 0, 10) <= RT_DEBUG_LOUD)
12916 + RTDebugLevel = simple_strtol(arg, 0, 10);
12917 +
12918 + DBGPRINT(RT_DEBUG_TRACE, ("<== Set_Debug_Proc(RTDebugLevel = %ld)\n", RTDebugLevel));
12919 +
12920 + return TRUE;
12921 +}
12922 +#endif
12923 +
12924 +INT Show_DescInfo_Proc(
12925 + IN PRTMP_ADAPTER pAd,
12926 + IN PUCHAR arg)
12927 +{
12928 +#ifdef RT2860
12929 + INT i, QueIdx=0;
12930 + PRT28XX_RXD_STRUC pRxD;
12931 + PTXD_STRUC pTxD;
12932 + PRTMP_TX_RING pTxRing = &pAd->TxRing[QueIdx];
12933 + PRTMP_MGMT_RING pMgmtRing = &pAd->MgmtRing;
12934 + PRTMP_RX_RING pRxRing = &pAd->RxRing;
12935 +
12936 + for(i=0;i<TX_RING_SIZE;i++)
12937 + {
12938 + pTxD = (PTXD_STRUC) pTxRing->Cell[i].AllocVa;
12939 + printk("Desc #%d\n",i);
12940 + hex_dump("Tx Descriptor", (char *)pTxD, 16);
12941 + printk("pTxD->DMADONE = %x\n", pTxD->DMADONE);
12942 + }
12943 + printk("---------------------------------------------------\n");
12944 + for(i=0;i<MGMT_RING_SIZE;i++)
12945 + {
12946 + pTxD = (PTXD_STRUC) pMgmtRing->Cell[i].AllocVa;
12947 + printk("Desc #%d\n",i);
12948 + hex_dump("Mgmt Descriptor", (char *)pTxD, 16);
12949 + printk("pMgmt->DMADONE = %x\n", pTxD->DMADONE);
12950 + }
12951 + printk("---------------------------------------------------\n");
12952 + for(i=0;i<RX_RING_SIZE;i++)
12953 + {
12954 + pRxD = (PRT28XX_RXD_STRUC) pRxRing->Cell[i].AllocVa;
12955 + printk("Desc #%d\n",i);
12956 + hex_dump("Rx Descriptor", (char *)pRxD, 16);
12957 + printk("pRxD->DDONE = %x\n", pRxD->DDONE);
12958 + }
12959 +#endif // RT2860 //
12960 +
12961 + return TRUE;
12962 +}
12963 +
12964 +/*
12965 + ==========================================================================
12966 + Description:
12967 + Reset statistics counter
12968 +
12969 + Arguments:
12970 + pAdapter Pointer to our adapter
12971 + arg
12972 +
12973 + Return:
12974 + TRUE if all parameters are OK, FALSE otherwise
12975 + ==========================================================================
12976 +*/
12977 +INT Set_ResetStatCounter_Proc(
12978 + IN PRTMP_ADAPTER pAd,
12979 + IN PUCHAR arg)
12980 +{
12981 + DBGPRINT(RT_DEBUG_TRACE, ("==>Set_ResetStatCounter_Proc\n"));
12982 +
12983 + // add the most up-to-date h/w raw counters into software counters
12984 + NICUpdateRawCounters(pAd);
12985 +
12986 + NdisZeroMemory(&pAd->WlanCounters, sizeof(COUNTER_802_11));
12987 + NdisZeroMemory(&pAd->Counters8023, sizeof(COUNTER_802_3));
12988 + NdisZeroMemory(&pAd->RalinkCounters, sizeof(COUNTER_RALINK));
12989 +
12990 + return TRUE;
12991 +}
12992 +
12993 +BOOLEAN RTMPCheckStrPrintAble(
12994 + IN CHAR *pInPutStr,
12995 + IN UCHAR strLen)
12996 +{
12997 + UCHAR i=0;
12998 +
12999 + for (i=0; i<strLen; i++)
13000 + {
13001 + if ((pInPutStr[i] < 0x21) ||
13002 + (pInPutStr[i] > 0x7E))
13003 + return FALSE;
13004 + }
13005 +
13006 + return TRUE;
13007 +}
13008 +
13009 +/*
13010 + ========================================================================
13011 +
13012 + Routine Description:
13013 + Remove WPA Key process
13014 +
13015 + Arguments:
13016 + pAd Pointer to our adapter
13017 + pBuf Pointer to the where the key stored
13018 +
13019 + Return Value:
13020 + NDIS_SUCCESS Add key successfully
13021 +
13022 + IRQL = DISPATCH_LEVEL
13023 +
13024 + Note:
13025 +
13026 + ========================================================================
13027 +*/
13028 +#ifdef CONFIG_STA_SUPPORT
13029 +VOID RTMPSetDesiredRates(
13030 + IN PRTMP_ADAPTER pAdapter,
13031 + IN LONG Rates)
13032 +{
13033 + NDIS_802_11_RATES aryRates;
13034 +
13035 + memset(&aryRates, 0x00, sizeof(NDIS_802_11_RATES));
13036 + switch (pAdapter->CommonCfg.PhyMode)
13037 + {
13038 + case PHY_11A: // A only
13039 + switch (Rates)
13040 + {
13041 + case 6000000: //6M
13042 + aryRates[0] = 0x0c; // 6M
13043 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_0;
13044 + break;
13045 + case 9000000: //9M
13046 + aryRates[0] = 0x12; // 9M
13047 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_1;
13048 + break;
13049 + case 12000000: //12M
13050 + aryRates[0] = 0x18; // 12M
13051 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_2;
13052 + break;
13053 + case 18000000: //18M
13054 + aryRates[0] = 0x24; // 18M
13055 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_3;
13056 + break;
13057 + case 24000000: //24M
13058 + aryRates[0] = 0x30; // 24M
13059 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_4;
13060 + break;
13061 + case 36000000: //36M
13062 + aryRates[0] = 0x48; // 36M
13063 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_5;
13064 + break;
13065 + case 48000000: //48M
13066 + aryRates[0] = 0x60; // 48M
13067 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_6;
13068 + break;
13069 + case 54000000: //54M
13070 + aryRates[0] = 0x6c; // 54M
13071 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_7;
13072 + break;
13073 + case -1: //Auto
13074 + default:
13075 + aryRates[0] = 0x6c; // 54Mbps
13076 + aryRates[1] = 0x60; // 48Mbps
13077 + aryRates[2] = 0x48; // 36Mbps
13078 + aryRates[3] = 0x30; // 24Mbps
13079 + aryRates[4] = 0x24; // 18M
13080 + aryRates[5] = 0x18; // 12M
13081 + aryRates[6] = 0x12; // 9M
13082 + aryRates[7] = 0x0c; // 6M
13083 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
13084 + break;
13085 + }
13086 + break;
13087 + case PHY_11BG_MIXED: // B/G Mixed
13088 + case PHY_11B: // B only
13089 + case PHY_11ABG_MIXED: // A/B/G Mixed
13090 + default:
13091 + switch (Rates)
13092 + {
13093 + case 1000000: //1M
13094 + aryRates[0] = 0x02;
13095 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_0;
13096 + break;
13097 + case 2000000: //2M
13098 + aryRates[0] = 0x04;
13099 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_1;
13100 + break;
13101 + case 5000000: //5.5M
13102 + aryRates[0] = 0x0b; // 5.5M
13103 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_2;
13104 + break;
13105 + case 11000000: //11M
13106 + aryRates[0] = 0x16; // 11M
13107 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_3;
13108 + break;
13109 + case 6000000: //6M
13110 + aryRates[0] = 0x0c; // 6M
13111 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_0;
13112 + break;
13113 + case 9000000: //9M
13114 + aryRates[0] = 0x12; // 9M
13115 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_1;
13116 + break;
13117 + case 12000000: //12M
13118 + aryRates[0] = 0x18; // 12M
13119 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_2;
13120 + break;
13121 + case 18000000: //18M
13122 + aryRates[0] = 0x24; // 18M
13123 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_3;
13124 + break;
13125 + case 24000000: //24M
13126 + aryRates[0] = 0x30; // 24M
13127 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_4;
13128 + break;
13129 + case 36000000: //36M
13130 + aryRates[0] = 0x48; // 36M
13131 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_5;
13132 + break;
13133 + case 48000000: //48M
13134 + aryRates[0] = 0x60; // 48M
13135 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_6;
13136 + break;
13137 + case 54000000: //54M
13138 + aryRates[0] = 0x6c; // 54M
13139 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_7;
13140 + break;
13141 + case -1: //Auto
13142 + default:
13143 + if (pAdapter->CommonCfg.PhyMode == PHY_11B)
13144 + { //B Only
13145 + aryRates[0] = 0x16; // 11Mbps
13146 + aryRates[1] = 0x0b; // 5.5Mbps
13147 + aryRates[2] = 0x04; // 2Mbps
13148 + aryRates[3] = 0x02; // 1Mbps
13149 + }
13150 + else
13151 + { //(B/G) Mixed or (A/B/G) Mixed
13152 + aryRates[0] = 0x6c; // 54Mbps
13153 + aryRates[1] = 0x60; // 48Mbps
13154 + aryRates[2] = 0x48; // 36Mbps
13155 + aryRates[3] = 0x30; // 24Mbps
13156 + aryRates[4] = 0x16; // 11Mbps
13157 + aryRates[5] = 0x0b; // 5.5Mbps
13158 + aryRates[6] = 0x04; // 2Mbps
13159 + aryRates[7] = 0x02; // 1Mbps
13160 + }
13161 + pAdapter->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
13162 + break;
13163 + }
13164 + break;
13165 + }
13166 +
13167 + NdisZeroMemory(pAdapter->CommonCfg.DesireRate, MAX_LEN_OF_SUPPORTED_RATES);
13168 + NdisMoveMemory(pAdapter->CommonCfg.DesireRate, &aryRates, sizeof(NDIS_802_11_RATES));
13169 + DBGPRINT(RT_DEBUG_TRACE, (" RTMPSetDesiredRates (%02x,%02x,%02x,%02x,%02x,%02x,%02x,%02x)\n",
13170 + pAdapter->CommonCfg.DesireRate[0],pAdapter->CommonCfg.DesireRate[1],
13171 + pAdapter->CommonCfg.DesireRate[2],pAdapter->CommonCfg.DesireRate[3],
13172 + pAdapter->CommonCfg.DesireRate[4],pAdapter->CommonCfg.DesireRate[5],
13173 + pAdapter->CommonCfg.DesireRate[6],pAdapter->CommonCfg.DesireRate[7] ));
13174 + // Changing DesiredRate may affect the MAX TX rate we used to TX frames out
13175 + MlmeUpdateTxRates(pAdapter, FALSE, 0);
13176 +}
13177 +
13178 +NDIS_STATUS RTMPWPARemoveKeyProc(
13179 + IN PRTMP_ADAPTER pAd,
13180 + IN PVOID pBuf)
13181 +{
13182 + PNDIS_802_11_REMOVE_KEY pKey;
13183 + ULONG KeyIdx;
13184 + NDIS_STATUS Status = NDIS_STATUS_FAILURE;
13185 + BOOLEAN bTxKey; // Set the key as transmit key
13186 + BOOLEAN bPairwise; // Indicate the key is pairwise key
13187 + BOOLEAN bKeyRSC; // indicate the receive SC set by KeyRSC value.
13188 + // Otherwise, it will set by the NIC.
13189 + BOOLEAN bAuthenticator; // indicate key is set by authenticator.
13190 + INT i;
13191 +
13192 + DBGPRINT(RT_DEBUG_TRACE,("---> RTMPWPARemoveKeyProc\n"));
13193 +
13194 + pKey = (PNDIS_802_11_REMOVE_KEY) pBuf;
13195 + KeyIdx = pKey->KeyIndex & 0xff;
13196 + // Bit 31 of Add-key, Tx Key
13197 + bTxKey = (pKey->KeyIndex & 0x80000000) ? TRUE : FALSE;
13198 + // Bit 30 of Add-key PairwiseKey
13199 + bPairwise = (pKey->KeyIndex & 0x40000000) ? TRUE : FALSE;
13200 + // Bit 29 of Add-key KeyRSC
13201 + bKeyRSC = (pKey->KeyIndex & 0x20000000) ? TRUE : FALSE;
13202 + // Bit 28 of Add-key Authenticator
13203 + bAuthenticator = (pKey->KeyIndex & 0x10000000) ? TRUE : FALSE;
13204 +
13205 + // 1. If bTx is TRUE, return failure information
13206 + if (bTxKey == TRUE)
13207 + return(NDIS_STATUS_INVALID_DATA);
13208 +
13209 + // 2. Check Pairwise Key
13210 + if (bPairwise)
13211 + {
13212 + // a. If BSSID is broadcast, remove all pairwise keys.
13213 + // b. If not broadcast, remove the pairwise specified by BSSID
13214 + for (i = 0; i < SHARE_KEY_NUM; i++)
13215 + {
13216 + if (MAC_ADDR_EQUAL(pAd->SharedKey[BSS0][i].BssId, pKey->BSSID))
13217 + {
13218 + DBGPRINT(RT_DEBUG_TRACE,("RTMPWPARemoveKeyProc(KeyIdx=%d)\n", i));
13219 + pAd->SharedKey[BSS0][i].KeyLen = 0;
13220 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_NONE;
13221 + AsicRemoveSharedKeyEntry(pAd, BSS0, (UCHAR)i);
13222 + Status = NDIS_STATUS_SUCCESS;
13223 + break;
13224 + }
13225 + }
13226 + }
13227 + // 3. Group Key
13228 + else
13229 + {
13230 + // a. If BSSID is broadcast, remove all group keys indexed
13231 + // b. If BSSID matched, delete the group key indexed.
13232 + DBGPRINT(RT_DEBUG_TRACE,("RTMPWPARemoveKeyProc(KeyIdx=%ld)\n", KeyIdx));
13233 + pAd->SharedKey[BSS0][KeyIdx].KeyLen = 0;
13234 + pAd->SharedKey[BSS0][KeyIdx].CipherAlg = CIPHER_NONE;
13235 + AsicRemoveSharedKeyEntry(pAd, BSS0, (UCHAR)KeyIdx);
13236 + Status = NDIS_STATUS_SUCCESS;
13237 + }
13238 +
13239 + return (Status);
13240 +}
13241 +#endif // CONFIG_STA_SUPPORT //
13242 +
13243 +
13244 +#ifdef CONFIG_STA_SUPPORT
13245 +/*
13246 + ========================================================================
13247 +
13248 + Routine Description:
13249 + Remove All WPA Keys
13250 +
13251 + Arguments:
13252 + pAd Pointer to our adapter
13253 +
13254 + Return Value:
13255 + None
13256 +
13257 + IRQL = DISPATCH_LEVEL
13258 +
13259 + Note:
13260 +
13261 + ========================================================================
13262 +*/
13263 +VOID RTMPWPARemoveAllKeys(
13264 + IN PRTMP_ADAPTER pAd)
13265 +{
13266 +
13267 + UCHAR i;
13268 +
13269 + DBGPRINT(RT_DEBUG_TRACE,("RTMPWPARemoveAllKeys(AuthMode=%d, WepStatus=%d)\n", pAd->StaCfg.AuthMode, pAd->StaCfg.WepStatus));
13270 +
13271 + // For WEP/CKIP, there is no need to remove it, since WinXP won't set it again after
13272 + // Link up. And it will be replaced if user changed it.
13273 + if (pAd->StaCfg.AuthMode < Ndis802_11AuthModeWPA)
13274 + return;
13275 +
13276 + // For WPA-None, there is no need to remove it, since WinXP won't set it again after
13277 + // Link up. And it will be replaced if user changed it.
13278 + if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
13279 + return;
13280 +
13281 + // set BSSID wcid entry of the Pair-wise Key table as no-security mode
13282 + AsicRemovePairwiseKeyEntry(pAd, BSS0, BSSID_WCID);
13283 +
13284 + // set all shared key mode as no-security.
13285 + for (i = 0; i < SHARE_KEY_NUM; i++)
13286 + {
13287 + DBGPRINT(RT_DEBUG_TRACE,("remove %s key #%d\n", CipherName[pAd->SharedKey[BSS0][i].CipherAlg], i));
13288 + NdisZeroMemory(&pAd->SharedKey[BSS0][i], sizeof(CIPHER_KEY));
13289 +
13290 + AsicRemoveSharedKeyEntry(pAd, BSS0, i);
13291 + }
13292 +
13293 +}
13294 +#endif // CONFIG_STA_SUPPORT //
13295 +
13296 +/*
13297 + ========================================================================
13298 + Routine Description:
13299 + Change NIC PHY mode. Re-association may be necessary. possible settings
13300 + include - PHY_11B, PHY_11BG_MIXED, PHY_11A, and PHY_11ABG_MIXED
13301 +
13302 + Arguments:
13303 + pAd - Pointer to our adapter
13304 + phymode -
13305 +
13306 + IRQL = PASSIVE_LEVEL
13307 + IRQL = DISPATCH_LEVEL
13308 +
13309 + ========================================================================
13310 +*/
13311 +VOID RTMPSetPhyMode(
13312 + IN PRTMP_ADAPTER pAd,
13313 + IN ULONG phymode)
13314 +{
13315 + INT i;
13316 + // the selected phymode must be supported by the RF IC encoded in E2PROM
13317 +
13318 + // if no change, do nothing
13319 + /* bug fix
13320 + if (pAd->CommonCfg.PhyMode == phymode)
13321 + return;
13322 + */
13323 + pAd->CommonCfg.PhyMode = (UCHAR)phymode;
13324 +
13325 + DBGPRINT(RT_DEBUG_TRACE,("RTMPSetPhyMode : PhyMode=%d, channel=%d \n", pAd->CommonCfg.PhyMode, pAd->CommonCfg.Channel));
13326 +#ifdef EXT_BUILD_CHANNEL_LIST
13327 + BuildChannelListEx(pAd);
13328 +#else
13329 + BuildChannelList(pAd);
13330 +#endif // EXT_BUILD_CHANNEL_LIST //
13331 +
13332 + // sanity check user setting
13333 + for (i = 0; i < pAd->ChannelListNum; i++)
13334 + {
13335 + if (pAd->CommonCfg.Channel == pAd->ChannelList[i].Channel)
13336 + break;
13337 + }
13338 +
13339 + if (i == pAd->ChannelListNum)
13340 + {
13341 +#ifdef CONFIG_STA_SUPPORT
13342 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
13343 + pAd->CommonCfg.Channel = FirstChannel(pAd);
13344 +#endif // CONFIG_STA_SUPPORT //
13345 + DBGPRINT(RT_DEBUG_ERROR, ("RTMPSetPhyMode: channel is out of range, use first channel=%d \n", pAd->CommonCfg.Channel));
13346 + }
13347 +
13348 + NdisZeroMemory(pAd->CommonCfg.SupRate, MAX_LEN_OF_SUPPORTED_RATES);
13349 + NdisZeroMemory(pAd->CommonCfg.ExtRate, MAX_LEN_OF_SUPPORTED_RATES);
13350 + NdisZeroMemory(pAd->CommonCfg.DesireRate, MAX_LEN_OF_SUPPORTED_RATES);
13351 + switch (phymode) {
13352 + case PHY_11B:
13353 + pAd->CommonCfg.SupRate[0] = 0x82; // 1 mbps, in units of 0.5 Mbps, basic rate
13354 + pAd->CommonCfg.SupRate[1] = 0x84; // 2 mbps, in units of 0.5 Mbps, basic rate
13355 + pAd->CommonCfg.SupRate[2] = 0x8B; // 5.5 mbps, in units of 0.5 Mbps, basic rate
13356 + pAd->CommonCfg.SupRate[3] = 0x96; // 11 mbps, in units of 0.5 Mbps, basic rate
13357 + pAd->CommonCfg.SupRateLen = 4;
13358 + pAd->CommonCfg.ExtRateLen = 0;
13359 + pAd->CommonCfg.DesireRate[0] = 2; // 1 mbps, in units of 0.5 Mbps
13360 + pAd->CommonCfg.DesireRate[1] = 4; // 2 mbps, in units of 0.5 Mbps
13361 + pAd->CommonCfg.DesireRate[2] = 11; // 5.5 mbps, in units of 0.5 Mbps
13362 + pAd->CommonCfg.DesireRate[3] = 22; // 11 mbps, in units of 0.5 Mbps
13363 + //pAd->CommonCfg.HTPhyMode.field.MODE = MODE_CCK; // This MODE is only FYI. not use
13364 + break;
13365 +
13366 + case PHY_11G:
13367 + case PHY_11BG_MIXED:
13368 + case PHY_11ABG_MIXED:
13369 +#ifdef DOT11_N_SUPPORT
13370 + case PHY_11N_2_4G:
13371 + case PHY_11ABGN_MIXED:
13372 + case PHY_11BGN_MIXED:
13373 + case PHY_11GN_MIXED:
13374 +#endif // DOT11_N_SUPPORT //
13375 + pAd->CommonCfg.SupRate[0] = 0x82; // 1 mbps, in units of 0.5 Mbps, basic rate
13376 + pAd->CommonCfg.SupRate[1] = 0x84; // 2 mbps, in units of 0.5 Mbps, basic rate
13377 + pAd->CommonCfg.SupRate[2] = 0x8B; // 5.5 mbps, in units of 0.5 Mbps, basic rate
13378 + pAd->CommonCfg.SupRate[3] = 0x96; // 11 mbps, in units of 0.5 Mbps, basic rate
13379 + pAd->CommonCfg.SupRate[4] = 0x12; // 9 mbps, in units of 0.5 Mbps
13380 + pAd->CommonCfg.SupRate[5] = 0x24; // 18 mbps, in units of 0.5 Mbps
13381 + pAd->CommonCfg.SupRate[6] = 0x48; // 36 mbps, in units of 0.5 Mbps
13382 + pAd->CommonCfg.SupRate[7] = 0x6c; // 54 mbps, in units of 0.5 Mbps
13383 + pAd->CommonCfg.SupRateLen = 8;
13384 + pAd->CommonCfg.ExtRate[0] = 0x0C; // 6 mbps, in units of 0.5 Mbps
13385 + pAd->CommonCfg.ExtRate[1] = 0x18; // 12 mbps, in units of 0.5 Mbps
13386 + pAd->CommonCfg.ExtRate[2] = 0x30; // 24 mbps, in units of 0.5 Mbps
13387 + pAd->CommonCfg.ExtRate[3] = 0x60; // 48 mbps, in units of 0.5 Mbps
13388 + pAd->CommonCfg.ExtRateLen = 4;
13389 + pAd->CommonCfg.DesireRate[0] = 2; // 1 mbps, in units of 0.5 Mbps
13390 + pAd->CommonCfg.DesireRate[1] = 4; // 2 mbps, in units of 0.5 Mbps
13391 + pAd->CommonCfg.DesireRate[2] = 11; // 5.5 mbps, in units of 0.5 Mbps
13392 + pAd->CommonCfg.DesireRate[3] = 22; // 11 mbps, in units of 0.5 Mbps
13393 + pAd->CommonCfg.DesireRate[4] = 12; // 6 mbps, in units of 0.5 Mbps
13394 + pAd->CommonCfg.DesireRate[5] = 18; // 9 mbps, in units of 0.5 Mbps
13395 + pAd->CommonCfg.DesireRate[6] = 24; // 12 mbps, in units of 0.5 Mbps
13396 + pAd->CommonCfg.DesireRate[7] = 36; // 18 mbps, in units of 0.5 Mbps
13397 + pAd->CommonCfg.DesireRate[8] = 48; // 24 mbps, in units of 0.5 Mbps
13398 + pAd->CommonCfg.DesireRate[9] = 72; // 36 mbps, in units of 0.5 Mbps
13399 + pAd->CommonCfg.DesireRate[10] = 96; // 48 mbps, in units of 0.5 Mbps
13400 + pAd->CommonCfg.DesireRate[11] = 108; // 54 mbps, in units of 0.5 Mbps
13401 + break;
13402 +
13403 + case PHY_11A:
13404 +#ifdef DOT11_N_SUPPORT
13405 + case PHY_11AN_MIXED:
13406 + case PHY_11AGN_MIXED:
13407 + case PHY_11N_5G:
13408 +#endif // DOT11_N_SUPPORT //
13409 + pAd->CommonCfg.SupRate[0] = 0x8C; // 6 mbps, in units of 0.5 Mbps, basic rate
13410 + pAd->CommonCfg.SupRate[1] = 0x12; // 9 mbps, in units of 0.5 Mbps
13411 + pAd->CommonCfg.SupRate[2] = 0x98; // 12 mbps, in units of 0.5 Mbps, basic rate
13412 + pAd->CommonCfg.SupRate[3] = 0x24; // 18 mbps, in units of 0.5 Mbps
13413 + pAd->CommonCfg.SupRate[4] = 0xb0; // 24 mbps, in units of 0.5 Mbps, basic rate
13414 + pAd->CommonCfg.SupRate[5] = 0x48; // 36 mbps, in units of 0.5 Mbps
13415 + pAd->CommonCfg.SupRate[6] = 0x60; // 48 mbps, in units of 0.5 Mbps
13416 + pAd->CommonCfg.SupRate[7] = 0x6c; // 54 mbps, in units of 0.5 Mbps
13417 + pAd->CommonCfg.SupRateLen = 8;
13418 + pAd->CommonCfg.ExtRateLen = 0;
13419 + pAd->CommonCfg.DesireRate[0] = 12; // 6 mbps, in units of 0.5 Mbps
13420 + pAd->CommonCfg.DesireRate[1] = 18; // 9 mbps, in units of 0.5 Mbps
13421 + pAd->CommonCfg.DesireRate[2] = 24; // 12 mbps, in units of 0.5 Mbps
13422 + pAd->CommonCfg.DesireRate[3] = 36; // 18 mbps, in units of 0.5 Mbps
13423 + pAd->CommonCfg.DesireRate[4] = 48; // 24 mbps, in units of 0.5 Mbps
13424 + pAd->CommonCfg.DesireRate[5] = 72; // 36 mbps, in units of 0.5 Mbps
13425 + pAd->CommonCfg.DesireRate[6] = 96; // 48 mbps, in units of 0.5 Mbps
13426 + pAd->CommonCfg.DesireRate[7] = 108; // 54 mbps, in units of 0.5 Mbps
13427 + //pAd->CommonCfg.HTPhyMode.field.MODE = MODE_OFDM; // This MODE is only FYI. not use
13428 + break;
13429 +
13430 + default:
13431 + break;
13432 + }
13433 +
13434 +
13435 + pAd->CommonCfg.BandState = UNKNOWN_BAND;
13436 +}
13437 +
13438 +
13439 +#ifdef DOT11_N_SUPPORT
13440 +/*
13441 + ========================================================================
13442 + Routine Description:
13443 + Caller ensures we has 802.11n support.
13444 + Calls at setting HT from AP/STASetinformation
13445 +
13446 + Arguments:
13447 + pAd - Pointer to our adapter
13448 + phymode -
13449 +
13450 + ========================================================================
13451 +*/
13452 +VOID RTMPSetHT(
13453 + IN PRTMP_ADAPTER pAd,
13454 + IN OID_SET_HT_PHYMODE *pHTPhyMode)
13455 +{
13456 + //ULONG *pmcs;
13457 + UINT32 Value = 0;
13458 + UCHAR BBPValue = 0;
13459 + UCHAR BBP3Value = 0;
13460 + UCHAR RxStream = pAd->CommonCfg.RxStream;
13461 +
13462 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetHT : HT_mode(%d), ExtOffset(%d), MCS(%d), BW(%d), STBC(%d), SHORTGI(%d)\n",
13463 + pHTPhyMode->HtMode, pHTPhyMode->ExtOffset,
13464 + pHTPhyMode->MCS, pHTPhyMode->BW,
13465 + pHTPhyMode->STBC, pHTPhyMode->SHORTGI));
13466 +
13467 + // Don't zero supportedHyPhy structure.
13468 + RTMPZeroMemory(&pAd->CommonCfg.HtCapability, sizeof(pAd->CommonCfg.HtCapability));
13469 + RTMPZeroMemory(&pAd->CommonCfg.AddHTInfo, sizeof(pAd->CommonCfg.AddHTInfo));
13470 + RTMPZeroMemory(&pAd->CommonCfg.NewExtChanOffset, sizeof(pAd->CommonCfg.NewExtChanOffset));
13471 + RTMPZeroMemory(&pAd->CommonCfg.DesiredHtPhy, sizeof(pAd->CommonCfg.DesiredHtPhy));
13472 +
13473 + if (pAd->CommonCfg.bRdg)
13474 + {
13475 + pAd->CommonCfg.HtCapability.ExtHtCapInfo.PlusHTC = 1;
13476 + pAd->CommonCfg.HtCapability.ExtHtCapInfo.RDGSupport = 1;
13477 + }
13478 + else
13479 + {
13480 + pAd->CommonCfg.HtCapability.ExtHtCapInfo.PlusHTC = 0;
13481 + pAd->CommonCfg.HtCapability.ExtHtCapInfo.RDGSupport = 0;
13482 + }
13483 +
13484 + pAd->CommonCfg.HtCapability.HtCapParm.MaxRAmpduFactor = 3;
13485 + pAd->CommonCfg.DesiredHtPhy.MaxRAmpduFactor = 3;
13486 +
13487 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetHT : RxBAWinLimit = %d\n", pAd->CommonCfg.BACapability.field.RxBAWinLimit));
13488 +
13489 + // Mimo power save, A-MSDU size,
13490 + pAd->CommonCfg.DesiredHtPhy.AmsduEnable = (USHORT)pAd->CommonCfg.BACapability.field.AmsduEnable;
13491 + pAd->CommonCfg.DesiredHtPhy.AmsduSize = (UCHAR)pAd->CommonCfg.BACapability.field.AmsduSize;
13492 + pAd->CommonCfg.DesiredHtPhy.MimoPs = (UCHAR)pAd->CommonCfg.BACapability.field.MMPSmode;
13493 + pAd->CommonCfg.DesiredHtPhy.MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity;
13494 +
13495 + pAd->CommonCfg.HtCapability.HtCapInfo.AMsduSize = (USHORT)pAd->CommonCfg.BACapability.field.AmsduSize;
13496 + pAd->CommonCfg.HtCapability.HtCapInfo.MimoPs = (USHORT)pAd->CommonCfg.BACapability.field.MMPSmode;
13497 + pAd->CommonCfg.HtCapability.HtCapParm.MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity;
13498 +
13499 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetHT : AMsduSize = %d, MimoPs = %d, MpduDensity = %d, MaxRAmpduFactor = %d\n",
13500 + pAd->CommonCfg.DesiredHtPhy.AmsduSize,
13501 + pAd->CommonCfg.DesiredHtPhy.MimoPs,
13502 + pAd->CommonCfg.DesiredHtPhy.MpduDensity,
13503 + pAd->CommonCfg.DesiredHtPhy.MaxRAmpduFactor));
13504 +
13505 + if(pHTPhyMode->HtMode == HTMODE_GF)
13506 + {
13507 + pAd->CommonCfg.HtCapability.HtCapInfo.GF = 1;
13508 + pAd->CommonCfg.DesiredHtPhy.GF = 1;
13509 + }
13510 + else
13511 + pAd->CommonCfg.DesiredHtPhy.GF = 0;
13512 +
13513 + // Decide Rx MCSSet
13514 + switch (RxStream)
13515 + {
13516 + case 1:
13517 + pAd->CommonCfg.HtCapability.MCSSet[0] = 0xff;
13518 + pAd->CommonCfg.HtCapability.MCSSet[1] = 0x00;
13519 + break;
13520 +
13521 + case 2:
13522 + pAd->CommonCfg.HtCapability.MCSSet[0] = 0xff;
13523 + pAd->CommonCfg.HtCapability.MCSSet[1] = 0xff;
13524 + break;
13525 +
13526 + case 3: // 3*3
13527 + pAd->CommonCfg.HtCapability.MCSSet[0] = 0xff;
13528 + pAd->CommonCfg.HtCapability.MCSSet[1] = 0xff;
13529 + pAd->CommonCfg.HtCapability.MCSSet[2] = 0xff;
13530 + break;
13531 + }
13532 +
13533 + if (pAd->CommonCfg.bForty_Mhz_Intolerant && (pAd->CommonCfg.Channel <= 14) && (pHTPhyMode->BW == BW_40) )
13534 + {
13535 + pHTPhyMode->BW = BW_20;
13536 + pAd->CommonCfg.HtCapability.HtCapInfo.Forty_Mhz_Intolerant = 1;
13537 + }
13538 +
13539 + if(pHTPhyMode->BW == BW_40)
13540 + {
13541 + pAd->CommonCfg.HtCapability.MCSSet[4] = 0x1; // MCS 32
13542 + pAd->CommonCfg.HtCapability.HtCapInfo.ChannelWidth = 1;
13543 + if (pAd->CommonCfg.Channel <= 14)
13544 + pAd->CommonCfg.HtCapability.HtCapInfo.CCKmodein40 = 1;
13545 +
13546 + pAd->CommonCfg.DesiredHtPhy.ChannelWidth = 1;
13547 + pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth = 1;
13548 + pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset = (pHTPhyMode->ExtOffset == EXTCHA_BELOW)? (EXTCHA_BELOW): EXTCHA_ABOVE;
13549 + // Set Regsiter for extension channel position.
13550 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Value);
13551 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BBP3Value);
13552 + if ((pHTPhyMode->ExtOffset == EXTCHA_BELOW))
13553 + {
13554 + Value |= 0x1;
13555 + BBP3Value |= (0x20);
13556 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Value);
13557 + }
13558 + else if ((pHTPhyMode->ExtOffset == EXTCHA_ABOVE))
13559 + {
13560 + Value &= 0xfe;
13561 + BBP3Value &= (~0x20);
13562 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Value);
13563 + }
13564 +
13565 + // Turn on BBP 40MHz mode now only as AP .
13566 + // Sta can turn on BBP 40MHz after connection with 40MHz AP. Sta only broadcast 40MHz capability before connection.
13567 + if ((pAd->OpMode == OPMODE_AP) || INFRA_ON(pAd) || ADHOC_ON(pAd)
13568 + )
13569 + {
13570 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
13571 + BBPValue &= (~0x18);
13572 + BBPValue |= 0x10;
13573 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
13574 +
13575 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BBP3Value);
13576 + pAd->CommonCfg.BBPCurrentBW = BW_40;
13577 + }
13578 + }
13579 + else
13580 + {
13581 + pAd->CommonCfg.HtCapability.HtCapInfo.ChannelWidth = 0;
13582 + pAd->CommonCfg.DesiredHtPhy.ChannelWidth = 0;
13583 + pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth = 0;
13584 + pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset = EXTCHA_NONE;
13585 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel;
13586 + // Turn on BBP 20MHz mode by request here.
13587 + {
13588 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
13589 + BBPValue &= (~0x18);
13590 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
13591 + pAd->CommonCfg.BBPCurrentBW = BW_20;
13592 + }
13593 + }
13594 +
13595 + if(pHTPhyMode->STBC == STBC_USE)
13596 + {
13597 + pAd->CommonCfg.HtCapability.HtCapInfo.TxSTBC = 1;
13598 + pAd->CommonCfg.DesiredHtPhy.TxSTBC = 1;
13599 + pAd->CommonCfg.HtCapability.HtCapInfo.RxSTBC = 1;
13600 + pAd->CommonCfg.DesiredHtPhy.RxSTBC = 1;
13601 + }
13602 + else
13603 + {
13604 + pAd->CommonCfg.DesiredHtPhy.TxSTBC = 0;
13605 + pAd->CommonCfg.DesiredHtPhy.RxSTBC = 0;
13606 + }
13607 +
13608 +
13609 + if(pHTPhyMode->SHORTGI == GI_400)
13610 + {
13611 + pAd->CommonCfg.HtCapability.HtCapInfo.ShortGIfor20 = 1;
13612 + pAd->CommonCfg.HtCapability.HtCapInfo.ShortGIfor40 = 1;
13613 + pAd->CommonCfg.DesiredHtPhy.ShortGIfor20 = 1;
13614 + pAd->CommonCfg.DesiredHtPhy.ShortGIfor40 = 1;
13615 + }
13616 + else
13617 + {
13618 + pAd->CommonCfg.HtCapability.HtCapInfo.ShortGIfor20 = 0;
13619 + pAd->CommonCfg.HtCapability.HtCapInfo.ShortGIfor40 = 0;
13620 + pAd->CommonCfg.DesiredHtPhy.ShortGIfor20 = 0;
13621 + pAd->CommonCfg.DesiredHtPhy.ShortGIfor40 = 0;
13622 + }
13623 +
13624 + // We support link adaptation for unsolicit MCS feedback, set to 2.
13625 + pAd->CommonCfg.HtCapability.ExtHtCapInfo.MCSFeedback = MCSFBK_NONE; //MCSFBK_UNSOLICIT;
13626 + pAd->CommonCfg.AddHTInfo.ControlChan = pAd->CommonCfg.Channel;
13627 + // 1, the extension channel above the control channel.
13628 +
13629 + // EDCA parameters used for AP's own transmission
13630 + if (pAd->CommonCfg.APEdcaParm.bValid == FALSE)
13631 + {
13632 + pAd->CommonCfg.APEdcaParm.bValid = TRUE;
13633 + pAd->CommonCfg.APEdcaParm.Aifsn[0] = 3;
13634 + pAd->CommonCfg.APEdcaParm.Aifsn[1] = 7;
13635 + pAd->CommonCfg.APEdcaParm.Aifsn[2] = 1;
13636 + pAd->CommonCfg.APEdcaParm.Aifsn[3] = 1;
13637 +
13638 + pAd->CommonCfg.APEdcaParm.Cwmin[0] = 4;
13639 + pAd->CommonCfg.APEdcaParm.Cwmin[1] = 4;
13640 + pAd->CommonCfg.APEdcaParm.Cwmin[2] = 3;
13641 + pAd->CommonCfg.APEdcaParm.Cwmin[3] = 2;
13642 +
13643 + pAd->CommonCfg.APEdcaParm.Cwmax[0] = 6;
13644 + pAd->CommonCfg.APEdcaParm.Cwmax[1] = 10;
13645 + pAd->CommonCfg.APEdcaParm.Cwmax[2] = 4;
13646 + pAd->CommonCfg.APEdcaParm.Cwmax[3] = 3;
13647 +
13648 + pAd->CommonCfg.APEdcaParm.Txop[0] = 0;
13649 + pAd->CommonCfg.APEdcaParm.Txop[1] = 0;
13650 + pAd->CommonCfg.APEdcaParm.Txop[2] = 94;
13651 + pAd->CommonCfg.APEdcaParm.Txop[3] = 47;
13652 + }
13653 + AsicSetEdcaParm(pAd, &pAd->CommonCfg.APEdcaParm);
13654 +
13655 +
13656 +#ifdef CONFIG_STA_SUPPORT
13657 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
13658 + {
13659 + RTMPSetIndividualHT(pAd, 0);
13660 + }
13661 +#endif // CONFIG_STA_SUPPORT //
13662 +
13663 +}
13664 +
13665 +/*
13666 + ========================================================================
13667 + Routine Description:
13668 + Caller ensures we has 802.11n support.
13669 + Calls at setting HT from AP/STASetinformation
13670 +
13671 + Arguments:
13672 + pAd - Pointer to our adapter
13673 + phymode -
13674 +
13675 + ========================================================================
13676 +*/
13677 +VOID RTMPSetIndividualHT(
13678 + IN PRTMP_ADAPTER pAd,
13679 + IN UCHAR apidx)
13680 +{
13681 + PRT_HT_PHY_INFO pDesired_ht_phy = NULL;
13682 + UCHAR TxStream = pAd->CommonCfg.TxStream;
13683 + UCHAR DesiredMcs = MCS_AUTO;
13684 +
13685 + do
13686 + {
13687 +
13688 +#ifdef CONFIG_STA_SUPPORT
13689 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
13690 + {
13691 + pDesired_ht_phy = &pAd->StaCfg.DesiredHtPhyInfo;
13692 + DesiredMcs = pAd->StaCfg.DesiredTransmitSetting.field.MCS;
13693 + //pAd->StaCfg.bAutoTxRateSwitch = (DesiredMcs == MCS_AUTO) ? TRUE : FALSE;
13694 + break;
13695 + }
13696 +#endif // CONFIG_STA_SUPPORT //
13697 + } while (FALSE);
13698 +
13699 + if (pDesired_ht_phy == NULL)
13700 + {
13701 + DBGPRINT(RT_DEBUG_ERROR, ("RTMPSetIndividualHT: invalid apidx(%d)\n", apidx));
13702 + return;
13703 + }
13704 + RTMPZeroMemory(pDesired_ht_phy, sizeof(RT_HT_PHY_INFO));
13705 +
13706 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetIndividualHT : Desired MCS = %d\n", DesiredMcs));
13707 + // Check the validity of MCS
13708 + if ((TxStream == 1) && ((DesiredMcs >= MCS_8) && (DesiredMcs <= MCS_15)))
13709 + {
13710 + DBGPRINT(RT_DEBUG_WARN, ("RTMPSetIndividualHT: MCS(%d) is invalid in 1S, reset it as MCS_7\n", DesiredMcs));
13711 + DesiredMcs = MCS_7;
13712 + }
13713 +
13714 + if ((pAd->CommonCfg.DesiredHtPhy.ChannelWidth == BW_20) && (DesiredMcs == MCS_32))
13715 + {
13716 + DBGPRINT(RT_DEBUG_WARN, ("RTMPSetIndividualHT: MCS_32 is only supported in 40-MHz, reset it as MCS_0\n"));
13717 + DesiredMcs = MCS_0;
13718 + }
13719 +
13720 + pDesired_ht_phy->bHtEnable = TRUE;
13721 +
13722 + // Decide desired Tx MCS
13723 + switch (TxStream)
13724 + {
13725 + case 1:
13726 + if (DesiredMcs == MCS_AUTO)
13727 + {
13728 + pDesired_ht_phy->MCSSet[0]= 0xff;
13729 + pDesired_ht_phy->MCSSet[1]= 0x00;
13730 + }
13731 + else if (DesiredMcs <= MCS_7)
13732 + {
13733 + pDesired_ht_phy->MCSSet[0]= 1<<DesiredMcs;
13734 + pDesired_ht_phy->MCSSet[1]= 0x00;
13735 + }
13736 + break;
13737 +
13738 + case 2:
13739 + if (DesiredMcs == MCS_AUTO)
13740 + {
13741 + pDesired_ht_phy->MCSSet[0]= 0xff;
13742 + pDesired_ht_phy->MCSSet[1]= 0xff;
13743 + }
13744 + else if (DesiredMcs <= MCS_15)
13745 + {
13746 + ULONG mode;
13747 +
13748 + mode = DesiredMcs / 8;
13749 + if (mode < 2)
13750 + pDesired_ht_phy->MCSSet[mode] = (1 << (DesiredMcs - mode * 8));
13751 + }
13752 + break;
13753 +
13754 + case 3: // 3*3
13755 + if (DesiredMcs == MCS_AUTO)
13756 + {
13757 + /* MCS0 ~ MCS23, 3 bytes */
13758 + pDesired_ht_phy->MCSSet[0]= 0xff;
13759 + pDesired_ht_phy->MCSSet[1]= 0xff;
13760 + pDesired_ht_phy->MCSSet[2]= 0xff;
13761 + }
13762 + else if (DesiredMcs <= MCS_23)
13763 + {
13764 + ULONG mode;
13765 +
13766 + mode = DesiredMcs / 8;
13767 + if (mode < 3)
13768 + pDesired_ht_phy->MCSSet[mode] = (1 << (DesiredMcs - mode * 8));
13769 + }
13770 + break;
13771 + }
13772 +
13773 + if(pAd->CommonCfg.DesiredHtPhy.ChannelWidth == BW_40)
13774 + {
13775 + if (DesiredMcs == MCS_AUTO || DesiredMcs == MCS_32)
13776 + pDesired_ht_phy->MCSSet[4] = 0x1;
13777 + }
13778 +
13779 + // update HT Rate setting
13780 + if (pAd->OpMode == OPMODE_STA)
13781 + MlmeUpdateHtTxRates(pAd, BSS0);
13782 + else
13783 + MlmeUpdateHtTxRates(pAd, apidx);
13784 +}
13785 +
13786 +
13787 +/*
13788 + ========================================================================
13789 + Routine Description:
13790 + Update HT IE from our capability.
13791 +
13792 + Arguments:
13793 + Send all HT IE in beacon/probe rsp/assoc rsp/action frame.
13794 +
13795 +
13796 + ========================================================================
13797 +*/
13798 +VOID RTMPUpdateHTIE(
13799 + IN RT_HT_CAPABILITY *pRtHt,
13800 + IN UCHAR *pMcsSet,
13801 + OUT HT_CAPABILITY_IE *pHtCapability,
13802 + OUT ADD_HT_INFO_IE *pAddHtInfo)
13803 +{
13804 + RTMPZeroMemory(pHtCapability, sizeof(HT_CAPABILITY_IE));
13805 + RTMPZeroMemory(pAddHtInfo, sizeof(ADD_HT_INFO_IE));
13806 +
13807 + pHtCapability->HtCapInfo.ChannelWidth = pRtHt->ChannelWidth;
13808 + pHtCapability->HtCapInfo.MimoPs = pRtHt->MimoPs;
13809 + pHtCapability->HtCapInfo.GF = pRtHt->GF;
13810 + pHtCapability->HtCapInfo.ShortGIfor20 = pRtHt->ShortGIfor20;
13811 + pHtCapability->HtCapInfo.ShortGIfor40 = pRtHt->ShortGIfor40;
13812 + pHtCapability->HtCapInfo.TxSTBC = pRtHt->TxSTBC;
13813 + pHtCapability->HtCapInfo.RxSTBC = pRtHt->RxSTBC;
13814 + pHtCapability->HtCapInfo.AMsduSize = pRtHt->AmsduSize;
13815 + pHtCapability->HtCapParm.MaxRAmpduFactor = pRtHt->MaxRAmpduFactor;
13816 + pHtCapability->HtCapParm.MpduDensity = pRtHt->MpduDensity;
13817 +
13818 + pAddHtInfo->AddHtInfo.ExtChanOffset = pRtHt->ExtChanOffset ;
13819 + pAddHtInfo->AddHtInfo.RecomWidth = pRtHt->RecomWidth;
13820 + pAddHtInfo->AddHtInfo2.OperaionMode = pRtHt->OperaionMode;
13821 + pAddHtInfo->AddHtInfo2.NonGfPresent = pRtHt->NonGfPresent;
13822 + RTMPMoveMemory(pAddHtInfo->MCSSet, /*pRtHt->MCSSet*/pMcsSet, 4); // rt2860 only support MCS max=32, no need to copy all 16 uchar.
13823 +
13824 + DBGPRINT(RT_DEBUG_TRACE,("RTMPUpdateHTIE <== \n"));
13825 +}
13826 +#endif // DOT11_N_SUPPORT //
13827 +
13828 +/*
13829 + ========================================================================
13830 + Description:
13831 + Add Client security information into ASIC WCID table and IVEIV table.
13832 + Return:
13833 + ========================================================================
13834 +*/
13835 +VOID RTMPAddWcidAttributeEntry(
13836 + IN PRTMP_ADAPTER pAd,
13837 + IN UCHAR BssIdx,
13838 + IN UCHAR KeyIdx,
13839 + IN UCHAR CipherAlg,
13840 + IN MAC_TABLE_ENTRY *pEntry)
13841 +{
13842 + UINT32 WCIDAttri = 0;
13843 + USHORT offset;
13844 + UCHAR IVEIV = 0;
13845 + USHORT Wcid = 0;
13846 +
13847 + {
13848 +#ifdef CONFIG_STA_SUPPORT
13849 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
13850 + {
13851 + if (BssIdx > BSS0)
13852 + {
13853 + DBGPRINT(RT_DEBUG_ERROR, ("RTMPAddWcidAttributeEntry: The BSS-index(%d) is out of range for Infra link. \n", BssIdx));
13854 + return;
13855 + }
13856 +
13857 + // 1. In ADHOC mode, the AID is wcid number. And NO mesh link exists.
13858 + // 2. In Infra mode, the AID:1 MUST be wcid of infra STA.
13859 + // the AID:2~ assign to mesh link entry.
13860 + if (pEntry && ADHOC_ON(pAd))
13861 + Wcid = pEntry->Aid;
13862 + else if (pEntry && INFRA_ON(pAd))
13863 + {
13864 +#ifdef QOS_DLS_SUPPORT
13865 + if (pEntry->ValidAsDls == TRUE)
13866 + Wcid = pEntry->Aid;
13867 + else
13868 +#endif // QOS_DLS_SUPPORT //
13869 + Wcid = BSSID_WCID;
13870 + }
13871 + else
13872 + Wcid = MCAST_WCID;
13873 + }
13874 +#endif // CONFIG_STA_SUPPORT //
13875 + }
13876 +
13877 + // Update WCID attribute table
13878 + offset = MAC_WCID_ATTRIBUTE_BASE + (Wcid * HW_WCID_ATTRI_SIZE);
13879 +
13880 +#ifdef CONFIG_STA_SUPPORT
13881 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
13882 + {
13883 + if (pEntry && pEntry->ValidAsMesh)
13884 + WCIDAttri = (CipherAlg<<1) | PAIRWISEKEYTABLE;
13885 +#ifdef QOS_DLS_SUPPORT
13886 + else if ((pEntry) && (pEntry->ValidAsDls) &&
13887 + ((CipherAlg == CIPHER_TKIP) ||
13888 + (CipherAlg == CIPHER_TKIP_NO_MIC) ||
13889 + (CipherAlg == CIPHER_AES) ||
13890 + (CipherAlg == CIPHER_NONE)))
13891 + WCIDAttri = (CipherAlg<<1) | PAIRWISEKEYTABLE;
13892 +#endif // QOS_DLS_SUPPORT //
13893 + else
13894 + WCIDAttri = (CipherAlg<<1) | SHAREDKEYTABLE;
13895 + }
13896 +#endif // CONFIG_STA_SUPPORT //
13897 +
13898 + RTMP_IO_WRITE32(pAd, offset, WCIDAttri);
13899 +
13900 +
13901 + // Update IV/EIV table
13902 + offset = MAC_IVEIV_TABLE_BASE + (Wcid * HW_IVEIV_ENTRY_SIZE);
13903 +
13904 + // WPA mode
13905 + if ((CipherAlg == CIPHER_TKIP) || (CipherAlg == CIPHER_TKIP_NO_MIC) || (CipherAlg == CIPHER_AES))
13906 + {
13907 + // Eiv bit on. keyid always is 0 for pairwise key
13908 + IVEIV = (KeyIdx <<6) | 0x20;
13909 + }
13910 + else
13911 + {
13912 + // WEP KeyIdx is default tx key.
13913 + IVEIV = (KeyIdx << 6);
13914 + }
13915 +
13916 + // For key index and ext IV bit, so only need to update the position(offset+3).
13917 +#ifdef RT2860
13918 + RTMP_IO_WRITE8(pAd, offset+3, IVEIV);
13919 +#endif // RT2860 //
13920 +
13921 + DBGPRINT(RT_DEBUG_TRACE,("RTMPAddWcidAttributeEntry: WCID #%d, KeyIndex #%d, Alg=%s\n",Wcid, KeyIdx, CipherName[CipherAlg]));
13922 + DBGPRINT(RT_DEBUG_TRACE,(" WCIDAttri = 0x%x \n", WCIDAttri));
13923 +
13924 +}
13925 +
13926 +/*
13927 + ==========================================================================
13928 + Description:
13929 + Parse encryption type
13930 +Arguments:
13931 + pAdapter Pointer to our adapter
13932 + wrq Pointer to the ioctl argument
13933 +
13934 + Return Value:
13935 + None
13936 +
13937 + Note:
13938 + ==========================================================================
13939 +*/
13940 +CHAR *GetEncryptType(CHAR enc)
13941 +{
13942 + if(enc == Ndis802_11WEPDisabled)
13943 + return "NONE";
13944 + if(enc == Ndis802_11WEPEnabled)
13945 + return "WEP";
13946 + if(enc == Ndis802_11Encryption2Enabled)
13947 + return "TKIP";
13948 + if(enc == Ndis802_11Encryption3Enabled)
13949 + return "AES";
13950 + if(enc == Ndis802_11Encryption4Enabled)
13951 + return "TKIPAES";
13952 + else
13953 + return "UNKNOW";
13954 +}
13955 +
13956 +CHAR *GetAuthMode(CHAR auth)
13957 +{
13958 + if(auth == Ndis802_11AuthModeOpen)
13959 + return "OPEN";
13960 + if(auth == Ndis802_11AuthModeShared)
13961 + return "SHARED";
13962 + if(auth == Ndis802_11AuthModeAutoSwitch)
13963 + return "AUTOWEP";
13964 + if(auth == Ndis802_11AuthModeWPA)
13965 + return "WPA";
13966 + if(auth == Ndis802_11AuthModeWPAPSK)
13967 + return "WPAPSK";
13968 + if(auth == Ndis802_11AuthModeWPANone)
13969 + return "WPANONE";
13970 + if(auth == Ndis802_11AuthModeWPA2)
13971 + return "WPA2";
13972 + if(auth == Ndis802_11AuthModeWPA2PSK)
13973 + return "WPA2PSK";
13974 + if(auth == Ndis802_11AuthModeWPA1WPA2)
13975 + return "WPA1WPA2";
13976 + if(auth == Ndis802_11AuthModeWPA1PSKWPA2PSK)
13977 + return "WPA1PSKWPA2PSK";
13978 +
13979 + return "UNKNOW";
13980 +}
13981 +
13982 +#if 1 //#ifndef UCOS
13983 +/*
13984 + ==========================================================================
13985 + Description:
13986 + Get site survey results
13987 + Arguments:
13988 + pAdapter Pointer to our adapter
13989 + wrq Pointer to the ioctl argument
13990 +
13991 + Return Value:
13992 + None
13993 +
13994 + Note:
13995 + Usage:
13996 + 1.) UI needs to wait 4 seconds after issue a site survey command
13997 + 2.) iwpriv ra0 get_site_survey
13998 + 3.) UI needs to prepare at least 4096bytes to get the results
13999 + ==========================================================================
14000 +*/
14001 +#define LINE_LEN (4+33+20+8+10+9+7+3) // Channel+SSID+Bssid+WepStatus+AuthMode+Signal+WiressMode+NetworkType
14002 +VOID RTMPIoctlGetSiteSurvey(
14003 + IN PRTMP_ADAPTER pAdapter,
14004 + IN struct iwreq *wrq)
14005 +{
14006 + CHAR *msg;
14007 + INT i=0;
14008 + INT WaitCnt;
14009 + INT Status=0;
14010 + CHAR Ssid[MAX_LEN_OF_SSID +1];
14011 + INT Rssi = 0, max_len = LINE_LEN;
14012 + UINT Rssi_Quality = 0;
14013 + NDIS_802_11_NETWORK_TYPE wireless_mode;
14014 +
14015 + os_alloc_mem(NULL, (PUCHAR *)&msg, sizeof(CHAR)*((MAX_LEN_OF_BSS_TABLE)*max_len));
14016 +
14017 + if (msg == NULL)
14018 + {
14019 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPIoctlGetSiteSurvey - msg memory alloc fail.\n"));
14020 + return;
14021 + }
14022 +
14023 + memset(msg, 0 ,(MAX_LEN_OF_BSS_TABLE)*max_len );
14024 + memset(Ssid, 0 ,(MAX_LEN_OF_SSID +1));
14025 + sprintf(msg,"%s","\n");
14026 + sprintf(msg+strlen(msg),"%-4s%-33s%-20s%-8s%-10s%-9s%-7s%-3s\n",
14027 + "Ch", "SSID", "BSSID", "Enc", "Auth", "Siganl(%)", "W-Mode", " NT");
14028 +
14029 + WaitCnt = 0;
14030 +#ifdef CONFIG_STA_SUPPORT
14031 + pAdapter->StaCfg.bScanReqIsFromWebUI = TRUE;
14032 + while ((ScanRunning(pAdapter) == TRUE) && (WaitCnt++ < 200))
14033 + OS_WAIT(500);
14034 +#endif // CONFIG_STA_SUPPORT //
14035 +
14036 + for(i=0; i<pAdapter->ScanTab.BssNr ;i++)
14037 + {
14038 + if( pAdapter->ScanTab.BssEntry[i].Channel==0)
14039 + break;
14040 +
14041 + if((strlen(msg)+max_len ) >= IW_SCAN_MAX_DATA)
14042 + break;
14043 +
14044 + //Channel
14045 + sprintf(msg+strlen(msg),"%-4d", pAdapter->ScanTab.BssEntry[i].Channel);
14046 + //SSID
14047 + memcpy(Ssid, pAdapter->ScanTab.BssEntry[i].Ssid, pAdapter->ScanTab.BssEntry[i].SsidLen);
14048 + Ssid[pAdapter->ScanTab.BssEntry[i].SsidLen] = '\0';
14049 + sprintf(msg+strlen(msg),"%-33s", Ssid);
14050 + //BSSID
14051 + sprintf(msg+strlen(msg),"%02x:%02x:%02x:%02x:%02x:%02x ",
14052 + pAdapter->ScanTab.BssEntry[i].Bssid[0],
14053 + pAdapter->ScanTab.BssEntry[i].Bssid[1],
14054 + pAdapter->ScanTab.BssEntry[i].Bssid[2],
14055 + pAdapter->ScanTab.BssEntry[i].Bssid[3],
14056 + pAdapter->ScanTab.BssEntry[i].Bssid[4],
14057 + pAdapter->ScanTab.BssEntry[i].Bssid[5]);
14058 + //Encryption Type
14059 + sprintf(msg+strlen(msg),"%-8s",GetEncryptType(pAdapter->ScanTab.BssEntry[i].WepStatus));
14060 + //Authentication Mode
14061 + if (pAdapter->ScanTab.BssEntry[i].WepStatus == Ndis802_11WEPEnabled)
14062 + sprintf(msg+strlen(msg),"%-10s", "UNKNOW");
14063 + else
14064 + sprintf(msg+strlen(msg),"%-10s",GetAuthMode(pAdapter->ScanTab.BssEntry[i].AuthMode));
14065 + // Rssi
14066 + Rssi = (INT)pAdapter->ScanTab.BssEntry[i].Rssi;
14067 + if (Rssi >= -50)
14068 + Rssi_Quality = 100;
14069 + else if (Rssi >= -80) // between -50 ~ -80dbm
14070 + Rssi_Quality = (UINT)(24 + ((Rssi + 80) * 26)/10);
14071 + else if (Rssi >= -90) // between -80 ~ -90dbm
14072 + Rssi_Quality = (UINT)(((Rssi + 90) * 26)/10);
14073 + else // < -84 dbm
14074 + Rssi_Quality = 0;
14075 + sprintf(msg+strlen(msg),"%-9d", Rssi_Quality);
14076 + // Wireless Mode
14077 + wireless_mode = NetworkTypeInUseSanity(&pAdapter->ScanTab.BssEntry[i]);
14078 + if (wireless_mode == Ndis802_11FH ||
14079 + wireless_mode == Ndis802_11DS)
14080 + sprintf(msg+strlen(msg),"%-7s", "11b");
14081 + else if (wireless_mode == Ndis802_11OFDM5)
14082 + sprintf(msg+strlen(msg),"%-7s", "11a");
14083 + else if (wireless_mode == Ndis802_11OFDM5_N)
14084 + sprintf(msg+strlen(msg),"%-7s", "11a/n");
14085 + else if (wireless_mode == Ndis802_11OFDM24)
14086 + sprintf(msg+strlen(msg),"%-7s", "11b/g");
14087 + else if (wireless_mode == Ndis802_11OFDM24_N)
14088 + sprintf(msg+strlen(msg),"%-7s", "11b/g/n");
14089 + else
14090 + sprintf(msg+strlen(msg),"%-7s", "unknow");
14091 + //Network Type
14092 + if (pAdapter->ScanTab.BssEntry[i].BssType == BSS_ADHOC)
14093 + sprintf(msg+strlen(msg),"%-3s", " Ad");
14094 + else
14095 + sprintf(msg+strlen(msg),"%-3s", " In");
14096 +
14097 + sprintf(msg+strlen(msg),"\n");
14098 + }
14099 +
14100 +#ifdef CONFIG_STA_SUPPORT
14101 + pAdapter->StaCfg.bScanReqIsFromWebUI = FALSE;
14102 +#endif // CONFIG_STA_SUPPORT //
14103 + wrq->u.data.length = strlen(msg);
14104 + Status = copy_to_user(wrq->u.data.pointer, msg, wrq->u.data.length);
14105 +
14106 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPIoctlGetSiteSurvey - wrq->u.data.length = %d\n", wrq->u.data.length));
14107 + os_free_mem(NULL, (PUCHAR)msg);
14108 +}
14109 +
14110 +
14111 +#define MAC_LINE_LEN (14+4+4+10+10+10+6+6) // Addr+aid+psm+datatime+rxbyte+txbyte+current tx rate+last tx rate
14112 +VOID RTMPIoctlGetMacTable(
14113 + IN PRTMP_ADAPTER pAd,
14114 + IN struct iwreq *wrq)
14115 +{
14116 + INT i;
14117 + RT_802_11_MAC_TABLE MacTab;
14118 + char *msg;
14119 +
14120 + MacTab.Num = 0;
14121 + for (i=0; i<MAX_LEN_OF_MAC_TABLE; i++)
14122 + {
14123 + if (pAd->MacTab.Content[i].ValidAsCLI && (pAd->MacTab.Content[i].Sst == SST_ASSOC))
14124 + {
14125 + COPY_MAC_ADDR(MacTab.Entry[MacTab.Num].Addr, &pAd->MacTab.Content[i].Addr);
14126 + MacTab.Entry[MacTab.Num].Aid = (UCHAR)pAd->MacTab.Content[i].Aid;
14127 + MacTab.Entry[MacTab.Num].Psm = pAd->MacTab.Content[i].PsMode;
14128 +#ifdef DOT11_N_SUPPORT
14129 + MacTab.Entry[MacTab.Num].MimoPs = pAd->MacTab.Content[i].MmpsMode;
14130 +#endif // DOT11_N_SUPPORT //
14131 +
14132 + // Fill in RSSI per entry
14133 + MacTab.Entry[MacTab.Num].AvgRssi0 = pAd->MacTab.Content[i].RssiSample.AvgRssi0;
14134 + MacTab.Entry[MacTab.Num].AvgRssi1 = pAd->MacTab.Content[i].RssiSample.AvgRssi1;
14135 + MacTab.Entry[MacTab.Num].AvgRssi2 = pAd->MacTab.Content[i].RssiSample.AvgRssi2;
14136 +
14137 + // the connected time per entry
14138 + MacTab.Entry[MacTab.Num].ConnectedTime = pAd->MacTab.Content[i].StaConnectTime;
14139 + MacTab.Entry[MacTab.Num].TxRate.field.MCS = pAd->MacTab.Content[i].HTPhyMode.field.MCS;
14140 + MacTab.Entry[MacTab.Num].TxRate.field.BW = pAd->MacTab.Content[i].HTPhyMode.field.BW;
14141 + MacTab.Entry[MacTab.Num].TxRate.field.ShortGI = pAd->MacTab.Content[i].HTPhyMode.field.ShortGI;
14142 + MacTab.Entry[MacTab.Num].TxRate.field.STBC = pAd->MacTab.Content[i].HTPhyMode.field.STBC;
14143 + MacTab.Entry[MacTab.Num].TxRate.field.rsv = pAd->MacTab.Content[i].HTPhyMode.field.rsv;
14144 + MacTab.Entry[MacTab.Num].TxRate.field.MODE = pAd->MacTab.Content[i].HTPhyMode.field.MODE;
14145 + MacTab.Entry[MacTab.Num].TxRate.word = pAd->MacTab.Content[i].HTPhyMode.word;
14146 +
14147 + MacTab.Num += 1;
14148 + }
14149 + }
14150 + wrq->u.data.length = sizeof(RT_802_11_MAC_TABLE);
14151 + if (copy_to_user(wrq->u.data.pointer, &MacTab, wrq->u.data.length))
14152 + {
14153 + DBGPRINT(RT_DEBUG_TRACE, ("%s: copy_to_user() fail\n", __FUNCTION__));
14154 + }
14155 +
14156 + msg = (CHAR *) kmalloc(sizeof(CHAR)*(MAX_LEN_OF_MAC_TABLE*MAC_LINE_LEN), MEM_ALLOC_FLAG);
14157 + memset(msg, 0 ,MAX_LEN_OF_MAC_TABLE*MAC_LINE_LEN );
14158 + sprintf(msg,"%s","\n");
14159 + sprintf(msg+strlen(msg),"%-14s%-4s%-4s%-10s%-10s%-10s%-6s%-6s\n",
14160 + "MAC", "AID", "PSM", "LDT", "RxB", "TxB","CTxR", "LTxR");
14161 +
14162 + for (i=0; i<MAX_LEN_OF_MAC_TABLE; i++)
14163 + {
14164 + PMAC_TABLE_ENTRY pEntry = &pAd->MacTab.Content[i];
14165 + if (pEntry->ValidAsCLI && (pEntry->Sst == SST_ASSOC))
14166 + {
14167 + if((strlen(msg)+MAC_LINE_LEN ) >= (MAX_LEN_OF_MAC_TABLE*MAC_LINE_LEN) )
14168 + break;
14169 + sprintf(msg+strlen(msg),"%02x%02x%02x%02x%02x%02x ",
14170 + pEntry->Addr[0], pEntry->Addr[1], pEntry->Addr[2],
14171 + pEntry->Addr[3], pEntry->Addr[4], pEntry->Addr[5]);
14172 + sprintf(msg+strlen(msg),"%-4d", (int)pEntry->Aid);
14173 + sprintf(msg+strlen(msg),"%-4d", (int)pEntry->PsMode);
14174 + sprintf(msg+strlen(msg),"%-10d",0/*pAd->MacTab.Content[i].HSCounter.LastDataPacketTime*/); // ToDo
14175 + sprintf(msg+strlen(msg),"%-10d",0/*pAd->MacTab.Content[i].HSCounter.TotalRxByteCount*/); // ToDo
14176 + sprintf(msg+strlen(msg),"%-10d",0/*pAd->MacTab.Content[i].HSCounter.TotalTxByteCount*/); // ToDo
14177 + sprintf(msg+strlen(msg),"%-6d",RateIdToMbps[pAd->MacTab.Content[i].CurrTxRate]);
14178 + sprintf(msg+strlen(msg),"%-6d\n",0/*RateIdToMbps[pAd->MacTab.Content[i].LastTxRate]*/); // ToDo
14179 + }
14180 + }
14181 + // for compatible with old API just do the printk to console
14182 + //wrq->u.data.length = strlen(msg);
14183 + //if (copy_to_user(wrq->u.data.pointer, msg, wrq->u.data.length))
14184 + {
14185 + DBGPRINT(RT_DEBUG_TRACE, ("%s", msg));
14186 + }
14187 +
14188 + kfree(msg);
14189 +}
14190 +#endif // UCOS //
14191 +
14192 +#ifdef DOT11_N_SUPPORT
14193 +INT Set_BASetup_Proc(
14194 + IN PRTMP_ADAPTER pAd,
14195 + IN PUCHAR arg)
14196 +{
14197 + UCHAR mac[6], tid;
14198 + char *token, sepValue[] = ":", DASH = '-';
14199 + INT i;
14200 + MAC_TABLE_ENTRY *pEntry;
14201 +
14202 +/*
14203 + The BASetup inupt string format should be xx:xx:xx:xx:xx:xx-d,
14204 + =>The six 2 digit hex-decimal number previous are the Mac address,
14205 + =>The seventh decimal number is the tid value.
14206 +*/
14207 + //printk("\n%s\n", arg);
14208 +
14209 + if(strlen(arg) < 19) //Mac address acceptable format 01:02:03:04:05:06 length 17 plus the "-" and tid value in decimal format.
14210 + return FALSE;
14211 +
14212 + token = strchr(arg, DASH);
14213 + if ((token != NULL) && (strlen(token)>1))
14214 + {
14215 + tid = simple_strtol((token+1), 0, 10);
14216 + if (tid > 15)
14217 + return FALSE;
14218 +
14219 + *token = '\0';
14220 + for (i = 0, token = rstrtok(arg, &sepValue[0]); token; token = rstrtok(NULL, &sepValue[0]), i++)
14221 + {
14222 + if((strlen(token) != 2) || (!isxdigit(*token)) || (!isxdigit(*(token+1))))
14223 + return FALSE;
14224 + AtoH(token, (PUCHAR)(&mac[i]), 1);
14225 + }
14226 + if(i != 6)
14227 + return FALSE;
14228 +
14229 + printk("\n%02x:%02x:%02x:%02x:%02x:%02x-%02x\n", mac[0], mac[1],
14230 + mac[2], mac[3], mac[4], mac[5], tid);
14231 +
14232 + pEntry = MacTableLookup(pAd, mac);
14233 +
14234 + if (pEntry) {
14235 + printk("\nSetup BA Session: Tid = %d\n", tid);
14236 + BAOriSessionSetUp(pAd, pEntry, tid, 0, 100, TRUE);
14237 + }
14238 +
14239 + return TRUE;
14240 + }
14241 +
14242 + return FALSE;
14243 +
14244 +}
14245 +
14246 +INT Set_BADecline_Proc(
14247 + IN PRTMP_ADAPTER pAd,
14248 + IN PUCHAR arg)
14249 +{
14250 + ULONG bBADecline;
14251 +
14252 + bBADecline = simple_strtol(arg, 0, 10);
14253 +
14254 + if (bBADecline == 0)
14255 + {
14256 + pAd->CommonCfg.bBADecline = FALSE;
14257 + }
14258 + else if (bBADecline == 1)
14259 + {
14260 + pAd->CommonCfg.bBADecline = TRUE;
14261 + }
14262 + else
14263 + {
14264 + return FALSE; //Invalid argument
14265 + }
14266 +
14267 + DBGPRINT(RT_DEBUG_TRACE, ("Set_BADecline_Proc::(BADecline=%d)\n", pAd->CommonCfg.bBADecline));
14268 +
14269 + return TRUE;
14270 +}
14271 +
14272 +INT Set_BAOriTearDown_Proc(
14273 + IN PRTMP_ADAPTER pAd,
14274 + IN PUCHAR arg)
14275 +{
14276 + UCHAR mac[6], tid;
14277 + char *token, sepValue[] = ":", DASH = '-';
14278 + INT i;
14279 + MAC_TABLE_ENTRY *pEntry;
14280 +
14281 +/*
14282 + The BAOriTearDown inupt string format should be xx:xx:xx:xx:xx:xx-d,
14283 + =>The six 2 digit hex-decimal number previous are the Mac address,
14284 + =>The seventh decimal number is the tid value.
14285 +*/
14286 + if(strlen(arg) < 19) //Mac address acceptable format 01:02:03:04:05:06 length 17 plus the "-" and tid value in decimal format.
14287 + return FALSE;
14288 +
14289 + token = strchr(arg, DASH);
14290 + if ((token != NULL) && (strlen(token)>1))
14291 + {
14292 + tid = simple_strtol((token+1), 0, 10);
14293 + if (tid > NUM_OF_TID)
14294 + return FALSE;
14295 +
14296 + *token = '\0';
14297 + for (i = 0, token = rstrtok(arg, &sepValue[0]); token; token = rstrtok(NULL, &sepValue[0]), i++)
14298 + {
14299 + if((strlen(token) != 2) || (!isxdigit(*token)) || (!isxdigit(*(token+1))))
14300 + return FALSE;
14301 + AtoH(token, (PUCHAR)(&mac[i]), 1);
14302 + }
14303 + if(i != 6)
14304 + return FALSE;
14305 +
14306 + printk("\n%02x:%02x:%02x:%02x:%02x:%02x-%02x", mac[0], mac[1],
14307 + mac[2], mac[3], mac[4], mac[5], tid);
14308 +
14309 + pEntry = MacTableLookup(pAd, mac);
14310 +
14311 + if (pEntry) {
14312 + printk("\nTear down Ori BA Session: Tid = %d\n", tid);
14313 + BAOriSessionTearDown(pAd, pEntry->Aid, tid, FALSE, TRUE);
14314 + }
14315 +
14316 + return TRUE;
14317 + }
14318 +
14319 + return FALSE;
14320 +
14321 +}
14322 +
14323 +INT Set_BARecTearDown_Proc(
14324 + IN PRTMP_ADAPTER pAd,
14325 + IN PUCHAR arg)
14326 +{
14327 + UCHAR mac[6], tid;
14328 + char *token, sepValue[] = ":", DASH = '-';
14329 + INT i;
14330 + MAC_TABLE_ENTRY *pEntry;
14331 +
14332 + //printk("\n%s\n", arg);
14333 +/*
14334 + The BARecTearDown inupt string format should be xx:xx:xx:xx:xx:xx-d,
14335 + =>The six 2 digit hex-decimal number previous are the Mac address,
14336 + =>The seventh decimal number is the tid value.
14337 +*/
14338 + if(strlen(arg) < 19) //Mac address acceptable format 01:02:03:04:05:06 length 17 plus the "-" and tid value in decimal format.
14339 + return FALSE;
14340 +
14341 + token = strchr(arg, DASH);
14342 + if ((token != NULL) && (strlen(token)>1))
14343 + {
14344 + tid = simple_strtol((token+1), 0, 10);
14345 + if (tid > NUM_OF_TID)
14346 + return FALSE;
14347 +
14348 + *token = '\0';
14349 + for (i = 0, token = rstrtok(arg, &sepValue[0]); token; token = rstrtok(NULL, &sepValue[0]), i++)
14350 + {
14351 + if((strlen(token) != 2) || (!isxdigit(*token)) || (!isxdigit(*(token+1))))
14352 + return FALSE;
14353 + AtoH(token, (PUCHAR)(&mac[i]), 1);
14354 + }
14355 + if(i != 6)
14356 + return FALSE;
14357 +
14358 + printk("\n%02x:%02x:%02x:%02x:%02x:%02x-%02x", mac[0], mac[1],
14359 + mac[2], mac[3], mac[4], mac[5], tid);
14360 +
14361 + pEntry = MacTableLookup(pAd, mac);
14362 +
14363 + if (pEntry) {
14364 + printk("\nTear down Rec BA Session: Tid = %d\n", tid);
14365 + BARecSessionTearDown(pAd, pEntry->Aid, tid, FALSE);
14366 + }
14367 +
14368 + return TRUE;
14369 + }
14370 +
14371 + return FALSE;
14372 +
14373 +}
14374 +
14375 +INT Set_HtBw_Proc(
14376 + IN PRTMP_ADAPTER pAd,
14377 + IN PUCHAR arg)
14378 +{
14379 + ULONG HtBw;
14380 +
14381 + HtBw = simple_strtol(arg, 0, 10);
14382 + if (HtBw == BW_40)
14383 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_40;
14384 + else if (HtBw == BW_20)
14385 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
14386 + else
14387 + return FALSE; //Invalid argument
14388 +
14389 + SetCommonHT(pAd);
14390 +
14391 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtBw_Proc::(HtBw=%d)\n", pAd->CommonCfg.RegTransmitSetting.field.BW));
14392 +
14393 + return TRUE;
14394 +}
14395 +
14396 +INT Set_HtMcs_Proc(
14397 + IN PRTMP_ADAPTER pAd,
14398 + IN PUCHAR arg)
14399 +{
14400 + ULONG HtMcs, Mcs_tmp;
14401 +#ifdef CONFIG_STA_SUPPORT
14402 + BOOLEAN bAutoRate = FALSE;
14403 +#endif // CONFIG_STA_SUPPORT //
14404 +
14405 + Mcs_tmp = simple_strtol(arg, 0, 10);
14406 +
14407 + if (Mcs_tmp <= 15 || Mcs_tmp == 32)
14408 + HtMcs = Mcs_tmp;
14409 + else
14410 + HtMcs = MCS_AUTO;
14411 +
14412 +#ifdef CONFIG_STA_SUPPORT
14413 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
14414 + {
14415 + pAd->StaCfg.DesiredTransmitSetting.field.MCS = HtMcs;
14416 + pAd->StaCfg.bAutoTxRateSwitch = (HtMcs == MCS_AUTO) ? TRUE:FALSE;
14417 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtMcs_Proc::(HtMcs=%d, bAutoTxRateSwitch = %d)\n",
14418 + pAd->StaCfg.DesiredTransmitSetting.field.MCS, pAd->StaCfg.bAutoTxRateSwitch));
14419 +
14420 + if ((pAd->CommonCfg.PhyMode < PHY_11ABGN_MIXED) ||
14421 + (pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE < MODE_HTMIX))
14422 + {
14423 + if ((pAd->StaCfg.DesiredTransmitSetting.field.MCS != MCS_AUTO) &&
14424 + (HtMcs >= 0 && HtMcs <= 3) &&
14425 + (pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode == FIXED_TXMODE_CCK))
14426 + {
14427 + RTMPSetDesiredRates(pAd, (LONG) (RateIdToMbps[HtMcs] * 1000000));
14428 + }
14429 + else if ((pAd->StaCfg.DesiredTransmitSetting.field.MCS != MCS_AUTO) &&
14430 + (HtMcs >= 0 && HtMcs <= 7) &&
14431 + (pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode == FIXED_TXMODE_OFDM))
14432 + {
14433 + RTMPSetDesiredRates(pAd, (LONG) (RateIdToMbps[HtMcs+4] * 1000000));
14434 + }
14435 + else
14436 + bAutoRate = TRUE;
14437 +
14438 + if (bAutoRate)
14439 + {
14440 + pAd->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
14441 + RTMPSetDesiredRates(pAd, -1);
14442 + }
14443 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtMcs_Proc::(FixedTxMode=%d)\n",pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode));
14444 + }
14445 + if (ADHOC_ON(pAd))
14446 + return TRUE;
14447 + }
14448 +#endif // CONFIG_STA_SUPPORT //
14449 +
14450 + SetCommonHT(pAd);
14451 +
14452 + return TRUE;
14453 +}
14454 +
14455 +INT Set_HtGi_Proc(
14456 + IN PRTMP_ADAPTER pAd,
14457 + IN PUCHAR arg)
14458 +{
14459 + ULONG HtGi;
14460 +
14461 + HtGi = simple_strtol(arg, 0, 10);
14462 +
14463 + if ( HtGi == GI_400)
14464 + pAd->CommonCfg.RegTransmitSetting.field.ShortGI = GI_400;
14465 + else if ( HtGi == GI_800 )
14466 + pAd->CommonCfg.RegTransmitSetting.field.ShortGI = GI_800;
14467 + else
14468 + return FALSE; //Invalid argument
14469 +
14470 + SetCommonHT(pAd);
14471 +
14472 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtGi_Proc::(ShortGI=%d)\n",pAd->CommonCfg.RegTransmitSetting.field.ShortGI));
14473 +
14474 + return TRUE;
14475 +}
14476 +
14477 +
14478 +INT Set_HtTxBASize_Proc(
14479 + IN PRTMP_ADAPTER pAd,
14480 + IN PUCHAR arg)
14481 +{
14482 + UCHAR Size;
14483 +
14484 + Size = simple_strtol(arg, 0, 10);
14485 +
14486 + if (Size <=0 || Size >=64)
14487 + {
14488 + Size = 8;
14489 + }
14490 + pAd->CommonCfg.TxBASize = Size-1;
14491 + DBGPRINT(RT_DEBUG_ERROR, ("Set_HtTxBASize ::(TxBASize= %d)\n", Size));
14492 +
14493 + return TRUE;
14494 +}
14495 +
14496 +
14497 +INT Set_HtOpMode_Proc(
14498 + IN PRTMP_ADAPTER pAd,
14499 + IN PUCHAR arg)
14500 +{
14501 +
14502 + ULONG Value;
14503 +
14504 + Value = simple_strtol(arg, 0, 10);
14505 +
14506 + if (Value == HTMODE_GF)
14507 + pAd->CommonCfg.RegTransmitSetting.field.HTMODE = HTMODE_GF;
14508 + else if ( Value == HTMODE_MM )
14509 + pAd->CommonCfg.RegTransmitSetting.field.HTMODE = HTMODE_MM;
14510 + else
14511 + return FALSE; //Invalid argument
14512 +
14513 + SetCommonHT(pAd);
14514 +
14515 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtOpMode_Proc::(HtOpMode=%d)\n",pAd->CommonCfg.RegTransmitSetting.field.HTMODE));
14516 +
14517 + return TRUE;
14518 +
14519 +}
14520 +
14521 +INT Set_HtStbc_Proc(
14522 + IN PRTMP_ADAPTER pAd,
14523 + IN PUCHAR arg)
14524 +{
14525 +
14526 + ULONG Value;
14527 +
14528 + Value = simple_strtol(arg, 0, 10);
14529 +
14530 + if (Value == STBC_USE)
14531 + pAd->CommonCfg.RegTransmitSetting.field.STBC = STBC_USE;
14532 + else if ( Value == STBC_NONE )
14533 + pAd->CommonCfg.RegTransmitSetting.field.STBC = STBC_NONE;
14534 + else
14535 + return FALSE; //Invalid argument
14536 +
14537 + SetCommonHT(pAd);
14538 +
14539 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Stbc_Proc::(HtStbc=%d)\n",pAd->CommonCfg.RegTransmitSetting.field.STBC));
14540 +
14541 + return TRUE;
14542 +}
14543 +
14544 +INT Set_HtHtc_Proc(
14545 + IN PRTMP_ADAPTER pAd,
14546 + IN PUCHAR arg)
14547 +{
14548 +
14549 + ULONG Value;
14550 +
14551 + Value = simple_strtol(arg, 0, 10);
14552 + if (Value == 0)
14553 + pAd->HTCEnable = FALSE;
14554 + else if ( Value ==1 )
14555 + pAd->HTCEnable = TRUE;
14556 + else
14557 + return FALSE; //Invalid argument
14558 +
14559 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtHtc_Proc::(HtHtc=%d)\n",pAd->HTCEnable));
14560 +
14561 + return TRUE;
14562 +}
14563 +
14564 +INT Set_HtExtcha_Proc(
14565 + IN PRTMP_ADAPTER pAd,
14566 + IN PUCHAR arg)
14567 +{
14568 +
14569 + ULONG Value;
14570 +
14571 + Value = simple_strtol(arg, 0, 10);
14572 +
14573 + if (Value == 0)
14574 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_BELOW;
14575 + else if ( Value ==1 )
14576 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_ABOVE;
14577 + else
14578 + return FALSE; //Invalid argument
14579 +
14580 + SetCommonHT(pAd);
14581 +
14582 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtExtcha_Proc::(HtExtcha=%d)\n",pAd->CommonCfg.RegTransmitSetting.field.EXTCHA));
14583 +
14584 + return TRUE;
14585 +}
14586 +
14587 +INT Set_HtMpduDensity_Proc(
14588 + IN PRTMP_ADAPTER pAd,
14589 + IN PUCHAR arg)
14590 +{
14591 + ULONG Value;
14592 +
14593 + Value = simple_strtol(arg, 0, 10);
14594 +
14595 + if (Value <=7 && Value >= 0)
14596 + pAd->CommonCfg.BACapability.field.MpduDensity = Value;
14597 + else
14598 + pAd->CommonCfg.BACapability.field.MpduDensity = 4;
14599 +
14600 + SetCommonHT(pAd);
14601 +
14602 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtMpduDensity_Proc::(HtMpduDensity=%d)\n",pAd->CommonCfg.BACapability.field.MpduDensity));
14603 +
14604 + return TRUE;
14605 +}
14606 +
14607 +INT Set_HtBaWinSize_Proc(
14608 + IN PRTMP_ADAPTER pAd,
14609 + IN PUCHAR arg)
14610 +{
14611 + ULONG Value;
14612 +
14613 + Value = simple_strtol(arg, 0, 10);
14614 +
14615 +
14616 + if (Value >=1 && Value <= 64)
14617 + {
14618 + pAd->CommonCfg.REGBACapability.field.RxBAWinLimit = Value;
14619 + pAd->CommonCfg.BACapability.field.RxBAWinLimit = Value;
14620 + }
14621 + else
14622 + {
14623 + pAd->CommonCfg.REGBACapability.field.RxBAWinLimit = 64;
14624 + pAd->CommonCfg.BACapability.field.RxBAWinLimit = 64;
14625 + }
14626 +
14627 + SetCommonHT(pAd);
14628 +
14629 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtBaWinSize_Proc::(HtBaWinSize=%d)\n",pAd->CommonCfg.BACapability.field.RxBAWinLimit));
14630 +
14631 + return TRUE;
14632 +}
14633 +
14634 +INT Set_HtRdg_Proc(
14635 + IN PRTMP_ADAPTER pAd,
14636 + IN PUCHAR arg)
14637 +{
14638 + ULONG Value;
14639 +
14640 + Value = simple_strtol(arg, 0, 10);
14641 +
14642 + if (Value == 0)
14643 + pAd->CommonCfg.bRdg = FALSE;
14644 + else if ( Value ==1 )
14645 + {
14646 + pAd->HTCEnable = TRUE;
14647 + pAd->CommonCfg.bRdg = TRUE;
14648 + }
14649 + else
14650 + return FALSE; //Invalid argument
14651 +
14652 + SetCommonHT(pAd);
14653 +
14654 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtRdg_Proc::(HtRdg=%d)\n",pAd->CommonCfg.bRdg));
14655 +
14656 + return TRUE;
14657 +}
14658 +
14659 +INT Set_HtLinkAdapt_Proc(
14660 + IN PRTMP_ADAPTER pAd,
14661 + IN PUCHAR arg)
14662 +{
14663 + ULONG Value;
14664 +
14665 + Value = simple_strtol(arg, 0, 10);
14666 + if (Value == 0)
14667 + pAd->bLinkAdapt = FALSE;
14668 + else if ( Value ==1 )
14669 + {
14670 + pAd->HTCEnable = TRUE;
14671 + pAd->bLinkAdapt = TRUE;
14672 + }
14673 + else
14674 + return FALSE; //Invalid argument
14675 +
14676 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtLinkAdapt_Proc::(HtLinkAdapt=%d)\n",pAd->bLinkAdapt));
14677 +
14678 + return TRUE;
14679 +}
14680 +
14681 +INT Set_HtAmsdu_Proc(
14682 + IN PRTMP_ADAPTER pAd,
14683 + IN PUCHAR arg)
14684 +{
14685 + ULONG Value;
14686 +
14687 + Value = simple_strtol(arg, 0, 10);
14688 + if (Value == 0)
14689 + pAd->CommonCfg.BACapability.field.AmsduEnable = FALSE;
14690 + else if ( Value == 1 )
14691 + pAd->CommonCfg.BACapability.field.AmsduEnable = TRUE;
14692 + else
14693 + return FALSE; //Invalid argument
14694 +
14695 + SetCommonHT(pAd);
14696 +
14697 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtAmsdu_Proc::(HtAmsdu=%d)\n",pAd->CommonCfg.BACapability.field.AmsduEnable));
14698 +
14699 + return TRUE;
14700 +}
14701 +
14702 +INT Set_HtAutoBa_Proc(
14703 + IN PRTMP_ADAPTER pAd,
14704 + IN PUCHAR arg)
14705 +{
14706 + ULONG Value;
14707 +
14708 + Value = simple_strtol(arg, 0, 10);
14709 + if (Value == 0)
14710 + pAd->CommonCfg.BACapability.field.AutoBA = FALSE;
14711 + else if (Value == 1)
14712 + pAd->CommonCfg.BACapability.field.AutoBA = TRUE;
14713 + else
14714 + return FALSE; //Invalid argument
14715 +
14716 + pAd->CommonCfg.REGBACapability.field.AutoBA = pAd->CommonCfg.BACapability.field.AutoBA;
14717 + SetCommonHT(pAd);
14718 +
14719 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtAutoBa_Proc::(HtAutoBa=%d)\n",pAd->CommonCfg.BACapability.field.AutoBA));
14720 +
14721 + return TRUE;
14722 +
14723 +}
14724 +
14725 +INT Set_HtProtect_Proc(
14726 + IN PRTMP_ADAPTER pAd,
14727 + IN PUCHAR arg)
14728 +{
14729 + ULONG Value;
14730 +
14731 + Value = simple_strtol(arg, 0, 10);
14732 + if (Value == 0)
14733 + pAd->CommonCfg.bHTProtect = FALSE;
14734 + else if (Value == 1)
14735 + pAd->CommonCfg.bHTProtect = TRUE;
14736 + else
14737 + return FALSE; //Invalid argument
14738 +
14739 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtProtect_Proc::(HtProtect=%d)\n",pAd->CommonCfg.bHTProtect));
14740 +
14741 + return TRUE;
14742 +}
14743 +
14744 +INT Set_SendPSMPAction_Proc(
14745 + IN PRTMP_ADAPTER pAd,
14746 + IN PUCHAR arg)
14747 +{
14748 + UCHAR mac[6], mode;
14749 + char *token, sepValue[] = ":", DASH = '-';
14750 + INT i;
14751 + MAC_TABLE_ENTRY *pEntry;
14752 +
14753 + //printk("\n%s\n", arg);
14754 +/*
14755 + The BARecTearDown inupt string format should be xx:xx:xx:xx:xx:xx-d,
14756 + =>The six 2 digit hex-decimal number previous are the Mac address,
14757 + =>The seventh decimal number is the mode value.
14758 +*/
14759 + if(strlen(arg) < 19) //Mac address acceptable format 01:02:03:04:05:06 length 17 plus the "-" and mode value in decimal format.
14760 + return FALSE;
14761 +
14762 + token = strchr(arg, DASH);
14763 + if ((token != NULL) && (strlen(token)>1))
14764 + {
14765 + mode = simple_strtol((token+1), 0, 10);
14766 + if (mode > MMPS_ENABLE)
14767 + return FALSE;
14768 +
14769 + *token = '\0';
14770 + for (i = 0, token = rstrtok(arg, &sepValue[0]); token; token = rstrtok(NULL, &sepValue[0]), i++)
14771 + {
14772 + if((strlen(token) != 2) || (!isxdigit(*token)) || (!isxdigit(*(token+1))))
14773 + return FALSE;
14774 + AtoH(token, (PUCHAR)(&mac[i]), 1);
14775 + }
14776 + if(i != 6)
14777 + return FALSE;
14778 +
14779 + printk("\n%02x:%02x:%02x:%02x:%02x:%02x-%02x", mac[0], mac[1],
14780 + mac[2], mac[3], mac[4], mac[5], mode);
14781 +
14782 + pEntry = MacTableLookup(pAd, mac);
14783 +
14784 + if (pEntry) {
14785 + printk("\nSendPSMPAction MIPS mode = %d\n", mode);
14786 + SendPSMPAction(pAd, pEntry->Aid, mode);
14787 + }
14788 +
14789 + return TRUE;
14790 + }
14791 +
14792 + return FALSE;
14793 +
14794 +
14795 +}
14796 +
14797 +INT Set_HtMIMOPSmode_Proc(
14798 + IN PRTMP_ADAPTER pAd,
14799 + IN PUCHAR arg)
14800 +{
14801 + ULONG Value;
14802 +
14803 + Value = simple_strtol(arg, 0, 10);
14804 +
14805 + if (Value <=3 && Value >= 0)
14806 + pAd->CommonCfg.BACapability.field.MMPSmode = Value;
14807 + else
14808 + pAd->CommonCfg.BACapability.field.MMPSmode = 3;
14809 +
14810 + SetCommonHT(pAd);
14811 +
14812 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtMIMOPSmode_Proc::(MIMOPS mode=%d)\n",pAd->CommonCfg.BACapability.field.MMPSmode));
14813 +
14814 + return TRUE;
14815 +}
14816 +
14817 +
14818 +INT Set_ForceShortGI_Proc(
14819 + IN PRTMP_ADAPTER pAd,
14820 + IN PUCHAR arg)
14821 +{
14822 + ULONG Value;
14823 +
14824 + Value = simple_strtol(arg, 0, 10);
14825 + if (Value == 0)
14826 + pAd->WIFItestbed.bShortGI = FALSE;
14827 + else if (Value == 1)
14828 + pAd->WIFItestbed.bShortGI = TRUE;
14829 + else
14830 + return FALSE; //Invalid argument
14831 +
14832 + SetCommonHT(pAd);
14833 +
14834 + DBGPRINT(RT_DEBUG_TRACE, ("Set_ForceShortGI_Proc::(ForceShortGI=%d)\n", pAd->WIFItestbed.bShortGI));
14835 +
14836 + return TRUE;
14837 +}
14838 +
14839 +
14840 +
14841 +INT Set_ForceGF_Proc(
14842 + IN PRTMP_ADAPTER pAd,
14843 + IN PUCHAR arg)
14844 +{
14845 + ULONG Value;
14846 +
14847 + Value = simple_strtol(arg, 0, 10);
14848 + if (Value == 0)
14849 + pAd->WIFItestbed.bGreenField = FALSE;
14850 + else if (Value == 1)
14851 + pAd->WIFItestbed.bGreenField = TRUE;
14852 + else
14853 + return FALSE; //Invalid argument
14854 +
14855 + SetCommonHT(pAd);
14856 +
14857 + DBGPRINT(RT_DEBUG_TRACE, ("Set_ForceGF_Proc::(ForceGF=%d)\n", pAd->WIFItestbed.bGreenField));
14858 +
14859 + return TRUE;
14860 +}
14861 +
14862 +INT Set_HtMimoPs_Proc(
14863 + IN PRTMP_ADAPTER pAd,
14864 + IN PUCHAR arg)
14865 +{
14866 + ULONG Value;
14867 +
14868 + Value = simple_strtol(arg, 0, 10);
14869 + if (Value == 0)
14870 + pAd->CommonCfg.bMIMOPSEnable = FALSE;
14871 + else if (Value == 1)
14872 + pAd->CommonCfg.bMIMOPSEnable = TRUE;
14873 + else
14874 + return FALSE; //Invalid argument
14875 +
14876 + DBGPRINT(RT_DEBUG_TRACE, ("Set_HtMimoPs_Proc::(HtMimoPs=%d)\n",pAd->CommonCfg.bMIMOPSEnable));
14877 +
14878 + return TRUE;
14879 +}
14880 +#endif // DOT11_N_SUPPORT //
14881 +
14882 +
14883 +#ifdef DOT11_N_SUPPORT
14884 +INT SetCommonHT(
14885 + IN PRTMP_ADAPTER pAd)
14886 +{
14887 + OID_SET_HT_PHYMODE SetHT;
14888 +
14889 + if (pAd->CommonCfg.PhyMode < PHY_11ABGN_MIXED)
14890 + return FALSE;
14891 +
14892 + SetHT.PhyMode = pAd->CommonCfg.PhyMode;
14893 + SetHT.TransmitNo = ((UCHAR)pAd->Antenna.field.TxPath);
14894 + SetHT.HtMode = (UCHAR)pAd->CommonCfg.RegTransmitSetting.field.HTMODE;
14895 + SetHT.ExtOffset = (UCHAR)pAd->CommonCfg.RegTransmitSetting.field.EXTCHA;
14896 + SetHT.MCS = MCS_AUTO;
14897 + SetHT.BW = (UCHAR)pAd->CommonCfg.RegTransmitSetting.field.BW;
14898 + SetHT.STBC = (UCHAR)pAd->CommonCfg.RegTransmitSetting.field.STBC;
14899 + SetHT.SHORTGI = (UCHAR)pAd->CommonCfg.RegTransmitSetting.field.ShortGI;
14900 +
14901 + RTMPSetHT(pAd, &SetHT);
14902 +
14903 + return TRUE;
14904 +}
14905 +#endif // DOT11_N_SUPPORT //
14906 +
14907 +INT Set_FixedTxMode_Proc(
14908 + IN PRTMP_ADAPTER pAd,
14909 + IN PUCHAR arg)
14910 +{
14911 + UCHAR fix_tx_mode = FIXED_TXMODE_HT;
14912 +
14913 + if (strcmp(arg, "OFDM") == 0 || strcmp(arg, "ofdm") == 0)
14914 + {
14915 + fix_tx_mode = FIXED_TXMODE_OFDM;
14916 + }
14917 + else if (strcmp(arg, "CCK") == 0 || strcmp(arg, "cck") == 0)
14918 + {
14919 + fix_tx_mode = FIXED_TXMODE_CCK;
14920 + }
14921 +
14922 +#ifdef CONFIG_STA_SUPPORT
14923 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
14924 + pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode = fix_tx_mode;
14925 +#endif // CONFIG_STA_SUPPORT //
14926 +
14927 + DBGPRINT(RT_DEBUG_TRACE, ("Set_FixedTxMode_Proc::(FixedTxMode=%d)\n", fix_tx_mode));
14928 +
14929 + return TRUE;
14930 +}
14931 +
14932 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
14933 +INT Set_OpMode_Proc(
14934 + IN PRTMP_ADAPTER pAd,
14935 + IN PUCHAR arg)
14936 +{
14937 + ULONG Value;
14938 +
14939 + Value = simple_strtol(arg, 0, 10);
14940 +
14941 +#ifdef RT2860
14942 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE))
14943 +#endif // RT2860 //
14944 + {
14945 + DBGPRINT(RT_DEBUG_ERROR, ("Can not switch operate mode on interface up !! \n"));
14946 + return FALSE;
14947 + }
14948 +
14949 + if (Value == 0)
14950 + pAd->OpMode = OPMODE_STA;
14951 + else if (Value == 1)
14952 + pAd->OpMode = OPMODE_AP;
14953 + else
14954 + return FALSE; //Invalid argument
14955 +
14956 + DBGPRINT(RT_DEBUG_TRACE, ("Set_OpMode_Proc::(OpMode=%s)\n", pAd->OpMode == 1 ? "AP Mode" : "STA Mode"));
14957 +
14958 + return TRUE;
14959 +}
14960 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
14961 +
14962 +
14963 +/////////////////////////////////////////////////////////////////////////
14964 +PCHAR RTMPGetRalinkAuthModeStr(
14965 + IN NDIS_802_11_AUTHENTICATION_MODE authMode)
14966 +{
14967 + switch(authMode)
14968 + {
14969 + case Ndis802_11AuthModeOpen:
14970 + return "OPEN";
14971 + default:
14972 + case Ndis802_11AuthModeWPAPSK:
14973 + return "WPAPSK";
14974 + case Ndis802_11AuthModeShared:
14975 + return "SHARED";
14976 + case Ndis802_11AuthModeWPA:
14977 + return "WPA";
14978 + case Ndis802_11AuthModeWPA2:
14979 + return "WPA2";
14980 + case Ndis802_11AuthModeWPA2PSK:
14981 + return "WPA2PSK";
14982 + case Ndis802_11AuthModeWPA1PSKWPA2PSK:
14983 + return "WPAPSKWPA2PSK";
14984 + case Ndis802_11AuthModeWPA1WPA2:
14985 + return "WPA1WPA2";
14986 + case Ndis802_11AuthModeWPANone:
14987 + return "WPANONE";
14988 + }
14989 +}
14990 +
14991 +PCHAR RTMPGetRalinkEncryModeStr(
14992 + IN USHORT encryMode)
14993 +{
14994 + switch(encryMode)
14995 + {
14996 + default:
14997 + case Ndis802_11WEPDisabled:
14998 + return "NONE";
14999 + case Ndis802_11WEPEnabled:
15000 + return "WEP";
15001 + case Ndis802_11Encryption2Enabled:
15002 + return "TKIP";
15003 + case Ndis802_11Encryption3Enabled:
15004 + return "AES";
15005 + case Ndis802_11Encryption4Enabled:
15006 + return "TKIPAES";
15007 + }
15008 +}
15009 +
15010 +INT RTMPShowCfgValue(
15011 + IN PRTMP_ADAPTER pAd,
15012 + IN PUCHAR pName,
15013 + IN PUCHAR pBuf)
15014 +{
15015 + INT Status = 0;
15016 +
15017 + for (PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC = RTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC; PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC->name; PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC++)
15018 + {
15019 + if (!strcmp(pName, PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC->name))
15020 + {
15021 + if(PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC->show_proc(pAd, pBuf))
15022 + Status = -EINVAL;
15023 + break; //Exit for loop.
15024 + }
15025 + }
15026 +
15027 + if(PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC->name == NULL)
15028 + {
15029 + sprintf(pBuf, "\n");
15030 + for (PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC = RTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC; PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC->name; PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC++)
15031 + sprintf(pBuf, "%s%s\n", pBuf, PRTMP_PRIVATE_STA_SHOW_CFG_VALUE_PROC->name);
15032 + }
15033 +
15034 + return Status;
15035 +}
15036 +
15037 +INT Show_SSID_Proc(
15038 + IN PRTMP_ADAPTER pAd,
15039 + OUT PUCHAR pBuf)
15040 +{
15041 +
15042 +#ifdef CONFIG_STA_SUPPORT
15043 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15044 + sprintf(pBuf, "\t%s", pAd->CommonCfg.Ssid);
15045 +#endif // CONFIG_STA_SUPPORT //
15046 + return 0;
15047 +}
15048 +
15049 +INT Show_WirelessMode_Proc(
15050 + IN PRTMP_ADAPTER pAd,
15051 + OUT PUCHAR pBuf)
15052 +{
15053 + switch(pAd->CommonCfg.PhyMode)
15054 + {
15055 + case PHY_11BG_MIXED:
15056 + sprintf(pBuf, "\t11B/G");
15057 + break;
15058 + case PHY_11B:
15059 + sprintf(pBuf, "\t11B");
15060 + break;
15061 + case PHY_11A:
15062 + sprintf(pBuf, "\t11A");
15063 + break;
15064 + case PHY_11ABG_MIXED:
15065 + sprintf(pBuf, "\t11A/B/G");
15066 + break;
15067 + case PHY_11G:
15068 + sprintf(pBuf, "\t11G");
15069 + break;
15070 +#ifdef DOT11_N_SUPPORT
15071 + case PHY_11ABGN_MIXED:
15072 + sprintf(pBuf, "\t11A/B/G/N");
15073 + break;
15074 + case PHY_11N_2_4G:
15075 + sprintf(pBuf, "\t11N only with 2.4G");
15076 + break;
15077 + case PHY_11GN_MIXED:
15078 + sprintf(pBuf, "\t11G/N");
15079 + break;
15080 + case PHY_11AN_MIXED:
15081 + sprintf(pBuf, "\t11A/N");
15082 + break;
15083 + case PHY_11BGN_MIXED:
15084 + sprintf(pBuf, "\t11B/G/N");
15085 + break;
15086 + case PHY_11AGN_MIXED:
15087 + sprintf(pBuf, "\t11A/G/N");
15088 + break;
15089 + case PHY_11N_5G:
15090 + sprintf(pBuf, "\t11N only with 5G");
15091 + break;
15092 +#endif // DOT11_N_SUPPORT //
15093 + default:
15094 + sprintf(pBuf, "\tUnknow Value(%d)", pAd->CommonCfg.PhyMode);
15095 + break;
15096 + }
15097 + return 0;
15098 +}
15099 +
15100 +
15101 +INT Show_TxBurst_Proc(
15102 + IN PRTMP_ADAPTER pAd,
15103 + OUT PUCHAR pBuf)
15104 +{
15105 + sprintf(pBuf, "\t%s", pAd->CommonCfg.bEnableTxBurst ? "TRUE":"FALSE");
15106 + return 0;
15107 +}
15108 +
15109 +INT Show_TxPreamble_Proc(
15110 + IN PRTMP_ADAPTER pAd,
15111 + OUT PUCHAR pBuf)
15112 +{
15113 + switch(pAd->CommonCfg.TxPreamble)
15114 + {
15115 + case Rt802_11PreambleShort:
15116 + sprintf(pBuf, "\tShort");
15117 + break;
15118 + case Rt802_11PreambleLong:
15119 + sprintf(pBuf, "\tLong");
15120 + break;
15121 + case Rt802_11PreambleAuto:
15122 + sprintf(pBuf, "\tAuto");
15123 + break;
15124 + default:
15125 + sprintf(pBuf, "\tUnknow Value(%lu)", pAd->CommonCfg.TxPreamble);
15126 + break;
15127 + }
15128 +
15129 + return 0;
15130 +}
15131 +
15132 +INT Show_TxPower_Proc(
15133 + IN PRTMP_ADAPTER pAd,
15134 + OUT PUCHAR pBuf)
15135 +{
15136 + sprintf(pBuf, "\t%lu", pAd->CommonCfg.TxPowerPercentage);
15137 + return 0;
15138 +}
15139 +
15140 +INT Show_Channel_Proc(
15141 + IN PRTMP_ADAPTER pAd,
15142 + OUT PUCHAR pBuf)
15143 +{
15144 + sprintf(pBuf, "\t%d", pAd->CommonCfg.Channel);
15145 + return 0;
15146 +}
15147 +
15148 +INT Show_BGProtection_Proc(
15149 + IN PRTMP_ADAPTER pAd,
15150 + OUT PUCHAR pBuf)
15151 +{
15152 + switch(pAd->CommonCfg.UseBGProtection)
15153 + {
15154 + case 1: //Always On
15155 + sprintf(pBuf, "\tON");
15156 + break;
15157 + case 2: //Always OFF
15158 + sprintf(pBuf, "\tOFF");
15159 + break;
15160 + case 0: //AUTO
15161 + sprintf(pBuf, "\tAuto");
15162 + break;
15163 + default:
15164 + sprintf(pBuf, "\tUnknow Value(%lu)", pAd->CommonCfg.UseBGProtection);
15165 + break;
15166 + }
15167 + return 0;
15168 +}
15169 +
15170 +INT Show_RTSThreshold_Proc(
15171 + IN PRTMP_ADAPTER pAd,
15172 + OUT PUCHAR pBuf)
15173 +{
15174 + sprintf(pBuf, "\t%u", pAd->CommonCfg.RtsThreshold);
15175 + return 0;
15176 +}
15177 +
15178 +INT Show_FragThreshold_Proc(
15179 + IN PRTMP_ADAPTER pAd,
15180 + OUT PUCHAR pBuf)
15181 +{
15182 + sprintf(pBuf, "\t%u", pAd->CommonCfg.FragmentThreshold);
15183 + return 0;
15184 +}
15185 +
15186 +#ifdef DOT11_N_SUPPORT
15187 +INT Show_HtBw_Proc(
15188 + IN PRTMP_ADAPTER pAd,
15189 + OUT PUCHAR pBuf)
15190 +{
15191 + if (pAd->CommonCfg.RegTransmitSetting.field.BW == BW_40)
15192 + {
15193 + sprintf(pBuf, "\t40 MHz");
15194 + }
15195 + else
15196 + {
15197 + sprintf(pBuf, "\t20 MHz");
15198 + }
15199 + return 0;
15200 +}
15201 +
15202 +INT Show_HtMcs_Proc(
15203 + IN PRTMP_ADAPTER pAd,
15204 + OUT PUCHAR pBuf)
15205 +{
15206 +
15207 +#ifdef CONFIG_STA_SUPPORT
15208 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15209 + sprintf(pBuf, "\t%u", pAd->StaCfg.DesiredTransmitSetting.field.MCS);
15210 +#endif // CONFIG_STA_SUPPORT //
15211 + return 0;
15212 +}
15213 +
15214 +INT Show_HtGi_Proc(
15215 + IN PRTMP_ADAPTER pAd,
15216 + OUT PUCHAR pBuf)
15217 +{
15218 + switch(pAd->CommonCfg.RegTransmitSetting.field.ShortGI)
15219 + {
15220 + case GI_400:
15221 + sprintf(pBuf, "\tGI_400");
15222 + break;
15223 + case GI_800:
15224 + sprintf(pBuf, "\tGI_800");
15225 + break;
15226 + default:
15227 + sprintf(pBuf, "\tUnknow Value(%u)", pAd->CommonCfg.RegTransmitSetting.field.ShortGI);
15228 + break;
15229 + }
15230 + return 0;
15231 +}
15232 +
15233 +INT Show_HtOpMode_Proc(
15234 + IN PRTMP_ADAPTER pAd,
15235 + OUT PUCHAR pBuf)
15236 +{
15237 + switch(pAd->CommonCfg.RegTransmitSetting.field.HTMODE)
15238 + {
15239 + case HTMODE_GF:
15240 + sprintf(pBuf, "\tGF");
15241 + break;
15242 + case HTMODE_MM:
15243 + sprintf(pBuf, "\tMM");
15244 + break;
15245 + default:
15246 + sprintf(pBuf, "\tUnknow Value(%u)", pAd->CommonCfg.RegTransmitSetting.field.HTMODE);
15247 + break;
15248 + }
15249 + return 0;
15250 +}
15251 +
15252 +INT Show_HtExtcha_Proc(
15253 + IN PRTMP_ADAPTER pAd,
15254 + OUT PUCHAR pBuf)
15255 +{
15256 + switch(pAd->CommonCfg.RegTransmitSetting.field.EXTCHA)
15257 + {
15258 + case EXTCHA_BELOW:
15259 + sprintf(pBuf, "\tBelow");
15260 + break;
15261 + case EXTCHA_ABOVE:
15262 + sprintf(pBuf, "\tAbove");
15263 + break;
15264 + default:
15265 + sprintf(pBuf, "\tUnknow Value(%u)", pAd->CommonCfg.RegTransmitSetting.field.EXTCHA);
15266 + break;
15267 + }
15268 + return 0;
15269 +}
15270 +
15271 +
15272 +INT Show_HtMpduDensity_Proc(
15273 + IN PRTMP_ADAPTER pAd,
15274 + OUT PUCHAR pBuf)
15275 +{
15276 + sprintf(pBuf, "\t%u", pAd->CommonCfg.BACapability.field.MpduDensity);
15277 + return 0;
15278 +}
15279 +
15280 +INT Show_HtBaWinSize_Proc(
15281 + IN PRTMP_ADAPTER pAd,
15282 + OUT PUCHAR pBuf)
15283 +{
15284 + sprintf(pBuf, "\t%u", pAd->CommonCfg.BACapability.field.RxBAWinLimit);
15285 + return 0;
15286 +}
15287 +
15288 +INT Show_HtRdg_Proc(
15289 + IN PRTMP_ADAPTER pAd,
15290 + OUT PUCHAR pBuf)
15291 +{
15292 + sprintf(pBuf, "\t%s", pAd->CommonCfg.bRdg ? "TRUE":"FALSE");
15293 + return 0;
15294 +}
15295 +
15296 +INT Show_HtAmsdu_Proc(
15297 + IN PRTMP_ADAPTER pAd,
15298 + OUT PUCHAR pBuf)
15299 +{
15300 + sprintf(pBuf, "\t%s", pAd->CommonCfg.BACapability.field.AmsduEnable ? "TRUE":"FALSE");
15301 + return 0;
15302 +}
15303 +
15304 +INT Show_HtAutoBa_Proc(
15305 + IN PRTMP_ADAPTER pAd,
15306 + OUT PUCHAR pBuf)
15307 +{
15308 + sprintf(pBuf, "\t%s", pAd->CommonCfg.BACapability.field.AutoBA ? "TRUE":"FALSE");
15309 + return 0;
15310 +}
15311 +#endif // DOT11_N_SUPPORT //
15312 +
15313 +INT Show_CountryRegion_Proc(
15314 + IN PRTMP_ADAPTER pAd,
15315 + OUT PUCHAR pBuf)
15316 +{
15317 + sprintf(pBuf, "\t%d", pAd->CommonCfg.CountryRegion);
15318 + return 0;
15319 +}
15320 +
15321 +INT Show_CountryRegionABand_Proc(
15322 + IN PRTMP_ADAPTER pAd,
15323 + OUT PUCHAR pBuf)
15324 +{
15325 + sprintf(pBuf, "\t%d", pAd->CommonCfg.CountryRegionForABand);
15326 + return 0;
15327 +}
15328 +
15329 +INT Show_CountryCode_Proc(
15330 + IN PRTMP_ADAPTER pAd,
15331 + OUT PUCHAR pBuf)
15332 +{
15333 + sprintf(pBuf, "\t%s", pAd->CommonCfg.CountryCode);
15334 + return 0;
15335 +}
15336 +
15337 +#ifdef AGGREGATION_SUPPORT
15338 +INT Show_PktAggregate_Proc(
15339 + IN PRTMP_ADAPTER pAd,
15340 + OUT PUCHAR pBuf)
15341 +{
15342 + sprintf(pBuf, "\t%s", pAd->CommonCfg.bAggregationCapable ? "TRUE":"FALSE");
15343 + return 0;
15344 +}
15345 +#endif // AGGREGATION_SUPPORT //
15346 +
15347 +#ifdef WMM_SUPPORT
15348 +INT Show_WmmCapable_Proc(
15349 + IN PRTMP_ADAPTER pAd,
15350 + OUT PUCHAR pBuf)
15351 +{
15352 +
15353 +#ifdef CONFIG_STA_SUPPORT
15354 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15355 + sprintf(pBuf, "\t%s", pAd->CommonCfg.bWmmCapable ? "TRUE":"FALSE");
15356 +#endif // CONFIG_STA_SUPPORT //
15357 +
15358 + return 0;
15359 +}
15360 +#endif // WMM_SUPPORT //
15361 +
15362 +INT Show_IEEE80211H_Proc(
15363 + IN PRTMP_ADAPTER pAd,
15364 + OUT PUCHAR pBuf)
15365 +{
15366 + sprintf(pBuf, "\t%s", pAd->CommonCfg.bIEEE80211H ? "TRUE":"FALSE");
15367 + return 0;
15368 +}
15369 +
15370 +#ifdef CONFIG_STA_SUPPORT
15371 +INT Show_NetworkType_Proc(
15372 + IN PRTMP_ADAPTER pAd,
15373 + OUT PUCHAR pBuf)
15374 +{
15375 + switch(pAd->StaCfg.BssType)
15376 + {
15377 + case BSS_ADHOC:
15378 + sprintf(pBuf, "\tAdhoc");
15379 + break;
15380 + case BSS_INFRA:
15381 + sprintf(pBuf, "\tInfra");
15382 + break;
15383 + case BSS_ANY:
15384 + sprintf(pBuf, "\tAny");
15385 + break;
15386 + case BSS_MONITOR:
15387 + sprintf(pBuf, "\tMonitor");
15388 + break;
15389 + default:
15390 + sprintf(pBuf, "\tUnknow Value(%d)", pAd->StaCfg.BssType);
15391 + break;
15392 + }
15393 + return 0;
15394 +}
15395 +#endif // CONFIG_STA_SUPPORT //
15396 +
15397 +INT Show_AuthMode_Proc(
15398 + IN PRTMP_ADAPTER pAd,
15399 + OUT PUCHAR pBuf)
15400 +{
15401 + NDIS_802_11_AUTHENTICATION_MODE AuthMode = Ndis802_11AuthModeOpen;
15402 +
15403 +#ifdef CONFIG_STA_SUPPORT
15404 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15405 + AuthMode = pAd->StaCfg.AuthMode;
15406 +#endif // CONFIG_STA_SUPPORT //
15407 +
15408 + if ((AuthMode >= Ndis802_11AuthModeOpen) &&
15409 + (AuthMode <= Ndis802_11AuthModeWPA1PSKWPA2PSK))
15410 + sprintf(pBuf, "\t%s", RTMPGetRalinkAuthModeStr(AuthMode));
15411 + else
15412 + sprintf(pBuf, "\tUnknow Value(%d)", AuthMode);
15413 +
15414 + return 0;
15415 +}
15416 +
15417 +INT Show_EncrypType_Proc(
15418 + IN PRTMP_ADAPTER pAd,
15419 + OUT PUCHAR pBuf)
15420 +{
15421 + NDIS_802_11_WEP_STATUS WepStatus = Ndis802_11WEPDisabled;
15422 +
15423 +#ifdef CONFIG_STA_SUPPORT
15424 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15425 + WepStatus = pAd->StaCfg.WepStatus;
15426 +#endif // CONFIG_STA_SUPPORT //
15427 +
15428 + if ((WepStatus >= Ndis802_11WEPEnabled) &&
15429 + (WepStatus <= Ndis802_11Encryption4KeyAbsent))
15430 + sprintf(pBuf, "\t%s", RTMPGetRalinkEncryModeStr(WepStatus));
15431 + else
15432 + sprintf(pBuf, "\tUnknow Value(%d)", WepStatus);
15433 +
15434 + return 0;
15435 +}
15436 +
15437 +INT Show_DefaultKeyID_Proc(
15438 + IN PRTMP_ADAPTER pAd,
15439 + OUT PUCHAR pBuf)
15440 +{
15441 + UCHAR DefaultKeyId = 0;
15442 +
15443 +#ifdef CONFIG_STA_SUPPORT
15444 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15445 + DefaultKeyId = pAd->StaCfg.DefaultKeyId;
15446 +#endif // CONFIG_STA_SUPPORT //
15447 +
15448 + sprintf(pBuf, "\t%d", DefaultKeyId);
15449 +
15450 + return 0;
15451 +}
15452 +
15453 +INT Show_WepKey_Proc(
15454 + IN PRTMP_ADAPTER pAd,
15455 + IN INT KeyIdx,
15456 + OUT PUCHAR pBuf)
15457 +{
15458 + UCHAR Key[16] = {0}, KeyLength = 0;
15459 + INT index = BSS0;
15460 +
15461 + KeyLength = pAd->SharedKey[index][KeyIdx].KeyLen;
15462 + NdisMoveMemory(Key, pAd->SharedKey[index][KeyIdx].Key, KeyLength);
15463 +
15464 + //check key string is ASCII or not
15465 + if (RTMPCheckStrPrintAble(Key, KeyLength))
15466 + sprintf(pBuf, "\t%s", Key);
15467 + else
15468 + {
15469 + int idx;
15470 + sprintf(pBuf, "\t");
15471 + for (idx = 0; idx < KeyLength; idx++)
15472 + sprintf(pBuf+strlen(pBuf), "%02X", Key[idx]);
15473 + }
15474 + return 0;
15475 +}
15476 +
15477 +INT Show_Key1_Proc(
15478 + IN PRTMP_ADAPTER pAd,
15479 + OUT PUCHAR pBuf)
15480 +{
15481 + Show_WepKey_Proc(pAd, 0, pBuf);
15482 + return 0;
15483 +}
15484 +
15485 +INT Show_Key2_Proc(
15486 + IN PRTMP_ADAPTER pAd,
15487 + OUT PUCHAR pBuf)
15488 +{
15489 + Show_WepKey_Proc(pAd, 1, pBuf);
15490 + return 0;
15491 +}
15492 +
15493 +INT Show_Key3_Proc(
15494 + IN PRTMP_ADAPTER pAd,
15495 + OUT PUCHAR pBuf)
15496 +{
15497 + Show_WepKey_Proc(pAd, 2, pBuf);
15498 + return 0;
15499 +}
15500 +
15501 +INT Show_Key4_Proc(
15502 + IN PRTMP_ADAPTER pAd,
15503 + OUT PUCHAR pBuf)
15504 +{
15505 + Show_WepKey_Proc(pAd, 3, pBuf);
15506 + return 0;
15507 +}
15508 +
15509 +INT Show_WPAPSK_Proc(
15510 + IN PRTMP_ADAPTER pAd,
15511 + OUT PUCHAR pBuf)
15512 +{
15513 + INT idx;
15514 + UCHAR PMK[32] = {0};
15515 +
15516 +
15517 +#ifdef CONFIG_STA_SUPPORT
15518 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15519 + NdisMoveMemory(PMK, pAd->StaCfg.PMK, 32);
15520 +#endif // CONFIG_STA_SUPPORT //
15521 +
15522 + sprintf(pBuf, "\tPMK = ");
15523 + for (idx = 0; idx < 32; idx++)
15524 + sprintf(pBuf+strlen(pBuf), "%02X", PMK[idx]);
15525 +
15526 + return 0;
15527 +}
15528 +
15529 --- /dev/null
15530 +++ b/drivers/staging/rt2860/common/cmm_sanity.c
15531 @@ -0,0 +1,1633 @@
15532 +/*
15533 + *************************************************************************
15534 + * Ralink Tech Inc.
15535 + * 5F., No.36, Taiyuan St., Jhubei City,
15536 + * Hsinchu County 302,
15537 + * Taiwan, R.O.C.
15538 + *
15539 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
15540 + *
15541 + * This program is free software; you can redistribute it and/or modify *
15542 + * it under the terms of the GNU General Public License as published by *
15543 + * the Free Software Foundation; either version 2 of the License, or *
15544 + * (at your option) any later version. *
15545 + * *
15546 + * This program is distributed in the hope that it will be useful, *
15547 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
15548 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
15549 + * GNU General Public License for more details. *
15550 + * *
15551 + * You should have received a copy of the GNU General Public License *
15552 + * along with this program; if not, write to the *
15553 + * Free Software Foundation, Inc., *
15554 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
15555 + * *
15556 + *************************************************************************
15557 +
15558 + Module Name:
15559 + sanity.c
15560 +
15561 + Abstract:
15562 +
15563 + Revision History:
15564 + Who When What
15565 + -------- ---------- ----------------------------------------------
15566 + John Chang 2004-09-01 add WMM support
15567 +*/
15568 +#include "../rt_config.h"
15569 +
15570 +
15571 +extern UCHAR CISCO_OUI[];
15572 +
15573 +extern UCHAR WPA_OUI[];
15574 +extern UCHAR RSN_OUI[];
15575 +extern UCHAR WME_INFO_ELEM[];
15576 +extern UCHAR WME_PARM_ELEM[];
15577 +extern UCHAR Ccx2QosInfo[];
15578 +extern UCHAR RALINK_OUI[];
15579 +extern UCHAR BROADCOM_OUI[];
15580 +extern UCHAR WPS_OUI[];
15581 +
15582 +/*
15583 + ==========================================================================
15584 + Description:
15585 + MLME message sanity check
15586 + Return:
15587 + TRUE if all parameters are OK, FALSE otherwise
15588 +
15589 + IRQL = DISPATCH_LEVEL
15590 +
15591 + ==========================================================================
15592 + */
15593 +BOOLEAN MlmeAddBAReqSanity(
15594 + IN PRTMP_ADAPTER pAd,
15595 + IN VOID *Msg,
15596 + IN ULONG MsgLen,
15597 + OUT PUCHAR pAddr2)
15598 +{
15599 + PMLME_ADDBA_REQ_STRUCT pInfo;
15600 +
15601 + pInfo = (MLME_ADDBA_REQ_STRUCT *)Msg;
15602 +
15603 + if ((MsgLen != sizeof(MLME_ADDBA_REQ_STRUCT)))
15604 + {
15605 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeAddBAReqSanity fail - message lenght not correct.\n"));
15606 + return FALSE;
15607 + }
15608 +
15609 + if ((pInfo->Wcid >= MAX_LEN_OF_MAC_TABLE))
15610 + {
15611 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeAddBAReqSanity fail - The peer Mac is not associated yet.\n"));
15612 + return FALSE;
15613 + }
15614 +
15615 + if ((pInfo->pAddr[0]&0x01) == 0x01)
15616 + {
15617 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeAddBAReqSanity fail - broadcast address not support BA\n"));
15618 + return FALSE;
15619 + }
15620 +
15621 + return TRUE;
15622 +}
15623 +
15624 +/*
15625 + ==========================================================================
15626 + Description:
15627 + MLME message sanity check
15628 + Return:
15629 + TRUE if all parameters are OK, FALSE otherwise
15630 +
15631 + IRQL = DISPATCH_LEVEL
15632 +
15633 + ==========================================================================
15634 + */
15635 +BOOLEAN MlmeDelBAReqSanity(
15636 + IN PRTMP_ADAPTER pAd,
15637 + IN VOID *Msg,
15638 + IN ULONG MsgLen)
15639 +{
15640 + MLME_DELBA_REQ_STRUCT *pInfo;
15641 + pInfo = (MLME_DELBA_REQ_STRUCT *)Msg;
15642 +
15643 + if ((MsgLen != sizeof(MLME_DELBA_REQ_STRUCT)))
15644 + {
15645 + DBGPRINT(RT_DEBUG_ERROR, ("MlmeDelBAReqSanity fail - message lenght not correct.\n"));
15646 + return FALSE;
15647 + }
15648 +
15649 + if ((pInfo->Wcid >= MAX_LEN_OF_MAC_TABLE))
15650 + {
15651 + DBGPRINT(RT_DEBUG_ERROR, ("MlmeDelBAReqSanity fail - The peer Mac is not associated yet.\n"));
15652 + return FALSE;
15653 + }
15654 +
15655 + if ((pInfo->TID & 0xf0))
15656 + {
15657 + DBGPRINT(RT_DEBUG_ERROR, ("MlmeDelBAReqSanity fail - The peer TID is incorrect.\n"));
15658 + return FALSE;
15659 + }
15660 +
15661 + if (NdisEqualMemory(pAd->MacTab.Content[pInfo->Wcid].Addr, pInfo->Addr, MAC_ADDR_LEN) == 0)
15662 + {
15663 + DBGPRINT(RT_DEBUG_ERROR, ("MlmeDelBAReqSanity fail - the peer addr dosen't exist.\n"));
15664 + return FALSE;
15665 + }
15666 +
15667 + return TRUE;
15668 +}
15669 +
15670 +BOOLEAN PeerAddBAReqActionSanity(
15671 + IN PRTMP_ADAPTER pAd,
15672 + IN VOID *pMsg,
15673 + IN ULONG MsgLen,
15674 + OUT PUCHAR pAddr2)
15675 +{
15676 + PFRAME_802_11 pFrame = (PFRAME_802_11)pMsg;
15677 + PFRAME_ADDBA_REQ pAddFrame;
15678 + pAddFrame = (PFRAME_ADDBA_REQ)(pMsg);
15679 + if (MsgLen < (sizeof(FRAME_ADDBA_REQ)))
15680 + {
15681 + DBGPRINT(RT_DEBUG_ERROR,("PeerAddBAReqActionSanity: ADDBA Request frame length size = %ld incorrect\n", MsgLen));
15682 + return FALSE;
15683 + }
15684 + // we support immediate BA.
15685 + *(USHORT *)(&pAddFrame->BaParm) = cpu2le16(*(USHORT *)(&pAddFrame->BaParm));
15686 + pAddFrame->TimeOutValue = cpu2le16(pAddFrame->TimeOutValue);
15687 + pAddFrame->BaStartSeq.word = cpu2le16(pAddFrame->BaStartSeq.word);
15688 +
15689 + if (pAddFrame->BaParm.BAPolicy != IMMED_BA)
15690 + {
15691 + DBGPRINT(RT_DEBUG_ERROR,("PeerAddBAReqActionSanity: ADDBA Request Ba Policy[%d] not support\n", pAddFrame->BaParm.BAPolicy));
15692 + DBGPRINT(RT_DEBUG_ERROR,("ADDBA Request. tid=%x, Bufsize=%x, AMSDUSupported=%x \n", pAddFrame->BaParm.TID, pAddFrame->BaParm.BufSize, pAddFrame->BaParm.AMSDUSupported));
15693 + return FALSE;
15694 + }
15695 +
15696 + // we support immediate BA.
15697 + if (pAddFrame->BaParm.TID &0xfff0)
15698 + {
15699 + DBGPRINT(RT_DEBUG_ERROR,("PeerAddBAReqActionSanity: ADDBA Request incorrect TID = %d\n", pAddFrame->BaParm.TID));
15700 + return FALSE;
15701 + }
15702 + COPY_MAC_ADDR(pAddr2, pFrame->Hdr.Addr2);
15703 + return TRUE;
15704 +}
15705 +
15706 +BOOLEAN PeerAddBARspActionSanity(
15707 + IN PRTMP_ADAPTER pAd,
15708 + IN VOID *pMsg,
15709 + IN ULONG MsgLen)
15710 +{
15711 + PFRAME_ADDBA_RSP pAddFrame;
15712 +
15713 + pAddFrame = (PFRAME_ADDBA_RSP)(pMsg);
15714 + if (MsgLen < (sizeof(FRAME_ADDBA_RSP)))
15715 + {
15716 + DBGPRINT(RT_DEBUG_ERROR,("PeerAddBARspActionSanity: ADDBA Response frame length size = %ld incorrect\n", MsgLen));
15717 + return FALSE;
15718 + }
15719 + // we support immediate BA.
15720 + *(USHORT *)(&pAddFrame->BaParm) = cpu2le16(*(USHORT *)(&pAddFrame->BaParm));
15721 + pAddFrame->StatusCode = cpu2le16(pAddFrame->StatusCode);
15722 + pAddFrame->TimeOutValue = cpu2le16(pAddFrame->TimeOutValue);
15723 +
15724 + if (pAddFrame->BaParm.BAPolicy != IMMED_BA)
15725 + {
15726 + DBGPRINT(RT_DEBUG_ERROR,("PeerAddBAReqActionSanity: ADDBA Response Ba Policy[%d] not support\n", pAddFrame->BaParm.BAPolicy));
15727 + return FALSE;
15728 + }
15729 +
15730 + // we support immediate BA.
15731 + if (pAddFrame->BaParm.TID &0xfff0)
15732 + {
15733 + DBGPRINT(RT_DEBUG_ERROR,("PeerAddBARspActionSanity: ADDBA Response incorrect TID = %d\n", pAddFrame->BaParm.TID));
15734 + return FALSE;
15735 + }
15736 + return TRUE;
15737 +
15738 +}
15739 +
15740 +BOOLEAN PeerDelBAActionSanity(
15741 + IN PRTMP_ADAPTER pAd,
15742 + IN UCHAR Wcid,
15743 + IN VOID *pMsg,
15744 + IN ULONG MsgLen )
15745 +{
15746 + //PFRAME_802_11 pFrame = (PFRAME_802_11)pMsg;
15747 + PFRAME_DELBA_REQ pDelFrame;
15748 + if (MsgLen != (sizeof(FRAME_DELBA_REQ)))
15749 + return FALSE;
15750 +
15751 + if (Wcid >= MAX_LEN_OF_MAC_TABLE)
15752 + return FALSE;
15753 +
15754 + pDelFrame = (PFRAME_DELBA_REQ)(pMsg);
15755 +
15756 + *(USHORT *)(&pDelFrame->DelbaParm) = cpu2le16(*(USHORT *)(&pDelFrame->DelbaParm));
15757 + pDelFrame->ReasonCode = cpu2le16(pDelFrame->ReasonCode);
15758 +
15759 + if (pDelFrame->DelbaParm.TID &0xfff0)
15760 + return FALSE;
15761 +
15762 + return TRUE;
15763 +}
15764 +
15765 +/*
15766 + ==========================================================================
15767 + Description:
15768 + MLME message sanity check
15769 + Return:
15770 + TRUE if all parameters are OK, FALSE otherwise
15771 +
15772 + IRQL = DISPATCH_LEVEL
15773 +
15774 + ==========================================================================
15775 + */
15776 +BOOLEAN PeerBeaconAndProbeRspSanity(
15777 + IN PRTMP_ADAPTER pAd,
15778 + IN VOID *Msg,
15779 + IN ULONG MsgLen,
15780 + IN UCHAR MsgChannel,
15781 + OUT PUCHAR pAddr2,
15782 + OUT PUCHAR pBssid,
15783 + OUT CHAR Ssid[],
15784 + OUT UCHAR *pSsidLen,
15785 + OUT UCHAR *pBssType,
15786 + OUT USHORT *pBeaconPeriod,
15787 + OUT UCHAR *pChannel,
15788 + OUT UCHAR *pNewChannel,
15789 + OUT LARGE_INTEGER *pTimestamp,
15790 + OUT CF_PARM *pCfParm,
15791 + OUT USHORT *pAtimWin,
15792 + OUT USHORT *pCapabilityInfo,
15793 + OUT UCHAR *pErp,
15794 + OUT UCHAR *pDtimCount,
15795 + OUT UCHAR *pDtimPeriod,
15796 + OUT UCHAR *pBcastFlag,
15797 + OUT UCHAR *pMessageToMe,
15798 + OUT UCHAR SupRate[],
15799 + OUT UCHAR *pSupRateLen,
15800 + OUT UCHAR ExtRate[],
15801 + OUT UCHAR *pExtRateLen,
15802 + OUT UCHAR *pCkipFlag,
15803 + OUT UCHAR *pAironetCellPowerLimit,
15804 + OUT PEDCA_PARM pEdcaParm,
15805 + OUT PQBSS_LOAD_PARM pQbssLoad,
15806 + OUT PQOS_CAPABILITY_PARM pQosCapability,
15807 + OUT ULONG *pRalinkIe,
15808 + OUT UCHAR *pHtCapabilityLen,
15809 +#ifdef CONFIG_STA_SUPPORT
15810 + OUT UCHAR *pPreNHtCapabilityLen,
15811 +#endif // CONFIG_STA_SUPPORT //
15812 + OUT HT_CAPABILITY_IE *pHtCapability,
15813 + OUT UCHAR *AddHtInfoLen,
15814 + OUT ADD_HT_INFO_IE *AddHtInfo,
15815 + OUT UCHAR *NewExtChannelOffset, // Ht extension channel offset(above or below)
15816 + OUT USHORT *LengthVIE,
15817 + OUT PNDIS_802_11_VARIABLE_IEs pVIE)
15818 +{
15819 + CHAR *Ptr;
15820 +#ifdef CONFIG_STA_SUPPORT
15821 + CHAR TimLen;
15822 +#endif // CONFIG_STA_SUPPORT //
15823 + PFRAME_802_11 pFrame;
15824 + PEID_STRUCT pEid;
15825 + UCHAR SubType;
15826 + UCHAR Sanity;
15827 + //UCHAR ECWMin, ECWMax;
15828 + //MAC_CSR9_STRUC Csr9;
15829 + ULONG Length = 0;
15830 +
15831 + // For some 11a AP which didn't have DS_IE, we use two conditions to decide the channel
15832 + // 1. If the AP is 11n enabled, then check the control channel.
15833 + // 2. If the AP didn't have any info about channel, use the channel we received this frame as the channel. (May inaccuracy!!)
15834 + UCHAR CtrlChannel = 0;
15835 +
15836 + // Add for 3 necessary EID field check
15837 + Sanity = 0;
15838 +
15839 + *pAtimWin = 0;
15840 + *pErp = 0;
15841 + *pDtimCount = 0;
15842 + *pDtimPeriod = 0;
15843 + *pBcastFlag = 0;
15844 + *pMessageToMe = 0;
15845 + *pExtRateLen = 0;
15846 + *pCkipFlag = 0; // Default of CkipFlag is 0
15847 + *pAironetCellPowerLimit = 0xFF; // Default of AironetCellPowerLimit is 0xFF
15848 + *LengthVIE = 0; // Set the length of VIE to init value 0
15849 + *pHtCapabilityLen = 0; // Set the length of VIE to init value 0
15850 +#ifdef CONFIG_STA_SUPPORT
15851 + if (pAd->OpMode == OPMODE_STA)
15852 + *pPreNHtCapabilityLen = 0; // Set the length of VIE to init value 0
15853 +#endif // CONFIG_STA_SUPPORT //
15854 + *AddHtInfoLen = 0; // Set the length of VIE to init value 0
15855 + *pRalinkIe = 0;
15856 + *pNewChannel = 0;
15857 + *NewExtChannelOffset = 0xff; //Default 0xff means no such IE
15858 + pCfParm->bValid = FALSE; // default: no IE_CF found
15859 + pQbssLoad->bValid = FALSE; // default: no IE_QBSS_LOAD found
15860 + pEdcaParm->bValid = FALSE; // default: no IE_EDCA_PARAMETER found
15861 + pQosCapability->bValid = FALSE; // default: no IE_QOS_CAPABILITY found
15862 +
15863 + pFrame = (PFRAME_802_11)Msg;
15864 +
15865 + // get subtype from header
15866 + SubType = (UCHAR)pFrame->Hdr.FC.SubType;
15867 +
15868 + // get Addr2 and BSSID from header
15869 + COPY_MAC_ADDR(pAddr2, pFrame->Hdr.Addr2);
15870 + COPY_MAC_ADDR(pBssid, pFrame->Hdr.Addr3);
15871 +
15872 + Ptr = pFrame->Octet;
15873 + Length += LENGTH_802_11;
15874 +
15875 + // get timestamp from payload and advance the pointer
15876 + NdisMoveMemory(pTimestamp, Ptr, TIMESTAMP_LEN);
15877 +
15878 + pTimestamp->u.LowPart = cpu2le32(pTimestamp->u.LowPart);
15879 + pTimestamp->u.HighPart = cpu2le32(pTimestamp->u.HighPart);
15880 +
15881 + Ptr += TIMESTAMP_LEN;
15882 + Length += TIMESTAMP_LEN;
15883 +
15884 + // get beacon interval from payload and advance the pointer
15885 + NdisMoveMemory(pBeaconPeriod, Ptr, 2);
15886 + Ptr += 2;
15887 + Length += 2;
15888 +
15889 + // get capability info from payload and advance the pointer
15890 + NdisMoveMemory(pCapabilityInfo, Ptr, 2);
15891 + Ptr += 2;
15892 + Length += 2;
15893 +
15894 + if (CAP_IS_ESS_ON(*pCapabilityInfo))
15895 + *pBssType = BSS_INFRA;
15896 + else
15897 + *pBssType = BSS_ADHOC;
15898 +
15899 + pEid = (PEID_STRUCT) Ptr;
15900 +
15901 + // get variable fields from payload and advance the pointer
15902 + while ((Length + 2 + pEid->Len) <= MsgLen)
15903 + {
15904 + //
15905 + // Secure copy VIE to VarIE[MAX_VIE_LEN] didn't overflow.
15906 + //
15907 + if ((*LengthVIE + pEid->Len + 2) >= MAX_VIE_LEN)
15908 + {
15909 + DBGPRINT(RT_DEBUG_WARN, ("PeerBeaconAndProbeRspSanity - Variable IEs out of resource [len(=%d) > MAX_VIE_LEN(=%d)]\n",
15910 + (*LengthVIE + pEid->Len + 2), MAX_VIE_LEN));
15911 + break;
15912 + }
15913 +
15914 + switch(pEid->Eid)
15915 + {
15916 + case IE_SSID:
15917 + // Already has one SSID EID in this beacon, ignore the second one
15918 + if (Sanity & 0x1)
15919 + break;
15920 + if(pEid->Len <= MAX_LEN_OF_SSID)
15921 + {
15922 + NdisMoveMemory(Ssid, pEid->Octet, pEid->Len);
15923 + *pSsidLen = pEid->Len;
15924 + Sanity |= 0x1;
15925 + }
15926 + else
15927 + {
15928 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAndProbeRspSanity - wrong IE_SSID (len=%d)\n",pEid->Len));
15929 + return FALSE;
15930 + }
15931 + break;
15932 +
15933 + case IE_SUPP_RATES:
15934 + if(pEid->Len <= MAX_LEN_OF_SUPPORTED_RATES)
15935 + {
15936 + Sanity |= 0x2;
15937 + NdisMoveMemory(SupRate, pEid->Octet, pEid->Len);
15938 + *pSupRateLen = pEid->Len;
15939 +
15940 + // TODO: 2004-09-14 not a good design here, cause it exclude extra rates
15941 + // from ScanTab. We should report as is. And filter out unsupported
15942 + // rates in MlmeAux.
15943 + // Check against the supported rates
15944 + // RTMPCheckRates(pAd, SupRate, pSupRateLen);
15945 + }
15946 + else
15947 + {
15948 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAndProbeRspSanity - wrong IE_SUPP_RATES (len=%d)\n",pEid->Len));
15949 + return FALSE;
15950 + }
15951 + break;
15952 +
15953 + case IE_HT_CAP:
15954 + if (pEid->Len >= SIZE_HT_CAP_IE) //Note: allow extension.!!
15955 + {
15956 + NdisMoveMemory(pHtCapability, pEid->Octet, sizeof(HT_CAPABILITY_IE));
15957 + *pHtCapabilityLen = SIZE_HT_CAP_IE; // Nnow we only support 26 bytes.
15958 +
15959 + *(USHORT *)(&pHtCapability->HtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->HtCapInfo));
15960 + *(USHORT *)(&pHtCapability->ExtHtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->ExtHtCapInfo));
15961 +
15962 +#ifdef CONFIG_STA_SUPPORT
15963 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15964 + {
15965 + *pPreNHtCapabilityLen = 0; // Nnow we only support 26 bytes.
15966 +
15967 + Ptr = (PUCHAR) pVIE;
15968 + NdisMoveMemory(Ptr + *LengthVIE, &pEid->Eid, pEid->Len + 2);
15969 + *LengthVIE += (pEid->Len + 2);
15970 + }
15971 +#endif // CONFIG_STA_SUPPORT //
15972 + }
15973 + else
15974 + {
15975 + DBGPRINT(RT_DEBUG_WARN, ("PeerBeaconAndProbeRspSanity - wrong IE_HT_CAP. pEid->Len = %d\n", pEid->Len));
15976 + }
15977 +
15978 + break;
15979 + case IE_ADD_HT:
15980 + if (pEid->Len >= sizeof(ADD_HT_INFO_IE))
15981 + {
15982 + // This IE allows extension, but we can ignore extra bytes beyond our knowledge , so only
15983 + // copy first sizeof(ADD_HT_INFO_IE)
15984 + NdisMoveMemory(AddHtInfo, pEid->Octet, sizeof(ADD_HT_INFO_IE));
15985 + *AddHtInfoLen = SIZE_ADD_HT_INFO_IE;
15986 +
15987 + CtrlChannel = AddHtInfo->ControlChan;
15988 +
15989 + *(USHORT *)(&AddHtInfo->AddHtInfo2) = cpu2le16(*(USHORT *)(&AddHtInfo->AddHtInfo2));
15990 + *(USHORT *)(&AddHtInfo->AddHtInfo3) = cpu2le16(*(USHORT *)(&AddHtInfo->AddHtInfo3));
15991 +
15992 +#ifdef CONFIG_STA_SUPPORT
15993 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
15994 + {
15995 + Ptr = (PUCHAR) pVIE;
15996 + NdisMoveMemory(Ptr + *LengthVIE, &pEid->Eid, pEid->Len + 2);
15997 + *LengthVIE += (pEid->Len + 2);
15998 + }
15999 +#endif // CONFIG_STA_SUPPORT //
16000 + }
16001 + else
16002 + {
16003 + DBGPRINT(RT_DEBUG_WARN, ("PeerBeaconAndProbeRspSanity - wrong IE_ADD_HT. \n"));
16004 + }
16005 +
16006 + break;
16007 + case IE_SECONDARY_CH_OFFSET:
16008 + if (pEid->Len == 1)
16009 + {
16010 + *NewExtChannelOffset = pEid->Octet[0];
16011 + }
16012 + else
16013 + {
16014 + DBGPRINT(RT_DEBUG_WARN, ("PeerBeaconAndProbeRspSanity - wrong IE_SECONDARY_CH_OFFSET. \n"));
16015 + }
16016 +
16017 + break;
16018 + case IE_FH_PARM:
16019 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAndProbeRspSanity(IE_FH_PARM) \n"));
16020 + break;
16021 +
16022 + case IE_DS_PARM:
16023 + if(pEid->Len == 1)
16024 + {
16025 + *pChannel = *pEid->Octet;
16026 +#ifdef CONFIG_STA_SUPPORT
16027 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
16028 + {
16029 + if (ChannelSanity(pAd, *pChannel) == 0)
16030 + {
16031 +
16032 + return FALSE;
16033 + }
16034 + }
16035 +#endif // CONFIG_STA_SUPPORT //
16036 + Sanity |= 0x4;
16037 + }
16038 + else
16039 + {
16040 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAndProbeRspSanity - wrong IE_DS_PARM (len=%d)\n",pEid->Len));
16041 + return FALSE;
16042 + }
16043 + break;
16044 +
16045 + case IE_CF_PARM:
16046 + if(pEid->Len == 6)
16047 + {
16048 + pCfParm->bValid = TRUE;
16049 + pCfParm->CfpCount = pEid->Octet[0];
16050 + pCfParm->CfpPeriod = pEid->Octet[1];
16051 + pCfParm->CfpMaxDuration = pEid->Octet[2] + 256 * pEid->Octet[3];
16052 + pCfParm->CfpDurRemaining = pEid->Octet[4] + 256 * pEid->Octet[5];
16053 + }
16054 + else
16055 + {
16056 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAndProbeRspSanity - wrong IE_CF_PARM\n"));
16057 + return FALSE;
16058 + }
16059 + break;
16060 +
16061 + case IE_IBSS_PARM:
16062 + if(pEid->Len == 2)
16063 + {
16064 + NdisMoveMemory(pAtimWin, pEid->Octet, pEid->Len);
16065 + }
16066 + else
16067 + {
16068 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAndProbeRspSanity - wrong IE_IBSS_PARM\n"));
16069 + return FALSE;
16070 + }
16071 + break;
16072 +
16073 +#ifdef CONFIG_STA_SUPPORT
16074 + case IE_TIM:
16075 + if(INFRA_ON(pAd) && SubType == SUBTYPE_BEACON)
16076 + {
16077 + GetTimBit((PUCHAR)pEid, pAd->StaActive.Aid, &TimLen, pBcastFlag, pDtimCount, pDtimPeriod, pMessageToMe);
16078 + }
16079 + break;
16080 +#endif // CONFIG_STA_SUPPORT //
16081 + case IE_CHANNEL_SWITCH_ANNOUNCEMENT:
16082 + if(pEid->Len == 3)
16083 + {
16084 + *pNewChannel = pEid->Octet[1]; //extract new channel number
16085 + }
16086 + break;
16087 +
16088 + // New for WPA
16089 + // CCX v2 has the same IE, we need to parse that too
16090 + // Wifi WMM use the same IE vale, need to parse that too
16091 + // case IE_WPA:
16092 + case IE_VENDOR_SPECIFIC:
16093 + // Check the OUI version, filter out non-standard usage
16094 + if (NdisEqualMemory(pEid->Octet, RALINK_OUI, 3) && (pEid->Len == 7))
16095 + {
16096 + //*pRalinkIe = pEid->Octet[3];
16097 + if (pEid->Octet[3] != 0)
16098 + *pRalinkIe = pEid->Octet[3];
16099 + else
16100 + *pRalinkIe = 0xf0000000; // Set to non-zero value (can't set bit0-2) to represent this is Ralink Chip. So at linkup, we will set ralinkchip flag.
16101 + }
16102 +#ifdef CONFIG_STA_SUPPORT
16103 +#ifdef DOT11_N_SUPPORT
16104 + // This HT IE is before IEEE draft set HT IE value.2006-09-28 by Jan.
16105 +
16106 + // Other vendors had production before IE_HT_CAP value is assigned. To backward support those old-firmware AP,
16107 + // Check broadcom-defiend pre-802.11nD1.0 OUI for HT related IE, including HT Capatilities IE and HT Information IE
16108 + else if ((*pHtCapabilityLen == 0) && NdisEqualMemory(pEid->Octet, PRE_N_HT_OUI, 3) && (pEid->Len >= 4) && (pAd->OpMode == OPMODE_STA))
16109 + {
16110 + if ((pEid->Octet[3] == OUI_PREN_HT_CAP) && (pEid->Len >= 30) && (*pHtCapabilityLen == 0))
16111 + {
16112 + NdisMoveMemory(pHtCapability, &pEid->Octet[4], sizeof(HT_CAPABILITY_IE));
16113 + *pPreNHtCapabilityLen = SIZE_HT_CAP_IE;
16114 + }
16115 +
16116 + if ((pEid->Octet[3] == OUI_PREN_ADD_HT) && (pEid->Len >= 26))
16117 + {
16118 + NdisMoveMemory(AddHtInfo, &pEid->Octet[4], sizeof(ADD_HT_INFO_IE));
16119 + *AddHtInfoLen = SIZE_ADD_HT_INFO_IE;
16120 + }
16121 + }
16122 +#endif // DOT11_N_SUPPORT //
16123 +#endif // CONFIG_STA_SUPPORT //
16124 + else if (NdisEqualMemory(pEid->Octet, WPA_OUI, 4))
16125 + {
16126 + // Copy to pVIE which will report to microsoft bssid list.
16127 + Ptr = (PUCHAR) pVIE;
16128 + NdisMoveMemory(Ptr + *LengthVIE, &pEid->Eid, pEid->Len + 2);
16129 + *LengthVIE += (pEid->Len + 2);
16130 + }
16131 + else if (NdisEqualMemory(pEid->Octet, WME_PARM_ELEM, 6) && (pEid->Len == 24))
16132 + {
16133 + PUCHAR ptr;
16134 + int i;
16135 +
16136 + // parsing EDCA parameters
16137 + pEdcaParm->bValid = TRUE;
16138 + pEdcaParm->bQAck = FALSE; // pEid->Octet[0] & 0x10;
16139 + pEdcaParm->bQueueRequest = FALSE; // pEid->Octet[0] & 0x20;
16140 + pEdcaParm->bTxopRequest = FALSE; // pEid->Octet[0] & 0x40;
16141 + pEdcaParm->EdcaUpdateCount = pEid->Octet[6] & 0x0f;
16142 + pEdcaParm->bAPSDCapable = (pEid->Octet[6] & 0x80) ? 1 : 0;
16143 + ptr = &pEid->Octet[8];
16144 + for (i=0; i<4; i++)
16145 + {
16146 + UCHAR aci = (*ptr & 0x60) >> 5; // b5~6 is AC INDEX
16147 + pEdcaParm->bACM[aci] = (((*ptr) & 0x10) == 0x10); // b5 is ACM
16148 + pEdcaParm->Aifsn[aci] = (*ptr) & 0x0f; // b0~3 is AIFSN
16149 + pEdcaParm->Cwmin[aci] = *(ptr+1) & 0x0f; // b0~4 is Cwmin
16150 + pEdcaParm->Cwmax[aci] = *(ptr+1) >> 4; // b5~8 is Cwmax
16151 + pEdcaParm->Txop[aci] = *(ptr+2) + 256 * (*(ptr+3)); // in unit of 32-us
16152 + ptr += 4; // point to next AC
16153 + }
16154 + }
16155 + else if (NdisEqualMemory(pEid->Octet, WME_INFO_ELEM, 6) && (pEid->Len == 7))
16156 + {
16157 + // parsing EDCA parameters
16158 + pEdcaParm->bValid = TRUE;
16159 + pEdcaParm->bQAck = FALSE; // pEid->Octet[0] & 0x10;
16160 + pEdcaParm->bQueueRequest = FALSE; // pEid->Octet[0] & 0x20;
16161 + pEdcaParm->bTxopRequest = FALSE; // pEid->Octet[0] & 0x40;
16162 + pEdcaParm->EdcaUpdateCount = pEid->Octet[6] & 0x0f;
16163 + pEdcaParm->bAPSDCapable = (pEid->Octet[6] & 0x80) ? 1 : 0;
16164 +
16165 + // use default EDCA parameter
16166 + pEdcaParm->bACM[QID_AC_BE] = 0;
16167 + pEdcaParm->Aifsn[QID_AC_BE] = 3;
16168 + pEdcaParm->Cwmin[QID_AC_BE] = CW_MIN_IN_BITS;
16169 + pEdcaParm->Cwmax[QID_AC_BE] = CW_MAX_IN_BITS;
16170 + pEdcaParm->Txop[QID_AC_BE] = 0;
16171 +
16172 + pEdcaParm->bACM[QID_AC_BK] = 0;
16173 + pEdcaParm->Aifsn[QID_AC_BK] = 7;
16174 + pEdcaParm->Cwmin[QID_AC_BK] = CW_MIN_IN_BITS;
16175 + pEdcaParm->Cwmax[QID_AC_BK] = CW_MAX_IN_BITS;
16176 + pEdcaParm->Txop[QID_AC_BK] = 0;
16177 +
16178 + pEdcaParm->bACM[QID_AC_VI] = 0;
16179 + pEdcaParm->Aifsn[QID_AC_VI] = 2;
16180 + pEdcaParm->Cwmin[QID_AC_VI] = CW_MIN_IN_BITS-1;
16181 + pEdcaParm->Cwmax[QID_AC_VI] = CW_MAX_IN_BITS;
16182 + pEdcaParm->Txop[QID_AC_VI] = 96; // AC_VI: 96*32us ~= 3ms
16183 +
16184 + pEdcaParm->bACM[QID_AC_VO] = 0;
16185 + pEdcaParm->Aifsn[QID_AC_VO] = 2;
16186 + pEdcaParm->Cwmin[QID_AC_VO] = CW_MIN_IN_BITS-2;
16187 + pEdcaParm->Cwmax[QID_AC_VO] = CW_MAX_IN_BITS-1;
16188 + pEdcaParm->Txop[QID_AC_VO] = 48; // AC_VO: 48*32us ~= 1.5ms
16189 + }
16190 + break;
16191 +
16192 + case IE_EXT_SUPP_RATES:
16193 + if (pEid->Len <= MAX_LEN_OF_SUPPORTED_RATES)
16194 + {
16195 + NdisMoveMemory(ExtRate, pEid->Octet, pEid->Len);
16196 + *pExtRateLen = pEid->Len;
16197 +
16198 + // TODO: 2004-09-14 not a good design here, cause it exclude extra rates
16199 + // from ScanTab. We should report as is. And filter out unsupported
16200 + // rates in MlmeAux.
16201 + // Check against the supported rates
16202 + // RTMPCheckRates(pAd, ExtRate, pExtRateLen);
16203 + }
16204 + break;
16205 +
16206 + case IE_ERP:
16207 + if (pEid->Len == 1)
16208 + {
16209 + *pErp = (UCHAR)pEid->Octet[0];
16210 + }
16211 + break;
16212 +
16213 + case IE_AIRONET_CKIP:
16214 + // 0. Check Aironet IE length, it must be larger or equal to 28
16215 + // Cisco AP350 used length as 28
16216 + // Cisco AP12XX used length as 30
16217 + if (pEid->Len < (CKIP_NEGOTIATION_LENGTH - 2))
16218 + break;
16219 +
16220 + // 1. Copy CKIP flag byte to buffer for process
16221 + *pCkipFlag = *(pEid->Octet + 8);
16222 + break;
16223 +
16224 + case IE_AP_TX_POWER:
16225 + // AP Control of Client Transmit Power
16226 + //0. Check Aironet IE length, it must be 6
16227 + if (pEid->Len != 0x06)
16228 + break;
16229 +
16230 + // Get cell power limit in dBm
16231 + if (NdisEqualMemory(pEid->Octet, CISCO_OUI, 3) == 1)
16232 + *pAironetCellPowerLimit = *(pEid->Octet + 4);
16233 + break;
16234 +
16235 + // WPA2 & 802.11i RSN
16236 + case IE_RSN:
16237 + // There is no OUI for version anymore, check the group cipher OUI before copying
16238 + if (RTMPEqualMemory(pEid->Octet + 2, RSN_OUI, 3))
16239 + {
16240 + // Copy to pVIE which will report to microsoft bssid list.
16241 + Ptr = (PUCHAR) pVIE;
16242 + NdisMoveMemory(Ptr + *LengthVIE, &pEid->Eid, pEid->Len + 2);
16243 + *LengthVIE += (pEid->Len + 2);
16244 + }
16245 + break;
16246 +#ifdef CONFIG_STA_SUPPORT
16247 +#ifdef EXT_BUILD_CHANNEL_LIST
16248 + case IE_COUNTRY:
16249 + Ptr = (PUCHAR) pVIE;
16250 + NdisMoveMemory(Ptr + *LengthVIE, &pEid->Eid, pEid->Len + 2);
16251 + *LengthVIE += (pEid->Len + 2);
16252 + break;
16253 +#endif // EXT_BUILD_CHANNEL_LIST //
16254 +#endif // CONFIG_STA_SUPPORT //
16255 +
16256 + default:
16257 + break;
16258 + }
16259 +
16260 + Length = Length + 2 + pEid->Len; // Eid[1] + Len[1]+ content[Len]
16261 + pEid = (PEID_STRUCT)((UCHAR*)pEid + 2 + pEid->Len);
16262 + }
16263 +
16264 + // For some 11a AP. it did not have the channel EID, patch here
16265 +#ifdef CONFIG_STA_SUPPORT
16266 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
16267 + {
16268 + UCHAR LatchRfChannel = MsgChannel;
16269 + if ((pAd->LatchRfRegs.Channel > 14) && ((Sanity & 0x4) == 0))
16270 + {
16271 + if (CtrlChannel != 0)
16272 + *pChannel = CtrlChannel;
16273 + else
16274 + *pChannel = LatchRfChannel;
16275 + Sanity |= 0x4;
16276 + }
16277 + }
16278 +#endif // CONFIG_STA_SUPPORT //
16279 +
16280 + if (Sanity != 0x7)
16281 + {
16282 + DBGPRINT(RT_DEBUG_WARN, ("PeerBeaconAndProbeRspSanity - missing field, Sanity=0x%02x\n", Sanity));
16283 + return FALSE;
16284 + }
16285 + else
16286 + {
16287 + return TRUE;
16288 + }
16289 +
16290 +}
16291 +
16292 +#ifdef DOT11N_DRAFT3
16293 +/*
16294 + ==========================================================================
16295 + Description:
16296 + MLME message sanity check for some IE addressed in 802.11n d3.03.
16297 + Return:
16298 + TRUE if all parameters are OK, FALSE otherwise
16299 +
16300 + IRQL = DISPATCH_LEVEL
16301 +
16302 + ==========================================================================
16303 + */
16304 +BOOLEAN PeerBeaconAndProbeRspSanity2(
16305 + IN PRTMP_ADAPTER pAd,
16306 + IN VOID *Msg,
16307 + IN ULONG MsgLen,
16308 + OUT UCHAR *RegClass)
16309 +{
16310 + CHAR *Ptr;
16311 + PFRAME_802_11 pFrame;
16312 + PEID_STRUCT pEid;
16313 + ULONG Length = 0;
16314 +
16315 + pFrame = (PFRAME_802_11)Msg;
16316 +
16317 + *RegClass = 0;
16318 + Ptr = pFrame->Octet;
16319 + Length += LENGTH_802_11;
16320 +
16321 + // get timestamp from payload and advance the pointer
16322 + Ptr += TIMESTAMP_LEN;
16323 + Length += TIMESTAMP_LEN;
16324 +
16325 + // get beacon interval from payload and advance the pointer
16326 + Ptr += 2;
16327 + Length += 2;
16328 +
16329 + // get capability info from payload and advance the pointer
16330 + Ptr += 2;
16331 + Length += 2;
16332 +
16333 + pEid = (PEID_STRUCT) Ptr;
16334 +
16335 + // get variable fields from payload and advance the pointer
16336 + while ((Length + 2 + pEid->Len) <= MsgLen)
16337 + {
16338 + switch(pEid->Eid)
16339 + {
16340 + case IE_SUPP_REG_CLASS:
16341 + if(pEid->Len > 0)
16342 + {
16343 + *RegClass = *pEid->Octet;
16344 + }
16345 + else
16346 + {
16347 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAndProbeRspSanity - wrong IE_SSID (len=%d)\n",pEid->Len));
16348 + return FALSE;
16349 + }
16350 + break;
16351 + }
16352 +
16353 + Length = Length + 2 + pEid->Len; // Eid[1] + Len[1]+ content[Len]
16354 + pEid = (PEID_STRUCT)((UCHAR*)pEid + 2 + pEid->Len);
16355 + }
16356 +
16357 + return TRUE;
16358 +
16359 +}
16360 +#endif // DOT11N_DRAFT3 //
16361 +
16362 +/*
16363 + ==========================================================================
16364 + Description:
16365 + MLME message sanity check
16366 + Return:
16367 + TRUE if all parameters are OK, FALSE otherwise
16368 + ==========================================================================
16369 + */
16370 +BOOLEAN MlmeScanReqSanity(
16371 + IN PRTMP_ADAPTER pAd,
16372 + IN VOID *Msg,
16373 + IN ULONG MsgLen,
16374 + OUT UCHAR *pBssType,
16375 + OUT CHAR Ssid[],
16376 + OUT UCHAR *pSsidLen,
16377 + OUT UCHAR *pScanType)
16378 +{
16379 + MLME_SCAN_REQ_STRUCT *Info;
16380 +
16381 + Info = (MLME_SCAN_REQ_STRUCT *)(Msg);
16382 + *pBssType = Info->BssType;
16383 + *pSsidLen = Info->SsidLen;
16384 + NdisMoveMemory(Ssid, Info->Ssid, *pSsidLen);
16385 + *pScanType = Info->ScanType;
16386 +
16387 + if ((*pBssType == BSS_INFRA || *pBssType == BSS_ADHOC || *pBssType == BSS_ANY)
16388 + && (*pScanType == SCAN_ACTIVE || *pScanType == SCAN_PASSIVE
16389 +#ifdef CONFIG_STA_SUPPORT
16390 + || *pScanType == SCAN_CISCO_PASSIVE || *pScanType == SCAN_CISCO_ACTIVE
16391 + || *pScanType == SCAN_CISCO_CHANNEL_LOAD || *pScanType == SCAN_CISCO_NOISE
16392 +#endif // CONFIG_STA_SUPPORT //
16393 + ))
16394 + {
16395 + return TRUE;
16396 + }
16397 + else
16398 + {
16399 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeScanReqSanity fail - wrong BssType or ScanType\n"));
16400 + return FALSE;
16401 + }
16402 +}
16403 +
16404 +// IRQL = DISPATCH_LEVEL
16405 +UCHAR ChannelSanity(
16406 + IN PRTMP_ADAPTER pAd,
16407 + IN UCHAR channel)
16408 +{
16409 + int i;
16410 +
16411 + for (i = 0; i < pAd->ChannelListNum; i ++)
16412 + {
16413 + if (channel == pAd->ChannelList[i].Channel)
16414 + return 1;
16415 + }
16416 + return 0;
16417 +}
16418 +
16419 +/*
16420 + ==========================================================================
16421 + Description:
16422 + MLME message sanity check
16423 + Return:
16424 + TRUE if all parameters are OK, FALSE otherwise
16425 +
16426 + IRQL = DISPATCH_LEVEL
16427 +
16428 + ==========================================================================
16429 + */
16430 +BOOLEAN PeerDeauthSanity(
16431 + IN PRTMP_ADAPTER pAd,
16432 + IN VOID *Msg,
16433 + IN ULONG MsgLen,
16434 + OUT PUCHAR pAddr2,
16435 + OUT USHORT *pReason)
16436 +{
16437 + PFRAME_802_11 pFrame = (PFRAME_802_11)Msg;
16438 +
16439 + COPY_MAC_ADDR(pAddr2, pFrame->Hdr.Addr2);
16440 + NdisMoveMemory(pReason, &pFrame->Octet[0], 2);
16441 +
16442 + return TRUE;
16443 +}
16444 +
16445 +/*
16446 + ==========================================================================
16447 + Description:
16448 + MLME message sanity check
16449 + Return:
16450 + TRUE if all parameters are OK, FALSE otherwise
16451 +
16452 + IRQL = DISPATCH_LEVEL
16453 +
16454 + ==========================================================================
16455 + */
16456 +BOOLEAN PeerAuthSanity(
16457 + IN PRTMP_ADAPTER pAd,
16458 + IN VOID *Msg,
16459 + IN ULONG MsgLen,
16460 + OUT PUCHAR pAddr,
16461 + OUT USHORT *pAlg,
16462 + OUT USHORT *pSeq,
16463 + OUT USHORT *pStatus,
16464 + CHAR *pChlgText)
16465 +{
16466 + PFRAME_802_11 pFrame = (PFRAME_802_11)Msg;
16467 +
16468 + COPY_MAC_ADDR(pAddr, pFrame->Hdr.Addr2);
16469 + NdisMoveMemory(pAlg, &pFrame->Octet[0], 2);
16470 + NdisMoveMemory(pSeq, &pFrame->Octet[2], 2);
16471 + NdisMoveMemory(pStatus, &pFrame->Octet[4], 2);
16472 +
16473 + if ((*pAlg == Ndis802_11AuthModeOpen)
16474 +#ifdef LEAP_SUPPORT
16475 + || (*pAlg == CISCO_AuthModeLEAP)
16476 +#endif // LEAP_SUPPORT //
16477 + )
16478 + {
16479 + if (*pSeq == 1 || *pSeq == 2)
16480 + {
16481 + return TRUE;
16482 + }
16483 + else
16484 + {
16485 + DBGPRINT(RT_DEBUG_TRACE, ("PeerAuthSanity fail - wrong Seg#\n"));
16486 + return FALSE;
16487 + }
16488 + }
16489 + else if (*pAlg == Ndis802_11AuthModeShared)
16490 + {
16491 + if (*pSeq == 1 || *pSeq == 4)
16492 + {
16493 + return TRUE;
16494 + }
16495 + else if (*pSeq == 2 || *pSeq == 3)
16496 + {
16497 + NdisMoveMemory(pChlgText, &pFrame->Octet[8], CIPHER_TEXT_LEN);
16498 + return TRUE;
16499 + }
16500 + else
16501 + {
16502 + DBGPRINT(RT_DEBUG_TRACE, ("PeerAuthSanity fail - wrong Seg#\n"));
16503 + return FALSE;
16504 + }
16505 + }
16506 + else
16507 + {
16508 + DBGPRINT(RT_DEBUG_TRACE, ("PeerAuthSanity fail - wrong algorithm\n"));
16509 + return FALSE;
16510 + }
16511 +}
16512 +
16513 +/*
16514 + ==========================================================================
16515 + Description:
16516 + MLME message sanity check
16517 + Return:
16518 + TRUE if all parameters are OK, FALSE otherwise
16519 + ==========================================================================
16520 + */
16521 +BOOLEAN MlmeAuthReqSanity(
16522 + IN PRTMP_ADAPTER pAd,
16523 + IN VOID *Msg,
16524 + IN ULONG MsgLen,
16525 + OUT PUCHAR pAddr,
16526 + OUT ULONG *pTimeout,
16527 + OUT USHORT *pAlg)
16528 +{
16529 + MLME_AUTH_REQ_STRUCT *pInfo;
16530 +
16531 + pInfo = (MLME_AUTH_REQ_STRUCT *)Msg;
16532 + COPY_MAC_ADDR(pAddr, pInfo->Addr);
16533 + *pTimeout = pInfo->Timeout;
16534 + *pAlg = pInfo->Alg;
16535 +
16536 + if (((*pAlg == Ndis802_11AuthModeShared) ||(*pAlg == Ndis802_11AuthModeOpen)
16537 +#ifdef LEAP_SUPPORT
16538 + || (*pAlg == CISCO_AuthModeLEAP)
16539 +#endif // LEAP_SUPPORT //
16540 + ) &&
16541 + ((*pAddr & 0x01) == 0))
16542 + {
16543 + return TRUE;
16544 + }
16545 + else
16546 + {
16547 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeAuthReqSanity fail - wrong algorithm\n"));
16548 + return FALSE;
16549 + }
16550 +}
16551 +
16552 +/*
16553 + ==========================================================================
16554 + Description:
16555 + MLME message sanity check
16556 + Return:
16557 + TRUE if all parameters are OK, FALSE otherwise
16558 +
16559 + IRQL = DISPATCH_LEVEL
16560 +
16561 + ==========================================================================
16562 + */
16563 +BOOLEAN MlmeAssocReqSanity(
16564 + IN PRTMP_ADAPTER pAd,
16565 + IN VOID *Msg,
16566 + IN ULONG MsgLen,
16567 + OUT PUCHAR pApAddr,
16568 + OUT USHORT *pCapabilityInfo,
16569 + OUT ULONG *pTimeout,
16570 + OUT USHORT *pListenIntv)
16571 +{
16572 + MLME_ASSOC_REQ_STRUCT *pInfo;
16573 +
16574 + pInfo = (MLME_ASSOC_REQ_STRUCT *)Msg;
16575 + *pTimeout = pInfo->Timeout; // timeout
16576 + COPY_MAC_ADDR(pApAddr, pInfo->Addr); // AP address
16577 + *pCapabilityInfo = pInfo->CapabilityInfo; // capability info
16578 + *pListenIntv = pInfo->ListenIntv;
16579 +
16580 + return TRUE;
16581 +}
16582 +
16583 +/*
16584 + ==========================================================================
16585 + Description:
16586 + MLME message sanity check
16587 + Return:
16588 + TRUE if all parameters are OK, FALSE otherwise
16589 +
16590 + IRQL = DISPATCH_LEVEL
16591 +
16592 + ==========================================================================
16593 + */
16594 +BOOLEAN PeerDisassocSanity(
16595 + IN PRTMP_ADAPTER pAd,
16596 + IN VOID *Msg,
16597 + IN ULONG MsgLen,
16598 + OUT PUCHAR pAddr2,
16599 + OUT USHORT *pReason)
16600 +{
16601 + PFRAME_802_11 pFrame = (PFRAME_802_11)Msg;
16602 +
16603 + COPY_MAC_ADDR(pAddr2, pFrame->Hdr.Addr2);
16604 + NdisMoveMemory(pReason, &pFrame->Octet[0], 2);
16605 +
16606 + return TRUE;
16607 +}
16608 +
16609 +/*
16610 + ========================================================================
16611 + Routine Description:
16612 + Sanity check NetworkType (11b, 11g or 11a)
16613 +
16614 + Arguments:
16615 + pBss - Pointer to BSS table.
16616 +
16617 + Return Value:
16618 + Ndis802_11DS .......(11b)
16619 + Ndis802_11OFDM24....(11g)
16620 + Ndis802_11OFDM5.....(11a)
16621 +
16622 + IRQL = DISPATCH_LEVEL
16623 +
16624 + ========================================================================
16625 +*/
16626 +NDIS_802_11_NETWORK_TYPE NetworkTypeInUseSanity(
16627 + IN PBSS_ENTRY pBss)
16628 +{
16629 + NDIS_802_11_NETWORK_TYPE NetWorkType;
16630 + UCHAR rate, i;
16631 +
16632 + NetWorkType = Ndis802_11DS;
16633 +
16634 + if (pBss->Channel <= 14)
16635 + {
16636 + //
16637 + // First check support Rate.
16638 + //
16639 + for (i = 0; i < pBss->SupRateLen; i++)
16640 + {
16641 + rate = pBss->SupRate[i] & 0x7f; // Mask out basic rate set bit
16642 + if ((rate == 2) || (rate == 4) || (rate == 11) || (rate == 22))
16643 + {
16644 + continue;
16645 + }
16646 + else
16647 + {
16648 + //
16649 + // Otherwise (even rate > 108) means Ndis802_11OFDM24
16650 + //
16651 + NetWorkType = Ndis802_11OFDM24;
16652 + break;
16653 + }
16654 + }
16655 +
16656 + //
16657 + // Second check Extend Rate.
16658 + //
16659 + if (NetWorkType != Ndis802_11OFDM24)
16660 + {
16661 + for (i = 0; i < pBss->ExtRateLen; i++)
16662 + {
16663 + rate = pBss->SupRate[i] & 0x7f; // Mask out basic rate set bit
16664 + if ((rate == 2) || (rate == 4) || (rate == 11) || (rate == 22))
16665 + {
16666 + continue;
16667 + }
16668 + else
16669 + {
16670 + //
16671 + // Otherwise (even rate > 108) means Ndis802_11OFDM24
16672 + //
16673 + NetWorkType = Ndis802_11OFDM24;
16674 + break;
16675 + }
16676 + }
16677 + }
16678 + }
16679 + else
16680 + {
16681 + NetWorkType = Ndis802_11OFDM5;
16682 + }
16683 +
16684 + if (pBss->HtCapabilityLen != 0)
16685 + {
16686 + if (NetWorkType == Ndis802_11OFDM5)
16687 + NetWorkType = Ndis802_11OFDM5_N;
16688 + else
16689 + NetWorkType = Ndis802_11OFDM24_N;
16690 + }
16691 +
16692 + return NetWorkType;
16693 +}
16694 +
16695 +/*
16696 + ==========================================================================
16697 + Description:
16698 + WPA message sanity check
16699 + Return:
16700 + TRUE if all parameters are OK, FALSE otherwise
16701 + ==========================================================================
16702 + */
16703 +BOOLEAN PeerWpaMessageSanity(
16704 + IN PRTMP_ADAPTER pAd,
16705 + IN PEAPOL_PACKET pMsg,
16706 + IN ULONG MsgLen,
16707 + IN UCHAR MsgType,
16708 + IN MAC_TABLE_ENTRY *pEntry)
16709 +{
16710 + UCHAR mic[LEN_KEY_DESC_MIC], digest[80], KEYDATA[MAX_LEN_OF_RSNIE];
16711 + BOOLEAN bReplayDiff = FALSE;
16712 + BOOLEAN bWPA2 = FALSE;
16713 + KEY_INFO EapolKeyInfo;
16714 + UCHAR GroupKeyIndex = 0;
16715 +
16716 +
16717 + NdisZeroMemory(mic, sizeof(mic));
16718 + NdisZeroMemory(digest, sizeof(digest));
16719 + NdisZeroMemory(KEYDATA, sizeof(KEYDATA));
16720 + NdisZeroMemory((PUCHAR)&EapolKeyInfo, sizeof(EapolKeyInfo));
16721 +
16722 + NdisMoveMemory((PUCHAR)&EapolKeyInfo, (PUCHAR)&pMsg->KeyDesc.KeyInfo, sizeof(KEY_INFO));
16723 +
16724 + *((USHORT *)&EapolKeyInfo) = cpu2le16(*((USHORT *)&EapolKeyInfo));
16725 +
16726 + // Choose WPA2 or not
16727 + if ((pEntry->AuthMode == Ndis802_11AuthModeWPA2) || (pEntry->AuthMode == Ndis802_11AuthModeWPA2PSK))
16728 + bWPA2 = TRUE;
16729 +
16730 + // 0. Check MsgType
16731 + if ((MsgType > EAPOL_GROUP_MSG_2) || (MsgType < EAPOL_PAIR_MSG_1))
16732 + {
16733 + DBGPRINT(RT_DEBUG_ERROR, ("The message type is invalid(%d)! \n", MsgType));
16734 + return FALSE;
16735 + }
16736 +
16737 + // 1. Replay counter check
16738 + if (MsgType == EAPOL_PAIR_MSG_1 || MsgType == EAPOL_PAIR_MSG_3 || MsgType == EAPOL_GROUP_MSG_1) // For supplicant
16739 + {
16740 + // First validate replay counter, only accept message with larger replay counter.
16741 + // Let equal pass, some AP start with all zero replay counter
16742 + UCHAR ZeroReplay[LEN_KEY_DESC_REPLAY];
16743 +
16744 + NdisZeroMemory(ZeroReplay, LEN_KEY_DESC_REPLAY);
16745 + if ((RTMPCompareMemory(pMsg->KeyDesc.ReplayCounter, pEntry->R_Counter, LEN_KEY_DESC_REPLAY) != 1) &&
16746 + (RTMPCompareMemory(pMsg->KeyDesc.ReplayCounter, ZeroReplay, LEN_KEY_DESC_REPLAY) != 0))
16747 + {
16748 + bReplayDiff = TRUE;
16749 + }
16750 + }
16751 + else if (MsgType == EAPOL_PAIR_MSG_2 || MsgType == EAPOL_PAIR_MSG_4 || MsgType == EAPOL_GROUP_MSG_2) // For authenticator
16752 + {
16753 + // check Replay Counter coresponds to MSG from authenticator, otherwise discard
16754 + if (!NdisEqualMemory(pMsg->KeyDesc.ReplayCounter, pEntry->R_Counter, LEN_KEY_DESC_REPLAY))
16755 + {
16756 + bReplayDiff = TRUE;
16757 + }
16758 + }
16759 +
16760 + // Replay Counter different condition
16761 + if (bReplayDiff)
16762 + {
16763 + // send wireless event - for replay counter different
16764 + if (pAd->CommonCfg.bWirelessEvent)
16765 + RTMPSendWirelessEvent(pAd, IW_REPLAY_COUNTER_DIFF_EVENT_FLAG, pEntry->Addr, pEntry->apidx, 0);
16766 +
16767 + if (MsgType < EAPOL_GROUP_MSG_1)
16768 + {
16769 + DBGPRINT(RT_DEBUG_ERROR, ("Replay Counter Different in pairwise msg %d of 4-way handshake!\n", MsgType));
16770 + }
16771 + else
16772 + {
16773 + DBGPRINT(RT_DEBUG_ERROR, ("Replay Counter Different in group msg %d of 2-way handshake!\n", (MsgType - EAPOL_PAIR_MSG_4)));
16774 + }
16775 +
16776 + hex_dump("Receive replay counter ", pMsg->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
16777 + hex_dump("Current replay counter ", pEntry->R_Counter, LEN_KEY_DESC_REPLAY);
16778 + return FALSE;
16779 + }
16780 +
16781 + // 2. Verify MIC except Pairwise Msg1
16782 + if (MsgType != EAPOL_PAIR_MSG_1)
16783 + {
16784 + UCHAR rcvd_mic[LEN_KEY_DESC_MIC];
16785 +
16786 + // Record the received MIC for check later
16787 + NdisMoveMemory(rcvd_mic, pMsg->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
16788 + NdisZeroMemory(pMsg->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
16789 +
16790 + if (pEntry->WepStatus == Ndis802_11Encryption2Enabled) // TKIP
16791 + {
16792 + hmac_md5(pEntry->PTK, LEN_EAP_MICK, (PUCHAR)pMsg, MsgLen, mic);
16793 + }
16794 + else if (pEntry->WepStatus == Ndis802_11Encryption3Enabled) // AES
16795 + {
16796 + HMAC_SHA1((PUCHAR)pMsg, MsgLen, pEntry->PTK, LEN_EAP_MICK, digest);
16797 + NdisMoveMemory(mic, digest, LEN_KEY_DESC_MIC);
16798 + }
16799 +
16800 + if (!NdisEqualMemory(rcvd_mic, mic, LEN_KEY_DESC_MIC))
16801 + {
16802 + // send wireless event - for MIC different
16803 + if (pAd->CommonCfg.bWirelessEvent)
16804 + RTMPSendWirelessEvent(pAd, IW_MIC_DIFF_EVENT_FLAG, pEntry->Addr, pEntry->apidx, 0);
16805 +
16806 + if (MsgType < EAPOL_GROUP_MSG_1)
16807 + {
16808 + DBGPRINT(RT_DEBUG_ERROR, ("MIC Different in pairwise msg %d of 4-way handshake!\n", MsgType));
16809 + }
16810 + else
16811 + {
16812 + DBGPRINT(RT_DEBUG_ERROR, ("MIC Different in group msg %d of 2-way handshake!\n", (MsgType - EAPOL_PAIR_MSG_4)));
16813 + }
16814 +
16815 + hex_dump("Received MIC", rcvd_mic, LEN_KEY_DESC_MIC);
16816 + hex_dump("Desired MIC", mic, LEN_KEY_DESC_MIC);
16817 +
16818 + return FALSE;
16819 + }
16820 + }
16821 +
16822 + // Extract the context of the Key Data field if it exist
16823 + // The field in pairwise_msg_2_WPA1(WPA2) & pairwise_msg_3_WPA1 is un-encrypted.
16824 + // The field in group_msg_1_WPA1(WPA2) & pairwise_msg_3_WPA2 is encrypted.
16825 + if (pMsg->KeyDesc.KeyDataLen[1] > 0)
16826 + {
16827 + // Decrypt this field
16828 + if ((MsgType == EAPOL_PAIR_MSG_3 && bWPA2) || (MsgType == EAPOL_GROUP_MSG_1))
16829 + {
16830 + if(pEntry->WepStatus == Ndis802_11Encryption3Enabled)
16831 + {
16832 + // AES
16833 + AES_GTK_KEY_UNWRAP(&pEntry->PTK[16], KEYDATA, pMsg->KeyDesc.KeyDataLen[1],pMsg->KeyDesc.KeyData);
16834 + }
16835 + else
16836 + {
16837 + INT i;
16838 + UCHAR Key[32];
16839 + // Decrypt TKIP GTK
16840 + // Construct 32 bytes RC4 Key
16841 + NdisMoveMemory(Key, pMsg->KeyDesc.KeyIv, 16);
16842 + NdisMoveMemory(&Key[16], &pEntry->PTK[16], 16);
16843 + ARCFOUR_INIT(&pAd->PrivateInfo.WEPCONTEXT, Key, 32);
16844 + //discard first 256 bytes
16845 + for(i = 0; i < 256; i++)
16846 + ARCFOUR_BYTE(&pAd->PrivateInfo.WEPCONTEXT);
16847 + // Decrypt GTK. Becareful, there is no ICV to check the result is correct or not
16848 + ARCFOUR_DECRYPT(&pAd->PrivateInfo.WEPCONTEXT, KEYDATA, pMsg->KeyDesc.KeyData, pMsg->KeyDesc.KeyDataLen[1]);
16849 + }
16850 +
16851 + if (!bWPA2 && (MsgType == EAPOL_GROUP_MSG_1))
16852 + GroupKeyIndex = EapolKeyInfo.KeyIndex;
16853 +
16854 + }
16855 + else if ((MsgType == EAPOL_PAIR_MSG_2) || (MsgType == EAPOL_PAIR_MSG_3 && !bWPA2))
16856 + {
16857 + NdisMoveMemory(KEYDATA, pMsg->KeyDesc.KeyData, pMsg->KeyDesc.KeyDataLen[1]);
16858 + }
16859 + else
16860 + {
16861 +
16862 + return TRUE;
16863 + }
16864 +
16865 + // Parse Key Data field to
16866 + // 1. verify RSN IE for pairwise_msg_2_WPA1(WPA2) ,pairwise_msg_3_WPA1(WPA2)
16867 + // 2. verify KDE format for pairwise_msg_3_WPA2, group_msg_1_WPA2
16868 + // 3. update shared key for pairwise_msg_3_WPA2, group_msg_1_WPA1(WPA2)
16869 + if (!RTMPParseEapolKeyData(pAd, KEYDATA, pMsg->KeyDesc.KeyDataLen[1], GroupKeyIndex, MsgType, bWPA2, pEntry))
16870 + {
16871 + return FALSE;
16872 + }
16873 + }
16874 +
16875 + return TRUE;
16876 +
16877 +}
16878 +
16879 +#ifdef CONFIG_STA_SUPPORT
16880 +#ifdef QOS_DLS_SUPPORT
16881 +BOOLEAN MlmeDlsReqSanity(
16882 + IN PRTMP_ADAPTER pAd,
16883 + IN VOID *Msg,
16884 + IN ULONG MsgLen,
16885 + OUT PRT_802_11_DLS *pDLS,
16886 + OUT PUSHORT pReason)
16887 +{
16888 + MLME_DLS_REQ_STRUCT *pInfo;
16889 +
16890 + pInfo = (MLME_DLS_REQ_STRUCT *)Msg;
16891 +
16892 + *pDLS = pInfo->pDLS;
16893 + *pReason = pInfo->Reason;
16894 +
16895 + return TRUE;
16896 +}
16897 +#endif // QOS_DLS_SUPPORT //
16898 +#endif // CONFIG_STA_SUPPORT //
16899 +
16900 +#ifdef QOS_DLS_SUPPORT
16901 +BOOLEAN PeerDlsReqSanity(
16902 + IN PRTMP_ADAPTER pAd,
16903 + IN VOID *Msg,
16904 + IN ULONG MsgLen,
16905 + OUT PUCHAR pDA,
16906 + OUT PUCHAR pSA,
16907 + OUT USHORT *pCapabilityInfo,
16908 + OUT USHORT *pDlsTimeout,
16909 + OUT UCHAR *pRatesLen,
16910 + OUT UCHAR Rates[],
16911 + OUT UCHAR *pHtCapabilityLen,
16912 + OUT HT_CAPABILITY_IE *pHtCapability)
16913 +{
16914 + CHAR *Ptr;
16915 + PFRAME_802_11 Fr = (PFRAME_802_11)Msg;
16916 + PEID_STRUCT eid_ptr;
16917 +
16918 + // to prevent caller from using garbage output value
16919 + *pCapabilityInfo = 0;
16920 + *pDlsTimeout = 0;
16921 + *pHtCapabilityLen = 0;
16922 +
16923 + Ptr = Fr->Octet;
16924 +
16925 + // offset to destination MAC address (Category and Action field)
16926 + Ptr += 2;
16927 +
16928 + // get DA from payload and advance the pointer
16929 + NdisMoveMemory(pDA, Ptr, MAC_ADDR_LEN);
16930 + Ptr += MAC_ADDR_LEN;
16931 +
16932 + // get SA from payload and advance the pointer
16933 + NdisMoveMemory(pSA, Ptr, MAC_ADDR_LEN);
16934 + Ptr += MAC_ADDR_LEN;
16935 +
16936 + // get capability info from payload and advance the pointer
16937 + NdisMoveMemory(pCapabilityInfo, Ptr, 2);
16938 + Ptr += 2;
16939 +
16940 + // get capability info from payload and advance the pointer
16941 + NdisMoveMemory(pDlsTimeout, Ptr, 2);
16942 + Ptr += 2;
16943 +
16944 + // Category and Action field + DA + SA + capability + Timeout
16945 + eid_ptr = (PEID_STRUCT) &Fr->Octet[18];
16946 +
16947 + while (((UCHAR*)eid_ptr + eid_ptr->Len + 1) < ((UCHAR*)Fr + MsgLen))
16948 + {
16949 + switch(eid_ptr->Eid)
16950 + {
16951 + case IE_SUPP_RATES:
16952 + if ((eid_ptr->Len <= MAX_LEN_OF_SUPPORTED_RATES) && (eid_ptr->Len > 0))
16953 + {
16954 + NdisMoveMemory(Rates, eid_ptr->Octet, eid_ptr->Len);
16955 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsReqSanity - IE_SUPP_RATES., Len=%d. Rates[0]=%x\n",eid_ptr->Len, Rates[0]));
16956 + DBGPRINT(RT_DEBUG_TRACE, ("Rates[1]=%x %x %x %x %x %x %x\n", Rates[1], Rates[2], Rates[3], Rates[4], Rates[5], Rates[6], Rates[7]));
16957 + *pRatesLen = eid_ptr->Len;
16958 + }
16959 + else
16960 + {
16961 + *pRatesLen = 8;
16962 + Rates[0] = 0x82;
16963 + Rates[1] = 0x84;
16964 + Rates[2] = 0x8b;
16965 + Rates[3] = 0x96;
16966 + Rates[4] = 0x12;
16967 + Rates[5] = 0x24;
16968 + Rates[6] = 0x48;
16969 + Rates[7] = 0x6c;
16970 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsReqSanity - wrong IE_SUPP_RATES., Len=%d\n",eid_ptr->Len));
16971 + }
16972 + break;
16973 +
16974 + case IE_EXT_SUPP_RATES:
16975 + if (eid_ptr->Len + *pRatesLen <= MAX_LEN_OF_SUPPORTED_RATES)
16976 + {
16977 + NdisMoveMemory(&Rates[*pRatesLen], eid_ptr->Octet, eid_ptr->Len);
16978 + *pRatesLen = (*pRatesLen) + eid_ptr->Len;
16979 + }
16980 + else
16981 + {
16982 + NdisMoveMemory(&Rates[*pRatesLen], eid_ptr->Octet, MAX_LEN_OF_SUPPORTED_RATES - (*pRatesLen));
16983 + *pRatesLen = MAX_LEN_OF_SUPPORTED_RATES;
16984 + }
16985 + break;
16986 +
16987 + case IE_HT_CAP:
16988 + if (eid_ptr->Len >= sizeof(HT_CAPABILITY_IE))
16989 + {
16990 + NdisMoveMemory(pHtCapability, eid_ptr->Octet, sizeof(HT_CAPABILITY_IE));
16991 +
16992 + *(USHORT *)(&pHtCapability->HtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->HtCapInfo));
16993 + *(USHORT *)(&pHtCapability->ExtHtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->ExtHtCapInfo));
16994 + *pHtCapabilityLen = sizeof(HT_CAPABILITY_IE);
16995 +
16996 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsReqSanity - IE_HT_CAP\n"));
16997 + }
16998 + else
16999 + {
17000 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsReqSanity - wrong IE_HT_CAP.eid_ptr->Len = %d\n", eid_ptr->Len));
17001 + }
17002 + break;
17003 +
17004 + default:
17005 + break;
17006 + }
17007 +
17008 + eid_ptr = (PEID_STRUCT)((UCHAR*)eid_ptr + 2 + eid_ptr->Len);
17009 + }
17010 +
17011 + return TRUE;
17012 +}
17013 +
17014 +BOOLEAN PeerDlsRspSanity(
17015 + IN PRTMP_ADAPTER pAd,
17016 + IN VOID *Msg,
17017 + IN ULONG MsgLen,
17018 + OUT PUCHAR pDA,
17019 + OUT PUCHAR pSA,
17020 + OUT USHORT *pCapabilityInfo,
17021 + OUT USHORT *pStatus,
17022 + OUT UCHAR *pRatesLen,
17023 + OUT UCHAR Rates[],
17024 + OUT UCHAR *pHtCapabilityLen,
17025 + OUT HT_CAPABILITY_IE *pHtCapability)
17026 +{
17027 + CHAR *Ptr;
17028 + PFRAME_802_11 Fr = (PFRAME_802_11)Msg;
17029 + PEID_STRUCT eid_ptr;
17030 +
17031 + // to prevent caller from using garbage output value
17032 + *pStatus = 0;
17033 + *pCapabilityInfo = 0;
17034 + *pHtCapabilityLen = 0;
17035 +
17036 + Ptr = Fr->Octet;
17037 +
17038 + // offset to destination MAC address (Category and Action field)
17039 + Ptr += 2;
17040 +
17041 + // get status code from payload and advance the pointer
17042 + NdisMoveMemory(pStatus, Ptr, 2);
17043 + Ptr += 2;
17044 +
17045 + // get DA from payload and advance the pointer
17046 + NdisMoveMemory(pDA, Ptr, MAC_ADDR_LEN);
17047 + Ptr += MAC_ADDR_LEN;
17048 +
17049 + // get SA from payload and advance the pointer
17050 + NdisMoveMemory(pSA, Ptr, MAC_ADDR_LEN);
17051 + Ptr += MAC_ADDR_LEN;
17052 +
17053 + if (pStatus == 0)
17054 + {
17055 + // get capability info from payload and advance the pointer
17056 + NdisMoveMemory(pCapabilityInfo, Ptr, 2);
17057 + Ptr += 2;
17058 + }
17059 +
17060 + // Category and Action field + status code + DA + SA + capability
17061 + eid_ptr = (PEID_STRUCT) &Fr->Octet[18];
17062 +
17063 + while (((UCHAR*)eid_ptr + eid_ptr->Len + 1) < ((UCHAR*)Fr + MsgLen))
17064 + {
17065 + switch(eid_ptr->Eid)
17066 + {
17067 + case IE_SUPP_RATES:
17068 + if ((eid_ptr->Len <= MAX_LEN_OF_SUPPORTED_RATES) && (eid_ptr->Len > 0))
17069 + {
17070 + NdisMoveMemory(Rates, eid_ptr->Octet, eid_ptr->Len);
17071 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsRspSanity - IE_SUPP_RATES., Len=%d. Rates[0]=%x\n",eid_ptr->Len, Rates[0]));
17072 + DBGPRINT(RT_DEBUG_TRACE, ("Rates[1]=%x %x %x %x %x %x %x\n", Rates[1], Rates[2], Rates[3], Rates[4], Rates[5], Rates[6], Rates[7]));
17073 + *pRatesLen = eid_ptr->Len;
17074 + }
17075 + else
17076 + {
17077 + *pRatesLen = 8;
17078 + Rates[0] = 0x82;
17079 + Rates[1] = 0x84;
17080 + Rates[2] = 0x8b;
17081 + Rates[3] = 0x96;
17082 + Rates[4] = 0x12;
17083 + Rates[5] = 0x24;
17084 + Rates[6] = 0x48;
17085 + Rates[7] = 0x6c;
17086 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsRspSanity - wrong IE_SUPP_RATES., Len=%d\n",eid_ptr->Len));
17087 + }
17088 + break;
17089 +
17090 + case IE_EXT_SUPP_RATES:
17091 + if (eid_ptr->Len + *pRatesLen <= MAX_LEN_OF_SUPPORTED_RATES)
17092 + {
17093 + NdisMoveMemory(&Rates[*pRatesLen], eid_ptr->Octet, eid_ptr->Len);
17094 + *pRatesLen = (*pRatesLen) + eid_ptr->Len;
17095 + }
17096 + else
17097 + {
17098 + NdisMoveMemory(&Rates[*pRatesLen], eid_ptr->Octet, MAX_LEN_OF_SUPPORTED_RATES - (*pRatesLen));
17099 + *pRatesLen = MAX_LEN_OF_SUPPORTED_RATES;
17100 + }
17101 + break;
17102 +
17103 + case IE_HT_CAP:
17104 + if (eid_ptr->Len >= sizeof(HT_CAPABILITY_IE))
17105 + {
17106 + NdisMoveMemory(pHtCapability, eid_ptr->Octet, sizeof(HT_CAPABILITY_IE));
17107 +
17108 + *(USHORT *)(&pHtCapability->HtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->HtCapInfo));
17109 + *(USHORT *)(&pHtCapability->ExtHtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->ExtHtCapInfo));
17110 + *pHtCapabilityLen = sizeof(HT_CAPABILITY_IE);
17111 +
17112 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsRspSanity - IE_HT_CAP\n"));
17113 + }
17114 + else
17115 + {
17116 + DBGPRINT(RT_DEBUG_TRACE, ("PeerDlsRspSanity - wrong IE_HT_CAP.eid_ptr->Len = %d\n", eid_ptr->Len));
17117 + }
17118 + break;
17119 +
17120 + default:
17121 + break;
17122 + }
17123 +
17124 + eid_ptr = (PEID_STRUCT)((UCHAR*)eid_ptr + 2 + eid_ptr->Len);
17125 + }
17126 +
17127 + return TRUE;
17128 +}
17129 +
17130 +BOOLEAN PeerDlsTearDownSanity(
17131 + IN PRTMP_ADAPTER pAd,
17132 + IN VOID *Msg,
17133 + IN ULONG MsgLen,
17134 + OUT PUCHAR pDA,
17135 + OUT PUCHAR pSA,
17136 + OUT USHORT *pReason)
17137 +{
17138 + CHAR *Ptr;
17139 + PFRAME_802_11 Fr = (PFRAME_802_11)Msg;
17140 +
17141 + // to prevent caller from using garbage output value
17142 + *pReason = 0;
17143 +
17144 + Ptr = Fr->Octet;
17145 +
17146 + // offset to destination MAC address (Category and Action field)
17147 + Ptr += 2;
17148 +
17149 + // get DA from payload and advance the pointer
17150 + NdisMoveMemory(pDA, Ptr, MAC_ADDR_LEN);
17151 + Ptr += MAC_ADDR_LEN;
17152 +
17153 + // get SA from payload and advance the pointer
17154 + NdisMoveMemory(pSA, Ptr, MAC_ADDR_LEN);
17155 + Ptr += MAC_ADDR_LEN;
17156 +
17157 + // get reason code from payload and advance the pointer
17158 + NdisMoveMemory(pReason, Ptr, 2);
17159 + Ptr += 2;
17160 +
17161 + return TRUE;
17162 +}
17163 +#endif // QOS_DLS_SUPPORT //
17164 +
17165 --- /dev/null
17166 +++ b/drivers/staging/rt2860/common/cmm_sync.c
17167 @@ -0,0 +1,702 @@
17168 +/*
17169 + *************************************************************************
17170 + * Ralink Tech Inc.
17171 + * 5F., No.36, Taiyuan St., Jhubei City,
17172 + * Hsinchu County 302,
17173 + * Taiwan, R.O.C.
17174 + *
17175 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
17176 + *
17177 + * This program is free software; you can redistribute it and/or modify *
17178 + * it under the terms of the GNU General Public License as published by *
17179 + * the Free Software Foundation; either version 2 of the License, or *
17180 + * (at your option) any later version. *
17181 + * *
17182 + * This program is distributed in the hope that it will be useful, *
17183 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
17184 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
17185 + * GNU General Public License for more details. *
17186 + * *
17187 + * You should have received a copy of the GNU General Public License *
17188 + * along with this program; if not, write to the *
17189 + * Free Software Foundation, Inc., *
17190 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
17191 + * *
17192 + *************************************************************************
17193 +
17194 + Module Name:
17195 + sync.c
17196 +
17197 + Abstract:
17198 +
17199 + Revision History:
17200 + Who When What
17201 + -------- ---------- ----------------------------------------------
17202 + John Chang 2004-09-01 modified for rt2561/2661
17203 +*/
17204 +#include "../rt_config.h"
17205 +
17206 +// 2.4 Ghz channel plan index in the TxPower arrays.
17207 +#define BG_BAND_REGION_0_START 0 // 1,2,3,4,5,6,7,8,9,10,11
17208 +#define BG_BAND_REGION_0_SIZE 11
17209 +#define BG_BAND_REGION_1_START 0 // 1,2,3,4,5,6,7,8,9,10,11,12,13
17210 +#define BG_BAND_REGION_1_SIZE 13
17211 +#define BG_BAND_REGION_2_START 9 // 10,11
17212 +#define BG_BAND_REGION_2_SIZE 2
17213 +#define BG_BAND_REGION_3_START 9 // 10,11,12,13
17214 +#define BG_BAND_REGION_3_SIZE 4
17215 +#define BG_BAND_REGION_4_START 13 // 14
17216 +#define BG_BAND_REGION_4_SIZE 1
17217 +#define BG_BAND_REGION_5_START 0 // 1,2,3,4,5,6,7,8,9,10,11,12,13,14
17218 +#define BG_BAND_REGION_5_SIZE 14
17219 +#define BG_BAND_REGION_6_START 2 // 3,4,5,6,7,8,9
17220 +#define BG_BAND_REGION_6_SIZE 7
17221 +#define BG_BAND_REGION_7_START 4 // 5,6,7,8,9,10,11,12,13
17222 +#define BG_BAND_REGION_7_SIZE 9
17223 +#define BG_BAND_REGION_31_START 0 // 1,2,3,4,5,6,7,8,9,10,11,12,13,14
17224 +#define BG_BAND_REGION_31_SIZE 14
17225 +
17226 +// 5 Ghz channel plan index in the TxPower arrays.
17227 +UCHAR A_BAND_REGION_0_CHANNEL_LIST[]={36, 40, 44, 48, 52, 56, 60, 64, 149, 153, 157, 161, 165};
17228 +UCHAR A_BAND_REGION_1_CHANNEL_LIST[]={36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140};
17229 +UCHAR A_BAND_REGION_2_CHANNEL_LIST[]={36, 40, 44, 48, 52, 56, 60, 64};
17230 +UCHAR A_BAND_REGION_3_CHANNEL_LIST[]={52, 56, 60, 64, 149, 153, 157, 161};
17231 +UCHAR A_BAND_REGION_4_CHANNEL_LIST[]={149, 153, 157, 161, 165};
17232 +UCHAR A_BAND_REGION_5_CHANNEL_LIST[]={149, 153, 157, 161};
17233 +UCHAR A_BAND_REGION_6_CHANNEL_LIST[]={36, 40, 44, 48};
17234 +UCHAR A_BAND_REGION_7_CHANNEL_LIST[]={36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140, 149, 153, 157, 161, 165};
17235 +UCHAR A_BAND_REGION_8_CHANNEL_LIST[]={52, 56, 60, 64};
17236 +UCHAR A_BAND_REGION_9_CHANNEL_LIST[]={36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 132, 136, 140, 149, 153, 157, 161, 165};
17237 +UCHAR A_BAND_REGION_10_CHANNEL_LIST[]={36, 40, 44, 48, 149, 153, 157, 161, 165};
17238 +UCHAR A_BAND_REGION_11_CHANNEL_LIST[]={36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 149, 153, 157, 161};
17239 +
17240 +//BaSizeArray follows the 802.11n definition as MaxRxFactor. 2^(13+factor) bytes. When factor =0, it's about Ba buffer size =8.
17241 +UCHAR BaSizeArray[4] = {8,16,32,64};
17242 +
17243 +/*
17244 + ==========================================================================
17245 + Description:
17246 + Update StaCfg->ChannelList[] according to 1) Country Region 2) RF IC type,
17247 + and 3) PHY-mode user selected.
17248 + The outcome is used by driver when doing site survey.
17249 +
17250 + IRQL = PASSIVE_LEVEL
17251 + IRQL = DISPATCH_LEVEL
17252 +
17253 + ==========================================================================
17254 + */
17255 +VOID BuildChannelList(
17256 + IN PRTMP_ADAPTER pAd)
17257 +{
17258 + UCHAR i, j, index=0, num=0;
17259 + PUCHAR pChannelList = NULL;
17260 +
17261 + NdisZeroMemory(pAd->ChannelList, MAX_NUM_OF_CHANNELS * sizeof(CHANNEL_TX_POWER));
17262 +
17263 + // if not 11a-only mode, channel list starts from 2.4Ghz band
17264 + if ((pAd->CommonCfg.PhyMode != PHY_11A)
17265 +#ifdef DOT11_N_SUPPORT
17266 + && (pAd->CommonCfg.PhyMode != PHY_11AN_MIXED) && (pAd->CommonCfg.PhyMode != PHY_11N_5G)
17267 +#endif // DOT11_N_SUPPORT //
17268 + )
17269 + {
17270 + switch (pAd->CommonCfg.CountryRegion & 0x7f)
17271 + {
17272 + case REGION_0_BG_BAND: // 1 -11
17273 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_0_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_0_SIZE);
17274 + index += BG_BAND_REGION_0_SIZE;
17275 + break;
17276 + case REGION_1_BG_BAND: // 1 - 13
17277 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_1_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_1_SIZE);
17278 + index += BG_BAND_REGION_1_SIZE;
17279 + break;
17280 + case REGION_2_BG_BAND: // 10 - 11
17281 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_2_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_2_SIZE);
17282 + index += BG_BAND_REGION_2_SIZE;
17283 + break;
17284 + case REGION_3_BG_BAND: // 10 - 13
17285 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_3_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_3_SIZE);
17286 + index += BG_BAND_REGION_3_SIZE;
17287 + break;
17288 + case REGION_4_BG_BAND: // 14
17289 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_4_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_4_SIZE);
17290 + index += BG_BAND_REGION_4_SIZE;
17291 + break;
17292 + case REGION_5_BG_BAND: // 1 - 14
17293 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_5_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_5_SIZE);
17294 + index += BG_BAND_REGION_5_SIZE;
17295 + break;
17296 + case REGION_6_BG_BAND: // 3 - 9
17297 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_6_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_6_SIZE);
17298 + index += BG_BAND_REGION_6_SIZE;
17299 + break;
17300 + case REGION_7_BG_BAND: // 5 - 13
17301 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_7_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_7_SIZE);
17302 + index += BG_BAND_REGION_7_SIZE;
17303 + break;
17304 + case REGION_31_BG_BAND: // 1 - 14
17305 + NdisMoveMemory(&pAd->ChannelList[index], &pAd->TxPower[BG_BAND_REGION_31_START], sizeof(CHANNEL_TX_POWER) * BG_BAND_REGION_31_SIZE);
17306 + index += BG_BAND_REGION_31_SIZE;
17307 + break;
17308 + default: // Error. should never happen
17309 + break;
17310 + }
17311 + for (i=0; i<index; i++)
17312 + pAd->ChannelList[i].MaxTxPwr = 20;
17313 + }
17314 +
17315 + if ((pAd->CommonCfg.PhyMode == PHY_11A) || (pAd->CommonCfg.PhyMode == PHY_11ABG_MIXED)
17316 +#ifdef DOT11_N_SUPPORT
17317 + || (pAd->CommonCfg.PhyMode == PHY_11ABGN_MIXED) || (pAd->CommonCfg.PhyMode == PHY_11AN_MIXED)
17318 + || (pAd->CommonCfg.PhyMode == PHY_11AGN_MIXED) || (pAd->CommonCfg.PhyMode == PHY_11N_5G)
17319 +#endif // DOT11_N_SUPPORT //
17320 + )
17321 + {
17322 + switch (pAd->CommonCfg.CountryRegionForABand & 0x7f)
17323 + {
17324 + case REGION_0_A_BAND:
17325 + num = sizeof(A_BAND_REGION_0_CHANNEL_LIST)/sizeof(UCHAR);
17326 + pChannelList = A_BAND_REGION_0_CHANNEL_LIST;
17327 + break;
17328 + case REGION_1_A_BAND:
17329 + num = sizeof(A_BAND_REGION_1_CHANNEL_LIST)/sizeof(UCHAR);
17330 + pChannelList = A_BAND_REGION_1_CHANNEL_LIST;
17331 + break;
17332 + case REGION_2_A_BAND:
17333 + num = sizeof(A_BAND_REGION_2_CHANNEL_LIST)/sizeof(UCHAR);
17334 + pChannelList = A_BAND_REGION_2_CHANNEL_LIST;
17335 + break;
17336 + case REGION_3_A_BAND:
17337 + num = sizeof(A_BAND_REGION_3_CHANNEL_LIST)/sizeof(UCHAR);
17338 + pChannelList = A_BAND_REGION_3_CHANNEL_LIST;
17339 + break;
17340 + case REGION_4_A_BAND:
17341 + num = sizeof(A_BAND_REGION_4_CHANNEL_LIST)/sizeof(UCHAR);
17342 + pChannelList = A_BAND_REGION_4_CHANNEL_LIST;
17343 + break;
17344 + case REGION_5_A_BAND:
17345 + num = sizeof(A_BAND_REGION_5_CHANNEL_LIST)/sizeof(UCHAR);
17346 + pChannelList = A_BAND_REGION_5_CHANNEL_LIST;
17347 + break;
17348 + case REGION_6_A_BAND:
17349 + num = sizeof(A_BAND_REGION_6_CHANNEL_LIST)/sizeof(UCHAR);
17350 + pChannelList = A_BAND_REGION_6_CHANNEL_LIST;
17351 + break;
17352 + case REGION_7_A_BAND:
17353 + num = sizeof(A_BAND_REGION_7_CHANNEL_LIST)/sizeof(UCHAR);
17354 + pChannelList = A_BAND_REGION_7_CHANNEL_LIST;
17355 + break;
17356 + case REGION_8_A_BAND:
17357 + num = sizeof(A_BAND_REGION_8_CHANNEL_LIST)/sizeof(UCHAR);
17358 + pChannelList = A_BAND_REGION_8_CHANNEL_LIST;
17359 + break;
17360 + case REGION_9_A_BAND:
17361 + num = sizeof(A_BAND_REGION_9_CHANNEL_LIST)/sizeof(UCHAR);
17362 + pChannelList = A_BAND_REGION_9_CHANNEL_LIST;
17363 + break;
17364 +
17365 + case REGION_10_A_BAND:
17366 + num = sizeof(A_BAND_REGION_10_CHANNEL_LIST)/sizeof(UCHAR);
17367 + pChannelList = A_BAND_REGION_10_CHANNEL_LIST;
17368 + break;
17369 +
17370 + case REGION_11_A_BAND:
17371 + num = sizeof(A_BAND_REGION_11_CHANNEL_LIST)/sizeof(UCHAR);
17372 + pChannelList = A_BAND_REGION_11_CHANNEL_LIST;
17373 + break;
17374 +
17375 + default: // Error. should never happen
17376 + DBGPRINT(RT_DEBUG_WARN,("countryregion=%d not support", pAd->CommonCfg.CountryRegionForABand));
17377 + break;
17378 + }
17379 +
17380 + if (num != 0)
17381 + {
17382 + UCHAR RadarCh[15]={52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140};
17383 + for (i=0; i<num; i++)
17384 + {
17385 + for (j=0; j<MAX_NUM_OF_CHANNELS; j++)
17386 + {
17387 + if (pChannelList[i] == pAd->TxPower[j].Channel)
17388 + NdisMoveMemory(&pAd->ChannelList[index+i], &pAd->TxPower[j], sizeof(CHANNEL_TX_POWER));
17389 + }
17390 + for (j=0; j<15; j++)
17391 + {
17392 + if (pChannelList[i] == RadarCh[j])
17393 + pAd->ChannelList[index+i].DfsReq = TRUE;
17394 + }
17395 + pAd->ChannelList[index+i].MaxTxPwr = 20;
17396 + }
17397 + index += num;
17398 + }
17399 + }
17400 +
17401 + pAd->ChannelListNum = index;
17402 + DBGPRINT(RT_DEBUG_TRACE,("country code=%d/%d, RFIC=%d, PHY mode=%d, support %d channels\n",
17403 + pAd->CommonCfg.CountryRegion, pAd->CommonCfg.CountryRegionForABand, pAd->RfIcType, pAd->CommonCfg.PhyMode, pAd->ChannelListNum));
17404 +#ifdef DBG
17405 + for (i=0;i<pAd->ChannelListNum;i++)
17406 + {
17407 + DBGPRINT_RAW(RT_DEBUG_TRACE,("BuildChannel # %d :: Pwr0 = %d, Pwr1 =%d, \n ", pAd->ChannelList[i].Channel, pAd->ChannelList[i].Power, pAd->ChannelList[i].Power2));
17408 + }
17409 +#endif
17410 +}
17411 +
17412 +/*
17413 + ==========================================================================
17414 + Description:
17415 + This routine return the first channel number according to the country
17416 + code selection and RF IC selection (signal band or dual band). It is called
17417 + whenever driver need to start a site survey of all supported channels.
17418 + Return:
17419 + ch - the first channel number of current country code setting
17420 +
17421 + IRQL = PASSIVE_LEVEL
17422 +
17423 + ==========================================================================
17424 + */
17425 +UCHAR FirstChannel(
17426 + IN PRTMP_ADAPTER pAd)
17427 +{
17428 + return pAd->ChannelList[0].Channel;
17429 +}
17430 +
17431 +/*
17432 + ==========================================================================
17433 + Description:
17434 + This routine returns the next channel number. This routine is called
17435 + during driver need to start a site survey of all supported channels.
17436 + Return:
17437 + next_channel - the next channel number valid in current country code setting.
17438 + Note:
17439 + return 0 if no more next channel
17440 + ==========================================================================
17441 + */
17442 +UCHAR NextChannel(
17443 + IN PRTMP_ADAPTER pAd,
17444 + IN UCHAR channel)
17445 +{
17446 + int i;
17447 + UCHAR next_channel = 0;
17448 +
17449 + for (i = 0; i < (pAd->ChannelListNum - 1); i++)
17450 + if (channel == pAd->ChannelList[i].Channel)
17451 + {
17452 + next_channel = pAd->ChannelList[i+1].Channel;
17453 + break;
17454 + }
17455 + return next_channel;
17456 +}
17457 +
17458 +/*
17459 + ==========================================================================
17460 + Description:
17461 + This routine is for Cisco Compatible Extensions 2.X
17462 + Spec31. AP Control of Client Transmit Power
17463 + Return:
17464 + None
17465 + Note:
17466 + Required by Aironet dBm(mW)
17467 + 0dBm(1mW), 1dBm(5mW), 13dBm(20mW), 15dBm(30mW),
17468 + 17dBm(50mw), 20dBm(100mW)
17469 +
17470 + We supported
17471 + 3dBm(Lowest), 6dBm(10%), 9dBm(25%), 12dBm(50%),
17472 + 14dBm(75%), 15dBm(100%)
17473 +
17474 + The client station's actual transmit power shall be within +/- 5dB of
17475 + the minimum value or next lower value.
17476 + ==========================================================================
17477 + */
17478 +VOID ChangeToCellPowerLimit(
17479 + IN PRTMP_ADAPTER pAd,
17480 + IN UCHAR AironetCellPowerLimit)
17481 +{
17482 + //valud 0xFF means that hasn't found power limit information
17483 + //from the AP's Beacon/Probe response.
17484 + if (AironetCellPowerLimit == 0xFF)
17485 + return;
17486 +
17487 + if (AironetCellPowerLimit < 6) //Used Lowest Power Percentage.
17488 + pAd->CommonCfg.TxPowerPercentage = 6;
17489 + else if (AironetCellPowerLimit < 9)
17490 + pAd->CommonCfg.TxPowerPercentage = 10;
17491 + else if (AironetCellPowerLimit < 12)
17492 + pAd->CommonCfg.TxPowerPercentage = 25;
17493 + else if (AironetCellPowerLimit < 14)
17494 + pAd->CommonCfg.TxPowerPercentage = 50;
17495 + else if (AironetCellPowerLimit < 15)
17496 + pAd->CommonCfg.TxPowerPercentage = 75;
17497 + else
17498 + pAd->CommonCfg.TxPowerPercentage = 100; //else used maximum
17499 +
17500 + if (pAd->CommonCfg.TxPowerPercentage > pAd->CommonCfg.TxPowerDefault)
17501 + pAd->CommonCfg.TxPowerPercentage = pAd->CommonCfg.TxPowerDefault;
17502 +
17503 +}
17504 +
17505 +CHAR ConvertToRssi(
17506 + IN PRTMP_ADAPTER pAd,
17507 + IN CHAR Rssi,
17508 + IN UCHAR RssiNumber)
17509 +{
17510 + UCHAR RssiOffset, LNAGain;
17511 +
17512 + // Rssi equals to zero should be an invalid value
17513 + if (Rssi == 0)
17514 + return -99;
17515 +
17516 + LNAGain = GET_LNA_GAIN(pAd);
17517 + if (pAd->LatchRfRegs.Channel > 14)
17518 + {
17519 + if (RssiNumber == 0)
17520 + RssiOffset = pAd->ARssiOffset0;
17521 + else if (RssiNumber == 1)
17522 + RssiOffset = pAd->ARssiOffset1;
17523 + else
17524 + RssiOffset = pAd->ARssiOffset2;
17525 + }
17526 + else
17527 + {
17528 + if (RssiNumber == 0)
17529 + RssiOffset = pAd->BGRssiOffset0;
17530 + else if (RssiNumber == 1)
17531 + RssiOffset = pAd->BGRssiOffset1;
17532 + else
17533 + RssiOffset = pAd->BGRssiOffset2;
17534 + }
17535 +
17536 + return (-12 - RssiOffset - LNAGain - Rssi);
17537 +}
17538 +
17539 +/*
17540 + ==========================================================================
17541 + Description:
17542 + Scan next channel
17543 + ==========================================================================
17544 + */
17545 +VOID ScanNextChannel(
17546 + IN PRTMP_ADAPTER pAd)
17547 +{
17548 + HEADER_802_11 Hdr80211;
17549 + PUCHAR pOutBuffer = NULL;
17550 + NDIS_STATUS NStatus;
17551 + ULONG FrameLen = 0;
17552 + UCHAR SsidLen = 0, ScanType = pAd->MlmeAux.ScanType, BBPValue = 0;
17553 +#ifdef CONFIG_STA_SUPPORT
17554 + USHORT Status;
17555 + PHEADER_802_11 pHdr80211;
17556 +#endif // CONFIG_STA_SUPPORT //
17557 + UINT ScanTimeIn5gChannel = SHORT_CHANNEL_TIME;
17558 +
17559 +#ifdef CONFIG_STA_SUPPORT
17560 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
17561 + {
17562 + if (MONITOR_ON(pAd))
17563 + return;
17564 + }
17565 +#endif // CONFIG_STA_SUPPORT //
17566 +
17567 +#ifdef RALINK_ATE
17568 + // Nothing to do in ATE mode.
17569 + if (ATE_ON(pAd))
17570 + return;
17571 +#endif // RALINK_ATE //
17572 +
17573 + if (pAd->MlmeAux.Channel == 0)
17574 + {
17575 + if ((pAd->CommonCfg.BBPCurrentBW == BW_40)
17576 +#ifdef CONFIG_STA_SUPPORT
17577 + && (INFRA_ON(pAd)
17578 + || (pAd->OpMode == OPMODE_AP))
17579 +#endif // CONFIG_STA_SUPPORT //
17580 + )
17581 + {
17582 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
17583 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
17584 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
17585 + BBPValue &= (~0x18);
17586 + BBPValue |= 0x10;
17587 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
17588 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to 40MHz channel %d, Total BSS[%02d]\n",pAd->CommonCfg.CentralChannel, pAd->ScanTab.BssNr));
17589 + }
17590 + else
17591 + {
17592 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
17593 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
17594 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to channel %d, Total BSS[%02d]\n",pAd->CommonCfg.Channel, pAd->ScanTab.BssNr));
17595 + }
17596 +
17597 +#ifdef CONFIG_STA_SUPPORT
17598 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
17599 + {
17600 + //
17601 + // To prevent data lost.
17602 + // Send an NULL data with turned PSM bit on to current associated AP before SCAN progress.
17603 + // Now, we need to send an NULL data with turned PSM bit off to AP, when scan progress done
17604 + //
17605 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) && (INFRA_ON(pAd)))
17606 + {
17607 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer);
17608 + if (NStatus == NDIS_STATUS_SUCCESS)
17609 + {
17610 + pHdr80211 = (PHEADER_802_11) pOutBuffer;
17611 + MgtMacHeaderInit(pAd, pHdr80211, SUBTYPE_NULL_FUNC, 1, pAd->CommonCfg.Bssid, pAd->CommonCfg.Bssid);
17612 + pHdr80211->Duration = 0;
17613 + pHdr80211->FC.Type = BTYPE_DATA;
17614 + pHdr80211->FC.PwrMgmt = (pAd->StaCfg.Psm == PWR_SAVE);
17615 +
17616 + // Send using priority queue
17617 + MiniportMMRequest(pAd, 0, pOutBuffer, sizeof(HEADER_802_11));
17618 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeScanReqAction -- Send PSM Data frame\n"));
17619 + MlmeFreeMemory(pAd, pOutBuffer);
17620 + RTMPusecDelay(5000);
17621 + }
17622 + }
17623 +
17624 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
17625 + Status = MLME_SUCCESS;
17626 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_SCAN_CONF, 2, &Status);
17627 + }
17628 +#endif // CONFIG_STA_SUPPORT //
17629 +
17630 +
17631 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS);
17632 + }
17633 + else
17634 + {
17635 +#ifdef CONFIG_STA_SUPPORT
17636 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
17637 + {
17638 + // BBP and RF are not accessible in PS mode, we has to wake them up first
17639 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
17640 + AsicForceWakeup(pAd, TRUE);
17641 +
17642 + // leave PSM during scanning. otherwise we may lost ProbeRsp & BEACON
17643 + if (pAd->StaCfg.Psm == PWR_SAVE)
17644 + MlmeSetPsmBit(pAd, PWR_ACTIVE);
17645 + }
17646 +#endif // CONFIG_STA_SUPPORT //
17647 +
17648 + AsicSwitchChannel(pAd, pAd->MlmeAux.Channel, TRUE);
17649 + AsicLockChannel(pAd, pAd->MlmeAux.Channel);
17650 +
17651 +#ifdef CONFIG_STA_SUPPORT
17652 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
17653 + {
17654 + if (pAd->MlmeAux.Channel > 14)
17655 + {
17656 + if ((pAd->CommonCfg.bIEEE80211H == 1) && RadarChannelCheck(pAd, pAd->MlmeAux.Channel))
17657 + {
17658 + ScanType = SCAN_PASSIVE;
17659 + ScanTimeIn5gChannel = MIN_CHANNEL_TIME;
17660 + }
17661 + }
17662 +
17663 +#ifdef CARRIER_DETECTION_SUPPORT // Roger sync Carrier
17664 + // carrier detection
17665 + if (pAd->CommonCfg.CarrierDetect.Enable == TRUE)
17666 + {
17667 + ScanType = SCAN_PASSIVE;
17668 + ScanTimeIn5gChannel = MIN_CHANNEL_TIME;
17669 + }
17670 +#endif // CARRIER_DETECTION_SUPPORT //
17671 + }
17672 +
17673 +#endif // CONFIG_STA_SUPPORT //
17674 +
17675 + //Global country domain(ch1-11:active scan, ch12-14 passive scan)
17676 + if ((pAd->MlmeAux.Channel <= 14) && (pAd->MlmeAux.Channel >= 12) && ((pAd->CommonCfg.CountryRegion & 0x7f) == REGION_31_BG_BAND))
17677 + {
17678 + ScanType = SCAN_PASSIVE;
17679 + }
17680 +
17681 + // We need to shorten active scan time in order for WZC connect issue
17682 + // Chnage the channel scan time for CISCO stuff based on its IAPP announcement
17683 + if (ScanType == FAST_SCAN_ACTIVE)
17684 + RTMPSetTimer(&pAd->MlmeAux.ScanTimer, FAST_ACTIVE_SCAN_TIME);
17685 +#ifdef CONFIG_STA_SUPPORT
17686 + else if (((ScanType == SCAN_CISCO_ACTIVE) ||
17687 + (ScanType == SCAN_CISCO_PASSIVE) ||
17688 + (ScanType == SCAN_CISCO_CHANNEL_LOAD) ||
17689 + (ScanType == SCAN_CISCO_NOISE)) && (pAd->OpMode == OPMODE_STA))
17690 + {
17691 + if (pAd->StaCfg.CCXScanTime < 25)
17692 + RTMPSetTimer(&pAd->MlmeAux.ScanTimer, pAd->StaCfg.CCXScanTime * 2);
17693 + else
17694 + RTMPSetTimer(&pAd->MlmeAux.ScanTimer, pAd->StaCfg.CCXScanTime);
17695 + }
17696 +#endif // CONFIG_STA_SUPPORT //
17697 + else // must be SCAN_PASSIVE or SCAN_ACTIVE
17698 + {
17699 + if ((pAd->CommonCfg.PhyMode == PHY_11ABG_MIXED)
17700 +#ifdef DOT11_N_SUPPORT
17701 + || (pAd->CommonCfg.PhyMode == PHY_11ABGN_MIXED) || (pAd->CommonCfg.PhyMode == PHY_11AGN_MIXED)
17702 +#endif // DOT11_N_SUPPORT //
17703 + )
17704 + {
17705 + if (pAd->MlmeAux.Channel > 14)
17706 + RTMPSetTimer(&pAd->MlmeAux.ScanTimer, ScanTimeIn5gChannel);
17707 + else
17708 + RTMPSetTimer(&pAd->MlmeAux.ScanTimer, MIN_CHANNEL_TIME);
17709 + }
17710 + else
17711 + RTMPSetTimer(&pAd->MlmeAux.ScanTimer, MAX_CHANNEL_TIME);
17712 + }
17713 +
17714 + if ((ScanType == SCAN_ACTIVE) || (ScanType == FAST_SCAN_ACTIVE) ||
17715 + (ScanType == SCAN_CISCO_ACTIVE))
17716 + {
17717 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
17718 + if (NStatus != NDIS_STATUS_SUCCESS)
17719 + {
17720 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - ScanNextChannel() allocate memory fail\n"));
17721 +#ifdef CONFIG_STA_SUPPORT
17722 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
17723 + {
17724 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
17725 + Status = MLME_FAIL_NO_RESOURCE;
17726 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_SCAN_CONF, 2, &Status);
17727 + }
17728 +#endif // CONFIG_STA_SUPPORT //
17729 +
17730 + return;
17731 + }
17732 +
17733 + // There is no need to send broadcast probe request if active scan is in effect.
17734 + if ((ScanType == SCAN_ACTIVE) || (ScanType == FAST_SCAN_ACTIVE)
17735 + )
17736 + SsidLen = pAd->MlmeAux.SsidLen;
17737 + else
17738 + SsidLen = 0;
17739 +
17740 + MgtMacHeaderInit(pAd, &Hdr80211, SUBTYPE_PROBE_REQ, 0, BROADCAST_ADDR, BROADCAST_ADDR);
17741 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
17742 + sizeof(HEADER_802_11), &Hdr80211,
17743 + 1, &SsidIe,
17744 + 1, &SsidLen,
17745 + SsidLen, pAd->MlmeAux.Ssid,
17746 + 1, &SupRateIe,
17747 + 1, &pAd->CommonCfg.SupRateLen,
17748 + pAd->CommonCfg.SupRateLen, pAd->CommonCfg.SupRate,
17749 + END_OF_ARGS);
17750 +
17751 + if (pAd->CommonCfg.ExtRateLen)
17752 + {
17753 + ULONG Tmp;
17754 + MakeOutgoingFrame(pOutBuffer + FrameLen, &Tmp,
17755 + 1, &ExtRateIe,
17756 + 1, &pAd->CommonCfg.ExtRateLen,
17757 + pAd->CommonCfg.ExtRateLen, pAd->CommonCfg.ExtRate,
17758 + END_OF_ARGS);
17759 + FrameLen += Tmp;
17760 + }
17761 +
17762 +#ifdef DOT11_N_SUPPORT
17763 + if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED)
17764 + {
17765 + ULONG Tmp;
17766 + UCHAR HtLen;
17767 + UCHAR BROADCOM[4] = {0x0, 0x90, 0x4c, 0x33};
17768 +#ifdef RT_BIG_ENDIAN
17769 + HT_CAPABILITY_IE HtCapabilityTmp;
17770 +#endif
17771 + if (pAd->bBroadComHT == TRUE)
17772 + {
17773 + HtLen = pAd->MlmeAux.HtCapabilityLen + 4;
17774 +#ifdef RT_BIG_ENDIAN
17775 + NdisMoveMemory(&HtCapabilityTmp, &pAd->MlmeAux.HtCapability, SIZE_HT_CAP_IE);
17776 + *(USHORT *)(&HtCapabilityTmp.HtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.HtCapInfo));
17777 + *(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo));
17778 +
17779 + MakeOutgoingFrame(pOutBuffer + FrameLen, &Tmp,
17780 + 1, &WpaIe,
17781 + 1, &HtLen,
17782 + 4, &BROADCOM[0],
17783 + pAd->MlmeAux.HtCapabilityLen, &HtCapabilityTmp,
17784 + END_OF_ARGS);
17785 +#else
17786 + MakeOutgoingFrame(pOutBuffer + FrameLen, &Tmp,
17787 + 1, &WpaIe,
17788 + 1, &HtLen,
17789 + 4, &BROADCOM[0],
17790 + pAd->MlmeAux.HtCapabilityLen, &pAd->MlmeAux.HtCapability,
17791 + END_OF_ARGS);
17792 +#endif // RT_BIG_ENDIAN //
17793 + }
17794 + else
17795 + {
17796 + HtLen = pAd->MlmeAux.HtCapabilityLen;
17797 +#ifdef RT_BIG_ENDIAN
17798 + NdisMoveMemory(&HtCapabilityTmp, &pAd->CommonCfg.HtCapability, SIZE_HT_CAP_IE);
17799 + *(USHORT *)(&HtCapabilityTmp.HtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.HtCapInfo));
17800 + *(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo));
17801 +
17802 + MakeOutgoingFrame(pOutBuffer + FrameLen, &Tmp,
17803 + 1, &HtCapIe,
17804 + 1, &HtLen,
17805 + HtLen, &HtCapabilityTmp,
17806 + END_OF_ARGS);
17807 +#else
17808 + MakeOutgoingFrame(pOutBuffer + FrameLen, &Tmp,
17809 + 1, &HtCapIe,
17810 + 1, &HtLen,
17811 + HtLen, &pAd->CommonCfg.HtCapability,
17812 + END_OF_ARGS);
17813 +#endif // RT_BIG_ENDIAN //
17814 + }
17815 + FrameLen += Tmp;
17816 +
17817 +#ifdef DOT11N_DRAFT3
17818 + if (pAd->CommonCfg.BACapability.field.b2040CoexistScanSup == 1)
17819 + {
17820 + ULONG Tmp;
17821 + HtLen = 1;
17822 + MakeOutgoingFrame(pOutBuffer + FrameLen, &Tmp,
17823 + 1, &ExtHtCapIe,
17824 + 1, &HtLen,
17825 + 1, &pAd->CommonCfg.BSSCoexist2040.word,
17826 + END_OF_ARGS);
17827 +
17828 + FrameLen += Tmp;
17829 + }
17830 +#endif // DOT11N_DRAFT3 //
17831 + }
17832 +#endif // DOT11_N_SUPPORT //
17833 +
17834 +
17835 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
17836 + MlmeFreeMemory(pAd, pOutBuffer);
17837 + }
17838 +
17839 + // For SCAN_CISCO_PASSIVE, do nothing and silently wait for beacon or other probe reponse
17840 +
17841 +#ifdef CONFIG_STA_SUPPORT
17842 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
17843 + pAd->Mlme.SyncMachine.CurrState = SCAN_LISTEN;
17844 +#endif // CONFIG_STA_SUPPORT //
17845 +
17846 + }
17847 +}
17848 +
17849 +VOID MgtProbReqMacHeaderInit(
17850 + IN PRTMP_ADAPTER pAd,
17851 + IN OUT PHEADER_802_11 pHdr80211,
17852 + IN UCHAR SubType,
17853 + IN UCHAR ToDs,
17854 + IN PUCHAR pDA,
17855 + IN PUCHAR pBssid)
17856 +{
17857 + NdisZeroMemory(pHdr80211, sizeof(HEADER_802_11));
17858 +
17859 + pHdr80211->FC.Type = BTYPE_MGMT;
17860 + pHdr80211->FC.SubType = SubType;
17861 + if (SubType == SUBTYPE_ACK)
17862 + pHdr80211->FC.Type = BTYPE_CNTL;
17863 + pHdr80211->FC.ToDs = ToDs;
17864 + COPY_MAC_ADDR(pHdr80211->Addr1, pDA);
17865 + COPY_MAC_ADDR(pHdr80211->Addr2, pAd->CurrentAddress);
17866 + COPY_MAC_ADDR(pHdr80211->Addr3, pBssid);
17867 +}
17868 +
17869 +
17870 --- /dev/null
17871 +++ b/drivers/staging/rt2860/common/cmm_wpa.c
17872 @@ -0,0 +1,1606 @@
17873 +/*
17874 + *************************************************************************
17875 + * Ralink Tech Inc.
17876 + * 5F., No.36, Taiyuan St., Jhubei City,
17877 + * Hsinchu County 302,
17878 + * Taiwan, R.O.C.
17879 + *
17880 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
17881 + *
17882 + * This program is free software; you can redistribute it and/or modify *
17883 + * it under the terms of the GNU General Public License as published by *
17884 + * the Free Software Foundation; either version 2 of the License, or *
17885 + * (at your option) any later version. *
17886 + * *
17887 + * This program is distributed in the hope that it will be useful, *
17888 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
17889 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
17890 + * GNU General Public License for more details. *
17891 + * *
17892 + * You should have received a copy of the GNU General Public License *
17893 + * along with this program; if not, write to the *
17894 + * Free Software Foundation, Inc., *
17895 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
17896 + * *
17897 + *************************************************************************
17898 +
17899 + Module Name:
17900 + wpa.c
17901 +
17902 + Abstract:
17903 +
17904 + Revision History:
17905 + Who When What
17906 + -------- ---------- ----------------------------------------------
17907 + Jan Lee 03-07-22 Initial
17908 + Paul Lin 03-11-28 Modify for supplicant
17909 +*/
17910 +#include "../rt_config.h"
17911 +// WPA OUI
17912 +UCHAR OUI_WPA_NONE_AKM[4] = {0x00, 0x50, 0xF2, 0x00};
17913 +UCHAR OUI_WPA_VERSION[4] = {0x00, 0x50, 0xF2, 0x01};
17914 +UCHAR OUI_WPA_TKIP[4] = {0x00, 0x50, 0xF2, 0x02};
17915 +UCHAR OUI_WPA_CCMP[4] = {0x00, 0x50, 0xF2, 0x04};
17916 +UCHAR OUI_WPA_8021X_AKM[4] = {0x00, 0x50, 0xF2, 0x01};
17917 +UCHAR OUI_WPA_PSK_AKM[4] = {0x00, 0x50, 0xF2, 0x02};
17918 +// WPA2 OUI
17919 +UCHAR OUI_WPA2_WEP40[4] = {0x00, 0x0F, 0xAC, 0x01};
17920 +UCHAR OUI_WPA2_TKIP[4] = {0x00, 0x0F, 0xAC, 0x02};
17921 +UCHAR OUI_WPA2_CCMP[4] = {0x00, 0x0F, 0xAC, 0x04};
17922 +UCHAR OUI_WPA2_8021X_AKM[4] = {0x00, 0x0F, 0xAC, 0x01};
17923 +UCHAR OUI_WPA2_PSK_AKM[4] = {0x00, 0x0F, 0xAC, 0x02};
17924 +// MSA OUI
17925 +UCHAR OUI_MSA_8021X_AKM[4] = {0x00, 0x0F, 0xAC, 0x05}; // Not yet final - IEEE 802.11s-D1.06
17926 +UCHAR OUI_MSA_PSK_AKM[4] = {0x00, 0x0F, 0xAC, 0x06}; // Not yet final - IEEE 802.11s-D1.06
17927 +
17928 +/*
17929 + ========================================================================
17930 +
17931 + Routine Description:
17932 + The pseudo-random function(PRF) that hashes various inputs to
17933 + derive a pseudo-random value. To add liveness to the pseudo-random
17934 + value, a nonce should be one of the inputs.
17935 +
17936 + It is used to generate PTK, GTK or some specific random value.
17937 +
17938 + Arguments:
17939 + UCHAR *key, - the key material for HMAC_SHA1 use
17940 + INT key_len - the length of key
17941 + UCHAR *prefix - a prefix label
17942 + INT prefix_len - the length of the label
17943 + UCHAR *data - a specific data with variable length
17944 + INT data_len - the length of a specific data
17945 + INT len - the output lenght
17946 +
17947 + Return Value:
17948 + UCHAR *output - the calculated result
17949 +
17950 + Note:
17951 + 802.11i-2004 Annex H.3
17952 +
17953 + ========================================================================
17954 +*/
17955 +VOID PRF(
17956 + IN UCHAR *key,
17957 + IN INT key_len,
17958 + IN UCHAR *prefix,
17959 + IN INT prefix_len,
17960 + IN UCHAR *data,
17961 + IN INT data_len,
17962 + OUT UCHAR *output,
17963 + IN INT len)
17964 +{
17965 + INT i;
17966 + UCHAR *input;
17967 + INT currentindex = 0;
17968 + INT total_len;
17969 +
17970 + // Allocate memory for input
17971 + os_alloc_mem(NULL, (PUCHAR *)&input, 1024);
17972 +
17973 + if (input == NULL)
17974 + {
17975 + DBGPRINT(RT_DEBUG_ERROR, ("!!!PRF: no memory!!!\n"));
17976 + return;
17977 + }
17978 +
17979 + // Generate concatenation input
17980 + NdisMoveMemory(input, prefix, prefix_len);
17981 +
17982 + // Concatenate a single octet containing 0
17983 + input[prefix_len] = 0;
17984 +
17985 + // Concatenate specific data
17986 + NdisMoveMemory(&input[prefix_len + 1], data, data_len);
17987 + total_len = prefix_len + 1 + data_len;
17988 +
17989 + // Concatenate a single octet containing 0
17990 + // This octet shall be update later
17991 + input[total_len] = 0;
17992 + total_len++;
17993 +
17994 + // Iterate to calculate the result by hmac-sha-1
17995 + // Then concatenate to last result
17996 + for (i = 0; i < (len + 19) / 20; i++)
17997 + {
17998 + HMAC_SHA1(input, total_len, key, key_len, &output[currentindex]);
17999 + currentindex += 20;
18000 +
18001 + // update the last octet
18002 + input[total_len - 1]++;
18003 + }
18004 + os_free_mem(NULL, input);
18005 +}
18006 +
18007 +/*
18008 + ========================================================================
18009 +
18010 + Routine Description:
18011 + It utilizes PRF-384 or PRF-512 to derive session-specific keys from a PMK.
18012 + It shall be called by 4-way handshake processing.
18013 +
18014 + Arguments:
18015 + pAd - pointer to our pAdapter context
18016 + PMK - pointer to PMK
18017 + ANonce - pointer to ANonce
18018 + AA - pointer to Authenticator Address
18019 + SNonce - pointer to SNonce
18020 + SA - pointer to Supplicant Address
18021 + len - indicate the length of PTK (octet)
18022 +
18023 + Return Value:
18024 + Output pointer to the PTK
18025 +
18026 + Note:
18027 + Refer to IEEE 802.11i-2004 8.5.1.2
18028 +
18029 + ========================================================================
18030 +*/
18031 +VOID WpaCountPTK(
18032 + IN PRTMP_ADAPTER pAd,
18033 + IN UCHAR *PMK,
18034 + IN UCHAR *ANonce,
18035 + IN UCHAR *AA,
18036 + IN UCHAR *SNonce,
18037 + IN UCHAR *SA,
18038 + OUT UCHAR *output,
18039 + IN UINT len)
18040 +{
18041 + UCHAR concatenation[76];
18042 + UINT CurrPos = 0;
18043 + UCHAR temp[32];
18044 + UCHAR Prefix[] = {'P', 'a', 'i', 'r', 'w', 'i', 's', 'e', ' ', 'k', 'e', 'y', ' ',
18045 + 'e', 'x', 'p', 'a', 'n', 's', 'i', 'o', 'n'};
18046 +
18047 + // initiate the concatenation input
18048 + NdisZeroMemory(temp, sizeof(temp));
18049 + NdisZeroMemory(concatenation, 76);
18050 +
18051 + // Get smaller address
18052 + if (RTMPCompareMemory(SA, AA, 6) == 1)
18053 + NdisMoveMemory(concatenation, AA, 6);
18054 + else
18055 + NdisMoveMemory(concatenation, SA, 6);
18056 + CurrPos += 6;
18057 +
18058 + // Get larger address
18059 + if (RTMPCompareMemory(SA, AA, 6) == 1)
18060 + NdisMoveMemory(&concatenation[CurrPos], SA, 6);
18061 + else
18062 + NdisMoveMemory(&concatenation[CurrPos], AA, 6);
18063 +
18064 + // store the larger mac address for backward compatible of
18065 + // ralink proprietary STA-key issue
18066 + NdisMoveMemory(temp, &concatenation[CurrPos], MAC_ADDR_LEN);
18067 + CurrPos += 6;
18068 +
18069 + // Get smaller Nonce
18070 + if (RTMPCompareMemory(ANonce, SNonce, 32) == 0)
18071 + NdisMoveMemory(&concatenation[CurrPos], temp, 32); // patch for ralink proprietary STA-key issue
18072 + else if (RTMPCompareMemory(ANonce, SNonce, 32) == 1)
18073 + NdisMoveMemory(&concatenation[CurrPos], SNonce, 32);
18074 + else
18075 + NdisMoveMemory(&concatenation[CurrPos], ANonce, 32);
18076 + CurrPos += 32;
18077 +
18078 + // Get larger Nonce
18079 + if (RTMPCompareMemory(ANonce, SNonce, 32) == 0)
18080 + NdisMoveMemory(&concatenation[CurrPos], temp, 32); // patch for ralink proprietary STA-key issue
18081 + else if (RTMPCompareMemory(ANonce, SNonce, 32) == 1)
18082 + NdisMoveMemory(&concatenation[CurrPos], ANonce, 32);
18083 + else
18084 + NdisMoveMemory(&concatenation[CurrPos], SNonce, 32);
18085 + CurrPos += 32;
18086 +
18087 + hex_dump("concatenation=", concatenation, 76);
18088 +
18089 + // Use PRF to generate PTK
18090 + PRF(PMK, LEN_MASTER_KEY, Prefix, 22, concatenation, 76, output, len);
18091 +
18092 +}
18093 +
18094 +/*
18095 + ========================================================================
18096 +
18097 + Routine Description:
18098 + Generate random number by software.
18099 +
18100 + Arguments:
18101 + pAd - pointer to our pAdapter context
18102 + macAddr - pointer to local MAC address
18103 +
18104 + Return Value:
18105 +
18106 + Note:
18107 + 802.1ii-2004 Annex H.5
18108 +
18109 + ========================================================================
18110 +*/
18111 +VOID GenRandom(
18112 + IN PRTMP_ADAPTER pAd,
18113 + IN UCHAR *macAddr,
18114 + OUT UCHAR *random)
18115 +{
18116 + INT i, curr;
18117 + UCHAR local[80], KeyCounter[32];
18118 + UCHAR result[80];
18119 + ULONG CurrentTime;
18120 + UCHAR prefix[] = {'I', 'n', 'i', 't', ' ', 'C', 'o', 'u', 'n', 't', 'e', 'r'};
18121 +
18122 + // Zero the related information
18123 + NdisZeroMemory(result, 80);
18124 + NdisZeroMemory(local, 80);
18125 + NdisZeroMemory(KeyCounter, 32);
18126 +
18127 + for (i = 0; i < 32; i++)
18128 + {
18129 + // copy the local MAC address
18130 + COPY_MAC_ADDR(local, macAddr);
18131 + curr = MAC_ADDR_LEN;
18132 +
18133 + // concatenate the current time
18134 + NdisGetSystemUpTime(&CurrentTime);
18135 + NdisMoveMemory(&local[curr], &CurrentTime, sizeof(CurrentTime));
18136 + curr += sizeof(CurrentTime);
18137 +
18138 + // concatenate the last result
18139 + NdisMoveMemory(&local[curr], result, 32);
18140 + curr += 32;
18141 +
18142 + // concatenate a variable
18143 + NdisMoveMemory(&local[curr], &i, 2);
18144 + curr += 2;
18145 +
18146 + // calculate the result
18147 + PRF(KeyCounter, 32, prefix,12, local, curr, result, 32);
18148 + }
18149 +
18150 + NdisMoveMemory(random, result, 32);
18151 +}
18152 +
18153 +/*
18154 + ========================================================================
18155 +
18156 + Routine Description:
18157 + Build cipher suite in RSN-IE.
18158 + It only shall be called by RTMPMakeRSNIE.
18159 +
18160 + Arguments:
18161 + pAd - pointer to our pAdapter context
18162 + ElementID - indicate the WPA1 or WPA2
18163 + WepStatus - indicate the encryption type
18164 + bMixCipher - a boolean to indicate the pairwise cipher and group
18165 + cipher are the same or not
18166 +
18167 + Return Value:
18168 +
18169 + Note:
18170 +
18171 + ========================================================================
18172 +*/
18173 +static VOID RTMPInsertRsnIeCipher(
18174 + IN PRTMP_ADAPTER pAd,
18175 + IN UCHAR ElementID,
18176 + IN UINT WepStatus,
18177 + IN BOOLEAN bMixCipher,
18178 + IN UCHAR FlexibleCipher,
18179 + OUT PUCHAR pRsnIe,
18180 + OUT UCHAR *rsn_len)
18181 +{
18182 + UCHAR PairwiseCnt;
18183 +
18184 + *rsn_len = 0;
18185 +
18186 + // decide WPA2 or WPA1
18187 + if (ElementID == Wpa2Ie)
18188 + {
18189 + RSNIE2 *pRsnie_cipher = (RSNIE2*)pRsnIe;
18190 +
18191 + // Assign the verson as 1
18192 + pRsnie_cipher->version = 1;
18193 +
18194 + switch (WepStatus)
18195 + {
18196 + // TKIP mode
18197 + case Ndis802_11Encryption2Enabled:
18198 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA2_TKIP, 4);
18199 + pRsnie_cipher->ucount = 1;
18200 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA2_TKIP, 4);
18201 + *rsn_len = sizeof(RSNIE2);
18202 + break;
18203 +
18204 + // AES mode
18205 + case Ndis802_11Encryption3Enabled:
18206 + if (bMixCipher)
18207 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA2_TKIP, 4);
18208 + else
18209 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA2_CCMP, 4);
18210 + pRsnie_cipher->ucount = 1;
18211 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA2_CCMP, 4);
18212 + *rsn_len = sizeof(RSNIE2);
18213 + break;
18214 +
18215 + // TKIP-AES mix mode
18216 + case Ndis802_11Encryption4Enabled:
18217 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA2_TKIP, 4);
18218 +
18219 + PairwiseCnt = 1;
18220 + // Insert WPA2 TKIP as the first pairwise cipher
18221 + if (MIX_CIPHER_WPA2_TKIP_ON(FlexibleCipher))
18222 + {
18223 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA2_TKIP, 4);
18224 + // Insert WPA2 AES as the secondary pairwise cipher
18225 + if (MIX_CIPHER_WPA2_AES_ON(FlexibleCipher))
18226 + {
18227 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui + 4, OUI_WPA2_CCMP, 4);
18228 + PairwiseCnt = 2;
18229 + }
18230 + }
18231 + else
18232 + {
18233 + // Insert WPA2 AES as the first pairwise cipher
18234 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA2_CCMP, 4);
18235 + }
18236 +
18237 + pRsnie_cipher->ucount = PairwiseCnt;
18238 + *rsn_len = sizeof(RSNIE2) + (4 * (PairwiseCnt - 1));
18239 + break;
18240 + }
18241 +
18242 + // swap for big-endian platform
18243 + pRsnie_cipher->version = cpu2le16(pRsnie_cipher->version);
18244 + pRsnie_cipher->ucount = cpu2le16(pRsnie_cipher->ucount);
18245 + }
18246 + else
18247 + {
18248 + RSNIE *pRsnie_cipher = (RSNIE*)pRsnIe;
18249 +
18250 + // Assign OUI and version
18251 + NdisMoveMemory(pRsnie_cipher->oui, OUI_WPA_VERSION, 4);
18252 + pRsnie_cipher->version = 1;
18253 +
18254 + switch (WepStatus)
18255 + {
18256 + // TKIP mode
18257 + case Ndis802_11Encryption2Enabled:
18258 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA_TKIP, 4);
18259 + pRsnie_cipher->ucount = 1;
18260 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA_TKIP, 4);
18261 + *rsn_len = sizeof(RSNIE);
18262 + break;
18263 +
18264 + // AES mode
18265 + case Ndis802_11Encryption3Enabled:
18266 + if (bMixCipher)
18267 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA_TKIP, 4);
18268 + else
18269 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA_CCMP, 4);
18270 + pRsnie_cipher->ucount = 1;
18271 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA_CCMP, 4);
18272 + *rsn_len = sizeof(RSNIE);
18273 + break;
18274 +
18275 + // TKIP-AES mix mode
18276 + case Ndis802_11Encryption4Enabled:
18277 + NdisMoveMemory(pRsnie_cipher->mcast, OUI_WPA_TKIP, 4);
18278 +
18279 + PairwiseCnt = 1;
18280 + // Insert WPA TKIP as the first pairwise cipher
18281 + if (MIX_CIPHER_WPA_TKIP_ON(FlexibleCipher))
18282 + {
18283 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA_TKIP, 4);
18284 + // Insert WPA AES as the secondary pairwise cipher
18285 + if (MIX_CIPHER_WPA_AES_ON(FlexibleCipher))
18286 + {
18287 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui + 4, OUI_WPA_CCMP, 4);
18288 + PairwiseCnt = 2;
18289 + }
18290 + }
18291 + else
18292 + {
18293 + // Insert WPA AES as the first pairwise cipher
18294 + NdisMoveMemory(pRsnie_cipher->ucast[0].oui, OUI_WPA_CCMP, 4);
18295 + }
18296 +
18297 + pRsnie_cipher->ucount = PairwiseCnt;
18298 + *rsn_len = sizeof(RSNIE) + (4 * (PairwiseCnt - 1));
18299 + break;
18300 + }
18301 +
18302 + // swap for big-endian platform
18303 + pRsnie_cipher->version = cpu2le16(pRsnie_cipher->version);
18304 + pRsnie_cipher->ucount = cpu2le16(pRsnie_cipher->ucount);
18305 + }
18306 +
18307 +}
18308 +
18309 +/*
18310 + ========================================================================
18311 +
18312 + Routine Description:
18313 + Build AKM suite in RSN-IE.
18314 + It only shall be called by RTMPMakeRSNIE.
18315 +
18316 + Arguments:
18317 + pAd - pointer to our pAdapter context
18318 + ElementID - indicate the WPA1 or WPA2
18319 + AuthMode - indicate the authentication mode
18320 + apidx - indicate the interface index
18321 +
18322 + Return Value:
18323 +
18324 + Note:
18325 +
18326 + ========================================================================
18327 +*/
18328 +static VOID RTMPInsertRsnIeAKM(
18329 + IN PRTMP_ADAPTER pAd,
18330 + IN UCHAR ElementID,
18331 + IN UINT AuthMode,
18332 + IN UCHAR apidx,
18333 + OUT PUCHAR pRsnIe,
18334 + OUT UCHAR *rsn_len)
18335 +{
18336 + RSNIE_AUTH *pRsnie_auth;
18337 +
18338 + pRsnie_auth = (RSNIE_AUTH*)(pRsnIe + (*rsn_len));
18339 +
18340 + // decide WPA2 or WPA1
18341 + if (ElementID == Wpa2Ie)
18342 + {
18343 + switch (AuthMode)
18344 + {
18345 + case Ndis802_11AuthModeWPA2:
18346 + case Ndis802_11AuthModeWPA1WPA2:
18347 + pRsnie_auth->acount = 1;
18348 + NdisMoveMemory(pRsnie_auth->auth[0].oui, OUI_WPA2_8021X_AKM, 4);
18349 + break;
18350 +
18351 + case Ndis802_11AuthModeWPA2PSK:
18352 + case Ndis802_11AuthModeWPA1PSKWPA2PSK:
18353 + pRsnie_auth->acount = 1;
18354 + NdisMoveMemory(pRsnie_auth->auth[0].oui, OUI_WPA2_PSK_AKM, 4);
18355 + break;
18356 + }
18357 + }
18358 + else
18359 + {
18360 + switch (AuthMode)
18361 + {
18362 + case Ndis802_11AuthModeWPA:
18363 + case Ndis802_11AuthModeWPA1WPA2:
18364 + pRsnie_auth->acount = 1;
18365 + NdisMoveMemory(pRsnie_auth->auth[0].oui, OUI_WPA_8021X_AKM, 4);
18366 + break;
18367 +
18368 + case Ndis802_11AuthModeWPAPSK:
18369 + case Ndis802_11AuthModeWPA1PSKWPA2PSK:
18370 + pRsnie_auth->acount = 1;
18371 + NdisMoveMemory(pRsnie_auth->auth[0].oui, OUI_WPA_PSK_AKM, 4);
18372 + break;
18373 +
18374 + case Ndis802_11AuthModeWPANone:
18375 + pRsnie_auth->acount = 1;
18376 + NdisMoveMemory(pRsnie_auth->auth[0].oui, OUI_WPA_NONE_AKM, 4);
18377 + break;
18378 + }
18379 + }
18380 +
18381 + pRsnie_auth->acount = cpu2le16(pRsnie_auth->acount);
18382 +
18383 + (*rsn_len) += sizeof(RSNIE_AUTH); // update current RSNIE length
18384 +
18385 +}
18386 +
18387 +/*
18388 + ========================================================================
18389 +
18390 + Routine Description:
18391 + Build capability in RSN-IE.
18392 + It only shall be called by RTMPMakeRSNIE.
18393 +
18394 + Arguments:
18395 + pAd - pointer to our pAdapter context
18396 + ElementID - indicate the WPA1 or WPA2
18397 + apidx - indicate the interface index
18398 +
18399 + Return Value:
18400 +
18401 + Note:
18402 +
18403 + ========================================================================
18404 +*/
18405 +static VOID RTMPInsertRsnIeCap(
18406 + IN PRTMP_ADAPTER pAd,
18407 + IN UCHAR ElementID,
18408 + IN UCHAR apidx,
18409 + OUT PUCHAR pRsnIe,
18410 + OUT UCHAR *rsn_len)
18411 +{
18412 + RSN_CAPABILITIES *pRSN_Cap;
18413 +
18414 + // it could be ignored in WPA1 mode
18415 + if (ElementID == WpaIe)
18416 + return;
18417 +
18418 + pRSN_Cap = (RSN_CAPABILITIES*)(pRsnIe + (*rsn_len));
18419 +
18420 +
18421 + pRSN_Cap->word = cpu2le16(pRSN_Cap->word);
18422 +
18423 + (*rsn_len) += sizeof(RSN_CAPABILITIES); // update current RSNIE length
18424 +
18425 +}
18426 +
18427 +
18428 +/*
18429 + ========================================================================
18430 +
18431 + Routine Description:
18432 + Build RSN IE context. It is not included element-ID and length.
18433 +
18434 + Arguments:
18435 + pAd - pointer to our pAdapter context
18436 + AuthMode - indicate the authentication mode
18437 + WepStatus - indicate the encryption type
18438 + apidx - indicate the interface index
18439 +
18440 + Return Value:
18441 +
18442 + Note:
18443 +
18444 + ========================================================================
18445 +*/
18446 +VOID RTMPMakeRSNIE(
18447 + IN PRTMP_ADAPTER pAd,
18448 + IN UINT AuthMode,
18449 + IN UINT WepStatus,
18450 + IN UCHAR apidx)
18451 +{
18452 + PUCHAR pRsnIe = NULL; // primary RSNIE
18453 + UCHAR *rsnielen_cur_p = 0; // the length of the primary RSNIE
18454 + UCHAR *rsnielen_ex_cur_p = 0; // the length of the secondary RSNIE
18455 + UCHAR PrimaryRsnie;
18456 + BOOLEAN bMixCipher = FALSE; // indicate the pairwise and group cipher are different
18457 + UCHAR p_offset;
18458 + WPA_MIX_PAIR_CIPHER FlexibleCipher = MIX_CIPHER_NOTUSE; // it provide the more flexible cipher combination in WPA-WPA2 and TKIPAES mode
18459 +
18460 + rsnielen_cur_p = NULL;
18461 + rsnielen_ex_cur_p = NULL;
18462 +
18463 + {
18464 +#ifdef CONFIG_STA_SUPPORT
18465 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
18466 + {
18467 +#ifdef WPA_SUPPLICANT_SUPPORT
18468 + if (pAd->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE)
18469 + {
18470 + if (AuthMode < Ndis802_11AuthModeWPA)
18471 + return;
18472 + }
18473 + else
18474 +#endif // WPA_SUPPLICANT_SUPPORT //
18475 + {
18476 + // Support WPAPSK or WPA2PSK in STA-Infra mode
18477 + // Support WPANone in STA-Adhoc mode
18478 + if ((AuthMode != Ndis802_11AuthModeWPAPSK) &&
18479 + (AuthMode != Ndis802_11AuthModeWPA2PSK) &&
18480 + (AuthMode != Ndis802_11AuthModeWPANone)
18481 + )
18482 + return;
18483 + }
18484 +
18485 + DBGPRINT(RT_DEBUG_TRACE,("==> RTMPMakeRSNIE(STA)\n"));
18486 +
18487 + // Zero RSNIE context
18488 + pAd->StaCfg.RSNIE_Len = 0;
18489 + NdisZeroMemory(pAd->StaCfg.RSN_IE, MAX_LEN_OF_RSNIE);
18490 +
18491 + // Pointer to RSNIE
18492 + rsnielen_cur_p = &pAd->StaCfg.RSNIE_Len;
18493 + pRsnIe = pAd->StaCfg.RSN_IE;
18494 +
18495 + bMixCipher = pAd->StaCfg.bMixCipher;
18496 + }
18497 +#endif // CONFIG_STA_SUPPORT //
18498 + }
18499 +
18500 + // indicate primary RSNIE as WPA or WPA2
18501 + if ((AuthMode == Ndis802_11AuthModeWPA) ||
18502 + (AuthMode == Ndis802_11AuthModeWPAPSK) ||
18503 + (AuthMode == Ndis802_11AuthModeWPANone) ||
18504 + (AuthMode == Ndis802_11AuthModeWPA1WPA2) ||
18505 + (AuthMode == Ndis802_11AuthModeWPA1PSKWPA2PSK))
18506 + PrimaryRsnie = WpaIe;
18507 + else
18508 + PrimaryRsnie = Wpa2Ie;
18509 +
18510 + {
18511 + // Build the primary RSNIE
18512 + // 1. insert cipher suite
18513 + RTMPInsertRsnIeCipher(pAd, PrimaryRsnie, WepStatus, bMixCipher, FlexibleCipher, pRsnIe, &p_offset);
18514 +
18515 + // 2. insert AKM
18516 + RTMPInsertRsnIeAKM(pAd, PrimaryRsnie, AuthMode, apidx, pRsnIe, &p_offset);
18517 +
18518 + // 3. insert capability
18519 + RTMPInsertRsnIeCap(pAd, PrimaryRsnie, apidx, pRsnIe, &p_offset);
18520 + }
18521 +
18522 + // 4. update the RSNIE length
18523 + *rsnielen_cur_p = p_offset;
18524 +
18525 + hex_dump("The primary RSNIE", pRsnIe, (*rsnielen_cur_p));
18526 +
18527 +
18528 +}
18529 +
18530 +/*
18531 + ==========================================================================
18532 + Description:
18533 + Check whether the received frame is EAP frame.
18534 +
18535 + Arguments:
18536 + pAd - pointer to our pAdapter context
18537 + pEntry - pointer to active entry
18538 + pData - the received frame
18539 + DataByteCount - the received frame's length
18540 + FromWhichBSSID - indicate the interface index
18541 +
18542 + Return:
18543 + TRUE - This frame is EAP frame
18544 + FALSE - otherwise
18545 + ==========================================================================
18546 +*/
18547 +BOOLEAN RTMPCheckWPAframe(
18548 + IN PRTMP_ADAPTER pAd,
18549 + IN PMAC_TABLE_ENTRY pEntry,
18550 + IN PUCHAR pData,
18551 + IN ULONG DataByteCount,
18552 + IN UCHAR FromWhichBSSID)
18553 +{
18554 + ULONG Body_len;
18555 + BOOLEAN Cancelled;
18556 +
18557 +
18558 + if(DataByteCount < (LENGTH_802_1_H + LENGTH_EAPOL_H))
18559 + return FALSE;
18560 +
18561 +
18562 + // Skip LLC header
18563 + if (NdisEqualMemory(SNAP_802_1H, pData, 6) ||
18564 + // Cisco 1200 AP may send packet with SNAP_BRIDGE_TUNNEL
18565 + NdisEqualMemory(SNAP_BRIDGE_TUNNEL, pData, 6))
18566 + {
18567 + pData += 6;
18568 + }
18569 + // Skip 2-bytes EAPoL type
18570 + if (NdisEqualMemory(EAPOL, pData, 2))
18571 + {
18572 + pData += 2;
18573 + }
18574 + else
18575 + return FALSE;
18576 +
18577 + switch (*(pData+1))
18578 + {
18579 + case EAPPacket:
18580 + Body_len = (*(pData+2)<<8) | (*(pData+3));
18581 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAP-Packet frame, TYPE = 0, Length = %ld\n", Body_len));
18582 + break;
18583 + case EAPOLStart:
18584 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL-Start frame, TYPE = 1 \n"));
18585 + if (pEntry->EnqueueEapolStartTimerRunning != EAPOL_START_DISABLE)
18586 + {
18587 + DBGPRINT(RT_DEBUG_TRACE, ("Cancel the EnqueueEapolStartTimerRunning \n"));
18588 + RTMPCancelTimer(&pEntry->EnqueueStartForPSKTimer, &Cancelled);
18589 + pEntry->EnqueueEapolStartTimerRunning = EAPOL_START_DISABLE;
18590 + }
18591 + break;
18592 + case EAPOLLogoff:
18593 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOLLogoff frame, TYPE = 2 \n"));
18594 + break;
18595 + case EAPOLKey:
18596 + Body_len = (*(pData+2)<<8) | (*(pData+3));
18597 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL-Key frame, TYPE = 3, Length = %ld\n", Body_len));
18598 + break;
18599 + case EAPOLASFAlert:
18600 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOLASFAlert frame, TYPE = 4 \n"));
18601 + break;
18602 + default:
18603 + return FALSE;
18604 +
18605 + }
18606 + return TRUE;
18607 +}
18608 +
18609 +
18610 +/*
18611 + ==========================================================================
18612 + Description:
18613 + ENCRYPT AES GTK before sending in EAPOL frame.
18614 + AES GTK length = 128 bit, so fix blocks for aes-key-wrap as 2 in this function.
18615 + This function references to RFC 3394 for aes key wrap algorithm.
18616 + Return:
18617 + ==========================================================================
18618 +*/
18619 +VOID AES_GTK_KEY_WRAP(
18620 + IN UCHAR *key,
18621 + IN UCHAR *plaintext,
18622 + IN UCHAR p_len,
18623 + OUT UCHAR *ciphertext)
18624 +{
18625 + UCHAR A[8], BIN[16], BOUT[16];
18626 + UCHAR R[512];
18627 + INT num_blocks = p_len/8; // unit:64bits
18628 + INT i, j;
18629 + aes_context aesctx;
18630 + UCHAR xor;
18631 +
18632 + rtmp_aes_set_key(&aesctx, key, 128);
18633 +
18634 + // Init IA
18635 + for (i = 0; i < 8; i++)
18636 + A[i] = 0xa6;
18637 +
18638 + //Input plaintext
18639 + for (i = 0; i < num_blocks; i++)
18640 + {
18641 + for (j = 0 ; j < 8; j++)
18642 + R[8 * (i + 1) + j] = plaintext[8 * i + j];
18643 + }
18644 +
18645 + // Key Mix
18646 + for (j = 0; j < 6; j++)
18647 + {
18648 + for(i = 1; i <= num_blocks; i++)
18649 + {
18650 + //phase 1
18651 + NdisMoveMemory(BIN, A, 8);
18652 + NdisMoveMemory(&BIN[8], &R[8 * i], 8);
18653 + rtmp_aes_encrypt(&aesctx, BIN, BOUT);
18654 +
18655 + NdisMoveMemory(A, &BOUT[0], 8);
18656 + xor = num_blocks * j + i;
18657 + A[7] = BOUT[7] ^ xor;
18658 + NdisMoveMemory(&R[8 * i], &BOUT[8], 8);
18659 + }
18660 + }
18661 +
18662 + // Output ciphertext
18663 + NdisMoveMemory(ciphertext, A, 8);
18664 +
18665 + for (i = 1; i <= num_blocks; i++)
18666 + {
18667 + for (j = 0 ; j < 8; j++)
18668 + ciphertext[8 * i + j] = R[8 * i + j];
18669 + }
18670 +}
18671 +
18672 +
18673 +/*
18674 + ========================================================================
18675 +
18676 + Routine Description:
18677 + Misc function to decrypt AES body
18678 +
18679 + Arguments:
18680 +
18681 + Return Value:
18682 +
18683 + Note:
18684 + This function references to RFC 3394 for aes key unwrap algorithm.
18685 +
18686 + ========================================================================
18687 +*/
18688 +VOID AES_GTK_KEY_UNWRAP(
18689 + IN UCHAR *key,
18690 + OUT UCHAR *plaintext,
18691 + IN UCHAR c_len,
18692 + IN UCHAR *ciphertext)
18693 +
18694 +{
18695 + UCHAR A[8], BIN[16], BOUT[16];
18696 + UCHAR xor;
18697 + INT i, j;
18698 + aes_context aesctx;
18699 + UCHAR *R;
18700 + INT num_blocks = c_len/8; // unit:64bits
18701 +
18702 +
18703 + os_alloc_mem(NULL, (PUCHAR *)&R, 512);
18704 +
18705 + if (R == NULL)
18706 + {
18707 + DBGPRINT(RT_DEBUG_ERROR, ("!!!AES_GTK_KEY_UNWRAP: no memory!!!\n"));
18708 + return;
18709 + } /* End of if */
18710 +
18711 + // Initialize
18712 + NdisMoveMemory(A, ciphertext, 8);
18713 + //Input plaintext
18714 + for(i = 0; i < (c_len-8); i++)
18715 + {
18716 + R[ i] = ciphertext[i + 8];
18717 + }
18718 +
18719 + rtmp_aes_set_key(&aesctx, key, 128);
18720 +
18721 + for(j = 5; j >= 0; j--)
18722 + {
18723 + for(i = (num_blocks-1); i > 0; i--)
18724 + {
18725 + xor = (num_blocks -1 )* j + i;
18726 + NdisMoveMemory(BIN, A, 8);
18727 + BIN[7] = A[7] ^ xor;
18728 + NdisMoveMemory(&BIN[8], &R[(i-1)*8], 8);
18729 + rtmp_aes_decrypt(&aesctx, BIN, BOUT);
18730 + NdisMoveMemory(A, &BOUT[0], 8);
18731 + NdisMoveMemory(&R[(i-1)*8], &BOUT[8], 8);
18732 + }
18733 + }
18734 +
18735 + // OUTPUT
18736 + for(i = 0; i < c_len; i++)
18737 + {
18738 + plaintext[i] = R[i];
18739 + }
18740 +
18741 +
18742 + os_free_mem(NULL, R);
18743 +}
18744 +
18745 +/*
18746 + ==========================================================================
18747 + Description:
18748 + Report the EAP message type
18749 +
18750 + Arguments:
18751 + msg - EAPOL_PAIR_MSG_1
18752 + EAPOL_PAIR_MSG_2
18753 + EAPOL_PAIR_MSG_3
18754 + EAPOL_PAIR_MSG_4
18755 + EAPOL_GROUP_MSG_1
18756 + EAPOL_GROUP_MSG_2
18757 +
18758 + Return:
18759 + message type string
18760 +
18761 + ==========================================================================
18762 +*/
18763 +CHAR *GetEapolMsgType(CHAR msg)
18764 +{
18765 + if(msg == EAPOL_PAIR_MSG_1)
18766 + return "Pairwise Message 1";
18767 + else if(msg == EAPOL_PAIR_MSG_2)
18768 + return "Pairwise Message 2";
18769 + else if(msg == EAPOL_PAIR_MSG_3)
18770 + return "Pairwise Message 3";
18771 + else if(msg == EAPOL_PAIR_MSG_4)
18772 + return "Pairwise Message 4";
18773 + else if(msg == EAPOL_GROUP_MSG_1)
18774 + return "Group Message 1";
18775 + else if(msg == EAPOL_GROUP_MSG_2)
18776 + return "Group Message 2";
18777 + else
18778 + return "Invalid Message";
18779 +}
18780 +
18781 +
18782 +/*
18783 + ========================================================================
18784 +
18785 + Routine Description:
18786 + Check Sanity RSN IE of EAPoL message
18787 +
18788 + Arguments:
18789 +
18790 + Return Value:
18791 +
18792 +
18793 + ========================================================================
18794 +*/
18795 +BOOLEAN RTMPCheckRSNIE(
18796 + IN PRTMP_ADAPTER pAd,
18797 + IN PUCHAR pData,
18798 + IN UCHAR DataLen,
18799 + IN MAC_TABLE_ENTRY *pEntry,
18800 + OUT UCHAR *Offset)
18801 +{
18802 + PUCHAR pVIE;
18803 + UCHAR len;
18804 + PEID_STRUCT pEid;
18805 + BOOLEAN result = FALSE;
18806 +
18807 + pVIE = pData;
18808 + len = DataLen;
18809 + *Offset = 0;
18810 +
18811 + while (len > sizeof(RSNIE2))
18812 + {
18813 + pEid = (PEID_STRUCT) pVIE;
18814 + // WPA RSN IE
18815 + if ((pEid->Eid == IE_WPA) && (NdisEqualMemory(pEid->Octet, WPA_OUI, 4)))
18816 + {
18817 + if ((pEntry->AuthMode == Ndis802_11AuthModeWPA || pEntry->AuthMode == Ndis802_11AuthModeWPAPSK) &&
18818 + (NdisEqualMemory(pVIE, pEntry->RSN_IE, pEntry->RSNIE_Len)) &&
18819 + (pEntry->RSNIE_Len == (pEid->Len + 2)))
18820 + {
18821 + result = TRUE;
18822 + }
18823 +
18824 + *Offset += (pEid->Len + 2);
18825 + }
18826 + // WPA2 RSN IE
18827 + else if ((pEid->Eid == IE_RSN) && (NdisEqualMemory(pEid->Octet + 2, RSN_OUI, 3)))
18828 + {
18829 + if ((pEntry->AuthMode == Ndis802_11AuthModeWPA2 || pEntry->AuthMode == Ndis802_11AuthModeWPA2PSK) &&
18830 + (NdisEqualMemory(pVIE, pEntry->RSN_IE, pEntry->RSNIE_Len)) &&
18831 + (pEntry->RSNIE_Len == (pEid->Len + 2))/* ToDo-AlbertY for mesh*/)
18832 + {
18833 + result = TRUE;
18834 + }
18835 +
18836 + *Offset += (pEid->Len + 2);
18837 + }
18838 + else
18839 + {
18840 + break;
18841 + }
18842 +
18843 + pVIE += (pEid->Len + 2);
18844 + len -= (pEid->Len + 2);
18845 + }
18846 +
18847 +
18848 + return result;
18849 +
18850 +}
18851 +
18852 +
18853 +/*
18854 + ========================================================================
18855 +
18856 + Routine Description:
18857 + Parse KEYDATA field. KEYDATA[] May contain 2 RSN IE and optionally GTK.
18858 + GTK is encaptulated in KDE format at p.83 802.11i D10
18859 +
18860 + Arguments:
18861 +
18862 + Return Value:
18863 +
18864 + Note:
18865 + 802.11i D10
18866 +
18867 + ========================================================================
18868 +*/
18869 +BOOLEAN RTMPParseEapolKeyData(
18870 + IN PRTMP_ADAPTER pAd,
18871 + IN PUCHAR pKeyData,
18872 + IN UCHAR KeyDataLen,
18873 + IN UCHAR GroupKeyIndex,
18874 + IN UCHAR MsgType,
18875 + IN BOOLEAN bWPA2,
18876 + IN MAC_TABLE_ENTRY *pEntry)
18877 +{
18878 + PKDE_ENCAP pKDE = NULL;
18879 + PUCHAR pMyKeyData = pKeyData;
18880 + UCHAR KeyDataLength = KeyDataLen;
18881 + UCHAR GTKLEN = 0;
18882 + UCHAR DefaultIdx = 0;
18883 + UCHAR skip_offset;
18884 +
18885 + // Verify The RSN IE contained in pairewise_msg_2 && pairewise_msg_3 and skip it
18886 + if (MsgType == EAPOL_PAIR_MSG_2 || MsgType == EAPOL_PAIR_MSG_3)
18887 + {
18888 + // Check RSN IE whether it is WPA2/WPA2PSK
18889 + if (!RTMPCheckRSNIE(pAd, pKeyData, KeyDataLen, pEntry, &skip_offset))
18890 + {
18891 + // send wireless event - for RSN IE different
18892 + if (pAd->CommonCfg.bWirelessEvent)
18893 + RTMPSendWirelessEvent(pAd, IW_RSNIE_DIFF_EVENT_FLAG, pEntry->Addr, pEntry->apidx, 0);
18894 +
18895 + DBGPRINT(RT_DEBUG_ERROR, ("RSN_IE Different in msg %d of 4-way handshake!\n", MsgType));
18896 + hex_dump("Receive RSN_IE ", pKeyData, KeyDataLen);
18897 + hex_dump("Desired RSN_IE ", pEntry->RSN_IE, pEntry->RSNIE_Len);
18898 +
18899 + return FALSE;
18900 + }
18901 + else
18902 + {
18903 + if (bWPA2 && MsgType == EAPOL_PAIR_MSG_3)
18904 + {
18905 + // skip RSN IE
18906 + pMyKeyData += skip_offset;
18907 + KeyDataLength -= skip_offset;
18908 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPParseEapolKeyData ==> WPA2/WPA2PSK RSN IE matched in Msg 3, Length(%d) \n", skip_offset));
18909 + }
18910 + else
18911 + return TRUE;
18912 + }
18913 + }
18914 +
18915 + DBGPRINT(RT_DEBUG_TRACE,("RTMPParseEapolKeyData ==> KeyDataLength %d without RSN_IE \n", KeyDataLength));
18916 +
18917 + // Parse EKD format in pairwise_msg_3_WPA2 && group_msg_1_WPA2
18918 + if (bWPA2 && (MsgType == EAPOL_PAIR_MSG_3 || MsgType == EAPOL_GROUP_MSG_1))
18919 + {
18920 + if (KeyDataLength >= 8) // KDE format exclude GTK length
18921 + {
18922 + pKDE = (PKDE_ENCAP) pMyKeyData;
18923 +
18924 +
18925 + DefaultIdx = pKDE->GTKEncap.Kid;
18926 +
18927 + // Sanity check - KED length
18928 + if (KeyDataLength < (pKDE->Len + 2))
18929 + {
18930 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: The len from KDE is too short \n"));
18931 + return FALSE;
18932 + }
18933 +
18934 + // Get GTK length - refer to IEEE 802.11i-2004 p.82
18935 + GTKLEN = pKDE->Len -6;
18936 + if (GTKLEN < LEN_AES_KEY)
18937 + {
18938 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: GTK Key length is too short (%d) \n", GTKLEN));
18939 + return FALSE;
18940 + }
18941 +
18942 + }
18943 + else
18944 + {
18945 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: KDE format length is too short \n"));
18946 + return FALSE;
18947 + }
18948 +
18949 + DBGPRINT(RT_DEBUG_TRACE, ("GTK in KDE format ,DefaultKeyID=%d, KeyLen=%d \n", DefaultIdx, GTKLEN));
18950 + // skip it
18951 + pMyKeyData += 8;
18952 + KeyDataLength -= 8;
18953 +
18954 + }
18955 + else if (!bWPA2 && MsgType == EAPOL_GROUP_MSG_1)
18956 + {
18957 + DefaultIdx = GroupKeyIndex;
18958 + DBGPRINT(RT_DEBUG_TRACE, ("GTK DefaultKeyID=%d \n", DefaultIdx));
18959 + }
18960 +
18961 + // Sanity check - shared key index must be 1 ~ 3
18962 + if (DefaultIdx < 1 || DefaultIdx > 3)
18963 + {
18964 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: GTK Key index(%d) is invalid in %s %s \n", DefaultIdx, ((bWPA2) ? "WPA2" : "WPA"), GetEapolMsgType(MsgType)));
18965 + return FALSE;
18966 + }
18967 +
18968 +
18969 +#ifdef CONFIG_STA_SUPPORT
18970 + // Todo
18971 +#endif // CONFIG_STA_SUPPORT //
18972 +
18973 + return TRUE;
18974 +
18975 +}
18976 +
18977 +
18978 +/*
18979 + ========================================================================
18980 +
18981 + Routine Description:
18982 + Construct EAPoL message for WPA handshaking
18983 + Its format is below,
18984 +
18985 + +--------------------+
18986 + | Protocol Version | 1 octet
18987 + +--------------------+
18988 + | Protocol Type | 1 octet
18989 + +--------------------+
18990 + | Body Length | 2 octets
18991 + +--------------------+
18992 + | Descriptor Type | 1 octet
18993 + +--------------------+
18994 + | Key Information | 2 octets
18995 + +--------------------+
18996 + | Key Length | 1 octet
18997 + +--------------------+
18998 + | Key Repaly Counter | 8 octets
18999 + +--------------------+
19000 + | Key Nonce | 32 octets
19001 + +--------------------+
19002 + | Key IV | 16 octets
19003 + +--------------------+
19004 + | Key RSC | 8 octets
19005 + +--------------------+
19006 + | Key ID or Reserved | 8 octets
19007 + +--------------------+
19008 + | Key MIC | 16 octets
19009 + +--------------------+
19010 + | Key Data Length | 2 octets
19011 + +--------------------+
19012 + | Key Data | n octets
19013 + +--------------------+
19014 +
19015 +
19016 + Arguments:
19017 + pAd Pointer to our adapter
19018 +
19019 + Return Value:
19020 + None
19021 +
19022 + Note:
19023 +
19024 + ========================================================================
19025 +*/
19026 +VOID ConstructEapolMsg(
19027 + IN PRTMP_ADAPTER pAd,
19028 + IN UCHAR AuthMode,
19029 + IN UCHAR WepStatus,
19030 + IN UCHAR GroupKeyWepStatus,
19031 + IN UCHAR MsgType,
19032 + IN UCHAR DefaultKeyIdx,
19033 + IN UCHAR *ReplayCounter,
19034 + IN UCHAR *KeyNonce,
19035 + IN UCHAR *TxRSC,
19036 + IN UCHAR *PTK,
19037 + IN UCHAR *GTK,
19038 + IN UCHAR *RSNIE,
19039 + IN UCHAR RSNIE_Len,
19040 + OUT PEAPOL_PACKET pMsg)
19041 +{
19042 + BOOLEAN bWPA2 = FALSE;
19043 +
19044 + // Choose WPA2 or not
19045 + if ((AuthMode == Ndis802_11AuthModeWPA2) || (AuthMode == Ndis802_11AuthModeWPA2PSK))
19046 + bWPA2 = TRUE;
19047 +
19048 + // Init Packet and Fill header
19049 + pMsg->ProVer = EAPOL_VER;
19050 + pMsg->ProType = EAPOLKey;
19051 +
19052 + // Default 95 bytes, the EAPoL-Key descriptor exclude Key-data field
19053 + pMsg->Body_Len[1] = LEN_EAPOL_KEY_MSG;
19054 +
19055 + // Fill in EAPoL descriptor
19056 + if (bWPA2)
19057 + pMsg->KeyDesc.Type = WPA2_KEY_DESC;
19058 + else
19059 + pMsg->KeyDesc.Type = WPA1_KEY_DESC;
19060 +
19061 + // Fill in Key information, refer to IEEE Std 802.11i-2004 page 78
19062 + // When either the pairwise or the group cipher is AES, the DESC_TYPE_AES(2) shall be used.
19063 + pMsg->KeyDesc.KeyInfo.KeyDescVer =
19064 + (((WepStatus == Ndis802_11Encryption3Enabled) || (GroupKeyWepStatus == Ndis802_11Encryption3Enabled)) ? (DESC_TYPE_AES) : (DESC_TYPE_TKIP));
19065 +
19066 + // Specify Key Type as Group(0) or Pairwise(1)
19067 + if (MsgType >= EAPOL_GROUP_MSG_1)
19068 + pMsg->KeyDesc.KeyInfo.KeyType = GROUPKEY;
19069 + else
19070 + pMsg->KeyDesc.KeyInfo.KeyType = PAIRWISEKEY;
19071 +
19072 + // Specify Key Index, only group_msg1_WPA1
19073 + if (!bWPA2 && (MsgType >= EAPOL_GROUP_MSG_1))
19074 + pMsg->KeyDesc.KeyInfo.KeyIndex = DefaultKeyIdx;
19075 +
19076 + if (MsgType == EAPOL_PAIR_MSG_3)
19077 + pMsg->KeyDesc.KeyInfo.Install = 1;
19078 +
19079 + if ((MsgType == EAPOL_PAIR_MSG_1) || (MsgType == EAPOL_PAIR_MSG_3) || (MsgType == EAPOL_GROUP_MSG_1))
19080 + pMsg->KeyDesc.KeyInfo.KeyAck = 1;
19081 +
19082 + if (MsgType != EAPOL_PAIR_MSG_1)
19083 + pMsg->KeyDesc.KeyInfo.KeyMic = 1;
19084 +
19085 + if ((bWPA2 && (MsgType >= EAPOL_PAIR_MSG_3)) || (!bWPA2 && (MsgType >= EAPOL_GROUP_MSG_1)))
19086 + {
19087 + pMsg->KeyDesc.KeyInfo.Secure = 1;
19088 + }
19089 +
19090 + if (bWPA2 && ((MsgType == EAPOL_PAIR_MSG_3) || (MsgType == EAPOL_GROUP_MSG_1)))
19091 + {
19092 + pMsg->KeyDesc.KeyInfo.EKD_DL = 1;
19093 + }
19094 +
19095 + // key Information element has done.
19096 + *(USHORT *)(&pMsg->KeyDesc.KeyInfo) = cpu2le16(*(USHORT *)(&pMsg->KeyDesc.KeyInfo));
19097 +
19098 + // Fill in Key Length
19099 + {
19100 + if (MsgType >= EAPOL_GROUP_MSG_1)
19101 + {
19102 + // the length of group key cipher
19103 + pMsg->KeyDesc.KeyLength[1] = ((GroupKeyWepStatus == Ndis802_11Encryption2Enabled) ? TKIP_GTK_LENGTH : LEN_AES_KEY);
19104 + }
19105 + else
19106 + {
19107 + // the length of pairwise key cipher
19108 + pMsg->KeyDesc.KeyLength[1] = ((WepStatus == Ndis802_11Encryption2Enabled) ? LEN_TKIP_KEY : LEN_AES_KEY);
19109 + }
19110 + }
19111 +
19112 + // Fill in replay counter
19113 + NdisMoveMemory(pMsg->KeyDesc.ReplayCounter, ReplayCounter, LEN_KEY_DESC_REPLAY);
19114 +
19115 + // Fill Key Nonce field
19116 + // ANonce : pairwise_msg1 & pairwise_msg3
19117 + // SNonce : pairwise_msg2
19118 + // GNonce : group_msg1_wpa1
19119 + if ((MsgType <= EAPOL_PAIR_MSG_3) || ((!bWPA2 && (MsgType == EAPOL_GROUP_MSG_1))))
19120 + NdisMoveMemory(pMsg->KeyDesc.KeyNonce, KeyNonce, LEN_KEY_DESC_NONCE);
19121 +
19122 + // Fill key IV - WPA2 as 0, WPA1 as random
19123 + if (!bWPA2 && (MsgType == EAPOL_GROUP_MSG_1))
19124 + {
19125 + // Suggest IV be random number plus some number,
19126 + NdisMoveMemory(pMsg->KeyDesc.KeyIv, &KeyNonce[16], LEN_KEY_DESC_IV);
19127 + pMsg->KeyDesc.KeyIv[15] += 2;
19128 + }
19129 +
19130 + // Fill Key RSC field
19131 + // It contains the RSC for the GTK being installed.
19132 + if ((MsgType == EAPOL_PAIR_MSG_3 && bWPA2) || (MsgType == EAPOL_GROUP_MSG_1))
19133 + {
19134 + NdisMoveMemory(pMsg->KeyDesc.KeyRsc, TxRSC, 6);
19135 + }
19136 +
19137 + // Clear Key MIC field for MIC calculation later
19138 + NdisZeroMemory(pMsg->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
19139 +
19140 + ConstructEapolKeyData(pAd,
19141 + AuthMode,
19142 + WepStatus,
19143 + GroupKeyWepStatus,
19144 + MsgType,
19145 + DefaultKeyIdx,
19146 + bWPA2,
19147 + PTK,
19148 + GTK,
19149 + RSNIE,
19150 + RSNIE_Len,
19151 + pMsg);
19152 +
19153 + // Calculate MIC and fill in KeyMic Field except Pairwise Msg 1.
19154 + if (MsgType != EAPOL_PAIR_MSG_1)
19155 + {
19156 + CalculateMIC(pAd, WepStatus, PTK, pMsg);
19157 + }
19158 +
19159 + DBGPRINT(RT_DEBUG_TRACE, ("===> ConstructEapolMsg for %s %s\n", ((bWPA2) ? "WPA2" : "WPA"), GetEapolMsgType(MsgType)));
19160 + DBGPRINT(RT_DEBUG_TRACE, (" Body length = %d \n", pMsg->Body_Len[1]));
19161 + DBGPRINT(RT_DEBUG_TRACE, (" Key length = %d \n", pMsg->KeyDesc.KeyLength[1]));
19162 +
19163 +
19164 +}
19165 +
19166 +/*
19167 + ========================================================================
19168 +
19169 + Routine Description:
19170 + Construct the Key Data field of EAPoL message
19171 +
19172 + Arguments:
19173 + pAd Pointer to our adapter
19174 + Elem Message body
19175 +
19176 + Return Value:
19177 + None
19178 +
19179 + Note:
19180 +
19181 + ========================================================================
19182 +*/
19183 +VOID ConstructEapolKeyData(
19184 + IN PRTMP_ADAPTER pAd,
19185 + IN UCHAR AuthMode,
19186 + IN UCHAR WepStatus,
19187 + IN UCHAR GroupKeyWepStatus,
19188 + IN UCHAR MsgType,
19189 + IN UCHAR DefaultKeyIdx,
19190 + IN BOOLEAN bWPA2Capable,
19191 + IN UCHAR *PTK,
19192 + IN UCHAR *GTK,
19193 + IN UCHAR *RSNIE,
19194 + IN UCHAR RSNIE_LEN,
19195 + OUT PEAPOL_PACKET pMsg)
19196 +{
19197 + UCHAR *mpool, *Key_Data, *Rc4GTK;
19198 + UCHAR ekey[(LEN_KEY_DESC_IV+LEN_EAP_EK)];
19199 + UCHAR data_offset;
19200 +
19201 +
19202 + if (MsgType == EAPOL_PAIR_MSG_1 || MsgType == EAPOL_PAIR_MSG_4 || MsgType == EAPOL_GROUP_MSG_2)
19203 + return;
19204 +
19205 + // allocate memory pool
19206 + os_alloc_mem(pAd, (PUCHAR *)&mpool, 1500);
19207 +
19208 + if (mpool == NULL)
19209 + return;
19210 +
19211 + /* Rc4GTK Len = 512 */
19212 + Rc4GTK = (UCHAR *) ROUND_UP(mpool, 4);
19213 + /* Key_Data Len = 512 */
19214 + Key_Data = (UCHAR *) ROUND_UP(Rc4GTK + 512, 4);
19215 +
19216 + NdisZeroMemory(Key_Data, 512);
19217 + pMsg->KeyDesc.KeyDataLen[1] = 0;
19218 + data_offset = 0;
19219 +
19220 + // Encapsulate RSNIE in pairwise_msg2 & pairwise_msg3
19221 + if (RSNIE_LEN && ((MsgType == EAPOL_PAIR_MSG_2) || (MsgType == EAPOL_PAIR_MSG_3)))
19222 + {
19223 + if (bWPA2Capable)
19224 + Key_Data[data_offset + 0] = IE_WPA2;
19225 + else
19226 + Key_Data[data_offset + 0] = IE_WPA;
19227 +
19228 + Key_Data[data_offset + 1] = RSNIE_LEN;
19229 + NdisMoveMemory(&Key_Data[data_offset + 2], RSNIE, RSNIE_LEN);
19230 + data_offset += (2 + RSNIE_LEN);
19231 + }
19232 +
19233 + // Encapsulate KDE format in pairwise_msg3_WPA2 & group_msg1_WPA2
19234 + if (bWPA2Capable && ((MsgType == EAPOL_PAIR_MSG_3) || (MsgType == EAPOL_GROUP_MSG_1)))
19235 + {
19236 + // Key Data Encapsulation (KDE) format - 802.11i-2004 Figure-43w and Table-20h
19237 + Key_Data[data_offset + 0] = 0xDD;
19238 +
19239 + if (GroupKeyWepStatus == Ndis802_11Encryption3Enabled)
19240 + {
19241 + Key_Data[data_offset + 1] = 0x16;// 4+2+16(OUI+DataType+DataField)
19242 + }
19243 + else
19244 + {
19245 + Key_Data[data_offset + 1] = 0x26;// 4+2+32(OUI+DataType+DataField)
19246 + }
19247 +
19248 + Key_Data[data_offset + 2] = 0x00;
19249 + Key_Data[data_offset + 3] = 0x0F;
19250 + Key_Data[data_offset + 4] = 0xAC;
19251 + Key_Data[data_offset + 5] = 0x01;
19252 +
19253 + // GTK KDE format - 802.11i-2004 Figure-43x
19254 + Key_Data[data_offset + 6] = (DefaultKeyIdx & 0x03);
19255 + Key_Data[data_offset + 7] = 0x00; // Reserved Byte
19256 +
19257 + data_offset += 8;
19258 + }
19259 +
19260 +
19261 + // Encapsulate GTK and encrypt the key-data field with KEK.
19262 + // Only for pairwise_msg3_WPA2 and group_msg1
19263 + if ((MsgType == EAPOL_PAIR_MSG_3 && bWPA2Capable) || (MsgType == EAPOL_GROUP_MSG_1))
19264 + {
19265 + // Fill in GTK
19266 + if (GroupKeyWepStatus == Ndis802_11Encryption3Enabled)
19267 + {
19268 + NdisMoveMemory(&Key_Data[data_offset], GTK, LEN_AES_KEY);
19269 + data_offset += LEN_AES_KEY;
19270 + }
19271 + else
19272 + {
19273 + NdisMoveMemory(&Key_Data[data_offset], GTK, TKIP_GTK_LENGTH);
19274 + data_offset += TKIP_GTK_LENGTH;
19275 + }
19276 +
19277 + // Still dont know why, but if not append will occur "GTK not include in MSG3"
19278 + // Patch for compatibility between zero config and funk
19279 + if (MsgType == EAPOL_PAIR_MSG_3 && bWPA2Capable)
19280 + {
19281 + if (GroupKeyWepStatus == Ndis802_11Encryption3Enabled)
19282 + {
19283 + Key_Data[data_offset + 0] = 0xDD;
19284 + Key_Data[data_offset + 1] = 0;
19285 + data_offset += 2;
19286 + }
19287 + else
19288 + {
19289 + Key_Data[data_offset + 0] = 0xDD;
19290 + Key_Data[data_offset + 1] = 0;
19291 + Key_Data[data_offset + 2] = 0;
19292 + Key_Data[data_offset + 3] = 0;
19293 + Key_Data[data_offset + 4] = 0;
19294 + Key_Data[data_offset + 5] = 0;
19295 + data_offset += 6;
19296 + }
19297 + }
19298 +
19299 + // Encrypt the data material in key data field
19300 + if (WepStatus == Ndis802_11Encryption3Enabled)
19301 + {
19302 + AES_GTK_KEY_WRAP(&PTK[16], Key_Data, data_offset, Rc4GTK);
19303 + // AES wrap function will grow 8 bytes in length
19304 + data_offset += 8;
19305 + }
19306 + else
19307 + {
19308 + // PREPARE Encrypted "Key DATA" field. (Encrypt GTK with RC4, usinf PTK[16]->[31] as Key, IV-field as IV)
19309 + // put TxTsc in Key RSC field
19310 + pAd->PrivateInfo.FCSCRC32 = PPPINITFCS32; //Init crc32.
19311 +
19312 + // ekey is the contanetion of IV-field, and PTK[16]->PTK[31]
19313 + NdisMoveMemory(ekey, pMsg->KeyDesc.KeyIv, LEN_KEY_DESC_IV);
19314 + NdisMoveMemory(&ekey[LEN_KEY_DESC_IV], &PTK[16], LEN_EAP_EK);
19315 + ARCFOUR_INIT(&pAd->PrivateInfo.WEPCONTEXT, ekey, sizeof(ekey)); //INIT SBOX, KEYLEN+3(IV)
19316 + pAd->PrivateInfo.FCSCRC32 = RTMP_CALC_FCS32(pAd->PrivateInfo.FCSCRC32, Key_Data, data_offset);
19317 + WPAARCFOUR_ENCRYPT(&pAd->PrivateInfo.WEPCONTEXT, Rc4GTK, Key_Data, data_offset);
19318 + }
19319 +
19320 + NdisMoveMemory(pMsg->KeyDesc.KeyData, Rc4GTK, data_offset);
19321 + }
19322 + else
19323 + {
19324 + NdisMoveMemory(pMsg->KeyDesc.KeyData, Key_Data, data_offset);
19325 + }
19326 +
19327 + // set key data length field and total length
19328 + pMsg->KeyDesc.KeyDataLen[1] = data_offset;
19329 + pMsg->Body_Len[1] += data_offset;
19330 +
19331 + os_free_mem(pAd, mpool);
19332 +
19333 +}
19334 +
19335 +/*
19336 + ========================================================================
19337 +
19338 + Routine Description:
19339 + Calcaulate MIC. It is used during 4-ways handsharking.
19340 +
19341 + Arguments:
19342 + pAd - pointer to our pAdapter context
19343 + PeerWepStatus - indicate the encryption type
19344 +
19345 + Return Value:
19346 +
19347 + Note:
19348 +
19349 + ========================================================================
19350 +*/
19351 +VOID CalculateMIC(
19352 + IN PRTMP_ADAPTER pAd,
19353 + IN UCHAR PeerWepStatus,
19354 + IN UCHAR *PTK,
19355 + OUT PEAPOL_PACKET pMsg)
19356 +{
19357 + UCHAR *OutBuffer;
19358 + ULONG FrameLen = 0;
19359 + UCHAR mic[LEN_KEY_DESC_MIC];
19360 + UCHAR digest[80];
19361 +
19362 + // allocate memory for MIC calculation
19363 + os_alloc_mem(pAd, (PUCHAR *)&OutBuffer, 512);
19364 +
19365 + if (OutBuffer == NULL)
19366 + {
19367 + DBGPRINT(RT_DEBUG_ERROR, ("!!!CalculateMIC: no memory!!!\n"));
19368 + return;
19369 + }
19370 +
19371 + // make a frame for calculating MIC.
19372 + MakeOutgoingFrame(OutBuffer, &FrameLen,
19373 + pMsg->Body_Len[1] + 4, pMsg,
19374 + END_OF_ARGS);
19375 +
19376 + NdisZeroMemory(mic, sizeof(mic));
19377 +
19378 + // Calculate MIC
19379 + if (PeerWepStatus == Ndis802_11Encryption3Enabled)
19380 + {
19381 + HMAC_SHA1(OutBuffer, FrameLen, PTK, LEN_EAP_MICK, digest);
19382 + NdisMoveMemory(mic, digest, LEN_KEY_DESC_MIC);
19383 + }
19384 + else
19385 + {
19386 + hmac_md5(PTK, LEN_EAP_MICK, OutBuffer, FrameLen, mic);
19387 + }
19388 +
19389 + // store the calculated MIC
19390 + NdisMoveMemory(pMsg->KeyDesc.KeyMic, mic, LEN_KEY_DESC_MIC);
19391 +
19392 + os_free_mem(pAd, OutBuffer);
19393 +}
19394 +
19395 +/*
19396 + ========================================================================
19397 +
19398 + Routine Description:
19399 + Some received frames can't decrypt by Asic, so decrypt them by software.
19400 +
19401 + Arguments:
19402 + pAd - pointer to our pAdapter context
19403 + PeerWepStatus - indicate the encryption type
19404 +
19405 + Return Value:
19406 + NDIS_STATUS_SUCCESS - decryption successful
19407 + NDIS_STATUS_FAILURE - decryption failure
19408 +
19409 + ========================================================================
19410 +*/
19411 +NDIS_STATUS RTMPSoftDecryptBroadCastData(
19412 + IN PRTMP_ADAPTER pAd,
19413 + IN RX_BLK *pRxBlk,
19414 + IN NDIS_802_11_ENCRYPTION_STATUS GroupCipher,
19415 + IN PCIPHER_KEY pShard_key)
19416 +{
19417 + PRXWI_STRUC pRxWI = pRxBlk->pRxWI;
19418 +
19419 +
19420 +
19421 + // handle WEP decryption
19422 + if (GroupCipher == Ndis802_11Encryption1Enabled)
19423 + {
19424 + if (RTMPSoftDecryptWEP(pAd, pRxBlk->pData, pRxWI->MPDUtotalByteCount, pShard_key))
19425 + {
19426 +
19427 + //Minus IV[4] & ICV[4]
19428 + pRxWI->MPDUtotalByteCount -= 8;
19429 + }
19430 + else
19431 + {
19432 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR : Software decrypt WEP data fails.\n"));
19433 + // give up this frame
19434 + return NDIS_STATUS_FAILURE;
19435 + }
19436 + }
19437 + // handle TKIP decryption
19438 + else if (GroupCipher == Ndis802_11Encryption2Enabled)
19439 + {
19440 + if (RTMPSoftDecryptTKIP(pAd, pRxBlk->pData, pRxWI->MPDUtotalByteCount, 0, pShard_key))
19441 + {
19442 +
19443 + //Minus 8 bytes MIC, 8 bytes IV/EIV, 4 bytes ICV
19444 + pRxWI->MPDUtotalByteCount -= 20;
19445 + }
19446 + else
19447 + {
19448 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR : RTMPSoftDecryptTKIP Failed\n"));
19449 + // give up this frame
19450 + return NDIS_STATUS_FAILURE;
19451 + }
19452 + }
19453 + // handle AES decryption
19454 + else if (GroupCipher == Ndis802_11Encryption3Enabled)
19455 + {
19456 + if (RTMPSoftDecryptAES(pAd, pRxBlk->pData, pRxWI->MPDUtotalByteCount , pShard_key))
19457 + {
19458 +
19459 + //8 bytes MIC, 8 bytes IV/EIV (CCMP Header)
19460 + pRxWI->MPDUtotalByteCount -= 16;
19461 + }
19462 + else
19463 + {
19464 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR : RTMPSoftDecryptAES Failed\n"));
19465 + // give up this frame
19466 + return NDIS_STATUS_FAILURE;
19467 + }
19468 + }
19469 + else
19470 + {
19471 + // give up this frame
19472 + return NDIS_STATUS_FAILURE;
19473 + }
19474 +
19475 + return NDIS_STATUS_SUCCESS;
19476 +
19477 +}
19478 +
19479 --- /dev/null
19480 +++ b/drivers/staging/rt2860/common/dfs.c
19481 @@ -0,0 +1,453 @@
19482 +/*
19483 + *************************************************************************
19484 + * Ralink Tech Inc.
19485 + * 5F., No.36, Taiyuan St., Jhubei City,
19486 + * Hsinchu County 302,
19487 + * Taiwan, R.O.C.
19488 + *
19489 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
19490 + *
19491 + * This program is free software; you can redistribute it and/or modify *
19492 + * it under the terms of the GNU General Public License as published by *
19493 + * the Free Software Foundation; either version 2 of the License, or *
19494 + * (at your option) any later version. *
19495 + * *
19496 + * This program is distributed in the hope that it will be useful, *
19497 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
19498 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
19499 + * GNU General Public License for more details. *
19500 + * *
19501 + * You should have received a copy of the GNU General Public License *
19502 + * along with this program; if not, write to the *
19503 + * Free Software Foundation, Inc., *
19504 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19505 + * *
19506 + *************************************************************************
19507 +
19508 + Module Name:
19509 + ap_dfs.c
19510 +
19511 + Abstract:
19512 + Support DFS function.
19513 +
19514 + Revision History:
19515 + Who When What
19516 + -------- ---------- ----------------------------------------------
19517 + Fonchi 03-12-2007 created
19518 +*/
19519 +
19520 +#include "../rt_config.h"
19521 +
19522 +typedef struct _RADAR_DURATION_TABLE
19523 +{
19524 + ULONG RDDurRegion;
19525 + ULONG RadarSignalDuration;
19526 + ULONG Tolerance;
19527 +} RADAR_DURATION_TABLE, *PRADAR_DURATION_TABLE;
19528 +
19529 +
19530 +static UCHAR RdIdleTimeTable[MAX_RD_REGION][4] =
19531 +{
19532 + {9, 250, 250, 250}, // CE
19533 + {4, 250, 250, 250}, // FCC
19534 + {4, 250, 250, 250}, // JAP
19535 + {15, 250, 250, 250}, // JAP_W53
19536 + {4, 250, 250, 250} // JAP_W56
19537 +};
19538 +
19539 +/*
19540 + ========================================================================
19541 +
19542 + Routine Description:
19543 + Bbp Radar detection routine
19544 +
19545 + Arguments:
19546 + pAd Pointer to our adapter
19547 +
19548 + Return Value:
19549 +
19550 + ========================================================================
19551 +*/
19552 +VOID BbpRadarDetectionStart(
19553 + IN PRTMP_ADAPTER pAd)
19554 +{
19555 + UINT8 RadarPeriod;
19556 +
19557 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, 114, 0x02);
19558 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, 121, 0x20);
19559 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, 122, 0x00);
19560 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, 123, 0x08/*0x80*/);
19561 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, 124, 0x28);
19562 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, 125, 0xff);
19563 +
19564 +#if 0
19565 + // toggle Rx enable bit for radar detection.
19566 + // it's Andy's recommand.
19567 + {
19568 + UINT32 Value;
19569 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
19570 + Value |= (0x1 << 3);
19571 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
19572 + Value &= ~(0x1 << 3);
19573 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
19574 + }
19575 +#endif
19576 + RadarPeriod = ((UINT)RdIdleTimeTable[pAd->CommonCfg.RadarDetect.RDDurRegion][0] + (UINT)pAd->CommonCfg.RadarDetect.DfsSessionTime) < 250 ?
19577 + (RdIdleTimeTable[pAd->CommonCfg.RadarDetect.RDDurRegion][0] + pAd->CommonCfg.RadarDetect.DfsSessionTime) : 250;
19578 +
19579 + RTMP_IO_WRITE8(pAd, 0x7020, 0x1d);
19580 + RTMP_IO_WRITE8(pAd, 0x7021, 0x40);
19581 +
19582 + RadarDetectionStart(pAd, 0, RadarPeriod);
19583 + return;
19584 +}
19585 +
19586 +/*
19587 + ========================================================================
19588 +
19589 + Routine Description:
19590 + Bbp Radar detection routine
19591 +
19592 + Arguments:
19593 + pAd Pointer to our adapter
19594 +
19595 + Return Value:
19596 +
19597 + ========================================================================
19598 +*/
19599 +VOID BbpRadarDetectionStop(
19600 + IN PRTMP_ADAPTER pAd)
19601 +{
19602 + RTMP_IO_WRITE8(pAd, 0x7020, 0x1d);
19603 + RTMP_IO_WRITE8(pAd, 0x7021, 0x60);
19604 +
19605 + RadarDetectionStop(pAd);
19606 + return;
19607 +}
19608 +
19609 +/*
19610 + ========================================================================
19611 +
19612 + Routine Description:
19613 + Radar detection routine
19614 +
19615 + Arguments:
19616 + pAd Pointer to our adapter
19617 +
19618 + Return Value:
19619 +
19620 + ========================================================================
19621 +*/
19622 +VOID RadarDetectionStart(
19623 + IN PRTMP_ADAPTER pAd,
19624 + IN BOOLEAN CTSProtect,
19625 + IN UINT8 CTSPeriod)
19626 +{
19627 + UINT8 DfsActiveTime = (pAd->CommonCfg.RadarDetect.DfsSessionTime & 0x1f);
19628 + UINT8 CtsProtect = (CTSProtect == 1) ? 0x02 : 0x01; // CTS protect.
19629 +
19630 + if (CTSProtect != 0)
19631 + {
19632 + switch(pAd->CommonCfg.RadarDetect.RDDurRegion)
19633 + {
19634 + case FCC:
19635 + case JAP_W56:
19636 + CtsProtect = 0x03;
19637 + break;
19638 +
19639 + case CE:
19640 + case JAP_W53:
19641 + default:
19642 + CtsProtect = 0x02;
19643 + break;
19644 + }
19645 + }
19646 + else
19647 + CtsProtect = 0x01;
19648 +
19649 +
19650 + // send start-RD with CTS protection command to MCU
19651 + // highbyte [7] reserve
19652 + // highbyte [6:5] 0x: stop Carrier/Radar detection
19653 + // highbyte [10]: Start Carrier/Radar detection without CTS protection, 11: Start Carrier/Radar detection with CTS protection
19654 + // highbyte [4:0] Radar/carrier detection duration. In 1ms.
19655 +
19656 + // lowbyte [7:0] Radar/carrier detection period, in 1ms.
19657 + AsicSendCommandToMcu(pAd, 0x60, 0xff, CTSPeriod, DfsActiveTime | (CtsProtect << 5));
19658 + //AsicSendCommandToMcu(pAd, 0x63, 0xff, 10, 0);
19659 +
19660 + return;
19661 +}
19662 +
19663 +/*
19664 + ========================================================================
19665 +
19666 + Routine Description:
19667 + Radar detection routine
19668 +
19669 + Arguments:
19670 + pAd Pointer to our adapter
19671 +
19672 + Return Value:
19673 + TRUE Found radar signal
19674 + FALSE Not found radar signal
19675 +
19676 + ========================================================================
19677 +*/
19678 +VOID RadarDetectionStop(
19679 + IN PRTMP_ADAPTER pAd)
19680 +{
19681 + DBGPRINT(RT_DEBUG_TRACE,("RadarDetectionStop.\n"));
19682 + AsicSendCommandToMcu(pAd, 0x60, 0xff, 0x00, 0x00); // send start-RD with CTS protection command to MCU
19683 +
19684 + return;
19685 +}
19686 +
19687 +/*
19688 + ========================================================================
19689 +
19690 + Routine Description:
19691 + Radar channel check routine
19692 +
19693 + Arguments:
19694 + pAd Pointer to our adapter
19695 +
19696 + Return Value:
19697 + TRUE need to do radar detect
19698 + FALSE need not to do radar detect
19699 +
19700 + ========================================================================
19701 +*/
19702 +BOOLEAN RadarChannelCheck(
19703 + IN PRTMP_ADAPTER pAd,
19704 + IN UCHAR Ch)
19705 +{
19706 +#if 1
19707 + INT i;
19708 + BOOLEAN result = FALSE;
19709 +
19710 + for (i=0; i<pAd->ChannelListNum; i++)
19711 + {
19712 + if (Ch == pAd->ChannelList[i].Channel)
19713 + {
19714 + result = pAd->ChannelList[i].DfsReq;
19715 + break;
19716 + }
19717 + }
19718 +
19719 + return result;
19720 +#else
19721 + INT i;
19722 + UCHAR Channel[15]={52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140};
19723 +
19724 + for (i=0; i<15; i++)
19725 + {
19726 + if (Ch == Channel[i])
19727 + {
19728 + break;
19729 + }
19730 + }
19731 +
19732 + if (i != 15)
19733 + return TRUE;
19734 + else
19735 + return FALSE;
19736 +#endif
19737 +}
19738 +
19739 +ULONG JapRadarType(
19740 + IN PRTMP_ADAPTER pAd)
19741 +{
19742 + ULONG i;
19743 + const UCHAR Channel[15]={52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140};
19744 +
19745 + if (pAd->CommonCfg.RadarDetect.RDDurRegion != JAP)
19746 + {
19747 + return pAd->CommonCfg.RadarDetect.RDDurRegion;
19748 + }
19749 +
19750 + for (i=0; i<15; i++)
19751 + {
19752 + if (pAd->CommonCfg.Channel == Channel[i])
19753 + {
19754 + break;
19755 + }
19756 + }
19757 +
19758 + if (i < 4)
19759 + return JAP_W53;
19760 + else if (i < 15)
19761 + return JAP_W56;
19762 + else
19763 + return JAP; // W52
19764 +
19765 +}
19766 +
19767 +ULONG RTMPBbpReadRadarDuration(
19768 + IN PRTMP_ADAPTER pAd)
19769 +{
19770 + UINT8 byteValue = 0;
19771 + ULONG result;
19772 +
19773 + BBP_IO_READ8_BY_REG_ID(pAd, BBP_R115, &byteValue);
19774 +
19775 + result = 0;
19776 + switch (byteValue)
19777 + {
19778 + case 1: // radar signal detected by pulse mode.
19779 + case 2: // radar signal detected by width mode.
19780 + result = RTMPReadRadarDuration(pAd);
19781 + break;
19782 +
19783 + case 0: // No radar signal.
19784 + default:
19785 +
19786 + result = 0;
19787 + break;
19788 + }
19789 +
19790 + return result;
19791 +}
19792 +
19793 +ULONG RTMPReadRadarDuration(
19794 + IN PRTMP_ADAPTER pAd)
19795 +{
19796 + ULONG result = 0;
19797 +
19798 +#ifdef DFS_SUPPORT
19799 + UINT8 duration1 = 0, duration2 = 0, duration3 = 0;
19800 +
19801 + BBP_IO_READ8_BY_REG_ID(pAd, BBP_R116, &duration1);
19802 + BBP_IO_READ8_BY_REG_ID(pAd, BBP_R117, &duration2);
19803 + BBP_IO_READ8_BY_REG_ID(pAd, BBP_R118, &duration3);
19804 + result = (duration1 << 16) + (duration2 << 8) + duration3;
19805 +#endif // DFS_SUPPORT //
19806 +
19807 + return result;
19808 +
19809 +}
19810 +
19811 +VOID RTMPCleanRadarDuration(
19812 + IN PRTMP_ADAPTER pAd)
19813 +{
19814 + return;
19815 +}
19816 +
19817 +/*
19818 + ========================================================================
19819 + Routine Description:
19820 + Radar wave detection. The API should be invoke each second.
19821 +
19822 + Arguments:
19823 + pAd - Adapter pointer
19824 +
19825 + Return Value:
19826 + None
19827 +
19828 + ========================================================================
19829 +*/
19830 +VOID ApRadarDetectPeriodic(
19831 + IN PRTMP_ADAPTER pAd)
19832 +{
19833 + INT i;
19834 +
19835 + pAd->CommonCfg.RadarDetect.InServiceMonitorCount++;
19836 +
19837 + for (i=0; i<pAd->ChannelListNum; i++)
19838 + {
19839 + if (pAd->ChannelList[i].RemainingTimeForUse > 0)
19840 + {
19841 + pAd->ChannelList[i].RemainingTimeForUse --;
19842 + if ((pAd->Mlme.PeriodicRound%5) == 0)
19843 + {
19844 + DBGPRINT(RT_DEBUG_TRACE, ("RadarDetectPeriodic - ch=%d, RemainingTimeForUse=%d\n", pAd->ChannelList[i].Channel, pAd->ChannelList[i].RemainingTimeForUse));
19845 + }
19846 + }
19847 + }
19848 +
19849 + //radar detect
19850 + if ((pAd->CommonCfg.Channel > 14)
19851 + && (pAd->CommonCfg.bIEEE80211H == 1)
19852 + && RadarChannelCheck(pAd, pAd->CommonCfg.Channel))
19853 + {
19854 + RadarDetectPeriodic(pAd);
19855 + }
19856 +
19857 + return;
19858 +}
19859 +
19860 +// Periodic Radar detection, switch channel will occur in RTMPHandleTBTTInterrupt()
19861 +// Before switch channel, driver needs doing channel switch announcement.
19862 +VOID RadarDetectPeriodic(
19863 + IN PRTMP_ADAPTER pAd)
19864 +{
19865 + // need to check channel availability, after switch channel
19866 + if (pAd->CommonCfg.RadarDetect.RDMode != RD_SILENCE_MODE)
19867 + return;
19868 +
19869 + // channel availability check time is 60sec, use 65 for assurance
19870 + if (pAd->CommonCfg.RadarDetect.RDCount++ > pAd->CommonCfg.RadarDetect.ChMovingTime)
19871 + {
19872 + DBGPRINT(RT_DEBUG_TRACE, ("Not found radar signal, start send beacon and radar detection in service monitor\n\n"));
19873 + BbpRadarDetectionStop(pAd);
19874 + AsicEnableBssSync(pAd);
19875 + pAd->CommonCfg.RadarDetect.RDMode = RD_NORMAL_MODE;
19876 +
19877 +
19878 + return;
19879 + }
19880 +
19881 + return;
19882 +}
19883 +
19884 +
19885 +/*
19886 + ==========================================================================
19887 + Description:
19888 + change channel moving time for DFS testing.
19889 +
19890 + Arguments:
19891 + pAdapter Pointer to our adapter
19892 + wrq Pointer to the ioctl argument
19893 +
19894 + Return Value:
19895 + None
19896 +
19897 + Note:
19898 + Usage:
19899 + 1.) iwpriv ra0 set ChMovTime=[value]
19900 + ==========================================================================
19901 +*/
19902 +INT Set_ChMovingTime_Proc(
19903 + IN PRTMP_ADAPTER pAd,
19904 + IN PUCHAR arg)
19905 +{
19906 + UINT8 Value;
19907 +
19908 + Value = simple_strtol(arg, 0, 10);
19909 +
19910 + pAd->CommonCfg.RadarDetect.ChMovingTime = Value;
19911 +
19912 + DBGPRINT(RT_DEBUG_TRACE, ("%s:: %d\n", __FUNCTION__,
19913 + pAd->CommonCfg.RadarDetect.ChMovingTime));
19914 +
19915 + return TRUE;
19916 +}
19917 +
19918 +INT Set_LongPulseRadarTh_Proc(
19919 + IN PRTMP_ADAPTER pAd,
19920 + IN PUCHAR arg)
19921 +{
19922 + UINT8 Value;
19923 +
19924 + Value = simple_strtol(arg, 0, 10) > 10 ? 10 : simple_strtol(arg, 0, 10);
19925 +
19926 + pAd->CommonCfg.RadarDetect.LongPulseRadarTh = Value;
19927 +
19928 + DBGPRINT(RT_DEBUG_TRACE, ("%s:: %d\n", __FUNCTION__,
19929 + pAd->CommonCfg.RadarDetect.LongPulseRadarTh));
19930 +
19931 + return TRUE;
19932 +}
19933 +
19934 +
19935 --- /dev/null
19936 +++ b/drivers/staging/rt2860/common/eeprom.c
19937 @@ -0,0 +1,244 @@
19938 +/*
19939 + *************************************************************************
19940 + * Ralink Tech Inc.
19941 + * 5F., No.36, Taiyuan St., Jhubei City,
19942 + * Hsinchu County 302,
19943 + * Taiwan, R.O.C.
19944 + *
19945 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
19946 + *
19947 + * This program is free software; you can redistribute it and/or modify *
19948 + * it under the terms of the GNU General Public License as published by *
19949 + * the Free Software Foundation; either version 2 of the License, or *
19950 + * (at your option) any later version. *
19951 + * *
19952 + * This program is distributed in the hope that it will be useful, *
19953 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
19954 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
19955 + * GNU General Public License for more details. *
19956 + * *
19957 + * You should have received a copy of the GNU General Public License *
19958 + * along with this program; if not, write to the *
19959 + * Free Software Foundation, Inc., *
19960 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19961 + * *
19962 + *************************************************************************
19963 +
19964 + Module Name:
19965 + eeprom.c
19966 +
19967 + Abstract:
19968 +
19969 + Revision History:
19970 + Who When What
19971 + -------- ---------- ----------------------------------------------
19972 + Name Date Modification logs
19973 +*/
19974 +#include "../rt_config.h"
19975 +
19976 +// IRQL = PASSIVE_LEVEL
19977 +VOID RaiseClock(
19978 + IN PRTMP_ADAPTER pAd,
19979 + IN UINT32 *x)
19980 +{
19981 + *x = *x | EESK;
19982 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, *x);
19983 + RTMPusecDelay(1); // Max frequency = 1MHz in Spec. definition
19984 +}
19985 +
19986 +// IRQL = PASSIVE_LEVEL
19987 +VOID LowerClock(
19988 + IN PRTMP_ADAPTER pAd,
19989 + IN UINT32 *x)
19990 +{
19991 + *x = *x & ~EESK;
19992 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, *x);
19993 + RTMPusecDelay(1);
19994 +}
19995 +
19996 +// IRQL = PASSIVE_LEVEL
19997 +USHORT ShiftInBits(
19998 + IN PRTMP_ADAPTER pAd)
19999 +{
20000 + UINT32 x,i;
20001 + USHORT data=0;
20002 +
20003 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20004 +
20005 + x &= ~( EEDO | EEDI);
20006 +
20007 + for(i=0; i<16; i++)
20008 + {
20009 + data = data << 1;
20010 + RaiseClock(pAd, &x);
20011 +
20012 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20013 +
20014 + x &= ~(EEDI);
20015 + if(x & EEDO)
20016 + data |= 1;
20017 +
20018 + LowerClock(pAd, &x);
20019 + }
20020 +
20021 + return data;
20022 +}
20023 +
20024 +// IRQL = PASSIVE_LEVEL
20025 +VOID ShiftOutBits(
20026 + IN PRTMP_ADAPTER pAd,
20027 + IN USHORT data,
20028 + IN USHORT count)
20029 +{
20030 + UINT32 x,mask;
20031 +
20032 + mask = 0x01 << (count - 1);
20033 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20034 +
20035 + x &= ~(EEDO | EEDI);
20036 +
20037 + do
20038 + {
20039 + x &= ~EEDI;
20040 + if(data & mask) x |= EEDI;
20041 +
20042 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
20043 +
20044 + RaiseClock(pAd, &x);
20045 + LowerClock(pAd, &x);
20046 +
20047 + mask = mask >> 1;
20048 + } while(mask);
20049 +
20050 + x &= ~EEDI;
20051 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
20052 +}
20053 +
20054 +// IRQL = PASSIVE_LEVEL
20055 +VOID EEpromCleanup(
20056 + IN PRTMP_ADAPTER pAd)
20057 +{
20058 + UINT32 x;
20059 +
20060 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20061 +
20062 + x &= ~(EECS | EEDI);
20063 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
20064 +
20065 + RaiseClock(pAd, &x);
20066 + LowerClock(pAd, &x);
20067 +}
20068 +
20069 +VOID EWEN(
20070 + IN PRTMP_ADAPTER pAd)
20071 +{
20072 + UINT32 x;
20073 +
20074 + // reset bits and set EECS
20075 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20076 + x &= ~(EEDI | EEDO | EESK);
20077 + x |= EECS;
20078 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
20079 +
20080 + // kick a pulse
20081 + RaiseClock(pAd, &x);
20082 + LowerClock(pAd, &x);
20083 +
20084 + // output the read_opcode and six pulse in that order
20085 + ShiftOutBits(pAd, EEPROM_EWEN_OPCODE, 5);
20086 + ShiftOutBits(pAd, 0, 6);
20087 +
20088 + EEpromCleanup(pAd);
20089 +}
20090 +
20091 +VOID EWDS(
20092 + IN PRTMP_ADAPTER pAd)
20093 +{
20094 + UINT32 x;
20095 +
20096 + // reset bits and set EECS
20097 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20098 + x &= ~(EEDI | EEDO | EESK);
20099 + x |= EECS;
20100 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
20101 +
20102 + // kick a pulse
20103 + RaiseClock(pAd, &x);
20104 + LowerClock(pAd, &x);
20105 +
20106 + // output the read_opcode and six pulse in that order
20107 + ShiftOutBits(pAd, EEPROM_EWDS_OPCODE, 5);
20108 + ShiftOutBits(pAd, 0, 6);
20109 +
20110 + EEpromCleanup(pAd);
20111 +}
20112 +
20113 +// IRQL = PASSIVE_LEVEL
20114 +USHORT RTMP_EEPROM_READ16(
20115 + IN PRTMP_ADAPTER pAd,
20116 + IN USHORT Offset)
20117 +{
20118 + UINT32 x;
20119 + USHORT data;
20120 +
20121 + Offset /= 2;
20122 + // reset bits and set EECS
20123 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20124 + x &= ~(EEDI | EEDO | EESK);
20125 + x |= EECS;
20126 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
20127 +
20128 + // kick a pulse
20129 + RaiseClock(pAd, &x);
20130 + LowerClock(pAd, &x);
20131 +
20132 + // output the read_opcode and register number in that order
20133 + ShiftOutBits(pAd, EEPROM_READ_OPCODE, 3);
20134 + ShiftOutBits(pAd, Offset, pAd->EEPROMAddressNum);
20135 +
20136 + // Now read the data (16 bits) in from the selected EEPROM word
20137 + data = ShiftInBits(pAd);
20138 +
20139 + EEpromCleanup(pAd);
20140 +
20141 + return data;
20142 +} //ReadEEprom
20143 +
20144 +VOID RTMP_EEPROM_WRITE16(
20145 + IN PRTMP_ADAPTER pAd,
20146 + IN USHORT Offset,
20147 + IN USHORT Data)
20148 +{
20149 + UINT32 x;
20150 +
20151 + Offset /= 2;
20152 +
20153 + EWEN(pAd);
20154 +
20155 + // reset bits and set EECS
20156 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20157 + x &= ~(EEDI | EEDO | EESK);
20158 + x |= EECS;
20159 + RTMP_IO_WRITE32(pAd, E2PROM_CSR, x);
20160 +
20161 + // kick a pulse
20162 + RaiseClock(pAd, &x);
20163 + LowerClock(pAd, &x);
20164 +
20165 + // output the read_opcode ,register number and data in that order
20166 + ShiftOutBits(pAd, EEPROM_WRITE_OPCODE, 3);
20167 + ShiftOutBits(pAd, Offset, pAd->EEPROMAddressNum);
20168 + ShiftOutBits(pAd, Data, 16); // 16-bit access
20169 +
20170 + // read DO status
20171 + RTMP_IO_READ32(pAd, E2PROM_CSR, &x);
20172 +
20173 + EEpromCleanup(pAd);
20174 +
20175 + RTMPusecDelay(10000); //delay for twp(MAX)=10ms
20176 +
20177 + EWDS(pAd);
20178 +
20179 + EEpromCleanup(pAd);
20180 +}
20181 +
20182 --- /dev/null
20183 +++ b/drivers/staging/rt2860/common/firmware.h
20184 @@ -0,0 +1,558 @@
20185 +/*
20186 + Copyright (c) 2007, Ralink Technology Corporation
20187 + All rights reserved.
20188 +
20189 + Redistribution. Redistribution and use in binary form, without
20190 + modification, are permitted provided that the following conditions are
20191 + met:
20192 +
20193 + * Redistributions must reproduce the above copyright notice and the
20194 + following disclaimer in the documentation and/or other materials
20195 + provided with the distribution.
20196 + * Neither the name of Ralink Technology Corporation nor the names of its
20197 + suppliers may be used to endorse or promote products derived from this
20198 + software without specific prior written permission.
20199 + * No reverse engineering, decompilation, or disassembly of this software
20200 + is permitted.
20201 +
20202 + Limited patent license. Ralink Technology Corporation grants a world-wide,
20203 + royalty-free, non-exclusive license under patents it now or hereafter
20204 + owns or controls to make, have made, use, import, offer to sell and
20205 + sell ("Utilize") this software, but solely to the extent that any
20206 + such patent is necessary to Utilize the software alone, or in
20207 + combination with an operating system licensed under an approved Open
20208 + Source license as listed by the Open Source Initiative at
20209 + http://opensource.org/licenses. The patent license shall not apply to
20210 + any other combinations which include this software. No hardware per
20211 + se is licensed hereunder.
20212 +
20213 + DISCLAIMER. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
20214 + CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING,
20215 + BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
20216 + FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
20217 + COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
20218 + INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
20219 + BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
20220 + OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
20221 + ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
20222 + TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
20223 + USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
20224 + DAMAGE.
20225 +*/
20226 +/* AUTO GEN PLEASE DO NOT MODIFY IT */
20227 +/* AUTO GEN PLEASE DO NOT MODIFY IT */
20228 +
20229 +
20230 +UCHAR FirmwareImage [] = {
20231 +0x02, 0x03, 0x5e, 0x02, 0x02, 0xb1, 0x22, 0x22, 0xff, 0xff, 0xff, 0x02, 0x01, 0x82, 0xff, 0xff,
20232 +0xff, 0xff, 0xff, 0x02, 0x00, 0x1e, 0xff, 0xff, 0xff, 0xff, 0xff, 0x02, 0x01, 0x33, 0xc0, 0xe0,
20233 +0xc0, 0xf0, 0xc0, 0x83, 0xc0, 0x82, 0xc0, 0xd0, 0x75, 0xd0, 0x18, 0xc2, 0xaf, 0x30, 0x45, 0x03,
20234 +0x12, 0x10, 0x09, 0x90, 0x04, 0x16, 0xe0, 0x30, 0xe3, 0x03, 0x74, 0x08, 0xf0, 0x90, 0x04, 0x14,
20235 +0xe0, 0x20, 0xe7, 0x03, 0x02, 0x00, 0xcb, 0x74, 0x80, 0xf0, 0x90, 0x70, 0x12, 0xe0, 0xf5, 0x2f,
20236 +0x90, 0x04, 0x04, 0xe0, 0x24, 0xcf, 0x60, 0x30, 0x14, 0x60, 0x42, 0x24, 0xe2, 0x60, 0x47, 0x14,
20237 +0x60, 0x55, 0x24, 0x21, 0x70, 0x60, 0xe5, 0x55, 0x24, 0xfe, 0x60, 0x07, 0x14, 0x60, 0x08, 0x24,
20238 +0x02, 0x70, 0x08, 0x7d, 0x01, 0x80, 0x28, 0x7d, 0x02, 0x80, 0x24, 0x90, 0x70, 0x10, 0xe0, 0xf5,
20239 +0x50, 0x85, 0x2f, 0x40, 0xd2, 0x01, 0x80, 0x3e, 0xe5, 0x55, 0x64, 0x03, 0x60, 0x04, 0xe5, 0x55,
20240 +0x70, 0x04, 0x7d, 0x02, 0x80, 0x09, 0x85, 0x2f, 0x41, 0xd2, 0x02, 0x80, 0x29, 0xad, 0x55, 0xaf,
20241 +0x2f, 0x12, 0x02, 0x8d, 0x80, 0x20, 0x90, 0x70, 0x10, 0xe0, 0xf5, 0x47, 0x90, 0x70, 0x11, 0xe0,
20242 +0xf5, 0x44, 0x12, 0x10, 0x25, 0x80, 0x06, 0x90, 0x70, 0x10, 0xe0, 0xf5, 0x45, 0xe4, 0xfd, 0xaf,
20243 +0x2f, 0x12, 0x02, 0x8d, 0xd2, 0x04, 0x90, 0x70, 0x13, 0xe4, 0xf0, 0xd2, 0xaf, 0xd0, 0xd0, 0xd0,
20244 +0x82, 0xd0, 0x83, 0xd0, 0xf0, 0xd0, 0xe0, 0x32, 0x90, 0x70, 0x2a, 0xe0, 0x30, 0xe1, 0x53, 0xc2,
20245 +0xaf, 0x90, 0x70, 0x28, 0xe0, 0x90, 0x10, 0x1c, 0xf0, 0x90, 0x70, 0x29, 0xe0, 0x90, 0x10, 0x1d,
20246 +0xf0, 0x90, 0x70, 0x2a, 0xe0, 0x90, 0x10, 0x1e, 0xf0, 0x90, 0x10, 0x1c, 0xe0, 0xf5, 0x30, 0x90,
20247 +0x10, 0x1e, 0xe0, 0x20, 0xe1, 0xf3, 0x90, 0x10, 0x1c, 0xe0, 0x90, 0x70, 0x28, 0xf0, 0x90, 0x10,
20248 +0x1d, 0xe0, 0x90, 0x70, 0x29, 0xf0, 0x90, 0x10, 0x1e, 0xe0, 0x90, 0x70, 0x2a, 0xf0, 0x30, 0x4a,
20249 +0x0d, 0x90, 0x70, 0x24, 0xe0, 0x44, 0x01, 0xf0, 0x90, 0x02, 0x2c, 0x74, 0xff, 0xf0, 0xc2, 0x05,
20250 +0xd2, 0xaf, 0x22, 0xc0, 0xe0, 0xc0, 0xf0, 0xc0, 0x83, 0xc0, 0x82, 0xc0, 0xd0, 0xe8, 0xc0, 0xe0,
20251 +0xe9, 0xc0, 0xe0, 0xea, 0xc0, 0xe0, 0xeb, 0xc0, 0xe0, 0xec, 0xc0, 0xe0, 0xed, 0xc0, 0xe0, 0xee,
20252 +0xc0, 0xe0, 0xef, 0xc0, 0xe0, 0xc2, 0xaf, 0x30, 0x45, 0x03, 0x12, 0x10, 0x12, 0xd2, 0xaf, 0xd0,
20253 +0xe0, 0xff, 0xd0, 0xe0, 0xfe, 0xd0, 0xe0, 0xfd, 0xd0, 0xe0, 0xfc, 0xd0, 0xe0, 0xfb, 0xd0, 0xe0,
20254 +0xfa, 0xd0, 0xe0, 0xf9, 0xd0, 0xe0, 0xf8, 0xd0, 0xd0, 0xd0, 0x82, 0xd0, 0x83, 0xd0, 0xf0, 0xd0,
20255 +0xe0, 0x32, 0xc0, 0xe0, 0xc0, 0xf0, 0xc0, 0x83, 0xc0, 0x82, 0xc0, 0xd0, 0x75, 0xd0, 0x10, 0xc2,
20256 +0xaf, 0x30, 0x45, 0x03, 0x12, 0x10, 0x0c, 0x30, 0x58, 0x0a, 0xe5, 0x54, 0x60, 0x04, 0x15, 0x54,
20257 +0x80, 0x02, 0xc2, 0x58, 0x30, 0x59, 0x0a, 0xe5, 0x50, 0x60, 0x04, 0x15, 0x50, 0x80, 0x02, 0xc2,
20258 +0x59, 0xd5, 0x53, 0x07, 0x30, 0x60, 0x04, 0x15, 0x46, 0xd2, 0x04, 0x30, 0x45, 0x03, 0x12, 0x10,
20259 +0x0f, 0xc2, 0x8d, 0xd2, 0xaf, 0xd0, 0xd0, 0xd0, 0x82, 0xd0, 0x83, 0xd0, 0xf0, 0xd0, 0xe0, 0x32,
20260 +0x12, 0x02, 0xd3, 0x30, 0x45, 0x03, 0x12, 0x10, 0x03, 0x30, 0x01, 0x06, 0x20, 0x09, 0x03, 0x12,
20261 +0x10, 0x1c, 0x30, 0x02, 0x06, 0x20, 0x0a, 0x03, 0x12, 0x10, 0x1f, 0x30, 0x03, 0x06, 0x20, 0x0b,
20262 +0x03, 0x12, 0x10, 0x1f, 0x30, 0x04, 0x06, 0x20, 0x0c, 0x03, 0x12, 0x10, 0x22, 0x20, 0x13, 0x09,
20263 +0x20, 0x11, 0x06, 0xe5, 0x2b, 0x45, 0x2c, 0x60, 0x03, 0xd3, 0x80, 0x01, 0xc3, 0x92, 0xa9, 0x12,
20264 +0x02, 0xec, 0x80, 0xbf, 0xc2, 0x43, 0xd2, 0x45, 0xe4, 0xf5, 0x20, 0xf5, 0x21, 0xf5, 0x53, 0xf5,
20265 +0x46, 0xf5, 0x2b, 0xf5, 0x2c, 0xc2, 0x42, 0xf5, 0x51, 0xf5, 0x52, 0xf5, 0x55, 0x90, 0x04, 0x18,
20266 +0x74, 0x80, 0xf0, 0x90, 0x04, 0x1a, 0x74, 0x08, 0xf0, 0xc2, 0x19, 0xc2, 0x18, 0xc2, 0x1a, 0x22,
20267 +0xc8, 0xef, 0xc8, 0xe6, 0xfa, 0x08, 0xe6, 0x4a, 0x60, 0x0c, 0xc8, 0xef, 0xc8, 0x08, 0xe6, 0x16,
20268 +0x18, 0x70, 0x01, 0x16, 0xc3, 0x22, 0xed, 0x24, 0xff, 0xfd, 0xec, 0x34, 0xff, 0xc8, 0xef, 0xc8,
20269 +0xf6, 0x08, 0xc6, 0xed, 0xc6, 0xd3, 0x22, 0xd0, 0x83, 0xd0, 0x82, 0xf8, 0xe4, 0x93, 0x70, 0x12,
20270 +0x74, 0x01, 0x93, 0x70, 0x0d, 0xa3, 0xa3, 0x93, 0xf8, 0x74, 0x01, 0x93, 0xf5, 0x82, 0x88, 0x83,
20271 +0xe4, 0x73, 0x74, 0x02, 0x93, 0x68, 0x60, 0xef, 0xa3, 0xa3, 0xa3, 0x80, 0xdf, 0xef, 0xf4, 0x60,
20272 +0x1f, 0xe4, 0xfe, 0x12, 0x03, 0x6a, 0xe0, 0xb4, 0xff, 0x12, 0x12, 0x03, 0x6a, 0xef, 0xf0, 0x74,
20273 +0x1c, 0x2e, 0xf5, 0x82, 0xe4, 0x34, 0x70, 0xf5, 0x83, 0xed, 0xf0, 0x22, 0x0e, 0xbe, 0x04, 0xe3,
20274 +0x22, 0xc0, 0xe0, 0xc0, 0xf0, 0xc0, 0x83, 0xc0, 0x82, 0xc0, 0xd0, 0x75, 0xd0, 0x08, 0xc2, 0xaf,
20275 +0x30, 0x45, 0x03, 0x12, 0x10, 0x06, 0xd2, 0xaf, 0xd0, 0xd0, 0xd0, 0x82, 0xd0, 0x83, 0xd0, 0xf0,
20276 +0xd0, 0xe0, 0x32, 0xc2, 0xaf, 0x12, 0x00, 0x06, 0x12, 0x02, 0x14, 0x12, 0x03, 0x1c, 0xe4, 0xf5,
20277 +0x22, 0xf5, 0x47, 0x90, 0x04, 0x00, 0x74, 0x80, 0xf0, 0xd2, 0xaf, 0x22, 0x30, 0x45, 0x03, 0x12,
20278 +0x10, 0x15, 0xe5, 0x20, 0x70, 0x03, 0x20, 0x10, 0x03, 0x30, 0x11, 0x03, 0x43, 0x87, 0x01, 0x22,
20279 +0xc0, 0x2a, 0x74, 0x03, 0xc0, 0xe0, 0xc0, 0x82, 0xc0, 0x83, 0x75, 0x2a, 0x0a, 0x22, 0xc0, 0x2a,
20280 +0x74, 0x03, 0xc0, 0xe0, 0xc0, 0x82, 0xc0, 0x83, 0x75, 0x2a, 0x18, 0x22, 0x75, 0x89, 0x02, 0xe4,
20281 +0xf5, 0x8c, 0xf5, 0x8a, 0xf5, 0x88, 0xf5, 0xb8, 0xf5, 0xe8, 0x75, 0x90, 0x18, 0xd2, 0x8c, 0x75,
20282 +0xa8, 0x05, 0x22, 0xce, 0xef, 0xce, 0xee, 0x60, 0x08, 0x7f, 0xff, 0x12, 0x03, 0x80, 0x1e, 0x80,
20283 +0xf5, 0x22, 0xc8, 0xef, 0xc8, 0xe6, 0x60, 0x03, 0x16, 0xc3, 0x22, 0xed, 0x14, 0xf6, 0xd3, 0x22,
20284 +0xc8, 0xef, 0xc8, 0xe6, 0x60, 0x06, 0x16, 0xe6, 0x24, 0xff, 0xb3, 0x22, 0xc3, 0x22, 0x78, 0x7f,
20285 +0xe4, 0xf6, 0xd8, 0xfd, 0x75, 0x81, 0x5f, 0x02, 0x01, 0xd0, 0x74, 0x14, 0x2e, 0xf5, 0x82, 0xe4,
20286 +0x34, 0x70, 0xf5, 0x83, 0x22, 0xef, 0x90, 0x03, 0x7e, 0x93, 0x90, 0x03, 0x00, 0x73, 0x0a, 0x18,
20287 +0xef, 0x60, 0x03, 0x1f, 0x80, 0xfa, 0x22, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20288 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20289 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20290 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20291 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20292 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20293 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20294 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20295 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20296 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20297 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20298 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20299 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20300 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20301 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20302 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20303 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20304 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20305 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20306 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20307 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20308 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20309 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20310 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20311 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20312 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20313 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20314 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20315 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20316 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20317 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20318 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20319 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20320 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20321 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20322 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20323 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20324 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20325 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20326 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20327 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20328 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20329 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20330 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20331 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20332 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20333 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20334 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20335 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20336 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20337 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20338 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20339 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20340 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20341 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20342 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20343 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20344 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20345 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20346 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20347 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20348 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20349 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20350 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20351 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20352 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20353 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20354 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20355 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20356 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20357 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20358 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20359 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20360 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20361 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20362 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20363 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20364 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20365 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20366 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20367 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20368 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20369 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20370 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20371 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20372 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20373 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20374 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20375 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20376 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20377 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20378 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20379 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20380 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20381 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20382 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20383 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20384 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20385 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20386 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20387 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20388 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20389 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20390 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20391 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20392 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20393 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20394 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20395 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20396 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20397 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20398 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20399 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20400 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20401 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20402 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20403 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20404 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20405 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20406 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20407 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20408 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20409 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20410 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20411 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20412 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20413 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20414 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20415 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20416 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20417 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20418 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20419 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20420 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20421 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20422 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20423 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20424 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20425 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20426 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20427 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20428 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20429 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20430 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20431 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20432 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20433 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20434 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20435 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20436 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20437 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20438 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20439 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20440 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20441 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20442 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20443 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20444 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20445 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20446 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20447 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20448 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20449 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20450 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20451 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20452 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20453 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20454 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20455 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20456 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20457 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20458 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20459 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20460 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20461 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20462 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20463 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20464 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20465 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20466 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20467 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20468 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20469 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20470 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20471 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20472 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20473 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20474 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20475 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20476 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20477 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20478 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20479 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20480 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20481 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20482 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20483 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20484 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20485 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20486 +0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
20487 +0xff, 0xff, 0xff, 0x02, 0x10, 0x28, 0x02, 0x10, 0x3b, 0x02, 0x10, 0x3c, 0x02, 0x12, 0xb8, 0x02,
20488 +0x12, 0xb9, 0x02, 0x13, 0x3e, 0x02, 0x13, 0x3f, 0xc3, 0x22, 0xff, 0xff, 0x02, 0x16, 0x56, 0x02,
20489 +0x17, 0x6b, 0x02, 0x14, 0x2a, 0x02, 0x13, 0x40, 0x30, 0x05, 0x06, 0x20, 0x0d, 0x03, 0x12, 0x00,
20490 +0xd8, 0x30, 0x06, 0x06, 0x20, 0x0e, 0x03, 0x12, 0x18, 0x5e, 0x22, 0x22, 0x90, 0x04, 0x14, 0xe0,
20491 +0x20, 0xe7, 0x03, 0x02, 0x12, 0xb7, 0x90, 0x70, 0x12, 0xe0, 0xf5, 0x56, 0x90, 0x04, 0x04, 0xe0,
20492 +0x12, 0x02, 0x67, 0x11, 0x4e, 0x30, 0x11, 0x25, 0x31, 0x10, 0x87, 0x33, 0x10, 0xaa, 0x34, 0x10,
20493 +0xc3, 0x35, 0x11, 0x57, 0x50, 0x11, 0x7b, 0x51, 0x11, 0x84, 0x52, 0x11, 0x84, 0x53, 0x11, 0x84,
20494 +0x54, 0x11, 0xc5, 0x55, 0x11, 0xdc, 0x70, 0x12, 0x07, 0x71, 0x12, 0x34, 0x72, 0x12, 0x5e, 0x80,
20495 +0x12, 0x81, 0x83, 0x00, 0x00, 0x12, 0xb7, 0x75, 0x24, 0x05, 0x75, 0x25, 0xdc, 0x90, 0x70, 0x9f,
20496 +0x74, 0x12, 0xf0, 0xd2, 0x18, 0xd2, 0x61, 0x75, 0x35, 0x0d, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5,
20497 +0x56, 0xf4, 0x70, 0x03, 0x02, 0x12, 0xb7, 0x02, 0x12, 0xaa, 0xc2, 0x18, 0x90, 0x01, 0x14, 0xe0,
20498 +0x54, 0xfd, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x70, 0x03, 0x02, 0x12, 0xb7,
20499 +0x02, 0x12, 0xaa, 0xe5, 0x55, 0x64, 0x02, 0x70, 0x37, 0x90, 0x70, 0x10, 0xe0, 0x60, 0x08, 0x90,
20500 +0x01, 0x0d, 0x74, 0x09, 0xf0, 0x80, 0x25, 0xe5, 0x34, 0x14, 0x60, 0x0a, 0x14, 0x60, 0x0f, 0x14,
20501 +0x60, 0x14, 0x24, 0x03, 0x70, 0x16, 0x90, 0x01, 0x0d, 0x74, 0x08, 0xf0, 0x80, 0x0e, 0x90, 0x01,
20502 +0x0d, 0x74, 0x0b, 0xf0, 0x80, 0x06, 0x90, 0x01, 0x0d, 0x74, 0x1b, 0xf0, 0x7d, 0x01, 0x80, 0x02,
20503 +0x7d, 0x02, 0xaf, 0x56, 0x12, 0x02, 0x8d, 0x90, 0x70, 0x11, 0xe0, 0x24, 0xff, 0x92, 0x1b, 0x90,
20504 +0x04, 0x14, 0x74, 0x80, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x70, 0x03, 0x02,
20505 +0x12, 0xb7, 0x02, 0x12, 0xaa, 0x20, 0x02, 0x03, 0x30, 0x03, 0x1d, 0x7d, 0x02, 0xaf, 0x56, 0x12,
20506 +0x02, 0x8d, 0x90, 0x04, 0x14, 0x74, 0x80, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4,
20507 +0x70, 0x03, 0x02, 0x12, 0xb7, 0x02, 0x12, 0xaa, 0x85, 0x56, 0x41, 0xd2, 0x02, 0x22, 0x90, 0x70,
20508 +0x11, 0xe0, 0x24, 0xff, 0x92, 0x1b, 0x22, 0x90, 0x70, 0x10, 0xe0, 0x54, 0x7f, 0x64, 0x02, 0x60,
20509 +0x03, 0x02, 0x12, 0xb7, 0x90, 0x70, 0x11, 0xe0, 0x64, 0x08, 0x60, 0x08, 0xe0, 0x64, 0x20, 0x60,
20510 +0x03, 0x02, 0x12, 0xb7, 0x75, 0x4e, 0x03, 0x75, 0x4f, 0x20, 0x22, 0x90, 0x70, 0x11, 0xe0, 0x24,
20511 +0xff, 0x92, 0x47, 0x22, 0x90, 0x04, 0x04, 0xe0, 0x25, 0xe0, 0x24, 0x5d, 0xf5, 0x57, 0x90, 0x70,
20512 +0x10, 0xe0, 0xff, 0x74, 0x47, 0x25, 0x57, 0xf8, 0xc6, 0xef, 0xc6, 0x90, 0x70, 0x11, 0xe0, 0xff,
20513 +0x74, 0x48, 0x25, 0x57, 0xf8, 0xc6, 0xef, 0xc6, 0xe4, 0xfd, 0xaf, 0x56, 0x12, 0x02, 0x8d, 0x90,
20514 +0x04, 0x14, 0x74, 0x80, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x70, 0x03, 0x02,
20515 +0x12, 0xb7, 0x02, 0x12, 0xaa, 0xe5, 0x47, 0xb4, 0x07, 0x08, 0x90, 0x70, 0x11, 0xe0, 0x54, 0x07,
20516 +0xf5, 0x26, 0xe4, 0xfd, 0xaf, 0x56, 0x12, 0x02, 0x8d, 0xd2, 0x04, 0x22, 0x90, 0x70, 0x10, 0xe0,
20517 +0xfe, 0x90, 0x70, 0x11, 0xe0, 0xfd, 0xed, 0xf8, 0xe6, 0xf5, 0x57, 0xfd, 0xaf, 0x56, 0x12, 0x02,
20518 +0x8d, 0x90, 0x04, 0x14, 0x74, 0x80, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x70,
20519 +0x03, 0x02, 0x12, 0xb7, 0x02, 0x12, 0xaa, 0x90, 0x70, 0x10, 0xe0, 0xfe, 0x90, 0x70, 0x11, 0xe0,
20520 +0xfd, 0xed, 0xf5, 0x82, 0x8e, 0x83, 0xe0, 0xf5, 0x57, 0xfd, 0xaf, 0x56, 0x12, 0x02, 0x8d, 0x90,
20521 +0x04, 0x14, 0x74, 0x80, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x70, 0x03, 0x02,
20522 +0x12, 0xb7, 0x80, 0x76, 0xe4, 0xf5, 0x4e, 0xf5, 0x4f, 0x75, 0x26, 0xff, 0xc2, 0x19, 0xc2, 0x18,
20523 +0xc2, 0x1a, 0x75, 0x34, 0xff, 0xad, 0x57, 0xaf, 0x56, 0x12, 0x02, 0x8d, 0x90, 0x04, 0x14, 0x74,
20524 +0x80, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x60, 0x5b, 0x80, 0x4c, 0x90, 0x70,
20525 +0x10, 0xe0, 0x24, 0xff, 0x92, 0x4a, 0xd2, 0x05, 0xad, 0x57, 0xaf, 0x56, 0x12, 0x02, 0x8d, 0x90,
20526 +0x04, 0x14, 0x74, 0x80, 0xf0, 0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x60, 0x38, 0x80,
20527 +0x29, 0x90, 0x70, 0x10, 0xe0, 0xf5, 0x34, 0xd3, 0x94, 0x00, 0x40, 0x07, 0x90, 0x01, 0x0d, 0xe0,
20528 +0x54, 0xfb, 0xf0, 0xad, 0x57, 0xaf, 0x56, 0x12, 0x02, 0x8d, 0x90, 0x04, 0x14, 0x74, 0x80, 0xf0,
20529 +0xe4, 0x90, 0x70, 0x13, 0xf0, 0xe5, 0x56, 0xf4, 0x60, 0x0d, 0x90, 0x70, 0x25, 0xe0, 0x44, 0x01,
20530 +0xf0, 0x90, 0x02, 0x2c, 0x74, 0xff, 0xf0, 0x22, 0x22, 0xe5, 0x53, 0x60, 0x03, 0x02, 0x13, 0x3d,
20531 +0xe5, 0x4f, 0x45, 0x4e, 0x60, 0x08, 0xe5, 0x4f, 0x15, 0x4f, 0x70, 0x02, 0x15, 0x4e, 0xa2, 0x19,
20532 +0xe4, 0x33, 0x90, 0x70, 0x90, 0xf0, 0xa2, 0x18, 0xe4, 0x33, 0xa3, 0xf0, 0x30, 0x19, 0x4d, 0x90,
20533 +0x70, 0x98, 0x74, 0x23, 0xf0, 0xa3, 0xe5, 0x25, 0xf0, 0xe5, 0x24, 0xa3, 0xf0, 0x7f, 0x35, 0x7d,
20534 +0x32, 0x12, 0x03, 0x42, 0x50, 0x09, 0x90, 0x10, 0x04, 0xe0, 0x54, 0xf7, 0xf0, 0xd2, 0x06, 0xe5,
20535 +0x35, 0xd3, 0x94, 0x10, 0x40, 0x1e, 0x30, 0x1a, 0x1b, 0xc2, 0x1a, 0xa2, 0x18, 0x92, 0x19, 0x20,
20536 +0x19, 0x12, 0x90, 0x04, 0x09, 0xe0, 0x54, 0xdd, 0xf0, 0x90, 0x10, 0x04, 0xe0, 0x44, 0x08, 0xf0,
20537 +0xc2, 0x61, 0xd2, 0x03, 0xe5, 0x35, 0xb4, 0x0b, 0x14, 0xd2, 0x03, 0x22, 0xe4, 0xf5, 0x35, 0xa2,
20538 +0x18, 0x92, 0x19, 0x30, 0x19, 0x07, 0x90, 0x04, 0x09, 0xe0, 0x44, 0x22, 0xf0, 0x22, 0x22, 0x22,
20539 +0xc2, 0x4b, 0xc2, 0x4c, 0xe5, 0x44, 0x12, 0x02, 0x67, 0x13, 0x62, 0x00, 0x13, 0xf5, 0x04, 0x13,
20540 +0xf1, 0x08, 0x13, 0xcc, 0x10, 0x13, 0x76, 0x20, 0x13, 0x96, 0x60, 0x13, 0xa7, 0xa0, 0x00, 0x00,
20541 +0x13, 0xf7, 0x85, 0x48, 0x43, 0x85, 0x4a, 0x42, 0x85, 0x4c, 0x5e, 0xe5, 0x47, 0x64, 0x06, 0x60,
20542 +0x03, 0x02, 0x13, 0xf7, 0x80, 0x1b, 0xe5, 0x48, 0xc4, 0x54, 0x0f, 0xf5, 0x43, 0xe5, 0x4a, 0xc4,
20543 +0x54, 0x0f, 0xf5, 0x42, 0xe5, 0x4c, 0xc4, 0x54, 0x0f, 0xf5, 0x5e, 0xe5, 0x47, 0x64, 0x06, 0x70,
20544 +0x66, 0x53, 0x43, 0x0f, 0x80, 0x61, 0x85, 0x49, 0x43, 0x85, 0x4b, 0x42, 0x85, 0x4d, 0x5e, 0xe5,
20545 +0x47, 0x64, 0x06, 0x70, 0x52, 0x80, 0x1b, 0xe5, 0x49, 0xc4, 0x54, 0x0f, 0xf5, 0x43, 0xe5, 0x4b,
20546 +0xc4, 0x54, 0x0f, 0xf5, 0x42, 0xe5, 0x4d, 0xc4, 0x54, 0x0f, 0xf5, 0x5e, 0xe5, 0x47, 0x64, 0x06,
20547 +0x70, 0x35, 0xe5, 0x43, 0x54, 0x0f, 0x44, 0x10, 0xf5, 0x43, 0x80, 0x2b, 0xe5, 0x47, 0xb4, 0x04,
20548 +0x06, 0x53, 0x5e, 0xfb, 0x75, 0x42, 0x09, 0xe5, 0x47, 0xb4, 0x05, 0x06, 0x43, 0x5e, 0x04, 0x75,
20549 +0x42, 0x09, 0xe5, 0x47, 0xb4, 0x06, 0x10, 0xe5, 0x43, 0x54, 0x0f, 0x44, 0x30, 0xf5, 0x43, 0x80,
20550 +0x06, 0xd2, 0x4b, 0x80, 0x02, 0xd2, 0x4c, 0xe4, 0xf5, 0x38, 0xe5, 0x42, 0xc4, 0x54, 0xf0, 0xff,
20551 +0xe5, 0x43, 0x54, 0x0f, 0x4f, 0xf5, 0x5f, 0x90, 0x70, 0x44, 0xf0, 0xa3, 0xe5, 0x5e, 0xf0, 0xa3,
20552 +0xe5, 0x4a, 0xf0, 0xa3, 0xe5, 0x48, 0xf0, 0xa3, 0xe5, 0x4c, 0xf0, 0xa3, 0xe5, 0x44, 0xf0, 0xa3,
20553 +0xe5, 0x42, 0xf0, 0xa3, 0xe5, 0x43, 0xf0, 0xd2, 0x60, 0x22, 0xe5, 0x47, 0x60, 0x10, 0x24, 0xc0,
20554 +0x70, 0x03, 0x12, 0x16, 0x36, 0x12, 0x14, 0x3f, 0xc2, 0xaf, 0xc2, 0x04, 0xd2, 0xaf, 0x22, 0xc2,
20555 +0xaf, 0x90, 0x04, 0x14, 0xe0, 0x54, 0x0e, 0x60, 0x04, 0xd2, 0x1c, 0x80, 0x08, 0xe5, 0x4e, 0x45,
20556 +0x4f, 0x24, 0xff, 0x92, 0x1c, 0xd2, 0xaf, 0x90, 0x04, 0x14, 0xe0, 0xa2, 0xe4, 0x92, 0x1d, 0x74,
20557 +0x1e, 0xf0, 0xe5, 0x5f, 0x54, 0x0f, 0xf5, 0x2d, 0xe5, 0x38, 0x70, 0x13, 0x30, 0x1c, 0x05, 0xe5,
20558 +0x5f, 0x20, 0xe5, 0x0b, 0x30, 0x1d, 0x19, 0xe5, 0x5f, 0x54, 0x30, 0xff, 0xbf, 0x30, 0x11, 0xe5,
20559 +0x38, 0x70, 0x05, 0x75, 0x38, 0x0c, 0x80, 0x02, 0x15, 0x38, 0xd2, 0x6c, 0xd2, 0x6d, 0x80, 0x0f,
20560 +0xe5, 0x5f, 0x30, 0xe6, 0x06, 0xc2, 0x6c, 0xd2, 0x6d, 0x80, 0x04, 0xd2, 0x6c, 0xc2, 0x6d, 0xe5,
20561 +0x47, 0x64, 0x03, 0x70, 0x21, 0x30, 0x4b, 0x06, 0xc2, 0x6c, 0xd2, 0x6d, 0x80, 0x18, 0xe5, 0x38,
20562 +0x70, 0x03, 0x30, 0x4c, 0x11, 0xc2, 0x4c, 0xe5, 0x38, 0x70, 0x05, 0x75, 0x38, 0x07, 0x80, 0x02,
20563 +0x15, 0x38, 0xd2, 0x6c, 0xd2, 0x6d, 0x90, 0x70, 0x46, 0xe5, 0x2d, 0xf0, 0x20, 0x69, 0x07, 0xe5,
20564 +0x5e, 0x20, 0xe0, 0x02, 0xb2, 0x68, 0x20, 0x6b, 0x07, 0xe5, 0x5e, 0x20, 0xe1, 0x02, 0xb2, 0x6a,
20565 +0x20, 0x6d, 0x07, 0xe5, 0x5e, 0x20, 0xe2, 0x02, 0xb2, 0x6c, 0x90, 0x70, 0x47, 0xe5, 0x2d, 0xf0,
20566 +0x75, 0x2e, 0x40, 0x20, 0x69, 0x04, 0xa2, 0x68, 0x80, 0x15, 0x30, 0x68, 0x06, 0xe5, 0x46, 0xa2,
20567 +0xe3, 0x80, 0x0c, 0xe5, 0x46, 0x54, 0xf0, 0xff, 0xbf, 0xf0, 0x03, 0xd3, 0x80, 0x01, 0xc3, 0x92,
20568 +0x73, 0x92, 0x72, 0x20, 0x6b, 0x04, 0xa2, 0x6a, 0x80, 0x15, 0x30, 0x6a, 0x06, 0xe5, 0x46, 0xa2,
20569 +0xe3, 0x80, 0x0c, 0xe5, 0x46, 0x54, 0xf0, 0xff, 0xbf, 0xf0, 0x03, 0xd3, 0x80, 0x01, 0xc3, 0x92,
20570 +0x75, 0x92, 0x74, 0x20, 0x6d, 0x04, 0xa2, 0x6c, 0x80, 0x15, 0x30, 0x6c, 0x06, 0xe5, 0x46, 0xa2,
20571 +0xe3, 0x80, 0x0c, 0xe5, 0x46, 0x54, 0xf0, 0xff, 0xbf, 0xf0, 0x03, 0xd3, 0x80, 0x01, 0xc3, 0x92,
20572 +0x71, 0x92, 0x70, 0x90, 0x10, 0x2f, 0xe5, 0x2e, 0xf0, 0xe5, 0x47, 0x64, 0x06, 0x70, 0x46, 0x90,
20573 +0x02, 0x29, 0xe0, 0x54, 0xfe, 0xf0, 0xe5, 0x43, 0xc4, 0x54, 0x0f, 0x14, 0x60, 0x14, 0x24, 0xfe,
20574 +0x60, 0x1f, 0x24, 0x03, 0x60, 0x03, 0x02, 0x16, 0x35, 0x90, 0x02, 0x28, 0xe0, 0x30, 0x47, 0x0d,
20575 +0x80, 0x07, 0x90, 0x02, 0x28, 0xe0, 0x20, 0x47, 0x04, 0x54, 0xfe, 0xf0, 0x22, 0x44, 0x01, 0xf0,
20576 +0x22, 0xe5, 0x46, 0x30, 0xe3, 0x04, 0x7f, 0x01, 0x80, 0x02, 0x7f, 0x00, 0x90, 0x02, 0x28, 0xe0,
20577 +0x54, 0xfe, 0x4f, 0xf0, 0x22, 0xe5, 0x47, 0x64, 0x07, 0x60, 0x03, 0x02, 0x16, 0x35, 0xf5, 0x27,
20578 +0x90, 0x02, 0x29, 0xe0, 0x54, 0xfc, 0xf0, 0xe5, 0x26, 0x14, 0x60, 0x26, 0x14, 0x60, 0x2e, 0x14,
20579 +0x60, 0x36, 0x24, 0x03, 0x70, 0x5f, 0xe5, 0x46, 0x13, 0x13, 0x13, 0x54, 0x1f, 0x75, 0xf0, 0x03,
20580 +0x84, 0xaf, 0xf0, 0x20, 0x47, 0x04, 0x7e, 0x01, 0x80, 0x02, 0x7e, 0x00, 0xef, 0x6e, 0x24, 0xff,
20581 +0x80, 0x02, 0xa2, 0x47, 0x92, 0x39, 0xa2, 0x47, 0xb3, 0x92, 0x38, 0x80, 0x3f, 0xe5, 0x46, 0x30,
20582 +0xe3, 0x03, 0xd3, 0x80, 0x27, 0xc3, 0x80, 0x24, 0xe5, 0x46, 0x30, 0xe3, 0x0d, 0x54, 0x70, 0xc3,
20583 +0x94, 0x60, 0x50, 0x06, 0x7e, 0x00, 0x7f, 0x01, 0x80, 0x04, 0x7e, 0x00, 0x7f, 0x00, 0x20, 0x47,
20584 +0x04, 0x7d, 0x01, 0x80, 0x02, 0x7d, 0x00, 0xef, 0x6d, 0x4e, 0x24, 0xff, 0x92, 0x38, 0xa2, 0x47,
20585 +0xb3, 0x92, 0x39, 0x80, 0x07, 0xa2, 0x47, 0xb3, 0x92, 0x38, 0x92, 0x39, 0x90, 0x02, 0x28, 0xe0,
20586 +0x54, 0xfc, 0x45, 0x27, 0xf0, 0x22, 0xe4, 0x90, 0x02, 0x29, 0xf0, 0x30, 0x47, 0x04, 0xaf, 0x45,
20587 +0x80, 0x04, 0xe5, 0x45, 0xf4, 0xff, 0x90, 0x02, 0x28, 0xef, 0xf0, 0x22, 0x8f, 0x50, 0xd2, 0x59,
20588 +0x22, 0x8f, 0x54, 0xd2, 0x58, 0x22, 0xe4, 0xf5, 0x30, 0xc2, 0xaf, 0xe5, 0x51, 0x14, 0x60, 0x4a,
20589 +0x14, 0x60, 0x6a, 0x24, 0x02, 0x60, 0x03, 0x02, 0x17, 0x4c, 0xd2, 0x59, 0x75, 0x55, 0x01, 0x20,
20590 +0x19, 0x1c, 0x90, 0x02, 0x08, 0xe0, 0x54, 0xfe, 0xf0, 0xe0, 0x20, 0xe1, 0x23, 0x90, 0x04, 0x34,
20591 +0xe0, 0xb4, 0x02, 0x1c, 0xa3, 0xe0, 0xb4, 0x02, 0x17, 0xa3, 0xe0, 0xb4, 0x02, 0x12, 0x7f, 0x20,
20592 +0x12, 0x16, 0x4c, 0x90, 0x10, 0x04, 0xe0, 0x54, 0xf3, 0xf0, 0x75, 0x51, 0x01, 0x02, 0x17, 0x4c,
20593 +0xe5, 0x50, 0x70, 0x06, 0x75, 0x30, 0x03, 0x02, 0x17, 0x4c, 0x90, 0x12, 0x00, 0xe0, 0x54, 0x03,
20594 +0x70, 0x15, 0x7f, 0x20, 0x12, 0x16, 0x4c, 0x20, 0x19, 0x07, 0x90, 0x02, 0x08, 0xe0, 0x54, 0xfb,
20595 +0xf0, 0x75, 0x51, 0x02, 0x02, 0x17, 0x4c, 0xe5, 0x50, 0x70, 0x02, 0x80, 0x7a, 0x20, 0x19, 0x0f,
20596 +0x90, 0x02, 0x08, 0xe0, 0x20, 0xe3, 0x6c, 0x90, 0x04, 0x37, 0xe0, 0x64, 0x22, 0x70, 0x64, 0x90,
20597 +0x12, 0x04, 0x74, 0x0a, 0xf0, 0x30, 0x1b, 0x11, 0x90, 0x13, 0x28, 0xe0, 0x54, 0xf0, 0xf0, 0xa3,
20598 +0xe0, 0x54, 0xf0, 0xf0, 0xa3, 0xe0, 0x54, 0xfa, 0xf0, 0x20, 0x19, 0x07, 0x90, 0x04, 0x01, 0xe0,
20599 +0x44, 0x10, 0xf0, 0xe5, 0x34, 0xf4, 0x90, 0x04, 0x01, 0x60, 0x06, 0xe0, 0x54, 0xfb, 0xf0, 0x80,
20600 +0x04, 0xe0, 0x54, 0xf9, 0xf0, 0x20, 0x19, 0x07, 0x90, 0x12, 0x04, 0xe0, 0x44, 0x04, 0xf0, 0xe5,
20601 +0x34, 0xf4, 0x60, 0x14, 0x90, 0x01, 0x0d, 0xe0, 0xf5, 0x33, 0xe5, 0x34, 0xd3, 0x94, 0x02, 0x40,
20602 +0x07, 0x90, 0x12, 0x04, 0xe0, 0x54, 0xfd, 0xf0, 0x75, 0x30, 0x01, 0x75, 0x55, 0x02, 0xe4, 0xf5,
20603 +0x51, 0x80, 0x09, 0xe5, 0x50, 0x70, 0x05, 0x75, 0x30, 0x03, 0xf5, 0x51, 0xe5, 0x30, 0x60, 0x18,
20604 +0xc2, 0x01, 0xe4, 0xf5, 0x51, 0xc2, 0x59, 0x20, 0x19, 0x0e, 0xad, 0x30, 0xaf, 0x40, 0x12, 0x18,
20605 +0x2a, 0xe5, 0x30, 0xb4, 0x03, 0x02, 0xd2, 0x03, 0xd2, 0xaf, 0x22, 0xc2, 0xaf, 0x30, 0x01, 0x0e,
20606 +0xe4, 0xf5, 0x51, 0xc2, 0x59, 0xc2, 0x01, 0x7d, 0x02, 0xaf, 0x40, 0x12, 0x18, 0x2a, 0xe5, 0x52,
20607 +0x14, 0x60, 0x55, 0x14, 0x60, 0x2f, 0x24, 0x02, 0x60, 0x03, 0x02, 0x18, 0x27, 0xe5, 0x34, 0xf4,
20608 +0x60, 0x23, 0xe5, 0x34, 0xd3, 0x94, 0x02, 0x40, 0x16, 0x90, 0x12, 0x04, 0xe0, 0x44, 0x02, 0xf0,
20609 +0x90, 0x01, 0x0d, 0xe0, 0x20, 0xe3, 0x03, 0x02, 0x18, 0x27, 0x7f, 0x50, 0x12, 0x16, 0x51, 0x75,
20610 +0x52, 0x02, 0x75, 0x55, 0x03, 0xe5, 0x34, 0xf4, 0x60, 0x0a, 0xe5, 0x54, 0x70, 0x69, 0x90, 0x01,
20611 +0x0d, 0xe5, 0x33, 0xf0, 0x90, 0x12, 0x04, 0xe0, 0x54, 0xfb, 0xf0, 0x7f, 0x20, 0x12, 0x16, 0x51,
20612 +0x75, 0x52, 0x01, 0x75, 0x55, 0x03, 0x80, 0x4f, 0xe5, 0x54, 0x70, 0x4b, 0x90, 0x04, 0x01, 0xe0,
20613 +0x44, 0x0e, 0xf0, 0x20, 0x19, 0x04, 0xe0, 0x54, 0xef, 0xf0, 0x90, 0x13, 0x28, 0xe0, 0x44, 0x0f,
20614 +0xf0, 0xa3, 0xe0, 0x44, 0x0f, 0xf0, 0xa3, 0xe0, 0x44, 0x05, 0xf0, 0x90, 0x12, 0x04, 0x74, 0x03,
20615 +0xf0, 0x20, 0x19, 0x07, 0x90, 0x02, 0x08, 0xe0, 0x44, 0x05, 0xf0, 0x90, 0x10, 0x04, 0xe0, 0x44,
20616 +0x0c, 0xf0, 0xe4, 0xf5, 0x52, 0xf5, 0x55, 0x30, 0x02, 0x0b, 0xc2, 0x02, 0x7d, 0x01, 0xaf, 0x41,
20617 +0x12, 0x18, 0x2a, 0x80, 0x02, 0xc2, 0x03, 0xd2, 0xaf, 0x22, 0xef, 0xf4, 0x60, 0x2d, 0xe4, 0xfe,
20618 +0x74, 0x14, 0x2e, 0xf5, 0x82, 0xe4, 0x34, 0x70, 0xf5, 0x83, 0xe0, 0xb4, 0xff, 0x19, 0x74, 0x14,
20619 +0x2e, 0xf5, 0x82, 0xe4, 0x34, 0x70, 0xf5, 0x83, 0xef, 0xf0, 0x74, 0x1c, 0x2e, 0xf5, 0x82, 0xe4,
20620 +0x34, 0x70, 0xf5, 0x83, 0xed, 0xf0, 0x22, 0x0e, 0xbe, 0x04, 0xd5, 0x22, 0x22, 0x22, 0x20, 0x19,
20621 +0x03, 0x02, 0x19, 0x0f, 0x90, 0x70, 0x80, 0xe0, 0x04, 0xf0, 0x90, 0x04, 0x37, 0xe0, 0x30, 0xe5,
20622 +0x03, 0x02, 0x19, 0x0b, 0x90, 0x04, 0x28, 0xe0, 0xf5, 0x31, 0xa3, 0xe0, 0xf5, 0x30, 0xf5, 0x32,
20623 +0xe4, 0xf5, 0x37, 0x90, 0x70, 0x81, 0xe0, 0x04, 0xf0, 0x90, 0x70, 0x82, 0xe0, 0x04, 0xf0, 0xe5,
20624 +0x32, 0x75, 0xf0, 0x80, 0xa4, 0x24, 0x00, 0xff, 0xe5, 0xf0, 0x34, 0x80, 0xfe, 0xe5, 0x30, 0x65,
20625 +0x32, 0x70, 0x05, 0xfc, 0x7d, 0x18, 0x80, 0x04, 0x7c, 0x00, 0x7d, 0x00, 0xef, 0x2d, 0xff, 0xee,
20626 +0x3c, 0xfe, 0x12, 0x19, 0x10, 0x50, 0x25, 0x90, 0x70, 0x83, 0xe0, 0x04, 0xf0, 0x90, 0x01, 0x14,
20627 +0xe0, 0x44, 0x02, 0xf0, 0xe0, 0x30, 0xe1, 0x06, 0x90, 0x70, 0x92, 0x74, 0x45, 0xf0, 0x90, 0x70,
20628 +0x93, 0xe0, 0x04, 0xf0, 0x90, 0x04, 0x01, 0xe0, 0x90, 0x70, 0x94, 0xf0, 0xe5, 0x32, 0x65, 0x31,
20629 +0x60, 0x10, 0xe4, 0x25, 0x32, 0xff, 0xe4, 0x34, 0x80, 0x8f, 0x82, 0xf5, 0x83, 0xe0, 0xf5, 0x32,
20630 +0x80, 0x97, 0x90, 0x04, 0x10, 0x74, 0x01, 0xf0, 0x90, 0x04, 0x28, 0xe5, 0x31, 0xf0, 0xa3, 0xe5,
20631 +0x30, 0xf0, 0x90, 0x04, 0x11, 0x74, 0x01, 0xf0, 0x02, 0x18, 0x6a, 0xc2, 0x06, 0xd2, 0x1a, 0x22,
20632 +0x90, 0x70, 0x84, 0xe5, 0x37, 0xf0, 0xc3, 0x94, 0x06, 0x50, 0x19, 0x8f, 0x82, 0x8e, 0x83, 0xe0,
20633 +0xb4, 0xff, 0x07, 0x05, 0x37, 0xe4, 0xf5, 0x36, 0x80, 0x59, 0xe4, 0xf5, 0x37, 0x8f, 0x82, 0x8e,
20634 +0x83, 0xf0, 0x80, 0x4f, 0xe5, 0x36, 0x75, 0xf0, 0x06, 0x84, 0x74, 0x08, 0x25, 0xf0, 0xf5, 0x82,
20635 +0xe4, 0x34, 0x10, 0xf5, 0x83, 0xe0, 0xfd, 0x8f, 0x82, 0x8e, 0x83, 0xe0, 0xfc, 0x6d, 0x70, 0x30,
20636 +0x90, 0x70, 0x88, 0xe0, 0x04, 0xf0, 0xa3, 0xe0, 0xfd, 0xd3, 0x95, 0x37, 0x40, 0x02, 0x80, 0x02,
20637 +0xad, 0x37, 0x90, 0x70, 0x89, 0xed, 0xf0, 0x05, 0x37, 0x05, 0x36, 0xe5, 0x36, 0x75, 0xf0, 0x06,
20638 +0x84, 0x74, 0x8a, 0x25, 0xf0, 0xf5, 0x82, 0xe4, 0x34, 0x70, 0xf5, 0x83, 0xec, 0xf0, 0x80, 0x03,
20639 +0xe4, 0xf5, 0x37, 0x0f, 0xbf, 0x00, 0x01, 0x0e, 0xef, 0x54, 0x7f, 0x60, 0x0a, 0xe5, 0x37, 0xc3,
20640 +0x94, 0x4e, 0x50, 0x03, 0x02, 0x19, 0x10, 0xe5, 0x37, 0xb4, 0x4e, 0x03, 0xd3, 0x80, 0x01, 0xc3,
20641 +0x22, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20642 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20643 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20644 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20645 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20646 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20647 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20648 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20649 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20650 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20651 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20652 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20653 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20654 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20655 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20656 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20657 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20658 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20659 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20660 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20661 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20662 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20663 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20664 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20665 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20666 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20667 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20668 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20669 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20670 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20671 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20672 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20673 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20674 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20675 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20676 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20677 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20678 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20679 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20680 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20681 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20682 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20683 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20684 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20685 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20686 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20687 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20688 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20689 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20690 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20691 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20692 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20693 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20694 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20695 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20696 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20697 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20698 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20699 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20700 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20701 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20702 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20703 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20704 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20705 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20706 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20707 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20708 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20709 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20710 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20711 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20712 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20713 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20714 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20715 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20716 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20717 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20718 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20719 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20720 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20721 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20722 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20723 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20724 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20725 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20726 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20727 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20728 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20729 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20730 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20731 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20732 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20733 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20734 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20735 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20736 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20737 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20738 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20739 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20740 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20741 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
20742 +0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0b, 0x94, 0xeb, } ;
20743 --- /dev/null
20744 +++ b/drivers/staging/rt2860/common/md5.c
20745 @@ -0,0 +1,1427 @@
20746 +/*
20747 + *************************************************************************
20748 + * Ralink Tech Inc.
20749 + * 5F., No.36, Taiyuan St., Jhubei City,
20750 + * Hsinchu County 302,
20751 + * Taiwan, R.O.C.
20752 + *
20753 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
20754 + *
20755 + * This program is free software; you can redistribute it and/or modify *
20756 + * it under the terms of the GNU General Public License as published by *
20757 + * the Free Software Foundation; either version 2 of the License, or *
20758 + * (at your option) any later version. *
20759 + * *
20760 + * This program is distributed in the hope that it will be useful, *
20761 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
20762 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
20763 + * GNU General Public License for more details. *
20764 + * *
20765 + * You should have received a copy of the GNU General Public License *
20766 + * along with this program; if not, write to the *
20767 + * Free Software Foundation, Inc., *
20768 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
20769 + * *
20770 + *************************************************************************
20771 +
20772 + Module Name:
20773 + md5.c
20774 +
20775 + Abstract:
20776 +
20777 + Revision History:
20778 + Who When What
20779 + -------- ---------- ----------------------------------------------
20780 + Name Date Modification logs
20781 + jan 10-28-03 Initial
20782 + Rita 11-23-04 Modify MD5 and SHA-1
20783 + Rita 10-14-05 Modify SHA-1 in big-endian platform
20784 + */
20785 +#include "../rt_config.h"
20786 +
20787 +/**
20788 + * md5_mac:
20789 + * @key: pointer to the key used for MAC generation
20790 + * @key_len: length of the key in bytes
20791 + * @data: pointer to the data area for which the MAC is generated
20792 + * @data_len: length of the data in bytes
20793 + * @mac: pointer to the buffer holding space for the MAC; the buffer should
20794 + * have space for 128-bit (16 bytes) MD5 hash value
20795 + *
20796 + * md5_mac() determines the message authentication code by using secure hash
20797 + * MD5(key | data | key).
20798 + */
20799 +void md5_mac(u8 *key, size_t key_len, u8 *data, size_t data_len, u8 *mac)
20800 +{
20801 + MD5_CTX context;
20802 +
20803 + MD5Init(&context);
20804 + MD5Update(&context, key, key_len);
20805 + MD5Update(&context, data, data_len);
20806 + MD5Update(&context, key, key_len);
20807 + MD5Final(mac, &context);
20808 +}
20809 +
20810 +/**
20811 + * hmac_md5:
20812 + * @key: pointer to the key used for MAC generation
20813 + * @key_len: length of the key in bytes
20814 + * @data: pointer to the data area for which the MAC is generated
20815 + * @data_len: length of the data in bytes
20816 + * @mac: pointer to the buffer holding space for the MAC; the buffer should
20817 + * have space for 128-bit (16 bytes) MD5 hash value
20818 + *
20819 + * hmac_md5() determines the message authentication code using HMAC-MD5.
20820 + * This implementation is based on the sample code presented in RFC 2104.
20821 + */
20822 +void hmac_md5(u8 *key, size_t key_len, u8 *data, size_t data_len, u8 *mac)
20823 +{
20824 + MD5_CTX context;
20825 + u8 k_ipad[65]; /* inner padding - key XORd with ipad */
20826 + u8 k_opad[65]; /* outer padding - key XORd with opad */
20827 + u8 tk[16];
20828 + int i;
20829 +
20830 + //assert(key != NULL && data != NULL && mac != NULL);
20831 +
20832 + /* if key is longer than 64 bytes reset it to key = MD5(key) */
20833 + if (key_len > 64) {
20834 + MD5_CTX ttcontext;
20835 +
20836 + MD5Init(&ttcontext);
20837 + MD5Update(&ttcontext, key, key_len);
20838 + MD5Final(tk, &ttcontext);
20839 + //key=(PUCHAR)ttcontext.buf;
20840 + key = tk;
20841 + key_len = 16;
20842 + }
20843 +
20844 + /* the HMAC_MD5 transform looks like:
20845 + *
20846 + * MD5(K XOR opad, MD5(K XOR ipad, text))
20847 + *
20848 + * where K is an n byte key
20849 + * ipad is the byte 0x36 repeated 64 times
20850 + * opad is the byte 0x5c repeated 64 times
20851 + * and text is the data being protected */
20852 +
20853 + /* start out by storing key in pads */
20854 + NdisZeroMemory(k_ipad, sizeof(k_ipad));
20855 + NdisZeroMemory(k_opad, sizeof(k_opad));
20856 + //assert(key_len < sizeof(k_ipad));
20857 + NdisMoveMemory(k_ipad, key, key_len);
20858 + NdisMoveMemory(k_opad, key, key_len);
20859 +
20860 + /* XOR key with ipad and opad values */
20861 + for (i = 0; i < 64; i++) {
20862 + k_ipad[i] ^= 0x36;
20863 + k_opad[i] ^= 0x5c;
20864 + }
20865 +
20866 + /* perform inner MD5 */
20867 + MD5Init(&context); /* init context for 1st pass */
20868 + MD5Update(&context, k_ipad, 64); /* start with inner pad */
20869 + MD5Update(&context, data, data_len); /* then text of datagram */
20870 + MD5Final(mac, &context); /* finish up 1st pass */
20871 +
20872 + /* perform outer MD5 */
20873 + MD5Init(&context); /* init context for 2nd pass */
20874 + MD5Update(&context, k_opad, 64); /* start with outer pad */
20875 + MD5Update(&context, mac, 16); /* then results of 1st hash */
20876 + MD5Final(mac, &context); /* finish up 2nd pass */
20877 +}
20878 +
20879 +#ifndef RT_BIG_ENDIAN
20880 +#define byteReverse(buf, len) /* Nothing */
20881 +#else
20882 +void byteReverse(unsigned char *buf, unsigned longs);
20883 +void byteReverse(unsigned char *buf, unsigned longs)
20884 +{
20885 + do {
20886 + *(UINT32 *)buf = SWAP32(*(UINT32 *)buf);
20887 + buf += 4;
20888 + } while (--longs);
20889 +}
20890 +#endif
20891 +
20892 +
20893 +/* ========================== MD5 implementation =========================== */
20894 +// four base functions for MD5
20895 +#define MD5_F1(x, y, z) (((x) & (y)) | ((~x) & (z)))
20896 +#define MD5_F2(x, y, z) (((x) & (z)) | ((y) & (~z)))
20897 +#define MD5_F3(x, y, z) ((x) ^ (y) ^ (z))
20898 +#define MD5_F4(x, y, z) ((y) ^ ((x) | (~z)))
20899 +#define CYCLIC_LEFT_SHIFT(w, s) (((w) << (s)) | ((w) >> (32-(s))))
20900 +
20901 +#define MD5Step(f, w, x, y, z, data, t, s) \
20902 + ( w += f(x, y, z) + data + t, w = (CYCLIC_LEFT_SHIFT(w, s)) & 0xffffffff, w += x )
20903 +
20904 +
20905 +/*
20906 + * Function Description:
20907 + * Initiate MD5 Context satisfied in RFC 1321
20908 + *
20909 + * Arguments:
20910 + * pCtx Pointer to MD5 context
20911 + *
20912 + * Return Value:
20913 + * None
20914 + */
20915 +VOID MD5Init(MD5_CTX *pCtx)
20916 +{
20917 + pCtx->Buf[0]=0x67452301;
20918 + pCtx->Buf[1]=0xefcdab89;
20919 + pCtx->Buf[2]=0x98badcfe;
20920 + pCtx->Buf[3]=0x10325476;
20921 +
20922 + pCtx->LenInBitCount[0]=0;
20923 + pCtx->LenInBitCount[1]=0;
20924 +}
20925 +
20926 +
20927 +/*
20928 + * Function Description:
20929 + * Update MD5 Context, allow of an arrary of octets as the next portion
20930 + * of the message
20931 + *
20932 + * Arguments:
20933 + * pCtx Pointer to MD5 context
20934 + * pData Pointer to input data
20935 + * LenInBytes The length of input data (unit: byte)
20936 + *
20937 + * Return Value:
20938 + * None
20939 + *
20940 + * Note:
20941 + * Called after MD5Init or MD5Update(itself)
20942 + */
20943 +VOID MD5Update(MD5_CTX *pCtx, UCHAR *pData, UINT32 LenInBytes)
20944 +{
20945 +
20946 + UINT32 TfTimes;
20947 + UINT32 temp;
20948 + unsigned int i;
20949 +
20950 + temp = pCtx->LenInBitCount[0];
20951 +
20952 + pCtx->LenInBitCount[0] = (UINT32) (pCtx->LenInBitCount[0] + (LenInBytes << 3));
20953 +
20954 + if (pCtx->LenInBitCount[0] < temp)
20955 + pCtx->LenInBitCount[1]++; //carry in
20956 +
20957 + pCtx->LenInBitCount[1] += LenInBytes >> 29;
20958 +
20959 + // mod 64 bytes
20960 + temp = (temp >> 3) & 0x3f;
20961 +
20962 + // process lacks of 64-byte data
20963 + if (temp)
20964 + {
20965 + UCHAR *pAds = (UCHAR *) pCtx->Input + temp;
20966 +
20967 + if ((temp+LenInBytes) < 64)
20968 + {
20969 + NdisMoveMemory(pAds, (UCHAR *)pData, LenInBytes);
20970 + return;
20971 + }
20972 +
20973 + NdisMoveMemory(pAds, (UCHAR *)pData, 64-temp);
20974 + byteReverse(pCtx->Input, 16);
20975 + MD5Transform(pCtx->Buf, (UINT32 *)pCtx->Input);
20976 +
20977 + pData += 64-temp;
20978 + LenInBytes -= 64-temp;
20979 + } // end of if (temp)
20980 +
20981 +
20982 + TfTimes = (LenInBytes >> 6);
20983 +
20984 + for (i=TfTimes; i>0; i--)
20985 + {
20986 + NdisMoveMemory(pCtx->Input, (UCHAR *)pData, 64);
20987 + byteReverse(pCtx->Input, 16);
20988 + MD5Transform(pCtx->Buf, (UINT32 *)pCtx->Input);
20989 + pData += 64;
20990 + LenInBytes -= 64;
20991 + } // end of for
20992 +
20993 + // buffering lacks of 64-byte data
20994 + if(LenInBytes)
20995 + NdisMoveMemory(pCtx->Input, (UCHAR *)pData, LenInBytes);
20996 +
20997 +}
20998 +
20999 +
21000 +/*
21001 + * Function Description:
21002 + * Append padding bits and length of original message in the tail
21003 + * The message digest has to be completed in the end
21004 + *
21005 + * Arguments:
21006 + * Digest Output of Digest-Message for MD5
21007 + * pCtx Pointer to MD5 context
21008 + *
21009 + * Return Value:
21010 + * None
21011 + *
21012 + * Note:
21013 + * Called after MD5Update
21014 + */
21015 +VOID MD5Final(UCHAR Digest[16], MD5_CTX *pCtx)
21016 +{
21017 + UCHAR Remainder;
21018 + UCHAR PadLenInBytes;
21019 + UCHAR *pAppend=0;
21020 + unsigned int i;
21021 +
21022 + Remainder = (UCHAR)((pCtx->LenInBitCount[0] >> 3) & 0x3f);
21023 +
21024 + PadLenInBytes = (Remainder < 56) ? (56-Remainder) : (120-Remainder);
21025 +
21026 + pAppend = (UCHAR *)pCtx->Input + Remainder;
21027 +
21028 + // padding bits without crossing block(64-byte based) boundary
21029 + if (Remainder < 56)
21030 + {
21031 + *pAppend = 0x80;
21032 + PadLenInBytes --;
21033 +
21034 + NdisZeroMemory((UCHAR *)pCtx->Input + Remainder+1, PadLenInBytes);
21035 +
21036 + // add data-length field, from low to high
21037 + for (i=0; i<4; i++)
21038 + {
21039 + pCtx->Input[56+i] = (UCHAR)((pCtx->LenInBitCount[0] >> (i << 3)) & 0xff);
21040 + pCtx->Input[60+i] = (UCHAR)((pCtx->LenInBitCount[1] >> (i << 3)) & 0xff);
21041 + }
21042 +
21043 + byteReverse(pCtx->Input, 16);
21044 + MD5Transform(pCtx->Buf, (UINT32 *)pCtx->Input);
21045 + } // end of if
21046 +
21047 + // padding bits with crossing block(64-byte based) boundary
21048 + else
21049 + {
21050 + // the first block ===
21051 + *pAppend = 0x80;
21052 + PadLenInBytes --;
21053 +
21054 + NdisZeroMemory((UCHAR *)pCtx->Input + Remainder+1, (64-Remainder-1));
21055 + PadLenInBytes -= (64 - Remainder - 1);
21056 +
21057 + byteReverse(pCtx->Input, 16);
21058 + MD5Transform(pCtx->Buf, (UINT32 *)pCtx->Input);
21059 +
21060 +
21061 + // the second block ===
21062 + NdisZeroMemory((UCHAR *)pCtx->Input, PadLenInBytes);
21063 +
21064 + // add data-length field
21065 + for (i=0; i<4; i++)
21066 + {
21067 + pCtx->Input[56+i] = (UCHAR)((pCtx->LenInBitCount[0] >> (i << 3)) & 0xff);
21068 + pCtx->Input[60+i] = (UCHAR)((pCtx->LenInBitCount[1] >> (i << 3)) & 0xff);
21069 + }
21070 +
21071 + byteReverse(pCtx->Input, 16);
21072 + MD5Transform(pCtx->Buf, (UINT32 *)pCtx->Input);
21073 + } // end of else
21074 +
21075 +
21076 + NdisMoveMemory((UCHAR *)Digest, (UINT32 *)pCtx->Buf, 16); // output
21077 + byteReverse((UCHAR *)Digest, 4);
21078 + NdisZeroMemory(pCtx, sizeof(pCtx)); // memory free
21079 +}
21080 +
21081 +
21082 +/*
21083 + * Function Description:
21084 + * The central algorithm of MD5, consists of four rounds and sixteen
21085 + * steps per round
21086 + *
21087 + * Arguments:
21088 + * Buf Buffers of four states (output: 16 bytes)
21089 + * Mes Input data (input: 64 bytes)
21090 + *
21091 + * Return Value:
21092 + * None
21093 + *
21094 + * Note:
21095 + * Called by MD5Update or MD5Final
21096 + */
21097 +VOID MD5Transform(UINT32 Buf[4], UINT32 Mes[16])
21098 +{
21099 + UINT32 Reg[4], Temp;
21100 + unsigned int i;
21101 +
21102 + static UCHAR LShiftVal[16] =
21103 + {
21104 + 7, 12, 17, 22,
21105 + 5, 9 , 14, 20,
21106 + 4, 11, 16, 23,
21107 + 6, 10, 15, 21,
21108 + };
21109 +
21110 +
21111 + // [equal to 4294967296*abs(sin(index))]
21112 + static UINT32 MD5Table[64] =
21113 + {
21114 + 0xd76aa478, 0xe8c7b756, 0x242070db, 0xc1bdceee,
21115 + 0xf57c0faf, 0x4787c62a, 0xa8304613, 0xfd469501,
21116 + 0x698098d8, 0x8b44f7af, 0xffff5bb1, 0x895cd7be,
21117 + 0x6b901122, 0xfd987193, 0xa679438e, 0x49b40821,
21118 +
21119 + 0xf61e2562, 0xc040b340, 0x265e5a51, 0xe9b6c7aa,
21120 + 0xd62f105d, 0x02441453, 0xd8a1e681, 0xe7d3fbc8,
21121 + 0x21e1cde6, 0xc33707d6, 0xf4d50d87, 0x455a14ed,
21122 + 0xa9e3e905, 0xfcefa3f8, 0x676f02d9, 0x8d2a4c8a,
21123 +
21124 + 0xfffa3942, 0x8771f681, 0x6d9d6122, 0xfde5380c,
21125 + 0xa4beea44, 0x4bdecfa9, 0xf6bb4b60, 0xbebfbc70,
21126 + 0x289b7ec6, 0xeaa127fa, 0xd4ef3085, 0x04881d05,
21127 + 0xd9d4d039, 0xe6db99e5, 0x1fa27cf8, 0xc4ac5665,
21128 +
21129 + 0xf4292244, 0x432aff97, 0xab9423a7, 0xfc93a039,
21130 + 0x655b59c3, 0x8f0ccc92, 0xffeff47d, 0x85845dd1,
21131 + 0x6fa87e4f, 0xfe2ce6e0, 0xa3014314, 0x4e0811a1,
21132 + 0xf7537e82, 0xbd3af235, 0x2ad7d2bb, 0xeb86d391
21133 + };
21134 +
21135 +
21136 + for (i=0; i<4; i++)
21137 + Reg[i]=Buf[i];
21138 +
21139 +
21140 + // 64 steps in MD5 algorithm
21141 + for (i=0; i<16; i++)
21142 + {
21143 + MD5Step(MD5_F1, Reg[0], Reg[1], Reg[2], Reg[3], Mes[i],
21144 + MD5Table[i], LShiftVal[i & 0x3]);
21145 +
21146 + // one-word right shift
21147 + Temp = Reg[3];
21148 + Reg[3] = Reg[2];
21149 + Reg[2] = Reg[1];
21150 + Reg[1] = Reg[0];
21151 + Reg[0] = Temp;
21152 + }
21153 + for (i=16; i<32; i++)
21154 + {
21155 + MD5Step(MD5_F2, Reg[0], Reg[1], Reg[2], Reg[3], Mes[(5*(i & 0xf)+1) & 0xf],
21156 + MD5Table[i], LShiftVal[(0x1 << 2)+(i & 0x3)]);
21157 +
21158 + // one-word right shift
21159 + Temp = Reg[3];
21160 + Reg[3] = Reg[2];
21161 + Reg[2] = Reg[1];
21162 + Reg[1] = Reg[0];
21163 + Reg[0] = Temp;
21164 + }
21165 + for (i=32; i<48; i++)
21166 + {
21167 + MD5Step(MD5_F3, Reg[0], Reg[1], Reg[2], Reg[3], Mes[(3*(i & 0xf)+5) & 0xf],
21168 + MD5Table[i], LShiftVal[(0x1 << 3)+(i & 0x3)]);
21169 +
21170 + // one-word right shift
21171 + Temp = Reg[3];
21172 + Reg[3] = Reg[2];
21173 + Reg[2] = Reg[1];
21174 + Reg[1] = Reg[0];
21175 + Reg[0] = Temp;
21176 + }
21177 + for (i=48; i<64; i++)
21178 + {
21179 + MD5Step(MD5_F4, Reg[0], Reg[1], Reg[2], Reg[3], Mes[(7*(i & 0xf)) & 0xf],
21180 + MD5Table[i], LShiftVal[(0x3 << 2)+(i & 0x3)]);
21181 +
21182 + // one-word right shift
21183 + Temp = Reg[3];
21184 + Reg[3] = Reg[2];
21185 + Reg[2] = Reg[1];
21186 + Reg[1] = Reg[0];
21187 + Reg[0] = Temp;
21188 + }
21189 +
21190 +
21191 + // (temporary)output
21192 + for (i=0; i<4; i++)
21193 + Buf[i] += Reg[i];
21194 +
21195 +}
21196 +
21197 +
21198 +
21199 +/* ========================= SHA-1 implementation ========================== */
21200 +// four base functions for SHA-1
21201 +#define SHA1_F1(b, c, d) (((b) & (c)) | ((~b) & (d)))
21202 +#define SHA1_F2(b, c, d) ((b) ^ (c) ^ (d))
21203 +#define SHA1_F3(b, c, d) (((b) & (c)) | ((b) & (d)) | ((c) & (d)))
21204 +
21205 +
21206 +#define SHA1Step(f, a, b, c, d, e, w, k) \
21207 + ( e += ( f(b, c, d) + w + k + CYCLIC_LEFT_SHIFT(a, 5)) & 0xffffffff, \
21208 + b = CYCLIC_LEFT_SHIFT(b, 30) )
21209 +
21210 +//Initiate SHA-1 Context satisfied in RFC 3174
21211 +VOID SHAInit(SHA_CTX *pCtx)
21212 +{
21213 + pCtx->Buf[0]=0x67452301;
21214 + pCtx->Buf[1]=0xefcdab89;
21215 + pCtx->Buf[2]=0x98badcfe;
21216 + pCtx->Buf[3]=0x10325476;
21217 + pCtx->Buf[4]=0xc3d2e1f0;
21218 +
21219 + pCtx->LenInBitCount[0]=0;
21220 + pCtx->LenInBitCount[1]=0;
21221 +}
21222 +
21223 +/*
21224 + * Function Description:
21225 + * Update SHA-1 Context, allow of an arrary of octets as the next
21226 + * portion of the message
21227 + *
21228 + * Arguments:
21229 + * pCtx Pointer to SHA-1 context
21230 + * pData Pointer to input data
21231 + * LenInBytes The length of input data (unit: byte)
21232 + *
21233 + * Return Value:
21234 + * error indicate more than pow(2,64) bits of data
21235 + *
21236 + * Note:
21237 + * Called after SHAInit or SHAUpdate(itself)
21238 + */
21239 +UCHAR SHAUpdate(SHA_CTX *pCtx, UCHAR *pData, UINT32 LenInBytes)
21240 +{
21241 + UINT32 TfTimes;
21242 + UINT32 temp1,temp2;
21243 + unsigned int i;
21244 + UCHAR err=1;
21245 +
21246 + temp1 = pCtx->LenInBitCount[0];
21247 + temp2 = pCtx->LenInBitCount[1];
21248 +
21249 + pCtx->LenInBitCount[0] = (UINT32) (pCtx->LenInBitCount[0] + (LenInBytes << 3));
21250 + if (pCtx->LenInBitCount[0] < temp1)
21251 + pCtx->LenInBitCount[1]++; //carry in
21252 +
21253 +
21254 + pCtx->LenInBitCount[1] = (UINT32) (pCtx->LenInBitCount[1] +(LenInBytes >> 29));
21255 + if (pCtx->LenInBitCount[1] < temp2)
21256 + return (err); //check total length of original data
21257 +
21258 +
21259 + // mod 64 bytes
21260 + temp1 = (temp1 >> 3) & 0x3f;
21261 +
21262 + // process lacks of 64-byte data
21263 + if (temp1)
21264 + {
21265 + UCHAR *pAds = (UCHAR *) pCtx->Input + temp1;
21266 +
21267 + if ((temp1+LenInBytes) < 64)
21268 + {
21269 + NdisMoveMemory(pAds, (UCHAR *)pData, LenInBytes);
21270 + return (0);
21271 + }
21272 +
21273 + NdisMoveMemory(pAds, (UCHAR *)pData, 64-temp1);
21274 + byteReverse((UCHAR *)pCtx->Input, 16);
21275 +
21276 + NdisZeroMemory((UCHAR *)pCtx->Input + 64, 16);
21277 + SHATransform(pCtx->Buf, (UINT32 *)pCtx->Input);
21278 +
21279 + pData += 64-temp1;
21280 + LenInBytes -= 64-temp1;
21281 + } // end of if (temp1)
21282 +
21283 +
21284 + TfTimes = (LenInBytes >> 6);
21285 +
21286 + for (i=TfTimes; i>0; i--)
21287 + {
21288 + NdisMoveMemory(pCtx->Input, (UCHAR *)pData, 64);
21289 + byteReverse((UCHAR *)pCtx->Input, 16);
21290 +
21291 + NdisZeroMemory((UCHAR *)pCtx->Input + 64, 16);
21292 + SHATransform(pCtx->Buf, (UINT32 *)pCtx->Input);
21293 + pData += 64;
21294 + LenInBytes -= 64;
21295 + } // end of for
21296 +
21297 + // buffering lacks of 64-byte data
21298 + if(LenInBytes)
21299 + NdisMoveMemory(pCtx->Input, (UCHAR *)pData, LenInBytes);
21300 +
21301 + return (0);
21302 +
21303 +}
21304 +
21305 +// Append padding bits and length of original message in the tail
21306 +// The message digest has to be completed in the end
21307 +VOID SHAFinal(SHA_CTX *pCtx, UCHAR Digest[20])
21308 +{
21309 + UCHAR Remainder;
21310 + UCHAR PadLenInBytes;
21311 + UCHAR *pAppend=0;
21312 + unsigned int i;
21313 +
21314 + Remainder = (UCHAR)((pCtx->LenInBitCount[0] >> 3) & 0x3f);
21315 +
21316 + pAppend = (UCHAR *)pCtx->Input + Remainder;
21317 +
21318 + PadLenInBytes = (Remainder < 56) ? (56-Remainder) : (120-Remainder);
21319 +
21320 + // padding bits without crossing block(64-byte based) boundary
21321 + if (Remainder < 56)
21322 + {
21323 + *pAppend = 0x80;
21324 + PadLenInBytes --;
21325 +
21326 + NdisZeroMemory((UCHAR *)pCtx->Input + Remainder+1, PadLenInBytes);
21327 +
21328 + // add data-length field, from high to low
21329 + for (i=0; i<4; i++)
21330 + {
21331 + pCtx->Input[56+i] = (UCHAR)((pCtx->LenInBitCount[1] >> ((3-i) << 3)) & 0xff);
21332 + pCtx->Input[60+i] = (UCHAR)((pCtx->LenInBitCount[0] >> ((3-i) << 3)) & 0xff);
21333 + }
21334 +
21335 + byteReverse((UCHAR *)pCtx->Input, 16);
21336 + NdisZeroMemory((UCHAR *)pCtx->Input + 64, 14);
21337 + SHATransform(pCtx->Buf, (UINT32 *)pCtx->Input);
21338 + } // end of if
21339 +
21340 + // padding bits with crossing block(64-byte based) boundary
21341 + else
21342 + {
21343 + // the first block ===
21344 + *pAppend = 0x80;
21345 + PadLenInBytes --;
21346 +
21347 + NdisZeroMemory((UCHAR *)pCtx->Input + Remainder+1, (64-Remainder-1));
21348 + PadLenInBytes -= (64 - Remainder - 1);
21349 +
21350 + byteReverse((UCHAR *)pCtx->Input, 16);
21351 + NdisZeroMemory((UCHAR *)pCtx->Input + 64, 16);
21352 + SHATransform(pCtx->Buf, (UINT32 *)pCtx->Input);
21353 +
21354 +
21355 + // the second block ===
21356 + NdisZeroMemory((UCHAR *)pCtx->Input, PadLenInBytes);
21357 +
21358 + // add data-length field
21359 + for (i=0; i<4; i++)
21360 + {
21361 + pCtx->Input[56+i] = (UCHAR)((pCtx->LenInBitCount[1] >> ((3-i) << 3)) & 0xff);
21362 + pCtx->Input[60+i] = (UCHAR)((pCtx->LenInBitCount[0] >> ((3-i) << 3)) & 0xff);
21363 + }
21364 +
21365 + byteReverse((UCHAR *)pCtx->Input, 16);
21366 + NdisZeroMemory((UCHAR *)pCtx->Input + 64, 16);
21367 + SHATransform(pCtx->Buf, (UINT32 *)pCtx->Input);
21368 + } // end of else
21369 +
21370 +
21371 + //Output, bytereverse
21372 + for (i=0; i<20; i++)
21373 + {
21374 + Digest [i] = (UCHAR)(pCtx->Buf[i>>2] >> 8*(3-(i & 0x3)));
21375 + }
21376 +
21377 + NdisZeroMemory(pCtx, sizeof(pCtx)); // memory free
21378 +}
21379 +
21380 +
21381 +// The central algorithm of SHA-1, consists of four rounds and
21382 +// twenty steps per round
21383 +VOID SHATransform(UINT32 Buf[5], UINT32 Mes[20])
21384 +{
21385 + UINT32 Reg[5],Temp;
21386 + unsigned int i;
21387 + UINT32 W[80];
21388 +
21389 + static UINT32 SHA1Table[4] = { 0x5a827999, 0x6ed9eba1,
21390 + 0x8f1bbcdc, 0xca62c1d6 };
21391 +
21392 + Reg[0]=Buf[0];
21393 + Reg[1]=Buf[1];
21394 + Reg[2]=Buf[2];
21395 + Reg[3]=Buf[3];
21396 + Reg[4]=Buf[4];
21397 +
21398 + //the first octet of a word is stored in the 0th element, bytereverse
21399 + for(i = 0; i < 16; i++)
21400 + {
21401 + W[i] = (Mes[i] >> 24) & 0xff;
21402 + W[i] |= (Mes[i] >> 8 ) & 0xff00;
21403 + W[i] |= (Mes[i] << 8 ) & 0xff0000;
21404 + W[i] |= (Mes[i] << 24) & 0xff000000;
21405 + }
21406 +
21407 +
21408 + for (i = 0; i < 64; i++)
21409 + W[16+i] = CYCLIC_LEFT_SHIFT(W[i] ^ W[2+i] ^ W[8+i] ^ W[13+i], 1);
21410 +
21411 +
21412 + // 80 steps in SHA-1 algorithm
21413 + for (i=0; i<80; i++)
21414 + {
21415 + if (i<20)
21416 + SHA1Step(SHA1_F1, Reg[0], Reg[1], Reg[2], Reg[3], Reg[4],
21417 + W[i], SHA1Table[0]);
21418 +
21419 + else if (i>=20 && i<40)
21420 + SHA1Step(SHA1_F2, Reg[0], Reg[1], Reg[2], Reg[3], Reg[4],
21421 + W[i], SHA1Table[1]);
21422 +
21423 + else if (i>=40 && i<60)
21424 + SHA1Step(SHA1_F3, Reg[0], Reg[1], Reg[2], Reg[3], Reg[4],
21425 + W[i], SHA1Table[2]);
21426 +
21427 + else
21428 + SHA1Step(SHA1_F2, Reg[0], Reg[1], Reg[2], Reg[3], Reg[4],
21429 + W[i], SHA1Table[3]);
21430 +
21431 +
21432 + // one-word right shift
21433 + Temp = Reg[4];
21434 + Reg[4] = Reg[3];
21435 + Reg[3] = Reg[2];
21436 + Reg[2] = Reg[1];
21437 + Reg[1] = Reg[0];
21438 + Reg[0] = Temp;
21439 +
21440 + } // end of for-loop
21441 +
21442 +
21443 + // (temporary)output
21444 + for (i=0; i<5; i++)
21445 + Buf[i] += Reg[i];
21446 +
21447 +}
21448 +
21449 +
21450 +/* ========================= AES En/Decryption ========================== */
21451 +
21452 +/* forward S-box */
21453 +static uint32 FSb[256] =
21454 +{
21455 + 0x63, 0x7C, 0x77, 0x7B, 0xF2, 0x6B, 0x6F, 0xC5,
21456 + 0x30, 0x01, 0x67, 0x2B, 0xFE, 0xD7, 0xAB, 0x76,
21457 + 0xCA, 0x82, 0xC9, 0x7D, 0xFA, 0x59, 0x47, 0xF0,
21458 + 0xAD, 0xD4, 0xA2, 0xAF, 0x9C, 0xA4, 0x72, 0xC0,
21459 + 0xB7, 0xFD, 0x93, 0x26, 0x36, 0x3F, 0xF7, 0xCC,
21460 + 0x34, 0xA5, 0xE5, 0xF1, 0x71, 0xD8, 0x31, 0x15,
21461 + 0x04, 0xC7, 0x23, 0xC3, 0x18, 0x96, 0x05, 0x9A,
21462 + 0x07, 0x12, 0x80, 0xE2, 0xEB, 0x27, 0xB2, 0x75,
21463 + 0x09, 0x83, 0x2C, 0x1A, 0x1B, 0x6E, 0x5A, 0xA0,
21464 + 0x52, 0x3B, 0xD6, 0xB3, 0x29, 0xE3, 0x2F, 0x84,
21465 + 0x53, 0xD1, 0x00, 0xED, 0x20, 0xFC, 0xB1, 0x5B,
21466 + 0x6A, 0xCB, 0xBE, 0x39, 0x4A, 0x4C, 0x58, 0xCF,
21467 + 0xD0, 0xEF, 0xAA, 0xFB, 0x43, 0x4D, 0x33, 0x85,
21468 + 0x45, 0xF9, 0x02, 0x7F, 0x50, 0x3C, 0x9F, 0xA8,
21469 + 0x51, 0xA3, 0x40, 0x8F, 0x92, 0x9D, 0x38, 0xF5,
21470 + 0xBC, 0xB6, 0xDA, 0x21, 0x10, 0xFF, 0xF3, 0xD2,
21471 + 0xCD, 0x0C, 0x13, 0xEC, 0x5F, 0x97, 0x44, 0x17,
21472 + 0xC4, 0xA7, 0x7E, 0x3D, 0x64, 0x5D, 0x19, 0x73,
21473 + 0x60, 0x81, 0x4F, 0xDC, 0x22, 0x2A, 0x90, 0x88,
21474 + 0x46, 0xEE, 0xB8, 0x14, 0xDE, 0x5E, 0x0B, 0xDB,
21475 + 0xE0, 0x32, 0x3A, 0x0A, 0x49, 0x06, 0x24, 0x5C,
21476 + 0xC2, 0xD3, 0xAC, 0x62, 0x91, 0x95, 0xE4, 0x79,
21477 + 0xE7, 0xC8, 0x37, 0x6D, 0x8D, 0xD5, 0x4E, 0xA9,
21478 + 0x6C, 0x56, 0xF4, 0xEA, 0x65, 0x7A, 0xAE, 0x08,
21479 + 0xBA, 0x78, 0x25, 0x2E, 0x1C, 0xA6, 0xB4, 0xC6,
21480 + 0xE8, 0xDD, 0x74, 0x1F, 0x4B, 0xBD, 0x8B, 0x8A,
21481 + 0x70, 0x3E, 0xB5, 0x66, 0x48, 0x03, 0xF6, 0x0E,
21482 + 0x61, 0x35, 0x57, 0xB9, 0x86, 0xC1, 0x1D, 0x9E,
21483 + 0xE1, 0xF8, 0x98, 0x11, 0x69, 0xD9, 0x8E, 0x94,
21484 + 0x9B, 0x1E, 0x87, 0xE9, 0xCE, 0x55, 0x28, 0xDF,
21485 + 0x8C, 0xA1, 0x89, 0x0D, 0xBF, 0xE6, 0x42, 0x68,
21486 + 0x41, 0x99, 0x2D, 0x0F, 0xB0, 0x54, 0xBB, 0x16
21487 +};
21488 +
21489 +/* forward table */
21490 +#define FT \
21491 +\
21492 + V(C6,63,63,A5), V(F8,7C,7C,84), V(EE,77,77,99), V(F6,7B,7B,8D), \
21493 + V(FF,F2,F2,0D), V(D6,6B,6B,BD), V(DE,6F,6F,B1), V(91,C5,C5,54), \
21494 + V(60,30,30,50), V(02,01,01,03), V(CE,67,67,A9), V(56,2B,2B,7D), \
21495 + V(E7,FE,FE,19), V(B5,D7,D7,62), V(4D,AB,AB,E6), V(EC,76,76,9A), \
21496 + V(8F,CA,CA,45), V(1F,82,82,9D), V(89,C9,C9,40), V(FA,7D,7D,87), \
21497 + V(EF,FA,FA,15), V(B2,59,59,EB), V(8E,47,47,C9), V(FB,F0,F0,0B), \
21498 + V(41,AD,AD,EC), V(B3,D4,D4,67), V(5F,A2,A2,FD), V(45,AF,AF,EA), \
21499 + V(23,9C,9C,BF), V(53,A4,A4,F7), V(E4,72,72,96), V(9B,C0,C0,5B), \
21500 + V(75,B7,B7,C2), V(E1,FD,FD,1C), V(3D,93,93,AE), V(4C,26,26,6A), \
21501 + V(6C,36,36,5A), V(7E,3F,3F,41), V(F5,F7,F7,02), V(83,CC,CC,4F), \
21502 + V(68,34,34,5C), V(51,A5,A5,F4), V(D1,E5,E5,34), V(F9,F1,F1,08), \
21503 + V(E2,71,71,93), V(AB,D8,D8,73), V(62,31,31,53), V(2A,15,15,3F), \
21504 + V(08,04,04,0C), V(95,C7,C7,52), V(46,23,23,65), V(9D,C3,C3,5E), \
21505 + V(30,18,18,28), V(37,96,96,A1), V(0A,05,05,0F), V(2F,9A,9A,B5), \
21506 + V(0E,07,07,09), V(24,12,12,36), V(1B,80,80,9B), V(DF,E2,E2,3D), \
21507 + V(CD,EB,EB,26), V(4E,27,27,69), V(7F,B2,B2,CD), V(EA,75,75,9F), \
21508 + V(12,09,09,1B), V(1D,83,83,9E), V(58,2C,2C,74), V(34,1A,1A,2E), \
21509 + V(36,1B,1B,2D), V(DC,6E,6E,B2), V(B4,5A,5A,EE), V(5B,A0,A0,FB), \
21510 + V(A4,52,52,F6), V(76,3B,3B,4D), V(B7,D6,D6,61), V(7D,B3,B3,CE), \
21511 + V(52,29,29,7B), V(DD,E3,E3,3E), V(5E,2F,2F,71), V(13,84,84,97), \
21512 + V(A6,53,53,F5), V(B9,D1,D1,68), V(00,00,00,00), V(C1,ED,ED,2C), \
21513 + V(40,20,20,60), V(E3,FC,FC,1F), V(79,B1,B1,C8), V(B6,5B,5B,ED), \
21514 + V(D4,6A,6A,BE), V(8D,CB,CB,46), V(67,BE,BE,D9), V(72,39,39,4B), \
21515 + V(94,4A,4A,DE), V(98,4C,4C,D4), V(B0,58,58,E8), V(85,CF,CF,4A), \
21516 + V(BB,D0,D0,6B), V(C5,EF,EF,2A), V(4F,AA,AA,E5), V(ED,FB,FB,16), \
21517 + V(86,43,43,C5), V(9A,4D,4D,D7), V(66,33,33,55), V(11,85,85,94), \
21518 + V(8A,45,45,CF), V(E9,F9,F9,10), V(04,02,02,06), V(FE,7F,7F,81), \
21519 + V(A0,50,50,F0), V(78,3C,3C,44), V(25,9F,9F,BA), V(4B,A8,A8,E3), \
21520 + V(A2,51,51,F3), V(5D,A3,A3,FE), V(80,40,40,C0), V(05,8F,8F,8A), \
21521 + V(3F,92,92,AD), V(21,9D,9D,BC), V(70,38,38,48), V(F1,F5,F5,04), \
21522 + V(63,BC,BC,DF), V(77,B6,B6,C1), V(AF,DA,DA,75), V(42,21,21,63), \
21523 + V(20,10,10,30), V(E5,FF,FF,1A), V(FD,F3,F3,0E), V(BF,D2,D2,6D), \
21524 + V(81,CD,CD,4C), V(18,0C,0C,14), V(26,13,13,35), V(C3,EC,EC,2F), \
21525 + V(BE,5F,5F,E1), V(35,97,97,A2), V(88,44,44,CC), V(2E,17,17,39), \
21526 + V(93,C4,C4,57), V(55,A7,A7,F2), V(FC,7E,7E,82), V(7A,3D,3D,47), \
21527 + V(C8,64,64,AC), V(BA,5D,5D,E7), V(32,19,19,2B), V(E6,73,73,95), \
21528 + V(C0,60,60,A0), V(19,81,81,98), V(9E,4F,4F,D1), V(A3,DC,DC,7F), \
21529 + V(44,22,22,66), V(54,2A,2A,7E), V(3B,90,90,AB), V(0B,88,88,83), \
21530 + V(8C,46,46,CA), V(C7,EE,EE,29), V(6B,B8,B8,D3), V(28,14,14,3C), \
21531 + V(A7,DE,DE,79), V(BC,5E,5E,E2), V(16,0B,0B,1D), V(AD,DB,DB,76), \
21532 + V(DB,E0,E0,3B), V(64,32,32,56), V(74,3A,3A,4E), V(14,0A,0A,1E), \
21533 + V(92,49,49,DB), V(0C,06,06,0A), V(48,24,24,6C), V(B8,5C,5C,E4), \
21534 + V(9F,C2,C2,5D), V(BD,D3,D3,6E), V(43,AC,AC,EF), V(C4,62,62,A6), \
21535 + V(39,91,91,A8), V(31,95,95,A4), V(D3,E4,E4,37), V(F2,79,79,8B), \
21536 + V(D5,E7,E7,32), V(8B,C8,C8,43), V(6E,37,37,59), V(DA,6D,6D,B7), \
21537 + V(01,8D,8D,8C), V(B1,D5,D5,64), V(9C,4E,4E,D2), V(49,A9,A9,E0), \
21538 + V(D8,6C,6C,B4), V(AC,56,56,FA), V(F3,F4,F4,07), V(CF,EA,EA,25), \
21539 + V(CA,65,65,AF), V(F4,7A,7A,8E), V(47,AE,AE,E9), V(10,08,08,18), \
21540 + V(6F,BA,BA,D5), V(F0,78,78,88), V(4A,25,25,6F), V(5C,2E,2E,72), \
21541 + V(38,1C,1C,24), V(57,A6,A6,F1), V(73,B4,B4,C7), V(97,C6,C6,51), \
21542 + V(CB,E8,E8,23), V(A1,DD,DD,7C), V(E8,74,74,9C), V(3E,1F,1F,21), \
21543 + V(96,4B,4B,DD), V(61,BD,BD,DC), V(0D,8B,8B,86), V(0F,8A,8A,85), \
21544 + V(E0,70,70,90), V(7C,3E,3E,42), V(71,B5,B5,C4), V(CC,66,66,AA), \
21545 + V(90,48,48,D8), V(06,03,03,05), V(F7,F6,F6,01), V(1C,0E,0E,12), \
21546 + V(C2,61,61,A3), V(6A,35,35,5F), V(AE,57,57,F9), V(69,B9,B9,D0), \
21547 + V(17,86,86,91), V(99,C1,C1,58), V(3A,1D,1D,27), V(27,9E,9E,B9), \
21548 + V(D9,E1,E1,38), V(EB,F8,F8,13), V(2B,98,98,B3), V(22,11,11,33), \
21549 + V(D2,69,69,BB), V(A9,D9,D9,70), V(07,8E,8E,89), V(33,94,94,A7), \
21550 + V(2D,9B,9B,B6), V(3C,1E,1E,22), V(15,87,87,92), V(C9,E9,E9,20), \
21551 + V(87,CE,CE,49), V(AA,55,55,FF), V(50,28,28,78), V(A5,DF,DF,7A), \
21552 + V(03,8C,8C,8F), V(59,A1,A1,F8), V(09,89,89,80), V(1A,0D,0D,17), \
21553 + V(65,BF,BF,DA), V(D7,E6,E6,31), V(84,42,42,C6), V(D0,68,68,B8), \
21554 + V(82,41,41,C3), V(29,99,99,B0), V(5A,2D,2D,77), V(1E,0F,0F,11), \
21555 + V(7B,B0,B0,CB), V(A8,54,54,FC), V(6D,BB,BB,D6), V(2C,16,16,3A)
21556 +
21557 +#define V(a,b,c,d) 0x##a##b##c##d
21558 +static uint32 FT0[256] = { FT };
21559 +#undef V
21560 +
21561 +#define V(a,b,c,d) 0x##d##a##b##c
21562 +static uint32 FT1[256] = { FT };
21563 +#undef V
21564 +
21565 +#define V(a,b,c,d) 0x##c##d##a##b
21566 +static uint32 FT2[256] = { FT };
21567 +#undef V
21568 +
21569 +#define V(a,b,c,d) 0x##b##c##d##a
21570 +static uint32 FT3[256] = { FT };
21571 +#undef V
21572 +
21573 +#undef FT
21574 +
21575 +/* reverse S-box */
21576 +
21577 +static uint32 RSb[256] =
21578 +{
21579 + 0x52, 0x09, 0x6A, 0xD5, 0x30, 0x36, 0xA5, 0x38,
21580 + 0xBF, 0x40, 0xA3, 0x9E, 0x81, 0xF3, 0xD7, 0xFB,
21581 + 0x7C, 0xE3, 0x39, 0x82, 0x9B, 0x2F, 0xFF, 0x87,
21582 + 0x34, 0x8E, 0x43, 0x44, 0xC4, 0xDE, 0xE9, 0xCB,
21583 + 0x54, 0x7B, 0x94, 0x32, 0xA6, 0xC2, 0x23, 0x3D,
21584 + 0xEE, 0x4C, 0x95, 0x0B, 0x42, 0xFA, 0xC3, 0x4E,
21585 + 0x08, 0x2E, 0xA1, 0x66, 0x28, 0xD9, 0x24, 0xB2,
21586 + 0x76, 0x5B, 0xA2, 0x49, 0x6D, 0x8B, 0xD1, 0x25,
21587 + 0x72, 0xF8, 0xF6, 0x64, 0x86, 0x68, 0x98, 0x16,
21588 + 0xD4, 0xA4, 0x5C, 0xCC, 0x5D, 0x65, 0xB6, 0x92,
21589 + 0x6C, 0x70, 0x48, 0x50, 0xFD, 0xED, 0xB9, 0xDA,
21590 + 0x5E, 0x15, 0x46, 0x57, 0xA7, 0x8D, 0x9D, 0x84,
21591 + 0x90, 0xD8, 0xAB, 0x00, 0x8C, 0xBC, 0xD3, 0x0A,
21592 + 0xF7, 0xE4, 0x58, 0x05, 0xB8, 0xB3, 0x45, 0x06,
21593 + 0xD0, 0x2C, 0x1E, 0x8F, 0xCA, 0x3F, 0x0F, 0x02,
21594 + 0xC1, 0xAF, 0xBD, 0x03, 0x01, 0x13, 0x8A, 0x6B,
21595 + 0x3A, 0x91, 0x11, 0x41, 0x4F, 0x67, 0xDC, 0xEA,
21596 + 0x97, 0xF2, 0xCF, 0xCE, 0xF0, 0xB4, 0xE6, 0x73,
21597 + 0x96, 0xAC, 0x74, 0x22, 0xE7, 0xAD, 0x35, 0x85,
21598 + 0xE2, 0xF9, 0x37, 0xE8, 0x1C, 0x75, 0xDF, 0x6E,
21599 + 0x47, 0xF1, 0x1A, 0x71, 0x1D, 0x29, 0xC5, 0x89,
21600 + 0x6F, 0xB7, 0x62, 0x0E, 0xAA, 0x18, 0xBE, 0x1B,
21601 + 0xFC, 0x56, 0x3E, 0x4B, 0xC6, 0xD2, 0x79, 0x20,
21602 + 0x9A, 0xDB, 0xC0, 0xFE, 0x78, 0xCD, 0x5A, 0xF4,
21603 + 0x1F, 0xDD, 0xA8, 0x33, 0x88, 0x07, 0xC7, 0x31,
21604 + 0xB1, 0x12, 0x10, 0x59, 0x27, 0x80, 0xEC, 0x5F,
21605 + 0x60, 0x51, 0x7F, 0xA9, 0x19, 0xB5, 0x4A, 0x0D,
21606 + 0x2D, 0xE5, 0x7A, 0x9F, 0x93, 0xC9, 0x9C, 0xEF,
21607 + 0xA0, 0xE0, 0x3B, 0x4D, 0xAE, 0x2A, 0xF5, 0xB0,
21608 + 0xC8, 0xEB, 0xBB, 0x3C, 0x83, 0x53, 0x99, 0x61,
21609 + 0x17, 0x2B, 0x04, 0x7E, 0xBA, 0x77, 0xD6, 0x26,
21610 + 0xE1, 0x69, 0x14, 0x63, 0x55, 0x21, 0x0C, 0x7D
21611 +};
21612 +
21613 +/* reverse table */
21614 +
21615 +#define RT \
21616 +\
21617 + V(51,F4,A7,50), V(7E,41,65,53), V(1A,17,A4,C3), V(3A,27,5E,96), \
21618 + V(3B,AB,6B,CB), V(1F,9D,45,F1), V(AC,FA,58,AB), V(4B,E3,03,93), \
21619 + V(20,30,FA,55), V(AD,76,6D,F6), V(88,CC,76,91), V(F5,02,4C,25), \
21620 + V(4F,E5,D7,FC), V(C5,2A,CB,D7), V(26,35,44,80), V(B5,62,A3,8F), \
21621 + V(DE,B1,5A,49), V(25,BA,1B,67), V(45,EA,0E,98), V(5D,FE,C0,E1), \
21622 + V(C3,2F,75,02), V(81,4C,F0,12), V(8D,46,97,A3), V(6B,D3,F9,C6), \
21623 + V(03,8F,5F,E7), V(15,92,9C,95), V(BF,6D,7A,EB), V(95,52,59,DA), \
21624 + V(D4,BE,83,2D), V(58,74,21,D3), V(49,E0,69,29), V(8E,C9,C8,44), \
21625 + V(75,C2,89,6A), V(F4,8E,79,78), V(99,58,3E,6B), V(27,B9,71,DD), \
21626 + V(BE,E1,4F,B6), V(F0,88,AD,17), V(C9,20,AC,66), V(7D,CE,3A,B4), \
21627 + V(63,DF,4A,18), V(E5,1A,31,82), V(97,51,33,60), V(62,53,7F,45), \
21628 + V(B1,64,77,E0), V(BB,6B,AE,84), V(FE,81,A0,1C), V(F9,08,2B,94), \
21629 + V(70,48,68,58), V(8F,45,FD,19), V(94,DE,6C,87), V(52,7B,F8,B7), \
21630 + V(AB,73,D3,23), V(72,4B,02,E2), V(E3,1F,8F,57), V(66,55,AB,2A), \
21631 + V(B2,EB,28,07), V(2F,B5,C2,03), V(86,C5,7B,9A), V(D3,37,08,A5), \
21632 + V(30,28,87,F2), V(23,BF,A5,B2), V(02,03,6A,BA), V(ED,16,82,5C), \
21633 + V(8A,CF,1C,2B), V(A7,79,B4,92), V(F3,07,F2,F0), V(4E,69,E2,A1), \
21634 + V(65,DA,F4,CD), V(06,05,BE,D5), V(D1,34,62,1F), V(C4,A6,FE,8A), \
21635 + V(34,2E,53,9D), V(A2,F3,55,A0), V(05,8A,E1,32), V(A4,F6,EB,75), \
21636 + V(0B,83,EC,39), V(40,60,EF,AA), V(5E,71,9F,06), V(BD,6E,10,51), \
21637 + V(3E,21,8A,F9), V(96,DD,06,3D), V(DD,3E,05,AE), V(4D,E6,BD,46), \
21638 + V(91,54,8D,B5), V(71,C4,5D,05), V(04,06,D4,6F), V(60,50,15,FF), \
21639 + V(19,98,FB,24), V(D6,BD,E9,97), V(89,40,43,CC), V(67,D9,9E,77), \
21640 + V(B0,E8,42,BD), V(07,89,8B,88), V(E7,19,5B,38), V(79,C8,EE,DB), \
21641 + V(A1,7C,0A,47), V(7C,42,0F,E9), V(F8,84,1E,C9), V(00,00,00,00), \
21642 + V(09,80,86,83), V(32,2B,ED,48), V(1E,11,70,AC), V(6C,5A,72,4E), \
21643 + V(FD,0E,FF,FB), V(0F,85,38,56), V(3D,AE,D5,1E), V(36,2D,39,27), \
21644 + V(0A,0F,D9,64), V(68,5C,A6,21), V(9B,5B,54,D1), V(24,36,2E,3A), \
21645 + V(0C,0A,67,B1), V(93,57,E7,0F), V(B4,EE,96,D2), V(1B,9B,91,9E), \
21646 + V(80,C0,C5,4F), V(61,DC,20,A2), V(5A,77,4B,69), V(1C,12,1A,16), \
21647 + V(E2,93,BA,0A), V(C0,A0,2A,E5), V(3C,22,E0,43), V(12,1B,17,1D), \
21648 + V(0E,09,0D,0B), V(F2,8B,C7,AD), V(2D,B6,A8,B9), V(14,1E,A9,C8), \
21649 + V(57,F1,19,85), V(AF,75,07,4C), V(EE,99,DD,BB), V(A3,7F,60,FD), \
21650 + V(F7,01,26,9F), V(5C,72,F5,BC), V(44,66,3B,C5), V(5B,FB,7E,34), \
21651 + V(8B,43,29,76), V(CB,23,C6,DC), V(B6,ED,FC,68), V(B8,E4,F1,63), \
21652 + V(D7,31,DC,CA), V(42,63,85,10), V(13,97,22,40), V(84,C6,11,20), \
21653 + V(85,4A,24,7D), V(D2,BB,3D,F8), V(AE,F9,32,11), V(C7,29,A1,6D), \
21654 + V(1D,9E,2F,4B), V(DC,B2,30,F3), V(0D,86,52,EC), V(77,C1,E3,D0), \
21655 + V(2B,B3,16,6C), V(A9,70,B9,99), V(11,94,48,FA), V(47,E9,64,22), \
21656 + V(A8,FC,8C,C4), V(A0,F0,3F,1A), V(56,7D,2C,D8), V(22,33,90,EF), \
21657 + V(87,49,4E,C7), V(D9,38,D1,C1), V(8C,CA,A2,FE), V(98,D4,0B,36), \
21658 + V(A6,F5,81,CF), V(A5,7A,DE,28), V(DA,B7,8E,26), V(3F,AD,BF,A4), \
21659 + V(2C,3A,9D,E4), V(50,78,92,0D), V(6A,5F,CC,9B), V(54,7E,46,62), \
21660 + V(F6,8D,13,C2), V(90,D8,B8,E8), V(2E,39,F7,5E), V(82,C3,AF,F5), \
21661 + V(9F,5D,80,BE), V(69,D0,93,7C), V(6F,D5,2D,A9), V(CF,25,12,B3), \
21662 + V(C8,AC,99,3B), V(10,18,7D,A7), V(E8,9C,63,6E), V(DB,3B,BB,7B), \
21663 + V(CD,26,78,09), V(6E,59,18,F4), V(EC,9A,B7,01), V(83,4F,9A,A8), \
21664 + V(E6,95,6E,65), V(AA,FF,E6,7E), V(21,BC,CF,08), V(EF,15,E8,E6), \
21665 + V(BA,E7,9B,D9), V(4A,6F,36,CE), V(EA,9F,09,D4), V(29,B0,7C,D6), \
21666 + V(31,A4,B2,AF), V(2A,3F,23,31), V(C6,A5,94,30), V(35,A2,66,C0), \
21667 + V(74,4E,BC,37), V(FC,82,CA,A6), V(E0,90,D0,B0), V(33,A7,D8,15), \
21668 + V(F1,04,98,4A), V(41,EC,DA,F7), V(7F,CD,50,0E), V(17,91,F6,2F), \
21669 + V(76,4D,D6,8D), V(43,EF,B0,4D), V(CC,AA,4D,54), V(E4,96,04,DF), \
21670 + V(9E,D1,B5,E3), V(4C,6A,88,1B), V(C1,2C,1F,B8), V(46,65,51,7F), \
21671 + V(9D,5E,EA,04), V(01,8C,35,5D), V(FA,87,74,73), V(FB,0B,41,2E), \
21672 + V(B3,67,1D,5A), V(92,DB,D2,52), V(E9,10,56,33), V(6D,D6,47,13), \
21673 + V(9A,D7,61,8C), V(37,A1,0C,7A), V(59,F8,14,8E), V(EB,13,3C,89), \
21674 + V(CE,A9,27,EE), V(B7,61,C9,35), V(E1,1C,E5,ED), V(7A,47,B1,3C), \
21675 + V(9C,D2,DF,59), V(55,F2,73,3F), V(18,14,CE,79), V(73,C7,37,BF), \
21676 + V(53,F7,CD,EA), V(5F,FD,AA,5B), V(DF,3D,6F,14), V(78,44,DB,86), \
21677 + V(CA,AF,F3,81), V(B9,68,C4,3E), V(38,24,34,2C), V(C2,A3,40,5F), \
21678 + V(16,1D,C3,72), V(BC,E2,25,0C), V(28,3C,49,8B), V(FF,0D,95,41), \
21679 + V(39,A8,01,71), V(08,0C,B3,DE), V(D8,B4,E4,9C), V(64,56,C1,90), \
21680 + V(7B,CB,84,61), V(D5,32,B6,70), V(48,6C,5C,74), V(D0,B8,57,42)
21681 +
21682 +#define V(a,b,c,d) 0x##a##b##c##d
21683 +static uint32 RT0[256] = { RT };
21684 +#undef V
21685 +
21686 +#define V(a,b,c,d) 0x##d##a##b##c
21687 +static uint32 RT1[256] = { RT };
21688 +#undef V
21689 +
21690 +#define V(a,b,c,d) 0x##c##d##a##b
21691 +static uint32 RT2[256] = { RT };
21692 +#undef V
21693 +
21694 +#define V(a,b,c,d) 0x##b##c##d##a
21695 +static uint32 RT3[256] = { RT };
21696 +#undef V
21697 +
21698 +#undef RT
21699 +
21700 +/* round constants */
21701 +
21702 +static uint32 RCON[10] =
21703 +{
21704 + 0x01000000, 0x02000000, 0x04000000, 0x08000000,
21705 + 0x10000000, 0x20000000, 0x40000000, 0x80000000,
21706 + 0x1B000000, 0x36000000
21707 +};
21708 +
21709 +/* key schedule tables */
21710 +
21711 +static int KT_init = 1;
21712 +
21713 +static uint32 KT0[256];
21714 +static uint32 KT1[256];
21715 +static uint32 KT2[256];
21716 +static uint32 KT3[256];
21717 +
21718 +/* platform-independant 32-bit integer manipulation macros */
21719 +
21720 +#define GET_UINT32(n,b,i) \
21721 +{ \
21722 + (n) = ( (uint32) (b)[(i) ] << 24 ) \
21723 + | ( (uint32) (b)[(i) + 1] << 16 ) \
21724 + | ( (uint32) (b)[(i) + 2] << 8 ) \
21725 + | ( (uint32) (b)[(i) + 3] ); \
21726 +}
21727 +
21728 +#define PUT_UINT32(n,b,i) \
21729 +{ \
21730 + (b)[(i) ] = (uint8) ( (n) >> 24 ); \
21731 + (b)[(i) + 1] = (uint8) ( (n) >> 16 ); \
21732 + (b)[(i) + 2] = (uint8) ( (n) >> 8 ); \
21733 + (b)[(i) + 3] = (uint8) ( (n) ); \
21734 +}
21735 +
21736 +/* AES key scheduling routine */
21737 +
21738 +int rtmp_aes_set_key( aes_context *ctx, uint8 *key, int nbits )
21739 +{
21740 + int i;
21741 + uint32 *RK, *SK;
21742 +
21743 + switch( nbits )
21744 + {
21745 + case 128: ctx->nr = 10; break;
21746 + case 192: ctx->nr = 12; break;
21747 + case 256: ctx->nr = 14; break;
21748 + default : return( 1 );
21749 + }
21750 +
21751 + RK = ctx->erk;
21752 +
21753 + for( i = 0; i < (nbits >> 5); i++ )
21754 + {
21755 + GET_UINT32( RK[i], key, i * 4 );
21756 + }
21757 +
21758 + /* setup encryption round keys */
21759 +
21760 + switch( nbits )
21761 + {
21762 + case 128:
21763 +
21764 + for( i = 0; i < 10; i++, RK += 4 )
21765 + {
21766 + RK[4] = RK[0] ^ RCON[i] ^
21767 + ( FSb[ (uint8) ( RK[3] >> 16 ) ] << 24 ) ^
21768 + ( FSb[ (uint8) ( RK[3] >> 8 ) ] << 16 ) ^
21769 + ( FSb[ (uint8) ( RK[3] ) ] << 8 ) ^
21770 + ( FSb[ (uint8) ( RK[3] >> 24 ) ] );
21771 +
21772 + RK[5] = RK[1] ^ RK[4];
21773 + RK[6] = RK[2] ^ RK[5];
21774 + RK[7] = RK[3] ^ RK[6];
21775 + }
21776 + break;
21777 +
21778 + case 192:
21779 +
21780 + for( i = 0; i < 8; i++, RK += 6 )
21781 + {
21782 + RK[6] = RK[0] ^ RCON[i] ^
21783 + ( FSb[ (uint8) ( RK[5] >> 16 ) ] << 24 ) ^
21784 + ( FSb[ (uint8) ( RK[5] >> 8 ) ] << 16 ) ^
21785 + ( FSb[ (uint8) ( RK[5] ) ] << 8 ) ^
21786 + ( FSb[ (uint8) ( RK[5] >> 24 ) ] );
21787 +
21788 + RK[7] = RK[1] ^ RK[6];
21789 + RK[8] = RK[2] ^ RK[7];
21790 + RK[9] = RK[3] ^ RK[8];
21791 + RK[10] = RK[4] ^ RK[9];
21792 + RK[11] = RK[5] ^ RK[10];
21793 + }
21794 + break;
21795 +
21796 + case 256:
21797 +
21798 + for( i = 0; i < 7; i++, RK += 8 )
21799 + {
21800 + RK[8] = RK[0] ^ RCON[i] ^
21801 + ( FSb[ (uint8) ( RK[7] >> 16 ) ] << 24 ) ^
21802 + ( FSb[ (uint8) ( RK[7] >> 8 ) ] << 16 ) ^
21803 + ( FSb[ (uint8) ( RK[7] ) ] << 8 ) ^
21804 + ( FSb[ (uint8) ( RK[7] >> 24 ) ] );
21805 +
21806 + RK[9] = RK[1] ^ RK[8];
21807 + RK[10] = RK[2] ^ RK[9];
21808 + RK[11] = RK[3] ^ RK[10];
21809 +
21810 + RK[12] = RK[4] ^
21811 + ( FSb[ (uint8) ( RK[11] >> 24 ) ] << 24 ) ^
21812 + ( FSb[ (uint8) ( RK[11] >> 16 ) ] << 16 ) ^
21813 + ( FSb[ (uint8) ( RK[11] >> 8 ) ] << 8 ) ^
21814 + ( FSb[ (uint8) ( RK[11] ) ] );
21815 +
21816 + RK[13] = RK[5] ^ RK[12];
21817 + RK[14] = RK[6] ^ RK[13];
21818 + RK[15] = RK[7] ^ RK[14];
21819 + }
21820 + break;
21821 + }
21822 +
21823 + /* setup decryption round keys */
21824 +
21825 + if( KT_init )
21826 + {
21827 + for( i = 0; i < 256; i++ )
21828 + {
21829 + KT0[i] = RT0[ FSb[i] ];
21830 + KT1[i] = RT1[ FSb[i] ];
21831 + KT2[i] = RT2[ FSb[i] ];
21832 + KT3[i] = RT3[ FSb[i] ];
21833 + }
21834 +
21835 + KT_init = 0;
21836 + }
21837 +
21838 + SK = ctx->drk;
21839 +
21840 + *SK++ = *RK++;
21841 + *SK++ = *RK++;
21842 + *SK++ = *RK++;
21843 + *SK++ = *RK++;
21844 +
21845 + for( i = 1; i < ctx->nr; i++ )
21846 + {
21847 + RK -= 8;
21848 +
21849 + *SK++ = KT0[ (uint8) ( *RK >> 24 ) ] ^
21850 + KT1[ (uint8) ( *RK >> 16 ) ] ^
21851 + KT2[ (uint8) ( *RK >> 8 ) ] ^
21852 + KT3[ (uint8) ( *RK ) ]; RK++;
21853 +
21854 + *SK++ = KT0[ (uint8) ( *RK >> 24 ) ] ^
21855 + KT1[ (uint8) ( *RK >> 16 ) ] ^
21856 + KT2[ (uint8) ( *RK >> 8 ) ] ^
21857 + KT3[ (uint8) ( *RK ) ]; RK++;
21858 +
21859 + *SK++ = KT0[ (uint8) ( *RK >> 24 ) ] ^
21860 + KT1[ (uint8) ( *RK >> 16 ) ] ^
21861 + KT2[ (uint8) ( *RK >> 8 ) ] ^
21862 + KT3[ (uint8) ( *RK ) ]; RK++;
21863 +
21864 + *SK++ = KT0[ (uint8) ( *RK >> 24 ) ] ^
21865 + KT1[ (uint8) ( *RK >> 16 ) ] ^
21866 + KT2[ (uint8) ( *RK >> 8 ) ] ^
21867 + KT3[ (uint8) ( *RK ) ]; RK++;
21868 + }
21869 +
21870 + RK -= 8;
21871 +
21872 + *SK++ = *RK++;
21873 + *SK++ = *RK++;
21874 + *SK++ = *RK++;
21875 + *SK++ = *RK++;
21876 +
21877 + return( 0 );
21878 +}
21879 +
21880 +/* AES 128-bit block encryption routine */
21881 +
21882 +void rtmp_aes_encrypt(aes_context *ctx, uint8 input[16], uint8 output[16] )
21883 +{
21884 + uint32 *RK, X0, X1, X2, X3, Y0, Y1, Y2, Y3;
21885 +
21886 + RK = ctx->erk;
21887 + GET_UINT32( X0, input, 0 ); X0 ^= RK[0];
21888 + GET_UINT32( X1, input, 4 ); X1 ^= RK[1];
21889 + GET_UINT32( X2, input, 8 ); X2 ^= RK[2];
21890 + GET_UINT32( X3, input, 12 ); X3 ^= RK[3];
21891 +
21892 +#define AES_FROUND(X0,X1,X2,X3,Y0,Y1,Y2,Y3) \
21893 +{ \
21894 + RK += 4; \
21895 + \
21896 + X0 = RK[0] ^ FT0[ (uint8) ( Y0 >> 24 ) ] ^ \
21897 + FT1[ (uint8) ( Y1 >> 16 ) ] ^ \
21898 + FT2[ (uint8) ( Y2 >> 8 ) ] ^ \
21899 + FT3[ (uint8) ( Y3 ) ]; \
21900 + \
21901 + X1 = RK[1] ^ FT0[ (uint8) ( Y1 >> 24 ) ] ^ \
21902 + FT1[ (uint8) ( Y2 >> 16 ) ] ^ \
21903 + FT2[ (uint8) ( Y3 >> 8 ) ] ^ \
21904 + FT3[ (uint8) ( Y0 ) ]; \
21905 + \
21906 + X2 = RK[2] ^ FT0[ (uint8) ( Y2 >> 24 ) ] ^ \
21907 + FT1[ (uint8) ( Y3 >> 16 ) ] ^ \
21908 + FT2[ (uint8) ( Y0 >> 8 ) ] ^ \
21909 + FT3[ (uint8) ( Y1 ) ]; \
21910 + \
21911 + X3 = RK[3] ^ FT0[ (uint8) ( Y3 >> 24 ) ] ^ \
21912 + FT1[ (uint8) ( Y0 >> 16 ) ] ^ \
21913 + FT2[ (uint8) ( Y1 >> 8 ) ] ^ \
21914 + FT3[ (uint8) ( Y2 ) ]; \
21915 +}
21916 +
21917 + AES_FROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 1 */
21918 + AES_FROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 2 */
21919 + AES_FROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 3 */
21920 + AES_FROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 4 */
21921 + AES_FROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 5 */
21922 + AES_FROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 6 */
21923 + AES_FROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 7 */
21924 + AES_FROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 8 */
21925 + AES_FROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 9 */
21926 +
21927 + if( ctx->nr > 10 )
21928 + {
21929 + AES_FROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 10 */
21930 + AES_FROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 11 */
21931 + }
21932 +
21933 + if( ctx->nr > 12 )
21934 + {
21935 + AES_FROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 12 */
21936 + AES_FROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 13 */
21937 + }
21938 +
21939 + /* last round */
21940 +
21941 + RK += 4;
21942 +
21943 + X0 = RK[0] ^ ( FSb[ (uint8) ( Y0 >> 24 ) ] << 24 ) ^
21944 + ( FSb[ (uint8) ( Y1 >> 16 ) ] << 16 ) ^
21945 + ( FSb[ (uint8) ( Y2 >> 8 ) ] << 8 ) ^
21946 + ( FSb[ (uint8) ( Y3 ) ] );
21947 +
21948 + X1 = RK[1] ^ ( FSb[ (uint8) ( Y1 >> 24 ) ] << 24 ) ^
21949 + ( FSb[ (uint8) ( Y2 >> 16 ) ] << 16 ) ^
21950 + ( FSb[ (uint8) ( Y3 >> 8 ) ] << 8 ) ^
21951 + ( FSb[ (uint8) ( Y0 ) ] );
21952 +
21953 + X2 = RK[2] ^ ( FSb[ (uint8) ( Y2 >> 24 ) ] << 24 ) ^
21954 + ( FSb[ (uint8) ( Y3 >> 16 ) ] << 16 ) ^
21955 + ( FSb[ (uint8) ( Y0 >> 8 ) ] << 8 ) ^
21956 + ( FSb[ (uint8) ( Y1 ) ] );
21957 +
21958 + X3 = RK[3] ^ ( FSb[ (uint8) ( Y3 >> 24 ) ] << 24 ) ^
21959 + ( FSb[ (uint8) ( Y0 >> 16 ) ] << 16 ) ^
21960 + ( FSb[ (uint8) ( Y1 >> 8 ) ] << 8 ) ^
21961 + ( FSb[ (uint8) ( Y2 ) ] );
21962 +
21963 + PUT_UINT32( X0, output, 0 );
21964 + PUT_UINT32( X1, output, 4 );
21965 + PUT_UINT32( X2, output, 8 );
21966 + PUT_UINT32( X3, output, 12 );
21967 +}
21968 +
21969 +/* AES 128-bit block decryption routine */
21970 +
21971 +void rtmp_aes_decrypt( aes_context *ctx, uint8 input[16], uint8 output[16] )
21972 +{
21973 + uint32 *RK, X0, X1, X2, X3, Y0, Y1, Y2, Y3;
21974 +
21975 + RK = ctx->drk;
21976 +
21977 + GET_UINT32( X0, input, 0 ); X0 ^= RK[0];
21978 + GET_UINT32( X1, input, 4 ); X1 ^= RK[1];
21979 + GET_UINT32( X2, input, 8 ); X2 ^= RK[2];
21980 + GET_UINT32( X3, input, 12 ); X3 ^= RK[3];
21981 +
21982 +#define AES_RROUND(X0,X1,X2,X3,Y0,Y1,Y2,Y3) \
21983 +{ \
21984 + RK += 4; \
21985 + \
21986 + X0 = RK[0] ^ RT0[ (uint8) ( Y0 >> 24 ) ] ^ \
21987 + RT1[ (uint8) ( Y3 >> 16 ) ] ^ \
21988 + RT2[ (uint8) ( Y2 >> 8 ) ] ^ \
21989 + RT3[ (uint8) ( Y1 ) ]; \
21990 + \
21991 + X1 = RK[1] ^ RT0[ (uint8) ( Y1 >> 24 ) ] ^ \
21992 + RT1[ (uint8) ( Y0 >> 16 ) ] ^ \
21993 + RT2[ (uint8) ( Y3 >> 8 ) ] ^ \
21994 + RT3[ (uint8) ( Y2 ) ]; \
21995 + \
21996 + X2 = RK[2] ^ RT0[ (uint8) ( Y2 >> 24 ) ] ^ \
21997 + RT1[ (uint8) ( Y1 >> 16 ) ] ^ \
21998 + RT2[ (uint8) ( Y0 >> 8 ) ] ^ \
21999 + RT3[ (uint8) ( Y3 ) ]; \
22000 + \
22001 + X3 = RK[3] ^ RT0[ (uint8) ( Y3 >> 24 ) ] ^ \
22002 + RT1[ (uint8) ( Y2 >> 16 ) ] ^ \
22003 + RT2[ (uint8) ( Y1 >> 8 ) ] ^ \
22004 + RT3[ (uint8) ( Y0 ) ]; \
22005 +}
22006 +
22007 + AES_RROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 1 */
22008 + AES_RROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 2 */
22009 + AES_RROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 3 */
22010 + AES_RROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 4 */
22011 + AES_RROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 5 */
22012 + AES_RROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 6 */
22013 + AES_RROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 7 */
22014 + AES_RROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 8 */
22015 + AES_RROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 9 */
22016 +
22017 + if( ctx->nr > 10 )
22018 + {
22019 + AES_RROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 10 */
22020 + AES_RROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 11 */
22021 + }
22022 +
22023 + if( ctx->nr > 12 )
22024 + {
22025 + AES_RROUND( X0, X1, X2, X3, Y0, Y1, Y2, Y3 ); /* round 12 */
22026 + AES_RROUND( Y0, Y1, Y2, Y3, X0, X1, X2, X3 ); /* round 13 */
22027 + }
22028 +
22029 + /* last round */
22030 +
22031 + RK += 4;
22032 +
22033 + X0 = RK[0] ^ ( RSb[ (uint8) ( Y0 >> 24 ) ] << 24 ) ^
22034 + ( RSb[ (uint8) ( Y3 >> 16 ) ] << 16 ) ^
22035 + ( RSb[ (uint8) ( Y2 >> 8 ) ] << 8 ) ^
22036 + ( RSb[ (uint8) ( Y1 ) ] );
22037 +
22038 + X1 = RK[1] ^ ( RSb[ (uint8) ( Y1 >> 24 ) ] << 24 ) ^
22039 + ( RSb[ (uint8) ( Y0 >> 16 ) ] << 16 ) ^
22040 + ( RSb[ (uint8) ( Y3 >> 8 ) ] << 8 ) ^
22041 + ( RSb[ (uint8) ( Y2 ) ] );
22042 +
22043 + X2 = RK[2] ^ ( RSb[ (uint8) ( Y2 >> 24 ) ] << 24 ) ^
22044 + ( RSb[ (uint8) ( Y1 >> 16 ) ] << 16 ) ^
22045 + ( RSb[ (uint8) ( Y0 >> 8 ) ] << 8 ) ^
22046 + ( RSb[ (uint8) ( Y3 ) ] );
22047 +
22048 + X3 = RK[3] ^ ( RSb[ (uint8) ( Y3 >> 24 ) ] << 24 ) ^
22049 + ( RSb[ (uint8) ( Y2 >> 16 ) ] << 16 ) ^
22050 + ( RSb[ (uint8) ( Y1 >> 8 ) ] << 8 ) ^
22051 + ( RSb[ (uint8) ( Y0 ) ] );
22052 +
22053 + PUT_UINT32( X0, output, 0 );
22054 + PUT_UINT32( X1, output, 4 );
22055 + PUT_UINT32( X2, output, 8 );
22056 + PUT_UINT32( X3, output, 12 );
22057 +}
22058 +
22059 +/*
22060 + ========================================================================
22061 +
22062 + Routine Description:
22063 + SHA1 function
22064 +
22065 + Arguments:
22066 +
22067 + Return Value:
22068 +
22069 + Note:
22070 +
22071 + ========================================================================
22072 +*/
22073 +VOID HMAC_SHA1(
22074 + IN UCHAR *text,
22075 + IN UINT text_len,
22076 + IN UCHAR *key,
22077 + IN UINT key_len,
22078 + IN UCHAR *digest)
22079 +{
22080 + SHA_CTX context;
22081 + UCHAR k_ipad[65]; /* inner padding - key XORd with ipad */
22082 + UCHAR k_opad[65]; /* outer padding - key XORd with opad */
22083 + INT i;
22084 +
22085 + // if key is longer than 64 bytes reset it to key=SHA1(key)
22086 + if (key_len > 64)
22087 + {
22088 + SHA_CTX tctx;
22089 + SHAInit(&tctx);
22090 + SHAUpdate(&tctx, key, key_len);
22091 + SHAFinal(&tctx, key);
22092 + key_len = 20;
22093 + }
22094 + NdisZeroMemory(k_ipad, sizeof(k_ipad));
22095 + NdisZeroMemory(k_opad, sizeof(k_opad));
22096 + NdisMoveMemory(k_ipad, key, key_len);
22097 + NdisMoveMemory(k_opad, key, key_len);
22098 +
22099 + // XOR key with ipad and opad values
22100 + for (i = 0; i < 64; i++)
22101 + {
22102 + k_ipad[i] ^= 0x36;
22103 + k_opad[i] ^= 0x5c;
22104 + }
22105 +
22106 + // perform inner SHA1
22107 + SHAInit(&context); /* init context for 1st pass */
22108 + SHAUpdate(&context, k_ipad, 64); /* start with inner pad */
22109 + SHAUpdate(&context, text, text_len); /* then text of datagram */
22110 + SHAFinal(&context, digest); /* finish up 1st pass */
22111 +
22112 + //perform outer SHA1
22113 + SHAInit(&context); /* init context for 2nd pass */
22114 + SHAUpdate(&context, k_opad, 64); /* start with outer pad */
22115 + SHAUpdate(&context, digest, 20); /* then results of 1st hash */
22116 + SHAFinal(&context, digest); /* finish up 2nd pass */
22117 +
22118 +}
22119 +
22120 +/*
22121 +* F(P, S, c, i) = U1 xor U2 xor ... Uc
22122 +* U1 = PRF(P, S || Int(i))
22123 +* U2 = PRF(P, U1)
22124 +* Uc = PRF(P, Uc-1)
22125 +*/
22126 +
22127 +void F(char *password, unsigned char *ssid, int ssidlength, int iterations, int count, unsigned char *output)
22128 +{
22129 + unsigned char digest[36], digest1[SHA_DIGEST_LEN];
22130 + int i, j;
22131 +
22132 + /* U1 = PRF(P, S || int(i)) */
22133 + memcpy(digest, ssid, ssidlength);
22134 + digest[ssidlength] = (unsigned char)((count>>24) & 0xff);
22135 + digest[ssidlength+1] = (unsigned char)((count>>16) & 0xff);
22136 + digest[ssidlength+2] = (unsigned char)((count>>8) & 0xff);
22137 + digest[ssidlength+3] = (unsigned char)(count & 0xff);
22138 + HMAC_SHA1(digest, ssidlength+4, (unsigned char*) password, (int) strlen(password), digest1); // for WPA update
22139 +
22140 + /* output = U1 */
22141 + memcpy(output, digest1, SHA_DIGEST_LEN);
22142 +
22143 + for (i = 1; i < iterations; i++)
22144 + {
22145 + /* Un = PRF(P, Un-1) */
22146 + HMAC_SHA1(digest1, SHA_DIGEST_LEN, (unsigned char*) password, (int) strlen(password), digest); // for WPA update
22147 + memcpy(digest1, digest, SHA_DIGEST_LEN);
22148 +
22149 + /* output = output xor Un */
22150 + for (j = 0; j < SHA_DIGEST_LEN; j++)
22151 + {
22152 + output[j] ^= digest[j];
22153 + }
22154 + }
22155 +}
22156 +/*
22157 +* password - ascii string up to 63 characters in length
22158 +* ssid - octet string up to 32 octets
22159 +* ssidlength - length of ssid in octets
22160 +* output must be 40 octets in length and outputs 256 bits of key
22161 +*/
22162 +int PasswordHash(char *password, unsigned char *ssid, int ssidlength, unsigned char *output)
22163 +{
22164 + if ((strlen(password) > 63) || (ssidlength > 32))
22165 + return 0;
22166 +
22167 + F(password, ssid, ssidlength, 4096, 1, output);
22168 + F(password, ssid, ssidlength, 4096, 2, &output[SHA_DIGEST_LEN]);
22169 + return 1;
22170 +}
22171 +
22172 +
22173 --- /dev/null
22174 +++ b/drivers/staging/rt2860/common/mlme.c
22175 @@ -0,0 +1,8667 @@
22176 +/*
22177 + *************************************************************************
22178 + * Ralink Tech Inc.
22179 + * 5F., No.36, Taiyuan St., Jhubei City,
22180 + * Hsinchu County 302,
22181 + * Taiwan, R.O.C.
22182 + *
22183 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
22184 + *
22185 + * This program is free software; you can redistribute it and/or modify *
22186 + * it under the terms of the GNU General Public License as published by *
22187 + * the Free Software Foundation; either version 2 of the License, or *
22188 + * (at your option) any later version. *
22189 + * *
22190 + * This program is distributed in the hope that it will be useful, *
22191 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
22192 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
22193 + * GNU General Public License for more details. *
22194 + * *
22195 + * You should have received a copy of the GNU General Public License *
22196 + * along with this program; if not, write to the *
22197 + * Free Software Foundation, Inc., *
22198 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
22199 + * *
22200 + *************************************************************************
22201 +
22202 + Module Name:
22203 + mlme.c
22204 +
22205 + Abstract:
22206 +
22207 + Revision History:
22208 + Who When What
22209 + -------- ---------- ----------------------------------------------
22210 + John Chang 2004-08-25 Modify from RT2500 code base
22211 + John Chang 2004-09-06 modified for RT2600
22212 +*/
22213 +
22214 +#include "../rt_config.h"
22215 +#include <stdarg.h>
22216 +
22217 +UCHAR CISCO_OUI[] = {0x00, 0x40, 0x96};
22218 +
22219 +UCHAR WPA_OUI[] = {0x00, 0x50, 0xf2, 0x01};
22220 +UCHAR RSN_OUI[] = {0x00, 0x0f, 0xac};
22221 +UCHAR WAPI_OUI[] = {0x00, 0x14, 0x72};
22222 +UCHAR WME_INFO_ELEM[] = {0x00, 0x50, 0xf2, 0x02, 0x00, 0x01};
22223 +UCHAR WME_PARM_ELEM[] = {0x00, 0x50, 0xf2, 0x02, 0x01, 0x01};
22224 +UCHAR Ccx2QosInfo[] = {0x00, 0x40, 0x96, 0x04};
22225 +UCHAR RALINK_OUI[] = {0x00, 0x0c, 0x43};
22226 +UCHAR BROADCOM_OUI[] = {0x00, 0x90, 0x4c};
22227 +UCHAR WPS_OUI[] = {0x00, 0x50, 0xf2, 0x04};
22228 +#ifdef CONFIG_STA_SUPPORT
22229 +#ifdef DOT11_N_SUPPORT
22230 +UCHAR PRE_N_HT_OUI[] = {0x00, 0x90, 0x4c};
22231 +#endif // DOT11_N_SUPPORT //
22232 +#endif // CONFIG_STA_SUPPORT //
22233 +
22234 +UCHAR RateSwitchTable[] = {
22235 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22236 + 0x11, 0x00, 0, 0, 0, // Initial used item after association
22237 + 0x00, 0x00, 0, 40, 101,
22238 + 0x01, 0x00, 1, 40, 50,
22239 + 0x02, 0x00, 2, 35, 45,
22240 + 0x03, 0x00, 3, 20, 45,
22241 + 0x04, 0x21, 0, 30, 50,
22242 + 0x05, 0x21, 1, 20, 50,
22243 + 0x06, 0x21, 2, 20, 50,
22244 + 0x07, 0x21, 3, 15, 50,
22245 + 0x08, 0x21, 4, 15, 30,
22246 + 0x09, 0x21, 5, 10, 25,
22247 + 0x0a, 0x21, 6, 8, 25,
22248 + 0x0b, 0x21, 7, 8, 25,
22249 + 0x0c, 0x20, 12, 15, 30,
22250 + 0x0d, 0x20, 13, 8, 20,
22251 + 0x0e, 0x20, 14, 8, 20,
22252 + 0x0f, 0x20, 15, 8, 25,
22253 + 0x10, 0x22, 15, 8, 25,
22254 + 0x11, 0x00, 0, 0, 0,
22255 + 0x12, 0x00, 0, 0, 0,
22256 + 0x13, 0x00, 0, 0, 0,
22257 + 0x14, 0x00, 0, 0, 0,
22258 + 0x15, 0x00, 0, 0, 0,
22259 + 0x16, 0x00, 0, 0, 0,
22260 + 0x17, 0x00, 0, 0, 0,
22261 + 0x18, 0x00, 0, 0, 0,
22262 + 0x19, 0x00, 0, 0, 0,
22263 + 0x1a, 0x00, 0, 0, 0,
22264 + 0x1b, 0x00, 0, 0, 0,
22265 + 0x1c, 0x00, 0, 0, 0,
22266 + 0x1d, 0x00, 0, 0, 0,
22267 + 0x1e, 0x00, 0, 0, 0,
22268 + 0x1f, 0x00, 0, 0, 0,
22269 +};
22270 +
22271 +UCHAR RateSwitchTable11B[] = {
22272 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22273 + 0x04, 0x03, 0, 0, 0, // Initial used item after association
22274 + 0x00, 0x00, 0, 40, 101,
22275 + 0x01, 0x00, 1, 40, 50,
22276 + 0x02, 0x00, 2, 35, 45,
22277 + 0x03, 0x00, 3, 20, 45,
22278 +};
22279 +
22280 +UCHAR RateSwitchTable11BG[] = {
22281 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22282 + 0x0a, 0x00, 0, 0, 0, // Initial used item after association
22283 + 0x00, 0x00, 0, 40, 101,
22284 + 0x01, 0x00, 1, 40, 50,
22285 + 0x02, 0x00, 2, 35, 45,
22286 + 0x03, 0x00, 3, 20, 45,
22287 + 0x04, 0x10, 2, 20, 35,
22288 + 0x05, 0x10, 3, 16, 35,
22289 + 0x06, 0x10, 4, 10, 25,
22290 + 0x07, 0x10, 5, 16, 25,
22291 + 0x08, 0x10, 6, 10, 25,
22292 + 0x09, 0x10, 7, 10, 13,
22293 +};
22294 +
22295 +UCHAR RateSwitchTable11G[] = {
22296 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22297 + 0x08, 0x00, 0, 0, 0, // Initial used item after association
22298 + 0x00, 0x10, 0, 20, 101,
22299 + 0x01, 0x10, 1, 20, 35,
22300 + 0x02, 0x10, 2, 20, 35,
22301 + 0x03, 0x10, 3, 16, 35,
22302 + 0x04, 0x10, 4, 10, 25,
22303 + 0x05, 0x10, 5, 16, 25,
22304 + 0x06, 0x10, 6, 10, 25,
22305 + 0x07, 0x10, 7, 10, 13,
22306 +};
22307 +
22308 +#ifdef DOT11_N_SUPPORT
22309 +UCHAR RateSwitchTable11N1S[] = {
22310 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22311 + 0x09, 0x00, 0, 0, 0, // Initial used item after association
22312 + 0x00, 0x21, 0, 30, 101,
22313 + 0x01, 0x21, 1, 20, 50,
22314 + 0x02, 0x21, 2, 20, 50,
22315 + 0x03, 0x21, 3, 15, 50,
22316 + 0x04, 0x21, 4, 15, 30,
22317 + 0x05, 0x21, 5, 10, 25,
22318 + 0x06, 0x21, 6, 8, 14,
22319 + 0x07, 0x21, 7, 8, 14,
22320 + 0x08, 0x23, 7, 8, 14,
22321 +};
22322 +
22323 +UCHAR RateSwitchTable11N2S[] = {
22324 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22325 + 0x0a, 0x00, 0, 0, 0, // Initial used item after association
22326 + 0x00, 0x21, 0, 30, 101,
22327 + 0x01, 0x21, 1, 20, 50,
22328 + 0x02, 0x21, 2, 20, 50,
22329 + 0x03, 0x21, 3, 15, 50,
22330 + 0x04, 0x21, 4, 15, 30,
22331 + 0x05, 0x20, 12, 15, 30,
22332 + 0x06, 0x20, 13, 8, 20,
22333 + 0x07, 0x20, 14, 8, 20,
22334 + 0x08, 0x20, 15, 8, 25,
22335 + 0x09, 0x22, 15, 8, 25,
22336 +};
22337 +
22338 +UCHAR RateSwitchTable11N3S[] = {
22339 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22340 + 0x0a, 0x00, 0, 0, 0, // Initial used item after association
22341 + 0x00, 0x21, 0, 30, 101,
22342 + 0x01, 0x21, 1, 20, 50,
22343 + 0x02, 0x21, 2, 20, 50,
22344 + 0x03, 0x21, 3, 15, 50,
22345 + 0x04, 0x21, 4, 15, 30,
22346 + 0x05, 0x20, 12, 15, 30,
22347 + 0x06, 0x20, 13, 8, 20,
22348 + 0x07, 0x20, 14, 8, 20,
22349 + 0x08, 0x20, 15, 8, 25,
22350 + 0x09, 0x22, 15, 8, 25,
22351 +};
22352 +
22353 +UCHAR RateSwitchTable11N2SForABand[] = {
22354 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22355 + 0x0b, 0x09, 0, 0, 0, // Initial used item after association
22356 + 0x00, 0x21, 0, 30, 101,
22357 + 0x01, 0x21, 1, 20, 50,
22358 + 0x02, 0x21, 2, 20, 50,
22359 + 0x03, 0x21, 3, 15, 50,
22360 + 0x04, 0x21, 4, 15, 30,
22361 + 0x05, 0x21, 5, 15, 30,
22362 + 0x06, 0x20, 12, 15, 30,
22363 + 0x07, 0x20, 13, 8, 20,
22364 + 0x08, 0x20, 14, 8, 20,
22365 + 0x09, 0x20, 15, 8, 25,
22366 + 0x0a, 0x22, 15, 8, 25,
22367 +};
22368 +
22369 +UCHAR RateSwitchTable11N3SForABand[] = { // 3*3
22370 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22371 + 0x0b, 0x09, 0, 0, 0, // Initial used item after association
22372 + 0x00, 0x21, 0, 30, 101,
22373 + 0x01, 0x21, 1, 20, 50,
22374 + 0x02, 0x21, 2, 20, 50,
22375 + 0x03, 0x21, 3, 15, 50,
22376 + 0x04, 0x21, 4, 15, 30,
22377 + 0x05, 0x21, 5, 15, 30,
22378 + 0x06, 0x20, 12, 15, 30,
22379 + 0x07, 0x20, 13, 8, 20,
22380 + 0x08, 0x20, 14, 8, 20,
22381 + 0x09, 0x20, 15, 8, 25,
22382 + 0x0a, 0x22, 15, 8, 25,
22383 +};
22384 +
22385 +UCHAR RateSwitchTable11BGN1S[] = {
22386 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22387 + 0x0d, 0x00, 0, 0, 0, // Initial used item after association
22388 + 0x00, 0x00, 0, 40, 101,
22389 + 0x01, 0x00, 1, 40, 50,
22390 + 0x02, 0x00, 2, 35, 45,
22391 + 0x03, 0x00, 3, 20, 45,
22392 + 0x04, 0x21, 0, 30,101, //50
22393 + 0x05, 0x21, 1, 20, 50,
22394 + 0x06, 0x21, 2, 20, 50,
22395 + 0x07, 0x21, 3, 15, 50,
22396 + 0x08, 0x21, 4, 15, 30,
22397 + 0x09, 0x21, 5, 10, 25,
22398 + 0x0a, 0x21, 6, 8, 14,
22399 + 0x0b, 0x21, 7, 8, 14,
22400 + 0x0c, 0x23, 7, 8, 14,
22401 +};
22402 +
22403 +UCHAR RateSwitchTable11BGN2S[] = {
22404 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22405 + 0x0a, 0x00, 0, 0, 0, // Initial used item after association
22406 + 0x00, 0x21, 0, 30,101, //50
22407 + 0x01, 0x21, 1, 20, 50,
22408 + 0x02, 0x21, 2, 20, 50,
22409 + 0x03, 0x21, 3, 15, 50,
22410 + 0x04, 0x21, 4, 15, 30,
22411 + 0x05, 0x20, 12, 15, 30,
22412 + 0x06, 0x20, 13, 8, 20,
22413 + 0x07, 0x20, 14, 8, 20,
22414 + 0x08, 0x20, 15, 8, 25,
22415 + 0x09, 0x22, 15, 8, 25,
22416 +};
22417 +
22418 +UCHAR RateSwitchTable11BGN3S[] = { // 3*3
22419 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22420 + 0x0a, 0x00, 0, 0, 0, // Initial used item after association
22421 + 0x00, 0x21, 0, 30,101, //50
22422 + 0x01, 0x21, 1, 20, 50,
22423 + 0x02, 0x21, 2, 20, 50,
22424 + 0x03, 0x21, 3, 20, 50,
22425 + 0x04, 0x21, 4, 15, 50,
22426 + 0x05, 0x20, 20, 15, 30,
22427 + 0x06, 0x20, 21, 8, 20,
22428 + 0x07, 0x20, 22, 8, 20,
22429 + 0x08, 0x20, 23, 8, 25,
22430 + 0x09, 0x22, 23, 8, 25,
22431 +};
22432 +
22433 +UCHAR RateSwitchTable11BGN2SForABand[] = {
22434 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22435 + 0x0b, 0x09, 0, 0, 0, // Initial used item after association
22436 + 0x00, 0x21, 0, 30,101, //50
22437 + 0x01, 0x21, 1, 20, 50,
22438 + 0x02, 0x21, 2, 20, 50,
22439 + 0x03, 0x21, 3, 15, 50,
22440 + 0x04, 0x21, 4, 15, 30,
22441 + 0x05, 0x21, 5, 15, 30,
22442 + 0x06, 0x20, 12, 15, 30,
22443 + 0x07, 0x20, 13, 8, 20,
22444 + 0x08, 0x20, 14, 8, 20,
22445 + 0x09, 0x20, 15, 8, 25,
22446 + 0x0a, 0x22, 15, 8, 25,
22447 +};
22448 +
22449 +UCHAR RateSwitchTable11BGN3SForABand[] = { // 3*3
22450 +// Item No. Mode Curr-MCS TrainUp TrainDown // Mode- Bit0: STBC, Bit1: Short GI, Bit4,5: Mode(0:CCK, 1:OFDM, 2:HT Mix, 3:HT GF)
22451 + 0x0c, 0x09, 0, 0, 0, // Initial used item after association
22452 + 0x00, 0x21, 0, 30,101, //50
22453 + 0x01, 0x21, 1, 20, 50,
22454 + 0x02, 0x21, 2, 20, 50,
22455 + 0x03, 0x21, 3, 15, 50,
22456 + 0x04, 0x21, 4, 15, 30,
22457 + 0x05, 0x21, 5, 15, 30,
22458 + 0x06, 0x21, 12, 15, 30,
22459 + 0x07, 0x20, 20, 15, 30,
22460 + 0x08, 0x20, 21, 8, 20,
22461 + 0x09, 0x20, 22, 8, 20,
22462 + 0x0a, 0x20, 23, 8, 25,
22463 + 0x0b, 0x22, 23, 8, 25,
22464 +};
22465 +#endif // DOT11_N_SUPPORT //
22466 +
22467 +PUCHAR ReasonString[] = {
22468 + /* 0 */ "Reserved",
22469 + /* 1 */ "Unspecified Reason",
22470 + /* 2 */ "Previous Auth no longer valid",
22471 + /* 3 */ "STA is leaving / has left",
22472 + /* 4 */ "DIS-ASSOC due to inactivity",
22473 + /* 5 */ "AP unable to hanle all associations",
22474 + /* 6 */ "class 2 error",
22475 + /* 7 */ "class 3 error",
22476 + /* 8 */ "STA is leaving / has left",
22477 + /* 9 */ "require auth before assoc/re-assoc",
22478 + /* 10 */ "Reserved",
22479 + /* 11 */ "Reserved",
22480 + /* 12 */ "Reserved",
22481 + /* 13 */ "invalid IE",
22482 + /* 14 */ "MIC error",
22483 + /* 15 */ "4-way handshake timeout",
22484 + /* 16 */ "2-way (group key) handshake timeout",
22485 + /* 17 */ "4-way handshake IE diff among AssosReq/Rsp/Beacon",
22486 + /* 18 */
22487 +};
22488 +
22489 +extern UCHAR OfdmRateToRxwiMCS[];
22490 +// since RT61 has better RX sensibility, we have to limit TX ACK rate not to exceed our normal data TX rate.
22491 +// otherwise the WLAN peer may not be able to receive the ACK thus downgrade its data TX rate
22492 +ULONG BasicRateMask[12] = {0xfffff001 /* 1-Mbps */, 0xfffff003 /* 2 Mbps */, 0xfffff007 /* 5.5 */, 0xfffff00f /* 11 */,
22493 + 0xfffff01f /* 6 */ , 0xfffff03f /* 9 */ , 0xfffff07f /* 12 */ , 0xfffff0ff /* 18 */,
22494 + 0xfffff1ff /* 24 */ , 0xfffff3ff /* 36 */ , 0xfffff7ff /* 48 */ , 0xffffffff /* 54 */};
22495 +
22496 +UCHAR MULTICAST_ADDR[MAC_ADDR_LEN] = {0x1, 0x00, 0x00, 0x00, 0x00, 0x00};
22497 +UCHAR BROADCAST_ADDR[MAC_ADDR_LEN] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff};
22498 +UCHAR ZERO_MAC_ADDR[MAC_ADDR_LEN] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
22499 +
22500 +// e.g. RssiSafeLevelForTxRate[RATE_36]" means if the current RSSI is greater than
22501 +// this value, then it's quaranteed capable of operating in 36 mbps TX rate in
22502 +// clean environment.
22503 +// TxRate: 1 2 5.5 11 6 9 12 18 24 36 48 54 72 100
22504 +CHAR RssiSafeLevelForTxRate[] ={ -92, -91, -90, -87, -88, -86, -85, -83, -81, -78, -72, -71, -40, -40 };
22505 +
22506 +UCHAR RateIdToMbps[] = { 1, 2, 5, 11, 6, 9, 12, 18, 24, 36, 48, 54, 72, 100};
22507 +USHORT RateIdTo500Kbps[] = { 2, 4, 11, 22, 12, 18, 24, 36, 48, 72, 96, 108, 144, 200};
22508 +
22509 +UCHAR SsidIe = IE_SSID;
22510 +UCHAR SupRateIe = IE_SUPP_RATES;
22511 +UCHAR ExtRateIe = IE_EXT_SUPP_RATES;
22512 +#ifdef DOT11_N_SUPPORT
22513 +UCHAR HtCapIe = IE_HT_CAP;
22514 +UCHAR AddHtInfoIe = IE_ADD_HT;
22515 +UCHAR NewExtChanIe = IE_SECONDARY_CH_OFFSET;
22516 +#ifdef DOT11N_DRAFT3
22517 +UCHAR ExtHtCapIe = IE_EXT_CAPABILITY;
22518 +#endif // DOT11N_DRAFT3 //
22519 +#endif // DOT11_N_SUPPORT //
22520 +UCHAR ErpIe = IE_ERP;
22521 +UCHAR DsIe = IE_DS_PARM;
22522 +UCHAR TimIe = IE_TIM;
22523 +UCHAR WpaIe = IE_WPA;
22524 +UCHAR Wpa2Ie = IE_WPA2;
22525 +UCHAR IbssIe = IE_IBSS_PARM;
22526 +UCHAR Ccx2Ie = IE_CCX_V2;
22527 +
22528 +extern UCHAR WPA_OUI[];
22529 +
22530 +UCHAR SES_OUI[] = {0x00, 0x90, 0x4c};
22531 +
22532 +UCHAR ZeroSsid[32] = {0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
22533 + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
22534 +
22535 +// Reset the RFIC setting to new series
22536 +RTMP_RF_REGS RF2850RegTable[] = {
22537 +// ch R1 R2 R3(TX0~4=0) R4
22538 + {1, 0x98402ecc, 0x984c0786, 0x9816b455, 0x9800510b},
22539 + {2, 0x98402ecc, 0x984c0786, 0x98168a55, 0x9800519f},
22540 + {3, 0x98402ecc, 0x984c078a, 0x98168a55, 0x9800518b},
22541 + {4, 0x98402ecc, 0x984c078a, 0x98168a55, 0x9800519f},
22542 + {5, 0x98402ecc, 0x984c078e, 0x98168a55, 0x9800518b},
22543 + {6, 0x98402ecc, 0x984c078e, 0x98168a55, 0x9800519f},
22544 + {7, 0x98402ecc, 0x984c0792, 0x98168a55, 0x9800518b},
22545 + {8, 0x98402ecc, 0x984c0792, 0x98168a55, 0x9800519f},
22546 + {9, 0x98402ecc, 0x984c0796, 0x98168a55, 0x9800518b},
22547 + {10, 0x98402ecc, 0x984c0796, 0x98168a55, 0x9800519f},
22548 + {11, 0x98402ecc, 0x984c079a, 0x98168a55, 0x9800518b},
22549 + {12, 0x98402ecc, 0x984c079a, 0x98168a55, 0x9800519f},
22550 + {13, 0x98402ecc, 0x984c079e, 0x98168a55, 0x9800518b},
22551 + {14, 0x98402ecc, 0x984c07a2, 0x98168a55, 0x98005193},
22552 +
22553 + // 802.11 UNI / HyperLan 2
22554 + {36, 0x98402ecc, 0x984c099a, 0x98158a55, 0x980ed1a3},
22555 + {38, 0x98402ecc, 0x984c099e, 0x98158a55, 0x980ed193},
22556 + {40, 0x98402ec8, 0x984c0682, 0x98158a55, 0x980ed183},
22557 + {44, 0x98402ec8, 0x984c0682, 0x98158a55, 0x980ed1a3},
22558 + {46, 0x98402ec8, 0x984c0686, 0x98158a55, 0x980ed18b},
22559 + {48, 0x98402ec8, 0x984c0686, 0x98158a55, 0x980ed19b},
22560 + {52, 0x98402ec8, 0x984c068a, 0x98158a55, 0x980ed193},
22561 + {54, 0x98402ec8, 0x984c068a, 0x98158a55, 0x980ed1a3},
22562 + {56, 0x98402ec8, 0x984c068e, 0x98158a55, 0x980ed18b},
22563 + {60, 0x98402ec8, 0x984c0692, 0x98158a55, 0x980ed183},
22564 + {62, 0x98402ec8, 0x984c0692, 0x98158a55, 0x980ed193},
22565 + {64, 0x98402ec8, 0x984c0692, 0x98158a55, 0x980ed1a3}, // Plugfest#4, Day4, change RFR3 left4th 9->5.
22566 +
22567 + // 802.11 HyperLan 2
22568 + {100, 0x98402ec8, 0x984c06b2, 0x98178a55, 0x980ed783},
22569 +
22570 + // 2008.04.30 modified
22571 + // The system team has AN to improve the EVM value
22572 + // for channel 102 to 108 for the RT2850/RT2750 dual band solution.
22573 + {102, 0x98402ec8, 0x985c06b2, 0x98578a55, 0x980ed793},
22574 + {104, 0x98402ec8, 0x985c06b2, 0x98578a55, 0x980ed1a3},
22575 + {108, 0x98402ecc, 0x985c0a32, 0x98578a55, 0x980ed193},
22576 +
22577 + {110, 0x98402ecc, 0x984c0a36, 0x98178a55, 0x980ed183},
22578 + {112, 0x98402ecc, 0x984c0a36, 0x98178a55, 0x980ed19b},
22579 + {116, 0x98402ecc, 0x984c0a3a, 0x98178a55, 0x980ed1a3},
22580 + {118, 0x98402ecc, 0x984c0a3e, 0x98178a55, 0x980ed193},
22581 + {120, 0x98402ec4, 0x984c0382, 0x98178a55, 0x980ed183},
22582 + {124, 0x98402ec4, 0x984c0382, 0x98178a55, 0x980ed193},
22583 + {126, 0x98402ec4, 0x984c0382, 0x98178a55, 0x980ed15b}, // 0x980ed1bb->0x980ed15b required by Rory 20070927
22584 + {128, 0x98402ec4, 0x984c0382, 0x98178a55, 0x980ed1a3},
22585 + {132, 0x98402ec4, 0x984c0386, 0x98178a55, 0x980ed18b},
22586 + {134, 0x98402ec4, 0x984c0386, 0x98178a55, 0x980ed193},
22587 + {136, 0x98402ec4, 0x984c0386, 0x98178a55, 0x980ed19b},
22588 + {140, 0x98402ec4, 0x984c038a, 0x98178a55, 0x980ed183},
22589 +
22590 + // 802.11 UNII
22591 + {149, 0x98402ec4, 0x984c038a, 0x98178a55, 0x980ed1a7},
22592 + {151, 0x98402ec4, 0x984c038e, 0x98178a55, 0x980ed187},
22593 + {153, 0x98402ec4, 0x984c038e, 0x98178a55, 0x980ed18f},
22594 + {157, 0x98402ec4, 0x984c038e, 0x98178a55, 0x980ed19f},
22595 + {159, 0x98402ec4, 0x984c038e, 0x98178a55, 0x980ed1a7},
22596 + {161, 0x98402ec4, 0x984c0392, 0x98178a55, 0x980ed187},
22597 + {165, 0x98402ec4, 0x984c0392, 0x98178a55, 0x980ed197},
22598 +
22599 + // Japan
22600 + {184, 0x95002ccc, 0x9500491e, 0x9509be55, 0x950c0a0b},
22601 + {188, 0x95002ccc, 0x95004922, 0x9509be55, 0x950c0a13},
22602 + {192, 0x95002ccc, 0x95004926, 0x9509be55, 0x950c0a1b},
22603 + {196, 0x95002ccc, 0x9500492a, 0x9509be55, 0x950c0a23},
22604 + {208, 0x95002ccc, 0x9500493a, 0x9509be55, 0x950c0a13},
22605 + {212, 0x95002ccc, 0x9500493e, 0x9509be55, 0x950c0a1b},
22606 + {216, 0x95002ccc, 0x95004982, 0x9509be55, 0x950c0a23},
22607 +
22608 + // still lack of MMAC(Japan) ch 34,38,42,46
22609 +};
22610 +UCHAR NUM_OF_2850_CHNL = (sizeof(RF2850RegTable) / sizeof(RTMP_RF_REGS));
22611 +
22612 +FREQUENCY_ITEM FreqItems3020[] =
22613 +{
22614 + /**************************************************/
22615 + // ISM : 2.4 to 2.483 GHz //
22616 + /**************************************************/
22617 + // 11g
22618 + /**************************************************/
22619 + //-CH---N-------R---K-----------
22620 + {1, 241, 2, 2},
22621 + {2, 241, 2, 7},
22622 + {3, 242, 2, 2},
22623 + {4, 242, 2, 7},
22624 + {5, 243, 2, 2},
22625 + {6, 243, 2, 7},
22626 + {7, 244, 2, 2},
22627 + {8, 244, 2, 7},
22628 + {9, 245, 2, 2},
22629 + {10, 245, 2, 7},
22630 + {11, 246, 2, 2},
22631 + {12, 246, 2, 7},
22632 + {13, 247, 2, 2},
22633 + {14, 248, 2, 4},
22634 +};
22635 +#define NUM_OF_3020_CHNL (sizeof(FreqItems3020) / sizeof(FREQUENCY_ITEM))
22636 +
22637 +/*
22638 + ==========================================================================
22639 + Description:
22640 + initialize the MLME task and its data structure (queue, spinlock,
22641 + timer, state machines).
22642 +
22643 + IRQL = PASSIVE_LEVEL
22644 +
22645 + Return:
22646 + always return NDIS_STATUS_SUCCESS
22647 +
22648 + ==========================================================================
22649 +*/
22650 +NDIS_STATUS MlmeInit(
22651 + IN PRTMP_ADAPTER pAd)
22652 +{
22653 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
22654 +
22655 + DBGPRINT(RT_DEBUG_TRACE, ("--> MLME Initialize\n"));
22656 +
22657 + do
22658 + {
22659 + Status = MlmeQueueInit(&pAd->Mlme.Queue);
22660 + if(Status != NDIS_STATUS_SUCCESS)
22661 + break;
22662 +
22663 + pAd->Mlme.bRunning = FALSE;
22664 + NdisAllocateSpinLock(&pAd->Mlme.TaskLock);
22665 +
22666 +#ifdef CONFIG_STA_SUPPORT
22667 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
22668 + {
22669 + BssTableInit(&pAd->ScanTab);
22670 +
22671 + // init STA state machines
22672 + AssocStateMachineInit(pAd, &pAd->Mlme.AssocMachine, pAd->Mlme.AssocFunc);
22673 + AuthStateMachineInit(pAd, &pAd->Mlme.AuthMachine, pAd->Mlme.AuthFunc);
22674 + AuthRspStateMachineInit(pAd, &pAd->Mlme.AuthRspMachine, pAd->Mlme.AuthRspFunc);
22675 + SyncStateMachineInit(pAd, &pAd->Mlme.SyncMachine, pAd->Mlme.SyncFunc);
22676 + WpaPskStateMachineInit(pAd, &pAd->Mlme.WpaPskMachine, pAd->Mlme.WpaPskFunc);
22677 + AironetStateMachineInit(pAd, &pAd->Mlme.AironetMachine, pAd->Mlme.AironetFunc);
22678 +
22679 +#ifdef QOS_DLS_SUPPORT
22680 + DlsStateMachineInit(pAd, &pAd->Mlme.DlsMachine, pAd->Mlme.DlsFunc);
22681 +#endif // QOS_DLS_SUPPORT //
22682 +
22683 +
22684 + // Since we are using switch/case to implement it, the init is different from the above
22685 + // state machine init
22686 + MlmeCntlInit(pAd, &pAd->Mlme.CntlMachine, NULL);
22687 + }
22688 +#endif // CONFIG_STA_SUPPORT //
22689 +
22690 +
22691 +
22692 + ActionStateMachineInit(pAd, &pAd->Mlme.ActMachine, pAd->Mlme.ActFunc);
22693 +
22694 + // Init mlme periodic timer
22695 + RTMPInitTimer(pAd, &pAd->Mlme.PeriodicTimer, GET_TIMER_FUNCTION(MlmePeriodicExec), pAd, TRUE);
22696 +
22697 + // Set mlme periodic timer
22698 + RTMPSetTimer(&pAd->Mlme.PeriodicTimer, MLME_TASK_EXEC_INTV);
22699 +
22700 + // software-based RX Antenna diversity
22701 + RTMPInitTimer(pAd, &pAd->Mlme.RxAntEvalTimer, GET_TIMER_FUNCTION(AsicRxAntEvalTimeout), pAd, FALSE);
22702 +
22703 +
22704 +#ifdef CONFIG_STA_SUPPORT
22705 +#ifdef RT2860
22706 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
22707 + {
22708 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
22709 + {
22710 + // only PCIe cards need these two timers
22711 + RTMPInitTimer(pAd, &pAd->Mlme.PsPollTimer, GET_TIMER_FUNCTION(PsPollWakeExec), pAd, FALSE);
22712 + RTMPInitTimer(pAd, &pAd->Mlme.RadioOnOffTimer, GET_TIMER_FUNCTION(RadioOnExec), pAd, FALSE);
22713 + }
22714 + }
22715 +#endif // RT2860 //
22716 +#endif // CONFIG_STA_SUPPORT //
22717 +
22718 + } while (FALSE);
22719 +
22720 + DBGPRINT(RT_DEBUG_TRACE, ("<-- MLME Initialize\n"));
22721 +
22722 + return Status;
22723 +}
22724 +
22725 +/*
22726 + ==========================================================================
22727 + Description:
22728 + main loop of the MLME
22729 + Pre:
22730 + Mlme has to be initialized, and there are something inside the queue
22731 + Note:
22732 + This function is invoked from MPSetInformation and MPReceive;
22733 + This task guarantee only one MlmeHandler will run.
22734 +
22735 + IRQL = DISPATCH_LEVEL
22736 +
22737 + ==========================================================================
22738 + */
22739 +VOID MlmeHandler(
22740 + IN PRTMP_ADAPTER pAd)
22741 +{
22742 + MLME_QUEUE_ELEM *Elem = NULL;
22743 +#ifdef APCLI_SUPPORT
22744 + SHORT apcliIfIndex;
22745 +#endif
22746 +
22747 + // Only accept MLME and Frame from peer side, no other (control/data) frame should
22748 + // get into this state machine
22749 +
22750 + NdisAcquireSpinLock(&pAd->Mlme.TaskLock);
22751 + if(pAd->Mlme.bRunning)
22752 + {
22753 + NdisReleaseSpinLock(&pAd->Mlme.TaskLock);
22754 + return;
22755 + }
22756 + else
22757 + {
22758 + pAd->Mlme.bRunning = TRUE;
22759 + }
22760 + NdisReleaseSpinLock(&pAd->Mlme.TaskLock);
22761 +
22762 + while (!MlmeQueueEmpty(&pAd->Mlme.Queue))
22763 + {
22764 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_MLME_RESET_IN_PROGRESS) ||
22765 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS) ||
22766 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST))
22767 + {
22768 + DBGPRINT(RT_DEBUG_TRACE, ("Device Halted or Removed or MlmeRest, exit MlmeHandler! (queue num = %ld)\n", pAd->Mlme.Queue.Num));
22769 + break;
22770 + }
22771 +
22772 +#ifdef RALINK_ATE
22773 + if(ATE_ON(pAd))
22774 + {
22775 + DBGPRINT(RT_DEBUG_TRACE, ("The driver is in ATE mode now in MlmeHandler\n"));
22776 + break;
22777 + }
22778 +#endif // RALINK_ATE //
22779 +
22780 + //From message type, determine which state machine I should drive
22781 + if (MlmeDequeue(&pAd->Mlme.Queue, &Elem))
22782 + {
22783 +
22784 + // if dequeue success
22785 + switch (Elem->Machine)
22786 + {
22787 + // STA state machines
22788 +#ifdef CONFIG_STA_SUPPORT
22789 + case ASSOC_STATE_MACHINE:
22790 + StateMachinePerformAction(pAd, &pAd->Mlme.AssocMachine, Elem);
22791 + break;
22792 + case AUTH_STATE_MACHINE:
22793 + StateMachinePerformAction(pAd, &pAd->Mlme.AuthMachine, Elem);
22794 + break;
22795 + case AUTH_RSP_STATE_MACHINE:
22796 + StateMachinePerformAction(pAd, &pAd->Mlme.AuthRspMachine, Elem);
22797 + break;
22798 + case SYNC_STATE_MACHINE:
22799 + StateMachinePerformAction(pAd, &pAd->Mlme.SyncMachine, Elem);
22800 + break;
22801 + case MLME_CNTL_STATE_MACHINE:
22802 + MlmeCntlMachinePerformAction(pAd, &pAd->Mlme.CntlMachine, Elem);
22803 + break;
22804 + case WPA_PSK_STATE_MACHINE:
22805 + StateMachinePerformAction(pAd, &pAd->Mlme.WpaPskMachine, Elem);
22806 + break;
22807 +#ifdef LEAP_SUPPORT
22808 + case LEAP_STATE_MACHINE:
22809 + LeapMachinePerformAction(pAd, &pAd->Mlme.LeapMachine, Elem);
22810 + break;
22811 +#endif
22812 + case AIRONET_STATE_MACHINE:
22813 + StateMachinePerformAction(pAd, &pAd->Mlme.AironetMachine, Elem);
22814 + break;
22815 +
22816 +#ifdef QOS_DLS_SUPPORT
22817 + case DLS_STATE_MACHINE:
22818 + StateMachinePerformAction(pAd, &pAd->Mlme.DlsMachine, Elem);
22819 + break;
22820 +#endif // QOS_DLS_SUPPORT //
22821 +#endif // CONFIG_STA_SUPPORT //
22822 +
22823 + case ACTION_STATE_MACHINE:
22824 + StateMachinePerformAction(pAd, &pAd->Mlme.ActMachine, Elem);
22825 + break;
22826 +
22827 +
22828 +
22829 +
22830 + default:
22831 + DBGPRINT(RT_DEBUG_TRACE, ("ERROR: Illegal machine %ld in MlmeHandler()\n", Elem->Machine));
22832 + break;
22833 + } // end of switch
22834 +
22835 + // free MLME element
22836 + Elem->Occupied = FALSE;
22837 + Elem->MsgLen = 0;
22838 +
22839 + }
22840 + else {
22841 + DBGPRINT_ERR(("MlmeHandler: MlmeQueue empty\n"));
22842 + }
22843 + }
22844 +
22845 + NdisAcquireSpinLock(&pAd->Mlme.TaskLock);
22846 + pAd->Mlme.bRunning = FALSE;
22847 + NdisReleaseSpinLock(&pAd->Mlme.TaskLock);
22848 +}
22849 +
22850 +/*
22851 + ==========================================================================
22852 + Description:
22853 + Destructor of MLME (Destroy queue, state machine, spin lock and timer)
22854 + Parameters:
22855 + Adapter - NIC Adapter pointer
22856 + Post:
22857 + The MLME task will no longer work properly
22858 +
22859 + IRQL = PASSIVE_LEVEL
22860 +
22861 + ==========================================================================
22862 + */
22863 +VOID MlmeHalt(
22864 + IN PRTMP_ADAPTER pAd)
22865 +{
22866 + BOOLEAN Cancelled;
22867 +
22868 + DBGPRINT(RT_DEBUG_TRACE, ("==> MlmeHalt\n"));
22869 +
22870 + if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST))
22871 + {
22872 + // disable BEACON generation and other BEACON related hardware timers
22873 + AsicDisableSync(pAd);
22874 + }
22875 +
22876 +#ifdef CONFIG_STA_SUPPORT
22877 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
22878 + {
22879 +#ifdef QOS_DLS_SUPPORT
22880 + UCHAR i;
22881 +#endif // QOS_DLS_SUPPORT //
22882 + // Cancel pending timers
22883 + RTMPCancelTimer(&pAd->MlmeAux.AssocTimer, &Cancelled);
22884 + RTMPCancelTimer(&pAd->MlmeAux.ReassocTimer, &Cancelled);
22885 + RTMPCancelTimer(&pAd->MlmeAux.DisassocTimer, &Cancelled);
22886 + RTMPCancelTimer(&pAd->MlmeAux.AuthTimer, &Cancelled);
22887 + RTMPCancelTimer(&pAd->MlmeAux.BeaconTimer, &Cancelled);
22888 + RTMPCancelTimer(&pAd->MlmeAux.ScanTimer, &Cancelled);
22889 +#ifdef RT2860
22890 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
22891 + {
22892 + RTMPCancelTimer(&pAd->Mlme.PsPollTimer, &Cancelled);
22893 + RTMPCancelTimer(&pAd->Mlme.RadioOnOffTimer, &Cancelled);
22894 + }
22895 +#endif // RT2860 //
22896 +
22897 +#ifdef QOS_DLS_SUPPORT
22898 + for (i=0; i<MAX_NUM_OF_DLS_ENTRY; i++)
22899 + {
22900 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &Cancelled);
22901 + }
22902 +#endif // QOS_DLS_SUPPORT //
22903 + }
22904 +#endif // CONFIG_STA_SUPPORT //
22905 +
22906 + RTMPCancelTimer(&pAd->Mlme.PeriodicTimer, &Cancelled);
22907 + RTMPCancelTimer(&pAd->Mlme.RxAntEvalTimer, &Cancelled);
22908 +
22909 +
22910 +
22911 + if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST))
22912 + {
22913 + // Set LED
22914 + RTMPSetLED(pAd, LED_HALT);
22915 + RTMPSetSignalLED(pAd, -100); // Force signal strength Led to be turned off, firmware is not done it.
22916 + }
22917 +
22918 + RTMPusecDelay(5000); // 5 msec to gurantee Ant Diversity timer canceled
22919 +
22920 + MlmeQueueDestroy(&pAd->Mlme.Queue);
22921 + NdisFreeSpinLock(&pAd->Mlme.TaskLock);
22922 +
22923 + DBGPRINT(RT_DEBUG_TRACE, ("<== MlmeHalt\n"));
22924 +}
22925 +
22926 +VOID MlmeResetRalinkCounters(
22927 + IN PRTMP_ADAPTER pAd)
22928 +{
22929 + pAd->RalinkCounters.LastOneSecRxOkDataCnt = pAd->RalinkCounters.OneSecRxOkDataCnt;
22930 + // clear all OneSecxxx counters.
22931 + pAd->RalinkCounters.OneSecBeaconSentCnt = 0;
22932 + pAd->RalinkCounters.OneSecFalseCCACnt = 0;
22933 + pAd->RalinkCounters.OneSecRxFcsErrCnt = 0;
22934 + pAd->RalinkCounters.OneSecRxOkCnt = 0;
22935 + pAd->RalinkCounters.OneSecTxFailCount = 0;
22936 + pAd->RalinkCounters.OneSecTxNoRetryOkCount = 0;
22937 + pAd->RalinkCounters.OneSecTxRetryOkCount = 0;
22938 + pAd->RalinkCounters.OneSecRxOkDataCnt = 0;
22939 +
22940 + // TODO: for debug only. to be removed
22941 + pAd->RalinkCounters.OneSecOsTxCount[QID_AC_BE] = 0;
22942 + pAd->RalinkCounters.OneSecOsTxCount[QID_AC_BK] = 0;
22943 + pAd->RalinkCounters.OneSecOsTxCount[QID_AC_VI] = 0;
22944 + pAd->RalinkCounters.OneSecOsTxCount[QID_AC_VO] = 0;
22945 + pAd->RalinkCounters.OneSecDmaDoneCount[QID_AC_BE] = 0;
22946 + pAd->RalinkCounters.OneSecDmaDoneCount[QID_AC_BK] = 0;
22947 + pAd->RalinkCounters.OneSecDmaDoneCount[QID_AC_VI] = 0;
22948 + pAd->RalinkCounters.OneSecDmaDoneCount[QID_AC_VO] = 0;
22949 + pAd->RalinkCounters.OneSecTxDoneCount = 0;
22950 + pAd->RalinkCounters.OneSecRxCount = 0;
22951 + pAd->RalinkCounters.OneSecTxAggregationCount = 0;
22952 + pAd->RalinkCounters.OneSecRxAggregationCount = 0;
22953 +
22954 + return;
22955 +}
22956 +
22957 +unsigned long rx_AMSDU;
22958 +unsigned long rx_Total;
22959 +
22960 +/*
22961 + ==========================================================================
22962 + Description:
22963 + This routine is executed periodically to -
22964 + 1. Decide if it's a right time to turn on PwrMgmt bit of all
22965 + outgoiing frames
22966 + 2. Calculate ChannelQuality based on statistics of the last
22967 + period, so that TX rate won't toggling very frequently between a
22968 + successful TX and a failed TX.
22969 + 3. If the calculated ChannelQuality indicated current connection not
22970 + healthy, then a ROAMing attempt is tried here.
22971 +
22972 + IRQL = DISPATCH_LEVEL
22973 +
22974 + ==========================================================================
22975 + */
22976 +#define ADHOC_BEACON_LOST_TIME (8*OS_HZ) // 8 sec
22977 +VOID MlmePeriodicExec(
22978 + IN PVOID SystemSpecific1,
22979 + IN PVOID FunctionContext,
22980 + IN PVOID SystemSpecific2,
22981 + IN PVOID SystemSpecific3)
22982 +{
22983 + ULONG TxTotalCnt;
22984 + PRTMP_ADAPTER pAd = (RTMP_ADAPTER *)FunctionContext;
22985 +
22986 +#ifdef CONFIG_STA_SUPPORT
22987 +#ifdef RT2860
22988 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
22989 + {
22990 + // If Hardware controlled Radio enabled, we have to check GPIO pin2 every 2 second.
22991 + // Move code to here, because following code will return when radio is off
22992 + if ((pAd->Mlme.PeriodicRound % (MLME_TASK_EXEC_MULTIPLE * 2) == 0) && (pAd->StaCfg.bHardwareRadio == TRUE) &&
22993 + (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST)) &&
22994 + (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS)) &&
22995 + (pAd->bPCIclkOff == FALSE))
22996 + {
22997 + UINT32 data = 0;
22998 +
22999 + // Read GPIO pin2 as Hardware controlled radio state
23000 + RTMP_IO_READ32(pAd, GPIO_CTRL_CFG, &data);
23001 + if (data & 0x04)
23002 + {
23003 + pAd->StaCfg.bHwRadio = TRUE;
23004 + }
23005 + else
23006 + {
23007 + pAd->StaCfg.bHwRadio = FALSE;
23008 + }
23009 + if (pAd->StaCfg.bRadio != (pAd->StaCfg.bHwRadio && pAd->StaCfg.bSwRadio))
23010 + {
23011 + pAd->StaCfg.bRadio = (pAd->StaCfg.bHwRadio && pAd->StaCfg.bSwRadio);
23012 + if (pAd->StaCfg.bRadio == TRUE)
23013 + {
23014 + MlmeRadioOn(pAd);
23015 + // Update extra information
23016 + pAd->ExtraInfo = EXTRA_INFO_CLEAR;
23017 + }
23018 + else
23019 + {
23020 + MlmeRadioOff(pAd);
23021 + // Update extra information
23022 + pAd->ExtraInfo = HW_RADIO_OFF;
23023 + }
23024 + }
23025 + }
23026 + }
23027 +#endif // RT2860 //
23028 +#endif // CONFIG_STA_SUPPORT //
23029 +
23030 + // Do nothing if the driver is starting halt state.
23031 + // This might happen when timer already been fired before cancel timer with mlmehalt
23032 + if ((RTMP_TEST_FLAG(pAd, (fRTMP_ADAPTER_HALT_IN_PROGRESS |
23033 + fRTMP_ADAPTER_RADIO_OFF |
23034 + fRTMP_ADAPTER_RADIO_MEASUREMENT |
23035 + fRTMP_ADAPTER_RESET_IN_PROGRESS))))
23036 + return;
23037 +
23038 + RT28XX_MLME_PRE_SANITY_CHECK(pAd);
23039 +
23040 +#ifdef RALINK_ATE
23041 + /* Do not show RSSI until "Normal 1 second Mlme PeriodicExec". */
23042 + if (ATE_ON(pAd))
23043 + {
23044 + if (pAd->Mlme.PeriodicRound % MLME_TASK_EXEC_MULTIPLE != (MLME_TASK_EXEC_MULTIPLE - 1))
23045 + {
23046 + pAd->Mlme.PeriodicRound ++;
23047 + return;
23048 + }
23049 + }
23050 +#endif // RALINK_ATE //
23051 +
23052 +#ifdef CONFIG_STA_SUPPORT
23053 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
23054 + {
23055 + // Do nothing if monitor mode is on
23056 + if (MONITOR_ON(pAd))
23057 + return;
23058 +
23059 + if (pAd->Mlme.PeriodicRound & 0x1)
23060 + {
23061 + // This is the fix for wifi 11n extension channel overlapping test case. for 2860D
23062 + if (((pAd->MACVersion & 0xffff) == 0x0101) &&
23063 + (STA_TGN_WIFI_ON(pAd)) &&
23064 + (pAd->CommonCfg.IOTestParm.bToggle == FALSE))
23065 +
23066 + {
23067 + RTMP_IO_WRITE32(pAd, TXOP_CTRL_CFG, 0x24Bf);
23068 + pAd->CommonCfg.IOTestParm.bToggle = TRUE;
23069 + }
23070 + else if ((STA_TGN_WIFI_ON(pAd)) &&
23071 + ((pAd->MACVersion & 0xffff) == 0x0101))
23072 + {
23073 + RTMP_IO_WRITE32(pAd, TXOP_CTRL_CFG, 0x243f);
23074 + pAd->CommonCfg.IOTestParm.bToggle = FALSE;
23075 + }
23076 + }
23077 + }
23078 +#endif // CONFIG_STA_SUPPORT //
23079 +
23080 + pAd->bUpdateBcnCntDone = FALSE;
23081 +
23082 +// RECBATimerTimeout(SystemSpecific1,FunctionContext,SystemSpecific2,SystemSpecific3);
23083 + pAd->Mlme.PeriodicRound ++;
23084 +
23085 + // execute every 500ms
23086 + if ((pAd->Mlme.PeriodicRound % 5 == 0) && RTMPAutoRateSwitchCheck(pAd)/*(OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_TX_RATE_SWITCH_ENABLED))*/)
23087 + {
23088 +#ifdef CONFIG_STA_SUPPORT
23089 + // perform dynamic tx rate switching based on past TX history
23090 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
23091 + {
23092 + if ((OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED)
23093 + )
23094 + && (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE)))
23095 + MlmeDynamicTxRateSwitching(pAd);
23096 + }
23097 +#endif // CONFIG_STA_SUPPORT //
23098 + }
23099 +
23100 + // Normal 1 second Mlme PeriodicExec.
23101 + if (pAd->Mlme.PeriodicRound %MLME_TASK_EXEC_MULTIPLE == 0)
23102 + {
23103 + pAd->Mlme.OneSecPeriodicRound ++;
23104 +
23105 +#ifdef RALINK_ATE
23106 + if (ATE_ON(pAd))
23107 + {
23108 + /* request from Baron : move this routine from later to here */
23109 + /* for showing Rx error count in ATE RXFRAME */
23110 + NICUpdateRawCounters(pAd);
23111 + if (pAd->ate.bRxFer == 1)
23112 + {
23113 + pAd->ate.RxTotalCnt += pAd->ate.RxCntPerSec;
23114 + ate_print(KERN_EMERG "MlmePeriodicExec: Rx packet cnt = %d/%d\n", pAd->ate.RxCntPerSec, pAd->ate.RxTotalCnt);
23115 + pAd->ate.RxCntPerSec = 0;
23116 +
23117 + if (pAd->ate.RxAntennaSel == 0)
23118 + ate_print(KERN_EMERG "MlmePeriodicExec: Rx AvgRssi0=%d, AvgRssi1=%d, AvgRssi2=%d\n\n",
23119 + pAd->ate.AvgRssi0, pAd->ate.AvgRssi1, pAd->ate.AvgRssi2);
23120 + else
23121 + ate_print(KERN_EMERG "MlmePeriodicExec: Rx AvgRssi=%d\n\n", pAd->ate.AvgRssi0);
23122 + }
23123 + MlmeResetRalinkCounters(pAd);
23124 + return;
23125 + }
23126 +#endif // RALINK_ATE //
23127 +
23128 +
23129 + if (rx_Total)
23130 + {
23131 +
23132 + // reset counters
23133 + rx_AMSDU = 0;
23134 + rx_Total = 0;
23135 + }
23136 +
23137 + // Media status changed, report to NDIS
23138 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_MEDIA_STATE_CHANGE))
23139 + {
23140 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_MEDIA_STATE_CHANGE);
23141 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
23142 + {
23143 + pAd->IndicateMediaState = NdisMediaStateConnected;
23144 + RTMP_IndicateMediaState(pAd);
23145 +
23146 + }
23147 + else
23148 + {
23149 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
23150 + RTMP_IndicateMediaState(pAd);
23151 + }
23152 + }
23153 +
23154 + NdisGetSystemUpTime(&pAd->Mlme.Now32);
23155 +
23156 + // add the most up-to-date h/w raw counters into software variable, so that
23157 + // the dynamic tuning mechanism below are based on most up-to-date information
23158 + NICUpdateRawCounters(pAd);
23159 +
23160 +
23161 +#ifdef DOT11_N_SUPPORT
23162 + // Need statistics after read counter. So put after NICUpdateRawCounters
23163 + ORIBATimerTimeout(pAd);
23164 +#endif // DOT11_N_SUPPORT //
23165 +
23166 +
23167 + // The time period for checking antenna is according to traffic
23168 + if (pAd->Mlme.bEnableAutoAntennaCheck)
23169 + {
23170 + TxTotalCnt = pAd->RalinkCounters.OneSecTxNoRetryOkCount +
23171 + pAd->RalinkCounters.OneSecTxRetryOkCount +
23172 + pAd->RalinkCounters.OneSecTxFailCount;
23173 +
23174 + if (TxTotalCnt > 50)
23175 + {
23176 + if (pAd->Mlme.OneSecPeriodicRound % 10 == 0)
23177 + {
23178 + AsicEvaluateRxAnt(pAd);
23179 + }
23180 + }
23181 + else
23182 + {
23183 + if (pAd->Mlme.OneSecPeriodicRound % 3 == 0)
23184 + {
23185 + AsicEvaluateRxAnt(pAd);
23186 + }
23187 + }
23188 + }
23189 +
23190 +#ifdef CONFIG_STA_SUPPORT
23191 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
23192 + STAMlmePeriodicExec(pAd);
23193 +#endif // CONFIG_STA_SUPPORT //
23194 +
23195 + MlmeResetRalinkCounters(pAd);
23196 +
23197 +#ifdef CONFIG_STA_SUPPORT
23198 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
23199 + {
23200 +#ifdef RT2860
23201 + if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST) && (pAd->bPCIclkOff == FALSE))
23202 +#endif // RT2860 //
23203 + {
23204 + // When Adhoc beacon is enabled and RTS/CTS is enabled, there is a chance that hardware MAC FSM will run into a deadlock
23205 + // and sending CTS-to-self over and over.
23206 + // Software Patch Solution:
23207 + // 1. Polling debug state register 0x10F4 every one second.
23208 + // 2. If in 0x10F4 the ((bit29==1) && (bit7==1)) OR ((bit29==1) && (bit5==1)), it means the deadlock has occurred.
23209 + // 3. If the deadlock occurred, reset MAC/BBP by setting 0x1004 to 0x0001 for a while then setting it back to 0x000C again.
23210 +
23211 + UINT32 MacReg = 0;
23212 +
23213 + RTMP_IO_READ32(pAd, 0x10F4, &MacReg);
23214 + if (((MacReg & 0x20000000) && (MacReg & 0x80)) || ((MacReg & 0x20000000) && (MacReg & 0x20)))
23215 + {
23216 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x1);
23217 + RTMPusecDelay(1);
23218 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0xC);
23219 +
23220 + DBGPRINT(RT_DEBUG_WARN,("Warning, MAC specific condition occurs \n"));
23221 + }
23222 + }
23223 + }
23224 +#endif // CONFIG_STA_SUPPORT //
23225 +
23226 + RT28XX_MLME_HANDLER(pAd);
23227 + }
23228 +
23229 +
23230 + pAd->bUpdateBcnCntDone = FALSE;
23231 +}
23232 +
23233 +#ifdef CONFIG_STA_SUPPORT
23234 +VOID STAMlmePeriodicExec(
23235 + PRTMP_ADAPTER pAd)
23236 +{
23237 + ULONG TxTotalCnt;
23238 +
23239 +//
23240 +// We return here in ATE mode, because the statistics
23241 +// that ATE needs are not collected via this routine.
23242 +//
23243 +#ifdef RALINK_ATE
23244 + // It is supposed that we will never reach here in ATE mode.
23245 + ASSERT(!(ATE_ON(pAd)));
23246 + if (ATE_ON(pAd))
23247 + return;
23248 +#endif // RALINK_ATE //
23249 +
23250 +#ifdef WPA_SUPPLICANT_SUPPORT
23251 + if (pAd->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_DISABLE)
23252 +#endif // WPA_SUPPLICANT_SUPPORT //
23253 + {
23254 + // WPA MIC error should block association attempt for 60 seconds
23255 + if (pAd->StaCfg.bBlockAssoc && (pAd->StaCfg.LastMicErrorTime + (60 * OS_HZ) < pAd->Mlme.Now32))
23256 + pAd->StaCfg.bBlockAssoc = FALSE;
23257 + }
23258 +
23259 + if ((pAd->PreMediaState != pAd->IndicateMediaState) && (pAd->CommonCfg.bWirelessEvent))
23260 + {
23261 + if (pAd->IndicateMediaState == NdisMediaStateConnected)
23262 + {
23263 + RTMPSendWirelessEvent(pAd, IW_STA_LINKUP_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
23264 + }
23265 + pAd->PreMediaState = pAd->IndicateMediaState;
23266 + }
23267 +
23268 +
23269 +
23270 +
23271 + AsicStaBbpTuning(pAd);
23272 +
23273 + TxTotalCnt = pAd->RalinkCounters.OneSecTxNoRetryOkCount +
23274 + pAd->RalinkCounters.OneSecTxRetryOkCount +
23275 + pAd->RalinkCounters.OneSecTxFailCount;
23276 +
23277 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
23278 + {
23279 + // update channel quality for Roaming and UI LinkQuality display
23280 + MlmeCalculateChannelQuality(pAd, pAd->Mlme.Now32);
23281 + }
23282 +
23283 + // must be AFTER MlmeDynamicTxRateSwitching() because it needs to know if
23284 + // Radio is currently in noisy environment
23285 + if (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
23286 + AsicAdjustTxPower(pAd);
23287 +
23288 + if (INFRA_ON(pAd))
23289 + {
23290 +#ifdef QOS_DLS_SUPPORT
23291 + // Check DLS time out, then tear down those session
23292 + RTMPCheckDLSTimeOut(pAd);
23293 +#endif // QOS_DLS_SUPPORT //
23294 +
23295 + // Is PSM bit consistent with user power management policy?
23296 + // This is the only place that will set PSM bit ON.
23297 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
23298 + MlmeCheckPsmChange(pAd, pAd->Mlme.Now32);
23299 +
23300 + pAd->RalinkCounters.LastOneSecTotalTxCount = TxTotalCnt;
23301 +
23302 + if ((pAd->StaCfg.LastBeaconRxTime + 1*OS_HZ < pAd->Mlme.Now32) &&
23303 + (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS)) &&
23304 + ((TxTotalCnt + pAd->RalinkCounters.OneSecRxOkCnt < 600)))
23305 + {
23306 + RTMPSetAGCInitValue(pAd, BW_20);
23307 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - No BEACON. restore R66 to the low bound(%d) \n", (0x2E + GET_LNA_GAIN(pAd))));
23308 + }
23309 +
23310 + {
23311 + if (pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable)
23312 + {
23313 + // When APSD is enabled, the period changes as 20 sec
23314 + if ((pAd->Mlme.OneSecPeriodicRound % 20) == 8)
23315 + RTMPSendNullFrame(pAd, pAd->CommonCfg.TxRate, TRUE);
23316 + }
23317 + else
23318 + {
23319 + // Send out a NULL frame every 10 sec to inform AP that STA is still alive (Avoid being age out)
23320 + if ((pAd->Mlme.OneSecPeriodicRound % 10) == 8)
23321 + {
23322 + if (pAd->CommonCfg.bWmmCapable)
23323 + RTMPSendNullFrame(pAd, pAd->CommonCfg.TxRate, TRUE);
23324 + else
23325 + RTMPSendNullFrame(pAd, pAd->CommonCfg.TxRate, FALSE);
23326 + }
23327 + }
23328 + }
23329 +
23330 + if (CQI_IS_DEAD(pAd->Mlme.ChannelQuality))
23331 + {
23332 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - No BEACON. Dead CQI. Auto Recovery attempt #%ld\n", pAd->RalinkCounters.BadCQIAutoRecoveryCount));
23333 + pAd->StaCfg.CCXAdjacentAPReportFlag = TRUE;
23334 + pAd->StaCfg.CCXAdjacentAPLinkDownTime = pAd->StaCfg.LastBeaconRxTime;
23335 +
23336 + // Lost AP, send disconnect & link down event
23337 + LinkDown(pAd, FALSE);
23338 +
23339 +#ifdef WPA_SUPPLICANT_SUPPORT
23340 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
23341 + if (pAd->StaCfg.WpaSupplicantUP)
23342 + {
23343 + union iwreq_data wrqu;
23344 + //send disassociate event to wpa_supplicant
23345 + memset(&wrqu, 0, sizeof(wrqu));
23346 + wrqu.data.flags = RT_DISASSOC_EVENT_FLAG;
23347 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
23348 + }
23349 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
23350 +#endif // WPA_SUPPLICANT_SUPPORT //
23351 +
23352 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
23353 + {
23354 + union iwreq_data wrqu;
23355 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
23356 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
23357 + }
23358 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
23359 +
23360 + MlmeAutoReconnectLastSSID(pAd);
23361 + }
23362 + else if (CQI_IS_BAD(pAd->Mlme.ChannelQuality))
23363 + {
23364 + pAd->RalinkCounters.BadCQIAutoRecoveryCount ++;
23365 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - Bad CQI. Auto Recovery attempt #%ld\n", pAd->RalinkCounters.BadCQIAutoRecoveryCount));
23366 + MlmeAutoReconnectLastSSID(pAd);
23367 + }
23368 +
23369 + // Add auto seamless roaming
23370 + if (pAd->StaCfg.bFastRoaming)
23371 + {
23372 + SHORT dBmToRoam = (SHORT)pAd->StaCfg.dBmToRoam;
23373 +
23374 + DBGPRINT(RT_DEBUG_TRACE, ("Rssi=%d, dBmToRoam=%d\n", RTMPMaxRssi(pAd, pAd->StaCfg.RssiSample.LastRssi0, pAd->StaCfg.RssiSample.LastRssi1, pAd->StaCfg.RssiSample.LastRssi2), (CHAR)dBmToRoam));
23375 +
23376 + if (RTMPMaxRssi(pAd, pAd->StaCfg.RssiSample.LastRssi0, pAd->StaCfg.RssiSample.LastRssi1, pAd->StaCfg.RssiSample.LastRssi2) <= (CHAR)dBmToRoam)
23377 + {
23378 + MlmeCheckForFastRoaming(pAd, pAd->Mlme.Now32);
23379 + }
23380 + }
23381 + }
23382 + else if (ADHOC_ON(pAd))
23383 + {
23384 + // 2003-04-17 john. this is a patch that driver forces a BEACON out if ASIC fails
23385 + // the "TX BEACON competition" for the entire past 1 sec.
23386 + // So that even when ASIC's BEACONgen engine been blocked
23387 + // by peer's BEACON due to slower system clock, this STA still can send out
23388 + // minimum BEACON to tell the peer I'm alive.
23389 + // drawback is that this BEACON won't be well aligned at TBTT boundary.
23390 + // EnqueueBeaconFrame(pAd); // software send BEACON
23391 +
23392 + // if all 11b peers leave this BSS more than 5 seconds, update Tx rate,
23393 + // restore outgoing BEACON to support B/G-mixed mode
23394 + if ((pAd->CommonCfg.Channel <= 14) &&
23395 + (pAd->CommonCfg.MaxTxRate <= RATE_11) &&
23396 + (pAd->CommonCfg.MaxDesiredRate > RATE_11) &&
23397 + ((pAd->StaCfg.Last11bBeaconRxTime + 5*OS_HZ) < pAd->Mlme.Now32))
23398 + {
23399 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - last 11B peer left, update Tx rates\n"));
23400 + NdisMoveMemory(pAd->StaActive.SupRate, pAd->CommonCfg.SupRate, MAX_LEN_OF_SUPPORTED_RATES);
23401 + pAd->StaActive.SupRateLen = pAd->CommonCfg.SupRateLen;
23402 + MlmeUpdateTxRates(pAd, FALSE, 0);
23403 + MakeIbssBeacon(pAd); // re-build BEACON frame
23404 + AsicEnableIbssSync(pAd); // copy to on-chip memory
23405 + pAd->StaCfg.AdhocBOnlyJoined = FALSE;
23406 + }
23407 +
23408 +#ifdef DOT11_N_SUPPORT
23409 + if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED)
23410 + {
23411 + if ((pAd->StaCfg.AdhocBGJoined) &&
23412 + ((pAd->StaCfg.Last11gBeaconRxTime + 5 * OS_HZ) < pAd->Mlme.Now32))
23413 + {
23414 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - last 11G peer left\n"));
23415 + pAd->StaCfg.AdhocBGJoined = FALSE;
23416 + }
23417 +
23418 + if ((pAd->StaCfg.Adhoc20NJoined) &&
23419 + ((pAd->StaCfg.Last20NBeaconRxTime + 5 * OS_HZ) < pAd->Mlme.Now32))
23420 + {
23421 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - last 20MHz N peer left\n"));
23422 + pAd->StaCfg.Adhoc20NJoined = FALSE;
23423 + }
23424 + }
23425 +#endif // DOT11_N_SUPPORT //
23426 +
23427 + //radar detect
23428 + if ((pAd->CommonCfg.Channel > 14)
23429 + && (pAd->CommonCfg.bIEEE80211H == 1)
23430 + && RadarChannelCheck(pAd, pAd->CommonCfg.Channel))
23431 + {
23432 + RadarDetectPeriodic(pAd);
23433 + }
23434 +
23435 + // If all peers leave, and this STA becomes the last one in this IBSS, then change MediaState
23436 + // to DISCONNECTED. But still holding this IBSS (i.e. sending BEACON) so that other STAs can
23437 + // join later.
23438 + if ((pAd->StaCfg.LastBeaconRxTime + ADHOC_BEACON_LOST_TIME < pAd->Mlme.Now32) &&
23439 + OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
23440 + {
23441 + MLME_START_REQ_STRUCT StartReq;
23442 +
23443 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - excessive BEACON lost, last STA in this IBSS, MediaState=Disconnected\n"));
23444 + LinkDown(pAd, FALSE);
23445 +
23446 + StartParmFill(pAd, &StartReq, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen);
23447 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_START_REQ, sizeof(MLME_START_REQ_STRUCT), &StartReq);
23448 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_START;
23449 + }
23450 + }
23451 + else // no INFRA nor ADHOC connection
23452 + {
23453 +
23454 + if (pAd->StaCfg.bScanReqIsFromWebUI &&
23455 + ((pAd->StaCfg.LastScanTime + 30 * OS_HZ) > pAd->Mlme.Now32))
23456 + goto SKIP_AUTO_SCAN_CONN;
23457 + else
23458 + pAd->StaCfg.bScanReqIsFromWebUI = FALSE;
23459 +
23460 + if ((pAd->StaCfg.bAutoReconnect == TRUE)
23461 + && RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_START_UP)
23462 + && (MlmeValidateSSID(pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.AutoReconnectSsidLen) == TRUE))
23463 + {
23464 + if ((pAd->ScanTab.BssNr==0) && (pAd->Mlme.CntlMachine.CurrState == CNTL_IDLE))
23465 + {
23466 + MLME_SCAN_REQ_STRUCT ScanReq;
23467 +
23468 + if ((pAd->StaCfg.LastScanTime + 10 * OS_HZ) < pAd->Mlme.Now32)
23469 + {
23470 + DBGPRINT(RT_DEBUG_TRACE, ("STAMlmePeriodicExec():CNTL - ScanTab.BssNr==0, start a new ACTIVE scan SSID[%s]\n", pAd->MlmeAux.AutoReconnectSsid));
23471 + ScanParmFill(pAd, &ScanReq, pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.AutoReconnectSsidLen, BSS_ANY, SCAN_ACTIVE);
23472 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ, sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
23473 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
23474 + // Reset Missed scan number
23475 + pAd->StaCfg.LastScanTime = pAd->Mlme.Now32;
23476 + }
23477 + else if (pAd->StaCfg.BssType == BSS_ADHOC) // Quit the forever scan when in a very clean room
23478 + MlmeAutoReconnectLastSSID(pAd);
23479 + }
23480 + else if (pAd->Mlme.CntlMachine.CurrState == CNTL_IDLE)
23481 + {
23482 + if ((pAd->Mlme.OneSecPeriodicRound % 7) == 0)
23483 + {
23484 + MlmeAutoScan(pAd);
23485 + pAd->StaCfg.LastScanTime = pAd->Mlme.Now32;
23486 + }
23487 + else
23488 + {
23489 +#ifdef CARRIER_DETECTION_SUPPORT // Roger sync Carrier
23490 + if (pAd->CommonCfg.CarrierDetect.Enable == TRUE)
23491 + {
23492 + if ((pAd->Mlme.OneSecPeriodicRound % 5) == 1)
23493 + MlmeAutoReconnectLastSSID(pAd);
23494 + }
23495 + else
23496 +#endif // CARRIER_DETECTION_SUPPORT //
23497 + MlmeAutoReconnectLastSSID(pAd);
23498 + }
23499 + }
23500 + }
23501 + }
23502 +
23503 +SKIP_AUTO_SCAN_CONN:
23504 +
23505 +#ifdef DOT11_N_SUPPORT
23506 + if ((pAd->MacTab.Content[BSSID_WCID].TXBAbitmap !=0) && (pAd->MacTab.fAnyBASession == FALSE))
23507 + {
23508 + pAd->MacTab.fAnyBASession = TRUE;
23509 + AsicUpdateProtect(pAd, HT_FORCERTSCTS, ALLN_SETPROTECT, FALSE, FALSE);
23510 + }
23511 + else if ((pAd->MacTab.Content[BSSID_WCID].TXBAbitmap ==0) && (pAd->MacTab.fAnyBASession == TRUE))
23512 + {
23513 + pAd->MacTab.fAnyBASession = FALSE;
23514 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, FALSE, FALSE);
23515 + }
23516 +#endif // DOT11_N_SUPPORT //
23517 +
23518 +
23519 +#ifdef DOT11_N_SUPPORT
23520 +#ifdef DOT11N_DRAFT3
23521 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_SCAN_2040))
23522 + TriEventCounterMaintenance(pAd);
23523 +#endif // DOT11N_DRAFT3 //
23524 +#endif // DOT11_N_SUPPORT //
23525 +
23526 + return;
23527 +}
23528 +
23529 +// Link down report
23530 +VOID LinkDownExec(
23531 + IN PVOID SystemSpecific1,
23532 + IN PVOID FunctionContext,
23533 + IN PVOID SystemSpecific2,
23534 + IN PVOID SystemSpecific3)
23535 +{
23536 +
23537 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
23538 +
23539 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
23540 + RTMP_IndicateMediaState(pAd);
23541 + pAd->ExtraInfo = GENERAL_LINK_DOWN;
23542 +}
23543 +
23544 +// IRQL = DISPATCH_LEVEL
23545 +VOID MlmeAutoScan(
23546 + IN PRTMP_ADAPTER pAd)
23547 +{
23548 + // check CntlMachine.CurrState to avoid collision with NDIS SetOID request
23549 + if (pAd->Mlme.CntlMachine.CurrState == CNTL_IDLE)
23550 + {
23551 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - Driver auto scan\n"));
23552 + MlmeEnqueue(pAd,
23553 + MLME_CNTL_STATE_MACHINE,
23554 + OID_802_11_BSSID_LIST_SCAN,
23555 + 0,
23556 + NULL);
23557 + RT28XX_MLME_HANDLER(pAd);
23558 + }
23559 +}
23560 +
23561 +// IRQL = DISPATCH_LEVEL
23562 +VOID MlmeAutoReconnectLastSSID(
23563 + IN PRTMP_ADAPTER pAd)
23564 +{
23565 +
23566 +
23567 + // check CntlMachine.CurrState to avoid collision with NDIS SetOID request
23568 + if ((pAd->Mlme.CntlMachine.CurrState == CNTL_IDLE) &&
23569 + (MlmeValidateSSID(pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.AutoReconnectSsidLen) == TRUE))
23570 + {
23571 + NDIS_802_11_SSID OidSsid;
23572 + OidSsid.SsidLength = pAd->MlmeAux.AutoReconnectSsidLen;
23573 + NdisMoveMemory(OidSsid.Ssid, pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.AutoReconnectSsidLen);
23574 +
23575 + DBGPRINT(RT_DEBUG_TRACE, ("Driver auto reconnect to last OID_802_11_SSID setting - %s, len - %d\n", pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.AutoReconnectSsidLen));
23576 + MlmeEnqueue(pAd,
23577 + MLME_CNTL_STATE_MACHINE,
23578 + OID_802_11_SSID,
23579 + sizeof(NDIS_802_11_SSID),
23580 + &OidSsid);
23581 + RT28XX_MLME_HANDLER(pAd);
23582 + }
23583 +}
23584 +#endif // CONFIG_STA_SUPPORT //
23585 +
23586 +/*
23587 + ==========================================================================
23588 + Validate SSID for connection try and rescan purpose
23589 + Valid SSID will have visible chars only.
23590 + The valid length is from 0 to 32.
23591 + IRQL = DISPATCH_LEVEL
23592 + ==========================================================================
23593 + */
23594 +BOOLEAN MlmeValidateSSID(
23595 + IN PUCHAR pSsid,
23596 + IN UCHAR SsidLen)
23597 +{
23598 + int index;
23599 +
23600 + if (SsidLen > MAX_LEN_OF_SSID)
23601 + return (FALSE);
23602 +
23603 + // Check each character value
23604 + for (index = 0; index < SsidLen; index++)
23605 + {
23606 + if (pSsid[index] < 0x20)
23607 + return (FALSE);
23608 + }
23609 +
23610 + // All checked
23611 + return (TRUE);
23612 +}
23613 +
23614 +VOID MlmeSelectTxRateTable(
23615 + IN PRTMP_ADAPTER pAd,
23616 + IN PMAC_TABLE_ENTRY pEntry,
23617 + IN PUCHAR *ppTable,
23618 + IN PUCHAR pTableSize,
23619 + IN PUCHAR pInitTxRateIdx)
23620 +{
23621 + do
23622 + {
23623 + // decide the rate table for tuning
23624 + if (pAd->CommonCfg.TxRateTableSize > 0)
23625 + {
23626 + *ppTable = RateSwitchTable;
23627 + *pTableSize = RateSwitchTable[0];
23628 + *pInitTxRateIdx = RateSwitchTable[1];
23629 +
23630 + break;
23631 + }
23632 +
23633 +#ifdef CONFIG_STA_SUPPORT
23634 + if ((pAd->OpMode == OPMODE_STA) && ADHOC_ON(pAd))
23635 + {
23636 +#ifdef DOT11_N_SUPPORT
23637 + if ((pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED) &&
23638 + !pAd->StaCfg.AdhocBOnlyJoined &&
23639 + !pAd->StaCfg.AdhocBGJoined &&
23640 + (pAd->StaActive.SupportedPhyInfo.MCSSet[0] == 0xff) &&
23641 + ((pAd->StaActive.SupportedPhyInfo.MCSSet[1] == 0x00) || (pAd->Antenna.field.TxPath == 1)))
23642 + {// 11N 1S Adhoc
23643 + *ppTable = RateSwitchTable11N1S;
23644 + *pTableSize = RateSwitchTable11N1S[0];
23645 + *pInitTxRateIdx = RateSwitchTable11N1S[1];
23646 +
23647 + }
23648 + else if ((pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED) &&
23649 + !pAd->StaCfg.AdhocBOnlyJoined &&
23650 + !pAd->StaCfg.AdhocBGJoined &&
23651 + (pAd->StaActive.SupportedPhyInfo.MCSSet[0] == 0xff) &&
23652 + (pAd->StaActive.SupportedPhyInfo.MCSSet[1] == 0xff) &&
23653 + (pAd->Antenna.field.TxPath == 2))
23654 + {// 11N 2S Adhoc
23655 + if (pAd->LatchRfRegs.Channel <= 14)
23656 + {
23657 + *ppTable = RateSwitchTable11N2S;
23658 + *pTableSize = RateSwitchTable11N2S[0];
23659 + *pInitTxRateIdx = RateSwitchTable11N2S[1];
23660 + }
23661 + else
23662 + {
23663 + *ppTable = RateSwitchTable11N2SForABand;
23664 + *pTableSize = RateSwitchTable11N2SForABand[0];
23665 + *pInitTxRateIdx = RateSwitchTable11N2SForABand[1];
23666 + }
23667 +
23668 + }
23669 + else
23670 +#endif // DOT11_N_SUPPORT //
23671 + if (pAd->CommonCfg.PhyMode == PHY_11B)
23672 + {
23673 + *ppTable = RateSwitchTable11B;
23674 + *pTableSize = RateSwitchTable11B[0];
23675 + *pInitTxRateIdx = RateSwitchTable11B[1];
23676 +
23677 + }
23678 + else if((pAd->LatchRfRegs.Channel <= 14) && (pAd->StaCfg.AdhocBOnlyJoined == TRUE))
23679 + {
23680 + // USe B Table when Only b-only Station in my IBSS .
23681 + *ppTable = RateSwitchTable11B;
23682 + *pTableSize = RateSwitchTable11B[0];
23683 + *pInitTxRateIdx = RateSwitchTable11B[1];
23684 +
23685 + }
23686 + else if (pAd->LatchRfRegs.Channel <= 14)
23687 + {
23688 + *ppTable = RateSwitchTable11BG;
23689 + *pTableSize = RateSwitchTable11BG[0];
23690 + *pInitTxRateIdx = RateSwitchTable11BG[1];
23691 +
23692 + }
23693 + else
23694 + {
23695 + *ppTable = RateSwitchTable11G;
23696 + *pTableSize = RateSwitchTable11G[0];
23697 + *pInitTxRateIdx = RateSwitchTable11G[1];
23698 +
23699 + }
23700 + break;
23701 + }
23702 +#endif // CONFIG_STA_SUPPORT //
23703 +
23704 +#ifdef DOT11_N_SUPPORT
23705 + if ((pEntry->RateLen == 12) && (pEntry->HTCapability.MCSSet[0] == 0xff) &&
23706 + ((pEntry->HTCapability.MCSSet[1] == 0x00) || (pAd->CommonCfg.TxStream == 1)))
23707 + {// 11BGN 1S AP
23708 + *ppTable = RateSwitchTable11BGN1S;
23709 + *pTableSize = RateSwitchTable11BGN1S[0];
23710 + *pInitTxRateIdx = RateSwitchTable11BGN1S[1];
23711 +
23712 + break;
23713 + }
23714 +
23715 + if ((pEntry->RateLen == 12) && (pEntry->HTCapability.MCSSet[0] == 0xff) &&
23716 + (pEntry->HTCapability.MCSSet[1] == 0xff) && (pAd->CommonCfg.TxStream == 2))
23717 + {// 11BGN 2S AP
23718 + if (pAd->LatchRfRegs.Channel <= 14)
23719 + {
23720 + *ppTable = RateSwitchTable11BGN2S;
23721 + *pTableSize = RateSwitchTable11BGN2S[0];
23722 + *pInitTxRateIdx = RateSwitchTable11BGN2S[1];
23723 +
23724 + }
23725 + else
23726 + {
23727 + *ppTable = RateSwitchTable11BGN2SForABand;
23728 + *pTableSize = RateSwitchTable11BGN2SForABand[0];
23729 + *pInitTxRateIdx = RateSwitchTable11BGN2SForABand[1];
23730 +
23731 + }
23732 + break;
23733 + }
23734 +
23735 + if ((pEntry->HTCapability.MCSSet[0] == 0xff) && ((pEntry->HTCapability.MCSSet[1] == 0x00) || (pAd->CommonCfg.TxStream == 1)))
23736 + {// 11N 1S AP
23737 + *ppTable = RateSwitchTable11N1S;
23738 + *pTableSize = RateSwitchTable11N1S[0];
23739 + *pInitTxRateIdx = RateSwitchTable11N1S[1];
23740 +
23741 + break;
23742 + }
23743 +
23744 + if ((pEntry->HTCapability.MCSSet[0] == 0xff) && (pEntry->HTCapability.MCSSet[1] == 0xff) && (pAd->CommonCfg.TxStream == 2))
23745 + {// 11N 2S AP
23746 + if (pAd->LatchRfRegs.Channel <= 14)
23747 + {
23748 + *ppTable = RateSwitchTable11N2S;
23749 + *pTableSize = RateSwitchTable11N2S[0];
23750 + *pInitTxRateIdx = RateSwitchTable11N2S[1];
23751 + }
23752 + else
23753 + {
23754 + *ppTable = RateSwitchTable11N2SForABand;
23755 + *pTableSize = RateSwitchTable11N2SForABand[0];
23756 + *pInitTxRateIdx = RateSwitchTable11N2SForABand[1];
23757 + }
23758 +
23759 + break;
23760 + }
23761 +#endif // DOT11_N_SUPPORT //
23762 + //else if ((pAd->StaActive.SupRateLen == 4) && (pAd->StaActive.ExtRateLen == 0) && (pAd->StaActive.SupportedPhyInfo.MCSSet[0] == 0) && (pAd->StaActive.SupportedPhyInfo.MCSSet[1] == 0))
23763 + if ((pEntry->RateLen == 4)
23764 +#ifdef DOT11_N_SUPPORT
23765 + && (pEntry->HTCapability.MCSSet[0] == 0) && (pEntry->HTCapability.MCSSet[1] == 0)
23766 +#endif // DOT11_N_SUPPORT //
23767 + )
23768 + {// B only AP
23769 + *ppTable = RateSwitchTable11B;
23770 + *pTableSize = RateSwitchTable11B[0];
23771 + *pInitTxRateIdx = RateSwitchTable11B[1];
23772 +
23773 + break;
23774 + }
23775 +
23776 + //else if ((pAd->StaActive.SupRateLen + pAd->StaActive.ExtRateLen > 8) && (pAd->StaActive.SupportedPhyInfo.MCSSet[0] == 0) && (pAd->StaActive.SupportedPhyInfo.MCSSet[1] == 0))
23777 + if ((pEntry->RateLen > 8)
23778 +#ifdef DOT11_N_SUPPORT
23779 + && (pEntry->HTCapability.MCSSet[0] == 0) && (pEntry->HTCapability.MCSSet[1] == 0)
23780 +#endif // DOT11_N_SUPPORT //
23781 + )
23782 + {// B/G mixed AP
23783 + *ppTable = RateSwitchTable11BG;
23784 + *pTableSize = RateSwitchTable11BG[0];
23785 + *pInitTxRateIdx = RateSwitchTable11BG[1];
23786 +
23787 + break;
23788 + }
23789 +
23790 + //else if ((pAd->StaActive.SupRateLen + pAd->StaActive.ExtRateLen == 8) && (pAd->StaActive.SupportedPhyInfo.MCSSet[0] == 0) && (pAd->StaActive.SupportedPhyInfo.MCSSet[1] == 0))
23791 + if ((pEntry->RateLen == 8)
23792 +#ifdef DOT11_N_SUPPORT
23793 + && (pEntry->HTCapability.MCSSet[0] == 0) && (pEntry->HTCapability.MCSSet[1] == 0)
23794 +#endif // DOT11_N_SUPPORT //
23795 + )
23796 + {// G only AP
23797 + *ppTable = RateSwitchTable11G;
23798 + *pTableSize = RateSwitchTable11G[0];
23799 + *pInitTxRateIdx = RateSwitchTable11G[1];
23800 +
23801 + break;
23802 + }
23803 +#ifdef DOT11_N_SUPPORT
23804 +#endif // DOT11_N_SUPPORT //
23805 +
23806 +#ifdef CONFIG_STA_SUPPORT
23807 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
23808 + {
23809 +#ifdef DOT11_N_SUPPORT
23810 + //else if ((pAd->StaActive.SupportedPhyInfo.MCSSet[0] == 0) && (pAd->StaActive.SupportedPhyInfo.MCSSet[1] == 0))
23811 + if ((pEntry->HTCapability.MCSSet[0] == 0) && (pEntry->HTCapability.MCSSet[1] == 0))
23812 +#endif // DOT11_N_SUPPORT //
23813 + { // Legacy mode
23814 + if (pAd->CommonCfg.MaxTxRate <= RATE_11)
23815 + {
23816 + *ppTable = RateSwitchTable11B;
23817 + *pTableSize = RateSwitchTable11B[0];
23818 + *pInitTxRateIdx = RateSwitchTable11B[1];
23819 + }
23820 + else if ((pAd->CommonCfg.MaxTxRate > RATE_11) && (pAd->CommonCfg.MinTxRate > RATE_11))
23821 + {
23822 + *ppTable = RateSwitchTable11G;
23823 + *pTableSize = RateSwitchTable11G[0];
23824 + *pInitTxRateIdx = RateSwitchTable11G[1];
23825 +
23826 + }
23827 + else
23828 + {
23829 + *ppTable = RateSwitchTable11BG;
23830 + *pTableSize = RateSwitchTable11BG[0];
23831 + *pInitTxRateIdx = RateSwitchTable11BG[1];
23832 + }
23833 + break;
23834 + }
23835 +#ifdef DOT11_N_SUPPORT
23836 + if (pAd->LatchRfRegs.Channel <= 14)
23837 + {
23838 + if (pAd->CommonCfg.TxStream == 1)
23839 + {
23840 + *ppTable = RateSwitchTable11N1S;
23841 + *pTableSize = RateSwitchTable11N1S[0];
23842 + *pInitTxRateIdx = RateSwitchTable11N1S[1];
23843 + DBGPRINT_RAW(RT_DEBUG_ERROR,("DRS: unkown mode,default use 11N 1S AP \n"));
23844 + }
23845 + else
23846 + {
23847 + *ppTable = RateSwitchTable11N2S;
23848 + *pTableSize = RateSwitchTable11N2S[0];
23849 + *pInitTxRateIdx = RateSwitchTable11N2S[1];
23850 + DBGPRINT_RAW(RT_DEBUG_ERROR,("DRS: unkown mode,default use 11N 2S AP \n"));
23851 + }
23852 + }
23853 + else
23854 + {
23855 + if (pAd->CommonCfg.TxStream == 1)
23856 + {
23857 + *ppTable = RateSwitchTable11N1S;
23858 + *pTableSize = RateSwitchTable11N1S[0];
23859 + *pInitTxRateIdx = RateSwitchTable11N1S[1];
23860 + DBGPRINT_RAW(RT_DEBUG_ERROR,("DRS: unkown mode,default use 11N 1S AP \n"));
23861 + }
23862 + else
23863 + {
23864 + *ppTable = RateSwitchTable11N2SForABand;
23865 + *pTableSize = RateSwitchTable11N2SForABand[0];
23866 + *pInitTxRateIdx = RateSwitchTable11N2SForABand[1];
23867 + DBGPRINT_RAW(RT_DEBUG_ERROR,("DRS: unkown mode,default use 11N 2S AP \n"));
23868 + }
23869 + }
23870 +#endif // DOT11_N_SUPPORT //
23871 + DBGPRINT_RAW(RT_DEBUG_ERROR,("DRS: unkown mode (SupRateLen=%d, ExtRateLen=%d, MCSSet[0]=0x%x, MCSSet[1]=0x%x)\n",
23872 + pAd->StaActive.SupRateLen, pAd->StaActive.ExtRateLen, pAd->StaActive.SupportedPhyInfo.MCSSet[0], pAd->StaActive.SupportedPhyInfo.MCSSet[1]));
23873 + }
23874 +#endif // CONFIG_STA_SUPPORT //
23875 + } while(FALSE);
23876 +}
23877 +
23878 +#ifdef CONFIG_STA_SUPPORT
23879 +/*
23880 + ==========================================================================
23881 + Description:
23882 + This routine checks if there're other APs out there capable for
23883 + roaming. Caller should call this routine only when Link up in INFRA mode
23884 + and channel quality is below CQI_GOOD_THRESHOLD.
23885 +
23886 + IRQL = DISPATCH_LEVEL
23887 +
23888 + Output:
23889 + ==========================================================================
23890 + */
23891 +VOID MlmeCheckForRoaming(
23892 + IN PRTMP_ADAPTER pAd,
23893 + IN ULONG Now32)
23894 +{
23895 + USHORT i;
23896 + BSS_TABLE *pRoamTab = &pAd->MlmeAux.RoamTab;
23897 + BSS_ENTRY *pBss;
23898 +
23899 + DBGPRINT(RT_DEBUG_TRACE, ("==> MlmeCheckForRoaming\n"));
23900 + // put all roaming candidates into RoamTab, and sort in RSSI order
23901 + BssTableInit(pRoamTab);
23902 + for (i = 0; i < pAd->ScanTab.BssNr; i++)
23903 + {
23904 + pBss = &pAd->ScanTab.BssEntry[i];
23905 +
23906 + if ((pBss->LastBeaconRxTime + BEACON_LOST_TIME) < Now32)
23907 + continue; // AP disappear
23908 + if (pBss->Rssi <= RSSI_THRESHOLD_FOR_ROAMING)
23909 + continue; // RSSI too weak. forget it.
23910 + if (MAC_ADDR_EQUAL(pBss->Bssid, pAd->CommonCfg.Bssid))
23911 + continue; // skip current AP
23912 + if (pBss->Rssi < (pAd->StaCfg.RssiSample.LastRssi0 + RSSI_DELTA))
23913 + continue; // only AP with stronger RSSI is eligible for roaming
23914 +
23915 + // AP passing all above rules is put into roaming candidate table
23916 + NdisMoveMemory(&pRoamTab->BssEntry[pRoamTab->BssNr], pBss, sizeof(BSS_ENTRY));
23917 + pRoamTab->BssNr += 1;
23918 + }
23919 +
23920 + if (pRoamTab->BssNr > 0)
23921 + {
23922 + // check CntlMachine.CurrState to avoid collision with NDIS SetOID request
23923 + if (pAd->Mlme.CntlMachine.CurrState == CNTL_IDLE)
23924 + {
23925 + pAd->RalinkCounters.PoorCQIRoamingCount ++;
23926 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - Roaming attempt #%ld\n", pAd->RalinkCounters.PoorCQIRoamingCount));
23927 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_MLME_ROAMING_REQ, 0, NULL);
23928 + RT28XX_MLME_HANDLER(pAd);
23929 + }
23930 + }
23931 + DBGPRINT(RT_DEBUG_TRACE, ("<== MlmeCheckForRoaming(# of candidate= %d)\n",pRoamTab->BssNr));
23932 +}
23933 +
23934 +/*
23935 + ==========================================================================
23936 + Description:
23937 + This routine checks if there're other APs out there capable for
23938 + roaming. Caller should call this routine only when link up in INFRA mode
23939 + and channel quality is below CQI_GOOD_THRESHOLD.
23940 +
23941 + IRQL = DISPATCH_LEVEL
23942 +
23943 + Output:
23944 + ==========================================================================
23945 + */
23946 +VOID MlmeCheckForFastRoaming(
23947 + IN PRTMP_ADAPTER pAd,
23948 + IN ULONG Now)
23949 +{
23950 + USHORT i;
23951 + BSS_TABLE *pRoamTab = &pAd->MlmeAux.RoamTab;
23952 + BSS_ENTRY *pBss;
23953 +
23954 + DBGPRINT(RT_DEBUG_TRACE, ("==> MlmeCheckForFastRoaming\n"));
23955 + // put all roaming candidates into RoamTab, and sort in RSSI order
23956 + BssTableInit(pRoamTab);
23957 + for (i = 0; i < pAd->ScanTab.BssNr; i++)
23958 + {
23959 + pBss = &pAd->ScanTab.BssEntry[i];
23960 +
23961 + if ((pBss->Rssi <= -50) && (pBss->Channel == pAd->CommonCfg.Channel))
23962 + continue; // RSSI too weak. forget it.
23963 + if (MAC_ADDR_EQUAL(pBss->Bssid, pAd->CommonCfg.Bssid))
23964 + continue; // skip current AP
23965 + if (!SSID_EQUAL(pBss->Ssid, pBss->SsidLen, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen))
23966 + continue; // skip different SSID
23967 + if (pBss->Rssi < (RTMPMaxRssi(pAd, pAd->StaCfg.RssiSample.LastRssi0, pAd->StaCfg.RssiSample.LastRssi1, pAd->StaCfg.RssiSample.LastRssi2) + RSSI_DELTA))
23968 + continue; // skip AP without better RSSI
23969 +
23970 + DBGPRINT(RT_DEBUG_TRACE, ("LastRssi0 = %d, pBss->Rssi = %d\n", RTMPMaxRssi(pAd, pAd->StaCfg.RssiSample.LastRssi0, pAd->StaCfg.RssiSample.LastRssi1, pAd->StaCfg.RssiSample.LastRssi2), pBss->Rssi));
23971 + // AP passing all above rules is put into roaming candidate table
23972 + NdisMoveMemory(&pRoamTab->BssEntry[pRoamTab->BssNr], pBss, sizeof(BSS_ENTRY));
23973 + pRoamTab->BssNr += 1;
23974 + }
23975 +
23976 + if (pRoamTab->BssNr > 0)
23977 + {
23978 + // check CntlMachine.CurrState to avoid collision with NDIS SetOID request
23979 + if (pAd->Mlme.CntlMachine.CurrState == CNTL_IDLE)
23980 + {
23981 + pAd->RalinkCounters.PoorCQIRoamingCount ++;
23982 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - Roaming attempt #%ld\n", pAd->RalinkCounters.PoorCQIRoamingCount));
23983 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_MLME_ROAMING_REQ, 0, NULL);
23984 + RT28XX_MLME_HANDLER(pAd);
23985 + }
23986 + }
23987 + // Maybe site survey required
23988 + else
23989 + {
23990 + if ((pAd->StaCfg.LastScanTime + 10 * 1000) < Now)
23991 + {
23992 + // check CntlMachine.CurrState to avoid collision with NDIS SetOID request
23993 + DBGPRINT(RT_DEBUG_TRACE, ("MMCHK - Roaming, No eligable entry, try new scan!\n"));
23994 + pAd->StaCfg.ScanCnt = 2;
23995 + pAd->StaCfg.LastScanTime = Now;
23996 + MlmeAutoScan(pAd);
23997 + }
23998 + }
23999 +
24000 + DBGPRINT(RT_DEBUG_TRACE, ("<== MlmeCheckForFastRoaming (BssNr=%d)\n", pRoamTab->BssNr));
24001 +}
24002 +
24003 +/*
24004 + ==========================================================================
24005 + Description:
24006 + This routine calculates TxPER, RxPER of the past N-sec period. And
24007 + according to the calculation result, ChannelQuality is calculated here
24008 + to decide if current AP is still doing the job.
24009 +
24010 + If ChannelQuality is not good, a ROAMing attempt may be tried later.
24011 + Output:
24012 + StaCfg.ChannelQuality - 0..100
24013 +
24014 + IRQL = DISPATCH_LEVEL
24015 +
24016 + NOTE: This routine decide channle quality based on RX CRC error ratio.
24017 + Caller should make sure a function call to NICUpdateRawCounters(pAd)
24018 + is performed right before this routine, so that this routine can decide
24019 + channel quality based on the most up-to-date information
24020 + ==========================================================================
24021 + */
24022 +VOID MlmeCalculateChannelQuality(
24023 + IN PRTMP_ADAPTER pAd,
24024 + IN ULONG Now32)
24025 +{
24026 + ULONG TxOkCnt, TxCnt, TxPER, TxPRR;
24027 + ULONG RxCnt, RxPER;
24028 + UCHAR NorRssi;
24029 + CHAR MaxRssi;
24030 + ULONG BeaconLostTime = BEACON_LOST_TIME;
24031 +
24032 +#ifdef CARRIER_DETECTION_SUPPORT // Roger sync Carrier
24033 + // longer beacon lost time when carrier detection enabled
24034 + if (pAd->CommonCfg.CarrierDetect.Enable == TRUE)
24035 + {
24036 + BeaconLostTime = BEACON_LOST_TIME + BEACON_LOST_TIME/2;
24037 + }
24038 +#endif // CARRIER_DETECTION_SUPPORT //
24039 +
24040 + MaxRssi = RTMPMaxRssi(pAd, pAd->StaCfg.RssiSample.LastRssi0, pAd->StaCfg.RssiSample.LastRssi1, pAd->StaCfg.RssiSample.LastRssi2);
24041 +
24042 + //
24043 + // calculate TX packet error ratio and TX retry ratio - if too few TX samples, skip TX related statistics
24044 + //
24045 + TxOkCnt = pAd->RalinkCounters.OneSecTxNoRetryOkCount + pAd->RalinkCounters.OneSecTxRetryOkCount;
24046 + TxCnt = TxOkCnt + pAd->RalinkCounters.OneSecTxFailCount;
24047 + if (TxCnt < 5)
24048 + {
24049 + TxPER = 0;
24050 + TxPRR = 0;
24051 + }
24052 + else
24053 + {
24054 + TxPER = (pAd->RalinkCounters.OneSecTxFailCount * 100) / TxCnt;
24055 + TxPRR = ((TxCnt - pAd->RalinkCounters.OneSecTxNoRetryOkCount) * 100) / TxCnt;
24056 + }
24057 +
24058 + //
24059 + // calculate RX PER - don't take RxPER into consideration if too few sample
24060 + //
24061 + RxCnt = pAd->RalinkCounters.OneSecRxOkCnt + pAd->RalinkCounters.OneSecRxFcsErrCnt;
24062 + if (RxCnt < 5)
24063 + RxPER = 0;
24064 + else
24065 + RxPER = (pAd->RalinkCounters.OneSecRxFcsErrCnt * 100) / RxCnt;
24066 +
24067 + //
24068 + // decide ChannelQuality based on: 1)last BEACON received time, 2)last RSSI, 3)TxPER, and 4)RxPER
24069 + //
24070 + if (INFRA_ON(pAd) &&
24071 + (pAd->RalinkCounters.OneSecTxNoRetryOkCount < 2) && // no heavy traffic
24072 + (pAd->StaCfg.LastBeaconRxTime + BeaconLostTime < Now32))
24073 + {
24074 + DBGPRINT(RT_DEBUG_TRACE, ("BEACON lost > %ld msec with TxOkCnt=%ld -> CQI=0\n", BeaconLostTime, TxOkCnt));
24075 + pAd->Mlme.ChannelQuality = 0;
24076 + }
24077 + else
24078 + {
24079 + // Normalize Rssi
24080 + if (MaxRssi > -40)
24081 + NorRssi = 100;
24082 + else if (MaxRssi < -90)
24083 + NorRssi = 0;
24084 + else
24085 + NorRssi = (MaxRssi + 90) * 2;
24086 +
24087 + // ChannelQuality = W1*RSSI + W2*TxPRR + W3*RxPER (RSSI 0..100), (TxPER 100..0), (RxPER 100..0)
24088 + pAd->Mlme.ChannelQuality = (RSSI_WEIGHTING * NorRssi +
24089 + TX_WEIGHTING * (100 - TxPRR) +
24090 + RX_WEIGHTING* (100 - RxPER)) / 100;
24091 + if (pAd->Mlme.ChannelQuality >= 100)
24092 + pAd->Mlme.ChannelQuality = 100;
24093 + }
24094 +
24095 +}
24096 +
24097 +VOID MlmeSetTxRate(
24098 + IN PRTMP_ADAPTER pAd,
24099 + IN PMAC_TABLE_ENTRY pEntry,
24100 + IN PRTMP_TX_RATE_SWITCH pTxRate)
24101 +{
24102 + UCHAR MaxMode = MODE_OFDM;
24103 +
24104 +#ifdef DOT11_N_SUPPORT
24105 + MaxMode = MODE_HTGREENFIELD;
24106 +
24107 + if (pTxRate->STBC && (pAd->StaCfg.MaxHTPhyMode.field.STBC) && (pAd->Antenna.field.TxPath == 2))
24108 + pAd->StaCfg.HTPhyMode.field.STBC = STBC_USE;
24109 + else
24110 +#endif // DOT11_N_SUPPORT //
24111 + pAd->StaCfg.HTPhyMode.field.STBC = STBC_NONE;
24112 +
24113 + if (pTxRate->CurrMCS < MCS_AUTO)
24114 + pAd->StaCfg.HTPhyMode.field.MCS = pTxRate->CurrMCS;
24115 +
24116 + if (pAd->StaCfg.HTPhyMode.field.MCS > 7)
24117 + pAd->StaCfg.HTPhyMode.field.STBC = STBC_NONE;
24118 +
24119 + if (ADHOC_ON(pAd))
24120 + {
24121 + // If peer adhoc is b-only mode, we can't send 11g rate.
24122 + pAd->StaCfg.HTPhyMode.field.ShortGI = GI_800;
24123 + pEntry->HTPhyMode.field.STBC = STBC_NONE;
24124 +
24125 + //
24126 + // For Adhoc MODE_CCK, driver will use AdhocBOnlyJoined flag to roll back to B only if necessary
24127 + //
24128 + pEntry->HTPhyMode.field.MODE = pTxRate->Mode;
24129 + pEntry->HTPhyMode.field.ShortGI = pAd->StaCfg.HTPhyMode.field.ShortGI;
24130 + pEntry->HTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
24131 +
24132 + // Patch speed error in status page
24133 + pAd->StaCfg.HTPhyMode.field.MODE = pEntry->HTPhyMode.field.MODE;
24134 + }
24135 + else
24136 + {
24137 + if (pTxRate->Mode <= MaxMode)
24138 + pAd->StaCfg.HTPhyMode.field.MODE = pTxRate->Mode;
24139 +
24140 +#ifdef DOT11_N_SUPPORT
24141 + if (pTxRate->ShortGI && (pAd->StaCfg.MaxHTPhyMode.field.ShortGI))
24142 + pAd->StaCfg.HTPhyMode.field.ShortGI = GI_400;
24143 + else
24144 +#endif // DOT11_N_SUPPORT //
24145 + pAd->StaCfg.HTPhyMode.field.ShortGI = GI_800;
24146 +
24147 +#ifdef DOT11_N_SUPPORT
24148 + // Reexam each bandwidth's SGI support.
24149 + if (pAd->StaCfg.HTPhyMode.field.ShortGI == GI_400)
24150 + {
24151 + if ((pEntry->HTPhyMode.field.BW == BW_20) && (!CLIENT_STATUS_TEST_FLAG(pEntry, fCLIENT_STATUS_SGI20_CAPABLE)))
24152 + pAd->StaCfg.HTPhyMode.field.ShortGI = GI_800;
24153 + if ((pEntry->HTPhyMode.field.BW == BW_40) && (!CLIENT_STATUS_TEST_FLAG(pEntry, fCLIENT_STATUS_SGI40_CAPABLE)))
24154 + pAd->StaCfg.HTPhyMode.field.ShortGI = GI_800;
24155 + }
24156 +
24157 + // Turn RTS/CTS rate to 6Mbps.
24158 + if ((pEntry->HTPhyMode.field.MCS == 0) && (pAd->StaCfg.HTPhyMode.field.MCS != 0))
24159 + {
24160 + pEntry->HTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
24161 + if (pAd->MacTab.fAnyBASession)
24162 + {
24163 + AsicUpdateProtect(pAd, HT_FORCERTSCTS, ALLN_SETPROTECT, TRUE, (BOOLEAN)pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent);
24164 + }
24165 + else
24166 + {
24167 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, TRUE, (BOOLEAN)pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent);
24168 + }
24169 + }
24170 + else if ((pEntry->HTPhyMode.field.MCS == 8) && (pAd->StaCfg.HTPhyMode.field.MCS != 8))
24171 + {
24172 + pEntry->HTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
24173 + if (pAd->MacTab.fAnyBASession)
24174 + {
24175 + AsicUpdateProtect(pAd, HT_FORCERTSCTS, ALLN_SETPROTECT, TRUE, (BOOLEAN)pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent);
24176 + }
24177 + else
24178 + {
24179 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, TRUE, (BOOLEAN)pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent);
24180 + }
24181 + }
24182 + else if ((pEntry->HTPhyMode.field.MCS != 0) && (pAd->StaCfg.HTPhyMode.field.MCS == 0))
24183 + {
24184 + AsicUpdateProtect(pAd, HT_RTSCTS_6M, ALLN_SETPROTECT, TRUE, (BOOLEAN)pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent);
24185 +
24186 + }
24187 + else if ((pEntry->HTPhyMode.field.MCS != 8) && (pAd->StaCfg.HTPhyMode.field.MCS == 8))
24188 + {
24189 + AsicUpdateProtect(pAd, HT_RTSCTS_6M, ALLN_SETPROTECT, TRUE, (BOOLEAN)pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent);
24190 + }
24191 +#endif // DOT11_N_SUPPORT //
24192 +
24193 + pEntry->HTPhyMode.field.STBC = pAd->StaCfg.HTPhyMode.field.STBC;
24194 + pEntry->HTPhyMode.field.ShortGI = pAd->StaCfg.HTPhyMode.field.ShortGI;
24195 + pEntry->HTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
24196 + pEntry->HTPhyMode.field.MODE = pAd->StaCfg.HTPhyMode.field.MODE;
24197 +#ifdef DOT11_N_SUPPORT
24198 + if ((pAd->StaCfg.MaxHTPhyMode.field.MODE == MODE_HTGREENFIELD) &&
24199 + pAd->WIFItestbed.bGreenField)
24200 + pEntry->HTPhyMode.field.MODE = MODE_HTGREENFIELD;
24201 +#endif // DOT11_N_SUPPORT //
24202 + }
24203 +
24204 + pAd->LastTxRate = (USHORT)(pEntry->HTPhyMode.word);
24205 +}
24206 +
24207 +/*
24208 + ==========================================================================
24209 + Description:
24210 + This routine calculates the acumulated TxPER of eaxh TxRate. And
24211 + according to the calculation result, change CommonCfg.TxRate which
24212 + is the stable TX Rate we expect the Radio situation could sustained.
24213 +
24214 + CommonCfg.TxRate will change dynamically within {RATE_1/RATE_6, MaxTxRate}
24215 + Output:
24216 + CommonCfg.TxRate -
24217 +
24218 + IRQL = DISPATCH_LEVEL
24219 +
24220 + NOTE:
24221 + call this routine every second
24222 + ==========================================================================
24223 + */
24224 +VOID MlmeDynamicTxRateSwitching(
24225 + IN PRTMP_ADAPTER pAd)
24226 +{
24227 + UCHAR UpRateIdx = 0, DownRateIdx = 0, CurrRateIdx;
24228 + ULONG i, AccuTxTotalCnt = 0, TxTotalCnt;
24229 + ULONG TxErrorRatio = 0;
24230 + BOOLEAN bTxRateChanged, bUpgradeQuality = FALSE;
24231 + PRTMP_TX_RATE_SWITCH pCurrTxRate, pNextTxRate = NULL;
24232 + PUCHAR pTable;
24233 + UCHAR TableSize = 0;
24234 + UCHAR InitTxRateIdx = 0, TrainUp, TrainDown;
24235 + CHAR Rssi, RssiOffset = 0;
24236 + TX_STA_CNT1_STRUC StaTx1;
24237 + TX_STA_CNT0_STRUC TxStaCnt0;
24238 + ULONG TxRetransmit = 0, TxSuccess = 0, TxFailCount = 0;
24239 + MAC_TABLE_ENTRY *pEntry;
24240 +
24241 +#ifdef RALINK_ATE
24242 + if (ATE_ON(pAd))
24243 + {
24244 + return;
24245 + }
24246 +#endif // RALINK_ATE //
24247 +
24248 + /*if (pAd->Antenna.field.RxPath > 1)
24249 + Rssi = (pAd->StaCfg.RssiSample.AvgRssi0 + pAd->StaCfg.RssiSample.AvgRssi1) >> 1;
24250 + else
24251 + Rssi = pAd->StaCfg.RssiSample.AvgRssi0;*/
24252 +
24253 + //
24254 + // walk through MAC table, see if need to change AP's TX rate toward each entry
24255 + //
24256 + for (i = 1; i < MAX_LEN_OF_MAC_TABLE; i++)
24257 + {
24258 + pEntry = &pAd->MacTab.Content[i];
24259 +
24260 + // check if this entry need to switch rate automatically
24261 + if (RTMPCheckEntryEnableAutoRateSwitch(pAd, pEntry) == FALSE)
24262 + continue;
24263 +
24264 + if ((pAd->MacTab.Size == 1) || (pEntry->ValidAsDls))
24265 + {
24266 + Rssi = RTMPMaxRssi(pAd, (CHAR)pAd->StaCfg.RssiSample.AvgRssi0, (CHAR)pAd->StaCfg.RssiSample.AvgRssi1, (CHAR)pAd->StaCfg.RssiSample.AvgRssi2);
24267 +
24268 + // Update statistic counter
24269 + RTMP_IO_READ32(pAd, TX_STA_CNT0, &TxStaCnt0.word);
24270 + RTMP_IO_READ32(pAd, TX_STA_CNT1, &StaTx1.word);
24271 + pAd->bUpdateBcnCntDone = TRUE;
24272 + TxRetransmit = StaTx1.field.TxRetransmit;
24273 + TxSuccess = StaTx1.field.TxSuccess;
24274 + TxFailCount = TxStaCnt0.field.TxFailCount;
24275 + TxTotalCnt = TxRetransmit + TxSuccess + TxFailCount;
24276 +
24277 + pAd->RalinkCounters.OneSecTxRetryOkCount += StaTx1.field.TxRetransmit;
24278 + pAd->RalinkCounters.OneSecTxNoRetryOkCount += StaTx1.field.TxSuccess;
24279 + pAd->RalinkCounters.OneSecTxFailCount += TxStaCnt0.field.TxFailCount;
24280 + pAd->WlanCounters.TransmittedFragmentCount.u.LowPart += StaTx1.field.TxSuccess;
24281 + pAd->WlanCounters.RetryCount.u.LowPart += StaTx1.field.TxRetransmit;
24282 + pAd->WlanCounters.FailedCount.u.LowPart += TxStaCnt0.field.TxFailCount;
24283 +
24284 + // if no traffic in the past 1-sec period, don't change TX rate,
24285 + // but clear all bad history. because the bad history may affect the next
24286 + // Chariot throughput test
24287 + AccuTxTotalCnt = pAd->RalinkCounters.OneSecTxNoRetryOkCount +
24288 + pAd->RalinkCounters.OneSecTxRetryOkCount +
24289 + pAd->RalinkCounters.OneSecTxFailCount;
24290 +
24291 + if (TxTotalCnt)
24292 + TxErrorRatio = ((TxRetransmit + TxFailCount) * 100) / TxTotalCnt;
24293 + }
24294 + else
24295 + {
24296 + Rssi = RTMPMaxRssi(pAd, (CHAR)pEntry->RssiSample.AvgRssi0, (CHAR)pEntry->RssiSample.AvgRssi1, (CHAR)pEntry->RssiSample.AvgRssi2);
24297 +
24298 + TxTotalCnt = pEntry->OneSecTxNoRetryOkCount +
24299 + pEntry->OneSecTxRetryOkCount +
24300 + pEntry->OneSecTxFailCount;
24301 +
24302 + if (TxTotalCnt)
24303 + TxErrorRatio = ((pEntry->OneSecTxRetryOkCount + pEntry->OneSecTxFailCount) * 100) / TxTotalCnt;
24304 + }
24305 +
24306 + CurrRateIdx = pEntry->CurrTxRateIndex;
24307 +
24308 + MlmeSelectTxRateTable(pAd, pEntry, &pTable, &TableSize, &InitTxRateIdx);
24309 +
24310 + if (CurrRateIdx >= TableSize)
24311 + {
24312 + CurrRateIdx = TableSize - 1;
24313 + }
24314 +
24315 + // When switch from Fixed rate -> auto rate, the REAL TX rate might be different from pAd->CommonCfg.TxRateIndex.
24316 + // So need to sync here.
24317 + pCurrTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(CurrRateIdx+1)*5];
24318 + if ((pEntry->HTPhyMode.field.MCS != pCurrTxRate->CurrMCS)
24319 + //&& (pAd->StaCfg.bAutoTxRateSwitch == TRUE)
24320 + )
24321 + {
24322 +
24323 + // Need to sync Real Tx rate and our record.
24324 + // Then return for next DRS.
24325 + pCurrTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(InitTxRateIdx+1)*5];
24326 + pEntry->CurrTxRateIndex = InitTxRateIdx;
24327 + MlmeSetTxRate(pAd, pEntry, pCurrTxRate);
24328 +
24329 + // reset all OneSecTx counters
24330 + RESET_ONE_SEC_TX_CNT(pEntry);
24331 + continue;
24332 + }
24333 +
24334 + // decide the next upgrade rate and downgrade rate, if any
24335 + if ((CurrRateIdx > 0) && (CurrRateIdx < (TableSize - 1)))
24336 + {
24337 + UpRateIdx = CurrRateIdx + 1;
24338 + DownRateIdx = CurrRateIdx -1;
24339 + }
24340 + else if (CurrRateIdx == 0)
24341 + {
24342 + UpRateIdx = CurrRateIdx + 1;
24343 + DownRateIdx = CurrRateIdx;
24344 + }
24345 + else if (CurrRateIdx == (TableSize - 1))
24346 + {
24347 + UpRateIdx = CurrRateIdx;
24348 + DownRateIdx = CurrRateIdx - 1;
24349 + }
24350 +
24351 + pCurrTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(CurrRateIdx+1)*5];
24352 +
24353 +#ifdef DOT11_N_SUPPORT
24354 + if ((Rssi > -65) && (pCurrTxRate->Mode >= MODE_HTMIX))
24355 + {
24356 + TrainUp = (pCurrTxRate->TrainUp + (pCurrTxRate->TrainUp >> 1));
24357 + TrainDown = (pCurrTxRate->TrainDown + (pCurrTxRate->TrainDown >> 1));
24358 + }
24359 + else
24360 +#endif // DOT11_N_SUPPORT //
24361 + {
24362 + TrainUp = pCurrTxRate->TrainUp;
24363 + TrainDown = pCurrTxRate->TrainDown;
24364 + }
24365 +
24366 + //pAd->DrsCounters.LastTimeTxRateChangeAction = pAd->DrsCounters.LastSecTxRateChangeAction;
24367 +
24368 + //
24369 + // Keep the last time TxRateChangeAction status.
24370 + //
24371 + pEntry->LastTimeTxRateChangeAction = pEntry->LastSecTxRateChangeAction;
24372 +
24373 +
24374 +
24375 + //
24376 + // CASE 1. when TX samples are fewer than 15, then decide TX rate solely on RSSI
24377 + // (criteria copied from RT2500 for Netopia case)
24378 + //
24379 + if (TxTotalCnt <= 15)
24380 + {
24381 + CHAR idx = 0;
24382 + UCHAR TxRateIdx;
24383 + //UCHAR MCS0 = 0, MCS1 = 0, MCS2 = 0, MCS3 = 0, MCS4 = 0, MCS7 = 0, MCS12 = 0, MCS13 = 0, MCS14 = 0, MCS15 = 0;
24384 + UCHAR MCS0 = 0, MCS1 = 0, MCS2 = 0, MCS3 = 0, MCS4 = 0, MCS5 =0, MCS6 = 0, MCS7 = 0;
24385 + UCHAR MCS12 = 0, MCS13 = 0, MCS14 = 0, MCS15 = 0;
24386 + UCHAR MCS20 = 0, MCS21 = 0, MCS22 = 0, MCS23 = 0; // 3*3
24387 +
24388 + // check the existence and index of each needed MCS
24389 + while (idx < pTable[0])
24390 + {
24391 + pCurrTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(idx+1)*5];
24392 +
24393 + if (pCurrTxRate->CurrMCS == MCS_0)
24394 + {
24395 + MCS0 = idx;
24396 + }
24397 + else if (pCurrTxRate->CurrMCS == MCS_1)
24398 + {
24399 + MCS1 = idx;
24400 + }
24401 + else if (pCurrTxRate->CurrMCS == MCS_2)
24402 + {
24403 + MCS2 = idx;
24404 + }
24405 + else if (pCurrTxRate->CurrMCS == MCS_3)
24406 + {
24407 + MCS3 = idx;
24408 + }
24409 + else if (pCurrTxRate->CurrMCS == MCS_4)
24410 + {
24411 + MCS4 = idx;
24412 + }
24413 + else if (pCurrTxRate->CurrMCS == MCS_5)
24414 + {
24415 + MCS5 = idx;
24416 + }
24417 + else if (pCurrTxRate->CurrMCS == MCS_6)
24418 + {
24419 + MCS6 = idx;
24420 + }
24421 + //else if (pCurrTxRate->CurrMCS == MCS_7)
24422 + else if ((pCurrTxRate->CurrMCS == MCS_7) && (pCurrTxRate->ShortGI == GI_800)) // prevent the highest MCS using short GI when 1T and low throughput
24423 + {
24424 + MCS7 = idx;
24425 + }
24426 + else if (pCurrTxRate->CurrMCS == MCS_12)
24427 + {
24428 + MCS12 = idx;
24429 + }
24430 + else if (pCurrTxRate->CurrMCS == MCS_13)
24431 + {
24432 + MCS13 = idx;
24433 + }
24434 + else if (pCurrTxRate->CurrMCS == MCS_14)
24435 + {
24436 + MCS14 = idx;
24437 + }
24438 + //else if ((pCurrTxRate->CurrMCS == MCS_15)/* && (pCurrTxRate->ShortGI == GI_800)*/) //we hope to use ShortGI as initial rate
24439 + else if ((pCurrTxRate->CurrMCS == MCS_15) && (pCurrTxRate->ShortGI == GI_800)) //we hope to use ShortGI as initial rate, however Atheros's chip has bugs when short GI
24440 + {
24441 + MCS15 = idx;
24442 + }
24443 + else if (pCurrTxRate->CurrMCS == MCS_20) // 3*3
24444 + {
24445 + MCS20 = idx;
24446 + }
24447 + else if (pCurrTxRate->CurrMCS == MCS_21)
24448 + {
24449 + MCS21 = idx;
24450 + }
24451 + else if (pCurrTxRate->CurrMCS == MCS_22)
24452 + {
24453 + MCS22 = idx;
24454 + }
24455 + else if (pCurrTxRate->CurrMCS == MCS_23)
24456 + {
24457 + MCS23 = idx;
24458 + }
24459 + idx ++;
24460 + }
24461 +
24462 + if (pAd->LatchRfRegs.Channel <= 14)
24463 + {
24464 + if (pAd->NicConfig2.field.ExternalLNAForG)
24465 + {
24466 + RssiOffset = 2;
24467 + }
24468 + else
24469 + {
24470 + RssiOffset = 5;
24471 + }
24472 + }
24473 + else
24474 + {
24475 + if (pAd->NicConfig2.field.ExternalLNAForA)
24476 + {
24477 + RssiOffset = 5;
24478 + }
24479 + else
24480 + {
24481 + RssiOffset = 8;
24482 + }
24483 + }
24484 +#ifdef DOT11_N_SUPPORT
24485 + /*if (MCS15)*/
24486 + if ((pTable == RateSwitchTable11BGN3S) ||
24487 + (pTable == RateSwitchTable11N3S) ||
24488 + (pTable == RateSwitchTable))
24489 + {// N mode with 3 stream // 3*3
24490 + if (MCS23 && (Rssi >= -70))
24491 + TxRateIdx = MCS15;
24492 + else if (MCS22 && (Rssi >= -72))
24493 + TxRateIdx = MCS14;
24494 + else if (MCS21 && (Rssi >= -76))
24495 + TxRateIdx = MCS13;
24496 + else if (MCS20 && (Rssi >= -78))
24497 + TxRateIdx = MCS12;
24498 + else if (MCS4 && (Rssi >= -82))
24499 + TxRateIdx = MCS4;
24500 + else if (MCS3 && (Rssi >= -84))
24501 + TxRateIdx = MCS3;
24502 + else if (MCS2 && (Rssi >= -86))
24503 + TxRateIdx = MCS2;
24504 + else if (MCS1 && (Rssi >= -88))
24505 + TxRateIdx = MCS1;
24506 + else
24507 + TxRateIdx = MCS0;
24508 + }
24509 + else if ((pTable == RateSwitchTable11BGN2S) || (pTable == RateSwitchTable11BGN2SForABand) ||(pTable == RateSwitchTable11N2S) ||(pTable == RateSwitchTable11N2SForABand)) // 3*3
24510 + {// N mode with 2 stream
24511 + if (MCS15 && (Rssi >= (-70+RssiOffset)))
24512 + TxRateIdx = MCS15;
24513 + else if (MCS14 && (Rssi >= (-72+RssiOffset)))
24514 + TxRateIdx = MCS14;
24515 + else if (MCS13 && (Rssi >= (-76+RssiOffset)))
24516 + TxRateIdx = MCS13;
24517 + else if (MCS12 && (Rssi >= (-78+RssiOffset)))
24518 + TxRateIdx = MCS12;
24519 + else if (MCS4 && (Rssi >= (-82+RssiOffset)))
24520 + TxRateIdx = MCS4;
24521 + else if (MCS3 && (Rssi >= (-84+RssiOffset)))
24522 + TxRateIdx = MCS3;
24523 + else if (MCS2 && (Rssi >= (-86+RssiOffset)))
24524 + TxRateIdx = MCS2;
24525 + else if (MCS1 && (Rssi >= (-88+RssiOffset)))
24526 + TxRateIdx = MCS1;
24527 + else
24528 + TxRateIdx = MCS0;
24529 + }
24530 + else if ((pTable == RateSwitchTable11BGN1S) || (pTable == RateSwitchTable11N1S))
24531 + {// N mode with 1 stream
24532 + if (MCS7 && (Rssi > (-72+RssiOffset)))
24533 + TxRateIdx = MCS7;
24534 + else if (MCS6 && (Rssi > (-74+RssiOffset)))
24535 + TxRateIdx = MCS6;
24536 + else if (MCS5 && (Rssi > (-77+RssiOffset)))
24537 + TxRateIdx = MCS5;
24538 + else if (MCS4 && (Rssi > (-79+RssiOffset)))
24539 + TxRateIdx = MCS4;
24540 + else if (MCS3 && (Rssi > (-81+RssiOffset)))
24541 + TxRateIdx = MCS3;
24542 + else if (MCS2 && (Rssi > (-83+RssiOffset)))
24543 + TxRateIdx = MCS2;
24544 + else if (MCS1 && (Rssi > (-86+RssiOffset)))
24545 + TxRateIdx = MCS1;
24546 + else
24547 + TxRateIdx = MCS0;
24548 + }
24549 + else
24550 +#endif // DOT11_N_SUPPORT //
24551 + {// Legacy mode
24552 + if (MCS7 && (Rssi > -70))
24553 + TxRateIdx = MCS7;
24554 + else if (MCS6 && (Rssi > -74))
24555 + TxRateIdx = MCS6;
24556 + else if (MCS5 && (Rssi > -78))
24557 + TxRateIdx = MCS5;
24558 + else if (MCS4 && (Rssi > -82))
24559 + TxRateIdx = MCS4;
24560 + else if (MCS4 == 0) // for B-only mode
24561 + TxRateIdx = MCS3;
24562 + else if (MCS3 && (Rssi > -85))
24563 + TxRateIdx = MCS3;
24564 + else if (MCS2 && (Rssi > -87))
24565 + TxRateIdx = MCS2;
24566 + else if (MCS1 && (Rssi > -90))
24567 + TxRateIdx = MCS1;
24568 + else
24569 + TxRateIdx = MCS0;
24570 + }
24571 +
24572 + {
24573 + pEntry->CurrTxRateIndex = TxRateIdx;
24574 + pNextTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(pEntry->CurrTxRateIndex+1)*5];
24575 + MlmeSetTxRate(pAd, pEntry, pNextTxRate);
24576 + }
24577 +
24578 + NdisZeroMemory(pEntry->TxQuality, sizeof(USHORT) * MAX_STEP_OF_TX_RATE_SWITCH);
24579 + NdisZeroMemory(pEntry->PER, sizeof(UCHAR) * MAX_STEP_OF_TX_RATE_SWITCH);
24580 + pEntry->fLastSecAccordingRSSI = TRUE;
24581 + // reset all OneSecTx counters
24582 + RESET_ONE_SEC_TX_CNT(pEntry);
24583 +
24584 + continue;
24585 + }
24586 +
24587 + if (pEntry->fLastSecAccordingRSSI == TRUE)
24588 + {
24589 + pEntry->fLastSecAccordingRSSI = FALSE;
24590 + pEntry->LastSecTxRateChangeAction = 0;
24591 + // reset all OneSecTx counters
24592 + RESET_ONE_SEC_TX_CNT(pEntry);
24593 +
24594 + continue;
24595 + }
24596 +
24597 + do
24598 + {
24599 + BOOLEAN bTrainUpDown = FALSE;
24600 +
24601 + pEntry->CurrTxRateStableTime ++;
24602 +
24603 + // downgrade TX quality if PER >= Rate-Down threshold
24604 + if (TxErrorRatio >= TrainDown)
24605 + {
24606 + bTrainUpDown = TRUE;
24607 + pEntry->TxQuality[CurrRateIdx] = DRS_TX_QUALITY_WORST_BOUND;
24608 + }
24609 + // upgrade TX quality if PER <= Rate-Up threshold
24610 + else if (TxErrorRatio <= TrainUp)
24611 + {
24612 + bTrainUpDown = TRUE;
24613 + bUpgradeQuality = TRUE;
24614 + if (pEntry->TxQuality[CurrRateIdx])
24615 + pEntry->TxQuality[CurrRateIdx] --; // quality very good in CurrRate
24616 +
24617 + if (pEntry->TxRateUpPenalty)
24618 + pEntry->TxRateUpPenalty --;
24619 + else if (pEntry->TxQuality[UpRateIdx])
24620 + pEntry->TxQuality[UpRateIdx] --; // may improve next UP rate's quality
24621 + }
24622 +
24623 + pEntry->PER[CurrRateIdx] = (UCHAR)TxErrorRatio;
24624 +
24625 + if (bTrainUpDown)
24626 + {
24627 + // perform DRS - consider TxRate Down first, then rate up.
24628 + if ((CurrRateIdx != DownRateIdx) && (pEntry->TxQuality[CurrRateIdx] >= DRS_TX_QUALITY_WORST_BOUND))
24629 + {
24630 + pEntry->CurrTxRateIndex = DownRateIdx;
24631 + }
24632 + else if ((CurrRateIdx != UpRateIdx) && (pEntry->TxQuality[UpRateIdx] <= 0))
24633 + {
24634 + pEntry->CurrTxRateIndex = UpRateIdx;
24635 + }
24636 + }
24637 + } while (FALSE);
24638 +
24639 + // if rate-up happen, clear all bad history of all TX rates
24640 + if (pEntry->CurrTxRateIndex > CurrRateIdx)
24641 + {
24642 + pEntry->CurrTxRateStableTime = 0;
24643 + pEntry->TxRateUpPenalty = 0;
24644 + pEntry->LastSecTxRateChangeAction = 1; // rate UP
24645 + NdisZeroMemory(pEntry->TxQuality, sizeof(USHORT) * MAX_STEP_OF_TX_RATE_SWITCH);
24646 + NdisZeroMemory(pEntry->PER, sizeof(UCHAR) * MAX_STEP_OF_TX_RATE_SWITCH);
24647 +
24648 + //
24649 + // For TxRate fast train up
24650 + //
24651 + if (!pAd->StaCfg.StaQuickResponeForRateUpTimerRunning)
24652 + {
24653 + RTMPSetTimer(&pAd->StaCfg.StaQuickResponeForRateUpTimer, 100);
24654 +
24655 + pAd->StaCfg.StaQuickResponeForRateUpTimerRunning = TRUE;
24656 + }
24657 + bTxRateChanged = TRUE;
24658 + }
24659 + // if rate-down happen, only clear DownRate's bad history
24660 + else if (pEntry->CurrTxRateIndex < CurrRateIdx)
24661 + {
24662 + pEntry->CurrTxRateStableTime = 0;
24663 + pEntry->TxRateUpPenalty = 0; // no penalty
24664 + pEntry->LastSecTxRateChangeAction = 2; // rate DOWN
24665 + pEntry->TxQuality[pEntry->CurrTxRateIndex] = 0;
24666 + pEntry->PER[pEntry->CurrTxRateIndex] = 0;
24667 +
24668 + //
24669 + // For TxRate fast train down
24670 + //
24671 + if (!pAd->StaCfg.StaQuickResponeForRateUpTimerRunning)
24672 + {
24673 + RTMPSetTimer(&pAd->StaCfg.StaQuickResponeForRateUpTimer, 100);
24674 +
24675 + pAd->StaCfg.StaQuickResponeForRateUpTimerRunning = TRUE;
24676 + }
24677 + bTxRateChanged = TRUE;
24678 + }
24679 + else
24680 + {
24681 + pEntry->LastSecTxRateChangeAction = 0; // rate no change
24682 + bTxRateChanged = FALSE;
24683 + }
24684 +
24685 + pEntry->LastTxOkCount = TxSuccess;
24686 +
24687 + // reset all OneSecTx counters
24688 + RESET_ONE_SEC_TX_CNT(pEntry);
24689 +
24690 + pNextTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(pEntry->CurrTxRateIndex+1)*5];
24691 + if (bTxRateChanged && pNextTxRate)
24692 + {
24693 + MlmeSetTxRate(pAd, pEntry, pNextTxRate);
24694 + }
24695 + }
24696 +}
24697 +
24698 +/*
24699 + ========================================================================
24700 + Routine Description:
24701 + Station side, Auto TxRate faster train up timer call back function.
24702 +
24703 + Arguments:
24704 + SystemSpecific1 - Not used.
24705 + FunctionContext - Pointer to our Adapter context.
24706 + SystemSpecific2 - Not used.
24707 + SystemSpecific3 - Not used.
24708 +
24709 + Return Value:
24710 + None
24711 +
24712 + ========================================================================
24713 +*/
24714 +VOID StaQuickResponeForRateUpExec(
24715 + IN PVOID SystemSpecific1,
24716 + IN PVOID FunctionContext,
24717 + IN PVOID SystemSpecific2,
24718 + IN PVOID SystemSpecific3)
24719 +{
24720 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)FunctionContext;
24721 + UCHAR UpRateIdx = 0, DownRateIdx = 0, CurrRateIdx = 0;
24722 + ULONG TxTotalCnt;
24723 + ULONG TxErrorRatio = 0;
24724 + BOOLEAN bTxRateChanged = TRUE; //, bUpgradeQuality = FALSE;
24725 + PRTMP_TX_RATE_SWITCH pCurrTxRate, pNextTxRate = NULL;
24726 + PUCHAR pTable;
24727 + UCHAR TableSize = 0;
24728 + UCHAR InitTxRateIdx = 0, TrainUp, TrainDown;
24729 + TX_STA_CNT1_STRUC StaTx1;
24730 + TX_STA_CNT0_STRUC TxStaCnt0;
24731 + CHAR Rssi, ratio;
24732 + ULONG TxRetransmit = 0, TxSuccess = 0, TxFailCount = 0;
24733 + MAC_TABLE_ENTRY *pEntry;
24734 + ULONG i;
24735 +
24736 + pAd->StaCfg.StaQuickResponeForRateUpTimerRunning = FALSE;
24737 +
24738 + //
24739 + // walk through MAC table, see if need to change AP's TX rate toward each entry
24740 + //
24741 + for (i = 1; i < MAX_LEN_OF_MAC_TABLE; i++)
24742 + {
24743 + pEntry = &pAd->MacTab.Content[i];
24744 +
24745 + // check if this entry need to switch rate automatically
24746 + if (RTMPCheckEntryEnableAutoRateSwitch(pAd, pEntry) == FALSE)
24747 + continue;
24748 +
24749 + //Rssi = RTMPMaxRssi(pAd, (CHAR)pAd->StaCfg.AvgRssi0, (CHAR)pAd->StaCfg.AvgRssi1, (CHAR)pAd->StaCfg.AvgRssi2);
24750 + if (pAd->Antenna.field.TxPath > 1)
24751 + Rssi = (pAd->StaCfg.RssiSample.AvgRssi0 + pAd->StaCfg.RssiSample.AvgRssi1) >> 1;
24752 + else
24753 + Rssi = pAd->StaCfg.RssiSample.AvgRssi0;
24754 +
24755 + CurrRateIdx = pAd->CommonCfg.TxRateIndex;
24756 +
24757 + MlmeSelectTxRateTable(pAd, pEntry, &pTable, &TableSize, &InitTxRateIdx);
24758 +
24759 + // decide the next upgrade rate and downgrade rate, if any
24760 + if ((CurrRateIdx > 0) && (CurrRateIdx < (TableSize - 1)))
24761 + {
24762 + UpRateIdx = CurrRateIdx + 1;
24763 + DownRateIdx = CurrRateIdx -1;
24764 + }
24765 + else if (CurrRateIdx == 0)
24766 + {
24767 + UpRateIdx = CurrRateIdx + 1;
24768 + DownRateIdx = CurrRateIdx;
24769 + }
24770 + else if (CurrRateIdx == (TableSize - 1))
24771 + {
24772 + UpRateIdx = CurrRateIdx;
24773 + DownRateIdx = CurrRateIdx - 1;
24774 + }
24775 +
24776 + pCurrTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(CurrRateIdx+1)*5];
24777 +
24778 +#ifdef DOT11_N_SUPPORT
24779 + if ((Rssi > -65) && (pCurrTxRate->Mode >= MODE_HTMIX))
24780 + {
24781 + TrainUp = (pCurrTxRate->TrainUp + (pCurrTxRate->TrainUp >> 1));
24782 + TrainDown = (pCurrTxRate->TrainDown + (pCurrTxRate->TrainDown >> 1));
24783 + }
24784 + else
24785 +#endif // DOT11_N_SUPPORT //
24786 + {
24787 + TrainUp = pCurrTxRate->TrainUp;
24788 + TrainDown = pCurrTxRate->TrainDown;
24789 + }
24790 +
24791 + if (pAd->MacTab.Size == 1)
24792 + {
24793 + // Update statistic counter
24794 + RTMP_IO_READ32(pAd, TX_STA_CNT0, &TxStaCnt0.word);
24795 + RTMP_IO_READ32(pAd, TX_STA_CNT1, &StaTx1.word);
24796 +
24797 + TxRetransmit = StaTx1.field.TxRetransmit;
24798 + TxSuccess = StaTx1.field.TxSuccess;
24799 + TxFailCount = TxStaCnt0.field.TxFailCount;
24800 + TxTotalCnt = TxRetransmit + TxSuccess + TxFailCount;
24801 +
24802 + pAd->RalinkCounters.OneSecTxRetryOkCount += StaTx1.field.TxRetransmit;
24803 + pAd->RalinkCounters.OneSecTxNoRetryOkCount += StaTx1.field.TxSuccess;
24804 + pAd->RalinkCounters.OneSecTxFailCount += TxStaCnt0.field.TxFailCount;
24805 + pAd->WlanCounters.TransmittedFragmentCount.u.LowPart += StaTx1.field.TxSuccess;
24806 + pAd->WlanCounters.RetryCount.u.LowPart += StaTx1.field.TxRetransmit;
24807 + pAd->WlanCounters.FailedCount.u.LowPart += TxStaCnt0.field.TxFailCount;
24808 +
24809 + if (TxTotalCnt)
24810 + TxErrorRatio = ((TxRetransmit + TxFailCount) * 100) / TxTotalCnt;
24811 + }
24812 + else
24813 + {
24814 + TxTotalCnt = pEntry->OneSecTxNoRetryOkCount +
24815 + pEntry->OneSecTxRetryOkCount +
24816 + pEntry->OneSecTxFailCount;
24817 +
24818 + if (TxTotalCnt)
24819 + TxErrorRatio = ((pEntry->OneSecTxRetryOkCount + pEntry->OneSecTxFailCount) * 100) / TxTotalCnt;
24820 + }
24821 +
24822 +
24823 + //
24824 + // CASE 1. when TX samples are fewer than 15, then decide TX rate solely on RSSI
24825 + // (criteria copied from RT2500 for Netopia case)
24826 + //
24827 + if (TxTotalCnt <= 12)
24828 + {
24829 + NdisZeroMemory(pAd->DrsCounters.TxQuality, sizeof(USHORT) * MAX_STEP_OF_TX_RATE_SWITCH);
24830 + NdisZeroMemory(pAd->DrsCounters.PER, sizeof(UCHAR) * MAX_STEP_OF_TX_RATE_SWITCH);
24831 +
24832 + if ((pAd->DrsCounters.LastSecTxRateChangeAction == 1) && (CurrRateIdx != DownRateIdx))
24833 + {
24834 + pAd->CommonCfg.TxRateIndex = DownRateIdx;
24835 + pAd->DrsCounters.TxQuality[CurrRateIdx] = DRS_TX_QUALITY_WORST_BOUND;
24836 + }
24837 + else if ((pAd->DrsCounters.LastSecTxRateChangeAction == 2) && (CurrRateIdx != UpRateIdx))
24838 + {
24839 + pAd->CommonCfg.TxRateIndex = UpRateIdx;
24840 + }
24841 +
24842 + DBGPRINT_RAW(RT_DEBUG_TRACE,("QuickDRS: TxTotalCnt <= 15, train back to original rate \n"));
24843 + return;
24844 + }
24845 +
24846 + do
24847 + {
24848 + ULONG OneSecTxNoRetryOKRationCount;
24849 +
24850 + if (pAd->DrsCounters.LastTimeTxRateChangeAction == 0)
24851 + ratio = 5;
24852 + else
24853 + ratio = 4;
24854 +
24855 + // downgrade TX quality if PER >= Rate-Down threshold
24856 + if (TxErrorRatio >= TrainDown)
24857 + {
24858 + pAd->DrsCounters.TxQuality[CurrRateIdx] = DRS_TX_QUALITY_WORST_BOUND;
24859 + }
24860 +
24861 + pAd->DrsCounters.PER[CurrRateIdx] = (UCHAR)TxErrorRatio;
24862 +
24863 + OneSecTxNoRetryOKRationCount = (TxSuccess * ratio);
24864 +
24865 + // perform DRS - consider TxRate Down first, then rate up.
24866 + if ((pAd->DrsCounters.LastSecTxRateChangeAction == 1) && (CurrRateIdx != DownRateIdx))
24867 + {
24868 + if ((pAd->DrsCounters.LastTxOkCount + 2) >= OneSecTxNoRetryOKRationCount)
24869 + {
24870 + pAd->CommonCfg.TxRateIndex = DownRateIdx;
24871 + pAd->DrsCounters.TxQuality[CurrRateIdx] = DRS_TX_QUALITY_WORST_BOUND;
24872 +
24873 + }
24874 +
24875 + }
24876 + else if ((pAd->DrsCounters.LastSecTxRateChangeAction == 2) && (CurrRateIdx != UpRateIdx))
24877 + {
24878 + if ((TxErrorRatio >= 50) || (TxErrorRatio >= TrainDown))
24879 + {
24880 +
24881 + }
24882 + else if ((pAd->DrsCounters.LastTxOkCount + 2) >= OneSecTxNoRetryOKRationCount)
24883 + {
24884 + pAd->CommonCfg.TxRateIndex = UpRateIdx;
24885 + }
24886 + }
24887 + }while (FALSE);
24888 +
24889 + // if rate-up happen, clear all bad history of all TX rates
24890 + if (pAd->CommonCfg.TxRateIndex > CurrRateIdx)
24891 + {
24892 + pAd->DrsCounters.TxRateUpPenalty = 0;
24893 + NdisZeroMemory(pAd->DrsCounters.TxQuality, sizeof(USHORT) * MAX_STEP_OF_TX_RATE_SWITCH);
24894 + NdisZeroMemory(pAd->DrsCounters.PER, sizeof(UCHAR) * MAX_STEP_OF_TX_RATE_SWITCH);
24895 + }
24896 + // if rate-down happen, only clear DownRate's bad history
24897 + else if (pAd->CommonCfg.TxRateIndex < CurrRateIdx)
24898 + {
24899 + DBGPRINT_RAW(RT_DEBUG_TRACE,("QuickDRS: --TX rate from %d to %d \n", CurrRateIdx, pAd->CommonCfg.TxRateIndex));
24900 +
24901 + pAd->DrsCounters.TxRateUpPenalty = 0; // no penalty
24902 + pAd->DrsCounters.TxQuality[pAd->CommonCfg.TxRateIndex] = 0;
24903 + pAd->DrsCounters.PER[pAd->CommonCfg.TxRateIndex] = 0;
24904 + }
24905 + else
24906 + {
24907 + bTxRateChanged = FALSE;
24908 + }
24909 +
24910 + pNextTxRate = (PRTMP_TX_RATE_SWITCH) &pTable[(pAd->CommonCfg.TxRateIndex+1)*5];
24911 + if (bTxRateChanged && pNextTxRate)
24912 + {
24913 + MlmeSetTxRate(pAd, pEntry, pNextTxRate);
24914 + }
24915 + }
24916 +}
24917 +
24918 +/*
24919 + ==========================================================================
24920 + Description:
24921 + This routine is executed periodically inside MlmePeriodicExec() after
24922 + association with an AP.
24923 + It checks if StaCfg.Psm is consistent with user policy (recorded in
24924 + StaCfg.WindowsPowerMode). If not, enforce user policy. However,
24925 + there're some conditions to consider:
24926 + 1. we don't support power-saving in ADHOC mode, so Psm=PWR_ACTIVE all
24927 + the time when Mibss==TRUE
24928 + 2. When link up in INFRA mode, Psm should not be switch to PWR_SAVE
24929 + if outgoing traffic available in TxRing or MgmtRing.
24930 + Output:
24931 + 1. change pAd->StaCfg.Psm to PWR_SAVE or leave it untouched
24932 +
24933 + IRQL = DISPATCH_LEVEL
24934 +
24935 + ==========================================================================
24936 + */
24937 +VOID MlmeCheckPsmChange(
24938 + IN PRTMP_ADAPTER pAd,
24939 + IN ULONG Now32)
24940 +{
24941 + ULONG PowerMode;
24942 +
24943 + // condition -
24944 + // 1. Psm maybe ON only happen in INFRASTRUCTURE mode
24945 + // 2. user wants either MAX_PSP or FAST_PSP
24946 + // 3. but current psm is not in PWR_SAVE
24947 + // 4. CNTL state machine is not doing SCANning
24948 + // 5. no TX SUCCESS event for the past 1-sec period
24949 +#ifdef NDIS51_MINIPORT
24950 + if (pAd->StaCfg.WindowsPowerProfile == NdisPowerProfileBattery)
24951 + PowerMode = pAd->StaCfg.WindowsBatteryPowerMode;
24952 + else
24953 +#endif
24954 + PowerMode = pAd->StaCfg.WindowsPowerMode;
24955 +
24956 + if (INFRA_ON(pAd) &&
24957 + (PowerMode != Ndis802_11PowerModeCAM) &&
24958 + (pAd->StaCfg.Psm == PWR_ACTIVE) &&
24959 + (pAd->Mlme.CntlMachine.CurrState == CNTL_IDLE))
24960 + {
24961 + NdisGetSystemUpTime(&pAd->Mlme.LastSendNULLpsmTime);
24962 + pAd->RalinkCounters.RxCountSinceLastNULL = 0;
24963 + MlmeSetPsmBit(pAd, PWR_SAVE);
24964 + if (!(pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable))
24965 + {
24966 + RTMPSendNullFrame(pAd, pAd->CommonCfg.TxRate, FALSE);
24967 + }
24968 + else
24969 + {
24970 + RTMPSendNullFrame(pAd, pAd->CommonCfg.TxRate, TRUE);
24971 + }
24972 + }
24973 +}
24974 +
24975 +// IRQL = PASSIVE_LEVEL
24976 +// IRQL = DISPATCH_LEVEL
24977 +VOID MlmeSetPsmBit(
24978 + IN PRTMP_ADAPTER pAd,
24979 + IN USHORT psm)
24980 +{
24981 + AUTO_RSP_CFG_STRUC csr4;
24982 +
24983 + pAd->StaCfg.Psm = psm;
24984 + RTMP_IO_READ32(pAd, AUTO_RSP_CFG, &csr4.word);
24985 + csr4.field.AckCtsPsmBit = (psm == PWR_SAVE)? 1:0;
24986 + RTMP_IO_WRITE32(pAd, AUTO_RSP_CFG, csr4.word);
24987 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeSetPsmBit = %d\n", psm));
24988 +}
24989 +#endif // CONFIG_STA_SUPPORT //
24990 +
24991 +
24992 +// IRQL = DISPATCH_LEVEL
24993 +VOID MlmeSetTxPreamble(
24994 + IN PRTMP_ADAPTER pAd,
24995 + IN USHORT TxPreamble)
24996 +{
24997 + AUTO_RSP_CFG_STRUC csr4;
24998 +
24999 + //
25000 + // Always use Long preamble before verifiation short preamble functionality works well.
25001 + // Todo: remove the following line if short preamble functionality works
25002 + //
25003 + //TxPreamble = Rt802_11PreambleLong;
25004 +
25005 + RTMP_IO_READ32(pAd, AUTO_RSP_CFG, &csr4.word);
25006 + if (TxPreamble == Rt802_11PreambleLong)
25007 + {
25008 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeSetTxPreamble (= LONG PREAMBLE)\n"));
25009 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED);
25010 + csr4.field.AutoResponderPreamble = 0;
25011 + }
25012 + else
25013 + {
25014 + // NOTE: 1Mbps should always use long preamble
25015 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeSetTxPreamble (= SHORT PREAMBLE)\n"));
25016 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED);
25017 + csr4.field.AutoResponderPreamble = 1;
25018 + }
25019 +
25020 + RTMP_IO_WRITE32(pAd, AUTO_RSP_CFG, csr4.word);
25021 +}
25022 +
25023 +/*
25024 + ==========================================================================
25025 + Description:
25026 + Update basic rate bitmap
25027 + ==========================================================================
25028 + */
25029 +
25030 +VOID UpdateBasicRateBitmap(
25031 + IN PRTMP_ADAPTER pAdapter)
25032 +{
25033 + INT i, j;
25034 + /* 1 2 5.5, 11, 6, 9, 12, 18, 24, 36, 48, 54 */
25035 + UCHAR rate[] = { 2, 4, 11, 22, 12, 18, 24, 36, 48, 72, 96, 108 };
25036 + UCHAR *sup_p = pAdapter->CommonCfg.SupRate;
25037 + UCHAR *ext_p = pAdapter->CommonCfg.ExtRate;
25038 + ULONG bitmap = pAdapter->CommonCfg.BasicRateBitmap;
25039 +
25040 +
25041 + /* if A mode, always use fix BasicRateBitMap */
25042 + //if (pAdapter->CommonCfg.Channel == PHY_11A)
25043 + if (pAdapter->CommonCfg.Channel > 14)
25044 + pAdapter->CommonCfg.BasicRateBitmap = 0x150; /* 6, 12, 24M */
25045 + /* End of if */
25046 +
25047 + if (pAdapter->CommonCfg.BasicRateBitmap > 4095)
25048 + {
25049 + /* (2 ^ MAX_LEN_OF_SUPPORTED_RATES) -1 */
25050 + return;
25051 + } /* End of if */
25052 +
25053 + for(i=0; i<MAX_LEN_OF_SUPPORTED_RATES; i++)
25054 + {
25055 + sup_p[i] &= 0x7f;
25056 + ext_p[i] &= 0x7f;
25057 + } /* End of for */
25058 +
25059 + for(i=0; i<MAX_LEN_OF_SUPPORTED_RATES; i++)
25060 + {
25061 + if (bitmap & (1 << i))
25062 + {
25063 + for(j=0; j<MAX_LEN_OF_SUPPORTED_RATES; j++)
25064 + {
25065 + if (sup_p[j] == rate[i])
25066 + sup_p[j] |= 0x80;
25067 + /* End of if */
25068 + } /* End of for */
25069 +
25070 + for(j=0; j<MAX_LEN_OF_SUPPORTED_RATES; j++)
25071 + {
25072 + if (ext_p[j] == rate[i])
25073 + ext_p[j] |= 0x80;
25074 + /* End of if */
25075 + } /* End of for */
25076 + } /* End of if */
25077 + } /* End of for */
25078 +} /* End of UpdateBasicRateBitmap */
25079 +
25080 +// IRQL = PASSIVE_LEVEL
25081 +// IRQL = DISPATCH_LEVEL
25082 +// bLinkUp is to identify the inital link speed.
25083 +// TRUE indicates the rate update at linkup, we should not try to set the rate at 54Mbps.
25084 +VOID MlmeUpdateTxRates(
25085 + IN PRTMP_ADAPTER pAd,
25086 + IN BOOLEAN bLinkUp,
25087 + IN UCHAR apidx)
25088 +{
25089 + int i, num;
25090 + UCHAR Rate = RATE_6, MaxDesire = RATE_1, MaxSupport = RATE_1;
25091 + UCHAR MinSupport = RATE_54;
25092 + ULONG BasicRateBitmap = 0;
25093 + UCHAR CurrBasicRate = RATE_1;
25094 + UCHAR *pSupRate, SupRateLen, *pExtRate, ExtRateLen;
25095 + PHTTRANSMIT_SETTING pHtPhy = NULL;
25096 + PHTTRANSMIT_SETTING pMaxHtPhy = NULL;
25097 + PHTTRANSMIT_SETTING pMinHtPhy = NULL;
25098 + BOOLEAN *auto_rate_cur_p;
25099 + UCHAR HtMcs = MCS_AUTO;
25100 +
25101 + // find max desired rate
25102 + UpdateBasicRateBitmap(pAd);
25103 +
25104 + num = 0;
25105 + auto_rate_cur_p = NULL;
25106 + for (i=0; i<MAX_LEN_OF_SUPPORTED_RATES; i++)
25107 + {
25108 + switch (pAd->CommonCfg.DesireRate[i] & 0x7f)
25109 + {
25110 + case 2: Rate = RATE_1; num++; break;
25111 + case 4: Rate = RATE_2; num++; break;
25112 + case 11: Rate = RATE_5_5; num++; break;
25113 + case 22: Rate = RATE_11; num++; break;
25114 + case 12: Rate = RATE_6; num++; break;
25115 + case 18: Rate = RATE_9; num++; break;
25116 + case 24: Rate = RATE_12; num++; break;
25117 + case 36: Rate = RATE_18; num++; break;
25118 + case 48: Rate = RATE_24; num++; break;
25119 + case 72: Rate = RATE_36; num++; break;
25120 + case 96: Rate = RATE_48; num++; break;
25121 + case 108: Rate = RATE_54; num++; break;
25122 + //default: Rate = RATE_1; break;
25123 + }
25124 + if (MaxDesire < Rate) MaxDesire = Rate;
25125 + }
25126 +
25127 +//===========================================================================
25128 +//===========================================================================
25129 +
25130 +#ifdef CONFIG_STA_SUPPORT
25131 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
25132 + {
25133 + pHtPhy = &pAd->StaCfg.HTPhyMode;
25134 + pMaxHtPhy = &pAd->StaCfg.MaxHTPhyMode;
25135 + pMinHtPhy = &pAd->StaCfg.MinHTPhyMode;
25136 +
25137 + auto_rate_cur_p = &pAd->StaCfg.bAutoTxRateSwitch;
25138 + HtMcs = pAd->StaCfg.DesiredTransmitSetting.field.MCS;
25139 +
25140 + if ((pAd->StaCfg.BssType == BSS_ADHOC) &&
25141 + (pAd->CommonCfg.PhyMode == PHY_11B) &&
25142 + (MaxDesire > RATE_11))
25143 + {
25144 + MaxDesire = RATE_11;
25145 + }
25146 + }
25147 +#endif // CONFIG_STA_SUPPORT //
25148 +
25149 + pAd->CommonCfg.MaxDesiredRate = MaxDesire;
25150 + pMinHtPhy->word = 0;
25151 + pMaxHtPhy->word = 0;
25152 + pHtPhy->word = 0;
25153 +
25154 + // Auto rate switching is enabled only if more than one DESIRED RATES are
25155 + // specified; otherwise disabled
25156 + if (num <= 1)
25157 + {
25158 + *auto_rate_cur_p = FALSE;
25159 + }
25160 + else
25161 + {
25162 + *auto_rate_cur_p = TRUE;
25163 + }
25164 +
25165 +#if 1
25166 + if (HtMcs != MCS_AUTO)
25167 + {
25168 + *auto_rate_cur_p = FALSE;
25169 + }
25170 + else
25171 + {
25172 + *auto_rate_cur_p = TRUE;
25173 + }
25174 +#endif
25175 +
25176 +#ifdef CONFIG_STA_SUPPORT
25177 + if ((ADHOC_ON(pAd) || INFRA_ON(pAd)) && (pAd->OpMode == OPMODE_STA))
25178 + {
25179 + pSupRate = &pAd->StaActive.SupRate[0];
25180 + pExtRate = &pAd->StaActive.ExtRate[0];
25181 + SupRateLen = pAd->StaActive.SupRateLen;
25182 + ExtRateLen = pAd->StaActive.ExtRateLen;
25183 + }
25184 + else
25185 +#endif // CONFIG_STA_SUPPORT //
25186 + {
25187 + pSupRate = &pAd->CommonCfg.SupRate[0];
25188 + pExtRate = &pAd->CommonCfg.ExtRate[0];
25189 + SupRateLen = pAd->CommonCfg.SupRateLen;
25190 + ExtRateLen = pAd->CommonCfg.ExtRateLen;
25191 + }
25192 +
25193 + // find max supported rate
25194 + for (i=0; i<SupRateLen; i++)
25195 + {
25196 + switch (pSupRate[i] & 0x7f)
25197 + {
25198 + case 2: Rate = RATE_1; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0001; break;
25199 + case 4: Rate = RATE_2; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0002; break;
25200 + case 11: Rate = RATE_5_5; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0004; break;
25201 + case 22: Rate = RATE_11; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0008; break;
25202 + case 12: Rate = RATE_6; /*if (pSupRate[i] & 0x80)*/ BasicRateBitmap |= 0x0010; break;
25203 + case 18: Rate = RATE_9; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0020; break;
25204 + case 24: Rate = RATE_12; /*if (pSupRate[i] & 0x80)*/ BasicRateBitmap |= 0x0040; break;
25205 + case 36: Rate = RATE_18; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0080; break;
25206 + case 48: Rate = RATE_24; /*if (pSupRate[i] & 0x80)*/ BasicRateBitmap |= 0x0100; break;
25207 + case 72: Rate = RATE_36; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0200; break;
25208 + case 96: Rate = RATE_48; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0400; break;
25209 + case 108: Rate = RATE_54; if (pSupRate[i] & 0x80) BasicRateBitmap |= 0x0800; break;
25210 + default: Rate = RATE_1; break;
25211 + }
25212 + if (MaxSupport < Rate) MaxSupport = Rate;
25213 +
25214 + if (MinSupport > Rate) MinSupport = Rate;
25215 + }
25216 +
25217 + for (i=0; i<ExtRateLen; i++)
25218 + {
25219 + switch (pExtRate[i] & 0x7f)
25220 + {
25221 + case 2: Rate = RATE_1; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0001; break;
25222 + case 4: Rate = RATE_2; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0002; break;
25223 + case 11: Rate = RATE_5_5; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0004; break;
25224 + case 22: Rate = RATE_11; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0008; break;
25225 + case 12: Rate = RATE_6; /*if (pExtRate[i] & 0x80)*/ BasicRateBitmap |= 0x0010; break;
25226 + case 18: Rate = RATE_9; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0020; break;
25227 + case 24: Rate = RATE_12; /*if (pExtRate[i] & 0x80)*/ BasicRateBitmap |= 0x0040; break;
25228 + case 36: Rate = RATE_18; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0080; break;
25229 + case 48: Rate = RATE_24; /*if (pExtRate[i] & 0x80)*/ BasicRateBitmap |= 0x0100; break;
25230 + case 72: Rate = RATE_36; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0200; break;
25231 + case 96: Rate = RATE_48; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0400; break;
25232 + case 108: Rate = RATE_54; if (pExtRate[i] & 0x80) BasicRateBitmap |= 0x0800; break;
25233 + default: Rate = RATE_1; break;
25234 + }
25235 + if (MaxSupport < Rate) MaxSupport = Rate;
25236 +
25237 + if (MinSupport > Rate) MinSupport = Rate;
25238 + }
25239 +
25240 + RTMP_IO_WRITE32(pAd, LEGACY_BASIC_RATE, BasicRateBitmap);
25241 +
25242 + // calculate the exptected ACK rate for each TX rate. This info is used to caculate
25243 + // the DURATION field of outgoing uniicast DATA/MGMT frame
25244 + for (i=0; i<MAX_LEN_OF_SUPPORTED_RATES; i++)
25245 + {
25246 + if (BasicRateBitmap & (0x01 << i))
25247 + CurrBasicRate = (UCHAR)i;
25248 + pAd->CommonCfg.ExpectedACKRate[i] = CurrBasicRate;
25249 + }
25250 +
25251 + DBGPRINT(RT_DEBUG_TRACE,("MlmeUpdateTxRates[MaxSupport = %d] = MaxDesire %d Mbps\n", RateIdToMbps[MaxSupport], RateIdToMbps[MaxDesire]));
25252 + // max tx rate = min {max desire rate, max supported rate}
25253 + if (MaxSupport < MaxDesire)
25254 + pAd->CommonCfg.MaxTxRate = MaxSupport;
25255 + else
25256 + pAd->CommonCfg.MaxTxRate = MaxDesire;
25257 +
25258 + pAd->CommonCfg.MinTxRate = MinSupport;
25259 + if (*auto_rate_cur_p)
25260 + {
25261 + short dbm = 0;
25262 +#ifdef CONFIG_STA_SUPPORT
25263 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
25264 + dbm = pAd->StaCfg.RssiSample.AvgRssi0 - pAd->BbpRssiToDbmDelta;
25265 +#endif // CONFIG_STA_SUPPORT //
25266 + if (bLinkUp == TRUE)
25267 + pAd->CommonCfg.TxRate = RATE_24;
25268 + else
25269 + pAd->CommonCfg.TxRate = pAd->CommonCfg.MaxTxRate;
25270 +
25271 + if (dbm < -75)
25272 + pAd->CommonCfg.TxRate = RATE_11;
25273 + else if (dbm < -70)
25274 + pAd->CommonCfg.TxRate = RATE_24;
25275 +
25276 + // should never exceed MaxTxRate (consider 11B-only mode)
25277 + if (pAd->CommonCfg.TxRate > pAd->CommonCfg.MaxTxRate)
25278 + pAd->CommonCfg.TxRate = pAd->CommonCfg.MaxTxRate;
25279 +
25280 + pAd->CommonCfg.TxRateIndex = 0;
25281 + }
25282 + else
25283 + {
25284 + pAd->CommonCfg.TxRate = pAd->CommonCfg.MaxTxRate;
25285 + pHtPhy->field.MCS = (pAd->CommonCfg.MaxTxRate > 3) ? (pAd->CommonCfg.MaxTxRate - 4) : pAd->CommonCfg.MaxTxRate;
25286 + pHtPhy->field.MODE = (pAd->CommonCfg.MaxTxRate > 3) ? MODE_OFDM : MODE_CCK;
25287 +
25288 + pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.STBC = pHtPhy->field.STBC;
25289 + pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.ShortGI = pHtPhy->field.ShortGI;
25290 + pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MCS = pHtPhy->field.MCS;
25291 + pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE = pHtPhy->field.MODE;
25292 + }
25293 +
25294 + if (pAd->CommonCfg.TxRate <= RATE_11)
25295 + {
25296 + pMaxHtPhy->field.MODE = MODE_CCK;
25297 + pMaxHtPhy->field.MCS = pAd->CommonCfg.TxRate;
25298 + pMinHtPhy->field.MCS = pAd->CommonCfg.MinTxRate;
25299 + }
25300 + else
25301 + {
25302 + pMaxHtPhy->field.MODE = MODE_OFDM;
25303 + pMaxHtPhy->field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.TxRate];
25304 + if (pAd->CommonCfg.MinTxRate >= RATE_6 && (pAd->CommonCfg.MinTxRate <= RATE_54))
25305 + {pMinHtPhy->field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MinTxRate];}
25306 + else
25307 + {pMinHtPhy->field.MCS = pAd->CommonCfg.MinTxRate;}
25308 + }
25309 +
25310 + pHtPhy->word = (pMaxHtPhy->word);
25311 + if (bLinkUp && (pAd->OpMode == OPMODE_STA))
25312 + {
25313 + pAd->MacTab.Content[BSSID_WCID].HTPhyMode.word = pHtPhy->word;
25314 + pAd->MacTab.Content[BSSID_WCID].MaxHTPhyMode.word = pMaxHtPhy->word;
25315 + pAd->MacTab.Content[BSSID_WCID].MinHTPhyMode.word = pMinHtPhy->word;
25316 + }
25317 + else
25318 + {
25319 + switch (pAd->CommonCfg.PhyMode)
25320 + {
25321 + case PHY_11BG_MIXED:
25322 + case PHY_11B:
25323 +#ifdef DOT11_N_SUPPORT
25324 + case PHY_11BGN_MIXED:
25325 +#endif // DOT11_N_SUPPORT //
25326 + pAd->CommonCfg.MlmeRate = RATE_1;
25327 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_CCK;
25328 + pAd->CommonCfg.MlmeTransmit.field.MCS = RATE_1;
25329 + pAd->CommonCfg.RtsRate = RATE_11;
25330 + break;
25331 + case PHY_11G:
25332 + case PHY_11A:
25333 +#ifdef DOT11_N_SUPPORT
25334 + case PHY_11AGN_MIXED:
25335 + case PHY_11GN_MIXED:
25336 + case PHY_11N_2_4G:
25337 + case PHY_11AN_MIXED:
25338 + case PHY_11N_5G:
25339 +#endif // DOT11_N_SUPPORT //
25340 + pAd->CommonCfg.MlmeRate = RATE_6;
25341 + pAd->CommonCfg.RtsRate = RATE_6;
25342 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_OFDM;
25343 + pAd->CommonCfg.MlmeTransmit.field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MlmeRate];
25344 + break;
25345 + case PHY_11ABG_MIXED:
25346 +#ifdef DOT11_N_SUPPORT
25347 + case PHY_11ABGN_MIXED:
25348 +#endif // DOT11_N_SUPPORT //
25349 + if (pAd->CommonCfg.Channel <= 14)
25350 + {
25351 + pAd->CommonCfg.MlmeRate = RATE_1;
25352 + pAd->CommonCfg.RtsRate = RATE_1;
25353 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_CCK;
25354 + pAd->CommonCfg.MlmeTransmit.field.MCS = RATE_1;
25355 + }
25356 + else
25357 + {
25358 + pAd->CommonCfg.MlmeRate = RATE_6;
25359 + pAd->CommonCfg.RtsRate = RATE_6;
25360 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_OFDM;
25361 + pAd->CommonCfg.MlmeTransmit.field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MlmeRate];
25362 + }
25363 + break;
25364 + default: // error
25365 + pAd->CommonCfg.MlmeRate = RATE_6;
25366 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_OFDM;
25367 + pAd->CommonCfg.MlmeTransmit.field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MlmeRate];
25368 + pAd->CommonCfg.RtsRate = RATE_1;
25369 + break;
25370 + }
25371 + //
25372 + // Keep Basic Mlme Rate.
25373 + //
25374 + pAd->MacTab.Content[MCAST_WCID].HTPhyMode.word = pAd->CommonCfg.MlmeTransmit.word;
25375 + if (pAd->CommonCfg.MlmeTransmit.field.MODE == MODE_OFDM)
25376 + pAd->MacTab.Content[MCAST_WCID].HTPhyMode.field.MCS = OfdmRateToRxwiMCS[RATE_24];
25377 + else
25378 + pAd->MacTab.Content[MCAST_WCID].HTPhyMode.field.MCS = RATE_1;
25379 + pAd->CommonCfg.BasicMlmeRate = pAd->CommonCfg.MlmeRate;
25380 + }
25381 +
25382 + DBGPRINT(RT_DEBUG_TRACE, (" MlmeUpdateTxRates (MaxDesire=%d, MaxSupport=%d, MaxTxRate=%d, MinRate=%d, Rate Switching =%d)\n",
25383 + RateIdToMbps[MaxDesire], RateIdToMbps[MaxSupport], RateIdToMbps[pAd->CommonCfg.MaxTxRate], RateIdToMbps[pAd->CommonCfg.MinTxRate],
25384 + /*OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_TX_RATE_SWITCH_ENABLED)*/*auto_rate_cur_p));
25385 + DBGPRINT(RT_DEBUG_TRACE, (" MlmeUpdateTxRates (TxRate=%d, RtsRate=%d, BasicRateBitmap=0x%04lx)\n",
25386 + RateIdToMbps[pAd->CommonCfg.TxRate], RateIdToMbps[pAd->CommonCfg.RtsRate], BasicRateBitmap));
25387 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeUpdateTxRates (MlmeTransmit=0x%x, MinHTPhyMode=%x, MaxHTPhyMode=0x%x, HTPhyMode=0x%x)\n",
25388 + pAd->CommonCfg.MlmeTransmit.word, pAd->MacTab.Content[BSSID_WCID].MinHTPhyMode.word ,pAd->MacTab.Content[BSSID_WCID].MaxHTPhyMode.word ,pAd->MacTab.Content[BSSID_WCID].HTPhyMode.word ));
25389 +}
25390 +
25391 +#ifdef DOT11_N_SUPPORT
25392 +/*
25393 + ==========================================================================
25394 + Description:
25395 + This function update HT Rate setting.
25396 + Input Wcid value is valid for 2 case :
25397 + 1. it's used for Station in infra mode that copy AP rate to Mactable.
25398 + 2. OR Station in adhoc mode to copy peer's HT rate to Mactable.
25399 +
25400 + IRQL = DISPATCH_LEVEL
25401 +
25402 + ==========================================================================
25403 + */
25404 +VOID MlmeUpdateHtTxRates(
25405 + IN PRTMP_ADAPTER pAd,
25406 + IN UCHAR apidx)
25407 +{
25408 + UCHAR StbcMcs; //j, StbcMcs, bitmask;
25409 + CHAR i; // 3*3
25410 + RT_HT_CAPABILITY *pRtHtCap = NULL;
25411 + RT_HT_PHY_INFO *pActiveHtPhy = NULL;
25412 + ULONG BasicMCS;
25413 + UCHAR j, bitmask;
25414 + PRT_HT_PHY_INFO pDesireHtPhy = NULL;
25415 + PHTTRANSMIT_SETTING pHtPhy = NULL;
25416 + PHTTRANSMIT_SETTING pMaxHtPhy = NULL;
25417 + PHTTRANSMIT_SETTING pMinHtPhy = NULL;
25418 + BOOLEAN *auto_rate_cur_p;
25419 +
25420 + DBGPRINT(RT_DEBUG_TRACE,("MlmeUpdateHtTxRates===> \n"));
25421 +
25422 + auto_rate_cur_p = NULL;
25423 +
25424 +#ifdef CONFIG_STA_SUPPORT
25425 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
25426 + {
25427 + pDesireHtPhy = &pAd->StaCfg.DesiredHtPhyInfo;
25428 + pActiveHtPhy = &pAd->StaCfg.DesiredHtPhyInfo;
25429 + pHtPhy = &pAd->StaCfg.HTPhyMode;
25430 + pMaxHtPhy = &pAd->StaCfg.MaxHTPhyMode;
25431 + pMinHtPhy = &pAd->StaCfg.MinHTPhyMode;
25432 +
25433 + auto_rate_cur_p = &pAd->StaCfg.bAutoTxRateSwitch;
25434 + }
25435 +#endif // CONFIG_STA_SUPPORT //
25436 +
25437 +#ifdef CONFIG_STA_SUPPORT
25438 + if ((ADHOC_ON(pAd) || INFRA_ON(pAd)) && (pAd->OpMode == OPMODE_STA))
25439 + {
25440 + if (pAd->StaActive.SupportedPhyInfo.bHtEnable == FALSE)
25441 + return;
25442 +
25443 + pRtHtCap = &pAd->StaActive.SupportedHtPhy;
25444 + pActiveHtPhy = &pAd->StaActive.SupportedPhyInfo;
25445 + StbcMcs = (UCHAR)pAd->MlmeAux.AddHtInfo.AddHtInfo3.StbcMcs;
25446 + BasicMCS =pAd->MlmeAux.AddHtInfo.MCSSet[0]+(pAd->MlmeAux.AddHtInfo.MCSSet[1]<<8)+(StbcMcs<<16);
25447 + if ((pAd->CommonCfg.DesiredHtPhy.TxSTBC) && (pRtHtCap->RxSTBC) && (pAd->Antenna.field.TxPath == 2))
25448 + pMaxHtPhy->field.STBC = STBC_USE;
25449 + else
25450 + pMaxHtPhy->field.STBC = STBC_NONE;
25451 + }
25452 + else
25453 +#endif // CONFIG_STA_SUPPORT //
25454 + {
25455 + if (pDesireHtPhy->bHtEnable == FALSE)
25456 + return;
25457 +
25458 + pRtHtCap = &pAd->CommonCfg.DesiredHtPhy;
25459 + StbcMcs = (UCHAR)pAd->CommonCfg.AddHTInfo.AddHtInfo3.StbcMcs;
25460 + BasicMCS = pAd->CommonCfg.AddHTInfo.MCSSet[0]+(pAd->CommonCfg.AddHTInfo.MCSSet[1]<<8)+(StbcMcs<<16);
25461 + if ((pAd->CommonCfg.DesiredHtPhy.TxSTBC) && (pRtHtCap->RxSTBC) && (pAd->Antenna.field.TxPath == 2))
25462 + pMaxHtPhy->field.STBC = STBC_USE;
25463 + else
25464 + pMaxHtPhy->field.STBC = STBC_NONE;
25465 + }
25466 +
25467 + // Decide MAX ht rate.
25468 + if ((pRtHtCap->GF) && (pAd->CommonCfg.DesiredHtPhy.GF))
25469 + pMaxHtPhy->field.MODE = MODE_HTGREENFIELD;
25470 + else
25471 + pMaxHtPhy->field.MODE = MODE_HTMIX;
25472 +
25473 + if ((pAd->CommonCfg.DesiredHtPhy.ChannelWidth) && (pRtHtCap->ChannelWidth))
25474 + pMaxHtPhy->field.BW = BW_40;
25475 + else
25476 + pMaxHtPhy->field.BW = BW_20;
25477 +
25478 + if (pMaxHtPhy->field.BW == BW_20)
25479 + pMaxHtPhy->field.ShortGI = (pAd->CommonCfg.DesiredHtPhy.ShortGIfor20 & pRtHtCap->ShortGIfor20);
25480 + else
25481 + pMaxHtPhy->field.ShortGI = (pAd->CommonCfg.DesiredHtPhy.ShortGIfor40 & pRtHtCap->ShortGIfor40);
25482 +
25483 + for (i=23; i>=0; i--) // 3*3
25484 + {
25485 + j = i/8;
25486 + bitmask = (1<<(i-(j*8)));
25487 +
25488 + if ((pActiveHtPhy->MCSSet[j] & bitmask) && (pDesireHtPhy->MCSSet[j] & bitmask))
25489 + {
25490 + pMaxHtPhy->field.MCS = i;
25491 + break;
25492 + }
25493 +
25494 + if (i==0)
25495 + break;
25496 + }
25497 +
25498 + // Copy MIN ht rate. rt2860???
25499 + pMinHtPhy->field.BW = BW_20;
25500 + pMinHtPhy->field.MCS = 0;
25501 + pMinHtPhy->field.STBC = 0;
25502 + pMinHtPhy->field.ShortGI = 0;
25503 + //If STA assigns fixed rate. update to fixed here.
25504 +#ifdef CONFIG_STA_SUPPORT
25505 + if ( (pAd->OpMode == OPMODE_STA) && (pDesireHtPhy->MCSSet[0] != 0xff))
25506 + {
25507 + if (pDesireHtPhy->MCSSet[4] != 0)
25508 + {
25509 + pMaxHtPhy->field.MCS = 32;
25510 + pMinHtPhy->field.MCS = 32;
25511 + DBGPRINT(RT_DEBUG_TRACE,("MlmeUpdateHtTxRates<=== Use Fixed MCS = %d\n",pMinHtPhy->field.MCS));
25512 + }
25513 +
25514 + for (i=23; (CHAR)i >= 0; i--) // 3*3
25515 + {
25516 + j = i/8;
25517 + bitmask = (1<<(i-(j*8)));
25518 + if ( (pDesireHtPhy->MCSSet[j] & bitmask) && (pActiveHtPhy->MCSSet[j] & bitmask))
25519 + {
25520 + pMaxHtPhy->field.MCS = i;
25521 + pMinHtPhy->field.MCS = i;
25522 + break;
25523 + }
25524 + if (i==0)
25525 + break;
25526 + }
25527 + }
25528 +#endif // CONFIG_STA_SUPPORT //
25529 +
25530 +
25531 + // Decide ht rate
25532 + pHtPhy->field.STBC = pMaxHtPhy->field.STBC;
25533 + pHtPhy->field.BW = pMaxHtPhy->field.BW;
25534 + pHtPhy->field.MODE = pMaxHtPhy->field.MODE;
25535 + pHtPhy->field.MCS = pMaxHtPhy->field.MCS;
25536 + pHtPhy->field.ShortGI = pMaxHtPhy->field.ShortGI;
25537 +
25538 + // use default now. rt2860
25539 + if (pDesireHtPhy->MCSSet[0] != 0xff)
25540 + *auto_rate_cur_p = FALSE;
25541 + else
25542 + *auto_rate_cur_p = TRUE;
25543 +
25544 + DBGPRINT(RT_DEBUG_TRACE, (" MlmeUpdateHtTxRates<---.AMsduSize = %d \n", pAd->CommonCfg.DesiredHtPhy.AmsduSize ));
25545 + DBGPRINT(RT_DEBUG_TRACE,("TX: MCS[0] = %x (choose %d), BW = %d, ShortGI = %d, MODE = %d, \n", pActiveHtPhy->MCSSet[0],pHtPhy->field.MCS,
25546 + pHtPhy->field.BW, pHtPhy->field.ShortGI, pHtPhy->field.MODE));
25547 + DBGPRINT(RT_DEBUG_TRACE,("MlmeUpdateHtTxRates<=== \n"));
25548 +}
25549 +#endif // DOT11_N_SUPPORT //
25550 +
25551 +// IRQL = DISPATCH_LEVEL
25552 +VOID MlmeRadioOff(
25553 + IN PRTMP_ADAPTER pAd)
25554 +{
25555 + RT28XX_MLME_RADIO_OFF(pAd);
25556 +}
25557 +
25558 +// IRQL = DISPATCH_LEVEL
25559 +VOID MlmeRadioOn(
25560 + IN PRTMP_ADAPTER pAd)
25561 +{
25562 + RT28XX_MLME_RADIO_ON(pAd);
25563 +}
25564 +
25565 +// ===========================================================================================
25566 +// bss_table.c
25567 +// ===========================================================================================
25568 +
25569 +
25570 +/*! \brief initialize BSS table
25571 + * \param p_tab pointer to the table
25572 + * \return none
25573 + * \pre
25574 + * \post
25575 +
25576 + IRQL = PASSIVE_LEVEL
25577 + IRQL = DISPATCH_LEVEL
25578 +
25579 + */
25580 +VOID BssTableInit(
25581 + IN BSS_TABLE *Tab)
25582 +{
25583 + int i;
25584 +
25585 + Tab->BssNr = 0;
25586 + Tab->BssOverlapNr = 0;
25587 + for (i = 0; i < MAX_LEN_OF_BSS_TABLE; i++)
25588 + {
25589 + NdisZeroMemory(&Tab->BssEntry[i], sizeof(BSS_ENTRY));
25590 + Tab->BssEntry[i].Rssi = -127; // initial the rssi as a minimum value
25591 + }
25592 +}
25593 +
25594 +#ifdef DOT11_N_SUPPORT
25595 +VOID BATableInit(
25596 + IN PRTMP_ADAPTER pAd,
25597 + IN BA_TABLE *Tab)
25598 +{
25599 + int i;
25600 +
25601 + Tab->numAsOriginator = 0;
25602 + Tab->numAsRecipient = 0;
25603 + NdisAllocateSpinLock(&pAd->BATabLock);
25604 + for (i = 0; i < MAX_LEN_OF_BA_REC_TABLE; i++)
25605 + {
25606 + Tab->BARecEntry[i].REC_BA_Status = Recipient_NONE;
25607 + NdisAllocateSpinLock(&(Tab->BARecEntry[i].RxReRingLock));
25608 + }
25609 + for (i = 0; i < MAX_LEN_OF_BA_ORI_TABLE; i++)
25610 + {
25611 + Tab->BAOriEntry[i].ORI_BA_Status = Originator_NONE;
25612 + }
25613 +}
25614 +#endif // DOT11_N_SUPPORT //
25615 +
25616 +/*! \brief search the BSS table by SSID
25617 + * \param p_tab pointer to the bss table
25618 + * \param ssid SSID string
25619 + * \return index of the table, BSS_NOT_FOUND if not in the table
25620 + * \pre
25621 + * \post
25622 + * \note search by sequential search
25623 +
25624 + IRQL = DISPATCH_LEVEL
25625 +
25626 + */
25627 +ULONG BssTableSearch(
25628 + IN BSS_TABLE *Tab,
25629 + IN PUCHAR pBssid,
25630 + IN UCHAR Channel)
25631 +{
25632 + UCHAR i;
25633 +
25634 + for (i = 0; i < Tab->BssNr; i++)
25635 + {
25636 + //
25637 + // Some AP that support A/B/G mode that may used the same BSSID on 11A and 11B/G.
25638 + // We should distinguish this case.
25639 + //
25640 + if ((((Tab->BssEntry[i].Channel <= 14) && (Channel <= 14)) ||
25641 + ((Tab->BssEntry[i].Channel > 14) && (Channel > 14))) &&
25642 + MAC_ADDR_EQUAL(Tab->BssEntry[i].Bssid, pBssid))
25643 + {
25644 + return i;
25645 + }
25646 + }
25647 + return (ULONG)BSS_NOT_FOUND;
25648 +}
25649 +
25650 +ULONG BssSsidTableSearch(
25651 + IN BSS_TABLE *Tab,
25652 + IN PUCHAR pBssid,
25653 + IN PUCHAR pSsid,
25654 + IN UCHAR SsidLen,
25655 + IN UCHAR Channel)
25656 +{
25657 + UCHAR i;
25658 +
25659 + for (i = 0; i < Tab->BssNr; i++)
25660 + {
25661 + //
25662 + // Some AP that support A/B/G mode that may used the same BSSID on 11A and 11B/G.
25663 + // We should distinguish this case.
25664 + //
25665 + if ((((Tab->BssEntry[i].Channel <= 14) && (Channel <= 14)) ||
25666 + ((Tab->BssEntry[i].Channel > 14) && (Channel > 14))) &&
25667 + MAC_ADDR_EQUAL(Tab->BssEntry[i].Bssid, pBssid) &&
25668 + SSID_EQUAL(pSsid, SsidLen, Tab->BssEntry[i].Ssid, Tab->BssEntry[i].SsidLen))
25669 + {
25670 + return i;
25671 + }
25672 + }
25673 + return (ULONG)BSS_NOT_FOUND;
25674 +}
25675 +
25676 +ULONG BssTableSearchWithSSID(
25677 + IN BSS_TABLE *Tab,
25678 + IN PUCHAR Bssid,
25679 + IN PUCHAR pSsid,
25680 + IN UCHAR SsidLen,
25681 + IN UCHAR Channel)
25682 +{
25683 + UCHAR i;
25684 +
25685 + for (i = 0; i < Tab->BssNr; i++)
25686 + {
25687 + if ((((Tab->BssEntry[i].Channel <= 14) && (Channel <= 14)) ||
25688 + ((Tab->BssEntry[i].Channel > 14) && (Channel > 14))) &&
25689 + MAC_ADDR_EQUAL(&(Tab->BssEntry[i].Bssid), Bssid) &&
25690 + (SSID_EQUAL(pSsid, SsidLen, Tab->BssEntry[i].Ssid, Tab->BssEntry[i].SsidLen) ||
25691 + (NdisEqualMemory(pSsid, ZeroSsid, SsidLen)) ||
25692 + (NdisEqualMemory(Tab->BssEntry[i].Ssid, ZeroSsid, Tab->BssEntry[i].SsidLen))))
25693 + {
25694 + return i;
25695 + }
25696 + }
25697 + return (ULONG)BSS_NOT_FOUND;
25698 +}
25699 +
25700 +// IRQL = DISPATCH_LEVEL
25701 +VOID BssTableDeleteEntry(
25702 + IN OUT BSS_TABLE *Tab,
25703 + IN PUCHAR pBssid,
25704 + IN UCHAR Channel)
25705 +{
25706 + UCHAR i, j;
25707 +
25708 + for (i = 0; i < Tab->BssNr; i++)
25709 + {
25710 + if ((Tab->BssEntry[i].Channel == Channel) &&
25711 + (MAC_ADDR_EQUAL(Tab->BssEntry[i].Bssid, pBssid)))
25712 + {
25713 + for (j = i; j < Tab->BssNr - 1; j++)
25714 + {
25715 + NdisMoveMemory(&(Tab->BssEntry[j]), &(Tab->BssEntry[j + 1]), sizeof(BSS_ENTRY));
25716 + }
25717 + NdisZeroMemory(&(Tab->BssEntry[Tab->BssNr - 1]), sizeof(BSS_ENTRY));
25718 + Tab->BssNr -= 1;
25719 + return;
25720 + }
25721 + }
25722 +}
25723 +
25724 +#ifdef DOT11_N_SUPPORT
25725 +/*
25726 + ========================================================================
25727 + Routine Description:
25728 + Delete the Originator Entry in BAtable. Or decrease numAs Originator by 1 if needed.
25729 +
25730 + Arguments:
25731 + // IRQL = DISPATCH_LEVEL
25732 + ========================================================================
25733 +*/
25734 +VOID BATableDeleteORIEntry(
25735 + IN OUT PRTMP_ADAPTER pAd,
25736 + IN BA_ORI_ENTRY *pBAORIEntry)
25737 +{
25738 +
25739 + if (pBAORIEntry->ORI_BA_Status != Originator_NONE)
25740 + {
25741 + NdisAcquireSpinLock(&pAd->BATabLock);
25742 + if (pBAORIEntry->ORI_BA_Status == Originator_Done)
25743 + {
25744 + pAd->BATable.numAsOriginator -= 1;
25745 + DBGPRINT(RT_DEBUG_TRACE, ("BATableDeleteORIEntry numAsOriginator= %ld\n", pAd->BATable.numAsRecipient));
25746 + // Erase Bitmap flag.
25747 + }
25748 + pAd->MacTab.Content[pBAORIEntry->Wcid].TXBAbitmap &= (~(1<<(pBAORIEntry->TID) )); // If STA mode, erase flag here
25749 + pAd->MacTab.Content[pBAORIEntry->Wcid].BAOriWcidArray[pBAORIEntry->TID] = 0; // If STA mode, erase flag here
25750 + pBAORIEntry->ORI_BA_Status = Originator_NONE;
25751 + pBAORIEntry->Token = 1;
25752 + // Not clear Sequence here.
25753 + NdisReleaseSpinLock(&pAd->BATabLock);
25754 + }
25755 +}
25756 +#endif // DOT11_N_SUPPORT //
25757 +
25758 +/*! \brief
25759 + * \param
25760 + * \return
25761 + * \pre
25762 + * \post
25763 +
25764 + IRQL = DISPATCH_LEVEL
25765 +
25766 + */
25767 +VOID BssEntrySet(
25768 + IN PRTMP_ADAPTER pAd,
25769 + OUT BSS_ENTRY *pBss,
25770 + IN PUCHAR pBssid,
25771 + IN CHAR Ssid[],
25772 + IN UCHAR SsidLen,
25773 + IN UCHAR BssType,
25774 + IN USHORT BeaconPeriod,
25775 + IN PCF_PARM pCfParm,
25776 + IN USHORT AtimWin,
25777 + IN USHORT CapabilityInfo,
25778 + IN UCHAR SupRate[],
25779 + IN UCHAR SupRateLen,
25780 + IN UCHAR ExtRate[],
25781 + IN UCHAR ExtRateLen,
25782 + IN HT_CAPABILITY_IE *pHtCapability,
25783 + IN ADD_HT_INFO_IE *pAddHtInfo, // AP might use this additional ht info IE
25784 + IN UCHAR HtCapabilityLen,
25785 + IN UCHAR AddHtInfoLen,
25786 + IN UCHAR NewExtChanOffset,
25787 + IN UCHAR Channel,
25788 + IN CHAR Rssi,
25789 + IN LARGE_INTEGER TimeStamp,
25790 + IN UCHAR CkipFlag,
25791 + IN PEDCA_PARM pEdcaParm,
25792 + IN PQOS_CAPABILITY_PARM pQosCapability,
25793 + IN PQBSS_LOAD_PARM pQbssLoad,
25794 + IN USHORT LengthVIE,
25795 + IN PNDIS_802_11_VARIABLE_IEs pVIE)
25796 +{
25797 + COPY_MAC_ADDR(pBss->Bssid, pBssid);
25798 + // Default Hidden SSID to be TRUE, it will be turned to FALSE after coping SSID
25799 + pBss->Hidden = 1;
25800 + if (SsidLen > 0)
25801 + {
25802 + // For hidden SSID AP, it might send beacon with SSID len equal to 0
25803 + // Or send beacon /probe response with SSID len matching real SSID length,
25804 + // but SSID is all zero. such as "00-00-00-00" with length 4.
25805 + // We have to prevent this case overwrite correct table
25806 + if (NdisEqualMemory(Ssid, ZeroSsid, SsidLen) == 0)
25807 + {
25808 + NdisZeroMemory(pBss->Ssid, MAX_LEN_OF_SSID);
25809 + NdisMoveMemory(pBss->Ssid, Ssid, SsidLen);
25810 + pBss->SsidLen = SsidLen;
25811 + pBss->Hidden = 0;
25812 + }
25813 + }
25814 + else
25815 + pBss->SsidLen = 0;
25816 + pBss->BssType = BssType;
25817 + pBss->BeaconPeriod = BeaconPeriod;
25818 + if (BssType == BSS_INFRA)
25819 + {
25820 + if (pCfParm->bValid)
25821 + {
25822 + pBss->CfpCount = pCfParm->CfpCount;
25823 + pBss->CfpPeriod = pCfParm->CfpPeriod;
25824 + pBss->CfpMaxDuration = pCfParm->CfpMaxDuration;
25825 + pBss->CfpDurRemaining = pCfParm->CfpDurRemaining;
25826 + }
25827 + }
25828 + else
25829 + {
25830 + pBss->AtimWin = AtimWin;
25831 + }
25832 +
25833 + pBss->CapabilityInfo = CapabilityInfo;
25834 + // The privacy bit indicate security is ON, it maight be WEP, TKIP or AES
25835 + // Combine with AuthMode, they will decide the connection methods.
25836 + pBss->Privacy = CAP_IS_PRIVACY_ON(pBss->CapabilityInfo);
25837 + ASSERT(SupRateLen <= MAX_LEN_OF_SUPPORTED_RATES);
25838 + if (SupRateLen <= MAX_LEN_OF_SUPPORTED_RATES)
25839 + NdisMoveMemory(pBss->SupRate, SupRate, SupRateLen);
25840 + else
25841 + NdisMoveMemory(pBss->SupRate, SupRate, MAX_LEN_OF_SUPPORTED_RATES);
25842 + pBss->SupRateLen = SupRateLen;
25843 + ASSERT(ExtRateLen <= MAX_LEN_OF_SUPPORTED_RATES);
25844 + NdisMoveMemory(pBss->ExtRate, ExtRate, ExtRateLen);
25845 + NdisMoveMemory(&pBss->HtCapability, pHtCapability, HtCapabilityLen);
25846 + NdisMoveMemory(&pBss->AddHtInfo, pAddHtInfo, AddHtInfoLen);
25847 + pBss->NewExtChanOffset = NewExtChanOffset;
25848 + pBss->ExtRateLen = ExtRateLen;
25849 + pBss->Channel = Channel;
25850 + pBss->CentralChannel = Channel;
25851 + pBss->Rssi = Rssi;
25852 + // Update CkipFlag. if not exists, the value is 0x0
25853 + pBss->CkipFlag = CkipFlag;
25854 +
25855 + // New for microsoft Fixed IEs
25856 + NdisMoveMemory(pBss->FixIEs.Timestamp, &TimeStamp, 8);
25857 + pBss->FixIEs.BeaconInterval = BeaconPeriod;
25858 + pBss->FixIEs.Capabilities = CapabilityInfo;
25859 +
25860 + // New for microsoft Variable IEs
25861 + if (LengthVIE != 0)
25862 + {
25863 + pBss->VarIELen = LengthVIE;
25864 + NdisMoveMemory(pBss->VarIEs, pVIE, pBss->VarIELen);
25865 + }
25866 + else
25867 + {
25868 + pBss->VarIELen = 0;
25869 + }
25870 +
25871 + pBss->AddHtInfoLen = 0;
25872 + pBss->HtCapabilityLen = 0;
25873 +#ifdef DOT11_N_SUPPORT
25874 + if (HtCapabilityLen> 0)
25875 + {
25876 + pBss->HtCapabilityLen = HtCapabilityLen;
25877 + NdisMoveMemory(&pBss->HtCapability, pHtCapability, HtCapabilityLen);
25878 + if (AddHtInfoLen > 0)
25879 + {
25880 + pBss->AddHtInfoLen = AddHtInfoLen;
25881 + NdisMoveMemory(&pBss->AddHtInfo, pAddHtInfo, AddHtInfoLen);
25882 +
25883 + if ((pAddHtInfo->ControlChan > 2)&& (pAddHtInfo->AddHtInfo.ExtChanOffset == EXTCHA_BELOW) && (pHtCapability->HtCapInfo.ChannelWidth == BW_40))
25884 + {
25885 + pBss->CentralChannel = pAddHtInfo->ControlChan - 2;
25886 + }
25887 + else if ((pAddHtInfo->AddHtInfo.ExtChanOffset == EXTCHA_ABOVE) && (pHtCapability->HtCapInfo.ChannelWidth == BW_40))
25888 + {
25889 + pBss->CentralChannel = pAddHtInfo->ControlChan + 2;
25890 + }
25891 + }
25892 + }
25893 +#endif // DOT11_N_SUPPORT //
25894 +
25895 + BssCipherParse(pBss);
25896 +
25897 + // new for QOS
25898 + if (pEdcaParm)
25899 + NdisMoveMemory(&pBss->EdcaParm, pEdcaParm, sizeof(EDCA_PARM));
25900 + else
25901 + pBss->EdcaParm.bValid = FALSE;
25902 + if (pQosCapability)
25903 + NdisMoveMemory(&pBss->QosCapability, pQosCapability, sizeof(QOS_CAPABILITY_PARM));
25904 + else
25905 + pBss->QosCapability.bValid = FALSE;
25906 + if (pQbssLoad)
25907 + NdisMoveMemory(&pBss->QbssLoad, pQbssLoad, sizeof(QBSS_LOAD_PARM));
25908 + else
25909 + pBss->QbssLoad.bValid = FALSE;
25910 +
25911 +#ifdef CONFIG_STA_SUPPORT
25912 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
25913 + {
25914 + PEID_STRUCT pEid;
25915 + USHORT Length = 0;
25916 +
25917 +
25918 + NdisZeroMemory(&pBss->WpaIE.IE[0], MAX_CUSTOM_LEN);
25919 + NdisZeroMemory(&pBss->RsnIE.IE[0], MAX_CUSTOM_LEN);
25920 +#ifdef EXT_BUILD_CHANNEL_LIST
25921 + NdisZeroMemory(&pBss->CountryString[0], 3);
25922 + pBss->bHasCountryIE = FALSE;
25923 +#endif // EXT_BUILD_CHANNEL_LIST //
25924 + pEid = (PEID_STRUCT) pVIE;
25925 + while ((Length + 2 + (USHORT)pEid->Len) <= LengthVIE)
25926 + {
25927 + switch(pEid->Eid)
25928 + {
25929 + case IE_WPA:
25930 + if (NdisEqualMemory(pEid->Octet, WPA_OUI, 4))
25931 + {
25932 + if ((pEid->Len + 2) > MAX_CUSTOM_LEN)
25933 + {
25934 + pBss->WpaIE.IELen = 0;
25935 + break;
25936 + }
25937 + pBss->WpaIE.IELen = pEid->Len + 2;
25938 + NdisMoveMemory(pBss->WpaIE.IE, pEid, pBss->WpaIE.IELen);
25939 + }
25940 + break;
25941 + case IE_RSN:
25942 + if (NdisEqualMemory(pEid->Octet + 2, RSN_OUI, 3))
25943 + {
25944 + if ((pEid->Len + 2) > MAX_CUSTOM_LEN)
25945 + {
25946 + pBss->RsnIE.IELen = 0;
25947 + break;
25948 + }
25949 + pBss->RsnIE.IELen = pEid->Len + 2;
25950 + NdisMoveMemory(pBss->RsnIE.IE, pEid, pBss->RsnIE.IELen);
25951 + }
25952 + break;
25953 +#ifdef EXT_BUILD_CHANNEL_LIST
25954 + case IE_COUNTRY:
25955 + NdisMoveMemory(&pBss->CountryString[0], pEid->Octet, 3);
25956 + pBss->bHasCountryIE = TRUE;
25957 + break;
25958 +#endif // EXT_BUILD_CHANNEL_LIST //
25959 + }
25960 + Length = Length + 2 + (USHORT)pEid->Len; // Eid[1] + Len[1]+ content[Len]
25961 + pEid = (PEID_STRUCT)((UCHAR*)pEid + 2 + pEid->Len);
25962 + }
25963 + }
25964 +#endif // CONFIG_STA_SUPPORT //
25965 +}
25966 +
25967 +/*!
25968 + * \brief insert an entry into the bss table
25969 + * \param p_tab The BSS table
25970 + * \param Bssid BSSID
25971 + * \param ssid SSID
25972 + * \param ssid_len Length of SSID
25973 + * \param bss_type
25974 + * \param beacon_period
25975 + * \param timestamp
25976 + * \param p_cf
25977 + * \param atim_win
25978 + * \param cap
25979 + * \param rates
25980 + * \param rates_len
25981 + * \param channel_idx
25982 + * \return none
25983 + * \pre
25984 + * \post
25985 + * \note If SSID is identical, the old entry will be replaced by the new one
25986 +
25987 + IRQL = DISPATCH_LEVEL
25988 +
25989 + */
25990 +ULONG BssTableSetEntry(
25991 + IN PRTMP_ADAPTER pAd,
25992 + OUT BSS_TABLE *Tab,
25993 + IN PUCHAR pBssid,
25994 + IN CHAR Ssid[],
25995 + IN UCHAR SsidLen,
25996 + IN UCHAR BssType,
25997 + IN USHORT BeaconPeriod,
25998 + IN CF_PARM *CfParm,
25999 + IN USHORT AtimWin,
26000 + IN USHORT CapabilityInfo,
26001 + IN UCHAR SupRate[],
26002 + IN UCHAR SupRateLen,
26003 + IN UCHAR ExtRate[],
26004 + IN UCHAR ExtRateLen,
26005 + IN HT_CAPABILITY_IE *pHtCapability,
26006 + IN ADD_HT_INFO_IE *pAddHtInfo, // AP might use this additional ht info IE
26007 + IN UCHAR HtCapabilityLen,
26008 + IN UCHAR AddHtInfoLen,
26009 + IN UCHAR NewExtChanOffset,
26010 + IN UCHAR ChannelNo,
26011 + IN CHAR Rssi,
26012 + IN LARGE_INTEGER TimeStamp,
26013 + IN UCHAR CkipFlag,
26014 + IN PEDCA_PARM pEdcaParm,
26015 + IN PQOS_CAPABILITY_PARM pQosCapability,
26016 + IN PQBSS_LOAD_PARM pQbssLoad,
26017 + IN USHORT LengthVIE,
26018 + IN PNDIS_802_11_VARIABLE_IEs pVIE)
26019 +{
26020 + ULONG Idx;
26021 +
26022 + Idx = BssTableSearchWithSSID(Tab, pBssid, Ssid, SsidLen, ChannelNo);
26023 + if (Idx == BSS_NOT_FOUND)
26024 + {
26025 + if (Tab->BssNr >= MAX_LEN_OF_BSS_TABLE)
26026 + {
26027 + //
26028 + // It may happen when BSS Table was full.
26029 + // The desired AP will not be added into BSS Table
26030 + // In this case, if we found the desired AP then overwrite BSS Table.
26031 + //
26032 + if(!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
26033 + {
26034 + if (MAC_ADDR_EQUAL(pAd->MlmeAux.Bssid, pBssid) ||
26035 + SSID_EQUAL(pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen, Ssid, SsidLen))
26036 + {
26037 + Idx = Tab->BssOverlapNr;
26038 + BssEntrySet(pAd, &Tab->BssEntry[Idx], pBssid, Ssid, SsidLen, BssType, BeaconPeriod, CfParm, AtimWin,
26039 + CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen,pHtCapability, pAddHtInfo,HtCapabilityLen, AddHtInfoLen,
26040 + NewExtChanOffset, ChannelNo, Rssi, TimeStamp, CkipFlag, pEdcaParm, pQosCapability, pQbssLoad, LengthVIE, pVIE);
26041 + Tab->BssOverlapNr = (Tab->BssOverlapNr++) % MAX_LEN_OF_BSS_TABLE;
26042 + }
26043 + return Idx;
26044 + }
26045 + else
26046 + {
26047 + return BSS_NOT_FOUND;
26048 + }
26049 + }
26050 + Idx = Tab->BssNr;
26051 + BssEntrySet(pAd, &Tab->BssEntry[Idx], pBssid, Ssid, SsidLen, BssType, BeaconPeriod, CfParm, AtimWin,
26052 + CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen,pHtCapability, pAddHtInfo,HtCapabilityLen, AddHtInfoLen,
26053 + NewExtChanOffset, ChannelNo, Rssi, TimeStamp, CkipFlag, pEdcaParm, pQosCapability, pQbssLoad, LengthVIE, pVIE);
26054 + Tab->BssNr++;
26055 + }
26056 + else
26057 + {
26058 + BssEntrySet(pAd, &Tab->BssEntry[Idx], pBssid, Ssid, SsidLen, BssType, BeaconPeriod,CfParm, AtimWin,
26059 + CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen,pHtCapability, pAddHtInfo,HtCapabilityLen, AddHtInfoLen,
26060 + NewExtChanOffset, ChannelNo, Rssi, TimeStamp, CkipFlag, pEdcaParm, pQosCapability, pQbssLoad, LengthVIE, pVIE);
26061 + }
26062 +
26063 + return Idx;
26064 +}
26065 +
26066 +#ifdef CONFIG_STA_SUPPORT
26067 +#ifdef DOT11_N_SUPPORT
26068 +#ifdef DOT11N_DRAFT3
26069 +VOID TriEventInit(
26070 + IN PRTMP_ADAPTER pAd)
26071 +{
26072 + UCHAR i;
26073 +
26074 + for (i = 0;i < MAX_TRIGGER_EVENT;i++)
26075 + pAd->CommonCfg.TriggerEventTab.EventA[i].bValid = FALSE;
26076 +
26077 + pAd->CommonCfg.TriggerEventTab.EventANo = 0;
26078 + pAd->CommonCfg.TriggerEventTab.EventBCountDown = 0;
26079 +}
26080 +
26081 +ULONG TriEventTableSetEntry(
26082 + IN PRTMP_ADAPTER pAd,
26083 + OUT TRIGGER_EVENT_TAB *Tab,
26084 + IN PUCHAR pBssid,
26085 + IN HT_CAPABILITY_IE *pHtCapability,
26086 + IN UCHAR HtCapabilityLen,
26087 + IN UCHAR RegClass,
26088 + IN UCHAR ChannelNo)
26089 +{
26090 + // Event A
26091 + if (HtCapabilityLen == 0)
26092 + {
26093 + if (Tab->EventANo < MAX_TRIGGER_EVENT)
26094 + {
26095 + RTMPMoveMemory(Tab->EventA[Tab->EventANo].BSSID, pBssid, 6);
26096 + Tab->EventA[Tab->EventANo].bValid = TRUE;
26097 + Tab->EventA[Tab->EventANo].Channel = ChannelNo;
26098 + Tab->EventA[Tab->EventANo].CDCounter = pAd->CommonCfg.Dot11BssWidthChanTranDelay;
26099 + if (RegClass != 0)
26100 + {
26101 + // Beacon has Regulatory class IE. So use beacon's
26102 + Tab->EventA[Tab->EventANo].RegClass = RegClass;
26103 + }
26104 + else
26105 + {
26106 + // Use Station's Regulatory class instead.
26107 + if (pAd->StaActive.SupportedHtPhy.bHtEnable == TRUE)
26108 + {
26109 + if (pAd->CommonCfg.CentralChannel > pAd->CommonCfg.Channel)
26110 + {
26111 + Tab->EventA[Tab->EventANo].RegClass = 32;
26112 + }
26113 + else if (pAd->CommonCfg.CentralChannel < pAd->CommonCfg.Channel)
26114 + Tab->EventA[Tab->EventANo].RegClass = 33;
26115 + }
26116 + else
26117 + Tab->EventA[Tab->EventANo].RegClass = ??;
26118 +
26119 + }
26120 +
26121 + Tab->EventANo ++;
26122 + }
26123 + }
26124 + else if (pHtCapability->HtCapInfo.Intolerant40)
26125 + {
26126 + Tab->EventBCountDown = pAd->CommonCfg.Dot11BssWidthChanTranDelay;
26127 + }
26128 +
26129 +}
26130 +
26131 +/*
26132 + ========================================================================
26133 + Routine Description:
26134 + Trigger Event table Maintainence called once every second.
26135 +
26136 + Arguments:
26137 + // IRQL = DISPATCH_LEVEL
26138 + ========================================================================
26139 +*/
26140 +VOID TriEventCounterMaintenance(
26141 + IN PRTMP_ADAPTER pAd)
26142 +{
26143 + UCHAR i;
26144 + BOOLEAN bNotify = FALSE;
26145 + for (i = 0;i < MAX_TRIGGER_EVENT;i++)
26146 + {
26147 + if (pAd->CommonCfg.TriggerEventTab.EventA[i].bValid && (pAd->CommonCfg.TriggerEventTab.EventA[i].CDCounter > 0))
26148 + {
26149 + pAd->CommonCfg.TriggerEventTab.EventA[i].CDCounter--;
26150 + if (pAd->CommonCfg.TriggerEventTab.EventA[i].CDCounter == 0)
26151 + {
26152 + pAd->CommonCfg.TriggerEventTab.EventA[i].bValid = FALSE;
26153 + pAd->CommonCfg.TriggerEventTab.EventANo --;
26154 + // Need to send 20/40 Coexistence Notify frame if has status change.
26155 + bNotify = TRUE;
26156 + }
26157 + }
26158 + }
26159 + if (pAd->CommonCfg.TriggerEventTab.EventBCountDown > 0)
26160 + {
26161 + pAd->CommonCfg.TriggerEventTab.EventBCountDown--;
26162 + if (pAd->CommonCfg.TriggerEventTab.EventBCountDown == 0)
26163 + bNotify = TRUE;
26164 + }
26165 +
26166 + if (bNotify == TRUE)
26167 + Update2040CoexistFrameAndNotify(pAd, BSSID_WCID, TRUE);
26168 +}
26169 +#endif // DOT11N_DRAFT3 //
26170 +#endif // DOT11_N_SUPPORT //
26171 +
26172 +// IRQL = DISPATCH_LEVEL
26173 +VOID BssTableSsidSort(
26174 + IN PRTMP_ADAPTER pAd,
26175 + OUT BSS_TABLE *OutTab,
26176 + IN CHAR Ssid[],
26177 + IN UCHAR SsidLen)
26178 +{
26179 + INT i;
26180 + BssTableInit(OutTab);
26181 +
26182 + for (i = 0; i < pAd->ScanTab.BssNr; i++)
26183 + {
26184 + BSS_ENTRY *pInBss = &pAd->ScanTab.BssEntry[i];
26185 + BOOLEAN bIsHiddenApIncluded = FALSE;
26186 +
26187 + if (((pAd->CommonCfg.bIEEE80211H == 1) &&
26188 + (pAd->MlmeAux.Channel > 14) &&
26189 + RadarChannelCheck(pAd, pInBss->Channel))
26190 +#ifdef CARRIER_DETECTION_SUPPORT // Roger sync Carrier
26191 + || (pAd->CommonCfg.CarrierDetect.Enable == TRUE)
26192 +#endif // CARRIER_DETECTION_SUPPORT //
26193 + )
26194 + {
26195 + if (pInBss->Hidden)
26196 + bIsHiddenApIncluded = TRUE;
26197 + }
26198 +
26199 + if ((pInBss->BssType == pAd->StaCfg.BssType) &&
26200 + (SSID_EQUAL(Ssid, SsidLen, pInBss->Ssid, pInBss->SsidLen) || bIsHiddenApIncluded))
26201 + {
26202 + BSS_ENTRY *pOutBss = &OutTab->BssEntry[OutTab->BssNr];
26203 +
26204 +
26205 +#ifdef EXT_BUILD_CHANNEL_LIST
26206 + // If no Country IE exists no Connection will be established when IEEE80211dClientMode is strict.
26207 + if ((pAd->StaCfg.IEEE80211dClientMode == Rt802_11_D_Strict) &&
26208 + (pInBss->bHasCountryIE == FALSE))
26209 + {
26210 + DBGPRINT(RT_DEBUG_TRACE,("StaCfg.IEEE80211dClientMode == Rt802_11_D_Strict, but this AP doesn't have country IE.\n"));
26211 + continue;
26212 + }
26213 +#endif // EXT_BUILD_CHANNEL_LIST //
26214 +
26215 +#ifdef DOT11_N_SUPPORT
26216 + // 2.4G/5G N only mode
26217 + if ((pInBss->HtCapabilityLen == 0) &&
26218 + ((pAd->CommonCfg.PhyMode == PHY_11N_2_4G) || (pAd->CommonCfg.PhyMode == PHY_11N_5G)))
26219 + {
26220 + DBGPRINT(RT_DEBUG_TRACE,("STA is in N-only Mode, this AP don't have Ht capability in Beacon.\n"));
26221 + continue;
26222 + }
26223 +#endif // DOT11_N_SUPPORT //
26224 +
26225 + // New for WPA2
26226 + // Check the Authmode first
26227 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
26228 + {
26229 + // Check AuthMode and AuthModeAux for matching, in case AP support dual-mode
26230 + if ((pAd->StaCfg.AuthMode != pInBss->AuthMode) && (pAd->StaCfg.AuthMode != pInBss->AuthModeAux))
26231 + // None matched
26232 + continue;
26233 +
26234 + // Check cipher suite, AP must have more secured cipher than station setting
26235 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK))
26236 + {
26237 + // If it's not mixed mode, we should only let BSS pass with the same encryption
26238 + if (pInBss->WPA.bMixMode == FALSE)
26239 + if (pAd->StaCfg.WepStatus != pInBss->WPA.GroupCipher)
26240 + continue;
26241 +
26242 + // check group cipher
26243 + if (pAd->StaCfg.WepStatus < pInBss->WPA.GroupCipher)
26244 + continue;
26245 +
26246 + // check pairwise cipher, skip if none matched
26247 + // If profile set to AES, let it pass without question.
26248 + // If profile set to TKIP, we must find one mateched
26249 + if ((pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) &&
26250 + (pAd->StaCfg.WepStatus != pInBss->WPA.PairCipher) &&
26251 + (pAd->StaCfg.WepStatus != pInBss->WPA.PairCipherAux))
26252 + continue;
26253 + }
26254 + else if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
26255 + {
26256 + // If it's not mixed mode, we should only let BSS pass with the same encryption
26257 + if (pInBss->WPA2.bMixMode == FALSE)
26258 + if (pAd->StaCfg.WepStatus != pInBss->WPA2.GroupCipher)
26259 + continue;
26260 +
26261 + // check group cipher
26262 + if (pAd->StaCfg.WepStatus < pInBss->WPA2.GroupCipher)
26263 + continue;
26264 +
26265 + // check pairwise cipher, skip if none matched
26266 + // If profile set to AES, let it pass without question.
26267 + // If profile set to TKIP, we must find one mateched
26268 + if ((pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) &&
26269 + (pAd->StaCfg.WepStatus != pInBss->WPA2.PairCipher) &&
26270 + (pAd->StaCfg.WepStatus != pInBss->WPA2.PairCipherAux))
26271 + continue;
26272 + }
26273 + }
26274 + // Bss Type matched, SSID matched.
26275 + // We will check wepstatus for qualification Bss
26276 + else if (pAd->StaCfg.WepStatus != pInBss->WepStatus)
26277 + {
26278 + DBGPRINT(RT_DEBUG_TRACE,("StaCfg.WepStatus=%d, while pInBss->WepStatus=%d\n", pAd->StaCfg.WepStatus, pInBss->WepStatus));
26279 + //
26280 + // For the SESv2 case, we will not qualify WepStatus.
26281 + //
26282 + if (!pInBss->bSES)
26283 + continue;
26284 + }
26285 +
26286 + // Since the AP is using hidden SSID, and we are trying to connect to ANY
26287 + // It definitely will fail. So, skip it.
26288 + // CCX also require not even try to connect it!!
26289 + if (SsidLen == 0)
26290 + continue;
26291 +
26292 +#ifdef DOT11_N_SUPPORT
26293 + // If both station and AP use 40MHz, still need to check if the 40MHZ band's legality in my country region
26294 + // If this 40MHz wideband is not allowed in my country list, use bandwidth 20MHZ instead,
26295 + if ((pInBss->CentralChannel != pInBss->Channel) &&
26296 + (pAd->CommonCfg.RegTransmitSetting.field.BW == BW_40))
26297 + {
26298 + if (RTMPCheckChannel(pAd, pInBss->CentralChannel, pInBss->Channel) == FALSE)
26299 + {
26300 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
26301 + SetCommonHT(pAd);
26302 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_40;
26303 + }
26304 + else
26305 + {
26306 + if (pAd->CommonCfg.DesiredHtPhy.ChannelWidth == BAND_WIDTH_20)
26307 + {
26308 + SetCommonHT(pAd);
26309 + }
26310 + }
26311 + }
26312 +#endif // DOT11_N_SUPPORT //
26313 +
26314 + // copy matching BSS from InTab to OutTab
26315 + NdisMoveMemory(pOutBss, pInBss, sizeof(BSS_ENTRY));
26316 +
26317 + OutTab->BssNr++;
26318 + }
26319 + else if ((pInBss->BssType == pAd->StaCfg.BssType) && (SsidLen == 0))
26320 + {
26321 + BSS_ENTRY *pOutBss = &OutTab->BssEntry[OutTab->BssNr];
26322 +
26323 +
26324 +#ifdef DOT11_N_SUPPORT
26325 + // 2.4G/5G N only mode
26326 + if ((pInBss->HtCapabilityLen == 0) &&
26327 + ((pAd->CommonCfg.PhyMode == PHY_11N_2_4G) || (pAd->CommonCfg.PhyMode == PHY_11N_5G)))
26328 + {
26329 + DBGPRINT(RT_DEBUG_TRACE,("STA is in N-only Mode, this AP don't have Ht capability in Beacon.\n"));
26330 + continue;
26331 + }
26332 +#endif // DOT11_N_SUPPORT //
26333 +
26334 + // New for WPA2
26335 + // Check the Authmode first
26336 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
26337 + {
26338 + // Check AuthMode and AuthModeAux for matching, in case AP support dual-mode
26339 + if ((pAd->StaCfg.AuthMode != pInBss->AuthMode) && (pAd->StaCfg.AuthMode != pInBss->AuthModeAux))
26340 + // None matched
26341 + continue;
26342 +
26343 + // Check cipher suite, AP must have more secured cipher than station setting
26344 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK))
26345 + {
26346 + // If it's not mixed mode, we should only let BSS pass with the same encryption
26347 + if (pInBss->WPA.bMixMode == FALSE)
26348 + if (pAd->StaCfg.WepStatus != pInBss->WPA.GroupCipher)
26349 + continue;
26350 +
26351 + // check group cipher
26352 + if (pAd->StaCfg.WepStatus < pInBss->WPA.GroupCipher)
26353 + continue;
26354 +
26355 + // check pairwise cipher, skip if none matched
26356 + // If profile set to AES, let it pass without question.
26357 + // If profile set to TKIP, we must find one mateched
26358 + if ((pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) &&
26359 + (pAd->StaCfg.WepStatus != pInBss->WPA.PairCipher) &&
26360 + (pAd->StaCfg.WepStatus != pInBss->WPA.PairCipherAux))
26361 + continue;
26362 + }
26363 + else if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
26364 + {
26365 + // If it's not mixed mode, we should only let BSS pass with the same encryption
26366 + if (pInBss->WPA2.bMixMode == FALSE)
26367 + if (pAd->StaCfg.WepStatus != pInBss->WPA2.GroupCipher)
26368 + continue;
26369 +
26370 + // check group cipher
26371 + if (pAd->StaCfg.WepStatus < pInBss->WPA2.GroupCipher)
26372 + continue;
26373 +
26374 + // check pairwise cipher, skip if none matched
26375 + // If profile set to AES, let it pass without question.
26376 + // If profile set to TKIP, we must find one mateched
26377 + if ((pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) &&
26378 + (pAd->StaCfg.WepStatus != pInBss->WPA2.PairCipher) &&
26379 + (pAd->StaCfg.WepStatus != pInBss->WPA2.PairCipherAux))
26380 + continue;
26381 + }
26382 + }
26383 + // Bss Type matched, SSID matched.
26384 + // We will check wepstatus for qualification Bss
26385 + else if (pAd->StaCfg.WepStatus != pInBss->WepStatus)
26386 + continue;
26387 +
26388 +#ifdef DOT11_N_SUPPORT
26389 + // If both station and AP use 40MHz, still need to check if the 40MHZ band's legality in my country region
26390 + // If this 40MHz wideband is not allowed in my country list, use bandwidth 20MHZ instead,
26391 + if ((pInBss->CentralChannel != pInBss->Channel) &&
26392 + (pAd->CommonCfg.RegTransmitSetting.field.BW == BW_40))
26393 + {
26394 + if (RTMPCheckChannel(pAd, pInBss->CentralChannel, pInBss->Channel) == FALSE)
26395 + {
26396 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
26397 + SetCommonHT(pAd);
26398 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_40;
26399 + }
26400 + }
26401 +#endif // DOT11_N_SUPPORT //
26402 +
26403 + // copy matching BSS from InTab to OutTab
26404 + NdisMoveMemory(pOutBss, pInBss, sizeof(BSS_ENTRY));
26405 +
26406 + OutTab->BssNr++;
26407 + }
26408 +
26409 + if (OutTab->BssNr >= MAX_LEN_OF_BSS_TABLE)
26410 + break;
26411 + }
26412 +
26413 + BssTableSortByRssi(OutTab);
26414 +}
26415 +
26416 +
26417 +// IRQL = DISPATCH_LEVEL
26418 +VOID BssTableSortByRssi(
26419 + IN OUT BSS_TABLE *OutTab)
26420 +{
26421 + INT i, j;
26422 + BSS_ENTRY TmpBss;
26423 +
26424 + for (i = 0; i < OutTab->BssNr - 1; i++)
26425 + {
26426 + for (j = i+1; j < OutTab->BssNr; j++)
26427 + {
26428 + if (OutTab->BssEntry[j].Rssi > OutTab->BssEntry[i].Rssi)
26429 + {
26430 + NdisMoveMemory(&TmpBss, &OutTab->BssEntry[j], sizeof(BSS_ENTRY));
26431 + NdisMoveMemory(&OutTab->BssEntry[j], &OutTab->BssEntry[i], sizeof(BSS_ENTRY));
26432 + NdisMoveMemory(&OutTab->BssEntry[i], &TmpBss, sizeof(BSS_ENTRY));
26433 + }
26434 + }
26435 + }
26436 +}
26437 +#endif // CONFIG_STA_SUPPORT //
26438 +
26439 +
26440 +VOID BssCipherParse(
26441 + IN OUT PBSS_ENTRY pBss)
26442 +{
26443 + PEID_STRUCT pEid;
26444 + PUCHAR pTmp;
26445 + PRSN_IE_HEADER_STRUCT pRsnHeader;
26446 + PCIPHER_SUITE_STRUCT pCipher;
26447 + PAKM_SUITE_STRUCT pAKM;
26448 + USHORT Count;
26449 + INT Length;
26450 + NDIS_802_11_ENCRYPTION_STATUS TmpCipher;
26451 +
26452 + //
26453 + // WepStatus will be reset later, if AP announce TKIP or AES on the beacon frame.
26454 + //
26455 + if (pBss->Privacy)
26456 + {
26457 + pBss->WepStatus = Ndis802_11WEPEnabled;
26458 + }
26459 + else
26460 + {
26461 + pBss->WepStatus = Ndis802_11WEPDisabled;
26462 + }
26463 + // Set default to disable & open authentication before parsing variable IE
26464 + pBss->AuthMode = Ndis802_11AuthModeOpen;
26465 + pBss->AuthModeAux = Ndis802_11AuthModeOpen;
26466 +
26467 + // Init WPA setting
26468 + pBss->WPA.PairCipher = Ndis802_11WEPDisabled;
26469 + pBss->WPA.PairCipherAux = Ndis802_11WEPDisabled;
26470 + pBss->WPA.GroupCipher = Ndis802_11WEPDisabled;
26471 + pBss->WPA.RsnCapability = 0;
26472 + pBss->WPA.bMixMode = FALSE;
26473 +
26474 + // Init WPA2 setting
26475 + pBss->WPA2.PairCipher = Ndis802_11WEPDisabled;
26476 + pBss->WPA2.PairCipherAux = Ndis802_11WEPDisabled;
26477 + pBss->WPA2.GroupCipher = Ndis802_11WEPDisabled;
26478 + pBss->WPA2.RsnCapability = 0;
26479 + pBss->WPA2.bMixMode = FALSE;
26480 +
26481 +
26482 + Length = (INT) pBss->VarIELen;
26483 +
26484 + while (Length > 0)
26485 + {
26486 + // Parse cipher suite base on WPA1 & WPA2, they should be parsed differently
26487 + pTmp = ((PUCHAR) pBss->VarIEs) + pBss->VarIELen - Length;
26488 + pEid = (PEID_STRUCT) pTmp;
26489 + switch (pEid->Eid)
26490 + {
26491 + case IE_WPA:
26492 + //Parse Cisco IE_WPA (LEAP, CCKM, etc.)
26493 + if ( NdisEqualMemory((pTmp+8), CISCO_OUI, 3))
26494 + {
26495 + pTmp += 11;
26496 + switch (*pTmp)
26497 + {
26498 + case 1:
26499 + case 5: // Although WEP is not allowed in WPA related auth mode, we parse it anyway
26500 + pBss->WepStatus = Ndis802_11Encryption1Enabled;
26501 + pBss->WPA.PairCipher = Ndis802_11Encryption1Enabled;
26502 + pBss->WPA.GroupCipher = Ndis802_11Encryption1Enabled;
26503 + break;
26504 + case 2:
26505 + pBss->WepStatus = Ndis802_11Encryption2Enabled;
26506 + pBss->WPA.PairCipher = Ndis802_11Encryption1Enabled;
26507 + pBss->WPA.GroupCipher = Ndis802_11Encryption1Enabled;
26508 + break;
26509 + case 4:
26510 + pBss->WepStatus = Ndis802_11Encryption3Enabled;
26511 + pBss->WPA.PairCipher = Ndis802_11Encryption1Enabled;
26512 + pBss->WPA.GroupCipher = Ndis802_11Encryption1Enabled;
26513 + break;
26514 + default:
26515 + break;
26516 + }
26517 +
26518 + // if Cisco IE_WPA, break
26519 + break;
26520 + }
26521 + else if (NdisEqualMemory(pEid->Octet, SES_OUI, 3) && (pEid->Len == 7))
26522 + {
26523 + pBss->bSES = TRUE;
26524 + break;
26525 + }
26526 + else if (NdisEqualMemory(pEid->Octet, WPA_OUI, 4) != 1)
26527 + {
26528 + // if unsupported vendor specific IE
26529 + break;
26530 + }
26531 + // Skip OUI, version, and multicast suite
26532 + // This part should be improved in the future when AP supported multiple cipher suite.
26533 + // For now, it's OK since almost all APs have fixed cipher suite supported.
26534 + // pTmp = (PUCHAR) pEid->Octet;
26535 + pTmp += 11;
26536 +
26537 + // Cipher Suite Selectors from Spec P802.11i/D3.2 P26.
26538 + // Value Meaning
26539 + // 0 None
26540 + // 1 WEP-40
26541 + // 2 Tkip
26542 + // 3 WRAP
26543 + // 4 AES
26544 + // 5 WEP-104
26545 + // Parse group cipher
26546 + switch (*pTmp)
26547 + {
26548 + case 1:
26549 + case 5: // Although WEP is not allowed in WPA related auth mode, we parse it anyway
26550 + pBss->WPA.GroupCipher = Ndis802_11Encryption1Enabled;
26551 + break;
26552 + case 2:
26553 + pBss->WPA.GroupCipher = Ndis802_11Encryption2Enabled;
26554 + break;
26555 + case 4:
26556 + pBss->WPA.GroupCipher = Ndis802_11Encryption3Enabled;
26557 + break;
26558 + default:
26559 + break;
26560 + }
26561 + // number of unicast suite
26562 + pTmp += 1;
26563 +
26564 + // skip all unicast cipher suites
26565 + //Count = *(PUSHORT) pTmp;
26566 + Count = (pTmp[1]<<8) + pTmp[0];
26567 + pTmp += sizeof(USHORT);
26568 +
26569 + // Parsing all unicast cipher suite
26570 + while (Count > 0)
26571 + {
26572 + // Skip OUI
26573 + pTmp += 3;
26574 + TmpCipher = Ndis802_11WEPDisabled;
26575 + switch (*pTmp)
26576 + {
26577 + case 1:
26578 + case 5: // Although WEP is not allowed in WPA related auth mode, we parse it anyway
26579 + TmpCipher = Ndis802_11Encryption1Enabled;
26580 + break;
26581 + case 2:
26582 + TmpCipher = Ndis802_11Encryption2Enabled;
26583 + break;
26584 + case 4:
26585 + TmpCipher = Ndis802_11Encryption3Enabled;
26586 + break;
26587 + default:
26588 + break;
26589 + }
26590 + if (TmpCipher > pBss->WPA.PairCipher)
26591 + {
26592 + // Move the lower cipher suite to PairCipherAux
26593 + pBss->WPA.PairCipherAux = pBss->WPA.PairCipher;
26594 + pBss->WPA.PairCipher = TmpCipher;
26595 + }
26596 + else
26597 + {
26598 + pBss->WPA.PairCipherAux = TmpCipher;
26599 + }
26600 + pTmp++;
26601 + Count--;
26602 + }
26603 +
26604 + // 4. get AKM suite counts
26605 + //Count = *(PUSHORT) pTmp;
26606 + Count = (pTmp[1]<<8) + pTmp[0];
26607 + pTmp += sizeof(USHORT);
26608 + pTmp += 3;
26609 +
26610 + switch (*pTmp)
26611 + {
26612 + case 1:
26613 + // Set AP support WPA mode
26614 + if (pBss->AuthMode == Ndis802_11AuthModeOpen)
26615 + pBss->AuthMode = Ndis802_11AuthModeWPA;
26616 + else
26617 + pBss->AuthModeAux = Ndis802_11AuthModeWPA;
26618 + break;
26619 + case 2:
26620 + // Set AP support WPA mode
26621 + if (pBss->AuthMode == Ndis802_11AuthModeOpen)
26622 + pBss->AuthMode = Ndis802_11AuthModeWPAPSK;
26623 + else
26624 + pBss->AuthModeAux = Ndis802_11AuthModeWPAPSK;
26625 + break;
26626 + default:
26627 + break;
26628 + }
26629 + pTmp += 1;
26630 +
26631 + // Fixed for WPA-None
26632 + if (pBss->BssType == BSS_ADHOC)
26633 + {
26634 + pBss->AuthMode = Ndis802_11AuthModeWPANone;
26635 + pBss->AuthModeAux = Ndis802_11AuthModeWPANone;
26636 + pBss->WepStatus = pBss->WPA.GroupCipher;
26637 + // Patched bugs for old driver
26638 + if (pBss->WPA.PairCipherAux == Ndis802_11WEPDisabled)
26639 + pBss->WPA.PairCipherAux = pBss->WPA.GroupCipher;
26640 + }
26641 + else
26642 + pBss->WepStatus = pBss->WPA.PairCipher;
26643 +
26644 + // Check the Pair & Group, if different, turn on mixed mode flag
26645 + if (pBss->WPA.GroupCipher != pBss->WPA.PairCipher)
26646 + pBss->WPA.bMixMode = TRUE;
26647 +
26648 + break;
26649 +
26650 + case IE_RSN:
26651 + pRsnHeader = (PRSN_IE_HEADER_STRUCT) pTmp;
26652 +
26653 + // 0. Version must be 1
26654 + if (le2cpu16(pRsnHeader->Version) != 1)
26655 + break;
26656 + pTmp += sizeof(RSN_IE_HEADER_STRUCT);
26657 +
26658 + // 1. Check group cipher
26659 + pCipher = (PCIPHER_SUITE_STRUCT) pTmp;
26660 + if (!RTMPEqualMemory(pTmp, RSN_OUI, 3))
26661 + break;
26662 +
26663 + // Parse group cipher
26664 + switch (pCipher->Type)
26665 + {
26666 + case 1:
26667 + case 5: // Although WEP is not allowed in WPA related auth mode, we parse it anyway
26668 + pBss->WPA2.GroupCipher = Ndis802_11Encryption1Enabled;
26669 + break;
26670 + case 2:
26671 + pBss->WPA2.GroupCipher = Ndis802_11Encryption2Enabled;
26672 + break;
26673 + case 4:
26674 + pBss->WPA2.GroupCipher = Ndis802_11Encryption3Enabled;
26675 + break;
26676 + default:
26677 + break;
26678 + }
26679 + // set to correct offset for next parsing
26680 + pTmp += sizeof(CIPHER_SUITE_STRUCT);
26681 +
26682 + // 2. Get pairwise cipher counts
26683 + //Count = *(PUSHORT) pTmp;
26684 + Count = (pTmp[1]<<8) + pTmp[0];
26685 + pTmp += sizeof(USHORT);
26686 +
26687 + // 3. Get pairwise cipher
26688 + // Parsing all unicast cipher suite
26689 + while (Count > 0)
26690 + {
26691 + // Skip OUI
26692 + pCipher = (PCIPHER_SUITE_STRUCT) pTmp;
26693 + TmpCipher = Ndis802_11WEPDisabled;
26694 + switch (pCipher->Type)
26695 + {
26696 + case 1:
26697 + case 5: // Although WEP is not allowed in WPA related auth mode, we parse it anyway
26698 + TmpCipher = Ndis802_11Encryption1Enabled;
26699 + break;
26700 + case 2:
26701 + TmpCipher = Ndis802_11Encryption2Enabled;
26702 + break;
26703 + case 4:
26704 + TmpCipher = Ndis802_11Encryption3Enabled;
26705 + break;
26706 + default:
26707 + break;
26708 + }
26709 + if (TmpCipher > pBss->WPA2.PairCipher)
26710 + {
26711 + // Move the lower cipher suite to PairCipherAux
26712 + pBss->WPA2.PairCipherAux = pBss->WPA2.PairCipher;
26713 + pBss->WPA2.PairCipher = TmpCipher;
26714 + }
26715 + else
26716 + {
26717 + pBss->WPA2.PairCipherAux = TmpCipher;
26718 + }
26719 + pTmp += sizeof(CIPHER_SUITE_STRUCT);
26720 + Count--;
26721 + }
26722 +
26723 + // 4. get AKM suite counts
26724 + //Count = *(PUSHORT) pTmp;
26725 + Count = (pTmp[1]<<8) + pTmp[0];
26726 + pTmp += sizeof(USHORT);
26727 +
26728 + // 5. Get AKM ciphers
26729 + pAKM = (PAKM_SUITE_STRUCT) pTmp;
26730 + if (!RTMPEqualMemory(pTmp, RSN_OUI, 3))
26731 + break;
26732 +
26733 + switch (pAKM->Type)
26734 + {
26735 + case 1:
26736 + // Set AP support WPA mode
26737 + if (pBss->AuthMode == Ndis802_11AuthModeOpen)
26738 + pBss->AuthMode = Ndis802_11AuthModeWPA2;
26739 + else
26740 + pBss->AuthModeAux = Ndis802_11AuthModeWPA2;
26741 + break;
26742 + case 2:
26743 + // Set AP support WPA mode
26744 + if (pBss->AuthMode == Ndis802_11AuthModeOpen)
26745 + pBss->AuthMode = Ndis802_11AuthModeWPA2PSK;
26746 + else
26747 + pBss->AuthModeAux = Ndis802_11AuthModeWPA2PSK;
26748 + break;
26749 + default:
26750 + break;
26751 + }
26752 + pTmp += (Count * sizeof(AKM_SUITE_STRUCT));
26753 +
26754 + // Fixed for WPA-None
26755 + if (pBss->BssType == BSS_ADHOC)
26756 + {
26757 + pBss->AuthMode = Ndis802_11AuthModeWPANone;
26758 + pBss->AuthModeAux = Ndis802_11AuthModeWPANone;
26759 + pBss->WPA.PairCipherAux = pBss->WPA2.PairCipherAux;
26760 + pBss->WPA.GroupCipher = pBss->WPA2.GroupCipher;
26761 + pBss->WepStatus = pBss->WPA.GroupCipher;
26762 + // Patched bugs for old driver
26763 + if (pBss->WPA.PairCipherAux == Ndis802_11WEPDisabled)
26764 + pBss->WPA.PairCipherAux = pBss->WPA.GroupCipher;
26765 + }
26766 + pBss->WepStatus = pBss->WPA2.PairCipher;
26767 +
26768 + // 6. Get RSN capability
26769 + //pBss->WPA2.RsnCapability = *(PUSHORT) pTmp;
26770 + pBss->WPA2.RsnCapability = (pTmp[1]<<8) + pTmp[0];
26771 + pTmp += sizeof(USHORT);
26772 +
26773 + // Check the Pair & Group, if different, turn on mixed mode flag
26774 + if (pBss->WPA2.GroupCipher != pBss->WPA2.PairCipher)
26775 + pBss->WPA2.bMixMode = TRUE;
26776 +
26777 + break;
26778 + default:
26779 + break;
26780 + }
26781 + Length -= (pEid->Len + 2);
26782 + }
26783 +}
26784 +
26785 +// ===========================================================================================
26786 +// mac_table.c
26787 +// ===========================================================================================
26788 +
26789 +/*! \brief generates a random mac address value for IBSS BSSID
26790 + * \param Addr the bssid location
26791 + * \return none
26792 + * \pre
26793 + * \post
26794 + */
26795 +VOID MacAddrRandomBssid(
26796 + IN PRTMP_ADAPTER pAd,
26797 + OUT PUCHAR pAddr)
26798 +{
26799 + INT i;
26800 +
26801 + for (i = 0; i < MAC_ADDR_LEN; i++)
26802 + {
26803 + pAddr[i] = RandomByte(pAd);
26804 + }
26805 +
26806 + pAddr[0] = (pAddr[0] & 0xfe) | 0x02; // the first 2 bits must be 01xxxxxxxx
26807 +}
26808 +
26809 +/*! \brief init the management mac frame header
26810 + * \param p_hdr mac header
26811 + * \param subtype subtype of the frame
26812 + * \param p_ds destination address, don't care if it is a broadcast address
26813 + * \return none
26814 + * \pre the station has the following information in the pAd->StaCfg
26815 + * - bssid
26816 + * - station address
26817 + * \post
26818 + * \note this function initializes the following field
26819 +
26820 + IRQL = PASSIVE_LEVEL
26821 + IRQL = DISPATCH_LEVEL
26822 +
26823 + */
26824 +VOID MgtMacHeaderInit(
26825 + IN PRTMP_ADAPTER pAd,
26826 + IN OUT PHEADER_802_11 pHdr80211,
26827 + IN UCHAR SubType,
26828 + IN UCHAR ToDs,
26829 + IN PUCHAR pDA,
26830 + IN PUCHAR pBssid)
26831 +{
26832 + NdisZeroMemory(pHdr80211, sizeof(HEADER_802_11));
26833 +
26834 + pHdr80211->FC.Type = BTYPE_MGMT;
26835 + pHdr80211->FC.SubType = SubType;
26836 + pHdr80211->FC.ToDs = ToDs;
26837 + COPY_MAC_ADDR(pHdr80211->Addr1, pDA);
26838 +#ifdef CONFIG_STA_SUPPORT
26839 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
26840 + COPY_MAC_ADDR(pHdr80211->Addr2, pAd->CurrentAddress);
26841 +#endif // CONFIG_STA_SUPPORT //
26842 + COPY_MAC_ADDR(pHdr80211->Addr3, pBssid);
26843 +}
26844 +
26845 +// ===========================================================================================
26846 +// mem_mgmt.c
26847 +// ===========================================================================================
26848 +
26849 +/*!***************************************************************************
26850 + * This routine build an outgoing frame, and fill all information specified
26851 + * in argument list to the frame body. The actual frame size is the summation
26852 + * of all arguments.
26853 + * input params:
26854 + * Buffer - pointer to a pre-allocated memory segment
26855 + * args - a list of <int arg_size, arg> pairs.
26856 + * NOTE NOTE NOTE!!!! the last argument must be NULL, otherwise this
26857 + * function will FAIL!!!
26858 + * return:
26859 + * Size of the buffer
26860 + * usage:
26861 + * MakeOutgoingFrame(Buffer, output_length, 2, &fc, 2, &dur, 6, p_addr1, 6,p_addr2, END_OF_ARGS);
26862 +
26863 + IRQL = PASSIVE_LEVEL
26864 + IRQL = DISPATCH_LEVEL
26865 +
26866 + ****************************************************************************/
26867 +ULONG MakeOutgoingFrame(
26868 + OUT CHAR *Buffer,
26869 + OUT ULONG *FrameLen, ...)
26870 +{
26871 + CHAR *p;
26872 + int leng;
26873 + ULONG TotLeng;
26874 + va_list Args;
26875 +
26876 + // calculates the total length
26877 + TotLeng = 0;
26878 + va_start(Args, FrameLen);
26879 + do
26880 + {
26881 + leng = va_arg(Args, int);
26882 + if (leng == END_OF_ARGS)
26883 + {
26884 + break;
26885 + }
26886 + p = va_arg(Args, PVOID);
26887 + NdisMoveMemory(&Buffer[TotLeng], p, leng);
26888 + TotLeng = TotLeng + leng;
26889 + } while(TRUE);
26890 +
26891 + va_end(Args); /* clean up */
26892 + *FrameLen = TotLeng;
26893 + return TotLeng;
26894 +}
26895 +
26896 +// ===========================================================================================
26897 +// mlme_queue.c
26898 +// ===========================================================================================
26899 +
26900 +/*! \brief Initialize The MLME Queue, used by MLME Functions
26901 + * \param *Queue The MLME Queue
26902 + * \return Always Return NDIS_STATE_SUCCESS in this implementation
26903 + * \pre
26904 + * \post
26905 + * \note Because this is done only once (at the init stage), no need to be locked
26906 +
26907 + IRQL = PASSIVE_LEVEL
26908 +
26909 + */
26910 +NDIS_STATUS MlmeQueueInit(
26911 + IN MLME_QUEUE *Queue)
26912 +{
26913 + INT i;
26914 +
26915 + NdisAllocateSpinLock(&Queue->Lock);
26916 +
26917 + Queue->Num = 0;
26918 + Queue->Head = 0;
26919 + Queue->Tail = 0;
26920 +
26921 + for (i = 0; i < MAX_LEN_OF_MLME_QUEUE; i++)
26922 + {
26923 + Queue->Entry[i].Occupied = FALSE;
26924 + Queue->Entry[i].MsgLen = 0;
26925 + NdisZeroMemory(Queue->Entry[i].Msg, MGMT_DMA_BUFFER_SIZE);
26926 + }
26927 +
26928 + return NDIS_STATUS_SUCCESS;
26929 +}
26930 +
26931 +/*! \brief Enqueue a message for other threads, if they want to send messages to MLME thread
26932 + * \param *Queue The MLME Queue
26933 + * \param Machine The State Machine Id
26934 + * \param MsgType The Message Type
26935 + * \param MsgLen The Message length
26936 + * \param *Msg The message pointer
26937 + * \return TRUE if enqueue is successful, FALSE if the queue is full
26938 + * \pre
26939 + * \post
26940 + * \note The message has to be initialized
26941 +
26942 + IRQL = PASSIVE_LEVEL
26943 + IRQL = DISPATCH_LEVEL
26944 +
26945 + */
26946 +BOOLEAN MlmeEnqueue(
26947 + IN PRTMP_ADAPTER pAd,
26948 + IN ULONG Machine,
26949 + IN ULONG MsgType,
26950 + IN ULONG MsgLen,
26951 + IN VOID *Msg)
26952 +{
26953 + INT Tail;
26954 + MLME_QUEUE *Queue = (MLME_QUEUE *)&pAd->Mlme.Queue;
26955 +
26956 + // Do nothing if the driver is starting halt state.
26957 + // This might happen when timer already been fired before cancel timer with mlmehalt
26958 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
26959 + return FALSE;
26960 +
26961 + // First check the size, it MUST not exceed the mlme queue size
26962 + if (MsgLen > MGMT_DMA_BUFFER_SIZE)
26963 + {
26964 + DBGPRINT_ERR(("MlmeEnqueue: msg too large, size = %ld \n", MsgLen));
26965 + return FALSE;
26966 + }
26967 +
26968 + if (MlmeQueueFull(Queue))
26969 + {
26970 + return FALSE;
26971 + }
26972 +
26973 + NdisAcquireSpinLock(&(Queue->Lock));
26974 + Tail = Queue->Tail;
26975 + Queue->Tail++;
26976 + Queue->Num++;
26977 + if (Queue->Tail == MAX_LEN_OF_MLME_QUEUE)
26978 + {
26979 + Queue->Tail = 0;
26980 + }
26981 +
26982 + Queue->Entry[Tail].Wcid = RESERVED_WCID;
26983 + Queue->Entry[Tail].Occupied = TRUE;
26984 + Queue->Entry[Tail].Machine = Machine;
26985 + Queue->Entry[Tail].MsgType = MsgType;
26986 + Queue->Entry[Tail].MsgLen = MsgLen;
26987 +
26988 + if (Msg != NULL)
26989 + {
26990 + NdisMoveMemory(Queue->Entry[Tail].Msg, Msg, MsgLen);
26991 + }
26992 +
26993 + NdisReleaseSpinLock(&(Queue->Lock));
26994 + return TRUE;
26995 +}
26996 +
26997 +/*! \brief This function is used when Recv gets a MLME message
26998 + * \param *Queue The MLME Queue
26999 + * \param TimeStampHigh The upper 32 bit of timestamp
27000 + * \param TimeStampLow The lower 32 bit of timestamp
27001 + * \param Rssi The receiving RSSI strength
27002 + * \param MsgLen The length of the message
27003 + * \param *Msg The message pointer
27004 + * \return TRUE if everything ok, FALSE otherwise (like Queue Full)
27005 + * \pre
27006 + * \post
27007 +
27008 + IRQL = DISPATCH_LEVEL
27009 +
27010 + */
27011 +BOOLEAN MlmeEnqueueForRecv(
27012 + IN PRTMP_ADAPTER pAd,
27013 + IN ULONG Wcid,
27014 + IN ULONG TimeStampHigh,
27015 + IN ULONG TimeStampLow,
27016 + IN UCHAR Rssi0,
27017 + IN UCHAR Rssi1,
27018 + IN UCHAR Rssi2,
27019 + IN ULONG MsgLen,
27020 + IN VOID *Msg,
27021 + IN UCHAR Signal)
27022 +{
27023 + INT Tail, Machine;
27024 + PFRAME_802_11 pFrame = (PFRAME_802_11)Msg;
27025 + INT MsgType;
27026 + MLME_QUEUE *Queue = (MLME_QUEUE *)&pAd->Mlme.Queue;
27027 +
27028 +#ifdef RALINK_ATE
27029 + /* Nothing to do in ATE mode */
27030 + if(ATE_ON(pAd))
27031 + return FALSE;
27032 +#endif // RALINK_ATE //
27033 +
27034 + // Do nothing if the driver is starting halt state.
27035 + // This might happen when timer already been fired before cancel timer with mlmehalt
27036 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
27037 + {
27038 + DBGPRINT_ERR(("MlmeEnqueueForRecv: fRTMP_ADAPTER_HALT_IN_PROGRESS\n"));
27039 + return FALSE;
27040 + }
27041 +
27042 + // First check the size, it MUST not exceed the mlme queue size
27043 + if (MsgLen > MGMT_DMA_BUFFER_SIZE)
27044 + {
27045 + DBGPRINT_ERR(("MlmeEnqueueForRecv: frame too large, size = %ld \n", MsgLen));
27046 + return FALSE;
27047 + }
27048 +
27049 + if (MlmeQueueFull(Queue))
27050 + {
27051 + return FALSE;
27052 + }
27053 +
27054 +#ifdef CONFIG_STA_SUPPORT
27055 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
27056 + {
27057 + if (!MsgTypeSubst(pAd, pFrame, &Machine, &MsgType))
27058 + {
27059 + DBGPRINT_ERR(("MlmeEnqueueForRecv: un-recongnized mgmt->subtype=%d\n",pFrame->Hdr.FC.SubType));
27060 + return FALSE;
27061 + }
27062 + }
27063 +#endif // CONFIG_STA_SUPPORT //
27064 +
27065 + // OK, we got all the informations, it is time to put things into queue
27066 + NdisAcquireSpinLock(&(Queue->Lock));
27067 + Tail = Queue->Tail;
27068 + Queue->Tail++;
27069 + Queue->Num++;
27070 + if (Queue->Tail == MAX_LEN_OF_MLME_QUEUE)
27071 + {
27072 + Queue->Tail = 0;
27073 + }
27074 + Queue->Entry[Tail].Occupied = TRUE;
27075 + Queue->Entry[Tail].Machine = Machine;
27076 + Queue->Entry[Tail].MsgType = MsgType;
27077 + Queue->Entry[Tail].MsgLen = MsgLen;
27078 + Queue->Entry[Tail].TimeStamp.u.LowPart = TimeStampLow;
27079 + Queue->Entry[Tail].TimeStamp.u.HighPart = TimeStampHigh;
27080 + Queue->Entry[Tail].Rssi0 = Rssi0;
27081 + Queue->Entry[Tail].Rssi1 = Rssi1;
27082 + Queue->Entry[Tail].Rssi2 = Rssi2;
27083 + Queue->Entry[Tail].Signal = Signal;
27084 + Queue->Entry[Tail].Wcid = (UCHAR)Wcid;
27085 +
27086 + Queue->Entry[Tail].Channel = pAd->LatchRfRegs.Channel;
27087 +
27088 + if (Msg != NULL)
27089 + {
27090 + NdisMoveMemory(Queue->Entry[Tail].Msg, Msg, MsgLen);
27091 + }
27092 +
27093 + NdisReleaseSpinLock(&(Queue->Lock));
27094 +
27095 + RT28XX_MLME_HANDLER(pAd);
27096 +
27097 + return TRUE;
27098 +}
27099 +
27100 +
27101 +/*! \brief Dequeue a message from the MLME Queue
27102 + * \param *Queue The MLME Queue
27103 + * \param *Elem The message dequeued from MLME Queue
27104 + * \return TRUE if the Elem contains something, FALSE otherwise
27105 + * \pre
27106 + * \post
27107 +
27108 + IRQL = DISPATCH_LEVEL
27109 +
27110 + */
27111 +BOOLEAN MlmeDequeue(
27112 + IN MLME_QUEUE *Queue,
27113 + OUT MLME_QUEUE_ELEM **Elem)
27114 +{
27115 + NdisAcquireSpinLock(&(Queue->Lock));
27116 + *Elem = &(Queue->Entry[Queue->Head]);
27117 + Queue->Num--;
27118 + Queue->Head++;
27119 + if (Queue->Head == MAX_LEN_OF_MLME_QUEUE)
27120 + {
27121 + Queue->Head = 0;
27122 + }
27123 + NdisReleaseSpinLock(&(Queue->Lock));
27124 + return TRUE;
27125 +}
27126 +
27127 +// IRQL = DISPATCH_LEVEL
27128 +VOID MlmeRestartStateMachine(
27129 + IN PRTMP_ADAPTER pAd)
27130 +{
27131 +#ifdef RT2860
27132 + MLME_QUEUE_ELEM *Elem = NULL;
27133 +#endif // RT2860 //
27134 +#ifdef CONFIG_STA_SUPPORT
27135 + BOOLEAN Cancelled;
27136 +#endif // CONFIG_STA_SUPPORT //
27137 +
27138 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeRestartStateMachine \n"));
27139 +
27140 +#ifdef RT2860
27141 + NdisAcquireSpinLock(&pAd->Mlme.TaskLock);
27142 + if(pAd->Mlme.bRunning)
27143 + {
27144 + NdisReleaseSpinLock(&pAd->Mlme.TaskLock);
27145 + return;
27146 + }
27147 + else
27148 + {
27149 + pAd->Mlme.bRunning = TRUE;
27150 + }
27151 + NdisReleaseSpinLock(&pAd->Mlme.TaskLock);
27152 +
27153 + // Remove all Mlme queues elements
27154 + while (!MlmeQueueEmpty(&pAd->Mlme.Queue))
27155 + {
27156 + //From message type, determine which state machine I should drive
27157 + if (MlmeDequeue(&pAd->Mlme.Queue, &Elem))
27158 + {
27159 + // free MLME element
27160 + Elem->Occupied = FALSE;
27161 + Elem->MsgLen = 0;
27162 +
27163 + }
27164 + else {
27165 + DBGPRINT_ERR(("MlmeRestartStateMachine: MlmeQueue empty\n"));
27166 + }
27167 + }
27168 +#endif // RT2860 //
27169 +
27170 +#ifdef CONFIG_STA_SUPPORT
27171 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
27172 + {
27173 +#ifdef QOS_DLS_SUPPORT
27174 + UCHAR i;
27175 +#endif // QOS_DLS_SUPPORT //
27176 + // Cancel all timer events
27177 + // Be careful to cancel new added timer
27178 + RTMPCancelTimer(&pAd->MlmeAux.AssocTimer, &Cancelled);
27179 + RTMPCancelTimer(&pAd->MlmeAux.ReassocTimer, &Cancelled);
27180 + RTMPCancelTimer(&pAd->MlmeAux.DisassocTimer, &Cancelled);
27181 + RTMPCancelTimer(&pAd->MlmeAux.AuthTimer, &Cancelled);
27182 + RTMPCancelTimer(&pAd->MlmeAux.BeaconTimer, &Cancelled);
27183 + RTMPCancelTimer(&pAd->MlmeAux.ScanTimer, &Cancelled);
27184 +
27185 +#ifdef QOS_DLS_SUPPORT
27186 + for (i=0; i<MAX_NUM_OF_DLS_ENTRY; i++)
27187 + {
27188 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &Cancelled);
27189 + }
27190 +#endif // QOS_DLS_SUPPORT //
27191 + }
27192 +#endif // CONFIG_STA_SUPPORT //
27193 +
27194 + // Change back to original channel in case of doing scan
27195 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
27196 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
27197 +
27198 + // Resume MSDU which is turned off durning scan
27199 + RTMPResumeMsduTransmission(pAd);
27200 +
27201 +#ifdef CONFIG_STA_SUPPORT
27202 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
27203 + {
27204 + // Set all state machines back IDLE
27205 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
27206 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
27207 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
27208 + pAd->Mlme.AuthRspMachine.CurrState = AUTH_RSP_IDLE;
27209 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
27210 + pAd->Mlme.ActMachine.CurrState = ACT_IDLE;
27211 +#ifdef QOS_DLS_SUPPORT
27212 + pAd->Mlme.DlsMachine.CurrState = DLS_IDLE;
27213 +#endif // QOS_DLS_SUPPORT //
27214 + }
27215 +#endif // CONFIG_STA_SUPPORT //
27216 +
27217 +#ifdef RT2860
27218 + // Remove running state
27219 + NdisAcquireSpinLock(&pAd->Mlme.TaskLock);
27220 + pAd->Mlme.bRunning = FALSE;
27221 + NdisReleaseSpinLock(&pAd->Mlme.TaskLock);
27222 +#endif // RT2860 //
27223 +}
27224 +
27225 +/*! \brief test if the MLME Queue is empty
27226 + * \param *Queue The MLME Queue
27227 + * \return TRUE if the Queue is empty, FALSE otherwise
27228 + * \pre
27229 + * \post
27230 +
27231 + IRQL = DISPATCH_LEVEL
27232 +
27233 + */
27234 +BOOLEAN MlmeQueueEmpty(
27235 + IN MLME_QUEUE *Queue)
27236 +{
27237 + BOOLEAN Ans;
27238 +
27239 + NdisAcquireSpinLock(&(Queue->Lock));
27240 + Ans = (Queue->Num == 0);
27241 + NdisReleaseSpinLock(&(Queue->Lock));
27242 +
27243 + return Ans;
27244 +}
27245 +
27246 +/*! \brief test if the MLME Queue is full
27247 + * \param *Queue The MLME Queue
27248 + * \return TRUE if the Queue is empty, FALSE otherwise
27249 + * \pre
27250 + * \post
27251 +
27252 + IRQL = PASSIVE_LEVEL
27253 + IRQL = DISPATCH_LEVEL
27254 +
27255 + */
27256 +BOOLEAN MlmeQueueFull(
27257 + IN MLME_QUEUE *Queue)
27258 +{
27259 + BOOLEAN Ans;
27260 +
27261 + NdisAcquireSpinLock(&(Queue->Lock));
27262 + Ans = (Queue->Num == MAX_LEN_OF_MLME_QUEUE || Queue->Entry[Queue->Tail].Occupied);
27263 + NdisReleaseSpinLock(&(Queue->Lock));
27264 +
27265 + return Ans;
27266 +}
27267 +
27268 +/*! \brief The destructor of MLME Queue
27269 + * \param
27270 + * \return
27271 + * \pre
27272 + * \post
27273 + * \note Clear Mlme Queue, Set Queue->Num to Zero.
27274 +
27275 + IRQL = PASSIVE_LEVEL
27276 +
27277 + */
27278 +VOID MlmeQueueDestroy(
27279 + IN MLME_QUEUE *pQueue)
27280 +{
27281 + NdisAcquireSpinLock(&(pQueue->Lock));
27282 + pQueue->Num = 0;
27283 + pQueue->Head = 0;
27284 + pQueue->Tail = 0;
27285 + NdisReleaseSpinLock(&(pQueue->Lock));
27286 + NdisFreeSpinLock(&(pQueue->Lock));
27287 +}
27288 +
27289 +/*! \brief To substitute the message type if the message is coming from external
27290 + * \param pFrame The frame received
27291 + * \param *Machine The state machine
27292 + * \param *MsgType the message type for the state machine
27293 + * \return TRUE if the substitution is successful, FALSE otherwise
27294 + * \pre
27295 + * \post
27296 +
27297 + IRQL = DISPATCH_LEVEL
27298 +
27299 + */
27300 +#ifdef CONFIG_STA_SUPPORT
27301 +BOOLEAN MsgTypeSubst(
27302 + IN PRTMP_ADAPTER pAd,
27303 + IN PFRAME_802_11 pFrame,
27304 + OUT INT *Machine,
27305 + OUT INT *MsgType)
27306 +{
27307 + USHORT Seq;
27308 + UCHAR EAPType;
27309 + PUCHAR pData;
27310 +
27311 + // Pointer to start of data frames including SNAP header
27312 + pData = (PUCHAR) pFrame + LENGTH_802_11;
27313 +
27314 + // The only data type will pass to this function is EAPOL frame
27315 + if (pFrame->Hdr.FC.Type == BTYPE_DATA)
27316 + {
27317 + if (NdisEqualMemory(SNAP_AIRONET, pData, LENGTH_802_1_H))
27318 + {
27319 + // Cisco Aironet SNAP header
27320 + *Machine = AIRONET_STATE_MACHINE;
27321 + *MsgType = MT2_AIRONET_MSG;
27322 + return (TRUE);
27323 + }
27324 +#ifdef LEAP_SUPPORT
27325 + if ( pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP ) //LEAP
27326 + {
27327 + // LEAP frames
27328 + *Machine = LEAP_STATE_MACHINE;
27329 + EAPType = *((UCHAR*)pFrame + LENGTH_802_11 + LENGTH_802_1_H + 1);
27330 + return (LeapMsgTypeSubst(EAPType, MsgType));
27331 + }
27332 + else
27333 +#endif // LEAP_SUPPORT //
27334 + {
27335 + *Machine = WPA_PSK_STATE_MACHINE;
27336 + EAPType = *((UCHAR*)pFrame + LENGTH_802_11 + LENGTH_802_1_H + 1);
27337 + return(WpaMsgTypeSubst(EAPType, MsgType));
27338 + }
27339 + }
27340 +
27341 + switch (pFrame->Hdr.FC.SubType)
27342 + {
27343 + case SUBTYPE_ASSOC_REQ:
27344 + *Machine = ASSOC_STATE_MACHINE;
27345 + *MsgType = MT2_PEER_ASSOC_REQ;
27346 + break;
27347 + case SUBTYPE_ASSOC_RSP:
27348 + *Machine = ASSOC_STATE_MACHINE;
27349 + *MsgType = MT2_PEER_ASSOC_RSP;
27350 + break;
27351 + case SUBTYPE_REASSOC_REQ:
27352 + *Machine = ASSOC_STATE_MACHINE;
27353 + *MsgType = MT2_PEER_REASSOC_REQ;
27354 + break;
27355 + case SUBTYPE_REASSOC_RSP:
27356 + *Machine = ASSOC_STATE_MACHINE;
27357 + *MsgType = MT2_PEER_REASSOC_RSP;
27358 + break;
27359 + case SUBTYPE_PROBE_REQ:
27360 + *Machine = SYNC_STATE_MACHINE;
27361 + *MsgType = MT2_PEER_PROBE_REQ;
27362 + break;
27363 + case SUBTYPE_PROBE_RSP:
27364 + *Machine = SYNC_STATE_MACHINE;
27365 + *MsgType = MT2_PEER_PROBE_RSP;
27366 + break;
27367 + case SUBTYPE_BEACON:
27368 + *Machine = SYNC_STATE_MACHINE;
27369 + *MsgType = MT2_PEER_BEACON;
27370 + break;
27371 + case SUBTYPE_ATIM:
27372 + *Machine = SYNC_STATE_MACHINE;
27373 + *MsgType = MT2_PEER_ATIM;
27374 + break;
27375 + case SUBTYPE_DISASSOC:
27376 + *Machine = ASSOC_STATE_MACHINE;
27377 + *MsgType = MT2_PEER_DISASSOC_REQ;
27378 + break;
27379 + case SUBTYPE_AUTH:
27380 + // get the sequence number from payload 24 Mac Header + 2 bytes algorithm
27381 + NdisMoveMemory(&Seq, &pFrame->Octet[2], sizeof(USHORT));
27382 + if (Seq == 1 || Seq == 3)
27383 + {
27384 + *Machine = AUTH_RSP_STATE_MACHINE;
27385 + *MsgType = MT2_PEER_AUTH_ODD;
27386 + }
27387 + else if (Seq == 2 || Seq == 4)
27388 + {
27389 + *Machine = AUTH_STATE_MACHINE;
27390 + *MsgType = MT2_PEER_AUTH_EVEN;
27391 + }
27392 + else
27393 + {
27394 + return FALSE;
27395 + }
27396 + break;
27397 + case SUBTYPE_DEAUTH:
27398 + *Machine = AUTH_RSP_STATE_MACHINE;
27399 + *MsgType = MT2_PEER_DEAUTH;
27400 + break;
27401 + case SUBTYPE_ACTION:
27402 + *Machine = ACTION_STATE_MACHINE;
27403 + // Sometimes Sta will return with category bytes with MSB = 1, if they receive catogory out of their support
27404 + if ((pFrame->Octet[0]&0x7F) > MAX_PEER_CATE_MSG)
27405 + {
27406 + *MsgType = MT2_ACT_INVALID;
27407 + }
27408 + else
27409 + {
27410 + *MsgType = (pFrame->Octet[0]&0x7F);
27411 + }
27412 + break;
27413 + default:
27414 + return FALSE;
27415 + break;
27416 + }
27417 +
27418 + return TRUE;
27419 +}
27420 +#endif // CONFIG_STA_SUPPORT //
27421 +
27422 +// ===========================================================================================
27423 +// state_machine.c
27424 +// ===========================================================================================
27425 +
27426 +/*! \brief Initialize the state machine.
27427 + * \param *S pointer to the state machine
27428 + * \param Trans State machine transition function
27429 + * \param StNr number of states
27430 + * \param MsgNr number of messages
27431 + * \param DefFunc default function, when there is invalid state/message combination
27432 + * \param InitState initial state of the state machine
27433 + * \param Base StateMachine base, internal use only
27434 + * \pre p_sm should be a legal pointer
27435 + * \post
27436 +
27437 + IRQL = PASSIVE_LEVEL
27438 +
27439 + */
27440 +VOID StateMachineInit(
27441 + IN STATE_MACHINE *S,
27442 + IN STATE_MACHINE_FUNC Trans[],
27443 + IN ULONG StNr,
27444 + IN ULONG MsgNr,
27445 + IN STATE_MACHINE_FUNC DefFunc,
27446 + IN ULONG InitState,
27447 + IN ULONG Base)
27448 +{
27449 + ULONG i, j;
27450 +
27451 + // set number of states and messages
27452 + S->NrState = StNr;
27453 + S->NrMsg = MsgNr;
27454 + S->Base = Base;
27455 +
27456 + S->TransFunc = Trans;
27457 +
27458 + // init all state transition to default function
27459 + for (i = 0; i < StNr; i++)
27460 + {
27461 + for (j = 0; j < MsgNr; j++)
27462 + {
27463 + S->TransFunc[i * MsgNr + j] = DefFunc;
27464 + }
27465 + }
27466 +
27467 + // set the starting state
27468 + S->CurrState = InitState;
27469 +}
27470 +
27471 +/*! \brief This function fills in the function pointer into the cell in the state machine
27472 + * \param *S pointer to the state machine
27473 + * \param St state
27474 + * \param Msg incoming message
27475 + * \param f the function to be executed when (state, message) combination occurs at the state machine
27476 + * \pre *S should be a legal pointer to the state machine, st, msg, should be all within the range, Base should be set in the initial state
27477 + * \post
27478 +
27479 + IRQL = PASSIVE_LEVEL
27480 +
27481 + */
27482 +VOID StateMachineSetAction(
27483 + IN STATE_MACHINE *S,
27484 + IN ULONG St,
27485 + IN ULONG Msg,
27486 + IN STATE_MACHINE_FUNC Func)
27487 +{
27488 + ULONG MsgIdx;
27489 +
27490 + MsgIdx = Msg - S->Base;
27491 +
27492 + if (St < S->NrState && MsgIdx < S->NrMsg)
27493 + {
27494 + // boundary checking before setting the action
27495 + S->TransFunc[St * S->NrMsg + MsgIdx] = Func;
27496 + }
27497 +}
27498 +
27499 +/*! \brief This function does the state transition
27500 + * \param *Adapter the NIC adapter pointer
27501 + * \param *S the state machine
27502 + * \param *Elem the message to be executed
27503 + * \return None
27504 +
27505 + IRQL = DISPATCH_LEVEL
27506 +
27507 + */
27508 +VOID StateMachinePerformAction(
27509 + IN PRTMP_ADAPTER pAd,
27510 + IN STATE_MACHINE *S,
27511 + IN MLME_QUEUE_ELEM *Elem)
27512 +{
27513 + (*(S->TransFunc[S->CurrState * S->NrMsg + Elem->MsgType - S->Base]))(pAd, Elem);
27514 +}
27515 +
27516 +/*
27517 + ==========================================================================
27518 + Description:
27519 + The drop function, when machine executes this, the message is simply
27520 + ignored. This function does nothing, the message is freed in
27521 + StateMachinePerformAction()
27522 + ==========================================================================
27523 + */
27524 +VOID Drop(
27525 + IN PRTMP_ADAPTER pAd,
27526 + IN MLME_QUEUE_ELEM *Elem)
27527 +{
27528 +}
27529 +
27530 +// ===========================================================================================
27531 +// lfsr.c
27532 +// ===========================================================================================
27533 +
27534 +/*
27535 + ==========================================================================
27536 + Description:
27537 +
27538 + IRQL = PASSIVE_LEVEL
27539 +
27540 + ==========================================================================
27541 + */
27542 +VOID LfsrInit(
27543 + IN PRTMP_ADAPTER pAd,
27544 + IN ULONG Seed)
27545 +{
27546 + if (Seed == 0)
27547 + pAd->Mlme.ShiftReg = 1;
27548 + else
27549 + pAd->Mlme.ShiftReg = Seed;
27550 +}
27551 +
27552 +/*
27553 + ==========================================================================
27554 + Description:
27555 + ==========================================================================
27556 + */
27557 +UCHAR RandomByte(
27558 + IN PRTMP_ADAPTER pAd)
27559 +{
27560 + ULONG i;
27561 + UCHAR R, Result;
27562 +
27563 + R = 0;
27564 +
27565 + if (pAd->Mlme.ShiftReg == 0)
27566 + NdisGetSystemUpTime((ULONG *)&pAd->Mlme.ShiftReg);
27567 +
27568 + for (i = 0; i < 8; i++)
27569 + {
27570 + if (pAd->Mlme.ShiftReg & 0x00000001)
27571 + {
27572 + pAd->Mlme.ShiftReg = ((pAd->Mlme.ShiftReg ^ LFSR_MASK) >> 1) | 0x80000000;
27573 + Result = 1;
27574 + }
27575 + else
27576 + {
27577 + pAd->Mlme.ShiftReg = pAd->Mlme.ShiftReg >> 1;
27578 + Result = 0;
27579 + }
27580 + R = (R << 1) | Result;
27581 + }
27582 +
27583 + return R;
27584 +}
27585 +
27586 +VOID AsicUpdateAutoFallBackTable(
27587 + IN PRTMP_ADAPTER pAd,
27588 + IN PUCHAR pRateTable)
27589 +{
27590 + UCHAR i;
27591 + HT_FBK_CFG0_STRUC HtCfg0;
27592 + HT_FBK_CFG1_STRUC HtCfg1;
27593 + LG_FBK_CFG0_STRUC LgCfg0;
27594 + LG_FBK_CFG1_STRUC LgCfg1;
27595 + PRTMP_TX_RATE_SWITCH pCurrTxRate, pNextTxRate;
27596 +
27597 + // set to initial value
27598 + HtCfg0.word = 0x65432100;
27599 + HtCfg1.word = 0xedcba988;
27600 + LgCfg0.word = 0xedcba988;
27601 + LgCfg1.word = 0x00002100;
27602 +
27603 + pNextTxRate = (PRTMP_TX_RATE_SWITCH)pRateTable+1;
27604 + for (i = 1; i < *((PUCHAR) pRateTable); i++)
27605 + {
27606 + pCurrTxRate = (PRTMP_TX_RATE_SWITCH)pRateTable+1+i;
27607 + switch (pCurrTxRate->Mode)
27608 + {
27609 + case 0: //CCK
27610 + break;
27611 + case 1: //OFDM
27612 + {
27613 + switch(pCurrTxRate->CurrMCS)
27614 + {
27615 + case 0:
27616 + LgCfg0.field.OFDMMCS0FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27617 + break;
27618 + case 1:
27619 + LgCfg0.field.OFDMMCS1FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27620 + break;
27621 + case 2:
27622 + LgCfg0.field.OFDMMCS2FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27623 + break;
27624 + case 3:
27625 + LgCfg0.field.OFDMMCS3FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27626 + break;
27627 + case 4:
27628 + LgCfg0.field.OFDMMCS4FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27629 + break;
27630 + case 5:
27631 + LgCfg0.field.OFDMMCS5FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27632 + break;
27633 + case 6:
27634 + LgCfg0.field.OFDMMCS6FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27635 + break;
27636 + case 7:
27637 + LgCfg0.field.OFDMMCS7FBK = (pNextTxRate->Mode == MODE_OFDM) ? (pNextTxRate->CurrMCS+8): pNextTxRate->CurrMCS;
27638 + break;
27639 + }
27640 + }
27641 + break;
27642 +#ifdef DOT11_N_SUPPORT
27643 + case 2: //HT-MIX
27644 + case 3: //HT-GF
27645 + {
27646 + if ((pNextTxRate->Mode >= MODE_HTMIX) && (pCurrTxRate->CurrMCS != pNextTxRate->CurrMCS))
27647 + {
27648 + switch(pCurrTxRate->CurrMCS)
27649 + {
27650 + case 0:
27651 + HtCfg0.field.HTMCS0FBK = pNextTxRate->CurrMCS;
27652 + break;
27653 + case 1:
27654 + HtCfg0.field.HTMCS1FBK = pNextTxRate->CurrMCS;
27655 + break;
27656 + case 2:
27657 + HtCfg0.field.HTMCS2FBK = pNextTxRate->CurrMCS;
27658 + break;
27659 + case 3:
27660 + HtCfg0.field.HTMCS3FBK = pNextTxRate->CurrMCS;
27661 + break;
27662 + case 4:
27663 + HtCfg0.field.HTMCS4FBK = pNextTxRate->CurrMCS;
27664 + break;
27665 + case 5:
27666 + HtCfg0.field.HTMCS5FBK = pNextTxRate->CurrMCS;
27667 + break;
27668 + case 6:
27669 + HtCfg0.field.HTMCS6FBK = pNextTxRate->CurrMCS;
27670 + break;
27671 + case 7:
27672 + HtCfg0.field.HTMCS7FBK = pNextTxRate->CurrMCS;
27673 + break;
27674 + case 8:
27675 + HtCfg1.field.HTMCS8FBK = pNextTxRate->CurrMCS;
27676 + break;
27677 + case 9:
27678 + HtCfg1.field.HTMCS9FBK = pNextTxRate->CurrMCS;
27679 + break;
27680 + case 10:
27681 + HtCfg1.field.HTMCS10FBK = pNextTxRate->CurrMCS;
27682 + break;
27683 + case 11:
27684 + HtCfg1.field.HTMCS11FBK = pNextTxRate->CurrMCS;
27685 + break;
27686 + case 12:
27687 + HtCfg1.field.HTMCS12FBK = pNextTxRate->CurrMCS;
27688 + break;
27689 + case 13:
27690 + HtCfg1.field.HTMCS13FBK = pNextTxRate->CurrMCS;
27691 + break;
27692 + case 14:
27693 + HtCfg1.field.HTMCS14FBK = pNextTxRate->CurrMCS;
27694 + break;
27695 + case 15:
27696 + HtCfg1.field.HTMCS15FBK = pNextTxRate->CurrMCS;
27697 + break;
27698 + default:
27699 + DBGPRINT(RT_DEBUG_ERROR, ("AsicUpdateAutoFallBackTable: not support CurrMCS=%d\n", pCurrTxRate->CurrMCS));
27700 + }
27701 + }
27702 + }
27703 + break;
27704 +#endif // DOT11_N_SUPPORT //
27705 + }
27706 +
27707 + pNextTxRate = pCurrTxRate;
27708 + }
27709 +
27710 + RTMP_IO_WRITE32(pAd, HT_FBK_CFG0, HtCfg0.word);
27711 + RTMP_IO_WRITE32(pAd, HT_FBK_CFG1, HtCfg1.word);
27712 + RTMP_IO_WRITE32(pAd, LG_FBK_CFG0, LgCfg0.word);
27713 + RTMP_IO_WRITE32(pAd, LG_FBK_CFG1, LgCfg1.word);
27714 +}
27715 +
27716 +/*
27717 + ========================================================================
27718 +
27719 + Routine Description:
27720 + Set MAC register value according operation mode.
27721 + OperationMode AND bNonGFExist are for MM and GF Proteciton.
27722 + If MM or GF mask is not set, those passing argument doesn't not take effect.
27723 +
27724 + Operation mode meaning:
27725 + = 0 : Pure HT, no preotection.
27726 + = 0x01; there may be non-HT devices in both the control and extension channel, protection is optional in BSS.
27727 + = 0x10: No Transmission in 40M is protected.
27728 + = 0x11: Transmission in both 40M and 20M shall be protected
27729 + if (bNonGFExist)
27730 + we should choose not to use GF. But still set correct ASIC registers.
27731 + ========================================================================
27732 +*/
27733 +VOID AsicUpdateProtect(
27734 + IN PRTMP_ADAPTER pAd,
27735 + IN USHORT OperationMode,
27736 + IN UCHAR SetMask,
27737 + IN BOOLEAN bDisableBGProtect,
27738 + IN BOOLEAN bNonGFExist)
27739 +{
27740 + PROT_CFG_STRUC ProtCfg, ProtCfg4;
27741 + UINT32 Protect[6];
27742 + USHORT offset;
27743 + UCHAR i;
27744 + UINT32 MacReg = 0;
27745 +
27746 +#ifdef RALINK_ATE
27747 + if (ATE_ON(pAd))
27748 + return;
27749 +#endif // RALINK_ATE //
27750 +
27751 +#ifdef DOT11_N_SUPPORT
27752 + if (!(pAd->CommonCfg.bHTProtect) && (OperationMode != 8))
27753 + {
27754 + return;
27755 + }
27756 +
27757 + if (pAd->BATable.numAsOriginator)
27758 + {
27759 + //
27760 + // enable the RTS/CTS to avoid channel collision
27761 + //
27762 + SetMask = ALLN_SETPROTECT;
27763 + OperationMode = 8;
27764 + }
27765 +#endif // DOT11_N_SUPPORT //
27766 +
27767 + // Config ASIC RTS threshold register
27768 + RTMP_IO_READ32(pAd, TX_RTS_CFG, &MacReg);
27769 + MacReg &= 0xFF0000FF;
27770 +#if 0
27771 + MacReg |= (pAd->CommonCfg.RtsThreshold << 8);
27772 +#else
27773 + // If the user want disable RtsThreshold and enbale Amsdu/Ralink-Aggregation, set the RtsThreshold as 4096
27774 + if ((
27775 +#ifdef DOT11_N_SUPPORT
27776 + (pAd->CommonCfg.BACapability.field.AmsduEnable) ||
27777 +#endif // DOT11_N_SUPPORT //
27778 + (pAd->CommonCfg.bAggregationCapable == TRUE))
27779 + && pAd->CommonCfg.RtsThreshold == MAX_RTS_THRESHOLD)
27780 + {
27781 + MacReg |= (0x1000 << 8);
27782 + }
27783 + else
27784 + {
27785 + MacReg |= (pAd->CommonCfg.RtsThreshold << 8);
27786 + }
27787 +#endif
27788 +
27789 + RTMP_IO_WRITE32(pAd, TX_RTS_CFG, MacReg);
27790 +
27791 + // Initial common protection settings
27792 + RTMPZeroMemory(Protect, sizeof(Protect));
27793 + ProtCfg4.word = 0;
27794 + ProtCfg.word = 0;
27795 + ProtCfg.field.TxopAllowGF40 = 1;
27796 + ProtCfg.field.TxopAllowGF20 = 1;
27797 + ProtCfg.field.TxopAllowMM40 = 1;
27798 + ProtCfg.field.TxopAllowMM20 = 1;
27799 + ProtCfg.field.TxopAllowOfdm = 1;
27800 + ProtCfg.field.TxopAllowCck = 1;
27801 + ProtCfg.field.RTSThEn = 1;
27802 + ProtCfg.field.ProtectNav = ASIC_SHORTNAV;
27803 +
27804 + // update PHY mode and rate
27805 + if (pAd->CommonCfg.Channel > 14)
27806 + ProtCfg.field.ProtectRate = 0x4000;
27807 + ProtCfg.field.ProtectRate |= pAd->CommonCfg.RtsRate;
27808 +
27809 + // Handle legacy(B/G) protection
27810 + if (bDisableBGProtect)
27811 + {
27812 + //ProtCfg.field.ProtectRate = pAd->CommonCfg.RtsRate;
27813 + ProtCfg.field.ProtectCtrl = 0;
27814 + Protect[0] = ProtCfg.word;
27815 + Protect[1] = ProtCfg.word;
27816 + }
27817 + else
27818 + {
27819 + //ProtCfg.field.ProtectRate = pAd->CommonCfg.RtsRate;
27820 + ProtCfg.field.ProtectCtrl = 0; // CCK do not need to be protected
27821 + Protect[0] = ProtCfg.word;
27822 + ProtCfg.field.ProtectCtrl = ASIC_CTS; // OFDM needs using CCK to protect
27823 + Protect[1] = ProtCfg.word;
27824 + }
27825 +
27826 +#ifdef DOT11_N_SUPPORT
27827 + // Decide HT frame protection.
27828 + if ((SetMask & ALLN_SETPROTECT) != 0)
27829 + {
27830 + switch(OperationMode)
27831 + {
27832 + case 0x0:
27833 + // NO PROTECT
27834 + // 1.All STAs in the BSS are 20/40 MHz HT
27835 + // 2. in ai 20/40MHz BSS
27836 + // 3. all STAs are 20MHz in a 20MHz BSS
27837 + // Pure HT. no protection.
27838 +
27839 + // MM20_PROT_CFG
27840 + // Reserved (31:27)
27841 + // PROT_TXOP(25:20) -- 010111
27842 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
27843 + // PROT_CTRL(17:16) -- 00 (None)
27844 + // PROT_RATE(15:0) -- 0x4004 (OFDM 24M)
27845 + Protect[2] = 0x01744004;
27846 +
27847 + // MM40_PROT_CFG
27848 + // Reserved (31:27)
27849 + // PROT_TXOP(25:20) -- 111111
27850 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
27851 + // PROT_CTRL(17:16) -- 00 (None)
27852 + // PROT_RATE(15:0) -- 0x4084 (duplicate OFDM 24M)
27853 + Protect[3] = 0x03f44084;
27854 +
27855 + // CF20_PROT_CFG
27856 + // Reserved (31:27)
27857 + // PROT_TXOP(25:20) -- 010111
27858 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
27859 + // PROT_CTRL(17:16) -- 00 (None)
27860 + // PROT_RATE(15:0) -- 0x4004 (OFDM 24M)
27861 + Protect[4] = 0x01744004;
27862 +
27863 + // CF40_PROT_CFG
27864 + // Reserved (31:27)
27865 + // PROT_TXOP(25:20) -- 111111
27866 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
27867 + // PROT_CTRL(17:16) -- 00 (None)
27868 + // PROT_RATE(15:0) -- 0x4084 (duplicate OFDM 24M)
27869 + Protect[5] = 0x03f44084;
27870 +
27871 + if (bNonGFExist)
27872 + {
27873 + // PROT_NAV(19:18) -- 01 (Short NAV protectiion)
27874 + // PROT_CTRL(17:16) -- 01 (RTS/CTS)
27875 + Protect[4] = 0x01754004;
27876 + Protect[5] = 0x03f54084;
27877 + }
27878 + pAd->CommonCfg.IOTestParm.bRTSLongProtOn = FALSE;
27879 + break;
27880 +
27881 + case 1:
27882 + // This is "HT non-member protection mode."
27883 + // If there may be non-HT STAs my BSS
27884 + ProtCfg.word = 0x01744004; // PROT_CTRL(17:16) : 0 (None)
27885 + ProtCfg4.word = 0x03f44084; // duplicaet legacy 24M. BW set 1.
27886 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED))
27887 + {
27888 + ProtCfg.word = 0x01740003; //ERP use Protection bit is set, use protection rate at Clause 18..
27889 + ProtCfg4.word = 0x03f40003; // Don't duplicate RTS/CTS in CCK mode. 0x03f40083;
27890 + }
27891 + //Assign Protection method for 20&40 MHz packets
27892 + ProtCfg.field.ProtectCtrl = ASIC_RTS;
27893 + ProtCfg.field.ProtectNav = ASIC_SHORTNAV;
27894 + ProtCfg4.field.ProtectCtrl = ASIC_RTS;
27895 + ProtCfg4.field.ProtectNav = ASIC_SHORTNAV;
27896 + Protect[2] = ProtCfg.word;
27897 + Protect[3] = ProtCfg4.word;
27898 + Protect[4] = ProtCfg.word;
27899 + Protect[5] = ProtCfg4.word;
27900 + pAd->CommonCfg.IOTestParm.bRTSLongProtOn = TRUE;
27901 + break;
27902 +
27903 + case 2:
27904 + // If only HT STAs are in BSS. at least one is 20MHz. Only protect 40MHz packets
27905 + ProtCfg.word = 0x01744004; // PROT_CTRL(17:16) : 0 (None)
27906 + ProtCfg4.word = 0x03f44084; // duplicaet legacy 24M. BW set 1.
27907 +
27908 + //Assign Protection method for 40MHz packets
27909 + ProtCfg4.field.ProtectCtrl = ASIC_RTS;
27910 + ProtCfg4.field.ProtectNav = ASIC_SHORTNAV;
27911 + Protect[2] = ProtCfg.word;
27912 + Protect[3] = ProtCfg4.word;
27913 + if (bNonGFExist)
27914 + {
27915 + ProtCfg.field.ProtectCtrl = ASIC_RTS;
27916 + ProtCfg.field.ProtectNav = ASIC_SHORTNAV;
27917 + }
27918 + Protect[4] = ProtCfg.word;
27919 + Protect[5] = ProtCfg4.word;
27920 +
27921 + pAd->CommonCfg.IOTestParm.bRTSLongProtOn = FALSE;
27922 + break;
27923 +
27924 + case 3:
27925 + // HT mixed mode. PROTECT ALL!
27926 + // Assign Rate
27927 + ProtCfg.word = 0x01744004; //duplicaet legacy 24M. BW set 1.
27928 + ProtCfg4.word = 0x03f44084;
27929 + // both 20MHz and 40MHz are protected. Whether use RTS or CTS-to-self depends on the
27930 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED))
27931 + {
27932 + ProtCfg.word = 0x01740003; //ERP use Protection bit is set, use protection rate at Clause 18..
27933 + ProtCfg4.word = 0x03f40003; // Don't duplicate RTS/CTS in CCK mode. 0x03f40083
27934 + }
27935 + //Assign Protection method for 20&40 MHz packets
27936 + ProtCfg.field.ProtectCtrl = ASIC_RTS;
27937 + ProtCfg.field.ProtectNav = ASIC_SHORTNAV;
27938 + ProtCfg4.field.ProtectCtrl = ASIC_RTS;
27939 + ProtCfg4.field.ProtectNav = ASIC_SHORTNAV;
27940 + Protect[2] = ProtCfg.word;
27941 + Protect[3] = ProtCfg4.word;
27942 + Protect[4] = ProtCfg.word;
27943 + Protect[5] = ProtCfg4.word;
27944 + pAd->CommonCfg.IOTestParm.bRTSLongProtOn = TRUE;
27945 + break;
27946 +
27947 + case 8:
27948 + // Special on for Atheros problem n chip.
27949 + Protect[2] = 0x01754004;
27950 + Protect[3] = 0x03f54084;
27951 + Protect[4] = 0x01754004;
27952 + Protect[5] = 0x03f54084;
27953 + pAd->CommonCfg.IOTestParm.bRTSLongProtOn = TRUE;
27954 + break;
27955 + }
27956 + }
27957 +#endif // DOT11_N_SUPPORT //
27958 +
27959 + offset = CCK_PROT_CFG;
27960 + for (i = 0;i < 6;i++)
27961 + {
27962 + if ((SetMask & (1<< i)))
27963 + {
27964 + RTMP_IO_WRITE32(pAd, offset + i*4, Protect[i]);
27965 + }
27966 + }
27967 +}
27968 +
27969 +/*
27970 + ==========================================================================
27971 + Description:
27972 +
27973 + IRQL = PASSIVE_LEVEL
27974 + IRQL = DISPATCH_LEVEL
27975 +
27976 + ==========================================================================
27977 + */
27978 +VOID AsicSwitchChannel(
27979 + IN PRTMP_ADAPTER pAd,
27980 + IN UCHAR Channel,
27981 + IN BOOLEAN bScan)
27982 +{
27983 + ULONG R2 = 0, R3 = DEFAULT_RF_TX_POWER, R4 = 0;
27984 + CHAR TxPwer = 0, TxPwer2 = DEFAULT_RF_TX_POWER; //Bbp94 = BBPR94_DEFAULT, TxPwer2 = DEFAULT_RF_TX_POWER;
27985 + UCHAR index;
27986 + UINT32 Value = 0; //BbpReg, Value;
27987 + RTMP_RF_REGS *RFRegTable;
27988 +
27989 + // Search Tx power value
27990 + for (index = 0; index < pAd->ChannelListNum; index++)
27991 + {
27992 + if (Channel == pAd->ChannelList[index].Channel)
27993 + {
27994 + TxPwer = pAd->ChannelList[index].Power;
27995 + TxPwer2 = pAd->ChannelList[index].Power2;
27996 + break;
27997 + }
27998 + }
27999 +
28000 + if (index == MAX_NUM_OF_CHANNELS)
28001 + {
28002 + DBGPRINT(RT_DEBUG_ERROR, ("AsicSwitchChannel: Cant find the Channel#%d \n", Channel));
28003 + }
28004 +
28005 + {
28006 + RFRegTable = RF2850RegTable;
28007 +
28008 + switch (pAd->RfIcType)
28009 + {
28010 + case RFIC_2820:
28011 + case RFIC_2850:
28012 + case RFIC_2720:
28013 + case RFIC_2750:
28014 +
28015 + for (index = 0; index < NUM_OF_2850_CHNL; index++)
28016 + {
28017 + if (Channel == RFRegTable[index].Channel)
28018 + {
28019 + R2 = RFRegTable[index].R2;
28020 + if (pAd->Antenna.field.TxPath == 1)
28021 + {
28022 + R2 |= 0x4000; // If TXpath is 1, bit 14 = 1;
28023 + }
28024 +
28025 + if (pAd->Antenna.field.RxPath == 2)
28026 + {
28027 + R2 |= 0x40; // write 1 to off Rxpath.
28028 + }
28029 + else if (pAd->Antenna.field.RxPath == 1)
28030 + {
28031 + R2 |= 0x20040; // write 1 to off RxPath
28032 + }
28033 +
28034 + if (Channel > 14)
28035 + {
28036 + // initialize R3, R4
28037 + R3 = (RFRegTable[index].R3 & 0xffffc1ff);
28038 + R4 = (RFRegTable[index].R4 & (~0x001f87c0)) | (pAd->RfFreqOffset << 15);
28039 +
28040 + // 5G band power range: 0xF9~0X0F, TX0 Reg3 bit9/TX1 Reg4 bit6="0" means the TX power reduce 7dB
28041 + // R3
28042 + if ((TxPwer >= -7) && (TxPwer < 0))
28043 + {
28044 + TxPwer = (7+TxPwer);
28045 + TxPwer = (TxPwer > 0xF) ? (0xF) : (TxPwer);
28046 + R3 |= (TxPwer << 10);
28047 + DBGPRINT(RT_DEBUG_ERROR, ("AsicSwitchChannel: TxPwer=%d \n", TxPwer));
28048 + }
28049 + else
28050 + {
28051 + TxPwer = (TxPwer > 0xF) ? (0xF) : (TxPwer);
28052 + R3 |= (TxPwer << 10) | (1 << 9);
28053 + }
28054 +
28055 + // R4
28056 + if ((TxPwer2 >= -7) && (TxPwer2 < 0))
28057 + {
28058 + TxPwer2 = (7+TxPwer2);
28059 + TxPwer2 = (TxPwer2 > 0xF) ? (0xF) : (TxPwer2);
28060 + R4 |= (TxPwer2 << 7);
28061 + DBGPRINT(RT_DEBUG_ERROR, ("AsicSwitchChannel: TxPwer2=%d \n", TxPwer2));
28062 + }
28063 + else
28064 + {
28065 + TxPwer2 = (TxPwer2 > 0xF) ? (0xF) : (TxPwer2);
28066 + R4 |= (TxPwer2 << 7) | (1 << 6);
28067 + }
28068 + }
28069 + else
28070 + {
28071 + R3 = (RFRegTable[index].R3 & 0xffffc1ff) | (TxPwer << 9); // set TX power0
28072 + R4 = (RFRegTable[index].R4 & (~0x001f87c0)) | (pAd->RfFreqOffset << 15) | (TxPwer2 <<6);// Set freq Offset & TxPwr1
28073 + }
28074 +
28075 + // Based on BBP current mode before changing RF channel.
28076 + if (!bScan && (pAd->CommonCfg.BBPCurrentBW == BW_40))
28077 + {
28078 + R4 |=0x200000;
28079 + }
28080 +
28081 + // Update variables
28082 + pAd->LatchRfRegs.Channel = Channel;
28083 + pAd->LatchRfRegs.R1 = RFRegTable[index].R1;
28084 + pAd->LatchRfRegs.R2 = R2;
28085 + pAd->LatchRfRegs.R3 = R3;
28086 + pAd->LatchRfRegs.R4 = R4;
28087 +
28088 + // Set RF value 1's set R3[bit2] = [0]
28089 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R1);
28090 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R2);
28091 + RTMP_RF_IO_WRITE32(pAd, (pAd->LatchRfRegs.R3 & (~0x04)));
28092 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R4);
28093 +
28094 + RTMPusecDelay(200);
28095 +
28096 + // Set RF value 2's set R3[bit2] = [1]
28097 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R1);
28098 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R2);
28099 + RTMP_RF_IO_WRITE32(pAd, (pAd->LatchRfRegs.R3 | 0x04));
28100 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R4);
28101 +
28102 + RTMPusecDelay(200);
28103 +
28104 + // Set RF value 3's set R3[bit2] = [0]
28105 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R1);
28106 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R2);
28107 + RTMP_RF_IO_WRITE32(pAd, (pAd->LatchRfRegs.R3 & (~0x04)));
28108 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R4);
28109 +
28110 + break;
28111 + }
28112 + }
28113 + break;
28114 +
28115 + default:
28116 + break;
28117 + }
28118 + }
28119 +
28120 + // Change BBP setting during siwtch from a->g, g->a
28121 + if (Channel <= 14)
28122 + {
28123 + ULONG TxPinCfg = 0x00050F0A;//Gary 2007/08/09 0x050A0A
28124 +
28125 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R62, (0x37 - GET_LNA_GAIN(pAd)));
28126 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R63, (0x37 - GET_LNA_GAIN(pAd)));
28127 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R64, (0x37 - GET_LNA_GAIN(pAd)));
28128 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R86, 0);//(0x44 - GET_LNA_GAIN(pAd))); // According the Rory's suggestion to solve the middle range issue.
28129 + //RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R82, 0x62);
28130 +
28131 + // Rx High power VGA offset for LNA select
28132 + if (pAd->NicConfig2.field.ExternalLNAForG)
28133 + {
28134 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R82, 0x62);
28135 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R75, 0x46);
28136 + }
28137 + else
28138 + {
28139 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R82, 0x84);
28140 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R75, 0x50);
28141 + }
28142 +
28143 + // 5G band selection PIN, bit1 and bit2 are complement
28144 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Value);
28145 + Value &= (~0x6);
28146 + Value |= (0x04);
28147 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Value);
28148 +
28149 + // Turn off unused PA or LNA when only 1T or 1R
28150 + if (pAd->Antenna.field.TxPath == 1)
28151 + {
28152 + TxPinCfg &= 0xFFFFFFF3;
28153 + }
28154 + if (pAd->Antenna.field.RxPath == 1)
28155 + {
28156 + TxPinCfg &= 0xFFFFF3FF;
28157 + }
28158 +
28159 + RTMP_IO_WRITE32(pAd, TX_PIN_CFG, TxPinCfg);
28160 + }
28161 + else
28162 + {
28163 + ULONG TxPinCfg = 0x00050F05;//Gary 2007/8/9 0x050505
28164 +
28165 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R62, (0x37 - GET_LNA_GAIN(pAd)));
28166 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R63, (0x37 - GET_LNA_GAIN(pAd)));
28167 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R64, (0x37 - GET_LNA_GAIN(pAd)));
28168 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R86, 0);//(0x44 - GET_LNA_GAIN(pAd))); // According the Rory's suggestion to solve the middle range issue.
28169 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R82, 0xF2);
28170 +
28171 + // Rx High power VGA offset for LNA select
28172 + if (pAd->NicConfig2.field.ExternalLNAForA)
28173 + {
28174 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R75, 0x46);
28175 + }
28176 + else
28177 + {
28178 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R75, 0x50);
28179 + }
28180 +
28181 + // 5G band selection PIN, bit1 and bit2 are complement
28182 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Value);
28183 + Value &= (~0x6);
28184 + Value |= (0x02);
28185 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Value);
28186 +
28187 + // Turn off unused PA or LNA when only 1T or 1R
28188 + if (pAd->Antenna.field.TxPath == 1)
28189 + {
28190 + TxPinCfg &= 0xFFFFFFF3;
28191 + }
28192 + if (pAd->Antenna.field.RxPath == 1)
28193 + {
28194 + TxPinCfg &= 0xFFFFF3FF;
28195 + }
28196 +
28197 + RTMP_IO_WRITE32(pAd, TX_PIN_CFG, TxPinCfg);
28198 + }
28199 +
28200 + // R66 should be set according to Channel and use 20MHz when scanning
28201 + //RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, (0x2E + GET_LNA_GAIN(pAd)));
28202 + if (bScan)
28203 + RTMPSetAGCInitValue(pAd, BW_20);
28204 + else
28205 + RTMPSetAGCInitValue(pAd, pAd->CommonCfg.BBPCurrentBW);
28206 +
28207 + //
28208 + // On 11A, We should delay and wait RF/BBP to be stable
28209 + // and the appropriate time should be 1000 micro seconds
28210 + // 2005/06/05 - On 11G, We also need this delay time. Otherwise it's difficult to pass the WHQL.
28211 + //
28212 + RTMPusecDelay(1000);
28213 +
28214 + DBGPRINT(RT_DEBUG_TRACE, ("SwitchChannel#%d(RF=%d, Pwr0=%lu, Pwr1=%lu, %dT) to , R1=0x%08lx, R2=0x%08lx, R3=0x%08lx, R4=0x%08lx\n",
28215 + Channel,
28216 + pAd->RfIcType,
28217 + (R3 & 0x00003e00) >> 9,
28218 + (R4 & 0x000007c0) >> 6,
28219 + pAd->Antenna.field.TxPath,
28220 + pAd->LatchRfRegs.R1,
28221 + pAd->LatchRfRegs.R2,
28222 + pAd->LatchRfRegs.R3,
28223 + pAd->LatchRfRegs.R4));
28224 +}
28225 +
28226 +/*
28227 + ==========================================================================
28228 + Description:
28229 + This function is required for 2421 only, and should not be used during
28230 + site survey. It's only required after NIC decided to stay at a channel
28231 + for a longer period.
28232 + When this function is called, it's always after AsicSwitchChannel().
28233 +
28234 + IRQL = PASSIVE_LEVEL
28235 + IRQL = DISPATCH_LEVEL
28236 +
28237 + ==========================================================================
28238 + */
28239 +VOID AsicLockChannel(
28240 + IN PRTMP_ADAPTER pAd,
28241 + IN UCHAR Channel)
28242 +{
28243 +}
28244 +
28245 +/*
28246 + ==========================================================================
28247 + Description:
28248 +
28249 + IRQL = PASSIVE_LEVEL
28250 + IRQL = DISPATCH_LEVEL
28251 +
28252 + ==========================================================================
28253 + */
28254 +VOID AsicAntennaSelect(
28255 + IN PRTMP_ADAPTER pAd,
28256 + IN UCHAR Channel)
28257 +{
28258 +}
28259 +
28260 +/*
28261 + ========================================================================
28262 +
28263 + Routine Description:
28264 + Antenna miscellaneous setting.
28265 +
28266 + Arguments:
28267 + pAd Pointer to our adapter
28268 + BandState Indicate current Band State.
28269 +
28270 + Return Value:
28271 + None
28272 +
28273 + IRQL <= DISPATCH_LEVEL
28274 +
28275 + Note:
28276 + 1.) Frame End type control
28277 + only valid for G only (RF_2527 & RF_2529)
28278 + 0: means DPDT, set BBP R4 bit 5 to 1
28279 + 1: means SPDT, set BBP R4 bit 5 to 0
28280 +
28281 +
28282 + ========================================================================
28283 +*/
28284 +VOID AsicAntennaSetting(
28285 + IN PRTMP_ADAPTER pAd,
28286 + IN ABGBAND_STATE BandState)
28287 +{
28288 +}
28289 +
28290 +VOID AsicRfTuningExec(
28291 + IN PVOID SystemSpecific1,
28292 + IN PVOID FunctionContext,
28293 + IN PVOID SystemSpecific2,
28294 + IN PVOID SystemSpecific3)
28295 +{
28296 +}
28297 +
28298 +/*
28299 + ==========================================================================
28300 + Description:
28301 + Gives CCK TX rate 2 more dB TX power.
28302 + This routine works only in LINK UP in INFRASTRUCTURE mode.
28303 +
28304 + calculate desired Tx power in RF R3.Tx0~5, should consider -
28305 + 0. if current radio is a noisy environment (pAd->DrsCounters.fNoisyEnvironment)
28306 + 1. TxPowerPercentage
28307 + 2. auto calibration based on TSSI feedback
28308 + 3. extra 2 db for CCK
28309 + 4. -10 db upon very-short distance (AvgRSSI >= -40db) to AP
28310 +
28311 + NOTE: Since this routine requires the value of (pAd->DrsCounters.fNoisyEnvironment),
28312 + it should be called AFTER MlmeDynamicTxRatSwitching()
28313 + ==========================================================================
28314 + */
28315 +VOID AsicAdjustTxPower(
28316 + IN PRTMP_ADAPTER pAd)
28317 +{
28318 + INT i, j;
28319 + CHAR DeltaPwr = 0;
28320 + BOOLEAN bAutoTxAgc = FALSE;
28321 + UCHAR TssiRef, *pTssiMinusBoundary, *pTssiPlusBoundary, TxAgcStep;
28322 + UCHAR BbpR1 = 0, BbpR49 = 0, idx;
28323 + PCHAR pTxAgcCompensate;
28324 + ULONG TxPwr[5];
28325 + CHAR Value;
28326 +
28327 + if (pAd->CommonCfg.BBPCurrentBW == BW_40)
28328 + {
28329 + if (pAd->CommonCfg.CentralChannel > 14)
28330 + {
28331 + TxPwr[0] = pAd->Tx40MPwrCfgABand[0];
28332 + TxPwr[1] = pAd->Tx40MPwrCfgABand[1];
28333 + TxPwr[2] = pAd->Tx40MPwrCfgABand[2];
28334 + TxPwr[3] = pAd->Tx40MPwrCfgABand[3];
28335 + TxPwr[4] = pAd->Tx40MPwrCfgABand[4];
28336 + }
28337 + else
28338 + {
28339 + TxPwr[0] = pAd->Tx40MPwrCfgGBand[0];
28340 + TxPwr[1] = pAd->Tx40MPwrCfgGBand[1];
28341 + TxPwr[2] = pAd->Tx40MPwrCfgGBand[2];
28342 + TxPwr[3] = pAd->Tx40MPwrCfgGBand[3];
28343 + TxPwr[4] = pAd->Tx40MPwrCfgGBand[4];
28344 + }
28345 + }
28346 + else
28347 + {
28348 + if (pAd->CommonCfg.Channel > 14)
28349 + {
28350 + TxPwr[0] = pAd->Tx20MPwrCfgABand[0];
28351 + TxPwr[1] = pAd->Tx20MPwrCfgABand[1];
28352 + TxPwr[2] = pAd->Tx20MPwrCfgABand[2];
28353 + TxPwr[3] = pAd->Tx20MPwrCfgABand[3];
28354 + TxPwr[4] = pAd->Tx20MPwrCfgABand[4];
28355 + }
28356 + else
28357 + {
28358 + TxPwr[0] = pAd->Tx20MPwrCfgGBand[0];
28359 + TxPwr[1] = pAd->Tx20MPwrCfgGBand[1];
28360 + TxPwr[2] = pAd->Tx20MPwrCfgGBand[2];
28361 + TxPwr[3] = pAd->Tx20MPwrCfgGBand[3];
28362 + TxPwr[4] = pAd->Tx20MPwrCfgGBand[4];
28363 + }
28364 + }
28365 +
28366 + // TX power compensation for temperature variation based on TSSI. try every 4 second
28367 + if (pAd->Mlme.OneSecPeriodicRound % 4 == 0)
28368 + {
28369 + if (pAd->CommonCfg.Channel <= 14)
28370 + {
28371 + /* bg channel */
28372 + bAutoTxAgc = pAd->bAutoTxAgcG;
28373 + TssiRef = pAd->TssiRefG;
28374 + pTssiMinusBoundary = &pAd->TssiMinusBoundaryG[0];
28375 + pTssiPlusBoundary = &pAd->TssiPlusBoundaryG[0];
28376 + TxAgcStep = pAd->TxAgcStepG;
28377 + pTxAgcCompensate = &pAd->TxAgcCompensateG;
28378 + }
28379 + else
28380 + {
28381 + /* a channel */
28382 + bAutoTxAgc = pAd->bAutoTxAgcA;
28383 + TssiRef = pAd->TssiRefA;
28384 + pTssiMinusBoundary = &pAd->TssiMinusBoundaryA[0];
28385 + pTssiPlusBoundary = &pAd->TssiPlusBoundaryA[0];
28386 + TxAgcStep = pAd->TxAgcStepA;
28387 + pTxAgcCompensate = &pAd->TxAgcCompensateA;
28388 + }
28389 +
28390 + if (bAutoTxAgc)
28391 + {
28392 + /* BbpR1 is unsigned char */
28393 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R49, &BbpR49);
28394 +
28395 + /* (p) TssiPlusBoundaryG[0] = 0 = (m) TssiMinusBoundaryG[0] */
28396 + /* compensate: +4 +3 +2 +1 0 -1 -2 -3 -4 * steps */
28397 + /* step value is defined in pAd->TxAgcStepG for tx power value */
28398 +
28399 + /* [4]+1+[4] p4 p3 p2 p1 o1 m1 m2 m3 m4 */
28400 + /* ex: 0x00 0x15 0x25 0x45 0x88 0xA0 0xB5 0xD0 0xF0
28401 + above value are examined in mass factory production */
28402 + /* [4] [3] [2] [1] [0] [1] [2] [3] [4] */
28403 +
28404 + /* plus (+) is 0x00 ~ 0x45, minus (-) is 0xa0 ~ 0xf0 */
28405 + /* if value is between p1 ~ o1 or o1 ~ s1, no need to adjust tx power */
28406 + /* if value is 0xa5, tx power will be -= TxAgcStep*(2-1) */
28407 +
28408 + if (BbpR49 > pTssiMinusBoundary[1])
28409 + {
28410 + // Reading is larger than the reference value
28411 + // check for how large we need to decrease the Tx power
28412 + for (idx = 1; idx < 5; idx++)
28413 + {
28414 + if (BbpR49 <= pTssiMinusBoundary[idx]) // Found the range
28415 + break;
28416 + }
28417 + // The index is the step we should decrease, idx = 0 means there is nothing to compensate
28418 + *pTxAgcCompensate = -(TxAgcStep * (idx-1));
28419 +
28420 + DeltaPwr += (*pTxAgcCompensate);
28421 + DBGPRINT(RT_DEBUG_TRACE, ("-- Tx Power, BBP R1=%x, TssiRef=%x, TxAgcStep=%x, step = -%d\n",
28422 + BbpR49, TssiRef, TxAgcStep, idx-1));
28423 + }
28424 + else if (BbpR49 < pTssiPlusBoundary[1])
28425 + {
28426 + // Reading is smaller than the reference value
28427 + // check for how large we need to increase the Tx power
28428 + for (idx = 1; idx < 5; idx++)
28429 + {
28430 + if (BbpR49 >= pTssiPlusBoundary[idx]) // Found the range
28431 + break;
28432 + }
28433 + // The index is the step we should increase, idx = 0 means there is nothing to compensate
28434 + *pTxAgcCompensate = TxAgcStep * (idx-1);
28435 + DeltaPwr += (*pTxAgcCompensate);
28436 + DBGPRINT(RT_DEBUG_TRACE, ("++ Tx Power, BBP R1=%x, TssiRef=%x, TxAgcStep=%x, step = +%d\n",
28437 + BbpR49, TssiRef, TxAgcStep, idx-1));
28438 + }
28439 + else
28440 + {
28441 + *pTxAgcCompensate = 0;
28442 + DBGPRINT(RT_DEBUG_TRACE, (" Tx Power, BBP R49=%x, TssiRef=%x, TxAgcStep=%x, step = +%d\n",
28443 + BbpR49, TssiRef, TxAgcStep, 0));
28444 + }
28445 + }
28446 + }
28447 + else
28448 + {
28449 + if (pAd->CommonCfg.Channel <= 14)
28450 + {
28451 + bAutoTxAgc = pAd->bAutoTxAgcG;
28452 + pTxAgcCompensate = &pAd->TxAgcCompensateG;
28453 + }
28454 + else
28455 + {
28456 + bAutoTxAgc = pAd->bAutoTxAgcA;
28457 + pTxAgcCompensate = &pAd->TxAgcCompensateA;
28458 + }
28459 +
28460 + if (bAutoTxAgc)
28461 + DeltaPwr += (*pTxAgcCompensate);
28462 + }
28463 +
28464 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &BbpR1);
28465 + BbpR1 &= 0xFC;
28466 +
28467 +#ifdef SINGLE_SKU
28468 + // Handle regulatory max tx power constrain
28469 + do
28470 + {
28471 + UCHAR TxPwrInEEPROM = 0xFF, CountryTxPwr = 0xFF, criterion;
28472 + UCHAR AdjustMaxTxPwr[40];
28473 +
28474 + if (pAd->CommonCfg.Channel > 14) // 5G band
28475 + TxPwrInEEPROM = ((pAd->CommonCfg.DefineMaxTxPwr & 0xFF00) >> 8);
28476 + else // 2.4G band
28477 + TxPwrInEEPROM = (pAd->CommonCfg.DefineMaxTxPwr & 0x00FF);
28478 + CountryTxPwr = GetCuntryMaxTxPwr(pAd, pAd->CommonCfg.Channel);
28479 +
28480 + // error handling, range check
28481 + if ((TxPwrInEEPROM > 0x50) || (CountryTxPwr > 0x50))
28482 + {
28483 + DBGPRINT(RT_DEBUG_ERROR,("AsicAdjustTxPower - Invalid max tx power (=0x%02x), CountryTxPwr=%d\n", TxPwrInEEPROM, CountryTxPwr));
28484 + break;
28485 + }
28486 +
28487 + criterion = *((PUCHAR)TxPwr + 2) & 0xF; // FAE use OFDM 6M as criterion
28488 +
28489 + DBGPRINT_RAW(RT_DEBUG_TRACE,("AsicAdjustTxPower (criterion=%d, TxPwrInEEPROM=%d, CountryTxPwr=%d)\n", criterion, TxPwrInEEPROM, CountryTxPwr));
28490 +
28491 + // Adjust max tx power according to the relationship of tx power in E2PROM
28492 + for (i=0; i<5; i++)
28493 + {
28494 + // CCK will have 4dBm larger than OFDM
28495 + // Therefore, we should separate to parse the tx power field
28496 + if (i == 0)
28497 + {
28498 + for (j=0; j<8; j++)
28499 + {
28500 + Value = (CHAR)((TxPwr[i] >> j*4) & 0x0F);
28501 +
28502 + if (j < 4)
28503 + {
28504 + // CCK will have 4dBm larger than OFDM
28505 + AdjustMaxTxPwr[i*8+j] = TxPwrInEEPROM + (Value - criterion) + 4;
28506 + }
28507 + else
28508 + {
28509 + AdjustMaxTxPwr[i*8+j] = TxPwrInEEPROM + (Value - criterion);
28510 + }
28511 + DBGPRINT_RAW(RT_DEBUG_TRACE,("AsicAdjustTxPower (i/j=%d/%d, Value=%d, %d)\n", i, j, Value, AdjustMaxTxPwr[i*8+j]));
28512 + }
28513 + }
28514 + else
28515 + {
28516 + for (j=0; j<8; j++)
28517 + {
28518 + Value = (CHAR)((TxPwr[i] >> j*4) & 0x0F);
28519 +
28520 + AdjustMaxTxPwr[i*8+j] = TxPwrInEEPROM + (Value - criterion);
28521 + DBGPRINT_RAW(RT_DEBUG_TRACE,("AsicAdjustTxPower (i/j=%d/%d, Value=%d, %d)\n", i, j, Value, AdjustMaxTxPwr[i*8+j]));
28522 + }
28523 + }
28524 + }
28525 +
28526 + // Adjust tx power according to the relationship
28527 + for (i=0; i<5; i++)
28528 + {
28529 + if (TxPwr[i] != 0xffffffff)
28530 + {
28531 + for (j=0; j<8; j++)
28532 + {
28533 + Value = (CHAR)((TxPwr[i] >> j*4) & 0x0F);
28534 +
28535 + // The system tx power is larger than the regulatory, the power should be restrain
28536 + if (AdjustMaxTxPwr[i*8+j] > CountryTxPwr)
28537 + {
28538 + // decrease to zero and don't need to take care BBPR1
28539 + if ((Value - (AdjustMaxTxPwr[i*8+j] - CountryTxPwr)) > 0)
28540 + Value -= (AdjustMaxTxPwr[i*8+j] - CountryTxPwr);
28541 + else
28542 + Value = 0;
28543 +
28544 + DBGPRINT_RAW(RT_DEBUG_TRACE,("AsicAdjustTxPower (i/j=%d/%d, Value=%d, %d)\n", i, j, Value, AdjustMaxTxPwr[i*8+j]));
28545 + }
28546 + else
28547 + DBGPRINT_RAW(RT_DEBUG_TRACE,("AsicAdjustTxPower (i/j=%d/%d, Value=%d, %d, no change)\n", i, j, Value, AdjustMaxTxPwr[i*8+j]));
28548 +
28549 + TxPwr[i] = (TxPwr[i] & ~(0x0000000F << j*4)) | (Value << j*4);
28550 + }
28551 + }
28552 + }
28553 + } while (FALSE);
28554 +#endif // SINGLE_SKU //
28555 +
28556 + /* calculate delta power based on the percentage specified from UI */
28557 + // E2PROM setting is calibrated for maximum TX power (i.e. 100%)
28558 + // We lower TX power here according to the percentage specified from UI
28559 + if (pAd->CommonCfg.TxPowerPercentage == 0xffffffff) // AUTO TX POWER control
28560 + ;
28561 + else if (pAd->CommonCfg.TxPowerPercentage > 90) // 91 ~ 100% & AUTO, treat as 100% in terms of mW
28562 + ;
28563 + else if (pAd->CommonCfg.TxPowerPercentage > 60) // 61 ~ 90%, treat as 75% in terms of mW // DeltaPwr -= 1;
28564 + {
28565 + DeltaPwr -= 1;
28566 + }
28567 + else if (pAd->CommonCfg.TxPowerPercentage > 30) // 31 ~ 60%, treat as 50% in terms of mW // DeltaPwr -= 3;
28568 + {
28569 + DeltaPwr -= 3;
28570 + }
28571 + else if (pAd->CommonCfg.TxPowerPercentage > 15) // 16 ~ 30%, treat as 25% in terms of mW // DeltaPwr -= 6;
28572 + {
28573 + BbpR1 |= 0x01;
28574 + }
28575 + else if (pAd->CommonCfg.TxPowerPercentage > 9) // 10 ~ 15%, treat as 12.5% in terms of mW // DeltaPwr -= 9;
28576 + {
28577 + BbpR1 |= 0x01;
28578 + DeltaPwr -= 3;
28579 + }
28580 + else // 0 ~ 9 %, treat as MIN(~3%) in terms of mW // DeltaPwr -= 12;
28581 + {
28582 + BbpR1 |= 0x02;
28583 + }
28584 +
28585 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, BbpR1);
28586 +
28587 + /* reset different new tx power for different TX rate */
28588 + for(i=0; i<5; i++)
28589 + {
28590 + if (TxPwr[i] != 0xffffffff)
28591 + {
28592 + for (j=0; j<8; j++)
28593 + {
28594 + Value = (CHAR)((TxPwr[i] >> j*4) & 0x0F); /* 0 ~ 15 */
28595 +
28596 + if ((Value + DeltaPwr) < 0)
28597 + {
28598 + Value = 0; /* min */
28599 + }
28600 + else if ((Value + DeltaPwr) > 0xF)
28601 + {
28602 + Value = 0xF; /* max */
28603 + }
28604 + else
28605 + {
28606 + Value += DeltaPwr; /* temperature compensation */
28607 + }
28608 +
28609 + /* fill new value to CSR offset */
28610 + TxPwr[i] = (TxPwr[i] & ~(0x0000000F << j*4)) | (Value << j*4);
28611 + }
28612 +
28613 + /* write tx power value to CSR */
28614 + /* TX_PWR_CFG_0 (8 tx rate) for TX power for OFDM 12M/18M
28615 + TX power for OFDM 6M/9M
28616 + TX power for CCK5.5M/11M
28617 + TX power for CCK1M/2M */
28618 + /* TX_PWR_CFG_1 ~ TX_PWR_CFG_4 */
28619 + RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i*4, TxPwr[i]);
28620 + }
28621 + }
28622 +
28623 +}
28624 +
28625 +#ifdef CONFIG_STA_SUPPORT
28626 +/*
28627 + ==========================================================================
28628 + Description:
28629 + put PHY to sleep here, and set next wakeup timer. PHY doesn't not wakeup
28630 + automatically. Instead, MCU will issue a TwakeUpInterrupt to host after
28631 + the wakeup timer timeout. Driver has to issue a separate command to wake
28632 + PHY up.
28633 +
28634 + IRQL = DISPATCH_LEVEL
28635 +
28636 + ==========================================================================
28637 + */
28638 +VOID AsicSleepThenAutoWakeup(
28639 + IN PRTMP_ADAPTER pAd,
28640 + IN USHORT TbttNumToNextWakeUp)
28641 +{
28642 + RT28XX_STA_SLEEP_THEN_AUTO_WAKEUP(pAd, TbttNumToNextWakeUp);
28643 +}
28644 +
28645 +/*
28646 + ==========================================================================
28647 + Description:
28648 + AsicForceWakeup() is used whenever manual wakeup is required
28649 + AsicForceSleep() should only be used when not in INFRA BSS. When
28650 + in INFRA BSS, we should use AsicSleepThenAutoWakeup() instead.
28651 + ==========================================================================
28652 + */
28653 +VOID AsicForceSleep(
28654 + IN PRTMP_ADAPTER pAd)
28655 +{
28656 +
28657 +}
28658 +
28659 +/*
28660 + ==========================================================================
28661 + Description:
28662 + AsicForceWakeup() is used whenever Twakeup timer (set via AsicSleepThenAutoWakeup)
28663 + expired.
28664 +
28665 + IRQL = PASSIVE_LEVEL
28666 + IRQL = DISPATCH_LEVEL
28667 + ==========================================================================
28668 + */
28669 +VOID AsicForceWakeup(
28670 + IN PRTMP_ADAPTER pAd,
28671 + IN BOOLEAN bFromTx)
28672 +{
28673 + DBGPRINT(RT_DEBUG_TRACE, ("--> AsicForceWakeup \n"));
28674 + RT28XX_STA_FORCE_WAKEUP(pAd, bFromTx);
28675 +}
28676 +#endif // CONFIG_STA_SUPPORT //
28677 +/*
28678 + ==========================================================================
28679 + Description:
28680 + Set My BSSID
28681 +
28682 + IRQL = DISPATCH_LEVEL
28683 +
28684 + ==========================================================================
28685 + */
28686 +VOID AsicSetBssid(
28687 + IN PRTMP_ADAPTER pAd,
28688 + IN PUCHAR pBssid)
28689 +{
28690 + ULONG Addr4;
28691 + DBGPRINT(RT_DEBUG_TRACE, ("==============> AsicSetBssid %x:%x:%x:%x:%x:%x\n",
28692 + pBssid[0],pBssid[1],pBssid[2],pBssid[3], pBssid[4],pBssid[5]));
28693 +
28694 + Addr4 = (ULONG)(pBssid[0]) |
28695 + (ULONG)(pBssid[1] << 8) |
28696 + (ULONG)(pBssid[2] << 16) |
28697 + (ULONG)(pBssid[3] << 24);
28698 + RTMP_IO_WRITE32(pAd, MAC_BSSID_DW0, Addr4);
28699 +
28700 + Addr4 = 0;
28701 + // always one BSSID in STA mode
28702 + Addr4 = (ULONG)(pBssid[4]) | (ULONG)(pBssid[5] << 8);
28703 +
28704 + RTMP_IO_WRITE32(pAd, MAC_BSSID_DW1, Addr4);
28705 +}
28706 +
28707 +VOID AsicSetMcastWC(
28708 + IN PRTMP_ADAPTER pAd)
28709 +{
28710 + MAC_TABLE_ENTRY *pEntry = &pAd->MacTab.Content[MCAST_WCID];
28711 + USHORT offset;
28712 +
28713 + pEntry->Sst = SST_ASSOC;
28714 + pEntry->Aid = MCAST_WCID; // Softap supports 1 BSSID and use WCID=0 as multicast Wcid index
28715 + pEntry->PsMode = PWR_ACTIVE;
28716 + pEntry->CurrTxRate = pAd->CommonCfg.MlmeRate;
28717 + offset = MAC_WCID_BASE + BSS0Mcast_WCID * HW_WCID_ENTRY_SIZE;
28718 +}
28719 +
28720 +/*
28721 + ==========================================================================
28722 + Description:
28723 +
28724 + IRQL = DISPATCH_LEVEL
28725 +
28726 + ==========================================================================
28727 + */
28728 +VOID AsicDelWcidTab(
28729 + IN PRTMP_ADAPTER pAd,
28730 + IN UCHAR Wcid)
28731 +{
28732 + ULONG Addr0 = 0x0, Addr1 = 0x0;
28733 + ULONG offset;
28734 +
28735 + DBGPRINT(RT_DEBUG_TRACE, ("AsicDelWcidTab==>Wcid = 0x%x\n",Wcid));
28736 + offset = MAC_WCID_BASE + Wcid * HW_WCID_ENTRY_SIZE;
28737 + RTMP_IO_WRITE32(pAd, offset, Addr0);
28738 + offset += 4;
28739 + RTMP_IO_WRITE32(pAd, offset, Addr1);
28740 +}
28741 +
28742 +/*
28743 + ==========================================================================
28744 + Description:
28745 +
28746 + IRQL = DISPATCH_LEVEL
28747 +
28748 + ==========================================================================
28749 + */
28750 +VOID AsicEnableRDG(
28751 + IN PRTMP_ADAPTER pAd)
28752 +{
28753 + TX_LINK_CFG_STRUC TxLinkCfg;
28754 + UINT32 Data = 0;
28755 +
28756 + RTMP_IO_READ32(pAd, TX_LINK_CFG, &TxLinkCfg.word);
28757 + TxLinkCfg.field.TxRDGEn = 1;
28758 + RTMP_IO_WRITE32(pAd, TX_LINK_CFG, TxLinkCfg.word);
28759 +
28760 + RTMP_IO_READ32(pAd, EDCA_AC0_CFG, &Data);
28761 + Data &= 0xFFFFFF00;
28762 + Data |= 0x80;
28763 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, Data);
28764 +
28765 + //OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_AGGREGATION_INUSED);
28766 +}
28767 +
28768 +/*
28769 + ==========================================================================
28770 + Description:
28771 +
28772 + IRQL = DISPATCH_LEVEL
28773 +
28774 + ==========================================================================
28775 + */
28776 +VOID AsicDisableRDG(
28777 + IN PRTMP_ADAPTER pAd)
28778 +{
28779 + TX_LINK_CFG_STRUC TxLinkCfg;
28780 + UINT32 Data = 0;
28781 +
28782 +
28783 + RTMP_IO_READ32(pAd, TX_LINK_CFG, &TxLinkCfg.word);
28784 + TxLinkCfg.field.TxRDGEn = 0;
28785 + RTMP_IO_WRITE32(pAd, TX_LINK_CFG, TxLinkCfg.word);
28786 +
28787 + RTMP_IO_READ32(pAd, EDCA_AC0_CFG, &Data);
28788 +
28789 + Data &= 0xFFFFFF00;
28790 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_DYNAMIC_BE_TXOP_ACTIVE)
28791 +#ifdef DOT11_N_SUPPORT
28792 + && (pAd->MacTab.fAnyStationMIMOPSDynamic == FALSE)
28793 +#endif // DOT11_N_SUPPORT //
28794 + )
28795 + {
28796 + // For CWC test, change txop from 0x30 to 0x20 in TxBurst mode
28797 + if (pAd->CommonCfg.bEnableTxBurst)
28798 + Data |= 0x20;
28799 + }
28800 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, Data);
28801 +}
28802 +
28803 +/*
28804 + ==========================================================================
28805 + Description:
28806 +
28807 + IRQL = PASSIVE_LEVEL
28808 + IRQL = DISPATCH_LEVEL
28809 +
28810 + ==========================================================================
28811 + */
28812 +VOID AsicDisableSync(
28813 + IN PRTMP_ADAPTER pAd)
28814 +{
28815 + BCN_TIME_CFG_STRUC csr;
28816 +
28817 + DBGPRINT(RT_DEBUG_TRACE, ("--->Disable TSF synchronization\n"));
28818 +
28819 + // 2003-12-20 disable TSF and TBTT while NIC in power-saving have side effect
28820 + // that NIC will never wakes up because TSF stops and no more
28821 + // TBTT interrupts
28822 + pAd->TbttTickCount = 0;
28823 + RTMP_IO_READ32(pAd, BCN_TIME_CFG, &csr.word);
28824 + csr.field.bBeaconGen = 0;
28825 + csr.field.bTBTTEnable = 0;
28826 + csr.field.TsfSyncMode = 0;
28827 + csr.field.bTsfTicking = 0;
28828 + RTMP_IO_WRITE32(pAd, BCN_TIME_CFG, csr.word);
28829 +
28830 +}
28831 +
28832 +/*
28833 + ==========================================================================
28834 + Description:
28835 +
28836 + IRQL = DISPATCH_LEVEL
28837 +
28838 + ==========================================================================
28839 + */
28840 +VOID AsicEnableBssSync(
28841 + IN PRTMP_ADAPTER pAd)
28842 +{
28843 + BCN_TIME_CFG_STRUC csr;
28844 +
28845 + DBGPRINT(RT_DEBUG_TRACE, ("--->AsicEnableBssSync(INFRA mode)\n"));
28846 +
28847 + RTMP_IO_READ32(pAd, BCN_TIME_CFG, &csr.word);
28848 +#ifdef CONFIG_STA_SUPPORT
28849 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
28850 + {
28851 + csr.field.BeaconInterval = pAd->CommonCfg.BeaconPeriod << 4; // ASIC register in units of 1/16 TU
28852 + csr.field.bTsfTicking = 1;
28853 + csr.field.TsfSyncMode = 1; // sync TSF in INFRASTRUCTURE mode
28854 + csr.field.bBeaconGen = 0; // do NOT generate BEACON
28855 + csr.field.bTBTTEnable = 1;
28856 + }
28857 +#endif // CONFIG_STA_SUPPORT //
28858 + RTMP_IO_WRITE32(pAd, BCN_TIME_CFG, csr.word);
28859 +}
28860 +
28861 +/*
28862 + ==========================================================================
28863 + Description:
28864 + Note:
28865 + BEACON frame in shared memory should be built ok before this routine
28866 + can be called. Otherwise, a garbage frame maybe transmitted out every
28867 + Beacon period.
28868 +
28869 + IRQL = DISPATCH_LEVEL
28870 +
28871 + ==========================================================================
28872 + */
28873 +VOID AsicEnableIbssSync(
28874 + IN PRTMP_ADAPTER pAd)
28875 +{
28876 + BCN_TIME_CFG_STRUC csr9;
28877 + PUCHAR ptr;
28878 + UINT i;
28879 +
28880 + DBGPRINT(RT_DEBUG_TRACE, ("--->AsicEnableIbssSync(ADHOC mode. MPDUtotalByteCount = %d)\n", pAd->BeaconTxWI.MPDUtotalByteCount));
28881 +
28882 + RTMP_IO_READ32(pAd, BCN_TIME_CFG, &csr9.word);
28883 + csr9.field.bBeaconGen = 0;
28884 + csr9.field.bTBTTEnable = 0;
28885 + csr9.field.bTsfTicking = 0;
28886 + RTMP_IO_WRITE32(pAd, BCN_TIME_CFG, csr9.word);
28887 +
28888 +#ifdef RT2860
28889 + // move BEACON TXD and frame content to on-chip memory
28890 + ptr = (PUCHAR)&pAd->BeaconTxWI;
28891 + for (i=0; i<TXWI_SIZE; i+=4) // 16-byte TXWI field
28892 + {
28893 + UINT32 longptr = *ptr + (*(ptr+1)<<8) + (*(ptr+2)<<16) + (*(ptr+3)<<24);
28894 + RTMP_IO_WRITE32(pAd, HW_BEACON_BASE0 + i, longptr);
28895 + ptr += 4;
28896 + }
28897 +
28898 + // start right after the 16-byte TXWI field
28899 + ptr = pAd->BeaconBuf;
28900 + for (i=0; i< pAd->BeaconTxWI.MPDUtotalByteCount; i+=4)
28901 + {
28902 + UINT32 longptr = *ptr + (*(ptr+1)<<8) + (*(ptr+2)<<16) + (*(ptr+3)<<24);
28903 + RTMP_IO_WRITE32(pAd, HW_BEACON_BASE0 + TXWI_SIZE + i, longptr);
28904 + ptr +=4;
28905 + }
28906 +#endif // RT2860 //
28907 +
28908 + // start sending BEACON
28909 + csr9.field.BeaconInterval = pAd->CommonCfg.BeaconPeriod << 4; // ASIC register in units of 1/16 TU
28910 + csr9.field.bTsfTicking = 1;
28911 + csr9.field.TsfSyncMode = 2; // sync TSF in IBSS mode
28912 + csr9.field.bTBTTEnable = 1;
28913 + csr9.field.bBeaconGen = 1;
28914 + RTMP_IO_WRITE32(pAd, BCN_TIME_CFG, csr9.word);
28915 +}
28916 +
28917 +/*
28918 + ==========================================================================
28919 + Description:
28920 +
28921 + IRQL = PASSIVE_LEVEL
28922 + IRQL = DISPATCH_LEVEL
28923 +
28924 + ==========================================================================
28925 + */
28926 +VOID AsicSetEdcaParm(
28927 + IN PRTMP_ADAPTER pAd,
28928 + IN PEDCA_PARM pEdcaParm)
28929 +{
28930 + EDCA_AC_CFG_STRUC Ac0Cfg, Ac1Cfg, Ac2Cfg, Ac3Cfg;
28931 + AC_TXOP_CSR0_STRUC csr0;
28932 + AC_TXOP_CSR1_STRUC csr1;
28933 + AIFSN_CSR_STRUC AifsnCsr;
28934 + CWMIN_CSR_STRUC CwminCsr;
28935 + CWMAX_CSR_STRUC CwmaxCsr;
28936 + int i;
28937 +
28938 + Ac0Cfg.word = 0;
28939 + Ac1Cfg.word = 0;
28940 + Ac2Cfg.word = 0;
28941 + Ac3Cfg.word = 0;
28942 + if ((pEdcaParm == NULL) || (pEdcaParm->bValid == FALSE))
28943 + {
28944 + DBGPRINT(RT_DEBUG_TRACE,("AsicSetEdcaParm\n"));
28945 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_WMM_INUSED);
28946 + for (i=0; i<MAX_LEN_OF_MAC_TABLE; i++)
28947 + {
28948 + if (pAd->MacTab.Content[i].ValidAsCLI || pAd->MacTab.Content[i].ValidAsApCli)
28949 + CLIENT_STATUS_CLEAR_FLAG(&pAd->MacTab.Content[i], fCLIENT_STATUS_WMM_CAPABLE);
28950 + }
28951 +
28952 + //========================================================
28953 + // MAC Register has a copy .
28954 + //========================================================
28955 + if( pAd->CommonCfg.bEnableTxBurst )
28956 + {
28957 + // For CWC test, change txop from 0x30 to 0x20 in TxBurst mode
28958 + Ac0Cfg.field.AcTxop = 0x20; // Suggest by John for TxBurst in HT Mode
28959 + }
28960 + else
28961 + Ac0Cfg.field.AcTxop = 0; // QID_AC_BE
28962 + Ac0Cfg.field.Cwmin = CW_MIN_IN_BITS;
28963 + Ac0Cfg.field.Cwmax = CW_MAX_IN_BITS;
28964 + Ac0Cfg.field.Aifsn = 2;
28965 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, Ac0Cfg.word);
28966 +
28967 + Ac1Cfg.field.AcTxop = 0; // QID_AC_BK
28968 + Ac1Cfg.field.Cwmin = CW_MIN_IN_BITS;
28969 + Ac1Cfg.field.Cwmax = CW_MAX_IN_BITS;
28970 + Ac1Cfg.field.Aifsn = 2;
28971 + RTMP_IO_WRITE32(pAd, EDCA_AC1_CFG, Ac1Cfg.word);
28972 +
28973 + if (pAd->CommonCfg.PhyMode == PHY_11B)
28974 + {
28975 + Ac2Cfg.field.AcTxop = 192; // AC_VI: 192*32us ~= 6ms
28976 + Ac3Cfg.field.AcTxop = 96; // AC_VO: 96*32us ~= 3ms
28977 + }
28978 + else
28979 + {
28980 + Ac2Cfg.field.AcTxop = 96; // AC_VI: 96*32us ~= 3ms
28981 + Ac3Cfg.field.AcTxop = 48; // AC_VO: 48*32us ~= 1.5ms
28982 + }
28983 + Ac2Cfg.field.Cwmin = CW_MIN_IN_BITS;
28984 + Ac2Cfg.field.Cwmax = CW_MAX_IN_BITS;
28985 + Ac2Cfg.field.Aifsn = 2;
28986 + RTMP_IO_WRITE32(pAd, EDCA_AC2_CFG, Ac2Cfg.word);
28987 + Ac3Cfg.field.Cwmin = CW_MIN_IN_BITS;
28988 + Ac3Cfg.field.Cwmax = CW_MAX_IN_BITS;
28989 + Ac3Cfg.field.Aifsn = 2;
28990 + RTMP_IO_WRITE32(pAd, EDCA_AC3_CFG, Ac3Cfg.word);
28991 +
28992 + //========================================================
28993 + // DMA Register has a copy too.
28994 + //========================================================
28995 + csr0.field.Ac0Txop = 0; // QID_AC_BE
28996 + csr0.field.Ac1Txop = 0; // QID_AC_BK
28997 + RTMP_IO_WRITE32(pAd, WMM_TXOP0_CFG, csr0.word);
28998 + if (pAd->CommonCfg.PhyMode == PHY_11B)
28999 + {
29000 + csr1.field.Ac2Txop = 192; // AC_VI: 192*32us ~= 6ms
29001 + csr1.field.Ac3Txop = 96; // AC_VO: 96*32us ~= 3ms
29002 + }
29003 + else
29004 + {
29005 + csr1.field.Ac2Txop = 96; // AC_VI: 96*32us ~= 3ms
29006 + csr1.field.Ac3Txop = 48; // AC_VO: 48*32us ~= 1.5ms
29007 + }
29008 + RTMP_IO_WRITE32(pAd, WMM_TXOP1_CFG, csr1.word);
29009 +
29010 + CwminCsr.word = 0;
29011 + CwminCsr.field.Cwmin0 = CW_MIN_IN_BITS;
29012 + CwminCsr.field.Cwmin1 = CW_MIN_IN_BITS;
29013 + CwminCsr.field.Cwmin2 = CW_MIN_IN_BITS;
29014 + CwminCsr.field.Cwmin3 = CW_MIN_IN_BITS;
29015 + RTMP_IO_WRITE32(pAd, WMM_CWMIN_CFG, CwminCsr.word);
29016 +
29017 + CwmaxCsr.word = 0;
29018 + CwmaxCsr.field.Cwmax0 = CW_MAX_IN_BITS;
29019 + CwmaxCsr.field.Cwmax1 = CW_MAX_IN_BITS;
29020 + CwmaxCsr.field.Cwmax2 = CW_MAX_IN_BITS;
29021 + CwmaxCsr.field.Cwmax3 = CW_MAX_IN_BITS;
29022 + RTMP_IO_WRITE32(pAd, WMM_CWMAX_CFG, CwmaxCsr.word);
29023 +
29024 + RTMP_IO_WRITE32(pAd, WMM_AIFSN_CFG, 0x00002222);
29025 +
29026 + NdisZeroMemory(&pAd->CommonCfg.APEdcaParm, sizeof(EDCA_PARM));
29027 + }
29028 + else
29029 + {
29030 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_WMM_INUSED);
29031 + //========================================================
29032 + // MAC Register has a copy.
29033 + //========================================================
29034 + //
29035 + // Modify Cwmin/Cwmax/Txop on queue[QID_AC_VI], Recommend by Jerry 2005/07/27
29036 + // To degrade our VIDO Queue's throughput for WiFi WMM S3T07 Issue.
29037 + //
29038 + //pEdcaParm->Txop[QID_AC_VI] = pEdcaParm->Txop[QID_AC_VI] * 7 / 10; // rt2860c need this
29039 +
29040 + Ac0Cfg.field.AcTxop = pEdcaParm->Txop[QID_AC_BE];
29041 + Ac0Cfg.field.Cwmin= pEdcaParm->Cwmin[QID_AC_BE];
29042 + Ac0Cfg.field.Cwmax = pEdcaParm->Cwmax[QID_AC_BE];
29043 + Ac0Cfg.field.Aifsn = pEdcaParm->Aifsn[QID_AC_BE]; //+1;
29044 +
29045 + Ac1Cfg.field.AcTxop = pEdcaParm->Txop[QID_AC_BK];
29046 + Ac1Cfg.field.Cwmin = pEdcaParm->Cwmin[QID_AC_BK]; //+2;
29047 + Ac1Cfg.field.Cwmax = pEdcaParm->Cwmax[QID_AC_BK];
29048 + Ac1Cfg.field.Aifsn = pEdcaParm->Aifsn[QID_AC_BK]; //+1;
29049 +
29050 + Ac2Cfg.field.AcTxop = (pEdcaParm->Txop[QID_AC_VI] * 6) / 10;
29051 + Ac2Cfg.field.Cwmin = pEdcaParm->Cwmin[QID_AC_VI];
29052 + Ac2Cfg.field.Cwmax = pEdcaParm->Cwmax[QID_AC_VI];
29053 + Ac2Cfg.field.Aifsn = pEdcaParm->Aifsn[QID_AC_VI];
29054 +#ifdef CONFIG_STA_SUPPORT
29055 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
29056 + {
29057 + // Tuning for Wi-Fi WMM S06
29058 + if (pAd->CommonCfg.bWiFiTest &&
29059 + pEdcaParm->Aifsn[QID_AC_VI] == 10)
29060 + Ac2Cfg.field.Aifsn -= 1;
29061 +
29062 + // Tuning for TGn Wi-Fi 5.2.32
29063 + // STA TestBed changes in this item: conexant legacy sta ==> broadcom 11n sta
29064 + if (STA_TGN_WIFI_ON(pAd) &&
29065 + pEdcaParm->Aifsn[QID_AC_VI] == 10)
29066 + {
29067 + Ac0Cfg.field.Aifsn = 3;
29068 + Ac2Cfg.field.AcTxop = 5;
29069 + }
29070 + }
29071 +#endif // CONFIG_STA_SUPPORT //
29072 +
29073 + Ac3Cfg.field.AcTxop = pEdcaParm->Txop[QID_AC_VO];
29074 + Ac3Cfg.field.Cwmin = pEdcaParm->Cwmin[QID_AC_VO];
29075 + Ac3Cfg.field.Cwmax = pEdcaParm->Cwmax[QID_AC_VO];
29076 + Ac3Cfg.field.Aifsn = pEdcaParm->Aifsn[QID_AC_VO];
29077 +
29078 +//#ifdef WIFI_TEST
29079 + if (pAd->CommonCfg.bWiFiTest)
29080 + {
29081 + if (Ac3Cfg.field.AcTxop == 102)
29082 + {
29083 + Ac0Cfg.field.AcTxop = pEdcaParm->Txop[QID_AC_BE] ? pEdcaParm->Txop[QID_AC_BE] : 10;
29084 + Ac0Cfg.field.Aifsn = pEdcaParm->Aifsn[QID_AC_BE]-1; /* AIFSN must >= 1 */
29085 + Ac1Cfg.field.AcTxop = pEdcaParm->Txop[QID_AC_BK];
29086 + Ac1Cfg.field.Aifsn = pEdcaParm->Aifsn[QID_AC_BK];
29087 + Ac2Cfg.field.AcTxop = pEdcaParm->Txop[QID_AC_VI];
29088 + } /* End of if */
29089 + }
29090 +//#endif // WIFI_TEST //
29091 +
29092 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, Ac0Cfg.word);
29093 + RTMP_IO_WRITE32(pAd, EDCA_AC1_CFG, Ac1Cfg.word);
29094 + RTMP_IO_WRITE32(pAd, EDCA_AC2_CFG, Ac2Cfg.word);
29095 + RTMP_IO_WRITE32(pAd, EDCA_AC3_CFG, Ac3Cfg.word);
29096 +
29097 +
29098 + //========================================================
29099 + // DMA Register has a copy too.
29100 + //========================================================
29101 + csr0.field.Ac0Txop = Ac0Cfg.field.AcTxop;
29102 + csr0.field.Ac1Txop = Ac1Cfg.field.AcTxop;
29103 + RTMP_IO_WRITE32(pAd, WMM_TXOP0_CFG, csr0.word);
29104 +
29105 + csr1.field.Ac2Txop = Ac2Cfg.field.AcTxop;
29106 + csr1.field.Ac3Txop = Ac3Cfg.field.AcTxop;
29107 + RTMP_IO_WRITE32(pAd, WMM_TXOP1_CFG, csr1.word);
29108 +
29109 + CwminCsr.word = 0;
29110 + CwminCsr.field.Cwmin0 = pEdcaParm->Cwmin[QID_AC_BE];
29111 + CwminCsr.field.Cwmin1 = pEdcaParm->Cwmin[QID_AC_BK];
29112 + CwminCsr.field.Cwmin2 = pEdcaParm->Cwmin[QID_AC_VI];
29113 +#ifdef CONFIG_STA_SUPPORT
29114 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
29115 + CwminCsr.field.Cwmin3 = pEdcaParm->Cwmin[QID_AC_VO] - 1; //for TGn wifi test
29116 +#endif // CONFIG_STA_SUPPORT //
29117 + RTMP_IO_WRITE32(pAd, WMM_CWMIN_CFG, CwminCsr.word);
29118 +
29119 + CwmaxCsr.word = 0;
29120 + CwmaxCsr.field.Cwmax0 = pEdcaParm->Cwmax[QID_AC_BE];
29121 + CwmaxCsr.field.Cwmax1 = pEdcaParm->Cwmax[QID_AC_BK];
29122 + CwmaxCsr.field.Cwmax2 = pEdcaParm->Cwmax[QID_AC_VI];
29123 + CwmaxCsr.field.Cwmax3 = pEdcaParm->Cwmax[QID_AC_VO];
29124 + RTMP_IO_WRITE32(pAd, WMM_CWMAX_CFG, CwmaxCsr.word);
29125 +
29126 + AifsnCsr.word = 0;
29127 + AifsnCsr.field.Aifsn0 = Ac0Cfg.field.Aifsn; //pEdcaParm->Aifsn[QID_AC_BE];
29128 + AifsnCsr.field.Aifsn1 = Ac1Cfg.field.Aifsn; //pEdcaParm->Aifsn[QID_AC_BK];
29129 + AifsnCsr.field.Aifsn2 = Ac2Cfg.field.Aifsn; //pEdcaParm->Aifsn[QID_AC_VI];
29130 +#ifdef CONFIG_STA_SUPPORT
29131 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
29132 + {
29133 + // Tuning for Wi-Fi WMM S06
29134 + if (pAd->CommonCfg.bWiFiTest &&
29135 + pEdcaParm->Aifsn[QID_AC_VI] == 10)
29136 + AifsnCsr.field.Aifsn2 = Ac2Cfg.field.Aifsn - 4;
29137 +
29138 + // Tuning for TGn Wi-Fi 5.2.32
29139 + // STA TestBed changes in this item: conexant legacy sta ==> broadcom 11n sta
29140 + if (STA_TGN_WIFI_ON(pAd) &&
29141 + pEdcaParm->Aifsn[QID_AC_VI] == 10)
29142 + {
29143 + AifsnCsr.field.Aifsn0 = 3;
29144 + AifsnCsr.field.Aifsn2 = 7;
29145 + }
29146 + }
29147 +#endif // CONFIG_STA_SUPPORT //
29148 +
29149 +#ifdef CONFIG_STA_SUPPORT
29150 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
29151 + AifsnCsr.field.Aifsn3 = Ac3Cfg.field.Aifsn - 1; //pEdcaParm->Aifsn[QID_AC_VO]; //for TGn wifi test
29152 +#endif // CONFIG_STA_SUPPORT //
29153 + RTMP_IO_WRITE32(pAd, WMM_AIFSN_CFG, AifsnCsr.word);
29154 +
29155 + NdisMoveMemory(&pAd->CommonCfg.APEdcaParm, pEdcaParm, sizeof(EDCA_PARM));
29156 + if (!ADHOC_ON(pAd))
29157 + {
29158 + DBGPRINT(RT_DEBUG_TRACE,("EDCA [#%d]: AIFSN CWmin CWmax TXOP(us) ACM\n", pEdcaParm->EdcaUpdateCount));
29159 + DBGPRINT(RT_DEBUG_TRACE,(" AC_BE %2d %2d %2d %4d %d\n",
29160 + pEdcaParm->Aifsn[0],
29161 + pEdcaParm->Cwmin[0],
29162 + pEdcaParm->Cwmax[0],
29163 + pEdcaParm->Txop[0]<<5,
29164 + pEdcaParm->bACM[0]));
29165 + DBGPRINT(RT_DEBUG_TRACE,(" AC_BK %2d %2d %2d %4d %d\n",
29166 + pEdcaParm->Aifsn[1],
29167 + pEdcaParm->Cwmin[1],
29168 + pEdcaParm->Cwmax[1],
29169 + pEdcaParm->Txop[1]<<5,
29170 + pEdcaParm->bACM[1]));
29171 + DBGPRINT(RT_DEBUG_TRACE,(" AC_VI %2d %2d %2d %4d %d\n",
29172 + pEdcaParm->Aifsn[2],
29173 + pEdcaParm->Cwmin[2],
29174 + pEdcaParm->Cwmax[2],
29175 + pEdcaParm->Txop[2]<<5,
29176 + pEdcaParm->bACM[2]));
29177 + DBGPRINT(RT_DEBUG_TRACE,(" AC_VO %2d %2d %2d %4d %d\n",
29178 + pEdcaParm->Aifsn[3],
29179 + pEdcaParm->Cwmin[3],
29180 + pEdcaParm->Cwmax[3],
29181 + pEdcaParm->Txop[3]<<5,
29182 + pEdcaParm->bACM[3]));
29183 + }
29184 + }
29185 +}
29186 +
29187 +/*
29188 + ==========================================================================
29189 + Description:
29190 +
29191 + IRQL = PASSIVE_LEVEL
29192 + IRQL = DISPATCH_LEVEL
29193 +
29194 + ==========================================================================
29195 + */
29196 +VOID AsicSetSlotTime(
29197 + IN PRTMP_ADAPTER pAd,
29198 + IN BOOLEAN bUseShortSlotTime)
29199 +{
29200 + ULONG SlotTime;
29201 + UINT32 RegValue = 0;
29202 +
29203 +#ifdef CONFIG_STA_SUPPORT
29204 + if (pAd->CommonCfg.Channel > 14)
29205 + bUseShortSlotTime = TRUE;
29206 +#endif // CONFIG_STA_SUPPORT //
29207 +
29208 + if (bUseShortSlotTime)
29209 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_SHORT_SLOT_INUSED);
29210 + else
29211 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_SLOT_INUSED);
29212 +
29213 + SlotTime = (bUseShortSlotTime)? 9 : 20;
29214 +
29215 +#ifdef CONFIG_STA_SUPPORT
29216 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
29217 + {
29218 + // force using short SLOT time for FAE to demo performance when TxBurst is ON
29219 + if (((pAd->StaActive.SupportedPhyInfo.bHtEnable == FALSE) && (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED)))
29220 +#ifdef DOT11_N_SUPPORT
29221 + || ((pAd->StaActive.SupportedPhyInfo.bHtEnable == TRUE) && (pAd->CommonCfg.BACapability.field.Policy == BA_NOTUSE))
29222 +#endif // DOT11_N_SUPPORT //
29223 + )
29224 + {
29225 + // In this case, we will think it is doing Wi-Fi test
29226 + // And we will not set to short slot when bEnableTxBurst is TRUE.
29227 + }
29228 + else if (pAd->CommonCfg.bEnableTxBurst)
29229 + SlotTime = 9;
29230 + }
29231 +#endif // CONFIG_STA_SUPPORT //
29232 +
29233 + //
29234 + // For some reasons, always set it to short slot time.
29235 + //
29236 + // ToDo: Should consider capability with 11B
29237 + //
29238 +#ifdef CONFIG_STA_SUPPORT
29239 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
29240 + {
29241 + if (pAd->StaCfg.BssType == BSS_ADHOC)
29242 + SlotTime = 20;
29243 + }
29244 +#endif // CONFIG_STA_SUPPORT //
29245 +
29246 + RTMP_IO_READ32(pAd, BKOFF_SLOT_CFG, &RegValue);
29247 + RegValue = RegValue & 0xFFFFFF00;
29248 +
29249 + RegValue |= SlotTime;
29250 +
29251 + RTMP_IO_WRITE32(pAd, BKOFF_SLOT_CFG, RegValue);
29252 +}
29253 +
29254 +/*
29255 + ========================================================================
29256 + Description:
29257 + Add Shared key information into ASIC.
29258 + Update shared key, TxMic and RxMic to Asic Shared key table
29259 + Update its cipherAlg to Asic Shared key Mode.
29260 +
29261 + Return:
29262 + ========================================================================
29263 +*/
29264 +VOID AsicAddSharedKeyEntry(
29265 + IN PRTMP_ADAPTER pAd,
29266 + IN UCHAR BssIndex,
29267 + IN UCHAR KeyIdx,
29268 + IN UCHAR CipherAlg,
29269 + IN PUCHAR pKey,
29270 + IN PUCHAR pTxMic,
29271 + IN PUCHAR pRxMic)
29272 +{
29273 + ULONG offset; //, csr0;
29274 + SHAREDKEY_MODE_STRUC csr1;
29275 +#ifdef RT2860
29276 + INT i;
29277 +#endif // RT2860 //
29278 +
29279 + DBGPRINT(RT_DEBUG_TRACE, ("AsicAddSharedKeyEntry BssIndex=%d, KeyIdx=%d\n", BssIndex,KeyIdx));
29280 +//============================================================================================
29281 +
29282 + DBGPRINT(RT_DEBUG_TRACE,("AsicAddSharedKeyEntry: %s key #%d\n", CipherName[CipherAlg], BssIndex*4 + KeyIdx));
29283 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" Key = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n",
29284 + pKey[0],pKey[1],pKey[2],pKey[3],pKey[4],pKey[5],pKey[6],pKey[7],pKey[8],pKey[9],pKey[10],pKey[11],pKey[12],pKey[13],pKey[14],pKey[15]));
29285 + if (pRxMic)
29286 + {
29287 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" Rx MIC Key = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n",
29288 + pRxMic[0],pRxMic[1],pRxMic[2],pRxMic[3],pRxMic[4],pRxMic[5],pRxMic[6],pRxMic[7]));
29289 + }
29290 + if (pTxMic)
29291 + {
29292 + DBGPRINT_RAW(RT_DEBUG_TRACE, (" Tx MIC Key = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n",
29293 + pTxMic[0],pTxMic[1],pTxMic[2],pTxMic[3],pTxMic[4],pTxMic[5],pTxMic[6],pTxMic[7]));
29294 + }
29295 +//============================================================================================
29296 + //
29297 + // fill key material - key + TX MIC + RX MIC
29298 + //
29299 +#ifdef RT2860
29300 + offset = SHARED_KEY_TABLE_BASE + (4*BssIndex + KeyIdx)*HW_KEY_ENTRY_SIZE;
29301 + for (i=0; i<MAX_LEN_OF_SHARE_KEY; i++)
29302 + {
29303 + RTMP_IO_WRITE8(pAd, offset + i, pKey[i]);
29304 + }
29305 +
29306 + offset += MAX_LEN_OF_SHARE_KEY;
29307 + if (pTxMic)
29308 + {
29309 + for (i=0; i<8; i++)
29310 + {
29311 + RTMP_IO_WRITE8(pAd, offset + i, pTxMic[i]);
29312 + }
29313 + }
29314 +
29315 + offset += 8;
29316 + if (pRxMic)
29317 + {
29318 + for (i=0; i<8; i++)
29319 + {
29320 + RTMP_IO_WRITE8(pAd, offset + i, pRxMic[i]);
29321 + }
29322 + }
29323 +#endif // RT2860 //
29324 +
29325 +
29326 + //
29327 + // Update cipher algorithm. WSTA always use BSS0
29328 + //
29329 + RTMP_IO_READ32(pAd, SHARED_KEY_MODE_BASE+4*(BssIndex/2), &csr1.word);
29330 + DBGPRINT(RT_DEBUG_TRACE,("Read: SHARED_KEY_MODE_BASE at this Bss[%d] KeyIdx[%d]= 0x%x \n", BssIndex,KeyIdx, csr1.word));
29331 + if ((BssIndex%2) == 0)
29332 + {
29333 + if (KeyIdx == 0)
29334 + csr1.field.Bss0Key0CipherAlg = CipherAlg;
29335 + else if (KeyIdx == 1)
29336 + csr1.field.Bss0Key1CipherAlg = CipherAlg;
29337 + else if (KeyIdx == 2)
29338 + csr1.field.Bss0Key2CipherAlg = CipherAlg;
29339 + else
29340 + csr1.field.Bss0Key3CipherAlg = CipherAlg;
29341 + }
29342 + else
29343 + {
29344 + if (KeyIdx == 0)
29345 + csr1.field.Bss1Key0CipherAlg = CipherAlg;
29346 + else if (KeyIdx == 1)
29347 + csr1.field.Bss1Key1CipherAlg = CipherAlg;
29348 + else if (KeyIdx == 2)
29349 + csr1.field.Bss1Key2CipherAlg = CipherAlg;
29350 + else
29351 + csr1.field.Bss1Key3CipherAlg = CipherAlg;
29352 + }
29353 + DBGPRINT(RT_DEBUG_TRACE,("Write: SHARED_KEY_MODE_BASE at this Bss[%d] = 0x%x \n", BssIndex, csr1.word));
29354 + RTMP_IO_WRITE32(pAd, SHARED_KEY_MODE_BASE+4*(BssIndex/2), csr1.word);
29355 +
29356 +}
29357 +
29358 +// IRQL = DISPATCH_LEVEL
29359 +VOID AsicRemoveSharedKeyEntry(
29360 + IN PRTMP_ADAPTER pAd,
29361 + IN UCHAR BssIndex,
29362 + IN UCHAR KeyIdx)
29363 +{
29364 + //ULONG SecCsr0;
29365 + SHAREDKEY_MODE_STRUC csr1;
29366 +
29367 + DBGPRINT(RT_DEBUG_TRACE,("AsicRemoveSharedKeyEntry: #%d \n", BssIndex*4 + KeyIdx));
29368 +
29369 + RTMP_IO_READ32(pAd, SHARED_KEY_MODE_BASE+4*(BssIndex/2), &csr1.word);
29370 + if ((BssIndex%2) == 0)
29371 + {
29372 + if (KeyIdx == 0)
29373 + csr1.field.Bss0Key0CipherAlg = 0;
29374 + else if (KeyIdx == 1)
29375 + csr1.field.Bss0Key1CipherAlg = 0;
29376 + else if (KeyIdx == 2)
29377 + csr1.field.Bss0Key2CipherAlg = 0;
29378 + else
29379 + csr1.field.Bss0Key3CipherAlg = 0;
29380 + }
29381 + else
29382 + {
29383 + if (KeyIdx == 0)
29384 + csr1.field.Bss1Key0CipherAlg = 0;
29385 + else if (KeyIdx == 1)
29386 + csr1.field.Bss1Key1CipherAlg = 0;
29387 + else if (KeyIdx == 2)
29388 + csr1.field.Bss1Key2CipherAlg = 0;
29389 + else
29390 + csr1.field.Bss1Key3CipherAlg = 0;
29391 + }
29392 + DBGPRINT(RT_DEBUG_TRACE,("Write: SHARED_KEY_MODE_BASE at this Bss[%d] = 0x%x \n", BssIndex, csr1.word));
29393 + RTMP_IO_WRITE32(pAd, SHARED_KEY_MODE_BASE+4*(BssIndex/2), csr1.word);
29394 + ASSERT(BssIndex < 4);
29395 + ASSERT(KeyIdx < 4);
29396 +
29397 +}
29398 +
29399 +
29400 +VOID AsicUpdateWCIDAttribute(
29401 + IN PRTMP_ADAPTER pAd,
29402 + IN USHORT WCID,
29403 + IN UCHAR BssIndex,
29404 + IN UCHAR CipherAlg,
29405 + IN BOOLEAN bUsePairewiseKeyTable)
29406 +{
29407 + ULONG WCIDAttri = 0, offset;
29408 +
29409 + //
29410 + // Update WCID attribute.
29411 + // Only TxKey could update WCID attribute.
29412 + //
29413 + offset = MAC_WCID_ATTRIBUTE_BASE + (WCID * HW_WCID_ATTRI_SIZE);
29414 + WCIDAttri = (BssIndex << 4) | (CipherAlg << 1) | (bUsePairewiseKeyTable);
29415 + RTMP_IO_WRITE32(pAd, offset, WCIDAttri);
29416 +}
29417 +
29418 +VOID AsicUpdateWCIDIVEIV(
29419 + IN PRTMP_ADAPTER pAd,
29420 + IN USHORT WCID,
29421 + IN ULONG uIV,
29422 + IN ULONG uEIV)
29423 +{
29424 + ULONG offset;
29425 +
29426 + offset = MAC_IVEIV_TABLE_BASE + (WCID * HW_IVEIV_ENTRY_SIZE);
29427 +
29428 + RTMP_IO_WRITE32(pAd, offset, uIV);
29429 + RTMP_IO_WRITE32(pAd, offset + 4, uEIV);
29430 +}
29431 +
29432 +VOID AsicUpdateRxWCIDTable(
29433 + IN PRTMP_ADAPTER pAd,
29434 + IN USHORT WCID,
29435 + IN PUCHAR pAddr)
29436 +{
29437 + ULONG offset;
29438 + ULONG Addr;
29439 +
29440 + offset = MAC_WCID_BASE + (WCID * HW_WCID_ENTRY_SIZE);
29441 + Addr = pAddr[0] + (pAddr[1] << 8) +(pAddr[2] << 16) +(pAddr[3] << 24);
29442 + RTMP_IO_WRITE32(pAd, offset, Addr);
29443 + Addr = pAddr[4] + (pAddr[5] << 8);
29444 + RTMP_IO_WRITE32(pAd, offset + 4, Addr);
29445 +}
29446 +
29447 +
29448 +/*
29449 + ========================================================================
29450 +
29451 + Routine Description:
29452 + Set Cipher Key, Cipher algorithm, IV/EIV to Asic
29453 +
29454 + Arguments:
29455 + pAd Pointer to our adapter
29456 + WCID WCID Entry number.
29457 + BssIndex BSSID index, station or none multiple BSSID support
29458 + this value should be 0.
29459 + KeyIdx This KeyIdx will set to IV's KeyID if bTxKey enabled
29460 + pCipherKey Pointer to Cipher Key.
29461 + bUsePairewiseKeyTable TRUE means saved the key in SharedKey table,
29462 + otherwise PairewiseKey table
29463 + bTxKey This is the transmit key if enabled.
29464 +
29465 + Return Value:
29466 + None
29467 +
29468 + Note:
29469 + This routine will set the relative key stuff to Asic including WCID attribute,
29470 + Cipher Key, Cipher algorithm and IV/EIV.
29471 +
29472 + IV/EIV will be update if this CipherKey is the transmission key because
29473 + ASIC will base on IV's KeyID value to select Cipher Key.
29474 +
29475 + If bTxKey sets to FALSE, this is not the TX key, but it could be
29476 + RX key
29477 +
29478 + For AP mode bTxKey must be always set to TRUE.
29479 + ========================================================================
29480 +*/
29481 +VOID AsicAddKeyEntry(
29482 + IN PRTMP_ADAPTER pAd,
29483 + IN USHORT WCID,
29484 + IN UCHAR BssIndex,
29485 + IN UCHAR KeyIdx,
29486 + IN PCIPHER_KEY pCipherKey,
29487 + IN BOOLEAN bUsePairewiseKeyTable,
29488 + IN BOOLEAN bTxKey)
29489 +{
29490 + ULONG offset;
29491 + UCHAR IV4 = 0;
29492 + PUCHAR pKey = pCipherKey->Key;
29493 + PUCHAR pTxMic = pCipherKey->TxMic;
29494 + PUCHAR pRxMic = pCipherKey->RxMic;
29495 + PUCHAR pTxtsc = pCipherKey->TxTsc;
29496 + UCHAR CipherAlg = pCipherKey->CipherAlg;
29497 + SHAREDKEY_MODE_STRUC csr1;
29498 +#ifdef RT2860
29499 + UCHAR i;
29500 +#endif // RT2860 //
29501 +
29502 + DBGPRINT(RT_DEBUG_TRACE, ("==> AsicAddKeyEntry\n"));
29503 + //
29504 + // 1.) decide key table offset
29505 + //
29506 + if (bUsePairewiseKeyTable)
29507 + offset = PAIRWISE_KEY_TABLE_BASE + (WCID * HW_KEY_ENTRY_SIZE);
29508 + else
29509 + offset = SHARED_KEY_TABLE_BASE + (4 * BssIndex + KeyIdx) * HW_KEY_ENTRY_SIZE;
29510 +
29511 + //
29512 + // 2.) Set Key to Asic
29513 + //
29514 + //for (i = 0; i < KeyLen; i++)
29515 +#ifdef RT2860
29516 + for (i = 0; i < MAX_LEN_OF_PEER_KEY; i++)
29517 + {
29518 + RTMP_IO_WRITE8(pAd, offset + i, pKey[i]);
29519 + }
29520 + offset += MAX_LEN_OF_PEER_KEY;
29521 +
29522 + //
29523 + // 3.) Set MIC key if available
29524 + //
29525 + if (pTxMic)
29526 + {
29527 + for (i = 0; i < 8; i++)
29528 + {
29529 + RTMP_IO_WRITE8(pAd, offset + i, pTxMic[i]);
29530 + }
29531 + }
29532 + offset += LEN_TKIP_TXMICK;
29533 +
29534 + if (pRxMic)
29535 + {
29536 + for (i = 0; i < 8; i++)
29537 + {
29538 + RTMP_IO_WRITE8(pAd, offset + i, pRxMic[i]);
29539 + }
29540 + }
29541 +#endif // RT2860 //
29542 +
29543 +
29544 + //
29545 + // 4.) Modify IV/EIV if needs
29546 + // This will force Asic to use this key ID by setting IV.
29547 + //
29548 + if (bTxKey)
29549 + {
29550 +#ifdef RT2860
29551 + offset = MAC_IVEIV_TABLE_BASE + (WCID * HW_IVEIV_ENTRY_SIZE);
29552 + //
29553 + // Write IV
29554 + //
29555 + RTMP_IO_WRITE8(pAd, offset, pTxtsc[1]);
29556 + RTMP_IO_WRITE8(pAd, offset + 1, ((pTxtsc[1] | 0x20) & 0x7f));
29557 + RTMP_IO_WRITE8(pAd, offset + 2, pTxtsc[0]);
29558 +
29559 + IV4 = (KeyIdx << 6);
29560 + if ((CipherAlg == CIPHER_TKIP) || (CipherAlg == CIPHER_TKIP_NO_MIC) ||(CipherAlg == CIPHER_AES))
29561 + IV4 |= 0x20; // turn on extension bit means EIV existence
29562 +
29563 + RTMP_IO_WRITE8(pAd, offset + 3, IV4);
29564 +
29565 + //
29566 + // Write EIV
29567 + //
29568 + offset += 4;
29569 + for (i = 0; i < 4; i++)
29570 + {
29571 + RTMP_IO_WRITE8(pAd, offset + i, pTxtsc[i + 2]);
29572 + }
29573 +#endif // RT2860 //
29574 +
29575 + AsicUpdateWCIDAttribute(pAd, WCID, BssIndex, CipherAlg, bUsePairewiseKeyTable);
29576 + }
29577 +
29578 + if (!bUsePairewiseKeyTable)
29579 + {
29580 + //
29581 + // Only update the shared key security mode
29582 + //
29583 + RTMP_IO_READ32(pAd, SHARED_KEY_MODE_BASE + 4 * (BssIndex / 2), &csr1.word);
29584 + if ((BssIndex % 2) == 0)
29585 + {
29586 + if (KeyIdx == 0)
29587 + csr1.field.Bss0Key0CipherAlg = CipherAlg;
29588 + else if (KeyIdx == 1)
29589 + csr1.field.Bss0Key1CipherAlg = CipherAlg;
29590 + else if (KeyIdx == 2)
29591 + csr1.field.Bss0Key2CipherAlg = CipherAlg;
29592 + else
29593 + csr1.field.Bss0Key3CipherAlg = CipherAlg;
29594 + }
29595 + else
29596 + {
29597 + if (KeyIdx == 0)
29598 + csr1.field.Bss1Key0CipherAlg = CipherAlg;
29599 + else if (KeyIdx == 1)
29600 + csr1.field.Bss1Key1CipherAlg = CipherAlg;
29601 + else if (KeyIdx == 2)
29602 + csr1.field.Bss1Key2CipherAlg = CipherAlg;
29603 + else
29604 + csr1.field.Bss1Key3CipherAlg = CipherAlg;
29605 + }
29606 + RTMP_IO_WRITE32(pAd, SHARED_KEY_MODE_BASE + 4 * (BssIndex / 2), csr1.word);
29607 + }
29608 +
29609 + DBGPRINT(RT_DEBUG_TRACE, ("<== AsicAddKeyEntry\n"));
29610 +}
29611 +
29612 +
29613 +/*
29614 + ========================================================================
29615 + Description:
29616 + Add Pair-wise key material into ASIC.
29617 + Update pairwise key, TxMic and RxMic to Asic Pair-wise key table
29618 +
29619 + Return:
29620 + ========================================================================
29621 +*/
29622 +VOID AsicAddPairwiseKeyEntry(
29623 + IN PRTMP_ADAPTER pAd,
29624 + IN PUCHAR pAddr,
29625 + IN UCHAR WCID,
29626 + IN CIPHER_KEY *pCipherKey)
29627 +{
29628 + INT i;
29629 + ULONG offset;
29630 + PUCHAR pKey = pCipherKey->Key;
29631 + PUCHAR pTxMic = pCipherKey->TxMic;
29632 + PUCHAR pRxMic = pCipherKey->RxMic;
29633 +#ifdef DBG
29634 + UCHAR CipherAlg = pCipherKey->CipherAlg;
29635 +#endif // DBG //
29636 +
29637 + // EKEY
29638 + offset = PAIRWISE_KEY_TABLE_BASE + (WCID * HW_KEY_ENTRY_SIZE);
29639 +#ifdef RT2860
29640 + for (i=0; i<MAX_LEN_OF_PEER_KEY; i++)
29641 + {
29642 + RTMP_IO_WRITE8(pAd, offset + i, pKey[i]);
29643 + }
29644 +#endif // RT2860 //
29645 + for (i=0; i<MAX_LEN_OF_PEER_KEY; i+=4)
29646 + {
29647 + UINT32 Value;
29648 + RTMP_IO_READ32(pAd, offset + i, &Value);
29649 + }
29650 +
29651 + offset += MAX_LEN_OF_PEER_KEY;
29652 +
29653 + // MIC KEY
29654 + if (pTxMic)
29655 + {
29656 +#ifdef RT2860
29657 + for (i=0; i<8; i++)
29658 + {
29659 + RTMP_IO_WRITE8(pAd, offset+i, pTxMic[i]);
29660 + }
29661 +#endif // RT2860 //
29662 + }
29663 + offset += 8;
29664 + if (pRxMic)
29665 + {
29666 +#ifdef RT2860
29667 + for (i=0; i<8; i++)
29668 + {
29669 + RTMP_IO_WRITE8(pAd, offset+i, pRxMic[i]);
29670 + }
29671 +#endif // RT2860 //
29672 + }
29673 +
29674 + DBGPRINT(RT_DEBUG_TRACE,("AsicAddPairwiseKeyEntry: WCID #%d Alg=%s\n",WCID, CipherName[CipherAlg]));
29675 + DBGPRINT(RT_DEBUG_TRACE,(" Key = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n",
29676 + pKey[0],pKey[1],pKey[2],pKey[3],pKey[4],pKey[5],pKey[6],pKey[7],pKey[8],pKey[9],pKey[10],pKey[11],pKey[12],pKey[13],pKey[14],pKey[15]));
29677 + if (pRxMic)
29678 + {
29679 + DBGPRINT(RT_DEBUG_TRACE, (" Rx MIC Key = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n",
29680 + pRxMic[0],pRxMic[1],pRxMic[2],pRxMic[3],pRxMic[4],pRxMic[5],pRxMic[6],pRxMic[7]));
29681 + }
29682 + if (pTxMic)
29683 + {
29684 + DBGPRINT(RT_DEBUG_TRACE, (" Tx MIC Key = %02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n",
29685 + pTxMic[0],pTxMic[1],pTxMic[2],pTxMic[3],pTxMic[4],pTxMic[5],pTxMic[6],pTxMic[7]));
29686 + }
29687 +}
29688 +/*
29689 + ========================================================================
29690 + Description:
29691 + Remove Pair-wise key material from ASIC.
29692 +
29693 + Return:
29694 + ========================================================================
29695 +*/
29696 +VOID AsicRemovePairwiseKeyEntry(
29697 + IN PRTMP_ADAPTER pAd,
29698 + IN UCHAR BssIdx,
29699 + IN UCHAR Wcid)
29700 +{
29701 + ULONG WCIDAttri;
29702 + USHORT offset;
29703 +
29704 + // re-set the entry's WCID attribute as OPEN-NONE.
29705 + offset = MAC_WCID_ATTRIBUTE_BASE + (Wcid * HW_WCID_ATTRI_SIZE);
29706 + WCIDAttri = (BssIdx<<4) | PAIRWISEKEYTABLE;
29707 + RTMP_IO_WRITE32(pAd, offset, WCIDAttri);
29708 +}
29709 +
29710 +BOOLEAN AsicSendCommandToMcu(
29711 + IN PRTMP_ADAPTER pAd,
29712 + IN UCHAR Command,
29713 + IN UCHAR Token,
29714 + IN UCHAR Arg0,
29715 + IN UCHAR Arg1)
29716 +{
29717 + HOST_CMD_CSR_STRUC H2MCmd;
29718 + H2M_MAILBOX_STRUC H2MMailbox;
29719 + ULONG i = 0;
29720 +#ifdef RT2860
29721 +#ifdef RALINK_ATE
29722 + static UINT32 j = 0;
29723 +#endif // RALINK_ATE //
29724 +#endif // RT2860 //
29725 + do
29726 + {
29727 + RTMP_IO_READ32(pAd, H2M_MAILBOX_CSR, &H2MMailbox.word);
29728 + if (H2MMailbox.field.Owner == 0)
29729 + break;
29730 +
29731 + RTMPusecDelay(2);
29732 + } while(i++ < 100);
29733 +
29734 + if (i >= 100)
29735 + {
29736 +#ifdef RT2860
29737 +#ifdef RALINK_ATE
29738 + if (pAd->ate.bFWLoading == TRUE)
29739 + {
29740 + /* reloading firmware when received iwpriv cmd "ATE=ATESTOP" */
29741 + if (j > 0)
29742 + {
29743 + if (j % 64 != 0)
29744 + {
29745 + DBGPRINT(RT_DEBUG_ERROR, ("#"));
29746 + }
29747 + else
29748 + {
29749 + DBGPRINT(RT_DEBUG_ERROR, ("\n"));
29750 + }
29751 + ++j;
29752 + }
29753 + else if (j == 0)
29754 + {
29755 + DBGPRINT(RT_DEBUG_ERROR, ("Loading firmware. Please wait for a moment...\n"));
29756 + ++j;
29757 + }
29758 + }
29759 + else
29760 +#endif // RALINK_ATE //
29761 +#endif // RT2860 //
29762 + {
29763 + DBGPRINT_ERR(("H2M_MAILBOX still hold by MCU. command fail\n"));
29764 + }
29765 + return FALSE;
29766 + }
29767 +
29768 +#ifdef RT2860
29769 +#ifdef RALINK_ATE
29770 + else if (pAd->ate.bFWLoading == TRUE)
29771 + {
29772 + /* reloading of firmware is completed */
29773 + pAd->ate.bFWLoading = FALSE;
29774 + DBGPRINT(RT_DEBUG_ERROR, ("\n"));
29775 + j = 0;
29776 + }
29777 +#endif // RALINK_ATE //
29778 +#endif // RT2860 //
29779 +
29780 + H2MMailbox.field.Owner = 1; // pass ownership to MCU
29781 + H2MMailbox.field.CmdToken = Token;
29782 + H2MMailbox.field.HighByte = Arg1;
29783 + H2MMailbox.field.LowByte = Arg0;
29784 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_CSR, H2MMailbox.word);
29785 +
29786 + H2MCmd.word = 0;
29787 + H2MCmd.field.HostCommand = Command;
29788 + RTMP_IO_WRITE32(pAd, HOST_CMD_CSR, H2MCmd.word);
29789 +
29790 + if (Command != 0x80)
29791 + {
29792 + }
29793 +
29794 + return TRUE;
29795 +}
29796 +
29797 +#ifdef RT2860
29798 +BOOLEAN AsicCheckCommanOk(
29799 + IN PRTMP_ADAPTER pAd,
29800 + IN UCHAR Command)
29801 +{
29802 + UINT32 CmdStatus = 0, CID = 0, i;
29803 + UINT32 ThisCIDMask = 0;
29804 +
29805 + i = 0;
29806 + do
29807 + {
29808 + RTMP_IO_READ32(pAd, H2M_MAILBOX_CID, &CID);
29809 + // Find where the command is. Because this is randomly specified by firmware.
29810 + if ((CID & CID0MASK) == Command)
29811 + {
29812 + ThisCIDMask = CID0MASK;
29813 + break;
29814 + }
29815 + else if ((((CID & CID1MASK)>>8) & 0xff) == Command)
29816 + {
29817 + ThisCIDMask = CID1MASK;
29818 + break;
29819 + }
29820 + else if ((((CID & CID2MASK)>>16) & 0xff) == Command)
29821 + {
29822 + ThisCIDMask = CID2MASK;
29823 + break;
29824 + }
29825 + else if ((((CID & CID3MASK)>>24) & 0xff) == Command)
29826 + {
29827 + ThisCIDMask = CID3MASK;
29828 + break;
29829 + }
29830 +
29831 + RTMPusecDelay(100);
29832 + i++;
29833 + }while (i < 200);
29834 +
29835 + // Get CommandStatus Value
29836 + RTMP_IO_READ32(pAd, H2M_MAILBOX_STATUS, &CmdStatus);
29837 +
29838 + // This command's status is at the same position as command. So AND command position's bitmask to read status.
29839 + if (i < 200)
29840 + {
29841 + // If Status is 1, the comamnd is success.
29842 + if (((CmdStatus & ThisCIDMask) == 0x1) || ((CmdStatus & ThisCIDMask) == 0x100)
29843 + || ((CmdStatus & ThisCIDMask) == 0x10000) || ((CmdStatus & ThisCIDMask) == 0x1000000))
29844 + {
29845 + DBGPRINT(RT_DEBUG_TRACE, ("--> AsicCheckCommanOk CID = 0x%x, CmdStatus= 0x%x \n", CID, CmdStatus));
29846 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_STATUS, 0xffffffff);
29847 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_CID, 0xffffffff);
29848 + return TRUE;
29849 + }
29850 + DBGPRINT(RT_DEBUG_TRACE, ("--> AsicCheckCommanFail1 CID = 0x%x, CmdStatus= 0x%x \n", CID, CmdStatus));
29851 + }
29852 + else
29853 + {
29854 + DBGPRINT(RT_DEBUG_TRACE, ("--> AsicCheckCommanFail2 Timeout Command = %d, CmdStatus= 0x%x \n", Command, CmdStatus));
29855 + }
29856 + // Clear Command and Status.
29857 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_STATUS, 0xffffffff);
29858 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_CID, 0xffffffff);
29859 +
29860 + return FALSE;
29861 +}
29862 +#endif // RT2860 //
29863 +
29864 +/*
29865 + ========================================================================
29866 +
29867 + Routine Description:
29868 + Verify the support rate for different PHY type
29869 +
29870 + Arguments:
29871 + pAd Pointer to our adapter
29872 +
29873 + Return Value:
29874 + None
29875 +
29876 + IRQL = PASSIVE_LEVEL
29877 +
29878 + ========================================================================
29879 +*/
29880 +VOID RTMPCheckRates(
29881 + IN PRTMP_ADAPTER pAd,
29882 + IN OUT UCHAR SupRate[],
29883 + IN OUT UCHAR *SupRateLen)
29884 +{
29885 + UCHAR RateIdx, i, j;
29886 + UCHAR NewRate[12], NewRateLen;
29887 +
29888 + NewRateLen = 0;
29889 +
29890 + if (pAd->CommonCfg.PhyMode == PHY_11B)
29891 + RateIdx = 4;
29892 + else
29893 + RateIdx = 12;
29894 +
29895 + // Check for support rates exclude basic rate bit
29896 + for (i = 0; i < *SupRateLen; i++)
29897 + for (j = 0; j < RateIdx; j++)
29898 + if ((SupRate[i] & 0x7f) == RateIdTo500Kbps[j])
29899 + NewRate[NewRateLen++] = SupRate[i];
29900 +
29901 + *SupRateLen = NewRateLen;
29902 + NdisMoveMemory(SupRate, NewRate, NewRateLen);
29903 +}
29904 +
29905 +#ifdef CONFIG_STA_SUPPORT
29906 +#ifdef DOT11_N_SUPPORT
29907 +BOOLEAN RTMPCheckChannel(
29908 + IN PRTMP_ADAPTER pAd,
29909 + IN UCHAR CentralChannel,
29910 + IN UCHAR Channel)
29911 +{
29912 + UCHAR k;
29913 + UCHAR UpperChannel = 0, LowerChannel = 0;
29914 + UCHAR NoEffectChannelinList = 0;
29915 +
29916 + // Find upper and lower channel according to 40MHz current operation.
29917 + if (CentralChannel < Channel)
29918 + {
29919 + UpperChannel = Channel;
29920 + if (CentralChannel > 2)
29921 + LowerChannel = CentralChannel - 2;
29922 + else
29923 + return FALSE;
29924 + }
29925 + else if (CentralChannel > Channel)
29926 + {
29927 + UpperChannel = CentralChannel + 2;
29928 + LowerChannel = Channel;
29929 + }
29930 +
29931 + for (k = 0;k < pAd->ChannelListNum;k++)
29932 + {
29933 + if (pAd->ChannelList[k].Channel == UpperChannel)
29934 + {
29935 + NoEffectChannelinList ++;
29936 + }
29937 + if (pAd->ChannelList[k].Channel == LowerChannel)
29938 + {
29939 + NoEffectChannelinList ++;
29940 + }
29941 + }
29942 +
29943 + DBGPRINT(RT_DEBUG_TRACE,("Total Channel in Channel List = [%d]\n", NoEffectChannelinList));
29944 + if (NoEffectChannelinList == 2)
29945 + return TRUE;
29946 + else
29947 + return FALSE;
29948 +}
29949 +
29950 +/*
29951 + ========================================================================
29952 +
29953 + Routine Description:
29954 + Verify the support rate for HT phy type
29955 +
29956 + Arguments:
29957 + pAd Pointer to our adapter
29958 +
29959 + Return Value:
29960 + FALSE if pAd->CommonCfg.SupportedHtPhy doesn't accept the pHtCapability. (AP Mode)
29961 +
29962 + IRQL = PASSIVE_LEVEL
29963 +
29964 + ========================================================================
29965 +*/
29966 +BOOLEAN RTMPCheckHt(
29967 + IN PRTMP_ADAPTER pAd,
29968 + IN UCHAR Wcid,
29969 + IN HT_CAPABILITY_IE *pHtCapability,
29970 + IN ADD_HT_INFO_IE *pAddHtInfo)
29971 +{
29972 + if (Wcid >= MAX_LEN_OF_MAC_TABLE)
29973 + return FALSE;
29974 +
29975 + // If use AMSDU, set flag.
29976 + if (pAd->CommonCfg.DesiredHtPhy.AmsduEnable)
29977 + CLIENT_STATUS_SET_FLAG(&pAd->MacTab.Content[Wcid], fCLIENT_STATUS_AMSDU_INUSED);
29978 + // Save Peer Capability
29979 + if (pHtCapability->HtCapInfo.ShortGIfor20)
29980 + CLIENT_STATUS_SET_FLAG(&pAd->MacTab.Content[Wcid], fCLIENT_STATUS_SGI20_CAPABLE);
29981 + if (pHtCapability->HtCapInfo.ShortGIfor40)
29982 + CLIENT_STATUS_SET_FLAG(&pAd->MacTab.Content[Wcid], fCLIENT_STATUS_SGI40_CAPABLE);
29983 + if (pHtCapability->HtCapInfo.TxSTBC)
29984 + CLIENT_STATUS_SET_FLAG(&pAd->MacTab.Content[Wcid], fCLIENT_STATUS_TxSTBC_CAPABLE);
29985 + if (pHtCapability->HtCapInfo.RxSTBC)
29986 + CLIENT_STATUS_SET_FLAG(&pAd->MacTab.Content[Wcid], fCLIENT_STATUS_RxSTBC_CAPABLE);
29987 + if (pAd->CommonCfg.bRdg && pHtCapability->ExtHtCapInfo.RDGSupport)
29988 + {
29989 + CLIENT_STATUS_SET_FLAG(&pAd->MacTab.Content[Wcid], fCLIENT_STATUS_RDG_CAPABLE);
29990 + }
29991 +
29992 + if (Wcid < MAX_LEN_OF_MAC_TABLE)
29993 + {
29994 + pAd->MacTab.Content[Wcid].MpduDensity = pHtCapability->HtCapParm.MpduDensity;
29995 + }
29996 +
29997 + // Will check ChannelWidth for MCSSet[4] below
29998 + pAd->MlmeAux.HtCapability.MCSSet[4] = 0x1;
29999 + switch (pAd->CommonCfg.RxStream)
30000 + {
30001 + case 1:
30002 + pAd->MlmeAux.HtCapability.MCSSet[0] = 0xff;
30003 + pAd->MlmeAux.HtCapability.MCSSet[1] = 0x00;
30004 + pAd->MlmeAux.HtCapability.MCSSet[2] = 0x00;
30005 + pAd->MlmeAux.HtCapability.MCSSet[3] = 0x00;
30006 + break;
30007 + case 2:
30008 + pAd->MlmeAux.HtCapability.MCSSet[0] = 0xff;
30009 + pAd->MlmeAux.HtCapability.MCSSet[1] = 0xff;
30010 + pAd->MlmeAux.HtCapability.MCSSet[2] = 0x00;
30011 + pAd->MlmeAux.HtCapability.MCSSet[3] = 0x00;
30012 + break;
30013 + case 3:
30014 + pAd->MlmeAux.HtCapability.MCSSet[0] = 0xff;
30015 + pAd->MlmeAux.HtCapability.MCSSet[1] = 0xff;
30016 + pAd->MlmeAux.HtCapability.MCSSet[2] = 0xff;
30017 + pAd->MlmeAux.HtCapability.MCSSet[3] = 0x00;
30018 + break;
30019 + }
30020 +
30021 + pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth = pAddHtInfo->AddHtInfo.RecomWidth & pAd->CommonCfg.DesiredHtPhy.ChannelWidth;
30022 +
30023 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPCheckHt:: HtCapInfo.ChannelWidth=%d, RecomWidth=%d, DesiredHtPhy.ChannelWidth=%d, BW40MAvailForA/G=%d/%d, PhyMode=%d \n",
30024 + pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth, pAddHtInfo->AddHtInfo.RecomWidth, pAd->CommonCfg.DesiredHtPhy.ChannelWidth,
30025 + pAd->NicConfig2.field.BW40MAvailForA, pAd->NicConfig2.field.BW40MAvailForG, pAd->CommonCfg.PhyMode));
30026 +
30027 + pAd->MlmeAux.HtCapability.HtCapInfo.GF = pHtCapability->HtCapInfo.GF &pAd->CommonCfg.DesiredHtPhy.GF;
30028 +
30029 + // Send Assoc Req with my HT capability.
30030 + pAd->MlmeAux.HtCapability.HtCapInfo.AMsduSize = pAd->CommonCfg.DesiredHtPhy.AmsduSize;
30031 + pAd->MlmeAux.HtCapability.HtCapInfo.MimoPs = pAd->CommonCfg.DesiredHtPhy.MimoPs;
30032 + pAd->MlmeAux.HtCapability.HtCapInfo.ShortGIfor20 = (pAd->CommonCfg.DesiredHtPhy.ShortGIfor20) & (pHtCapability->HtCapInfo.ShortGIfor20);
30033 + pAd->MlmeAux.HtCapability.HtCapInfo.ShortGIfor40 = (pAd->CommonCfg.DesiredHtPhy.ShortGIfor40) & (pHtCapability->HtCapInfo.ShortGIfor40);
30034 + pAd->MlmeAux.HtCapability.HtCapInfo.TxSTBC = (pAd->CommonCfg.DesiredHtPhy.TxSTBC)&(pHtCapability->HtCapInfo.RxSTBC);
30035 + pAd->MlmeAux.HtCapability.HtCapInfo.RxSTBC = (pAd->CommonCfg.DesiredHtPhy.RxSTBC)&(pHtCapability->HtCapInfo.TxSTBC);
30036 + pAd->MlmeAux.HtCapability.HtCapParm.MaxRAmpduFactor = pAd->CommonCfg.DesiredHtPhy.MaxRAmpduFactor;
30037 + pAd->MlmeAux.HtCapability.HtCapParm.MpduDensity = pAd->CommonCfg.HtCapability.HtCapParm.MpduDensity;
30038 + pAd->MlmeAux.HtCapability.ExtHtCapInfo.PlusHTC = pHtCapability->ExtHtCapInfo.PlusHTC;
30039 + pAd->MacTab.Content[Wcid].HTCapability.ExtHtCapInfo.PlusHTC = pHtCapability->ExtHtCapInfo.PlusHTC;
30040 + if (pAd->CommonCfg.bRdg)
30041 + {
30042 + pAd->MlmeAux.HtCapability.ExtHtCapInfo.RDGSupport = pHtCapability->ExtHtCapInfo.RDGSupport;
30043 + pAd->MlmeAux.HtCapability.ExtHtCapInfo.PlusHTC = 1;
30044 + }
30045 +
30046 + if (pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth == BW_20)
30047 + pAd->MlmeAux.HtCapability.MCSSet[4] = 0x0; // BW20 can't transmit MCS32
30048 +
30049 + COPY_AP_HTSETTINGS_FROM_BEACON(pAd, pHtCapability);
30050 + return TRUE;
30051 +}
30052 +#endif // DOT11_N_SUPPORT //
30053 +#endif // CONFIG_STA_SUPPORT //
30054 +
30055 +/*
30056 + ========================================================================
30057 +
30058 + Routine Description:
30059 + Verify the support rate for different PHY type
30060 +
30061 + Arguments:
30062 + pAd Pointer to our adapter
30063 +
30064 + Return Value:
30065 + None
30066 +
30067 + IRQL = PASSIVE_LEVEL
30068 +
30069 + ========================================================================
30070 +*/
30071 +VOID RTMPUpdateMlmeRate(
30072 + IN PRTMP_ADAPTER pAd)
30073 +{
30074 + UCHAR MinimumRate;
30075 + UCHAR ProperMlmeRate; //= RATE_54;
30076 + UCHAR i, j, RateIdx = 12; //1, 2, 5.5, 11, 6, 9, 12, 18, 24, 36, 48, 54
30077 + BOOLEAN bMatch = FALSE;
30078 +
30079 + switch (pAd->CommonCfg.PhyMode)
30080 + {
30081 + case PHY_11B:
30082 + ProperMlmeRate = RATE_11;
30083 + MinimumRate = RATE_1;
30084 + break;
30085 + case PHY_11BG_MIXED:
30086 +#ifdef DOT11_N_SUPPORT
30087 + case PHY_11ABGN_MIXED:
30088 + case PHY_11BGN_MIXED:
30089 +#endif // DOT11_N_SUPPORT //
30090 + if ((pAd->MlmeAux.SupRateLen == 4) &&
30091 + (pAd->MlmeAux.ExtRateLen == 0))
30092 + // B only AP
30093 + ProperMlmeRate = RATE_11;
30094 + else
30095 + ProperMlmeRate = RATE_24;
30096 +
30097 + if (pAd->MlmeAux.Channel <= 14)
30098 + MinimumRate = RATE_1;
30099 + else
30100 + MinimumRate = RATE_6;
30101 + break;
30102 + case PHY_11A:
30103 +#ifdef DOT11_N_SUPPORT
30104 + case PHY_11N_2_4G: // rt2860 need to check mlmerate for 802.11n
30105 + case PHY_11GN_MIXED:
30106 + case PHY_11AGN_MIXED:
30107 + case PHY_11AN_MIXED:
30108 + case PHY_11N_5G:
30109 +#endif // DOT11_N_SUPPORT //
30110 + ProperMlmeRate = RATE_24;
30111 + MinimumRate = RATE_6;
30112 + break;
30113 + case PHY_11ABG_MIXED:
30114 + ProperMlmeRate = RATE_24;
30115 + if (pAd->MlmeAux.Channel <= 14)
30116 + MinimumRate = RATE_1;
30117 + else
30118 + MinimumRate = RATE_6;
30119 + break;
30120 + default: // error
30121 + ProperMlmeRate = RATE_1;
30122 + MinimumRate = RATE_1;
30123 + break;
30124 + }
30125 +
30126 + for (i = 0; i < pAd->MlmeAux.SupRateLen; i++)
30127 + {
30128 + for (j = 0; j < RateIdx; j++)
30129 + {
30130 + if ((pAd->MlmeAux.SupRate[i] & 0x7f) == RateIdTo500Kbps[j])
30131 + {
30132 + if (j == ProperMlmeRate)
30133 + {
30134 + bMatch = TRUE;
30135 + break;
30136 + }
30137 + }
30138 + }
30139 +
30140 + if (bMatch)
30141 + break;
30142 + }
30143 +
30144 + if (bMatch == FALSE)
30145 + {
30146 + for (i = 0; i < pAd->MlmeAux.ExtRateLen; i++)
30147 + {
30148 + for (j = 0; j < RateIdx; j++)
30149 + {
30150 + if ((pAd->MlmeAux.ExtRate[i] & 0x7f) == RateIdTo500Kbps[j])
30151 + {
30152 + if (j == ProperMlmeRate)
30153 + {
30154 + bMatch = TRUE;
30155 + break;
30156 + }
30157 + }
30158 + }
30159 +
30160 + if (bMatch)
30161 + break;
30162 + }
30163 + }
30164 +
30165 + if (bMatch == FALSE)
30166 + {
30167 + ProperMlmeRate = MinimumRate;
30168 + }
30169 +
30170 + pAd->CommonCfg.MlmeRate = MinimumRate;
30171 + pAd->CommonCfg.RtsRate = ProperMlmeRate;
30172 + if (pAd->CommonCfg.MlmeRate >= RATE_6)
30173 + {
30174 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_OFDM;
30175 + pAd->CommonCfg.MlmeTransmit.field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MlmeRate];
30176 + pAd->MacTab.Content[BSS0Mcast_WCID].HTPhyMode.field.MODE = MODE_OFDM;
30177 + pAd->MacTab.Content[BSS0Mcast_WCID].HTPhyMode.field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MlmeRate];
30178 + }
30179 + else
30180 + {
30181 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_CCK;
30182 + pAd->CommonCfg.MlmeTransmit.field.MCS = pAd->CommonCfg.MlmeRate;
30183 + pAd->MacTab.Content[BSS0Mcast_WCID].HTPhyMode.field.MODE = MODE_CCK;
30184 + pAd->MacTab.Content[BSS0Mcast_WCID].HTPhyMode.field.MCS = pAd->CommonCfg.MlmeRate;
30185 + }
30186 +
30187 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPUpdateMlmeRate ==> MlmeTransmit = 0x%x \n" , pAd->CommonCfg.MlmeTransmit.word));
30188 +}
30189 +
30190 +CHAR RTMPMaxRssi(
30191 + IN PRTMP_ADAPTER pAd,
30192 + IN CHAR Rssi0,
30193 + IN CHAR Rssi1,
30194 + IN CHAR Rssi2)
30195 +{
30196 + CHAR larger = -127;
30197 +
30198 + if ((pAd->Antenna.field.RxPath == 1) && (Rssi0 != 0))
30199 + {
30200 + larger = Rssi0;
30201 + }
30202 +
30203 + if ((pAd->Antenna.field.RxPath >= 2) && (Rssi1 != 0))
30204 + {
30205 + larger = max(Rssi0, Rssi1);
30206 + }
30207 +
30208 + if ((pAd->Antenna.field.RxPath == 3) && (Rssi2 != 0))
30209 + {
30210 + larger = max(larger, Rssi2);
30211 + }
30212 +
30213 + if (larger == -127)
30214 + larger = 0;
30215 +
30216 + return larger;
30217 +}
30218 +
30219 +/*
30220 + ========================================================================
30221 + Routine Description:
30222 + Periodic evaluate antenna link status
30223 +
30224 + Arguments:
30225 + pAd - Adapter pointer
30226 +
30227 + Return Value:
30228 + None
30229 +
30230 + ========================================================================
30231 +*/
30232 +VOID AsicEvaluateRxAnt(
30233 + IN PRTMP_ADAPTER pAd)
30234 +{
30235 + UCHAR BBPR3 = 0;
30236 +
30237 +#ifdef RALINK_ATE
30238 + if (ATE_ON(pAd))
30239 + return;
30240 +#endif // RALINK_ATE //
30241 +
30242 +
30243 +#ifdef CONFIG_STA_SUPPORT
30244 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
30245 + {
30246 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS |
30247 + fRTMP_ADAPTER_HALT_IN_PROGRESS |
30248 + fRTMP_ADAPTER_RADIO_OFF |
30249 + fRTMP_ADAPTER_NIC_NOT_EXIST |
30250 + fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
30251 + return;
30252 +
30253 + if (pAd->StaCfg.Psm == PWR_SAVE)
30254 + return;
30255 + }
30256 +#endif // CONFIG_STA_SUPPORT //
30257 +
30258 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BBPR3);
30259 + BBPR3 &= (~0x18);
30260 + if(pAd->Antenna.field.RxPath == 3)
30261 + {
30262 + BBPR3 |= (0x10);
30263 + }
30264 + else if(pAd->Antenna.field.RxPath == 2)
30265 + {
30266 + BBPR3 |= (0x8);
30267 + }
30268 + else if(pAd->Antenna.field.RxPath == 1)
30269 + {
30270 + BBPR3 |= (0x0);
30271 + }
30272 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BBPR3);
30273 +#ifdef CONFIG_STA_SUPPORT
30274 +#ifdef RT2860
30275 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
30276 + pAd->StaCfg.BBPR3 = BBPR3;
30277 +#endif // RT2860 //
30278 +#endif // CONFIG_STA_SUPPORT //
30279 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED)
30280 + )
30281 + {
30282 + ULONG TxTotalCnt = pAd->RalinkCounters.OneSecTxNoRetryOkCount +
30283 + pAd->RalinkCounters.OneSecTxRetryOkCount +
30284 + pAd->RalinkCounters.OneSecTxFailCount;
30285 +
30286 + if (TxTotalCnt > 50)
30287 + {
30288 + RTMPSetTimer(&pAd->Mlme.RxAntEvalTimer, 20);
30289 + pAd->Mlme.bLowThroughput = FALSE;
30290 + }
30291 + else
30292 + {
30293 + RTMPSetTimer(&pAd->Mlme.RxAntEvalTimer, 300);
30294 + pAd->Mlme.bLowThroughput = TRUE;
30295 + }
30296 + }
30297 +}
30298 +
30299 +/*
30300 + ========================================================================
30301 + Routine Description:
30302 + After evaluation, check antenna link status
30303 +
30304 + Arguments:
30305 + pAd - Adapter pointer
30306 +
30307 + Return Value:
30308 + None
30309 +
30310 + ========================================================================
30311 +*/
30312 +VOID AsicRxAntEvalTimeout(
30313 + IN PVOID SystemSpecific1,
30314 + IN PVOID FunctionContext,
30315 + IN PVOID SystemSpecific2,
30316 + IN PVOID SystemSpecific3)
30317 +{
30318 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
30319 +#ifdef CONFIG_STA_SUPPORT
30320 + UCHAR BBPR3 = 0;
30321 + CHAR larger = -127, rssi0, rssi1, rssi2;
30322 +#endif // CONFIG_STA_SUPPORT //
30323 +
30324 +#ifdef RALINK_ATE
30325 + if (ATE_ON(pAd))
30326 + return;
30327 +#endif // RALINK_ATE //
30328 +
30329 +
30330 +#ifdef CONFIG_STA_SUPPORT
30331 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
30332 + {
30333 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||
30334 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS) ||
30335 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF) ||
30336 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST))
30337 + return;
30338 +
30339 + if (pAd->StaCfg.Psm == PWR_SAVE)
30340 + return;
30341 +
30342 +
30343 + // if the traffic is low, use average rssi as the criteria
30344 + if (pAd->Mlme.bLowThroughput == TRUE)
30345 + {
30346 + rssi0 = pAd->StaCfg.RssiSample.LastRssi0;
30347 + rssi1 = pAd->StaCfg.RssiSample.LastRssi1;
30348 + rssi2 = pAd->StaCfg.RssiSample.LastRssi2;
30349 + }
30350 + else
30351 + {
30352 + rssi0 = pAd->StaCfg.RssiSample.AvgRssi0;
30353 + rssi1 = pAd->StaCfg.RssiSample.AvgRssi1;
30354 + rssi2 = pAd->StaCfg.RssiSample.AvgRssi2;
30355 + }
30356 +
30357 + if(pAd->Antenna.field.RxPath == 3)
30358 + {
30359 + larger = max(rssi0, rssi1);
30360 +
30361 + if (larger > (rssi2 + 20))
30362 + pAd->Mlme.RealRxPath = 2;
30363 + else
30364 + pAd->Mlme.RealRxPath = 3;
30365 + }
30366 + else if(pAd->Antenna.field.RxPath == 2)
30367 + {
30368 + if (rssi0 > (rssi1 + 20))
30369 + pAd->Mlme.RealRxPath = 1;
30370 + else
30371 + pAd->Mlme.RealRxPath = 2;
30372 + }
30373 +
30374 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BBPR3);
30375 + BBPR3 &= (~0x18);
30376 + if(pAd->Mlme.RealRxPath == 3)
30377 + {
30378 + BBPR3 |= (0x10);
30379 + }
30380 + else if(pAd->Mlme.RealRxPath == 2)
30381 + {
30382 + BBPR3 |= (0x8);
30383 + }
30384 + else if(pAd->Mlme.RealRxPath == 1)
30385 + {
30386 + BBPR3 |= (0x0);
30387 + }
30388 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BBPR3);
30389 +#ifdef RT2860
30390 + pAd->StaCfg.BBPR3 = BBPR3;
30391 +#endif // RT2860 //
30392 + }
30393 +
30394 +#endif // CONFIG_STA_SUPPORT //
30395 +
30396 +}
30397 +
30398 +
30399 +
30400 +VOID APSDPeriodicExec(
30401 + IN PVOID SystemSpecific1,
30402 + IN PVOID FunctionContext,
30403 + IN PVOID SystemSpecific2,
30404 + IN PVOID SystemSpecific3)
30405 +{
30406 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
30407 +
30408 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
30409 + return;
30410 +
30411 + pAd->CommonCfg.TriggerTimerCount++;
30412 +
30413 +}
30414 +
30415 +/*
30416 + ========================================================================
30417 + Routine Description:
30418 + Set/reset MAC registers according to bPiggyBack parameter
30419 +
30420 + Arguments:
30421 + pAd - Adapter pointer
30422 + bPiggyBack - Enable / Disable Piggy-Back
30423 +
30424 + Return Value:
30425 + None
30426 +
30427 + ========================================================================
30428 +*/
30429 +VOID RTMPSetPiggyBack(
30430 + IN PRTMP_ADAPTER pAd,
30431 + IN BOOLEAN bPiggyBack)
30432 +{
30433 + TX_LINK_CFG_STRUC TxLinkCfg;
30434 +
30435 + RTMP_IO_READ32(pAd, TX_LINK_CFG, &TxLinkCfg.word);
30436 +
30437 + TxLinkCfg.field.TxCFAckEn = bPiggyBack;
30438 + RTMP_IO_WRITE32(pAd, TX_LINK_CFG, TxLinkCfg.word);
30439 +}
30440 +
30441 +/*
30442 + ========================================================================
30443 + Routine Description:
30444 + check if this entry need to switch rate automatically
30445 +
30446 + Arguments:
30447 + pAd
30448 + pEntry
30449 +
30450 + Return Value:
30451 + TURE
30452 + FALSE
30453 +
30454 + ========================================================================
30455 +*/
30456 +BOOLEAN RTMPCheckEntryEnableAutoRateSwitch(
30457 + IN PRTMP_ADAPTER pAd,
30458 + IN PMAC_TABLE_ENTRY pEntry)
30459 +{
30460 + BOOLEAN result = TRUE;
30461 +
30462 +
30463 +#ifdef CONFIG_STA_SUPPORT
30464 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
30465 + {
30466 + // only associated STA counts
30467 + if (pEntry && (pEntry->ValidAsCLI) && (pEntry->Sst == SST_ASSOC))
30468 + {
30469 + result = pAd->StaCfg.bAutoTxRateSwitch;
30470 + }
30471 + else
30472 + result = FALSE;
30473 +
30474 +#ifdef QOS_DLS_SUPPORT
30475 + if (pEntry && (pEntry->ValidAsDls))
30476 + result = pAd->StaCfg.bAutoTxRateSwitch;
30477 +#endif // QOS_DLS_SUPPORT //
30478 + }
30479 +#endif // CONFIG_STA_SUPPORT //
30480 +
30481 +
30482 +
30483 + return result;
30484 +}
30485 +
30486 +
30487 +BOOLEAN RTMPAutoRateSwitchCheck(
30488 + IN PRTMP_ADAPTER pAd)
30489 +{
30490 +
30491 +#ifdef CONFIG_STA_SUPPORT
30492 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
30493 + {
30494 + if (pAd->StaCfg.bAutoTxRateSwitch)
30495 + return TRUE;
30496 + }
30497 +#endif // CONFIG_STA_SUPPORT //
30498 + return FALSE;
30499 +}
30500 +
30501 +
30502 +/*
30503 + ========================================================================
30504 + Routine Description:
30505 + check if this entry need to fix tx legacy rate
30506 +
30507 + Arguments:
30508 + pAd
30509 + pEntry
30510 +
30511 + Return Value:
30512 + TURE
30513 + FALSE
30514 +
30515 + ========================================================================
30516 +*/
30517 +UCHAR RTMPStaFixedTxMode(
30518 + IN PRTMP_ADAPTER pAd,
30519 + IN PMAC_TABLE_ENTRY pEntry)
30520 +{
30521 + UCHAR tx_mode = FIXED_TXMODE_HT;
30522 +
30523 +
30524 +#ifdef CONFIG_STA_SUPPORT
30525 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
30526 + {
30527 + tx_mode = (UCHAR)pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode;
30528 + }
30529 +#endif // CONFIG_STA_SUPPORT //
30530 +
30531 + return tx_mode;
30532 +}
30533 +
30534 +/*
30535 + ========================================================================
30536 + Routine Description:
30537 + Overwrite HT Tx Mode by Fixed Legency Tx Mode, if specified.
30538 +
30539 + Arguments:
30540 + pAd
30541 + pEntry
30542 +
30543 + Return Value:
30544 + TURE
30545 + FALSE
30546 +
30547 + ========================================================================
30548 +*/
30549 +VOID RTMPUpdateLegacyTxSetting(
30550 + UCHAR fixed_tx_mode,
30551 + PMAC_TABLE_ENTRY pEntry)
30552 +{
30553 + HTTRANSMIT_SETTING TransmitSetting;
30554 +
30555 + if (fixed_tx_mode == FIXED_TXMODE_HT)
30556 + return;
30557 +
30558 + TransmitSetting.word = 0;
30559 +
30560 + TransmitSetting.field.MODE = pEntry->HTPhyMode.field.MODE;
30561 + TransmitSetting.field.MCS = pEntry->HTPhyMode.field.MCS;
30562 +
30563 + if (fixed_tx_mode == FIXED_TXMODE_CCK)
30564 + {
30565 + TransmitSetting.field.MODE = MODE_CCK;
30566 + // CCK mode allow MCS 0~3
30567 + if (TransmitSetting.field.MCS > MCS_3)
30568 + TransmitSetting.field.MCS = MCS_3;
30569 + }
30570 + else
30571 + {
30572 + TransmitSetting.field.MODE = MODE_OFDM;
30573 + // OFDM mode allow MCS 0~7
30574 + if (TransmitSetting.field.MCS > MCS_7)
30575 + TransmitSetting.field.MCS = MCS_7;
30576 + }
30577 +
30578 + if (pEntry->HTPhyMode.field.MODE >= TransmitSetting.field.MODE)
30579 + {
30580 + pEntry->HTPhyMode.word = TransmitSetting.word;
30581 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPUpdateLegacyTxSetting : wcid-%d, MODE=%s, MCS=%d \n",
30582 + pEntry->Aid, GetPhyMode(pEntry->HTPhyMode.field.MODE), pEntry->HTPhyMode.field.MCS));
30583 + }
30584 +}
30585 +
30586 +#ifdef CONFIG_STA_SUPPORT
30587 +/*
30588 + ==========================================================================
30589 + Description:
30590 + dynamic tune BBP R66 to find a balance between sensibility and
30591 + noise isolation
30592 +
30593 + IRQL = DISPATCH_LEVEL
30594 +
30595 + ==========================================================================
30596 + */
30597 +VOID AsicStaBbpTuning(
30598 + IN PRTMP_ADAPTER pAd)
30599 +{
30600 + UCHAR OrigR66Value = 0, R66;//, R66UpperBound = 0x30, R66LowerBound = 0x30;
30601 + CHAR Rssi;
30602 +
30603 + // 2860C did not support Fase CCA, therefore can't tune
30604 + if (pAd->MACVersion == 0x28600100)
30605 + return;
30606 +
30607 + //
30608 + // work as a STA
30609 + //
30610 + if (pAd->Mlme.CntlMachine.CurrState != CNTL_IDLE) // no R66 tuning when SCANNING
30611 + return;
30612 +
30613 + if ((pAd->OpMode == OPMODE_STA)
30614 + && (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED)
30615 + )
30616 + && !(OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
30617 +#ifdef RT2860
30618 + && (pAd->bPCIclkOff == FALSE)
30619 +#endif // RT2860 //
30620 + )
30621 + {
30622 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R66, &OrigR66Value);
30623 + R66 = OrigR66Value;
30624 +
30625 + if (pAd->Antenna.field.RxPath > 1)
30626 + Rssi = (pAd->StaCfg.RssiSample.AvgRssi0 + pAd->StaCfg.RssiSample.AvgRssi1) >> 1;
30627 + else
30628 + Rssi = pAd->StaCfg.RssiSample.AvgRssi0;
30629 +
30630 + if (pAd->LatchRfRegs.Channel <= 14)
30631 + { //BG band
30632 + {
30633 + if (Rssi > RSSI_FOR_MID_LOW_SENSIBILITY)
30634 + {
30635 + R66 = (0x2E + GET_LNA_GAIN(pAd)) + 0x10;
30636 + if (OrigR66Value != R66)
30637 + {
30638 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30639 + }
30640 + }
30641 + else
30642 + {
30643 + R66 = 0x2E + GET_LNA_GAIN(pAd);
30644 + if (OrigR66Value != R66)
30645 + {
30646 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30647 + }
30648 + }
30649 + }
30650 + }
30651 + else
30652 + { //A band
30653 + if (pAd->CommonCfg.BBPCurrentBW == BW_20)
30654 + {
30655 + if (Rssi > RSSI_FOR_MID_LOW_SENSIBILITY)
30656 + {
30657 + R66 = 0x32 + (GET_LNA_GAIN(pAd)*5)/3 + 0x10;
30658 + if (OrigR66Value != R66)
30659 + {
30660 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30661 + }
30662 + }
30663 + else
30664 + {
30665 + R66 = 0x32 + (GET_LNA_GAIN(pAd)*5)/3;
30666 + if (OrigR66Value != R66)
30667 + {
30668 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30669 + }
30670 + }
30671 + }
30672 + else
30673 + {
30674 + if (Rssi > RSSI_FOR_MID_LOW_SENSIBILITY)
30675 + {
30676 + R66 = 0x3A + (GET_LNA_GAIN(pAd)*5)/3 + 0x10;
30677 + if (OrigR66Value != R66)
30678 + {
30679 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30680 + }
30681 + }
30682 + else
30683 + {
30684 + R66 = 0x3A + (GET_LNA_GAIN(pAd)*5)/3;
30685 + if (OrigR66Value != R66)
30686 + {
30687 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30688 + }
30689 + }
30690 + }
30691 + }
30692 +
30693 +
30694 + }
30695 +}
30696 +#endif // CONFIG_STA_SUPPORT //
30697 +
30698 +VOID RTMPSetAGCInitValue(
30699 + IN PRTMP_ADAPTER pAd,
30700 + IN UCHAR BandWidth)
30701 +{
30702 + UCHAR R66 = 0x30;
30703 +
30704 + if (pAd->LatchRfRegs.Channel <= 14)
30705 + { // BG band
30706 + R66 = 0x2E + GET_LNA_GAIN(pAd);
30707 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30708 + }
30709 + else
30710 + { //A band
30711 + if (BandWidth == BW_20)
30712 + {
30713 + R66 = (UCHAR)(0x32 + (GET_LNA_GAIN(pAd)*5)/3);
30714 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30715 + }
30716 +#ifdef DOT11_N_SUPPORT
30717 + else
30718 + {
30719 + R66 = (UCHAR)(0x3A + (GET_LNA_GAIN(pAd)*5)/3);
30720 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
30721 + }
30722 +#endif // DOT11_N_SUPPORT //
30723 + }
30724 +
30725 +}
30726 +
30727 +VOID AsicTurnOffRFClk(
30728 + IN PRTMP_ADAPTER pAd,
30729 + IN UCHAR Channel)
30730 +{
30731 +
30732 + // RF R2 bit 18 = 0
30733 + UINT32 R1 = 0, R2 = 0, R3 = 0;
30734 + UCHAR index;
30735 + RTMP_RF_REGS *RFRegTable;
30736 +
30737 + RFRegTable = RF2850RegTable;
30738 +
30739 + switch (pAd->RfIcType)
30740 + {
30741 + case RFIC_2820:
30742 + case RFIC_2850:
30743 + case RFIC_2720:
30744 + case RFIC_2750:
30745 +
30746 + for (index = 0; index < NUM_OF_2850_CHNL; index++)
30747 + {
30748 + if (Channel == RFRegTable[index].Channel)
30749 + {
30750 + R1 = RFRegTable[index].R1 & 0xffffdfff;
30751 + R2 = RFRegTable[index].R2 & 0xfffbffff;
30752 + R3 = RFRegTable[index].R3 & 0xfff3ffff;
30753 +
30754 + RTMP_RF_IO_WRITE32(pAd, R1);
30755 + RTMP_RF_IO_WRITE32(pAd, R2);
30756 +
30757 + // Program R1b13 to 1, R3/b18,19 to 0, R2b18 to 0.
30758 + // Set RF R2 bit18=0, R3 bit[18:19]=0
30759 + //if (pAd->StaCfg.bRadio == FALSE)
30760 + if (1)
30761 + {
30762 + RTMP_RF_IO_WRITE32(pAd, R3);
30763 +
30764 + DBGPRINT(RT_DEBUG_TRACE, ("AsicTurnOffRFClk#%d(RF=%d, ) , R2=0x%08x, R3 = 0x%08x \n",
30765 + Channel, pAd->RfIcType, R2, R3));
30766 + }
30767 + else
30768 + DBGPRINT(RT_DEBUG_TRACE, ("AsicTurnOffRFClk#%d(RF=%d, ) , R2=0x%08x \n",
30769 + Channel, pAd->RfIcType, R2));
30770 + break;
30771 + }
30772 + }
30773 + break;
30774 +
30775 + default:
30776 + break;
30777 + }
30778 +}
30779 +
30780 +
30781 +VOID AsicTurnOnRFClk(
30782 + IN PRTMP_ADAPTER pAd,
30783 + IN UCHAR Channel)
30784 +{
30785 +
30786 + // RF R2 bit 18 = 0
30787 + UINT32 R1 = 0, R2 = 0, R3 = 0;
30788 + UCHAR index;
30789 + RTMP_RF_REGS *RFRegTable;
30790 +
30791 + RFRegTable = RF2850RegTable;
30792 +
30793 + switch (pAd->RfIcType)
30794 + {
30795 + case RFIC_2820:
30796 + case RFIC_2850:
30797 + case RFIC_2720:
30798 + case RFIC_2750:
30799 +
30800 + for (index = 0; index < NUM_OF_2850_CHNL; index++)
30801 + {
30802 + if (Channel == RFRegTable[index].Channel)
30803 + {
30804 + R3 = pAd->LatchRfRegs.R3;
30805 + R3 &= 0xfff3ffff;
30806 + R3 |= 0x00080000;
30807 + RTMP_RF_IO_WRITE32(pAd, R3);
30808 +
30809 + R1 = RFRegTable[index].R1;
30810 + RTMP_RF_IO_WRITE32(pAd, R1);
30811 +
30812 + R2 = RFRegTable[index].R2;
30813 + if (pAd->Antenna.field.TxPath == 1)
30814 + {
30815 + R2 |= 0x4000; // If TXpath is 1, bit 14 = 1;
30816 + }
30817 +
30818 + if (pAd->Antenna.field.RxPath == 2)
30819 + {
30820 + R2 |= 0x40; // write 1 to off Rxpath.
30821 + }
30822 + else if (pAd->Antenna.field.RxPath == 1)
30823 + {
30824 + R2 |= 0x20040; // write 1 to off RxPath
30825 + }
30826 + RTMP_RF_IO_WRITE32(pAd, R2);
30827 +
30828 + break;
30829 + }
30830 + }
30831 + break;
30832 +
30833 + default:
30834 + break;
30835 + }
30836 +
30837 + DBGPRINT(RT_DEBUG_TRACE, ("AsicTurnOnRFClk#%d(RF=%d, ) , R2=0x%08x\n",
30838 + Channel,
30839 + pAd->RfIcType,
30840 + R2));
30841 +}
30842 +
30843 --- /dev/null
30844 +++ b/drivers/staging/rt2860/common/netif_block.c
30845 @@ -0,0 +1,144 @@
30846 +/*
30847 + *************************************************************************
30848 + * Ralink Tech Inc.
30849 + * 5F., No.36, Taiyuan St., Jhubei City,
30850 + * Hsinchu County 302,
30851 + * Taiwan, R.O.C.
30852 + *
30853 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
30854 + *
30855 + * This program is free software; you can redistribute it and/or modify *
30856 + * it under the terms of the GNU General Public License as published by *
30857 + * the Free Software Foundation; either version 2 of the License, or *
30858 + * (at your option) any later version. *
30859 + * *
30860 + * This program is distributed in the hope that it will be useful, *
30861 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
30862 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
30863 + * GNU General Public License for more details. *
30864 + * *
30865 + * You should have received a copy of the GNU General Public License *
30866 + * along with this program; if not, write to the *
30867 + * Free Software Foundation, Inc., *
30868 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
30869 + * *
30870 + *************************************************************************
30871 + */
30872 +
30873 +#include "../rt_config.h"
30874 +#include "netif_block.h"
30875 +
30876 +static NETIF_ENTRY freeNetIfEntryPool[FREE_NETIF_POOL_SIZE];
30877 +static LIST_HEADER freeNetIfEntryList;
30878 +
30879 +void initblockQueueTab(
30880 + IN PRTMP_ADAPTER pAd)
30881 +{
30882 + int i;
30883 +
30884 + initList(&freeNetIfEntryList);
30885 + for (i = 0; i < FREE_NETIF_POOL_SIZE; i++)
30886 + insertTailList(&freeNetIfEntryList, (PLIST_ENTRY)&freeNetIfEntryPool[i]);
30887 +
30888 + for (i=0; i < NUM_OF_TX_RING; i++)
30889 + initList(&pAd->blockQueueTab[i].NetIfList);
30890 +
30891 + return;
30892 +}
30893 +
30894 +BOOLEAN blockNetIf(
30895 + IN PBLOCK_QUEUE_ENTRY pBlockQueueEntry,
30896 + IN PNET_DEV pNetDev)
30897 +{
30898 + PNETIF_ENTRY pNetIfEntry = NULL;
30899 +
30900 + if ((pNetIfEntry = (PNETIF_ENTRY)removeHeadList(&freeNetIfEntryList)) != NULL)
30901 + {
30902 + netif_stop_queue(pNetDev);
30903 + pNetIfEntry->pNetDev = pNetDev;
30904 + insertTailList(&pBlockQueueEntry->NetIfList, (PLIST_ENTRY)pNetIfEntry);
30905 +
30906 + pBlockQueueEntry->SwTxQueueBlockFlag = TRUE;
30907 + DBGPRINT(RT_DEBUG_TRACE, ("netif_stop_queue(%s)\n", pNetDev->name));
30908 + }
30909 + else
30910 + return FALSE;
30911 +
30912 + return TRUE;
30913 +}
30914 +
30915 +VOID releaseNetIf(
30916 + IN PBLOCK_QUEUE_ENTRY pBlockQueueEntry)
30917 +{
30918 + PNETIF_ENTRY pNetIfEntry = NULL;
30919 + PLIST_HEADER pNetIfList = &pBlockQueueEntry->NetIfList;
30920 +
30921 + while((pNetIfEntry = (PNETIF_ENTRY)removeHeadList(pNetIfList)) != NULL)
30922 + {
30923 + PNET_DEV pNetDev = pNetIfEntry->pNetDev;
30924 + netif_wake_queue(pNetDev);
30925 + insertTailList(&freeNetIfEntryList, (PLIST_ENTRY)pNetIfEntry);
30926 +
30927 + DBGPRINT(RT_DEBUG_TRACE, ("netif_wake_queue(%s)\n", pNetDev->name));
30928 + }
30929 + pBlockQueueEntry->SwTxQueueBlockFlag = FALSE;
30930 + return;
30931 +}
30932 +
30933 +
30934 +VOID StopNetIfQueue(
30935 + IN PRTMP_ADAPTER pAd,
30936 + IN UCHAR QueIdx,
30937 + IN PNDIS_PACKET pPacket)
30938 +{
30939 + PNET_DEV NetDev = NULL;
30940 + UCHAR IfIdx = 0;
30941 + BOOLEAN valid = FALSE;
30942 +
30943 +#ifdef APCLI_SUPPORT
30944 + if (RTMP_GET_PACKET_NET_DEVICE(pPacket) >= MIN_NET_DEVICE_FOR_APCLI)
30945 + {
30946 + IfIdx = (RTMP_GET_PACKET_NET_DEVICE(pPacket) - MIN_NET_DEVICE_FOR_APCLI) % MAX_APCLI_NUM;
30947 + NetDev = pAd->ApCfg.ApCliTab[IfIdx].dev;
30948 + }
30949 + else
30950 +#endif // APCLI_SUPPORT //
30951 +#ifdef WDS_SUPPORT
30952 + if (RTMP_GET_PACKET_NET_DEVICE(pPacket) >= MIN_NET_DEVICE_FOR_WDS)
30953 + {
30954 + IfIdx = (RTMP_GET_PACKET_NET_DEVICE(pPacket) - MIN_NET_DEVICE_FOR_WDS) % MAX_WDS_ENTRY;
30955 + NetDev = pAd->WdsTab.WdsEntry[IfIdx].dev;
30956 + }
30957 + else
30958 +#endif // WDS_SUPPORT //
30959 + {
30960 +#ifdef MBSS_SUPPORT
30961 + if (pAd->OpMode == OPMODE_AP)
30962 + {
30963 + IfIdx = (RTMP_GET_PACKET_NET_DEVICE(pPacket) - MIN_NET_DEVICE_FOR_MBSSID) % MAX_MBSSID_NUM;
30964 + NetDev = pAd->ApCfg.MBSSID[IfIdx].MSSIDDev;
30965 + }
30966 + else
30967 + {
30968 + IfIdx = MAIN_MBSSID;
30969 + NetDev = pAd->net_dev;
30970 + }
30971 +#else
30972 + IfIdx = MAIN_MBSSID;
30973 + NetDev = pAd->net_dev;
30974 +#endif
30975 + }
30976 +
30977 + // WMM support 4 software queues.
30978 + // One software queue full doesn't mean device have no capbility to transmit packet.
30979 + // So disable block Net-If queue function while WMM enable.
30980 +#ifdef CONFIG_STA_SUPPORT
30981 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
30982 + valid = (pAd->CommonCfg.bWmmCapable == TRUE) ? FALSE : TRUE;
30983 +#endif // CONFIG_STA_SUPPORT //
30984 +
30985 + if (valid)
30986 + blockNetIf(&pAd->blockQueueTab[QueIdx], NetDev);
30987 + return;
30988 +}
30989 +
30990 --- /dev/null
30991 +++ b/drivers/staging/rt2860/common/netif_block.h
30992 @@ -0,0 +1,58 @@
30993 +/*
30994 + *************************************************************************
30995 + * Ralink Tech Inc.
30996 + * 5F., No.36, Taiyuan St., Jhubei City,
30997 + * Hsinchu County 302,
30998 + * Taiwan, R.O.C.
30999 + *
31000 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
31001 + *
31002 + * This program is free software; you can redistribute it and/or modify *
31003 + * it under the terms of the GNU General Public License as published by *
31004 + * the Free Software Foundation; either version 2 of the License, or *
31005 + * (at your option) any later version. *
31006 + * *
31007 + * This program is distributed in the hope that it will be useful, *
31008 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
31009 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
31010 + * GNU General Public License for more details. *
31011 + * *
31012 + * You should have received a copy of the GNU General Public License *
31013 + * along with this program; if not, write to the *
31014 + * Free Software Foundation, Inc., *
31015 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
31016 + * *
31017 + *************************************************************************
31018 + */
31019 +
31020 +#ifndef __NET_IF_BLOCK_H__
31021 +#define __NET_IF_BLOCK_H__
31022 +
31023 +//#include <linux/device.h>
31024 +#include "link_list.h"
31025 +#include "rtmp.h"
31026 +
31027 +#define FREE_NETIF_POOL_SIZE 32
31028 +
31029 +typedef struct _NETIF_ENTRY
31030 +{
31031 + struct _NETIF_ENTRY *pNext;
31032 + PNET_DEV pNetDev;
31033 +} NETIF_ENTRY, *PNETIF_ENTRY;
31034 +
31035 +void initblockQueueTab(
31036 + IN PRTMP_ADAPTER pAd);
31037 +
31038 +BOOLEAN blockNetIf(
31039 + IN PBLOCK_QUEUE_ENTRY pBlockQueueEntry,
31040 + IN PNET_DEV pNetDev);
31041 +
31042 +VOID releaseNetIf(
31043 + IN PBLOCK_QUEUE_ENTRY pBlockQueueEntry);
31044 +
31045 +VOID StopNetIfQueue(
31046 + IN PRTMP_ADAPTER pAd,
31047 + IN UCHAR QueIdx,
31048 + IN PNDIS_PACKET pPacket);
31049 +#endif // __NET_IF_BLOCK_H__
31050 +
31051 --- /dev/null
31052 +++ b/drivers/staging/rt2860/common/rtmp_init.c
31053 @@ -0,0 +1,3757 @@
31054 +/*
31055 + *************************************************************************
31056 + * Ralink Tech Inc.
31057 + * 5F., No.36, Taiyuan St., Jhubei City,
31058 + * Hsinchu County 302,
31059 + * Taiwan, R.O.C.
31060 + *
31061 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
31062 + *
31063 + * This program is free software; you can redistribute it and/or modify *
31064 + * it under the terms of the GNU General Public License as published by *
31065 + * the Free Software Foundation; either version 2 of the License, or *
31066 + * (at your option) any later version. *
31067 + * *
31068 + * This program is distributed in the hope that it will be useful, *
31069 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
31070 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
31071 + * GNU General Public License for more details. *
31072 + * *
31073 + * You should have received a copy of the GNU General Public License *
31074 + * along with this program; if not, write to the *
31075 + * Free Software Foundation, Inc., *
31076 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
31077 + * *
31078 + *************************************************************************
31079 +
31080 + Module Name:
31081 + rtmp_init.c
31082 +
31083 + Abstract:
31084 + Miniport generic portion header file
31085 +
31086 + Revision History:
31087 + Who When What
31088 + -------- ---------- ----------------------------------------------
31089 + Paul Lin 2002-08-01 created
31090 + John Chang 2004-08-20 RT2561/2661 use scatter-gather scheme
31091 + Jan Lee 2006-09-15 RT2860. Change for 802.11n , EEPROM, Led, BA, HT.
31092 +*/
31093 +#include "../rt_config.h"
31094 +#include "firmware.h"
31095 +
31096 +UCHAR BIT8[] = {0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80};
31097 +ULONG BIT32[] = {0x00000001, 0x00000002, 0x00000004, 0x00000008,
31098 + 0x00000010, 0x00000020, 0x00000040, 0x00000080,
31099 + 0x00000100, 0x00000200, 0x00000400, 0x00000800,
31100 + 0x00001000, 0x00002000, 0x00004000, 0x00008000,
31101 + 0x00010000, 0x00020000, 0x00040000, 0x00080000,
31102 + 0x00100000, 0x00200000, 0x00400000, 0x00800000,
31103 + 0x01000000, 0x02000000, 0x04000000, 0x08000000,
31104 + 0x10000000, 0x20000000, 0x40000000, 0x80000000};
31105 +
31106 +char* CipherName[] = {"none","wep64","wep128","TKIP","AES","CKIP64","CKIP128"};
31107 +
31108 +const unsigned short ccitt_16Table[] = {
31109 + 0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50A5, 0x60C6, 0x70E7,
31110 + 0x8108, 0x9129, 0xA14A, 0xB16B, 0xC18C, 0xD1AD, 0xE1CE, 0xF1EF,
31111 + 0x1231, 0x0210, 0x3273, 0x2252, 0x52B5, 0x4294, 0x72F7, 0x62D6,
31112 + 0x9339, 0x8318, 0xB37B, 0xA35A, 0xD3BD, 0xC39C, 0xF3FF, 0xE3DE,
31113 + 0x2462, 0x3443, 0x0420, 0x1401, 0x64E6, 0x74C7, 0x44A4, 0x5485,
31114 + 0xA56A, 0xB54B, 0x8528, 0x9509, 0xE5EE, 0xF5CF, 0xC5AC, 0xD58D,
31115 + 0x3653, 0x2672, 0x1611, 0x0630, 0x76D7, 0x66F6, 0x5695, 0x46B4,
31116 + 0xB75B, 0xA77A, 0x9719, 0x8738, 0xF7DF, 0xE7FE, 0xD79D, 0xC7BC,
31117 + 0x48C4, 0x58E5, 0x6886, 0x78A7, 0x0840, 0x1861, 0x2802, 0x3823,
31118 + 0xC9CC, 0xD9ED, 0xE98E, 0xF9AF, 0x8948, 0x9969, 0xA90A, 0xB92B,
31119 + 0x5AF5, 0x4AD4, 0x7AB7, 0x6A96, 0x1A71, 0x0A50, 0x3A33, 0x2A12,
31120 + 0xDBFD, 0xCBDC, 0xFBBF, 0xEB9E, 0x9B79, 0x8B58, 0xBB3B, 0xAB1A,
31121 + 0x6CA6, 0x7C87, 0x4CE4, 0x5CC5, 0x2C22, 0x3C03, 0x0C60, 0x1C41,
31122 + 0xEDAE, 0xFD8F, 0xCDEC, 0xDDCD, 0xAD2A, 0xBD0B, 0x8D68, 0x9D49,
31123 + 0x7E97, 0x6EB6, 0x5ED5, 0x4EF4, 0x3E13, 0x2E32, 0x1E51, 0x0E70,
31124 + 0xFF9F, 0xEFBE, 0xDFDD, 0xCFFC, 0xBF1B, 0xAF3A, 0x9F59, 0x8F78,
31125 + 0x9188, 0x81A9, 0xB1CA, 0xA1EB, 0xD10C, 0xC12D, 0xF14E, 0xE16F,
31126 + 0x1080, 0x00A1, 0x30C2, 0x20E3, 0x5004, 0x4025, 0x7046, 0x6067,
31127 + 0x83B9, 0x9398, 0xA3FB, 0xB3DA, 0xC33D, 0xD31C, 0xE37F, 0xF35E,
31128 + 0x02B1, 0x1290, 0x22F3, 0x32D2, 0x4235, 0x5214, 0x6277, 0x7256,
31129 + 0xB5EA, 0xA5CB, 0x95A8, 0x8589, 0xF56E, 0xE54F, 0xD52C, 0xC50D,
31130 + 0x34E2, 0x24C3, 0x14A0, 0x0481, 0x7466, 0x6447, 0x5424, 0x4405,
31131 + 0xA7DB, 0xB7FA, 0x8799, 0x97B8, 0xE75F, 0xF77E, 0xC71D, 0xD73C,
31132 + 0x26D3, 0x36F2, 0x0691, 0x16B0, 0x6657, 0x7676, 0x4615, 0x5634,
31133 + 0xD94C, 0xC96D, 0xF90E, 0xE92F, 0x99C8, 0x89E9, 0xB98A, 0xA9AB,
31134 + 0x5844, 0x4865, 0x7806, 0x6827, 0x18C0, 0x08E1, 0x3882, 0x28A3,
31135 + 0xCB7D, 0xDB5C, 0xEB3F, 0xFB1E, 0x8BF9, 0x9BD8, 0xABBB, 0xBB9A,
31136 + 0x4A75, 0x5A54, 0x6A37, 0x7A16, 0x0AF1, 0x1AD0, 0x2AB3, 0x3A92,
31137 + 0xFD2E, 0xED0F, 0xDD6C, 0xCD4D, 0xBDAA, 0xAD8B, 0x9DE8, 0x8DC9,
31138 + 0x7C26, 0x6C07, 0x5C64, 0x4C45, 0x3CA2, 0x2C83, 0x1CE0, 0x0CC1,
31139 + 0xEF1F, 0xFF3E, 0xCF5D, 0xDF7C, 0xAF9B, 0xBFBA, 0x8FD9, 0x9FF8,
31140 + 0x6E17, 0x7E36, 0x4E55, 0x5E74, 0x2E93, 0x3EB2, 0x0ED1, 0x1EF0
31141 +};
31142 +#define ByteCRC16(v, crc) \
31143 + (unsigned short)((crc << 8) ^ ccitt_16Table[((crc >> 8) ^ (v)) & 255])
31144 +
31145 +unsigned char BitReverse(unsigned char x)
31146 +{
31147 + int i;
31148 + unsigned char Temp=0;
31149 + for(i=0; ; i++)
31150 + {
31151 + if(x & 0x80) Temp |= 0x80;
31152 + if(i==7) break;
31153 + x <<= 1;
31154 + Temp >>= 1;
31155 + }
31156 + return Temp;
31157 +}
31158 +
31159 +//
31160 +// BBP register initialization set
31161 +//
31162 +REG_PAIR BBPRegTable[] = {
31163 + {BBP_R65, 0x2C}, // fix rssi issue
31164 + {BBP_R66, 0x38}, // Also set this default value to pAd->BbpTuning.R66CurrentValue at initial
31165 + {BBP_R69, 0x12},
31166 + {BBP_R70, 0xa}, // BBP_R70 will change to 0x8 in ApStartUp and LinkUp for rt2860C, otherwise value is 0xa
31167 + {BBP_R73, 0x10},
31168 + {BBP_R81, 0x37},
31169 + {BBP_R82, 0x62},
31170 + {BBP_R83, 0x6A},
31171 + {BBP_R84, 0x99}, // 0x19 is for rt2860E and after. This is for extension channel overlapping IOT. 0x99 is for rt2860D and before
31172 + {BBP_R86, 0x00}, // middle range issue, Rory @2008-01-28
31173 + {BBP_R91, 0x04}, // middle range issue, Rory @2008-01-28
31174 + {BBP_R92, 0x00}, // middle range issue, Rory @2008-01-28
31175 + {BBP_R103, 0x00}, // near range high-power issue, requested from Gary @2008-0528
31176 + {BBP_R105, 0x05}, // 0x05 is for rt2860E to turn on FEQ control. It is safe for rt2860D and before, because Bit 7:2 are reserved in rt2860D and before.
31177 +};
31178 +#define NUM_BBP_REG_PARMS (sizeof(BBPRegTable) / sizeof(REG_PAIR))
31179 +
31180 +//
31181 +// RF register initialization set
31182 +//
31183 +
31184 +//
31185 +// ASIC register initialization sets
31186 +//
31187 +
31188 +RTMP_REG_PAIR MACRegTable[] = {
31189 +#if defined(HW_BEACON_OFFSET) && (HW_BEACON_OFFSET == 0x200)
31190 + {BCN_OFFSET0, 0xf8f0e8e0}, /* 0x3800(e0), 0x3A00(e8), 0x3C00(f0), 0x3E00(f8), 512B for each beacon */
31191 + {BCN_OFFSET1, 0x6f77d0c8}, /* 0x3200(c8), 0x3400(d0), 0x1DC0(77), 0x1BC0(6f), 512B for each beacon */
31192 +#elif defined(HW_BEACON_OFFSET) && (HW_BEACON_OFFSET == 0x100)
31193 + {BCN_OFFSET0, 0xece8e4e0}, /* 0x3800, 0x3A00, 0x3C00, 0x3E00, 512B for each beacon */
31194 + {BCN_OFFSET1, 0xfcf8f4f0}, /* 0x3800, 0x3A00, 0x3C00, 0x3E00, 512B for each beacon */
31195 +#else
31196 + #error You must re-calculate new value for BCN_OFFSET0 & BCN_OFFSET1 in MACRegTable[]!!!
31197 +#endif // HW_BEACON_OFFSET //
31198 +
31199 + {LEGACY_BASIC_RATE, 0x0000013f}, // Basic rate set bitmap
31200 + {HT_BASIC_RATE, 0x00008003}, // Basic HT rate set , 20M, MCS=3, MM. Format is the same as in TXWI.
31201 + {MAC_SYS_CTRL, 0x00}, // 0x1004, , default Disable RX
31202 + {RX_FILTR_CFG, 0x17f97}, //0x1400 , RX filter control,
31203 + {BKOFF_SLOT_CFG, 0x209}, // default set short slot time, CC_DELAY_TIME should be 2
31204 + {TX_SW_CFG0, 0x0}, // Gary,2008-05-21 for CWC test
31205 + {TX_SW_CFG1, 0x80606}, // Gary,2006-08-23
31206 + {TX_LINK_CFG, 0x1020}, // Gary,2006-08-23
31207 + {TX_TIMEOUT_CFG, 0x000a2090}, // CCK has some problem. So increase timieout value. 2006-10-09// MArvek RT , Modify for 2860E ,2007-08-01
31208 + {MAX_LEN_CFG, MAX_AGGREGATION_SIZE | 0x00001000}, // 0x3018, MAX frame length. Max PSDU = 16kbytes.
31209 + {LED_CFG, 0x7f031e46}, // Gary, 2006-08-23
31210 + {PBF_MAX_PCNT, 0x1F3FBF9F}, //0x1F3f7f9f}, //Jan, 2006/04/20
31211 + {TX_RTY_CFG, 0x47d01f0f}, // Jan, 2006/11/16, Set TxWI->ACK =0 in Probe Rsp Modify for 2860E ,2007-08-03
31212 + {AUTO_RSP_CFG, 0x00000013}, // Initial Auto_Responder, because QA will turn off Auto-Responder
31213 + {CCK_PROT_CFG, 0x05740003 /*0x01740003*/}, // Initial Auto_Responder, because QA will turn off Auto-Responder. And RTS threshold is enabled.
31214 + {OFDM_PROT_CFG, 0x05740003 /*0x01740003*/}, // Initial Auto_Responder, because QA will turn off Auto-Responder. And RTS threshold is enabled.
31215 + {GF20_PROT_CFG, 0x01744004}, // set 19:18 --> Short NAV for MIMO PS
31216 + {GF40_PROT_CFG, 0x03F44084},
31217 + {MM20_PROT_CFG, 0x01744004},
31218 +#ifdef RT2860
31219 + {MM40_PROT_CFG, 0x03F54084},
31220 +#endif // RT2860 //
31221 + {TXOP_CTRL_CFG, 0x0000583f, /*0x0000243f*/ /*0x000024bf*/}, //Extension channel backoff.
31222 + {TX_RTS_CFG, 0x00092b20},
31223 + {EXP_ACK_TIME, 0x002400ca}, // default value
31224 + {TXOP_HLDR_ET, 0x00000002},
31225 +
31226 + /* Jerry comments 2008/01/16: we use SIFS = 10us in CCK defaultly, but it seems that 10us
31227 + is too small for INTEL 2200bg card, so in MBSS mode, the delta time between beacon0
31228 + and beacon1 is SIFS (10us), so if INTEL 2200bg card connects to BSS0, the ping
31229 + will always lost. So we change the SIFS of CCK from 10us to 16us. */
31230 + {XIFS_TIME_CFG, 0x33a41010},
31231 + {PWR_PIN_CFG, 0x00000003}, // patch for 2880-E
31232 +};
31233 +
31234 +
31235 +#ifdef CONFIG_STA_SUPPORT
31236 +RTMP_REG_PAIR STAMACRegTable[] = {
31237 + {WMM_AIFSN_CFG, 0x00002273},
31238 + {WMM_CWMIN_CFG, 0x00002344},
31239 + {WMM_CWMAX_CFG, 0x000034aa},
31240 +};
31241 +#endif // CONFIG_STA_SUPPORT //
31242 +
31243 +#define NUM_MAC_REG_PARMS (sizeof(MACRegTable) / sizeof(RTMP_REG_PAIR))
31244 +#ifdef CONFIG_STA_SUPPORT
31245 +#define NUM_STA_MAC_REG_PARMS (sizeof(STAMACRegTable) / sizeof(RTMP_REG_PAIR))
31246 +#endif // CONFIG_STA_SUPPORT //
31247 +
31248 +
31249 +// New 8k byte firmware size for RT3071/RT3072
31250 +#define FIRMWAREIMAGE_MAX_LENGTH 0x2000
31251 +#define FIRMWAREIMAGE_LENGTH (sizeof (FirmwareImage) / sizeof(UCHAR))
31252 +#define FIRMWARE_MAJOR_VERSION 0
31253 +
31254 +#define FIRMWAREIMAGEV1_LENGTH 0x1000
31255 +#define FIRMWAREIMAGEV2_LENGTH 0x1000
31256 +
31257 +#ifdef RT2860
31258 +#define FIRMWARE_MINOR_VERSION 2
31259 +#endif // RT2860 //
31260 +
31261 +
31262 +/*
31263 + ========================================================================
31264 +
31265 + Routine Description:
31266 + Allocate RTMP_ADAPTER data block and do some initialization
31267 +
31268 + Arguments:
31269 + Adapter Pointer to our adapter
31270 +
31271 + Return Value:
31272 + NDIS_STATUS_SUCCESS
31273 + NDIS_STATUS_FAILURE
31274 +
31275 + IRQL = PASSIVE_LEVEL
31276 +
31277 + Note:
31278 +
31279 + ========================================================================
31280 +*/
31281 +NDIS_STATUS RTMPAllocAdapterBlock(
31282 + IN PVOID handle,
31283 + OUT PRTMP_ADAPTER *ppAdapter)
31284 +{
31285 + PRTMP_ADAPTER pAd;
31286 + NDIS_STATUS Status;
31287 + INT index;
31288 + UCHAR *pBeaconBuf = NULL;
31289 +
31290 + DBGPRINT(RT_DEBUG_TRACE, ("--> RTMPAllocAdapterBlock\n"));
31291 +
31292 + *ppAdapter = NULL;
31293 +
31294 + do
31295 + {
31296 + // Allocate RTMP_ADAPTER memory block
31297 + pBeaconBuf = kmalloc(MAX_BEACON_SIZE, MEM_ALLOC_FLAG);
31298 + if (pBeaconBuf == NULL)
31299 + {
31300 + Status = NDIS_STATUS_FAILURE;
31301 + DBGPRINT_ERR(("Failed to allocate memory - BeaconBuf!\n"));
31302 + break;
31303 + }
31304 +
31305 + Status = AdapterBlockAllocateMemory(handle, (PVOID *)&pAd);
31306 + if (Status != NDIS_STATUS_SUCCESS)
31307 + {
31308 + DBGPRINT_ERR(("Failed to allocate memory - ADAPTER\n"));
31309 + break;
31310 + }
31311 + pAd->BeaconBuf = pBeaconBuf;
31312 + printk("\n\n=== pAd = %p, size = %d ===\n\n", pAd, (UINT32)sizeof(RTMP_ADAPTER));
31313 +
31314 +
31315 + // Init spin locks
31316 + NdisAllocateSpinLock(&pAd->MgmtRingLock);
31317 +#ifdef RT2860
31318 + NdisAllocateSpinLock(&pAd->RxRingLock);
31319 +#endif // RT2860 //
31320 +
31321 + for (index =0 ; index < NUM_OF_TX_RING; index++)
31322 + {
31323 + NdisAllocateSpinLock(&pAd->TxSwQueueLock[index]);
31324 + NdisAllocateSpinLock(&pAd->DeQueueLock[index]);
31325 + pAd->DeQueueRunning[index] = FALSE;
31326 + }
31327 +
31328 + NdisAllocateSpinLock(&pAd->irq_lock);
31329 +
31330 + } while (FALSE);
31331 +
31332 + if ((Status != NDIS_STATUS_SUCCESS) && (pBeaconBuf))
31333 + kfree(pBeaconBuf);
31334 +
31335 + *ppAdapter = pAd;
31336 +
31337 + DBGPRINT_S(Status, ("<-- RTMPAllocAdapterBlock, Status=%x\n", Status));
31338 + return Status;
31339 +}
31340 +
31341 +/*
31342 + ========================================================================
31343 +
31344 + Routine Description:
31345 + Read initial Tx power per MCS and BW from EEPROM
31346 +
31347 + Arguments:
31348 + Adapter Pointer to our adapter
31349 +
31350 + Return Value:
31351 + None
31352 +
31353 + IRQL = PASSIVE_LEVEL
31354 +
31355 + Note:
31356 +
31357 + ========================================================================
31358 +*/
31359 +VOID RTMPReadTxPwrPerRate(
31360 + IN PRTMP_ADAPTER pAd)
31361 +{
31362 + ULONG data, Adata, Gdata;
31363 + USHORT i, value, value2;
31364 + INT Apwrdelta, Gpwrdelta;
31365 + UCHAR t1,t2,t3,t4;
31366 + BOOLEAN bValid, bApwrdeltaMinus = TRUE, bGpwrdeltaMinus = TRUE;
31367 +
31368 + //
31369 + // Get power delta for 20MHz and 40MHz.
31370 + //
31371 + DBGPRINT(RT_DEBUG_TRACE, ("Txpower per Rate\n"));
31372 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_DELTA, value2);
31373 + Apwrdelta = 0;
31374 + Gpwrdelta = 0;
31375 +
31376 + if ((value2 & 0xff) != 0xff)
31377 + {
31378 + if ((value2 & 0x80))
31379 + Gpwrdelta = (value2&0xf);
31380 +
31381 + if ((value2 & 0x40))
31382 + bGpwrdeltaMinus = FALSE;
31383 + else
31384 + bGpwrdeltaMinus = TRUE;
31385 + }
31386 + if ((value2 & 0xff00) != 0xff00)
31387 + {
31388 + if ((value2 & 0x8000))
31389 + Apwrdelta = ((value2&0xf00)>>8);
31390 +
31391 + if ((value2 & 0x4000))
31392 + bApwrdeltaMinus = FALSE;
31393 + else
31394 + bApwrdeltaMinus = TRUE;
31395 + }
31396 + DBGPRINT(RT_DEBUG_TRACE, ("Gpwrdelta = %x, Apwrdelta = %x .\n", Gpwrdelta, Apwrdelta));
31397 +
31398 + //
31399 + // Get Txpower per MCS for 20MHz in 2.4G.
31400 + //
31401 + for (i=0; i<5; i++)
31402 + {
31403 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_20MHZ_2_4G + i*4, value);
31404 + data = value;
31405 + if (bApwrdeltaMinus == FALSE)
31406 + {
31407 + t1 = (value&0xf)+(Apwrdelta);
31408 + if (t1 > 0xf)
31409 + t1 = 0xf;
31410 + t2 = ((value&0xf0)>>4)+(Apwrdelta);
31411 + if (t2 > 0xf)
31412 + t2 = 0xf;
31413 + t3 = ((value&0xf00)>>8)+(Apwrdelta);
31414 + if (t3 > 0xf)
31415 + t3 = 0xf;
31416 + t4 = ((value&0xf000)>>12)+(Apwrdelta);
31417 + if (t4 > 0xf)
31418 + t4 = 0xf;
31419 + }
31420 + else
31421 + {
31422 + if ((value&0xf) > Apwrdelta)
31423 + t1 = (value&0xf)-(Apwrdelta);
31424 + else
31425 + t1 = 0;
31426 + if (((value&0xf0)>>4) > Apwrdelta)
31427 + t2 = ((value&0xf0)>>4)-(Apwrdelta);
31428 + else
31429 + t2 = 0;
31430 + if (((value&0xf00)>>8) > Apwrdelta)
31431 + t3 = ((value&0xf00)>>8)-(Apwrdelta);
31432 + else
31433 + t3 = 0;
31434 + if (((value&0xf000)>>12) > Apwrdelta)
31435 + t4 = ((value&0xf000)>>12)-(Apwrdelta);
31436 + else
31437 + t4 = 0;
31438 + }
31439 + Adata = t1 + (t2<<4) + (t3<<8) + (t4<<12);
31440 + if (bGpwrdeltaMinus == FALSE)
31441 + {
31442 + t1 = (value&0xf)+(Gpwrdelta);
31443 + if (t1 > 0xf)
31444 + t1 = 0xf;
31445 + t2 = ((value&0xf0)>>4)+(Gpwrdelta);
31446 + if (t2 > 0xf)
31447 + t2 = 0xf;
31448 + t3 = ((value&0xf00)>>8)+(Gpwrdelta);
31449 + if (t3 > 0xf)
31450 + t3 = 0xf;
31451 + t4 = ((value&0xf000)>>12)+(Gpwrdelta);
31452 + if (t4 > 0xf)
31453 + t4 = 0xf;
31454 + }
31455 + else
31456 + {
31457 + if ((value&0xf) > Gpwrdelta)
31458 + t1 = (value&0xf)-(Gpwrdelta);
31459 + else
31460 + t1 = 0;
31461 + if (((value&0xf0)>>4) > Gpwrdelta)
31462 + t2 = ((value&0xf0)>>4)-(Gpwrdelta);
31463 + else
31464 + t2 = 0;
31465 + if (((value&0xf00)>>8) > Gpwrdelta)
31466 + t3 = ((value&0xf00)>>8)-(Gpwrdelta);
31467 + else
31468 + t3 = 0;
31469 + if (((value&0xf000)>>12) > Gpwrdelta)
31470 + t4 = ((value&0xf000)>>12)-(Gpwrdelta);
31471 + else
31472 + t4 = 0;
31473 + }
31474 + Gdata = t1 + (t2<<4) + (t3<<8) + (t4<<12);
31475 +
31476 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_20MHZ_2_4G + i*4 + 2, value);
31477 + if (bApwrdeltaMinus == FALSE)
31478 + {
31479 + t1 = (value&0xf)+(Apwrdelta);
31480 + if (t1 > 0xf)
31481 + t1 = 0xf;
31482 + t2 = ((value&0xf0)>>4)+(Apwrdelta);
31483 + if (t2 > 0xf)
31484 + t2 = 0xf;
31485 + t3 = ((value&0xf00)>>8)+(Apwrdelta);
31486 + if (t3 > 0xf)
31487 + t3 = 0xf;
31488 + t4 = ((value&0xf000)>>12)+(Apwrdelta);
31489 + if (t4 > 0xf)
31490 + t4 = 0xf;
31491 + }
31492 + else
31493 + {
31494 + if ((value&0xf) > Apwrdelta)
31495 + t1 = (value&0xf)-(Apwrdelta);
31496 + else
31497 + t1 = 0;
31498 + if (((value&0xf0)>>4) > Apwrdelta)
31499 + t2 = ((value&0xf0)>>4)-(Apwrdelta);
31500 + else
31501 + t2 = 0;
31502 + if (((value&0xf00)>>8) > Apwrdelta)
31503 + t3 = ((value&0xf00)>>8)-(Apwrdelta);
31504 + else
31505 + t3 = 0;
31506 + if (((value&0xf000)>>12) > Apwrdelta)
31507 + t4 = ((value&0xf000)>>12)-(Apwrdelta);
31508 + else
31509 + t4 = 0;
31510 + }
31511 + Adata |= ((t1<<16) + (t2<<20) + (t3<<24) + (t4<<28));
31512 + if (bGpwrdeltaMinus == FALSE)
31513 + {
31514 + t1 = (value&0xf)+(Gpwrdelta);
31515 + if (t1 > 0xf)
31516 + t1 = 0xf;
31517 + t2 = ((value&0xf0)>>4)+(Gpwrdelta);
31518 + if (t2 > 0xf)
31519 + t2 = 0xf;
31520 + t3 = ((value&0xf00)>>8)+(Gpwrdelta);
31521 + if (t3 > 0xf)
31522 + t3 = 0xf;
31523 + t4 = ((value&0xf000)>>12)+(Gpwrdelta);
31524 + if (t4 > 0xf)
31525 + t4 = 0xf;
31526 + }
31527 + else
31528 + {
31529 + if ((value&0xf) > Gpwrdelta)
31530 + t1 = (value&0xf)-(Gpwrdelta);
31531 + else
31532 + t1 = 0;
31533 + if (((value&0xf0)>>4) > Gpwrdelta)
31534 + t2 = ((value&0xf0)>>4)-(Gpwrdelta);
31535 + else
31536 + t2 = 0;
31537 + if (((value&0xf00)>>8) > Gpwrdelta)
31538 + t3 = ((value&0xf00)>>8)-(Gpwrdelta);
31539 + else
31540 + t3 = 0;
31541 + if (((value&0xf000)>>12) > Gpwrdelta)
31542 + t4 = ((value&0xf000)>>12)-(Gpwrdelta);
31543 + else
31544 + t4 = 0;
31545 + }
31546 + Gdata |= ((t1<<16) + (t2<<20) + (t3<<24) + (t4<<28));
31547 + data |= (value<<16);
31548 +
31549 + pAd->Tx20MPwrCfgABand[i] = pAd->Tx40MPwrCfgABand[i] = Adata;
31550 + pAd->Tx20MPwrCfgGBand[i] = pAd->Tx40MPwrCfgGBand[i] = Gdata;
31551 +
31552 + if (data != 0xffffffff)
31553 + RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i*4, data);
31554 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("20MHz BW, 2.4G band-%lx, Adata = %lx, Gdata = %lx \n", data, Adata, Gdata));
31555 + }
31556 +
31557 + //
31558 + // Check this block is valid for 40MHz in 2.4G. If invalid, use parameter for 20MHz in 2.4G
31559 + //
31560 + bValid = TRUE;
31561 + for (i=0; i<6; i++)
31562 + {
31563 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_40MHZ_2_4G + 2 + i*2, value);
31564 + if (((value & 0x00FF) == 0x00FF) || ((value & 0xFF00) == 0xFF00))
31565 + {
31566 + bValid = FALSE;
31567 + break;
31568 + }
31569 + }
31570 +
31571 + //
31572 + // Get Txpower per MCS for 40MHz in 2.4G.
31573 + //
31574 + if (bValid)
31575 + {
31576 + for (i=0; i<4; i++)
31577 + {
31578 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_40MHZ_2_4G + i*4, value);
31579 + if (bGpwrdeltaMinus == FALSE)
31580 + {
31581 + t1 = (value&0xf)+(Gpwrdelta);
31582 + if (t1 > 0xf)
31583 + t1 = 0xf;
31584 + t2 = ((value&0xf0)>>4)+(Gpwrdelta);
31585 + if (t2 > 0xf)
31586 + t2 = 0xf;
31587 + t3 = ((value&0xf00)>>8)+(Gpwrdelta);
31588 + if (t3 > 0xf)
31589 + t3 = 0xf;
31590 + t4 = ((value&0xf000)>>12)+(Gpwrdelta);
31591 + if (t4 > 0xf)
31592 + t4 = 0xf;
31593 + }
31594 + else
31595 + {
31596 + if ((value&0xf) > Gpwrdelta)
31597 + t1 = (value&0xf)-(Gpwrdelta);
31598 + else
31599 + t1 = 0;
31600 + if (((value&0xf0)>>4) > Gpwrdelta)
31601 + t2 = ((value&0xf0)>>4)-(Gpwrdelta);
31602 + else
31603 + t2 = 0;
31604 + if (((value&0xf00)>>8) > Gpwrdelta)
31605 + t3 = ((value&0xf00)>>8)-(Gpwrdelta);
31606 + else
31607 + t3 = 0;
31608 + if (((value&0xf000)>>12) > Gpwrdelta)
31609 + t4 = ((value&0xf000)>>12)-(Gpwrdelta);
31610 + else
31611 + t4 = 0;
31612 + }
31613 + Gdata = t1 + (t2<<4) + (t3<<8) + (t4<<12);
31614 +
31615 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_40MHZ_2_4G + i*4 + 2, value);
31616 + if (bGpwrdeltaMinus == FALSE)
31617 + {
31618 + t1 = (value&0xf)+(Gpwrdelta);
31619 + if (t1 > 0xf)
31620 + t1 = 0xf;
31621 + t2 = ((value&0xf0)>>4)+(Gpwrdelta);
31622 + if (t2 > 0xf)
31623 + t2 = 0xf;
31624 + t3 = ((value&0xf00)>>8)+(Gpwrdelta);
31625 + if (t3 > 0xf)
31626 + t3 = 0xf;
31627 + t4 = ((value&0xf000)>>12)+(Gpwrdelta);
31628 + if (t4 > 0xf)
31629 + t4 = 0xf;
31630 + }
31631 + else
31632 + {
31633 + if ((value&0xf) > Gpwrdelta)
31634 + t1 = (value&0xf)-(Gpwrdelta);
31635 + else
31636 + t1 = 0;
31637 + if (((value&0xf0)>>4) > Gpwrdelta)
31638 + t2 = ((value&0xf0)>>4)-(Gpwrdelta);
31639 + else
31640 + t2 = 0;
31641 + if (((value&0xf00)>>8) > Gpwrdelta)
31642 + t3 = ((value&0xf00)>>8)-(Gpwrdelta);
31643 + else
31644 + t3 = 0;
31645 + if (((value&0xf000)>>12) > Gpwrdelta)
31646 + t4 = ((value&0xf000)>>12)-(Gpwrdelta);
31647 + else
31648 + t4 = 0;
31649 + }
31650 + Gdata |= ((t1<<16) + (t2<<20) + (t3<<24) + (t4<<28));
31651 +
31652 + if (i == 0)
31653 + pAd->Tx40MPwrCfgGBand[i+1] = (pAd->Tx40MPwrCfgGBand[i+1] & 0x0000FFFF) | (Gdata & 0xFFFF0000);
31654 + else
31655 + pAd->Tx40MPwrCfgGBand[i+1] = Gdata;
31656 +
31657 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("40MHz BW, 2.4G band, Gdata = %lx \n", Gdata));
31658 + }
31659 + }
31660 +
31661 + //
31662 + // Check this block is valid for 20MHz in 5G. If invalid, use parameter for 20MHz in 2.4G
31663 + //
31664 + bValid = TRUE;
31665 + for (i=0; i<8; i++)
31666 + {
31667 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_20MHZ_5G + 2 + i*2, value);
31668 + if (((value & 0x00FF) == 0x00FF) || ((value & 0xFF00) == 0xFF00))
31669 + {
31670 + bValid = FALSE;
31671 + break;
31672 + }
31673 + }
31674 +
31675 + //
31676 + // Get Txpower per MCS for 20MHz in 5G.
31677 + //
31678 + if (bValid)
31679 + {
31680 + for (i=0; i<5; i++)
31681 + {
31682 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_20MHZ_5G + i*4, value);
31683 + if (bApwrdeltaMinus == FALSE)
31684 + {
31685 + t1 = (value&0xf)+(Apwrdelta);
31686 + if (t1 > 0xf)
31687 + t1 = 0xf;
31688 + t2 = ((value&0xf0)>>4)+(Apwrdelta);
31689 + if (t2 > 0xf)
31690 + t2 = 0xf;
31691 + t3 = ((value&0xf00)>>8)+(Apwrdelta);
31692 + if (t3 > 0xf)
31693 + t3 = 0xf;
31694 + t4 = ((value&0xf000)>>12)+(Apwrdelta);
31695 + if (t4 > 0xf)
31696 + t4 = 0xf;
31697 + }
31698 + else
31699 + {
31700 + if ((value&0xf) > Apwrdelta)
31701 + t1 = (value&0xf)-(Apwrdelta);
31702 + else
31703 + t1 = 0;
31704 + if (((value&0xf0)>>4) > Apwrdelta)
31705 + t2 = ((value&0xf0)>>4)-(Apwrdelta);
31706 + else
31707 + t2 = 0;
31708 + if (((value&0xf00)>>8) > Apwrdelta)
31709 + t3 = ((value&0xf00)>>8)-(Apwrdelta);
31710 + else
31711 + t3 = 0;
31712 + if (((value&0xf000)>>12) > Apwrdelta)
31713 + t4 = ((value&0xf000)>>12)-(Apwrdelta);
31714 + else
31715 + t4 = 0;
31716 + }
31717 + Adata = t1 + (t2<<4) + (t3<<8) + (t4<<12);
31718 +
31719 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_20MHZ_5G + i*4 + 2, value);
31720 + if (bApwrdeltaMinus == FALSE)
31721 + {
31722 + t1 = (value&0xf)+(Apwrdelta);
31723 + if (t1 > 0xf)
31724 + t1 = 0xf;
31725 + t2 = ((value&0xf0)>>4)+(Apwrdelta);
31726 + if (t2 > 0xf)
31727 + t2 = 0xf;
31728 + t3 = ((value&0xf00)>>8)+(Apwrdelta);
31729 + if (t3 > 0xf)
31730 + t3 = 0xf;
31731 + t4 = ((value&0xf000)>>12)+(Apwrdelta);
31732 + if (t4 > 0xf)
31733 + t4 = 0xf;
31734 + }
31735 + else
31736 + {
31737 + if ((value&0xf) > Apwrdelta)
31738 + t1 = (value&0xf)-(Apwrdelta);
31739 + else
31740 + t1 = 0;
31741 + if (((value&0xf0)>>4) > Apwrdelta)
31742 + t2 = ((value&0xf0)>>4)-(Apwrdelta);
31743 + else
31744 + t2 = 0;
31745 + if (((value&0xf00)>>8) > Apwrdelta)
31746 + t3 = ((value&0xf00)>>8)-(Apwrdelta);
31747 + else
31748 + t3 = 0;
31749 + if (((value&0xf000)>>12) > Apwrdelta)
31750 + t4 = ((value&0xf000)>>12)-(Apwrdelta);
31751 + else
31752 + t4 = 0;
31753 + }
31754 + Adata |= ((t1<<16) + (t2<<20) + (t3<<24) + (t4<<28));
31755 +
31756 + if (i == 0)
31757 + pAd->Tx20MPwrCfgABand[i] = (pAd->Tx20MPwrCfgABand[i] & 0x0000FFFF) | (Adata & 0xFFFF0000);
31758 + else
31759 + pAd->Tx20MPwrCfgABand[i] = Adata;
31760 +
31761 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("20MHz BW, 5GHz band, Adata = %lx \n", Adata));
31762 + }
31763 + }
31764 +
31765 + //
31766 + // Check this block is valid for 40MHz in 5G. If invalid, use parameter for 20MHz in 2.4G
31767 + //
31768 + bValid = TRUE;
31769 + for (i=0; i<6; i++)
31770 + {
31771 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_40MHZ_5G + 2 + i*2, value);
31772 + if (((value & 0x00FF) == 0x00FF) || ((value & 0xFF00) == 0xFF00))
31773 + {
31774 + bValid = FALSE;
31775 + break;
31776 + }
31777 + }
31778 +
31779 + //
31780 + // Get Txpower per MCS for 40MHz in 5G.
31781 + //
31782 + if (bValid)
31783 + {
31784 + for (i=0; i<4; i++)
31785 + {
31786 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_40MHZ_5G + i*4, value);
31787 + if (bApwrdeltaMinus == FALSE)
31788 + {
31789 + t1 = (value&0xf)+(Apwrdelta);
31790 + if (t1 > 0xf)
31791 + t1 = 0xf;
31792 + t2 = ((value&0xf0)>>4)+(Apwrdelta);
31793 + if (t2 > 0xf)
31794 + t2 = 0xf;
31795 + t3 = ((value&0xf00)>>8)+(Apwrdelta);
31796 + if (t3 > 0xf)
31797 + t3 = 0xf;
31798 + t4 = ((value&0xf000)>>12)+(Apwrdelta);
31799 + if (t4 > 0xf)
31800 + t4 = 0xf;
31801 + }
31802 + else
31803 + {
31804 + if ((value&0xf) > Apwrdelta)
31805 + t1 = (value&0xf)-(Apwrdelta);
31806 + else
31807 + t1 = 0;
31808 + if (((value&0xf0)>>4) > Apwrdelta)
31809 + t2 = ((value&0xf0)>>4)-(Apwrdelta);
31810 + else
31811 + t2 = 0;
31812 + if (((value&0xf00)>>8) > Apwrdelta)
31813 + t3 = ((value&0xf00)>>8)-(Apwrdelta);
31814 + else
31815 + t3 = 0;
31816 + if (((value&0xf000)>>12) > Apwrdelta)
31817 + t4 = ((value&0xf000)>>12)-(Apwrdelta);
31818 + else
31819 + t4 = 0;
31820 + }
31821 + Adata = t1 + (t2<<4) + (t3<<8) + (t4<<12);
31822 +
31823 + RT28xx_EEPROM_READ16(pAd, EEPROM_TXPOWER_BYRATE_40MHZ_5G + i*4 + 2, value);
31824 + if (bApwrdeltaMinus == FALSE)
31825 + {
31826 + t1 = (value&0xf)+(Apwrdelta);
31827 + if (t1 > 0xf)
31828 + t1 = 0xf;
31829 + t2 = ((value&0xf0)>>4)+(Apwrdelta);
31830 + if (t2 > 0xf)
31831 + t2 = 0xf;
31832 + t3 = ((value&0xf00)>>8)+(Apwrdelta);
31833 + if (t3 > 0xf)
31834 + t3 = 0xf;
31835 + t4 = ((value&0xf000)>>12)+(Apwrdelta);
31836 + if (t4 > 0xf)
31837 + t4 = 0xf;
31838 + }
31839 + else
31840 + {
31841 + if ((value&0xf) > Apwrdelta)
31842 + t1 = (value&0xf)-(Apwrdelta);
31843 + else
31844 + t1 = 0;
31845 + if (((value&0xf0)>>4) > Apwrdelta)
31846 + t2 = ((value&0xf0)>>4)-(Apwrdelta);
31847 + else
31848 + t2 = 0;
31849 + if (((value&0xf00)>>8) > Apwrdelta)
31850 + t3 = ((value&0xf00)>>8)-(Apwrdelta);
31851 + else
31852 + t3 = 0;
31853 + if (((value&0xf000)>>12) > Apwrdelta)
31854 + t4 = ((value&0xf000)>>12)-(Apwrdelta);
31855 + else
31856 + t4 = 0;
31857 + }
31858 + Adata |= ((t1<<16) + (t2<<20) + (t3<<24) + (t4<<28));
31859 +
31860 + if (i == 0)
31861 + pAd->Tx40MPwrCfgABand[i+1] = (pAd->Tx40MPwrCfgABand[i+1] & 0x0000FFFF) | (Adata & 0xFFFF0000);
31862 + else
31863 + pAd->Tx40MPwrCfgABand[i+1] = Adata;
31864 +
31865 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("40MHz BW, 5GHz band, Adata = %lx \n", Adata));
31866 + }
31867 + }
31868 +}
31869 +
31870 +
31871 +/*
31872 + ========================================================================
31873 +
31874 + Routine Description:
31875 + Read initial channel power parameters from EEPROM
31876 +
31877 + Arguments:
31878 + Adapter Pointer to our adapter
31879 +
31880 + Return Value:
31881 + None
31882 +
31883 + IRQL = PASSIVE_LEVEL
31884 +
31885 + Note:
31886 +
31887 + ========================================================================
31888 +*/
31889 +VOID RTMPReadChannelPwr(
31890 + IN PRTMP_ADAPTER pAd)
31891 +{
31892 + UCHAR i, choffset;
31893 + EEPROM_TX_PWR_STRUC Power;
31894 + EEPROM_TX_PWR_STRUC Power2;
31895 +
31896 + // Read Tx power value for all channels
31897 + // Value from 1 - 0x7f. Default value is 24.
31898 + // Power value : 2.4G 0x00 (0) ~ 0x1F (31)
31899 + // : 5.5G 0xF9 (-7) ~ 0x0F (15)
31900 +
31901 + // 0. 11b/g, ch1 - ch 14
31902 + for (i = 0; i < 7; i++)
31903 + {
31904 + RT28xx_EEPROM_READ16(pAd, EEPROM_G_TX_PWR_OFFSET + i * 2, Power.word);
31905 + RT28xx_EEPROM_READ16(pAd, EEPROM_G_TX2_PWR_OFFSET + i * 2, Power2.word);
31906 + pAd->TxPower[i * 2].Channel = i * 2 + 1;
31907 + pAd->TxPower[i * 2 + 1].Channel = i * 2 + 2;
31908 +
31909 + if ((Power.field.Byte0 > 31) || (Power.field.Byte0 < 0))
31910 + pAd->TxPower[i * 2].Power = DEFAULT_RF_TX_POWER;
31911 + else
31912 + pAd->TxPower[i * 2].Power = Power.field.Byte0;
31913 +
31914 + if ((Power.field.Byte1 > 31) || (Power.field.Byte1 < 0))
31915 + pAd->TxPower[i * 2 + 1].Power = DEFAULT_RF_TX_POWER;
31916 + else
31917 + pAd->TxPower[i * 2 + 1].Power = Power.field.Byte1;
31918 +
31919 + if ((Power2.field.Byte0 > 31) || (Power2.field.Byte0 < 0))
31920 + pAd->TxPower[i * 2].Power2 = DEFAULT_RF_TX_POWER;
31921 + else
31922 + pAd->TxPower[i * 2].Power2 = Power2.field.Byte0;
31923 +
31924 + if ((Power2.field.Byte1 > 31) || (Power2.field.Byte1 < 0))
31925 + pAd->TxPower[i * 2 + 1].Power2 = DEFAULT_RF_TX_POWER;
31926 + else
31927 + pAd->TxPower[i * 2 + 1].Power2 = Power2.field.Byte1;
31928 + }
31929 +
31930 + // 1. U-NII lower/middle band: 36, 38, 40; 44, 46, 48; 52, 54, 56; 60, 62, 64 (including central frequency in BW 40MHz)
31931 + // 1.1 Fill up channel
31932 + choffset = 14;
31933 + for (i = 0; i < 4; i++)
31934 + {
31935 + pAd->TxPower[3 * i + choffset + 0].Channel = 36 + i * 8 + 0;
31936 + pAd->TxPower[3 * i + choffset + 0].Power = DEFAULT_RF_TX_POWER;
31937 + pAd->TxPower[3 * i + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
31938 +
31939 + pAd->TxPower[3 * i + choffset + 1].Channel = 36 + i * 8 + 2;
31940 + pAd->TxPower[3 * i + choffset + 1].Power = DEFAULT_RF_TX_POWER;
31941 + pAd->TxPower[3 * i + choffset + 1].Power2 = DEFAULT_RF_TX_POWER;
31942 +
31943 + pAd->TxPower[3 * i + choffset + 2].Channel = 36 + i * 8 + 4;
31944 + pAd->TxPower[3 * i + choffset + 2].Power = DEFAULT_RF_TX_POWER;
31945 + pAd->TxPower[3 * i + choffset + 2].Power2 = DEFAULT_RF_TX_POWER;
31946 + }
31947 +
31948 + // 1.2 Fill up power
31949 + for (i = 0; i < 6; i++)
31950 + {
31951 + RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX_PWR_OFFSET + i * 2, Power.word);
31952 + RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX2_PWR_OFFSET + i * 2, Power2.word);
31953 +
31954 + if ((Power.field.Byte0 < 16) && (Power.field.Byte0 >= -7))
31955 + pAd->TxPower[i * 2 + choffset + 0].Power = Power.field.Byte0;
31956 +
31957 + if ((Power.field.Byte1 < 16) && (Power.field.Byte1 >= -7))
31958 + pAd->TxPower[i * 2 + choffset + 1].Power = Power.field.Byte1;
31959 +
31960 + if ((Power2.field.Byte0 < 16) && (Power2.field.Byte0 >= -7))
31961 + pAd->TxPower[i * 2 + choffset + 0].Power2 = Power2.field.Byte0;
31962 +
31963 + if ((Power2.field.Byte1 < 16) && (Power2.field.Byte1 >= -7))
31964 + pAd->TxPower[i * 2 + choffset + 1].Power2 = Power2.field.Byte1;
31965 + }
31966 +
31967 + // 2. HipperLAN 2 100, 102 ,104; 108, 110, 112; 116, 118, 120; 124, 126, 128; 132, 134, 136; 140 (including central frequency in BW 40MHz)
31968 + // 2.1 Fill up channel
31969 + choffset = 14 + 12;
31970 + for (i = 0; i < 5; i++)
31971 + {
31972 + pAd->TxPower[3 * i + choffset + 0].Channel = 100 + i * 8 + 0;
31973 + pAd->TxPower[3 * i + choffset + 0].Power = DEFAULT_RF_TX_POWER;
31974 + pAd->TxPower[3 * i + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
31975 +
31976 + pAd->TxPower[3 * i + choffset + 1].Channel = 100 + i * 8 + 2;
31977 + pAd->TxPower[3 * i + choffset + 1].Power = DEFAULT_RF_TX_POWER;
31978 + pAd->TxPower[3 * i + choffset + 1].Power2 = DEFAULT_RF_TX_POWER;
31979 +
31980 + pAd->TxPower[3 * i + choffset + 2].Channel = 100 + i * 8 + 4;
31981 + pAd->TxPower[3 * i + choffset + 2].Power = DEFAULT_RF_TX_POWER;
31982 + pAd->TxPower[3 * i + choffset + 2].Power2 = DEFAULT_RF_TX_POWER;
31983 + }
31984 + pAd->TxPower[3 * 5 + choffset + 0].Channel = 140;
31985 + pAd->TxPower[3 * 5 + choffset + 0].Power = DEFAULT_RF_TX_POWER;
31986 + pAd->TxPower[3 * 5 + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
31987 +
31988 + // 2.2 Fill up power
31989 + for (i = 0; i < 8; i++)
31990 + {
31991 + RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX_PWR_OFFSET + (choffset - 14) + i * 2, Power.word);
31992 + RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX2_PWR_OFFSET + (choffset - 14) + i * 2, Power2.word);
31993 +
31994 + if ((Power.field.Byte0 < 16) && (Power.field.Byte0 >= -7))
31995 + pAd->TxPower[i * 2 + choffset + 0].Power = Power.field.Byte0;
31996 +
31997 + if ((Power.field.Byte1 < 16) && (Power.field.Byte1 >= -7))
31998 + pAd->TxPower[i * 2 + choffset + 1].Power = Power.field.Byte1;
31999 +
32000 + if ((Power2.field.Byte0 < 16) && (Power2.field.Byte0 >= -7))
32001 + pAd->TxPower[i * 2 + choffset + 0].Power2 = Power2.field.Byte0;
32002 +
32003 + if ((Power2.field.Byte1 < 16) && (Power2.field.Byte1 >= -7))
32004 + pAd->TxPower[i * 2 + choffset + 1].Power2 = Power2.field.Byte1;
32005 + }
32006 +
32007 + // 3. U-NII upper band: 149, 151, 153; 157, 159, 161; 165 (including central frequency in BW 40MHz)
32008 + // 3.1 Fill up channel
32009 + choffset = 14 + 12 + 16;
32010 + for (i = 0; i < 2; i++)
32011 + {
32012 + pAd->TxPower[3 * i + choffset + 0].Channel = 149 + i * 8 + 0;
32013 + pAd->TxPower[3 * i + choffset + 0].Power = DEFAULT_RF_TX_POWER;
32014 + pAd->TxPower[3 * i + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
32015 +
32016 + pAd->TxPower[3 * i + choffset + 1].Channel = 149 + i * 8 + 2;
32017 + pAd->TxPower[3 * i + choffset + 1].Power = DEFAULT_RF_TX_POWER;
32018 + pAd->TxPower[3 * i + choffset + 1].Power2 = DEFAULT_RF_TX_POWER;
32019 +
32020 + pAd->TxPower[3 * i + choffset + 2].Channel = 149 + i * 8 + 4;
32021 + pAd->TxPower[3 * i + choffset + 2].Power = DEFAULT_RF_TX_POWER;
32022 + pAd->TxPower[3 * i + choffset + 2].Power2 = DEFAULT_RF_TX_POWER;
32023 + }
32024 + pAd->TxPower[3 * 2 + choffset + 0].Channel = 165;
32025 + pAd->TxPower[3 * 2 + choffset + 0].Power = DEFAULT_RF_TX_POWER;
32026 + pAd->TxPower[3 * 2 + choffset + 0].Power2 = DEFAULT_RF_TX_POWER;
32027 +
32028 + // 3.2 Fill up power
32029 + for (i = 0; i < 4; i++)
32030 + {
32031 + RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX_PWR_OFFSET + (choffset - 14) + i * 2, Power.word);
32032 + RT28xx_EEPROM_READ16(pAd, EEPROM_A_TX2_PWR_OFFSET + (choffset - 14) + i * 2, Power2.word);
32033 +
32034 + if ((Power.field.Byte0 < 16) && (Power.field.Byte0 >= -7))
32035 + pAd->TxPower[i * 2 + choffset + 0].Power = Power.field.Byte0;
32036 +
32037 + if ((Power.field.Byte1 < 16) && (Power.field.Byte1 >= -7))
32038 + pAd->TxPower[i * 2 + choffset + 1].Power = Power.field.Byte1;
32039 +
32040 + if ((Power2.field.Byte0 < 16) && (Power2.field.Byte0 >= -7))
32041 + pAd->TxPower[i * 2 + choffset + 0].Power2 = Power2.field.Byte0;
32042 +
32043 + if ((Power2.field.Byte1 < 16) && (Power2.field.Byte1 >= -7))
32044 + pAd->TxPower[i * 2 + choffset + 1].Power2 = Power2.field.Byte1;
32045 + }
32046 +
32047 + // 4. Print and Debug
32048 + choffset = 14 + 12 + 16 + 7;
32049 +
32050 +
32051 +#if 0
32052 + // Init the 802.11j channel number for TX channel power
32053 + // 0. 20MHz
32054 + for (i = 0; i < 3; i++)
32055 + {
32056 + pAd->TxPower11J[i].Channel = 8 + i * 4;
32057 + pAd->TxPower11J[i].BW = BW_20;
32058 + }
32059 +
32060 + for (i = 0; i < 4; i++)
32061 + {
32062 + pAd->TxPower11J[i + 3].Channel = 34 + i * 4;
32063 + pAd->TxPower11J[i + 3].BW = BW_20;
32064 + }
32065 +
32066 + for (i = 0; i < 4; i++)
32067 + {
32068 + pAd->TxPower11J[i + 7].Channel = 184 + i * 4;
32069 + pAd->TxPower11J[i + 7].BW = BW_20;
32070 + }
32071 +
32072 + // 0. 10MHz
32073 + for (i = 0; i < 2; i++)
32074 + {
32075 + pAd->TxPower11J[i + 11].Channel = 7 + i;
32076 + pAd->TxPower11J[i + 11].BW = BW_10;
32077 + }
32078 + pAd->TxPower11J[13].Channel = 11;
32079 + pAd->TxPower11J[13].BW = BW_10;
32080 +
32081 + for (i = 0; i < 3; i++)
32082 + {
32083 + pAd->TxPower11J[i + 14].Channel = 183 + i;
32084 + pAd->TxPower11J[i + 14].BW= BW_10;
32085 + }
32086 +
32087 + for (i = 0; i < 3; i++)
32088 + {
32089 + pAd->TxPower11J[i + 17].Channel = 187 + i;
32090 + pAd->TxPower11J[i + 17].BW = BW_10;
32091 + }
32092 + for (i = 0; i < 10; i++)
32093 + {
32094 + Power.word = RTMP_EEPROM_READ16(pAd, EEPROM_Japan_TX_PWR_OFFSET + i * 2);
32095 + Power2.word = RTMP_EEPROM_READ16(pAd, EEPROM_Japan_TX2_PWR_OFFSET + i * 2);
32096 +
32097 + if ((Power.field.Byte0 < 36) && (Power.field.Byte0 > -6))
32098 + pAd->TxPower11J[i * 2].Power = Power.field.Byte0;
32099 +
32100 + if ((Power.field.Byte1 < 36) && (Power.field.Byte1 > -6))
32101 + pAd->TxPower11J[i * 2 + 1].Power = Power.field.Byte1;
32102 +
32103 + if ((Power2.field.Byte0 < 36) && (Power2.field.Byte0 > -6))
32104 + pAd->TxPower11J[i * 2].Power2 = Power2.field.Byte0;
32105 +
32106 + if ((Power2.field.Byte1 < 36) && (Power2.field.Byte1 > -6))
32107 + pAd->TxPower11J[i * 2 + 1].Power2 = Power2.field.Byte1;
32108 + }
32109 +#endif
32110 +}
32111 +
32112 +/*
32113 + ========================================================================
32114 +
32115 + Routine Description:
32116 + Read the following from the registry
32117 + 1. All the parameters
32118 + 2. NetworkAddres
32119 +
32120 + Arguments:
32121 + Adapter Pointer to our adapter
32122 + WrapperConfigurationContext For use by NdisOpenConfiguration
32123 +
32124 + Return Value:
32125 + NDIS_STATUS_SUCCESS
32126 + NDIS_STATUS_FAILURE
32127 + NDIS_STATUS_RESOURCES
32128 +
32129 + IRQL = PASSIVE_LEVEL
32130 +
32131 + Note:
32132 +
32133 + ========================================================================
32134 +*/
32135 +NDIS_STATUS NICReadRegParameters(
32136 + IN PRTMP_ADAPTER pAd,
32137 + IN NDIS_HANDLE WrapperConfigurationContext
32138 + )
32139 +{
32140 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
32141 + DBGPRINT_S(Status, ("<-- NICReadRegParameters, Status=%x\n", Status));
32142 + return Status;
32143 +}
32144 +
32145 +
32146 +
32147 +
32148 +/*
32149 + ========================================================================
32150 +
32151 + Routine Description:
32152 + Read initial parameters from EEPROM
32153 +
32154 + Arguments:
32155 + Adapter Pointer to our adapter
32156 +
32157 + Return Value:
32158 + None
32159 +
32160 + IRQL = PASSIVE_LEVEL
32161 +
32162 + Note:
32163 +
32164 + ========================================================================
32165 +*/
32166 +VOID NICReadEEPROMParameters(
32167 + IN PRTMP_ADAPTER pAd,
32168 + IN PUCHAR mac_addr)
32169 +{
32170 + UINT32 data = 0;
32171 + USHORT i, value, value2;
32172 + UCHAR TmpPhy;
32173 + EEPROM_TX_PWR_STRUC Power;
32174 + EEPROM_VERSION_STRUC Version;
32175 + EEPROM_ANTENNA_STRUC Antenna;
32176 + EEPROM_NIC_CONFIG2_STRUC NicConfig2;
32177 +
32178 + DBGPRINT(RT_DEBUG_TRACE, ("--> NICReadEEPROMParameters\n"));
32179 +
32180 + // Init EEPROM Address Number, before access EEPROM; if 93c46, EEPROMAddressNum=6, else if 93c66, EEPROMAddressNum=8
32181 + RTMP_IO_READ32(pAd, E2PROM_CSR, &data);
32182 + DBGPRINT(RT_DEBUG_TRACE, ("--> E2PROM_CSR = 0x%x\n", data));
32183 +
32184 + if((data & 0x30) == 0)
32185 + pAd->EEPROMAddressNum = 6; // 93C46
32186 + else if((data & 0x30) == 0x10)
32187 + pAd->EEPROMAddressNum = 8; // 93C66
32188 + else
32189 + pAd->EEPROMAddressNum = 8; // 93C86
32190 + DBGPRINT(RT_DEBUG_TRACE, ("--> EEPROMAddressNum = %d\n", pAd->EEPROMAddressNum ));
32191 +
32192 + // RT2860 MAC no longer auto load MAC address from E2PROM. Driver has to intialize
32193 + // MAC address registers according to E2PROM setting
32194 + if (mac_addr == NULL ||
32195 + strlen(mac_addr) != 17 ||
32196 + mac_addr[2] != ':' || mac_addr[5] != ':' || mac_addr[8] != ':' ||
32197 + mac_addr[11] != ':' || mac_addr[14] != ':')
32198 + {
32199 + USHORT Addr01,Addr23,Addr45 ;
32200 +
32201 + RT28xx_EEPROM_READ16(pAd, 0x04, Addr01);
32202 + RT28xx_EEPROM_READ16(pAd, 0x06, Addr23);
32203 + RT28xx_EEPROM_READ16(pAd, 0x08, Addr45);
32204 +
32205 + pAd->PermanentAddress[0] = (UCHAR)(Addr01 & 0xff);
32206 + pAd->PermanentAddress[1] = (UCHAR)(Addr01 >> 8);
32207 + pAd->PermanentAddress[2] = (UCHAR)(Addr23 & 0xff);
32208 + pAd->PermanentAddress[3] = (UCHAR)(Addr23 >> 8);
32209 + pAd->PermanentAddress[4] = (UCHAR)(Addr45 & 0xff);
32210 + pAd->PermanentAddress[5] = (UCHAR)(Addr45 >> 8);
32211 +
32212 + DBGPRINT(RT_DEBUG_TRACE, ("Initialize MAC Address from E2PROM \n"));
32213 + }
32214 + else
32215 + {
32216 + INT j;
32217 + PUCHAR macptr;
32218 +
32219 + macptr = mac_addr;
32220 +
32221 + for (j=0; j<MAC_ADDR_LEN; j++)
32222 + {
32223 + AtoH(macptr, &pAd->PermanentAddress[j], 1);
32224 + macptr=macptr+3;
32225 + }
32226 +
32227 + DBGPRINT(RT_DEBUG_TRACE, ("Initialize MAC Address from module parameter \n"));
32228 + }
32229 +
32230 +
32231 + {
32232 + //more conveninet to test mbssid, so ap's bssid &0xf1
32233 + if (pAd->PermanentAddress[0] == 0xff)
32234 + pAd->PermanentAddress[0] = RandomByte(pAd)&0xf8;
32235 +
32236 + //if (pAd->PermanentAddress[5] == 0xff)
32237 + // pAd->PermanentAddress[5] = RandomByte(pAd)&0xf8;
32238 +
32239 + DBGPRINT_RAW(RT_DEBUG_TRACE,("E2PROM MAC: =%02x:%02x:%02x:%02x:%02x:%02x\n",
32240 + pAd->PermanentAddress[0], pAd->PermanentAddress[1],
32241 + pAd->PermanentAddress[2], pAd->PermanentAddress[3],
32242 + pAd->PermanentAddress[4], pAd->PermanentAddress[5]));
32243 + if (pAd->bLocalAdminMAC == FALSE)
32244 + {
32245 + MAC_DW0_STRUC csr2;
32246 + MAC_DW1_STRUC csr3;
32247 + COPY_MAC_ADDR(pAd->CurrentAddress, pAd->PermanentAddress);
32248 + csr2.field.Byte0 = pAd->CurrentAddress[0];
32249 + csr2.field.Byte1 = pAd->CurrentAddress[1];
32250 + csr2.field.Byte2 = pAd->CurrentAddress[2];
32251 + csr2.field.Byte3 = pAd->CurrentAddress[3];
32252 + RTMP_IO_WRITE32(pAd, MAC_ADDR_DW0, csr2.word);
32253 + csr3.word = 0;
32254 + csr3.field.Byte4 = pAd->CurrentAddress[4];
32255 + csr3.field.Byte5 = pAd->CurrentAddress[5];
32256 + csr3.field.U2MeMask = 0xff;
32257 + RTMP_IO_WRITE32(pAd, MAC_ADDR_DW1, csr3.word);
32258 + DBGPRINT_RAW(RT_DEBUG_TRACE,("E2PROM MAC: =%02x:%02x:%02x:%02x:%02x:%02x\n",
32259 + pAd->PermanentAddress[0], pAd->PermanentAddress[1],
32260 + pAd->PermanentAddress[2], pAd->PermanentAddress[3],
32261 + pAd->PermanentAddress[4], pAd->PermanentAddress[5]));
32262 + }
32263 + }
32264 +
32265 + // if not return early. cause fail at emulation.
32266 + // Init the channel number for TX channel power
32267 + RTMPReadChannelPwr(pAd);
32268 +
32269 + // if E2PROM version mismatch with driver's expectation, then skip
32270 + // all subsequent E2RPOM retieval and set a system error bit to notify GUI
32271 + RT28xx_EEPROM_READ16(pAd, EEPROM_VERSION_OFFSET, Version.word);
32272 + pAd->EepromVersion = Version.field.Version + Version.field.FaeReleaseNumber * 256;
32273 + DBGPRINT(RT_DEBUG_TRACE, ("E2PROM: Version = %d, FAE release #%d\n", Version.field.Version, Version.field.FaeReleaseNumber));
32274 +
32275 + if (Version.field.Version > VALID_EEPROM_VERSION)
32276 + {
32277 + DBGPRINT_ERR(("E2PROM: WRONG VERSION 0x%x, should be %d\n",Version.field.Version, VALID_EEPROM_VERSION));
32278 + /*pAd->SystemErrorBitmap |= 0x00000001;
32279 +
32280 + // hard-code default value when no proper E2PROM installed
32281 + pAd->bAutoTxAgcA = FALSE;
32282 + pAd->bAutoTxAgcG = FALSE;
32283 +
32284 + // Default the channel power
32285 + for (i = 0; i < MAX_NUM_OF_CHANNELS; i++)
32286 + pAd->TxPower[i].Power = DEFAULT_RF_TX_POWER;
32287 +
32288 + // Default the channel power
32289 + for (i = 0; i < MAX_NUM_OF_11JCHANNELS; i++)
32290 + pAd->TxPower11J[i].Power = DEFAULT_RF_TX_POWER;
32291 +
32292 + for(i = 0; i < NUM_EEPROM_BBP_PARMS; i++)
32293 + pAd->EEPROMDefaultValue[i] = 0xffff;
32294 + return; */
32295 + }
32296 +
32297 + // Read BBP default value from EEPROM and store to array(EEPROMDefaultValue) in pAd
32298 + RT28xx_EEPROM_READ16(pAd, EEPROM_NIC1_OFFSET, value);
32299 + pAd->EEPROMDefaultValue[0] = value;
32300 +
32301 + RT28xx_EEPROM_READ16(pAd, EEPROM_NIC2_OFFSET, value);
32302 + pAd->EEPROMDefaultValue[1] = value;
32303 +
32304 + RT28xx_EEPROM_READ16(pAd, 0x38, value); // Country Region
32305 + pAd->EEPROMDefaultValue[2] = value;
32306 +
32307 + for(i = 0; i < 8; i++)
32308 + {
32309 + RT28xx_EEPROM_READ16(pAd, EEPROM_BBP_BASE_OFFSET + i*2, value);
32310 + pAd->EEPROMDefaultValue[i+3] = value;
32311 + }
32312 +
32313 + // We have to parse NIC configuration 0 at here.
32314 + // If TSSI did not have preloaded value, it should reset the TxAutoAgc to false
32315 + // Therefore, we have to read TxAutoAgc control beforehand.
32316 + // Read Tx AGC control bit
32317 + Antenna.word = pAd->EEPROMDefaultValue[0];
32318 + if (Antenna.word == 0xFFFF)
32319 + {
32320 + Antenna.word = 0;
32321 + Antenna.field.RfIcType = RFIC_2820;
32322 + Antenna.field.TxPath = 1;
32323 + Antenna.field.RxPath = 2;
32324 + DBGPRINT(RT_DEBUG_WARN, ("E2PROM error, hard code as 0x%04x\n", Antenna.word));
32325 + }
32326 +
32327 + // Choose the desired Tx&Rx stream.
32328 + if ((pAd->CommonCfg.TxStream == 0) || (pAd->CommonCfg.TxStream > Antenna.field.TxPath))
32329 + pAd->CommonCfg.TxStream = Antenna.field.TxPath;
32330 +
32331 + if ((pAd->CommonCfg.RxStream == 0) || (pAd->CommonCfg.RxStream > Antenna.field.RxPath))
32332 + {
32333 + pAd->CommonCfg.RxStream = Antenna.field.RxPath;
32334 +
32335 + if ((pAd->MACVersion < RALINK_2883_VERSION) &&
32336 + (pAd->CommonCfg.RxStream > 2))
32337 + {
32338 + // only 2 Rx streams for RT2860 series
32339 + pAd->CommonCfg.RxStream = 2;
32340 + }
32341 + }
32342 +
32343 + // 3*3
32344 + // read value from EEPROM and set them to CSR174 ~ 177 in chain0 ~ chain2
32345 + // yet implement
32346 + for(i=0; i<3; i++)
32347 + {
32348 + }
32349 +
32350 + NicConfig2.word = pAd->EEPROMDefaultValue[1];
32351 +
32352 +
32353 +
32354 +#ifdef CONFIG_STA_SUPPORT
32355 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
32356 + {
32357 + NicConfig2.word = 0;
32358 + if ((NicConfig2.word & 0x00ff) == 0xff)
32359 + {
32360 + NicConfig2.word &= 0xff00;
32361 + }
32362 +
32363 + if ((NicConfig2.word >> 8) == 0xff)
32364 + {
32365 + NicConfig2.word &= 0x00ff;
32366 + }
32367 + }
32368 +#endif // CONFIG_STA_SUPPORT //
32369 +
32370 + if (NicConfig2.field.DynamicTxAgcControl == 1)
32371 + pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = TRUE;
32372 + else
32373 + pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = FALSE;
32374 +
32375 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("NICReadEEPROMParameters: RxPath = %d, TxPath = %d\n", Antenna.field.RxPath, Antenna.field.TxPath));
32376 +
32377 + // Save the antenna for future use
32378 + pAd->Antenna.word = Antenna.word;
32379 +
32380 + //
32381 + // Reset PhyMode if we don't support 802.11a
32382 + // Only RFIC_2850 & RFIC_2750 support 802.11a
32383 + //
32384 + if ((Antenna.field.RfIcType != RFIC_2850) && (Antenna.field.RfIcType != RFIC_2750))
32385 + {
32386 + if ((pAd->CommonCfg.PhyMode == PHY_11ABG_MIXED) ||
32387 + (pAd->CommonCfg.PhyMode == PHY_11A))
32388 + pAd->CommonCfg.PhyMode = PHY_11BG_MIXED;
32389 +#ifdef DOT11_N_SUPPORT
32390 + else if ((pAd->CommonCfg.PhyMode == PHY_11ABGN_MIXED) ||
32391 + (pAd->CommonCfg.PhyMode == PHY_11AN_MIXED) ||
32392 + (pAd->CommonCfg.PhyMode == PHY_11AGN_MIXED) ||
32393 + (pAd->CommonCfg.PhyMode == PHY_11N_5G))
32394 + pAd->CommonCfg.PhyMode = PHY_11BGN_MIXED;
32395 +#endif // DOT11_N_SUPPORT //
32396 + }
32397 +
32398 + // Read TSSI reference and TSSI boundary for temperature compensation. This is ugly
32399 + // 0. 11b/g
32400 + {
32401 + /* these are tempature reference value (0x00 ~ 0xFE)
32402 + ex: 0x00 0x15 0x25 0x45 0x88 0xA0 0xB5 0xD0 0xF0
32403 + TssiPlusBoundaryG [4] [3] [2] [1] [0] (smaller) +
32404 + TssiMinusBoundaryG[0] [1] [2] [3] [4] (larger) */
32405 + RT28xx_EEPROM_READ16(pAd, 0x6E, Power.word);
32406 + pAd->TssiMinusBoundaryG[4] = Power.field.Byte0;
32407 + pAd->TssiMinusBoundaryG[3] = Power.field.Byte1;
32408 + RT28xx_EEPROM_READ16(pAd, 0x70, Power.word);
32409 + pAd->TssiMinusBoundaryG[2] = Power.field.Byte0;
32410 + pAd->TssiMinusBoundaryG[1] = Power.field.Byte1;
32411 + RT28xx_EEPROM_READ16(pAd, 0x72, Power.word);
32412 + pAd->TssiRefG = Power.field.Byte0; /* reference value [0] */
32413 + pAd->TssiPlusBoundaryG[1] = Power.field.Byte1;
32414 + RT28xx_EEPROM_READ16(pAd, 0x74, Power.word);
32415 + pAd->TssiPlusBoundaryG[2] = Power.field.Byte0;
32416 + pAd->TssiPlusBoundaryG[3] = Power.field.Byte1;
32417 + RT28xx_EEPROM_READ16(pAd, 0x76, Power.word);
32418 + pAd->TssiPlusBoundaryG[4] = Power.field.Byte0;
32419 + pAd->TxAgcStepG = Power.field.Byte1;
32420 + pAd->TxAgcCompensateG = 0;
32421 + pAd->TssiMinusBoundaryG[0] = pAd->TssiRefG;
32422 + pAd->TssiPlusBoundaryG[0] = pAd->TssiRefG;
32423 +
32424 + // Disable TxAgc if the based value is not right
32425 + if (pAd->TssiRefG == 0xff)
32426 + pAd->bAutoTxAgcG = FALSE;
32427 +
32428 + DBGPRINT(RT_DEBUG_TRACE,("E2PROM: G Tssi[-4 .. +4] = %d %d %d %d - %d -%d %d %d %d, step=%d, tuning=%d\n",
32429 + pAd->TssiMinusBoundaryG[4], pAd->TssiMinusBoundaryG[3], pAd->TssiMinusBoundaryG[2], pAd->TssiMinusBoundaryG[1],
32430 + pAd->TssiRefG,
32431 + pAd->TssiPlusBoundaryG[1], pAd->TssiPlusBoundaryG[2], pAd->TssiPlusBoundaryG[3], pAd->TssiPlusBoundaryG[4],
32432 + pAd->TxAgcStepG, pAd->bAutoTxAgcG));
32433 + }
32434 + // 1. 11a
32435 + {
32436 + RT28xx_EEPROM_READ16(pAd, 0xD4, Power.word);
32437 + pAd->TssiMinusBoundaryA[4] = Power.field.Byte0;
32438 + pAd->TssiMinusBoundaryA[3] = Power.field.Byte1;
32439 + RT28xx_EEPROM_READ16(pAd, 0xD6, Power.word);
32440 + pAd->TssiMinusBoundaryA[2] = Power.field.Byte0;
32441 + pAd->TssiMinusBoundaryA[1] = Power.field.Byte1;
32442 + RT28xx_EEPROM_READ16(pAd, 0xD8, Power.word);
32443 + pAd->TssiRefA = Power.field.Byte0;
32444 + pAd->TssiPlusBoundaryA[1] = Power.field.Byte1;
32445 + RT28xx_EEPROM_READ16(pAd, 0xDA, Power.word);
32446 + pAd->TssiPlusBoundaryA[2] = Power.field.Byte0;
32447 + pAd->TssiPlusBoundaryA[3] = Power.field.Byte1;
32448 + RT28xx_EEPROM_READ16(pAd, 0xDC, Power.word);
32449 + pAd->TssiPlusBoundaryA[4] = Power.field.Byte0;
32450 + pAd->TxAgcStepA = Power.field.Byte1;
32451 + pAd->TxAgcCompensateA = 0;
32452 + pAd->TssiMinusBoundaryA[0] = pAd->TssiRefA;
32453 + pAd->TssiPlusBoundaryA[0] = pAd->TssiRefA;
32454 +
32455 + // Disable TxAgc if the based value is not right
32456 + if (pAd->TssiRefA == 0xff)
32457 + pAd->bAutoTxAgcA = FALSE;
32458 +
32459 + DBGPRINT(RT_DEBUG_TRACE,("E2PROM: A Tssi[-4 .. +4] = %d %d %d %d - %d -%d %d %d %d, step=%d, tuning=%d\n",
32460 + pAd->TssiMinusBoundaryA[4], pAd->TssiMinusBoundaryA[3], pAd->TssiMinusBoundaryA[2], pAd->TssiMinusBoundaryA[1],
32461 + pAd->TssiRefA,
32462 + pAd->TssiPlusBoundaryA[1], pAd->TssiPlusBoundaryA[2], pAd->TssiPlusBoundaryA[3], pAd->TssiPlusBoundaryA[4],
32463 + pAd->TxAgcStepA, pAd->bAutoTxAgcA));
32464 + }
32465 + pAd->BbpRssiToDbmDelta = 0x0;
32466 +
32467 + // Read frequency offset setting for RF
32468 + RT28xx_EEPROM_READ16(pAd, EEPROM_FREQ_OFFSET, value);
32469 + if ((value & 0x00FF) != 0x00FF)
32470 + pAd->RfFreqOffset = (ULONG) (value & 0x00FF);
32471 + else
32472 + pAd->RfFreqOffset = 0;
32473 + DBGPRINT(RT_DEBUG_TRACE, ("E2PROM: RF FreqOffset=0x%lx \n", pAd->RfFreqOffset));
32474 +
32475 + //CountryRegion byte offset (38h)
32476 + value = pAd->EEPROMDefaultValue[2] >> 8; // 2.4G band
32477 + value2 = pAd->EEPROMDefaultValue[2] & 0x00FF; // 5G band
32478 +
32479 + if ((value <= REGION_MAXIMUM_BG_BAND) && (value2 <= REGION_MAXIMUM_A_BAND))
32480 + {
32481 + pAd->CommonCfg.CountryRegion = ((UCHAR) value) | 0x80;
32482 + pAd->CommonCfg.CountryRegionForABand = ((UCHAR) value2) | 0x80;
32483 + TmpPhy = pAd->CommonCfg.PhyMode;
32484 + pAd->CommonCfg.PhyMode = 0xff;
32485 + RTMPSetPhyMode(pAd, TmpPhy);
32486 +#ifdef DOT11_N_SUPPORT
32487 + SetCommonHT(pAd);
32488 +#endif // DOT11_N_SUPPORT //
32489 + }
32490 +
32491 + //
32492 + // Get RSSI Offset on EEPROM 0x9Ah & 0x9Ch.
32493 + // The valid value are (-10 ~ 10)
32494 + //
32495 + RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_BG_OFFSET, value);
32496 + pAd->BGRssiOffset0 = value & 0x00ff;
32497 + pAd->BGRssiOffset1 = (value >> 8);
32498 + RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_BG_OFFSET+2, value);
32499 + pAd->BGRssiOffset2 = value & 0x00ff;
32500 + pAd->ALNAGain1 = (value >> 8);
32501 + RT28xx_EEPROM_READ16(pAd, EEPROM_LNA_OFFSET, value);
32502 + pAd->BLNAGain = value & 0x00ff;
32503 + pAd->ALNAGain0 = (value >> 8);
32504 +
32505 + // Validate 11b/g RSSI_0 offset.
32506 + if ((pAd->BGRssiOffset0 < -10) || (pAd->BGRssiOffset0 > 10))
32507 + pAd->BGRssiOffset0 = 0;
32508 +
32509 + // Validate 11b/g RSSI_1 offset.
32510 + if ((pAd->BGRssiOffset1 < -10) || (pAd->BGRssiOffset1 > 10))
32511 + pAd->BGRssiOffset1 = 0;
32512 +
32513 + // Validate 11b/g RSSI_2 offset.
32514 + if ((pAd->BGRssiOffset2 < -10) || (pAd->BGRssiOffset2 > 10))
32515 + pAd->BGRssiOffset2 = 0;
32516 +
32517 + RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_A_OFFSET, value);
32518 + pAd->ARssiOffset0 = value & 0x00ff;
32519 + pAd->ARssiOffset1 = (value >> 8);
32520 + RT28xx_EEPROM_READ16(pAd, (EEPROM_RSSI_A_OFFSET+2), value);
32521 + pAd->ARssiOffset2 = value & 0x00ff;
32522 + pAd->ALNAGain2 = (value >> 8);
32523 +
32524 + if (((UCHAR)pAd->ALNAGain1 == 0xFF) || (pAd->ALNAGain1 == 0x00))
32525 + pAd->ALNAGain1 = pAd->ALNAGain0;
32526 + if (((UCHAR)pAd->ALNAGain2 == 0xFF) || (pAd->ALNAGain2 == 0x00))
32527 + pAd->ALNAGain2 = pAd->ALNAGain0;
32528 +
32529 + // Validate 11a RSSI_0 offset.
32530 + if ((pAd->ARssiOffset0 < -10) || (pAd->ARssiOffset0 > 10))
32531 + pAd->ARssiOffset0 = 0;
32532 +
32533 + // Validate 11a RSSI_1 offset.
32534 + if ((pAd->ARssiOffset1 < -10) || (pAd->ARssiOffset1 > 10))
32535 + pAd->ARssiOffset1 = 0;
32536 +
32537 + //Validate 11a RSSI_2 offset.
32538 + if ((pAd->ARssiOffset2 < -10) || (pAd->ARssiOffset2 > 10))
32539 + pAd->ARssiOffset2 = 0;
32540 +
32541 + //
32542 + // Get LED Setting.
32543 + //
32544 + RT28xx_EEPROM_READ16(pAd, 0x3a, value);
32545 + pAd->LedCntl.word = (value&0xff00) >> 8;
32546 + RT28xx_EEPROM_READ16(pAd, EEPROM_LED1_OFFSET, value);
32547 + pAd->Led1 = value;
32548 + RT28xx_EEPROM_READ16(pAd, EEPROM_LED2_OFFSET, value);
32549 + pAd->Led2 = value;
32550 + RT28xx_EEPROM_READ16(pAd, EEPROM_LED3_OFFSET, value);
32551 + pAd->Led3 = value;
32552 +
32553 + RTMPReadTxPwrPerRate(pAd);
32554 +
32555 +#ifdef SINGLE_SKU
32556 + //pAd->CommonCfg.DefineMaxTxPwr = RTMP_EEPROM_READ16(pAd, EEPROM_DEFINE_MAX_TXPWR);
32557 + RT28xx_EEPROM_READ16(pAd, EEPROM_DEFINE_MAX_TXPWR, pAd->CommonCfg.DefineMaxTxPwr);
32558 +#endif // SINGLE_SKU //
32559 +
32560 + DBGPRINT(RT_DEBUG_TRACE, ("<-- NICReadEEPROMParameters\n"));
32561 +}
32562 +
32563 +/*
32564 + ========================================================================
32565 +
32566 + Routine Description:
32567 + Set default value from EEPROM
32568 +
32569 + Arguments:
32570 + Adapter Pointer to our adapter
32571 +
32572 + Return Value:
32573 + None
32574 +
32575 + IRQL = PASSIVE_LEVEL
32576 +
32577 + Note:
32578 +
32579 + ========================================================================
32580 +*/
32581 +VOID NICInitAsicFromEEPROM(
32582 + IN PRTMP_ADAPTER pAd)
32583 +{
32584 +#ifdef CONFIG_STA_SUPPORT
32585 + UINT32 data = 0;
32586 + UCHAR BBPR1 = 0;
32587 +#endif // CONFIG_STA_SUPPORT //
32588 + USHORT i;
32589 + EEPROM_ANTENNA_STRUC Antenna;
32590 + EEPROM_NIC_CONFIG2_STRUC NicConfig2;
32591 + UCHAR BBPR3 = 0;
32592 +
32593 + DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitAsicFromEEPROM\n"));
32594 + for(i = 3; i < NUM_EEPROM_BBP_PARMS; i++)
32595 + {
32596 + UCHAR BbpRegIdx, BbpValue;
32597 +
32598 + if ((pAd->EEPROMDefaultValue[i] != 0xFFFF) && (pAd->EEPROMDefaultValue[i] != 0))
32599 + {
32600 + BbpRegIdx = (UCHAR)(pAd->EEPROMDefaultValue[i] >> 8);
32601 + BbpValue = (UCHAR)(pAd->EEPROMDefaultValue[i] & 0xff);
32602 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BbpRegIdx, BbpValue);
32603 + }
32604 + }
32605 +
32606 + Antenna.word = pAd->Antenna.word;
32607 + pAd->Mlme.RealRxPath = (UCHAR) Antenna.field.RxPath;
32608 + pAd->RfIcType = (UCHAR) Antenna.field.RfIcType;
32609 +
32610 + NicConfig2.word = pAd->EEPROMDefaultValue[1];
32611 +
32612 +
32613 + // Save the antenna for future use
32614 + pAd->NicConfig2.word = NicConfig2.word;
32615 +
32616 + //
32617 + // Send LED Setting to MCU.
32618 + //
32619 + if (pAd->LedCntl.word == 0xFF)
32620 + {
32621 + pAd->LedCntl.word = 0x01;
32622 + pAd->Led1 = 0x5555;
32623 + pAd->Led2 = 0x2221;
32624 +
32625 +#ifdef RT2860
32626 + pAd->Led3 = 0xA9F8;
32627 +#endif // RT2860 //
32628 + }
32629 +
32630 + AsicSendCommandToMcu(pAd, 0x52, 0xff, (UCHAR)pAd->Led1, (UCHAR)(pAd->Led1 >> 8));
32631 + AsicSendCommandToMcu(pAd, 0x53, 0xff, (UCHAR)pAd->Led2, (UCHAR)(pAd->Led2 >> 8));
32632 + AsicSendCommandToMcu(pAd, 0x54, 0xff, (UCHAR)pAd->Led3, (UCHAR)(pAd->Led3 >> 8));
32633 + pAd->LedIndicatorStregth = 0xFF;
32634 + RTMPSetSignalLED(pAd, -100); // Force signal strength Led to be turned off, before link up
32635 +
32636 +#ifdef CONFIG_STA_SUPPORT
32637 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
32638 + {
32639 + // Read Hardware controlled Radio state enable bit
32640 + if (NicConfig2.field.HardwareRadioControl == 1)
32641 + {
32642 + pAd->StaCfg.bHardwareRadio = TRUE;
32643 +
32644 + // Read GPIO pin2 as Hardware controlled radio state
32645 + RTMP_IO_READ32(pAd, GPIO_CTRL_CFG, &data);
32646 + if ((data & 0x04) == 0)
32647 + {
32648 + pAd->StaCfg.bHwRadio = FALSE;
32649 + pAd->StaCfg.bRadio = FALSE;
32650 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
32651 + }
32652 + }
32653 + else
32654 + pAd->StaCfg.bHardwareRadio = FALSE;
32655 +
32656 + if (pAd->StaCfg.bRadio == FALSE)
32657 + {
32658 + RTMPSetLED(pAd, LED_RADIO_OFF);
32659 + }
32660 + else
32661 + {
32662 + RTMPSetLED(pAd, LED_RADIO_ON);
32663 +#ifdef RT2860
32664 + AsicSendCommandToMcu(pAd, 0x30, 0xff, 0xff, 0x02);
32665 + AsicSendCommandToMcu(pAd, 0x31, PowerWakeCID, 0x00, 0x00);
32666 + // 2-1. wait command ok.
32667 + AsicCheckCommanOk(pAd, PowerWakeCID);
32668 +#endif // RT2860 //
32669 + }
32670 + }
32671 +#endif // CONFIG_STA_SUPPORT //
32672 +
32673 + // Turn off patching for cardbus controller
32674 + if (NicConfig2.field.CardbusAcceleration == 1)
32675 + {
32676 + }
32677 +
32678 + if (NicConfig2.field.DynamicTxAgcControl == 1)
32679 + pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = TRUE;
32680 + else
32681 + pAd->bAutoTxAgcA = pAd->bAutoTxAgcG = FALSE;
32682 + //
32683 + // Since BBP has been progamed, to make sure BBP setting will be
32684 + // upate inside of AsicAntennaSelect, so reset to UNKNOWN_BAND!!
32685 + //
32686 + pAd->CommonCfg.BandState = UNKNOWN_BAND;
32687 +
32688 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BBPR3);
32689 + BBPR3 &= (~0x18);
32690 + if(pAd->Antenna.field.RxPath == 3)
32691 + {
32692 + BBPR3 |= (0x10);
32693 + }
32694 + else if(pAd->Antenna.field.RxPath == 2)
32695 + {
32696 + BBPR3 |= (0x8);
32697 + }
32698 + else if(pAd->Antenna.field.RxPath == 1)
32699 + {
32700 + BBPR3 |= (0x0);
32701 + }
32702 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BBPR3);
32703 +
32704 +#ifdef CONFIG_STA_SUPPORT
32705 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
32706 + {
32707 + // Handle the difference when 1T
32708 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &BBPR1);
32709 + if(pAd->Antenna.field.TxPath == 1)
32710 + {
32711 + BBPR1 &= (~0x18);
32712 + }
32713 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, BBPR1);
32714 +
32715 + DBGPRINT(RT_DEBUG_TRACE, ("Use Hw Radio Control Pin=%d; if used Pin=%d;\n", pAd->CommonCfg.bHardwareRadio, pAd->CommonCfg.bHardwareRadio));
32716 + }
32717 +#endif // CONFIG_STA_SUPPORT //
32718 + DBGPRINT(RT_DEBUG_TRACE, ("TxPath = %d, RxPath = %d, RFIC=%d, Polar+LED mode=%x\n", pAd->Antenna.field.TxPath, pAd->Antenna.field.RxPath, pAd->RfIcType, pAd->LedCntl.word));
32719 + DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitAsicFromEEPROM\n"));
32720 +}
32721 +
32722 +/*
32723 + ========================================================================
32724 +
32725 + Routine Description:
32726 + Initialize NIC hardware
32727 +
32728 + Arguments:
32729 + Adapter Pointer to our adapter
32730 +
32731 + Return Value:
32732 + None
32733 +
32734 + IRQL = PASSIVE_LEVEL
32735 +
32736 + Note:
32737 +
32738 + ========================================================================
32739 +*/
32740 +NDIS_STATUS NICInitializeAdapter(
32741 + IN PRTMP_ADAPTER pAd,
32742 + IN BOOLEAN bHardReset)
32743 +{
32744 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
32745 + WPDMA_GLO_CFG_STRUC GloCfg;
32746 +#ifdef RT2860
32747 + UINT32 Value;
32748 + DELAY_INT_CFG_STRUC IntCfg;
32749 +#endif // RT2860 //
32750 + ULONG i =0, j=0;
32751 + AC_TXOP_CSR0_STRUC csr0;
32752 +
32753 + DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitializeAdapter\n"));
32754 +
32755 + // 3. Set DMA global configuration except TX_DMA_EN and RX_DMA_EN bits:
32756 +retry:
32757 + i = 0;
32758 + do
32759 + {
32760 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word);
32761 + if ((GloCfg.field.TxDMABusy == 0) && (GloCfg.field.RxDMABusy == 0))
32762 + break;
32763 +
32764 + RTMPusecDelay(1000);
32765 + i++;
32766 + }while ( i<100);
32767 + DBGPRINT(RT_DEBUG_TRACE, ("<== DMA offset 0x208 = 0x%x\n", GloCfg.word));
32768 + GloCfg.word &= 0xff0;
32769 + GloCfg.field.EnTXWriteBackDDONE =1;
32770 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word);
32771 +
32772 + // Record HW Beacon offset
32773 + pAd->BeaconOffset[0] = HW_BEACON_BASE0;
32774 + pAd->BeaconOffset[1] = HW_BEACON_BASE1;
32775 + pAd->BeaconOffset[2] = HW_BEACON_BASE2;
32776 + pAd->BeaconOffset[3] = HW_BEACON_BASE3;
32777 + pAd->BeaconOffset[4] = HW_BEACON_BASE4;
32778 + pAd->BeaconOffset[5] = HW_BEACON_BASE5;
32779 + pAd->BeaconOffset[6] = HW_BEACON_BASE6;
32780 + pAd->BeaconOffset[7] = HW_BEACON_BASE7;
32781 +
32782 + //
32783 + // write all shared Ring's base address into ASIC
32784 + //
32785 +
32786 + // asic simulation sequence put this ahead before loading firmware.
32787 + // pbf hardware reset
32788 +#ifdef RT2860
32789 + RTMP_IO_WRITE32(pAd, WPDMA_RST_IDX, 0x1003f); // 0x10000 for reset rx, 0x3f resets all 6 tx rings.
32790 + RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, 0xe1f);
32791 + RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, 0xe00);
32792 +#endif // RT2860 //
32793 +
32794 + // Initialze ASIC for TX & Rx operation
32795 + if (NICInitializeAsic(pAd , bHardReset) != NDIS_STATUS_SUCCESS)
32796 + {
32797 + if (j++ == 0)
32798 + {
32799 + NICLoadFirmware(pAd);
32800 + goto retry;
32801 + }
32802 + return NDIS_STATUS_FAILURE;
32803 + }
32804 +
32805 +
32806 +#ifdef RT2860
32807 + // Write AC_BK base address register
32808 + Value = RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_BK].Cell[0].AllocPa);
32809 + RTMP_IO_WRITE32(pAd, TX_BASE_PTR1, Value);
32810 + DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR1 : 0x%x\n", Value));
32811 +
32812 + // Write AC_BE base address register
32813 + Value = RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_BE].Cell[0].AllocPa);
32814 + RTMP_IO_WRITE32(pAd, TX_BASE_PTR0, Value);
32815 + DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR0 : 0x%x\n", Value));
32816 +
32817 + // Write AC_VI base address register
32818 + Value = RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_VI].Cell[0].AllocPa);
32819 + RTMP_IO_WRITE32(pAd, TX_BASE_PTR2, Value);
32820 + DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR2 : 0x%x\n", Value));
32821 +
32822 + // Write AC_VO base address register
32823 + Value = RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_AC_VO].Cell[0].AllocPa);
32824 + RTMP_IO_WRITE32(pAd, TX_BASE_PTR3, Value);
32825 + DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR3 : 0x%x\n", Value));
32826 +
32827 + // Write HCCA base address register
32828 + Value = RTMP_GetPhysicalAddressLow(pAd->TxRing[QID_HCCA].Cell[0].AllocPa);
32829 + RTMP_IO_WRITE32(pAd, TX_BASE_PTR4, Value);
32830 + DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR4 : 0x%x\n", Value));
32831 +
32832 + // Write MGMT_BASE_CSR register
32833 + Value = RTMP_GetPhysicalAddressLow(pAd->MgmtRing.Cell[0].AllocPa);
32834 + RTMP_IO_WRITE32(pAd, TX_BASE_PTR5, Value);
32835 + DBGPRINT(RT_DEBUG_TRACE, ("--> TX_BASE_PTR5 : 0x%x\n", Value));
32836 +
32837 + // Write RX_BASE_CSR register
32838 + Value = RTMP_GetPhysicalAddressLow(pAd->RxRing.Cell[0].AllocPa);
32839 + RTMP_IO_WRITE32(pAd, RX_BASE_PTR, Value);
32840 + DBGPRINT(RT_DEBUG_TRACE, ("--> RX_BASE_PTR : 0x%x\n", Value));
32841 +
32842 + // Init RX Ring index pointer
32843 + pAd->RxRing.RxSwReadIdx = 0;
32844 + pAd->RxRing.RxCpuIdx = RX_RING_SIZE-1;
32845 + RTMP_IO_WRITE32(pAd, RX_CRX_IDX, pAd->RxRing.RxCpuIdx);
32846 +
32847 + // Init TX rings index pointer
32848 + {
32849 + for (i=0; i<NUM_OF_TX_RING; i++)
32850 + {
32851 + pAd->TxRing[i].TxSwFreeIdx = 0;
32852 + pAd->TxRing[i].TxCpuIdx = 0;
32853 + RTMP_IO_WRITE32(pAd, (TX_CTX_IDX0 + i * 0x10) , pAd->TxRing[i].TxCpuIdx);
32854 + }
32855 + }
32856 +
32857 + // init MGMT ring index pointer
32858 + pAd->MgmtRing.TxSwFreeIdx = 0;
32859 + pAd->MgmtRing.TxCpuIdx = 0;
32860 + RTMP_IO_WRITE32(pAd, TX_MGMTCTX_IDX, pAd->MgmtRing.TxCpuIdx);
32861 +
32862 + //
32863 + // set each Ring's SIZE into ASIC. Descriptor Size is fixed by design.
32864 + //
32865 +
32866 + // Write TX_RING_CSR0 register
32867 + Value = TX_RING_SIZE;
32868 + RTMP_IO_WRITE32(pAd, TX_MAX_CNT0, Value);
32869 + RTMP_IO_WRITE32(pAd, TX_MAX_CNT1, Value);
32870 + RTMP_IO_WRITE32(pAd, TX_MAX_CNT2, Value);
32871 + RTMP_IO_WRITE32(pAd, TX_MAX_CNT3, Value);
32872 + RTMP_IO_WRITE32(pAd, TX_MAX_CNT4, Value);
32873 + Value = MGMT_RING_SIZE;
32874 + RTMP_IO_WRITE32(pAd, TX_MGMTMAX_CNT, Value);
32875 +
32876 + // Write RX_RING_CSR register
32877 + Value = RX_RING_SIZE;
32878 + RTMP_IO_WRITE32(pAd, RX_MAX_CNT, Value);
32879 +#endif // RT2860 //
32880 +
32881 +
32882 + // WMM parameter
32883 + csr0.word = 0;
32884 + RTMP_IO_WRITE32(pAd, WMM_TXOP0_CFG, csr0.word);
32885 + if (pAd->CommonCfg.PhyMode == PHY_11B)
32886 + {
32887 + csr0.field.Ac0Txop = 192; // AC_VI: 192*32us ~= 6ms
32888 + csr0.field.Ac1Txop = 96; // AC_VO: 96*32us ~= 3ms
32889 + }
32890 + else
32891 + {
32892 + csr0.field.Ac0Txop = 96; // AC_VI: 96*32us ~= 3ms
32893 + csr0.field.Ac1Txop = 48; // AC_VO: 48*32us ~= 1.5ms
32894 + }
32895 + RTMP_IO_WRITE32(pAd, WMM_TXOP1_CFG, csr0.word);
32896 +
32897 +
32898 +#ifdef RT2860
32899 + // 3. Set DMA global configuration except TX_DMA_EN and RX_DMA_EN bits:
32900 + i = 0;
32901 + do
32902 + {
32903 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word);
32904 + if ((GloCfg.field.TxDMABusy == 0) && (GloCfg.field.RxDMABusy == 0))
32905 + break;
32906 +
32907 + RTMPusecDelay(1000);
32908 + i++;
32909 + }while ( i < 100);
32910 +
32911 + GloCfg.word &= 0xff0;
32912 + GloCfg.field.EnTXWriteBackDDONE =1;
32913 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word);
32914 +
32915 + IntCfg.word = 0;
32916 + RTMP_IO_WRITE32(pAd, DELAY_INT_CFG, IntCfg.word);
32917 +#endif // RT2860 //
32918 +
32919 +
32920 + // reset action
32921 + // Load firmware
32922 + // Status = NICLoadFirmware(pAd);
32923 +
32924 + DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitializeAdapter\n"));
32925 + return Status;
32926 +}
32927 +
32928 +/*
32929 + ========================================================================
32930 +
32931 + Routine Description:
32932 + Initialize ASIC
32933 +
32934 + Arguments:
32935 + Adapter Pointer to our adapter
32936 +
32937 + Return Value:
32938 + None
32939 +
32940 + IRQL = PASSIVE_LEVEL
32941 +
32942 + Note:
32943 +
32944 + ========================================================================
32945 +*/
32946 +NDIS_STATUS NICInitializeAsic(
32947 + IN PRTMP_ADAPTER pAd,
32948 + IN BOOLEAN bHardReset)
32949 +{
32950 + ULONG Index = 0;
32951 + UCHAR R0 = 0xff;
32952 + UINT32 MacCsr12 = 0, Counter = 0;
32953 + USHORT KeyIdx;
32954 + INT i,apidx;
32955 +
32956 + DBGPRINT(RT_DEBUG_TRACE, ("--> NICInitializeAsic\n"));
32957 +
32958 +#ifdef RT2860
32959 + if (bHardReset == TRUE)
32960 + {
32961 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x3);
32962 + }
32963 + else
32964 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x1);
32965 +
32966 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x0);
32967 + // Initialize MAC register to default value
32968 + for (Index = 0; Index < NUM_MAC_REG_PARMS; Index++)
32969 + {
32970 + RTMP_IO_WRITE32(pAd, MACRegTable[Index].Register, MACRegTable[Index].Value);
32971 + }
32972 +
32973 +
32974 +#ifdef CONFIG_STA_SUPPORT
32975 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
32976 + {
32977 + for (Index = 0; Index < NUM_STA_MAC_REG_PARMS; Index++)
32978 + {
32979 + RTMP_IO_WRITE32(pAd, STAMACRegTable[Index].Register, STAMACRegTable[Index].Value);
32980 + }
32981 + }
32982 +#endif // CONFIG_STA_SUPPORT //
32983 +#endif // RT2860 //
32984 +
32985 +
32986 + //
32987 + // Before program BBP, we need to wait BBP/RF get wake up.
32988 + //
32989 + Index = 0;
32990 + do
32991 + {
32992 + RTMP_IO_READ32(pAd, MAC_STATUS_CFG, &MacCsr12);
32993 +
32994 + if ((MacCsr12 & 0x03) == 0) // if BB.RF is stable
32995 + break;
32996 +
32997 + DBGPRINT(RT_DEBUG_TRACE, ("Check MAC_STATUS_CFG = Busy = %x\n", MacCsr12));
32998 + RTMPusecDelay(1000);
32999 + } while (Index++ < 100);
33000 +
33001 + // The commands to firmware should be after these commands, these commands will init firmware
33002 + // PCI and USB are not the same because PCI driver needs to wait for PCI bus ready
33003 + RTMP_IO_WRITE32(pAd, H2M_BBP_AGENT, 0); // initialize BBP R/W access agent
33004 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_CSR, 0);
33005 + RTMPusecDelay(1000);
33006 +
33007 + // Read BBP register, make sure BBP is up and running before write new data
33008 + Index = 0;
33009 + do
33010 + {
33011 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R0, &R0);
33012 + DBGPRINT(RT_DEBUG_TRACE, ("BBP version = %x\n", R0));
33013 + } while ((++Index < 20) && ((R0 == 0xff) || (R0 == 0x00)));
33014 + //ASSERT(Index < 20); //this will cause BSOD on Check-build driver
33015 +
33016 + if ((R0 == 0xff) || (R0 == 0x00))
33017 + return NDIS_STATUS_FAILURE;
33018 +
33019 + // Initialize BBP register to default value
33020 + for (Index = 0; Index < NUM_BBP_REG_PARMS; Index++)
33021 + {
33022 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBPRegTable[Index].Register, BBPRegTable[Index].Value);
33023 + }
33024 +
33025 + // for rt2860E and after, init BBP_R84 with 0x19. This is for extension channel overlapping IOT.
33026 + if ((pAd->MACVersion&0xffff) != 0x0101)
33027 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R84, 0x19);
33028 +
33029 +
33030 + if (pAd->MACVersion == 0x28600100)
33031 + {
33032 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, 0x16);
33033 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, 0x12);
33034 + }
33035 +
33036 + if (pAd->MACVersion >= RALINK_2880E_VERSION && pAd->MACVersion < RALINK_3070_VERSION) // 3*3
33037 + {
33038 + // enlarge MAX_LEN_CFG
33039 + UINT32 csr;
33040 + RTMP_IO_READ32(pAd, MAX_LEN_CFG, &csr);
33041 + csr &= 0xFFF;
33042 + csr |= 0x2000;
33043 + RTMP_IO_WRITE32(pAd, MAX_LEN_CFG, csr);
33044 + }
33045 +
33046 +
33047 + // Add radio off control
33048 +#ifdef CONFIG_STA_SUPPORT
33049 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
33050 + {
33051 + if (pAd->StaCfg.bRadio == FALSE)
33052 + {
33053 +// RTMP_IO_WRITE32(pAd, PWR_PIN_CFG, 0x00001818);
33054 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF);
33055 + DBGPRINT(RT_DEBUG_TRACE, ("Set Radio Off\n"));
33056 + }
33057 + }
33058 +#endif // CONFIG_STA_SUPPORT //
33059 +
33060 + // Clear raw counters
33061 + RTMP_IO_READ32(pAd, RX_STA_CNT0, &Counter);
33062 + RTMP_IO_READ32(pAd, RX_STA_CNT1, &Counter);
33063 + RTMP_IO_READ32(pAd, RX_STA_CNT2, &Counter);
33064 + RTMP_IO_READ32(pAd, TX_STA_CNT0, &Counter);
33065 + RTMP_IO_READ32(pAd, TX_STA_CNT1, &Counter);
33066 + RTMP_IO_READ32(pAd, TX_STA_CNT2, &Counter);
33067 +
33068 + // ASIC will keep garbage value after boot
33069 + // Clear all seared key table when initial
33070 + // This routine can be ignored in radio-ON/OFF operation.
33071 + if (bHardReset)
33072 + {
33073 + for (KeyIdx = 0; KeyIdx < 4; KeyIdx++)
33074 + {
33075 + RTMP_IO_WRITE32(pAd, SHARED_KEY_MODE_BASE + 4*KeyIdx, 0);
33076 + }
33077 +
33078 + // Clear all pairwise key table when initial
33079 + for (KeyIdx = 0; KeyIdx < 256; KeyIdx++)
33080 + {
33081 + RTMP_IO_WRITE32(pAd, MAC_WCID_ATTRIBUTE_BASE + (KeyIdx * HW_WCID_ATTRI_SIZE), 1);
33082 + }
33083 + }
33084 +
33085 +
33086 + // It isn't necessary to clear this space when not hard reset.
33087 + if (bHardReset == TRUE)
33088 + {
33089 + // clear all on-chip BEACON frame space
33090 + for (apidx = 0; apidx < HW_BEACON_MAX_COUNT; apidx++)
33091 + {
33092 + for (i = 0; i < HW_BEACON_OFFSET>>2; i+=4)
33093 + RTMP_IO_WRITE32(pAd, pAd->BeaconOffset[apidx] + i, 0x00);
33094 + }
33095 + }
33096 +
33097 +#ifdef CONFIG_STA_SUPPORT
33098 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
33099 + {
33100 + // for rt2860E and after, init TXOP_CTRL_CFG with 0x583f. This is for extension channel overlapping IOT.
33101 + if ((pAd->MACVersion&0xffff) != 0x0101)
33102 + RTMP_IO_WRITE32(pAd, TXOP_CTRL_CFG, 0x583f);
33103 + }
33104 +#endif // CONFIG_STA_SUPPORT //
33105 +
33106 + DBGPRINT(RT_DEBUG_TRACE, ("<-- NICInitializeAsic\n"));
33107 + return NDIS_STATUS_SUCCESS;
33108 +}
33109 +
33110 +/*
33111 + ========================================================================
33112 +
33113 + Routine Description:
33114 + Reset NIC Asics
33115 +
33116 + Arguments:
33117 + Adapter Pointer to our adapter
33118 +
33119 + Return Value:
33120 + None
33121 +
33122 + IRQL = PASSIVE_LEVEL
33123 +
33124 + Note:
33125 + Reset NIC to initial state AS IS system boot up time.
33126 +
33127 + ========================================================================
33128 +*/
33129 +VOID NICIssueReset(
33130 + IN PRTMP_ADAPTER pAd)
33131 +{
33132 + UINT32 Value = 0;
33133 + DBGPRINT(RT_DEBUG_TRACE, ("--> NICIssueReset\n"));
33134 +
33135 + // Disable Rx, register value supposed will remain after reset
33136 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
33137 + Value &= (0xfffffff3);
33138 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
33139 +
33140 + // Issue reset and clear from reset state
33141 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x03); // 2004-09-17 change from 0x01
33142 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x00);
33143 +
33144 + DBGPRINT(RT_DEBUG_TRACE, ("<-- NICIssueReset\n"));
33145 +}
33146 +
33147 +/*
33148 + ========================================================================
33149 +
33150 + Routine Description:
33151 + Check ASIC registers and find any reason the system might hang
33152 +
33153 + Arguments:
33154 + Adapter Pointer to our adapter
33155 +
33156 + Return Value:
33157 + None
33158 +
33159 + IRQL = DISPATCH_LEVEL
33160 +
33161 + ========================================================================
33162 +*/
33163 +BOOLEAN NICCheckForHang(
33164 + IN PRTMP_ADAPTER pAd)
33165 +{
33166 + return (FALSE);
33167 +}
33168 +
33169 +VOID NICUpdateFifoStaCounters(
33170 + IN PRTMP_ADAPTER pAd)
33171 +{
33172 + TX_STA_FIFO_STRUC StaFifo;
33173 + MAC_TABLE_ENTRY *pEntry;
33174 + UCHAR i = 0;
33175 + UCHAR pid = 0, wcid = 0;
33176 + CHAR reTry;
33177 + UCHAR succMCS;
33178 +
33179 +#ifdef RALINK_ATE
33180 + /* Nothing to do in ATE mode */
33181 + if (ATE_ON(pAd))
33182 + return;
33183 +#endif // RALINK_ATE //
33184 +
33185 + do
33186 + {
33187 + RTMP_IO_READ32(pAd, TX_STA_FIFO, &StaFifo.word);
33188 +
33189 + if (StaFifo.field.bValid == 0)
33190 + break;
33191 +
33192 + wcid = (UCHAR)StaFifo.field.wcid;
33193 +
33194 +
33195 + /* ignore NoACK and MGMT frame use 0xFF as WCID */
33196 + if ((StaFifo.field.TxAckRequired == 0) || (wcid >= MAX_LEN_OF_MAC_TABLE))
33197 + {
33198 + i++;
33199 + continue;
33200 + }
33201 +
33202 + /* PID store Tx MCS Rate */
33203 + pid = (UCHAR)StaFifo.field.PidType;
33204 +
33205 + pEntry = &pAd->MacTab.Content[wcid];
33206 +
33207 + pEntry->DebugFIFOCount++;
33208 +
33209 +#ifdef DOT11_N_SUPPORT
33210 + if (StaFifo.field.TxBF) // 3*3
33211 + pEntry->TxBFCount++;
33212 +#endif // DOT11_N_SUPPORT //
33213 +
33214 +#ifdef UAPSD_AP_SUPPORT
33215 + UAPSD_SP_AUE_Handle(pAd, pEntry, StaFifo.field.TxSuccess);
33216 +#endif // UAPSD_AP_SUPPORT //
33217 +
33218 + if (!StaFifo.field.TxSuccess)
33219 + {
33220 + pEntry->FIFOCount++;
33221 + pEntry->OneSecTxFailCount++;
33222 +
33223 + if (pEntry->FIFOCount >= 1)
33224 + {
33225 + DBGPRINT(RT_DEBUG_TRACE, ("#"));
33226 +#if 0
33227 + SendRefreshBAR(pAd, pEntry);
33228 + pEntry->NoBADataCountDown = 64;
33229 +#else
33230 +#ifdef DOT11_N_SUPPORT
33231 + pEntry->NoBADataCountDown = 64;
33232 +#endif // DOT11_N_SUPPORT //
33233 +
33234 + if(pEntry->PsMode == PWR_ACTIVE)
33235 + {
33236 +#ifdef DOT11_N_SUPPORT
33237 + int tid;
33238 + for (tid=0; tid<NUM_OF_TID; tid++)
33239 + {
33240 + BAOriSessionTearDown(pAd, pEntry->Aid, tid, FALSE, FALSE);
33241 + }
33242 +#endif // DOT11_N_SUPPORT //
33243 +
33244 + // Update the continuous transmission counter except PS mode
33245 + pEntry->ContinueTxFailCnt++;
33246 + }
33247 + else
33248 + {
33249 + // Clear the FIFOCount when sta in Power Save mode. Basically we assume
33250 + // this tx error happened due to sta just go to sleep.
33251 + pEntry->FIFOCount = 0;
33252 + pEntry->ContinueTxFailCnt = 0;
33253 + }
33254 +#endif
33255 + //pEntry->FIFOCount = 0;
33256 + }
33257 + //pEntry->bSendBAR = TRUE;
33258 + }
33259 + else
33260 + {
33261 +#ifdef DOT11_N_SUPPORT
33262 + if ((pEntry->PsMode != PWR_SAVE) && (pEntry->NoBADataCountDown > 0))
33263 + {
33264 + pEntry->NoBADataCountDown--;
33265 + if (pEntry->NoBADataCountDown==0)
33266 + {
33267 + DBGPRINT(RT_DEBUG_TRACE, ("@\n"));
33268 + }
33269 + }
33270 +#endif // DOT11_N_SUPPORT //
33271 + pEntry->FIFOCount = 0;
33272 + pEntry->OneSecTxNoRetryOkCount++;
33273 + // update NoDataIdleCount when sucessful send packet to STA.
33274 + pEntry->NoDataIdleCount = 0;
33275 + pEntry->ContinueTxFailCnt = 0;
33276 + }
33277 +
33278 + succMCS = StaFifo.field.SuccessRate & 0x7F;
33279 +
33280 + reTry = pid - succMCS;
33281 +
33282 + if (StaFifo.field.TxSuccess)
33283 + {
33284 + pEntry->TXMCSExpected[pid]++;
33285 + if (pid == succMCS)
33286 + {
33287 + pEntry->TXMCSSuccessful[pid]++;
33288 + }
33289 + else
33290 + {
33291 + pEntry->TXMCSAutoFallBack[pid][succMCS]++;
33292 + }
33293 + }
33294 + else
33295 + {
33296 + pEntry->TXMCSFailed[pid]++;
33297 + }
33298 +
33299 + if (reTry > 0)
33300 + {
33301 + if ((pid >= 12) && succMCS <=7)
33302 + {
33303 + reTry -= 4;
33304 + }
33305 + pEntry->OneSecTxRetryOkCount += reTry;
33306 + }
33307 +
33308 + i++;
33309 + // ASIC store 16 stack
33310 + } while ( i < (2*TX_RING_SIZE) );
33311 +
33312 +}
33313 +
33314 +/*
33315 + ========================================================================
33316 +
33317 + Routine Description:
33318 + Read statistical counters from hardware registers and record them
33319 + in software variables for later on query
33320 +
33321 + Arguments:
33322 + pAd Pointer to our adapter
33323 +
33324 + Return Value:
33325 + None
33326 +
33327 + IRQL = DISPATCH_LEVEL
33328 +
33329 + ========================================================================
33330 +*/
33331 +VOID NICUpdateRawCounters(
33332 + IN PRTMP_ADAPTER pAd)
33333 +{
33334 + UINT32 OldValue;
33335 + RX_STA_CNT0_STRUC RxStaCnt0;
33336 + RX_STA_CNT1_STRUC RxStaCnt1;
33337 + RX_STA_CNT2_STRUC RxStaCnt2;
33338 + TX_STA_CNT0_STRUC TxStaCnt0;
33339 + TX_STA_CNT1_STRUC StaTx1;
33340 + TX_STA_CNT2_STRUC StaTx2;
33341 + TX_AGG_CNT_STRUC TxAggCnt;
33342 + TX_AGG_CNT0_STRUC TxAggCnt0;
33343 + TX_AGG_CNT1_STRUC TxAggCnt1;
33344 + TX_AGG_CNT2_STRUC TxAggCnt2;
33345 + TX_AGG_CNT3_STRUC TxAggCnt3;
33346 + TX_AGG_CNT4_STRUC TxAggCnt4;
33347 + TX_AGG_CNT5_STRUC TxAggCnt5;
33348 + TX_AGG_CNT6_STRUC TxAggCnt6;
33349 + TX_AGG_CNT7_STRUC TxAggCnt7;
33350 +
33351 + RTMP_IO_READ32(pAd, RX_STA_CNT0, &RxStaCnt0.word);
33352 + RTMP_IO_READ32(pAd, RX_STA_CNT2, &RxStaCnt2.word);
33353 +
33354 + {
33355 + RTMP_IO_READ32(pAd, RX_STA_CNT1, &RxStaCnt1.word);
33356 + // Update RX PLCP error counter
33357 + pAd->PrivateInfo.PhyRxErrCnt += RxStaCnt1.field.PlcpErr;
33358 + // Update False CCA counter
33359 + pAd->RalinkCounters.OneSecFalseCCACnt += RxStaCnt1.field.FalseCca;
33360 + }
33361 +
33362 + // Update FCS counters
33363 + OldValue= pAd->WlanCounters.FCSErrorCount.u.LowPart;
33364 + pAd->WlanCounters.FCSErrorCount.u.LowPart += (RxStaCnt0.field.CrcErr); // >> 7);
33365 + if (pAd->WlanCounters.FCSErrorCount.u.LowPart < OldValue)
33366 + pAd->WlanCounters.FCSErrorCount.u.HighPart++;
33367 +
33368 + // Add FCS error count to private counters
33369 + pAd->RalinkCounters.OneSecRxFcsErrCnt += RxStaCnt0.field.CrcErr;
33370 + OldValue = pAd->RalinkCounters.RealFcsErrCount.u.LowPart;
33371 + pAd->RalinkCounters.RealFcsErrCount.u.LowPart += RxStaCnt0.field.CrcErr;
33372 + if (pAd->RalinkCounters.RealFcsErrCount.u.LowPart < OldValue)
33373 + pAd->RalinkCounters.RealFcsErrCount.u.HighPart++;
33374 +
33375 + // Update Duplicate Rcv check
33376 + pAd->RalinkCounters.DuplicateRcv += RxStaCnt2.field.RxDupliCount;
33377 + pAd->WlanCounters.FrameDuplicateCount.u.LowPart += RxStaCnt2.field.RxDupliCount;
33378 + // Update RX Overflow counter
33379 + pAd->Counters8023.RxNoBuffer += (RxStaCnt2.field.RxFifoOverflowCount);
33380 +
33381 + if (!pAd->bUpdateBcnCntDone)
33382 + {
33383 + // Update BEACON sent count
33384 + RTMP_IO_READ32(pAd, TX_STA_CNT0, &TxStaCnt0.word);
33385 + RTMP_IO_READ32(pAd, TX_STA_CNT1, &StaTx1.word);
33386 + RTMP_IO_READ32(pAd, TX_STA_CNT2, &StaTx2.word);
33387 + pAd->RalinkCounters.OneSecBeaconSentCnt += TxStaCnt0.field.TxBeaconCount;
33388 + pAd->RalinkCounters.OneSecTxRetryOkCount += StaTx1.field.TxRetransmit;
33389 + pAd->RalinkCounters.OneSecTxNoRetryOkCount += StaTx1.field.TxSuccess;
33390 + pAd->RalinkCounters.OneSecTxFailCount += TxStaCnt0.field.TxFailCount;
33391 + pAd->WlanCounters.TransmittedFragmentCount.u.LowPart += StaTx1.field.TxSuccess;
33392 + pAd->WlanCounters.RetryCount.u.LowPart += StaTx1.field.TxRetransmit;
33393 + pAd->WlanCounters.FailedCount.u.LowPart += TxStaCnt0.field.TxFailCount;
33394 + }
33395 +
33396 + {
33397 + RTMP_IO_READ32(pAd, TX_AGG_CNT, &TxAggCnt.word);
33398 + RTMP_IO_READ32(pAd, TX_AGG_CNT0, &TxAggCnt0.word);
33399 + RTMP_IO_READ32(pAd, TX_AGG_CNT1, &TxAggCnt1.word);
33400 + RTMP_IO_READ32(pAd, TX_AGG_CNT2, &TxAggCnt2.word);
33401 + RTMP_IO_READ32(pAd, TX_AGG_CNT3, &TxAggCnt3.word);
33402 + RTMP_IO_READ32(pAd, TX_AGG_CNT4, &TxAggCnt4.word);
33403 + RTMP_IO_READ32(pAd, TX_AGG_CNT5, &TxAggCnt5.word);
33404 + RTMP_IO_READ32(pAd, TX_AGG_CNT6, &TxAggCnt6.word);
33405 + RTMP_IO_READ32(pAd, TX_AGG_CNT7, &TxAggCnt7.word);
33406 + pAd->RalinkCounters.TxAggCount += TxAggCnt.field.AggTxCount;
33407 + pAd->RalinkCounters.TxNonAggCount += TxAggCnt.field.NonAggTxCount;
33408 + pAd->RalinkCounters.TxAgg1MPDUCount += TxAggCnt0.field.AggSize1Count;
33409 + pAd->RalinkCounters.TxAgg2MPDUCount += TxAggCnt0.field.AggSize2Count;
33410 +
33411 + pAd->RalinkCounters.TxAgg3MPDUCount += TxAggCnt1.field.AggSize3Count;
33412 + pAd->RalinkCounters.TxAgg4MPDUCount += TxAggCnt1.field.AggSize4Count;
33413 + pAd->RalinkCounters.TxAgg5MPDUCount += TxAggCnt2.field.AggSize5Count;
33414 + pAd->RalinkCounters.TxAgg6MPDUCount += TxAggCnt2.field.AggSize6Count;
33415 +
33416 + pAd->RalinkCounters.TxAgg7MPDUCount += TxAggCnt3.field.AggSize7Count;
33417 + pAd->RalinkCounters.TxAgg8MPDUCount += TxAggCnt3.field.AggSize8Count;
33418 + pAd->RalinkCounters.TxAgg9MPDUCount += TxAggCnt4.field.AggSize9Count;
33419 + pAd->RalinkCounters.TxAgg10MPDUCount += TxAggCnt4.field.AggSize10Count;
33420 +
33421 + pAd->RalinkCounters.TxAgg11MPDUCount += TxAggCnt5.field.AggSize11Count;
33422 + pAd->RalinkCounters.TxAgg12MPDUCount += TxAggCnt5.field.AggSize12Count;
33423 + pAd->RalinkCounters.TxAgg13MPDUCount += TxAggCnt6.field.AggSize13Count;
33424 + pAd->RalinkCounters.TxAgg14MPDUCount += TxAggCnt6.field.AggSize14Count;
33425 +
33426 + pAd->RalinkCounters.TxAgg15MPDUCount += TxAggCnt7.field.AggSize15Count;
33427 + pAd->RalinkCounters.TxAgg16MPDUCount += TxAggCnt7.field.AggSize16Count;
33428 +
33429 + // Calculate the transmitted A-MPDU count
33430 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += TxAggCnt0.field.AggSize1Count;
33431 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt0.field.AggSize2Count / 2);
33432 +
33433 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt1.field.AggSize3Count / 3);
33434 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt1.field.AggSize4Count / 4);
33435 +
33436 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt2.field.AggSize5Count / 5);
33437 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt2.field.AggSize6Count / 6);
33438 +
33439 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt3.field.AggSize7Count / 7);
33440 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt3.field.AggSize8Count / 8);
33441 +
33442 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt4.field.AggSize9Count / 9);
33443 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt4.field.AggSize10Count / 10);
33444 +
33445 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt5.field.AggSize11Count / 11);
33446 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt5.field.AggSize12Count / 12);
33447 +
33448 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt6.field.AggSize13Count / 13);
33449 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt6.field.AggSize14Count / 14);
33450 +
33451 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt7.field.AggSize15Count / 15);
33452 + pAd->RalinkCounters.TransmittedAMPDUCount.u.LowPart += (TxAggCnt7.field.AggSize16Count / 16);
33453 + }
33454 +
33455 +#ifdef DBG_DIAGNOSE
33456 + {
33457 + RtmpDiagStruct *pDiag;
33458 + COUNTER_RALINK *pRalinkCounters;
33459 + UCHAR ArrayCurIdx, i;
33460 +
33461 + pDiag = &pAd->DiagStruct;
33462 + pRalinkCounters = &pAd->RalinkCounters;
33463 + ArrayCurIdx = pDiag->ArrayCurIdx;
33464 +
33465 + if (pDiag->inited == 0)
33466 + {
33467 + NdisZeroMemory(pDiag, sizeof(struct _RtmpDiagStrcut_));
33468 + pDiag->ArrayStartIdx = pDiag->ArrayCurIdx = 0;
33469 + pDiag->inited = 1;
33470 + }
33471 + else
33472 + {
33473 + // Tx
33474 + pDiag->TxFailCnt[ArrayCurIdx] = TxStaCnt0.field.TxFailCount;
33475 + pDiag->TxAggCnt[ArrayCurIdx] = TxAggCnt.field.AggTxCount;
33476 + pDiag->TxNonAggCnt[ArrayCurIdx] = TxAggCnt.field.NonAggTxCount;
33477 + pDiag->TxAMPDUCnt[ArrayCurIdx][0] = TxAggCnt0.field.AggSize1Count;
33478 + pDiag->TxAMPDUCnt[ArrayCurIdx][1] = TxAggCnt0.field.AggSize2Count;
33479 + pDiag->TxAMPDUCnt[ArrayCurIdx][2] = TxAggCnt1.field.AggSize3Count;
33480 + pDiag->TxAMPDUCnt[ArrayCurIdx][3] = TxAggCnt1.field.AggSize4Count;
33481 + pDiag->TxAMPDUCnt[ArrayCurIdx][4] = TxAggCnt2.field.AggSize5Count;
33482 + pDiag->TxAMPDUCnt[ArrayCurIdx][5] = TxAggCnt2.field.AggSize6Count;
33483 + pDiag->TxAMPDUCnt[ArrayCurIdx][6] = TxAggCnt3.field.AggSize7Count;
33484 + pDiag->TxAMPDUCnt[ArrayCurIdx][7] = TxAggCnt3.field.AggSize8Count;
33485 + pDiag->TxAMPDUCnt[ArrayCurIdx][8] = TxAggCnt4.field.AggSize9Count;
33486 + pDiag->TxAMPDUCnt[ArrayCurIdx][9] = TxAggCnt4.field.AggSize10Count;
33487 + pDiag->TxAMPDUCnt[ArrayCurIdx][10] = TxAggCnt5.field.AggSize11Count;
33488 + pDiag->TxAMPDUCnt[ArrayCurIdx][11] = TxAggCnt5.field.AggSize12Count;
33489 + pDiag->TxAMPDUCnt[ArrayCurIdx][12] = TxAggCnt6.field.AggSize13Count;
33490 + pDiag->TxAMPDUCnt[ArrayCurIdx][13] = TxAggCnt6.field.AggSize14Count;
33491 + pDiag->TxAMPDUCnt[ArrayCurIdx][14] = TxAggCnt7.field.AggSize15Count;
33492 + pDiag->TxAMPDUCnt[ArrayCurIdx][15] = TxAggCnt7.field.AggSize16Count;
33493 +
33494 + pDiag->RxCrcErrCnt[ArrayCurIdx] = RxStaCnt0.field.CrcErr;
33495 +
33496 + INC_RING_INDEX(pDiag->ArrayCurIdx, DIAGNOSE_TIME);
33497 + ArrayCurIdx = pDiag->ArrayCurIdx;
33498 + for (i =0; i < 9; i++)
33499 + {
33500 + pDiag->TxDescCnt[ArrayCurIdx][i]= 0;
33501 + pDiag->TxSWQueCnt[ArrayCurIdx][i] =0;
33502 + pDiag->TxMcsCnt[ArrayCurIdx][i] = 0;
33503 + pDiag->RxMcsCnt[ArrayCurIdx][i] = 0;
33504 + }
33505 + pDiag->TxDataCnt[ArrayCurIdx] = 0;
33506 + pDiag->TxFailCnt[ArrayCurIdx] = 0;
33507 + pDiag->RxDataCnt[ArrayCurIdx] = 0;
33508 + pDiag->RxCrcErrCnt[ArrayCurIdx] = 0;
33509 + for (i = 9; i < 24; i++) // 3*3
33510 + {
33511 + pDiag->TxDescCnt[ArrayCurIdx][i] = 0;
33512 + pDiag->TxMcsCnt[ArrayCurIdx][i] = 0;
33513 + pDiag->RxMcsCnt[ArrayCurIdx][i] = 0;
33514 +}
33515 +
33516 + if (pDiag->ArrayCurIdx == pDiag->ArrayStartIdx)
33517 + INC_RING_INDEX(pDiag->ArrayStartIdx, DIAGNOSE_TIME);
33518 + }
33519 +
33520 + }
33521 +#endif // DBG_DIAGNOSE //
33522 +
33523 +
33524 +}
33525 +
33526 +
33527 +/*
33528 + ========================================================================
33529 +
33530 + Routine Description:
33531 + Reset NIC from error
33532 +
33533 + Arguments:
33534 + Adapter Pointer to our adapter
33535 +
33536 + Return Value:
33537 + None
33538 +
33539 + IRQL = PASSIVE_LEVEL
33540 +
33541 + Note:
33542 + Reset NIC from error state
33543 +
33544 + ========================================================================
33545 +*/
33546 +VOID NICResetFromError(
33547 + IN PRTMP_ADAPTER pAd)
33548 +{
33549 + // Reset BBP (according to alex, reset ASIC will force reset BBP
33550 + // Therefore, skip the reset BBP
33551 + // RTMP_IO_WRITE32(pAd, MAC_CSR1, 0x2);
33552 +
33553 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x1);
33554 + // Remove ASIC from reset state
33555 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0x0);
33556 +
33557 + NICInitializeAdapter(pAd, FALSE);
33558 + NICInitAsicFromEEPROM(pAd);
33559 +
33560 + // Switch to current channel, since during reset process, the connection should remains on.
33561 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
33562 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
33563 +}
33564 +
33565 +/*
33566 + ========================================================================
33567 +
33568 + Routine Description:
33569 + erase 8051 firmware image in MAC ASIC
33570 +
33571 + Arguments:
33572 + Adapter Pointer to our adapter
33573 +
33574 + IRQL = PASSIVE_LEVEL
33575 +
33576 + ========================================================================
33577 +*/
33578 +VOID NICEraseFirmware(
33579 + IN PRTMP_ADAPTER pAd)
33580 +{
33581 + ULONG i;
33582 +
33583 + for(i=0; i<MAX_FIRMWARE_IMAGE_SIZE; i+=4)
33584 + RTMP_IO_WRITE32(pAd, FIRMWARE_IMAGE_BASE + i, 0);
33585 +
33586 +}/* End of NICEraseFirmware */
33587 +
33588 +/*
33589 + ========================================================================
33590 +
33591 + Routine Description:
33592 + Load 8051 firmware RT2561.BIN file into MAC ASIC
33593 +
33594 + Arguments:
33595 + Adapter Pointer to our adapter
33596 +
33597 + Return Value:
33598 + NDIS_STATUS_SUCCESS firmware image load ok
33599 + NDIS_STATUS_FAILURE image not found
33600 +
33601 + IRQL = PASSIVE_LEVEL
33602 +
33603 + ========================================================================
33604 +*/
33605 +NDIS_STATUS NICLoadFirmware(
33606 + IN PRTMP_ADAPTER pAd)
33607 +{
33608 +#ifdef BIN_IN_FILE
33609 +#define NICLF_DEFAULT_USE() \
33610 + flg_default_firm_use = TRUE; \
33611 + printk("%s - Use default firmware!\n", __FUNCTION__);
33612 +
33613 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
33614 + PUCHAR src;
33615 + struct file *srcf;
33616 + INT retval, orgfsuid, orgfsgid, i;
33617 + mm_segment_t orgfs;
33618 + PUCHAR pFirmwareImage;
33619 + UINT FileLength = 0;
33620 + UINT32 MacReg;
33621 + ULONG Index;
33622 + ULONG firm;
33623 + BOOLEAN flg_default_firm_use = FALSE;
33624 +
33625 +
33626 + DBGPRINT(RT_DEBUG_TRACE, ("===> %s\n", __FUNCTION__));
33627 +
33628 + /* init */
33629 + pFirmwareImage = NULL;
33630 + src = RTMP_FIRMWARE_FILE_NAME;
33631 +
33632 + /* save uid and gid used for filesystem access.
33633 + set user and group to 0 (root) */
33634 + orgfsuid = current->fsuid;
33635 + orgfsgid = current->fsgid;
33636 + current->fsuid = current->fsgid = 0;
33637 + orgfs = get_fs();
33638 + set_fs(KERNEL_DS);
33639 +
33640 + pAd->FirmwareVersion = (FIRMWARE_MAJOR_VERSION << 8) + \
33641 + FIRMWARE_MINOR_VERSION;
33642 +
33643 +
33644 + /* allocate firmware buffer */
33645 + pFirmwareImage = kmalloc(MAX_FIRMWARE_IMAGE_SIZE, MEM_ALLOC_FLAG);
33646 + if (pFirmwareImage == NULL)
33647 + {
33648 + /* allocate fail, use default firmware array in firmware.h */
33649 + printk("%s - Allocate memory fail!\n", __FUNCTION__);
33650 + NICLF_DEFAULT_USE();
33651 + }
33652 + else
33653 + {
33654 + /* allocate ok! zero the firmware buffer */
33655 + memset(pFirmwareImage, 0x00, MAX_FIRMWARE_IMAGE_SIZE);
33656 + } /* End of if */
33657 +
33658 +
33659 + /* if ok, read firmware file from *.bin file */
33660 + if (flg_default_firm_use == FALSE)
33661 + {
33662 + do
33663 + {
33664 + /* open the bin file */
33665 + srcf = filp_open(src, O_RDONLY, 0);
33666 +
33667 + if (IS_ERR(srcf))
33668 + {
33669 + printk("%s - Error %ld opening %s\n",
33670 + __FUNCTION__, -PTR_ERR(srcf), src);
33671 + NICLF_DEFAULT_USE();
33672 + break;
33673 + } /* End of if */
33674 +
33675 + /* the object must have a read method */
33676 + if ((srcf->f_op == NULL) || (srcf->f_op->read == NULL))
33677 + {
33678 + printk("%s - %s does not have a write method\n", __FUNCTION__, src);
33679 + NICLF_DEFAULT_USE();
33680 + break;
33681 + } /* End of if */
33682 +
33683 + /* read the firmware from the file *.bin */
33684 + FileLength = srcf->f_op->read(srcf,
33685 + pFirmwareImage,
33686 + MAX_FIRMWARE_IMAGE_SIZE,
33687 + &srcf->f_pos);
33688 +
33689 + if (FileLength != MAX_FIRMWARE_IMAGE_SIZE)
33690 + {
33691 + printk("%s: error file length (=%d) in RT2860AP.BIN\n",
33692 + __FUNCTION__, FileLength);
33693 + NICLF_DEFAULT_USE();
33694 + break;
33695 + }
33696 + else
33697 + {
33698 + PUCHAR ptr = pFirmwareImage;
33699 + USHORT crc = 0xffff;
33700 +
33701 +
33702 + /* calculate firmware CRC */
33703 + for(i=0; i<(MAX_FIRMWARE_IMAGE_SIZE-2); i++, ptr++)
33704 + crc = ByteCRC16(BitReverse(*ptr), crc);
33705 + /* End of for */
33706 +
33707 + if ((pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-2] != \
33708 + (UCHAR)BitReverse((UCHAR)(crc>>8))) ||
33709 + (pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-1] != \
33710 + (UCHAR)BitReverse((UCHAR)crc)))
33711 + {
33712 + /* CRC fail */
33713 + printk("%s: CRC = 0x%02x 0x%02x "
33714 + "error, should be 0x%02x 0x%02x\n",
33715 + __FUNCTION__,
33716 + pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-2],
33717 + pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-1],
33718 + (UCHAR)(crc>>8), (UCHAR)(crc));
33719 + NICLF_DEFAULT_USE();
33720 + break;
33721 + }
33722 + else
33723 + {
33724 + /* firmware is ok */
33725 + pAd->FirmwareVersion = \
33726 + (pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-4] << 8) +
33727 + pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-3];
33728 +
33729 + /* check if firmware version of the file is too old */
33730 + if ((pAd->FirmwareVersion) < \
33731 + ((FIRMWARE_MAJOR_VERSION << 8) +
33732 + FIRMWARE_MINOR_VERSION))
33733 + {
33734 + printk("%s: firmware version too old!\n", __FUNCTION__);
33735 + NICLF_DEFAULT_USE();
33736 + break;
33737 + } /* End of if */
33738 + } /* End of if */
33739 +
33740 + DBGPRINT(RT_DEBUG_TRACE,
33741 + ("NICLoadFirmware: CRC ok, ver=%d.%d\n",
33742 + pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-4],
33743 + pFirmwareImage[MAX_FIRMWARE_IMAGE_SIZE-3]));
33744 + } /* End of if (FileLength == MAX_FIRMWARE_IMAGE_SIZE) */
33745 + break;
33746 + } while(TRUE);
33747 +
33748 + /* close firmware file */
33749 + if (IS_ERR(srcf))
33750 + ;
33751 + else
33752 + {
33753 + retval = filp_close(srcf, NULL);
33754 + if (retval)
33755 + {
33756 + DBGPRINT(RT_DEBUG_ERROR,
33757 + ("--> Error %d closing %s\n", -retval, src));
33758 + } /* End of if */
33759 + } /* End of if */
33760 + } /* End of if */
33761 +
33762 +
33763 + /* write firmware to ASIC */
33764 + if (flg_default_firm_use == TRUE)
33765 + {
33766 + /* use default fimeware, free allocated buffer */
33767 + if (pFirmwareImage != NULL)
33768 + kfree(pFirmwareImage);
33769 + /* End of if */
33770 +
33771 + /* use default *.bin array */
33772 + pFirmwareImage = FirmwareImage;
33773 + FileLength = sizeof(FirmwareImage);
33774 + } /* End of if */
33775 +
33776 + /* enable Host program ram write selection */
33777 + RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, 0x10000);
33778 +
33779 + for(i=0; i<FileLength; i+=4)
33780 + {
33781 + firm = pFirmwareImage[i] +
33782 + (pFirmwareImage[i+3] << 24) +
33783 + (pFirmwareImage[i+2] << 16) +
33784 + (pFirmwareImage[i+1] << 8);
33785 +
33786 + RTMP_IO_WRITE32(pAd, FIRMWARE_IMAGE_BASE + i, firm);
33787 + } /* End of for */
33788 +
33789 + RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, 0x00000);
33790 + RTMP_IO_WRITE32(pAd, PBF_SYS_CTRL, 0x00001);
33791 +
33792 + /* initialize BBP R/W access agent */
33793 + RTMP_IO_WRITE32(pAd, H2M_BBP_AGENT, 0);
33794 + RTMP_IO_WRITE32(pAd, H2M_MAILBOX_CSR, 0);
33795 +
33796 + if (flg_default_firm_use == FALSE)
33797 + {
33798 + /* use file firmware, free allocated buffer */
33799 + if (pFirmwareImage != NULL)
33800 + kfree(pFirmwareImage);
33801 + /* End of if */
33802 + } /* End of if */
33803 +
33804 + set_fs(orgfs);
33805 + current->fsuid = orgfsuid;
33806 + current->fsgid = orgfsgid;
33807 +#else
33808 +
33809 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
33810 + PUCHAR pFirmwareImage;
33811 + ULONG FileLength, Index;
33812 + //ULONG firm;
33813 + UINT32 MacReg = 0;
33814 +
33815 + pFirmwareImage = FirmwareImage;
33816 + FileLength = sizeof(FirmwareImage);
33817 + RT28XX_WRITE_FIRMWARE(pAd, pFirmwareImage, FileLength);
33818 +#endif
33819 +
33820 + /* check if MCU is ready */
33821 + Index = 0;
33822 + do
33823 + {
33824 + RTMP_IO_READ32(pAd, PBF_SYS_CTRL, &MacReg);
33825 +
33826 + if (MacReg & 0x80)
33827 + break;
33828 +
33829 + RTMPusecDelay(1000);
33830 + } while (Index++ < 1000);
33831 +
33832 + if (Index >= 1000)
33833 + {
33834 + Status = NDIS_STATUS_FAILURE;
33835 + DBGPRINT(RT_DEBUG_ERROR, ("NICLoadFirmware: MCU is not ready\n\n\n"));
33836 + } /* End of if */
33837 +
33838 + DBGPRINT(RT_DEBUG_TRACE,
33839 + ("<=== %s (status=%d)\n", __FUNCTION__, Status));
33840 + return Status;
33841 +} /* End of NICLoadFirmware */
33842 +
33843 +
33844 +/*
33845 + ========================================================================
33846 +
33847 + Routine Description:
33848 + Load Tx rate switching parameters
33849 +
33850 + Arguments:
33851 + Adapter Pointer to our adapter
33852 +
33853 + Return Value:
33854 + NDIS_STATUS_SUCCESS firmware image load ok
33855 + NDIS_STATUS_FAILURE image not found
33856 +
33857 + IRQL = PASSIVE_LEVEL
33858 +
33859 + Rate Table Format:
33860 + 1. (B0: Valid Item number) (B1:Initial item from zero)
33861 + 2. Item Number(Dec) Mode(Hex) Current MCS(Dec) TrainUp(Dec) TrainDown(Dec)
33862 +
33863 + ========================================================================
33864 +*/
33865 +NDIS_STATUS NICLoadRateSwitchingParams(
33866 + IN PRTMP_ADAPTER pAd)
33867 +{
33868 + return NDIS_STATUS_SUCCESS;
33869 +}
33870 +
33871 +/*
33872 + ========================================================================
33873 +
33874 + Routine Description:
33875 + if pSrc1 all zero with length Length, return 0.
33876 + If not all zero, return 1
33877 +
33878 + Arguments:
33879 + pSrc1
33880 +
33881 + Return Value:
33882 + 1: not all zero
33883 + 0: all zero
33884 +
33885 + IRQL = DISPATCH_LEVEL
33886 +
33887 + Note:
33888 +
33889 + ========================================================================
33890 +*/
33891 +ULONG RTMPNotAllZero(
33892 + IN PVOID pSrc1,
33893 + IN ULONG Length)
33894 +{
33895 + PUCHAR pMem1;
33896 + ULONG Index = 0;
33897 +
33898 + pMem1 = (PUCHAR) pSrc1;
33899 +
33900 + for (Index = 0; Index < Length; Index++)
33901 + {
33902 + if (pMem1[Index] != 0x0)
33903 + {
33904 + break;
33905 + }
33906 + }
33907 +
33908 + if (Index == Length)
33909 + {
33910 + return (0);
33911 + }
33912 + else
33913 + {
33914 + return (1);
33915 + }
33916 +}
33917 +
33918 +/*
33919 + ========================================================================
33920 +
33921 + Routine Description:
33922 + Compare two memory block
33923 +
33924 + Arguments:
33925 + pSrc1 Pointer to first memory address
33926 + pSrc2 Pointer to second memory address
33927 +
33928 + Return Value:
33929 + 0: memory is equal
33930 + 1: pSrc1 memory is larger
33931 + 2: pSrc2 memory is larger
33932 +
33933 + IRQL = DISPATCH_LEVEL
33934 +
33935 + Note:
33936 +
33937 + ========================================================================
33938 +*/
33939 +ULONG RTMPCompareMemory(
33940 + IN PVOID pSrc1,
33941 + IN PVOID pSrc2,
33942 + IN ULONG Length)
33943 +{
33944 + PUCHAR pMem1;
33945 + PUCHAR pMem2;
33946 + ULONG Index = 0;
33947 +
33948 + pMem1 = (PUCHAR) pSrc1;
33949 + pMem2 = (PUCHAR) pSrc2;
33950 +
33951 + for (Index = 0; Index < Length; Index++)
33952 + {
33953 + if (pMem1[Index] > pMem2[Index])
33954 + return (1);
33955 + else if (pMem1[Index] < pMem2[Index])
33956 + return (2);
33957 + }
33958 +
33959 + // Equal
33960 + return (0);
33961 +}
33962 +
33963 +/*
33964 + ========================================================================
33965 +
33966 + Routine Description:
33967 + Zero out memory block
33968 +
33969 + Arguments:
33970 + pSrc1 Pointer to memory address
33971 + Length Size
33972 +
33973 + Return Value:
33974 + None
33975 +
33976 + IRQL = PASSIVE_LEVEL
33977 + IRQL = DISPATCH_LEVEL
33978 +
33979 + Note:
33980 +
33981 + ========================================================================
33982 +*/
33983 +VOID RTMPZeroMemory(
33984 + IN PVOID pSrc,
33985 + IN ULONG Length)
33986 +{
33987 + PUCHAR pMem;
33988 + ULONG Index = 0;
33989 +
33990 + pMem = (PUCHAR) pSrc;
33991 +
33992 + for (Index = 0; Index < Length; Index++)
33993 + {
33994 + pMem[Index] = 0x00;
33995 + }
33996 +}
33997 +
33998 +VOID RTMPFillMemory(
33999 + IN PVOID pSrc,
34000 + IN ULONG Length,
34001 + IN UCHAR Fill)
34002 +{
34003 + PUCHAR pMem;
34004 + ULONG Index = 0;
34005 +
34006 + pMem = (PUCHAR) pSrc;
34007 +
34008 + for (Index = 0; Index < Length; Index++)
34009 + {
34010 + pMem[Index] = Fill;
34011 + }
34012 +}
34013 +
34014 +/*
34015 + ========================================================================
34016 +
34017 + Routine Description:
34018 + Copy data from memory block 1 to memory block 2
34019 +
34020 + Arguments:
34021 + pDest Pointer to destination memory address
34022 + pSrc Pointer to source memory address
34023 + Length Copy size
34024 +
34025 + Return Value:
34026 + None
34027 +
34028 + IRQL = PASSIVE_LEVEL
34029 + IRQL = DISPATCH_LEVEL
34030 +
34031 + Note:
34032 +
34033 + ========================================================================
34034 +*/
34035 +VOID RTMPMoveMemory(
34036 + OUT PVOID pDest,
34037 + IN PVOID pSrc,
34038 + IN ULONG Length)
34039 +{
34040 + PUCHAR pMem1;
34041 + PUCHAR pMem2;
34042 + UINT Index;
34043 +
34044 + ASSERT((Length==0) || (pDest && pSrc));
34045 +
34046 + pMem1 = (PUCHAR) pDest;
34047 + pMem2 = (PUCHAR) pSrc;
34048 +
34049 + for (Index = 0; Index < Length; Index++)
34050 + {
34051 + pMem1[Index] = pMem2[Index];
34052 + }
34053 +}
34054 +
34055 +/*
34056 + ========================================================================
34057 +
34058 + Routine Description:
34059 + Initialize port configuration structure
34060 +
34061 + Arguments:
34062 + Adapter Pointer to our adapter
34063 +
34064 + Return Value:
34065 + None
34066 +
34067 + IRQL = PASSIVE_LEVEL
34068 +
34069 + Note:
34070 +
34071 + ========================================================================
34072 +*/
34073 +VOID UserCfgInit(
34074 + IN PRTMP_ADAPTER pAd)
34075 +{
34076 + UINT key_index, bss_index;
34077 +
34078 + DBGPRINT(RT_DEBUG_TRACE, ("--> UserCfgInit\n"));
34079 +
34080 + //
34081 + // part I. intialize common configuration
34082 + //
34083 +
34084 + for(key_index=0; key_index<SHARE_KEY_NUM; key_index++)
34085 + {
34086 + for(bss_index = 0; bss_index < MAX_MBSSID_NUM; bss_index++)
34087 + {
34088 + pAd->SharedKey[bss_index][key_index].KeyLen = 0;
34089 + pAd->SharedKey[bss_index][key_index].CipherAlg = CIPHER_NONE;
34090 + }
34091 + }
34092 +
34093 + pAd->Antenna.word = 0;
34094 + pAd->CommonCfg.BBPCurrentBW = BW_20;
34095 +
34096 + pAd->LedCntl.word = 0;
34097 +#ifdef RT2860
34098 + pAd->LedIndicatorStregth = 0;
34099 + pAd->RLnkCtrlOffset = 0;
34100 + pAd->HostLnkCtrlOffset = 0;
34101 +#endif // RT2860 //
34102 +
34103 + pAd->bAutoTxAgcA = FALSE; // Default is OFF
34104 + pAd->bAutoTxAgcG = FALSE; // Default is OFF
34105 + pAd->RfIcType = RFIC_2820;
34106 +
34107 + // Init timer for reset complete event
34108 + pAd->CommonCfg.CentralChannel = 1;
34109 + pAd->bForcePrintTX = FALSE;
34110 + pAd->bForcePrintRX = FALSE;
34111 + pAd->bStaFifoTest = FALSE;
34112 + pAd->bProtectionTest = FALSE;
34113 + pAd->bHCCATest = FALSE;
34114 + pAd->bGenOneHCCA = FALSE;
34115 + pAd->CommonCfg.Dsifs = 10; // in units of usec
34116 + pAd->CommonCfg.TxPower = 100; //mW
34117 + pAd->CommonCfg.TxPowerPercentage = 0xffffffff; // AUTO
34118 + pAd->CommonCfg.TxPowerDefault = 0xffffffff; // AUTO
34119 + pAd->CommonCfg.TxPreamble = Rt802_11PreambleAuto; // use Long preamble on TX by defaut
34120 + pAd->CommonCfg.bUseZeroToDisableFragment = FALSE;
34121 + pAd->CommonCfg.RtsThreshold = 2347;
34122 + pAd->CommonCfg.FragmentThreshold = 2346;
34123 + pAd->CommonCfg.UseBGProtection = 0; // 0: AUTO
34124 + pAd->CommonCfg.bEnableTxBurst = TRUE; //0;
34125 + pAd->CommonCfg.PhyMode = 0xff; // unknown
34126 + pAd->CommonCfg.BandState = UNKNOWN_BAND;
34127 + pAd->CommonCfg.RadarDetect.CSPeriod = 10;
34128 + pAd->CommonCfg.RadarDetect.CSCount = 0;
34129 + pAd->CommonCfg.RadarDetect.RDMode = RD_NORMAL_MODE;
34130 + pAd->CommonCfg.RadarDetect.ChMovingTime = 65;
34131 + pAd->CommonCfg.RadarDetect.LongPulseRadarTh = 3;
34132 + pAd->CommonCfg.bAPSDCapable = FALSE;
34133 + pAd->CommonCfg.bNeedSendTriggerFrame = FALSE;
34134 + pAd->CommonCfg.TriggerTimerCount = 0;
34135 + pAd->CommonCfg.bAPSDForcePowerSave = FALSE;
34136 + pAd->CommonCfg.bCountryFlag = FALSE;
34137 + pAd->CommonCfg.TxStream = 0;
34138 + pAd->CommonCfg.RxStream = 0;
34139 +
34140 + NdisZeroMemory(&pAd->BeaconTxWI, sizeof(pAd->BeaconTxWI));
34141 +
34142 +#ifdef DOT11_N_SUPPORT
34143 + NdisZeroMemory(&pAd->CommonCfg.HtCapability, sizeof(pAd->CommonCfg.HtCapability));
34144 + pAd->HTCEnable = FALSE;
34145 + pAd->bBroadComHT = FALSE;
34146 + pAd->CommonCfg.bRdg = FALSE;
34147 +
34148 +#ifdef DOT11N_DRAFT3
34149 + pAd->CommonCfg.Dot11OBssScanPassiveDwell = dot11OBSSScanPassiveDwell; // Unit : TU. 5~1000
34150 + pAd->CommonCfg.Dot11OBssScanActiveDwell = dot11OBSSScanActiveDwell; // Unit : TU. 10~1000
34151 + pAd->CommonCfg.Dot11BssWidthTriggerScanInt = dot11BSSWidthTriggerScanInterval; // Unit : Second
34152 + pAd->CommonCfg.Dot11OBssScanPassiveTotalPerChannel = dot11OBSSScanPassiveTotalPerChannel; // Unit : TU. 200~10000
34153 + pAd->CommonCfg.Dot11OBssScanActiveTotalPerChannel = dot11OBSSScanActiveTotalPerChannel; // Unit : TU. 20~10000
34154 + pAd->CommonCfg.Dot11BssWidthChanTranDelayFactor = dot11BSSWidthChannelTransactionDelayFactor;
34155 + pAd->CommonCfg.Dot11OBssScanActivityThre = dot11BSSScanActivityThreshold; // Unit : percentage
34156 + pAd->CommonCfg.Dot11BssWidthChanTranDelay = (pAd->CommonCfg.Dot11BssWidthTriggerScanInt * pAd->CommonCfg.Dot11BssWidthChanTranDelayFactor);
34157 +#endif // DOT11N_DRAFT3 //
34158 +
34159 + NdisZeroMemory(&pAd->CommonCfg.AddHTInfo, sizeof(pAd->CommonCfg.AddHTInfo));
34160 + pAd->CommonCfg.BACapability.field.MMPSmode = MMPS_ENABLE;
34161 + pAd->CommonCfg.BACapability.field.MpduDensity = 0;
34162 + pAd->CommonCfg.BACapability.field.Policy = IMMED_BA;
34163 + pAd->CommonCfg.BACapability.field.RxBAWinLimit = 64; //32;
34164 + pAd->CommonCfg.BACapability.field.TxBAWinLimit = 64; //32;
34165 + DBGPRINT(RT_DEBUG_TRACE, ("--> UserCfgInit. BACapability = 0x%x\n", pAd->CommonCfg.BACapability.word));
34166 +
34167 + pAd->CommonCfg.BACapability.field.AutoBA = FALSE;
34168 + BATableInit(pAd, &pAd->BATable);
34169 +
34170 + pAd->CommonCfg.bExtChannelSwitchAnnouncement = 1;
34171 + pAd->CommonCfg.bHTProtect = 1;
34172 + pAd->CommonCfg.bMIMOPSEnable = TRUE;
34173 + pAd->CommonCfg.bBADecline = FALSE;
34174 + pAd->CommonCfg.bDisableReordering = FALSE;
34175 +
34176 + pAd->CommonCfg.TxBASize = 7;
34177 +
34178 + pAd->CommonCfg.REGBACapability.word = pAd->CommonCfg.BACapability.word;
34179 +#endif // DOT11_N_SUPPORT //
34180 +
34181 + //pAd->CommonCfg.HTPhyMode.field.BW = BW_20;
34182 + //pAd->CommonCfg.HTPhyMode.field.MCS = MCS_AUTO;
34183 + //pAd->CommonCfg.HTPhyMode.field.ShortGI = GI_800;
34184 + //pAd->CommonCfg.HTPhyMode.field.STBC = STBC_NONE;
34185 + pAd->CommonCfg.TxRate = RATE_6;
34186 +
34187 + pAd->CommonCfg.MlmeTransmit.field.MCS = MCS_RATE_6;
34188 + pAd->CommonCfg.MlmeTransmit.field.BW = BW_20;
34189 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_OFDM;
34190 +
34191 + pAd->CommonCfg.BeaconPeriod = 100; // in mSec
34192 +
34193 + //
34194 + // part II. intialize STA specific configuration
34195 + //
34196 +#ifdef CONFIG_STA_SUPPORT
34197 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
34198 + {
34199 + RX_FILTER_SET_FLAG(pAd, fRX_FILTER_ACCEPT_DIRECT);
34200 + RX_FILTER_CLEAR_FLAG(pAd, fRX_FILTER_ACCEPT_MULTICAST);
34201 + RX_FILTER_SET_FLAG(pAd, fRX_FILTER_ACCEPT_BROADCAST);
34202 + RX_FILTER_SET_FLAG(pAd, fRX_FILTER_ACCEPT_ALL_MULTICAST);
34203 +
34204 + pAd->StaCfg.Psm = PWR_ACTIVE;
34205 +
34206 + pAd->StaCfg.OrigWepStatus = Ndis802_11EncryptionDisabled;
34207 + pAd->StaCfg.PairCipher = Ndis802_11EncryptionDisabled;
34208 + pAd->StaCfg.GroupCipher = Ndis802_11EncryptionDisabled;
34209 + pAd->StaCfg.bMixCipher = FALSE;
34210 + pAd->StaCfg.DefaultKeyId = 0;
34211 +
34212 + // 802.1x port control
34213 + pAd->StaCfg.PrivacyFilter = Ndis802_11PrivFilter8021xWEP;
34214 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
34215 + pAd->StaCfg.LastMicErrorTime = 0;
34216 + pAd->StaCfg.MicErrCnt = 0;
34217 + pAd->StaCfg.bBlockAssoc = FALSE;
34218 + pAd->StaCfg.WpaState = SS_NOTUSE;
34219 +
34220 + pAd->CommonCfg.NdisRadioStateOff = FALSE; // New to support microsoft disable radio with OID command
34221 +
34222 + pAd->StaCfg.RssiTrigger = 0;
34223 + NdisZeroMemory(&pAd->StaCfg.RssiSample, sizeof(RSSI_SAMPLE));
34224 + pAd->StaCfg.RssiTriggerMode = RSSI_TRIGGERED_UPON_BELOW_THRESHOLD;
34225 + pAd->StaCfg.AtimWin = 0;
34226 + pAd->StaCfg.DefaultListenCount = 3;//default listen count;
34227 + pAd->StaCfg.BssType = BSS_INFRA; // BSS_INFRA or BSS_ADHOC or BSS_MONITOR
34228 + pAd->StaCfg.bScanReqIsFromWebUI = FALSE;
34229 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
34230 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_WAKEUP_NOW);
34231 +
34232 + pAd->StaCfg.bAutoTxRateSwitch = TRUE;
34233 + pAd->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
34234 + }
34235 +
34236 +#ifdef EXT_BUILD_CHANNEL_LIST
34237 + pAd->StaCfg.IEEE80211dClientMode = Rt802_11_D_None;
34238 +#endif // EXT_BUILD_CHANNEL_LIST //
34239 +#endif // CONFIG_STA_SUPPORT //
34240 +
34241 + // global variables mXXXX used in MAC protocol state machines
34242 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM);
34243 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_ADHOC_ON);
34244 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_INFRA_ON);
34245 +
34246 + // PHY specification
34247 + pAd->CommonCfg.PhyMode = PHY_11BG_MIXED; // default PHY mode
34248 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED); // CCK use LONG preamble
34249 +
34250 +#ifdef CONFIG_STA_SUPPORT
34251 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
34252 + {
34253 + // user desired power mode
34254 + pAd->StaCfg.WindowsPowerMode = Ndis802_11PowerModeCAM;
34255 + pAd->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeCAM;
34256 + pAd->StaCfg.bWindowsACCAMEnable = FALSE;
34257 +
34258 +#ifdef LEAP_SUPPORT
34259 + // CCX v1.0 releated init value
34260 + RTMPInitTimer(pAd, &pAd->StaCfg.LeapAuthTimer, GET_TIMER_FUNCTION(LeapAuthTimeout), pAd, FALSE);
34261 + pAd->StaCfg.LeapAuthMode = CISCO_AuthModeLEAPNone;
34262 + pAd->StaCfg.bCkipOn = FALSE;
34263 +#endif // LEAP_SUPPORT //
34264 +
34265 + RTMPInitTimer(pAd, &pAd->StaCfg.StaQuickResponeForRateUpTimer, GET_TIMER_FUNCTION(StaQuickResponeForRateUpExec), pAd, FALSE);
34266 + pAd->StaCfg.StaQuickResponeForRateUpTimerRunning = FALSE;
34267 +
34268 + // Patch for Ndtest
34269 + pAd->StaCfg.ScanCnt = 0;
34270 +
34271 + // CCX 2.0 control flag init
34272 + pAd->StaCfg.CCXEnable = FALSE;
34273 + pAd->StaCfg.CCXReqType = MSRN_TYPE_UNUSED;
34274 + pAd->StaCfg.CCXQosECWMin = 4;
34275 + pAd->StaCfg.CCXQosECWMax = 10;
34276 +
34277 + pAd->StaCfg.bHwRadio = TRUE; // Default Hardware Radio status is On
34278 + pAd->StaCfg.bSwRadio = TRUE; // Default Software Radio status is On
34279 + pAd->StaCfg.bRadio = TRUE; // bHwRadio && bSwRadio
34280 + pAd->StaCfg.bHardwareRadio = FALSE; // Default is OFF
34281 + pAd->StaCfg.bShowHiddenSSID = FALSE; // Default no show
34282 +
34283 + // Nitro mode control
34284 + pAd->StaCfg.bAutoReconnect = TRUE;
34285 +
34286 + // Save the init time as last scan time, the system should do scan after 2 seconds.
34287 + // This patch is for driver wake up from standby mode, system will do scan right away.
34288 + pAd->StaCfg.LastScanTime = 0;
34289 + NdisZeroMemory(pAd->nickname, IW_ESSID_MAX_SIZE+1);
34290 + sprintf(pAd->nickname, "%s", STA_NIC_DEVICE_NAME);
34291 + RTMPInitTimer(pAd, &pAd->StaCfg.WpaDisassocAndBlockAssocTimer, GET_TIMER_FUNCTION(WpaDisassocApAndBlockAssoc), pAd, FALSE);
34292 +#ifdef WPA_SUPPLICANT_SUPPORT
34293 + pAd->StaCfg.IEEE8021X = FALSE;
34294 + pAd->StaCfg.IEEE8021x_required_keys = FALSE;
34295 + pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_DISABLE;
34296 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
34297 + pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_ENABLE;
34298 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
34299 +#endif // WPA_SUPPLICANT_SUPPORT //
34300 +
34301 + }
34302 +#endif // CONFIG_STA_SUPPORT //
34303 +
34304 + // Default for extra information is not valid
34305 + pAd->ExtraInfo = EXTRA_INFO_CLEAR;
34306 +
34307 + // Default Config change flag
34308 + pAd->bConfigChanged = FALSE;
34309 +
34310 + //
34311 + // part III. AP configurations
34312 + //
34313 +
34314 +
34315 + //
34316 + // part IV. others
34317 + //
34318 + // dynamic BBP R66:sensibity tuning to overcome background noise
34319 + pAd->BbpTuning.bEnable = TRUE;
34320 + pAd->BbpTuning.FalseCcaLowerThreshold = 100;
34321 + pAd->BbpTuning.FalseCcaUpperThreshold = 512;
34322 + pAd->BbpTuning.R66Delta = 4;
34323 + pAd->Mlme.bEnableAutoAntennaCheck = TRUE;
34324 +
34325 + //
34326 + // Also initial R66CurrentValue, RTUSBResumeMsduTransmission might use this value.
34327 + // if not initial this value, the default value will be 0.
34328 + //
34329 + pAd->BbpTuning.R66CurrentValue = 0x38;
34330 +
34331 + pAd->Bbp94 = BBPR94_DEFAULT;
34332 + pAd->BbpForCCK = FALSE;
34333 +
34334 + // initialize MAC table and allocate spin lock
34335 + NdisZeroMemory(&pAd->MacTab, sizeof(MAC_TABLE));
34336 + InitializeQueueHeader(&pAd->MacTab.McastPsQueue);
34337 + NdisAllocateSpinLock(&pAd->MacTabLock);
34338 +
34339 +#ifdef RALINK_ATE
34340 + NdisZeroMemory(&pAd->ate, sizeof(ATE_INFO));
34341 + pAd->ate.Mode = ATE_STOP;
34342 + pAd->ate.TxCount = 200;/* to exceed TX_RING_SIZE ... */
34343 + pAd->ate.TxLength = 1024;
34344 + pAd->ate.TxWI.ShortGI = 0;// LONG GI : 800 ns
34345 + pAd->ate.TxWI.PHYMODE = MODE_CCK;
34346 + pAd->ate.TxWI.MCS = 3;
34347 + pAd->ate.TxWI.BW = BW_20;
34348 + pAd->ate.Channel = 1;
34349 + pAd->ate.QID = QID_AC_BE;
34350 + pAd->ate.Addr1[0] = 0x00;
34351 + pAd->ate.Addr1[1] = 0x11;
34352 + pAd->ate.Addr1[2] = 0x22;
34353 + pAd->ate.Addr1[3] = 0xAA;
34354 + pAd->ate.Addr1[4] = 0xBB;
34355 + pAd->ate.Addr1[5] = 0xCC;
34356 + NdisMoveMemory(pAd->ate.Addr2, pAd->ate.Addr1, ETH_LENGTH_OF_ADDRESS);
34357 + NdisMoveMemory(pAd->ate.Addr3, pAd->ate.Addr1, ETH_LENGTH_OF_ADDRESS);
34358 + pAd->ate.bRxFer = 0;
34359 + pAd->ate.bQATxStart = FALSE;
34360 + pAd->ate.bQARxStart = FALSE;
34361 +#ifdef RT2860
34362 + pAd->ate.bFWLoading = FALSE;
34363 +#endif // RT2860 //
34364 +#ifdef RALINK_28xx_QA
34365 + //pAd->ate.Repeat = 0;
34366 + pAd->ate.TxStatus = 0;
34367 + pAd->ate.AtePid = THREAD_PID_INIT_VALUE;
34368 +#endif // RALINK_28xx_QA //
34369 +#endif // RALINK_ATE //
34370 +
34371 +
34372 + pAd->CommonCfg.bWiFiTest = FALSE;
34373 +#ifdef RT2860
34374 + pAd->bPCIclkOff = FALSE;
34375 +#endif // RT2860 //
34376 +
34377 +
34378 + DBGPRINT(RT_DEBUG_TRACE, ("<-- UserCfgInit\n"));
34379 +}
34380 +
34381 +// IRQL = PASSIVE_LEVEL
34382 +UCHAR BtoH(char ch)
34383 +{
34384 + if (ch >= '0' && ch <= '9') return (ch - '0'); // Handle numerals
34385 + if (ch >= 'A' && ch <= 'F') return (ch - 'A' + 0xA); // Handle capitol hex digits
34386 + if (ch >= 'a' && ch <= 'f') return (ch - 'a' + 0xA); // Handle small hex digits
34387 + return(255);
34388 +}
34389 +
34390 +//
34391 +// FUNCTION: AtoH(char *, UCHAR *, int)
34392 +//
34393 +// PURPOSE: Converts ascii string to network order hex
34394 +//
34395 +// PARAMETERS:
34396 +// src - pointer to input ascii string
34397 +// dest - pointer to output hex
34398 +// destlen - size of dest
34399 +//
34400 +// COMMENTS:
34401 +//
34402 +// 2 ascii bytes make a hex byte so must put 1st ascii byte of pair
34403 +// into upper nibble and 2nd ascii byte of pair into lower nibble.
34404 +//
34405 +// IRQL = PASSIVE_LEVEL
34406 +
34407 +void AtoH(char * src, UCHAR * dest, int destlen)
34408 +{
34409 + char * srcptr;
34410 + PUCHAR destTemp;
34411 +
34412 + srcptr = src;
34413 + destTemp = (PUCHAR) dest;
34414 +
34415 + while(destlen--)
34416 + {
34417 + *destTemp = BtoH(*srcptr++) << 4; // Put 1st ascii byte in upper nibble.
34418 + *destTemp += BtoH(*srcptr++); // Add 2nd ascii byte to above.
34419 + destTemp++;
34420 + }
34421 +}
34422 +
34423 +VOID RTMPPatchMacBbpBug(
34424 + IN PRTMP_ADAPTER pAd)
34425 +{
34426 + ULONG Index;
34427 +
34428 + // Initialize BBP register to default value
34429 + for (Index = 0; Index < NUM_BBP_REG_PARMS; Index++)
34430 + {
34431 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBPRegTable[Index].Register, (UCHAR)BBPRegTable[Index].Value);
34432 + }
34433 +
34434 + // Initialize RF register to default value
34435 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
34436 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
34437 +
34438 + // Re-init BBP register from EEPROM value
34439 + NICInitAsicFromEEPROM(pAd);
34440 +}
34441 +
34442 +/*
34443 + ========================================================================
34444 +
34445 + Routine Description:
34446 + Init timer objects
34447 +
34448 + Arguments:
34449 + pAd Pointer to our adapter
34450 + pTimer Timer structure
34451 + pTimerFunc Function to execute when timer expired
34452 + Repeat Ture for period timer
34453 +
34454 + Return Value:
34455 + None
34456 +
34457 + Note:
34458 +
34459 + ========================================================================
34460 +*/
34461 +VOID RTMPInitTimer(
34462 + IN PRTMP_ADAPTER pAd,
34463 + IN PRALINK_TIMER_STRUCT pTimer,
34464 + IN PVOID pTimerFunc,
34465 + IN PVOID pData,
34466 + IN BOOLEAN Repeat)
34467 +{
34468 + //
34469 + // Set Valid to TRUE for later used.
34470 + // It will crash if we cancel a timer or set a timer
34471 + // that we haven't initialize before.
34472 + //
34473 + pTimer->Valid = TRUE;
34474 +
34475 + pTimer->PeriodicType = Repeat;
34476 + pTimer->State = FALSE;
34477 + pTimer->cookie = (ULONG) pData;
34478 +
34479 +
34480 + RTMP_OS_Init_Timer(pAd, &pTimer->TimerObj, pTimerFunc, (PVOID) pTimer);
34481 +}
34482 +
34483 +/*
34484 + ========================================================================
34485 +
34486 + Routine Description:
34487 + Init timer objects
34488 +
34489 + Arguments:
34490 + pTimer Timer structure
34491 + Value Timer value in milliseconds
34492 +
34493 + Return Value:
34494 + None
34495 +
34496 + Note:
34497 + To use this routine, must call RTMPInitTimer before.
34498 +
34499 + ========================================================================
34500 +*/
34501 +VOID RTMPSetTimer(
34502 + IN PRALINK_TIMER_STRUCT pTimer,
34503 + IN ULONG Value)
34504 +{
34505 + if (pTimer->Valid)
34506 + {
34507 + pTimer->TimerValue = Value;
34508 + pTimer->State = FALSE;
34509 + if (pTimer->PeriodicType == TRUE)
34510 + {
34511 + pTimer->Repeat = TRUE;
34512 + RTMP_SetPeriodicTimer(&pTimer->TimerObj, Value);
34513 + }
34514 + else
34515 + {
34516 + pTimer->Repeat = FALSE;
34517 + RTMP_OS_Add_Timer(&pTimer->TimerObj, Value);
34518 + }
34519 + }
34520 + else
34521 + {
34522 + DBGPRINT_ERR(("RTMPSetTimer failed, Timer hasn't been initialize!\n"));
34523 + }
34524 +}
34525 +
34526 +
34527 +/*
34528 + ========================================================================
34529 +
34530 + Routine Description:
34531 + Init timer objects
34532 +
34533 + Arguments:
34534 + pTimer Timer structure
34535 + Value Timer value in milliseconds
34536 +
34537 + Return Value:
34538 + None
34539 +
34540 + Note:
34541 + To use this routine, must call RTMPInitTimer before.
34542 +
34543 + ========================================================================
34544 +*/
34545 +VOID RTMPModTimer(
34546 + IN PRALINK_TIMER_STRUCT pTimer,
34547 + IN ULONG Value)
34548 +{
34549 + BOOLEAN Cancel;
34550 +
34551 + if (pTimer->Valid)
34552 + {
34553 + pTimer->TimerValue = Value;
34554 + pTimer->State = FALSE;
34555 + if (pTimer->PeriodicType == TRUE)
34556 + {
34557 + RTMPCancelTimer(pTimer, &Cancel);
34558 + RTMPSetTimer(pTimer, Value);
34559 + }
34560 + else
34561 + {
34562 + RTMP_OS_Mod_Timer(&pTimer->TimerObj, Value);
34563 + }
34564 + }
34565 + else
34566 + {
34567 + DBGPRINT_ERR(("RTMPModTimer failed, Timer hasn't been initialize!\n"));
34568 + }
34569 +}
34570 +
34571 +/*
34572 + ========================================================================
34573 +
34574 + Routine Description:
34575 + Cancel timer objects
34576 +
34577 + Arguments:
34578 + Adapter Pointer to our adapter
34579 +
34580 + Return Value:
34581 + None
34582 +
34583 + IRQL = PASSIVE_LEVEL
34584 + IRQL = DISPATCH_LEVEL
34585 +
34586 + Note:
34587 + 1.) To use this routine, must call RTMPInitTimer before.
34588 + 2.) Reset NIC to initial state AS IS system boot up time.
34589 +
34590 + ========================================================================
34591 +*/
34592 +VOID RTMPCancelTimer(
34593 + IN PRALINK_TIMER_STRUCT pTimer,
34594 + OUT BOOLEAN *pCancelled)
34595 +{
34596 + if (pTimer->Valid)
34597 + {
34598 + if (pTimer->State == FALSE)
34599 + pTimer->Repeat = FALSE;
34600 + RTMP_OS_Del_Timer(&pTimer->TimerObj, pCancelled);
34601 +
34602 + if (*pCancelled == TRUE)
34603 + pTimer->State = TRUE;
34604 +
34605 + }
34606 + else
34607 + {
34608 + //
34609 + // NdisMCancelTimer just canced the timer and not mean release the timer.
34610 + // And don't set the "Valid" to False. So that we can use this timer again.
34611 + //
34612 + DBGPRINT_ERR(("RTMPCancelTimer failed, Timer hasn't been initialize!\n"));
34613 + }
34614 +}
34615 +
34616 +/*
34617 + ========================================================================
34618 +
34619 + Routine Description:
34620 + Set LED Status
34621 +
34622 + Arguments:
34623 + pAd Pointer to our adapter
34624 + Status LED Status
34625 +
34626 + Return Value:
34627 + None
34628 +
34629 + IRQL = PASSIVE_LEVEL
34630 + IRQL = DISPATCH_LEVEL
34631 +
34632 + Note:
34633 +
34634 + ========================================================================
34635 +*/
34636 +VOID RTMPSetLED(
34637 + IN PRTMP_ADAPTER pAd,
34638 + IN UCHAR Status)
34639 +{
34640 + //ULONG data;
34641 + UCHAR HighByte = 0;
34642 + UCHAR LowByte;
34643 +
34644 +// In ATE mode of RT2860 AP/STA, we have erased 8051 firmware.
34645 +// So LED mode is not supported when ATE is running.
34646 +#ifdef RALINK_ATE
34647 + if (ATE_ON(pAd))
34648 + return;
34649 +#endif // RALINK_ATE //
34650 +
34651 + LowByte = pAd->LedCntl.field.LedMode&0x7f;
34652 + switch (Status)
34653 + {
34654 + case LED_LINK_DOWN:
34655 + HighByte = 0x20;
34656 + AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
34657 + pAd->LedIndicatorStregth = 0;
34658 + break;
34659 + case LED_LINK_UP:
34660 + if (pAd->CommonCfg.Channel > 14)
34661 + HighByte = 0xa0;
34662 + else
34663 + HighByte = 0x60;
34664 + AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
34665 + break;
34666 + case LED_RADIO_ON:
34667 + HighByte = 0x20;
34668 + AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
34669 + break;
34670 + case LED_HALT:
34671 + LowByte = 0; // Driver sets MAC register and MAC controls LED
34672 + case LED_RADIO_OFF:
34673 + HighByte = 0;
34674 + AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
34675 + break;
34676 + case LED_WPS:
34677 + HighByte = 0x10;
34678 + AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
34679 + break;
34680 + case LED_ON_SITE_SURVEY:
34681 + HighByte = 0x08;
34682 + AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
34683 + break;
34684 + case LED_POWER_UP:
34685 + HighByte = 0x04;
34686 + AsicSendCommandToMcu(pAd, 0x50, 0xff, LowByte, HighByte);
34687 + break;
34688 + default:
34689 + DBGPRINT(RT_DEBUG_WARN, ("RTMPSetLED::Unknown Status %d\n", Status));
34690 + break;
34691 + }
34692 +
34693 + //
34694 + // Keep LED status for LED SiteSurvey mode.
34695 + // After SiteSurvey, we will set the LED mode to previous status.
34696 + //
34697 + if ((Status != LED_ON_SITE_SURVEY) && (Status != LED_POWER_UP))
34698 + pAd->LedStatus = Status;
34699 +
34700 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetLED::Mode=%d,HighByte=0x%02x,LowByte=0x%02x\n", pAd->LedCntl.field.LedMode, HighByte, LowByte));
34701 +}
34702 +
34703 +/*
34704 + ========================================================================
34705 +
34706 + Routine Description:
34707 + Set LED Signal Stregth
34708 +
34709 + Arguments:
34710 + pAd Pointer to our adapter
34711 + Dbm Signal Stregth
34712 +
34713 + Return Value:
34714 + None
34715 +
34716 + IRQL = PASSIVE_LEVEL
34717 +
34718 + Note:
34719 + Can be run on any IRQL level.
34720 +
34721 + According to Microsoft Zero Config Wireless Signal Stregth definition as belows.
34722 + <= -90 No Signal
34723 + <= -81 Very Low
34724 + <= -71 Low
34725 + <= -67 Good
34726 + <= -57 Very Good
34727 + > -57 Excellent
34728 + ========================================================================
34729 +*/
34730 +VOID RTMPSetSignalLED(
34731 + IN PRTMP_ADAPTER pAd,
34732 + IN NDIS_802_11_RSSI Dbm)
34733 +{
34734 + UCHAR nLed = 0;
34735 +
34736 + //
34737 + // if not Signal Stregth, then do nothing.
34738 + //
34739 + if (pAd->LedCntl.field.LedMode != LED_MODE_SIGNAL_STREGTH)
34740 + {
34741 + return;
34742 + }
34743 +
34744 + if (Dbm <= -90)
34745 + nLed = 0;
34746 + else if (Dbm <= -81)
34747 + nLed = 1;
34748 + else if (Dbm <= -71)
34749 + nLed = 3;
34750 + else if (Dbm <= -67)
34751 + nLed = 7;
34752 + else if (Dbm <= -57)
34753 + nLed = 15;
34754 + else
34755 + nLed = 31;
34756 +
34757 + //
34758 + // Update Signal Stregth to firmware if changed.
34759 + //
34760 + if (pAd->LedIndicatorStregth != nLed)
34761 + {
34762 + AsicSendCommandToMcu(pAd, 0x51, 0xff, nLed, pAd->LedCntl.field.Polarity);
34763 + pAd->LedIndicatorStregth = nLed;
34764 + }
34765 +}
34766 +
34767 +/*
34768 + ========================================================================
34769 +
34770 + Routine Description:
34771 + Enable RX
34772 +
34773 + Arguments:
34774 + pAd Pointer to our adapter
34775 +
34776 + Return Value:
34777 + None
34778 +
34779 + IRQL <= DISPATCH_LEVEL
34780 +
34781 + Note:
34782 + Before Enable RX, make sure you have enabled Interrupt.
34783 + ========================================================================
34784 +*/
34785 +VOID RTMPEnableRxTx(
34786 + IN PRTMP_ADAPTER pAd)
34787 +{
34788 + DBGPRINT(RT_DEBUG_TRACE, ("==> RTMPEnableRxTx\n"));
34789 +
34790 + // Enable Rx DMA.
34791 + RT28XXDMAEnable(pAd);
34792 +
34793 + // enable RX of MAC block
34794 + if (pAd->OpMode == OPMODE_AP)
34795 + {
34796 + UINT32 rx_filter_flag = APNORMAL;
34797 +
34798 +
34799 + RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, rx_filter_flag); // enable RX of DMA block
34800 + }
34801 + else
34802 + {
34803 + RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, STANORMAL); // Staion not drop control frame will fail WiFi Certification.
34804 + }
34805 +
34806 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0xc);
34807 + DBGPRINT(RT_DEBUG_TRACE, ("<== RTMPEnableRxTx\n"));
34808 +}
34809 +
34810 +
34811 --- /dev/null
34812 +++ b/drivers/staging/rt2860/common/rtmp_tkip.c
34813 @@ -0,0 +1,1607 @@
34814 +/*
34815 + *************************************************************************
34816 + * Ralink Tech Inc.
34817 + * 5F., No.36, Taiyuan St., Jhubei City,
34818 + * Hsinchu County 302,
34819 + * Taiwan, R.O.C.
34820 + *
34821 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
34822 + *
34823 + * This program is free software; you can redistribute it and/or modify *
34824 + * it under the terms of the GNU General Public License as published by *
34825 + * the Free Software Foundation; either version 2 of the License, or *
34826 + * (at your option) any later version. *
34827 + * *
34828 + * This program is distributed in the hope that it will be useful, *
34829 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
34830 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
34831 + * GNU General Public License for more details. *
34832 + * *
34833 + * You should have received a copy of the GNU General Public License *
34834 + * along with this program; if not, write to the *
34835 + * Free Software Foundation, Inc., *
34836 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
34837 + * *
34838 + *************************************************************************
34839 +
34840 + Module Name:
34841 + rtmp_tkip.c
34842 +
34843 + Abstract:
34844 +
34845 + Revision History:
34846 + Who When What
34847 + -------- ---------- ----------------------------------------------
34848 + Paul Wu 02-25-02 Initial
34849 +*/
34850 +
34851 +#include "../rt_config.h"
34852 +
34853 +// Rotation functions on 32 bit values
34854 +#define ROL32( A, n ) \
34855 + ( ((A) << (n)) | ( ((A)>>(32-(n))) & ( (1UL << (n)) - 1 ) ) )
34856 +#define ROR32( A, n ) ROL32( (A), 32-(n) )
34857 +
34858 +UINT Tkip_Sbox_Lower[256] =
34859 +{
34860 + 0xA5,0x84,0x99,0x8D,0x0D,0xBD,0xB1,0x54,
34861 + 0x50,0x03,0xA9,0x7D,0x19,0x62,0xE6,0x9A,
34862 + 0x45,0x9D,0x40,0x87,0x15,0xEB,0xC9,0x0B,
34863 + 0xEC,0x67,0xFD,0xEA,0xBF,0xF7,0x96,0x5B,
34864 + 0xC2,0x1C,0xAE,0x6A,0x5A,0x41,0x02,0x4F,
34865 + 0x5C,0xF4,0x34,0x08,0x93,0x73,0x53,0x3F,
34866 + 0x0C,0x52,0x65,0x5E,0x28,0xA1,0x0F,0xB5,
34867 + 0x09,0x36,0x9B,0x3D,0x26,0x69,0xCD,0x9F,
34868 + 0x1B,0x9E,0x74,0x2E,0x2D,0xB2,0xEE,0xFB,
34869 + 0xF6,0x4D,0x61,0xCE,0x7B,0x3E,0x71,0x97,
34870 + 0xF5,0x68,0x00,0x2C,0x60,0x1F,0xC8,0xED,
34871 + 0xBE,0x46,0xD9,0x4B,0xDE,0xD4,0xE8,0x4A,
34872 + 0x6B,0x2A,0xE5,0x16,0xC5,0xD7,0x55,0x94,
34873 + 0xCF,0x10,0x06,0x81,0xF0,0x44,0xBA,0xE3,
34874 + 0xF3,0xFE,0xC0,0x8A,0xAD,0xBC,0x48,0x04,
34875 + 0xDF,0xC1,0x75,0x63,0x30,0x1A,0x0E,0x6D,
34876 + 0x4C,0x14,0x35,0x2F,0xE1,0xA2,0xCC,0x39,
34877 + 0x57,0xF2,0x82,0x47,0xAC,0xE7,0x2B,0x95,
34878 + 0xA0,0x98,0xD1,0x7F,0x66,0x7E,0xAB,0x83,
34879 + 0xCA,0x29,0xD3,0x3C,0x79,0xE2,0x1D,0x76,
34880 + 0x3B,0x56,0x4E,0x1E,0xDB,0x0A,0x6C,0xE4,
34881 + 0x5D,0x6E,0xEF,0xA6,0xA8,0xA4,0x37,0x8B,
34882 + 0x32,0x43,0x59,0xB7,0x8C,0x64,0xD2,0xE0,
34883 + 0xB4,0xFA,0x07,0x25,0xAF,0x8E,0xE9,0x18,
34884 + 0xD5,0x88,0x6F,0x72,0x24,0xF1,0xC7,0x51,
34885 + 0x23,0x7C,0x9C,0x21,0xDD,0xDC,0x86,0x85,
34886 + 0x90,0x42,0xC4,0xAA,0xD8,0x05,0x01,0x12,
34887 + 0xA3,0x5F,0xF9,0xD0,0x91,0x58,0x27,0xB9,
34888 + 0x38,0x13,0xB3,0x33,0xBB,0x70,0x89,0xA7,
34889 + 0xB6,0x22,0x92,0x20,0x49,0xFF,0x78,0x7A,
34890 + 0x8F,0xF8,0x80,0x17,0xDA,0x31,0xC6,0xB8,
34891 + 0xC3,0xB0,0x77,0x11,0xCB,0xFC,0xD6,0x3A
34892 +};
34893 +
34894 +UINT Tkip_Sbox_Upper[256] =
34895 +{
34896 + 0xC6,0xF8,0xEE,0xF6,0xFF,0xD6,0xDE,0x91,
34897 + 0x60,0x02,0xCE,0x56,0xE7,0xB5,0x4D,0xEC,
34898 + 0x8F,0x1F,0x89,0xFA,0xEF,0xB2,0x8E,0xFB,
34899 + 0x41,0xB3,0x5F,0x45,0x23,0x53,0xE4,0x9B,
34900 + 0x75,0xE1,0x3D,0x4C,0x6C,0x7E,0xF5,0x83,
34901 + 0x68,0x51,0xD1,0xF9,0xE2,0xAB,0x62,0x2A,
34902 + 0x08,0x95,0x46,0x9D,0x30,0x37,0x0A,0x2F,
34903 + 0x0E,0x24,0x1B,0xDF,0xCD,0x4E,0x7F,0xEA,
34904 + 0x12,0x1D,0x58,0x34,0x36,0xDC,0xB4,0x5B,
34905 + 0xA4,0x76,0xB7,0x7D,0x52,0xDD,0x5E,0x13,
34906 + 0xA6,0xB9,0x00,0xC1,0x40,0xE3,0x79,0xB6,
34907 + 0xD4,0x8D,0x67,0x72,0x94,0x98,0xB0,0x85,
34908 + 0xBB,0xC5,0x4F,0xED,0x86,0x9A,0x66,0x11,
34909 + 0x8A,0xE9,0x04,0xFE,0xA0,0x78,0x25,0x4B,
34910 + 0xA2,0x5D,0x80,0x05,0x3F,0x21,0x70,0xF1,
34911 + 0x63,0x77,0xAF,0x42,0x20,0xE5,0xFD,0xBF,
34912 + 0x81,0x18,0x26,0xC3,0xBE,0x35,0x88,0x2E,
34913 + 0x93,0x55,0xFC,0x7A,0xC8,0xBA,0x32,0xE6,
34914 + 0xC0,0x19,0x9E,0xA3,0x44,0x54,0x3B,0x0B,
34915 + 0x8C,0xC7,0x6B,0x28,0xA7,0xBC,0x16,0xAD,
34916 + 0xDB,0x64,0x74,0x14,0x92,0x0C,0x48,0xB8,
34917 + 0x9F,0xBD,0x43,0xC4,0x39,0x31,0xD3,0xF2,
34918 + 0xD5,0x8B,0x6E,0xDA,0x01,0xB1,0x9C,0x49,
34919 + 0xD8,0xAC,0xF3,0xCF,0xCA,0xF4,0x47,0x10,
34920 + 0x6F,0xF0,0x4A,0x5C,0x38,0x57,0x73,0x97,
34921 + 0xCB,0xA1,0xE8,0x3E,0x96,0x61,0x0D,0x0F,
34922 + 0xE0,0x7C,0x71,0xCC,0x90,0x06,0xF7,0x1C,
34923 + 0xC2,0x6A,0xAE,0x69,0x17,0x99,0x3A,0x27,
34924 + 0xD9,0xEB,0x2B,0x22,0xD2,0xA9,0x07,0x33,
34925 + 0x2D,0x3C,0x15,0xC9,0x87,0xAA,0x50,0xA5,
34926 + 0x03,0x59,0x09,0x1A,0x65,0xD7,0x84,0xD0,
34927 + 0x82,0x29,0x5A,0x1E,0x7B,0xA8,0x6D,0x2C
34928 +};
34929 +
34930 +/*****************************/
34931 +/******** SBOX Table *********/
34932 +/*****************************/
34933 +
34934 +UCHAR SboxTable[256] =
34935 +{
34936 + 0x63, 0x7c, 0x77, 0x7b, 0xf2, 0x6b, 0x6f, 0xc5,
34937 + 0x30, 0x01, 0x67, 0x2b, 0xfe, 0xd7, 0xab, 0x76,
34938 + 0xca, 0x82, 0xc9, 0x7d, 0xfa, 0x59, 0x47, 0xf0,
34939 + 0xad, 0xd4, 0xa2, 0xaf, 0x9c, 0xa4, 0x72, 0xc0,
34940 + 0xb7, 0xfd, 0x93, 0x26, 0x36, 0x3f, 0xf7, 0xcc,
34941 + 0x34, 0xa5, 0xe5, 0xf1, 0x71, 0xd8, 0x31, 0x15,
34942 + 0x04, 0xc7, 0x23, 0xc3, 0x18, 0x96, 0x05, 0x9a,
34943 + 0x07, 0x12, 0x80, 0xe2, 0xeb, 0x27, 0xb2, 0x75,
34944 + 0x09, 0x83, 0x2c, 0x1a, 0x1b, 0x6e, 0x5a, 0xa0,
34945 + 0x52, 0x3b, 0xd6, 0xb3, 0x29, 0xe3, 0x2f, 0x84,
34946 + 0x53, 0xd1, 0x00, 0xed, 0x20, 0xfc, 0xb1, 0x5b,
34947 + 0x6a, 0xcb, 0xbe, 0x39, 0x4a, 0x4c, 0x58, 0xcf,
34948 + 0xd0, 0xef, 0xaa, 0xfb, 0x43, 0x4d, 0x33, 0x85,
34949 + 0x45, 0xf9, 0x02, 0x7f, 0x50, 0x3c, 0x9f, 0xa8,
34950 + 0x51, 0xa3, 0x40, 0x8f, 0x92, 0x9d, 0x38, 0xf5,
34951 + 0xbc, 0xb6, 0xda, 0x21, 0x10, 0xff, 0xf3, 0xd2,
34952 + 0xcd, 0x0c, 0x13, 0xec, 0x5f, 0x97, 0x44, 0x17,
34953 + 0xc4, 0xa7, 0x7e, 0x3d, 0x64, 0x5d, 0x19, 0x73,
34954 + 0x60, 0x81, 0x4f, 0xdc, 0x22, 0x2a, 0x90, 0x88,
34955 + 0x46, 0xee, 0xb8, 0x14, 0xde, 0x5e, 0x0b, 0xdb,
34956 + 0xe0, 0x32, 0x3a, 0x0a, 0x49, 0x06, 0x24, 0x5c,
34957 + 0xc2, 0xd3, 0xac, 0x62, 0x91, 0x95, 0xe4, 0x79,
34958 + 0xe7, 0xc8, 0x37, 0x6d, 0x8d, 0xd5, 0x4e, 0xa9,
34959 + 0x6c, 0x56, 0xf4, 0xea, 0x65, 0x7a, 0xae, 0x08,
34960 + 0xba, 0x78, 0x25, 0x2e, 0x1c, 0xa6, 0xb4, 0xc6,
34961 + 0xe8, 0xdd, 0x74, 0x1f, 0x4b, 0xbd, 0x8b, 0x8a,
34962 + 0x70, 0x3e, 0xb5, 0x66, 0x48, 0x03, 0xf6, 0x0e,
34963 + 0x61, 0x35, 0x57, 0xb9, 0x86, 0xc1, 0x1d, 0x9e,
34964 + 0xe1, 0xf8, 0x98, 0x11, 0x69, 0xd9, 0x8e, 0x94,
34965 + 0x9b, 0x1e, 0x87, 0xe9, 0xce, 0x55, 0x28, 0xdf,
34966 + 0x8c, 0xa1, 0x89, 0x0d, 0xbf, 0xe6, 0x42, 0x68,
34967 + 0x41, 0x99, 0x2d, 0x0f, 0xb0, 0x54, 0xbb, 0x16
34968 +};
34969 +
34970 +VOID xor_32(
34971 + IN PUCHAR a,
34972 + IN PUCHAR b,
34973 + OUT PUCHAR out);
34974 +
34975 +VOID xor_128(
34976 + IN PUCHAR a,
34977 + IN PUCHAR b,
34978 + OUT PUCHAR out);
34979 +
34980 +VOID next_key(
34981 + IN PUCHAR key,
34982 + IN INT round);
34983 +
34984 +VOID byte_sub(
34985 + IN PUCHAR in,
34986 + OUT PUCHAR out);
34987 +
34988 +VOID shift_row(
34989 + IN PUCHAR in,
34990 + OUT PUCHAR out);
34991 +
34992 +VOID mix_column(
34993 + IN PUCHAR in,
34994 + OUT PUCHAR out);
34995 +
34996 +UCHAR RTMPCkipSbox(
34997 + IN UCHAR a);
34998 +//
34999 +// Expanded IV for TKIP function.
35000 +//
35001 +typedef struct PACKED _IV_CONTROL_
35002 +{
35003 + union PACKED
35004 + {
35005 + struct PACKED
35006 + {
35007 + UCHAR rc0;
35008 + UCHAR rc1;
35009 + UCHAR rc2;
35010 +
35011 + union PACKED
35012 + {
35013 + struct PACKED
35014 + {
35015 +#ifdef RT_BIG_ENDIAN
35016 + UCHAR KeyID:2;
35017 + UCHAR ExtIV:1;
35018 + UCHAR Rsvd:5;
35019 +#else
35020 + UCHAR Rsvd:5;
35021 + UCHAR ExtIV:1;
35022 + UCHAR KeyID:2;
35023 +#endif
35024 + } field;
35025 + UCHAR Byte;
35026 + } CONTROL;
35027 + } field;
35028 +
35029 + ULONG word;
35030 + } IV16;
35031 +
35032 + ULONG IV32;
35033 +} TKIP_IV, *PTKIP_IV;
35034 +
35035 +
35036 +/*
35037 + ========================================================================
35038 +
35039 + Routine Description:
35040 + Convert from UCHAR[] to ULONG in a portable way
35041 +
35042 + Arguments:
35043 + pMICKey pointer to MIC Key
35044 +
35045 + Return Value:
35046 + None
35047 +
35048 + Note:
35049 +
35050 + ========================================================================
35051 +*/
35052 +ULONG RTMPTkipGetUInt32(
35053 + IN PUCHAR pMICKey)
35054 +{
35055 + ULONG res = 0;
35056 + INT i;
35057 +
35058 + for (i = 0; i < 4; i++)
35059 + {
35060 + res |= (*pMICKey++) << (8 * i);
35061 + }
35062 +
35063 + return res;
35064 +}
35065 +
35066 +/*
35067 + ========================================================================
35068 +
35069 + Routine Description:
35070 + Convert from ULONG to UCHAR[] in a portable way
35071 +
35072 + Arguments:
35073 + pDst pointer to destination for convert ULONG to UCHAR[]
35074 + val the value for convert
35075 +
35076 + Return Value:
35077 + None
35078 +
35079 + IRQL = DISPATCH_LEVEL
35080 +
35081 + Note:
35082 +
35083 + ========================================================================
35084 +*/
35085 +VOID RTMPTkipPutUInt32(
35086 + IN OUT PUCHAR pDst,
35087 + IN ULONG val)
35088 +{
35089 + INT i;
35090 +
35091 + for(i = 0; i < 4; i++)
35092 + {
35093 + *pDst++ = (UCHAR) (val & 0xff);
35094 + val >>= 8;
35095 + }
35096 +}
35097 +
35098 +/*
35099 + ========================================================================
35100 +
35101 + Routine Description:
35102 + Set the MIC Key.
35103 +
35104 + Arguments:
35105 + pAd Pointer to our adapter
35106 + pMICKey pointer to MIC Key
35107 +
35108 + Return Value:
35109 + None
35110 +
35111 + IRQL = DISPATCH_LEVEL
35112 +
35113 + Note:
35114 +
35115 + ========================================================================
35116 +*/
35117 +VOID RTMPTkipSetMICKey(
35118 + IN PTKIP_KEY_INFO pTkip,
35119 + IN PUCHAR pMICKey)
35120 +{
35121 + // Set the key
35122 + pTkip->K0 = RTMPTkipGetUInt32(pMICKey);
35123 + pTkip->K1 = RTMPTkipGetUInt32(pMICKey + 4);
35124 + // and reset the message
35125 + pTkip->L = pTkip->K0;
35126 + pTkip->R = pTkip->K1;
35127 + pTkip->nBytesInM = 0;
35128 + pTkip->M = 0;
35129 +}
35130 +
35131 +/*
35132 + ========================================================================
35133 +
35134 + Routine Description:
35135 + Calculate the MIC Value.
35136 +
35137 + Arguments:
35138 + pAd Pointer to our adapter
35139 + uChar Append this uChar
35140 +
35141 + Return Value:
35142 + None
35143 +
35144 + IRQL = DISPATCH_LEVEL
35145 +
35146 + Note:
35147 +
35148 + ========================================================================
35149 +*/
35150 +VOID RTMPTkipAppendByte(
35151 + IN PTKIP_KEY_INFO pTkip,
35152 + IN UCHAR uChar)
35153 +{
35154 + // Append the byte to our word-sized buffer
35155 + pTkip->M |= (uChar << (8* pTkip->nBytesInM));
35156 + pTkip->nBytesInM++;
35157 + // Process the word if it is full.
35158 + if( pTkip->nBytesInM >= 4 )
35159 + {
35160 + pTkip->L ^= pTkip->M;
35161 + pTkip->R ^= ROL32( pTkip->L, 17 );
35162 + pTkip->L += pTkip->R;
35163 + pTkip->R ^= ((pTkip->L & 0xff00ff00) >> 8) | ((pTkip->L & 0x00ff00ff) << 8);
35164 + pTkip->L += pTkip->R;
35165 + pTkip->R ^= ROL32( pTkip->L, 3 );
35166 + pTkip->L += pTkip->R;
35167 + pTkip->R ^= ROR32( pTkip->L, 2 );
35168 + pTkip->L += pTkip->R;
35169 + // Clear the buffer
35170 + pTkip->M = 0;
35171 + pTkip->nBytesInM = 0;
35172 + }
35173 +}
35174 +
35175 +/*
35176 + ========================================================================
35177 +
35178 + Routine Description:
35179 + Calculate the MIC Value.
35180 +
35181 + Arguments:
35182 + pAd Pointer to our adapter
35183 + pSrc Pointer to source data for Calculate MIC Value
35184 + Len Indicate the length of the source data
35185 +
35186 + Return Value:
35187 + None
35188 +
35189 + IRQL = DISPATCH_LEVEL
35190 +
35191 + Note:
35192 +
35193 + ========================================================================
35194 +*/
35195 +VOID RTMPTkipAppend(
35196 + IN PTKIP_KEY_INFO pTkip,
35197 + IN PUCHAR pSrc,
35198 + IN UINT nBytes)
35199 +{
35200 + // This is simple
35201 + while(nBytes > 0)
35202 + {
35203 + RTMPTkipAppendByte(pTkip, *pSrc++);
35204 + nBytes--;
35205 + }
35206 +}
35207 +
35208 +/*
35209 + ========================================================================
35210 +
35211 + Routine Description:
35212 + Get the MIC Value.
35213 +
35214 + Arguments:
35215 + pAd Pointer to our adapter
35216 +
35217 + Return Value:
35218 + None
35219 +
35220 + IRQL = DISPATCH_LEVEL
35221 +
35222 + Note:
35223 + the MIC Value is store in pAd->PrivateInfo.MIC
35224 + ========================================================================
35225 +*/
35226 +VOID RTMPTkipGetMIC(
35227 + IN PTKIP_KEY_INFO pTkip)
35228 +{
35229 + // Append the minimum padding
35230 + RTMPTkipAppendByte(pTkip, 0x5a );
35231 + RTMPTkipAppendByte(pTkip, 0 );
35232 + RTMPTkipAppendByte(pTkip, 0 );
35233 + RTMPTkipAppendByte(pTkip, 0 );
35234 + RTMPTkipAppendByte(pTkip, 0 );
35235 + // and then zeroes until the length is a multiple of 4
35236 + while( pTkip->nBytesInM != 0 )
35237 + {
35238 + RTMPTkipAppendByte(pTkip, 0 );
35239 + }
35240 + // The appendByte function has already computed the result.
35241 + RTMPTkipPutUInt32(pTkip->MIC, pTkip->L);
35242 + RTMPTkipPutUInt32(pTkip->MIC + 4, pTkip->R);
35243 +}
35244 +
35245 +/*
35246 + ========================================================================
35247 +
35248 + Routine Description:
35249 + Init Tkip function.
35250 +
35251 + Arguments:
35252 + pAd Pointer to our adapter
35253 + pTKey Pointer to the Temporal Key (TK), TK shall be 128bits.
35254 + KeyId TK Key ID
35255 + pTA Pointer to transmitter address
35256 + pMICKey pointer to MIC Key
35257 +
35258 + Return Value:
35259 + None
35260 +
35261 + IRQL = DISPATCH_LEVEL
35262 +
35263 + Note:
35264 +
35265 + ========================================================================
35266 +*/
35267 +VOID RTMPInitTkipEngine(
35268 + IN PRTMP_ADAPTER pAd,
35269 + IN PUCHAR pKey,
35270 + IN UCHAR KeyId,
35271 + IN PUCHAR pTA,
35272 + IN PUCHAR pMICKey,
35273 + IN PUCHAR pTSC,
35274 + OUT PULONG pIV16,
35275 + OUT PULONG pIV32)
35276 +{
35277 + TKIP_IV tkipIv;
35278 +
35279 + // Prepare 8 bytes TKIP encapsulation for MPDU
35280 + NdisZeroMemory(&tkipIv, sizeof(TKIP_IV));
35281 + tkipIv.IV16.field.rc0 = *(pTSC + 1);
35282 + tkipIv.IV16.field.rc1 = (tkipIv.IV16.field.rc0 | 0x20) & 0x7f;
35283 + tkipIv.IV16.field.rc2 = *pTSC;
35284 + tkipIv.IV16.field.CONTROL.field.ExtIV = 1; // 0: non-extended IV, 1: an extended IV
35285 + tkipIv.IV16.field.CONTROL.field.KeyID = KeyId;
35286 + NdisMoveMemory(&tkipIv.IV32, (pTSC + 2), 4); // Copy IV
35287 +
35288 + *pIV16 = tkipIv.IV16.word;
35289 + *pIV32 = tkipIv.IV32;
35290 +}
35291 +
35292 +/*
35293 + ========================================================================
35294 +
35295 + Routine Description:
35296 + Init MIC Value calculation function which include set MIC key &
35297 + calculate first 16 bytes (DA + SA + priority + 0)
35298 +
35299 + Arguments:
35300 + pAd Pointer to our adapter
35301 + pTKey Pointer to the Temporal Key (TK), TK shall be 128bits.
35302 + pDA Pointer to DA address
35303 + pSA Pointer to SA address
35304 + pMICKey pointer to MIC Key
35305 +
35306 + Return Value:
35307 + None
35308 +
35309 + Note:
35310 +
35311 + ========================================================================
35312 +*/
35313 +VOID RTMPInitMICEngine(
35314 + IN PRTMP_ADAPTER pAd,
35315 + IN PUCHAR pKey,
35316 + IN PUCHAR pDA,
35317 + IN PUCHAR pSA,
35318 + IN UCHAR UserPriority,
35319 + IN PUCHAR pMICKey)
35320 +{
35321 + ULONG Priority = UserPriority;
35322 +
35323 + // Init MIC value calculation
35324 + RTMPTkipSetMICKey(&pAd->PrivateInfo.Tx, pMICKey);
35325 + // DA
35326 + RTMPTkipAppend(&pAd->PrivateInfo.Tx, pDA, MAC_ADDR_LEN);
35327 + // SA
35328 + RTMPTkipAppend(&pAd->PrivateInfo.Tx, pSA, MAC_ADDR_LEN);
35329 + // Priority + 3 bytes of 0
35330 + RTMPTkipAppend(&pAd->PrivateInfo.Tx, (PUCHAR)&Priority, 4);
35331 +}
35332 +
35333 +/*
35334 + ========================================================================
35335 +
35336 + Routine Description:
35337 + Compare MIC value of received MSDU
35338 +
35339 + Arguments:
35340 + pAd Pointer to our adapter
35341 + pSrc Pointer to the received Plain text data
35342 + pDA Pointer to DA address
35343 + pSA Pointer to SA address
35344 + pMICKey pointer to MIC Key
35345 + Len the length of the received plain text data exclude MIC value
35346 +
35347 + Return Value:
35348 + TRUE MIC value matched
35349 + FALSE MIC value mismatched
35350 +
35351 + IRQL = DISPATCH_LEVEL
35352 +
35353 + Note:
35354 +
35355 + ========================================================================
35356 +*/
35357 +BOOLEAN RTMPTkipCompareMICValue(
35358 + IN PRTMP_ADAPTER pAd,
35359 + IN PUCHAR pSrc,
35360 + IN PUCHAR pDA,
35361 + IN PUCHAR pSA,
35362 + IN PUCHAR pMICKey,
35363 + IN UCHAR UserPriority,
35364 + IN UINT Len)
35365 +{
35366 + UCHAR OldMic[8];
35367 + ULONG Priority = UserPriority;
35368 +
35369 + // Init MIC value calculation
35370 + RTMPTkipSetMICKey(&pAd->PrivateInfo.Rx, pMICKey);
35371 + // DA
35372 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, pDA, MAC_ADDR_LEN);
35373 + // SA
35374 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, pSA, MAC_ADDR_LEN);
35375 + // Priority + 3 bytes of 0
35376 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, (PUCHAR)&Priority, 4);
35377 +
35378 + // Calculate MIC value from plain text data
35379 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, pSrc, Len);
35380 +
35381 + // Get MIC valude from received frame
35382 + NdisMoveMemory(OldMic, pSrc + Len, 8);
35383 +
35384 + // Get MIC value from decrypted plain data
35385 + RTMPTkipGetMIC(&pAd->PrivateInfo.Rx);
35386 +
35387 + // Move MIC value from MSDU, this steps should move to data path.
35388 + // Since the MIC value might cross MPDUs.
35389 + if(!NdisEqualMemory(pAd->PrivateInfo.Rx.MIC, OldMic, 8))
35390 + {
35391 + DBGPRINT_RAW(RT_DEBUG_ERROR, ("RTMPTkipCompareMICValue(): TKIP MIC Error !\n")); //MIC error.
35392 +
35393 +
35394 + return (FALSE);
35395 + }
35396 + return (TRUE);
35397 +}
35398 +
35399 +/*
35400 + ========================================================================
35401 +
35402 + Routine Description:
35403 + Compare MIC value of received MSDU
35404 +
35405 + Arguments:
35406 + pAd Pointer to our adapter
35407 + pLLC LLC header
35408 + pSrc Pointer to the received Plain text data
35409 + pDA Pointer to DA address
35410 + pSA Pointer to SA address
35411 + pMICKey pointer to MIC Key
35412 + Len the length of the received plain text data exclude MIC value
35413 +
35414 + Return Value:
35415 + TRUE MIC value matched
35416 + FALSE MIC value mismatched
35417 +
35418 + IRQL = DISPATCH_LEVEL
35419 +
35420 + Note:
35421 +
35422 + ========================================================================
35423 +*/
35424 +BOOLEAN RTMPTkipCompareMICValueWithLLC(
35425 + IN PRTMP_ADAPTER pAd,
35426 + IN PUCHAR pLLC,
35427 + IN PUCHAR pSrc,
35428 + IN PUCHAR pDA,
35429 + IN PUCHAR pSA,
35430 + IN PUCHAR pMICKey,
35431 + IN UINT Len)
35432 +{
35433 + UCHAR OldMic[8];
35434 + ULONG Priority = 0;
35435 +
35436 + // Init MIC value calculation
35437 + RTMPTkipSetMICKey(&pAd->PrivateInfo.Rx, pMICKey);
35438 + // DA
35439 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, pDA, MAC_ADDR_LEN);
35440 + // SA
35441 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, pSA, MAC_ADDR_LEN);
35442 + // Priority + 3 bytes of 0
35443 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, (PUCHAR)&Priority, 4);
35444 +
35445 + // Start with LLC header
35446 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, pLLC, 8);
35447 +
35448 + // Calculate MIC value from plain text data
35449 + RTMPTkipAppend(&pAd->PrivateInfo.Rx, pSrc, Len);
35450 +
35451 + // Get MIC valude from received frame
35452 + NdisMoveMemory(OldMic, pSrc + Len, 8);
35453 +
35454 + // Get MIC value from decrypted plain data
35455 + RTMPTkipGetMIC(&pAd->PrivateInfo.Rx);
35456 +
35457 + // Move MIC value from MSDU, this steps should move to data path.
35458 + // Since the MIC value might cross MPDUs.
35459 + if(!NdisEqualMemory(pAd->PrivateInfo.Rx.MIC, OldMic, 8))
35460 + {
35461 + DBGPRINT_RAW(RT_DEBUG_ERROR, ("RTMPTkipCompareMICValueWithLLC(): TKIP MIC Error !\n")); //MIC error.
35462 +
35463 +
35464 + return (FALSE);
35465 + }
35466 + return (TRUE);
35467 +}
35468 +/*
35469 + ========================================================================
35470 +
35471 + Routine Description:
35472 + Copy frame from waiting queue into relative ring buffer and set
35473 + appropriate ASIC register to kick hardware transmit function
35474 +
35475 + Arguments:
35476 + pAd Pointer to our adapter
35477 + PNDIS_PACKET Pointer to Ndis Packet for MIC calculation
35478 + pEncap Pointer to LLC encap data
35479 + LenEncap Total encap length, might be 0 which indicates no encap
35480 +
35481 + Return Value:
35482 + None
35483 +
35484 + IRQL = DISPATCH_LEVEL
35485 +
35486 + Note:
35487 +
35488 + ========================================================================
35489 +*/
35490 +VOID RTMPCalculateMICValue(
35491 + IN PRTMP_ADAPTER pAd,
35492 + IN PNDIS_PACKET pPacket,
35493 + IN PUCHAR pEncap,
35494 + IN PCIPHER_KEY pKey,
35495 + IN UCHAR apidx)
35496 +{
35497 + PACKET_INFO PacketInfo;
35498 + PUCHAR pSrcBufVA;
35499 + UINT SrcBufLen;
35500 + PUCHAR pSrc;
35501 + UCHAR UserPriority;
35502 + UCHAR vlan_offset = 0;
35503 +
35504 + RTMP_QueryPacketInfo(pPacket, &PacketInfo, &pSrcBufVA, &SrcBufLen);
35505 +
35506 + UserPriority = RTMP_GET_PACKET_UP(pPacket);
35507 + pSrc = pSrcBufVA;
35508 +
35509 + // determine if this is a vlan packet
35510 + if (((*(pSrc + 12) << 8) + *(pSrc + 13)) == 0x8100)
35511 + vlan_offset = 4;
35512 +
35513 + {
35514 + RTMPInitMICEngine(
35515 + pAd,
35516 + pKey->Key,
35517 + pSrc,
35518 + pSrc + 6,
35519 + UserPriority,
35520 + pKey->TxMic);
35521 + }
35522 +
35523 +
35524 + if (pEncap != NULL)
35525 + {
35526 + // LLC encapsulation
35527 + RTMPTkipAppend(&pAd->PrivateInfo.Tx, pEncap, 6);
35528 + // Protocol Type
35529 + RTMPTkipAppend(&pAd->PrivateInfo.Tx, pSrc + 12 + vlan_offset, 2);
35530 + }
35531 + SrcBufLen -= (14 + vlan_offset);
35532 + pSrc += (14 + vlan_offset);
35533 + do
35534 + {
35535 + if (SrcBufLen > 0)
35536 + {
35537 + RTMPTkipAppend(&pAd->PrivateInfo.Tx, pSrc, SrcBufLen);
35538 + }
35539 +
35540 + break; // No need handle next packet
35541 +
35542 + } while (TRUE); // End of copying payload
35543 +
35544 + // Compute the final MIC Value
35545 + RTMPTkipGetMIC(&pAd->PrivateInfo.Tx);
35546 +}
35547 +
35548 +
35549 +/************************************************************/
35550 +/* tkip_sbox() */
35551 +/* Returns a 16 bit value from a 64K entry table. The Table */
35552 +/* is synthesized from two 256 entry byte wide tables. */
35553 +/************************************************************/
35554 +
35555 +UINT tkip_sbox(UINT index)
35556 +{
35557 + UINT index_low;
35558 + UINT index_high;
35559 + UINT left, right;
35560 +
35561 + index_low = (index % 256);
35562 + index_high = ((index >> 8) % 256);
35563 +
35564 + left = Tkip_Sbox_Lower[index_low] + (Tkip_Sbox_Upper[index_low] * 256);
35565 + right = Tkip_Sbox_Upper[index_high] + (Tkip_Sbox_Lower[index_high] * 256);
35566 +
35567 + return (left ^ right);
35568 +}
35569 +
35570 +UINT rotr1(UINT a)
35571 +{
35572 + unsigned int b;
35573 +
35574 + if ((a & 0x01) == 0x01)
35575 + {
35576 + b = (a >> 1) | 0x8000;
35577 + }
35578 + else
35579 + {
35580 + b = (a >> 1) & 0x7fff;
35581 + }
35582 + b = b % 65536;
35583 + return b;
35584 +}
35585 +
35586 +VOID RTMPTkipMixKey(
35587 + UCHAR *key,
35588 + UCHAR *ta,
35589 + ULONG pnl, /* Least significant 16 bits of PN */
35590 + ULONG pnh, /* Most significant 32 bits of PN */
35591 + UCHAR *rc4key,
35592 + UINT *p1k)
35593 +{
35594 +
35595 + UINT tsc0;
35596 + UINT tsc1;
35597 + UINT tsc2;
35598 +
35599 + UINT ppk0;
35600 + UINT ppk1;
35601 + UINT ppk2;
35602 + UINT ppk3;
35603 + UINT ppk4;
35604 + UINT ppk5;
35605 +
35606 + INT i;
35607 + INT j;
35608 +
35609 + tsc0 = (unsigned int)((pnh >> 16) % 65536); /* msb */
35610 + tsc1 = (unsigned int)(pnh % 65536);
35611 + tsc2 = (unsigned int)(pnl % 65536); /* lsb */
35612 +
35613 + /* Phase 1, step 1 */
35614 + p1k[0] = tsc1;
35615 + p1k[1] = tsc0;
35616 + p1k[2] = (UINT)(ta[0] + (ta[1]*256));
35617 + p1k[3] = (UINT)(ta[2] + (ta[3]*256));
35618 + p1k[4] = (UINT)(ta[4] + (ta[5]*256));
35619 +
35620 + /* Phase 1, step 2 */
35621 + for (i=0; i<8; i++)
35622 + {
35623 + j = 2*(i & 1);
35624 + p1k[0] = (p1k[0] + tkip_sbox( (p1k[4] ^ ((256*key[1+j]) + key[j])) % 65536 )) % 65536;
35625 + p1k[1] = (p1k[1] + tkip_sbox( (p1k[0] ^ ((256*key[5+j]) + key[4+j])) % 65536 )) % 65536;
35626 + p1k[2] = (p1k[2] + tkip_sbox( (p1k[1] ^ ((256*key[9+j]) + key[8+j])) % 65536 )) % 65536;
35627 + p1k[3] = (p1k[3] + tkip_sbox( (p1k[2] ^ ((256*key[13+j]) + key[12+j])) % 65536 )) % 65536;
35628 + p1k[4] = (p1k[4] + tkip_sbox( (p1k[3] ^ (((256*key[1+j]) + key[j]))) % 65536 )) % 65536;
35629 + p1k[4] = (p1k[4] + i) % 65536;
35630 + }
35631 +
35632 + /* Phase 2, Step 1 */
35633 + ppk0 = p1k[0];
35634 + ppk1 = p1k[1];
35635 + ppk2 = p1k[2];
35636 + ppk3 = p1k[3];
35637 + ppk4 = p1k[4];
35638 + ppk5 = (p1k[4] + tsc2) % 65536;
35639 +
35640 + /* Phase2, Step 2 */
35641 + ppk0 = ppk0 + tkip_sbox( (ppk5 ^ ((256*key[1]) + key[0])) % 65536);
35642 + ppk1 = ppk1 + tkip_sbox( (ppk0 ^ ((256*key[3]) + key[2])) % 65536);
35643 + ppk2 = ppk2 + tkip_sbox( (ppk1 ^ ((256*key[5]) + key[4])) % 65536);
35644 + ppk3 = ppk3 + tkip_sbox( (ppk2 ^ ((256*key[7]) + key[6])) % 65536);
35645 + ppk4 = ppk4 + tkip_sbox( (ppk3 ^ ((256*key[9]) + key[8])) % 65536);
35646 + ppk5 = ppk5 + tkip_sbox( (ppk4 ^ ((256*key[11]) + key[10])) % 65536);
35647 +
35648 + ppk0 = ppk0 + rotr1(ppk5 ^ ((256*key[13]) + key[12]));
35649 + ppk1 = ppk1 + rotr1(ppk0 ^ ((256*key[15]) + key[14]));
35650 + ppk2 = ppk2 + rotr1(ppk1);
35651 + ppk3 = ppk3 + rotr1(ppk2);
35652 + ppk4 = ppk4 + rotr1(ppk3);
35653 + ppk5 = ppk5 + rotr1(ppk4);
35654 +
35655 + /* Phase 2, Step 3 */
35656 + /* Phase 2, Step 3 */
35657 +
35658 + tsc0 = (unsigned int)((pnh >> 16) % 65536); /* msb */
35659 + tsc1 = (unsigned int)(pnh % 65536);
35660 + tsc2 = (unsigned int)(pnl % 65536); /* lsb */
35661 +
35662 + rc4key[0] = (tsc2 >> 8) % 256;
35663 + rc4key[1] = (((tsc2 >> 8) % 256) | 0x20) & 0x7f;
35664 + rc4key[2] = tsc2 % 256;
35665 + rc4key[3] = ((ppk5 ^ ((256*key[1]) + key[0])) >> 1) % 256;
35666 +
35667 + rc4key[4] = ppk0 % 256;
35668 + rc4key[5] = (ppk0 >> 8) % 256;
35669 +
35670 + rc4key[6] = ppk1 % 256;
35671 + rc4key[7] = (ppk1 >> 8) % 256;
35672 +
35673 + rc4key[8] = ppk2 % 256;
35674 + rc4key[9] = (ppk2 >> 8) % 256;
35675 +
35676 + rc4key[10] = ppk3 % 256;
35677 + rc4key[11] = (ppk3 >> 8) % 256;
35678 +
35679 + rc4key[12] = ppk4 % 256;
35680 + rc4key[13] = (ppk4 >> 8) % 256;
35681 +
35682 + rc4key[14] = ppk5 % 256;
35683 + rc4key[15] = (ppk5 >> 8) % 256;
35684 +}
35685 +
35686 +
35687 +/************************************************/
35688 +/* construct_mic_header1() */
35689 +/* Builds the first MIC header block from */
35690 +/* header fields. */
35691 +/************************************************/
35692 +
35693 +void construct_mic_header1(
35694 + unsigned char *mic_header1,
35695 + int header_length,
35696 + unsigned char *mpdu)
35697 +{
35698 + mic_header1[0] = (unsigned char)((header_length - 2) / 256);
35699 + mic_header1[1] = (unsigned char)((header_length - 2) % 256);
35700 + mic_header1[2] = mpdu[0] & 0xcf; /* Mute CF poll & CF ack bits */
35701 + mic_header1[3] = mpdu[1] & 0xc7; /* Mute retry, more data and pwr mgt bits */
35702 + mic_header1[4] = mpdu[4]; /* A1 */
35703 + mic_header1[5] = mpdu[5];
35704 + mic_header1[6] = mpdu[6];
35705 + mic_header1[7] = mpdu[7];
35706 + mic_header1[8] = mpdu[8];
35707 + mic_header1[9] = mpdu[9];
35708 + mic_header1[10] = mpdu[10]; /* A2 */
35709 + mic_header1[11] = mpdu[11];
35710 + mic_header1[12] = mpdu[12];
35711 + mic_header1[13] = mpdu[13];
35712 + mic_header1[14] = mpdu[14];
35713 + mic_header1[15] = mpdu[15];
35714 +}
35715 +
35716 +/************************************************/
35717 +/* construct_mic_header2() */
35718 +/* Builds the last MIC header block from */
35719 +/* header fields. */
35720 +/************************************************/
35721 +
35722 +void construct_mic_header2(
35723 + unsigned char *mic_header2,
35724 + unsigned char *mpdu,
35725 + int a4_exists,
35726 + int qc_exists)
35727 +{
35728 + int i;
35729 +
35730 + for (i = 0; i<16; i++) mic_header2[i]=0x00;
35731 +
35732 + mic_header2[0] = mpdu[16]; /* A3 */
35733 + mic_header2[1] = mpdu[17];
35734 + mic_header2[2] = mpdu[18];
35735 + mic_header2[3] = mpdu[19];
35736 + mic_header2[4] = mpdu[20];
35737 + mic_header2[5] = mpdu[21];
35738 +
35739 + // In Sequence Control field, mute sequence numer bits (12-bit)
35740 + mic_header2[6] = mpdu[22] & 0x0f; /* SC */
35741 + mic_header2[7] = 0x00; /* mpdu[23]; */
35742 +
35743 + if ((!qc_exists) & a4_exists)
35744 + {
35745 + for (i=0;i<6;i++) mic_header2[8+i] = mpdu[24+i]; /* A4 */
35746 +
35747 + }
35748 +
35749 + if (qc_exists && (!a4_exists))
35750 + {
35751 + mic_header2[8] = mpdu[24] & 0x0f; /* mute bits 15 - 4 */
35752 + mic_header2[9] = mpdu[25] & 0x00;
35753 + }
35754 +
35755 + if (qc_exists && a4_exists)
35756 + {
35757 + for (i=0;i<6;i++) mic_header2[8+i] = mpdu[24+i]; /* A4 */
35758 +
35759 + mic_header2[14] = mpdu[30] & 0x0f;
35760 + mic_header2[15] = mpdu[31] & 0x00;
35761 + }
35762 +}
35763 +
35764 +
35765 +/************************************************/
35766 +/* construct_mic_iv() */
35767 +/* Builds the MIC IV from header fields and PN */
35768 +/************************************************/
35769 +
35770 +void construct_mic_iv(
35771 + unsigned char *mic_iv,
35772 + int qc_exists,
35773 + int a4_exists,
35774 + unsigned char *mpdu,
35775 + unsigned int payload_length,
35776 + unsigned char *pn_vector)
35777 +{
35778 + int i;
35779 +
35780 + mic_iv[0] = 0x59;
35781 + if (qc_exists && a4_exists)
35782 + mic_iv[1] = mpdu[30] & 0x0f; /* QoS_TC */
35783 + if (qc_exists && !a4_exists)
35784 + mic_iv[1] = mpdu[24] & 0x0f; /* mute bits 7-4 */
35785 + if (!qc_exists)
35786 + mic_iv[1] = 0x00;
35787 + for (i = 2; i < 8; i++)
35788 + mic_iv[i] = mpdu[i + 8]; /* mic_iv[2:7] = A2[0:5] = mpdu[10:15] */
35789 +#ifdef CONSISTENT_PN_ORDER
35790 + for (i = 8; i < 14; i++)
35791 + mic_iv[i] = pn_vector[i - 8]; /* mic_iv[8:13] = PN[0:5] */
35792 +#else
35793 + for (i = 8; i < 14; i++)
35794 + mic_iv[i] = pn_vector[13 - i]; /* mic_iv[8:13] = PN[5:0] */
35795 +#endif
35796 + i = (payload_length / 256);
35797 + i = (payload_length % 256);
35798 + mic_iv[14] = (unsigned char) (payload_length / 256);
35799 + mic_iv[15] = (unsigned char) (payload_length % 256);
35800 +
35801 +}
35802 +
35803 +
35804 +
35805 +/************************************/
35806 +/* bitwise_xor() */
35807 +/* A 128 bit, bitwise exclusive or */
35808 +/************************************/
35809 +
35810 +void bitwise_xor(unsigned char *ina, unsigned char *inb, unsigned char *out)
35811 +{
35812 + int i;
35813 + for (i=0; i<16; i++)
35814 + {
35815 + out[i] = ina[i] ^ inb[i];
35816 + }
35817 +}
35818 +
35819 +
35820 +void aes128k128d(unsigned char *key, unsigned char *data, unsigned char *ciphertext)
35821 +{
35822 + int round;
35823 + int i;
35824 + unsigned char intermediatea[16];
35825 + unsigned char intermediateb[16];
35826 + unsigned char round_key[16];
35827 +
35828 + for(i=0; i<16; i++) round_key[i] = key[i];
35829 +
35830 + for (round = 0; round < 11; round++)
35831 + {
35832 + if (round == 0)
35833 + {
35834 + xor_128(round_key, data, ciphertext);
35835 + next_key(round_key, round);
35836 + }
35837 + else if (round == 10)
35838 + {
35839 + byte_sub(ciphertext, intermediatea);
35840 + shift_row(intermediatea, intermediateb);
35841 + xor_128(intermediateb, round_key, ciphertext);
35842 + }
35843 + else /* 1 - 9 */
35844 + {
35845 + byte_sub(ciphertext, intermediatea);
35846 + shift_row(intermediatea, intermediateb);
35847 + mix_column(&intermediateb[0], &intermediatea[0]);
35848 + mix_column(&intermediateb[4], &intermediatea[4]);
35849 + mix_column(&intermediateb[8], &intermediatea[8]);
35850 + mix_column(&intermediateb[12], &intermediatea[12]);
35851 + xor_128(intermediatea, round_key, ciphertext);
35852 + next_key(round_key, round);
35853 + }
35854 + }
35855 +
35856 +}
35857 +
35858 +void construct_ctr_preload(
35859 + unsigned char *ctr_preload,
35860 + int a4_exists,
35861 + int qc_exists,
35862 + unsigned char *mpdu,
35863 + unsigned char *pn_vector,
35864 + int c)
35865 +{
35866 +
35867 + int i = 0;
35868 + for (i=0; i<16; i++) ctr_preload[i] = 0x00;
35869 + i = 0;
35870 +
35871 + ctr_preload[0] = 0x01; /* flag */
35872 + if (qc_exists && a4_exists) ctr_preload[1] = mpdu[30] & 0x0f; /* QoC_Control */
35873 + if (qc_exists && !a4_exists) ctr_preload[1] = mpdu[24] & 0x0f;
35874 +
35875 + for (i = 2; i < 8; i++)
35876 + ctr_preload[i] = mpdu[i + 8]; /* ctr_preload[2:7] = A2[0:5] = mpdu[10:15] */
35877 +#ifdef CONSISTENT_PN_ORDER
35878 + for (i = 8; i < 14; i++)
35879 + ctr_preload[i] = pn_vector[i - 8]; /* ctr_preload[8:13] = PN[0:5] */
35880 +#else
35881 + for (i = 8; i < 14; i++)
35882 + ctr_preload[i] = pn_vector[13 - i]; /* ctr_preload[8:13] = PN[5:0] */
35883 +#endif
35884 + ctr_preload[14] = (unsigned char) (c / 256); // Ctr
35885 + ctr_preload[15] = (unsigned char) (c % 256);
35886 +
35887 +}
35888 +
35889 +
35890 +//
35891 +// TRUE: Success!
35892 +// FALSE: Decrypt Error!
35893 +//
35894 +BOOLEAN RTMPSoftDecryptTKIP(
35895 + IN PRTMP_ADAPTER pAd,
35896 + IN PUCHAR pData,
35897 + IN ULONG DataByteCnt,
35898 + IN UCHAR UserPriority,
35899 + IN PCIPHER_KEY pWpaKey)
35900 +{
35901 + UCHAR KeyID;
35902 + UINT HeaderLen;
35903 + UCHAR fc0;
35904 + UCHAR fc1;
35905 + USHORT fc;
35906 + UINT frame_type;
35907 + UINT frame_subtype;
35908 + UINT from_ds;
35909 + UINT to_ds;
35910 + INT a4_exists;
35911 + INT qc_exists;
35912 + USHORT duration;
35913 + USHORT seq_control;
35914 + USHORT qos_control;
35915 + UCHAR TA[MAC_ADDR_LEN];
35916 + UCHAR DA[MAC_ADDR_LEN];
35917 + UCHAR SA[MAC_ADDR_LEN];
35918 + UCHAR RC4Key[16];
35919 + UINT p1k[5]; //for mix_key;
35920 + ULONG pnl;/* Least significant 16 bits of PN */
35921 + ULONG pnh;/* Most significant 32 bits of PN */
35922 + UINT num_blocks;
35923 + UINT payload_remainder;
35924 + ARCFOURCONTEXT ArcFourContext;
35925 + UINT crc32 = 0;
35926 + UINT trailfcs = 0;
35927 + UCHAR MIC[8];
35928 + UCHAR TrailMIC[8];
35929 +
35930 +#ifdef RT_BIG_ENDIAN
35931 + RTMPFrameEndianChange(pAd, (PUCHAR)pData, DIR_READ, FALSE);
35932 +#endif
35933 +
35934 + fc0 = *pData;
35935 + fc1 = *(pData + 1);
35936 +
35937 + fc = *((PUSHORT)pData);
35938 +
35939 + frame_type = ((fc0 >> 2) & 0x03);
35940 + frame_subtype = ((fc0 >> 4) & 0x0f);
35941 +
35942 + from_ds = (fc1 & 0x2) >> 1;
35943 + to_ds = (fc1 & 0x1);
35944 +
35945 + a4_exists = (from_ds & to_ds);
35946 + qc_exists = ((frame_subtype == 0x08) || /* Assumed QoS subtypes */
35947 + (frame_subtype == 0x09) || /* Likely to change. */
35948 + (frame_subtype == 0x0a) ||
35949 + (frame_subtype == 0x0b)
35950 + );
35951 +
35952 + HeaderLen = 24;
35953 + if (a4_exists)
35954 + HeaderLen += 6;
35955 +
35956 + KeyID = *((PUCHAR)(pData+ HeaderLen + 3));
35957 + KeyID = KeyID >> 6;
35958 +
35959 + if (pWpaKey[KeyID].KeyLen == 0)
35960 + {
35961 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSoftDecryptTKIP failed!(KeyID[%d] Length can not be 0)\n", KeyID));
35962 + return FALSE;
35963 + }
35964 +
35965 + duration = *((PUSHORT)(pData+2));
35966 +
35967 + seq_control = *((PUSHORT)(pData+22));
35968 +
35969 + if (qc_exists)
35970 + {
35971 + if (a4_exists)
35972 + {
35973 + qos_control = *((PUSHORT)(pData+30));
35974 + }
35975 + else
35976 + {
35977 + qos_control = *((PUSHORT)(pData+24));
35978 + }
35979 + }
35980 +
35981 + if (to_ds == 0 && from_ds == 1)
35982 + {
35983 + NdisMoveMemory(DA, pData+4, MAC_ADDR_LEN);
35984 + NdisMoveMemory(SA, pData+16, MAC_ADDR_LEN);
35985 + NdisMoveMemory(TA, pData+10, MAC_ADDR_LEN); //BSSID
35986 + }
35987 + else if (to_ds == 0 && from_ds == 0 )
35988 + {
35989 + NdisMoveMemory(TA, pData+10, MAC_ADDR_LEN);
35990 + NdisMoveMemory(DA, pData+4, MAC_ADDR_LEN);
35991 + NdisMoveMemory(SA, pData+10, MAC_ADDR_LEN);
35992 + }
35993 + else if (to_ds == 1 && from_ds == 0)
35994 + {
35995 + NdisMoveMemory(SA, pData+10, MAC_ADDR_LEN);
35996 + NdisMoveMemory(TA, pData+10, MAC_ADDR_LEN);
35997 + NdisMoveMemory(DA, pData+16, MAC_ADDR_LEN);
35998 + }
35999 + else if (to_ds == 1 && from_ds == 1)
36000 + {
36001 + NdisMoveMemory(TA, pData+10, MAC_ADDR_LEN);
36002 + NdisMoveMemory(DA, pData+16, MAC_ADDR_LEN);
36003 + NdisMoveMemory(SA, pData+22, MAC_ADDR_LEN);
36004 + }
36005 +
36006 + num_blocks = (DataByteCnt - 16) / 16;
36007 + payload_remainder = (DataByteCnt - 16) % 16;
36008 +
36009 + pnl = (*(pData + HeaderLen)) * 256 + *(pData + HeaderLen + 2);
36010 + pnh = *((PULONG)(pData + HeaderLen + 4));
36011 + pnh = cpu2le32(pnh);
36012 + RTMPTkipMixKey(pWpaKey[KeyID].Key, TA, pnl, pnh, RC4Key, p1k);
36013 +
36014 + ARCFOUR_INIT(&ArcFourContext, RC4Key, 16);
36015 +
36016 + ARCFOUR_DECRYPT(&ArcFourContext, pData + HeaderLen, pData + HeaderLen + 8, DataByteCnt - HeaderLen - 8);
36017 + NdisMoveMemory(&trailfcs, pData + DataByteCnt - 8 - 4, 4);
36018 + crc32 = RTMP_CALC_FCS32(PPPINITFCS32, pData + HeaderLen, DataByteCnt - HeaderLen - 8 - 4); //Skip IV+EIV 8 bytes & Skip last 4 bytes(FCS).
36019 + crc32 ^= 0xffffffff; /* complement */
36020 +
36021 + if(crc32 != cpu2le32(trailfcs))
36022 + {
36023 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSoftDecryptTKIP, WEP Data ICV Error !\n")); //ICV error.
36024 +
36025 + return (FALSE);
36026 + }
36027 +
36028 + NdisMoveMemory(TrailMIC, pData + DataByteCnt - 8 - 8 - 4, 8);
36029 + RTMPInitMICEngine(pAd, pWpaKey[KeyID].Key, DA, SA, UserPriority, pWpaKey[KeyID].RxMic);
36030 + RTMPTkipAppend(&pAd->PrivateInfo.Tx, pData + HeaderLen, DataByteCnt - HeaderLen - 8 - 12);
36031 + RTMPTkipGetMIC(&pAd->PrivateInfo.Tx);
36032 + NdisMoveMemory(MIC, pAd->PrivateInfo.Tx.MIC, 8);
36033 +
36034 + if (!NdisEqualMemory(MIC, TrailMIC, 8))
36035 + {
36036 + DBGPRINT(RT_DEBUG_ERROR, ("RTMPSoftDecryptTKIP, WEP Data MIC Error !\n")); //MIC error.
36037 + return (FALSE);
36038 + }
36039 +
36040 +#ifdef RT_BIG_ENDIAN
36041 + RTMPFrameEndianChange(pAd, (PUCHAR)pData, DIR_READ, FALSE);
36042 +#endif
36043 + return TRUE;
36044 +}
36045 +
36046 +
36047 +
36048 +
36049 +BOOLEAN RTMPSoftDecryptAES(
36050 + IN PRTMP_ADAPTER pAd,
36051 + IN PUCHAR pData,
36052 + IN ULONG DataByteCnt,
36053 + IN PCIPHER_KEY pWpaKey)
36054 +{
36055 + UCHAR KeyID;
36056 + UINT HeaderLen;
36057 + UCHAR PN[6];
36058 + UINT payload_len;
36059 + UINT num_blocks;
36060 + UINT payload_remainder;
36061 + USHORT fc;
36062 + UCHAR fc0;
36063 + UCHAR fc1;
36064 + UINT frame_type;
36065 + UINT frame_subtype;
36066 + UINT from_ds;
36067 + UINT to_ds;
36068 + INT a4_exists;
36069 + INT qc_exists;
36070 + UCHAR aes_out[16];
36071 + int payload_index;
36072 + UINT i;
36073 + UCHAR ctr_preload[16];
36074 + UCHAR chain_buffer[16];
36075 + UCHAR padded_buffer[16];
36076 + UCHAR mic_iv[16];
36077 + UCHAR mic_header1[16];
36078 + UCHAR mic_header2[16];
36079 + UCHAR MIC[8];
36080 + UCHAR TrailMIC[8];
36081 +
36082 +#ifdef RT_BIG_ENDIAN
36083 + RTMPFrameEndianChange(pAd, (PUCHAR)pData, DIR_READ, FALSE);
36084 +#endif
36085 +
36086 + fc0 = *pData;
36087 + fc1 = *(pData + 1);
36088 +
36089 + fc = *((PUSHORT)pData);
36090 +
36091 + frame_type = ((fc0 >> 2) & 0x03);
36092 + frame_subtype = ((fc0 >> 4) & 0x0f);
36093 +
36094 + from_ds = (fc1 & 0x2) >> 1;
36095 + to_ds = (fc1 & 0x1);
36096 +
36097 + a4_exists = (from_ds & to_ds);
36098 + qc_exists = ((frame_subtype == 0x08) || /* Assumed QoS subtypes */
36099 + (frame_subtype == 0x09) || /* Likely to change. */
36100 + (frame_subtype == 0x0a) ||
36101 + (frame_subtype == 0x0b)
36102 + );
36103 +
36104 + HeaderLen = 24;
36105 + if (a4_exists)
36106 + HeaderLen += 6;
36107 +
36108 + KeyID = *((PUCHAR)(pData+ HeaderLen + 3));
36109 + KeyID = KeyID >> 6;
36110 +
36111 + if (pWpaKey[KeyID].KeyLen == 0)
36112 + {
36113 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSoftDecryptAES failed!(KeyID[%d] Length can not be 0)\n", KeyID));
36114 + return FALSE;
36115 + }
36116 +
36117 + PN[0] = *(pData+ HeaderLen);
36118 + PN[1] = *(pData+ HeaderLen + 1);
36119 + PN[2] = *(pData+ HeaderLen + 4);
36120 + PN[3] = *(pData+ HeaderLen + 5);
36121 + PN[4] = *(pData+ HeaderLen + 6);
36122 + PN[5] = *(pData+ HeaderLen + 7);
36123 +
36124 + payload_len = DataByteCnt - HeaderLen - 8 - 8; // 8 bytes for CCMP header , 8 bytes for MIC
36125 + payload_remainder = (payload_len) % 16;
36126 + num_blocks = (payload_len) / 16;
36127 +
36128 +
36129 +
36130 + // Find start of payload
36131 + payload_index = HeaderLen + 8; //IV+EIV
36132 +
36133 + for (i=0; i< num_blocks; i++)
36134 + {
36135 + construct_ctr_preload(ctr_preload,
36136 + a4_exists,
36137 + qc_exists,
36138 + pData,
36139 + PN,
36140 + i+1 );
36141 +
36142 + aes128k128d(pWpaKey[KeyID].Key, ctr_preload, aes_out);
36143 +
36144 + bitwise_xor(aes_out, pData + payload_index, chain_buffer);
36145 + NdisMoveMemory(pData + payload_index - 8, chain_buffer, 16);
36146 + payload_index += 16;
36147 + }
36148 +
36149 + //
36150 + // If there is a short final block, then pad it
36151 + // encrypt it and copy the unpadded part back
36152 + //
36153 + if (payload_remainder > 0)
36154 + {
36155 + construct_ctr_preload(ctr_preload,
36156 + a4_exists,
36157 + qc_exists,
36158 + pData,
36159 + PN,
36160 + num_blocks + 1);
36161 +
36162 + NdisZeroMemory(padded_buffer, 16);
36163 + NdisMoveMemory(padded_buffer, pData + payload_index, payload_remainder);
36164 +
36165 + aes128k128d(pWpaKey[KeyID].Key, ctr_preload, aes_out);
36166 +
36167 + bitwise_xor(aes_out, padded_buffer, chain_buffer);
36168 + NdisMoveMemory(pData + payload_index - 8, chain_buffer, payload_remainder);
36169 + payload_index += payload_remainder;
36170 + }
36171 +
36172 + //
36173 + // Descrypt the MIC
36174 + //
36175 + construct_ctr_preload(ctr_preload,
36176 + a4_exists,
36177 + qc_exists,
36178 + pData,
36179 + PN,
36180 + 0);
36181 + NdisZeroMemory(padded_buffer, 16);
36182 + NdisMoveMemory(padded_buffer, pData + payload_index, 8);
36183 +
36184 + aes128k128d(pWpaKey[KeyID].Key, ctr_preload, aes_out);
36185 +
36186 + bitwise_xor(aes_out, padded_buffer, chain_buffer);
36187 +
36188 + NdisMoveMemory(TrailMIC, chain_buffer, 8);
36189 +
36190 + //
36191 + // Calculate MIC
36192 + //
36193 +
36194 + //Force the protected frame bit on
36195 + *(pData + 1) = *(pData + 1) | 0x40;
36196 +
36197 + // Find start of payload
36198 + // Because the CCMP header has been removed
36199 + payload_index = HeaderLen;
36200 +
36201 + construct_mic_iv(
36202 + mic_iv,
36203 + qc_exists,
36204 + a4_exists,
36205 + pData,
36206 + payload_len,
36207 + PN);
36208 +
36209 + construct_mic_header1(
36210 + mic_header1,
36211 + HeaderLen,
36212 + pData);
36213 +
36214 + construct_mic_header2(
36215 + mic_header2,
36216 + pData,
36217 + a4_exists,
36218 + qc_exists);
36219 +
36220 + aes128k128d(pWpaKey[KeyID].Key, mic_iv, aes_out);
36221 + bitwise_xor(aes_out, mic_header1, chain_buffer);
36222 + aes128k128d(pWpaKey[KeyID].Key, chain_buffer, aes_out);
36223 + bitwise_xor(aes_out, mic_header2, chain_buffer);
36224 + aes128k128d(pWpaKey[KeyID].Key, chain_buffer, aes_out);
36225 +
36226 + // iterate through each 16 byte payload block
36227 + for (i = 0; i < num_blocks; i++)
36228 + {
36229 + bitwise_xor(aes_out, pData + payload_index, chain_buffer);
36230 + payload_index += 16;
36231 + aes128k128d(pWpaKey[KeyID].Key, chain_buffer, aes_out);
36232 + }
36233 +
36234 + // Add on the final payload block if it needs padding
36235 + if (payload_remainder > 0)
36236 + {
36237 + NdisZeroMemory(padded_buffer, 16);
36238 + NdisMoveMemory(padded_buffer, pData + payload_index, payload_remainder);
36239 +
36240 + bitwise_xor(aes_out, padded_buffer, chain_buffer);
36241 + aes128k128d(pWpaKey[KeyID].Key, chain_buffer, aes_out);
36242 + }
36243 + // aes_out contains padded mic, discard most significant
36244 + // 8 bytes to generate 64 bit MIC
36245 + for (i = 0 ; i < 8; i++) MIC[i] = aes_out[i];
36246 +
36247 + if (!NdisEqualMemory(MIC, TrailMIC, 8))
36248 + {
36249 + DBGPRINT(RT_DEBUG_ERROR, ("RTMPSoftDecryptAES, MIC Error !\n")); //MIC error.
36250 + return FALSE;
36251 + }
36252 +
36253 +#ifdef RT_BIG_ENDIAN
36254 + RTMPFrameEndianChange(pAd, (PUCHAR)pData, DIR_READ, FALSE);
36255 +#endif
36256 +
36257 + return TRUE;
36258 +}
36259 +
36260 +/****************************************/
36261 +/* aes128k128d() */
36262 +/* Performs a 128 bit AES encrypt with */
36263 +/* 128 bit data. */
36264 +/****************************************/
36265 +VOID xor_128(
36266 + IN PUCHAR a,
36267 + IN PUCHAR b,
36268 + OUT PUCHAR out)
36269 +{
36270 + INT i;
36271 +
36272 + for (i=0;i<16; i++)
36273 + {
36274 + out[i] = a[i] ^ b[i];
36275 + }
36276 +}
36277 +
36278 +VOID next_key(
36279 + IN PUCHAR key,
36280 + IN INT round)
36281 +{
36282 + UCHAR rcon;
36283 + UCHAR sbox_key[4];
36284 + UCHAR rcon_table[12] =
36285 + {
36286 + 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80,
36287 + 0x1b, 0x36, 0x36, 0x36
36288 + };
36289 +
36290 + sbox_key[0] = RTMPCkipSbox(key[13]);
36291 + sbox_key[1] = RTMPCkipSbox(key[14]);
36292 + sbox_key[2] = RTMPCkipSbox(key[15]);
36293 + sbox_key[3] = RTMPCkipSbox(key[12]);
36294 +
36295 + rcon = rcon_table[round];
36296 +
36297 + xor_32(&key[0], sbox_key, &key[0]);
36298 + key[0] = key[0] ^ rcon;
36299 +
36300 + xor_32(&key[4], &key[0], &key[4]);
36301 + xor_32(&key[8], &key[4], &key[8]);
36302 + xor_32(&key[12], &key[8], &key[12]);
36303 +}
36304 +
36305 +VOID xor_32(
36306 + IN PUCHAR a,
36307 + IN PUCHAR b,
36308 + OUT PUCHAR out)
36309 +{
36310 + INT i;
36311 +
36312 + for (i=0;i<4; i++)
36313 + {
36314 + out[i] = a[i] ^ b[i];
36315 + }
36316 +}
36317 +
36318 +VOID byte_sub(
36319 + IN PUCHAR in,
36320 + OUT PUCHAR out)
36321 +{
36322 + INT i;
36323 +
36324 + for (i=0; i< 16; i++)
36325 + {
36326 + out[i] = RTMPCkipSbox(in[i]);
36327 + }
36328 +}
36329 +
36330 +UCHAR RTMPCkipSbox(
36331 + IN UCHAR a)
36332 +{
36333 + return SboxTable[(int)a];
36334 +}
36335 +
36336 +VOID shift_row(
36337 + IN PUCHAR in,
36338 + OUT PUCHAR out)
36339 +{
36340 + out[0] = in[0];
36341 + out[1] = in[5];
36342 + out[2] = in[10];
36343 + out[3] = in[15];
36344 + out[4] = in[4];
36345 + out[5] = in[9];
36346 + out[6] = in[14];
36347 + out[7] = in[3];
36348 + out[8] = in[8];
36349 + out[9] = in[13];
36350 + out[10] = in[2];
36351 + out[11] = in[7];
36352 + out[12] = in[12];
36353 + out[13] = in[1];
36354 + out[14] = in[6];
36355 + out[15] = in[11];
36356 +}
36357 +
36358 +VOID mix_column(
36359 + IN PUCHAR in,
36360 + OUT PUCHAR out)
36361 +{
36362 + INT i;
36363 + UCHAR add1b[4];
36364 + UCHAR add1bf7[4];
36365 + UCHAR rotl[4];
36366 + UCHAR swap_halfs[4];
36367 + UCHAR andf7[4];
36368 + UCHAR rotr[4];
36369 + UCHAR temp[4];
36370 + UCHAR tempb[4];
36371 +
36372 + for (i=0 ; i<4; i++)
36373 + {
36374 + if ((in[i] & 0x80)== 0x80)
36375 + add1b[i] = 0x1b;
36376 + else
36377 + add1b[i] = 0x00;
36378 + }
36379 +
36380 + swap_halfs[0] = in[2]; /* Swap halfs */
36381 + swap_halfs[1] = in[3];
36382 + swap_halfs[2] = in[0];
36383 + swap_halfs[3] = in[1];
36384 +
36385 + rotl[0] = in[3]; /* Rotate left 8 bits */
36386 + rotl[1] = in[0];
36387 + rotl[2] = in[1];
36388 + rotl[3] = in[2];
36389 +
36390 + andf7[0] = in[0] & 0x7f;
36391 + andf7[1] = in[1] & 0x7f;
36392 + andf7[2] = in[2] & 0x7f;
36393 + andf7[3] = in[3] & 0x7f;
36394 +
36395 + for (i = 3; i>0; i--) /* logical shift left 1 bit */
36396 + {
36397 + andf7[i] = andf7[i] << 1;
36398 + if ((andf7[i-1] & 0x80) == 0x80)
36399 + {
36400 + andf7[i] = (andf7[i] | 0x01);
36401 + }
36402 + }
36403 + andf7[0] = andf7[0] << 1;
36404 + andf7[0] = andf7[0] & 0xfe;
36405 +
36406 + xor_32(add1b, andf7, add1bf7);
36407 +
36408 + xor_32(in, add1bf7, rotr);
36409 +
36410 + temp[0] = rotr[0]; /* Rotate right 8 bits */
36411 + rotr[0] = rotr[1];
36412 + rotr[1] = rotr[2];
36413 + rotr[2] = rotr[3];
36414 + rotr[3] = temp[0];
36415 +
36416 + xor_32(add1bf7, rotr, temp);
36417 + xor_32(swap_halfs, rotl,tempb);
36418 + xor_32(temp, tempb, out);
36419 +}
36420 +
36421 --- /dev/null
36422 +++ b/drivers/staging/rt2860/common/rtmp_wep.c
36423 @@ -0,0 +1,499 @@
36424 +/*
36425 + *************************************************************************
36426 + * Ralink Tech Inc.
36427 + * 5F., No.36, Taiyuan St., Jhubei City,
36428 + * Hsinchu County 302,
36429 + * Taiwan, R.O.C.
36430 + *
36431 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
36432 + *
36433 + * This program is free software; you can redistribute it and/or modify *
36434 + * it under the terms of the GNU General Public License as published by *
36435 + * the Free Software Foundation; either version 2 of the License, or *
36436 + * (at your option) any later version. *
36437 + * *
36438 + * This program is distributed in the hope that it will be useful, *
36439 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
36440 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
36441 + * GNU General Public License for more details. *
36442 + * *
36443 + * You should have received a copy of the GNU General Public License *
36444 + * along with this program; if not, write to the *
36445 + * Free Software Foundation, Inc., *
36446 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
36447 + * *
36448 + *************************************************************************
36449 +
36450 + Module Name:
36451 + rtmp_wep.c
36452 +
36453 + Abstract:
36454 +
36455 + Revision History:
36456 + Who When What
36457 + -------- ---------- ----------------------------------------------
36458 + Paul Wu 10-28-02 Initial
36459 +*/
36460 +
36461 +#include "../rt_config.h"
36462 +
36463 +UINT FCSTAB_32[256] =
36464 +{
36465 + 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba,
36466 + 0x076dc419, 0x706af48f, 0xe963a535, 0x9e6495a3,
36467 + 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988,
36468 + 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91,
36469 + 0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de,
36470 + 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7,
36471 + 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec,
36472 + 0x14015c4f, 0x63066cd9, 0xfa0f3d63, 0x8d080df5,
36473 + 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172,
36474 + 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b,
36475 + 0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940,
36476 + 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59,
36477 + 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116,
36478 + 0x21b4f4b5, 0x56b3c423, 0xcfba9599, 0xb8bda50f,
36479 + 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924,
36480 + 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d,
36481 + 0x76dc4190, 0x01db7106, 0x98d220bc, 0xefd5102a,
36482 + 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433,
36483 + 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818,
36484 + 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01,
36485 + 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e,
36486 + 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457,
36487 + 0x65b0d9c6, 0x12b7e950, 0x8bbeb8ea, 0xfcb9887c,
36488 + 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65,
36489 + 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2,
36490 + 0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb,
36491 + 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0,
36492 + 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9,
36493 + 0x5005713c, 0x270241aa, 0xbe0b1010, 0xc90c2086,
36494 + 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
36495 + 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4,
36496 + 0x59b33d17, 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad,
36497 + 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a,
36498 + 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683,
36499 + 0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8,
36500 + 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1,
36501 + 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe,
36502 + 0xf762575d, 0x806567cb, 0x196c3671, 0x6e6b06e7,
36503 + 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc,
36504 + 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5,
36505 + 0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252,
36506 + 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b,
36507 + 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60,
36508 + 0xdf60efc3, 0xa867df55, 0x316e8eef, 0x4669be79,
36509 + 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236,
36510 + 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f,
36511 + 0xc5ba3bbe, 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04,
36512 + 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d,
36513 + 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a,
36514 + 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713,
36515 + 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38,
36516 + 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21,
36517 + 0x86d3d2d4, 0xf1d4e242, 0x68ddb3f8, 0x1fda836e,
36518 + 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777,
36519 + 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c,
36520 + 0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45,
36521 + 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2,
36522 + 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db,
36523 + 0xaed16a4a, 0xd9d65adc, 0x40df0b66, 0x37d83bf0,
36524 + 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
36525 + 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6,
36526 + 0xbad03605, 0xcdd70693, 0x54de5729, 0x23d967bf,
36527 + 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94,
36528 + 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d
36529 +};
36530 +
36531 +/*
36532 + ========================================================================
36533 +
36534 + Routine Description:
36535 + Init WEP function.
36536 +
36537 + Arguments:
36538 + pAd Pointer to our adapter
36539 + pKey Pointer to the WEP KEY
36540 + KeyId WEP Key ID
36541 + KeyLen the length of WEP KEY
36542 + pDest Pointer to the destination which Encryption data will store in.
36543 +
36544 + Return Value:
36545 + None
36546 +
36547 + IRQL = DISPATCH_LEVEL
36548 +
36549 + Note:
36550 +
36551 + ========================================================================
36552 +*/
36553 +VOID RTMPInitWepEngine(
36554 + IN PRTMP_ADAPTER pAd,
36555 + IN PUCHAR pKey,
36556 + IN UCHAR KeyId,
36557 + IN UCHAR KeyLen,
36558 + IN OUT PUCHAR pDest)
36559 +{
36560 + UINT i;
36561 + UCHAR WEPKEY[] = {
36562 + //IV
36563 + 0x00, 0x11, 0x22,
36564 + //WEP KEY
36565 + 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88, 0x99, 0xAA, 0xBB, 0xCC
36566 + };
36567 +
36568 + pAd->PrivateInfo.FCSCRC32 = PPPINITFCS32; //Init crc32.
36569 +
36570 +#ifdef CONFIG_STA_SUPPORT
36571 + if (pAd->StaCfg.bCkipOn && (pAd->StaCfg.CkipFlag & 0x10) && (pAd->OpMode == OPMODE_STA))
36572 + {
36573 + ARCFOUR_INIT(&pAd->PrivateInfo.WEPCONTEXT, pKey, KeyLen); //INIT SBOX, KEYLEN+3(IV)
36574 + NdisMoveMemory(pDest, pKey, 3); //Append Init Vector
36575 + }
36576 + else
36577 +#endif // CONFIG_STA_SUPPORT //
36578 + {
36579 + NdisMoveMemory(WEPKEY + 3, pKey, KeyLen);
36580 +
36581 + for(i = 0; i < 3; i++)
36582 + WEPKEY[i] = RandomByte(pAd); //Call mlme RandomByte() function.
36583 + ARCFOUR_INIT(&pAd->PrivateInfo.WEPCONTEXT, WEPKEY, KeyLen + 3); //INIT SBOX, KEYLEN+3(IV)
36584 +
36585 + NdisMoveMemory(pDest, WEPKEY, 3); //Append Init Vector
36586 + }
36587 + *(pDest+3) = (KeyId << 6); //Append KEYID
36588 +
36589 +}
36590 +
36591 +/*
36592 + ========================================================================
36593 +
36594 + Routine Description:
36595 + Encrypt transimitted data
36596 +
36597 + Arguments:
36598 + pAd Pointer to our adapter
36599 + pSrc Pointer to the transimitted source data that will be encrypt
36600 + pDest Pointer to the destination where entryption data will be store in.
36601 + Len Indicate the length of the source data
36602 +
36603 + Return Value:
36604 + None
36605 +
36606 + IRQL = DISPATCH_LEVEL
36607 +
36608 + Note:
36609 +
36610 + ========================================================================
36611 +*/
36612 +VOID RTMPEncryptData(
36613 + IN PRTMP_ADAPTER pAd,
36614 + IN PUCHAR pSrc,
36615 + IN PUCHAR pDest,
36616 + IN UINT Len)
36617 +{
36618 + pAd->PrivateInfo.FCSCRC32 = RTMP_CALC_FCS32(pAd->PrivateInfo.FCSCRC32, pSrc, Len);
36619 + ARCFOUR_ENCRYPT(&pAd->PrivateInfo.WEPCONTEXT, pDest, pSrc, Len);
36620 +}
36621 +
36622 +
36623 +/*
36624 + ========================================================================
36625 +
36626 + Routine Description:
36627 + Decrypt received WEP data
36628 +
36629 + Arguments:
36630 + pAdapter Pointer to our adapter
36631 + pSrc Pointer to the received data
36632 + Len the length of the received data
36633 +
36634 + Return Value:
36635 + TRUE Decrypt WEP data success
36636 + FALSE Decrypt WEP data failed
36637 +
36638 + Note:
36639 +
36640 + ========================================================================
36641 +*/
36642 +BOOLEAN RTMPSoftDecryptWEP(
36643 + IN PRTMP_ADAPTER pAd,
36644 + IN PUCHAR pData,
36645 + IN ULONG DataByteCnt,
36646 + IN PCIPHER_KEY pGroupKey)
36647 +{
36648 + UINT trailfcs;
36649 + UINT crc32;
36650 + UCHAR KeyIdx;
36651 + UCHAR WEPKEY[] = {
36652 + //IV
36653 + 0x00, 0x11, 0x22,
36654 + //WEP KEY
36655 + 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88, 0x99, 0xAA, 0xBB, 0xCC
36656 + };
36657 + UCHAR *pPayload = (UCHAR *)pData + LENGTH_802_11;
36658 + ULONG payload_len = DataByteCnt - LENGTH_802_11;
36659 +
36660 + NdisMoveMemory(WEPKEY, pPayload, 3); //Get WEP IV
36661 +
36662 + KeyIdx = (*(pPayload + 3) & 0xc0) >> 6;
36663 + if (pGroupKey[KeyIdx].KeyLen == 0)
36664 + return (FALSE);
36665 +
36666 + NdisMoveMemory(WEPKEY + 3, pGroupKey[KeyIdx].Key, pGroupKey[KeyIdx].KeyLen);
36667 + ARCFOUR_INIT(&pAd->PrivateInfo.WEPCONTEXT, WEPKEY, pGroupKey[KeyIdx].KeyLen + 3);
36668 + ARCFOUR_DECRYPT(&pAd->PrivateInfo.WEPCONTEXT, pPayload, pPayload + 4, payload_len - 4);
36669 + NdisMoveMemory(&trailfcs, pPayload + payload_len - 8, 4);
36670 + crc32 = RTMP_CALC_FCS32(PPPINITFCS32, pPayload, payload_len - 8); //Skip last 4 bytes(FCS).
36671 + crc32 ^= 0xffffffff; /* complement */
36672 +
36673 + if(crc32 != cpu2le32(trailfcs))
36674 + {
36675 + DBGPRINT(RT_DEBUG_TRACE, ("! WEP Data CRC Error !\n")); //CRC error.
36676 + return (FALSE);
36677 + }
36678 + return (TRUE);
36679 +}
36680 +
36681 +/*
36682 + ========================================================================
36683 +
36684 + Routine Description:
36685 + The Stream Cipher Encryption Algorithm "ARCFOUR" initialize
36686 +
36687 + Arguments:
36688 + Ctx Pointer to ARCFOUR CONTEXT (SBOX)
36689 + pKey Pointer to the WEP KEY
36690 + KeyLen Indicate the length fo the WEP KEY
36691 +
36692 + Return Value:
36693 + None
36694 +
36695 + IRQL = DISPATCH_LEVEL
36696 +
36697 + Note:
36698 +
36699 + ========================================================================
36700 +*/
36701 +VOID ARCFOUR_INIT(
36702 + IN PARCFOURCONTEXT Ctx,
36703 + IN PUCHAR pKey,
36704 + IN UINT KeyLen)
36705 +{
36706 + UCHAR t, u;
36707 + UINT keyindex;
36708 + UINT stateindex;
36709 + PUCHAR state;
36710 + UINT counter;
36711 +
36712 + state = Ctx->STATE;
36713 + Ctx->X = 0;
36714 + Ctx->Y = 0;
36715 + for (counter = 0; counter < 256; counter++)
36716 + state[counter] = (UCHAR)counter;
36717 + keyindex = 0;
36718 + stateindex = 0;
36719 + for (counter = 0; counter < 256; counter++)
36720 + {
36721 + t = state[counter];
36722 + stateindex = (stateindex + pKey[keyindex] + t) & 0xff;
36723 + u = state[stateindex];
36724 + state[stateindex] = t;
36725 + state[counter] = u;
36726 + if (++keyindex >= KeyLen)
36727 + keyindex = 0;
36728 + }
36729 +}
36730 +
36731 +/*
36732 + ========================================================================
36733 +
36734 + Routine Description:
36735 + Get bytes from ARCFOUR CONTEXT (S-BOX)
36736 +
36737 + Arguments:
36738 + Ctx Pointer to ARCFOUR CONTEXT (SBOX)
36739 +
36740 + Return Value:
36741 + UCHAR - the value of the ARCFOUR CONTEXT (S-BOX)
36742 +
36743 + Note:
36744 +
36745 + ========================================================================
36746 +*/
36747 +UCHAR ARCFOUR_BYTE(
36748 + IN PARCFOURCONTEXT Ctx)
36749 +{
36750 + UINT x;
36751 + UINT y;
36752 + UCHAR sx, sy;
36753 + PUCHAR state;
36754 +
36755 + state = Ctx->STATE;
36756 + x = (Ctx->X + 1) & 0xff;
36757 + sx = state[x];
36758 + y = (sx + Ctx->Y) & 0xff;
36759 + sy = state[y];
36760 + Ctx->X = x;
36761 + Ctx->Y = y;
36762 + state[y] = sx;
36763 + state[x] = sy;
36764 +
36765 + return(state[(sx + sy) & 0xff]);
36766 +
36767 +}
36768 +
36769 +/*
36770 + ========================================================================
36771 +
36772 + Routine Description:
36773 + The Stream Cipher Decryption Algorithm
36774 +
36775 + Arguments:
36776 + Ctx Pointer to ARCFOUR CONTEXT (SBOX)
36777 + pDest Pointer to the Destination
36778 + pSrc Pointer to the Source data
36779 + Len Indicate the length of the Source data
36780 +
36781 + Return Value:
36782 + None
36783 +
36784 + Note:
36785 +
36786 + ========================================================================
36787 +*/
36788 +VOID ARCFOUR_DECRYPT(
36789 + IN PARCFOURCONTEXT Ctx,
36790 + IN PUCHAR pDest,
36791 + IN PUCHAR pSrc,
36792 + IN UINT Len)
36793 +{
36794 + UINT i;
36795 +
36796 + for (i = 0; i < Len; i++)
36797 + pDest[i] = pSrc[i] ^ ARCFOUR_BYTE(Ctx);
36798 +}
36799 +
36800 +/*
36801 + ========================================================================
36802 +
36803 + Routine Description:
36804 + The Stream Cipher Encryption Algorithm
36805 +
36806 + Arguments:
36807 + Ctx Pointer to ARCFOUR CONTEXT (SBOX)
36808 + pDest Pointer to the Destination
36809 + pSrc Pointer to the Source data
36810 + Len Indicate the length of the Source dta
36811 +
36812 + Return Value:
36813 + None
36814 +
36815 + IRQL = DISPATCH_LEVEL
36816 +
36817 + Note:
36818 +
36819 + ========================================================================
36820 +*/
36821 +VOID ARCFOUR_ENCRYPT(
36822 + IN PARCFOURCONTEXT Ctx,
36823 + IN PUCHAR pDest,
36824 + IN PUCHAR pSrc,
36825 + IN UINT Len)
36826 +{
36827 + UINT i;
36828 +
36829 + for (i = 0; i < Len; i++)
36830 + pDest[i] = pSrc[i] ^ ARCFOUR_BYTE(Ctx);
36831 +}
36832 +
36833 +/*
36834 + ========================================================================
36835 +
36836 + Routine Description:
36837 + The Stream Cipher Encryption Algorithm which conform to the special requirement to encrypt GTK.
36838 +
36839 + Arguments:
36840 + Ctx Pointer to ARCFOUR CONTEXT (SBOX)
36841 + pDest Pointer to the Destination
36842 + pSrc Pointer to the Source data
36843 + Len Indicate the length of the Source dta
36844 +
36845 +
36846 + ========================================================================
36847 +*/
36848 +
36849 +VOID WPAARCFOUR_ENCRYPT(
36850 + IN PARCFOURCONTEXT Ctx,
36851 + IN PUCHAR pDest,
36852 + IN PUCHAR pSrc,
36853 + IN UINT Len)
36854 +{
36855 + UINT i;
36856 + //discard first 256 bytes
36857 + for (i = 0; i < 256; i++)
36858 + ARCFOUR_BYTE(Ctx);
36859 +
36860 + for (i = 0; i < Len; i++)
36861 + pDest[i] = pSrc[i] ^ ARCFOUR_BYTE(Ctx);
36862 +}
36863 +
36864 +
36865 +/*
36866 + ========================================================================
36867 +
36868 + Routine Description:
36869 + Calculate a new FCS given the current FCS and the new data.
36870 +
36871 + Arguments:
36872 + Fcs the original FCS value
36873 + Cp pointer to the data which will be calculate the FCS
36874 + Len the length of the data
36875 +
36876 + Return Value:
36877 + UINT - FCS 32 bits
36878 +
36879 + IRQL = DISPATCH_LEVEL
36880 +
36881 + Note:
36882 +
36883 + ========================================================================
36884 +*/
36885 +UINT RTMP_CALC_FCS32(
36886 + IN UINT Fcs,
36887 + IN PUCHAR Cp,
36888 + IN INT Len)
36889 +{
36890 + while (Len--)
36891 + Fcs = (((Fcs) >> 8) ^ FCSTAB_32[((Fcs) ^ (*Cp++)) & 0xff]);
36892 +
36893 + return (Fcs);
36894 +}
36895 +
36896 +
36897 +/*
36898 + ========================================================================
36899 +
36900 + Routine Description:
36901 + Get last FCS and encrypt it to the destination
36902 +
36903 + Arguments:
36904 + pDest Pointer to the Destination
36905 +
36906 + Return Value:
36907 + None
36908 +
36909 + Note:
36910 +
36911 + ========================================================================
36912 +*/
36913 +VOID RTMPSetICV(
36914 + IN PRTMP_ADAPTER pAd,
36915 + IN PUCHAR pDest)
36916 +{
36917 + pAd->PrivateInfo.FCSCRC32 ^= 0xffffffff; /* complement */
36918 + pAd->PrivateInfo.FCSCRC32 = cpu2le32(pAd->PrivateInfo.FCSCRC32);
36919 +
36920 + ARCFOUR_ENCRYPT(&pAd->PrivateInfo.WEPCONTEXT, pDest, (PUCHAR) &pAd->PrivateInfo.FCSCRC32, 4);
36921 +}
36922 +
36923 --- /dev/null
36924 +++ b/drivers/staging/rt2860/common/spectrum.c
36925 @@ -0,0 +1,1877 @@
36926 +/*
36927 + *************************************************************************
36928 + * Ralink Tech Inc.
36929 + * 5F., No.36, Taiyuan St., Jhubei City,
36930 + * Hsinchu County 302,
36931 + * Taiwan, R.O.C.
36932 + *
36933 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
36934 + *
36935 + * This program is free software; you can redistribute it and/or modify *
36936 + * it under the terms of the GNU General Public License as published by *
36937 + * the Free Software Foundation; either version 2 of the License, or *
36938 + * (at your option) any later version. *
36939 + * *
36940 + * This program is distributed in the hope that it will be useful, *
36941 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
36942 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
36943 + * GNU General Public License for more details. *
36944 + * *
36945 + * You should have received a copy of the GNU General Public License *
36946 + * along with this program; if not, write to the *
36947 + * Free Software Foundation, Inc., *
36948 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
36949 + * *
36950 + *************************************************************************
36951 +
36952 +
36953 + Module Name:
36954 + action.c
36955 +
36956 + Abstract:
36957 + Handle association related requests either from WSTA or from local MLME
36958 +
36959 + Revision History:
36960 + Who When What
36961 + --------- ---------- ----------------------------------------------
36962 + Fonchi Wu 2008 created for 802.11h
36963 + */
36964 +
36965 +#include "../rt_config.h"
36966 +#include "action.h"
36967 +
36968 +VOID MeasureReqTabInit(
36969 + IN PRTMP_ADAPTER pAd)
36970 +{
36971 + NdisAllocateSpinLock(&pAd->CommonCfg.MeasureReqTabLock);
36972 +
36973 + pAd->CommonCfg.pMeasureReqTab = kmalloc(sizeof(MEASURE_REQ_TAB), GFP_ATOMIC);
36974 + if (pAd->CommonCfg.pMeasureReqTab)
36975 + NdisZeroMemory(pAd->CommonCfg.pMeasureReqTab, sizeof(MEASURE_REQ_TAB));
36976 + else
36977 + DBGPRINT(RT_DEBUG_ERROR, ("%s Fail to alloc memory for pAd->CommonCfg.pMeasureReqTab.\n", __FUNCTION__));
36978 +
36979 + return;
36980 +}
36981 +
36982 +VOID MeasureReqTabExit(
36983 + IN PRTMP_ADAPTER pAd)
36984 +{
36985 + NdisFreeSpinLock(pAd->CommonCfg.MeasureReqTabLock);
36986 +
36987 + if (pAd->CommonCfg.pMeasureReqTab)
36988 + kfree(pAd->CommonCfg.pMeasureReqTab);
36989 + pAd->CommonCfg.pMeasureReqTab = NULL;
36990 +
36991 + return;
36992 +}
36993 +
36994 +static PMEASURE_REQ_ENTRY MeasureReqLookUp(
36995 + IN PRTMP_ADAPTER pAd,
36996 + IN UINT8 DialogToken)
36997 +{
36998 + UINT HashIdx;
36999 + PMEASURE_REQ_TAB pTab = pAd->CommonCfg.pMeasureReqTab;
37000 + PMEASURE_REQ_ENTRY pEntry = NULL;
37001 + PMEASURE_REQ_ENTRY pPrevEntry = NULL;
37002 +
37003 + if (pTab == NULL)
37004 + {
37005 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pMeasureReqTab doesn't exist.\n", __FUNCTION__));
37006 + return NULL;
37007 + }
37008 +
37009 + RTMP_SEM_LOCK(&pAd->CommonCfg.MeasureReqTabLock);
37010 +
37011 + HashIdx = MQ_DIALOGTOKEN_HASH_INDEX(DialogToken);
37012 + pEntry = pTab->Hash[HashIdx];
37013 +
37014 + while (pEntry)
37015 + {
37016 + if (pEntry->DialogToken == DialogToken)
37017 + break;
37018 + else
37019 + {
37020 + pPrevEntry = pEntry;
37021 + pEntry = pEntry->pNext;
37022 + }
37023 + }
37024 +
37025 + RTMP_SEM_UNLOCK(&pAd->CommonCfg.MeasureReqTabLock);
37026 +
37027 + return pEntry;
37028 +}
37029 +
37030 +static PMEASURE_REQ_ENTRY MeasureReqInsert(
37031 + IN PRTMP_ADAPTER pAd,
37032 + IN UINT8 DialogToken)
37033 +{
37034 + INT i;
37035 + ULONG HashIdx;
37036 + PMEASURE_REQ_TAB pTab = pAd->CommonCfg.pMeasureReqTab;
37037 + PMEASURE_REQ_ENTRY pEntry = NULL, pCurrEntry;
37038 + ULONG Now;
37039 +
37040 + if(pTab == NULL)
37041 + {
37042 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pMeasureReqTab doesn't exist.\n", __FUNCTION__));
37043 + return NULL;
37044 + }
37045 +
37046 + pEntry = MeasureReqLookUp(pAd, DialogToken);
37047 + if (pEntry == NULL)
37048 + {
37049 + RTMP_SEM_LOCK(&pAd->CommonCfg.MeasureReqTabLock);
37050 + for (i = 0; i < MAX_MEASURE_REQ_TAB_SIZE; i++)
37051 + {
37052 + NdisGetSystemUpTime(&Now);
37053 + pEntry = &pTab->Content[i];
37054 +
37055 + if ((pEntry->Valid == TRUE)
37056 + && RTMP_TIME_AFTER((unsigned long)Now, (unsigned long)(pEntry->lastTime + MQ_REQ_AGE_OUT)))
37057 + {
37058 + PMEASURE_REQ_ENTRY pPrevEntry = NULL;
37059 + ULONG HashIdx = MQ_DIALOGTOKEN_HASH_INDEX(pEntry->DialogToken);
37060 + PMEASURE_REQ_ENTRY pProbeEntry = pTab->Hash[HashIdx];
37061 +
37062 + // update Hash list
37063 + do
37064 + {
37065 + if (pProbeEntry == pEntry)
37066 + {
37067 + if (pPrevEntry == NULL)
37068 + {
37069 + pTab->Hash[HashIdx] = pEntry->pNext;
37070 + }
37071 + else
37072 + {
37073 + pPrevEntry->pNext = pEntry->pNext;
37074 + }
37075 + break;
37076 + }
37077 +
37078 + pPrevEntry = pProbeEntry;
37079 + pProbeEntry = pProbeEntry->pNext;
37080 + } while (pProbeEntry);
37081 +
37082 + NdisZeroMemory(pEntry, sizeof(MEASURE_REQ_ENTRY));
37083 + pTab->Size--;
37084 +
37085 + break;
37086 + }
37087 +
37088 + if (pEntry->Valid == FALSE)
37089 + break;
37090 + }
37091 +
37092 + if (i < MAX_MEASURE_REQ_TAB_SIZE)
37093 + {
37094 + NdisGetSystemUpTime(&Now);
37095 + pEntry->lastTime = Now;
37096 + pEntry->Valid = TRUE;
37097 + pEntry->DialogToken = DialogToken;
37098 + pTab->Size++;
37099 + }
37100 + else
37101 + {
37102 + pEntry = NULL;
37103 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pMeasureReqTab tab full.\n", __FUNCTION__));
37104 + }
37105 +
37106 + // add this Neighbor entry into HASH table
37107 + if (pEntry)
37108 + {
37109 + HashIdx = MQ_DIALOGTOKEN_HASH_INDEX(DialogToken);
37110 + if (pTab->Hash[HashIdx] == NULL)
37111 + {
37112 + pTab->Hash[HashIdx] = pEntry;
37113 + }
37114 + else
37115 + {
37116 + pCurrEntry = pTab->Hash[HashIdx];
37117 + while (pCurrEntry->pNext != NULL)
37118 + pCurrEntry = pCurrEntry->pNext;
37119 + pCurrEntry->pNext = pEntry;
37120 + }
37121 + }
37122 +
37123 + RTMP_SEM_UNLOCK(&pAd->CommonCfg.MeasureReqTabLock);
37124 + }
37125 +
37126 + return pEntry;
37127 +}
37128 +
37129 +static VOID MeasureReqDelete(
37130 + IN PRTMP_ADAPTER pAd,
37131 + IN UINT8 DialogToken)
37132 +{
37133 + PMEASURE_REQ_TAB pTab = pAd->CommonCfg.pMeasureReqTab;
37134 + PMEASURE_REQ_ENTRY pEntry = NULL;
37135 +
37136 + if(pTab == NULL)
37137 + {
37138 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pMeasureReqTab doesn't exist.\n", __FUNCTION__));
37139 + return;
37140 + }
37141 +
37142 + // if empty, return
37143 + if (pTab->Size == 0)
37144 + {
37145 + DBGPRINT(RT_DEBUG_ERROR, ("pMeasureReqTab empty.\n"));
37146 + return;
37147 + }
37148 +
37149 + pEntry = MeasureReqLookUp(pAd, DialogToken);
37150 + if (pEntry != NULL)
37151 + {
37152 + PMEASURE_REQ_ENTRY pPrevEntry = NULL;
37153 + ULONG HashIdx = MQ_DIALOGTOKEN_HASH_INDEX(pEntry->DialogToken);
37154 + PMEASURE_REQ_ENTRY pProbeEntry = pTab->Hash[HashIdx];
37155 +
37156 + RTMP_SEM_LOCK(&pAd->CommonCfg.MeasureReqTabLock);
37157 + // update Hash list
37158 + do
37159 + {
37160 + if (pProbeEntry == pEntry)
37161 + {
37162 + if (pPrevEntry == NULL)
37163 + {
37164 + pTab->Hash[HashIdx] = pEntry->pNext;
37165 + }
37166 + else
37167 + {
37168 + pPrevEntry->pNext = pEntry->pNext;
37169 + }
37170 + break;
37171 + }
37172 +
37173 + pPrevEntry = pProbeEntry;
37174 + pProbeEntry = pProbeEntry->pNext;
37175 + } while (pProbeEntry);
37176 +
37177 + NdisZeroMemory(pEntry, sizeof(MEASURE_REQ_ENTRY));
37178 + pTab->Size--;
37179 +
37180 + RTMP_SEM_UNLOCK(&pAd->CommonCfg.MeasureReqTabLock);
37181 + }
37182 +
37183 + return;
37184 +}
37185 +
37186 +VOID TpcReqTabInit(
37187 + IN PRTMP_ADAPTER pAd)
37188 +{
37189 + NdisAllocateSpinLock(&pAd->CommonCfg.TpcReqTabLock);
37190 +
37191 + pAd->CommonCfg.pTpcReqTab = kmalloc(sizeof(TPC_REQ_TAB), GFP_ATOMIC);
37192 + if (pAd->CommonCfg.pTpcReqTab)
37193 + NdisZeroMemory(pAd->CommonCfg.pTpcReqTab, sizeof(TPC_REQ_TAB));
37194 + else
37195 + DBGPRINT(RT_DEBUG_ERROR, ("%s Fail to alloc memory for pAd->CommonCfg.pTpcReqTab.\n", __FUNCTION__));
37196 +
37197 + return;
37198 +}
37199 +
37200 +VOID TpcReqTabExit(
37201 + IN PRTMP_ADAPTER pAd)
37202 +{
37203 + NdisFreeSpinLock(pAd->CommonCfg.TpcReqTabLock);
37204 +
37205 + if (pAd->CommonCfg.pTpcReqTab)
37206 + kfree(pAd->CommonCfg.pTpcReqTab);
37207 + pAd->CommonCfg.pTpcReqTab = NULL;
37208 +
37209 + return;
37210 +}
37211 +
37212 +static PTPC_REQ_ENTRY TpcReqLookUp(
37213 + IN PRTMP_ADAPTER pAd,
37214 + IN UINT8 DialogToken)
37215 +{
37216 + UINT HashIdx;
37217 + PTPC_REQ_TAB pTab = pAd->CommonCfg.pTpcReqTab;
37218 + PTPC_REQ_ENTRY pEntry = NULL;
37219 + PTPC_REQ_ENTRY pPrevEntry = NULL;
37220 +
37221 + if (pTab == NULL)
37222 + {
37223 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pTpcReqTab doesn't exist.\n", __FUNCTION__));
37224 + return NULL;
37225 + }
37226 +
37227 + RTMP_SEM_LOCK(&pAd->CommonCfg.TpcReqTabLock);
37228 +
37229 + HashIdx = TPC_DIALOGTOKEN_HASH_INDEX(DialogToken);
37230 + pEntry = pTab->Hash[HashIdx];
37231 +
37232 + while (pEntry)
37233 + {
37234 + if (pEntry->DialogToken == DialogToken)
37235 + break;
37236 + else
37237 + {
37238 + pPrevEntry = pEntry;
37239 + pEntry = pEntry->pNext;
37240 + }
37241 + }
37242 +
37243 + RTMP_SEM_UNLOCK(&pAd->CommonCfg.TpcReqTabLock);
37244 +
37245 + return pEntry;
37246 +}
37247 +
37248 +
37249 +static PTPC_REQ_ENTRY TpcReqInsert(
37250 + IN PRTMP_ADAPTER pAd,
37251 + IN UINT8 DialogToken)
37252 +{
37253 + INT i;
37254 + ULONG HashIdx;
37255 + PTPC_REQ_TAB pTab = pAd->CommonCfg.pTpcReqTab;
37256 + PTPC_REQ_ENTRY pEntry = NULL, pCurrEntry;
37257 + ULONG Now;
37258 +
37259 + if(pTab == NULL)
37260 + {
37261 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pTpcReqTab doesn't exist.\n", __FUNCTION__));
37262 + return NULL;
37263 + }
37264 +
37265 + pEntry = TpcReqLookUp(pAd, DialogToken);
37266 + if (pEntry == NULL)
37267 + {
37268 + RTMP_SEM_LOCK(&pAd->CommonCfg.TpcReqTabLock);
37269 + for (i = 0; i < MAX_TPC_REQ_TAB_SIZE; i++)
37270 + {
37271 + NdisGetSystemUpTime(&Now);
37272 + pEntry = &pTab->Content[i];
37273 +
37274 + if ((pEntry->Valid == TRUE)
37275 + && RTMP_TIME_AFTER((unsigned long)Now, (unsigned long)(pEntry->lastTime + TPC_REQ_AGE_OUT)))
37276 + {
37277 + PTPC_REQ_ENTRY pPrevEntry = NULL;
37278 + ULONG HashIdx = TPC_DIALOGTOKEN_HASH_INDEX(pEntry->DialogToken);
37279 + PTPC_REQ_ENTRY pProbeEntry = pTab->Hash[HashIdx];
37280 +
37281 + // update Hash list
37282 + do
37283 + {
37284 + if (pProbeEntry == pEntry)
37285 + {
37286 + if (pPrevEntry == NULL)
37287 + {
37288 + pTab->Hash[HashIdx] = pEntry->pNext;
37289 + }
37290 + else
37291 + {
37292 + pPrevEntry->pNext = pEntry->pNext;
37293 + }
37294 + break;
37295 + }
37296 +
37297 + pPrevEntry = pProbeEntry;
37298 + pProbeEntry = pProbeEntry->pNext;
37299 + } while (pProbeEntry);
37300 +
37301 + NdisZeroMemory(pEntry, sizeof(TPC_REQ_ENTRY));
37302 + pTab->Size--;
37303 +
37304 + break;
37305 + }
37306 +
37307 + if (pEntry->Valid == FALSE)
37308 + break;
37309 + }
37310 +
37311 + if (i < MAX_TPC_REQ_TAB_SIZE)
37312 + {
37313 + NdisGetSystemUpTime(&Now);
37314 + pEntry->lastTime = Now;
37315 + pEntry->Valid = TRUE;
37316 + pEntry->DialogToken = DialogToken;
37317 + pTab->Size++;
37318 + }
37319 + else
37320 + {
37321 + pEntry = NULL;
37322 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pTpcReqTab tab full.\n", __FUNCTION__));
37323 + }
37324 +
37325 + // add this Neighbor entry into HASH table
37326 + if (pEntry)
37327 + {
37328 + HashIdx = TPC_DIALOGTOKEN_HASH_INDEX(DialogToken);
37329 + if (pTab->Hash[HashIdx] == NULL)
37330 + {
37331 + pTab->Hash[HashIdx] = pEntry;
37332 + }
37333 + else
37334 + {
37335 + pCurrEntry = pTab->Hash[HashIdx];
37336 + while (pCurrEntry->pNext != NULL)
37337 + pCurrEntry = pCurrEntry->pNext;
37338 + pCurrEntry->pNext = pEntry;
37339 + }
37340 + }
37341 +
37342 + RTMP_SEM_UNLOCK(&pAd->CommonCfg.TpcReqTabLock);
37343 + }
37344 +
37345 + return pEntry;
37346 +}
37347 +
37348 +static VOID TpcReqDelete(
37349 + IN PRTMP_ADAPTER pAd,
37350 + IN UINT8 DialogToken)
37351 +{
37352 + PTPC_REQ_TAB pTab = pAd->CommonCfg.pTpcReqTab;
37353 + PTPC_REQ_ENTRY pEntry = NULL;
37354 +
37355 + if(pTab == NULL)
37356 + {
37357 + DBGPRINT(RT_DEBUG_ERROR, ("%s: pTpcReqTab doesn't exist.\n", __FUNCTION__));
37358 + return;
37359 + }
37360 +
37361 + // if empty, return
37362 + if (pTab->Size == 0)
37363 + {
37364 + DBGPRINT(RT_DEBUG_ERROR, ("pTpcReqTab empty.\n"));
37365 + return;
37366 + }
37367 +
37368 + pEntry = TpcReqLookUp(pAd, DialogToken);
37369 + if (pEntry != NULL)
37370 + {
37371 + PTPC_REQ_ENTRY pPrevEntry = NULL;
37372 + ULONG HashIdx = TPC_DIALOGTOKEN_HASH_INDEX(pEntry->DialogToken);
37373 + PTPC_REQ_ENTRY pProbeEntry = pTab->Hash[HashIdx];
37374 +
37375 + RTMP_SEM_LOCK(&pAd->CommonCfg.TpcReqTabLock);
37376 + // update Hash list
37377 + do
37378 + {
37379 + if (pProbeEntry == pEntry)
37380 + {
37381 + if (pPrevEntry == NULL)
37382 + {
37383 + pTab->Hash[HashIdx] = pEntry->pNext;
37384 + }
37385 + else
37386 + {
37387 + pPrevEntry->pNext = pEntry->pNext;
37388 + }
37389 + break;
37390 + }
37391 +
37392 + pPrevEntry = pProbeEntry;
37393 + pProbeEntry = pProbeEntry->pNext;
37394 + } while (pProbeEntry);
37395 +
37396 + NdisZeroMemory(pEntry, sizeof(TPC_REQ_ENTRY));
37397 + pTab->Size--;
37398 +
37399 + RTMP_SEM_UNLOCK(&pAd->CommonCfg.TpcReqTabLock);
37400 + }
37401 +
37402 + return;
37403 +}
37404 +
37405 +/*
37406 + ==========================================================================
37407 + Description:
37408 + Get Current TimeS tamp.
37409 +
37410 + Parametrs:
37411 +
37412 + Return : Current Time Stamp.
37413 + ==========================================================================
37414 + */
37415 +static UINT64 GetCurrentTimeStamp(
37416 + IN PRTMP_ADAPTER pAd)
37417 +{
37418 + // get current time stamp.
37419 + return 0;
37420 +}
37421 +
37422 +/*
37423 + ==========================================================================
37424 + Description:
37425 + Get Current Transmit Power.
37426 +
37427 + Parametrs:
37428 +
37429 + Return : Current Time Stamp.
37430 + ==========================================================================
37431 + */
37432 +static UINT8 GetCurTxPwr(
37433 + IN PRTMP_ADAPTER pAd,
37434 + IN UINT8 Wcid)
37435 +{
37436 + return 16; /* 16 dBm */
37437 +}
37438 +
37439 +/*
37440 + ==========================================================================
37441 + Description:
37442 + Insert Dialog Token into frame.
37443 +
37444 + Parametrs:
37445 + 1. frame buffer pointer.
37446 + 2. frame length.
37447 + 3. Dialog token.
37448 +
37449 + Return : None.
37450 + ==========================================================================
37451 + */
37452 +static VOID InsertDialogToken(
37453 + IN PRTMP_ADAPTER pAd,
37454 + OUT PUCHAR pFrameBuf,
37455 + OUT PULONG pFrameLen,
37456 + IN UINT8 DialogToken)
37457 +{
37458 + ULONG TempLen;
37459 + MakeOutgoingFrame(pFrameBuf, &TempLen,
37460 + 1, &DialogToken,
37461 + END_OF_ARGS);
37462 +
37463 + *pFrameLen = *pFrameLen + TempLen;
37464 +
37465 + return;
37466 +}
37467 +
37468 +/*
37469 + ==========================================================================
37470 + Description:
37471 + Insert TPC Request IE into frame.
37472 +
37473 + Parametrs:
37474 + 1. frame buffer pointer.
37475 + 2. frame length.
37476 +
37477 + Return : None.
37478 + ==========================================================================
37479 + */
37480 + static VOID InsertTpcReqIE(
37481 + IN PRTMP_ADAPTER pAd,
37482 + OUT PUCHAR pFrameBuf,
37483 + OUT PULONG pFrameLen)
37484 +{
37485 + ULONG TempLen;
37486 + ULONG Len = 0;
37487 + UINT8 ElementID = IE_TPC_REQUEST;
37488 +
37489 + MakeOutgoingFrame(pFrameBuf, &TempLen,
37490 + 1, &ElementID,
37491 + 1, &Len,
37492 + END_OF_ARGS);
37493 +
37494 + *pFrameLen = *pFrameLen + TempLen;
37495 +
37496 + return;
37497 +}
37498 +
37499 +/*
37500 + ==========================================================================
37501 + Description:
37502 + Insert TPC Report IE into frame.
37503 +
37504 + Parametrs:
37505 + 1. frame buffer pointer.
37506 + 2. frame length.
37507 + 3. Transmit Power.
37508 + 4. Link Margin.
37509 +
37510 + Return : None.
37511 + ==========================================================================
37512 + */
37513 + static VOID InsertTpcReportIE(
37514 + IN PRTMP_ADAPTER pAd,
37515 + OUT PUCHAR pFrameBuf,
37516 + OUT PULONG pFrameLen,
37517 + IN UINT8 TxPwr,
37518 + IN UINT8 LinkMargin)
37519 +{
37520 + ULONG TempLen;
37521 + ULONG Len = sizeof(TPC_REPORT_INFO);
37522 + UINT8 ElementID = IE_TPC_REPORT;
37523 + TPC_REPORT_INFO TpcReportIE;
37524 +
37525 + TpcReportIE.TxPwr = TxPwr;
37526 + TpcReportIE.LinkMargin = LinkMargin;
37527 +
37528 + MakeOutgoingFrame(pFrameBuf, &TempLen,
37529 + 1, &ElementID,
37530 + 1, &Len,
37531 + Len, &TpcReportIE,
37532 + END_OF_ARGS);
37533 +
37534 + *pFrameLen = *pFrameLen + TempLen;
37535 +
37536 +
37537 + return;
37538 +}
37539 +
37540 +/*
37541 + ==========================================================================
37542 + Description:
37543 + Insert Channel Switch Announcement IE into frame.
37544 +
37545 + Parametrs:
37546 + 1. frame buffer pointer.
37547 + 2. frame length.
37548 + 3. channel switch announcement mode.
37549 + 4. new selected channel.
37550 + 5. channel switch announcement count.
37551 +
37552 + Return : None.
37553 + ==========================================================================
37554 + */
37555 +static VOID InsertChSwAnnIE(
37556 + IN PRTMP_ADAPTER pAd,
37557 + OUT PUCHAR pFrameBuf,
37558 + OUT PULONG pFrameLen,
37559 + IN UINT8 ChSwMode,
37560 + IN UINT8 NewChannel,
37561 + IN UINT8 ChSwCnt)
37562 +{
37563 + ULONG TempLen;
37564 + ULONG Len = sizeof(CH_SW_ANN_INFO);
37565 + UINT8 ElementID = IE_CHANNEL_SWITCH_ANNOUNCEMENT;
37566 + CH_SW_ANN_INFO ChSwAnnIE;
37567 +
37568 + ChSwAnnIE.ChSwMode = ChSwMode;
37569 + ChSwAnnIE.Channel = NewChannel;
37570 + ChSwAnnIE.ChSwCnt = ChSwCnt;
37571 +
37572 + MakeOutgoingFrame(pFrameBuf, &TempLen,
37573 + 1, &ElementID,
37574 + 1, &Len,
37575 + Len, &ChSwAnnIE,
37576 + END_OF_ARGS);
37577 +
37578 + *pFrameLen = *pFrameLen + TempLen;
37579 +
37580 +
37581 + return;
37582 +}
37583 +
37584 +/*
37585 + ==========================================================================
37586 + Description:
37587 + Insert Measure Request IE into frame.
37588 +
37589 + Parametrs:
37590 + 1. frame buffer pointer.
37591 + 2. frame length.
37592 + 3. Measure Token.
37593 + 4. Measure Request Mode.
37594 + 5. Measure Request Type.
37595 + 6. Measure Channel.
37596 + 7. Measure Start time.
37597 + 8. Measure Duration.
37598 +
37599 +
37600 + Return : None.
37601 + ==========================================================================
37602 + */
37603 +static VOID InsertMeasureReqIE(
37604 + IN PRTMP_ADAPTER pAd,
37605 + OUT PUCHAR pFrameBuf,
37606 + OUT PULONG pFrameLen,
37607 + IN PMEASURE_REQ_INFO pMeasureReqIE)
37608 +{
37609 + ULONG TempLen;
37610 + UINT8 Len = sizeof(MEASURE_REQ_INFO);
37611 + UINT8 ElementID = IE_MEASUREMENT_REQUEST;
37612 +
37613 + MakeOutgoingFrame(pFrameBuf, &TempLen,
37614 + 1, &ElementID,
37615 + 1, &Len,
37616 + Len, pMeasureReqIE,
37617 + END_OF_ARGS);
37618 +
37619 + *pFrameLen = *pFrameLen + TempLen;
37620 +
37621 + return;
37622 +}
37623 +
37624 +/*
37625 + ==========================================================================
37626 + Description:
37627 + Insert Measure Report IE into frame.
37628 +
37629 + Parametrs:
37630 + 1. frame buffer pointer.
37631 + 2. frame length.
37632 + 3. Measure Token.
37633 + 4. Measure Request Mode.
37634 + 5. Measure Request Type.
37635 + 6. Length of Report Infomation
37636 + 7. Pointer of Report Infomation Buffer.
37637 +
37638 + Return : None.
37639 + ==========================================================================
37640 + */
37641 +static VOID InsertMeasureReportIE(
37642 + IN PRTMP_ADAPTER pAd,
37643 + OUT PUCHAR pFrameBuf,
37644 + OUT PULONG pFrameLen,
37645 + IN PMEASURE_REPORT_INFO pMeasureReportIE,
37646 + IN UINT8 ReportLnfoLen,
37647 + IN PUINT8 pReportInfo)
37648 +{
37649 + ULONG TempLen;
37650 + ULONG Len;
37651 + UINT8 ElementID = IE_MEASUREMENT_REPORT;
37652 +
37653 + Len = sizeof(MEASURE_REPORT_INFO) + ReportLnfoLen;
37654 +
37655 + MakeOutgoingFrame(pFrameBuf, &TempLen,
37656 + 1, &ElementID,
37657 + 1, &Len,
37658 + Len, pMeasureReportIE,
37659 + END_OF_ARGS);
37660 +
37661 + *pFrameLen = *pFrameLen + TempLen;
37662 +
37663 + if ((ReportLnfoLen > 0) && (pReportInfo != NULL))
37664 + {
37665 + MakeOutgoingFrame(pFrameBuf + *pFrameLen, &TempLen,
37666 + ReportLnfoLen, pReportInfo,
37667 + END_OF_ARGS);
37668 +
37669 + *pFrameLen = *pFrameLen + TempLen;
37670 + }
37671 + return;
37672 +}
37673 +
37674 +/*
37675 + ==========================================================================
37676 + Description:
37677 + Prepare Measurement request action frame and enqueue it into
37678 + management queue waiting for transmition.
37679 +
37680 + Parametrs:
37681 + 1. the destination mac address of the frame.
37682 +
37683 + Return : None.
37684 + ==========================================================================
37685 + */
37686 +VOID EnqueueMeasurementReq(
37687 + IN PRTMP_ADAPTER pAd,
37688 + IN PUCHAR pDA,
37689 + IN UINT8 MeasureToken,
37690 + IN UINT8 MeasureReqMode,
37691 + IN UINT8 MeasureReqType,
37692 + IN UINT8 MeasureCh,
37693 + IN UINT16 MeasureDuration)
37694 +{
37695 + PUCHAR pOutBuffer = NULL;
37696 + NDIS_STATUS NStatus;
37697 + ULONG FrameLen;
37698 + HEADER_802_11 ActHdr;
37699 + MEASURE_REQ_INFO MeasureReqIE;
37700 + UINT8 RmReqDailogToken = RandomByte(pAd);
37701 + UINT64 MeasureStartTime = GetCurrentTimeStamp(pAd);
37702 +
37703 + // build action frame header.
37704 + MgtMacHeaderInit(pAd, &ActHdr, SUBTYPE_ACTION, 0, pDA,
37705 + pAd->CurrentAddress);
37706 +
37707 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
37708 + if(NStatus != NDIS_STATUS_SUCCESS)
37709 + {
37710 + DBGPRINT(RT_DEBUG_TRACE, ("%s() allocate memory failed \n", __FUNCTION__));
37711 + return;
37712 + }
37713 + NdisMoveMemory(pOutBuffer, (PCHAR)&ActHdr, sizeof(HEADER_802_11));
37714 + FrameLen = sizeof(HEADER_802_11);
37715 +
37716 + InsertActField(pAd, (pOutBuffer + FrameLen), &FrameLen, CATEGORY_SPECTRUM, SPEC_MRQ);
37717 +
37718 + // fill Dialog Token
37719 + InsertDialogToken(pAd, (pOutBuffer + FrameLen), &FrameLen, MeasureToken);
37720 +
37721 + // prepare Measurement IE.
37722 + NdisZeroMemory(&MeasureReqIE, sizeof(MEASURE_REQ_INFO));
37723 + MeasureReqIE.Token = RmReqDailogToken;
37724 + MeasureReqIE.ReqMode.word = MeasureReqMode;
37725 + MeasureReqIE.ReqType = MeasureReqType;
37726 + MeasureReqIE.MeasureReq.ChNum = MeasureCh;
37727 + MeasureReqIE.MeasureReq.MeasureStartTime = cpu2le64(MeasureStartTime);
37728 + MeasureReqIE.MeasureReq.MeasureDuration = cpu2le16(MeasureDuration);
37729 + InsertMeasureReqIE(pAd, (pOutBuffer + FrameLen), &FrameLen, &MeasureReqIE);
37730 +
37731 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
37732 + MlmeFreeMemory(pAd, pOutBuffer);
37733 +
37734 + return;
37735 +}
37736 +
37737 +/*
37738 + ==========================================================================
37739 + Description:
37740 + Prepare Measurement report action frame and enqueue it into
37741 + management queue waiting for transmition.
37742 +
37743 + Parametrs:
37744 + 1. the destination mac address of the frame.
37745 +
37746 + Return : None.
37747 + ==========================================================================
37748 + */
37749 +VOID EnqueueMeasurementRep(
37750 + IN PRTMP_ADAPTER pAd,
37751 + IN PUCHAR pDA,
37752 + IN UINT8 DialogToken,
37753 + IN UINT8 MeasureToken,
37754 + IN UINT8 MeasureReqMode,
37755 + IN UINT8 MeasureReqType,
37756 + IN UINT8 ReportInfoLen,
37757 + IN PUINT8 pReportInfo)
37758 +{
37759 + PUCHAR pOutBuffer = NULL;
37760 + NDIS_STATUS NStatus;
37761 + ULONG FrameLen;
37762 + HEADER_802_11 ActHdr;
37763 + MEASURE_REPORT_INFO MeasureRepIE;
37764 +
37765 + // build action frame header.
37766 + MgtMacHeaderInit(pAd, &ActHdr, SUBTYPE_ACTION, 0, pDA,
37767 + pAd->CurrentAddress);
37768 +
37769 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
37770 + if(NStatus != NDIS_STATUS_SUCCESS)
37771 + {
37772 + DBGPRINT(RT_DEBUG_TRACE, ("%s() allocate memory failed \n", __FUNCTION__));
37773 + return;
37774 + }
37775 + NdisMoveMemory(pOutBuffer, (PCHAR)&ActHdr, sizeof(HEADER_802_11));
37776 + FrameLen = sizeof(HEADER_802_11);
37777 +
37778 + InsertActField(pAd, (pOutBuffer + FrameLen), &FrameLen, CATEGORY_SPECTRUM, SPEC_MRP);
37779 +
37780 + // fill Dialog Token
37781 + InsertDialogToken(pAd, (pOutBuffer + FrameLen), &FrameLen, DialogToken);
37782 +
37783 + // prepare Measurement IE.
37784 + NdisZeroMemory(&MeasureRepIE, sizeof(MEASURE_REPORT_INFO));
37785 + MeasureRepIE.Token = MeasureToken;
37786 + MeasureRepIE.ReportMode.word = MeasureReqMode;
37787 + MeasureRepIE.ReportType = MeasureReqType;
37788 + InsertMeasureReportIE(pAd, (pOutBuffer + FrameLen), &FrameLen, &MeasureRepIE, ReportInfoLen, pReportInfo);
37789 +
37790 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
37791 + MlmeFreeMemory(pAd, pOutBuffer);
37792 +
37793 + return;
37794 +}
37795 +
37796 +/*
37797 + ==========================================================================
37798 + Description:
37799 + Prepare TPC Request action frame and enqueue it into
37800 + management queue waiting for transmition.
37801 +
37802 + Parametrs:
37803 + 1. the destination mac address of the frame.
37804 +
37805 + Return : None.
37806 + ==========================================================================
37807 + */
37808 +VOID EnqueueTPCReq(
37809 + IN PRTMP_ADAPTER pAd,
37810 + IN PUCHAR pDA,
37811 + IN UCHAR DialogToken)
37812 +{
37813 + PUCHAR pOutBuffer = NULL;
37814 + NDIS_STATUS NStatus;
37815 + ULONG FrameLen;
37816 +
37817 + HEADER_802_11 ActHdr;
37818 +
37819 + // build action frame header.
37820 + MgtMacHeaderInit(pAd, &ActHdr, SUBTYPE_ACTION, 0, pDA,
37821 + pAd->CurrentAddress);
37822 +
37823 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
37824 + if(NStatus != NDIS_STATUS_SUCCESS)
37825 + {
37826 + DBGPRINT(RT_DEBUG_TRACE, ("%s() allocate memory failed \n", __FUNCTION__));
37827 + return;
37828 + }
37829 + NdisMoveMemory(pOutBuffer, (PCHAR)&ActHdr, sizeof(HEADER_802_11));
37830 + FrameLen = sizeof(HEADER_802_11);
37831 +
37832 + InsertActField(pAd, (pOutBuffer + FrameLen), &FrameLen, CATEGORY_SPECTRUM, SPEC_TPCRQ);
37833 +
37834 + // fill Dialog Token
37835 + InsertDialogToken(pAd, (pOutBuffer + FrameLen), &FrameLen, DialogToken);
37836 +
37837 + // Insert TPC Request IE.
37838 + InsertTpcReqIE(pAd, (pOutBuffer + FrameLen), &FrameLen);
37839 +
37840 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
37841 + MlmeFreeMemory(pAd, pOutBuffer);
37842 +
37843 + return;
37844 +}
37845 +
37846 +/*
37847 + ==========================================================================
37848 + Description:
37849 + Prepare TPC Report action frame and enqueue it into
37850 + management queue waiting for transmition.
37851 +
37852 + Parametrs:
37853 + 1. the destination mac address of the frame.
37854 +
37855 + Return : None.
37856 + ==========================================================================
37857 + */
37858 +VOID EnqueueTPCRep(
37859 + IN PRTMP_ADAPTER pAd,
37860 + IN PUCHAR pDA,
37861 + IN UINT8 DialogToken,
37862 + IN UINT8 TxPwr,
37863 + IN UINT8 LinkMargin)
37864 +{
37865 + PUCHAR pOutBuffer = NULL;
37866 + NDIS_STATUS NStatus;
37867 + ULONG FrameLen;
37868 +
37869 + HEADER_802_11 ActHdr;
37870 +
37871 + // build action frame header.
37872 + MgtMacHeaderInit(pAd, &ActHdr, SUBTYPE_ACTION, 0, pDA,
37873 + pAd->CurrentAddress);
37874 +
37875 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
37876 + if(NStatus != NDIS_STATUS_SUCCESS)
37877 + {
37878 + DBGPRINT(RT_DEBUG_TRACE, ("%s() allocate memory failed \n", __FUNCTION__));
37879 + return;
37880 + }
37881 + NdisMoveMemory(pOutBuffer, (PCHAR)&ActHdr, sizeof(HEADER_802_11));
37882 + FrameLen = sizeof(HEADER_802_11);
37883 +
37884 + InsertActField(pAd, (pOutBuffer + FrameLen), &FrameLen, CATEGORY_SPECTRUM, SPEC_TPCRP);
37885 +
37886 + // fill Dialog Token
37887 + InsertDialogToken(pAd, (pOutBuffer + FrameLen), &FrameLen, DialogToken);
37888 +
37889 + // Insert TPC Request IE.
37890 + InsertTpcReportIE(pAd, (pOutBuffer + FrameLen), &FrameLen, TxPwr, LinkMargin);
37891 +
37892 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
37893 + MlmeFreeMemory(pAd, pOutBuffer);
37894 +
37895 + return;
37896 +}
37897 +
37898 +/*
37899 + ==========================================================================
37900 + Description:
37901 + Prepare Channel Switch Announcement action frame and enqueue it into
37902 + management queue waiting for transmition.
37903 +
37904 + Parametrs:
37905 + 1. the destination mac address of the frame.
37906 + 2. Channel switch announcement mode.
37907 + 2. a New selected channel.
37908 +
37909 + Return : None.
37910 + ==========================================================================
37911 + */
37912 +VOID EnqueueChSwAnn(
37913 + IN PRTMP_ADAPTER pAd,
37914 + IN PUCHAR pDA,
37915 + IN UINT8 ChSwMode,
37916 + IN UINT8 NewCh)
37917 +{
37918 + PUCHAR pOutBuffer = NULL;
37919 + NDIS_STATUS NStatus;
37920 + ULONG FrameLen;
37921 +
37922 + HEADER_802_11 ActHdr;
37923 +
37924 + // build action frame header.
37925 + MgtMacHeaderInit(pAd, &ActHdr, SUBTYPE_ACTION, 0, pDA,
37926 + pAd->CurrentAddress);
37927 +
37928 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
37929 + if(NStatus != NDIS_STATUS_SUCCESS)
37930 + {
37931 + DBGPRINT(RT_DEBUG_TRACE, ("%s() allocate memory failed \n", __FUNCTION__));
37932 + return;
37933 + }
37934 + NdisMoveMemory(pOutBuffer, (PCHAR)&ActHdr, sizeof(HEADER_802_11));
37935 + FrameLen = sizeof(HEADER_802_11);
37936 +
37937 + InsertActField(pAd, (pOutBuffer + FrameLen), &FrameLen, CATEGORY_SPECTRUM, SPEC_CHANNEL_SWITCH);
37938 +
37939 + InsertChSwAnnIE(pAd, (pOutBuffer + FrameLen), &FrameLen, ChSwMode, NewCh, 0);
37940 +
37941 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
37942 + MlmeFreeMemory(pAd, pOutBuffer);
37943 +
37944 + return;
37945 +}
37946 +
37947 +static BOOLEAN DfsRequirementCheck(
37948 + IN PRTMP_ADAPTER pAd,
37949 + IN UINT8 Channel)
37950 +{
37951 + BOOLEAN Result = FALSE;
37952 + INT i;
37953 +
37954 + do
37955 + {
37956 + // check DFS procedure is running.
37957 + // make sure DFS procedure won't start twice.
37958 + if (pAd->CommonCfg.RadarDetect.RDMode != RD_NORMAL_MODE)
37959 + {
37960 + Result = FALSE;
37961 + break;
37962 + }
37963 +
37964 + // check the new channel carried from Channel Switch Announcemnet is valid.
37965 + for (i=0; i<pAd->ChannelListNum; i++)
37966 + {
37967 + if ((Channel == pAd->ChannelList[i].Channel)
37968 + &&(pAd->ChannelList[i].RemainingTimeForUse == 0))
37969 + {
37970 + // found radar signal in the channel. the channel can't use at least for 30 minutes.
37971 + pAd->ChannelList[i].RemainingTimeForUse = 1800;//30 min = 1800 sec
37972 + Result = TRUE;
37973 + break;
37974 + }
37975 + }
37976 + } while(FALSE);
37977 +
37978 + return Result;
37979 +}
37980 +
37981 +VOID NotifyChSwAnnToPeerAPs(
37982 + IN PRTMP_ADAPTER pAd,
37983 + IN PUCHAR pRA,
37984 + IN PUCHAR pTA,
37985 + IN UINT8 ChSwMode,
37986 + IN UINT8 Channel)
37987 +{
37988 +#ifdef WDS_SUPPORT
37989 + if (!((pRA[0] & 0xff) == 0xff)) // is pRA a broadcase address.
37990 + {
37991 + INT i;
37992 + // info neighbor APs that Radar signal found throgh WDS link.
37993 + for (i = 0; i < MAX_WDS_ENTRY; i++)
37994 + {
37995 + if (ValidWdsEntry(pAd, i))
37996 + {
37997 + PUCHAR pDA = pAd->WdsTab.WdsEntry[i].PeerWdsAddr;
37998 +
37999 + // DA equal to SA. have no necessary orignal AP which found Radar signal.
38000 + if (MAC_ADDR_EQUAL(pTA, pDA))
38001 + continue;
38002 +
38003 + // send Channel Switch Action frame to info Neighbro APs.
38004 + EnqueueChSwAnn(pAd, pDA, ChSwMode, Channel);
38005 + }
38006 + }
38007 + }
38008 +#endif // WDS_SUPPORT //
38009 +}
38010 +
38011 +static VOID StartDFSProcedure(
38012 + IN PRTMP_ADAPTER pAd,
38013 + IN UCHAR Channel,
38014 + IN UINT8 ChSwMode)
38015 +{
38016 + // start DFS procedure
38017 + pAd->CommonCfg.Channel = Channel;
38018 +#ifdef DOT11_N_SUPPORT
38019 + N_ChannelCheck(pAd);
38020 +#endif // DOT11_N_SUPPORT //
38021 + pAd->CommonCfg.RadarDetect.RDMode = RD_SWITCHING_MODE;
38022 + pAd->CommonCfg.RadarDetect.CSCount = 0;
38023 +}
38024 +
38025 +/*
38026 + ==========================================================================
38027 + Description:
38028 + Channel Switch Announcement action frame sanity check.
38029 +
38030 + Parametrs:
38031 + 1. MLME message containing the received frame
38032 + 2. message length.
38033 + 3. Channel switch announcement infomation buffer.
38034 +
38035 +
38036 + Return : None.
38037 + ==========================================================================
38038 + */
38039 +
38040 +/*
38041 + Channel Switch Announcement IE.
38042 + +----+-----+-----------+------------+-----------+
38043 + | ID | Len |Ch Sw Mode | New Ch Num | Ch Sw Cnt |
38044 + +----+-----+-----------+------------+-----------+
38045 + 1 1 1 1 1
38046 +*/
38047 +static BOOLEAN PeerChSwAnnSanity(
38048 + IN PRTMP_ADAPTER pAd,
38049 + IN VOID *pMsg,
38050 + IN ULONG MsgLen,
38051 + OUT PCH_SW_ANN_INFO pChSwAnnInfo)
38052 +{
38053 + PFRAME_802_11 Fr = (PFRAME_802_11)pMsg;
38054 + PUCHAR pFramePtr = Fr->Octet;
38055 + BOOLEAN result = FALSE;
38056 + PEID_STRUCT eid_ptr;
38057 +
38058 + // skip 802.11 header.
38059 + MsgLen -= sizeof(HEADER_802_11);
38060 +
38061 + // skip category and action code.
38062 + pFramePtr += 2;
38063 + MsgLen -= 2;
38064 +
38065 + if (pChSwAnnInfo == NULL)
38066 + return result;
38067 +
38068 + eid_ptr = (PEID_STRUCT)pFramePtr;
38069 + while (((UCHAR*)eid_ptr + eid_ptr->Len + 1) < ((PUCHAR)pFramePtr + MsgLen))
38070 + {
38071 + switch(eid_ptr->Eid)
38072 + {
38073 + case IE_CHANNEL_SWITCH_ANNOUNCEMENT:
38074 + NdisMoveMemory(&pChSwAnnInfo->ChSwMode, eid_ptr->Octet, 1);
38075 + NdisMoveMemory(&pChSwAnnInfo->Channel, eid_ptr->Octet + 1, 1);
38076 + NdisMoveMemory(&pChSwAnnInfo->ChSwCnt, eid_ptr->Octet + 2, 1);
38077 +
38078 + result = TRUE;
38079 + break;
38080 +
38081 + default:
38082 + break;
38083 + }
38084 + eid_ptr = (PEID_STRUCT)((UCHAR*)eid_ptr + 2 + eid_ptr->Len);
38085 + }
38086 +
38087 + return result;
38088 +}
38089 +
38090 +/*
38091 + ==========================================================================
38092 + Description:
38093 + Measurement request action frame sanity check.
38094 +
38095 + Parametrs:
38096 + 1. MLME message containing the received frame
38097 + 2. message length.
38098 + 3. Measurement request infomation buffer.
38099 +
38100 + Return : None.
38101 + ==========================================================================
38102 + */
38103 +static BOOLEAN PeerMeasureReqSanity(
38104 + IN PRTMP_ADAPTER pAd,
38105 + IN VOID *pMsg,
38106 + IN ULONG MsgLen,
38107 + OUT PUINT8 pDialogToken,
38108 + OUT PMEASURE_REQ_INFO pMeasureReqInfo)
38109 +{
38110 + PFRAME_802_11 Fr = (PFRAME_802_11)pMsg;
38111 + PUCHAR pFramePtr = Fr->Octet;
38112 + BOOLEAN result = FALSE;
38113 + PEID_STRUCT eid_ptr;
38114 + PUCHAR ptr;
38115 + UINT64 MeasureStartTime;
38116 + UINT16 MeasureDuration;
38117 +
38118 + // skip 802.11 header.
38119 + MsgLen -= sizeof(HEADER_802_11);
38120 +
38121 + // skip category and action code.
38122 + pFramePtr += 2;
38123 + MsgLen -= 2;
38124 +
38125 + if (pMeasureReqInfo == NULL)
38126 + return result;
38127 +
38128 + NdisMoveMemory(pDialogToken, pFramePtr, 1);
38129 + pFramePtr += 1;
38130 + MsgLen -= 1;
38131 +
38132 + eid_ptr = (PEID_STRUCT)pFramePtr;
38133 + while (((UCHAR*)eid_ptr + eid_ptr->Len + 1) < ((PUCHAR)pFramePtr + MsgLen))
38134 + {
38135 + switch(eid_ptr->Eid)
38136 + {
38137 + case IE_MEASUREMENT_REQUEST:
38138 + NdisMoveMemory(&pMeasureReqInfo->Token, eid_ptr->Octet, 1);
38139 + NdisMoveMemory(&pMeasureReqInfo->ReqMode.word, eid_ptr->Octet + 1, 1);
38140 + NdisMoveMemory(&pMeasureReqInfo->ReqType, eid_ptr->Octet + 2, 1);
38141 + ptr = eid_ptr->Octet + 3;
38142 + NdisMoveMemory(&pMeasureReqInfo->MeasureReq.ChNum, ptr, 1);
38143 + NdisMoveMemory(&MeasureStartTime, ptr + 1, 8);
38144 + pMeasureReqInfo->MeasureReq.MeasureStartTime = SWAP64(MeasureStartTime);
38145 + NdisMoveMemory(&MeasureDuration, ptr + 9, 2);
38146 + pMeasureReqInfo->MeasureReq.MeasureDuration = SWAP16(MeasureDuration);
38147 +
38148 + result = TRUE;
38149 + break;
38150 +
38151 + default:
38152 + break;
38153 + }
38154 + eid_ptr = (PEID_STRUCT)((UCHAR*)eid_ptr + 2 + eid_ptr->Len);
38155 + }
38156 +
38157 + return result;
38158 +}
38159 +
38160 +/*
38161 + ==========================================================================
38162 + Description:
38163 + Measurement report action frame sanity check.
38164 +
38165 + Parametrs:
38166 + 1. MLME message containing the received frame
38167 + 2. message length.
38168 + 3. Measurement report infomation buffer.
38169 + 4. basic report infomation buffer.
38170 +
38171 + Return : None.
38172 + ==========================================================================
38173 + */
38174 +
38175 +/*
38176 + Measurement Report IE.
38177 + +----+-----+-------+-------------+--------------+----------------+
38178 + | ID | Len | Token | Report Mode | Measure Type | Measure Report |
38179 + +----+-----+-------+-------------+--------------+----------------+
38180 + 1 1 1 1 1 variable
38181 +
38182 + Basic Report.
38183 + +--------+------------+----------+-----+
38184 + | Ch Num | Start Time | Duration | Map |
38185 + +--------+------------+----------+-----+
38186 + 1 8 2 1
38187 +
38188 + Map Field Bit Format.
38189 + +-----+---------------+---------------------+-------+------------+----------+
38190 + | Bss | OFDM Preamble | Unidentified signal | Radar | Unmeasured | Reserved |
38191 + +-----+---------------+---------------------+-------+------------+----------+
38192 + 0 1 2 3 4 5-7
38193 +*/
38194 +static BOOLEAN PeerMeasureReportSanity(
38195 + IN PRTMP_ADAPTER pAd,
38196 + IN VOID *pMsg,
38197 + IN ULONG MsgLen,
38198 + OUT PUINT8 pDialogToken,
38199 + OUT PMEASURE_REPORT_INFO pMeasureReportInfo,
38200 + OUT PUINT8 pReportBuf)
38201 +{
38202 + PFRAME_802_11 Fr = (PFRAME_802_11)pMsg;
38203 + PUCHAR pFramePtr = Fr->Octet;
38204 + BOOLEAN result = FALSE;
38205 + PEID_STRUCT eid_ptr;
38206 + PUCHAR ptr;
38207 +
38208 + // skip 802.11 header.
38209 + MsgLen -= sizeof(HEADER_802_11);
38210 +
38211 + // skip category and action code.
38212 + pFramePtr += 2;
38213 + MsgLen -= 2;
38214 +
38215 + if (pMeasureReportInfo == NULL)
38216 + return result;
38217 +
38218 + NdisMoveMemory(pDialogToken, pFramePtr, 1);
38219 + pFramePtr += 1;
38220 + MsgLen -= 1;
38221 +
38222 + eid_ptr = (PEID_STRUCT)pFramePtr;
38223 + while (((UCHAR*)eid_ptr + eid_ptr->Len + 1) < ((PUCHAR)pFramePtr + MsgLen))
38224 + {
38225 + switch(eid_ptr->Eid)
38226 + {
38227 + case IE_MEASUREMENT_REPORT:
38228 + NdisMoveMemory(&pMeasureReportInfo->Token, eid_ptr->Octet, 1);
38229 + NdisMoveMemory(&pMeasureReportInfo->ReportMode, eid_ptr->Octet + 1, 1);
38230 + NdisMoveMemory(&pMeasureReportInfo->ReportType, eid_ptr->Octet + 2, 1);
38231 + if (pMeasureReportInfo->ReportType == RM_BASIC)
38232 + {
38233 + PMEASURE_BASIC_REPORT pReport = (PMEASURE_BASIC_REPORT)pReportBuf;
38234 + ptr = eid_ptr->Octet + 3;
38235 + NdisMoveMemory(&pReport->ChNum, ptr, 1);
38236 + NdisMoveMemory(&pReport->MeasureStartTime, ptr + 1, 8);
38237 + NdisMoveMemory(&pReport->MeasureDuration, ptr + 9, 2);
38238 + NdisMoveMemory(&pReport->Map, ptr + 11, 1);
38239 +
38240 + }
38241 + else if (pMeasureReportInfo->ReportType == RM_CCA)
38242 + {
38243 + PMEASURE_CCA_REPORT pReport = (PMEASURE_CCA_REPORT)pReportBuf;
38244 + ptr = eid_ptr->Octet + 3;
38245 + NdisMoveMemory(&pReport->ChNum, ptr, 1);
38246 + NdisMoveMemory(&pReport->MeasureStartTime, ptr + 1, 8);
38247 + NdisMoveMemory(&pReport->MeasureDuration, ptr + 9, 2);
38248 + NdisMoveMemory(&pReport->CCA_Busy_Fraction, ptr + 11, 1);
38249 +
38250 + }
38251 + else if (pMeasureReportInfo->ReportType == RM_RPI_HISTOGRAM)
38252 + {
38253 + PMEASURE_RPI_REPORT pReport = (PMEASURE_RPI_REPORT)pReportBuf;
38254 + ptr = eid_ptr->Octet + 3;
38255 + NdisMoveMemory(&pReport->ChNum, ptr, 1);
38256 + NdisMoveMemory(&pReport->MeasureStartTime, ptr + 1, 8);
38257 + NdisMoveMemory(&pReport->MeasureDuration, ptr + 9, 2);
38258 + NdisMoveMemory(&pReport->RPI_Density, ptr + 11, 8);
38259 + }
38260 + result = TRUE;
38261 + break;
38262 +
38263 + default:
38264 + break;
38265 + }
38266 + eid_ptr = (PEID_STRUCT)((UCHAR*)eid_ptr + 2 + eid_ptr->Len);
38267 + }
38268 +
38269 + return result;
38270 +}
38271 +
38272 +/*
38273 + ==========================================================================
38274 + Description:
38275 + TPC Request action frame sanity check.
38276 +
38277 + Parametrs:
38278 + 1. MLME message containing the received frame
38279 + 2. message length.
38280 + 3. Dialog Token.
38281 +
38282 + Return : None.
38283 + ==========================================================================
38284 + */
38285 +static BOOLEAN PeerTpcReqSanity(
38286 + IN PRTMP_ADAPTER pAd,
38287 + IN VOID *pMsg,
38288 + IN ULONG MsgLen,
38289 + OUT PUINT8 pDialogToken)
38290 +{
38291 + PFRAME_802_11 Fr = (PFRAME_802_11)pMsg;
38292 + PUCHAR pFramePtr = Fr->Octet;
38293 + BOOLEAN result = FALSE;
38294 + PEID_STRUCT eid_ptr;
38295 +
38296 + MsgLen -= sizeof(HEADER_802_11);
38297 +
38298 + // skip category and action code.
38299 + pFramePtr += 2;
38300 + MsgLen -= 2;
38301 +
38302 + if (pDialogToken == NULL)
38303 + return result;
38304 +
38305 + NdisMoveMemory(pDialogToken, pFramePtr, 1);
38306 + pFramePtr += 1;
38307 + MsgLen -= 1;
38308 +
38309 + eid_ptr = (PEID_STRUCT)pFramePtr;
38310 + while (((UCHAR*)eid_ptr + eid_ptr->Len + 1) < ((PUCHAR)pFramePtr + MsgLen))
38311 + {
38312 + switch(eid_ptr->Eid)
38313 + {
38314 + case IE_TPC_REQUEST:
38315 + result = TRUE;
38316 + break;
38317 +
38318 + default:
38319 + break;
38320 + }
38321 + eid_ptr = (PEID_STRUCT)((UCHAR*)eid_ptr + 2 + eid_ptr->Len);
38322 + }
38323 +
38324 + return result;
38325 +}
38326 +
38327 +/*
38328 + ==========================================================================
38329 + Description:
38330 + TPC Report action frame sanity check.
38331 +
38332 + Parametrs:
38333 + 1. MLME message containing the received frame
38334 + 2. message length.
38335 + 3. Dialog Token.
38336 + 4. TPC Report IE.
38337 +
38338 + Return : None.
38339 + ==========================================================================
38340 + */
38341 +static BOOLEAN PeerTpcRepSanity(
38342 + IN PRTMP_ADAPTER pAd,
38343 + IN VOID *pMsg,
38344 + IN ULONG MsgLen,
38345 + OUT PUINT8 pDialogToken,
38346 + OUT PTPC_REPORT_INFO pTpcRepInfo)
38347 +{
38348 + PFRAME_802_11 Fr = (PFRAME_802_11)pMsg;
38349 + PUCHAR pFramePtr = Fr->Octet;
38350 + BOOLEAN result = FALSE;
38351 + PEID_STRUCT eid_ptr;
38352 +
38353 + MsgLen -= sizeof(HEADER_802_11);
38354 +
38355 + // skip category and action code.
38356 + pFramePtr += 2;
38357 + MsgLen -= 2;
38358 +
38359 + if (pDialogToken == NULL)
38360 + return result;
38361 +
38362 + NdisMoveMemory(pDialogToken, pFramePtr, 1);
38363 + pFramePtr += 1;
38364 + MsgLen -= 1;
38365 +
38366 + eid_ptr = (PEID_STRUCT)pFramePtr;
38367 + while (((UCHAR*)eid_ptr + eid_ptr->Len + 1) < ((PUCHAR)pFramePtr + MsgLen))
38368 + {
38369 + switch(eid_ptr->Eid)
38370 + {
38371 + case IE_TPC_REPORT:
38372 + NdisMoveMemory(&pTpcRepInfo->TxPwr, eid_ptr->Octet, 1);
38373 + NdisMoveMemory(&pTpcRepInfo->LinkMargin, eid_ptr->Octet + 1, 1);
38374 + result = TRUE;
38375 + break;
38376 +
38377 + default:
38378 + break;
38379 + }
38380 + eid_ptr = (PEID_STRUCT)((UCHAR*)eid_ptr + 2 + eid_ptr->Len);
38381 + }
38382 +
38383 + return result;
38384 +}
38385 +
38386 +/*
38387 + ==========================================================================
38388 + Description:
38389 + Channel Switch Announcement action frame handler.
38390 +
38391 + Parametrs:
38392 + Elme - MLME message containing the received frame
38393 +
38394 + Return : None.
38395 + ==========================================================================
38396 + */
38397 +static VOID PeerChSwAnnAction(
38398 + IN PRTMP_ADAPTER pAd,
38399 + IN MLME_QUEUE_ELEM *Elem)
38400 +{
38401 + CH_SW_ANN_INFO ChSwAnnInfo;
38402 + PFRAME_802_11 pFr = (PFRAME_802_11)Elem->Msg;
38403 +#ifdef CONFIG_STA_SUPPORT
38404 + UCHAR index = 0, Channel = 0, NewChannel = 0;
38405 + ULONG Bssidx = 0;
38406 +#endif // CONFIG_STA_SUPPORT //
38407 +
38408 + NdisZeroMemory(&ChSwAnnInfo, sizeof(CH_SW_ANN_INFO));
38409 + if (! PeerChSwAnnSanity(pAd, Elem->Msg, Elem->MsgLen, &ChSwAnnInfo))
38410 + {
38411 + DBGPRINT(RT_DEBUG_TRACE, ("Invalid Channel Switch Action Frame.\n"));
38412 + return;
38413 + }
38414 +
38415 +
38416 +#ifdef CONFIG_STA_SUPPORT
38417 + if (pAd->OpMode == OPMODE_STA)
38418 + {
38419 + Bssidx = BssTableSearch(&pAd->ScanTab, pFr->Hdr.Addr3, pAd->CommonCfg.Channel);
38420 + if (Bssidx == BSS_NOT_FOUND)
38421 + {
38422 + DBGPRINT(RT_DEBUG_TRACE, ("PeerChSwAnnAction - Bssidx is not found\n"));
38423 + return;
38424 + }
38425 +
38426 + DBGPRINT(RT_DEBUG_TRACE, ("\n****Bssidx is %d, Channel = %d\n", index, pAd->ScanTab.BssEntry[Bssidx].Channel));
38427 + hex_dump("SSID",pAd->ScanTab.BssEntry[Bssidx].Bssid ,6);
38428 +
38429 + Channel = pAd->CommonCfg.Channel;
38430 + NewChannel = ChSwAnnInfo.Channel;
38431 +
38432 + if ((pAd->CommonCfg.bIEEE80211H == 1) && (NewChannel != 0) && (Channel != NewChannel))
38433 + {
38434 + // Switching to channel 1 can prevent from rescanning the current channel immediately (by auto reconnection).
38435 + // In addition, clear the MLME queue and the scan table to discard the RX packets and previous scanning results.
38436 + AsicSwitchChannel(pAd, 1, FALSE);
38437 + AsicLockChannel(pAd, 1);
38438 + LinkDown(pAd, FALSE);
38439 + MlmeQueueInit(&pAd->Mlme.Queue);
38440 + BssTableInit(&pAd->ScanTab);
38441 + RTMPusecDelay(1000000); // use delay to prevent STA do reassoc
38442 +
38443 + // channel sanity check
38444 + for (index = 0 ; index < pAd->ChannelListNum; index++)
38445 + {
38446 + if (pAd->ChannelList[index].Channel == NewChannel)
38447 + {
38448 + pAd->ScanTab.BssEntry[Bssidx].Channel = NewChannel;
38449 + pAd->CommonCfg.Channel = NewChannel;
38450 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
38451 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
38452 + DBGPRINT(RT_DEBUG_TRACE, ("&&&&&&&&&&&&&&&&PeerChSwAnnAction - STA receive channel switch announcement IE (New Channel =%d)\n", NewChannel));
38453 + break;
38454 + }
38455 + }
38456 +
38457 + if (index >= pAd->ChannelListNum)
38458 + {
38459 + DBGPRINT_ERR(("&&&&&&&&&&&&&&&&&&&&&&&&&&PeerChSwAnnAction(can not find New Channel=%d in ChannelList[%d]\n", pAd->CommonCfg.Channel, pAd->ChannelListNum));
38460 + }
38461 + }
38462 + }
38463 +#endif // CONFIG_STA_SUPPORT //
38464 +
38465 + return;
38466 +}
38467 +
38468 +
38469 +/*
38470 + ==========================================================================
38471 + Description:
38472 + Measurement Request action frame handler.
38473 +
38474 + Parametrs:
38475 + Elme - MLME message containing the received frame
38476 +
38477 + Return : None.
38478 + ==========================================================================
38479 + */
38480 +static VOID PeerMeasureReqAction(
38481 + IN PRTMP_ADAPTER pAd,
38482 + IN MLME_QUEUE_ELEM *Elem)
38483 +{
38484 + PFRAME_802_11 pFr = (PFRAME_802_11)Elem->Msg;
38485 + UINT8 DialogToken;
38486 + MEASURE_REQ_INFO MeasureReqInfo;
38487 + MEASURE_REPORT_MODE ReportMode;
38488 +
38489 + if(PeerMeasureReqSanity(pAd, Elem->Msg, Elem->MsgLen, &DialogToken, &MeasureReqInfo))
38490 + {
38491 + ReportMode.word = 0;
38492 + ReportMode.field.Incapable = 1;
38493 + EnqueueMeasurementRep(pAd, pFr->Hdr.Addr2, DialogToken, MeasureReqInfo.Token, ReportMode.word, MeasureReqInfo.ReqType, 0, NULL);
38494 + }
38495 +
38496 + return;
38497 +}
38498 +
38499 +/*
38500 + ==========================================================================
38501 + Description:
38502 + Measurement Report action frame handler.
38503 +
38504 + Parametrs:
38505 + Elme - MLME message containing the received frame
38506 +
38507 + Return : None.
38508 + ==========================================================================
38509 + */
38510 +static VOID PeerMeasureReportAction(
38511 + IN PRTMP_ADAPTER pAd,
38512 + IN MLME_QUEUE_ELEM *Elem)
38513 +{
38514 + MEASURE_REPORT_INFO MeasureReportInfo;
38515 + PFRAME_802_11 pFr = (PFRAME_802_11)Elem->Msg;
38516 + UINT8 DialogToken;
38517 + PUINT8 pMeasureReportInfo;
38518 +
38519 +// if (pAd->CommonCfg.bIEEE80211H != TRUE)
38520 +// return;
38521 +
38522 + if ((pMeasureReportInfo = kmalloc(sizeof(MEASURE_RPI_REPORT), GFP_ATOMIC)) == NULL)
38523 + {
38524 + DBGPRINT(RT_DEBUG_ERROR, ("%s unable to alloc memory for measure report buffer (size=%d).\n", __FUNCTION__, sizeof(MEASURE_RPI_REPORT)));
38525 + return;
38526 + }
38527 +
38528 + NdisZeroMemory(&MeasureReportInfo, sizeof(MEASURE_REPORT_INFO));
38529 + NdisZeroMemory(pMeasureReportInfo, sizeof(MEASURE_RPI_REPORT));
38530 + if (PeerMeasureReportSanity(pAd, Elem->Msg, Elem->MsgLen, &DialogToken, &MeasureReportInfo, pMeasureReportInfo))
38531 + {
38532 + do {
38533 + PMEASURE_REQ_ENTRY pEntry = NULL;
38534 +
38535 + // Not a autonomous measure report.
38536 + // check the dialog token field. drop it if the dialog token doesn't match.
38537 + if ((DialogToken != 0)
38538 + && ((pEntry = MeasureReqLookUp(pAd, DialogToken)) == NULL))
38539 + break;
38540 +
38541 + if (pEntry != NULL)
38542 + MeasureReqDelete(pAd, pEntry->DialogToken);
38543 +
38544 + if (MeasureReportInfo.ReportType == RM_BASIC)
38545 + {
38546 + PMEASURE_BASIC_REPORT pBasicReport = (PMEASURE_BASIC_REPORT)pMeasureReportInfo;
38547 + if ((pBasicReport->Map.field.Radar)
38548 + && (DfsRequirementCheck(pAd, pBasicReport->ChNum) == TRUE))
38549 + {
38550 + NotifyChSwAnnToPeerAPs(pAd, pFr->Hdr.Addr1, pFr->Hdr.Addr2, 1, pBasicReport->ChNum);
38551 + StartDFSProcedure(pAd, pBasicReport->ChNum, 1);
38552 + }
38553 + }
38554 + } while (FALSE);
38555 + }
38556 + else
38557 + DBGPRINT(RT_DEBUG_TRACE, ("Invalid Measurement Report Frame.\n"));
38558 +
38559 + kfree(pMeasureReportInfo);
38560 +
38561 + return;
38562 +}
38563 +
38564 +/*
38565 + ==========================================================================
38566 + Description:
38567 + TPC Request action frame handler.
38568 +
38569 + Parametrs:
38570 + Elme - MLME message containing the received frame
38571 +
38572 + Return : None.
38573 + ==========================================================================
38574 + */
38575 +static VOID PeerTpcReqAction(
38576 + IN PRTMP_ADAPTER pAd,
38577 + IN MLME_QUEUE_ELEM *Elem)
38578 +{
38579 + PFRAME_802_11 pFr = (PFRAME_802_11)Elem->Msg;
38580 + PUCHAR pFramePtr = pFr->Octet;
38581 + UINT8 DialogToken;
38582 + UINT8 TxPwr = GetCurTxPwr(pAd, Elem->Wcid);
38583 + UINT8 LinkMargin = 0;
38584 + CHAR RealRssi;
38585 +
38586 + // link margin: Ratio of the received signal power to the minimum desired by the station (STA). The
38587 + // STA may incorporate rate information and channel conditions, including interference, into its computation
38588 + // of link margin.
38589 +
38590 + RealRssi = RTMPMaxRssi(pAd, ConvertToRssi(pAd, Elem->Rssi0, RSSI_0),
38591 + ConvertToRssi(pAd, Elem->Rssi1, RSSI_1),
38592 + ConvertToRssi(pAd, Elem->Rssi2, RSSI_2));
38593 +
38594 + // skip Category and action code.
38595 + pFramePtr += 2;
38596 +
38597 + // Dialog token.
38598 + NdisMoveMemory(&DialogToken, pFramePtr, 1);
38599 +
38600 + LinkMargin = (RealRssi / MIN_RCV_PWR);
38601 + if (PeerTpcReqSanity(pAd, Elem->Msg, Elem->MsgLen, &DialogToken))
38602 + EnqueueTPCRep(pAd, pFr->Hdr.Addr2, DialogToken, TxPwr, LinkMargin);
38603 +
38604 + return;
38605 +}
38606 +
38607 +/*
38608 + ==========================================================================
38609 + Description:
38610 + TPC Report action frame handler.
38611 +
38612 + Parametrs:
38613 + Elme - MLME message containing the received frame
38614 +
38615 + Return : None.
38616 + ==========================================================================
38617 + */
38618 +static VOID PeerTpcRepAction(
38619 + IN PRTMP_ADAPTER pAd,
38620 + IN MLME_QUEUE_ELEM *Elem)
38621 +{
38622 + UINT8 DialogToken;
38623 + TPC_REPORT_INFO TpcRepInfo;
38624 + PTPC_REQ_ENTRY pEntry = NULL;
38625 +
38626 + NdisZeroMemory(&TpcRepInfo, sizeof(TPC_REPORT_INFO));
38627 + if (PeerTpcRepSanity(pAd, Elem->Msg, Elem->MsgLen, &DialogToken, &TpcRepInfo))
38628 + {
38629 + if ((pEntry = TpcReqLookUp(pAd, DialogToken)) != NULL)
38630 + {
38631 + TpcReqDelete(pAd, pEntry->DialogToken);
38632 + DBGPRINT(RT_DEBUG_TRACE, ("%s: DialogToken=%x, TxPwr=%d, LinkMargin=%d\n",
38633 + __FUNCTION__, DialogToken, TpcRepInfo.TxPwr, TpcRepInfo.LinkMargin));
38634 + }
38635 + }
38636 +
38637 + return;
38638 +}
38639 +
38640 +/*
38641 + ==========================================================================
38642 + Description:
38643 + Spectrun action frames Handler such as channel switch annoucement,
38644 + measurement report, measurement request actions frames.
38645 +
38646 + Parametrs:
38647 + Elme - MLME message containing the received frame
38648 +
38649 + Return : None.
38650 + ==========================================================================
38651 + */
38652 +VOID PeerSpectrumAction(
38653 + IN PRTMP_ADAPTER pAd,
38654 + IN MLME_QUEUE_ELEM *Elem)
38655 +{
38656 +
38657 + UCHAR Action = Elem->Msg[LENGTH_802_11+1];
38658 +
38659 + if (pAd->CommonCfg.bIEEE80211H != TRUE)
38660 + return;
38661 +
38662 + switch(Action)
38663 + {
38664 + case SPEC_MRQ:
38665 + // current rt2860 unable do such measure specified in Measurement Request.
38666 + // reject all measurement request.
38667 + PeerMeasureReqAction(pAd, Elem);
38668 + break;
38669 +
38670 + case SPEC_MRP:
38671 + PeerMeasureReportAction(pAd, Elem);
38672 + break;
38673 +
38674 + case SPEC_TPCRQ:
38675 + PeerTpcReqAction(pAd, Elem);
38676 + break;
38677 +
38678 + case SPEC_TPCRP:
38679 + PeerTpcRepAction(pAd, Elem);
38680 + break;
38681 +
38682 + case SPEC_CHANNEL_SWITCH:
38683 +{
38684 +#ifdef DOT11N_DRAFT3
38685 + SEC_CHA_OFFSET_IE Secondary;
38686 + CHA_SWITCH_ANNOUNCE_IE ChannelSwitch;
38687 +
38688 + // 802.11h only has Channel Switch Announcement IE.
38689 + RTMPMoveMemory(&ChannelSwitch, &Elem->Msg[LENGTH_802_11+4], sizeof (CHA_SWITCH_ANNOUNCE_IE));
38690 +
38691 + // 802.11n D3.03 adds secondary channel offset element in the end.
38692 + if (Elem->MsgLen == (LENGTH_802_11 + 2 + sizeof (CHA_SWITCH_ANNOUNCE_IE) + sizeof (SEC_CHA_OFFSET_IE)))
38693 + {
38694 + RTMPMoveMemory(&Secondary, &Elem->Msg[LENGTH_802_11+9], sizeof (SEC_CHA_OFFSET_IE));
38695 + }
38696 + else
38697 + {
38698 + Secondary.SecondaryChannelOffset = 0;
38699 + }
38700 +
38701 + if ((Elem->Msg[LENGTH_802_11+2] == IE_CHANNEL_SWITCH_ANNOUNCEMENT) && (Elem->Msg[LENGTH_802_11+3] == 3))
38702 + {
38703 + ChannelSwitchAction(pAd, Elem->Wcid, ChannelSwitch.NewChannel, Secondary.SecondaryChannelOffset);
38704 + }
38705 +#endif // DOT11N_DRAFT3 //
38706 +}
38707 + PeerChSwAnnAction(pAd, Elem);
38708 + break;
38709 + }
38710 +
38711 + return;
38712 +}
38713 +
38714 +/*
38715 + ==========================================================================
38716 + Description:
38717 +
38718 + Parametrs:
38719 +
38720 + Return : None.
38721 + ==========================================================================
38722 + */
38723 +INT Set_MeasureReq_Proc(
38724 + IN PRTMP_ADAPTER pAd,
38725 + IN PUCHAR arg)
38726 +{
38727 + UINT Aid = 1;
38728 + UINT ArgIdx;
38729 + PUCHAR thisChar;
38730 +
38731 + MEASURE_REQ_MODE MeasureReqMode;
38732 + UINT8 MeasureReqToken = RandomByte(pAd);
38733 + UINT8 MeasureReqType = RM_BASIC;
38734 + UINT8 MeasureCh = 1;
38735 +
38736 + ArgIdx = 1;
38737 + while ((thisChar = strsep((char **)&arg, "-")) != NULL)
38738 + {
38739 + switch(ArgIdx)
38740 + {
38741 + case 1: // Aid.
38742 + Aid = simple_strtol(thisChar, 0, 16);
38743 + break;
38744 +
38745 + case 2: // Measurement Request Type.
38746 + MeasureReqType = simple_strtol(thisChar, 0, 16);
38747 + if (MeasureReqType > 3)
38748 + {
38749 + DBGPRINT(RT_DEBUG_ERROR, ("%s: unknow MeasureReqType(%d)\n", __FUNCTION__, MeasureReqType));
38750 + return TRUE;
38751 + }
38752 + break;
38753 +
38754 + case 3: // Measurement channel.
38755 + MeasureCh = simple_strtol(thisChar, 0, 16);
38756 + break;
38757 + }
38758 + ArgIdx++;
38759 + }
38760 +
38761 + DBGPRINT(RT_DEBUG_TRACE, ("%s::Aid = %d, MeasureReqType=%d MeasureCh=%d\n", __FUNCTION__, Aid, MeasureReqType, MeasureCh));
38762 + if (!VALID_WCID(Aid))
38763 + {
38764 + DBGPRINT(RT_DEBUG_ERROR, ("%s: unknow sta of Aid(%d)\n", __FUNCTION__, Aid));
38765 + return TRUE;
38766 + }
38767 +
38768 + MeasureReqMode.word = 0;
38769 + MeasureReqMode.field.Enable = 1;
38770 +
38771 + MeasureReqInsert(pAd, MeasureReqToken);
38772 +
38773 + EnqueueMeasurementReq(pAd, pAd->MacTab.Content[Aid].Addr,
38774 + MeasureReqToken, MeasureReqMode.word, MeasureReqType, MeasureCh, 2000);
38775 +
38776 + return TRUE;
38777 +}
38778 +
38779 +INT Set_TpcReq_Proc(
38780 + IN PRTMP_ADAPTER pAd,
38781 + IN PUCHAR arg)
38782 +{
38783 + UINT Aid;
38784 +
38785 + UINT8 TpcReqToken = RandomByte(pAd);
38786 +
38787 + Aid = simple_strtol(arg, 0, 16);
38788 +
38789 + DBGPRINT(RT_DEBUG_TRACE, ("%s::Aid = %d\n", __FUNCTION__, Aid));
38790 + if (!VALID_WCID(Aid))
38791 + {
38792 + DBGPRINT(RT_DEBUG_ERROR, ("%s: unknow sta of Aid(%d)\n", __FUNCTION__, Aid));
38793 + return TRUE;
38794 + }
38795 +
38796 + TpcReqInsert(pAd, TpcReqToken);
38797 +
38798 + EnqueueTPCReq(pAd, pAd->MacTab.Content[Aid].Addr, TpcReqToken);
38799 +
38800 + return TRUE;
38801 +}
38802 +
38803 --- /dev/null
38804 +++ b/drivers/staging/rt2860/config.mk
38805 @@ -0,0 +1,245 @@
38806 +# Support ATE function
38807 +HAS_ATE=n
38808 +
38809 +# Support 28xx QA ATE function
38810 +HAS_28xx_QA=n
38811 +
38812 +# Support Wpa_Supplicant
38813 +HAS_WPA_SUPPLICANT=n
38814 +
38815 +# Support Native WpaSupplicant for Network Maganger
38816 +HAS_NATIVE_WPA_SUPPLICANT_SUPPORT=n
38817 +
38818 +#Support Net interface block while Tx-Sw queue full
38819 +HAS_BLOCK_NET_IF=n
38820 +
38821 +#Support DFS function
38822 +HAS_DFS_SUPPORT=n
38823 +
38824 +#Support Carrier-Sense function
38825 +HAS_CS_SUPPORT=n
38826 +
38827 +#ifdef MULTI_CARD
38828 +# Support for Multiple Cards
38829 +HAS_MC_SUPPORT=n
38830 +#endif // MULTI_CARD //
38831 +
38832 +#Support for IEEE802.11e DLS
38833 +HAS_QOS_DLS_SUPPORT=n
38834 +
38835 +#Support for EXT_CHANNEL
38836 +HAS_EXT_BUILD_CHANNEL_LIST=n
38837 +
38838 +#Support for Net-SNMP
38839 +HAS_SNMP_SUPPORT=n
38840 +
38841 +#Support features of Single SKU.
38842 +HAS_SINGLE_SKU_SUPPORT=n
38843 +
38844 +#Support features of 802.11n
38845 +HAS_DOT11_N_SUPPORT=y
38846 +
38847 +
38848 +#################################################
38849 +
38850 +CC := $(CROSS_COMPILE)gcc
38851 +LD := $(CROSS_COMPILE)ld
38852 +
38853 +WFLAGS := -DAGGREGATION_SUPPORT -DPIGGYBACK_SUPPORT -DWMM_SUPPORT -DLINUX -Wall -Wstrict-prototypes -Wno-trigraphs
38854 +
38855 +
38856 +#################################################
38857 +
38858 +#ifdef CONFIG_STA_SUPPORT
38859 +# config for STA mode
38860 +
38861 +ifeq ($(RT28xx_MODE),STA)
38862 +WFLAGS += -DCONFIG_STA_SUPPORT -DDBG
38863 +
38864 +ifeq ($(HAS_WPA_SUPPLICANT),y)
38865 +WFLAGS += -DWPA_SUPPLICANT_SUPPORT
38866 +endif
38867 +
38868 +ifeq ($(HAS_NATIVE_WPA_SUPPLICANT_SUPPORT),y)
38869 +WFLAGS += -DNATIVE_WPA_SUPPLICANT_SUPPORT
38870 +endif
38871 +
38872 +ifeq ($(HAS_ATE),y)
38873 +WFLAGS += -DRALINK_ATE
38874 +ifeq ($(HAS_28xx_QA),y)
38875 +WFLAGS += -DRALINK_28xx_QA
38876 +endif
38877 +endif
38878 +
38879 +ifeq ($(HAS_SNMP_SUPPORT),y)
38880 +WFLAGS += -DSNMP_SUPPORT
38881 +endif
38882 +
38883 +ifeq ($(HAS_QOS_DLS_SUPPORT),y)
38884 +WFLAGS += -DQOS_DLS_SUPPORT
38885 +endif
38886 +
38887 +ifeq ($(HAS_DOT11_N_SUPPORT),y)
38888 +WFLAGS += -DDOT11_N_SUPPORT
38889 +endif
38890 +
38891 +ifeq ($(HAS_CS_SUPPORT),y)
38892 +WFLAGS += -DCARRIER_DETECTION_SUPPORT
38893 +endif
38894 +
38895 +ifeq ($(HAS_SINGLE_SKU_SUPPORT),y)
38896 +WFLAGS += -DSINGLE_SKU
38897 +endif
38898 +
38899 +endif
38900 +# endif of ifeq ($(RT28xx_MODE),STA)
38901 +#endif // CONFIG_STA_SUPPORT //
38902 +
38903 +#################################################
38904 +
38905 +#################################################
38906 +
38907 +#
38908 +# Common compiler flag
38909 +#
38910 +
38911 +
38912 +ifeq ($(HAS_EXT_BUILD_CHANNEL_LIST),y)
38913 +WFLAGS += -DEXT_BUILD_CHANNEL_LIST
38914 +endif
38915 +
38916 +ifeq ($(CHIPSET),2860)
38917 +WFLAGS +=-DRT2860
38918 +endif
38919 +
38920 +ifeq ($(CHIPSET),2870)
38921 +WFLAGS +=-DRT2870
38922 +endif
38923 +
38924 +ifeq ($(PLATFORM),5VT)
38925 +#WFLAGS += -DCONFIG_5VT_ENHANCE
38926 +endif
38927 +
38928 +ifeq ($(HAS_BLOCK_NET_IF),y)
38929 +WFLAGS += -DBLOCK_NET_IF
38930 +endif
38931 +
38932 +ifeq ($(HAS_DFS_SUPPORT),y)
38933 +WFLAGS += -DDFS_SUPPORT
38934 +endif
38935 +
38936 +#ifdef MULTI_CARD
38937 +ifeq ($(HAS_MC_SUPPORT),y)
38938 +WFLAGS += -DMULTIPLE_CARD_SUPPORT
38939 +endif
38940 +#endif // MULTI_CARD //
38941 +
38942 +ifeq ($(HAS_LLTD),y)
38943 +WFLAGS += -DLLTD_SUPPORT
38944 +endif
38945 +
38946 +ifeq ($(PLATFORM),IXP)
38947 +WFLAGS += -DRT_BIG_ENDIAN
38948 +endif
38949 +
38950 +ifeq ($(PLATFORM),IKANOS_V160)
38951 +WFLAGS += -DRT_BIG_ENDIAN -DIKANOS_VX_1X0
38952 +endif
38953 +
38954 +ifeq ($(PLATFORM),IKANOS_V180)
38955 +WFLAGS += -DRT_BIG_ENDIAN -DIKANOS_VX_1X0
38956 +endif
38957 +
38958 +ifeq ($(PLATFORM),INF_TWINPASS)
38959 +WFLAGS += -DRT_BIG_ENDIAN -DINF_TWINPASS
38960 +endif
38961 +
38962 +ifeq ($(PLATFORM),INF_DANUBE)
38963 +WFLAGS += -DINF_DANUBE -DRT_BIG_ENDIAN
38964 +endif
38965 +
38966 +ifeq ($(PLATFORM),CAVM_OCTEON)
38967 +WFLAGS += -DRT_BIG_ENDIAN
38968 +endif
38969 +
38970 +ifeq ($(PLATFORM),BRCM_6358)
38971 +WFLAGS += -DRT_BIG_ENDIAN
38972 +endif
38973 +
38974 +ifeq ($(PLATFORM),INF_AMAZON_SE)
38975 +#WFLAGS += -DRT_BIG_ENDIAN -DINF_AMAZON_SE -DBG_FT_SUPPORT
38976 +WFLAGS += -DRT_BIG_ENDIAN -DINF_AMAZON_SE
38977 +endif
38978 +
38979 +#kernel build options for 2.4
38980 +# move to Makefile outside LINUX_SRC := /opt/star/kernel/linux-2.4.27-star
38981 +
38982 +ifeq ($(PLATFORM),STAR)
38983 +CFLAGS := -D__KERNEL__ -I$(LINUX_SRC)/include -I$(RT28xx_DIR)/include -Wall -Wstrict-prototypes -Wno-trigraphs -O2 -fno-strict-aliasing -fno-common -Uarm -fno-common -pipe -mapcs-32 -D__LINUX_ARM_ARCH__=4 -march=armv4 -mshort-load-bytes -msoft-float -Uarm -DMODULE -DMODVERSIONS -include $(LINUX_SRC)/include/linux/modversions.h $(WFLAGS)
38984 +
38985 +export CFLAGS
38986 +endif
38987 +
38988 +ifeq ($(PLATFORM),SIGMA)
38989 +CFLAGS := -D__KERNEL__ -I$(RT28xx_DIR)/include -I$(LINUX_SRC)/include -I$(LINUX_SRC)/include/asm/gcc -I$(LINUX_SRC)/include/asm-mips/mach-tango2 -I$(LINUX_SRC)/include/asm-mips/mach-tango2 -DEM86XX_CHIP=EM86XX_CHIPID_TANGO2 -DEM86XX_REVISION=6 -I$(LINUX_SRC)/include/asm-mips/mach-generic -I$(RT2860_DIR)/include -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -ffreestanding -O2 -fomit-frame-pointer -G 0 -mno-abicalls -fno-pic -pipe -mabi=32 -march=mips32r2 -Wa,-32 -Wa,-march=mips32r2 -Wa,-mips32r2 -Wa,--trap -DMODULE $(WFLAGS)
38990 +
38991 +export CFLAGS
38992 +endif
38993 +
38994 +ifeq ($(PLATFORM),SIGMA_8622)
38995 +CFLAGS := -D__KERNEL__ -I$(CROSS_COMPILE_INCLUDE)/include -I$(LINUX_SRC)/include -I$(RT28xx_DIR)/include -Wall -Wstrict-prototypes -Wno-trigraphs -O2 -fno-strict-aliasing -fno-common -fno-common -pipe -fno-builtin -D__linux__ -DNO_MM -mapcs-32 -march=armv4 -mtune=arm7tdmi -msoft-float -DMODULE -mshort-load-bytes -nostdinc -iwithprefix -DMODULE $(WFLAGS)
38996 +export CFLAGS
38997 +endif
38998 +
38999 +ifeq ($(PLATFORM),5VT)
39000 +CFLAGS := -D__KERNEL__ -I$(LINUX_SRC)/include -I$(RT28xx_DIR)/include -mlittle-endian -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -O3 -fno-omit-frame-pointer -fno-optimize-sibling-calls -fno-omit-frame-pointer -mapcs -mno-sched-prolog -mabi=apcs-gnu -mno-thumb-interwork -D__LINUX_ARM_ARCH__=5 -march=armv5te -mtune=arm926ej-s --param max-inline-insns-single=40000 -Uarm -Wdeclaration-after-statement -Wno-pointer-sign -DMODULE $(WFLAGS)
39001 +
39002 +export CFLAGS
39003 +endif
39004 +
39005 +ifeq ($(PLATFORM),IKANOS_V160)
39006 +CFLAGS := -D__KERNEL__ -I$(LINUX_SRC)/include -I$(LINUX_SRC)/include/asm/gcc -I$(LINUX_SRC)/include/asm-mips/mach-tango2 -I$(LINUX_SRC)/include/asm-mips/mach-tango2 -I$(LINUX_SRC)/include/asm-mips/mach-generic -I$(RT28xx_DIR)/include -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -ffreestanding -O2 -fomit-frame-pointer -G 0 -mno-abicalls -fno-pic -pipe -march=lx4189 -Wa, -DMODULE $(WFLAGS)
39007 +export CFLAGS
39008 +endif
39009 +
39010 +ifeq ($(PLATFORM),IKANOS_V180)
39011 +CFLAGS := -D__KERNEL__ -I$(LINUX_SRC)/include -I$(LINUX_SRC)/include/asm/gcc -I$(LINUX_SRC)/include/asm-mips/mach-tango2 -I$(LINUX_SRC)/include/asm-mips/mach-tango2 -I$(LINUX_SRC)/include/asm-mips/mach-generic -I$(RT28xx_DIR)/include -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -ffreestanding -O2 -fomit-frame-pointer -G 0 -mno-abicalls -fno-pic -pipe -mips32r2 -Wa, -DMODULE $(WFLAGS)
39012 +export CFLAGS
39013 +endif
39014 +
39015 +ifeq ($(PLATFORM),INF_TWINPASS)
39016 +CFLAGS := -D__KERNEL__ -DMODULE -I$(LINUX_SRC)/include -I$(RT28xx_DIR)/include -Wall -Wstrict-prototypes -Wno-trigraphs -O2 -fomit-frame-pointer -fno-strict-aliasing -fno-common -G 0 -mno-abicalls -fno-pic -march=4kc -mips32 -Wa,--trap -pipe -mlong-calls $(WFLAGS)
39017 +export CFLAGS
39018 +endif
39019 +
39020 +ifeq ($(PLATFORM),INF_DANUBE)
39021 +CFLAGS := -I$(RT28xx_DIR)/include $(WFLAGS) -Wundef -fno-strict-aliasing -fno-common -ffreestanding -Os -fomit-frame-pointer -G 0 -mno-abicalls -fno-pic -pipe -msoft-float -mabi=32 -march=mips32 -Wa,-32 -Wa,-march=mips32 -Wa,-mips32 -Wa,--trap -I$(LINUX_SRC)/include/asm-mips/mach-generic
39022 +export CFLAGS
39023 +endif
39024 +
39025 +ifeq ($(PLATFORM),BRCM_6358)
39026 +CFLAGS := $(WFLAGS) -I$(RT28xx_DIR)/include -nostdinc -iwithprefix include -D__KERNEL__ -Wall -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -I $(LINUX_SRC)/include/asm/gcc -G 0 -mno-abicalls -fno-pic -pipe -finline-limit=100000 -mabi=32 -march=mips32 -Wa,-32 -Wa,-march=mips32 -Wa,-mips32 -Wa,--trap -I$(LINUX_SRC)/include/asm-mips/mach-bcm963xx -I$(LINUX_SRC)/include/asm-mips/mach-generic -Os -fomit-frame-pointer -Wdeclaration-after-statement -DMODULE -mlong-calls
39027 +export CFLAGS
39028 +endif
39029 +
39030 +ifeq ($(PLATFORM),PC)
39031 + ifneq (,$(findstring 2.4,$(LINUX_SRC)))
39032 + # Linux 2.4
39033 + CFLAGS := -D__KERNEL__ -I$(LINUX_SRC)/include -I$(RT28xx_DIR)/include -O2 -fomit-frame-pointer -fno-strict-aliasing -fno-common -pipe -mpreferred-stack-boundary=2 -march=i686 -DMODULE -DMODVERSIONS -include $(LINUX_SRC)/include/linux/modversions.h $(WFLAGS)
39034 + export CFLAGS
39035 + else
39036 + # Linux 2.6
39037 + EXTRA_CFLAGS := $(WFLAGS) -I$(RT28xx_DIR)/include
39038 + endif
39039 +endif
39040 +
39041 +ifeq ($(PLATFORM),IXP)
39042 + EXTRA_CFLAGS := -v $(WFLAGS) -I$(RT28xx_DIR)/include -mbig-endian
39043 +endif
39044 +
39045 +ifeq ($(PLATFORM),CAVM_OCTEON)
39046 + EXTRA_CFLAGS := $(WFLAGS) -I$(RT28xx_DIR)/include \
39047 + -mabi=64 $(WFLAGS)
39048 +export CFLAGS
39049 +endif
39050 +
39051 --- /dev/null
39052 +++ b/drivers/staging/rt2860/dfs.h
39053 @@ -0,0 +1,100 @@
39054 +/*
39055 + *************************************************************************
39056 + * Ralink Tech Inc.
39057 + * 5F., No.36, Taiyuan St., Jhubei City,
39058 + * Hsinchu County 302,
39059 + * Taiwan, R.O.C.
39060 + *
39061 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
39062 + *
39063 + * This program is free software; you can redistribute it and/or modify *
39064 + * it under the terms of the GNU General Public License as published by *
39065 + * the Free Software Foundation; either version 2 of the License, or *
39066 + * (at your option) any later version. *
39067 + * *
39068 + * This program is distributed in the hope that it will be useful, *
39069 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
39070 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
39071 + * GNU General Public License for more details. *
39072 + * *
39073 + * You should have received a copy of the GNU General Public License *
39074 + * along with this program; if not, write to the *
39075 + * Free Software Foundation, Inc., *
39076 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
39077 + * *
39078 + *************************************************************************
39079 +
39080 + Module Name:
39081 + dfs.h
39082 +
39083 + Abstract:
39084 + Support DFS function.
39085 +
39086 + Revision History:
39087 + Who When What
39088 + -------- ---------- ----------------------------------------------
39089 + Fonchi 03-12-2007 created
39090 +*/
39091 +
39092 +#define RADAR_PULSE 1
39093 +#define RADAR_WIDTH 2
39094 +
39095 +#define WIDTH_RD_IDLE 0
39096 +#define WIDTH_RD_CHECK 1
39097 +
39098 +
39099 +VOID BbpRadarDetectionStart(
39100 + IN PRTMP_ADAPTER pAd);
39101 +
39102 +VOID BbpRadarDetectionStop(
39103 + IN PRTMP_ADAPTER pAd);
39104 +
39105 +VOID RadarDetectionStart(
39106 + IN PRTMP_ADAPTER pAd,
39107 + IN BOOLEAN CTS_Protect,
39108 + IN UINT8 CTSPeriod);
39109 +
39110 +VOID RadarDetectionStop(
39111 + IN PRTMP_ADAPTER pAd);
39112 +
39113 +VOID RadarDetectPeriodic(
39114 + IN PRTMP_ADAPTER pAd);
39115 +
39116 +
39117 +BOOLEAN RadarChannelCheck(
39118 + IN PRTMP_ADAPTER pAd,
39119 + IN UCHAR Ch);
39120 +
39121 +ULONG JapRadarType(
39122 + IN PRTMP_ADAPTER pAd);
39123 +
39124 +ULONG RTMPBbpReadRadarDuration(
39125 + IN PRTMP_ADAPTER pAd);
39126 +
39127 +ULONG RTMPReadRadarDuration(
39128 + IN PRTMP_ADAPTER pAd);
39129 +
39130 +VOID RTMPCleanRadarDuration(
39131 + IN PRTMP_ADAPTER pAd);
39132 +
39133 +VOID RTMPPrepareRDCTSFrame(
39134 + IN PRTMP_ADAPTER pAd,
39135 + IN PUCHAR pDA,
39136 + IN ULONG Duration,
39137 + IN UCHAR RTSRate,
39138 + IN ULONG CTSBaseAddr,
39139 + IN UCHAR FrameGap);
39140 +
39141 +VOID RTMPPrepareRadarDetectParams(
39142 + IN PRTMP_ADAPTER pAd);
39143 +
39144 +
39145 +INT Set_ChMovingTime_Proc(
39146 + IN PRTMP_ADAPTER pAd,
39147 + IN PUCHAR arg);
39148 +
39149 +INT Set_LongPulseRadarTh_Proc(
39150 + IN PRTMP_ADAPTER pAd,
39151 + IN PUCHAR arg);
39152 +
39153 +
39154 --- /dev/null
39155 +++ b/drivers/staging/rt2860/Kconfig
39156 @@ -0,0 +1,5 @@
39157 +config RT2860
39158 + tristate "Ralink 2860 wireless support"
39159 + depends on PCI && X86 && WLAN_80211
39160 + ---help---
39161 + This is an experimental driver for the Ralink 2860 wireless chip.
39162 --- /dev/null
39163 +++ b/drivers/staging/rt2860/leap.h
39164 @@ -0,0 +1,215 @@
39165 +/*
39166 + *************************************************************************
39167 + * Ralink Tech Inc.
39168 + * 5F., No.36, Taiyuan St., Jhubei City,
39169 + * Hsinchu County 302,
39170 + * Taiwan, R.O.C.
39171 + *
39172 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
39173 + *
39174 + * This program is free software; you can redistribute it and/or modify *
39175 + * it under the terms of the GNU General Public License as published by *
39176 + * the Free Software Foundation; either version 2 of the License, or *
39177 + * (at your option) any later version. *
39178 + * *
39179 + * This program is distributed in the hope that it will be useful, *
39180 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
39181 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
39182 + * GNU General Public License for more details. *
39183 + * *
39184 + * You should have received a copy of the GNU General Public License *
39185 + * along with this program; if not, write to the *
39186 + * Free Software Foundation, Inc., *
39187 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
39188 + * *
39189 + *************************************************************************
39190 +
39191 + Module Name:
39192 + leap.h
39193 +
39194 + Abstract:
39195 +
39196 + Revision History:
39197 + Who When What
39198 + -------- ---------- ----------------------------------------------
39199 + Name Date Modification logs
39200 +*/
39201 +#ifndef __LEAP_H__
39202 +#define __LEAP_H__
39203 +
39204 +// Messages for Associate state machine
39205 +#define LEAP_MACHINE_BASE 30
39206 +
39207 +#define LEAP_MSG_REQUEST_IDENTITY 31
39208 +#define LEAP_MSG_REQUEST_LEAP 32
39209 +#define LEAP_MSG_SUCCESS 33
39210 +#define LEAP_MSG_FAILED 34
39211 +#define LEAP_MSG_RESPONSE_LEAP 35
39212 +#define LEAP_MSG_EAPOLKEY 36
39213 +#define LEAP_MSG_UNKNOWN 37
39214 +#define LEAP_MSG 38
39215 +//! assoc state-machine states
39216 +#define LEAP_IDLE 0
39217 +#define LEAP_WAIT_IDENTITY_REQUEST 1
39218 +#define LEAP_WAIT_CHANLLENGE_REQUEST 2
39219 +#define LEAP_WAIT_SUCCESS 3
39220 +#define LEAP_WAIT_CHANLLENGE_RESPONSE 4
39221 +#define LEAP_WAIT_EAPOLKEY 5
39222 +
39223 +#define LEAP_REASON_INVALID_AUTH 0x01
39224 +#define LEAP_REASON_AUTH_TIMEOUT 0x02
39225 +#define LEAP_REASON_CHALLENGE_FROM_AP_FAILED 0x03
39226 +#define LEAP_REASON_CHALLENGE_TO_AP_FAILED 0x04
39227 +
39228 +#define CISCO_AuthModeLEAP 0x80
39229 +#define CISCO_AuthModeLEAPNone 0x00
39230 +#define LEAP_AUTH_TIMEOUT 30000
39231 +#define LEAP_CHALLENGE_RESPONSE_LENGTH 24
39232 +#define LEAP_CHALLENGE_REQUEST_LENGTH 8
39233 +
39234 +typedef struct _LEAP_EAPOL_HEADER_ {
39235 + UCHAR Version;
39236 + UCHAR Type;
39237 + UCHAR Length[2];
39238 +} LEAP_EAPOL_HEADER, *PLEAP_EAPOL_HEADER;
39239 +
39240 +typedef struct _LEAP_EAPOL_PACKET_ {
39241 + UCHAR Code;
39242 + UCHAR Identifier;
39243 + UCHAR Length[2];
39244 + UCHAR Type;
39245 +} LEAP_EAPOL_PACKET, *PLEAP_EAPOL_PACKET;
39246 +
39247 +typedef struct _LEAP_EAP_CONTENTS_ {
39248 + UCHAR Version;
39249 + UCHAR Reserved;
39250 + UCHAR Length;
39251 +} LEAP_EAP_CONTENTS, *PLEAP_EAP_CONTENTS;
39252 +
39253 +/*** EAPOL key ***/
39254 +typedef struct _EAPOL_KEY_HEADER_ {
39255 + UCHAR Type;
39256 + UCHAR Length[2];
39257 + UCHAR Counter[8];
39258 + UCHAR IV[16];
39259 + UCHAR Index;
39260 + UCHAR Signature[16];
39261 +} EAPOL_KEY_HEADER, *PEAPOL_KEY_HEADER;
39262 +
39263 +BOOLEAN LeapMsgTypeSubst(
39264 + IN UCHAR EAPType,
39265 + OUT ULONG *MsgType);
39266 +
39267 +VOID LeapMachinePerformAction(
39268 + IN PRTMP_ADAPTER pAd,
39269 + IN STATE_MACHINE *S,
39270 + IN MLME_QUEUE_ELEM *Elem);
39271 +
39272 +VOID LeapMacHeaderInit(
39273 + IN PRTMP_ADAPTER pAd,
39274 + IN OUT PHEADER_802_11 pHdr80211,
39275 + IN UCHAR wep,
39276 + IN PUCHAR pAddr3);
39277 +
39278 +VOID LeapStartAction(
39279 + IN PRTMP_ADAPTER pAd,
39280 + IN MLME_QUEUE_ELEM *Elem);
39281 +
39282 +VOID LeapIdentityAction(
39283 + IN PRTMP_ADAPTER pAd,
39284 + IN MLME_QUEUE_ELEM *Elem);
39285 +
39286 +VOID LeapPeerChallengeAction(
39287 + IN PRTMP_ADAPTER pAd,
39288 + IN MLME_QUEUE_ELEM *Elem);
39289 +
39290 +VOID HashPwd(
39291 + IN PUCHAR pwd,
39292 + IN INT pwdlen,
39293 + OUT PUCHAR hash);
39294 +
39295 +VOID PeerChallengeResponse(
39296 + IN PUCHAR szChallenge,
39297 + IN PUCHAR smbPasswd,
39298 + OUT PUCHAR szResponse);
39299 +
39300 +VOID ParityKey(
39301 + OUT PUCHAR szOut,
39302 + IN PUCHAR szIn);
39303 +
39304 +VOID DesKey(
39305 + OUT ULONG k[16][2],
39306 + IN PUCHAR key,
39307 + IN INT decrypt);
39308 +
39309 +VOID Des(
39310 + IN ULONG ks[16][2],
39311 + OUT UCHAR block[8]);
39312 +
39313 +VOID DesEncrypt(
39314 + IN PUCHAR szClear,
39315 + IN PUCHAR szKey,
39316 + OUT PUCHAR szOut);
39317 +
39318 +VOID LeapNetworkChallengeAction(
39319 + IN PRTMP_ADAPTER pAd,
39320 + IN MLME_QUEUE_ELEM *Elem);
39321 +
39322 +VOID LeapNetworkChallengeResponse(
39323 + IN PRTMP_ADAPTER pAd,
39324 + IN MLME_QUEUE_ELEM *Elem);
39325 +
39326 +VOID HashpwdHash(
39327 + IN PUCHAR hash,
39328 + IN PUCHAR hashhash);
39329 +
39330 +VOID ProcessSessionKey(
39331 + OUT PUCHAR SessionKey,
39332 + IN PUCHAR hash2,
39333 + IN PUCHAR ChallengeToRadius,
39334 + IN PUCHAR ChallengeResponseFromRadius,
39335 + IN PUCHAR ChallengeFromRadius,
39336 + IN PUCHAR ChallengeResponseToRadius);
39337 +
39338 +VOID LeapEapolKeyAction(
39339 + IN PRTMP_ADAPTER pAd,
39340 + IN MLME_QUEUE_ELEM *Elem);
39341 +
39342 +VOID RogueApTableInit(
39343 + IN ROGUEAP_TABLE *Tab);
39344 +
39345 +ULONG RogueApTableSearch(
39346 + IN ROGUEAP_TABLE *Tab,
39347 + IN PUCHAR pAddr);
39348 +
39349 +VOID RogueApEntrySet(
39350 + IN PRTMP_ADAPTER pAd,
39351 + OUT ROGUEAP_ENTRY *pRogueAp,
39352 + IN PUCHAR pAddr,
39353 + IN UCHAR FaileCode);
39354 +
39355 +ULONG RogueApTableSetEntry(
39356 + IN PRTMP_ADAPTER pAd,
39357 + OUT ROGUEAP_TABLE *Tab,
39358 + IN PUCHAR pAddr,
39359 + IN UCHAR FaileCode);
39360 +
39361 +VOID RogueApTableDeleteEntry(
39362 + IN OUT ROGUEAP_TABLE *Tab,
39363 + IN PUCHAR pAddr);
39364 +
39365 +VOID LeapAuthTimeout(
39366 + IN PVOID SystemSpecific1,
39367 + IN PVOID FunctionContext,
39368 + IN PVOID SystemSpecific2,
39369 + IN PVOID SystemSpecific3);
39370 +
39371 +VOID LeapSendRogueAPReport(
39372 + IN PRTMP_ADAPTER pAd);
39373 +
39374 +BOOLEAN CCKMAssocRspSanity(
39375 + IN PRTMP_ADAPTER pAd,
39376 + IN VOID *Msg,
39377 + IN ULONG MsgLen);
39378 +
39379 +#endif // __LEAP_H__
39380 --- /dev/null
39381 +++ b/drivers/staging/rt2860/link_list.h
39382 @@ -0,0 +1,134 @@
39383 +/*
39384 + *************************************************************************
39385 + * Ralink Tech Inc.
39386 + * 5F., No.36, Taiyuan St., Jhubei City,
39387 + * Hsinchu County 302,
39388 + * Taiwan, R.O.C.
39389 + *
39390 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
39391 + *
39392 + * This program is free software; you can redistribute it and/or modify *
39393 + * it under the terms of the GNU General Public License as published by *
39394 + * the Free Software Foundation; either version 2 of the License, or *
39395 + * (at your option) any later version. *
39396 + * *
39397 + * This program is distributed in the hope that it will be useful, *
39398 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
39399 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
39400 + * GNU General Public License for more details. *
39401 + * *
39402 + * You should have received a copy of the GNU General Public License *
39403 + * along with this program; if not, write to the *
39404 + * Free Software Foundation, Inc., *
39405 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
39406 + * *
39407 + *************************************************************************
39408 + */
39409 +
39410 +#ifndef __LINK_LIST_H__
39411 +#define __LINK_LIST_H__
39412 +
39413 +typedef struct _LIST_ENTRY
39414 +{
39415 + struct _LIST_ENTRY *pNext;
39416 +} LIST_ENTRY, *PLIST_ENTRY;
39417 +
39418 +typedef struct _LIST_HEADR
39419 +{
39420 + PLIST_ENTRY pHead;
39421 + PLIST_ENTRY pTail;
39422 + UCHAR size;
39423 +} LIST_HEADER, *PLIST_HEADER;
39424 +
39425 +static inline VOID initList(
39426 + IN PLIST_HEADER pList)
39427 +{
39428 + pList->pHead = pList->pTail = NULL;
39429 + pList->size = 0;
39430 + return;
39431 +}
39432 +
39433 +static inline VOID insertTailList(
39434 + IN PLIST_HEADER pList,
39435 + IN PLIST_ENTRY pEntry)
39436 +{
39437 + pEntry->pNext = NULL;
39438 + if (pList->pTail)
39439 + pList->pTail->pNext = pEntry;
39440 + else
39441 + pList->pHead = pEntry;
39442 + pList->pTail = pEntry;
39443 + pList->size++;
39444 +
39445 + return;
39446 +}
39447 +
39448 +static inline PLIST_ENTRY removeHeadList(
39449 + IN PLIST_HEADER pList)
39450 +{
39451 + PLIST_ENTRY pNext;
39452 + PLIST_ENTRY pEntry;
39453 +
39454 + pEntry = pList->pHead;
39455 + if (pList->pHead != NULL)
39456 + {
39457 + pNext = pList->pHead->pNext;
39458 + pList->pHead = pNext;
39459 + if (pNext == NULL)
39460 + pList->pTail = NULL;
39461 + pList->size--;
39462 + }
39463 + return pEntry;
39464 +}
39465 +
39466 +static inline int getListSize(
39467 + IN PLIST_HEADER pList)
39468 +{
39469 + return pList->size;
39470 +}
39471 +
39472 +static inline PLIST_ENTRY delEntryList(
39473 + IN PLIST_HEADER pList,
39474 + IN PLIST_ENTRY pEntry)
39475 +{
39476 + PLIST_ENTRY pCurEntry;
39477 + PLIST_ENTRY pPrvEntry;
39478 +
39479 + if(pList->pHead == NULL)
39480 + return NULL;
39481 +
39482 + if(pEntry == pList->pHead)
39483 + {
39484 + pCurEntry = pList->pHead;
39485 + pList->pHead = pCurEntry->pNext;
39486 +
39487 + if(pList->pHead == NULL)
39488 + pList->pTail = NULL;
39489 +
39490 + pList->size--;
39491 + return pCurEntry;
39492 + }
39493 +
39494 + pPrvEntry = pList->pHead;
39495 + pCurEntry = pPrvEntry->pNext;
39496 + while(pCurEntry != NULL)
39497 + {
39498 + if (pEntry == pCurEntry)
39499 + {
39500 + pPrvEntry->pNext = pCurEntry->pNext;
39501 +
39502 + if(pEntry == pList->pTail)
39503 + pList->pTail = pPrvEntry;
39504 +
39505 + pList->size--;
39506 + break;
39507 + }
39508 + pPrvEntry = pCurEntry;
39509 + pCurEntry = pPrvEntry->pNext;
39510 + }
39511 +
39512 + return pCurEntry;
39513 +}
39514 +
39515 +#endif // ___LINK_LIST_H__ //
39516 +
39517 --- /dev/null
39518 +++ b/drivers/staging/rt2860/Makefile
39519 @@ -0,0 +1,41 @@
39520 +obj-$(CONFIG_RT2860) += rt2860sta.o
39521 +
39522 +# TODO: all of these should be removed
39523 +EXTRA_CFLAGS += -DLINUX -DAGGREGATION_SUPPORT -DPIGGYBACK_SUPPORT -DWMM_SUPPORT
39524 +EXTRA_CFLAGS += -DRT2860
39525 +EXTRA_CFLAGS += -DCONFIG_STA_SUPPORT
39526 +EXTRA_CFLAGS += -DDBG
39527 +EXTRA_CFLAGS += -DDOT11_N_SUPPORT
39528 +
39529 +rt2860sta-objs := \
39530 + common/md5.o \
39531 + common/mlme.o \
39532 + common/rtmp_wep.o \
39533 + common/action.o \
39534 + common/cmm_data.o \
39535 + common/rtmp_init.o \
39536 + common/rtmp_tkip.o \
39537 + common/cmm_sync.o \
39538 + common/eeprom.o \
39539 + common/cmm_sanity.o \
39540 + common/cmm_info.o \
39541 + common/cmm_wpa.o \
39542 + common/dfs.o \
39543 + common/spectrum.o \
39544 + sta/assoc.o \
39545 + sta/aironet.o \
39546 + sta/auth.o \
39547 + sta/auth_rsp.o \
39548 + sta/sync.o \
39549 + sta/sanity.o \
39550 + sta/rtmp_data.o \
39551 + sta/connect.o \
39552 + sta/wpa.o \
39553 + rt_linux.o \
39554 + rt_profile.o \
39555 + rt_main_dev.o \
39556 + sta_ioctl.o \
39557 + common/ba_action.o \
39558 + common/2860_rtmp_init.o \
39559 + 2860_main_dev.o \
39560 + common/cmm_data_2860.o
39561 --- /dev/null
39562 +++ b/drivers/staging/rt2860/md4.h
39563 @@ -0,0 +1,42 @@
39564 +/*
39565 + *************************************************************************
39566 + * Ralink Tech Inc.
39567 + * 5F., No.36, Taiyuan St., Jhubei City,
39568 + * Hsinchu County 302,
39569 + * Taiwan, R.O.C.
39570 + *
39571 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
39572 + *
39573 + * This program is free software; you can redistribute it and/or modify *
39574 + * it under the terms of the GNU General Public License as published by *
39575 + * the Free Software Foundation; either version 2 of the License, or *
39576 + * (at your option) any later version. *
39577 + * *
39578 + * This program is distributed in the hope that it will be useful, *
39579 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
39580 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
39581 + * GNU General Public License for more details. *
39582 + * *
39583 + * You should have received a copy of the GNU General Public License *
39584 + * along with this program; if not, write to the *
39585 + * Free Software Foundation, Inc., *
39586 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
39587 + * *
39588 + *************************************************************************
39589 + */
39590 +
39591 +#ifndef __MD4_H__
39592 +#define __MD4_H__
39593 +
39594 +/* MD4 context. */
39595 +typedef struct _MD4_CTX_ {
39596 + ULONG state[4]; /* state (ABCD) */
39597 + ULONG count[2]; /* number of bits, modulo 2^64 (lsb first) */
39598 + UCHAR buffer[64]; /* input buffer */
39599 +} MD4_CTX;
39600 +
39601 +VOID MD4Init (MD4_CTX *);
39602 +VOID MD4Update (MD4_CTX *, PUCHAR, UINT);
39603 +VOID MD4Final (UCHAR [16], MD4_CTX *);
39604 +
39605 +#endif //__MD4_H__
39606 \ No newline at end of file
39607 --- /dev/null
39608 +++ b/drivers/staging/rt2860/md5.h
39609 @@ -0,0 +1,107 @@
39610 +/*
39611 + *************************************************************************
39612 + * Ralink Tech Inc.
39613 + * 5F., No.36, Taiyuan St., Jhubei City,
39614 + * Hsinchu County 302,
39615 + * Taiwan, R.O.C.
39616 + *
39617 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
39618 + *
39619 + * This program is free software; you can redistribute it and/or modify *
39620 + * it under the terms of the GNU General Public License as published by *
39621 + * the Free Software Foundation; either version 2 of the License, or *
39622 + * (at your option) any later version. *
39623 + * *
39624 + * This program is distributed in the hope that it will be useful, *
39625 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
39626 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
39627 + * GNU General Public License for more details. *
39628 + * *
39629 + * You should have received a copy of the GNU General Public License *
39630 + * along with this program; if not, write to the *
39631 + * Free Software Foundation, Inc., *
39632 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
39633 + * *
39634 + *************************************************************************
39635 +
39636 + Module Name:
39637 + md5.h
39638 +
39639 + Abstract:
39640 +
39641 + Revision History:
39642 + Who When What
39643 + -------- ---------- ----------------------------------------------
39644 + Name Date Modification logs
39645 + jan 10-28-03 Initial
39646 + Rita 11-23-04 Modify MD5 and SHA-1
39647 +*/
39648 +
39649 +#ifndef uint8
39650 +#define uint8 unsigned char
39651 +#endif
39652 +
39653 +#ifndef uint32
39654 +#define uint32 unsigned long int
39655 +#endif
39656 +
39657 +
39658 +#ifndef __MD5_H__
39659 +#define __MD5_H__
39660 +
39661 +#define MD5_MAC_LEN 16
39662 +
39663 +typedef struct _MD5_CTX {
39664 + UINT32 Buf[4]; // buffers of four states
39665 + UCHAR Input[64]; // input message
39666 + UINT32 LenInBitCount[2]; // length counter for input message, 0 up to 64 bits
39667 +} MD5_CTX;
39668 +
39669 +VOID MD5Init(MD5_CTX *pCtx);
39670 +VOID MD5Update(MD5_CTX *pCtx, UCHAR *pData, UINT32 LenInBytes);
39671 +VOID MD5Final(UCHAR Digest[16], MD5_CTX *pCtx);
39672 +VOID MD5Transform(UINT32 Buf[4], UINT32 Mes[16]);
39673 +
39674 +void md5_mac(u8 *key, size_t key_len, u8 *data, size_t data_len, u8 *mac);
39675 +void hmac_md5(u8 *key, size_t key_len, u8 *data, size_t data_len, u8 *mac);
39676 +
39677 +//
39678 +// SHA context
39679 +//
39680 +typedef struct _SHA_CTX
39681 +{
39682 + UINT32 Buf[5]; // buffers of five states
39683 + UCHAR Input[80]; // input message
39684 + UINT32 LenInBitCount[2]; // length counter for input message, 0 up to 64 bits
39685 +
39686 +} SHA_CTX;
39687 +
39688 +VOID SHAInit(SHA_CTX *pCtx);
39689 +UCHAR SHAUpdate(SHA_CTX *pCtx, UCHAR *pData, UINT32 LenInBytes);
39690 +VOID SHAFinal(SHA_CTX *pCtx, UCHAR Digest[20]);
39691 +VOID SHATransform(UINT32 Buf[5], UINT32 Mes[20]);
39692 +
39693 +#define SHA_DIGEST_LEN 20
39694 +#endif // __MD5_H__
39695 +
39696 +/******************************************************************************/
39697 +#ifndef _AES_H
39698 +#define _AES_H
39699 +
39700 +typedef struct
39701 +{
39702 + uint32 erk[64]; /* encryption round keys */
39703 + uint32 drk[64]; /* decryption round keys */
39704 + int nr; /* number of rounds */
39705 +}
39706 +aes_context;
39707 +
39708 +int rtmp_aes_set_key( aes_context *ctx, uint8 *key, int nbits );
39709 +void rtmp_aes_encrypt( aes_context *ctx, uint8 input[16], uint8 output[16] );
39710 +void rtmp_aes_decrypt( aes_context *ctx, uint8 input[16], uint8 output[16] );
39711 +
39712 +void F(char *password, unsigned char *ssid, int ssidlength, int iterations, int count, unsigned char *output);
39713 +int PasswordHash(char *password, unsigned char *ssid, int ssidlength, unsigned char *output);
39714 +
39715 +#endif /* aes.h */
39716 +
39717 --- /dev/null
39718 +++ b/drivers/staging/rt2860/mlme.h
39719 @@ -0,0 +1,1447 @@
39720 +/*
39721 + *************************************************************************
39722 + * Ralink Tech Inc.
39723 + * 5F., No.36, Taiyuan St., Jhubei City,
39724 + * Hsinchu County 302,
39725 + * Taiwan, R.O.C.
39726 + *
39727 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
39728 + *
39729 + * This program is free software; you can redistribute it and/or modify *
39730 + * it under the terms of the GNU General Public License as published by *
39731 + * the Free Software Foundation; either version 2 of the License, or *
39732 + * (at your option) any later version. *
39733 + * *
39734 + * This program is distributed in the hope that it will be useful, *
39735 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
39736 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
39737 + * GNU General Public License for more details. *
39738 + * *
39739 + * You should have received a copy of the GNU General Public License *
39740 + * along with this program; if not, write to the *
39741 + * Free Software Foundation, Inc., *
39742 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
39743 + * *
39744 + *************************************************************************
39745 +
39746 + Module Name:
39747 + mlme.h
39748 +
39749 + Abstract:
39750 +
39751 + Revision History:
39752 + Who When What
39753 + -------- ---------- ----------------------------------------------
39754 + John Chang 2003-08-28 Created
39755 + John Chang 2004-09-06 modified for RT2600
39756 +
39757 +*/
39758 +#ifndef __MLME_H__
39759 +#define __MLME_H__
39760 +
39761 +// maximum supported capability information -
39762 +// ESS, IBSS, Privacy, Short Preamble, Spectrum mgmt, Short Slot
39763 +#define SUPPORTED_CAPABILITY_INFO 0x0533
39764 +
39765 +#define END_OF_ARGS -1
39766 +#define LFSR_MASK 0x80000057
39767 +#define MLME_TASK_EXEC_INTV 100/*200*/ //
39768 +#define LEAD_TIME 5
39769 +#define MLME_TASK_EXEC_MULTIPLE 10 /*5*/ // MLME_TASK_EXEC_MULTIPLE * MLME_TASK_EXEC_INTV = 1 sec
39770 +#define REORDER_EXEC_INTV 100 // 0.1 sec
39771 +
39772 +// The definition of Radar detection duration region
39773 +#define CE 0
39774 +#define FCC 1
39775 +#define JAP 2
39776 +#define JAP_W53 3
39777 +#define JAP_W56 4
39778 +#define MAX_RD_REGION 5
39779 +
39780 +#ifdef NDIS51_MINIPORT
39781 +#define BEACON_LOST_TIME 4000 // 2048 msec = 2 sec
39782 +#else
39783 +#define BEACON_LOST_TIME 4 * OS_HZ // 2048 msec = 2 sec
39784 +#endif
39785 +
39786 +#define DLS_TIMEOUT 1200 // unit: msec
39787 +#define AUTH_TIMEOUT 300 // unit: msec
39788 +#define ASSOC_TIMEOUT 300 // unit: msec
39789 +#define JOIN_TIMEOUT 2 * OS_HZ // unit: msec
39790 +#define SHORT_CHANNEL_TIME 90 // unit: msec
39791 +#define MIN_CHANNEL_TIME 110 // unit: msec, for dual band scan
39792 +#define MAX_CHANNEL_TIME 140 // unit: msec, for single band scan
39793 +#define FAST_ACTIVE_SCAN_TIME 30 // Active scan waiting for probe response time
39794 +#define CW_MIN_IN_BITS 4 // actual CwMin = 2^CW_MIN_IN_BITS - 1
39795 +
39796 +
39797 +#ifdef CONFIG_STA_SUPPORT
39798 +#ifndef CONFIG_AP_SUPPORT
39799 +#define CW_MAX_IN_BITS 10 // actual CwMax = 2^CW_MAX_IN_BITS - 1
39800 +#endif
39801 +#endif // CONFIG_STA_SUPPORT //
39802 +
39803 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
39804 +extern UINT32 CW_MAX_IN_BITS;
39805 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
39806 +
39807 +// Note: RSSI_TO_DBM_OFFSET has been changed to variable for new RF (2004-0720).
39808 +// SHould not refer to this constant anymore
39809 +//#define RSSI_TO_DBM_OFFSET 120 // for RT2530 RSSI-115 = dBm
39810 +#define RSSI_FOR_MID_TX_POWER -55 // -55 db is considered mid-distance
39811 +#define RSSI_FOR_LOW_TX_POWER -45 // -45 db is considered very short distance and
39812 + // eligible to use a lower TX power
39813 +#define RSSI_FOR_LOWEST_TX_POWER -30
39814 +//#define MID_TX_POWER_DELTA 0 // 0 db from full TX power upon mid-distance to AP
39815 +#define LOW_TX_POWER_DELTA 6 // -3 db from full TX power upon very short distance. 1 grade is 0.5 db
39816 +#define LOWEST_TX_POWER_DELTA 16 // -8 db from full TX power upon shortest distance. 1 grade is 0.5 db
39817 +
39818 +#define RSSI_TRIGGERED_UPON_BELOW_THRESHOLD 0
39819 +#define RSSI_TRIGGERED_UPON_EXCCEED_THRESHOLD 1
39820 +#define RSSI_THRESHOLD_FOR_ROAMING 25
39821 +#define RSSI_DELTA 5
39822 +
39823 +// Channel Quality Indication
39824 +#define CQI_IS_GOOD(cqi) ((cqi) >= 50)
39825 +//#define CQI_IS_FAIR(cqi) (((cqi) >= 20) && ((cqi) < 50))
39826 +#define CQI_IS_POOR(cqi) (cqi < 50) //(((cqi) >= 5) && ((cqi) < 20))
39827 +#define CQI_IS_BAD(cqi) (cqi < 5)
39828 +#define CQI_IS_DEAD(cqi) (cqi == 0)
39829 +
39830 +// weighting factor to calculate Channel quality, total should be 100%
39831 +#define RSSI_WEIGHTING 50
39832 +#define TX_WEIGHTING 30
39833 +#define RX_WEIGHTING 20
39834 +
39835 +#define BSS_NOT_FOUND 0xFFFFFFFF
39836 +
39837 +
39838 +#ifdef CONFIG_STA_SUPPORT
39839 +#define MAX_LEN_OF_MLME_QUEUE 40 //10
39840 +#endif // CONFIG_STA_SUPPORT //
39841 +
39842 +#define SCAN_PASSIVE 18 // scan with no probe request, only wait beacon and probe response
39843 +#define SCAN_ACTIVE 19 // scan with probe request, and wait beacon and probe response
39844 +#define SCAN_CISCO_PASSIVE 20 // Single channel passive scan
39845 +#define SCAN_CISCO_ACTIVE 21 // Single channel active scan
39846 +#define SCAN_CISCO_NOISE 22 // Single channel passive scan for noise histogram collection
39847 +#define SCAN_CISCO_CHANNEL_LOAD 23 // Single channel passive scan for channel load collection
39848 +#define FAST_SCAN_ACTIVE 24 // scan with probe request, and wait beacon and probe response
39849 +
39850 +#ifdef DOT11N_DRAFT3
39851 +#define SCAN_2040_BSS_COEXIST 26
39852 +#endif // DOT11N_DRAFT3 //
39853 +
39854 +#define MAC_ADDR_IS_GROUP(Addr) (((Addr[0]) & 0x01))
39855 +#define MAC_ADDR_HASH(Addr) (Addr[0] ^ Addr[1] ^ Addr[2] ^ Addr[3] ^ Addr[4] ^ Addr[5])
39856 +#define MAC_ADDR_HASH_INDEX(Addr) (MAC_ADDR_HASH(Addr) % HASH_TABLE_SIZE)
39857 +#define TID_MAC_HASH(Addr,TID) (TID^Addr[0] ^ Addr[1] ^ Addr[2] ^ Addr[3] ^ Addr[4] ^ Addr[5])
39858 +#define TID_MAC_HASH_INDEX(Addr,TID) (TID_MAC_HASH(Addr,TID) % HASH_TABLE_SIZE)
39859 +
39860 +// LED Control
39861 +// assoiation ON. one LED ON. another blinking when TX, OFF when idle
39862 +// no association, both LED off
39863 +#define ASIC_LED_ACT_ON(pAd) RTMP_IO_WRITE32(pAd, MAC_CSR14, 0x00031e46)
39864 +#define ASIC_LED_ACT_OFF(pAd) RTMP_IO_WRITE32(pAd, MAC_CSR14, 0x00001e46)
39865 +
39866 +// bit definition of the 2-byte pBEACON->Capability field
39867 +#define CAP_IS_ESS_ON(x) (((x) & 0x0001) != 0)
39868 +#define CAP_IS_IBSS_ON(x) (((x) & 0x0002) != 0)
39869 +#define CAP_IS_CF_POLLABLE_ON(x) (((x) & 0x0004) != 0)
39870 +#define CAP_IS_CF_POLL_REQ_ON(x) (((x) & 0x0008) != 0)
39871 +#define CAP_IS_PRIVACY_ON(x) (((x) & 0x0010) != 0)
39872 +#define CAP_IS_SHORT_PREAMBLE_ON(x) (((x) & 0x0020) != 0)
39873 +#define CAP_IS_PBCC_ON(x) (((x) & 0x0040) != 0)
39874 +#define CAP_IS_AGILITY_ON(x) (((x) & 0x0080) != 0)
39875 +#define CAP_IS_SPECTRUM_MGMT(x) (((x) & 0x0100) != 0) // 802.11e d9
39876 +#define CAP_IS_QOS(x) (((x) & 0x0200) != 0) // 802.11e d9
39877 +#define CAP_IS_SHORT_SLOT(x) (((x) & 0x0400) != 0)
39878 +#define CAP_IS_APSD(x) (((x) & 0x0800) != 0) // 802.11e d9
39879 +#define CAP_IS_IMMED_BA(x) (((x) & 0x1000) != 0) // 802.11e d9
39880 +#define CAP_IS_DSSS_OFDM(x) (((x) & 0x2000) != 0)
39881 +#define CAP_IS_DELAY_BA(x) (((x) & 0x4000) != 0) // 802.11e d9
39882 +
39883 +#define CAP_GENERATE(ess,ibss,priv,s_pre,s_slot,spectrum) (((ess) ? 0x0001 : 0x0000) | ((ibss) ? 0x0002 : 0x0000) | ((priv) ? 0x0010 : 0x0000) | ((s_pre) ? 0x0020 : 0x0000) | ((s_slot) ? 0x0400 : 0x0000) | ((spectrum) ? 0x0100 : 0x0000))
39884 +
39885 +#define ERP_IS_NON_ERP_PRESENT(x) (((x) & 0x01) != 0) // 802.11g
39886 +#define ERP_IS_USE_PROTECTION(x) (((x) & 0x02) != 0) // 802.11g
39887 +#define ERP_IS_USE_BARKER_PREAMBLE(x) (((x) & 0x04) != 0) // 802.11g
39888 +
39889 +#define DRS_TX_QUALITY_WORST_BOUND 8// 3 // just test by gary
39890 +#define DRS_PENALTY 8
39891 +
39892 +#define BA_NOTUSE 2
39893 +//BA Policy subfiled value in ADDBA frame
39894 +#define IMMED_BA 1
39895 +#define DELAY_BA 0
39896 +
39897 +// BA Initiator subfield in DELBA frame
39898 +#define ORIGINATOR 1
39899 +#define RECIPIENT 0
39900 +
39901 +// ADDBA Status Code
39902 +#define ADDBA_RESULTCODE_SUCCESS 0
39903 +#define ADDBA_RESULTCODE_REFUSED 37
39904 +#define ADDBA_RESULTCODE_INVALID_PARAMETERS 38
39905 +
39906 +// DELBA Reason Code
39907 +#define DELBA_REASONCODE_QSTA_LEAVING 36
39908 +#define DELBA_REASONCODE_END_BA 37
39909 +#define DELBA_REASONCODE_UNKNOWN_BA 38
39910 +#define DELBA_REASONCODE_TIMEOUT 39
39911 +
39912 +// reset all OneSecTx counters
39913 +#define RESET_ONE_SEC_TX_CNT(__pEntry) \
39914 +if (((__pEntry)) != NULL) \
39915 +{ \
39916 + (__pEntry)->OneSecTxRetryOkCount = 0; \
39917 + (__pEntry)->OneSecTxFailCount = 0; \
39918 + (__pEntry)->OneSecTxNoRetryOkCount = 0; \
39919 +}
39920 +
39921 +//
39922 +// 802.11 frame formats
39923 +//
39924 +// HT Capability INFO field in HT Cap IE .
39925 +typedef struct PACKED {
39926 +#ifdef RT_BIG_ENDIAN
39927 + USHORT LSIGTxopProSup:1;
39928 + USHORT Forty_Mhz_Intolerant:1;
39929 + USHORT PSMP:1;
39930 + USHORT CCKmodein40:1;
39931 + USHORT AMsduSize:1;
39932 + USHORT DelayedBA:1; //rt2860c not support
39933 + USHORT RxSTBC:2;
39934 + USHORT TxSTBC:1;
39935 + USHORT ShortGIfor40:1; //for40MHz
39936 + USHORT ShortGIfor20:1;
39937 + USHORT GF:1; //green field
39938 + USHORT MimoPs:2;//momi power safe
39939 + USHORT ChannelWidth:1;
39940 + USHORT AdvCoding:1;
39941 +#else
39942 + USHORT AdvCoding:1;
39943 + USHORT ChannelWidth:1;
39944 + USHORT MimoPs:2;//momi power safe
39945 + USHORT GF:1; //green field
39946 + USHORT ShortGIfor20:1;
39947 + USHORT ShortGIfor40:1; //for40MHz
39948 + USHORT TxSTBC:1;
39949 + USHORT RxSTBC:2;
39950 + USHORT DelayedBA:1; //rt2860c not support
39951 + USHORT AMsduSize:1; // only support as zero
39952 + USHORT CCKmodein40:1;
39953 + USHORT PSMP:1;
39954 + USHORT Forty_Mhz_Intolerant:1;
39955 + USHORT LSIGTxopProSup:1;
39956 +#endif /* !RT_BIG_ENDIAN */
39957 +} HT_CAP_INFO, *PHT_CAP_INFO;
39958 +
39959 +// HT Capability INFO field in HT Cap IE .
39960 +typedef struct PACKED {
39961 +#ifdef RT_BIG_ENDIAN
39962 + UCHAR rsv:3;//momi power safe
39963 + UCHAR MpduDensity:3;
39964 + UCHAR MaxRAmpduFactor:2;
39965 +#else
39966 + UCHAR MaxRAmpduFactor:2;
39967 + UCHAR MpduDensity:3;
39968 + UCHAR rsv:3;//momi power safe
39969 +#endif /* !RT_BIG_ENDIAN */
39970 +} HT_CAP_PARM, *PHT_CAP_PARM;
39971 +
39972 +// HT Capability INFO field in HT Cap IE .
39973 +typedef struct PACKED {
39974 + UCHAR MCSSet[10];
39975 + UCHAR SupRate[2]; // unit : 1Mbps
39976 +#ifdef RT_BIG_ENDIAN
39977 + UCHAR rsv:3;
39978 + UCHAR MpduDensity:1;
39979 + UCHAR TxStream:2;
39980 + UCHAR TxRxNotEqual:1;
39981 + UCHAR TxMCSSetDefined:1;
39982 +#else
39983 + UCHAR TxMCSSetDefined:1;
39984 + UCHAR TxRxNotEqual:1;
39985 + UCHAR TxStream:2;
39986 + UCHAR MpduDensity:1;
39987 + UCHAR rsv:3;
39988 +#endif // RT_BIG_ENDIAN //
39989 + UCHAR rsv3[3];
39990 +} HT_MCS_SET, *PHT_MCS_SET;
39991 +
39992 +// HT Capability INFO field in HT Cap IE .
39993 +typedef struct PACKED {
39994 +#ifdef RT_BIG_ENDIAN
39995 + USHORT rsv2:4;
39996 + USHORT RDGSupport:1; //reverse Direction Grant support
39997 + USHORT PlusHTC:1; //+HTC control field support
39998 + USHORT MCSFeedback:2; //0:no MCS feedback, 2:unsolicited MCS feedback, 3:Full MCS feedback, 1:rsv.
39999 + USHORT rsv:5;//momi power safe
40000 + USHORT TranTime:2;
40001 + USHORT Pco:1;
40002 +#else
40003 + USHORT Pco:1;
40004 + USHORT TranTime:2;
40005 + USHORT rsv:5;//momi power safe
40006 + USHORT MCSFeedback:2; //0:no MCS feedback, 2:unsolicited MCS feedback, 3:Full MCS feedback, 1:rsv.
40007 + USHORT PlusHTC:1; //+HTC control field support
40008 + USHORT RDGSupport:1; //reverse Direction Grant support
40009 + USHORT rsv2:4;
40010 +#endif /* RT_BIG_ENDIAN */
40011 +} EXT_HT_CAP_INFO, *PEXT_HT_CAP_INFO;
40012 +
40013 +// HT Beamforming field in HT Cap IE .
40014 +typedef struct PACKED _HT_BF_CAP{
40015 +#ifdef RT_BIG_ENDIAN
40016 + ULONG rsv:3;
40017 + ULONG ChanEstimation:2;
40018 + ULONG CSIRowBFSup:2;
40019 + ULONG ComSteerBFAntSup:2;
40020 + ULONG NoComSteerBFAntSup:2;
40021 + ULONG CSIBFAntSup:2;
40022 + ULONG MinGrouping:2;
40023 + ULONG ExpComBF:2;
40024 + ULONG ExpNoComBF:2;
40025 + ULONG ExpCSIFbk:2;
40026 + ULONG ExpComSteerCapable:1;
40027 + ULONG ExpNoComSteerCapable:1;
40028 + ULONG ExpCSICapable:1;
40029 + ULONG Calibration:2;
40030 + ULONG ImpTxBFCapable:1;
40031 + ULONG TxNDPCapable:1;
40032 + ULONG RxNDPCapable:1;
40033 + ULONG TxSoundCapable:1;
40034 + ULONG RxSoundCapable:1;
40035 + ULONG TxBFRecCapable:1;
40036 +#else
40037 + ULONG TxBFRecCapable:1;
40038 + ULONG RxSoundCapable:1;
40039 + ULONG TxSoundCapable:1;
40040 + ULONG RxNDPCapable:1;
40041 + ULONG TxNDPCapable:1;
40042 + ULONG ImpTxBFCapable:1;
40043 + ULONG Calibration:2;
40044 + ULONG ExpCSICapable:1;
40045 + ULONG ExpNoComSteerCapable:1;
40046 + ULONG ExpComSteerCapable:1;
40047 + ULONG ExpCSIFbk:2;
40048 + ULONG ExpNoComBF:2;
40049 + ULONG ExpComBF:2;
40050 + ULONG MinGrouping:2;
40051 + ULONG CSIBFAntSup:2;
40052 + ULONG NoComSteerBFAntSup:2;
40053 + ULONG ComSteerBFAntSup:2;
40054 + ULONG CSIRowBFSup:2;
40055 + ULONG ChanEstimation:2;
40056 + ULONG rsv:3;
40057 +#endif // RT_BIG_ENDIAN //
40058 +} HT_BF_CAP, *PHT_BF_CAP;
40059 +
40060 +// HT antenna selection field in HT Cap IE .
40061 +typedef struct PACKED _HT_AS_CAP{
40062 +#ifdef RT_BIG_ENDIAN
40063 + UCHAR rsv:1;
40064 + UCHAR TxSoundPPDU:1;
40065 + UCHAR RxASel:1;
40066 + UCHAR AntIndFbk:1;
40067 + UCHAR ExpCSIFbk:1;
40068 + UCHAR AntIndFbkTxASEL:1;
40069 + UCHAR ExpCSIFbkTxASEL:1;
40070 + UCHAR AntSelect:1;
40071 +#else
40072 + UCHAR AntSelect:1;
40073 + UCHAR ExpCSIFbkTxASEL:1;
40074 + UCHAR AntIndFbkTxASEL:1;
40075 + UCHAR ExpCSIFbk:1;
40076 + UCHAR AntIndFbk:1;
40077 + UCHAR RxASel:1;
40078 + UCHAR TxSoundPPDU:1;
40079 + UCHAR rsv:1;
40080 +#endif // RT_BIG_ENDIAN //
40081 +} HT_AS_CAP, *PHT_AS_CAP;
40082 +
40083 +// Draft 1.0 set IE length 26, but is extensible..
40084 +#define SIZE_HT_CAP_IE 26
40085 +// The structure for HT Capability IE.
40086 +typedef struct PACKED _HT_CAPABILITY_IE{
40087 + HT_CAP_INFO HtCapInfo;
40088 + HT_CAP_PARM HtCapParm;
40089 +// HT_MCS_SET HtMCSSet;
40090 + UCHAR MCSSet[16];
40091 + EXT_HT_CAP_INFO ExtHtCapInfo;
40092 + HT_BF_CAP TxBFCap; // beamforming cap. rt2860c not support beamforming.
40093 + HT_AS_CAP ASCap; //antenna selection.
40094 +} HT_CAPABILITY_IE, *PHT_CAPABILITY_IE;
40095 +
40096 +
40097 +// 802.11n draft3 related structure definitions.
40098 +// 7.3.2.60
40099 +#define dot11OBSSScanPassiveDwell 20 // in TU. min amount of time that the STA continously scans each channel when performing an active OBSS scan.
40100 +#define dot11OBSSScanActiveDwell 10 // in TU.min amount of time that the STA continously scans each channel when performing an passive OBSS scan.
40101 +#define dot11BSSWidthTriggerScanInterval 300 // in sec. max interval between scan operations to be performed to detect BSS channel width trigger events.
40102 +#define dot11OBSSScanPassiveTotalPerChannel 200 // in TU. min total amount of time that the STA scans each channel when performing a passive OBSS scan.
40103 +#define dot11OBSSScanActiveTotalPerChannel 20 //in TU. min total amount of time that the STA scans each channel when performing a active OBSS scan
40104 +#define dot11BSSWidthChannelTransactionDelayFactor 5 // min ratio between the delay time in performing a switch from 20MHz BSS to 20/40 BSS operation and the maxima
40105 + // interval between overlapping BSS scan operations.
40106 +#define dot11BSSScanActivityThreshold 25 // in %%, max total time that a STA may be active on the medium during a period of
40107 + // (dot11BSSWidthChannelTransactionDelayFactor * dot11BSSWidthTriggerScanInterval) seconds without
40108 + // being obligated to perform OBSS Scan operations. default is 25(== 0.25%)
40109 +
40110 +typedef struct PACKED _OVERLAP_BSS_SCAN_IE{
40111 + USHORT ScanPassiveDwell;
40112 + USHORT ScanActiveDwell;
40113 + USHORT TriggerScanInt; // Trigger scan interval
40114 + USHORT PassiveTalPerChannel; // passive total per channel
40115 + USHORT ActiveTalPerChannel; // active total per channel
40116 + USHORT DelayFactor; // BSS width channel transition delay factor
40117 + USHORT ScanActThre; // Scan Activity threshold
40118 +}OVERLAP_BSS_SCAN_IE, *POVERLAP_BSS_SCAN_IE;
40119 +
40120 +
40121 +// 7.3.2.56. 20/40 Coexistence element used in Element ID = 72 = IE_2040_BSS_COEXIST
40122 +typedef union PACKED _BSS_2040_COEXIST_IE{
40123 + struct PACKED {
40124 + #ifdef RT_BIG_ENDIAN
40125 + UCHAR rsv:5;
40126 + UCHAR BSS20WidthReq:1;
40127 + UCHAR Intolerant40:1;
40128 + UCHAR InfoReq:1;
40129 + #else
40130 + UCHAR InfoReq:1;
40131 + UCHAR Intolerant40:1; // Inter-BSS. set 1 when prohibits a receiving BSS from operating as a 20/40 Mhz BSS.
40132 + UCHAR BSS20WidthReq:1; // Intra-BSS set 1 when prohibits a receiving AP from operating its BSS as a 20/40MHz BSS.
40133 + UCHAR rsv:5;
40134 +#endif // RT_BIG_ENDIAN //
40135 + } field;
40136 + UCHAR word;
40137 +} BSS_2040_COEXIST_IE, *PBSS_2040_COEXIST_IE;
40138 +
40139 +
40140 +typedef struct _TRIGGER_EVENTA{
40141 + BOOLEAN bValid;
40142 + UCHAR BSSID[6];
40143 + UCHAR RegClass; // Regulatory Class
40144 + USHORT Channel;
40145 + ULONG CDCounter; // Maintain a seperate count down counter for each Event A.
40146 +} TRIGGER_EVENTA, *PTRIGGER_EVENTA;
40147 +
40148 +// 20/40 trigger event table
40149 +// If one Event A delete or created, or if Event B is detected or not detected, STA should send 2040BSSCoexistence to AP.
40150 +#define MAX_TRIGGER_EVENT 64
40151 +typedef struct _TRIGGER_EVENT_TAB{
40152 + UCHAR EventANo;
40153 + TRIGGER_EVENTA EventA[MAX_TRIGGER_EVENT];
40154 + ULONG EventBCountDown; // Count down counter for Event B.
40155 +} TRIGGER_EVENT_TAB, *PTRIGGER_EVENT_TAB;
40156 +
40157 +// 7.3.27 20/40 Bss Coexistence Mgmt capability used in extended capabilities information IE( ID = 127 = IE_EXT_CAPABILITY).
40158 +// This is the first octet and was defined in 802.11n D3.03 and 802.11yD9.0
40159 +typedef struct PACKED _EXT_CAP_INFO_ELEMENT{
40160 +#ifdef RT_BIG_ENDIAN
40161 + UCHAR rsv2:5;
40162 + UCHAR ExtendChannelSwitch:1;
40163 + UCHAR rsv:1;
40164 + UCHAR BssCoexistMgmtSupport:1;
40165 +#else
40166 + UCHAR BssCoexistMgmtSupport:1;
40167 + UCHAR rsv:1;
40168 + UCHAR ExtendChannelSwitch:1;
40169 + UCHAR rsv2:5;
40170 +#endif // RT_BIG_ENDIAN //
40171 +}EXT_CAP_INFO_ELEMENT, *PEXT_CAP_INFO_ELEMENT;
40172 +
40173 +
40174 +// 802.11n 7.3.2.61
40175 +typedef struct PACKED _BSS_2040_COEXIST_ELEMENT{
40176 + UCHAR ElementID; // ID = IE_2040_BSS_COEXIST = 72
40177 + UCHAR Len;
40178 + BSS_2040_COEXIST_IE BssCoexistIe;
40179 +}BSS_2040_COEXIST_ELEMENT, *PBSS_2040_COEXIST_ELEMENT;
40180 +
40181 +
40182 +//802.11n 7.3.2.59
40183 +typedef struct PACKED _BSS_2040_INTOLERANT_CH_REPORT{
40184 + UCHAR ElementID; // ID = IE_2040_BSS_INTOLERANT_REPORT = 73
40185 + UCHAR Len;
40186 + UCHAR RegulatoryClass;
40187 + UCHAR ChList[0];
40188 +}BSS_2040_INTOLERANT_CH_REPORT, *PBSS_2040_INTOLERANT_CH_REPORT;
40189 +
40190 +
40191 +// The structure for channel switch annoucement IE. This is in 802.11n D3.03
40192 +typedef struct PACKED _CHA_SWITCH_ANNOUNCE_IE{
40193 + UCHAR SwitchMode; //channel switch mode
40194 + UCHAR NewChannel; //
40195 + UCHAR SwitchCount; //
40196 +} CHA_SWITCH_ANNOUNCE_IE, *PCHA_SWITCH_ANNOUNCE_IE;
40197 +
40198 +
40199 +// The structure for channel switch annoucement IE. This is in 802.11n D3.03
40200 +typedef struct PACKED _SEC_CHA_OFFSET_IE{
40201 + UCHAR SecondaryChannelOffset; // 1: Secondary above, 3: Secondary below, 0: no Secondary
40202 +} SEC_CHA_OFFSET_IE, *PSEC_CHA_OFFSET_IE;
40203 +
40204 +
40205 +// This structure is extracted from struct RT_HT_CAPABILITY
40206 +typedef struct {
40207 + BOOLEAN bHtEnable; // If we should use ht rate.
40208 + BOOLEAN bPreNHt; // If we should use ht rate.
40209 + //Substract from HT Capability IE
40210 + UCHAR MCSSet[16]; //only supoort MCS=0-15,32 ,
40211 +} RT_HT_PHY_INFO, *PRT_HT_PHY_INFO;
40212 +
40213 +//This structure substracts ralink supports from all 802.11n-related features.
40214 +//Features not listed here but contained in 802.11n spec are not supported in rt2860.
40215 +typedef struct {
40216 +#ifdef RT_BIG_ENDIAN
40217 + USHORT rsv:5;
40218 + USHORT AmsduSize:1; // Max receiving A-MSDU size
40219 + USHORT AmsduEnable:1; // Enable to transmit A-MSDU. Suggest disable. We should use A-MPDU to gain best benifit of 802.11n
40220 + USHORT RxSTBC:2; // 2 bits
40221 + USHORT TxSTBC:1;
40222 + USHORT ShortGIfor40:1; //for40MHz
40223 + USHORT ShortGIfor20:1;
40224 + USHORT GF:1; //green field
40225 + USHORT MimoPs:2;//mimo power safe MMPS_
40226 + USHORT ChannelWidth:1;
40227 +#else
40228 + USHORT ChannelWidth:1;
40229 + USHORT MimoPs:2;//mimo power safe MMPS_
40230 + USHORT GF:1; //green field
40231 + USHORT ShortGIfor20:1;
40232 + USHORT ShortGIfor40:1; //for40MHz
40233 + USHORT TxSTBC:1;
40234 + USHORT RxSTBC:2; // 2 bits
40235 + USHORT AmsduEnable:1; // Enable to transmit A-MSDU. Suggest disable. We should use A-MPDU to gain best benifit of 802.11n
40236 + USHORT AmsduSize:1; // Max receiving A-MSDU size
40237 + USHORT rsv:5;
40238 +#endif
40239 +
40240 + //Substract from Addiont HT INFO IE
40241 +#ifdef RT_BIG_ENDIAN
40242 + UCHAR RecomWidth:1;
40243 + UCHAR ExtChanOffset:2; // Please not the difference with following UCHAR NewExtChannelOffset; from 802.11n
40244 + UCHAR MpduDensity:3;
40245 + UCHAR MaxRAmpduFactor:2;
40246 +#else
40247 + UCHAR MaxRAmpduFactor:2;
40248 + UCHAR MpduDensity:3;
40249 + UCHAR ExtChanOffset:2; // Please not the difference with following UCHAR NewExtChannelOffset; from 802.11n
40250 + UCHAR RecomWidth:1;
40251 +#endif
40252 +
40253 +#ifdef RT_BIG_ENDIAN
40254 + USHORT rsv2:11;
40255 + USHORT OBSS_NonHTExist:1;
40256 + USHORT rsv3:1;
40257 + USHORT NonGfPresent:1;
40258 + USHORT OperaionMode:2;
40259 +#else
40260 + USHORT OperaionMode:2;
40261 + USHORT NonGfPresent:1;
40262 + USHORT rsv3:1;
40263 + USHORT OBSS_NonHTExist:1;
40264 + USHORT rsv2:11;
40265 +#endif
40266 +
40267 + // New Extension Channel Offset IE
40268 + UCHAR NewExtChannelOffset;
40269 + // Extension Capability IE = 127
40270 + UCHAR BSSCoexist2040;
40271 +} RT_HT_CAPABILITY, *PRT_HT_CAPABILITY;
40272 +
40273 +// field in Addtional HT Information IE .
40274 +typedef struct PACKED {
40275 +#ifdef RT_BIG_ENDIAN
40276 + UCHAR SerInterGranu:3;
40277 + UCHAR S_PSMPSup:1;
40278 + UCHAR RifsMode:1;
40279 + UCHAR RecomWidth:1;
40280 + UCHAR ExtChanOffset:2;
40281 +#else
40282 + UCHAR ExtChanOffset:2;
40283 + UCHAR RecomWidth:1;
40284 + UCHAR RifsMode:1;
40285 + UCHAR S_PSMPSup:1; //Indicate support for scheduled PSMP
40286 + UCHAR SerInterGranu:3; //service interval granularity
40287 +#endif
40288 +} ADD_HTINFO, *PADD_HTINFO;
40289 +
40290 +typedef struct PACKED{
40291 +#ifdef RT_BIG_ENDIAN
40292 + USHORT rsv2:11;
40293 + USHORT OBSS_NonHTExist:1;
40294 + USHORT rsv:1;
40295 + USHORT NonGfPresent:1;
40296 + USHORT OperaionMode:2;
40297 +#else
40298 + USHORT OperaionMode:2;
40299 + USHORT NonGfPresent:1;
40300 + USHORT rsv:1;
40301 + USHORT OBSS_NonHTExist:1;
40302 + USHORT rsv2:11;
40303 +#endif
40304 +} ADD_HTINFO2, *PADD_HTINFO2;
40305 +
40306 +
40307 +// TODO: Need sync with spec about the definition of StbcMcs. In Draft 3.03, it's reserved.
40308 +typedef struct PACKED{
40309 +#ifdef RT_BIG_ENDIAN
40310 + USHORT rsv:4;
40311 + USHORT PcoPhase:1;
40312 + USHORT PcoActive:1;
40313 + USHORT LsigTxopProt:1;
40314 + USHORT STBCBeacon:1;
40315 + USHORT DualCTSProtect:1;
40316 + USHORT DualBeacon:1;
40317 + USHORT StbcMcs:6;
40318 +#else
40319 + USHORT StbcMcs:6;
40320 + USHORT DualBeacon:1;
40321 + USHORT DualCTSProtect:1;
40322 + USHORT STBCBeacon:1;
40323 + USHORT LsigTxopProt:1; // L-SIG TXOP protection full support
40324 + USHORT PcoActive:1;
40325 + USHORT PcoPhase:1;
40326 + USHORT rsv:4;
40327 +#endif // RT_BIG_ENDIAN //
40328 +} ADD_HTINFO3, *PADD_HTINFO3;
40329 +
40330 +#define SIZE_ADD_HT_INFO_IE 22
40331 +typedef struct PACKED{
40332 + UCHAR ControlChan;
40333 + ADD_HTINFO AddHtInfo;
40334 + ADD_HTINFO2 AddHtInfo2;
40335 + ADD_HTINFO3 AddHtInfo3;
40336 + UCHAR MCSSet[16]; // Basic MCS set
40337 +} ADD_HT_INFO_IE, *PADD_HT_INFO_IE;
40338 +
40339 +typedef struct PACKED{
40340 + UCHAR NewExtChanOffset;
40341 +} NEW_EXT_CHAN_IE, *PNEW_EXT_CHAN_IE;
40342 +
40343 +
40344 +// 4-byte HTC field. maybe included in any frame except non-QOS data frame. The Order bit must set 1.
40345 +typedef struct PACKED {
40346 +#ifdef RT_BIG_ENDIAN
40347 + UINT32 RDG:1; //RDG / More PPDU
40348 + UINT32 ACConstraint:1; //feedback request
40349 + UINT32 rsv:5; //calibration sequence
40350 + UINT32 ZLFAnnouce:1; // ZLF announcement
40351 + UINT32 CSISTEERING:2; //CSI/ STEERING
40352 + UINT32 FBKReq:2; //feedback request
40353 + UINT32 CalSeq:2; //calibration sequence
40354 + UINT32 CalPos:2; // calibration position
40355 + UINT32 MFBorASC:7; //Link adaptation feedback containing recommended MCS. 0x7f for no feedback or not available
40356 + UINT32 MFS:3; //SET to the received value of MRS. 0x111 for unsolicited MFB.
40357 + UINT32 MRSorASI:3; // MRQ Sequence identifier. unchanged during entire procedure. 0x000-0x110.
40358 + UINT32 MRQ:1; //MCS feedback. Request for a MCS feedback
40359 + UINT32 TRQ:1; //sounding request
40360 + UINT32 MA:1; //management action payload exist in (QoS Null+HTC)
40361 +#else
40362 + UINT32 MA:1; //management action payload exist in (QoS Null+HTC)
40363 + UINT32 TRQ:1; //sounding request
40364 + UINT32 MRQ:1; //MCS feedback. Request for a MCS feedback
40365 + UINT32 MRSorASI:3; // MRQ Sequence identifier. unchanged during entire procedure. 0x000-0x110.
40366 + UINT32 MFS:3; //SET to the received value of MRS. 0x111 for unsolicited MFB.
40367 + UINT32 MFBorASC:7; //Link adaptation feedback containing recommended MCS. 0x7f for no feedback or not available
40368 + UINT32 CalPos:2; // calibration position
40369 + UINT32 CalSeq:2; //calibration sequence
40370 + UINT32 FBKReq:2; //feedback request
40371 + UINT32 CSISTEERING:2; //CSI/ STEERING
40372 + UINT32 ZLFAnnouce:1; // ZLF announcement
40373 + UINT32 rsv:5; //calibration sequence
40374 + UINT32 ACConstraint:1; //feedback request
40375 + UINT32 RDG:1; //RDG / More PPDU
40376 +#endif /* !RT_BIG_ENDIAN */
40377 +} HT_CONTROL, *PHT_CONTROL;
40378 +
40379 +// 2-byte QOS CONTROL field
40380 +typedef struct PACKED {
40381 +#ifdef RT_BIG_ENDIAN
40382 + USHORT Txop_QueueSize:8;
40383 + USHORT AMsduPresent:1;
40384 + USHORT AckPolicy:2; //0: normal ACK 1:No ACK 2:scheduled under MTBA/PSMP 3: BA
40385 + USHORT EOSP:1;
40386 + USHORT TID:4;
40387 +#else
40388 + USHORT TID:4;
40389 + USHORT EOSP:1;
40390 + USHORT AckPolicy:2; //0: normal ACK 1:No ACK 2:scheduled under MTBA/PSMP 3: BA
40391 + USHORT AMsduPresent:1;
40392 + USHORT Txop_QueueSize:8;
40393 +#endif /* !RT_BIG_ENDIAN */
40394 +} QOS_CONTROL, *PQOS_CONTROL;
40395 +
40396 +// 2-byte Frame control field
40397 +typedef struct PACKED {
40398 +#ifdef RT_BIG_ENDIAN
40399 + USHORT Order:1; // Strict order expected
40400 + USHORT Wep:1; // Wep data
40401 + USHORT MoreData:1; // More data bit
40402 + USHORT PwrMgmt:1; // Power management bit
40403 + USHORT Retry:1; // Retry status bit
40404 + USHORT MoreFrag:1; // More fragment bit
40405 + USHORT FrDs:1; // From DS indication
40406 + USHORT ToDs:1; // To DS indication
40407 + USHORT SubType:4; // MSDU subtype
40408 + USHORT Type:2; // MSDU type
40409 + USHORT Ver:2; // Protocol version
40410 +#else
40411 + USHORT Ver:2; // Protocol version
40412 + USHORT Type:2; // MSDU type
40413 + USHORT SubType:4; // MSDU subtype
40414 + USHORT ToDs:1; // To DS indication
40415 + USHORT FrDs:1; // From DS indication
40416 + USHORT MoreFrag:1; // More fragment bit
40417 + USHORT Retry:1; // Retry status bit
40418 + USHORT PwrMgmt:1; // Power management bit
40419 + USHORT MoreData:1; // More data bit
40420 + USHORT Wep:1; // Wep data
40421 + USHORT Order:1; // Strict order expected
40422 +#endif /* !RT_BIG_ENDIAN */
40423 +} FRAME_CONTROL, *PFRAME_CONTROL;
40424 +
40425 +typedef struct PACKED _HEADER_802_11 {
40426 + FRAME_CONTROL FC;
40427 + USHORT Duration;
40428 + UCHAR Addr1[MAC_ADDR_LEN];
40429 + UCHAR Addr2[MAC_ADDR_LEN];
40430 + UCHAR Addr3[MAC_ADDR_LEN];
40431 +#ifdef RT_BIG_ENDIAN
40432 + USHORT Sequence:12;
40433 + USHORT Frag:4;
40434 +#else
40435 + USHORT Frag:4;
40436 + USHORT Sequence:12;
40437 +#endif /* !RT_BIG_ENDIAN */
40438 + UCHAR Octet[0];
40439 +} HEADER_802_11, *PHEADER_802_11;
40440 +
40441 +typedef struct PACKED _FRAME_802_11 {
40442 + HEADER_802_11 Hdr;
40443 + UCHAR Octet[1];
40444 +} FRAME_802_11, *PFRAME_802_11;
40445 +
40446 +// QoSNull embedding of management action. When HT Control MA field set to 1.
40447 +typedef struct PACKED _MA_BODY {
40448 + UCHAR Category;
40449 + UCHAR Action;
40450 + UCHAR Octet[1];
40451 +} MA_BODY, *PMA_BODY;
40452 +
40453 +typedef struct PACKED _HEADER_802_3 {
40454 + UCHAR DAAddr1[MAC_ADDR_LEN];
40455 + UCHAR SAAddr2[MAC_ADDR_LEN];
40456 + UCHAR Octet[2];
40457 +} HEADER_802_3, *PHEADER_802_3;
40458 +////Block ACK related format
40459 +// 2-byte BA Parameter field in DELBA frames to terminate an already set up bA
40460 +typedef struct PACKED{
40461 +#ifdef RT_BIG_ENDIAN
40462 + USHORT TID:4; // value of TC os TS
40463 + USHORT Initiator:1; // 1: originator 0:recipient
40464 + USHORT Rsv:11; // always set to 0
40465 +#else
40466 + USHORT Rsv:11; // always set to 0
40467 + USHORT Initiator:1; // 1: originator 0:recipient
40468 + USHORT TID:4; // value of TC os TS
40469 +#endif /* !RT_BIG_ENDIAN */
40470 +} DELBA_PARM, *PDELBA_PARM;
40471 +
40472 +// 2-byte BA Parameter Set field in ADDBA frames to signal parm for setting up a BA
40473 +typedef struct PACKED {
40474 +#ifdef RT_BIG_ENDIAN
40475 + USHORT BufSize:10; // number of buffe of size 2304 octetsr
40476 + USHORT TID:4; // value of TC os TS
40477 + USHORT BAPolicy:1; // 1: immediately BA 0:delayed BA
40478 + USHORT AMSDUSupported:1; // 0: not permitted 1: permitted
40479 +#else
40480 + USHORT AMSDUSupported:1; // 0: not permitted 1: permitted
40481 + USHORT BAPolicy:1; // 1: immediately BA 0:delayed BA
40482 + USHORT TID:4; // value of TC os TS
40483 + USHORT BufSize:10; // number of buffe of size 2304 octetsr
40484 +#endif /* !RT_BIG_ENDIAN */
40485 +} BA_PARM, *PBA_PARM;
40486 +
40487 +// 2-byte BA Starting Seq CONTROL field
40488 +typedef union PACKED {
40489 + struct PACKED {
40490 +#ifdef RT_BIG_ENDIAN
40491 + USHORT StartSeq:12; // sequence number of the 1st MSDU for which this BAR is sent
40492 + USHORT FragNum:4; // always set to 0
40493 +#else
40494 + USHORT FragNum:4; // always set to 0
40495 + USHORT StartSeq:12; // sequence number of the 1st MSDU for which this BAR is sent
40496 +#endif /* RT_BIG_ENDIAN */
40497 + } field;
40498 + USHORT word;
40499 +} BASEQ_CONTROL, *PBASEQ_CONTROL;
40500 +
40501 +//BAControl and BARControl are the same
40502 +// 2-byte BA CONTROL field in BA frame
40503 +typedef struct PACKED {
40504 +#ifdef RT_BIG_ENDIAN
40505 + USHORT TID:4;
40506 + USHORT Rsv:9;
40507 + USHORT Compressed:1;
40508 + USHORT MTID:1; //EWC V1.24
40509 + USHORT ACKPolicy:1; // only related to N-Delayed BA. But not support in RT2860b. 0:NormalACK 1:No ACK
40510 +#else
40511 + USHORT ACKPolicy:1; // only related to N-Delayed BA. But not support in RT2860b. 0:NormalACK 1:No ACK
40512 + USHORT MTID:1; //EWC V1.24
40513 + USHORT Compressed:1;
40514 + USHORT Rsv:9;
40515 + USHORT TID:4;
40516 +#endif /* !RT_BIG_ENDIAN */
40517 +} BA_CONTROL, *PBA_CONTROL;
40518 +
40519 +// 2-byte BAR CONTROL field in BAR frame
40520 +typedef struct PACKED {
40521 +#ifdef RT_BIG_ENDIAN
40522 + USHORT TID:4;
40523 + USHORT Rsv1:9;
40524 + USHORT Compressed:1;
40525 + USHORT MTID:1; //if this bit1, use FRAME_MTBA_REQ, if 0, use FRAME_BA_REQ
40526 + USHORT ACKPolicy:1;
40527 +#else
40528 + USHORT ACKPolicy:1; // 0:normal ack, 1:no ack.
40529 + USHORT MTID:1; //if this bit1, use FRAME_MTBA_REQ, if 0, use FRAME_BA_REQ
40530 + USHORT Compressed:1;
40531 + USHORT Rsv1:9;
40532 + USHORT TID:4;
40533 +#endif /* !RT_BIG_ENDIAN */
40534 +} BAR_CONTROL, *PBAR_CONTROL;
40535 +
40536 +// BARControl in MTBAR frame
40537 +typedef struct PACKED {
40538 +#ifdef RT_BIG_ENDIAN
40539 + USHORT NumTID:4;
40540 + USHORT Rsv1:9;
40541 + USHORT Compressed:1;
40542 + USHORT MTID:1;
40543 + USHORT ACKPolicy:1;
40544 +#else
40545 + USHORT ACKPolicy:1;
40546 + USHORT MTID:1;
40547 + USHORT Compressed:1;
40548 + USHORT Rsv1:9;
40549 + USHORT NumTID:4;
40550 +#endif /* !RT_BIG_ENDIAN */
40551 +} MTBAR_CONTROL, *PMTBAR_CONTROL;
40552 +
40553 +typedef struct PACKED {
40554 +#ifdef RT_BIG_ENDIAN
40555 + USHORT TID:4;
40556 + USHORT Rsv1:12;
40557 +#else
40558 + USHORT Rsv1:12;
40559 + USHORT TID:4;
40560 +#endif /* !RT_BIG_ENDIAN */
40561 +} PER_TID_INFO, *PPER_TID_INFO;
40562 +
40563 +typedef struct {
40564 + PER_TID_INFO PerTID;
40565 + BASEQ_CONTROL BAStartingSeq;
40566 +} EACH_TID, *PEACH_TID;
40567 +
40568 +
40569 +typedef struct PACKED _PSPOLL_FRAME {
40570 + FRAME_CONTROL FC;
40571 + USHORT Aid;
40572 + UCHAR Bssid[MAC_ADDR_LEN];
40573 + UCHAR Ta[MAC_ADDR_LEN];
40574 +} PSPOLL_FRAME, *PPSPOLL_FRAME;
40575 +
40576 +typedef struct PACKED _RTS_FRAME {
40577 + FRAME_CONTROL FC;
40578 + USHORT Duration;
40579 + UCHAR Addr1[MAC_ADDR_LEN];
40580 + UCHAR Addr2[MAC_ADDR_LEN];
40581 +}RTS_FRAME, *PRTS_FRAME;
40582 +
40583 +// BAREQ AND MTBAREQ have the same subtype BAR, 802.11n BAR use compressed bitmap.
40584 +typedef struct PACKED _FRAME_BA_REQ {
40585 + FRAME_CONTROL FC;
40586 + USHORT Duration;
40587 + UCHAR Addr1[MAC_ADDR_LEN];
40588 + UCHAR Addr2[MAC_ADDR_LEN];
40589 + BAR_CONTROL BARControl;
40590 + BASEQ_CONTROL BAStartingSeq;
40591 +} FRAME_BA_REQ, *PFRAME_BA_REQ;
40592 +
40593 +typedef struct PACKED _FRAME_MTBA_REQ {
40594 + FRAME_CONTROL FC;
40595 + USHORT Duration;
40596 + UCHAR Addr1[MAC_ADDR_LEN];
40597 + UCHAR Addr2[MAC_ADDR_LEN];
40598 + MTBAR_CONTROL MTBARControl;
40599 + PER_TID_INFO PerTIDInfo;
40600 + BASEQ_CONTROL BAStartingSeq;
40601 +} FRAME_MTBA_REQ, *PFRAME_MTBA_REQ;
40602 +
40603 +// Compressed format is mandantory in HT STA
40604 +typedef struct PACKED _FRAME_MTBA {
40605 + FRAME_CONTROL FC;
40606 + USHORT Duration;
40607 + UCHAR Addr1[MAC_ADDR_LEN];
40608 + UCHAR Addr2[MAC_ADDR_LEN];
40609 + BA_CONTROL BAControl;
40610 + BASEQ_CONTROL BAStartingSeq;
40611 + UCHAR BitMap[8];
40612 +} FRAME_MTBA, *PFRAME_MTBA;
40613 +
40614 +typedef struct PACKED _FRAME_PSMP_ACTION {
40615 + HEADER_802_11 Hdr;
40616 + UCHAR Category;
40617 + UCHAR Action;
40618 + UCHAR Psmp; // 7.3.1.25
40619 +} FRAME_PSMP_ACTION, *PFRAME_PSMP_ACTION;
40620 +
40621 +typedef struct PACKED _FRAME_ACTION_HDR {
40622 + HEADER_802_11 Hdr;
40623 + UCHAR Category;
40624 + UCHAR Action;
40625 +} FRAME_ACTION_HDR, *PFRAME_ACTION_HDR;
40626 +
40627 +//Action Frame
40628 +//Action Frame Category:Spectrum, Action:Channel Switch. 7.3.2.20
40629 +typedef struct PACKED _CHAN_SWITCH_ANNOUNCE {
40630 + UCHAR ElementID; // ID = IE_CHANNEL_SWITCH_ANNOUNCEMENT = 37
40631 + UCHAR Len;
40632 + CHA_SWITCH_ANNOUNCE_IE CSAnnounceIe;
40633 +} CHAN_SWITCH_ANNOUNCE, *PCHAN_SWITCH_ANNOUNCE;
40634 +
40635 +
40636 +//802.11n : 7.3.2.20a
40637 +typedef struct PACKED _SECOND_CHAN_OFFSET {
40638 + UCHAR ElementID; // ID = IE_SECONDARY_CH_OFFSET = 62
40639 + UCHAR Len;
40640 + SEC_CHA_OFFSET_IE SecChOffsetIe;
40641 +} SECOND_CHAN_OFFSET, *PSECOND_CHAN_OFFSET;
40642 +
40643 +
40644 +typedef struct PACKED _FRAME_SPETRUM_CS {
40645 + HEADER_802_11 Hdr;
40646 + UCHAR Category;
40647 + UCHAR Action;
40648 + CHAN_SWITCH_ANNOUNCE CSAnnounce;
40649 + SECOND_CHAN_OFFSET SecondChannel;
40650 +} FRAME_SPETRUM_CS, *PFRAME_SPETRUM_CS;
40651 +
40652 +
40653 +typedef struct PACKED _FRAME_ADDBA_REQ {
40654 + HEADER_802_11 Hdr;
40655 + UCHAR Category;
40656 + UCHAR Action;
40657 + UCHAR Token; // 1
40658 + BA_PARM BaParm; // 2 - 10
40659 + USHORT TimeOutValue; // 0 - 0
40660 + BASEQ_CONTROL BaStartSeq; // 0-0
40661 +} FRAME_ADDBA_REQ, *PFRAME_ADDBA_REQ;
40662 +
40663 +typedef struct PACKED _FRAME_ADDBA_RSP {
40664 + HEADER_802_11 Hdr;
40665 + UCHAR Category;
40666 + UCHAR Action;
40667 + UCHAR Token;
40668 + USHORT StatusCode;
40669 + BA_PARM BaParm; //0 - 2
40670 + USHORT TimeOutValue;
40671 +} FRAME_ADDBA_RSP, *PFRAME_ADDBA_RSP;
40672 +
40673 +typedef struct PACKED _FRAME_DELBA_REQ {
40674 + HEADER_802_11 Hdr;
40675 + UCHAR Category;
40676 + UCHAR Action;
40677 + DELBA_PARM DelbaParm;
40678 + USHORT ReasonCode;
40679 +} FRAME_DELBA_REQ, *PFRAME_DELBA_REQ;
40680 +
40681 +
40682 +//7.2.1.7
40683 +typedef struct PACKED _FRAME_BAR {
40684 + FRAME_CONTROL FC;
40685 + USHORT Duration;
40686 + UCHAR Addr1[MAC_ADDR_LEN];
40687 + UCHAR Addr2[MAC_ADDR_LEN];
40688 + BAR_CONTROL BarControl;
40689 + BASEQ_CONTROL StartingSeq;
40690 +} FRAME_BAR, *PFRAME_BAR;
40691 +
40692 +//7.2.1.7
40693 +typedef struct PACKED _FRAME_BA {
40694 + FRAME_CONTROL FC;
40695 + USHORT Duration;
40696 + UCHAR Addr1[MAC_ADDR_LEN];
40697 + UCHAR Addr2[MAC_ADDR_LEN];
40698 + BAR_CONTROL BarControl;
40699 + BASEQ_CONTROL StartingSeq;
40700 + UCHAR bitmask[8];
40701 +} FRAME_BA, *PFRAME_BA;
40702 +
40703 +
40704 +// Radio Measuement Request Frame Format
40705 +typedef struct PACKED _FRAME_RM_REQ_ACTION {
40706 + HEADER_802_11 Hdr;
40707 + UCHAR Category;
40708 + UCHAR Action;
40709 + UCHAR Token;
40710 + USHORT Repetition;
40711 + UCHAR data[0];
40712 +} FRAME_RM_REQ_ACTION, *PFRAME_RM_REQ_ACTION;
40713 +
40714 +typedef struct PACKED {
40715 + UCHAR ID;
40716 + UCHAR Length;
40717 + UCHAR ChannelSwitchMode;
40718 + UCHAR NewRegClass;
40719 + UCHAR NewChannelNum;
40720 + UCHAR ChannelSwitchCount;
40721 +} HT_EXT_CHANNEL_SWITCH_ANNOUNCEMENT_IE, *PHT_EXT_CHANNEL_SWITCH_ANNOUNCEMENT_IE;
40722 +
40723 +
40724 +//
40725 +// _Limit must be the 2**n - 1
40726 +// _SEQ1 , _SEQ2 must be within 0 ~ _Limit
40727 +//
40728 +#define SEQ_STEPONE(_SEQ1, _SEQ2, _Limit) ((_SEQ1 == ((_SEQ2+1) & _Limit)))
40729 +#define SEQ_SMALLER(_SEQ1, _SEQ2, _Limit) (((_SEQ1-_SEQ2) & ((_Limit+1)>>1)))
40730 +#define SEQ_LARGER(_SEQ1, _SEQ2, _Limit) ((_SEQ1 != _SEQ2) && !(((_SEQ1-_SEQ2) & ((_Limit+1)>>1))))
40731 +#define SEQ_WITHIN_WIN(_SEQ1, _SEQ2, _WIN, _Limit) (SEQ_LARGER(_SEQ1, _SEQ2, _Limit) && \
40732 + SEQ_SMALLER(_SEQ1, ((_SEQ2+_WIN+1)&_Limit), _Limit))
40733 +
40734 +//
40735 +// Contention-free parameter (without ID and Length)
40736 +//
40737 +typedef struct PACKED {
40738 + BOOLEAN bValid; // 1: variable contains valid value
40739 + UCHAR CfpCount;
40740 + UCHAR CfpPeriod;
40741 + USHORT CfpMaxDuration;
40742 + USHORT CfpDurRemaining;
40743 +} CF_PARM, *PCF_PARM;
40744 +
40745 +typedef struct _CIPHER_SUITE {
40746 + NDIS_802_11_ENCRYPTION_STATUS PairCipher; // Unicast cipher 1, this one has more secured cipher suite
40747 + NDIS_802_11_ENCRYPTION_STATUS PairCipherAux; // Unicast cipher 2 if AP announce two unicast cipher suite
40748 + NDIS_802_11_ENCRYPTION_STATUS GroupCipher; // Group cipher
40749 + USHORT RsnCapability; // RSN capability from beacon
40750 + BOOLEAN bMixMode; // Indicate Pair & Group cipher might be different
40751 +} CIPHER_SUITE, *PCIPHER_SUITE;
40752 +
40753 +// EDCA configuration from AP's BEACON/ProbeRsp
40754 +typedef struct {
40755 + BOOLEAN bValid; // 1: variable contains valid value
40756 + BOOLEAN bAdd; // 1: variable contains valid value
40757 + BOOLEAN bQAck;
40758 + BOOLEAN bQueueRequest;
40759 + BOOLEAN bTxopRequest;
40760 + BOOLEAN bAPSDCapable;
40761 +// BOOLEAN bMoreDataAck;
40762 + UCHAR EdcaUpdateCount;
40763 + UCHAR Aifsn[4]; // 0:AC_BK, 1:AC_BE, 2:AC_VI, 3:AC_VO
40764 + UCHAR Cwmin[4];
40765 + UCHAR Cwmax[4];
40766 + USHORT Txop[4]; // in unit of 32-us
40767 + BOOLEAN bACM[4]; // 1: Admission Control of AC_BK is mandattory
40768 +} EDCA_PARM, *PEDCA_PARM;
40769 +
40770 +// QBSS LOAD information from QAP's BEACON/ProbeRsp
40771 +typedef struct {
40772 + BOOLEAN bValid; // 1: variable contains valid value
40773 + USHORT StaNum;
40774 + UCHAR ChannelUtilization;
40775 + USHORT RemainingAdmissionControl; // in unit of 32-us
40776 +} QBSS_LOAD_PARM, *PQBSS_LOAD_PARM;
40777 +
40778 +// QBSS Info field in QSTA's assoc req
40779 +typedef struct PACKED {
40780 +#ifdef RT_BIG_ENDIAN
40781 + UCHAR Rsv2:1;
40782 + UCHAR MaxSPLength:2;
40783 + UCHAR Rsv1:1;
40784 + UCHAR UAPSD_AC_BE:1;
40785 + UCHAR UAPSD_AC_BK:1;
40786 + UCHAR UAPSD_AC_VI:1;
40787 + UCHAR UAPSD_AC_VO:1;
40788 +#else
40789 + UCHAR UAPSD_AC_VO:1;
40790 + UCHAR UAPSD_AC_VI:1;
40791 + UCHAR UAPSD_AC_BK:1;
40792 + UCHAR UAPSD_AC_BE:1;
40793 + UCHAR Rsv1:1;
40794 + UCHAR MaxSPLength:2;
40795 + UCHAR Rsv2:1;
40796 +#endif /* !RT_BIG_ENDIAN */
40797 +} QBSS_STA_INFO_PARM, *PQBSS_STA_INFO_PARM;
40798 +
40799 +// QBSS Info field in QAP's Beacon/ProbeRsp
40800 +typedef struct PACKED {
40801 +#ifdef RT_BIG_ENDIAN
40802 + UCHAR UAPSD:1;
40803 + UCHAR Rsv:3;
40804 + UCHAR ParamSetCount:4;
40805 +#else
40806 + UCHAR ParamSetCount:4;
40807 + UCHAR Rsv:3;
40808 + UCHAR UAPSD:1;
40809 +#endif /* !RT_BIG_ENDIAN */
40810 +} QBSS_AP_INFO_PARM, *PQBSS_AP_INFO_PARM;
40811 +
40812 +// QOS Capability reported in QAP's BEACON/ProbeRsp
40813 +// QOS Capability sent out in QSTA's AssociateReq/ReAssociateReq
40814 +typedef struct {
40815 + BOOLEAN bValid; // 1: variable contains valid value
40816 + BOOLEAN bQAck;
40817 + BOOLEAN bQueueRequest;
40818 + BOOLEAN bTxopRequest;
40819 +// BOOLEAN bMoreDataAck;
40820 + UCHAR EdcaUpdateCount;
40821 +} QOS_CAPABILITY_PARM, *PQOS_CAPABILITY_PARM;
40822 +
40823 +#ifdef CONFIG_STA_SUPPORT
40824 +typedef struct {
40825 + UCHAR IELen;
40826 + UCHAR IE[MAX_CUSTOM_LEN];
40827 +} WPA_IE_;
40828 +#endif // CONFIG_STA_SUPPORT //
40829 +
40830 +
40831 +typedef struct {
40832 + UCHAR Bssid[MAC_ADDR_LEN];
40833 + UCHAR Channel;
40834 + UCHAR CentralChannel; //Store the wide-band central channel for 40MHz. .used in 40MHz AP. Or this is the same as Channel.
40835 + UCHAR BssType;
40836 + USHORT AtimWin;
40837 + USHORT BeaconPeriod;
40838 +
40839 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES];
40840 + UCHAR SupRateLen;
40841 + UCHAR ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
40842 + UCHAR ExtRateLen;
40843 + HT_CAPABILITY_IE HtCapability;
40844 + UCHAR HtCapabilityLen;
40845 + ADD_HT_INFO_IE AddHtInfo; // AP might use this additional ht info IE
40846 + UCHAR AddHtInfoLen;
40847 + UCHAR NewExtChanOffset;
40848 + CHAR Rssi;
40849 + UCHAR Privacy; // Indicate security function ON/OFF. Don't mess up with auth mode.
40850 + UCHAR Hidden;
40851 +
40852 + USHORT DtimPeriod;
40853 + USHORT CapabilityInfo;
40854 +
40855 + USHORT CfpCount;
40856 + USHORT CfpPeriod;
40857 + USHORT CfpMaxDuration;
40858 + USHORT CfpDurRemaining;
40859 + UCHAR SsidLen;
40860 + CHAR Ssid[MAX_LEN_OF_SSID];
40861 +
40862 + ULONG LastBeaconRxTime; // OS's timestamp
40863 +
40864 + BOOLEAN bSES;
40865 +
40866 + // New for WPA2
40867 + CIPHER_SUITE WPA; // AP announced WPA cipher suite
40868 + CIPHER_SUITE WPA2; // AP announced WPA2 cipher suite
40869 +
40870 + // New for microsoft WPA support
40871 + NDIS_802_11_FIXED_IEs FixIEs;
40872 + NDIS_802_11_AUTHENTICATION_MODE AuthModeAux; // Addition mode for WPA2 / WPA capable AP
40873 + NDIS_802_11_AUTHENTICATION_MODE AuthMode;
40874 + NDIS_802_11_WEP_STATUS WepStatus; // Unicast Encryption Algorithm extract from VAR_IE
40875 + USHORT VarIELen; // Length of next VIE include EID & Length
40876 + UCHAR VarIEs[MAX_VIE_LEN];
40877 +
40878 + // CCX Ckip information
40879 + UCHAR CkipFlag;
40880 +
40881 + // CCX 2 TSF
40882 + UCHAR PTSF[4]; // Parent TSF
40883 + UCHAR TTSF[8]; // Target TSF
40884 +
40885 + // 802.11e d9, and WMM
40886 + EDCA_PARM EdcaParm;
40887 + QOS_CAPABILITY_PARM QosCapability;
40888 + QBSS_LOAD_PARM QbssLoad;
40889 +#ifdef CONFIG_STA_SUPPORT
40890 + WPA_IE_ WpaIE;
40891 + WPA_IE_ RsnIE;
40892 +#ifdef EXT_BUILD_CHANNEL_LIST
40893 + UCHAR CountryString[3];
40894 + BOOLEAN bHasCountryIE;
40895 +#endif // EXT_BUILD_CHANNEL_LIST //
40896 +#endif // CONFIG_STA_SUPPORT //
40897 +} BSS_ENTRY, *PBSS_ENTRY;
40898 +
40899 +typedef struct {
40900 + UCHAR BssNr;
40901 + UCHAR BssOverlapNr;
40902 + BSS_ENTRY BssEntry[MAX_LEN_OF_BSS_TABLE];
40903 +} BSS_TABLE, *PBSS_TABLE;
40904 +
40905 +
40906 +typedef struct _MLME_QUEUE_ELEM {
40907 + ULONG Machine;
40908 + ULONG MsgType;
40909 + ULONG MsgLen;
40910 + UCHAR Msg[MGMT_DMA_BUFFER_SIZE];
40911 + LARGE_INTEGER TimeStamp;
40912 + UCHAR Rssi0;
40913 + UCHAR Rssi1;
40914 + UCHAR Rssi2;
40915 + UCHAR Signal;
40916 + UCHAR Channel;
40917 + UCHAR Wcid;
40918 + BOOLEAN Occupied;
40919 +} MLME_QUEUE_ELEM, *PMLME_QUEUE_ELEM;
40920 +
40921 +typedef struct _MLME_QUEUE {
40922 + ULONG Num;
40923 + ULONG Head;
40924 + ULONG Tail;
40925 + NDIS_SPIN_LOCK Lock;
40926 + MLME_QUEUE_ELEM Entry[MAX_LEN_OF_MLME_QUEUE];
40927 +} MLME_QUEUE, *PMLME_QUEUE;
40928 +
40929 +typedef VOID (*STATE_MACHINE_FUNC)(VOID *Adaptor, MLME_QUEUE_ELEM *Elem);
40930 +
40931 +typedef struct _STATE_MACHINE {
40932 + ULONG Base;
40933 + ULONG NrState;
40934 + ULONG NrMsg;
40935 + ULONG CurrState;
40936 + STATE_MACHINE_FUNC *TransFunc;
40937 +} STATE_MACHINE, *PSTATE_MACHINE;
40938 +
40939 +
40940 +// MLME AUX data structure that hold temporarliy settings during a connection attempt.
40941 +// Once this attemp succeeds, all settings will be copy to pAd->StaActive.
40942 +// A connection attempt (user set OID, roaming, CCX fast roaming,..) consists of
40943 +// several steps (JOIN, AUTH, ASSOC or REASSOC) and may fail at any step. We purposely
40944 +// separate this under-trial settings away from pAd->StaActive so that once
40945 +// this new attempt failed, driver can auto-recover back to the active settings.
40946 +typedef struct _MLME_AUX {
40947 + UCHAR BssType;
40948 + UCHAR Ssid[MAX_LEN_OF_SSID];
40949 + UCHAR SsidLen;
40950 + UCHAR Bssid[MAC_ADDR_LEN];
40951 + UCHAR AutoReconnectSsid[MAX_LEN_OF_SSID];
40952 + UCHAR AutoReconnectSsidLen;
40953 + USHORT Alg;
40954 + UCHAR ScanType;
40955 + UCHAR Channel;
40956 + UCHAR CentralChannel;
40957 + USHORT Aid;
40958 + USHORT CapabilityInfo;
40959 + USHORT BeaconPeriod;
40960 + USHORT CfpMaxDuration;
40961 + USHORT CfpPeriod;
40962 + USHORT AtimWin;
40963 +
40964 + // Copy supported rate from desired AP's beacon. We are trying to match
40965 + // AP's supported and extended rate settings.
40966 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES];
40967 + UCHAR ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
40968 + UCHAR SupRateLen;
40969 + UCHAR ExtRateLen;
40970 + HT_CAPABILITY_IE HtCapability;
40971 + UCHAR HtCapabilityLen;
40972 + ADD_HT_INFO_IE AddHtInfo; // AP might use this additional ht info IE
40973 + UCHAR NewExtChannelOffset;
40974 + //RT_HT_CAPABILITY SupportedHtPhy;
40975 +
40976 + // new for QOS
40977 + QOS_CAPABILITY_PARM APQosCapability; // QOS capability of the current associated AP
40978 + EDCA_PARM APEdcaParm; // EDCA parameters of the current associated AP
40979 + QBSS_LOAD_PARM APQbssLoad; // QBSS load of the current associated AP
40980 +
40981 + // new to keep Ralink specific feature
40982 + ULONG APRalinkIe;
40983 +
40984 + BSS_TABLE SsidBssTab; // AP list for the same SSID
40985 + BSS_TABLE RoamTab; // AP list eligible for roaming
40986 + ULONG BssIdx;
40987 + ULONG RoamIdx;
40988 +
40989 + BOOLEAN CurrReqIsFromNdis;
40990 +
40991 + RALINK_TIMER_STRUCT BeaconTimer, ScanTimer;
40992 + RALINK_TIMER_STRUCT AuthTimer;
40993 + RALINK_TIMER_STRUCT AssocTimer, ReassocTimer, DisassocTimer;
40994 +} MLME_AUX, *PMLME_AUX;
40995 +
40996 +typedef struct _MLME_ADDBA_REQ_STRUCT{
40997 + UCHAR Wcid; //
40998 + UCHAR pAddr[MAC_ADDR_LEN];
40999 + UCHAR BaBufSize;
41000 + USHORT TimeOutValue;
41001 + UCHAR TID;
41002 + UCHAR Token;
41003 + USHORT BaStartSeq;
41004 +} MLME_ADDBA_REQ_STRUCT, *PMLME_ADDBA_REQ_STRUCT;
41005 +
41006 +
41007 +typedef struct _MLME_DELBA_REQ_STRUCT{
41008 + UCHAR Wcid; //
41009 + UCHAR Addr[MAC_ADDR_LEN];
41010 + UCHAR TID;
41011 + UCHAR Initiator;
41012 +} MLME_DELBA_REQ_STRUCT, *PMLME_DELBA_REQ_STRUCT;
41013 +
41014 +// assoc struct is equal to reassoc
41015 +typedef struct _MLME_ASSOC_REQ_STRUCT{
41016 + UCHAR Addr[MAC_ADDR_LEN];
41017 + USHORT CapabilityInfo;
41018 + USHORT ListenIntv;
41019 + ULONG Timeout;
41020 +} MLME_ASSOC_REQ_STRUCT, *PMLME_ASSOC_REQ_STRUCT, MLME_REASSOC_REQ_STRUCT, *PMLME_REASSOC_REQ_STRUCT;
41021 +
41022 +typedef struct _MLME_DISASSOC_REQ_STRUCT{
41023 + UCHAR Addr[MAC_ADDR_LEN];
41024 + USHORT Reason;
41025 +} MLME_DISASSOC_REQ_STRUCT, *PMLME_DISASSOC_REQ_STRUCT;
41026 +
41027 +typedef struct _MLME_AUTH_REQ_STRUCT {
41028 + UCHAR Addr[MAC_ADDR_LEN];
41029 + USHORT Alg;
41030 + ULONG Timeout;
41031 +} MLME_AUTH_REQ_STRUCT, *PMLME_AUTH_REQ_STRUCT;
41032 +
41033 +typedef struct _MLME_DEAUTH_REQ_STRUCT {
41034 + UCHAR Addr[MAC_ADDR_LEN];
41035 + USHORT Reason;
41036 +} MLME_DEAUTH_REQ_STRUCT, *PMLME_DEAUTH_REQ_STRUCT;
41037 +
41038 +typedef struct {
41039 + ULONG BssIdx;
41040 +} MLME_JOIN_REQ_STRUCT;
41041 +
41042 +typedef struct _MLME_SCAN_REQ_STRUCT {
41043 + UCHAR Bssid[MAC_ADDR_LEN];
41044 + UCHAR BssType;
41045 + UCHAR ScanType;
41046 + UCHAR SsidLen;
41047 + CHAR Ssid[MAX_LEN_OF_SSID];
41048 +} MLME_SCAN_REQ_STRUCT, *PMLME_SCAN_REQ_STRUCT;
41049 +
41050 +typedef struct _MLME_START_REQ_STRUCT {
41051 + CHAR Ssid[MAX_LEN_OF_SSID];
41052 + UCHAR SsidLen;
41053 +} MLME_START_REQ_STRUCT, *PMLME_START_REQ_STRUCT;
41054 +
41055 +#ifdef CONFIG_STA_SUPPORT
41056 +#ifdef QOS_DLS_SUPPORT
41057 +// structure for DLS
41058 +typedef struct _RT_802_11_DLS {
41059 + USHORT TimeOut; // Use to time out while slience, unit: second , set by UI
41060 + USHORT CountDownTimer; // Use to time out while slience,unit: second , used by driver only
41061 + NDIS_802_11_MAC_ADDRESS MacAddr; // set by UI
41062 + UCHAR Status; // 0: none , 1: wait STAkey, 2: finish DLS setup , set by driver only
41063 + BOOLEAN Valid; // 1: valid , 0: invalid , set by UI, use to setup or tear down DLS link
41064 + RALINK_TIMER_STRUCT Timer; // Use to time out while handshake
41065 + USHORT Sequence;
41066 + USHORT MacTabMatchWCID; // ASIC
41067 + BOOLEAN bHTCap;
41068 + PVOID pAd;
41069 +} RT_802_11_DLS, *PRT_802_11_DLS;
41070 +
41071 +typedef struct _MLME_DLS_REQ_STRUCT {
41072 + PRT_802_11_DLS pDLS;
41073 + USHORT Reason;
41074 +} MLME_DLS_REQ_STRUCT, *PMLME_DLS_REQ_STRUCT;
41075 +#endif // QOS_DLS_SUPPORT //
41076 +#endif // CONFIG_STA_SUPPORT //
41077 +
41078 +typedef struct PACKED {
41079 + UCHAR Eid;
41080 + UCHAR Len;
41081 + CHAR Octet[1];
41082 +} EID_STRUCT,*PEID_STRUCT, BEACON_EID_STRUCT, *PBEACON_EID_STRUCT;
41083 +
41084 +typedef struct PACKED _RTMP_TX_RATE_SWITCH
41085 +{
41086 + UCHAR ItemNo;
41087 +#ifdef RT_BIG_ENDIAN
41088 + UCHAR Rsv2:2;
41089 + UCHAR Mode:2;
41090 + UCHAR Rsv1:1;
41091 + UCHAR BW:1;
41092 + UCHAR ShortGI:1;
41093 + UCHAR STBC:1;
41094 +#else
41095 + UCHAR STBC:1;
41096 + UCHAR ShortGI:1;
41097 + UCHAR BW:1;
41098 + UCHAR Rsv1:1;
41099 + UCHAR Mode:2;
41100 + UCHAR Rsv2:2;
41101 +#endif
41102 + UCHAR CurrMCS;
41103 + UCHAR TrainUp;
41104 + UCHAR TrainDown;
41105 +} RRTMP_TX_RATE_SWITCH, *PRTMP_TX_RATE_SWITCH;
41106 +
41107 +// ========================== AP mlme.h ===============================
41108 +#define TBTT_PRELOAD_TIME 384 // usec. LomgPreamble + 24-byte at 1Mbps
41109 +#define DEFAULT_DTIM_PERIOD 1
41110 +
41111 +#define MAC_TABLE_AGEOUT_TIME 300 // unit: sec
41112 +#define MAC_TABLE_ASSOC_TIMEOUT 5 // unit: sec
41113 +#define MAC_TABLE_FULL(Tab) ((Tab).size == MAX_LEN_OF_MAC_TABLE)
41114 +
41115 +// AP shall drop the sta if contine Tx fail count reach it.
41116 +#define MAC_ENTRY_LIFE_CHECK_CNT 20 // packet cnt.
41117 +
41118 +// Value domain of pMacEntry->Sst
41119 +typedef enum _Sst {
41120 + SST_NOT_AUTH, // 0: equivalent to IEEE 802.11/1999 state 1
41121 + SST_AUTH, // 1: equivalent to IEEE 802.11/1999 state 2
41122 + SST_ASSOC // 2: equivalent to IEEE 802.11/1999 state 3
41123 +} SST;
41124 +
41125 +// value domain of pMacEntry->AuthState
41126 +typedef enum _AuthState {
41127 + AS_NOT_AUTH,
41128 + AS_AUTH_OPEN, // STA has been authenticated using OPEN SYSTEM
41129 + AS_AUTH_KEY, // STA has been authenticated using SHARED KEY
41130 + AS_AUTHENTICATING // STA is waiting for AUTH seq#3 using SHARED KEY
41131 +} AUTH_STATE;
41132 +
41133 +//for-wpa value domain of pMacEntry->WpaState 802.1i D3 p.114
41134 +typedef enum _ApWpaState {
41135 + AS_NOTUSE, // 0
41136 + AS_DISCONNECT, // 1
41137 + AS_DISCONNECTED, // 2
41138 + AS_INITIALIZE, // 3
41139 + AS_AUTHENTICATION, // 4
41140 + AS_AUTHENTICATION2, // 5
41141 + AS_INITPMK, // 6
41142 + AS_INITPSK, // 7
41143 + AS_PTKSTART, // 8
41144 + AS_PTKINIT_NEGOTIATING, // 9
41145 + AS_PTKINITDONE, // 10
41146 + AS_UPDATEKEYS, // 11
41147 + AS_INTEGRITY_FAILURE, // 12
41148 + AS_KEYUPDATE, // 13
41149 +} AP_WPA_STATE;
41150 +
41151 +// for-wpa value domain of pMacEntry->WpaState 802.1i D3 p.114
41152 +typedef enum _GTKState {
41153 + REKEY_NEGOTIATING,
41154 + REKEY_ESTABLISHED,
41155 + KEYERROR,
41156 +} GTK_STATE;
41157 +
41158 +// for-wpa value domain of pMacEntry->WpaState 802.1i D3 p.114
41159 +typedef enum _WpaGTKState {
41160 + SETKEYS,
41161 + SETKEYS_DONE,
41162 +} WPA_GTK_STATE;
41163 +// ====================== end of AP mlme.h ============================
41164 +
41165 +
41166 +#endif // MLME_H__
41167 --- /dev/null
41168 +++ b/drivers/staging/rt2860/oid.h
41169 @@ -0,0 +1,995 @@
41170 +/*
41171 + *************************************************************************
41172 + * Ralink Tech Inc.
41173 + * 5F., No.36, Taiyuan St., Jhubei City,
41174 + * Hsinchu County 302,
41175 + * Taiwan, R.O.C.
41176 + *
41177 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
41178 + *
41179 + * This program is free software; you can redistribute it and/or modify *
41180 + * it under the terms of the GNU General Public License as published by *
41181 + * the Free Software Foundation; either version 2 of the License, or *
41182 + * (at your option) any later version. *
41183 + * *
41184 + * This program is distributed in the hope that it will be useful, *
41185 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
41186 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
41187 + * GNU General Public License for more details. *
41188 + * *
41189 + * You should have received a copy of the GNU General Public License *
41190 + * along with this program; if not, write to the *
41191 + * Free Software Foundation, Inc., *
41192 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
41193 + * *
41194 + *************************************************************************
41195 +
41196 + Module Name:
41197 + oid.h
41198 +
41199 + Abstract:
41200 +
41201 + Revision History:
41202 + Who When What
41203 + -------- ---------- ----------------------------------------------
41204 + Name Date Modification logs
41205 +*/
41206 +#ifndef _OID_H_
41207 +#define _OID_H_
41208 +
41209 +
41210 +#define TRUE 1
41211 +#define FALSE 0
41212 +//
41213 +// IEEE 802.11 Structures and definitions
41214 +//
41215 +#define MAX_TX_POWER_LEVEL 100 /* mW */
41216 +#define MAX_RSSI_TRIGGER -10 /* dBm */
41217 +#define MIN_RSSI_TRIGGER -200 /* dBm */
41218 +#define MAX_FRAG_THRESHOLD 2346 /* byte count */
41219 +#define MIN_FRAG_THRESHOLD 256 /* byte count */
41220 +#define MAX_RTS_THRESHOLD 2347 /* byte count */
41221 +
41222 +// new types for Media Specific Indications
41223 +// Extension channel offset
41224 +#define EXTCHA_NONE 0
41225 +#define EXTCHA_ABOVE 0x1
41226 +#define EXTCHA_BELOW 0x3
41227 +
41228 +// BW
41229 +#define BAND_WIDTH_20 0
41230 +#define BAND_WIDTH_40 1
41231 +#define BAND_WIDTH_BOTH 2
41232 +#define BAND_WIDTH_10 3 // 802.11j has 10MHz. This definition is for internal usage. doesn't fill in the IE or other field.
41233 +// SHORTGI
41234 +#define GAP_INTERVAL_400 1 // only support in HT mode
41235 +#define GAP_INTERVAL_800 0
41236 +#define GAP_INTERVAL_BOTH 2
41237 +
41238 +#define NdisMediaStateConnected 1
41239 +#define NdisMediaStateDisconnected 0
41240 +
41241 +#define NDIS_802_11_LENGTH_SSID 32
41242 +#define NDIS_802_11_LENGTH_RATES 8
41243 +#define NDIS_802_11_LENGTH_RATES_EX 16
41244 +#define MAC_ADDR_LENGTH 6
41245 +#define MAX_NUM_OF_CHS 49 // 14 channels @2.4G + 12@UNII + 4 @MMAC + 11 @HiperLAN2 + 7 @Japan + 1 as NULL terminationc
41246 +#define MAX_NUMBER_OF_EVENT 10 // entry # in EVENT table
41247 +#define MAX_NUMBER_OF_MAC 32 // if MAX_MBSSID_NUM is 8, this value can't be larger than 211
41248 +#define MAX_NUMBER_OF_ACL 64
41249 +#define MAX_LENGTH_OF_SUPPORT_RATES 12 // 1, 2, 5.5, 11, 6, 9, 12, 18, 24, 36, 48, 54
41250 +#define MAX_NUMBER_OF_DLS_ENTRY 4
41251 +
41252 +#ifndef UNDER_CE
41253 +
41254 +#define OID_GEN_MACHINE_NAME 0x0001021A
41255 +
41256 +#ifdef RALINK_ATE
41257 +#define RT_QUERY_ATE_TXDONE_COUNT 0x0401
41258 +#endif // RALINK_ATE //
41259 +#define RT_QUERY_SIGNAL_CONTEXT 0x0402
41260 +#define RT_SET_IAPP_PID 0x0404
41261 +#define RT_SET_APD_PID 0x0405
41262 +#define RT_SET_DEL_MAC_ENTRY 0x0406
41263 +
41264 +//
41265 +// IEEE 802.11 OIDs
41266 +//
41267 +#define OID_GET_SET_TOGGLE 0x8000
41268 +
41269 +#define OID_802_11_NETWORK_TYPES_SUPPORTED 0x0103
41270 +#define OID_802_11_NETWORK_TYPE_IN_USE 0x0104
41271 +#define OID_802_11_RSSI_TRIGGER 0x0107
41272 +#define RT_OID_802_11_RSSI 0x0108 //rt2860 only , kathy
41273 +#define RT_OID_802_11_RSSI_1 0x0109 //rt2860 only , kathy
41274 +#define RT_OID_802_11_RSSI_2 0x010A //rt2860 only , kathy
41275 +#define OID_802_11_NUMBER_OF_ANTENNAS 0x010B
41276 +#define OID_802_11_RX_ANTENNA_SELECTED 0x010C
41277 +#define OID_802_11_TX_ANTENNA_SELECTED 0x010D
41278 +#define OID_802_11_SUPPORTED_RATES 0x010E
41279 +#define OID_802_11_ADD_WEP 0x0112
41280 +#define OID_802_11_REMOVE_WEP 0x0113
41281 +#define OID_802_11_DISASSOCIATE 0x0114
41282 +#define OID_802_11_PRIVACY_FILTER 0x0118
41283 +#define OID_802_11_ASSOCIATION_INFORMATION 0x011E
41284 +#define OID_802_11_TEST 0x011F
41285 +#define RT_OID_802_11_COUNTRY_REGION 0x0507
41286 +#define OID_802_11_BSSID_LIST_SCAN 0x0508
41287 +#define OID_802_11_SSID 0x0509
41288 +#define OID_802_11_BSSID 0x050A
41289 +#define RT_OID_802_11_RADIO 0x050B
41290 +#define RT_OID_802_11_PHY_MODE 0x050C
41291 +#define RT_OID_802_11_STA_CONFIG 0x050D
41292 +#define OID_802_11_DESIRED_RATES 0x050E
41293 +#define RT_OID_802_11_PREAMBLE 0x050F
41294 +#define OID_802_11_WEP_STATUS 0x0510
41295 +#define OID_802_11_AUTHENTICATION_MODE 0x0511
41296 +#define OID_802_11_INFRASTRUCTURE_MODE 0x0512
41297 +#define RT_OID_802_11_RESET_COUNTERS 0x0513
41298 +#define OID_802_11_RTS_THRESHOLD 0x0514
41299 +#define OID_802_11_FRAGMENTATION_THRESHOLD 0x0515
41300 +#define OID_802_11_POWER_MODE 0x0516
41301 +#define OID_802_11_TX_POWER_LEVEL 0x0517
41302 +#define RT_OID_802_11_ADD_WPA 0x0518
41303 +#define OID_802_11_REMOVE_KEY 0x0519
41304 +#define OID_802_11_ADD_KEY 0x0520
41305 +#define OID_802_11_CONFIGURATION 0x0521
41306 +#define OID_802_11_TX_PACKET_BURST 0x0522
41307 +#define RT_OID_802_11_QUERY_NOISE_LEVEL 0x0523
41308 +#define RT_OID_802_11_EXTRA_INFO 0x0524
41309 +#ifdef DBG
41310 +#define RT_OID_802_11_HARDWARE_REGISTER 0x0525
41311 +#endif
41312 +#define OID_802_11_ENCRYPTION_STATUS OID_802_11_WEP_STATUS
41313 +#define OID_802_11_DEAUTHENTICATION 0x0526
41314 +#define OID_802_11_DROP_UNENCRYPTED 0x0527
41315 +#define OID_802_11_MIC_FAILURE_REPORT_FRAME 0x0528
41316 +
41317 +// For 802.1x daemin using to require current driver configuration
41318 +#define OID_802_11_RADIUS_QUERY_SETTING 0x0540
41319 +
41320 +#define RT_OID_DEVICE_NAME 0x0607
41321 +#define RT_OID_VERSION_INFO 0x0608
41322 +#define OID_802_11_BSSID_LIST 0x0609
41323 +#define OID_802_3_CURRENT_ADDRESS 0x060A
41324 +#define OID_GEN_MEDIA_CONNECT_STATUS 0x060B
41325 +#define RT_OID_802_11_QUERY_LINK_STATUS 0x060C
41326 +#define OID_802_11_RSSI 0x060D
41327 +#define OID_802_11_STATISTICS 0x060E
41328 +#define OID_GEN_RCV_OK 0x060F
41329 +#define OID_GEN_RCV_NO_BUFFER 0x0610
41330 +#define RT_OID_802_11_QUERY_EEPROM_VERSION 0x0611
41331 +#define RT_OID_802_11_QUERY_FIRMWARE_VERSION 0x0612
41332 +#define RT_OID_802_11_QUERY_LAST_RX_RATE 0x0613
41333 +#define RT_OID_802_11_TX_POWER_LEVEL_1 0x0614
41334 +#define RT_OID_802_11_QUERY_PIDVID 0x0615
41335 +//for WPA_SUPPLICANT_SUPPORT
41336 +#define OID_SET_COUNTERMEASURES 0x0616
41337 +#define OID_802_11_SET_IEEE8021X 0x0617
41338 +#define OID_802_11_SET_IEEE8021X_REQUIRE_KEY 0x0618
41339 +#define OID_802_11_PMKID 0x0620
41340 +#define RT_OID_WPA_SUPPLICANT_SUPPORT 0x0621
41341 +#define RT_OID_WE_VERSION_COMPILED 0x0622
41342 +#define RT_OID_NEW_DRIVER 0x0623
41343 +
41344 +
41345 +//rt2860 , kathy
41346 +#define RT_OID_802_11_SNR_0 0x0630
41347 +#define RT_OID_802_11_SNR_1 0x0631
41348 +#define RT_OID_802_11_QUERY_LAST_TX_RATE 0x0632
41349 +#define RT_OID_802_11_QUERY_HT_PHYMODE 0x0633
41350 +#define RT_OID_802_11_SET_HT_PHYMODE 0x0634
41351 +#define OID_802_11_RELOAD_DEFAULTS 0x0635
41352 +#define RT_OID_802_11_QUERY_APSD_SETTING 0x0636
41353 +#define RT_OID_802_11_SET_APSD_SETTING 0x0637
41354 +#define RT_OID_802_11_QUERY_APSD_PSM 0x0638
41355 +#define RT_OID_802_11_SET_APSD_PSM 0x0639
41356 +#define RT_OID_802_11_QUERY_DLS 0x063A
41357 +#define RT_OID_802_11_SET_DLS 0x063B
41358 +#define RT_OID_802_11_QUERY_DLS_PARAM 0x063C
41359 +#define RT_OID_802_11_SET_DLS_PARAM 0x063D
41360 +#define RT_OID_802_11_QUERY_WMM 0x063E
41361 +#define RT_OID_802_11_SET_WMM 0x063F
41362 +#define RT_OID_802_11_QUERY_IMME_BA_CAP 0x0640
41363 +#define RT_OID_802_11_SET_IMME_BA_CAP 0x0641
41364 +#define RT_OID_802_11_QUERY_BATABLE 0x0642
41365 +#define RT_OID_802_11_ADD_IMME_BA 0x0643
41366 +#define RT_OID_802_11_TEAR_IMME_BA 0x0644
41367 +#define RT_OID_DRIVER_DEVICE_NAME 0x0645
41368 +#define RT_OID_802_11_QUERY_DAT_HT_PHYMODE 0x0646
41369 +#define RT_OID_QUERY_MULTIPLE_CARD_SUPPORT 0x0647
41370 +
41371 +// Ralink defined OIDs
41372 +// Dennis Lee move to platform specific
41373 +
41374 +#define RT_OID_802_11_BSSID (OID_GET_SET_TOGGLE | OID_802_11_BSSID)
41375 +#define RT_OID_802_11_SSID (OID_GET_SET_TOGGLE | OID_802_11_SSID)
41376 +#define RT_OID_802_11_INFRASTRUCTURE_MODE (OID_GET_SET_TOGGLE | OID_802_11_INFRASTRUCTURE_MODE)
41377 +#define RT_OID_802_11_ADD_WEP (OID_GET_SET_TOGGLE | OID_802_11_ADD_WEP)
41378 +#define RT_OID_802_11_ADD_KEY (OID_GET_SET_TOGGLE | OID_802_11_ADD_KEY)
41379 +#define RT_OID_802_11_REMOVE_WEP (OID_GET_SET_TOGGLE | OID_802_11_REMOVE_WEP)
41380 +#define RT_OID_802_11_REMOVE_KEY (OID_GET_SET_TOGGLE | OID_802_11_REMOVE_KEY)
41381 +#define RT_OID_802_11_DISASSOCIATE (OID_GET_SET_TOGGLE | OID_802_11_DISASSOCIATE)
41382 +#define RT_OID_802_11_AUTHENTICATION_MODE (OID_GET_SET_TOGGLE | OID_802_11_AUTHENTICATION_MODE)
41383 +#define RT_OID_802_11_PRIVACY_FILTER (OID_GET_SET_TOGGLE | OID_802_11_PRIVACY_FILTER)
41384 +#define RT_OID_802_11_BSSID_LIST_SCAN (OID_GET_SET_TOGGLE | OID_802_11_BSSID_LIST_SCAN)
41385 +#define RT_OID_802_11_WEP_STATUS (OID_GET_SET_TOGGLE | OID_802_11_WEP_STATUS)
41386 +#define RT_OID_802_11_RELOAD_DEFAULTS (OID_GET_SET_TOGGLE | OID_802_11_RELOAD_DEFAULTS)
41387 +#define RT_OID_802_11_NETWORK_TYPE_IN_USE (OID_GET_SET_TOGGLE | OID_802_11_NETWORK_TYPE_IN_USE)
41388 +#define RT_OID_802_11_TX_POWER_LEVEL (OID_GET_SET_TOGGLE | OID_802_11_TX_POWER_LEVEL)
41389 +#define RT_OID_802_11_RSSI_TRIGGER (OID_GET_SET_TOGGLE | OID_802_11_RSSI_TRIGGER)
41390 +#define RT_OID_802_11_FRAGMENTATION_THRESHOLD (OID_GET_SET_TOGGLE | OID_802_11_FRAGMENTATION_THRESHOLD)
41391 +#define RT_OID_802_11_RTS_THRESHOLD (OID_GET_SET_TOGGLE | OID_802_11_RTS_THRESHOLD)
41392 +#define RT_OID_802_11_RX_ANTENNA_SELECTED (OID_GET_SET_TOGGLE | OID_802_11_RX_ANTENNA_SELECTED)
41393 +#define RT_OID_802_11_TX_ANTENNA_SELECTED (OID_GET_SET_TOGGLE | OID_802_11_TX_ANTENNA_SELECTED)
41394 +#define RT_OID_802_11_SUPPORTED_RATES (OID_GET_SET_TOGGLE | OID_802_11_SUPPORTED_RATES)
41395 +#define RT_OID_802_11_DESIRED_RATES (OID_GET_SET_TOGGLE | OID_802_11_DESIRED_RATES)
41396 +#define RT_OID_802_11_CONFIGURATION (OID_GET_SET_TOGGLE | OID_802_11_CONFIGURATION)
41397 +#define RT_OID_802_11_POWER_MODE (OID_GET_SET_TOGGLE | OID_802_11_POWER_MODE)
41398 +
41399 +typedef enum _NDIS_802_11_STATUS_TYPE
41400 +{
41401 + Ndis802_11StatusType_Authentication,
41402 + Ndis802_11StatusType_MediaStreamMode,
41403 + Ndis802_11StatusType_PMKID_CandidateList,
41404 + Ndis802_11StatusTypeMax // not a real type, defined as an upper bound
41405 +} NDIS_802_11_STATUS_TYPE, *PNDIS_802_11_STATUS_TYPE;
41406 +
41407 +typedef UCHAR NDIS_802_11_MAC_ADDRESS[6];
41408 +
41409 +typedef struct _NDIS_802_11_STATUS_INDICATION
41410 +{
41411 + NDIS_802_11_STATUS_TYPE StatusType;
41412 +} NDIS_802_11_STATUS_INDICATION, *PNDIS_802_11_STATUS_INDICATION;
41413 +
41414 +// mask for authentication/integrity fields
41415 +#define NDIS_802_11_AUTH_REQUEST_AUTH_FIELDS 0x0f
41416 +
41417 +#define NDIS_802_11_AUTH_REQUEST_REAUTH 0x01
41418 +#define NDIS_802_11_AUTH_REQUEST_KEYUPDATE 0x02
41419 +#define NDIS_802_11_AUTH_REQUEST_PAIRWISE_ERROR 0x06
41420 +#define NDIS_802_11_AUTH_REQUEST_GROUP_ERROR 0x0E
41421 +
41422 +typedef struct _NDIS_802_11_AUTHENTICATION_REQUEST
41423 +{
41424 + ULONG Length; // Length of structure
41425 + NDIS_802_11_MAC_ADDRESS Bssid;
41426 + ULONG Flags;
41427 +} NDIS_802_11_AUTHENTICATION_REQUEST, *PNDIS_802_11_AUTHENTICATION_REQUEST;
41428 +
41429 +//Added new types for PMKID Candidate lists.
41430 +typedef struct _PMKID_CANDIDATE {
41431 + NDIS_802_11_MAC_ADDRESS BSSID;
41432 + ULONG Flags;
41433 +} PMKID_CANDIDATE, *PPMKID_CANDIDATE;
41434 +
41435 +typedef struct _NDIS_802_11_PMKID_CANDIDATE_LIST
41436 +{
41437 + ULONG Version; // Version of the structure
41438 + ULONG NumCandidates; // No. of pmkid candidates
41439 + PMKID_CANDIDATE CandidateList[1];
41440 +} NDIS_802_11_PMKID_CANDIDATE_LIST, *PNDIS_802_11_PMKID_CANDIDATE_LIST;
41441 +
41442 +//Flags for PMKID Candidate list structure
41443 +#define NDIS_802_11_PMKID_CANDIDATE_PREAUTH_ENABLED 0x01
41444 +
41445 +// Added new types for OFDM 5G and 2.4G
41446 +typedef enum _NDIS_802_11_NETWORK_TYPE
41447 +{
41448 + Ndis802_11FH,
41449 + Ndis802_11DS,
41450 + Ndis802_11OFDM5,
41451 + Ndis802_11OFDM5_N,
41452 + Ndis802_11OFDM24,
41453 + Ndis802_11OFDM24_N,
41454 + Ndis802_11Automode,
41455 + Ndis802_11NetworkTypeMax // not a real type, defined as an upper bound
41456 +} NDIS_802_11_NETWORK_TYPE, *PNDIS_802_11_NETWORK_TYPE;
41457 +
41458 +typedef struct _NDIS_802_11_NETWORK_TYPE_LIST
41459 +{
41460 + UINT NumberOfItems; // in list below, at least 1
41461 + NDIS_802_11_NETWORK_TYPE NetworkType [1];
41462 +} NDIS_802_11_NETWORK_TYPE_LIST, *PNDIS_802_11_NETWORK_TYPE_LIST;
41463 +
41464 +typedef enum _NDIS_802_11_POWER_MODE
41465 +{
41466 + Ndis802_11PowerModeCAM,
41467 + Ndis802_11PowerModeMAX_PSP,
41468 + Ndis802_11PowerModeFast_PSP,
41469 + Ndis802_11PowerModeLegacy_PSP,
41470 + Ndis802_11PowerModeMax // not a real mode, defined as an upper bound
41471 +} NDIS_802_11_POWER_MODE, *PNDIS_802_11_POWER_MODE;
41472 +
41473 +typedef ULONG NDIS_802_11_TX_POWER_LEVEL; // in milliwatts
41474 +
41475 +//
41476 +// Received Signal Strength Indication
41477 +//
41478 +typedef LONG NDIS_802_11_RSSI; // in dBm
41479 +
41480 +typedef struct _NDIS_802_11_CONFIGURATION_FH
41481 +{
41482 + ULONG Length; // Length of structure
41483 + ULONG HopPattern; // As defined by 802.11, MSB set
41484 + ULONG HopSet; // to one if non-802.11
41485 + ULONG DwellTime; // units are Kusec
41486 +} NDIS_802_11_CONFIGURATION_FH, *PNDIS_802_11_CONFIGURATION_FH;
41487 +
41488 +typedef struct _NDIS_802_11_CONFIGURATION
41489 +{
41490 + ULONG Length; // Length of structure
41491 + ULONG BeaconPeriod; // units are Kusec
41492 + ULONG ATIMWindow; // units are Kusec
41493 + ULONG DSConfig; // Frequency, units are kHz
41494 + NDIS_802_11_CONFIGURATION_FH FHConfig;
41495 +} NDIS_802_11_CONFIGURATION, *PNDIS_802_11_CONFIGURATION;
41496 +
41497 +typedef struct _NDIS_802_11_STATISTICS
41498 +{
41499 + ULONG Length; // Length of structure
41500 + LARGE_INTEGER TransmittedFragmentCount;
41501 + LARGE_INTEGER MulticastTransmittedFrameCount;
41502 + LARGE_INTEGER FailedCount;
41503 + LARGE_INTEGER RetryCount;
41504 + LARGE_INTEGER MultipleRetryCount;
41505 + LARGE_INTEGER RTSSuccessCount;
41506 + LARGE_INTEGER RTSFailureCount;
41507 + LARGE_INTEGER ACKFailureCount;
41508 + LARGE_INTEGER FrameDuplicateCount;
41509 + LARGE_INTEGER ReceivedFragmentCount;
41510 + LARGE_INTEGER MulticastReceivedFrameCount;
41511 + LARGE_INTEGER FCSErrorCount;
41512 + LARGE_INTEGER TKIPLocalMICFailures;
41513 + LARGE_INTEGER TKIPRemoteMICErrors;
41514 + LARGE_INTEGER TKIPICVErrors;
41515 + LARGE_INTEGER TKIPCounterMeasuresInvoked;
41516 + LARGE_INTEGER TKIPReplays;
41517 + LARGE_INTEGER CCMPFormatErrors;
41518 + LARGE_INTEGER CCMPReplays;
41519 + LARGE_INTEGER CCMPDecryptErrors;
41520 + LARGE_INTEGER FourWayHandshakeFailures;
41521 +} NDIS_802_11_STATISTICS, *PNDIS_802_11_STATISTICS;
41522 +
41523 +typedef ULONG NDIS_802_11_KEY_INDEX;
41524 +typedef ULONGLONG NDIS_802_11_KEY_RSC;
41525 +
41526 +#define MAX_RADIUS_SRV_NUM 2 // 802.1x failover number
41527 +
41528 +typedef struct PACKED _RADIUS_SRV_INFO {
41529 + UINT32 radius_ip;
41530 + UINT32 radius_port;
41531 + UCHAR radius_key[64];
41532 + UCHAR radius_key_len;
41533 +} RADIUS_SRV_INFO, *PRADIUS_SRV_INFO;
41534 +
41535 +typedef struct PACKED _RADIUS_KEY_INFO
41536 +{
41537 + UCHAR radius_srv_num;
41538 + RADIUS_SRV_INFO radius_srv_info[MAX_RADIUS_SRV_NUM];
41539 + UCHAR ieee8021xWEP; // dynamic WEP
41540 + UCHAR key_index;
41541 + UCHAR key_length; // length of key in bytes
41542 + UCHAR key_material[13];
41543 +} RADIUS_KEY_INFO, *PRADIUS_KEY_INFO;
41544 +
41545 +// It's used by 802.1x daemon to require relative configuration
41546 +typedef struct PACKED _RADIUS_CONF
41547 +{
41548 + UINT32 Length; // Length of this structure
41549 + UCHAR mbss_num; // indicate multiple BSS number
41550 + UINT32 own_ip_addr;
41551 + UINT32 retry_interval;
41552 + UINT32 session_timeout_interval;
41553 + UCHAR EAPifname[IFNAMSIZ];
41554 + UCHAR EAPifname_len;
41555 + UCHAR PreAuthifname[IFNAMSIZ];
41556 + UCHAR PreAuthifname_len;
41557 + RADIUS_KEY_INFO RadiusInfo[8/*MAX_MBSSID_NUM*/];
41558 +} RADIUS_CONF, *PRADIUS_CONF;
41559 +
41560 +
41561 +
41562 +#ifdef CONFIG_STA_SUPPORT
41563 +// Key mapping keys require a BSSID
41564 +typedef struct _NDIS_802_11_KEY
41565 +{
41566 + UINT Length; // Length of this structure
41567 + UINT KeyIndex;
41568 + UINT KeyLength; // length of key in bytes
41569 + NDIS_802_11_MAC_ADDRESS BSSID;
41570 + NDIS_802_11_KEY_RSC KeyRSC;
41571 + UCHAR KeyMaterial[1]; // variable length depending on above field
41572 +} NDIS_802_11_KEY, *PNDIS_802_11_KEY;
41573 +#endif // CONFIG_STA_SUPPORT //
41574 +
41575 +typedef struct _NDIS_802_11_REMOVE_KEY
41576 +{
41577 + UINT Length; // Length of this structure
41578 + UINT KeyIndex;
41579 + NDIS_802_11_MAC_ADDRESS BSSID;
41580 +} NDIS_802_11_REMOVE_KEY, *PNDIS_802_11_REMOVE_KEY;
41581 +
41582 +typedef struct _NDIS_802_11_WEP
41583 +{
41584 + UINT Length; // Length of this structure
41585 + UINT KeyIndex; // 0 is the per-client key, 1-N are the
41586 + // global keys
41587 + UINT KeyLength; // length of key in bytes
41588 + UCHAR KeyMaterial[1];// variable length depending on above field
41589 +} NDIS_802_11_WEP, *PNDIS_802_11_WEP;
41590 +
41591 +
41592 +typedef enum _NDIS_802_11_NETWORK_INFRASTRUCTURE
41593 +{
41594 + Ndis802_11IBSS,
41595 + Ndis802_11Infrastructure,
41596 + Ndis802_11AutoUnknown,
41597 + Ndis802_11Monitor,
41598 + Ndis802_11InfrastructureMax // Not a real value, defined as upper bound
41599 +} NDIS_802_11_NETWORK_INFRASTRUCTURE, *PNDIS_802_11_NETWORK_INFRASTRUCTURE;
41600 +
41601 +// Add new authentication modes
41602 +typedef enum _NDIS_802_11_AUTHENTICATION_MODE
41603 +{
41604 + Ndis802_11AuthModeOpen,
41605 + Ndis802_11AuthModeShared,
41606 + Ndis802_11AuthModeAutoSwitch,
41607 + Ndis802_11AuthModeWPA,
41608 + Ndis802_11AuthModeWPAPSK,
41609 + Ndis802_11AuthModeWPANone,
41610 + Ndis802_11AuthModeWPA2,
41611 + Ndis802_11AuthModeWPA2PSK,
41612 + Ndis802_11AuthModeWPA1WPA2,
41613 + Ndis802_11AuthModeWPA1PSKWPA2PSK,
41614 + Ndis802_11AuthModeMax // Not a real mode, defined as upper bound
41615 +} NDIS_802_11_AUTHENTICATION_MODE, *PNDIS_802_11_AUTHENTICATION_MODE;
41616 +
41617 +typedef UCHAR NDIS_802_11_RATES[NDIS_802_11_LENGTH_RATES]; // Set of 8 data rates
41618 +typedef UCHAR NDIS_802_11_RATES_EX[NDIS_802_11_LENGTH_RATES_EX]; // Set of 16 data rates
41619 +
41620 +typedef struct PACKED _NDIS_802_11_SSID
41621 +{
41622 + UINT SsidLength; // length of SSID field below, in bytes;
41623 + // this can be zero.
41624 + UCHAR Ssid[NDIS_802_11_LENGTH_SSID]; // SSID information field
41625 +} NDIS_802_11_SSID, *PNDIS_802_11_SSID;
41626 +
41627 +
41628 +typedef struct PACKED _NDIS_WLAN_BSSID
41629 +{
41630 + ULONG Length; // Length of this structure
41631 + NDIS_802_11_MAC_ADDRESS MacAddress; // BSSID
41632 + UCHAR Reserved[2];
41633 + NDIS_802_11_SSID Ssid; // SSID
41634 + ULONG Privacy; // WEP encryption requirement
41635 + NDIS_802_11_RSSI Rssi; // receive signal strength in dBm
41636 + NDIS_802_11_NETWORK_TYPE NetworkTypeInUse;
41637 + NDIS_802_11_CONFIGURATION Configuration;
41638 + NDIS_802_11_NETWORK_INFRASTRUCTURE InfrastructureMode;
41639 + NDIS_802_11_RATES SupportedRates;
41640 +} NDIS_WLAN_BSSID, *PNDIS_WLAN_BSSID;
41641 +
41642 +typedef struct PACKED _NDIS_802_11_BSSID_LIST
41643 +{
41644 + UINT NumberOfItems; // in list below, at least 1
41645 + NDIS_WLAN_BSSID Bssid[1];
41646 +} NDIS_802_11_BSSID_LIST, *PNDIS_802_11_BSSID_LIST;
41647 +
41648 +// Added Capabilities, IELength and IEs for each BSSID
41649 +typedef struct PACKED _NDIS_WLAN_BSSID_EX
41650 +{
41651 + ULONG Length; // Length of this structure
41652 + NDIS_802_11_MAC_ADDRESS MacAddress; // BSSID
41653 + UCHAR Reserved[2];
41654 + NDIS_802_11_SSID Ssid; // SSID
41655 + UINT Privacy; // WEP encryption requirement
41656 + NDIS_802_11_RSSI Rssi; // receive signal
41657 + // strength in dBm
41658 + NDIS_802_11_NETWORK_TYPE NetworkTypeInUse;
41659 + NDIS_802_11_CONFIGURATION Configuration;
41660 + NDIS_802_11_NETWORK_INFRASTRUCTURE InfrastructureMode;
41661 + NDIS_802_11_RATES_EX SupportedRates;
41662 + ULONG IELength;
41663 + UCHAR IEs[1];
41664 +} NDIS_WLAN_BSSID_EX, *PNDIS_WLAN_BSSID_EX;
41665 +
41666 +typedef struct PACKED _NDIS_802_11_BSSID_LIST_EX
41667 +{
41668 + UINT NumberOfItems; // in list below, at least 1
41669 + NDIS_WLAN_BSSID_EX Bssid[1];
41670 +} NDIS_802_11_BSSID_LIST_EX, *PNDIS_802_11_BSSID_LIST_EX;
41671 +
41672 +typedef struct PACKED _NDIS_802_11_FIXED_IEs
41673 +{
41674 + UCHAR Timestamp[8];
41675 + USHORT BeaconInterval;
41676 + USHORT Capabilities;
41677 +} NDIS_802_11_FIXED_IEs, *PNDIS_802_11_FIXED_IEs;
41678 +
41679 +typedef struct _NDIS_802_11_VARIABLE_IEs
41680 +{
41681 + UCHAR ElementID;
41682 + UCHAR Length; // Number of bytes in data field
41683 + UCHAR data[1];
41684 +} NDIS_802_11_VARIABLE_IEs, *PNDIS_802_11_VARIABLE_IEs;
41685 +
41686 +typedef ULONG NDIS_802_11_FRAGMENTATION_THRESHOLD;
41687 +
41688 +typedef ULONG NDIS_802_11_RTS_THRESHOLD;
41689 +
41690 +typedef ULONG NDIS_802_11_ANTENNA;
41691 +
41692 +typedef enum _NDIS_802_11_PRIVACY_FILTER
41693 +{
41694 + Ndis802_11PrivFilterAcceptAll,
41695 + Ndis802_11PrivFilter8021xWEP
41696 +} NDIS_802_11_PRIVACY_FILTER, *PNDIS_802_11_PRIVACY_FILTER;
41697 +
41698 +// Added new encryption types
41699 +// Also aliased typedef to new name
41700 +typedef enum _NDIS_802_11_WEP_STATUS
41701 +{
41702 + Ndis802_11WEPEnabled,
41703 + Ndis802_11Encryption1Enabled = Ndis802_11WEPEnabled,
41704 + Ndis802_11WEPDisabled,
41705 + Ndis802_11EncryptionDisabled = Ndis802_11WEPDisabled,
41706 + Ndis802_11WEPKeyAbsent,
41707 + Ndis802_11Encryption1KeyAbsent = Ndis802_11WEPKeyAbsent,
41708 + Ndis802_11WEPNotSupported,
41709 + Ndis802_11EncryptionNotSupported = Ndis802_11WEPNotSupported,
41710 + Ndis802_11Encryption2Enabled,
41711 + Ndis802_11Encryption2KeyAbsent,
41712 + Ndis802_11Encryption3Enabled,
41713 + Ndis802_11Encryption3KeyAbsent,
41714 + Ndis802_11Encryption4Enabled, // TKIP or AES mix
41715 + Ndis802_11Encryption4KeyAbsent,
41716 +} NDIS_802_11_WEP_STATUS, *PNDIS_802_11_WEP_STATUS,
41717 + NDIS_802_11_ENCRYPTION_STATUS, *PNDIS_802_11_ENCRYPTION_STATUS;
41718 +
41719 +typedef enum _NDIS_802_11_RELOAD_DEFAULTS
41720 +{
41721 + Ndis802_11ReloadWEPKeys
41722 +} NDIS_802_11_RELOAD_DEFAULTS, *PNDIS_802_11_RELOAD_DEFAULTS;
41723 +
41724 +#define NDIS_802_11_AI_REQFI_CAPABILITIES 1
41725 +#define NDIS_802_11_AI_REQFI_LISTENINTERVAL 2
41726 +#define NDIS_802_11_AI_REQFI_CURRENTAPADDRESS 4
41727 +
41728 +#define NDIS_802_11_AI_RESFI_CAPABILITIES 1
41729 +#define NDIS_802_11_AI_RESFI_STATUSCODE 2
41730 +#define NDIS_802_11_AI_RESFI_ASSOCIATIONID 4
41731 +
41732 +typedef struct _NDIS_802_11_AI_REQFI
41733 +{
41734 + USHORT Capabilities;
41735 + USHORT ListenInterval;
41736 + NDIS_802_11_MAC_ADDRESS CurrentAPAddress;
41737 +} NDIS_802_11_AI_REQFI, *PNDIS_802_11_AI_REQFI;
41738 +
41739 +typedef struct _NDIS_802_11_AI_RESFI
41740 +{
41741 + USHORT Capabilities;
41742 + USHORT StatusCode;
41743 + USHORT AssociationId;
41744 +} NDIS_802_11_AI_RESFI, *PNDIS_802_11_AI_RESFI;
41745 +
41746 +typedef struct _NDIS_802_11_ASSOCIATION_INFORMATION
41747 +{
41748 + ULONG Length;
41749 + USHORT AvailableRequestFixedIEs;
41750 + NDIS_802_11_AI_REQFI RequestFixedIEs;
41751 + ULONG RequestIELength;
41752 + ULONG OffsetRequestIEs;
41753 + USHORT AvailableResponseFixedIEs;
41754 + NDIS_802_11_AI_RESFI ResponseFixedIEs;
41755 + ULONG ResponseIELength;
41756 + ULONG OffsetResponseIEs;
41757 +} NDIS_802_11_ASSOCIATION_INFORMATION, *PNDIS_802_11_ASSOCIATION_INFORMATION;
41758 +
41759 +typedef struct _NDIS_802_11_AUTHENTICATION_EVENT
41760 +{
41761 + NDIS_802_11_STATUS_INDICATION Status;
41762 + NDIS_802_11_AUTHENTICATION_REQUEST Request[1];
41763 +} NDIS_802_11_AUTHENTICATION_EVENT, *PNDIS_802_11_AUTHENTICATION_EVENT;
41764 +
41765 +// 802.11 Media stream constraints, associated with OID_802_11_MEDIA_STREAM_MODE
41766 +typedef enum _NDIS_802_11_MEDIA_STREAM_MODE
41767 +{
41768 + Ndis802_11MediaStreamOff,
41769 + Ndis802_11MediaStreamOn,
41770 +} NDIS_802_11_MEDIA_STREAM_MODE, *PNDIS_802_11_MEDIA_STREAM_MODE;
41771 +
41772 +// PMKID Structures
41773 +typedef UCHAR NDIS_802_11_PMKID_VALUE[16];
41774 +
41775 +#ifdef CONFIG_STA_SUPPORT
41776 +typedef struct _BSSID_INFO
41777 +{
41778 + NDIS_802_11_MAC_ADDRESS BSSID;
41779 + NDIS_802_11_PMKID_VALUE PMKID;
41780 +} BSSID_INFO, *PBSSID_INFO;
41781 +
41782 +typedef struct _NDIS_802_11_PMKID
41783 +{
41784 + UINT Length;
41785 + UINT BSSIDInfoCount;
41786 + BSSID_INFO BSSIDInfo[1];
41787 +} NDIS_802_11_PMKID, *PNDIS_802_11_PMKID;
41788 +#endif // CONFIG_STA_SUPPORT //
41789 +
41790 +
41791 +typedef struct _NDIS_802_11_AUTHENTICATION_ENCRYPTION
41792 +{
41793 + NDIS_802_11_AUTHENTICATION_MODE AuthModeSupported;
41794 + NDIS_802_11_ENCRYPTION_STATUS EncryptStatusSupported;
41795 +} NDIS_802_11_AUTHENTICATION_ENCRYPTION, *PNDIS_802_11_AUTHENTICATION_ENCRYPTION;
41796 +
41797 +typedef struct _NDIS_802_11_CAPABILITY
41798 +{
41799 + ULONG Length;
41800 + ULONG Version;
41801 + ULONG NoOfPMKIDs;
41802 + ULONG NoOfAuthEncryptPairsSupported;
41803 + NDIS_802_11_AUTHENTICATION_ENCRYPTION AuthenticationEncryptionSupported[1];
41804 +} NDIS_802_11_CAPABILITY, *PNDIS_802_11_CAPABILITY;
41805 +
41806 +//#endif //of WIN 2k
41807 +#endif //UNDER_CE
41808 +
41809 +#if WIRELESS_EXT <= 11
41810 +#ifndef SIOCDEVPRIVATE
41811 +#define SIOCDEVPRIVATE 0x8BE0
41812 +#endif
41813 +#define SIOCIWFIRSTPRIV SIOCDEVPRIVATE
41814 +#endif
41815 +
41816 +#ifdef CONFIG_STA_SUPPORT
41817 +#define RTPRIV_IOCTL_SET (SIOCIWFIRSTPRIV + 0x02)
41818 +
41819 +#ifdef DBG
41820 +#define RTPRIV_IOCTL_BBP (SIOCIWFIRSTPRIV + 0x03)
41821 +#define RTPRIV_IOCTL_MAC (SIOCIWFIRSTPRIV + 0x05)
41822 +#define RTPRIV_IOCTL_E2P (SIOCIWFIRSTPRIV + 0x07)
41823 +#endif
41824 +
41825 +#ifdef RALINK_ATE
41826 +#ifdef RALINK_28xx_QA
41827 +#define RTPRIV_IOCTL_ATE (SIOCIWFIRSTPRIV + 0x08)
41828 +#endif // RALINK_28xx_QA //
41829 +#endif // RALINK_ATE //
41830 +
41831 +#define RTPRIV_IOCTL_STATISTICS (SIOCIWFIRSTPRIV + 0x09)
41832 +#define RTPRIV_IOCTL_ADD_PMKID_CACHE (SIOCIWFIRSTPRIV + 0x0A)
41833 +#define RTPRIV_IOCTL_RADIUS_DATA (SIOCIWFIRSTPRIV + 0x0C)
41834 +#define RTPRIV_IOCTL_GSITESURVEY (SIOCIWFIRSTPRIV + 0x0D)
41835 +#define RT_PRIV_IOCTL (SIOCIWFIRSTPRIV + 0x0E) // Sync. with RT61 (for wpa_supplicant)
41836 +#define RTPRIV_IOCTL_GET_MAC_TABLE (SIOCIWFIRSTPRIV + 0x0F)
41837 +
41838 +#define RTPRIV_IOCTL_SHOW (SIOCIWFIRSTPRIV + 0x11)
41839 +enum {
41840 + SHOW_CONN_STATUS = 4,
41841 + SHOW_DRVIER_VERION = 5,
41842 + SHOW_BA_INFO = 6,
41843 + SHOW_DESC_INFO = 7,
41844 + RAIO_OFF = 10,
41845 + RAIO_ON = 11,
41846 +#ifdef QOS_DLS_SUPPORT
41847 + SHOW_DLS_ENTRY_INFO = 19,
41848 +#endif // QOS_DLS_SUPPORT //
41849 + SHOW_CFG_VALUE = 20,
41850 +};
41851 +
41852 +#endif // CONFIG_STA_SUPPORT //
41853 +
41854 +#ifdef SNMP_SUPPORT
41855 +//SNMP ieee 802dot11, kathy , 2008_0220
41856 +// dot11res(3)
41857 +#define RT_OID_802_11_MANUFACTUREROUI 0x0700
41858 +#define RT_OID_802_11_MANUFACTURERNAME 0x0701
41859 +#define RT_OID_802_11_RESOURCETYPEIDNAME 0x0702
41860 +
41861 +// dot11smt(1)
41862 +#define RT_OID_802_11_PRIVACYOPTIONIMPLEMENTED 0x0703
41863 +#define RT_OID_802_11_POWERMANAGEMENTMODE 0x0704
41864 +#define OID_802_11_WEPDEFAULTKEYVALUE 0x0705 // read , write
41865 +#define OID_802_11_WEPDEFAULTKEYID 0x0706
41866 +#define RT_OID_802_11_WEPKEYMAPPINGLENGTH 0x0707
41867 +#define OID_802_11_SHORTRETRYLIMIT 0x0708
41868 +#define OID_802_11_LONGRETRYLIMIT 0x0709
41869 +#define RT_OID_802_11_PRODUCTID 0x0710
41870 +#define RT_OID_802_11_MANUFACTUREID 0x0711
41871 +
41872 +// //dot11Phy(4)
41873 +#define OID_802_11_CURRENTCHANNEL 0x0712
41874 +
41875 +//dot11mac
41876 +#define RT_OID_802_11_MAC_ADDRESS 0x0713
41877 +#endif // SNMP_SUPPORT //
41878 +
41879 +#define OID_802_11_BUILD_CHANNEL_EX 0x0714
41880 +#define OID_802_11_GET_CH_LIST 0x0715
41881 +#define OID_802_11_GET_COUNTRY_CODE 0x0716
41882 +#define OID_802_11_GET_CHANNEL_GEOGRAPHY 0x0717
41883 +
41884 +#ifdef LLTD_SUPPORT
41885 +// for consistency with RT61
41886 +#define RT_OID_GET_PHY_MODE 0x761
41887 +#endif // LLTD_SUPPORT //
41888 +
41889 +// New for MeetingHouse Api support
41890 +#define OID_MH_802_1X_SUPPORTED 0xFFEDC100
41891 +
41892 +// MIMO Tx parameter, ShortGI, MCS, STBC, etc. these are fields in TXWI. Don't change this definition!!!
41893 +typedef union _HTTRANSMIT_SETTING {
41894 +#ifdef RT_BIG_ENDIAN
41895 + struct {
41896 + USHORT MODE:2; // Use definition MODE_xxx.
41897 + USHORT TxBF:1;
41898 + USHORT rsv:2;
41899 + USHORT STBC:2; //SPACE
41900 + USHORT ShortGI:1;
41901 + USHORT BW:1; //channel bandwidth 20MHz or 40 MHz
41902 + USHORT MCS:7; // MCS
41903 + } field;
41904 +#else
41905 + struct {
41906 + USHORT MCS:7; // MCS
41907 + USHORT BW:1; //channel bandwidth 20MHz or 40 MHz
41908 + USHORT ShortGI:1;
41909 + USHORT STBC:2; //SPACE
41910 + USHORT rsv:2;
41911 + USHORT TxBF:1;
41912 + USHORT MODE:2; // Use definition MODE_xxx.
41913 + } field;
41914 +#endif
41915 + USHORT word;
41916 + } HTTRANSMIT_SETTING, *PHTTRANSMIT_SETTING;
41917 +
41918 +typedef enum _RT_802_11_PREAMBLE {
41919 + Rt802_11PreambleLong,
41920 + Rt802_11PreambleShort,
41921 + Rt802_11PreambleAuto
41922 +} RT_802_11_PREAMBLE, *PRT_802_11_PREAMBLE;
41923 +
41924 +// Only for STA, need to sync with AP
41925 +// 2005-03-08 match current RaConfig.
41926 +typedef enum _RT_802_11_PHY_MODE {
41927 + PHY_11BG_MIXED = 0,
41928 + PHY_11B,
41929 + PHY_11A,
41930 + PHY_11ABG_MIXED,
41931 + PHY_11G,
41932 +#ifdef DOT11_N_SUPPORT
41933 + PHY_11ABGN_MIXED, // both band 5
41934 + PHY_11N_2_4G, // 11n-only with 2.4G band 6
41935 + PHY_11GN_MIXED, // 2.4G band 7
41936 + PHY_11AN_MIXED, // 5G band 8
41937 + PHY_11BGN_MIXED, // if check 802.11b. 9
41938 + PHY_11AGN_MIXED, // if check 802.11b. 10
41939 + PHY_11N_5G, // 11n-only with 5G band 11
41940 +#endif // DOT11_N_SUPPORT //
41941 +} RT_802_11_PHY_MODE;
41942 +
41943 +// put all proprietery for-query objects here to reduce # of Query_OID
41944 +typedef struct _RT_802_11_LINK_STATUS {
41945 + ULONG CurrTxRate; // in units of 0.5Mbps
41946 + ULONG ChannelQuality; // 0..100 %
41947 + ULONG TxByteCount; // both ok and fail
41948 + ULONG RxByteCount; // both ok and fail
41949 + ULONG CentralChannel; // 40MHz central channel number
41950 +} RT_802_11_LINK_STATUS, *PRT_802_11_LINK_STATUS;
41951 +
41952 +typedef struct _RT_802_11_EVENT_LOG {
41953 + LARGE_INTEGER SystemTime; // timestammp via NdisGetCurrentSystemTime()
41954 + UCHAR Addr[MAC_ADDR_LENGTH];
41955 + USHORT Event; // EVENT_xxx
41956 +} RT_802_11_EVENT_LOG, *PRT_802_11_EVENT_LOG;
41957 +
41958 +typedef struct _RT_802_11_EVENT_TABLE {
41959 + ULONG Num;
41960 + ULONG Rsv; // to align Log[] at LARGE_INEGER boundary
41961 + RT_802_11_EVENT_LOG Log[MAX_NUMBER_OF_EVENT];
41962 +} RT_802_11_EVENT_TABLE, PRT_802_11_EVENT_TABLE;
41963 +
41964 +// MIMO Tx parameter, ShortGI, MCS, STBC, etc. these are fields in TXWI. Don't change this definition!!!
41965 +typedef union _MACHTTRANSMIT_SETTING {
41966 + struct {
41967 + USHORT MCS:7; // MCS
41968 + USHORT BW:1; //channel bandwidth 20MHz or 40 MHz
41969 + USHORT ShortGI:1;
41970 + USHORT STBC:2; //SPACE
41971 + USHORT rsv:3;
41972 + USHORT MODE:2; // Use definition MODE_xxx.
41973 + } field;
41974 + USHORT word;
41975 + } MACHTTRANSMIT_SETTING, *PMACHTTRANSMIT_SETTING;
41976 +
41977 +typedef struct _RT_802_11_MAC_ENTRY {
41978 + UCHAR Addr[MAC_ADDR_LENGTH];
41979 + UCHAR Aid;
41980 + UCHAR Psm; // 0:PWR_ACTIVE, 1:PWR_SAVE
41981 + UCHAR MimoPs; // 0:MMPS_STATIC, 1:MMPS_DYNAMIC, 3:MMPS_Enabled
41982 + CHAR AvgRssi0;
41983 + CHAR AvgRssi1;
41984 + CHAR AvgRssi2;
41985 + UINT32 ConnectedTime;
41986 + MACHTTRANSMIT_SETTING TxRate;
41987 +} RT_802_11_MAC_ENTRY, *PRT_802_11_MAC_ENTRY;
41988 +
41989 +typedef struct _RT_802_11_MAC_TABLE {
41990 + ULONG Num;
41991 + RT_802_11_MAC_ENTRY Entry[MAX_NUMBER_OF_MAC];
41992 +} RT_802_11_MAC_TABLE, *PRT_802_11_MAC_TABLE;
41993 +
41994 +// structure for query/set hardware register - MAC, BBP, RF register
41995 +typedef struct _RT_802_11_HARDWARE_REGISTER {
41996 + ULONG HardwareType; // 0:MAC, 1:BBP, 2:RF register, 3:EEPROM
41997 + ULONG Offset; // Q/S register offset addr
41998 + ULONG Data; // R/W data buffer
41999 +} RT_802_11_HARDWARE_REGISTER, *PRT_802_11_HARDWARE_REGISTER;
42000 +
42001 +typedef struct _RT_802_11_AP_CONFIG {
42002 + ULONG EnableTxBurst; // 0-disable, 1-enable
42003 + ULONG EnableTurboRate; // 0-disable, 1-enable 72/100mbps turbo rate
42004 + ULONG IsolateInterStaTraffic; // 0-disable, 1-enable isolation
42005 + ULONG HideSsid; // 0-disable, 1-enable hiding
42006 + ULONG UseBGProtection; // 0-AUTO, 1-always ON, 2-always OFF
42007 + ULONG UseShortSlotTime; // 0-no use, 1-use 9-us short slot time
42008 + ULONG Rsv1; // must be 0
42009 + ULONG SystemErrorBitmap; // ignore upon SET, return system error upon QUERY
42010 +} RT_802_11_AP_CONFIG, *PRT_802_11_AP_CONFIG;
42011 +
42012 +// structure to query/set STA_CONFIG
42013 +typedef struct _RT_802_11_STA_CONFIG {
42014 + ULONG EnableTxBurst; // 0-disable, 1-enable
42015 + ULONG EnableTurboRate; // 0-disable, 1-enable 72/100mbps turbo rate
42016 + ULONG UseBGProtection; // 0-AUTO, 1-always ON, 2-always OFF
42017 + ULONG UseShortSlotTime; // 0-no use, 1-use 9-us short slot time when applicable
42018 + ULONG AdhocMode; // 0-11b rates only (WIFI spec), 1 - b/g mixed, 2 - g only
42019 + ULONG HwRadioStatus; // 0-OFF, 1-ON, default is 1, Read-Only
42020 + ULONG Rsv1; // must be 0
42021 + ULONG SystemErrorBitmap; // ignore upon SET, return system error upon QUERY
42022 +} RT_802_11_STA_CONFIG, *PRT_802_11_STA_CONFIG;
42023 +
42024 +//
42025 +// For OID Query or Set about BA structure
42026 +//
42027 +typedef struct _OID_BACAP_STRUC {
42028 + UCHAR RxBAWinLimit;
42029 + UCHAR TxBAWinLimit;
42030 + UCHAR Policy; // 0: DELAY_BA 1:IMMED_BA (//BA Policy subfiled value in ADDBA frame) 2:BA-not use. other value invalid
42031 + UCHAR MpduDensity; // 0: DELAY_BA 1:IMMED_BA (//BA Policy subfiled value in ADDBA frame) 2:BA-not use. other value invalid
42032 + UCHAR AmsduEnable; //Enable AMSDU transmisstion
42033 + UCHAR AmsduSize; // 0:3839, 1:7935 bytes. UINT MSDUSizeToBytes[] = { 3839, 7935};
42034 + UCHAR MMPSmode; // MIMO power save more, 0:static, 1:dynamic, 2:rsv, 3:mimo enable
42035 + BOOLEAN AutoBA; // Auto BA will automatically
42036 +} OID_BACAP_STRUC, *POID_BACAP_STRUC;
42037 +
42038 +typedef struct _RT_802_11_ACL_ENTRY {
42039 + UCHAR Addr[MAC_ADDR_LENGTH];
42040 + USHORT Rsv;
42041 +} RT_802_11_ACL_ENTRY, *PRT_802_11_ACL_ENTRY;
42042 +
42043 +typedef struct PACKED _RT_802_11_ACL {
42044 + ULONG Policy; // 0-disable, 1-positive list, 2-negative list
42045 + ULONG Num;
42046 + RT_802_11_ACL_ENTRY Entry[MAX_NUMBER_OF_ACL];
42047 +} RT_802_11_ACL, *PRT_802_11_ACL;
42048 +
42049 +typedef struct _RT_802_11_WDS {
42050 + ULONG Num;
42051 + NDIS_802_11_MAC_ADDRESS Entry[24/*MAX_NUM_OF_WDS_LINK*/];
42052 + ULONG KeyLength;
42053 + UCHAR KeyMaterial[32];
42054 +} RT_802_11_WDS, *PRT_802_11_WDS;
42055 +
42056 +typedef struct _RT_802_11_TX_RATES_ {
42057 + UCHAR SupRateLen;
42058 + UCHAR SupRate[MAX_LENGTH_OF_SUPPORT_RATES];
42059 + UCHAR ExtRateLen;
42060 + UCHAR ExtRate[MAX_LENGTH_OF_SUPPORT_RATES];
42061 +} RT_802_11_TX_RATES, *PRT_802_11_TX_RATES;
42062 +
42063 +
42064 +// Definition of extra information code
42065 +#define GENERAL_LINK_UP 0x0 // Link is Up
42066 +#define GENERAL_LINK_DOWN 0x1 // Link is Down
42067 +#define HW_RADIO_OFF 0x2 // Hardware radio off
42068 +#define SW_RADIO_OFF 0x3 // Software radio off
42069 +#define AUTH_FAIL 0x4 // Open authentication fail
42070 +#define AUTH_FAIL_KEYS 0x5 // Shared authentication fail
42071 +#define ASSOC_FAIL 0x6 // Association failed
42072 +#define EAP_MIC_FAILURE 0x7 // Deauthencation because MIC failure
42073 +#define EAP_4WAY_TIMEOUT 0x8 // Deauthencation on 4-way handshake timeout
42074 +#define EAP_GROUP_KEY_TIMEOUT 0x9 // Deauthencation on group key handshake timeout
42075 +#define EAP_SUCCESS 0xa // EAP succeed
42076 +#define DETECT_RADAR_SIGNAL 0xb // Radar signal occur in current channel
42077 +#define EXTRA_INFO_MAX 0xb // Indicate Last OID
42078 +
42079 +#define EXTRA_INFO_CLEAR 0xffffffff
42080 +
42081 +// This is OID setting structure. So only GF or MM as Mode. This is valid when our wirelss mode has 802.11n in use.
42082 +typedef struct {
42083 + RT_802_11_PHY_MODE PhyMode; //
42084 + UCHAR TransmitNo;
42085 + UCHAR HtMode; //HTMODE_GF or HTMODE_MM
42086 + UCHAR ExtOffset; //extension channel above or below
42087 + UCHAR MCS;
42088 + UCHAR BW;
42089 + UCHAR STBC;
42090 + UCHAR SHORTGI;
42091 + UCHAR rsv;
42092 +} OID_SET_HT_PHYMODE, *POID_SET_HT_PHYMODE;
42093 +
42094 +#ifdef LLTD_SUPPORT
42095 +typedef struct _RT_LLTD_ASSOICATION_ENTRY {
42096 + UCHAR Addr[ETH_LENGTH_OF_ADDRESS];
42097 + unsigned short MOR; // maximum operational rate
42098 + UCHAR phyMode;
42099 +} RT_LLTD_ASSOICATION_ENTRY, *PRT_LLTD_ASSOICATION_ENTRY;
42100 +
42101 +typedef struct _RT_LLTD_ASSOICATION_TABLE {
42102 + unsigned int Num;
42103 + RT_LLTD_ASSOICATION_ENTRY Entry[MAX_NUMBER_OF_MAC];
42104 +} RT_LLTD_ASSOICATION_TABLE, *PRT_LLTD_ASSOICATION_TABLE;
42105 +#endif // LLTD_SUPPORT //
42106 +
42107 +#ifdef CONFIG_STA_SUPPORT
42108 +#ifdef QOS_DLS_SUPPORT
42109 +//rt2860, kathy 2007-0118
42110 +// structure for DLS
42111 +typedef struct _RT_802_11_DLS_UI {
42112 + USHORT TimeOut; // unit: second , set by UI
42113 + USHORT CountDownTimer; // unit: second , used by driver only
42114 + NDIS_802_11_MAC_ADDRESS MacAddr; // set by UI
42115 + UCHAR Status; // 0: none , 1: wait STAkey, 2: finish DLS setup , set by driver only
42116 + BOOLEAN Valid; // 1: valid , 0: invalid , set by UI, use to setup or tear down DLS link
42117 +} RT_802_11_DLS_UI, *PRT_802_11_DLS_UI;
42118 +
42119 +typedef struct _RT_802_11_DLS_INFO {
42120 + RT_802_11_DLS_UI Entry[MAX_NUMBER_OF_DLS_ENTRY];
42121 + UCHAR num;
42122 +} RT_802_11_DLS_INFO, *PRT_802_11_DLS_INFO;
42123 +
42124 +typedef enum _RT_802_11_DLS_MODE {
42125 + DLS_NONE,
42126 + DLS_WAIT_KEY,
42127 + DLS_FINISH
42128 +} RT_802_11_DLS_MODE;
42129 +#endif // QOS_DLS_SUPPORT //
42130 +
42131 +#ifdef WPA_SUPPLICANT_SUPPORT
42132 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
42133 +#define RT_ASSOC_EVENT_FLAG 0x0101
42134 +#define RT_DISASSOC_EVENT_FLAG 0x0102
42135 +#define RT_REQIE_EVENT_FLAG 0x0103
42136 +#define RT_RESPIE_EVENT_FLAG 0x0104
42137 +#define RT_ASSOCINFO_EVENT_FLAG 0x0105
42138 +#define RT_PMKIDCAND_FLAG 0x0106
42139 +#define RT_INTERFACE_DOWN 0x0107
42140 +#define RT_INTERFACE_UP 0x0108
42141 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
42142 +#endif // WPA_SUPPLICANT_SUPPORT //
42143 +#endif // CONFIG_STA_SUPPORT //
42144 +
42145 +#define MAX_CUSTOM_LEN 128
42146 +
42147 +#ifdef CONFIG_STA_SUPPORT
42148 +typedef enum _RT_802_11_D_CLIENT_MODE
42149 +{
42150 + Rt802_11_D_None,
42151 + Rt802_11_D_Flexible,
42152 + Rt802_11_D_Strict,
42153 +} RT_802_11_D_CLIENT_MODE, *PRT_802_11_D_CLIENT_MODE;
42154 +#endif // CONFIG_STA_SUPPORT //
42155 +
42156 +typedef struct _RT_CHANNEL_LIST_INFO
42157 +{
42158 + UCHAR ChannelList[MAX_NUM_OF_CHS]; // list all supported channels for site survey
42159 + UCHAR ChannelListNum; // number of channel in ChannelList[]
42160 +} RT_CHANNEL_LIST_INFO, *PRT_CHANNEL_LIST_INFO;
42161 +
42162 +
42163 +#endif // _OID_H_
42164 +
42165 --- /dev/null
42166 +++ b/drivers/staging/rt2860/rt2860.h
42167 @@ -0,0 +1,349 @@
42168 +/*
42169 + *************************************************************************
42170 + * Ralink Tech Inc.
42171 + * 5F., No.36, Taiyuan St., Jhubei City,
42172 + * Hsinchu County 302,
42173 + * Taiwan, R.O.C.
42174 + *
42175 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
42176 + *
42177 + * This program is free software; you can redistribute it and/or modify *
42178 + * it under the terms of the GNU General Public License as published by *
42179 + * the Free Software Foundation; either version 2 of the License, or *
42180 + * (at your option) any later version. *
42181 + * *
42182 + * This program is distributed in the hope that it will be useful, *
42183 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
42184 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
42185 + * GNU General Public License for more details. *
42186 + * *
42187 + * You should have received a copy of the GNU General Public License *
42188 + * along with this program; if not, write to the *
42189 + * Free Software Foundation, Inc., *
42190 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
42191 + * *
42192 + *************************************************************************
42193 + */
42194 +
42195 +#ifndef __RT2860_H__
42196 +#define __RT2860_H__
42197 +
42198 +#define RT28xx_CHIP_NAME "RT2860"
42199 +
42200 +#define TXINFO_SIZE 0
42201 +#define TXPADDING_SIZE 0
42202 +
42203 +/* ----------------- EEPROM Related MACRO ----------------- */
42204 +#define RT28xx_EEPROM_READ16(pAd, offset, var) \
42205 + var = RTMP_EEPROM_READ16(pAd, offset)
42206 +
42207 +#define RT28xx_EEPROM_WRITE16(pAd, offset, var) \
42208 + RTMP_EEPROM_WRITE16(pAd, offset, var)
42209 +
42210 +/* ----------------- TASK/THREAD Related MACRO ----------------- */
42211 +#define RT28XX_TASK_THREAD_INIT(pAd, Status) \
42212 + init_thread_task(pAd); NICInitTxRxRingAndBacklogQueue(pAd); \
42213 + Status = NDIS_STATUS_SUCCESS;
42214 +
42215 +/* function declarations */
42216 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
42217 +#define IRQ_HANDLE_TYPE irqreturn_t
42218 +#else
42219 +#define IRQ_HANDLE_TYPE void
42220 +#endif
42221 +
42222 +IRQ_HANDLE_TYPE
42223 +#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,19))
42224 +rt2860_interrupt(int irq, void *dev_instance);
42225 +#else
42226 +rt2860_interrupt(int irq, void *dev_instance, struct pt_regs *regs);
42227 +#endif
42228 +
42229 +/* ----------------- Frimware Related MACRO ----------------- */
42230 +#define RT28XX_WRITE_FIRMWARE(_pAd, _pFwImage, _FwLen) \
42231 + do{ \
42232 + ULONG _i, _firm; \
42233 + RTMP_IO_WRITE32(_pAd, PBF_SYS_CTRL, 0x10000); \
42234 + \
42235 + for(_i=0; _i<_FwLen; _i+=4) \
42236 + { \
42237 + _firm = _pFwImage[_i] + \
42238 + (_pFwImage[_i+3] << 24) + \
42239 + (_pFwImage[_i+2] << 16) + \
42240 + (_pFwImage[_i+1] << 8); \
42241 + RTMP_IO_WRITE32(_pAd, FIRMWARE_IMAGE_BASE + _i, _firm); \
42242 + } \
42243 + RTMP_IO_WRITE32(_pAd, PBF_SYS_CTRL, 0x00000); \
42244 + RTMP_IO_WRITE32(_pAd, PBF_SYS_CTRL, 0x00001); \
42245 + \
42246 + /* initialize BBP R/W access agent */ \
42247 + RTMP_IO_WRITE32(_pAd, H2M_BBP_AGENT, 0); \
42248 + RTMP_IO_WRITE32(_pAd, H2M_MAILBOX_CSR, 0); \
42249 + }while(0)
42250 +
42251 +/* ----------------- TX Related MACRO ----------------- */
42252 +#define RT28XX_START_DEQUEUE(pAd, QueIdx, irqFlags) do{}while(0)
42253 +#define RT28XX_STOP_DEQUEUE(pAd, QueIdx, irqFlags) do{}while(0)
42254 +
42255 +
42256 +#define RT28XX_HAS_ENOUGH_FREE_DESC(pAd, pTxBlk, freeNum, pPacket) \
42257 + ((freeNum) >= (ULONG)(pTxBlk->TotalFragNum + RTMP_GET_PACKET_FRAGMENTS(pPacket) + 3)) /* rough estimate we will use 3 more descriptor. */
42258 +#define RT28XX_RELEASE_DESC_RESOURCE(pAd, QueIdx) \
42259 + do{}while(0)
42260 +
42261 +#define NEED_QUEUE_BACK_FOR_AGG(pAd, QueIdx, freeNum, _TxFrameType) \
42262 + (((freeNum != (TX_RING_SIZE-1)) && (pAd->TxSwQueue[QueIdx].Number == 0)) || (freeNum<3))
42263 + //(((freeNum) != (TX_RING_SIZE-1)) && (pAd->TxSwQueue[QueIdx].Number == 1 /*0*/))
42264 +
42265 +
42266 +#define HAL_KickOutMgmtTx(_pAd, _QueIdx, _pPacket, _pSrcBufVA, _SrcBufLen) \
42267 + RtmpPCIMgmtKickOut(_pAd, _QueIdx, _pPacket, _pSrcBufVA, _SrcBufLen)
42268 +
42269 +#define RTMP_PKT_TAIL_PADDING 0
42270 +
42271 +#define fRTMP_ADAPTER_NEED_STOP_TX 0
42272 +
42273 +#define HAL_WriteSubTxResource(pAd, pTxBlk, bIsLast, pFreeNumber) \
42274 + /* RtmpPCI_WriteSubTxResource(pAd, pTxBlk, bIsLast, pFreeNumber)*/
42275 +
42276 +#define HAL_WriteTxResource(pAd, pTxBlk,bIsLast, pFreeNumber) \
42277 + RtmpPCI_WriteSingleTxResource(pAd, pTxBlk, bIsLast, pFreeNumber)
42278 +
42279 +#define HAL_WriteFragTxResource(pAd, pTxBlk, fragNum, pFreeNumber) \
42280 + RtmpPCI_WriteFragTxResource(pAd, pTxBlk, fragNum, pFreeNumber)
42281 +
42282 +#define HAL_WriteMultiTxResource(pAd, pTxBlk,frameNum, pFreeNumber) \
42283 + RtmpPCI_WriteMultiTxResource(pAd, pTxBlk, frameNum, pFreeNumber)
42284 +
42285 +#define HAL_FinalWriteTxResource(_pAd, _pTxBlk, _TotalMPDUSize, _FirstTxIdx) \
42286 + RtmpPCI_FinalWriteTxResource(_pAd, _pTxBlk, _TotalMPDUSize, _FirstTxIdx)
42287 +
42288 +#define HAL_LastTxIdx(_pAd, _QueIdx,_LastTxIdx) \
42289 + /*RtmpPCIDataLastTxIdx(_pAd, _QueIdx,_LastTxIdx)*/
42290 +
42291 +#define HAL_KickOutTx(_pAd, _pTxBlk, _QueIdx) \
42292 + RTMP_IO_WRITE32((_pAd), TX_CTX_IDX0+((_QueIdx)*0x10), (_pAd)->TxRing[(_QueIdx)].TxCpuIdx)
42293 +/* RtmpPCIDataKickOut(_pAd, _pTxBlk, _QueIdx)*/
42294 +
42295 +#define HAL_KickOutNullFrameTx(_pAd, _QueIdx, _pNullFrame, _frameLen) \
42296 + MiniportMMRequest(_pAd, _QueIdx, _pNullFrame, _frameLen)
42297 +
42298 +#define GET_TXRING_FREENO(_pAd, _QueIdx) \
42299 + (_pAd->TxRing[_QueIdx].TxSwFreeIdx > _pAd->TxRing[_QueIdx].TxCpuIdx) ? \
42300 + (_pAd->TxRing[_QueIdx].TxSwFreeIdx - _pAd->TxRing[_QueIdx].TxCpuIdx - 1) \
42301 + : \
42302 + (_pAd->TxRing[_QueIdx].TxSwFreeIdx + TX_RING_SIZE - _pAd->TxRing[_QueIdx].TxCpuIdx - 1);
42303 +
42304 +
42305 +#define GET_MGMTRING_FREENO(_pAd) \
42306 + (_pAd->MgmtRing.TxSwFreeIdx > _pAd->MgmtRing.TxCpuIdx) ? \
42307 + (_pAd->MgmtRing.TxSwFreeIdx - _pAd->MgmtRing.TxCpuIdx - 1) \
42308 + : \
42309 + (_pAd->MgmtRing.TxSwFreeIdx + MGMT_RING_SIZE - _pAd->MgmtRing.TxCpuIdx - 1);
42310 +
42311 +
42312 +/* ----------------- RX Related MACRO ----------------- */
42313 +
42314 +// no use
42315 +#define RT28XX_RCV_PKT_GET_INIT(pAd)
42316 +#define RT28XX_RV_A_BUF_END
42317 +//#define RT28XX_RV_ALL_BUF_END
42318 +
42319 +
42320 +/* ----------------- ASIC Related MACRO ----------------- */
42321 +// no use
42322 +#define RT28XX_DMA_POST_WRITE(pAd)
42323 +
42324 +// reset MAC of a station entry to 0x000000000000
42325 +#define RT28XX_STA_ENTRY_MAC_RESET(pAd, Wcid) \
42326 + AsicDelWcidTab(pAd, Wcid);
42327 +
42328 +// add this entry into ASIC RX WCID search table
42329 +#define RT28XX_STA_ENTRY_ADD(pAd, pEntry) \
42330 + AsicUpdateRxWCIDTable(pAd, pEntry->Aid, pEntry->Addr);
42331 +
42332 +// remove Pair-wise key material from ASIC
42333 +#define RT28XX_STA_ENTRY_KEY_DEL(pAd, BssIdx, Wcid) \
42334 + AsicRemovePairwiseKeyEntry(pAd, BssIdx, (UCHAR)Wcid);
42335 +
42336 +// add Client security information into ASIC WCID table and IVEIV table
42337 +#define RT28XX_STA_SECURITY_INFO_ADD(pAd, apidx, KeyID, pEntry) \
42338 + RTMPAddWcidAttributeEntry(pAd, apidx, KeyID, \
42339 + pAd->SharedKey[apidx][KeyID].CipherAlg, pEntry);
42340 +
42341 +#define RT28XX_SECURITY_KEY_ADD(pAd, apidx, KeyID, pEntry) \
42342 + { /* update pairwise key information to ASIC Shared Key Table */ \
42343 + AsicAddSharedKeyEntry(pAd, apidx, KeyID, \
42344 + pAd->SharedKey[apidx][KeyID].CipherAlg, \
42345 + pAd->SharedKey[apidx][KeyID].Key, \
42346 + pAd->SharedKey[apidx][KeyID].TxMic, \
42347 + pAd->SharedKey[apidx][KeyID].RxMic); \
42348 + /* update ASIC WCID attribute table and IVEIV table */ \
42349 + RTMPAddWcidAttributeEntry(pAd, apidx, KeyID, \
42350 + pAd->SharedKey[apidx][KeyID].CipherAlg, \
42351 + pEntry); }
42352 +
42353 +
42354 +// Insert the BA bitmap to ASIC for the Wcid entry
42355 +#define RT28XX_ADD_BA_SESSION_TO_ASIC(_pAd, _Aid, _TID) \
42356 + do{ \
42357 + UINT32 _Value = 0, _Offset; \
42358 + _Offset = MAC_WCID_BASE + (_Aid) * HW_WCID_ENTRY_SIZE + 4; \
42359 + RTMP_IO_READ32((_pAd), _Offset, &_Value); \
42360 + _Value |= (0x10000<<(_TID)); \
42361 + RTMP_IO_WRITE32((_pAd), _Offset, _Value); \
42362 + }while(0)
42363 +
42364 +
42365 +// Remove the BA bitmap from ASIC for the Wcid entry
42366 +// bitmap field starts at 0x10000 in ASIC WCID table
42367 +#define RT28XX_DEL_BA_SESSION_FROM_ASIC(_pAd, _Wcid, _TID) \
42368 + do{ \
42369 + UINT32 _Value = 0, _Offset; \
42370 + _Offset = MAC_WCID_BASE + (_Wcid) * HW_WCID_ENTRY_SIZE + 4; \
42371 + RTMP_IO_READ32((_pAd), _Offset, &_Value); \
42372 + _Value &= (~(0x10000 << (_TID))); \
42373 + RTMP_IO_WRITE32((_pAd), _Offset, _Value); \
42374 + }while(0)
42375 +
42376 +
42377 +/* ----------------- PCI/USB Related MACRO ----------------- */
42378 +
42379 +#define RT28XX_HANDLE_DEV_ASSIGN(handle, dev_p) \
42380 + ((POS_COOKIE)handle)->pci_dev = dev_p;
42381 +
42382 +// set driver data
42383 +#define RT28XX_DRVDATA_SET(_a) pci_set_drvdata(_a, net_dev);
42384 +
42385 +#define RT28XX_UNMAP() \
42386 +{ if (net_dev->base_addr) { \
42387 + iounmap((void *)(net_dev->base_addr)); \
42388 + release_mem_region(pci_resource_start(dev_p, 0), \
42389 + pci_resource_len(dev_p, 0)); } \
42390 + if (net_dev->irq) pci_release_regions(dev_p); }
42391 +
42392 +#ifdef PCI_MSI_SUPPORT
42393 +#define RTMP_MSI_ENABLE(_pAd) \
42394 +{ POS_COOKIE _pObj = (POS_COOKIE)(_pAd->OS_Cookie); \
42395 + (_pAd)->HaveMsi = pci_enable_msi(_pObj->pci_dev) == 0 ? TRUE : FALSE; }
42396 +
42397 +#define RTMP_MSI_DISABLE(_pAd) \
42398 +{ POS_COOKIE _pObj = (POS_COOKIE)(_pAd->OS_Cookie); \
42399 + if (_pAd->HaveMsi == TRUE) \
42400 + pci_disable_msi(_pObj->pci_dev); \
42401 + _pAd->HaveMsi = FALSE; }
42402 +#else
42403 +#define RTMP_MSI_ENABLE(_pAd)
42404 +#define RTMP_MSI_DISABLE(_pAd)
42405 +#endif // PCI_MSI_SUPPORT //
42406 +
42407 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,24)
42408 +#define SA_SHIRQ IRQF_SHARED
42409 +#endif
42410 +
42411 +#define RT28XX_IRQ_REQUEST(net_dev) \
42412 +{ PRTMP_ADAPTER _pAd = (PRTMP_ADAPTER)((net_dev)->priv); \
42413 + POS_COOKIE _pObj = (POS_COOKIE)(_pAd->OS_Cookie); \
42414 + RTMP_MSI_ENABLE(_pAd); \
42415 + if ((retval = request_irq(_pObj->pci_dev->irq, \
42416 + rt2860_interrupt, SA_SHIRQ, \
42417 + (net_dev)->name, (net_dev)))) { \
42418 + printk("RT2860: request_irq ERROR(%d)\n", retval); \
42419 + return retval; } }
42420 +
42421 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
42422 +#define RT28XX_IRQ_RELEASE(net_dev) \
42423 +{ PRTMP_ADAPTER _pAd = (PRTMP_ADAPTER)((net_dev)->priv); \
42424 + POS_COOKIE _pObj = (POS_COOKIE)(_pAd->OS_Cookie); \
42425 + synchronize_irq(_pObj->pci_dev->irq); \
42426 + free_irq(_pObj->pci_dev->irq, (net_dev)); \
42427 + RTMP_MSI_DISABLE(_pAd); }
42428 +#else
42429 +#define RT28XX_IRQ_RELEASE(net_dev) \
42430 +{ PRTMP_ADAPTER _pAd = (PRTMP_ADAPTER)((net_dev)->priv); \
42431 + POS_COOKIE _pObj = (POS_COOKIE)(_pAd->OS_Cookie); \
42432 + free_irq(_pObj->pci_dev->irq, (net_dev)); \
42433 + RTMP_MSI_DISABLE(_pAd); }
42434 +#endif
42435 +
42436 +#define RT28XX_IRQ_INIT(pAd) \
42437 + { pAd->int_enable_reg = ((DELAYINTMASK) | \
42438 + (RxINT|TxDataInt|TxMgmtInt)) & ~(0x03); \
42439 + pAd->int_disable_mask = 0; \
42440 + pAd->int_pending = 0; }
42441 +
42442 +#define RT28XX_IRQ_ENABLE(pAd) \
42443 + { /* clear garbage ints */ \
42444 + RTMP_IO_WRITE32(pAd, INT_SOURCE_CSR, 0xffffffff); \
42445 + NICEnableInterrupt(pAd); }
42446 +
42447 +#define RT28XX_PUT_DEVICE(dev_p)
42448 +
42449 +
42450 +/* ----------------- MLME Related MACRO ----------------- */
42451 +#define RT28XX_MLME_HANDLER(pAd) MlmeHandler(pAd)
42452 +
42453 +#define RT28XX_MLME_PRE_SANITY_CHECK(pAd)
42454 +
42455 +#define RT28XX_MLME_STA_QUICK_RSP_WAKE_UP(pAd) \
42456 + RTMPSetTimer(&pAd->StaCfg.StaQuickResponeForRateUpTimer, 100);
42457 +
42458 +#define RT28XX_MLME_RESET_STATE_MACHINE(pAd) \
42459 + MlmeRestartStateMachine(pAd)
42460 +
42461 +#define RT28XX_HANDLE_COUNTER_MEASURE(_pAd, _pEntry) \
42462 + HandleCounterMeasure(_pAd, _pEntry)
42463 +
42464 +/* ----------------- Power Save Related MACRO ----------------- */
42465 +#define RT28XX_PS_POLL_ENQUEUE(pAd) EnqueuePsPoll(pAd)
42466 +
42467 +//
42468 +// Device ID & Vendor ID, these values should match EEPROM value
42469 +//
42470 +#define NIC2860_PCI_DEVICE_ID 0x0601
42471 +#define NIC2860_PCIe_DEVICE_ID 0x0681
42472 +#define NIC2760_PCI_DEVICE_ID 0x0701 // 1T/2R Cardbus ???
42473 +#define NIC2790_PCIe_DEVICE_ID 0x0781 // 1T/2R miniCard
42474 +
42475 +#define NIC_PCI_VENDOR_ID 0x1814
42476 +
42477 +#define VEN_AWT_PCIe_DEVICE_ID 0x1059
42478 +#define VEN_AWT_PCI_VENDOR_ID 0x1A3B
42479 +
42480 +// For RTMPPCIePowerLinkCtrlRestore () function
42481 +#define RESTORE_HALT 1
42482 +#define RESTORE_WAKEUP 2
42483 +#define RESTORE_CLOSE 3
42484 +
42485 +#define PowerSafeCID 1
42486 +#define PowerRadioOffCID 2
42487 +#define PowerWakeCID 3
42488 +#define CID0MASK 0x000000ff
42489 +#define CID1MASK 0x0000ff00
42490 +#define CID2MASK 0x00ff0000
42491 +#define CID3MASK 0xff000000
42492 +
42493 +#define PCI_REG_READ_WORD(pci_dev, offset, Configuration) \
42494 + if (pci_read_config_word(pci_dev, offset, &reg16) == 0) \
42495 + Configuration = le2cpu16(reg16); \
42496 + else \
42497 + Configuration = 0;
42498 +
42499 +#define PCI_REG_WIRTE_WORD(pci_dev, offset, Configuration) \
42500 + reg16 = cpu2le16(Configuration); \
42501 + pci_write_config_word(pci_dev, offset, reg16); \
42502 +
42503 +#define RT28XX_STA_FORCE_WAKEUP(pAd, bFromTx) \
42504 + RT28xxPciStaAsicForceWakeup(pAd, bFromTx);
42505 +
42506 +#define RT28XX_STA_SLEEP_THEN_AUTO_WAKEUP(pAd, TbttNumToNextWakeUp) \
42507 + RT28xxPciStaAsicSleepThenAutoWakeup(pAd, TbttNumToNextWakeUp);
42508 +
42509 +#define RT28XX_MLME_RADIO_ON(pAd) \
42510 + RT28xxPciMlmeRadioOn(pAd);
42511 +
42512 +#define RT28XX_MLME_RADIO_OFF(pAd) \
42513 + RT28xxPciMlmeRadioOFF(pAd);
42514 +
42515 +#endif //__RT2860_H__
42516 +
42517 --- /dev/null
42518 +++ b/drivers/staging/rt2860/rt28xx.h
42519 @@ -0,0 +1,2714 @@
42520 +/*
42521 + *************************************************************************
42522 + * Ralink Tech Inc.
42523 + * 5F., No.36, Taiyuan St., Jhubei City,
42524 + * Hsinchu County 302,
42525 + * Taiwan, R.O.C.
42526 + *
42527 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
42528 + *
42529 + * This program is free software; you can redistribute it and/or modify *
42530 + * it under the terms of the GNU General Public License as published by *
42531 + * the Free Software Foundation; either version 2 of the License, or *
42532 + * (at your option) any later version. *
42533 + * *
42534 + * This program is distributed in the hope that it will be useful, *
42535 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
42536 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
42537 + * GNU General Public License for more details. *
42538 + * *
42539 + * You should have received a copy of the GNU General Public License *
42540 + * along with this program; if not, write to the *
42541 + * Free Software Foundation, Inc., *
42542 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
42543 + * *
42544 + *************************************************************************
42545 +
42546 + Module Name:
42547 + rt28xx.h
42548 +
42549 + Abstract:
42550 + RT28xx ASIC related definition & structures
42551 +
42552 + Revision History:
42553 + Who When What
42554 + -------- ---------- ----------------------------------------------
42555 + Jan Lee Jan-3-2006 created for RT2860c
42556 +*/
42557 +
42558 +#ifndef __RT28XX_H__
42559 +#define __RT28XX_H__
42560 +
42561 +
42562 +//
42563 +// PCI registers - base address 0x0000
42564 +//
42565 +#define PCI_CFG 0x0000
42566 +#define PCI_EECTRL 0x0004
42567 +#define PCI_MCUCTRL 0x0008
42568 +
42569 +//
42570 +// SCH/DMA registers - base address 0x0200
42571 +//
42572 +// INT_SOURCE_CSR: Interrupt source register. Write one to clear corresponding bit
42573 +//
42574 +#define DMA_CSR0 0x200
42575 +#define INT_SOURCE_CSR 0x200
42576 +#ifdef RT_BIG_ENDIAN
42577 +typedef union _INT_SOURCE_CSR_STRUC {
42578 + struct {
42579 + UINT32 :14;
42580 + UINT32 TxCoherent:1;
42581 + UINT32 RxCoherent:1;
42582 + UINT32 GPTimer:1;
42583 + UINT32 AutoWakeup:1;//bit14
42584 + UINT32 TXFifoStatusInt:1;//FIFO Statistics is full, sw should read 0x171c
42585 + UINT32 PreTBTT:1;
42586 + UINT32 TBTTInt:1;
42587 + UINT32 RxTxCoherent:1;
42588 + UINT32 MCUCommandINT:1;
42589 + UINT32 MgmtDmaDone:1;
42590 + UINT32 HccaDmaDone:1;
42591 + UINT32 Ac3DmaDone:1;
42592 + UINT32 Ac2DmaDone:1;
42593 + UINT32 Ac1DmaDone:1;
42594 + UINT32 Ac0DmaDone:1;
42595 + UINT32 RxDone:1;
42596 + UINT32 TxDelayINT:1; //delayed interrupt, not interrupt until several int or time limit hit
42597 + UINT32 RxDelayINT:1; //dealyed interrupt
42598 + } field;
42599 + UINT32 word;
42600 +} INT_SOURCE_CSR_STRUC, *PINT_SOURCE_CSR_STRUC;
42601 +#else
42602 +typedef union _INT_SOURCE_CSR_STRUC {
42603 + struct {
42604 + UINT32 RxDelayINT:1;
42605 + UINT32 TxDelayINT:1;
42606 + UINT32 RxDone:1;
42607 + UINT32 Ac0DmaDone:1;//4
42608 + UINT32 Ac1DmaDone:1;
42609 + UINT32 Ac2DmaDone:1;
42610 + UINT32 Ac3DmaDone:1;
42611 + UINT32 HccaDmaDone:1; // bit7
42612 + UINT32 MgmtDmaDone:1;
42613 + UINT32 MCUCommandINT:1;//bit 9
42614 + UINT32 RxTxCoherent:1;
42615 + UINT32 TBTTInt:1;
42616 + UINT32 PreTBTT:1;
42617 + UINT32 TXFifoStatusInt:1;//FIFO Statistics is full, sw should read 0x171c
42618 + UINT32 AutoWakeup:1;//bit14
42619 + UINT32 GPTimer:1;
42620 + UINT32 RxCoherent:1;//bit16
42621 + UINT32 TxCoherent:1;
42622 + UINT32 :14;
42623 + } field;
42624 + UINT32 word;
42625 +} INT_SOURCE_CSR_STRUC, *PINT_SOURCE_CSR_STRUC;
42626 +#endif
42627 +
42628 +//
42629 +// INT_MASK_CSR: Interrupt MASK register. 1: the interrupt is mask OFF
42630 +//
42631 +#define INT_MASK_CSR 0x204
42632 +#ifdef RT_BIG_ENDIAN
42633 +typedef union _INT_MASK_CSR_STRUC {
42634 + struct {
42635 + UINT32 TxCoherent:1;
42636 + UINT32 RxCoherent:1;
42637 + UINT32 :20;
42638 + UINT32 MCUCommandINT:1;
42639 + UINT32 MgmtDmaDone:1;
42640 + UINT32 HccaDmaDone:1;
42641 + UINT32 Ac3DmaDone:1;
42642 + UINT32 Ac2DmaDone:1;
42643 + UINT32 Ac1DmaDone:1;
42644 + UINT32 Ac0DmaDone:1;
42645 + UINT32 RxDone:1;
42646 + UINT32 TxDelay:1;
42647 + UINT32 RXDelay_INT_MSK:1;
42648 + } field;
42649 + UINT32 word;
42650 +}INT_MASK_CSR_STRUC, *PINT_MASK_CSR_STRUC;
42651 +#else
42652 +typedef union _INT_MASK_CSR_STRUC {
42653 + struct {
42654 + UINT32 RXDelay_INT_MSK:1;
42655 + UINT32 TxDelay:1;
42656 + UINT32 RxDone:1;
42657 + UINT32 Ac0DmaDone:1;
42658 + UINT32 Ac1DmaDone:1;
42659 + UINT32 Ac2DmaDone:1;
42660 + UINT32 Ac3DmaDone:1;
42661 + UINT32 HccaDmaDone:1;
42662 + UINT32 MgmtDmaDone:1;
42663 + UINT32 MCUCommandINT:1;
42664 + UINT32 :20;
42665 + UINT32 RxCoherent:1;
42666 + UINT32 TxCoherent:1;
42667 + } field;
42668 + UINT32 word;
42669 +} INT_MASK_CSR_STRUC, *PINT_MASK_CSR_STRUC;
42670 +#endif
42671 +#define WPDMA_GLO_CFG 0x208
42672 +#ifdef RT_BIG_ENDIAN
42673 +typedef union _WPDMA_GLO_CFG_STRUC {
42674 + struct {
42675 + UINT32 HDR_SEG_LEN:16;
42676 + UINT32 RXHdrScater:8;
42677 + UINT32 BigEndian:1;
42678 + UINT32 EnTXWriteBackDDONE:1;
42679 + UINT32 WPDMABurstSIZE:2;
42680 + UINT32 RxDMABusy:1;
42681 + UINT32 EnableRxDMA:1;
42682 + UINT32 TxDMABusy:1;
42683 + UINT32 EnableTxDMA:1;
42684 + } field;
42685 + UINT32 word;
42686 +}WPDMA_GLO_CFG_STRUC, *PWPDMA_GLO_CFG_STRUC;
42687 +#else
42688 +typedef union _WPDMA_GLO_CFG_STRUC {
42689 + struct {
42690 + UINT32 EnableTxDMA:1;
42691 + UINT32 TxDMABusy:1;
42692 + UINT32 EnableRxDMA:1;
42693 + UINT32 RxDMABusy:1;
42694 + UINT32 WPDMABurstSIZE:2;
42695 + UINT32 EnTXWriteBackDDONE:1;
42696 + UINT32 BigEndian:1;
42697 + UINT32 RXHdrScater:8;
42698 + UINT32 HDR_SEG_LEN:16;
42699 + } field;
42700 + UINT32 word;
42701 +} WPDMA_GLO_CFG_STRUC, *PWPDMA_GLO_CFG_STRUC;
42702 +#endif
42703 +#define WPDMA_RST_IDX 0x20c
42704 +#ifdef RT_BIG_ENDIAN
42705 +typedef union _WPDMA_RST_IDX_STRUC {
42706 + struct {
42707 + UINT32 :15;
42708 + UINT32 RST_DRX_IDX0:1;
42709 + UINT32 rsv:10;
42710 + UINT32 RST_DTX_IDX5:1;
42711 + UINT32 RST_DTX_IDX4:1;
42712 + UINT32 RST_DTX_IDX3:1;
42713 + UINT32 RST_DTX_IDX2:1;
42714 + UINT32 RST_DTX_IDX1:1;
42715 + UINT32 RST_DTX_IDX0:1;
42716 + } field;
42717 + UINT32 word;
42718 +}WPDMA_RST_IDX_STRUC, *PWPDMA_RST_IDX_STRUC;
42719 +#else
42720 +typedef union _WPDMA_RST_IDX_STRUC {
42721 + struct {
42722 + UINT32 RST_DTX_IDX0:1;
42723 + UINT32 RST_DTX_IDX1:1;
42724 + UINT32 RST_DTX_IDX2:1;
42725 + UINT32 RST_DTX_IDX3:1;
42726 + UINT32 RST_DTX_IDX4:1;
42727 + UINT32 RST_DTX_IDX5:1;
42728 + UINT32 rsv:10;
42729 + UINT32 RST_DRX_IDX0:1;
42730 + UINT32 :15;
42731 + } field;
42732 + UINT32 word;
42733 +} WPDMA_RST_IDX_STRUC, *PWPDMA_RST_IDX_STRUC;
42734 +#endif
42735 +#define DELAY_INT_CFG 0x0210
42736 +#ifdef RT_BIG_ENDIAN
42737 +typedef union _DELAY_INT_CFG_STRUC {
42738 + struct {
42739 + UINT32 TXDLY_INT_EN:1;
42740 + UINT32 TXMAX_PINT:7;
42741 + UINT32 TXMAX_PTIME:8;
42742 + UINT32 RXDLY_INT_EN:1;
42743 + UINT32 RXMAX_PINT:7;
42744 + UINT32 RXMAX_PTIME:8;
42745 + } field;
42746 + UINT32 word;
42747 +}DELAY_INT_CFG_STRUC, *PDELAY_INT_CFG_STRUC;
42748 +#else
42749 +typedef union _DELAY_INT_CFG_STRUC {
42750 + struct {
42751 + UINT32 RXMAX_PTIME:8;
42752 + UINT32 RXMAX_PINT:7;
42753 + UINT32 RXDLY_INT_EN:1;
42754 + UINT32 TXMAX_PTIME:8;
42755 + UINT32 TXMAX_PINT:7;
42756 + UINT32 TXDLY_INT_EN:1;
42757 + } field;
42758 + UINT32 word;
42759 +} DELAY_INT_CFG_STRUC, *PDELAY_INT_CFG_STRUC;
42760 +#endif
42761 +#define WMM_AIFSN_CFG 0x0214
42762 +#ifdef RT_BIG_ENDIAN
42763 +typedef union _AIFSN_CSR_STRUC {
42764 + struct {
42765 + UINT32 Rsv:16;
42766 + UINT32 Aifsn3:4; // for AC_VO
42767 + UINT32 Aifsn2:4; // for AC_VI
42768 + UINT32 Aifsn1:4; // for AC_BK
42769 + UINT32 Aifsn0:4; // for AC_BE
42770 + } field;
42771 + UINT32 word;
42772 +} AIFSN_CSR_STRUC, *PAIFSN_CSR_STRUC;
42773 +#else
42774 +typedef union _AIFSN_CSR_STRUC {
42775 + struct {
42776 + UINT32 Aifsn0:4; // for AC_BE
42777 + UINT32 Aifsn1:4; // for AC_BK
42778 + UINT32 Aifsn2:4; // for AC_VI
42779 + UINT32 Aifsn3:4; // for AC_VO
42780 + UINT32 Rsv:16;
42781 + } field;
42782 + UINT32 word;
42783 +} AIFSN_CSR_STRUC, *PAIFSN_CSR_STRUC;
42784 +#endif
42785 +//
42786 +// CWMIN_CSR: CWmin for each EDCA AC
42787 +//
42788 +#define WMM_CWMIN_CFG 0x0218
42789 +#ifdef RT_BIG_ENDIAN
42790 +typedef union _CWMIN_CSR_STRUC {
42791 + struct {
42792 + UINT32 Rsv:16;
42793 + UINT32 Cwmin3:4; // for AC_VO
42794 + UINT32 Cwmin2:4; // for AC_VI
42795 + UINT32 Cwmin1:4; // for AC_BK
42796 + UINT32 Cwmin0:4; // for AC_BE
42797 + } field;
42798 + UINT32 word;
42799 +} CWMIN_CSR_STRUC, *PCWMIN_CSR_STRUC;
42800 +#else
42801 +typedef union _CWMIN_CSR_STRUC {
42802 + struct {
42803 + UINT32 Cwmin0:4; // for AC_BE
42804 + UINT32 Cwmin1:4; // for AC_BK
42805 + UINT32 Cwmin2:4; // for AC_VI
42806 + UINT32 Cwmin3:4; // for AC_VO
42807 + UINT32 Rsv:16;
42808 + } field;
42809 + UINT32 word;
42810 +} CWMIN_CSR_STRUC, *PCWMIN_CSR_STRUC;
42811 +#endif
42812 +
42813 +//
42814 +// CWMAX_CSR: CWmin for each EDCA AC
42815 +//
42816 +#define WMM_CWMAX_CFG 0x021c
42817 +#ifdef RT_BIG_ENDIAN
42818 +typedef union _CWMAX_CSR_STRUC {
42819 + struct {
42820 + UINT32 Rsv:16;
42821 + UINT32 Cwmax3:4; // for AC_VO
42822 + UINT32 Cwmax2:4; // for AC_VI
42823 + UINT32 Cwmax1:4; // for AC_BK
42824 + UINT32 Cwmax0:4; // for AC_BE
42825 + } field;
42826 + UINT32 word;
42827 +} CWMAX_CSR_STRUC, *PCWMAX_CSR_STRUC;
42828 +#else
42829 +typedef union _CWMAX_CSR_STRUC {
42830 + struct {
42831 + UINT32 Cwmax0:4; // for AC_BE
42832 + UINT32 Cwmax1:4; // for AC_BK
42833 + UINT32 Cwmax2:4; // for AC_VI
42834 + UINT32 Cwmax3:4; // for AC_VO
42835 + UINT32 Rsv:16;
42836 + } field;
42837 + UINT32 word;
42838 +} CWMAX_CSR_STRUC, *PCWMAX_CSR_STRUC;
42839 +#endif
42840 +
42841 +
42842 +//
42843 +// AC_TXOP_CSR0: AC_BK/AC_BE TXOP register
42844 +//
42845 +#define WMM_TXOP0_CFG 0x0220
42846 +#ifdef RT_BIG_ENDIAN
42847 +typedef union _AC_TXOP_CSR0_STRUC {
42848 + struct {
42849 + USHORT Ac1Txop; // for AC_BE, in unit of 32us
42850 + USHORT Ac0Txop; // for AC_BK, in unit of 32us
42851 + } field;
42852 + UINT32 word;
42853 +} AC_TXOP_CSR0_STRUC, *PAC_TXOP_CSR0_STRUC;
42854 +#else
42855 +typedef union _AC_TXOP_CSR0_STRUC {
42856 + struct {
42857 + USHORT Ac0Txop; // for AC_BK, in unit of 32us
42858 + USHORT Ac1Txop; // for AC_BE, in unit of 32us
42859 + } field;
42860 + UINT32 word;
42861 +} AC_TXOP_CSR0_STRUC, *PAC_TXOP_CSR0_STRUC;
42862 +#endif
42863 +
42864 +//
42865 +// AC_TXOP_CSR1: AC_VO/AC_VI TXOP register
42866 +//
42867 +#define WMM_TXOP1_CFG 0x0224
42868 +#ifdef RT_BIG_ENDIAN
42869 +typedef union _AC_TXOP_CSR1_STRUC {
42870 + struct {
42871 + USHORT Ac3Txop; // for AC_VO, in unit of 32us
42872 + USHORT Ac2Txop; // for AC_VI, in unit of 32us
42873 + } field;
42874 + UINT32 word;
42875 +} AC_TXOP_CSR1_STRUC, *PAC_TXOP_CSR1_STRUC;
42876 +#else
42877 +typedef union _AC_TXOP_CSR1_STRUC {
42878 + struct {
42879 + USHORT Ac2Txop; // for AC_VI, in unit of 32us
42880 + USHORT Ac3Txop; // for AC_VO, in unit of 32us
42881 + } field;
42882 + UINT32 word;
42883 +} AC_TXOP_CSR1_STRUC, *PAC_TXOP_CSR1_STRUC;
42884 +#endif
42885 +#define RINGREG_DIFF 0x10
42886 +#define GPIO_CTRL_CFG 0x0228 //MAC_CSR13
42887 +#define MCU_CMD_CFG 0x022c
42888 +#define TX_BASE_PTR0 0x0230 //AC_BK base address
42889 +#define TX_MAX_CNT0 0x0234
42890 +#define TX_CTX_IDX0 0x0238
42891 +#define TX_DTX_IDX0 0x023c
42892 +#define TX_BASE_PTR1 0x0240 //AC_BE base address
42893 +#define TX_MAX_CNT1 0x0244
42894 +#define TX_CTX_IDX1 0x0248
42895 +#define TX_DTX_IDX1 0x024c
42896 +#define TX_BASE_PTR2 0x0250 //AC_VI base address
42897 +#define TX_MAX_CNT2 0x0254
42898 +#define TX_CTX_IDX2 0x0258
42899 +#define TX_DTX_IDX2 0x025c
42900 +#define TX_BASE_PTR3 0x0260 //AC_VO base address
42901 +#define TX_MAX_CNT3 0x0264
42902 +#define TX_CTX_IDX3 0x0268
42903 +#define TX_DTX_IDX3 0x026c
42904 +#define TX_BASE_PTR4 0x0270 //HCCA base address
42905 +#define TX_MAX_CNT4 0x0274
42906 +#define TX_CTX_IDX4 0x0278
42907 +#define TX_DTX_IDX4 0x027c
42908 +#define TX_BASE_PTR5 0x0280 //MGMT base address
42909 +#define TX_MAX_CNT5 0x0284
42910 +#define TX_CTX_IDX5 0x0288
42911 +#define TX_DTX_IDX5 0x028c
42912 +#define TX_MGMTMAX_CNT TX_MAX_CNT5
42913 +#define TX_MGMTCTX_IDX TX_CTX_IDX5
42914 +#define TX_MGMTDTX_IDX TX_DTX_IDX5
42915 +#define RX_BASE_PTR 0x0290 //RX base address
42916 +#define RX_MAX_CNT 0x0294
42917 +#define RX_CRX_IDX 0x0298
42918 +#define RX_DRX_IDX 0x029c
42919 +#define USB_DMA_CFG 0x02a0
42920 +#ifdef RT_BIG_ENDIAN
42921 +typedef union _USB_DMA_CFG_STRUC {
42922 + struct {
42923 + UINT32 TxBusy:1; //USB DMA TX FSM busy . debug only
42924 + UINT32 RxBusy:1; //USB DMA RX FSM busy . debug only
42925 + UINT32 EpoutValid:6; //OUT endpoint data valid. debug only
42926 + UINT32 TxBulkEn:1; //Enable USB DMA Tx
42927 + UINT32 RxBulkEn:1; //Enable USB DMA Rx
42928 + UINT32 RxBulkAggEn:1; //Enable Rx Bulk Aggregation
42929 + UINT32 TxopHalt:1; //Halt TXOP count down when TX buffer is full.
42930 + UINT32 TxClear:1; //Clear USB DMA TX path
42931 + UINT32 rsv:2;
42932 + UINT32 phyclear:1; //phy watch dog enable. write 1
42933 + UINT32 RxBulkAggLmt:8; //Rx Bulk Aggregation Limit in unit of 1024 bytes
42934 + UINT32 RxBulkAggTOut:8; //Rx Bulk Aggregation TimeOut in unit of 33ns
42935 + } field;
42936 + UINT32 word;
42937 +} USB_DMA_CFG_STRUC, *PUSB_DMA_CFG_STRUC;
42938 +#else
42939 +typedef union _USB_DMA_CFG_STRUC {
42940 + struct {
42941 + UINT32 RxBulkAggTOut:8; //Rx Bulk Aggregation TimeOut in unit of 33ns
42942 + UINT32 RxBulkAggLmt:8; //Rx Bulk Aggregation Limit in unit of 256 bytes
42943 + UINT32 phyclear:1; //phy watch dog enable. write 1
42944 + UINT32 rsv:2;
42945 + UINT32 TxClear:1; //Clear USB DMA TX path
42946 + UINT32 TxopHalt:1; //Halt TXOP count down when TX buffer is full.
42947 + UINT32 RxBulkAggEn:1; //Enable Rx Bulk Aggregation
42948 + UINT32 RxBulkEn:1; //Enable USB DMA Rx
42949 + UINT32 TxBulkEn:1; //Enable USB DMA Tx
42950 + UINT32 EpoutValid:6; //OUT endpoint data valid
42951 + UINT32 RxBusy:1; //USB DMA RX FSM busy
42952 + UINT32 TxBusy:1; //USB DMA TX FSM busy
42953 + } field;
42954 + UINT32 word;
42955 +} USB_DMA_CFG_STRUC, *PUSB_DMA_CFG_STRUC;
42956 +#endif
42957 +
42958 +//
42959 +// 3 PBF registers
42960 +//
42961 +//
42962 +// Most are for debug. Driver doesn't touch PBF register.
42963 +#define PBF_SYS_CTRL 0x0400
42964 +#define PBF_CFG 0x0408
42965 +#define PBF_MAX_PCNT 0x040C
42966 +#define PBF_CTRL 0x0410
42967 +#define PBF_INT_STA 0x0414
42968 +#define PBF_INT_ENA 0x0418
42969 +#define TXRXQ_PCNT 0x0438
42970 +#define PBF_DBG 0x043c
42971 +#define PBF_CAP_CTRL 0x0440
42972 +
42973 +//
42974 +// 4 MAC registers
42975 +//
42976 +//
42977 +// 4.1 MAC SYSTEM configuration registers (offset:0x1000)
42978 +//
42979 +#define MAC_CSR0 0x1000
42980 +#ifdef RT_BIG_ENDIAN
42981 +typedef union _ASIC_VER_ID_STRUC {
42982 + struct {
42983 + USHORT ASICVer; // version : 2860
42984 + USHORT ASICRev; // reversion : 0
42985 + } field;
42986 + UINT32 word;
42987 +} ASIC_VER_ID_STRUC, *PASIC_VER_ID_STRUC;
42988 +#else
42989 +typedef union _ASIC_VER_ID_STRUC {
42990 + struct {
42991 + USHORT ASICRev; // reversion : 0
42992 + USHORT ASICVer; // version : 2860
42993 + } field;
42994 + UINT32 word;
42995 +} ASIC_VER_ID_STRUC, *PASIC_VER_ID_STRUC;
42996 +#endif
42997 +#define MAC_SYS_CTRL 0x1004 //MAC_CSR1
42998 +#define MAC_ADDR_DW0 0x1008 // MAC ADDR DW0
42999 +#define MAC_ADDR_DW1 0x100c // MAC ADDR DW1
43000 +//
43001 +// MAC_CSR2: STA MAC register 0
43002 +//
43003 +#ifdef RT_BIG_ENDIAN
43004 +typedef union _MAC_DW0_STRUC {
43005 + struct {
43006 + UCHAR Byte3; // MAC address byte 3
43007 + UCHAR Byte2; // MAC address byte 2
43008 + UCHAR Byte1; // MAC address byte 1
43009 + UCHAR Byte0; // MAC address byte 0
43010 + } field;
43011 + UINT32 word;
43012 +} MAC_DW0_STRUC, *PMAC_DW0_STRUC;
43013 +#else
43014 +typedef union _MAC_DW0_STRUC {
43015 + struct {
43016 + UCHAR Byte0; // MAC address byte 0
43017 + UCHAR Byte1; // MAC address byte 1
43018 + UCHAR Byte2; // MAC address byte 2
43019 + UCHAR Byte3; // MAC address byte 3
43020 + } field;
43021 + UINT32 word;
43022 +} MAC_DW0_STRUC, *PMAC_DW0_STRUC;
43023 +#endif
43024 +
43025 +//
43026 +// MAC_CSR3: STA MAC register 1
43027 +//
43028 +#ifdef RT_BIG_ENDIAN
43029 +typedef union _MAC_DW1_STRUC {
43030 + struct {
43031 + UCHAR Rsvd1;
43032 + UCHAR U2MeMask;
43033 + UCHAR Byte5; // MAC address byte 5
43034 + UCHAR Byte4; // MAC address byte 4
43035 + } field;
43036 + UINT32 word;
43037 +} MAC_DW1_STRUC, *PMAC_DW1_STRUC;
43038 +#else
43039 +typedef union _MAC_DW1_STRUC {
43040 + struct {
43041 + UCHAR Byte4; // MAC address byte 4
43042 + UCHAR Byte5; // MAC address byte 5
43043 + UCHAR U2MeMask;
43044 + UCHAR Rsvd1;
43045 + } field;
43046 + UINT32 word;
43047 +} MAC_DW1_STRUC, *PMAC_DW1_STRUC;
43048 +#endif
43049 +
43050 +#define MAC_BSSID_DW0 0x1010 // MAC BSSID DW0
43051 +#define MAC_BSSID_DW1 0x1014 // MAC BSSID DW1
43052 +
43053 +//
43054 +// MAC_CSR5: BSSID register 1
43055 +//
43056 +#ifdef RT_BIG_ENDIAN
43057 +typedef union _MAC_CSR5_STRUC {
43058 + struct {
43059 + USHORT Rsvd:11;
43060 + USHORT MBssBcnNum:3;
43061 + USHORT BssIdMode:2; // 0: one BSSID, 10: 4 BSSID, 01: 2 BSSID , 11: 8BSSID
43062 + UCHAR Byte5; // BSSID byte 5
43063 + UCHAR Byte4; // BSSID byte 4
43064 + } field;
43065 + UINT32 word;
43066 +} MAC_CSR5_STRUC, *PMAC_CSR5_STRUC;
43067 +#else
43068 +typedef union _MAC_CSR5_STRUC {
43069 + struct {
43070 + UCHAR Byte4; // BSSID byte 4
43071 + UCHAR Byte5; // BSSID byte 5
43072 + USHORT BssIdMask:2; // 0: one BSSID, 10: 4 BSSID, 01: 2 BSSID , 11: 8BSSID
43073 + USHORT MBssBcnNum:3;
43074 + USHORT Rsvd:11;
43075 + } field;
43076 + UINT32 word;
43077 +} MAC_CSR5_STRUC, *PMAC_CSR5_STRUC;
43078 +#endif
43079 +
43080 +#define MAX_LEN_CFG 0x1018 // rt2860b max 16k bytes. bit12:13 Maximum PSDU length (power factor) 0:2^13, 1:2^14, 2:2^15, 3:2^16
43081 +#define BBP_CSR_CFG 0x101c //
43082 +//
43083 +// BBP_CSR_CFG: BBP serial control register
43084 +//
43085 +#ifdef RT_BIG_ENDIAN
43086 +typedef union _BBP_CSR_CFG_STRUC {
43087 + struct {
43088 + UINT32 :12;
43089 + UINT32 BBP_RW_MODE:1; // 0: use serial mode 1:parallel
43090 + UINT32 BBP_PAR_DUR:1; // 0: 4 MAC clock cycles 1: 8 MAC clock cycles
43091 + UINT32 Busy:1; // 1: ASIC is busy execute BBP programming.
43092 + UINT32 fRead:1; // 0: Write BBP, 1: Read BBP
43093 + UINT32 RegNum:8; // Selected BBP register
43094 + UINT32 Value:8; // Register value to program into BBP
43095 + } field;
43096 + UINT32 word;
43097 +} BBP_CSR_CFG_STRUC, *PBBP_CSR_CFG_STRUC;
43098 +#else
43099 +typedef union _BBP_CSR_CFG_STRUC {
43100 + struct {
43101 + UINT32 Value:8; // Register value to program into BBP
43102 + UINT32 RegNum:8; // Selected BBP register
43103 + UINT32 fRead:1; // 0: Write BBP, 1: Read BBP
43104 + UINT32 Busy:1; // 1: ASIC is busy execute BBP programming.
43105 + UINT32 BBP_PAR_DUR:1; // 0: 4 MAC clock cycles 1: 8 MAC clock cycles
43106 + UINT32 BBP_RW_MODE:1; // 0: use serial mode 1:parallel
43107 + UINT32 :12;
43108 + } field;
43109 + UINT32 word;
43110 +} BBP_CSR_CFG_STRUC, *PBBP_CSR_CFG_STRUC;
43111 +#endif
43112 +#define RF_CSR_CFG0 0x1020
43113 +//
43114 +// RF_CSR_CFG: RF control register
43115 +//
43116 +#ifdef RT_BIG_ENDIAN
43117 +typedef union _RF_CSR_CFG0_STRUC {
43118 + struct {
43119 + UINT32 Busy:1; // 0: idle 1: 8busy
43120 + UINT32 Sel:1; // 0:RF_LE0 activate 1:RF_LE1 activate
43121 + UINT32 StandbyMode:1; // 0: high when stand by 1: low when standby
43122 + UINT32 bitwidth:5; // Selected BBP register
43123 + UINT32 RegIdAndContent:24; // Register value to program into BBP
43124 + } field;
43125 + UINT32 word;
43126 +} RF_CSR_CFG0_STRUC, *PRF_CSR_CFG0_STRUC;
43127 +#else
43128 +typedef union _RF_CSR_CFG0_STRUC {
43129 + struct {
43130 + UINT32 RegIdAndContent:24; // Register value to program into BBP
43131 + UINT32 bitwidth:5; // Selected BBP register
43132 + UINT32 StandbyMode:1; // 0: high when stand by 1: low when standby
43133 + UINT32 Sel:1; // 0:RF_LE0 activate 1:RF_LE1 activate
43134 + UINT32 Busy:1; // 0: idle 1: 8busy
43135 + } field;
43136 + UINT32 word;
43137 +} RF_CSR_CFG0_STRUC, *PRF_CSR_CFG0_STRUC;
43138 +#endif
43139 +#define RF_CSR_CFG1 0x1024
43140 +#ifdef RT_BIG_ENDIAN
43141 +typedef union _RF_CSR_CFG1_STRUC {
43142 + struct {
43143 + UINT32 rsv:7; // 0: idle 1: 8busy
43144 + UINT32 RFGap:5; // Gap between BB_CONTROL_RF and RF_LE. 0: 3 system clock cycle (37.5usec) 1: 5 system clock cycle (62.5usec)
43145 + UINT32 RegIdAndContent:24; // Register value to program into BBP
43146 + } field;
43147 + UINT32 word;
43148 +} RF_CSR_CFG1_STRUC, *PRF_CSR_CFG1_STRUC;
43149 +#else
43150 +typedef union _RF_CSR_CFG1_STRUC {
43151 + struct {
43152 + UINT32 RegIdAndContent:24; // Register value to program into BBP
43153 + UINT32 RFGap:5; // Gap between BB_CONTROL_RF and RF_LE. 0: 3 system clock cycle (37.5usec) 1: 5 system clock cycle (62.5usec)
43154 + UINT32 rsv:7; // 0: idle 1: 8busy
43155 + } field;
43156 + UINT32 word;
43157 +} RF_CSR_CFG1_STRUC, *PRF_CSR_CFG1_STRUC;
43158 +#endif
43159 +#define RF_CSR_CFG2 0x1028 //
43160 +#ifdef RT_BIG_ENDIAN
43161 +typedef union _RF_CSR_CFG2_STRUC {
43162 + struct {
43163 + UINT32 rsv:8; // 0: idle 1: 8busy
43164 + UINT32 RegIdAndContent:24; // Register value to program into BBP
43165 + } field;
43166 + UINT32 word;
43167 +} RF_CSR_CFG2_STRUC, *PRF_CSR_CFG2_STRUC;
43168 +#else
43169 +typedef union _RF_CSR_CFG2_STRUC {
43170 + struct {
43171 + UINT32 RegIdAndContent:24; // Register value to program into BBP
43172 + UINT32 rsv:8; // 0: idle 1: 8busy
43173 + } field;
43174 + UINT32 word;
43175 +} RF_CSR_CFG2_STRUC, *PRF_CSR_CFG2_STRUC;
43176 +#endif
43177 +#define LED_CFG 0x102c // MAC_CSR14
43178 +#ifdef RT_BIG_ENDIAN
43179 +typedef union _LED_CFG_STRUC {
43180 + struct {
43181 + UINT32 :1;
43182 + UINT32 LedPolar:1; // Led Polarity. 0: active low1: active high
43183 + UINT32 YLedMode:2; // yellow Led Mode
43184 + UINT32 GLedMode:2; // green Led Mode
43185 + UINT32 RLedMode:2; // red Led Mode 0: off1: blinking upon TX2: periodic slow blinking3: always on
43186 + UINT32 rsv:2;
43187 + UINT32 SlowBlinkPeriod:6; // slow blinking period. unit:1ms
43188 + UINT32 OffPeriod:8; // blinking off period unit 1ms
43189 + UINT32 OnPeriod:8; // blinking on period unit 1ms
43190 + } field;
43191 + UINT32 word;
43192 +} LED_CFG_STRUC, *PLED_CFG_STRUC;
43193 +#else
43194 +typedef union _LED_CFG_STRUC {
43195 + struct {
43196 + UINT32 OnPeriod:8; // blinking on period unit 1ms
43197 + UINT32 OffPeriod:8; // blinking off period unit 1ms
43198 + UINT32 SlowBlinkPeriod:6; // slow blinking period. unit:1ms
43199 + UINT32 rsv:2;
43200 + UINT32 RLedMode:2; // red Led Mode 0: off1: blinking upon TX2: periodic slow blinking3: always on
43201 + UINT32 GLedMode:2; // green Led Mode
43202 + UINT32 YLedMode:2; // yellow Led Mode
43203 + UINT32 LedPolar:1; // Led Polarity. 0: active low1: active high
43204 + UINT32 :1;
43205 + } field;
43206 + UINT32 word;
43207 +} LED_CFG_STRUC, *PLED_CFG_STRUC;
43208 +#endif
43209 +//
43210 +// 4.2 MAC TIMING configuration registers (offset:0x1100)
43211 +//
43212 +#define XIFS_TIME_CFG 0x1100 // MAC_CSR8 MAC_CSR9
43213 +#ifdef RT_BIG_ENDIAN
43214 +typedef union _IFS_SLOT_CFG_STRUC {
43215 + struct {
43216 + UINT32 rsv:2;
43217 + UINT32 BBRxendEnable:1; // reference RXEND signal to begin XIFS defer
43218 + UINT32 EIFS:9; // unit 1us
43219 + UINT32 OfdmXifsTime:4; //OFDM SIFS. unit 1us. Applied after OFDM RX when MAC doesn't reference BBP signal BBRXEND
43220 + UINT32 OfdmSifsTime:8; // unit 1us. Applied after OFDM RX/TX
43221 + UINT32 CckmSifsTime:8; // unit 1us. Applied after CCK RX/TX
43222 + } field;
43223 + UINT32 word;
43224 +} IFS_SLOT_CFG_STRUC, *PIFS_SLOT_CFG_STRUC;
43225 +#else
43226 +typedef union _IFS_SLOT_CFG_STRUC {
43227 + struct {
43228 + UINT32 CckmSifsTime:8; // unit 1us. Applied after CCK RX/TX
43229 + UINT32 OfdmSifsTime:8; // unit 1us. Applied after OFDM RX/TX
43230 + UINT32 OfdmXifsTime:4; //OFDM SIFS. unit 1us. Applied after OFDM RX when MAC doesn't reference BBP signal BBRXEND
43231 + UINT32 EIFS:9; // unit 1us
43232 + UINT32 BBRxendEnable:1; // reference RXEND signal to begin XIFS defer
43233 + UINT32 rsv:2;
43234 + } field;
43235 + UINT32 word;
43236 +} IFS_SLOT_CFG_STRUC, *PIFS_SLOT_CFG_STRUC;
43237 +#endif
43238 +
43239 +#define BKOFF_SLOT_CFG 0x1104 // mac_csr9 last 8 bits
43240 +#define NAV_TIME_CFG 0x1108 // NAV (MAC_CSR15)
43241 +#define CH_TIME_CFG 0x110C // Count as channel busy
43242 +#define PBF_LIFE_TIMER 0x1110 //TX/RX MPDU timestamp timer (free run)Unit: 1us
43243 +#define BCN_TIME_CFG 0x1114 // TXRX_CSR9
43244 +
43245 +#define BCN_OFFSET0 0x042C
43246 +#define BCN_OFFSET1 0x0430
43247 +
43248 +//
43249 +// BCN_TIME_CFG : Synchronization control register
43250 +//
43251 +#ifdef RT_BIG_ENDIAN
43252 +typedef union _BCN_TIME_CFG_STRUC {
43253 + struct {
43254 + UINT32 TxTimestampCompensate:8;
43255 + UINT32 :3;
43256 + UINT32 bBeaconGen:1; // Enable beacon generator
43257 + UINT32 bTBTTEnable:1;
43258 + UINT32 TsfSyncMode:2; // Enable TSF sync, 00: disable, 01: infra mode, 10: ad-hoc mode
43259 + UINT32 bTsfTicking:1; // Enable TSF auto counting
43260 + UINT32 BeaconInterval:16; // in unit of 1/16 TU
43261 + } field;
43262 + UINT32 word;
43263 +} BCN_TIME_CFG_STRUC, *PBCN_TIME_CFG_STRUC;
43264 +#else
43265 +typedef union _BCN_TIME_CFG_STRUC {
43266 + struct {
43267 + UINT32 BeaconInterval:16; // in unit of 1/16 TU
43268 + UINT32 bTsfTicking:1; // Enable TSF auto counting
43269 + UINT32 TsfSyncMode:2; // Enable TSF sync, 00: disable, 01: infra mode, 10: ad-hoc mode
43270 + UINT32 bTBTTEnable:1;
43271 + UINT32 bBeaconGen:1; // Enable beacon generator
43272 + UINT32 :3;
43273 + UINT32 TxTimestampCompensate:8;
43274 + } field;
43275 + UINT32 word;
43276 +} BCN_TIME_CFG_STRUC, *PBCN_TIME_CFG_STRUC;
43277 +#endif
43278 +#define TBTT_SYNC_CFG 0x1118 // txrx_csr10
43279 +#define TSF_TIMER_DW0 0x111C // Local TSF timer lsb 32 bits. Read-only
43280 +#define TSF_TIMER_DW1 0x1120 // msb 32 bits. Read-only.
43281 +#define TBTT_TIMER 0x1124 // TImer remains till next TBTT. Read-only. TXRX_CSR14
43282 +#define INT_TIMER_CFG 0x1128 //
43283 +#define INT_TIMER_EN 0x112c // GP-timer and pre-tbtt Int enable
43284 +#define CH_IDLE_STA 0x1130 // channel idle time
43285 +#define CH_BUSY_STA 0x1134 // channle busy time
43286 +//
43287 +// 4.2 MAC POWER configuration registers (offset:0x1200)
43288 +//
43289 +#define MAC_STATUS_CFG 0x1200 // old MAC_CSR12
43290 +#define PWR_PIN_CFG 0x1204 // old MAC_CSR12
43291 +#define AUTO_WAKEUP_CFG 0x1208 // old MAC_CSR10
43292 +//
43293 +// AUTO_WAKEUP_CFG: Manual power control / status register
43294 +//
43295 +#ifdef RT_BIG_ENDIAN
43296 +typedef union _AUTO_WAKEUP_STRUC {
43297 + struct {
43298 + UINT32 :16;
43299 + UINT32 EnableAutoWakeup:1; // 0:sleep, 1:awake
43300 + UINT32 NumofSleepingTbtt:7; // ForceWake has high privilege than PutToSleep when both set
43301 + UINT32 AutoLeadTime:8;
43302 + } field;
43303 + UINT32 word;
43304 +} AUTO_WAKEUP_STRUC, *PAUTO_WAKEUP_STRUC;
43305 +#else
43306 +typedef union _AUTO_WAKEUP_STRUC {
43307 + struct {
43308 + UINT32 AutoLeadTime:8;
43309 + UINT32 NumofSleepingTbtt:7; // ForceWake has high privilege than PutToSleep when both set
43310 + UINT32 EnableAutoWakeup:1; // 0:sleep, 1:awake
43311 + UINT32 :16;
43312 + } field;
43313 + UINT32 word;
43314 +} AUTO_WAKEUP_STRUC, *PAUTO_WAKEUP_STRUC;
43315 +#endif
43316 +//
43317 +// 4.3 MAC TX configuration registers (offset:0x1300)
43318 +//
43319 +
43320 +#define EDCA_AC0_CFG 0x1300 //AC_TXOP_CSR0 0x3474
43321 +#define EDCA_AC1_CFG 0x1304
43322 +#define EDCA_AC2_CFG 0x1308
43323 +#define EDCA_AC3_CFG 0x130c
43324 +#ifdef RT_BIG_ENDIAN
43325 +typedef union _EDCA_AC_CFG_STRUC {
43326 + struct {
43327 + UINT32 :12; //
43328 + UINT32 Cwmax:4; //unit power of 2
43329 + UINT32 Cwmin:4; //
43330 + UINT32 Aifsn:4; // # of slot time
43331 + UINT32 AcTxop:8; // in unit of 32us
43332 + } field;
43333 + UINT32 word;
43334 +} EDCA_AC_CFG_STRUC, *PEDCA_AC_CFG_STRUC;
43335 +#else
43336 +typedef union _EDCA_AC_CFG_STRUC {
43337 + struct {
43338 + UINT32 AcTxop:8; // in unit of 32us
43339 + UINT32 Aifsn:4; // # of slot time
43340 + UINT32 Cwmin:4; //
43341 + UINT32 Cwmax:4; //unit power of 2
43342 + UINT32 :12; //
43343 + } field;
43344 + UINT32 word;
43345 +} EDCA_AC_CFG_STRUC, *PEDCA_AC_CFG_STRUC;
43346 +#endif
43347 +
43348 +#define EDCA_TID_AC_MAP 0x1310
43349 +#define TX_PWR_CFG_0 0x1314
43350 +#define TX_PWR_CFG_1 0x1318
43351 +#define TX_PWR_CFG_2 0x131C
43352 +#define TX_PWR_CFG_3 0x1320
43353 +#define TX_PWR_CFG_4 0x1324
43354 +#define TX_PIN_CFG 0x1328
43355 +#define TX_BAND_CFG 0x132c // 0x1 use upper 20MHz. 0 juse lower 20MHz
43356 +#define TX_SW_CFG0 0x1330
43357 +#define TX_SW_CFG1 0x1334
43358 +#define TX_SW_CFG2 0x1338
43359 +#define TXOP_THRES_CFG 0x133c
43360 +#define TXOP_CTRL_CFG 0x1340
43361 +#define TX_RTS_CFG 0x1344
43362 +
43363 +#ifdef RT_BIG_ENDIAN
43364 +typedef union _TX_RTS_CFG_STRUC {
43365 + struct {
43366 + UINT32 rsv:7;
43367 + UINT32 RtsFbkEn:1; // enable rts rate fallback
43368 + UINT32 RtsThres:16; // unit:byte
43369 + UINT32 AutoRtsRetryLimit:8;
43370 + } field;
43371 + UINT32 word;
43372 +} TX_RTS_CFG_STRUC, *PTX_RTS_CFG_STRUC;
43373 +#else
43374 +typedef union _TX_RTS_CFG_STRUC {
43375 + struct {
43376 + UINT32 AutoRtsRetryLimit:8;
43377 + UINT32 RtsThres:16; // unit:byte
43378 + UINT32 RtsFbkEn:1; // enable rts rate fallback
43379 + UINT32 rsv:7; // 1: HT non-STBC control frame enable
43380 + } field;
43381 + UINT32 word;
43382 +} TX_RTS_CFG_STRUC, *PTX_RTS_CFG_STRUC;
43383 +#endif
43384 +#define TX_TIMEOUT_CFG 0x1348
43385 +#ifdef RT_BIG_ENDIAN
43386 +typedef union _TX_TIMEOUT_CFG_STRUC {
43387 + struct {
43388 + UINT32 rsv2:8;
43389 + UINT32 TxopTimeout:8; //TXOP timeout value for TXOP truncation. It is recommended that (SLOT_TIME) > (TX_OP_TIMEOUT) > (RX_ACK_TIMEOUT)
43390 + UINT32 RxAckTimeout:8; // unit:slot. Used for TX precedure
43391 + UINT32 MpduLifeTime:4; // expiration time = 2^(9+MPDU LIFE TIME) us
43392 + UINT32 rsv:4;
43393 + } field;
43394 + UINT32 word;
43395 +} TX_TIMEOUT_CFG_STRUC, *PTX_TIMEOUT_CFG_STRUC;
43396 +#else
43397 +typedef union _TX_TIMEOUT_CFG_STRUC {
43398 + struct {
43399 + UINT32 rsv:4;
43400 + UINT32 MpduLifeTime:4; // expiration time = 2^(9+MPDU LIFE TIME) us
43401 + UINT32 RxAckTimeout:8; // unit:slot. Used for TX precedure
43402 + UINT32 TxopTimeout:8; //TXOP timeout value for TXOP truncation. It is recommended that (SLOT_TIME) > (TX_OP_TIMEOUT) > (RX_ACK_TIMEOUT)
43403 + UINT32 rsv2:8; // 1: HT non-STBC control frame enable
43404 + } field;
43405 + UINT32 word;
43406 +} TX_TIMEOUT_CFG_STRUC, *PTX_TIMEOUT_CFG_STRUC;
43407 +#endif
43408 +#define TX_RTY_CFG 0x134c
43409 +#ifdef RT_BIG_ENDIAN
43410 +typedef union PACKED _TX_RTY_CFG_STRUC {
43411 + struct {
43412 + UINT32 rsv:1;
43413 + UINT32 TxautoFBEnable:1; // Tx retry PHY rate auto fallback enable
43414 + UINT32 AggRtyMode:1; // Aggregate MPDU retry mode. 0:expired by retry limit, 1: expired by mpdu life timer
43415 + UINT32 NonAggRtyMode:1; // Non-Aggregate MPDU retry mode. 0:expired by retry limit, 1: expired by mpdu life timer
43416 + UINT32 LongRtyThre:12; // Long retry threshoold
43417 + UINT32 LongRtyLimit:8; //long retry limit
43418 + UINT32 ShortRtyLimit:8; // short retry limit
43419 +
43420 + } field;
43421 + UINT32 word;
43422 +} TX_RTY_CFG_STRUC, *PTX_RTY_CFG_STRUC;
43423 +#else
43424 +typedef union PACKED _TX_RTY_CFG_STRUC {
43425 + struct {
43426 + UINT32 ShortRtyLimit:8; // short retry limit
43427 + UINT32 LongRtyLimit:8; //long retry limit
43428 + UINT32 LongRtyThre:12; // Long retry threshoold
43429 + UINT32 NonAggRtyMode:1; // Non-Aggregate MPDU retry mode. 0:expired by retry limit, 1: expired by mpdu life timer
43430 + UINT32 AggRtyMode:1; // Aggregate MPDU retry mode. 0:expired by retry limit, 1: expired by mpdu life timer
43431 + UINT32 TxautoFBEnable:1; // Tx retry PHY rate auto fallback enable
43432 + UINT32 rsv:1; // 1: HT non-STBC control frame enable
43433 + } field;
43434 + UINT32 word;
43435 +} TX_RTY_CFG_STRUC, *PTX_RTY_CFG_STRUC;
43436 +#endif
43437 +#define TX_LINK_CFG 0x1350
43438 +#ifdef RT_BIG_ENDIAN
43439 +typedef union PACKED _TX_LINK_CFG_STRUC {
43440 + struct PACKED {
43441 + UINT32 RemotMFS:8; //remote MCS feedback sequence number
43442 + UINT32 RemotMFB:8; // remote MCS feedback
43443 + UINT32 rsv:3; //
43444 + UINT32 TxCFAckEn:1; // Piggyback CF-ACK enable
43445 + UINT32 TxRDGEn:1; // RDG TX enable
43446 + UINT32 TxMRQEn:1; // MCS request TX enable
43447 + UINT32 RemoteUMFSEnable:1; // remote unsolicit MFB enable. 0: not apply remote remote unsolicit (MFS=7)
43448 + UINT32 MFBEnable:1; // TX apply remote MFB 1:enable
43449 + UINT32 RemoteMFBLifeTime:8; //remote MFB life time. unit : 32us
43450 + } field;
43451 + UINT32 word;
43452 +} TX_LINK_CFG_STRUC, *PTX_LINK_CFG_STRUC;
43453 +#else
43454 +typedef union PACKED _TX_LINK_CFG_STRUC {
43455 + struct PACKED {
43456 + UINT32 RemoteMFBLifeTime:8; //remote MFB life time. unit : 32us
43457 + UINT32 MFBEnable:1; // TX apply remote MFB 1:enable
43458 + UINT32 RemoteUMFSEnable:1; // remote unsolicit MFB enable. 0: not apply remote remote unsolicit (MFS=7)
43459 + UINT32 TxMRQEn:1; // MCS request TX enable
43460 + UINT32 TxRDGEn:1; // RDG TX enable
43461 + UINT32 TxCFAckEn:1; // Piggyback CF-ACK enable
43462 + UINT32 rsv:3; //
43463 + UINT32 RemotMFB:8; // remote MCS feedback
43464 + UINT32 RemotMFS:8; //remote MCS feedback sequence number
43465 + } field;
43466 + UINT32 word;
43467 +} TX_LINK_CFG_STRUC, *PTX_LINK_CFG_STRUC;
43468 +#endif
43469 +#define HT_FBK_CFG0 0x1354
43470 +#ifdef RT_BIG_ENDIAN
43471 +typedef union PACKED _HT_FBK_CFG0_STRUC {
43472 + struct {
43473 + UINT32 HTMCS7FBK:4;
43474 + UINT32 HTMCS6FBK:4;
43475 + UINT32 HTMCS5FBK:4;
43476 + UINT32 HTMCS4FBK:4;
43477 + UINT32 HTMCS3FBK:4;
43478 + UINT32 HTMCS2FBK:4;
43479 + UINT32 HTMCS1FBK:4;
43480 + UINT32 HTMCS0FBK:4;
43481 + } field;
43482 + UINT32 word;
43483 +} HT_FBK_CFG0_STRUC, *PHT_FBK_CFG0_STRUC;
43484 +#else
43485 +typedef union PACKED _HT_FBK_CFG0_STRUC {
43486 + struct {
43487 + UINT32 HTMCS0FBK:4;
43488 + UINT32 HTMCS1FBK:4;
43489 + UINT32 HTMCS2FBK:4;
43490 + UINT32 HTMCS3FBK:4;
43491 + UINT32 HTMCS4FBK:4;
43492 + UINT32 HTMCS5FBK:4;
43493 + UINT32 HTMCS6FBK:4;
43494 + UINT32 HTMCS7FBK:4;
43495 + } field;
43496 + UINT32 word;
43497 +} HT_FBK_CFG0_STRUC, *PHT_FBK_CFG0_STRUC;
43498 +#endif
43499 +#define HT_FBK_CFG1 0x1358
43500 +#ifdef RT_BIG_ENDIAN
43501 +typedef union _HT_FBK_CFG1_STRUC {
43502 + struct {
43503 + UINT32 HTMCS15FBK:4;
43504 + UINT32 HTMCS14FBK:4;
43505 + UINT32 HTMCS13FBK:4;
43506 + UINT32 HTMCS12FBK:4;
43507 + UINT32 HTMCS11FBK:4;
43508 + UINT32 HTMCS10FBK:4;
43509 + UINT32 HTMCS9FBK:4;
43510 + UINT32 HTMCS8FBK:4;
43511 + } field;
43512 + UINT32 word;
43513 +} HT_FBK_CFG1_STRUC, *PHT_FBK_CFG1_STRUC;
43514 +#else
43515 +typedef union _HT_FBK_CFG1_STRUC {
43516 + struct {
43517 + UINT32 HTMCS8FBK:4;
43518 + UINT32 HTMCS9FBK:4;
43519 + UINT32 HTMCS10FBK:4;
43520 + UINT32 HTMCS11FBK:4;
43521 + UINT32 HTMCS12FBK:4;
43522 + UINT32 HTMCS13FBK:4;
43523 + UINT32 HTMCS14FBK:4;
43524 + UINT32 HTMCS15FBK:4;
43525 + } field;
43526 + UINT32 word;
43527 +} HT_FBK_CFG1_STRUC, *PHT_FBK_CFG1_STRUC;
43528 +#endif
43529 +#define LG_FBK_CFG0 0x135c
43530 +#ifdef RT_BIG_ENDIAN
43531 +typedef union _LG_FBK_CFG0_STRUC {
43532 + struct {
43533 + UINT32 OFDMMCS7FBK:4; //initial value is 6
43534 + UINT32 OFDMMCS6FBK:4; //initial value is 5
43535 + UINT32 OFDMMCS5FBK:4; //initial value is 4
43536 + UINT32 OFDMMCS4FBK:4; //initial value is 3
43537 + UINT32 OFDMMCS3FBK:4; //initial value is 2
43538 + UINT32 OFDMMCS2FBK:4; //initial value is 1
43539 + UINT32 OFDMMCS1FBK:4; //initial value is 0
43540 + UINT32 OFDMMCS0FBK:4; //initial value is 0
43541 + } field;
43542 + UINT32 word;
43543 +} LG_FBK_CFG0_STRUC, *PLG_FBK_CFG0_STRUC;
43544 +#else
43545 +typedef union _LG_FBK_CFG0_STRUC {
43546 + struct {
43547 + UINT32 OFDMMCS0FBK:4; //initial value is 0
43548 + UINT32 OFDMMCS1FBK:4; //initial value is 0
43549 + UINT32 OFDMMCS2FBK:4; //initial value is 1
43550 + UINT32 OFDMMCS3FBK:4; //initial value is 2
43551 + UINT32 OFDMMCS4FBK:4; //initial value is 3
43552 + UINT32 OFDMMCS5FBK:4; //initial value is 4
43553 + UINT32 OFDMMCS6FBK:4; //initial value is 5
43554 + UINT32 OFDMMCS7FBK:4; //initial value is 6
43555 + } field;
43556 + UINT32 word;
43557 +} LG_FBK_CFG0_STRUC, *PLG_FBK_CFG0_STRUC;
43558 +#endif
43559 +#define LG_FBK_CFG1 0x1360
43560 +#ifdef RT_BIG_ENDIAN
43561 +typedef union _LG_FBK_CFG1_STRUC {
43562 + struct {
43563 + UINT32 rsv:16;
43564 + UINT32 CCKMCS3FBK:4; //initial value is 2
43565 + UINT32 CCKMCS2FBK:4; //initial value is 1
43566 + UINT32 CCKMCS1FBK:4; //initial value is 0
43567 + UINT32 CCKMCS0FBK:4; //initial value is 0
43568 + } field;
43569 + UINT32 word;
43570 +} LG_FBK_CFG1_STRUC, *PLG_FBK_CFG1_STRUC;
43571 +#else
43572 +typedef union _LG_FBK_CFG1_STRUC {
43573 + struct {
43574 + UINT32 CCKMCS0FBK:4; //initial value is 0
43575 + UINT32 CCKMCS1FBK:4; //initial value is 0
43576 + UINT32 CCKMCS2FBK:4; //initial value is 1
43577 + UINT32 CCKMCS3FBK:4; //initial value is 2
43578 + UINT32 rsv:16;
43579 + } field;
43580 + UINT32 word;
43581 +} LG_FBK_CFG1_STRUC, *PLG_FBK_CFG1_STRUC;
43582 +#endif
43583 +
43584 +//=======================================================
43585 +//================ Protection Paramater================================
43586 +//=======================================================
43587 +#define CCK_PROT_CFG 0x1364 //CCK Protection
43588 +#define ASIC_SHORTNAV 1
43589 +#define ASIC_LONGNAV 2
43590 +#define ASIC_RTS 1
43591 +#define ASIC_CTS 2
43592 +#ifdef RT_BIG_ENDIAN
43593 +typedef union _PROT_CFG_STRUC {
43594 + struct {
43595 + UINT32 rsv:5;
43596 + UINT32 RTSThEn:1; //RTS threshold enable on CCK TX
43597 + UINT32 TxopAllowGF40:1; //CCK TXOP allowance.0:disallow.
43598 + UINT32 TxopAllowGF20:1; //CCK TXOP allowance.0:disallow.
43599 + UINT32 TxopAllowMM40:1; //CCK TXOP allowance.0:disallow.
43600 + UINT32 TxopAllowMM20:1; //CCK TXOP allowance. 0:disallow.
43601 + UINT32 TxopAllowOfdm:1; //CCK TXOP allowance.0:disallow.
43602 + UINT32 TxopAllowCck:1; //CCK TXOP allowance.0:disallow.
43603 + UINT32 ProtectNav:2; //TXOP protection type for CCK TX. 0:None, 1:ShortNAVprotect, 2:LongNAVProtect, 3:rsv
43604 + UINT32 ProtectCtrl:2; //Protection control frame type for CCK TX. 1:RTS/CTS, 2:CTS-to-self, 0:None, 3:rsv
43605 + UINT32 ProtectRate:16; //Protection control frame rate for CCK TX(RTS/CTS/CFEnd).
43606 + } field;
43607 + UINT32 word;
43608 +} PROT_CFG_STRUC, *PPROT_CFG_STRUC;
43609 +#else
43610 +typedef union _PROT_CFG_STRUC {
43611 + struct {
43612 + UINT32 ProtectRate:16; //Protection control frame rate for CCK TX(RTS/CTS/CFEnd).
43613 + UINT32 ProtectCtrl:2; //Protection control frame type for CCK TX. 1:RTS/CTS, 2:CTS-to-self, 0:None, 3:rsv
43614 + UINT32 ProtectNav:2; //TXOP protection type for CCK TX. 0:None, 1:ShortNAVprotect, 2:LongNAVProtect, 3:rsv
43615 + UINT32 TxopAllowCck:1; //CCK TXOP allowance.0:disallow.
43616 + UINT32 TxopAllowOfdm:1; //CCK TXOP allowance.0:disallow.
43617 + UINT32 TxopAllowMM20:1; //CCK TXOP allowance. 0:disallow.
43618 + UINT32 TxopAllowMM40:1; //CCK TXOP allowance.0:disallow.
43619 + UINT32 TxopAllowGF20:1; //CCK TXOP allowance.0:disallow.
43620 + UINT32 TxopAllowGF40:1; //CCK TXOP allowance.0:disallow.
43621 + UINT32 RTSThEn:1; //RTS threshold enable on CCK TX
43622 + UINT32 rsv:5;
43623 + } field;
43624 + UINT32 word;
43625 +} PROT_CFG_STRUC, *PPROT_CFG_STRUC;
43626 +#endif
43627 +
43628 +#define OFDM_PROT_CFG 0x1368 //OFDM Protection
43629 +#define MM20_PROT_CFG 0x136C //MM20 Protection
43630 +#define MM40_PROT_CFG 0x1370 //MM40 Protection
43631 +#define GF20_PROT_CFG 0x1374 //GF20 Protection
43632 +#define GF40_PROT_CFG 0x1378 //GR40 Protection
43633 +#define EXP_CTS_TIME 0x137C //
43634 +#define EXP_ACK_TIME 0x1380 //
43635 +
43636 +//
43637 +// 4.4 MAC RX configuration registers (offset:0x1400)
43638 +//
43639 +#define RX_FILTR_CFG 0x1400 //TXRX_CSR0
43640 +#define AUTO_RSP_CFG 0x1404 //TXRX_CSR4
43641 +//
43642 +// TXRX_CSR4: Auto-Responder/
43643 +//
43644 +#ifdef RT_BIG_ENDIAN
43645 +typedef union _AUTO_RSP_CFG_STRUC {
43646 + struct {
43647 + UINT32 :24;
43648 + UINT32 AckCtsPsmBit:1; // Power bit value in conrtrol frame
43649 + UINT32 DualCTSEn:1; // Power bit value in conrtrol frame
43650 + UINT32 rsv:1; // Power bit value in conrtrol frame
43651 + UINT32 AutoResponderPreamble:1; // 0:long, 1:short preamble
43652 + UINT32 CTS40MRef:1; // Response CTS 40MHz duplicate mode
43653 + UINT32 CTS40MMode:1; // Response CTS 40MHz duplicate mode
43654 + UINT32 BACAckPolicyEnable:1; // 0:long, 1:short preamble
43655 + UINT32 AutoResponderEnable:1;
43656 + } field;
43657 + UINT32 word;
43658 +} AUTO_RSP_CFG_STRUC, *PAUTO_RSP_CFG_STRUC;
43659 +#else
43660 +typedef union _AUTO_RSP_CFG_STRUC {
43661 + struct {
43662 + UINT32 AutoResponderEnable:1;
43663 + UINT32 BACAckPolicyEnable:1; // 0:long, 1:short preamble
43664 + UINT32 CTS40MMode:1; // Response CTS 40MHz duplicate mode
43665 + UINT32 CTS40MRef:1; // Response CTS 40MHz duplicate mode
43666 + UINT32 AutoResponderPreamble:1; // 0:long, 1:short preamble
43667 + UINT32 rsv:1; // Power bit value in conrtrol frame
43668 + UINT32 DualCTSEn:1; // Power bit value in conrtrol frame
43669 + UINT32 AckCtsPsmBit:1; // Power bit value in conrtrol frame
43670 + UINT32 :24;
43671 + } field;
43672 + UINT32 word;
43673 +} AUTO_RSP_CFG_STRUC, *PAUTO_RSP_CFG_STRUC;
43674 +#endif
43675 +
43676 +#define LEGACY_BASIC_RATE 0x1408 // TXRX_CSR5 0x3054
43677 +#define HT_BASIC_RATE 0x140c
43678 +#define HT_CTRL_CFG 0x1410
43679 +#define SIFS_COST_CFG 0x1414
43680 +#define RX_PARSER_CFG 0x1418 //Set NAV for all received frames
43681 +
43682 +//
43683 +// 4.5 MAC Security configuration (offset:0x1500)
43684 +//
43685 +#define TX_SEC_CNT0 0x1500 //
43686 +#define RX_SEC_CNT0 0x1504 //
43687 +#define CCMP_FC_MUTE 0x1508 //
43688 +//
43689 +// 4.6 HCCA/PSMP (offset:0x1600)
43690 +//
43691 +#define TXOP_HLDR_ADDR0 0x1600
43692 +#define TXOP_HLDR_ADDR1 0x1604
43693 +#define TXOP_HLDR_ET 0x1608
43694 +#define QOS_CFPOLL_RA_DW0 0x160c
43695 +#define QOS_CFPOLL_A1_DW1 0x1610
43696 +#define QOS_CFPOLL_QC 0x1614
43697 +//
43698 +// 4.7 MAC Statistis registers (offset:0x1700)
43699 +//
43700 +#define RX_STA_CNT0 0x1700 //
43701 +#define RX_STA_CNT1 0x1704 //
43702 +#define RX_STA_CNT2 0x1708 //
43703 +
43704 +//
43705 +// RX_STA_CNT0_STRUC: RX PLCP error count & RX CRC error count
43706 +//
43707 +#ifdef RT_BIG_ENDIAN
43708 +typedef union _RX_STA_CNT0_STRUC {
43709 + struct {
43710 + USHORT PhyErr;
43711 + USHORT CrcErr;
43712 + } field;
43713 + UINT32 word;
43714 +} RX_STA_CNT0_STRUC, *PRX_STA_CNT0_STRUC;
43715 +#else
43716 +typedef union _RX_STA_CNT0_STRUC {
43717 + struct {
43718 + USHORT CrcErr;
43719 + USHORT PhyErr;
43720 + } field;
43721 + UINT32 word;
43722 +} RX_STA_CNT0_STRUC, *PRX_STA_CNT0_STRUC;
43723 +#endif
43724 +
43725 +//
43726 +// RX_STA_CNT1_STRUC: RX False CCA count & RX LONG frame count
43727 +//
43728 +#ifdef RT_BIG_ENDIAN
43729 +typedef union _RX_STA_CNT1_STRUC {
43730 + struct {
43731 + USHORT PlcpErr;
43732 + USHORT FalseCca;
43733 + } field;
43734 + UINT32 word;
43735 +} RX_STA_CNT1_STRUC, *PRX_STA_CNT1_STRUC;
43736 +#else
43737 +typedef union _RX_STA_CNT1_STRUC {
43738 + struct {
43739 + USHORT FalseCca;
43740 + USHORT PlcpErr;
43741 + } field;
43742 + UINT32 word;
43743 +} RX_STA_CNT1_STRUC, *PRX_STA_CNT1_STRUC;
43744 +#endif
43745 +
43746 +//
43747 +// RX_STA_CNT2_STRUC:
43748 +//
43749 +#ifdef RT_BIG_ENDIAN
43750 +typedef union _RX_STA_CNT2_STRUC {
43751 + struct {
43752 + USHORT RxFifoOverflowCount;
43753 + USHORT RxDupliCount;
43754 + } field;
43755 + UINT32 word;
43756 +} RX_STA_CNT2_STRUC, *PRX_STA_CNT2_STRUC;
43757 +#else
43758 +typedef union _RX_STA_CNT2_STRUC {
43759 + struct {
43760 + USHORT RxDupliCount;
43761 + USHORT RxFifoOverflowCount;
43762 + } field;
43763 + UINT32 word;
43764 +} RX_STA_CNT2_STRUC, *PRX_STA_CNT2_STRUC;
43765 +#endif
43766 +#define TX_STA_CNT0 0x170C //
43767 +//
43768 +// STA_CSR3: TX Beacon count
43769 +//
43770 +#ifdef RT_BIG_ENDIAN
43771 +typedef union _TX_STA_CNT0_STRUC {
43772 + struct {
43773 + USHORT TxBeaconCount;
43774 + USHORT TxFailCount;
43775 + } field;
43776 + UINT32 word;
43777 +} TX_STA_CNT0_STRUC, *PTX_STA_CNT0_STRUC;
43778 +#else
43779 +typedef union _TX_STA_CNT0_STRUC {
43780 + struct {
43781 + USHORT TxFailCount;
43782 + USHORT TxBeaconCount;
43783 + } field;
43784 + UINT32 word;
43785 +} TX_STA_CNT0_STRUC, *PTX_STA_CNT0_STRUC;
43786 +#endif
43787 +#define TX_STA_CNT1 0x1710 //
43788 +//
43789 +// TX_STA_CNT1: TX tx count
43790 +//
43791 +#ifdef RT_BIG_ENDIAN
43792 +typedef union _TX_STA_CNT1_STRUC {
43793 + struct {
43794 + USHORT TxRetransmit;
43795 + USHORT TxSuccess;
43796 + } field;
43797 + UINT32 word;
43798 +} TX_STA_CNT1_STRUC, *PTX_STA_CNT1_STRUC;
43799 +#else
43800 +typedef union _TX_STA_CNT1_STRUC {
43801 + struct {
43802 + USHORT TxSuccess;
43803 + USHORT TxRetransmit;
43804 + } field;
43805 + UINT32 word;
43806 +} TX_STA_CNT1_STRUC, *PTX_STA_CNT1_STRUC;
43807 +#endif
43808 +#define TX_STA_CNT2 0x1714 //
43809 +//
43810 +// TX_STA_CNT2: TX tx count
43811 +//
43812 +#ifdef RT_BIG_ENDIAN
43813 +typedef union _TX_STA_CNT2_STRUC {
43814 + struct {
43815 + USHORT TxUnderFlowCount;
43816 + USHORT TxZeroLenCount;
43817 + } field;
43818 + UINT32 word;
43819 +} TX_STA_CNT2_STRUC, *PTX_STA_CNT2_STRUC;
43820 +#else
43821 +typedef union _TX_STA_CNT2_STRUC {
43822 + struct {
43823 + USHORT TxZeroLenCount;
43824 + USHORT TxUnderFlowCount;
43825 + } field;
43826 + UINT32 word;
43827 +} TX_STA_CNT2_STRUC, *PTX_STA_CNT2_STRUC;
43828 +#endif
43829 +#define TX_STA_FIFO 0x1718 //
43830 +//
43831 +// TX_STA_FIFO_STRUC: TX Result for specific PID status fifo register
43832 +//
43833 +#ifdef RT_BIG_ENDIAN
43834 +typedef union PACKED _TX_STA_FIFO_STRUC {
43835 + struct {
43836 + UINT32 Reserve:2;
43837 + UINT32 TxBF:1; // 3*3
43838 + UINT32 SuccessRate:13; //include MCS, mode ,shortGI, BW settingSame format as TXWI Word 0 Bit 31-16.
43839 +// UINT32 SuccessRate:16; //include MCS, mode ,shortGI, BW settingSame format as TXWI Word 0 Bit 31-16.
43840 + UINT32 wcid:8; //wireless client index
43841 + UINT32 TxAckRequired:1; // ack required
43842 + UINT32 TxAggre:1; // Tx is aggregated
43843 + UINT32 TxSuccess:1; // Tx success. whether success or not
43844 + UINT32 PidType:4;
43845 + UINT32 bValid:1; // 1:This register contains a valid TX result
43846 + } field;
43847 + UINT32 word;
43848 +} TX_STA_FIFO_STRUC, *PTX_STA_FIFO_STRUC;
43849 +#else
43850 +typedef union PACKED _TX_STA_FIFO_STRUC {
43851 + struct {
43852 + UINT32 bValid:1; // 1:This register contains a valid TX result
43853 + UINT32 PidType:4;
43854 + UINT32 TxSuccess:1; // Tx No retry success
43855 + UINT32 TxAggre:1; // Tx Retry Success
43856 + UINT32 TxAckRequired:1; // Tx fail
43857 + UINT32 wcid:8; //wireless client index
43858 +// UINT32 SuccessRate:16; //include MCS, mode ,shortGI, BW settingSame format as TXWI Word 0 Bit 31-16.
43859 + UINT32 SuccessRate:13; //include MCS, mode ,shortGI, BW settingSame format as TXWI Word 0 Bit 31-16.
43860 + UINT32 TxBF:1;
43861 + UINT32 Reserve:2;
43862 + } field;
43863 + UINT32 word;
43864 +} TX_STA_FIFO_STRUC, *PTX_STA_FIFO_STRUC;
43865 +#endif
43866 +// Debug counter
43867 +#define TX_AGG_CNT 0x171c
43868 +#ifdef RT_BIG_ENDIAN
43869 +typedef union _TX_AGG_CNT_STRUC {
43870 + struct {
43871 + USHORT AggTxCount;
43872 + USHORT NonAggTxCount;
43873 + } field;
43874 + UINT32 word;
43875 +} TX_AGG_CNT_STRUC, *PTX_AGG_CNT_STRUC;
43876 +#else
43877 +typedef union _TX_AGG_CNT_STRUC {
43878 + struct {
43879 + USHORT NonAggTxCount;
43880 + USHORT AggTxCount;
43881 + } field;
43882 + UINT32 word;
43883 +} TX_AGG_CNT_STRUC, *PTX_AGG_CNT_STRUC;
43884 +#endif
43885 +// Debug counter
43886 +#define TX_AGG_CNT0 0x1720
43887 +#ifdef RT_BIG_ENDIAN
43888 +typedef union _TX_AGG_CNT0_STRUC {
43889 + struct {
43890 + USHORT AggSize2Count;
43891 + USHORT AggSize1Count;
43892 + } field;
43893 + UINT32 word;
43894 +} TX_AGG_CNT0_STRUC, *PTX_AGG_CNT0_STRUC;
43895 +#else
43896 +typedef union _TX_AGG_CNT0_STRUC {
43897 + struct {
43898 + USHORT AggSize1Count;
43899 + USHORT AggSize2Count;
43900 + } field;
43901 + UINT32 word;
43902 +} TX_AGG_CNT0_STRUC, *PTX_AGG_CNT0_STRUC;
43903 +#endif
43904 +// Debug counter
43905 +#define TX_AGG_CNT1 0x1724
43906 +#ifdef RT_BIG_ENDIAN
43907 +typedef union _TX_AGG_CNT1_STRUC {
43908 + struct {
43909 + USHORT AggSize4Count;
43910 + USHORT AggSize3Count;
43911 + } field;
43912 + UINT32 word;
43913 +} TX_AGG_CNT1_STRUC, *PTX_AGG_CNT1_STRUC;
43914 +#else
43915 +typedef union _TX_AGG_CNT1_STRUC {
43916 + struct {
43917 + USHORT AggSize3Count;
43918 + USHORT AggSize4Count;
43919 + } field;
43920 + UINT32 word;
43921 +} TX_AGG_CNT1_STRUC, *PTX_AGG_CNT1_STRUC;
43922 +#endif
43923 +#define TX_AGG_CNT2 0x1728
43924 +#ifdef RT_BIG_ENDIAN
43925 +typedef union _TX_AGG_CNT2_STRUC {
43926 + struct {
43927 + USHORT AggSize6Count;
43928 + USHORT AggSize5Count;
43929 + } field;
43930 + UINT32 word;
43931 +} TX_AGG_CNT2_STRUC, *PTX_AGG_CNT2_STRUC;
43932 +#else
43933 +typedef union _TX_AGG_CNT2_STRUC {
43934 + struct {
43935 + USHORT AggSize5Count;
43936 + USHORT AggSize6Count;
43937 + } field;
43938 + UINT32 word;
43939 +} TX_AGG_CNT2_STRUC, *PTX_AGG_CNT2_STRUC;
43940 +#endif
43941 +// Debug counter
43942 +#define TX_AGG_CNT3 0x172c
43943 +#ifdef RT_BIG_ENDIAN
43944 +typedef union _TX_AGG_CNT3_STRUC {
43945 + struct {
43946 + USHORT AggSize8Count;
43947 + USHORT AggSize7Count;
43948 + } field;
43949 + UINT32 word;
43950 +} TX_AGG_CNT3_STRUC, *PTX_AGG_CNT3_STRUC;
43951 +#else
43952 +typedef union _TX_AGG_CNT3_STRUC {
43953 + struct {
43954 + USHORT AggSize7Count;
43955 + USHORT AggSize8Count;
43956 + } field;
43957 + UINT32 word;
43958 +} TX_AGG_CNT3_STRUC, *PTX_AGG_CNT3_STRUC;
43959 +#endif
43960 +// Debug counter
43961 +#define TX_AGG_CNT4 0x1730
43962 +#ifdef RT_BIG_ENDIAN
43963 +typedef union _TX_AGG_CNT4_STRUC {
43964 + struct {
43965 + USHORT AggSize10Count;
43966 + USHORT AggSize9Count;
43967 + } field;
43968 + UINT32 word;
43969 +} TX_AGG_CNT4_STRUC, *PTX_AGG_CNT4_STRUC;
43970 +#else
43971 +typedef union _TX_AGG_CNT4_STRUC {
43972 + struct {
43973 + USHORT AggSize9Count;
43974 + USHORT AggSize10Count;
43975 + } field;
43976 + UINT32 word;
43977 +} TX_AGG_CNT4_STRUC, *PTX_AGG_CNT4_STRUC;
43978 +#endif
43979 +#define TX_AGG_CNT5 0x1734
43980 +#ifdef RT_BIG_ENDIAN
43981 +typedef union _TX_AGG_CNT5_STRUC {
43982 + struct {
43983 + USHORT AggSize12Count;
43984 + USHORT AggSize11Count;
43985 + } field;
43986 + UINT32 word;
43987 +} TX_AGG_CNT5_STRUC, *PTX_AGG_CNT5_STRUC;
43988 +#else
43989 +typedef union _TX_AGG_CNT5_STRUC {
43990 + struct {
43991 + USHORT AggSize11Count;
43992 + USHORT AggSize12Count;
43993 + } field;
43994 + UINT32 word;
43995 +} TX_AGG_CNT5_STRUC, *PTX_AGG_CNT5_STRUC;
43996 +#endif
43997 +#define TX_AGG_CNT6 0x1738
43998 +#ifdef RT_BIG_ENDIAN
43999 +typedef union _TX_AGG_CNT6_STRUC {
44000 + struct {
44001 + USHORT AggSize14Count;
44002 + USHORT AggSize13Count;
44003 + } field;
44004 + UINT32 word;
44005 +} TX_AGG_CNT6_STRUC, *PTX_AGG_CNT6_STRUC;
44006 +#else
44007 +typedef union _TX_AGG_CNT6_STRUC {
44008 + struct {
44009 + USHORT AggSize13Count;
44010 + USHORT AggSize14Count;
44011 + } field;
44012 + UINT32 word;
44013 +} TX_AGG_CNT6_STRUC, *PTX_AGG_CNT6_STRUC;
44014 +#endif
44015 +#define TX_AGG_CNT7 0x173c
44016 +#ifdef RT_BIG_ENDIAN
44017 +typedef union _TX_AGG_CNT7_STRUC {
44018 + struct {
44019 + USHORT AggSize16Count;
44020 + USHORT AggSize15Count;
44021 + } field;
44022 + UINT32 word;
44023 +} TX_AGG_CNT7_STRUC, *PTX_AGG_CNT7_STRUC;
44024 +#else
44025 +typedef union _TX_AGG_CNT7_STRUC {
44026 + struct {
44027 + USHORT AggSize15Count;
44028 + USHORT AggSize16Count;
44029 + } field;
44030 + UINT32 word;
44031 +} TX_AGG_CNT7_STRUC, *PTX_AGG_CNT7_STRUC;
44032 +#endif
44033 +#define MPDU_DENSITY_CNT 0x1740
44034 +#ifdef RT_BIG_ENDIAN
44035 +typedef union _MPDU_DEN_CNT_STRUC {
44036 + struct {
44037 + USHORT RXZeroDelCount; //RX zero length delimiter count
44038 + USHORT TXZeroDelCount; //TX zero length delimiter count
44039 + } field;
44040 + UINT32 word;
44041 +} MPDU_DEN_CNT_STRUC, *PMPDU_DEN_CNT_STRUC;
44042 +#else
44043 +typedef union _MPDU_DEN_CNT_STRUC {
44044 + struct {
44045 + USHORT TXZeroDelCount; //TX zero length delimiter count
44046 + USHORT RXZeroDelCount; //RX zero length delimiter count
44047 + } field;
44048 + UINT32 word;
44049 +} MPDU_DEN_CNT_STRUC, *PMPDU_DEN_CNT_STRUC;
44050 +#endif
44051 +//
44052 +// TXRX control registers - base address 0x3000
44053 +//
44054 +// rt2860b UNKNOWN reg use R/O Reg Addr 0x77d0 first..
44055 +#define TXRX_CSR1 0x77d0
44056 +
44057 +//
44058 +// Security key table memory, base address = 0x1000
44059 +//
44060 +#define MAC_WCID_BASE 0x1800 //8-bytes(use only 6-bytes) * 256 entry =
44061 +#define HW_WCID_ENTRY_SIZE 8
44062 +#define PAIRWISE_KEY_TABLE_BASE 0x4000 // 32-byte * 256-entry = -byte
44063 +#define HW_KEY_ENTRY_SIZE 0x20
44064 +#define PAIRWISE_IVEIV_TABLE_BASE 0x6000 // 8-byte * 256-entry = -byte
44065 +#define MAC_IVEIV_TABLE_BASE 0x6000 // 8-byte * 256-entry = -byte
44066 +#define HW_IVEIV_ENTRY_SIZE 8
44067 +#define MAC_WCID_ATTRIBUTE_BASE 0x6800 // 4-byte * 256-entry = -byte
44068 +#define HW_WCID_ATTRI_SIZE 4
44069 +#define WCID_RESERVED 0x6bfc
44070 +#define SHARED_KEY_TABLE_BASE 0x6c00 // 32-byte * 16-entry = 512-byte
44071 +#define SHARED_KEY_MODE_BASE 0x7000 // 32-byte * 16-entry = 512-byte
44072 +#define HW_SHARED_KEY_MODE_SIZE 4
44073 +#define SHAREDKEYTABLE 0
44074 +#define PAIRWISEKEYTABLE 1
44075 +
44076 +
44077 +#ifdef RT_BIG_ENDIAN
44078 +typedef union _SHAREDKEY_MODE_STRUC {
44079 + struct {
44080 + UINT32 :1;
44081 + UINT32 Bss1Key3CipherAlg:3;
44082 + UINT32 :1;
44083 + UINT32 Bss1Key2CipherAlg:3;
44084 + UINT32 :1;
44085 + UINT32 Bss1Key1CipherAlg:3;
44086 + UINT32 :1;
44087 + UINT32 Bss1Key0CipherAlg:3;
44088 + UINT32 :1;
44089 + UINT32 Bss0Key3CipherAlg:3;
44090 + UINT32 :1;
44091 + UINT32 Bss0Key2CipherAlg:3;
44092 + UINT32 :1;
44093 + UINT32 Bss0Key1CipherAlg:3;
44094 + UINT32 :1;
44095 + UINT32 Bss0Key0CipherAlg:3;
44096 + } field;
44097 + UINT32 word;
44098 +} SHAREDKEY_MODE_STRUC, *PSHAREDKEY_MODE_STRUC;
44099 +#else
44100 +typedef union _SHAREDKEY_MODE_STRUC {
44101 + struct {
44102 + UINT32 Bss0Key0CipherAlg:3;
44103 + UINT32 :1;
44104 + UINT32 Bss0Key1CipherAlg:3;
44105 + UINT32 :1;
44106 + UINT32 Bss0Key2CipherAlg:3;
44107 + UINT32 :1;
44108 + UINT32 Bss0Key3CipherAlg:3;
44109 + UINT32 :1;
44110 + UINT32 Bss1Key0CipherAlg:3;
44111 + UINT32 :1;
44112 + UINT32 Bss1Key1CipherAlg:3;
44113 + UINT32 :1;
44114 + UINT32 Bss1Key2CipherAlg:3;
44115 + UINT32 :1;
44116 + UINT32 Bss1Key3CipherAlg:3;
44117 + UINT32 :1;
44118 + } field;
44119 + UINT32 word;
44120 +} SHAREDKEY_MODE_STRUC, *PSHAREDKEY_MODE_STRUC;
44121 +#endif
44122 +// 64-entry for pairwise key table
44123 +typedef struct _HW_WCID_ENTRY { // 8-byte per entry
44124 + UCHAR Address[6];
44125 + UCHAR Rsv[2];
44126 +} HW_WCID_ENTRY, PHW_WCID_ENTRY;
44127 +
44128 +
44129 +
44130 +//
44131 +// Other on-chip shared memory space, base = 0x2000
44132 +//
44133 +
44134 +// CIS space - base address = 0x2000
44135 +#define HW_CIS_BASE 0x2000
44136 +
44137 +// Carrier-sense CTS frame base address. It's where mac stores carrier-sense frame for carrier-sense function.
44138 +#define HW_CS_CTS_BASE 0x7700
44139 +// DFS CTS frame base address. It's where mac stores CTS frame for DFS.
44140 +#define HW_DFS_CTS_BASE 0x7780
44141 +#define HW_CTS_FRAME_SIZE 0x80
44142 +
44143 +// 2004-11-08 john - since NULL frame won't be that long (256 byte). We steal 16 tail bytes
44144 +// to save debugging settings
44145 +#define HW_DEBUG_SETTING_BASE 0x77f0 // 0x77f0~0x77ff total 16 bytes
44146 +#define HW_DEBUG_SETTING_BASE2 0x7770 // 0x77f0~0x77ff total 16 bytes
44147 +
44148 +// In order to support maximum 8 MBSS and its maximum length is 512 for each beacon
44149 +// Three section discontinue memory segments will be used.
44150 +// 1. The original region for BCN 0~3
44151 +// 2. Extract memory from FCE table for BCN 4~5
44152 +// 3. Extract memory from Pair-wise key table for BCN 6~7
44153 +// It occupied those memory of wcid 238~253 for BCN 6
44154 +// and wcid 222~237 for BCN 7
44155 +#define HW_BEACON_MAX_SIZE 0x1000 /* unit: byte */
44156 +#define HW_BEACON_BASE0 0x7800
44157 +#define HW_BEACON_BASE1 0x7A00
44158 +#define HW_BEACON_BASE2 0x7C00
44159 +#define HW_BEACON_BASE3 0x7E00
44160 +#define HW_BEACON_BASE4 0x7200
44161 +#define HW_BEACON_BASE5 0x7400
44162 +#define HW_BEACON_BASE6 0x5DC0
44163 +#define HW_BEACON_BASE7 0x5BC0
44164 +
44165 +#define HW_BEACON_MAX_COUNT 8
44166 +#define HW_BEACON_OFFSET 0x0200
44167 +#define HW_BEACON_CONTENT_LEN (HW_BEACON_OFFSET - TXWI_SIZE)
44168 +
44169 +// HOST-MCU shared memory - base address = 0x2100
44170 +#define HOST_CMD_CSR 0x404
44171 +#define H2M_MAILBOX_CSR 0x7010
44172 +#define H2M_MAILBOX_CID 0x7014
44173 +#define H2M_MAILBOX_STATUS 0x701c
44174 +#define H2M_INT_SRC 0x7024
44175 +#define H2M_BBP_AGENT 0x7028
44176 +#define M2H_CMD_DONE_CSR 0x000c
44177 +#define MCU_TXOP_ARRAY_BASE 0x000c // TODO: to be provided by Albert
44178 +#define MCU_TXOP_ENTRY_SIZE 32 // TODO: to be provided by Albert
44179 +#define MAX_NUM_OF_TXOP_ENTRY 16 // TODO: must be same with 8051 firmware
44180 +#define MCU_MBOX_VERSION 0x01 // TODO: to be confirmed by Albert
44181 +#define MCU_MBOX_VERSION_OFFSET 5 // TODO: to be provided by Albert
44182 +
44183 +//
44184 +// Host DMA registers - base address 0x200 . TX0-3=EDCAQid0-3, TX4=HCCA, TX5=MGMT,
44185 +//
44186 +//
44187 +// DMA RING DESCRIPTOR
44188 +//
44189 +#define E2PROM_CSR 0x0004
44190 +#define IO_CNTL_CSR 0x77d0
44191 +
44192 +#ifdef RT2860
44193 +// 8051 firmware image for RT2860 - base address = 0x4000
44194 +#define FIRMWARE_IMAGE_BASE 0x2000
44195 +#define MAX_FIRMWARE_IMAGE_SIZE 0x2000 // 8kbyte
44196 +#endif // RT2860 //
44197 +
44198 +
44199 +// ================================================================
44200 +// Tx / Rx / Mgmt ring descriptor definition
44201 +// ================================================================
44202 +
44203 +// the following PID values are used to mark outgoing frame type in TXD->PID so that
44204 +// proper TX statistics can be collected based on these categories
44205 +// b3-2 of PID field -
44206 +#define PID_MGMT 0x05
44207 +#define PID_BEACON 0x0c
44208 +#define PID_DATA_NORMALUCAST 0x02
44209 +#define PID_DATA_AMPDU 0x04
44210 +#define PID_DATA_NO_ACK 0x08
44211 +#define PID_DATA_NOT_NORM_ACK 0x03
44212 +// value domain of pTxD->HostQId (4-bit: 0~15)
44213 +#define QID_AC_BK 1 // meet ACI definition in 802.11e
44214 +#define QID_AC_BE 0 // meet ACI definition in 802.11e
44215 +#define QID_AC_VI 2
44216 +#define QID_AC_VO 3
44217 +#define QID_HCCA 4
44218 +#define NUM_OF_TX_RING 5
44219 +#define QID_MGMT 13
44220 +#define QID_RX 14
44221 +#define QID_OTHER 15
44222 +
44223 +
44224 +// ------------------------------------------------------
44225 +// BBP & RF definition
44226 +// ------------------------------------------------------
44227 +#define BUSY 1
44228 +#define IDLE 0
44229 +
44230 +#define RF_R00 0
44231 +#define RF_R01 1
44232 +#define RF_R02 2
44233 +#define RF_R03 3
44234 +#define RF_R04 4
44235 +#define RF_R05 5
44236 +#define RF_R06 6
44237 +#define RF_R07 7
44238 +#define RF_R08 8
44239 +#define RF_R09 9
44240 +#define RF_R10 10
44241 +#define RF_R11 11
44242 +#define RF_R12 12
44243 +#define RF_R13 13
44244 +#define RF_R14 14
44245 +#define RF_R15 15
44246 +#define RF_R16 16
44247 +#define RF_R17 17
44248 +#define RF_R18 18
44249 +#define RF_R19 19
44250 +#define RF_R20 20
44251 +#define RF_R21 21
44252 +#define RF_R22 22
44253 +#define RF_R23 23
44254 +#define RF_R24 24
44255 +#define RF_R25 25
44256 +#define RF_R26 26
44257 +#define RF_R27 27
44258 +#define RF_R28 28
44259 +#define RF_R29 29
44260 +#define RF_R30 30
44261 +#define RF_R31 31
44262 +
44263 +#define BBP_R0 0 // version
44264 +#define BBP_R1 1 // TSSI
44265 +#define BBP_R2 2 // TX configure
44266 +#define BBP_R3 3
44267 +#define BBP_R4 4
44268 +#define BBP_R5 5
44269 +#define BBP_R6 6
44270 +#define BBP_R14 14 // RX configure
44271 +#define BBP_R16 16
44272 +#define BBP_R17 17 // RX sensibility
44273 +#define BBP_R18 18
44274 +#define BBP_R21 21
44275 +#define BBP_R22 22
44276 +#define BBP_R24 24
44277 +#define BBP_R25 25
44278 +#define BBP_R49 49 //TSSI
44279 +#define BBP_R50 50
44280 +#define BBP_R51 51
44281 +#define BBP_R52 52
44282 +#define BBP_R55 55
44283 +#define BBP_R62 62 // Rx SQ0 Threshold HIGH
44284 +#define BBP_R63 63
44285 +#define BBP_R64 64
44286 +#define BBP_R65 65
44287 +#define BBP_R66 66
44288 +#define BBP_R67 67
44289 +#define BBP_R68 68
44290 +#define BBP_R69 69
44291 +#define BBP_R70 70 // Rx AGC SQ CCK Xcorr threshold
44292 +#define BBP_R73 73
44293 +#define BBP_R75 75
44294 +#define BBP_R77 77
44295 +#define BBP_R81 81
44296 +#define BBP_R82 82
44297 +#define BBP_R83 83
44298 +#define BBP_R84 84
44299 +#define BBP_R86 86
44300 +#define BBP_R91 91
44301 +#define BBP_R92 92
44302 +#define BBP_R94 94 // Tx Gain Control
44303 +#define BBP_R103 103
44304 +#define BBP_R105 105
44305 +#define BBP_R113 113
44306 +#define BBP_R114 114
44307 +#define BBP_R115 115
44308 +#define BBP_R116 116
44309 +#define BBP_R117 117
44310 +#define BBP_R118 118
44311 +#define BBP_R119 119
44312 +#define BBP_R120 120
44313 +#define BBP_R121 121
44314 +#define BBP_R122 122
44315 +#define BBP_R123 123
44316 +
44317 +
44318 +#define BBPR94_DEFAULT 0x06 // Add 1 value will gain 1db
44319 +
44320 +#define RSSI_FOR_VERY_LOW_SENSIBILITY -35
44321 +#define RSSI_FOR_LOW_SENSIBILITY -58
44322 +#define RSSI_FOR_MID_LOW_SENSIBILITY -80
44323 +#define RSSI_FOR_MID_SENSIBILITY -90
44324 +
44325 +//-------------------------------------------------------------------------
44326 +// EEPROM definition
44327 +//-------------------------------------------------------------------------
44328 +#define EEDO 0x08
44329 +#define EEDI 0x04
44330 +#define EECS 0x02
44331 +#define EESK 0x01
44332 +#define EERL 0x80
44333 +
44334 +#define EEPROM_WRITE_OPCODE 0x05
44335 +#define EEPROM_READ_OPCODE 0x06
44336 +#define EEPROM_EWDS_OPCODE 0x10
44337 +#define EEPROM_EWEN_OPCODE 0x13
44338 +
44339 +#define NUM_EEPROM_BBP_PARMS 19 // Include NIC Config 0, 1, CR, TX ALC step, BBPs
44340 +#define NUM_EEPROM_TX_G_PARMS 7
44341 +#define EEPROM_NIC1_OFFSET 0x34 // The address is from NIC config 0, not BBP register ID
44342 +#define EEPROM_NIC2_OFFSET 0x36 // The address is from NIC config 0, not BBP register ID
44343 +#define EEPROM_BBP_BASE_OFFSET 0xf0 // The address is from NIC config 0, not BBP register ID
44344 +#define EEPROM_G_TX_PWR_OFFSET 0x52
44345 +#define EEPROM_G_TX2_PWR_OFFSET 0x60
44346 +#define EEPROM_LED1_OFFSET 0x3c
44347 +#define EEPROM_LED2_OFFSET 0x3e
44348 +#define EEPROM_LED3_OFFSET 0x40
44349 +#define EEPROM_LNA_OFFSET 0x44
44350 +#define EEPROM_RSSI_BG_OFFSET 0x46
44351 +#define EEPROM_RSSI_A_OFFSET 0x4a
44352 +#define EEPROM_DEFINE_MAX_TXPWR 0x4e
44353 +#define EEPROM_TXPOWER_BYRATE_20MHZ_2_4G 0xde // 20MHZ 2.4G tx power.
44354 +#define EEPROM_TXPOWER_BYRATE_40MHZ_2_4G 0xee // 40MHZ 2.4G tx power.
44355 +#define EEPROM_TXPOWER_BYRATE_20MHZ_5G 0xfa // 20MHZ 5G tx power.
44356 +#define EEPROM_TXPOWER_BYRATE_40MHZ_5G 0x10a // 40MHZ 5G tx power.
44357 +#define EEPROM_A_TX_PWR_OFFSET 0x78
44358 +#define EEPROM_A_TX2_PWR_OFFSET 0xa6
44359 +#define EEPROM_VERSION_OFFSET 0x02
44360 +#define EEPROM_FREQ_OFFSET 0x3a
44361 +#define EEPROM_TXPOWER_BYRATE 0xde // 20MHZ power.
44362 +#define EEPROM_TXPOWER_DELTA 0x50 // 20MHZ AND 40 MHZ use different power. This is delta in 40MHZ.
44363 +#define VALID_EEPROM_VERSION 1
44364 +
44365 +// PairKeyMode definition
44366 +#define PKMODE_NONE 0
44367 +#define PKMODE_WEP64 1
44368 +#define PKMODE_WEP128 2
44369 +#define PKMODE_TKIP 3
44370 +#define PKMODE_AES 4
44371 +#define PKMODE_CKIP64 5
44372 +#define PKMODE_CKIP128 6
44373 +#define PKMODE_TKIP_NO_MIC 7 // MIC appended by driver: not a valid value in hardware key table
44374 +
44375 +// =================================================================================
44376 +// WCID format
44377 +// =================================================================================
44378 +//7.1 WCID ENTRY format : 8bytes
44379 +typedef struct _WCID_ENTRY_STRUC {
44380 + UCHAR RXBABitmap7; // bit0 for TID8, bit7 for TID 15
44381 + UCHAR RXBABitmap0; // bit0 for TID0, bit7 for TID 7
44382 + UCHAR MAC[6]; // 0 for shared key table. 1 for pairwise key table
44383 +} WCID_ENTRY_STRUC, *PWCID_ENTRY_STRUC;
44384 +
44385 +//8.1.1 SECURITY KEY format : 8DW
44386 +// 32-byte per entry, total 16-entry for shared key table, 64-entry for pairwise key table
44387 +typedef struct _HW_KEY_ENTRY { // 32-byte per entry
44388 + UCHAR Key[16];
44389 + UCHAR TxMic[8];
44390 + UCHAR RxMic[8];
44391 +} HW_KEY_ENTRY, *PHW_KEY_ENTRY;
44392 +
44393 +//8.1.2 IV/EIV format : 2DW
44394 +
44395 +//8.1.3 RX attribute entry format : 1DW
44396 +#ifdef RT_BIG_ENDIAN
44397 +typedef struct _MAC_ATTRIBUTE_STRUC {
44398 + UINT32 rsv:22;
44399 + UINT32 RXWIUDF:3;
44400 + UINT32 BSSIDIdx:3; //multipleBSS index for the WCID
44401 + UINT32 PairKeyMode:3;
44402 + UINT32 KeyTab:1; // 0 for shared key table. 1 for pairwise key table
44403 +} MAC_ATTRIBUTE_STRUC, *PMAC_ATTRIBUTE_STRUC;
44404 +#else
44405 +typedef struct _MAC_ATTRIBUTE_STRUC {
44406 + UINT32 KeyTab:1; // 0 for shared key table. 1 for pairwise key table
44407 + UINT32 PairKeyMode:3;
44408 + UINT32 BSSIDIdx:3; //multipleBSS index for the WCID
44409 + UINT32 RXWIUDF:3;
44410 + UINT32 rsv:22;
44411 +} MAC_ATTRIBUTE_STRUC, *PMAC_ATTRIBUTE_STRUC;
44412 +#endif
44413 +
44414 +
44415 +// =================================================================================
44416 +// TX / RX ring descriptor format
44417 +// =================================================================================
44418 +
44419 +// the first 24-byte in TXD is called TXINFO and will be DMAed to MAC block through TXFIFO.
44420 +// MAC block use this TXINFO to control the transmission behavior of this frame.
44421 +#define FIFO_MGMT 0
44422 +#define FIFO_HCCA 1
44423 +#define FIFO_EDCA 2
44424 +
44425 +//
44426 +// TX descriptor format, Tx ring, Mgmt Ring
44427 +//
44428 +#ifdef RT_BIG_ENDIAN
44429 +typedef struct PACKED _TXD_STRUC {
44430 + // Word 0
44431 + UINT32 SDPtr0;
44432 + // Word 1
44433 + UINT32 DMADONE:1;
44434 + UINT32 LastSec0:1;
44435 + UINT32 SDLen0:14;
44436 + UINT32 Burst:1;
44437 + UINT32 LastSec1:1;
44438 + UINT32 SDLen1:14;
44439 + // Word 2
44440 + UINT32 SDPtr1;
44441 + // Word 3
44442 + UINT32 ICO:1;
44443 + UINT32 UCO:1;
44444 + UINT32 TCO:1;
44445 + UINT32 rsv:2;
44446 + UINT32 QSEL:2; // select on-chip FIFO ID for 2nd-stage output scheduler.0:MGMT, 1:HCCA 2:EDCA
44447 + UINT32 WIV:1; // Wireless Info Valid. 1 if Driver already fill WI, o if DMA needs to copy WI to correctposition
44448 + UINT32 rsv2:24;
44449 +} TXD_STRUC, *PTXD_STRUC;
44450 +#else
44451 +typedef struct PACKED _TXD_STRUC {
44452 + // Word 0
44453 + UINT32 SDPtr0;
44454 + // Word 1
44455 + UINT32 SDLen1:14;
44456 + UINT32 LastSec1:1;
44457 + UINT32 Burst:1;
44458 + UINT32 SDLen0:14;
44459 + UINT32 LastSec0:1;
44460 + UINT32 DMADONE:1;
44461 + //Word2
44462 + UINT32 SDPtr1;
44463 + //Word3
44464 + UINT32 rsv2:24;
44465 + UINT32 WIV:1; // Wireless Info Valid. 1 if Driver already fill WI, o if DMA needs to copy WI to correctposition
44466 + UINT32 QSEL:2; // select on-chip FIFO ID for 2nd-stage output scheduler.0:MGMT, 1:HCCA 2:EDCA
44467 + UINT32 rsv:2;
44468 + UINT32 TCO:1; //
44469 + UINT32 UCO:1; //
44470 + UINT32 ICO:1; //
44471 +} TXD_STRUC, *PTXD_STRUC;
44472 +#endif
44473 +
44474 +
44475 +//
44476 +// TXD Wireless Information format for Tx ring and Mgmt Ring
44477 +//
44478 +//txop : for txop mode
44479 +// 0:txop for the MPDU frame will be handles by ASIC by register
44480 +// 1/2/3:the MPDU frame is send after PIFS/backoff/SIFS
44481 +#ifdef RT_BIG_ENDIAN
44482 +typedef struct PACKED _TXWI_STRUC {
44483 + // Word 0
44484 + UINT32 PHYMODE:2;
44485 + UINT32 TxBF:1; // 3*3
44486 + UINT32 rsv2:1;
44487 + UINT32 Ifs:1; //
44488 + UINT32 STBC:2; //channel bandwidth 20MHz or 40 MHz
44489 + UINT32 ShortGI:1;
44490 + UINT32 BW:1; //channel bandwidth 20MHz or 40 MHz
44491 + UINT32 MCS:7;
44492 +
44493 + UINT32 rsv:6;
44494 + UINT32 txop:2; //tx back off mode 0:HT TXOP rule , 1:PIFS TX ,2:Backoff, 3:sifs only when previous frame exchange is successful.
44495 + UINT32 MpduDensity:3;
44496 + UINT32 AMPDU:1;
44497 +
44498 + UINT32 TS:1;
44499 + UINT32 CFACK:1;
44500 + UINT32 MIMOps:1; // the remote peer is in dynamic MIMO-PS mode
44501 + UINT32 FRAG:1; // 1 to inform TKIP engine this is a fragment.
44502 + // Word 1
44503 + UINT32 PacketId:4;
44504 + UINT32 MPDUtotalByteCount:12;
44505 + UINT32 WirelessCliID:8;
44506 + UINT32 BAWinSize:6;
44507 + UINT32 NSEQ:1;
44508 + UINT32 ACK:1;
44509 + // Word 2
44510 + UINT32 IV;
44511 + // Word 3
44512 + UINT32 EIV;
44513 +} TXWI_STRUC, *PTXWI_STRUC;
44514 +#else
44515 +typedef struct PACKED _TXWI_STRUC {
44516 + // Word 0
44517 + UINT32 FRAG:1; // 1 to inform TKIP engine this is a fragment.
44518 + UINT32 MIMOps:1; // the remote peer is in dynamic MIMO-PS mode
44519 + UINT32 CFACK:1;
44520 + UINT32 TS:1;
44521 +
44522 + UINT32 AMPDU:1;
44523 + UINT32 MpduDensity:3;
44524 + UINT32 txop:2; //FOR "THIS" frame. 0:HT TXOP rule , 1:PIFS TX ,2:Backoff, 3:sifs only when previous frame exchange is successful.
44525 + UINT32 rsv:6;
44526 +
44527 + UINT32 MCS:7;
44528 + UINT32 BW:1; //channel bandwidth 20MHz or 40 MHz
44529 + UINT32 ShortGI:1;
44530 + UINT32 STBC:2; // 1: STBC support MCS =0-7, 2,3 : RESERVE
44531 + UINT32 Ifs:1; //
44532 + UINT32 rsv2:1;
44533 + UINT32 TxBF:1; // 3*3
44534 + UINT32 PHYMODE:2;
44535 + // Word 1
44536 + UINT32 ACK:1;
44537 + UINT32 NSEQ:1;
44538 + UINT32 BAWinSize:6;
44539 + UINT32 WirelessCliID:8;
44540 + UINT32 MPDUtotalByteCount:12;
44541 + UINT32 PacketId:4;
44542 + //Word2
44543 + UINT32 IV;
44544 + //Word3
44545 + UINT32 EIV;
44546 +} TXWI_STRUC, *PTXWI_STRUC;
44547 +#endif
44548 +//
44549 +// Rx descriptor format, Rx Ring
44550 +//
44551 +#ifdef RT2860
44552 +#ifdef RT_BIG_ENDIAN
44553 +typedef struct PACKED _RXD_STRUC {
44554 + // Word 0
44555 + UINT32 SDP0;
44556 + // Word 1
44557 + UINT32 DDONE:1;
44558 + UINT32 LS0:1;
44559 + UINT32 SDL0:14;
44560 + UINT32 Rsv:2;
44561 + UINT32 SDL1:14;
44562 + // Word 2
44563 + UINT32 SDP1;
44564 + // Word 3
44565 + UINT32 Rsv1:13;
44566 + UINT32 PlcpRssil:1;// To be moved
44567 + UINT32 PlcpSignal:1; // To be moved
44568 + UINT32 Decrypted:1; // this frame is being decrypted.
44569 + UINT32 AMPDU:1;
44570 + UINT32 L2PAD:1;
44571 + UINT32 RSSI:1;
44572 + UINT32 HTC:1;
44573 + UINT32 AMSDU:1; // rx with 802.3 header, not 802.11 header. obsolete.
44574 + UINT32 CipherErr:2; // 0: decryption okay, 1:ICV error, 2:MIC error, 3:KEY not valid
44575 + UINT32 Crc:1; // 1: CRC error
44576 + UINT32 MyBss:1; // 1: this frame belongs to the same BSSID
44577 + UINT32 Bcast:1; // 1: this is a broadcast frame
44578 + UINT32 Mcast:1; // 1: this is a multicast frame
44579 + UINT32 U2M:1; // 1: this RX frame is unicast to me
44580 + UINT32 FRAG:1;
44581 + UINT32 NULLDATA:1;
44582 + UINT32 DATA:1;
44583 + UINT32 BA:1;
44584 +
44585 +} RXD_STRUC, *PRXD_STRUC, RT28XX_RXD_STRUC, *PRT28XX_RXD_STRUC;
44586 +#else
44587 +typedef struct PACKED _RXD_STRUC {
44588 + // Word 0
44589 + UINT32 SDP0;
44590 + // Word 1
44591 + UINT32 SDL1:14;
44592 + UINT32 Rsv:2;
44593 + UINT32 SDL0:14;
44594 + UINT32 LS0:1;
44595 + UINT32 DDONE:1;
44596 + // Word 2
44597 + UINT32 SDP1;
44598 + // Word 3
44599 + UINT32 BA:1;
44600 + UINT32 DATA:1;
44601 + UINT32 NULLDATA:1;
44602 + UINT32 FRAG:1;
44603 + UINT32 U2M:1; // 1: this RX frame is unicast to me
44604 + UINT32 Mcast:1; // 1: this is a multicast frame
44605 + UINT32 Bcast:1; // 1: this is a broadcast frame
44606 + UINT32 MyBss:1; // 1: this frame belongs to the same BSSID
44607 + UINT32 Crc:1; // 1: CRC error
44608 + UINT32 CipherErr:2; // 0: decryption okay, 1:ICV error, 2:MIC error, 3:KEY not valid
44609 + UINT32 AMSDU:1; // rx with 802.3 header, not 802.11 header.
44610 + UINT32 HTC:1;
44611 + UINT32 RSSI:1;
44612 + UINT32 L2PAD:1;
44613 + UINT32 AMPDU:1;
44614 + UINT32 Decrypted:1; // this frame is being decrypted.
44615 + UINT32 PlcpSignal:1; // To be moved
44616 + UINT32 PlcpRssil:1;// To be moved
44617 + UINT32 Rsv1:13;
44618 +} RXD_STRUC, *PRXD_STRUC, RT28XX_RXD_STRUC, *PRT28XX_RXD_STRUC;
44619 +#endif
44620 +#endif // RT2860 //
44621 +//
44622 +// RXWI wireless information format, in PBF. invisible in driver.
44623 +//
44624 +#ifdef RT_BIG_ENDIAN
44625 +typedef struct PACKED _RXWI_STRUC {
44626 + // Word 0
44627 + UINT32 TID:4;
44628 + UINT32 MPDUtotalByteCount:12;
44629 + UINT32 UDF:3;
44630 + UINT32 BSSID:3;
44631 + UINT32 KeyIndex:2;
44632 + UINT32 WirelessCliID:8;
44633 + // Word 1
44634 + UINT32 PHYMODE:2; // 1: this RX frame is unicast to me
44635 + UINT32 rsv:3;
44636 + UINT32 STBC:2;
44637 + UINT32 ShortGI:1;
44638 + UINT32 BW:1;
44639 + UINT32 MCS:7;
44640 + UINT32 SEQUENCE:12;
44641 + UINT32 FRAG:4;
44642 + // Word 2
44643 + UINT32 rsv1:8;
44644 + UINT32 RSSI2:8;
44645 + UINT32 RSSI1:8;
44646 + UINT32 RSSI0:8;
44647 + // Word 3
44648 + UINT32 rsv2:16;
44649 + UINT32 SNR1:8;
44650 + UINT32 SNR0:8;
44651 +} RXWI_STRUC, *PRXWI_STRUC;
44652 +#else
44653 +typedef struct PACKED _RXWI_STRUC {
44654 + // Word 0
44655 + UINT32 WirelessCliID:8;
44656 + UINT32 KeyIndex:2;
44657 + UINT32 BSSID:3;
44658 + UINT32 UDF:3;
44659 + UINT32 MPDUtotalByteCount:12;
44660 + UINT32 TID:4;
44661 + // Word 1
44662 + UINT32 FRAG:4;
44663 + UINT32 SEQUENCE:12;
44664 + UINT32 MCS:7;
44665 + UINT32 BW:1;
44666 + UINT32 ShortGI:1;
44667 + UINT32 STBC:2;
44668 + UINT32 rsv:3;
44669 + UINT32 PHYMODE:2; // 1: this RX frame is unicast to me
44670 + //Word2
44671 + UINT32 RSSI0:8;
44672 + UINT32 RSSI1:8;
44673 + UINT32 RSSI2:8;
44674 + UINT32 rsv1:8;
44675 + //Word3
44676 + UINT32 SNR0:8;
44677 + UINT32 SNR1:8;
44678 + UINT32 rsv2:16;
44679 +} RXWI_STRUC, *PRXWI_STRUC;
44680 +#endif
44681 +
44682 +
44683 +// =================================================================================
44684 +// HOST-MCU communication data structure
44685 +// =================================================================================
44686 +
44687 +//
44688 +// H2M_MAILBOX_CSR: Host-to-MCU Mailbox
44689 +//
44690 +#ifdef RT_BIG_ENDIAN
44691 +typedef union _H2M_MAILBOX_STRUC {
44692 + struct {
44693 + UINT32 Owner:8;
44694 + UINT32 CmdToken:8; // 0xff tells MCU not to report CmdDoneInt after excuting the command
44695 + UINT32 HighByte:8;
44696 + UINT32 LowByte:8;
44697 + } field;
44698 + UINT32 word;
44699 +} H2M_MAILBOX_STRUC, *PH2M_MAILBOX_STRUC;
44700 +#else
44701 +typedef union _H2M_MAILBOX_STRUC {
44702 + struct {
44703 + UINT32 LowByte:8;
44704 + UINT32 HighByte:8;
44705 + UINT32 CmdToken:8;
44706 + UINT32 Owner:8;
44707 + } field;
44708 + UINT32 word;
44709 +} H2M_MAILBOX_STRUC, *PH2M_MAILBOX_STRUC;
44710 +#endif
44711 +
44712 +//
44713 +// M2H_CMD_DONE_CSR: MCU-to-Host command complete indication
44714 +//
44715 +#ifdef RT_BIG_ENDIAN
44716 +typedef union _M2H_CMD_DONE_STRUC {
44717 + struct {
44718 + UINT32 CmdToken3;
44719 + UINT32 CmdToken2;
44720 + UINT32 CmdToken1;
44721 + UINT32 CmdToken0;
44722 + } field;
44723 + UINT32 word;
44724 +} M2H_CMD_DONE_STRUC, *PM2H_CMD_DONE_STRUC;
44725 +#else
44726 +typedef union _M2H_CMD_DONE_STRUC {
44727 + struct {
44728 + UINT32 CmdToken0;
44729 + UINT32 CmdToken1;
44730 + UINT32 CmdToken2;
44731 + UINT32 CmdToken3;
44732 + } field;
44733 + UINT32 word;
44734 +} M2H_CMD_DONE_STRUC, *PM2H_CMD_DONE_STRUC;
44735 +#endif
44736 +
44737 +
44738 +
44739 +//
44740 +// MCU_LEDCS: MCU LED Control Setting.
44741 +//
44742 +#ifdef RT_BIG_ENDIAN
44743 +typedef union _MCU_LEDCS_STRUC {
44744 + struct {
44745 + UCHAR Polarity:1;
44746 + UCHAR LedMode:7;
44747 + } field;
44748 + UCHAR word;
44749 +} MCU_LEDCS_STRUC, *PMCU_LEDCS_STRUC;
44750 +#else
44751 +typedef union _MCU_LEDCS_STRUC {
44752 + struct {
44753 + UCHAR LedMode:7;
44754 + UCHAR Polarity:1;
44755 + } field;
44756 + UCHAR word;
44757 +} MCU_LEDCS_STRUC, *PMCU_LEDCS_STRUC;
44758 +#endif
44759 +// =================================================================================
44760 +// Register format
44761 +// =================================================================================
44762 +
44763 +
44764 +
44765 +//NAV_TIME_CFG :NAV
44766 +#ifdef RT_BIG_ENDIAN
44767 +typedef union _NAV_TIME_CFG_STRUC {
44768 + struct {
44769 + USHORT rsv:6;
44770 + USHORT ZeroSifs:1; // Applied zero SIFS timer after OFDM RX 0: disable
44771 + USHORT Eifs:9; // in unit of 1-us
44772 + UCHAR SlotTime; // in unit of 1-us
44773 + UCHAR Sifs; // in unit of 1-us
44774 + } field;
44775 + UINT32 word;
44776 +} NAV_TIME_CFG_STRUC, *PNAV_TIME_CFG_STRUC;
44777 +#else
44778 +typedef union _NAV_TIME_CFG_STRUC {
44779 + struct {
44780 + UCHAR Sifs; // in unit of 1-us
44781 + UCHAR SlotTime; // in unit of 1-us
44782 + USHORT Eifs:9; // in unit of 1-us
44783 + USHORT ZeroSifs:1; // Applied zero SIFS timer after OFDM RX 0: disable
44784 + USHORT rsv:6;
44785 + } field;
44786 + UINT32 word;
44787 +} NAV_TIME_CFG_STRUC, *PNAV_TIME_CFG_STRUC;
44788 +#endif
44789 +
44790 +
44791 +
44792 +
44793 +
44794 +//
44795 +// RX_FILTR_CFG: /RX configuration register
44796 +//
44797 +#ifdef RT_BIG_ENDIAN
44798 +typedef union RX_FILTR_CFG_STRUC {
44799 + struct {
44800 + UINT32 :15;
44801 + UINT32 DropRsvCntlType:1;
44802 +
44803 + UINT32 DropBAR:1; //
44804 + UINT32 DropBA:1; //
44805 + UINT32 DropPsPoll:1; // Drop Ps-Poll
44806 + UINT32 DropRts:1; // Drop Ps-Poll
44807 +
44808 + UINT32 DropCts:1; // Drop Ps-Poll
44809 + UINT32 DropAck:1; // Drop Ps-Poll
44810 + UINT32 DropCFEnd:1; // Drop Ps-Poll
44811 + UINT32 DropCFEndAck:1; // Drop Ps-Poll
44812 +
44813 + UINT32 DropDuplicate:1; // Drop duplicate frame
44814 + UINT32 DropBcast:1; // Drop broadcast frames
44815 + UINT32 DropMcast:1; // Drop multicast frames
44816 + UINT32 DropVerErr:1; // Drop version error frame
44817 +
44818 + UINT32 DropNotMyBSSID:1; // Drop fram ToDs bit is true
44819 + UINT32 DropNotToMe:1; // Drop not to me unicast frame
44820 + UINT32 DropPhyErr:1; // Drop physical error
44821 + UINT32 DropCRCErr:1; // Drop CRC error
44822 + } field;
44823 + UINT32 word;
44824 +} RX_FILTR_CFG_STRUC, *PRX_FILTR_CFG_STRUC;
44825 +#else
44826 +typedef union _RX_FILTR_CFG_STRUC {
44827 + struct {
44828 + UINT32 DropCRCErr:1; // Drop CRC error
44829 + UINT32 DropPhyErr:1; // Drop physical error
44830 + UINT32 DropNotToMe:1; // Drop not to me unicast frame
44831 + UINT32 DropNotMyBSSID:1; // Drop fram ToDs bit is true
44832 +
44833 + UINT32 DropVerErr:1; // Drop version error frame
44834 + UINT32 DropMcast:1; // Drop multicast frames
44835 + UINT32 DropBcast:1; // Drop broadcast frames
44836 + UINT32 DropDuplicate:1; // Drop duplicate frame
44837 +
44838 + UINT32 DropCFEndAck:1; // Drop Ps-Poll
44839 + UINT32 DropCFEnd:1; // Drop Ps-Poll
44840 + UINT32 DropAck:1; // Drop Ps-Poll
44841 + UINT32 DropCts:1; // Drop Ps-Poll
44842 +
44843 + UINT32 DropRts:1; // Drop Ps-Poll
44844 + UINT32 DropPsPoll:1; // Drop Ps-Poll
44845 + UINT32 DropBA:1; //
44846 + UINT32 DropBAR:1; //
44847 +
44848 + UINT32 DropRsvCntlType:1;
44849 + UINT32 :15;
44850 + } field;
44851 + UINT32 word;
44852 +} RX_FILTR_CFG_STRUC, *PRX_FILTR_CFG_STRUC;
44853 +#endif
44854 +
44855 +
44856 +
44857 +
44858 +//
44859 +// PHY_CSR4: RF serial control register
44860 +//
44861 +#ifdef RT_BIG_ENDIAN
44862 +typedef union _PHY_CSR4_STRUC {
44863 + struct {
44864 + UINT32 Busy:1; // 1: ASIC is busy execute RF programming.
44865 + UINT32 PLL_LD:1; // RF PLL_LD status
44866 + UINT32 IFSelect:1; // 1: select IF to program, 0: select RF to program
44867 + UINT32 NumberOfBits:5; // Number of bits used in RFRegValue (I:20, RFMD:22)
44868 + UINT32 RFRegValue:24; // Register value (include register id) serial out to RF/IF chip.
44869 + } field;
44870 + UINT32 word;
44871 +} PHY_CSR4_STRUC, *PPHY_CSR4_STRUC;
44872 +#else
44873 +typedef union _PHY_CSR4_STRUC {
44874 + struct {
44875 + UINT32 RFRegValue:24; // Register value (include register id) serial out to RF/IF chip.
44876 + UINT32 NumberOfBits:5; // Number of bits used in RFRegValue (I:20, RFMD:22)
44877 + UINT32 IFSelect:1; // 1: select IF to program, 0: select RF to program
44878 + UINT32 PLL_LD:1; // RF PLL_LD status
44879 + UINT32 Busy:1; // 1: ASIC is busy execute RF programming.
44880 + } field;
44881 + UINT32 word;
44882 +} PHY_CSR4_STRUC, *PPHY_CSR4_STRUC;
44883 +#endif
44884 +
44885 +
44886 +//
44887 +// SEC_CSR5: shared key table security mode register
44888 +//
44889 +#ifdef RT_BIG_ENDIAN
44890 +typedef union _SEC_CSR5_STRUC {
44891 + struct {
44892 + UINT32 :1;
44893 + UINT32 Bss3Key3CipherAlg:3;
44894 + UINT32 :1;
44895 + UINT32 Bss3Key2CipherAlg:3;
44896 + UINT32 :1;
44897 + UINT32 Bss3Key1CipherAlg:3;
44898 + UINT32 :1;
44899 + UINT32 Bss3Key0CipherAlg:3;
44900 + UINT32 :1;
44901 + UINT32 Bss2Key3CipherAlg:3;
44902 + UINT32 :1;
44903 + UINT32 Bss2Key2CipherAlg:3;
44904 + UINT32 :1;
44905 + UINT32 Bss2Key1CipherAlg:3;
44906 + UINT32 :1;
44907 + UINT32 Bss2Key0CipherAlg:3;
44908 + } field;
44909 + UINT32 word;
44910 +} SEC_CSR5_STRUC, *PSEC_CSR5_STRUC;
44911 +#else
44912 +typedef union _SEC_CSR5_STRUC {
44913 + struct {
44914 + UINT32 Bss2Key0CipherAlg:3;
44915 + UINT32 :1;
44916 + UINT32 Bss2Key1CipherAlg:3;
44917 + UINT32 :1;
44918 + UINT32 Bss2Key2CipherAlg:3;
44919 + UINT32 :1;
44920 + UINT32 Bss2Key3CipherAlg:3;
44921 + UINT32 :1;
44922 + UINT32 Bss3Key0CipherAlg:3;
44923 + UINT32 :1;
44924 + UINT32 Bss3Key1CipherAlg:3;
44925 + UINT32 :1;
44926 + UINT32 Bss3Key2CipherAlg:3;
44927 + UINT32 :1;
44928 + UINT32 Bss3Key3CipherAlg:3;
44929 + UINT32 :1;
44930 + } field;
44931 + UINT32 word;
44932 +} SEC_CSR5_STRUC, *PSEC_CSR5_STRUC;
44933 +#endif
44934 +
44935 +
44936 +//
44937 +// HOST_CMD_CSR: For HOST to interrupt embedded processor
44938 +//
44939 +#ifdef RT_BIG_ENDIAN
44940 +typedef union _HOST_CMD_CSR_STRUC {
44941 + struct {
44942 + UINT32 Rsv:24;
44943 + UINT32 HostCommand:8;
44944 + } field;
44945 + UINT32 word;
44946 +} HOST_CMD_CSR_STRUC, *PHOST_CMD_CSR_STRUC;
44947 +#else
44948 +typedef union _HOST_CMD_CSR_STRUC {
44949 + struct {
44950 + UINT32 HostCommand:8;
44951 + UINT32 Rsv:24;
44952 + } field;
44953 + UINT32 word;
44954 +} HOST_CMD_CSR_STRUC, *PHOST_CMD_CSR_STRUC;
44955 +#endif
44956 +
44957 +
44958 +//
44959 +// AIFSN_CSR: AIFSN for each EDCA AC
44960 +//
44961 +
44962 +
44963 +
44964 +//
44965 +// E2PROM_CSR: EEPROM control register
44966 +//
44967 +#ifdef RT_BIG_ENDIAN
44968 +typedef union _E2PROM_CSR_STRUC {
44969 + struct {
44970 + UINT32 Rsvd:25;
44971 + UINT32 LoadStatus:1; // 1:loading, 0:done
44972 + UINT32 Type:1; // 1: 93C46, 0:93C66
44973 + UINT32 EepromDO:1;
44974 + UINT32 EepromDI:1;
44975 + UINT32 EepromCS:1;
44976 + UINT32 EepromSK:1;
44977 + UINT32 Reload:1; // Reload EEPROM content, write one to reload, self-cleared.
44978 + } field;
44979 + UINT32 word;
44980 +} E2PROM_CSR_STRUC, *PE2PROM_CSR_STRUC;
44981 +#else
44982 +typedef union _E2PROM_CSR_STRUC {
44983 + struct {
44984 + UINT32 Reload:1; // Reload EEPROM content, write one to reload, self-cleared.
44985 + UINT32 EepromSK:1;
44986 + UINT32 EepromCS:1;
44987 + UINT32 EepromDI:1;
44988 + UINT32 EepromDO:1;
44989 + UINT32 Type:1; // 1: 93C46, 0:93C66
44990 + UINT32 LoadStatus:1; // 1:loading, 0:done
44991 + UINT32 Rsvd:25;
44992 + } field;
44993 + UINT32 word;
44994 +} E2PROM_CSR_STRUC, *PE2PROM_CSR_STRUC;
44995 +#endif
44996 +
44997 +
44998 +// -------------------------------------------------------------------
44999 +// E2PROM data layout
45000 +// -------------------------------------------------------------------
45001 +
45002 +//
45003 +// EEPROM antenna select format
45004 +//
45005 +#ifdef RT_BIG_ENDIAN
45006 +typedef union _EEPROM_ANTENNA_STRUC {
45007 + struct {
45008 + USHORT Rsv:4;
45009 + USHORT RfIcType:4; // see E2PROM document
45010 + USHORT TxPath:4; // 1: 1T, 2: 2T
45011 + USHORT RxPath:4; // 1: 1R, 2: 2R, 3: 3R
45012 + } field;
45013 + USHORT word;
45014 +} EEPROM_ANTENNA_STRUC, *PEEPROM_ANTENNA_STRUC;
45015 +#else
45016 +typedef union _EEPROM_ANTENNA_STRUC {
45017 + struct {
45018 + USHORT RxPath:4; // 1: 1R, 2: 2R, 3: 3R
45019 + USHORT TxPath:4; // 1: 1T, 2: 2T
45020 + USHORT RfIcType:4; // see E2PROM document
45021 + USHORT Rsv:4;
45022 + } field;
45023 + USHORT word;
45024 +} EEPROM_ANTENNA_STRUC, *PEEPROM_ANTENNA_STRUC;
45025 +#endif
45026 +
45027 +#ifdef RT_BIG_ENDIAN
45028 +typedef union _EEPROM_NIC_CINFIG2_STRUC {
45029 + struct {
45030 + USHORT Rsv2:6; // must be 0
45031 + USHORT BW40MAvailForA:1; // 0:enable, 1:disable
45032 + USHORT BW40MAvailForG:1; // 0:enable, 1:disable
45033 + USHORT EnableWPSPBC:1; // WPS PBC Control bit
45034 + USHORT BW40MSidebandForA:1;
45035 + USHORT BW40MSidebandForG:1;
45036 + USHORT CardbusAcceleration:1; // !!! NOTE: 0 - enable, 1 - disable
45037 + USHORT ExternalLNAForA:1; // external LNA enable for 5G
45038 + USHORT ExternalLNAForG:1; // external LNA enable for 2.4G
45039 + USHORT DynamicTxAgcControl:1; //
45040 + USHORT HardwareRadioControl:1; // Whether RF is controlled by driver or HW. 1:enable hw control, 0:disable
45041 + } field;
45042 + USHORT word;
45043 +} EEPROM_NIC_CONFIG2_STRUC, *PEEPROM_NIC_CONFIG2_STRUC;
45044 +#else
45045 +typedef union _EEPROM_NIC_CINFIG2_STRUC {
45046 + struct {
45047 + USHORT HardwareRadioControl:1; // 1:enable, 0:disable
45048 + USHORT DynamicTxAgcControl:1; //
45049 + USHORT ExternalLNAForG:1; //
45050 + USHORT ExternalLNAForA:1; // external LNA enable for 2.4G
45051 + USHORT CardbusAcceleration:1; // !!! NOTE: 0 - enable, 1 - disable
45052 + USHORT BW40MSidebandForG:1;
45053 + USHORT BW40MSidebandForA:1;
45054 + USHORT EnableWPSPBC:1; // WPS PBC Control bit
45055 + USHORT BW40MAvailForG:1; // 0:enable, 1:disable
45056 + USHORT BW40MAvailForA:1; // 0:enable, 1:disable
45057 + USHORT Rsv2:6; // must be 0
45058 + } field;
45059 + USHORT word;
45060 +} EEPROM_NIC_CONFIG2_STRUC, *PEEPROM_NIC_CONFIG2_STRUC;
45061 +#endif
45062 +
45063 +//
45064 +// TX_PWR Value valid range 0xFA(-6) ~ 0x24(36)
45065 +//
45066 +#ifdef RT_BIG_ENDIAN
45067 +typedef union _EEPROM_TX_PWR_STRUC {
45068 + struct {
45069 + CHAR Byte1; // High Byte
45070 + CHAR Byte0; // Low Byte
45071 + } field;
45072 + USHORT word;
45073 +} EEPROM_TX_PWR_STRUC, *PEEPROM_TX_PWR_STRUC;
45074 +#else
45075 +typedef union _EEPROM_TX_PWR_STRUC {
45076 + struct {
45077 + CHAR Byte0; // Low Byte
45078 + CHAR Byte1; // High Byte
45079 + } field;
45080 + USHORT word;
45081 +} EEPROM_TX_PWR_STRUC, *PEEPROM_TX_PWR_STRUC;
45082 +#endif
45083 +
45084 +#ifdef RT_BIG_ENDIAN
45085 +typedef union _EEPROM_VERSION_STRUC {
45086 + struct {
45087 + UCHAR Version; // High Byte
45088 + UCHAR FaeReleaseNumber; // Low Byte
45089 + } field;
45090 + USHORT word;
45091 +} EEPROM_VERSION_STRUC, *PEEPROM_VERSION_STRUC;
45092 +#else
45093 +typedef union _EEPROM_VERSION_STRUC {
45094 + struct {
45095 + UCHAR FaeReleaseNumber; // Low Byte
45096 + UCHAR Version; // High Byte
45097 + } field;
45098 + USHORT word;
45099 +} EEPROM_VERSION_STRUC, *PEEPROM_VERSION_STRUC;
45100 +#endif
45101 +
45102 +#ifdef RT_BIG_ENDIAN
45103 +typedef union _EEPROM_LED_STRUC {
45104 + struct {
45105 + USHORT Rsvd:3; // Reserved
45106 + USHORT LedMode:5; // Led mode.
45107 + USHORT PolarityGPIO_4:1; // Polarity GPIO#4 setting.
45108 + USHORT PolarityGPIO_3:1; // Polarity GPIO#3 setting.
45109 + USHORT PolarityGPIO_2:1; // Polarity GPIO#2 setting.
45110 + USHORT PolarityGPIO_1:1; // Polarity GPIO#1 setting.
45111 + USHORT PolarityGPIO_0:1; // Polarity GPIO#0 setting.
45112 + USHORT PolarityACT:1; // Polarity ACT setting.
45113 + USHORT PolarityRDY_A:1; // Polarity RDY_A setting.
45114 + USHORT PolarityRDY_G:1; // Polarity RDY_G setting.
45115 + } field;
45116 + USHORT word;
45117 +} EEPROM_LED_STRUC, *PEEPROM_LED_STRUC;
45118 +#else
45119 +typedef union _EEPROM_LED_STRUC {
45120 + struct {
45121 + USHORT PolarityRDY_G:1; // Polarity RDY_G setting.
45122 + USHORT PolarityRDY_A:1; // Polarity RDY_A setting.
45123 + USHORT PolarityACT:1; // Polarity ACT setting.
45124 + USHORT PolarityGPIO_0:1; // Polarity GPIO#0 setting.
45125 + USHORT PolarityGPIO_1:1; // Polarity GPIO#1 setting.
45126 + USHORT PolarityGPIO_2:1; // Polarity GPIO#2 setting.
45127 + USHORT PolarityGPIO_3:1; // Polarity GPIO#3 setting.
45128 + USHORT PolarityGPIO_4:1; // Polarity GPIO#4 setting.
45129 + USHORT LedMode:5; // Led mode.
45130 + USHORT Rsvd:3; // Reserved
45131 + } field;
45132 + USHORT word;
45133 +} EEPROM_LED_STRUC, *PEEPROM_LED_STRUC;
45134 +#endif
45135 +
45136 +#ifdef RT_BIG_ENDIAN
45137 +typedef union _EEPROM_TXPOWER_DELTA_STRUC {
45138 + struct {
45139 + UCHAR TxPowerEnable:1;// Enable
45140 + UCHAR Type:1; // 1: plus the delta value, 0: minus the delta value
45141 + UCHAR DeltaValue:6; // Tx Power dalta value (MAX=4)
45142 + } field;
45143 + UCHAR value;
45144 +} EEPROM_TXPOWER_DELTA_STRUC, *PEEPROM_TXPOWER_DELTA_STRUC;
45145 +#else
45146 +typedef union _EEPROM_TXPOWER_DELTA_STRUC {
45147 + struct {
45148 + UCHAR DeltaValue:6; // Tx Power dalta value (MAX=4)
45149 + UCHAR Type:1; // 1: plus the delta value, 0: minus the delta value
45150 + UCHAR TxPowerEnable:1;// Enable
45151 + } field;
45152 + UCHAR value;
45153 +} EEPROM_TXPOWER_DELTA_STRUC, *PEEPROM_TXPOWER_DELTA_STRUC;
45154 +#endif
45155 +
45156 +//
45157 +// QOS_CSR0: TXOP holder address0 register
45158 +//
45159 +#ifdef RT_BIG_ENDIAN
45160 +typedef union _QOS_CSR0_STRUC {
45161 + struct {
45162 + UCHAR Byte3; // MAC address byte 3
45163 + UCHAR Byte2; // MAC address byte 2
45164 + UCHAR Byte1; // MAC address byte 1
45165 + UCHAR Byte0; // MAC address byte 0
45166 + } field;
45167 + UINT32 word;
45168 +} QOS_CSR0_STRUC, *PQOS_CSR0_STRUC;
45169 +#else
45170 +typedef union _QOS_CSR0_STRUC {
45171 + struct {
45172 + UCHAR Byte0; // MAC address byte 0
45173 + UCHAR Byte1; // MAC address byte 1
45174 + UCHAR Byte2; // MAC address byte 2
45175 + UCHAR Byte3; // MAC address byte 3
45176 + } field;
45177 + UINT32 word;
45178 +} QOS_CSR0_STRUC, *PQOS_CSR0_STRUC;
45179 +#endif
45180 +
45181 +//
45182 +// QOS_CSR1: TXOP holder address1 register
45183 +//
45184 +#ifdef RT_BIG_ENDIAN
45185 +typedef union _QOS_CSR1_STRUC {
45186 + struct {
45187 + UCHAR Rsvd1;
45188 + UCHAR Rsvd0;
45189 + UCHAR Byte5; // MAC address byte 5
45190 + UCHAR Byte4; // MAC address byte 4
45191 + } field;
45192 + UINT32 word;
45193 +} QOS_CSR1_STRUC, *PQOS_CSR1_STRUC;
45194 +#else
45195 +typedef union _QOS_CSR1_STRUC {
45196 + struct {
45197 + UCHAR Byte4; // MAC address byte 4
45198 + UCHAR Byte5; // MAC address byte 5
45199 + UCHAR Rsvd0;
45200 + UCHAR Rsvd1;
45201 + } field;
45202 + UINT32 word;
45203 +} QOS_CSR1_STRUC, *PQOS_CSR1_STRUC;
45204 +#endif
45205 +
45206 +#define RF_CSR_CFG 0x500
45207 +#ifdef RT_BIG_ENDIAN
45208 +typedef union _RF_CSR_CFG_STRUC {
45209 + struct {
45210 + UINT Rsvd1:14; // Reserved
45211 + UINT RF_CSR_KICK:1; // kick RF register read/write
45212 + UINT RF_CSR_WR:1; // 0: read 1: write
45213 + UINT Rsvd2:3; // Reserved
45214 + UINT TESTCSR_RFACC_REGNUM:5; // RF register ID
45215 + UINT RF_CSR_DATA:8; // DATA
45216 + } field;
45217 + UINT word;
45218 +} RF_CSR_CFG_STRUC, *PRF_CSR_CFG_STRUC;
45219 +#else
45220 +typedef union _RF_CSR_CFG_STRUC {
45221 + struct {
45222 + UINT RF_CSR_DATA:8; // DATA
45223 + UINT TESTCSR_RFACC_REGNUM:5; // RF register ID
45224 + UINT Rsvd2:3; // Reserved
45225 + UINT RF_CSR_WR:1; // 0: read 1: write
45226 + UINT RF_CSR_KICK:1; // kick RF register read/write
45227 + UINT Rsvd1:14; // Reserved
45228 + } field;
45229 + UINT word;
45230 +} RF_CSR_CFG_STRUC, *PRF_CSR_CFG_STRUC;
45231 +#endif
45232 +
45233 +#endif // __RT28XX_H__
45234 --- /dev/null
45235 +++ b/drivers/staging/rt2860/rt_ate.c
45236 @@ -0,0 +1,6025 @@
45237 +/*
45238 + *************************************************************************
45239 + * Ralink Tech Inc.
45240 + * 5F., No.36, Taiyuan St., Jhubei City,
45241 + * Hsinchu County 302,
45242 + * Taiwan, R.O.C.
45243 + *
45244 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
45245 + *
45246 + * This program is free software; you can redistribute it and/or modify *
45247 + * it under the terms of the GNU General Public License as published by *
45248 + * the Free Software Foundation; either version 2 of the License, or *
45249 + * (at your option) any later version. *
45250 + * *
45251 + * This program is distributed in the hope that it will be useful, *
45252 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
45253 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
45254 + * GNU General Public License for more details. *
45255 + * *
45256 + * You should have received a copy of the GNU General Public License *
45257 + * along with this program; if not, write to the *
45258 + * Free Software Foundation, Inc., *
45259 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
45260 + * *
45261 + *************************************************************************
45262 + */
45263 +
45264 +#include "rt_config.h"
45265 +
45266 +#ifdef RALINK_ATE
45267 +UCHAR TemplateFrame[24] = {0x08/* Data type */,0x00,0x00,0x00,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,0xAA,0xBB,0x12,0x34,0x56,0x00,0x11,0x22,0xAA,0xBB,0xCC,0x00,0x00}; // 802.11 MAC Header, Type:Data, Length:24bytes
45268 +extern RTMP_RF_REGS RF2850RegTable[];
45269 +extern UCHAR NUM_OF_2850_CHNL;
45270 +
45271 +static CHAR CCKRateTable[] = {0, 1, 2, 3, 8, 9, 10, 11, -1}; /* CCK Mode. */
45272 +static CHAR OFDMRateTable[] = {0, 1, 2, 3, 4, 5, 6, 7, -1}; /* OFDM Mode. */
45273 +static CHAR HTMIXRateTable[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, -1}; /* HT Mix Mode. */
45274 +
45275 +static INT TxDmaBusy(
45276 + IN PRTMP_ADAPTER pAd);
45277 +
45278 +static INT RxDmaBusy(
45279 + IN PRTMP_ADAPTER pAd);
45280 +
45281 +static VOID RtmpDmaEnable(
45282 + IN PRTMP_ADAPTER pAd,
45283 + IN INT Enable);
45284 +
45285 +static VOID BbpSoftReset(
45286 + IN PRTMP_ADAPTER pAd);
45287 +
45288 +static VOID RtmpRfIoWrite(
45289 + IN PRTMP_ADAPTER pAd);
45290 +
45291 +static INT ATESetUpFrame(
45292 + IN PRTMP_ADAPTER pAd,
45293 + IN UINT32 TxIdx);
45294 +
45295 +static INT ATETxPwrHandler(
45296 + IN PRTMP_ADAPTER pAd,
45297 + IN char index);
45298 +
45299 +static INT ATECmdHandler(
45300 + IN PRTMP_ADAPTER pAd,
45301 + IN PUCHAR arg);
45302 +
45303 +static int CheckMCSValid(
45304 + IN UCHAR Mode,
45305 + IN UCHAR Mcs);
45306 +
45307 +#ifdef RT2860
45308 +static VOID ATEWriteTxWI(
45309 + IN PRTMP_ADAPTER pAd,
45310 + IN PTXWI_STRUC pOutTxWI,
45311 + IN BOOLEAN FRAG,
45312 + IN BOOLEAN CFACK,
45313 + IN BOOLEAN InsTimestamp,
45314 + IN BOOLEAN AMPDU,
45315 + IN BOOLEAN Ack,
45316 + IN BOOLEAN NSeq, // HW new a sequence.
45317 + IN UCHAR BASize,
45318 + IN UCHAR WCID,
45319 + IN ULONG Length,
45320 + IN UCHAR PID,
45321 + IN UCHAR TID,
45322 + IN UCHAR TxRate,
45323 + IN UCHAR Txopmode,
45324 + IN BOOLEAN CfAck,
45325 + IN HTTRANSMIT_SETTING *pTransmit);
45326 +#endif // RT2860 //
45327 +
45328 +
45329 +static VOID SetJapanFilter(
45330 + IN PRTMP_ADAPTER pAd);
45331 +
45332 +/*=========================end of prototype=========================*/
45333 +
45334 +#ifdef RT2860
45335 +static INT TxDmaBusy(
45336 + IN PRTMP_ADAPTER pAd)
45337 +{
45338 + INT result;
45339 + WPDMA_GLO_CFG_STRUC GloCfg;
45340 +
45341 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word); // disable DMA
45342 + if (GloCfg.field.TxDMABusy)
45343 + result = 1;
45344 + else
45345 + result = 0;
45346 +
45347 + return result;
45348 +}
45349 +
45350 +static INT RxDmaBusy(
45351 + IN PRTMP_ADAPTER pAd)
45352 +{
45353 + INT result;
45354 + WPDMA_GLO_CFG_STRUC GloCfg;
45355 +
45356 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word); // disable DMA
45357 + if (GloCfg.field.RxDMABusy)
45358 + result = 1;
45359 + else
45360 + result = 0;
45361 +
45362 + return result;
45363 +}
45364 +
45365 +static VOID RtmpDmaEnable(
45366 + IN PRTMP_ADAPTER pAd,
45367 + IN INT Enable)
45368 +{
45369 + BOOLEAN value;
45370 + ULONG WaitCnt;
45371 + WPDMA_GLO_CFG_STRUC GloCfg;
45372 +
45373 + value = Enable > 0 ? 1 : 0;
45374 +
45375 + // check DMA is in busy mode.
45376 + WaitCnt = 0;
45377 + while (TxDmaBusy(pAd) || RxDmaBusy(pAd))
45378 + {
45379 + RTMPusecDelay(10);
45380 + if (WaitCnt++ > 100)
45381 + break;
45382 + }
45383 +
45384 + RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word); // disable DMA
45385 + GloCfg.field.EnableTxDMA = value;
45386 + GloCfg.field.EnableRxDMA = value;
45387 + RTMP_IO_WRITE32(pAd, WPDMA_GLO_CFG, GloCfg.word); // abort all TX rings
45388 + RTMPusecDelay(5000);
45389 +
45390 + return;
45391 +}
45392 +#endif // RT2860 //
45393 +
45394 +
45395 +static VOID BbpSoftReset(
45396 + IN PRTMP_ADAPTER pAd)
45397 +{
45398 + UCHAR BbpData = 0;
45399 +
45400 + // Soft reset, set BBP R21 bit0=1->0
45401 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R21, &BbpData);
45402 + BbpData |= 0x00000001; //set bit0=1
45403 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R21, BbpData);
45404 +
45405 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R21, &BbpData);
45406 + BbpData &= ~(0x00000001); //set bit0=0
45407 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R21, BbpData);
45408 +
45409 + return;
45410 +}
45411 +
45412 +static VOID RtmpRfIoWrite(
45413 + IN PRTMP_ADAPTER pAd)
45414 +{
45415 + // Set RF value 1's set R3[bit2] = [0]
45416 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R1);
45417 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R2);
45418 + RTMP_RF_IO_WRITE32(pAd, (pAd->LatchRfRegs.R3 & (~0x04)));
45419 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R4);
45420 +
45421 + RTMPusecDelay(200);
45422 +
45423 + // Set RF value 2's set R3[bit2] = [1]
45424 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R1);
45425 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R2);
45426 + RTMP_RF_IO_WRITE32(pAd, (pAd->LatchRfRegs.R3 | 0x04));
45427 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R4);
45428 +
45429 + RTMPusecDelay(200);
45430 +
45431 + // Set RF value 3's set R3[bit2] = [0]
45432 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R1);
45433 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R2);
45434 + RTMP_RF_IO_WRITE32(pAd, (pAd->LatchRfRegs.R3 & (~0x04)));
45435 + RTMP_RF_IO_WRITE32(pAd, pAd->LatchRfRegs.R4);
45436 +
45437 + return;
45438 +}
45439 +
45440 +static int CheckMCSValid(
45441 + UCHAR Mode,
45442 + UCHAR Mcs)
45443 +{
45444 + int i;
45445 + PCHAR pRateTab;
45446 +
45447 + switch(Mode)
45448 + {
45449 + case 0:
45450 + pRateTab = CCKRateTable;
45451 + break;
45452 + case 1:
45453 + pRateTab = OFDMRateTable;
45454 + break;
45455 + case 2:
45456 + case 3:
45457 + pRateTab = HTMIXRateTable;
45458 + break;
45459 + default:
45460 + ATEDBGPRINT(RT_DEBUG_ERROR, ("unrecognizable Tx Mode %d\n", Mode));
45461 + return -1;
45462 + break;
45463 + }
45464 +
45465 + i = 0;
45466 + while(pRateTab[i] != -1)
45467 + {
45468 + if (pRateTab[i] == Mcs)
45469 + return 0;
45470 + i++;
45471 + }
45472 +
45473 + return -1;
45474 +}
45475 +
45476 +#if 1
45477 +static INT ATETxPwrHandler(
45478 + IN PRTMP_ADAPTER pAd,
45479 + IN char index)
45480 +{
45481 + ULONG R;
45482 + CHAR TxPower;
45483 + UCHAR Bbp94 = 0;
45484 + BOOLEAN bPowerReduce = FALSE;
45485 +
45486 +#ifdef RALINK_28xx_QA
45487 + if ((pAd->ate.bQATxStart == TRUE) || (pAd->ate.bQARxStart == TRUE))
45488 + {
45489 + /* When QA is used for Tx, pAd->ate.TxPower0/1 and real tx power
45490 + ** are not synchronized.
45491 + */
45492 +/*
45493 + pAd->ate.TxPower0 = pAd->LatchRfRegs.xxx;
45494 + pAd->ate.TxPower1 = pAd->LatchRfRegs.xxx;
45495 +*/
45496 + return 0;
45497 + }
45498 + else
45499 +#endif // RALINK_28xx_QA //
45500 + {
45501 + TxPower = index == 0 ? pAd->ate.TxPower0 : pAd->ate.TxPower1;
45502 +
45503 + if (pAd->ate.Channel <= 14)
45504 + {
45505 + if (TxPower > 31)
45506 + {
45507 + //
45508 + // R3, R4 can't large than 31 (0x24), 31 ~ 36 used by BBP 94
45509 + //
45510 + R = 31;
45511 + if (TxPower <= 36)
45512 + Bbp94 = BBPR94_DEFAULT + (UCHAR)(TxPower - 31);
45513 + }
45514 + else if (TxPower < 0)
45515 + {
45516 + //
45517 + // R3, R4 can't less than 0, -1 ~ -6 used by BBP 94
45518 + //
45519 + R = 0;
45520 + if (TxPower >= -6)
45521 + Bbp94 = BBPR94_DEFAULT + TxPower;
45522 + }
45523 + else
45524 + {
45525 + // 0 ~ 31
45526 + R = (ULONG) TxPower;
45527 + Bbp94 = BBPR94_DEFAULT;
45528 + }
45529 +
45530 + ATEDBGPRINT(RT_DEBUG_TRACE, ("%s (TxPower=%d, R=%ld, BBP_R94=%d)\n", __FUNCTION__, TxPower, R, Bbp94));
45531 + }
45532 + else// 5.5 GHz
45533 + {
45534 + if (TxPower > 15)
45535 + {
45536 + //
45537 + // R3, R4 can't large than 15 (0x0F)
45538 + //
45539 + R = 15;
45540 + }
45541 + else if (TxPower < 0)
45542 + {
45543 + //
45544 + // R3, R4 can't less than 0
45545 + //
45546 + // -1 ~ -7
45547 + ASSERT((TxPower >= -7));
45548 + R = (ULONG)(TxPower + 7);
45549 + bPowerReduce = TRUE;
45550 + }
45551 + else
45552 + {
45553 + // 0 ~ 15
45554 + R = (ULONG) TxPower;
45555 + }
45556 +
45557 + ATEDBGPRINT(RT_DEBUG_TRACE, ("%s (TxPower=%d, R=%lu)\n", __FUNCTION__, TxPower, R));
45558 + }
45559 +
45560 + if (pAd->ate.Channel <= 14)
45561 + {
45562 + if (index == 0)
45563 + {
45564 + R = R << 9; // shift TX power control to correct RF(R3) register bit position
45565 + R |= (pAd->LatchRfRegs.R3 & 0xffffc1ff);
45566 + pAd->LatchRfRegs.R3 = R;
45567 + }
45568 + else
45569 + {
45570 + R = R << 6; // shift TX power control to correct RF(R4) register bit position
45571 + R |= (pAd->LatchRfRegs.R4 & 0xfffff83f);
45572 + pAd->LatchRfRegs.R4 = R;
45573 + }
45574 + }
45575 + else// 5.5GHz
45576 + {
45577 + if (bPowerReduce == FALSE)
45578 + {
45579 + if (index == 0)
45580 + {
45581 + R = (R << 10) | (1 << 9); // shift TX power control to correct RF(R3) register bit position
45582 + R |= (pAd->LatchRfRegs.R3 & 0xffffc1ff);
45583 + pAd->LatchRfRegs.R3 = R;
45584 + }
45585 + else
45586 + {
45587 + R = (R << 7) | (1 << 6); // shift TX power control to correct RF(R4) register bit position
45588 + R |= (pAd->LatchRfRegs.R4 & 0xfffff83f);
45589 + pAd->LatchRfRegs.R4 = R;
45590 + }
45591 + }
45592 + else
45593 + {
45594 + if (index == 0)
45595 + {
45596 + R = (R << 10); // shift TX power control to correct RF(R3) register bit position
45597 + R |= (pAd->LatchRfRegs.R3 & 0xffffc1ff);
45598 +
45599 + /* Clear bit 9 of R3 to reduce 7dB. */
45600 + pAd->LatchRfRegs.R3 = (R & (~(1 << 9)));
45601 + }
45602 + else
45603 + {
45604 + R = (R << 7); // shift TX power control to correct RF(R4) register bit position
45605 + R |= (pAd->LatchRfRegs.R4 & 0xfffff83f);
45606 +
45607 + /* Clear bit 6 of R4 to reduce 7dB. */
45608 + pAd->LatchRfRegs.R4 = (R & (~(1 << 6)));
45609 + }
45610 + }
45611 + }
45612 +
45613 + RtmpRfIoWrite(pAd);
45614 +
45615 + return 0;
45616 + }
45617 +}
45618 +#else// 1 //
45619 +static INT ATETxPwrHandler(
45620 + IN PRTMP_ADAPTER pAd,
45621 + IN char index)
45622 +{
45623 + ULONG R;
45624 + CHAR TxPower;
45625 + UCHAR Bbp94 = 0;
45626 +
45627 +#ifdef RALINK_28xx_QA
45628 + if ((pAd->ate.bQATxStart == TRUE) || (pAd->ate.bQARxStart == TRUE))
45629 + {
45630 + // TODO: how to get current TxPower0/1 from pAd->LatchRfRegs ?
45631 + /* When QA is used for Tx, pAd->ate.TxPower0/1 and real tx power
45632 + ** are not synchronized.
45633 + */
45634 +/*
45635 + pAd->ate.TxPower0 = pAd->LatchRfRegs.xxx;
45636 + pAd->ate.TxPower1 = pAd->LatchRfRegs.xxx;
45637 +*/
45638 + return 0;
45639 + }
45640 + else
45641 +#endif // RALINK_28xx_QA //
45642 + {
45643 + TxPower = index == 0 ? pAd->ate.TxPower0 : pAd->ate.TxPower1;
45644 +
45645 + if (TxPower > 31)
45646 + {
45647 + //
45648 + // R3, R4 can't large than 36 (0x24), 31 ~ 36 used by BBP 94
45649 + //
45650 + R = 31;
45651 + if (TxPower <= 36)
45652 + Bbp94 = BBPR94_DEFAULT + (UCHAR)(TxPower - 31);
45653 + }
45654 + else if (TxPower < 0)
45655 + {
45656 + //
45657 + // R3, R4 can't less than 0, -1 ~ -6 used by BBP 94
45658 + //
45659 + R = 0;
45660 + if (TxPower >= -6)
45661 + Bbp94 = BBPR94_DEFAULT + TxPower;
45662 + }
45663 + else
45664 + {
45665 + // 0 ~ 31
45666 + R = (ULONG) TxPower;
45667 + Bbp94 = BBPR94_DEFAULT;
45668 + }
45669 +
45670 + ATEDBGPRINT(RT_DEBUG_TRACE, ("%s (TxPower=%d, R3=%ld, BBP_R94=%d)\n", __FUNCTION__, TxPower, R, Bbp94));
45671 +
45672 + if (pAd->ate.Channel <= 14)
45673 + {
45674 + if (index == 0)
45675 + {
45676 + R = R << 9; // shift TX power control to correct RF(R3) register bit position
45677 + R |= (pAd->LatchRfRegs.R3 & 0xffffc1ff);
45678 + pAd->LatchRfRegs.R3 = R;
45679 + }
45680 + else
45681 + {
45682 + R = R << 6; // shift TX power control to correct RF(R4) register bit position
45683 + R |= (pAd->LatchRfRegs.R4 & 0xfffff83f);
45684 + pAd->LatchRfRegs.R4 = R;
45685 + }
45686 + }
45687 + else
45688 + {
45689 + if (index == 0)
45690 + {
45691 + R = (R << 10) | (1 << 9); // shift TX power control to correct RF(R3) register bit position
45692 + R |= (pAd->LatchRfRegs.R3 & 0xffffc1ff);
45693 + pAd->LatchRfRegs.R3 = R;
45694 + }
45695 + else
45696 + {
45697 + R = (R << 7) | (1 << 6); // shift TX power control to correct RF(R4) register bit position
45698 + R |= (pAd->LatchRfRegs.R4 & 0xfffff83f);
45699 + pAd->LatchRfRegs.R4 = R;
45700 + }
45701 + }
45702 +
45703 + RtmpRfIoWrite(pAd);
45704 +
45705 + return 0;
45706 + }
45707 +}
45708 +#endif // 1 //
45709 +/*
45710 + ==========================================================================
45711 + Description:
45712 + Set ATE operation mode to
45713 + 0. ATESTART = Start ATE Mode
45714 + 1. ATESTOP = Stop ATE Mode
45715 + 2. TXCONT = Continuous Transmit
45716 + 3. TXCARR = Transmit Carrier
45717 + 4. TXFRAME = Transmit Frames
45718 + 5. RXFRAME = Receive Frames
45719 +#ifdef RALINK_28xx_QA
45720 + 6. TXSTOP = Stop Any Type of Transmition
45721 + 7. RXSTOP = Stop Receiving Frames
45722 +#endif // RALINK_28xx_QA //
45723 + Return:
45724 + TRUE if all parameters are OK, FALSE otherwise
45725 + ==========================================================================
45726 +*/
45727 +#ifdef RT2860
45728 +static INT ATECmdHandler(
45729 + IN PRTMP_ADAPTER pAd,
45730 + IN PUCHAR arg)
45731 +{
45732 + UINT32 Value = 0;
45733 + UCHAR BbpData;
45734 + UINT32 MacData = 0;
45735 + PTXD_STRUC pTxD;
45736 + INT index;
45737 + UINT i=0, atemode;
45738 + PRXD_STRUC pRxD;
45739 + PRTMP_TX_RING pTxRing = &pAd->TxRing[QID_AC_BE];
45740 +#ifndef UCOS
45741 + NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
45742 +#endif // UCOS //
45743 +#ifdef RT_BIG_ENDIAN
45744 + PTXD_STRUC pDestTxD;
45745 + TXD_STRUC TxD;
45746 +#endif
45747 + ATEDBGPRINT(RT_DEBUG_TRACE, ("===> ATECmdHandler()\n"));
45748 +
45749 + ATEAsicSwitchChannel(pAd);
45750 + AsicLockChannel(pAd, pAd->ate.Channel);
45751 +
45752 + RTMPusecDelay(5000);
45753 +
45754 + // read MAC_SYS_CTRL and backup MAC_SYS_CTRL value.
45755 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &MacData);
45756 +
45757 + // Default value in BBP R22 is 0x0.
45758 + BbpData = 0;
45759 +
45760 + // clean bit4 to stop continuous Tx production test.
45761 + MacData &= 0xFFFFFFEF;
45762 +
45763 + if (!strcmp(arg, "ATESTART")) //Enter ATE mode and set Tx/Rx Idle
45764 + {
45765 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: ATESTART\n"));
45766 +
45767 +#ifndef UCOS
45768 + // check if we have removed the firmware
45769 + if (!(ATE_ON(pAd)))
45770 + {
45771 + NICEraseFirmware(pAd);
45772 + }
45773 +#endif // !UCOS //
45774 + atemode = pAd->ate.Mode;
45775 + pAd->ate.Mode = ATE_START;
45776 +// pAd->ate.TxDoneCount = pAd->ate.TxCount;
45777 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, MacData);
45778 +
45779 + if (atemode & ATE_TXCARR)
45780 + {
45781 + // No Carrier Test set BBP R22 bit7=0, bit6=0, bit[5~0]=0x0
45782 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
45783 + BbpData &= 0xFFFFFF00; //clear bit7, bit6, bit[5~0]
45784 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
45785 + }
45786 + else if (atemode & ATE_TXCARRSUPP)
45787 + {
45788 + // No Cont. TX set BBP R22 bit7=0
45789 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
45790 + BbpData &= ~(1 << 7); //set bit7=0
45791 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
45792 +
45793 + // No Carrier Suppression set BBP R24 bit0=0
45794 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R24, &BbpData);
45795 + BbpData &= 0xFFFFFFFE; //clear bit0
45796 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R24, BbpData);
45797 + }
45798 + // We should free some resource which was allocated when ATE_TXFRAME , ATE_STOP, and ATE_TXCONT.
45799 + else if ((atemode & ATE_TXFRAME) || (atemode == ATE_STOP))
45800 + {
45801 + PRTMP_TX_RING pTxRing = &pAd->TxRing[QID_AC_BE];
45802 +
45803 + if (atemode & ATE_TXCONT)
45804 + {
45805 + // No Cont. TX set BBP R22 bit7=0
45806 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
45807 + BbpData &= ~(1 << 7); //set bit7=0
45808 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
45809 + }
45810 + // Abort Tx, Rx DMA.
45811 + RtmpDmaEnable(pAd, 0);
45812 + for (i=0; i<TX_RING_SIZE; i++)
45813 + {
45814 + PNDIS_PACKET pPacket;
45815 +
45816 +#ifndef RT_BIG_ENDIAN
45817 + pTxD = (PTXD_STRUC)pAd->TxRing[QID_AC_BE].Cell[i].AllocVa;
45818 +#else
45819 + pDestTxD = (PTXD_STRUC)pAd->TxRing[QID_AC_BE].Cell[i].AllocVa;
45820 + TxD = *pDestTxD;
45821 + pTxD = &TxD;
45822 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
45823 +#endif
45824 + pTxD->DMADONE = 0;
45825 + pPacket = pTxRing->Cell[i].pNdisPacket;
45826 + if (pPacket)
45827 + {
45828 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
45829 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
45830 + }
45831 + //Always assign pNdisPacket as NULL after clear
45832 + pTxRing->Cell[i].pNdisPacket = NULL;
45833 +
45834 + pPacket = pTxRing->Cell[i].pNextNdisPacket;
45835 + if (pPacket)
45836 + {
45837 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
45838 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
45839 + }
45840 + //Always assign pNextNdisPacket as NULL after clear
45841 + pTxRing->Cell[i].pNextNdisPacket = NULL;
45842 +#ifdef RT_BIG_ENDIAN
45843 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
45844 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
45845 +#endif
45846 + }
45847 + // Start Tx, RX DMA
45848 + RtmpDmaEnable(pAd, 1);
45849 + }
45850 + // reset Rx statistics.
45851 + pAd->ate.LastSNR0 = 0;
45852 + pAd->ate.LastSNR1 = 0;
45853 + pAd->ate.LastRssi0 = 0;
45854 + pAd->ate.LastRssi1 = 0;
45855 + pAd->ate.LastRssi2 = 0;
45856 + pAd->ate.AvgRssi0 = 0;
45857 + pAd->ate.AvgRssi1 = 0;
45858 + pAd->ate.AvgRssi2 = 0;
45859 + pAd->ate.AvgRssi0X8 = 0;
45860 + pAd->ate.AvgRssi1X8 = 0;
45861 + pAd->ate.AvgRssi2X8 = 0;
45862 + pAd->ate.NumOfAvgRssiSample = 0;
45863 +
45864 +#ifdef RALINK_28xx_QA
45865 + // Tx frame
45866 + pAd->ate.bQATxStart = FALSE;
45867 + pAd->ate.bQARxStart = FALSE;
45868 + pAd->ate.seq = 0;
45869 +
45870 + // counters
45871 + pAd->ate.U2M = 0;
45872 + pAd->ate.OtherData = 0;
45873 + pAd->ate.Beacon = 0;
45874 + pAd->ate.OtherCount = 0;
45875 + pAd->ate.TxAc0 = 0;
45876 + pAd->ate.TxAc1 = 0;
45877 + pAd->ate.TxAc2 = 0;
45878 + pAd->ate.TxAc3 = 0;
45879 + pAd->ate.TxHCCA = 0;
45880 + pAd->ate.TxMgmt = 0;
45881 + pAd->ate.RSSI0 = 0;
45882 + pAd->ate.RSSI1 = 0;
45883 + pAd->ate.RSSI2 = 0;
45884 + pAd->ate.SNR0 = 0;
45885 + pAd->ate.SNR1 = 0;
45886 +
45887 + // control
45888 + pAd->ate.TxDoneCount = 0;
45889 + pAd->ate.TxStatus = 0; // task Tx status // 0 --> task is idle, 1 --> task is running
45890 +#endif // RALINK_28xx_QA //
45891 +
45892 + // Soft reset BBP.
45893 + BbpSoftReset(pAd);
45894 +
45895 +
45896 +#ifdef CONFIG_STA_SUPPORT
45897 + //
45898 + // LinkDown() has "AsicDisableSync();" and "RTMP_BBP_IO_R/W8_BY_REG_ID();" inside.
45899 + //
45900 +// LinkDown(pAd, FALSE);
45901 +// AsicEnableBssSync(pAd);
45902 +#ifndef UCOS
45903 + netif_stop_queue(pAd->net_dev);
45904 +#endif // !UCOS //
45905 + //
45906 + // If we skip "LinkDown()", we should disable protection
45907 + // to prevent from sending out RTS or CTS-to-self.
45908 + //
45909 + ATEDisableAsicProtect(pAd);
45910 + RTMPStationStop(pAd);
45911 +#endif // CONFIG_STA_SUPPORT //
45912 +
45913 + /* Disable Tx */
45914 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
45915 + Value &= ~(1 << 2);
45916 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
45917 +
45918 + /* Disable Rx */
45919 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
45920 + Value &= ~(1 << 3);
45921 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
45922 + }
45923 + else if (!strcmp(arg, "ATESTOP"))
45924 + {
45925 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: ATESTOP\n"));
45926 +
45927 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
45928 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, MacData); // recover the MAC_SYS_CTRL register back.
45929 +
45930 + // Disable Tx, Rx
45931 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
45932 + Value &= (0xfffffff3);
45933 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
45934 +
45935 + // Abort Tx, RX DMA.
45936 + RtmpDmaEnable(pAd, 0);
45937 +
45938 +#ifndef UCOS
45939 + pAd->ate.bFWLoading = TRUE;
45940 + Status = NICLoadFirmware(pAd);
45941 + if (Status != NDIS_STATUS_SUCCESS)
45942 + {
45943 + ATEDBGPRINT(RT_DEBUG_ERROR, ("NICLoadFirmware failed, Status[=0x%08x]\n", Status));
45944 + return FALSE;
45945 + }
45946 +#endif // !UCOS //
45947 + pAd->ate.Mode = ATE_STOP;
45948 +
45949 +
45950 +#ifdef CONFIG_STA_SUPPORT
45951 + //
45952 + // Even the firmware has been loaded,
45953 + // we still could use ATE_BBP_IO_READ8_BY_REG_ID().
45954 + // But this is not suggested.
45955 + //
45956 + BbpSoftReset(pAd);
45957 +#endif // CONFIG_STA_SUPPORT //
45958 +
45959 + NICDisableInterrupt(pAd);
45960 +
45961 + NICInitializeAdapter(pAd, TRUE);
45962 +
45963 +
45964 + // Reinitialize Rx Ring before Rx DMA is enabled.
45965 + // The nightmare of >>>RxCoherent<<< was gone !
45966 + for (index = 0; index < RX_RING_SIZE; index++)
45967 + {
45968 + pRxD = (PRXD_STRUC) pAd->RxRing.Cell[index].AllocVa;
45969 + pRxD->DDONE = 0;
45970 + }
45971 +
45972 + // We should read EEPROM for all cases.
45973 + NICReadEEPROMParameters(pAd, NULL);
45974 + NICInitAsicFromEEPROM(pAd);
45975 +
45976 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
45977 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
45978 +
45979 + //
45980 + // Enable Interrupt
45981 + //
45982 +
45983 + //
45984 + // These steps are only for APAutoSelectChannel().
45985 + //
45986 +#if 0
45987 + //pAd->bStaFifoTest = TRUE;
45988 + pAd->int_enable_reg = ((DELAYINTMASK) | (RxINT|TxDataInt|TxMgmtInt)) & ~(0x03);
45989 + pAd->int_disable_mask = 0;
45990 + pAd->int_pending = 0;
45991 +#endif
45992 + RTMP_IO_WRITE32(pAd, INT_SOURCE_CSR, 0xffffffff); // clear garbage interrupts
45993 + NICEnableInterrupt(pAd);
45994 +
45995 +
45996 +/*=========================================================================*/
45997 + /* restore RX_FILTR_CFG */
45998 +#ifdef CONFIG_STA_SUPPORT
45999 + /* restore RX_FILTR_CFG due to that QA maybe set it to 0x3 */
46000 + RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, STANORMAL);
46001 +#endif // CONFIG_STA_SUPPORT //
46002 +/*=========================================================================*/
46003 +
46004 + // Enable Tx
46005 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46006 + Value |= (1 << 2);
46007 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46008 +
46009 + // Enable Tx, Rx DMA.
46010 + RtmpDmaEnable(pAd, 1);
46011 +
46012 + // Enable Rx
46013 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46014 + Value |= (1 << 3);
46015 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46016 +
46017 +
46018 +#ifdef CONFIG_STA_SUPPORT
46019 + RTMPStationStart(pAd);
46020 +#endif // CONFIG_STA_SUPPORT //
46021 +#ifndef UCOS
46022 + netif_start_queue(pAd->net_dev);
46023 +#endif // !UCOS //
46024 + }
46025 + else if (!strcmp(arg, "TXCARR")) // Tx Carrier
46026 + {
46027 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: TXCARR\n"));
46028 + pAd->ate.Mode |= ATE_TXCARR;
46029 +
46030 + // QA has done the following steps if it is used.
46031 + if (pAd->ate.bQATxStart == FALSE)
46032 + {
46033 + // Soft reset BBP.
46034 + BbpSoftReset(pAd);
46035 +
46036 + // Carrier Test set BBP R22 bit7=1, bit6=1, bit[5~0]=0x01
46037 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
46038 + BbpData &= 0xFFFFFF00; //clear bit7, bit6, bit[5~0]
46039 + BbpData |= 0x000000C1; //set bit7=1, bit6=1, bit[5~0]=0x01
46040 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46041 +
46042 + // set MAC_SYS_CTRL(0x1004) Continuous Tx Production Test (bit4) = 1
46043 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46044 + Value = Value | 0x00000010;
46045 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46046 + }
46047 + }
46048 + else if (!strcmp(arg, "TXCONT")) // Tx Continue
46049 + {
46050 + if (pAd->ate.bQATxStart == TRUE)
46051 + {
46052 + /* set MAC_SYS_CTRL(0x1004) bit4(Continuous Tx Production Test)
46053 + and bit2(MAC TX enable) back to zero. */
46054 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &MacData);
46055 + MacData &= 0xFFFFFFEB;
46056 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, MacData);
46057 +
46058 + // set BBP R22 bit7=0
46059 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
46060 + BbpData &= 0xFFFFFF7F; //set bit7=0
46061 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46062 + }
46063 +
46064 + /* for TxCont mode.
46065 + ** Step 1: Send 50 packets first then wait for a moment.
46066 + ** Step 2: Send more 50 packet then start continue mode.
46067 + */
46068 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: TXCONT\n"));
46069 + // Step 1: send 50 packets first.
46070 + pAd->ate.Mode |= ATE_TXCONT;
46071 + pAd->ate.TxCount = 50;
46072 + /* Do it after Tx/Rx DMA is aborted. */
46073 +// pAd->ate.TxDoneCount = 0;
46074 +
46075 + // Soft reset BBP.
46076 + BbpSoftReset(pAd);
46077 +
46078 + // Abort Tx, RX DMA.
46079 + RtmpDmaEnable(pAd, 0);
46080 +
46081 + // Fix can't smooth kick
46082 + {
46083 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + QID_AC_BE * 0x10, &pTxRing->TxDmaIdx);
46084 + pTxRing->TxSwFreeIdx = pTxRing->TxDmaIdx;
46085 + pTxRing->TxCpuIdx = pTxRing->TxDmaIdx;
46086 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QID_AC_BE * 0x10, pTxRing->TxCpuIdx);
46087 + }
46088 +
46089 + pAd->ate.TxDoneCount = 0;
46090 +
46091 + /* Only needed if we have to send some normal frames. */
46092 + SetJapanFilter(pAd);
46093 +
46094 + for (i = 0; (i < TX_RING_SIZE-1) && (i < pAd->ate.TxCount); i++)
46095 + {
46096 + PNDIS_PACKET pPacket;
46097 + UINT32 TxIdx = pTxRing->TxCpuIdx;
46098 +
46099 +#ifndef RT_BIG_ENDIAN
46100 + pTxD = (PTXD_STRUC)pTxRing->Cell[TxIdx].AllocVa;
46101 +#else
46102 + pDestTxD = (PTXD_STRUC)pTxRing->Cell[TxIdx].AllocVa;
46103 + TxD = *pDestTxD;
46104 + pTxD = &TxD;
46105 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46106 +#endif
46107 + // Clean current cell.
46108 + pPacket = pTxRing->Cell[TxIdx].pNdisPacket;
46109 + if (pPacket)
46110 + {
46111 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
46112 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46113 + }
46114 + //Always assign pNdisPacket as NULL after clear
46115 + pTxRing->Cell[TxIdx].pNdisPacket = NULL;
46116 +
46117 + pPacket = pTxRing->Cell[TxIdx].pNextNdisPacket;
46118 + if (pPacket)
46119 + {
46120 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
46121 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46122 + }
46123 + //Always assign pNextNdisPacket as NULL after clear
46124 + pTxRing->Cell[TxIdx].pNextNdisPacket = NULL;
46125 +
46126 +#ifdef RT_BIG_ENDIAN
46127 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46128 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
46129 +#endif
46130 +
46131 + if (ATESetUpFrame(pAd, TxIdx) != 0)
46132 + break;
46133 +
46134 + INC_RING_INDEX(pTxRing->TxCpuIdx, TX_RING_SIZE);
46135 + }
46136 +
46137 + // Setup frame format.
46138 + ATESetUpFrame(pAd, pTxRing->TxCpuIdx);
46139 +
46140 + // Start Tx, RX DMA.
46141 + RtmpDmaEnable(pAd, 1);
46142 +
46143 + // Enable Tx
46144 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46145 + Value |= (1 << 2);
46146 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46147 +
46148 + // Disable Rx
46149 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46150 + Value &= ~(1 << 3);
46151 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46152 +
46153 +#ifdef RALINK_28xx_QA
46154 + if (pAd->ate.bQATxStart == TRUE)
46155 + {
46156 + pAd->ate.TxStatus = 1;
46157 + //pAd->ate.Repeat = 0;
46158 + }
46159 +#endif // RALINK_28xx_QA //
46160 +
46161 + // kick Tx-Ring.
46162 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QID_AC_BE * RINGREG_DIFF, pAd->TxRing[QID_AC_BE].TxCpuIdx);
46163 +
46164 + RTMPusecDelay(5000);
46165 +
46166 +
46167 + // Step 2: send more 50 packets then start continue mode.
46168 + // Abort Tx, RX DMA.
46169 + RtmpDmaEnable(pAd, 0);
46170 +
46171 + // Cont. TX set BBP R22 bit7=1
46172 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
46173 + BbpData |= 0x00000080; //set bit7=1
46174 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46175 +
46176 + pAd->ate.TxCount = 50;
46177 +
46178 + // Fix can't smooth kick
46179 + {
46180 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + QID_AC_BE * 0x10, &pTxRing->TxDmaIdx);
46181 + pTxRing->TxSwFreeIdx = pTxRing->TxDmaIdx;
46182 + pTxRing->TxCpuIdx = pTxRing->TxDmaIdx;
46183 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QID_AC_BE * 0x10, pTxRing->TxCpuIdx);
46184 + }
46185 +
46186 + pAd->ate.TxDoneCount = 0;
46187 +
46188 + SetJapanFilter(pAd);
46189 +
46190 + for (i = 0; (i < TX_RING_SIZE-1) && (i < pAd->ate.TxCount); i++)
46191 + {
46192 + PNDIS_PACKET pPacket;
46193 + UINT32 TxIdx = pTxRing->TxCpuIdx;
46194 +
46195 +#ifndef RT_BIG_ENDIAN
46196 + pTxD = (PTXD_STRUC)pTxRing->Cell[TxIdx].AllocVa;
46197 +#else
46198 + pDestTxD = (PTXD_STRUC)pTxRing->Cell[TxIdx].AllocVa;
46199 + TxD = *pDestTxD;
46200 + pTxD = &TxD;
46201 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46202 +#endif
46203 + // clean current cell.
46204 + pPacket = pTxRing->Cell[TxIdx].pNdisPacket;
46205 + if (pPacket)
46206 + {
46207 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
46208 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46209 + }
46210 + //Always assign pNdisPacket as NULL after clear
46211 + pTxRing->Cell[TxIdx].pNdisPacket = NULL;
46212 +
46213 + pPacket = pTxRing->Cell[TxIdx].pNextNdisPacket;
46214 + if (pPacket)
46215 + {
46216 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
46217 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46218 + }
46219 + //Always assign pNextNdisPacket as NULL after clear
46220 + pTxRing->Cell[TxIdx].pNextNdisPacket = NULL;
46221 +
46222 +#ifdef RT_BIG_ENDIAN
46223 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46224 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
46225 +#endif
46226 +
46227 + if (ATESetUpFrame(pAd, TxIdx) != 0)
46228 + break;
46229 +
46230 + INC_RING_INDEX(pTxRing->TxCpuIdx, TX_RING_SIZE);
46231 + }
46232 +
46233 + ATESetUpFrame(pAd, pTxRing->TxCpuIdx);
46234 +
46235 + // Start Tx, RX DMA.
46236 + RtmpDmaEnable(pAd, 1);
46237 +
46238 + // Enable Tx
46239 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46240 + Value |= (1 << 2);
46241 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46242 +
46243 + // Disable Rx
46244 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46245 + Value &= ~(1 << 3);
46246 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46247 +
46248 +#ifdef RALINK_28xx_QA
46249 + if (pAd->ate.bQATxStart == TRUE)
46250 + {
46251 + pAd->ate.TxStatus = 1;
46252 + //pAd->ate.Repeat = 0;
46253 + }
46254 +#endif // RALINK_28xx_QA //
46255 +
46256 + // kick Tx-Ring.
46257 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QID_AC_BE * RINGREG_DIFF, pAd->TxRing[QID_AC_BE].TxCpuIdx);
46258 +
46259 + RTMPusecDelay(500);
46260 +
46261 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &MacData);
46262 + MacData |= 0x00000010;
46263 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, MacData);
46264 + }
46265 + else if (!strcmp(arg, "TXFRAME")) // Tx Frames
46266 + {
46267 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: TXFRAME(Count=%d)\n", pAd->ate.TxCount));
46268 + pAd->ate.Mode |= ATE_TXFRAME;
46269 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46270 +
46271 + // Soft reset BBP.
46272 + BbpSoftReset(pAd);
46273 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, MacData);
46274 +
46275 + // Abort Tx, RX DMA.
46276 + RtmpDmaEnable(pAd, 0);
46277 +
46278 + // Fix can't smooth kick
46279 + {
46280 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + QID_AC_BE * 0x10, &pTxRing->TxDmaIdx);
46281 + pTxRing->TxSwFreeIdx = pTxRing->TxDmaIdx;
46282 + pTxRing->TxCpuIdx = pTxRing->TxDmaIdx;
46283 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QID_AC_BE * 0x10, pTxRing->TxCpuIdx);
46284 + }
46285 +
46286 + pAd->ate.TxDoneCount = 0;
46287 +
46288 + SetJapanFilter(pAd);
46289 +
46290 + for (i = 0; (i < TX_RING_SIZE-1) && (i < pAd->ate.TxCount); i++)
46291 + {
46292 + PNDIS_PACKET pPacket;
46293 + UINT32 TxIdx = pTxRing->TxCpuIdx;
46294 +
46295 +#ifndef RT_BIG_ENDIAN
46296 + pTxD = (PTXD_STRUC)pTxRing->Cell[TxIdx].AllocVa;
46297 +#else
46298 + pDestTxD = (PTXD_STRUC)pTxRing->Cell[TxIdx].AllocVa;
46299 + TxD = *pDestTxD;
46300 + pTxD = &TxD;
46301 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46302 +#endif
46303 + // Clean current cell.
46304 + pPacket = pTxRing->Cell[TxIdx].pNdisPacket;
46305 + if (pPacket)
46306 + {
46307 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
46308 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46309 + }
46310 + //Always assign pNdisPacket as NULL after clear
46311 + pTxRing->Cell[TxIdx].pNdisPacket = NULL;
46312 +
46313 + pPacket = pTxRing->Cell[TxIdx].pNextNdisPacket;
46314 + if (pPacket)
46315 + {
46316 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
46317 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46318 + }
46319 + //Always assign pNextNdisPacket as NULL after clear
46320 + pTxRing->Cell[TxIdx].pNextNdisPacket = NULL;
46321 +
46322 +#ifdef RT_BIG_ENDIAN
46323 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46324 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
46325 +#endif
46326 +
46327 + if (ATESetUpFrame(pAd, TxIdx) != 0)
46328 + break;
46329 +
46330 + INC_RING_INDEX(pTxRing->TxCpuIdx, TX_RING_SIZE);
46331 +
46332 + }
46333 +
46334 + ATESetUpFrame(pAd, pTxRing->TxCpuIdx);
46335 +
46336 + // Start Tx, Rx DMA.
46337 + RtmpDmaEnable(pAd, 1);
46338 +
46339 + // Enable Tx
46340 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46341 + Value |= (1 << 2);
46342 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46343 +#ifdef RALINK_28xx_QA
46344 + // add this for LoopBack mode
46345 + if (pAd->ate.bQARxStart == FALSE)
46346 + {
46347 + // Disable Rx
46348 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46349 + Value &= ~(1 << 3);
46350 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46351 + }
46352 +
46353 + if (pAd->ate.bQATxStart == TRUE)
46354 + {
46355 + pAd->ate.TxStatus = 1;
46356 + //pAd->ate.Repeat = 0;
46357 + }
46358 +#else
46359 + // Disable Rx
46360 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46361 + Value &= ~(1 << 3);
46362 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46363 +#endif // RALINK_28xx_QA //
46364 +
46365 + RTMP_IO_READ32(pAd, TX_DTX_IDX0 + QID_AC_BE * RINGREG_DIFF, &pAd->TxRing[QID_AC_BE].TxDmaIdx);
46366 + // kick Tx-Ring.
46367 + RTMP_IO_WRITE32(pAd, TX_CTX_IDX0 + QID_AC_BE * RINGREG_DIFF, pAd->TxRing[QID_AC_BE].TxCpuIdx);
46368 +
46369 + pAd->RalinkCounters.KickTxCount++;
46370 + }
46371 +#ifdef RALINK_28xx_QA
46372 + else if (!strcmp(arg, "TXSTOP"))
46373 + {
46374 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: TXSTOP\n"));
46375 + atemode = pAd->ate.Mode;
46376 + pAd->ate.Mode &= ATE_TXSTOP;
46377 + pAd->ate.bQATxStart = FALSE;
46378 +// pAd->ate.TxDoneCount = pAd->ate.TxCount;
46379 +
46380 + if (atemode & ATE_TXCARR)
46381 + {
46382 + // No Carrier Test set BBP R22 bit7=0, bit6=0, bit[5~0]=0x0
46383 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
46384 + BbpData &= 0xFFFFFF00; //clear bit7, bit6, bit[5~0]
46385 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46386 + }
46387 + else if (atemode & ATE_TXCARRSUPP)
46388 + {
46389 + // No Cont. TX set BBP R22 bit7=0
46390 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
46391 + BbpData &= ~(1 << 7); //set bit7=0
46392 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46393 +
46394 + // No Carrier Suppression set BBP R24 bit0=0
46395 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R24, &BbpData);
46396 + BbpData &= 0xFFFFFFFE; //clear bit0
46397 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R24, BbpData);
46398 + }
46399 + // We should free some resource which allocate when ATE_TXFRAME , ATE_STOP, and ATE_TXCONT.
46400 + else if ((atemode & ATE_TXFRAME) || (atemode == ATE_STOP))
46401 + {
46402 +
46403 + PRTMP_TX_RING pTxRing = &pAd->TxRing[QID_AC_BE];
46404 +
46405 + if (atemode & ATE_TXCONT)
46406 + {
46407 + // No Cont. TX set BBP R22 bit7=0
46408 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R22, &BbpData);
46409 + BbpData &= ~(1 << 7); //set bit7=0
46410 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46411 + }
46412 +
46413 + // Abort Tx, Rx DMA.
46414 + RtmpDmaEnable(pAd, 0);
46415 + for (i=0; i<TX_RING_SIZE; i++)
46416 + {
46417 + PNDIS_PACKET pPacket;
46418 +
46419 +#ifndef RT_BIG_ENDIAN
46420 + pTxD = (PTXD_STRUC)pAd->TxRing[QID_AC_BE].Cell[i].AllocVa;
46421 +#else
46422 + pDestTxD = (PTXD_STRUC)pAd->TxRing[QID_AC_BE].Cell[i].AllocVa;
46423 + TxD = *pDestTxD;
46424 + pTxD = &TxD;
46425 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46426 +#endif
46427 + pTxD->DMADONE = 0;
46428 + pPacket = pTxRing->Cell[i].pNdisPacket;
46429 + if (pPacket)
46430 + {
46431 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr0, pTxD->SDLen0, PCI_DMA_TODEVICE);
46432 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46433 + }
46434 + //Always assign pNdisPacket as NULL after clear
46435 + pTxRing->Cell[i].pNdisPacket = NULL;
46436 +
46437 + pPacket = pTxRing->Cell[i].pNextNdisPacket;
46438 + if (pPacket)
46439 + {
46440 + PCI_UNMAP_SINGLE(pAd, pTxD->SDPtr1, pTxD->SDLen1, PCI_DMA_TODEVICE);
46441 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_SUCCESS);
46442 + }
46443 + //Always assign pNextNdisPacket as NULL after clear
46444 + pTxRing->Cell[i].pNextNdisPacket = NULL;
46445 +#ifdef RT_BIG_ENDIAN
46446 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
46447 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
46448 +#endif
46449 + }
46450 + // Enable Tx, Rx DMA
46451 + RtmpDmaEnable(pAd, 1);
46452 +
46453 + }
46454 +
46455 + // control
46456 +// pAd->ate.TxDoneCount = 0;
46457 + pAd->ate.TxStatus = 0; // task Tx status // 0 --> task is idle, 1 --> task is running
46458 +
46459 + // Soft reset BBP.
46460 + BbpSoftReset(pAd);
46461 +
46462 + // Disable Tx
46463 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46464 + Value &= ~(1 << 2);
46465 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46466 + }
46467 + else if (!strcmp(arg, "RXSTOP"))
46468 + {
46469 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: RXSTOP\n"));
46470 + atemode = pAd->ate.Mode;
46471 + pAd->ate.Mode &= ATE_RXSTOP;
46472 + pAd->ate.bQARxStart = FALSE;
46473 +// pAd->ate.TxDoneCount = pAd->ate.TxCount;
46474 +
46475 + if (atemode & ATE_TXCARR)
46476 + {
46477 + ;
46478 + }
46479 + else if (atemode & ATE_TXCARRSUPP)
46480 + {
46481 + ;
46482 + }
46483 +
46484 + // We should free some resource which was allocated when ATE_TXFRAME , ATE_STOP, and ATE_TXCONT.
46485 + else if ((atemode & ATE_TXFRAME) || (atemode == ATE_STOP))
46486 + {
46487 + if (atemode & ATE_TXCONT)
46488 + {
46489 + ;
46490 + }
46491 + }
46492 +
46493 + // control
46494 +// pAd->ate.TxDoneCount = 0;
46495 +// pAd->ate.TxStatus = 0; // task Tx status // 0 --> task is idle, 1 --> task is running
46496 +
46497 + // Soft reset BBP.
46498 + BbpSoftReset(pAd);
46499 +
46500 + // Disable Rx
46501 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46502 + Value &= ~(1 << 3);
46503 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46504 + }
46505 +#endif // RALINK_28xx_QA //
46506 + else if (!strcmp(arg, "RXFRAME")) // Rx Frames
46507 + {
46508 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: RXFRAME\n"));
46509 +
46510 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R22, BbpData);
46511 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, MacData);
46512 +
46513 + pAd->ate.Mode |= ATE_RXFRAME;
46514 +
46515 + // Disable Tx of MAC block.
46516 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46517 + Value &= ~(1 << 2);
46518 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46519 +
46520 + // Enable Rx of MAC block.
46521 + RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value);
46522 + Value |= (1 << 3);
46523 + RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value);
46524 + }
46525 + else
46526 + {
46527 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATE: Invalid arg!\n"));
46528 + return FALSE;
46529 + }
46530 + RTMPusecDelay(5000);
46531 +
46532 + ATEDBGPRINT(RT_DEBUG_TRACE, ("<=== ATECmdHandler()\n"));
46533 +
46534 + return TRUE;
46535 +}
46536 +#endif // RT2860 //
46537 +/* */
46538 +/* */
46539 +/*=======================End of RT2860=======================*/
46540 +
46541 +
46542 +/*======================Start of RT2870======================*/
46543 +/* */
46544 +/* */
46545 +
46546 +
46547 +INT Set_ATE_Proc(
46548 + IN PRTMP_ADAPTER pAd,
46549 + IN PUCHAR arg)
46550 +{
46551 + if (ATECmdHandler(pAd, arg))
46552 + {
46553 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_Proc Success\n"));
46554 +
46555 +
46556 + return TRUE;
46557 + }
46558 + else
46559 + {
46560 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_Proc Failed\n"));
46561 + return FALSE;
46562 + }
46563 +}
46564 +
46565 +/*
46566 + ==========================================================================
46567 + Description:
46568 + Set ATE ADDR1=DA for TxFrame(AP : To DS = 0 ; From DS = 1)
46569 + or
46570 + Set ATE ADDR3=DA for TxFrame(STA : To DS = 1 ; From DS = 0)
46571 +
46572 + Return:
46573 + TRUE if all parameters are OK, FALSE otherwise
46574 + ==========================================================================
46575 +*/
46576 +INT Set_ATE_DA_Proc(
46577 + IN PRTMP_ADAPTER pAd,
46578 + IN PUCHAR arg)
46579 +{
46580 + CHAR *value;
46581 + INT i;
46582 +
46583 + if(strlen(arg) != 17) //Mac address acceptable format 01:02:03:04:05:06 length 17
46584 + return FALSE;
46585 +
46586 + for (i=0, value = rstrtok(arg, ":"); value; value = rstrtok(NULL, ":"))
46587 + {
46588 + if((strlen(value) != 2) || (!isxdigit(*value)) || (!isxdigit(*(value+1))) )
46589 + return FALSE; //Invalid
46590 +
46591 +
46592 +#ifdef CONFIG_STA_SUPPORT
46593 + AtoH(value, &pAd->ate.Addr3[i++], 1);
46594 +#endif // CONFIG_STA_SUPPORT //
46595 + }
46596 +
46597 + if(i != 6)
46598 + return FALSE; //Invalid
46599 +
46600 +
46601 +#ifdef CONFIG_STA_SUPPORT
46602 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_DA_Proc (DA = %2X:%2X:%2X:%2X:%2X:%2X)\n", pAd->ate.Addr3[0],
46603 + pAd->ate.Addr3[1], pAd->ate.Addr3[2], pAd->ate.Addr3[3], pAd->ate.Addr3[4], pAd->ate.Addr3[5]));
46604 +#endif // CONFIG_STA_SUPPORT //
46605 +
46606 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_DA_Proc Success\n"));
46607 +
46608 + return TRUE;
46609 +}
46610 +
46611 +/*
46612 + ==========================================================================
46613 + Description:
46614 + Set ATE ADDR3=SA for TxFrame(AP : To DS = 0 ; From DS = 1)
46615 + or
46616 + Set ATE ADDR2=SA for TxFrame(STA : To DS = 1 ; From DS = 0)
46617 +
46618 + Return:
46619 + TRUE if all parameters are OK, FALSE otherwise
46620 + ==========================================================================
46621 +*/
46622 +INT Set_ATE_SA_Proc(
46623 + IN PRTMP_ADAPTER pAd,
46624 + IN PUCHAR arg)
46625 +{
46626 + CHAR *value;
46627 + INT i;
46628 +
46629 + if(strlen(arg) != 17) //Mac address acceptable format 01:02:03:04:05:06 length 17
46630 + return FALSE;
46631 +
46632 + for (i=0, value = rstrtok(arg, ":"); value; value = rstrtok(NULL, ":"))
46633 + {
46634 + if((strlen(value) != 2) || (!isxdigit(*value)) || (!isxdigit(*(value+1))) )
46635 + return FALSE; //Invalid
46636 +
46637 +
46638 +#ifdef CONFIG_STA_SUPPORT
46639 + AtoH(value, &pAd->ate.Addr2[i++], 1);
46640 +#endif // CONFIG_STA_SUPPORT //
46641 + }
46642 +
46643 + if(i != 6)
46644 + return FALSE; //Invalid
46645 +
46646 +
46647 +#ifdef CONFIG_STA_SUPPORT
46648 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_SA_Proc (SA = %2X:%2X:%2X:%2X:%2X:%2X)\n", pAd->ate.Addr2[0],
46649 + pAd->ate.Addr2[1], pAd->ate.Addr2[2], pAd->ate.Addr2[3], pAd->ate.Addr2[4], pAd->ate.Addr2[5]));
46650 +#endif // CONFIG_STA_SUPPORT //
46651 +
46652 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_SA_Proc Success\n"));
46653 +
46654 + return TRUE;
46655 +}
46656 +
46657 +/*
46658 + ==========================================================================
46659 + Description:
46660 + Set ATE ADDR2=BSSID for TxFrame(AP : To DS = 0 ; From DS = 1)
46661 + or
46662 + Set ATE ADDR1=BSSID for TxFrame(STA : To DS = 1 ; From DS = 0)
46663 +
46664 + Return:
46665 + TRUE if all parameters are OK, FALSE otherwise
46666 + ==========================================================================
46667 +*/
46668 +INT Set_ATE_BSSID_Proc(
46669 + IN PRTMP_ADAPTER pAd,
46670 + IN PUCHAR arg)
46671 +{
46672 + CHAR *value;
46673 + INT i;
46674 +
46675 + if(strlen(arg) != 17) //Mac address acceptable format 01:02:03:04:05:06 length 17
46676 + return FALSE;
46677 +
46678 + for (i=0, value = rstrtok(arg, ":"); value; value = rstrtok(NULL, ":"))
46679 + {
46680 + if((strlen(value) != 2) || (!isxdigit(*value)) || (!isxdigit(*(value+1))) )
46681 + return FALSE; //Invalid
46682 +
46683 +
46684 +#ifdef CONFIG_STA_SUPPORT
46685 + AtoH(value, &pAd->ate.Addr1[i++], 1);
46686 +#endif // CONFIG_STA_SUPPORT //
46687 + }
46688 +
46689 + if(i != 6)
46690 + return FALSE; //Invalid
46691 +
46692 +
46693 +#ifdef CONFIG_STA_SUPPORT
46694 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_BSSID_Proc (BSSID = %2X:%2X:%2X:%2X:%2X:%2X)\n", pAd->ate.Addr1[0],
46695 + pAd->ate.Addr1[1], pAd->ate.Addr1[2], pAd->ate.Addr1[3], pAd->ate.Addr1[4], pAd->ate.Addr1[5]));
46696 +#endif // CONFIG_STA_SUPPORT //
46697 +
46698 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_BSSID_Proc Success\n"));
46699 +
46700 + return TRUE;
46701 +}
46702 +
46703 +/*
46704 + ==========================================================================
46705 + Description:
46706 + Set ATE Tx Channel
46707 +
46708 + Return:
46709 + TRUE if all parameters are OK, FALSE otherwise
46710 + ==========================================================================
46711 +*/
46712 +INT Set_ATE_CHANNEL_Proc(
46713 + IN PRTMP_ADAPTER pAd,
46714 + IN PUCHAR arg)
46715 +{
46716 + UCHAR channel;
46717 +
46718 + channel = simple_strtol(arg, 0, 10);
46719 +
46720 + if ((channel < 1) || (channel > 216))// to allow A band channel : ((channel < 1) || (channel > 14))
46721 + {
46722 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_CHANNEL_Proc::Out of range, it should be in range of 1~14.\n"));
46723 + return FALSE;
46724 + }
46725 + pAd->ate.Channel = channel;
46726 +
46727 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_CHANNEL_Proc (ATE Channel = %d)\n", pAd->ate.Channel));
46728 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_CHANNEL_Proc Success\n"));
46729 +
46730 +
46731 + return TRUE;
46732 +}
46733 +
46734 +/*
46735 + ==========================================================================
46736 + Description:
46737 + Set ATE Tx Power0
46738 +
46739 + Return:
46740 + TRUE if all parameters are OK, FALSE otherwise
46741 + ==========================================================================
46742 +*/
46743 +INT Set_ATE_TX_POWER0_Proc(
46744 + IN PRTMP_ADAPTER pAd,
46745 + IN PUCHAR arg)
46746 +{
46747 + CHAR TxPower;
46748 +
46749 + TxPower = simple_strtol(arg, 0, 10);
46750 +
46751 + if (pAd->ate.Channel <= 14)
46752 + {
46753 + if ((TxPower > 31) || (TxPower < 0))
46754 + {
46755 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_POWER0_Proc::Out of range (Value=%d)\n", TxPower));
46756 + return FALSE;
46757 + }
46758 + }
46759 + else// 5.5GHz
46760 + {
46761 + if ((TxPower > 15) || (TxPower < -7))
46762 + {
46763 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_POWER0_Proc::Out of range (Value=%d)\n", TxPower));
46764 + return FALSE;
46765 + }
46766 + }
46767 +
46768 + pAd->ate.TxPower0 = TxPower;
46769 + ATETxPwrHandler(pAd, 0);
46770 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_POWER0_Proc Success\n"));
46771 +
46772 +
46773 + return TRUE;
46774 +}
46775 +
46776 +/*
46777 + ==========================================================================
46778 + Description:
46779 + Set ATE Tx Power1
46780 +
46781 + Return:
46782 + TRUE if all parameters are OK, FALSE otherwise
46783 + ==========================================================================
46784 +*/
46785 +INT Set_ATE_TX_POWER1_Proc(
46786 + IN PRTMP_ADAPTER pAd,
46787 + IN PUCHAR arg)
46788 +{
46789 + CHAR TxPower;
46790 +
46791 + TxPower = simple_strtol(arg, 0, 10);
46792 +
46793 + if (pAd->ate.Channel <= 14)
46794 + {
46795 + if ((TxPower > 31) || (TxPower < 0))
46796 + {
46797 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_POWER1_Proc::Out of range (Value=%d)\n", TxPower));
46798 + return FALSE;
46799 + }
46800 + }
46801 + else
46802 + {
46803 + if ((TxPower > 15) || (TxPower < -7))
46804 + {
46805 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_POWER1_Proc::Out of range (Value=%d)\n", TxPower));
46806 + return FALSE;
46807 + }
46808 + }
46809 +
46810 + pAd->ate.TxPower1 = TxPower;
46811 + ATETxPwrHandler(pAd, 1);
46812 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_POWER1_Proc Success\n"));
46813 +
46814 +
46815 + return TRUE;
46816 +}
46817 +
46818 +/*
46819 + ==========================================================================
46820 + Description:
46821 + Set ATE Tx Antenna
46822 +
46823 + Return:
46824 + TRUE if all parameters are OK, FALSE otherwise
46825 + ==========================================================================
46826 +*/
46827 +INT Set_ATE_TX_Antenna_Proc(
46828 + IN PRTMP_ADAPTER pAd,
46829 + IN PUCHAR arg)
46830 +{
46831 + CHAR value;
46832 +
46833 + value = simple_strtol(arg, 0, 10);
46834 +
46835 + if ((value > 2) || (value < 0))
46836 + {
46837 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_Antenna_Proc::Out of range (Value=%d)\n", value));
46838 + return FALSE;
46839 + }
46840 +
46841 + pAd->ate.TxAntennaSel = value;
46842 +
46843 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_Antenna_Proc (Antenna = %d)\n", pAd->ate.TxAntennaSel));
46844 + ATEDBGPRINT(RT_DEBUG_TRACE,("Ralink: Set_ATE_TX_Antenna_Proc Success\n"));
46845 +
46846 +
46847 + return TRUE;
46848 +}
46849 +
46850 +/*
46851 + ==========================================================================
46852 + Description:
46853 + Set ATE Rx Antenna
46854 +
46855 + Return:
46856 + TRUE if all parameters are OK, FALSE otherwise
46857 + ==========================================================================
46858 +*/
46859 +INT Set_ATE_RX_Antenna_Proc(
46860 + IN PRTMP_ADAPTER pAd,
46861 + IN PUCHAR arg)
46862 +{
46863 + CHAR value;
46864 +
46865 + value = simple_strtol(arg, 0, 10);
46866 +
46867 + if ((value > 3) || (value < 0))
46868 + {
46869 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_RX_Antenna_Proc::Out of range (Value=%d)\n", value));
46870 + return FALSE;
46871 + }
46872 +
46873 + pAd->ate.RxAntennaSel = value;
46874 +
46875 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_RX_Antenna_Proc (Antenna = %d)\n", pAd->ate.RxAntennaSel));
46876 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_RX_Antenna_Proc Success\n"));
46877 +
46878 +
46879 + return TRUE;
46880 +}
46881 +
46882 +/*
46883 + ==========================================================================
46884 + Description:
46885 + Set ATE RF frequence offset
46886 +
46887 + Return:
46888 + TRUE if all parameters are OK, FALSE otherwise
46889 + ==========================================================================
46890 +*/
46891 +INT Set_ATE_TX_FREQOFFSET_Proc(
46892 + IN PRTMP_ADAPTER pAd,
46893 + IN PUCHAR arg)
46894 +{
46895 + UCHAR RFFreqOffset;
46896 + ULONG R4;
46897 +
46898 + RFFreqOffset = simple_strtol(arg, 0, 10);
46899 +
46900 + if(RFFreqOffset >= 64)
46901 + {
46902 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_FREQOFFSET_Proc::Out of range, it should be in range of 0~63.\n"));
46903 + return FALSE;
46904 + }
46905 +
46906 + pAd->ate.RFFreqOffset = RFFreqOffset;
46907 + R4 = pAd->ate.RFFreqOffset << 15; // shift TX power control to correct RF register bit position
46908 + R4 |= (pAd->LatchRfRegs.R4 & ((~0x001f8000)));
46909 + pAd->LatchRfRegs.R4 = R4;
46910 +
46911 + RtmpRfIoWrite(pAd);
46912 +
46913 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_FREQOFFSET_Proc (RFFreqOffset = %d)\n", pAd->ate.RFFreqOffset));
46914 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_FREQOFFSET_Proc Success\n"));
46915 +
46916 +
46917 + return TRUE;
46918 +}
46919 +
46920 +/*
46921 + ==========================================================================
46922 + Description:
46923 + Set ATE RF BW
46924 +
46925 + Return:
46926 + TRUE if all parameters are OK, FALSE otherwise
46927 + ==========================================================================
46928 +*/
46929 +INT Set_ATE_TX_BW_Proc(
46930 + IN PRTMP_ADAPTER pAd,
46931 + IN PUCHAR arg)
46932 +{
46933 + int i;
46934 + UCHAR value = 0;
46935 + UCHAR BBPCurrentBW;
46936 +
46937 + BBPCurrentBW = simple_strtol(arg, 0, 10);
46938 +
46939 + if(BBPCurrentBW == 0)
46940 + pAd->ate.TxWI.BW = BW_20;
46941 + else
46942 + pAd->ate.TxWI.BW = BW_40;
46943 +
46944 + if(pAd->ate.TxWI.BW == BW_20)
46945 + {
46946 + if(pAd->ate.Channel <= 14)
46947 + {
46948 + for (i=0; i<5; i++)
46949 + {
46950 + if (pAd->Tx20MPwrCfgGBand[i] != 0xffffffff)
46951 + {
46952 + RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i*4, pAd->Tx20MPwrCfgGBand[i]);
46953 + RTMPusecDelay(5000);
46954 + }
46955 + }
46956 + }
46957 + else
46958 + {
46959 + for (i=0; i<5; i++)
46960 + {
46961 + if (pAd->Tx20MPwrCfgABand[i] != 0xffffffff)
46962 + {
46963 + RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i*4, pAd->Tx20MPwrCfgABand[i]);
46964 + RTMPusecDelay(5000);
46965 + }
46966 + }
46967 + }
46968 +
46969 + //Set BBP R4 bit[4:3]=0:0
46970 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &value);
46971 + value &= (~0x18);
46972 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, value);
46973 +
46974 + //Set BBP R66=0x3C
46975 + value = 0x3C;
46976 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, value);
46977 + //Set BBP R68=0x0B
46978 + //to improve Rx sensitivity.
46979 + value = 0x0B;
46980 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R68, value);
46981 + //Set BBP R69=0x16
46982 + value = 0x16;
46983 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, value);
46984 + //Set BBP R70=0x08
46985 + value = 0x08;
46986 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, value);
46987 + //Set BBP R73=0x11
46988 + value = 0x11;
46989 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, value);
46990 +
46991 + // If Channel=14, Bandwidth=20M and Mode=CCK, Set BBP R4 bit5=1
46992 + // (Japan filter coefficients)
46993 + // This segment of code will only works when ATETXMODE and ATECHANNEL
46994 + // were set to MODE_CCK and 14 respectively before ATETXBW is set to 0.
46995 + //=====================================================================
46996 + if (pAd->ate.Channel == 14)
46997 + {
46998 + int TxMode = pAd->ate.TxWI.PHYMODE;
46999 + if (TxMode == MODE_CCK)
47000 + {
47001 + // when Channel==14 && Mode==CCK && BandWidth==20M, BBP R4 bit5=1
47002 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &value);
47003 + value |= 0x20; //set bit5=1
47004 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, value);
47005 + }
47006 + }
47007 +
47008 + //=====================================================================
47009 + // If bandwidth != 40M, RF Reg4 bit 21 = 0.
47010 + pAd->LatchRfRegs.R4 &= ~0x00200000;
47011 + RtmpRfIoWrite(pAd);
47012 + }
47013 + else if(pAd->ate.TxWI.BW == BW_40)
47014 + {
47015 + if(pAd->ate.Channel <= 14)
47016 + {
47017 + for (i=0; i<5; i++)
47018 + {
47019 + if (pAd->Tx40MPwrCfgGBand[i] != 0xffffffff)
47020 + {
47021 + RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i*4, pAd->Tx40MPwrCfgGBand[i]);
47022 + RTMPusecDelay(5000);
47023 + }
47024 + }
47025 + }
47026 + else
47027 + {
47028 + for (i=0; i<5; i++)
47029 + {
47030 + if (pAd->Tx40MPwrCfgABand[i] != 0xffffffff)
47031 + {
47032 + RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i*4, pAd->Tx40MPwrCfgABand[i]);
47033 + RTMPusecDelay(5000);
47034 + }
47035 + }
47036 +#ifdef DOT11_N_SUPPORT
47037 + if ((pAd->ate.TxWI.PHYMODE >= MODE_HTMIX) && (pAd->ate.TxWI.MCS == 7))
47038 + {
47039 + value = 0x28;
47040 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R67, value);
47041 + }
47042 +#endif // DOT11_N_SUPPORT //
47043 + }
47044 +
47045 + //Set BBP R4 bit[4:3]=1:0
47046 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &value);
47047 + value &= (~0x18);
47048 + value |= 0x10;
47049 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, value);
47050 +
47051 + //Set BBP R66=0x3C
47052 + value = 0x3C;
47053 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, value);
47054 + //Set BBP R68=0x0C
47055 + //to improve Rx sensitivity.
47056 + value = 0x0C;
47057 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R68, value);
47058 + //Set BBP R69=0x1A
47059 + value = 0x1A;
47060 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, value);
47061 + //Set BBP R70=0x0A
47062 + value = 0x0A;
47063 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, value);
47064 + //Set BBP R73=0x16
47065 + value = 0x16;
47066 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, value);
47067 +
47068 + // If bandwidth = 40M, set RF Reg4 bit 21 = 1.
47069 + pAd->LatchRfRegs.R4 |= 0x00200000;
47070 + RtmpRfIoWrite(pAd);
47071 + }
47072 +
47073 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_BW_Proc (BBPCurrentBW = %d)\n", pAd->ate.TxWI.BW));
47074 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_BW_Proc Success\n"));
47075 +
47076 +
47077 + return TRUE;
47078 +}
47079 +
47080 +/*
47081 + ==========================================================================
47082 + Description:
47083 + Set ATE Tx frame length
47084 +
47085 + Return:
47086 + TRUE if all parameters are OK, FALSE otherwise
47087 + ==========================================================================
47088 +*/
47089 +INT Set_ATE_TX_LENGTH_Proc(
47090 + IN PRTMP_ADAPTER pAd,
47091 + IN PUCHAR arg)
47092 +{
47093 + pAd->ate.TxLength = simple_strtol(arg, 0, 10);
47094 +
47095 + if((pAd->ate.TxLength < 24) || (pAd->ate.TxLength > (MAX_FRAME_SIZE - 34/* == 2312 */)))
47096 + {
47097 + pAd->ate.TxLength = (MAX_FRAME_SIZE - 34/* == 2312 */);
47098 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_LENGTH_Proc::Out of range, it should be in range of 24~%d.\n", (MAX_FRAME_SIZE - 34/* == 2312 */)));
47099 + return FALSE;
47100 + }
47101 +
47102 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_LENGTH_Proc (TxLength = %d)\n", pAd->ate.TxLength));
47103 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_LENGTH_Proc Success\n"));
47104 +
47105 +
47106 + return TRUE;
47107 +}
47108 +
47109 +/*
47110 + ==========================================================================
47111 + Description:
47112 + Set ATE Tx frame count
47113 +
47114 + Return:
47115 + TRUE if all parameters are OK, FALSE otherwise
47116 + ==========================================================================
47117 +*/
47118 +INT Set_ATE_TX_COUNT_Proc(
47119 + IN PRTMP_ADAPTER pAd,
47120 + IN PUCHAR arg)
47121 +{
47122 + pAd->ate.TxCount = simple_strtol(arg, 0, 10);
47123 +
47124 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_COUNT_Proc (TxCount = %d)\n", pAd->ate.TxCount));
47125 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_COUNT_Proc Success\n"));
47126 +
47127 +
47128 + return TRUE;
47129 +}
47130 +
47131 +/*
47132 + ==========================================================================
47133 + Description:
47134 + Set ATE Tx frame MCS
47135 +
47136 + Return:
47137 + TRUE if all parameters are OK, FALSE otherwise
47138 + ==========================================================================
47139 +*/
47140 +INT Set_ATE_TX_MCS_Proc(
47141 + IN PRTMP_ADAPTER pAd,
47142 + IN PUCHAR arg)
47143 +{
47144 + UCHAR MCS;
47145 + int result;
47146 +
47147 + MCS = simple_strtol(arg, 0, 10);
47148 + result = CheckMCSValid(pAd->ate.TxWI.PHYMODE, MCS);
47149 +
47150 + if (result != -1)
47151 + {
47152 + pAd->ate.TxWI.MCS = (UCHAR)MCS;
47153 + }
47154 + else
47155 + {
47156 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_MCS_Proc::Out of range, refer to rate table.\n"));
47157 + return FALSE;
47158 + }
47159 +
47160 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_MCS_Proc (MCS = %d)\n", pAd->ate.TxWI.MCS));
47161 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_MCS_Proc Success\n"));
47162 +
47163 +
47164 + return TRUE;
47165 +}
47166 +
47167 +/*
47168 + ==========================================================================
47169 + Description:
47170 + Set ATE Tx frame Mode
47171 + 0: MODE_CCK
47172 + 1: MODE_OFDM
47173 + 2: MODE_HTMIX
47174 + 3: MODE_HTGREENFIELD
47175 +
47176 + Return:
47177 + TRUE if all parameters are OK, FALSE otherwise
47178 + ==========================================================================
47179 +*/
47180 +INT Set_ATE_TX_MODE_Proc(
47181 + IN PRTMP_ADAPTER pAd,
47182 + IN PUCHAR arg)
47183 +{
47184 + pAd->ate.TxWI.PHYMODE = simple_strtol(arg, 0, 10);
47185 +
47186 + if(pAd->ate.TxWI.PHYMODE > 3)
47187 + {
47188 + pAd->ate.TxWI.PHYMODE = 0;
47189 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_MODE_Proc::Out of range. it should be in range of 0~3\n"));
47190 + ATEDBGPRINT(RT_DEBUG_ERROR, ("0: CCK, 1: OFDM, 2: HT_MIX, 3: HT_GREEN_FIELD.\n"));
47191 + return FALSE;
47192 + }
47193 +
47194 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_MODE_Proc (TxMode = %d)\n", pAd->ate.TxWI.PHYMODE));
47195 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_MODE_Proc Success\n"));
47196 +
47197 +
47198 + return TRUE;
47199 +}
47200 +
47201 +/*
47202 + ==========================================================================
47203 + Description:
47204 + Set ATE Tx frame GI
47205 +
47206 + Return:
47207 + TRUE if all parameters are OK, FALSE otherwise
47208 + ==========================================================================
47209 +*/
47210 +INT Set_ATE_TX_GI_Proc(
47211 + IN PRTMP_ADAPTER pAd,
47212 + IN PUCHAR arg)
47213 +{
47214 + pAd->ate.TxWI.ShortGI = simple_strtol(arg, 0, 10);
47215 +
47216 + if(pAd->ate.TxWI.ShortGI > 1)
47217 + {
47218 + pAd->ate.TxWI.ShortGI = 0;
47219 + ATEDBGPRINT(RT_DEBUG_ERROR, ("Set_ATE_TX_GI_Proc::Out of range\n"));
47220 + return FALSE;
47221 + }
47222 +
47223 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_GI_Proc (GI = %d)\n", pAd->ate.TxWI.ShortGI));
47224 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_GI_Proc Success\n"));
47225 +
47226 +
47227 + return TRUE;
47228 +}
47229 +
47230 +/*
47231 + ==========================================================================
47232 + Description:
47233 + ==========================================================================
47234 + */
47235 +INT Set_ATE_RX_FER_Proc(
47236 + IN PRTMP_ADAPTER pAd,
47237 + IN PUCHAR arg)
47238 +{
47239 + pAd->ate.bRxFer = simple_strtol(arg, 0, 10);
47240 +
47241 + if (pAd->ate.bRxFer == 1)
47242 + {
47243 + pAd->ate.RxCntPerSec = 0;
47244 + pAd->ate.RxTotalCnt = 0;
47245 + }
47246 +
47247 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_RX_FER_Proc (bRxFer = %d)\n", pAd->ate.bRxFer));
47248 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_RX_FER_Proc Success\n"));
47249 +
47250 +
47251 + return TRUE;
47252 +}
47253 +
47254 +INT Set_ATE_Read_RF_Proc(
47255 + IN PRTMP_ADAPTER pAd,
47256 + IN PUCHAR arg)
47257 +{
47258 + ate_print(KERN_EMERG "R1 = %lx\n", pAd->LatchRfRegs.R1);
47259 + ate_print(KERN_EMERG "R2 = %lx\n", pAd->LatchRfRegs.R2);
47260 + ate_print(KERN_EMERG "R3 = %lx\n", pAd->LatchRfRegs.R3);
47261 + ate_print(KERN_EMERG "R4 = %lx\n", pAd->LatchRfRegs.R4);
47262 +
47263 + return TRUE;
47264 +}
47265 +
47266 +INT Set_ATE_Write_RF1_Proc(
47267 + IN PRTMP_ADAPTER pAd,
47268 + IN PUCHAR arg)
47269 +{
47270 + UINT32 value = simple_strtol(arg, 0, 16);
47271 +
47272 + pAd->LatchRfRegs.R1 = value;
47273 + RtmpRfIoWrite(pAd);
47274 +
47275 + return TRUE;
47276 +}
47277 +
47278 +INT Set_ATE_Write_RF2_Proc(
47279 + IN PRTMP_ADAPTER pAd,
47280 + IN PUCHAR arg)
47281 +{
47282 + UINT32 value = simple_strtol(arg, 0, 16);
47283 +
47284 + pAd->LatchRfRegs.R2 = value;
47285 + RtmpRfIoWrite(pAd);
47286 +
47287 + return TRUE;
47288 +}
47289 +
47290 +INT Set_ATE_Write_RF3_Proc(
47291 + IN PRTMP_ADAPTER pAd,
47292 + IN PUCHAR arg)
47293 +{
47294 + UINT32 value = simple_strtol(arg, 0, 16);
47295 +
47296 + pAd->LatchRfRegs.R3 = value;
47297 + RtmpRfIoWrite(pAd);
47298 +
47299 + return TRUE;
47300 +}
47301 +
47302 +INT Set_ATE_Write_RF4_Proc(
47303 + IN PRTMP_ADAPTER pAd,
47304 + IN PUCHAR arg)
47305 +{
47306 + UINT32 value = simple_strtol(arg, 0, 16);
47307 +
47308 + pAd->LatchRfRegs.R4 = value;
47309 + RtmpRfIoWrite(pAd);
47310 +
47311 + return TRUE;
47312 +}
47313 +
47314 +/*
47315 + ==========================================================================
47316 + Description:
47317 + Load and Write EEPROM from a binary file prepared in advance.
47318 +
47319 + Return:
47320 + TRUE if all parameters are OK, FALSE otherwise
47321 + ==========================================================================
47322 +*/
47323 +#ifndef UCOS
47324 +INT Set_ATE_Load_E2P_Proc(
47325 + IN PRTMP_ADAPTER pAd,
47326 + IN PUCHAR arg)
47327 +{
47328 + BOOLEAN ret = FALSE;
47329 + PUCHAR src = EEPROM_BIN_FILE_NAME;
47330 + struct file *srcf;
47331 + INT32 retval, orgfsuid, orgfsgid;
47332 + mm_segment_t orgfs;
47333 + USHORT WriteEEPROM[(EEPROM_SIZE/2)];
47334 + UINT32 FileLength = 0;
47335 + UINT32 value = simple_strtol(arg, 0, 10);
47336 +
47337 + ATEDBGPRINT(RT_DEBUG_ERROR, ("===> %s (value=%d)\n\n", __FUNCTION__, value));
47338 +
47339 + if (value > 0)
47340 + {
47341 + /* zero the e2p buffer */
47342 + NdisZeroMemory((PUCHAR)WriteEEPROM, EEPROM_SIZE);
47343 +
47344 + /* save uid and gid used for filesystem access.
47345 + ** set user and group to 0 (root)
47346 + */
47347 + orgfsuid = current->fsuid;
47348 + orgfsgid = current->fsgid;
47349 + /* as root */
47350 + current->fsuid = current->fsgid = 0;
47351 + orgfs = get_fs();
47352 + set_fs(KERNEL_DS);
47353 +
47354 + do
47355 + {
47356 + /* open the bin file */
47357 + srcf = filp_open(src, O_RDONLY, 0);
47358 +
47359 + if (IS_ERR(srcf))
47360 + {
47361 + ate_print("%s - Error %ld opening %s\n", __FUNCTION__, -PTR_ERR(srcf), src);
47362 + break;
47363 + }
47364 +
47365 + /* the object must have a read method */
47366 + if ((srcf->f_op == NULL) || (srcf->f_op->read == NULL))
47367 + {
47368 + ate_print("%s - %s does not have a read method\n", __FUNCTION__, src);
47369 + break;
47370 + }
47371 +
47372 + /* read the firmware from the file *.bin */
47373 + FileLength = srcf->f_op->read(srcf,
47374 + (PUCHAR)WriteEEPROM,
47375 + EEPROM_SIZE,
47376 + &srcf->f_pos);
47377 +
47378 + if (FileLength != EEPROM_SIZE)
47379 + {
47380 + ate_print("%s: error file length (=%d) in e2p.bin\n",
47381 + __FUNCTION__, FileLength);
47382 + break;
47383 + }
47384 + else
47385 + {
47386 + /* write the content of .bin file to EEPROM */
47387 + rt_ee_write_all(pAd, WriteEEPROM);
47388 + ret = TRUE;
47389 + }
47390 + break;
47391 + } while(TRUE);
47392 +
47393 + /* close firmware file */
47394 + if (IS_ERR(srcf))
47395 + {
47396 + ;
47397 + }
47398 + else
47399 + {
47400 + retval = filp_close(srcf, NULL);
47401 + if (retval)
47402 + {
47403 + ATEDBGPRINT(RT_DEBUG_ERROR, ("--> Error %d closing %s\n", -retval, src));
47404 +
47405 + }
47406 + }
47407 +
47408 + /* restore */
47409 + set_fs(orgfs);
47410 + current->fsuid = orgfsuid;
47411 + current->fsgid = orgfsgid;
47412 + }
47413 + ATEDBGPRINT(RT_DEBUG_ERROR, ("<=== %s (ret=%d)\n", __FUNCTION__, ret));
47414 +
47415 + return ret;
47416 +
47417 +}
47418 +#else
47419 +INT Set_ATE_Load_E2P_Proc(
47420 + IN PRTMP_ADAPTER pAd,
47421 + IN PUCHAR arg)
47422 +{
47423 + USHORT WriteEEPROM[(EEPROM_SIZE/2)];
47424 + struct iwreq *wrq = (struct iwreq *)arg;
47425 +
47426 + ATEDBGPRINT(RT_DEBUG_TRACE, ("===> %s (wrq->u.data.length = %d)\n\n", __FUNCTION__, wrq->u.data.length));
47427 +
47428 + if (wrq->u.data.length != EEPROM_SIZE)
47429 + {
47430 + ate_print("%s: error length (=%d) from host\n",
47431 + __FUNCTION__, wrq->u.data.length);
47432 + return FALSE;
47433 + }
47434 + else/* (wrq->u.data.length == EEPROM_SIZE) */
47435 + {
47436 + /* zero the e2p buffer */
47437 + NdisZeroMemory((PUCHAR)WriteEEPROM, EEPROM_SIZE);
47438 +
47439 + /* fill the local buffer */
47440 + NdisMoveMemory((PUCHAR)WriteEEPROM, wrq->u.data.pointer, wrq->u.data.length);
47441 +
47442 + do
47443 + {
47444 + /* write the content of .bin file to EEPROM */
47445 + rt_ee_write_all(pAd, WriteEEPROM);
47446 +
47447 + } while(FALSE);
47448 + }
47449 +
47450 + ATEDBGPRINT(RT_DEBUG_TRACE, ("<=== %s\n", __FUNCTION__));
47451 +
47452 + return TRUE;
47453 +
47454 +}
47455 +#endif // !UCOS //
47456 +
47457 +INT Set_ATE_Read_E2P_Proc(
47458 + IN PRTMP_ADAPTER pAd,
47459 + IN PUCHAR arg)
47460 +{
47461 + USHORT buffer[EEPROM_SIZE/2];
47462 + USHORT *p;
47463 + int i;
47464 +
47465 + rt_ee_read_all(pAd, (USHORT *)buffer);
47466 + p = buffer;
47467 + for (i = 0; i < (EEPROM_SIZE/2); i++)
47468 + {
47469 + ate_print("%4.4x ", *p);
47470 + if (((i+1) % 16) == 0)
47471 + ate_print("\n");
47472 + p++;
47473 + }
47474 + return TRUE;
47475 +}
47476 +
47477 +INT Set_ATE_Show_Proc(
47478 + IN PRTMP_ADAPTER pAd,
47479 + IN PUCHAR arg)
47480 +{
47481 + ate_print("Mode=%d\n", pAd->ate.Mode);
47482 + ate_print("TxPower0=%d\n", pAd->ate.TxPower0);
47483 + ate_print("TxPower1=%d\n", pAd->ate.TxPower1);
47484 + ate_print("TxAntennaSel=%d\n", pAd->ate.TxAntennaSel);
47485 + ate_print("RxAntennaSel=%d\n", pAd->ate.RxAntennaSel);
47486 + ate_print("BBPCurrentBW=%d\n", pAd->ate.TxWI.BW);
47487 + ate_print("GI=%d\n", pAd->ate.TxWI.ShortGI);
47488 + ate_print("MCS=%d\n", pAd->ate.TxWI.MCS);
47489 + ate_print("TxMode=%d\n", pAd->ate.TxWI.PHYMODE);
47490 + ate_print("Addr1=%02x:%02x:%02x:%02x:%02x:%02x\n",
47491 + pAd->ate.Addr1[0], pAd->ate.Addr1[1], pAd->ate.Addr1[2], pAd->ate.Addr1[3], pAd->ate.Addr1[4], pAd->ate.Addr1[5]);
47492 + ate_print("Addr2=%02x:%02x:%02x:%02x:%02x:%02x\n",
47493 + pAd->ate.Addr2[0], pAd->ate.Addr2[1], pAd->ate.Addr2[2], pAd->ate.Addr2[3], pAd->ate.Addr2[4], pAd->ate.Addr2[5]);
47494 + ate_print("Addr3=%02x:%02x:%02x:%02x:%02x:%02x\n",
47495 + pAd->ate.Addr3[0], pAd->ate.Addr3[1], pAd->ate.Addr3[2], pAd->ate.Addr3[3], pAd->ate.Addr3[4], pAd->ate.Addr3[5]);
47496 + ate_print("Channel=%d\n", pAd->ate.Channel);
47497 + ate_print("TxLength=%d\n", pAd->ate.TxLength);
47498 + ate_print("TxCount=%u\n", pAd->ate.TxCount);
47499 + ate_print("RFFreqOffset=%d\n", pAd->ate.RFFreqOffset);
47500 + ate_print(KERN_EMERG "Set_ATE_Show_Proc Success\n");
47501 + return TRUE;
47502 +}
47503 +
47504 +INT Set_ATE_Help_Proc(
47505 + IN PRTMP_ADAPTER pAd,
47506 + IN PUCHAR arg)
47507 +{
47508 + ate_print("ATE=ATESTART, ATESTOP, TXCONT, TXCARR, TXFRAME, RXFRAME\n");
47509 + ate_print("ATEDA\n");
47510 + ate_print("ATESA\n");
47511 + ate_print("ATEBSSID\n");
47512 + ate_print("ATECHANNEL, range:0~14(unless A band !)\n");
47513 + ate_print("ATETXPOW0, set power level of antenna 1.\n");
47514 + ate_print("ATETXPOW1, set power level of antenna 2.\n");
47515 + ate_print("ATETXANT, set TX antenna. 0:all, 1:antenna one, 2:antenna two.\n");
47516 + ate_print("ATERXANT, set RX antenna.0:all, 1:antenna one, 2:antenna two, 3:antenna three.\n");
47517 + ate_print("ATETXFREQOFFSET, set frequency offset, range 0~63\n");
47518 + ate_print("ATETXBW, set BandWidth, 0:20MHz, 1:40MHz.\n");
47519 + ate_print("ATETXLEN, set Frame length, range 24~%d\n", (MAX_FRAME_SIZE - 34/* == 2312 */));
47520 + ate_print("ATETXCNT, set how many frame going to transmit.\n");
47521 + ate_print("ATETXMCS, set MCS, reference to rate table.\n");
47522 + ate_print("ATETXMODE, set Mode 0:CCK, 1:OFDM, 2:HT-Mix, 3:GreenField, reference to rate table.\n");
47523 + ate_print("ATETXGI, set GI interval, 0:Long, 1:Short\n");
47524 + ate_print("ATERXFER, 0:disable Rx Frame error rate. 1:enable Rx Frame error rate.\n");
47525 + ate_print("ATERRF, show all RF registers.\n");
47526 + ate_print("ATEWRF1, set RF1 register.\n");
47527 + ate_print("ATEWRF2, set RF2 register.\n");
47528 + ate_print("ATEWRF3, set RF3 register.\n");
47529 + ate_print("ATEWRF4, set RF4 register.\n");
47530 + ate_print("ATELDE2P, load EEPROM from .bin file.\n");
47531 + ate_print("ATERE2P, display all EEPROM content.\n");
47532 + ate_print("ATESHOW, display all parameters of ATE.\n");
47533 + ate_print("ATEHELP, online help.\n");
47534 +
47535 + return TRUE;
47536 +}
47537 +
47538 +/*
47539 + ==========================================================================
47540 + Description:
47541 +
47542 + AsicSwitchChannel() dedicated for ATE.
47543 +
47544 + ==========================================================================
47545 +*/
47546 +VOID ATEAsicSwitchChannel(
47547 + IN PRTMP_ADAPTER pAd)
47548 +{
47549 + UINT32 R2 = 0, R3 = DEFAULT_RF_TX_POWER, R4 = 0, Value = 0;
47550 + CHAR TxPwer = 0, TxPwer2 = 0;
47551 + UCHAR index, BbpValue = 0, R66 = 0x30;
47552 + RTMP_RF_REGS *RFRegTable;
47553 + UCHAR Channel;
47554 +
47555 +#ifdef RALINK_28xx_QA
47556 + if ((pAd->ate.bQATxStart == TRUE) || (pAd->ate.bQARxStart == TRUE))
47557 + {
47558 + if (pAd->ate.Channel != pAd->LatchRfRegs.Channel)
47559 + {
47560 + pAd->ate.Channel = pAd->LatchRfRegs.Channel;
47561 + }
47562 + return;
47563 + }
47564 + else
47565 +#endif // RALINK_28xx_QA //
47566 + Channel = pAd->ate.Channel;
47567 +
47568 + // Select antenna
47569 + AsicAntennaSelect(pAd, Channel);
47570 +
47571 + // fill Tx power value
47572 + TxPwer = pAd->ate.TxPower0;
47573 + TxPwer2 = pAd->ate.TxPower1;
47574 +
47575 + RFRegTable = RF2850RegTable;
47576 +
47577 + switch (pAd->RfIcType)
47578 + {
47579 + /* But only 2850 and 2750 support 5.5GHz band... */
47580 + case RFIC_2820:
47581 + case RFIC_2850:
47582 + case RFIC_2720:
47583 + case RFIC_2750:
47584 +
47585 + for (index = 0; index < NUM_OF_2850_CHNL; index++)
47586 + {
47587 + if (Channel == RFRegTable[index].Channel)
47588 + {
47589 + R2 = RFRegTable[index].R2;
47590 + if (pAd->Antenna.field.TxPath == 1)
47591 + {
47592 + R2 |= 0x4000; // If TXpath is 1, bit 14 = 1;
47593 + }
47594 +
47595 + if (pAd->Antenna.field.RxPath == 2)
47596 + {
47597 + switch (pAd->ate.RxAntennaSel)
47598 + {
47599 + case 1:
47600 + R2 |= 0x20040;
47601 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BbpValue);
47602 + BbpValue &= 0xE4;
47603 + BbpValue |= 0x00;
47604 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BbpValue);
47605 + break;
47606 + case 2:
47607 + R2 |= 0x10040;
47608 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BbpValue);
47609 + BbpValue &= 0xE4;
47610 + BbpValue |= 0x01;
47611 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BbpValue);
47612 + break;
47613 + default:
47614 + R2 |= 0x40;
47615 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BbpValue);
47616 + BbpValue &= 0xE4;
47617 + /* Only enable two Antenna to receive. */
47618 + BbpValue |= 0x08;
47619 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BbpValue);
47620 + break;
47621 + }
47622 + }
47623 + else if (pAd->Antenna.field.RxPath == 1)
47624 + {
47625 + R2 |= 0x20040; // write 1 to off RxPath
47626 + }
47627 +
47628 + if (pAd->Antenna.field.TxPath == 2)
47629 + {
47630 + if (pAd->ate.TxAntennaSel == 1)
47631 + {
47632 + R2 |= 0x4000; // If TX Antenna select is 1 , bit 14 = 1; Disable Ant 2
47633 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &BbpValue);
47634 + BbpValue &= 0xE7; //11100111B
47635 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, BbpValue);
47636 + }
47637 + else if (pAd->ate.TxAntennaSel == 2)
47638 + {
47639 + R2 |= 0x8000; // If TX Antenna select is 2 , bit 15 = 1; Disable Ant 1
47640 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &BbpValue);
47641 + BbpValue &= 0xE7;
47642 + BbpValue |= 0x08;
47643 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, BbpValue);
47644 + }
47645 + else
47646 + {
47647 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &BbpValue);
47648 + BbpValue &= 0xE7;
47649 + BbpValue |= 0x10;
47650 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, BbpValue);
47651 + }
47652 + }
47653 + if (pAd->Antenna.field.RxPath == 3)
47654 + {
47655 + switch (pAd->ate.RxAntennaSel)
47656 + {
47657 + case 1:
47658 + R2 |= 0x20040;
47659 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BbpValue);
47660 + BbpValue &= 0xE4;
47661 + BbpValue |= 0x00;
47662 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BbpValue);
47663 + break;
47664 + case 2:
47665 + R2 |= 0x10040;
47666 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BbpValue);
47667 + BbpValue &= 0xE4;
47668 + BbpValue |= 0x01;
47669 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BbpValue);
47670 + break;
47671 + case 3:
47672 + R2 |= 0x30000;
47673 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BbpValue);
47674 + BbpValue &= 0xE4;
47675 + BbpValue |= 0x02;
47676 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BbpValue);
47677 + break;
47678 + default:
47679 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &BbpValue);
47680 + BbpValue &= 0xE4;
47681 + BbpValue |= 0x10;
47682 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, BbpValue);
47683 + break;
47684 + }
47685 + }
47686 +
47687 + if (Channel > 14)
47688 + {
47689 + // initialize R3, R4
47690 + R3 = (RFRegTable[index].R3 & 0xffffc1ff);
47691 + R4 = (RFRegTable[index].R4 & (~0x001f87c0)) | (pAd->ate.RFFreqOffset << 15);
47692 +
47693 + // According the Rory's suggestion to solve the middle range issue.
47694 + // 5.5G band power range: 0xF9~0X0F, TX0 Reg3 bit9/TX1 Reg4 bit6="0" means the TX power reduce 7dB
47695 + // R3
47696 + if ((TxPwer >= -7) && (TxPwer < 0))
47697 + {
47698 + TxPwer = (7+TxPwer);
47699 + TxPwer = (TxPwer > 0xF) ? (0xF) : (TxPwer);
47700 + R3 |= (TxPwer << 10);
47701 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATEAsicSwitchChannel: TxPwer=%d \n", TxPwer));
47702 + }
47703 + else
47704 + {
47705 + TxPwer = (TxPwer > 0xF) ? (0xF) : (TxPwer);
47706 + R3 |= (TxPwer << 10) | (1 << 9);
47707 + }
47708 +
47709 + // R4
47710 + if ((TxPwer2 >= -7) && (TxPwer2 < 0))
47711 + {
47712 + TxPwer2 = (7+TxPwer2);
47713 + TxPwer2 = (TxPwer2 > 0xF) ? (0xF) : (TxPwer2);
47714 + R4 |= (TxPwer2 << 7);
47715 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ATEAsicSwitchChannel: TxPwer2=%d \n", TxPwer2));
47716 + }
47717 + else
47718 + {
47719 + TxPwer2 = (TxPwer2 > 0xF) ? (0xF) : (TxPwer2);
47720 + R4 |= (TxPwer2 << 7) | (1 << 6);
47721 + }
47722 + }
47723 + else
47724 + {
47725 + R3 = (RFRegTable[index].R3 & 0xffffc1ff) | (TxPwer << 9); // set TX power0
47726 + R4 = (RFRegTable[index].R4 & (~0x001f87c0)) | (pAd->ate.RFFreqOffset << 15) | (TxPwer2 <<6);// Set freq offset & TxPwr1
47727 + }
47728 +
47729 + // Based on BBP current mode before changing RF channel.
47730 + if (pAd->ate.TxWI.BW == BW_40)
47731 + {
47732 + R4 |=0x200000;
47733 + }
47734 +
47735 + // Update variables
47736 + pAd->LatchRfRegs.Channel = Channel;
47737 + pAd->LatchRfRegs.R1 = RFRegTable[index].R1;
47738 + pAd->LatchRfRegs.R2 = R2;
47739 + pAd->LatchRfRegs.R3 = R3;
47740 + pAd->LatchRfRegs.R4 = R4;
47741 +
47742 + RtmpRfIoWrite(pAd);
47743 +
47744 + break;
47745 + }
47746 + }
47747 + break;
47748 +
47749 + default:
47750 + break;
47751 + }
47752 +
47753 + // Change BBP setting during switch from a->g, g->a
47754 + if (Channel <= 14)
47755 + {
47756 + ULONG TxPinCfg = 0x00050F0A;// 2007.10.09 by Brian : 0x0005050A ==> 0x00050F0A
47757 +
47758 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R62, (0x37 - GET_LNA_GAIN(pAd)));
47759 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R63, (0x37 - GET_LNA_GAIN(pAd)));
47760 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R64, (0x37 - GET_LNA_GAIN(pAd)));
47761 +
47762 + /* For 1T/2R chip only... */
47763 + if (pAd->NicConfig2.field.ExternalLNAForG)
47764 + {
47765 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R82, 0x62);
47766 + }
47767 + else
47768 + {
47769 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R82, 0x84);
47770 + }
47771 +
47772 + // According the Rory's suggestion to solve the middle range issue.
47773 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R86, &BbpValue);
47774 + ASSERT((BbpValue == 0x00));
47775 + if ((BbpValue != 0x00))
47776 + {
47777 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R86, 0x00);
47778 + }
47779 +
47780 + // 5.5GHz band selection PIN, bit1 and bit2 are complement
47781 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Value);
47782 + Value &= (~0x6);
47783 + Value |= (0x04);
47784 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Value);
47785 +
47786 + // Turn off unused PA or LNA when only 1T or 1R.
47787 + if (pAd->Antenna.field.TxPath == 1)
47788 + {
47789 + TxPinCfg &= 0xFFFFFFF3;
47790 + }
47791 + if (pAd->Antenna.field.RxPath == 1)
47792 + {
47793 + TxPinCfg &= 0xFFFFF3FF;
47794 + }
47795 +
47796 + RTMP_IO_WRITE32(pAd, TX_PIN_CFG, TxPinCfg);
47797 + }
47798 + else
47799 + {
47800 + ULONG TxPinCfg = 0x00050F05;//2007.10.09 by Brian : 0x00050505 ==> 0x00050F05
47801 +
47802 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R62, (0x37 - GET_LNA_GAIN(pAd)));
47803 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R63, (0x37 - GET_LNA_GAIN(pAd)));
47804 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R64, (0x37 - GET_LNA_GAIN(pAd)));
47805 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R82, 0xF2);
47806 +
47807 + // According the Rory's suggestion to solve the middle range issue.
47808 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R86, &BbpValue);
47809 + ASSERT((BbpValue == 0x00));
47810 + if ((BbpValue != 0x00))
47811 + {
47812 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R86, 0x00);
47813 + }
47814 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R91, &BbpValue);
47815 + ASSERT((BbpValue == 0x04));
47816 +
47817 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R92, &BbpValue);
47818 + ASSERT((BbpValue == 0x00));
47819 +
47820 + // 5.5GHz band selection PIN, bit1 and bit2 are complement
47821 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Value);
47822 + Value &= (~0x6);
47823 + Value |= (0x02);
47824 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Value);
47825 +
47826 + // Turn off unused PA or LNA when only 1T or 1R.
47827 + if (pAd->Antenna.field.TxPath == 1)
47828 + {
47829 + TxPinCfg &= 0xFFFFFFF3;
47830 + }
47831 + if (pAd->Antenna.field.RxPath == 1)
47832 + {
47833 + TxPinCfg &= 0xFFFFF3FF;
47834 + }
47835 +
47836 + RTMP_IO_WRITE32(pAd, TX_PIN_CFG, TxPinCfg);
47837 + }
47838 +
47839 + // R66 should be set according to Channel and use 20MHz when scanning
47840 + if (Channel <= 14)
47841 + {
47842 + // BG band
47843 + R66 = 0x2E + GET_LNA_GAIN(pAd);
47844 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
47845 + }
47846 + else
47847 + {
47848 + // 5.5 GHz band
47849 + if (pAd->ate.TxWI.BW == BW_20)
47850 + {
47851 + R66 = (UCHAR)(0x32 + (GET_LNA_GAIN(pAd)*5)/3);
47852 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
47853 + }
47854 + else
47855 + {
47856 + R66 = (UCHAR)(0x3A + (GET_LNA_GAIN(pAd)*5)/3);
47857 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, R66);
47858 + }
47859 + }
47860 +
47861 + //
47862 + // On 11A, We should delay and wait RF/BBP to be stable
47863 + // and the appropriate time should be 1000 micro seconds
47864 + // 2005/06/05 - On 11G, We also need this delay time. Otherwise it's difficult to pass the WHQL.
47865 + //
47866 + RTMPusecDelay(1000);
47867 +
47868 + if (Channel > 14)
47869 + {
47870 + // When 5.5GHz band the LSB of TxPwr will be used to reduced 7dB or not.
47871 + ATEDBGPRINT(RT_DEBUG_TRACE, ("SwitchChannel#%d(RF=%d, %dT) to , R1=0x%08lx, R2=0x%08lx, R3=0x%08lx, R4=0x%08lx\n",
47872 + Channel,
47873 + pAd->RfIcType,
47874 + pAd->Antenna.field.TxPath,
47875 + pAd->LatchRfRegs.R1,
47876 + pAd->LatchRfRegs.R2,
47877 + pAd->LatchRfRegs.R3,
47878 + pAd->LatchRfRegs.R4));
47879 + }
47880 + else
47881 + {
47882 + ATEDBGPRINT(RT_DEBUG_TRACE, ("SwitchChannel#%d(RF=%d, Pwr0=%u, Pwr1=%u, %dT) to , R1=0x%08lx, R2=0x%08lx, R3=0x%08lx, R4=0x%08lx\n",
47883 + Channel,
47884 + pAd->RfIcType,
47885 + (R3 & 0x00003e00) >> 9,
47886 + (R4 & 0x000007c0) >> 6,
47887 + pAd->Antenna.field.TxPath,
47888 + pAd->LatchRfRegs.R1,
47889 + pAd->LatchRfRegs.R2,
47890 + pAd->LatchRfRegs.R3,
47891 + pAd->LatchRfRegs.R4));
47892 + }
47893 +}
47894 +
47895 +//
47896 +// In fact, no one will call this routine so far !
47897 +//
47898 +/*
47899 + ==========================================================================
47900 + Description:
47901 + Gives CCK TX rate 2 more dB TX power.
47902 + This routine works only in ATE mode.
47903 +
47904 + calculate desired Tx power in RF R3.Tx0~5, should consider -
47905 + 0. if current radio is a noisy environment (pAd->DrsCounters.fNoisyEnvironment)
47906 + 1. TxPowerPercentage
47907 + 2. auto calibration based on TSSI feedback
47908 + 3. extra 2 db for CCK
47909 + 4. -10 db upon very-short distance (AvgRSSI >= -40db) to AP
47910 +
47911 + NOTE: Since this routine requires the value of (pAd->DrsCounters.fNoisyEnvironment),
47912 + it should be called AFTER MlmeDynamicTxRateSwitching()
47913 + ==========================================================================
47914 + */
47915 +VOID ATEAsicAdjustTxPower(
47916 + IN PRTMP_ADAPTER pAd)
47917 +{
47918 + INT i, j;
47919 + CHAR DeltaPwr = 0;
47920 + BOOLEAN bAutoTxAgc = FALSE;
47921 + UCHAR TssiRef, *pTssiMinusBoundary, *pTssiPlusBoundary, TxAgcStep;
47922 + UCHAR BbpR49 = 0, idx;
47923 + PCHAR pTxAgcCompensate;
47924 + ULONG TxPwr[5];
47925 + CHAR Value;
47926 +
47927 + /* no one calls this procedure so far */
47928 + if (pAd->ate.TxWI.BW == BW_40)
47929 + {
47930 + if (pAd->ate.Channel > 14)
47931 + {
47932 + TxPwr[0] = pAd->Tx40MPwrCfgABand[0];
47933 + TxPwr[1] = pAd->Tx40MPwrCfgABand[1];
47934 + TxPwr[2] = pAd->Tx40MPwrCfgABand[2];
47935 + TxPwr[3] = pAd->Tx40MPwrCfgABand[3];
47936 + TxPwr[4] = pAd->Tx40MPwrCfgABand[4];
47937 + }
47938 + else
47939 + {
47940 + TxPwr[0] = pAd->Tx40MPwrCfgGBand[0];
47941 + TxPwr[1] = pAd->Tx40MPwrCfgGBand[1];
47942 + TxPwr[2] = pAd->Tx40MPwrCfgGBand[2];
47943 + TxPwr[3] = pAd->Tx40MPwrCfgGBand[3];
47944 + TxPwr[4] = pAd->Tx40MPwrCfgGBand[4];
47945 + }
47946 + }
47947 + else
47948 + {
47949 + if (pAd->ate.Channel > 14)
47950 + {
47951 + TxPwr[0] = pAd->Tx20MPwrCfgABand[0];
47952 + TxPwr[1] = pAd->Tx20MPwrCfgABand[1];
47953 + TxPwr[2] = pAd->Tx20MPwrCfgABand[2];
47954 + TxPwr[3] = pAd->Tx20MPwrCfgABand[3];
47955 + TxPwr[4] = pAd->Tx20MPwrCfgABand[4];
47956 + }
47957 + else
47958 + {
47959 + TxPwr[0] = pAd->Tx20MPwrCfgGBand[0];
47960 + TxPwr[1] = pAd->Tx20MPwrCfgGBand[1];
47961 + TxPwr[2] = pAd->Tx20MPwrCfgGBand[2];
47962 + TxPwr[3] = pAd->Tx20MPwrCfgGBand[3];
47963 + TxPwr[4] = pAd->Tx20MPwrCfgGBand[4];
47964 + }
47965 + }
47966 +
47967 + // TX power compensation for temperature variation based on TSSI.
47968 + // Do it per 4 seconds.
47969 + if (pAd->Mlme.OneSecPeriodicRound % 4 == 0)
47970 + {
47971 + if (pAd->ate.Channel <= 14)
47972 + {
47973 + /* bg channel */
47974 + bAutoTxAgc = pAd->bAutoTxAgcG;
47975 + TssiRef = pAd->TssiRefG;
47976 + pTssiMinusBoundary = &pAd->TssiMinusBoundaryG[0];
47977 + pTssiPlusBoundary = &pAd->TssiPlusBoundaryG[0];
47978 + TxAgcStep = pAd->TxAgcStepG;
47979 + pTxAgcCompensate = &pAd->TxAgcCompensateG;
47980 + }
47981 + else
47982 + {
47983 + /* a channel */
47984 + bAutoTxAgc = pAd->bAutoTxAgcA;
47985 + TssiRef = pAd->TssiRefA;
47986 + pTssiMinusBoundary = &pAd->TssiMinusBoundaryA[0];
47987 + pTssiPlusBoundary = &pAd->TssiPlusBoundaryA[0];
47988 + TxAgcStep = pAd->TxAgcStepA;
47989 + pTxAgcCompensate = &pAd->TxAgcCompensateA;
47990 + }
47991 +
47992 + if (bAutoTxAgc)
47993 + {
47994 + /* BbpR49 is unsigned char */
47995 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R49, &BbpR49);
47996 +
47997 + /* (p) TssiPlusBoundaryG[0] = 0 = (m) TssiMinusBoundaryG[0] */
47998 + /* compensate: +4 +3 +2 +1 0 -1 -2 -3 -4 * steps */
47999 + /* step value is defined in pAd->TxAgcStepG for tx power value */
48000 +
48001 + /* [4]+1+[4] p4 p3 p2 p1 o1 m1 m2 m3 m4 */
48002 + /* ex: 0x00 0x15 0x25 0x45 0x88 0xA0 0xB5 0xD0 0xF0
48003 + above value are examined in mass factory production */
48004 + /* [4] [3] [2] [1] [0] [1] [2] [3] [4] */
48005 +
48006 + /* plus is 0x10 ~ 0x40, minus is 0x60 ~ 0x90 */
48007 + /* if value is between p1 ~ o1 or o1 ~ s1, no need to adjust tx power */
48008 + /* if value is 0x65, tx power will be -= TxAgcStep*(2-1) */
48009 +
48010 + if (BbpR49 > pTssiMinusBoundary[1])
48011 + {
48012 + // Reading is larger than the reference value.
48013 + // Check for how large we need to decrease the Tx power.
48014 + for (idx = 1; idx < 5; idx++)
48015 + {
48016 + if (BbpR49 <= pTssiMinusBoundary[idx]) // Found the range
48017 + break;
48018 + }
48019 + // The index is the step we should decrease, idx = 0 means there is nothing to compensate
48020 +// if (R3 > (ULONG) (TxAgcStep * (idx-1)))
48021 + *pTxAgcCompensate = -(TxAgcStep * (idx-1));
48022 +// else
48023 +// *pTxAgcCompensate = -((UCHAR)R3);
48024 +
48025 + DeltaPwr += (*pTxAgcCompensate);
48026 + ATEDBGPRINT(RT_DEBUG_TRACE, ("-- Tx Power, BBP R1=%x, TssiRef=%x, TxAgcStep=%x, step = -%d\n",
48027 + BbpR49, TssiRef, TxAgcStep, idx-1));
48028 + }
48029 + else if (BbpR49 < pTssiPlusBoundary[1])
48030 + {
48031 + // Reading is smaller than the reference value
48032 + // check for how large we need to increase the Tx power
48033 + for (idx = 1; idx < 5; idx++)
48034 + {
48035 + if (BbpR49 >= pTssiPlusBoundary[idx]) // Found the range
48036 + break;
48037 + }
48038 + // The index is the step we should increase, idx = 0 means there is nothing to compensate
48039 + *pTxAgcCompensate = TxAgcStep * (idx-1);
48040 + DeltaPwr += (*pTxAgcCompensate);
48041 + ATEDBGPRINT(RT_DEBUG_TRACE, ("++ Tx Power, BBP R1=%x, TssiRef=%x, TxAgcStep=%x, step = +%d\n",
48042 + BbpR49, TssiRef, TxAgcStep, idx-1));
48043 + }
48044 + else
48045 + {
48046 + *pTxAgcCompensate = 0;
48047 + ATEDBGPRINT(RT_DEBUG_TRACE, (" Tx Power, BBP R1=%x, TssiRef=%x, TxAgcStep=%x, step = +%d\n",
48048 + BbpR49, TssiRef, TxAgcStep, 0));
48049 + }
48050 + }
48051 + }
48052 + else
48053 + {
48054 + if (pAd->ate.Channel <= 14)
48055 + {
48056 + bAutoTxAgc = pAd->bAutoTxAgcG;
48057 + pTxAgcCompensate = &pAd->TxAgcCompensateG;
48058 + }
48059 + else
48060 + {
48061 + bAutoTxAgc = pAd->bAutoTxAgcA;
48062 + pTxAgcCompensate = &pAd->TxAgcCompensateA;
48063 + }
48064 +
48065 + if (bAutoTxAgc)
48066 + DeltaPwr += (*pTxAgcCompensate);
48067 + }
48068 +
48069 + /* calculate delta power based on the percentage specified from UI */
48070 + // E2PROM setting is calibrated for maximum TX power (i.e. 100%)
48071 + // We lower TX power here according to the percentage specified from UI
48072 + if (pAd->CommonCfg.TxPowerPercentage == 0xffffffff) // AUTO TX POWER control
48073 + ;
48074 + else if (pAd->CommonCfg.TxPowerPercentage > 90) // 91 ~ 100% & AUTO, treat as 100% in terms of mW
48075 + ;
48076 + else if (pAd->CommonCfg.TxPowerPercentage > 60) // 61 ~ 90%, treat as 75% in terms of mW
48077 + {
48078 + DeltaPwr -= 1;
48079 + }
48080 + else if (pAd->CommonCfg.TxPowerPercentage > 30) // 31 ~ 60%, treat as 50% in terms of mW
48081 + {
48082 + DeltaPwr -= 3;
48083 + }
48084 + else if (pAd->CommonCfg.TxPowerPercentage > 15) // 16 ~ 30%, treat as 25% in terms of mW
48085 + {
48086 + DeltaPwr -= 6;
48087 + }
48088 + else if (pAd->CommonCfg.TxPowerPercentage > 9) // 10 ~ 15%, treat as 12.5% in terms of mW
48089 + {
48090 + DeltaPwr -= 9;
48091 + }
48092 + else // 0 ~ 9 %, treat as MIN(~3%) in terms of mW
48093 + {
48094 + DeltaPwr -= 12;
48095 + }
48096 +
48097 + /* reset different new tx power for different TX rate */
48098 + for(i=0; i<5; i++)
48099 + {
48100 + if (TxPwr[i] != 0xffffffff)
48101 + {
48102 + for (j=0; j<8; j++)
48103 + {
48104 + Value = (CHAR)((TxPwr[i] >> j*4) & 0x0F); /* 0 ~ 15 */
48105 +
48106 + if ((Value + DeltaPwr) < 0)
48107 + {
48108 + Value = 0; /* min */
48109 + }
48110 + else if ((Value + DeltaPwr) > 0xF)
48111 + {
48112 + Value = 0xF; /* max */
48113 + }
48114 + else
48115 + {
48116 + Value += DeltaPwr; /* temperature compensation */
48117 + }
48118 +
48119 + /* fill new value to CSR offset */
48120 + TxPwr[i] = (TxPwr[i] & ~(0x0000000F << j*4)) | (Value << j*4);
48121 + }
48122 +
48123 + /* write tx power value to CSR */
48124 + /* TX_PWR_CFG_0 (8 tx rate) for TX power for OFDM 12M/18M
48125 + TX power for OFDM 6M/9M
48126 + TX power for CCK5.5M/11M
48127 + TX power for CCK1M/2M */
48128 + /* TX_PWR_CFG_1 ~ TX_PWR_CFG_4 */
48129 + RTMP_IO_WRITE32(pAd, TX_PWR_CFG_0 + i*4, TxPwr[i]);
48130 +
48131 +
48132 + }
48133 + }
48134 +
48135 +}
48136 +
48137 +/*
48138 + ========================================================================
48139 + Routine Description:
48140 + Write TxWI for ATE mode.
48141 +
48142 + Return Value:
48143 + None
48144 + ========================================================================
48145 +*/
48146 +#ifdef RT2860
48147 +static VOID ATEWriteTxWI(
48148 + IN PRTMP_ADAPTER pAd,
48149 + IN PTXWI_STRUC pOutTxWI,
48150 + IN BOOLEAN FRAG,
48151 + IN BOOLEAN CFACK,
48152 + IN BOOLEAN InsTimestamp,
48153 + IN BOOLEAN AMPDU,
48154 + IN BOOLEAN Ack,
48155 + IN BOOLEAN NSeq, // HW new a sequence.
48156 + IN UCHAR BASize,
48157 + IN UCHAR WCID,
48158 + IN ULONG Length,
48159 + IN UCHAR PID,
48160 + IN UCHAR TID,
48161 + IN UCHAR TxRate,
48162 + IN UCHAR Txopmode,
48163 + IN BOOLEAN CfAck,
48164 + IN HTTRANSMIT_SETTING *pTransmit)
48165 +{
48166 + TXWI_STRUC TxWI;
48167 + PTXWI_STRUC pTxWI;
48168 +
48169 + //
48170 + // Always use Long preamble before verifiation short preamble functionality works well.
48171 + // Todo: remove the following line if short preamble functionality works
48172 + //
48173 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED);
48174 + NdisZeroMemory(&TxWI, TXWI_SIZE);
48175 + pTxWI = &TxWI;
48176 +
48177 + pTxWI->FRAG= FRAG;
48178 +
48179 + pTxWI->CFACK = CFACK;
48180 + pTxWI->TS= InsTimestamp;
48181 + pTxWI->AMPDU = AMPDU;
48182 + pTxWI->ACK = Ack;
48183 + pTxWI->txop= Txopmode;
48184 +
48185 + pTxWI->NSEQ = NSeq;
48186 + // John tune the performace with Intel Client in 20 MHz performance
48187 + if( BASize >7 )
48188 + BASize =7;
48189 +
48190 + pTxWI->BAWinSize = BASize;
48191 + pTxWI->WirelessCliID = WCID;
48192 + pTxWI->MPDUtotalByteCount = Length;
48193 + pTxWI->PacketId = PID;
48194 +
48195 + // If CCK or OFDM, BW must be 20
48196 + pTxWI->BW = (pTransmit->field.MODE <= MODE_OFDM) ? (BW_20) : (pTransmit->field.BW);
48197 + pTxWI->ShortGI = pTransmit->field.ShortGI;
48198 + pTxWI->STBC = pTransmit->field.STBC;
48199 +
48200 + pTxWI->MCS = pTransmit->field.MCS;
48201 + pTxWI->PHYMODE = pTransmit->field.MODE;
48202 + pTxWI->CFACK = CfAck;
48203 + pTxWI->MIMOps = 0;
48204 + pTxWI->MpduDensity = 0;
48205 +
48206 + pTxWI->PacketId = pTxWI->MCS;
48207 + NdisMoveMemory(pOutTxWI, &TxWI, sizeof(TXWI_STRUC));
48208 +
48209 + return;
48210 +}
48211 +#endif // RT2860 //
48212 +
48213 +/*
48214 + ========================================================================
48215 +
48216 + Routine Description:
48217 + Disable protection for ATE.
48218 + ========================================================================
48219 +*/
48220 +VOID ATEDisableAsicProtect(
48221 + IN PRTMP_ADAPTER pAd)
48222 +{
48223 + PROT_CFG_STRUC ProtCfg, ProtCfg4;
48224 + UINT32 Protect[6];
48225 + USHORT offset;
48226 + UCHAR i;
48227 + UINT32 MacReg = 0;
48228 +
48229 + // Config ASIC RTS threshold register
48230 + RTMP_IO_READ32(pAd, TX_RTS_CFG, &MacReg);
48231 + MacReg &= 0xFF0000FF;
48232 + MacReg |= (pAd->CommonCfg.RtsThreshold << 8);
48233 + RTMP_IO_WRITE32(pAd, TX_RTS_CFG, MacReg);
48234 +
48235 + // Initial common protection settings
48236 + RTMPZeroMemory(Protect, sizeof(Protect));
48237 + ProtCfg4.word = 0;
48238 + ProtCfg.word = 0;
48239 + ProtCfg.field.TxopAllowGF40 = 1;
48240 + ProtCfg.field.TxopAllowGF20 = 1;
48241 + ProtCfg.field.TxopAllowMM40 = 1;
48242 + ProtCfg.field.TxopAllowMM20 = 1;
48243 + ProtCfg.field.TxopAllowOfdm = 1;
48244 + ProtCfg.field.TxopAllowCck = 1;
48245 + ProtCfg.field.RTSThEn = 1;
48246 + ProtCfg.field.ProtectNav = ASIC_SHORTNAV;
48247 +
48248 + // Handle legacy(B/G) protection
48249 + ProtCfg.field.ProtectRate = pAd->CommonCfg.RtsRate;
48250 + ProtCfg.field.ProtectCtrl = 0;
48251 + Protect[0] = ProtCfg.word;
48252 + Protect[1] = ProtCfg.word;
48253 +
48254 + // NO PROTECT
48255 + // 1.All STAs in the BSS are 20/40 MHz HT
48256 + // 2. in ai 20/40MHz BSS
48257 + // 3. all STAs are 20MHz in a 20MHz BSS
48258 + // Pure HT. no protection.
48259 +
48260 + // MM20_PROT_CFG
48261 + // Reserved (31:27)
48262 + // PROT_TXOP(25:20) -- 010111
48263 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
48264 + // PROT_CTRL(17:16) -- 00 (None)
48265 + // PROT_RATE(15:0) -- 0x4004 (OFDM 24M)
48266 + Protect[2] = 0x01744004;
48267 +
48268 + // MM40_PROT_CFG
48269 + // Reserved (31:27)
48270 + // PROT_TXOP(25:20) -- 111111
48271 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
48272 + // PROT_CTRL(17:16) -- 00 (None)
48273 + // PROT_RATE(15:0) -- 0x4084 (duplicate OFDM 24M)
48274 + Protect[3] = 0x03f44084;
48275 +
48276 + // CF20_PROT_CFG
48277 + // Reserved (31:27)
48278 + // PROT_TXOP(25:20) -- 010111
48279 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
48280 + // PROT_CTRL(17:16) -- 00 (None)
48281 + // PROT_RATE(15:0) -- 0x4004 (OFDM 24M)
48282 + Protect[4] = 0x01744004;
48283 +
48284 + // CF40_PROT_CFG
48285 + // Reserved (31:27)
48286 + // PROT_TXOP(25:20) -- 111111
48287 + // PROT_NAV(19:18) -- 01 (Short NAV protection)
48288 + // PROT_CTRL(17:16) -- 00 (None)
48289 + // PROT_RATE(15:0) -- 0x4084 (duplicate OFDM 24M)
48290 + Protect[5] = 0x03f44084;
48291 +
48292 + pAd->CommonCfg.IOTestParm.bRTSLongProtOn = FALSE;
48293 +
48294 + offset = CCK_PROT_CFG;
48295 + for (i = 0;i < 6;i++)
48296 + RTMP_IO_WRITE32(pAd, offset + i*4, Protect[i]);
48297 +
48298 +}
48299 +
48300 +
48301 +/* There are two ways to convert Rssi */
48302 +#if 1
48303 +//
48304 +// The way used with GET_LNA_GAIN().
48305 +//
48306 +CHAR ATEConvertToRssi(
48307 + IN PRTMP_ADAPTER pAd,
48308 + IN CHAR Rssi,
48309 + IN UCHAR RssiNumber)
48310 +{
48311 + UCHAR RssiOffset, LNAGain;
48312 +
48313 + // Rssi equals to zero should be an invalid value
48314 + if (Rssi == 0)
48315 + return -99;
48316 +
48317 + LNAGain = GET_LNA_GAIN(pAd);
48318 + if (pAd->LatchRfRegs.Channel > 14)
48319 + {
48320 + if (RssiNumber == 0)
48321 + RssiOffset = pAd->ARssiOffset0;
48322 + else if (RssiNumber == 1)
48323 + RssiOffset = pAd->ARssiOffset1;
48324 + else
48325 + RssiOffset = pAd->ARssiOffset2;
48326 + }
48327 + else
48328 + {
48329 + if (RssiNumber == 0)
48330 + RssiOffset = pAd->BGRssiOffset0;
48331 + else if (RssiNumber == 1)
48332 + RssiOffset = pAd->BGRssiOffset1;
48333 + else
48334 + RssiOffset = pAd->BGRssiOffset2;
48335 + }
48336 +
48337 + return (-12 - RssiOffset - LNAGain - Rssi);
48338 +}
48339 +#else
48340 +//
48341 +// The way originally used in ATE of rt2860ap.
48342 +//
48343 +CHAR ATEConvertToRssi(
48344 + IN PRTMP_ADAPTER pAd,
48345 + IN CHAR Rssi,
48346 + IN UCHAR RssiNumber)
48347 +{
48348 + UCHAR RssiOffset, LNAGain;
48349 +
48350 + // Rssi equals to zero should be an invalid value
48351 + if (Rssi == 0)
48352 + return -99;
48353 +
48354 + if (pAd->LatchRfRegs.Channel > 14)
48355 + {
48356 + LNAGain = pAd->ALNAGain;
48357 + if (RssiNumber == 0)
48358 + RssiOffset = pAd->ARssiOffset0;
48359 + else if (RssiNumber == 1)
48360 + RssiOffset = pAd->ARssiOffset1;
48361 + else
48362 + RssiOffset = pAd->ARssiOffset2;
48363 + }
48364 + else
48365 + {
48366 + LNAGain = pAd->BLNAGain;
48367 + if (RssiNumber == 0)
48368 + RssiOffset = pAd->BGRssiOffset0;
48369 + else if (RssiNumber == 1)
48370 + RssiOffset = pAd->BGRssiOffset1;
48371 + else
48372 + RssiOffset = pAd->BGRssiOffset2;
48373 + }
48374 +
48375 + return (-32 - RssiOffset + LNAGain - Rssi);
48376 +}
48377 +#endif /* end of #if 1 */
48378 +
48379 +/*
48380 + ========================================================================
48381 +
48382 + Routine Description:
48383 + Set Japan filter coefficients if needed.
48384 + Note:
48385 + This routine should only be called when
48386 + entering TXFRAME mode or TXCONT mode.
48387 +
48388 + ========================================================================
48389 +*/
48390 +static VOID SetJapanFilter(
48391 + IN PRTMP_ADAPTER pAd)
48392 +{
48393 + UCHAR BbpData = 0;
48394 +
48395 + //
48396 + // If Channel=14 and Bandwidth=20M and Mode=CCK, set BBP R4 bit5=1
48397 + // (Japan Tx filter coefficients)when (TXFRAME or TXCONT).
48398 + //
48399 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BbpData);
48400 +
48401 + if ((pAd->ate.TxWI.PHYMODE == MODE_CCK) && (pAd->ate.Channel == 14) && (pAd->ate.TxWI.BW == BW_20))
48402 + {
48403 + BbpData |= 0x20; // turn on
48404 + ATEDBGPRINT(RT_DEBUG_TRACE, ("SetJapanFilter!!!\n"));
48405 + }
48406 + else
48407 + {
48408 + BbpData &= 0xdf; // turn off
48409 + ATEDBGPRINT(RT_DEBUG_TRACE, ("ClearJapanFilter!!!\n"));
48410 + }
48411 +
48412 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BbpData);
48413 +}
48414 +
48415 +VOID ATESampleRssi(
48416 + IN PRTMP_ADAPTER pAd,
48417 + IN PRXWI_STRUC pRxWI)
48418 +{
48419 + /* There are two ways to collect RSSI. */
48420 +#if 1
48421 + //pAd->LastRxRate = (USHORT)((pRxWI->MCS) + (pRxWI->BW <<7) + (pRxWI->ShortGI <<8)+ (pRxWI->PHYMODE <<14)) ;
48422 + if (pRxWI->RSSI0 != 0)
48423 + {
48424 + pAd->ate.LastRssi0 = ATEConvertToRssi(pAd, (CHAR) pRxWI->RSSI0, RSSI_0);
48425 + pAd->ate.AvgRssi0X8 = (pAd->ate.AvgRssi0X8 - pAd->ate.AvgRssi0) + pAd->ate.LastRssi0;
48426 + pAd->ate.AvgRssi0 = pAd->ate.AvgRssi0X8 >> 3;
48427 + }
48428 + if (pRxWI->RSSI1 != 0)
48429 + {
48430 + pAd->ate.LastRssi1 = ATEConvertToRssi(pAd, (CHAR) pRxWI->RSSI1, RSSI_1);
48431 + pAd->ate.AvgRssi1X8 = (pAd->ate.AvgRssi1X8 - pAd->ate.AvgRssi1) + pAd->ate.LastRssi1;
48432 + pAd->ate.AvgRssi1 = pAd->ate.AvgRssi1X8 >> 3;
48433 + }
48434 + if (pRxWI->RSSI2 != 0)
48435 + {
48436 + pAd->ate.LastRssi2 = ATEConvertToRssi(pAd, (CHAR) pRxWI->RSSI2, RSSI_2);
48437 + pAd->ate.AvgRssi2X8 = (pAd->ate.AvgRssi2X8 - pAd->ate.AvgRssi2) + pAd->ate.LastRssi2;
48438 + pAd->ate.AvgRssi2 = pAd->ate.AvgRssi2X8 >> 3;
48439 + }
48440 +
48441 + pAd->ate.LastSNR0 = (CHAR)(pRxWI->SNR0);// CHAR ==> UCHAR ?
48442 + pAd->ate.LastSNR1 = (CHAR)(pRxWI->SNR1);// CHAR ==> UCHAR ?
48443 +
48444 + pAd->ate.NumOfAvgRssiSample ++;
48445 +#else
48446 + pAd->ate.LastSNR0 = (CHAR)(pRxWI->SNR0);
48447 + pAd->ate.LastSNR1 = (CHAR)(pRxWI->SNR1);
48448 + pAd->ate.RxCntPerSec++;
48449 + pAd->ate.LastRssi0 = ATEConvertToRssi(pAd, (CHAR) pRxWI->RSSI0, RSSI_0);
48450 + pAd->ate.LastRssi1 = ATEConvertToRssi(pAd, (CHAR) pRxWI->RSSI1, RSSI_1);
48451 + pAd->ate.LastRssi2 = ATEConvertToRssi(pAd, (CHAR) pRxWI->RSSI2, RSSI_2);
48452 + pAd->ate.AvgRssi0X8 = (pAd->ate.AvgRssi0X8 - pAd->ate.AvgRssi0) + pAd->ate.LastRssi0;
48453 + pAd->ate.AvgRssi0 = pAd->ate.AvgRssi0X8 >> 3;
48454 + pAd->ate.AvgRssi1X8 = (pAd->ate.AvgRssi1X8 - pAd->ate.AvgRssi1) + pAd->ate.LastRssi1;
48455 + pAd->ate.AvgRssi1 = pAd->ate.AvgRssi1X8 >> 3;
48456 + pAd->ate.AvgRssi2X8 = (pAd->ate.AvgRssi2X8 - pAd->ate.AvgRssi2) + pAd->ate.LastRssi2;
48457 + pAd->ate.AvgRssi2 = pAd->ate.AvgRssi2X8 >> 3;
48458 + pAd->ate.NumOfAvgRssiSample ++;
48459 +#endif
48460 +}
48461 +
48462 +#ifdef CONFIG_STA_SUPPORT
48463 +VOID RTMPStationStop(
48464 + IN PRTMP_ADAPTER pAd)
48465 +{
48466 +// BOOLEAN Cancelled;
48467 +
48468 + ATEDBGPRINT(RT_DEBUG_TRACE, ("==> RTMPStationStop\n"));
48469 +
48470 +#if 0
48471 + RTMPCancelTimer(&pAd->MlmeAux.AssocTimer, &Cancelled);
48472 + RTMPCancelTimer(&pAd->MlmeAux.ReassocTimer, &Cancelled);
48473 + RTMPCancelTimer(&pAd->MlmeAux.DisassocTimer, &Cancelled);
48474 + RTMPCancelTimer(&pAd->MlmeAux.AuthTimer, &Cancelled);
48475 + RTMPCancelTimer(&pAd->MlmeAux.BeaconTimer, &Cancelled);
48476 + RTMPCancelTimer(&pAd->MlmeAux.ScanTimer, &Cancelled);
48477 +#endif
48478 + // For rx statistics, we need to keep this timer running.
48479 +// RTMPCancelTimer(&pAd->Mlme.PeriodicTimer, &Cancelled);
48480 +
48481 + ATEDBGPRINT(RT_DEBUG_TRACE, ("<== RTMPStationStop\n"));
48482 +}
48483 +
48484 +VOID RTMPStationStart(
48485 + IN PRTMP_ADAPTER pAd)
48486 +{
48487 + ATEDBGPRINT(RT_DEBUG_TRACE, ("==> RTMPStationStart\n"));
48488 +#ifdef RT2860
48489 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
48490 + //
48491 + // We did not cancel this timer when entering ATE mode.
48492 + //
48493 +// RTMPSetTimer(&pAd->Mlme.PeriodicTimer, MLME_TASK_EXEC_INTV);
48494 +#endif // RT2860 //
48495 + ATEDBGPRINT(RT_DEBUG_TRACE, ("<== RTMPStationStart\n"));
48496 +}
48497 +#endif // CONFIG_STA_SUPPORT //
48498 +
48499 +/*
48500 + ==========================================================================
48501 + Description:
48502 + Setup Frame format.
48503 + NOTE:
48504 + This routine should only be used in ATE mode.
48505 + ==========================================================================
48506 + */
48507 +#ifdef RT2860
48508 +static INT ATESetUpFrame(
48509 + IN PRTMP_ADAPTER pAd,
48510 + IN UINT32 TxIdx)
48511 +{
48512 + UINT j;
48513 + PTXD_STRUC pTxD;
48514 +#ifdef RT_BIG_ENDIAN
48515 + PTXD_STRUC pDestTxD;
48516 + TXD_STRUC TxD;
48517 +#endif
48518 + PNDIS_PACKET pPacket;
48519 + PUCHAR pDest;
48520 + PVOID AllocVa;
48521 + NDIS_PHYSICAL_ADDRESS AllocPa;
48522 + HTTRANSMIT_SETTING TxHTPhyMode;
48523 +
48524 + PRTMP_TX_RING pTxRing = &pAd->TxRing[QID_AC_BE];
48525 + PTXWI_STRUC pTxWI = (PTXWI_STRUC) pTxRing->Cell[TxIdx].DmaBuf.AllocVa;
48526 + PUCHAR pDMAHeaderBufVA = (PUCHAR) pTxRing->Cell[TxIdx].DmaBuf.AllocVa;
48527 +
48528 +#ifdef RALINK_28xx_QA
48529 + PHEADER_802_11 pHeader80211;
48530 +#endif // RALINK_28xx_QA //
48531 +
48532 + if (pAd->ate.bQATxStart == TRUE)
48533 + {
48534 + // always use QID_AC_BE and FIFO_EDCA
48535 +
48536 + // fill TxWI
48537 + TxHTPhyMode.field.BW = pAd->ate.TxWI.BW;
48538 + TxHTPhyMode.field.ShortGI = pAd->ate.TxWI.ShortGI;
48539 + TxHTPhyMode.field.STBC = 0;
48540 + TxHTPhyMode.field.MCS = pAd->ate.TxWI.MCS;
48541 + TxHTPhyMode.field.MODE = pAd->ate.TxWI.PHYMODE;
48542 + ATEWriteTxWI(pAd, pTxWI, pAd->ate.TxWI.FRAG, pAd->ate.TxWI.CFACK, pAd->ate.TxWI.TS, pAd->ate.TxWI.AMPDU, pAd->ate.TxWI.ACK, pAd->ate.TxWI.NSEQ,
48543 + pAd->ate.TxWI.BAWinSize, 0, pAd->ate.TxWI.MPDUtotalByteCount, pAd->ate.TxWI.PacketId, 0, 0, pAd->ate.TxWI.txop/*IFS_HTTXOP*/, pAd->ate.TxWI.CFACK/*FALSE*/, &TxHTPhyMode);
48544 + }
48545 + else
48546 + {
48547 + TxHTPhyMode.field.BW = pAd->ate.TxWI.BW;
48548 + TxHTPhyMode.field.ShortGI = pAd->ate.TxWI.ShortGI;
48549 + TxHTPhyMode.field.STBC = 0;
48550 + TxHTPhyMode.field.MCS = pAd->ate.TxWI.MCS;
48551 + TxHTPhyMode.field.MODE = pAd->ate.TxWI.PHYMODE;
48552 + ATEWriteTxWI(pAd, pTxWI, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE,
48553 + 4, 0, pAd->ate.TxLength, 0, 0, 0, IFS_HTTXOP, FALSE, &TxHTPhyMode);
48554 + }
48555 +
48556 + // fill 802.11 header.
48557 +#ifdef RALINK_28xx_QA
48558 + if (pAd->ate.bQATxStart == TRUE)
48559 + {
48560 + NdisMoveMemory(pDMAHeaderBufVA+TXWI_SIZE, pAd->ate.Header, pAd->ate.HLen);
48561 + }
48562 + else
48563 +#endif // RALINK_28xx_QA //
48564 + {
48565 + NdisMoveMemory(pDMAHeaderBufVA+TXWI_SIZE, TemplateFrame, LENGTH_802_11);
48566 + NdisMoveMemory(pDMAHeaderBufVA+TXWI_SIZE+4, pAd->ate.Addr1, ETH_LENGTH_OF_ADDRESS);
48567 + NdisMoveMemory(pDMAHeaderBufVA+TXWI_SIZE+10, pAd->ate.Addr2, ETH_LENGTH_OF_ADDRESS);
48568 + NdisMoveMemory(pDMAHeaderBufVA+TXWI_SIZE+16, pAd->ate.Addr3, ETH_LENGTH_OF_ADDRESS);
48569 + }
48570 +
48571 +#ifdef RT_BIG_ENDIAN
48572 + RTMPFrameEndianChange(pAd, (((PUCHAR)pDMAHeaderBufVA)+TXWI_SIZE), DIR_READ, FALSE);
48573 +#endif // RT_BIG_ENDIAN //
48574 +
48575 + /* alloc buffer for payload */
48576 +#ifdef RALINK_28xx_QA
48577 + if (pAd->ate.bQATxStart == TRUE)
48578 + {
48579 + /* Why not use RTMP_AllocateTxPacketBuffer() instead of RTMP_AllocateRxPacketBuffer()? */
48580 + pPacket = RTMP_AllocateRxPacketBuffer(pAd, pAd->ate.DLen + 0x100, FALSE, &AllocVa, &AllocPa);
48581 + }
48582 + else
48583 +#endif // RALINK_28xx_QA //
48584 + {
48585 + /* Why not use RTMP_AllocateTxPacketBuffer() instead of RTMP_AllocateRxPacketBuffer()? */
48586 + pPacket = RTMP_AllocateRxPacketBuffer(pAd, pAd->ate.TxLength, FALSE, &AllocVa, &AllocPa);
48587 + }
48588 +
48589 + if (pPacket == NULL)
48590 + {
48591 + pAd->ate.TxCount = 0;
48592 + ATEDBGPRINT(RT_DEBUG_TRACE, ("%s fail to alloc packet space.\n", __FUNCTION__));
48593 + return -1;
48594 + }
48595 + pTxRing->Cell[TxIdx].pNextNdisPacket = pPacket;
48596 +
48597 + pDest = (PUCHAR) AllocVa;
48598 +
48599 +#ifdef RALINK_28xx_QA
48600 + if (pAd->ate.bQATxStart == TRUE)
48601 + {
48602 + RTPKT_TO_OSPKT(pPacket)->len = pAd->ate.DLen;
48603 + }
48604 + else
48605 +#endif // RALINK_28xx_QA //
48606 + {
48607 + RTPKT_TO_OSPKT(pPacket)->len = pAd->ate.TxLength - LENGTH_802_11;
48608 + }
48609 +
48610 + // Prepare frame payload
48611 +#ifdef RALINK_28xx_QA
48612 + if (pAd->ate.bQATxStart == TRUE)
48613 + {
48614 + // copy pattern
48615 + if ((pAd->ate.PLen != 0))
48616 + {
48617 + int j;
48618 +
48619 + for (j = 0; j < pAd->ate.DLen; j+=pAd->ate.PLen)
48620 + {
48621 + memcpy(RTPKT_TO_OSPKT(pPacket)->data + j, pAd->ate.Pattern, pAd->ate.PLen);
48622 + }
48623 + }
48624 + }
48625 + else
48626 +#endif // RALINK_28xx_QA //
48627 + {
48628 + for(j = 0; j < RTPKT_TO_OSPKT(pPacket)->len; j++)
48629 + pDest[j] = 0xA5;
48630 + }
48631 +
48632 + //
48633 + // build Tx Descriptor
48634 + //
48635 +#ifndef RT_BIG_ENDIAN
48636 + pTxD = (PTXD_STRUC) pTxRing->Cell[TxIdx].AllocVa;
48637 +#else
48638 + pDestTxD = (PTXD_STRUC)pTxRing->Cell[TxIdx].AllocVa;
48639 + TxD = *pDestTxD;
48640 + pTxD = &TxD;
48641 +#endif // !RT_BIG_ENDIAN //
48642 +
48643 +#ifdef RALINK_28xx_QA
48644 + if (pAd->ate.bQATxStart == TRUE)
48645 + {
48646 + // prepare TxD
48647 + NdisZeroMemory(pTxD, TXD_SIZE);
48648 + RTMPWriteTxDescriptor(pAd, pTxD, FALSE, FIFO_EDCA);
48649 + // build TX DESC
48650 + pTxD->SDPtr0 = RTMP_GetPhysicalAddressLow(pTxRing->Cell[TxIdx].DmaBuf.AllocPa);
48651 + pTxD->SDLen0 = TXWI_SIZE + pAd->ate.HLen;
48652 + pTxD->LastSec0 = 0;
48653 + pTxD->SDPtr1 = AllocPa;
48654 + pTxD->SDLen1 = RTPKT_TO_OSPKT(pPacket)->len;
48655 + pTxD->LastSec1 = 1;
48656 +
48657 + pDest = (PUCHAR)pTxWI;
48658 + pDest += TXWI_SIZE;
48659 + pHeader80211 = (PHEADER_802_11)pDest;
48660 +
48661 + // modify sequence number....
48662 + if (pAd->ate.TxDoneCount == 0)
48663 + {
48664 + pAd->ate.seq = pHeader80211->Sequence;
48665 + }
48666 + else
48667 + pHeader80211->Sequence = ++pAd->ate.seq;
48668 + }
48669 + else
48670 +#endif // RALINK_28xx_QA //
48671 + {
48672 + NdisZeroMemory(pTxD, TXD_SIZE);
48673 + RTMPWriteTxDescriptor(pAd, pTxD, FALSE, FIFO_EDCA);
48674 + // build TX DESC
48675 + pTxD->SDPtr0 = RTMP_GetPhysicalAddressLow (pTxRing->Cell[TxIdx].DmaBuf.AllocPa);
48676 + pTxD->SDLen0 = TXWI_SIZE + LENGTH_802_11;
48677 + pTxD->LastSec0 = 0;
48678 + pTxD->SDPtr1 = AllocPa;
48679 + pTxD->SDLen1 = RTPKT_TO_OSPKT(pPacket)->len;
48680 + pTxD->LastSec1 = 1;
48681 + }
48682 +
48683 +#ifdef RT_BIG_ENDIAN
48684 + RTMPWIEndianChange((PUCHAR)pTxWI, TYPE_TXWI);
48685 + RTMPFrameEndianChange(pAd, (((PUCHAR)pDMAHeaderBufVA)+TXWI_SIZE), DIR_WRITE, FALSE);
48686 + RTMPDescriptorEndianChange((PUCHAR)pTxD, TYPE_TXD);
48687 + WriteBackToDescriptor((PUCHAR)pDestTxD, (PUCHAR)pTxD, FALSE, TYPE_TXD);
48688 +#endif // RT_BIG_ENDIAN //
48689 + return 0;
48690 +}
48691 +/* */
48692 +/* */
48693 +/*=======================End of RT2860=======================*/
48694 +#endif // RT2860 //
48695 +
48696 +
48697 +VOID rt_ee_read_all(PRTMP_ADAPTER pAd, USHORT *Data)
48698 +{
48699 + USHORT i;
48700 + USHORT value;
48701 +
48702 + for (i = 0 ; i < EEPROM_SIZE/2 ; )
48703 + {
48704 + /* "value" is expecially for some compilers... */
48705 + RT28xx_EEPROM_READ16(pAd, i*2, value);
48706 + Data[i] = value;
48707 + i++;
48708 + }
48709 +}
48710 +
48711 +VOID rt_ee_write_all(PRTMP_ADAPTER pAd, USHORT *Data)
48712 +{
48713 + USHORT i;
48714 + USHORT value;
48715 +
48716 + for (i = 0 ; i < EEPROM_SIZE/2 ; )
48717 + {
48718 + /* "value" is expecially for some compilers... */
48719 + value = Data[i];
48720 + RT28xx_EEPROM_WRITE16(pAd, i*2, value);
48721 + i ++;
48722 + }
48723 +}
48724 +#ifdef RALINK_28xx_QA
48725 +VOID ATE_QA_Statistics(
48726 + IN PRTMP_ADAPTER pAd,
48727 + IN PRXWI_STRUC pRxWI,
48728 + IN PRT28XX_RXD_STRUC pRxD,
48729 + IN PHEADER_802_11 pHeader)
48730 +{
48731 + // update counter first
48732 + if (pHeader != NULL)
48733 + {
48734 + if (pHeader->FC.Type == BTYPE_DATA)
48735 + {
48736 + if (pRxD->U2M)
48737 + pAd->ate.U2M++;
48738 + else
48739 + pAd->ate.OtherData++;
48740 + }
48741 + else if (pHeader->FC.Type == BTYPE_MGMT)
48742 + {
48743 + if (pHeader->FC.SubType == SUBTYPE_BEACON)
48744 + pAd->ate.Beacon++;
48745 + else
48746 + pAd->ate.OtherCount++;
48747 + }
48748 + else if (pHeader->FC.Type == BTYPE_CNTL)
48749 + {
48750 + pAd->ate.OtherCount++;
48751 + }
48752 + }
48753 + pAd->ate.RSSI0 = pRxWI->RSSI0;
48754 + pAd->ate.RSSI1 = pRxWI->RSSI1;
48755 + pAd->ate.RSSI2 = pRxWI->RSSI2;
48756 + pAd->ate.SNR0 = pRxWI->SNR0;
48757 + pAd->ate.SNR1 = pRxWI->SNR1;
48758 +}
48759 +
48760 +/* command id with Cmd Type == 0x0008(for 28xx)/0x0005(for iNIC) */
48761 +#define RACFG_CMD_RF_WRITE_ALL 0x0000
48762 +#define RACFG_CMD_E2PROM_READ16 0x0001
48763 +#define RACFG_CMD_E2PROM_WRITE16 0x0002
48764 +#define RACFG_CMD_E2PROM_READ_ALL 0x0003
48765 +#define RACFG_CMD_E2PROM_WRITE_ALL 0x0004
48766 +#define RACFG_CMD_IO_READ 0x0005
48767 +#define RACFG_CMD_IO_WRITE 0x0006
48768 +#define RACFG_CMD_IO_READ_BULK 0x0007
48769 +#define RACFG_CMD_BBP_READ8 0x0008
48770 +#define RACFG_CMD_BBP_WRITE8 0x0009
48771 +#define RACFG_CMD_BBP_READ_ALL 0x000a
48772 +#define RACFG_CMD_GET_COUNTER 0x000b
48773 +#define RACFG_CMD_CLEAR_COUNTER 0x000c
48774 +
48775 +#define RACFG_CMD_RSV1 0x000d
48776 +#define RACFG_CMD_RSV2 0x000e
48777 +#define RACFG_CMD_RSV3 0x000f
48778 +
48779 +#define RACFG_CMD_TX_START 0x0010
48780 +#define RACFG_CMD_GET_TX_STATUS 0x0011
48781 +#define RACFG_CMD_TX_STOP 0x0012
48782 +#define RACFG_CMD_RX_START 0x0013
48783 +#define RACFG_CMD_RX_STOP 0x0014
48784 +#define RACFG_CMD_GET_NOISE_LEVEL 0x0015
48785 +
48786 +#define RACFG_CMD_ATE_START 0x0080
48787 +#define RACFG_CMD_ATE_STOP 0x0081
48788 +
48789 +#define RACFG_CMD_ATE_START_TX_CARRIER 0x0100
48790 +#define RACFG_CMD_ATE_START_TX_CONT 0x0101
48791 +#define RACFG_CMD_ATE_START_TX_FRAME 0x0102
48792 +#define RACFG_CMD_ATE_SET_BW 0x0103
48793 +#define RACFG_CMD_ATE_SET_TX_POWER0 0x0104
48794 +#define RACFG_CMD_ATE_SET_TX_POWER1 0x0105
48795 +#define RACFG_CMD_ATE_SET_FREQ_OFFSET 0x0106
48796 +#define RACFG_CMD_ATE_GET_STATISTICS 0x0107
48797 +#define RACFG_CMD_ATE_RESET_COUNTER 0x0108
48798 +#define RACFG_CMD_ATE_SEL_TX_ANTENNA 0x0109
48799 +#define RACFG_CMD_ATE_SEL_RX_ANTENNA 0x010a
48800 +#define RACFG_CMD_ATE_SET_PREAMBLE 0x010b
48801 +#define RACFG_CMD_ATE_SET_CHANNEL 0x010c
48802 +#define RACFG_CMD_ATE_SET_ADDR1 0x010d
48803 +#define RACFG_CMD_ATE_SET_ADDR2 0x010e
48804 +#define RACFG_CMD_ATE_SET_ADDR3 0x010f
48805 +#define RACFG_CMD_ATE_SET_RATE 0x0110
48806 +#define RACFG_CMD_ATE_SET_TX_FRAME_LEN 0x0111
48807 +#define RACFG_CMD_ATE_SET_TX_FRAME_COUNT 0x0112
48808 +#define RACFG_CMD_ATE_START_RX_FRAME 0x0113
48809 +#define RACFG_CMD_ATE_E2PROM_READ_BULK 0x0114
48810 +#define RACFG_CMD_ATE_E2PROM_WRITE_BULK 0x0115
48811 +#define RACFG_CMD_ATE_IO_WRITE_BULK 0x0116
48812 +#define RACFG_CMD_ATE_BBP_READ_BULK 0x0117
48813 +#define RACFG_CMD_ATE_BBP_WRITE_BULK 0x0118
48814 +#define RACFG_CMD_ATE_RF_READ_BULK 0x0119
48815 +#define RACFG_CMD_ATE_RF_WRITE_BULK 0x011a
48816 +
48817 +
48818 +
48819 +#define A2Hex(_X, _p) \
48820 +{ \
48821 + UCHAR *p; \
48822 + _X = 0; \
48823 + p = _p; \
48824 + while (((*p >= 'a') && (*p <= 'f')) || ((*p >= 'A') && (*p <= 'F')) || ((*p >= '0') && (*p <= '9'))) \
48825 + { \
48826 + if ((*p >= 'a') && (*p <= 'f')) \
48827 + _X = _X * 16 + *p - 87; \
48828 + else if ((*p >= 'A') && (*p <= 'F')) \
48829 + _X = _X * 16 + *p - 55; \
48830 + else if ((*p >= '0') && (*p <= '9')) \
48831 + _X = _X * 16 + *p - 48; \
48832 + p++; \
48833 + } \
48834 +}
48835 +
48836 +
48837 +static VOID memcpy_exl(PRTMP_ADAPTER pAd, UCHAR *dst, UCHAR *src, ULONG len);
48838 +static VOID memcpy_exs(PRTMP_ADAPTER pAd, UCHAR *dst, UCHAR *src, ULONG len);
48839 +static VOID RTMP_IO_READ_BULK(PRTMP_ADAPTER pAd, UCHAR *dst, UCHAR *src, UINT32 len);
48840 +
48841 +#ifdef UCOS
48842 +int ate_copy_to_user(
48843 + IN PUCHAR payload,
48844 + IN PUCHAR msg,
48845 + IN INT len)
48846 +{
48847 + memmove(payload, msg, len);
48848 + return 0;
48849 +}
48850 +
48851 +#undef copy_to_user
48852 +#define copy_to_user(x,y,z) ate_copy_to_user((PUCHAR)x, (PUCHAR)y, z)
48853 +#endif // UCOS //
48854 +
48855 +#define LEN_OF_ARG 16
48856 +
48857 +VOID RtmpDoAte(
48858 + IN PRTMP_ADAPTER pAdapter,
48859 + IN struct iwreq *wrq)
48860 +{
48861 + unsigned short Command_Id;
48862 + struct ate_racfghdr *pRaCfg;
48863 + INT Status = NDIS_STATUS_SUCCESS;
48864 +
48865 +
48866 +
48867 + if((pRaCfg = kmalloc(sizeof(struct ate_racfghdr), GFP_KERNEL)) == NULL)
48868 + {
48869 + Status = -EINVAL;
48870 + return;
48871 + }
48872 +
48873 + NdisZeroMemory(pRaCfg, sizeof(struct ate_racfghdr));
48874 +
48875 + if (copy_from_user((PUCHAR)pRaCfg, wrq->u.data.pointer, wrq->u.data.length))
48876 + {
48877 + Status = -EFAULT;
48878 + kfree(pRaCfg);
48879 + return;
48880 + }
48881 +
48882 +
48883 + Command_Id = ntohs(pRaCfg->command_id);
48884 +
48885 + ATEDBGPRINT(RT_DEBUG_TRACE,("\n%s: Command_Id = 0x%04x !\n", __FUNCTION__, Command_Id));
48886 +
48887 + switch (Command_Id)
48888 + {
48889 + // We will get this command when QA starts.
48890 + case RACFG_CMD_ATE_START:
48891 + {
48892 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_START\n"));
48893 +
48894 + // prepare feedback as soon as we can to avoid QA timeout.
48895 + pRaCfg->length = htons(2);
48896 + pRaCfg->status = htons(0);
48897 +
48898 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
48899 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
48900 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
48901 +
48902 + ATEDBGPRINT(RT_DEBUG_TRACE, ("wrq->u.data.length = %d\n", wrq->u.data.length));
48903 +
48904 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
48905 + {
48906 + ATEDBGPRINT(RT_DEBUG_TRACE, ("copy_to_user() fail in case RACFG_CMD_ATE_START\n"));
48907 + Status = -EFAULT;
48908 + }
48909 + else
48910 + {
48911 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_START is done !\n"));
48912 + }
48913 + Set_ATE_Proc(pAdapter, "ATESTART");
48914 + }
48915 + break;
48916 +
48917 + // We will get this command either QA is closed or ated is killed by user.
48918 + case RACFG_CMD_ATE_STOP:
48919 + {
48920 +#ifndef UCOS
48921 + INT32 ret;
48922 +#endif // !UCOS //
48923 +
48924 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_STOP\n"));
48925 +
48926 + // Distinguish this command came from QA(via ated)
48927 + // or ate daemon according to the existence of pid in payload.
48928 + // No need to prepare feedback if this cmd came directly from ate daemon.
48929 + pRaCfg->length = ntohs(pRaCfg->length);
48930 +
48931 + if (pRaCfg->length == sizeof(pAdapter->ate.AtePid))
48932 + {
48933 + // This command came from QA.
48934 + // Get the pid of ATE daemon.
48935 + memcpy((UCHAR *)&pAdapter->ate.AtePid,
48936 + (&pRaCfg->data[0]) - 2/* == &(pRaCfg->status) */,
48937 + sizeof(pAdapter->ate.AtePid));
48938 +
48939 + // prepare feedback as soon as we can to avoid QA timeout.
48940 + pRaCfg->length = htons(2);
48941 + pRaCfg->status = htons(0);
48942 +
48943 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
48944 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
48945 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
48946 +
48947 + ATEDBGPRINT(RT_DEBUG_TRACE, ("wrq->u.data.length = %d\n", wrq->u.data.length));
48948 +
48949 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
48950 + {
48951 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_STOP\n"));
48952 + Status = -EFAULT;
48953 + }
48954 +
48955 + //
48956 + // kill ATE daemon when leaving ATE mode.
48957 + // We must kill ATE daemon first before setting ATESTOP,
48958 + // or Microsoft will report sth. wrong.
48959 +#ifndef UCOS
48960 + ret = KILL_THREAD_PID(pAdapter->ate.AtePid, SIGTERM, 1);
48961 + if (ret)
48962 + {
48963 + ATEDBGPRINT(RT_DEBUG_ERROR, ("%s: unable to signal thread\n", pAdapter->net_dev->name));
48964 + }
48965 +#endif // !UCOS //
48966 + }
48967 +
48968 + // AP might have in ATE_STOP mode due to cmd from QA.
48969 + if (ATE_ON(pAdapter))
48970 + {
48971 + // Someone has killed ate daemon while QA GUI is still open.
48972 + Set_ATE_Proc(pAdapter, "ATESTOP");
48973 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_AP_START is done !\n"));
48974 + }
48975 + }
48976 + break;
48977 +
48978 + case RACFG_CMD_RF_WRITE_ALL:
48979 + {
48980 + UINT32 R1, R2, R3, R4;
48981 + USHORT channel;
48982 +
48983 + memcpy(&R1, pRaCfg->data-2, 4);
48984 + memcpy(&R2, pRaCfg->data+2, 4);
48985 + memcpy(&R3, pRaCfg->data+6, 4);
48986 + memcpy(&R4, pRaCfg->data+10, 4);
48987 + memcpy(&channel, pRaCfg->data+14, 2);
48988 +
48989 + pAdapter->LatchRfRegs.R1 = ntohl(R1);
48990 + pAdapter->LatchRfRegs.R2 = ntohl(R2);
48991 + pAdapter->LatchRfRegs.R3 = ntohl(R3);
48992 + pAdapter->LatchRfRegs.R4 = ntohl(R4);
48993 + pAdapter->LatchRfRegs.Channel = ntohs(channel);
48994 +
48995 + RTMP_RF_IO_WRITE32(pAdapter, pAdapter->LatchRfRegs.R1);
48996 + RTMP_RF_IO_WRITE32(pAdapter, pAdapter->LatchRfRegs.R2);
48997 + RTMP_RF_IO_WRITE32(pAdapter, pAdapter->LatchRfRegs.R3);
48998 + RTMP_RF_IO_WRITE32(pAdapter, pAdapter->LatchRfRegs.R4);
48999 +
49000 + // prepare feedback
49001 + pRaCfg->length = htons(2);
49002 + pRaCfg->status = htons(0);
49003 +
49004 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49005 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49006 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49007 +
49008 + ATEDBGPRINT(RT_DEBUG_TRACE, ("wrq->u.data.length = %d\n", wrq->u.data.length));
49009 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49010 + {
49011 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_RF_WRITE_ALL\n"));
49012 + Status = -EFAULT;
49013 + }
49014 + else
49015 + {
49016 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_RF_WRITE_ALL is done !\n"));
49017 + }
49018 + }
49019 + break;
49020 +
49021 + case RACFG_CMD_E2PROM_READ16:
49022 + {
49023 + USHORT offset, value, tmp;
49024 +
49025 + offset = ntohs(pRaCfg->status);
49026 + /* "tmp" is expecially for some compilers... */
49027 + RT28xx_EEPROM_READ16(pAdapter, offset, tmp);
49028 + value = tmp;
49029 + value = htons(value);
49030 +
49031 + ATEDBGPRINT(RT_DEBUG_TRACE,("EEPROM Read offset = 0x%04x, value = 0x%04x\n", offset, value));
49032 +
49033 + // prepare feedback
49034 + pRaCfg->length = htons(4);
49035 + pRaCfg->status = htons(0);
49036 + memcpy(pRaCfg->data, &value, 2);
49037 +
49038 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49039 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49040 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49041 +
49042 + ATEDBGPRINT(RT_DEBUG_TRACE, ("sizeof(struct ate_racfghdr) = %d\n", sizeof(struct ate_racfghdr)));
49043 + ATEDBGPRINT(RT_DEBUG_TRACE, ("wrq->u.data.length = %d\n", wrq->u.data.length));
49044 +
49045 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49046 + {
49047 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_E2PROM_READ16\n"));
49048 + Status = -EFAULT;
49049 + }
49050 + else
49051 + {
49052 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_E2PROM_READ16 is done !\n"));
49053 + }
49054 + }
49055 + break;
49056 +
49057 + case RACFG_CMD_E2PROM_WRITE16:
49058 + {
49059 + USHORT offset, value;
49060 +
49061 + offset = ntohs(pRaCfg->status);
49062 + memcpy(&value, pRaCfg->data, 2);
49063 + value = ntohs(value);
49064 + RT28xx_EEPROM_WRITE16(pAdapter, offset, value);
49065 +
49066 + // prepare feedback
49067 + pRaCfg->length = htons(2);
49068 + pRaCfg->status = htons(0);
49069 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49070 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49071 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49072 +
49073 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49074 + {
49075 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_E2PROM_WRITE16\n"));
49076 + Status = -EFAULT;
49077 + }
49078 + else
49079 + {
49080 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_E2PROM_WRITE16 is done !\n"));
49081 + }
49082 + }
49083 + break;
49084 +
49085 + case RACFG_CMD_E2PROM_READ_ALL:
49086 + {
49087 + USHORT buffer[EEPROM_SIZE/2];
49088 +
49089 + rt_ee_read_all(pAdapter,(USHORT *)buffer);
49090 + memcpy_exs(pAdapter, pRaCfg->data, (UCHAR *)buffer, EEPROM_SIZE);
49091 +
49092 + // prepare feedback
49093 + pRaCfg->length = htons(2+EEPROM_SIZE);
49094 + pRaCfg->status = htons(0);
49095 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49096 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49097 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49098 +
49099 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49100 + {
49101 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_E2PROM_READ_ALL\n"));
49102 + Status = -EFAULT;
49103 + }
49104 + else
49105 + {
49106 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_E2PROM_READ_ALL is done !\n"));
49107 + }
49108 + }
49109 + break;
49110 +
49111 + case RACFG_CMD_E2PROM_WRITE_ALL:
49112 + {
49113 + USHORT buffer[EEPROM_SIZE/2];
49114 +
49115 + NdisZeroMemory((UCHAR *)buffer, EEPROM_SIZE);
49116 + memcpy_exs(pAdapter, (UCHAR *)buffer, (UCHAR *)&pRaCfg->status, EEPROM_SIZE);
49117 + rt_ee_write_all(pAdapter,(USHORT *)buffer);
49118 +
49119 + // prepare feedback
49120 + pRaCfg->length = htons(2);
49121 + pRaCfg->status = htons(0);
49122 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49123 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49124 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49125 +
49126 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49127 + {
49128 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_E2PROM_WRITE_ALL\n"));
49129 + Status = -EFAULT;
49130 + }
49131 + else
49132 + {
49133 + ATEDBGPRINT(RT_DEBUG_ERROR, ("RACFG_CMD_E2PROM_WRITE_ALL is done !\n"));
49134 + }
49135 +
49136 + }
49137 + break;
49138 +
49139 + case RACFG_CMD_IO_READ:
49140 + {
49141 + UINT32 offset;
49142 + UINT32 value;
49143 +
49144 + memcpy(&offset, &pRaCfg->status, 4);
49145 + offset = ntohl(offset);
49146 +
49147 + // We do not need the base address.
49148 + // So just extract the offset out.
49149 + offset &= 0x0000FFFF;
49150 + RTMP_IO_READ32(pAdapter, offset, &value);
49151 + value = htonl(value);
49152 +
49153 + // prepare feedback
49154 + pRaCfg->length = htons(6);
49155 + pRaCfg->status = htons(0);
49156 + memcpy(pRaCfg->data, &value, 4);
49157 +
49158 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49159 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49160 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49161 +
49162 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49163 + {
49164 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_IO_READ\n"));
49165 + Status = -EFAULT;
49166 + }
49167 + else
49168 + {
49169 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_IO_READ is done !\n"));
49170 + }
49171 + }
49172 + break;
49173 +
49174 + case RACFG_CMD_IO_WRITE:
49175 + {
49176 + UINT32 offset, value;
49177 +
49178 + memcpy(&offset, pRaCfg->data-2, 4);
49179 + memcpy(&value, pRaCfg->data+2, 4);
49180 +
49181 + offset = ntohl(offset);
49182 +
49183 + // We do not need the base address.
49184 + // So just extract out the offset.
49185 + offset &= 0x0000FFFF;
49186 + value = ntohl(value);
49187 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_IO_WRITE: offset = %x, value = %x\n", offset, value));
49188 + RTMP_IO_WRITE32(pAdapter, offset, value);
49189 +
49190 + // prepare feedback
49191 + pRaCfg->length = htons(2);
49192 + pRaCfg->status = htons(0);
49193 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49194 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49195 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49196 +
49197 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49198 + {
49199 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_IO_WRITE\n"));
49200 + Status = -EFAULT;
49201 + }
49202 + else
49203 + {
49204 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_IO_WRITE is done !\n"));
49205 + }
49206 + }
49207 + break;
49208 +
49209 + case RACFG_CMD_IO_READ_BULK:
49210 + {
49211 + UINT32 offset;
49212 + USHORT len;
49213 +
49214 + memcpy(&offset, &pRaCfg->status, 4);
49215 + offset = ntohl(offset);
49216 +
49217 + // We do not need the base address.
49218 + // So just extract the offset.
49219 + offset &= 0x0000FFFF;
49220 + memcpy(&len, pRaCfg->data+2, 2);
49221 + len = ntohs(len);
49222 +
49223 + if (len > 371)
49224 + {
49225 + ATEDBGPRINT(RT_DEBUG_TRACE,("len is too large, make it smaller\n"));
49226 + pRaCfg->length = htons(2);
49227 + pRaCfg->status = htons(1);
49228 + break;
49229 + }
49230 +
49231 + RTMP_IO_READ_BULK(pAdapter, pRaCfg->data, (UCHAR *)offset, len*4);// unit in four bytes
49232 +
49233 + // prepare feedback
49234 + pRaCfg->length = htons(2+len*4);// unit in four bytes
49235 + pRaCfg->status = htons(0);
49236 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49237 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49238 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49239 +
49240 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49241 + {
49242 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_IO_READ_BULK\n"));
49243 + Status = -EFAULT;
49244 + }
49245 + else
49246 + {
49247 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_IO_READ_BULK is done !\n"));
49248 + }
49249 + }
49250 + break;
49251 +
49252 + case RACFG_CMD_BBP_READ8:
49253 + {
49254 + USHORT offset;
49255 + UCHAR value;
49256 +
49257 + value = 0;
49258 + offset = ntohs(pRaCfg->status);
49259 +
49260 + if (ATE_ON(pAdapter))
49261 + {
49262 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, offset, &value);
49263 + }
49264 + else
49265 + {
49266 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, offset, &value);
49267 + }
49268 + // prepare feedback
49269 + pRaCfg->length = htons(3);
49270 + pRaCfg->status = htons(0);
49271 + pRaCfg->data[0] = value;
49272 +
49273 + ATEDBGPRINT(RT_DEBUG_TRACE,("BBP value = %x\n", value));
49274 +
49275 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49276 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49277 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49278 +
49279 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49280 + {
49281 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_BBP_READ8\n"));
49282 + Status = -EFAULT;
49283 + }
49284 + else
49285 + {
49286 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_BBP_READ8 is done !\n"));
49287 + }
49288 + }
49289 + break;
49290 + case RACFG_CMD_BBP_WRITE8:
49291 + {
49292 + USHORT offset;
49293 + UCHAR value;
49294 +
49295 + offset = ntohs(pRaCfg->status);
49296 + memcpy(&value, pRaCfg->data, 1);
49297 +
49298 + if (ATE_ON(pAdapter))
49299 + {
49300 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAdapter, offset, value);
49301 + }
49302 + else
49303 + {
49304 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, offset, value);
49305 + }
49306 +
49307 + if ((offset == BBP_R1) || (offset == BBP_R3))
49308 + {
49309 + SyncTxRxConfig(pAdapter, offset, value);
49310 + }
49311 +
49312 + // prepare feedback
49313 + pRaCfg->length = htons(2);
49314 + pRaCfg->status = htons(0);
49315 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49316 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49317 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49318 +
49319 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49320 + {
49321 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_BBP_WRITE8\n"));
49322 + Status = -EFAULT;
49323 + }
49324 + else
49325 + {
49326 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_BBP_WRITE8 is done !\n"));
49327 + }
49328 + }
49329 + break;
49330 +
49331 + case RACFG_CMD_BBP_READ_ALL:
49332 + {
49333 + USHORT j;
49334 +
49335 + for (j = 0; j < 137; j++)
49336 + {
49337 + pRaCfg->data[j] = 0;
49338 +
49339 + if (ATE_ON(pAdapter))
49340 + {
49341 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, j, &pRaCfg->data[j]);
49342 + }
49343 + else
49344 + {
49345 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, j, &pRaCfg->data[j]);
49346 + }
49347 + }
49348 +
49349 + // prepare feedback
49350 + pRaCfg->length = htons(2+137);
49351 + pRaCfg->status = htons(0);
49352 +
49353 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49354 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49355 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49356 +
49357 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49358 + {
49359 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_BBP_READ_ALL\n"));
49360 + Status = -EFAULT;
49361 + }
49362 + else
49363 + {
49364 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_BBP_READ_ALL is done !\n"));
49365 + }
49366 + }
49367 +
49368 + break;
49369 +
49370 + case RACFG_CMD_ATE_E2PROM_READ_BULK:
49371 + {
49372 + USHORT offset;
49373 + USHORT len;
49374 + USHORT buffer[EEPROM_SIZE/2];
49375 +
49376 + offset = ntohs(pRaCfg->status);
49377 + memcpy(&len, pRaCfg->data, 2);
49378 + len = ntohs(len);
49379 +
49380 + rt_ee_read_all(pAdapter,(USHORT *)buffer);
49381 + if (offset + len <= EEPROM_SIZE)
49382 + memcpy_exs(pAdapter, pRaCfg->data, (UCHAR *)buffer+offset, len);
49383 + else
49384 + ATEDBGPRINT(RT_DEBUG_ERROR, ("exceed EEPROM size\n"));
49385 +
49386 + // prepare feedback
49387 + pRaCfg->length = htons(2+len);
49388 + pRaCfg->status = htons(0);
49389 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49390 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49391 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49392 +
49393 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49394 + {
49395 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_E2PROM_READ_BULK\n"));
49396 + Status = -EFAULT;
49397 + }
49398 + else
49399 + {
49400 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_E2PROM_READ_BULK is done !\n"));
49401 + }
49402 +
49403 + }
49404 + break;
49405 +
49406 + case RACFG_CMD_ATE_E2PROM_WRITE_BULK:
49407 + {
49408 + USHORT offset;
49409 + USHORT len;
49410 + USHORT buffer[EEPROM_SIZE/2];
49411 +
49412 + offset = ntohs(pRaCfg->status);
49413 + memcpy(&len, pRaCfg->data, 2);
49414 + len = ntohs(len);
49415 +
49416 + rt_ee_read_all(pAdapter,(USHORT *)buffer);
49417 + memcpy_exs(pAdapter, (UCHAR *)buffer + offset, (UCHAR *)pRaCfg->data + 2, len);
49418 + rt_ee_write_all(pAdapter,(USHORT *)buffer);
49419 +
49420 + // prepare feedback
49421 + pRaCfg->length = htons(2);
49422 + pRaCfg->status = htons(0);
49423 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49424 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49425 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49426 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49427 + {
49428 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_E2PROM_WRITE_BULK\n"));
49429 + Status = -EFAULT;
49430 + }
49431 + else
49432 + {
49433 + ATEDBGPRINT(RT_DEBUG_ERROR, ("RACFG_CMD_ATE_E2PROM_WRITE_BULK is done !\n"));
49434 + }
49435 +
49436 + }
49437 + break;
49438 +
49439 + case RACFG_CMD_ATE_IO_WRITE_BULK:
49440 + {
49441 + UINT32 offset, i, value;
49442 + USHORT len;
49443 +
49444 + memcpy(&offset, &pRaCfg->status, 4);
49445 + offset = ntohl(offset);
49446 + memcpy(&len, pRaCfg->data+2, 2);
49447 + len = ntohs(len);
49448 +
49449 + for (i = 0; i < len; i += 4)
49450 + {
49451 + memcpy_exl(pAdapter, (UCHAR *)&value, pRaCfg->data+4+i, 4);
49452 + printk("Write %x %x\n", offset + i, value);
49453 + RTMP_IO_WRITE32(pAdapter, (offset +i) & 0xffff, value);
49454 + }
49455 +
49456 + // prepare feedback
49457 + pRaCfg->length = htons(2);
49458 + pRaCfg->status = htons(0);
49459 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49460 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49461 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49462 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49463 + {
49464 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_IO_WRITE_BULK\n"));
49465 + Status = -EFAULT;
49466 + }
49467 + else
49468 + {
49469 + ATEDBGPRINT(RT_DEBUG_ERROR, ("RACFG_CMD_ATE_IO_WRITE_BULK is done !\n"));
49470 + }
49471 +
49472 + }
49473 + break;
49474 +
49475 + case RACFG_CMD_ATE_BBP_READ_BULK:
49476 + {
49477 + USHORT offset;
49478 + USHORT len;
49479 + USHORT j;
49480 +
49481 + offset = ntohs(pRaCfg->status);
49482 + memcpy(&len, pRaCfg->data, 2);
49483 + len = ntohs(len);
49484 +
49485 +
49486 + for (j = offset; j < (offset+len); j++)
49487 + {
49488 + pRaCfg->data[j - offset] = 0;
49489 +
49490 + if (pAdapter->ate.Mode == ATE_STOP)
49491 + {
49492 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, j, &pRaCfg->data[j - offset]);
49493 + }
49494 + else
49495 + {
49496 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, j, &pRaCfg->data[j - offset]);
49497 + }
49498 + }
49499 +
49500 + // prepare feedback
49501 + pRaCfg->length = htons(2+len);
49502 + pRaCfg->status = htons(0);
49503 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49504 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49505 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49506 +
49507 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49508 + {
49509 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_BBP_READ_BULK\n"));
49510 + Status = -EFAULT;
49511 + }
49512 + else
49513 + {
49514 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_BBP_READ_BULK is done !\n"));
49515 + }
49516 +
49517 + }
49518 + break;
49519 +
49520 + case RACFG_CMD_ATE_BBP_WRITE_BULK:
49521 + {
49522 + USHORT offset;
49523 + USHORT len;
49524 + USHORT j;
49525 + UCHAR *value;
49526 +
49527 + offset = ntohs(pRaCfg->status);
49528 + memcpy(&len, pRaCfg->data, 2);
49529 + len = ntohs(len);
49530 +
49531 + for (j = offset; j < (offset+len); j++)
49532 + {
49533 + value = pRaCfg->data + 2 + (j - offset);
49534 + if (pAdapter->ate.Mode == ATE_STOP)
49535 + {
49536 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, j, *value);
49537 + }
49538 + else
49539 + {
49540 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAdapter, j, *value);
49541 + }
49542 + }
49543 +
49544 + // prepare feedback
49545 + pRaCfg->length = htons(2);
49546 + pRaCfg->status = htons(0);
49547 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49548 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49549 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49550 +
49551 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49552 + {
49553 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_BBP_WRITE_BULK\n"));
49554 + Status = -EFAULT;
49555 + }
49556 + else
49557 + {
49558 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_BBP_WRITE_BULK is done !\n"));
49559 + }
49560 + }
49561 + break;
49562 +
49563 +#ifdef CONFIG_RALINK_RT3052
49564 + case RACFG_CMD_ATE_RF_READ_BULK:
49565 + {
49566 + USHORT offset;
49567 + USHORT len;
49568 + USHORT j;
49569 +
49570 + offset = ntohs(pRaCfg->status);
49571 + memcpy(&len, pRaCfg->data, 2);
49572 + len = ntohs(len);
49573 +
49574 + for (j = offset; j < (offset+len); j++)
49575 + {
49576 + pRaCfg->data[j - offset] = 0;
49577 + RT30xxReadRFRegister(pAdapter, j, &pRaCfg->data[j - offset]);
49578 + }
49579 +
49580 + // prepare feedback
49581 + pRaCfg->length = htons(2+len);
49582 + pRaCfg->status = htons(0);
49583 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49584 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49585 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49586 +
49587 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49588 + {
49589 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_RF_READ_BULK\n"));
49590 + Status = -EFAULT;
49591 + }
49592 + else
49593 + {
49594 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_RF_READ_BULK is done !\n"));
49595 + }
49596 +
49597 + }
49598 + break;
49599 +
49600 + case RACFG_CMD_ATE_RF_WRITE_BULK:
49601 + {
49602 + USHORT offset;
49603 + USHORT len;
49604 + USHORT j;
49605 + UCHAR *value;
49606 +
49607 + offset = ntohs(pRaCfg->status);
49608 + memcpy(&len, pRaCfg->data, 2);
49609 + len = ntohs(len);
49610 +
49611 + for (j = offset; j < (offset+len); j++)
49612 + {
49613 + value = pRaCfg->data + 2 + (j - offset);
49614 + RT30xxWriteRFRegister(pAdapter, j, *value);
49615 + }
49616 +
49617 + // prepare feedback
49618 + pRaCfg->length = htons(2);
49619 + pRaCfg->status = htons(0);
49620 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49621 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49622 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49623 +
49624 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49625 + {
49626 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_RF_WRITE_BULK\n"));
49627 + Status = -EFAULT;
49628 + }
49629 + else
49630 + {
49631 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_RF_WRITE_BULK is done !\n"));
49632 + }
49633 +
49634 + }
49635 + break;
49636 +#endif
49637 +
49638 +
49639 + case RACFG_CMD_GET_NOISE_LEVEL:
49640 + {
49641 + UCHAR channel;
49642 + INT32 buffer[3][10];/* 3 : RxPath ; 10 : no. of per rssi samples */
49643 +
49644 + channel = (ntohs(pRaCfg->status) & 0x00FF);
49645 + CalNoiseLevel(pAdapter, channel, buffer);
49646 + memcpy_exl(pAdapter, (UCHAR *)pRaCfg->data, (UCHAR *)&(buffer[0][0]), (sizeof(INT32)*3*10));
49647 +
49648 + // prepare feedback
49649 + pRaCfg->length = htons(2 + (sizeof(INT32)*3*10));
49650 + pRaCfg->status = htons(0);
49651 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49652 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49653 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49654 +
49655 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49656 + {
49657 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_GET_NOISE_LEVEL\n"));
49658 + Status = -EFAULT;
49659 + }
49660 + else
49661 + {
49662 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_GET_NOISE_LEVEL is done !\n"));
49663 + }
49664 + }
49665 + break;
49666 +
49667 + case RACFG_CMD_GET_COUNTER:
49668 + {
49669 + memcpy_exl(pAdapter, &pRaCfg->data[0], (UCHAR *)&pAdapter->ate.U2M, 4);
49670 + memcpy_exl(pAdapter, &pRaCfg->data[4], (UCHAR *)&pAdapter->ate.OtherData, 4);
49671 + memcpy_exl(pAdapter, &pRaCfg->data[8], (UCHAR *)&pAdapter->ate.Beacon, 4);
49672 + memcpy_exl(pAdapter, &pRaCfg->data[12], (UCHAR *)&pAdapter->ate.OtherCount, 4);
49673 + memcpy_exl(pAdapter, &pRaCfg->data[16], (UCHAR *)&pAdapter->ate.TxAc0, 4);
49674 + memcpy_exl(pAdapter, &pRaCfg->data[20], (UCHAR *)&pAdapter->ate.TxAc1, 4);
49675 + memcpy_exl(pAdapter, &pRaCfg->data[24], (UCHAR *)&pAdapter->ate.TxAc2, 4);
49676 + memcpy_exl(pAdapter, &pRaCfg->data[28], (UCHAR *)&pAdapter->ate.TxAc3, 4);
49677 + memcpy_exl(pAdapter, &pRaCfg->data[32], (UCHAR *)&pAdapter->ate.TxHCCA, 4);
49678 + memcpy_exl(pAdapter, &pRaCfg->data[36], (UCHAR *)&pAdapter->ate.TxMgmt, 4);
49679 + memcpy_exl(pAdapter, &pRaCfg->data[40], (UCHAR *)&pAdapter->ate.RSSI0, 4);
49680 + memcpy_exl(pAdapter, &pRaCfg->data[44], (UCHAR *)&pAdapter->ate.RSSI1, 4);
49681 + memcpy_exl(pAdapter, &pRaCfg->data[48], (UCHAR *)&pAdapter->ate.RSSI2, 4);
49682 + memcpy_exl(pAdapter, &pRaCfg->data[52], (UCHAR *)&pAdapter->ate.SNR0, 4);
49683 + memcpy_exl(pAdapter, &pRaCfg->data[56], (UCHAR *)&pAdapter->ate.SNR1, 4);
49684 +
49685 + pRaCfg->length = htons(2+60);
49686 + pRaCfg->status = htons(0);
49687 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49688 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49689 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49690 +
49691 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49692 + {
49693 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_GET_COUNTER\n"));
49694 + Status = -EFAULT;
49695 + }
49696 + else
49697 + {
49698 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_GET_COUNTER is done !\n"));
49699 + }
49700 + }
49701 + break;
49702 +
49703 + case RACFG_CMD_CLEAR_COUNTER:
49704 + {
49705 + pAdapter->ate.U2M = 0;
49706 + pAdapter->ate.OtherData = 0;
49707 + pAdapter->ate.Beacon = 0;
49708 + pAdapter->ate.OtherCount = 0;
49709 + pAdapter->ate.TxAc0 = 0;
49710 + pAdapter->ate.TxAc1 = 0;
49711 + pAdapter->ate.TxAc2 = 0;
49712 + pAdapter->ate.TxAc3 = 0;
49713 + pAdapter->ate.TxHCCA = 0;
49714 + pAdapter->ate.TxMgmt = 0;
49715 + pAdapter->ate.TxDoneCount = 0;
49716 +
49717 + pRaCfg->length = htons(2);
49718 + pRaCfg->status = htons(0);
49719 +
49720 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49721 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49722 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49723 +
49724 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49725 + {
49726 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_CLEAR_COUNTER\n"));
49727 + Status = -EFAULT;
49728 + }
49729 + else
49730 + {
49731 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_CLEAR_COUNTER is done !\n"));
49732 + }
49733 + }
49734 +
49735 + break;
49736 +
49737 + case RACFG_CMD_TX_START:
49738 + {
49739 + USHORT *p;
49740 + USHORT err = 1;
49741 + UCHAR Bbp22Value = 0, Bbp24Value = 0;
49742 +
49743 + if ((pAdapter->ate.TxStatus != 0) && (pAdapter->ate.Mode & ATE_TXFRAME))
49744 + {
49745 + ATEDBGPRINT(RT_DEBUG_TRACE,("Ate Tx is already running, to run next Tx, you must stop it first\n"));
49746 + err = 2;
49747 + goto TX_START_ERROR;
49748 + }
49749 + else if ((pAdapter->ate.TxStatus != 0) && !(pAdapter->ate.Mode & ATE_TXFRAME))
49750 + {
49751 + int i = 0;
49752 +
49753 + while ((i++ < 10) && (pAdapter->ate.TxStatus != 0))
49754 + {
49755 + RTMPusecDelay(5000);
49756 + }
49757 +
49758 + // force it to stop
49759 + pAdapter->ate.TxStatus = 0;
49760 + pAdapter->ate.TxDoneCount = 0;
49761 + //pAdapter->ate.Repeat = 0;
49762 + pAdapter->ate.bQATxStart = FALSE;
49763 + }
49764 +
49765 + // If pRaCfg->length == 0, this "RACFG_CMD_TX_START" is for Carrier test or Carrier Suppression.
49766 + if (ntohs(pRaCfg->length) != 0)
49767 + {
49768 + // Get frame info
49769 +
49770 + NdisMoveMemory(&pAdapter->ate.TxWI, pRaCfg->data + 2, 16);
49771 +#ifdef RT_BIG_ENDIAN
49772 + RTMPWIEndianChange((PUCHAR)&pAdapter->ate.TxWI, TYPE_TXWI);
49773 +#endif // RT_BIG_ENDIAN //
49774 +
49775 + NdisMoveMemory(&pAdapter->ate.TxCount, pRaCfg->data + 18, 4);
49776 + pAdapter->ate.TxCount = ntohl(pAdapter->ate.TxCount);
49777 +
49778 + p = (USHORT *)(&pRaCfg->data[22]);
49779 + //p = pRaCfg->data + 22;
49780 + // always use QID_AC_BE
49781 + pAdapter->ate.QID = 0;
49782 + p = (USHORT *)(&pRaCfg->data[24]);
49783 + //p = pRaCfg->data + 24;
49784 + pAdapter->ate.HLen = ntohs(*p);
49785 +
49786 + if (pAdapter->ate.HLen > 32)
49787 + {
49788 + ATEDBGPRINT(RT_DEBUG_ERROR,("pAdapter->ate.HLen > 32\n"));
49789 + err = 3;
49790 + goto TX_START_ERROR;
49791 + }
49792 +
49793 + NdisMoveMemory(&pAdapter->ate.Header, pRaCfg->data + 26, pAdapter->ate.HLen);
49794 +
49795 +
49796 + pAdapter->ate.PLen = ntohs(pRaCfg->length) - (pAdapter->ate.HLen + 28);
49797 +
49798 + if (pAdapter->ate.PLen > 32)
49799 + {
49800 + ATEDBGPRINT(RT_DEBUG_ERROR,("pAdapter->ate.PLen > 32\n"));
49801 + err = 4;
49802 + goto TX_START_ERROR;
49803 + }
49804 +
49805 + NdisMoveMemory(&pAdapter->ate.Pattern, pRaCfg->data + 26 + pAdapter->ate.HLen, pAdapter->ate.PLen);
49806 + pAdapter->ate.DLen = pAdapter->ate.TxWI.MPDUtotalByteCount - pAdapter->ate.HLen;
49807 + }
49808 +
49809 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R22, &Bbp22Value);
49810 +
49811 + switch (Bbp22Value)
49812 + {
49813 + case BBP22_TXFRAME:
49814 + {
49815 + if (pAdapter->ate.TxCount == 0)
49816 + {
49817 +#ifdef RT2860
49818 + pAdapter->ate.TxCount = 0xFFFFFFFF;
49819 +#endif // RT2860 //
49820 + }
49821 + ATEDBGPRINT(RT_DEBUG_TRACE,("START TXFRAME\n"));
49822 + pAdapter->ate.bQATxStart = TRUE;
49823 + Set_ATE_Proc(pAdapter, "TXFRAME");
49824 + }
49825 + break;
49826 +
49827 + case BBP22_TXCONT_OR_CARRSUPP:
49828 + {
49829 + ATEDBGPRINT(RT_DEBUG_TRACE,("BBP22_TXCONT_OR_CARRSUPP\n"));
49830 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, 24, &Bbp24Value);
49831 +
49832 + switch (Bbp24Value)
49833 + {
49834 + case BBP24_TXCONT:
49835 + {
49836 + ATEDBGPRINT(RT_DEBUG_TRACE,("START TXCONT\n"));
49837 + pAdapter->ate.bQATxStart = TRUE;
49838 + Set_ATE_Proc(pAdapter, "TXCONT");
49839 + }
49840 + break;
49841 +
49842 + case BBP24_CARRSUPP:
49843 + {
49844 + ATEDBGPRINT(RT_DEBUG_TRACE,("START TXCARRSUPP\n"));
49845 + pAdapter->ate.bQATxStart = TRUE;
49846 + pAdapter->ate.Mode |= ATE_TXCARRSUPP;
49847 + }
49848 + break;
49849 +
49850 + default:
49851 + {
49852 + ATEDBGPRINT(RT_DEBUG_ERROR,("Unknown Start TX subtype !"));
49853 + }
49854 + break;
49855 + }
49856 + }
49857 + break;
49858 +
49859 + case BBP22_TXCARR:
49860 + {
49861 + ATEDBGPRINT(RT_DEBUG_TRACE,("START TXCARR\n"));
49862 + pAdapter->ate.bQATxStart = TRUE;
49863 + Set_ATE_Proc(pAdapter, "TXCARR");
49864 + }
49865 + break;
49866 +
49867 + default:
49868 + {
49869 + ATEDBGPRINT(RT_DEBUG_ERROR,("Unknown Start TX subtype !"));
49870 + }
49871 + break;
49872 + }
49873 +
49874 + if (pAdapter->ate.bQATxStart == TRUE)
49875 + {
49876 + // prepare feedback
49877 + pRaCfg->length = htons(2);
49878 + pRaCfg->status = htons(0);
49879 +
49880 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49881 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49882 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49883 +
49884 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49885 + {
49886 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() was failed in case RACFG_CMD_TX_START\n"));
49887 + Status = -EFAULT;
49888 + }
49889 + else
49890 + {
49891 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_TX_START is done !\n"));
49892 + }
49893 + break;
49894 + }
49895 +
49896 +TX_START_ERROR:
49897 + // prepare feedback
49898 + pRaCfg->length = htons(2);
49899 + pRaCfg->status = htons(err);
49900 +
49901 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49902 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49903 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49904 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49905 + {
49906 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_TX_START\n"));
49907 + Status = -EFAULT;
49908 + }
49909 + else
49910 + {
49911 + ATEDBGPRINT(RT_DEBUG_TRACE, ("feedback of TX_START_ERROR is done !\n"));
49912 + }
49913 + }
49914 + break;
49915 +
49916 + case RACFG_CMD_GET_TX_STATUS:
49917 + {
49918 + UINT32 count;
49919 +
49920 + // prepare feedback
49921 + pRaCfg->length = htons(6);
49922 + pRaCfg->status = htons(0);
49923 + count = htonl(pAdapter->ate.TxDoneCount);
49924 + NdisMoveMemory(pRaCfg->data, &count, 4);
49925 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49926 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49927 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49928 +
49929 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49930 + {
49931 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_GET_TX_STATUS\n"));
49932 + Status = -EFAULT;
49933 + }
49934 + else
49935 + {
49936 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_GET_TX_STATUS is done !\n"));
49937 + }
49938 + }
49939 + break;
49940 +
49941 + case RACFG_CMD_TX_STOP:
49942 + {
49943 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_TX_STOP\n"));
49944 +
49945 + Set_ATE_Proc(pAdapter, "TXSTOP");
49946 +
49947 + // prepare feedback
49948 + pRaCfg->length = htons(2);
49949 + pRaCfg->status = htons(0);
49950 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49951 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49952 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49953 +
49954 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49955 + {
49956 + ATEDBGPRINT(RT_DEBUG_TRACE, ("copy_to_user() fail in case RACFG_CMD_TX_STOP\n"));
49957 + Status = -EFAULT;
49958 + }
49959 + else
49960 + {
49961 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_TX_STOP is done !\n"));
49962 + }
49963 + }
49964 + break;
49965 +
49966 + case RACFG_CMD_RX_START:
49967 + {
49968 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_RX_START\n"));
49969 +
49970 + pAdapter->ate.bQARxStart = TRUE;
49971 + Set_ATE_Proc(pAdapter, "RXFRAME");
49972 +
49973 + // prepare feedback
49974 + pRaCfg->length = htons(2);
49975 + pRaCfg->status = htons(0);
49976 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
49977 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
49978 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
49979 +
49980 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
49981 + {
49982 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_RX_START\n"));
49983 + Status = -EFAULT;
49984 + }
49985 + else
49986 + {
49987 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_RX_START is done !\n"));
49988 + }
49989 + }
49990 + break;
49991 +
49992 + case RACFG_CMD_RX_STOP:
49993 + {
49994 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_RX_STOP\n"));
49995 +
49996 + Set_ATE_Proc(pAdapter, "RXSTOP");
49997 +
49998 + // prepare feedback
49999 + pRaCfg->length = htons(2);
50000 + pRaCfg->status = htons(0);
50001 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50002 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50003 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50004 +
50005 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50006 + {
50007 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_RX_STOP\n"));
50008 + Status = -EFAULT;
50009 + }
50010 + else
50011 + {
50012 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_RX_STOP is done !\n"));
50013 + }
50014 + }
50015 + break;
50016 +
50017 + /* The following cases are for new ATE GUI(not QA). */
50018 + /*==================================================*/
50019 + case RACFG_CMD_ATE_START_TX_CARRIER:
50020 + {
50021 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_START_TX_CARRIER\n"));
50022 +
50023 + Set_ATE_Proc(pAdapter, "TXCARR");
50024 +
50025 + pRaCfg->length = htons(2);
50026 + pRaCfg->status = htons(0);
50027 +
50028 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50029 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50030 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50031 +
50032 + ATEDBGPRINT(RT_DEBUG_TRACE, ("wrq->u.data.length = %d\n", wrq->u.data.length));
50033 +
50034 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50035 + {
50036 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_START_TX_CARRIER\n"));
50037 + Status = -EFAULT;
50038 + }
50039 + else
50040 + {
50041 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_START_TX_CARRIER is done !\n"));
50042 + }
50043 + }
50044 + break;
50045 +
50046 + case RACFG_CMD_ATE_START_TX_CONT:
50047 + {
50048 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_START_TX_CONT\n"));
50049 +
50050 + Set_ATE_Proc(pAdapter, "TXCONT");
50051 +
50052 + pRaCfg->length = htons(2);
50053 + pRaCfg->status = htons(0);
50054 +
50055 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50056 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50057 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50058 +
50059 + ATEDBGPRINT(RT_DEBUG_TRACE, ("wrq->u.data.length = %d\n", wrq->u.data.length));
50060 +
50061 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50062 + {
50063 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_START_TX_CONT\n"));
50064 + Status = -EFAULT;
50065 + }
50066 + else
50067 + {
50068 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_START_TX_CONT is done !\n"));
50069 + }
50070 + }
50071 + break;
50072 +
50073 + case RACFG_CMD_ATE_START_TX_FRAME:
50074 + {
50075 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_START_TX_FRAME\n"));
50076 +
50077 + Set_ATE_Proc(pAdapter, "TXFRAME");
50078 +
50079 + pRaCfg->length = htons(2);
50080 + pRaCfg->status = htons(0);
50081 +
50082 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50083 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50084 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50085 +
50086 + ATEDBGPRINT(RT_DEBUG_TRACE, ("wrq->u.data.length = %d\n", wrq->u.data.length));
50087 +
50088 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50089 + {
50090 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_START_TX_FRAME\n"));
50091 + Status = -EFAULT;
50092 + }
50093 + else
50094 + {
50095 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_START_TX_FRAME is done !\n"));
50096 + }
50097 + }
50098 + break;
50099 +
50100 + case RACFG_CMD_ATE_SET_BW:
50101 + {
50102 + SHORT value = 0;
50103 + UCHAR str[LEN_OF_ARG];
50104 +
50105 + NdisZeroMemory(str, LEN_OF_ARG);
50106 +
50107 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_BW\n"));
50108 +
50109 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50110 + value = ntohs(value);
50111 + sprintf((PCHAR)str, "%d", value);
50112 +
50113 + Set_ATE_TX_BW_Proc(pAdapter, str);
50114 +
50115 + // prepare feedback
50116 + pRaCfg->length = htons(2);
50117 + pRaCfg->status = htons(0);
50118 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50119 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50120 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50121 +
50122 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50123 + {
50124 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_BW\n"));
50125 + Status = -EFAULT;
50126 + }
50127 + else
50128 + {
50129 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_BW is done !\n"));
50130 + }
50131 + }
50132 + break;
50133 +
50134 + case RACFG_CMD_ATE_SET_TX_POWER0:
50135 + {
50136 + SHORT value = 0;
50137 + UCHAR str[LEN_OF_ARG];
50138 +
50139 + NdisZeroMemory(str, LEN_OF_ARG);
50140 +
50141 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_TX_POWER0\n"));
50142 +
50143 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50144 + value = ntohs(value);
50145 + sprintf((PCHAR)str, "%d", value);
50146 + Set_ATE_TX_POWER0_Proc(pAdapter, str);
50147 +
50148 + // prepare feedback
50149 + pRaCfg->length = htons(2);
50150 + pRaCfg->status = htons(0);
50151 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50152 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50153 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50154 +
50155 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50156 + {
50157 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_TX_POWER0\n"));
50158 + Status = -EFAULT;
50159 + }
50160 + else
50161 + {
50162 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_TX_POWER0 is done !\n"));
50163 + }
50164 + }
50165 + break;
50166 +
50167 + case RACFG_CMD_ATE_SET_TX_POWER1:
50168 + {
50169 + SHORT value = 0;
50170 + UCHAR str[LEN_OF_ARG];
50171 +
50172 + NdisZeroMemory(str, LEN_OF_ARG);
50173 +
50174 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_TX_POWER1\n"));
50175 +
50176 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50177 + value = ntohs(value);
50178 + sprintf((PCHAR)str, "%d", value);
50179 + Set_ATE_TX_POWER1_Proc(pAdapter, str);
50180 +
50181 + // prepare feedback
50182 + pRaCfg->length = htons(2);
50183 + pRaCfg->status = htons(0);
50184 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50185 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50186 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50187 +
50188 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50189 + {
50190 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_TX_POWER1\n"));
50191 + Status = -EFAULT;
50192 + }
50193 + else
50194 + {
50195 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_TX_POWER1 is done !\n"));
50196 + }
50197 + }
50198 + break;
50199 +
50200 + case RACFG_CMD_ATE_SET_FREQ_OFFSET:
50201 + {
50202 + SHORT value = 0;
50203 + UCHAR str[LEN_OF_ARG];
50204 +
50205 + NdisZeroMemory(str, LEN_OF_ARG);
50206 +
50207 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_FREQ_OFFSET\n"));
50208 +
50209 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50210 + value = ntohs(value);
50211 + sprintf((PCHAR)str, "%d", value);
50212 + Set_ATE_TX_FREQOFFSET_Proc(pAdapter, str);
50213 +
50214 + // prepare feedback
50215 + pRaCfg->length = htons(2);
50216 + pRaCfg->status = htons(0);
50217 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50218 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50219 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50220 +
50221 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50222 + {
50223 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_FREQ_OFFSET\n"));
50224 + Status = -EFAULT;
50225 + }
50226 + else
50227 + {
50228 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_FREQ_OFFSET is done !\n"));
50229 + }
50230 + }
50231 + break;
50232 +
50233 + case RACFG_CMD_ATE_GET_STATISTICS:
50234 + {
50235 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_GET_STATISTICS\n"));
50236 +
50237 + memcpy_exl(pAdapter, &pRaCfg->data[0], (UCHAR *)&pAdapter->ate.TxDoneCount, 4);
50238 + memcpy_exl(pAdapter, &pRaCfg->data[4], (UCHAR *)&pAdapter->WlanCounters.RetryCount.u.LowPart, 4);
50239 + memcpy_exl(pAdapter, &pRaCfg->data[8], (UCHAR *)&pAdapter->WlanCounters.FailedCount.u.LowPart, 4);
50240 + memcpy_exl(pAdapter, &pRaCfg->data[12], (UCHAR *)&pAdapter->WlanCounters.RTSSuccessCount.u.LowPart, 4);
50241 + memcpy_exl(pAdapter, &pRaCfg->data[16], (UCHAR *)&pAdapter->WlanCounters.RTSFailureCount.u.LowPart, 4);
50242 + memcpy_exl(pAdapter, &pRaCfg->data[20], (UCHAR *)&pAdapter->WlanCounters.ReceivedFragmentCount.QuadPart, 4);
50243 + memcpy_exl(pAdapter, &pRaCfg->data[24], (UCHAR *)&pAdapter->WlanCounters.FCSErrorCount.u.LowPart, 4);
50244 + memcpy_exl(pAdapter, &pRaCfg->data[28], (UCHAR *)&pAdapter->Counters8023.RxNoBuffer, 4);
50245 + memcpy_exl(pAdapter, &pRaCfg->data[32], (UCHAR *)&pAdapter->WlanCounters.FrameDuplicateCount.u.LowPart, 4);
50246 + memcpy_exl(pAdapter, &pRaCfg->data[36], (UCHAR *)&pAdapter->RalinkCounters.OneSecFalseCCACnt, 4);
50247 +
50248 + if (pAdapter->ate.RxAntennaSel == 0)
50249 + {
50250 + INT32 RSSI0 = 0;
50251 + INT32 RSSI1 = 0;
50252 + INT32 RSSI2 = 0;
50253 +
50254 + RSSI0 = (INT32)(pAdapter->ate.LastRssi0 - pAdapter->BbpRssiToDbmDelta);
50255 + RSSI1 = (INT32)(pAdapter->ate.LastRssi1 - pAdapter->BbpRssiToDbmDelta);
50256 + RSSI2 = (INT32)(pAdapter->ate.LastRssi2 - pAdapter->BbpRssiToDbmDelta);
50257 + memcpy_exl(pAdapter, &pRaCfg->data[40], (UCHAR *)&RSSI0, 4);
50258 + memcpy_exl(pAdapter, &pRaCfg->data[44], (UCHAR *)&RSSI1, 4);
50259 + memcpy_exl(pAdapter, &pRaCfg->data[48], (UCHAR *)&RSSI2, 4);
50260 + pRaCfg->length = htons(2+52);
50261 + }
50262 + else
50263 + {
50264 + INT32 RSSI0 = 0;
50265 +
50266 + RSSI0 = (INT32)(pAdapter->ate.LastRssi0 - pAdapter->BbpRssiToDbmDelta);
50267 + memcpy_exl(pAdapter, &pRaCfg->data[40], (UCHAR *)&RSSI0, 4);
50268 + pRaCfg->length = htons(2+44);
50269 + }
50270 + pRaCfg->status = htons(0);
50271 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50272 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50273 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50274 +
50275 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50276 + {
50277 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_GET_STATISTICS\n"));
50278 + Status = -EFAULT;
50279 + }
50280 + else
50281 + {
50282 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_GET_STATISTICS is done !\n"));
50283 + }
50284 + }
50285 + break;
50286 +
50287 + case RACFG_CMD_ATE_RESET_COUNTER:
50288 + {
50289 + SHORT value = 1;
50290 + UCHAR str[LEN_OF_ARG];
50291 +
50292 + NdisZeroMemory(str, LEN_OF_ARG);
50293 +
50294 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_RESET_COUNTER\n"));
50295 +
50296 + sprintf((PCHAR)str, "%d", value);
50297 + Set_ResetStatCounter_Proc(pAdapter, str);
50298 +
50299 + pAdapter->ate.TxDoneCount = 0;
50300 +
50301 + pRaCfg->length = htons(2);
50302 + pRaCfg->status = htons(0);
50303 +
50304 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50305 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50306 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50307 +
50308 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50309 + {
50310 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_RESET_COUNTER\n"));
50311 + Status = -EFAULT;
50312 + }
50313 + else
50314 + {
50315 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_RESET_COUNTER is done !\n"));
50316 + }
50317 + }
50318 +
50319 + break;
50320 +
50321 + case RACFG_CMD_ATE_SEL_TX_ANTENNA:
50322 + {
50323 + SHORT value = 0;
50324 + UCHAR str[LEN_OF_ARG];
50325 +
50326 + NdisZeroMemory(str, LEN_OF_ARG);
50327 +
50328 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SEL_TX_ANTENNA\n"));
50329 +
50330 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50331 + value = ntohs(value);
50332 + sprintf((PCHAR)str, "%d", value);
50333 + Set_ATE_TX_Antenna_Proc(pAdapter, str);
50334 +
50335 + // prepare feedback
50336 + pRaCfg->length = htons(2);
50337 + pRaCfg->status = htons(0);
50338 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50339 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50340 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50341 +
50342 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50343 + {
50344 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SEL_TX_ANTENNA\n"));
50345 + Status = -EFAULT;
50346 + }
50347 + else
50348 + {
50349 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SEL_TX_ANTENNA is done !\n"));
50350 + }
50351 + }
50352 + break;
50353 +
50354 + case RACFG_CMD_ATE_SEL_RX_ANTENNA:
50355 + {
50356 + SHORT value = 0;
50357 + UCHAR str[LEN_OF_ARG];
50358 +
50359 + NdisZeroMemory(str, LEN_OF_ARG);
50360 +
50361 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SEL_RX_ANTENNA\n"));
50362 +
50363 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50364 + value = ntohs(value);
50365 + sprintf((PCHAR)str, "%d", value);
50366 + Set_ATE_RX_Antenna_Proc(pAdapter, str);
50367 +
50368 + // prepare feedback
50369 + pRaCfg->length = htons(2);
50370 + pRaCfg->status = htons(0);
50371 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50372 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50373 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50374 +
50375 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50376 + {
50377 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SEL_RX_ANTENNA\n"));
50378 + Status = -EFAULT;
50379 + }
50380 + else
50381 + {
50382 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SEL_RX_ANTENNA is done !\n"));
50383 + }
50384 + }
50385 + break;
50386 +
50387 + case RACFG_CMD_ATE_SET_PREAMBLE:
50388 + {
50389 + SHORT value = 0;
50390 + UCHAR str[LEN_OF_ARG];
50391 +
50392 + NdisZeroMemory(str, LEN_OF_ARG);
50393 +
50394 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_PREAMBLE\n"));
50395 +
50396 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50397 + value = ntohs(value);
50398 + sprintf((PCHAR)str, "%d", value);
50399 + Set_ATE_TX_MODE_Proc(pAdapter, str);
50400 +
50401 + // prepare feedback
50402 + pRaCfg->length = htons(2);
50403 + pRaCfg->status = htons(0);
50404 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50405 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50406 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50407 +
50408 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50409 + {
50410 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_PREAMBLE\n"));
50411 + Status = -EFAULT;
50412 + }
50413 + else
50414 + {
50415 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_PREAMBLE is done !\n"));
50416 + }
50417 + }
50418 + break;
50419 +
50420 + case RACFG_CMD_ATE_SET_CHANNEL:
50421 + {
50422 + SHORT value = 0;
50423 + UCHAR str[LEN_OF_ARG];
50424 +
50425 + NdisZeroMemory(str, LEN_OF_ARG);
50426 +
50427 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_CHANNEL\n"));
50428 +
50429 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50430 + value = ntohs(value);
50431 + sprintf((PCHAR)str, "%d", value);
50432 + Set_ATE_CHANNEL_Proc(pAdapter, str);
50433 +
50434 + // prepare feedback
50435 + pRaCfg->length = htons(2);
50436 + pRaCfg->status = htons(0);
50437 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50438 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50439 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50440 +
50441 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50442 + {
50443 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_CHANNEL\n"));
50444 + Status = -EFAULT;
50445 + }
50446 + else
50447 + {
50448 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_CHANNEL is done !\n"));
50449 + }
50450 + }
50451 + break;
50452 +
50453 + case RACFG_CMD_ATE_SET_ADDR1:
50454 + {
50455 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_ADDR1\n"));
50456 +
50457 + // Addr is an array of UCHAR,
50458 + // so no need to perform endian swap.
50459 + memcpy(pAdapter->ate.Addr1, (PUCHAR)(pRaCfg->data - 2), MAC_ADDR_LEN);
50460 +
50461 + // prepare feedback
50462 + pRaCfg->length = htons(2);
50463 + pRaCfg->status = htons(0);
50464 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50465 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50466 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50467 +
50468 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50469 + {
50470 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_ADDR1\n"));
50471 + Status = -EFAULT;
50472 + }
50473 + else
50474 + {
50475 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_ADDR1 is done !\n (ADDR1 = %2X:%2X:%2X:%2X:%2X:%2X)\n", pAdapter->ate.Addr1[0],
50476 + pAdapter->ate.Addr1[1], pAdapter->ate.Addr1[2], pAdapter->ate.Addr1[3], pAdapter->ate.Addr1[4], pAdapter->ate.Addr1[5]));
50477 + }
50478 + }
50479 + break;
50480 +
50481 + case RACFG_CMD_ATE_SET_ADDR2:
50482 + {
50483 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_ADDR2\n"));
50484 +
50485 + // Addr is an array of UCHAR,
50486 + // so no need to perform endian swap.
50487 + memcpy(pAdapter->ate.Addr2, (PUCHAR)(pRaCfg->data - 2), MAC_ADDR_LEN);
50488 +
50489 + // prepare feedback
50490 + pRaCfg->length = htons(2);
50491 + pRaCfg->status = htons(0);
50492 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50493 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50494 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50495 +
50496 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50497 + {
50498 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_ADDR2\n"));
50499 + Status = -EFAULT;
50500 + }
50501 + else
50502 + {
50503 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_ADDR2 is done !\n (ADDR2 = %2X:%2X:%2X:%2X:%2X:%2X)\n", pAdapter->ate.Addr2[0],
50504 + pAdapter->ate.Addr2[1], pAdapter->ate.Addr2[2], pAdapter->ate.Addr2[3], pAdapter->ate.Addr2[4], pAdapter->ate.Addr2[5]));
50505 + }
50506 + }
50507 + break;
50508 +
50509 + case RACFG_CMD_ATE_SET_ADDR3:
50510 + {
50511 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_ADDR3\n"));
50512 +
50513 + // Addr is an array of UCHAR,
50514 + // so no need to perform endian swap.
50515 + memcpy(pAdapter->ate.Addr3, (PUCHAR)(pRaCfg->data - 2), MAC_ADDR_LEN);
50516 +
50517 + // prepare feedback
50518 + pRaCfg->length = htons(2);
50519 + pRaCfg->status = htons(0);
50520 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50521 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50522 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50523 +
50524 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50525 + {
50526 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_ADDR3\n"));
50527 + Status = -EFAULT;
50528 + }
50529 + else
50530 + {
50531 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_ADDR3 is done !\n (ADDR3 = %2X:%2X:%2X:%2X:%2X:%2X)\n", pAdapter->ate.Addr3[0],
50532 + pAdapter->ate.Addr3[1], pAdapter->ate.Addr3[2], pAdapter->ate.Addr3[3], pAdapter->ate.Addr3[4], pAdapter->ate.Addr3[5]));
50533 + }
50534 + }
50535 + break;
50536 +
50537 + case RACFG_CMD_ATE_SET_RATE:
50538 + {
50539 + SHORT value = 0;
50540 + UCHAR str[LEN_OF_ARG];
50541 +
50542 + NdisZeroMemory(str, LEN_OF_ARG);
50543 +
50544 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_RATE\n"));
50545 +
50546 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50547 + value = ntohs(value);
50548 + sprintf((PCHAR)str, "%d", value);
50549 + Set_ATE_TX_MCS_Proc(pAdapter, str);
50550 +
50551 + // prepare feedback
50552 + pRaCfg->length = htons(2);
50553 + pRaCfg->status = htons(0);
50554 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50555 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50556 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50557 +
50558 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50559 + {
50560 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_RATE\n"));
50561 + Status = -EFAULT;
50562 + }
50563 + else
50564 + {
50565 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_RATE is done !\n"));
50566 + }
50567 + }
50568 + break;
50569 +
50570 + case RACFG_CMD_ATE_SET_TX_FRAME_LEN:
50571 + {
50572 + SHORT value = 0;
50573 + UCHAR str[LEN_OF_ARG];
50574 +
50575 + NdisZeroMemory(str, LEN_OF_ARG);
50576 +
50577 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_TX_FRAME_LEN\n"));
50578 +
50579 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50580 + value = ntohs(value);
50581 + sprintf((PCHAR)str, "%d", value);
50582 + Set_ATE_TX_LENGTH_Proc(pAdapter, str);
50583 +
50584 + // prepare feedback
50585 + pRaCfg->length = htons(2);
50586 + pRaCfg->status = htons(0);
50587 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50588 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50589 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50590 +
50591 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50592 + {
50593 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_TX_FRAME_LEN\n"));
50594 + Status = -EFAULT;
50595 + }
50596 + else
50597 + {
50598 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_TX_FRAME_LEN is done !\n"));
50599 + }
50600 + }
50601 + break;
50602 +
50603 + case RACFG_CMD_ATE_SET_TX_FRAME_COUNT:
50604 + {
50605 + USHORT value = 0;
50606 + UCHAR str[LEN_OF_ARG];
50607 +
50608 + NdisZeroMemory(str, LEN_OF_ARG);
50609 +
50610 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_ATE_SET_TX_FRAME_COUNT\n"));
50611 +
50612 + memcpy((PUCHAR)&value, (PUCHAR)&(pRaCfg->status), 2);
50613 + value = ntohs(value);
50614 +#ifdef RT2860
50615 + /* TX_FRAME_COUNT == 0 means tx infinitely */
50616 + if (value == 0)
50617 + {
50618 + /* Use TxCount = 0xFFFFFFFF to approximate the infinity. */
50619 + pAdapter->ate.TxCount = 0xFFFFFFFF;
50620 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Set_ATE_TX_COUNT_Proc (TxCount = %d)\n", pAdapter->ate.TxCount));
50621 + ATEDBGPRINT(RT_DEBUG_TRACE, ("Ralink: Set_ATE_TX_COUNT_Proc Success\n"));
50622 +
50623 +
50624 + }
50625 + else
50626 +#endif // RT2860 //
50627 + {
50628 + sprintf((PCHAR)str, "%d", value);
50629 + Set_ATE_TX_COUNT_Proc(pAdapter, str);
50630 + }
50631 +
50632 + // prepare feedback
50633 + pRaCfg->length = htons(2);
50634 + pRaCfg->status = htons(0);
50635 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50636 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50637 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50638 +
50639 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50640 + {
50641 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_ATE_SET_TX_FRAME_COUNT\n"));
50642 + Status = -EFAULT;
50643 + }
50644 + else
50645 + {
50646 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_ATE_SET_TX_FRAME_COUNT is done !\n"));
50647 + }
50648 + }
50649 + break;
50650 +
50651 + case RACFG_CMD_ATE_START_RX_FRAME:
50652 + {
50653 + ATEDBGPRINT(RT_DEBUG_TRACE,("RACFG_CMD_RX_START\n"));
50654 +
50655 + Set_ATE_Proc(pAdapter, "RXFRAME");
50656 +
50657 + // prepare feedback
50658 + pRaCfg->length = htons(2);
50659 + pRaCfg->status = htons(0);
50660 + wrq->u.data.length = sizeof(pRaCfg->magic_no) + sizeof(pRaCfg->command_type)
50661 + + sizeof(pRaCfg->command_id) + sizeof(pRaCfg->length)
50662 + + sizeof(pRaCfg->sequence) + ntohs(pRaCfg->length);
50663 +
50664 + if (copy_to_user(wrq->u.data.pointer, pRaCfg, wrq->u.data.length))
50665 + {
50666 + ATEDBGPRINT(RT_DEBUG_ERROR, ("copy_to_user() fail in case RACFG_CMD_RX_START\n"));
50667 + Status = -EFAULT;
50668 + }
50669 + else
50670 + {
50671 + ATEDBGPRINT(RT_DEBUG_TRACE, ("RACFG_CMD_RX_START is done !\n"));
50672 + }
50673 + }
50674 + break;
50675 + default:
50676 + break;
50677 + }
50678 + ASSERT(pRaCfg != NULL);
50679 + if (pRaCfg != NULL)
50680 + {
50681 + kfree(pRaCfg);
50682 + }
50683 + return;
50684 +}
50685 +
50686 +VOID BubbleSort(INT32 n, INT32 a[])
50687 +{
50688 + INT32 k, j, temp;
50689 +
50690 + for (k = n-1; k>0; k--)
50691 + {
50692 + for (j = 0; j<k; j++)
50693 + {
50694 + if(a[j] > a[j+1])
50695 + {
50696 + temp = a[j];
50697 + a[j]=a[j+1];
50698 + a[j+1]=temp;
50699 + }
50700 + }
50701 + }
50702 +}
50703 +
50704 +VOID CalNoiseLevel(PRTMP_ADAPTER pAd, UCHAR channel, INT32 RSSI[3][10])
50705 +{
50706 + INT32 RSSI0, RSSI1, RSSI2;
50707 + CHAR Rssi0Offset, Rssi1Offset, Rssi2Offset;
50708 + UCHAR BbpR50Rssi0 = 0, BbpR51Rssi1 = 0, BbpR52Rssi2 = 0;
50709 + UCHAR Org_BBP66value = 0, Org_BBP69value = 0, Org_BBP70value = 0, data = 0;
50710 + USHORT LNA_Gain = 0;
50711 + INT32 j = 0;
50712 + UCHAR Org_Channel = pAd->ate.Channel;
50713 + USHORT GainValue = 0, OffsetValue = 0;
50714 +
50715 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R66, &Org_BBP66value);
50716 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R69, &Org_BBP69value);
50717 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R70, &Org_BBP70value);
50718 +
50719 + //**********************************************************************
50720 + // Read the value of LNA gain and Rssi offset
50721 + //**********************************************************************
50722 + RT28xx_EEPROM_READ16(pAd, EEPROM_LNA_OFFSET, GainValue);
50723 +
50724 + // for Noise Level
50725 + if (channel <= 14)
50726 + {
50727 + LNA_Gain = GainValue & 0x00FF;
50728 +
50729 + RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_BG_OFFSET, OffsetValue);
50730 + Rssi0Offset = OffsetValue & 0x00FF;
50731 + Rssi1Offset = (OffsetValue & 0xFF00) >> 8;
50732 + RT28xx_EEPROM_READ16(pAd, (EEPROM_RSSI_BG_OFFSET + 2)/* 0x48 */, OffsetValue);
50733 + Rssi2Offset = OffsetValue & 0x00FF;
50734 + }
50735 + else
50736 + {
50737 + LNA_Gain = (GainValue & 0xFF00) >> 8;
50738 +
50739 + RT28xx_EEPROM_READ16(pAd, EEPROM_RSSI_A_OFFSET, OffsetValue);
50740 + Rssi0Offset = OffsetValue & 0x00FF;
50741 + Rssi1Offset = (OffsetValue & 0xFF00) >> 8;
50742 + RT28xx_EEPROM_READ16(pAd, (EEPROM_RSSI_A_OFFSET + 2)/* 0x4C */, OffsetValue);
50743 + Rssi2Offset = OffsetValue & 0x00FF;
50744 + }
50745 + //**********************************************************************
50746 + {
50747 + pAd->ate.Channel = channel;
50748 + ATEAsicSwitchChannel(pAd);
50749 + mdelay(5);
50750 +
50751 + data = 0x10;
50752 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, data);
50753 + data = 0x40;
50754 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, data);
50755 + data = 0x40;
50756 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, data);
50757 + mdelay(5);
50758 +
50759 + // Start Rx
50760 + pAd->ate.bQARxStart = TRUE;
50761 + Set_ATE_Proc(pAd, "RXFRAME");
50762 +
50763 + mdelay(5);
50764 +
50765 + for (j = 0; j < 10; j++)
50766 + {
50767 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R50, &BbpR50Rssi0);
50768 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R51, &BbpR51Rssi1);
50769 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R52, &BbpR52Rssi2);
50770 +
50771 + mdelay(10);
50772 +
50773 + // Calculate RSSI 0
50774 + if (BbpR50Rssi0 == 0)
50775 + {
50776 + RSSI0 = -100;
50777 + }
50778 + else
50779 + {
50780 + RSSI0 = (INT32)(-12 - BbpR50Rssi0 - LNA_Gain - Rssi0Offset);
50781 + }
50782 + RSSI[0][j] = RSSI0;
50783 +
50784 + if ( pAd->Antenna.field.RxPath >= 2 ) // 2R
50785 + {
50786 + // Calculate RSSI 1
50787 + if (BbpR51Rssi1 == 0)
50788 + {
50789 + RSSI1 = -100;
50790 + }
50791 + else
50792 + {
50793 + RSSI1 = (INT32)(-12 - BbpR51Rssi1 - LNA_Gain - Rssi1Offset);
50794 + }
50795 + RSSI[1][j] = RSSI1;
50796 + }
50797 +
50798 + if ( pAd->Antenna.field.RxPath >= 3 ) // 3R
50799 + {
50800 + // Calculate RSSI 2
50801 + if (BbpR52Rssi2 == 0)
50802 + RSSI2 = -100;
50803 + else
50804 + RSSI2 = (INT32)(-12 - BbpR52Rssi2 - LNA_Gain - Rssi2Offset);
50805 +
50806 + RSSI[2][j] = RSSI2;
50807 + }
50808 + }
50809 +
50810 + // Stop Rx
50811 + Set_ATE_Proc(pAd, "RXSTOP");
50812 +
50813 + mdelay(5);
50814 +
50815 +#if 0// Debug Message................
50816 + ate_print("\n**********************************************************\n");
50817 + ate_print("Noise Level: Channel %d\n", channel);
50818 + ate_print("RSSI0 = %d, %d, %d, %d, %d, %d, %d, %d, %d, %d\n",
50819 + RSSI[0][0], RSSI[0][1], RSSI[0][2],
50820 + RSSI[0][3], RSSI[0][4], RSSI[0][5],
50821 + RSSI[0][6], RSSI[0][7], RSSI[0][8],
50822 + RSSI[0][9]);
50823 + if ( pAd->Antenna.field.RxPath >= 2 ) // 2R
50824 + {
50825 + ate_print("RSSI1 = %d, %d, %d, %d, %d, %d, %d, %d, %d, %d\n",
50826 + RSSI[1][0], RSSI[1][1], RSSI[1][2],
50827 + RSSI[1][3], RSSI[1][4], RSSI[1][5],
50828 + RSSI[1][6], RSSI[1][7], RSSI[1][8],
50829 + RSSI[1][9]);
50830 + }
50831 + if ( pAd->Antenna.field.RxPath >= 3 ) // 3R
50832 + {
50833 + ate_print("RSSI2 = %d, %d, %d, %d, %d, %d, %d, %d, %d, %d\n",
50834 + RSSI[2][0], RSSI[2][1], RSSI[2][2],
50835 + RSSI[2][3], RSSI[2][4], RSSI[2][5],
50836 + RSSI[2][6], RSSI[2][7], RSSI[2][8],
50837 + RSSI[2][9]);
50838 + }
50839 +#endif // 0 //
50840 + BubbleSort(10, RSSI[0]); // 1R
50841 +
50842 + if ( pAd->Antenna.field.RxPath >= 2 ) // 2R
50843 + {
50844 + BubbleSort(10, RSSI[1]);
50845 + }
50846 +
50847 + if ( pAd->Antenna.field.RxPath >= 3 ) // 3R
50848 + {
50849 + BubbleSort(10, RSSI[2]);
50850 + }
50851 +
50852 +#if 0// Debug Message................
50853 + ate_print("\nAfter Sorting....Channel %d\n", channel);
50854 + ate_print("RSSI0 = %d, %d, %d, %d, %d, %d, %d, %d, %d, %d\n",
50855 + RSSI[0][0], RSSI[0][1], RSSI[0][2],
50856 + RSSI[0][3], RSSI[0][4], RSSI[0][5],
50857 + RSSI[0][6], RSSI[0][7], RSSI[0][8],
50858 + RSSI[0][9]);
50859 + if ( pAd->Antenna.field.RxPath >= 2 ) // 2R
50860 + {
50861 + ate_print("RSSI1 = %d, %d, %d, %d, %d, %d, %d, %d, %d, %d\n",
50862 + RSSI[1][0], RSSI[1][1], RSSI[1][2],
50863 + RSSI[1][3], RSSI[1][4], RSSI[1][5],
50864 + RSSI[1][6], RSSI[1][7], RSSI[1][8],
50865 + RSSI[1][9]);
50866 + }
50867 + if ( pAd->Antenna.field.RxPath >= 3 ) // 3R
50868 + {
50869 + ate_print("RSSI2 = %d, %d, %d, %d, %d, %d, %d, %d, %d, %d\n",
50870 + RSSI[2][0], RSSI[2][1], RSSI[2][2],
50871 + RSSI[2][3], RSSI[2][4], RSSI[2][5],
50872 + RSSI[2][6], RSSI[2][7], RSSI[2][8],
50873 + RSSI[2][9]);
50874 + }
50875 + ate_print("**********************************************************\n");
50876 +#endif // 0 //
50877 + }
50878 +
50879 + pAd->ate.Channel = Org_Channel;
50880 + ATEAsicSwitchChannel(pAd);
50881 +
50882 + // Restore original value
50883 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R66, Org_BBP66value);
50884 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, Org_BBP69value);
50885 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, Org_BBP70value);
50886 +
50887 + return;
50888 +}
50889 +
50890 +BOOLEAN SyncTxRxConfig(PRTMP_ADAPTER pAd, USHORT offset, UCHAR value)
50891 +{
50892 + UCHAR tmp = 0, bbp_data = 0;
50893 +
50894 + if (ATE_ON(pAd))
50895 + {
50896 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, offset, &bbp_data);
50897 + }
50898 + else
50899 + {
50900 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, offset, &bbp_data);
50901 + }
50902 +
50903 + /* confirm again */
50904 + ASSERT(bbp_data == value);
50905 +
50906 + switch(offset)
50907 + {
50908 + case BBP_R1:
50909 + /* Need to sync. tx configuration with legacy ATE. */
50910 + tmp = (bbp_data & ((1 << 4) | (1 << 3))/* 0x18 */) >> 3;
50911 + switch(tmp)
50912 + {
50913 + /* The BBP R1 bit[4:3] = 2 :: Both DACs will be used by QA. */
50914 + case 2:
50915 + /* All */
50916 + pAd->ate.TxAntennaSel = 0;
50917 + break;
50918 + /* The BBP R1 bit[4:3] = 0 :: DAC 0 will be used by QA. */
50919 + case 0:
50920 + /* Antenna one */
50921 + pAd->ate.TxAntennaSel = 1;
50922 + break;
50923 + /* The BBP R1 bit[4:3] = 1 :: DAC 1 will be used by QA. */
50924 + case 1:
50925 + /* Antenna two */
50926 + pAd->ate.TxAntennaSel = 2;
50927 + break;
50928 + default:
50929 + DBGPRINT(RT_DEBUG_TRACE, ("%s -- Sth. wrong! : return FALSE; \n", __FUNCTION__));
50930 + return FALSE;
50931 + }
50932 + break;/* case BBP_R1 */
50933 +
50934 + case BBP_R3:
50935 + /* Need to sync. rx configuration with legacy ATE. */
50936 + tmp = (bbp_data & ((1 << 1) | (1 << 0))/* 0x03 */);
50937 + switch(tmp)
50938 + {
50939 + /* The BBP R3 bit[1:0] = 3 :: All ADCs will be used by QA. */
50940 + case 3:
50941 + /* All */
50942 + pAd->ate.RxAntennaSel = 0;
50943 + break;
50944 + /* The BBP R3 bit[1:0] = 0 :: ADC 0 will be used by QA, */
50945 + /* unless the BBP R3 bit[4:3] = 2 */
50946 + case 0:
50947 + /* Antenna one */
50948 + pAd->ate.RxAntennaSel = 1;
50949 + tmp = ((bbp_data & ((1 << 4) | (1 << 3))/* 0x03 */) >> 3);
50950 + if (tmp == 2)// 3R
50951 + {
50952 + /* Default : All ADCs will be used by QA */
50953 + pAd->ate.RxAntennaSel = 0;
50954 + }
50955 + break;
50956 + /* The BBP R3 bit[1:0] = 1 :: ADC 1 will be used by QA. */
50957 + case 1:
50958 + /* Antenna two */
50959 + pAd->ate.RxAntennaSel = 2;
50960 + break;
50961 + /* The BBP R3 bit[1:0] = 2 :: ADC 2 will be used by QA. */
50962 + case 2:
50963 + /* Antenna three */
50964 + pAd->ate.RxAntennaSel = 3;
50965 + break;
50966 + default:
50967 + DBGPRINT(RT_DEBUG_ERROR, ("%s -- Impossible! : return FALSE; \n", __FUNCTION__));
50968 + return FALSE;
50969 + }
50970 + break;/* case BBP_R3 */
50971 +
50972 + default:
50973 + DBGPRINT(RT_DEBUG_ERROR, ("%s -- Sth. wrong! : return FALSE; \n", __FUNCTION__));
50974 + return FALSE;
50975 +
50976 + }
50977 + return TRUE;
50978 +}
50979 +
50980 +static VOID memcpy_exl(PRTMP_ADAPTER pAd, UCHAR *dst, UCHAR *src, ULONG len)
50981 +{
50982 + ULONG i, Value = 0;
50983 + ULONG *pDst, *pSrc;
50984 + UCHAR *p8;
50985 +
50986 + p8 = src;
50987 + pDst = (ULONG *) dst;
50988 + pSrc = (ULONG *) src;
50989 +
50990 + for (i = 0 ; i < (len/4); i++)
50991 + {
50992 + /* For alignment issue, we need a variable "Value". */
50993 + memmove(&Value, pSrc, 4);
50994 + Value = htonl(Value);
50995 + memmove(pDst, &Value, 4);
50996 + pDst++;
50997 + pSrc++;
50998 + }
50999 + if ((len % 4) != 0)
51000 + {
51001 + /* wish that it will never reach here */
51002 + memmove(&Value, pSrc, (len % 4));
51003 + Value = htonl(Value);
51004 + memmove(pDst, &Value, (len % 4));
51005 + }
51006 +}
51007 +
51008 +static VOID memcpy_exs(PRTMP_ADAPTER pAd, UCHAR *dst, UCHAR *src, ULONG len)
51009 +{
51010 + ULONG i;
51011 + UCHAR *pDst, *pSrc;
51012 +
51013 + pDst = dst;
51014 + pSrc = src;
51015 +
51016 + for (i = 0; i < (len/2); i++)
51017 + {
51018 + memmove(pDst, pSrc, 2);
51019 + *((USHORT *)pDst) = htons(*((USHORT *)pDst));
51020 + pDst+=2;
51021 + pSrc+=2;
51022 + }
51023 +
51024 + if ((len % 2) != 0)
51025 + {
51026 + memmove(pDst, pSrc, 1);
51027 + }
51028 +}
51029 +
51030 +static VOID RTMP_IO_READ_BULK(PRTMP_ADAPTER pAd, UCHAR *dst, UCHAR *src, UINT32 len)
51031 +{
51032 + UINT32 i, Value;
51033 + UINT32 *pDst, *pSrc;
51034 +
51035 + pDst = (UINT32 *) dst;
51036 + pSrc = (UINT32 *) src;
51037 +
51038 + for (i = 0 ; i < (len/4); i++)
51039 + {
51040 + RTMP_IO_READ32(pAd, (ULONG)pSrc, &Value);
51041 + Value = htonl(Value);
51042 + memmove(pDst, &Value, 4);
51043 + pDst++;
51044 + pSrc++;
51045 + }
51046 + return;
51047 +}
51048 +
51049 +// TODO:
51050 +#if 0
51051 +/* These work only when RALINK_ATE is defined */
51052 +INT Set_TxStart_Proc(
51053 + IN PRTMP_ADAPTER pAd,
51054 + IN PUCHAR arg)
51055 +{
51056 + ULONG value = simple_strtol(arg, 0, 10);
51057 + UCHAR buffer[26] = {0x88, 0x02, 0x2c, 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x00, 0x55, 0x44, 0x33, 0x22, 0x11, 0xc0, 0x22, 0x00, 0x00};
51058 + POS_COOKIE pObj;
51059 +
51060 + if (pAd->ate.TxStatus != 0)
51061 + return FALSE;
51062 +
51063 + pAd->ate.TxInfo = 0x04000000;
51064 + bzero(&pAd->ate.TxWI, sizeof(TXWI_STRUC));
51065 + pAd->ate.TxWI.PHYMODE = 0;// MODE_CCK
51066 + pAd->ate.TxWI.MPDUtotalByteCount = 1226;
51067 + pAd->ate.TxWI.MCS = 3;
51068 + //pAd->ate.Mode = ATE_START;
51069 + pAd->ate.Mode |= ATE_TXFRAME;
51070 + pAd->ate.TxCount = value;
51071 + pAd->ate.QID = 0;
51072 + pAd->ate.HLen = 26;
51073 + pAd->ate.PLen = 0;
51074 + pAd->ate.DLen = 1200;
51075 + memcpy(pAd->ate.Header, buffer, 26);
51076 + pAd->ate.bQATxStart = TRUE;
51077 + //pObj = (POS_COOKIE) pAd->OS_Cookie;
51078 + //tasklet_hi_schedule(&pObj->AteTxTask);
51079 + return TRUE;
51080 +}
51081 +#endif /* end of #if 0 */
51082 +
51083 +INT Set_TxStop_Proc(
51084 + IN PRTMP_ADAPTER pAd,
51085 + IN PUCHAR arg)
51086 +{
51087 + ATEDBGPRINT(RT_DEBUG_TRACE,("Set_TxStop_Proc\n"));
51088 +
51089 + if (Set_ATE_Proc(pAd, "TXSTOP"))
51090 + {
51091 + return TRUE;
51092 +}
51093 + else
51094 + {
51095 + return FALSE;
51096 + }
51097 +}
51098 +
51099 +INT Set_RxStop_Proc(
51100 + IN PRTMP_ADAPTER pAd,
51101 + IN PUCHAR arg)
51102 +{
51103 + ATEDBGPRINT(RT_DEBUG_TRACE,("Set_RxStop_Proc\n"));
51104 +
51105 + if (Set_ATE_Proc(pAd, "RXSTOP"))
51106 + {
51107 + return TRUE;
51108 +}
51109 + else
51110 + {
51111 + return FALSE;
51112 + }
51113 +}
51114 +
51115 +#if 0
51116 +INT Set_EEWrite_Proc(
51117 + IN PRTMP_ADAPTER pAd,
51118 + IN PUCHAR arg)
51119 +{
51120 + USHORT offset = 0, value;
51121 + PUCHAR p2 = arg;
51122 +
51123 + while((*p2 != ':') && (*p2 != '\0'))
51124 + {
51125 + p2++;
51126 + }
51127 +
51128 + if (*p2 == ':')
51129 + {
51130 + A2Hex(offset, arg);
51131 + A2Hex(value, p2+ 1);
51132 + }
51133 + else
51134 + {
51135 + A2Hex(value, arg);
51136 + }
51137 +
51138 + if (offset >= EEPROM_SIZE)
51139 + {
51140 + ate_print("Offset can not exceed EEPROM_SIZE( == 0x%04x)\n", EEPROM_SIZE);
51141 + return FALSE;
51142 + }
51143 +
51144 + RTMP_EEPROM_WRITE16(pAd, offset, value);
51145 +
51146 + return TRUE;
51147 +}
51148 +
51149 +INT Set_BBPRead_Proc(
51150 + IN PRTMP_ADAPTER pAd,
51151 + IN PUCHAR arg)
51152 +{
51153 + UCHAR value = 0, offset;
51154 +
51155 + A2Hex(offset, arg);
51156 +
51157 + if (ATE_ON(pAd))
51158 + {
51159 + ATE_BBP_IO_READ8_BY_REG_ID(pAd, offset, &value);
51160 + }
51161 + else
51162 + {
51163 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, offset, &value);
51164 + }
51165 +
51166 + ate_print("%x\n", value);
51167 +
51168 + return TRUE;
51169 +}
51170 +
51171 +
51172 +INT Set_BBPWrite_Proc(
51173 + IN PRTMP_ADAPTER pAd,
51174 + IN PUCHAR arg)
51175 +{
51176 + USHORT offset = 0;
51177 + PUCHAR p2 = arg;
51178 + UCHAR value;
51179 +
51180 + while((*p2 != ':') && (*p2 != '\0'))
51181 + {
51182 + p2++;
51183 + }
51184 +
51185 + if (*p2 == ':')
51186 + {
51187 + A2Hex(offset, arg);
51188 + A2Hex(value, p2+ 1);
51189 + }
51190 + else
51191 + {
51192 + A2Hex(value, arg);
51193 + }
51194 +
51195 + if (ATE_ON(pAd))
51196 + {
51197 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAd, offset, value);
51198 + }
51199 + else
51200 + {
51201 + RTNP_BBP_IO_WRITE8_BY_REG_ID(pAd, offset, value);
51202 + }
51203 +
51204 + return TRUE;
51205 +}
51206 +
51207 +INT Set_RFWrite_Proc(
51208 + IN PRTMP_ADAPTER pAd,
51209 + IN PUCHAR arg)
51210 +{
51211 + PUCHAR p2, p3, p4;
51212 + ULONG R1, R2, R3, R4;
51213 +
51214 + p2 = arg;
51215 +
51216 + while((*p2 != ':') && (*p2 != '\0'))
51217 + {
51218 + p2++;
51219 + }
51220 +
51221 + if (*p2 != ':')
51222 + return FALSE;
51223 +
51224 + p3 = p2 + 1;
51225 +
51226 + while((*p3 != ':') && (*p3 != '\0'))
51227 + {
51228 + p3++;
51229 + }
51230 +
51231 + if (*p3 != ':')
51232 + return FALSE;
51233 +
51234 + p4 = p3 + 1;
51235 +
51236 + while((*p4 != ':') && (*p4 != '\0'))
51237 + {
51238 + p4++;
51239 + }
51240 +
51241 + if (*p4 != ':')
51242 + return FALSE;
51243 +
51244 +
51245 + A2Hex(R1, arg);
51246 + A2Hex(R2, p2 + 1);
51247 + A2Hex(R3, p3 + 1);
51248 + A2Hex(R4, p4 + 1);
51249 +
51250 + RTMP_RF_IO_WRITE32(pAd, R1);
51251 + RTMP_RF_IO_WRITE32(pAd, R2);
51252 + RTMP_RF_IO_WRITE32(pAd, R3);
51253 + RTMP_RF_IO_WRITE32(pAd, R4);
51254 +
51255 + return TRUE;
51256 +}
51257 +#endif // end of #if 0 //
51258 +#endif // RALINK_28xx_QA //
51259 +
51260 +#endif // RALINK_ATE //
51261 +
51262 --- /dev/null
51263 +++ b/drivers/staging/rt2860/rt_ate.h
51264 @@ -0,0 +1,353 @@
51265 +/*
51266 + *************************************************************************
51267 + * Ralink Tech Inc.
51268 + * 5F., No.36, Taiyuan St., Jhubei City,
51269 + * Hsinchu County 302,
51270 + * Taiwan, R.O.C.
51271 + *
51272 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
51273 + *
51274 + * This program is free software; you can redistribute it and/or modify *
51275 + * it under the terms of the GNU General Public License as published by *
51276 + * the Free Software Foundation; either version 2 of the License, or *
51277 + * (at your option) any later version. *
51278 + * *
51279 + * This program is distributed in the hope that it will be useful, *
51280 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
51281 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
51282 + * GNU General Public License for more details. *
51283 + * *
51284 + * You should have received a copy of the GNU General Public License *
51285 + * along with this program; if not, write to the *
51286 + * Free Software Foundation, Inc., *
51287 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
51288 + * *
51289 + *************************************************************************
51290 + */
51291 +
51292 +#ifndef __ATE_H__
51293 +#define __ATE_H__
51294 +
51295 +#ifndef UCOS
51296 +#define ate_print printk
51297 +#define ATEDBGPRINT DBGPRINT
51298 +#ifdef RT2860
51299 +#define EEPROM_SIZE 0x200
51300 +#ifdef CONFIG_STA_SUPPORT
51301 +#define EEPROM_BIN_FILE_NAME "/etc/Wireless/RT2860STA/e2p.bin"
51302 +#endif // CONFIG_STA_SUPPORT //
51303 +#endif // RT2860 //
51304 +
51305 +#else // !UCOS //
51306 +#define fATE_LOAD_EEPROM 0x0C43
51307 +#ifdef CONFIG_PRINTK
51308 +extern INT ConsoleResponse(IN PUCHAR buff);
51309 +extern int (*remote_display)(char *);
51310 +extern void puts (const char *s);
51311 +
51312 +/* specificly defined to redirect and show ate-related messages to host. */
51313 +/* Try to define ate_print as a macro. */
51314 +#define ate_print(fmt, args...) \
51315 +do{ int (*org_remote_display)(char *) = NULL; \
51316 + org_remote_display = remote_display;\
51317 + /* Save original "remote_display" */\
51318 + remote_display = (int (*)(char *))ConsoleResponse; \
51319 + printk(fmt, ## args); \
51320 + /* Restore the remote_display function pointer */ \
51321 + remote_display = org_remote_display; }while(0)
51322 +
51323 +#define ATEDBGPRINT(Level, Fmt) \
51324 +{ \
51325 + if ((Level) <= RTDebugLevel) \
51326 + { \
51327 + ate_print Fmt; \
51328 + } \
51329 +}
51330 +#endif // CONFIG_PRINTK //
51331 +#endif // !UCOS //
51332 +
51333 +#define ATE_ON(_p) (((_p)->ate.Mode) != ATE_STOP)
51334 +
51335 +/* RT2880_iNIC will define "RT2860". */
51336 +#ifdef RT2860
51337 +#define ATE_BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) \
51338 +{ \
51339 + BBP_CSR_CFG_STRUC BbpCsr; \
51340 + int i, k; \
51341 + for (i=0; i<MAX_BUSY_COUNT; i++) \
51342 + { \
51343 + RTMP_IO_READ32(_A, BBP_CSR_CFG, &BbpCsr.word); \
51344 + if (BbpCsr.field.Busy == BUSY) \
51345 + { \
51346 + continue; \
51347 + } \
51348 + BbpCsr.word = 0; \
51349 + BbpCsr.field.fRead = 1; \
51350 + BbpCsr.field.BBP_RW_MODE = 1; \
51351 + BbpCsr.field.Busy = 1; \
51352 + BbpCsr.field.RegNum = _I; \
51353 + RTMP_IO_WRITE32(_A, BBP_CSR_CFG, BbpCsr.word); \
51354 + for (k=0; k<MAX_BUSY_COUNT; k++) \
51355 + { \
51356 + RTMP_IO_READ32(_A, BBP_CSR_CFG, &BbpCsr.word); \
51357 + if (BbpCsr.field.Busy == IDLE) \
51358 + break; \
51359 + } \
51360 + if ((BbpCsr.field.Busy == IDLE) && \
51361 + (BbpCsr.field.RegNum == _I)) \
51362 + { \
51363 + *(_pV) = (UCHAR)BbpCsr.field.Value; \
51364 + break; \
51365 + } \
51366 + } \
51367 + if (BbpCsr.field.Busy == BUSY) \
51368 + { \
51369 + ATEDBGPRINT(RT_DEBUG_ERROR, ("BBP read R%d fail\n", _I)); \
51370 + *(_pV) = (_A)->BbpWriteLatch[_I]; \
51371 + } \
51372 +}
51373 +
51374 +#define ATE_BBP_IO_WRITE8_BY_REG_ID(_A, _I, _V) \
51375 +{ \
51376 + BBP_CSR_CFG_STRUC BbpCsr; \
51377 + int BusyCnt; \
51378 + for (BusyCnt=0; BusyCnt<MAX_BUSY_COUNT; BusyCnt++) \
51379 + { \
51380 + RTMP_IO_READ32(_A, BBP_CSR_CFG, &BbpCsr.word); \
51381 + if (BbpCsr.field.Busy == BUSY) \
51382 + continue; \
51383 + BbpCsr.word = 0; \
51384 + BbpCsr.field.fRead = 0; \
51385 + BbpCsr.field.BBP_RW_MODE = 1; \
51386 + BbpCsr.field.Busy = 1; \
51387 + BbpCsr.field.Value = _V; \
51388 + BbpCsr.field.RegNum = _I; \
51389 + RTMP_IO_WRITE32(_A, BBP_CSR_CFG, BbpCsr.word); \
51390 + (_A)->BbpWriteLatch[_I] = _V; \
51391 + break; \
51392 + } \
51393 + if (BusyCnt == MAX_BUSY_COUNT) \
51394 + { \
51395 + ATEDBGPRINT(RT_DEBUG_ERROR, ("BBP write R%d fail\n", _I)); \
51396 + } \
51397 +}
51398 +#endif // RT2860 //
51399 +
51400 +/* RT2880_iNIC will define RT2860. */
51401 +#ifdef RT2860
51402 +#define EEPROM_SIZE 0x200
51403 +/* iNIC has its own EEPROM_BIN_FILE_NAME */
51404 +#ifndef UCOS
51405 +#ifdef CONFIG_STA_SUPPORT
51406 +#define EEPROM_BIN_FILE_NAME "/etc/Wireless/RT2860STA/e2p.bin"
51407 +#endif // CONFIG_STA_SUPPORT //
51408 +#endif // !UCOS //
51409 +#endif // RT2860 //
51410 +
51411 +
51412 +
51413 +VOID rt_ee_read_all(
51414 + IN PRTMP_ADAPTER pAd,
51415 + OUT USHORT *Data);
51416 +
51417 +
51418 +VOID rt_ee_write_all(
51419 + IN PRTMP_ADAPTER pAd,
51420 + IN USHORT *Data);
51421 +
51422 +INT Set_ATE_Proc(
51423 + IN PRTMP_ADAPTER pAd,
51424 + IN PUCHAR arg);
51425 +
51426 +INT Set_ATE_DA_Proc(
51427 + IN PRTMP_ADAPTER pAd,
51428 + IN PUCHAR arg);
51429 +
51430 +INT Set_ATE_SA_Proc(
51431 + IN PRTMP_ADAPTER pAd,
51432 + IN PUCHAR arg);
51433 +
51434 +INT Set_ATE_BSSID_Proc(
51435 + IN PRTMP_ADAPTER pAd,
51436 + IN PUCHAR arg);
51437 +
51438 +INT Set_ATE_CHANNEL_Proc(
51439 + IN PRTMP_ADAPTER pAd,
51440 + IN PUCHAR arg);
51441 +
51442 +INT Set_ATE_TX_POWER0_Proc(
51443 + IN PRTMP_ADAPTER pAd,
51444 + IN PUCHAR arg);
51445 +
51446 +INT Set_ATE_TX_POWER1_Proc(
51447 + IN PRTMP_ADAPTER pAd,
51448 + IN PUCHAR arg);
51449 +
51450 +INT Set_ATE_TX_Antenna_Proc(
51451 + IN PRTMP_ADAPTER pAd,
51452 + IN PUCHAR arg);
51453 +
51454 +INT Set_ATE_RX_Antenna_Proc(
51455 + IN PRTMP_ADAPTER pAd,
51456 + IN PUCHAR arg);
51457 +
51458 +INT Set_ATE_TX_FREQOFFSET_Proc(
51459 + IN PRTMP_ADAPTER pAd,
51460 + IN PUCHAR arg);
51461 +
51462 +INT Set_ATE_TX_BW_Proc(
51463 + IN PRTMP_ADAPTER pAd,
51464 + IN PUCHAR arg);
51465 +
51466 +INT Set_ATE_TX_LENGTH_Proc(
51467 + IN PRTMP_ADAPTER pAd,
51468 + IN PUCHAR arg);
51469 +
51470 +INT Set_ATE_TX_COUNT_Proc(
51471 + IN PRTMP_ADAPTER pAd,
51472 + IN PUCHAR arg);
51473 +
51474 +INT Set_ATE_TX_MCS_Proc(
51475 + IN PRTMP_ADAPTER pAd,
51476 + IN PUCHAR arg);
51477 +
51478 +INT Set_ATE_TX_MODE_Proc(
51479 + IN PRTMP_ADAPTER pAd,
51480 + IN PUCHAR arg);
51481 +
51482 +INT Set_ATE_TX_GI_Proc(
51483 + IN PRTMP_ADAPTER pAd,
51484 + IN PUCHAR arg);
51485 +
51486 +
51487 +INT Set_ATE_RX_FER_Proc(
51488 + IN PRTMP_ADAPTER pAd,
51489 + IN PUCHAR arg);
51490 +
51491 +INT Set_ATE_Read_RF_Proc(
51492 + IN PRTMP_ADAPTER pAd,
51493 + IN PUCHAR arg);
51494 +
51495 +INT Set_ATE_Write_RF1_Proc(
51496 + IN PRTMP_ADAPTER pAd,
51497 + IN PUCHAR arg);
51498 +
51499 +INT Set_ATE_Write_RF2_Proc(
51500 + IN PRTMP_ADAPTER pAd,
51501 + IN PUCHAR arg);
51502 +
51503 +INT Set_ATE_Write_RF3_Proc(
51504 + IN PRTMP_ADAPTER pAd,
51505 + IN PUCHAR arg);
51506 +
51507 +INT Set_ATE_Write_RF4_Proc(
51508 + IN PRTMP_ADAPTER pAd,
51509 + IN PUCHAR arg);
51510 +
51511 +INT Set_ATE_Load_E2P_Proc(
51512 + IN PRTMP_ADAPTER pAd,
51513 + IN PUCHAR arg);
51514 +
51515 +INT Set_ATE_Read_E2P_Proc(
51516 + IN PRTMP_ADAPTER pAd,
51517 + IN PUCHAR arg);
51518 +
51519 +INT Set_ATE_Show_Proc(
51520 + IN PRTMP_ADAPTER pAd,
51521 + IN PUCHAR arg);
51522 +
51523 +INT Set_ATE_Help_Proc(
51524 + IN PRTMP_ADAPTER pAd,
51525 + IN PUCHAR arg);
51526 +
51527 +#ifdef RALINK_ATE
51528 +#ifdef RALINK_28xx_QA
51529 +VOID ATE_QA_Statistics(
51530 + IN PRTMP_ADAPTER pAd,
51531 + IN PRXWI_STRUC pRxWI,
51532 + IN PRT28XX_RXD_STRUC p28xxRxD,
51533 + IN PHEADER_802_11 pHeader);
51534 +
51535 +VOID RtmpDoAte(
51536 + IN PRTMP_ADAPTER pAdapter,
51537 + IN struct iwreq *wrq);
51538 +
51539 +VOID BubbleSort(
51540 + IN INT32 n,
51541 + IN INT32 a[]);
51542 +
51543 +VOID CalNoiseLevel(
51544 + IN PRTMP_ADAPTER pAdapter,
51545 + IN UCHAR channel,
51546 + OUT INT32 buffer[3][10]);
51547 +
51548 +BOOLEAN SyncTxRxConfig(
51549 + IN PRTMP_ADAPTER pAdapter,
51550 + IN USHORT offset,
51551 + IN UCHAR value);
51552 +
51553 +#if 0
51554 +INT Set_TxStart_Proc(
51555 + IN PRTMP_ADAPTER pAd,
51556 + IN PUCHAR arg);
51557 +#endif // 0 //
51558 +
51559 +INT Set_TxStop_Proc(
51560 + IN PRTMP_ADAPTER pAd,
51561 + IN PUCHAR arg);
51562 +
51563 +INT Set_RxStop_Proc(
51564 + IN PRTMP_ADAPTER pAd,
51565 + IN PUCHAR arg);
51566 +
51567 +#if 0
51568 +INT Set_EERead_Proc(
51569 + IN PRTMP_ADAPTER pAd,
51570 + IN PUCHAR arg);
51571 +
51572 +INT Set_EEWrite_Proc(
51573 + IN PRTMP_ADAPTER pAd,
51574 + IN PUCHAR arg);
51575 +
51576 +INT Set_BBPRead_Proc(
51577 + IN PRTMP_ADAPTER pAd,
51578 + IN PUCHAR arg);
51579 +
51580 +INT Set_BBPWrite_Proc(
51581 + IN PRTMP_ADAPTER pAd,
51582 + IN PUCHAR arg);
51583 +
51584 +INT Set_RFWrite_Proc(
51585 + IN PRTMP_ADAPTER pAd,
51586 + IN PUCHAR arg);
51587 +#endif // end of #if 0 //
51588 +#endif // RALINK_28xx_QA //
51589 +#endif // RALINK_ATE //
51590 +
51591 +VOID ATEAsicSwitchChannel(
51592 + IN PRTMP_ADAPTER pAd);
51593 +
51594 +VOID ATEAsicAdjustTxPower(
51595 + IN PRTMP_ADAPTER pAd);
51596 +
51597 +VOID ATEDisableAsicProtect(
51598 + IN PRTMP_ADAPTER pAd);
51599 +
51600 +CHAR ATEConvertToRssi(
51601 + IN PRTMP_ADAPTER pAd,
51602 + IN CHAR Rssi,
51603 + IN UCHAR RssiNumber);
51604 +
51605 +VOID ATESampleRssi(
51606 + IN PRTMP_ADAPTER pAd,
51607 + IN PRXWI_STRUC pRxWI);
51608 +
51609 +
51610 +#ifdef CONFIG_STA_SUPPORT
51611 +VOID RTMPStationStop(
51612 + IN PRTMP_ADAPTER pAd);
51613 +
51614 +VOID RTMPStationStart(
51615 + IN PRTMP_ADAPTER pAd);
51616 +#endif // CONFIG_STA_SUPPORT //
51617 +#endif // __ATE_H__ //
51618 --- /dev/null
51619 +++ b/drivers/staging/rt2860/rt_config.h
51620 @@ -0,0 +1,101 @@
51621 +/*
51622 + *************************************************************************
51623 + * Ralink Tech Inc.
51624 + * 5F., No.36, Taiyuan St., Jhubei City,
51625 + * Hsinchu County 302,
51626 + * Taiwan, R.O.C.
51627 + *
51628 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
51629 + *
51630 + * This program is free software; you can redistribute it and/or modify *
51631 + * it under the terms of the GNU General Public License as published by *
51632 + * the Free Software Foundation; either version 2 of the License, or *
51633 + * (at your option) any later version. *
51634 + * *
51635 + * This program is distributed in the hope that it will be useful, *
51636 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
51637 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
51638 + * GNU General Public License for more details. *
51639 + * *
51640 + * You should have received a copy of the GNU General Public License *
51641 + * along with this program; if not, write to the *
51642 + * Free Software Foundation, Inc., *
51643 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
51644 + * *
51645 + *************************************************************************
51646 +
51647 + Module Name:
51648 + rt_config.h
51649 +
51650 + Abstract:
51651 + Central header file to maintain all include files for all NDIS
51652 + miniport driver routines.
51653 +
51654 + Revision History:
51655 + Who When What
51656 + -------- ---------- ----------------------------------------------
51657 + Paul Lin 08-01-2002 created
51658 +
51659 +*/
51660 +#ifndef __RT_CONFIG_H__
51661 +#define __RT_CONFIG_H__
51662 +
51663 +#include "rtmp_type.h"
51664 +#ifdef UCOS
51665 +#include "includes.h"
51666 +#include <stdio.h>
51667 +#include "rt_ucos.h"
51668 +#endif
51669 +
51670 +#ifdef LINUX
51671 +#include "rt_linux.h"
51672 +#endif
51673 +#include "rtmp_def.h"
51674 +#include "rt28xx.h"
51675 +
51676 +#ifdef RT2860
51677 +#include "rt2860.h"
51678 +#endif // RT2860 //
51679 +
51680 +
51681 +#include "oid.h"
51682 +#include "mlme.h"
51683 +#include "wpa.h"
51684 +#include "md5.h"
51685 +#include "rtmp.h"
51686 +#include "ap.h"
51687 +#include "dfs.h"
51688 +#include "chlist.h"
51689 +#include "spectrum.h"
51690 +
51691 +#ifdef LEAP_SUPPORT
51692 +#include "leap.h"
51693 +#endif // LEAP_SUPPORT //
51694 +
51695 +#ifdef BLOCK_NET_IF
51696 +#include "netif_block.h"
51697 +#endif // BLOCK_NET_IF //
51698 +
51699 +#ifdef IGMP_SNOOP_SUPPORT
51700 +#include "igmp_snoop.h"
51701 +#endif // IGMP_SNOOP_SUPPORT //
51702 +
51703 +#ifdef RALINK_ATE
51704 +#include "rt_ate.h"
51705 +#endif // RALINK_ATE //
51706 +
51707 +#ifdef CONFIG_STA_SUPPORT
51708 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
51709 +#ifndef WPA_SUPPLICANT_SUPPORT
51710 +#error "Build for being controlled by NetworkManager or wext, please set HAS_WPA_SUPPLICANT=y and HAS_NATIVE_WPA_SUPPLICANT_SUPPORT=y"
51711 +#endif // WPA_SUPPLICANT_SUPPORT //
51712 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
51713 +
51714 +#endif // CONFIG_STA_SUPPORT //
51715 +
51716 +#ifdef IKANOS_VX_1X0
51717 +#include "vr_ikans.h"
51718 +#endif // IKANOS_VX_1X0 //
51719 +
51720 +#endif // __RT_CONFIG_H__
51721 +
51722 --- /dev/null
51723 +++ b/drivers/staging/rt2860/rt_linux.c
51724 @@ -0,0 +1,1054 @@
51725 +/*
51726 + *************************************************************************
51727 + * Ralink Tech Inc.
51728 + * 5F., No.36, Taiyuan St., Jhubei City,
51729 + * Hsinchu County 302,
51730 + * Taiwan, R.O.C.
51731 + *
51732 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
51733 + *
51734 + * This program is free software; you can redistribute it and/or modify *
51735 + * it under the terms of the GNU General Public License as published by *
51736 + * the Free Software Foundation; either version 2 of the License, or *
51737 + * (at your option) any later version. *
51738 + * *
51739 + * This program is distributed in the hope that it will be useful, *
51740 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
51741 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
51742 + * GNU General Public License for more details. *
51743 + * *
51744 + * You should have received a copy of the GNU General Public License *
51745 + * along with this program; if not, write to the *
51746 + * Free Software Foundation, Inc., *
51747 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
51748 + * *
51749 + *************************************************************************
51750 + */
51751 +
51752 +#include "rt_config.h"
51753 +
51754 +ULONG RTDebugLevel = RT_DEBUG_ERROR;
51755 +
51756 +BUILD_TIMER_FUNCTION(MlmePeriodicExec);
51757 +BUILD_TIMER_FUNCTION(AsicRxAntEvalTimeout);
51758 +BUILD_TIMER_FUNCTION(APSDPeriodicExec);
51759 +BUILD_TIMER_FUNCTION(AsicRfTuningExec);
51760 +
51761 +
51762 +#ifdef CONFIG_STA_SUPPORT
51763 +BUILD_TIMER_FUNCTION(BeaconTimeout);
51764 +BUILD_TIMER_FUNCTION(ScanTimeout);
51765 +BUILD_TIMER_FUNCTION(AuthTimeout);
51766 +BUILD_TIMER_FUNCTION(AssocTimeout);
51767 +BUILD_TIMER_FUNCTION(ReassocTimeout);
51768 +BUILD_TIMER_FUNCTION(DisassocTimeout);
51769 +BUILD_TIMER_FUNCTION(LinkDownExec);
51770 +#ifdef LEAP_SUPPORT
51771 +BUILD_TIMER_FUNCTION(LeapAuthTimeout);
51772 +#endif
51773 +BUILD_TIMER_FUNCTION(StaQuickResponeForRateUpExec);
51774 +BUILD_TIMER_FUNCTION(WpaDisassocApAndBlockAssoc);
51775 +#ifdef RT2860
51776 +BUILD_TIMER_FUNCTION(PsPollWakeExec);
51777 +BUILD_TIMER_FUNCTION(RadioOnExec);
51778 +#endif // RT2860 //
51779 +#ifdef QOS_DLS_SUPPORT
51780 +BUILD_TIMER_FUNCTION(DlsTimeoutAction);
51781 +#endif // QOS_DLS_SUPPORT //
51782 +#endif // CONFIG_STA_SUPPORT //
51783 +
51784 +// for wireless system event message
51785 +char const *pWirelessSysEventText[IW_SYS_EVENT_TYPE_NUM] = {
51786 + // system status event
51787 + "had associated successfully", /* IW_ASSOC_EVENT_FLAG */
51788 + "had disassociated", /* IW_DISASSOC_EVENT_FLAG */
51789 + "had deauthenticated", /* IW_DEAUTH_EVENT_FLAG */
51790 + "had been aged-out and disassociated", /* IW_AGEOUT_EVENT_FLAG */
51791 + "occurred CounterMeasures attack", /* IW_COUNTER_MEASURES_EVENT_FLAG */
51792 + "occurred replay counter different in Key Handshaking", /* IW_REPLAY_COUNTER_DIFF_EVENT_FLAG */
51793 + "occurred RSNIE different in Key Handshaking", /* IW_RSNIE_DIFF_EVENT_FLAG */
51794 + "occurred MIC different in Key Handshaking", /* IW_MIC_DIFF_EVENT_FLAG */
51795 + "occurred ICV error in RX", /* IW_ICV_ERROR_EVENT_FLAG */
51796 + "occurred MIC error in RX", /* IW_MIC_ERROR_EVENT_FLAG */
51797 + "Group Key Handshaking timeout", /* IW_GROUP_HS_TIMEOUT_EVENT_FLAG */
51798 + "Pairwise Key Handshaking timeout", /* IW_PAIRWISE_HS_TIMEOUT_EVENT_FLAG */
51799 + "RSN IE sanity check failure", /* IW_RSNIE_SANITY_FAIL_EVENT_FLAG */
51800 + "set key done in WPA/WPAPSK", /* IW_SET_KEY_DONE_WPA1_EVENT_FLAG */
51801 + "set key done in WPA2/WPA2PSK", /* IW_SET_KEY_DONE_WPA2_EVENT_FLAG */
51802 + "connects with our wireless client", /* IW_STA_LINKUP_EVENT_FLAG */
51803 + "disconnects with our wireless client", /* IW_STA_LINKDOWN_EVENT_FLAG */
51804 + "scan completed" /* IW_SCAN_COMPLETED_EVENT_FLAG */
51805 + "scan terminate!! Busy!! Enqueue fail!!" /* IW_SCAN_ENQUEUE_FAIL_EVENT_FLAG */
51806 + };
51807 +
51808 +// for wireless IDS_spoof_attack event message
51809 +char const *pWirelessSpoofEventText[IW_SPOOF_EVENT_TYPE_NUM] = {
51810 + "detected conflict SSID", /* IW_CONFLICT_SSID_EVENT_FLAG */
51811 + "detected spoofed association response", /* IW_SPOOF_ASSOC_RESP_EVENT_FLAG */
51812 + "detected spoofed reassociation responses", /* IW_SPOOF_REASSOC_RESP_EVENT_FLAG */
51813 + "detected spoofed probe response", /* IW_SPOOF_PROBE_RESP_EVENT_FLAG */
51814 + "detected spoofed beacon", /* IW_SPOOF_BEACON_EVENT_FLAG */
51815 + "detected spoofed disassociation", /* IW_SPOOF_DISASSOC_EVENT_FLAG */
51816 + "detected spoofed authentication", /* IW_SPOOF_AUTH_EVENT_FLAG */
51817 + "detected spoofed deauthentication", /* IW_SPOOF_DEAUTH_EVENT_FLAG */
51818 + "detected spoofed unknown management frame", /* IW_SPOOF_UNKNOWN_MGMT_EVENT_FLAG */
51819 + "detected replay attack" /* IW_REPLAY_ATTACK_EVENT_FLAG */
51820 + };
51821 +
51822 +// for wireless IDS_flooding_attack event message
51823 +char const *pWirelessFloodEventText[IW_FLOOD_EVENT_TYPE_NUM] = {
51824 + "detected authentication flooding", /* IW_FLOOD_AUTH_EVENT_FLAG */
51825 + "detected association request flooding", /* IW_FLOOD_ASSOC_REQ_EVENT_FLAG */
51826 + "detected reassociation request flooding", /* IW_FLOOD_REASSOC_REQ_EVENT_FLAG */
51827 + "detected probe request flooding", /* IW_FLOOD_PROBE_REQ_EVENT_FLAG */
51828 + "detected disassociation flooding", /* IW_FLOOD_DISASSOC_EVENT_FLAG */
51829 + "detected deauthentication flooding", /* IW_FLOOD_DEAUTH_EVENT_FLAG */
51830 + "detected 802.1x eap-request flooding" /* IW_FLOOD_EAP_REQ_EVENT_FLAG */
51831 + };
51832 +
51833 +/* timeout -- ms */
51834 +VOID RTMP_SetPeriodicTimer(
51835 + IN NDIS_MINIPORT_TIMER *pTimer,
51836 + IN unsigned long timeout)
51837 +{
51838 + timeout = ((timeout*HZ) / 1000);
51839 + pTimer->expires = jiffies + timeout;
51840 + add_timer(pTimer);
51841 +}
51842 +
51843 +/* convert NdisMInitializeTimer --> RTMP_OS_Init_Timer */
51844 +VOID RTMP_OS_Init_Timer(
51845 + IN PRTMP_ADAPTER pAd,
51846 + IN NDIS_MINIPORT_TIMER *pTimer,
51847 + IN TIMER_FUNCTION function,
51848 + IN PVOID data)
51849 +{
51850 + init_timer(pTimer);
51851 + pTimer->data = (unsigned long)data;
51852 + pTimer->function = function;
51853 +}
51854 +
51855 +
51856 +VOID RTMP_OS_Add_Timer(
51857 + IN NDIS_MINIPORT_TIMER *pTimer,
51858 + IN unsigned long timeout)
51859 +{
51860 + if (timer_pending(pTimer))
51861 + return;
51862 +
51863 + timeout = ((timeout*HZ) / 1000);
51864 + pTimer->expires = jiffies + timeout;
51865 + add_timer(pTimer);
51866 +}
51867 +
51868 +VOID RTMP_OS_Mod_Timer(
51869 + IN NDIS_MINIPORT_TIMER *pTimer,
51870 + IN unsigned long timeout)
51871 +{
51872 + timeout = ((timeout*HZ) / 1000);
51873 + mod_timer(pTimer, jiffies + timeout);
51874 +}
51875 +
51876 +VOID RTMP_OS_Del_Timer(
51877 + IN NDIS_MINIPORT_TIMER *pTimer,
51878 + OUT BOOLEAN *pCancelled)
51879 +{
51880 + if (timer_pending(pTimer))
51881 + {
51882 + *pCancelled = del_timer_sync(pTimer);
51883 + }
51884 + else
51885 + {
51886 + *pCancelled = TRUE;
51887 + }
51888 +
51889 +}
51890 +
51891 +VOID RTMP_OS_Release_Packet(
51892 + IN PRTMP_ADAPTER pAd,
51893 + IN PQUEUE_ENTRY pEntry)
51894 +{
51895 + //RTMPFreeNdisPacket(pAd, (struct sk_buff *)pEntry);
51896 +}
51897 +
51898 +// Unify all delay routine by using udelay
51899 +VOID RTMPusecDelay(
51900 + IN ULONG usec)
51901 +{
51902 + ULONG i;
51903 +
51904 + for (i = 0; i < (usec / 50); i++)
51905 + udelay(50);
51906 +
51907 + if (usec % 50)
51908 + udelay(usec % 50);
51909 +}
51910 +
51911 +void RTMP_GetCurrentSystemTime(LARGE_INTEGER *time)
51912 +{
51913 + time->u.LowPart = jiffies;
51914 +}
51915 +
51916 +// pAd MUST allow to be NULL
51917 +NDIS_STATUS os_alloc_mem(
51918 + IN PRTMP_ADAPTER pAd,
51919 + OUT PUCHAR *mem,
51920 + IN ULONG size)
51921 +{
51922 + *mem = (PUCHAR) kmalloc(size, GFP_ATOMIC);
51923 + if (*mem)
51924 + return (NDIS_STATUS_SUCCESS);
51925 + else
51926 + return (NDIS_STATUS_FAILURE);
51927 +}
51928 +
51929 +// pAd MUST allow to be NULL
51930 +NDIS_STATUS os_free_mem(
51931 + IN PRTMP_ADAPTER pAd,
51932 + IN PUCHAR mem)
51933 +{
51934 +
51935 + ASSERT(mem);
51936 + kfree(mem);
51937 + return (NDIS_STATUS_SUCCESS);
51938 +}
51939 +
51940 +
51941 +PNDIS_PACKET RTMP_AllocateFragPacketBuffer(
51942 + IN PRTMP_ADAPTER pAd,
51943 + IN ULONG Length)
51944 +{
51945 + struct sk_buff *pkt;
51946 +
51947 + pkt = dev_alloc_skb(Length);
51948 +
51949 + if (pkt == NULL)
51950 + {
51951 + DBGPRINT(RT_DEBUG_ERROR, ("can't allocate frag rx %ld size packet\n",Length));
51952 + }
51953 +
51954 + if (pkt)
51955 + {
51956 + RTMP_SET_PACKET_SOURCE(OSPKT_TO_RTPKT(pkt), PKTSRC_NDIS);
51957 + }
51958 +
51959 + return (PNDIS_PACKET) pkt;
51960 +}
51961 +
51962 +
51963 +PNDIS_PACKET RTMP_AllocateTxPacketBuffer(
51964 + IN PRTMP_ADAPTER pAd,
51965 + IN ULONG Length,
51966 + IN BOOLEAN Cached,
51967 + OUT PVOID *VirtualAddress)
51968 +{
51969 + struct sk_buff *pkt;
51970 +
51971 + pkt = dev_alloc_skb(Length);
51972 +
51973 + if (pkt == NULL)
51974 + {
51975 + DBGPRINT(RT_DEBUG_ERROR, ("can't allocate tx %ld size packet\n",Length));
51976 + }
51977 +
51978 + if (pkt)
51979 + {
51980 + RTMP_SET_PACKET_SOURCE(OSPKT_TO_RTPKT(pkt), PKTSRC_NDIS);
51981 + *VirtualAddress = (PVOID) pkt->data;
51982 + }
51983 + else
51984 + {
51985 + *VirtualAddress = (PVOID) NULL;
51986 + }
51987 +
51988 + return (PNDIS_PACKET) pkt;
51989 +}
51990 +
51991 +
51992 +VOID build_tx_packet(
51993 + IN PRTMP_ADAPTER pAd,
51994 + IN PNDIS_PACKET pPacket,
51995 + IN PUCHAR pFrame,
51996 + IN ULONG FrameLen)
51997 +{
51998 +
51999 + struct sk_buff *pTxPkt;
52000 +
52001 + ASSERT(pPacket);
52002 + pTxPkt = RTPKT_TO_OSPKT(pPacket);
52003 +
52004 + NdisMoveMemory(skb_put(pTxPkt, FrameLen), pFrame, FrameLen);
52005 +}
52006 +
52007 +VOID RTMPFreeAdapter(
52008 + IN PRTMP_ADAPTER pAd)
52009 +{
52010 + POS_COOKIE os_cookie;
52011 + int index;
52012 +
52013 + os_cookie=(POS_COOKIE)pAd->OS_Cookie;
52014 +
52015 + kfree(pAd->BeaconBuf);
52016 +
52017 +
52018 + NdisFreeSpinLock(&pAd->MgmtRingLock);
52019 +
52020 +#ifdef RT2860
52021 + NdisFreeSpinLock(&pAd->RxRingLock);
52022 +#endif // RT2860 //
52023 +
52024 + for (index =0 ; index < NUM_OF_TX_RING; index++)
52025 + {
52026 + NdisFreeSpinLock(&pAd->TxSwQueueLock[index]);
52027 + NdisFreeSpinLock(&pAd->DeQueueLock[index]);
52028 + pAd->DeQueueRunning[index] = FALSE;
52029 + }
52030 +
52031 + NdisFreeSpinLock(&pAd->irq_lock);
52032 +
52033 + vfree(pAd); // pci_free_consistent(os_cookie->pci_dev,sizeof(RTMP_ADAPTER),pAd,os_cookie->pAd_pa);
52034 + kfree(os_cookie);
52035 +}
52036 +
52037 +BOOLEAN OS_Need_Clone_Packet(void)
52038 +{
52039 + return (FALSE);
52040 +}
52041 +
52042 +
52043 +
52044 +/*
52045 + ========================================================================
52046 +
52047 + Routine Description:
52048 + clone an input NDIS PACKET to another one. The new internally created NDIS PACKET
52049 + must have only one NDIS BUFFER
52050 + return - byte copied. 0 means can't create NDIS PACKET
52051 + NOTE: internally created NDIS_PACKET should be destroyed by RTMPFreeNdisPacket
52052 +
52053 + Arguments:
52054 + pAd Pointer to our adapter
52055 + pInsAMSDUHdr EWC A-MSDU format has extra 14-bytes header. if TRUE, insert this 14-byte hdr in front of MSDU.
52056 + *pSrcTotalLen return total packet length. This lenght is calculated with 802.3 format packet.
52057 +
52058 + Return Value:
52059 + NDIS_STATUS_SUCCESS
52060 + NDIS_STATUS_FAILURE
52061 +
52062 + Note:
52063 +
52064 + ========================================================================
52065 +*/
52066 +NDIS_STATUS RTMPCloneNdisPacket(
52067 + IN PRTMP_ADAPTER pAd,
52068 + IN BOOLEAN pInsAMSDUHdr,
52069 + IN PNDIS_PACKET pInPacket,
52070 + OUT PNDIS_PACKET *ppOutPacket)
52071 +{
52072 +
52073 + struct sk_buff *pkt;
52074 +
52075 + ASSERT(pInPacket);
52076 + ASSERT(ppOutPacket);
52077 +
52078 + // 1. Allocate a packet
52079 + pkt = dev_alloc_skb(2048);
52080 +
52081 + if (pkt == NULL)
52082 + {
52083 + return NDIS_STATUS_FAILURE;
52084 + }
52085 +
52086 + skb_put(pkt, GET_OS_PKT_LEN(pInPacket));
52087 + NdisMoveMemory(pkt->data, GET_OS_PKT_DATAPTR(pInPacket), GET_OS_PKT_LEN(pInPacket));
52088 + *ppOutPacket = OSPKT_TO_RTPKT(pkt);
52089 +
52090 +
52091 + RTMP_SET_PACKET_SOURCE(OSPKT_TO_RTPKT(pkt), PKTSRC_NDIS);
52092 +
52093 + printk("###Clone###\n");
52094 +
52095 + return NDIS_STATUS_SUCCESS;
52096 +}
52097 +
52098 +
52099 +// the allocated NDIS PACKET must be freed via RTMPFreeNdisPacket()
52100 +NDIS_STATUS RTMPAllocateNdisPacket(
52101 + IN PRTMP_ADAPTER pAd,
52102 + OUT PNDIS_PACKET *ppPacket,
52103 + IN PUCHAR pHeader,
52104 + IN UINT HeaderLen,
52105 + IN PUCHAR pData,
52106 + IN UINT DataLen)
52107 +{
52108 + PNDIS_PACKET pPacket;
52109 + ASSERT(pData);
52110 + ASSERT(DataLen);
52111 +
52112 + // 1. Allocate a packet
52113 + pPacket = (PNDIS_PACKET *) dev_alloc_skb(HeaderLen + DataLen + TXPADDING_SIZE);
52114 + if (pPacket == NULL)
52115 + {
52116 + *ppPacket = NULL;
52117 +#ifdef DEBUG
52118 + printk("RTMPAllocateNdisPacket Fail\n\n");
52119 +#endif
52120 + return NDIS_STATUS_FAILURE;
52121 + }
52122 +
52123 + // 2. clone the frame content
52124 + if (HeaderLen > 0)
52125 + NdisMoveMemory(GET_OS_PKT_DATAPTR(pPacket), pHeader, HeaderLen);
52126 + if (DataLen > 0)
52127 + NdisMoveMemory(GET_OS_PKT_DATAPTR(pPacket) + HeaderLen, pData, DataLen);
52128 +
52129 + // 3. update length of packet
52130 + skb_put(GET_OS_PKT_TYPE(pPacket), HeaderLen+DataLen);
52131 +
52132 + RTMP_SET_PACKET_SOURCE(pPacket, PKTSRC_NDIS);
52133 +// printk("%s : pPacket = %p, len = %d\n", __FUNCTION__, pPacket, GET_OS_PKT_LEN(pPacket));
52134 + *ppPacket = pPacket;
52135 + return NDIS_STATUS_SUCCESS;
52136 +}
52137 +
52138 +/*
52139 + ========================================================================
52140 + Description:
52141 + This routine frees a miniport internally allocated NDIS_PACKET and its
52142 + corresponding NDIS_BUFFER and allocated memory.
52143 + ========================================================================
52144 +*/
52145 +VOID RTMPFreeNdisPacket(
52146 + IN PRTMP_ADAPTER pAd,
52147 + IN PNDIS_PACKET pPacket)
52148 +{
52149 + dev_kfree_skb_any(RTPKT_TO_OSPKT(pPacket));
52150 +}
52151 +
52152 +
52153 +// IRQL = DISPATCH_LEVEL
52154 +// NOTE: we do have an assumption here, that Byte0 and Byte1 always reasid at the same
52155 +// scatter gather buffer
52156 +NDIS_STATUS Sniff2BytesFromNdisBuffer(
52157 + IN PNDIS_BUFFER pFirstBuffer,
52158 + IN UCHAR DesiredOffset,
52159 + OUT PUCHAR pByte0,
52160 + OUT PUCHAR pByte1)
52161 +{
52162 + *pByte0 = *(PUCHAR)(pFirstBuffer + DesiredOffset);
52163 + *pByte1 = *(PUCHAR)(pFirstBuffer + DesiredOffset + 1);
52164 +
52165 + return NDIS_STATUS_SUCCESS;
52166 +}
52167 +
52168 +
52169 +void RTMP_QueryPacketInfo(
52170 + IN PNDIS_PACKET pPacket,
52171 + OUT PACKET_INFO *pPacketInfo,
52172 + OUT PUCHAR *pSrcBufVA,
52173 + OUT UINT *pSrcBufLen)
52174 +{
52175 + pPacketInfo->BufferCount = 1;
52176 + pPacketInfo->pFirstBuffer = GET_OS_PKT_DATAPTR(pPacket);
52177 + pPacketInfo->PhysicalBufferCount = 1;
52178 + pPacketInfo->TotalPacketLength = GET_OS_PKT_LEN(pPacket);
52179 +
52180 + *pSrcBufVA = GET_OS_PKT_DATAPTR(pPacket);
52181 + *pSrcBufLen = GET_OS_PKT_LEN(pPacket);
52182 +}
52183 +
52184 +void RTMP_QueryNextPacketInfo(
52185 + IN PNDIS_PACKET *ppPacket,
52186 + OUT PACKET_INFO *pPacketInfo,
52187 + OUT PUCHAR *pSrcBufVA,
52188 + OUT UINT *pSrcBufLen)
52189 +{
52190 + PNDIS_PACKET pPacket = NULL;
52191 +
52192 + if (*ppPacket)
52193 + pPacket = GET_OS_PKT_NEXT(*ppPacket);
52194 +
52195 + if (pPacket)
52196 + {
52197 + pPacketInfo->BufferCount = 1;
52198 + pPacketInfo->pFirstBuffer = GET_OS_PKT_DATAPTR(pPacket);
52199 + pPacketInfo->PhysicalBufferCount = 1;
52200 + pPacketInfo->TotalPacketLength = GET_OS_PKT_LEN(pPacket);
52201 +
52202 + *pSrcBufVA = GET_OS_PKT_DATAPTR(pPacket);
52203 + *pSrcBufLen = GET_OS_PKT_LEN(pPacket);
52204 + *ppPacket = GET_OS_PKT_NEXT(pPacket);
52205 + }
52206 + else
52207 + {
52208 + pPacketInfo->BufferCount = 0;
52209 + pPacketInfo->pFirstBuffer = NULL;
52210 + pPacketInfo->PhysicalBufferCount = 0;
52211 + pPacketInfo->TotalPacketLength = 0;
52212 +
52213 + *pSrcBufVA = NULL;
52214 + *pSrcBufLen = 0;
52215 + *ppPacket = NULL;
52216 + }
52217 +}
52218 +
52219 +// not yet support MBSS
52220 +PNET_DEV get_netdev_from_bssid(
52221 + IN PRTMP_ADAPTER pAd,
52222 + IN UCHAR FromWhichBSSID)
52223 +{
52224 + PNET_DEV dev_p = NULL;
52225 +
52226 +#ifdef CONFIG_STA_SUPPORT
52227 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
52228 + {
52229 + dev_p = pAd->net_dev;
52230 + }
52231 +#endif // CONFIG_STA_SUPPORT //
52232 +
52233 + ASSERT(dev_p);
52234 + return dev_p; /* return one of MBSS */
52235 +}
52236 +
52237 +PNDIS_PACKET DuplicatePacket(
52238 + IN PRTMP_ADAPTER pAd,
52239 + IN PNDIS_PACKET pPacket,
52240 + IN UCHAR FromWhichBSSID)
52241 +{
52242 + struct sk_buff *skb;
52243 + PNDIS_PACKET pRetPacket = NULL;
52244 + USHORT DataSize;
52245 + UCHAR *pData;
52246 +
52247 + DataSize = (USHORT) GET_OS_PKT_LEN(pPacket);
52248 + pData = (PUCHAR) GET_OS_PKT_DATAPTR(pPacket);
52249 +
52250 +
52251 + skb = skb_clone(RTPKT_TO_OSPKT(pPacket), MEM_ALLOC_FLAG);
52252 + if (skb)
52253 + {
52254 + skb->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
52255 + pRetPacket = OSPKT_TO_RTPKT(skb);
52256 + }
52257 +
52258 + return pRetPacket;
52259 +
52260 +}
52261 +
52262 +PNDIS_PACKET duplicate_pkt(
52263 + IN PRTMP_ADAPTER pAd,
52264 + IN PUCHAR pHeader802_3,
52265 + IN UINT HdrLen,
52266 + IN PUCHAR pData,
52267 + IN ULONG DataSize,
52268 + IN UCHAR FromWhichBSSID)
52269 +{
52270 + struct sk_buff *skb;
52271 + PNDIS_PACKET pPacket = NULL;
52272 +
52273 +
52274 + if ((skb = __dev_alloc_skb(HdrLen + DataSize + 2, MEM_ALLOC_FLAG)) != NULL)
52275 + {
52276 + skb_reserve(skb, 2);
52277 + NdisMoveMemory(skb->tail, pHeader802_3, HdrLen);
52278 + skb_put(skb, HdrLen);
52279 + NdisMoveMemory(skb->tail, pData, DataSize);
52280 + skb_put(skb, DataSize);
52281 + skb->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
52282 + pPacket = OSPKT_TO_RTPKT(skb);
52283 + }
52284 +
52285 + return pPacket;
52286 +}
52287 +
52288 +
52289 +#define TKIP_TX_MIC_SIZE 8
52290 +PNDIS_PACKET duplicate_pkt_with_TKIP_MIC(
52291 + IN PRTMP_ADAPTER pAd,
52292 + IN PNDIS_PACKET pPacket)
52293 +{
52294 + struct sk_buff *skb, *newskb;
52295 +
52296 +
52297 + skb = RTPKT_TO_OSPKT(pPacket);
52298 + if (skb_tailroom(skb) < TKIP_TX_MIC_SIZE)
52299 + {
52300 + // alloc a new skb and copy the packet
52301 + newskb = skb_copy_expand(skb, skb_headroom(skb), TKIP_TX_MIC_SIZE, GFP_ATOMIC);
52302 + dev_kfree_skb_any(skb);
52303 + if (newskb == NULL)
52304 + {
52305 + DBGPRINT(RT_DEBUG_ERROR, ("Extend Tx.MIC for packet failed!, dropping packet!\n"));
52306 + return NULL;
52307 + }
52308 + skb = newskb;
52309 + }
52310 +
52311 + return OSPKT_TO_RTPKT(skb);
52312 +}
52313 +
52314 +
52315 +
52316 +
52317 +PNDIS_PACKET ClonePacket(
52318 + IN PRTMP_ADAPTER pAd,
52319 + IN PNDIS_PACKET pPacket,
52320 + IN PUCHAR pData,
52321 + IN ULONG DataSize)
52322 +{
52323 + struct sk_buff *pRxPkt;
52324 + struct sk_buff *pClonedPkt;
52325 +
52326 + ASSERT(pPacket);
52327 + pRxPkt = RTPKT_TO_OSPKT(pPacket);
52328 +
52329 + // clone the packet
52330 + pClonedPkt = skb_clone(pRxPkt, MEM_ALLOC_FLAG);
52331 +
52332 + if (pClonedPkt)
52333 + {
52334 + // set the correct dataptr and data len
52335 + pClonedPkt->dev = pRxPkt->dev;
52336 + pClonedPkt->data = pData;
52337 + pClonedPkt->len = DataSize;
52338 + pClonedPkt->tail = pClonedPkt->data + pClonedPkt->len;
52339 + ASSERT(DataSize < 1530);
52340 + }
52341 + return pClonedPkt;
52342 +}
52343 +
52344 +//
52345 +// change OS packet DataPtr and DataLen
52346 +//
52347 +void update_os_packet_info(
52348 + IN PRTMP_ADAPTER pAd,
52349 + IN RX_BLK *pRxBlk,
52350 + IN UCHAR FromWhichBSSID)
52351 +{
52352 + struct sk_buff *pOSPkt;
52353 +
52354 + ASSERT(pRxBlk->pRxPacket);
52355 + pOSPkt = RTPKT_TO_OSPKT(pRxBlk->pRxPacket);
52356 +
52357 + pOSPkt->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
52358 + pOSPkt->data = pRxBlk->pData;
52359 + pOSPkt->len = pRxBlk->DataSize;
52360 + pOSPkt->tail = pOSPkt->data + pOSPkt->len;
52361 +}
52362 +
52363 +
52364 +void wlan_802_11_to_802_3_packet(
52365 + IN PRTMP_ADAPTER pAd,
52366 + IN RX_BLK *pRxBlk,
52367 + IN PUCHAR pHeader802_3,
52368 + IN UCHAR FromWhichBSSID)
52369 +{
52370 + struct sk_buff *pOSPkt;
52371 +
52372 + ASSERT(pRxBlk->pRxPacket);
52373 + ASSERT(pHeader802_3);
52374 +
52375 + pOSPkt = RTPKT_TO_OSPKT(pRxBlk->pRxPacket);
52376 +
52377 + pOSPkt->dev = get_netdev_from_bssid(pAd, FromWhichBSSID);
52378 + pOSPkt->data = pRxBlk->pData;
52379 + pOSPkt->len = pRxBlk->DataSize;
52380 + pOSPkt->tail = pOSPkt->data + pOSPkt->len;
52381 +
52382 + //
52383 + // copy 802.3 header
52384 + //
52385 + //
52386 +
52387 +#ifdef CONFIG_STA_SUPPORT
52388 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
52389 + NdisMoveMemory(skb_push(pOSPkt, LENGTH_802_3), pHeader802_3, LENGTH_802_3);
52390 +#endif // CONFIG_STA_SUPPORT //
52391 + }
52392 +
52393 +
52394 +
52395 +void announce_802_3_packet(
52396 + IN PRTMP_ADAPTER pAd,
52397 + IN PNDIS_PACKET pPacket)
52398 +{
52399 +
52400 + struct sk_buff *pRxPkt;
52401 +
52402 + ASSERT(pPacket);
52403 +
52404 + pRxPkt = RTPKT_TO_OSPKT(pPacket);
52405 +
52406 + /* Push up the protocol stack */
52407 +#ifdef IKANOS_VX_1X0
52408 + IKANOS_DataFrameRx(pAd, pRxPkt->dev, pRxPkt, pRxPkt->len);
52409 +#else
52410 + pRxPkt->protocol = eth_type_trans(pRxPkt, pRxPkt->dev);
52411 +
52412 + netif_rx(pRxPkt);
52413 +#endif // IKANOS_VX_1X0 //
52414 +}
52415 +
52416 +
52417 +PRTMP_SCATTER_GATHER_LIST
52418 +rt_get_sg_list_from_packet(PNDIS_PACKET pPacket, RTMP_SCATTER_GATHER_LIST *sg)
52419 +{
52420 + sg->NumberOfElements = 1;
52421 + sg->Elements[0].Address = GET_OS_PKT_DATAPTR(pPacket);
52422 + sg->Elements[0].Length = GET_OS_PKT_LEN(pPacket);
52423 + return (sg);
52424 +}
52425 +
52426 +void hex_dump(char *str, unsigned char *pSrcBufVA, unsigned int SrcBufLen)
52427 +{
52428 + unsigned char *pt;
52429 + int x;
52430 +
52431 + if (RTDebugLevel < RT_DEBUG_TRACE)
52432 + return;
52433 +
52434 + pt = pSrcBufVA;
52435 + printk("%s: %p, len = %d\n",str, pSrcBufVA, SrcBufLen);
52436 + for (x=0; x<SrcBufLen; x++)
52437 + {
52438 + if (x % 16 == 0)
52439 + printk("0x%04x : ", x);
52440 + printk("%02x ", ((unsigned char)pt[x]));
52441 + if (x%16 == 15) printk("\n");
52442 + }
52443 + printk("\n");
52444 +}
52445 +
52446 +/*
52447 + ========================================================================
52448 +
52449 + Routine Description:
52450 + Send log message through wireless event
52451 +
52452 + Support standard iw_event with IWEVCUSTOM. It is used below.
52453 +
52454 + iwreq_data.data.flags is used to store event_flag that is defined by user.
52455 + iwreq_data.data.length is the length of the event log.
52456 +
52457 + The format of the event log is composed of the entry's MAC address and
52458 + the desired log message (refer to pWirelessEventText).
52459 +
52460 + ex: 11:22:33:44:55:66 has associated successfully
52461 +
52462 + p.s. The requirement of Wireless Extension is v15 or newer.
52463 +
52464 + ========================================================================
52465 +*/
52466 +VOID RTMPSendWirelessEvent(
52467 + IN PRTMP_ADAPTER pAd,
52468 + IN USHORT Event_flag,
52469 + IN PUCHAR pAddr,
52470 + IN UCHAR BssIdx,
52471 + IN CHAR Rssi)
52472 +{
52473 +#if WIRELESS_EXT >= 15
52474 +
52475 + union iwreq_data wrqu;
52476 + PUCHAR pBuf = NULL, pBufPtr = NULL;
52477 + USHORT event, type, BufLen;
52478 + UCHAR event_table_len = 0;
52479 +
52480 + type = Event_flag & 0xFF00;
52481 + event = Event_flag & 0x00FF;
52482 +
52483 + switch (type)
52484 + {
52485 + case IW_SYS_EVENT_FLAG_START:
52486 + event_table_len = IW_SYS_EVENT_TYPE_NUM;
52487 + break;
52488 +
52489 + case IW_SPOOF_EVENT_FLAG_START:
52490 + event_table_len = IW_SPOOF_EVENT_TYPE_NUM;
52491 + break;
52492 +
52493 + case IW_FLOOD_EVENT_FLAG_START:
52494 + event_table_len = IW_FLOOD_EVENT_TYPE_NUM;
52495 + break;
52496 + }
52497 +
52498 + if (event_table_len == 0)
52499 + {
52500 + DBGPRINT(RT_DEBUG_ERROR, ("%s : The type(%0x02x) is not valid.\n", __FUNCTION__, type));
52501 + return;
52502 + }
52503 +
52504 + if (event >= event_table_len)
52505 + {
52506 + DBGPRINT(RT_DEBUG_ERROR, ("%s : The event(%0x02x) is not valid.\n", __FUNCTION__, event));
52507 + return;
52508 + }
52509 +
52510 + //Allocate memory and copy the msg.
52511 + if((pBuf = kmalloc(IW_CUSTOM_MAX_LEN, GFP_ATOMIC)) != NULL)
52512 + {
52513 + //Prepare the payload
52514 + memset(pBuf, 0, IW_CUSTOM_MAX_LEN);
52515 +
52516 + pBufPtr = pBuf;
52517 +
52518 + if (pAddr)
52519 + pBufPtr += sprintf(pBufPtr, "(RT2860) STA(%02x:%02x:%02x:%02x:%02x:%02x) ", PRINT_MAC(pAddr));
52520 + else if (BssIdx < MAX_MBSSID_NUM)
52521 + pBufPtr += sprintf(pBufPtr, "(RT2860) BSS(ra%d) ", BssIdx);
52522 + else
52523 + pBufPtr += sprintf(pBufPtr, "(RT2860) ");
52524 +
52525 + if (type == IW_SYS_EVENT_FLAG_START)
52526 + pBufPtr += sprintf(pBufPtr, "%s", pWirelessSysEventText[event]);
52527 + else if (type == IW_SPOOF_EVENT_FLAG_START)
52528 + pBufPtr += sprintf(pBufPtr, "%s (RSSI=%d)", pWirelessSpoofEventText[event], Rssi);
52529 + else if (type == IW_FLOOD_EVENT_FLAG_START)
52530 + pBufPtr += sprintf(pBufPtr, "%s", pWirelessFloodEventText[event]);
52531 + else
52532 + pBufPtr += sprintf(pBufPtr, "%s", "unknown event");
52533 +
52534 + pBufPtr[pBufPtr - pBuf] = '\0';
52535 + BufLen = pBufPtr - pBuf;
52536 +
52537 + memset(&wrqu, 0, sizeof(wrqu));
52538 + wrqu.data.flags = Event_flag;
52539 + wrqu.data.length = BufLen;
52540 +
52541 + //send wireless event
52542 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, pBuf);
52543 +
52544 + //DBGPRINT(RT_DEBUG_TRACE, ("%s : %s\n", __FUNCTION__, pBuf));
52545 +
52546 + kfree(pBuf);
52547 + }
52548 + else
52549 + DBGPRINT(RT_DEBUG_ERROR, ("%s : Can't allocate memory for wireless event.\n", __FUNCTION__));
52550 +#else
52551 + DBGPRINT(RT_DEBUG_ERROR, ("%s : The Wireless Extension MUST be v15 or newer.\n", __FUNCTION__));
52552 +#endif /* WIRELESS_EXT >= 15 */
52553 +}
52554 +
52555 +
52556 +#ifdef CONFIG_STA_SUPPORT
52557 +void send_monitor_packets(
52558 + IN PRTMP_ADAPTER pAd,
52559 + IN RX_BLK *pRxBlk)
52560 +{
52561 + struct sk_buff *pOSPkt;
52562 + wlan_ng_prism2_header *ph;
52563 + int rate_index = 0;
52564 + USHORT header_len = 0;
52565 + UCHAR temp_header[40] = {0};
52566 +
52567 + u_int32_t ralinkrate[256] = {2,4,11,22, 12,18,24,36,48,72,96, 108, 109, 110, 111, 112, 13, 26, 39, 52,78,104, 117, 130, 26, 52, 78,104, 156, 208, 234, 260, 27, 54,81,108,162, 216, 243, 270, // Last 38
52568 + 54, 108, 162, 216, 324, 432, 486, 540, 14, 29, 43, 57, 87, 115, 130, 144, 29, 59,87,115, 173, 230,260, 288, 30, 60,90,120,180,240,270,300,60,120,180,240,360,480,540,600, 0,1,2,3,4,5,6,7,8,9,10,
52569 + 11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80};
52570 +
52571 +
52572 + ASSERT(pRxBlk->pRxPacket);
52573 + if (pRxBlk->DataSize < 10)
52574 + {
52575 + DBGPRINT(RT_DEBUG_ERROR, ("%s : Size is too small! (%d)\n", __FUNCTION__, pRxBlk->DataSize));
52576 + goto err_free_sk_buff;
52577 + }
52578 +
52579 + if (pRxBlk->DataSize + sizeof(wlan_ng_prism2_header) > RX_BUFFER_AGGRESIZE)
52580 + {
52581 + DBGPRINT(RT_DEBUG_ERROR, ("%s : Size is too large! (%d)\n", __FUNCTION__, pRxBlk->DataSize + sizeof(wlan_ng_prism2_header)));
52582 + goto err_free_sk_buff;
52583 + }
52584 +
52585 + pOSPkt = RTPKT_TO_OSPKT(pRxBlk->pRxPacket);
52586 + pOSPkt->dev = get_netdev_from_bssid(pAd, BSS0);
52587 + if (pRxBlk->pHeader->FC.Type == BTYPE_DATA)
52588 + {
52589 + pRxBlk->DataSize -= LENGTH_802_11;
52590 + if ((pRxBlk->pHeader->FC.ToDs == 1) &&
52591 + (pRxBlk->pHeader->FC.FrDs == 1))
52592 + header_len = LENGTH_802_11_WITH_ADDR4;
52593 + else
52594 + header_len = LENGTH_802_11;
52595 +
52596 + // QOS
52597 + if (pRxBlk->pHeader->FC.SubType & 0x08)
52598 + {
52599 + header_len += 2;
52600 + // Data skip QOS contorl field
52601 + pRxBlk->DataSize -=2;
52602 + }
52603 +
52604 + // Order bit: A-Ralink or HTC+
52605 + if (pRxBlk->pHeader->FC.Order)
52606 + {
52607 + header_len += 4;
52608 + // Data skip HTC contorl field
52609 + pRxBlk->DataSize -= 4;
52610 + }
52611 +
52612 + // Copy Header
52613 + if (header_len <= 40)
52614 + NdisMoveMemory(temp_header, pRxBlk->pData, header_len);
52615 +
52616 + // skip HW padding
52617 + if (pRxBlk->RxD.L2PAD)
52618 + pRxBlk->pData += (header_len + 2);
52619 + else
52620 + pRxBlk->pData += header_len;
52621 + } //end if
52622 +
52623 +
52624 + if (pRxBlk->DataSize < pOSPkt->len) {
52625 + skb_trim(pOSPkt,pRxBlk->DataSize);
52626 + } else {
52627 + skb_put(pOSPkt,(pRxBlk->DataSize - pOSPkt->len));
52628 + } //end if
52629 +
52630 + if ((pRxBlk->pData - pOSPkt->data) > 0) {
52631 + skb_put(pOSPkt,(pRxBlk->pData - pOSPkt->data));
52632 + skb_pull(pOSPkt,(pRxBlk->pData - pOSPkt->data));
52633 + } //end if
52634 +
52635 + if (skb_headroom(pOSPkt) < (sizeof(wlan_ng_prism2_header)+ header_len)) {
52636 + if (pskb_expand_head(pOSPkt, (sizeof(wlan_ng_prism2_header) + header_len), 0, GFP_ATOMIC)) {
52637 + DBGPRINT(RT_DEBUG_ERROR, ("%s : Reallocate header size of sk_buff fail!\n", __FUNCTION__));
52638 + goto err_free_sk_buff;
52639 + } //end if
52640 + } //end if
52641 +
52642 + if (header_len > 0)
52643 + NdisMoveMemory(skb_push(pOSPkt, header_len), temp_header, header_len);
52644 +
52645 + ph = (wlan_ng_prism2_header *) skb_push(pOSPkt, sizeof(wlan_ng_prism2_header));
52646 + NdisZeroMemory(ph, sizeof(wlan_ng_prism2_header));
52647 +
52648 + ph->msgcode = DIDmsg_lnxind_wlansniffrm;
52649 + ph->msglen = sizeof(wlan_ng_prism2_header);
52650 + strcpy(ph->devname, pAd->net_dev->name);
52651 +
52652 + ph->hosttime.did = DIDmsg_lnxind_wlansniffrm_hosttime;
52653 + ph->hosttime.status = 0;
52654 + ph->hosttime.len = 4;
52655 + ph->hosttime.data = jiffies;
52656 +
52657 + ph->mactime.did = DIDmsg_lnxind_wlansniffrm_mactime;
52658 + ph->mactime.status = 0;
52659 + ph->mactime.len = 0;
52660 + ph->mactime.data = 0;
52661 +
52662 + ph->istx.did = DIDmsg_lnxind_wlansniffrm_istx;
52663 + ph->istx.status = 0;
52664 + ph->istx.len = 0;
52665 + ph->istx.data = 0;
52666 +
52667 + ph->channel.did = DIDmsg_lnxind_wlansniffrm_channel;
52668 + ph->channel.status = 0;
52669 + ph->channel.len = 4;
52670 +
52671 + ph->channel.data = (u_int32_t)pAd->CommonCfg.Channel;
52672 +
52673 + ph->rssi.did = DIDmsg_lnxind_wlansniffrm_rssi;
52674 + ph->rssi.status = 0;
52675 + ph->rssi.len = 4;
52676 + ph->rssi.data = (u_int32_t)RTMPMaxRssi(pAd, ConvertToRssi(pAd, pRxBlk->pRxWI->RSSI0, RSSI_0), ConvertToRssi(pAd, pRxBlk->pRxWI->RSSI1, RSSI_1), ConvertToRssi(pAd, pRxBlk->pRxWI->RSSI2, RSSI_2));;
52677 +
52678 + ph->signal.did = DIDmsg_lnxind_wlansniffrm_signal;
52679 + ph->signal.status = 0;
52680 + ph->signal.len = 4;
52681 + ph->signal.data = 0; //rssi + noise;
52682 +
52683 + ph->noise.did = DIDmsg_lnxind_wlansniffrm_noise;
52684 + ph->noise.status = 0;
52685 + ph->noise.len = 4;
52686 + ph->noise.data = 0;
52687 +
52688 +#ifdef DOT11_N_SUPPORT
52689 + if (pRxBlk->pRxWI->PHYMODE >= MODE_HTMIX)
52690 + {
52691 + rate_index = 16 + ((UCHAR)pRxBlk->pRxWI->BW *16) + ((UCHAR)pRxBlk->pRxWI->ShortGI *32) + ((UCHAR)pRxBlk->pRxWI->MCS);
52692 + }
52693 + else
52694 +#endif // DOT11_N_SUPPORT //
52695 + if (pRxBlk->pRxWI->PHYMODE == MODE_OFDM)
52696 + rate_index = (UCHAR)(pRxBlk->pRxWI->MCS) + 4;
52697 + else
52698 + rate_index = (UCHAR)(pRxBlk->pRxWI->MCS);
52699 + if (rate_index < 0)
52700 + rate_index = 0;
52701 + if (rate_index > 255)
52702 + rate_index = 255;
52703 +
52704 + ph->rate.did = DIDmsg_lnxind_wlansniffrm_rate;
52705 + ph->rate.status = 0;
52706 + ph->rate.len = 4;
52707 + ph->rate.data = ralinkrate[rate_index];
52708 +
52709 + ph->frmlen.did = DIDmsg_lnxind_wlansniffrm_frmlen;
52710 + ph->frmlen.status = 0;
52711 + ph->frmlen.len = 4;
52712 + ph->frmlen.data = (u_int32_t)pRxBlk->DataSize;
52713 +
52714 +
52715 + pOSPkt->pkt_type = PACKET_OTHERHOST;
52716 + pOSPkt->protocol = eth_type_trans(pOSPkt, pOSPkt->dev);
52717 + pOSPkt->ip_summed = CHECKSUM_NONE;
52718 + netif_rx(pOSPkt);
52719 +
52720 + return;
52721 +
52722 +err_free_sk_buff:
52723 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
52724 + return;
52725 +
52726 +}
52727 +#endif // CONFIG_STA_SUPPORT //
52728 +
52729 +
52730 +void rtmp_os_thread_init(PUCHAR pThreadName, PVOID pNotify)
52731 +{
52732 +
52733 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
52734 + daemonize(pThreadName /*"%s",pAd->net_dev->name*/);
52735 +
52736 + allow_signal(SIGTERM);
52737 + allow_signal(SIGKILL);
52738 + current->flags |= PF_NOFREEZE;
52739 +#else
52740 + unsigned long flags;
52741 +
52742 + daemonize();
52743 + reparent_to_init();
52744 + strcpy(current->comm, pThreadName);
52745 +
52746 + siginitsetinv(&current->blocked, sigmask(SIGTERM) | sigmask(SIGKILL));
52747 +
52748 + /* Allow interception of SIGKILL only
52749 + * Don't allow other signals to interrupt the transmission */
52750 +#if LINUX_VERSION_CODE > KERNEL_VERSION(2,4,22)
52751 + spin_lock_irqsave(&current->sigmask_lock, flags);
52752 + flush_signals(current);
52753 + recalc_sigpending(current);
52754 + spin_unlock_irqrestore(&current->sigmask_lock, flags);
52755 +#endif
52756 +#endif
52757 +
52758 + /* signal that we've started the thread */
52759 + complete(pNotify);
52760 +
52761 +}
52762 +
52763 +void RTMP_IndicateMediaState(
52764 + IN PRTMP_ADAPTER pAd)
52765 +{
52766 + if (pAd->CommonCfg.bWirelessEvent)
52767 + {
52768 + if (pAd->IndicateMediaState == NdisMediaStateConnected)
52769 + {
52770 + RTMPSendWirelessEvent(pAd, IW_STA_LINKUP_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
52771 + }
52772 + else
52773 + {
52774 + RTMPSendWirelessEvent(pAd, IW_STA_LINKDOWN_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
52775 + }
52776 + }
52777 +}
52778 +
52779 --- /dev/null
52780 +++ b/drivers/staging/rt2860/rt_linux.h
52781 @@ -0,0 +1,926 @@
52782 +/*
52783 + *************************************************************************
52784 + * Ralink Tech Inc.
52785 + * 5F., No.36, Taiyuan St., Jhubei City,
52786 + * Hsinchu County 302,
52787 + * Taiwan, R.O.C.
52788 + *
52789 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
52790 + *
52791 + * This program is free software; you can redistribute it and/or modify *
52792 + * it under the terms of the GNU General Public License as published by *
52793 + * the Free Software Foundation; either version 2 of the License, or *
52794 + * (at your option) any later version. *
52795 + * *
52796 + * This program is distributed in the hope that it will be useful, *
52797 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
52798 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
52799 + * GNU General Public License for more details. *
52800 + * *
52801 + * You should have received a copy of the GNU General Public License *
52802 + * along with this program; if not, write to the *
52803 + * Free Software Foundation, Inc., *
52804 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
52805 + * *
52806 + *************************************************************************
52807 + */
52808 +
52809 +/***********************************************************************/
52810 +/* */
52811 +/* Program: rt_linux.c */
52812 +/* Created: 4/21/2006 1:17:38 PM */
52813 +/* Author: Wu Xi-Kun */
52814 +/* Comments: `description` */
52815 +/* */
52816 +/*---------------------------------------------------------------------*/
52817 +/* */
52818 +/* History: */
52819 +/* Revision 1.1 4/21/2006 1:17:38 PM xsikun */
52820 +/* Initial revision */
52821 +/* */
52822 +/***********************************************************************/
52823 +
52824 +#include "rtmp_type.h"
52825 +#include <linux/module.h>
52826 +#include <linux/version.h>
52827 +#include <linux/kernel.h>
52828 +
52829 +#include <linux/spinlock.h>
52830 +#include <linux/init.h>
52831 +#include <linux/string.h>
52832 +#include <linux/timer.h>
52833 +#include <linux/errno.h>
52834 +#include <linux/slab.h>
52835 +#include <linux/interrupt.h>
52836 +#include <linux/pci.h>
52837 +#include <linux/netdevice.h>
52838 +#include <linux/etherdevice.h>
52839 +#include <linux/skbuff.h>
52840 +#include <linux/ethtool.h>
52841 +#include <linux/wireless.h>
52842 +#include <linux/proc_fs.h>
52843 +#include <linux/delay.h>
52844 +#include <linux/if_arp.h>
52845 +#include <linux/ctype.h>
52846 +#include <linux/vmalloc.h>
52847 +
52848 +
52849 +#include <linux/wireless.h>
52850 +#include <net/iw_handler.h>
52851 +
52852 +// load firmware
52853 +#define __KERNEL_SYSCALLS__
52854 +#include <linux/unistd.h>
52855 +#include <asm/uaccess.h>
52856 +
52857 +
52858 +#define MEM_ALLOC_FLAG (GFP_ATOMIC) //(GFP_DMA | GFP_ATOMIC)
52859 +
52860 +#ifndef IFNAMSIZ
52861 +#define IFNAMSIZ 16
52862 +#endif
52863 +
52864 +//#define CONFIG_CKIP_SUPPORT
52865 +
52866 +#undef __inline
52867 +#define __inline static inline
52868 +
52869 +typedef int (*HARD_START_XMIT_FUNC)(struct sk_buff *skb, struct net_device *net_dev);
52870 +
52871 +// add by kathy
52872 +
52873 +#ifdef CONFIG_STA_SUPPORT
52874 +#ifdef RT2860
52875 +#define STA_PROFILE_PATH "/etc/Wireless/RT2860STA/RT2860STA.dat"
52876 +#define STA_RTMP_FIRMWARE_FILE_NAME "/etc/Wireless/RT2860STA/RT2860STA.bin"
52877 +#define STA_NIC_DEVICE_NAME "RT2860STA"
52878 +#define STA_DRIVER_VERSION "1.8.0.0"
52879 +#ifdef MULTIPLE_CARD_SUPPORT
52880 +#define CARD_INFO_PATH "/etc/Wireless/RT2860STA/RT2860STACard.dat"
52881 +#endif // MULTIPLE_CARD_SUPPORT //
52882 +#endif // RT2860 //
52883 +
52884 +
52885 +#endif // CONFIG_STA_SUPPORT //
52886 +
52887 +#ifdef RT2860
52888 +#ifndef PCI_DEVICE
52889 +#define PCI_DEVICE(vend,dev) \
52890 + .vendor = (vend), .device = (dev), \
52891 + .subvendor = PCI_ANY_ID, .subdevice = PCI_ANY_ID
52892 +#endif // PCI_DEVICE //
52893 +#endif // RT2860 //
52894 +
52895 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
52896 +
52897 +#define RTMP_TIME_AFTER(a,b) \
52898 + (typecheck(unsigned long, (unsigned long)a) && \
52899 + typecheck(unsigned long, (unsigned long)b) && \
52900 + ((long)(b) - (long)(a) < 0))
52901 +
52902 +#define RTMP_TIME_AFTER_EQ(a,b) \
52903 + (typecheck(unsigned long, (unsigned long)a) && \
52904 + typecheck(unsigned long, (unsigned long)b) && \
52905 + ((long)(a) - (long)(b) >= 0))
52906 +#define RTMP_TIME_BEFORE(a,b) RTMP_TIME_AFTER_EQ(b,a)
52907 +#else
52908 +#define RTMP_TIME_AFTER(a,b) time_after(a, b)
52909 +#endif
52910 +
52911 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
52912 +#define RT_MOD_INC_USE_COUNT() \
52913 + if (!try_module_get(THIS_MODULE)) \
52914 + { \
52915 + DBGPRINT(RT_DEBUG_ERROR, ("%s: cannot reserve module\n", __FUNCTION__)); \
52916 + return -1; \
52917 + }
52918 +
52919 +#define RT_MOD_DEC_USE_COUNT() module_put(THIS_MODULE);
52920 +#else
52921 +#define RT_MOD_INC_USE_COUNT() MOD_INC_USE_COUNT;
52922 +#define RT_MOD_DEC_USE_COUNT() MOD_DEC_USE_COUNT;
52923 +#endif
52924 +
52925 +#define OS_HZ HZ
52926 +
52927 +#define ETH_LENGTH_OF_ADDRESS 6
52928 +
52929 +#define IN
52930 +#define OUT
52931 +
52932 +#define NDIS_STATUS INT
52933 +#define NDIS_STATUS_SUCCESS 0x00
52934 +#define NDIS_STATUS_FAILURE 0x01
52935 +#define NDIS_STATUS_INVALID_DATA 0x02
52936 +#define NDIS_STATUS_RESOURCES 0x03
52937 +
52938 +#define MIN_NET_DEVICE_FOR_AID 0x00 //0x00~0x3f
52939 +#define MIN_NET_DEVICE_FOR_MBSSID 0x00 //0x00,0x10,0x20,0x30
52940 +#define MIN_NET_DEVICE_FOR_WDS 0x10 //0x40,0x50,0x60,0x70
52941 +#define MIN_NET_DEVICE_FOR_APCLI 0x20
52942 +#define MIN_NET_DEVICE_FOR_MESH 0x30
52943 +#ifdef CONFIG_STA_SUPPORT
52944 +#define MIN_NET_DEVICE_FOR_DLS 0x40
52945 +#endif // CONFIG_STA_SUPPORT //
52946 +
52947 +
52948 +#ifdef CONFIG_STA_SUPPORT
52949 +#define NDIS_PACKET_TYPE_DIRECTED 0
52950 +#define NDIS_PACKET_TYPE_MULTICAST 1
52951 +#define NDIS_PACKET_TYPE_BROADCAST 2
52952 +#define NDIS_PACKET_TYPE_ALL_MULTICAST 3
52953 +#endif // CONFIG_STA_SUPPORT //
52954 +
52955 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,27)
52956 +typedef struct pid * THREAD_PID;
52957 +#define THREAD_PID_INIT_VALUE NULL
52958 +#define GET_PID(_v) find_get_pid(_v)
52959 +#define GET_PID_NUMBER(_v) pid_nr(_v)
52960 +#define CHECK_PID_LEGALITY(_pid) if (pid_nr(_pid) >= 0)
52961 +#define KILL_THREAD_PID(_A, _B, _C) kill_pid(_A, _B, _C)
52962 +#else
52963 +typedef pid_t THREAD_PID;
52964 +#define THREAD_PID_INIT_VALUE -1
52965 +#define GET_PID(_v) _v
52966 +#define GET_PID_NUMBER(_v) _v
52967 +#define CHECK_PID_LEGALITY(_pid) if (_pid >= 0)
52968 +#define KILL_THREAD_PID(_A, _B, _C) kill_proc(_A, _B, _C)
52969 +#endif
52970 +
52971 +struct os_lock {
52972 + spinlock_t lock;
52973 + unsigned long flags;
52974 +};
52975 +
52976 +
52977 +struct os_cookie {
52978 +#ifdef RT2860
52979 + struct pci_dev *pci_dev;
52980 + struct pci_dev *parent_pci_dev;
52981 + dma_addr_t pAd_pa;
52982 +#endif // RT2860 //
52983 +
52984 +
52985 + struct tasklet_struct rx_done_task;
52986 + struct tasklet_struct mgmt_dma_done_task;
52987 + struct tasklet_struct ac0_dma_done_task;
52988 + struct tasklet_struct ac1_dma_done_task;
52989 + struct tasklet_struct ac2_dma_done_task;
52990 + struct tasklet_struct ac3_dma_done_task;
52991 + struct tasklet_struct hcca_dma_done_task;
52992 + struct tasklet_struct tbtt_task;
52993 +#ifdef RT2860
52994 + struct tasklet_struct fifo_statistic_full_task;
52995 +#endif // RT2860 //
52996 +
52997 +
52998 + unsigned long apd_pid; //802.1x daemon pid
52999 + INT ioctl_if_type;
53000 + INT ioctl_if;
53001 +};
53002 +
53003 +typedef struct _VIRTUAL_ADAPTER
53004 +{
53005 + struct net_device *RtmpDev;
53006 + struct net_device *VirtualDev;
53007 +} VIRTUAL_ADAPTER, PVIRTUAL_ADAPTER;
53008 +
53009 +#undef ASSERT
53010 +#define ASSERT(x) \
53011 +{ \
53012 + if (!(x)) \
53013 + { \
53014 + printk(KERN_WARNING __FILE__ ":%d assert " #x "failed\n", __LINE__); \
53015 + } \
53016 +}
53017 +
53018 +typedef struct os_cookie * POS_COOKIE;
53019 +typedef struct pci_dev * PPCI_DEV;
53020 +typedef struct net_device * PNET_DEV;
53021 +typedef void * PNDIS_PACKET;
53022 +typedef char NDIS_PACKET;
53023 +typedef PNDIS_PACKET * PPNDIS_PACKET;
53024 +typedef dma_addr_t NDIS_PHYSICAL_ADDRESS;
53025 +typedef dma_addr_t * PNDIS_PHYSICAL_ADDRESS;
53026 +typedef spinlock_t NDIS_SPIN_LOCK;
53027 +typedef struct timer_list NDIS_MINIPORT_TIMER;
53028 +typedef void * NDIS_HANDLE;
53029 +typedef char * PNDIS_BUFFER;
53030 +
53031 +
53032 +
53033 +void hex_dump(char *str, unsigned char *pSrcBufVA, unsigned int SrcBufLen);
53034 +
53035 +dma_addr_t linux_pci_map_single(void *handle, void *ptr, size_t size, int sd_idx, int direction);
53036 +void linux_pci_unmap_single(void *handle, dma_addr_t dma_addr, size_t size, int direction);
53037 +
53038 +
53039 +////////////////////////////////////////
53040 +// MOVE TO rtmp.h ?
53041 +/////////////////////////////////////////
53042 +#define PKTSRC_NDIS 0x7f
53043 +#define PKTSRC_DRIVER 0x0f
53044 +#define PRINT_MAC(addr) \
53045 + addr[0], addr[1], addr[2], addr[3], addr[4], addr[5]
53046 +
53047 +
53048 +#define RT2860_PCI_DEVICE_ID 0x0601
53049 +
53050 +#ifdef RT2860
53051 +#define PCI_MAP_SINGLE(_handle, _ptr, _size, _sd_idx, _dir) \
53052 + linux_pci_map_single(_handle, _ptr, _size, _sd_idx, _dir)
53053 +
53054 +#define PCI_UNMAP_SINGLE(_handle, _ptr, _size, _dir) \
53055 + linux_pci_unmap_single(_handle, _ptr, _size, _dir)
53056 +
53057 +#define PCI_ALLOC_CONSISTENT(_pci_dev, _size, _ptr) \
53058 + pci_alloc_consistent(_pci_dev, _size, _ptr)
53059 +
53060 +#define PCI_FREE_CONSISTENT(_pci_dev, _size, _virtual_addr, _physical_addr) \
53061 + pci_free_consistent(_pci_dev, _size, _virtual_addr, _physical_addr)
53062 +
53063 +#define DEV_ALLOC_SKB(_length) \
53064 + dev_alloc_skb(_length)
53065 +#endif // RT2860 //
53066 +
53067 +
53068 +
53069 +#define BEACON_FRAME_DMA_CACHE_WBACK(_ptr, _size) \
53070 + dma_cache_wback(_ptr, _size)
53071 +
53072 +
53073 +//////////////////////////////////////////
53074 +//
53075 +//////////////////////////////////////////
53076 +
53077 +
53078 +#define NdisMIndicateStatus(_w, _x, _y, _z)
53079 +
53080 +
53081 +typedef struct timer_list RTMP_OS_TIMER;
53082 +
53083 +
53084 +
53085 +typedef struct _RALINK_TIMER_STRUCT {
53086 + RTMP_OS_TIMER TimerObj; // Ndis Timer object
53087 + BOOLEAN Valid; // Set to True when call RTMPInitTimer
53088 + BOOLEAN State; // True if timer cancelled
53089 + BOOLEAN PeriodicType; // True if timer is periodic timer
53090 + BOOLEAN Repeat; // True if periodic timer
53091 + ULONG TimerValue; // Timer value in milliseconds
53092 + ULONG cookie; // os specific object
53093 +} RALINK_TIMER_STRUCT, *PRALINK_TIMER_STRUCT;
53094 +
53095 +
53096 +
53097 +
53098 +//#define DBG 1
53099 +
53100 +//
53101 +// MACRO for debugging information
53102 +//
53103 +
53104 +#ifdef DBG
53105 +extern ULONG RTDebugLevel;
53106 +
53107 +#define DBGPRINT_RAW(Level, Fmt) \
53108 +{ \
53109 + if (Level <= RTDebugLevel) \
53110 + { \
53111 + printk Fmt; \
53112 + } \
53113 +}
53114 +
53115 +#define DBGPRINT(Level, Fmt) DBGPRINT_RAW(Level, Fmt)
53116 +
53117 +
53118 +#define DBGPRINT_ERR(Fmt) \
53119 +{ \
53120 + printk("ERROR!!! "); \
53121 + printk Fmt; \
53122 +}
53123 +
53124 +#define DBGPRINT_S(Status, Fmt) \
53125 +{ \
53126 + printk Fmt; \
53127 +}
53128 +
53129 +
53130 +#else
53131 +#define DBGPRINT(Level, Fmt)
53132 +#define DBGPRINT_RAW(Level, Fmt)
53133 +#define DBGPRINT_S(Status, Fmt)
53134 +#define DBGPRINT_ERR(Fmt)
53135 +#endif
53136 +
53137 +
53138 +//
53139 +// spin_lock enhanced for Nested spin lock
53140 +//
53141 +#define NdisAllocateSpinLock(__lock) \
53142 +{ \
53143 + spin_lock_init((spinlock_t *)(__lock)); \
53144 +}
53145 +
53146 +#define NdisFreeSpinLock(lock) \
53147 +{ \
53148 +}
53149 +
53150 +
53151 +#define RTMP_SEM_LOCK(__lock) \
53152 +{ \
53153 + spin_lock_bh((spinlock_t *)(__lock)); \
53154 +}
53155 +
53156 +#define RTMP_SEM_UNLOCK(__lock) \
53157 +{ \
53158 + spin_unlock_bh((spinlock_t *)(__lock)); \
53159 +}
53160 +
53161 +// sample, use semaphore lock to replace IRQ lock, 2007/11/15
53162 +#define RTMP_IRQ_LOCK(__lock, __irqflags) \
53163 +{ \
53164 + __irqflags = 0; \
53165 + spin_lock_bh((spinlock_t *)(__lock)); \
53166 + pAd->irq_disabled |= 1; \
53167 +}
53168 +
53169 +#define RTMP_IRQ_UNLOCK(__lock, __irqflag) \
53170 +{ \
53171 + pAd->irq_disabled &= 0; \
53172 + spin_unlock_bh((spinlock_t *)(__lock)); \
53173 +}
53174 +
53175 +#define RTMP_INT_LOCK(__lock, __irqflags) \
53176 +{ \
53177 + spin_lock_irqsave((spinlock_t *)__lock, __irqflags); \
53178 +}
53179 +
53180 +#define RTMP_INT_UNLOCK(__lock, __irqflag) \
53181 +{ \
53182 + spin_unlock_irqrestore((spinlock_t *)(__lock), ((unsigned long)__irqflag)); \
53183 +}
53184 +
53185 +#ifdef RT2860
53186 +#if defined(INF_TWINPASS) || defined(INF_DANUBE) || defined(IKANOS_VX_1X0)
53187 +//Patch for ASIC turst read/write bug, needs to remove after metel fix
53188 +#define RTMP_IO_READ32(_A, _R, _pV) \
53189 +{ \
53190 + if ((_A)->bPCIclkOff == FALSE) \
53191 + { \
53192 + (*_pV = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0))); \
53193 + (*_pV = readl((void *)((_A)->CSRBaseAddress + (_R)))); \
53194 + (*_pV = SWAP32(*((UINT32 *)(_pV)))); \
53195 + } \
53196 +}
53197 +#define RTMP_IO_READ8(_A, _R, _pV) \
53198 +{ \
53199 + (*_pV = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0))); \
53200 + (*_pV = readb((void *)((_A)->CSRBaseAddress + (_R)))); \
53201 +}
53202 +#define RTMP_IO_WRITE32(_A, _R, _V) \
53203 +{ \
53204 + if ((_A)->bPCIclkOff == FALSE) \
53205 + { \
53206 + UINT32 _Val; \
53207 + _Val = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0)); \
53208 + _Val = SWAP32(_V); \
53209 + writel(_Val, (void *)((_A)->CSRBaseAddress + (_R))); \
53210 + } \
53211 +}
53212 +#define RTMP_IO_WRITE8(_A, _R, _V) \
53213 +{ \
53214 + UINT Val; \
53215 + Val = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0)); \
53216 + writeb((_V), (PUCHAR)((_A)->CSRBaseAddress + (_R))); \
53217 +}
53218 +#define RTMP_IO_WRITE16(_A, _R, _V) \
53219 +{ \
53220 + UINT Val; \
53221 + Val = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0)); \
53222 + writew(SWAP16((_V)), (PUSHORT)((_A)->CSRBaseAddress + (_R))); \
53223 +}
53224 +#else
53225 +//Patch for ASIC turst read/write bug, needs to remove after metel fix
53226 +#define RTMP_IO_READ32(_A, _R, _pV) \
53227 +{ \
53228 + if ((_A)->bPCIclkOff == FALSE) \
53229 + { \
53230 + (*_pV = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0))); \
53231 + (*_pV = readl((void *)((_A)->CSRBaseAddress + (_R)))); \
53232 + } \
53233 + else \
53234 + *_pV = 0; \
53235 +}
53236 +#define RTMP_IO_READ8(_A, _R, _pV) \
53237 +{ \
53238 + (*_pV = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0))); \
53239 + (*_pV = readb((void *)((_A)->CSRBaseAddress + (_R)))); \
53240 +}
53241 +#define RTMP_IO_WRITE32(_A, _R, _V) \
53242 +{ \
53243 + if ((_A)->bPCIclkOff == FALSE) \
53244 + { \
53245 + UINT Val; \
53246 + Val = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0)); \
53247 + writel(_V, (void *)((_A)->CSRBaseAddress + (_R))); \
53248 + } \
53249 +}
53250 +#if defined(BRCM_6358)
53251 +#define RTMP_IO_WRITE8(_A, _R, _V) \
53252 +{ \
53253 + ULONG Val; \
53254 + UCHAR _i; \
53255 + _i = (_R & 0x3); \
53256 + Val = readl((void *)((_A)->CSRBaseAddress + (_R - _i))); \
53257 + Val = Val & (~(0x000000ff << ((_i)*8))); \
53258 + Val = Val | ((ULONG)_V << ((_i)*8)); \
53259 + writel((Val), (void *)((_A)->CSRBaseAddress + (_R - _i))); \
53260 +}
53261 +#else
53262 +#define RTMP_IO_WRITE8(_A, _R, _V) \
53263 +{ \
53264 + UINT Val; \
53265 + Val = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0)); \
53266 + writeb((_V), (PUCHAR)((_A)->CSRBaseAddress + (_R))); \
53267 +}
53268 +#endif
53269 +#define RTMP_IO_WRITE16(_A, _R, _V) \
53270 +{ \
53271 + UINT Val; \
53272 + Val = readl((void *)((_A)->CSRBaseAddress + MAC_CSR0)); \
53273 + writew((_V), (PUSHORT)((_A)->CSRBaseAddress + (_R))); \
53274 +}
53275 +#endif
53276 +#endif // RT2860 //
53277 +
53278 +
53279 +#ifndef wait_event_interruptible_timeout
53280 +#define __wait_event_interruptible_timeout(wq, condition, ret) \
53281 +do { \
53282 + wait_queue_t __wait; \
53283 + init_waitqueue_entry(&__wait, current); \
53284 + add_wait_queue(&wq, &__wait); \
53285 + for (;;) { \
53286 + set_current_state(TASK_INTERRUPTIBLE); \
53287 + if (condition) \
53288 + break; \
53289 + if (!signal_pending(current)) { \
53290 + ret = schedule_timeout(ret); \
53291 + if (!ret) \
53292 + break; \
53293 + continue; \
53294 + } \
53295 + ret = -ERESTARTSYS; \
53296 + break; \
53297 + } \
53298 + current->state = TASK_RUNNING; \
53299 + remove_wait_queue(&wq, &__wait); \
53300 +} while (0)
53301 +
53302 +#define wait_event_interruptible_timeout(wq, condition, timeout) \
53303 +({ \
53304 + long __ret = timeout; \
53305 + if (!(condition)) \
53306 + __wait_event_interruptible_timeout(wq, condition, __ret); \
53307 + __ret; \
53308 +})
53309 +#endif
53310 +#define ONE_TICK 1
53311 +#define OS_WAIT(_time) \
53312 +{ int _i; \
53313 + long _loop = ((_time)/(1000/OS_HZ)) > 0 ? ((_time)/(1000/OS_HZ)) : 1;\
53314 + wait_queue_head_t _wait; \
53315 + init_waitqueue_head(&_wait); \
53316 + for (_i=0; _i<(_loop); _i++) \
53317 + wait_event_interruptible_timeout(_wait, 0, ONE_TICK); }
53318 +
53319 +
53320 +/* Modified by Wu Xi-Kun 4/21/2006 */
53321 +typedef void (*TIMER_FUNCTION)(unsigned long);
53322 +
53323 +#define COPY_MAC_ADDR(Addr1, Addr2) memcpy((Addr1), (Addr2), MAC_ADDR_LEN)
53324 +
53325 +#define MlmeAllocateMemory(_pAd, _ppVA) os_alloc_mem(_pAd, _ppVA, MGMT_DMA_BUFFER_SIZE)
53326 +#define MlmeFreeMemory(_pAd, _pVA) os_free_mem(_pAd, _pVA)
53327 +
53328 +#ifdef RT2860
53329 +#define BUILD_TIMER_FUNCTION(_func) \
53330 +void linux_##_func(unsigned long data) \
53331 +{ \
53332 + PRALINK_TIMER_STRUCT pTimer = (PRALINK_TIMER_STRUCT) data; \
53333 + \
53334 + _func(NULL, (PVOID) pTimer->cookie, NULL, pTimer); \
53335 + if (pTimer->Repeat) \
53336 + RTMP_OS_Add_Timer(&pTimer->TimerObj, pTimer->TimerValue); \
53337 +}
53338 +#endif // RT2860 //
53339 +
53340 +
53341 +
53342 +#define DECLARE_TIMER_FUNCTION(_func) \
53343 +void linux_##_func(unsigned long data)
53344 +
53345 +#define GET_TIMER_FUNCTION(_func) \
53346 + linux_##_func
53347 +
53348 +DECLARE_TIMER_FUNCTION(MlmePeriodicExec);
53349 +DECLARE_TIMER_FUNCTION(MlmeRssiReportExec);
53350 +DECLARE_TIMER_FUNCTION(AsicRxAntEvalTimeout);
53351 +DECLARE_TIMER_FUNCTION(APSDPeriodicExec);
53352 +DECLARE_TIMER_FUNCTION(AsicRfTuningExec);
53353 +
53354 +
53355 +#ifdef CONFIG_STA_SUPPORT
53356 +DECLARE_TIMER_FUNCTION(BeaconTimeout);
53357 +DECLARE_TIMER_FUNCTION(ScanTimeout);
53358 +DECLARE_TIMER_FUNCTION(AuthTimeout);
53359 +DECLARE_TIMER_FUNCTION(AssocTimeout);
53360 +DECLARE_TIMER_FUNCTION(ReassocTimeout);
53361 +DECLARE_TIMER_FUNCTION(DisassocTimeout);
53362 +DECLARE_TIMER_FUNCTION(LinkDownExec);
53363 +#ifdef LEAP_SUPPORT
53364 +DECLARE_TIMER_FUNCTION(LeapAuthTimeout);
53365 +#endif
53366 +DECLARE_TIMER_FUNCTION(StaQuickResponeForRateUpExec);
53367 +DECLARE_TIMER_FUNCTION(WpaDisassocApAndBlockAssoc);
53368 +DECLARE_TIMER_FUNCTION(PsPollWakeExec);
53369 +DECLARE_TIMER_FUNCTION(RadioOnExec);
53370 +
53371 +#ifdef QOS_DLS_SUPPORT
53372 +DECLARE_TIMER_FUNCTION(DlsTimeoutAction);
53373 +#endif // QOS_DLS_SUPPORT //
53374 +#endif // CONFIG_STA_SUPPORT //
53375 +
53376 +void RTMP_GetCurrentSystemTime(LARGE_INTEGER *time);
53377 +
53378 +
53379 +/*
53380 + * packet helper
53381 + * - convert internal rt packet to os packet or
53382 + * os packet to rt packet
53383 + */
53384 +#define RTPKT_TO_OSPKT(_p) ((struct sk_buff *)(_p))
53385 +#define OSPKT_TO_RTPKT(_p) ((PNDIS_PACKET)(_p))
53386 +
53387 +#define GET_OS_PKT_DATAPTR(_pkt) \
53388 + (RTPKT_TO_OSPKT(_pkt)->data)
53389 +
53390 +#define GET_OS_PKT_LEN(_pkt) \
53391 + (RTPKT_TO_OSPKT(_pkt)->len)
53392 +
53393 +#define GET_OS_PKT_DATATAIL(_pkt) \
53394 + (RTPKT_TO_OSPKT(_pkt)->tail)
53395 +
53396 +#define GET_OS_PKT_HEAD(_pkt) \
53397 + (RTPKT_TO_OSPKT(_pkt)->head)
53398 +
53399 +#define GET_OS_PKT_END(_pkt) \
53400 + (RTPKT_TO_OSPKT(_pkt)->end)
53401 +
53402 +#define GET_OS_PKT_NETDEV(_pkt) \
53403 + (RTPKT_TO_OSPKT(_pkt)->dev)
53404 +
53405 +#define GET_OS_PKT_TYPE(_pkt) \
53406 + (RTPKT_TO_OSPKT(_pkt))
53407 +
53408 +#define GET_OS_PKT_NEXT(_pkt) \
53409 + (RTPKT_TO_OSPKT(_pkt)->next)
53410 +
53411 +
53412 +#define OS_NTOHS(_Val) \
53413 + (ntohs(_Val))
53414 +#define OS_HTONS(_Val) \
53415 + (htons(_Val))
53416 +#define OS_NTOHL(_Val) \
53417 + (ntohl(_Val))
53418 +#define OS_HTONL(_Val) \
53419 + (htonl(_Val))
53420 +
53421 +/* statistics counter */
53422 +#define STATS_INC_RX_PACKETS(_pAd, _dev)
53423 +#define STATS_INC_TX_PACKETS(_pAd, _dev)
53424 +
53425 +#define STATS_INC_RX_BYTESS(_pAd, _dev, len)
53426 +#define STATS_INC_TX_BYTESS(_pAd, _dev, len)
53427 +
53428 +#define STATS_INC_RX_ERRORS(_pAd, _dev)
53429 +#define STATS_INC_TX_ERRORS(_pAd, _dev)
53430 +
53431 +#define STATS_INC_RX_DROPPED(_pAd, _dev)
53432 +#define STATS_INC_TX_DROPPED(_pAd, _dev)
53433 +
53434 +
53435 +#define CB_OFF 10
53436 +
53437 +
53438 +// check DDK NDIS_PACKET data structure and find out only MiniportReservedEx[0..7] can be used by our driver without
53439 +// ambiguity. Fields after pPacket->MiniportReservedEx[8] may be used by other wrapper layer thus crashes the driver
53440 +//
53441 +
53442 +// User Priority
53443 +#define RTMP_SET_PACKET_UP(_p, _prio) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+0] = _prio)
53444 +#define RTMP_GET_PACKET_UP(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+0])
53445 +
53446 +// Fragment #
53447 +#define RTMP_SET_PACKET_FRAGMENTS(_p, _num) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+1] = _num)
53448 +#define RTMP_GET_PACKET_FRAGMENTS(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+1])
53449 +
53450 +// 0x0 ~0x7f: TX to AP's own BSS which has the specified AID. if AID>127, set bit 7 in RTMP_SET_PACKET_EMACTAB too.
53451 +//(this value also as MAC(on-chip WCID) table index)
53452 +// 0x80~0xff: TX to a WDS link. b0~6: WDS index
53453 +#define RTMP_SET_PACKET_WCID(_p, _wdsidx) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+2] = _wdsidx)
53454 +#define RTMP_GET_PACKET_WCID(_p) ((UCHAR)(RTPKT_TO_OSPKT(_p)->cb[CB_OFF+2]))
53455 +
53456 +// 0xff: PKTSRC_NDIS, others: local TX buffer index. This value affects how to a packet
53457 +#define RTMP_SET_PACKET_SOURCE(_p, _pktsrc) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+3] = _pktsrc)
53458 +#define RTMP_GET_PACKET_SOURCE(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+3])
53459 +
53460 +// RTS/CTS-to-self protection method
53461 +#define RTMP_SET_PACKET_RTS(_p, _num) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+4] = _num)
53462 +#define RTMP_GET_PACKET_RTS(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+4])
53463 +// see RTMP_S(G)ET_PACKET_EMACTAB
53464 +
53465 +// TX rate index
53466 +#define RTMP_SET_PACKET_TXRATE(_p, _rate) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+5] = _rate)
53467 +#define RTMP_GET_PACKET_TXRATE(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+5])
53468 +
53469 +// From which Interface
53470 +#define RTMP_SET_PACKET_IF(_p, _ifdx) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+6] = _ifdx)
53471 +#define RTMP_GET_PACKET_IF(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+6])
53472 +#define RTMP_SET_PACKET_NET_DEVICE_MBSSID(_p, _bss) RTMP_SET_PACKET_IF((_p), (_bss))
53473 +#define RTMP_SET_PACKET_NET_DEVICE_WDS(_p, _bss) RTMP_SET_PACKET_IF((_p), ((_bss) + MIN_NET_DEVICE_FOR_WDS))
53474 +#define RTMP_SET_PACKET_NET_DEVICE_APCLI(_p, _idx) RTMP_SET_PACKET_IF((_p), ((_idx) + MIN_NET_DEVICE_FOR_APCLI))
53475 +#define RTMP_SET_PACKET_NET_DEVICE_MESH(_p, _idx) RTMP_SET_PACKET_IF((_p), ((_idx) + MIN_NET_DEVICE_FOR_MESH))
53476 +#define RTMP_GET_PACKET_NET_DEVICE_MBSSID(_p) RTMP_GET_PACKET_IF((_p))
53477 +#define RTMP_GET_PACKET_NET_DEVICE(_p) RTMP_GET_PACKET_IF((_p))
53478 +
53479 +#define RTMP_SET_PACKET_MOREDATA(_p, _morebit) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+7] = _morebit)
53480 +#define RTMP_GET_PACKET_MOREDATA(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+7])
53481 +
53482 +
53483 +#if 0
53484 +//#define RTMP_SET_PACKET_DHCP(_p, _flg) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] = _flg)
53485 +//#define RTMP_GET_PACKET_DHCP(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11])
53486 +#else
53487 +//
53488 +// Sepcific Pakcet Type definition
53489 +//
53490 +#define RTMP_PACKET_SPECIFIC_CB_OFFSET 11
53491 +
53492 +#define RTMP_PACKET_SPECIFIC_DHCP 0x01
53493 +#define RTMP_PACKET_SPECIFIC_EAPOL 0x02
53494 +#define RTMP_PACKET_SPECIFIC_IPV4 0x04
53495 +#define RTMP_PACKET_SPECIFIC_WAI 0x08
53496 +#define RTMP_PACKET_SPECIFIC_VLAN 0x10
53497 +#define RTMP_PACKET_SPECIFIC_LLCSNAP 0x20
53498 +
53499 +//Specific
53500 +#define RTMP_SET_PACKET_SPECIFIC(_p, _flg) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] = _flg)
53501 +
53502 +//DHCP
53503 +#define RTMP_SET_PACKET_DHCP(_p, _flg) \
53504 + do{ \
53505 + if (_flg) \
53506 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) |= (RTMP_PACKET_SPECIFIC_DHCP); \
53507 + else \
53508 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) &= (!RTMP_PACKET_SPECIFIC_DHCP); \
53509 + }while(0)
53510 +#define RTMP_GET_PACKET_DHCP(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] & RTMP_PACKET_SPECIFIC_DHCP)
53511 +
53512 +//EAPOL
53513 +#define RTMP_SET_PACKET_EAPOL(_p, _flg) \
53514 + do{ \
53515 + if (_flg) \
53516 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) |= (RTMP_PACKET_SPECIFIC_EAPOL); \
53517 + else \
53518 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) &= (!RTMP_PACKET_SPECIFIC_EAPOL); \
53519 + }while(0)
53520 +#define RTMP_GET_PACKET_EAPOL(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] & RTMP_PACKET_SPECIFIC_EAPOL)
53521 +
53522 +//WAI
53523 +#define RTMP_SET_PACKET_WAI(_p, _flg) \
53524 + do{ \
53525 + if (_flg) \
53526 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) |= (RTMP_PACKET_SPECIFIC_WAI); \
53527 + else \
53528 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) &= (!RTMP_PACKET_SPECIFIC_WAI); \
53529 + }while(0)
53530 +#define RTMP_GET_PACKET_WAI(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] & RTMP_PACKET_SPECIFIC_WAI)
53531 +
53532 +#define RTMP_GET_PACKET_LOWRATE(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] & (RTMP_PACKET_SPECIFIC_EAPOL | RTMP_PACKET_SPECIFIC_DHCP | RTMP_PACKET_SPECIFIC_WAI))
53533 +
53534 +//VLAN
53535 +#define RTMP_SET_PACKET_VLAN(_p, _flg) \
53536 + do{ \
53537 + if (_flg) \
53538 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) |= (RTMP_PACKET_SPECIFIC_VLAN); \
53539 + else \
53540 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) &= (!RTMP_PACKET_SPECIFIC_VLAN); \
53541 + }while(0)
53542 +#define RTMP_GET_PACKET_VLAN(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] & RTMP_PACKET_SPECIFIC_VLAN)
53543 +
53544 +//LLC/SNAP
53545 +#define RTMP_SET_PACKET_LLCSNAP(_p, _flg) \
53546 + do{ \
53547 + if (_flg) \
53548 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) |= (RTMP_PACKET_SPECIFIC_LLCSNAP); \
53549 + else \
53550 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) &= (!RTMP_PACKET_SPECIFIC_LLCSNAP); \
53551 + }while(0)
53552 +
53553 +#define RTMP_GET_PACKET_LLCSNAP(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] & RTMP_PACKET_SPECIFIC_LLCSNAP)
53554 +
53555 +// IP
53556 +#define RTMP_SET_PACKET_IPV4(_p, _flg) \
53557 + do{ \
53558 + if (_flg) \
53559 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) |= (RTMP_PACKET_SPECIFIC_IPV4); \
53560 + else \
53561 + (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11]) &= (!RTMP_PACKET_SPECIFIC_IPV4); \
53562 + }while(0)
53563 +
53564 +#define RTMP_GET_PACKET_IPV4(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+11] & RTMP_PACKET_SPECIFIC_IPV4)
53565 +
53566 +#endif
53567 +
53568 +
53569 +// If this flag is set, it indicates that this EAPoL frame MUST be clear.
53570 +#define RTMP_SET_PACKET_CLEAR_EAP_FRAME(_p, _flg) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+12] = _flg)
53571 +#define RTMP_GET_PACKET_CLEAR_EAP_FRAME(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+12])
53572 +
53573 +#define RTMP_SET_PACKET_5VT(_p, _flg) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+22] = _flg)
53574 +#define RTMP_GET_PACKET_5VT(_p) (RTPKT_TO_OSPKT(_p)->cb[CB_OFF+22])
53575 +
53576 +#ifdef CONFIG_5VT_ENHANCE
53577 +#define BRIDGE_TAG 0x35564252 // depends on 5VT define in br_input.c
53578 +#endif
53579 +
53580 +
53581 +#define NDIS_SET_PACKET_STATUS(_p, _status)
53582 +
53583 +
53584 +#define GET_SG_LIST_FROM_PACKET(_p, _sc) \
53585 + rt_get_sg_list_from_packet(_p, _sc)
53586 +
53587 +#define NdisMoveMemory(Destination, Source, Length) memmove(Destination, Source, Length)
53588 +#define NdisZeroMemory(Destination, Length) memset(Destination, 0, Length)
53589 +#define NdisFillMemory(Destination, Length, Fill) memset(Destination, Fill, Length)
53590 +#define NdisEqualMemory(Source1, Source2, Length) (!memcmp(Source1, Source2, Length))
53591 +#define RTMPEqualMemory(Source1, Source2, Length) (!memcmp(Source1, Source2, Length))
53592 +
53593 +
53594 +#define RTMP_INC_REF(_A) 0
53595 +#define RTMP_DEC_REF(_A) 0
53596 +#define RTMP_GET_REF(_A) 0
53597 +
53598 +
53599 +
53600 +/*
53601 + * ULONG
53602 + * RTMP_GetPhysicalAddressLow(
53603 + * IN NDIS_PHYSICAL_ADDRESS PhysicalAddress);
53604 + */
53605 +#define RTMP_GetPhysicalAddressLow(PhysicalAddress) (PhysicalAddress)
53606 +
53607 +/*
53608 + * ULONG
53609 + * RTMP_GetPhysicalAddressHigh(
53610 + * IN NDIS_PHYSICAL_ADDRESS PhysicalAddress);
53611 + */
53612 +#define RTMP_GetPhysicalAddressHigh(PhysicalAddress) (0)
53613 +
53614 +/*
53615 + * VOID
53616 + * RTMP_SetPhysicalAddressLow(
53617 + * IN NDIS_PHYSICAL_ADDRESS PhysicalAddress,
53618 + * IN ULONG Value);
53619 + */
53620 +#define RTMP_SetPhysicalAddressLow(PhysicalAddress, Value) \
53621 + PhysicalAddress = Value;
53622 +
53623 +/*
53624 + * VOID
53625 + * RTMP_SetPhysicalAddressHigh(
53626 + * IN NDIS_PHYSICAL_ADDRESS PhysicalAddress,
53627 + * IN ULONG Value);
53628 + */
53629 +#define RTMP_SetPhysicalAddressHigh(PhysicalAddress, Value)
53630 +
53631 +
53632 +//CONTAINING_RECORD(pEntry, NDIS_PACKET, MiniportReservedEx);
53633 +#define QUEUE_ENTRY_TO_PACKET(pEntry) \
53634 + (PNDIS_PACKET)(pEntry)
53635 +
53636 +#define PACKET_TO_QUEUE_ENTRY(pPacket) \
53637 + (PQUEUE_ENTRY)(pPacket)
53638 +
53639 +
53640 +#ifndef CONTAINING_RECORD
53641 +#define CONTAINING_RECORD(address, type, field) \
53642 +((type *)((PCHAR)(address) - offsetof(type, field)))
53643 +#endif
53644 +
53645 +
53646 +#define RELEASE_NDIS_PACKET(_pAd, _pPacket, _Status) \
53647 +{ \
53648 + RTMPFreeNdisPacket(_pAd, _pPacket); \
53649 +}
53650 +
53651 +
53652 +#define SWITCH_PhyAB(_pAA, _pBB) \
53653 +{ \
53654 + ULONG AABasePaHigh; \
53655 + ULONG AABasePaLow; \
53656 + ULONG BBBasePaHigh; \
53657 + ULONG BBBasePaLow; \
53658 + BBBasePaHigh = RTMP_GetPhysicalAddressHigh(_pBB); \
53659 + BBBasePaLow = RTMP_GetPhysicalAddressLow(_pBB); \
53660 + AABasePaHigh = RTMP_GetPhysicalAddressHigh(_pAA); \
53661 + AABasePaLow = RTMP_GetPhysicalAddressLow(_pAA); \
53662 + RTMP_SetPhysicalAddressHigh(_pAA, BBBasePaHigh); \
53663 + RTMP_SetPhysicalAddressLow(_pAA, BBBasePaLow); \
53664 + RTMP_SetPhysicalAddressHigh(_pBB, AABasePaHigh); \
53665 + RTMP_SetPhysicalAddressLow(_pBB, AABasePaLow); \
53666 +}
53667 +
53668 +
53669 +#define NdisWriteErrorLogEntry(_a, _b, _c, _d)
53670 +#define NdisMAllocateMapRegisters(_a, _b, _c, _d, _e) NDIS_STATUS_SUCCESS
53671 +
53672 +
53673 +#define NdisAcquireSpinLock RTMP_SEM_LOCK
53674 +#define NdisReleaseSpinLock RTMP_SEM_UNLOCK
53675 +
53676 +static inline void NdisGetSystemUpTime(ULONG *time)
53677 +{
53678 + *time = jiffies;
53679 +}
53680 +
53681 +//pPacket = CONTAINING_RECORD(pEntry, NDIS_PACKET, MiniportReservedEx);
53682 +#define QUEUE_ENTRY_TO_PKT(pEntry) \
53683 + ((PNDIS_PACKET) (pEntry))
53684 +
53685 +int rt28xx_packet_xmit(struct sk_buff *skb);
53686 +
53687 +
53688 +
53689 +void rtmp_os_thread_init(PUCHAR pThreadName, PVOID pNotify);
53690 +
53691 +#ifdef RT2860
53692 +#if !defined(PCI_CAP_ID_EXP)
53693 +#define PCI_CAP_ID_EXP 0x10
53694 +#endif
53695 +
53696 +#if !defined(PCI_EXP_LNKCTL)
53697 +#define PCI_EXP_LNKCTL 0x10
53698 +#endif
53699 +
53700 +#if !defined(PCI_CLASS_BRIDGE_PCI)
53701 +#define PCI_CLASS_BRIDGE_PCI 0x0604
53702 +#endif
53703 +
53704 +#define PCIBUS_INTEL_VENDOR 0x8086
53705 +#endif // RT2860 //
53706 +
53707 +
53708 --- /dev/null
53709 +++ b/drivers/staging/rt2860/rt_main_dev.c
53710 @@ -0,0 +1,1686 @@
53711 +/*
53712 + *************************************************************************
53713 + * Ralink Tech Inc.
53714 + * 5F., No.36, Taiyuan St., Jhubei City,
53715 + * Hsinchu County 302,
53716 + * Taiwan, R.O.C.
53717 + *
53718 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
53719 + *
53720 + * This program is free software; you can redistribute it and/or modify *
53721 + * it under the terms of the GNU General Public License as published by *
53722 + * the Free Software Foundation; either version 2 of the License, or *
53723 + * (at your option) any later version. *
53724 + * *
53725 + * This program is distributed in the hope that it will be useful, *
53726 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
53727 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
53728 + * GNU General Public License for more details. *
53729 + * *
53730 + * You should have received a copy of the GNU General Public License *
53731 + * along with this program; if not, write to the *
53732 + * Free Software Foundation, Inc., *
53733 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
53734 + * *
53735 + *************************************************************************
53736 +
53737 + Module Name:
53738 + rt_main_dev.c
53739 +
53740 + Abstract:
53741 + Create and register network interface.
53742 +
53743 + Revision History:
53744 + Who When What
53745 + -------- ---------- ----------------------------------------------
53746 + Sample Mar/21/07 Merge RT2870 and RT2860 drivers.
53747 +*/
53748 +
53749 +#include "rt_config.h"
53750 +
53751 +#define FORTY_MHZ_INTOLERANT_INTERVAL (60*1000) // 1 min
53752 +
53753 +#ifdef MULTIPLE_CARD_SUPPORT
53754 +// record whether the card in the card list is used in the card file
53755 +UINT8 MC_CardUsed[MAX_NUM_OF_MULTIPLE_CARD];
53756 +// record used card mac address in the card list
53757 +static UINT8 MC_CardMac[MAX_NUM_OF_MULTIPLE_CARD][6];
53758 +#endif // MULTIPLE_CARD_SUPPORT //
53759 +
53760 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
53761 +UINT32 CW_MAX_IN_BITS;
53762 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
53763 +
53764 +/*---------------------------------------------------------------------*/
53765 +/* Private Variables Used */
53766 +/*---------------------------------------------------------------------*/
53767 +//static RALINK_TIMER_STRUCT PeriodicTimer;
53768 +
53769 +char *mac = ""; // default 00:00:00:00:00:00
53770 +char *hostname = ""; // default CMPC
53771 +#if LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,12)
53772 +MODULE_PARM (mac, "s");
53773 +#else
53774 +module_param (mac, charp, 0);
53775 +#endif
53776 +MODULE_PARM_DESC (mac, "rt28xx: wireless mac addr");
53777 +
53778 +
53779 +/*---------------------------------------------------------------------*/
53780 +/* Prototypes of Functions Used */
53781 +/*---------------------------------------------------------------------*/
53782 +#ifdef DOT11_N_SUPPORT
53783 +extern BOOLEAN ba_reordering_resource_init(PRTMP_ADAPTER pAd, int num);
53784 +extern void ba_reordering_resource_release(PRTMP_ADAPTER pAd);
53785 +#endif // DOT11_N_SUPPORT //
53786 +extern NDIS_STATUS NICLoadRateSwitchingParams(IN PRTMP_ADAPTER pAd);
53787 +
53788 +#ifdef RT2860
53789 +extern void init_thread_task(PRTMP_ADAPTER pAd);
53790 +#endif // RT2860 //
53791 +
53792 +// public function prototype
53793 +INT __devinit rt28xx_probe(IN void *_dev_p, IN void *_dev_id_p,
53794 + IN UINT argc, OUT PRTMP_ADAPTER *ppAd);
53795 +
53796 +// private function prototype
53797 +static int rt28xx_init(IN struct net_device *net_dev);
53798 +INT rt28xx_send_packets(IN struct sk_buff *skb_p, IN struct net_device *net_dev);
53799 +
53800 +#if LINUX_VERSION_CODE <= 0x20402 // Red Hat 7.1
53801 +struct net_device *alloc_netdev(
53802 + int sizeof_priv,
53803 + const char *mask,
53804 + void (*setup)(struct net_device *));
53805 +#endif // LINUX_VERSION_CODE //
53806 +
53807 +static void CfgInitHook(PRTMP_ADAPTER pAd);
53808 +
53809 +#ifdef CONFIG_STA_SUPPORT
53810 +extern const struct iw_handler_def rt28xx_iw_handler_def;
53811 +#endif // CONFIG_STA_SUPPORT //
53812 +
53813 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
53814 +extern const struct iw_handler_def rt28xx_ap_iw_handler_def;
53815 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
53816 +
53817 +#if WIRELESS_EXT >= 12
53818 +// This function will be called when query /proc
53819 +struct iw_statistics *rt28xx_get_wireless_stats(
53820 + IN struct net_device *net_dev);
53821 +#endif
53822 +
53823 +struct net_device_stats *RT28xx_get_ether_stats(
53824 + IN struct net_device *net_dev);
53825 +
53826 +/*
53827 +========================================================================
53828 +Routine Description:
53829 + Close raxx interface.
53830 +
53831 +Arguments:
53832 + *net_dev the raxx interface pointer
53833 +
53834 +Return Value:
53835 + 0 Open OK
53836 + otherwise Open Fail
53837 +
53838 +Note:
53839 + 1. if open fail, kernel will not call the close function.
53840 + 2. Free memory for
53841 + (1) Mlme Memory Handler: MlmeHalt()
53842 + (2) TX & RX: RTMPFreeTxRxRingMemory()
53843 + (3) BA Reordering: ba_reordering_resource_release()
53844 +========================================================================
53845 +*/
53846 +int MainVirtualIF_close(IN struct net_device *net_dev)
53847 +{
53848 + RTMP_ADAPTER *pAd = net_dev->priv;
53849 +
53850 + // Sanity check for pAd
53851 + if (pAd == NULL)
53852 + return 0; // close ok
53853 +
53854 + netif_carrier_off(pAd->net_dev);
53855 + netif_stop_queue(pAd->net_dev);
53856 +
53857 +
53858 + VIRTUAL_IF_DOWN(pAd);
53859 +
53860 + RT_MOD_DEC_USE_COUNT();
53861 +
53862 + return 0; // close ok
53863 +}
53864 +
53865 +/*
53866 +========================================================================
53867 +Routine Description:
53868 + Open raxx interface.
53869 +
53870 +Arguments:
53871 + *net_dev the raxx interface pointer
53872 +
53873 +Return Value:
53874 + 0 Open OK
53875 + otherwise Open Fail
53876 +
53877 +Note:
53878 + 1. if open fail, kernel will not call the close function.
53879 + 2. Free memory for
53880 + (1) Mlme Memory Handler: MlmeHalt()
53881 + (2) TX & RX: RTMPFreeTxRxRingMemory()
53882 + (3) BA Reordering: ba_reordering_resource_release()
53883 +========================================================================
53884 +*/
53885 +int MainVirtualIF_open(IN struct net_device *net_dev)
53886 +{
53887 + RTMP_ADAPTER *pAd = net_dev->priv;
53888 +
53889 + // Sanity check for pAd
53890 + if (pAd == NULL)
53891 + return 0; // close ok
53892 +
53893 + if (VIRTUAL_IF_UP(pAd) != 0)
53894 + return -1;
53895 +
53896 + // increase MODULE use count
53897 + RT_MOD_INC_USE_COUNT();
53898 +
53899 + netif_start_queue(net_dev);
53900 + netif_carrier_on(net_dev);
53901 + netif_wake_queue(net_dev);
53902 +
53903 + return 0;
53904 +}
53905 +
53906 +/*
53907 +========================================================================
53908 +Routine Description:
53909 + Close raxx interface.
53910 +
53911 +Arguments:
53912 + *net_dev the raxx interface pointer
53913 +
53914 +Return Value:
53915 + 0 Open OK
53916 + otherwise Open Fail
53917 +
53918 +Note:
53919 + 1. if open fail, kernel will not call the close function.
53920 + 2. Free memory for
53921 + (1) Mlme Memory Handler: MlmeHalt()
53922 + (2) TX & RX: RTMPFreeTxRxRingMemory()
53923 + (3) BA Reordering: ba_reordering_resource_release()
53924 +========================================================================
53925 +*/
53926 +int rt28xx_close(IN PNET_DEV dev)
53927 +{
53928 + struct net_device * net_dev = (struct net_device *)dev;
53929 + RTMP_ADAPTER *pAd = net_dev->priv;
53930 + BOOLEAN Cancelled = FALSE;
53931 + UINT32 i = 0;
53932 +
53933 +
53934 + DBGPRINT(RT_DEBUG_TRACE, ("===> rt28xx_close\n"));
53935 +
53936 + // Sanity check for pAd
53937 + if (pAd == NULL)
53938 + return 0; // close ok
53939 +
53940 +
53941 +#ifdef WDS_SUPPORT
53942 + WdsDown(pAd);
53943 +#endif // WDS_SUPPORT //
53944 +
53945 +#ifdef CONFIG_STA_SUPPORT
53946 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
53947 + {
53948 +#ifdef RT2860
53949 + RTMPPCIeLinkCtrlValueRestore(pAd, RESTORE_CLOSE);
53950 +#endif // RT2860 //
53951 +
53952 + // If dirver doesn't wake up firmware here,
53953 + // NICLoadFirmware will hang forever when interface is up again.
53954 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
53955 + {
53956 + AsicForceWakeup(pAd, TRUE);
53957 + }
53958 +
53959 +#ifdef QOS_DLS_SUPPORT
53960 + // send DLS-TEAR_DOWN message,
53961 + if (pAd->CommonCfg.bDLSCapable)
53962 + {
53963 + UCHAR i;
53964 +
53965 + // tear down local dls table entry
53966 + for (i=0; i<MAX_NUM_OF_INIT_DLS_ENTRY; i++)
53967 + {
53968 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH))
53969 + {
53970 + RTMPSendDLSTearDownFrame(pAd, pAd->StaCfg.DLSEntry[i].MacAddr);
53971 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
53972 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
53973 + }
53974 + }
53975 +
53976 + // tear down peer dls table entry
53977 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
53978 + {
53979 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH))
53980 + {
53981 + RTMPSendDLSTearDownFrame(pAd, pAd->StaCfg.DLSEntry[i].MacAddr);
53982 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
53983 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
53984 + }
53985 + }
53986 + RT28XX_MLME_HANDLER(pAd);
53987 + }
53988 +#endif // QOS_DLS_SUPPORT //
53989 +
53990 + if (INFRA_ON(pAd) &&
53991 + (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_NIC_NOT_EXIST)))
53992 + {
53993 + MLME_DISASSOC_REQ_STRUCT DisReq;
53994 + MLME_QUEUE_ELEM *MsgElem = (MLME_QUEUE_ELEM *) kmalloc(sizeof(MLME_QUEUE_ELEM), MEM_ALLOC_FLAG);
53995 +
53996 + COPY_MAC_ADDR(DisReq.Addr, pAd->CommonCfg.Bssid);
53997 + DisReq.Reason = REASON_DEAUTH_STA_LEAVING;
53998 +
53999 + MsgElem->Machine = ASSOC_STATE_MACHINE;
54000 + MsgElem->MsgType = MT2_MLME_DISASSOC_REQ;
54001 + MsgElem->MsgLen = sizeof(MLME_DISASSOC_REQ_STRUCT);
54002 + NdisMoveMemory(MsgElem->Msg, &DisReq, sizeof(MLME_DISASSOC_REQ_STRUCT));
54003 +
54004 + // Prevent to connect AP again in STAMlmePeriodicExec
54005 + pAd->MlmeAux.AutoReconnectSsidLen= 32;
54006 + NdisZeroMemory(pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.AutoReconnectSsidLen);
54007 +
54008 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_DISASSOC;
54009 + MlmeDisassocReqAction(pAd, MsgElem);
54010 + kfree(MsgElem);
54011 +
54012 + RTMPusecDelay(1000);
54013 + }
54014 +
54015 +
54016 +#ifdef CCX_SUPPORT
54017 + RTMPCancelTimer(&pAd->StaCfg.LeapAuthTimer, &Cancelled);
54018 +#endif
54019 +
54020 + RTMPCancelTimer(&pAd->StaCfg.StaQuickResponeForRateUpTimer, &Cancelled);
54021 + RTMPCancelTimer(&pAd->StaCfg.WpaDisassocAndBlockAssocTimer, &Cancelled);
54022 +
54023 +#ifdef WPA_SUPPLICANT_SUPPORT
54024 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
54025 + {
54026 + union iwreq_data wrqu;
54027 + // send wireless event to wpa_supplicant for infroming interface down.
54028 + memset(&wrqu, 0, sizeof(wrqu));
54029 + wrqu.data.flags = RT_INTERFACE_DOWN;
54030 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
54031 + }
54032 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
54033 +#endif // WPA_SUPPLICANT_SUPPORT //
54034 +
54035 + MlmeRadioOff(pAd);
54036 +#ifdef RT2860
54037 + pAd->bPCIclkOff = FALSE;
54038 +#endif // RT2860 //
54039 + }
54040 +#endif // CONFIG_STA_SUPPORT //
54041 +
54042 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS);
54043 +
54044 + for (i = 0 ; i < NUM_OF_TX_RING; i++)
54045 + {
54046 + while (pAd->DeQueueRunning[i] == TRUE)
54047 + {
54048 + printk("Waiting for TxQueue[%d] done..........\n", i);
54049 + RTMPusecDelay(1000);
54050 + }
54051 + }
54052 +
54053 + // Stop Mlme state machine
54054 + MlmeHalt(pAd);
54055 +
54056 + // Close kernel threads or tasklets
54057 + kill_thread_task(pAd);
54058 +
54059 +
54060 +#ifdef CONFIG_STA_SUPPORT
54061 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
54062 + {
54063 + MacTableReset(pAd);
54064 + }
54065 +#endif // CONFIG_STA_SUPPORT //
54066 +
54067 +
54068 + MeasureReqTabExit(pAd);
54069 + TpcReqTabExit(pAd);
54070 +
54071 +
54072 +#ifdef RT2860
54073 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE))
54074 + {
54075 + NICDisableInterrupt(pAd);
54076 + }
54077 +
54078 + // Disable Rx, register value supposed will remain after reset
54079 + NICIssueReset(pAd);
54080 +
54081 + // Free IRQ
54082 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE))
54083 + {
54084 + // Deregister interrupt function
54085 + RT28XX_IRQ_RELEASE(net_dev)
54086 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE);
54087 + }
54088 +#endif // RT2860 //
54089 +
54090 +
54091 + // Free Ring or USB buffers
54092 + RTMPFreeTxRxRingMemory(pAd);
54093 +
54094 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS);
54095 +
54096 +#ifdef DOT11_N_SUPPORT
54097 + // Free BA reorder resource
54098 + ba_reordering_resource_release(pAd);
54099 +#endif // DOT11_N_SUPPORT //
54100 +
54101 +
54102 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_START_UP);
54103 +
54104 + return 0; // close ok
54105 +} /* End of rt28xx_close */
54106 +
54107 +static int rt28xx_init(IN struct net_device *net_dev)
54108 +{
54109 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)net_dev->priv;
54110 + UINT index;
54111 + UCHAR TmpPhy;
54112 + NDIS_STATUS Status;
54113 + UINT32 MacCsr0 = 0;
54114 +
54115 +
54116 +#ifdef DOT11_N_SUPPORT
54117 + // Allocate BA Reordering memory
54118 + ba_reordering_resource_init(pAd, MAX_REORDERING_MPDU_NUM);
54119 +#endif // DOT11_N_SUPPORT //
54120 +
54121 + // Make sure MAC gets ready.
54122 + index = 0;
54123 + do
54124 + {
54125 + RTMP_IO_READ32(pAd, MAC_CSR0, &MacCsr0);
54126 + pAd->MACVersion = MacCsr0;
54127 +
54128 + if ((pAd->MACVersion != 0x00) && (pAd->MACVersion != 0xFFFFFFFF))
54129 + break;
54130 +
54131 + RTMPusecDelay(10);
54132 + } while (index++ < 100);
54133 +
54134 + DBGPRINT(RT_DEBUG_TRACE, ("MAC_CSR0 [ Ver:Rev=0x%08x]\n", pAd->MACVersion));
54135 +
54136 + // Disable DMA
54137 + RT28XXDMADisable(pAd);
54138 +
54139 +
54140 + // Load 8051 firmware
54141 + Status = NICLoadFirmware(pAd);
54142 + if (Status != NDIS_STATUS_SUCCESS)
54143 + {
54144 + DBGPRINT_ERR(("NICLoadFirmware failed, Status[=0x%08x]\n", Status));
54145 + goto err1;
54146 + }
54147 +
54148 + NICLoadRateSwitchingParams(pAd);
54149 +
54150 + // Disable interrupts here which is as soon as possible
54151 + // This statement should never be true. We might consider to remove it later
54152 +#ifdef RT2860
54153 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE))
54154 + {
54155 + NICDisableInterrupt(pAd);
54156 + }
54157 +#endif // RT2860 //
54158 +
54159 + Status = RTMPAllocTxRxRingMemory(pAd);
54160 + if (Status != NDIS_STATUS_SUCCESS)
54161 + {
54162 + DBGPRINT_ERR(("RTMPAllocDMAMemory failed, Status[=0x%08x]\n", Status));
54163 + goto err1;
54164 + }
54165 +
54166 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE);
54167 +
54168 + // initialize MLME
54169 + //
54170 +
54171 + Status = MlmeInit(pAd);
54172 + if (Status != NDIS_STATUS_SUCCESS)
54173 + {
54174 + DBGPRINT_ERR(("MlmeInit failed, Status[=0x%08x]\n", Status));
54175 + goto err2;
54176 + }
54177 +
54178 + // Initialize pAd->StaCfg, pAd->ApCfg, pAd->CommonCfg to manufacture default
54179 + //
54180 + UserCfgInit(pAd);
54181 +
54182 +
54183 + RT28XX_TASK_THREAD_INIT(pAd, Status);
54184 + if (Status != NDIS_STATUS_SUCCESS)
54185 + goto err1;
54186 +
54187 + CfgInitHook(pAd);
54188 +
54189 +
54190 +#ifdef BLOCK_NET_IF
54191 + initblockQueueTab(pAd);
54192 +#endif // BLOCK_NET_IF //
54193 +
54194 +#ifdef CONFIG_STA_SUPPORT
54195 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
54196 + NdisAllocateSpinLock(&pAd->MacTabLock);
54197 +#endif // CONFIG_STA_SUPPORT //
54198 +
54199 + MeasureReqTabInit(pAd);
54200 + TpcReqTabInit(pAd);
54201 +
54202 + //
54203 + // Init the hardware, we need to init asic before read registry, otherwise mac register will be reset
54204 + //
54205 + Status = NICInitializeAdapter(pAd, TRUE);
54206 + if (Status != NDIS_STATUS_SUCCESS)
54207 + {
54208 + DBGPRINT_ERR(("NICInitializeAdapter failed, Status[=0x%08x]\n", Status));
54209 + if (Status != NDIS_STATUS_SUCCESS)
54210 + goto err3;
54211 + }
54212 +
54213 + // Read parameters from Config File
54214 + Status = RTMPReadParametersHook(pAd);
54215 +
54216 + printk("1. Phy Mode = %d\n", pAd->CommonCfg.PhyMode);
54217 + if (Status != NDIS_STATUS_SUCCESS)
54218 + {
54219 + DBGPRINT_ERR(("NICReadRegParameters failed, Status[=0x%08x]\n",Status));
54220 + goto err4;
54221 + }
54222 +
54223 +
54224 +
54225 + //Init Ba Capability parameters.
54226 +#ifdef DOT11_N_SUPPORT
54227 + pAd->CommonCfg.DesiredHtPhy.MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity;
54228 + pAd->CommonCfg.DesiredHtPhy.AmsduEnable = (USHORT)pAd->CommonCfg.BACapability.field.AmsduEnable;
54229 + pAd->CommonCfg.DesiredHtPhy.AmsduSize = (USHORT)pAd->CommonCfg.BACapability.field.AmsduSize;
54230 + pAd->CommonCfg.DesiredHtPhy.MimoPs = (USHORT)pAd->CommonCfg.BACapability.field.MMPSmode;
54231 + // UPdata to HT IE
54232 + pAd->CommonCfg.HtCapability.HtCapInfo.MimoPs = (USHORT)pAd->CommonCfg.BACapability.field.MMPSmode;
54233 + pAd->CommonCfg.HtCapability.HtCapInfo.AMsduSize = (USHORT)pAd->CommonCfg.BACapability.field.AmsduSize;
54234 + pAd->CommonCfg.HtCapability.HtCapParm.MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity;
54235 +#endif // DOT11_N_SUPPORT //
54236 +
54237 + printk("2. Phy Mode = %d\n", pAd->CommonCfg.PhyMode);
54238 +
54239 + // We should read EEPROM for all cases. rt2860b
54240 + NICReadEEPROMParameters(pAd, mac);
54241 +
54242 + printk("3. Phy Mode = %d\n", pAd->CommonCfg.PhyMode);
54243 +
54244 + NICInitAsicFromEEPROM(pAd); //rt2860b
54245 +
54246 + // Set PHY to appropriate mode
54247 + TmpPhy = pAd->CommonCfg.PhyMode;
54248 + pAd->CommonCfg.PhyMode = 0xff;
54249 + RTMPSetPhyMode(pAd, TmpPhy);
54250 +#ifdef DOT11_N_SUPPORT
54251 + SetCommonHT(pAd);
54252 +#endif // DOT11_N_SUPPORT //
54253 +
54254 + // No valid channels.
54255 + if (pAd->ChannelListNum == 0)
54256 + {
54257 + printk("Wrong configuration. No valid channel found. Check \"ContryCode\" and \"ChannelGeography\" setting.\n");
54258 + goto err4;
54259 + }
54260 +
54261 +#ifdef DOT11_N_SUPPORT
54262 + printk("MCS Set = %02x %02x %02x %02x %02x\n", pAd->CommonCfg.HtCapability.MCSSet[0],
54263 + pAd->CommonCfg.HtCapability.MCSSet[1], pAd->CommonCfg.HtCapability.MCSSet[2],
54264 + pAd->CommonCfg.HtCapability.MCSSet[3], pAd->CommonCfg.HtCapability.MCSSet[4]);
54265 +#endif // DOT11_N_SUPPORT //
54266 +
54267 +#ifdef IKANOS_VX_1X0
54268 + VR_IKANOS_FP_Init(pAd->ApCfg.BssidNum, pAd->PermanentAddress);
54269 +#endif // IKANOS_VX_1X0 //
54270 +
54271 + //
54272 + // Initialize RF register to default value
54273 + //
54274 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
54275 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
54276 +
54277 + // 8051 firmware require the signal during booting time.
54278 + AsicSendCommandToMcu(pAd, 0x72, 0xFF, 0x00, 0x00);
54279 +
54280 + if (pAd && (Status != NDIS_STATUS_SUCCESS))
54281 + {
54282 + //
54283 + // Undo everything if it failed
54284 + //
54285 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE))
54286 + {
54287 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE);
54288 + }
54289 + }
54290 + else if (pAd)
54291 + {
54292 + // Microsoft HCT require driver send a disconnect event after driver initialization.
54293 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
54294 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_MEDIA_STATE_CHANGE);
54295 + DBGPRINT(RT_DEBUG_TRACE, ("NDIS_STATUS_MEDIA_DISCONNECT Event B!\n"));
54296 +
54297 +
54298 + }// end of else
54299 +
54300 +
54301 + DBGPRINT_S(Status, ("<==== RTMPInitialize, Status=%x\n", Status));
54302 +
54303 + return TRUE;
54304 +
54305 +
54306 +err4:
54307 +err3:
54308 + MlmeHalt(pAd);
54309 +err2:
54310 + RTMPFreeTxRxRingMemory(pAd);
54311 +err1:
54312 +
54313 +#ifdef DOT11_N_SUPPORT
54314 + os_free_mem(pAd, pAd->mpdu_blk_pool.mem); // free BA pool
54315 +#endif // DOT11_N_SUPPORT //
54316 + RT28XX_IRQ_RELEASE(net_dev);
54317 +
54318 + // shall not set priv to NULL here because the priv didn't been free yet.
54319 + //net_dev->priv = 0;
54320 +#ifdef INF_AMAZON_SE
54321 +err0:
54322 +#endif // INF_AMAZON_SE //
54323 + printk("!!! %s Initialized fail !!!\n", RT28xx_CHIP_NAME);
54324 + return FALSE;
54325 +} /* End of rt28xx_init */
54326 +
54327 +
54328 +/*
54329 +========================================================================
54330 +Routine Description:
54331 + Open raxx interface.
54332 +
54333 +Arguments:
54334 + *net_dev the raxx interface pointer
54335 +
54336 +Return Value:
54337 + 0 Open OK
54338 + otherwise Open Fail
54339 +
54340 +Note:
54341 +========================================================================
54342 +*/
54343 +int rt28xx_open(IN PNET_DEV dev)
54344 +{
54345 + struct net_device * net_dev = (struct net_device *)dev;
54346 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)net_dev->priv;
54347 + int retval = 0;
54348 + POS_COOKIE pObj;
54349 +
54350 +
54351 + // Sanity check for pAd
54352 + if (pAd == NULL)
54353 + {
54354 + /* if 1st open fail, pAd will be free;
54355 + So the net_dev->priv will be NULL in 2rd open */
54356 + return -1;
54357 + }
54358 +
54359 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
54360 + if (pAd->OpMode == OPMODE_AP)
54361 + {
54362 + CW_MAX_IN_BITS = 6;
54363 + }
54364 + else if (pAd->OpMode == OPMODE_STA)
54365 + {
54366 + CW_MAX_IN_BITS = 10;
54367 + }
54368 +
54369 +#if WIRELESS_EXT >= 12
54370 + if (net_dev->priv_flags == INT_MAIN)
54371 + {
54372 + if (pAd->OpMode == OPMODE_AP)
54373 + net_dev->wireless_handlers = (struct iw_handler_def *) &rt28xx_ap_iw_handler_def;
54374 + else if (pAd->OpMode == OPMODE_STA)
54375 + net_dev->wireless_handlers = (struct iw_handler_def *) &rt28xx_iw_handler_def;
54376 + }
54377 +#endif // WIRELESS_EXT >= 12 //
54378 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
54379 +
54380 +#ifdef CONFIG_STA_SUPPORT
54381 +#ifdef RT2860
54382 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
54383 + {
54384 + // If dirver doesn't wake up firmware here,
54385 + // NICLoadFirmware will hang forever when interface is up again.
54386 + // RT2860 PCI
54387 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE) &&
54388 + OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
54389 + {
54390 + AUTO_WAKEUP_STRUC AutoWakeupCfg;
54391 + AsicForceWakeup(pAd, TRUE);
54392 + AutoWakeupCfg.word = 0;
54393 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
54394 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
54395 + }
54396 + }
54397 +#endif // RT2860 //
54398 +#endif // CONFIG_STA_SUPPORT //
54399 +
54400 + // Init
54401 + pObj = (POS_COOKIE)pAd->OS_Cookie;
54402 +
54403 + // reset Adapter flags
54404 + RTMP_CLEAR_FLAGS(pAd);
54405 +
54406 + // Request interrupt service routine for PCI device
54407 + // register the interrupt routine with the os
54408 + RT28XX_IRQ_REQUEST(net_dev);
54409 +
54410 +
54411 + // Init BssTab & ChannelInfo tabbles for auto channel select.
54412 +
54413 +
54414 + // Chip & other init
54415 + if (rt28xx_init(net_dev) == FALSE)
54416 + goto err;
54417 +
54418 +#ifdef CONFIG_STA_SUPPORT
54419 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
54420 + {
54421 + NdisZeroMemory(pAd->StaCfg.dev_name, 16);
54422 + NdisMoveMemory(pAd->StaCfg.dev_name, net_dev->name, strlen(net_dev->name));
54423 + }
54424 +#endif // CONFIG_STA_SUPPORT //
54425 +
54426 + // Set up the Mac address
54427 + NdisMoveMemory(net_dev->dev_addr, (void *) pAd->CurrentAddress, 6);
54428 +
54429 + // Init IRQ parameters
54430 + RT28XX_IRQ_INIT(pAd);
54431 +
54432 + // Various AP function init
54433 +
54434 +#ifdef CONFIG_STA_SUPPORT
54435 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
54436 + {
54437 +#ifdef WPA_SUPPLICANT_SUPPORT
54438 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
54439 + {
54440 + union iwreq_data wrqu;
54441 + // send wireless event to wpa_supplicant for infroming interface down.
54442 + memset(&wrqu, 0, sizeof(wrqu));
54443 + wrqu.data.flags = RT_INTERFACE_UP;
54444 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
54445 + }
54446 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
54447 +#endif // WPA_SUPPLICANT_SUPPORT //
54448 +
54449 + }
54450 +#endif // CONFIG_STA_SUPPORT //
54451 +
54452 + // Enable Interrupt
54453 + RT28XX_IRQ_ENABLE(pAd);
54454 +
54455 + // Now Enable RxTx
54456 + RTMPEnableRxTx(pAd);
54457 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_START_UP);
54458 +
54459 + {
54460 + UINT32 reg = 0;
54461 + RTMP_IO_READ32(pAd, 0x1300, &reg); // clear garbage interrupts
54462 + printk("0x1300 = %08x\n", reg);
54463 + }
54464 +
54465 +#ifdef CONFIG_STA_SUPPORT
54466 +#ifdef RT2860
54467 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
54468 + RTMPInitPCIeLinkCtrlValue(pAd);
54469 +#endif // RT2860 //
54470 +#endif // CONFIG_STA_SUPPORT //
54471 +
54472 + return (retval);
54473 +
54474 +err:
54475 + return (-1);
54476 +} /* End of rt28xx_open */
54477 +
54478 +
54479 +/* Must not be called for mdev and apdev */
54480 +static NDIS_STATUS rt_ieee80211_if_setup(struct net_device *dev, PRTMP_ADAPTER pAd)
54481 +{
54482 + NDIS_STATUS Status;
54483 + INT i=0;
54484 + CHAR slot_name[IFNAMSIZ];
54485 + struct net_device *device;
54486 +
54487 +
54488 + //ether_setup(dev);
54489 + dev->hard_start_xmit = rt28xx_send_packets;
54490 +
54491 +#ifdef IKANOS_VX_1X0
54492 + dev->hard_start_xmit = IKANOS_DataFramesTx;
54493 +#endif // IKANOS_VX_1X0 //
54494 +
54495 +#ifdef CONFIG_STA_SUPPORT
54496 +#if WIRELESS_EXT >= 12
54497 + if (pAd->OpMode == OPMODE_STA)
54498 + {
54499 + dev->wireless_handlers = &rt28xx_iw_handler_def;
54500 + }
54501 +#endif //WIRELESS_EXT >= 12
54502 +#endif // CONFIG_STA_SUPPORT //
54503 +
54504 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
54505 +#if WIRELESS_EXT >= 12
54506 + if (pAd->OpMode == OPMODE_AP)
54507 + {
54508 + dev->wireless_handlers = &rt28xx_ap_iw_handler_def;
54509 + }
54510 +#endif //WIRELESS_EXT >= 12
54511 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
54512 +
54513 +#if WIRELESS_EXT < 21
54514 + dev->get_wireless_stats = rt28xx_get_wireless_stats;
54515 +#endif
54516 + dev->get_stats = RT28xx_get_ether_stats;
54517 + dev->open = MainVirtualIF_open; //rt28xx_open;
54518 + dev->stop = MainVirtualIF_close; //rt28xx_close;
54519 + dev->priv_flags = INT_MAIN;
54520 + dev->do_ioctl = rt28xx_ioctl;
54521 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,24)
54522 + dev->validate_addr = NULL;
54523 +#endif
54524 + // find available device name
54525 + for (i = 0; i < 8; i++)
54526 + {
54527 +#ifdef MULTIPLE_CARD_SUPPORT
54528 + if (pAd->MC_RowID >= 0)
54529 + sprintf(slot_name, "ra%02d_%d", pAd->MC_RowID, i);
54530 + else
54531 +#endif // MULTIPLE_CARD_SUPPORT //
54532 + sprintf(slot_name, "ra%d", i);
54533 +
54534 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
54535 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,24)
54536 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,26)
54537 + device = dev_get_by_name(dev_net(dev), slot_name);
54538 +#else
54539 + device = dev_get_by_name(dev->nd_net, slot_name);
54540 +#endif
54541 +#else
54542 + device = dev_get_by_name(slot_name);
54543 +#endif
54544 + if (device != NULL) dev_put(device);
54545 +#else
54546 + for (device = dev_base; device != NULL; device = device->next)
54547 + {
54548 + if (strncmp(device->name, slot_name, 4) == 0)
54549 + break;
54550 + }
54551 +#endif
54552 + if(device == NULL)
54553 + break;
54554 + }
54555 +
54556 + if(i == 8)
54557 + {
54558 + DBGPRINT(RT_DEBUG_ERROR, ("No available slot name\n"));
54559 + Status = NDIS_STATUS_FAILURE;
54560 + }
54561 + else
54562 + {
54563 +#ifdef MULTIPLE_CARD_SUPPORT
54564 + if (pAd->MC_RowID >= 0)
54565 + sprintf(dev->name, "ra%02d_%d", pAd->MC_RowID, i);
54566 + else
54567 +#endif // MULTIPLE_CARD_SUPPORT //
54568 + sprintf(dev->name, "ra%d", i);
54569 + Status = NDIS_STATUS_SUCCESS;
54570 + }
54571 +
54572 + return Status;
54573 +
54574 +}
54575 +
54576 +
54577 +#ifdef MULTIPLE_CARD_SUPPORT
54578 +/*
54579 +========================================================================
54580 +Routine Description:
54581 + Get card profile path.
54582 +
54583 +Arguments:
54584 + pAd
54585 +
54586 +Return Value:
54587 + TRUE - Find a card profile
54588 + FALSE - use default profile
54589 +
54590 +Note:
54591 +========================================================================
54592 +*/
54593 +extern INT RTMPGetKeyParameter(
54594 + IN PCHAR key,
54595 + OUT PCHAR dest,
54596 + IN INT destsize,
54597 + IN PCHAR buffer);
54598 +
54599 +BOOLEAN RTMP_CardInfoRead(
54600 + IN PRTMP_ADAPTER pAd)
54601 +{
54602 +#define MC_SELECT_CARDID 0 /* use CARD ID (0 ~ 31) to identify different cards */
54603 +#define MC_SELECT_MAC 1 /* use CARD MAC to identify different cards */
54604 +#define MC_SELECT_CARDTYPE 2 /* use CARD type (abgn or bgn) to identify different cards */
54605 +
54606 +#define LETTER_CASE_TRANSLATE(txt_p, card_id) \
54607 + { UINT32 _len; char _char; \
54608 + for(_len=0; _len<strlen(card_id); _len++) { \
54609 + _char = *(txt_p + _len); \
54610 + if (('A' <= _char) && (_char <= 'Z')) \
54611 + *(txt_p+_len) = 'a'+(_char-'A'); \
54612 + } }
54613 +
54614 + struct file *srcf;
54615 + INT retval, orgfsuid, orgfsgid;
54616 + mm_segment_t orgfs;
54617 + CHAR *buffer, *tmpbuf, card_id_buf[30], RFIC_word[30];
54618 + BOOLEAN flg_match_ok = FALSE;
54619 + INT32 card_select_method;
54620 + INT32 card_free_id, card_nouse_id, card_same_mac_id, card_match_id;
54621 + EEPROM_ANTENNA_STRUC antenna;
54622 + USHORT addr01, addr23, addr45;
54623 + UINT8 mac[6];
54624 + UINT32 data, card_index;
54625 + UCHAR *start_ptr;
54626 +
54627 +
54628 + // init
54629 + buffer = kmalloc(MAX_INI_BUFFER_SIZE, MEM_ALLOC_FLAG);
54630 + if (buffer == NULL)
54631 + return FALSE;
54632 +
54633 + tmpbuf = kmalloc(MAX_PARAM_BUFFER_SIZE, MEM_ALLOC_FLAG);
54634 + if(tmpbuf == NULL)
54635 + {
54636 + kfree(buffer);
54637 + return NDIS_STATUS_FAILURE;
54638 + }
54639 +
54640 + orgfsuid = current->fsuid;
54641 + orgfsgid = current->fsgid;
54642 + current->fsuid = current->fsgid = 0;
54643 + orgfs = get_fs();
54644 + set_fs(KERNEL_DS);
54645 +
54646 + // get RF IC type
54647 + RTMP_IO_READ32(pAd, E2PROM_CSR, &data);
54648 +
54649 + if ((data & 0x30) == 0)
54650 + pAd->EEPROMAddressNum = 6; // 93C46
54651 + else if ((data & 0x30) == 0x10)
54652 + pAd->EEPROMAddressNum = 8; // 93C66
54653 + else
54654 + pAd->EEPROMAddressNum = 8; // 93C86
54655 +
54656 + RT28xx_EEPROM_READ16(pAd, EEPROM_NIC1_OFFSET, antenna.word);
54657 +
54658 + if ((antenna.field.RfIcType == RFIC_2850) ||
54659 + (antenna.field.RfIcType == RFIC_2750))
54660 + {
54661 + /* ABGN card */
54662 + strcpy(RFIC_word, "abgn");
54663 + }
54664 + else
54665 + {
54666 + /* BGN card */
54667 + strcpy(RFIC_word, "bgn");
54668 + }
54669 +
54670 + // get MAC address
54671 + RT28xx_EEPROM_READ16(pAd, 0x04, addr01);
54672 + RT28xx_EEPROM_READ16(pAd, 0x06, addr23);
54673 + RT28xx_EEPROM_READ16(pAd, 0x08, addr45);
54674 +
54675 + mac[0] = (UCHAR)(addr01 & 0xff);
54676 + mac[1] = (UCHAR)(addr01 >> 8);
54677 + mac[2] = (UCHAR)(addr23 & 0xff);
54678 + mac[3] = (UCHAR)(addr23 >> 8);
54679 + mac[4] = (UCHAR)(addr45 & 0xff);
54680 + mac[5] = (UCHAR)(addr45 >> 8);
54681 +
54682 + // open card information file
54683 + srcf = filp_open(CARD_INFO_PATH, O_RDONLY, 0);
54684 + if (IS_ERR(srcf))
54685 + {
54686 + /* card information file does not exist */
54687 + DBGPRINT(RT_DEBUG_TRACE,
54688 + ("--> Error %ld opening %s\n", -PTR_ERR(srcf), CARD_INFO_PATH));
54689 + return FALSE;
54690 + }
54691 +
54692 + if (srcf->f_op && srcf->f_op->read)
54693 + {
54694 + /* card information file exists so reading the card information */
54695 + memset(buffer, 0x00, MAX_INI_BUFFER_SIZE);
54696 + retval = srcf->f_op->read(srcf, buffer, MAX_INI_BUFFER_SIZE, &srcf->f_pos);
54697 + if (retval < 0)
54698 + {
54699 + /* read fail */
54700 + DBGPRINT(RT_DEBUG_TRACE,
54701 + ("--> Read %s error %d\n", CARD_INFO_PATH, -retval));
54702 + }
54703 + else
54704 + {
54705 + /* get card selection method */
54706 + memset(tmpbuf, 0x00, MAX_PARAM_BUFFER_SIZE);
54707 + card_select_method = MC_SELECT_CARDTYPE; // default
54708 +
54709 + if (RTMPGetKeyParameter("SELECT", tmpbuf, 256, buffer))
54710 + {
54711 + if (strcmp(tmpbuf, "CARDID") == 0)
54712 + card_select_method = MC_SELECT_CARDID;
54713 + else if (strcmp(tmpbuf, "MAC") == 0)
54714 + card_select_method = MC_SELECT_MAC;
54715 + else if (strcmp(tmpbuf, "CARDTYPE") == 0)
54716 + card_select_method = MC_SELECT_CARDTYPE;
54717 + }
54718 +
54719 + DBGPRINT(RT_DEBUG_TRACE,
54720 + ("MC> Card Selection = %d\n", card_select_method));
54721 +
54722 + // init
54723 + card_free_id = -1;
54724 + card_nouse_id = -1;
54725 + card_same_mac_id = -1;
54726 + card_match_id = -1;
54727 +
54728 + // search current card information records
54729 + for(card_index=0;
54730 + card_index<MAX_NUM_OF_MULTIPLE_CARD;
54731 + card_index++)
54732 + {
54733 + if ((*(UINT32 *)&MC_CardMac[card_index][0] == 0) &&
54734 + (*(UINT16 *)&MC_CardMac[card_index][4] == 0))
54735 + {
54736 + // MAC is all-0 so the entry is available
54737 + MC_CardUsed[card_index] = 0;
54738 +
54739 + if (card_free_id < 0)
54740 + card_free_id = card_index; // 1st free entry
54741 + }
54742 + else
54743 + {
54744 + if (memcmp(MC_CardMac[card_index], mac, 6) == 0)
54745 + {
54746 + // we find the entry with same MAC
54747 + if (card_same_mac_id < 0)
54748 + card_same_mac_id = card_index; // 1st same entry
54749 + }
54750 + else
54751 + {
54752 + // MAC is not all-0 but used flag == 0
54753 + if ((MC_CardUsed[card_index] == 0) &&
54754 + (card_nouse_id < 0))
54755 + {
54756 + card_nouse_id = card_index; // 1st available entry
54757 + }
54758 + }
54759 + }
54760 + }
54761 +
54762 + DBGPRINT(RT_DEBUG_TRACE,
54763 + ("MC> Free = %d, Same = %d, NOUSE = %d\n",
54764 + card_free_id, card_same_mac_id, card_nouse_id));
54765 +
54766 + if ((card_same_mac_id >= 0) &&
54767 + ((card_select_method == MC_SELECT_CARDID) ||
54768 + (card_select_method == MC_SELECT_CARDTYPE)))
54769 + {
54770 + // same MAC entry is found
54771 + card_match_id = card_same_mac_id;
54772 +
54773 + if (card_select_method == MC_SELECT_CARDTYPE)
54774 + {
54775 + // for CARDTYPE
54776 + sprintf(card_id_buf, "%02dCARDTYPE%s",
54777 + card_match_id, RFIC_word);
54778 +
54779 + if ((start_ptr=rtstrstruncasecmp(buffer, card_id_buf)) != NULL)
54780 + {
54781 + // we found the card ID
54782 + LETTER_CASE_TRANSLATE(start_ptr, card_id_buf);
54783 + }
54784 + }
54785 + }
54786 + else
54787 + {
54788 + // the card is 1st plug-in, try to find the match card profile
54789 + switch(card_select_method)
54790 + {
54791 + case MC_SELECT_CARDID: // CARDID
54792 + default:
54793 + if (card_free_id >= 0)
54794 + card_match_id = card_free_id;
54795 + else
54796 + card_match_id = card_nouse_id;
54797 + break;
54798 +
54799 + case MC_SELECT_MAC: // MAC
54800 + sprintf(card_id_buf, "MAC%02x:%02x:%02x:%02x:%02x:%02x",
54801 + mac[0], mac[1], mac[2],
54802 + mac[3], mac[4], mac[5]);
54803 +
54804 + /* try to find the key word in the card file */
54805 + if ((start_ptr=rtstrstruncasecmp(buffer, card_id_buf)) != NULL)
54806 + {
54807 + LETTER_CASE_TRANSLATE(start_ptr, card_id_buf);
54808 +
54809 + /* get the row ID (2 ASCII characters) */
54810 + start_ptr -= 2;
54811 + card_id_buf[0] = *(start_ptr);
54812 + card_id_buf[1] = *(start_ptr+1);
54813 + card_id_buf[2] = 0x00;
54814 +
54815 + card_match_id = simple_strtol(card_id_buf, 0, 10);
54816 + }
54817 + break;
54818 +
54819 + case MC_SELECT_CARDTYPE: // CARDTYPE
54820 + card_nouse_id = -1;
54821 +
54822 + for(card_index=0;
54823 + card_index<MAX_NUM_OF_MULTIPLE_CARD;
54824 + card_index++)
54825 + {
54826 + sprintf(card_id_buf, "%02dCARDTYPE%s",
54827 + card_index, RFIC_word);
54828 +
54829 + if ((start_ptr=rtstrstruncasecmp(buffer,
54830 + card_id_buf)) != NULL)
54831 + {
54832 + LETTER_CASE_TRANSLATE(start_ptr, card_id_buf);
54833 +
54834 + if (MC_CardUsed[card_index] == 0)
54835 + {
54836 + /* current the card profile is not used */
54837 + if ((*(UINT32 *)&MC_CardMac[card_index][0] == 0) &&
54838 + (*(UINT16 *)&MC_CardMac[card_index][4] == 0))
54839 + {
54840 + // find it and no previous card use it
54841 + card_match_id = card_index;
54842 + break;
54843 + }
54844 + else
54845 + {
54846 + // ever a card use it
54847 + if (card_nouse_id < 0)
54848 + card_nouse_id = card_index;
54849 + }
54850 + }
54851 + }
54852 + }
54853 +
54854 + // if not find a free one, use the available one
54855 + if (card_match_id < 0)
54856 + card_match_id = card_nouse_id;
54857 + break;
54858 + }
54859 + }
54860 +
54861 + if (card_match_id >= 0)
54862 + {
54863 + // make up search keyword
54864 + switch(card_select_method)
54865 + {
54866 + case MC_SELECT_CARDID: // CARDID
54867 + sprintf(card_id_buf, "%02dCARDID", card_match_id);
54868 + break;
54869 +
54870 + case MC_SELECT_MAC: // MAC
54871 + sprintf(card_id_buf,
54872 + "%02dmac%02x:%02x:%02x:%02x:%02x:%02x",
54873 + card_match_id,
54874 + mac[0], mac[1], mac[2],
54875 + mac[3], mac[4], mac[5]);
54876 + break;
54877 +
54878 + case MC_SELECT_CARDTYPE: // CARDTYPE
54879 + default:
54880 + sprintf(card_id_buf, "%02dcardtype%s",
54881 + card_match_id, RFIC_word);
54882 + break;
54883 + }
54884 +
54885 + DBGPRINT(RT_DEBUG_TRACE, ("Search Keyword = %s\n", card_id_buf));
54886 +
54887 + // read card file path
54888 + if (RTMPGetKeyParameter(card_id_buf, tmpbuf, 256, buffer))
54889 + {
54890 + if (strlen(tmpbuf) < sizeof(pAd->MC_FileName))
54891 + {
54892 + // backup card information
54893 + pAd->MC_RowID = card_match_id; /* base 0 */
54894 + MC_CardUsed[card_match_id] = 1;
54895 + memcpy(MC_CardMac[card_match_id], mac, sizeof(mac));
54896 +
54897 + // backup card file path
54898 + NdisMoveMemory(pAd->MC_FileName, tmpbuf , strlen(tmpbuf));
54899 + pAd->MC_FileName[strlen(tmpbuf)] = '\0';
54900 + flg_match_ok = TRUE;
54901 +
54902 + DBGPRINT(RT_DEBUG_TRACE,
54903 + ("Card Profile Name = %s\n", pAd->MC_FileName));
54904 + }
54905 + else
54906 + {
54907 + DBGPRINT(RT_DEBUG_ERROR,
54908 + ("Card Profile Name length too large!\n"));
54909 + }
54910 + }
54911 + else
54912 + {
54913 + DBGPRINT(RT_DEBUG_ERROR,
54914 + ("Can not find search key word in card.dat!\n"));
54915 + }
54916 +
54917 + if ((flg_match_ok != TRUE) &&
54918 + (card_match_id < MAX_NUM_OF_MULTIPLE_CARD))
54919 + {
54920 + MC_CardUsed[card_match_id] = 0;
54921 + memset(MC_CardMac[card_match_id], 0, sizeof(mac));
54922 + }
54923 + } // if (card_match_id >= 0)
54924 + }
54925 + }
54926 +
54927 + // close file
54928 + retval = filp_close(srcf, NULL);
54929 + set_fs(orgfs);
54930 + current->fsuid = orgfsuid;
54931 + current->fsgid = orgfsgid;
54932 + kfree(buffer);
54933 + kfree(tmpbuf);
54934 + return flg_match_ok;
54935 +}
54936 +#endif // MULTIPLE_CARD_SUPPORT //
54937 +
54938 +
54939 +/*
54940 +========================================================================
54941 +Routine Description:
54942 + Probe RT28XX chipset.
54943 +
54944 +Arguments:
54945 + _dev_p Point to the PCI or USB device
54946 + _dev_id_p Point to the PCI or USB device ID
54947 +
54948 +Return Value:
54949 + 0 Probe OK
54950 + -ENODEV Probe Fail
54951 +
54952 +Note:
54953 +========================================================================
54954 +*/
54955 +INT __devinit rt28xx_probe(
54956 + IN void *_dev_p,
54957 + IN void *_dev_id_p,
54958 + IN UINT argc,
54959 + OUT PRTMP_ADAPTER *ppAd)
54960 +{
54961 + struct net_device *net_dev;
54962 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) NULL;
54963 + INT status;
54964 + PVOID handle;
54965 +#ifdef RT2860
54966 + struct pci_dev *dev_p = (struct pci_dev *)_dev_p;
54967 +#endif // RT2860 //
54968 +
54969 +
54970 +#ifdef CONFIG_STA_SUPPORT
54971 + DBGPRINT(RT_DEBUG_TRACE, ("STA Driver version-%s\n", STA_DRIVER_VERSION));
54972 +#endif // CONFIG_STA_SUPPORT //
54973 +
54974 +#if LINUX_VERSION_CODE <= 0x20402 // Red Hat 7.1
54975 + net_dev = alloc_netdev(sizeof(PRTMP_ADAPTER), "eth%d", ether_setup);
54976 +#else
54977 + net_dev = alloc_etherdev(sizeof(PRTMP_ADAPTER));
54978 +#endif
54979 + if (net_dev == NULL)
54980 + {
54981 + printk("alloc_netdev failed\n");
54982 +
54983 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
54984 +#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15)
54985 + module_put(THIS_MODULE);
54986 +#endif //LINUX_VERSION_CODE < KERNEL_VERSION(2,6,15)
54987 +#else
54988 + MOD_DEC_USE_COUNT;
54989 +#endif
54990 + goto err_out;
54991 + }
54992 +
54993 +#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24)
54994 + SET_MODULE_OWNER(net_dev);
54995 +#endif
54996 +
54997 + netif_stop_queue(net_dev);
54998 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
54999 +/* for supporting Network Manager */
55000 +/* Set the sysfs physical device reference for the network logical device
55001 + * if set prior to registration will cause a symlink during initialization.
55002 + */
55003 +#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0))
55004 + SET_NETDEV_DEV(net_dev, &(dev_p->dev));
55005 +#endif
55006 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
55007 +
55008 + // Allocate RTMP_ADAPTER miniport adapter structure
55009 + handle = kmalloc(sizeof(struct os_cookie), GFP_KERNEL);
55010 + RT28XX_HANDLE_DEV_ASSIGN(handle, dev_p);
55011 +
55012 + status = RTMPAllocAdapterBlock(handle, &pAd);
55013 + if (status != NDIS_STATUS_SUCCESS)
55014 + goto err_out_free_netdev;
55015 +
55016 + net_dev->priv = (PVOID)pAd;
55017 + pAd->net_dev = net_dev; // must be before RT28XXNetDevInit()
55018 +
55019 + RT28XXNetDevInit(_dev_p, net_dev, pAd);
55020 +
55021 +#ifdef CONFIG_STA_SUPPORT
55022 + pAd->StaCfg.OriDevType = net_dev->type;
55023 +#endif // CONFIG_STA_SUPPORT //
55024 +
55025 + // Post config
55026 +#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
55027 + if (RT28XXProbePostConfig(_dev_p, pAd, argc) == FALSE)
55028 + goto err_out_unmap;
55029 +#else
55030 + if (RT28XXProbePostConfig(_dev_p, pAd, 0) == FALSE)
55031 + goto err_out_unmap;
55032 +#endif // LINUX_VERSION_CODE //
55033 +
55034 +#ifdef CONFIG_STA_SUPPORT
55035 + pAd->OpMode = OPMODE_STA;
55036 +#endif // CONFIG_STA_SUPPORT //
55037 +
55038 +
55039 +#ifdef MULTIPLE_CARD_SUPPORT
55040 + // find its profile path
55041 + pAd->MC_RowID = -1; // use default profile path
55042 + RTMP_CardInfoRead(pAd);
55043 +
55044 + if (pAd->MC_RowID == -1)
55045 +#ifdef CONFIG_STA_SUPPORT
55046 + strcpy(pAd->MC_FileName, STA_PROFILE_PATH);
55047 +#endif // CONFIG_STA_SUPPORT //
55048 +
55049 + DBGPRINT(RT_DEBUG_TRACE,
55050 + ("MC> ROW = %d, PATH = %s\n", pAd->MC_RowID, pAd->MC_FileName));
55051 +#endif // MULTIPLE_CARD_SUPPORT //
55052 +
55053 + // sample move
55054 + if (rt_ieee80211_if_setup(net_dev, pAd) != NDIS_STATUS_SUCCESS)
55055 + goto err_out_unmap;
55056 +
55057 + // Register this device
55058 + status = register_netdev(net_dev);
55059 + if (status)
55060 + goto err_out_unmap;
55061 +
55062 + // Set driver data
55063 + RT28XX_DRVDATA_SET(_dev_p);
55064 +
55065 + *ppAd = pAd;
55066 + return 0; // probe ok
55067 +
55068 +
55069 + /* --------------------------- ERROR HANDLE --------------------------- */
55070 +err_out_unmap:
55071 + RTMPFreeAdapter(pAd);
55072 + RT28XX_UNMAP();
55073 +
55074 +err_out_free_netdev:
55075 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
55076 + free_netdev(net_dev);
55077 +#else
55078 + kfree(net_dev);
55079 +#endif
55080 +
55081 +err_out:
55082 + RT28XX_PUT_DEVICE(dev_p);
55083 +
55084 +#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0)
55085 + return (LONG)NULL;
55086 +#else
55087 + return -ENODEV; /* probe fail */
55088 +#endif // LINUX_VERSION_CODE //
55089 +} /* End of rt28xx_probe */
55090 +
55091 +
55092 +/*
55093 +========================================================================
55094 +Routine Description:
55095 + The entry point for Linux kernel sent packet to our driver.
55096 +
55097 +Arguments:
55098 + sk_buff *skb the pointer refer to a sk_buffer.
55099 +
55100 +Return Value:
55101 + 0
55102 +
55103 +Note:
55104 + This function is the entry point of Tx Path for Os delivery packet to
55105 + our driver. You only can put OS-depened & STA/AP common handle procedures
55106 + in here.
55107 +========================================================================
55108 +*/
55109 +int rt28xx_packet_xmit(struct sk_buff *skb)
55110 +{
55111 + struct net_device *net_dev = skb->dev;
55112 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) net_dev->priv;
55113 + int status = 0;
55114 + PNDIS_PACKET pPacket = (PNDIS_PACKET) skb;
55115 +
55116 + /* RT2870STA does this in RTMPSendPackets() */
55117 +#ifdef RALINK_ATE
55118 + if (ATE_ON(pAd))
55119 + {
55120 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_RESOURCES);
55121 + return 0;
55122 + }
55123 +#endif // RALINK_ATE //
55124 +
55125 +#ifdef CONFIG_STA_SUPPORT
55126 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
55127 + {
55128 + // Drop send request since we are in monitor mode
55129 + if (MONITOR_ON(pAd))
55130 + {
55131 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
55132 + goto done;
55133 + }
55134 + }
55135 +#endif // CONFIG_STA_SUPPORT //
55136 +
55137 + // EapolStart size is 18
55138 + if (skb->len < 14)
55139 + {
55140 + //printk("bad packet size: %d\n", pkt->len);
55141 + hex_dump("bad packet", skb->data, skb->len);
55142 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
55143 + goto done;
55144 + }
55145 +
55146 + RTMP_SET_PACKET_5VT(pPacket, 0);
55147 +#ifdef CONFIG_5VT_ENHANCE
55148 + if (*(int*)(skb->cb) == BRIDGE_TAG) {
55149 + RTMP_SET_PACKET_5VT(pPacket, 1);
55150 + }
55151 +#endif
55152 +
55153 +
55154 +
55155 +#ifdef CONFIG_STA_SUPPORT
55156 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
55157 + {
55158 +
55159 + STASendPackets((NDIS_HANDLE)pAd, (PPNDIS_PACKET) &pPacket, 1);
55160 + }
55161 +
55162 +#endif // CONFIG_STA_SUPPORT //
55163 +
55164 + status = 0;
55165 +done:
55166 +
55167 + return status;
55168 +}
55169 +
55170 +
55171 +/*
55172 +========================================================================
55173 +Routine Description:
55174 + Send a packet to WLAN.
55175 +
55176 +Arguments:
55177 + skb_p points to our adapter
55178 + dev_p which WLAN network interface
55179 +
55180 +Return Value:
55181 + 0: transmit successfully
55182 + otherwise: transmit fail
55183 +
55184 +Note:
55185 +========================================================================
55186 +*/
55187 +INT rt28xx_send_packets(
55188 + IN struct sk_buff *skb_p,
55189 + IN struct net_device *net_dev)
55190 +{
55191 + RTMP_ADAPTER *pAd = net_dev->priv;
55192 + if (!(net_dev->flags & IFF_UP))
55193 + {
55194 + RELEASE_NDIS_PACKET(pAd, (PNDIS_PACKET)skb_p, NDIS_STATUS_FAILURE);
55195 + return 0;
55196 + }
55197 +
55198 + NdisZeroMemory((PUCHAR)&skb_p->cb[CB_OFF], 15);
55199 + RTMP_SET_PACKET_NET_DEVICE_MBSSID(skb_p, MAIN_MBSSID);
55200 +
55201 + return rt28xx_packet_xmit(skb_p);
55202 +
55203 +} /* End of MBSS_VirtualIF_PacketSend */
55204 +
55205 +
55206 +
55207 +
55208 +#if LINUX_VERSION_CODE <= 0x20402 // Red Hat 7.1
55209 +struct net_device *alloc_netdev(
55210 + int sizeof_priv,
55211 + const char *mask,
55212 + void (*setup)(struct net_device *))
55213 +{
55214 + struct net_device *dev;
55215 + INT alloc_size;
55216 +
55217 +
55218 + /* ensure 32-byte alignment of the private area */
55219 + alloc_size = sizeof (*dev) + sizeof_priv + 31;
55220 +
55221 + dev = (struct net_device *) kmalloc(alloc_size, GFP_KERNEL);
55222 + if (dev == NULL)
55223 + {
55224 + DBGPRINT(RT_DEBUG_ERROR,
55225 + ("alloc_netdev: Unable to allocate device memory.\n"));
55226 + return NULL;
55227 + }
55228 +
55229 + memset(dev, 0, alloc_size);
55230 +
55231 + if (sizeof_priv)
55232 + dev->priv = (void *) (((long)(dev + 1) + 31) & ~31);
55233 +
55234 + setup(dev);
55235 + strcpy(dev->name, mask);
55236 +
55237 + return dev;
55238 +}
55239 +#endif // LINUX_VERSION_CODE //
55240 +
55241 +
55242 +void CfgInitHook(PRTMP_ADAPTER pAd)
55243 +{
55244 + pAd->bBroadComHT = TRUE;
55245 +} /* End of CfgInitHook */
55246 +
55247 +
55248 +#if WIRELESS_EXT >= 12
55249 +// This function will be called when query /proc
55250 +struct iw_statistics *rt28xx_get_wireless_stats(
55251 + IN struct net_device *net_dev)
55252 +{
55253 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) net_dev->priv;
55254 +
55255 +
55256 + DBGPRINT(RT_DEBUG_TRACE, ("rt28xx_get_wireless_stats --->\n"));
55257 +
55258 + pAd->iw_stats.status = 0; // Status - device dependent for now
55259 +
55260 + // link quality
55261 + pAd->iw_stats.qual.qual = ((pAd->Mlme.ChannelQuality * 12)/10 + 10);
55262 + if(pAd->iw_stats.qual.qual > 100)
55263 + pAd->iw_stats.qual.qual = 100;
55264 +
55265 +#ifdef CONFIG_STA_SUPPORT
55266 + if (pAd->OpMode == OPMODE_STA)
55267 + pAd->iw_stats.qual.level = RTMPMaxRssi(pAd, pAd->StaCfg.RssiSample.LastRssi0, pAd->StaCfg.RssiSample.LastRssi1, pAd->StaCfg.RssiSample.LastRssi2);
55268 +#endif // CONFIG_STA_SUPPORT //
55269 +
55270 + pAd->iw_stats.qual.noise = pAd->BbpWriteLatch[66]; // noise level (dBm)
55271 +
55272 + pAd->iw_stats.qual.noise += 256 - 143;
55273 + pAd->iw_stats.qual.updated = 1; // Flags to know if updated
55274 +#ifdef IW_QUAL_DBM
55275 + pAd->iw_stats.qual.updated |= IW_QUAL_DBM; // Level + Noise are dBm
55276 +#endif // IW_QUAL_DBM //
55277 +
55278 + pAd->iw_stats.discard.nwid = 0; // Rx : Wrong nwid/essid
55279 + pAd->iw_stats.miss.beacon = 0; // Missed beacons/superframe
55280 +
55281 + DBGPRINT(RT_DEBUG_TRACE, ("<--- rt28xx_get_wireless_stats\n"));
55282 + return &pAd->iw_stats;
55283 +} /* End of rt28xx_get_wireless_stats */
55284 +#endif // WIRELESS_EXT //
55285 +
55286 +
55287 +
55288 +void tbtt_tasklet(unsigned long data)
55289 +{
55290 +#define MAX_TX_IN_TBTT (16)
55291 +
55292 +}
55293 +
55294 +INT rt28xx_ioctl(
55295 + IN struct net_device *net_dev,
55296 + IN OUT struct ifreq *rq,
55297 + IN INT cmd)
55298 +{
55299 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
55300 + RTMP_ADAPTER *pAd = NULL;
55301 + INT ret = 0;
55302 +
55303 + if (net_dev->priv_flags == INT_MAIN)
55304 + {
55305 + pAd = net_dev->priv;
55306 + }
55307 + else
55308 + {
55309 + pVirtualAd = net_dev->priv;
55310 + pAd = pVirtualAd->RtmpDev->priv;
55311 + }
55312 +
55313 + if (pAd == NULL)
55314 + {
55315 + /* if 1st open fail, pAd will be free;
55316 + So the net_dev->priv will be NULL in 2rd open */
55317 + return -ENETDOWN;
55318 + }
55319 +
55320 +
55321 +#ifdef CONFIG_STA_SUPPORT
55322 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
55323 + {
55324 + ret = rt28xx_sta_ioctl(net_dev, rq, cmd);
55325 + }
55326 +#endif // CONFIG_STA_SUPPORT //
55327 +
55328 + return ret;
55329 +}
55330 +
55331 +/*
55332 + ========================================================================
55333 +
55334 + Routine Description:
55335 + return ethernet statistics counter
55336 +
55337 + Arguments:
55338 + net_dev Pointer to net_device
55339 +
55340 + Return Value:
55341 + net_device_stats*
55342 +
55343 + Note:
55344 +
55345 + ========================================================================
55346 +*/
55347 +struct net_device_stats *RT28xx_get_ether_stats(
55348 + IN struct net_device *net_dev)
55349 +{
55350 + RTMP_ADAPTER *pAd = NULL;
55351 +
55352 + if (net_dev)
55353 + pAd = net_dev->priv;
55354 +
55355 + if (pAd)
55356 + {
55357 +
55358 + pAd->stats.rx_packets = pAd->WlanCounters.ReceivedFragmentCount.QuadPart;
55359 + pAd->stats.tx_packets = pAd->WlanCounters.TransmittedFragmentCount.QuadPart;
55360 +
55361 + pAd->stats.rx_bytes = pAd->RalinkCounters.ReceivedByteCount;
55362 + pAd->stats.tx_bytes = pAd->RalinkCounters.TransmittedByteCount;
55363 +
55364 + pAd->stats.rx_errors = pAd->Counters8023.RxErrors;
55365 + pAd->stats.tx_errors = pAd->Counters8023.TxErrors;
55366 +
55367 + pAd->stats.rx_dropped = 0;
55368 + pAd->stats.tx_dropped = 0;
55369 +
55370 + pAd->stats.multicast = pAd->WlanCounters.MulticastReceivedFrameCount.QuadPart; // multicast packets received
55371 + pAd->stats.collisions = pAd->Counters8023.OneCollision + pAd->Counters8023.MoreCollisions; // Collision packets
55372 +
55373 + pAd->stats.rx_length_errors = 0;
55374 + pAd->stats.rx_over_errors = pAd->Counters8023.RxNoBuffer; // receiver ring buff overflow
55375 + pAd->stats.rx_crc_errors = 0;//pAd->WlanCounters.FCSErrorCount; // recved pkt with crc error
55376 + pAd->stats.rx_frame_errors = pAd->Counters8023.RcvAlignmentErrors; // recv'd frame alignment error
55377 + pAd->stats.rx_fifo_errors = pAd->Counters8023.RxNoBuffer; // recv'r fifo overrun
55378 + pAd->stats.rx_missed_errors = 0; // receiver missed packet
55379 +
55380 + // detailed tx_errors
55381 + pAd->stats.tx_aborted_errors = 0;
55382 + pAd->stats.tx_carrier_errors = 0;
55383 + pAd->stats.tx_fifo_errors = 0;
55384 + pAd->stats.tx_heartbeat_errors = 0;
55385 + pAd->stats.tx_window_errors = 0;
55386 +
55387 + // for cslip etc
55388 + pAd->stats.rx_compressed = 0;
55389 + pAd->stats.tx_compressed = 0;
55390 +
55391 + return &pAd->stats;
55392 + }
55393 + else
55394 + return NULL;
55395 +}
55396 +
55397 --- /dev/null
55398 +++ b/drivers/staging/rt2860/rtmp_ckipmic.h
55399 @@ -0,0 +1,113 @@
55400 +/*
55401 + *************************************************************************
55402 + * Ralink Tech Inc.
55403 + * 5F., No.36, Taiyuan St., Jhubei City,
55404 + * Hsinchu County 302,
55405 + * Taiwan, R.O.C.
55406 + *
55407 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
55408 + *
55409 + * This program is free software; you can redistribute it and/or modify *
55410 + * it under the terms of the GNU General Public License as published by *
55411 + * the Free Software Foundation; either version 2 of the License, or *
55412 + * (at your option) any later version. *
55413 + * *
55414 + * This program is distributed in the hope that it will be useful, *
55415 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
55416 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
55417 + * GNU General Public License for more details. *
55418 + * *
55419 + * You should have received a copy of the GNU General Public License *
55420 + * along with this program; if not, write to the *
55421 + * Free Software Foundation, Inc., *
55422 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
55423 + * *
55424 + *************************************************************************
55425 +
55426 + Module Name:
55427 + rtmp_ckipmic.h
55428 +
55429 + Abstract:
55430 +
55431 + Revision History:
55432 + Who When What
55433 + -------- ---------- ----------------------------------------------
55434 + Name Date Modification logs
55435 +*/
55436 +#ifndef __RTMP_CKIPMIC_H__
55437 +#define __RTMP_CKIPMIC_H__
55438 +
55439 +typedef struct _MIC_CONTEXT {
55440 + /* --- MMH context */
55441 + UCHAR CK[16]; /* the key */
55442 + UCHAR coefficient[16]; /* current aes counter mode coefficients */
55443 + ULONGLONG accum; /* accumulated mic, reduced to u32 in final() */
55444 + UINT position; /* current position (byte offset) in message */
55445 + UCHAR part[4]; /* for conversion of message to u32 for mmh */
55446 +} MIC_CONTEXT, *PMIC_CONTEXT;
55447 +
55448 +VOID CKIP_key_permute(
55449 + OUT UCHAR *PK, /* output permuted key */
55450 + IN UCHAR *CK, /* input CKIP key */
55451 + IN UCHAR toDsFromDs, /* input toDs/FromDs bits */
55452 + IN UCHAR *piv); /* input pointer to IV */
55453 +
55454 +VOID RTMPCkipMicInit(
55455 + IN PMIC_CONTEXT pContext,
55456 + IN PUCHAR CK);
55457 +
55458 +VOID RTMPMicUpdate(
55459 + IN PMIC_CONTEXT pContext,
55460 + IN PUCHAR pOctets,
55461 + IN INT len);
55462 +
55463 +ULONG RTMPMicGetCoefficient(
55464 + IN PMIC_CONTEXT pContext);
55465 +
55466 +VOID xor_128(
55467 + IN PUCHAR a,
55468 + IN PUCHAR b,
55469 + OUT PUCHAR out);
55470 +
55471 +UCHAR RTMPCkipSbox(
55472 + IN UCHAR a);
55473 +
55474 +VOID xor_32(
55475 + IN PUCHAR a,
55476 + IN PUCHAR b,
55477 + OUT PUCHAR out);
55478 +
55479 +VOID next_key(
55480 + IN PUCHAR key,
55481 + IN INT round);
55482 +
55483 +VOID byte_sub(
55484 + IN PUCHAR in,
55485 + OUT PUCHAR out);
55486 +
55487 +VOID shift_row(
55488 + IN PUCHAR in,
55489 + OUT PUCHAR out);
55490 +
55491 +VOID mix_column(
55492 + IN PUCHAR in,
55493 + OUT PUCHAR out);
55494 +
55495 +VOID RTMPAesEncrypt(
55496 + IN PUCHAR key,
55497 + IN PUCHAR data,
55498 + IN PUCHAR ciphertext);
55499 +
55500 +VOID RTMPMicFinal(
55501 + IN PMIC_CONTEXT pContext,
55502 + OUT UCHAR digest[4]);
55503 +
55504 +VOID RTMPCkipInsertCMIC(
55505 + IN PRTMP_ADAPTER pAd,
55506 + OUT PUCHAR pMIC,
55507 + IN PUCHAR p80211hdr,
55508 + IN PNDIS_PACKET pPacket,
55509 + IN PCIPHER_KEY pKey,
55510 + IN PUCHAR mic_snap);
55511 +
55512 +#endif //__RTMP_CKIPMIC_H__
55513 --- /dev/null
55514 +++ b/drivers/staging/rt2860/rtmp_def.h
55515 @@ -0,0 +1,1588 @@
55516 +/*
55517 + *************************************************************************
55518 + * Ralink Tech Inc.
55519 + * 5F., No.36, Taiyuan St., Jhubei City,
55520 + * Hsinchu County 302,
55521 + * Taiwan, R.O.C.
55522 + *
55523 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
55524 + *
55525 + * This program is free software; you can redistribute it and/or modify *
55526 + * it under the terms of the GNU General Public License as published by *
55527 + * the Free Software Foundation; either version 2 of the License, or *
55528 + * (at your option) any later version. *
55529 + * *
55530 + * This program is distributed in the hope that it will be useful, *
55531 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
55532 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
55533 + * GNU General Public License for more details. *
55534 + * *
55535 + * You should have received a copy of the GNU General Public License *
55536 + * along with this program; if not, write to the *
55537 + * Free Software Foundation, Inc., *
55538 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
55539 + * *
55540 + *************************************************************************
55541 +
55542 + Module Name:
55543 + rtmp_def.h
55544 +
55545 + Abstract:
55546 + Miniport related definition header
55547 +
55548 + Revision History:
55549 + Who When What
55550 + -------- ---------- ----------------------------------------------
55551 + Paul Lin 08-01-2002 created
55552 + John Chang 08-05-2003 add definition for 11g & other drafts
55553 +*/
55554 +#ifndef __RTMP_DEF_H__
55555 +#define __RTMP_DEF_H__
55556 +
55557 +#include "oid.h"
55558 +
55559 +//
55560 +// Debug information verbosity: lower values indicate higher urgency
55561 +//
55562 +#define RT_DEBUG_OFF 0
55563 +#define RT_DEBUG_ERROR 1
55564 +#define RT_DEBUG_WARN 2
55565 +#define RT_DEBUG_TRACE 3
55566 +#define RT_DEBUG_INFO 4
55567 +#define RT_DEBUG_LOUD 5
55568 +
55569 +#define NIC_TAG ((ULONG)'0682')
55570 +#define NIC_DBG_STRING ("**RT28xx**")
55571 +
55572 +#ifdef SNMP_SUPPORT
55573 +// for snmp
55574 +// to get manufacturer OUI, kathy, 2008_0220
55575 +#define ManufacturerOUI_LEN 3
55576 +#define ManufacturerNAME ("Ralink Technology Company.")
55577 +#define ResourceTypeIdName ("Ralink_ID")
55578 +#endif
55579 +
55580 +
55581 +#define RALINK_2883_VERSION ((UINT32)0x28830300)
55582 +#define RALINK_2880E_VERSION ((UINT32)0x28720200)
55583 +#define RALINK_3070_VERSION ((UINT32)0x30700200)
55584 +
55585 +//
55586 +// NDIS version in use by the NIC driver.
55587 +// The high byte is the major version. The low byte is the minor version.
55588 +//
55589 +#ifdef NDIS51_MINIPORT
55590 +#define NIC_DRIVER_VERSION 0x0501
55591 +#else
55592 +#define NIC_DRIVER_VERSION 0x0500
55593 +#endif
55594 +
55595 +//
55596 +// NDIS media type, current is ethernet, change if native wireless supported
55597 +//
55598 +#define NIC_MEDIA_TYPE NdisMedium802_3
55599 +#define NIC_PCI_HDR_LENGTH 0xe2
55600 +#define NIC_MAX_PACKET_SIZE 2304
55601 +#define NIC_HEADER_SIZE 14
55602 +#define MAX_MAP_REGISTERS_NEEDED 32
55603 +#define MIN_MAP_REGISTERS_NEEDED 2 //Todo: should consider fragment issue.
55604 +
55605 +//
55606 +// interface type, we use PCI
55607 +//
55608 +#define NIC_INTERFACE_TYPE NdisInterfacePci
55609 +#define NIC_INTERRUPT_MODE NdisInterruptLevelSensitive
55610 +
55611 +//
55612 +// buffer size passed in NdisMQueryAdapterResources
55613 +// We should only need three adapter resources (IO, interrupt and memory),
55614 +// Some devices get extra resources, so have room for 10 resources
55615 +// UF_SIZE (sizeof(NDIS_RESOURCE_LIST) + (10*sizeof(CM_PARTIAL_RESOURCE_DESCRIPTOR)))
55616 +
55617 +
55618 +#define NIC_RESOURCE_B//
55619 +// IO space length
55620 +//
55621 +#define NIC_MAP_IOSPACE_LENGTH sizeof(CSR_STRUC)
55622 +
55623 +#define MAX_RX_PKT_LEN 1520
55624 +
55625 +//
55626 +// Entry number for each DMA descriptor ring
55627 +//
55628 +
55629 +#ifdef RT2860
55630 +#define TX_RING_SIZE 64 //64
55631 +#define MGMT_RING_SIZE 128
55632 +#define RX_RING_SIZE 128 //64
55633 +#define MAX_TX_PROCESS TX_RING_SIZE //8
55634 +#define MAX_DMA_DONE_PROCESS TX_RING_SIZE
55635 +#define MAX_TX_DONE_PROCESS TX_RING_SIZE //8
55636 +#define LOCAL_TXBUF_SIZE 2
55637 +#endif // RT2860 //
55638 +
55639 +
55640 +#ifdef MULTIPLE_CARD_SUPPORT
55641 +// MC: Multple Cards
55642 +#define MAX_NUM_OF_MULTIPLE_CARD 32
55643 +#endif // MULTIPLE_CARD_SUPPORT //
55644 +
55645 +#define MAX_RX_PROCESS 128 //64 //32
55646 +#define NUM_OF_LOCAL_TXBUF 2
55647 +#define TXD_SIZE 16
55648 +#define TXWI_SIZE 16
55649 +#define RXD_SIZE 16
55650 +#define RXWI_SIZE 16
55651 +// TXINFO_SIZE + TXWI_SIZE + 802.11 Header Size + AMSDU sub frame header
55652 +#define TX_DMA_1ST_BUFFER_SIZE 96 // only the 1st physical buffer is pre-allocated
55653 +#define MGMT_DMA_BUFFER_SIZE 1536 //2048
55654 +#define RX_BUFFER_AGGRESIZE 3840 //3904 //3968 //4096 //2048 //4096
55655 +#define RX_BUFFER_NORMSIZE 3840 //3904 //3968 //4096 //2048 //4096
55656 +#define TX_BUFFER_NORMSIZE RX_BUFFER_NORMSIZE
55657 +#define MAX_FRAME_SIZE 2346 // Maximum 802.11 frame size
55658 +#define MAX_AGGREGATION_SIZE 3840 //3904 //3968 //4096
55659 +#define MAX_NUM_OF_TUPLE_CACHE 2
55660 +#define MAX_MCAST_LIST_SIZE 32
55661 +#define MAX_LEN_OF_VENDOR_DESC 64
55662 +//#define MAX_SIZE_OF_MCAST_PSQ (NUM_OF_LOCAL_TXBUF >> 2) // AP won't spend more than 1/4 of total buffers on M/BCAST PSQ
55663 +#define MAX_SIZE_OF_MCAST_PSQ 32
55664 +
55665 +#define MAX_RX_PROCESS_CNT (RX_RING_SIZE)
55666 +
55667 +
55668 +#define MAX_PACKETS_IN_QUEUE (512) //(512) // to pass WMM A5-WPAPSK
55669 +#define MAX_PACKETS_IN_MCAST_PS_QUEUE 32
55670 +#define MAX_PACKETS_IN_PS_QUEUE 128 //32
55671 +#define WMM_NUM_OF_AC 4 /* AC0, AC1, AC2, and AC3 */
55672 +
55673 +
55674 +
55675 +// RxFilter
55676 +#define STANORMAL 0x17f97
55677 +#define APNORMAL 0x15f97
55678 +//
55679 +// RTMP_ADAPTER flags
55680 +//
55681 +#define fRTMP_ADAPTER_MAP_REGISTER 0x00000001
55682 +#define fRTMP_ADAPTER_INTERRUPT_IN_USE 0x00000002
55683 +#define fRTMP_ADAPTER_HARDWARE_ERROR 0x00000004
55684 +#define fRTMP_ADAPTER_SCATTER_GATHER 0x00000008
55685 +#define fRTMP_ADAPTER_SEND_PACKET_ERROR 0x00000010
55686 +#define fRTMP_ADAPTER_MLME_RESET_IN_PROGRESS 0x00000020
55687 +#define fRTMP_ADAPTER_HALT_IN_PROGRESS 0x00000040
55688 +#define fRTMP_ADAPTER_RESET_IN_PROGRESS 0x00000080
55689 +#define fRTMP_ADAPTER_NIC_NOT_EXIST 0x00000100
55690 +#define fRTMP_ADAPTER_TX_RING_ALLOCATED 0x00000200
55691 +#define fRTMP_ADAPTER_REMOVE_IN_PROGRESS 0x00000400
55692 +#define fRTMP_ADAPTER_MIMORATE_INUSED 0x00000800
55693 +#define fRTMP_ADAPTER_RX_RING_ALLOCATED 0x00001000
55694 +#define fRTMP_ADAPTER_INTERRUPT_ACTIVE 0x00002000
55695 +#define fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS 0x00004000
55696 +#define fRTMP_ADAPTER_REASSOC_IN_PROGRESS 0x00008000
55697 +#define fRTMP_ADAPTER_MEDIA_STATE_PENDING 0x00010000
55698 +#define fRTMP_ADAPTER_RADIO_OFF 0x00020000
55699 +#define fRTMP_ADAPTER_BULKOUT_RESET 0x00040000
55700 +#define fRTMP_ADAPTER_BULKIN_RESET 0x00080000
55701 +#define fRTMP_ADAPTER_RDG_ACTIVE 0x00100000
55702 +#define fRTMP_ADAPTER_DYNAMIC_BE_TXOP_ACTIVE 0x00200000
55703 +#define fRTMP_ADAPTER_SCAN_2040 0x04000000
55704 +#define fRTMP_ADAPTER_RADIO_MEASUREMENT 0x08000000
55705 +
55706 +#define fRTMP_ADAPTER_START_UP 0x10000000 //Devive already initialized and enabled Tx/Rx.
55707 +#define fRTMP_ADAPTER_MEDIA_STATE_CHANGE 0x20000000
55708 +#define fRTMP_ADAPTER_IDLE_RADIO_OFF 0x40000000
55709 +
55710 +//
55711 +// STA operation status flags
55712 +//
55713 +#define fOP_STATUS_INFRA_ON 0x00000001
55714 +#define fOP_STATUS_ADHOC_ON 0x00000002
55715 +#define fOP_STATUS_BG_PROTECTION_INUSED 0x00000004
55716 +#define fOP_STATUS_SHORT_SLOT_INUSED 0x00000008
55717 +#define fOP_STATUS_SHORT_PREAMBLE_INUSED 0x00000010
55718 +#define fOP_STATUS_RECEIVE_DTIM 0x00000020
55719 +#define fOP_STATUS_MEDIA_STATE_CONNECTED 0x00000080
55720 +#define fOP_STATUS_WMM_INUSED 0x00000100
55721 +#define fOP_STATUS_AGGREGATION_INUSED 0x00000200
55722 +#define fOP_STATUS_DOZE 0x00000400 // debug purpose
55723 +#define fOP_STATUS_PIGGYBACK_INUSED 0x00000800 // piggy-back, and aggregation
55724 +#define fOP_STATUS_APSD_INUSED 0x00001000
55725 +#define fOP_STATUS_TX_AMSDU_INUSED 0x00002000
55726 +#define fOP_STATUS_MAX_RETRY_ENABLED 0x00004000
55727 +#define fOP_STATUS_WAKEUP_NOW 0x00008000
55728 +#define fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE 0x00020000
55729 +
55730 +#ifdef DOT11N_DRAFT3
55731 +#define fOP_STATUS_SCAN_2040 0x00040000
55732 +#endif // DOT11N_DRAFT3 //
55733 +
55734 +#define CCKSETPROTECT 0x1
55735 +#define OFDMSETPROTECT 0x2
55736 +#define MM20SETPROTECT 0x4
55737 +#define MM40SETPROTECT 0x8
55738 +#define GF20SETPROTECT 0x10
55739 +#define GR40SETPROTECT 0x20
55740 +#define ALLN_SETPROTECT (GR40SETPROTECT | GF20SETPROTECT | MM40SETPROTECT | MM20SETPROTECT)
55741 +
55742 +//
55743 +// AP's client table operation status flags
55744 +//
55745 +#define fCLIENT_STATUS_WMM_CAPABLE 0x00000001 // CLIENT can parse QOS DATA frame
55746 +#define fCLIENT_STATUS_AGGREGATION_CAPABLE 0x00000002 // CLIENT can receive Ralink's proprietary TX aggregation frame
55747 +#define fCLIENT_STATUS_PIGGYBACK_CAPABLE 0x00000004 // CLIENT support piggy-back
55748 +#define fCLIENT_STATUS_AMSDU_INUSED 0x00000008
55749 +#define fCLIENT_STATUS_SGI20_CAPABLE 0x00000010
55750 +#define fCLIENT_STATUS_SGI40_CAPABLE 0x00000020
55751 +#define fCLIENT_STATUS_TxSTBC_CAPABLE 0x00000040
55752 +#define fCLIENT_STATUS_RxSTBC_CAPABLE 0x00000080
55753 +#define fCLIENT_STATUS_HTC_CAPABLE 0x00000100
55754 +#define fCLIENT_STATUS_RDG_CAPABLE 0x00000200
55755 +#define fCLIENT_STATUS_MCSFEEDBACK_CAPABLE 0x00000400
55756 +#define fCLIENT_STATUS_APSD_CAPABLE 0x00000800 /* UAPSD STATION */
55757 +
55758 +#ifdef DOT11N_DRAFT3
55759 +#define fCLIENT_STATUS_BSSCOEXIST_CAPABLE 0x00001000
55760 +#endif // DOT11N_DRAFT3 //
55761 +
55762 +#define fCLIENT_STATUS_RALINK_CHIPSET 0x00100000
55763 +//
55764 +// STA configuration flags
55765 +//
55766 +
55767 +// 802.11n Operating Mode Definition. 0-3 also used in ASICUPdateProtect switch case
55768 +#define HT_NO_PROTECT 0
55769 +#define HT_LEGACY_PROTECT 1
55770 +#define HT_40_PROTECT 2
55771 +#define HT_2040_PROTECT 3
55772 +#define HT_RTSCTS_6M 7
55773 +//following is our own definition in order to turn on our ASIC protection register in INFRASTRUCTURE.
55774 +#define HT_ATHEROS 8 // rt2860c has problem with atheros chip. we need to turn on RTS/CTS .
55775 +#define HT_FORCERTSCTS 9 // Force turn on RTS/CTS first. then go to evaluate if this force RTS is necessary.
55776 +
55777 +//
55778 +// RX Packet Filter control flags. Apply on pAd->PacketFilter
55779 +//
55780 +#define fRX_FILTER_ACCEPT_DIRECT NDIS_PACKET_TYPE_DIRECTED
55781 +#define fRX_FILTER_ACCEPT_MULTICAST NDIS_PACKET_TYPE_MULTICAST
55782 +#define fRX_FILTER_ACCEPT_BROADCAST NDIS_PACKET_TYPE_BROADCAST
55783 +#define fRX_FILTER_ACCEPT_ALL_MULTICAST NDIS_PACKET_TYPE_ALL_MULTICAST
55784 +
55785 +//
55786 +// Error code section
55787 +//
55788 +// NDIS_ERROR_CODE_ADAPTER_NOT_FOUND
55789 +#define ERRLOG_READ_PCI_SLOT_FAILED 0x00000101L
55790 +#define ERRLOG_WRITE_PCI_SLOT_FAILED 0x00000102L
55791 +#define ERRLOG_VENDOR_DEVICE_NOMATCH 0x00000103L
55792 +
55793 +// NDIS_ERROR_CODE_ADAPTER_DISABLED
55794 +#define ERRLOG_BUS_MASTER_DISABLED 0x00000201L
55795 +
55796 +// NDIS_ERROR_CODE_UNSUPPORTED_CONFIGURATION
55797 +#define ERRLOG_INVALID_SPEED_DUPLEX 0x00000301L
55798 +#define ERRLOG_SET_SECONDARY_FAILED 0x00000302L
55799 +
55800 +// NDIS_ERROR_CODE_OUT_OF_RESOURCES
55801 +#define ERRLOG_OUT_OF_MEMORY 0x00000401L
55802 +#define ERRLOG_OUT_OF_SHARED_MEMORY 0x00000402L
55803 +#define ERRLOG_OUT_OF_MAP_REGISTERS 0x00000403L
55804 +#define ERRLOG_OUT_OF_BUFFER_POOL 0x00000404L
55805 +#define ERRLOG_OUT_OF_NDIS_BUFFER 0x00000405L
55806 +#define ERRLOG_OUT_OF_PACKET_POOL 0x00000406L
55807 +#define ERRLOG_OUT_OF_NDIS_PACKET 0x00000407L
55808 +#define ERRLOG_OUT_OF_LOOKASIDE_MEMORY 0x00000408L
55809 +
55810 +// NDIS_ERROR_CODE_HARDWARE_FAILURE
55811 +#define ERRLOG_SELFTEST_FAILED 0x00000501L
55812 +#define ERRLOG_INITIALIZE_ADAPTER 0x00000502L
55813 +#define ERRLOG_REMOVE_MINIPORT 0x00000503L
55814 +
55815 +// NDIS_ERROR_CODE_RESOURCE_CONFLICT
55816 +#define ERRLOG_MAP_IO_SPACE 0x00000601L
55817 +#define ERRLOG_QUERY_ADAPTER_RESOURCES 0x00000602L
55818 +#define ERRLOG_NO_IO_RESOURCE 0x00000603L
55819 +#define ERRLOG_NO_INTERRUPT_RESOURCE 0x00000604L
55820 +#define ERRLOG_NO_MEMORY_RESOURCE 0x00000605L
55821 +
55822 +
55823 +// WDS definition
55824 +#define MAX_WDS_ENTRY 4
55825 +#define WDS_PAIRWISE_KEY_OFFSET 60 // WDS links uses pairwise key#60 ~ 63 in ASIC pairwise key table
55826 +
55827 +#define WDS_DISABLE_MODE 0
55828 +#define WDS_RESTRICT_MODE 1
55829 +#define WDS_BRIDGE_MODE 2
55830 +#define WDS_REPEATER_MODE 3
55831 +#define WDS_LAZY_MODE 4
55832 +
55833 +
55834 +#define MAX_MESH_NUM 0
55835 +
55836 +#define MAX_APCLI_NUM 0
55837 +#ifdef APCLI_SUPPORT
55838 +#undef MAX_APCLI_NUM
55839 +#define MAX_APCLI_NUM 1
55840 +#endif // APCLI_SUPPORT //
55841 +
55842 +#define MAX_MBSSID_NUM 1
55843 +#ifdef MBSS_SUPPORT
55844 +#undef MAX_MBSSID_NUM
55845 +#define MAX_MBSSID_NUM (8 - MAX_MESH_NUM - MAX_APCLI_NUM)
55846 +#endif // MBSS_SUPPORT //
55847 +
55848 +/* sanity check for apidx */
55849 +#define MBSS_MR_APIDX_SANITY_CHECK(apidx) \
55850 + { if (apidx > MAX_MBSSID_NUM) { \
55851 + printk("%s> Error! apidx = %d > MAX_MBSSID_NUM!\n", __FUNCTION__, apidx); \
55852 + apidx = MAIN_MBSSID; } }
55853 +
55854 +#define VALID_WCID(_wcid) ((_wcid) > 0 && (_wcid) < MAX_LEN_OF_MAC_TABLE )
55855 +
55856 +#define MAIN_MBSSID 0
55857 +#define FIRST_MBSSID 1
55858 +
55859 +
55860 +#define MAX_BEACON_SIZE 512
55861 +// If the MAX_MBSSID_NUM is larger than 6,
55862 +// it shall reserve some WCID space(wcid 222~253) for beacon frames.
55863 +// - these wcid 238~253 are reserved for beacon#6(ra6).
55864 +// - these wcid 222~237 are reserved for beacon#7(ra7).
55865 +#if defined(MAX_MBSSID_NUM) && (MAX_MBSSID_NUM == 8)
55866 +#define HW_RESERVED_WCID 222
55867 +#elif defined(MAX_MBSSID_NUM) && (MAX_MBSSID_NUM == 7)
55868 +#define HW_RESERVED_WCID 238
55869 +#else
55870 +#define HW_RESERVED_WCID 255
55871 +#endif
55872 +
55873 +// Then dedicate wcid of DFS and Carrier-Sense.
55874 +#define DFS_CTS_WCID (HW_RESERVED_WCID - 1)
55875 +#define CS_CTS_WCID (HW_RESERVED_WCID - 2)
55876 +#define LAST_SPECIFIC_WCID (HW_RESERVED_WCID - 2)
55877 +
55878 +// If MAX_MBSSID_NUM is 8, the maximum available wcid for the associated STA is 211.
55879 +// If MAX_MBSSID_NUM is 7, the maximum available wcid for the associated STA is 228.
55880 +#define MAX_AVAILABLE_CLIENT_WCID (LAST_SPECIFIC_WCID - MAX_MBSSID_NUM - 1)
55881 +
55882 +// TX need WCID to find Cipher Key
55883 +// these wcid 212 ~ 219 are reserved for bc/mc packets if MAX_MBSSID_NUM is 8.
55884 +#define GET_GroupKey_WCID(__wcid, __bssidx) \
55885 + { \
55886 + __wcid = LAST_SPECIFIC_WCID - (MAX_MBSSID_NUM) + __bssidx; \
55887 + }
55888 +
55889 +#define IsGroupKeyWCID(__wcid) (((__wcid) < LAST_SPECIFIC_WCID) && ((__wcid) >= (LAST_SPECIFIC_WCID - (MAX_MBSSID_NUM))))
55890 +
55891 +
55892 +// definition to support multiple BSSID
55893 +#define BSS0 0
55894 +#define BSS1 1
55895 +#define BSS2 2
55896 +#define BSS3 3
55897 +#define BSS4 4
55898 +#define BSS5 5
55899 +#define BSS6 6
55900 +#define BSS7 7
55901 +
55902 +
55903 +//============================================================
55904 +// Length definitions
55905 +#define PEER_KEY_NO 2
55906 +#define MAC_ADDR_LEN 6
55907 +#define TIMESTAMP_LEN 8
55908 +#define MAX_LEN_OF_SUPPORTED_RATES MAX_LENGTH_OF_SUPPORT_RATES // 1, 2, 5.5, 11, 6, 9, 12, 18, 24, 36, 48, 54
55909 +#define MAX_LEN_OF_KEY 32 // 32 octets == 256 bits, Redefine for WPA
55910 +#define MAX_NUM_OF_CHANNELS MAX_NUM_OF_CHS // 14 channels @2.4G + 12@UNII + 4 @MMAC + 11 @HiperLAN2 + 7 @Japan + 1 as NULL termination
55911 +#define MAX_NUM_OF_11JCHANNELS 20 // 14 channels @2.4G + 12@UNII + 4 @MMAC + 11 @HiperLAN2 + 7 @Japan + 1 as NULL termination
55912 +#define MAX_LEN_OF_SSID 32
55913 +#define CIPHER_TEXT_LEN 128
55914 +#define HASH_TABLE_SIZE 256
55915 +#define MAX_VIE_LEN 1024 // New for WPA cipher suite variable IE sizes.
55916 +#define MAX_SUPPORT_MCS 32
55917 +
55918 +//============================================================
55919 +// ASIC WCID Table definition.
55920 +//============================================================
55921 +#define BSSID_WCID 1 // in infra mode, always put bssid with this WCID
55922 +#define MCAST_WCID 0x0
55923 +#define BSS0Mcast_WCID 0x0
55924 +#define BSS1Mcast_WCID 0xf8
55925 +#define BSS2Mcast_WCID 0xf9
55926 +#define BSS3Mcast_WCID 0xfa
55927 +#define BSS4Mcast_WCID 0xfb
55928 +#define BSS5Mcast_WCID 0xfc
55929 +#define BSS6Mcast_WCID 0xfd
55930 +#define BSS7Mcast_WCID 0xfe
55931 +#define RESERVED_WCID 0xff
55932 +
55933 +#define MAX_NUM_OF_ACL_LIST MAX_NUMBER_OF_ACL
55934 +
55935 +#define MAX_LEN_OF_MAC_TABLE MAX_NUMBER_OF_MAC // if MAX_MBSSID_NUM is 8, this value can't be larger than 211
55936 +
55937 +#if MAX_LEN_OF_MAC_TABLE>MAX_AVAILABLE_CLIENT_WCID
55938 +#error MAX_LEN_OF_MAC_TABLE can not be larger than MAX_AVAILABLE_CLIENT_WCID!!!!
55939 +#endif
55940 +
55941 +#define MAX_NUM_OF_WDS_LINK_PERBSSID 3
55942 +#define MAX_NUM_OF_WDS_LINK (MAX_NUM_OF_WDS_LINK_PERBSSID*MAX_MBSSID_NUM)
55943 +#define MAX_NUM_OF_EVENT MAX_NUMBER_OF_EVENT
55944 +#define WDS_LINK_START_WCID (MAX_LEN_OF_MAC_TABLE-1)
55945 +
55946 +#define NUM_OF_TID 8
55947 +#define MAX_AID_BA 4
55948 +#define MAX_LEN_OF_BA_REC_TABLE ((NUM_OF_TID * MAX_LEN_OF_MAC_TABLE)/2)// (NUM_OF_TID*MAX_AID_BA + 32) //Block ACK recipient
55949 +#define MAX_LEN_OF_BA_ORI_TABLE ((NUM_OF_TID * MAX_LEN_OF_MAC_TABLE)/2)// (NUM_OF_TID*MAX_AID_BA + 32) // Block ACK originator
55950 +#define MAX_LEN_OF_BSS_TABLE 64
55951 +#define MAX_REORDERING_MPDU_NUM 512
55952 +
55953 +// key related definitions
55954 +#define SHARE_KEY_NUM 4
55955 +#define MAX_LEN_OF_SHARE_KEY 16 // byte count
55956 +#define MAX_LEN_OF_PEER_KEY 16 // byte count
55957 +#define PAIRWISE_KEY_NUM 64 // in MAC ASIC pairwise key table
55958 +#define GROUP_KEY_NUM 4
55959 +#define PMK_LEN 32
55960 +#define WDS_PAIRWISE_KEY_OFFSET 60 // WDS links uses pairwise key#60 ~ 63 in ASIC pairwise key table
55961 +#define PMKID_NO 4 // Number of PMKID saved supported
55962 +#define MAX_LEN_OF_MLME_BUFFER 2048
55963 +
55964 +// power status related definitions
55965 +#define PWR_ACTIVE 0
55966 +#define PWR_SAVE 1
55967 +#define PWR_MMPS 2 //MIMO power save
55968 +
55969 +// Auth and Assoc mode related definitions
55970 +#define AUTH_MODE_OPEN 0x00
55971 +#define AUTH_MODE_KEY 0x01
55972 +
55973 +// BSS Type definitions
55974 +#define BSS_ADHOC 0 // = Ndis802_11IBSS
55975 +#define BSS_INFRA 1 // = Ndis802_11Infrastructure
55976 +#define BSS_ANY 2 // = Ndis802_11AutoUnknown
55977 +#define BSS_MONITOR 3 // = Ndis802_11Monitor
55978 +
55979 +
55980 +// Reason code definitions
55981 +#define REASON_RESERVED 0
55982 +#define REASON_UNSPECIFY 1
55983 +#define REASON_NO_LONGER_VALID 2
55984 +#define REASON_DEAUTH_STA_LEAVING 3
55985 +#define REASON_DISASSOC_INACTIVE 4
55986 +#define REASON_DISASSPC_AP_UNABLE 5
55987 +#define REASON_CLS2ERR 6
55988 +#define REASON_CLS3ERR 7
55989 +#define REASON_DISASSOC_STA_LEAVING 8
55990 +#define REASON_STA_REQ_ASSOC_NOT_AUTH 9
55991 +#define REASON_INVALID_IE 13
55992 +#define REASON_MIC_FAILURE 14
55993 +#define REASON_4_WAY_TIMEOUT 15
55994 +#define REASON_GROUP_KEY_HS_TIMEOUT 16
55995 +#define REASON_IE_DIFFERENT 17
55996 +#define REASON_MCIPHER_NOT_VALID 18
55997 +#define REASON_UCIPHER_NOT_VALID 19
55998 +#define REASON_AKMP_NOT_VALID 20
55999 +#define REASON_UNSUPPORT_RSNE_VER 21
56000 +#define REASON_INVALID_RSNE_CAP 22
56001 +#define REASON_8021X_AUTH_FAIL 23
56002 +#define REASON_CIPHER_SUITE_REJECTED 24
56003 +#define REASON_DECLINED 37
56004 +
56005 +#define REASON_QOS_UNSPECIFY 32
56006 +#define REASON_QOS_LACK_BANDWIDTH 33
56007 +#define REASON_POOR_CHANNEL_CONDITION 34
56008 +#define REASON_QOS_OUTSIDE_TXOP_LIMITION 35
56009 +#define REASON_QOS_QSTA_LEAVING_QBSS 36
56010 +#define REASON_QOS_UNWANTED_MECHANISM 37
56011 +#define REASON_QOS_MECH_SETUP_REQUIRED 38
56012 +#define REASON_QOS_REQUEST_TIMEOUT 39
56013 +#define REASON_QOS_CIPHER_NOT_SUPPORT 45
56014 +
56015 +// Status code definitions
56016 +#define MLME_SUCCESS 0
56017 +#define MLME_UNSPECIFY_FAIL 1
56018 +#define MLME_CANNOT_SUPPORT_CAP 10
56019 +#define MLME_REASSOC_DENY_ASSOC_EXIST 11
56020 +#define MLME_ASSOC_DENY_OUT_SCOPE 12
56021 +#define MLME_ALG_NOT_SUPPORT 13
56022 +#define MLME_SEQ_NR_OUT_OF_SEQUENCE 14
56023 +#define MLME_REJ_CHALLENGE_FAILURE 15
56024 +#define MLME_REJ_TIMEOUT 16
56025 +#define MLME_ASSOC_REJ_UNABLE_HANDLE_STA 17
56026 +#define MLME_ASSOC_REJ_DATA_RATE 18
56027 +
56028 +#define MLME_ASSOC_REJ_NO_EXT_RATE 22
56029 +#define MLME_ASSOC_REJ_NO_EXT_RATE_PBCC 23
56030 +#define MLME_ASSOC_REJ_NO_CCK_OFDM 24
56031 +
56032 +#define MLME_QOS_UNSPECIFY 32
56033 +#define MLME_REQUEST_DECLINED 37
56034 +#define MLME_REQUEST_WITH_INVALID_PARAM 38
56035 +#define MLME_DLS_NOT_ALLOW_IN_QBSS 48
56036 +#define MLME_DEST_STA_NOT_IN_QBSS 49
56037 +#define MLME_DEST_STA_IS_NOT_A_QSTA 50
56038 +
56039 +#define MLME_INVALID_FORMAT 0x51
56040 +#define MLME_FAIL_NO_RESOURCE 0x52
56041 +#define MLME_STATE_MACHINE_REJECT 0x53
56042 +#define MLME_MAC_TABLE_FAIL 0x54
56043 +
56044 +// IE code
56045 +#define IE_SSID 0
56046 +#define IE_SUPP_RATES 1
56047 +#define IE_FH_PARM 2
56048 +#define IE_DS_PARM 3
56049 +#define IE_CF_PARM 4
56050 +#define IE_TIM 5
56051 +#define IE_IBSS_PARM 6
56052 +#define IE_COUNTRY 7 // 802.11d
56053 +#define IE_802_11D_REQUEST 10 // 802.11d
56054 +#define IE_QBSS_LOAD 11 // 802.11e d9
56055 +#define IE_EDCA_PARAMETER 12 // 802.11e d9
56056 +#define IE_TSPEC 13 // 802.11e d9
56057 +#define IE_TCLAS 14 // 802.11e d9
56058 +#define IE_SCHEDULE 15 // 802.11e d9
56059 +#define IE_CHALLENGE_TEXT 16
56060 +#define IE_POWER_CONSTRAINT 32 // 802.11h d3.3
56061 +#define IE_POWER_CAPABILITY 33 // 802.11h d3.3
56062 +#define IE_TPC_REQUEST 34 // 802.11h d3.3
56063 +#define IE_TPC_REPORT 35 // 802.11h d3.3
56064 +#define IE_SUPP_CHANNELS 36 // 802.11h d3.3
56065 +#define IE_CHANNEL_SWITCH_ANNOUNCEMENT 37 // 802.11h d3.3
56066 +#define IE_MEASUREMENT_REQUEST 38 // 802.11h d3.3
56067 +#define IE_MEASUREMENT_REPORT 39 // 802.11h d3.3
56068 +#define IE_QUIET 40 // 802.11h d3.3
56069 +#define IE_IBSS_DFS 41 // 802.11h d3.3
56070 +#define IE_ERP 42 // 802.11g
56071 +#define IE_TS_DELAY 43 // 802.11e d9
56072 +#define IE_TCLAS_PROCESSING 44 // 802.11e d9
56073 +#define IE_QOS_CAPABILITY 46 // 802.11e d6
56074 +#define IE_HT_CAP 45 // 802.11n d1. HT CAPABILITY. ELEMENT ID TBD
56075 +#define IE_AP_CHANNEL_REPORT 51 // 802.11k d6
56076 +#define IE_HT_CAP2 52 // 802.11n d1. HT CAPABILITY. ELEMENT ID TBD
56077 +#define IE_RSN 48 // 802.11i d3.0
56078 +#define IE_WPA2 48 // WPA2
56079 +#define IE_EXT_SUPP_RATES 50 // 802.11g
56080 +#define IE_SUPP_REG_CLASS 59 // 802.11y. Supported regulatory classes.
56081 +#define IE_EXT_CHANNEL_SWITCH_ANNOUNCEMENT 60 // 802.11n
56082 +#define IE_ADD_HT 61 // 802.11n d1. ADDITIONAL HT CAPABILITY. ELEMENT ID TBD
56083 +#define IE_ADD_HT2 53 // 802.11n d1. ADDITIONAL HT CAPABILITY. ELEMENT ID TBD
56084 +
56085 +
56086 +// For 802.11n D3.03
56087 +//#define IE_NEW_EXT_CHA_OFFSET 62 // 802.11n d1. New extension channel offset elemet
56088 +#define IE_SECONDARY_CH_OFFSET 62 // 802.11n D3.03 Secondary Channel Offset element
56089 +#define IE_2040_BSS_COEXIST 72 // 802.11n D3.0.3
56090 +#define IE_2040_BSS_INTOLERANT_REPORT 73 // 802.11n D3.03
56091 +#define IE_OVERLAPBSS_SCAN_PARM 74 // 802.11n D3.03
56092 +#define IE_EXT_CAPABILITY 127 // 802.11n D3.03
56093 +
56094 +
56095 +#define IE_WPA 221 // WPA
56096 +#define IE_VENDOR_SPECIFIC 221 // Wifi WMM (WME)
56097 +
56098 +#define OUI_BROADCOM_HT 51 //
56099 +#define OUI_BROADCOM_HTADD 52 //
56100 +#define OUI_PREN_HT_CAP 51 //
56101 +#define OUI_PREN_ADD_HT 52 //
56102 +
56103 +// CCX information
56104 +#define IE_AIRONET_CKIP 133 // CCX1.0 ID 85H for CKIP
56105 +#define IE_AP_TX_POWER 150 // CCX 2.0 for AP transmit power
56106 +#define IE_MEASUREMENT_CAPABILITY 221 // CCX 2.0
56107 +#define IE_CCX_V2 221
56108 +#define IE_AIRONET_IPADDRESS 149 // CCX ID 95H for IP Address
56109 +#define IE_AIRONET_CCKMREASSOC 156 // CCX ID 9CH for CCKM Reassociation Request element
56110 +#define CKIP_NEGOTIATION_LENGTH 30
56111 +#define AIRONET_IPADDRESS_LENGTH 10
56112 +#define AIRONET_CCKMREASSOC_LENGTH 24
56113 +
56114 +// ========================================================
56115 +// MLME state machine definition
56116 +// ========================================================
56117 +
56118 +// STA MLME state mahcines
56119 +#define ASSOC_STATE_MACHINE 1
56120 +#define AUTH_STATE_MACHINE 2
56121 +#define AUTH_RSP_STATE_MACHINE 3
56122 +#define SYNC_STATE_MACHINE 4
56123 +#define MLME_CNTL_STATE_MACHINE 5
56124 +#define WPA_PSK_STATE_MACHINE 6
56125 +#define LEAP_STATE_MACHINE 7
56126 +#define AIRONET_STATE_MACHINE 8
56127 +#define ACTION_STATE_MACHINE 9
56128 +
56129 +// AP MLME state machines
56130 +#define AP_ASSOC_STATE_MACHINE 11
56131 +#define AP_AUTH_STATE_MACHINE 12
56132 +#define AP_AUTH_RSP_STATE_MACHINE 13
56133 +#define AP_SYNC_STATE_MACHINE 14
56134 +#define AP_CNTL_STATE_MACHINE 15
56135 +#define AP_WPA_STATE_MACHINE 16
56136 +
56137 +#ifdef QOS_DLS_SUPPORT
56138 +#define DLS_STATE_MACHINE 26
56139 +#endif // QOS_DLS_SUPPORT //
56140 +
56141 +//
56142 +// STA's CONTROL/CONNECT state machine: states, events, total function #
56143 +//
56144 +#define CNTL_IDLE 0
56145 +#define CNTL_WAIT_DISASSOC 1
56146 +#define CNTL_WAIT_JOIN 2
56147 +#define CNTL_WAIT_REASSOC 3
56148 +#define CNTL_WAIT_START 4
56149 +#define CNTL_WAIT_AUTH 5
56150 +#define CNTL_WAIT_ASSOC 6
56151 +#define CNTL_WAIT_AUTH2 7
56152 +#define CNTL_WAIT_OID_LIST_SCAN 8
56153 +#define CNTL_WAIT_OID_DISASSOC 9
56154 +
56155 +#define MT2_ASSOC_CONF 34
56156 +#define MT2_AUTH_CONF 35
56157 +#define MT2_DEAUTH_CONF 36
56158 +#define MT2_DISASSOC_CONF 37
56159 +#define MT2_REASSOC_CONF 38
56160 +#define MT2_PWR_MGMT_CONF 39
56161 +#define MT2_JOIN_CONF 40
56162 +#define MT2_SCAN_CONF 41
56163 +#define MT2_START_CONF 42
56164 +#define MT2_GET_CONF 43
56165 +#define MT2_SET_CONF 44
56166 +#define MT2_RESET_CONF 45
56167 +#define MT2_MLME_ROAMING_REQ 52
56168 +
56169 +#define CNTL_FUNC_SIZE 1
56170 +
56171 +//
56172 +// STA's ASSOC state machine: states, events, total function #
56173 +//
56174 +#define ASSOC_IDLE 0
56175 +#define ASSOC_WAIT_RSP 1
56176 +#define REASSOC_WAIT_RSP 2
56177 +#define DISASSOC_WAIT_RSP 3
56178 +#define MAX_ASSOC_STATE 4
56179 +
56180 +#define ASSOC_MACHINE_BASE 0
56181 +#define MT2_MLME_ASSOC_REQ 0
56182 +#define MT2_MLME_REASSOC_REQ 1
56183 +#define MT2_MLME_DISASSOC_REQ 2
56184 +#define MT2_PEER_DISASSOC_REQ 3
56185 +#define MT2_PEER_ASSOC_REQ 4
56186 +#define MT2_PEER_ASSOC_RSP 5
56187 +#define MT2_PEER_REASSOC_REQ 6
56188 +#define MT2_PEER_REASSOC_RSP 7
56189 +#define MT2_DISASSOC_TIMEOUT 8
56190 +#define MT2_ASSOC_TIMEOUT 9
56191 +#define MT2_REASSOC_TIMEOUT 10
56192 +#define MAX_ASSOC_MSG 11
56193 +
56194 +#define ASSOC_FUNC_SIZE (MAX_ASSOC_STATE * MAX_ASSOC_MSG)
56195 +
56196 +//
56197 +// ACT state machine: states, events, total function #
56198 +//
56199 +#define ACT_IDLE 0
56200 +#define MAX_ACT_STATE 1
56201 +
56202 +#define ACT_MACHINE_BASE 0
56203 +
56204 +//Those PEER_xx_CATE number is based on real Categary value in IEEE spec. Please don'es modify it by your self.
56205 +//Category
56206 +#define MT2_PEER_SPECTRUM_CATE 0
56207 +#define MT2_PEER_QOS_CATE 1
56208 +#define MT2_PEER_DLS_CATE 2
56209 +#define MT2_PEER_BA_CATE 3
56210 +#define MT2_PEER_PUBLIC_CATE 4
56211 +#define MT2_PEER_RM_CATE 5
56212 +#define MT2_PEER_HT_CATE 7 // 7.4.7
56213 +#define MAX_PEER_CATE_MSG 7
56214 +#define MT2_MLME_ADD_BA_CATE 8
56215 +#define MT2_MLME_ORI_DELBA_CATE 9
56216 +#define MT2_MLME_REC_DELBA_CATE 10
56217 +#define MT2_MLME_QOS_CATE 11
56218 +#define MT2_MLME_DLS_CATE 12
56219 +#define MT2_ACT_INVALID 13
56220 +#define MAX_ACT_MSG 14
56221 +
56222 +//Category field
56223 +#define CATEGORY_SPECTRUM 0
56224 +#define CATEGORY_QOS 1
56225 +#define CATEGORY_DLS 2
56226 +#define CATEGORY_BA 3
56227 +#define CATEGORY_PUBLIC 4
56228 +#define CATEGORY_RM 5
56229 +#define CATEGORY_HT 7
56230 +
56231 +
56232 +// DLS Action frame definition
56233 +#define ACTION_DLS_REQUEST 0
56234 +#define ACTION_DLS_RESPONSE 1
56235 +#define ACTION_DLS_TEARDOWN 2
56236 +
56237 +//Spectrum Action field value 802.11h 7.4.1
56238 +#define SPEC_MRQ 0 // Request
56239 +#define SPEC_MRP 1 //Report
56240 +#define SPEC_TPCRQ 2
56241 +#define SPEC_TPCRP 3
56242 +#define SPEC_CHANNEL_SWITCH 4
56243 +
56244 +
56245 +//BA Action field value
56246 +#define ADDBA_REQ 0
56247 +#define ADDBA_RESP 1
56248 +#define DELBA 2
56249 +
56250 +//Public's Action field value in Public Category. Some in 802.11y and some in 11n
56251 +#define ACTION_BSS_2040_COEXIST 0 // 11n
56252 +#define ACTION_DSE_ENABLEMENT 1 // 11y D9.0
56253 +#define ACTION_DSE_DEENABLEMENT 2 // 11y D9.0
56254 +#define ACTION_DSE_REG_LOCATION_ANNOUNCE 3 // 11y D9.0
56255 +#define ACTION_EXT_CH_SWITCH_ANNOUNCE 4 // 11y D9.0
56256 +#define ACTION_DSE_MEASUREMENT_REQ 5 // 11y D9.0
56257 +#define ACTION_DSE_MEASUREMENT_REPORT 6 // 11y D9.0
56258 +#define ACTION_MEASUREMENT_PILOT_ACTION 7 // 11y D9.0
56259 +#define ACTION_DSE_POWER_CONSTRAINT 8 // 11y D9.0
56260 +
56261 +
56262 +//HT Action field value
56263 +#define NOTIFY_BW_ACTION 0
56264 +#define SMPS_ACTION 1
56265 +#define PSMP_ACTION 2
56266 +#define SETPCO_ACTION 3
56267 +#define MIMO_CHA_MEASURE_ACTION 4
56268 +#define MIMO_N_BEACONFORM 5
56269 +#define MIMO_BEACONFORM 6
56270 +#define ANTENNA_SELECT 7
56271 +#define HT_INFO_EXCHANGE 8
56272 +
56273 +#define ACT_FUNC_SIZE (MAX_ACT_STATE * MAX_ACT_MSG)
56274 +//
56275 +// STA's AUTHENTICATION state machine: states, evvents, total function #
56276 +//
56277 +#define AUTH_REQ_IDLE 0
56278 +#define AUTH_WAIT_SEQ2 1
56279 +#define AUTH_WAIT_SEQ4 2
56280 +#define MAX_AUTH_STATE 3
56281 +
56282 +#define AUTH_MACHINE_BASE 0
56283 +#define MT2_MLME_AUTH_REQ 0
56284 +#define MT2_PEER_AUTH_EVEN 1
56285 +#define MT2_AUTH_TIMEOUT 2
56286 +#define MAX_AUTH_MSG 3
56287 +
56288 +#define AUTH_FUNC_SIZE (MAX_AUTH_STATE * MAX_AUTH_MSG)
56289 +
56290 +//
56291 +// STA's AUTH_RSP state machine: states, events, total function #
56292 +//
56293 +#define AUTH_RSP_IDLE 0
56294 +#define AUTH_RSP_WAIT_CHAL 1
56295 +#define MAX_AUTH_RSP_STATE 2
56296 +
56297 +#define AUTH_RSP_MACHINE_BASE 0
56298 +#define MT2_AUTH_CHALLENGE_TIMEOUT 0
56299 +#define MT2_PEER_AUTH_ODD 1
56300 +#define MT2_PEER_DEAUTH 2
56301 +#define MAX_AUTH_RSP_MSG 3
56302 +
56303 +#define AUTH_RSP_FUNC_SIZE (MAX_AUTH_RSP_STATE * MAX_AUTH_RSP_MSG)
56304 +
56305 +//
56306 +// STA's SYNC state machine: states, events, total function #
56307 +//
56308 +#define SYNC_IDLE 0 // merge NO_BSS,IBSS_IDLE,IBSS_ACTIVE and BSS in to 1 state
56309 +#define JOIN_WAIT_BEACON 1
56310 +#define SCAN_LISTEN 2
56311 +#define MAX_SYNC_STATE 3
56312 +
56313 +#define SYNC_MACHINE_BASE 0
56314 +#define MT2_MLME_SCAN_REQ 0
56315 +#define MT2_MLME_JOIN_REQ 1
56316 +#define MT2_MLME_START_REQ 2
56317 +#define MT2_PEER_BEACON 3
56318 +#define MT2_PEER_PROBE_RSP 4
56319 +#define MT2_PEER_ATIM 5
56320 +#define MT2_SCAN_TIMEOUT 6
56321 +#define MT2_BEACON_TIMEOUT 7
56322 +#define MT2_ATIM_TIMEOUT 8
56323 +#define MT2_PEER_PROBE_REQ 9
56324 +#define MAX_SYNC_MSG 10
56325 +
56326 +#define SYNC_FUNC_SIZE (MAX_SYNC_STATE * MAX_SYNC_MSG)
56327 +
56328 +//Messages for the DLS state machine
56329 +#define DLS_IDLE 0
56330 +#define MAX_DLS_STATE 1
56331 +
56332 +#define DLS_MACHINE_BASE 0
56333 +#define MT2_MLME_DLS_REQ 0
56334 +#define MT2_PEER_DLS_REQ 1
56335 +#define MT2_PEER_DLS_RSP 2
56336 +#define MT2_MLME_DLS_TEAR_DOWN 3
56337 +#define MT2_PEER_DLS_TEAR_DOWN 4
56338 +#define MAX_DLS_MSG 5
56339 +
56340 +#define DLS_FUNC_SIZE (MAX_DLS_STATE * MAX_DLS_MSG)
56341 +
56342 +//
56343 +// STA's WPA-PSK State machine: states, events, total function #
56344 +//
56345 +#define WPA_PSK_IDLE 0
56346 +#define MAX_WPA_PSK_STATE 1
56347 +
56348 +#define WPA_MACHINE_BASE 0
56349 +#define MT2_EAPPacket 0
56350 +#define MT2_EAPOLStart 1
56351 +#define MT2_EAPOLLogoff 2
56352 +#define MT2_EAPOLKey 3
56353 +#define MT2_EAPOLASFAlert 4
56354 +#define MAX_WPA_PSK_MSG 5
56355 +
56356 +#define WPA_PSK_FUNC_SIZE (MAX_WPA_PSK_STATE * MAX_WPA_PSK_MSG)
56357 +
56358 +//
56359 +// STA's CISCO-AIRONET State machine: states, events, total function #
56360 +//
56361 +#define AIRONET_IDLE 0
56362 +#define AIRONET_SCANNING 1
56363 +#define MAX_AIRONET_STATE 2
56364 +
56365 +#define AIRONET_MACHINE_BASE 0
56366 +#define MT2_AIRONET_MSG 0
56367 +#define MT2_AIRONET_SCAN_REQ 1
56368 +#define MT2_AIRONET_SCAN_DONE 2
56369 +#define MAX_AIRONET_MSG 3
56370 +
56371 +#define AIRONET_FUNC_SIZE (MAX_AIRONET_STATE * MAX_AIRONET_MSG)
56372 +
56373 +//
56374 +// AP's CONTROL/CONNECT state machine: states, events, total function #
56375 +//
56376 +#define AP_CNTL_FUNC_SIZE 1
56377 +
56378 +//
56379 +// AP's ASSOC state machine: states, events, total function #
56380 +//
56381 +#define AP_ASSOC_IDLE 0
56382 +#define AP_MAX_ASSOC_STATE 1
56383 +
56384 +#define AP_ASSOC_MACHINE_BASE 0
56385 +#define APMT2_MLME_DISASSOC_REQ 0
56386 +#define APMT2_PEER_DISASSOC_REQ 1
56387 +#define APMT2_PEER_ASSOC_REQ 2
56388 +#define APMT2_PEER_REASSOC_REQ 3
56389 +#define APMT2_CLS3ERR 4
56390 +#define AP_MAX_ASSOC_MSG 5
56391 +
56392 +#define AP_ASSOC_FUNC_SIZE (AP_MAX_ASSOC_STATE * AP_MAX_ASSOC_MSG)
56393 +
56394 +//
56395 +// AP's AUTHENTICATION state machine: states, events, total function #
56396 +//
56397 +#define AP_AUTH_REQ_IDLE 0
56398 +#define AP_MAX_AUTH_STATE 1
56399 +
56400 +#define AP_AUTH_MACHINE_BASE 0
56401 +#define APMT2_MLME_DEAUTH_REQ 0
56402 +#define APMT2_CLS2ERR 1
56403 +#define AP_MAX_AUTH_MSG 2
56404 +
56405 +#define AP_AUTH_FUNC_SIZE (AP_MAX_AUTH_STATE * AP_MAX_AUTH_MSG)
56406 +
56407 +//
56408 +// AP's AUTH-RSP state machine: states, events, total function #
56409 +//
56410 +#define AP_AUTH_RSP_IDLE 0
56411 +#define AP_MAX_AUTH_RSP_STATE 1
56412 +
56413 +#define AP_AUTH_RSP_MACHINE_BASE 0
56414 +#define APMT2_AUTH_CHALLENGE_TIMEOUT 0
56415 +#define APMT2_PEER_AUTH_ODD 1
56416 +#define APMT2_PEER_DEAUTH 2
56417 +#define AP_MAX_AUTH_RSP_MSG 3
56418 +
56419 +#define AP_AUTH_RSP_FUNC_SIZE (AP_MAX_AUTH_RSP_STATE * AP_MAX_AUTH_RSP_MSG)
56420 +
56421 +//
56422 +// AP's SYNC state machine: states, events, total function #
56423 +//
56424 +#define AP_SYNC_IDLE 0
56425 +#define AP_SCAN_LISTEN 1
56426 +#define AP_MAX_SYNC_STATE 2
56427 +
56428 +#define AP_SYNC_MACHINE_BASE 0
56429 +#define APMT2_PEER_PROBE_REQ 0
56430 +#define APMT2_PEER_BEACON 1
56431 +#define APMT2_MLME_SCAN_REQ 2
56432 +#define APMT2_PEER_PROBE_RSP 3
56433 +#define APMT2_SCAN_TIMEOUT 4
56434 +#define APMT2_MLME_SCAN_CNCL 5
56435 +#define AP_MAX_SYNC_MSG 6
56436 +
56437 +#define AP_SYNC_FUNC_SIZE (AP_MAX_SYNC_STATE * AP_MAX_SYNC_MSG)
56438 +
56439 +//
56440 +// AP's WPA state machine: states, events, total function #
56441 +//
56442 +#define AP_WPA_PTK 0
56443 +#define AP_MAX_WPA_PTK_STATE 1
56444 +
56445 +#define AP_WPA_MACHINE_BASE 0
56446 +#define APMT2_EAPPacket 0
56447 +#define APMT2_EAPOLStart 1
56448 +#define APMT2_EAPOLLogoff 2
56449 +#define APMT2_EAPOLKey 3
56450 +#define APMT2_EAPOLASFAlert 4
56451 +#define AP_MAX_WPA_MSG 5
56452 +
56453 +#define AP_WPA_FUNC_SIZE (AP_MAX_WPA_PTK_STATE * AP_MAX_WPA_MSG)
56454 +
56455 +#ifdef APCLI_SUPPORT
56456 +//ApCli authentication state machine
56457 +#define APCLI_AUTH_REQ_IDLE 0
56458 +#define APCLI_AUTH_WAIT_SEQ2 1
56459 +#define APCLI_AUTH_WAIT_SEQ4 2
56460 +#define APCLI_MAX_AUTH_STATE 3
56461 +
56462 +#define APCLI_AUTH_MACHINE_BASE 0
56463 +#define APCLI_MT2_MLME_AUTH_REQ 0
56464 +#define APCLI_MT2_MLME_DEAUTH_REQ 1
56465 +#define APCLI_MT2_PEER_AUTH_EVEN 2
56466 +#define APCLI_MT2_PEER_DEAUTH 3
56467 +#define APCLI_MT2_AUTH_TIMEOUT 4
56468 +#define APCLI_MAX_AUTH_MSG 5
56469 +
56470 +#define APCLI_AUTH_FUNC_SIZE (APCLI_MAX_AUTH_STATE * APCLI_MAX_AUTH_MSG)
56471 +
56472 +//ApCli association state machine
56473 +#define APCLI_ASSOC_IDLE 0
56474 +#define APCLI_ASSOC_WAIT_RSP 1
56475 +#define APCLI_MAX_ASSOC_STATE 2
56476 +
56477 +#define APCLI_ASSOC_MACHINE_BASE 0
56478 +#define APCLI_MT2_MLME_ASSOC_REQ 0
56479 +#define APCLI_MT2_MLME_DISASSOC_REQ 1
56480 +#define APCLI_MT2_PEER_DISASSOC_REQ 2
56481 +#define APCLI_MT2_PEER_ASSOC_RSP 3
56482 +#define APCLI_MT2_ASSOC_TIMEOUT 4
56483 +#define APCLI_MAX_ASSOC_MSG 5
56484 +
56485 +#define APCLI_ASSOC_FUNC_SIZE (APCLI_MAX_ASSOC_STATE * APCLI_MAX_ASSOC_MSG)
56486 +
56487 +//ApCli sync state machine
56488 +#define APCLI_SYNC_IDLE 0 // merge NO_BSS,IBSS_IDLE,IBSS_ACTIVE and BSS in to 1 state
56489 +#define APCLI_JOIN_WAIT_PROBE_RSP 1
56490 +#define APCLI_MAX_SYNC_STATE 2
56491 +
56492 +#define APCLI_SYNC_MACHINE_BASE 0
56493 +#define APCLI_MT2_MLME_PROBE_REQ 0
56494 +#define APCLI_MT2_PEER_PROBE_RSP 1
56495 +#define APCLI_MT2_PROBE_TIMEOUT 2
56496 +#define APCLI_MAX_SYNC_MSG 3
56497 +
56498 +#define APCLI_SYNC_FUNC_SIZE (APCLI_MAX_SYNC_STATE * APCLI_MAX_SYNC_MSG)
56499 +
56500 +//ApCli ctrl state machine
56501 +#define APCLI_CTRL_DISCONNECTED 0 // merge NO_BSS,IBSS_IDLE,IBSS_ACTIVE and BSS in to 1 state
56502 +#define APCLI_CTRL_PROBE 1
56503 +#define APCLI_CTRL_AUTH 2
56504 +#define APCLI_CTRL_AUTH_2 3
56505 +#define APCLI_CTRL_ASSOC 4
56506 +#define APCLI_CTRL_DEASSOC 5
56507 +#define APCLI_CTRL_CONNECTED 6
56508 +#define APCLI_MAX_CTRL_STATE 7
56509 +
56510 +#define APCLI_CTRL_MACHINE_BASE 0
56511 +#define APCLI_CTRL_JOIN_REQ 0
56512 +#define APCLI_CTRL_PROBE_RSP 1
56513 +#define APCLI_CTRL_AUTH_RSP 2
56514 +#define APCLI_CTRL_DISCONNECT_REQ 3
56515 +#define APCLI_CTRL_PEER_DISCONNECT_REQ 4
56516 +#define APCLI_CTRL_ASSOC_RSP 5
56517 +#define APCLI_CTRL_DEASSOC_RSP 6
56518 +#define APCLI_CTRL_JOIN_REQ_TIMEOUT 7
56519 +#define APCLI_CTRL_AUTH_REQ_TIMEOUT 8
56520 +#define APCLI_CTRL_ASSOC_REQ_TIMEOUT 9
56521 +#define APCLI_MAX_CTRL_MSG 10
56522 +
56523 +#define APCLI_CTRL_FUNC_SIZE (APCLI_MAX_CTRL_STATE * APCLI_MAX_CTRL_MSG)
56524 +
56525 +#endif // APCLI_SUPPORT //
56526 +
56527 +
56528 +// =============================================================================
56529 +
56530 +// value domain of 802.11 header FC.Tyte, which is b3..b2 of the 1st-byte of MAC header
56531 +#define BTYPE_MGMT 0
56532 +#define BTYPE_CNTL 1
56533 +#define BTYPE_DATA 2
56534 +
56535 +// value domain of 802.11 MGMT frame's FC.subtype, which is b7..4 of the 1st-byte of MAC header
56536 +#define SUBTYPE_ASSOC_REQ 0
56537 +#define SUBTYPE_ASSOC_RSP 1
56538 +#define SUBTYPE_REASSOC_REQ 2
56539 +#define SUBTYPE_REASSOC_RSP 3
56540 +#define SUBTYPE_PROBE_REQ 4
56541 +#define SUBTYPE_PROBE_RSP 5
56542 +#define SUBTYPE_BEACON 8
56543 +#define SUBTYPE_ATIM 9
56544 +#define SUBTYPE_DISASSOC 10
56545 +#define SUBTYPE_AUTH 11
56546 +#define SUBTYPE_DEAUTH 12
56547 +#define SUBTYPE_ACTION 13
56548 +#define SUBTYPE_ACTION_NO_ACK 14
56549 +
56550 +// value domain of 802.11 CNTL frame's FC.subtype, which is b7..4 of the 1st-byte of MAC header
56551 +#define SUBTYPE_WRAPPER 7
56552 +#define SUBTYPE_BLOCK_ACK_REQ 8
56553 +#define SUBTYPE_BLOCK_ACK 9
56554 +#define SUBTYPE_PS_POLL 10
56555 +#define SUBTYPE_RTS 11
56556 +#define SUBTYPE_CTS 12
56557 +#define SUBTYPE_ACK 13
56558 +#define SUBTYPE_CFEND 14
56559 +#define SUBTYPE_CFEND_CFACK 15
56560 +
56561 +// value domain of 802.11 DATA frame's FC.subtype, which is b7..4 of the 1st-byte of MAC header
56562 +#define SUBTYPE_DATA 0
56563 +#define SUBTYPE_DATA_CFACK 1
56564 +#define SUBTYPE_DATA_CFPOLL 2
56565 +#define SUBTYPE_DATA_CFACK_CFPOLL 3
56566 +#define SUBTYPE_NULL_FUNC 4
56567 +#define SUBTYPE_CFACK 5
56568 +#define SUBTYPE_CFPOLL 6
56569 +#define SUBTYPE_CFACK_CFPOLL 7
56570 +#define SUBTYPE_QDATA 8
56571 +#define SUBTYPE_QDATA_CFACK 9
56572 +#define SUBTYPE_QDATA_CFPOLL 10
56573 +#define SUBTYPE_QDATA_CFACK_CFPOLL 11
56574 +#define SUBTYPE_QOS_NULL 12
56575 +#define SUBTYPE_QOS_CFACK 13
56576 +#define SUBTYPE_QOS_CFPOLL 14
56577 +#define SUBTYPE_QOS_CFACK_CFPOLL 15
56578 +
56579 +// ACK policy of QOS Control field bit 6:5
56580 +#define NORMAL_ACK 0x00 // b6:5 = 00
56581 +#define NO_ACK 0x20 // b6:5 = 01
56582 +#define NO_EXPLICIT_ACK 0x40 // b6:5 = 10
56583 +#define BLOCK_ACK 0x60 // b6:5 = 11
56584 +
56585 +//
56586 +// rtmp_data.c use these definition
56587 +//
56588 +#define LENGTH_802_11 24
56589 +#define LENGTH_802_11_AND_H 30
56590 +#define LENGTH_802_11_CRC_H 34
56591 +#define LENGTH_802_11_CRC 28
56592 +#define LENGTH_802_11_WITH_ADDR4 30
56593 +#define LENGTH_802_3 14
56594 +#define LENGTH_802_3_TYPE 2
56595 +#define LENGTH_802_1_H 8
56596 +#define LENGTH_EAPOL_H 4
56597 +#define LENGTH_WMMQOS_H 2
56598 +#define LENGTH_CRC 4
56599 +#define MAX_SEQ_NUMBER 0x0fff
56600 +#define LENGTH_802_3_NO_TYPE 12
56601 +#define LENGTH_802_1Q 4 /* VLAN related */
56602 +
56603 +// STA_CSR4.field.TxResult
56604 +#define TX_RESULT_SUCCESS 0
56605 +#define TX_RESULT_ZERO_LENGTH 1
56606 +#define TX_RESULT_UNDER_RUN 2
56607 +#define TX_RESULT_OHY_ERROR 4
56608 +#define TX_RESULT_RETRY_FAIL 6
56609 +
56610 +// All PHY rate summary in TXD
56611 +// Preamble MODE in TxD
56612 +#define MODE_CCK 0
56613 +#define MODE_OFDM 1
56614 +#ifdef DOT11_N_SUPPORT
56615 +#define MODE_HTMIX 2
56616 +#define MODE_HTGREENFIELD 3
56617 +#endif // DOT11_N_SUPPORT //
56618 +// MCS for CCK. BW.SGI.STBC are reserved
56619 +#define MCS_LONGP_RATE_1 0 // long preamble CCK 1Mbps
56620 +#define MCS_LONGP_RATE_2 1 // long preamble CCK 1Mbps
56621 +#define MCS_LONGP_RATE_5_5 2
56622 +#define MCS_LONGP_RATE_11 3
56623 +#define MCS_SHORTP_RATE_1 4 // long preamble CCK 1Mbps. short is forbidden in 1Mbps
56624 +#define MCS_SHORTP_RATE_2 5 // short preamble CCK 2Mbps
56625 +#define MCS_SHORTP_RATE_5_5 6
56626 +#define MCS_SHORTP_RATE_11 7
56627 +// To send duplicate legacy OFDM. set BW=BW_40. SGI.STBC are reserved
56628 +#define MCS_RATE_6 0 // legacy OFDM
56629 +#define MCS_RATE_9 1 // OFDM
56630 +#define MCS_RATE_12 2 // OFDM
56631 +#define MCS_RATE_18 3 // OFDM
56632 +#define MCS_RATE_24 4 // OFDM
56633 +#define MCS_RATE_36 5 // OFDM
56634 +#define MCS_RATE_48 6 // OFDM
56635 +#define MCS_RATE_54 7 // OFDM
56636 +// HT
56637 +#define MCS_0 0 // 1S
56638 +#define MCS_1 1
56639 +#define MCS_2 2
56640 +#define MCS_3 3
56641 +#define MCS_4 4
56642 +#define MCS_5 5
56643 +#define MCS_6 6
56644 +#define MCS_7 7
56645 +#define MCS_8 8 // 2S
56646 +#define MCS_9 9
56647 +#define MCS_10 10
56648 +#define MCS_11 11
56649 +#define MCS_12 12
56650 +#define MCS_13 13
56651 +#define MCS_14 14
56652 +#define MCS_15 15
56653 +#define MCS_16 16 // 3*3
56654 +#define MCS_17 17
56655 +#define MCS_18 18
56656 +#define MCS_19 19
56657 +#define MCS_20 20
56658 +#define MCS_21 21
56659 +#define MCS_22 22
56660 +#define MCS_23 23
56661 +#define MCS_32 32
56662 +#define MCS_AUTO 33
56663 +
56664 +#ifdef DOT11_N_SUPPORT
56665 +// OID_HTPHYMODE
56666 +// MODE
56667 +#define HTMODE_MM 0
56668 +#define HTMODE_GF 1
56669 +#endif // DOT11_N_SUPPORT //
56670 +
56671 +// Fixed Tx MODE - HT, CCK or OFDM
56672 +#define FIXED_TXMODE_HT 0
56673 +#define FIXED_TXMODE_CCK 1
56674 +#define FIXED_TXMODE_OFDM 2
56675 +// BW
56676 +#define BW_20 BAND_WIDTH_20
56677 +#define BW_40 BAND_WIDTH_40
56678 +#define BW_BOTH BAND_WIDTH_BOTH
56679 +#define BW_10 BAND_WIDTH_10 // 802.11j has 10MHz. This definition is for internal usage. doesn't fill in the IE or other field.
56680 +
56681 +#ifdef DOT11_N_SUPPORT
56682 +// SHORTGI
56683 +#define GI_400 GAP_INTERVAL_400 // only support in HT mode
56684 +#define GI_BOTH GAP_INTERVAL_BOTH
56685 +#endif // DOT11_N_SUPPORT //
56686 +#define GI_800 GAP_INTERVAL_800
56687 +// STBC
56688 +#define STBC_NONE 0
56689 +#ifdef DOT11_N_SUPPORT
56690 +#define STBC_USE 1 // limited use in rt2860b phy
56691 +#define RXSTBC_ONE 1 // rx support of one spatial stream
56692 +#define RXSTBC_TWO 2 // rx support of 1 and 2 spatial stream
56693 +#define RXSTBC_THR 3 // rx support of 1~3 spatial stream
56694 +// MCS FEEDBACK
56695 +#define MCSFBK_NONE 0 // not support mcs feedback /
56696 +#define MCSFBK_RSV 1 // reserved
56697 +#define MCSFBK_UNSOLICIT 2 // only support unsolict mcs feedback
56698 +#define MCSFBK_MRQ 3 // response to both MRQ and unsolict mcs feedback
56699 +
56700 +// MIMO power safe
56701 +#define MMPS_STATIC 0
56702 +#define MMPS_DYNAMIC 1
56703 +#define MMPS_RSV 2
56704 +#define MMPS_ENABLE 3
56705 +
56706 +
56707 +// A-MSDU size
56708 +#define AMSDU_0 0
56709 +#define AMSDU_1 1
56710 +
56711 +#endif // DOT11_N_SUPPORT //
56712 +
56713 +// MCS use 7 bits
56714 +#define TXRATEMIMO 0x80
56715 +#define TXRATEMCS 0x7F
56716 +#define TXRATEOFDM 0x7F
56717 +#define RATE_1 0
56718 +#define RATE_2 1
56719 +#define RATE_5_5 2
56720 +#define RATE_11 3
56721 +#define RATE_6 4 // OFDM
56722 +#define RATE_9 5 // OFDM
56723 +#define RATE_12 6 // OFDM
56724 +#define RATE_18 7 // OFDM
56725 +#define RATE_24 8 // OFDM
56726 +#define RATE_36 9 // OFDM
56727 +#define RATE_48 10 // OFDM
56728 +#define RATE_54 11 // OFDM
56729 +#define RATE_FIRST_OFDM_RATE RATE_6
56730 +#define RATE_LAST_OFDM_RATE RATE_54
56731 +#define RATE_6_5 12 // HT mix
56732 +#define RATE_13 13 // HT mix
56733 +#define RATE_19_5 14 // HT mix
56734 +#define RATE_26 15 // HT mix
56735 +#define RATE_39 16 // HT mix
56736 +#define RATE_52 17 // HT mix
56737 +#define RATE_58_5 18 // HT mix
56738 +#define RATE_65 19 // HT mix
56739 +#define RATE_78 20 // HT mix
56740 +#define RATE_104 21 // HT mix
56741 +#define RATE_117 22 // HT mix
56742 +#define RATE_130 23 // HT mix
56743 +//#define RATE_AUTO_SWITCH 255 // for StaCfg.FixedTxRate only
56744 +#define HTRATE_0 12
56745 +#define RATE_FIRST_MM_RATE HTRATE_0
56746 +#define RATE_FIRST_HT_RATE HTRATE_0
56747 +#define RATE_LAST_HT_RATE HTRATE_0
56748 +
56749 +// pTxWI->txop
56750 +#define IFS_HTTXOP 0 // The txop will be handles by ASIC.
56751 +#define IFS_PIFS 1
56752 +#define IFS_SIFS 2
56753 +#define IFS_BACKOFF 3
56754 +
56755 +// pTxD->RetryMode
56756 +#define LONG_RETRY 1
56757 +#define SHORT_RETRY 0
56758 +
56759 +// Country Region definition
56760 +#define REGION_MINIMUM_BG_BAND 0
56761 +#define REGION_0_BG_BAND 0 // 1-11
56762 +#define REGION_1_BG_BAND 1 // 1-13
56763 +#define REGION_2_BG_BAND 2 // 10-11
56764 +#define REGION_3_BG_BAND 3 // 10-13
56765 +#define REGION_4_BG_BAND 4 // 14
56766 +#define REGION_5_BG_BAND 5 // 1-14
56767 +#define REGION_6_BG_BAND 6 // 3-9
56768 +#define REGION_7_BG_BAND 7 // 5-13
56769 +#define REGION_31_BG_BAND 31 // 5-13
56770 +#define REGION_MAXIMUM_BG_BAND 7
56771 +
56772 +#define REGION_MINIMUM_A_BAND 0
56773 +#define REGION_0_A_BAND 0 // 36, 40, 44, 48, 52, 56, 60, 64, 149, 153, 157, 161, 165
56774 +#define REGION_1_A_BAND 1 // 36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140
56775 +#define REGION_2_A_BAND 2 // 36, 40, 44, 48, 52, 56, 60, 64
56776 +#define REGION_3_A_BAND 3 // 52, 56, 60, 64, 149, 153, 157, 161
56777 +#define REGION_4_A_BAND 4 // 149, 153, 157, 161, 165
56778 +#define REGION_5_A_BAND 5 // 149, 153, 157, 161
56779 +#define REGION_6_A_BAND 6 // 36, 40, 44, 48
56780 +#define REGION_7_A_BAND 7 // 36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 124, 128, 132, 136, 140, 149, 153, 157, 161, 165
56781 +#define REGION_8_A_BAND 8 // 52, 56, 60, 64
56782 +#define REGION_9_A_BAND 9 // 36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 132, 136, 140, 149, 153, 157, 161, 165
56783 +#define REGION_10_A_BAND 10 // 36, 40, 44, 48, 149, 153, 157, 161, 165
56784 +#define REGION_11_A_BAND 11 // 36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116, 120, 149, 153, 157, 161
56785 +#define REGION_MAXIMUM_A_BAND 11
56786 +
56787 +// pTxD->CipherAlg
56788 +#define CIPHER_NONE 0
56789 +#define CIPHER_WEP64 1
56790 +#define CIPHER_WEP128 2
56791 +#define CIPHER_TKIP 3
56792 +#define CIPHER_AES 4
56793 +#define CIPHER_CKIP64 5
56794 +#define CIPHER_CKIP128 6
56795 +#define CIPHER_TKIP_NO_MIC 7 // MIC appended by driver: not a valid value in hardware key table
56796 +#define CIPHER_SMS4 8
56797 +
56798 +// value domain of pAd->RfIcType
56799 +#define RFIC_2820 1 // 2.4G 2T3R
56800 +#define RFIC_2850 2 // 2.4G/5G 2T3R
56801 +#define RFIC_2720 3 // 2.4G 1T2R
56802 +#define RFIC_2750 4 // 2.4G/5G 1T2R
56803 +#define RFIC_3020 5 // 2.4G 1T1R
56804 +#define RFIC_2020 6 // 2.4G B/G
56805 +
56806 +// LED Status.
56807 +#define LED_LINK_DOWN 0
56808 +#define LED_LINK_UP 1
56809 +#define LED_RADIO_OFF 2
56810 +#define LED_RADIO_ON 3
56811 +#define LED_HALT 4
56812 +#define LED_WPS 5
56813 +#define LED_ON_SITE_SURVEY 6
56814 +#define LED_POWER_UP 7
56815 +
56816 +// value domain of pAd->LedCntl.LedMode and E2PROM
56817 +#define LED_MODE_DEFAULT 0
56818 +#define LED_MODE_TWO_LED 1
56819 +#define LED_MODE_SIGNAL_STREGTH 8 // EEPROM define =8
56820 +
56821 +// RC4 init value, used fro WEP & TKIP
56822 +#define PPPINITFCS32 0xffffffff /* Initial FCS value */
56823 +
56824 +// value domain of pAd->StaCfg.PortSecured. 802.1X controlled port definition
56825 +#define WPA_802_1X_PORT_SECURED 1
56826 +#define WPA_802_1X_PORT_NOT_SECURED 2
56827 +
56828 +#define PAIRWISE_KEY 1
56829 +#define GROUP_KEY 2
56830 +
56831 +//definition of DRS
56832 +#define MAX_STEP_OF_TX_RATE_SWITCH 32
56833 +
56834 +
56835 +// pre-allocated free NDIS PACKET/BUFFER poll for internal usage
56836 +#define MAX_NUM_OF_FREE_NDIS_PACKET 128
56837 +
56838 +//Block ACK
56839 +#define MAX_TX_REORDERBUF 64
56840 +#define MAX_RX_REORDERBUF 64
56841 +#define DEFAULT_TX_TIMEOUT 30
56842 +#define DEFAULT_RX_TIMEOUT 30
56843 +
56844 +// definition of Recipient or Originator
56845 +#define I_RECIPIENT TRUE
56846 +#define I_ORIGINATOR FALSE
56847 +
56848 +#define DEFAULT_BBP_TX_POWER 0
56849 +#define DEFAULT_RF_TX_POWER 5
56850 +
56851 +#define MAX_INI_BUFFER_SIZE 4096
56852 +#define MAX_PARAM_BUFFER_SIZE (2048) // enough for ACL (18*64)
56853 + //18 : the length of Mac address acceptable format "01:02:03:04:05:06;")
56854 + //64 : MAX_NUM_OF_ACL_LIST
56855 +// definition of pAd->OpMode
56856 +#define OPMODE_STA 0
56857 +#define OPMODE_AP 1
56858 +//#define OPMODE_L3_BRG 2 // as AP and STA at the same time
56859 +
56860 +#ifdef RT_BIG_ENDIAN
56861 +#define DIR_READ 0
56862 +#define DIR_WRITE 1
56863 +#define TYPE_TXD 0
56864 +#define TYPE_RXD 1
56865 +#define TYPE_TXINFO 0
56866 +#define TYPE_RXINFO 1
56867 +#define TYPE_TXWI 0
56868 +#define TYPE_RXWI 1
56869 +#endif
56870 +
56871 +// ========================= AP rtmp_def.h ===========================
56872 +// value domain for pAd->EventTab.Log[].Event
56873 +#define EVENT_RESET_ACCESS_POINT 0 // Log = "hh:mm:ss Restart Access Point"
56874 +#define EVENT_ASSOCIATED 1 // Log = "hh:mm:ss STA 00:01:02:03:04:05 associated"
56875 +#define EVENT_DISASSOCIATED 2 // Log = "hh:mm:ss STA 00:01:02:03:04:05 left this BSS"
56876 +#define EVENT_AGED_OUT 3 // Log = "hh:mm:ss STA 00:01:02:03:04:05 was aged-out and removed from this BSS"
56877 +#define EVENT_COUNTER_M 4
56878 +#define EVENT_INVALID_PSK 5
56879 +#define EVENT_MAX_EVENT_TYPE 6
56880 +// ==== end of AP rtmp_def.h ============
56881 +
56882 +// definition RSSI Number
56883 +#define RSSI_0 0
56884 +#define RSSI_1 1
56885 +#define RSSI_2 2
56886 +
56887 +// definition of radar detection
56888 +#define RD_NORMAL_MODE 0 // Not found radar signal
56889 +#define RD_SWITCHING_MODE 1 // Found radar signal, and doing channel switch
56890 +#define RD_SILENCE_MODE 2 // After channel switch, need to be silence a while to ensure radar not found
56891 +
56892 +//Driver defined cid for mapping status and command.
56893 +#define SLEEPCID 0x11
56894 +#define WAKECID 0x22
56895 +#define QUERYPOWERCID 0x33
56896 +#define OWNERMCU 0x1
56897 +#define OWNERCPU 0x0
56898 +
56899 +// MBSSID definition
56900 +#define ENTRY_NOT_FOUND 0xFF
56901 +
56902 +
56903 +/* After Linux 2.6.9,
56904 + * VLAN module use Private (from user) interface flags (netdevice->priv_flags).
56905 + * #define IFF_802_1Q_VLAN 0x1 -- 802.1Q VLAN device. in if.h
56906 + * ref to ip_sabotage_out() [ out->priv_flags & IFF_802_1Q_VLAN ] in br_netfilter.c
56907 + *
56908 + * For this reason, we MUST use EVEN value in priv_flags
56909 + */
56910 +#define INT_MAIN 0x0100
56911 +#define INT_MBSSID 0x0200
56912 +#define INT_WDS 0x0300
56913 +#define INT_APCLI 0x0400
56914 +#define INT_MESH 0x0500
56915 +
56916 +// Use bitmap to allow coexist of ATE_TXFRAME and ATE_RXFRAME(i.e.,to support LoopBack mode)
56917 +#ifdef RALINK_ATE
56918 +#define ATE_START 0x00 // Start ATE
56919 +#define ATE_STOP 0x80 // Stop ATE
56920 +#define ATE_TXCONT 0x05 // Continuous Transmit
56921 +#define ATE_TXCARR 0x09 // Transmit Carrier
56922 +#define ATE_TXCARRSUPP 0x11 // Transmit Carrier Suppression
56923 +#define ATE_TXFRAME 0x01 // Transmit Frames
56924 +#define ATE_RXFRAME 0x02 // Receive Frames
56925 +#ifdef RALINK_28xx_QA
56926 +#define ATE_TXSTOP 0xe2 // Stop Transmition(i.e., TXCONT, TXCARR, TXCARRSUPP, and TXFRAME)
56927 +#define ATE_RXSTOP 0xfd // Stop receiving Frames
56928 +#define BBP22_TXFRAME 0x00 // Transmit Frames
56929 +#define BBP22_TXCONT_OR_CARRSUPP 0x80 // Continuous Transmit or Carrier Suppression
56930 +#define BBP22_TXCARR 0xc1 // Transmit Carrier
56931 +#define BBP24_TXCONT 0x00 // Continuous Transmit
56932 +#define BBP24_CARRSUPP 0x01 // Carrier Suppression
56933 +#endif // RALINK_28xx_QA //
56934 +#endif // RALINK_ATE //
56935 +
56936 +// WEP Key TYPE
56937 +#define WEP_HEXADECIMAL_TYPE 0
56938 +#define WEP_ASCII_TYPE 1
56939 +
56940 +
56941 +
56942 +// WIRELESS EVENTS definition
56943 +/* Max number of char in custom event, refer to wireless_tools.28/wireless.20.h */
56944 +#define IW_CUSTOM_MAX_LEN 255 /* In bytes */
56945 +
56946 +// For system event - start
56947 +#define IW_SYS_EVENT_FLAG_START 0x0200
56948 +#define IW_ASSOC_EVENT_FLAG 0x0200
56949 +#define IW_DISASSOC_EVENT_FLAG 0x0201
56950 +#define IW_DEAUTH_EVENT_FLAG 0x0202
56951 +#define IW_AGEOUT_EVENT_FLAG 0x0203
56952 +#define IW_COUNTER_MEASURES_EVENT_FLAG 0x0204
56953 +#define IW_REPLAY_COUNTER_DIFF_EVENT_FLAG 0x0205
56954 +#define IW_RSNIE_DIFF_EVENT_FLAG 0x0206
56955 +#define IW_MIC_DIFF_EVENT_FLAG 0x0207
56956 +#define IW_ICV_ERROR_EVENT_FLAG 0x0208
56957 +#define IW_MIC_ERROR_EVENT_FLAG 0x0209
56958 +#define IW_GROUP_HS_TIMEOUT_EVENT_FLAG 0x020A
56959 +#define IW_PAIRWISE_HS_TIMEOUT_EVENT_FLAG 0x020B
56960 +#define IW_RSNIE_SANITY_FAIL_EVENT_FLAG 0x020C
56961 +#define IW_SET_KEY_DONE_WPA1_EVENT_FLAG 0x020D
56962 +#define IW_SET_KEY_DONE_WPA2_EVENT_FLAG 0x020E
56963 +#define IW_STA_LINKUP_EVENT_FLAG 0x020F
56964 +#define IW_STA_LINKDOWN_EVENT_FLAG 0x0210
56965 +#define IW_SCAN_COMPLETED_EVENT_FLAG 0x0211
56966 +#define IW_SCAN_ENQUEUE_FAIL_EVENT_FLAG 0x0212
56967 +// if add new system event flag, please upadte the IW_SYS_EVENT_FLAG_END
56968 +#define IW_SYS_EVENT_FLAG_END 0x0212
56969 +#define IW_SYS_EVENT_TYPE_NUM (IW_SYS_EVENT_FLAG_END - IW_SYS_EVENT_FLAG_START + 1)
56970 +// For system event - end
56971 +
56972 +// For spoof attack event - start
56973 +#define IW_SPOOF_EVENT_FLAG_START 0x0300
56974 +#define IW_CONFLICT_SSID_EVENT_FLAG 0x0300
56975 +#define IW_SPOOF_ASSOC_RESP_EVENT_FLAG 0x0301
56976 +#define IW_SPOOF_REASSOC_RESP_EVENT_FLAG 0x0302
56977 +#define IW_SPOOF_PROBE_RESP_EVENT_FLAG 0x0303
56978 +#define IW_SPOOF_BEACON_EVENT_FLAG 0x0304
56979 +#define IW_SPOOF_DISASSOC_EVENT_FLAG 0x0305
56980 +#define IW_SPOOF_AUTH_EVENT_FLAG 0x0306
56981 +#define IW_SPOOF_DEAUTH_EVENT_FLAG 0x0307
56982 +#define IW_SPOOF_UNKNOWN_MGMT_EVENT_FLAG 0x0308
56983 +#define IW_REPLAY_ATTACK_EVENT_FLAG 0x0309
56984 +// if add new spoof attack event flag, please upadte the IW_SPOOF_EVENT_FLAG_END
56985 +#define IW_SPOOF_EVENT_FLAG_END 0x0309
56986 +#define IW_SPOOF_EVENT_TYPE_NUM (IW_SPOOF_EVENT_FLAG_END - IW_SPOOF_EVENT_FLAG_START + 1)
56987 +// For spoof attack event - end
56988 +
56989 +// For flooding attack event - start
56990 +#define IW_FLOOD_EVENT_FLAG_START 0x0400
56991 +#define IW_FLOOD_AUTH_EVENT_FLAG 0x0400
56992 +#define IW_FLOOD_ASSOC_REQ_EVENT_FLAG 0x0401
56993 +#define IW_FLOOD_REASSOC_REQ_EVENT_FLAG 0x0402
56994 +#define IW_FLOOD_PROBE_REQ_EVENT_FLAG 0x0403
56995 +#define IW_FLOOD_DISASSOC_EVENT_FLAG 0x0404
56996 +#define IW_FLOOD_DEAUTH_EVENT_FLAG 0x0405
56997 +#define IW_FLOOD_EAP_REQ_EVENT_FLAG 0x0406
56998 +// if add new flooding attack event flag, please upadte the IW_FLOOD_EVENT_FLAG_END
56999 +#define IW_FLOOD_EVENT_FLAG_END 0x0406
57000 +#define IW_FLOOD_EVENT_TYPE_NUM (IW_FLOOD_EVENT_FLAG_END - IW_FLOOD_EVENT_FLAG_START + 1)
57001 +// For flooding attack - end
57002 +
57003 +// End - WIRELESS EVENTS definition
57004 +
57005 +#ifdef CONFIG_STA_SUPPORT
57006 +// definition for DLS, kathy
57007 +#define MAX_NUM_OF_INIT_DLS_ENTRY 1
57008 +#define MAX_NUM_OF_DLS_ENTRY MAX_NUMBER_OF_DLS_ENTRY
57009 +
57010 +//Block ACK , rt2860, kathy
57011 +#define MAX_TX_REORDERBUF 64
57012 +#define MAX_RX_REORDERBUF 64
57013 +#define DEFAULT_TX_TIMEOUT 30
57014 +#define DEFAULT_RX_TIMEOUT 30
57015 +#ifndef CONFIG_AP_SUPPORT
57016 +#define MAX_BARECI_SESSION 8
57017 +#endif
57018 +
57019 +#ifndef IW_ESSID_MAX_SIZE
57020 +/* Maximum size of the ESSID and pAd->nickname strings */
57021 +#define IW_ESSID_MAX_SIZE 32
57022 +#endif
57023 +#endif // CONFIG_STA_SUPPORT //
57024 +
57025 +#ifdef MCAST_RATE_SPECIFIC
57026 +#define MCAST_DISABLE 0
57027 +#define MCAST_CCK 1
57028 +#define MCAST_OFDM 2
57029 +#define MCAST_HTMIX 3
57030 +#endif // MCAST_RATE_SPECIFIC //
57031 +
57032 +// For AsicRadioOff/AsicRadioOn function
57033 +#define DOT11POWERSAVE 0
57034 +#define GUIRADIO_OFF 1
57035 +#define RTMP_HALT 2
57036 +#define GUI_IDLE_POWER_SAVE 3
57037 +// --
57038 +
57039 +
57040 +// definition for WpaSupport flag
57041 +#define WPA_SUPPLICANT_DISABLE 0
57042 +#define WPA_SUPPLICANT_ENABLE 1
57043 +#define WPA_SUPPLICANT_ENABLE_WITH_WEB_UI 2
57044 +
57045 +// Endian byte swapping codes
57046 +#define SWAP16(x) \
57047 + ((UINT16)( \
57048 + (((UINT16)(x) & (UINT16) 0x00ffU) << 8) | \
57049 + (((UINT16)(x) & (UINT16) 0xff00U) >> 8) ))
57050 +
57051 +#define SWAP32(x) \
57052 + ((UINT32)( \
57053 + (((UINT32)(x) & (UINT32) 0x000000ffUL) << 24) | \
57054 + (((UINT32)(x) & (UINT32) 0x0000ff00UL) << 8) | \
57055 + (((UINT32)(x) & (UINT32) 0x00ff0000UL) >> 8) | \
57056 + (((UINT32)(x) & (UINT32) 0xff000000UL) >> 24) ))
57057 +
57058 +#define SWAP64(x) \
57059 + ((UINT64)( \
57060 + (UINT64)(((UINT64)(x) & (UINT64) 0x00000000000000ffULL) << 56) | \
57061 + (UINT64)(((UINT64)(x) & (UINT64) 0x000000000000ff00ULL) << 40) | \
57062 + (UINT64)(((UINT64)(x) & (UINT64) 0x0000000000ff0000ULL) << 24) | \
57063 + (UINT64)(((UINT64)(x) & (UINT64) 0x00000000ff000000ULL) << 8) | \
57064 + (UINT64)(((UINT64)(x) & (UINT64) 0x000000ff00000000ULL) >> 8) | \
57065 + (UINT64)(((UINT64)(x) & (UINT64) 0x0000ff0000000000ULL) >> 24) | \
57066 + (UINT64)(((UINT64)(x) & (UINT64) 0x00ff000000000000ULL) >> 40) | \
57067 + (UINT64)(((UINT64)(x) & (UINT64) 0xff00000000000000ULL) >> 56) ))
57068 +
57069 +#ifdef RT_BIG_ENDIAN
57070 +
57071 +#define cpu2le64(x) SWAP64((x))
57072 +#define le2cpu64(x) SWAP64((x))
57073 +#define cpu2le32(x) SWAP32((x))
57074 +#define le2cpu32(x) SWAP32((x))
57075 +#define cpu2le16(x) SWAP16((x))
57076 +#define le2cpu16(x) SWAP16((x))
57077 +#define cpu2be64(x) ((UINT64)(x))
57078 +#define be2cpu64(x) ((UINT64)(x))
57079 +#define cpu2be32(x) ((UINT32)(x))
57080 +#define be2cpu32(x) ((UINT32)(x))
57081 +#define cpu2be16(x) ((UINT16)(x))
57082 +#define be2cpu16(x) ((UINT16)(x))
57083 +
57084 +#else // Little_Endian
57085 +
57086 +#define cpu2le64(x) ((UINT64)(x))
57087 +#define le2cpu64(x) ((UINT64)(x))
57088 +#define cpu2le32(x) ((UINT32)(x))
57089 +#define le2cpu32(x) ((UINT32)(x))
57090 +#define cpu2le16(x) ((UINT16)(x))
57091 +#define le2cpu16(x) ((UINT16)(x))
57092 +#define cpu2be64(x) SWAP64((x))
57093 +#define be2cpu64(x) SWAP64((x))
57094 +#define cpu2be32(x) SWAP32((x))
57095 +#define be2cpu32(x) SWAP32((x))
57096 +#define cpu2be16(x) SWAP16((x))
57097 +#define be2cpu16(x) SWAP16((x))
57098 +
57099 +#endif // RT_BIG_ENDIAN
57100 +
57101 +#endif // __RTMP_DEF_H__
57102 +
57103 +
57104 --- /dev/null
57105 +++ b/drivers/staging/rt2860/rtmp.h
57106 @@ -0,0 +1,7177 @@
57107 +/*
57108 + *************************************************************************
57109 + * Ralink Tech Inc.
57110 + * 5F., No.36, Taiyuan St., Jhubei City,
57111 + * Hsinchu County 302,
57112 + * Taiwan, R.O.C.
57113 + *
57114 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
57115 + *
57116 + * This program is free software; you can redistribute it and/or modify *
57117 + * it under the terms of the GNU General Public License as published by *
57118 + * the Free Software Foundation; either version 2 of the License, or *
57119 + * (at your option) any later version. *
57120 + * *
57121 + * This program is distributed in the hope that it will be useful, *
57122 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
57123 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
57124 + * GNU General Public License for more details. *
57125 + * *
57126 + * You should have received a copy of the GNU General Public License *
57127 + * along with this program; if not, write to the *
57128 + * Free Software Foundation, Inc., *
57129 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
57130 + * *
57131 + *************************************************************************
57132 +
57133 + Module Name:
57134 + rtmp.h
57135 +
57136 + Abstract:
57137 + Miniport generic portion header file
57138 +
57139 + Revision History:
57140 + Who When What
57141 + -------- ---------- ----------------------------------------------
57142 + Paul Lin 2002-08-01 created
57143 + James Tan 2002-09-06 modified (Revise NTCRegTable)
57144 + John Chang 2004-09-06 modified for RT2600
57145 +*/
57146 +#ifndef __RTMP_H__
57147 +#define __RTMP_H__
57148 +
57149 +#include "link_list.h"
57150 +#include "spectrum_def.h"
57151 +
57152 +
57153 +#ifdef CONFIG_STA_SUPPORT
57154 +#include "aironet.h"
57155 +#endif // CONFIG_STA_SUPPORT //
57156 +
57157 +//#define DBG_DIAGNOSE 1
57158 +
57159 +#if defined(CONFIG_AP_SUPPORT) && defined(CONFIG_STA_SUPPORT)
57160 +#define IF_DEV_CONFIG_OPMODE_ON_AP(_pAd) if(_pAd->OpMode == OPMODE_AP)
57161 +#define IF_DEV_CONFIG_OPMODE_ON_STA(_pAd) if(_pAd->OpMode == OPMODE_STA)
57162 +#else
57163 +#define IF_DEV_CONFIG_OPMODE_ON_AP(_pAd)
57164 +#define IF_DEV_CONFIG_OPMODE_ON_STA(_pAd)
57165 +#endif
57166 +
57167 +#define VIRTUAL_IF_INC(__pAd) ((__pAd)->VirtualIfCnt++)
57168 +#define VIRTUAL_IF_DEC(__pAd) ((__pAd)->VirtualIfCnt--)
57169 +#define VIRTUAL_IF_NUM(__pAd) ((__pAd)->VirtualIfCnt)
57170 +
57171 +
57172 +
57173 +//
57174 +// NDIS Version definitions
57175 +//
57176 +#ifdef NDIS50_MINIPORT
57177 +#define RTMP_NDIS_MAJOR_VERSION 5
57178 +#define RTMP_NDIS_MINOR_VERSION 0
57179 +#endif
57180 +
57181 +#ifdef NDIS51_MINIPORT
57182 +#define RTMP_NDIS_MAJOR_VERSION 5
57183 +#define RTMP_NDIS_MINOR_VERSION 1
57184 +#endif
57185 +
57186 +extern char NIC_VENDOR_DESC[];
57187 +extern int NIC_VENDOR_DESC_LEN;
57188 +
57189 +extern unsigned char SNAP_AIRONET[];
57190 +extern unsigned char CipherSuiteCiscoCCKM[];
57191 +extern unsigned char CipherSuiteCiscoCCKMLen;
57192 +extern unsigned char CipherSuiteCiscoCCKM24[];
57193 +extern unsigned char CipherSuiteCiscoCCKM24Len;
57194 +extern unsigned char CipherSuiteCCXTkip[];
57195 +extern unsigned char CipherSuiteCCXTkipLen;
57196 +extern unsigned char CISCO_OUI[];
57197 +extern UCHAR BaSizeArray[4];
57198 +
57199 +extern UCHAR BROADCAST_ADDR[MAC_ADDR_LEN];
57200 +extern UCHAR MULTICAST_ADDR[MAC_ADDR_LEN];
57201 +extern UCHAR ZERO_MAC_ADDR[MAC_ADDR_LEN];
57202 +extern ULONG BIT32[32];
57203 +extern UCHAR BIT8[8];
57204 +extern char* CipherName[];
57205 +extern char* MCSToMbps[];
57206 +extern UCHAR RxwiMCSToOfdmRate[12];
57207 +extern UCHAR SNAP_802_1H[6];
57208 +extern UCHAR SNAP_BRIDGE_TUNNEL[6];
57209 +extern UCHAR SNAP_AIRONET[8];
57210 +extern UCHAR CKIP_LLC_SNAP[8];
57211 +extern UCHAR EAPOL_LLC_SNAP[8];
57212 +extern UCHAR EAPOL[2];
57213 +extern UCHAR IPX[2];
57214 +extern UCHAR APPLE_TALK[2];
57215 +extern UCHAR RateIdToPlcpSignal[12]; // see IEEE802.11a-1999 p.14
57216 +extern UCHAR OfdmRateToRxwiMCS[];
57217 +extern UCHAR OfdmSignalToRateId[16] ;
57218 +extern UCHAR default_cwmin[4];
57219 +extern UCHAR default_cwmax[4];
57220 +extern UCHAR default_sta_aifsn[4];
57221 +extern UCHAR MapUserPriorityToAccessCategory[8];
57222 +
57223 +extern USHORT RateUpPER[];
57224 +extern USHORT RateDownPER[];
57225 +extern UCHAR Phy11BNextRateDownward[];
57226 +extern UCHAR Phy11BNextRateUpward[];
57227 +extern UCHAR Phy11BGNextRateDownward[];
57228 +extern UCHAR Phy11BGNextRateUpward[];
57229 +extern UCHAR Phy11ANextRateDownward[];
57230 +extern UCHAR Phy11ANextRateUpward[];
57231 +extern CHAR RssiSafeLevelForTxRate[];
57232 +extern UCHAR RateIdToMbps[];
57233 +extern USHORT RateIdTo500Kbps[];
57234 +
57235 +extern UCHAR CipherSuiteWpaNoneTkip[];
57236 +extern UCHAR CipherSuiteWpaNoneTkipLen;
57237 +
57238 +extern UCHAR CipherSuiteWpaNoneAes[];
57239 +extern UCHAR CipherSuiteWpaNoneAesLen;
57240 +
57241 +extern UCHAR SsidIe;
57242 +extern UCHAR SupRateIe;
57243 +extern UCHAR ExtRateIe;
57244 +
57245 +#ifdef DOT11_N_SUPPORT
57246 +extern UCHAR HtCapIe;
57247 +extern UCHAR AddHtInfoIe;
57248 +extern UCHAR NewExtChanIe;
57249 +#ifdef DOT11N_DRAFT3
57250 +extern UCHAR ExtHtCapIe;
57251 +#endif // DOT11N_DRAFT3 //
57252 +#endif // DOT11_N_SUPPORT //
57253 +
57254 +extern UCHAR ErpIe;
57255 +extern UCHAR DsIe;
57256 +extern UCHAR TimIe;
57257 +extern UCHAR WpaIe;
57258 +extern UCHAR Wpa2Ie;
57259 +extern UCHAR IbssIe;
57260 +extern UCHAR Ccx2Ie;
57261 +
57262 +extern UCHAR WPA_OUI[];
57263 +extern UCHAR RSN_OUI[];
57264 +extern UCHAR WME_INFO_ELEM[];
57265 +extern UCHAR WME_PARM_ELEM[];
57266 +extern UCHAR Ccx2QosInfo[];
57267 +extern UCHAR Ccx2IeInfo[];
57268 +extern UCHAR RALINK_OUI[];
57269 +extern UCHAR PowerConstraintIE[];
57270 +
57271 +
57272 +extern UCHAR RateSwitchTable[];
57273 +extern UCHAR RateSwitchTable11B[];
57274 +extern UCHAR RateSwitchTable11G[];
57275 +extern UCHAR RateSwitchTable11BG[];
57276 +
57277 +#ifdef DOT11_N_SUPPORT
57278 +extern UCHAR RateSwitchTable11BGN1S[];
57279 +extern UCHAR RateSwitchTable11BGN2S[];
57280 +extern UCHAR RateSwitchTable11BGN2SForABand[];
57281 +extern UCHAR RateSwitchTable11N1S[];
57282 +extern UCHAR RateSwitchTable11N2S[];
57283 +extern UCHAR RateSwitchTable11N2SForABand[];
57284 +
57285 +#ifdef CONFIG_STA_SUPPORT
57286 +extern UCHAR PRE_N_HT_OUI[];
57287 +#endif // CONFIG_STA_SUPPORT //
57288 +#endif // DOT11_N_SUPPORT //
57289 +
57290 +#define MAXSEQ (0xFFF)
57291 +
57292 +#ifdef RALINK_ATE
57293 +typedef struct _ATE_INFO {
57294 + UCHAR Mode;
57295 + CHAR TxPower0;
57296 + CHAR TxPower1;
57297 + CHAR TxAntennaSel;
57298 + CHAR RxAntennaSel;
57299 + TXWI_STRUC TxWI; // TXWI
57300 + USHORT QID;
57301 + UCHAR Addr1[MAC_ADDR_LEN];
57302 + UCHAR Addr2[MAC_ADDR_LEN];
57303 + UCHAR Addr3[MAC_ADDR_LEN];
57304 + UCHAR Channel;
57305 + UINT32 TxLength;
57306 + UINT32 TxCount;
57307 + UINT32 TxDoneCount; // Tx DMA Done
57308 + UINT32 RFFreqOffset;
57309 + BOOLEAN bRxFer;
57310 + BOOLEAN bQATxStart; // Have compiled QA in and use it to ATE tx.
57311 + BOOLEAN bQARxStart; // Have compiled QA in and use it to ATE rx.
57312 +#ifdef RT2860
57313 + BOOLEAN bFWLoading; // Reload firmware when ATE is done.
57314 +#endif // RT2860 //
57315 + UINT32 RxTotalCnt;
57316 + UINT32 RxCntPerSec;
57317 +
57318 + CHAR LastSNR0; // last received SNR
57319 + CHAR LastSNR1; // last received SNR for 2nd antenna
57320 + CHAR LastRssi0; // last received RSSI
57321 + CHAR LastRssi1; // last received RSSI for 2nd antenna
57322 + CHAR LastRssi2; // last received RSSI for 3rd antenna
57323 + CHAR AvgRssi0; // last 8 frames' average RSSI
57324 + CHAR AvgRssi1; // last 8 frames' average RSSI
57325 + CHAR AvgRssi2; // last 8 frames' average RSSI
57326 + SHORT AvgRssi0X8; // sum of last 8 frames' RSSI
57327 + SHORT AvgRssi1X8; // sum of last 8 frames' RSSI
57328 + SHORT AvgRssi2X8; // sum of last 8 frames' RSSI
57329 +
57330 + UINT32 NumOfAvgRssiSample;
57331 +
57332 +#ifdef RALINK_28xx_QA
57333 + // Tx frame
57334 + USHORT HLen; // Header Length
57335 + USHORT PLen; // Pattern Length
57336 + UCHAR Header[32]; // Header buffer
57337 + UCHAR Pattern[32]; // Pattern buffer
57338 + USHORT DLen; // Data Length
57339 + USHORT seq;
57340 + UINT32 CID;
57341 + THREAD_PID AtePid;
57342 + // counters
57343 + UINT32 U2M;
57344 + UINT32 OtherData;
57345 + UINT32 Beacon;
57346 + UINT32 OtherCount;
57347 + UINT32 TxAc0;
57348 + UINT32 TxAc1;
57349 + UINT32 TxAc2;
57350 + UINT32 TxAc3;
57351 + UINT32 TxHCCA;
57352 + UINT32 TxMgmt;
57353 + UINT32 RSSI0;
57354 + UINT32 RSSI1;
57355 + UINT32 RSSI2;
57356 + UINT32 SNR0;
57357 + UINT32 SNR1;
57358 + // control
57359 + //UINT32 Repeat; // Tx Cpu count
57360 + UCHAR TxStatus; // task Tx status // 0 --> task is idle, 1 --> task is running
57361 +#endif // RALINK_28xx_QA //
57362 +} ATE_INFO, *PATE_INFO;
57363 +
57364 +#ifdef RALINK_28xx_QA
57365 +struct ate_racfghdr {
57366 + UINT32 magic_no;
57367 + USHORT command_type;
57368 + USHORT command_id;
57369 + USHORT length;
57370 + USHORT sequence;
57371 + USHORT status;
57372 + UCHAR data[2046];
57373 +} __attribute__((packed));
57374 +#endif // RALINK_28xx_QA //
57375 +#endif // RALINK_ATE //
57376 +
57377 +#ifdef DOT11_N_SUPPORT
57378 +struct reordering_mpdu
57379 +{
57380 + struct reordering_mpdu *next;
57381 + PNDIS_PACKET pPacket; /* coverted to 802.3 frame */
57382 + int Sequence; /* sequence number of MPDU */
57383 + BOOLEAN bAMSDU;
57384 +};
57385 +
57386 +struct reordering_list
57387 +{
57388 + struct reordering_mpdu *next;
57389 + int qlen;
57390 +};
57391 +
57392 +struct reordering_mpdu_pool
57393 +{
57394 + PVOID mem;
57395 + NDIS_SPIN_LOCK lock;
57396 + struct reordering_list freelist;
57397 +};
57398 +#endif // DOT11_N_SUPPORT //
57399 +
57400 +typedef struct _RSSI_SAMPLE {
57401 + CHAR LastRssi0; // last received RSSI
57402 + CHAR LastRssi1; // last received RSSI
57403 + CHAR LastRssi2; // last received RSSI
57404 + CHAR AvgRssi0;
57405 + CHAR AvgRssi1;
57406 + CHAR AvgRssi2;
57407 + SHORT AvgRssi0X8;
57408 + SHORT AvgRssi1X8;
57409 + SHORT AvgRssi2X8;
57410 +} RSSI_SAMPLE;
57411 +
57412 +//
57413 +// Queue structure and macros
57414 +//
57415 +typedef struct _QUEUE_ENTRY {
57416 + struct _QUEUE_ENTRY *Next;
57417 +} QUEUE_ENTRY, *PQUEUE_ENTRY;
57418 +
57419 +// Queue structure
57420 +typedef struct _QUEUE_HEADER {
57421 + PQUEUE_ENTRY Head;
57422 + PQUEUE_ENTRY Tail;
57423 + ULONG Number;
57424 +} QUEUE_HEADER, *PQUEUE_HEADER;
57425 +
57426 +#define InitializeQueueHeader(QueueHeader) \
57427 +{ \
57428 + (QueueHeader)->Head = (QueueHeader)->Tail = NULL; \
57429 + (QueueHeader)->Number = 0; \
57430 +}
57431 +
57432 +#define RemoveHeadQueue(QueueHeader) \
57433 +(QueueHeader)->Head; \
57434 +{ \
57435 + PQUEUE_ENTRY pNext; \
57436 + if ((QueueHeader)->Head != NULL) \
57437 + { \
57438 + pNext = (QueueHeader)->Head->Next; \
57439 + (QueueHeader)->Head = pNext; \
57440 + if (pNext == NULL) \
57441 + (QueueHeader)->Tail = NULL; \
57442 + (QueueHeader)->Number--; \
57443 + } \
57444 +}
57445 +
57446 +#define InsertHeadQueue(QueueHeader, QueueEntry) \
57447 +{ \
57448 + ((PQUEUE_ENTRY)QueueEntry)->Next = (QueueHeader)->Head; \
57449 + (QueueHeader)->Head = (PQUEUE_ENTRY)(QueueEntry); \
57450 + if ((QueueHeader)->Tail == NULL) \
57451 + (QueueHeader)->Tail = (PQUEUE_ENTRY)(QueueEntry); \
57452 + (QueueHeader)->Number++; \
57453 +}
57454 +
57455 +#define InsertTailQueue(QueueHeader, QueueEntry) \
57456 +{ \
57457 + ((PQUEUE_ENTRY)QueueEntry)->Next = NULL; \
57458 + if ((QueueHeader)->Tail) \
57459 + (QueueHeader)->Tail->Next = (PQUEUE_ENTRY)(QueueEntry); \
57460 + else \
57461 + (QueueHeader)->Head = (PQUEUE_ENTRY)(QueueEntry); \
57462 + (QueueHeader)->Tail = (PQUEUE_ENTRY)(QueueEntry); \
57463 + (QueueHeader)->Number++; \
57464 +}
57465 +
57466 +//
57467 +// Macros for flag and ref count operations
57468 +//
57469 +#define RTMP_SET_FLAG(_M, _F) ((_M)->Flags |= (_F))
57470 +#define RTMP_CLEAR_FLAG(_M, _F) ((_M)->Flags &= ~(_F))
57471 +#define RTMP_CLEAR_FLAGS(_M) ((_M)->Flags = 0)
57472 +#define RTMP_TEST_FLAG(_M, _F) (((_M)->Flags & (_F)) != 0)
57473 +#define RTMP_TEST_FLAGS(_M, _F) (((_M)->Flags & (_F)) == (_F))
57474 +
57475 +#define OPSTATUS_SET_FLAG(_pAd, _F) ((_pAd)->CommonCfg.OpStatusFlags |= (_F))
57476 +#define OPSTATUS_CLEAR_FLAG(_pAd, _F) ((_pAd)->CommonCfg.OpStatusFlags &= ~(_F))
57477 +#define OPSTATUS_TEST_FLAG(_pAd, _F) (((_pAd)->CommonCfg.OpStatusFlags & (_F)) != 0)
57478 +
57479 +#define CLIENT_STATUS_SET_FLAG(_pEntry,_F) ((_pEntry)->ClientStatusFlags |= (_F))
57480 +#define CLIENT_STATUS_CLEAR_FLAG(_pEntry,_F) ((_pEntry)->ClientStatusFlags &= ~(_F))
57481 +#define CLIENT_STATUS_TEST_FLAG(_pEntry,_F) (((_pEntry)->ClientStatusFlags & (_F)) != 0)
57482 +
57483 +#define RX_FILTER_SET_FLAG(_pAd, _F) ((_pAd)->CommonCfg.PacketFilter |= (_F))
57484 +#define RX_FILTER_CLEAR_FLAG(_pAd, _F) ((_pAd)->CommonCfg.PacketFilter &= ~(_F))
57485 +#define RX_FILTER_TEST_FLAG(_pAd, _F) (((_pAd)->CommonCfg.PacketFilter & (_F)) != 0)
57486 +
57487 +#ifdef CONFIG_STA_SUPPORT
57488 +#define STA_NO_SECURITY_ON(_p) (_p->StaCfg.WepStatus == Ndis802_11EncryptionDisabled)
57489 +#define STA_WEP_ON(_p) (_p->StaCfg.WepStatus == Ndis802_11Encryption1Enabled)
57490 +#define STA_TKIP_ON(_p) (_p->StaCfg.WepStatus == Ndis802_11Encryption2Enabled)
57491 +#define STA_AES_ON(_p) (_p->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
57492 +
57493 +#define STA_TGN_WIFI_ON(_p) (_p->StaCfg.bTGnWifiTest == TRUE)
57494 +#endif // CONFIG_STA_SUPPORT //
57495 +
57496 +#define CKIP_KP_ON(_p) ((((_p)->StaCfg.CkipFlag) & 0x10) && ((_p)->StaCfg.bCkipCmicOn == TRUE))
57497 +#define CKIP_CMIC_ON(_p) ((((_p)->StaCfg.CkipFlag) & 0x08) && ((_p)->StaCfg.bCkipCmicOn == TRUE))
57498 +
57499 +
57500 +#define INC_RING_INDEX(_idx, _RingSize) \
57501 +{ \
57502 + (_idx) = (_idx+1) % (_RingSize); \
57503 +}
57504 +
57505 +#define IS_RT3070(_pAd) (((_pAd)->MACVersion & 0xffff0000) == 0x30700000)
57506 +
57507 +#define RING_PACKET_INIT(_TxRing, _idx) \
57508 +{ \
57509 + _TxRing->Cell[_idx].pNdisPacket = NULL; \
57510 + _TxRing->Cell[_idx].pNextNdisPacket = NULL; \
57511 +}
57512 +
57513 +#define TXDT_INIT(_TxD) \
57514 +{ \
57515 + NdisZeroMemory(_TxD, TXD_SIZE); \
57516 + _TxD->DMADONE = 1; \
57517 +}
57518 +
57519 +//Set last data segment
57520 +#define RING_SET_LASTDS(_TxD, _IsSD0) \
57521 +{ \
57522 + if (_IsSD0) {_TxD->LastSec0 = 1;} \
57523 + else {_TxD->LastSec1 = 1;} \
57524 +}
57525 +
57526 +// Increase TxTsc value for next transmission
57527 +// TODO:
57528 +// When i==6, means TSC has done one full cycle, do re-keying stuff follow specs
57529 +// Should send a special event microsoft defined to request re-key
57530 +#define INC_TX_TSC(_tsc) \
57531 +{ \
57532 + int i=0; \
57533 + while (++_tsc[i] == 0x0) \
57534 + { \
57535 + i++; \
57536 + if (i == 6) \
57537 + break; \
57538 + } \
57539 +}
57540 +
57541 +#ifdef DOT11_N_SUPPORT
57542 +// StaActive.SupportedHtPhy.MCSSet is copied from AP beacon. Don't need to update here.
57543 +#define COPY_HTSETTINGS_FROM_MLME_AUX_TO_ACTIVE_CFG(_pAd) \
57544 +{ \
57545 + _pAd->StaActive.SupportedHtPhy.ChannelWidth = _pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth; \
57546 + _pAd->StaActive.SupportedHtPhy.MimoPs = _pAd->MlmeAux.HtCapability.HtCapInfo.MimoPs; \
57547 + _pAd->StaActive.SupportedHtPhy.GF = _pAd->MlmeAux.HtCapability.HtCapInfo.GF; \
57548 + _pAd->StaActive.SupportedHtPhy.ShortGIfor20 = _pAd->MlmeAux.HtCapability.HtCapInfo.ShortGIfor20; \
57549 + _pAd->StaActive.SupportedHtPhy.ShortGIfor40 = _pAd->MlmeAux.HtCapability.HtCapInfo.ShortGIfor40; \
57550 + _pAd->StaActive.SupportedHtPhy.TxSTBC = _pAd->MlmeAux.HtCapability.HtCapInfo.TxSTBC; \
57551 + _pAd->StaActive.SupportedHtPhy.RxSTBC = _pAd->MlmeAux.HtCapability.HtCapInfo.RxSTBC; \
57552 + _pAd->StaActive.SupportedHtPhy.ExtChanOffset = _pAd->MlmeAux.AddHtInfo.AddHtInfo.ExtChanOffset; \
57553 + _pAd->StaActive.SupportedHtPhy.RecomWidth = _pAd->MlmeAux.AddHtInfo.AddHtInfo.RecomWidth; \
57554 + _pAd->StaActive.SupportedHtPhy.OperaionMode = _pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode; \
57555 + _pAd->StaActive.SupportedHtPhy.NonGfPresent = _pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent; \
57556 + NdisMoveMemory((_pAd)->MacTab.Content[BSSID_WCID].HTCapability.MCSSet, (_pAd)->StaActive.SupportedPhyInfo.MCSSet, sizeof(UCHAR) * 16);\
57557 +}
57558 +
57559 +#define COPY_AP_HTSETTINGS_FROM_BEACON(_pAd, _pHtCapability) \
57560 +{ \
57561 + _pAd->MacTab.Content[BSSID_WCID].AMsduSize = (UCHAR)(_pHtCapability->HtCapInfo.AMsduSize); \
57562 + _pAd->MacTab.Content[BSSID_WCID].MmpsMode= (UCHAR)(_pHtCapability->HtCapInfo.MimoPs); \
57563 + _pAd->MacTab.Content[BSSID_WCID].MaxRAmpduFactor = (UCHAR)(_pHtCapability->HtCapParm.MaxRAmpduFactor); \
57564 +}
57565 +#endif // DOT11_N_SUPPORT //
57566 +
57567 +//
57568 +// MACRO for 32-bit PCI register read / write
57569 +//
57570 +// Usage : RTMP_IO_READ32(
57571 +// PRTMP_ADAPTER pAd,
57572 +// ULONG Register_Offset,
57573 +// PULONG pValue)
57574 +//
57575 +// RTMP_IO_WRITE32(
57576 +// PRTMP_ADAPTER pAd,
57577 +// ULONG Register_Offset,
57578 +// ULONG Value)
57579 +//
57580 +
57581 +//
57582 +// BBP & RF are using indirect access. Before write any value into it.
57583 +// We have to make sure there is no outstanding command pending via checking busy bit.
57584 +//
57585 +#define MAX_BUSY_COUNT 100 // Number of retry before failing access BBP & RF indirect register
57586 +//
57587 +#ifdef RT2860
57588 +#define RTMP_RF_IO_WRITE32(_A, _V) \
57589 +{ \
57590 + PHY_CSR4_STRUC Value; \
57591 + ULONG BusyCnt = 0; \
57592 + if ((_A)->bPCIclkOff) \
57593 + { \
57594 + return; \
57595 + } \
57596 + do { \
57597 + RTMP_IO_READ32(_A, RF_CSR_CFG0, &Value.word); \
57598 + if (Value.field.Busy == IDLE) \
57599 + break; \
57600 + BusyCnt++; \
57601 + } while (BusyCnt < MAX_BUSY_COUNT); \
57602 + if (BusyCnt < MAX_BUSY_COUNT) \
57603 + { \
57604 + RTMP_IO_WRITE32(_A, RF_CSR_CFG0, _V); \
57605 + } \
57606 +}
57607 +
57608 +#define BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) \
57609 +{ \
57610 + BBP_CSR_CFG_STRUC BbpCsr; \
57611 + int i, k; \
57612 + for (i=0; i<MAX_BUSY_COUNT; i++) \
57613 + { \
57614 + RTMP_IO_READ32(_A, BBP_CSR_CFG, &BbpCsr.word); \
57615 + if (BbpCsr.field.Busy == BUSY) \
57616 + { \
57617 + continue; \
57618 + } \
57619 + BbpCsr.word = 0; \
57620 + BbpCsr.field.fRead = 1; \
57621 + BbpCsr.field.BBP_RW_MODE = 1; \
57622 + BbpCsr.field.Busy = 1; \
57623 + BbpCsr.field.RegNum = _I; \
57624 + RTMP_IO_WRITE32(_A, BBP_CSR_CFG, BbpCsr.word); \
57625 + for (k=0; k<MAX_BUSY_COUNT; k++) \
57626 + { \
57627 + RTMP_IO_READ32(_A, BBP_CSR_CFG, &BbpCsr.word); \
57628 + if (BbpCsr.field.Busy == IDLE) \
57629 + break; \
57630 + } \
57631 + if ((BbpCsr.field.Busy == IDLE) && \
57632 + (BbpCsr.field.RegNum == _I)) \
57633 + { \
57634 + *(_pV) = (UCHAR)BbpCsr.field.Value; \
57635 + break; \
57636 + } \
57637 + } \
57638 + if (BbpCsr.field.Busy == BUSY) \
57639 + { \
57640 + DBGPRINT_ERR(("DFS BBP read R%d fail\n", _I)); \
57641 + *(_pV) = (_A)->BbpWriteLatch[_I]; \
57642 + } \
57643 +}
57644 +
57645 +//#define RTMP_BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) {}
57646 +// Read BBP register by register's ID. Generate PER to test BA
57647 +#define RTMP_BBP_IO_READ8_BY_REG_ID(_A, _I, _pV) \
57648 +{ \
57649 + BBP_CSR_CFG_STRUC BbpCsr; \
57650 + int i, k; \
57651 + if ((_A)->bPCIclkOff == FALSE) \
57652 + { \
57653 + for (i=0; i<MAX_BUSY_COUNT; i++) \
57654 + { \
57655 + RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
57656 + if (BbpCsr.field.Busy == BUSY) \
57657 + { \
57658 + continue; \
57659 + } \
57660 + BbpCsr.word = 0; \
57661 + BbpCsr.field.fRead = 1; \
57662 + BbpCsr.field.BBP_RW_MODE = 1; \
57663 + BbpCsr.field.Busy = 1; \
57664 + BbpCsr.field.RegNum = _I; \
57665 + RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
57666 + AsicSendCommandToMcu(_A, 0x80, 0xff, 0x0, 0x0); \
57667 + RTMPusecDelay(1000); \
57668 + for (k=0; k<MAX_BUSY_COUNT; k++) \
57669 + { \
57670 + RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
57671 + if (BbpCsr.field.Busy == IDLE) \
57672 + break; \
57673 + } \
57674 + if ((BbpCsr.field.Busy == IDLE) && \
57675 + (BbpCsr.field.RegNum == _I)) \
57676 + { \
57677 + *(_pV) = (UCHAR)BbpCsr.field.Value; \
57678 + break; \
57679 + } \
57680 + } \
57681 + if (BbpCsr.field.Busy == BUSY) \
57682 + { \
57683 + DBGPRINT_ERR(("BBP read R%d=0x%x fail\n", _I, BbpCsr.word)); \
57684 + *(_pV) = (_A)->BbpWriteLatch[_I]; \
57685 + RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
57686 + BbpCsr.field.Busy = 0; \
57687 + RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
57688 + } \
57689 + } \
57690 +}
57691 +
57692 +#define BBP_IO_WRITE8_BY_REG_ID(_A, _I, _V) \
57693 +{ \
57694 + BBP_CSR_CFG_STRUC BbpCsr; \
57695 + int BusyCnt; \
57696 + for (BusyCnt=0; BusyCnt<MAX_BUSY_COUNT; BusyCnt++) \
57697 + { \
57698 + RTMP_IO_READ32(_A, BBP_CSR_CFG, &BbpCsr.word); \
57699 + if (BbpCsr.field.Busy == BUSY) \
57700 + continue; \
57701 + BbpCsr.word = 0; \
57702 + BbpCsr.field.fRead = 0; \
57703 + BbpCsr.field.BBP_RW_MODE = 1; \
57704 + BbpCsr.field.Busy = 1; \
57705 + BbpCsr.field.Value = _V; \
57706 + BbpCsr.field.RegNum = _I; \
57707 + RTMP_IO_WRITE32(_A, BBP_CSR_CFG, BbpCsr.word); \
57708 + (_A)->BbpWriteLatch[_I] = _V; \
57709 + break; \
57710 + } \
57711 + if (BusyCnt == MAX_BUSY_COUNT) \
57712 + { \
57713 + DBGPRINT_ERR(("BBP write R%d fail\n", _I)); \
57714 + } \
57715 +}
57716 +
57717 +// Write BBP register by register's ID & value
57718 +#define RTMP_BBP_IO_WRITE8_BY_REG_ID(_A, _I, _V) \
57719 +{ \
57720 + BBP_CSR_CFG_STRUC BbpCsr; \
57721 + int BusyCnt; \
57722 + if ((_A)->bPCIclkOff == FALSE) \
57723 + { \
57724 + for (BusyCnt=0; BusyCnt<MAX_BUSY_COUNT; BusyCnt++) \
57725 + { \
57726 + RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
57727 + if (BbpCsr.field.Busy == BUSY) \
57728 + continue; \
57729 + BbpCsr.word = 0; \
57730 + BbpCsr.field.fRead = 0; \
57731 + BbpCsr.field.BBP_RW_MODE = 1; \
57732 + BbpCsr.field.Busy = 1; \
57733 + BbpCsr.field.Value = _V; \
57734 + BbpCsr.field.RegNum = _I; \
57735 + RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
57736 + AsicSendCommandToMcu(_A, 0x80, 0xff, 0x0, 0x0); \
57737 + if (_A->OpMode == OPMODE_AP) \
57738 + RTMPusecDelay(1000); \
57739 + (_A)->BbpWriteLatch[_I] = _V; \
57740 + break; \
57741 + } \
57742 + if (BusyCnt == MAX_BUSY_COUNT) \
57743 + { \
57744 + DBGPRINT_ERR(("BBP write R%d=0x%x fail\n", _I, BbpCsr.word)); \
57745 + RTMP_IO_READ32(_A, H2M_BBP_AGENT, &BbpCsr.word); \
57746 + BbpCsr.field.Busy = 0; \
57747 + RTMP_IO_WRITE32(_A, H2M_BBP_AGENT, BbpCsr.word); \
57748 + } \
57749 + } \
57750 +}
57751 +#endif // RT2860 //
57752 +
57753 +
57754 +#define MAP_CHANNEL_ID_TO_KHZ(ch, khz) { \
57755 + switch (ch) \
57756 + { \
57757 + case 1: khz = 2412000; break; \
57758 + case 2: khz = 2417000; break; \
57759 + case 3: khz = 2422000; break; \
57760 + case 4: khz = 2427000; break; \
57761 + case 5: khz = 2432000; break; \
57762 + case 6: khz = 2437000; break; \
57763 + case 7: khz = 2442000; break; \
57764 + case 8: khz = 2447000; break; \
57765 + case 9: khz = 2452000; break; \
57766 + case 10: khz = 2457000; break; \
57767 + case 11: khz = 2462000; break; \
57768 + case 12: khz = 2467000; break; \
57769 + case 13: khz = 2472000; break; \
57770 + case 14: khz = 2484000; break; \
57771 + case 36: /* UNII */ khz = 5180000; break; \
57772 + case 40: /* UNII */ khz = 5200000; break; \
57773 + case 44: /* UNII */ khz = 5220000; break; \
57774 + case 48: /* UNII */ khz = 5240000; break; \
57775 + case 52: /* UNII */ khz = 5260000; break; \
57776 + case 56: /* UNII */ khz = 5280000; break; \
57777 + case 60: /* UNII */ khz = 5300000; break; \
57778 + case 64: /* UNII */ khz = 5320000; break; \
57779 + case 149: /* UNII */ khz = 5745000; break; \
57780 + case 153: /* UNII */ khz = 5765000; break; \
57781 + case 157: /* UNII */ khz = 5785000; break; \
57782 + case 161: /* UNII */ khz = 5805000; break; \
57783 + case 165: /* UNII */ khz = 5825000; break; \
57784 + case 100: /* HiperLAN2 */ khz = 5500000; break; \
57785 + case 104: /* HiperLAN2 */ khz = 5520000; break; \
57786 + case 108: /* HiperLAN2 */ khz = 5540000; break; \
57787 + case 112: /* HiperLAN2 */ khz = 5560000; break; \
57788 + case 116: /* HiperLAN2 */ khz = 5580000; break; \
57789 + case 120: /* HiperLAN2 */ khz = 5600000; break; \
57790 + case 124: /* HiperLAN2 */ khz = 5620000; break; \
57791 + case 128: /* HiperLAN2 */ khz = 5640000; break; \
57792 + case 132: /* HiperLAN2 */ khz = 5660000; break; \
57793 + case 136: /* HiperLAN2 */ khz = 5680000; break; \
57794 + case 140: /* HiperLAN2 */ khz = 5700000; break; \
57795 + case 34: /* Japan MMAC */ khz = 5170000; break; \
57796 + case 38: /* Japan MMAC */ khz = 5190000; break; \
57797 + case 42: /* Japan MMAC */ khz = 5210000; break; \
57798 + case 46: /* Japan MMAC */ khz = 5230000; break; \
57799 + case 184: /* Japan */ khz = 4920000; break; \
57800 + case 188: /* Japan */ khz = 4940000; break; \
57801 + case 192: /* Japan */ khz = 4960000; break; \
57802 + case 196: /* Japan */ khz = 4980000; break; \
57803 + case 208: /* Japan, means J08 */ khz = 5040000; break; \
57804 + case 212: /* Japan, means J12 */ khz = 5060000; break; \
57805 + case 216: /* Japan, means J16 */ khz = 5080000; break; \
57806 + default: khz = 2412000; break; \
57807 + } \
57808 + }
57809 +
57810 +#define MAP_KHZ_TO_CHANNEL_ID(khz, ch) { \
57811 + switch (khz) \
57812 + { \
57813 + case 2412000: ch = 1; break; \
57814 + case 2417000: ch = 2; break; \
57815 + case 2422000: ch = 3; break; \
57816 + case 2427000: ch = 4; break; \
57817 + case 2432000: ch = 5; break; \
57818 + case 2437000: ch = 6; break; \
57819 + case 2442000: ch = 7; break; \
57820 + case 2447000: ch = 8; break; \
57821 + case 2452000: ch = 9; break; \
57822 + case 2457000: ch = 10; break; \
57823 + case 2462000: ch = 11; break; \
57824 + case 2467000: ch = 12; break; \
57825 + case 2472000: ch = 13; break; \
57826 + case 2484000: ch = 14; break; \
57827 + case 5180000: ch = 36; /* UNII */ break; \
57828 + case 5200000: ch = 40; /* UNII */ break; \
57829 + case 5220000: ch = 44; /* UNII */ break; \
57830 + case 5240000: ch = 48; /* UNII */ break; \
57831 + case 5260000: ch = 52; /* UNII */ break; \
57832 + case 5280000: ch = 56; /* UNII */ break; \
57833 + case 5300000: ch = 60; /* UNII */ break; \
57834 + case 5320000: ch = 64; /* UNII */ break; \
57835 + case 5745000: ch = 149; /* UNII */ break; \
57836 + case 5765000: ch = 153; /* UNII */ break; \
57837 + case 5785000: ch = 157; /* UNII */ break; \
57838 + case 5805000: ch = 161; /* UNII */ break; \
57839 + case 5825000: ch = 165; /* UNII */ break; \
57840 + case 5500000: ch = 100; /* HiperLAN2 */ break; \
57841 + case 5520000: ch = 104; /* HiperLAN2 */ break; \
57842 + case 5540000: ch = 108; /* HiperLAN2 */ break; \
57843 + case 5560000: ch = 112; /* HiperLAN2 */ break; \
57844 + case 5580000: ch = 116; /* HiperLAN2 */ break; \
57845 + case 5600000: ch = 120; /* HiperLAN2 */ break; \
57846 + case 5620000: ch = 124; /* HiperLAN2 */ break; \
57847 + case 5640000: ch = 128; /* HiperLAN2 */ break; \
57848 + case 5660000: ch = 132; /* HiperLAN2 */ break; \
57849 + case 5680000: ch = 136; /* HiperLAN2 */ break; \
57850 + case 5700000: ch = 140; /* HiperLAN2 */ break; \
57851 + case 5170000: ch = 34; /* Japan MMAC */ break; \
57852 + case 5190000: ch = 38; /* Japan MMAC */ break; \
57853 + case 5210000: ch = 42; /* Japan MMAC */ break; \
57854 + case 5230000: ch = 46; /* Japan MMAC */ break; \
57855 + case 4920000: ch = 184; /* Japan */ break; \
57856 + case 4940000: ch = 188; /* Japan */ break; \
57857 + case 4960000: ch = 192; /* Japan */ break; \
57858 + case 4980000: ch = 196; /* Japan */ break; \
57859 + case 5040000: ch = 208; /* Japan, means J08 */ break; \
57860 + case 5060000: ch = 212; /* Japan, means J12 */ break; \
57861 + case 5080000: ch = 216; /* Japan, means J16 */ break; \
57862 + default: ch = 1; break; \
57863 + } \
57864 + }
57865 +
57866 +//
57867 +// Common fragment list structure - Identical to the scatter gather frag list structure
57868 +//
57869 +#define NIC_MAX_PHYS_BUF_COUNT 8
57870 +
57871 +typedef struct _RTMP_SCATTER_GATHER_ELEMENT {
57872 + PVOID Address;
57873 + ULONG Length;
57874 + PULONG Reserved;
57875 +} RTMP_SCATTER_GATHER_ELEMENT, *PRTMP_SCATTER_GATHER_ELEMENT;
57876 +
57877 +
57878 +typedef struct _RTMP_SCATTER_GATHER_LIST {
57879 + ULONG NumberOfElements;
57880 + PULONG Reserved;
57881 + RTMP_SCATTER_GATHER_ELEMENT Elements[NIC_MAX_PHYS_BUF_COUNT];
57882 +} RTMP_SCATTER_GATHER_LIST, *PRTMP_SCATTER_GATHER_LIST;
57883 +
57884 +//
57885 +// Some utility macros
57886 +//
57887 +#ifndef min
57888 +#define min(_a, _b) (((_a) < (_b)) ? (_a) : (_b))
57889 +#endif
57890 +
57891 +#ifndef max
57892 +#define max(_a, _b) (((_a) > (_b)) ? (_a) : (_b))
57893 +#endif
57894 +
57895 +#define GET_LNA_GAIN(_pAd) ((_pAd->LatchRfRegs.Channel <= 14) ? (_pAd->BLNAGain) : ((_pAd->LatchRfRegs.Channel <= 64) ? (_pAd->ALNAGain0) : ((_pAd->LatchRfRegs.Channel <= 128) ? (_pAd->ALNAGain1) : (_pAd->ALNAGain2))))
57896 +
57897 +#define INC_COUNTER64(Val) (Val.QuadPart++)
57898 +
57899 +#define INFRA_ON(_p) (OPSTATUS_TEST_FLAG(_p, fOP_STATUS_INFRA_ON))
57900 +#define ADHOC_ON(_p) (OPSTATUS_TEST_FLAG(_p, fOP_STATUS_ADHOC_ON))
57901 +#define MONITOR_ON(_p) (((_p)->StaCfg.BssType) == BSS_MONITOR)
57902 +#define IDLE_ON(_p) (!INFRA_ON(_p) && !ADHOC_ON(_p))
57903 +
57904 +// Check LEAP & CCKM flags
57905 +#define LEAP_ON(_p) (((_p)->StaCfg.LeapAuthMode) == CISCO_AuthModeLEAP)
57906 +#define LEAP_CCKM_ON(_p) ((((_p)->StaCfg.LeapAuthMode) == CISCO_AuthModeLEAP) && ((_p)->StaCfg.LeapAuthInfo.CCKM == TRUE))
57907 +
57908 +// if orginal Ethernet frame contains no LLC/SNAP, then an extra LLC/SNAP encap is required
57909 +#define EXTRA_LLCSNAP_ENCAP_FROM_PKT_START(_pBufVA, _pExtraLlcSnapEncap) \
57910 +{ \
57911 + if (((*(_pBufVA + 12) << 8) + *(_pBufVA + 13)) > 1500) \
57912 + { \
57913 + _pExtraLlcSnapEncap = SNAP_802_1H; \
57914 + if (NdisEqualMemory(IPX, _pBufVA + 12, 2) || \
57915 + NdisEqualMemory(APPLE_TALK, _pBufVA + 12, 2)) \
57916 + { \
57917 + _pExtraLlcSnapEncap = SNAP_BRIDGE_TUNNEL; \
57918 + } \
57919 + } \
57920 + else \
57921 + { \
57922 + _pExtraLlcSnapEncap = NULL; \
57923 + } \
57924 +}
57925 +
57926 +// New Define for new Tx Path.
57927 +#define EXTRA_LLCSNAP_ENCAP_FROM_PKT_OFFSET(_pBufVA, _pExtraLlcSnapEncap) \
57928 +{ \
57929 + if (((*(_pBufVA) << 8) + *(_pBufVA + 1)) > 1500) \
57930 + { \
57931 + _pExtraLlcSnapEncap = SNAP_802_1H; \
57932 + if (NdisEqualMemory(IPX, _pBufVA, 2) || \
57933 + NdisEqualMemory(APPLE_TALK, _pBufVA, 2)) \
57934 + { \
57935 + _pExtraLlcSnapEncap = SNAP_BRIDGE_TUNNEL; \
57936 + } \
57937 + } \
57938 + else \
57939 + { \
57940 + _pExtraLlcSnapEncap = NULL; \
57941 + } \
57942 +}
57943 +
57944 +
57945 +#define MAKE_802_3_HEADER(_p, _pMac1, _pMac2, _pType) \
57946 +{ \
57947 + NdisMoveMemory(_p, _pMac1, MAC_ADDR_LEN); \
57948 + NdisMoveMemory((_p + MAC_ADDR_LEN), _pMac2, MAC_ADDR_LEN); \
57949 + NdisMoveMemory((_p + MAC_ADDR_LEN * 2), _pType, LENGTH_802_3_TYPE); \
57950 +}
57951 +
57952 +// if pData has no LLC/SNAP (neither RFC1042 nor Bridge tunnel), keep it that way.
57953 +// else if the received frame is LLC/SNAP-encaped IPX or APPLETALK, preserve the LLC/SNAP field
57954 +// else remove the LLC/SNAP field from the result Ethernet frame
57955 +// Patch for WHQL only, which did not turn on Netbios but use IPX within its payload
57956 +// Note:
57957 +// _pData & _DataSize may be altered (remove 8-byte LLC/SNAP) by this MACRO
57958 +// _pRemovedLLCSNAP: pointer to removed LLC/SNAP; NULL is not removed
57959 +#define CONVERT_TO_802_3(_p8023hdr, _pDA, _pSA, _pData, _DataSize, _pRemovedLLCSNAP) \
57960 +{ \
57961 + char LLC_Len[2]; \
57962 + \
57963 + _pRemovedLLCSNAP = NULL; \
57964 + if (NdisEqualMemory(SNAP_802_1H, _pData, 6) || \
57965 + NdisEqualMemory(SNAP_BRIDGE_TUNNEL, _pData, 6)) \
57966 + { \
57967 + PUCHAR pProto = _pData + 6; \
57968 + \
57969 + if ((NdisEqualMemory(IPX, pProto, 2) || NdisEqualMemory(APPLE_TALK, pProto, 2)) && \
57970 + NdisEqualMemory(SNAP_802_1H, _pData, 6)) \
57971 + { \
57972 + LLC_Len[0] = (UCHAR)(_DataSize / 256); \
57973 + LLC_Len[1] = (UCHAR)(_DataSize % 256); \
57974 + MAKE_802_3_HEADER(_p8023hdr, _pDA, _pSA, LLC_Len); \
57975 + } \
57976 + else \
57977 + { \
57978 + MAKE_802_3_HEADER(_p8023hdr, _pDA, _pSA, pProto); \
57979 + _pRemovedLLCSNAP = _pData; \
57980 + _DataSize -= LENGTH_802_1_H; \
57981 + _pData += LENGTH_802_1_H; \
57982 + } \
57983 + } \
57984 + else \
57985 + { \
57986 + LLC_Len[0] = (UCHAR)(_DataSize / 256); \
57987 + LLC_Len[1] = (UCHAR)(_DataSize % 256); \
57988 + MAKE_802_3_HEADER(_p8023hdr, _pDA, _pSA, LLC_Len); \
57989 + } \
57990 +}
57991 +
57992 +#define SWITCH_AB( _pAA, _pBB) \
57993 +{ \
57994 + PVOID pCC; \
57995 + pCC = _pBB; \
57996 + _pBB = _pAA; \
57997 + _pAA = pCC; \
57998 +}
57999 +
58000 +// Enqueue this frame to MLME engine
58001 +// We need to enqueue the whole frame because MLME need to pass data type
58002 +// information from 802.11 header
58003 +#ifdef RT2860
58004 +#define REPORT_MGMT_FRAME_TO_MLME(_pAd, Wcid, _pFrame, _FrameSize, _Rssi0, _Rssi1, _Rssi2, _PlcpSignal) \
58005 +{ \
58006 + UINT32 High32TSF, Low32TSF; \
58007 + RTMP_IO_READ32(_pAd, TSF_TIMER_DW1, &High32TSF); \
58008 + RTMP_IO_READ32(_pAd, TSF_TIMER_DW0, &Low32TSF); \
58009 + MlmeEnqueueForRecv(_pAd, Wcid, High32TSF, Low32TSF, (UCHAR)_Rssi0, (UCHAR)_Rssi1,(UCHAR)_Rssi2,_FrameSize, _pFrame, (UCHAR)_PlcpSignal); \
58010 +}
58011 +#endif // RT2860 //
58012 +
58013 +#define NDIS_QUERY_BUFFER(_NdisBuf, _ppVA, _pBufLen) \
58014 + NdisQueryBuffer(_NdisBuf, _ppVA, _pBufLen)
58015 +
58016 +#define MAC_ADDR_EQUAL(pAddr1,pAddr2) RTMPEqualMemory((PVOID)(pAddr1), (PVOID)(pAddr2), MAC_ADDR_LEN)
58017 +#define SSID_EQUAL(ssid1, len1, ssid2, len2) ((len1==len2) && (RTMPEqualMemory(ssid1, ssid2, len1)))
58018 +
58019 +//
58020 +// Check if it is Japan W53(ch52,56,60,64) channel.
58021 +//
58022 +#define JapanChannelCheck(channel) ((channel == 52) || (channel == 56) || (channel == 60) || (channel == 64))
58023 +
58024 +#ifdef CONFIG_STA_SUPPORT
58025 +#define STA_PORT_SECURED(_pAd) \
58026 +{ \
58027 + _pAd->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED; \
58028 + NdisAcquireSpinLock(&_pAd->MacTabLock); \
58029 + _pAd->MacTab.Content[BSSID_WCID].PortSecured = _pAd->StaCfg.PortSecured; \
58030 + NdisReleaseSpinLock(&_pAd->MacTabLock); \
58031 +}
58032 +#endif // CONFIG_STA_SUPPORT //
58033 +
58034 +
58035 +//
58036 +// Register set pair for initialzation register set definition
58037 +//
58038 +typedef struct _RTMP_REG_PAIR
58039 +{
58040 + ULONG Register;
58041 + ULONG Value;
58042 +} RTMP_REG_PAIR, *PRTMP_REG_PAIR;
58043 +
58044 +typedef struct _REG_PAIR
58045 +{
58046 + UCHAR Register;
58047 + UCHAR Value;
58048 +} REG_PAIR, *PREG_PAIR;
58049 +
58050 +//
58051 +// Register set pair for initialzation register set definition
58052 +//
58053 +typedef struct _RTMP_RF_REGS
58054 +{
58055 + UCHAR Channel;
58056 + ULONG R1;
58057 + ULONG R2;
58058 + ULONG R3;
58059 + ULONG R4;
58060 +} RTMP_RF_REGS, *PRTMP_RF_REGS;
58061 +
58062 +typedef struct _FREQUENCY_ITEM {
58063 + UCHAR Channel;
58064 + UCHAR N;
58065 + UCHAR R;
58066 + UCHAR K;
58067 +} FREQUENCY_ITEM, *PFREQUENCY_ITEM;
58068 +
58069 +//
58070 +// Data buffer for DMA operation, the buffer must be contiguous physical memory
58071 +// Both DMA to / from CPU use the same structure.
58072 +//
58073 +typedef struct _RTMP_DMABUF
58074 +{
58075 + ULONG AllocSize;
58076 + PVOID AllocVa; // TxBuf virtual address
58077 + NDIS_PHYSICAL_ADDRESS AllocPa; // TxBuf physical address
58078 +} RTMP_DMABUF, *PRTMP_DMABUF;
58079 +
58080 +
58081 +typedef union _HEADER_802_11_SEQ{
58082 +#ifdef RT_BIG_ENDIAN
58083 + struct {
58084 + USHORT Sequence:12;
58085 + USHORT Frag:4;
58086 + } field;
58087 +#else
58088 + struct {
58089 + USHORT Frag:4;
58090 + USHORT Sequence:12;
58091 + } field;
58092 +#endif
58093 + USHORT value;
58094 +} HEADER_802_11_SEQ, *PHEADER_802_11_SEQ;
58095 +
58096 +//
58097 +// Data buffer for DMA operation, the buffer must be contiguous physical memory
58098 +// Both DMA to / from CPU use the same structure.
58099 +//
58100 +typedef struct _RTMP_REORDERBUF
58101 +{
58102 + BOOLEAN IsFull;
58103 + PVOID AllocVa; // TxBuf virtual address
58104 + UCHAR Header802_3[14];
58105 + HEADER_802_11_SEQ Sequence; //support compressed bitmap BA, so no consider fragment in BA
58106 + UCHAR DataOffset;
58107 + USHORT Datasize;
58108 + ULONG AllocSize;
58109 +#ifdef RT2860
58110 + NDIS_PHYSICAL_ADDRESS AllocPa; // TxBuf physical address
58111 +#endif // RT2860 //
58112 +} RTMP_REORDERBUF, *PRTMP_REORDERBUF;
58113 +
58114 +//
58115 +// Control block (Descriptor) for all ring descriptor DMA operation, buffer must be
58116 +// contiguous physical memory. NDIS_PACKET stored the binding Rx packet descriptor
58117 +// which won't be released, driver has to wait until upper layer return the packet
58118 +// before giveing up this rx ring descriptor to ASIC. NDIS_BUFFER is assocaited pair
58119 +// to describe the packet buffer. For Tx, NDIS_PACKET stored the tx packet descriptor
58120 +// which driver should ACK upper layer when the tx is physically done or failed.
58121 +//
58122 +typedef struct _RTMP_DMACB
58123 +{
58124 + ULONG AllocSize; // Control block size
58125 + PVOID AllocVa; // Control block virtual address
58126 + NDIS_PHYSICAL_ADDRESS AllocPa; // Control block physical address
58127 + PNDIS_PACKET pNdisPacket;
58128 + PNDIS_PACKET pNextNdisPacket;
58129 +
58130 + RTMP_DMABUF DmaBuf; // Associated DMA buffer structure
58131 +} RTMP_DMACB, *PRTMP_DMACB;
58132 +
58133 +typedef struct _RTMP_TX_BUF
58134 +{
58135 + PQUEUE_ENTRY Next;
58136 + UCHAR Index;
58137 + ULONG AllocSize; // Control block size
58138 + PVOID AllocVa; // Control block virtual address
58139 + NDIS_PHYSICAL_ADDRESS AllocPa; // Control block physical address
58140 +} RTMP_TXBUF, *PRTMP_TXBUF;
58141 +
58142 +typedef struct _RTMP_RX_BUF
58143 +{
58144 + BOOLEAN InUse;
58145 + ULONG ByBaRecIndex;
58146 + RTMP_REORDERBUF MAP_RXBuf[MAX_RX_REORDERBUF];
58147 +} RTMP_RXBUF, *PRTMP_RXBUF;
58148 +typedef struct _RTMP_TX_RING
58149 +{
58150 + RTMP_DMACB Cell[TX_RING_SIZE];
58151 + UINT32 TxCpuIdx;
58152 + UINT32 TxDmaIdx;
58153 + UINT32 TxSwFreeIdx; // software next free tx index
58154 +} RTMP_TX_RING, *PRTMP_TX_RING;
58155 +
58156 +typedef struct _RTMP_RX_RING
58157 +{
58158 + RTMP_DMACB Cell[RX_RING_SIZE];
58159 + UINT32 RxCpuIdx;
58160 + UINT32 RxDmaIdx;
58161 + INT32 RxSwReadIdx; // software next read index
58162 +} RTMP_RX_RING, *PRTMP_RX_RING;
58163 +
58164 +typedef struct _RTMP_MGMT_RING
58165 +{
58166 + RTMP_DMACB Cell[MGMT_RING_SIZE];
58167 + UINT32 TxCpuIdx;
58168 + UINT32 TxDmaIdx;
58169 + UINT32 TxSwFreeIdx; // software next free tx index
58170 +} RTMP_MGMT_RING, *PRTMP_MGMT_RING;
58171 +
58172 +//
58173 +// Statistic counter structure
58174 +//
58175 +typedef struct _COUNTER_802_3
58176 +{
58177 + // General Stats
58178 + ULONG GoodTransmits;
58179 + ULONG GoodReceives;
58180 + ULONG TxErrors;
58181 + ULONG RxErrors;
58182 + ULONG RxNoBuffer;
58183 +
58184 + // Ethernet Stats
58185 + ULONG RcvAlignmentErrors;
58186 + ULONG OneCollision;
58187 + ULONG MoreCollisions;
58188 +
58189 +} COUNTER_802_3, *PCOUNTER_802_3;
58190 +
58191 +typedef struct _COUNTER_802_11 {
58192 + ULONG Length;
58193 + LARGE_INTEGER LastTransmittedFragmentCount;
58194 + LARGE_INTEGER TransmittedFragmentCount;
58195 + LARGE_INTEGER MulticastTransmittedFrameCount;
58196 + LARGE_INTEGER FailedCount;
58197 + LARGE_INTEGER RetryCount;
58198 + LARGE_INTEGER MultipleRetryCount;
58199 + LARGE_INTEGER RTSSuccessCount;
58200 + LARGE_INTEGER RTSFailureCount;
58201 + LARGE_INTEGER ACKFailureCount;
58202 + LARGE_INTEGER FrameDuplicateCount;
58203 + LARGE_INTEGER ReceivedFragmentCount;
58204 + LARGE_INTEGER MulticastReceivedFrameCount;
58205 + LARGE_INTEGER FCSErrorCount;
58206 +} COUNTER_802_11, *PCOUNTER_802_11;
58207 +
58208 +typedef struct _COUNTER_RALINK {
58209 + ULONG TransmittedByteCount; // both successful and failure, used to calculate TX throughput
58210 + ULONG ReceivedByteCount; // both CRC okay and CRC error, used to calculate RX throughput
58211 + ULONG BeenDisassociatedCount;
58212 + ULONG BadCQIAutoRecoveryCount;
58213 + ULONG PoorCQIRoamingCount;
58214 + ULONG MgmtRingFullCount;
58215 + ULONG RxCountSinceLastNULL;
58216 + ULONG RxCount;
58217 + ULONG RxRingErrCount;
58218 + ULONG KickTxCount;
58219 + ULONG TxRingErrCount;
58220 + LARGE_INTEGER RealFcsErrCount;
58221 + ULONG PendingNdisPacketCount;
58222 +
58223 + ULONG OneSecOsTxCount[NUM_OF_TX_RING];
58224 + ULONG OneSecDmaDoneCount[NUM_OF_TX_RING];
58225 + UINT32 OneSecTxDoneCount;
58226 + ULONG OneSecRxCount;
58227 + UINT32 OneSecTxAggregationCount;
58228 + UINT32 OneSecRxAggregationCount;
58229 +
58230 + UINT32 OneSecFrameDuplicateCount;
58231 +
58232 +
58233 + UINT32 OneSecTxNoRetryOkCount;
58234 + UINT32 OneSecTxRetryOkCount;
58235 + UINT32 OneSecTxFailCount;
58236 + UINT32 OneSecFalseCCACnt; // CCA error count, for debug purpose, might move to global counter
58237 + UINT32 OneSecRxOkCnt; // RX without error
58238 + UINT32 OneSecRxOkDataCnt; // unicast-to-me DATA frame count
58239 + UINT32 OneSecRxFcsErrCnt; // CRC error
58240 + UINT32 OneSecBeaconSentCnt;
58241 + UINT32 LastOneSecTotalTxCount; // OneSecTxNoRetryOkCount + OneSecTxRetryOkCount + OneSecTxFailCount
58242 + UINT32 LastOneSecRxOkDataCnt; // OneSecRxOkDataCnt
58243 + ULONG DuplicateRcv;
58244 + ULONG TxAggCount;
58245 + ULONG TxNonAggCount;
58246 + ULONG TxAgg1MPDUCount;
58247 + ULONG TxAgg2MPDUCount;
58248 + ULONG TxAgg3MPDUCount;
58249 + ULONG TxAgg4MPDUCount;
58250 + ULONG TxAgg5MPDUCount;
58251 + ULONG TxAgg6MPDUCount;
58252 + ULONG TxAgg7MPDUCount;
58253 + ULONG TxAgg8MPDUCount;
58254 + ULONG TxAgg9MPDUCount;
58255 + ULONG TxAgg10MPDUCount;
58256 + ULONG TxAgg11MPDUCount;
58257 + ULONG TxAgg12MPDUCount;
58258 + ULONG TxAgg13MPDUCount;
58259 + ULONG TxAgg14MPDUCount;
58260 + ULONG TxAgg15MPDUCount;
58261 + ULONG TxAgg16MPDUCount;
58262 +
58263 + LARGE_INTEGER TransmittedOctetsInAMSDU;
58264 + LARGE_INTEGER TransmittedAMSDUCount;
58265 + LARGE_INTEGER ReceivedOctesInAMSDUCount;
58266 + LARGE_INTEGER ReceivedAMSDUCount;
58267 + LARGE_INTEGER TransmittedAMPDUCount;
58268 + LARGE_INTEGER TransmittedMPDUsInAMPDUCount;
58269 + LARGE_INTEGER TransmittedOctetsInAMPDUCount;
58270 + LARGE_INTEGER MPDUInReceivedAMPDUCount;
58271 +} COUNTER_RALINK, *PCOUNTER_RALINK;
58272 +
58273 +typedef struct _PID_COUNTER {
58274 + ULONG TxAckRequiredCount; // CRC error
58275 + ULONG TxAggreCount;
58276 + ULONG TxSuccessCount; // OneSecTxNoRetryOkCount + OneSecTxRetryOkCount + OneSecTxFailCount
58277 + ULONG LastSuccessRate;
58278 +} PID_COUNTER, *PPID_COUNTER;
58279 +
58280 +typedef struct _COUNTER_DRS {
58281 + // to record the each TX rate's quality. 0 is best, the bigger the worse.
58282 + USHORT TxQuality[MAX_STEP_OF_TX_RATE_SWITCH];
58283 + UCHAR PER[MAX_STEP_OF_TX_RATE_SWITCH];
58284 + UCHAR TxRateUpPenalty; // extra # of second penalty due to last unstable condition
58285 + ULONG CurrTxRateStableTime; // # of second in current TX rate
58286 + BOOLEAN fNoisyEnvironment;
58287 + BOOLEAN fLastSecAccordingRSSI;
58288 + UCHAR LastSecTxRateChangeAction; // 0: no change, 1:rate UP, 2:rate down
58289 + UCHAR LastTimeTxRateChangeAction; //Keep last time value of LastSecTxRateChangeAction
58290 + ULONG LastTxOkCount;
58291 +} COUNTER_DRS, *PCOUNTER_DRS;
58292 +
58293 +//
58294 +// Arcfour Structure Added by PaulWu
58295 +//
58296 +typedef struct _ARCFOUR
58297 +{
58298 + UINT X;
58299 + UINT Y;
58300 + UCHAR STATE[256];
58301 +} ARCFOURCONTEXT, *PARCFOURCONTEXT;
58302 +
58303 +// MIMO Tx parameter, ShortGI, MCS, STBC, etc. these are fields in TXWI too. just copy to TXWI.
58304 +typedef struct _RECEIVE_SETTING {
58305 +#ifdef RT_BIG_ENDIAN
58306 + USHORT MIMO:1;
58307 + USHORT OFDM:1;
58308 + USHORT rsv:3;
58309 + USHORT STBC:2; //SPACE
58310 + USHORT ShortGI:1;
58311 + USHORT Mode:2; //channel bandwidth 20MHz or 40 MHz
58312 + USHORT NumOfRX:2; // MIMO. WE HAVE 3R
58313 +#else
58314 + USHORT NumOfRX:2; // MIMO. WE HAVE 3R
58315 + USHORT Mode:2; //channel bandwidth 20MHz or 40 MHz
58316 + USHORT ShortGI:1;
58317 + USHORT STBC:2; //SPACE
58318 + USHORT rsv:3;
58319 + USHORT OFDM:1;
58320 + USHORT MIMO:1;
58321 +#endif
58322 + } RECEIVE_SETTING, *PRECEIVE_SETTING;
58323 +
58324 +// Shared key data structure
58325 +typedef struct _WEP_KEY {
58326 + UCHAR KeyLen; // Key length for each key, 0: entry is invalid
58327 + UCHAR Key[MAX_LEN_OF_KEY]; // right now we implement 4 keys, 128 bits max
58328 +} WEP_KEY, *PWEP_KEY;
58329 +
58330 +typedef struct _CIPHER_KEY {
58331 + UCHAR Key[16]; // right now we implement 4 keys, 128 bits max
58332 + UCHAR RxMic[8]; // make alignment
58333 + UCHAR TxMic[8];
58334 + UCHAR TxTsc[6]; // 48bit TSC value
58335 + UCHAR RxTsc[6]; // 48bit TSC value
58336 + UCHAR CipherAlg; // 0-none, 1:WEP64, 2:WEP128, 3:TKIP, 4:AES, 5:CKIP64, 6:CKIP128
58337 + UCHAR KeyLen;
58338 +#ifdef CONFIG_STA_SUPPORT
58339 + UCHAR BssId[6];
58340 +#endif // CONFIG_STA_SUPPORT //
58341 + // Key length for each key, 0: entry is invalid
58342 + UCHAR Type; // Indicate Pairwise/Group when reporting MIC error
58343 +} CIPHER_KEY, *PCIPHER_KEY;
58344 +
58345 +typedef struct _BBP_TUNING_STRUCT {
58346 + BOOLEAN Enable;
58347 + UCHAR FalseCcaCountUpperBound; // 100 per sec
58348 + UCHAR FalseCcaCountLowerBound; // 10 per sec
58349 + UCHAR R17LowerBound; // specified in E2PROM
58350 + UCHAR R17UpperBound; // 0x68 according to David Tung
58351 + UCHAR CurrentR17Value;
58352 +} BBP_TUNING, *PBBP_TUNING;
58353 +
58354 +typedef struct _SOFT_RX_ANT_DIVERSITY_STRUCT {
58355 + UCHAR EvaluatePeriod; // 0:not evalute status, 1: evaluate status, 2: switching status
58356 + UCHAR Pair1PrimaryRxAnt; // 0:Ant-E1, 1:Ant-E2
58357 + UCHAR Pair1SecondaryRxAnt; // 0:Ant-E1, 1:Ant-E2
58358 + UCHAR Pair2PrimaryRxAnt; // 0:Ant-E3, 1:Ant-E4
58359 + UCHAR Pair2SecondaryRxAnt; // 0:Ant-E3, 1:Ant-E4
58360 + SHORT Pair1AvgRssi[2]; // AvgRssi[0]:E1, AvgRssi[1]:E2
58361 + SHORT Pair2AvgRssi[2]; // AvgRssi[0]:E3, AvgRssi[1]:E4
58362 + SHORT Pair1LastAvgRssi; //
58363 + SHORT Pair2LastAvgRssi; //
58364 + ULONG RcvPktNumWhenEvaluate;
58365 + BOOLEAN FirstPktArrivedWhenEvaluate;
58366 + RALINK_TIMER_STRUCT RxAntDiversityTimer;
58367 +} SOFT_RX_ANT_DIVERSITY, *PSOFT_RX_ANT_DIVERSITY;
58368 +
58369 +typedef struct _LEAP_AUTH_INFO {
58370 + BOOLEAN Enabled; //Ture: Enable LEAP Authentication
58371 + BOOLEAN CCKM; //Ture: Use Fast Reauthentication with CCKM
58372 + UCHAR Reserve[2];
58373 + UCHAR UserName[256]; //LEAP, User name
58374 + ULONG UserNameLen;
58375 + UCHAR Password[256]; //LEAP, User Password
58376 + ULONG PasswordLen;
58377 +} LEAP_AUTH_INFO, *PLEAP_AUTH_INFO;
58378 +
58379 +typedef struct {
58380 + UCHAR Addr[MAC_ADDR_LEN];
58381 + UCHAR ErrorCode[2]; //00 01-Invalid authentication type
58382 + //00 02-Authentication timeout
58383 + //00 03-Challenge from AP failed
58384 + //00 04-Challenge to AP failed
58385 + BOOLEAN Reported;
58386 +} ROGUEAP_ENTRY, *PROGUEAP_ENTRY;
58387 +
58388 +typedef struct {
58389 + UCHAR RogueApNr;
58390 + ROGUEAP_ENTRY RogueApEntry[MAX_LEN_OF_BSS_TABLE];
58391 +} ROGUEAP_TABLE, *PROGUEAP_TABLE;
58392 +
58393 +typedef struct {
58394 + BOOLEAN Enable;
58395 + UCHAR Delta;
58396 + BOOLEAN PlusSign;
58397 +} CCK_TX_POWER_CALIBRATE, *PCCK_TX_POWER_CALIBRATE;
58398 +
58399 +//
58400 +// Receive Tuple Cache Format
58401 +//
58402 +typedef struct _TUPLE_CACHE {
58403 + BOOLEAN Valid;
58404 + UCHAR MacAddress[MAC_ADDR_LEN];
58405 + USHORT Sequence;
58406 + USHORT Frag;
58407 +} TUPLE_CACHE, *PTUPLE_CACHE;
58408 +
58409 +//
58410 +// Fragment Frame structure
58411 +//
58412 +typedef struct _FRAGMENT_FRAME {
58413 + PNDIS_PACKET pFragPacket;
58414 + ULONG RxSize;
58415 + USHORT Sequence;
58416 + USHORT LastFrag;
58417 + ULONG Flags; // Some extra frame information. bit 0: LLC presented
58418 +} FRAGMENT_FRAME, *PFRAGMENT_FRAME;
58419 +
58420 +
58421 +//
58422 +// Packet information for NdisQueryPacket
58423 +//
58424 +typedef struct _PACKET_INFO {
58425 + UINT PhysicalBufferCount; // Physical breaks of buffer descripor chained
58426 + UINT BufferCount ; // Number of Buffer descriptor chained
58427 + UINT TotalPacketLength ; // Self explained
58428 + PNDIS_BUFFER pFirstBuffer; // Pointer to first buffer descriptor
58429 +} PACKET_INFO, *PPACKET_INFO;
58430 +
58431 +//
58432 +// Tkip Key structure which RC4 key & MIC calculation
58433 +//
58434 +typedef struct _TKIP_KEY_INFO {
58435 + UINT nBytesInM; // # bytes in M for MICKEY
58436 + ULONG IV16;
58437 + ULONG IV32;
58438 + ULONG K0; // for MICKEY Low
58439 + ULONG K1; // for MICKEY Hig
58440 + ULONG L; // Current state for MICKEY
58441 + ULONG R; // Current state for MICKEY
58442 + ULONG M; // Message accumulator for MICKEY
58443 + UCHAR RC4KEY[16];
58444 + UCHAR MIC[8];
58445 +} TKIP_KEY_INFO, *PTKIP_KEY_INFO;
58446 +
58447 +//
58448 +// Private / Misc data, counters for driver internal use
58449 +//
58450 +typedef struct __PRIVATE_STRUC {
58451 + UINT SystemResetCnt; // System reset counter
58452 + UINT TxRingFullCnt; // Tx ring full occurrance number
58453 + UINT PhyRxErrCnt; // PHY Rx error count, for debug purpose, might move to global counter
58454 + // Variables for WEP encryption / decryption in rtmp_wep.c
58455 + UINT FCSCRC32;
58456 + ARCFOURCONTEXT WEPCONTEXT;
58457 + // Tkip stuff
58458 + TKIP_KEY_INFO Tx;
58459 + TKIP_KEY_INFO Rx;
58460 +} PRIVATE_STRUC, *PPRIVATE_STRUC;
58461 +
58462 +// structure to tune BBP R66 (BBP TUNING)
58463 +typedef struct _BBP_R66_TUNING {
58464 + BOOLEAN bEnable;
58465 + USHORT FalseCcaLowerThreshold; // default 100
58466 + USHORT FalseCcaUpperThreshold; // default 512
58467 + UCHAR R66Delta;
58468 + UCHAR R66CurrentValue;
58469 + BOOLEAN R66LowerUpperSelect; //Before LinkUp, Used LowerBound or UpperBound as R66 value.
58470 +} BBP_R66_TUNING, *PBBP_R66_TUNING;
58471 +
58472 +// structure to store channel TX power
58473 +typedef struct _CHANNEL_TX_POWER {
58474 + USHORT RemainingTimeForUse; //unit: sec
58475 + UCHAR Channel;
58476 +#ifdef DOT11N_DRAFT3
58477 + BOOLEAN bEffectedChannel; // For BW 40 operating in 2.4GHz , the "effected channel" is the channel that is covered in 40Mhz.
58478 +#endif // DOT11N_DRAFT3 //
58479 + CHAR Power;
58480 + CHAR Power2;
58481 + UCHAR MaxTxPwr;
58482 + UCHAR DfsReq;
58483 +} CHANNEL_TX_POWER, *PCHANNEL_TX_POWER;
58484 +
58485 +// structure to store 802.11j channel TX power
58486 +typedef struct _CHANNEL_11J_TX_POWER {
58487 + UCHAR Channel;
58488 + UCHAR BW; // BW_10 or BW_20
58489 + CHAR Power;
58490 + CHAR Power2;
58491 + USHORT RemainingTimeForUse; //unit: sec
58492 +} CHANNEL_11J_TX_POWER, *PCHANNEL_11J_TX_POWER;
58493 +
58494 +typedef enum _ABGBAND_STATE_ {
58495 + UNKNOWN_BAND,
58496 + BG_BAND,
58497 + A_BAND,
58498 +} ABGBAND_STATE;
58499 +
58500 +typedef struct _MLME_STRUCT {
58501 +#ifdef CONFIG_STA_SUPPORT
58502 + // STA state machines
58503 + STATE_MACHINE CntlMachine;
58504 + STATE_MACHINE AssocMachine;
58505 + STATE_MACHINE AuthMachine;
58506 + STATE_MACHINE AuthRspMachine;
58507 + STATE_MACHINE SyncMachine;
58508 + STATE_MACHINE WpaPskMachine;
58509 + STATE_MACHINE LeapMachine;
58510 + STATE_MACHINE AironetMachine;
58511 + STATE_MACHINE_FUNC AssocFunc[ASSOC_FUNC_SIZE];
58512 + STATE_MACHINE_FUNC AuthFunc[AUTH_FUNC_SIZE];
58513 + STATE_MACHINE_FUNC AuthRspFunc[AUTH_RSP_FUNC_SIZE];
58514 + STATE_MACHINE_FUNC SyncFunc[SYNC_FUNC_SIZE];
58515 + STATE_MACHINE_FUNC WpaPskFunc[WPA_PSK_FUNC_SIZE];
58516 + STATE_MACHINE_FUNC AironetFunc[AIRONET_FUNC_SIZE];
58517 +#endif // CONFIG_STA_SUPPORT //
58518 + STATE_MACHINE_FUNC ActFunc[ACT_FUNC_SIZE];
58519 + // Action
58520 + STATE_MACHINE ActMachine;
58521 +
58522 +
58523 +#ifdef QOS_DLS_SUPPORT
58524 + STATE_MACHINE DlsMachine;
58525 + STATE_MACHINE_FUNC DlsFunc[DLS_FUNC_SIZE];
58526 +#endif // QOS_DLS_SUPPORT //
58527 +
58528 +
58529 +
58530 +
58531 + ULONG ChannelQuality; // 0..100, Channel Quality Indication for Roaming
58532 + ULONG Now32; // latch the value of NdisGetSystemUpTime()
58533 + ULONG LastSendNULLpsmTime;
58534 +
58535 + BOOLEAN bRunning;
58536 + NDIS_SPIN_LOCK TaskLock;
58537 + MLME_QUEUE Queue;
58538 +
58539 + UINT ShiftReg;
58540 +
58541 + RALINK_TIMER_STRUCT PeriodicTimer;
58542 + RALINK_TIMER_STRUCT APSDPeriodicTimer;
58543 + RALINK_TIMER_STRUCT LinkDownTimer;
58544 + RALINK_TIMER_STRUCT LinkUpTimer;
58545 +#ifdef RT2860
58546 + UCHAR bPsPollTimerRunning;
58547 + RALINK_TIMER_STRUCT PsPollTimer;
58548 + RALINK_TIMER_STRUCT RadioOnOffTimer;
58549 +#endif // RT2860 //
58550 + ULONG PeriodicRound;
58551 + ULONG OneSecPeriodicRound;
58552 +
58553 + UCHAR RealRxPath;
58554 + BOOLEAN bLowThroughput;
58555 + BOOLEAN bEnableAutoAntennaCheck;
58556 + RALINK_TIMER_STRUCT RxAntEvalTimer;
58557 +
58558 +
58559 +} MLME_STRUCT, *PMLME_STRUCT;
58560 +
58561 +// structure for radar detection and channel switch
58562 +typedef struct _RADAR_DETECT_STRUCT {
58563 + UCHAR CSCount; //Channel switch counter
58564 + UCHAR CSPeriod; //Channel switch period (beacon count)
58565 + UCHAR RDCount; //Radar detection counter
58566 + UCHAR RDMode; //Radar Detection mode
58567 + UCHAR RDDurRegion; //Radar detection duration region
58568 + UCHAR BBPR16;
58569 + UCHAR BBPR17;
58570 + UCHAR BBPR18;
58571 + UCHAR BBPR21;
58572 + UCHAR BBPR22;
58573 + UCHAR BBPR64;
58574 + ULONG InServiceMonitorCount; // unit: sec
58575 + UINT8 DfsSessionTime;
58576 + BOOLEAN bFastDfs;
58577 + UINT8 ChMovingTime;
58578 + UINT8 LongPulseRadarTh;
58579 +} RADAR_DETECT_STRUCT, *PRADAR_DETECT_STRUCT;
58580 +
58581 +#ifdef CARRIER_DETECTION_SUPPORT
58582 +typedef enum CD_STATE_n
58583 +{
58584 + CD_NORMAL,
58585 + CD_SILENCE,
58586 + CD_MAX_STATE
58587 +} CD_STATE;
58588 +
58589 +typedef struct CARRIER_DETECTION_s
58590 +{
58591 + BOOLEAN Enable;
58592 + UINT8 CDSessionTime;
58593 + UINT8 CDPeriod;
58594 + CD_STATE CD_State;
58595 +} CARRIER_DETECTION, *PCARRIER_DETECTION;
58596 +#endif // CARRIER_DETECTION_SUPPORT //
58597 +
58598 +typedef enum _REC_BLOCKACK_STATUS
58599 +{
58600 + Recipient_NONE=0,
58601 + Recipient_USED,
58602 + Recipient_HandleRes,
58603 + Recipient_Accept
58604 +} REC_BLOCKACK_STATUS, *PREC_BLOCKACK_STATUS;
58605 +
58606 +typedef enum _ORI_BLOCKACK_STATUS
58607 +{
58608 + Originator_NONE=0,
58609 + Originator_USED,
58610 + Originator_WaitRes,
58611 + Originator_Done
58612 +} ORI_BLOCKACK_STATUS, *PORI_BLOCKACK_STATUS;
58613 +
58614 +#ifdef DOT11_N_SUPPORT
58615 +typedef struct _BA_ORI_ENTRY{
58616 + UCHAR Wcid;
58617 + UCHAR TID;
58618 + UCHAR BAWinSize;
58619 + UCHAR Token;
58620 +// Sequence is to fill every outgoing QoS DATA frame's sequence field in 802.11 header.
58621 + USHORT Sequence;
58622 + USHORT TimeOutValue;
58623 + ORI_BLOCKACK_STATUS ORI_BA_Status;
58624 + RALINK_TIMER_STRUCT ORIBATimer;
58625 + PVOID pAdapter;
58626 +} BA_ORI_ENTRY, *PBA_ORI_ENTRY;
58627 +
58628 +typedef struct _BA_REC_ENTRY {
58629 + UCHAR Wcid;
58630 + UCHAR TID;
58631 + UCHAR BAWinSize; // 7.3.1.14. each buffer is capable of holding a max AMSDU or MSDU.
58632 + USHORT LastIndSeq;
58633 + USHORT TimeOutValue;
58634 + RALINK_TIMER_STRUCT RECBATimer;
58635 + ULONG LastIndSeqAtTimer;
58636 + ULONG nDropPacket;
58637 + ULONG rcvSeq;
58638 + REC_BLOCKACK_STATUS REC_BA_Status;
58639 + NDIS_SPIN_LOCK RxReRingLock; // Rx Ring spinlock
58640 + PVOID pAdapter;
58641 + struct reordering_list list;
58642 +} BA_REC_ENTRY, *PBA_REC_ENTRY;
58643 +
58644 +
58645 +typedef struct {
58646 + ULONG numAsRecipient; // I am recipient of numAsRecipient clients. These client are in the BARecEntry[]
58647 + ULONG numAsOriginator; // I am originator of numAsOriginator clients. These clients are in the BAOriEntry[]
58648 + BA_ORI_ENTRY BAOriEntry[MAX_LEN_OF_BA_ORI_TABLE];
58649 + BA_REC_ENTRY BARecEntry[MAX_LEN_OF_BA_REC_TABLE];
58650 +} BA_TABLE, *PBA_TABLE;
58651 +
58652 +//For QureyBATableOID use;
58653 +typedef struct PACKED _OID_BA_REC_ENTRY{
58654 + UCHAR MACAddr[MAC_ADDR_LEN];
58655 + UCHAR BaBitmap; // if (BaBitmap&(1<<TID)), this session with{MACAddr, TID}exists, so read BufSize[TID] for BufferSize
58656 + UCHAR rsv;
58657 + UCHAR BufSize[8];
58658 + REC_BLOCKACK_STATUS REC_BA_Status[8];
58659 +} OID_BA_REC_ENTRY, *POID_BA_REC_ENTRY;
58660 +
58661 +//For QureyBATableOID use;
58662 +typedef struct PACKED _OID_BA_ORI_ENTRY{
58663 + UCHAR MACAddr[MAC_ADDR_LEN];
58664 + UCHAR BaBitmap; // if (BaBitmap&(1<<TID)), this session with{MACAddr, TID}exists, so read BufSize[TID] for BufferSize, read ORI_BA_Status[TID] for status
58665 + UCHAR rsv;
58666 + UCHAR BufSize[8];
58667 + ORI_BLOCKACK_STATUS ORI_BA_Status[8];
58668 +} OID_BA_ORI_ENTRY, *POID_BA_ORI_ENTRY;
58669 +
58670 +typedef struct _QUERYBA_TABLE{
58671 + OID_BA_ORI_ENTRY BAOriEntry[32];
58672 + OID_BA_REC_ENTRY BARecEntry[32];
58673 + UCHAR OriNum;// Number of below BAOriEntry
58674 + UCHAR RecNum;// Number of below BARecEntry
58675 +} QUERYBA_TABLE, *PQUERYBA_TABLE;
58676 +
58677 +typedef union _BACAP_STRUC {
58678 +#ifdef RT_BIG_ENDIAN
58679 + struct {
58680 + UINT32 :4;
58681 + UINT32 b2040CoexistScanSup:1; //As Sta, support do 2040 coexistence scan for AP. As Ap, support monitor trigger event to check if can use BW 40MHz.
58682 + UINT32 bHtAdhoc:1; // adhoc can use ht rate.
58683 + UINT32 MMPSmode:2; // MIMO power save more, 0:static, 1:dynamic, 2:rsv, 3:mimo enable
58684 + UINT32 AmsduSize:1; // 0:3839, 1:7935 bytes. UINT MSDUSizeToBytes[] = { 3839, 7935};
58685 + UINT32 AmsduEnable:1; //Enable AMSDU transmisstion
58686 + UINT32 MpduDensity:3;
58687 + UINT32 Policy:2; // 0: DELAY_BA 1:IMMED_BA (//BA Policy subfiled value in ADDBA frame) 2:BA-not use
58688 + UINT32 AutoBA:1; // automatically BA
58689 + UINT32 TxBAWinLimit:8;
58690 + UINT32 RxBAWinLimit:8;
58691 + } field;
58692 +#else
58693 + struct {
58694 + UINT32 RxBAWinLimit:8;
58695 + UINT32 TxBAWinLimit:8;
58696 + UINT32 AutoBA:1; // automatically BA
58697 + UINT32 Policy:2; // 0: DELAY_BA 1:IMMED_BA (//BA Policy subfiled value in ADDBA frame) 2:BA-not use
58698 + UINT32 MpduDensity:3;
58699 + UINT32 AmsduEnable:1; //Enable AMSDU transmisstion
58700 + UINT32 AmsduSize:1; // 0:3839, 1:7935 bytes. UINT MSDUSizeToBytes[] = { 3839, 7935};
58701 + UINT32 MMPSmode:2; // MIMO power save more, 0:static, 1:dynamic, 2:rsv, 3:mimo enable
58702 + UINT32 bHtAdhoc:1; // adhoc can use ht rate.
58703 + UINT32 b2040CoexistScanSup:1; //As Sta, support do 2040 coexistence scan for AP. As Ap, support monitor trigger event to check if can use BW 40MHz.
58704 + UINT32 :4;
58705 + } field;
58706 +#endif
58707 + UINT32 word;
58708 +} BACAP_STRUC, *PBACAP_STRUC;
58709 +#endif // DOT11_N_SUPPORT //
58710 +
58711 +//This structure is for all 802.11n card InterOptibilityTest action. Reset all Num every n second. (Details see MLMEPeriodic)
58712 +typedef struct _IOT_STRUC {
58713 + UCHAR Threshold[2];
58714 + UCHAR ReorderTimeOutNum[MAX_LEN_OF_BA_REC_TABLE]; // compare with threshold[0]
58715 + UCHAR RefreshNum[MAX_LEN_OF_BA_REC_TABLE]; // compare with threshold[1]
58716 + ULONG OneSecInWindowCount;
58717 + ULONG OneSecFrameDuplicateCount;
58718 + ULONG OneSecOutWindowCount;
58719 + UCHAR DelOriAct;
58720 + UCHAR DelRecAct;
58721 + UCHAR RTSShortProt;
58722 + UCHAR RTSLongProt;
58723 + BOOLEAN bRTSLongProtOn;
58724 +#ifdef CONFIG_STA_SUPPORT
58725 + BOOLEAN bLastAtheros;
58726 + BOOLEAN bCurrentAtheros;
58727 + BOOLEAN bNowAtherosBurstOn;
58728 + BOOLEAN bNextDisableRxBA;
58729 + BOOLEAN bToggle;
58730 +#endif // CONFIG_STA_SUPPORT //
58731 +} IOT_STRUC, *PIOT_STRUC;
58732 +
58733 +// This is the registry setting for 802.11n transmit setting. Used in advanced page.
58734 +typedef union _REG_TRANSMIT_SETTING {
58735 +#ifdef RT_BIG_ENDIAN
58736 + struct {
58737 + UINT32 rsv:13;
58738 + UINT32 EXTCHA:2;
58739 + UINT32 HTMODE:1;
58740 + UINT32 TRANSNO:2;
58741 + UINT32 STBC:1; //SPACE
58742 + UINT32 ShortGI:1;
58743 + UINT32 BW:1; //channel bandwidth 20MHz or 40 MHz
58744 + UINT32 TxBF:1; // 3*3
58745 + UINT32 rsv0:10;
58746 + } field;
58747 +#else
58748 + struct {
58749 + UINT32 rsv0:10;
58750 + UINT32 TxBF:1;
58751 + UINT32 BW:1; //channel bandwidth 20MHz or 40 MHz
58752 + UINT32 ShortGI:1;
58753 + UINT32 STBC:1; //SPACE
58754 + UINT32 TRANSNO:2;
58755 + UINT32 HTMODE:1;
58756 + UINT32 EXTCHA:2;
58757 + UINT32 rsv:13;
58758 + } field;
58759 +#endif
58760 + UINT32 word;
58761 +} REG_TRANSMIT_SETTING, *PREG_TRANSMIT_SETTING;
58762 +
58763 +typedef union _DESIRED_TRANSMIT_SETTING {
58764 +#ifdef RT_BIG_ENDIAN
58765 + struct {
58766 + USHORT rsv:3;
58767 + USHORT FixedTxMode:2; // If MCS isn't AUTO, fix rate in CCK, OFDM or HT mode.
58768 + USHORT PhyMode:4;
58769 + USHORT MCS:7; // MCS
58770 + } field;
58771 +#else
58772 + struct {
58773 + USHORT MCS:7; // MCS
58774 + USHORT PhyMode:4;
58775 + USHORT FixedTxMode:2; // If MCS isn't AUTO, fix rate in CCK, OFDM or HT mode.
58776 + USHORT rsv:3;
58777 + } field;
58778 +#endif
58779 + USHORT word;
58780 + } DESIRED_TRANSMIT_SETTING, *PDESIRED_TRANSMIT_SETTING;
58781 +
58782 +typedef struct {
58783 + BOOLEAN IsRecipient;
58784 + UCHAR MACAddr[MAC_ADDR_LEN];
58785 + UCHAR TID;
58786 + UCHAR nMSDU;
58787 + USHORT TimeOut;
58788 + BOOLEAN bAllTid; // If True, delete all TID for BA sessions with this MACaddr.
58789 +} OID_ADD_BA_ENTRY, *POID_ADD_BA_ENTRY;
58790 +
58791 +//
58792 +// Multiple SSID structure
58793 +//
58794 +#define WLAN_MAX_NUM_OF_TIM ((MAX_LEN_OF_MAC_TABLE >> 3) + 1) /* /8 + 1 */
58795 +#define WLAN_CT_TIM_BCMC_OFFSET 0 /* unit: 32B */
58796 +
58797 +/* clear bcmc TIM bit */
58798 +#define WLAN_MR_TIM_BCMC_CLEAR(apidx) \
58799 + pAd->ApCfg.MBSSID[apidx].TimBitmaps[WLAN_CT_TIM_BCMC_OFFSET] &= ~BIT8[0];
58800 +
58801 +/* set bcmc TIM bit */
58802 +#define WLAN_MR_TIM_BCMC_SET(apidx) \
58803 + pAd->ApCfg.MBSSID[apidx].TimBitmaps[WLAN_CT_TIM_BCMC_OFFSET] |= BIT8[0];
58804 +
58805 +/* clear a station PS TIM bit */
58806 +#define WLAN_MR_TIM_BIT_CLEAR(ad_p, apidx, wcid) \
58807 + { UCHAR tim_offset = wcid >> 3; \
58808 + UCHAR bit_offset = wcid & 0x7; \
58809 + ad_p->ApCfg.MBSSID[apidx].TimBitmaps[tim_offset] &= (~BIT8[bit_offset]); }
58810 +
58811 +/* set a station PS TIM bit */
58812 +#define WLAN_MR_TIM_BIT_SET(ad_p, apidx, wcid) \
58813 + { UCHAR tim_offset = wcid >> 3; \
58814 + UCHAR bit_offset = wcid & 0x7; \
58815 + ad_p->ApCfg.MBSSID[apidx].TimBitmaps[tim_offset] |= BIT8[bit_offset]; }
58816 +
58817 +
58818 +typedef struct _MULTISSID_STRUCT {
58819 + UCHAR Bssid[MAC_ADDR_LEN];
58820 + UCHAR SsidLen;
58821 + CHAR Ssid[MAX_LEN_OF_SSID];
58822 + USHORT CapabilityInfo;
58823 +
58824 + PNET_DEV MSSIDDev;
58825 +
58826 + NDIS_802_11_AUTHENTICATION_MODE AuthMode;
58827 + NDIS_802_11_WEP_STATUS WepStatus;
58828 + NDIS_802_11_WEP_STATUS GroupKeyWepStatus;
58829 + WPA_MIX_PAIR_CIPHER WpaMixPairCipher;
58830 +
58831 + ULONG TxCount;
58832 + ULONG RxCount;
58833 + ULONG ReceivedByteCount;
58834 + ULONG TransmittedByteCount;
58835 + ULONG RxErrorCount;
58836 + ULONG RxDropCount;
58837 +
58838 + HTTRANSMIT_SETTING HTPhyMode, MaxHTPhyMode, MinHTPhyMode;// For transmit phy setting in TXWI.
58839 + RT_HT_PHY_INFO DesiredHtPhyInfo;
58840 + DESIRED_TRANSMIT_SETTING DesiredTransmitSetting; // Desired transmit setting. this is for reading registry setting only. not useful.
58841 + BOOLEAN bAutoTxRateSwitch;
58842 +
58843 + UCHAR DefaultKeyId;
58844 +
58845 + UCHAR TxRate; // RATE_1, RATE_2, RATE_5_5, RATE_11, ...
58846 + UCHAR DesiredRates[MAX_LEN_OF_SUPPORTED_RATES];// OID_802_11_DESIRED_RATES
58847 + UCHAR DesiredRatesIndex;
58848 + UCHAR MaxTxRate; // RATE_1, RATE_2, RATE_5_5, RATE_11
58849 +
58850 + UCHAR TimBitmaps[WLAN_MAX_NUM_OF_TIM];
58851 +
58852 + // WPA
58853 + UCHAR GMK[32];
58854 + UCHAR PMK[32];
58855 + UCHAR GTK[32];
58856 + BOOLEAN IEEE8021X;
58857 + BOOLEAN PreAuth;
58858 + UCHAR GNonce[32];
58859 + UCHAR PortSecured;
58860 + NDIS_802_11_PRIVACY_FILTER PrivacyFilter;
58861 + UCHAR BANClass3Data;
58862 + ULONG IsolateInterStaTraffic;
58863 +
58864 + UCHAR RSNIE_Len[2];
58865 + UCHAR RSN_IE[2][MAX_LEN_OF_RSNIE];
58866 +
58867 +
58868 + UCHAR TimIELocationInBeacon;
58869 + UCHAR CapabilityInfoLocationInBeacon;
58870 + // outgoing BEACON frame buffer and corresponding TXWI
58871 + // PTXWI_STRUC BeaconTxWI; //
58872 + CHAR BeaconBuf[MAX_BEACON_SIZE]; // NOTE: BeaconBuf should be 4-byte aligned
58873 +
58874 + BOOLEAN bHideSsid;
58875 + UINT16 StationKeepAliveTime; // unit: second
58876 +
58877 + USHORT VLAN_VID;
58878 + USHORT VLAN_Priority;
58879 +
58880 + RT_802_11_ACL AccessControlList;
58881 +
58882 + // EDCA Qos
58883 + BOOLEAN bWmmCapable; // 0:disable WMM, 1:enable WMM
58884 + BOOLEAN bDLSCapable; // 0:disable DLS, 1:enable DLS
58885 +
58886 + UCHAR DlsPTK[64]; // Due to windows dirver count on meetinghouse to handle 4-way shake
58887 +
58888 + // For 802.1x daemon setting per BSS
58889 + UCHAR radius_srv_num;
58890 + RADIUS_SRV_INFO radius_srv_info[MAX_RADIUS_SRV_NUM];
58891 +
58892 +#ifdef RTL865X_SOC
58893 + unsigned int mylinkid;
58894 +#endif
58895 +
58896 +
58897 + UINT32 RcvdConflictSsidCount;
58898 + UINT32 RcvdSpoofedAssocRespCount;
58899 + UINT32 RcvdSpoofedReassocRespCount;
58900 + UINT32 RcvdSpoofedProbeRespCount;
58901 + UINT32 RcvdSpoofedBeaconCount;
58902 + UINT32 RcvdSpoofedDisassocCount;
58903 + UINT32 RcvdSpoofedAuthCount;
58904 + UINT32 RcvdSpoofedDeauthCount;
58905 + UINT32 RcvdSpoofedUnknownMgmtCount;
58906 + UINT32 RcvdReplayAttackCount;
58907 +
58908 + CHAR RssiOfRcvdConflictSsid;
58909 + CHAR RssiOfRcvdSpoofedAssocResp;
58910 + CHAR RssiOfRcvdSpoofedReassocResp;
58911 + CHAR RssiOfRcvdSpoofedProbeResp;
58912 + CHAR RssiOfRcvdSpoofedBeacon;
58913 + CHAR RssiOfRcvdSpoofedDisassoc;
58914 + CHAR RssiOfRcvdSpoofedAuth;
58915 + CHAR RssiOfRcvdSpoofedDeauth;
58916 + CHAR RssiOfRcvdSpoofedUnknownMgmt;
58917 + CHAR RssiOfRcvdReplayAttack;
58918 +
58919 + BOOLEAN bBcnSntReq;
58920 + UCHAR BcnBufIdx;
58921 +} MULTISSID_STRUCT, *PMULTISSID_STRUCT;
58922 +
58923 +
58924 +
58925 +#ifdef DOT11N_DRAFT3
58926 +typedef enum _BSS2040COEXIST_FLAG{
58927 + BSS_2040_COEXIST_DISABLE = 0,
58928 + BSS_2040_COEXIST_TIMER_FIRED = 1,
58929 + BSS_2040_COEXIST_INFO_SYNC = 2,
58930 + BSS_2040_COEXIST_INFO_NOTIFY = 4,
58931 +}BSS2040COEXIST_FLAG;
58932 +#endif // DOT11N_DRAFT3 //
58933 +
58934 +// configuration common to OPMODE_AP as well as OPMODE_STA
58935 +typedef struct _COMMON_CONFIG {
58936 +
58937 + BOOLEAN bCountryFlag;
58938 + UCHAR CountryCode[3];
58939 + UCHAR Geography;
58940 + UCHAR CountryRegion; // Enum of country region, 0:FCC, 1:IC, 2:ETSI, 3:SPAIN, 4:France, 5:MKK, 6:MKK1, 7:Israel
58941 + UCHAR CountryRegionForABand; // Enum of country region for A band
58942 + UCHAR PhyMode; // PHY_11A, PHY_11B, PHY_11BG_MIXED, PHY_ABG_MIXED
58943 + USHORT Dsifs; // in units of usec
58944 + ULONG PacketFilter; // Packet filter for receiving
58945 +
58946 + CHAR Ssid[MAX_LEN_OF_SSID]; // NOT NULL-terminated
58947 + UCHAR SsidLen; // the actual ssid length in used
58948 + UCHAR LastSsidLen; // the actual ssid length in used
58949 + CHAR LastSsid[MAX_LEN_OF_SSID]; // NOT NULL-terminated
58950 + UCHAR LastBssid[MAC_ADDR_LEN];
58951 +
58952 + UCHAR Bssid[MAC_ADDR_LEN];
58953 + USHORT BeaconPeriod;
58954 + UCHAR Channel;
58955 + UCHAR CentralChannel; // Central Channel when using 40MHz is indicating. not real channel.
58956 +
58957 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES];
58958 + UCHAR SupRateLen;
58959 + UCHAR ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
58960 + UCHAR ExtRateLen;
58961 + UCHAR DesireRate[MAX_LEN_OF_SUPPORTED_RATES]; // OID_802_11_DESIRED_RATES
58962 + UCHAR MaxDesiredRate;
58963 + UCHAR ExpectedACKRate[MAX_LEN_OF_SUPPORTED_RATES];
58964 +
58965 + ULONG BasicRateBitmap; // backup basic ratebitmap
58966 +
58967 + BOOLEAN bAPSDCapable;
58968 + BOOLEAN bInServicePeriod;
58969 + BOOLEAN bAPSDAC_BE;
58970 + BOOLEAN bAPSDAC_BK;
58971 + BOOLEAN bAPSDAC_VI;
58972 + BOOLEAN bAPSDAC_VO;
58973 + BOOLEAN bNeedSendTriggerFrame;
58974 + BOOLEAN bAPSDForcePowerSave; // Force power save mode, should only use in APSD-STAUT
58975 + ULONG TriggerTimerCount;
58976 + UCHAR MaxSPLength;
58977 + UCHAR BBPCurrentBW; // BW_10, BW_20, BW_40
58978 + REG_TRANSMIT_SETTING RegTransmitSetting; //registry transmit setting. this is for reading registry setting only. not useful.
58979 + UCHAR TxRate; // Same value to fill in TXD. TxRate is 6-bit
58980 + UCHAR MaxTxRate; // RATE_1, RATE_2, RATE_5_5, RATE_11
58981 + UCHAR TxRateIndex; // Tx rate index in RateSwitchTable
58982 + UCHAR TxRateTableSize; // Valid Tx rate table size in RateSwitchTable
58983 + UCHAR MinTxRate; // RATE_1, RATE_2, RATE_5_5, RATE_11
58984 + UCHAR RtsRate; // RATE_xxx
58985 + HTTRANSMIT_SETTING MlmeTransmit; // MGMT frame PHY rate setting when operatin at Ht rate.
58986 + UCHAR MlmeRate; // RATE_xxx, used to send MLME frames
58987 + UCHAR BasicMlmeRate; // Default Rate for sending MLME frames
58988 +
58989 + USHORT RtsThreshold; // in unit of BYTE
58990 + USHORT FragmentThreshold; // in unit of BYTE
58991 +
58992 + UCHAR TxPower; // in unit of mW
58993 + ULONG TxPowerPercentage; // 0~100 %
58994 + ULONG TxPowerDefault; // keep for TxPowerPercentage
58995 +
58996 +#ifdef DOT11_N_SUPPORT
58997 + BACAP_STRUC BACapability; // NO USE = 0XFF ; IMMED_BA =1 ; DELAY_BA=0
58998 + BACAP_STRUC REGBACapability; // NO USE = 0XFF ; IMMED_BA =1 ; DELAY_BA=0
58999 +#endif // DOT11_N_SUPPORT //
59000 + IOT_STRUC IOTestParm; // 802.11n InterOpbility Test Parameter;
59001 + ULONG TxPreamble; // Rt802_11PreambleLong, Rt802_11PreambleShort, Rt802_11PreambleAuto
59002 + BOOLEAN bUseZeroToDisableFragment; // Microsoft use 0 as disable
59003 + ULONG UseBGProtection; // 0: auto, 1: always use, 2: always not use
59004 + BOOLEAN bUseShortSlotTime; // 0: disable, 1 - use short slot (9us)
59005 + BOOLEAN bEnableTxBurst; // 1: enble TX PACKET BURST, 0: disable TX PACKET BURST
59006 + BOOLEAN bAggregationCapable; // 1: enable TX aggregation when the peer supports it
59007 + BOOLEAN bPiggyBackCapable; // 1: enable TX piggy-back according MAC's version
59008 + BOOLEAN bIEEE80211H; // 1: enable IEEE802.11h spec.
59009 + ULONG DisableOLBCDetect; // 0: enable OLBC detect; 1 disable OLBC detect
59010 +
59011 +#ifdef DOT11_N_SUPPORT
59012 + BOOLEAN bRdg;
59013 +#endif // DOT11_N_SUPPORT //
59014 + BOOLEAN bWmmCapable; // 0:disable WMM, 1:enable WMM
59015 + QOS_CAPABILITY_PARM APQosCapability; // QOS capability of the current associated AP
59016 + EDCA_PARM APEdcaParm; // EDCA parameters of the current associated AP
59017 + QBSS_LOAD_PARM APQbssLoad; // QBSS load of the current associated AP
59018 + UCHAR AckPolicy[4]; // ACK policy of the specified AC. see ACK_xxx
59019 +#ifdef CONFIG_STA_SUPPORT
59020 + BOOLEAN bDLSCapable; // 0:disable DLS, 1:enable DLS
59021 +#endif // CONFIG_STA_SUPPORT //
59022 + // a bitmap of BOOLEAN flags. each bit represent an operation status of a particular
59023 + // BOOLEAN control, either ON or OFF. These flags should always be accessed via
59024 + // OPSTATUS_TEST_FLAG(), OPSTATUS_SET_FLAG(), OP_STATUS_CLEAR_FLAG() macros.
59025 + // see fOP_STATUS_xxx in RTMP_DEF.C for detail bit definition
59026 + ULONG OpStatusFlags;
59027 +
59028 + BOOLEAN NdisRadioStateOff; //For HCT 12.0, set this flag to TRUE instead of called MlmeRadioOff.
59029 + ABGBAND_STATE BandState; // For setting BBP used on B/G or A mode.
59030 +
59031 + // IEEE802.11H--DFS.
59032 + RADAR_DETECT_STRUCT RadarDetect;
59033 +
59034 +#ifdef CARRIER_DETECTION_SUPPORT
59035 + CARRIER_DETECTION CarrierDetect;
59036 +#endif // CARRIER_DETECTION_SUPPORT //
59037 +
59038 +#ifdef DOT11_N_SUPPORT
59039 + // HT
59040 + UCHAR BASize; // USer desired BAWindowSize. Should not exceed our max capability
59041 + //RT_HT_CAPABILITY SupportedHtPhy;
59042 + RT_HT_CAPABILITY DesiredHtPhy;
59043 + HT_CAPABILITY_IE HtCapability;
59044 + ADD_HT_INFO_IE AddHTInfo; // Useful as AP.
59045 + //This IE is used with channel switch announcement element when changing to a new 40MHz.
59046 + //This IE is included in channel switch ammouncement frames 7.4.1.5, beacons, probe Rsp.
59047 + NEW_EXT_CHAN_IE NewExtChanOffset; //7.3.2.20A, 1 if extension channel is above the control channel, 3 if below, 0 if not present
59048 +
59049 +#ifdef DOT11N_DRAFT3
59050 + UCHAR Bss2040CoexistFlag; // bit 0: bBssCoexistTimerRunning, bit 1: NeedSyncAddHtInfo.
59051 + RALINK_TIMER_STRUCT Bss2040CoexistTimer;
59052 +
59053 + //This IE is used for 20/40 BSS Coexistence.
59054 + BSS_2040_COEXIST_IE BSS2040CoexistInfo;
59055 + // ====== 11n D3.0 =======================>
59056 + USHORT Dot11OBssScanPassiveDwell; // Unit : TU. 5~1000
59057 + USHORT Dot11OBssScanActiveDwell; // Unit : TU. 10~1000
59058 + USHORT Dot11BssWidthTriggerScanInt; // Unit : Second
59059 + USHORT Dot11OBssScanPassiveTotalPerChannel; // Unit : TU. 200~10000
59060 + USHORT Dot11OBssScanActiveTotalPerChannel; // Unit : TU. 20~10000
59061 + USHORT Dot11BssWidthChanTranDelayFactor;
59062 + USHORT Dot11OBssScanActivityThre; // Unit : percentage
59063 +
59064 + ULONG Dot11BssWidthChanTranDelay; // multiple of (Dot11BssWidthTriggerScanInt * Dot11BssWidthChanTranDelayFactor)
59065 + ULONG CountDownCtr; // CountDown Counter from (Dot11BssWidthTriggerScanInt * Dot11BssWidthChanTranDelayFactor)
59066 +
59067 + NDIS_SPIN_LOCK TriggerEventTabLock;
59068 + BSS_2040_COEXIST_IE LastBSSCoexist2040;
59069 + BSS_2040_COEXIST_IE BSSCoexist2040;
59070 + TRIGGER_EVENT_TAB TriggerEventTab;
59071 + UCHAR ChannelListIdx;
59072 + // <====== 11n D3.0 =======================
59073 + BOOLEAN bOverlapScanning;
59074 +#endif // DOT11N_DRAFT3 //
59075 +
59076 + BOOLEAN bHTProtect;
59077 + BOOLEAN bMIMOPSEnable;
59078 + BOOLEAN bBADecline;
59079 + BOOLEAN bDisableReordering;
59080 + BOOLEAN bForty_Mhz_Intolerant;
59081 + BOOLEAN bExtChannelSwitchAnnouncement;
59082 + BOOLEAN bRcvBSSWidthTriggerEvents;
59083 + ULONG LastRcvBSSWidthTriggerEventsTime;
59084 +
59085 + UCHAR TxBASize;
59086 +#endif // DOT11_N_SUPPORT //
59087 +
59088 + // Enable wireless event
59089 + BOOLEAN bWirelessEvent;
59090 + BOOLEAN bWiFiTest; // Enable this parameter for WiFi test
59091 +
59092 + // Tx & Rx Stream number selection
59093 + UCHAR TxStream;
59094 + UCHAR RxStream;
59095 +
59096 + // transmit phy mode, trasmit rate for Multicast.
59097 +#ifdef MCAST_RATE_SPECIFIC
59098 + UCHAR McastTransmitMcs;
59099 + UCHAR McastTransmitPhyMode;
59100 +#endif // MCAST_RATE_SPECIFIC //
59101 +
59102 + BOOLEAN bHardwareRadio; // Hardware controlled Radio enabled
59103 +
59104 +
59105 +
59106 + NDIS_SPIN_LOCK MeasureReqTabLock;
59107 + PMEASURE_REQ_TAB pMeasureReqTab;
59108 +
59109 + NDIS_SPIN_LOCK TpcReqTabLock;
59110 + PTPC_REQ_TAB pTpcReqTab;
59111 +
59112 + // transmit phy mode, trasmit rate for Multicast.
59113 +#ifdef MCAST_RATE_SPECIFIC
59114 + HTTRANSMIT_SETTING MCastPhyMode;
59115 +#endif // MCAST_RATE_SPECIFIC //
59116 +
59117 +#ifdef SINGLE_SKU
59118 + UINT16 DefineMaxTxPwr;
59119 +#endif // SINGLE_SKU //
59120 +
59121 +
59122 +} COMMON_CONFIG, *PCOMMON_CONFIG;
59123 +
59124 +
59125 +#ifdef CONFIG_STA_SUPPORT
59126 +/* Modified by Wu Xi-Kun 4/21/2006 */
59127 +// STA configuration and status
59128 +typedef struct _STA_ADMIN_CONFIG {
59129 + // GROUP 1 -
59130 + // User configuration loaded from Registry, E2PROM or OID_xxx. These settings describe
59131 + // the user intended configuration, but not necessary fully equal to the final
59132 + // settings in ACTIVE BSS after negotiation/compromize with the BSS holder (either
59133 + // AP or IBSS holder).
59134 + // Once initialized, user configuration can only be changed via OID_xxx
59135 + UCHAR BssType; // BSS_INFRA or BSS_ADHOC
59136 + USHORT AtimWin; // used when starting a new IBSS
59137 +
59138 + // GROUP 2 -
59139 + // User configuration loaded from Registry, E2PROM or OID_xxx. These settings describe
59140 + // the user intended configuration, and should be always applied to the final
59141 + // settings in ACTIVE BSS without compromising with the BSS holder.
59142 + // Once initialized, user configuration can only be changed via OID_xxx
59143 + UCHAR RssiTrigger;
59144 + UCHAR RssiTriggerMode; // RSSI_TRIGGERED_UPON_BELOW_THRESHOLD or RSSI_TRIGGERED_UPON_EXCCEED_THRESHOLD
59145 + USHORT DefaultListenCount; // default listen count;
59146 + ULONG WindowsPowerMode; // Power mode for AC power
59147 + ULONG WindowsBatteryPowerMode; // Power mode for battery if exists
59148 + BOOLEAN bWindowsACCAMEnable; // Enable CAM power mode when AC on
59149 + BOOLEAN bAutoReconnect; // Set to TRUE when setting OID_802_11_SSID with no matching BSSID
59150 + ULONG WindowsPowerProfile; // Windows power profile, for NDIS5.1 PnP
59151 +
59152 + // MIB:ieee802dot11.dot11smt(1).dot11StationConfigTable(1)
59153 + USHORT Psm; // power management mode (PWR_ACTIVE|PWR_SAVE)
59154 + USHORT DisassocReason;
59155 + UCHAR DisassocSta[MAC_ADDR_LEN];
59156 + USHORT DeauthReason;
59157 + UCHAR DeauthSta[MAC_ADDR_LEN];
59158 + USHORT AuthFailReason;
59159 + UCHAR AuthFailSta[MAC_ADDR_LEN];
59160 +
59161 + NDIS_802_11_PRIVACY_FILTER PrivacyFilter; // PrivacyFilter enum for 802.1X
59162 + NDIS_802_11_AUTHENTICATION_MODE AuthMode; // This should match to whatever microsoft defined
59163 + NDIS_802_11_WEP_STATUS WepStatus;
59164 + NDIS_802_11_WEP_STATUS OrigWepStatus; // Original wep status set from OID
59165 +
59166 + // Add to support different cipher suite for WPA2/WPA mode
59167 + NDIS_802_11_ENCRYPTION_STATUS GroupCipher; // Multicast cipher suite
59168 + NDIS_802_11_ENCRYPTION_STATUS PairCipher; // Unicast cipher suite
59169 + BOOLEAN bMixCipher; // Indicate current Pair & Group use different cipher suites
59170 + USHORT RsnCapability;
59171 +
59172 + NDIS_802_11_WEP_STATUS GroupKeyWepStatus;
59173 +
59174 + UCHAR PMK[32]; // WPA PSK mode PMK
59175 + UCHAR PTK[64]; // WPA PSK mode PTK
59176 + UCHAR GTK[32]; // GTK from authenticator
59177 + BSSID_INFO SavedPMK[PMKID_NO];
59178 + UINT SavedPMKNum; // Saved PMKID number
59179 +
59180 + UCHAR DefaultKeyId;
59181 +
59182 +
59183 + // WPA 802.1x port control, WPA_802_1X_PORT_SECURED, WPA_802_1X_PORT_NOT_SECURED
59184 + UCHAR PortSecured;
59185 +
59186 + // For WPA countermeasures
59187 + ULONG LastMicErrorTime; // record last MIC error time
59188 + ULONG MicErrCnt; // Should be 0, 1, 2, then reset to zero (after disassoiciation).
59189 + BOOLEAN bBlockAssoc; // Block associate attempt for 60 seconds after counter measure occurred.
59190 + // For WPA-PSK supplicant state
59191 + WPA_STATE WpaState; // Default is SS_NOTUSE and handled by microsoft 802.1x
59192 + UCHAR ReplayCounter[8];
59193 + UCHAR ANonce[32]; // ANonce for WPA-PSK from aurhenticator
59194 + UCHAR SNonce[32]; // SNonce for WPA-PSK
59195 +
59196 + UCHAR LastSNR0; // last received BEACON's SNR
59197 + UCHAR LastSNR1; // last received BEACON's SNR for 2nd antenna
59198 + RSSI_SAMPLE RssiSample;
59199 + ULONG NumOfAvgRssiSample;
59200 +
59201 + ULONG LastBeaconRxTime; // OS's timestamp of the last BEACON RX time
59202 + ULONG Last11bBeaconRxTime; // OS's timestamp of the last 11B BEACON RX time
59203 + ULONG Last11gBeaconRxTime; // OS's timestamp of the last 11G BEACON RX time
59204 + ULONG Last20NBeaconRxTime; // OS's timestamp of the last 20MHz N BEACON RX time
59205 +
59206 + ULONG LastScanTime; // Record last scan time for issue BSSID_SCAN_LIST
59207 + ULONG ScanCnt; // Scan counts since most recent SSID, BSSID, SCAN OID request
59208 + BOOLEAN bSwRadio; // Software controlled Radio On/Off, TRUE: On
59209 + BOOLEAN bHwRadio; // Hardware controlled Radio On/Off, TRUE: On
59210 + BOOLEAN bRadio; // Radio state, And of Sw & Hw radio state
59211 + BOOLEAN bHardwareRadio; // Hardware controlled Radio enabled
59212 + BOOLEAN bShowHiddenSSID; // Show all known SSID in SSID list get operation
59213 +
59214 + BOOLEAN AdhocBOnlyJoined; // Indicate Adhoc B Join.
59215 + BOOLEAN AdhocBGJoined; // Indicate Adhoc B/G Join.
59216 + BOOLEAN Adhoc20NJoined; // Indicate Adhoc 20MHz N Join.
59217 +
59218 + // New for WPA, windows want us to to keep association information and
59219 + // Fixed IEs from last association response
59220 + NDIS_802_11_ASSOCIATION_INFORMATION AssocInfo;
59221 + USHORT ReqVarIELen; // Length of next VIE include EID & Length
59222 + UCHAR ReqVarIEs[MAX_VIE_LEN]; // The content saved here should be little-endian format.
59223 + USHORT ResVarIELen; // Length of next VIE include EID & Length
59224 + UCHAR ResVarIEs[MAX_VIE_LEN];
59225 +
59226 + UCHAR RSNIE_Len;
59227 + UCHAR RSN_IE[MAX_LEN_OF_RSNIE]; // The content saved here should be little-endian format.
59228 +
59229 + // New variables used for CCX 1.0
59230 + BOOLEAN bCkipOn;
59231 + BOOLEAN bCkipCmicOn;
59232 + UCHAR CkipFlag;
59233 + UCHAR GIV[3]; //for CCX iv
59234 + UCHAR RxSEQ[4];
59235 + UCHAR TxSEQ[4];
59236 + UCHAR CKIPMIC[4];
59237 + UCHAR LeapAuthMode;
59238 + LEAP_AUTH_INFO LeapAuthInfo;
59239 + UCHAR HashPwd[16];
59240 + UCHAR NetworkChallenge[8];
59241 + UCHAR NetworkChallengeResponse[24];
59242 + UCHAR PeerChallenge[8];
59243 +
59244 + UCHAR PeerChallengeResponse[24];
59245 + UCHAR SessionKey[16]; //Network session keys (NSK)
59246 + RALINK_TIMER_STRUCT LeapAuthTimer;
59247 + ROGUEAP_TABLE RogueApTab; //Cisco CCX1 Rogue AP Detection
59248 +
59249 + // New control flags for CCX
59250 + CCX_CONTROL CCXControl; // Master administration state
59251 + BOOLEAN CCXEnable; // Actual CCX state
59252 + UCHAR CCXScanChannel; // Selected channel for CCX beacon request
59253 + USHORT CCXScanTime; // Time out to wait for beacon and probe response
59254 + UCHAR CCXReqType; // Current processing CCX request type
59255 + BSS_TABLE CCXBssTab; // BSS Table
59256 + UCHAR FrameReportBuf[2048]; // Buffer for creating frame report
59257 + USHORT FrameReportLen; // Current Frame report length
59258 + ULONG CLBusyBytes; // Save the total bytes received durning channel load scan time
59259 + USHORT RPIDensity[8]; // Array for RPI density collection
59260 + // Start address of each BSS table within FrameReportBuf
59261 + // It's important to update the RxPower of the corresponding Bss
59262 + USHORT BssReportOffset[MAX_LEN_OF_BSS_TABLE];
59263 + USHORT BeaconToken; // Token for beacon report
59264 + ULONG LastBssIndex; // Most current reported Bss index
59265 + RM_REQUEST_ACTION MeasurementRequest[16]; // Saved measurement request
59266 + UCHAR RMReqCnt; // Number of measurement request saved.
59267 + UCHAR CurrentRMReqIdx; // Number of measurement request saved.
59268 + BOOLEAN ParallelReq; // Parallel measurement, only one request performed,
59269 + // It must be the same channel with maximum duration
59270 + USHORT ParallelDuration; // Maximum duration for parallel measurement
59271 + UCHAR ParallelChannel; // Only one channel with parallel measurement
59272 + USHORT IAPPToken; // IAPP dialog token
59273 + UCHAR CCXQosECWMin; // Cisco QOS ECWMin for AC 0
59274 + UCHAR CCXQosECWMax; // Cisco QOS ECWMax for AC 0
59275 + // Hack for channel load and noise histogram parameters
59276 + UCHAR NHFactor; // Parameter for Noise histogram
59277 + UCHAR CLFactor; // Parameter for channel load
59278 +
59279 + UCHAR KRK[16]; //Key Refresh Key.
59280 + UCHAR BTK[32]; //Base Transient Key
59281 + BOOLEAN CCKMLinkUpFlag;
59282 + ULONG CCKMRN; //(Re)Association request number.
59283 + LARGE_INTEGER CCKMBeaconAtJoinTimeStamp; //TSF timer for Re-assocaite to the new AP
59284 + UCHAR AironetCellPowerLimit; //in dBm
59285 + UCHAR AironetIPAddress[4]; //eg. 192.168.1.1
59286 + BOOLEAN CCXAdjacentAPReportFlag; //flag for determining report Assoc Lost time
59287 + CHAR CCXAdjacentAPSsid[MAX_LEN_OF_SSID]; //Adjacent AP's SSID report
59288 + UCHAR CCXAdjacentAPSsidLen; // the actual ssid length in used
59289 + UCHAR CCXAdjacentAPBssid[MAC_ADDR_LEN]; //Adjacent AP's BSSID report
59290 + USHORT CCXAdjacentAPChannel;
59291 + ULONG CCXAdjacentAPLinkDownTime; //for Spec S32.
59292 +
59293 + RALINK_TIMER_STRUCT StaQuickResponeForRateUpTimer;
59294 + BOOLEAN StaQuickResponeForRateUpTimerRunning;
59295 +
59296 + UCHAR DtimCount; // 0.. DtimPeriod-1
59297 + UCHAR DtimPeriod; // default = 3
59298 +
59299 +#ifdef QOS_DLS_SUPPORT
59300 + RT_802_11_DLS DLSEntry[MAX_NUM_OF_DLS_ENTRY];
59301 + UCHAR DlsReplayCounter[8];
59302 +#endif // QOS_DLS_SUPPORT //
59303 + ////////////////////////////////////////////////////////////////////////////////////////
59304 + // This is only for WHQL test.
59305 + BOOLEAN WhqlTest;
59306 + ////////////////////////////////////////////////////////////////////////////////////////
59307 +
59308 + RALINK_TIMER_STRUCT WpaDisassocAndBlockAssocTimer;
59309 + // Fast Roaming
59310 + BOOLEAN bFastRoaming; // 0:disable fast roaming, 1:enable fast roaming
59311 + CHAR dBmToRoam; // the condition to roam when receiving Rssi less than this value. It's negative value.
59312 +
59313 +#ifdef WPA_SUPPLICANT_SUPPORT
59314 + BOOLEAN IEEE8021X;
59315 + BOOLEAN IEEE8021x_required_keys;
59316 + CIPHER_KEY DesireSharedKey[4]; // Record user desired WEP keys
59317 + UCHAR DesireSharedKeyId;
59318 +
59319 + // 0: driver ignores wpa_supplicant
59320 + // 1: wpa_supplicant initiates scanning and AP selection
59321 + // 2: driver takes care of scanning, AP selection, and IEEE 802.11 association parameters
59322 + UCHAR WpaSupplicantUP;
59323 + UCHAR WpaSupplicantScanCount;
59324 +#endif // WPA_SUPPLICANT_SUPPORT //
59325 +
59326 + CHAR dev_name[16];
59327 + USHORT OriDevType;
59328 +
59329 + BOOLEAN bTGnWifiTest;
59330 + BOOLEAN bScanReqIsFromWebUI;
59331 +
59332 + HTTRANSMIT_SETTING HTPhyMode, MaxHTPhyMode, MinHTPhyMode;// For transmit phy setting in TXWI.
59333 + DESIRED_TRANSMIT_SETTING DesiredTransmitSetting;
59334 + RT_HT_PHY_INFO DesiredHtPhyInfo;
59335 + BOOLEAN bAutoTxRateSwitch;
59336 +
59337 +#ifdef RT2860
59338 + UCHAR BBPR3;
59339 +#endif // RT2860 //
59340 +
59341 +#ifdef EXT_BUILD_CHANNEL_LIST
59342 + UCHAR IEEE80211dClientMode;
59343 + UCHAR StaOriCountryCode[3];
59344 + UCHAR StaOriGeography;
59345 +#endif // EXT_BUILD_CHANNEL_LIST //
59346 +} STA_ADMIN_CONFIG, *PSTA_ADMIN_CONFIG;
59347 +
59348 +// This data structure keep the current active BSS/IBSS's configuration that this STA
59349 +// had agreed upon joining the network. Which means these parameters are usually decided
59350 +// by the BSS/IBSS creator instead of user configuration. Data in this data structurre
59351 +// is valid only when either ADHOC_ON(pAd) or INFRA_ON(pAd) is TRUE.
59352 +// Normally, after SCAN or failed roaming attempts, we need to recover back to
59353 +// the current active settings.
59354 +typedef struct _STA_ACTIVE_CONFIG {
59355 + USHORT Aid;
59356 + USHORT AtimWin; // in kusec; IBSS parameter set element
59357 + USHORT CapabilityInfo;
59358 + USHORT CfpMaxDuration;
59359 + USHORT CfpPeriod;
59360 +
59361 + // Copy supported rate from desired AP's beacon. We are trying to match
59362 + // AP's supported and extended rate settings.
59363 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES];
59364 + UCHAR ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
59365 + UCHAR SupRateLen;
59366 + UCHAR ExtRateLen;
59367 + // Copy supported ht from desired AP's beacon. We are trying to match
59368 + RT_HT_PHY_INFO SupportedPhyInfo;
59369 + RT_HT_CAPABILITY SupportedHtPhy;
59370 +} STA_ACTIVE_CONFIG, *PSTA_ACTIVE_CONFIG;
59371 +#endif // CONFIG_STA_SUPPORT //
59372 +
59373 +// ----------- start of AP --------------------------
59374 +// AUTH-RSP State Machine Aux data structure
59375 +typedef struct _AP_MLME_AUX {
59376 + UCHAR Addr[MAC_ADDR_LEN];
59377 + USHORT Alg;
59378 + CHAR Challenge[CIPHER_TEXT_LEN];
59379 +} AP_MLME_AUX, *PAP_MLME_AUX;
59380 +
59381 +// structure to define WPA Group Key Rekey Interval
59382 +typedef struct PACKED _RT_802_11_WPA_REKEY {
59383 + ULONG ReKeyMethod; // mechanism for rekeying: 0:disable, 1: time-based, 2: packet-based
59384 + ULONG ReKeyInterval; // time-based: seconds, packet-based: kilo-packets
59385 +} RT_WPA_REKEY,*PRT_WPA_REKEY, RT_802_11_WPA_REKEY, *PRT_802_11_WPA_REKEY;
59386 +
59387 +typedef struct _MAC_TABLE_ENTRY {
59388 + //Choose 1 from ValidAsWDS and ValidAsCLI to validize.
59389 + BOOLEAN ValidAsCLI; // Sta mode, set this TRUE after Linkup,too.
59390 + BOOLEAN ValidAsWDS; // This is WDS Entry. only for AP mode.
59391 + BOOLEAN ValidAsApCli; //This is a AP-Client entry, only for AP mode which enable AP-Client functions.
59392 + BOOLEAN ValidAsMesh;
59393 + BOOLEAN ValidAsDls; // This is DLS Entry. only for STA mode.
59394 + BOOLEAN isCached;
59395 + BOOLEAN bIAmBadAtheros; // Flag if this is Atheros chip that has IOT problem. We need to turn on RTS/CTS protection.
59396 +
59397 + UCHAR EnqueueEapolStartTimerRunning; // Enqueue EAPoL-Start for triggering EAP SM
59398 + //jan for wpa
59399 + // record which entry revoke MIC Failure , if it leaves the BSS itself, AP won't update aMICFailTime MIB
59400 + UCHAR CMTimerRunning;
59401 + UCHAR apidx; // MBSS number
59402 + UCHAR RSNIE_Len;
59403 + UCHAR RSN_IE[MAX_LEN_OF_RSNIE];
59404 + UCHAR ANonce[LEN_KEY_DESC_NONCE];
59405 + UCHAR R_Counter[LEN_KEY_DESC_REPLAY];
59406 + UCHAR PTK[64];
59407 + UCHAR ReTryCounter;
59408 + RALINK_TIMER_STRUCT RetryTimer;
59409 + RALINK_TIMER_STRUCT EnqueueStartForPSKTimer; // A timer which enqueue EAPoL-Start for triggering PSK SM
59410 + NDIS_802_11_AUTHENTICATION_MODE AuthMode; // This should match to whatever microsoft defined
59411 + NDIS_802_11_WEP_STATUS WepStatus;
59412 + AP_WPA_STATE WpaState;
59413 + GTK_STATE GTKState;
59414 + USHORT PortSecured;
59415 + NDIS_802_11_PRIVACY_FILTER PrivacyFilter; // PrivacyFilter enum for 802.1X
59416 + CIPHER_KEY PairwiseKey;
59417 + PVOID pAd;
59418 + INT PMKID_CacheIdx;
59419 + UCHAR PMKID[LEN_PMKID];
59420 +
59421 +
59422 + UCHAR Addr[MAC_ADDR_LEN];
59423 + UCHAR PsMode;
59424 + SST Sst;
59425 + AUTH_STATE AuthState; // for SHARED KEY authentication state machine used only
59426 + BOOLEAN IsReassocSta; // Indicate whether this is a reassociation procedure
59427 + USHORT Aid;
59428 + USHORT CapabilityInfo;
59429 + UCHAR LastRssi;
59430 + ULONG NoDataIdleCount;
59431 + UINT16 StationKeepAliveCount; // unit: second
59432 + ULONG PsQIdleCount;
59433 + QUEUE_HEADER PsQueue;
59434 +
59435 + UINT32 StaConnectTime; // the live time of this station since associated with AP
59436 +
59437 +
59438 +#ifdef DOT11_N_SUPPORT
59439 + BOOLEAN bSendBAR;
59440 + USHORT NoBADataCountDown;
59441 +
59442 + UINT32 CachedBuf[16]; // UINT (4 bytes) for alignment
59443 + UINT TxBFCount; // 3*3
59444 +#endif // DOT11_N_SUPPORT //
59445 + UINT FIFOCount;
59446 + UINT DebugFIFOCount;
59447 + UINT DebugTxCount;
59448 + BOOLEAN bDlsInit;
59449 +
59450 +
59451 +//====================================================
59452 +//WDS entry needs these
59453 +// rt2860 add this. if ValidAsWDS==TRUE, MatchWDSTabIdx is the index in WdsTab.MacTab
59454 + UINT MatchWDSTabIdx;
59455 + UCHAR MaxSupportedRate;
59456 + UCHAR CurrTxRate;
59457 + UCHAR CurrTxRateIndex;
59458 + // to record the each TX rate's quality. 0 is best, the bigger the worse.
59459 + USHORT TxQuality[MAX_STEP_OF_TX_RATE_SWITCH];
59460 + UINT32 OneSecTxNoRetryOkCount;
59461 + UINT32 OneSecTxRetryOkCount;
59462 + UINT32 OneSecTxFailCount;
59463 + UINT32 ContinueTxFailCnt;
59464 + UINT32 CurrTxRateStableTime; // # of second in current TX rate
59465 + UCHAR TxRateUpPenalty; // extra # of second penalty due to last unstable condition
59466 +//====================================================
59467 +
59468 +
59469 +
59470 +#ifdef CONFIG_STA_SUPPORT
59471 +#ifdef QOS_DLS_SUPPORT
59472 + UINT MatchDlsEntryIdx; // indicate the index in pAd->StaCfg.DLSEntry
59473 +#endif // QOS_DLS_SUPPORT //
59474 +#endif // CONFIG_STA_SUPPORT //
59475 +
59476 + BOOLEAN fNoisyEnvironment;
59477 + BOOLEAN fLastSecAccordingRSSI;
59478 + UCHAR LastSecTxRateChangeAction; // 0: no change, 1:rate UP, 2:rate down
59479 + CHAR LastTimeTxRateChangeAction; //Keep last time value of LastSecTxRateChangeAction
59480 + ULONG LastTxOkCount;
59481 + UCHAR PER[MAX_STEP_OF_TX_RATE_SWITCH];
59482 +
59483 + // a bitmap of BOOLEAN flags. each bit represent an operation status of a particular
59484 + // BOOLEAN control, either ON or OFF. These flags should always be accessed via
59485 + // CLIENT_STATUS_TEST_FLAG(), CLIENT_STATUS_SET_FLAG(), CLIENT_STATUS_CLEAR_FLAG() macros.
59486 + // see fOP_STATUS_xxx in RTMP_DEF.C for detail bit definition. fCLIENT_STATUS_AMSDU_INUSED
59487 + ULONG ClientStatusFlags;
59488 +
59489 + // TODO: Shall we move that to DOT11_N_SUPPORT???
59490 + HTTRANSMIT_SETTING HTPhyMode, MaxHTPhyMode, MinHTPhyMode;// For transmit phy setting in TXWI.
59491 +
59492 +#ifdef DOT11_N_SUPPORT
59493 + // HT EWC MIMO-N used parameters
59494 + USHORT RXBAbitmap; // fill to on-chip RXWI_BA_BITMASK in 8.1.3RX attribute entry format
59495 + USHORT TXBAbitmap; // This bitmap as originator, only keep in software used to mark AMPDU bit in TXWI
59496 + USHORT TXAutoBAbitmap;
59497 + USHORT BADeclineBitmap;
59498 + USHORT BARecWcidArray[NUM_OF_TID]; // The mapping wcid of recipient session. if RXBAbitmap bit is masked
59499 + USHORT BAOriWcidArray[NUM_OF_TID]; // The mapping wcid of originator session. if TXBAbitmap bit is masked
59500 + USHORT BAOriSequence[NUM_OF_TID]; // The mapping wcid of originator session. if TXBAbitmap bit is masked
59501 +
59502 + // 802.11n features.
59503 + UCHAR MpduDensity;
59504 + UCHAR MaxRAmpduFactor;
59505 + UCHAR AMsduSize;
59506 + UCHAR MmpsMode; // MIMO power save more.
59507 +
59508 + HT_CAPABILITY_IE HTCapability;
59509 +
59510 +#ifdef DOT11N_DRAFT3
59511 + UCHAR BSS2040CoexistenceMgmtSupport;
59512 +#endif // DOT11N_DRAFT3 //
59513 +#endif // DOT11_N_SUPPORT //
59514 +
59515 + BOOLEAN bAutoTxRateSwitch;
59516 +
59517 + UCHAR RateLen;
59518 + struct _MAC_TABLE_ENTRY *pNext;
59519 + USHORT TxSeq[NUM_OF_TID];
59520 + USHORT NonQosDataSeq;
59521 +
59522 + RSSI_SAMPLE RssiSample;
59523 +
59524 + UINT32 TXMCSExpected[16];
59525 + UINT32 TXMCSSuccessful[16];
59526 + UINT32 TXMCSFailed[16];
59527 + UINT32 TXMCSAutoFallBack[16][16];
59528 +} MAC_TABLE_ENTRY, *PMAC_TABLE_ENTRY;
59529 +
59530 +typedef struct _MAC_TABLE {
59531 + USHORT Size;
59532 + MAC_TABLE_ENTRY *Hash[HASH_TABLE_SIZE];
59533 + MAC_TABLE_ENTRY Content[MAX_LEN_OF_MAC_TABLE];
59534 + QUEUE_HEADER McastPsQueue;
59535 + ULONG PsQIdleCount;
59536 + BOOLEAN fAnyStationInPsm;
59537 + BOOLEAN fAnyStationBadAtheros; // Check if any Station is atheros 802.11n Chip. We need to use RTS/CTS with Atheros 802,.11n chip.
59538 + BOOLEAN fAnyTxOPForceDisable; // Check if it is necessary to disable BE TxOP
59539 +#ifdef DOT11_N_SUPPORT
59540 + BOOLEAN fAnyStationIsLegacy; // Check if I use legacy rate to transmit to my BSS Station/
59541 + BOOLEAN fAnyStationNonGF; // Check if any Station can't support GF.
59542 + BOOLEAN fAnyStation20Only; // Check if any Station can't support GF.
59543 + BOOLEAN fAnyStationMIMOPSDynamic; // Check if any Station is MIMO Dynamic
59544 + BOOLEAN fAnyBASession; // Check if there is BA session. Force turn on RTS/CTS
59545 +#endif // DOT11_N_SUPPORT //
59546 +} MAC_TABLE, *PMAC_TABLE;
59547 +
59548 +#ifdef DOT11_N_SUPPORT
59549 +#define IS_HT_STA(_pMacEntry) \
59550 + (_pMacEntry->MaxHTPhyMode.field.MODE >= MODE_HTMIX)
59551 +
59552 +#define IS_HT_RATE(_pMacEntry) \
59553 + (_pMacEntry->HTPhyMode.field.MODE >= MODE_HTMIX)
59554 +
59555 +#define PEER_IS_HT_RATE(_pMacEntry) \
59556 + (_pMacEntry->HTPhyMode.field.MODE >= MODE_HTMIX)
59557 +#endif // DOT11_N_SUPPORT //
59558 +
59559 +typedef struct _WDS_ENTRY {
59560 + BOOLEAN Valid;
59561 + UCHAR Addr[MAC_ADDR_LEN];
59562 + ULONG NoDataIdleCount;
59563 + struct _WDS_ENTRY *pNext;
59564 +} WDS_ENTRY, *PWDS_ENTRY;
59565 +
59566 +typedef struct _WDS_TABLE_ENTRY {
59567 + USHORT Size;
59568 + UCHAR WdsAddr[MAC_ADDR_LEN];
59569 + WDS_ENTRY *Hash[HASH_TABLE_SIZE];
59570 + WDS_ENTRY Content[MAX_LEN_OF_MAC_TABLE];
59571 + UCHAR MaxSupportedRate;
59572 + UCHAR CurrTxRate;
59573 + USHORT TxQuality[MAX_LEN_OF_SUPPORTED_RATES];
59574 + USHORT OneSecTxOkCount;
59575 + USHORT OneSecTxRetryOkCount;
59576 + USHORT OneSecTxFailCount;
59577 + ULONG CurrTxRateStableTime; // # of second in current TX rate
59578 + UCHAR TxRateUpPenalty; // extra # of second penalty due to last unstable condition
59579 +} WDS_TABLE_ENTRY, *PWDS_TABLE_ENTRY;
59580 +
59581 +typedef struct _RT_802_11_WDS_ENTRY {
59582 + PNET_DEV dev;
59583 + UCHAR Valid;
59584 + UCHAR PhyMode;
59585 + UCHAR PeerWdsAddr[MAC_ADDR_LEN];
59586 + UCHAR MacTabMatchWCID; // ASIC
59587 + NDIS_802_11_WEP_STATUS WepStatus;
59588 + UCHAR KeyIdx;
59589 + CIPHER_KEY WdsKey;
59590 + HTTRANSMIT_SETTING HTPhyMode, MaxHTPhyMode, MinHTPhyMode;
59591 + RT_HT_PHY_INFO DesiredHtPhyInfo;
59592 + BOOLEAN bAutoTxRateSwitch;
59593 + DESIRED_TRANSMIT_SETTING DesiredTransmitSetting; // Desired transmit setting.
59594 +} RT_802_11_WDS_ENTRY, *PRT_802_11_WDS_ENTRY;
59595 +
59596 +typedef struct _WDS_TABLE {
59597 + UCHAR Mode;
59598 + ULONG Size;
59599 + RT_802_11_WDS_ENTRY WdsEntry[MAX_WDS_ENTRY];
59600 +} WDS_TABLE, *PWDS_TABLE;
59601 +
59602 +typedef struct _APCLI_STRUCT {
59603 + PNET_DEV dev;
59604 +#ifdef RTL865X_SOC
59605 + unsigned int mylinkid;
59606 +#endif
59607 + BOOLEAN Enable; // Set it as 1 if the apcli interface was configured to "1" or by iwpriv cmd "ApCliEnable"
59608 + BOOLEAN Valid; // Set it as 1 if the apcli interface associated success to remote AP.
59609 + UCHAR MacTabWCID; //WCID value, which point to the entry of ASIC Mac table.
59610 + UCHAR SsidLen;
59611 + CHAR Ssid[MAX_LEN_OF_SSID];
59612 +
59613 + UCHAR CfgSsidLen;
59614 + CHAR CfgSsid[MAX_LEN_OF_SSID];
59615 + UCHAR CfgApCliBssid[ETH_LENGTH_OF_ADDRESS];
59616 + UCHAR CurrentAddress[ETH_LENGTH_OF_ADDRESS];
59617 +
59618 + ULONG ApCliRcvBeaconTime;
59619 +
59620 + ULONG CtrlCurrState;
59621 + ULONG SyncCurrState;
59622 + ULONG AuthCurrState;
59623 + ULONG AssocCurrState;
59624 + ULONG WpaPskCurrState;
59625 +
59626 + USHORT AuthReqCnt;
59627 + USHORT AssocReqCnt;
59628 +
59629 + ULONG ClientStatusFlags;
59630 + UCHAR MpduDensity;
59631 +
59632 + NDIS_802_11_AUTHENTICATION_MODE AuthMode; // This should match to whatever microsoft defined
59633 + NDIS_802_11_WEP_STATUS WepStatus;
59634 +
59635 + // Add to support different cipher suite for WPA2/WPA mode
59636 + NDIS_802_11_ENCRYPTION_STATUS GroupCipher; // Multicast cipher suite
59637 + NDIS_802_11_ENCRYPTION_STATUS PairCipher; // Unicast cipher suite
59638 + BOOLEAN bMixCipher; // Indicate current Pair & Group use different cipher suites
59639 + USHORT RsnCapability;
59640 +
59641 + UCHAR PSK[100]; // reserve PSK key material
59642 + UCHAR PSKLen;
59643 + UCHAR PMK[32]; // WPA PSK mode PMK
59644 + UCHAR GTK[32]; // GTK from authenticator
59645 +
59646 + CIPHER_KEY SharedKey[SHARE_KEY_NUM];
59647 + UCHAR DefaultKeyId;
59648 +
59649 + // store RSN_IE built by driver
59650 + UCHAR RSN_IE[MAX_LEN_OF_RSNIE]; // The content saved here should be convert to little-endian format.
59651 + UCHAR RSNIE_Len;
59652 +
59653 + // For WPA countermeasures
59654 + ULONG LastMicErrorTime; // record last MIC error time
59655 + BOOLEAN bBlockAssoc; // Block associate attempt for 60 seconds after counter measure occurred.
59656 +
59657 + // For WPA-PSK supplicant state
59658 + UCHAR SNonce[32]; // SNonce for WPA-PSK
59659 + UCHAR GNonce[32]; // GNonce for WPA-PSK from authenticator
59660 +
59661 +#ifdef WSC_AP_SUPPORT
59662 + WSC_CTRL WscControl;
59663 +#endif // WSC_AP_SUPPORT //
59664 +
59665 + HTTRANSMIT_SETTING HTPhyMode, MaxHTPhyMode, MinHTPhyMode;
59666 + RT_HT_PHY_INFO DesiredHtPhyInfo;
59667 + BOOLEAN bAutoTxRateSwitch;
59668 + DESIRED_TRANSMIT_SETTING DesiredTransmitSetting; // Desired transmit setting.
59669 +} APCLI_STRUCT, *PAPCLI_STRUCT;
59670 +
59671 +// ----------- end of AP ----------------------------
59672 +
59673 +#ifdef BLOCK_NET_IF
59674 +typedef struct _BLOCK_QUEUE_ENTRY
59675 +{
59676 + BOOLEAN SwTxQueueBlockFlag;
59677 + LIST_HEADER NetIfList;
59678 +} BLOCK_QUEUE_ENTRY, *PBLOCK_QUEUE_ENTRY;
59679 +#endif // BLOCK_NET_IF //
59680 +
59681 +struct wificonf
59682 +{
59683 + BOOLEAN bShortGI;
59684 + BOOLEAN bGreenField;
59685 +};
59686 +
59687 +
59688 +
59689 +
59690 +typedef struct _INF_PCI_CONFIG
59691 +{
59692 + PUCHAR CSRBaseAddress; // PCI MMIO Base Address, all access will use
59693 +}INF_PCI_CONFIG;
59694 +
59695 +typedef struct _INF_USB_CONFIG
59696 +{
59697 + UINT BulkInEpAddr; // bulk-in endpoint address
59698 + UINT BulkOutEpAddr[6]; // bulk-out endpoint address
59699 +
59700 +}INF_USB_CONFIG;
59701 +
59702 +#ifdef IKANOS_VX_1X0
59703 + typedef void (*IkanosWlanTxCbFuncP)(void *, void *);
59704 +
59705 + struct IKANOS_TX_INFO
59706 + {
59707 + struct net_device *netdev;
59708 + IkanosWlanTxCbFuncP *fp;
59709 + };
59710 +#endif // IKANOS_VX_1X0 //
59711 +
59712 +#ifdef NINTENDO_AP
59713 +typedef struct _NINDO_CTRL_BLOCK {
59714 +
59715 + RT_NINTENDO_TABLE DS_TABLE;
59716 +
59717 +#ifdef CHIP25XX
59718 + spinlock_t NINTENDO_TABLE_Lock;
59719 +#else
59720 + NDIS_SPIN_LOCK NINTENDO_TABLE_Lock;
59721 +#endif // CHIP25XX //
59722 +
59723 + UCHAR NINTENDO_UP_BUFFER[512];
59724 + UCHAR Local_KeyIdx;
59725 + CIPHER_KEY Local_SharedKey;
59726 + UCHAR Local_bHideSsid;
59727 + UCHAR Local_AuthMode;
59728 + UCHAR Local_WepStatus;
59729 + USHORT Local_CapabilityInfo;
59730 +} NINDO_CTRL_BLOCK;
59731 +#endif // NINTENDO_AP //
59732 +
59733 +
59734 +#ifdef DBG_DIAGNOSE
59735 +#define DIAGNOSE_TIME 10 // 10 sec
59736 +typedef struct _RtmpDiagStrcut_
59737 +{ // Diagnosis Related element
59738 + unsigned char inited;
59739 + unsigned char qIdx;
59740 + unsigned char ArrayStartIdx;
59741 + unsigned char ArrayCurIdx;
59742 + // Tx Related Count
59743 + USHORT TxDataCnt[DIAGNOSE_TIME];
59744 + USHORT TxFailCnt[DIAGNOSE_TIME];
59745 + USHORT TxDescCnt[DIAGNOSE_TIME][24]; // 3*3 // TxDesc queue length in scale of 0~14, >=15
59746 + USHORT TxMcsCnt[DIAGNOSE_TIME][24]; // 3*3
59747 + USHORT TxSWQueCnt[DIAGNOSE_TIME][9]; // TxSwQueue length in scale of 0, 1, 2, 3, 4, 5, 6, 7, >=8
59748 +
59749 + USHORT TxAggCnt[DIAGNOSE_TIME];
59750 + USHORT TxNonAggCnt[DIAGNOSE_TIME];
59751 + USHORT TxAMPDUCnt[DIAGNOSE_TIME][24]; // 3*3 // 10 sec, TxDMA APMDU Aggregation count in range from 0 to 15, in setp of 1.
59752 + USHORT TxRalinkCnt[DIAGNOSE_TIME]; // TxRalink Aggregation Count in 1 sec scale.
59753 + USHORT TxAMSDUCnt[DIAGNOSE_TIME]; // TxAMSUD Aggregation Count in 1 sec scale.
59754 +
59755 + // Rx Related Count
59756 + USHORT RxDataCnt[DIAGNOSE_TIME]; // Rx Total Data count.
59757 + USHORT RxCrcErrCnt[DIAGNOSE_TIME];
59758 + USHORT RxMcsCnt[DIAGNOSE_TIME][24]; // 3*3
59759 +}RtmpDiagStruct;
59760 +#endif // DBG_DIAGNOSE //
59761 +
59762 +
59763 +//
59764 +// The miniport adapter structure
59765 +//
59766 +typedef struct _RTMP_ADAPTER
59767 +{
59768 + PVOID OS_Cookie; // save specific structure relative to OS
59769 + PNET_DEV net_dev;
59770 + ULONG VirtualIfCnt;
59771 +
59772 +#ifdef RT2860
59773 + USHORT LnkCtrlBitMask;
59774 + USHORT RLnkCtrlConfiguration;
59775 + USHORT RLnkCtrlOffset;
59776 + USHORT HostLnkCtrlConfiguration;
59777 + USHORT HostLnkCtrlOffset;
59778 + USHORT PCIePowerSaveLevel;
59779 + BOOLEAN bPCIclkOff; // flag that indicate if the PICE power status in Configuration SPace..
59780 + BOOLEAN bPCIclkOffDisableTx; //
59781 +
59782 +
59783 +/*****************************************************************************************/
59784 +/* PCI related parameters */
59785 +/*****************************************************************************************/
59786 + PUCHAR CSRBaseAddress; // PCI MMIO Base Address, all access will use
59787 +
59788 + UINT int_enable_reg;
59789 + UINT int_disable_mask;
59790 + UINT int_pending;
59791 +
59792 +
59793 + RTMP_DMABUF TxBufSpace[NUM_OF_TX_RING]; // Shared memory of all 1st pre-allocated TxBuf associated with each TXD
59794 + RTMP_DMABUF RxDescRing; // Shared memory for RX descriptors
59795 + RTMP_DMABUF TxDescRing[NUM_OF_TX_RING]; // Shared memory for Tx descriptors
59796 + RTMP_TX_RING TxRing[NUM_OF_TX_RING]; // AC0~4 + HCCA
59797 +#endif // RT2860 //
59798 +
59799 +
59800 + NDIS_SPIN_LOCK irq_lock;
59801 + UCHAR irq_disabled;
59802 +
59803 +
59804 +
59805 +/*****************************************************************************************/
59806 + /* Both PCI/USB related parameters */
59807 +/*****************************************************************************************/
59808 +
59809 +
59810 +/*****************************************************************************************/
59811 +/* Tx related parameters */
59812 +/*****************************************************************************************/
59813 + BOOLEAN DeQueueRunning[NUM_OF_TX_RING]; // for ensuring RTUSBDeQueuePacket get call once
59814 + NDIS_SPIN_LOCK DeQueueLock[NUM_OF_TX_RING];
59815 +
59816 +
59817 + // resource for software backlog queues
59818 + QUEUE_HEADER TxSwQueue[NUM_OF_TX_RING]; // 4 AC + 1 HCCA
59819 + NDIS_SPIN_LOCK TxSwQueueLock[NUM_OF_TX_RING]; // TxSwQueue spinlock
59820 +
59821 + RTMP_DMABUF MgmtDescRing; // Shared memory for MGMT descriptors
59822 + RTMP_MGMT_RING MgmtRing;
59823 + NDIS_SPIN_LOCK MgmtRingLock; // Prio Ring spinlock
59824 +
59825 +
59826 +/*****************************************************************************************/
59827 +/* Rx related parameters */
59828 +/*****************************************************************************************/
59829 +
59830 +#ifdef RT2860
59831 + RTMP_RX_RING RxRing;
59832 + NDIS_SPIN_LOCK RxRingLock; // Rx Ring spinlock
59833 +#endif // RT2860 //
59834 +
59835 +
59836 +
59837 +/*****************************************************************************************/
59838 +/* ASIC related parameters */
59839 +/*****************************************************************************************/
59840 + UINT32 MACVersion; // MAC version. Record rt2860C(0x28600100) or rt2860D (0x28600101)..
59841 +
59842 + // ---------------------------
59843 + // E2PROM
59844 + // ---------------------------
59845 + ULONG EepromVersion; // byte 0: version, byte 1: revision, byte 2~3: unused
59846 + UCHAR EEPROMAddressNum; // 93c46=6 93c66=8
59847 + USHORT EEPROMDefaultValue[NUM_EEPROM_BBP_PARMS];
59848 + ULONG FirmwareVersion; // byte 0: Minor version, byte 1: Major version, otherwise unused.
59849 +
59850 + // ---------------------------
59851 + // BBP Control
59852 + // ---------------------------
59853 + UCHAR BbpWriteLatch[140]; // record last BBP register value written via BBP_IO_WRITE/BBP_IO_WRITE_VY_REG_ID
59854 + UCHAR BbpRssiToDbmDelta;
59855 + BBP_R66_TUNING BbpTuning;
59856 +
59857 + // ----------------------------
59858 + // RFIC control
59859 + // ----------------------------
59860 + UCHAR RfIcType; // RFIC_xxx
59861 + ULONG RfFreqOffset; // Frequency offset for channel switching
59862 + RTMP_RF_REGS LatchRfRegs; // latch th latest RF programming value since RF IC doesn't support READ
59863 +
59864 + EEPROM_ANTENNA_STRUC Antenna; // Since ANtenna definition is different for a & g. We need to save it for future reference.
59865 + EEPROM_NIC_CONFIG2_STRUC NicConfig2;
59866 +
59867 + // This soft Rx Antenna Diversity mechanism is used only when user set
59868 + // RX Antenna = DIVERSITY ON
59869 + SOFT_RX_ANT_DIVERSITY RxAnt;
59870 +
59871 + UCHAR RFProgSeq;
59872 + CHANNEL_TX_POWER TxPower[MAX_NUM_OF_CHANNELS]; // Store Tx power value for all channels.
59873 + CHANNEL_TX_POWER ChannelList[MAX_NUM_OF_CHANNELS]; // list all supported channels for site survey
59874 + CHANNEL_11J_TX_POWER TxPower11J[MAX_NUM_OF_11JCHANNELS]; // 802.11j channel and bw
59875 + CHANNEL_11J_TX_POWER ChannelList11J[MAX_NUM_OF_11JCHANNELS]; // list all supported channels for site survey
59876 +
59877 + UCHAR ChannelListNum; // number of channel in ChannelList[]
59878 + UCHAR Bbp94;
59879 + BOOLEAN BbpForCCK;
59880 + ULONG Tx20MPwrCfgABand[5];
59881 + ULONG Tx20MPwrCfgGBand[5];
59882 + ULONG Tx40MPwrCfgABand[5];
59883 + ULONG Tx40MPwrCfgGBand[5];
59884 +
59885 + BOOLEAN bAutoTxAgcA; // Enable driver auto Tx Agc control
59886 + UCHAR TssiRefA; // Store Tssi reference value as 25 temperature.
59887 + UCHAR TssiPlusBoundaryA[5]; // Tssi boundary for increase Tx power to compensate.
59888 + UCHAR TssiMinusBoundaryA[5]; // Tssi boundary for decrease Tx power to compensate.
59889 + UCHAR TxAgcStepA; // Store Tx TSSI delta increment / decrement value
59890 + CHAR TxAgcCompensateA; // Store the compensation (TxAgcStep * (idx-1))
59891 +
59892 + BOOLEAN bAutoTxAgcG; // Enable driver auto Tx Agc control
59893 + UCHAR TssiRefG; // Store Tssi reference value as 25 temperature.
59894 + UCHAR TssiPlusBoundaryG[5]; // Tssi boundary for increase Tx power to compensate.
59895 + UCHAR TssiMinusBoundaryG[5]; // Tssi boundary for decrease Tx power to compensate.
59896 + UCHAR TxAgcStepG; // Store Tx TSSI delta increment / decrement value
59897 + CHAR TxAgcCompensateG; // Store the compensation (TxAgcStep * (idx-1))
59898 +
59899 + //+++For RT2870, the parameteres is start from BGRssiOffset1 ~ BGRssiOffset3
59900 + CHAR BGRssiOffset0; // Store B/G RSSI#0 Offset value on EEPROM 0x46h
59901 + CHAR BGRssiOffset1; // Store B/G RSSI#1 Offset value
59902 + CHAR BGRssiOffset2; // Store B/G RSSI#2 Offset value
59903 + //---
59904 +
59905 + //+++For RT2870, the parameteres is start from ARssiOffset1 ~ ARssiOffset3
59906 + CHAR ARssiOffset0; // Store A RSSI#0 Offset value on EEPROM 0x4Ah
59907 + CHAR ARssiOffset1; // Store A RSSI#1 Offset value
59908 + CHAR ARssiOffset2; // Store A RSSI#2 Offset value
59909 + //---
59910 +
59911 + CHAR BLNAGain; // Store B/G external LNA#0 value on EEPROM 0x44h
59912 + CHAR ALNAGain0; // Store A external LNA#0 value for ch36~64
59913 + CHAR ALNAGain1; // Store A external LNA#1 value for ch100~128
59914 + CHAR ALNAGain2; // Store A external LNA#2 value for ch132~165
59915 +
59916 + // ----------------------------
59917 + // LED control
59918 + // ----------------------------
59919 + MCU_LEDCS_STRUC LedCntl;
59920 + USHORT Led1; // read from EEPROM 0x3c
59921 + USHORT Led2; // EEPROM 0x3e
59922 + USHORT Led3; // EEPROM 0x40
59923 + UCHAR LedIndicatorStregth;
59924 + UCHAR RssiSingalstrengthOffet;
59925 + BOOLEAN bLedOnScanning;
59926 + UCHAR LedStatus;
59927 +
59928 +/*****************************************************************************************/
59929 +/* 802.11 related parameters */
59930 +/*****************************************************************************************/
59931 + // outgoing BEACON frame buffer and corresponding TXD
59932 + TXWI_STRUC BeaconTxWI;
59933 + PUCHAR BeaconBuf;
59934 + USHORT BeaconOffset[HW_BEACON_MAX_COUNT];
59935 +
59936 + // pre-build PS-POLL and NULL frame upon link up. for efficiency purpose.
59937 + PSPOLL_FRAME PsPollFrame;
59938 + HEADER_802_11 NullFrame;
59939 +
59940 +//=========AP===========
59941 +
59942 +
59943 +//=======STA===========
59944 +#ifdef CONFIG_STA_SUPPORT
59945 +/* Modified by Wu Xi-Kun 4/21/2006 */
59946 + // -----------------------------------------------
59947 + // STA specific configuration & operation status
59948 + // used only when pAd->OpMode == OPMODE_STA
59949 + // -----------------------------------------------
59950 + STA_ADMIN_CONFIG StaCfg; // user desired settings
59951 + STA_ACTIVE_CONFIG StaActive; // valid only when ADHOC_ON(pAd) || INFRA_ON(pAd)
59952 + CHAR nickname[IW_ESSID_MAX_SIZE+1]; // nickname, only used in the iwconfig i/f
59953 + NDIS_MEDIA_STATE PreMediaState;
59954 +#endif // CONFIG_STA_SUPPORT //
59955 +
59956 +//=======Common===========
59957 + // OP mode: either AP or STA
59958 + UCHAR OpMode; // OPMODE_STA, OPMODE_AP
59959 +
59960 + NDIS_MEDIA_STATE IndicateMediaState; // Base on Indication state, default is NdisMediaStateDisConnected
59961 +
59962 + // MAT related parameters
59963 +
59964 + // configuration: read from Registry & E2PROM
59965 + BOOLEAN bLocalAdminMAC; // Use user changed MAC
59966 + UCHAR PermanentAddress[MAC_ADDR_LEN]; // Factory default MAC address
59967 + UCHAR CurrentAddress[MAC_ADDR_LEN]; // User changed MAC address
59968 +
59969 + // ------------------------------------------------------
59970 + // common configuration to both OPMODE_STA and OPMODE_AP
59971 + // ------------------------------------------------------
59972 + COMMON_CONFIG CommonCfg;
59973 + MLME_STRUCT Mlme;
59974 +
59975 + // AP needs those vaiables for site survey feature.
59976 + MLME_AUX MlmeAux; // temporary settings used during MLME state machine
59977 + BSS_TABLE ScanTab; // store the latest SCAN result
59978 +
59979 + //About MacTab, the sta driver will use #0 and #1 for multicast and AP.
59980 + MAC_TABLE MacTab; // ASIC on-chip WCID entry table. At TX, ASIC always use key according to this on-chip table.
59981 + NDIS_SPIN_LOCK MacTabLock;
59982 +
59983 +#ifdef DOT11_N_SUPPORT
59984 + BA_TABLE BATable;
59985 +#endif // DOT11_N_SUPPORT //
59986 + NDIS_SPIN_LOCK BATabLock;
59987 + RALINK_TIMER_STRUCT RECBATimer;
59988 +
59989 + // encryption/decryption KEY tables
59990 + CIPHER_KEY SharedKey[MAX_MBSSID_NUM][4]; // STA always use SharedKey[BSS0][0..3]
59991 +
59992 + // RX re-assembly buffer for fragmentation
59993 + FRAGMENT_FRAME FragFrame; // Frame storage for fragment frame
59994 +
59995 + // various Counters
59996 + COUNTER_802_3 Counters8023; // 802.3 counters
59997 + COUNTER_802_11 WlanCounters; // 802.11 MIB counters
59998 + COUNTER_RALINK RalinkCounters; // Ralink propriety counters
59999 + COUNTER_DRS DrsCounters; // counters for Dynamic TX Rate Switching
60000 + PRIVATE_STRUC PrivateInfo; // Private information & counters
60001 +
60002 + // flags, see fRTMP_ADAPTER_xxx flags
60003 + ULONG Flags; // Represent current device status
60004 +
60005 + // current TX sequence #
60006 + USHORT Sequence;
60007 +
60008 +#ifdef UNDER_CE
60009 + NDIS_HANDLE hGiISR;
60010 +#endif
60011 +
60012 +
60013 + // Control disconnect / connect event generation
60014 + //+++Didn't used anymore
60015 + ULONG LinkDownTime;
60016 + //---
60017 + ULONG LastRxRate;
60018 + ULONG LastTxRate;
60019 + //+++Used only for Station
60020 + BOOLEAN bConfigChanged; // Config Change flag for the same SSID setting
60021 + //---
60022 +
60023 + ULONG ExtraInfo; // Extra information for displaying status
60024 + ULONG SystemErrorBitmap; // b0: E2PROM version error
60025 +
60026 + //+++Didn't used anymore
60027 + ULONG MacIcVersion; // MAC/BBP serial interface issue solved after ver.D
60028 + //---
60029 +
60030 + // ---------------------------
60031 + // System event log
60032 + // ---------------------------
60033 + RT_802_11_EVENT_TABLE EventTab;
60034 +
60035 +
60036 + BOOLEAN HTCEnable;
60037 +
60038 + /*****************************************************************************************/
60039 + /* Statistic related parameters */
60040 + /*****************************************************************************************/
60041 +
60042 + BOOLEAN bUpdateBcnCntDone;
60043 + ULONG watchDogMacDeadlock; // prevent MAC/BBP into deadlock condition
60044 + // ----------------------------
60045 + // DEBUG paramerts
60046 + // ----------------------------
60047 + BOOLEAN bBanAllBaSetup;
60048 + BOOLEAN bPromiscuous;
60049 +
60050 + // ----------------------------
60051 + // rt2860c emulation-use Parameters
60052 + // ----------------------------
60053 + ULONG rtsaccu[30];
60054 + ULONG ctsaccu[30];
60055 + ULONG cfendaccu[30];
60056 + ULONG bacontent[16];
60057 + ULONG rxint[RX_RING_SIZE+1];
60058 + UCHAR rcvba[60];
60059 + BOOLEAN bLinkAdapt;
60060 + BOOLEAN bForcePrintTX;
60061 + BOOLEAN bForcePrintRX;
60062 + BOOLEAN bDisablescanning; //defined in RT2870 USB
60063 + BOOLEAN bStaFifoTest;
60064 + BOOLEAN bProtectionTest;
60065 + BOOLEAN bHCCATest;
60066 + BOOLEAN bGenOneHCCA;
60067 + BOOLEAN bBroadComHT;
60068 + //+++Following add from RT2870 USB.
60069 + ULONG BulkOutReq;
60070 + ULONG BulkOutComplete;
60071 + ULONG BulkOutCompleteOther;
60072 + ULONG BulkOutCompleteCancel; // seems not use now?
60073 + ULONG BulkInReq;
60074 + ULONG BulkInComplete;
60075 + ULONG BulkInCompleteFail;
60076 + //---
60077 +
60078 + struct wificonf WIFItestbed;
60079 +
60080 +#ifdef RALINK_ATE
60081 + ATE_INFO ate;
60082 +#endif // RALINK_ATE //
60083 +
60084 +#ifdef DOT11_N_SUPPORT
60085 + struct reordering_mpdu_pool mpdu_blk_pool;
60086 +#endif // DOT11_N_SUPPORT //
60087 +
60088 + ULONG OneSecondnonBEpackets; // record non BE packets per second
60089 +
60090 +#if WIRELESS_EXT >= 12
60091 + struct iw_statistics iw_stats;
60092 +#endif
60093 +
60094 + struct net_device_stats stats;
60095 +
60096 +#ifdef BLOCK_NET_IF
60097 + BLOCK_QUEUE_ENTRY blockQueueTab[NUM_OF_TX_RING];
60098 +#endif // BLOCK_NET_IF //
60099 +
60100 +
60101 +
60102 +#ifdef MULTIPLE_CARD_SUPPORT
60103 + INT32 MC_RowID;
60104 + UCHAR MC_FileName[256];
60105 +#endif // MULTIPLE_CARD_SUPPORT //
60106 +
60107 + ULONG TbttTickCount;
60108 +#ifdef PCI_MSI_SUPPORT
60109 + BOOLEAN HaveMsi;
60110 +#endif // PCI_MSI_SUPPORT //
60111 +
60112 +
60113 + UCHAR is_on;
60114 +
60115 +#define TIME_BASE (1000000/OS_HZ)
60116 +#define TIME_ONE_SECOND (1000000/TIME_BASE)
60117 + UCHAR flg_be_adjust;
60118 + ULONG be_adjust_last_time;
60119 +
60120 +#ifdef NINTENDO_AP
60121 + NINDO_CTRL_BLOCK nindo_ctrl_block;
60122 +#endif // NINTENDO_AP //
60123 +
60124 +
60125 +#ifdef IKANOS_VX_1X0
60126 + struct IKANOS_TX_INFO IkanosTxInfo;
60127 + struct IKANOS_TX_INFO IkanosRxInfo[MAX_MBSSID_NUM + MAX_WDS_ENTRY + MAX_APCLI_NUM + MAX_MESH_NUM];
60128 +#endif // IKANOS_VX_1X0 //
60129 +
60130 +
60131 +#ifdef DBG_DIAGNOSE
60132 + RtmpDiagStruct DiagStruct;
60133 +#endif // DBG_DIAGNOSE //
60134 +
60135 +
60136 + UINT8 PM_FlgSuspend;
60137 +} RTMP_ADAPTER, *PRTMP_ADAPTER;
60138 +
60139 +//
60140 +// Cisco IAPP format
60141 +//
60142 +typedef struct _CISCO_IAPP_CONTENT_
60143 +{
60144 + USHORT Length; //IAPP Length
60145 + UCHAR MessageType; //IAPP type
60146 + UCHAR FunctionCode; //IAPP function type
60147 + UCHAR DestinaionMAC[MAC_ADDR_LEN];
60148 + UCHAR SourceMAC[MAC_ADDR_LEN];
60149 + USHORT Tag; //Tag(element IE) - Adjacent AP report
60150 + USHORT TagLength; //Length of element not including 4 byte header
60151 + UCHAR OUI[4]; //0x00, 0x40, 0x96, 0x00
60152 + UCHAR PreviousAP[MAC_ADDR_LEN]; //MAC Address of access point
60153 + USHORT Channel;
60154 + USHORT SsidLen;
60155 + UCHAR Ssid[MAX_LEN_OF_SSID];
60156 + USHORT Seconds; //Seconds that the client has been disassociated.
60157 +} CISCO_IAPP_CONTENT, *PCISCO_IAPP_CONTENT;
60158 +
60159 +#define DELAYINTMASK 0x0003fffb
60160 +#define INTMASK 0x0003fffb
60161 +#define IndMask 0x0003fffc
60162 +#define RxINT 0x00000005 // Delayed Rx or indivi rx
60163 +#define TxDataInt 0x000000fa // Delayed Tx or indivi tx
60164 +#define TxMgmtInt 0x00000102 // Delayed Tx or indivi tx
60165 +#define TxCoherent 0x00020000 // tx coherent
60166 +#define RxCoherent 0x00010000 // rx coherent
60167 +#define McuCommand 0x00000200 // mcu
60168 +#define PreTBTTInt 0x00001000 // Pre-TBTT interrupt
60169 +#define TBTTInt 0x00000800 // TBTT interrupt
60170 +#define GPTimeOutInt 0x00008000 // GPtimeout interrupt
60171 +#define AutoWakeupInt 0x00004000 // AutoWakeupInt interrupt
60172 +#define FifoStaFullInt 0x00002000 // fifo statistics full interrupt
60173 +
60174 +
60175 +typedef struct _RX_BLK_
60176 +{
60177 + RT28XX_RXD_STRUC RxD;
60178 + PRXWI_STRUC pRxWI;
60179 + PHEADER_802_11 pHeader;
60180 + PNDIS_PACKET pRxPacket;
60181 + UCHAR *pData;
60182 + USHORT DataSize;
60183 + USHORT Flags;
60184 + UCHAR UserPriority; // for calculate TKIP MIC using
60185 +} RX_BLK;
60186 +
60187 +
60188 +#define RX_BLK_SET_FLAG(_pRxBlk, _flag) (_pRxBlk->Flags |= _flag)
60189 +#define RX_BLK_TEST_FLAG(_pRxBlk, _flag) (_pRxBlk->Flags & _flag)
60190 +#define RX_BLK_CLEAR_FLAG(_pRxBlk, _flag) (_pRxBlk->Flags &= ~(_flag))
60191 +
60192 +
60193 +#define fRX_WDS 0x0001
60194 +#define fRX_AMSDU 0x0002
60195 +#define fRX_ARALINK 0x0004
60196 +#define fRX_HTC 0x0008
60197 +#define fRX_PAD 0x0010
60198 +#define fRX_AMPDU 0x0020
60199 +#define fRX_QOS 0x0040
60200 +#define fRX_INFRA 0x0080
60201 +#define fRX_EAP 0x0100
60202 +#define fRX_MESH 0x0200
60203 +#define fRX_APCLI 0x0400
60204 +#define fRX_DLS 0x0800
60205 +#define fRX_WPI 0x1000
60206 +
60207 +#define LENGTH_AMSDU_SUBFRAMEHEAD 14
60208 +#define LENGTH_ARALINK_SUBFRAMEHEAD 14
60209 +#define LENGTH_ARALINK_HEADER_FIELD 2
60210 +
60211 +#define TX_UNKOWN_FRAME 0x00
60212 +#define TX_MCAST_FRAME 0x01
60213 +#define TX_LEGACY_FRAME 0x02
60214 +#define TX_AMPDU_FRAME 0x04
60215 +#define TX_AMSDU_FRAME 0x08
60216 +#define TX_RALINK_FRAME 0x10
60217 +#define TX_FRAG_FRAME 0x20
60218 +
60219 +
60220 +// Currently the sizeof(TX_BLK) is 148 bytes.
60221 +typedef struct _TX_BLK_
60222 +{
60223 + UCHAR QueIdx;
60224 + UCHAR TxFrameType; // Indicate the Transmission type of the all frames in one batch
60225 + UCHAR TotalFrameNum; // Total frame number want to send-out in one batch
60226 + USHORT TotalFragNum; // Total frame fragments required in one batch
60227 + USHORT TotalFrameLen; // Total length of all frames want to send-out in one batch
60228 +
60229 + QUEUE_HEADER TxPacketList;
60230 + MAC_TABLE_ENTRY *pMacEntry; // NULL: packet with 802.11 RA field is multicast/broadcast address
60231 + HTTRANSMIT_SETTING *pTransmit;
60232 +
60233 + // Following structure used for the characteristics of a specific packet.
60234 + PNDIS_PACKET pPacket;
60235 + PUCHAR pSrcBufHeader; // Reference to the head of sk_buff->data
60236 + PUCHAR pSrcBufData; // Reference to the sk_buff->data, will changed depends on hanlding progresss
60237 + UINT SrcBufLen; // Length of packet payload which not including Layer 2 header
60238 + PUCHAR pExtraLlcSnapEncap; // NULL means no extra LLC/SNAP is required
60239 + UCHAR HeaderBuf[80]; // TempBuffer for TX_INFO + TX_WI + 802.11 Header + padding + AMSDU SubHeader + LLC/SNAP
60240 + UCHAR MpduHeaderLen; // 802.11 header length NOT including the padding
60241 + UCHAR HdrPadLen; // recording Header Padding Length;
60242 + UCHAR apidx; // The interface associated to this packet
60243 + UCHAR Wcid; // The MAC entry associated to this packet
60244 + UCHAR UserPriority; // priority class of packet
60245 + UCHAR FrameGap; // what kind of IFS this packet use
60246 + UCHAR MpduReqNum; // number of fragments of this frame
60247 + UCHAR TxRate; // TODO: Obsoleted? Should change to MCS?
60248 + UCHAR CipherAlg; // cipher alogrithm
60249 + PCIPHER_KEY pKey;
60250 +
60251 +
60252 +
60253 + USHORT Flags; //See following definitions for detail.
60254 +
60255 + //YOU SHOULD NOT TOUCH IT! Following parameters are used for hardware-depended layer.
60256 + ULONG Priv; // Hardware specific value saved in here.
60257 +} TX_BLK, *PTX_BLK;
60258 +
60259 +
60260 +#define fTX_bRtsRequired 0x0001 // Indicate if need send RTS frame for protection. Not used in RT2860/RT2870.
60261 +#define fTX_bAckRequired 0x0002 // the packet need ack response
60262 +#define fTX_bPiggyBack 0x0004 // Legacy device use Piggback or not
60263 +#define fTX_bHTRate 0x0008 // allow to use HT rate
60264 +#define fTX_bForceNonQoS 0x0010 // force to transmit frame without WMM-QoS in HT mode
60265 +#define fTX_bAllowFrag 0x0020 // allow to fragment the packet, A-MPDU, A-MSDU, A-Ralink is not allowed to fragment
60266 +#define fTX_bMoreData 0x0040 // there are more data packets in PowerSave Queue
60267 +#define fTX_bWMM 0x0080 // QOS Data
60268 +
60269 +#define fTX_bClearEAPFrame 0x0100
60270 +
60271 +#define TX_BLK_ASSIGN_FLAG(_pTxBlk, _flag, value) \
60272 + do { \
60273 + if (value) \
60274 + (_pTxBlk->Flags |= _flag) \
60275 + else \
60276 + (_pTxBlk->Flags &= ~(_flag)) \
60277 + }while(0)
60278 +
60279 +#define TX_BLK_SET_FLAG(_pTxBlk, _flag) (_pTxBlk->Flags |= _flag)
60280 +#define TX_BLK_TEST_FLAG(_pTxBlk, _flag) (((_pTxBlk->Flags & _flag) == _flag) ? 1 : 0)
60281 +#define TX_BLK_CLEAR_FLAG(_pTxBlk, _flag) (_pTxBlk->Flags &= ~(_flag))
60282 +
60283 +
60284 +
60285 +
60286 +
60287 +//------------------------------------------------------------------------------------------
60288 +
60289 +
60290 +#ifdef RT2860
60291 +//
60292 +// Enable & Disable NIC interrupt via writing interrupt mask register
60293 +// Since it use ADAPTER structure, it have to be put after structure definition.
60294 +//
60295 +__inline VOID NICDisableInterrupt(
60296 + IN PRTMP_ADAPTER pAd)
60297 +{
60298 + RTMP_IO_WRITE32(pAd, INT_MASK_CSR, 0x0); // 0: disable
60299 + //RTMP_IO_WRITE32(pAd, PBF_INT_ENA, 0x0); // 0x418 is for firmware . SW doesn't handle here.
60300 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE);
60301 +}
60302 +
60303 +__inline VOID NICEnableInterrupt(
60304 + IN PRTMP_ADAPTER pAd)
60305 +{
60306 + //
60307 + // Flag "fOP_STATUS_DOZE" On, means ASIC put to sleep, else means ASIC WakeUp
60308 + // To prevent System hang, we should enalbe the interrupt when
60309 + // ASIC is already Wake Up.
60310 + //
60311 + // RT2661 => when ASIC is sleeping, MAC register cannot be read and written.
60312 + // RT2860 => when ASIC is sleeping, MAC register can be read and written.
60313 + //if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
60314 + {
60315 + RTMP_IO_WRITE32(pAd, INT_MASK_CSR, pAd->int_enable_reg /*DELAYINTMASK*/); // 1:enable
60316 + }
60317 + //else
60318 + // DBGPRINT(RT_DEBUG_TRACE, ("fOP_STATUS_DOZE !\n"));
60319 +
60320 + //RTMP_IO_WRITE32(pAd, PBF_INT_ENA, 0x00000030); // 1 : enable
60321 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_ACTIVE);
60322 +}
60323 +#endif // RT2860 //
60324 +
60325 +#ifdef RT_BIG_ENDIAN
60326 +static inline VOID WriteBackToDescriptor(
60327 + IN PUCHAR Dest,
60328 + IN PUCHAR Src,
60329 + IN BOOLEAN DoEncrypt,
60330 + IN ULONG DescriptorType)
60331 +{
60332 + UINT32 *p1, *p2;
60333 +
60334 + p1 = ((UINT32 *)Dest);
60335 + p2 = ((UINT32 *)Src);
60336 +
60337 + *p1 = *p2;
60338 + *(p1+2) = *(p2+2);
60339 + *(p1+3) = *(p2+3);
60340 + *(p1+1) = *(p2+1); // Word 1; this must be written back last
60341 +}
60342 +
60343 +/*
60344 + ========================================================================
60345 +
60346 + Routine Description:
60347 + Endian conversion of Tx/Rx descriptor .
60348 +
60349 + Arguments:
60350 + pAd Pointer to our adapter
60351 + pData Pointer to Tx/Rx descriptor
60352 + DescriptorType Direction of the frame
60353 +
60354 + Return Value:
60355 + None
60356 +
60357 + Note:
60358 + Call this function when read or update descriptor
60359 + ========================================================================
60360 +*/
60361 +static inline VOID RTMPWIEndianChange(
60362 + IN PUCHAR pData,
60363 + IN ULONG DescriptorType)
60364 +{
60365 + int size;
60366 + int i;
60367 +
60368 + size = ((DescriptorType == TYPE_TXWI) ? TXWI_SIZE : RXWI_SIZE);
60369 +
60370 + if(DescriptorType == TYPE_TXWI)
60371 + {
60372 + *((UINT32 *)(pData)) = SWAP32(*((UINT32 *)(pData))); // Byte 0~3
60373 + *((UINT32 *)(pData + 4)) = SWAP32(*((UINT32 *)(pData+4))); // Byte 4~7
60374 + }
60375 + else
60376 + {
60377 + for(i=0; i < size/4 ; i++)
60378 + *(((UINT32 *)pData) +i) = SWAP32(*(((UINT32 *)pData)+i));
60379 + }
60380 +}
60381 +
60382 +/*
60383 + ========================================================================
60384 +
60385 + Routine Description:
60386 + Endian conversion of Tx/Rx descriptor .
60387 +
60388 + Arguments:
60389 + pAd Pointer to our adapter
60390 + pData Pointer to Tx/Rx descriptor
60391 + DescriptorType Direction of the frame
60392 +
60393 + Return Value:
60394 + None
60395 +
60396 + Note:
60397 + Call this function when read or update descriptor
60398 + ========================================================================
60399 +*/
60400 +#ifdef RT2860
60401 +static inline VOID RTMPDescriptorEndianChange(
60402 + IN PUCHAR pData,
60403 + IN ULONG DescriptorType)
60404 +{
60405 + *((UINT32 *)(pData)) = SWAP32(*((UINT32 *)(pData))); // Byte 0~3
60406 + *((UINT32 *)(pData + 8)) = SWAP32(*((UINT32 *)(pData+8))); // Byte 8~11
60407 + *((UINT32 *)(pData +12)) = SWAP32(*((UINT32 *)(pData + 12))); // Byte 12~15
60408 + *((UINT32 *)(pData + 4)) = SWAP32(*((UINT32 *)(pData + 4))); // Byte 4~7, this must be swapped last
60409 +}
60410 +#endif // RT2860 //
60411 +
60412 +/*
60413 + ========================================================================
60414 +
60415 + Routine Description:
60416 + Endian conversion of all kinds of 802.11 frames .
60417 +
60418 + Arguments:
60419 + pAd Pointer to our adapter
60420 + pData Pointer to the 802.11 frame structure
60421 + Dir Direction of the frame
60422 + FromRxDoneInt Caller is from RxDone interrupt
60423 +
60424 + Return Value:
60425 + None
60426 +
60427 + Note:
60428 + Call this function when read or update buffer data
60429 + ========================================================================
60430 +*/
60431 +static inline VOID RTMPFrameEndianChange(
60432 + IN PRTMP_ADAPTER pAd,
60433 + IN PUCHAR pData,
60434 + IN ULONG Dir,
60435 + IN BOOLEAN FromRxDoneInt)
60436 +{
60437 + PHEADER_802_11 pFrame;
60438 + PUCHAR pMacHdr;
60439 +
60440 + // swab 16 bit fields - Frame Control field
60441 + if(Dir == DIR_READ)
60442 + {
60443 + *(USHORT *)pData = SWAP16(*(USHORT *)pData);
60444 + }
60445 +
60446 + pFrame = (PHEADER_802_11) pData;
60447 + pMacHdr = (PUCHAR) pFrame;
60448 +
60449 + // swab 16 bit fields - Duration/ID field
60450 + *(USHORT *)(pMacHdr + 2) = SWAP16(*(USHORT *)(pMacHdr + 2));
60451 +
60452 + // swab 16 bit fields - Sequence Control field
60453 + *(USHORT *)(pMacHdr + 22) = SWAP16(*(USHORT *)(pMacHdr + 22));
60454 +
60455 + if(pFrame->FC.Type == BTYPE_MGMT)
60456 + {
60457 + switch(pFrame->FC.SubType)
60458 + {
60459 + case SUBTYPE_ASSOC_REQ:
60460 + case SUBTYPE_REASSOC_REQ:
60461 + // swab 16 bit fields - CapabilityInfo field
60462 + pMacHdr += sizeof(HEADER_802_11);
60463 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60464 +
60465 + // swab 16 bit fields - Listen Interval field
60466 + pMacHdr += 2;
60467 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60468 + break;
60469 +
60470 + case SUBTYPE_ASSOC_RSP:
60471 + case SUBTYPE_REASSOC_RSP:
60472 + // swab 16 bit fields - CapabilityInfo field
60473 + pMacHdr += sizeof(HEADER_802_11);
60474 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60475 +
60476 + // swab 16 bit fields - Status Code field
60477 + pMacHdr += 2;
60478 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60479 +
60480 + // swab 16 bit fields - AID field
60481 + pMacHdr += 2;
60482 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60483 + break;
60484 +
60485 + case SUBTYPE_AUTH:
60486 + // If from APHandleRxDoneInterrupt routine, it is still a encrypt format.
60487 + // The convertion is delayed to RTMPHandleDecryptionDoneInterrupt.
60488 + if(!FromRxDoneInt && pFrame->FC.Wep == 1)
60489 + break;
60490 + else
60491 + {
60492 + // swab 16 bit fields - Auth Alg No. field
60493 + pMacHdr += sizeof(HEADER_802_11);
60494 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60495 +
60496 + // swab 16 bit fields - Auth Seq No. field
60497 + pMacHdr += 2;
60498 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60499 +
60500 + // swab 16 bit fields - Status Code field
60501 + pMacHdr += 2;
60502 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60503 + }
60504 + break;
60505 +
60506 + case SUBTYPE_BEACON:
60507 + case SUBTYPE_PROBE_RSP:
60508 + // swab 16 bit fields - BeaconInterval field
60509 + pMacHdr += (sizeof(HEADER_802_11) + TIMESTAMP_LEN);
60510 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60511 +
60512 + // swab 16 bit fields - CapabilityInfo field
60513 + pMacHdr += sizeof(USHORT);
60514 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60515 + break;
60516 +
60517 + case SUBTYPE_DEAUTH:
60518 + case SUBTYPE_DISASSOC:
60519 + // swab 16 bit fields - Reason code field
60520 + pMacHdr += sizeof(HEADER_802_11);
60521 + *(USHORT *)pMacHdr = SWAP16(*(USHORT *)pMacHdr);
60522 + break;
60523 + }
60524 + }
60525 + else if( pFrame->FC.Type == BTYPE_DATA )
60526 + {
60527 + }
60528 + else if(pFrame->FC.Type == BTYPE_CNTL)
60529 + {
60530 + switch(pFrame->FC.SubType)
60531 + {
60532 + case SUBTYPE_BLOCK_ACK_REQ:
60533 + {
60534 + PFRAME_BA_REQ pBAReq = (PFRAME_BA_REQ)pFrame;
60535 + *(USHORT *)(&pBAReq->BARControl) = SWAP16(*(USHORT *)(&pBAReq->BARControl));
60536 + pBAReq->BAStartingSeq.word = SWAP16(pBAReq->BAStartingSeq.word);
60537 + }
60538 + break;
60539 + case SUBTYPE_BLOCK_ACK:
60540 + // For Block Ack packet, the HT_CONTROL field is in the same offset with Addr3
60541 + *(UINT32 *)(&pFrame->Addr3[0]) = SWAP32(*(UINT32 *)(&pFrame->Addr3[0]));
60542 + break;
60543 +
60544 + case SUBTYPE_ACK:
60545 + //For ACK packet, the HT_CONTROL field is in the same offset with Addr2
60546 + *(UINT32 *)(&pFrame->Addr2[0])= SWAP32(*(UINT32 *)(&pFrame->Addr2[0]));
60547 + break;
60548 + }
60549 + }
60550 + else
60551 + {
60552 + DBGPRINT(RT_DEBUG_ERROR,("Invalid Frame Type!!!\n"));
60553 + }
60554 +
60555 + // swab 16 bit fields - Frame Control
60556 + if(Dir == DIR_WRITE)
60557 + {
60558 + *(USHORT *)pData = SWAP16(*(USHORT *)pData);
60559 + }
60560 +}
60561 +#endif // RT_BIG_ENDIAN //
60562 +
60563 +
60564 +static inline VOID ConvertMulticastIP2MAC(
60565 + IN PUCHAR pIpAddr,
60566 + IN PUCHAR *ppMacAddr,
60567 + IN UINT16 ProtoType)
60568 +{
60569 + if (pIpAddr == NULL)
60570 + return;
60571 +
60572 + if (ppMacAddr == NULL || *ppMacAddr == NULL)
60573 + return;
60574 +
60575 + switch (ProtoType)
60576 + {
60577 + case ETH_P_IPV6:
60578 +// memset(*ppMacAddr, 0, ETH_LENGTH_OF_ADDRESS);
60579 + *(*ppMacAddr) = 0x33;
60580 + *(*ppMacAddr + 1) = 0x33;
60581 + *(*ppMacAddr + 2) = pIpAddr[12];
60582 + *(*ppMacAddr + 3) = pIpAddr[13];
60583 + *(*ppMacAddr + 4) = pIpAddr[14];
60584 + *(*ppMacAddr + 5) = pIpAddr[15];
60585 + break;
60586 +
60587 + case ETH_P_IP:
60588 + default:
60589 +// memset(*ppMacAddr, 0, ETH_LENGTH_OF_ADDRESS);
60590 + *(*ppMacAddr) = 0x01;
60591 + *(*ppMacAddr + 1) = 0x00;
60592 + *(*ppMacAddr + 2) = 0x5e;
60593 + *(*ppMacAddr + 3) = pIpAddr[1] & 0x7f;
60594 + *(*ppMacAddr + 4) = pIpAddr[2];
60595 + *(*ppMacAddr + 5) = pIpAddr[3];
60596 + break;
60597 + }
60598 +
60599 + return;
60600 +}
60601 +
60602 +BOOLEAN RTMPCheckForHang(
60603 + IN NDIS_HANDLE MiniportAdapterContext
60604 + );
60605 +
60606 +VOID RTMPHalt(
60607 + IN NDIS_HANDLE MiniportAdapterContext
60608 + );
60609 +
60610 +//
60611 +// Private routines in rtmp_init.c
60612 +//
60613 +NDIS_STATUS RTMPAllocAdapterBlock(
60614 + IN PVOID handle,
60615 + OUT PRTMP_ADAPTER *ppAdapter
60616 + );
60617 +
60618 +NDIS_STATUS RTMPAllocTxRxRingMemory(
60619 + IN PRTMP_ADAPTER pAd
60620 + );
60621 +
60622 +NDIS_STATUS RTMPFindAdapter(
60623 + IN PRTMP_ADAPTER pAd,
60624 + IN NDIS_HANDLE WrapperConfigurationContext
60625 + );
60626 +
60627 +NDIS_STATUS RTMPReadParametersHook(
60628 + IN PRTMP_ADAPTER pAd
60629 + );
60630 +
60631 +VOID RTMPFreeAdapter(
60632 + IN PRTMP_ADAPTER pAd
60633 + );
60634 +
60635 +NDIS_STATUS NICReadRegParameters(
60636 + IN PRTMP_ADAPTER pAd,
60637 + IN NDIS_HANDLE WrapperConfigurationContext
60638 + );
60639 +
60640 +
60641 +VOID NICReadEEPROMParameters(
60642 + IN PRTMP_ADAPTER pAd,
60643 + IN PUCHAR mac_addr);
60644 +
60645 +VOID NICInitAsicFromEEPROM(
60646 + IN PRTMP_ADAPTER pAd);
60647 +
60648 +VOID NICInitTxRxRingAndBacklogQueue(
60649 + IN PRTMP_ADAPTER pAd);
60650 +
60651 +NDIS_STATUS NICInitializeAdapter(
60652 + IN PRTMP_ADAPTER pAd,
60653 + IN BOOLEAN bHardReset);
60654 +
60655 +NDIS_STATUS NICInitializeAsic(
60656 + IN PRTMP_ADAPTER pAd,
60657 + IN BOOLEAN bHardReset);
60658 +
60659 +VOID NICIssueReset(
60660 + IN PRTMP_ADAPTER pAd);
60661 +
60662 +VOID RTMPRingCleanUp(
60663 + IN PRTMP_ADAPTER pAd,
60664 + IN UCHAR RingType);
60665 +
60666 +VOID RxTest(
60667 + IN PRTMP_ADAPTER pAd);
60668 +
60669 +NDIS_STATUS DbgSendPacket(
60670 + IN PRTMP_ADAPTER pAd,
60671 + IN PNDIS_PACKET pPacket);
60672 +
60673 +VOID UserCfgInit(
60674 + IN PRTMP_ADAPTER pAd);
60675 +
60676 +VOID NICResetFromError(
60677 + IN PRTMP_ADAPTER pAd);
60678 +
60679 +VOID NICEraseFirmware(
60680 + IN PRTMP_ADAPTER pAd);
60681 +
60682 +NDIS_STATUS NICLoadFirmware(
60683 + IN PRTMP_ADAPTER pAd);
60684 +
60685 +NDIS_STATUS NICLoadRateSwitchingParams(
60686 + IN PRTMP_ADAPTER pAd);
60687 +
60688 +BOOLEAN NICCheckForHang(
60689 + IN PRTMP_ADAPTER pAd);
60690 +
60691 +VOID NICUpdateFifoStaCounters(
60692 + IN PRTMP_ADAPTER pAd);
60693 +
60694 +VOID NICUpdateRawCounters(
60695 + IN PRTMP_ADAPTER pAd);
60696 +
60697 +ULONG RTMPNotAllZero(
60698 + IN PVOID pSrc1,
60699 + IN ULONG Length);
60700 +
60701 +VOID RTMPZeroMemory(
60702 + IN PVOID pSrc,
60703 + IN ULONG Length);
60704 +
60705 +ULONG RTMPCompareMemory(
60706 + IN PVOID pSrc1,
60707 + IN PVOID pSrc2,
60708 + IN ULONG Length);
60709 +
60710 +VOID RTMPMoveMemory(
60711 + OUT PVOID pDest,
60712 + IN PVOID pSrc,
60713 + IN ULONG Length);
60714 +
60715 +VOID AtoH(
60716 + char *src,
60717 + UCHAR *dest,
60718 + int destlen);
60719 +
60720 +UCHAR BtoH(
60721 + char ch);
60722 +
60723 +VOID RTMPPatchMacBbpBug(
60724 + IN PRTMP_ADAPTER pAd);
60725 +
60726 +VOID RTMPPatchCardBus(
60727 + IN PRTMP_ADAPTER pAdapter);
60728 +
60729 +VOID RTMPPatchRalinkCardBus(
60730 + IN PRTMP_ADAPTER pAdapter,
60731 + IN ULONG Bus);
60732 +
60733 +ULONG RTMPReadCBConfig(
60734 + IN ULONG Bus,
60735 + IN ULONG Slot,
60736 + IN ULONG Func,
60737 + IN ULONG Offset);
60738 +
60739 +VOID RTMPWriteCBConfig(
60740 + IN ULONG Bus,
60741 + IN ULONG Slot,
60742 + IN ULONG Func,
60743 + IN ULONG Offset,
60744 + IN ULONG Value);
60745 +
60746 +VOID RTMPInitTimer(
60747 + IN PRTMP_ADAPTER pAd,
60748 + IN PRALINK_TIMER_STRUCT pTimer,
60749 + IN PVOID pTimerFunc,
60750 + IN PVOID pData,
60751 + IN BOOLEAN Repeat);
60752 +
60753 +VOID RTMPSetTimer(
60754 + IN PRALINK_TIMER_STRUCT pTimer,
60755 + IN ULONG Value);
60756 +
60757 +
60758 +VOID RTMPModTimer(
60759 + IN PRALINK_TIMER_STRUCT pTimer,
60760 + IN ULONG Value);
60761 +
60762 +VOID RTMPCancelTimer(
60763 + IN PRALINK_TIMER_STRUCT pTimer,
60764 + OUT BOOLEAN *pCancelled);
60765 +
60766 +VOID RTMPSetLED(
60767 + IN PRTMP_ADAPTER pAd,
60768 + IN UCHAR Status);
60769 +
60770 +VOID RTMPSetSignalLED(
60771 + IN PRTMP_ADAPTER pAd,
60772 + IN NDIS_802_11_RSSI Dbm);
60773 +
60774 +VOID RTMPEnableRxTx(
60775 + IN PRTMP_ADAPTER pAd);
60776 +
60777 +//
60778 +// prototype in action.c
60779 +//
60780 +VOID ActionStateMachineInit(
60781 + IN PRTMP_ADAPTER pAd,
60782 + IN STATE_MACHINE *S,
60783 + OUT STATE_MACHINE_FUNC Trans[]);
60784 +
60785 +VOID MlmeADDBAAction(
60786 + IN PRTMP_ADAPTER pAd,
60787 + IN MLME_QUEUE_ELEM *Elem);
60788 +
60789 +VOID MlmeDELBAAction(
60790 + IN PRTMP_ADAPTER pAd,
60791 + IN MLME_QUEUE_ELEM *Elem);
60792 +
60793 +VOID MlmeDLSAction(
60794 + IN PRTMP_ADAPTER pAd,
60795 + IN MLME_QUEUE_ELEM *Elem);
60796 +
60797 +VOID MlmeInvalidAction(
60798 + IN PRTMP_ADAPTER pAd,
60799 + IN MLME_QUEUE_ELEM *Elem);
60800 +
60801 +VOID MlmeQOSAction(
60802 + IN PRTMP_ADAPTER pAd,
60803 + IN MLME_QUEUE_ELEM *Elem);
60804 +
60805 +#ifdef DOT11_N_SUPPORT
60806 +VOID PeerAddBAReqAction(
60807 + IN PRTMP_ADAPTER pAd,
60808 + IN MLME_QUEUE_ELEM *Elem);
60809 +
60810 +VOID PeerAddBARspAction(
60811 + IN PRTMP_ADAPTER pAd,
60812 + IN MLME_QUEUE_ELEM *Elem);
60813 +
60814 +VOID PeerDelBAAction(
60815 + IN PRTMP_ADAPTER pAd,
60816 + IN MLME_QUEUE_ELEM *Elem);
60817 +
60818 +VOID PeerBAAction(
60819 + IN PRTMP_ADAPTER pAd,
60820 + IN MLME_QUEUE_ELEM *Elem);
60821 +#endif // DOT11_N_SUPPORT //
60822 +
60823 +VOID SendPSMPAction(
60824 + IN PRTMP_ADAPTER pAd,
60825 + IN UCHAR Wcid,
60826 + IN UCHAR Psmp);
60827 +
60828 +
60829 +#ifdef DOT11N_DRAFT3
60830 +VOID SendBSS2040CoexistMgmtAction(
60831 + IN PRTMP_ADAPTER pAd,
60832 + IN UCHAR Wcid,
60833 + IN UCHAR apidx,
60834 + IN UCHAR InfoReq);
60835 +
60836 +VOID SendNotifyBWActionFrame(
60837 + IN PRTMP_ADAPTER pAd,
60838 + IN UCHAR Wcid,
60839 + IN UCHAR apidx);
60840 +
60841 +BOOLEAN ChannelSwitchSanityCheck(
60842 + IN PRTMP_ADAPTER pAd,
60843 + IN UCHAR Wcid,
60844 + IN UCHAR NewChannel,
60845 + IN UCHAR Secondary);
60846 +
60847 +VOID ChannelSwitchAction(
60848 + IN PRTMP_ADAPTER pAd,
60849 + IN UCHAR Wcid,
60850 + IN UCHAR Channel,
60851 + IN UCHAR Secondary);
60852 +
60853 +ULONG BuildIntolerantChannelRep(
60854 + IN PRTMP_ADAPTER pAd,
60855 + IN PUCHAR pDest);
60856 +
60857 +VOID Update2040CoexistFrameAndNotify(
60858 + IN PRTMP_ADAPTER pAd,
60859 + IN UCHAR Wcid,
60860 + IN BOOLEAN bAddIntolerantCha);
60861 +
60862 +VOID Send2040CoexistAction(
60863 + IN PRTMP_ADAPTER pAd,
60864 + IN UCHAR Wcid,
60865 + IN BOOLEAN bAddIntolerantCha);
60866 +#endif // DOT11N_DRAFT3 //
60867 +
60868 +VOID PeerRMAction(
60869 + IN PRTMP_ADAPTER pAd,
60870 + IN MLME_QUEUE_ELEM *Elem);
60871 +
60872 +VOID PeerPublicAction(
60873 + IN PRTMP_ADAPTER pAd,
60874 + IN MLME_QUEUE_ELEM *Elem);
60875 +
60876 +#ifdef CONFIG_STA_SUPPORT
60877 +VOID StaPublicAction(
60878 + IN PRTMP_ADAPTER pAd,
60879 + IN UCHAR Bss2040Coexist);
60880 +#endif // CONFIG_STA_SUPPORT //
60881 +
60882 +
60883 +VOID PeerBSSTranAction(
60884 + IN PRTMP_ADAPTER pAd,
60885 + IN MLME_QUEUE_ELEM *Elem);
60886 +
60887 +#ifdef DOT11_N_SUPPORT
60888 +VOID PeerHTAction(
60889 + IN PRTMP_ADAPTER pAd,
60890 + IN MLME_QUEUE_ELEM *Elem);
60891 +#endif // DOT11_N_SUPPORT //
60892 +
60893 +VOID PeerQOSAction(
60894 + IN PRTMP_ADAPTER pAd,
60895 + IN MLME_QUEUE_ELEM *Elem);
60896 +
60897 +#ifdef QOS_DLS_SUPPORT
60898 +VOID PeerDLSAction(
60899 + IN PRTMP_ADAPTER pAd,
60900 + IN MLME_QUEUE_ELEM *Elem);
60901 +#endif // QOS_DLS_SUPPORT //
60902 +
60903 +#ifdef CONFIG_STA_SUPPORT
60904 +#ifdef QOS_DLS_SUPPORT
60905 +VOID DlsParmFill(
60906 + IN PRTMP_ADAPTER pAd,
60907 + IN OUT MLME_DLS_REQ_STRUCT *pDlsReq,
60908 + IN PRT_802_11_DLS pDls,
60909 + IN USHORT reason);
60910 +#endif // QOS_DLS_SUPPORT //
60911 +#endif // CONFIG_STA_SUPPORT //
60912 +
60913 +#ifdef DOT11_N_SUPPORT
60914 +VOID RECBATimerTimeout(
60915 + IN PVOID SystemSpecific1,
60916 + IN PVOID FunctionContext,
60917 + IN PVOID SystemSpecific2,
60918 + IN PVOID SystemSpecific3);
60919 +
60920 +VOID ORIBATimerTimeout(
60921 + IN PRTMP_ADAPTER pAd);
60922 +
60923 +VOID SendRefreshBAR(
60924 + IN PRTMP_ADAPTER pAd,
60925 + IN MAC_TABLE_ENTRY *pEntry);
60926 +#endif // DOT11_N_SUPPORT //
60927 +
60928 +VOID ActHeaderInit(
60929 + IN PRTMP_ADAPTER pAd,
60930 + IN OUT PHEADER_802_11 pHdr80211,
60931 + IN PUCHAR Addr1,
60932 + IN PUCHAR Addr2,
60933 + IN PUCHAR Addr3);
60934 +
60935 +VOID BarHeaderInit(
60936 + IN PRTMP_ADAPTER pAd,
60937 + IN OUT PFRAME_BAR pCntlBar,
60938 + IN PUCHAR pDA,
60939 + IN PUCHAR pSA);
60940 +
60941 +VOID InsertActField(
60942 + IN PRTMP_ADAPTER pAd,
60943 + OUT PUCHAR pFrameBuf,
60944 + OUT PULONG pFrameLen,
60945 + IN UINT8 Category,
60946 + IN UINT8 ActCode);
60947 +
60948 +BOOLEAN QosBADataParse(
60949 + IN PRTMP_ADAPTER pAd,
60950 + IN BOOLEAN bAMSDU,
60951 + IN PUCHAR p8023Header,
60952 + IN UCHAR WCID,
60953 + IN UCHAR TID,
60954 + IN USHORT Sequence,
60955 + IN UCHAR DataOffset,
60956 + IN USHORT Datasize,
60957 + IN UINT CurRxIndex);
60958 +
60959 +#ifdef DOT11_N_SUPPORT
60960 +BOOLEAN CntlEnqueueForRecv(
60961 + IN PRTMP_ADAPTER pAd,
60962 + IN ULONG Wcid,
60963 + IN ULONG MsgLen,
60964 + IN PFRAME_BA_REQ pMsg);
60965 +
60966 +VOID BaAutoManSwitch(
60967 + IN PRTMP_ADAPTER pAd);
60968 +#endif // DOT11_N_SUPPORT //
60969 +
60970 +VOID HTIOTCheck(
60971 + IN PRTMP_ADAPTER pAd,
60972 + IN UCHAR BatRecIdx);
60973 +
60974 +//
60975 +// Private routines in rtmp_data.c
60976 +//
60977 +BOOLEAN RTMPHandleRxDoneInterrupt(
60978 + IN PRTMP_ADAPTER pAd);
60979 +
60980 +VOID RTMPHandleTxDoneInterrupt(
60981 + IN PRTMP_ADAPTER pAd);
60982 +
60983 +BOOLEAN RTMPHandleTxRingDmaDoneInterrupt(
60984 + IN PRTMP_ADAPTER pAd,
60985 + IN INT_SOURCE_CSR_STRUC TxRingBitmap);
60986 +
60987 +VOID RTMPHandleMgmtRingDmaDoneInterrupt(
60988 + IN PRTMP_ADAPTER pAd);
60989 +
60990 +VOID RTMPHandleTBTTInterrupt(
60991 + IN PRTMP_ADAPTER pAd);
60992 +
60993 +VOID RTMPHandlePreTBTTInterrupt(
60994 + IN PRTMP_ADAPTER pAd);
60995 +
60996 +void RTMPHandleTwakeupInterrupt(
60997 + IN PRTMP_ADAPTER pAd);
60998 +
60999 +VOID RTMPHandleRxCoherentInterrupt(
61000 + IN PRTMP_ADAPTER pAd);
61001 +
61002 +BOOLEAN TxFrameIsAggregatible(
61003 + IN PRTMP_ADAPTER pAd,
61004 + IN PUCHAR pPrevAddr1,
61005 + IN PUCHAR p8023hdr);
61006 +
61007 +BOOLEAN PeerIsAggreOn(
61008 + IN PRTMP_ADAPTER pAd,
61009 + IN ULONG TxRate,
61010 + IN PMAC_TABLE_ENTRY pMacEntry);
61011 +
61012 +NDIS_STATUS Sniff2BytesFromNdisBuffer(
61013 + IN PNDIS_BUFFER pFirstBuffer,
61014 + IN UCHAR DesiredOffset,
61015 + OUT PUCHAR pByte0,
61016 + OUT PUCHAR pByte1);
61017 +
61018 +NDIS_STATUS STASendPacket(
61019 + IN PRTMP_ADAPTER pAd,
61020 + IN PNDIS_PACKET pPacket);
61021 +
61022 +VOID STASendPackets(
61023 + IN NDIS_HANDLE MiniportAdapterContext,
61024 + IN PPNDIS_PACKET ppPacketArray,
61025 + IN UINT NumberOfPackets);
61026 +
61027 +VOID RTMPDeQueuePacket(
61028 + IN PRTMP_ADAPTER pAd,
61029 + IN BOOLEAN bIntContext,
61030 + IN UCHAR QueIdx,
61031 + IN UCHAR Max_Tx_Packets);
61032 +
61033 +NDIS_STATUS RTMPHardTransmit(
61034 + IN PRTMP_ADAPTER pAd,
61035 + IN PNDIS_PACKET pPacket,
61036 + IN UCHAR QueIdx,
61037 + OUT PULONG pFreeTXDLeft);
61038 +
61039 +NDIS_STATUS STAHardTransmit(
61040 + IN PRTMP_ADAPTER pAd,
61041 + IN TX_BLK *pTxBlk,
61042 + IN UCHAR QueIdx);
61043 +
61044 +VOID STARxEAPOLFrameIndicate(
61045 + IN PRTMP_ADAPTER pAd,
61046 + IN MAC_TABLE_ENTRY *pEntry,
61047 + IN RX_BLK *pRxBlk,
61048 + IN UCHAR FromWhichBSSID);
61049 +
61050 +NDIS_STATUS RTMPFreeTXDRequest(
61051 + IN PRTMP_ADAPTER pAd,
61052 + IN UCHAR RingType,
61053 + IN UCHAR NumberRequired,
61054 + IN PUCHAR FreeNumberIs);
61055 +
61056 +NDIS_STATUS MlmeHardTransmit(
61057 + IN PRTMP_ADAPTER pAd,
61058 + IN UCHAR QueIdx,
61059 + IN PNDIS_PACKET pPacket);
61060 +
61061 +NDIS_STATUS MlmeHardTransmitMgmtRing(
61062 + IN PRTMP_ADAPTER pAd,
61063 + IN UCHAR QueIdx,
61064 + IN PNDIS_PACKET pPacket);
61065 +
61066 +NDIS_STATUS MlmeHardTransmitTxRing(
61067 + IN PRTMP_ADAPTER pAd,
61068 + IN UCHAR QueIdx,
61069 + IN PNDIS_PACKET pPacket);
61070 +
61071 +USHORT RTMPCalcDuration(
61072 + IN PRTMP_ADAPTER pAd,
61073 + IN UCHAR Rate,
61074 + IN ULONG Size);
61075 +
61076 +VOID RTMPWriteTxWI(
61077 + IN PRTMP_ADAPTER pAd,
61078 + IN PTXWI_STRUC pTxWI,
61079 + IN BOOLEAN FRAG,
61080 + IN BOOLEAN CFACK,
61081 + IN BOOLEAN InsTimestamp,
61082 + IN BOOLEAN AMPDU,
61083 + IN BOOLEAN Ack,
61084 + IN BOOLEAN NSeq, // HW new a sequence.
61085 + IN UCHAR BASize,
61086 + IN UCHAR WCID,
61087 + IN ULONG Length,
61088 + IN UCHAR PID,
61089 + IN UCHAR TID,
61090 + IN UCHAR TxRate,
61091 + IN UCHAR Txopmode,
61092 + IN BOOLEAN CfAck,
61093 + IN HTTRANSMIT_SETTING *pTransmit);
61094 +
61095 +
61096 +VOID RTMPWriteTxWI_Data(
61097 + IN PRTMP_ADAPTER pAd,
61098 + IN OUT PTXWI_STRUC pTxWI,
61099 + IN TX_BLK *pTxBlk);
61100 +
61101 +
61102 +VOID RTMPWriteTxWI_Cache(
61103 + IN PRTMP_ADAPTER pAd,
61104 + IN OUT PTXWI_STRUC pTxWI,
61105 + IN TX_BLK *pTxBlk);
61106 +
61107 +VOID RTMPWriteTxDescriptor(
61108 + IN PRTMP_ADAPTER pAd,
61109 + IN PTXD_STRUC pTxD,
61110 + IN BOOLEAN bWIV,
61111 + IN UCHAR QSEL);
61112 +
61113 +VOID RTMPSuspendMsduTransmission(
61114 + IN PRTMP_ADAPTER pAd);
61115 +
61116 +VOID RTMPResumeMsduTransmission(
61117 + IN PRTMP_ADAPTER pAd);
61118 +
61119 +NDIS_STATUS MiniportMMRequest(
61120 + IN PRTMP_ADAPTER pAd,
61121 + IN UCHAR QueIdx,
61122 + IN PUCHAR pData,
61123 + IN UINT Length);
61124 +
61125 +VOID RTMPSendNullFrame(
61126 + IN PRTMP_ADAPTER pAd,
61127 + IN UCHAR TxRate,
61128 + IN BOOLEAN bQosNull);
61129 +
61130 +VOID RTMPSendDisassociationFrame(
61131 + IN PRTMP_ADAPTER pAd);
61132 +
61133 +VOID RTMPSendRTSFrame(
61134 + IN PRTMP_ADAPTER pAd,
61135 + IN PUCHAR pDA,
61136 + IN unsigned int NextMpduSize,
61137 + IN UCHAR TxRate,
61138 + IN UCHAR RTSRate,
61139 + IN USHORT AckDuration,
61140 + IN UCHAR QueIdx,
61141 + IN UCHAR FrameGap);
61142 +
61143 +
61144 +NDIS_STATUS RTMPApplyPacketFilter(
61145 + IN PRTMP_ADAPTER pAd,
61146 + IN PRT28XX_RXD_STRUC pRxD,
61147 + IN PHEADER_802_11 pHeader);
61148 +
61149 +PQUEUE_HEADER RTMPCheckTxSwQueue(
61150 + IN PRTMP_ADAPTER pAd,
61151 + OUT UCHAR *QueIdx);
61152 +
61153 +#ifdef CONFIG_STA_SUPPORT
61154 +VOID RTMPReportMicError(
61155 + IN PRTMP_ADAPTER pAd,
61156 + IN PCIPHER_KEY pWpaKey);
61157 +
61158 +VOID WpaMicFailureReportFrame(
61159 + IN PRTMP_ADAPTER pAd,
61160 + IN MLME_QUEUE_ELEM *Elem);
61161 +
61162 +VOID WpaDisassocApAndBlockAssoc(
61163 + IN PVOID SystemSpecific1,
61164 + IN PVOID FunctionContext,
61165 + IN PVOID SystemSpecific2,
61166 + IN PVOID SystemSpecific3);
61167 +#endif // CONFIG_STA_SUPPORT //
61168 +
61169 +NDIS_STATUS RTMPCloneNdisPacket(
61170 + IN PRTMP_ADAPTER pAd,
61171 + IN BOOLEAN pInsAMSDUHdr,
61172 + IN PNDIS_PACKET pInPacket,
61173 + OUT PNDIS_PACKET *ppOutPacket);
61174 +
61175 +NDIS_STATUS RTMPAllocateNdisPacket(
61176 + IN PRTMP_ADAPTER pAd,
61177 + IN PNDIS_PACKET *pPacket,
61178 + IN PUCHAR pHeader,
61179 + IN UINT HeaderLen,
61180 + IN PUCHAR pData,
61181 + IN UINT DataLen);
61182 +
61183 +VOID RTMPFreeNdisPacket(
61184 + IN PRTMP_ADAPTER pAd,
61185 + IN PNDIS_PACKET pPacket);
61186 +
61187 +BOOLEAN RTMPFreeTXDUponTxDmaDone(
61188 + IN PRTMP_ADAPTER pAd,
61189 + IN UCHAR QueIdx);
61190 +
61191 +BOOLEAN RTMPCheckDHCPFrame(
61192 + IN PRTMP_ADAPTER pAd,
61193 + IN PNDIS_PACKET pPacket);
61194 +
61195 +
61196 +BOOLEAN RTMPCheckEtherType(
61197 + IN PRTMP_ADAPTER pAd,
61198 + IN PNDIS_PACKET pPacket);
61199 +
61200 +
61201 +VOID RTMPCckBbpTuning(
61202 + IN PRTMP_ADAPTER pAd,
61203 + IN UINT TxRate);
61204 +
61205 +//
61206 +// Private routines in rtmp_wep.c
61207 +//
61208 +VOID RTMPInitWepEngine(
61209 + IN PRTMP_ADAPTER pAd,
61210 + IN PUCHAR pKey,
61211 + IN UCHAR KeyId,
61212 + IN UCHAR KeyLen,
61213 + IN PUCHAR pDest);
61214 +
61215 +VOID RTMPEncryptData(
61216 + IN PRTMP_ADAPTER pAd,
61217 + IN PUCHAR pSrc,
61218 + IN PUCHAR pDest,
61219 + IN UINT Len);
61220 +
61221 +BOOLEAN RTMPDecryptData(
61222 + IN PRTMP_ADAPTER pAdapter,
61223 + IN PUCHAR pSrc,
61224 + IN UINT Len,
61225 + IN UINT idx);
61226 +
61227 +BOOLEAN RTMPSoftDecryptWEP(
61228 + IN PRTMP_ADAPTER pAd,
61229 + IN PUCHAR pData,
61230 + IN ULONG DataByteCnt,
61231 + IN PCIPHER_KEY pGroupKey);
61232 +
61233 +VOID RTMPSetICV(
61234 + IN PRTMP_ADAPTER pAd,
61235 + IN PUCHAR pDest);
61236 +
61237 +VOID ARCFOUR_INIT(
61238 + IN PARCFOURCONTEXT Ctx,
61239 + IN PUCHAR pKey,
61240 + IN UINT KeyLen);
61241 +
61242 +UCHAR ARCFOUR_BYTE(
61243 + IN PARCFOURCONTEXT Ctx);
61244 +
61245 +VOID ARCFOUR_DECRYPT(
61246 + IN PARCFOURCONTEXT Ctx,
61247 + IN PUCHAR pDest,
61248 + IN PUCHAR pSrc,
61249 + IN UINT Len);
61250 +
61251 +VOID ARCFOUR_ENCRYPT(
61252 + IN PARCFOURCONTEXT Ctx,
61253 + IN PUCHAR pDest,
61254 + IN PUCHAR pSrc,
61255 + IN UINT Len);
61256 +
61257 +VOID WPAARCFOUR_ENCRYPT(
61258 + IN PARCFOURCONTEXT Ctx,
61259 + IN PUCHAR pDest,
61260 + IN PUCHAR pSrc,
61261 + IN UINT Len);
61262 +
61263 +UINT RTMP_CALC_FCS32(
61264 + IN UINT Fcs,
61265 + IN PUCHAR Cp,
61266 + IN INT Len);
61267 +
61268 +//
61269 +// MLME routines
61270 +//
61271 +
61272 +// Asic/RF/BBP related functions
61273 +
61274 +VOID AsicAdjustTxPower(
61275 + IN PRTMP_ADAPTER pAd);
61276 +
61277 +VOID AsicUpdateProtect(
61278 + IN PRTMP_ADAPTER pAd,
61279 + IN USHORT OperaionMode,
61280 + IN UCHAR SetMask,
61281 + IN BOOLEAN bDisableBGProtect,
61282 + IN BOOLEAN bNonGFExist);
61283 +
61284 +VOID AsicSwitchChannel(
61285 + IN PRTMP_ADAPTER pAd,
61286 + IN UCHAR Channel,
61287 + IN BOOLEAN bScan);
61288 +
61289 +VOID AsicLockChannel(
61290 + IN PRTMP_ADAPTER pAd,
61291 + IN UCHAR Channel) ;
61292 +
61293 +VOID AsicAntennaSelect(
61294 + IN PRTMP_ADAPTER pAd,
61295 + IN UCHAR Channel);
61296 +
61297 +VOID AsicAntennaSetting(
61298 + IN PRTMP_ADAPTER pAd,
61299 + IN ABGBAND_STATE BandState);
61300 +
61301 +VOID AsicRfTuningExec(
61302 + IN PVOID SystemSpecific1,
61303 + IN PVOID FunctionContext,
61304 + IN PVOID SystemSpecific2,
61305 + IN PVOID SystemSpecific3);
61306 +
61307 +#ifdef CONFIG_STA_SUPPORT
61308 +VOID AsicSleepThenAutoWakeup(
61309 + IN PRTMP_ADAPTER pAd,
61310 + IN USHORT TbttNumToNextWakeUp);
61311 +
61312 +VOID AsicForceSleep(
61313 + IN PRTMP_ADAPTER pAd);
61314 +
61315 +VOID AsicForceWakeup(
61316 + IN PRTMP_ADAPTER pAd,
61317 + IN BOOLEAN bFromTx);
61318 +#endif // CONFIG_STA_SUPPORT //
61319 +
61320 +VOID AsicSetBssid(
61321 + IN PRTMP_ADAPTER pAd,
61322 + IN PUCHAR pBssid);
61323 +
61324 +VOID AsicSetMcastWC(
61325 + IN PRTMP_ADAPTER pAd);
61326 +
61327 +VOID AsicDelWcidTab(
61328 + IN PRTMP_ADAPTER pAd,
61329 + IN UCHAR Wcid);
61330 +
61331 +VOID AsicEnableRDG(
61332 + IN PRTMP_ADAPTER pAd);
61333 +
61334 +VOID AsicDisableRDG(
61335 + IN PRTMP_ADAPTER pAd);
61336 +
61337 +VOID AsicDisableSync(
61338 + IN PRTMP_ADAPTER pAd);
61339 +
61340 +VOID AsicEnableBssSync(
61341 + IN PRTMP_ADAPTER pAd);
61342 +
61343 +VOID AsicEnableIbssSync(
61344 + IN PRTMP_ADAPTER pAd);
61345 +
61346 +VOID AsicSetEdcaParm(
61347 + IN PRTMP_ADAPTER pAd,
61348 + IN PEDCA_PARM pEdcaParm);
61349 +
61350 +VOID AsicSetSlotTime(
61351 + IN PRTMP_ADAPTER pAd,
61352 + IN BOOLEAN bUseShortSlotTime);
61353 +
61354 +VOID AsicAddSharedKeyEntry(
61355 + IN PRTMP_ADAPTER pAd,
61356 + IN UCHAR BssIndex,
61357 + IN UCHAR KeyIdx,
61358 + IN UCHAR CipherAlg,
61359 + IN PUCHAR pKey,
61360 + IN PUCHAR pTxMic,
61361 + IN PUCHAR pRxMic);
61362 +
61363 +VOID AsicRemoveSharedKeyEntry(
61364 + IN PRTMP_ADAPTER pAd,
61365 + IN UCHAR BssIndex,
61366 + IN UCHAR KeyIdx);
61367 +
61368 +VOID AsicUpdateWCIDAttribute(
61369 + IN PRTMP_ADAPTER pAd,
61370 + IN USHORT WCID,
61371 + IN UCHAR BssIndex,
61372 + IN UCHAR CipherAlg,
61373 + IN BOOLEAN bUsePairewiseKeyTable);
61374 +
61375 +VOID AsicUpdateWCIDIVEIV(
61376 + IN PRTMP_ADAPTER pAd,
61377 + IN USHORT WCID,
61378 + IN ULONG uIV,
61379 + IN ULONG uEIV);
61380 +
61381 +VOID AsicUpdateRxWCIDTable(
61382 + IN PRTMP_ADAPTER pAd,
61383 + IN USHORT WCID,
61384 + IN PUCHAR pAddr);
61385 +
61386 +VOID AsicAddKeyEntry(
61387 + IN PRTMP_ADAPTER pAd,
61388 + IN USHORT WCID,
61389 + IN UCHAR BssIndex,
61390 + IN UCHAR KeyIdx,
61391 + IN PCIPHER_KEY pCipherKey,
61392 + IN BOOLEAN bUsePairewiseKeyTable,
61393 + IN BOOLEAN bTxKey);
61394 +
61395 +VOID AsicAddPairwiseKeyEntry(
61396 + IN PRTMP_ADAPTER pAd,
61397 + IN PUCHAR pAddr,
61398 + IN UCHAR WCID,
61399 + IN CIPHER_KEY *pCipherKey);
61400 +
61401 +VOID AsicRemovePairwiseKeyEntry(
61402 + IN PRTMP_ADAPTER pAd,
61403 + IN UCHAR BssIdx,
61404 + IN UCHAR Wcid);
61405 +
61406 +BOOLEAN AsicSendCommandToMcu(
61407 + IN PRTMP_ADAPTER pAd,
61408 + IN UCHAR Command,
61409 + IN UCHAR Token,
61410 + IN UCHAR Arg0,
61411 + IN UCHAR Arg1);
61412 +
61413 +#ifdef RT2860
61414 +BOOLEAN AsicCheckCommanOk(
61415 + IN PRTMP_ADAPTER pAd,
61416 + IN UCHAR Command);
61417 +#endif // RT2860 //
61418 +
61419 +VOID MacAddrRandomBssid(
61420 + IN PRTMP_ADAPTER pAd,
61421 + OUT PUCHAR pAddr);
61422 +
61423 +VOID MgtMacHeaderInit(
61424 + IN PRTMP_ADAPTER pAd,
61425 + IN OUT PHEADER_802_11 pHdr80211,
61426 + IN UCHAR SubType,
61427 + IN UCHAR ToDs,
61428 + IN PUCHAR pDA,
61429 + IN PUCHAR pBssid);
61430 +
61431 +VOID MlmeRadioOff(
61432 + IN PRTMP_ADAPTER pAd);
61433 +
61434 +VOID MlmeRadioOn(
61435 + IN PRTMP_ADAPTER pAd);
61436 +
61437 +
61438 +VOID BssTableInit(
61439 + IN BSS_TABLE *Tab);
61440 +
61441 +#ifdef DOT11_N_SUPPORT
61442 +VOID BATableInit(
61443 + IN PRTMP_ADAPTER pAd,
61444 + IN BA_TABLE *Tab);
61445 +#endif // DOT11_N_SUPPORT //
61446 +
61447 +ULONG BssTableSearch(
61448 + IN BSS_TABLE *Tab,
61449 + IN PUCHAR pBssid,
61450 + IN UCHAR Channel);
61451 +
61452 +ULONG BssSsidTableSearch(
61453 + IN BSS_TABLE *Tab,
61454 + IN PUCHAR pBssid,
61455 + IN PUCHAR pSsid,
61456 + IN UCHAR SsidLen,
61457 + IN UCHAR Channel);
61458 +
61459 +ULONG BssTableSearchWithSSID(
61460 + IN BSS_TABLE *Tab,
61461 + IN PUCHAR Bssid,
61462 + IN PUCHAR pSsid,
61463 + IN UCHAR SsidLen,
61464 + IN UCHAR Channel);
61465 +
61466 +VOID BssTableDeleteEntry(
61467 + IN OUT PBSS_TABLE pTab,
61468 + IN PUCHAR pBssid,
61469 + IN UCHAR Channel);
61470 +
61471 +#ifdef DOT11_N_SUPPORT
61472 +VOID BATableDeleteORIEntry(
61473 + IN OUT PRTMP_ADAPTER pAd,
61474 + IN BA_ORI_ENTRY *pBAORIEntry);
61475 +
61476 +VOID BATableDeleteRECEntry(
61477 + IN OUT PRTMP_ADAPTER pAd,
61478 + IN BA_REC_ENTRY *pBARECEntry);
61479 +
61480 +VOID BATableTearORIEntry(
61481 + IN OUT PRTMP_ADAPTER pAd,
61482 + IN UCHAR TID,
61483 + IN UCHAR Wcid,
61484 + IN BOOLEAN bForceDelete,
61485 + IN BOOLEAN ALL);
61486 +
61487 +VOID BATableTearRECEntry(
61488 + IN OUT PRTMP_ADAPTER pAd,
61489 + IN UCHAR TID,
61490 + IN UCHAR WCID,
61491 + IN BOOLEAN ALL);
61492 +#endif // DOT11_N_SUPPORT //
61493 +
61494 +VOID BssEntrySet(
61495 + IN PRTMP_ADAPTER pAd,
61496 + OUT PBSS_ENTRY pBss,
61497 + IN PUCHAR pBssid,
61498 + IN CHAR Ssid[],
61499 + IN UCHAR SsidLen,
61500 + IN UCHAR BssType,
61501 + IN USHORT BeaconPeriod,
61502 + IN PCF_PARM CfParm,
61503 + IN USHORT AtimWin,
61504 + IN USHORT CapabilityInfo,
61505 + IN UCHAR SupRate[],
61506 + IN UCHAR SupRateLen,
61507 + IN UCHAR ExtRate[],
61508 + IN UCHAR ExtRateLen,
61509 + IN HT_CAPABILITY_IE *pHtCapability,
61510 + IN ADD_HT_INFO_IE *pAddHtInfo, // AP might use this additional ht info IE
61511 + IN UCHAR HtCapabilityLen,
61512 + IN UCHAR AddHtInfoLen,
61513 + IN UCHAR NewExtChanOffset,
61514 + IN UCHAR Channel,
61515 + IN CHAR Rssi,
61516 + IN LARGE_INTEGER TimeStamp,
61517 + IN UCHAR CkipFlag,
61518 + IN PEDCA_PARM pEdcaParm,
61519 + IN PQOS_CAPABILITY_PARM pQosCapability,
61520 + IN PQBSS_LOAD_PARM pQbssLoad,
61521 + IN USHORT LengthVIE,
61522 + IN PNDIS_802_11_VARIABLE_IEs pVIE);
61523 +
61524 +ULONG BssTableSetEntry(
61525 + IN PRTMP_ADAPTER pAd,
61526 + OUT PBSS_TABLE pTab,
61527 + IN PUCHAR pBssid,
61528 + IN CHAR Ssid[],
61529 + IN UCHAR SsidLen,
61530 + IN UCHAR BssType,
61531 + IN USHORT BeaconPeriod,
61532 + IN CF_PARM *CfParm,
61533 + IN USHORT AtimWin,
61534 + IN USHORT CapabilityInfo,
61535 + IN UCHAR SupRate[],
61536 + IN UCHAR SupRateLen,
61537 + IN UCHAR ExtRate[],
61538 + IN UCHAR ExtRateLen,
61539 + IN HT_CAPABILITY_IE *pHtCapability,
61540 + IN ADD_HT_INFO_IE *pAddHtInfo, // AP might use this additional ht info IE
61541 + IN UCHAR HtCapabilityLen,
61542 + IN UCHAR AddHtInfoLen,
61543 + IN UCHAR NewExtChanOffset,
61544 + IN UCHAR Channel,
61545 + IN CHAR Rssi,
61546 + IN LARGE_INTEGER TimeStamp,
61547 + IN UCHAR CkipFlag,
61548 + IN PEDCA_PARM pEdcaParm,
61549 + IN PQOS_CAPABILITY_PARM pQosCapability,
61550 + IN PQBSS_LOAD_PARM pQbssLoad,
61551 + IN USHORT LengthVIE,
61552 + IN PNDIS_802_11_VARIABLE_IEs pVIE);
61553 +
61554 +#ifdef DOT11_N_SUPPORT
61555 +VOID BATableInsertEntry(
61556 + IN PRTMP_ADAPTER pAd,
61557 + IN USHORT Aid,
61558 + IN USHORT TimeOutValue,
61559 + IN USHORT StartingSeq,
61560 + IN UCHAR TID,
61561 + IN UCHAR BAWinSize,
61562 + IN UCHAR OriginatorStatus,
61563 + IN BOOLEAN IsRecipient);
61564 +
61565 +#ifdef DOT11N_DRAFT3
61566 +VOID Bss2040CoexistTimeOut(
61567 + IN PVOID SystemSpecific1,
61568 + IN PVOID FunctionContext,
61569 + IN PVOID SystemSpecific2,
61570 + IN PVOID SystemSpecific3);
61571 +
61572 +
61573 +VOID TriEventInit(
61574 + IN PRTMP_ADAPTER pAd);
61575 +
61576 +ULONG TriEventTableSetEntry(
61577 + IN PRTMP_ADAPTER pAd,
61578 + OUT TRIGGER_EVENT_TAB *Tab,
61579 + IN PUCHAR pBssid,
61580 + IN HT_CAPABILITY_IE *pHtCapability,
61581 + IN UCHAR HtCapabilityLen,
61582 + IN UCHAR RegClass,
61583 + IN UCHAR ChannelNo);
61584 +
61585 +VOID TriEventCounterMaintenance(
61586 + IN PRTMP_ADAPTER pAd);
61587 +#endif // DOT11N_DRAFT3 //
61588 +#endif // DOT11_N_SUPPORT //
61589 +
61590 +VOID BssTableSsidSort(
61591 + IN PRTMP_ADAPTER pAd,
61592 + OUT BSS_TABLE *OutTab,
61593 + IN CHAR Ssid[],
61594 + IN UCHAR SsidLen);
61595 +
61596 +VOID BssTableSortByRssi(
61597 + IN OUT BSS_TABLE *OutTab);
61598 +
61599 +VOID BssCipherParse(
61600 + IN OUT PBSS_ENTRY pBss);
61601 +
61602 +NDIS_STATUS MlmeQueueInit(
61603 + IN MLME_QUEUE *Queue);
61604 +
61605 +VOID MlmeQueueDestroy(
61606 + IN MLME_QUEUE *Queue);
61607 +
61608 +BOOLEAN MlmeEnqueue(
61609 + IN PRTMP_ADAPTER pAd,
61610 + IN ULONG Machine,
61611 + IN ULONG MsgType,
61612 + IN ULONG MsgLen,
61613 + IN VOID *Msg);
61614 +
61615 +BOOLEAN MlmeEnqueueForRecv(
61616 + IN PRTMP_ADAPTER pAd,
61617 + IN ULONG Wcid,
61618 + IN ULONG TimeStampHigh,
61619 + IN ULONG TimeStampLow,
61620 + IN UCHAR Rssi0,
61621 + IN UCHAR Rssi1,
61622 + IN UCHAR Rssi2,
61623 + IN ULONG MsgLen,
61624 + IN PVOID Msg,
61625 + IN UCHAR Signal);
61626 +
61627 +
61628 +BOOLEAN MlmeDequeue(
61629 + IN MLME_QUEUE *Queue,
61630 + OUT MLME_QUEUE_ELEM **Elem);
61631 +
61632 +VOID MlmeRestartStateMachine(
61633 + IN PRTMP_ADAPTER pAd);
61634 +
61635 +BOOLEAN MlmeQueueEmpty(
61636 + IN MLME_QUEUE *Queue);
61637 +
61638 +BOOLEAN MlmeQueueFull(
61639 + IN MLME_QUEUE *Queue);
61640 +
61641 +BOOLEAN MsgTypeSubst(
61642 + IN PRTMP_ADAPTER pAd,
61643 + IN PFRAME_802_11 pFrame,
61644 + OUT INT *Machine,
61645 + OUT INT *MsgType);
61646 +
61647 +VOID StateMachineInit(
61648 + IN STATE_MACHINE *Sm,
61649 + IN STATE_MACHINE_FUNC Trans[],
61650 + IN ULONG StNr,
61651 + IN ULONG MsgNr,
61652 + IN STATE_MACHINE_FUNC DefFunc,
61653 + IN ULONG InitState,
61654 + IN ULONG Base);
61655 +
61656 +VOID StateMachineSetAction(
61657 + IN STATE_MACHINE *S,
61658 + IN ULONG St,
61659 + ULONG Msg,
61660 + IN STATE_MACHINE_FUNC F);
61661 +
61662 +VOID StateMachinePerformAction(
61663 + IN PRTMP_ADAPTER pAd,
61664 + IN STATE_MACHINE *S,
61665 + IN MLME_QUEUE_ELEM *Elem);
61666 +
61667 +VOID Drop(
61668 + IN PRTMP_ADAPTER pAd,
61669 + IN MLME_QUEUE_ELEM *Elem);
61670 +
61671 +VOID AssocStateMachineInit(
61672 + IN PRTMP_ADAPTER pAd,
61673 + IN STATE_MACHINE *Sm,
61674 + OUT STATE_MACHINE_FUNC Trans[]);
61675 +
61676 +VOID ReassocTimeout(
61677 + IN PVOID SystemSpecific1,
61678 + IN PVOID FunctionContext,
61679 + IN PVOID SystemSpecific2,
61680 + IN PVOID SystemSpecific3);
61681 +
61682 +VOID AssocTimeout(
61683 + IN PVOID SystemSpecific1,
61684 + IN PVOID FunctionContext,
61685 + IN PVOID SystemSpecific2,
61686 + IN PVOID SystemSpecific3);
61687 +
61688 +VOID DisassocTimeout(
61689 + IN PVOID SystemSpecific1,
61690 + IN PVOID FunctionContext,
61691 + IN PVOID SystemSpecific2,
61692 + IN PVOID SystemSpecific3);
61693 +
61694 +//----------------------------------------------
61695 +VOID MlmeDisassocReqAction(
61696 + IN PRTMP_ADAPTER pAd,
61697 + IN MLME_QUEUE_ELEM *Elem);
61698 +
61699 +VOID MlmeAssocReqAction(
61700 + IN PRTMP_ADAPTER pAd,
61701 + IN MLME_QUEUE_ELEM *Elem);
61702 +
61703 +VOID MlmeReassocReqAction(
61704 + IN PRTMP_ADAPTER pAd,
61705 + IN MLME_QUEUE_ELEM *Elem);
61706 +
61707 +VOID MlmeDisassocReqAction(
61708 + IN PRTMP_ADAPTER pAd,
61709 + IN MLME_QUEUE_ELEM *Elem);
61710 +
61711 +VOID PeerAssocRspAction(
61712 + IN PRTMP_ADAPTER pAd,
61713 + IN MLME_QUEUE_ELEM *Elem);
61714 +
61715 +VOID PeerReassocRspAction(
61716 + IN PRTMP_ADAPTER pAd,
61717 + IN MLME_QUEUE_ELEM *Elem);
61718 +
61719 +VOID PeerDisassocAction(
61720 + IN PRTMP_ADAPTER pAd,
61721 + IN MLME_QUEUE_ELEM *Elem);
61722 +
61723 +VOID DisassocTimeoutAction(
61724 + IN PRTMP_ADAPTER pAd,
61725 + IN MLME_QUEUE_ELEM *Elem);
61726 +
61727 +VOID AssocTimeoutAction(
61728 + IN PRTMP_ADAPTER pAd,
61729 + IN MLME_QUEUE_ELEM *Elem);
61730 +
61731 +VOID ReassocTimeoutAction(
61732 + IN PRTMP_ADAPTER pAd,
61733 + IN MLME_QUEUE_ELEM *Elem);
61734 +
61735 +VOID Cls3errAction(
61736 + IN PRTMP_ADAPTER pAd,
61737 + IN PUCHAR pAddr);
61738 +
61739 +VOID SwitchBetweenWepAndCkip(
61740 + IN PRTMP_ADAPTER pAd);
61741 +
61742 +VOID InvalidStateWhenAssoc(
61743 + IN PRTMP_ADAPTER pAd,
61744 + IN MLME_QUEUE_ELEM *Elem);
61745 +
61746 +VOID InvalidStateWhenReassoc(
61747 + IN PRTMP_ADAPTER pAd,
61748 + IN MLME_QUEUE_ELEM *Elem);
61749 +
61750 +VOID InvalidStateWhenDisassociate(
61751 + IN PRTMP_ADAPTER pAd,
61752 + IN MLME_QUEUE_ELEM *Elem);
61753 +
61754 +
61755 +VOID ComposePsPoll(
61756 + IN PRTMP_ADAPTER pAd);
61757 +
61758 +VOID ComposeNullFrame(
61759 + IN PRTMP_ADAPTER pAd);
61760 +
61761 +VOID AssocPostProc(
61762 + IN PRTMP_ADAPTER pAd,
61763 + IN PUCHAR pAddr2,
61764 + IN USHORT CapabilityInfo,
61765 + IN USHORT Aid,
61766 + IN UCHAR SupRate[],
61767 + IN UCHAR SupRateLen,
61768 + IN UCHAR ExtRate[],
61769 + IN UCHAR ExtRateLen,
61770 + IN PEDCA_PARM pEdcaParm,
61771 + IN HT_CAPABILITY_IE *pHtCapability,
61772 + IN UCHAR HtCapabilityLen,
61773 + IN ADD_HT_INFO_IE *pAddHtInfo);
61774 +
61775 +VOID AuthStateMachineInit(
61776 + IN PRTMP_ADAPTER pAd,
61777 + IN PSTATE_MACHINE sm,
61778 + OUT STATE_MACHINE_FUNC Trans[]);
61779 +
61780 +VOID AuthTimeout(
61781 + IN PVOID SystemSpecific1,
61782 + IN PVOID FunctionContext,
61783 + IN PVOID SystemSpecific2,
61784 + IN PVOID SystemSpecific3);
61785 +
61786 +VOID MlmeAuthReqAction(
61787 + IN PRTMP_ADAPTER pAd,
61788 + IN MLME_QUEUE_ELEM *Elem);
61789 +
61790 +VOID PeerAuthRspAtSeq2Action(
61791 + IN PRTMP_ADAPTER pAd,
61792 + IN MLME_QUEUE_ELEM *Elem);
61793 +
61794 +VOID PeerAuthRspAtSeq4Action(
61795 + IN PRTMP_ADAPTER pAd,
61796 + IN MLME_QUEUE_ELEM *Elem);
61797 +
61798 +VOID AuthTimeoutAction(
61799 + IN PRTMP_ADAPTER pAd,
61800 + IN MLME_QUEUE_ELEM *Elem);
61801 +
61802 +VOID Cls2errAction(
61803 + IN PRTMP_ADAPTER pAd,
61804 + IN PUCHAR pAddr);
61805 +
61806 +VOID MlmeDeauthReqAction(
61807 + IN PRTMP_ADAPTER pAd,
61808 + IN MLME_QUEUE_ELEM *Elem);
61809 +
61810 +VOID InvalidStateWhenAuth(
61811 + IN PRTMP_ADAPTER pAd,
61812 + IN MLME_QUEUE_ELEM *Elem);
61813 +
61814 +//=============================================
61815 +
61816 +VOID AuthRspStateMachineInit(
61817 + IN PRTMP_ADAPTER pAd,
61818 + IN PSTATE_MACHINE Sm,
61819 + IN STATE_MACHINE_FUNC Trans[]);
61820 +
61821 +VOID PeerDeauthAction(
61822 + IN PRTMP_ADAPTER pAd,
61823 + IN MLME_QUEUE_ELEM *Elem);
61824 +
61825 +VOID PeerAuthSimpleRspGenAndSend(
61826 + IN PRTMP_ADAPTER pAd,
61827 + IN PHEADER_802_11 pHdr80211,
61828 + IN USHORT Alg,
61829 + IN USHORT Seq,
61830 + IN USHORT Reason,
61831 + IN USHORT Status);
61832 +
61833 +//
61834 +// Private routines in dls.c
61835 +//
61836 +
61837 +#ifdef CONFIG_STA_SUPPORT
61838 +#ifdef QOS_DLS_SUPPORT
61839 +void DlsStateMachineInit(
61840 + IN PRTMP_ADAPTER pAd,
61841 + IN STATE_MACHINE *Sm,
61842 + OUT STATE_MACHINE_FUNC Trans[]);
61843 +
61844 +VOID MlmeDlsReqAction(
61845 + IN PRTMP_ADAPTER pAd,
61846 + IN MLME_QUEUE_ELEM *Elem);
61847 +
61848 +VOID PeerDlsReqAction(
61849 + IN PRTMP_ADAPTER pAd,
61850 + IN MLME_QUEUE_ELEM *Elem);
61851 +
61852 +VOID PeerDlsRspAction(
61853 + IN PRTMP_ADAPTER pAd,
61854 + IN MLME_QUEUE_ELEM *Elem);
61855 +
61856 +VOID MlmeDlsTearDownAction(
61857 + IN PRTMP_ADAPTER pAd,
61858 + IN MLME_QUEUE_ELEM *Elem);
61859 +
61860 +VOID PeerDlsTearDownAction(
61861 + IN PRTMP_ADAPTER pAd,
61862 + IN MLME_QUEUE_ELEM *Elem);
61863 +
61864 +VOID RTMPCheckDLSTimeOut(
61865 + IN PRTMP_ADAPTER pAd);
61866 +
61867 +BOOLEAN RTMPRcvFrameDLSCheck(
61868 + IN PRTMP_ADAPTER pAd,
61869 + IN PHEADER_802_11 pHeader,
61870 + IN ULONG Len,
61871 + IN PRT28XX_RXD_STRUC pRxD);
61872 +
61873 +INT RTMPCheckDLSFrame(
61874 + IN PRTMP_ADAPTER pAd,
61875 + IN PUCHAR pDA);
61876 +
61877 +VOID RTMPSendDLSTearDownFrame(
61878 + IN PRTMP_ADAPTER pAd,
61879 + IN PUCHAR pDA);
61880 +
61881 +NDIS_STATUS RTMPSendSTAKeyRequest(
61882 + IN PRTMP_ADAPTER pAd,
61883 + IN PUCHAR pDA);
61884 +
61885 +NDIS_STATUS RTMPSendSTAKeyHandShake(
61886 + IN PRTMP_ADAPTER pAd,
61887 + IN PUCHAR pDA);
61888 +
61889 +VOID DlsTimeoutAction(
61890 + IN PVOID SystemSpecific1,
61891 + IN PVOID FunctionContext,
61892 + IN PVOID SystemSpecific2,
61893 + IN PVOID SystemSpecific3);
61894 +
61895 +BOOLEAN MlmeDlsReqSanity(
61896 + IN PRTMP_ADAPTER pAd,
61897 + IN VOID *Msg,
61898 + IN ULONG MsgLen,
61899 + OUT PRT_802_11_DLS *pDLS,
61900 + OUT PUSHORT pReason);
61901 +
61902 +INT Set_DlsEntryInfo_Display_Proc(
61903 + IN PRTMP_ADAPTER pAd,
61904 + IN PUCHAR arg);
61905 +
61906 +MAC_TABLE_ENTRY *MacTableInsertDlsEntry(
61907 + IN PRTMP_ADAPTER pAd,
61908 + IN PUCHAR pAddr,
61909 + IN UINT DlsEntryIdx);
61910 +
61911 +BOOLEAN MacTableDeleteDlsEntry(
61912 + IN PRTMP_ADAPTER pAd,
61913 + IN USHORT wcid,
61914 + IN PUCHAR pAddr);
61915 +
61916 +MAC_TABLE_ENTRY *DlsEntryTableLookup(
61917 + IN PRTMP_ADAPTER pAd,
61918 + IN PUCHAR pAddr,
61919 + IN BOOLEAN bResetIdelCount);
61920 +
61921 +MAC_TABLE_ENTRY *DlsEntryTableLookupByWcid(
61922 + IN PRTMP_ADAPTER pAd,
61923 + IN UCHAR wcid,
61924 + IN PUCHAR pAddr,
61925 + IN BOOLEAN bResetIdelCount);
61926 +
61927 +INT Set_DlsAddEntry_Proc(
61928 + IN PRTMP_ADAPTER pAd,
61929 + IN PUCHAR arg);
61930 +
61931 +INT Set_DlsTearDownEntry_Proc(
61932 + IN PRTMP_ADAPTER pAd,
61933 + IN PUCHAR arg);
61934 +#endif // QOS_DLS_SUPPORT //
61935 +#endif // CONFIG_STA_SUPPORT //
61936 +
61937 +#ifdef QOS_DLS_SUPPORT
61938 +BOOLEAN PeerDlsReqSanity(
61939 + IN PRTMP_ADAPTER pAd,
61940 + IN VOID *Msg,
61941 + IN ULONG MsgLen,
61942 + OUT PUCHAR pDA,
61943 + OUT PUCHAR pSA,
61944 + OUT USHORT *pCapabilityInfo,
61945 + OUT USHORT *pDlsTimeout,
61946 + OUT UCHAR *pRatesLen,
61947 + OUT UCHAR Rates[],
61948 + OUT UCHAR *pHtCapabilityLen,
61949 + OUT HT_CAPABILITY_IE *pHtCapability);
61950 +
61951 +BOOLEAN PeerDlsRspSanity(
61952 + IN PRTMP_ADAPTER pAd,
61953 + IN VOID *Msg,
61954 + IN ULONG MsgLen,
61955 + OUT PUCHAR pDA,
61956 + OUT PUCHAR pSA,
61957 + OUT USHORT *pCapabilityInfo,
61958 + OUT USHORT *pStatus,
61959 + OUT UCHAR *pRatesLen,
61960 + OUT UCHAR Rates[],
61961 + OUT UCHAR *pHtCapabilityLen,
61962 + OUT HT_CAPABILITY_IE *pHtCapability);
61963 +
61964 +BOOLEAN PeerDlsTearDownSanity(
61965 + IN PRTMP_ADAPTER pAd,
61966 + IN VOID *Msg,
61967 + IN ULONG MsgLen,
61968 + OUT PUCHAR pDA,
61969 + OUT PUCHAR pSA,
61970 + OUT USHORT *pReason);
61971 +#endif // QOS_DLS_SUPPORT //
61972 +
61973 +//========================================
61974 +
61975 +VOID SyncStateMachineInit(
61976 + IN PRTMP_ADAPTER pAd,
61977 + IN STATE_MACHINE *Sm,
61978 + OUT STATE_MACHINE_FUNC Trans[]);
61979 +
61980 +VOID BeaconTimeout(
61981 + IN PVOID SystemSpecific1,
61982 + IN PVOID FunctionContext,
61983 + IN PVOID SystemSpecific2,
61984 + IN PVOID SystemSpecific3);
61985 +
61986 +VOID ScanTimeout(
61987 + IN PVOID SystemSpecific1,
61988 + IN PVOID FunctionContext,
61989 + IN PVOID SystemSpecific2,
61990 + IN PVOID SystemSpecific3);
61991 +
61992 +VOID MlmeScanReqAction(
61993 + IN PRTMP_ADAPTER pAd,
61994 + IN MLME_QUEUE_ELEM *Elem);
61995 +
61996 +VOID InvalidStateWhenScan(
61997 + IN PRTMP_ADAPTER pAd,
61998 + IN MLME_QUEUE_ELEM *Elem);
61999 +
62000 +VOID InvalidStateWhenJoin(
62001 + IN PRTMP_ADAPTER pAd,
62002 + IN MLME_QUEUE_ELEM *Elem);
62003 +
62004 +VOID InvalidStateWhenStart(
62005 + IN PRTMP_ADAPTER pAd,
62006 + IN MLME_QUEUE_ELEM *Elem);
62007 +
62008 +VOID PeerBeacon(
62009 + IN PRTMP_ADAPTER pAd,
62010 + IN MLME_QUEUE_ELEM *Elem);
62011 +
62012 +VOID EnqueueProbeRequest(
62013 + IN PRTMP_ADAPTER pAd);
62014 +
62015 +BOOLEAN ScanRunning(
62016 + IN PRTMP_ADAPTER pAd);
62017 +//=========================================
62018 +
62019 +VOID MlmeCntlInit(
62020 + IN PRTMP_ADAPTER pAd,
62021 + IN STATE_MACHINE *S,
62022 + OUT STATE_MACHINE_FUNC Trans[]);
62023 +
62024 +VOID MlmeCntlMachinePerformAction(
62025 + IN PRTMP_ADAPTER pAd,
62026 + IN STATE_MACHINE *S,
62027 + IN MLME_QUEUE_ELEM *Elem);
62028 +
62029 +VOID CntlIdleProc(
62030 + IN PRTMP_ADAPTER pAd,
62031 + IN MLME_QUEUE_ELEM *Elem);
62032 +
62033 +VOID CntlOidScanProc(
62034 + IN PRTMP_ADAPTER pAd,
62035 + IN MLME_QUEUE_ELEM *Elem);
62036 +
62037 +VOID CntlOidSsidProc(
62038 + IN PRTMP_ADAPTER pAd,
62039 + IN MLME_QUEUE_ELEM * Elem);
62040 +
62041 +VOID CntlOidRTBssidProc(
62042 + IN PRTMP_ADAPTER pAd,
62043 + IN MLME_QUEUE_ELEM * Elem);
62044 +
62045 +VOID CntlMlmeRoamingProc(
62046 + IN PRTMP_ADAPTER pAd,
62047 + IN MLME_QUEUE_ELEM * Elem);
62048 +
62049 +VOID CntlWaitDisassocProc(
62050 + IN PRTMP_ADAPTER pAd,
62051 + IN MLME_QUEUE_ELEM *Elem);
62052 +
62053 +VOID CntlWaitJoinProc(
62054 + IN PRTMP_ADAPTER pAd,
62055 + IN MLME_QUEUE_ELEM *Elem);
62056 +
62057 +VOID CntlWaitReassocProc(
62058 + IN PRTMP_ADAPTER pAd,
62059 + IN MLME_QUEUE_ELEM *Elem);
62060 +
62061 +VOID CntlWaitStartProc(
62062 + IN PRTMP_ADAPTER pAd,
62063 + IN MLME_QUEUE_ELEM *Elem);
62064 +
62065 +VOID CntlWaitAuthProc(
62066 + IN PRTMP_ADAPTER pAd,
62067 + IN MLME_QUEUE_ELEM *Elem);
62068 +
62069 +VOID CntlWaitAuthProc2(
62070 + IN PRTMP_ADAPTER pAd,
62071 + IN MLME_QUEUE_ELEM *Elem);
62072 +
62073 +VOID CntlWaitAssocProc(
62074 + IN PRTMP_ADAPTER pAd,
62075 + IN MLME_QUEUE_ELEM *Elem);
62076 +
62077 +#ifdef QOS_DLS_SUPPORT
62078 +VOID CntlOidDLSSetupProc(
62079 + IN PRTMP_ADAPTER pAd,
62080 + IN MLME_QUEUE_ELEM *Elem);
62081 +#endif // QOS_DLS_SUPPORT //
62082 +
62083 +VOID LinkUp(
62084 + IN PRTMP_ADAPTER pAd,
62085 + IN UCHAR BssType);
62086 +
62087 +VOID LinkDown(
62088 + IN PRTMP_ADAPTER pAd,
62089 + IN BOOLEAN IsReqFromAP);
62090 +
62091 +VOID IterateOnBssTab(
62092 + IN PRTMP_ADAPTER pAd);
62093 +
62094 +VOID IterateOnBssTab2(
62095 + IN PRTMP_ADAPTER pAd);;
62096 +
62097 +VOID JoinParmFill(
62098 + IN PRTMP_ADAPTER pAd,
62099 + IN OUT MLME_JOIN_REQ_STRUCT *JoinReq,
62100 + IN ULONG BssIdx);
62101 +
62102 +VOID AssocParmFill(
62103 + IN PRTMP_ADAPTER pAd,
62104 + IN OUT MLME_ASSOC_REQ_STRUCT *AssocReq,
62105 + IN PUCHAR pAddr,
62106 + IN USHORT CapabilityInfo,
62107 + IN ULONG Timeout,
62108 + IN USHORT ListenIntv);
62109 +
62110 +VOID ScanParmFill(
62111 + IN PRTMP_ADAPTER pAd,
62112 + IN OUT MLME_SCAN_REQ_STRUCT *ScanReq,
62113 + IN CHAR Ssid[],
62114 + IN UCHAR SsidLen,
62115 + IN UCHAR BssType,
62116 + IN UCHAR ScanType);
62117 +
62118 +VOID DisassocParmFill(
62119 + IN PRTMP_ADAPTER pAd,
62120 + IN OUT MLME_DISASSOC_REQ_STRUCT *DisassocReq,
62121 + IN PUCHAR pAddr,
62122 + IN USHORT Reason);
62123 +
62124 +VOID StartParmFill(
62125 + IN PRTMP_ADAPTER pAd,
62126 + IN OUT MLME_START_REQ_STRUCT *StartReq,
62127 + IN CHAR Ssid[],
62128 + IN UCHAR SsidLen);
62129 +
62130 +VOID AuthParmFill(
62131 + IN PRTMP_ADAPTER pAd,
62132 + IN OUT MLME_AUTH_REQ_STRUCT *AuthReq,
62133 + IN PUCHAR pAddr,
62134 + IN USHORT Alg);
62135 +
62136 +VOID EnqueuePsPoll(
62137 + IN PRTMP_ADAPTER pAd);
62138 +
62139 +VOID EnqueueBeaconFrame(
62140 + IN PRTMP_ADAPTER pAd);
62141 +
62142 +VOID MlmeJoinReqAction(
62143 + IN PRTMP_ADAPTER pAd,
62144 + IN MLME_QUEUE_ELEM *Elem);
62145 +
62146 +VOID MlmeScanReqAction(
62147 + IN PRTMP_ADAPTER pAd,
62148 + IN MLME_QUEUE_ELEM *Elem);
62149 +
62150 +VOID MlmeStartReqAction(
62151 + IN PRTMP_ADAPTER pAd,
62152 + IN MLME_QUEUE_ELEM *Elem);
62153 +
62154 +VOID ScanTimeoutAction(
62155 + IN PRTMP_ADAPTER pAd,
62156 + IN MLME_QUEUE_ELEM *Elem);
62157 +
62158 +VOID BeaconTimeoutAtJoinAction(
62159 + IN PRTMP_ADAPTER pAd,
62160 + IN MLME_QUEUE_ELEM *Elem);
62161 +
62162 +VOID PeerBeaconAtScanAction(
62163 + IN PRTMP_ADAPTER pAd,
62164 + IN MLME_QUEUE_ELEM *Elem);
62165 +
62166 +VOID PeerBeaconAtJoinAction(
62167 + IN PRTMP_ADAPTER pAd,
62168 + IN MLME_QUEUE_ELEM *Elem);
62169 +
62170 +VOID PeerBeacon(
62171 + IN PRTMP_ADAPTER pAd,
62172 + IN MLME_QUEUE_ELEM *Elem);
62173 +
62174 +VOID PeerProbeReqAction(
62175 + IN PRTMP_ADAPTER pAd,
62176 + IN MLME_QUEUE_ELEM *Elem);
62177 +
62178 +VOID ScanNextChannel(
62179 + IN PRTMP_ADAPTER pAd);
62180 +
62181 +ULONG MakeIbssBeacon(
62182 + IN PRTMP_ADAPTER pAd);
62183 +
62184 +VOID CCXAdjacentAPReport(
62185 + IN PRTMP_ADAPTER pAd);
62186 +
62187 +BOOLEAN MlmeScanReqSanity(
62188 + IN PRTMP_ADAPTER pAd,
62189 + IN VOID *Msg,
62190 + IN ULONG MsgLen,
62191 + OUT UCHAR *BssType,
62192 + OUT CHAR ssid[],
62193 + OUT UCHAR *SsidLen,
62194 + OUT UCHAR *ScanType);
62195 +
62196 +BOOLEAN PeerBeaconAndProbeRspSanity(
62197 + IN PRTMP_ADAPTER pAd,
62198 + IN VOID *Msg,
62199 + IN ULONG MsgLen,
62200 + IN UCHAR MsgChannel,
62201 + OUT PUCHAR pAddr2,
62202 + OUT PUCHAR pBssid,
62203 + OUT CHAR Ssid[],
62204 + OUT UCHAR *pSsidLen,
62205 + OUT UCHAR *pBssType,
62206 + OUT USHORT *pBeaconPeriod,
62207 + OUT UCHAR *pChannel,
62208 + OUT UCHAR *pNewChannel,
62209 + OUT LARGE_INTEGER *pTimestamp,
62210 + OUT CF_PARM *pCfParm,
62211 + OUT USHORT *pAtimWin,
62212 + OUT USHORT *pCapabilityInfo,
62213 + OUT UCHAR *pErp,
62214 + OUT UCHAR *pDtimCount,
62215 + OUT UCHAR *pDtimPeriod,
62216 + OUT UCHAR *pBcastFlag,
62217 + OUT UCHAR *pMessageToMe,
62218 + OUT UCHAR SupRate[],
62219 + OUT UCHAR *pSupRateLen,
62220 + OUT UCHAR ExtRate[],
62221 + OUT UCHAR *pExtRateLen,
62222 + OUT UCHAR *pCkipFlag,
62223 + OUT UCHAR *pAironetCellPowerLimit,
62224 + OUT PEDCA_PARM pEdcaParm,
62225 + OUT PQBSS_LOAD_PARM pQbssLoad,
62226 + OUT PQOS_CAPABILITY_PARM pQosCapability,
62227 + OUT ULONG *pRalinkIe,
62228 + OUT UCHAR *pHtCapabilityLen,
62229 +#ifdef CONFIG_STA_SUPPORT
62230 + OUT UCHAR *pPreNHtCapabilityLen,
62231 +#endif // CONFIG_STA_SUPPORT //
62232 + OUT HT_CAPABILITY_IE *pHtCapability,
62233 + OUT UCHAR *AddHtInfoLen,
62234 + OUT ADD_HT_INFO_IE *AddHtInfo,
62235 + OUT UCHAR *NewExtChannel,
62236 + OUT USHORT *LengthVIE,
62237 + OUT PNDIS_802_11_VARIABLE_IEs pVIE);
62238 +
62239 +BOOLEAN PeerAddBAReqActionSanity(
62240 + IN PRTMP_ADAPTER pAd,
62241 + IN VOID *pMsg,
62242 + IN ULONG MsgLen,
62243 + OUT PUCHAR pAddr2);
62244 +
62245 +BOOLEAN PeerAddBARspActionSanity(
62246 + IN PRTMP_ADAPTER pAd,
62247 + IN VOID *pMsg,
62248 + IN ULONG MsgLen);
62249 +
62250 +BOOLEAN PeerDelBAActionSanity(
62251 + IN PRTMP_ADAPTER pAd,
62252 + IN UCHAR Wcid,
62253 + IN VOID *pMsg,
62254 + IN ULONG MsgLen);
62255 +
62256 +BOOLEAN MlmeAssocReqSanity(
62257 + IN PRTMP_ADAPTER pAd,
62258 + IN VOID *Msg,
62259 + IN ULONG MsgLen,
62260 + OUT PUCHAR pApAddr,
62261 + OUT USHORT *CapabilityInfo,
62262 + OUT ULONG *Timeout,
62263 + OUT USHORT *ListenIntv);
62264 +
62265 +BOOLEAN MlmeAuthReqSanity(
62266 + IN PRTMP_ADAPTER pAd,
62267 + IN VOID *Msg,
62268 + IN ULONG MsgLen,
62269 + OUT PUCHAR pAddr,
62270 + OUT ULONG *Timeout,
62271 + OUT USHORT *Alg);
62272 +
62273 +BOOLEAN MlmeStartReqSanity(
62274 + IN PRTMP_ADAPTER pAd,
62275 + IN VOID *Msg,
62276 + IN ULONG MsgLen,
62277 + OUT CHAR Ssid[],
62278 + OUT UCHAR *Ssidlen);
62279 +
62280 +BOOLEAN PeerAuthSanity(
62281 + IN PRTMP_ADAPTER pAd,
62282 + IN VOID *Msg,
62283 + IN ULONG MsgLen,
62284 + OUT PUCHAR pAddr,
62285 + OUT USHORT *Alg,
62286 + OUT USHORT *Seq,
62287 + OUT USHORT *Status,
62288 + OUT CHAR ChlgText[]);
62289 +
62290 +BOOLEAN PeerAssocRspSanity(
62291 + IN PRTMP_ADAPTER pAd,
62292 + IN VOID *pMsg,
62293 + IN ULONG MsgLen,
62294 + OUT PUCHAR pAddr2,
62295 + OUT USHORT *pCapabilityInfo,
62296 + OUT USHORT *pStatus,
62297 + OUT USHORT *pAid,
62298 + OUT UCHAR SupRate[],
62299 + OUT UCHAR *pSupRateLen,
62300 + OUT UCHAR ExtRate[],
62301 + OUT UCHAR *pExtRateLen,
62302 + OUT HT_CAPABILITY_IE *pHtCapability,
62303 + OUT ADD_HT_INFO_IE *pAddHtInfo, // AP might use this additional ht info IE
62304 + OUT UCHAR *pHtCapabilityLen,
62305 + OUT UCHAR *pAddHtInfoLen,
62306 + OUT UCHAR *pNewExtChannelOffset,
62307 + OUT PEDCA_PARM pEdcaParm,
62308 + OUT UCHAR *pCkipFlag);
62309 +
62310 +BOOLEAN PeerDisassocSanity(
62311 + IN PRTMP_ADAPTER pAd,
62312 + IN VOID *Msg,
62313 + IN ULONG MsgLen,
62314 + OUT PUCHAR pAddr2,
62315 + OUT USHORT *Reason);
62316 +
62317 +BOOLEAN PeerWpaMessageSanity(
62318 + IN PRTMP_ADAPTER pAd,
62319 + IN PEAPOL_PACKET pMsg,
62320 + IN ULONG MsgLen,
62321 + IN UCHAR MsgType,
62322 + IN MAC_TABLE_ENTRY *pEntry);
62323 +
62324 +BOOLEAN PeerDeauthSanity(
62325 + IN PRTMP_ADAPTER pAd,
62326 + IN VOID *Msg,
62327 + IN ULONG MsgLen,
62328 + OUT PUCHAR pAddr2,
62329 + OUT USHORT *Reason);
62330 +
62331 +BOOLEAN PeerProbeReqSanity(
62332 + IN PRTMP_ADAPTER pAd,
62333 + IN VOID *Msg,
62334 + IN ULONG MsgLen,
62335 + OUT PUCHAR pAddr2,
62336 + OUT CHAR Ssid[],
62337 + OUT UCHAR *pSsidLen);
62338 +
62339 +BOOLEAN GetTimBit(
62340 + IN CHAR *Ptr,
62341 + IN USHORT Aid,
62342 + OUT UCHAR *TimLen,
62343 + OUT UCHAR *BcastFlag,
62344 + OUT UCHAR *DtimCount,
62345 + OUT UCHAR *DtimPeriod,
62346 + OUT UCHAR *MessageToMe);
62347 +
62348 +UCHAR ChannelSanity(
62349 + IN PRTMP_ADAPTER pAd,
62350 + IN UCHAR channel);
62351 +
62352 +NDIS_802_11_NETWORK_TYPE NetworkTypeInUseSanity(
62353 + IN PBSS_ENTRY pBss);
62354 +
62355 +BOOLEAN MlmeDelBAReqSanity(
62356 + IN PRTMP_ADAPTER pAd,
62357 + IN VOID *Msg,
62358 + IN ULONG MsgLen);
62359 +
62360 +BOOLEAN MlmeAddBAReqSanity(
62361 + IN PRTMP_ADAPTER pAd,
62362 + IN VOID *Msg,
62363 + IN ULONG MsgLen,
62364 + OUT PUCHAR pAddr2);
62365 +
62366 +ULONG MakeOutgoingFrame(
62367 + OUT CHAR *Buffer,
62368 + OUT ULONG *Length, ...);
62369 +
62370 +VOID LfsrInit(
62371 + IN PRTMP_ADAPTER pAd,
62372 + IN ULONG Seed);
62373 +
62374 +UCHAR RandomByte(
62375 + IN PRTMP_ADAPTER pAd);
62376 +
62377 +VOID AsicUpdateAutoFallBackTable(
62378 + IN PRTMP_ADAPTER pAd,
62379 + IN PUCHAR pTxRate);
62380 +
62381 +VOID MlmePeriodicExec(
62382 + IN PVOID SystemSpecific1,
62383 + IN PVOID FunctionContext,
62384 + IN PVOID SystemSpecific2,
62385 + IN PVOID SystemSpecific3);
62386 +
62387 +VOID LinkDownExec(
62388 + IN PVOID SystemSpecific1,
62389 + IN PVOID FunctionContext,
62390 + IN PVOID SystemSpecific2,
62391 + IN PVOID SystemSpecific3);
62392 +
62393 +VOID LinkUpExec(
62394 + IN PVOID SystemSpecific1,
62395 + IN PVOID FunctionContext,
62396 + IN PVOID SystemSpecific2,
62397 + IN PVOID SystemSpecific3);
62398 +
62399 +VOID STAMlmePeriodicExec(
62400 + PRTMP_ADAPTER pAd);
62401 +
62402 +VOID MlmeAutoScan(
62403 + IN PRTMP_ADAPTER pAd);
62404 +
62405 +VOID MlmeAutoReconnectLastSSID(
62406 + IN PRTMP_ADAPTER pAd);
62407 +
62408 +BOOLEAN MlmeValidateSSID(
62409 + IN PUCHAR pSsid,
62410 + IN UCHAR SsidLen);
62411 +
62412 +VOID MlmeCheckForRoaming(
62413 + IN PRTMP_ADAPTER pAd,
62414 + IN ULONG Now32);
62415 +
62416 +VOID MlmeCheckForFastRoaming(
62417 + IN PRTMP_ADAPTER pAd,
62418 + IN ULONG Now);
62419 +
62420 +VOID MlmeDynamicTxRateSwitching(
62421 + IN PRTMP_ADAPTER pAd);
62422 +
62423 +VOID MlmeSetTxRate(
62424 + IN PRTMP_ADAPTER pAd,
62425 + IN PMAC_TABLE_ENTRY pEntry,
62426 + IN PRTMP_TX_RATE_SWITCH pTxRate);
62427 +
62428 +VOID MlmeSelectTxRateTable(
62429 + IN PRTMP_ADAPTER pAd,
62430 + IN PMAC_TABLE_ENTRY pEntry,
62431 + IN PUCHAR *ppTable,
62432 + IN PUCHAR pTableSize,
62433 + IN PUCHAR pInitTxRateIdx);
62434 +
62435 +VOID MlmeCalculateChannelQuality(
62436 + IN PRTMP_ADAPTER pAd,
62437 + IN ULONG Now);
62438 +
62439 +VOID MlmeCheckPsmChange(
62440 + IN PRTMP_ADAPTER pAd,
62441 + IN ULONG Now32);
62442 +
62443 +VOID MlmeSetPsmBit(
62444 + IN PRTMP_ADAPTER pAd,
62445 + IN USHORT psm);
62446 +
62447 +VOID MlmeSetTxPreamble(
62448 + IN PRTMP_ADAPTER pAd,
62449 + IN USHORT TxPreamble);
62450 +
62451 +VOID UpdateBasicRateBitmap(
62452 + IN PRTMP_ADAPTER pAd);
62453 +
62454 +VOID MlmeUpdateTxRates(
62455 + IN PRTMP_ADAPTER pAd,
62456 + IN BOOLEAN bLinkUp,
62457 + IN UCHAR apidx);
62458 +
62459 +#ifdef DOT11_N_SUPPORT
62460 +VOID MlmeUpdateHtTxRates(
62461 + IN PRTMP_ADAPTER pAd,
62462 + IN UCHAR apidx);
62463 +#endif // DOT11_N_SUPPORT //
62464 +
62465 +VOID RTMPCheckRates(
62466 + IN PRTMP_ADAPTER pAd,
62467 + IN OUT UCHAR SupRate[],
62468 + IN OUT UCHAR *SupRateLen);
62469 +
62470 +#ifdef CONFIG_STA_SUPPORT
62471 +BOOLEAN RTMPCheckChannel(
62472 + IN PRTMP_ADAPTER pAd,
62473 + IN UCHAR CentralChannel,
62474 + IN UCHAR Channel);
62475 +#endif // CONFIG_STA_SUPPORT //
62476 +
62477 +BOOLEAN RTMPCheckHt(
62478 + IN PRTMP_ADAPTER pAd,
62479 + IN UCHAR Wcid,
62480 + IN OUT HT_CAPABILITY_IE *pHtCapability,
62481 + IN OUT ADD_HT_INFO_IE *pAddHtInfo);
62482 +
62483 +VOID StaQuickResponeForRateUpExec(
62484 + IN PVOID SystemSpecific1,
62485 + IN PVOID FunctionContext,
62486 + IN PVOID SystemSpecific2,
62487 + IN PVOID SystemSpecific3);
62488 +
62489 +VOID AsicBbpTuning1(
62490 + IN PRTMP_ADAPTER pAd);
62491 +
62492 +VOID AsicBbpTuning2(
62493 + IN PRTMP_ADAPTER pAd);
62494 +
62495 +VOID RTMPUpdateMlmeRate(
62496 + IN PRTMP_ADAPTER pAd);
62497 +
62498 +CHAR RTMPMaxRssi(
62499 + IN PRTMP_ADAPTER pAd,
62500 + IN CHAR Rssi0,
62501 + IN CHAR Rssi1,
62502 + IN CHAR Rssi2);
62503 +
62504 +VOID AsicEvaluateRxAnt(
62505 + IN PRTMP_ADAPTER pAd);
62506 +
62507 +VOID AsicRxAntEvalTimeout(
62508 + IN PVOID SystemSpecific1,
62509 + IN PVOID FunctionContext,
62510 + IN PVOID SystemSpecific2,
62511 + IN PVOID SystemSpecific3);
62512 +
62513 +VOID APSDPeriodicExec(
62514 + IN PVOID SystemSpecific1,
62515 + IN PVOID FunctionContext,
62516 + IN PVOID SystemSpecific2,
62517 + IN PVOID SystemSpecific3);
62518 +
62519 +BOOLEAN RTMPCheckEntryEnableAutoRateSwitch(
62520 + IN PRTMP_ADAPTER pAd,
62521 + IN PMAC_TABLE_ENTRY pEntry);
62522 +
62523 +UCHAR RTMPStaFixedTxMode(
62524 + IN PRTMP_ADAPTER pAd,
62525 + IN PMAC_TABLE_ENTRY pEntry);
62526 +
62527 +VOID RTMPUpdateLegacyTxSetting(
62528 + UCHAR fixed_tx_mode,
62529 + PMAC_TABLE_ENTRY pEntry);
62530 +
62531 +BOOLEAN RTMPAutoRateSwitchCheck(
62532 + IN PRTMP_ADAPTER pAd);
62533 +
62534 +NDIS_STATUS MlmeInit(
62535 + IN PRTMP_ADAPTER pAd);
62536 +
62537 +VOID MlmeHandler(
62538 + IN PRTMP_ADAPTER pAd);
62539 +
62540 +VOID MlmeHalt(
62541 + IN PRTMP_ADAPTER pAd);
62542 +
62543 +VOID MlmeResetRalinkCounters(
62544 + IN PRTMP_ADAPTER pAd);
62545 +
62546 +VOID BuildChannelList(
62547 + IN PRTMP_ADAPTER pAd);
62548 +
62549 +UCHAR FirstChannel(
62550 + IN PRTMP_ADAPTER pAd);
62551 +
62552 +UCHAR NextChannel(
62553 + IN PRTMP_ADAPTER pAd,
62554 + IN UCHAR channel);
62555 +
62556 +VOID ChangeToCellPowerLimit(
62557 + IN PRTMP_ADAPTER pAd,
62558 + IN UCHAR AironetCellPowerLimit);
62559 +
62560 +VOID RaiseClock(
62561 + IN PRTMP_ADAPTER pAd,
62562 + IN UINT32 *x);
62563 +
62564 +VOID LowerClock(
62565 + IN PRTMP_ADAPTER pAd,
62566 + IN UINT32 *x);
62567 +
62568 +USHORT ShiftInBits(
62569 + IN PRTMP_ADAPTER pAd);
62570 +
62571 +VOID ShiftOutBits(
62572 + IN PRTMP_ADAPTER pAd,
62573 + IN USHORT data,
62574 + IN USHORT count);
62575 +
62576 +VOID EEpromCleanup(
62577 + IN PRTMP_ADAPTER pAd);
62578 +
62579 +VOID EWDS(
62580 + IN PRTMP_ADAPTER pAd);
62581 +
62582 +VOID EWEN(
62583 + IN PRTMP_ADAPTER pAd);
62584 +
62585 +USHORT RTMP_EEPROM_READ16(
62586 + IN PRTMP_ADAPTER pAd,
62587 + IN USHORT Offset);
62588 +
62589 +VOID RTMP_EEPROM_WRITE16(
62590 + IN PRTMP_ADAPTER pAd,
62591 + IN USHORT Offset,
62592 + IN USHORT Data);
62593 +
62594 +//
62595 +// Prototypes of function definition in rtmp_tkip.c
62596 +//
62597 +VOID RTMPInitTkipEngine(
62598 + IN PRTMP_ADAPTER pAd,
62599 + IN PUCHAR pTKey,
62600 + IN UCHAR KeyId,
62601 + IN PUCHAR pTA,
62602 + IN PUCHAR pMICKey,
62603 + IN PUCHAR pTSC,
62604 + OUT PULONG pIV16,
62605 + OUT PULONG pIV32);
62606 +
62607 +VOID RTMPInitMICEngine(
62608 + IN PRTMP_ADAPTER pAd,
62609 + IN PUCHAR pKey,
62610 + IN PUCHAR pDA,
62611 + IN PUCHAR pSA,
62612 + IN UCHAR UserPriority,
62613 + IN PUCHAR pMICKey);
62614 +
62615 +BOOLEAN RTMPTkipCompareMICValue(
62616 + IN PRTMP_ADAPTER pAd,
62617 + IN PUCHAR pSrc,
62618 + IN PUCHAR pDA,
62619 + IN PUCHAR pSA,
62620 + IN PUCHAR pMICKey,
62621 + IN UCHAR UserPriority,
62622 + IN UINT Len);
62623 +
62624 +VOID RTMPCalculateMICValue(
62625 + IN PRTMP_ADAPTER pAd,
62626 + IN PNDIS_PACKET pPacket,
62627 + IN PUCHAR pEncap,
62628 + IN PCIPHER_KEY pKey,
62629 + IN UCHAR apidx);
62630 +
62631 +BOOLEAN RTMPTkipCompareMICValueWithLLC(
62632 + IN PRTMP_ADAPTER pAd,
62633 + IN PUCHAR pLLC,
62634 + IN PUCHAR pSrc,
62635 + IN PUCHAR pDA,
62636 + IN PUCHAR pSA,
62637 + IN PUCHAR pMICKey,
62638 + IN UINT Len);
62639 +
62640 +VOID RTMPTkipAppendByte(
62641 + IN PTKIP_KEY_INFO pTkip,
62642 + IN UCHAR uChar);
62643 +
62644 +VOID RTMPTkipAppend(
62645 + IN PTKIP_KEY_INFO pTkip,
62646 + IN PUCHAR pSrc,
62647 + IN UINT nBytes);
62648 +
62649 +VOID RTMPTkipGetMIC(
62650 + IN PTKIP_KEY_INFO pTkip);
62651 +
62652 +BOOLEAN RTMPSoftDecryptTKIP(
62653 + IN PRTMP_ADAPTER pAd,
62654 + IN PUCHAR pData,
62655 + IN ULONG DataByteCnt,
62656 + IN UCHAR UserPriority,
62657 + IN PCIPHER_KEY pWpaKey);
62658 +
62659 +BOOLEAN RTMPSoftDecryptAES(
62660 + IN PRTMP_ADAPTER pAd,
62661 + IN PUCHAR pData,
62662 + IN ULONG DataByteCnt,
62663 + IN PCIPHER_KEY pWpaKey);
62664 +
62665 +//
62666 +// Prototypes of function definition in cmm_info.c
62667 +//
62668 +NDIS_STATUS RTMPWPARemoveKeyProc(
62669 + IN PRTMP_ADAPTER pAd,
62670 + IN PVOID pBuf);
62671 +
62672 +VOID RTMPWPARemoveAllKeys(
62673 + IN PRTMP_ADAPTER pAd);
62674 +
62675 +BOOLEAN RTMPCheckStrPrintAble(
62676 + IN CHAR *pInPutStr,
62677 + IN UCHAR strLen);
62678 +
62679 +VOID RTMPSetPhyMode(
62680 + IN PRTMP_ADAPTER pAd,
62681 + IN ULONG phymode);
62682 +
62683 +VOID RTMPUpdateHTIE(
62684 + IN RT_HT_CAPABILITY *pRtHt,
62685 + IN UCHAR *pMcsSet,
62686 + OUT HT_CAPABILITY_IE *pHtCapability,
62687 + OUT ADD_HT_INFO_IE *pAddHtInfo);
62688 +
62689 +VOID RTMPAddWcidAttributeEntry(
62690 + IN PRTMP_ADAPTER pAd,
62691 + IN UCHAR BssIdx,
62692 + IN UCHAR KeyIdx,
62693 + IN UCHAR CipherAlg,
62694 + IN MAC_TABLE_ENTRY *pEntry);
62695 +
62696 +CHAR *GetEncryptType(
62697 + CHAR enc);
62698 +
62699 +CHAR *GetAuthMode(
62700 + CHAR auth);
62701 +
62702 +VOID RTMPIoctlGetSiteSurvey(
62703 + IN PRTMP_ADAPTER pAdapter,
62704 + IN struct iwreq *wrq);
62705 +
62706 +VOID RTMPIoctlGetMacTable(
62707 + IN PRTMP_ADAPTER pAd,
62708 + IN struct iwreq *wrq);
62709 +
62710 +VOID RTMPIndicateWPA2Status(
62711 + IN PRTMP_ADAPTER pAdapter);
62712 +
62713 +VOID RTMPOPModeSwitching(
62714 + IN PRTMP_ADAPTER pAd);
62715 +
62716 +#ifdef CONFIG_STA_SUPPORT
62717 +VOID RTMPAddBSSIDCipher(
62718 + IN PRTMP_ADAPTER pAd,
62719 + IN UCHAR Aid,
62720 + IN PNDIS_802_11_KEY pKey,
62721 + IN UCHAR CipherAlg);
62722 +#endif // CONFIG_STA_SUPPORT //
62723 +
62724 +#ifdef DOT11_N_SUPPORT
62725 +VOID RTMPSetHT(
62726 + IN PRTMP_ADAPTER pAd,
62727 + IN OID_SET_HT_PHYMODE *pHTPhyMode);
62728 +
62729 +VOID RTMPSetIndividualHT(
62730 + IN PRTMP_ADAPTER pAd,
62731 + IN UCHAR apidx);
62732 +#endif // DOT11_N_SUPPORT //
62733 +
62734 +VOID RTMPSendWirelessEvent(
62735 + IN PRTMP_ADAPTER pAd,
62736 + IN USHORT Event_flag,
62737 + IN PUCHAR pAddr,
62738 + IN UCHAR BssIdx,
62739 + IN CHAR Rssi);
62740 +
62741 +VOID NICUpdateCntlCounters(
62742 + IN PRTMP_ADAPTER pAd,
62743 + IN PHEADER_802_11 pHeader,
62744 + IN UCHAR SubType,
62745 + IN PRXWI_STRUC pRxWI);
62746 +//
62747 +// prototype in wpa.c
62748 +//
62749 +BOOLEAN WpaMsgTypeSubst(
62750 + IN UCHAR EAPType,
62751 + OUT INT *MsgType);
62752 +
62753 +VOID WpaPskStateMachineInit(
62754 + IN PRTMP_ADAPTER pAd,
62755 + IN STATE_MACHINE *S,
62756 + OUT STATE_MACHINE_FUNC Trans[]);
62757 +
62758 +VOID WpaEAPOLKeyAction(
62759 + IN PRTMP_ADAPTER pAd,
62760 + IN MLME_QUEUE_ELEM *Elem);
62761 +
62762 +VOID WpaPairMsg1Action(
62763 + IN PRTMP_ADAPTER pAd,
62764 + IN MLME_QUEUE_ELEM *Elem);
62765 +
62766 +VOID WpaPairMsg3Action(
62767 + IN PRTMP_ADAPTER pAd,
62768 + IN MLME_QUEUE_ELEM *Elem);
62769 +
62770 +VOID WpaGroupMsg1Action(
62771 + IN PRTMP_ADAPTER pAd,
62772 + IN MLME_QUEUE_ELEM *Elem);
62773 +
62774 +VOID WpaMacHeaderInit(
62775 + IN PRTMP_ADAPTER pAd,
62776 + IN OUT PHEADER_802_11 pHdr80211,
62777 + IN UCHAR wep,
62778 + IN PUCHAR pAddr1);
62779 +
62780 +VOID Wpa2PairMsg1Action(
62781 + IN PRTMP_ADAPTER pAd,
62782 + IN MLME_QUEUE_ELEM *Elem);
62783 +
62784 +VOID Wpa2PairMsg3Action(
62785 + IN PRTMP_ADAPTER pAd,
62786 + IN MLME_QUEUE_ELEM *Elem);
62787 +
62788 +BOOLEAN ParseKeyData(
62789 + IN PRTMP_ADAPTER pAd,
62790 + IN PUCHAR pKeyData,
62791 + IN UCHAR KeyDataLen,
62792 + IN UCHAR bPairewise);
62793 +
62794 +VOID RTMPToWirelessSta(
62795 + IN PRTMP_ADAPTER pAd,
62796 + IN PUCHAR pHeader802_3,
62797 + IN UINT HdrLen,
62798 + IN PUCHAR pData,
62799 + IN UINT DataLen,
62800 + IN BOOLEAN is4wayFrame);
62801 +
62802 +VOID HMAC_SHA1(
62803 + IN UCHAR *text,
62804 + IN UINT text_len,
62805 + IN UCHAR *key,
62806 + IN UINT key_len,
62807 + IN UCHAR *digest);
62808 +
62809 +VOID PRF(
62810 + IN UCHAR *key,
62811 + IN INT key_len,
62812 + IN UCHAR *prefix,
62813 + IN INT prefix_len,
62814 + IN UCHAR *data,
62815 + IN INT data_len,
62816 + OUT UCHAR *output,
62817 + IN INT len);
62818 +
62819 +VOID CCKMPRF(
62820 + IN UCHAR *key,
62821 + IN INT key_len,
62822 + IN UCHAR *data,
62823 + IN INT data_len,
62824 + OUT UCHAR *output,
62825 + IN INT len);
62826 +
62827 +VOID WpaCountPTK(
62828 + IN PRTMP_ADAPTER pAd,
62829 + IN UCHAR *PMK,
62830 + IN UCHAR *ANonce,
62831 + IN UCHAR *AA,
62832 + IN UCHAR *SNonce,
62833 + IN UCHAR *SA,
62834 + OUT UCHAR *output,
62835 + IN UINT len);
62836 +
62837 +VOID GenRandom(
62838 + IN PRTMP_ADAPTER pAd,
62839 + IN UCHAR *macAddr,
62840 + OUT UCHAR *random);
62841 +
62842 +//
62843 +// prototype in aironet.c
62844 +//
62845 +VOID AironetStateMachineInit(
62846 + IN PRTMP_ADAPTER pAd,
62847 + IN STATE_MACHINE *S,
62848 + OUT STATE_MACHINE_FUNC Trans[]);
62849 +
62850 +VOID AironetMsgAction(
62851 + IN PRTMP_ADAPTER pAd,
62852 + IN MLME_QUEUE_ELEM *Elem);
62853 +
62854 +VOID AironetRequestAction(
62855 + IN PRTMP_ADAPTER pAd,
62856 + IN MLME_QUEUE_ELEM *Elem);
62857 +
62858 +VOID ChannelLoadRequestAction(
62859 + IN PRTMP_ADAPTER pAd,
62860 + IN UCHAR Index);
62861 +
62862 +VOID NoiseHistRequestAction(
62863 + IN PRTMP_ADAPTER pAd,
62864 + IN UCHAR Index);
62865 +
62866 +VOID BeaconRequestAction(
62867 + IN PRTMP_ADAPTER pAd,
62868 + IN UCHAR Index);
62869 +
62870 +VOID AironetReportAction(
62871 + IN PRTMP_ADAPTER pAd,
62872 + IN MLME_QUEUE_ELEM *Elem);
62873 +
62874 +VOID ChannelLoadReportAction(
62875 + IN PRTMP_ADAPTER pAd,
62876 + IN UCHAR Index);
62877 +
62878 +VOID NoiseHistReportAction(
62879 + IN PRTMP_ADAPTER pAd,
62880 + IN UCHAR Index);
62881 +
62882 +VOID AironetFinalReportAction(
62883 + IN PRTMP_ADAPTER pAd);
62884 +
62885 +VOID BeaconReportAction(
62886 + IN PRTMP_ADAPTER pAd,
62887 + IN UCHAR Index);
62888 +
62889 +VOID AironetAddBeaconReport(
62890 + IN PRTMP_ADAPTER pAd,
62891 + IN ULONG Index,
62892 + IN PMLME_QUEUE_ELEM pElem);
62893 +
62894 +VOID AironetCreateBeaconReportFromBssTable(
62895 + IN PRTMP_ADAPTER pAd);
62896 +
62897 +VOID DBGPRINT_TX_RING(
62898 + IN PRTMP_ADAPTER pAd,
62899 + IN UCHAR QueIdx);
62900 +
62901 +VOID DBGPRINT_RX_RING(
62902 + IN PRTMP_ADAPTER pAd);
62903 +
62904 +CHAR ConvertToRssi(
62905 + IN PRTMP_ADAPTER pAd,
62906 + IN CHAR Rssi,
62907 + IN UCHAR RssiNumber);
62908 +
62909 +
62910 +#ifdef DOT11N_DRAFT3
62911 +VOID BuildEffectedChannelList(
62912 + IN PRTMP_ADAPTER pAd);
62913 +#endif // DOT11N_DRAFT3 //
62914 +
62915 +
62916 +VOID APAsicEvaluateRxAnt(
62917 + IN PRTMP_ADAPTER pAd);
62918 +
62919 +
62920 +VOID APAsicRxAntEvalTimeout(
62921 + IN PRTMP_ADAPTER pAd);
62922 +
62923 +//
62924 +// function prototype in cmm_wpa.c
62925 +//
62926 +BOOLEAN RTMPCheckWPAframe(
62927 + IN PRTMP_ADAPTER pAd,
62928 + IN PMAC_TABLE_ENTRY pEntry,
62929 + IN PUCHAR pData,
62930 + IN ULONG DataByteCount,
62931 + IN UCHAR FromWhichBSSID);
62932 +
62933 +VOID AES_GTK_KEY_UNWRAP(
62934 + IN UCHAR *key,
62935 + OUT UCHAR *plaintext,
62936 + IN UCHAR c_len,
62937 + IN UCHAR *ciphertext);
62938 +
62939 +BOOLEAN RTMPCheckRSNIE(
62940 + IN PRTMP_ADAPTER pAd,
62941 + IN PUCHAR pData,
62942 + IN UCHAR DataLen,
62943 + IN MAC_TABLE_ENTRY *pEntry,
62944 + OUT UCHAR *Offset);
62945 +
62946 +BOOLEAN RTMPParseEapolKeyData(
62947 + IN PRTMP_ADAPTER pAd,
62948 + IN PUCHAR pKeyData,
62949 + IN UCHAR KeyDataLen,
62950 + IN UCHAR GroupKeyIndex,
62951 + IN UCHAR MsgType,
62952 + IN BOOLEAN bWPA2,
62953 + IN MAC_TABLE_ENTRY *pEntry);
62954 +
62955 +VOID ConstructEapolMsg(
62956 + IN PRTMP_ADAPTER pAd,
62957 + IN UCHAR PeerAuthMode,
62958 + IN UCHAR PeerWepStatus,
62959 + IN UCHAR MyGroupKeyWepStatus,
62960 + IN UCHAR MsgType,
62961 + IN UCHAR DefaultKeyIdx,
62962 + IN UCHAR *ReplayCounter,
62963 + IN UCHAR *KeyNonce,
62964 + IN UCHAR *TxRSC,
62965 + IN UCHAR *PTK,
62966 + IN UCHAR *GTK,
62967 + IN UCHAR *RSNIE,
62968 + IN UCHAR RSNIE_Len,
62969 + OUT PEAPOL_PACKET pMsg);
62970 +
62971 +VOID CalculateMIC(
62972 + IN PRTMP_ADAPTER pAd,
62973 + IN UCHAR PeerWepStatus,
62974 + IN UCHAR *PTK,
62975 + OUT PEAPOL_PACKET pMsg);
62976 +
62977 +NDIS_STATUS RTMPSoftDecryptBroadCastData(
62978 + IN PRTMP_ADAPTER pAd,
62979 + IN RX_BLK *pRxBlk,
62980 + IN NDIS_802_11_ENCRYPTION_STATUS GroupCipher,
62981 + IN PCIPHER_KEY pShard_key);
62982 +
62983 +VOID ConstructEapolKeyData(
62984 + IN PRTMP_ADAPTER pAd,
62985 + IN UCHAR PeerAuthMode,
62986 + IN UCHAR PeerWepStatus,
62987 + IN UCHAR GroupKeyWepStatus,
62988 + IN UCHAR MsgType,
62989 + IN UCHAR DefaultKeyIdx,
62990 + IN BOOLEAN bWPA2Capable,
62991 + IN UCHAR *PTK,
62992 + IN UCHAR *GTK,
62993 + IN UCHAR *RSNIE,
62994 + IN UCHAR RSNIE_LEN,
62995 + OUT PEAPOL_PACKET pMsg);
62996 +
62997 +VOID RTMPMakeRSNIE(
62998 + IN PRTMP_ADAPTER pAd,
62999 + IN UINT AuthMode,
63000 + IN UINT WepStatus,
63001 + IN UCHAR apidx);
63002 +
63003 +//
63004 +// function prototype in ap_wpa.c
63005 +//
63006 +
63007 +BOOLEAN APWpaMsgTypeSubst(
63008 + IN UCHAR EAPType,
63009 + OUT INT *MsgType) ;
63010 +
63011 +MAC_TABLE_ENTRY *PACInquiry(
63012 + IN PRTMP_ADAPTER pAd,
63013 + IN ULONG Wcid);
63014 +
63015 +BOOLEAN RTMPCheckMcast(
63016 + IN PRTMP_ADAPTER pAd,
63017 + IN PEID_STRUCT eid_ptr,
63018 + IN MAC_TABLE_ENTRY *pEntry);
63019 +
63020 +BOOLEAN RTMPCheckUcast(
63021 + IN PRTMP_ADAPTER pAd,
63022 + IN PEID_STRUCT eid_ptr,
63023 + IN MAC_TABLE_ENTRY *pEntry);
63024 +
63025 +BOOLEAN RTMPCheckAUTH(
63026 + IN PRTMP_ADAPTER pAd,
63027 + IN PEID_STRUCT eid_ptr,
63028 + IN MAC_TABLE_ENTRY *pEntry);
63029 +
63030 +VOID WPAStart4WayHS(
63031 + IN PRTMP_ADAPTER pAd,
63032 + IN MAC_TABLE_ENTRY *pEntry,
63033 + IN ULONG TimeInterval);
63034 +
63035 +VOID WPAStart2WayGroupHS(
63036 + IN PRTMP_ADAPTER pAd,
63037 + IN MAC_TABLE_ENTRY *pEntry);
63038 +
63039 +VOID APWpaEAPPacketAction(
63040 + IN PRTMP_ADAPTER pAd,
63041 + IN MLME_QUEUE_ELEM *Elem);
63042 +
63043 +VOID APWpaEAPOLStartAction(
63044 + IN PRTMP_ADAPTER pAd,
63045 + IN MLME_QUEUE_ELEM *Elem);
63046 +
63047 +VOID APWpaEAPOLLogoffAction(
63048 + IN PRTMP_ADAPTER pAd,
63049 + IN MLME_QUEUE_ELEM *Elem);
63050 +
63051 +VOID APWpaEAPOLKeyAction(
63052 + IN PRTMP_ADAPTER pAd,
63053 + IN MLME_QUEUE_ELEM *Elem);
63054 +
63055 +VOID APWpaEAPOLASFAlertAction(
63056 + IN PRTMP_ADAPTER pAd,
63057 + IN MLME_QUEUE_ELEM *Elem);
63058 +
63059 +VOID HandleCounterMeasure(
63060 + IN PRTMP_ADAPTER pAd,
63061 + IN MAC_TABLE_ENTRY *pEntry);
63062 +
63063 +VOID PeerPairMsg2Action(
63064 + IN PRTMP_ADAPTER pAd,
63065 + IN MAC_TABLE_ENTRY *pEntry,
63066 + IN MLME_QUEUE_ELEM *Elem);
63067 +
63068 +VOID PeerPairMsg4Action(
63069 + IN PRTMP_ADAPTER pAd,
63070 + IN MAC_TABLE_ENTRY *pEntry,
63071 + IN MLME_QUEUE_ELEM *Elem);
63072 +
63073 +VOID CMTimerExec(
63074 + IN PVOID SystemSpecific1,
63075 + IN PVOID FunctionContext,
63076 + IN PVOID SystemSpecific2,
63077 + IN PVOID SystemSpecific3);
63078 +
63079 +VOID WPARetryExec(
63080 + IN PVOID SystemSpecific1,
63081 + IN PVOID FunctionContext,
63082 + IN PVOID SystemSpecific2,
63083 + IN PVOID SystemSpecific3);
63084 +
63085 +VOID EnqueueStartForPSKExec(
63086 + IN PVOID SystemSpecific1,
63087 + IN PVOID FunctionContext,
63088 + IN PVOID SystemSpecific2,
63089 + IN PVOID SystemSpecific3);
63090 +
63091 +VOID RTMPHandleSTAKey(
63092 + IN PRTMP_ADAPTER pAdapter,
63093 + IN MAC_TABLE_ENTRY *pEntry,
63094 + IN MLME_QUEUE_ELEM *Elem);
63095 +
63096 +VOID PeerGroupMsg2Action(
63097 + IN PRTMP_ADAPTER pAd,
63098 + IN PMAC_TABLE_ENTRY pEntry,
63099 + IN VOID *Msg,
63100 + IN UINT MsgLen);
63101 +
63102 +VOID PairDisAssocAction(
63103 + IN PRTMP_ADAPTER pAd,
63104 + IN PMAC_TABLE_ENTRY pEntry,
63105 + IN USHORT Reason);
63106 +
63107 +VOID MlmeDeAuthAction(
63108 + IN PRTMP_ADAPTER pAd,
63109 + IN PMAC_TABLE_ENTRY pEntry,
63110 + IN USHORT Reason);
63111 +
63112 +VOID GREKEYPeriodicExec(
63113 + IN PVOID SystemSpecific1,
63114 + IN PVOID FunctionContext,
63115 + IN PVOID SystemSpecific2,
63116 + IN PVOID SystemSpecific3);
63117 +
63118 +VOID CountGTK(
63119 + IN UCHAR *PMK,
63120 + IN UCHAR *GNonce,
63121 + IN UCHAR *AA,
63122 + OUT UCHAR *output,
63123 + IN UINT len);
63124 +
63125 +VOID GetSmall(
63126 + IN PVOID pSrc1,
63127 + IN PVOID pSrc2,
63128 + OUT PUCHAR out,
63129 + IN ULONG Length);
63130 +
63131 +VOID GetLarge(
63132 + IN PVOID pSrc1,
63133 + IN PVOID pSrc2,
63134 + OUT PUCHAR out,
63135 + IN ULONG Length);
63136 +
63137 +VOID APGenRandom(
63138 + IN PRTMP_ADAPTER pAd,
63139 + OUT UCHAR *random);
63140 +
63141 +VOID AES_GTK_KEY_WRAP(
63142 + IN UCHAR *key,
63143 + IN UCHAR *plaintext,
63144 + IN UCHAR p_len,
63145 + OUT UCHAR *ciphertext);
63146 +
63147 +VOID WpaSend(
63148 + IN PRTMP_ADAPTER pAdapter,
63149 + IN PUCHAR pPacket,
63150 + IN ULONG Len);
63151 +
63152 +VOID APToWirelessSta(
63153 + IN PRTMP_ADAPTER pAd,
63154 + IN MAC_TABLE_ENTRY *pEntry,
63155 + IN PUCHAR pHeader802_3,
63156 + IN UINT HdrLen,
63157 + IN PUCHAR pData,
63158 + IN UINT DataLen,
63159 + IN BOOLEAN bClearFrame);
63160 +
63161 +VOID RTMPAddPMKIDCache(
63162 + IN PRTMP_ADAPTER pAd,
63163 + IN INT apidx,
63164 + IN PUCHAR pAddr,
63165 + IN UCHAR *PMKID,
63166 + IN UCHAR *PMK);
63167 +
63168 +INT RTMPSearchPMKIDCache(
63169 + IN PRTMP_ADAPTER pAd,
63170 + IN INT apidx,
63171 + IN PUCHAR pAddr);
63172 +
63173 +VOID RTMPDeletePMKIDCache(
63174 + IN PRTMP_ADAPTER pAd,
63175 + IN INT apidx,
63176 + IN INT idx);
63177 +
63178 +VOID RTMPMaintainPMKIDCache(
63179 + IN PRTMP_ADAPTER pAd);
63180 +
63181 +VOID RTMPSendTriggerFrame(
63182 + IN PRTMP_ADAPTER pAd,
63183 + IN PVOID pBuffer,
63184 + IN ULONG Length,
63185 + IN UCHAR TxRate,
63186 + IN BOOLEAN bQosNull);
63187 +
63188 +
63189 +/* timeout -- ms */
63190 +VOID RTMP_SetPeriodicTimer(
63191 + IN NDIS_MINIPORT_TIMER *pTimer,
63192 + IN unsigned long timeout);
63193 +
63194 +VOID RTMP_OS_Init_Timer(
63195 + IN PRTMP_ADAPTER pAd,
63196 + IN NDIS_MINIPORT_TIMER *pTimer,
63197 + IN TIMER_FUNCTION function,
63198 + IN PVOID data);
63199 +
63200 +VOID RTMP_OS_Add_Timer(
63201 + IN NDIS_MINIPORT_TIMER *pTimer,
63202 + IN unsigned long timeout);
63203 +
63204 +VOID RTMP_OS_Mod_Timer(
63205 + IN NDIS_MINIPORT_TIMER *pTimer,
63206 + IN unsigned long timeout);
63207 +
63208 +
63209 +VOID RTMP_OS_Del_Timer(
63210 + IN NDIS_MINIPORT_TIMER *pTimer,
63211 + OUT BOOLEAN *pCancelled);
63212 +
63213 +
63214 +VOID RTMP_OS_Release_Packet(
63215 + IN PRTMP_ADAPTER pAd,
63216 + IN PQUEUE_ENTRY pEntry);
63217 +
63218 +VOID RTMPusecDelay(
63219 + IN ULONG usec);
63220 +
63221 +NDIS_STATUS os_alloc_mem(
63222 + IN PRTMP_ADAPTER pAd,
63223 + OUT PUCHAR *mem,
63224 + IN ULONG size);
63225 +
63226 +NDIS_STATUS os_free_mem(
63227 + IN PRTMP_ADAPTER pAd,
63228 + IN PUCHAR mem);
63229 +
63230 +
63231 +void RTMP_AllocateSharedMemory(
63232 + IN PRTMP_ADAPTER pAd,
63233 + IN ULONG Length,
63234 + IN BOOLEAN Cached,
63235 + OUT PVOID *VirtualAddress,
63236 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress);
63237 +
63238 +VOID RTMPFreeTxRxRingMemory(
63239 + IN PRTMP_ADAPTER pAd);
63240 +
63241 +NDIS_STATUS AdapterBlockAllocateMemory(
63242 + IN PVOID handle,
63243 + OUT PVOID *ppAd);
63244 +
63245 +void RTMP_AllocateTxDescMemory(
63246 + IN PRTMP_ADAPTER pAd,
63247 + IN UINT Index,
63248 + IN ULONG Length,
63249 + IN BOOLEAN Cached,
63250 + OUT PVOID *VirtualAddress,
63251 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress);
63252 +
63253 +void RTMP_AllocateFirstTxBuffer(
63254 + IN PRTMP_ADAPTER pAd,
63255 + IN UINT Index,
63256 + IN ULONG Length,
63257 + IN BOOLEAN Cached,
63258 + OUT PVOID *VirtualAddress,
63259 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress);
63260 +
63261 +void RTMP_AllocateMgmtDescMemory(
63262 + IN PRTMP_ADAPTER pAd,
63263 + IN ULONG Length,
63264 + IN BOOLEAN Cached,
63265 + OUT PVOID *VirtualAddress,
63266 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress);
63267 +
63268 +void RTMP_AllocateRxDescMemory(
63269 + IN PRTMP_ADAPTER pAd,
63270 + IN ULONG Length,
63271 + IN BOOLEAN Cached,
63272 + OUT PVOID *VirtualAddress,
63273 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress);
63274 +
63275 +PNDIS_PACKET RTMP_AllocateRxPacketBuffer(
63276 + IN PRTMP_ADAPTER pAd,
63277 + IN ULONG Length,
63278 + IN BOOLEAN Cached,
63279 + OUT PVOID *VirtualAddress,
63280 + OUT PNDIS_PHYSICAL_ADDRESS PhysicalAddress);
63281 +
63282 +PNDIS_PACKET RTMP_AllocateTxPacketBuffer(
63283 + IN PRTMP_ADAPTER pAd,
63284 + IN ULONG Length,
63285 + IN BOOLEAN Cached,
63286 + OUT PVOID *VirtualAddress);
63287 +
63288 +PNDIS_PACKET RTMP_AllocateFragPacketBuffer(
63289 + IN PRTMP_ADAPTER pAd,
63290 + IN ULONG Length);
63291 +
63292 +void RTMP_QueryPacketInfo(
63293 + IN PNDIS_PACKET pPacket,
63294 + OUT PACKET_INFO *pPacketInfo,
63295 + OUT PUCHAR *pSrcBufVA,
63296 + OUT UINT *pSrcBufLen);
63297 +
63298 +void RTMP_QueryNextPacketInfo(
63299 + IN PNDIS_PACKET *ppPacket,
63300 + OUT PACKET_INFO *pPacketInfo,
63301 + OUT PUCHAR *pSrcBufVA,
63302 + OUT UINT *pSrcBufLen);
63303 +
63304 +
63305 +BOOLEAN RTMP_FillTxBlkInfo(
63306 + IN RTMP_ADAPTER *pAd,
63307 + IN TX_BLK *pTxBlk);
63308 +
63309 +
63310 +PRTMP_SCATTER_GATHER_LIST
63311 +rt_get_sg_list_from_packet(PNDIS_PACKET pPacket, RTMP_SCATTER_GATHER_LIST *sg);
63312 +
63313 +
63314 + void announce_802_3_packet(
63315 + IN PRTMP_ADAPTER pAd,
63316 + IN PNDIS_PACKET pPacket);
63317 +
63318 +
63319 +UINT BA_Reorder_AMSDU_Annnounce(
63320 + IN PRTMP_ADAPTER pAd,
63321 + IN PNDIS_PACKET pPacket);
63322 +
63323 +
63324 +UINT Handle_AMSDU_Packet(
63325 + IN PRTMP_ADAPTER pAd,
63326 + IN PUCHAR pData,
63327 + IN ULONG DataSize,
63328 + IN UCHAR FromWhichBSSID);
63329 +
63330 +
63331 +void convert_802_11_to_802_3_packet(
63332 + IN PRTMP_ADAPTER pAd,
63333 + IN PNDIS_PACKET pPacket,
63334 + IN PUCHAR p8023hdr,
63335 + IN PUCHAR pData,
63336 + IN ULONG DataSize,
63337 + IN UCHAR FromWhichBSSID);
63338 +
63339 +
63340 +PNET_DEV get_netdev_from_bssid(
63341 + IN PRTMP_ADAPTER pAd,
63342 + IN UCHAR FromWhichBSSID);
63343 +
63344 +
63345 +PNDIS_PACKET duplicate_pkt(
63346 + IN PRTMP_ADAPTER pAd,
63347 + IN PUCHAR pHeader802_3,
63348 + IN UINT HdrLen,
63349 + IN PUCHAR pData,
63350 + IN ULONG DataSize,
63351 + IN UCHAR FromWhichBSSID);
63352 +
63353 +
63354 +PNDIS_PACKET duplicate_pkt_with_TKIP_MIC(
63355 + IN PRTMP_ADAPTER pAd,
63356 + IN PNDIS_PACKET pOldPkt);
63357 +
63358 +PNDIS_PACKET duplicate_pkt_with_VLAN(
63359 + IN PRTMP_ADAPTER pAd,
63360 + IN PUCHAR pHeader802_3,
63361 + IN UINT HdrLen,
63362 + IN PUCHAR pData,
63363 + IN ULONG DataSize,
63364 + IN UCHAR FromWhichBSSID);
63365 +
63366 +PNDIS_PACKET duplicate_pkt_with_WPI(
63367 + IN PRTMP_ADAPTER pAd,
63368 + IN PNDIS_PACKET pPacket,
63369 + IN UINT32 ext_head_len,
63370 + IN UINT32 ext_tail_len);
63371 +
63372 +UCHAR VLAN_8023_Header_Copy(
63373 + IN PRTMP_ADAPTER pAd,
63374 + IN PUCHAR pHeader802_3,
63375 + IN UINT HdrLen,
63376 + OUT PUCHAR pData,
63377 + IN UCHAR FromWhichBSSID);
63378 +
63379 +#ifdef DOT11_N_SUPPORT
63380 +void ba_flush_reordering_timeout_mpdus(
63381 + IN PRTMP_ADAPTER pAd,
63382 + IN PBA_REC_ENTRY pBAEntry,
63383 + IN ULONG Now32);
63384 +
63385 +
63386 +VOID BAOriSessionSetUp(
63387 + IN PRTMP_ADAPTER pAd,
63388 + IN MAC_TABLE_ENTRY *pEntry,
63389 + IN UCHAR TID,
63390 + IN USHORT TimeOut,
63391 + IN ULONG DelayTime,
63392 + IN BOOLEAN isForced);
63393 +
63394 +VOID BASessionTearDownALL(
63395 + IN OUT PRTMP_ADAPTER pAd,
63396 + IN UCHAR Wcid);
63397 +#endif // DOT11_N_SUPPORT //
63398 +
63399 +BOOLEAN OS_Need_Clone_Packet(void);
63400 +
63401 +
63402 +VOID build_tx_packet(
63403 + IN PRTMP_ADAPTER pAd,
63404 + IN PNDIS_PACKET pPacket,
63405 + IN PUCHAR pFrame,
63406 + IN ULONG FrameLen);
63407 +
63408 +
63409 +VOID BAOriSessionTearDown(
63410 + IN OUT PRTMP_ADAPTER pAd,
63411 + IN UCHAR Wcid,
63412 + IN UCHAR TID,
63413 + IN BOOLEAN bPassive,
63414 + IN BOOLEAN bForceSend);
63415 +
63416 +VOID BARecSessionTearDown(
63417 + IN OUT PRTMP_ADAPTER pAd,
63418 + IN UCHAR Wcid,
63419 + IN UCHAR TID,
63420 + IN BOOLEAN bPassive);
63421 +
63422 +BOOLEAN ba_reordering_resource_init(PRTMP_ADAPTER pAd, int num);
63423 +void ba_reordering_resource_release(PRTMP_ADAPTER pAd);
63424 +
63425 +ULONG AutoChBssInsertEntry(
63426 + IN PRTMP_ADAPTER pAd,
63427 + IN PUCHAR pBssid,
63428 + IN CHAR Ssid[],
63429 + IN UCHAR SsidLen,
63430 + IN UCHAR ChannelNo,
63431 + IN CHAR Rssi);
63432 +
63433 +void AutoChBssTableInit(
63434 + IN PRTMP_ADAPTER pAd);
63435 +
63436 +void ChannelInfoInit(
63437 + IN PRTMP_ADAPTER pAd);
63438 +
63439 +void AutoChBssTableDestroy(
63440 + IN PRTMP_ADAPTER pAd);
63441 +
63442 +void ChannelInfoDestroy(
63443 + IN PRTMP_ADAPTER pAd);
63444 +
63445 +UCHAR New_ApAutoSelectChannel(
63446 + IN PRTMP_ADAPTER pAd);
63447 +
63448 +BOOLEAN rtstrmactohex(
63449 + IN char *s1,
63450 + IN char *s2);
63451 +
63452 +BOOLEAN rtstrcasecmp(
63453 + IN char *s1,
63454 + IN char *s2);
63455 +
63456 +char *rtstrstruncasecmp(
63457 + IN char *s1,
63458 + IN char *s2);
63459 +
63460 +char *rtstrstr(
63461 + IN const char * s1,
63462 + IN const char * s2);
63463 +
63464 +char *rstrtok(
63465 + IN char * s,
63466 + IN const char * ct);
63467 +
63468 +int rtinet_aton(
63469 + const char *cp,
63470 + unsigned int *addr);
63471 +
63472 +////////// common ioctl functions //////////
63473 +INT Set_DriverVersion_Proc(
63474 + IN PRTMP_ADAPTER pAd,
63475 + IN PUCHAR arg);
63476 +
63477 +INT Set_CountryRegion_Proc(
63478 + IN PRTMP_ADAPTER pAd,
63479 + IN PUCHAR arg);
63480 +
63481 +INT Set_CountryRegionABand_Proc(
63482 + IN PRTMP_ADAPTER pAd,
63483 + IN PUCHAR arg);
63484 +
63485 +INT Set_WirelessMode_Proc(
63486 + IN PRTMP_ADAPTER pAd,
63487 + IN PUCHAR arg);
63488 +
63489 +INT Set_Channel_Proc(
63490 + IN PRTMP_ADAPTER pAd,
63491 + IN PUCHAR arg);
63492 +
63493 +INT Set_ShortSlot_Proc(
63494 + IN PRTMP_ADAPTER pAd,
63495 + IN PUCHAR arg);
63496 +
63497 +INT Set_TxPower_Proc(
63498 + IN PRTMP_ADAPTER pAd,
63499 + IN PUCHAR arg);
63500 +
63501 +INT Set_BGProtection_Proc(
63502 + IN PRTMP_ADAPTER pAd,
63503 + IN PUCHAR arg);
63504 +
63505 +INT Set_TxPreamble_Proc(
63506 + IN PRTMP_ADAPTER pAd,
63507 + IN PUCHAR arg);
63508 +
63509 +INT Set_RTSThreshold_Proc(
63510 + IN PRTMP_ADAPTER pAd,
63511 + IN PUCHAR arg);
63512 +
63513 +INT Set_FragThreshold_Proc(
63514 + IN PRTMP_ADAPTER pAd,
63515 + IN PUCHAR arg);
63516 +
63517 +INT Set_TxBurst_Proc(
63518 + IN PRTMP_ADAPTER pAd,
63519 + IN PUCHAR arg);
63520 +
63521 +#ifdef AGGREGATION_SUPPORT
63522 +INT Set_PktAggregate_Proc(
63523 + IN PRTMP_ADAPTER pAd,
63524 + IN PUCHAR arg);
63525 +#endif
63526 +
63527 +INT Set_IEEE80211H_Proc(
63528 + IN PRTMP_ADAPTER pAd,
63529 + IN PUCHAR arg);
63530 +
63531 +#ifdef DBG
63532 +INT Set_Debug_Proc(
63533 + IN PRTMP_ADAPTER pAd,
63534 + IN PUCHAR arg);
63535 +#endif
63536 +
63537 +INT Show_DescInfo_Proc(
63538 + IN PRTMP_ADAPTER pAd,
63539 + IN PUCHAR arg);
63540 +
63541 +INT Set_ResetStatCounter_Proc(
63542 + IN PRTMP_ADAPTER pAd,
63543 + IN PUCHAR arg);
63544 +
63545 +#ifdef DOT11_N_SUPPORT
63546 +INT Set_BASetup_Proc(
63547 + IN PRTMP_ADAPTER pAd,
63548 + IN PUCHAR arg);
63549 +
63550 +INT Set_BADecline_Proc(
63551 + IN PRTMP_ADAPTER pAd,
63552 + IN PUCHAR arg);
63553 +
63554 +INT Set_BAOriTearDown_Proc(
63555 + IN PRTMP_ADAPTER pAd,
63556 + IN PUCHAR arg);
63557 +
63558 +INT Set_BARecTearDown_Proc(
63559 + IN PRTMP_ADAPTER pAd,
63560 + IN PUCHAR arg);
63561 +
63562 +INT Set_HtBw_Proc(
63563 + IN PRTMP_ADAPTER pAd,
63564 + IN PUCHAR arg);
63565 +
63566 +INT Set_HtMcs_Proc(
63567 + IN PRTMP_ADAPTER pAd,
63568 + IN PUCHAR arg);
63569 +
63570 +INT Set_HtGi_Proc(
63571 + IN PRTMP_ADAPTER pAd,
63572 + IN PUCHAR arg);
63573 +
63574 +INT Set_HtOpMode_Proc(
63575 + IN PRTMP_ADAPTER pAd,
63576 + IN PUCHAR arg);
63577 +
63578 +INT Set_HtStbc_Proc(
63579 + IN PRTMP_ADAPTER pAd,
63580 + IN PUCHAR arg);
63581 +
63582 +INT Set_HtHtc_Proc(
63583 + IN PRTMP_ADAPTER pAd,
63584 + IN PUCHAR arg);
63585 +
63586 +INT Set_HtExtcha_Proc(
63587 + IN PRTMP_ADAPTER pAd,
63588 + IN PUCHAR arg);
63589 +
63590 +INT Set_HtMpduDensity_Proc(
63591 + IN PRTMP_ADAPTER pAd,
63592 + IN PUCHAR arg);
63593 +
63594 +INT Set_HtBaWinSize_Proc(
63595 + IN PRTMP_ADAPTER pAd,
63596 + IN PUCHAR arg);
63597 +
63598 +INT Set_HtRdg_Proc(
63599 + IN PRTMP_ADAPTER pAd,
63600 + IN PUCHAR arg);
63601 +
63602 +INT Set_HtLinkAdapt_Proc(
63603 + IN PRTMP_ADAPTER pAd,
63604 + IN PUCHAR arg);
63605 +
63606 +INT Set_HtAmsdu_Proc(
63607 + IN PRTMP_ADAPTER pAd,
63608 + IN PUCHAR arg);
63609 +
63610 +INT Set_HtAutoBa_Proc(
63611 + IN PRTMP_ADAPTER pAd,
63612 + IN PUCHAR arg);
63613 +
63614 +INT Set_HtProtect_Proc(
63615 + IN PRTMP_ADAPTER pAd,
63616 + IN PUCHAR arg);
63617 +
63618 +INT Set_HtMimoPs_Proc(
63619 + IN PRTMP_ADAPTER pAd,
63620 + IN PUCHAR arg);
63621 +
63622 +
63623 +INT Set_ForceShortGI_Proc(
63624 + IN PRTMP_ADAPTER pAd,
63625 + IN PUCHAR arg);
63626 +
63627 +INT Set_ForceGF_Proc(
63628 + IN PRTMP_ADAPTER pAd,
63629 + IN PUCHAR arg);
63630 +
63631 +INT SetCommonHT(
63632 + IN PRTMP_ADAPTER pAd);
63633 +
63634 +INT Set_SendPSMPAction_Proc(
63635 + IN PRTMP_ADAPTER pAd,
63636 + IN PUCHAR arg);
63637 +
63638 +INT Set_HtMIMOPSmode_Proc(
63639 + IN PRTMP_ADAPTER pAd,
63640 + IN PUCHAR arg);
63641 +
63642 +
63643 +INT Set_HtTxBASize_Proc(
63644 + IN PRTMP_ADAPTER pAd,
63645 + IN PUCHAR arg);
63646 +#endif // DOT11_N_SUPPORT //
63647 +
63648 +
63649 +
63650 +#ifdef CONFIG_STA_SUPPORT
63651 +//Dls , kathy
63652 +VOID RTMPSendDLSTearDownFrame(
63653 + IN PRTMP_ADAPTER pAd,
63654 + IN PUCHAR pDA);
63655 +
63656 +#ifdef DOT11_N_SUPPORT
63657 +//Block ACK
63658 +VOID QueryBATABLE(
63659 + IN PRTMP_ADAPTER pAd,
63660 + OUT PQUERYBA_TABLE pBAT);
63661 +#endif // DOT11_N_SUPPORT //
63662 +
63663 +#ifdef WPA_SUPPLICANT_SUPPORT
63664 +INT WpaCheckEapCode(
63665 + IN PRTMP_ADAPTER pAd,
63666 + IN PUCHAR pFrame,
63667 + IN USHORT FrameLen,
63668 + IN USHORT OffSet);
63669 +
63670 +VOID WpaSendMicFailureToWpaSupplicant(
63671 + IN PRTMP_ADAPTER pAd,
63672 + IN BOOLEAN bUnicast);
63673 +
63674 +VOID SendAssocIEsToWpaSupplicant(
63675 + IN PRTMP_ADAPTER pAd);
63676 +#endif // WPA_SUPPLICANT_SUPPORT //
63677 +
63678 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
63679 +int wext_notify_event_assoc(
63680 + IN RTMP_ADAPTER *pAd);
63681 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
63682 +
63683 +#endif // CONFIG_STA_SUPPORT //
63684 +
63685 +
63686 +
63687 +#ifdef DOT11_N_SUPPORT
63688 +VOID Handle_BSS_Width_Trigger_Events(
63689 + IN PRTMP_ADAPTER pAd);
63690 +
63691 +void build_ext_channel_switch_ie(
63692 + IN PRTMP_ADAPTER pAd,
63693 + IN HT_EXT_CHANNEL_SWITCH_ANNOUNCEMENT_IE *pIE);
63694 +#endif // DOT11_N_SUPPORT //
63695 +
63696 +
63697 +BOOLEAN APRxDoneInterruptHandle(
63698 + IN PRTMP_ADAPTER pAd);
63699 +
63700 +BOOLEAN STARxDoneInterruptHandle(
63701 + IN PRTMP_ADAPTER pAd,
63702 + IN BOOLEAN argc);
63703 +
63704 +#ifdef DOT11_N_SUPPORT
63705 +// AMPDU packet indication
63706 +VOID Indicate_AMPDU_Packet(
63707 + IN PRTMP_ADAPTER pAd,
63708 + IN RX_BLK *pRxBlk,
63709 + IN UCHAR FromWhichBSSID);
63710 +
63711 +// AMSDU packet indication
63712 +VOID Indicate_AMSDU_Packet(
63713 + IN PRTMP_ADAPTER pAd,
63714 + IN RX_BLK *pRxBlk,
63715 + IN UCHAR FromWhichBSSID);
63716 +#endif // DOT11_N_SUPPORT //
63717 +
63718 +// Normal legacy Rx packet indication
63719 +VOID Indicate_Legacy_Packet(
63720 + IN PRTMP_ADAPTER pAd,
63721 + IN RX_BLK *pRxBlk,
63722 + IN UCHAR FromWhichBSSID);
63723 +
63724 +VOID Indicate_EAPOL_Packet(
63725 + IN PRTMP_ADAPTER pAd,
63726 + IN RX_BLK *pRxBlk,
63727 + IN UCHAR FromWhichBSSID);
63728 +
63729 +void update_os_packet_info(
63730 + IN PRTMP_ADAPTER pAd,
63731 + IN RX_BLK *pRxBlk,
63732 + IN UCHAR FromWhichBSSID);
63733 +
63734 +void wlan_802_11_to_802_3_packet(
63735 + IN PRTMP_ADAPTER pAd,
63736 + IN RX_BLK *pRxBlk,
63737 + IN PUCHAR pHeader802_3,
63738 + IN UCHAR FromWhichBSSID);
63739 +
63740 +UINT deaggregate_AMSDU_announce(
63741 + IN PRTMP_ADAPTER pAd,
63742 + PNDIS_PACKET pPacket,
63743 + IN PUCHAR pData,
63744 + IN ULONG DataSize);
63745 +
63746 +
63747 +#ifdef CONFIG_STA_SUPPORT
63748 +// remove LLC and get 802_3 Header
63749 +#define RTMP_802_11_REMOVE_LLC_AND_CONVERT_TO_802_3(_pRxBlk, _pHeader802_3) \
63750 +{ \
63751 + PUCHAR _pRemovedLLCSNAP = NULL, _pDA, _pSA; \
63752 + \
63753 + if (RX_BLK_TEST_FLAG(_pRxBlk, fRX_MESH)) \
63754 + { \
63755 + _pDA = _pRxBlk->pHeader->Addr3; \
63756 + _pSA = (PUCHAR)_pRxBlk->pHeader + sizeof(HEADER_802_11); \
63757 + } \
63758 + else \
63759 + { \
63760 + if (RX_BLK_TEST_FLAG(_pRxBlk, fRX_INFRA)) \
63761 + { \
63762 + _pDA = _pRxBlk->pHeader->Addr1; \
63763 + if (RX_BLK_TEST_FLAG(_pRxBlk, fRX_DLS)) \
63764 + _pSA = _pRxBlk->pHeader->Addr2; \
63765 + else \
63766 + _pSA = _pRxBlk->pHeader->Addr3; \
63767 + } \
63768 + else \
63769 + { \
63770 + _pDA = _pRxBlk->pHeader->Addr1; \
63771 + _pSA = _pRxBlk->pHeader->Addr2; \
63772 + } \
63773 + } \
63774 + \
63775 + CONVERT_TO_802_3(_pHeader802_3, _pDA, _pSA, _pRxBlk->pData, \
63776 + _pRxBlk->DataSize, _pRemovedLLCSNAP); \
63777 +}
63778 +#endif // CONFIG_STA_SUPPORT //
63779 +
63780 +
63781 +BOOLEAN APFowardWirelessStaToWirelessSta(
63782 + IN PRTMP_ADAPTER pAd,
63783 + IN PNDIS_PACKET pPacket,
63784 + IN ULONG FromWhichBSSID);
63785 +
63786 +VOID Announce_or_Forward_802_3_Packet(
63787 + IN PRTMP_ADAPTER pAd,
63788 + IN PNDIS_PACKET pPacket,
63789 + IN UCHAR FromWhichBSSID);
63790 +
63791 +VOID Sta_Announce_or_Forward_802_3_Packet(
63792 + IN PRTMP_ADAPTER pAd,
63793 + IN PNDIS_PACKET pPacket,
63794 + IN UCHAR FromWhichBSSID);
63795 +
63796 +
63797 +#ifdef CONFIG_STA_SUPPORT
63798 +#define ANNOUNCE_OR_FORWARD_802_3_PACKET(_pAd, _pPacket, _FromWhichBSS)\
63799 + Sta_Announce_or_Forward_802_3_Packet(_pAd, _pPacket, _FromWhichBSS);
63800 + //announce_802_3_packet(_pAd, _pPacket);
63801 +#endif // CONFIG_STA_SUPPORT //
63802 +
63803 +
63804 +PNDIS_PACKET DuplicatePacket(
63805 + IN PRTMP_ADAPTER pAd,
63806 + IN PNDIS_PACKET pPacket,
63807 + IN UCHAR FromWhichBSSID);
63808 +
63809 +
63810 +PNDIS_PACKET ClonePacket(
63811 + IN PRTMP_ADAPTER pAd,
63812 + IN PNDIS_PACKET pPacket,
63813 + IN PUCHAR pData,
63814 + IN ULONG DataSize);
63815 +
63816 +
63817 +// Normal, AMPDU or AMSDU
63818 +VOID CmmRxnonRalinkFrameIndicate(
63819 + IN PRTMP_ADAPTER pAd,
63820 + IN RX_BLK *pRxBlk,
63821 + IN UCHAR FromWhichBSSID);
63822 +
63823 +VOID CmmRxRalinkFrameIndicate(
63824 + IN PRTMP_ADAPTER pAd,
63825 + IN MAC_TABLE_ENTRY *pEntry,
63826 + IN RX_BLK *pRxBlk,
63827 + IN UCHAR FromWhichBSSID);
63828 +
63829 +VOID Update_Rssi_Sample(
63830 + IN PRTMP_ADAPTER pAd,
63831 + IN RSSI_SAMPLE *pRssi,
63832 + IN PRXWI_STRUC pRxWI);
63833 +
63834 +PNDIS_PACKET GetPacketFromRxRing(
63835 + IN PRTMP_ADAPTER pAd,
63836 + OUT PRT28XX_RXD_STRUC pSaveRxD,
63837 + OUT BOOLEAN *pbReschedule,
63838 + IN OUT UINT32 *pRxPending);
63839 +
63840 +PNDIS_PACKET RTMPDeFragmentDataFrame(
63841 + IN PRTMP_ADAPTER pAd,
63842 + IN RX_BLK *pRxBlk);
63843 +
63844 +////////////////////////////////////////
63845 +
63846 +
63847 +
63848 +
63849 +
63850 +#ifdef SNMP_SUPPORT
63851 +//for snmp , kathy
63852 +typedef struct _DefaultKeyIdxValue
63853 +{
63854 + UCHAR KeyIdx;
63855 + UCHAR Value[16];
63856 +} DefaultKeyIdxValue, *PDefaultKeyIdxValue;
63857 +#endif
63858 +
63859 +
63860 +#ifdef CONFIG_STA_SUPPORT
63861 +enum {
63862 + DIDmsg_lnxind_wlansniffrm = 0x00000044,
63863 + DIDmsg_lnxind_wlansniffrm_hosttime = 0x00010044,
63864 + DIDmsg_lnxind_wlansniffrm_mactime = 0x00020044,
63865 + DIDmsg_lnxind_wlansniffrm_channel = 0x00030044,
63866 + DIDmsg_lnxind_wlansniffrm_rssi = 0x00040044,
63867 + DIDmsg_lnxind_wlansniffrm_sq = 0x00050044,
63868 + DIDmsg_lnxind_wlansniffrm_signal = 0x00060044,
63869 + DIDmsg_lnxind_wlansniffrm_noise = 0x00070044,
63870 + DIDmsg_lnxind_wlansniffrm_rate = 0x00080044,
63871 + DIDmsg_lnxind_wlansniffrm_istx = 0x00090044,
63872 + DIDmsg_lnxind_wlansniffrm_frmlen = 0x000A0044
63873 +};
63874 +enum {
63875 + P80211ENUM_msgitem_status_no_value = 0x00
63876 +};
63877 +enum {
63878 + P80211ENUM_truth_false = 0x00,
63879 + P80211ENUM_truth_true = 0x01
63880 +};
63881 +
63882 +/* Definition from madwifi */
63883 +typedef struct {
63884 + UINT32 did;
63885 + UINT16 status;
63886 + UINT16 len;
63887 + UINT32 data;
63888 +} p80211item_uint32_t;
63889 +
63890 +typedef struct {
63891 + UINT32 msgcode;
63892 + UINT32 msglen;
63893 +#define WLAN_DEVNAMELEN_MAX 16
63894 + UINT8 devname[WLAN_DEVNAMELEN_MAX];
63895 + p80211item_uint32_t hosttime;
63896 + p80211item_uint32_t mactime;
63897 + p80211item_uint32_t channel;
63898 + p80211item_uint32_t rssi;
63899 + p80211item_uint32_t sq;
63900 + p80211item_uint32_t signal;
63901 + p80211item_uint32_t noise;
63902 + p80211item_uint32_t rate;
63903 + p80211item_uint32_t istx;
63904 + p80211item_uint32_t frmlen;
63905 +} wlan_ng_prism2_header;
63906 +
63907 +/* The radio capture header precedes the 802.11 header. */
63908 +typedef struct PACKED _ieee80211_radiotap_header {
63909 + UINT8 it_version; /* Version 0. Only increases
63910 + * for drastic changes,
63911 + * introduction of compatible
63912 + * new fields does not count.
63913 + */
63914 + UINT8 it_pad;
63915 + UINT16 it_len; /* length of the whole
63916 + * header in bytes, including
63917 + * it_version, it_pad,
63918 + * it_len, and data fields.
63919 + */
63920 + UINT32 it_present; /* A bitmap telling which
63921 + * fields are present. Set bit 31
63922 + * (0x80000000) to extend the
63923 + * bitmap by another 32 bits.
63924 + * Additional extensions are made
63925 + * by setting bit 31.
63926 + */
63927 +}ieee80211_radiotap_header ;
63928 +
63929 +enum ieee80211_radiotap_type {
63930 + IEEE80211_RADIOTAP_TSFT = 0,
63931 + IEEE80211_RADIOTAP_FLAGS = 1,
63932 + IEEE80211_RADIOTAP_RATE = 2,
63933 + IEEE80211_RADIOTAP_CHANNEL = 3,
63934 + IEEE80211_RADIOTAP_FHSS = 4,
63935 + IEEE80211_RADIOTAP_DBM_ANTSIGNAL = 5,
63936 + IEEE80211_RADIOTAP_DBM_ANTNOISE = 6,
63937 + IEEE80211_RADIOTAP_LOCK_QUALITY = 7,
63938 + IEEE80211_RADIOTAP_TX_ATTENUATION = 8,
63939 + IEEE80211_RADIOTAP_DB_TX_ATTENUATION = 9,
63940 + IEEE80211_RADIOTAP_DBM_TX_POWER = 10,
63941 + IEEE80211_RADIOTAP_ANTENNA = 11,
63942 + IEEE80211_RADIOTAP_DB_ANTSIGNAL = 12,
63943 + IEEE80211_RADIOTAP_DB_ANTNOISE = 13
63944 +};
63945 +
63946 +#define WLAN_RADIOTAP_PRESENT ( \
63947 + (1 << IEEE80211_RADIOTAP_TSFT) | \
63948 + (1 << IEEE80211_RADIOTAP_FLAGS) | \
63949 + (1 << IEEE80211_RADIOTAP_RATE) | \
63950 + 0)
63951 +
63952 +typedef struct _wlan_radiotap_header {
63953 + ieee80211_radiotap_header wt_ihdr;
63954 + INT64 wt_tsft;
63955 + UINT8 wt_flags;
63956 + UINT8 wt_rate;
63957 +} wlan_radiotap_header;
63958 +/* Definition from madwifi */
63959 +
63960 +void send_monitor_packets(
63961 + IN PRTMP_ADAPTER pAd,
63962 + IN RX_BLK *pRxBlk);
63963 +
63964 +#if WIRELESS_EXT >= 12
63965 +// This function will be called when query /proc
63966 +struct iw_statistics *rt28xx_get_wireless_stats(
63967 + IN struct net_device *net_dev);
63968 +#endif
63969 +
63970 +VOID RTMPSetDesiredRates(
63971 + IN PRTMP_ADAPTER pAdapter,
63972 + IN LONG Rates);
63973 +#endif // CONFIG_STA_SUPPORT //
63974 +
63975 +INT Set_FixedTxMode_Proc(
63976 + IN PRTMP_ADAPTER pAd,
63977 + IN PUCHAR arg);
63978 +
63979 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
63980 +INT Set_OpMode_Proc(
63981 + IN PRTMP_ADAPTER pAd,
63982 + IN PUCHAR arg);
63983 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
63984 +
63985 +static inline char* GetPhyMode(
63986 + int Mode)
63987 +{
63988 + switch(Mode)
63989 + {
63990 + case MODE_CCK:
63991 + return "CCK";
63992 +
63993 + case MODE_OFDM:
63994 + return "OFDM";
63995 +#ifdef DOT11_N_SUPPORT
63996 + case MODE_HTMIX:
63997 + return "HTMIX";
63998 +
63999 + case MODE_HTGREENFIELD:
64000 + return "GREEN";
64001 +#endif // DOT11_N_SUPPORT //
64002 + default:
64003 + return "N/A";
64004 + }
64005 +}
64006 +
64007 +
64008 +static inline char* GetBW(
64009 + int BW)
64010 +{
64011 + switch(BW)
64012 + {
64013 + case BW_10:
64014 + return "10M";
64015 +
64016 + case BW_20:
64017 + return "20M";
64018 +#ifdef DOT11_N_SUPPORT
64019 + case BW_40:
64020 + return "40M";
64021 +#endif // DOT11_N_SUPPORT //
64022 + default:
64023 + return "N/A";
64024 + }
64025 +}
64026 +
64027 +
64028 +VOID RT28xxThreadTerminate(
64029 + IN RTMP_ADAPTER *pAd);
64030 +
64031 +BOOLEAN RT28XXChipsetCheck(
64032 + IN void *_dev_p);
64033 +
64034 +BOOLEAN RT28XXNetDevInit(
64035 + IN void *_dev_p,
64036 + IN struct net_device *net_dev,
64037 + IN RTMP_ADAPTER *pAd);
64038 +
64039 +BOOLEAN RT28XXProbePostConfig(
64040 + IN void *_dev_p,
64041 + IN RTMP_ADAPTER *pAd,
64042 + IN INT32 argc);
64043 +
64044 +VOID RT28XXDMADisable(
64045 + IN RTMP_ADAPTER *pAd);
64046 +
64047 +VOID RT28XXDMAEnable(
64048 + IN RTMP_ADAPTER *pAd);
64049 +
64050 +VOID RT28xx_UpdateBeaconToAsic(
64051 + IN RTMP_ADAPTER * pAd,
64052 + IN INT apidx,
64053 + IN ULONG BeaconLen,
64054 + IN ULONG UpdatePos);
64055 +
64056 +INT rt28xx_ioctl(
64057 + IN struct net_device *net_dev,
64058 + IN OUT struct ifreq *rq,
64059 + IN INT cmd);
64060 +
64061 +
64062 +#ifdef CONFIG_STA_SUPPORT
64063 +INT rt28xx_sta_ioctl(
64064 + IN struct net_device *net_dev,
64065 + IN OUT struct ifreq *rq,
64066 + IN INT cmd);
64067 +#endif // CONFIG_STA_SUPPORT //
64068 +
64069 +BOOLEAN RT28XXSecurityKeyAdd(
64070 + IN PRTMP_ADAPTER pAd,
64071 + IN ULONG apidx,
64072 + IN ULONG KeyIdx,
64073 + IN MAC_TABLE_ENTRY *pEntry);
64074 +
64075 +////////////////////////////////////////
64076 +PNDIS_PACKET GetPacketFromRxRing(
64077 + IN PRTMP_ADAPTER pAd,
64078 + OUT PRT28XX_RXD_STRUC pSaveRxD,
64079 + OUT BOOLEAN *pbReschedule,
64080 + IN OUT UINT32 *pRxPending);
64081 +
64082 +
64083 +void kill_thread_task(PRTMP_ADAPTER pAd);
64084 +
64085 +void tbtt_tasklet(unsigned long data);
64086 +
64087 +#ifdef RT2860
64088 +//
64089 +// Function Prototype in cmm_data_2860.c
64090 +//
64091 +USHORT RtmpPCI_WriteTxResource(
64092 + IN PRTMP_ADAPTER pAd,
64093 + IN TX_BLK *pTxBlk,
64094 + IN BOOLEAN bIsLast,
64095 + OUT USHORT *FreeNumber);
64096 +
64097 +USHORT RtmpPCI_WriteSingleTxResource(
64098 + IN PRTMP_ADAPTER pAd,
64099 + IN TX_BLK *pTxBlk,
64100 + IN BOOLEAN bIsLast,
64101 + OUT USHORT *FreeNumber);
64102 +
64103 +USHORT RtmpPCI_WriteMultiTxResource(
64104 + IN PRTMP_ADAPTER pAd,
64105 + IN TX_BLK *pTxBlk,
64106 + IN UCHAR frameNum,
64107 + OUT USHORT *FreeNumber);
64108 +
64109 +USHORT RtmpPCI_WriteFragTxResource(
64110 + IN PRTMP_ADAPTER pAd,
64111 + IN TX_BLK *pTxBlk,
64112 + IN UCHAR fragNum,
64113 + OUT USHORT *FreeNumber);
64114 +
64115 +USHORT RtmpPCI_WriteSubTxResource(
64116 + IN PRTMP_ADAPTER pAd,
64117 + IN TX_BLK *pTxBlk,
64118 + IN BOOLEAN bIsLast,
64119 + OUT USHORT *FreeNumber);
64120 +
64121 +VOID RtmpPCI_FinalWriteTxResource(
64122 + IN PRTMP_ADAPTER pAd,
64123 + IN TX_BLK *pTxBlk,
64124 + IN USHORT totalMPDUSize,
64125 + IN USHORT FirstTxIdx);
64126 +
64127 +VOID RtmpPCIDataLastTxIdx(
64128 + IN PRTMP_ADAPTER pAd,
64129 + IN UCHAR QueIdx,
64130 + IN USHORT LastTxIdx);
64131 +
64132 +VOID RtmpPCIDataKickOut(
64133 + IN PRTMP_ADAPTER pAd,
64134 + IN TX_BLK *pTxBlk,
64135 + IN UCHAR QueIdx);
64136 +
64137 +
64138 +int RtmpPCIMgmtKickOut(
64139 + IN RTMP_ADAPTER *pAd,
64140 + IN UCHAR QueIdx,
64141 + IN PNDIS_PACKET pPacket,
64142 + IN PUCHAR pSrcBufVA,
64143 + IN UINT SrcBufLen);
64144 +
64145 +
64146 +NDIS_STATUS RTMPCheckRxError(
64147 + IN PRTMP_ADAPTER pAd,
64148 + IN PHEADER_802_11 pHeader,
64149 + IN PRXWI_STRUC pRxWI,
64150 + IN PRT28XX_RXD_STRUC pRxD);
64151 +
64152 +#ifdef CONFIG_STA_SUPPORT
64153 +VOID RTMPInitPCIeLinkCtrlValue(
64154 + IN PRTMP_ADAPTER pAd);
64155 +
64156 +VOID RTMPFindHostPCIDev(
64157 + IN PRTMP_ADAPTER pAd);
64158 +
64159 +VOID RTMPPCIeLinkCtrlValueRestore(
64160 + IN PRTMP_ADAPTER pAd,
64161 + IN UCHAR Level);
64162 +
64163 +VOID RTMPPCIeLinkCtrlSetting(
64164 + IN PRTMP_ADAPTER pAd,
64165 + IN USHORT Max);
64166 +
64167 +VOID RT28xxPciAsicRadioOff(
64168 + IN PRTMP_ADAPTER pAd,
64169 + IN UCHAR Level,
64170 + IN USHORT TbttNumToNextWakeUp);
64171 +
64172 +BOOLEAN RT28xxPciAsicRadioOn(
64173 + IN PRTMP_ADAPTER pAd,
64174 + IN UCHAR Level);
64175 +
64176 +VOID RT28xxPciStaAsicForceWakeup(
64177 + IN PRTMP_ADAPTER pAd,
64178 + IN BOOLEAN bFromTx);
64179 +
64180 +VOID RT28xxPciStaAsicSleepThenAutoWakeup(
64181 + IN PRTMP_ADAPTER pAd,
64182 + IN USHORT TbttNumToNextWakeUp);
64183 +
64184 +VOID PsPollWakeExec(
64185 + IN PVOID SystemSpecific1,
64186 + IN PVOID FunctionContext,
64187 + IN PVOID SystemSpecific2,
64188 + IN PVOID SystemSpecific3);
64189 +
64190 +VOID RadioOnExec(
64191 + IN PVOID SystemSpecific1,
64192 + IN PVOID FunctionContext,
64193 + IN PVOID SystemSpecific2,
64194 + IN PVOID SystemSpecific3);
64195 +#endif // CONFIG_STA_SUPPORT //
64196 +
64197 +VOID RT28xxPciMlmeRadioOn(
64198 + IN PRTMP_ADAPTER pAd);
64199 +
64200 +VOID RT28xxPciMlmeRadioOFF(
64201 + IN PRTMP_ADAPTER pAd);
64202 +#endif // RT2860 //
64203 +
64204 +VOID AsicTurnOffRFClk(
64205 + IN PRTMP_ADAPTER pAd,
64206 + IN UCHAR Channel);
64207 +
64208 +VOID AsicTurnOnRFClk(
64209 + IN PRTMP_ADAPTER pAd,
64210 + IN UCHAR Channel);
64211 +
64212 +
64213 +////////////////////////////////////////
64214 +
64215 +VOID QBSS_LoadInit(
64216 + IN RTMP_ADAPTER *pAd);
64217 +
64218 +UINT32 QBSS_LoadElementAppend(
64219 + IN RTMP_ADAPTER *pAd,
64220 + OUT UINT8 *buf_p);
64221 +
64222 +VOID QBSS_LoadUpdate(
64223 + IN RTMP_ADAPTER *pAd);
64224 +
64225 +///////////////////////////////////////
64226 +INT RTMPShowCfgValue(
64227 + IN PRTMP_ADAPTER pAd,
64228 + IN PUCHAR pName,
64229 + IN PUCHAR pBuf);
64230 +
64231 +PCHAR RTMPGetRalinkAuthModeStr(
64232 + IN NDIS_802_11_AUTHENTICATION_MODE authMode);
64233 +
64234 +PCHAR RTMPGetRalinkEncryModeStr(
64235 + IN USHORT encryMode);
64236 +//////////////////////////////////////
64237 +
64238 +#ifdef CONFIG_STA_SUPPORT
64239 +VOID AsicStaBbpTuning(
64240 + IN PRTMP_ADAPTER pAd);
64241 +#endif // CONFIG_STA_SUPPORT //
64242 +
64243 +void RTMP_IndicateMediaState(
64244 + IN PRTMP_ADAPTER pAd);
64245 +
64246 +VOID ReSyncBeaconTime(
64247 + IN PRTMP_ADAPTER pAd);
64248 +
64249 +VOID RTMPSetAGCInitValue(
64250 + IN PRTMP_ADAPTER pAd,
64251 + IN UCHAR BandWidth);
64252 +
64253 +int rt28xx_close(IN PNET_DEV dev);
64254 +int rt28xx_open(IN PNET_DEV dev);
64255 +
64256 +__inline INT VIRTUAL_IF_UP(PRTMP_ADAPTER pAd)
64257 +{
64258 +extern VOID MeshMakeBeacon(IN PRTMP_ADAPTER pAd, IN UCHAR idx);
64259 +extern VOID MeshUpdateBeaconFrame(IN PRTMP_ADAPTER pAd, IN UCHAR idx);
64260 +
64261 + if (VIRTUAL_IF_NUM(pAd) == 0)
64262 + {
64263 + if (rt28xx_open(pAd->net_dev) != 0)
64264 + return -1;
64265 + }
64266 + else
64267 + {
64268 + }
64269 + VIRTUAL_IF_INC(pAd);
64270 + return 0;
64271 +}
64272 +
64273 +__inline VOID VIRTUAL_IF_DOWN(PRTMP_ADAPTER pAd)
64274 +{
64275 + VIRTUAL_IF_DEC(pAd);
64276 + if (VIRTUAL_IF_NUM(pAd) == 0)
64277 + rt28xx_close(pAd->net_dev);
64278 + return;
64279 +}
64280 +
64281 +
64282 +#endif // __RTMP_H__
64283 +
64284 --- /dev/null
64285 +++ b/drivers/staging/rt2860/rtmp_type.h
64286 @@ -0,0 +1,94 @@
64287 +/*
64288 + *************************************************************************
64289 + * Ralink Tech Inc.
64290 + * 5F., No.36, Taiyuan St., Jhubei City,
64291 + * Hsinchu County 302,
64292 + * Taiwan, R.O.C.
64293 + *
64294 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
64295 + *
64296 + * This program is free software; you can redistribute it and/or modify *
64297 + * it under the terms of the GNU General Public License as published by *
64298 + * the Free Software Foundation; either version 2 of the License, or *
64299 + * (at your option) any later version. *
64300 + * *
64301 + * This program is distributed in the hope that it will be useful, *
64302 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
64303 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
64304 + * GNU General Public License for more details. *
64305 + * *
64306 + * You should have received a copy of the GNU General Public License *
64307 + * along with this program; if not, write to the *
64308 + * Free Software Foundation, Inc., *
64309 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
64310 + * *
64311 + *************************************************************************
64312 +
64313 + Module Name:
64314 + rtmp_type.h
64315 +
64316 + Abstract:
64317 +
64318 + Revision History:
64319 + Who When What
64320 + -------- ---------- ----------------------------------------------
64321 + Name Date Modification logs
64322 + Paul Lin 1-2-2004
64323 +*/
64324 +#ifndef __RTMP_TYPE_H__
64325 +#define __RTMP_TYPE_H__
64326 +
64327 +#define PACKED __attribute__ ((packed))
64328 +
64329 +// Put platform dependent declaration here
64330 +// For example, linux type definition
64331 +typedef unsigned char UINT8;
64332 +typedef unsigned short UINT16;
64333 +typedef unsigned int UINT32;
64334 +typedef unsigned long long UINT64;
64335 +typedef int INT32;
64336 +typedef long long INT64;
64337 +
64338 +typedef unsigned char * PUINT8;
64339 +typedef unsigned short * PUINT16;
64340 +typedef unsigned int * PUINT32;
64341 +typedef unsigned long long * PUINT64;
64342 +typedef int * PINT32;
64343 +typedef long long * PINT64;
64344 +
64345 +typedef signed char CHAR;
64346 +typedef signed short SHORT;
64347 +typedef signed int INT;
64348 +typedef signed long LONG;
64349 +typedef signed long long LONGLONG;
64350 +
64351 +
64352 +typedef unsigned char UCHAR;
64353 +typedef unsigned short USHORT;
64354 +typedef unsigned int UINT;
64355 +typedef unsigned long ULONG;
64356 +typedef unsigned long long ULONGLONG;
64357 +
64358 +typedef unsigned char BOOLEAN;
64359 +typedef void VOID;
64360 +
64361 +typedef VOID * PVOID;
64362 +typedef CHAR * PCHAR;
64363 +typedef UCHAR * PUCHAR;
64364 +typedef USHORT * PUSHORT;
64365 +typedef LONG * PLONG;
64366 +typedef ULONG * PULONG;
64367 +typedef UINT * PUINT;
64368 +
64369 +typedef unsigned int NDIS_MEDIA_STATE;
64370 +
64371 +typedef union _LARGE_INTEGER {
64372 + struct {
64373 + UINT LowPart;
64374 + INT32 HighPart;
64375 + } u;
64376 + INT64 QuadPart;
64377 +} LARGE_INTEGER;
64378 +
64379 +#endif // __RTMP_TYPE_H__
64380 +
64381 --- /dev/null
64382 +++ b/drivers/staging/rt2860/rt_profile.c
64383 @@ -0,0 +1,1976 @@
64384 +/*
64385 + *************************************************************************
64386 + * Ralink Tech Inc.
64387 + * 5F., No.36, Taiyuan St., Jhubei City,
64388 + * Hsinchu County 302,
64389 + * Taiwan, R.O.C.
64390 + *
64391 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
64392 + *
64393 + * This program is free software; you can redistribute it and/or modify *
64394 + * it under the terms of the GNU General Public License as published by *
64395 + * the Free Software Foundation; either version 2 of the License, or *
64396 + * (at your option) any later version. *
64397 + * *
64398 + * This program is distributed in the hope that it will be useful, *
64399 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
64400 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
64401 + * GNU General Public License for more details. *
64402 + * *
64403 + * You should have received a copy of the GNU General Public License *
64404 + * along with this program; if not, write to the *
64405 + * Free Software Foundation, Inc., *
64406 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
64407 + * *
64408 + *************************************************************************
64409 + */
64410 +
64411 +#include "rt_config.h"
64412 +
64413 +#ifdef DOT11_N_SUPPORT
64414 +static void HTParametersHook(
64415 + IN PRTMP_ADAPTER pAd,
64416 + IN CHAR *pValueStr,
64417 + IN CHAR *pInput);
64418 +#endif // DOT11_N_SUPPORT //
64419 +
64420 +#define ETH_MAC_ADDR_STR_LEN 17 // in format of xx:xx:xx:xx:xx:xx
64421 +
64422 +// We assume the s1 is a sting, s2 is a memory space with 6 bytes. and content of s1 will be changed.
64423 +BOOLEAN rtstrmactohex(char *s1, char *s2)
64424 +{
64425 + int i = 0;
64426 + char *ptokS = s1, *ptokE = s1;
64427 +
64428 + if (strlen(s1) != ETH_MAC_ADDR_STR_LEN)
64429 + return FALSE;
64430 +
64431 + while((*ptokS) != '\0')
64432 + {
64433 + if((ptokE = strchr(ptokS, ':')) != NULL)
64434 + *ptokE++ = '\0';
64435 + if ((strlen(ptokS) != 2) || (!isxdigit(*ptokS)) || (!isxdigit(*(ptokS+1))))
64436 + break; // fail
64437 + AtoH(ptokS, &s2[i++], 1);
64438 + ptokS = ptokE;
64439 + if (i == 6)
64440 + break; // parsing finished
64441 + }
64442 +
64443 + return ( i == 6 ? TRUE : FALSE);
64444 +
64445 +}
64446 +
64447 +
64448 +// we assume the s1 and s2 both are strings.
64449 +BOOLEAN rtstrcasecmp(char *s1, char *s2)
64450 +{
64451 + char *p1 = s1, *p2 = s2;
64452 +
64453 + if (strlen(s1) != strlen(s2))
64454 + return FALSE;
64455 +
64456 + while(*p1 != '\0')
64457 + {
64458 + if((*p1 != *p2) && ((*p1 ^ *p2) != 0x20))
64459 + return FALSE;
64460 + p1++;
64461 + p2++;
64462 + }
64463 +
64464 + return TRUE;
64465 +}
64466 +
64467 +// we assume the s1 (buffer) and s2 (key) both are strings.
64468 +char * rtstrstruncasecmp(char * s1, char * s2)
64469 +{
64470 + INT l1, l2, i;
64471 + char temp1, temp2;
64472 +
64473 + l2 = strlen(s2);
64474 + if (!l2)
64475 + return (char *) s1;
64476 +
64477 + l1 = strlen(s1);
64478 +
64479 + while (l1 >= l2)
64480 + {
64481 + l1--;
64482 +
64483 + for(i=0; i<l2; i++)
64484 + {
64485 + temp1 = *(s1+i);
64486 + temp2 = *(s2+i);
64487 +
64488 + if (('a' <= temp1) && (temp1 <= 'z'))
64489 + temp1 = 'A'+(temp1-'a');
64490 + if (('a' <= temp2) && (temp2 <= 'z'))
64491 + temp2 = 'A'+(temp2-'a');
64492 +
64493 + if (temp1 != temp2)
64494 + break;
64495 + }
64496 +
64497 + if (i == l2)
64498 + return (char *) s1;
64499 +
64500 + s1++;
64501 + }
64502 +
64503 + return NULL; // not found
64504 +}
64505 +
64506 +//add by kathy
64507 +
64508 + /**
64509 + * strstr - Find the first substring in a %NUL terminated string
64510 + * @s1: The string to be searched
64511 + * @s2: The string to search for
64512 + */
64513 +char * rtstrstr(const char * s1,const char * s2)
64514 +{
64515 + INT l1, l2;
64516 +
64517 + l2 = strlen(s2);
64518 + if (!l2)
64519 + return (char *) s1;
64520 +
64521 + l1 = strlen(s1);
64522 +
64523 + while (l1 >= l2)
64524 + {
64525 + l1--;
64526 + if (!memcmp(s1,s2,l2))
64527 + return (char *) s1;
64528 + s1++;
64529 + }
64530 +
64531 + return NULL;
64532 +}
64533 +
64534 +/**
64535 + * rstrtok - Split a string into tokens
64536 + * @s: The string to be searched
64537 + * @ct: The characters to search for
64538 + * * WARNING: strtok is deprecated, use strsep instead. However strsep is not compatible with old architecture.
64539 + */
64540 +char * __rstrtok;
64541 +char * rstrtok(char * s,const char * ct)
64542 +{
64543 + char *sbegin, *send;
64544 +
64545 + sbegin = s ? s : __rstrtok;
64546 + if (!sbegin)
64547 + {
64548 + return NULL;
64549 + }
64550 +
64551 + sbegin += strspn(sbegin,ct);
64552 + if (*sbegin == '\0')
64553 + {
64554 + __rstrtok = NULL;
64555 + return( NULL );
64556 + }
64557 +
64558 + send = strpbrk( sbegin, ct);
64559 + if (send && *send != '\0')
64560 + *send++ = '\0';
64561 +
64562 + __rstrtok = send;
64563 +
64564 + return (sbegin);
64565 +}
64566 +
64567 +/**
64568 + * delimitcnt - return the count of a given delimiter in a given string.
64569 + * @s: The string to be searched.
64570 + * @ct: The delimiter to search for.
64571 + * Notice : We suppose the delimiter is a single-char string(for example : ";").
64572 + */
64573 +INT delimitcnt(char * s,const char * ct)
64574 +{
64575 + INT count = 0;
64576 + /* point to the beginning of the line */
64577 + const char *token = s;
64578 +
64579 + for ( ;; )
64580 + {
64581 + token = strpbrk(token, ct); /* search for delimiters */
64582 +
64583 + if ( token == NULL )
64584 + {
64585 + /* advanced to the terminating null character */
64586 + break;
64587 + }
64588 + /* skip the delimiter */
64589 + ++token;
64590 +
64591 + /*
64592 + * Print the found text: use len with %.*s to specify field width.
64593 + */
64594 +
64595 + /* accumulate delimiter count */
64596 + ++count;
64597 + }
64598 + return count;
64599 +}
64600 +
64601 +/*
64602 + * converts the Internet host address from the standard numbers-and-dots notation
64603 + * into binary data.
64604 + * returns nonzero if the address is valid, zero if not.
64605 + */
64606 +int rtinet_aton(const char *cp, unsigned int *addr)
64607 +{
64608 + unsigned int val;
64609 + int base, n;
64610 + char c;
64611 + unsigned int parts[4];
64612 + unsigned int *pp = parts;
64613 +
64614 + for (;;)
64615 + {
64616 + /*
64617 + * Collect number up to ``.''.
64618 + * Values are specified as for C:
64619 + * 0x=hex, 0=octal, other=decimal.
64620 + */
64621 + val = 0;
64622 + base = 10;
64623 + if (*cp == '0')
64624 + {
64625 + if (*++cp == 'x' || *cp == 'X')
64626 + base = 16, cp++;
64627 + else
64628 + base = 8;
64629 + }
64630 + while ((c = *cp) != '\0')
64631 + {
64632 + if (isdigit((unsigned char) c))
64633 + {
64634 + val = (val * base) + (c - '0');
64635 + cp++;
64636 + continue;
64637 + }
64638 + if (base == 16 && isxdigit((unsigned char) c))
64639 + {
64640 + val = (val << 4) +
64641 + (c + 10 - (islower((unsigned char) c) ? 'a' : 'A'));
64642 + cp++;
64643 + continue;
64644 + }
64645 + break;
64646 + }
64647 + if (*cp == '.')
64648 + {
64649 + /*
64650 + * Internet format: a.b.c.d a.b.c (with c treated as 16-bits)
64651 + * a.b (with b treated as 24 bits)
64652 + */
64653 + if (pp >= parts + 3 || val > 0xff)
64654 + return 0;
64655 + *pp++ = val, cp++;
64656 + }
64657 + else
64658 + break;
64659 + }
64660 +
64661 + /*
64662 + * Check for trailing junk.
64663 + */
64664 + while (*cp)
64665 + if (!isspace((unsigned char) *cp++))
64666 + return 0;
64667 +
64668 + /*
64669 + * Concoct the address according to the number of parts specified.
64670 + */
64671 + n = pp - parts + 1;
64672 + switch (n)
64673 + {
64674 +
64675 + case 1: /* a -- 32 bits */
64676 + break;
64677 +
64678 + case 2: /* a.b -- 8.24 bits */
64679 + if (val > 0xffffff)
64680 + return 0;
64681 + val |= parts[0] << 24;
64682 + break;
64683 +
64684 + case 3: /* a.b.c -- 8.8.16 bits */
64685 + if (val > 0xffff)
64686 + return 0;
64687 + val |= (parts[0] << 24) | (parts[1] << 16);
64688 + break;
64689 +
64690 + case 4: /* a.b.c.d -- 8.8.8.8 bits */
64691 + if (val > 0xff)
64692 + return 0;
64693 + val |= (parts[0] << 24) | (parts[1] << 16) | (parts[2] << 8);
64694 + break;
64695 + }
64696 +
64697 + *addr = htonl(val);
64698 + return 1;
64699 +
64700 +}
64701 +
64702 +/*
64703 + ========================================================================
64704 +
64705 + Routine Description:
64706 + Find key section for Get key parameter.
64707 +
64708 + Arguments:
64709 + buffer Pointer to the buffer to start find the key section
64710 + section the key of the secion to be find
64711 +
64712 + Return Value:
64713 + NULL Fail
64714 + Others Success
64715 + ========================================================================
64716 +*/
64717 +PUCHAR RTMPFindSection(
64718 + IN PCHAR buffer)
64719 +{
64720 + CHAR temp_buf[32];
64721 + PUCHAR ptr;
64722 +
64723 + strcpy(temp_buf, "Default");
64724 +
64725 + if((ptr = rtstrstr(buffer, temp_buf)) != NULL)
64726 + return (ptr+strlen("\n"));
64727 + else
64728 + return NULL;
64729 +}
64730 +
64731 +/*
64732 + ========================================================================
64733 +
64734 + Routine Description:
64735 + Get key parameter.
64736 +
64737 + Arguments:
64738 + key Pointer to key string
64739 + dest Pointer to destination
64740 + destsize The datasize of the destination
64741 + buffer Pointer to the buffer to start find the key
64742 +
64743 + Return Value:
64744 + TRUE Success
64745 + FALSE Fail
64746 +
64747 + Note:
64748 + This routine get the value with the matched key (case case-sensitive)
64749 + ========================================================================
64750 +*/
64751 +INT RTMPGetKeyParameter(
64752 + IN PCHAR key,
64753 + OUT PCHAR dest,
64754 + IN INT destsize,
64755 + IN PCHAR buffer)
64756 +{
64757 + UCHAR *temp_buf1 = NULL;
64758 + UCHAR *temp_buf2 = NULL;
64759 + CHAR *start_ptr;
64760 + CHAR *end_ptr;
64761 + CHAR *ptr;
64762 + CHAR *offset = 0;
64763 + INT len;
64764 +
64765 + //temp_buf1 = kmalloc(MAX_PARAM_BUFFER_SIZE, MEM_ALLOC_FLAG);
64766 + os_alloc_mem(NULL, &temp_buf1, MAX_PARAM_BUFFER_SIZE);
64767 +
64768 + if(temp_buf1 == NULL)
64769 + return (FALSE);
64770 +
64771 + //temp_buf2 = kmalloc(MAX_PARAM_BUFFER_SIZE, MEM_ALLOC_FLAG);
64772 + os_alloc_mem(NULL, &temp_buf2, MAX_PARAM_BUFFER_SIZE);
64773 + if(temp_buf2 == NULL)
64774 + {
64775 + os_free_mem(NULL, temp_buf1);
64776 + return (FALSE);
64777 + }
64778 +
64779 + //find section
64780 + if((offset = RTMPFindSection(buffer)) == NULL)
64781 + {
64782 + os_free_mem(NULL, temp_buf1);
64783 + os_free_mem(NULL, temp_buf2);
64784 + return (FALSE);
64785 + }
64786 +
64787 + strcpy(temp_buf1, "\n");
64788 + strcat(temp_buf1, key);
64789 + strcat(temp_buf1, "=");
64790 +
64791 + //search key
64792 + if((start_ptr=rtstrstr(offset, temp_buf1))==NULL)
64793 + {
64794 + os_free_mem(NULL, temp_buf1);
64795 + os_free_mem(NULL, temp_buf2);
64796 + return (FALSE);
64797 + }
64798 +
64799 + start_ptr+=strlen("\n");
64800 + if((end_ptr=rtstrstr(start_ptr, "\n"))==NULL)
64801 + end_ptr=start_ptr+strlen(start_ptr);
64802 +
64803 + if (end_ptr<start_ptr)
64804 + {
64805 + os_free_mem(NULL, temp_buf1);
64806 + os_free_mem(NULL, temp_buf2);
64807 + return (FALSE);
64808 + }
64809 +
64810 + NdisMoveMemory(temp_buf2, start_ptr, end_ptr-start_ptr);
64811 + temp_buf2[end_ptr-start_ptr]='\0';
64812 + len = strlen(temp_buf2);
64813 + strcpy(temp_buf1, temp_buf2);
64814 + if((start_ptr=rtstrstr(temp_buf1, "=")) == NULL)
64815 + {
64816 + os_free_mem(NULL, temp_buf1);
64817 + os_free_mem(NULL, temp_buf2);
64818 + return (FALSE);
64819 + }
64820 +
64821 + strcpy(temp_buf2, start_ptr+1);
64822 + ptr = temp_buf2;
64823 + //trim space or tab
64824 + while(*ptr != 0x00)
64825 + {
64826 + if( (*ptr == ' ') || (*ptr == '\t') )
64827 + ptr++;
64828 + else
64829 + break;
64830 + }
64831 +
64832 + len = strlen(ptr);
64833 + memset(dest, 0x00, destsize);
64834 + strncpy(dest, ptr, len >= destsize ? destsize: len);
64835 +
64836 + os_free_mem(NULL, temp_buf1);
64837 + os_free_mem(NULL, temp_buf2);
64838 + return TRUE;
64839 +}
64840 +
64841 +/*
64842 + ========================================================================
64843 +
64844 + Routine Description:
64845 + Get key parameter.
64846 +
64847 + Arguments:
64848 + key Pointer to key string
64849 + dest Pointer to destination
64850 + destsize The datasize of the destination
64851 + buffer Pointer to the buffer to start find the key
64852 +
64853 + Return Value:
64854 + TRUE Success
64855 + FALSE Fail
64856 +
64857 + Note:
64858 + This routine get the value with the matched key (case case-sensitive).
64859 + It is called for parsing SSID and any key string.
64860 + ========================================================================
64861 +*/
64862 +INT RTMPGetCriticalParameter(
64863 + IN PCHAR key,
64864 + OUT PCHAR dest,
64865 + IN INT destsize,
64866 + IN PCHAR buffer)
64867 +{
64868 + UCHAR *temp_buf1 = NULL;
64869 + UCHAR *temp_buf2 = NULL;
64870 + CHAR *start_ptr;
64871 + CHAR *end_ptr;
64872 + CHAR *ptr;
64873 + CHAR *offset = 0;
64874 + INT len;
64875 +
64876 + //temp_buf1 = kmalloc(MAX_PARAM_BUFFER_SIZE, MEM_ALLOC_FLAG);
64877 + os_alloc_mem(NULL, &temp_buf1, MAX_PARAM_BUFFER_SIZE);
64878 +
64879 + if(temp_buf1 == NULL)
64880 + return (FALSE);
64881 +
64882 + //temp_buf2 = kmalloc(MAX_PARAM_BUFFER_SIZE, MEM_ALLOC_FLAG);
64883 + os_alloc_mem(NULL, &temp_buf2, MAX_PARAM_BUFFER_SIZE);
64884 + if(temp_buf2 == NULL)
64885 + {
64886 + os_free_mem(NULL, temp_buf1);
64887 + return (FALSE);
64888 + }
64889 +
64890 + //find section
64891 + if((offset = RTMPFindSection(buffer)) == NULL)
64892 + {
64893 + os_free_mem(NULL, temp_buf1);
64894 + os_free_mem(NULL, temp_buf2);
64895 + return (FALSE);
64896 + }
64897 +
64898 + strcpy(temp_buf1, "\n");
64899 + strcat(temp_buf1, key);
64900 + strcat(temp_buf1, "=");
64901 +
64902 + //search key
64903 + if((start_ptr=rtstrstr(offset, temp_buf1))==NULL)
64904 + {
64905 + os_free_mem(NULL, temp_buf1);
64906 + os_free_mem(NULL, temp_buf2);
64907 + return (FALSE);
64908 + }
64909 +
64910 + start_ptr+=strlen("\n");
64911 + if((end_ptr=rtstrstr(start_ptr, "\n"))==NULL)
64912 + end_ptr=start_ptr+strlen(start_ptr);
64913 +
64914 + if (end_ptr<start_ptr)
64915 + {
64916 + os_free_mem(NULL, temp_buf1);
64917 + os_free_mem(NULL, temp_buf2);
64918 + return (FALSE);
64919 + }
64920 +
64921 + NdisMoveMemory(temp_buf2, start_ptr, end_ptr-start_ptr);
64922 + temp_buf2[end_ptr-start_ptr]='\0';
64923 + len = strlen(temp_buf2);
64924 + strcpy(temp_buf1, temp_buf2);
64925 + if((start_ptr=rtstrstr(temp_buf1, "=")) == NULL)
64926 + {
64927 + os_free_mem(NULL, temp_buf1);
64928 + os_free_mem(NULL, temp_buf2);
64929 + return (FALSE);
64930 + }
64931 +
64932 + strcpy(temp_buf2, start_ptr+1);
64933 + ptr = temp_buf2;
64934 +
64935 + //trim tab
64936 + /* We cannot trim space(' ') for SSID and key string. */
64937 + while(*ptr != 0x00)
64938 + {
64939 + //if( (*ptr == ' ') || (*ptr == '\t') )
64940 + if( (*ptr == '\t') )
64941 + ptr++;
64942 + else
64943 + break;
64944 + }
64945 +
64946 + len = strlen(ptr);
64947 + memset(dest, 0x00, destsize);
64948 + strncpy(dest, ptr, len >= destsize ? destsize: len);
64949 +
64950 + os_free_mem(NULL, temp_buf1);
64951 + os_free_mem(NULL, temp_buf2);
64952 + return TRUE;
64953 +}
64954 +
64955 +/*
64956 + ========================================================================
64957 +
64958 + Routine Description:
64959 + Get multiple key parameter.
64960 +
64961 + Arguments:
64962 + key Pointer to key string
64963 + dest Pointer to destination
64964 + destsize The datasize of the destination
64965 + buffer Pointer to the buffer to start find the key
64966 +
64967 + Return Value:
64968 + TRUE Success
64969 + FALSE Fail
64970 +
64971 + Note:
64972 + This routine get the value with the matched key (case case-sensitive)
64973 + ========================================================================
64974 +*/
64975 +INT RTMPGetKeyParameterWithOffset(
64976 + IN PCHAR key,
64977 + OUT PCHAR dest,
64978 + OUT USHORT *end_offset,
64979 + IN INT destsize,
64980 + IN PCHAR buffer,
64981 + IN BOOLEAN bTrimSpace)
64982 +{
64983 + UCHAR *temp_buf1 = NULL;
64984 + UCHAR *temp_buf2 = NULL;
64985 + CHAR *start_ptr;
64986 + CHAR *end_ptr;
64987 + CHAR *ptr;
64988 + CHAR *offset = 0;
64989 + INT len;
64990 +
64991 + if (*end_offset >= MAX_INI_BUFFER_SIZE)
64992 + return (FALSE);
64993 +
64994 + os_alloc_mem(NULL, &temp_buf1, MAX_PARAM_BUFFER_SIZE);
64995 +
64996 + if(temp_buf1 == NULL)
64997 + return (FALSE);
64998 +
64999 + os_alloc_mem(NULL, &temp_buf2, MAX_PARAM_BUFFER_SIZE);
65000 + if(temp_buf2 == NULL)
65001 + {
65002 + os_free_mem(NULL, temp_buf1);
65003 + return (FALSE);
65004 + }
65005 +
65006 + //find section
65007 + if(*end_offset == 0)
65008 + {
65009 + if ((offset = RTMPFindSection(buffer)) == NULL)
65010 + {
65011 + os_free_mem(NULL, temp_buf1);
65012 + os_free_mem(NULL, temp_buf2);
65013 + return (FALSE);
65014 + }
65015 + }
65016 + else
65017 + offset = buffer + (*end_offset);
65018 +
65019 + strcpy(temp_buf1, "\n");
65020 + strcat(temp_buf1, key);
65021 + strcat(temp_buf1, "=");
65022 +
65023 + //search key
65024 + if((start_ptr=rtstrstr(offset, temp_buf1))==NULL)
65025 + {
65026 + os_free_mem(NULL, temp_buf1);
65027 + os_free_mem(NULL, temp_buf2);
65028 + return (FALSE);
65029 + }
65030 +
65031 + start_ptr+=strlen("\n");
65032 + if((end_ptr=rtstrstr(start_ptr, "\n"))==NULL)
65033 + end_ptr=start_ptr+strlen(start_ptr);
65034 +
65035 + if (end_ptr<start_ptr)
65036 + {
65037 + os_free_mem(NULL, temp_buf1);
65038 + os_free_mem(NULL, temp_buf2);
65039 + return (FALSE);
65040 + }
65041 +
65042 + *end_offset = end_ptr - buffer;
65043 +
65044 + NdisMoveMemory(temp_buf2, start_ptr, end_ptr-start_ptr);
65045 + temp_buf2[end_ptr-start_ptr]='\0';
65046 + len = strlen(temp_buf2);
65047 + strcpy(temp_buf1, temp_buf2);
65048 + if((start_ptr=rtstrstr(temp_buf1, "=")) == NULL)
65049 + {
65050 + os_free_mem(NULL, temp_buf1);
65051 + os_free_mem(NULL, temp_buf2);
65052 + return (FALSE);
65053 + }
65054 +
65055 + strcpy(temp_buf2, start_ptr+1);
65056 + ptr = temp_buf2;
65057 + //trim space or tab
65058 + while(*ptr != 0x00)
65059 + {
65060 + if((bTrimSpace && (*ptr == ' ')) || (*ptr == '\t') )
65061 + ptr++;
65062 + else
65063 + break;
65064 + }
65065 +
65066 + len = strlen(ptr);
65067 + memset(dest, 0x00, destsize);
65068 + strncpy(dest, ptr, len >= destsize ? destsize: len);
65069 +
65070 + os_free_mem(NULL, temp_buf1);
65071 + os_free_mem(NULL, temp_buf2);
65072 + return TRUE;
65073 +}
65074 +
65075 +
65076 +static int rtmp_parse_key_buffer_from_file(IN PRTMP_ADAPTER pAd,IN char *buffer,IN ULONG KeyType,IN INT BSSIdx,IN INT KeyIdx)
65077 +{
65078 + PUCHAR keybuff;
65079 + INT i = BSSIdx, idx = KeyIdx;
65080 + ULONG KeyLen;
65081 + UCHAR CipherAlg = CIPHER_WEP64;
65082 +
65083 + keybuff = buffer;
65084 + KeyLen = strlen(keybuff);
65085 +
65086 + if (KeyType == 1)
65087 + {//Ascii
65088 + if( (KeyLen == 5) || (KeyLen == 13))
65089 + {
65090 + pAd->SharedKey[i][idx].KeyLen = KeyLen;
65091 + NdisMoveMemory(pAd->SharedKey[i][idx].Key, keybuff, KeyLen);
65092 + if (KeyLen == 5)
65093 + CipherAlg = CIPHER_WEP64;
65094 + else
65095 + CipherAlg = CIPHER_WEP128;
65096 + pAd->SharedKey[i][idx].CipherAlg = CipherAlg;
65097 +
65098 + DBGPRINT(RT_DEBUG_TRACE, ("I/F(ra%d) Key%dStr=%s and type=%s\n", i, idx+1, keybuff, (KeyType == 0) ? "Hex":"Ascii"));
65099 + return 1;
65100 + }
65101 + else
65102 + {//Invalid key length
65103 + DBGPRINT(RT_DEBUG_ERROR, ("Key%dStr is Invalid key length! KeyLen = %ld!\n", idx+1, KeyLen));
65104 + return 0;
65105 + }
65106 + }
65107 + else
65108 + {//Hex type
65109 + if( (KeyLen == 10) || (KeyLen == 26))
65110 + {
65111 + pAd->SharedKey[i][idx].KeyLen = KeyLen / 2;
65112 + AtoH(keybuff, pAd->SharedKey[i][idx].Key, KeyLen / 2);
65113 + if (KeyLen == 10)
65114 + CipherAlg = CIPHER_WEP64;
65115 + else
65116 + CipherAlg = CIPHER_WEP128;
65117 + pAd->SharedKey[i][idx].CipherAlg = CipherAlg;
65118 +
65119 + DBGPRINT(RT_DEBUG_TRACE, ("I/F(ra%d) Key%dStr=%s and type=%s\n", i, idx+1, keybuff, (KeyType == 0) ? "Hex":"Ascii"));
65120 + return 1;
65121 + }
65122 + else
65123 + {//Invalid key length
65124 + DBGPRINT(RT_DEBUG_ERROR, ("I/F(ra%d) Key%dStr is Invalid key length! KeyLen = %ld!\n", i, idx+1, KeyLen));
65125 + return 0;
65126 + }
65127 + }
65128 +}
65129 +static void rtmp_read_key_parms_from_file(IN PRTMP_ADAPTER pAd, char *tmpbuf, char *buffer)
65130 +{
65131 + char tok_str[16];
65132 + PUCHAR macptr;
65133 + INT i = 0, idx;
65134 + ULONG KeyType[MAX_MBSSID_NUM];
65135 + ULONG KeyIdx;
65136 +
65137 + NdisZeroMemory(KeyType, MAX_MBSSID_NUM);
65138 +
65139 + //DefaultKeyID
65140 + if(RTMPGetKeyParameter("DefaultKeyID", tmpbuf, 25, buffer))
65141 + {
65142 +
65143 +#ifdef CONFIG_STA_SUPPORT
65144 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65145 + {
65146 + KeyIdx = simple_strtol(tmpbuf, 0, 10);
65147 + if((KeyIdx >= 1 ) && (KeyIdx <= 4))
65148 + pAd->StaCfg.DefaultKeyId = (UCHAR) (KeyIdx - 1);
65149 + else
65150 + pAd->StaCfg.DefaultKeyId = 0;
65151 +
65152 + DBGPRINT(RT_DEBUG_TRACE, ("DefaultKeyID(0~3)=%d\n", pAd->StaCfg.DefaultKeyId));
65153 + }
65154 +#endif // CONFIG_STA_SUPPORT //
65155 + }
65156 +
65157 +
65158 + for (idx = 0; idx < 4; idx++)
65159 + {
65160 + sprintf(tok_str, "Key%dType", idx + 1);
65161 + //Key1Type
65162 + if (RTMPGetKeyParameter(tok_str, tmpbuf, 128, buffer))
65163 + {
65164 + for (i = 0, macptr = rstrtok(tmpbuf,";"); macptr; macptr = rstrtok(NULL,";"), i++)
65165 + {
65166 + KeyType[i] = simple_strtol(macptr, 0, 10);
65167 + }
65168 +
65169 +#ifdef CONFIG_STA_SUPPORT
65170 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65171 + {
65172 + sprintf(tok_str, "Key%dStr", idx + 1);
65173 + if (RTMPGetCriticalParameter(tok_str, tmpbuf, 128, buffer))
65174 + {
65175 + rtmp_parse_key_buffer_from_file(pAd, tmpbuf, KeyType[BSS0], BSS0, idx);
65176 + }
65177 + }
65178 +#endif // CONFIG_STA_SUPPORT //
65179 + }
65180 + }
65181 +}
65182 +
65183 +
65184 +#ifdef CONFIG_STA_SUPPORT
65185 +static void rtmp_read_sta_wmm_parms_from_file(IN PRTMP_ADAPTER pAd, char *tmpbuf, char *buffer)
65186 +{
65187 + PUCHAR macptr;
65188 + INT i=0;
65189 + BOOLEAN bWmmEnable = FALSE;
65190 +
65191 + //WmmCapable
65192 + if(RTMPGetKeyParameter("WmmCapable", tmpbuf, 32, buffer))
65193 + {
65194 + if(simple_strtol(tmpbuf, 0, 10) != 0) //Enable
65195 + {
65196 + pAd->CommonCfg.bWmmCapable = TRUE;
65197 + bWmmEnable = TRUE;
65198 + }
65199 + else //Disable
65200 + {
65201 + pAd->CommonCfg.bWmmCapable = FALSE;
65202 + }
65203 +
65204 + DBGPRINT(RT_DEBUG_TRACE, ("WmmCapable=%d\n", pAd->CommonCfg.bWmmCapable));
65205 + }
65206 +
65207 +#ifdef QOS_DLS_SUPPORT
65208 + //DLSCapable
65209 + if(RTMPGetKeyParameter("DLSCapable", tmpbuf, 32, buffer))
65210 + {
65211 + if(simple_strtol(tmpbuf, 0, 10) != 0) //Enable
65212 + {
65213 + pAd->CommonCfg.bDLSCapable = TRUE;
65214 + }
65215 + else //Disable
65216 + {
65217 + pAd->CommonCfg.bDLSCapable = FALSE;
65218 + }
65219 +
65220 + DBGPRINT(RT_DEBUG_TRACE, ("bDLSCapable=%d\n", pAd->CommonCfg.bDLSCapable));
65221 + }
65222 +#endif // QOS_DLS_SUPPORT //
65223 +
65224 + //AckPolicy for AC_BK, AC_BE, AC_VI, AC_VO
65225 + if(RTMPGetKeyParameter("AckPolicy", tmpbuf, 32, buffer))
65226 + {
65227 + for (i = 0, macptr = rstrtok(tmpbuf,";"); macptr; macptr = rstrtok(NULL,";"), i++)
65228 + {
65229 + pAd->CommonCfg.AckPolicy[i] = (UCHAR)simple_strtol(macptr, 0, 10);
65230 +
65231 + DBGPRINT(RT_DEBUG_TRACE, ("AckPolicy[%d]=%d\n", i, pAd->CommonCfg.AckPolicy[i]));
65232 + }
65233 + }
65234 +
65235 + if (bWmmEnable)
65236 + {
65237 + //APSDCapable
65238 + if(RTMPGetKeyParameter("APSDCapable", tmpbuf, 10, buffer))
65239 + {
65240 + if(simple_strtol(tmpbuf, 0, 10) != 0) //Enable
65241 + pAd->CommonCfg.bAPSDCapable = TRUE;
65242 + else
65243 + pAd->CommonCfg.bAPSDCapable = FALSE;
65244 +
65245 + DBGPRINT(RT_DEBUG_TRACE, ("APSDCapable=%d\n", pAd->CommonCfg.bAPSDCapable));
65246 + }
65247 +
65248 + //APSDAC for AC_BE, AC_BK, AC_VI, AC_VO
65249 + if(RTMPGetKeyParameter("APSDAC", tmpbuf, 32, buffer))
65250 + {
65251 + BOOLEAN apsd_ac[4];
65252 +
65253 + for (i = 0, macptr = rstrtok(tmpbuf,";"); macptr; macptr = rstrtok(NULL,";"), i++)
65254 + {
65255 + apsd_ac[i] = (BOOLEAN)simple_strtol(macptr, 0, 10);
65256 +
65257 + DBGPRINT(RT_DEBUG_TRACE, ("APSDAC%d %d\n", i, apsd_ac[i]));
65258 + }
65259 +
65260 + pAd->CommonCfg.bAPSDAC_BE = apsd_ac[0];
65261 + pAd->CommonCfg.bAPSDAC_BK = apsd_ac[1];
65262 + pAd->CommonCfg.bAPSDAC_VI = apsd_ac[2];
65263 + pAd->CommonCfg.bAPSDAC_VO = apsd_ac[3];
65264 + }
65265 + }
65266 +
65267 +}
65268 +#endif // CONFIG_STA_SUPPORT //
65269 +
65270 +
65271 +NDIS_STATUS RTMPReadParametersHook(
65272 + IN PRTMP_ADAPTER pAd)
65273 +{
65274 + PUCHAR src = NULL;
65275 + struct file *srcf;
65276 + INT retval, orgfsuid, orgfsgid;
65277 + mm_segment_t orgfs;
65278 + CHAR *buffer;
65279 + CHAR *tmpbuf;
65280 + ULONG RtsThresh;
65281 + ULONG FragThresh;
65282 +#ifdef CONFIG_STA_SUPPORT
65283 + UCHAR keyMaterial[40];
65284 +#endif // CONFIG_STA_SUPPORT //
65285 +
65286 +
65287 + PUCHAR macptr;
65288 + INT i = 0;
65289 +
65290 + buffer = kmalloc(MAX_INI_BUFFER_SIZE, MEM_ALLOC_FLAG);
65291 + if(buffer == NULL)
65292 + return NDIS_STATUS_FAILURE;
65293 +
65294 + tmpbuf = kmalloc(MAX_PARAM_BUFFER_SIZE, MEM_ALLOC_FLAG);
65295 + if(tmpbuf == NULL)
65296 + {
65297 + kfree(buffer);
65298 + return NDIS_STATUS_FAILURE;
65299 + }
65300 +
65301 +#ifdef CONFIG_STA_SUPPORT
65302 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65303 + src = STA_PROFILE_PATH;
65304 +#endif // CONFIG_STA_SUPPORT //
65305 +#ifdef MULTIPLE_CARD_SUPPORT
65306 + src = pAd->MC_FileName;
65307 +#endif // MULTIPLE_CARD_SUPPORT //
65308 +
65309 + // Save uid and gid used for filesystem access.
65310 + // Set user and group to 0 (root)
65311 + orgfsuid = current->fsuid;
65312 + orgfsgid = current->fsgid;
65313 + current->fsuid=current->fsgid = 0;
65314 + orgfs = get_fs();
65315 + set_fs(KERNEL_DS);
65316 +
65317 + if (src && *src)
65318 + {
65319 + srcf = filp_open(src, O_RDONLY, 0);
65320 + if (IS_ERR(srcf))
65321 + {
65322 + DBGPRINT(RT_DEBUG_ERROR, ("--> Error %ld opening %s\n", -PTR_ERR(srcf),src));
65323 + }
65324 + else
65325 + {
65326 + // The object must have a read method
65327 + if (srcf->f_op && srcf->f_op->read)
65328 + {
65329 + memset(buffer, 0x00, MAX_INI_BUFFER_SIZE);
65330 + retval=srcf->f_op->read(srcf, buffer, MAX_INI_BUFFER_SIZE, &srcf->f_pos);
65331 + if (retval < 0)
65332 + {
65333 + DBGPRINT(RT_DEBUG_TRACE, ("--> Read %s error %d\n", src, -retval));
65334 + }
65335 + else
65336 + {
65337 + // set file parameter to portcfg
65338 + //CountryRegion
65339 + if(RTMPGetKeyParameter("CountryRegion", tmpbuf, 25, buffer))
65340 + {
65341 + pAd->CommonCfg.CountryRegion = (UCHAR) simple_strtol(tmpbuf, 0, 10);
65342 + DBGPRINT(RT_DEBUG_TRACE, ("CountryRegion=%d\n", pAd->CommonCfg.CountryRegion));
65343 + }
65344 + //CountryRegionABand
65345 + if(RTMPGetKeyParameter("CountryRegionABand", tmpbuf, 25, buffer))
65346 + {
65347 + pAd->CommonCfg.CountryRegionForABand= (UCHAR) simple_strtol(tmpbuf, 0, 10);
65348 + DBGPRINT(RT_DEBUG_TRACE, ("CountryRegionABand=%d\n", pAd->CommonCfg.CountryRegionForABand));
65349 + }
65350 + //CountryCode
65351 + if(RTMPGetKeyParameter("CountryCode", tmpbuf, 25, buffer))
65352 + {
65353 + NdisMoveMemory(pAd->CommonCfg.CountryCode, tmpbuf , 2);
65354 +#ifdef CONFIG_STA_SUPPORT
65355 +#ifdef EXT_BUILD_CHANNEL_LIST
65356 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65357 + NdisMoveMemory(pAd->StaCfg.StaOriCountryCode, tmpbuf , 2);
65358 +#endif // EXT_BUILD_CHANNEL_LIST //
65359 +#endif // CONFIG_STA_SUPPORT //
65360 + if (strlen(pAd->CommonCfg.CountryCode) != 0)
65361 + {
65362 + pAd->CommonCfg.bCountryFlag = TRUE;
65363 + }
65364 + DBGPRINT(RT_DEBUG_TRACE, ("CountryCode=%s\n", pAd->CommonCfg.CountryCode));
65365 + }
65366 + //ChannelGeography
65367 + if(RTMPGetKeyParameter("ChannelGeography", tmpbuf, 25, buffer))
65368 + {
65369 + UCHAR Geography = (UCHAR) simple_strtol(tmpbuf, 0, 10);
65370 + if (Geography <= BOTH)
65371 + {
65372 + pAd->CommonCfg.Geography = Geography;
65373 + pAd->CommonCfg.CountryCode[2] =
65374 + (pAd->CommonCfg.Geography == BOTH) ? ' ' : ((pAd->CommonCfg.Geography == IDOR) ? 'I' : 'O');
65375 +#ifdef CONFIG_STA_SUPPORT
65376 +#ifdef EXT_BUILD_CHANNEL_LIST
65377 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65378 + pAd->StaCfg.StaOriGeography = pAd->CommonCfg.Geography;
65379 +#endif // EXT_BUILD_CHANNEL_LIST //
65380 +#endif // CONFIG_STA_SUPPORT //
65381 + DBGPRINT(RT_DEBUG_TRACE, ("ChannelGeography=%d\n", pAd->CommonCfg.Geography));
65382 + }
65383 + }
65384 + else
65385 + {
65386 + pAd->CommonCfg.Geography = BOTH;
65387 + pAd->CommonCfg.CountryCode[2] = ' ';
65388 + }
65389 +
65390 +
65391 +#ifdef CONFIG_STA_SUPPORT
65392 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65393 + {
65394 + //SSID
65395 + if (RTMPGetCriticalParameter("SSID", tmpbuf, 256, buffer))
65396 + {
65397 + if (strlen(tmpbuf) <= 32)
65398 + {
65399 + pAd->CommonCfg.SsidLen = (UCHAR) strlen(tmpbuf);
65400 + NdisZeroMemory(pAd->CommonCfg.Ssid, NDIS_802_11_LENGTH_SSID);
65401 + NdisMoveMemory(pAd->CommonCfg.Ssid, tmpbuf, pAd->CommonCfg.SsidLen);
65402 + pAd->MlmeAux.AutoReconnectSsidLen = pAd->CommonCfg.SsidLen;
65403 + NdisZeroMemory(pAd->MlmeAux.AutoReconnectSsid, NDIS_802_11_LENGTH_SSID);
65404 + NdisMoveMemory(pAd->MlmeAux.AutoReconnectSsid, tmpbuf, pAd->MlmeAux.AutoReconnectSsidLen);
65405 + pAd->MlmeAux.SsidLen = pAd->CommonCfg.SsidLen;
65406 + NdisZeroMemory(pAd->MlmeAux.Ssid, NDIS_802_11_LENGTH_SSID);
65407 + NdisMoveMemory(pAd->MlmeAux.Ssid, tmpbuf, pAd->MlmeAux.SsidLen);
65408 + DBGPRINT(RT_DEBUG_TRACE, ("%s::(SSID=%s)\n", __FUNCTION__, tmpbuf));
65409 + }
65410 + }
65411 + }
65412 +#endif // CONFIG_STA_SUPPORT //
65413 +
65414 +#ifdef CONFIG_STA_SUPPORT
65415 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65416 + {
65417 + //NetworkType
65418 + if (RTMPGetKeyParameter("NetworkType", tmpbuf, 25, buffer))
65419 + {
65420 + pAd->bConfigChanged = TRUE;
65421 + if (strcmp(tmpbuf, "Adhoc") == 0)
65422 + pAd->StaCfg.BssType = BSS_ADHOC;
65423 + else //Default Infrastructure mode
65424 + pAd->StaCfg.BssType = BSS_INFRA;
65425 + // Reset Ralink supplicant to not use, it will be set to start when UI set PMK key
65426 + pAd->StaCfg.WpaState = SS_NOTUSE;
65427 + DBGPRINT(RT_DEBUG_TRACE, ("%s::(NetworkType=%d)\n", __FUNCTION__, pAd->StaCfg.BssType));
65428 + }
65429 + }
65430 +#endif // CONFIG_STA_SUPPORT //
65431 + //Channel
65432 + if(RTMPGetKeyParameter("Channel", tmpbuf, 10, buffer))
65433 + {
65434 + pAd->CommonCfg.Channel = (UCHAR) simple_strtol(tmpbuf, 0, 10);
65435 + DBGPRINT(RT_DEBUG_TRACE, ("Channel=%d\n", pAd->CommonCfg.Channel));
65436 + }
65437 + //WirelessMode
65438 + if(RTMPGetKeyParameter("WirelessMode", tmpbuf, 10, buffer))
65439 + {
65440 + int value = 0, maxPhyMode = PHY_11G;
65441 +
65442 +#ifdef DOT11_N_SUPPORT
65443 + maxPhyMode = PHY_11N_5G;
65444 +#endif // DOT11_N_SUPPORT //
65445 +
65446 + value = simple_strtol(tmpbuf, 0, 10);
65447 +
65448 + if (value <= maxPhyMode)
65449 + {
65450 + pAd->CommonCfg.PhyMode = value;
65451 + }
65452 + DBGPRINT(RT_DEBUG_TRACE, ("PhyMode=%d\n", pAd->CommonCfg.PhyMode));
65453 + }
65454 + //BasicRate
65455 + if(RTMPGetKeyParameter("BasicRate", tmpbuf, 10, buffer))
65456 + {
65457 + pAd->CommonCfg.BasicRateBitmap = (ULONG) simple_strtol(tmpbuf, 0, 10);
65458 + DBGPRINT(RT_DEBUG_TRACE, ("BasicRate=%ld\n", pAd->CommonCfg.BasicRateBitmap));
65459 + }
65460 + //BeaconPeriod
65461 + if(RTMPGetKeyParameter("BeaconPeriod", tmpbuf, 10, buffer))
65462 + {
65463 + pAd->CommonCfg.BeaconPeriod = (USHORT) simple_strtol(tmpbuf, 0, 10);
65464 + DBGPRINT(RT_DEBUG_TRACE, ("BeaconPeriod=%d\n", pAd->CommonCfg.BeaconPeriod));
65465 + }
65466 + //TxPower
65467 + if(RTMPGetKeyParameter("TxPower", tmpbuf, 10, buffer))
65468 + {
65469 + pAd->CommonCfg.TxPowerPercentage = (ULONG) simple_strtol(tmpbuf, 0, 10);
65470 +#ifdef CONFIG_STA_SUPPORT
65471 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65472 + pAd->CommonCfg.TxPowerDefault = pAd->CommonCfg.TxPowerPercentage;
65473 +#endif // CONFIG_STA_SUPPORT //
65474 + DBGPRINT(RT_DEBUG_TRACE, ("TxPower=%ld\n", pAd->CommonCfg.TxPowerPercentage));
65475 + }
65476 + //BGProtection
65477 + if(RTMPGetKeyParameter("BGProtection", tmpbuf, 10, buffer))
65478 + {
65479 + switch (simple_strtol(tmpbuf, 0, 10))
65480 + {
65481 + case 1: //Always On
65482 + pAd->CommonCfg.UseBGProtection = 1;
65483 + break;
65484 + case 2: //Always OFF
65485 + pAd->CommonCfg.UseBGProtection = 2;
65486 + break;
65487 + case 0: //AUTO
65488 + default:
65489 + pAd->CommonCfg.UseBGProtection = 0;
65490 + break;
65491 + }
65492 + DBGPRINT(RT_DEBUG_TRACE, ("BGProtection=%ld\n", pAd->CommonCfg.UseBGProtection));
65493 + }
65494 + //OLBCDetection
65495 + if(RTMPGetKeyParameter("DisableOLBC", tmpbuf, 10, buffer))
65496 + {
65497 + switch (simple_strtol(tmpbuf, 0, 10))
65498 + {
65499 + case 1: //disable OLBC Detection
65500 + pAd->CommonCfg.DisableOLBCDetect = 1;
65501 + break;
65502 + case 0: //enable OLBC Detection
65503 + pAd->CommonCfg.DisableOLBCDetect = 0;
65504 + break;
65505 + default:
65506 + pAd->CommonCfg.DisableOLBCDetect= 0;
65507 + break;
65508 + }
65509 + DBGPRINT(RT_DEBUG_TRACE, ("OLBCDetection=%ld\n", pAd->CommonCfg.DisableOLBCDetect));
65510 + }
65511 + //TxPreamble
65512 + if(RTMPGetKeyParameter("TxPreamble", tmpbuf, 10, buffer))
65513 + {
65514 + switch (simple_strtol(tmpbuf, 0, 10))
65515 + {
65516 + case Rt802_11PreambleShort:
65517 + pAd->CommonCfg.TxPreamble = Rt802_11PreambleShort;
65518 + break;
65519 + case Rt802_11PreambleLong:
65520 + default:
65521 + pAd->CommonCfg.TxPreamble = Rt802_11PreambleLong;
65522 + break;
65523 + }
65524 + DBGPRINT(RT_DEBUG_TRACE, ("TxPreamble=%ld\n", pAd->CommonCfg.TxPreamble));
65525 + }
65526 + //RTSThreshold
65527 + if(RTMPGetKeyParameter("RTSThreshold", tmpbuf, 10, buffer))
65528 + {
65529 + RtsThresh = simple_strtol(tmpbuf, 0, 10);
65530 + if( (RtsThresh >= 1) && (RtsThresh <= MAX_RTS_THRESHOLD) )
65531 + pAd->CommonCfg.RtsThreshold = (USHORT)RtsThresh;
65532 + else
65533 + pAd->CommonCfg.RtsThreshold = MAX_RTS_THRESHOLD;
65534 +
65535 + DBGPRINT(RT_DEBUG_TRACE, ("RTSThreshold=%d\n", pAd->CommonCfg.RtsThreshold));
65536 + }
65537 + //FragThreshold
65538 + if(RTMPGetKeyParameter("FragThreshold", tmpbuf, 10, buffer))
65539 + {
65540 + FragThresh = simple_strtol(tmpbuf, 0, 10);
65541 + pAd->CommonCfg.bUseZeroToDisableFragment = FALSE;
65542 +
65543 + if (FragThresh > MAX_FRAG_THRESHOLD || FragThresh < MIN_FRAG_THRESHOLD)
65544 + { //illegal FragThresh so we set it to default
65545 + pAd->CommonCfg.FragmentThreshold = MAX_FRAG_THRESHOLD;
65546 + pAd->CommonCfg.bUseZeroToDisableFragment = TRUE;
65547 + }
65548 + else if (FragThresh % 2 == 1)
65549 + {
65550 + // The length of each fragment shall always be an even number of octets, except for the last fragment
65551 + // of an MSDU or MMPDU, which may be either an even or an odd number of octets.
65552 + pAd->CommonCfg.FragmentThreshold = (USHORT)(FragThresh - 1);
65553 + }
65554 + else
65555 + {
65556 + pAd->CommonCfg.FragmentThreshold = (USHORT)FragThresh;
65557 + }
65558 + //pAd->CommonCfg.AllowFragSize = (pAd->CommonCfg.FragmentThreshold) - LENGTH_802_11 - LENGTH_CRC;
65559 + DBGPRINT(RT_DEBUG_TRACE, ("FragThreshold=%d\n", pAd->CommonCfg.FragmentThreshold));
65560 + }
65561 + //TxBurst
65562 + if(RTMPGetKeyParameter("TxBurst", tmpbuf, 10, buffer))
65563 + {
65564 + if(simple_strtol(tmpbuf, 0, 10) != 0) //Enable
65565 + pAd->CommonCfg.bEnableTxBurst = TRUE;
65566 + else //Disable
65567 + pAd->CommonCfg.bEnableTxBurst = FALSE;
65568 + DBGPRINT(RT_DEBUG_TRACE, ("TxBurst=%d\n", pAd->CommonCfg.bEnableTxBurst));
65569 + }
65570 +
65571 +#ifdef AGGREGATION_SUPPORT
65572 + //PktAggregate
65573 + if(RTMPGetKeyParameter("PktAggregate", tmpbuf, 10, buffer))
65574 + {
65575 + if(simple_strtol(tmpbuf, 0, 10) != 0) //Enable
65576 + pAd->CommonCfg.bAggregationCapable = TRUE;
65577 + else //Disable
65578 + pAd->CommonCfg.bAggregationCapable = FALSE;
65579 +#ifdef PIGGYBACK_SUPPORT
65580 + pAd->CommonCfg.bPiggyBackCapable = pAd->CommonCfg.bAggregationCapable;
65581 +#endif // PIGGYBACK_SUPPORT //
65582 + DBGPRINT(RT_DEBUG_TRACE, ("PktAggregate=%d\n", pAd->CommonCfg.bAggregationCapable));
65583 + }
65584 +#else
65585 + pAd->CommonCfg.bAggregationCapable = FALSE;
65586 + pAd->CommonCfg.bPiggyBackCapable = FALSE;
65587 +#endif // AGGREGATION_SUPPORT //
65588 +
65589 + // WmmCapable
65590 +
65591 +#ifdef CONFIG_STA_SUPPORT
65592 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65593 + rtmp_read_sta_wmm_parms_from_file(pAd, tmpbuf, buffer);
65594 +#endif // CONFIG_STA_SUPPORT //
65595 +
65596 + //ShortSlot
65597 + if(RTMPGetKeyParameter("ShortSlot", tmpbuf, 10, buffer))
65598 + {
65599 + if(simple_strtol(tmpbuf, 0, 10) != 0) //Enable
65600 + pAd->CommonCfg.bUseShortSlotTime = TRUE;
65601 + else //Disable
65602 + pAd->CommonCfg.bUseShortSlotTime = FALSE;
65603 +
65604 + DBGPRINT(RT_DEBUG_TRACE, ("ShortSlot=%d\n", pAd->CommonCfg.bUseShortSlotTime));
65605 + }
65606 + //IEEE80211H
65607 + if(RTMPGetKeyParameter("IEEE80211H", tmpbuf, 10, buffer))
65608 + {
65609 + for (i = 0, macptr = rstrtok(tmpbuf,";"); macptr; macptr = rstrtok(NULL,";"), i++)
65610 + {
65611 + if(simple_strtol(macptr, 0, 10) != 0) //Enable
65612 + pAd->CommonCfg.bIEEE80211H = TRUE;
65613 + else //Disable
65614 + pAd->CommonCfg.bIEEE80211H = FALSE;
65615 +
65616 + DBGPRINT(RT_DEBUG_TRACE, ("IEEE80211H=%d\n", pAd->CommonCfg.bIEEE80211H));
65617 + }
65618 + }
65619 + //CSPeriod
65620 + if(RTMPGetKeyParameter("CSPeriod", tmpbuf, 10, buffer))
65621 + {
65622 + if(simple_strtol(tmpbuf, 0, 10) != 0)
65623 + pAd->CommonCfg.RadarDetect.CSPeriod = simple_strtol(tmpbuf, 0, 10);
65624 + else
65625 + pAd->CommonCfg.RadarDetect.CSPeriod = 0;
65626 +
65627 + DBGPRINT(RT_DEBUG_TRACE, ("CSPeriod=%d\n", pAd->CommonCfg.RadarDetect.CSPeriod));
65628 + }
65629 +
65630 + //RDRegion
65631 + if(RTMPGetKeyParameter("RDRegion", tmpbuf, 128, buffer))
65632 + {
65633 + if ((strncmp(tmpbuf, "JAP_W53", 7) == 0) || (strncmp(tmpbuf, "jap_w53", 7) == 0))
65634 + {
65635 + pAd->CommonCfg.RadarDetect.RDDurRegion = JAP_W53;
65636 + pAd->CommonCfg.RadarDetect.DfsSessionTime = 15;
65637 + }
65638 + else if ((strncmp(tmpbuf, "JAP_W56", 7) == 0) || (strncmp(tmpbuf, "jap_w56", 7) == 0))
65639 + {
65640 + pAd->CommonCfg.RadarDetect.RDDurRegion = JAP_W56;
65641 + pAd->CommonCfg.RadarDetect.DfsSessionTime = 13;
65642 + }
65643 + else if ((strncmp(tmpbuf, "JAP", 3) == 0) || (strncmp(tmpbuf, "jap", 3) == 0))
65644 + {
65645 + pAd->CommonCfg.RadarDetect.RDDurRegion = JAP;
65646 + pAd->CommonCfg.RadarDetect.DfsSessionTime = 5;
65647 + }
65648 + else if ((strncmp(tmpbuf, "FCC", 3) == 0) || (strncmp(tmpbuf, "fcc", 3) == 0))
65649 + {
65650 + pAd->CommonCfg.RadarDetect.RDDurRegion = FCC;
65651 + pAd->CommonCfg.RadarDetect.DfsSessionTime = 5;
65652 + }
65653 + else if ((strncmp(tmpbuf, "CE", 2) == 0) || (strncmp(tmpbuf, "ce", 2) == 0))
65654 + {
65655 + pAd->CommonCfg.RadarDetect.RDDurRegion = CE;
65656 + pAd->CommonCfg.RadarDetect.DfsSessionTime = 13;
65657 + }
65658 + else
65659 + {
65660 + pAd->CommonCfg.RadarDetect.RDDurRegion = CE;
65661 + pAd->CommonCfg.RadarDetect.DfsSessionTime = 13;
65662 + }
65663 +
65664 + DBGPRINT(RT_DEBUG_TRACE, ("RDRegion=%d\n", pAd->CommonCfg.RadarDetect.RDDurRegion));
65665 + }
65666 + else
65667 + {
65668 + pAd->CommonCfg.RadarDetect.RDDurRegion = CE;
65669 + pAd->CommonCfg.RadarDetect.DfsSessionTime = 13;
65670 + }
65671 +
65672 + //WirelessEvent
65673 + if(RTMPGetKeyParameter("WirelessEvent", tmpbuf, 10, buffer))
65674 + {
65675 +#if WIRELESS_EXT >= 15
65676 + if(simple_strtol(tmpbuf, 0, 10) != 0)
65677 + pAd->CommonCfg.bWirelessEvent = simple_strtol(tmpbuf, 0, 10);
65678 + else
65679 + pAd->CommonCfg.bWirelessEvent = 0; // disable
65680 +#else
65681 + pAd->CommonCfg.bWirelessEvent = 0; // disable
65682 +#endif
65683 + DBGPRINT(RT_DEBUG_TRACE, ("WirelessEvent=%d\n", pAd->CommonCfg.bWirelessEvent));
65684 + }
65685 + if(RTMPGetKeyParameter("WiFiTest", tmpbuf, 10, buffer))
65686 + {
65687 + if(simple_strtol(tmpbuf, 0, 10) != 0)
65688 + pAd->CommonCfg.bWiFiTest= simple_strtol(tmpbuf, 0, 10);
65689 + else
65690 + pAd->CommonCfg.bWiFiTest = 0; // disable
65691 +
65692 + DBGPRINT(RT_DEBUG_TRACE, ("WiFiTest=%d\n", pAd->CommonCfg.bWiFiTest));
65693 + }
65694 + //AuthMode
65695 + if(RTMPGetKeyParameter("AuthMode", tmpbuf, 128, buffer))
65696 + {
65697 +#ifdef CONFIG_STA_SUPPORT
65698 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65699 + {
65700 + if ((strcmp(tmpbuf, "WEPAUTO") == 0) || (strcmp(tmpbuf, "wepauto") == 0))
65701 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeAutoSwitch;
65702 + else if ((strcmp(tmpbuf, "SHARED") == 0) || (strcmp(tmpbuf, "shared") == 0))
65703 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeShared;
65704 + else if ((strcmp(tmpbuf, "WPAPSK") == 0) || (strcmp(tmpbuf, "wpapsk") == 0))
65705 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeWPAPSK;
65706 + else if ((strcmp(tmpbuf, "WPANONE") == 0) || (strcmp(tmpbuf, "wpanone") == 0))
65707 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeWPANone;
65708 + else if ((strcmp(tmpbuf, "WPA2PSK") == 0) || (strcmp(tmpbuf, "wpa2psk") == 0))
65709 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeWPA2PSK;
65710 +#ifdef WPA_SUPPLICANT_SUPPORT
65711 + else if ((strcmp(tmpbuf, "WPA") == 0) || (strcmp(tmpbuf, "wpa") == 0))
65712 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeWPA;
65713 + else if ((strcmp(tmpbuf, "WPA2") == 0) || (strcmp(tmpbuf, "wpa2") == 0))
65714 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeWPA2;
65715 +#endif // WPA_SUPPLICANT_SUPPORT //
65716 + else
65717 + pAd->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
65718 +
65719 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
65720 +
65721 + DBGPRINT(RT_DEBUG_TRACE, ("%s::(EncrypType=%d)\n", __FUNCTION__, pAd->StaCfg.WepStatus));
65722 + }
65723 +#endif // CONFIG_STA_SUPPORT //
65724 + }
65725 + //EncrypType
65726 + if(RTMPGetKeyParameter("EncrypType", tmpbuf, 128, buffer))
65727 + {
65728 +
65729 +#ifdef CONFIG_STA_SUPPORT
65730 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65731 + {
65732 + if ((strcmp(tmpbuf, "WEP") == 0) || (strcmp(tmpbuf, "wep") == 0))
65733 + pAd->StaCfg.WepStatus = Ndis802_11WEPEnabled;
65734 + else if ((strcmp(tmpbuf, "TKIP") == 0) || (strcmp(tmpbuf, "tkip") == 0))
65735 + pAd->StaCfg.WepStatus = Ndis802_11Encryption2Enabled;
65736 + else if ((strcmp(tmpbuf, "AES") == 0) || (strcmp(tmpbuf, "aes") == 0))
65737 + pAd->StaCfg.WepStatus = Ndis802_11Encryption3Enabled;
65738 + else
65739 + pAd->StaCfg.WepStatus = Ndis802_11WEPDisabled;
65740 +
65741 + // Update all wepstatus related
65742 + pAd->StaCfg.PairCipher = pAd->StaCfg.WepStatus;
65743 + pAd->StaCfg.GroupCipher = pAd->StaCfg.WepStatus;
65744 + pAd->StaCfg.OrigWepStatus = pAd->StaCfg.WepStatus;
65745 + pAd->StaCfg.bMixCipher = FALSE;
65746 +
65747 + DBGPRINT(RT_DEBUG_TRACE, ("%s::(EncrypType=%d)\n", __FUNCTION__, pAd->StaCfg.WepStatus));
65748 + }
65749 +#endif // CONFIG_STA_SUPPORT //
65750 + }
65751 +
65752 +
65753 +
65754 +#ifdef CONFIG_STA_SUPPORT
65755 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65756 + {
65757 + if(RTMPGetCriticalParameter("WPAPSK", tmpbuf, 512, buffer))
65758 + {
65759 + int err=0;
65760 +
65761 + tmpbuf[strlen(tmpbuf)] = '\0'; // make STA can process .$^& for WPAPSK input
65762 +
65763 + if ((pAd->StaCfg.AuthMode != Ndis802_11AuthModeWPAPSK) &&
65764 + (pAd->StaCfg.AuthMode != Ndis802_11AuthModeWPA2PSK) &&
65765 + (pAd->StaCfg.AuthMode != Ndis802_11AuthModeWPANone)
65766 + )
65767 + {
65768 + err = 1;
65769 + }
65770 + else if ((strlen(tmpbuf) >= 8) && (strlen(tmpbuf) < 64))
65771 + {
65772 + PasswordHash((char *)tmpbuf, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen, keyMaterial);
65773 + NdisMoveMemory(pAd->StaCfg.PMK, keyMaterial, 32);
65774 +
65775 + }
65776 + else if (strlen(tmpbuf) == 64)
65777 + {
65778 + AtoH(tmpbuf, keyMaterial, 32);
65779 + NdisMoveMemory(pAd->StaCfg.PMK, keyMaterial, 32);
65780 + }
65781 + else
65782 + {
65783 + err = 1;
65784 + DBGPRINT(RT_DEBUG_ERROR, ("%s::(WPAPSK key-string required 8 ~ 64 characters!)\n", __FUNCTION__));
65785 + }
65786 +
65787 + if (err == 0)
65788 + {
65789 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) ||
65790 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
65791 + {
65792 + // Start STA supplicant state machine
65793 + pAd->StaCfg.WpaState = SS_START;
65794 + }
65795 + else if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
65796 + {
65797 + pAd->StaCfg.WpaState = SS_NOTUSE;
65798 + }
65799 +
65800 + DBGPRINT(RT_DEBUG_TRACE, ("%s::(WPAPSK=%s)\n", __FUNCTION__, tmpbuf));
65801 + }
65802 + }
65803 + }
65804 +#endif // CONFIG_STA_SUPPORT //
65805 +
65806 + //DefaultKeyID, KeyType, KeyStr
65807 + rtmp_read_key_parms_from_file(pAd, tmpbuf, buffer);
65808 +
65809 +#ifdef DOT11_N_SUPPORT
65810 + HTParametersHook(pAd, tmpbuf, buffer);
65811 +#endif // DOT11_N_SUPPORT //
65812 +
65813 +
65814 +#ifdef CARRIER_DETECTION_SUPPORT
65815 + //CarrierDetect
65816 + if(RTMPGetKeyParameter("CarrierDetect", tmpbuf, 128, buffer))
65817 + {
65818 + if ((strncmp(tmpbuf, "0", 1) == 0))
65819 + pAd->CommonCfg.CarrierDetect.Enable = FALSE;
65820 + else if ((strncmp(tmpbuf, "1", 1) == 0))
65821 + pAd->CommonCfg.CarrierDetect.Enable = TRUE;
65822 + else
65823 + pAd->CommonCfg.CarrierDetect.Enable = FALSE;
65824 +
65825 + DBGPRINT(RT_DEBUG_TRACE, ("CarrierDetect.Enable=%d\n", pAd->CommonCfg.CarrierDetect.Enable));
65826 + }
65827 + else
65828 + pAd->CommonCfg.CarrierDetect.Enable = FALSE;
65829 +#endif // CARRIER_DETECTION_SUPPORT //
65830 +
65831 +#ifdef CONFIG_STA_SUPPORT
65832 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
65833 + {
65834 + //PSMode
65835 + if (RTMPGetKeyParameter("PSMode", tmpbuf, 10, buffer))
65836 + {
65837 + if (pAd->StaCfg.BssType == BSS_INFRA)
65838 + {
65839 + if ((strcmp(tmpbuf, "MAX_PSP") == 0) || (strcmp(tmpbuf, "max_psp") == 0))
65840 + {
65841 + // do NOT turn on PSM bit here, wait until MlmeCheckForPsmChange()
65842 + // to exclude certain situations.
65843 + // MlmeSetPsm(pAd, PWR_SAVE);
65844 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM);
65845 + if (pAd->StaCfg.bWindowsACCAMEnable == FALSE)
65846 + pAd->StaCfg.WindowsPowerMode = Ndis802_11PowerModeMAX_PSP;
65847 + pAd->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeMAX_PSP;
65848 + pAd->StaCfg.DefaultListenCount = 5;
65849 + }
65850 + else if ((strcmp(tmpbuf, "Fast_PSP") == 0) || (strcmp(tmpbuf, "fast_psp") == 0)
65851 + || (strcmp(tmpbuf, "FAST_PSP") == 0))
65852 + {
65853 + // do NOT turn on PSM bit here, wait until MlmeCheckForPsmChange()
65854 + // to exclude certain situations.
65855 + // MlmeSetPsmBit(pAd, PWR_SAVE);
65856 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM);
65857 + if (pAd->StaCfg.bWindowsACCAMEnable == FALSE)
65858 + pAd->StaCfg.WindowsPowerMode = Ndis802_11PowerModeFast_PSP;
65859 + pAd->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeFast_PSP;
65860 + pAd->StaCfg.DefaultListenCount = 3;
65861 + }
65862 + else if ((strcmp(tmpbuf, "Legacy_PSP") == 0) || (strcmp(tmpbuf, "legacy_psp") == 0)
65863 + || (strcmp(tmpbuf, "LEGACY_PSP") == 0))
65864 + {
65865 + // do NOT turn on PSM bit here, wait until MlmeCheckForPsmChange()
65866 + // to exclude certain situations.
65867 + // MlmeSetPsmBit(pAd, PWR_SAVE);
65868 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM);
65869 + if (pAd->StaCfg.bWindowsACCAMEnable == FALSE)
65870 + pAd->StaCfg.WindowsPowerMode = Ndis802_11PowerModeLegacy_PSP;
65871 + pAd->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeLegacy_PSP;
65872 + pAd->StaCfg.DefaultListenCount = 3;
65873 + }
65874 + else
65875 + { //Default Ndis802_11PowerModeCAM
65876 + // clear PSM bit immediately
65877 + MlmeSetPsmBit(pAd, PWR_ACTIVE);
65878 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM);
65879 + if (pAd->StaCfg.bWindowsACCAMEnable == FALSE)
65880 + pAd->StaCfg.WindowsPowerMode = Ndis802_11PowerModeCAM;
65881 + pAd->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeCAM;
65882 + }
65883 + DBGPRINT(RT_DEBUG_TRACE, ("PSMode=%ld\n", pAd->StaCfg.WindowsPowerMode));
65884 + }
65885 + }
65886 + // FastRoaming
65887 + if (RTMPGetKeyParameter("FastRoaming", tmpbuf, 32, buffer))
65888 + {
65889 + if (simple_strtol(tmpbuf, 0, 10) == 0)
65890 + pAd->StaCfg.bFastRoaming = FALSE;
65891 + else
65892 + pAd->StaCfg.bFastRoaming = TRUE;
65893 +
65894 + DBGPRINT(RT_DEBUG_TRACE, ("FastRoaming=%d\n", pAd->StaCfg.bFastRoaming));
65895 + }
65896 + // RoamThreshold
65897 + if (RTMPGetKeyParameter("RoamThreshold", tmpbuf, 32, buffer))
65898 + {
65899 + long lInfo = simple_strtol(tmpbuf, 0, 10);
65900 +
65901 + if (lInfo > 90 || lInfo < 60)
65902 + pAd->StaCfg.dBmToRoam = -70;
65903 + else
65904 + pAd->StaCfg.dBmToRoam = (CHAR)(-1)*lInfo;
65905 +
65906 + DBGPRINT(RT_DEBUG_TRACE, ("RoamThreshold=%d dBm\n", pAd->StaCfg.dBmToRoam));
65907 + }
65908 +
65909 + if(RTMPGetKeyParameter("TGnWifiTest", tmpbuf, 10, buffer))
65910 + {
65911 + if(simple_strtol(tmpbuf, 0, 10) == 0)
65912 + pAd->StaCfg.bTGnWifiTest = FALSE;
65913 + else
65914 + pAd->StaCfg.bTGnWifiTest = TRUE;
65915 + DBGPRINT(RT_DEBUG_TRACE, ("TGnWifiTest=%d\n", pAd->StaCfg.bTGnWifiTest));
65916 + }
65917 + }
65918 +#endif // CONFIG_STA_SUPPORT //
65919 +
65920 + }
65921 + }
65922 + else
65923 + {
65924 + DBGPRINT(RT_DEBUG_TRACE, ("--> %s does not have a write method\n", src));
65925 + }
65926 +
65927 + retval=filp_close(srcf,NULL);
65928 +
65929 + if (retval)
65930 + {
65931 + DBGPRINT(RT_DEBUG_TRACE, ("--> Error %d closing %s\n", -retval, src));
65932 + }
65933 + }
65934 + }
65935 +
65936 + set_fs(orgfs);
65937 + current->fsuid = orgfsuid;
65938 + current->fsgid = orgfsgid;
65939 +
65940 + kfree(buffer);
65941 + kfree(tmpbuf);
65942 +
65943 + return (NDIS_STATUS_SUCCESS);
65944 +}
65945 +
65946 +#ifdef DOT11_N_SUPPORT
65947 +static void HTParametersHook(
65948 + IN PRTMP_ADAPTER pAd,
65949 + IN CHAR *pValueStr,
65950 + IN CHAR *pInput)
65951 +{
65952 +
65953 + INT Value;
65954 +
65955 + if (RTMPGetKeyParameter("HT_PROTECT", pValueStr, 25, pInput))
65956 + {
65957 + Value = simple_strtol(pValueStr, 0, 10);
65958 + if (Value == 0)
65959 + {
65960 + pAd->CommonCfg.bHTProtect = FALSE;
65961 + }
65962 + else
65963 + {
65964 + pAd->CommonCfg.bHTProtect = TRUE;
65965 + }
65966 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Protection = %s\n", (Value==0) ? "Disable" : "Enable"));
65967 + }
65968 +
65969 + if (RTMPGetKeyParameter("HT_MIMOPSEnable", pValueStr, 25, pInput))
65970 + {
65971 + Value = simple_strtol(pValueStr, 0, 10);
65972 + if (Value == 0)
65973 + {
65974 + pAd->CommonCfg.bMIMOPSEnable = FALSE;
65975 + }
65976 + else
65977 + {
65978 + pAd->CommonCfg.bMIMOPSEnable = TRUE;
65979 + }
65980 + DBGPRINT(RT_DEBUG_TRACE, ("HT: MIMOPSEnable = %s\n", (Value==0) ? "Disable" : "Enable"));
65981 + }
65982 +
65983 +
65984 + if (RTMPGetKeyParameter("HT_MIMOPSMode", pValueStr, 25, pInput))
65985 + {
65986 + Value = simple_strtol(pValueStr, 0, 10);
65987 + if (Value > MMPS_ENABLE)
65988 + {
65989 + pAd->CommonCfg.BACapability.field.MMPSmode = MMPS_ENABLE;
65990 + }
65991 + else
65992 + {
65993 + //TODO: add mimo power saving mechanism
65994 + pAd->CommonCfg.BACapability.field.MMPSmode = MMPS_ENABLE;
65995 + //pAd->CommonCfg.BACapability.field.MMPSmode = Value;
65996 + }
65997 + DBGPRINT(RT_DEBUG_TRACE, ("HT: MIMOPS Mode = %d\n", Value));
65998 + }
65999 +
66000 + if (RTMPGetKeyParameter("HT_BADecline", pValueStr, 25, pInput))
66001 + {
66002 + Value = simple_strtol(pValueStr, 0, 10);
66003 + if (Value == 0)
66004 + {
66005 + pAd->CommonCfg.bBADecline = FALSE;
66006 + }
66007 + else
66008 + {
66009 + pAd->CommonCfg.bBADecline = TRUE;
66010 + }
66011 + DBGPRINT(RT_DEBUG_TRACE, ("HT: BA Decline = %s\n", (Value==0) ? "Disable" : "Enable"));
66012 + }
66013 +
66014 +
66015 + if (RTMPGetKeyParameter("HT_DisableReordering", pValueStr, 25, pInput))
66016 + {
66017 + Value = simple_strtol(pValueStr, 0, 10);
66018 + if (Value == 0)
66019 + {
66020 + pAd->CommonCfg.bDisableReordering = FALSE;
66021 + }
66022 + else
66023 + {
66024 + pAd->CommonCfg.bDisableReordering = TRUE;
66025 + }
66026 + DBGPRINT(RT_DEBUG_TRACE, ("HT: DisableReordering = %s\n", (Value==0) ? "Disable" : "Enable"));
66027 + }
66028 +
66029 + if (RTMPGetKeyParameter("HT_AutoBA", pValueStr, 25, pInput))
66030 + {
66031 + Value = simple_strtol(pValueStr, 0, 10);
66032 + if (Value == 0)
66033 + {
66034 + pAd->CommonCfg.BACapability.field.AutoBA = FALSE;
66035 + }
66036 + else
66037 + {
66038 + pAd->CommonCfg.BACapability.field.AutoBA = TRUE;
66039 + }
66040 + pAd->CommonCfg.REGBACapability.field.AutoBA = pAd->CommonCfg.BACapability.field.AutoBA;
66041 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Auto BA = %s\n", (Value==0) ? "Disable" : "Enable"));
66042 + }
66043 +
66044 + // Tx_+HTC frame
66045 + if (RTMPGetKeyParameter("HT_HTC", pValueStr, 25, pInput))
66046 + {
66047 + Value = simple_strtol(pValueStr, 0, 10);
66048 + if (Value == 0)
66049 + {
66050 + pAd->HTCEnable = FALSE;
66051 + }
66052 + else
66053 + {
66054 + pAd->HTCEnable = TRUE;
66055 + }
66056 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Tx +HTC frame = %s\n", (Value==0) ? "Disable" : "Enable"));
66057 + }
66058 +
66059 + // Enable HT Link Adaptation Control
66060 + if (RTMPGetKeyParameter("HT_LinkAdapt", pValueStr, 25, pInput))
66061 + {
66062 + Value = simple_strtol(pValueStr, 0, 10);
66063 + if (Value == 0)
66064 + {
66065 + pAd->bLinkAdapt = FALSE;
66066 + }
66067 + else
66068 + {
66069 + pAd->HTCEnable = TRUE;
66070 + pAd->bLinkAdapt = TRUE;
66071 + }
66072 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Link Adaptation Control = %s\n", (Value==0) ? "Disable" : "Enable(+HTC)"));
66073 + }
66074 +
66075 + // Reverse Direction Mechanism
66076 + if (RTMPGetKeyParameter("HT_RDG", pValueStr, 25, pInput))
66077 + {
66078 + Value = simple_strtol(pValueStr, 0, 10);
66079 + if (Value == 0)
66080 + {
66081 + pAd->CommonCfg.bRdg = FALSE;
66082 + }
66083 + else
66084 + {
66085 + pAd->HTCEnable = TRUE;
66086 + pAd->CommonCfg.bRdg = TRUE;
66087 + }
66088 + DBGPRINT(RT_DEBUG_TRACE, ("HT: RDG = %s\n", (Value==0) ? "Disable" : "Enable(+HTC)"));
66089 + }
66090 +
66091 +
66092 +
66093 +
66094 + // Tx A-MSUD ?
66095 + if (RTMPGetKeyParameter("HT_AMSDU", pValueStr, 25, pInput))
66096 + {
66097 + Value = simple_strtol(pValueStr, 0, 10);
66098 + if (Value == 0)
66099 + {
66100 + pAd->CommonCfg.BACapability.field.AmsduEnable = FALSE;
66101 + }
66102 + else
66103 + {
66104 + pAd->CommonCfg.BACapability.field.AmsduEnable = TRUE;
66105 + }
66106 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Tx A-MSDU = %s\n", (Value==0) ? "Disable" : "Enable"));
66107 + }
66108 +
66109 + // MPDU Density
66110 + if (RTMPGetKeyParameter("HT_MpduDensity", pValueStr, 25, pInput))
66111 + {
66112 + Value = simple_strtol(pValueStr, 0, 10);
66113 + if (Value <=7 && Value >= 0)
66114 + {
66115 + pAd->CommonCfg.BACapability.field.MpduDensity = Value;
66116 + DBGPRINT(RT_DEBUG_TRACE, ("HT: MPDU Density = %d\n", Value));
66117 + }
66118 + else
66119 + {
66120 + pAd->CommonCfg.BACapability.field.MpduDensity = 4;
66121 + DBGPRINT(RT_DEBUG_TRACE, ("HT: MPDU Density = %d (Default)\n", 4));
66122 + }
66123 + }
66124 +
66125 + // Max Rx BA Window Size
66126 + if (RTMPGetKeyParameter("HT_BAWinSize", pValueStr, 25, pInput))
66127 + {
66128 + Value = simple_strtol(pValueStr, 0, 10);
66129 +
66130 + if (Value >=1 && Value <= 64)
66131 + {
66132 + pAd->CommonCfg.REGBACapability.field.RxBAWinLimit = Value;
66133 + pAd->CommonCfg.BACapability.field.RxBAWinLimit = Value;
66134 + DBGPRINT(RT_DEBUG_TRACE, ("HT: BA Windw Size = %d\n", Value));
66135 + }
66136 + else
66137 + {
66138 + pAd->CommonCfg.REGBACapability.field.RxBAWinLimit = 64;
66139 + pAd->CommonCfg.BACapability.field.RxBAWinLimit = 64;
66140 + DBGPRINT(RT_DEBUG_TRACE, ("HT: BA Windw Size = 64 (Defualt)\n"));
66141 + }
66142 +
66143 + }
66144 +
66145 + // Guard Interval
66146 + if (RTMPGetKeyParameter("HT_GI", pValueStr, 25, pInput))
66147 + {
66148 + Value = simple_strtol(pValueStr, 0, 10);
66149 +
66150 + if (Value == GI_400)
66151 + {
66152 + pAd->CommonCfg.RegTransmitSetting.field.ShortGI = GI_400;
66153 + }
66154 + else
66155 + {
66156 + pAd->CommonCfg.RegTransmitSetting.field.ShortGI = GI_800;
66157 + }
66158 +
66159 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Guard Interval = %s\n", (Value==GI_400) ? "400" : "800" ));
66160 + }
66161 +
66162 + // HT Operation Mode : Mixed Mode , Green Field
66163 + if (RTMPGetKeyParameter("HT_OpMode", pValueStr, 25, pInput))
66164 + {
66165 + Value = simple_strtol(pValueStr, 0, 10);
66166 +
66167 + if (Value == HTMODE_GF)
66168 + {
66169 +
66170 + pAd->CommonCfg.RegTransmitSetting.field.HTMODE = HTMODE_GF;
66171 + }
66172 + else
66173 + {
66174 + pAd->CommonCfg.RegTransmitSetting.field.HTMODE = HTMODE_MM;
66175 + }
66176 +
66177 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Operate Mode = %s\n", (Value==HTMODE_GF) ? "Green Field" : "Mixed Mode" ));
66178 + }
66179 +
66180 + // Fixed Tx mode : CCK, OFDM
66181 + if (RTMPGetKeyParameter("FixedTxMode", pValueStr, 25, pInput))
66182 + {
66183 + UCHAR fix_tx_mode;
66184 +
66185 +#ifdef CONFIG_STA_SUPPORT
66186 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
66187 + {
66188 + fix_tx_mode = FIXED_TXMODE_HT;
66189 +
66190 + if (strcmp(pValueStr, "OFDM") == 0 || strcmp(pValueStr, "ofdm") == 0)
66191 + {
66192 + fix_tx_mode = FIXED_TXMODE_OFDM;
66193 + }
66194 + else if (strcmp(pValueStr, "CCK") == 0 || strcmp(pValueStr, "cck") == 0)
66195 + {
66196 + fix_tx_mode = FIXED_TXMODE_CCK;
66197 + }
66198 + else if (strcmp(pValueStr, "HT") == 0 || strcmp(pValueStr, "ht") == 0)
66199 + {
66200 + fix_tx_mode = FIXED_TXMODE_HT;
66201 + }
66202 + else
66203 + {
66204 + Value = simple_strtol(pValueStr, 0, 10);
66205 + // 1 : CCK
66206 + // 2 : OFDM
66207 + // otherwise : HT
66208 + if (Value == FIXED_TXMODE_CCK || Value == FIXED_TXMODE_OFDM)
66209 + fix_tx_mode = Value;
66210 + else
66211 + fix_tx_mode = FIXED_TXMODE_HT;
66212 + }
66213 +
66214 + pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode = fix_tx_mode;
66215 + DBGPRINT(RT_DEBUG_TRACE, ("Fixed Tx Mode = %d\n", fix_tx_mode));
66216 +
66217 + }
66218 +#endif // CONFIG_STA_SUPPORT //
66219 + }
66220 +
66221 +
66222 + // Channel Width
66223 + if (RTMPGetKeyParameter("HT_BW", pValueStr, 25, pInput))
66224 + {
66225 + Value = simple_strtol(pValueStr, 0, 10);
66226 +
66227 + if (Value == BW_40)
66228 + {
66229 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_40;
66230 + }
66231 + else
66232 + {
66233 + pAd->CommonCfg.RegTransmitSetting.field.BW = BW_20;
66234 + }
66235 +
66236 +#ifdef MCAST_RATE_SPECIFIC
66237 + pAd->CommonCfg.MCastPhyMode.field.BW = pAd->CommonCfg.RegTransmitSetting.field.BW;
66238 +#endif // MCAST_RATE_SPECIFIC //
66239 +
66240 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Channel Width = %s\n", (Value==BW_40) ? "40 MHz" : "20 MHz" ));
66241 + }
66242 +
66243 + if (RTMPGetKeyParameter("HT_EXTCHA", pValueStr, 25, pInput))
66244 + {
66245 + Value = simple_strtol(pValueStr, 0, 10);
66246 +
66247 + if (Value == 0)
66248 + {
66249 +
66250 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_BELOW;
66251 + }
66252 + else
66253 + {
66254 + pAd->CommonCfg.RegTransmitSetting.field.EXTCHA = EXTCHA_ABOVE;
66255 + }
66256 +
66257 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Ext Channel = %s\n", (Value==0) ? "BELOW" : "ABOVE" ));
66258 + }
66259 +
66260 + // MSC
66261 + if (RTMPGetKeyParameter("HT_MCS", pValueStr, 50, pInput))
66262 + {
66263 +
66264 +#ifdef CONFIG_STA_SUPPORT
66265 + IF_DEV_CONFIG_OPMODE_ON_STA(pAd)
66266 + {
66267 + Value = simple_strtol(pValueStr, 0, 10);
66268 +
66269 + if ((Value >= 0 && Value <= 23) || (Value == 32)) // 3*3
66270 + {
66271 + pAd->StaCfg.DesiredTransmitSetting.field.MCS = Value;
66272 + pAd->StaCfg.bAutoTxRateSwitch = FALSE;
66273 + DBGPRINT(RT_DEBUG_TRACE, ("HT: MCS = %d\n", pAd->StaCfg.DesiredTransmitSetting.field.MCS));
66274 + }
66275 + else
66276 + {
66277 + pAd->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
66278 + pAd->StaCfg.bAutoTxRateSwitch = TRUE;
66279 + DBGPRINT(RT_DEBUG_TRACE, ("HT: MCS = AUTO\n"));
66280 + }
66281 + }
66282 +#endif // CONFIG_STA_SUPPORT //
66283 + }
66284 +
66285 + // STBC
66286 + if (RTMPGetKeyParameter("HT_STBC", pValueStr, 25, pInput))
66287 + {
66288 + Value = simple_strtol(pValueStr, 0, 10);
66289 + if (Value == STBC_USE)
66290 + {
66291 + pAd->CommonCfg.RegTransmitSetting.field.STBC = STBC_USE;
66292 + }
66293 + else
66294 + {
66295 + pAd->CommonCfg.RegTransmitSetting.field.STBC = STBC_NONE;
66296 + }
66297 + DBGPRINT(RT_DEBUG_TRACE, ("HT: STBC = %d\n", pAd->CommonCfg.RegTransmitSetting.field.STBC));
66298 + }
66299 +
66300 + // 40_Mhz_Intolerant
66301 + if (RTMPGetKeyParameter("HT_40MHZ_INTOLERANT", pValueStr, 25, pInput))
66302 + {
66303 + Value = simple_strtol(pValueStr, 0, 10);
66304 + if (Value == 0)
66305 + {
66306 + pAd->CommonCfg.bForty_Mhz_Intolerant = FALSE;
66307 + }
66308 + else
66309 + {
66310 + pAd->CommonCfg.bForty_Mhz_Intolerant = TRUE;
66311 + }
66312 + DBGPRINT(RT_DEBUG_TRACE, ("HT: 40MHZ INTOLERANT = %d\n", pAd->CommonCfg.bForty_Mhz_Intolerant));
66313 + }
66314 + //HT_TxStream
66315 + if(RTMPGetKeyParameter("HT_TxStream", pValueStr, 10, pInput))
66316 + {
66317 + switch (simple_strtol(pValueStr, 0, 10))
66318 + {
66319 + case 1:
66320 + pAd->CommonCfg.TxStream = 1;
66321 + break;
66322 + case 2:
66323 + pAd->CommonCfg.TxStream = 2;
66324 + break;
66325 + case 3: // 3*3
66326 + default:
66327 + pAd->CommonCfg.TxStream = 3;
66328 +
66329 + if (pAd->MACVersion < RALINK_2883_VERSION)
66330 + pAd->CommonCfg.TxStream = 2; // only 2 tx streams for RT2860 series
66331 + break;
66332 + }
66333 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Tx Stream = %d\n", pAd->CommonCfg.TxStream));
66334 + }
66335 + //HT_RxStream
66336 + if(RTMPGetKeyParameter("HT_RxStream", pValueStr, 10, pInput))
66337 + {
66338 + switch (simple_strtol(pValueStr, 0, 10))
66339 + {
66340 + case 1:
66341 + pAd->CommonCfg.RxStream = 1;
66342 + break;
66343 + case 2:
66344 + pAd->CommonCfg.RxStream = 2;
66345 + break;
66346 + case 3:
66347 + default:
66348 + pAd->CommonCfg.RxStream = 3;
66349 +
66350 + if (pAd->MACVersion < RALINK_2883_VERSION)
66351 + pAd->CommonCfg.RxStream = 2; // only 2 rx streams for RT2860 series
66352 + break;
66353 + }
66354 + DBGPRINT(RT_DEBUG_TRACE, ("HT: Rx Stream = %d\n", pAd->CommonCfg.RxStream));
66355 + }
66356 +
66357 +}
66358 +#endif // DOT11_N_SUPPORT //
66359 +
66360 --- /dev/null
66361 +++ b/drivers/staging/rt2860/spectrum_def.h
66362 @@ -0,0 +1,95 @@
66363 +/*
66364 + *************************************************************************
66365 + * Ralink Tech Inc.
66366 + * 5F., No.36, Taiyuan St., Jhubei City,
66367 + * Hsinchu County 302,
66368 + * Taiwan, R.O.C.
66369 + *
66370 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
66371 + *
66372 + * This program is free software; you can redistribute it and/or modify *
66373 + * it under the terms of the GNU General Public License as published by *
66374 + * the Free Software Foundation; either version 2 of the License, or *
66375 + * (at your option) any later version. *
66376 + * *
66377 + * This program is distributed in the hope that it will be useful, *
66378 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
66379 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
66380 + * GNU General Public License for more details. *
66381 + * *
66382 + * You should have received a copy of the GNU General Public License *
66383 + * along with this program; if not, write to the *
66384 + * Free Software Foundation, Inc., *
66385 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
66386 + * *
66387 + *************************************************************************
66388 +
66389 + Module Name:
66390 + spectrum_def.h
66391 +
66392 + Abstract:
66393 + Handle association related requests either from WSTA or from local MLME
66394 +
66395 + Revision History:
66396 + Who When What
66397 + --------- ---------- ----------------------------------------------
66398 + Fonchi Wu 2008 created for 802.11h
66399 + */
66400 +
66401 +#ifndef __SPECTRUM_DEF_H__
66402 +#define __SPECTRUM_DEF_H__
66403 +
66404 +#define MAX_MEASURE_REQ_TAB_SIZE 3
66405 +#define MAX_HASH_MEASURE_REQ_TAB_SIZE MAX_MEASURE_REQ_TAB_SIZE
66406 +
66407 +#define MAX_TPC_REQ_TAB_SIZE 3
66408 +#define MAX_HASH_TPC_REQ_TAB_SIZE MAX_TPC_REQ_TAB_SIZE
66409 +
66410 +#define MIN_RCV_PWR 100 /* Negative value ((dBm) */
66411 +
66412 +#define RM_TPC_REQ 0
66413 +#define RM_MEASURE_REQ 1
66414 +
66415 +#define RM_BASIC 0
66416 +#define RM_CCA 1
66417 +#define RM_RPI_HISTOGRAM 2
66418 +
66419 +#define TPC_REQ_AGE_OUT 500 /* ms */
66420 +#define MQ_REQ_AGE_OUT 500 /* ms */
66421 +
66422 +#define TPC_DIALOGTOKEN_HASH_INDEX(_DialogToken) ((_DialogToken) % MAX_HASH_TPC_REQ_TAB_SIZE)
66423 +#define MQ_DIALOGTOKEN_HASH_INDEX(_DialogToken) ((_DialogToken) % MAX_MEASURE_REQ_TAB_SIZE)
66424 +
66425 +typedef struct _MEASURE_REQ_ENTRY
66426 +{
66427 + struct _MEASURE_REQ_ENTRY *pNext;
66428 + ULONG lastTime;
66429 + BOOLEAN Valid;
66430 + UINT8 DialogToken;
66431 + UINT8 MeasureDialogToken[3]; // 0:basic measure, 1: CCA measure, 2: RPI_Histogram measure.
66432 +} MEASURE_REQ_ENTRY, *PMEASURE_REQ_ENTRY;
66433 +
66434 +typedef struct _MEASURE_REQ_TAB
66435 +{
66436 + UCHAR Size;
66437 + PMEASURE_REQ_ENTRY Hash[MAX_HASH_MEASURE_REQ_TAB_SIZE];
66438 + MEASURE_REQ_ENTRY Content[MAX_MEASURE_REQ_TAB_SIZE];
66439 +} MEASURE_REQ_TAB, *PMEASURE_REQ_TAB;
66440 +
66441 +typedef struct _TPC_REQ_ENTRY
66442 +{
66443 + struct _TPC_REQ_ENTRY *pNext;
66444 + ULONG lastTime;
66445 + BOOLEAN Valid;
66446 + UINT8 DialogToken;
66447 +} TPC_REQ_ENTRY, *PTPC_REQ_ENTRY;
66448 +
66449 +typedef struct _TPC_REQ_TAB
66450 +{
66451 + UCHAR Size;
66452 + PTPC_REQ_ENTRY Hash[MAX_HASH_TPC_REQ_TAB_SIZE];
66453 + TPC_REQ_ENTRY Content[MAX_TPC_REQ_TAB_SIZE];
66454 +} TPC_REQ_TAB, *PTPC_REQ_TAB;
66455 +
66456 +#endif // __SPECTRUM_DEF_H__ //
66457 +
66458 --- /dev/null
66459 +++ b/drivers/staging/rt2860/spectrum.h
66460 @@ -0,0 +1,322 @@
66461 +/*
66462 + *************************************************************************
66463 + * Ralink Tech Inc.
66464 + * 5F., No.36, Taiyuan St., Jhubei City,
66465 + * Hsinchu County 302,
66466 + * Taiwan, R.O.C.
66467 + *
66468 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
66469 + *
66470 + * This program is free software; you can redistribute it and/or modify *
66471 + * it under the terms of the GNU General Public License as published by *
66472 + * the Free Software Foundation; either version 2 of the License, or *
66473 + * (at your option) any later version. *
66474 + * *
66475 + * This program is distributed in the hope that it will be useful, *
66476 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
66477 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
66478 + * GNU General Public License for more details. *
66479 + * *
66480 + * You should have received a copy of the GNU General Public License *
66481 + * along with this program; if not, write to the *
66482 + * Free Software Foundation, Inc., *
66483 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
66484 + * *
66485 + *************************************************************************
66486 +*/
66487 +
66488 +#ifndef __SPECTRUM_H__
66489 +#define __SPECTRUM_H__
66490 +
66491 +#include "rtmp_type.h"
66492 +#include "spectrum_def.h"
66493 +
66494 +typedef struct PACKED _TPC_REPORT_INFO
66495 +{
66496 + UINT8 TxPwr;
66497 + UINT8 LinkMargin;
66498 +} TPC_REPORT_INFO, *PTPC_REPORT_INFO;
66499 +
66500 +typedef struct PACKED _CH_SW_ANN_INFO
66501 +{
66502 + UINT8 ChSwMode;
66503 + UINT8 Channel;
66504 + UINT8 ChSwCnt;
66505 +} CH_SW_ANN_INFO, *PCH_SW_ANN_INFO;
66506 +
66507 +typedef union PACKED _MEASURE_REQ_MODE
66508 +{
66509 +#ifdef RT_BIG_ENDIAN
66510 + struct PACKED
66511 + {
66512 + UINT8 Rev1:4;
66513 + UINT8 Report:1;
66514 + UINT8 Request:1;
66515 + UINT8 Enable:1;
66516 + UINT8 Rev0:1;
66517 + } field;
66518 +#else
66519 + struct PACKED
66520 + {
66521 + UINT8 Rev0:1;
66522 + UINT8 Enable:1;
66523 + UINT8 Request:1;
66524 + UINT8 Report:1;
66525 + UINT8 Rev1:4;
66526 + } field;
66527 +#endif // RT_BIG_ENDIAN //
66528 + UINT8 word;
66529 +} MEASURE_REQ_MODE, *PMEASURE_REQ_MODE;
66530 +
66531 +typedef struct PACKED _MEASURE_REQ
66532 +{
66533 + UINT8 ChNum;
66534 + UINT64 MeasureStartTime;
66535 + UINT16 MeasureDuration;
66536 +} MEASURE_REQ, *PMEASURE_REQ;
66537 +
66538 +typedef struct PACKED _MEASURE_REQ_INFO
66539 +{
66540 + UINT8 Token;
66541 + MEASURE_REQ_MODE ReqMode;
66542 + UINT8 ReqType;
66543 + MEASURE_REQ MeasureReq;
66544 +} MEASURE_REQ_INFO, *PMEASURE_REQ_INFO;
66545 +
66546 +typedef union PACKED _MEASURE_BASIC_REPORT_MAP
66547 +{
66548 +#ifdef RT_BIG_ENDIAN
66549 + struct PACKED
66550 + {
66551 + UINT8 Rev:3;
66552 + UINT8 Unmeasure:1;
66553 + UINT8 Radar:1;
66554 + UINT8 UnidentifiedSignal:1;
66555 + UINT8 OfdmPreamble:1;
66556 + UINT8 BSS:1;
66557 + } field;
66558 +#else
66559 + struct PACKED
66560 + {
66561 + UINT8 BSS:1;
66562 + UINT8 OfdmPreamble:1;
66563 + UINT8 UnidentifiedSignal:1;
66564 + UINT8 Radar:1;
66565 + UINT8 Unmeasure:1;
66566 + UINT8 Rev:3;
66567 + } field;
66568 +#endif // RT_BIG_ENDIAN //
66569 + UINT8 word;
66570 +} MEASURE_BASIC_REPORT_MAP, *PMEASURE_BASIC_REPORT_MAP;
66571 +
66572 +typedef struct PACKED _MEASURE_BASIC_REPORT
66573 +{
66574 + UINT8 ChNum;
66575 + UINT64 MeasureStartTime;
66576 + UINT16 MeasureDuration;
66577 + MEASURE_BASIC_REPORT_MAP Map;
66578 +} MEASURE_BASIC_REPORT, *PMEASURE_BASIC_REPORT;
66579 +
66580 +typedef struct PACKED _MEASURE_CCA_REPORT
66581 +{
66582 + UINT8 ChNum;
66583 + UINT64 MeasureStartTime;
66584 + UINT16 MeasureDuration;
66585 + UINT8 CCA_Busy_Fraction;
66586 +} MEASURE_CCA_REPORT, *PMEASURE_CCA_REPORT;
66587 +
66588 +typedef struct PACKED _MEASURE_RPI_REPORT
66589 +{
66590 + UINT8 ChNum;
66591 + UINT64 MeasureStartTime;
66592 + UINT16 MeasureDuration;
66593 + UINT8 RPI_Density[8];
66594 +} MEASURE_RPI_REPORT, *PMEASURE_RPI_REPORT;
66595 +
66596 +typedef union PACKED _MEASURE_REPORT_MODE
66597 +{
66598 + struct PACKED
66599 + {
66600 +#ifdef RT_BIG_ENDIAN
66601 + UINT8 Rev:5;
66602 + UINT8 Refused:1;
66603 + UINT8 Incapable:1;
66604 + UINT8 Late:1;
66605 +#else
66606 + UINT8 Late:1;
66607 + UINT8 Incapable:1;
66608 + UINT8 Refused:1;
66609 + UINT8 Rev:5;
66610 +#endif // RT_BIG_ENDIAN //
66611 + } field;
66612 + UINT8 word;
66613 +} MEASURE_REPORT_MODE, *PMEASURE_REPORT_MODE;
66614 +
66615 +typedef struct PACKED _MEASURE_REPORT_INFO
66616 +{
66617 + UINT8 Token;
66618 + MEASURE_REPORT_MODE ReportMode;
66619 + UINT8 ReportType;
66620 + UINT8 Octect[0];
66621 +} MEASURE_REPORT_INFO, *PMEASURE_REPORT_INFO;
66622 +
66623 +typedef struct PACKED _QUIET_INFO
66624 +{
66625 + UINT8 QuietCnt;
66626 + UINT8 QuietPeriod;
66627 + UINT8 QuietDuration;
66628 + UINT8 QuietOffset;
66629 +} QUIET_INFO, *PQUIET_INFO;
66630 +
66631 +/*
66632 + ==========================================================================
66633 + Description:
66634 + Prepare Measurement request action frame and enqueue it into
66635 + management queue waiting for transmition.
66636 +
66637 + Parametrs:
66638 + 1. the destination mac address of the frame.
66639 +
66640 + Return : None.
66641 + ==========================================================================
66642 + */
66643 +VOID EnqueueMeasurementReq(
66644 + IN PRTMP_ADAPTER pAd,
66645 + IN PUCHAR pDA,
66646 + IN UINT8 MeasureToken,
66647 + IN UINT8 MeasureReqMode,
66648 + IN UINT8 MeasureReqType,
66649 + IN UINT8 MeasureCh,
66650 + IN UINT16 MeasureDuration);
66651 +
66652 +/*
66653 + ==========================================================================
66654 + Description:
66655 + Prepare Measurement report action frame and enqueue it into
66656 + management queue waiting for transmition.
66657 +
66658 + Parametrs:
66659 + 1. the destination mac address of the frame.
66660 +
66661 + Return : None.
66662 + ==========================================================================
66663 + */
66664 +VOID EnqueueMeasurementRep(
66665 + IN PRTMP_ADAPTER pAd,
66666 + IN PUCHAR pDA,
66667 + IN UINT8 DialogToken,
66668 + IN UINT8 MeasureToken,
66669 + IN UINT8 MeasureReqMode,
66670 + IN UINT8 MeasureReqType,
66671 + IN UINT8 ReportInfoLen,
66672 + IN PUINT8 pReportInfo);
66673 +
66674 +/*
66675 + ==========================================================================
66676 + Description:
66677 + Prepare TPC Request action frame and enqueue it into
66678 + management queue waiting for transmition.
66679 +
66680 + Parametrs:
66681 + 1. the destination mac address of the frame.
66682 +
66683 + Return : None.
66684 + ==========================================================================
66685 + */
66686 +VOID EnqueueTPCReq(
66687 + IN PRTMP_ADAPTER pAd,
66688 + IN PUCHAR pDA,
66689 + IN UCHAR DialogToken);
66690 +
66691 +/*
66692 + ==========================================================================
66693 + Description:
66694 + Prepare TPC Report action frame and enqueue it into
66695 + management queue waiting for transmition.
66696 +
66697 + Parametrs:
66698 + 1. the destination mac address of the frame.
66699 +
66700 + Return : None.
66701 + ==========================================================================
66702 + */
66703 +VOID EnqueueTPCRep(
66704 + IN PRTMP_ADAPTER pAd,
66705 + IN PUCHAR pDA,
66706 + IN UINT8 DialogToken,
66707 + IN UINT8 TxPwr,
66708 + IN UINT8 LinkMargin);
66709 +
66710 +/*
66711 + ==========================================================================
66712 + Description:
66713 + Prepare Channel Switch Announcement action frame and enqueue it into
66714 + management queue waiting for transmition.
66715 +
66716 + Parametrs:
66717 + 1. the destination mac address of the frame.
66718 + 2. Channel switch announcement mode.
66719 + 2. a New selected channel.
66720 +
66721 + Return : None.
66722 + ==========================================================================
66723 + */
66724 +VOID EnqueueChSwAnn(
66725 + IN PRTMP_ADAPTER pAd,
66726 + IN PUCHAR pDA,
66727 + IN UINT8 ChSwMode,
66728 + IN UINT8 NewCh);
66729 +
66730 +/*
66731 + ==========================================================================
66732 + Description:
66733 + Spectrun action frames Handler such as channel switch annoucement,
66734 + measurement report, measurement request actions frames.
66735 +
66736 + Parametrs:
66737 + Elme - MLME message containing the received frame
66738 +
66739 + Return : None.
66740 + ==========================================================================
66741 + */
66742 +VOID PeerSpectrumAction(
66743 + IN PRTMP_ADAPTER pAd,
66744 + IN MLME_QUEUE_ELEM *Elem);
66745 +
66746 +/*
66747 + ==========================================================================
66748 + Description:
66749 +
66750 + Parametrs:
66751 +
66752 + Return : None.
66753 + ==========================================================================
66754 + */
66755 +INT Set_MeasureReq_Proc(
66756 + IN PRTMP_ADAPTER pAd,
66757 + IN PUCHAR arg);
66758 +
66759 +INT Set_TpcReq_Proc(
66760 + IN PRTMP_ADAPTER pAd,
66761 + IN PUCHAR arg);
66762 +
66763 +VOID MeasureReqTabInit(
66764 + IN PRTMP_ADAPTER pAd);
66765 +
66766 +VOID MeasureReqTabExit(
66767 + IN PRTMP_ADAPTER pAd);
66768 +
66769 +VOID TpcReqTabInit(
66770 + IN PRTMP_ADAPTER pAd);
66771 +
66772 +VOID TpcReqTabExit(
66773 + IN PRTMP_ADAPTER pAd);
66774 +
66775 +VOID NotifyChSwAnnToPeerAPs(
66776 + IN PRTMP_ADAPTER pAd,
66777 + IN PUCHAR pRA,
66778 + IN PUCHAR pTA,
66779 + IN UINT8 ChSwMode,
66780 + IN UINT8 Channel);
66781 +#endif // __SPECTRUM_H__ //
66782 +
66783 --- /dev/null
66784 +++ b/drivers/staging/rt2860/sta/aironet.c
66785 @@ -0,0 +1,1312 @@
66786 +/*
66787 + *************************************************************************
66788 + * Ralink Tech Inc.
66789 + * 5F., No.36, Taiyuan St., Jhubei City,
66790 + * Hsinchu County 302,
66791 + * Taiwan, R.O.C.
66792 + *
66793 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
66794 + *
66795 + * This program is free software; you can redistribute it and/or modify *
66796 + * it under the terms of the GNU General Public License as published by *
66797 + * the Free Software Foundation; either version 2 of the License, or *
66798 + * (at your option) any later version. *
66799 + * *
66800 + * This program is distributed in the hope that it will be useful, *
66801 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
66802 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
66803 + * GNU General Public License for more details. *
66804 + * *
66805 + * You should have received a copy of the GNU General Public License *
66806 + * along with this program; if not, write to the *
66807 + * Free Software Foundation, Inc., *
66808 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
66809 + * *
66810 + *************************************************************************
66811 +
66812 + Module Name:
66813 + aironet.c
66814 +
66815 + Abstract:
66816 +
66817 + Revision History:
66818 + Who When What
66819 + -------- ---------- ----------------------------------------------
66820 + Paul Lin 04-06-15 Initial
66821 +*/
66822 +#include "../rt_config.h"
66823 +
66824 +/*
66825 + ==========================================================================
66826 + Description:
66827 + association state machine init, including state transition and timer init
66828 + Parameters:
66829 + S - pointer to the association state machine
66830 + ==========================================================================
66831 + */
66832 +VOID AironetStateMachineInit(
66833 + IN PRTMP_ADAPTER pAd,
66834 + IN STATE_MACHINE *S,
66835 + OUT STATE_MACHINE_FUNC Trans[])
66836 +{
66837 + StateMachineInit(S, Trans, MAX_AIRONET_STATE, MAX_AIRONET_MSG, (STATE_MACHINE_FUNC)Drop, AIRONET_IDLE, AIRONET_MACHINE_BASE);
66838 + StateMachineSetAction(S, AIRONET_IDLE, MT2_AIRONET_MSG, (STATE_MACHINE_FUNC)AironetMsgAction);
66839 + StateMachineSetAction(S, AIRONET_IDLE, MT2_AIRONET_SCAN_REQ, (STATE_MACHINE_FUNC)AironetRequestAction);
66840 + StateMachineSetAction(S, AIRONET_SCANNING, MT2_AIRONET_SCAN_DONE, (STATE_MACHINE_FUNC)AironetReportAction);
66841 +}
66842 +
66843 +/*
66844 + ==========================================================================
66845 + Description:
66846 + This is state machine function.
66847 + When receiving EAPOL packets which is for 802.1x key management.
66848 + Use both in WPA, and WPAPSK case.
66849 + In this function, further dispatch to different functions according to the received packet. 3 categories are :
66850 + 1. normal 4-way pairwisekey and 2-way groupkey handshake
66851 + 2. MIC error (Countermeasures attack) report packet from STA.
66852 + 3. Request for pairwise/group key update from STA
66853 + Return:
66854 + ==========================================================================
66855 +*/
66856 +VOID AironetMsgAction(
66857 + IN PRTMP_ADAPTER pAd,
66858 + IN MLME_QUEUE_ELEM *Elem)
66859 +{
66860 + USHORT Length;
66861 + UCHAR Index, i;
66862 + PUCHAR pData;
66863 + PAIRONET_RM_REQUEST_FRAME pRMReq;
66864 + PRM_REQUEST_ACTION pReqElem;
66865 +
66866 + DBGPRINT(RT_DEBUG_TRACE, ("-----> AironetMsgAction\n"));
66867 +
66868 + // 0. Get Aironet IAPP header first
66869 + pRMReq = (PAIRONET_RM_REQUEST_FRAME) &Elem->Msg[LENGTH_802_11];
66870 + pData = (PUCHAR) &Elem->Msg[LENGTH_802_11];
66871 +
66872 + // 1. Change endian format form network to little endian
66873 + Length = be2cpu16(pRMReq->IAPP.Length);
66874 +
66875 + // 2.0 Sanity check, this should only happen when CCX 2.0 support is enabled
66876 + if (pAd->StaCfg.CCXEnable != TRUE)
66877 + return;
66878 +
66879 + // 2.1 Radio measurement must be on
66880 + if (pAd->StaCfg.CCXControl.field.RMEnable != 1)
66881 + return;
66882 +
66883 + // 2.2. Debug print all bit information
66884 + DBGPRINT(RT_DEBUG_TRACE, ("IAPP ID & Length %d\n", Length));
66885 + DBGPRINT(RT_DEBUG_TRACE, ("IAPP Type %x\n", pRMReq->IAPP.Type));
66886 + DBGPRINT(RT_DEBUG_TRACE, ("IAPP SubType %x\n", pRMReq->IAPP.SubType));
66887 + DBGPRINT(RT_DEBUG_TRACE, ("IAPP Dialog Token %x\n", pRMReq->IAPP.Token));
66888 + DBGPRINT(RT_DEBUG_TRACE, ("IAPP Activation Delay %x\n", pRMReq->Delay));
66889 + DBGPRINT(RT_DEBUG_TRACE, ("IAPP Measurement Offset %x\n", pRMReq->Offset));
66890 +
66891 + // 3. Check IAPP frame type, it must be 0x32 for Cisco Aironet extension
66892 + if (pRMReq->IAPP.Type != AIRONET_IAPP_TYPE)
66893 + {
66894 + DBGPRINT(RT_DEBUG_ERROR, ("Wrong IAPP type for Cisco Aironet extension\n"));
66895 + return;
66896 + }
66897 +
66898 + // 4. Check IAPP frame subtype, it must be 0x01 for Cisco Aironet extension request.
66899 + // Since we are acting as client only, we will disregards reply subtype.
66900 + if (pRMReq->IAPP.SubType != AIRONET_IAPP_SUBTYPE_REQUEST)
66901 + {
66902 + DBGPRINT(RT_DEBUG_ERROR, ("Wrong IAPP subtype for Cisco Aironet extension\n"));
66903 + return;
66904 + }
66905 +
66906 + // 5. Verify Destination MAC and Source MAC, both should be all zeros.
66907 + if (! MAC_ADDR_EQUAL(pRMReq->IAPP.DA, ZERO_MAC_ADDR))
66908 + {
66909 + DBGPRINT(RT_DEBUG_ERROR, ("Wrong IAPP DA for Cisco Aironet extension, it's not Zero\n"));
66910 + return;
66911 + }
66912 +
66913 + if (! MAC_ADDR_EQUAL(pRMReq->IAPP.SA, ZERO_MAC_ADDR))
66914 + {
66915 + DBGPRINT(RT_DEBUG_ERROR, ("Wrong IAPP SA for Cisco Aironet extension, it's not Zero\n"));
66916 + return;
66917 + }
66918 +
66919 + // 6. Reinit all report related fields
66920 + NdisZeroMemory(pAd->StaCfg.FrameReportBuf, 2048);
66921 + NdisZeroMemory(pAd->StaCfg.BssReportOffset, sizeof(USHORT) * MAX_LEN_OF_BSS_TABLE);
66922 + NdisZeroMemory(pAd->StaCfg.MeasurementRequest, sizeof(RM_REQUEST_ACTION) * 4);
66923 +
66924 + // 7. Point to the start of first element report element
66925 + pAd->StaCfg.FrameReportLen = LENGTH_802_11 + sizeof(AIRONET_IAPP_HEADER);
66926 + DBGPRINT(RT_DEBUG_TRACE, ("FR len = %d\n", pAd->StaCfg.FrameReportLen));
66927 + pAd->StaCfg.LastBssIndex = 0xff;
66928 + pAd->StaCfg.RMReqCnt = 0;
66929 + pAd->StaCfg.ParallelReq = FALSE;
66930 + pAd->StaCfg.ParallelDuration = 0;
66931 + pAd->StaCfg.ParallelChannel = 0;
66932 + pAd->StaCfg.IAPPToken = pRMReq->IAPP.Token;
66933 + pAd->StaCfg.CurrentRMReqIdx = 0;
66934 + pAd->StaCfg.CLBusyBytes = 0;
66935 + // Reset the statistics
66936 + for (i = 0; i < 8; i++)
66937 + pAd->StaCfg.RPIDensity[i] = 0;
66938 +
66939 + Index = 0;
66940 +
66941 + // 8. Save dialog token for report
66942 + pAd->StaCfg.IAPPToken = pRMReq->IAPP.Token;
66943 +
66944 + // Save Activation delay & measurement offset, Not really needed
66945 +
66946 + // 9. Point to the first request element
66947 + pData += sizeof(AIRONET_RM_REQUEST_FRAME);
66948 + // Length should exclude the CISCO Aironet SNAP header
66949 + Length -= (sizeof(AIRONET_RM_REQUEST_FRAME) - LENGTH_802_1_H);
66950 +
66951 + // 10. Start Parsing the Measurement elements.
66952 + // Be careful about multiple MR elements within one frames.
66953 + while (Length > 0)
66954 + {
66955 + pReqElem = (PRM_REQUEST_ACTION) pData;
66956 + switch (pReqElem->ReqElem.Eid)
66957 + {
66958 + case IE_MEASUREMENT_REQUEST:
66959 + // From the example, it seems we only need to support one request in one frame
66960 + // There is no multiple request in one frame.
66961 + // Besides, looks like we need to take care the measurement request only.
66962 + // The measurement request is always 4 bytes.
66963 +
66964 + // Start parsing this type of request.
66965 + // 0. Eid is IE_MEASUREMENT_REQUEST
66966 + // 1. Length didn't include Eid and Length field, it always be 8.
66967 + // 2. Measurement Token, we nned to save it for the corresponding report.
66968 + // 3. Measurement Mode, Although there are definitions, but we din't see value other than
66969 + // 0 from test specs examples.
66970 + // 4. Measurement Type, this is what we need to do.
66971 + switch (pReqElem->ReqElem.Type)
66972 + {
66973 + case MSRN_TYPE_CHANNEL_LOAD_REQ:
66974 + case MSRN_TYPE_NOISE_HIST_REQ:
66975 + case MSRN_TYPE_BEACON_REQ:
66976 + // Check the Enable non-serving channel measurement control
66977 + if (pAd->StaCfg.CCXControl.field.DCRMEnable == 0)
66978 + {
66979 + // Check channel before enqueue the action
66980 + if (pReqElem->Measurement.Channel != pAd->CommonCfg.Channel)
66981 + break;
66982 + }
66983 + else
66984 + {
66985 + // If off channel measurement, check the TU duration limit
66986 + if (pReqElem->Measurement.Channel != pAd->CommonCfg.Channel)
66987 + if (pReqElem->Measurement.Duration > pAd->StaCfg.CCXControl.field.TuLimit)
66988 + break;
66989 + }
66990 +
66991 + // Save requests and execute actions later
66992 + NdisMoveMemory(&pAd->StaCfg.MeasurementRequest[Index], pReqElem, sizeof(RM_REQUEST_ACTION));
66993 + Index += 1;
66994 + break;
66995 +
66996 + case MSRN_TYPE_FRAME_REQ:
66997 + // Since it's option, we will support later
66998 + // FrameRequestAction(pAd, pData);
66999 + break;
67000 +
67001 + default:
67002 + break;
67003 + }
67004 +
67005 + // Point to next Measurement request
67006 + pData += sizeof(RM_REQUEST_ACTION);
67007 + Length -= sizeof(RM_REQUEST_ACTION);
67008 + break;
67009 +
67010 + // We accept request only, all others are dropped
67011 + case IE_MEASUREMENT_REPORT:
67012 + case IE_AP_TX_POWER:
67013 + case IE_MEASUREMENT_CAPABILITY:
67014 + default:
67015 + return;
67016 + }
67017 + }
67018 +
67019 + // 11. Update some flags and index
67020 + pAd->StaCfg.RMReqCnt = Index;
67021 +
67022 + if (Index)
67023 + {
67024 + MlmeEnqueue(pAd, AIRONET_STATE_MACHINE, MT2_AIRONET_SCAN_REQ, 0, NULL);
67025 + RT28XX_MLME_HANDLER(pAd);
67026 + }
67027 +
67028 + DBGPRINT(RT_DEBUG_TRACE, ("<----- AironetMsgAction\n"));
67029 +}
67030 +
67031 +/*
67032 + ========================================================================
67033 +
67034 + Routine Description:
67035 +
67036 + Arguments:
67037 +
67038 + Return Value:
67039 + None
67040 +
67041 + Note:
67042 +
67043 + ========================================================================
67044 +*/
67045 +VOID AironetRequestAction(
67046 + IN PRTMP_ADAPTER pAd,
67047 + IN MLME_QUEUE_ELEM *Elem)
67048 +{
67049 + PRM_REQUEST_ACTION pReq;
67050 +
67051 + // 1. Point to next request element
67052 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[pAd->StaCfg.CurrentRMReqIdx];
67053 +
67054 + // 2. Parse measurement type and call appropriate functions
67055 + if (pReq->ReqElem.Type == MSRN_TYPE_CHANNEL_LOAD_REQ)
67056 + // Channel Load measurement request
67057 + ChannelLoadRequestAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67058 + else if (pReq->ReqElem.Type == MSRN_TYPE_NOISE_HIST_REQ)
67059 + // Noise Histogram measurement request
67060 + NoiseHistRequestAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67061 + else if (pReq->ReqElem.Type == MSRN_TYPE_BEACON_REQ)
67062 + // Beacon measurement request
67063 + BeaconRequestAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67064 + else
67065 + // Unknown. Do nothing and return, this should never happen
67066 + return;
67067 +
67068 + // 3. Peek into the next request, if it's parallel, we will update the scan time to the largest one
67069 + if ((pAd->StaCfg.CurrentRMReqIdx + 1) < pAd->StaCfg.RMReqCnt)
67070 + {
67071 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[pAd->StaCfg.CurrentRMReqIdx + 1];
67072 + // Check for parallel bit
67073 + if ((pReq->ReqElem.Mode & 0x01) && (pReq->Measurement.Channel == pAd->StaCfg.CCXScanChannel))
67074 + {
67075 + // Update parallel mode request information
67076 + pAd->StaCfg.ParallelReq = TRUE;
67077 + pAd->StaCfg.CCXScanTime = ((pReq->Measurement.Duration > pAd->StaCfg.CCXScanTime) ?
67078 + (pReq->Measurement.Duration) : (pAd->StaCfg.CCXScanTime));
67079 + }
67080 + }
67081 +
67082 + // 4. Call RT28XX_MLME_HANDLER to execute the request mlme commands, Scan request is the only one used
67083 + RT28XX_MLME_HANDLER(pAd);
67084 +
67085 +}
67086 +
67087 +
67088 +/*
67089 + ========================================================================
67090 +
67091 + Routine Description:
67092 + Prepare channel load report action, special scan operation added
67093 + to support
67094 +
67095 + Arguments:
67096 + pAd Pointer to our adapter
67097 + pData Start from element ID
67098 +
67099 + Return Value:
67100 + None
67101 +
67102 + Note:
67103 +
67104 + ========================================================================
67105 +*/
67106 +VOID ChannelLoadRequestAction(
67107 + IN PRTMP_ADAPTER pAd,
67108 + IN UCHAR Index)
67109 +{
67110 + PRM_REQUEST_ACTION pReq;
67111 + MLME_SCAN_REQ_STRUCT ScanReq;
67112 + UCHAR ZeroSsid[32];
67113 + NDIS_STATUS NStatus;
67114 + PUCHAR pOutBuffer = NULL;
67115 + PHEADER_802_11 pNullFrame;
67116 +
67117 + DBGPRINT(RT_DEBUG_TRACE, ("ChannelLoadRequestAction ----->\n"));
67118 +
67119 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[Index];
67120 + NdisZeroMemory(ZeroSsid, 32);
67121 +
67122 + // Prepare for special scan request
67123 + // The scan definition is different with our Active, Passive scan definition.
67124 + // For CCX2, Active means send out probe request with broadcast BSSID.
67125 + // Passive means no probe request sent, only listen to the beacons.
67126 + // The channel scanned is fixed as specified, no need to scan all channels.
67127 + // The scan wait time is specified in the request too.
67128 + // Passive scan Mode
67129 +
67130 + // Control state machine is not idle, reject the request
67131 + if ((pAd->Mlme.CntlMachine.CurrState != CNTL_IDLE) && (Index == 0))
67132 + return;
67133 +
67134 + // Fill out stuff for scan request
67135 + ScanParmFill(pAd, &ScanReq, ZeroSsid, 0, BSS_ANY, SCAN_CISCO_CHANNEL_LOAD);
67136 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ, sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
67137 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
67138 +
67139 + // Reset some internal control flags to make sure this scan works.
67140 + BssTableInit(&pAd->StaCfg.CCXBssTab);
67141 + pAd->StaCfg.ScanCnt = 0;
67142 + pAd->StaCfg.CCXScanChannel = pReq->Measurement.Channel;
67143 + pAd->StaCfg.CCXScanTime = pReq->Measurement.Duration;
67144 +
67145 + DBGPRINT(RT_DEBUG_TRACE, ("Duration %d, Channel %d!\n", pReq->Measurement.Duration, pReq->Measurement.Channel));
67146 +
67147 + // If it's non serving channel scan, send out a null frame with PSM bit on.
67148 + if (pAd->StaCfg.CCXScanChannel != pAd->CommonCfg.Channel)
67149 + {
67150 + // Use MLME enqueue method
67151 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
67152 + if (NStatus != NDIS_STATUS_SUCCESS)
67153 + return;
67154 +
67155 + pNullFrame = (PHEADER_802_11) pOutBuffer;;
67156 + // Make the power save Null frame with PSM bit on
67157 + MgtMacHeaderInit(pAd, pNullFrame, SUBTYPE_NULL_FUNC, 1, pAd->CommonCfg.Bssid, pAd->CommonCfg.Bssid);
67158 + pNullFrame->Duration = 0;
67159 + pNullFrame->FC.Type = BTYPE_DATA;
67160 + pNullFrame->FC.PwrMgmt = PWR_SAVE;
67161 +
67162 + // Send using priority queue
67163 + MiniportMMRequest(pAd, 0, pOutBuffer, sizeof(HEADER_802_11));
67164 + MlmeFreeMemory(pAd, pOutBuffer);
67165 + DBGPRINT(RT_DEBUG_TRACE, ("Send PSM Data frame for off channel RM\n"));
67166 + RTMPusecDelay(5000);
67167 + }
67168 +
67169 + pAd->StaCfg.CCXReqType = MSRN_TYPE_CHANNEL_LOAD_REQ;
67170 + pAd->StaCfg.CLBusyBytes = 0;
67171 + // Enable Rx with promiscuous reception
67172 + RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, 0x1010);
67173 +
67174 + // Set channel load measurement flag
67175 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_MEASUREMENT);
67176 +
67177 + pAd->Mlme.AironetMachine.CurrState = AIRONET_SCANNING;
67178 +
67179 + DBGPRINT(RT_DEBUG_TRACE, ("ChannelLoadRequestAction <-----\n"));
67180 +}
67181 +
67182 +/*
67183 + ========================================================================
67184 +
67185 + Routine Description:
67186 + Prepare noise histogram report action, special scan operation added
67187 + to support
67188 +
67189 + Arguments:
67190 + pAd Pointer to our adapter
67191 + pData Start from element ID
67192 +
67193 + Return Value:
67194 + None
67195 +
67196 + Note:
67197 +
67198 + ========================================================================
67199 +*/
67200 +VOID NoiseHistRequestAction(
67201 + IN PRTMP_ADAPTER pAd,
67202 + IN UCHAR Index)
67203 +{
67204 + PRM_REQUEST_ACTION pReq;
67205 + MLME_SCAN_REQ_STRUCT ScanReq;
67206 + UCHAR ZeroSsid[32], i;
67207 + NDIS_STATUS NStatus;
67208 + PUCHAR pOutBuffer = NULL;
67209 + PHEADER_802_11 pNullFrame;
67210 +
67211 + DBGPRINT(RT_DEBUG_TRACE, ("NoiseHistRequestAction ----->\n"));
67212 +
67213 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[Index];
67214 + NdisZeroMemory(ZeroSsid, 32);
67215 +
67216 + // Prepare for special scan request
67217 + // The scan definition is different with our Active, Passive scan definition.
67218 + // For CCX2, Active means send out probe request with broadcast BSSID.
67219 + // Passive means no probe request sent, only listen to the beacons.
67220 + // The channel scanned is fixed as specified, no need to scan all channels.
67221 + // The scan wait time is specified in the request too.
67222 + // Passive scan Mode
67223 +
67224 + // Control state machine is not idle, reject the request
67225 + if ((pAd->Mlme.CntlMachine.CurrState != CNTL_IDLE) && (Index == 0))
67226 + return;
67227 +
67228 + // Fill out stuff for scan request
67229 + ScanParmFill(pAd, &ScanReq, ZeroSsid, 0, BSS_ANY, SCAN_CISCO_NOISE);
67230 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ, sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
67231 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
67232 +
67233 + // Reset some internal control flags to make sure this scan works.
67234 + BssTableInit(&pAd->StaCfg.CCXBssTab);
67235 + pAd->StaCfg.ScanCnt = 0;
67236 + pAd->StaCfg.CCXScanChannel = pReq->Measurement.Channel;
67237 + pAd->StaCfg.CCXScanTime = pReq->Measurement.Duration;
67238 + pAd->StaCfg.CCXReqType = MSRN_TYPE_NOISE_HIST_REQ;
67239 +
67240 + DBGPRINT(RT_DEBUG_TRACE, ("Duration %d, Channel %d!\n", pReq->Measurement.Duration, pReq->Measurement.Channel));
67241 +
67242 + // If it's non serving channel scan, send out a null frame with PSM bit on.
67243 + if (pAd->StaCfg.CCXScanChannel != pAd->CommonCfg.Channel)
67244 + {
67245 + // Use MLME enqueue method
67246 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
67247 + if (NStatus != NDIS_STATUS_SUCCESS)
67248 + return;
67249 +
67250 + pNullFrame = (PHEADER_802_11) pOutBuffer;
67251 + // Make the power save Null frame with PSM bit on
67252 + MgtMacHeaderInit(pAd, pNullFrame, SUBTYPE_NULL_FUNC, 1, pAd->CommonCfg.Bssid, pAd->CommonCfg.Bssid);
67253 + pNullFrame->Duration = 0;
67254 + pNullFrame->FC.Type = BTYPE_DATA;
67255 + pNullFrame->FC.PwrMgmt = PWR_SAVE;
67256 +
67257 + // Send using priority queue
67258 + MiniportMMRequest(pAd, 0, pOutBuffer, sizeof(HEADER_802_11));
67259 + MlmeFreeMemory(pAd, pOutBuffer);
67260 + DBGPRINT(RT_DEBUG_TRACE, ("Send PSM Data frame for off channel RM\n"));
67261 + RTMPusecDelay(5000);
67262 + }
67263 +
67264 + // Reset the statistics
67265 + for (i = 0; i < 8; i++)
67266 + pAd->StaCfg.RPIDensity[i] = 0;
67267 +
67268 + // Enable Rx with promiscuous reception
67269 + RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, 0x1010);
67270 +
67271 + // Set channel load measurement flag
67272 + RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_MEASUREMENT);
67273 +
67274 + pAd->Mlme.AironetMachine.CurrState = AIRONET_SCANNING;
67275 +
67276 + DBGPRINT(RT_DEBUG_TRACE, ("NoiseHistRequestAction <-----\n"));
67277 +}
67278 +
67279 +/*
67280 + ========================================================================
67281 +
67282 + Routine Description:
67283 + Prepare Beacon report action, special scan operation added
67284 + to support
67285 +
67286 + Arguments:
67287 + pAd Pointer to our adapter
67288 + pData Start from element ID
67289 +
67290 + Return Value:
67291 + None
67292 +
67293 + Note:
67294 +
67295 + ========================================================================
67296 +*/
67297 +VOID BeaconRequestAction(
67298 + IN PRTMP_ADAPTER pAd,
67299 + IN UCHAR Index)
67300 +{
67301 + PRM_REQUEST_ACTION pReq;
67302 + NDIS_STATUS NStatus;
67303 + PUCHAR pOutBuffer = NULL;
67304 + PHEADER_802_11 pNullFrame;
67305 + MLME_SCAN_REQ_STRUCT ScanReq;
67306 + UCHAR ZeroSsid[32];
67307 +
67308 + DBGPRINT(RT_DEBUG_TRACE, ("BeaconRequestAction ----->\n"));
67309 +
67310 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[Index];
67311 + NdisZeroMemory(ZeroSsid, 32);
67312 +
67313 + // Prepare for special scan request
67314 + // The scan definition is different with our Active, Passive scan definition.
67315 + // For CCX2, Active means send out probe request with broadcast BSSID.
67316 + // Passive means no probe request sent, only listen to the beacons.
67317 + // The channel scanned is fixed as specified, no need to scan all channels.
67318 + // The scan wait time is specified in the request too.
67319 + if (pReq->Measurement.ScanMode == MSRN_SCAN_MODE_PASSIVE)
67320 + {
67321 + // Passive scan Mode
67322 + DBGPRINT(RT_DEBUG_TRACE, ("Passive Scan Mode!\n"));
67323 +
67324 + // Control state machine is not idle, reject the request
67325 + if ((pAd->Mlme.CntlMachine.CurrState != CNTL_IDLE) && (Index == 0))
67326 + return;
67327 +
67328 + // Fill out stuff for scan request
67329 + ScanParmFill(pAd, &ScanReq, ZeroSsid, 0, BSS_ANY, SCAN_CISCO_PASSIVE);
67330 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ, sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
67331 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
67332 +
67333 + // Reset some internal control flags to make sure this scan works.
67334 + BssTableInit(&pAd->StaCfg.CCXBssTab);
67335 + pAd->StaCfg.ScanCnt = 0;
67336 + pAd->StaCfg.CCXScanChannel = pReq->Measurement.Channel;
67337 + pAd->StaCfg.CCXScanTime = pReq->Measurement.Duration;
67338 + pAd->StaCfg.CCXReqType = MSRN_TYPE_BEACON_REQ;
67339 + DBGPRINT(RT_DEBUG_TRACE, ("Duration %d!\n", pReq->Measurement.Duration));
67340 +
67341 + // If it's non serving channel scan, send out a null frame with PSM bit on.
67342 + if (pAd->StaCfg.CCXScanChannel != pAd->CommonCfg.Channel)
67343 + {
67344 + // Use MLME enqueue method
67345 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
67346 + if (NStatus != NDIS_STATUS_SUCCESS)
67347 + return;
67348 +
67349 + pNullFrame = (PHEADER_802_11) pOutBuffer;
67350 + // Make the power save Null frame with PSM bit on
67351 + MgtMacHeaderInit(pAd, pNullFrame, SUBTYPE_NULL_FUNC, 1, pAd->CommonCfg.Bssid, pAd->CommonCfg.Bssid);
67352 + pNullFrame->Duration = 0;
67353 + pNullFrame->FC.Type = BTYPE_DATA;
67354 + pNullFrame->FC.PwrMgmt = PWR_SAVE;
67355 +
67356 + // Send using priority queue
67357 + MiniportMMRequest(pAd, 0, pOutBuffer, sizeof(HEADER_802_11));
67358 + MlmeFreeMemory(pAd, pOutBuffer);
67359 + DBGPRINT(RT_DEBUG_TRACE, ("Send PSM Data frame for off channel RM\n"));
67360 + RTMPusecDelay(5000);
67361 + }
67362 +
67363 + pAd->Mlme.AironetMachine.CurrState = AIRONET_SCANNING;
67364 + }
67365 + else if (pReq->Measurement.ScanMode == MSRN_SCAN_MODE_ACTIVE)
67366 + {
67367 + // Active scan Mode
67368 + DBGPRINT(RT_DEBUG_TRACE, ("Active Scan Mode!\n"));
67369 +
67370 + // Control state machine is not idle, reject the request
67371 + if (pAd->Mlme.CntlMachine.CurrState != CNTL_IDLE)
67372 + return;
67373 +
67374 + // Fill out stuff for scan request
67375 + ScanParmFill(pAd, &ScanReq, ZeroSsid, 0, BSS_ANY, SCAN_CISCO_ACTIVE);
67376 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ, sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
67377 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
67378 +
67379 + // Reset some internal control flags to make sure this scan works.
67380 + BssTableInit(&pAd->StaCfg.CCXBssTab);
67381 + pAd->StaCfg.ScanCnt = 0;
67382 + pAd->StaCfg.CCXScanChannel = pReq->Measurement.Channel;
67383 + pAd->StaCfg.CCXScanTime = pReq->Measurement.Duration;
67384 + pAd->StaCfg.CCXReqType = MSRN_TYPE_BEACON_REQ;
67385 + DBGPRINT(RT_DEBUG_TRACE, ("Duration %d!\n", pReq->Measurement.Duration));
67386 +
67387 + // If it's non serving channel scan, send out a null frame with PSM bit on.
67388 + if (pAd->StaCfg.CCXScanChannel != pAd->CommonCfg.Channel)
67389 + {
67390 + // Use MLME enqueue method
67391 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); //Get an unused nonpaged memory
67392 + if (NStatus != NDIS_STATUS_SUCCESS)
67393 + return;
67394 +
67395 + pNullFrame = (PHEADER_802_11) pOutBuffer;
67396 + // Make the power save Null frame with PSM bit on
67397 + MgtMacHeaderInit(pAd, pNullFrame, SUBTYPE_NULL_FUNC, 1, pAd->CommonCfg.Bssid, pAd->CommonCfg.Bssid);
67398 + pNullFrame->Duration = 0;
67399 + pNullFrame->FC.Type = BTYPE_DATA;
67400 + pNullFrame->FC.PwrMgmt = PWR_SAVE;
67401 +
67402 + // Send using priority queue
67403 + MiniportMMRequest(pAd, 0, pOutBuffer, sizeof(HEADER_802_11));
67404 + MlmeFreeMemory(pAd, pOutBuffer);
67405 + DBGPRINT(RT_DEBUG_TRACE, ("Send PSM Data frame for off channel RM\n"));
67406 + RTMPusecDelay(5000);
67407 + }
67408 +
67409 + pAd->Mlme.AironetMachine.CurrState = AIRONET_SCANNING;
67410 + }
67411 + else if (pReq->Measurement.ScanMode == MSRN_SCAN_MODE_BEACON_TABLE)
67412 + {
67413 + // Beacon report Mode, report all the APS in current bss table
67414 + DBGPRINT(RT_DEBUG_TRACE, ("Beacon Report Mode!\n"));
67415 +
67416 + // Copy current BSS table to CCX table, we can omit this step later on.
67417 + NdisMoveMemory(&pAd->StaCfg.CCXBssTab, &pAd->ScanTab, sizeof(BSS_TABLE));
67418 +
67419 + // Create beacon report from Bss table
67420 + AironetCreateBeaconReportFromBssTable(pAd);
67421 +
67422 + // Set state to scanning
67423 + pAd->Mlme.AironetMachine.CurrState = AIRONET_SCANNING;
67424 +
67425 + // Enqueue report request
67426 + // Cisco scan request is finished, prepare beacon report
67427 + MlmeEnqueue(pAd, AIRONET_STATE_MACHINE, MT2_AIRONET_SCAN_DONE, 0, NULL);
67428 + }
67429 + else
67430 + {
67431 + // Wrong scan Mode
67432 + DBGPRINT(RT_DEBUG_TRACE, ("Wrong Scan Mode!\n"));
67433 + }
67434 +
67435 + DBGPRINT(RT_DEBUG_TRACE, ("BeaconRequestAction <-----\n"));
67436 +}
67437 +
67438 +/*
67439 + ========================================================================
67440 +
67441 + Routine Description:
67442 +
67443 + Arguments:
67444 +
67445 + Return Value:
67446 + None
67447 +
67448 + Note:
67449 +
67450 + ========================================================================
67451 +*/
67452 +VOID AironetReportAction(
67453 + IN PRTMP_ADAPTER pAd,
67454 + IN MLME_QUEUE_ELEM *Elem)
67455 +{
67456 + PRM_REQUEST_ACTION pReq;
67457 + ULONG Now32;
67458 +
67459 + NdisGetSystemUpTime(&Now32);
67460 + pAd->StaCfg.LastBeaconRxTime = Now32;
67461 +
67462 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[pAd->StaCfg.CurrentRMReqIdx];
67463 +
67464 + DBGPRINT(RT_DEBUG_TRACE, ("AironetReportAction ----->\n"));
67465 +
67466 + // 1. Parse measurement type and call appropriate functions
67467 + if (pReq->ReqElem.Type == MSRN_TYPE_CHANNEL_LOAD_REQ)
67468 + // Channel Load measurement request
67469 + ChannelLoadReportAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67470 + else if (pReq->ReqElem.Type == MSRN_TYPE_NOISE_HIST_REQ)
67471 + // Noise Histogram measurement request
67472 + NoiseHistReportAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67473 + else if (pReq->ReqElem.Type == MSRN_TYPE_BEACON_REQ)
67474 + // Beacon measurement request
67475 + BeaconReportAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67476 + else
67477 + // Unknown. Do nothing and return
67478 + ;
67479 +
67480 + // 2. Point to the correct index of action element, start from 0
67481 + pAd->StaCfg.CurrentRMReqIdx++;
67482 +
67483 + // 3. Check for parallel actions
67484 + if (pAd->StaCfg.ParallelReq == TRUE)
67485 + {
67486 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[pAd->StaCfg.CurrentRMReqIdx];
67487 +
67488 + // Process next action right away
67489 + if (pReq->ReqElem.Type == MSRN_TYPE_CHANNEL_LOAD_REQ)
67490 + // Channel Load measurement request
67491 + ChannelLoadReportAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67492 + else if (pReq->ReqElem.Type == MSRN_TYPE_NOISE_HIST_REQ)
67493 + // Noise Histogram measurement request
67494 + NoiseHistReportAction(pAd, pAd->StaCfg.CurrentRMReqIdx);
67495 +
67496 + pAd->StaCfg.ParallelReq = FALSE;
67497 + pAd->StaCfg.CurrentRMReqIdx++;
67498 + }
67499 +
67500 + if (pAd->StaCfg.CurrentRMReqIdx >= pAd->StaCfg.RMReqCnt)
67501 + {
67502 + // 4. There is no more unprocessed measurement request, go for transmit this report
67503 + AironetFinalReportAction(pAd);
67504 + pAd->Mlme.AironetMachine.CurrState = AIRONET_IDLE;
67505 + }
67506 + else
67507 + {
67508 + pReq = (PRM_REQUEST_ACTION) &pAd->StaCfg.MeasurementRequest[pAd->StaCfg.CurrentRMReqIdx];
67509 +
67510 + if (pReq->Measurement.Channel != pAd->CommonCfg.Channel)
67511 + {
67512 + RTMPusecDelay(100000);
67513 + }
67514 +
67515 + // 5. There are more requests to be measure
67516 + MlmeEnqueue(pAd, AIRONET_STATE_MACHINE, MT2_AIRONET_SCAN_REQ, 0, NULL);
67517 + RT28XX_MLME_HANDLER(pAd);
67518 + }
67519 +
67520 + DBGPRINT(RT_DEBUG_TRACE, ("AironetReportAction <-----\n"));
67521 +}
67522 +
67523 +/*
67524 + ========================================================================
67525 +
67526 + Routine Description:
67527 +
67528 + Arguments:
67529 +
67530 + Return Value:
67531 + None
67532 +
67533 + Note:
67534 +
67535 + ========================================================================
67536 +*/
67537 +VOID AironetFinalReportAction(
67538 + IN PRTMP_ADAPTER pAd)
67539 +{
67540 + PUCHAR pDest;
67541 + PAIRONET_IAPP_HEADER pIAPP;
67542 + PHEADER_802_11 pHeader;
67543 + UCHAR AckRate = RATE_2;
67544 + USHORT AckDuration = 0;
67545 + NDIS_STATUS NStatus;
67546 + PUCHAR pOutBuffer = NULL;
67547 + ULONG FrameLen = 0;
67548 +
67549 + DBGPRINT(RT_DEBUG_TRACE, ("AironetFinalReportAction ----->\n"));
67550 +
67551 + // 0. Set up the frame pointer, Frame was inited at the end of message action
67552 + pDest = &pAd->StaCfg.FrameReportBuf[LENGTH_802_11];
67553 +
67554 + // 1. Update report IAPP fields
67555 + pIAPP = (PAIRONET_IAPP_HEADER) pDest;
67556 +
67557 + // 2. Copy Cisco SNAP header
67558 + NdisMoveMemory(pIAPP->CiscoSnapHeader, SNAP_AIRONET, LENGTH_802_1_H);
67559 +
67560 + // 3. network order for this 16bit length
67561 + pIAPP->Length = cpu2be16(pAd->StaCfg.FrameReportLen - LENGTH_802_11 - LENGTH_802_1_H);
67562 +
67563 + // 3.1 sanity check the report length, ignore it if there is nothing to report
67564 + if (be2cpu16(pIAPP->Length) <= 18)
67565 + return;
67566 +
67567 + // 4. Type must be 0x32
67568 + pIAPP->Type = AIRONET_IAPP_TYPE;
67569 +
67570 + // 5. SubType for report must be 0x81
67571 + pIAPP->SubType = AIRONET_IAPP_SUBTYPE_REPORT;
67572 +
67573 + // 6. DA is not used and must be zero, although the whole frame was cleared at the start of function
67574 + // We will do it again here. We can use BSSID instead
67575 + COPY_MAC_ADDR(pIAPP->DA, pAd->CommonCfg.Bssid);
67576 +
67577 + // 7. SA is the client reporting which must be our MAC
67578 + COPY_MAC_ADDR(pIAPP->SA, pAd->CurrentAddress);
67579 +
67580 + // 8. Copy the saved dialog token
67581 + pIAPP->Token = pAd->StaCfg.IAPPToken;
67582 +
67583 + // 9. Make the Report frame 802.11 header
67584 + // Reuse function in wpa.c
67585 + pHeader = (PHEADER_802_11) pAd->StaCfg.FrameReportBuf;
67586 + pAd->Sequence ++;
67587 + WpaMacHeaderInit(pAd, pHeader, 0, pAd->CommonCfg.Bssid);
67588 +
67589 + // ACK size is 14 include CRC, and its rate is based on real time information
67590 + AckRate = pAd->CommonCfg.ExpectedACKRate[pAd->CommonCfg.MlmeRate];
67591 + AckDuration = RTMPCalcDuration(pAd, AckRate, 14);
67592 + pHeader->Duration = pAd->CommonCfg.Dsifs + AckDuration;
67593 +
67594 + // Use MLME enqueue method
67595 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
67596 + if (NStatus != NDIS_STATUS_SUCCESS)
67597 + return;
67598 +
67599 + // 10. Prepare report frame with dynamic outbuffer. Just simply copy everything.
67600 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
67601 + pAd->StaCfg.FrameReportLen, pAd->StaCfg.FrameReportBuf,
67602 + END_OF_ARGS);
67603 +
67604 + // 11. Send using priority queue
67605 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
67606 + MlmeFreeMemory(pAd, pOutBuffer);
67607 +
67608 + pAd->StaCfg.CCXReqType = MSRN_TYPE_UNUSED;
67609 +
67610 + DBGPRINT(RT_DEBUG_TRACE, ("AironetFinalReportAction <-----\n"));
67611 +}
67612 +
67613 +/*
67614 + ========================================================================
67615 +
67616 + Routine Description:
67617 +
67618 + Arguments:
67619 +
67620 + Return Value:
67621 + None
67622 +
67623 + Note:
67624 +
67625 + ========================================================================
67626 +*/
67627 +VOID ChannelLoadReportAction(
67628 + IN PRTMP_ADAPTER pAd,
67629 + IN UCHAR Index)
67630 +{
67631 + PMEASUREMENT_REPORT_ELEMENT pReport;
67632 + PCHANNEL_LOAD_REPORT pLoad;
67633 + PUCHAR pDest;
67634 + UCHAR CCABusyFraction;
67635 +
67636 + DBGPRINT(RT_DEBUG_TRACE, ("ChannelLoadReportAction ----->\n"));
67637 +
67638 + // Disable Rx with promiscuous reception, make it back to normal
67639 + RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, STANORMAL); // Staion not drop control frame will fail WiFi Certification.
67640 +
67641 + // 0. Setup pointer for processing beacon & probe response
67642 + pDest = (PUCHAR) &pAd->StaCfg.FrameReportBuf[pAd->StaCfg.FrameReportLen];
67643 + pReport = (PMEASUREMENT_REPORT_ELEMENT) pDest;
67644 +
67645 + // 1. Fill Measurement report element field.
67646 + pReport->Eid = IE_MEASUREMENT_REPORT;
67647 + // Fixed Length at 9, not include Eid and length fields
67648 + pReport->Length = 9;
67649 + pReport->Token = pAd->StaCfg.MeasurementRequest[Index].ReqElem.Token;
67650 + pReport->Mode = pAd->StaCfg.MeasurementRequest[Index].ReqElem.Mode;
67651 + pReport->Type = MSRN_TYPE_CHANNEL_LOAD_REQ;
67652 +
67653 + // 2. Fill channel report measurement data
67654 + pDest += sizeof(MEASUREMENT_REPORT_ELEMENT);
67655 + pLoad = (PCHANNEL_LOAD_REPORT) pDest;
67656 + pLoad->Channel = pAd->StaCfg.MeasurementRequest[Index].Measurement.Channel;
67657 + pLoad->Spare = 0;
67658 + pLoad->Duration = pAd->StaCfg.MeasurementRequest[Index].Measurement.Duration;
67659 +
67660 + // 3. Calculate the CCA Busy Fraction
67661 + // (Bytes + ACK size) * 8 / Tx speed * 255 / 1000 / measurement duration, use 24 us Tx speed
67662 + // = (Bytes + ACK) / 12 / duration
67663 + // 9 is the good value for pAd->StaCfg.CLFactor
67664 + // CCABusyFraction = (UCHAR) (pAd->StaCfg.CLBusyBytes / 9 / pLoad->Duration);
67665 + CCABusyFraction = (UCHAR) (pAd->StaCfg.CLBusyBytes / pAd->StaCfg.CLFactor / pLoad->Duration);
67666 + if (CCABusyFraction < 10)
67667 + CCABusyFraction = (UCHAR) (pAd->StaCfg.CLBusyBytes / 3 / pLoad->Duration) + 1;
67668 +
67669 + pLoad->CCABusy = CCABusyFraction;
67670 + DBGPRINT(RT_DEBUG_TRACE, ("CLBusyByte %ld, Duration %d, Result, %d\n", pAd->StaCfg.CLBusyBytes, pLoad->Duration, CCABusyFraction));
67671 +
67672 + DBGPRINT(RT_DEBUG_TRACE, ("FrameReportLen %d\n", pAd->StaCfg.FrameReportLen));
67673 + pAd->StaCfg.FrameReportLen += (sizeof(MEASUREMENT_REPORT_ELEMENT) + sizeof(CHANNEL_LOAD_REPORT));
67674 + DBGPRINT(RT_DEBUG_TRACE, ("FrameReportLen %d\n", pAd->StaCfg.FrameReportLen));
67675 +
67676 + // 4. Clear channel load measurement flag
67677 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_RADIO_MEASUREMENT);
67678 +
67679 + // 5. reset to idle state
67680 + pAd->Mlme.AironetMachine.CurrState = AIRONET_IDLE;
67681 +
67682 + DBGPRINT(RT_DEBUG_TRACE, ("ChannelLoadReportAction <-----\n"));
67683 +}
67684 +
67685 +/*
67686 + ========================================================================
67687 +
67688 + Routine Description:
67689 +
67690 + Arguments:
67691 +
67692 + Return Value:
67693 + None
67694 +
67695 + Note:
67696 +
67697 + ========================================================================
67698 +*/
67699 +VOID NoiseHistReportAction(
67700 + IN PRTMP_ADAPTER pAd,
67701 + IN UCHAR Index)
67702 +{
67703 + PMEASUREMENT_REPORT_ELEMENT pReport;
67704 + PNOISE_HIST_REPORT pNoise;
67705 + PUCHAR pDest;
67706 + UCHAR i,NoiseCnt;
67707 + USHORT TotalRPICnt, TotalRPISum;
67708 +
67709 + DBGPRINT(RT_DEBUG_TRACE, ("NoiseHistReportAction ----->\n"));
67710 +
67711 + // 0. Disable Rx with promiscuous reception, make it back to normal
67712 + RTMP_IO_WRITE32(pAd, RX_FILTR_CFG, STANORMAL); // Staion not drop control frame will fail WiFi Certification.
67713 + // 1. Setup pointer for processing beacon & probe response
67714 + pDest = (PUCHAR) &pAd->StaCfg.FrameReportBuf[pAd->StaCfg.FrameReportLen];
67715 + pReport = (PMEASUREMENT_REPORT_ELEMENT) pDest;
67716 +
67717 + // 2. Fill Measurement report element field.
67718 + pReport->Eid = IE_MEASUREMENT_REPORT;
67719 + // Fixed Length at 16, not include Eid and length fields
67720 + pReport->Length = 16;
67721 + pReport->Token = pAd->StaCfg.MeasurementRequest[Index].ReqElem.Token;
67722 + pReport->Mode = pAd->StaCfg.MeasurementRequest[Index].ReqElem.Mode;
67723 + pReport->Type = MSRN_TYPE_NOISE_HIST_REQ;
67724 +
67725 + // 3. Fill noise histogram report measurement data
67726 + pDest += sizeof(MEASUREMENT_REPORT_ELEMENT);
67727 + pNoise = (PNOISE_HIST_REPORT) pDest;
67728 + pNoise->Channel = pAd->StaCfg.MeasurementRequest[Index].Measurement.Channel;
67729 + pNoise->Spare = 0;
67730 + pNoise->Duration = pAd->StaCfg.MeasurementRequest[Index].Measurement.Duration;
67731 + // 4. Fill Noise histogram, the total RPI counts should be 0.4 * TU
67732 + // We estimate 4000 normal packets received durning 10 seconds test.
67733 + // Adjust it if required.
67734 + // 3 is a good value for pAd->StaCfg.NHFactor
67735 + // TotalRPICnt = pNoise->Duration * 3 / 10;
67736 + TotalRPICnt = pNoise->Duration * pAd->StaCfg.NHFactor / 10;
67737 + TotalRPISum = 0;
67738 +
67739 + for (i = 0; i < 8; i++)
67740 + {
67741 + TotalRPISum += pAd->StaCfg.RPIDensity[i];
67742 + DBGPRINT(RT_DEBUG_TRACE, ("RPI %d Conuts %d\n", i, pAd->StaCfg.RPIDensity[i]));
67743 + }
67744 +
67745 + // Double check if the counter is larger than our expectation.
67746 + // We will replace it with the total number plus a fraction.
67747 + if (TotalRPISum > TotalRPICnt)
67748 + TotalRPICnt = TotalRPISum + pNoise->Duration / 20;
67749 +
67750 + DBGPRINT(RT_DEBUG_TRACE, ("Total RPI Conuts %d\n", TotalRPICnt));
67751 +
67752 + // 5. Initialize noise count for the total summation of 0xff
67753 + NoiseCnt = 0;
67754 + for (i = 1; i < 8; i++)
67755 + {
67756 + pNoise->Density[i] = (UCHAR) (pAd->StaCfg.RPIDensity[i] * 255 / TotalRPICnt);
67757 + if ((pNoise->Density[i] == 0) && (pAd->StaCfg.RPIDensity[i] != 0))
67758 + pNoise->Density[i]++;
67759 + NoiseCnt += pNoise->Density[i];
67760 + DBGPRINT(RT_DEBUG_TRACE, ("Reported RPI[%d] = 0x%02x\n", i, pNoise->Density[i]));
67761 + }
67762 +
67763 + // 6. RPI[0] represents the rest of counts
67764 + pNoise->Density[0] = 0xff - NoiseCnt;
67765 + DBGPRINT(RT_DEBUG_TRACE, ("Reported RPI[0] = 0x%02x\n", pNoise->Density[0]));
67766 +
67767 + pAd->StaCfg.FrameReportLen += (sizeof(MEASUREMENT_REPORT_ELEMENT) + sizeof(NOISE_HIST_REPORT));
67768 +
67769 + // 7. Clear channel load measurement flag
67770 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_RADIO_MEASUREMENT);
67771 +
67772 + // 8. reset to idle state
67773 + pAd->Mlme.AironetMachine.CurrState = AIRONET_IDLE;
67774 +
67775 + DBGPRINT(RT_DEBUG_TRACE, ("NoiseHistReportAction <-----\n"));
67776 +}
67777 +
67778 +/*
67779 + ========================================================================
67780 +
67781 + Routine Description:
67782 + Prepare Beacon report action,
67783 +
67784 + Arguments:
67785 + pAd Pointer to our adapter
67786 +
67787 + Return Value:
67788 + None
67789 +
67790 + Note:
67791 +
67792 + ========================================================================
67793 +*/
67794 +VOID BeaconReportAction(
67795 + IN PRTMP_ADAPTER pAd,
67796 + IN UCHAR Index)
67797 +{
67798 + DBGPRINT(RT_DEBUG_TRACE, ("BeaconReportAction ----->\n"));
67799 +
67800 + // Looks like we don't have anything thing need to do here.
67801 + // All measurement report already finished in AddBeaconReport
67802 + // The length is in the FrameReportLen
67803 +
67804 + // reset Beacon index for next beacon request
67805 + pAd->StaCfg.LastBssIndex = 0xff;
67806 +
67807 + // reset to idle state
67808 + pAd->Mlme.AironetMachine.CurrState = AIRONET_IDLE;
67809 +
67810 + DBGPRINT(RT_DEBUG_TRACE, ("BeaconReportAction <-----\n"));
67811 +}
67812 +
67813 +/*
67814 + ========================================================================
67815 +
67816 + Routine Description:
67817 +
67818 + Arguments:
67819 + Index Current BSSID in CCXBsstab entry index
67820 +
67821 + Return Value:
67822 +
67823 + Note:
67824 +
67825 + ========================================================================
67826 +*/
67827 +VOID AironetAddBeaconReport(
67828 + IN PRTMP_ADAPTER pAd,
67829 + IN ULONG Index,
67830 + IN PMLME_QUEUE_ELEM pElem)
67831 +{
67832 + PVOID pMsg;
67833 + PUCHAR pSrc, pDest;
67834 + UCHAR ReqIdx;
67835 + ULONG MsgLen;
67836 + USHORT Length;
67837 + PFRAME_802_11 pFrame;
67838 + PMEASUREMENT_REPORT_ELEMENT pReport;
67839 + PEID_STRUCT pEid;
67840 + PBEACON_REPORT pBeaconReport;
67841 + PBSS_ENTRY pBss;
67842 +
67843 + // 0. Setup pointer for processing beacon & probe response
67844 + pMsg = pElem->Msg;
67845 + MsgLen = pElem->MsgLen;
67846 + pFrame = (PFRAME_802_11) pMsg;
67847 + pSrc = pFrame->Octet; // Start from AP TSF
67848 + pBss = (PBSS_ENTRY) &pAd->StaCfg.CCXBssTab.BssEntry[Index];
67849 + ReqIdx = pAd->StaCfg.CurrentRMReqIdx;
67850 +
67851 + // 1 Check the Index, if we already create this entry, only update the average RSSI
67852 + if ((Index <= pAd->StaCfg.LastBssIndex) && (pAd->StaCfg.LastBssIndex != 0xff))
67853 + {
67854 + pDest = (PUCHAR) &pAd->StaCfg.FrameReportBuf[pAd->StaCfg.BssReportOffset[Index]];
67855 + // Point to bss report information
67856 + pDest += sizeof(MEASUREMENT_REPORT_ELEMENT);
67857 + pBeaconReport = (PBEACON_REPORT) pDest;
67858 +
67859 + // Update Rx power, in dBm
67860 + // Get the original RSSI readback from BBP
67861 + pBeaconReport->RxPower += pAd->BbpRssiToDbmDelta;
67862 + // Average the Rssi reading
67863 + pBeaconReport->RxPower = (pBeaconReport->RxPower + pBss->Rssi) / 2;
67864 + // Get to dBm format
67865 + pBeaconReport->RxPower -= pAd->BbpRssiToDbmDelta;
67866 +
67867 + DBGPRINT(RT_DEBUG_TRACE, ("Bssid %02x:%02x:%02x:%02x:%02x:%02x ",
67868 + pBss->Bssid[0], pBss->Bssid[1], pBss->Bssid[2],
67869 + pBss->Bssid[3], pBss->Bssid[4], pBss->Bssid[5]));
67870 + DBGPRINT(RT_DEBUG_TRACE, ("RxPower[%ld] Rssi %d, Avg Rssi %d\n", Index, (pBss->Rssi - pAd->BbpRssiToDbmDelta), pBeaconReport->RxPower - 256));
67871 + DBGPRINT(RT_DEBUG_TRACE, ("FrameReportLen = %d\n", pAd->StaCfg.BssReportOffset[Index]));
67872 +
67873 + // Update other information here
67874 +
67875 + // Done
67876 + return;
67877 + }
67878 +
67879 + // 2. Update reported Index
67880 + pAd->StaCfg.LastBssIndex = Index;
67881 +
67882 + // 3. Setup the buffer address for copying this BSSID into reporting frame
67883 + // The offset should start after 802.11 header and report frame header.
67884 + pDest = (PUCHAR) &pAd->StaCfg.FrameReportBuf[pAd->StaCfg.FrameReportLen];
67885 +
67886 + // 4. Save the start offset of each Bss in report frame
67887 + pAd->StaCfg.BssReportOffset[Index] = pAd->StaCfg.FrameReportLen;
67888 +
67889 + // 5. Fill Measurement report fields
67890 + pReport = (PMEASUREMENT_REPORT_ELEMENT) pDest;
67891 + pReport->Eid = IE_MEASUREMENT_REPORT;
67892 + pReport->Length = 0;
67893 + pReport->Token = pAd->StaCfg.MeasurementRequest[ReqIdx].ReqElem.Token;
67894 + pReport->Mode = pAd->StaCfg.MeasurementRequest[ReqIdx].ReqElem.Mode;
67895 + pReport->Type = MSRN_TYPE_BEACON_REQ;
67896 + Length = sizeof(MEASUREMENT_REPORT_ELEMENT);
67897 + pDest += sizeof(MEASUREMENT_REPORT_ELEMENT);
67898 +
67899 + // 6. Start thebeacon report format
67900 + pBeaconReport = (PBEACON_REPORT) pDest;
67901 + pDest += sizeof(BEACON_REPORT);
67902 + Length += sizeof(BEACON_REPORT);
67903 +
67904 + // 7. Copy Channel number
67905 + pBeaconReport->Channel = pBss->Channel;
67906 + pBeaconReport->Spare = 0;
67907 + pBeaconReport->Duration = pAd->StaCfg.MeasurementRequest[ReqIdx].Measurement.Duration;
67908 + pBeaconReport->PhyType = ((pBss->SupRateLen+pBss->ExtRateLen > 4) ? PHY_ERP : PHY_DSS);
67909 + // 8. Rx power, in dBm
67910 + pBeaconReport->RxPower = pBss->Rssi - pAd->BbpRssiToDbmDelta;
67911 +
67912 + DBGPRINT(RT_DEBUG_TRACE, ("Bssid %02x:%02x:%02x:%02x:%02x:%02x ",
67913 + pBss->Bssid[0], pBss->Bssid[1], pBss->Bssid[2],
67914 + pBss->Bssid[3], pBss->Bssid[4], pBss->Bssid[5]));
67915 + DBGPRINT(RT_DEBUG_TRACE, ("RxPower[%ld], Rssi %d\n", Index, pBeaconReport->RxPower - 256));
67916 + DBGPRINT(RT_DEBUG_TRACE, ("FrameReportLen = %d\n", pAd->StaCfg.FrameReportLen));
67917 +
67918 + pBeaconReport->BeaconInterval = pBss->BeaconPeriod;
67919 + COPY_MAC_ADDR(pBeaconReport->BSSID, pFrame->Hdr.Addr3);
67920 + NdisMoveMemory(pBeaconReport->ParentTSF, pSrc, 4);
67921 + NdisMoveMemory(pBeaconReport->TargetTSF, &pElem->TimeStamp.u.LowPart, 4);
67922 + NdisMoveMemory(&pBeaconReport->TargetTSF[4], &pElem->TimeStamp.u.HighPart, 4);
67923 +
67924 + // 9. Skip the beacon frame and offset to start of capabilityinfo since we already processed capabilityinfo
67925 + pSrc += (TIMESTAMP_LEN + 2);
67926 + pBeaconReport->CapabilityInfo = *(USHORT *)pSrc;
67927 +
67928 + // 10. Point to start of element ID
67929 + pSrc += 2;
67930 + pEid = (PEID_STRUCT) pSrc;
67931 +
67932 + // 11. Start process all variable Eid oayload and add the appropriate to the frame report
67933 + while (((PUCHAR) pEid + pEid->Len + 1) < ((PUCHAR) pFrame + MsgLen))
67934 + {
67935 + // Only limited EID are required to report for CCX 2. It includes SSID, Supported rate,
67936 + // FH paramenter set, DS parameter set, CF parameter set, IBSS parameter set,
67937 + // TIM (report first 4 bytes only, radio measurement capability
67938 + switch (pEid->Eid)
67939 + {
67940 + case IE_SSID:
67941 + case IE_SUPP_RATES:
67942 + case IE_FH_PARM:
67943 + case IE_DS_PARM:
67944 + case IE_CF_PARM:
67945 + case IE_IBSS_PARM:
67946 + NdisMoveMemory(pDest, pEid, pEid->Len + 2);
67947 + pDest += (pEid->Len + 2);
67948 + Length += (pEid->Len + 2);
67949 + break;
67950 +
67951 + case IE_MEASUREMENT_CAPABILITY:
67952 + // Since this IE is duplicated with WPA security IE, we has to do sanity check before
67953 + // recognize it.
67954 + // 1. It also has fixed 6 bytes IE length.
67955 + if (pEid->Len != 6)
67956 + break;
67957 + // 2. Check the Cisco Aironet OUI
67958 + if (NdisEqualMemory(CISCO_OUI, (pSrc + 2), 3))
67959 + {
67960 + // Matched, this is what we want
67961 + NdisMoveMemory(pDest, pEid, pEid->Len + 2);
67962 + pDest += (pEid->Len + 2);
67963 + Length += (pEid->Len + 2);
67964 + }
67965 + break;
67966 +
67967 + case IE_TIM:
67968 + if (pEid->Len > 4)
67969 + {
67970 + // May truncate and report the first 4 bytes only, with the eid & len, total should be 6
67971 + NdisMoveMemory(pDest, pEid, 6);
67972 + pDest += 6;
67973 + Length += 6;
67974 + }
67975 + else
67976 + {
67977 + NdisMoveMemory(pDest, pEid, pEid->Len + 2);
67978 + pDest += (pEid->Len + 2);
67979 + Length += (pEid->Len + 2);
67980 + }
67981 + break;
67982 +
67983 + default:
67984 + break;
67985 + }
67986 + // 12. Move to next element ID
67987 + pSrc += (2 + pEid->Len);
67988 + pEid = (PEID_STRUCT) pSrc;
67989 + }
67990 +
67991 + // 13. Update the length in the header, not include EID and length
67992 + pReport->Length = Length - 4;
67993 +
67994 + // 14. Update the frame report buffer data length
67995 + pAd->StaCfg.FrameReportLen += Length;
67996 + DBGPRINT(RT_DEBUG_TRACE, ("FR len = %d\n", pAd->StaCfg.FrameReportLen));
67997 +}
67998 +
67999 +/*
68000 + ========================================================================
68001 +
68002 + Routine Description:
68003 +
68004 + Arguments:
68005 + Index Current BSSID in CCXBsstab entry index
68006 +
68007 + Return Value:
68008 +
68009 + Note:
68010 +
68011 + ========================================================================
68012 +*/
68013 +VOID AironetCreateBeaconReportFromBssTable(
68014 + IN PRTMP_ADAPTER pAd)
68015 +{
68016 + PMEASUREMENT_REPORT_ELEMENT pReport;
68017 + PBEACON_REPORT pBeaconReport;
68018 + UCHAR Index, ReqIdx;
68019 + USHORT Length;
68020 + PUCHAR pDest;
68021 + PBSS_ENTRY pBss;
68022 +
68023 + // 0. setup base pointer
68024 + ReqIdx = pAd->StaCfg.CurrentRMReqIdx;
68025 +
68026 + for (Index = 0; Index < pAd->StaCfg.CCXBssTab.BssNr; Index++)
68027 + {
68028 + // 1. Setup the buffer address for copying this BSSID into reporting frame
68029 + // The offset should start after 802.11 header and report frame header.
68030 + pDest = (PUCHAR) &pAd->StaCfg.FrameReportBuf[pAd->StaCfg.FrameReportLen];
68031 + pBss = (PBSS_ENTRY) &pAd->StaCfg.CCXBssTab.BssEntry[Index];
68032 + Length = 0;
68033 +
68034 + // 2. Fill Measurement report fields
68035 + pReport = (PMEASUREMENT_REPORT_ELEMENT) pDest;
68036 + pReport->Eid = IE_MEASUREMENT_REPORT;
68037 + pReport->Length = 0;
68038 + pReport->Token = pAd->StaCfg.MeasurementRequest[ReqIdx].ReqElem.Token;
68039 + pReport->Mode = pAd->StaCfg.MeasurementRequest[ReqIdx].ReqElem.Mode;
68040 + pReport->Type = MSRN_TYPE_BEACON_REQ;
68041 + Length = sizeof(MEASUREMENT_REPORT_ELEMENT);
68042 + pDest += sizeof(MEASUREMENT_REPORT_ELEMENT);
68043 +
68044 + // 3. Start the beacon report format
68045 + pBeaconReport = (PBEACON_REPORT) pDest;
68046 + pDest += sizeof(BEACON_REPORT);
68047 + Length += sizeof(BEACON_REPORT);
68048 +
68049 + // 4. Copy Channel number
68050 + pBeaconReport->Channel = pBss->Channel;
68051 + pBeaconReport->Spare = 0;
68052 + pBeaconReport->Duration = pAd->StaCfg.MeasurementRequest[ReqIdx].Measurement.Duration;
68053 + pBeaconReport->PhyType = ((pBss->SupRateLen+pBss->ExtRateLen > 4) ? PHY_ERP : PHY_DSS);
68054 + pBeaconReport->RxPower = pBss->Rssi - pAd->BbpRssiToDbmDelta;
68055 + pBeaconReport->BeaconInterval = pBss->BeaconPeriod;
68056 + pBeaconReport->CapabilityInfo = pBss->CapabilityInfo;
68057 + COPY_MAC_ADDR(pBeaconReport->BSSID, pBss->Bssid);
68058 + NdisMoveMemory(pBeaconReport->ParentTSF, pBss->PTSF, 4);
68059 + NdisMoveMemory(pBeaconReport->TargetTSF, pBss->TTSF, 8);
68060 +
68061 + // 5. Create SSID
68062 + *pDest++ = 0x00;
68063 + *pDest++ = pBss->SsidLen;
68064 + NdisMoveMemory(pDest, pBss->Ssid, pBss->SsidLen);
68065 + pDest += pBss->SsidLen;
68066 + Length += (2 + pBss->SsidLen);
68067 +
68068 + // 6. Create SupportRates
68069 + *pDest++ = 0x01;
68070 + *pDest++ = pBss->SupRateLen;
68071 + NdisMoveMemory(pDest, pBss->SupRate, pBss->SupRateLen);
68072 + pDest += pBss->SupRateLen;
68073 + Length += (2 + pBss->SupRateLen);
68074 +
68075 + // 7. DS Parameter
68076 + *pDest++ = 0x03;
68077 + *pDest++ = 1;
68078 + *pDest++ = pBss->Channel;
68079 + Length += 3;
68080 +
68081 + // 8. IBSS parameter if presents
68082 + if (pBss->BssType == BSS_ADHOC)
68083 + {
68084 + *pDest++ = 0x06;
68085 + *pDest++ = 2;
68086 + *(PUSHORT) pDest = pBss->AtimWin;
68087 + pDest += 2;
68088 + Length += 4;
68089 + }
68090 +
68091 + // 9. Update length field, not include EID and length
68092 + pReport->Length = Length - 4;
68093 +
68094 + // 10. Update total frame size
68095 + pAd->StaCfg.FrameReportLen += Length;
68096 + }
68097 +}
68098 --- /dev/null
68099 +++ b/drivers/staging/rt2860/sta/assoc.c
68100 @@ -0,0 +1,1826 @@
68101 +/*
68102 + *************************************************************************
68103 + * Ralink Tech Inc.
68104 + * 5F., No.36, Taiyuan St., Jhubei City,
68105 + * Hsinchu County 302,
68106 + * Taiwan, R.O.C.
68107 + *
68108 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
68109 + *
68110 + * This program is free software; you can redistribute it and/or modify *
68111 + * it under the terms of the GNU General Public License as published by *
68112 + * the Free Software Foundation; either version 2 of the License, or *
68113 + * (at your option) any later version. *
68114 + * *
68115 + * This program is distributed in the hope that it will be useful, *
68116 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
68117 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
68118 + * GNU General Public License for more details. *
68119 + * *
68120 + * You should have received a copy of the GNU General Public License *
68121 + * along with this program; if not, write to the *
68122 + * Free Software Foundation, Inc., *
68123 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
68124 + * *
68125 + *************************************************************************
68126 +
68127 + Module Name:
68128 + assoc.c
68129 +
68130 + Abstract:
68131 +
68132 + Revision History:
68133 + Who When What
68134 + -------- ---------- ----------------------------------------------
68135 + John 2004-9-3 porting from RT2500
68136 +*/
68137 +#include "../rt_config.h"
68138 +
68139 +UCHAR CipherWpaTemplate[] = {
68140 + 0xdd, // WPA IE
68141 + 0x16, // Length
68142 + 0x00, 0x50, 0xf2, 0x01, // oui
68143 + 0x01, 0x00, // Version
68144 + 0x00, 0x50, 0xf2, 0x02, // Multicast
68145 + 0x01, 0x00, // Number of unicast
68146 + 0x00, 0x50, 0xf2, 0x02, // unicast
68147 + 0x01, 0x00, // number of authentication method
68148 + 0x00, 0x50, 0xf2, 0x01 // authentication
68149 + };
68150 +
68151 +UCHAR CipherWpa2Template[] = {
68152 + 0x30, // RSN IE
68153 + 0x14, // Length
68154 + 0x01, 0x00, // Version
68155 + 0x00, 0x0f, 0xac, 0x02, // group cipher, TKIP
68156 + 0x01, 0x00, // number of pairwise
68157 + 0x00, 0x0f, 0xac, 0x02, // unicast
68158 + 0x01, 0x00, // number of authentication method
68159 + 0x00, 0x0f, 0xac, 0x02, // authentication
68160 + 0x00, 0x00, // RSN capability
68161 + };
68162 +
68163 +UCHAR Ccx2IeInfo[] = { 0x00, 0x40, 0x96, 0x03, 0x02};
68164 +
68165 +/*
68166 + ==========================================================================
68167 + Description:
68168 + association state machine init, including state transition and timer init
68169 + Parameters:
68170 + S - pointer to the association state machine
68171 +
68172 + IRQL = PASSIVE_LEVEL
68173 +
68174 + ==========================================================================
68175 + */
68176 +VOID AssocStateMachineInit(
68177 + IN PRTMP_ADAPTER pAd,
68178 + IN STATE_MACHINE *S,
68179 + OUT STATE_MACHINE_FUNC Trans[])
68180 +{
68181 + StateMachineInit(S, Trans, MAX_ASSOC_STATE, MAX_ASSOC_MSG, (STATE_MACHINE_FUNC)Drop, ASSOC_IDLE, ASSOC_MACHINE_BASE);
68182 +
68183 + // first column
68184 + StateMachineSetAction(S, ASSOC_IDLE, MT2_MLME_ASSOC_REQ, (STATE_MACHINE_FUNC)MlmeAssocReqAction);
68185 + StateMachineSetAction(S, ASSOC_IDLE, MT2_MLME_REASSOC_REQ, (STATE_MACHINE_FUNC)MlmeReassocReqAction);
68186 + StateMachineSetAction(S, ASSOC_IDLE, MT2_MLME_DISASSOC_REQ, (STATE_MACHINE_FUNC)MlmeDisassocReqAction);
68187 + StateMachineSetAction(S, ASSOC_IDLE, MT2_PEER_DISASSOC_REQ, (STATE_MACHINE_FUNC)PeerDisassocAction);
68188 +
68189 + // second column
68190 + StateMachineSetAction(S, ASSOC_WAIT_RSP, MT2_MLME_ASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenAssoc);
68191 + StateMachineSetAction(S, ASSOC_WAIT_RSP, MT2_MLME_REASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenReassoc);
68192 + StateMachineSetAction(S, ASSOC_WAIT_RSP, MT2_MLME_DISASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenDisassociate);
68193 + StateMachineSetAction(S, ASSOC_WAIT_RSP, MT2_PEER_DISASSOC_REQ, (STATE_MACHINE_FUNC)PeerDisassocAction);
68194 + StateMachineSetAction(S, ASSOC_WAIT_RSP, MT2_PEER_ASSOC_RSP, (STATE_MACHINE_FUNC)PeerAssocRspAction);
68195 + //
68196 + // Patch 3Com AP MOde:3CRWE454G72
68197 + // We send Assoc request frame to this AP, it always send Reassoc Rsp not Associate Rsp.
68198 + //
68199 + StateMachineSetAction(S, ASSOC_WAIT_RSP, MT2_PEER_REASSOC_RSP, (STATE_MACHINE_FUNC)PeerAssocRspAction);
68200 + StateMachineSetAction(S, ASSOC_WAIT_RSP, MT2_ASSOC_TIMEOUT, (STATE_MACHINE_FUNC)AssocTimeoutAction);
68201 +
68202 + // third column
68203 + StateMachineSetAction(S, REASSOC_WAIT_RSP, MT2_MLME_ASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenAssoc);
68204 + StateMachineSetAction(S, REASSOC_WAIT_RSP, MT2_MLME_REASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenReassoc);
68205 + StateMachineSetAction(S, REASSOC_WAIT_RSP, MT2_MLME_DISASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenDisassociate);
68206 + StateMachineSetAction(S, REASSOC_WAIT_RSP, MT2_PEER_DISASSOC_REQ, (STATE_MACHINE_FUNC)PeerDisassocAction);
68207 + StateMachineSetAction(S, REASSOC_WAIT_RSP, MT2_PEER_REASSOC_RSP, (STATE_MACHINE_FUNC)PeerReassocRspAction);
68208 + //
68209 + // Patch, AP doesn't send Reassociate Rsp frame to Station.
68210 + //
68211 + StateMachineSetAction(S, REASSOC_WAIT_RSP, MT2_PEER_ASSOC_RSP, (STATE_MACHINE_FUNC)PeerReassocRspAction);
68212 + StateMachineSetAction(S, REASSOC_WAIT_RSP, MT2_REASSOC_TIMEOUT, (STATE_MACHINE_FUNC)ReassocTimeoutAction);
68213 +
68214 + // fourth column
68215 + StateMachineSetAction(S, DISASSOC_WAIT_RSP, MT2_MLME_ASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenAssoc);
68216 + StateMachineSetAction(S, DISASSOC_WAIT_RSP, MT2_MLME_REASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenReassoc);
68217 + StateMachineSetAction(S, DISASSOC_WAIT_RSP, MT2_MLME_DISASSOC_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenDisassociate);
68218 + StateMachineSetAction(S, DISASSOC_WAIT_RSP, MT2_PEER_DISASSOC_REQ, (STATE_MACHINE_FUNC)PeerDisassocAction);
68219 + StateMachineSetAction(S, DISASSOC_WAIT_RSP, MT2_DISASSOC_TIMEOUT, (STATE_MACHINE_FUNC)DisassocTimeoutAction);
68220 +
68221 + // initialize the timer
68222 + RTMPInitTimer(pAd, &pAd->MlmeAux.AssocTimer, GET_TIMER_FUNCTION(AssocTimeout), pAd, FALSE);
68223 + RTMPInitTimer(pAd, &pAd->MlmeAux.ReassocTimer, GET_TIMER_FUNCTION(ReassocTimeout), pAd, FALSE);
68224 + RTMPInitTimer(pAd, &pAd->MlmeAux.DisassocTimer, GET_TIMER_FUNCTION(DisassocTimeout), pAd, FALSE);
68225 +}
68226 +
68227 +/*
68228 + ==========================================================================
68229 + Description:
68230 + Association timeout procedure. After association timeout, this function
68231 + will be called and it will put a message into the MLME queue
68232 + Parameters:
68233 + Standard timer parameters
68234 +
68235 + IRQL = DISPATCH_LEVEL
68236 +
68237 + ==========================================================================
68238 + */
68239 +VOID AssocTimeout(IN PVOID SystemSpecific1,
68240 + IN PVOID FunctionContext,
68241 + IN PVOID SystemSpecific2,
68242 + IN PVOID SystemSpecific3)
68243 +{
68244 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
68245 +
68246 + // Do nothing if the driver is starting halt state.
68247 + // This might happen when timer already been fired before cancel timer with mlmehalt
68248 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
68249 + return;
68250 +
68251 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_ASSOC_TIMEOUT, 0, NULL);
68252 + RT28XX_MLME_HANDLER(pAd);
68253 +}
68254 +
68255 +/*
68256 + ==========================================================================
68257 + Description:
68258 + Reassociation timeout procedure. After reassociation timeout, this
68259 + function will be called and put a message into the MLME queue
68260 + Parameters:
68261 + Standard timer parameters
68262 +
68263 + IRQL = DISPATCH_LEVEL
68264 +
68265 + ==========================================================================
68266 + */
68267 +VOID ReassocTimeout(IN PVOID SystemSpecific1,
68268 + IN PVOID FunctionContext,
68269 + IN PVOID SystemSpecific2,
68270 + IN PVOID SystemSpecific3)
68271 +{
68272 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
68273 +
68274 + // Do nothing if the driver is starting halt state.
68275 + // This might happen when timer already been fired before cancel timer with mlmehalt
68276 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
68277 + return;
68278 +
68279 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_REASSOC_TIMEOUT, 0, NULL);
68280 + RT28XX_MLME_HANDLER(pAd);
68281 +}
68282 +
68283 +/*
68284 + ==========================================================================
68285 + Description:
68286 + Disassociation timeout procedure. After disassociation timeout, this
68287 + function will be called and put a message into the MLME queue
68288 + Parameters:
68289 + Standard timer parameters
68290 +
68291 + IRQL = DISPATCH_LEVEL
68292 +
68293 + ==========================================================================
68294 + */
68295 +VOID DisassocTimeout(IN PVOID SystemSpecific1,
68296 + IN PVOID FunctionContext,
68297 + IN PVOID SystemSpecific2,
68298 + IN PVOID SystemSpecific3)
68299 +{
68300 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
68301 +
68302 + // Do nothing if the driver is starting halt state.
68303 + // This might happen when timer already been fired before cancel timer with mlmehalt
68304 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
68305 + return;
68306 +
68307 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_DISASSOC_TIMEOUT, 0, NULL);
68308 + RT28XX_MLME_HANDLER(pAd);
68309 +}
68310 +
68311 +/*
68312 + ==========================================================================
68313 + Description:
68314 + mlme assoc req handling procedure
68315 + Parameters:
68316 + Adapter - Adapter pointer
68317 + Elem - MLME Queue Element
68318 + Pre:
68319 + the station has been authenticated and the following information is stored in the config
68320 + -# SSID
68321 + -# supported rates and their length
68322 + -# listen interval (Adapter->StaCfg.default_listen_count)
68323 + -# Transmit power (Adapter->StaCfg.tx_power)
68324 + Post :
68325 + -# An association request frame is generated and sent to the air
68326 + -# Association timer starts
68327 + -# Association state -> ASSOC_WAIT_RSP
68328 +
68329 + IRQL = DISPATCH_LEVEL
68330 +
68331 + ==========================================================================
68332 + */
68333 +VOID MlmeAssocReqAction(
68334 + IN PRTMP_ADAPTER pAd,
68335 + IN MLME_QUEUE_ELEM *Elem)
68336 +{
68337 + UCHAR ApAddr[6];
68338 + HEADER_802_11 AssocHdr;
68339 + UCHAR Ccx2Len = 5;
68340 + UCHAR WmeIe[9] = {IE_VENDOR_SPECIFIC, 0x07, 0x00, 0x50, 0xf2, 0x02, 0x00, 0x01, 0x00};
68341 + USHORT ListenIntv;
68342 + ULONG Timeout;
68343 + USHORT CapabilityInfo;
68344 + BOOLEAN TimerCancelled;
68345 + PUCHAR pOutBuffer = NULL;
68346 + NDIS_STATUS NStatus;
68347 + ULONG FrameLen = 0;
68348 + ULONG tmp;
68349 + USHORT VarIesOffset;
68350 + UCHAR CkipFlag;
68351 + UCHAR CkipNegotiationBuffer[CKIP_NEGOTIATION_LENGTH];
68352 + UCHAR AironetCkipIe = IE_AIRONET_CKIP;
68353 + UCHAR AironetCkipLen = CKIP_NEGOTIATION_LENGTH;
68354 + UCHAR AironetIPAddressIE = IE_AIRONET_IPADDRESS;
68355 + UCHAR AironetIPAddressLen = AIRONET_IPADDRESS_LENGTH;
68356 + UCHAR AironetIPAddressBuffer[AIRONET_IPADDRESS_LENGTH] = {0x00, 0x40, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00};
68357 + USHORT Status;
68358 +
68359 + // Block all authentication request durning WPA block period
68360 + if (pAd->StaCfg.bBlockAssoc == TRUE)
68361 + {
68362 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - Block Assoc request durning WPA block period!\n"));
68363 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
68364 + Status = MLME_STATE_MACHINE_REJECT;
68365 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_ASSOC_CONF, 2, &Status);
68366 + }
68367 + // check sanity first
68368 + else if (MlmeAssocReqSanity(pAd, Elem->Msg, Elem->MsgLen, ApAddr, &CapabilityInfo, &Timeout, &ListenIntv))
68369 + {
68370 + RTMPCancelTimer(&pAd->MlmeAux.AssocTimer, &TimerCancelled);
68371 + COPY_MAC_ADDR(pAd->MlmeAux.Bssid, ApAddr);
68372 +
68373 + // Get an unused nonpaged memory
68374 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer);
68375 + if (NStatus != NDIS_STATUS_SUCCESS)
68376 + {
68377 + DBGPRINT(RT_DEBUG_TRACE,("ASSOC - MlmeAssocReqAction() allocate memory failed \n"));
68378 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
68379 + Status = MLME_FAIL_NO_RESOURCE;
68380 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_ASSOC_CONF, 2, &Status);
68381 + return;
68382 + }
68383 +
68384 + // Add by James 03/06/27
68385 + pAd->StaCfg.AssocInfo.Length = sizeof(NDIS_802_11_ASSOCIATION_INFORMATION);
68386 + // Association don't need to report MAC address
68387 + pAd->StaCfg.AssocInfo.AvailableRequestFixedIEs =
68388 + NDIS_802_11_AI_REQFI_CAPABILITIES | NDIS_802_11_AI_REQFI_LISTENINTERVAL;
68389 + pAd->StaCfg.AssocInfo.RequestFixedIEs.Capabilities = CapabilityInfo;
68390 + pAd->StaCfg.AssocInfo.RequestFixedIEs.ListenInterval = ListenIntv;
68391 + // Only reassociate need this
68392 + //COPY_MAC_ADDR(pAd->StaCfg.AssocInfo.RequestFixedIEs.CurrentAPAddress, ApAddr);
68393 + pAd->StaCfg.AssocInfo.OffsetRequestIEs = sizeof(NDIS_802_11_ASSOCIATION_INFORMATION);
68394 +
68395 + NdisZeroMemory(pAd->StaCfg.ReqVarIEs, MAX_VIE_LEN);
68396 + // First add SSID
68397 + VarIesOffset = 0;
68398 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, &SsidIe, 1);
68399 + VarIesOffset += 1;
68400 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, &pAd->MlmeAux.SsidLen, 1);
68401 + VarIesOffset += 1;
68402 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen);
68403 + VarIesOffset += pAd->MlmeAux.SsidLen;
68404 +
68405 + // Second add Supported rates
68406 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, &SupRateIe, 1);
68407 + VarIesOffset += 1;
68408 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, &pAd->MlmeAux.SupRateLen, 1);
68409 + VarIesOffset += 1;
68410 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, pAd->MlmeAux.SupRate, pAd->MlmeAux.SupRateLen);
68411 + VarIesOffset += pAd->MlmeAux.SupRateLen;
68412 + // End Add by James
68413 +
68414 + if ((pAd->CommonCfg.Channel > 14) &&
68415 + (pAd->CommonCfg.bIEEE80211H == TRUE))
68416 + CapabilityInfo |= 0x0100;
68417 +
68418 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - Send ASSOC request...\n"));
68419 + MgtMacHeaderInit(pAd, &AssocHdr, SUBTYPE_ASSOC_REQ, 0, ApAddr, ApAddr);
68420 +
68421 + // Build basic frame first
68422 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
68423 + sizeof(HEADER_802_11), &AssocHdr,
68424 + 2, &CapabilityInfo,
68425 + 2, &ListenIntv,
68426 + 1, &SsidIe,
68427 + 1, &pAd->MlmeAux.SsidLen,
68428 + pAd->MlmeAux.SsidLen, pAd->MlmeAux.Ssid,
68429 + 1, &SupRateIe,
68430 + 1, &pAd->MlmeAux.SupRateLen,
68431 + pAd->MlmeAux.SupRateLen, pAd->MlmeAux.SupRate,
68432 + END_OF_ARGS);
68433 +
68434 + if (pAd->MlmeAux.ExtRateLen != 0)
68435 + {
68436 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68437 + 1, &ExtRateIe,
68438 + 1, &pAd->MlmeAux.ExtRateLen,
68439 + pAd->MlmeAux.ExtRateLen, pAd->MlmeAux.ExtRate,
68440 + END_OF_ARGS);
68441 + FrameLen += tmp;
68442 + }
68443 +
68444 +#ifdef DOT11_N_SUPPORT
68445 + // HT
68446 + if ((pAd->MlmeAux.HtCapabilityLen > 0) && (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
68447 + {
68448 + ULONG TmpLen;
68449 + UCHAR HtLen;
68450 + UCHAR BROADCOM[4] = {0x0, 0x90, 0x4c, 0x33};
68451 + if (pAd->StaActive.SupportedPhyInfo.bPreNHt == TRUE)
68452 + {
68453 + HtLen = SIZE_HT_CAP_IE + 4;
68454 + MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen,
68455 + 1, &WpaIe,
68456 + 1, &HtLen,
68457 + 4, &BROADCOM[0],
68458 + pAd->MlmeAux.HtCapabilityLen, &pAd->MlmeAux.HtCapability,
68459 + END_OF_ARGS);
68460 + }
68461 + else
68462 + {
68463 +#ifdef RT_BIG_ENDIAN
68464 + HT_CAPABILITY_IE HtCapabilityTmp;
68465 +#endif
68466 +
68467 +#ifndef RT_BIG_ENDIAN
68468 + MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen,
68469 + 1, &HtCapIe,
68470 + 1, &pAd->MlmeAux.HtCapabilityLen,
68471 + pAd->MlmeAux.HtCapabilityLen, &pAd->MlmeAux.HtCapability,
68472 + END_OF_ARGS);
68473 +#else
68474 + NdisZeroMemory(&HtCapabilityTmp, sizeof(HT_CAPABILITY_IE));
68475 + NdisMoveMemory(&HtCapabilityTmp, &pAd->MlmeAux.HtCapability, pAd->MlmeAux.HtCapabilityLen);
68476 + *(USHORT *)(&HtCapabilityTmp.HtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.HtCapInfo));
68477 + *(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo));
68478 +
68479 + MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen,
68480 + 1, &HtCapIe,
68481 + 1, &pAd->MlmeAux.HtCapabilityLen,
68482 + pAd->MlmeAux.HtCapabilityLen,&HtCapabilityTmp,
68483 + END_OF_ARGS);
68484 +#endif
68485 + }
68486 + FrameLen += TmpLen;
68487 + }
68488 +#endif // DOT11_N_SUPPORT //
68489 +
68490 + // add Ralink proprietary IE to inform AP this STA is going to use AGGREGATION or PIGGY-BACK+AGGREGATION
68491 + // Case I: (Aggregation + Piggy-Back)
68492 + // 1. user enable aggregation, AND
68493 + // 2. Mac support piggy-back
68494 + // 3. AP annouces it's PIGGY-BACK+AGGREGATION-capable in BEACON
68495 + // Case II: (Aggregation)
68496 + // 1. user enable aggregation, AND
68497 + // 2. AP annouces it's AGGREGATION-capable in BEACON
68498 + if (pAd->CommonCfg.bAggregationCapable)
68499 + {
68500 + if ((pAd->CommonCfg.bPiggyBackCapable) && ((pAd->MlmeAux.APRalinkIe & 0x00000003) == 3))
68501 + {
68502 + ULONG TmpLen;
68503 + UCHAR RalinkIe[9] = {IE_VENDOR_SPECIFIC, 7, 0x00, 0x0c, 0x43, 0x03, 0x00, 0x00, 0x00};
68504 + MakeOutgoingFrame(pOutBuffer+FrameLen, &TmpLen,
68505 + 9, RalinkIe,
68506 + END_OF_ARGS);
68507 + FrameLen += TmpLen;
68508 + }
68509 + else if (pAd->MlmeAux.APRalinkIe & 0x00000001)
68510 + {
68511 + ULONG TmpLen;
68512 + UCHAR RalinkIe[9] = {IE_VENDOR_SPECIFIC, 7, 0x00, 0x0c, 0x43, 0x01, 0x00, 0x00, 0x00};
68513 + MakeOutgoingFrame(pOutBuffer+FrameLen, &TmpLen,
68514 + 9, RalinkIe,
68515 + END_OF_ARGS);
68516 + FrameLen += TmpLen;
68517 + }
68518 + }
68519 + else
68520 + {
68521 + ULONG TmpLen;
68522 + UCHAR RalinkIe[9] = {IE_VENDOR_SPECIFIC, 7, 0x00, 0x0c, 0x43, 0x06, 0x00, 0x00, 0x00};
68523 + MakeOutgoingFrame(pOutBuffer+FrameLen, &TmpLen,
68524 + 9, RalinkIe,
68525 + END_OF_ARGS);
68526 + FrameLen += TmpLen;
68527 + }
68528 +
68529 + if (pAd->MlmeAux.APEdcaParm.bValid)
68530 + {
68531 + if (pAd->CommonCfg.bAPSDCapable && pAd->MlmeAux.APEdcaParm.bAPSDCapable)
68532 + {
68533 + QBSS_STA_INFO_PARM QosInfo;
68534 +
68535 + NdisZeroMemory(&QosInfo, sizeof(QBSS_STA_INFO_PARM));
68536 + QosInfo.UAPSD_AC_BE = pAd->CommonCfg.bAPSDAC_BE;
68537 + QosInfo.UAPSD_AC_BK = pAd->CommonCfg.bAPSDAC_BK;
68538 + QosInfo.UAPSD_AC_VI = pAd->CommonCfg.bAPSDAC_VI;
68539 + QosInfo.UAPSD_AC_VO = pAd->CommonCfg.bAPSDAC_VO;
68540 + QosInfo.MaxSPLength = pAd->CommonCfg.MaxSPLength;
68541 + WmeIe[8] |= *(PUCHAR)&QosInfo;
68542 + }
68543 + else
68544 + {
68545 + // The Parameter Set Count is set to ¡§0¡¨ in the association request frames
68546 + // WmeIe[8] |= (pAd->MlmeAux.APEdcaParm.EdcaUpdateCount & 0x0f);
68547 + }
68548 +
68549 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68550 + 9, &WmeIe[0],
68551 + END_OF_ARGS);
68552 + FrameLen += tmp;
68553 + }
68554 +
68555 + //
68556 + // Let WPA(#221) Element ID on the end of this association frame.
68557 + // Otherwise some AP will fail on parsing Element ID and set status fail on Assoc Rsp.
68558 + // For example: Put Vendor Specific IE on the front of WPA IE.
68559 + // This happens on AP (Model No:Linksys WRK54G)
68560 + //
68561 + if (((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) ||
68562 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK) ||
68563 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) ||
68564 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2)
68565 + )
68566 + )
68567 + {
68568 + UCHAR RSNIe = IE_WPA;
68569 +
68570 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK) ||
68571 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2))
68572 + {
68573 + RSNIe = IE_WPA2;
68574 + }
68575 +
68576 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
68577 +#ifdef SIOCSIWGENIE
68578 + if (pAd->StaCfg.WpaSupplicantUP != 1)
68579 +#endif // SIOCSIWGENIE //
68580 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
68581 + RTMPMakeRSNIE(pAd, pAd->StaCfg.AuthMode, pAd->StaCfg.WepStatus, BSS0);
68582 +
68583 + // Check for WPA PMK cache list
68584 + if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2)
68585 + {
68586 + INT idx;
68587 + BOOLEAN FoundPMK = FALSE;
68588 + // Search chched PMKID, append it if existed
68589 + for (idx = 0; idx < PMKID_NO; idx++)
68590 + {
68591 + if (NdisEqualMemory(ApAddr, &pAd->StaCfg.SavedPMK[idx].BSSID, 6))
68592 + {
68593 + FoundPMK = TRUE;
68594 + break;
68595 + }
68596 + }
68597 +
68598 + if (FoundPMK)
68599 + {
68600 + // Set PMK number
68601 + *(PUSHORT) &pAd->StaCfg.RSN_IE[pAd->StaCfg.RSNIE_Len] = 1;
68602 + NdisMoveMemory(&pAd->StaCfg.RSN_IE[pAd->StaCfg.RSNIE_Len + 2], &pAd->StaCfg.SavedPMK[idx].PMKID, 16);
68603 + pAd->StaCfg.RSNIE_Len += 18;
68604 + }
68605 + }
68606 +
68607 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
68608 +#ifdef SIOCSIWGENIE
68609 + if (pAd->StaCfg.WpaSupplicantUP == 1)
68610 + {
68611 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68612 + pAd->StaCfg.RSNIE_Len, pAd->StaCfg.RSN_IE,
68613 + END_OF_ARGS);
68614 + }
68615 + else
68616 +#endif
68617 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
68618 + {
68619 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68620 + 1, &RSNIe,
68621 + 1, &pAd->StaCfg.RSNIE_Len,
68622 + pAd->StaCfg.RSNIE_Len, pAd->StaCfg.RSN_IE,
68623 + END_OF_ARGS);
68624 + }
68625 +
68626 + FrameLen += tmp;
68627 +
68628 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
68629 +#ifdef SIOCSIWGENIE
68630 + if (pAd->StaCfg.WpaSupplicantUP != 1)
68631 +#endif
68632 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
68633 + {
68634 + // Append Variable IE
68635 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, &RSNIe, 1);
68636 + VarIesOffset += 1;
68637 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, &pAd->StaCfg.RSNIE_Len, 1);
68638 + VarIesOffset += 1;
68639 + }
68640 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, pAd->StaCfg.RSN_IE, pAd->StaCfg.RSNIE_Len);
68641 + VarIesOffset += pAd->StaCfg.RSNIE_Len;
68642 +
68643 + // Set Variable IEs Length
68644 + pAd->StaCfg.ReqVarIELen = VarIesOffset;
68645 + }
68646 +
68647 + // We have update that at PeerBeaconAtJoinRequest()
68648 + CkipFlag = pAd->StaCfg.CkipFlag;
68649 + if (CkipFlag != 0)
68650 + {
68651 + NdisZeroMemory(CkipNegotiationBuffer, CKIP_NEGOTIATION_LENGTH);
68652 + CkipNegotiationBuffer[2] = 0x66;
68653 + // Make it try KP & MIC, since we have to follow the result from AssocRsp
68654 + CkipNegotiationBuffer[8] = 0x18;
68655 + CkipNegotiationBuffer[CKIP_NEGOTIATION_LENGTH - 1] = 0x22;
68656 + CkipFlag = 0x18;
68657 +
68658 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68659 + 1, &AironetCkipIe,
68660 + 1, &AironetCkipLen,
68661 + AironetCkipLen, CkipNegotiationBuffer,
68662 + END_OF_ARGS);
68663 + FrameLen += tmp;
68664 + }
68665 +
68666 + // Add CCX v2 request if CCX2 admin state is on
68667 + if (pAd->StaCfg.CCXControl.field.Enable == 1)
68668 + {
68669 +
68670 + //
68671 + // Add AironetIPAddressIE for Cisco CCX 2.X
68672 + // Add CCX Version
68673 + //
68674 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68675 + 1, &AironetIPAddressIE,
68676 + 1, &AironetIPAddressLen,
68677 + AironetIPAddressLen, AironetIPAddressBuffer,
68678 + 1, &Ccx2Ie,
68679 + 1, &Ccx2Len,
68680 + Ccx2Len, Ccx2IeInfo,
68681 + END_OF_ARGS);
68682 + FrameLen += tmp;
68683 +
68684 + //
68685 + // Add CipherSuite CCKM or LeapTkip if setting.
68686 + //
68687 +#ifdef LEAP_SUPPORT
68688 + if (LEAP_CCKM_ON(pAd))
68689 + {
68690 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68691 + CipherSuiteCiscoCCKMLen, CipherSuiteCiscoCCKM,
68692 + END_OF_ARGS);
68693 + FrameLen += tmp;
68694 +
68695 + // Third add RSN
68696 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, CipherSuiteCiscoCCKM, CipherSuiteCiscoCCKMLen); //Save CipherSuite
68697 + VarIesOffset += CipherSuiteCiscoCCKMLen;
68698 + }
68699 + else if ((pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP) && (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled))
68700 + {
68701 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68702 + CipherSuiteCCXTkipLen, CipherSuiteCCXTkip,
68703 + END_OF_ARGS);
68704 + FrameLen += tmp;
68705 +
68706 + // Third add RSN
68707 + NdisMoveMemory(pAd->StaCfg.ReqVarIEs + VarIesOffset, CipherSuiteCCXTkip, CipherSuiteCCXTkipLen);
68708 + VarIesOffset += CipherSuiteCCXTkipLen;
68709 + }
68710 +#endif // LEAP_SUPPORT //
68711 +
68712 + // Add by James 03/06/27
68713 + // Set Variable IEs Length
68714 + pAd->StaCfg.ReqVarIELen = VarIesOffset;
68715 + pAd->StaCfg.AssocInfo.RequestIELength = VarIesOffset;
68716 +
68717 + // OffsetResponseIEs follow ReqVarIE
68718 + pAd->StaCfg.AssocInfo.OffsetResponseIEs = sizeof(NDIS_802_11_ASSOCIATION_INFORMATION) + pAd->StaCfg.ReqVarIELen;
68719 + // End Add by James
68720 + }
68721 +
68722 +
68723 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
68724 + MlmeFreeMemory(pAd, pOutBuffer);
68725 +
68726 + RTMPSetTimer(&pAd->MlmeAux.AssocTimer, Timeout);
68727 + pAd->Mlme.AssocMachine.CurrState = ASSOC_WAIT_RSP;
68728 + }
68729 + else
68730 + {
68731 + DBGPRINT(RT_DEBUG_TRACE,("ASSOC - MlmeAssocReqAction() sanity check failed. BUG!!!!!! \n"));
68732 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
68733 + Status = MLME_INVALID_FORMAT;
68734 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_ASSOC_CONF, 2, &Status);
68735 + }
68736 +
68737 +}
68738 +
68739 +/*
68740 + ==========================================================================
68741 + Description:
68742 + mlme reassoc req handling procedure
68743 + Parameters:
68744 + Elem -
68745 + Pre:
68746 + -# SSID (Adapter->StaCfg.ssid[])
68747 + -# BSSID (AP address, Adapter->StaCfg.bssid)
68748 + -# Supported rates (Adapter->StaCfg.supported_rates[])
68749 + -# Supported rates length (Adapter->StaCfg.supported_rates_len)
68750 + -# Tx power (Adapter->StaCfg.tx_power)
68751 +
68752 + IRQL = DISPATCH_LEVEL
68753 +
68754 + ==========================================================================
68755 + */
68756 +VOID MlmeReassocReqAction(
68757 + IN PRTMP_ADAPTER pAd,
68758 + IN MLME_QUEUE_ELEM *Elem)
68759 +{
68760 + UCHAR ApAddr[6];
68761 + HEADER_802_11 ReassocHdr;
68762 + UCHAR Ccx2Len = 5;
68763 + UCHAR WmeIe[9] = {IE_VENDOR_SPECIFIC, 0x07, 0x00, 0x50, 0xf2, 0x02, 0x00, 0x01, 0x00};
68764 + USHORT CapabilityInfo, ListenIntv;
68765 + ULONG Timeout;
68766 + ULONG FrameLen = 0;
68767 + BOOLEAN TimerCancelled;
68768 + NDIS_STATUS NStatus;
68769 + ULONG tmp;
68770 + PUCHAR pOutBuffer = NULL;
68771 +//CCX 2.X
68772 +#ifdef LEAP_SUPPORT
68773 + UCHAR CkipFlag;
68774 + UCHAR CkipNegotiationBuffer[CKIP_NEGOTIATION_LENGTH];
68775 + UCHAR AironetCkipIe = IE_AIRONET_CKIP;
68776 + UCHAR AironetCkipLen = CKIP_NEGOTIATION_LENGTH;
68777 + UCHAR AironetIPAddressIE = IE_AIRONET_IPADDRESS;
68778 + UCHAR AironetIPAddressLen = AIRONET_IPADDRESS_LENGTH;
68779 + UCHAR AironetIPAddressBuffer[AIRONET_IPADDRESS_LENGTH] = {0x00, 0x40, 0x96, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00};
68780 + UCHAR AironetCCKMReassocIE = IE_AIRONET_CCKMREASSOC;
68781 + UCHAR AironetCCKMReassocLen = AIRONET_CCKMREASSOC_LENGTH;
68782 + UCHAR AironetCCKMReassocBuffer[AIRONET_CCKMREASSOC_LENGTH];
68783 + UCHAR AironetOUI[] = {0x00, 0x40, 0x96, 0x00};
68784 + UCHAR MICMN[16];
68785 + UCHAR CalcMicBuffer[80];
68786 + ULONG CalcMicBufferLen = 0;
68787 +#endif // LEAP_SUPPORT //
68788 + USHORT Status;
68789 +
68790 + // Block all authentication request durning WPA block period
68791 + if (pAd->StaCfg.bBlockAssoc == TRUE)
68792 + {
68793 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - Block ReAssoc request durning WPA block period!\n"));
68794 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
68795 + Status = MLME_STATE_MACHINE_REJECT;
68796 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_REASSOC_CONF, 2, &Status);
68797 + }
68798 + // the parameters are the same as the association
68799 + else if(MlmeAssocReqSanity(pAd, Elem->Msg, Elem->MsgLen, ApAddr, &CapabilityInfo, &Timeout, &ListenIntv))
68800 + {
68801 + RTMPCancelTimer(&pAd->MlmeAux.ReassocTimer, &TimerCancelled);
68802 +
68803 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
68804 + if(NStatus != NDIS_STATUS_SUCCESS)
68805 + {
68806 + DBGPRINT(RT_DEBUG_TRACE,("ASSOC - MlmeReassocReqAction() allocate memory failed \n"));
68807 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
68808 + Status = MLME_FAIL_NO_RESOURCE;
68809 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_REASSOC_CONF, 2, &Status);
68810 + return;
68811 + }
68812 +
68813 + COPY_MAC_ADDR(pAd->MlmeAux.Bssid, ApAddr);
68814 +
68815 + // make frame, use bssid as the AP address??
68816 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - Send RE-ASSOC request...\n"));
68817 + MgtMacHeaderInit(pAd, &ReassocHdr, SUBTYPE_REASSOC_REQ, 0, ApAddr, ApAddr);
68818 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
68819 + sizeof(HEADER_802_11), &ReassocHdr,
68820 + 2, &CapabilityInfo,
68821 + 2, &ListenIntv,
68822 + MAC_ADDR_LEN, ApAddr,
68823 + 1, &SsidIe,
68824 + 1, &pAd->MlmeAux.SsidLen,
68825 + pAd->MlmeAux.SsidLen, pAd->MlmeAux.Ssid,
68826 + 1, &SupRateIe,
68827 + 1, &pAd->MlmeAux.SupRateLen,
68828 + pAd->MlmeAux.SupRateLen, pAd->MlmeAux.SupRate,
68829 + END_OF_ARGS);
68830 +
68831 + if (pAd->MlmeAux.ExtRateLen != 0)
68832 + {
68833 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68834 + 1, &ExtRateIe,
68835 + 1, &pAd->MlmeAux.ExtRateLen,
68836 + pAd->MlmeAux.ExtRateLen, pAd->MlmeAux.ExtRate,
68837 + END_OF_ARGS);
68838 + FrameLen += tmp;
68839 + }
68840 +
68841 + if (pAd->MlmeAux.APEdcaParm.bValid)
68842 + {
68843 + if (pAd->CommonCfg.bAPSDCapable && pAd->MlmeAux.APEdcaParm.bAPSDCapable)
68844 + {
68845 + QBSS_STA_INFO_PARM QosInfo;
68846 +
68847 + NdisZeroMemory(&QosInfo, sizeof(QBSS_STA_INFO_PARM));
68848 + QosInfo.UAPSD_AC_BE = pAd->CommonCfg.bAPSDAC_BE;
68849 + QosInfo.UAPSD_AC_BK = pAd->CommonCfg.bAPSDAC_BK;
68850 + QosInfo.UAPSD_AC_VI = pAd->CommonCfg.bAPSDAC_VI;
68851 + QosInfo.UAPSD_AC_VO = pAd->CommonCfg.bAPSDAC_VO;
68852 + QosInfo.MaxSPLength = pAd->CommonCfg.MaxSPLength;
68853 + WmeIe[8] |= *(PUCHAR)&QosInfo;
68854 + }
68855 +
68856 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68857 + 9, &WmeIe[0],
68858 + END_OF_ARGS);
68859 + FrameLen += tmp;
68860 + }
68861 +
68862 +#ifdef DOT11_N_SUPPORT
68863 + // HT
68864 + if ((pAd->MlmeAux.HtCapabilityLen > 0) && (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
68865 + {
68866 + ULONG TmpLen;
68867 + UCHAR HtLen;
68868 + UCHAR BROADCOM[4] = {0x0, 0x90, 0x4c, 0x33};
68869 + if (pAd->StaActive.SupportedPhyInfo.bPreNHt == TRUE)
68870 + {
68871 + HtLen = SIZE_HT_CAP_IE + 4;
68872 + MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen,
68873 + 1, &WpaIe,
68874 + 1, &HtLen,
68875 + 4, &BROADCOM[0],
68876 + pAd->MlmeAux.HtCapabilityLen, &pAd->MlmeAux.HtCapability,
68877 + END_OF_ARGS);
68878 + }
68879 + else
68880 + {
68881 + MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen,
68882 + 1, &HtCapIe,
68883 + 1, &pAd->MlmeAux.HtCapabilityLen,
68884 + pAd->MlmeAux.HtCapabilityLen, &pAd->MlmeAux.HtCapability,
68885 + END_OF_ARGS);
68886 + }
68887 + FrameLen += TmpLen;
68888 + }
68889 +#endif // DOT11_N_SUPPORT //
68890 +
68891 + // add Ralink proprietary IE to inform AP this STA is going to use AGGREGATION or PIGGY-BACK+AGGREGATION
68892 + // Case I: (Aggregation + Piggy-Back)
68893 + // 1. user enable aggregation, AND
68894 + // 2. Mac support piggy-back
68895 + // 3. AP annouces it's PIGGY-BACK+AGGREGATION-capable in BEACON
68896 + // Case II: (Aggregation)
68897 + // 1. user enable aggregation, AND
68898 + // 2. AP annouces it's AGGREGATION-capable in BEACON
68899 + if (pAd->CommonCfg.bAggregationCapable)
68900 + {
68901 + if ((pAd->CommonCfg.bPiggyBackCapable) && ((pAd->MlmeAux.APRalinkIe & 0x00000003) == 3))
68902 + {
68903 + ULONG TmpLen;
68904 + UCHAR RalinkIe[9] = {IE_VENDOR_SPECIFIC, 7, 0x00, 0x0c, 0x43, 0x03, 0x00, 0x00, 0x00};
68905 + MakeOutgoingFrame(pOutBuffer+FrameLen, &TmpLen,
68906 + 9, RalinkIe,
68907 + END_OF_ARGS);
68908 + FrameLen += TmpLen;
68909 + }
68910 + else if (pAd->MlmeAux.APRalinkIe & 0x00000001)
68911 + {
68912 + ULONG TmpLen;
68913 + UCHAR RalinkIe[9] = {IE_VENDOR_SPECIFIC, 7, 0x00, 0x0c, 0x43, 0x01, 0x00, 0x00, 0x00};
68914 + MakeOutgoingFrame(pOutBuffer+FrameLen, &TmpLen,
68915 + 9, RalinkIe,
68916 + END_OF_ARGS);
68917 + FrameLen += TmpLen;
68918 + }
68919 + }
68920 + else
68921 + {
68922 + ULONG TmpLen;
68923 + UCHAR RalinkIe[9] = {IE_VENDOR_SPECIFIC, 7, 0x00, 0x0c, 0x43, 0x04, 0x00, 0x00, 0x00};
68924 + MakeOutgoingFrame(pOutBuffer+FrameLen, &TmpLen,
68925 + 9, RalinkIe,
68926 + END_OF_ARGS);
68927 + FrameLen += TmpLen;
68928 + }
68929 +#ifdef LEAP_SUPPORT
68930 + if (LEAP_CCKM_ON(pAd) && (pAd->StaCfg.CCKMLinkUpFlag == TRUE))
68931 + {
68932 + CkipFlag = pAd->StaCfg.CkipFlag; // We have update that at PeerBeaconAtJoinRequest()
68933 + if (CkipFlag != 0)
68934 + {
68935 + NdisZeroMemory(CkipNegotiationBuffer, CKIP_NEGOTIATION_LENGTH);
68936 + CkipNegotiationBuffer[2] = 0x66;
68937 + // Make it try KP & MIC, since we have to follow the result from AssocRsp
68938 + CkipNegotiationBuffer[8] = 0x18;
68939 + CkipNegotiationBuffer[CKIP_NEGOTIATION_LENGTH - 1] = 0x22;
68940 +
68941 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68942 + 1, &AironetCkipIe,
68943 + 1, &AironetCkipLen,
68944 + AironetCkipLen, CkipNegotiationBuffer,
68945 + END_OF_ARGS);
68946 + FrameLen += tmp;
68947 + }
68948 +
68949 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68950 + 1, &AironetIPAddressIE,
68951 + 1, &AironetIPAddressLen,
68952 + AironetIPAddressLen, AironetIPAddressBuffer,
68953 + END_OF_ARGS);
68954 + FrameLen += tmp;
68955 +
68956 + //
68957 + // The RN is incremented before each reassociation request.
68958 + //
68959 + pAd->StaCfg.CCKMRN++;
68960 + //
68961 + // Calculate MIC = hmac-md5(krk, STA-ID|BSSID|RSNIE|TSF|RN);
68962 + //
68963 + COPY_MAC_ADDR(CalcMicBuffer, pAd->CurrentAddress);
68964 + CalcMicBufferLen = MAC_ADDR_LEN;
68965 + COPY_MAC_ADDR(CalcMicBuffer + CalcMicBufferLen, pAd->MlmeAux.Bssid);
68966 + CalcMicBufferLen += MAC_ADDR_LEN;
68967 + NdisMoveMemory(CalcMicBuffer + CalcMicBufferLen, CipherSuiteCiscoCCKM, CipherSuiteCiscoCCKMLen);
68968 + CalcMicBufferLen += CipherSuiteCiscoCCKMLen;
68969 + NdisMoveMemory(CalcMicBuffer + CalcMicBufferLen, (PUCHAR) &pAd->StaCfg.CCKMBeaconAtJoinTimeStamp, sizeof(pAd->StaCfg.CCKMBeaconAtJoinTimeStamp));
68970 + CalcMicBufferLen += sizeof(pAd->StaCfg.CCKMBeaconAtJoinTimeStamp);
68971 + NdisMoveMemory(CalcMicBuffer + CalcMicBufferLen, (PUCHAR)&pAd->StaCfg.CCKMRN, sizeof(pAd->StaCfg.CCKMRN));
68972 + CalcMicBufferLen += sizeof(pAd->StaCfg.CCKMRN);
68973 + hmac_md5(pAd->StaCfg.KRK, LEN_EAP_MICK, CalcMicBuffer, CalcMicBufferLen, MICMN);
68974 +
68975 + //
68976 + // fill up CCKM reassociation request element
68977 + //
68978 + NdisMoveMemory(AironetCCKMReassocBuffer, AironetOUI, 4);
68979 + NdisMoveMemory(AironetCCKMReassocBuffer + 4, (PUCHAR)&pAd->StaCfg.CCKMBeaconAtJoinTimeStamp, 8);
68980 + NdisMoveMemory(AironetCCKMReassocBuffer + 12, (PUCHAR) &pAd->StaCfg.CCKMRN, 4);
68981 + NdisMoveMemory(AironetCCKMReassocBuffer +16, MICMN, 8);
68982 +
68983 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68984 + 1, &AironetCCKMReassocIE,
68985 + 1, &AironetCCKMReassocLen,
68986 + AironetCCKMReassocLen, AironetCCKMReassocBuffer,
68987 + END_OF_ARGS);
68988 + FrameLen += tmp;
68989 +
68990 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
68991 + CipherSuiteCiscoCCKMLen,CipherSuiteCiscoCCKM,
68992 + END_OF_ARGS);
68993 + FrameLen += tmp;
68994 + }
68995 +#endif // LEAP_SUPPORT //
68996 +
68997 + // Add CCX v2 request if CCX2 admin state is on
68998 + if (pAd->StaCfg.CCXControl.field.Enable == 1)
68999 + {
69000 + //
69001 + // Add CCX Version
69002 + //
69003 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
69004 + 1, &Ccx2Ie,
69005 + 1, &Ccx2Len,
69006 + Ccx2Len, Ccx2IeInfo,
69007 + END_OF_ARGS);
69008 + FrameLen += tmp;
69009 + }
69010 +
69011 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
69012 + MlmeFreeMemory(pAd, pOutBuffer);
69013 +
69014 + RTMPSetTimer(&pAd->MlmeAux.ReassocTimer, Timeout); /* in mSec */
69015 + pAd->Mlme.AssocMachine.CurrState = REASSOC_WAIT_RSP;
69016 + }
69017 + else
69018 + {
69019 + DBGPRINT(RT_DEBUG_TRACE,("ASSOC - MlmeReassocReqAction() sanity check failed. BUG!!!! \n"));
69020 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69021 + Status = MLME_INVALID_FORMAT;
69022 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_REASSOC_CONF, 2, &Status);
69023 + }
69024 +}
69025 +
69026 +/*
69027 + ==========================================================================
69028 + Description:
69029 + Upper layer issues disassoc request
69030 + Parameters:
69031 + Elem -
69032 +
69033 + IRQL = PASSIVE_LEVEL
69034 +
69035 + ==========================================================================
69036 + */
69037 +VOID MlmeDisassocReqAction(
69038 + IN PRTMP_ADAPTER pAd,
69039 + IN MLME_QUEUE_ELEM *Elem)
69040 +{
69041 + PMLME_DISASSOC_REQ_STRUCT pDisassocReq;
69042 + HEADER_802_11 DisassocHdr;
69043 + PHEADER_802_11 pDisassocHdr;
69044 + PUCHAR pOutBuffer = NULL;
69045 + ULONG FrameLen = 0;
69046 + NDIS_STATUS NStatus;
69047 + BOOLEAN TimerCancelled;
69048 + ULONG Timeout = 0;
69049 + USHORT Status;
69050 +
69051 +#ifdef QOS_DLS_SUPPORT
69052 + // send DLS-TEAR_DOWN message,
69053 + if (pAd->CommonCfg.bDLSCapable)
69054 + {
69055 + UCHAR i;
69056 +
69057 + // tear down local dls table entry
69058 + for (i=0; i<MAX_NUM_OF_INIT_DLS_ENTRY; i++)
69059 + {
69060 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH))
69061 + {
69062 + RTMPSendDLSTearDownFrame(pAd, pAd->StaCfg.DLSEntry[i].MacAddr);
69063 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
69064 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
69065 + }
69066 + }
69067 +
69068 + // tear down peer dls table entry
69069 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
69070 + {
69071 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH))
69072 + {
69073 + RTMPSendDLSTearDownFrame(pAd, pAd->StaCfg.DLSEntry[i].MacAddr);
69074 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
69075 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
69076 + }
69077 + }
69078 + }
69079 +#endif // QOS_DLS_SUPPORT //
69080 +
69081 + // skip sanity check
69082 + pDisassocReq = (PMLME_DISASSOC_REQ_STRUCT)(Elem->Msg);
69083 +
69084 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
69085 + if (NStatus != NDIS_STATUS_SUCCESS)
69086 + {
69087 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - MlmeDisassocReqAction() allocate memory failed\n"));
69088 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69089 + Status = MLME_FAIL_NO_RESOURCE;
69090 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_DISASSOC_CONF, 2, &Status);
69091 + return;
69092 + }
69093 +
69094 +
69095 +
69096 + RTMPCancelTimer(&pAd->MlmeAux.DisassocTimer, &TimerCancelled);
69097 +
69098 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - Send DISASSOC request[BSSID::%02x:%02x:%02x:%02x:%02x:%02x (Reason=%d)\n",
69099 + pDisassocReq->Addr[0], pDisassocReq->Addr[1], pDisassocReq->Addr[2],
69100 + pDisassocReq->Addr[3], pDisassocReq->Addr[4], pDisassocReq->Addr[5], pDisassocReq->Reason));
69101 + MgtMacHeaderInit(pAd, &DisassocHdr, SUBTYPE_DISASSOC, 0, pDisassocReq->Addr, pDisassocReq->Addr); // patch peap ttls switching issue
69102 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
69103 + sizeof(HEADER_802_11),&DisassocHdr,
69104 + 2, &pDisassocReq->Reason,
69105 + END_OF_ARGS);
69106 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
69107 +
69108 + // To patch Instance and Buffalo(N) AP
69109 + // Driver has to send deauth to Instance AP, but Buffalo(N) needs to send disassoc to reset Authenticator's state machine
69110 + // Therefore, we send both of them.
69111 + pDisassocHdr = (PHEADER_802_11)pOutBuffer;
69112 + pDisassocHdr->FC.SubType = SUBTYPE_DEAUTH;
69113 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
69114 +
69115 + MlmeFreeMemory(pAd, pOutBuffer);
69116 +
69117 + pAd->StaCfg.DisassocReason = REASON_DISASSOC_STA_LEAVING;
69118 + COPY_MAC_ADDR(pAd->StaCfg.DisassocSta, pDisassocReq->Addr);
69119 +
69120 + RTMPSetTimer(&pAd->MlmeAux.DisassocTimer, Timeout); /* in mSec */
69121 + pAd->Mlme.AssocMachine.CurrState = DISASSOC_WAIT_RSP;
69122 +
69123 +#ifdef WPA_SUPPLICANT_SUPPORT
69124 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
69125 + if (pAd->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE)
69126 + {
69127 + union iwreq_data wrqu;
69128 + //send disassociate event to wpa_supplicant
69129 + memset(&wrqu, 0, sizeof(wrqu));
69130 + wrqu.data.flags = RT_DISASSOC_EVENT_FLAG;
69131 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
69132 + }
69133 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69134 +#endif // WPA_SUPPLICANT_SUPPORT //
69135 +
69136 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
69137 + {
69138 + union iwreq_data wrqu;
69139 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
69140 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
69141 + }
69142 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69143 +
69144 +}
69145 +
69146 +/*
69147 + ==========================================================================
69148 + Description:
69149 + peer sends assoc rsp back
69150 + Parameters:
69151 + Elme - MLME message containing the received frame
69152 +
69153 + IRQL = DISPATCH_LEVEL
69154 +
69155 + ==========================================================================
69156 + */
69157 +VOID PeerAssocRspAction(
69158 + IN PRTMP_ADAPTER pAd,
69159 + IN MLME_QUEUE_ELEM *Elem)
69160 +{
69161 + USHORT CapabilityInfo, Status, Aid;
69162 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES], SupRateLen;
69163 + UCHAR ExtRate[MAX_LEN_OF_SUPPORTED_RATES], ExtRateLen;
69164 + UCHAR Addr2[MAC_ADDR_LEN];
69165 + BOOLEAN TimerCancelled;
69166 + UCHAR CkipFlag;
69167 + EDCA_PARM EdcaParm;
69168 + HT_CAPABILITY_IE HtCapability;
69169 + ADD_HT_INFO_IE AddHtInfo; // AP might use this additional ht info IE
69170 + UCHAR HtCapabilityLen;
69171 + UCHAR AddHtInfoLen;
69172 + UCHAR NewExtChannelOffset = 0xff;
69173 +
69174 + if (PeerAssocRspSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, &CapabilityInfo, &Status, &Aid, SupRate, &SupRateLen, ExtRate, &ExtRateLen,
69175 + &HtCapability,&AddHtInfo, &HtCapabilityLen,&AddHtInfoLen,&NewExtChannelOffset, &EdcaParm, &CkipFlag))
69176 + {
69177 + // The frame is for me ?
69178 + if(MAC_ADDR_EQUAL(Addr2, pAd->MlmeAux.Bssid))
69179 + {
69180 + DBGPRINT(RT_DEBUG_TRACE, ("PeerAssocRspAction():ASSOC - receive ASSOC_RSP to me (status=%d)\n", Status));
69181 +#ifdef DOT11_N_SUPPORT
69182 + DBGPRINT(RT_DEBUG_TRACE, ("PeerAssocRspAction():MacTable [%d].AMsduSize = %d. ClientStatusFlags = 0x%lx \n",Elem->Wcid, pAd->MacTab.Content[BSSID_WCID].AMsduSize, pAd->MacTab.Content[BSSID_WCID].ClientStatusFlags));
69183 +#endif // DOT11_N_SUPPORT //
69184 + RTMPCancelTimer(&pAd->MlmeAux.AssocTimer, &TimerCancelled);
69185 + if(Status == MLME_SUCCESS)
69186 + {
69187 + // go to procedure listed on page 376
69188 + AssocPostProc(pAd, Addr2, CapabilityInfo, Aid, SupRate, SupRateLen, ExtRate, ExtRateLen,
69189 + &EdcaParm, &HtCapability, HtCapabilityLen, &AddHtInfo);
69190 +
69191 +#ifdef WPA_SUPPLICANT_SUPPORT
69192 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
69193 + if (pAd->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE)
69194 + {
69195 + union iwreq_data wrqu;
69196 +
69197 + SendAssocIEsToWpaSupplicant(pAd);
69198 + memset(&wrqu, 0, sizeof(wrqu));
69199 + wrqu.data.flags = RT_ASSOC_EVENT_FLAG;
69200 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
69201 + }
69202 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69203 +#endif // WPA_SUPPLICANT_SUPPORT //
69204 +
69205 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
69206 + {
69207 + union iwreq_data wrqu;
69208 + wext_notify_event_assoc(pAd);
69209 +
69210 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
69211 + memcpy(wrqu.ap_addr.sa_data, pAd->MlmeAux.Bssid, MAC_ADDR_LEN);
69212 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
69213 +
69214 + }
69215 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69216 +
69217 +
69218 + pAd->StaCfg.CkipFlag = CkipFlag;
69219 + if (CkipFlag & 0x18)
69220 + {
69221 + NdisZeroMemory(pAd->StaCfg.TxSEQ, 4);
69222 + NdisZeroMemory(pAd->StaCfg.RxSEQ, 4);
69223 + NdisZeroMemory(pAd->StaCfg.CKIPMIC, 4);
69224 + pAd->StaCfg.GIV[0] = RandomByte(pAd);
69225 + pAd->StaCfg.GIV[1] = RandomByte(pAd);
69226 + pAd->StaCfg.GIV[2] = RandomByte(pAd);
69227 + pAd->StaCfg.bCkipOn = TRUE;
69228 + DBGPRINT(RT_DEBUG_TRACE, ("<CCX> pAd->StaCfg.CkipFlag = 0x%02x\n", pAd->StaCfg.CkipFlag));
69229 + }
69230 + }
69231 + else
69232 + {
69233 + // Faile on Association, we need to check the status code
69234 + // Is that a Rogue AP?
69235 +#ifdef LEAP_SUPPORT
69236 + if ((pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP) && (Status == MLME_ALG_NOT_SUPPORT))
69237 + { //Possibly Rogue AP
69238 + RogueApTableSetEntry(pAd, &pAd->StaCfg.RogueApTab, pAd->MlmeAux.Bssid, LEAP_REASON_INVALID_AUTH);
69239 + }
69240 +#endif // LEAP_SUPPORT //
69241 + }
69242 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69243 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_ASSOC_CONF, 2, &Status);
69244 + }
69245 + }
69246 + else
69247 + {
69248 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - PeerAssocRspAction() sanity check fail\n"));
69249 + }
69250 +}
69251 +
69252 +/*
69253 + ==========================================================================
69254 + Description:
69255 + peer sends reassoc rsp
69256 + Parametrs:
69257 + Elem - MLME message cntaining the received frame
69258 +
69259 + IRQL = DISPATCH_LEVEL
69260 +
69261 + ==========================================================================
69262 + */
69263 +VOID PeerReassocRspAction(
69264 + IN PRTMP_ADAPTER pAd,
69265 + IN MLME_QUEUE_ELEM *Elem)
69266 +{
69267 + USHORT CapabilityInfo;
69268 + USHORT Status;
69269 + USHORT Aid;
69270 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES], SupRateLen;
69271 + UCHAR ExtRate[MAX_LEN_OF_SUPPORTED_RATES], ExtRateLen;
69272 + UCHAR Addr2[MAC_ADDR_LEN];
69273 + UCHAR CkipFlag;
69274 + BOOLEAN TimerCancelled;
69275 + EDCA_PARM EdcaParm;
69276 + HT_CAPABILITY_IE HtCapability;
69277 + ADD_HT_INFO_IE AddHtInfo; // AP might use this additional ht info IE
69278 + UCHAR HtCapabilityLen;
69279 + UCHAR AddHtInfoLen;
69280 + UCHAR NewExtChannelOffset = 0xff;
69281 +
69282 + if(PeerAssocRspSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, &CapabilityInfo, &Status, &Aid, SupRate, &SupRateLen, ExtRate, &ExtRateLen,
69283 + &HtCapability, &AddHtInfo, &HtCapabilityLen, &AddHtInfoLen,&NewExtChannelOffset, &EdcaParm, &CkipFlag))
69284 + {
69285 + if(MAC_ADDR_EQUAL(Addr2, pAd->MlmeAux.Bssid)) // The frame is for me ?
69286 + {
69287 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - receive REASSOC_RSP to me (status=%d)\n", Status));
69288 + RTMPCancelTimer(&pAd->MlmeAux.ReassocTimer, &TimerCancelled);
69289 +
69290 + if(Status == MLME_SUCCESS)
69291 + {
69292 + // go to procedure listed on page 376
69293 + AssocPostProc(pAd, Addr2, CapabilityInfo, Aid, SupRate, SupRateLen, ExtRate, ExtRateLen,
69294 + &EdcaParm, &HtCapability, HtCapabilityLen, &AddHtInfo);
69295 +
69296 +#ifdef WPA_SUPPLICANT_SUPPORT
69297 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
69298 + if (pAd->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE)
69299 + {
69300 + union iwreq_data wrqu;
69301 +
69302 + SendAssocIEsToWpaSupplicant(pAd);
69303 + memset(&wrqu, 0, sizeof(wrqu));
69304 + wrqu.data.flags = RT_ASSOC_EVENT_FLAG;
69305 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
69306 + }
69307 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69308 +#endif // WPA_SUPPLICANT_SUPPORT //
69309 +
69310 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
69311 + {
69312 + union iwreq_data wrqu;
69313 + wext_notify_event_assoc(pAd);
69314 +
69315 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
69316 + memcpy(wrqu.ap_addr.sa_data, pAd->MlmeAux.Bssid, MAC_ADDR_LEN);
69317 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
69318 +
69319 + }
69320 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69321 +
69322 + }
69323 +
69324 + //
69325 + // Cisco Leap CCKM supported Re-association.
69326 + //
69327 +#ifdef LEAP_SUPPORT
69328 + if (LEAP_CCKM_ON(pAd) && (pAd->StaCfg.CCKMLinkUpFlag == TRUE))
69329 + {
69330 + if (CCKMAssocRspSanity(pAd, Elem->Msg, Elem->MsgLen) == TRUE)
69331 + {
69332 + pAd->StaCfg.CkipFlag = CkipFlag;
69333 + if (CkipFlag & 0x18)
69334 + {
69335 + NdisZeroMemory(pAd->StaCfg.TxSEQ, 4);
69336 + NdisZeroMemory(pAd->StaCfg.RxSEQ, 4);
69337 + NdisZeroMemory(pAd->StaCfg.CKIPMIC, 4);
69338 + pAd->StaCfg.GIV[0] = RandomByte(pAd);
69339 + pAd->StaCfg.GIV[1] = RandomByte(pAd);
69340 + pAd->StaCfg.GIV[2] = RandomByte(pAd);
69341 + pAd->StaCfg.bCkipOn = TRUE;
69342 + DBGPRINT(RT_DEBUG_TRACE, ("<CCX> pAd->StaCfg.CkipFlag = 0x%02x\n", pAd->StaCfg.CkipFlag));
69343 + }
69344 +
69345 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69346 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_REASSOC_CONF, 2, &Status);
69347 + }
69348 + else
69349 + {
69350 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - CCKMAssocRspSanity() sanity check fail\n"));
69351 + }
69352 + }
69353 + else
69354 +#endif // LEAP_SUPPORT //
69355 + {
69356 + // CkipFlag is no use for reassociate
69357 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69358 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_REASSOC_CONF, 2, &Status);
69359 + }
69360 + }
69361 + }
69362 + else
69363 + {
69364 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - PeerReassocRspAction() sanity check fail\n"));
69365 + }
69366 +
69367 +}
69368 +
69369 +/*
69370 + ==========================================================================
69371 + Description:
69372 + procedures on IEEE 802.11/1999 p.376
69373 + Parametrs:
69374 +
69375 + IRQL = DISPATCH_LEVEL
69376 +
69377 + ==========================================================================
69378 + */
69379 +VOID AssocPostProc(
69380 + IN PRTMP_ADAPTER pAd,
69381 + IN PUCHAR pAddr2,
69382 + IN USHORT CapabilityInfo,
69383 + IN USHORT Aid,
69384 + IN UCHAR SupRate[],
69385 + IN UCHAR SupRateLen,
69386 + IN UCHAR ExtRate[],
69387 + IN UCHAR ExtRateLen,
69388 + IN PEDCA_PARM pEdcaParm,
69389 + IN HT_CAPABILITY_IE *pHtCapability,
69390 + IN UCHAR HtCapabilityLen,
69391 + IN ADD_HT_INFO_IE *pAddHtInfo) // AP might use this additional ht info IE
69392 +{
69393 + ULONG Idx;
69394 +
69395 + pAd->MlmeAux.BssType = BSS_INFRA;
69396 + COPY_MAC_ADDR(pAd->MlmeAux.Bssid, pAddr2);
69397 + pAd->MlmeAux.Aid = Aid;
69398 + pAd->MlmeAux.CapabilityInfo = CapabilityInfo & SUPPORTED_CAPABILITY_INFO;
69399 +#ifdef DOT11_N_SUPPORT
69400 + // Some HT AP might lost WMM IE. We add WMM ourselves. beacuase HT requires QoS on.
69401 + if ((HtCapabilityLen > 0) && (pEdcaParm->bValid == FALSE))
69402 + {
69403 + pEdcaParm->bValid = TRUE;
69404 + pEdcaParm->Aifsn[0] = 3;
69405 + pEdcaParm->Aifsn[1] = 7;
69406 + pEdcaParm->Aifsn[2] = 2;
69407 + pEdcaParm->Aifsn[3] = 2;
69408 +
69409 + pEdcaParm->Cwmin[0] = 4;
69410 + pEdcaParm->Cwmin[1] = 4;
69411 + pEdcaParm->Cwmin[2] = 3;
69412 + pEdcaParm->Cwmin[3] = 2;
69413 +
69414 + pEdcaParm->Cwmax[0] = 10;
69415 + pEdcaParm->Cwmax[1] = 10;
69416 + pEdcaParm->Cwmax[2] = 4;
69417 + pEdcaParm->Cwmax[3] = 3;
69418 +
69419 + pEdcaParm->Txop[0] = 0;
69420 + pEdcaParm->Txop[1] = 0;
69421 + pEdcaParm->Txop[2] = 96;
69422 + pEdcaParm->Txop[3] = 48;
69423 +
69424 + }
69425 +#endif // DOT11_N_SUPPORT //
69426 +
69427 + NdisMoveMemory(&pAd->MlmeAux.APEdcaParm, pEdcaParm, sizeof(EDCA_PARM));
69428 +
69429 + // filter out un-supported rates
69430 + pAd->MlmeAux.SupRateLen = SupRateLen;
69431 + NdisMoveMemory(pAd->MlmeAux.SupRate, SupRate, SupRateLen);
69432 + RTMPCheckRates(pAd, pAd->MlmeAux.SupRate, &pAd->MlmeAux.SupRateLen);
69433 +
69434 + // filter out un-supported rates
69435 + pAd->MlmeAux.ExtRateLen = ExtRateLen;
69436 + NdisMoveMemory(pAd->MlmeAux.ExtRate, ExtRate, ExtRateLen);
69437 + RTMPCheckRates(pAd, pAd->MlmeAux.ExtRate, &pAd->MlmeAux.ExtRateLen);
69438 +
69439 +#ifdef DOT11_N_SUPPORT
69440 + if (HtCapabilityLen > 0)
69441 + {
69442 + RTMPCheckHt(pAd, BSSID_WCID, pHtCapability, pAddHtInfo);
69443 + }
69444 + DBGPRINT(RT_DEBUG_TRACE, ("AssocPostProc===> AP.AMsduSize = %d. ClientStatusFlags = 0x%lx \n", pAd->MacTab.Content[BSSID_WCID].AMsduSize, pAd->MacTab.Content[BSSID_WCID].ClientStatusFlags));
69445 +
69446 + DBGPRINT(RT_DEBUG_TRACE, ("AssocPostProc===> (Mmps=%d, AmsduSize=%d, )\n",
69447 + pAd->MacTab.Content[BSSID_WCID].MmpsMode, pAd->MacTab.Content[BSSID_WCID].AMsduSize));
69448 +#endif // DOT11_N_SUPPORT //
69449 +
69450 + // Set New WPA information
69451 + Idx = BssTableSearch(&pAd->ScanTab, pAddr2, pAd->MlmeAux.Channel);
69452 + if (Idx == BSS_NOT_FOUND)
69453 + {
69454 + DBGPRINT_ERR(("ASSOC - Can't find BSS after receiving Assoc response\n"));
69455 + }
69456 + else
69457 + {
69458 + // Init variable
69459 + pAd->MacTab.Content[BSSID_WCID].RSNIE_Len = 0;
69460 + NdisZeroMemory(pAd->MacTab.Content[BSSID_WCID].RSN_IE, MAX_LEN_OF_RSNIE);
69461 +
69462 + // Store appropriate RSN_IE for WPA SM negotiation later
69463 + if ((pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA) && (pAd->ScanTab.BssEntry[Idx].VarIELen != 0))
69464 + {
69465 + PUCHAR pVIE;
69466 + USHORT len;
69467 + PEID_STRUCT pEid;
69468 +
69469 + pVIE = pAd->ScanTab.BssEntry[Idx].VarIEs;
69470 + len = pAd->ScanTab.BssEntry[Idx].VarIELen;
69471 +
69472 + while (len > 0)
69473 + {
69474 + pEid = (PEID_STRUCT) pVIE;
69475 + // For WPA/WPAPSK
69476 + if ((pEid->Eid == IE_WPA) && (NdisEqualMemory(pEid->Octet, WPA_OUI, 4))
69477 + && (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA || pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK))
69478 + {
69479 + NdisMoveMemory(pAd->MacTab.Content[BSSID_WCID].RSN_IE, pVIE, (pEid->Len + 2));
69480 + pAd->MacTab.Content[BSSID_WCID].RSNIE_Len = (pEid->Len + 2);
69481 + DBGPRINT(RT_DEBUG_TRACE, ("AssocPostProc===> Store RSN_IE for WPA SM negotiation \n"));
69482 + }
69483 + // For WPA2/WPA2PSK
69484 + else if ((pEid->Eid == IE_RSN) && (NdisEqualMemory(pEid->Octet + 2, RSN_OUI, 3))
69485 + && (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2 || pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
69486 + {
69487 + NdisMoveMemory(pAd->MacTab.Content[BSSID_WCID].RSN_IE, pVIE, (pEid->Len + 2));
69488 + pAd->MacTab.Content[BSSID_WCID].RSNIE_Len = (pEid->Len + 2);
69489 + DBGPRINT(RT_DEBUG_TRACE, ("AssocPostProc===> Store RSN_IE for WPA2 SM negotiation \n"));
69490 + }
69491 +
69492 + pVIE += (pEid->Len + 2);
69493 + len -= (pEid->Len + 2);
69494 + }
69495 + }
69496 +
69497 + if (pAd->MacTab.Content[BSSID_WCID].RSNIE_Len == 0)
69498 + {
69499 + DBGPRINT(RT_DEBUG_TRACE, ("AssocPostProc===> no RSN_IE \n"));
69500 + }
69501 + else
69502 + {
69503 + hex_dump("RSN_IE", pAd->MacTab.Content[BSSID_WCID].RSN_IE, pAd->MacTab.Content[BSSID_WCID].RSNIE_Len);
69504 + }
69505 + }
69506 +}
69507 +
69508 +/*
69509 + ==========================================================================
69510 + Description:
69511 + left part of IEEE 802.11/1999 p.374
69512 + Parameters:
69513 + Elem - MLME message containing the received frame
69514 +
69515 + IRQL = DISPATCH_LEVEL
69516 +
69517 + ==========================================================================
69518 + */
69519 +VOID PeerDisassocAction(
69520 + IN PRTMP_ADAPTER pAd,
69521 + IN MLME_QUEUE_ELEM *Elem)
69522 +{
69523 + UCHAR Addr2[MAC_ADDR_LEN];
69524 + USHORT Reason;
69525 +
69526 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - PeerDisassocAction()\n"));
69527 + if(PeerDisassocSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, &Reason))
69528 + {
69529 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - PeerDisassocAction() Reason = %d\n", Reason));
69530 + if (INFRA_ON(pAd) && MAC_ADDR_EQUAL(pAd->CommonCfg.Bssid, Addr2))
69531 + {
69532 +
69533 + if (pAd->CommonCfg.bWirelessEvent)
69534 + {
69535 + RTMPSendWirelessEvent(pAd, IW_DISASSOC_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
69536 + }
69537 +
69538 +
69539 +#ifdef LEAP_SUPPORT
69540 + if (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
69541 + {
69542 + // Cisco_LEAP has start a timer
69543 + // We should cancel it if using LEAP
69544 + RTMPCancelTimer(&pAd->StaCfg.LeapAuthTimer, &TimerCancelled);
69545 + //Check is it mach the LEAP Authentication failed as possible a Rogue AP
69546 + //on it's PortSecured not equal to WPA_802_1X_PORT_SECURED while process the Association.
69547 + if ((pAd->Mlme.LeapMachine.CurrState != LEAP_IDLE) && (pAd->StaCfg.PortSecured != WPA_802_1X_PORT_SECURED))
69548 + {
69549 + RogueApTableSetEntry(pAd, &pAd->StaCfg.RogueApTab, Addr2, LEAP_REASON_AUTH_TIMEOUT);
69550 + }
69551 + }
69552 +#endif // LEAP_SUPPORT //
69553 + //
69554 + // Get Current System time and Turn on AdjacentAPReport
69555 + //
69556 + NdisGetSystemUpTime(&pAd->StaCfg.CCXAdjacentAPLinkDownTime);
69557 + pAd->StaCfg.CCXAdjacentAPReportFlag = TRUE;
69558 + LinkDown(pAd, TRUE);
69559 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69560 +
69561 +#ifdef WPA_SUPPLICANT_SUPPORT
69562 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
69563 + if (pAd->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE)
69564 + {
69565 + union iwreq_data wrqu;
69566 + //send disassociate event to wpa_supplicant
69567 + memset(&wrqu, 0, sizeof(wrqu));
69568 + wrqu.data.flags = RT_DISASSOC_EVENT_FLAG;
69569 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
69570 + }
69571 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69572 +#endif // WPA_SUPPLICANT_SUPPORT //
69573 +
69574 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
69575 + {
69576 + union iwreq_data wrqu;
69577 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
69578 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
69579 + }
69580 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69581 + }
69582 + }
69583 + else
69584 + {
69585 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - PeerDisassocAction() sanity check fail\n"));
69586 + }
69587 +
69588 +}
69589 +
69590 +/*
69591 + ==========================================================================
69592 + Description:
69593 + what the state machine will do after assoc timeout
69594 + Parameters:
69595 + Elme -
69596 +
69597 + IRQL = DISPATCH_LEVEL
69598 +
69599 + ==========================================================================
69600 + */
69601 +VOID AssocTimeoutAction(
69602 + IN PRTMP_ADAPTER pAd,
69603 + IN MLME_QUEUE_ELEM *Elem)
69604 +{
69605 + USHORT Status;
69606 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - AssocTimeoutAction\n"));
69607 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69608 + Status = MLME_REJ_TIMEOUT;
69609 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_ASSOC_CONF, 2, &Status);
69610 +}
69611 +
69612 +/*
69613 + ==========================================================================
69614 + Description:
69615 + what the state machine will do after reassoc timeout
69616 +
69617 + IRQL = DISPATCH_LEVEL
69618 +
69619 + ==========================================================================
69620 + */
69621 +VOID ReassocTimeoutAction(
69622 + IN PRTMP_ADAPTER pAd,
69623 + IN MLME_QUEUE_ELEM *Elem)
69624 +{
69625 + USHORT Status;
69626 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - ReassocTimeoutAction\n"));
69627 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69628 + Status = MLME_REJ_TIMEOUT;
69629 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_REASSOC_CONF, 2, &Status);
69630 +}
69631 +
69632 +/*
69633 + ==========================================================================
69634 + Description:
69635 + what the state machine will do after disassoc timeout
69636 +
69637 + IRQL = DISPATCH_LEVEL
69638 +
69639 + ==========================================================================
69640 + */
69641 +VOID DisassocTimeoutAction(
69642 + IN PRTMP_ADAPTER pAd,
69643 + IN MLME_QUEUE_ELEM *Elem)
69644 +{
69645 + USHORT Status;
69646 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - DisassocTimeoutAction\n"));
69647 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69648 + Status = MLME_SUCCESS;
69649 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_DISASSOC_CONF, 2, &Status);
69650 +}
69651 +
69652 +VOID InvalidStateWhenAssoc(
69653 + IN PRTMP_ADAPTER pAd,
69654 + IN MLME_QUEUE_ELEM *Elem)
69655 +{
69656 + USHORT Status;
69657 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - InvalidStateWhenAssoc(state=%ld), reset ASSOC state machine\n",
69658 + pAd->Mlme.AssocMachine.CurrState));
69659 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69660 + Status = MLME_STATE_MACHINE_REJECT;
69661 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_ASSOC_CONF, 2, &Status);
69662 +}
69663 +
69664 +VOID InvalidStateWhenReassoc(
69665 + IN PRTMP_ADAPTER pAd,
69666 + IN MLME_QUEUE_ELEM *Elem)
69667 +{
69668 + USHORT Status;
69669 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - InvalidStateWhenReassoc(state=%ld), reset ASSOC state machine\n",
69670 + pAd->Mlme.AssocMachine.CurrState));
69671 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69672 + Status = MLME_STATE_MACHINE_REJECT;
69673 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_REASSOC_CONF, 2, &Status);
69674 +}
69675 +
69676 +VOID InvalidStateWhenDisassociate(
69677 + IN PRTMP_ADAPTER pAd,
69678 + IN MLME_QUEUE_ELEM *Elem)
69679 +{
69680 + USHORT Status;
69681 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - InvalidStateWhenDisassoc(state=%ld), reset ASSOC state machine\n",
69682 + pAd->Mlme.AssocMachine.CurrState));
69683 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
69684 + Status = MLME_STATE_MACHINE_REJECT;
69685 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_DISASSOC_CONF, 2, &Status);
69686 +}
69687 +
69688 +/*
69689 + ==========================================================================
69690 + Description:
69691 + right part of IEEE 802.11/1999 page 374
69692 + Note:
69693 + This event should never cause ASSOC state machine perform state
69694 + transition, and has no relationship with CNTL machine. So we separate
69695 + this routine as a service outside of ASSOC state transition table.
69696 +
69697 + IRQL = DISPATCH_LEVEL
69698 +
69699 + ==========================================================================
69700 + */
69701 +VOID Cls3errAction(
69702 + IN PRTMP_ADAPTER pAd,
69703 + IN PUCHAR pAddr)
69704 +{
69705 + HEADER_802_11 DisassocHdr;
69706 + PHEADER_802_11 pDisassocHdr;
69707 + PUCHAR pOutBuffer = NULL;
69708 + ULONG FrameLen = 0;
69709 + NDIS_STATUS NStatus;
69710 + USHORT Reason = REASON_CLS3ERR;
69711 +
69712 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
69713 + if (NStatus != NDIS_STATUS_SUCCESS)
69714 + return;
69715 +
69716 + DBGPRINT(RT_DEBUG_TRACE, ("ASSOC - Class 3 Error, Send DISASSOC frame\n"));
69717 + MgtMacHeaderInit(pAd, &DisassocHdr, SUBTYPE_DISASSOC, 0, pAddr, pAd->CommonCfg.Bssid); // patch peap ttls switching issue
69718 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
69719 + sizeof(HEADER_802_11),&DisassocHdr,
69720 + 2, &Reason,
69721 + END_OF_ARGS);
69722 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
69723 +
69724 + // To patch Instance and Buffalo(N) AP
69725 + // Driver has to send deauth to Instance AP, but Buffalo(N) needs to send disassoc to reset Authenticator's state machine
69726 + // Therefore, we send both of them.
69727 + pDisassocHdr = (PHEADER_802_11)pOutBuffer;
69728 + pDisassocHdr->FC.SubType = SUBTYPE_DEAUTH;
69729 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
69730 +
69731 + MlmeFreeMemory(pAd, pOutBuffer);
69732 +
69733 + pAd->StaCfg.DisassocReason = REASON_CLS3ERR;
69734 + COPY_MAC_ADDR(pAd->StaCfg.DisassocSta, pAddr);
69735 +}
69736 +
69737 + /*
69738 + ==========================================================================
69739 + Description:
69740 + Switch between WEP and CKIP upon new association up.
69741 + Parameters:
69742 +
69743 + IRQL = DISPATCH_LEVEL
69744 +
69745 + ==========================================================================
69746 + */
69747 +VOID SwitchBetweenWepAndCkip(
69748 + IN PRTMP_ADAPTER pAd)
69749 +{
69750 + int i;
69751 + SHAREDKEY_MODE_STRUC csr1;
69752 +
69753 + // if KP is required. change the CipherAlg in hardware shard key table from WEP
69754 + // to CKIP. else remain as WEP
69755 + if (pAd->StaCfg.bCkipOn && (pAd->StaCfg.CkipFlag & 0x10))
69756 + {
69757 + // modify hardware key table so that MAC use correct algorithm to decrypt RX
69758 + RTMP_IO_READ32(pAd, SHARED_KEY_MODE_BASE, &csr1.word);
69759 + if (csr1.field.Bss0Key0CipherAlg == CIPHER_WEP64)
69760 + csr1.field.Bss0Key0CipherAlg = CIPHER_CKIP64;
69761 + else if (csr1.field.Bss0Key0CipherAlg == CIPHER_WEP128)
69762 + csr1.field.Bss0Key0CipherAlg = CIPHER_CKIP128;
69763 +
69764 + if (csr1.field.Bss0Key1CipherAlg == CIPHER_WEP64)
69765 + csr1.field.Bss0Key1CipherAlg = CIPHER_CKIP64;
69766 + else if (csr1.field.Bss0Key1CipherAlg == CIPHER_WEP128)
69767 + csr1.field.Bss0Key1CipherAlg = CIPHER_CKIP128;
69768 +
69769 + if (csr1.field.Bss0Key2CipherAlg == CIPHER_WEP64)
69770 + csr1.field.Bss0Key2CipherAlg = CIPHER_CKIP64;
69771 + else if (csr1.field.Bss0Key2CipherAlg == CIPHER_WEP128)
69772 + csr1.field.Bss0Key2CipherAlg = CIPHER_CKIP128;
69773 +
69774 + if (csr1.field.Bss0Key3CipherAlg == CIPHER_WEP64)
69775 + csr1.field.Bss0Key3CipherAlg = CIPHER_CKIP64;
69776 + else if (csr1.field.Bss0Key3CipherAlg == CIPHER_WEP128)
69777 + csr1.field.Bss0Key3CipherAlg = CIPHER_CKIP128;
69778 + RTMP_IO_WRITE32(pAd, SHARED_KEY_MODE_BASE, csr1.word);
69779 + DBGPRINT(RT_DEBUG_TRACE, ("SwitchBetweenWepAndCkip: modify BSS0 cipher to %s\n", CipherName[csr1.field.Bss0Key0CipherAlg]));
69780 +
69781 + // modify software key table so that driver can specify correct algorithm in TXD upon TX
69782 + for (i=0; i<SHARE_KEY_NUM; i++)
69783 + {
69784 + if (pAd->SharedKey[BSS0][i].CipherAlg == CIPHER_WEP64)
69785 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_CKIP64;
69786 + else if (pAd->SharedKey[BSS0][i].CipherAlg == CIPHER_WEP128)
69787 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_CKIP128;
69788 + }
69789 + }
69790 +
69791 + // else if KP NOT inused. change the CipherAlg in hardware shard key table from CKIP
69792 + // to WEP.
69793 + else
69794 + {
69795 + // modify hardware key table so that MAC use correct algorithm to decrypt RX
69796 + RTMP_IO_READ32(pAd, SHARED_KEY_MODE_BASE, &csr1.word);
69797 + if (csr1.field.Bss0Key0CipherAlg == CIPHER_CKIP64)
69798 + csr1.field.Bss0Key0CipherAlg = CIPHER_WEP64;
69799 + else if (csr1.field.Bss0Key0CipherAlg == CIPHER_CKIP128)
69800 + csr1.field.Bss0Key0CipherAlg = CIPHER_WEP128;
69801 +
69802 + if (csr1.field.Bss0Key1CipherAlg == CIPHER_CKIP64)
69803 + csr1.field.Bss0Key1CipherAlg = CIPHER_WEP64;
69804 + else if (csr1.field.Bss0Key1CipherAlg == CIPHER_CKIP128)
69805 + csr1.field.Bss0Key1CipherAlg = CIPHER_WEP128;
69806 +
69807 + if (csr1.field.Bss0Key2CipherAlg == CIPHER_CKIP64)
69808 + csr1.field.Bss0Key2CipherAlg = CIPHER_WEP64;
69809 + else if (csr1.field.Bss0Key2CipherAlg == CIPHER_CKIP128)
69810 + csr1.field.Bss0Key2CipherAlg = CIPHER_WEP128;
69811 +
69812 + if (csr1.field.Bss0Key3CipherAlg == CIPHER_CKIP64)
69813 + csr1.field.Bss0Key3CipherAlg = CIPHER_WEP64;
69814 + else if (csr1.field.Bss0Key3CipherAlg == CIPHER_CKIP128)
69815 + csr1.field.Bss0Key3CipherAlg = CIPHER_WEP128;
69816 +
69817 + // modify software key table so that driver can specify correct algorithm in TXD upon TX
69818 + for (i=0; i<SHARE_KEY_NUM; i++)
69819 + {
69820 + if (pAd->SharedKey[BSS0][i].CipherAlg == CIPHER_CKIP64)
69821 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_WEP64;
69822 + else if (pAd->SharedKey[BSS0][i].CipherAlg == CIPHER_CKIP128)
69823 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_WEP128;
69824 + }
69825 +
69826 + //
69827 + // On WPA-NONE, must update CipherAlg.
69828 + // Because the OID_802_11_WEP_STATUS was been set after OID_802_11_ADD_KEY
69829 + // and CipherAlg will be CIPHER_NONE by Windows ZeroConfig.
69830 + // So we need to update CipherAlg after connect.
69831 + //
69832 + if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
69833 + {
69834 + for (i = 0; i < SHARE_KEY_NUM; i++)
69835 + {
69836 + if (pAd->SharedKey[BSS0][i].KeyLen != 0)
69837 + {
69838 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled)
69839 + {
69840 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_TKIP;
69841 + }
69842 + else if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
69843 + {
69844 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_AES;
69845 + }
69846 + }
69847 + else
69848 + {
69849 + pAd->SharedKey[BSS0][i].CipherAlg = CIPHER_NONE;
69850 + }
69851 + }
69852 +
69853 + csr1.field.Bss0Key0CipherAlg = pAd->SharedKey[BSS0][0].CipherAlg;
69854 + csr1.field.Bss0Key1CipherAlg = pAd->SharedKey[BSS0][1].CipherAlg;
69855 + csr1.field.Bss0Key2CipherAlg = pAd->SharedKey[BSS0][2].CipherAlg;
69856 + csr1.field.Bss0Key3CipherAlg = pAd->SharedKey[BSS0][3].CipherAlg;
69857 + }
69858 + RTMP_IO_WRITE32(pAd, SHARED_KEY_MODE_BASE, csr1.word);
69859 + DBGPRINT(RT_DEBUG_TRACE, ("SwitchBetweenWepAndCkip: modify BSS0 cipher to %s\n", CipherName[csr1.field.Bss0Key0CipherAlg]));
69860 + }
69861 +}
69862 +
69863 +#ifdef WPA_SUPPLICANT_SUPPORT
69864 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
69865 +VOID SendAssocIEsToWpaSupplicant(
69866 + IN PRTMP_ADAPTER pAd)
69867 +{
69868 + union iwreq_data wrqu;
69869 + unsigned char custom[IW_CUSTOM_MAX] = {0};
69870 +
69871 + if ((pAd->StaCfg.ReqVarIELen + 17) <= IW_CUSTOM_MAX)
69872 + {
69873 + sprintf(custom, "ASSOCINFO_ReqIEs=");
69874 + NdisMoveMemory(custom+17, pAd->StaCfg.ReqVarIEs, pAd->StaCfg.ReqVarIELen);
69875 + memset(&wrqu, 0, sizeof(wrqu));
69876 + wrqu.data.length = pAd->StaCfg.ReqVarIELen + 17;
69877 + wrqu.data.flags = RT_REQIE_EVENT_FLAG;
69878 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, custom);
69879 +
69880 + memset(&wrqu, 0, sizeof(wrqu));
69881 + wrqu.data.flags = RT_ASSOCINFO_EVENT_FLAG;
69882 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
69883 + }
69884 + else
69885 + DBGPRINT(RT_DEBUG_TRACE, ("pAd->StaCfg.ReqVarIELen + 17 > MAX_CUSTOM_LEN\n"));
69886 +
69887 + return;
69888 +}
69889 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69890 +#endif // WPA_SUPPLICANT_SUPPORT //
69891 +
69892 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
69893 +int wext_notify_event_assoc(
69894 + IN RTMP_ADAPTER *pAd)
69895 +{
69896 + union iwreq_data wrqu;
69897 + char custom[IW_CUSTOM_MAX] = {0};
69898 +
69899 +#if WIRELESS_EXT > 17
69900 + if (pAd->StaCfg.ReqVarIELen <= IW_CUSTOM_MAX)
69901 + {
69902 + wrqu.data.length = pAd->StaCfg.ReqVarIELen;
69903 + memcpy(custom, pAd->StaCfg.ReqVarIEs, pAd->StaCfg.ReqVarIELen);
69904 + wireless_send_event(pAd->net_dev, IWEVASSOCREQIE, &wrqu, custom);
69905 + }
69906 + else
69907 + DBGPRINT(RT_DEBUG_TRACE, ("pAd->StaCfg.ReqVarIELen > MAX_CUSTOM_LEN\n"));
69908 +#else
69909 + if (((pAd->StaCfg.ReqVarIELen*2) + 17) <= IW_CUSTOM_MAX)
69910 + {
69911 + UCHAR idx;
69912 + wrqu.data.length = (pAd->StaCfg.ReqVarIELen*2) + 17;
69913 + sprintf(custom, "ASSOCINFO(ReqIEs=");
69914 + for (idx=0; idx<pAd->StaCfg.ReqVarIELen; idx++)
69915 + sprintf(custom, "%s%02x", custom, pAd->StaCfg.ReqVarIEs[idx]);
69916 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, custom);
69917 + }
69918 + else
69919 + DBGPRINT(RT_DEBUG_TRACE, ("(pAd->StaCfg.ReqVarIELen*2) + 17 > MAX_CUSTOM_LEN\n"));
69920 +#endif
69921 +
69922 + return 0;
69923 +
69924 +}
69925 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
69926 +
69927 --- /dev/null
69928 +++ b/drivers/staging/rt2860/sta/auth.c
69929 @@ -0,0 +1,474 @@
69930 +/*
69931 + *************************************************************************
69932 + * Ralink Tech Inc.
69933 + * 5F., No.36, Taiyuan St., Jhubei City,
69934 + * Hsinchu County 302,
69935 + * Taiwan, R.O.C.
69936 + *
69937 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
69938 + *
69939 + * This program is free software; you can redistribute it and/or modify *
69940 + * it under the terms of the GNU General Public License as published by *
69941 + * the Free Software Foundation; either version 2 of the License, or *
69942 + * (at your option) any later version. *
69943 + * *
69944 + * This program is distributed in the hope that it will be useful, *
69945 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
69946 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
69947 + * GNU General Public License for more details. *
69948 + * *
69949 + * You should have received a copy of the GNU General Public License *
69950 + * along with this program; if not, write to the *
69951 + * Free Software Foundation, Inc., *
69952 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
69953 + * *
69954 + *************************************************************************
69955 +
69956 + Module Name:
69957 + auth.c
69958 +
69959 + Abstract:
69960 +
69961 + Revision History:
69962 + Who When What
69963 + -------- ---------- ----------------------------------------------
69964 + John 2004-9-3 porting from RT2500
69965 +*/
69966 +#include "../rt_config.h"
69967 +
69968 +/*
69969 + ==========================================================================
69970 + Description:
69971 + authenticate state machine init, including state transition and timer init
69972 + Parameters:
69973 + Sm - pointer to the auth state machine
69974 + Note:
69975 + The state machine looks like this
69976 +
69977 + AUTH_REQ_IDLE AUTH_WAIT_SEQ2 AUTH_WAIT_SEQ4
69978 + MT2_MLME_AUTH_REQ mlme_auth_req_action invalid_state_when_auth invalid_state_when_auth
69979 + MT2_PEER_AUTH_EVEN drop peer_auth_even_at_seq2_action peer_auth_even_at_seq4_action
69980 + MT2_AUTH_TIMEOUT Drop auth_timeout_action auth_timeout_action
69981 +
69982 + IRQL = PASSIVE_LEVEL
69983 +
69984 + ==========================================================================
69985 + */
69986 +
69987 +void AuthStateMachineInit(
69988 + IN PRTMP_ADAPTER pAd,
69989 + IN STATE_MACHINE *Sm,
69990 + OUT STATE_MACHINE_FUNC Trans[])
69991 +{
69992 + StateMachineInit(Sm, Trans, MAX_AUTH_STATE, MAX_AUTH_MSG, (STATE_MACHINE_FUNC)Drop, AUTH_REQ_IDLE, AUTH_MACHINE_BASE);
69993 +
69994 + // the first column
69995 + StateMachineSetAction(Sm, AUTH_REQ_IDLE, MT2_MLME_AUTH_REQ, (STATE_MACHINE_FUNC)MlmeAuthReqAction);
69996 +
69997 + // the second column
69998 + StateMachineSetAction(Sm, AUTH_WAIT_SEQ2, MT2_MLME_AUTH_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenAuth);
69999 + StateMachineSetAction(Sm, AUTH_WAIT_SEQ2, MT2_PEER_AUTH_EVEN, (STATE_MACHINE_FUNC)PeerAuthRspAtSeq2Action);
70000 + StateMachineSetAction(Sm, AUTH_WAIT_SEQ2, MT2_AUTH_TIMEOUT, (STATE_MACHINE_FUNC)AuthTimeoutAction);
70001 +
70002 + // the third column
70003 + StateMachineSetAction(Sm, AUTH_WAIT_SEQ4, MT2_MLME_AUTH_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenAuth);
70004 + StateMachineSetAction(Sm, AUTH_WAIT_SEQ4, MT2_PEER_AUTH_EVEN, (STATE_MACHINE_FUNC)PeerAuthRspAtSeq4Action);
70005 + StateMachineSetAction(Sm, AUTH_WAIT_SEQ4, MT2_AUTH_TIMEOUT, (STATE_MACHINE_FUNC)AuthTimeoutAction);
70006 +
70007 + RTMPInitTimer(pAd, &pAd->MlmeAux.AuthTimer, GET_TIMER_FUNCTION(AuthTimeout), pAd, FALSE);
70008 +}
70009 +
70010 +/*
70011 + ==========================================================================
70012 + Description:
70013 + function to be executed at timer thread when auth timer expires
70014 +
70015 + IRQL = DISPATCH_LEVEL
70016 +
70017 + ==========================================================================
70018 + */
70019 +VOID AuthTimeout(
70020 + IN PVOID SystemSpecific1,
70021 + IN PVOID FunctionContext,
70022 + IN PVOID SystemSpecific2,
70023 + IN PVOID SystemSpecific3)
70024 +{
70025 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
70026 +
70027 + DBGPRINT(RT_DEBUG_TRACE,("AUTH - AuthTimeout\n"));
70028 +
70029 + // Do nothing if the driver is starting halt state.
70030 + // This might happen when timer already been fired before cancel timer with mlmehalt
70031 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS | fRTMP_ADAPTER_NIC_NOT_EXIST))
70032 + return;
70033 +
70034 + // send a de-auth to reset AP's state machine (Patch AP-Dir635)
70035 + if (pAd->Mlme.AuthMachine.CurrState == AUTH_WAIT_SEQ2)
70036 + Cls2errAction(pAd, pAd->MlmeAux.Bssid);
70037 +
70038 +
70039 + MlmeEnqueue(pAd, AUTH_STATE_MACHINE, MT2_AUTH_TIMEOUT, 0, NULL);
70040 + RT28XX_MLME_HANDLER(pAd);
70041 +}
70042 +
70043 +
70044 +/*
70045 + ==========================================================================
70046 + Description:
70047 +
70048 + IRQL = DISPATCH_LEVEL
70049 +
70050 + ==========================================================================
70051 + */
70052 +VOID MlmeAuthReqAction(
70053 + IN PRTMP_ADAPTER pAd,
70054 + IN MLME_QUEUE_ELEM *Elem)
70055 +{
70056 + UCHAR Addr[6];
70057 + USHORT Alg, Seq, Status;
70058 + ULONG Timeout;
70059 + HEADER_802_11 AuthHdr;
70060 + BOOLEAN TimerCancelled;
70061 + NDIS_STATUS NStatus;
70062 + PUCHAR pOutBuffer = NULL;
70063 + ULONG FrameLen = 0;
70064 +
70065 + // Block all authentication request durning WPA block period
70066 + if (pAd->StaCfg.bBlockAssoc == TRUE)
70067 + {
70068 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - Block Auth request durning WPA block period!\n"));
70069 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70070 + Status = MLME_STATE_MACHINE_REJECT;
70071 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70072 + }
70073 + else if(MlmeAuthReqSanity(pAd, Elem->Msg, Elem->MsgLen, Addr, &Timeout, &Alg))
70074 + {
70075 + // reset timer
70076 + RTMPCancelTimer(&pAd->MlmeAux.AuthTimer, &TimerCancelled);
70077 + COPY_MAC_ADDR(pAd->MlmeAux.Bssid, Addr);
70078 + pAd->MlmeAux.Alg = Alg;
70079 + Seq = 1;
70080 + Status = MLME_SUCCESS;
70081 +
70082 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
70083 + if(NStatus != NDIS_STATUS_SUCCESS)
70084 + {
70085 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - MlmeAuthReqAction(Alg:%d) allocate memory failed\n", Alg));
70086 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70087 + Status = MLME_FAIL_NO_RESOURCE;
70088 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70089 + return;
70090 + }
70091 +
70092 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - Send AUTH request seq#1 (Alg=%d)...\n", Alg));
70093 + MgtMacHeaderInit(pAd, &AuthHdr, SUBTYPE_AUTH, 0, Addr, pAd->MlmeAux.Bssid);
70094 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
70095 + sizeof(HEADER_802_11),&AuthHdr,
70096 + 2, &Alg,
70097 + 2, &Seq,
70098 + 2, &Status,
70099 + END_OF_ARGS);
70100 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
70101 + MlmeFreeMemory(pAd, pOutBuffer);
70102 +
70103 + RTMPSetTimer(&pAd->MlmeAux.AuthTimer, Timeout);
70104 + pAd->Mlme.AuthMachine.CurrState = AUTH_WAIT_SEQ2;
70105 + }
70106 + else
70107 + {
70108 + DBGPRINT_ERR(("AUTH - MlmeAuthReqAction() sanity check failed\n"));
70109 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70110 + Status = MLME_INVALID_FORMAT;
70111 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70112 + }
70113 +}
70114 +
70115 +/*
70116 + ==========================================================================
70117 + Description:
70118 +
70119 + IRQL = DISPATCH_LEVEL
70120 +
70121 + ==========================================================================
70122 + */
70123 +VOID PeerAuthRspAtSeq2Action(
70124 + IN PRTMP_ADAPTER pAd,
70125 + IN MLME_QUEUE_ELEM *Elem)
70126 +{
70127 + UCHAR Addr2[MAC_ADDR_LEN];
70128 + USHORT Seq, Status, RemoteStatus, Alg;
70129 + UCHAR ChlgText[CIPHER_TEXT_LEN];
70130 + UCHAR CyperChlgText[CIPHER_TEXT_LEN + 8 + 8];
70131 + UCHAR Element[2];
70132 + HEADER_802_11 AuthHdr;
70133 + BOOLEAN TimerCancelled;
70134 + PUCHAR pOutBuffer = NULL;
70135 + NDIS_STATUS NStatus;
70136 + ULONG FrameLen = 0;
70137 + USHORT Status2;
70138 +
70139 + if (PeerAuthSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, &Alg, &Seq, &Status, ChlgText))
70140 + {
70141 + if (MAC_ADDR_EQUAL(pAd->MlmeAux.Bssid, Addr2) && Seq == 2)
70142 + {
70143 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - Receive AUTH_RSP seq#2 to me (Alg=%d, Status=%d)\n", Alg, Status));
70144 + RTMPCancelTimer(&pAd->MlmeAux.AuthTimer, &TimerCancelled);
70145 +
70146 + if (Status == MLME_SUCCESS)
70147 + {
70148 + // Authentication Mode "LEAP" has allow for CCX 1.X
70149 + if ((pAd->MlmeAux.Alg == Ndis802_11AuthModeOpen)
70150 +#ifdef LEAP_SUPPORT
70151 + || (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
70152 +#endif // LEAP_SUPPORT //
70153 + )
70154 + {
70155 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70156 +#ifdef LEAP_SUPPORT
70157 + pAd->Mlme.LeapMachine.CurrState = LEAP_IDLE;
70158 +#endif // LEAP_SUPPORT //
70159 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70160 + }
70161 + else
70162 + {
70163 + // 2. shared key, need to be challenged
70164 + Seq++;
70165 + RemoteStatus = MLME_SUCCESS;
70166 +
70167 + // Get an unused nonpaged memory
70168 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer);
70169 + if(NStatus != NDIS_STATUS_SUCCESS)
70170 + {
70171 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - PeerAuthRspAtSeq2Action() allocate memory fail\n"));
70172 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70173 + Status2 = MLME_FAIL_NO_RESOURCE;
70174 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status2);
70175 + return;
70176 + }
70177 +
70178 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - Send AUTH request seq#3...\n"));
70179 + MgtMacHeaderInit(pAd, &AuthHdr, SUBTYPE_AUTH, 0, Addr2, pAd->MlmeAux.Bssid);
70180 + AuthHdr.FC.Wep = 1;
70181 + // Encrypt challenge text & auth information
70182 + RTMPInitWepEngine(
70183 + pAd,
70184 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key,
70185 + pAd->StaCfg.DefaultKeyId,
70186 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].KeyLen,
70187 + CyperChlgText);
70188 +
70189 + Alg = cpu2le16(*(USHORT *)&Alg);
70190 + Seq = cpu2le16(*(USHORT *)&Seq);
70191 + RemoteStatus= cpu2le16(*(USHORT *)&RemoteStatus);
70192 +
70193 + RTMPEncryptData(pAd, (PUCHAR) &Alg, CyperChlgText + 4, 2);
70194 + RTMPEncryptData(pAd, (PUCHAR) &Seq, CyperChlgText + 6, 2);
70195 + RTMPEncryptData(pAd, (PUCHAR) &RemoteStatus, CyperChlgText + 8, 2);
70196 + Element[0] = 16;
70197 + Element[1] = 128;
70198 + RTMPEncryptData(pAd, Element, CyperChlgText + 10, 2);
70199 + RTMPEncryptData(pAd, ChlgText, CyperChlgText + 12, 128);
70200 + RTMPSetICV(pAd, CyperChlgText + 140);
70201 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
70202 + sizeof(HEADER_802_11), &AuthHdr,
70203 + CIPHER_TEXT_LEN + 16, CyperChlgText,
70204 + END_OF_ARGS);
70205 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
70206 + MlmeFreeMemory(pAd, pOutBuffer);
70207 +
70208 + RTMPSetTimer(&pAd->MlmeAux.AuthTimer, AUTH_TIMEOUT);
70209 + pAd->Mlme.AuthMachine.CurrState = AUTH_WAIT_SEQ4;
70210 + }
70211 + }
70212 + else
70213 + {
70214 +#ifdef LEAP_SUPPORT
70215 + if (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
70216 + {
70217 + //Invalid Authentication possible rogue AP
70218 + //Add this Ap to Rogue AP.
70219 + RogueApTableSetEntry(pAd, &pAd->StaCfg.RogueApTab, Addr2, LEAP_REASON_INVALID_AUTH);
70220 + }
70221 +#endif // LEAP_SUPPORT //
70222 + pAd->StaCfg.AuthFailReason = Status;
70223 + COPY_MAC_ADDR(pAd->StaCfg.AuthFailSta, Addr2);
70224 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70225 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70226 + }
70227 + }
70228 + }
70229 + else
70230 + {
70231 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - PeerAuthSanity() sanity check fail\n"));
70232 + }
70233 +}
70234 +
70235 +/*
70236 + ==========================================================================
70237 + Description:
70238 +
70239 + IRQL = DISPATCH_LEVEL
70240 +
70241 + ==========================================================================
70242 + */
70243 +VOID PeerAuthRspAtSeq4Action(
70244 + IN PRTMP_ADAPTER pAd,
70245 + IN MLME_QUEUE_ELEM *Elem)
70246 +{
70247 + UCHAR Addr2[MAC_ADDR_LEN];
70248 + USHORT Alg, Seq, Status;
70249 + CHAR ChlgText[CIPHER_TEXT_LEN];
70250 + BOOLEAN TimerCancelled;
70251 +
70252 + if(PeerAuthSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, &Alg, &Seq, &Status, ChlgText))
70253 + {
70254 + if(MAC_ADDR_EQUAL(pAd->MlmeAux.Bssid, Addr2) && Seq == 4)
70255 + {
70256 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - Receive AUTH_RSP seq#4 to me\n"));
70257 + RTMPCancelTimer(&pAd->MlmeAux.AuthTimer, &TimerCancelled);
70258 +
70259 + if (Status != MLME_SUCCESS)
70260 + {
70261 + pAd->StaCfg.AuthFailReason = Status;
70262 + COPY_MAC_ADDR(pAd->StaCfg.AuthFailSta, Addr2);
70263 + }
70264 +
70265 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70266 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70267 + }
70268 + }
70269 + else
70270 + {
70271 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - PeerAuthRspAtSeq4Action() sanity check fail\n"));
70272 + }
70273 +}
70274 +
70275 +/*
70276 + ==========================================================================
70277 + Description:
70278 +
70279 + IRQL = DISPATCH_LEVEL
70280 +
70281 + ==========================================================================
70282 + */
70283 +VOID MlmeDeauthReqAction(
70284 + IN PRTMP_ADAPTER pAd,
70285 + IN MLME_QUEUE_ELEM *Elem)
70286 +{
70287 + MLME_DEAUTH_REQ_STRUCT *pInfo;
70288 + HEADER_802_11 DeauthHdr;
70289 + PUCHAR pOutBuffer = NULL;
70290 + NDIS_STATUS NStatus;
70291 + ULONG FrameLen = 0;
70292 + USHORT Status;
70293 +
70294 + pInfo = (MLME_DEAUTH_REQ_STRUCT *)Elem->Msg;
70295 +
70296 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
70297 + if (NStatus != NDIS_STATUS_SUCCESS)
70298 + {
70299 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - MlmeDeauthReqAction() allocate memory fail\n"));
70300 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70301 + Status = MLME_FAIL_NO_RESOURCE;
70302 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_DEAUTH_CONF, 2, &Status);
70303 + return;
70304 + }
70305 +
70306 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - Send DE-AUTH request (Reason=%d)...\n", pInfo->Reason));
70307 + MgtMacHeaderInit(pAd, &DeauthHdr, SUBTYPE_DEAUTH, 0, pInfo->Addr, pAd->MlmeAux.Bssid);
70308 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
70309 + sizeof(HEADER_802_11),&DeauthHdr,
70310 + 2, &pInfo->Reason,
70311 + END_OF_ARGS);
70312 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
70313 + MlmeFreeMemory(pAd, pOutBuffer);
70314 +
70315 + pAd->StaCfg.DeauthReason = pInfo->Reason;
70316 + COPY_MAC_ADDR(pAd->StaCfg.DeauthSta, pInfo->Addr);
70317 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70318 + Status = MLME_SUCCESS;
70319 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_DEAUTH_CONF, 2, &Status);
70320 +
70321 + // send wireless event - for deauthentication
70322 + if (pAd->CommonCfg.bWirelessEvent)
70323 + RTMPSendWirelessEvent(pAd, IW_DEAUTH_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
70324 +}
70325 +
70326 +/*
70327 + ==========================================================================
70328 + Description:
70329 +
70330 + IRQL = DISPATCH_LEVEL
70331 +
70332 + ==========================================================================
70333 + */
70334 +VOID AuthTimeoutAction(
70335 + IN PRTMP_ADAPTER pAd,
70336 + IN MLME_QUEUE_ELEM *Elem)
70337 +{
70338 + USHORT Status;
70339 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - AuthTimeoutAction\n"));
70340 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70341 + Status = MLME_REJ_TIMEOUT;
70342 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70343 +}
70344 +
70345 +/*
70346 + ==========================================================================
70347 + Description:
70348 +
70349 + IRQL = DISPATCH_LEVEL
70350 +
70351 + ==========================================================================
70352 + */
70353 +VOID InvalidStateWhenAuth(
70354 + IN PRTMP_ADAPTER pAd,
70355 + IN MLME_QUEUE_ELEM *Elem)
70356 +{
70357 + USHORT Status;
70358 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - InvalidStateWhenAuth (state=%ld), reset AUTH state machine\n", pAd->Mlme.AuthMachine.CurrState));
70359 + pAd->Mlme.AuthMachine.CurrState = AUTH_REQ_IDLE;
70360 + Status = MLME_STATE_MACHINE_REJECT;
70361 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_AUTH_CONF, 2, &Status);
70362 +}
70363 +
70364 +/*
70365 + ==========================================================================
70366 + Description:
70367 + Some STA/AP
70368 + Note:
70369 + This action should never trigger AUTH state transition, therefore we
70370 + separate it from AUTH state machine, and make it as a standalone service
70371 +
70372 + IRQL = DISPATCH_LEVEL
70373 +
70374 + ==========================================================================
70375 + */
70376 +VOID Cls2errAction(
70377 + IN PRTMP_ADAPTER pAd,
70378 + IN PUCHAR pAddr)
70379 +{
70380 + HEADER_802_11 DeauthHdr;
70381 + PUCHAR pOutBuffer = NULL;
70382 + NDIS_STATUS NStatus;
70383 + ULONG FrameLen = 0;
70384 + USHORT Reason = REASON_CLS2ERR;
70385 +
70386 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
70387 + if (NStatus != NDIS_STATUS_SUCCESS)
70388 + return;
70389 +
70390 + DBGPRINT(RT_DEBUG_TRACE, ("AUTH - Class 2 error, Send DEAUTH frame...\n"));
70391 + MgtMacHeaderInit(pAd, &DeauthHdr, SUBTYPE_DEAUTH, 0, pAddr, pAd->MlmeAux.Bssid);
70392 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
70393 + sizeof(HEADER_802_11),&DeauthHdr,
70394 + 2, &Reason,
70395 + END_OF_ARGS);
70396 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
70397 + MlmeFreeMemory(pAd, pOutBuffer);
70398 +
70399 + pAd->StaCfg.DeauthReason = Reason;
70400 + COPY_MAC_ADDR(pAd->StaCfg.DeauthSta, pAddr);
70401 +}
70402 +
70403 +
70404 --- /dev/null
70405 +++ b/drivers/staging/rt2860/sta/auth_rsp.c
70406 @@ -0,0 +1,167 @@
70407 +/*
70408 + *************************************************************************
70409 + * Ralink Tech Inc.
70410 + * 5F., No.36, Taiyuan St., Jhubei City,
70411 + * Hsinchu County 302,
70412 + * Taiwan, R.O.C.
70413 + *
70414 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
70415 + *
70416 + * This program is free software; you can redistribute it and/or modify *
70417 + * it under the terms of the GNU General Public License as published by *
70418 + * the Free Software Foundation; either version 2 of the License, or *
70419 + * (at your option) any later version. *
70420 + * *
70421 + * This program is distributed in the hope that it will be useful, *
70422 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
70423 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
70424 + * GNU General Public License for more details. *
70425 + * *
70426 + * You should have received a copy of the GNU General Public License *
70427 + * along with this program; if not, write to the *
70428 + * Free Software Foundation, Inc., *
70429 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
70430 + * *
70431 + *************************************************************************
70432 +
70433 + Module Name:
70434 + auth_rsp.c
70435 +
70436 + Abstract:
70437 +
70438 + Revision History:
70439 + Who When What
70440 + -------- ---------- ----------------------------------------------
70441 + John 2004-10-1 copy from RT2560
70442 +*/
70443 +#include "../rt_config.h"
70444 +
70445 +/*
70446 + ==========================================================================
70447 + Description:
70448 + authentication state machine init procedure
70449 + Parameters:
70450 + Sm - the state machine
70451 +
70452 + IRQL = PASSIVE_LEVEL
70453 +
70454 + ==========================================================================
70455 + */
70456 +VOID AuthRspStateMachineInit(
70457 + IN PRTMP_ADAPTER pAd,
70458 + IN PSTATE_MACHINE Sm,
70459 + IN STATE_MACHINE_FUNC Trans[])
70460 +{
70461 + StateMachineInit(Sm, Trans, MAX_AUTH_RSP_STATE, MAX_AUTH_RSP_MSG, (STATE_MACHINE_FUNC)Drop, AUTH_RSP_IDLE, AUTH_RSP_MACHINE_BASE);
70462 +
70463 + // column 1
70464 + StateMachineSetAction(Sm, AUTH_RSP_IDLE, MT2_PEER_DEAUTH, (STATE_MACHINE_FUNC)PeerDeauthAction);
70465 +
70466 + // column 2
70467 + StateMachineSetAction(Sm, AUTH_RSP_WAIT_CHAL, MT2_PEER_DEAUTH, (STATE_MACHINE_FUNC)PeerDeauthAction);
70468 +
70469 +}
70470 +
70471 +/*
70472 + ==========================================================================
70473 + Description:
70474 +
70475 + IRQL = DISPATCH_LEVEL
70476 +
70477 + ==========================================================================
70478 +*/
70479 +VOID PeerAuthSimpleRspGenAndSend(
70480 + IN PRTMP_ADAPTER pAd,
70481 + IN PHEADER_802_11 pHdr80211,
70482 + IN USHORT Alg,
70483 + IN USHORT Seq,
70484 + IN USHORT Reason,
70485 + IN USHORT Status)
70486 +{
70487 + HEADER_802_11 AuthHdr;
70488 + ULONG FrameLen = 0;
70489 + PUCHAR pOutBuffer = NULL;
70490 + NDIS_STATUS NStatus;
70491 +
70492 + if (Reason != MLME_SUCCESS)
70493 + {
70494 + DBGPRINT(RT_DEBUG_TRACE, ("Peer AUTH fail...\n"));
70495 + return;
70496 + }
70497 +
70498 + //Get an unused nonpaged memory
70499 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer);
70500 + if (NStatus != NDIS_STATUS_SUCCESS)
70501 + return;
70502 +
70503 + DBGPRINT(RT_DEBUG_TRACE, ("Send AUTH response (seq#2)...\n"));
70504 + MgtMacHeaderInit(pAd, &AuthHdr, SUBTYPE_AUTH, 0, pHdr80211->Addr2, pAd->MlmeAux.Bssid);
70505 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
70506 + sizeof(HEADER_802_11), &AuthHdr,
70507 + 2, &Alg,
70508 + 2, &Seq,
70509 + 2, &Reason,
70510 + END_OF_ARGS);
70511 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
70512 + MlmeFreeMemory(pAd, pOutBuffer);
70513 +}
70514 +
70515 +/*
70516 + ==========================================================================
70517 + Description:
70518 +
70519 + IRQL = DISPATCH_LEVEL
70520 +
70521 + ==========================================================================
70522 +*/
70523 +VOID PeerDeauthAction(
70524 + IN PRTMP_ADAPTER pAd,
70525 + IN PMLME_QUEUE_ELEM Elem)
70526 +{
70527 + UCHAR Addr2[MAC_ADDR_LEN];
70528 + USHORT Reason;
70529 +
70530 + if (PeerDeauthSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, &Reason))
70531 + {
70532 + if (INFRA_ON(pAd) && MAC_ADDR_EQUAL(Addr2, pAd->CommonCfg.Bssid))
70533 + {
70534 + DBGPRINT(RT_DEBUG_TRACE,("AUTH_RSP - receive DE-AUTH from our AP (Reason=%d)\n", Reason));
70535 +
70536 +
70537 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
70538 + {
70539 + union iwreq_data wrqu;
70540 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
70541 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
70542 + }
70543 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
70544 +
70545 +
70546 + // send wireless event - for deauthentication
70547 + if (pAd->CommonCfg.bWirelessEvent)
70548 + RTMPSendWirelessEvent(pAd, IW_DEAUTH_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
70549 +
70550 + LinkDown(pAd, TRUE);
70551 +
70552 + // Authentication Mode Cisco_LEAP has start a timer
70553 + // We should cancel it if using LEAP
70554 +#ifdef LEAP_SUPPORT
70555 + if (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
70556 + {
70557 + RTMPCancelTimer(&pAd->StaCfg.LeapAuthTimer, &TimerCancelled);
70558 + //Check is it mach the LEAP Authentication failed as possible a Rogue AP
70559 + //on it's PortSecured not equal to WPA_802_1X_PORT_SECURED while process the Authenticaton.
70560 + if ((pAd->StaCfg.PortSecured != WPA_802_1X_PORT_SECURED) && (pAd->Mlme.LeapMachine.CurrState != LEAP_IDLE))
70561 + {
70562 + RogueApTableSetEntry(pAd, &pAd->StaCfg.RogueApTab, Addr2, LEAP_REASON_AUTH_TIMEOUT);
70563 + }
70564 + }
70565 +#endif // LEAP_SUPPORT //
70566 + }
70567 + }
70568 + else
70569 + {
70570 + DBGPRINT(RT_DEBUG_TRACE,("AUTH_RSP - PeerDeauthAction() sanity check fail\n"));
70571 + }
70572 +}
70573 +
70574 --- /dev/null
70575 +++ b/drivers/staging/rt2860/sta/connect.c
70576 @@ -0,0 +1,2751 @@
70577 +/*
70578 + *************************************************************************
70579 + * Ralink Tech Inc.
70580 + * 5F., No.36, Taiyuan St., Jhubei City,
70581 + * Hsinchu County 302,
70582 + * Taiwan, R.O.C.
70583 + *
70584 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
70585 + *
70586 + * This program is free software; you can redistribute it and/or modify *
70587 + * it under the terms of the GNU General Public License as published by *
70588 + * the Free Software Foundation; either version 2 of the License, or *
70589 + * (at your option) any later version. *
70590 + * *
70591 + * This program is distributed in the hope that it will be useful, *
70592 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
70593 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
70594 + * GNU General Public License for more details. *
70595 + * *
70596 + * You should have received a copy of the GNU General Public License *
70597 + * along with this program; if not, write to the *
70598 + * Free Software Foundation, Inc., *
70599 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
70600 + * *
70601 + *************************************************************************
70602 +
70603 + Module Name:
70604 + connect.c
70605 +
70606 + Abstract:
70607 +
70608 + Revision History:
70609 + Who When What
70610 + -------- ---------- ----------------------------------------------
70611 + John 2004-08-08 Major modification from RT2560
70612 +*/
70613 +#include "../rt_config.h"
70614 +
70615 +UCHAR CipherSuiteWpaNoneTkip[] = {
70616 + 0x00, 0x50, 0xf2, 0x01, // oui
70617 + 0x01, 0x00, // Version
70618 + 0x00, 0x50, 0xf2, 0x02, // Multicast
70619 + 0x01, 0x00, // Number of unicast
70620 + 0x00, 0x50, 0xf2, 0x02, // unicast
70621 + 0x01, 0x00, // number of authentication method
70622 + 0x00, 0x50, 0xf2, 0x00 // authentication
70623 + };
70624 +UCHAR CipherSuiteWpaNoneTkipLen = (sizeof(CipherSuiteWpaNoneTkip) / sizeof(UCHAR));
70625 +
70626 +UCHAR CipherSuiteWpaNoneAes[] = {
70627 + 0x00, 0x50, 0xf2, 0x01, // oui
70628 + 0x01, 0x00, // Version
70629 + 0x00, 0x50, 0xf2, 0x04, // Multicast
70630 + 0x01, 0x00, // Number of unicast
70631 + 0x00, 0x50, 0xf2, 0x04, // unicast
70632 + 0x01, 0x00, // number of authentication method
70633 + 0x00, 0x50, 0xf2, 0x00 // authentication
70634 + };
70635 +UCHAR CipherSuiteWpaNoneAesLen = (sizeof(CipherSuiteWpaNoneAes) / sizeof(UCHAR));
70636 +
70637 +// The following MACRO is called after 1. starting an new IBSS, 2. succesfully JOIN an IBSS,
70638 +// or 3. succesfully ASSOCIATE to a BSS, 4. successfully RE_ASSOCIATE to a BSS
70639 +// All settings successfuly negotiated furing MLME state machines become final settings
70640 +// and are copied to pAd->StaActive
70641 +#define COPY_SETTINGS_FROM_MLME_AUX_TO_ACTIVE_CFG(_pAd) \
70642 +{ \
70643 + (_pAd)->CommonCfg.SsidLen = (_pAd)->MlmeAux.SsidLen; \
70644 + NdisMoveMemory((_pAd)->CommonCfg.Ssid, (_pAd)->MlmeAux.Ssid, (_pAd)->MlmeAux.SsidLen); \
70645 + COPY_MAC_ADDR((_pAd)->CommonCfg.Bssid, (_pAd)->MlmeAux.Bssid); \
70646 + (_pAd)->CommonCfg.Channel = (_pAd)->MlmeAux.Channel; \
70647 + (_pAd)->CommonCfg.CentralChannel = (_pAd)->MlmeAux.CentralChannel; \
70648 + (_pAd)->StaActive.Aid = (_pAd)->MlmeAux.Aid; \
70649 + (_pAd)->StaActive.AtimWin = (_pAd)->MlmeAux.AtimWin; \
70650 + (_pAd)->StaActive.CapabilityInfo = (_pAd)->MlmeAux.CapabilityInfo; \
70651 + (_pAd)->CommonCfg.BeaconPeriod = (_pAd)->MlmeAux.BeaconPeriod; \
70652 + (_pAd)->StaActive.CfpMaxDuration = (_pAd)->MlmeAux.CfpMaxDuration; \
70653 + (_pAd)->StaActive.CfpPeriod = (_pAd)->MlmeAux.CfpPeriod; \
70654 + (_pAd)->StaActive.SupRateLen = (_pAd)->MlmeAux.SupRateLen; \
70655 + NdisMoveMemory((_pAd)->StaActive.SupRate, (_pAd)->MlmeAux.SupRate, (_pAd)->MlmeAux.SupRateLen);\
70656 + (_pAd)->StaActive.ExtRateLen = (_pAd)->MlmeAux.ExtRateLen; \
70657 + NdisMoveMemory((_pAd)->StaActive.ExtRate, (_pAd)->MlmeAux.ExtRate, (_pAd)->MlmeAux.ExtRateLen);\
70658 + NdisMoveMemory(&(_pAd)->CommonCfg.APEdcaParm, &(_pAd)->MlmeAux.APEdcaParm, sizeof(EDCA_PARM));\
70659 + NdisMoveMemory(&(_pAd)->CommonCfg.APQosCapability, &(_pAd)->MlmeAux.APQosCapability, sizeof(QOS_CAPABILITY_PARM));\
70660 + NdisMoveMemory(&(_pAd)->CommonCfg.APQbssLoad, &(_pAd)->MlmeAux.APQbssLoad, sizeof(QBSS_LOAD_PARM));\
70661 + COPY_MAC_ADDR((_pAd)->MacTab.Content[BSSID_WCID].Addr, (_pAd)->MlmeAux.Bssid); \
70662 + (_pAd)->MacTab.Content[BSSID_WCID].Aid = (_pAd)->MlmeAux.Aid; \
70663 + (_pAd)->MacTab.Content[BSSID_WCID].PairwiseKey.CipherAlg = (_pAd)->StaCfg.PairCipher;\
70664 + COPY_MAC_ADDR((_pAd)->MacTab.Content[BSSID_WCID].PairwiseKey.BssId, (_pAd)->MlmeAux.Bssid);\
70665 + (_pAd)->MacTab.Content[BSSID_WCID].RateLen = (_pAd)->StaActive.SupRateLen + (_pAd)->StaActive.ExtRateLen;\
70666 +}
70667 +
70668 +/*
70669 + ==========================================================================
70670 + Description:
70671 +
70672 + IRQL = PASSIVE_LEVEL
70673 +
70674 + ==========================================================================
70675 +*/
70676 +VOID MlmeCntlInit(
70677 + IN PRTMP_ADAPTER pAd,
70678 + IN STATE_MACHINE *S,
70679 + OUT STATE_MACHINE_FUNC Trans[])
70680 +{
70681 + // Control state machine differs from other state machines, the interface
70682 + // follows the standard interface
70683 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
70684 +}
70685 +
70686 +/*
70687 + ==========================================================================
70688 + Description:
70689 +
70690 + IRQL = DISPATCH_LEVEL
70691 +
70692 + ==========================================================================
70693 +*/
70694 +VOID MlmeCntlMachinePerformAction(
70695 + IN PRTMP_ADAPTER pAd,
70696 + IN STATE_MACHINE *S,
70697 + IN MLME_QUEUE_ELEM *Elem)
70698 +{
70699 + switch(pAd->Mlme.CntlMachine.CurrState)
70700 + {
70701 + case CNTL_IDLE:
70702 + {
70703 + CntlIdleProc(pAd, Elem);
70704 + }
70705 + break;
70706 + case CNTL_WAIT_DISASSOC:
70707 + CntlWaitDisassocProc(pAd, Elem);
70708 + break;
70709 + case CNTL_WAIT_JOIN:
70710 + CntlWaitJoinProc(pAd, Elem);
70711 + break;
70712 +
70713 + // CNTL_WAIT_REASSOC is the only state in CNTL machine that does
70714 + // not triggered directly or indirectly by "RTMPSetInformation(OID_xxx)".
70715 + // Therefore not protected by NDIS's "only one outstanding OID request"
70716 + // rule. Which means NDIS may SET OID in the middle of ROAMing attempts.
70717 + // Current approach is to block new SET request at RTMPSetInformation()
70718 + // when CntlMachine.CurrState is not CNTL_IDLE
70719 + case CNTL_WAIT_REASSOC:
70720 + CntlWaitReassocProc(pAd, Elem);
70721 + break;
70722 +
70723 + case CNTL_WAIT_START:
70724 + CntlWaitStartProc(pAd, Elem);
70725 + break;
70726 + case CNTL_WAIT_AUTH:
70727 + CntlWaitAuthProc(pAd, Elem);
70728 + break;
70729 + case CNTL_WAIT_AUTH2:
70730 + CntlWaitAuthProc2(pAd, Elem);
70731 + break;
70732 + case CNTL_WAIT_ASSOC:
70733 + CntlWaitAssocProc(pAd, Elem);
70734 + break;
70735 +
70736 + case CNTL_WAIT_OID_LIST_SCAN:
70737 + if(Elem->MsgType == MT2_SCAN_CONF)
70738 + {
70739 + // Resume TxRing after SCANING complete. We hope the out-of-service time
70740 + // won't be too long to let upper layer time-out the waiting frames
70741 + RTMPResumeMsduTransmission(pAd);
70742 + if (pAd->StaCfg.CCXReqType != MSRN_TYPE_UNUSED)
70743 + {
70744 + // Cisco scan request is finished, prepare beacon report
70745 + MlmeEnqueue(pAd, AIRONET_STATE_MACHINE, MT2_AIRONET_SCAN_DONE, 0, NULL);
70746 + }
70747 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
70748 +
70749 + //
70750 + // Set LED status to previous status.
70751 + //
70752 + if (pAd->bLedOnScanning)
70753 + {
70754 + pAd->bLedOnScanning = FALSE;
70755 + RTMPSetLED(pAd, pAd->LedStatus);
70756 + }
70757 +#ifdef DOT11N_DRAFT3
70758 + // AP sent a 2040Coexistence mgmt frame, then station perform a scan, and then send back the respone.
70759 + if (pAd->CommonCfg.BSSCoexist2040.field.InfoReq == 1)
70760 + {
70761 + Update2040CoexistFrameAndNotify(pAd, BSSID_WCID, TRUE);
70762 + }
70763 +#endif // DOT11N_DRAFT3 //
70764 + }
70765 + break;
70766 +
70767 + case CNTL_WAIT_OID_DISASSOC:
70768 + if (Elem->MsgType == MT2_DISASSOC_CONF)
70769 + {
70770 + LinkDown(pAd, FALSE);
70771 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
70772 + }
70773 + break;
70774 + default:
70775 + DBGPRINT_ERR(("!ERROR! CNTL - Illegal message type(=%ld)", Elem->MsgType));
70776 + break;
70777 + }
70778 +}
70779 +
70780 +
70781 +/*
70782 + ==========================================================================
70783 + Description:
70784 +
70785 + IRQL = DISPATCH_LEVEL
70786 +
70787 + ==========================================================================
70788 +*/
70789 +VOID CntlIdleProc(
70790 + IN PRTMP_ADAPTER pAd,
70791 + IN MLME_QUEUE_ELEM *Elem)
70792 +{
70793 + MLME_DISASSOC_REQ_STRUCT DisassocReq;
70794 +
70795 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF))
70796 + return;
70797 +
70798 + switch(Elem->MsgType)
70799 + {
70800 + case OID_802_11_SSID:
70801 + CntlOidSsidProc(pAd, Elem);
70802 + break;
70803 +
70804 + case OID_802_11_BSSID:
70805 + CntlOidRTBssidProc(pAd,Elem);
70806 + break;
70807 +
70808 + case OID_802_11_BSSID_LIST_SCAN:
70809 + CntlOidScanProc(pAd,Elem);
70810 + break;
70811 +
70812 + case OID_802_11_DISASSOCIATE:
70813 +#ifdef RALINK_ATE
70814 + if(ATE_ON(pAd))
70815 + {
70816 + DBGPRINT(RT_DEBUG_TRACE, ("The driver is in ATE mode now\n"));
70817 + break;
70818 + }
70819 +#endif // RALINK_ATE //
70820 + DisassocParmFill(pAd, &DisassocReq, pAd->CommonCfg.Bssid, REASON_DISASSOC_STA_LEAVING);
70821 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_DISASSOC_REQ, sizeof(MLME_DISASSOC_REQ_STRUCT), &DisassocReq);
70822 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_DISASSOC;
70823 +#ifdef WPA_SUPPLICANT_SUPPORT
70824 + if (pAd->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_ENABLE_WITH_WEB_UI)
70825 +#endif // WPA_SUPPLICANT_SUPPORT //
70826 + {
70827 + // Set the AutoReconnectSsid to prevent it reconnect to old SSID
70828 + // Since calling this indicate user don't want to connect to that SSID anymore.
70829 + pAd->MlmeAux.AutoReconnectSsidLen= 32;
70830 + NdisZeroMemory(pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.AutoReconnectSsidLen);
70831 + }
70832 + break;
70833 +
70834 + case MT2_MLME_ROAMING_REQ:
70835 + CntlMlmeRoamingProc(pAd, Elem);
70836 + break;
70837 +
70838 + case OID_802_11_MIC_FAILURE_REPORT_FRAME:
70839 + WpaMicFailureReportFrame(pAd, Elem);
70840 + break;
70841 +
70842 +#ifdef QOS_DLS_SUPPORT
70843 + case RT_OID_802_11_SET_DLS_PARAM:
70844 + CntlOidDLSSetupProc(pAd, Elem);
70845 + break;
70846 +#endif // QOS_DLS_SUPPORT //
70847 +
70848 + default:
70849 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Illegal message in CntlIdleProc(MsgType=%ld)\n",Elem->MsgType));
70850 + break;
70851 + }
70852 +}
70853 +
70854 +VOID CntlOidScanProc(
70855 + IN PRTMP_ADAPTER pAd,
70856 + IN MLME_QUEUE_ELEM *Elem)
70857 +{
70858 + MLME_SCAN_REQ_STRUCT ScanReq;
70859 + ULONG BssIdx = BSS_NOT_FOUND;
70860 + BSS_ENTRY CurrBss;
70861 +
70862 +#ifdef RALINK_ATE
70863 +/* Disable scanning when ATE is running. */
70864 + if (ATE_ON(pAd))
70865 + return;
70866 +#endif // RALINK_ATE //
70867 +
70868 +
70869 + // record current BSS if network is connected.
70870 + // 2003-2-13 do not include current IBSS if this is the only STA in this IBSS.
70871 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
70872 + {
70873 + BssIdx = BssSsidTableSearch(&pAd->ScanTab, pAd->CommonCfg.Bssid, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen, pAd->CommonCfg.Channel);
70874 + if (BssIdx != BSS_NOT_FOUND)
70875 + {
70876 + NdisMoveMemory(&CurrBss, &pAd->ScanTab.BssEntry[BssIdx], sizeof(BSS_ENTRY));
70877 + }
70878 + }
70879 +
70880 + // clean up previous SCAN result, add current BSS back to table if any
70881 + BssTableInit(&pAd->ScanTab);
70882 + if (BssIdx != BSS_NOT_FOUND)
70883 + {
70884 + // DDK Note: If the NIC is associated with a particular BSSID and SSID
70885 + // that are not contained in the list of BSSIDs generated by this scan, the
70886 + // BSSID description of the currently associated BSSID and SSID should be
70887 + // appended to the list of BSSIDs in the NIC's database.
70888 + // To ensure this, we append this BSS as the first entry in SCAN result
70889 + NdisMoveMemory(&pAd->ScanTab.BssEntry[0], &CurrBss, sizeof(BSS_ENTRY));
70890 + pAd->ScanTab.BssNr = 1;
70891 + }
70892 +
70893 + ScanParmFill(pAd, &ScanReq, "", 0, BSS_ANY, SCAN_ACTIVE);
70894 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ,
70895 + sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
70896 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
70897 +}
70898 +
70899 +/*
70900 + ==========================================================================
70901 + Description:
70902 + Before calling this routine, user desired SSID should already been
70903 + recorded in CommonCfg.Ssid[]
70904 + IRQL = DISPATCH_LEVEL
70905 +
70906 + ==========================================================================
70907 +*/
70908 +VOID CntlOidSsidProc(
70909 + IN PRTMP_ADAPTER pAd,
70910 + IN MLME_QUEUE_ELEM * Elem)
70911 +{
70912 + PNDIS_802_11_SSID pOidSsid = (NDIS_802_11_SSID *)Elem->Msg;
70913 + MLME_DISASSOC_REQ_STRUCT DisassocReq;
70914 + ULONG Now;
70915 +
70916 + // Step 1. record the desired user settings to MlmeAux
70917 + NdisZeroMemory(pAd->MlmeAux.Ssid, MAX_LEN_OF_SSID);
70918 + NdisMoveMemory(pAd->MlmeAux.Ssid, pOidSsid->Ssid, pOidSsid->SsidLength);
70919 + pAd->MlmeAux.SsidLen = (UCHAR)pOidSsid->SsidLength;
70920 + NdisZeroMemory(pAd->MlmeAux.Bssid, MAC_ADDR_LEN);
70921 + pAd->MlmeAux.BssType = pAd->StaCfg.BssType;
70922 +
70923 +
70924 + //
70925 + // Update Reconnect Ssid, that user desired to connect.
70926 + //
70927 + NdisZeroMemory(pAd->MlmeAux.AutoReconnectSsid, MAX_LEN_OF_SSID);
70928 + NdisMoveMemory(pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen);
70929 + pAd->MlmeAux.AutoReconnectSsidLen = pAd->MlmeAux.SsidLen;
70930 +
70931 + // step 2. find all matching BSS in the lastest SCAN result (inBssTab)
70932 + // & log them into MlmeAux.SsidBssTab for later-on iteration. Sort by RSSI order
70933 + BssTableSsidSort(pAd, &pAd->MlmeAux.SsidBssTab, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen);
70934 +
70935 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():CNTL - %d BSS of %d BSS match the desire (%d)SSID - %s\n",
70936 + pAd->MlmeAux.SsidBssTab.BssNr, pAd->ScanTab.BssNr, pAd->MlmeAux.SsidLen, pAd->MlmeAux.Ssid));
70937 + NdisGetSystemUpTime(&Now);
70938 +
70939 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) &&
70940 + (pAd->CommonCfg.SsidLen == pAd->MlmeAux.SsidBssTab.BssEntry[0].SsidLen) &&
70941 + NdisEqualMemory(pAd->CommonCfg.Ssid, pAd->MlmeAux.SsidBssTab.BssEntry[0].Ssid, pAd->CommonCfg.SsidLen) &&
70942 + MAC_ADDR_EQUAL(pAd->CommonCfg.Bssid, pAd->MlmeAux.SsidBssTab.BssEntry[0].Bssid))
70943 + {
70944 + // Case 1. already connected with an AP who has the desired SSID
70945 + // with highest RSSI
70946 +
70947 + // Add checking Mode "LEAP" for CCX 1.0
70948 + if (((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) ||
70949 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) ||
70950 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) ||
70951 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)
70952 +#ifdef LEAP_SUPPORT
70953 + || (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
70954 +#endif // LEAP_SUPPORT //
70955 + ) &&
70956 + (pAd->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED))
70957 + {
70958 + // case 1.1 For WPA, WPA-PSK, if the 1x port is not secured, we have to redo
70959 + // connection process
70960 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():CNTL - disassociate with current AP...\n"));
70961 + DisassocParmFill(pAd, &DisassocReq, pAd->CommonCfg.Bssid, REASON_DISASSOC_STA_LEAVING);
70962 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_DISASSOC_REQ,
70963 + sizeof(MLME_DISASSOC_REQ_STRUCT), &DisassocReq);
70964 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_DISASSOC;
70965 + }
70966 + else if (pAd->bConfigChanged == TRUE)
70967 + {
70968 + // case 1.2 Important Config has changed, we have to reconnect to the same AP
70969 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():CNTL - disassociate with current AP Because config changed...\n"));
70970 + DisassocParmFill(pAd, &DisassocReq, pAd->CommonCfg.Bssid, REASON_DISASSOC_STA_LEAVING);
70971 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_DISASSOC_REQ,
70972 + sizeof(MLME_DISASSOC_REQ_STRUCT), &DisassocReq);
70973 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_DISASSOC;
70974 + }
70975 + else
70976 + {
70977 + // case 1.3. already connected to the SSID with highest RSSI.
70978 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():CNTL - already with this BSSID. ignore this SET_SSID request\n"));
70979 + //
70980 + // (HCT 12.1) 1c_wlan_mediaevents required
70981 + // media connect events are indicated when associating with the same AP
70982 + //
70983 + if (INFRA_ON(pAd))
70984 + {
70985 + //
70986 + // Since MediaState already is NdisMediaStateConnected
70987 + // We just indicate the connect event again to meet the WHQL required.
70988 + //
70989 + pAd->IndicateMediaState = NdisMediaStateConnected;
70990 + RTMP_IndicateMediaState(pAd);
70991 + pAd->ExtraInfo = GENERAL_LINK_UP; // Update extra information to link is up
70992 + }
70993 +
70994 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
70995 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
70996 + {
70997 + union iwreq_data wrqu;
70998 +
70999 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
71000 + memcpy(wrqu.ap_addr.sa_data, pAd->MlmeAux.Bssid, MAC_ADDR_LEN);
71001 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
71002 +
71003 + }
71004 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
71005 + }
71006 + }
71007 + else if (INFRA_ON(pAd))
71008 + {
71009 + //
71010 + // For RT61
71011 + // [88888] OID_802_11_SSID should have returned NDTEST_WEP_AP2(Returned: )
71012 + // RT61 may lost SSID, and not connect to NDTEST_WEP_AP2 and will connect to NDTEST_WEP_AP2 by Autoreconnect
71013 + // But media status is connected, so the SSID not report correctly.
71014 + //
71015 + if (!SSID_EQUAL(pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen))
71016 + {
71017 + //
71018 + // Different SSID means not Roaming case, so we let LinkDown() to Indicate a disconnect event.
71019 + //
71020 + pAd->MlmeAux.CurrReqIsFromNdis = TRUE;
71021 + }
71022 + // case 2. active INFRA association existent
71023 + // roaming is done within miniport driver, nothing to do with configuration
71024 + // utility. so upon a new SET(OID_802_11_SSID) is received, we just
71025 + // disassociate with the current associated AP,
71026 + // then perform a new association with this new SSID, no matter the
71027 + // new/old SSID are the same or not.
71028 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():CNTL - disassociate with current AP...\n"));
71029 + DisassocParmFill(pAd, &DisassocReq, pAd->CommonCfg.Bssid, REASON_DISASSOC_STA_LEAVING);
71030 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_DISASSOC_REQ,
71031 + sizeof(MLME_DISASSOC_REQ_STRUCT), &DisassocReq);
71032 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_DISASSOC;
71033 + }
71034 + else
71035 + {
71036 + if (ADHOC_ON(pAd))
71037 + {
71038 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():CNTL - drop current ADHOC\n"));
71039 + LinkDown(pAd, FALSE);
71040 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
71041 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
71042 + RTMP_IndicateMediaState(pAd);
71043 + pAd->ExtraInfo = GENERAL_LINK_DOWN;
71044 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():NDIS_STATUS_MEDIA_DISCONNECT Event C!\n"));
71045 + }
71046 +
71047 + if ((pAd->MlmeAux.SsidBssTab.BssNr == 0) &&
71048 + (pAd->StaCfg.bAutoReconnect == TRUE) &&
71049 + (pAd->MlmeAux.BssType == BSS_INFRA) &&
71050 + (MlmeValidateSSID(pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen) == TRUE)
71051 + )
71052 + {
71053 + MLME_SCAN_REQ_STRUCT ScanReq;
71054 +
71055 + DBGPRINT(RT_DEBUG_TRACE, ("CntlOidSsidProc():CNTL - No matching BSS, start a new scan\n"));
71056 + ScanParmFill(pAd, &ScanReq, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen, BSS_ANY, SCAN_ACTIVE);
71057 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_SCAN_REQ, sizeof(MLME_SCAN_REQ_STRUCT), &ScanReq);
71058 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_LIST_SCAN;
71059 + // Reset Missed scan number
71060 + pAd->StaCfg.LastScanTime = Now;
71061 + }
71062 + else
71063 + {
71064 + pAd->MlmeAux.BssIdx = 0;
71065 + IterateOnBssTab(pAd);
71066 + }
71067 + }
71068 +}
71069 +
71070 +
71071 +/*
71072 + ==========================================================================
71073 + Description:
71074 +
71075 + IRQL = DISPATCH_LEVEL
71076 +
71077 + ==========================================================================
71078 +*/
71079 +VOID CntlOidRTBssidProc(
71080 + IN PRTMP_ADAPTER pAd,
71081 + IN MLME_QUEUE_ELEM * Elem)
71082 +{
71083 + ULONG BssIdx;
71084 + PUCHAR pOidBssid = (PUCHAR)Elem->Msg;
71085 + MLME_DISASSOC_REQ_STRUCT DisassocReq;
71086 + MLME_JOIN_REQ_STRUCT JoinReq;
71087 +
71088 +#ifdef RALINK_ATE
71089 +/* No need to perform this routine when ATE is running. */
71090 + if (ATE_ON(pAd))
71091 + return;
71092 +#endif // RALINK_ATE //
71093 +
71094 + // record user desired settings
71095 + COPY_MAC_ADDR(pAd->MlmeAux.Bssid, pOidBssid);
71096 + pAd->MlmeAux.BssType = pAd->StaCfg.BssType;
71097 +
71098 + //
71099 + // Update Reconnect Ssid, that user desired to connect.
71100 + //
71101 + NdisZeroMemory(pAd->MlmeAux.AutoReconnectSsid, MAX_LEN_OF_SSID);
71102 + pAd->MlmeAux.AutoReconnectSsidLen = pAd->MlmeAux.SsidLen;
71103 + NdisMoveMemory(pAd->MlmeAux.AutoReconnectSsid, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen);
71104 +
71105 + // find the desired BSS in the latest SCAN result table
71106 + BssIdx = BssTableSearch(&pAd->ScanTab, pOidBssid, pAd->MlmeAux.Channel);
71107 + if (BssIdx == BSS_NOT_FOUND)
71108 + {
71109 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - BSSID not found. reply NDIS_STATUS_NOT_ACCEPTED\n"));
71110 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71111 + return;
71112 + }
71113 +
71114 + // copy the matched BSS entry from ScanTab to MlmeAux.SsidBssTab. Why?
71115 + // Because we need this entry to become the JOIN target in later on SYNC state machine
71116 + pAd->MlmeAux.BssIdx = 0;
71117 + pAd->MlmeAux.SsidBssTab.BssNr = 1;
71118 + NdisMoveMemory(&pAd->MlmeAux.SsidBssTab.BssEntry[0], &pAd->ScanTab.BssEntry[BssIdx], sizeof(BSS_ENTRY));
71119 +
71120 + // 2002-11-26 skip the following checking. i.e. if user wants to re-connect to same AP
71121 + // we just follow normal procedure. The reason of user doing this may because he/she changed
71122 + // AP to another channel, but we still received BEACON from it thus don't claim Link Down.
71123 + // Since user knows he's changed AP channel, he'll re-connect again. By skipping the following
71124 + // checking, we'll disassociate then re-do normal association with this AP at the new channel.
71125 + // 2003-1-6 Re-enable this feature based on microsoft requirement which prefer not to re-do
71126 + // connection when setting the same BSSID.
71127 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) &&
71128 + MAC_ADDR_EQUAL(pAd->CommonCfg.Bssid, pOidBssid))
71129 + {
71130 + // already connected to the same BSSID, go back to idle state directly
71131 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - already in this BSSID. ignore this SET_BSSID request\n"));
71132 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71133 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
71134 + {
71135 + union iwreq_data wrqu;
71136 +
71137 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
71138 + memcpy(wrqu.ap_addr.sa_data, pAd->MlmeAux.Bssid, MAC_ADDR_LEN);
71139 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
71140 +
71141 + }
71142 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
71143 + }
71144 + else
71145 + {
71146 + if (INFRA_ON(pAd))
71147 + {
71148 + // disassoc from current AP first
71149 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - disassociate with current AP ...\n"));
71150 + DisassocParmFill(pAd, &DisassocReq, pAd->CommonCfg.Bssid, REASON_DISASSOC_STA_LEAVING);
71151 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_DISASSOC_REQ,
71152 + sizeof(MLME_DISASSOC_REQ_STRUCT), &DisassocReq);
71153 +
71154 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_DISASSOC;
71155 + }
71156 + else
71157 + {
71158 + if (ADHOC_ON(pAd))
71159 + {
71160 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - drop current ADHOC\n"));
71161 + LinkDown(pAd, FALSE);
71162 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
71163 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
71164 + RTMP_IndicateMediaState(pAd);
71165 + pAd->ExtraInfo = GENERAL_LINK_DOWN;
71166 + DBGPRINT(RT_DEBUG_TRACE, ("NDIS_STATUS_MEDIA_DISCONNECT Event C!\n"));
71167 + }
71168 +
71169 + // Change the wepstatus to original wepstatus
71170 + pAd->StaCfg.WepStatus = pAd->StaCfg.OrigWepStatus;
71171 + pAd->StaCfg.PairCipher = pAd->StaCfg.OrigWepStatus;
71172 + pAd->StaCfg.GroupCipher = pAd->StaCfg.OrigWepStatus;
71173 +
71174 + // Check cipher suite, AP must have more secured cipher than station setting
71175 + // Set the Pairwise and Group cipher to match the intended AP setting
71176 + // We can only connect to AP with less secured cipher setting
71177 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK))
71178 + {
71179 + pAd->StaCfg.GroupCipher = pAd->ScanTab.BssEntry[BssIdx].WPA.GroupCipher;
71180 +
71181 + if (pAd->StaCfg.WepStatus == pAd->ScanTab.BssEntry[BssIdx].WPA.PairCipher)
71182 + pAd->StaCfg.PairCipher = pAd->ScanTab.BssEntry[BssIdx].WPA.PairCipher;
71183 + else if (pAd->ScanTab.BssEntry[BssIdx].WPA.PairCipherAux != Ndis802_11WEPDisabled)
71184 + pAd->StaCfg.PairCipher = pAd->ScanTab.BssEntry[BssIdx].WPA.PairCipherAux;
71185 + else // There is no PairCipher Aux, downgrade our capability to TKIP
71186 + pAd->StaCfg.PairCipher = Ndis802_11Encryption2Enabled;
71187 + }
71188 + else if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
71189 + {
71190 + pAd->StaCfg.GroupCipher = pAd->ScanTab.BssEntry[BssIdx].WPA2.GroupCipher;
71191 +
71192 + if (pAd->StaCfg.WepStatus == pAd->ScanTab.BssEntry[BssIdx].WPA2.PairCipher)
71193 + pAd->StaCfg.PairCipher = pAd->ScanTab.BssEntry[BssIdx].WPA2.PairCipher;
71194 + else if (pAd->ScanTab.BssEntry[BssIdx].WPA2.PairCipherAux != Ndis802_11WEPDisabled)
71195 + pAd->StaCfg.PairCipher = pAd->ScanTab.BssEntry[BssIdx].WPA2.PairCipherAux;
71196 + else // There is no PairCipher Aux, downgrade our capability to TKIP
71197 + pAd->StaCfg.PairCipher = Ndis802_11Encryption2Enabled;
71198 +
71199 + // RSN capability
71200 + pAd->StaCfg.RsnCapability = pAd->ScanTab.BssEntry[BssIdx].WPA2.RsnCapability;
71201 + }
71202 +
71203 + // Set Mix cipher flag
71204 + pAd->StaCfg.bMixCipher = (pAd->StaCfg.PairCipher == pAd->StaCfg.GroupCipher) ? FALSE : TRUE;
71205 + if (pAd->StaCfg.bMixCipher == TRUE)
71206 + {
71207 + // If mix cipher, re-build RSNIE
71208 + RTMPMakeRSNIE(pAd, pAd->StaCfg.AuthMode, pAd->StaCfg.WepStatus, 0);
71209 + }
71210 + // No active association, join the BSS immediately
71211 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - joining %02x:%02x:%02x:%02x:%02x:%02x ...\n",
71212 + pOidBssid[0],pOidBssid[1],pOidBssid[2],pOidBssid[3],pOidBssid[4],pOidBssid[5]));
71213 +
71214 + JoinParmFill(pAd, &JoinReq, pAd->MlmeAux.BssIdx);
71215 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_JOIN_REQ, sizeof(MLME_JOIN_REQ_STRUCT), &JoinReq);
71216 +
71217 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_JOIN;
71218 + }
71219 + }
71220 +}
71221 +
71222 +// Roaming is the only external request triggering CNTL state machine
71223 +// despite of other "SET OID" operation. All "SET OID" related oerations
71224 +// happen in sequence, because no other SET OID will be sent to this device
71225 +// until the the previous SET operation is complete (successful o failed).
71226 +// So, how do we quarantee this ROAMING request won't corrupt other "SET OID"?
71227 +// or been corrupted by other "SET OID"?
71228 +//
71229 +// IRQL = DISPATCH_LEVEL
71230 +VOID CntlMlmeRoamingProc(
71231 + IN PRTMP_ADAPTER pAd,
71232 + IN MLME_QUEUE_ELEM *Elem)
71233 +{
71234 + // TODO:
71235 + // AP in different channel may show lower RSSI than actual value??
71236 + // should we add a weighting factor to compensate it?
71237 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - Roaming in MlmeAux.RoamTab...\n"));
71238 +
71239 + NdisMoveMemory(&pAd->MlmeAux.SsidBssTab, &pAd->MlmeAux.RoamTab, sizeof(pAd->MlmeAux.RoamTab));
71240 + pAd->MlmeAux.SsidBssTab.BssNr = pAd->MlmeAux.RoamTab.BssNr;
71241 +
71242 + BssTableSortByRssi(&pAd->MlmeAux.SsidBssTab);
71243 + pAd->MlmeAux.BssIdx = 0;
71244 + IterateOnBssTab(pAd);
71245 +}
71246 +
71247 +#ifdef QOS_DLS_SUPPORT
71248 +/*
71249 + ==========================================================================
71250 + Description:
71251 +
71252 + IRQL = DISPATCH_LEVEL
71253 +
71254 + ==========================================================================
71255 +*/
71256 +VOID CntlOidDLSSetupProc(
71257 + IN PRTMP_ADAPTER pAd,
71258 + IN MLME_QUEUE_ELEM *Elem)
71259 +{
71260 + PRT_802_11_DLS pDLS = (PRT_802_11_DLS)Elem->Msg;
71261 + MLME_DLS_REQ_STRUCT MlmeDlsReq;
71262 + INT i;
71263 + USHORT reason = REASON_UNSPECIFY;
71264 +
71265 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - (OID set %02x:%02x:%02x:%02x:%02x:%02x with Valid=%d, Status=%d, TimeOut=%d, CountDownTimer=%d)\n",
71266 + pDLS->MacAddr[0], pDLS->MacAddr[1], pDLS->MacAddr[2], pDLS->MacAddr[3], pDLS->MacAddr[4], pDLS->MacAddr[5],
71267 + pDLS->Valid, pDLS->Status, pDLS->TimeOut, pDLS->CountDownTimer));
71268 +
71269 + if (!pAd->CommonCfg.bDLSCapable)
71270 + return;
71271 +
71272 + // DLS will not be supported when Adhoc mode
71273 + if (INFRA_ON(pAd))
71274 + {
71275 + for (i = 0; i < MAX_NUM_OF_DLS_ENTRY; i++)
71276 + {
71277 + if (pDLS->Valid && pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH) &&
71278 + (pDLS->TimeOut == pAd->StaCfg.DLSEntry[i].TimeOut) && MAC_ADDR_EQUAL(pDLS->MacAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
71279 + {
71280 + // 1. Same setting, just drop it
71281 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - setting unchanged\n"));
71282 + break;
71283 + }
71284 + else if (!pDLS->Valid && pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH) &&
71285 + MAC_ADDR_EQUAL(pDLS->MacAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
71286 + {
71287 + // 2. Disable DLS link case, just tear down DLS link
71288 + reason = REASON_QOS_UNWANTED_MECHANISM;
71289 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
71290 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
71291 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
71292 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
71293 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - start tear down procedure\n"));
71294 + break;
71295 + }
71296 + else if ((i < MAX_NUM_OF_DLS_ENTRY) && pDLS->Valid && !pAd->StaCfg.DLSEntry[i].Valid)
71297 + {
71298 + // 3. Enable case, start DLS setup procedure
71299 + NdisMoveMemory(&pAd->StaCfg.DLSEntry[i], pDLS, sizeof(RT_802_11_DLS_UI));
71300 +
71301 + //Update countdown timer
71302 + pAd->StaCfg.DLSEntry[i].CountDownTimer = pAd->StaCfg.DLSEntry[i].TimeOut;
71303 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
71304 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_REQ, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
71305 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - DLS setup case\n"));
71306 + break;
71307 + }
71308 + else if ((i < MAX_NUM_OF_DLS_ENTRY) && pDLS->Valid && pAd->StaCfg.DLSEntry[i].Valid &&
71309 + (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH) && !MAC_ADDR_EQUAL(pDLS->MacAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
71310 + {
71311 + // 4. update mac case, tear down old DLS and setup new DLS
71312 + reason = REASON_QOS_UNWANTED_MECHANISM;
71313 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
71314 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
71315 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
71316 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
71317 + NdisMoveMemory(&pAd->StaCfg.DLSEntry[i], pDLS, sizeof(RT_802_11_DLS_UI));
71318 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
71319 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_REQ, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
71320 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - DLS tear down and restart case\n"));
71321 + break;
71322 + }
71323 + else if (pDLS->Valid && pAd->StaCfg.DLSEntry[i].Valid &&
71324 + MAC_ADDR_EQUAL(pDLS->MacAddr, pAd->StaCfg.DLSEntry[i].MacAddr) && (pAd->StaCfg.DLSEntry[i].TimeOut != pDLS->TimeOut))
71325 + {
71326 + // 5. update timeout case, start DLS setup procedure (no tear down)
71327 + pAd->StaCfg.DLSEntry[i].TimeOut = pDLS->TimeOut;
71328 + //Update countdown timer
71329 + pAd->StaCfg.DLSEntry[i].CountDownTimer = pAd->StaCfg.DLSEntry[i].TimeOut;
71330 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
71331 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_REQ, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
71332 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - DLS update timeout case\n"));
71333 + break;
71334 + }
71335 + else if (pDLS->Valid && pAd->StaCfg.DLSEntry[i].Valid &&
71336 + (pAd->StaCfg.DLSEntry[i].Status != DLS_FINISH) && MAC_ADDR_EQUAL(pDLS->MacAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
71337 + {
71338 + // 6. re-setup case, start DLS setup procedure (no tear down)
71339 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
71340 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_REQ, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
71341 + DBGPRINT(RT_DEBUG_TRACE,("CNTL - DLS retry setup procedure\n"));
71342 + break;
71343 + }
71344 + else
71345 + {
71346 + DBGPRINT(RT_DEBUG_WARN,("CNTL - DLS not changed in entry - %d - Valid=%d, Status=%d, TimeOut=%d\n",
71347 + i, pAd->StaCfg.DLSEntry[i].Valid, pAd->StaCfg.DLSEntry[i].Status, pAd->StaCfg.DLSEntry[i].TimeOut));
71348 + }
71349 + }
71350 + }
71351 +}
71352 +#endif // QOS_DLS_SUPPORT //
71353 +
71354 +/*
71355 + ==========================================================================
71356 + Description:
71357 +
71358 + IRQL = DISPATCH_LEVEL
71359 +
71360 + ==========================================================================
71361 +*/
71362 +VOID CntlWaitDisassocProc(
71363 + IN PRTMP_ADAPTER pAd,
71364 + IN MLME_QUEUE_ELEM *Elem)
71365 +{
71366 + MLME_START_REQ_STRUCT StartReq;
71367 +
71368 + if (Elem->MsgType == MT2_DISASSOC_CONF)
71369 + {
71370 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Dis-associate successful\n"));
71371 +
71372 + if (pAd->CommonCfg.bWirelessEvent)
71373 + {
71374 + RTMPSendWirelessEvent(pAd, IW_DISASSOC_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
71375 + }
71376 +
71377 + LinkDown(pAd, FALSE);
71378 +
71379 + // case 1. no matching BSS, and user wants ADHOC, so we just start a new one
71380 + if ((pAd->MlmeAux.SsidBssTab.BssNr==0) && (pAd->StaCfg.BssType == BSS_ADHOC))
71381 + {
71382 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - No matching BSS, start a new ADHOC (Ssid=%s)...\n",pAd->MlmeAux.Ssid));
71383 + StartParmFill(pAd, &StartReq, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen);
71384 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_START_REQ, sizeof(MLME_START_REQ_STRUCT), &StartReq);
71385 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_START;
71386 + }
71387 + // case 2. try each matched BSS
71388 + else
71389 + {
71390 + pAd->MlmeAux.BssIdx = 0;
71391 +
71392 + IterateOnBssTab(pAd);
71393 + }
71394 + }
71395 +}
71396 +
71397 +/*
71398 + ==========================================================================
71399 + Description:
71400 +
71401 + IRQL = DISPATCH_LEVEL
71402 +
71403 + ==========================================================================
71404 +*/
71405 +VOID CntlWaitJoinProc(
71406 + IN PRTMP_ADAPTER pAd,
71407 + IN MLME_QUEUE_ELEM *Elem)
71408 +{
71409 + USHORT Reason;
71410 + MLME_AUTH_REQ_STRUCT AuthReq;
71411 +
71412 + if (Elem->MsgType == MT2_JOIN_CONF)
71413 + {
71414 + NdisMoveMemory(&Reason, Elem->Msg, sizeof(USHORT));
71415 + if (Reason == MLME_SUCCESS)
71416 + {
71417 + // 1. joined an IBSS, we are pretty much done here
71418 + if (pAd->MlmeAux.BssType == BSS_ADHOC)
71419 + {
71420 + //
71421 + // 5G bands rules of Japan:
71422 + // Ad hoc must be disabled in W53(ch52,56,60,64) channels.
71423 + //
71424 + if ( (pAd->CommonCfg.bIEEE80211H == 1) &&
71425 + RadarChannelCheck(pAd, pAd->CommonCfg.Channel)
71426 + )
71427 + {
71428 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71429 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Channel=%d, Join adhoc on W53(52,56,60,64) Channels are not accepted\n", pAd->CommonCfg.Channel));
71430 + return;
71431 + }
71432 +
71433 + LinkUp(pAd, BSS_ADHOC);
71434 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71435 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - join the IBSS = %02x:%02x:%02x:%02x:%02x:%02x ...\n",
71436 + pAd->CommonCfg.Bssid[0],pAd->CommonCfg.Bssid[1],pAd->CommonCfg.Bssid[2],
71437 + pAd->CommonCfg.Bssid[3],pAd->CommonCfg.Bssid[4],pAd->CommonCfg.Bssid[5]));
71438 +
71439 + pAd->IndicateMediaState = NdisMediaStateConnected;
71440 + pAd->ExtraInfo = GENERAL_LINK_UP;
71441 + }
71442 + // 2. joined a new INFRA network, start from authentication
71443 + else
71444 + {
71445 +#ifdef LEAP_SUPPORT
71446 + // Add AuthMode "LEAP" for CCX 1.X
71447 + if (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
71448 + {
71449 + AuthParmFill(pAd, &AuthReq, pAd->MlmeAux.Bssid, CISCO_AuthModeLEAP);
71450 + }
71451 + else
71452 +#endif // LEAP_SUPPORT //
71453 + {
71454 + // either Ndis802_11AuthModeShared or Ndis802_11AuthModeAutoSwitch, try shared key first
71455 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeShared) ||
71456 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeAutoSwitch))
71457 + {
71458 + AuthParmFill(pAd, &AuthReq, pAd->MlmeAux.Bssid, Ndis802_11AuthModeShared);
71459 + }
71460 + else
71461 + {
71462 + AuthParmFill(pAd, &AuthReq, pAd->MlmeAux.Bssid, Ndis802_11AuthModeOpen);
71463 + }
71464 + }
71465 + MlmeEnqueue(pAd, AUTH_STATE_MACHINE, MT2_MLME_AUTH_REQ,
71466 + sizeof(MLME_AUTH_REQ_STRUCT), &AuthReq);
71467 +
71468 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_AUTH;
71469 + }
71470 + }
71471 + else
71472 + {
71473 + // 3. failed, try next BSS
71474 + pAd->MlmeAux.BssIdx++;
71475 + IterateOnBssTab(pAd);
71476 + }
71477 + }
71478 +}
71479 +
71480 +
71481 +/*
71482 + ==========================================================================
71483 + Description:
71484 +
71485 + IRQL = DISPATCH_LEVEL
71486 +
71487 + ==========================================================================
71488 +*/
71489 +VOID CntlWaitStartProc(
71490 + IN PRTMP_ADAPTER pAd,
71491 + IN MLME_QUEUE_ELEM *Elem)
71492 +{
71493 + USHORT Result;
71494 +
71495 + if (Elem->MsgType == MT2_START_CONF)
71496 + {
71497 + NdisMoveMemory(&Result, Elem->Msg, sizeof(USHORT));
71498 + if (Result == MLME_SUCCESS)
71499 + {
71500 + //
71501 + // 5G bands rules of Japan:
71502 + // Ad hoc must be disabled in W53(ch52,56,60,64) channels.
71503 + //
71504 + if ( (pAd->CommonCfg.bIEEE80211H == 1) &&
71505 + RadarChannelCheck(pAd, pAd->CommonCfg.Channel)
71506 + )
71507 + {
71508 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71509 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Channel=%d, Start adhoc on W53(52,56,60,64) Channels are not accepted\n", pAd->CommonCfg.Channel));
71510 + return;
71511 + }
71512 +#ifdef DOT11_N_SUPPORT
71513 + if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED)
71514 + {
71515 + N_ChannelCheck(pAd);
71516 + SetCommonHT(pAd);
71517 + NdisMoveMemory(&pAd->MlmeAux.AddHtInfo, &pAd->CommonCfg.AddHTInfo, sizeof(ADD_HT_INFO_IE));
71518 + RTMPCheckHt(pAd, BSSID_WCID, &pAd->CommonCfg.HtCapability, &pAd->CommonCfg.AddHTInfo);
71519 + pAd->StaActive.SupportedPhyInfo.bHtEnable = TRUE;
71520 + NdisZeroMemory(&pAd->StaActive.SupportedPhyInfo.MCSSet[0], 16);
71521 + NdisMoveMemory(&pAd->StaActive.SupportedPhyInfo.MCSSet[0], &pAd->CommonCfg.HtCapability.MCSSet[0], 16);
71522 + COPY_HTSETTINGS_FROM_MLME_AUX_TO_ACTIVE_CFG(pAd);
71523 +
71524 + if ((pAd->CommonCfg.HtCapability.HtCapInfo.ChannelWidth == BW_40) &&
71525 + (pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset == EXTCHA_ABOVE))
71526 + {
71527 + pAd->MlmeAux.CentralChannel = pAd->CommonCfg.Channel + 2;
71528 + }
71529 + else if ((pAd->CommonCfg.HtCapability.HtCapInfo.ChannelWidth == BW_40) &&
71530 + (pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset == EXTCHA_BELOW))
71531 + {
71532 + pAd->MlmeAux.CentralChannel = pAd->CommonCfg.Channel - 2;
71533 + }
71534 + }
71535 + else
71536 +#endif // DOT11_N_SUPPORT //
71537 + {
71538 + pAd->StaActive.SupportedPhyInfo.bHtEnable = FALSE;
71539 + }
71540 + LinkUp(pAd, BSS_ADHOC);
71541 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71542 + // Before send beacon, driver need do radar detection
71543 + if ((pAd->CommonCfg.Channel > 14 )
71544 + && (pAd->CommonCfg.bIEEE80211H == 1)
71545 + && RadarChannelCheck(pAd, pAd->CommonCfg.Channel))
71546 + {
71547 + pAd->CommonCfg.RadarDetect.RDMode = RD_SILENCE_MODE;
71548 + pAd->CommonCfg.RadarDetect.RDCount = 0;
71549 +#ifdef DFS_SUPPORT
71550 + BbpRadarDetectionStart(pAd);
71551 +#endif // DFS_SUPPORT //
71552 + }
71553 +
71554 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - start a new IBSS = %02x:%02x:%02x:%02x:%02x:%02x ...\n",
71555 + pAd->CommonCfg.Bssid[0],pAd->CommonCfg.Bssid[1],pAd->CommonCfg.Bssid[2],
71556 + pAd->CommonCfg.Bssid[3],pAd->CommonCfg.Bssid[4],pAd->CommonCfg.Bssid[5]));
71557 + }
71558 + else
71559 + {
71560 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Start IBSS fail. BUG!!!!!\n"));
71561 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71562 + }
71563 + }
71564 +}
71565 +
71566 +/*
71567 + ==========================================================================
71568 + Description:
71569 +
71570 + IRQL = DISPATCH_LEVEL
71571 +
71572 + ==========================================================================
71573 +*/
71574 +VOID CntlWaitAuthProc(
71575 + IN PRTMP_ADAPTER pAd,
71576 + IN MLME_QUEUE_ELEM *Elem)
71577 +{
71578 + USHORT Reason;
71579 + MLME_ASSOC_REQ_STRUCT AssocReq;
71580 + MLME_AUTH_REQ_STRUCT AuthReq;
71581 +
71582 + if (Elem->MsgType == MT2_AUTH_CONF)
71583 + {
71584 + NdisMoveMemory(&Reason, Elem->Msg, sizeof(USHORT));
71585 + if (Reason == MLME_SUCCESS)
71586 + {
71587 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - AUTH OK\n"));
71588 + AssocParmFill(pAd, &AssocReq, pAd->MlmeAux.Bssid, pAd->MlmeAux.CapabilityInfo,
71589 + ASSOC_TIMEOUT, pAd->StaCfg.DefaultListenCount);
71590 +
71591 +#ifdef LEAP_SUPPORT
71592 + //
71593 + // Cisco Leap CCKM supported Re-association.
71594 + //
71595 + if (LEAP_CCKM_ON(pAd) && (pAd->StaCfg.CCKMLinkUpFlag == TRUE))
71596 + {
71597 + //if CCKM is turn on , that's mean Fast Reauthentication
71598 + //Use CCKM Reassociation instead of normal association for Fast Roaming.
71599 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_REASSOC_REQ,
71600 + sizeof(MLME_ASSOC_REQ_STRUCT), &AssocReq);
71601 +
71602 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_REASSOC;
71603 + }
71604 + else
71605 +#endif // LEAP_SUPPORT //
71606 + {
71607 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_ASSOC_REQ,
71608 + sizeof(MLME_ASSOC_REQ_STRUCT), &AssocReq);
71609 +
71610 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_ASSOC;
71611 + }
71612 + }
71613 + else
71614 + {
71615 + // This fail may because of the AP already keep us in its MAC table without
71616 + // ageing-out. The previous authentication attempt must have let it remove us.
71617 + // so try Authentication again may help. For D-Link DWL-900AP+ compatibility.
71618 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - AUTH FAIL, try again...\n"));
71619 +#ifdef LEAP_SUPPORT
71620 + //Add AuthMode "LEAP" for CCX 1.X
71621 + if (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
71622 + {
71623 + AuthParmFill(pAd, &AuthReq, pAd->MlmeAux.Bssid, CISCO_AuthModeLEAP);
71624 + }
71625 + else
71626 +#endif // LEAP_SUPPORT //
71627 + {
71628 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeShared) ||
71629 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeAutoSwitch))
71630 + {
71631 + // either Ndis802_11AuthModeShared or Ndis802_11AuthModeAutoSwitch, try shared key first
71632 + AuthParmFill(pAd, &AuthReq, pAd->MlmeAux.Bssid, Ndis802_11AuthModeShared);
71633 + }
71634 + else
71635 + {
71636 + AuthParmFill(pAd, &AuthReq, pAd->MlmeAux.Bssid, Ndis802_11AuthModeOpen);
71637 + }
71638 + }
71639 + MlmeEnqueue(pAd, AUTH_STATE_MACHINE, MT2_MLME_AUTH_REQ,
71640 + sizeof(MLME_AUTH_REQ_STRUCT), &AuthReq);
71641 +
71642 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_AUTH2;
71643 + }
71644 + }
71645 +}
71646 +
71647 +/*
71648 + ==========================================================================
71649 + Description:
71650 +
71651 + IRQL = DISPATCH_LEVEL
71652 +
71653 + ==========================================================================
71654 +*/
71655 +VOID CntlWaitAuthProc2(
71656 + IN PRTMP_ADAPTER pAd,
71657 + IN MLME_QUEUE_ELEM *Elem)
71658 +{
71659 + USHORT Reason;
71660 + MLME_ASSOC_REQ_STRUCT AssocReq;
71661 + MLME_AUTH_REQ_STRUCT AuthReq;
71662 +
71663 + if (Elem->MsgType == MT2_AUTH_CONF)
71664 + {
71665 + NdisMoveMemory(&Reason, Elem->Msg, sizeof(USHORT));
71666 + if (Reason == MLME_SUCCESS)
71667 + {
71668 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - AUTH OK\n"));
71669 + AssocParmFill(pAd, &AssocReq, pAd->MlmeAux.Bssid, pAd->MlmeAux.CapabilityInfo,
71670 + ASSOC_TIMEOUT, pAd->StaCfg.DefaultListenCount);
71671 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_ASSOC_REQ,
71672 + sizeof(MLME_ASSOC_REQ_STRUCT), &AssocReq);
71673 +
71674 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_ASSOC;
71675 + }
71676 + else
71677 + {
71678 +#ifdef LEAP_SUPPORT
71679 + // Process LEAP first, since it use different control variable
71680 + // We don't want to affect other poven operation
71681 + if (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
71682 + {
71683 + // LEAP Auth not success, try next BSS
71684 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - *LEAP* AUTH FAIL, give up; try next BSS\n"));
71685 + DBGPRINT(RT_DEBUG_TRACE, ("Total match BSSID [=%d]\n", pAd->MlmeAux.SsidBssTab.BssNr));
71686 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71687 + pAd->MlmeAux.BssIdx++;
71688 + IterateOnBssTab(pAd);
71689 + }
71690 + else
71691 +#endif // LEAP_SUPPORT //
71692 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeAutoSwitch) &&
71693 + (pAd->MlmeAux.Alg == Ndis802_11AuthModeShared))
71694 + {
71695 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - AUTH FAIL, try OPEN system...\n"));
71696 + AuthParmFill(pAd, &AuthReq, pAd->MlmeAux.Bssid, Ndis802_11AuthModeOpen);
71697 + MlmeEnqueue(pAd, AUTH_STATE_MACHINE, MT2_MLME_AUTH_REQ,
71698 + sizeof(MLME_AUTH_REQ_STRUCT), &AuthReq);
71699 +
71700 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_AUTH2;
71701 + }
71702 + else
71703 + {
71704 + // not success, try next BSS
71705 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - AUTH FAIL, give up; try next BSS\n"));
71706 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE; //???????
71707 + pAd->MlmeAux.BssIdx++;
71708 + IterateOnBssTab(pAd);
71709 + }
71710 + }
71711 + }
71712 +}
71713 +
71714 +/*
71715 + ==========================================================================
71716 + Description:
71717 +
71718 + IRQL = DISPATCH_LEVEL
71719 +
71720 + ==========================================================================
71721 +*/
71722 +VOID CntlWaitAssocProc(
71723 + IN PRTMP_ADAPTER pAd,
71724 + IN MLME_QUEUE_ELEM *Elem)
71725 +{
71726 + USHORT Reason;
71727 +
71728 + if (Elem->MsgType == MT2_ASSOC_CONF)
71729 + {
71730 + NdisMoveMemory(&Reason, Elem->Msg, sizeof(USHORT));
71731 + if (Reason == MLME_SUCCESS)
71732 + {
71733 + LinkUp(pAd, BSS_INFRA);
71734 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71735 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Association successful on BSS #%ld\n",pAd->MlmeAux.BssIdx));
71736 +
71737 + if (pAd->CommonCfg.bWirelessEvent)
71738 + {
71739 + RTMPSendWirelessEvent(pAd, IW_ASSOC_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
71740 + }
71741 + }
71742 + else
71743 + {
71744 + // not success, try next BSS
71745 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Association fails on BSS #%ld\n",pAd->MlmeAux.BssIdx));
71746 + pAd->MlmeAux.BssIdx++;
71747 + IterateOnBssTab(pAd);
71748 + }
71749 + }
71750 +}
71751 +
71752 +/*
71753 + ==========================================================================
71754 + Description:
71755 +
71756 + IRQL = DISPATCH_LEVEL
71757 +
71758 + ==========================================================================
71759 +*/
71760 +VOID CntlWaitReassocProc(
71761 + IN PRTMP_ADAPTER pAd,
71762 + IN MLME_QUEUE_ELEM *Elem)
71763 +{
71764 + USHORT Result;
71765 +
71766 + if (Elem->MsgType == MT2_REASSOC_CONF)
71767 + {
71768 + NdisMoveMemory(&Result, Elem->Msg, sizeof(USHORT));
71769 + if (Result == MLME_SUCCESS)
71770 + {
71771 + //
71772 + // NDIS requires a new Link UP indication but no Link Down for RE-ASSOC
71773 + //
71774 + LinkUp(pAd, BSS_INFRA);
71775 +
71776 + // send wireless event - for association
71777 + if (pAd->CommonCfg.bWirelessEvent)
71778 + RTMPSendWirelessEvent(pAd, IW_ASSOC_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
71779 +
71780 +
71781 +#ifdef LEAP_SUPPORT
71782 + if (LEAP_CCKM_ON(pAd))
71783 + {
71784 + STA_PORT_SECURED(pAd);
71785 + pAd->StaCfg.WpaState = SS_FINISH;
71786 + }
71787 +#endif // LEAP_SUPPORT //
71788 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
71789 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Re-assocition successful on BSS #%ld\n", pAd->MlmeAux.RoamIdx));
71790 + }
71791 + else
71792 + {
71793 + // reassoc failed, try to pick next BSS in the BSS Table
71794 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - Re-assocition fails on BSS #%ld\n", pAd->MlmeAux.RoamIdx));
71795 + pAd->MlmeAux.RoamIdx++;
71796 + IterateOnBssTab2(pAd);
71797 + }
71798 + }
71799 +}
71800 +
71801 +/*
71802 + ==========================================================================
71803 + Description:
71804 +
71805 + IRQL = DISPATCH_LEVEL
71806 +
71807 + ==========================================================================
71808 +*/
71809 +VOID LinkUp(
71810 + IN PRTMP_ADAPTER pAd,
71811 + IN UCHAR BssType)
71812 +{
71813 + ULONG Now;
71814 + UINT32 Data;
71815 + BOOLEAN Cancelled;
71816 + UCHAR Value = 0, idx;
71817 + MAC_TABLE_ENTRY *pEntry = NULL, *pCurrEntry;
71818 +
71819 + pEntry = &pAd->MacTab.Content[BSSID_WCID];
71820 +
71821 + //
71822 + // ASSOC - DisassocTimeoutAction
71823 + // CNTL - Dis-associate successful
71824 + // !!! LINK DOWN !!!
71825 + // [88888] OID_802_11_SSID should have returned NDTEST_WEP_AP2(Returned: )
71826 + //
71827 + // To prevent DisassocTimeoutAction to call Link down after we link up,
71828 + // cancel the DisassocTimer no matter what it start or not.
71829 + //
71830 + RTMPCancelTimer(&pAd->MlmeAux.DisassocTimer, &Cancelled);
71831 +
71832 + COPY_SETTINGS_FROM_MLME_AUX_TO_ACTIVE_CFG(pAd);
71833 +
71834 +#ifdef DOT11_N_SUPPORT
71835 + COPY_HTSETTINGS_FROM_MLME_AUX_TO_ACTIVE_CFG(pAd);
71836 +#endif // DOT11_N_SUPPORT //
71837 + // It's quite difficult to tell if a newly added KEY is WEP or CKIP until a new BSS
71838 + // is formed (either ASSOC/RE-ASSOC done or IBSS started. LinkUP should be a safe place
71839 + // to examine if cipher algorithm switching is required.
71840 + //rt2860b. Don't know why need this
71841 + SwitchBetweenWepAndCkip(pAd);
71842 +
71843 +#ifdef RT2860
71844 + // Before power save before link up function, We will force use 1R.
71845 + // So after link up, check Rx antenna # again.
71846 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &Value);
71847 + if(pAd->Antenna.field.RxPath == 3)
71848 + {
71849 + Value |= (0x10);
71850 + }
71851 + else if(pAd->Antenna.field.RxPath == 2)
71852 + {
71853 + Value |= (0x8);
71854 + }
71855 + else if(pAd->Antenna.field.RxPath == 1)
71856 + {
71857 + Value |= (0x0);
71858 + }
71859 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, Value);
71860 + pAd->StaCfg.BBPR3 = Value;
71861 +#endif // RT2860 //
71862 +
71863 + if (BssType == BSS_ADHOC)
71864 + {
71865 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_ADHOC_ON);
71866 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_INFRA_ON);
71867 +
71868 +#ifdef CARRIER_DETECTION_SUPPORT // Roger sync Carrier
71869 + // No carrier detection when adhoc
71870 + // CarrierDetectionStop(pAd);
71871 + pAd->CommonCfg.CarrierDetect.CD_State = CD_NORMAL;
71872 +#endif // CARRIER_DETECTION_SUPPORT //
71873 +
71874 + DBGPRINT(RT_DEBUG_TRACE, ("!!!Adhoc LINK UP !!! \n" ));
71875 + }
71876 + else
71877 + {
71878 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_INFRA_ON);
71879 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_ADHOC_ON);
71880 +
71881 + DBGPRINT(RT_DEBUG_TRACE, ("!!!Infra LINK UP !!! \n" ));
71882 + }
71883 +
71884 + // 3*3
71885 + // reset Tx beamforming bit
71886 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &Value);
71887 + Value &= (~0x01);
71888 + Value |= pAd->CommonCfg.RegTransmitSetting.field.TxBF;
71889 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, Value);
71890 +
71891 +#ifdef DOT11_N_SUPPORT
71892 + // Change to AP channel
71893 + if ((pAd->CommonCfg.CentralChannel > pAd->CommonCfg.Channel) && (pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth == BW_40))
71894 + {
71895 + // Must using 40MHz.
71896 + pAd->CommonCfg.BBPCurrentBW = BW_40;
71897 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
71898 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
71899 +
71900 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &Value);
71901 + Value &= (~0x18);
71902 + Value |= 0x10;
71903 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, Value);
71904 +
71905 + // RX : control channel at lower
71906 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &Value);
71907 + Value &= (~0x20);
71908 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, Value);
71909 +#ifdef RT2860
71910 + pAd->StaCfg.BBPR3 = Value;
71911 +#endif // RT2860 //
71912 +
71913 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Data);
71914 + Data &= 0xfffffffe;
71915 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Data);
71916 +
71917 + if (pAd->MACVersion == 0x28600100)
71918 + {
71919 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, 0x1A);
71920 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, 0x0A);
71921 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, 0x16);
71922 + DBGPRINT(RT_DEBUG_TRACE, ("!!!rt2860C !!! \n" ));
71923 + }
71924 +
71925 + DBGPRINT(RT_DEBUG_TRACE, ("!!!40MHz Lower LINK UP !!! Control Channel at Below. Central = %d \n", pAd->CommonCfg.CentralChannel ));
71926 + }
71927 + else if ((pAd->CommonCfg.CentralChannel < pAd->CommonCfg.Channel) && (pAd->MlmeAux.HtCapability.HtCapInfo.ChannelWidth == BW_40))
71928 + {
71929 + // Must using 40MHz.
71930 + pAd->CommonCfg.BBPCurrentBW = BW_40;
71931 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
71932 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
71933 +
71934 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &Value);
71935 + Value &= (~0x18);
71936 + Value |= 0x10;
71937 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, Value);
71938 +
71939 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Data);
71940 + Data |= 0x1;
71941 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Data);
71942 +
71943 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &Value);
71944 + Value |= (0x20);
71945 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, Value);
71946 +#ifdef RT2860
71947 + pAd->StaCfg.BBPR3 = Value;
71948 +#endif // RT2860 //
71949 +
71950 + if (pAd->MACVersion == 0x28600100)
71951 + {
71952 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, 0x1A);
71953 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, 0x0A);
71954 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, 0x16);
71955 + DBGPRINT(RT_DEBUG_TRACE, ("!!!rt2860C !!! \n" ));
71956 + }
71957 +
71958 + DBGPRINT(RT_DEBUG_TRACE, ("!!! 40MHz Upper LINK UP !!! Control Channel at UpperCentral = %d \n", pAd->CommonCfg.CentralChannel ));
71959 + }
71960 + else
71961 +#endif // DOT11_N_SUPPORT //
71962 + {
71963 + pAd->CommonCfg.BBPCurrentBW = BW_20;
71964 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel;
71965 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
71966 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
71967 +
71968 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &Value);
71969 + Value &= (~0x18);
71970 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, Value);
71971 +
71972 + RTMP_IO_READ32(pAd, TX_BAND_CFG, &Data);
71973 + Data &= 0xfffffffe;
71974 + RTMP_IO_WRITE32(pAd, TX_BAND_CFG, Data);
71975 +
71976 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R3, &Value);
71977 + Value &= (~0x20);
71978 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, Value);
71979 +#ifdef RT2860
71980 + pAd->StaCfg.BBPR3 = Value;
71981 +#endif // RT2860 //
71982 +
71983 + if (pAd->MACVersion == 0x28600100)
71984 + {
71985 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R69, 0x16);
71986 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R70, 0x08);
71987 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R73, 0x11);
71988 + DBGPRINT(RT_DEBUG_TRACE, ("!!!rt2860C !!! \n" ));
71989 + }
71990 +
71991 + DBGPRINT(RT_DEBUG_TRACE, ("!!! 20MHz LINK UP !!! \n" ));
71992 + }
71993 +
71994 + RTMPSetAGCInitValue(pAd, pAd->CommonCfg.BBPCurrentBW);
71995 + //
71996 + // Save BBP_R66 value, it will be used in RTUSBResumeMsduTransmission
71997 + //
71998 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R66, &pAd->BbpTuning.R66CurrentValue);
71999 +
72000 + DBGPRINT(RT_DEBUG_TRACE, ("!!! LINK UP !!! (BssType=%d, AID=%d, ssid=%s, Channel=%d, CentralChannel = %d)\n",
72001 + BssType, pAd->StaActive.Aid, pAd->CommonCfg.Ssid, pAd->CommonCfg.Channel, pAd->CommonCfg.CentralChannel));
72002 +
72003 +#ifdef DOT11_N_SUPPORT
72004 + DBGPRINT(RT_DEBUG_TRACE, ("!!! LINK UP !!! (Density =%d, )\n", pAd->MacTab.Content[BSSID_WCID].MpduDensity));
72005 +#endif // DOT11_N_SUPPORT //
72006 +
72007 + AsicSetBssid(pAd, pAd->CommonCfg.Bssid);
72008 +
72009 + AsicSetSlotTime(pAd, TRUE);
72010 + AsicSetEdcaParm(pAd, &pAd->CommonCfg.APEdcaParm);
72011 +
72012 + // Call this for RTS protectionfor legacy rate, we will always enable RTS threshold, but normally it will not hit
72013 + AsicUpdateProtect(pAd, 0, (OFDMSETPROTECT | CCKSETPROTECT), TRUE, FALSE);
72014 +
72015 +#ifdef DOT11_N_SUPPORT
72016 + if ((pAd->StaActive.SupportedPhyInfo.bHtEnable == TRUE))
72017 + {
72018 + // Update HT protectionfor based on AP's operating mode.
72019 + if (pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent == 1)
72020 + {
72021 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, FALSE, TRUE);
72022 + }
72023 + else
72024 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, FALSE, FALSE);
72025 + }
72026 +#endif // DOT11_N_SUPPORT //
72027 +
72028 + NdisZeroMemory(&pAd->DrsCounters, sizeof(COUNTER_DRS));
72029 +
72030 + NdisGetSystemUpTime(&Now);
72031 + pAd->StaCfg.LastBeaconRxTime = Now; // last RX timestamp
72032 +
72033 + if ((pAd->CommonCfg.TxPreamble != Rt802_11PreambleLong) &&
72034 + CAP_IS_SHORT_PREAMBLE_ON(pAd->StaActive.CapabilityInfo))
72035 + {
72036 + MlmeSetTxPreamble(pAd, Rt802_11PreambleShort);
72037 + }
72038 +
72039 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_AGGREGATION_INUSED);
72040 +
72041 + if (pAd->CommonCfg.RadarDetect.RDMode == RD_SILENCE_MODE)
72042 + {
72043 +#ifdef DFS_SUPPORT
72044 + RadarDetectionStop(pAd);
72045 +#endif // DFS_SUPPORT //
72046 + }
72047 + pAd->CommonCfg.RadarDetect.RDMode = RD_NORMAL_MODE;
72048 +
72049 + if (BssType == BSS_ADHOC)
72050 + {
72051 + MakeIbssBeacon(pAd);
72052 + if ((pAd->CommonCfg.Channel > 14)
72053 + && (pAd->CommonCfg.bIEEE80211H == 1)
72054 + && RadarChannelCheck(pAd, pAd->CommonCfg.Channel))
72055 + {
72056 + ; //Do nothing
72057 + }
72058 + else
72059 + {
72060 + AsicEnableIbssSync(pAd);
72061 + }
72062 +
72063 + // In ad hoc mode, use MAC table from index 1.
72064 + // p.s ASIC use all 0xff as termination of WCID table search.To prevent it's 0xff-ff-ff-ff-ff-ff, Write 0 here.
72065 + RTMP_IO_WRITE32(pAd, MAC_WCID_BASE, 0x00);
72066 + RTMP_IO_WRITE32(pAd, 0x1808, 0x00);
72067 +
72068 + // If WEP is enabled, add key material and cipherAlg into Asic
72069 + // Fill in Shared Key Table(offset: 0x6c00) and Shared Key Mode(offset: 0x7000)
72070 +
72071 + if (pAd->StaCfg.WepStatus == Ndis802_11WEPEnabled)
72072 + {
72073 + PUCHAR Key;
72074 + UCHAR CipherAlg;
72075 +
72076 + for (idx=0; idx < SHARE_KEY_NUM; idx++)
72077 + {
72078 + CipherAlg = pAd->SharedKey[BSS0][idx].CipherAlg;
72079 + Key = pAd->SharedKey[BSS0][idx].Key;
72080 +
72081 + if (pAd->SharedKey[BSS0][idx].KeyLen > 0)
72082 + {
72083 + // Set key material and cipherAlg to Asic
72084 + AsicAddSharedKeyEntry(pAd, BSS0, idx, CipherAlg, Key, NULL, NULL);
72085 +
72086 + if (idx == pAd->StaCfg.DefaultKeyId)
72087 + {
72088 + // Update WCID attribute table and IVEIV table for this group key table
72089 + RTMPAddWcidAttributeEntry(pAd, BSS0, idx, CipherAlg, NULL);
72090 + }
72091 + }
72092 +
72093 +
72094 + }
72095 + }
72096 + // If WPANone is enabled, add key material and cipherAlg into Asic
72097 + // Fill in Shared Key Table(offset: 0x6c00) and Shared Key Mode(offset: 0x7000)
72098 + else if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
72099 + {
72100 + pAd->StaCfg.DefaultKeyId = 0; // always be zero
72101 +
72102 + NdisZeroMemory(&pAd->SharedKey[BSS0][0], sizeof(CIPHER_KEY));
72103 + pAd->SharedKey[BSS0][0].KeyLen = LEN_TKIP_EK;
72104 + NdisMoveMemory(pAd->SharedKey[BSS0][0].Key, pAd->StaCfg.PMK, LEN_TKIP_EK);
72105 +
72106 + if (pAd->StaCfg.PairCipher == Ndis802_11Encryption2Enabled)
72107 + {
72108 + NdisMoveMemory(pAd->SharedKey[BSS0][0].RxMic, &pAd->StaCfg.PMK[16], LEN_TKIP_RXMICK);
72109 + NdisMoveMemory(pAd->SharedKey[BSS0][0].TxMic, &pAd->StaCfg.PMK[16], LEN_TKIP_TXMICK);
72110 + }
72111 +
72112 + // Decide its ChiperAlg
72113 + if (pAd->StaCfg.PairCipher == Ndis802_11Encryption2Enabled)
72114 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_TKIP;
72115 + else if (pAd->StaCfg.PairCipher == Ndis802_11Encryption3Enabled)
72116 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_AES;
72117 + else
72118 + {
72119 + DBGPRINT(RT_DEBUG_TRACE, ("Unknow Cipher (=%d), set Cipher to AES\n", pAd->StaCfg.PairCipher));
72120 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_AES;
72121 + }
72122 +
72123 + // Set key material and cipherAlg to Asic
72124 + AsicAddSharedKeyEntry(pAd,
72125 + BSS0,
72126 + 0,
72127 + pAd->SharedKey[BSS0][0].CipherAlg,
72128 + pAd->SharedKey[BSS0][0].Key,
72129 + pAd->SharedKey[BSS0][0].TxMic,
72130 + pAd->SharedKey[BSS0][0].RxMic);
72131 +
72132 + // Update WCID attribute table and IVEIV table for this group key table
72133 + RTMPAddWcidAttributeEntry(pAd, BSS0, 0, pAd->SharedKey[BSS0][0].CipherAlg, NULL);
72134 +
72135 + }
72136 +
72137 + }
72138 + else // BSS_INFRA
72139 + {
72140 + // Check the new SSID with last SSID
72141 + while (Cancelled == TRUE)
72142 + {
72143 + if (pAd->CommonCfg.LastSsidLen == pAd->CommonCfg.SsidLen)
72144 + {
72145 + if (RTMPCompareMemory(pAd->CommonCfg.LastSsid, pAd->CommonCfg.Ssid, pAd->CommonCfg.LastSsidLen) == 0)
72146 + {
72147 + // Link to the old one no linkdown is required.
72148 + break;
72149 + }
72150 + }
72151 + // Send link down event before set to link up
72152 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
72153 + RTMP_IndicateMediaState(pAd);
72154 + pAd->ExtraInfo = GENERAL_LINK_DOWN;
72155 + DBGPRINT(RT_DEBUG_TRACE, ("NDIS_STATUS_MEDIA_DISCONNECT Event AA!\n"));
72156 + break;
72157 + }
72158 +
72159 + //
72160 + // On WPA mode, Remove All Keys if not connect to the last BSSID
72161 + // Key will be set after 4-way handshake.
72162 + //
72163 + if ((pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA))
72164 + {
72165 + ULONG IV;
72166 +
72167 + // Remove all WPA keys
72168 + RTMPWPARemoveAllKeys(pAd);
72169 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
72170 + pAd->StaCfg.PrivacyFilter = Ndis802_11PrivFilter8021xWEP;
72171 +
72172 + // Fixed connection failed with Range Maximizer - 515 AP (Marvell Chip) when security is WPAPSK/TKIP
72173 + // If IV related values are too large in GroupMsg2, AP would ignore this message.
72174 + IV = 0;
72175 + IV |= (pAd->StaCfg.DefaultKeyId << 30);
72176 + AsicUpdateWCIDIVEIV(pAd, BSSID_WCID, IV, 0);
72177 + }
72178 + // NOTE:
72179 + // the decision of using "short slot time" or not may change dynamically due to
72180 + // new STA association to the AP. so we have to decide that upon parsing BEACON, not here
72181 +
72182 + // NOTE:
72183 + // the decision to use "RTC/CTS" or "CTS-to-self" protection or not may change dynamically
72184 + // due to new STA association to the AP. so we have to decide that upon parsing BEACON, not here
72185 +
72186 + ComposePsPoll(pAd);
72187 + ComposeNullFrame(pAd);
72188 +
72189 + AsicEnableBssSync(pAd);
72190 +
72191 + // Add BSSID to WCID search table
72192 + AsicUpdateRxWCIDTable(pAd, BSSID_WCID, pAd->CommonCfg.Bssid);
72193 +
72194 + NdisAcquireSpinLock(&pAd->MacTabLock);
72195 + // add this BSSID entry into HASH table
72196 + {
72197 + UCHAR HashIdx;
72198 +
72199 + //pEntry = &pAd->MacTab.Content[BSSID_WCID];
72200 + HashIdx = MAC_ADDR_HASH_INDEX(pAd->CommonCfg.Bssid);
72201 + if (pAd->MacTab.Hash[HashIdx] == NULL)
72202 + {
72203 + pAd->MacTab.Hash[HashIdx] = pEntry;
72204 + }
72205 + else
72206 + {
72207 + pCurrEntry = pAd->MacTab.Hash[HashIdx];
72208 + while (pCurrEntry->pNext != NULL)
72209 + pCurrEntry = pCurrEntry->pNext;
72210 + pCurrEntry->pNext = pEntry;
72211 + }
72212 + }
72213 + NdisReleaseSpinLock(&pAd->MacTabLock);
72214 +
72215 +
72216 + // If WEP is enabled, add paiewise and shared key
72217 +#ifdef WPA_SUPPLICANT_SUPPORT
72218 + if (((pAd->StaCfg.WpaSupplicantUP)&&
72219 + (pAd->StaCfg.WepStatus == Ndis802_11WEPEnabled)&&
72220 + (pAd->StaCfg.PortSecured == WPA_802_1X_PORT_SECURED)) ||
72221 + ((pAd->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_DISABLE)&&
72222 + (pAd->StaCfg.WepStatus == Ndis802_11WEPEnabled)))
72223 +#else
72224 + if (pAd->StaCfg.WepStatus == Ndis802_11WEPEnabled)
72225 +#endif // WPA_SUPPLICANT_SUPPORT //
72226 + {
72227 + PUCHAR Key;
72228 + UCHAR CipherAlg;
72229 +
72230 + for (idx=0; idx < SHARE_KEY_NUM; idx++)
72231 + {
72232 + CipherAlg = pAd->SharedKey[BSS0][idx].CipherAlg;
72233 + Key = pAd->SharedKey[BSS0][idx].Key;
72234 +
72235 + if (pAd->SharedKey[BSS0][idx].KeyLen > 0)
72236 + {
72237 + // Set key material and cipherAlg to Asic
72238 + AsicAddSharedKeyEntry(pAd, BSS0, idx, CipherAlg, Key, NULL, NULL);
72239 +
72240 + if (idx == pAd->StaCfg.DefaultKeyId)
72241 + {
72242 + // Assign group key info
72243 + RTMPAddWcidAttributeEntry(pAd, BSS0, idx, CipherAlg, NULL);
72244 +
72245 + // Assign pairwise key info
72246 + RTMPAddWcidAttributeEntry(pAd, BSS0, idx, CipherAlg, pEntry);
72247 + }
72248 + }
72249 + }
72250 + }
72251 +
72252 + // only INFRASTRUCTURE mode need to indicate connectivity immediately; ADHOC mode
72253 + // should wait until at least 2 active nodes in this BSSID.
72254 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
72255 +
72256 + // For GUI ++
72257 + if (pAd->StaCfg.AuthMode < Ndis802_11AuthModeWPA)
72258 + {
72259 + pAd->IndicateMediaState = NdisMediaStateConnected;
72260 + pAd->ExtraInfo = GENERAL_LINK_UP;
72261 + }
72262 + // --
72263 + RTMP_IndicateMediaState(pAd);
72264 +
72265 + // Add BSSID in my MAC Table.
72266 + NdisAcquireSpinLock(&pAd->MacTabLock);
72267 + RTMPMoveMemory(pAd->MacTab.Content[BSSID_WCID].Addr, pAd->CommonCfg.Bssid, MAC_ADDR_LEN);
72268 + pAd->MacTab.Content[BSSID_WCID].Aid = BSSID_WCID;
72269 + pAd->MacTab.Content[BSSID_WCID].pAd = pAd;
72270 + pAd->MacTab.Content[BSSID_WCID].ValidAsCLI = TRUE; //Although this is bssid..still set ValidAsCl
72271 + pAd->MacTab.Size = 1; // infra mode always set MACtab size =1.
72272 + pAd->MacTab.Content[BSSID_WCID].Sst = SST_ASSOC;
72273 + pAd->MacTab.Content[BSSID_WCID].AuthState = SST_ASSOC;
72274 + pAd->MacTab.Content[BSSID_WCID].WepStatus = pAd->StaCfg.WepStatus;
72275 + NdisReleaseSpinLock(&pAd->MacTabLock);
72276 +
72277 + DBGPRINT(RT_DEBUG_TRACE, ("!!! LINK UP !!! ClientStatusFlags=%lx)\n",
72278 + pAd->MacTab.Content[BSSID_WCID].ClientStatusFlags));
72279 +
72280 + MlmeUpdateTxRates(pAd, TRUE, BSS0);
72281 +#ifdef DOT11_N_SUPPORT
72282 + MlmeUpdateHtTxRates(pAd, BSS0);
72283 + DBGPRINT(RT_DEBUG_TRACE, ("!!! LINK UP !! (StaActive.bHtEnable =%d, )\n", pAd->StaActive.SupportedPhyInfo.bHtEnable));
72284 +#endif // DOT11_N_SUPPORT //
72285 +
72286 + //
72287 + // Report Adjacent AP report.
72288 + //
72289 +#ifdef LEAP_SUPPORT
72290 + CCXAdjacentAPReport(pAd);
72291 +#endif // LEAP_SUPPORT //
72292 +
72293 + if (pAd->CommonCfg.bAggregationCapable)
72294 + {
72295 + if ((pAd->CommonCfg.bPiggyBackCapable) && (pAd->MlmeAux.APRalinkIe & 0x00000003) == 3)
72296 + {
72297 +
72298 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_PIGGYBACK_INUSED);
72299 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_AGGREGATION_INUSED);
72300 + RTMPSetPiggyBack(pAd, TRUE);
72301 + DBGPRINT(RT_DEBUG_TRACE, ("Turn on Piggy-Back\n"));
72302 + }
72303 + else if (pAd->MlmeAux.APRalinkIe & 0x00000001)
72304 + {
72305 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_AGGREGATION_INUSED);
72306 + }
72307 + }
72308 +
72309 + if (pAd->MlmeAux.APRalinkIe != 0x0)
72310 + {
72311 +#ifdef DOT11_N_SUPPORT
72312 + if (CLIENT_STATUS_TEST_FLAG(&pAd->MacTab.Content[BSSID_WCID], fCLIENT_STATUS_RDG_CAPABLE))
72313 + {
72314 + AsicEnableRDG(pAd);
72315 + }
72316 +#endif // DOT11_N_SUPPORT //
72317 + OPSTATUS_SET_FLAG(pAd, fCLIENT_STATUS_RALINK_CHIPSET);
72318 + CLIENT_STATUS_SET_FLAG(&pAd->MacTab.Content[BSSID_WCID], fCLIENT_STATUS_RALINK_CHIPSET);
72319 + }
72320 + else
72321 + {
72322 + OPSTATUS_CLEAR_FLAG(pAd, fCLIENT_STATUS_RALINK_CHIPSET);
72323 + CLIENT_STATUS_CLEAR_FLAG(&pAd->MacTab.Content[BSSID_WCID], fCLIENT_STATUS_RALINK_CHIPSET);
72324 + }
72325 + }
72326 +
72327 +#ifdef DOT11_N_SUPPORT
72328 + DBGPRINT(RT_DEBUG_TRACE, ("NDIS_STATUS_MEDIA_CONNECT Event B!.BACapability = %x. ClientStatusFlags = %lx\n", pAd->CommonCfg.BACapability.word, pAd->MacTab.Content[BSSID_WCID].ClientStatusFlags));
72329 +#endif // DOT11_N_SUPPORT //
72330 +
72331 + // Set LED
72332 + RTMPSetLED(pAd, LED_LINK_UP);
72333 +
72334 + pAd->Mlme.PeriodicRound = 0;
72335 + pAd->Mlme.OneSecPeriodicRound = 0;
72336 + pAd->bConfigChanged = FALSE; // Reset config flag
72337 + pAd->ExtraInfo = GENERAL_LINK_UP; // Update extra information to link is up
72338 +
72339 + // Set asic auto fall back
72340 + {
72341 + PUCHAR pTable;
72342 + UCHAR TableSize = 0;
72343 +
72344 + MlmeSelectTxRateTable(pAd, &pAd->MacTab.Content[BSSID_WCID], &pTable, &TableSize, &pAd->CommonCfg.TxRateIndex);
72345 + AsicUpdateAutoFallBackTable(pAd, pTable);
72346 + }
72347 +
72348 + NdisAcquireSpinLock(&pAd->MacTabLock);
72349 + pEntry->HTPhyMode.word = pAd->StaCfg.HTPhyMode.word;
72350 + pEntry->MaxHTPhyMode.word = pAd->StaCfg.HTPhyMode.word;
72351 + if (pAd->StaCfg.bAutoTxRateSwitch == FALSE)
72352 + {
72353 + pEntry->bAutoTxRateSwitch = FALSE;
72354 +#ifdef DOT11_N_SUPPORT
72355 + if (pEntry->HTPhyMode.field.MCS == 32)
72356 + pEntry->HTPhyMode.field.ShortGI = GI_800;
72357 +
72358 + if ((pEntry->HTPhyMode.field.MCS > MCS_7) || (pEntry->HTPhyMode.field.MCS == 32))
72359 + pEntry->HTPhyMode.field.STBC = STBC_NONE;
72360 +#endif // DOT11_N_SUPPORT //
72361 + // If the legacy mode is set, overwrite the transmit setting of this entry.
72362 + if (pEntry->HTPhyMode.field.MODE <= MODE_OFDM)
72363 + RTMPUpdateLegacyTxSetting((UCHAR)pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode, pEntry);
72364 + }
72365 + else
72366 + pEntry->bAutoTxRateSwitch = TRUE;
72367 + NdisReleaseSpinLock(&pAd->MacTabLock);
72368 +
72369 + // Let Link Status Page display first initial rate.
72370 + pAd->LastTxRate = (USHORT)(pEntry->HTPhyMode.word);
72371 + // Select DAC according to HT or Legacy
72372 + if (pAd->StaActive.SupportedPhyInfo.MCSSet[0] != 0x00)
72373 + {
72374 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &Value);
72375 + Value &= (~0x18);
72376 + if (pAd->Antenna.field.TxPath == 2)
72377 + {
72378 + Value |= 0x10;
72379 + }
72380 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, Value);
72381 + }
72382 + else
72383 + {
72384 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &Value);
72385 + Value &= (~0x18);
72386 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, Value);
72387 + }
72388 +
72389 +#ifdef DOT11_N_SUPPORT
72390 + if (pAd->StaActive.SupportedPhyInfo.bHtEnable == FALSE)
72391 + {
72392 + }
72393 + else if (pEntry->MaxRAmpduFactor == 0)
72394 + {
72395 + // If HT AP doesn't support MaxRAmpduFactor = 1, we need to set max PSDU to 0.
72396 + // Because our Init value is 1 at MACRegTable.
72397 + RTMP_IO_WRITE32(pAd, MAX_LEN_CFG, 0x0fff);
72398 + }
72399 +#endif // DOT11_N_SUPPORT //
72400 +
72401 + // Patch for Marvel AP to gain high throughput
72402 + // Need to set as following,
72403 + // 1. Set txop in register-EDCA_AC0_CFG as 0x60
72404 + // 2. Set EnTXWriteBackDDONE in register-WPDMA_GLO_CFG as zero
72405 + // 3. PBF_MAX_PCNT as 0x1F3FBF9F
72406 + // 4. kick per two packets when dequeue
72407 + //
72408 + // Txop can only be modified when RDG is off, WMM is disable and TxBurst is enable
72409 + //
72410 + // if 1. Legacy AP WMM on, or 2. 11n AP, AMPDU disable. Force turn off burst no matter what bEnableTxBurst is.
72411 +#ifdef DOT11_N_SUPPORT
72412 + if (((pAd->StaActive.SupportedPhyInfo.bHtEnable == FALSE) && (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED)))
72413 + || ((pAd->StaActive.SupportedPhyInfo.bHtEnable == TRUE) && (pAd->CommonCfg.BACapability.field.Policy == BA_NOTUSE)))
72414 + {
72415 + RTMP_IO_READ32(pAd, EDCA_AC0_CFG, &Data);
72416 + Data &= 0xFFFFFF00;
72417 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, Data);
72418 +
72419 + RTMP_IO_WRITE32(pAd, PBF_MAX_PCNT, 0x1F3F7F9F);
72420 + DBGPRINT(RT_DEBUG_TRACE, ("Txburst 1\n"));
72421 + }
72422 + else
72423 +#endif // DOT11_N_SUPPORT //
72424 + if (pAd->CommonCfg.bEnableTxBurst)
72425 + {
72426 + RTMP_IO_READ32(pAd, EDCA_AC0_CFG, &Data);
72427 + Data &= 0xFFFFFF00;
72428 + Data |= 0x60;
72429 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, Data);
72430 + pAd->CommonCfg.IOTestParm.bNowAtherosBurstOn = TRUE;
72431 +
72432 + RTMP_IO_WRITE32(pAd, PBF_MAX_PCNT, 0x1F3FBF9F);
72433 + DBGPRINT(RT_DEBUG_TRACE, ("Txburst 2\n"));
72434 + }
72435 + else
72436 + {
72437 + RTMP_IO_READ32(pAd, EDCA_AC0_CFG, &Data);
72438 + Data &= 0xFFFFFF00;
72439 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, Data);
72440 +
72441 + RTMP_IO_WRITE32(pAd, PBF_MAX_PCNT, 0x1F3F7F9F);
72442 + DBGPRINT(RT_DEBUG_TRACE, ("Txburst 3\n"));
72443 + }
72444 +
72445 +#ifdef DOT11_N_SUPPORT
72446 + // Re-check to turn on TX burst or not.
72447 + if ((pAd->CommonCfg.IOTestParm.bLastAtheros == TRUE) && ((STA_WEP_ON(pAd))||(STA_TKIP_ON(pAd))))
72448 + {
72449 + pAd->CommonCfg.IOTestParm.bNextDisableRxBA = TRUE;
72450 + if (pAd->CommonCfg.bEnableTxBurst)
72451 + {
72452 + UINT32 MACValue = 0;
72453 + // Force disable TXOP value in this case. The same action in MLMEUpdateProtect too.
72454 + // I didn't change PBF_MAX_PCNT setting.
72455 + RTMP_IO_READ32(pAd, EDCA_AC0_CFG, &MACValue);
72456 + MACValue &= 0xFFFFFF00;
72457 + RTMP_IO_WRITE32(pAd, EDCA_AC0_CFG, MACValue);
72458 + pAd->CommonCfg.IOTestParm.bNowAtherosBurstOn = FALSE;
72459 + }
72460 + }
72461 + else
72462 + {
72463 + pAd->CommonCfg.IOTestParm.bNextDisableRxBA = FALSE;
72464 + }
72465 +#endif // DOT11_N_SUPPORT //
72466 +
72467 + pAd->CommonCfg.IOTestParm.bLastAtheros = FALSE;
72468 + COPY_MAC_ADDR(pAd->CommonCfg.LastBssid, pAd->CommonCfg.Bssid);
72469 + DBGPRINT(RT_DEBUG_TRACE, ("!!!pAd->bNextDisableRxBA= %d \n", pAd->CommonCfg.IOTestParm.bNextDisableRxBA));
72470 + // BSSID add in one MAC entry too. Because in Tx, ASIC need to check Cipher and IV/EIV, BAbitmap
72471 + // Pther information in MACTab.Content[BSSID_WCID] is not necessary for driver.
72472 + // Note: As STA, The MACTab.Content[BSSID_WCID]. PairwiseKey and Shared Key for BSS0 are the same.
72473 +
72474 + if (pAd->StaCfg.WepStatus <= Ndis802_11WEPDisabled)
72475 + {
72476 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED;
72477 + pAd->StaCfg.PrivacyFilter = Ndis802_11PrivFilterAcceptAll;
72478 + }
72479 +
72480 + NdisAcquireSpinLock(&pAd->MacTabLock);
72481 + pEntry->PortSecured = pAd->StaCfg.PortSecured;
72482 + NdisReleaseSpinLock(&pAd->MacTabLock);
72483 +
72484 + //
72485 + // Patch Atheros AP TX will breakdown issue.
72486 + // AP Model: DLink DWL-8200AP
72487 + //
72488 + if (INFRA_ON(pAd) && OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED) && STA_TKIP_ON(pAd))
72489 + {
72490 + RTMP_IO_WRITE32(pAd, RX_PARSER_CFG, 0x01);
72491 + }
72492 + else
72493 + {
72494 + RTMP_IO_WRITE32(pAd, RX_PARSER_CFG, 0x00);
72495 + }
72496 +
72497 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS);
72498 +
72499 +#ifdef DOT11_N_SUPPORT
72500 +#ifdef DOT11N_DRAFT3
72501 + if ((pAd->CommonCfg.BACapability.field.b2040CoexistScanSup) && (pAd->CommonCfg.Channel <= 11))
72502 + {
72503 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_SCAN_2040);
72504 + BuildEffectedChannelList(pAd);
72505 + }
72506 +#endif // DOT11N_DRAFT3 //
72507 +#endif // DOT11_N_SUPPORT //
72508 +}
72509 +
72510 +/*
72511 + ==========================================================================
72512 +
72513 + Routine Description:
72514 + Disconnect current BSSID
72515 +
72516 + Arguments:
72517 + pAd - Pointer to our adapter
72518 + IsReqFromAP - Request from AP
72519 +
72520 + Return Value:
72521 + None
72522 +
72523 + IRQL = DISPATCH_LEVEL
72524 +
72525 + Note:
72526 + We need more information to know it's this requst from AP.
72527 + If yes! we need to do extra handling, for example, remove the WPA key.
72528 + Otherwise on 4-way handshaking will faied, since the WPA key didn't be
72529 + remove while auto reconnect.
72530 + Disconnect request from AP, it means we will start afresh 4-way handshaking
72531 + on WPA mode.
72532 +
72533 + ==========================================================================
72534 +*/
72535 +VOID LinkDown(
72536 + IN PRTMP_ADAPTER pAd,
72537 + IN BOOLEAN IsReqFromAP)
72538 +{
72539 + UCHAR i, ByteValue = 0;
72540 +
72541 + // Do nothing if monitor mode is on
72542 + if (MONITOR_ON(pAd))
72543 + return;
72544 +
72545 +#ifdef RALINK_ATE
72546 + // Nothing to do in ATE mode.
72547 + if (ATE_ON(pAd))
72548 + return;
72549 +#endif // RALINK_ATE //
72550 +
72551 + if (pAd->CommonCfg.bWirelessEvent)
72552 + {
72553 + RTMPSendWirelessEvent(pAd, IW_STA_LINKDOWN_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
72554 + }
72555 +
72556 + DBGPRINT(RT_DEBUG_TRACE, ("!!! LINK DOWN !!!\n"));
72557 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_AGGREGATION_INUSED);
72558 +
72559 +#ifdef RT2860
72560 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
72561 + {
72562 + BOOLEAN Cancelled;
72563 + pAd->Mlme.bPsPollTimerRunning = FALSE;
72564 + RTMPCancelTimer(&pAd->Mlme.PsPollTimer, &Cancelled);
72565 + }
72566 +
72567 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
72568 + {
72569 + AUTO_WAKEUP_STRUC AutoWakeupCfg;
72570 + AsicForceWakeup(pAd, TRUE);
72571 + AutoWakeupCfg.word = 0;
72572 + RTMP_IO_WRITE32(pAd, AUTO_WAKEUP_CFG, AutoWakeupCfg.word);
72573 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_DOZE);
72574 + }
72575 +
72576 + pAd->bPCIclkOff = FALSE;
72577 +#endif // RT2860 //
72578 + if (ADHOC_ON(pAd)) // Adhoc mode link down
72579 + {
72580 + DBGPRINT(RT_DEBUG_TRACE, ("!!! LINK DOWN 1!!!\n"));
72581 +
72582 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_ADHOC_ON);
72583 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
72584 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
72585 + RTMP_IndicateMediaState(pAd);
72586 + pAd->ExtraInfo = GENERAL_LINK_DOWN;
72587 + BssTableDeleteEntry(&pAd->ScanTab, pAd->CommonCfg.Bssid, pAd->CommonCfg.Channel);
72588 + DBGPRINT(RT_DEBUG_TRACE, ("!!! MacTab.Size=%d !!!\n", pAd->MacTab.Size));
72589 + }
72590 + else // Infra structure mode
72591 + {
72592 + DBGPRINT(RT_DEBUG_TRACE, ("!!! LINK DOWN 2!!!\n"));
72593 +
72594 +#ifdef QOS_DLS_SUPPORT
72595 + // DLS tear down frame must be sent before link down
72596 + // send DLS-TEAR_DOWN message
72597 + if (pAd->CommonCfg.bDLSCapable)
72598 + {
72599 + // tear down local dls table entry
72600 + for (i=0; i<MAX_NUM_OF_INIT_DLS_ENTRY; i++)
72601 + {
72602 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH))
72603 + {
72604 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
72605 + RTMPSendDLSTearDownFrame(pAd, pAd->StaCfg.DLSEntry[i].MacAddr);
72606 + }
72607 + }
72608 +
72609 + // tear down peer dls table entry
72610 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
72611 + {
72612 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH))
72613 + {
72614 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
72615 + RTMPSendDLSTearDownFrame(pAd, pAd->StaCfg.DLSEntry[i].MacAddr);
72616 + }
72617 + }
72618 + }
72619 +#endif // QOS_DLS_SUPPORT //
72620 +
72621 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_INFRA_ON);
72622 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
72623 +
72624 + // Saved last SSID for linkup comparison
72625 + pAd->CommonCfg.LastSsidLen = pAd->CommonCfg.SsidLen;
72626 + NdisMoveMemory(pAd->CommonCfg.LastSsid, pAd->CommonCfg.Ssid, pAd->CommonCfg.LastSsidLen);
72627 + COPY_MAC_ADDR(pAd->CommonCfg.LastBssid, pAd->CommonCfg.Bssid);
72628 + if (pAd->MlmeAux.CurrReqIsFromNdis == TRUE)
72629 + {
72630 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
72631 + RTMP_IndicateMediaState(pAd);
72632 + pAd->ExtraInfo = GENERAL_LINK_DOWN;
72633 + DBGPRINT(RT_DEBUG_TRACE, ("NDIS_STATUS_MEDIA_DISCONNECT Event A!\n"));
72634 + pAd->MlmeAux.CurrReqIsFromNdis = FALSE;
72635 + }
72636 + else
72637 + {
72638 + //
72639 + // If disassociation request is from NDIS, then we don't need to delete BSSID from entry.
72640 + // Otherwise lost beacon or receive De-Authentication from AP,
72641 + // then we should delete BSSID from BssTable.
72642 + // If we don't delete from entry, roaming will fail.
72643 + //
72644 + BssTableDeleteEntry(&pAd->ScanTab, pAd->CommonCfg.Bssid, pAd->CommonCfg.Channel);
72645 + }
72646 +
72647 + // restore back to -
72648 + // 1. long slot (20 us) or short slot (9 us) time
72649 + // 2. turn on/off RTS/CTS and/or CTS-to-self protection
72650 + // 3. short preamble
72651 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED);
72652 +
72653 + if (pAd->StaCfg.CCXAdjacentAPReportFlag == TRUE)
72654 + {
72655 + //
72656 + // Record current AP's information.
72657 + // for later used reporting Adjacent AP report.
72658 + //
72659 + pAd->StaCfg.CCXAdjacentAPChannel = pAd->CommonCfg.Channel;
72660 + pAd->StaCfg.CCXAdjacentAPSsidLen = pAd->CommonCfg.SsidLen;
72661 + NdisMoveMemory(pAd->StaCfg.CCXAdjacentAPSsid, pAd->CommonCfg.Ssid, pAd->StaCfg.CCXAdjacentAPSsidLen);
72662 + COPY_MAC_ADDR(pAd->StaCfg.CCXAdjacentAPBssid, pAd->CommonCfg.Bssid);
72663 + }
72664 +
72665 +#ifdef EXT_BUILD_CHANNEL_LIST
72666 + // Country IE of the AP will be evaluated and will be used.
72667 + if (pAd->StaCfg.IEEE80211dClientMode != Rt802_11_D_None)
72668 + {
72669 + NdisMoveMemory(&pAd->CommonCfg.CountryCode[0], &pAd->StaCfg.StaOriCountryCode[0], 2);
72670 + pAd->CommonCfg.Geography = pAd->StaCfg.StaOriGeography;
72671 + BuildChannelListEx(pAd);
72672 + }
72673 +#endif // EXT_BUILD_CHANNEL_LIST //
72674 +
72675 + }
72676 +
72677 + for (i=1; i<MAX_LEN_OF_MAC_TABLE; i++)
72678 + {
72679 + if (pAd->MacTab.Content[i].ValidAsCLI == TRUE)
72680 + MacTableDeleteEntry(pAd, pAd->MacTab.Content[i].Aid, pAd->MacTab.Content[i].Addr);
72681 + }
72682 +
72683 + pAd->StaCfg.CCXQosECWMin = 4;
72684 + pAd->StaCfg.CCXQosECWMax = 10;
72685 +
72686 + AsicSetSlotTime(pAd, TRUE); //FALSE);
72687 + AsicSetEdcaParm(pAd, NULL);
72688 +
72689 + // Set LED
72690 + RTMPSetLED(pAd, LED_LINK_DOWN);
72691 + pAd->LedIndicatorStregth = 0xF0;
72692 + RTMPSetSignalLED(pAd, -100); // Force signal strength Led to be turned off, firmware is not done it.
72693 +
72694 + AsicDisableSync(pAd);
72695 +
72696 + pAd->Mlme.PeriodicRound = 0;
72697 + pAd->Mlme.OneSecPeriodicRound = 0;
72698 +
72699 + if (pAd->StaCfg.BssType == BSS_INFRA)
72700 + {
72701 + // Remove StaCfg Information after link down
72702 + NdisZeroMemory(pAd->CommonCfg.Bssid, MAC_ADDR_LEN);
72703 + NdisZeroMemory(pAd->CommonCfg.Ssid, MAX_LEN_OF_SSID);
72704 + pAd->CommonCfg.SsidLen = 0;
72705 + }
72706 +#ifdef DOT11_N_SUPPORT
72707 + NdisZeroMemory(&pAd->MlmeAux.HtCapability, sizeof(HT_CAPABILITY_IE));
72708 + NdisZeroMemory(&pAd->MlmeAux.AddHtInfo, sizeof(ADD_HT_INFO_IE));
72709 + pAd->MlmeAux.HtCapabilityLen = 0;
72710 + pAd->MlmeAux.NewExtChannelOffset = 0xff;
72711 +#endif // DOT11_N_SUPPORT //
72712 +
72713 + // Reset WPA-PSK state. Only reset when supplicant enabled
72714 + if (pAd->StaCfg.WpaState != SS_NOTUSE)
72715 + {
72716 + pAd->StaCfg.WpaState = SS_START;
72717 + // Clear Replay counter
72718 + NdisZeroMemory(pAd->StaCfg.ReplayCounter, 8);
72719 +
72720 +#ifdef QOS_DLS_SUPPORT
72721 + if (pAd->CommonCfg.bDLSCapable)
72722 + NdisZeroMemory(pAd->StaCfg.DlsReplayCounter, 8);
72723 +#endif // QOS_DLS_SUPPORT //
72724 + }
72725 +
72726 +
72727 + //
72728 + // if link down come from AP, we need to remove all WPA keys on WPA mode.
72729 + // otherwise will cause 4-way handshaking failed, since the WPA key not empty.
72730 + //
72731 + if ((IsReqFromAP) && (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA))
72732 + {
72733 + // Remove all WPA keys
72734 + RTMPWPARemoveAllKeys(pAd);
72735 + }
72736 +
72737 + // 802.1x port control
72738 +#ifdef WPA_SUPPLICANT_SUPPORT
72739 + // Prevent clear PortSecured here with static WEP
72740 + // NetworkManger set security policy first then set SSID to connect AP.
72741 + if (pAd->StaCfg.WpaSupplicantUP &&
72742 + (pAd->StaCfg.WepStatus == Ndis802_11WEPEnabled) &&
72743 + (pAd->StaCfg.IEEE8021X == FALSE))
72744 + {
72745 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED;
72746 + }
72747 + else
72748 +#endif // WPA_SUPPLICANT_SUPPORT //
72749 + {
72750 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
72751 + pAd->StaCfg.PrivacyFilter = Ndis802_11PrivFilter8021xWEP;
72752 + }
72753 +
72754 + NdisAcquireSpinLock(&pAd->MacTabLock);
72755 + pAd->MacTab.Content[BSSID_WCID].PortSecured = pAd->StaCfg.PortSecured;
72756 + NdisReleaseSpinLock(&pAd->MacTabLock);
72757 +
72758 + pAd->StaCfg.MicErrCnt = 0;
72759 +
72760 + // Turn off Ckip control flag
72761 + pAd->StaCfg.bCkipOn = FALSE;
72762 + pAd->StaCfg.CCXEnable = FALSE;
72763 +
72764 + pAd->IndicateMediaState = NdisMediaStateDisconnected;
72765 + // Update extra information to link is up
72766 + pAd->ExtraInfo = GENERAL_LINK_DOWN;
72767 +
72768 + pAd->StaCfg.AdhocBOnlyJoined = FALSE;
72769 + pAd->StaCfg.AdhocBGJoined = FALSE;
72770 + pAd->StaCfg.Adhoc20NJoined = FALSE;
72771 + pAd->StaActive.SupportedPhyInfo.bHtEnable = FALSE;
72772 +
72773 + // Reset the Current AP's IP address
72774 + NdisZeroMemory(pAd->StaCfg.AironetIPAddress, 4);
72775 +
72776 + // Clean association information
72777 + NdisZeroMemory(&pAd->StaCfg.AssocInfo, sizeof(NDIS_802_11_ASSOCIATION_INFORMATION));
72778 + pAd->StaCfg.AssocInfo.Length = sizeof(NDIS_802_11_ASSOCIATION_INFORMATION);
72779 + pAd->StaCfg.ReqVarIELen = 0;
72780 + pAd->StaCfg.ResVarIELen = 0;
72781 +
72782 + //
72783 + // Reset RSSI value after link down
72784 + //
72785 + pAd->StaCfg.RssiSample.AvgRssi0 = 0;
72786 + pAd->StaCfg.RssiSample.AvgRssi0X8 = 0;
72787 + pAd->StaCfg.RssiSample.AvgRssi1 = 0;
72788 + pAd->StaCfg.RssiSample.AvgRssi1X8 = 0;
72789 + pAd->StaCfg.RssiSample.AvgRssi2 = 0;
72790 + pAd->StaCfg.RssiSample.AvgRssi2X8 = 0;
72791 +
72792 + // Restore MlmeRate
72793 + pAd->CommonCfg.MlmeRate = pAd->CommonCfg.BasicMlmeRate;
72794 + pAd->CommonCfg.RtsRate = pAd->CommonCfg.BasicMlmeRate;
72795 +
72796 +#ifdef DOT11_N_SUPPORT
72797 + //
72798 + // After Link down, reset piggy-back setting in ASIC. Disable RDG.
72799 + //
72800 + if (pAd->CommonCfg.BBPCurrentBW == BW_40)
72801 + {
72802 + pAd->CommonCfg.BBPCurrentBW = BW_20;
72803 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &ByteValue);
72804 + ByteValue &= (~0x18);
72805 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, ByteValue);
72806 + }
72807 +#endif // DOT11_N_SUPPORT //
72808 + // Reset DAC
72809 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R1, &ByteValue);
72810 + ByteValue &= (~0x18);
72811 + if (pAd->Antenna.field.TxPath == 2)
72812 + {
72813 + ByteValue |= 0x10;
72814 + }
72815 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R1, ByteValue);
72816 +
72817 + RTMPSetPiggyBack(pAd,FALSE);
72818 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_PIGGYBACK_INUSED);
72819 +
72820 +#ifdef DOT11_N_SUPPORT
72821 + pAd->CommonCfg.BACapability.word = pAd->CommonCfg.REGBACapability.word;
72822 +#endif // DOT11_N_SUPPORT //
72823 +
72824 + // Restore all settings in the following.
72825 + AsicUpdateProtect(pAd, 0, (ALLN_SETPROTECT|CCKSETPROTECT|OFDMSETPROTECT), TRUE, FALSE);
72826 + AsicDisableRDG(pAd);
72827 + pAd->CommonCfg.IOTestParm.bCurrentAtheros = FALSE;
72828 + pAd->CommonCfg.IOTestParm.bNowAtherosBurstOn = FALSE;
72829 +
72830 +#ifdef DOT11_N_SUPPORT
72831 +#ifdef DOT11N_DRAFT3
72832 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_SCAN_2040);
72833 + pAd->CommonCfg.BSSCoexist2040.word = 0;
72834 + TriEventInit(pAd);
72835 + for (i = 0; i < (pAd->ChannelListNum - 1); i++)
72836 + {
72837 + pAd->ChannelList[i].bEffectedChannel = FALSE;
72838 + }
72839 +#endif // DOT11N_DRAFT3 //
72840 +#endif // DOT11_N_SUPPORT //
72841 +
72842 + RTMP_IO_WRITE32(pAd, MAX_LEN_CFG, 0x1fff);
72843 + RTMP_CLEAR_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS);
72844 +
72845 +#ifdef WPA_SUPPLICANT_SUPPORT
72846 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
72847 + if (pAd->StaCfg.WpaSupplicantUP) {
72848 + union iwreq_data wrqu;
72849 + //send disassociate event to wpa_supplicant
72850 + memset(&wrqu, 0, sizeof(wrqu));
72851 + wrqu.data.flags = RT_DISASSOC_EVENT_FLAG;
72852 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
72853 + }
72854 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
72855 +#endif // WPA_SUPPLICANT_SUPPORT //
72856 +
72857 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
72858 + {
72859 + union iwreq_data wrqu;
72860 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
72861 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
72862 + }
72863 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
72864 +}
72865 +
72866 +/*
72867 + ==========================================================================
72868 + Description:
72869 +
72870 + IRQL = DISPATCH_LEVEL
72871 +
72872 + ==========================================================================
72873 +*/
72874 +VOID IterateOnBssTab(
72875 + IN PRTMP_ADAPTER pAd)
72876 +{
72877 + MLME_START_REQ_STRUCT StartReq;
72878 + MLME_JOIN_REQ_STRUCT JoinReq;
72879 + ULONG BssIdx;
72880 +
72881 + // Change the wepstatus to original wepstatus
72882 + pAd->StaCfg.WepStatus = pAd->StaCfg.OrigWepStatus;
72883 + pAd->StaCfg.PairCipher = pAd->StaCfg.OrigWepStatus;
72884 + pAd->StaCfg.GroupCipher = pAd->StaCfg.OrigWepStatus;
72885 +
72886 + BssIdx = pAd->MlmeAux.BssIdx;
72887 + if (BssIdx < pAd->MlmeAux.SsidBssTab.BssNr)
72888 + {
72889 + // Check cipher suite, AP must have more secured cipher than station setting
72890 + // Set the Pairwise and Group cipher to match the intended AP setting
72891 + // We can only connect to AP with less secured cipher setting
72892 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK))
72893 + {
72894 + pAd->StaCfg.GroupCipher = pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA.GroupCipher;
72895 +
72896 + if (pAd->StaCfg.WepStatus == pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA.PairCipher)
72897 + pAd->StaCfg.PairCipher = pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA.PairCipher;
72898 + else if (pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA.PairCipherAux != Ndis802_11WEPDisabled)
72899 + pAd->StaCfg.PairCipher = pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA.PairCipherAux;
72900 + else // There is no PairCipher Aux, downgrade our capability to TKIP
72901 + pAd->StaCfg.PairCipher = Ndis802_11Encryption2Enabled;
72902 + }
72903 + else if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
72904 + {
72905 + pAd->StaCfg.GroupCipher = pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA2.GroupCipher;
72906 +
72907 + if (pAd->StaCfg.WepStatus == pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA2.PairCipher)
72908 + pAd->StaCfg.PairCipher = pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA2.PairCipher;
72909 + else if (pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA2.PairCipherAux != Ndis802_11WEPDisabled)
72910 + pAd->StaCfg.PairCipher = pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA2.PairCipherAux;
72911 + else // There is no PairCipher Aux, downgrade our capability to TKIP
72912 + pAd->StaCfg.PairCipher = Ndis802_11Encryption2Enabled;
72913 +
72914 + // RSN capability
72915 + pAd->StaCfg.RsnCapability = pAd->MlmeAux.SsidBssTab.BssEntry[BssIdx].WPA2.RsnCapability;
72916 + }
72917 +
72918 + // Set Mix cipher flag
72919 + pAd->StaCfg.bMixCipher = (pAd->StaCfg.PairCipher == pAd->StaCfg.GroupCipher) ? FALSE : TRUE;
72920 + if (pAd->StaCfg.bMixCipher == TRUE)
72921 + {
72922 + // If mix cipher, re-build RSNIE
72923 + RTMPMakeRSNIE(pAd, pAd->StaCfg.AuthMode, pAd->StaCfg.WepStatus, 0);
72924 + }
72925 +
72926 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - iterate BSS %ld of %d\n", BssIdx, pAd->MlmeAux.SsidBssTab.BssNr));
72927 + JoinParmFill(pAd, &JoinReq, BssIdx);
72928 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_JOIN_REQ, sizeof(MLME_JOIN_REQ_STRUCT),
72929 + &JoinReq);
72930 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_JOIN;
72931 + }
72932 + else if (pAd->StaCfg.BssType == BSS_ADHOC)
72933 + {
72934 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - All BSS fail; start a new ADHOC (Ssid=%s)...\n",pAd->MlmeAux.Ssid));
72935 + StartParmFill(pAd, &StartReq, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen);
72936 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_MLME_START_REQ, sizeof(MLME_START_REQ_STRUCT), &StartReq);
72937 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_START;
72938 + }
72939 + else // no more BSS
72940 + {
72941 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - All roaming failed, stay @ ch #%d\n", pAd->CommonCfg.Channel));
72942 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
72943 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
72944 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
72945 + }
72946 +}
72947 +
72948 +// for re-association only
72949 +// IRQL = DISPATCH_LEVEL
72950 +VOID IterateOnBssTab2(
72951 + IN PRTMP_ADAPTER pAd)
72952 +{
72953 + MLME_REASSOC_REQ_STRUCT ReassocReq;
72954 + ULONG BssIdx;
72955 + BSS_ENTRY *pBss;
72956 +
72957 + BssIdx = pAd->MlmeAux.RoamIdx;
72958 + pBss = &pAd->MlmeAux.RoamTab.BssEntry[BssIdx];
72959 +
72960 + if (BssIdx < pAd->MlmeAux.RoamTab.BssNr)
72961 + {
72962 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - iterate BSS %ld of %d\n", BssIdx, pAd->MlmeAux.RoamTab.BssNr));
72963 +
72964 + AsicSwitchChannel(pAd, pBss->Channel, FALSE);
72965 + AsicLockChannel(pAd, pBss->Channel);
72966 +
72967 + // reassociate message has the same structure as associate message
72968 + AssocParmFill(pAd, &ReassocReq, pBss->Bssid, pBss->CapabilityInfo,
72969 + ASSOC_TIMEOUT, pAd->StaCfg.DefaultListenCount);
72970 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_REASSOC_REQ,
72971 + sizeof(MLME_REASSOC_REQ_STRUCT), &ReassocReq);
72972 +
72973 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_REASSOC;
72974 + }
72975 + else // no more BSS
72976 + {
72977 + DBGPRINT(RT_DEBUG_TRACE, ("CNTL - All fast roaming failed, back to ch #%d\n",pAd->CommonCfg.Channel));
72978 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
72979 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
72980 + pAd->Mlme.CntlMachine.CurrState = CNTL_IDLE;
72981 + }
72982 +}
72983 +
72984 +/*
72985 + ==========================================================================
72986 + Description:
72987 +
72988 + IRQL = DISPATCH_LEVEL
72989 +
72990 + ==========================================================================
72991 +*/
72992 +VOID JoinParmFill(
72993 + IN PRTMP_ADAPTER pAd,
72994 + IN OUT MLME_JOIN_REQ_STRUCT *JoinReq,
72995 + IN ULONG BssIdx)
72996 +{
72997 + JoinReq->BssIdx = BssIdx;
72998 +}
72999 +
73000 +/*
73001 + ==========================================================================
73002 + Description:
73003 +
73004 + IRQL = DISPATCH_LEVEL
73005 +
73006 + ==========================================================================
73007 +*/
73008 +VOID ScanParmFill(
73009 + IN PRTMP_ADAPTER pAd,
73010 + IN OUT MLME_SCAN_REQ_STRUCT *ScanReq,
73011 + IN CHAR Ssid[],
73012 + IN UCHAR SsidLen,
73013 + IN UCHAR BssType,
73014 + IN UCHAR ScanType)
73015 +{
73016 + NdisZeroMemory(ScanReq->Ssid, MAX_LEN_OF_SSID);
73017 + ScanReq->SsidLen = SsidLen;
73018 + NdisMoveMemory(ScanReq->Ssid, Ssid, SsidLen);
73019 + ScanReq->BssType = BssType;
73020 + ScanReq->ScanType = ScanType;
73021 +}
73022 +
73023 +#ifdef QOS_DLS_SUPPORT
73024 +/*
73025 + ==========================================================================
73026 + Description:
73027 +
73028 + IRQL = DISPATCH_LEVEL
73029 +
73030 + ==========================================================================
73031 +*/
73032 +VOID DlsParmFill(
73033 + IN PRTMP_ADAPTER pAd,
73034 + IN OUT MLME_DLS_REQ_STRUCT *pDlsReq,
73035 + IN PRT_802_11_DLS pDls,
73036 + IN USHORT reason)
73037 +{
73038 + pDlsReq->pDLS = pDls;
73039 + pDlsReq->Reason = reason;
73040 +}
73041 +#endif // QOS_DLS_SUPPORT //
73042 +
73043 +/*
73044 + ==========================================================================
73045 + Description:
73046 +
73047 + IRQL = DISPATCH_LEVEL
73048 +
73049 + ==========================================================================
73050 +*/
73051 +VOID StartParmFill(
73052 + IN PRTMP_ADAPTER pAd,
73053 + IN OUT MLME_START_REQ_STRUCT *StartReq,
73054 + IN CHAR Ssid[],
73055 + IN UCHAR SsidLen)
73056 +{
73057 + ASSERT(SsidLen <= MAX_LEN_OF_SSID);
73058 + NdisMoveMemory(StartReq->Ssid, Ssid, SsidLen);
73059 + StartReq->SsidLen = SsidLen;
73060 +}
73061 +
73062 +/*
73063 + ==========================================================================
73064 + Description:
73065 +
73066 + IRQL = DISPATCH_LEVEL
73067 +
73068 + ==========================================================================
73069 +*/
73070 +VOID AuthParmFill(
73071 + IN PRTMP_ADAPTER pAd,
73072 + IN OUT MLME_AUTH_REQ_STRUCT *AuthReq,
73073 + IN PUCHAR pAddr,
73074 + IN USHORT Alg)
73075 +{
73076 + COPY_MAC_ADDR(AuthReq->Addr, pAddr);
73077 + AuthReq->Alg = Alg;
73078 + AuthReq->Timeout = AUTH_TIMEOUT;
73079 +}
73080 +
73081 +/*
73082 + ==========================================================================
73083 + Description:
73084 +
73085 + IRQL = DISPATCH_LEVEL
73086 +
73087 + ==========================================================================
73088 + */
73089 +#ifdef RT2860
73090 +VOID ComposePsPoll(
73091 + IN PRTMP_ADAPTER pAd)
73092 +{
73093 + NdisZeroMemory(&pAd->PsPollFrame, sizeof(PSPOLL_FRAME));
73094 + pAd->PsPollFrame.FC.Type = BTYPE_CNTL;
73095 + pAd->PsPollFrame.FC.SubType = SUBTYPE_PS_POLL;
73096 + pAd->PsPollFrame.Aid = pAd->StaActive.Aid | 0xC000;
73097 + COPY_MAC_ADDR(pAd->PsPollFrame.Bssid, pAd->CommonCfg.Bssid);
73098 + COPY_MAC_ADDR(pAd->PsPollFrame.Ta, pAd->CurrentAddress);
73099 +}
73100 +
73101 +// IRQL = DISPATCH_LEVEL
73102 +VOID ComposeNullFrame(
73103 + IN PRTMP_ADAPTER pAd)
73104 +{
73105 + NdisZeroMemory(&pAd->NullFrame, sizeof(HEADER_802_11));
73106 + pAd->NullFrame.FC.Type = BTYPE_DATA;
73107 + pAd->NullFrame.FC.SubType = SUBTYPE_NULL_FUNC;
73108 + pAd->NullFrame.FC.ToDs = 1;
73109 + COPY_MAC_ADDR(pAd->NullFrame.Addr1, pAd->CommonCfg.Bssid);
73110 + COPY_MAC_ADDR(pAd->NullFrame.Addr2, pAd->CurrentAddress);
73111 + COPY_MAC_ADDR(pAd->NullFrame.Addr3, pAd->CommonCfg.Bssid);
73112 +}
73113 +#endif // RT2860 //
73114 +
73115 +
73116 +
73117 +
73118 +/*
73119 + ==========================================================================
73120 + Description:
73121 + Pre-build a BEACON frame in the shared memory
73122 +
73123 + IRQL = PASSIVE_LEVEL
73124 + IRQL = DISPATCH_LEVEL
73125 +
73126 + ==========================================================================
73127 +*/
73128 +ULONG MakeIbssBeacon(
73129 + IN PRTMP_ADAPTER pAd)
73130 +{
73131 + UCHAR DsLen = 1, IbssLen = 2;
73132 + UCHAR LocalErpIe[3] = {IE_ERP, 1, 0x04};
73133 + HEADER_802_11 BcnHdr;
73134 + USHORT CapabilityInfo;
73135 + LARGE_INTEGER FakeTimestamp;
73136 + ULONG FrameLen = 0;
73137 + PTXWI_STRUC pTxWI = &pAd->BeaconTxWI;
73138 + CHAR *pBeaconFrame = pAd->BeaconBuf;
73139 + BOOLEAN Privacy;
73140 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES];
73141 + UCHAR SupRateLen = 0;
73142 + UCHAR ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
73143 + UCHAR ExtRateLen = 0;
73144 + UCHAR RSNIe = IE_WPA;
73145 +
73146 + if ((pAd->CommonCfg.PhyMode == PHY_11B) && (pAd->CommonCfg.Channel <= 14))
73147 + {
73148 + SupRate[0] = 0x82; // 1 mbps
73149 + SupRate[1] = 0x84; // 2 mbps
73150 + SupRate[2] = 0x8b; // 5.5 mbps
73151 + SupRate[3] = 0x96; // 11 mbps
73152 + SupRateLen = 4;
73153 + ExtRateLen = 0;
73154 + }
73155 + else if (pAd->CommonCfg.Channel > 14)
73156 + {
73157 + SupRate[0] = 0x8C; // 6 mbps, in units of 0.5 Mbps, basic rate
73158 + SupRate[1] = 0x12; // 9 mbps, in units of 0.5 Mbps
73159 + SupRate[2] = 0x98; // 12 mbps, in units of 0.5 Mbps, basic rate
73160 + SupRate[3] = 0x24; // 18 mbps, in units of 0.5 Mbps
73161 + SupRate[4] = 0xb0; // 24 mbps, in units of 0.5 Mbps, basic rate
73162 + SupRate[5] = 0x48; // 36 mbps, in units of 0.5 Mbps
73163 + SupRate[6] = 0x60; // 48 mbps, in units of 0.5 Mbps
73164 + SupRate[7] = 0x6c; // 54 mbps, in units of 0.5 Mbps
73165 + SupRateLen = 8;
73166 + ExtRateLen = 0;
73167 +
73168 + //
73169 + // Also Update MlmeRate & RtsRate for G only & A only
73170 + //
73171 + pAd->CommonCfg.MlmeRate = RATE_6;
73172 + pAd->CommonCfg.RtsRate = RATE_6;
73173 + pAd->CommonCfg.MlmeTransmit.field.MODE = MODE_OFDM;
73174 + pAd->CommonCfg.MlmeTransmit.field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MlmeRate];
73175 + pAd->MacTab.Content[BSS0Mcast_WCID].HTPhyMode.field.MODE = MODE_OFDM;
73176 + pAd->MacTab.Content[BSS0Mcast_WCID].HTPhyMode.field.MCS = OfdmRateToRxwiMCS[pAd->CommonCfg.MlmeRate];
73177 + }
73178 + else
73179 + {
73180 + SupRate[0] = 0x82; // 1 mbps
73181 + SupRate[1] = 0x84; // 2 mbps
73182 + SupRate[2] = 0x8b; // 5.5 mbps
73183 + SupRate[3] = 0x96; // 11 mbps
73184 + SupRateLen = 4;
73185 +
73186 + ExtRate[0] = 0x0C; // 6 mbps, in units of 0.5 Mbps,
73187 + ExtRate[1] = 0x12; // 9 mbps, in units of 0.5 Mbps
73188 + ExtRate[2] = 0x18; // 12 mbps, in units of 0.5 Mbps,
73189 + ExtRate[3] = 0x24; // 18 mbps, in units of 0.5 Mbps
73190 + ExtRate[4] = 0x30; // 24 mbps, in units of 0.5 Mbps,
73191 + ExtRate[5] = 0x48; // 36 mbps, in units of 0.5 Mbps
73192 + ExtRate[6] = 0x60; // 48 mbps, in units of 0.5 Mbps
73193 + ExtRate[7] = 0x6c; // 54 mbps, in units of 0.5 Mbps
73194 + ExtRateLen = 8;
73195 + }
73196 +
73197 + pAd->StaActive.SupRateLen = SupRateLen;
73198 + NdisMoveMemory(pAd->StaActive.SupRate, SupRate, SupRateLen);
73199 + pAd->StaActive.ExtRateLen = ExtRateLen;
73200 + NdisMoveMemory(pAd->StaActive.ExtRate, ExtRate, ExtRateLen);
73201 +
73202 + // compose IBSS beacon frame
73203 + MgtMacHeaderInit(pAd, &BcnHdr, SUBTYPE_BEACON, 0, BROADCAST_ADDR, pAd->CommonCfg.Bssid);
73204 + Privacy = (pAd->StaCfg.WepStatus == Ndis802_11Encryption1Enabled) ||
73205 + (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) ||
73206 + (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled);
73207 + CapabilityInfo = CAP_GENERATE(0, 1, Privacy, (pAd->CommonCfg.TxPreamble == Rt802_11PreambleShort), 0, 0);
73208 +
73209 + MakeOutgoingFrame(pBeaconFrame, &FrameLen,
73210 + sizeof(HEADER_802_11), &BcnHdr,
73211 + TIMESTAMP_LEN, &FakeTimestamp,
73212 + 2, &pAd->CommonCfg.BeaconPeriod,
73213 + 2, &CapabilityInfo,
73214 + 1, &SsidIe,
73215 + 1, &pAd->CommonCfg.SsidLen,
73216 + pAd->CommonCfg.SsidLen, pAd->CommonCfg.Ssid,
73217 + 1, &SupRateIe,
73218 + 1, &SupRateLen,
73219 + SupRateLen, SupRate,
73220 + 1, &DsIe,
73221 + 1, &DsLen,
73222 + 1, &pAd->CommonCfg.Channel,
73223 + 1, &IbssIe,
73224 + 1, &IbssLen,
73225 + 2, &pAd->StaActive.AtimWin,
73226 + END_OF_ARGS);
73227 +
73228 + // add ERP_IE and EXT_RAE IE of in 802.11g
73229 + if (ExtRateLen)
73230 + {
73231 + ULONG tmp;
73232 +
73233 + MakeOutgoingFrame(pBeaconFrame + FrameLen, &tmp,
73234 + 3, LocalErpIe,
73235 + 1, &ExtRateIe,
73236 + 1, &ExtRateLen,
73237 + ExtRateLen, ExtRate,
73238 + END_OF_ARGS);
73239 + FrameLen += tmp;
73240 + }
73241 +
73242 + // If adhoc secruity is set for WPA-None, append the cipher suite IE
73243 + if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
73244 + {
73245 + ULONG tmp;
73246 + RTMPMakeRSNIE(pAd, pAd->StaCfg.AuthMode, pAd->StaCfg.WepStatus, BSS0);
73247 +
73248 + MakeOutgoingFrame(pBeaconFrame + FrameLen, &tmp,
73249 + 1, &RSNIe,
73250 + 1, &pAd->StaCfg.RSNIE_Len,
73251 + pAd->StaCfg.RSNIE_Len, pAd->StaCfg.RSN_IE,
73252 + END_OF_ARGS);
73253 + FrameLen += tmp;
73254 + }
73255 +
73256 +#ifdef DOT11_N_SUPPORT
73257 + if ((pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
73258 + {
73259 + ULONG TmpLen;
73260 + UCHAR HtLen, HtLen1;
73261 +
73262 +#ifdef RT_BIG_ENDIAN
73263 + HT_CAPABILITY_IE HtCapabilityTmp;
73264 + ADD_HT_INFO_IE addHTInfoTmp;
73265 + USHORT b2lTmp, b2lTmp2;
73266 +#endif
73267 +
73268 + // add HT Capability IE
73269 + HtLen = sizeof(pAd->CommonCfg.HtCapability);
73270 + HtLen1 = sizeof(pAd->CommonCfg.AddHTInfo);
73271 +#ifndef RT_BIG_ENDIAN
73272 + MakeOutgoingFrame(pBeaconFrame+FrameLen, &TmpLen,
73273 + 1, &HtCapIe,
73274 + 1, &HtLen,
73275 + HtLen, &pAd->CommonCfg.HtCapability,
73276 + 1, &AddHtInfoIe,
73277 + 1, &HtLen1,
73278 + HtLen1, &pAd->CommonCfg.AddHTInfo,
73279 + END_OF_ARGS);
73280 +#else
73281 + NdisMoveMemory(&HtCapabilityTmp, &pAd->CommonCfg.HtCapability, HtLen);
73282 + *(USHORT *)(&HtCapabilityTmp.HtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.HtCapInfo));
73283 + *(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo));
73284 +
73285 + NdisMoveMemory(&addHTInfoTmp, &pAd->CommonCfg.AddHTInfo, HtLen1);
73286 + *(USHORT *)(&addHTInfoTmp.AddHtInfo2) = SWAP16(*(USHORT *)(&addHTInfoTmp.AddHtInfo2));
73287 + *(USHORT *)(&addHTInfoTmp.AddHtInfo3) = SWAP16(*(USHORT *)(&addHTInfoTmp.AddHtInfo3));
73288 +
73289 + MakeOutgoingFrame(pBeaconFrame+FrameLen, &TmpLen,
73290 + 1, &HtCapIe,
73291 + 1, &HtLen,
73292 + HtLen, &HtCapabilityTmp,
73293 + 1, &AddHtInfoIe,
73294 + 1, &HtLen1,
73295 + HtLen1, &addHTInfoTmp,
73296 + END_OF_ARGS);
73297 +#endif
73298 + FrameLen += TmpLen;
73299 + }
73300 +#endif // DOT11_N_SUPPORT //
73301 +
73302 + //beacon use reserved WCID 0xff
73303 + if (pAd->CommonCfg.Channel > 14)
73304 + {
73305 + RTMPWriteTxWI(pAd, pTxWI, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, 0, 0xff, FrameLen,
73306 + PID_MGMT, PID_BEACON, RATE_1, IFS_HTTXOP, FALSE, &pAd->CommonCfg.MlmeTransmit);
73307 + }
73308 + else
73309 + {
73310 + // Set to use 1Mbps for Adhoc beacon.
73311 + HTTRANSMIT_SETTING Transmit;
73312 + Transmit.word = 0;
73313 + RTMPWriteTxWI(pAd, pTxWI, FALSE, FALSE, TRUE, FALSE, FALSE, TRUE, 0, 0xff, FrameLen,
73314 + PID_MGMT, PID_BEACON, RATE_1, IFS_HTTXOP, FALSE, &Transmit);
73315 + }
73316 +
73317 +#ifdef RT_BIG_ENDIAN
73318 + RTMPFrameEndianChange(pAd, pBeaconFrame, DIR_WRITE, FALSE);
73319 + RTMPWIEndianChange((PUCHAR)pTxWI, TYPE_TXWI);
73320 +#endif
73321 +
73322 + DBGPRINT(RT_DEBUG_TRACE, ("MakeIbssBeacon (len=%ld), SupRateLen=%d, ExtRateLen=%d, Channel=%d, PhyMode=%d\n",
73323 + FrameLen, SupRateLen, ExtRateLen, pAd->CommonCfg.Channel, pAd->CommonCfg.PhyMode));
73324 + return FrameLen;
73325 +}
73326 +
73327 +
73328 --- /dev/null
73329 +++ b/drivers/staging/rt2860/sta/dls.c
73330 @@ -0,0 +1,2201 @@
73331 +/*
73332 + *************************************************************************
73333 + * Ralink Tech Inc.
73334 + * 5F., No.36, Taiyuan St., Jhubei City,
73335 + * Hsinchu County 302,
73336 + * Taiwan, R.O.C.
73337 + *
73338 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
73339 + *
73340 + * This program is free software; you can redistribute it and/or modify *
73341 + * it under the terms of the GNU General Public License as published by *
73342 + * the Free Software Foundation; either version 2 of the License, or *
73343 + * (at your option) any later version. *
73344 + * *
73345 + * This program is distributed in the hope that it will be useful, *
73346 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
73347 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
73348 + * GNU General Public License for more details. *
73349 + * *
73350 + * You should have received a copy of the GNU General Public License *
73351 + * along with this program; if not, write to the *
73352 + * Free Software Foundation, Inc., *
73353 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
73354 + * *
73355 + *************************************************************************
73356 +
73357 + Module Name:
73358 + dls.c
73359 +
73360 + Abstract:
73361 + Handle WMM-DLS state machine
73362 +
73363 + Revision History:
73364 + Who When What
73365 + -------- ---------- ----------------------------------------------
73366 + Rory Chen 02-14-2006
73367 + Arvin Tai 06-03-2008 Modified for RT28xx
73368 + */
73369 +
73370 +#include "../rt_config.h"
73371 +
73372 +/*
73373 + ==========================================================================
73374 + Description:
73375 + dls state machine init, including state transition and timer init
73376 + Parameters:
73377 + Sm - pointer to the dls state machine
73378 + Note:
73379 + The state machine looks like this
73380 +
73381 + DLS_IDLE
73382 + MT2_MLME_DLS_REQUEST MlmeDlsReqAction
73383 + MT2_PEER_DLS_REQUEST PeerDlsReqAction
73384 + MT2_PEER_DLS_RESPONSE PeerDlsRspAction
73385 + MT2_MLME_DLS_TEARDOWN MlmeTearDownAction
73386 + MT2_PEER_DLS_TEARDOWN PeerTearDownAction
73387 +
73388 + IRQL = PASSIVE_LEVEL
73389 +
73390 + ==========================================================================
73391 + */
73392 +void DlsStateMachineInit(
73393 + IN PRTMP_ADAPTER pAd,
73394 + IN STATE_MACHINE *Sm,
73395 + OUT STATE_MACHINE_FUNC Trans[])
73396 +{
73397 + UCHAR i;
73398 +
73399 + StateMachineInit(Sm, (STATE_MACHINE_FUNC*)Trans, MAX_DLS_STATE, MAX_DLS_MSG, (STATE_MACHINE_FUNC)Drop, DLS_IDLE, DLS_MACHINE_BASE);
73400 +
73401 + // the first column
73402 + StateMachineSetAction(Sm, DLS_IDLE, MT2_MLME_DLS_REQ, (STATE_MACHINE_FUNC)MlmeDlsReqAction);
73403 + StateMachineSetAction(Sm, DLS_IDLE, MT2_PEER_DLS_REQ, (STATE_MACHINE_FUNC)PeerDlsReqAction);
73404 + StateMachineSetAction(Sm, DLS_IDLE, MT2_PEER_DLS_RSP, (STATE_MACHINE_FUNC)PeerDlsRspAction);
73405 + StateMachineSetAction(Sm, DLS_IDLE, MT2_MLME_DLS_TEAR_DOWN, (STATE_MACHINE_FUNC)MlmeDlsTearDownAction);
73406 + StateMachineSetAction(Sm, DLS_IDLE, MT2_PEER_DLS_TEAR_DOWN, (STATE_MACHINE_FUNC)PeerDlsTearDownAction);
73407 +
73408 + for (i=0; i<MAX_NUM_OF_DLS_ENTRY; i++)
73409 + {
73410 + pAd->StaCfg.DLSEntry[i].pAd = pAd;
73411 + RTMPInitTimer(pAd, &pAd->StaCfg.DLSEntry[i].Timer, GET_TIMER_FUNCTION(DlsTimeoutAction), pAd, FALSE);
73412 + }
73413 +}
73414 +
73415 +/*
73416 + ==========================================================================
73417 + Description:
73418 +
73419 + IRQL = DISPATCH_LEVEL
73420 +
73421 + ==========================================================================
73422 + */
73423 +VOID MlmeDlsReqAction(
73424 + IN PRTMP_ADAPTER pAd,
73425 + IN MLME_QUEUE_ELEM *Elem)
73426 +{
73427 + PUCHAR pOutBuffer = NULL;
73428 + NDIS_STATUS NStatus;
73429 + ULONG FrameLen = 0;
73430 + HEADER_802_11 DlsReqHdr;
73431 + PRT_802_11_DLS pDLS = NULL;
73432 + UCHAR Category = CATEGORY_DLS;
73433 + UCHAR Action = ACTION_DLS_REQUEST;
73434 + ULONG tmp;
73435 + USHORT reason;
73436 + ULONG Timeout;
73437 + BOOLEAN TimerCancelled;
73438 +
73439 + if(!MlmeDlsReqSanity(pAd, Elem->Msg, Elem->MsgLen, &pDLS, &reason))
73440 + return;
73441 +
73442 + DBGPRINT(RT_DEBUG_TRACE,("DLS - MlmeDlsReqAction() \n"));
73443 +
73444 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
73445 + if (NStatus != NDIS_STATUS_SUCCESS)
73446 + {
73447 + DBGPRINT(RT_DEBUG_ERROR,("DLS - MlmeDlsReqAction() allocate memory failed \n"));
73448 + return;
73449 + }
73450 +
73451 + ActHeaderInit(pAd, &DlsReqHdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
73452 +
73453 + // Build basic frame first
73454 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
73455 + sizeof(HEADER_802_11), &DlsReqHdr,
73456 + 1, &Category,
73457 + 1, &Action,
73458 + 6, &pDLS->MacAddr,
73459 + 6, pAd->CurrentAddress,
73460 + 2, &pAd->StaActive.CapabilityInfo,
73461 + 2, &pDLS->TimeOut,
73462 + 1, &SupRateIe,
73463 + 1, &pAd->MlmeAux.SupRateLen,
73464 + pAd->MlmeAux.SupRateLen, pAd->MlmeAux.SupRate,
73465 + END_OF_ARGS);
73466 +
73467 + if (pAd->MlmeAux.ExtRateLen != 0)
73468 + {
73469 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
73470 + 1, &ExtRateIe,
73471 + 1, &pAd->MlmeAux.ExtRateLen,
73472 + pAd->MlmeAux.ExtRateLen, pAd->MlmeAux.ExtRate,
73473 + END_OF_ARGS);
73474 + FrameLen += tmp;
73475 + }
73476 +
73477 +#ifdef DOT11_N_SUPPORT
73478 + if ((pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
73479 + {
73480 + UCHAR HtLen;
73481 +
73482 +#ifdef RT_BIG_ENDIAN
73483 + HT_CAPABILITY_IE HtCapabilityTmp;
73484 +#endif
73485 +
73486 + // add HT Capability IE
73487 + HtLen = sizeof(HT_CAPABILITY_IE);
73488 +#ifndef RT_BIG_ENDIAN
73489 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
73490 + 1, &HtCapIe,
73491 + 1, &HtLen,
73492 + HtLen, &pAd->CommonCfg.HtCapability,
73493 + END_OF_ARGS);
73494 +#else
73495 + NdisMoveMemory(&HtCapabilityTmp, &pAd->CommonCfg.HtCapability, HtLen);
73496 + *(USHORT *)(&HtCapabilityTmp.HtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.HtCapInfo));
73497 + *(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo));
73498 +
73499 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
73500 + 1, &HtCapIe,
73501 + 1, &HtLen,
73502 + HtLen, &HtCapabilityTmp,
73503 + END_OF_ARGS);
73504 +#endif
73505 + FrameLen = FrameLen + tmp;
73506 + }
73507 +#endif // DOT11_N_SUPPORT //
73508 +
73509 + RTMPCancelTimer(&pDLS->Timer, &TimerCancelled);
73510 + Timeout = DLS_TIMEOUT;
73511 + RTMPSetTimer(&pDLS->Timer, Timeout);
73512 +
73513 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
73514 + MlmeFreeMemory(pAd, pOutBuffer);
73515 +}
73516 +
73517 +/*
73518 + ==========================================================================
73519 + Description:
73520 +
73521 + IRQL = DISPATCH_LEVEL
73522 +
73523 + ==========================================================================
73524 + */
73525 +VOID PeerDlsReqAction(
73526 + IN PRTMP_ADAPTER pAd,
73527 + IN MLME_QUEUE_ELEM *Elem)
73528 +{
73529 + PUCHAR pOutBuffer = NULL;
73530 + NDIS_STATUS NStatus;
73531 + ULONG FrameLen = 0;
73532 + USHORT StatusCode = MLME_SUCCESS;
73533 + HEADER_802_11 DlsRspHdr;
73534 + UCHAR Category = CATEGORY_DLS;
73535 + UCHAR Action = ACTION_DLS_RESPONSE;
73536 + ULONG tmp;
73537 + USHORT CapabilityInfo;
73538 + UCHAR DA[MAC_ADDR_LEN], SA[MAC_ADDR_LEN];
73539 + USHORT DLSTimeOut;
73540 + SHORT i;
73541 + ULONG Timeout;
73542 + BOOLEAN TimerCancelled;
73543 + PRT_802_11_DLS pDLS = NULL;
73544 + UCHAR MaxSupportedRateIn500Kbps = 0;
73545 + UCHAR SupportedRatesLen;
73546 + UCHAR SupportedRates[MAX_LEN_OF_SUPPORTED_RATES];
73547 + UCHAR HtCapabilityLen;
73548 + HT_CAPABILITY_IE HtCapability;
73549 +
73550 + if (!PeerDlsReqSanity(pAd, Elem->Msg, Elem->MsgLen, DA, SA, &CapabilityInfo, &DLSTimeOut,
73551 + &SupportedRatesLen, &SupportedRates[0], &HtCapabilityLen, &HtCapability))
73552 + return;
73553 +
73554 + // supported rates array may not be sorted. sort it and find the maximum rate
73555 + for (i = 0; i < SupportedRatesLen; i++)
73556 + {
73557 + if (MaxSupportedRateIn500Kbps < (SupportedRates[i] & 0x7f))
73558 + MaxSupportedRateIn500Kbps = SupportedRates[i] & 0x7f;
73559 + }
73560 +
73561 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsReqAction() from %02x:%02x:%02x:%02x:%02x:%02x\n", SA[0], SA[1], SA[2], SA[3], SA[4], SA[5]));
73562 +
73563 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
73564 + if (NStatus != NDIS_STATUS_SUCCESS)
73565 + {
73566 + DBGPRINT(RT_DEBUG_ERROR,("DLS - PeerDlsReqAction() allocate memory failed \n"));
73567 + return;
73568 + }
73569 +
73570 + if (!INFRA_ON(pAd))
73571 + {
73572 + StatusCode = MLME_REQUEST_DECLINED;
73573 + }
73574 + else if (!pAd->CommonCfg.bWmmCapable)
73575 + {
73576 + StatusCode = MLME_DEST_STA_IS_NOT_A_QSTA;
73577 + }
73578 + else if (!pAd->CommonCfg.bDLSCapable)
73579 + {
73580 + StatusCode = MLME_REQUEST_DECLINED;
73581 + }
73582 + else
73583 + {
73584 + // find table to update parameters
73585 + for (i = (MAX_NUM_OF_DLS_ENTRY-1); i >= 0; i--)
73586 + {
73587 + if (pAd->StaCfg.DLSEntry[i].Valid && MAC_ADDR_EQUAL(SA, pAd->StaCfg.DLSEntry[i].MacAddr))
73588 + {
73589 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
73590 + pAd->StaCfg.DLSEntry[i].Status = DLS_WAIT_KEY;
73591 + else
73592 + {
73593 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
73594 + pAd->StaCfg.DLSEntry[i].Status = DLS_FINISH;
73595 + }
73596 +
73597 + pAd->StaCfg.DLSEntry[i].Sequence = 0;
73598 + pAd->StaCfg.DLSEntry[i].TimeOut = DLSTimeOut;
73599 + pAd->StaCfg.DLSEntry[i].CountDownTimer = DLSTimeOut;
73600 + if (HtCapabilityLen != 0)
73601 + pAd->StaCfg.DLSEntry[i].bHTCap = TRUE;
73602 + else
73603 + pAd->StaCfg.DLSEntry[i].bHTCap = FALSE;
73604 + pDLS = &pAd->StaCfg.DLSEntry[i];
73605 + break;
73606 + }
73607 + }
73608 +
73609 + // can not find in table, create a new one
73610 + if (i < 0)
73611 + {
73612 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsReqAction() can not find same entry \n"));
73613 + for (i=(MAX_NUM_OF_DLS_ENTRY - 1); i >= MAX_NUM_OF_INIT_DLS_ENTRY; i--)
73614 + {
73615 + if (!pAd->StaCfg.DLSEntry[i].Valid)
73616 + {
73617 + MAC_TABLE_ENTRY *pEntry;
73618 + UCHAR MaxSupportedRate = RATE_11;
73619 +
73620 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
73621 + {
73622 + pAd->StaCfg.DLSEntry[i].Status = DLS_WAIT_KEY;
73623 + }
73624 + else
73625 + {
73626 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
73627 + pAd->StaCfg.DLSEntry[i].Status = DLS_FINISH;
73628 + }
73629 +
73630 + pAd->StaCfg.DLSEntry[i].Sequence = 0;
73631 + pAd->StaCfg.DLSEntry[i].Valid = TRUE;
73632 + pAd->StaCfg.DLSEntry[i].TimeOut = DLSTimeOut;
73633 + pAd->StaCfg.DLSEntry[i].CountDownTimer = DLSTimeOut;
73634 + NdisMoveMemory(pAd->StaCfg.DLSEntry[i].MacAddr, SA, MAC_ADDR_LEN);
73635 + if (HtCapabilityLen != 0)
73636 + pAd->StaCfg.DLSEntry[i].bHTCap = TRUE;
73637 + else
73638 + pAd->StaCfg.DLSEntry[i].bHTCap = FALSE;
73639 + pDLS = &pAd->StaCfg.DLSEntry[i];
73640 + pEntry = MacTableInsertDlsEntry(pAd, SA, i);
73641 +
73642 + switch (MaxSupportedRateIn500Kbps)
73643 + {
73644 + case 108: MaxSupportedRate = RATE_54; break;
73645 + case 96: MaxSupportedRate = RATE_48; break;
73646 + case 72: MaxSupportedRate = RATE_36; break;
73647 + case 48: MaxSupportedRate = RATE_24; break;
73648 + case 36: MaxSupportedRate = RATE_18; break;
73649 + case 24: MaxSupportedRate = RATE_12; break;
73650 + case 18: MaxSupportedRate = RATE_9; break;
73651 + case 12: MaxSupportedRate = RATE_6; break;
73652 + case 22: MaxSupportedRate = RATE_11; break;
73653 + case 11: MaxSupportedRate = RATE_5_5; break;
73654 + case 4: MaxSupportedRate = RATE_2; break;
73655 + case 2: MaxSupportedRate = RATE_1; break;
73656 + default: MaxSupportedRate = RATE_11; break;
73657 + }
73658 +
73659 + pEntry->MaxSupportedRate = min(pAd->CommonCfg.MaxTxRate, MaxSupportedRate);
73660 +
73661 + if (pEntry->MaxSupportedRate < RATE_FIRST_OFDM_RATE)
73662 + {
73663 + pEntry->MaxHTPhyMode.field.MODE = MODE_CCK;
73664 + pEntry->MaxHTPhyMode.field.MCS = pEntry->MaxSupportedRate;
73665 + pEntry->MinHTPhyMode.field.MODE = MODE_CCK;
73666 + pEntry->MinHTPhyMode.field.MCS = pEntry->MaxSupportedRate;
73667 + pEntry->HTPhyMode.field.MODE = MODE_CCK;
73668 + pEntry->HTPhyMode.field.MCS = pEntry->MaxSupportedRate;
73669 + }
73670 + else
73671 + {
73672 + pEntry->MaxHTPhyMode.field.MODE = MODE_OFDM;
73673 + pEntry->MaxHTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
73674 + pEntry->MinHTPhyMode.field.MODE = MODE_OFDM;
73675 + pEntry->MinHTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
73676 + pEntry->HTPhyMode.field.MODE = MODE_OFDM;
73677 + pEntry->HTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
73678 + }
73679 +
73680 + pEntry->MaxHTPhyMode.field.BW = BW_20;
73681 + pEntry->MinHTPhyMode.field.BW = BW_20;
73682 +
73683 +#ifdef DOT11_N_SUPPORT
73684 + pEntry->HTCapability.MCSSet[0] = 0;
73685 + pEntry->HTCapability.MCSSet[1] = 0;
73686 +
73687 + // If this Entry supports 802.11n, upgrade to HT rate.
73688 + if ((HtCapabilityLen != 0) && (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
73689 + {
73690 + UCHAR j, bitmask; //k,bitmask;
73691 + CHAR ii;
73692 +
73693 + DBGPRINT(RT_DEBUG_OFF, ("DLS - PeerDlsReqAction() Receive Peer HT Capable STA from %02x:%02x:%02x:%02x:%02x:%02x\n",
73694 + SA[0], SA[1], SA[2], SA[3], SA[4], SA[5]));
73695 +
73696 + if ((HtCapability.HtCapInfo.GF) && (pAd->CommonCfg.DesiredHtPhy.GF))
73697 + {
73698 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTGREENFIELD;
73699 + }
73700 + else
73701 + {
73702 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTMIX;
73703 + pAd->MacTab.fAnyStationNonGF = TRUE;
73704 + pAd->CommonCfg.AddHTInfo.AddHtInfo2.NonGfPresent = 1;
73705 + }
73706 +
73707 + if ((HtCapability.HtCapInfo.ChannelWidth) && (pAd->CommonCfg.DesiredHtPhy.ChannelWidth))
73708 + {
73709 + pEntry->MaxHTPhyMode.field.BW= BW_40;
73710 + pEntry->MaxHTPhyMode.field.ShortGI = ((pAd->CommonCfg.DesiredHtPhy.ShortGIfor40)&(HtCapability.HtCapInfo.ShortGIfor40));
73711 + }
73712 + else
73713 + {
73714 + pEntry->MaxHTPhyMode.field.BW = BW_20;
73715 + pEntry->MaxHTPhyMode.field.ShortGI = ((pAd->CommonCfg.DesiredHtPhy.ShortGIfor20)&(HtCapability.HtCapInfo.ShortGIfor20));
73716 + pAd->MacTab.fAnyStation20Only = TRUE;
73717 + }
73718 +
73719 + // find max fixed rate
73720 + for (ii=15; ii>=0; ii--)
73721 + {
73722 + j = ii/8;
73723 + bitmask = (1<<(ii-(j*8)));
73724 + if ( (pAd->StaCfg.DesiredHtPhyInfo.MCSSet[j]&bitmask) && (HtCapability.MCSSet[j]&bitmask))
73725 + {
73726 + pEntry->MaxHTPhyMode.field.MCS = ii;
73727 + break;
73728 + }
73729 + if (ii==0)
73730 + break;
73731 + }
73732 +
73733 +
73734 + if (pAd->StaCfg.DesiredTransmitSetting.field.MCS != MCS_AUTO)
73735 + {
73736 +
73737 + printk("@@@ pAd->CommonCfg.RegTransmitSetting.field.MCS = %d\n",
73738 + pAd->StaCfg.DesiredTransmitSetting.field.MCS);
73739 + if (pAd->StaCfg.DesiredTransmitSetting.field.MCS == 32)
73740 + {
73741 + // Fix MCS as HT Duplicated Mode
73742 + pEntry->MaxHTPhyMode.field.BW = 1;
73743 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTMIX;
73744 + pEntry->MaxHTPhyMode.field.STBC = 0;
73745 + pEntry->MaxHTPhyMode.field.ShortGI = 0;
73746 + pEntry->MaxHTPhyMode.field.MCS = 32;
73747 + }
73748 + else if (pEntry->MaxHTPhyMode.field.MCS > pAd->StaCfg.HTPhyMode.field.MCS)
73749 + {
73750 + // STA supports fixed MCS
73751 + pEntry->MaxHTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
73752 + }
73753 + }
73754 +
73755 + pEntry->MaxHTPhyMode.field.STBC = (HtCapability.HtCapInfo.RxSTBC & (pAd->CommonCfg.DesiredHtPhy.TxSTBC));
73756 + pEntry->MpduDensity = HtCapability.HtCapParm.MpduDensity;
73757 + pEntry->MaxRAmpduFactor = HtCapability.HtCapParm.MaxRAmpduFactor;
73758 + pEntry->MmpsMode = (UCHAR)HtCapability.HtCapInfo.MimoPs;
73759 + pEntry->AMsduSize = (UCHAR)HtCapability.HtCapInfo.AMsduSize;
73760 + pEntry->HTPhyMode.word = pEntry->MaxHTPhyMode.word;
73761 +
73762 + if (HtCapability.HtCapInfo.ShortGIfor20)
73763 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_SGI20_CAPABLE);
73764 + if (HtCapability.HtCapInfo.ShortGIfor40)
73765 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_SGI40_CAPABLE);
73766 + if (HtCapability.HtCapInfo.TxSTBC)
73767 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_TxSTBC_CAPABLE);
73768 + if (HtCapability.HtCapInfo.RxSTBC)
73769 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_RxSTBC_CAPABLE);
73770 + if (HtCapability.ExtHtCapInfo.PlusHTC)
73771 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_HTC_CAPABLE);
73772 + if (pAd->CommonCfg.bRdg && HtCapability.ExtHtCapInfo.RDGSupport)
73773 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_RDG_CAPABLE);
73774 + if (HtCapability.ExtHtCapInfo.MCSFeedback == 0x03)
73775 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_MCSFEEDBACK_CAPABLE);
73776 +
73777 + NdisMoveMemory(&pEntry->HTCapability, &HtCapability, sizeof(HT_CAPABILITY_IE));
73778 + }
73779 +#endif // DOT11_N_SUPPORT //
73780 +
73781 + pEntry->HTPhyMode.word = pEntry->MaxHTPhyMode.word;
73782 + pEntry->CurrTxRate = pEntry->MaxSupportedRate;
73783 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_WMM_CAPABLE);
73784 +
73785 + if (pAd->StaCfg.bAutoTxRateSwitch == TRUE)
73786 + {
73787 + PUCHAR pTable;
73788 + UCHAR TableSize = 0;
73789 +
73790 + MlmeSelectTxRateTable(pAd, pEntry, &pTable, &TableSize, &pEntry->CurrTxRateIndex);
73791 + pEntry->bAutoTxRateSwitch = TRUE;
73792 + }
73793 + else
73794 + {
73795 + pEntry->HTPhyMode.field.MODE = pAd->StaCfg.HTPhyMode.field.MODE;
73796 + pEntry->HTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
73797 + pEntry->bAutoTxRateSwitch = FALSE;
73798 +
73799 + RTMPUpdateLegacyTxSetting((UCHAR)pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode, pEntry);
73800 + }
73801 + pEntry->RateLen = SupportedRatesLen;
73802 +
73803 + break;
73804 + }
73805 + }
73806 + }
73807 + StatusCode = MLME_SUCCESS;
73808 +
73809 + // can not find in table, create a new one
73810 + if (i < 0)
73811 + {
73812 + StatusCode = MLME_QOS_UNSPECIFY;
73813 + DBGPRINT(RT_DEBUG_ERROR,("DLS - PeerDlsReqAction() DLSEntry table full(only can support %d DLS session) \n", MAX_NUM_OF_DLS_ENTRY - MAX_NUM_OF_INIT_DLS_ENTRY));
73814 + }
73815 + else
73816 + {
73817 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsReqAction() use entry(%d) %02x:%02x:%02x:%02x:%02x:%02x\n",
73818 + i, SA[0], SA[1], SA[2], SA[3], SA[4], SA[5]));
73819 + }
73820 + }
73821 +
73822 + ActHeaderInit(pAd, &DlsRspHdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
73823 +
73824 + // Build basic frame first
73825 + if (StatusCode == MLME_SUCCESS)
73826 + {
73827 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
73828 + sizeof(HEADER_802_11), &DlsRspHdr,
73829 + 1, &Category,
73830 + 1, &Action,
73831 + 2, &StatusCode,
73832 + 6, SA,
73833 + 6, pAd->CurrentAddress,
73834 + 2, &pAd->StaActive.CapabilityInfo,
73835 + 1, &SupRateIe,
73836 + 1, &pAd->MlmeAux.SupRateLen,
73837 + pAd->MlmeAux.SupRateLen, pAd->MlmeAux.SupRate,
73838 + END_OF_ARGS);
73839 +
73840 + if (pAd->MlmeAux.ExtRateLen != 0)
73841 + {
73842 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
73843 + 1, &ExtRateIe,
73844 + 1, &pAd->MlmeAux.ExtRateLen,
73845 + pAd->MlmeAux.ExtRateLen, pAd->MlmeAux.ExtRate,
73846 + END_OF_ARGS);
73847 + FrameLen += tmp;
73848 + }
73849 +
73850 +#ifdef DOT11_N_SUPPORT
73851 + if ((pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
73852 + {
73853 + UCHAR HtLen;
73854 +
73855 +#ifdef RT_BIG_ENDIAN
73856 + HT_CAPABILITY_IE HtCapabilityTmp;
73857 +#endif
73858 +
73859 + // add HT Capability IE
73860 + HtLen = sizeof(HT_CAPABILITY_IE);
73861 +#ifndef RT_BIG_ENDIAN
73862 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
73863 + 1, &HtCapIe,
73864 + 1, &HtLen,
73865 + HtLen, &pAd->CommonCfg.HtCapability,
73866 + END_OF_ARGS);
73867 +#else
73868 + NdisMoveMemory(&HtCapabilityTmp, &pAd->CommonCfg.HtCapability, HtLen);
73869 + *(USHORT *)(&HtCapabilityTmp.HtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.HtCapInfo));
73870 + *(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo) = SWAP16(*(USHORT *)(&HtCapabilityTmp.ExtHtCapInfo));
73871 +
73872 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
73873 + 1, &HtCapIe,
73874 + 1, &HtLen,
73875 + HtLen, &HtCapabilityTmp,
73876 + END_OF_ARGS);
73877 +#endif
73878 + FrameLen = FrameLen + tmp;
73879 + }
73880 +#endif // DOT11_N_SUPPORT //
73881 +
73882 + if (pDLS && (pDLS->Status != DLS_FINISH))
73883 + {
73884 + RTMPCancelTimer(&pDLS->Timer, &TimerCancelled);
73885 + Timeout = DLS_TIMEOUT;
73886 + RTMPSetTimer(&pDLS->Timer, Timeout);
73887 + }
73888 + }
73889 + else
73890 + {
73891 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
73892 + sizeof(HEADER_802_11), &DlsRspHdr,
73893 + 1, &Category,
73894 + 1, &Action,
73895 + 2, &StatusCode,
73896 + 6, SA,
73897 + 6, pAd->CurrentAddress,
73898 + END_OF_ARGS);
73899 + }
73900 +
73901 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
73902 + MlmeFreeMemory(pAd, pOutBuffer);
73903 +}
73904 +
73905 +/*
73906 + ==========================================================================
73907 + Description:
73908 +
73909 + IRQL = DISPATCH_LEVEL
73910 +
73911 + ==========================================================================
73912 + */
73913 +VOID PeerDlsRspAction(
73914 + IN PRTMP_ADAPTER pAd,
73915 + IN MLME_QUEUE_ELEM *Elem)
73916 +{
73917 + USHORT CapabilityInfo;
73918 + UCHAR DA[MAC_ADDR_LEN], SA[MAC_ADDR_LEN];
73919 + USHORT StatusCode;
73920 + SHORT i;
73921 + BOOLEAN TimerCancelled;
73922 + UCHAR MaxSupportedRateIn500Kbps = 0;
73923 + UCHAR SupportedRatesLen;
73924 + UCHAR SupportedRates[MAX_LEN_OF_SUPPORTED_RATES];
73925 + UCHAR HtCapabilityLen;
73926 + HT_CAPABILITY_IE HtCapability;
73927 +
73928 + if (!pAd->CommonCfg.bDLSCapable)
73929 + return;
73930 +
73931 + if (!INFRA_ON(pAd))
73932 + return;
73933 +
73934 + if (!PeerDlsRspSanity(pAd, Elem->Msg, Elem->MsgLen, DA, SA, &CapabilityInfo, &StatusCode,
73935 + &SupportedRatesLen, &SupportedRates[0], &HtCapabilityLen, &HtCapability))
73936 + return;
73937 +
73938 + // supported rates array may not be sorted. sort it and find the maximum rate
73939 + for (i=0; i<SupportedRatesLen; i++)
73940 + {
73941 + if (MaxSupportedRateIn500Kbps < (SupportedRates[i] & 0x7f))
73942 + MaxSupportedRateIn500Kbps = SupportedRates[i] & 0x7f;
73943 + }
73944 +
73945 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsRspAction() from %02x:%02x:%02x:%02x:%02x:%02x with StatusCode=%d, CapabilityInfo=0x%x\n",
73946 + SA[0], SA[1], SA[2], SA[3], SA[4], SA[5], StatusCode, CapabilityInfo));
73947 +
73948 + for (i = 0; i < MAX_NUM_OF_INIT_DLS_ENTRY; i++)
73949 + {
73950 + if (pAd->StaCfg.DLSEntry[i].Valid && MAC_ADDR_EQUAL(SA, pAd->StaCfg.DLSEntry[i].MacAddr))
73951 + {
73952 + if (StatusCode == MLME_SUCCESS)
73953 + {
73954 + MAC_TABLE_ENTRY *pEntry;
73955 + UCHAR MaxSupportedRate = RATE_11;
73956 +
73957 + pEntry = MacTableInsertDlsEntry(pAd, SA, i);
73958 +
73959 + switch (MaxSupportedRateIn500Kbps)
73960 + {
73961 + case 108: MaxSupportedRate = RATE_54; break;
73962 + case 96: MaxSupportedRate = RATE_48; break;
73963 + case 72: MaxSupportedRate = RATE_36; break;
73964 + case 48: MaxSupportedRate = RATE_24; break;
73965 + case 36: MaxSupportedRate = RATE_18; break;
73966 + case 24: MaxSupportedRate = RATE_12; break;
73967 + case 18: MaxSupportedRate = RATE_9; break;
73968 + case 12: MaxSupportedRate = RATE_6; break;
73969 + case 22: MaxSupportedRate = RATE_11; break;
73970 + case 11: MaxSupportedRate = RATE_5_5; break;
73971 + case 4: MaxSupportedRate = RATE_2; break;
73972 + case 2: MaxSupportedRate = RATE_1; break;
73973 + default: MaxSupportedRate = RATE_11; break;
73974 + }
73975 +
73976 + pEntry->MaxSupportedRate = min(pAd->CommonCfg.MaxTxRate, MaxSupportedRate);
73977 +
73978 + if (pEntry->MaxSupportedRate < RATE_FIRST_OFDM_RATE)
73979 + {
73980 + pEntry->MaxHTPhyMode.field.MODE = MODE_CCK;
73981 + pEntry->MaxHTPhyMode.field.MCS = pEntry->MaxSupportedRate;
73982 + pEntry->MinHTPhyMode.field.MODE = MODE_CCK;
73983 + pEntry->MinHTPhyMode.field.MCS = pEntry->MaxSupportedRate;
73984 + pEntry->HTPhyMode.field.MODE = MODE_CCK;
73985 + pEntry->HTPhyMode.field.MCS = pEntry->MaxSupportedRate;
73986 + }
73987 + else
73988 + {
73989 + pEntry->MaxHTPhyMode.field.MODE = MODE_OFDM;
73990 + pEntry->MaxHTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
73991 + pEntry->MinHTPhyMode.field.MODE = MODE_OFDM;
73992 + pEntry->MinHTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
73993 + pEntry->HTPhyMode.field.MODE = MODE_OFDM;
73994 + pEntry->HTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
73995 + }
73996 +
73997 + pEntry->MaxHTPhyMode.field.BW = BW_20;
73998 + pEntry->MinHTPhyMode.field.BW = BW_20;
73999 +
74000 +#ifdef DOT11_N_SUPPORT
74001 + pEntry->HTCapability.MCSSet[0] = 0;
74002 + pEntry->HTCapability.MCSSet[1] = 0;
74003 +
74004 + // If this Entry supports 802.11n, upgrade to HT rate.
74005 + if ((HtCapabilityLen != 0) && (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
74006 + {
74007 + UCHAR j, bitmask; //k,bitmask;
74008 + CHAR ii;
74009 +
74010 + DBGPRINT(RT_DEBUG_OFF, ("DLS - PeerDlsRspAction Receive Peer HT Capable STA from %02x:%02x:%02x:%02x:%02x:%02x\n",
74011 + SA[0], SA[1], SA[2], SA[3], SA[4], SA[5]));
74012 +
74013 + if ((HtCapability.HtCapInfo.GF) && (pAd->CommonCfg.DesiredHtPhy.GF))
74014 + {
74015 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTGREENFIELD;
74016 + }
74017 + else
74018 + {
74019 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTMIX;
74020 + pAd->MacTab.fAnyStationNonGF = TRUE;
74021 + pAd->CommonCfg.AddHTInfo.AddHtInfo2.NonGfPresent = 1;
74022 + }
74023 +
74024 + if ((HtCapability.HtCapInfo.ChannelWidth) && (pAd->CommonCfg.DesiredHtPhy.ChannelWidth))
74025 + {
74026 + pEntry->MaxHTPhyMode.field.BW= BW_40;
74027 + pEntry->MaxHTPhyMode.field.ShortGI = ((pAd->CommonCfg.DesiredHtPhy.ShortGIfor40)&(HtCapability.HtCapInfo.ShortGIfor40));
74028 + }
74029 + else
74030 + {
74031 + pEntry->MaxHTPhyMode.field.BW = BW_20;
74032 + pEntry->MaxHTPhyMode.field.ShortGI = ((pAd->CommonCfg.DesiredHtPhy.ShortGIfor20)&(HtCapability.HtCapInfo.ShortGIfor20));
74033 + pAd->MacTab.fAnyStation20Only = TRUE;
74034 + }
74035 +
74036 + // find max fixed rate
74037 + for (ii=15; ii>=0; ii--)
74038 + {
74039 + j = ii/8;
74040 + bitmask = (1<<(ii-(j*8)));
74041 + if ( (pAd->StaCfg.DesiredHtPhyInfo.MCSSet[j]&bitmask) && (HtCapability.MCSSet[j]&bitmask))
74042 + {
74043 + pEntry->MaxHTPhyMode.field.MCS = ii;
74044 + break;
74045 + }
74046 + if (ii==0)
74047 + break;
74048 + }
74049 +
74050 + if (pAd->StaCfg.DesiredTransmitSetting.field.MCS != MCS_AUTO)
74051 + {
74052 + if (pAd->StaCfg.DesiredTransmitSetting.field.MCS == 32)
74053 + {
74054 + // Fix MCS as HT Duplicated Mode
74055 + pEntry->MaxHTPhyMode.field.BW = 1;
74056 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTMIX;
74057 + pEntry->MaxHTPhyMode.field.STBC = 0;
74058 + pEntry->MaxHTPhyMode.field.ShortGI = 0;
74059 + pEntry->MaxHTPhyMode.field.MCS = 32;
74060 + }
74061 + else if (pEntry->MaxHTPhyMode.field.MCS > pAd->StaCfg.HTPhyMode.field.MCS)
74062 + {
74063 + // STA supports fixed MCS
74064 + pEntry->MaxHTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
74065 + }
74066 + }
74067 +
74068 + pEntry->MaxHTPhyMode.field.STBC = (HtCapability.HtCapInfo.RxSTBC & (pAd->CommonCfg.DesiredHtPhy.TxSTBC));
74069 + pEntry->MpduDensity = HtCapability.HtCapParm.MpduDensity;
74070 + pEntry->MaxRAmpduFactor = HtCapability.HtCapParm.MaxRAmpduFactor;
74071 + pEntry->MmpsMode = (UCHAR)HtCapability.HtCapInfo.MimoPs;
74072 + pEntry->AMsduSize = (UCHAR)HtCapability.HtCapInfo.AMsduSize;
74073 + pEntry->HTPhyMode.word = pEntry->MaxHTPhyMode.word;
74074 +
74075 + if (HtCapability.HtCapInfo.ShortGIfor20)
74076 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_SGI20_CAPABLE);
74077 + if (HtCapability.HtCapInfo.ShortGIfor40)
74078 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_SGI40_CAPABLE);
74079 + if (HtCapability.HtCapInfo.TxSTBC)
74080 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_TxSTBC_CAPABLE);
74081 + if (HtCapability.HtCapInfo.RxSTBC)
74082 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_RxSTBC_CAPABLE);
74083 + if (HtCapability.ExtHtCapInfo.PlusHTC)
74084 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_HTC_CAPABLE);
74085 + if (pAd->CommonCfg.bRdg && HtCapability.ExtHtCapInfo.RDGSupport)
74086 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_RDG_CAPABLE);
74087 + if (HtCapability.ExtHtCapInfo.MCSFeedback == 0x03)
74088 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_MCSFEEDBACK_CAPABLE);
74089 +
74090 + NdisMoveMemory(&pEntry->HTCapability, &HtCapability, sizeof(HT_CAPABILITY_IE));
74091 + }
74092 +#endif // DOT11_N_SUPPORT //
74093 + pEntry->HTPhyMode.word = pEntry->MaxHTPhyMode.word;
74094 + pEntry->CurrTxRate = pEntry->MaxSupportedRate;
74095 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_WMM_CAPABLE);
74096 +
74097 + if (pAd->StaCfg.bAutoTxRateSwitch == TRUE)
74098 + {
74099 + PUCHAR pTable;
74100 + UCHAR TableSize = 0;
74101 +
74102 + MlmeSelectTxRateTable(pAd, pEntry, &pTable, &TableSize, &pEntry->CurrTxRateIndex);
74103 + pEntry->bAutoTxRateSwitch = TRUE;
74104 + }
74105 + else
74106 + {
74107 + pEntry->HTPhyMode.field.MODE = pAd->StaCfg.HTPhyMode.field.MODE;
74108 + pEntry->HTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
74109 + pEntry->bAutoTxRateSwitch = FALSE;
74110 +
74111 + RTMPUpdateLegacyTxSetting((UCHAR)pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode, pEntry);
74112 + }
74113 + pEntry->RateLen = SupportedRatesLen;
74114 +
74115 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
74116 + {
74117 + // If support WPA or WPA2, start STAKey hand shake,
74118 + // If failed hand shake, just tear down peer DLS
74119 + if (RTMPSendSTAKeyRequest(pAd, pAd->StaCfg.DLSEntry[i].MacAddr) != NDIS_STATUS_SUCCESS)
74120 + {
74121 + MLME_DLS_REQ_STRUCT MlmeDlsReq;
74122 + USHORT reason = REASON_QOS_CIPHER_NOT_SUPPORT;
74123 +
74124 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
74125 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
74126 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74127 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74128 + DBGPRINT(RT_DEBUG_ERROR,("DLS - PeerDlsRspAction failed when call RTMPSendSTAKeyRequest \n"));
74129 + }
74130 + else
74131 + {
74132 + pAd->StaCfg.DLSEntry[i].Status = DLS_WAIT_KEY;
74133 + DBGPRINT(RT_DEBUG_TRACE,("DLS - waiting for STAKey handshake procedure\n"));
74134 + }
74135 + }
74136 + else
74137 + {
74138 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74139 + pAd->StaCfg.DLSEntry[i].Status = DLS_FINISH;
74140 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsRspAction() from %02x:%02x:%02x:%02x:%02x:%02x Succeed with WEP or no security\n", SA[0], SA[1], SA[2], SA[3], SA[4], SA[5]));
74141 + }
74142 +
74143 + //initialize seq no for DLS frames.
74144 + pAd->StaCfg.DLSEntry[i].Sequence = 0;
74145 + if (HtCapabilityLen != 0)
74146 + pAd->StaCfg.DLSEntry[i].bHTCap = TRUE;
74147 + else
74148 + pAd->StaCfg.DLSEntry[i].bHTCap = FALSE;
74149 + }
74150 + else
74151 + {
74152 + // DLS setup procedure failed.
74153 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74154 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74155 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74156 + DBGPRINT(RT_DEBUG_ERROR,("DLS - PeerDlsRspAction failed with StatusCode=%d \n", StatusCode));
74157 + }
74158 + }
74159 + }
74160 +
74161 + if (i >= MAX_NUM_OF_INIT_DLS_ENTRY)
74162 + {
74163 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsRspAction() update timeout value \n"));
74164 + for (i=(MAX_NUM_OF_DLS_ENTRY-1); i>=MAX_NUM_OF_INIT_DLS_ENTRY; i--)
74165 + {
74166 + if (pAd->StaCfg.DLSEntry[i].Valid && MAC_ADDR_EQUAL(SA, pAd->StaCfg.DLSEntry[i].MacAddr))
74167 + {
74168 + if (StatusCode == MLME_SUCCESS)
74169 + {
74170 + MAC_TABLE_ENTRY *pEntry;
74171 + UCHAR MaxSupportedRate = RATE_11;
74172 +
74173 + pEntry = MacTableInsertDlsEntry(pAd, SA, i);
74174 +
74175 + switch (MaxSupportedRateIn500Kbps)
74176 + {
74177 + case 108: MaxSupportedRate = RATE_54; break;
74178 + case 96: MaxSupportedRate = RATE_48; break;
74179 + case 72: MaxSupportedRate = RATE_36; break;
74180 + case 48: MaxSupportedRate = RATE_24; break;
74181 + case 36: MaxSupportedRate = RATE_18; break;
74182 + case 24: MaxSupportedRate = RATE_12; break;
74183 + case 18: MaxSupportedRate = RATE_9; break;
74184 + case 12: MaxSupportedRate = RATE_6; break;
74185 + case 22: MaxSupportedRate = RATE_11; break;
74186 + case 11: MaxSupportedRate = RATE_5_5; break;
74187 + case 4: MaxSupportedRate = RATE_2; break;
74188 + case 2: MaxSupportedRate = RATE_1; break;
74189 + default: MaxSupportedRate = RATE_11; break;
74190 + }
74191 +
74192 + pEntry->MaxSupportedRate = min(pAd->CommonCfg.MaxTxRate, MaxSupportedRate);
74193 +
74194 + if (pEntry->MaxSupportedRate < RATE_FIRST_OFDM_RATE)
74195 + {
74196 + pEntry->MaxHTPhyMode.field.MODE = MODE_CCK;
74197 + pEntry->MaxHTPhyMode.field.MCS = pEntry->MaxSupportedRate;
74198 + pEntry->MinHTPhyMode.field.MODE = MODE_CCK;
74199 + pEntry->MinHTPhyMode.field.MCS = pEntry->MaxSupportedRate;
74200 + pEntry->HTPhyMode.field.MODE = MODE_CCK;
74201 + pEntry->HTPhyMode.field.MCS = pEntry->MaxSupportedRate;
74202 + }
74203 + else
74204 + {
74205 + pEntry->MaxHTPhyMode.field.MODE = MODE_OFDM;
74206 + pEntry->MaxHTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
74207 + pEntry->MinHTPhyMode.field.MODE = MODE_OFDM;
74208 + pEntry->MinHTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
74209 + pEntry->HTPhyMode.field.MODE = MODE_OFDM;
74210 + pEntry->HTPhyMode.field.MCS = OfdmRateToRxwiMCS[pEntry->MaxSupportedRate];
74211 + }
74212 +
74213 + pEntry->MaxHTPhyMode.field.BW = BW_20;
74214 + pEntry->MinHTPhyMode.field.BW = BW_20;
74215 +
74216 +#ifdef DOT11_N_SUPPORT
74217 + pEntry->HTCapability.MCSSet[0] = 0;
74218 + pEntry->HTCapability.MCSSet[1] = 0;
74219 +
74220 + // If this Entry supports 802.11n, upgrade to HT rate.
74221 + if ((HtCapabilityLen != 0) && (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
74222 + {
74223 + UCHAR j, bitmask; //k,bitmask;
74224 + CHAR ii;
74225 +
74226 + DBGPRINT(RT_DEBUG_OFF, ("DLS - PeerDlsRspAction Receive Peer HT Capable STA from %02x:%02x:%02x:%02x:%02x:%02x\n",
74227 + SA[0], SA[1], SA[2], SA[3], SA[4], SA[5]));
74228 +
74229 + if ((HtCapability.HtCapInfo.GF) && (pAd->CommonCfg.DesiredHtPhy.GF))
74230 + {
74231 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTGREENFIELD;
74232 + }
74233 + else
74234 + {
74235 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTMIX;
74236 + pAd->MacTab.fAnyStationNonGF = TRUE;
74237 + pAd->CommonCfg.AddHTInfo.AddHtInfo2.NonGfPresent = 1;
74238 + }
74239 +
74240 + if ((HtCapability.HtCapInfo.ChannelWidth) && (pAd->CommonCfg.DesiredHtPhy.ChannelWidth))
74241 + {
74242 + pEntry->MaxHTPhyMode.field.BW= BW_40;
74243 + pEntry->MaxHTPhyMode.field.ShortGI = ((pAd->CommonCfg.DesiredHtPhy.ShortGIfor40)&(HtCapability.HtCapInfo.ShortGIfor40));
74244 + }
74245 + else
74246 + {
74247 + pEntry->MaxHTPhyMode.field.BW = BW_20;
74248 + pEntry->MaxHTPhyMode.field.ShortGI = ((pAd->CommonCfg.DesiredHtPhy.ShortGIfor20)&(HtCapability.HtCapInfo.ShortGIfor20));
74249 + pAd->MacTab.fAnyStation20Only = TRUE;
74250 + }
74251 +
74252 + // find max fixed rate
74253 + for (ii=15; ii>=0; ii--)
74254 + {
74255 + j = ii/8;
74256 + bitmask = (1<<(ii-(j*8)));
74257 + if ( (pAd->StaCfg.DesiredHtPhyInfo.MCSSet[j]&bitmask) && (HtCapability.MCSSet[j]&bitmask))
74258 + {
74259 + pEntry->MaxHTPhyMode.field.MCS = ii;
74260 + break;
74261 + }
74262 + if (ii==0)
74263 + break;
74264 + }
74265 +
74266 + if (pAd->StaCfg.DesiredTransmitSetting.field.MCS != MCS_AUTO)
74267 + {
74268 + printk("@@@ pAd->CommonCfg.RegTransmitSetting.field.MCS = %d\n",
74269 + pAd->StaCfg.DesiredTransmitSetting.field.MCS);
74270 + if (pAd->StaCfg.DesiredTransmitSetting.field.MCS == 32)
74271 + {
74272 + // Fix MCS as HT Duplicated Mode
74273 + pEntry->MaxHTPhyMode.field.BW = 1;
74274 + pEntry->MaxHTPhyMode.field.MODE = MODE_HTMIX;
74275 + pEntry->MaxHTPhyMode.field.STBC = 0;
74276 + pEntry->MaxHTPhyMode.field.ShortGI = 0;
74277 + pEntry->MaxHTPhyMode.field.MCS = 32;
74278 + }
74279 + else if (pEntry->MaxHTPhyMode.field.MCS > pAd->StaCfg.HTPhyMode.field.MCS)
74280 + {
74281 + // STA supports fixed MCS
74282 + pEntry->MaxHTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
74283 + }
74284 + }
74285 +
74286 + pEntry->MaxHTPhyMode.field.STBC = (HtCapability.HtCapInfo.RxSTBC & (pAd->CommonCfg.DesiredHtPhy.TxSTBC));
74287 + pEntry->MpduDensity = HtCapability.HtCapParm.MpduDensity;
74288 + pEntry->MaxRAmpduFactor = HtCapability.HtCapParm.MaxRAmpduFactor;
74289 + pEntry->MmpsMode = (UCHAR)HtCapability.HtCapInfo.MimoPs;
74290 + pEntry->AMsduSize = (UCHAR)HtCapability.HtCapInfo.AMsduSize;
74291 + pEntry->HTPhyMode.word = pEntry->MaxHTPhyMode.word;
74292 +
74293 + if (HtCapability.HtCapInfo.ShortGIfor20)
74294 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_SGI20_CAPABLE);
74295 + if (HtCapability.HtCapInfo.ShortGIfor40)
74296 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_SGI40_CAPABLE);
74297 + if (HtCapability.HtCapInfo.TxSTBC)
74298 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_TxSTBC_CAPABLE);
74299 + if (HtCapability.HtCapInfo.RxSTBC)
74300 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_RxSTBC_CAPABLE);
74301 + if (HtCapability.ExtHtCapInfo.PlusHTC)
74302 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_HTC_CAPABLE);
74303 + if (pAd->CommonCfg.bRdg && HtCapability.ExtHtCapInfo.RDGSupport)
74304 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_RDG_CAPABLE);
74305 + if (HtCapability.ExtHtCapInfo.MCSFeedback == 0x03)
74306 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_MCSFEEDBACK_CAPABLE);
74307 +
74308 + NdisMoveMemory(&pEntry->HTCapability, &HtCapability, sizeof(HT_CAPABILITY_IE));
74309 + }
74310 +#endif // DOT11_N_SUPPORT //
74311 +
74312 + pEntry->HTPhyMode.word = pEntry->MaxHTPhyMode.word;
74313 + pEntry->CurrTxRate = pEntry->MaxSupportedRate;
74314 + CLIENT_STATUS_SET_FLAG(pEntry, fCLIENT_STATUS_WMM_CAPABLE);
74315 +
74316 + if (pAd->StaCfg.bAutoTxRateSwitch == TRUE)
74317 + {
74318 + PUCHAR pTable;
74319 + UCHAR TableSize = 0;
74320 +
74321 + MlmeSelectTxRateTable(pAd, pEntry, &pTable, &TableSize, &pEntry->CurrTxRateIndex);
74322 + pEntry->bAutoTxRateSwitch = TRUE;
74323 + }
74324 + else
74325 + {
74326 + pEntry->HTPhyMode.field.MODE = pAd->StaCfg.HTPhyMode.field.MODE;
74327 + pEntry->HTPhyMode.field.MCS = pAd->StaCfg.HTPhyMode.field.MCS;
74328 + pEntry->bAutoTxRateSwitch = FALSE;
74329 +
74330 + RTMPUpdateLegacyTxSetting((UCHAR)pAd->StaCfg.DesiredTransmitSetting.field.FixedTxMode, pEntry);
74331 + }
74332 + pEntry->RateLen = SupportedRatesLen;
74333 +
74334 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
74335 + {
74336 + // If support WPA or WPA2, start STAKey hand shake,
74337 + // If failed hand shake, just tear down peer DLS
74338 + if (RTMPSendSTAKeyRequest(pAd, pAd->StaCfg.DLSEntry[i].MacAddr) != NDIS_STATUS_SUCCESS)
74339 + {
74340 + MLME_DLS_REQ_STRUCT MlmeDlsReq;
74341 + USHORT reason = REASON_QOS_CIPHER_NOT_SUPPORT;
74342 +
74343 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
74344 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
74345 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74346 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74347 + DBGPRINT(RT_DEBUG_ERROR,("DLS - PeerDlsRspAction failed when call RTMPSendSTAKeyRequest \n"));
74348 + }
74349 + else
74350 + {
74351 + pAd->StaCfg.DLSEntry[i].Status = DLS_WAIT_KEY;
74352 + DBGPRINT(RT_DEBUG_TRACE,("DLS - waiting for STAKey handshake procedure\n"));
74353 + }
74354 + }
74355 + else
74356 + {
74357 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74358 + pAd->StaCfg.DLSEntry[i].Status = DLS_FINISH;
74359 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsRspAction() from %02x:%02x:%02x:%02x:%02x:%02x Succeed with WEP or no security\n", SA[0], SA[1], SA[2], SA[3], SA[4], SA[5]));
74360 + }
74361 + pAd->StaCfg.DLSEntry[i].Sequence = 0;
74362 + if (HtCapabilityLen != 0)
74363 + pAd->StaCfg.DLSEntry[i].bHTCap = TRUE;
74364 + else
74365 + pAd->StaCfg.DLSEntry[i].bHTCap = FALSE;
74366 + }
74367 + else
74368 + {
74369 + // DLS setup procedure failed.
74370 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74371 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74372 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74373 + DBGPRINT(RT_DEBUG_ERROR,("DLS - PeerDlsRspAction failed with StatusCode=%d \n", StatusCode));
74374 + }
74375 + }
74376 + }
74377 + }
74378 +}
74379 +
74380 +/*
74381 + ==========================================================================
74382 + Description:
74383 +
74384 + IRQL = DISPATCH_LEVEL
74385 +
74386 + ==========================================================================
74387 + */
74388 +VOID MlmeDlsTearDownAction(
74389 + IN PRTMP_ADAPTER pAd,
74390 + IN MLME_QUEUE_ELEM *Elem)
74391 +{
74392 + PUCHAR pOutBuffer = NULL;
74393 + NDIS_STATUS NStatus;
74394 + ULONG FrameLen = 0;
74395 + UCHAR Category = CATEGORY_DLS;
74396 + UCHAR Action = ACTION_DLS_TEARDOWN;
74397 + USHORT ReasonCode = REASON_QOS_UNSPECIFY;
74398 + HEADER_802_11 DlsTearDownHdr;
74399 + PRT_802_11_DLS pDLS;
74400 + BOOLEAN TimerCancelled;
74401 + UCHAR i;
74402 +
74403 + if(!MlmeDlsReqSanity(pAd, Elem->Msg, Elem->MsgLen, &pDLS, &ReasonCode))
74404 + return;
74405 +
74406 + DBGPRINT(RT_DEBUG_TRACE,("DLS - MlmeDlsTearDownAction() with ReasonCode=%d \n", ReasonCode));
74407 +
74408 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
74409 + if (NStatus != NDIS_STATUS_SUCCESS)
74410 + {
74411 + DBGPRINT(RT_DEBUG_ERROR,("DLS - MlmeDlsTearDownAction() allocate memory failed \n"));
74412 + return;
74413 + }
74414 +
74415 + ActHeaderInit(pAd, &DlsTearDownHdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
74416 +
74417 + // Build basic frame first
74418 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
74419 + sizeof(HEADER_802_11), &DlsTearDownHdr,
74420 + 1, &Category,
74421 + 1, &Action,
74422 + 6, &pDLS->MacAddr,
74423 + 6, pAd->CurrentAddress,
74424 + 2, &ReasonCode,
74425 + END_OF_ARGS);
74426 +
74427 + MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen);
74428 + MlmeFreeMemory(pAd, pOutBuffer);
74429 + RTMPCancelTimer(&pDLS->Timer, &TimerCancelled);
74430 +
74431 + // Remove key in local dls table entry
74432 + for (i = 0; i < MAX_NUM_OF_INIT_DLS_ENTRY; i++)
74433 + {
74434 + if (MAC_ADDR_EQUAL(pDLS->MacAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
74435 + {
74436 + MacTableDeleteDlsEntry(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID, pAd->StaCfg.DLSEntry[i].MacAddr);
74437 + }
74438 + }
74439 +
74440 + // clear peer dls table entry
74441 + for (i = MAX_NUM_OF_INIT_DLS_ENTRY; i < MAX_NUM_OF_DLS_ENTRY; i++)
74442 + {
74443 + if (MAC_ADDR_EQUAL(pDLS->MacAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
74444 + {
74445 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74446 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74447 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74448 + MacTableDeleteDlsEntry(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID, pAd->StaCfg.DLSEntry[i].MacAddr);
74449 + }
74450 + }
74451 +}
74452 +
74453 +/*
74454 + ==========================================================================
74455 + Description:
74456 +
74457 + IRQL = DISPATCH_LEVEL
74458 +
74459 + ==========================================================================
74460 + */
74461 +VOID PeerDlsTearDownAction(
74462 + IN PRTMP_ADAPTER pAd,
74463 + IN MLME_QUEUE_ELEM *Elem)
74464 +{
74465 + UCHAR DA[MAC_ADDR_LEN], SA[MAC_ADDR_LEN];
74466 + USHORT ReasonCode;
74467 + UINT i;
74468 + BOOLEAN TimerCancelled;
74469 +
74470 + if (!pAd->CommonCfg.bDLSCapable)
74471 + return;
74472 +
74473 + if (!INFRA_ON(pAd))
74474 + return;
74475 +
74476 + if (!PeerDlsTearDownSanity(pAd, Elem->Msg, Elem->MsgLen, DA, SA, &ReasonCode))
74477 + return;
74478 +
74479 + DBGPRINT(RT_DEBUG_TRACE,("DLS - PeerDlsTearDownAction() from %02x:%02x:%02x:%02x:%02x:%02x with ReasonCode=%d\n", SA[0], SA[1], SA[2], SA[3], SA[4], SA[5], ReasonCode));
74480 +
74481 + // clear local dls table entry
74482 + for (i=0; i<MAX_NUM_OF_INIT_DLS_ENTRY; i++)
74483 + {
74484 + if (pAd->StaCfg.DLSEntry[i].Valid && MAC_ADDR_EQUAL(SA, pAd->StaCfg.DLSEntry[i].MacAddr))
74485 + {
74486 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74487 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74488 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74489 + //AsicDelWcidTab(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID);
74490 + //AsicRemovePairwiseKeyEntry(pAd, BSS0, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID);
74491 + MacTableDeleteDlsEntry(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID, pAd->StaCfg.DLSEntry[i].MacAddr);
74492 + }
74493 + }
74494 +
74495 + // clear peer dls table entry
74496 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
74497 + {
74498 + if (pAd->StaCfg.DLSEntry[i].Valid && MAC_ADDR_EQUAL(SA, pAd->StaCfg.DLSEntry[i].MacAddr))
74499 + {
74500 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74501 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74502 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74503 + //AsicDelWcidTab(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID);
74504 + //AsicRemovePairwiseKeyEntry(pAd, BSS0, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID);
74505 + MacTableDeleteDlsEntry(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID, pAd->StaCfg.DLSEntry[i].MacAddr);
74506 + }
74507 + }
74508 +}
74509 +
74510 +/*
74511 + ==========================================================================
74512 + Description:
74513 +
74514 + IRQL = DISPATCH_LEVEL
74515 +
74516 + ==========================================================================
74517 + */
74518 +VOID RTMPCheckDLSTimeOut(
74519 + IN PRTMP_ADAPTER pAd)
74520 +{
74521 + ULONG i;
74522 + MLME_DLS_REQ_STRUCT MlmeDlsReq;
74523 + USHORT reason = REASON_QOS_UNSPECIFY;
74524 +
74525 + if (! pAd->CommonCfg.bDLSCapable)
74526 + return;
74527 +
74528 + if (! INFRA_ON(pAd))
74529 + return;
74530 +
74531 + // If timeout value is equaled to zero, it means always not be timeout.
74532 +
74533 + // update local dls table entry
74534 + for (i=0; i<MAX_NUM_OF_INIT_DLS_ENTRY; i++)
74535 + {
74536 + if ((pAd->StaCfg.DLSEntry[i].Valid) && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH)
74537 + && (pAd->StaCfg.DLSEntry[i].TimeOut != 0))
74538 + {
74539 + pAd->StaCfg.DLSEntry[i].CountDownTimer --;
74540 +
74541 + if (pAd->StaCfg.DLSEntry[i].CountDownTimer == 0)
74542 + {
74543 + reason = REASON_QOS_REQUEST_TIMEOUT;
74544 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74545 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74546 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
74547 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
74548 + }
74549 + }
74550 + }
74551 +
74552 + // update peer dls table entry
74553 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
74554 + {
74555 + if ((pAd->StaCfg.DLSEntry[i].Valid) && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH)
74556 + && (pAd->StaCfg.DLSEntry[i].TimeOut != 0))
74557 + {
74558 + pAd->StaCfg.DLSEntry[i].CountDownTimer --;
74559 +
74560 + if (pAd->StaCfg.DLSEntry[i].CountDownTimer == 0)
74561 + {
74562 + reason = REASON_QOS_REQUEST_TIMEOUT;
74563 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74564 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74565 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
74566 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
74567 + }
74568 + }
74569 + }
74570 +}
74571 +
74572 +/*
74573 + ==========================================================================
74574 + Description:
74575 +
74576 + IRQL = DISPATCH_LEVEL
74577 +
74578 + ==========================================================================
74579 + */
74580 +BOOLEAN RTMPRcvFrameDLSCheck(
74581 + IN PRTMP_ADAPTER pAd,
74582 + IN PHEADER_802_11 pHeader,
74583 + IN ULONG Len,
74584 + IN PRT28XX_RXD_STRUC pRxD)
74585 +{
74586 + ULONG i;
74587 + BOOLEAN bFindEntry = FALSE;
74588 + BOOLEAN bSTAKeyFrame = FALSE;
74589 + PEAPOL_PACKET pEap;
74590 + PUCHAR pProto, pAddr = NULL;
74591 + PUCHAR pSTAKey = NULL;
74592 + UCHAR ZeroReplay[LEN_KEY_DESC_REPLAY];
74593 + UCHAR Mic[16], OldMic[16];
74594 + UCHAR digest[80];
74595 + UCHAR DlsPTK[80];
74596 + UCHAR temp[64];
74597 + BOOLEAN TimerCancelled;
74598 + CIPHER_KEY PairwiseKey;
74599 +
74600 +
74601 + if (! pAd->CommonCfg.bDLSCapable)
74602 + return bSTAKeyFrame;
74603 +
74604 + if (! INFRA_ON(pAd))
74605 + return bSTAKeyFrame;
74606 +
74607 + if (! (pHeader->FC.SubType & 0x08))
74608 + return bSTAKeyFrame;
74609 +
74610 + if (Len < LENGTH_802_11 + 6 + 2 + 2)
74611 + return bSTAKeyFrame;
74612 +
74613 + pProto = (PUCHAR)pHeader + LENGTH_802_11 + 2 + 6; // QOS Control field , 0xAA 0xAA 0xAA 0x00 0x00 0x00
74614 + pAddr = pHeader->Addr2;
74615 +
74616 + // L2PAD bit on will pad 2 bytes at LLC
74617 + if (pRxD->L2PAD)
74618 + {
74619 + pProto += 2;
74620 + }
74621 +
74622 + if (RTMPEqualMemory(EAPOL, pProto, 2) && (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA))
74623 + {
74624 + pEap = (PEAPOL_PACKET) (pProto + 2);
74625 +
74626 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Sniff Len=%ld, DataLen=%d, KeyMic=%d, Install=%d, KeyAck=%d, Secure=%d, EKD_DL=%d, Error=%d, Request=%d\n", Len,
74627 + (LENGTH_802_11 + 6 + 2 + 2 + sizeof(EAPOL_PACKET) - MAX_LEN_OF_RSNIE + 16),
74628 + pEap->KeyDesc.KeyInfo.KeyMic,
74629 + pEap->KeyDesc.KeyInfo.Install,
74630 + pEap->KeyDesc.KeyInfo.KeyAck,
74631 + pEap->KeyDesc.KeyInfo.Secure,
74632 + pEap->KeyDesc.KeyInfo.EKD_DL,
74633 + pEap->KeyDesc.KeyInfo.Error,
74634 + pEap->KeyDesc.KeyInfo.Request));
74635 +
74636 + if ((Len >= (LENGTH_802_11 + 6 + 2 + 2 + sizeof(EAPOL_PACKET) - MAX_LEN_OF_RSNIE + 16)) && pEap->KeyDesc.KeyInfo.KeyMic
74637 + && pEap->KeyDesc.KeyInfo.Install && pEap->KeyDesc.KeyInfo.KeyAck && pEap->KeyDesc.KeyInfo.Secure
74638 + && pEap->KeyDesc.KeyInfo.EKD_DL && !pEap->KeyDesc.KeyInfo.Error && !pEap->KeyDesc.KeyInfo.Request)
74639 + {
74640 + // First validate replay counter, only accept message with larger replay counter
74641 + // Let equal pass, some AP start with all zero replay counter
74642 + NdisZeroMemory(ZeroReplay, LEN_KEY_DESC_REPLAY);
74643 + if ((RTMPCompareMemory(pEap->KeyDesc.ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY) != 1) &&
74644 + (RTMPCompareMemory(pEap->KeyDesc.ReplayCounter, ZeroReplay, LEN_KEY_DESC_REPLAY) != 0))
74645 + return bSTAKeyFrame;
74646 +
74647 + //RTMPMoveMemory(pAd->StaCfg.ReplayCounter, pEap->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
74648 + RTMPMoveMemory(pAd->StaCfg.DlsReplayCounter, pEap->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
74649 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Sniff replay counter (%02x-%02x-%02x-%02x-%02x-%02x-%02x-%02x) Len=%ld, KeyDataLen=%d\n",
74650 + pAd->StaCfg.ReplayCounter[0], pAd->StaCfg.ReplayCounter[1], pAd->StaCfg.ReplayCounter[2],
74651 + pAd->StaCfg.ReplayCounter[3], pAd->StaCfg.ReplayCounter[4], pAd->StaCfg.ReplayCounter[5],
74652 + pAd->StaCfg.ReplayCounter[6], pAd->StaCfg.ReplayCounter[7], Len, pEap->KeyDesc.KeyData[1]));
74653 +
74654 + // put these code segment to get the replay counter
74655 + if (pAd->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED)
74656 + return bSTAKeyFrame;
74657 +
74658 + // Check MIC value
74659 + // Save the MIC and replace with zero
74660 + // use proprietary PTK
74661 + NdisZeroMemory(temp, 64);
74662 + NdisMoveMemory(temp, "IEEE802.11 WIRELESS ACCESS POINT", 32);
74663 + WpaCountPTK(pAd, temp, temp, pAd->CommonCfg.Bssid, temp, pAd->CurrentAddress, DlsPTK, LEN_PTK);
74664 +
74665 + NdisMoveMemory(OldMic, pEap->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
74666 + NdisZeroMemory(pEap->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
74667 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
74668 + {
74669 + // AES
74670 + HMAC_SHA1((PUCHAR) pEap, pEap->Body_Len[1] + 4, DlsPTK, LEN_EAP_MICK, digest);
74671 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
74672 + }
74673 + else
74674 + {
74675 + hmac_md5(DlsPTK, LEN_EAP_MICK, (PUCHAR) pEap, pEap->Body_Len[1] + 4, Mic);
74676 + }
74677 +
74678 + if (!NdisEqualMemory(OldMic, Mic, LEN_KEY_DESC_MIC))
74679 + {
74680 + DBGPRINT(RT_DEBUG_ERROR, ("MIC Different in Msg1 of STAKey handshake! \n"));
74681 + return bSTAKeyFrame;
74682 + }
74683 + else
74684 + DBGPRINT(RT_DEBUG_TRACE, ("MIC VALID in Msg1 of STAKey handshake! \n"));
74685 +#if 1
74686 + if ((pEap->KeyDesc.KeyData[0] == 0xDD) && (pEap->KeyDesc.KeyData[2] == 0x00) && (pEap->KeyDesc.KeyData[3] == 0x0C)
74687 + && (pEap->KeyDesc.KeyData[4] == 0x43) && (pEap->KeyDesc.KeyData[5] == 0x02))
74688 + {
74689 + pAddr = pEap->KeyDesc.KeyData + 8; // Tpe(1), Len(1), OUI(3), DataType(1), Reserved(2)
74690 + pSTAKey = pEap->KeyDesc.KeyData + 14; // Tpe(1), Len(1), OUI(3), DataType(1), Reserved(2), STAKey_Mac_Addr(6)
74691 +
74692 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Receive STAKey Message-1 from %02x:%02x:%02x:%02x:%02x:%02x Len=%ld, KeyDataLen=%d\n",
74693 + pAddr[0], pAddr[1], pAddr[2], pAddr[3], pAddr[4], pAddr[5], Len, pEap->KeyDesc.KeyData[1]));
74694 +
74695 + bSTAKeyFrame = TRUE;
74696 + }
74697 +#else
74698 + if ((pEap->KeyDesc.KeyData[0] == 0xDD) && (pEap->KeyDesc.KeyData[2] == 0x00) && (pEap->KeyDesc.KeyData[3] == 0x0F)
74699 + && (pEap->KeyDesc.KeyData[4] == 0xAC) && (pEap->KeyDesc.KeyData[5] == 0x02))
74700 + {
74701 + pAddr = pEap->KeyDesc.KeyData + 8; // Tpe(1), Len(1), OUI(3), DataType(1), Reserved(2)
74702 + pSTAKey = pEap->KeyDesc.KeyData + 14; // Tpe(1), Len(1), OUI(3), DataType(1), Reserved(2), STAKey_Mac_Addr(6)
74703 +
74704 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Receive STAKey Message-1 from %02x:%02x:%02x:%02x:%02x:%02x Len=%d, KeyDataLen=%d\n",
74705 + pAddr[0], pAddr[1], pAddr[2], pAddr[3], pAddr[4], pAddr[5], Len, pEap->KeyDesc.KeyData[1]));
74706 +
74707 + bSTAKeyFrame = TRUE;
74708 + }
74709 +#endif
74710 +
74711 + }
74712 + else if (Len >= (LENGTH_802_11 + 6 + 2 + 2 + sizeof(EAPOL_PACKET) - MAX_LEN_OF_RSNIE))
74713 + {
74714 +#if 0
74715 + RTMPMoveMemory(pAd->StaCfg.ReplayCounter, pEap->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
74716 +
74717 +#endif
74718 + RTMPMoveMemory(pAd->StaCfg.DlsReplayCounter, pEap->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
74719 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Sniff replay counter 2(%02x-%02x-%02x-%02x-%02x-%02x-%02x-%02x) Len=%ld, KeyDataLen=%d\n",
74720 + pAd->StaCfg.ReplayCounter[0], pAd->StaCfg.ReplayCounter[1], pAd->StaCfg.ReplayCounter[2],
74721 + pAd->StaCfg.ReplayCounter[3], pAd->StaCfg.ReplayCounter[4], pAd->StaCfg.ReplayCounter[5],
74722 + pAd->StaCfg.ReplayCounter[6], pAd->StaCfg.ReplayCounter[7], Len, pEap->KeyDesc.KeyData[1]));
74723 +
74724 + }
74725 + }
74726 +
74727 + // If timeout value is equaled to zero, it means always not be timeout.
74728 + // update local dls table entry
74729 + for (i= 0; i < MAX_NUM_OF_INIT_DLS_ENTRY; i++)
74730 + {
74731 + if (pAd->StaCfg.DLSEntry[i].Valid && MAC_ADDR_EQUAL(pAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
74732 + {
74733 + if (bSTAKeyFrame)
74734 + {
74735 + PMAC_TABLE_ENTRY pEntry;
74736 +
74737 + // STAKey frame, add pairwise key table
74738 + pAd->StaCfg.DLSEntry[i].Status = DLS_FINISH;
74739 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74740 +
74741 + PairwiseKey.KeyLen = LEN_TKIP_EK;
74742 + NdisMoveMemory(PairwiseKey.Key, &pSTAKey[0], LEN_TKIP_EK);
74743 + NdisMoveMemory(PairwiseKey.TxMic, &pSTAKey[16], LEN_TKIP_RXMICK);
74744 + NdisMoveMemory(PairwiseKey.RxMic, &pSTAKey[24], LEN_TKIP_TXMICK);
74745 +
74746 + PairwiseKey.CipherAlg = pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg;
74747 +
74748 + pEntry = DlsEntryTableLookup(pAd, pAd->StaCfg.DLSEntry[i].MacAddr, TRUE);
74749 + //AsicAddKeyEntry(pAd, (USHORT)(i + 2), BSS0, 0, &PairwiseKey, TRUE, TRUE); // reserve 0 for multicast, 1 for unicast
74750 + //AsicUpdateRxWCIDTable(pAd, (USHORT)(i + 2), pAddr);
74751 + // Add Pair-wise key to Asic
74752 +#ifdef RT2860
74753 + AsicAddPairwiseKeyEntry(pAd,
74754 + pAd->StaCfg.DLSEntry[i].MacAddr,
74755 + (UCHAR)pAd->StaCfg.DLSEntry[i].MacTabMatchWCID,
74756 + &PairwiseKey);
74757 +
74758 + RTMPAddWcidAttributeEntry(pAd,
74759 + BSS0,
74760 + 0,
74761 + PairwiseKey.CipherAlg,
74762 + pEntry);
74763 +
74764 +#endif // RT2860 //
74765 + NdisMoveMemory(&pEntry->PairwiseKey, &PairwiseKey, sizeof(CIPHER_KEY));
74766 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Receive STAKey Message-1 (Peer STA MAC Address STAKey) \n"));
74767 +
74768 + RTMPSendSTAKeyHandShake(pAd, pAd->StaCfg.DLSEntry[i].MacAddr);
74769 +
74770 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Finish STAKey handshake procedure (Initiator side)\n"));
74771 + }
74772 + else
74773 + {
74774 + // Data frame, update timeout value
74775 + if (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH)
74776 + {
74777 + pAd->StaCfg.DLSEntry[i].CountDownTimer = pAd->StaCfg.DLSEntry[i].TimeOut;
74778 + //AsicUpdateRxWCIDTable(pAd, (USHORT)(i + 2), pAddr);
74779 + }
74780 + }
74781 +
74782 + bFindEntry = TRUE;
74783 + }
74784 + }
74785 +
74786 + // update peer dls table entry
74787 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
74788 + {
74789 + if (pAd->StaCfg.DLSEntry[i].Valid && MAC_ADDR_EQUAL(pAddr, pAd->StaCfg.DLSEntry[i].MacAddr))
74790 + {
74791 + if (bSTAKeyFrame)
74792 + {
74793 + PMAC_TABLE_ENTRY pEntry = NULL;
74794 +
74795 + // STAKey frame, add pairwise key table, and send STAkey Msg-2
74796 + pAd->StaCfg.DLSEntry[i].Status = DLS_FINISH;
74797 + RTMPCancelTimer(&pAd->StaCfg.DLSEntry[i].Timer, &TimerCancelled);
74798 +
74799 + PairwiseKey.KeyLen = LEN_TKIP_EK;
74800 + NdisMoveMemory(PairwiseKey.Key, &pSTAKey[0], LEN_TKIP_EK);
74801 + NdisMoveMemory(PairwiseKey.TxMic, &pSTAKey[16], LEN_TKIP_RXMICK);
74802 + NdisMoveMemory(PairwiseKey.RxMic, &pSTAKey[24], LEN_TKIP_TXMICK);
74803 +
74804 + PairwiseKey.CipherAlg = pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg;
74805 +
74806 + pEntry = DlsEntryTableLookup(pAd, pAd->StaCfg.DLSEntry[i].MacAddr, TRUE);
74807 + //AsicAddKeyEntry(pAd, (USHORT)(i + 2), BSS0, 0, &PairwiseKey, TRUE, TRUE); // reserve 0 for multicast, 1 for unicast
74808 + //AsicUpdateRxWCIDTable(pAd, (USHORT)(i + 2), pAddr);
74809 + // Add Pair-wise key to Asic
74810 +#ifdef RT2860
74811 + AsicAddPairwiseKeyEntry(pAd,
74812 + pAd->StaCfg.DLSEntry[i].MacAddr,
74813 + (UCHAR)pAd->StaCfg.DLSEntry[i].MacTabMatchWCID,
74814 + &PairwiseKey);
74815 +
74816 + RTMPAddWcidAttributeEntry(pAd,
74817 + BSS0,
74818 + 0,
74819 + PairwiseKey.CipherAlg,
74820 + pEntry);
74821 +#endif // RT2860 //
74822 + NdisMoveMemory(&pEntry->PairwiseKey, &PairwiseKey, sizeof(CIPHER_KEY));
74823 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Receive STAKey Message-1 (Initiator STA MAC Address STAKey)\n"));
74824 +
74825 + // If support WPA or WPA2, start STAKey hand shake,
74826 + // If failed hand shake, just tear down peer DLS
74827 + if (RTMPSendSTAKeyHandShake(pAd, pAddr) != NDIS_STATUS_SUCCESS)
74828 + {
74829 + MLME_DLS_REQ_STRUCT MlmeDlsReq;
74830 + USHORT reason = REASON_QOS_CIPHER_NOT_SUPPORT;
74831 +
74832 + pAd->StaCfg.DLSEntry[i].Valid = FALSE;
74833 + pAd->StaCfg.DLSEntry[i].Status = DLS_NONE;
74834 + DlsParmFill(pAd, &MlmeDlsReq, &pAd->StaCfg.DLSEntry[i], reason);
74835 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
74836 + }
74837 + else
74838 + {
74839 + DBGPRINT(RT_DEBUG_TRACE,("DLS - Finish STAKey handshake procedure (Peer side)\n"));
74840 + }
74841 + }
74842 + else
74843 + {
74844 + // Data frame, update timeout value
74845 + if (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH)
74846 + {
74847 + pAd->StaCfg.DLSEntry[i].CountDownTimer = pAd->StaCfg.DLSEntry[i].TimeOut;
74848 + }
74849 + }
74850 +
74851 + bFindEntry = TRUE;
74852 + }
74853 + }
74854 +
74855 +
74856 + return bSTAKeyFrame;
74857 +}
74858 +
74859 +/*
74860 + ========================================================================
74861 +
74862 + Routine Description:
74863 + Check if the frame can be sent through DLS direct link interface
74864 +
74865 + Arguments:
74866 + pAd Pointer to adapter
74867 +
74868 + Return Value:
74869 + DLS entry index
74870 +
74871 + Note:
74872 +
74873 + ========================================================================
74874 +*/
74875 +INT RTMPCheckDLSFrame(
74876 + IN PRTMP_ADAPTER pAd,
74877 + IN PUCHAR pDA)
74878 +{
74879 + INT rval = -1;
74880 + INT i;
74881 +
74882 + if (!pAd->CommonCfg.bDLSCapable)
74883 + return rval;
74884 +
74885 + if (!INFRA_ON(pAd))
74886 + return rval;
74887 +
74888 + do{
74889 + // check local dls table entry
74890 + for (i=0; i<MAX_NUM_OF_INIT_DLS_ENTRY; i++)
74891 + {
74892 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH) &&
74893 + MAC_ADDR_EQUAL(pDA, pAd->StaCfg.DLSEntry[i].MacAddr))
74894 + {
74895 + rval = i;
74896 + break;
74897 + }
74898 + }
74899 +
74900 + // check peer dls table entry
74901 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
74902 + {
74903 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH) &&
74904 + MAC_ADDR_EQUAL(pDA, pAd->StaCfg.DLSEntry[i].MacAddr))
74905 + {
74906 + rval = i;
74907 + break;
74908 + }
74909 + }
74910 + } while (FALSE);
74911 +
74912 + return rval;
74913 +}
74914 +
74915 +/*
74916 + ==========================================================================
74917 + Description:
74918 +
74919 + IRQL = DISPATCH_LEVEL
74920 +
74921 + ==========================================================================
74922 + */
74923 +VOID RTMPSendDLSTearDownFrame(
74924 + IN PRTMP_ADAPTER pAd,
74925 + IN PUCHAR pDA)
74926 +{
74927 + PUCHAR pOutBuffer = NULL;
74928 + NDIS_STATUS NStatus;
74929 + HEADER_802_11 DlsTearDownHdr;
74930 + ULONG FrameLen = 0;
74931 + USHORT Reason = REASON_QOS_QSTA_LEAVING_QBSS;
74932 + UCHAR Category = CATEGORY_DLS;
74933 + UCHAR Action = ACTION_DLS_TEARDOWN;
74934 + UCHAR i = 0;
74935 +
74936 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||
74937 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS))
74938 + return;
74939 +
74940 + DBGPRINT(RT_DEBUG_TRACE, ("Send DLS TearDown Frame \n"));
74941 +
74942 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
74943 + if (NStatus != NDIS_STATUS_SUCCESS)
74944 + {
74945 + DBGPRINT(RT_DEBUG_ERROR,("ASSOC - RTMPSendDLSTearDownFrame() allocate memory failed \n"));
74946 + return;
74947 + }
74948 +
74949 + ActHeaderInit(pAd, &DlsTearDownHdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAd->CommonCfg.Bssid);
74950 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
74951 + sizeof(HEADER_802_11), &DlsTearDownHdr,
74952 + 1, &Category,
74953 + 1, &Action,
74954 + 6, pDA,
74955 + 6, pAd->CurrentAddress,
74956 + 2, &Reason,
74957 + END_OF_ARGS);
74958 +
74959 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
74960 + MlmeFreeMemory(pAd, pOutBuffer);
74961 +
74962 + // Remove key in local dls table entry
74963 + for (i = 0; i < MAX_NUM_OF_INIT_DLS_ENTRY; i++)
74964 + {
74965 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH)
74966 + && MAC_ADDR_EQUAL(pDA, pAd->StaCfg.DLSEntry[i].MacAddr))
74967 + {
74968 + MacTableDeleteDlsEntry(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID, pAd->StaCfg.DLSEntry[i].MacAddr);
74969 + }
74970 + }
74971 +
74972 + // Remove key in peer dls table entry
74973 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
74974 + {
74975 + if (pAd->StaCfg.DLSEntry[i].Valid && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH)
74976 + && MAC_ADDR_EQUAL(pDA, pAd->StaCfg.DLSEntry[i].MacAddr))
74977 + {
74978 + MacTableDeleteDlsEntry(pAd, pAd->StaCfg.DLSEntry[i].MacTabMatchWCID, pAd->StaCfg.DLSEntry[i].MacAddr);
74979 + }
74980 + }
74981 +
74982 + DBGPRINT(RT_DEBUG_TRACE, ("Send DLS TearDown Frame and remove key in (i=%d) \n", i));
74983 +}
74984 +
74985 +/*
74986 + ==========================================================================
74987 + Description:
74988 +
74989 + IRQL = DISPATCH_LEVEL
74990 +
74991 + ==========================================================================
74992 + */
74993 +NDIS_STATUS RTMPSendSTAKeyRequest(
74994 + IN PRTMP_ADAPTER pAd,
74995 + IN PUCHAR pDA)
74996 +{
74997 + UCHAR Header802_3[14];
74998 + NDIS_STATUS NStatus;
74999 + ULONG FrameLen = 0;
75000 + EAPOL_PACKET Packet;
75001 + UCHAR Mic[16];
75002 + UCHAR digest[80];
75003 + PUCHAR pOutBuffer = NULL;
75004 + PNDIS_PACKET pNdisPacket;
75005 + UCHAR temp[64];
75006 + UCHAR DlsPTK[80];
75007 +
75008 + DBGPRINT(RT_DEBUG_TRACE,("DLS - RTMPSendSTAKeyRequest() to %02x:%02x:%02x:%02x:%02x:%02x\n", pDA[0], pDA[1], pDA[2], pDA[3], pDA[4], pDA[5]));
75009 +
75010 + pAd->Sequence ++;
75011 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
75012 +
75013 + // Zero message body
75014 + NdisZeroMemory(&Packet, sizeof(Packet));
75015 + Packet.ProVer = EAPOL_VER;
75016 + Packet.ProType = EAPOLKey;
75017 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE + 6 + MAC_ADDR_LEN; // data field contain KDE andPeer MAC address
75018 +
75019 + // STAKey Message is as EAPOL-Key(1,1,0,0,G/0,0,0, MIC, 0,Peer MAC KDE)
75020 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK))
75021 + {
75022 + Packet.KeyDesc.Type = WPA1_KEY_DESC;
75023 + }
75024 + else if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
75025 + {
75026 + Packet.KeyDesc.Type = WPA2_KEY_DESC;
75027 + }
75028 +
75029 + // Key descriptor version
75030 + Packet.KeyDesc.KeyInfo.KeyDescVer =
75031 + (((pAd->StaCfg.PairCipher == Ndis802_11Encryption3Enabled) || (pAd->StaCfg.GroupCipher == Ndis802_11Encryption3Enabled)) ? (DESC_TYPE_AES) : (DESC_TYPE_TKIP));
75032 +
75033 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
75034 + Packet.KeyDesc.KeyInfo.Secure = 1;
75035 + Packet.KeyDesc.KeyInfo.Request = 1;
75036 +
75037 + Packet.KeyDesc.KeyDataLen[1] = 12;
75038 +
75039 + // use our own OUI to distinguish proprietary with standard.
75040 + Packet.KeyDesc.KeyData[0] = 0xDD;
75041 + Packet.KeyDesc.KeyData[1] = 0x0A;
75042 + Packet.KeyDesc.KeyData[2] = 0x00;
75043 + Packet.KeyDesc.KeyData[3] = 0x0C;
75044 + Packet.KeyDesc.KeyData[4] = 0x43;
75045 + Packet.KeyDesc.KeyData[5] = 0x03;
75046 + NdisMoveMemory(&Packet.KeyDesc.KeyData[6], pDA, MAC_ADDR_LEN);
75047 +
75048 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pAd->StaCfg.DlsReplayCounter, LEN_KEY_DESC_REPLAY);
75049 +
75050 + // Allocate buffer for transmitting message
75051 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer);
75052 + if (NStatus != NDIS_STATUS_SUCCESS)
75053 + return NStatus;
75054 +
75055 + // Prepare EAPOL frame for MIC calculation
75056 + // Be careful, only EAPOL frame is counted for MIC calculation
75057 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
75058 + Packet.Body_Len[1] + 4, &Packet,
75059 + END_OF_ARGS);
75060 +
75061 + // use proprietary PTK
75062 + NdisZeroMemory(temp, 64);
75063 + NdisMoveMemory(temp, "IEEE802.11 WIRELESS ACCESS POINT", 32);
75064 + WpaCountPTK(pAd, temp, temp, pAd->CommonCfg.Bssid, temp, pAd->CurrentAddress, DlsPTK, LEN_PTK);
75065 +
75066 + // calculate MIC
75067 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
75068 + {
75069 + // AES
75070 + NdisZeroMemory(digest, sizeof(digest));
75071 + HMAC_SHA1(pOutBuffer, FrameLen, DlsPTK, LEN_EAP_MICK, digest);
75072 + NdisMoveMemory(Packet.KeyDesc.KeyMic, digest, LEN_KEY_DESC_MIC);
75073 + }
75074 + else
75075 + {
75076 + NdisZeroMemory(Mic, sizeof(Mic));
75077 + hmac_md5(DlsPTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
75078 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
75079 + }
75080 +
75081 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
75082 + sizeof(Header802_3), Header802_3,
75083 + Packet.Body_Len[1] + 4, &Packet,
75084 + END_OF_ARGS);
75085 +
75086 + NStatus = RTMPAllocateNdisPacket(pAd, &pNdisPacket, NULL, 0, pOutBuffer, FrameLen);
75087 + if (NStatus == NDIS_STATUS_SUCCESS)
75088 + {
75089 + RTMP_SET_PACKET_WCID(pNdisPacket, BSSID_WCID);
75090 + STASendPacket(pAd, pNdisPacket);
75091 + RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
75092 + }
75093 +
75094 + MlmeFreeMemory(pAd, pOutBuffer);
75095 +
75096 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSendSTAKeyRequest- Send STAKey request (NStatus=%x, FrameLen=%ld)\n", NStatus, FrameLen));
75097 +
75098 + return NStatus;
75099 +}
75100 +
75101 +/*
75102 + ==========================================================================
75103 + Description:
75104 +
75105 + IRQL = DISPATCH_LEVEL
75106 +
75107 + ==========================================================================
75108 + */
75109 +NDIS_STATUS RTMPSendSTAKeyHandShake(
75110 + IN PRTMP_ADAPTER pAd,
75111 + IN PUCHAR pDA)
75112 +{
75113 + UCHAR Header802_3[14];
75114 + NDIS_STATUS NStatus;
75115 + ULONG FrameLen = 0;
75116 + EAPOL_PACKET Packet;
75117 + UCHAR Mic[16];
75118 + UCHAR digest[80];
75119 + PUCHAR pOutBuffer = NULL;
75120 + PNDIS_PACKET pNdisPacket;
75121 + UCHAR temp[64];
75122 + UCHAR DlsPTK[80]; // Due to dirver can not get PTK, use proprietary PTK
75123 +
75124 + DBGPRINT(RT_DEBUG_TRACE,("DLS - RTMPSendSTAKeyHandShake() to %02x:%02x:%02x:%02x:%02x:%02x\n", pDA[0], pDA[1], pDA[2], pDA[3], pDA[4], pDA[5]));
75125 +
75126 + pAd->Sequence ++;
75127 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
75128 +
75129 + // Zero message body
75130 + NdisZeroMemory(&Packet, sizeof(Packet));
75131 + Packet.ProVer = EAPOL_VER;
75132 + Packet.ProType = EAPOLKey;
75133 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE + 6 + MAC_ADDR_LEN; // data field contain KDE and Peer MAC address
75134 +
75135 + // STAKey Message is as EAPOL-Key(1,1,0,0,G/0,0,0, MIC, 0,Peer MAC KDE)
75136 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK))
75137 + {
75138 + Packet.KeyDesc.Type = WPA1_KEY_DESC;
75139 + }
75140 + else if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK))
75141 + {
75142 + Packet.KeyDesc.Type = WPA2_KEY_DESC;
75143 + }
75144 +
75145 + // Key descriptor version
75146 + Packet.KeyDesc.KeyInfo.KeyDescVer =
75147 + (((pAd->StaCfg.PairCipher == Ndis802_11Encryption3Enabled) || (pAd->StaCfg.GroupCipher == Ndis802_11Encryption3Enabled)) ? (DESC_TYPE_AES) : (DESC_TYPE_TKIP));
75148 +
75149 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
75150 + Packet.KeyDesc.KeyInfo.Secure = 1;
75151 +
75152 + Packet.KeyDesc.KeyDataLen[1] = 12;
75153 +
75154 + // use our own OUI to distinguish proprietary with standard.
75155 + Packet.KeyDesc.KeyData[0] = 0xDD;
75156 + Packet.KeyDesc.KeyData[1] = 0x0A;
75157 + Packet.KeyDesc.KeyData[2] = 0x00;
75158 + Packet.KeyDesc.KeyData[3] = 0x0C;
75159 + Packet.KeyDesc.KeyData[4] = 0x43;
75160 + Packet.KeyDesc.KeyData[5] = 0x03;
75161 + NdisMoveMemory(&Packet.KeyDesc.KeyData[6], pDA, MAC_ADDR_LEN);
75162 +
75163 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pAd->StaCfg.DlsReplayCounter, LEN_KEY_DESC_REPLAY);
75164 +
75165 + // Allocate buffer for transmitting message
75166 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer);
75167 + if (NStatus != NDIS_STATUS_SUCCESS)
75168 + return NStatus;
75169 +
75170 + // Prepare EAPOL frame for MIC calculation
75171 + // Be careful, only EAPOL frame is counted for MIC calculation
75172 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
75173 + Packet.Body_Len[1] + 4, &Packet,
75174 + END_OF_ARGS);
75175 +
75176 + // use proprietary PTK
75177 + NdisZeroMemory(temp, 64);
75178 + NdisMoveMemory(temp, "IEEE802.11 WIRELESS ACCESS POINT", 32);
75179 + WpaCountPTK(pAd, temp, temp, pAd->CommonCfg.Bssid, temp, pAd->CurrentAddress, DlsPTK, LEN_PTK);
75180 +
75181 + // calculate MIC
75182 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
75183 + {
75184 + // AES
75185 + NdisZeroMemory(digest, sizeof(digest));
75186 + HMAC_SHA1(pOutBuffer, FrameLen, DlsPTK, LEN_EAP_MICK, digest);
75187 + NdisMoveMemory(Packet.KeyDesc.KeyMic, digest, LEN_KEY_DESC_MIC);
75188 + }
75189 + else
75190 + {
75191 + NdisZeroMemory(Mic, sizeof(Mic));
75192 + hmac_md5(DlsPTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
75193 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
75194 + }
75195 +
75196 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
75197 + sizeof(Header802_3), Header802_3,
75198 + Packet.Body_Len[1] + 4, &Packet,
75199 + END_OF_ARGS);
75200 +
75201 + NStatus = RTMPAllocateNdisPacket(pAd, &pNdisPacket, NULL, 0, pOutBuffer, FrameLen);
75202 + if (NStatus == NDIS_STATUS_SUCCESS)
75203 + {
75204 + RTMP_SET_PACKET_WCID(pNdisPacket, BSSID_WCID);
75205 + STASendPacket(pAd, pNdisPacket);
75206 + RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
75207 + }
75208 +
75209 + MlmeFreeMemory(pAd, pOutBuffer);
75210 +
75211 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPSendSTAKeyHandShake- Send STAKey Message-2 (NStatus=%x, FrameLen=%ld)\n", NStatus, FrameLen));
75212 +
75213 + return NStatus;
75214 +}
75215 +
75216 +VOID DlsTimeoutAction(
75217 + IN PVOID SystemSpecific1,
75218 + IN PVOID FunctionContext,
75219 + IN PVOID SystemSpecific2,
75220 + IN PVOID SystemSpecific3)
75221 +{
75222 + MLME_DLS_REQ_STRUCT MlmeDlsReq;
75223 + USHORT reason;
75224 + PRT_802_11_DLS pDLS = (PRT_802_11_DLS)FunctionContext;
75225 + PRTMP_ADAPTER pAd = pDLS->pAd;
75226 +
75227 + DBGPRINT(RT_DEBUG_TRACE, ("DlsTimeout - Tear down DLS links (%02x:%02x:%02x:%02x:%02x:%02x)\n",
75228 + pDLS->MacAddr[0], pDLS->MacAddr[1], pDLS->MacAddr[2], pDLS->MacAddr[3], pDLS->MacAddr[4], pDLS->MacAddr[5]));
75229 +
75230 + if ((pDLS) && (pDLS->Valid))
75231 + {
75232 + reason = REASON_QOS_REQUEST_TIMEOUT;
75233 + pDLS->Valid = FALSE;
75234 + pDLS->Status = DLS_NONE;
75235 + DlsParmFill(pAd, &MlmeDlsReq, pDLS, reason);
75236 + MlmeEnqueue(pAd, DLS_STATE_MACHINE, MT2_MLME_DLS_TEAR_DOWN, sizeof(MLME_DLS_REQ_STRUCT), &MlmeDlsReq);
75237 + RT28XX_MLME_HANDLER(pAd);
75238 + }
75239 +}
75240 +
75241 +/*
75242 +================================================================
75243 +Description : because DLS and CLI share the same WCID table in ASIC.
75244 +Mesh entry also insert to pAd->MacTab.content[]. Such is marked as ValidAsDls = TRUE.
75245 +Also fills the pairwise key.
75246 +Because front MAX_AID_BA entries have direct mapping to BAEntry, which is only used as CLI. So we insert Dls
75247 +from index MAX_AID_BA.
75248 +================================================================
75249 +*/
75250 +MAC_TABLE_ENTRY *MacTableInsertDlsEntry(
75251 + IN PRTMP_ADAPTER pAd,
75252 + IN PUCHAR pAddr,
75253 + IN UINT DlsEntryIdx)
75254 +{
75255 + PMAC_TABLE_ENTRY pEntry = NULL;
75256 +
75257 + DBGPRINT(RT_DEBUG_TRACE, ("====> MacTableInsertDlsEntry\n"));
75258 + // if FULL, return
75259 + if (pAd->MacTab.Size >= MAX_LEN_OF_MAC_TABLE)
75260 + return NULL;
75261 +
75262 + do
75263 + {
75264 + if((pEntry = DlsEntryTableLookup(pAd, pAddr, TRUE)) != NULL)
75265 + break;
75266 +
75267 + // allocate one MAC entry
75268 + pEntry = MacTableInsertEntry(pAd, pAddr, DlsEntryIdx + MIN_NET_DEVICE_FOR_DLS, TRUE);
75269 + if (pEntry)
75270 + {
75271 + pAd->StaCfg.DLSEntry[DlsEntryIdx].MacTabMatchWCID = pEntry->Aid;
75272 + pEntry->MatchDlsEntryIdx = DlsEntryIdx;
75273 + pEntry->AuthMode = pAd->StaCfg.AuthMode;
75274 + pEntry->WepStatus = pAd->StaCfg.WepStatus;
75275 + pEntry->PortSecured = WPA_802_1X_PORT_SECURED;
75276 +
75277 + DBGPRINT(RT_DEBUG_TRACE, ("MacTableInsertDlsEntry - allocate entry #%d, Total= %d\n",pEntry->Aid, pAd->MacTab.Size));
75278 +
75279 + // If legacy WEP is used, set pair-wise cipherAlg into WCID attribute table for this entry
75280 + if ((pEntry->ValidAsDls) && (pEntry->WepStatus == Ndis802_11WEPEnabled))
75281 + {
75282 + UCHAR KeyIdx = 0;
75283 + UCHAR CipherAlg = 0;
75284 +
75285 + KeyIdx = pAd->StaCfg.DefaultKeyId;
75286 +
75287 + CipherAlg = pAd->SharedKey[BSS0][KeyIdx].CipherAlg;
75288 +
75289 + RTMPAddWcidAttributeEntry(pAd,
75290 + BSS0,
75291 + pAd->StaCfg.DefaultKeyId,
75292 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg,
75293 + pEntry);
75294 + }
75295 +
75296 + break;
75297 + }
75298 + } while(FALSE);
75299 +
75300 + DBGPRINT(RT_DEBUG_TRACE, ("<==== MacTableInsertDlsEntry\n"));
75301 +
75302 + return pEntry;
75303 +}
75304 +
75305 +
75306 +/*
75307 + ==========================================================================
75308 + Description:
75309 + Delete all Mesh Entry in pAd->MacTab
75310 + ==========================================================================
75311 + */
75312 +BOOLEAN MacTableDeleteDlsEntry(
75313 + IN PRTMP_ADAPTER pAd,
75314 + IN USHORT wcid,
75315 + IN PUCHAR pAddr)
75316 +{
75317 + DBGPRINT(RT_DEBUG_TRACE, ("====> MacTableDeleteDlsEntry\n"));
75318 +
75319 + if (!VALID_WCID(wcid))
75320 + return FALSE;
75321 +
75322 + MacTableDeleteEntry(pAd, wcid, pAddr);
75323 +
75324 + DBGPRINT(RT_DEBUG_TRACE, ("<==== MacTableDeleteDlsEntry\n"));
75325 +
75326 + return TRUE;
75327 +}
75328 +
75329 +MAC_TABLE_ENTRY *DlsEntryTableLookup(
75330 + IN PRTMP_ADAPTER pAd,
75331 + IN PUCHAR pAddr,
75332 + IN BOOLEAN bResetIdelCount)
75333 +{
75334 + ULONG HashIdx;
75335 + MAC_TABLE_ENTRY *pEntry = NULL;
75336 +
75337 + RTMP_SEM_LOCK(&pAd->MacTabLock);
75338 + HashIdx = MAC_ADDR_HASH_INDEX(pAddr);
75339 + pEntry = pAd->MacTab.Hash[HashIdx];
75340 +
75341 + while (pEntry)
75342 + {
75343 + if ((pEntry->ValidAsDls == TRUE)
75344 + && MAC_ADDR_EQUAL(pEntry->Addr, pAddr))
75345 + {
75346 + if(bResetIdelCount)
75347 + pEntry->NoDataIdleCount = 0;
75348 + break;
75349 + }
75350 + else
75351 + pEntry = pEntry->pNext;
75352 + }
75353 +
75354 + RTMP_SEM_UNLOCK(&pAd->MacTabLock);
75355 + return pEntry;
75356 +}
75357 +
75358 +MAC_TABLE_ENTRY *DlsEntryTableLookupByWcid(
75359 + IN PRTMP_ADAPTER pAd,
75360 + IN UCHAR wcid,
75361 + IN PUCHAR pAddr,
75362 + IN BOOLEAN bResetIdelCount)
75363 +{
75364 + ULONG DLsIndex;
75365 + PMAC_TABLE_ENTRY pCurEntry = NULL;
75366 + PMAC_TABLE_ENTRY pEntry = NULL;
75367 +
75368 + if (!VALID_WCID(wcid))
75369 + return NULL;
75370 +
75371 + RTMP_SEM_LOCK(&pAd->MacTabLock);
75372 +
75373 + do
75374 + {
75375 + pCurEntry = &pAd->MacTab.Content[wcid];
75376 +
75377 + DLsIndex = 0xff;
75378 + if ((pCurEntry) && (pCurEntry->ValidAsDls== TRUE))
75379 + {
75380 + DLsIndex = pCurEntry->MatchDlsEntryIdx;
75381 + }
75382 +
75383 + if (DLsIndex == 0xff)
75384 + break;
75385 +
75386 + if (MAC_ADDR_EQUAL(pCurEntry->Addr, pAddr))
75387 + {
75388 + if(bResetIdelCount)
75389 + pCurEntry->NoDataIdleCount = 0;
75390 + pEntry = pCurEntry;
75391 + break;
75392 + }
75393 + } while(FALSE);
75394 +
75395 + RTMP_SEM_UNLOCK(&pAd->MacTabLock);
75396 +
75397 + return pEntry;
75398 +}
75399 +
75400 +INT Set_DlsEntryInfo_Display_Proc(
75401 + IN PRTMP_ADAPTER pAd,
75402 + IN PUCHAR arg)
75403 +{
75404 + INT i;
75405 +
75406 + printk("\n%-19s%-8s\n", "MAC", "TIMEOUT\n");
75407 + for (i=0; i<MAX_NUM_OF_DLS_ENTRY; i++)
75408 + {
75409 + if ((pAd->StaCfg.DLSEntry[i].Valid) && (pAd->StaCfg.DLSEntry[i].Status == DLS_FINISH))
75410 + {
75411 + PMAC_TABLE_ENTRY pEntry = &pAd->MacTab.Content[pAd->StaCfg.DLSEntry[i].MacTabMatchWCID];
75412 +
75413 + printk("%02x:%02x:%02x:%02x:%02x:%02x ",
75414 + pAd->StaCfg.DLSEntry[i].MacAddr[0], pAd->StaCfg.DLSEntry[i].MacAddr[1], pAd->StaCfg.DLSEntry[i].MacAddr[2],
75415 + pAd->StaCfg.DLSEntry[i].MacAddr[3], pAd->StaCfg.DLSEntry[i].MacAddr[4], pAd->StaCfg.DLSEntry[i].MacAddr[5]);
75416 + printk("%-8d\n", pAd->StaCfg.DLSEntry[i].TimeOut);
75417 +
75418 + printk("\n");
75419 + printk("\n%-19s%-4s%-4s%-4s%-4s%-8s%-7s%-7s%-7s%-10s%-6s%-6s%-6s%-6s\n",
75420 + "MAC", "AID", "BSS", "PSM", "WMM", "MIMOPS", "RSSI0", "RSSI1", "RSSI2", "PhMd", "BW", "MCS", "SGI", "STBC");
75421 + printk("%02X:%02X:%02X:%02X:%02X:%02X ",
75422 + pEntry->Addr[0], pEntry->Addr[1], pEntry->Addr[2],
75423 + pEntry->Addr[3], pEntry->Addr[4], pEntry->Addr[5]);
75424 + printk("%-4d", (int)pEntry->Aid);
75425 + printk("%-4d", (int)pEntry->apidx);
75426 + printk("%-4d", (int)pEntry->PsMode);
75427 + printk("%-4d", (int)CLIENT_STATUS_TEST_FLAG(pEntry, fCLIENT_STATUS_WMM_CAPABLE));
75428 + printk("%-8d", (int)pEntry->MmpsMode);
75429 + printk("%-7d", pEntry->RssiSample.AvgRssi0);
75430 + printk("%-7d", pEntry->RssiSample.AvgRssi1);
75431 + printk("%-7d", pEntry->RssiSample.AvgRssi2);
75432 + printk("%-10s", GetPhyMode(pEntry->HTPhyMode.field.MODE));
75433 + printk("%-6s", GetBW(pEntry->HTPhyMode.field.BW));
75434 + printk("%-6d", pEntry->HTPhyMode.field.MCS);
75435 + printk("%-6d", pEntry->HTPhyMode.field.ShortGI);
75436 + printk("%-6d", pEntry->HTPhyMode.field.STBC);
75437 + printk("%-10d, %d, %d%%\n", pEntry->DebugFIFOCount, pEntry->DebugTxCount,
75438 + (pEntry->DebugTxCount) ? ((pEntry->DebugTxCount-pEntry->DebugFIFOCount)*100/pEntry->DebugTxCount) : 0);
75439 + printk("\n");
75440 +
75441 + }
75442 + }
75443 +
75444 + return TRUE;
75445 +}
75446 +
75447 +INT Set_DlsAddEntry_Proc(
75448 + IN PRTMP_ADAPTER pAd,
75449 + IN PUCHAR arg)
75450 +{
75451 + UCHAR mac[MAC_ADDR_LEN];
75452 + USHORT Timeout;
75453 + char *token, sepValue[] = ":", DASH = '-';
75454 + INT i;
75455 + RT_802_11_DLS Dls;
75456 +
75457 + if(strlen(arg) < 19) //Mac address acceptable format 01:02:03:04:05:06 length 17 plus the "-" and timeout value in decimal format.
75458 + return FALSE;
75459 +
75460 + token = strchr(arg, DASH);
75461 + if ((token != NULL) && (strlen(token)>1))
75462 + {
75463 + Timeout = simple_strtol((token+1), 0, 10);
75464 +
75465 + *token = '\0';
75466 + for (i = 0, token = rstrtok(arg, &sepValue[0]); token; token = rstrtok(NULL, &sepValue[0]), i++)
75467 + {
75468 + if((strlen(token) != 2) || (!isxdigit(*token)) || (!isxdigit(*(token+1))))
75469 + return FALSE;
75470 + AtoH(token, (PUCHAR)(&mac[i]), 1);
75471 + }
75472 + if(i != 6)
75473 + return FALSE;
75474 +
75475 + printk("\n%02x:%02x:%02x:%02x:%02x:%02x-%d", mac[0], mac[1],
75476 + mac[2], mac[3], mac[4], mac[5], (int)Timeout);
75477 +
75478 + NdisZeroMemory(&Dls, sizeof(RT_802_11_DLS));
75479 + Dls.TimeOut = Timeout;
75480 + COPY_MAC_ADDR(Dls.MacAddr, mac);
75481 + Dls.Valid = 1;
75482 +
75483 + MlmeEnqueue(pAd,
75484 + MLME_CNTL_STATE_MACHINE,
75485 + RT_OID_802_11_SET_DLS_PARAM,
75486 + sizeof(RT_802_11_DLS),
75487 + &Dls);
75488 +
75489 + return TRUE;
75490 + }
75491 +
75492 + return FALSE;
75493 +
75494 +}
75495 +
75496 +INT Set_DlsTearDownEntry_Proc(
75497 + IN PRTMP_ADAPTER pAd,
75498 + IN PUCHAR arg)
75499 +{
75500 + UCHAR macAddr[MAC_ADDR_LEN];
75501 + CHAR *value;
75502 + INT i;
75503 + RT_802_11_DLS Dls;
75504 +
75505 + if(strlen(arg) != 17) //Mac address acceptable format 01:02:03:04:05:06 length 17
75506 + return FALSE;
75507 +
75508 + for (i=0, value = rstrtok(arg,":"); value; value = rstrtok(NULL,":"))
75509 + {
75510 + if((strlen(value) != 2) || (!isxdigit(*value)) || (!isxdigit(*(value+1))) )
75511 + return FALSE; //Invalid
75512 +
75513 + AtoH(value, &macAddr[i++], 2);
75514 + }
75515 +
75516 + printk("\n%02x:%02x:%02x:%02x:%02x:%02x", macAddr[0], macAddr[1],
75517 + macAddr[2], macAddr[3], macAddr[4], macAddr[5]);
75518 +
75519 + NdisZeroMemory(&Dls, sizeof(RT_802_11_DLS));
75520 + COPY_MAC_ADDR(Dls.MacAddr, macAddr);
75521 + Dls.Valid = 0;
75522 +
75523 + MlmeEnqueue(pAd,
75524 + MLME_CNTL_STATE_MACHINE,
75525 + RT_OID_802_11_SET_DLS_PARAM,
75526 + sizeof(RT_802_11_DLS),
75527 + &Dls);
75528 +
75529 + return TRUE;
75530 +}
75531 +
75532 --- /dev/null
75533 +++ b/drivers/staging/rt2860/sta_ioctl.c
75534 @@ -0,0 +1,6944 @@
75535 +/*
75536 + *************************************************************************
75537 + * Ralink Tech Inc.
75538 + * 5F., No.36, Taiyuan St., Jhubei City,
75539 + * Hsinchu County 302,
75540 + * Taiwan, R.O.C.
75541 + *
75542 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
75543 + *
75544 + * This program is free software; you can redistribute it and/or modify *
75545 + * it under the terms of the GNU General Public License as published by *
75546 + * the Free Software Foundation; either version 2 of the License, or *
75547 + * (at your option) any later version. *
75548 + * *
75549 + * This program is distributed in the hope that it will be useful, *
75550 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
75551 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
75552 + * GNU General Public License for more details. *
75553 + * *
75554 + * You should have received a copy of the GNU General Public License *
75555 + * along with this program; if not, write to the *
75556 + * Free Software Foundation, Inc., *
75557 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
75558 + * *
75559 + *************************************************************************
75560 +
75561 + Module Name:
75562 + sta_ioctl.c
75563 +
75564 + Abstract:
75565 + IOCTL related subroutines
75566 +
75567 + Revision History:
75568 + Who When What
75569 + -------- ---------- ----------------------------------------------
75570 + Rory Chen 01-03-2003 created
75571 + Rory Chen 02-14-2005 modify to support RT61
75572 +*/
75573 +
75574 +#include "rt_config.h"
75575 +
75576 +#ifdef DBG
75577 +extern ULONG RTDebugLevel;
75578 +#endif
75579 +
75580 +#define NR_WEP_KEYS 4
75581 +#define WEP_SMALL_KEY_LEN (40/8)
75582 +#define WEP_LARGE_KEY_LEN (104/8)
75583 +
75584 +#define GROUP_KEY_NO 4
75585 +
75586 +#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,27)
75587 +#define IWE_STREAM_ADD_EVENT(_A, _B, _C, _D, _E) iwe_stream_add_event(_A, _B, _C, _D, _E)
75588 +#define IWE_STREAM_ADD_POINT(_A, _B, _C, _D, _E) iwe_stream_add_point(_A, _B, _C, _D, _E)
75589 +#define IWE_STREAM_ADD_VALUE(_A, _B, _C, _D, _E, _F) iwe_stream_add_value(_A, _B, _C, _D, _E, _F)
75590 +#else
75591 +#define IWE_STREAM_ADD_EVENT(_A, _B, _C, _D, _E) iwe_stream_add_event(_B, _C, _D, _E)
75592 +#define IWE_STREAM_ADD_POINT(_A, _B, _C, _D, _E) iwe_stream_add_point(_B, _C, _D, _E)
75593 +#define IWE_STREAM_ADD_VALUE(_A, _B, _C, _D, _E, _F) iwe_stream_add_value(_B, _C, _D, _E, _F)
75594 +#endif
75595 +
75596 +extern UCHAR CipherWpa2Template[];
75597 +extern UCHAR CipherWpaPskTkip[];
75598 +extern UCHAR CipherWpaPskTkipLen;
75599 +
75600 +typedef struct PACKED _RT_VERSION_INFO{
75601 + UCHAR DriverVersionW;
75602 + UCHAR DriverVersionX;
75603 + UCHAR DriverVersionY;
75604 + UCHAR DriverVersionZ;
75605 + UINT DriverBuildYear;
75606 + UINT DriverBuildMonth;
75607 + UINT DriverBuildDay;
75608 +} RT_VERSION_INFO, *PRT_VERSION_INFO;
75609 +
75610 +struct iw_priv_args privtab[] = {
75611 +{ RTPRIV_IOCTL_SET,
75612 + IW_PRIV_TYPE_CHAR | 1024, 0,
75613 + "set"},
75614 +
75615 +{ RTPRIV_IOCTL_SHOW, 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK,
75616 + ""},
75617 +{ RTPRIV_IOCTL_SHOW, IW_PRIV_TYPE_CHAR | 1024, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK,
75618 + ""},
75619 +/* --- sub-ioctls definitions --- */
75620 + { SHOW_CONN_STATUS,
75621 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "connStatus" },
75622 + { SHOW_DRVIER_VERION,
75623 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "driverVer" },
75624 + { SHOW_BA_INFO,
75625 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "bainfo" },
75626 + { SHOW_DESC_INFO,
75627 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "descinfo" },
75628 + { RAIO_OFF,
75629 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "radio_off" },
75630 + { RAIO_ON,
75631 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "radio_on" },
75632 +#ifdef QOS_DLS_SUPPORT
75633 + { SHOW_DLS_ENTRY_INFO,
75634 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "dlsentryinfo" },
75635 +#endif // QOS_DLS_SUPPORT //
75636 + { SHOW_CFG_VALUE,
75637 + IW_PRIV_TYPE_CHAR | 1024, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, "show" },
75638 +/* --- sub-ioctls relations --- */
75639 +
75640 +#ifdef DBG
75641 +{ RTPRIV_IOCTL_BBP,
75642 + IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK,
75643 + "bbp"},
75644 +{ RTPRIV_IOCTL_MAC,
75645 + IW_PRIV_TYPE_CHAR | 1024, IW_PRIV_TYPE_CHAR | 1024,
75646 + "mac"},
75647 +{ RTPRIV_IOCTL_E2P,
75648 + IW_PRIV_TYPE_CHAR | 1024, IW_PRIV_TYPE_CHAR | 1024,
75649 + "e2p"},
75650 +#endif /* DBG */
75651 +
75652 +{ RTPRIV_IOCTL_STATISTICS,
75653 + 0, IW_PRIV_TYPE_CHAR | IW_PRIV_SIZE_MASK,
75654 + "stat"},
75655 +{ RTPRIV_IOCTL_GSITESURVEY,
75656 + 0, IW_PRIV_TYPE_CHAR | 1024,
75657 + "get_site_survey"},
75658 +};
75659 +
75660 +INT Set_SSID_Proc(
75661 + IN PRTMP_ADAPTER pAdapter,
75662 + IN PUCHAR arg);
75663 +
75664 +#ifdef WMM_SUPPORT
75665 +INT Set_WmmCapable_Proc(
75666 + IN PRTMP_ADAPTER pAd,
75667 + IN PUCHAR arg);
75668 +#endif
75669 +
75670 +INT Set_NetworkType_Proc(
75671 + IN PRTMP_ADAPTER pAdapter,
75672 + IN PUCHAR arg);
75673 +
75674 +INT Set_AuthMode_Proc(
75675 + IN PRTMP_ADAPTER pAdapter,
75676 + IN PUCHAR arg);
75677 +
75678 +INT Set_EncrypType_Proc(
75679 + IN PRTMP_ADAPTER pAdapter,
75680 + IN PUCHAR arg);
75681 +
75682 +INT Set_DefaultKeyID_Proc(
75683 + IN PRTMP_ADAPTER pAdapter,
75684 + IN PUCHAR arg);
75685 +
75686 +INT Set_Key1_Proc(
75687 + IN PRTMP_ADAPTER pAdapter,
75688 + IN PUCHAR arg);
75689 +
75690 +INT Set_Key2_Proc(
75691 + IN PRTMP_ADAPTER pAdapter,
75692 + IN PUCHAR arg);
75693 +
75694 +INT Set_Key3_Proc(
75695 + IN PRTMP_ADAPTER pAdapter,
75696 + IN PUCHAR arg);
75697 +
75698 +INT Set_Key4_Proc(
75699 + IN PRTMP_ADAPTER pAdapter,
75700 + IN PUCHAR arg);
75701 +
75702 +INT Set_WPAPSK_Proc(
75703 + IN PRTMP_ADAPTER pAdapter,
75704 + IN PUCHAR arg);
75705 +
75706 +
75707 +INT Set_PSMode_Proc(
75708 + IN PRTMP_ADAPTER pAdapter,
75709 + IN PUCHAR arg);
75710 +
75711 +#ifdef WPA_SUPPLICANT_SUPPORT
75712 +INT Set_Wpa_Support(
75713 + IN PRTMP_ADAPTER pAd,
75714 + IN PUCHAR arg);
75715 +#endif // WPA_SUPPLICANT_SUPPORT //
75716 +
75717 +#ifdef DBG
75718 +VOID RTMPIoctlBBP(
75719 + IN PRTMP_ADAPTER pAdapter,
75720 + IN struct iwreq *wrq);
75721 +
75722 +VOID RTMPIoctlMAC(
75723 + IN PRTMP_ADAPTER pAdapter,
75724 + IN struct iwreq *wrq);
75725 +
75726 +VOID RTMPIoctlE2PROM(
75727 + IN PRTMP_ADAPTER pAdapter,
75728 + IN struct iwreq *wrq);
75729 +#endif // DBG //
75730 +
75731 +
75732 +NDIS_STATUS RTMPWPANoneAddKeyProc(
75733 + IN PRTMP_ADAPTER pAd,
75734 + IN PVOID pBuf);
75735 +
75736 +INT Set_FragTest_Proc(
75737 + IN PRTMP_ADAPTER pAdapter,
75738 + IN PUCHAR arg);
75739 +
75740 +#ifdef DOT11_N_SUPPORT
75741 +INT Set_TGnWifiTest_Proc(
75742 + IN PRTMP_ADAPTER pAd,
75743 + IN PUCHAR arg);
75744 +#endif // DOT11_N_SUPPORT //
75745 +
75746 +INT Set_LongRetryLimit_Proc(
75747 + IN PRTMP_ADAPTER pAdapter,
75748 + IN PUCHAR arg);
75749 +
75750 +INT Set_ShortRetryLimit_Proc(
75751 + IN PRTMP_ADAPTER pAdapter,
75752 + IN PUCHAR arg);
75753 +
75754 +#ifdef EXT_BUILD_CHANNEL_LIST
75755 +INT Set_Ieee80211dClientMode_Proc(
75756 + IN PRTMP_ADAPTER pAdapter,
75757 + IN PUCHAR arg);
75758 +#endif // EXT_BUILD_CHANNEL_LIST //
75759 +
75760 +#ifdef CARRIER_DETECTION_SUPPORT
75761 +INT Set_CarrierDetect_Proc(
75762 + IN PRTMP_ADAPTER pAd,
75763 + IN PUCHAR arg);
75764 +#endif // CARRIER_DETECTION_SUPPORT //
75765 +
75766 +static struct {
75767 + CHAR *name;
75768 + INT (*set_proc)(PRTMP_ADAPTER pAdapter, PUCHAR arg);
75769 +} *PRTMP_PRIVATE_SET_PROC, RTMP_PRIVATE_SUPPORT_PROC[] = {
75770 + {"DriverVersion", Set_DriverVersion_Proc},
75771 + {"CountryRegion", Set_CountryRegion_Proc},
75772 + {"CountryRegionABand", Set_CountryRegionABand_Proc},
75773 + {"SSID", Set_SSID_Proc},
75774 + {"WirelessMode", Set_WirelessMode_Proc},
75775 + {"TxBurst", Set_TxBurst_Proc},
75776 + {"TxPreamble", Set_TxPreamble_Proc},
75777 + {"TxPower", Set_TxPower_Proc},
75778 + {"Channel", Set_Channel_Proc},
75779 + {"BGProtection", Set_BGProtection_Proc},
75780 + {"RTSThreshold", Set_RTSThreshold_Proc},
75781 + {"FragThreshold", Set_FragThreshold_Proc},
75782 +#ifdef DOT11_N_SUPPORT
75783 + {"HtBw", Set_HtBw_Proc},
75784 + {"HtMcs", Set_HtMcs_Proc},
75785 + {"HtGi", Set_HtGi_Proc},
75786 + {"HtOpMode", Set_HtOpMode_Proc},
75787 + {"HtExtcha", Set_HtExtcha_Proc},
75788 + {"HtMpduDensity", Set_HtMpduDensity_Proc},
75789 + {"HtBaWinSize", Set_HtBaWinSize_Proc},
75790 + {"HtRdg", Set_HtRdg_Proc},
75791 + {"HtAmsdu", Set_HtAmsdu_Proc},
75792 + {"HtAutoBa", Set_HtAutoBa_Proc},
75793 + {"HtBaDecline", Set_BADecline_Proc},
75794 + {"HtProtect", Set_HtProtect_Proc},
75795 + {"HtMimoPs", Set_HtMimoPs_Proc},
75796 +#endif // DOT11_N_SUPPORT //
75797 +
75798 +#ifdef AGGREGATION_SUPPORT
75799 + {"PktAggregate", Set_PktAggregate_Proc},
75800 +#endif
75801 +
75802 +#ifdef WMM_SUPPORT
75803 + {"WmmCapable", Set_WmmCapable_Proc},
75804 +#endif
75805 + {"IEEE80211H", Set_IEEE80211H_Proc},
75806 + {"NetworkType", Set_NetworkType_Proc},
75807 + {"AuthMode", Set_AuthMode_Proc},
75808 + {"EncrypType", Set_EncrypType_Proc},
75809 + {"DefaultKeyID", Set_DefaultKeyID_Proc},
75810 + {"Key1", Set_Key1_Proc},
75811 + {"Key2", Set_Key2_Proc},
75812 + {"Key3", Set_Key3_Proc},
75813 + {"Key4", Set_Key4_Proc},
75814 + {"WPAPSK", Set_WPAPSK_Proc},
75815 + {"ResetCounter", Set_ResetStatCounter_Proc},
75816 + {"PSMode", Set_PSMode_Proc},
75817 +#ifdef DBG
75818 + {"Debug", Set_Debug_Proc},
75819 +#endif
75820 +
75821 +#ifdef RALINK_ATE
75822 + {"ATE", Set_ATE_Proc},
75823 + {"ATEDA", Set_ATE_DA_Proc},
75824 + {"ATESA", Set_ATE_SA_Proc},
75825 + {"ATEBSSID", Set_ATE_BSSID_Proc},
75826 + {"ATECHANNEL", Set_ATE_CHANNEL_Proc},
75827 + {"ATETXPOW0", Set_ATE_TX_POWER0_Proc},
75828 + {"ATETXPOW1", Set_ATE_TX_POWER1_Proc},
75829 + {"ATETXANT", Set_ATE_TX_Antenna_Proc},
75830 + {"ATERXANT", Set_ATE_RX_Antenna_Proc},
75831 + {"ATETXFREQOFFSET", Set_ATE_TX_FREQOFFSET_Proc},
75832 + {"ATETXBW", Set_ATE_TX_BW_Proc},
75833 + {"ATETXLEN", Set_ATE_TX_LENGTH_Proc},
75834 + {"ATETXCNT", Set_ATE_TX_COUNT_Proc},
75835 + {"ATETXMCS", Set_ATE_TX_MCS_Proc},
75836 + {"ATETXMODE", Set_ATE_TX_MODE_Proc},
75837 + {"ATETXGI", Set_ATE_TX_GI_Proc},
75838 + {"ATERXFER", Set_ATE_RX_FER_Proc},
75839 + {"ATERRF", Set_ATE_Read_RF_Proc},
75840 + {"ATEWRF1", Set_ATE_Write_RF1_Proc},
75841 + {"ATEWRF2", Set_ATE_Write_RF2_Proc},
75842 + {"ATEWRF3", Set_ATE_Write_RF3_Proc},
75843 + {"ATEWRF4", Set_ATE_Write_RF4_Proc},
75844 + {"ATELDE2P", Set_ATE_Load_E2P_Proc},
75845 + {"ATERE2P", Set_ATE_Read_E2P_Proc},
75846 + {"ATESHOW", Set_ATE_Show_Proc},
75847 + {"ATEHELP", Set_ATE_Help_Proc},
75848 +
75849 +#ifdef RALINK_28xx_QA
75850 + {"TxStop", Set_TxStop_Proc},
75851 + {"RxStop", Set_RxStop_Proc},
75852 +#endif // RALINK_28xx_QA //
75853 +#endif // RALINK_ATE //
75854 +
75855 +#ifdef WPA_SUPPLICANT_SUPPORT
75856 + {"WpaSupport", Set_Wpa_Support},
75857 +#endif // WPA_SUPPLICANT_SUPPORT //
75858 +
75859 +
75860 +
75861 + {"FixedTxMode", Set_FixedTxMode_Proc},
75862 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
75863 + {"OpMode", Set_OpMode_Proc},
75864 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
75865 +#ifdef DOT11_N_SUPPORT
75866 + {"TGnWifiTest", Set_TGnWifiTest_Proc},
75867 + {"ForceGF", Set_ForceGF_Proc},
75868 +#endif // DOT11_N_SUPPORT //
75869 +#ifdef QOS_DLS_SUPPORT
75870 + {"DlsAddEntry", Set_DlsAddEntry_Proc},
75871 + {"DlsTearDownEntry", Set_DlsTearDownEntry_Proc},
75872 +#endif // QOS_DLS_SUPPORT //
75873 + {"LongRetry", Set_LongRetryLimit_Proc},
75874 + {"ShortRetry", Set_ShortRetryLimit_Proc},
75875 +#ifdef EXT_BUILD_CHANNEL_LIST
75876 + {"11dClientMode", Set_Ieee80211dClientMode_Proc},
75877 +#endif // EXT_BUILD_CHANNEL_LIST //
75878 +#ifdef CARRIER_DETECTION_SUPPORT
75879 + {"CarrierDetect", Set_CarrierDetect_Proc},
75880 +#endif // CARRIER_DETECTION_SUPPORT //
75881 +
75882 + {NULL,}
75883 +};
75884 +
75885 +
75886 +VOID RTMPAddKey(
75887 + IN PRTMP_ADAPTER pAd,
75888 + IN PNDIS_802_11_KEY pKey)
75889 +{
75890 + ULONG KeyIdx;
75891 + MAC_TABLE_ENTRY *pEntry;
75892 +
75893 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPAddKey ------>\n"));
75894 +
75895 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
75896 + {
75897 + if (pKey->KeyIndex & 0x80000000)
75898 + {
75899 + if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
75900 + {
75901 + NdisZeroMemory(pAd->StaCfg.PMK, 32);
75902 + NdisMoveMemory(pAd->StaCfg.PMK, pKey->KeyMaterial, pKey->KeyLength);
75903 + goto end;
75904 + }
75905 + // Update PTK
75906 + NdisZeroMemory(&pAd->SharedKey[BSS0][0], sizeof(CIPHER_KEY));
75907 + pAd->SharedKey[BSS0][0].KeyLen = LEN_TKIP_EK;
75908 + NdisMoveMemory(pAd->SharedKey[BSS0][0].Key, pKey->KeyMaterial, LEN_TKIP_EK);
75909 +#ifdef WPA_SUPPLICANT_SUPPORT
75910 + if (pAd->StaCfg.PairCipher == Ndis802_11Encryption2Enabled)
75911 + {
75912 + NdisMoveMemory(pAd->SharedKey[BSS0][0].RxMic, pKey->KeyMaterial + LEN_TKIP_EK, LEN_TKIP_TXMICK);
75913 + NdisMoveMemory(pAd->SharedKey[BSS0][0].TxMic, pKey->KeyMaterial + LEN_TKIP_EK + LEN_TKIP_TXMICK, LEN_TKIP_RXMICK);
75914 + }
75915 + else
75916 +#endif // WPA_SUPPLICANT_SUPPORT //
75917 + {
75918 + NdisMoveMemory(pAd->SharedKey[BSS0][0].TxMic, pKey->KeyMaterial + LEN_TKIP_EK, LEN_TKIP_TXMICK);
75919 + NdisMoveMemory(pAd->SharedKey[BSS0][0].RxMic, pKey->KeyMaterial + LEN_TKIP_EK + LEN_TKIP_TXMICK, LEN_TKIP_RXMICK);
75920 + }
75921 +
75922 + // Decide its ChiperAlg
75923 + if (pAd->StaCfg.PairCipher == Ndis802_11Encryption2Enabled)
75924 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_TKIP;
75925 + else if (pAd->StaCfg.PairCipher == Ndis802_11Encryption3Enabled)
75926 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_AES;
75927 + else
75928 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_NONE;
75929 +
75930 + // Update these related information to MAC_TABLE_ENTRY
75931 + pEntry = &pAd->MacTab.Content[BSSID_WCID];
75932 + NdisMoveMemory(pEntry->PairwiseKey.Key, pAd->SharedKey[BSS0][0].Key, LEN_TKIP_EK);
75933 + NdisMoveMemory(pEntry->PairwiseKey.RxMic, pAd->SharedKey[BSS0][0].RxMic, LEN_TKIP_RXMICK);
75934 + NdisMoveMemory(pEntry->PairwiseKey.TxMic, pAd->SharedKey[BSS0][0].TxMic, LEN_TKIP_TXMICK);
75935 + pEntry->PairwiseKey.CipherAlg = pAd->SharedKey[BSS0][0].CipherAlg;
75936 +
75937 + // Update pairwise key information to ASIC Shared Key Table
75938 + AsicAddSharedKeyEntry(pAd,
75939 + BSS0,
75940 + 0,
75941 + pAd->SharedKey[BSS0][0].CipherAlg,
75942 + pAd->SharedKey[BSS0][0].Key,
75943 + pAd->SharedKey[BSS0][0].TxMic,
75944 + pAd->SharedKey[BSS0][0].RxMic);
75945 +
75946 + // Update ASIC WCID attribute table and IVEIV table
75947 + RTMPAddWcidAttributeEntry(pAd,
75948 + BSS0,
75949 + 0,
75950 + pAd->SharedKey[BSS0][0].CipherAlg,
75951 + pEntry);
75952 +
75953 + if (pAd->StaCfg.AuthMode >= Ndis802_11AuthModeWPA2)
75954 + {
75955 + // set 802.1x port control
75956 + STA_PORT_SECURED(pAd);
75957 +
75958 + // Indicate Connected for GUI
75959 + pAd->IndicateMediaState = NdisMediaStateConnected;
75960 + }
75961 + }
75962 + else
75963 + {
75964 + // Update GTK
75965 + pAd->StaCfg.DefaultKeyId = (pKey->KeyIndex & 0xFF);
75966 + NdisZeroMemory(&pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId], sizeof(CIPHER_KEY));
75967 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].KeyLen = LEN_TKIP_EK;
75968 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key, pKey->KeyMaterial, LEN_TKIP_EK);
75969 +#ifdef WPA_SUPPLICANT_SUPPORT
75970 + if (pAd->StaCfg.GroupCipher == Ndis802_11Encryption2Enabled)
75971 + {
75972 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].RxMic, pKey->KeyMaterial + LEN_TKIP_EK, LEN_TKIP_TXMICK);
75973 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].TxMic, pKey->KeyMaterial + LEN_TKIP_EK + LEN_TKIP_TXMICK, LEN_TKIP_RXMICK);
75974 + }
75975 + else
75976 +#endif // WPA_SUPPLICANT_SUPPORT //
75977 + {
75978 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].TxMic, pKey->KeyMaterial + LEN_TKIP_EK, LEN_TKIP_TXMICK);
75979 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].RxMic, pKey->KeyMaterial + LEN_TKIP_EK + LEN_TKIP_TXMICK, LEN_TKIP_RXMICK);
75980 + }
75981 +
75982 + // Update Shared Key CipherAlg
75983 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_NONE;
75984 + if (pAd->StaCfg.GroupCipher == Ndis802_11Encryption2Enabled)
75985 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_TKIP;
75986 + else if (pAd->StaCfg.GroupCipher == Ndis802_11Encryption3Enabled)
75987 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_AES;
75988 +
75989 + // Update group key information to ASIC Shared Key Table
75990 + AsicAddSharedKeyEntry(pAd,
75991 + BSS0,
75992 + pAd->StaCfg.DefaultKeyId,
75993 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg,
75994 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key,
75995 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].TxMic,
75996 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].RxMic);
75997 +
75998 + // Update ASIC WCID attribute table and IVEIV table
75999 + RTMPAddWcidAttributeEntry(pAd,
76000 + BSS0,
76001 + pAd->StaCfg.DefaultKeyId,
76002 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg,
76003 + NULL);
76004 +
76005 + // set 802.1x port control
76006 + STA_PORT_SECURED(pAd);
76007 +
76008 + // Indicate Connected for GUI
76009 + pAd->IndicateMediaState = NdisMediaStateConnected;
76010 + }
76011 + }
76012 + else // dynamic WEP from wpa_supplicant
76013 + {
76014 + UCHAR CipherAlg;
76015 + PUCHAR Key;
76016 +
76017 + if(pKey->KeyLength == 32)
76018 + goto end;
76019 +
76020 + KeyIdx = pKey->KeyIndex & 0x0fffffff;
76021 +
76022 + if (KeyIdx < 4)
76023 + {
76024 + // it is a default shared key, for Pairwise key setting
76025 + if (pKey->KeyIndex & 0x80000000)
76026 + {
76027 + pEntry = MacTableLookup(pAd, pKey->BSSID);
76028 +
76029 + if (pEntry)
76030 + {
76031 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPAddKey: Set Pair-wise Key\n"));
76032 +
76033 + // set key material and key length
76034 + pEntry->PairwiseKey.KeyLen = (UCHAR)pKey->KeyLength;
76035 + NdisMoveMemory(pEntry->PairwiseKey.Key, &pKey->KeyMaterial, pKey->KeyLength);
76036 +
76037 + // set Cipher type
76038 + if (pKey->KeyLength == 5)
76039 + pEntry->PairwiseKey.CipherAlg = CIPHER_WEP64;
76040 + else
76041 + pEntry->PairwiseKey.CipherAlg = CIPHER_WEP128;
76042 +
76043 + // Add Pair-wise key to Asic
76044 + AsicAddPairwiseKeyEntry(
76045 + pAd,
76046 + pEntry->Addr,
76047 + (UCHAR)pEntry->Aid,
76048 + &pEntry->PairwiseKey);
76049 +
76050 + // update WCID attribute table and IVEIV table for this entry
76051 + RTMPAddWcidAttributeEntry(
76052 + pAd,
76053 + BSS0,
76054 + KeyIdx, // The value may be not zero
76055 + pEntry->PairwiseKey.CipherAlg,
76056 + pEntry);
76057 +
76058 + }
76059 + }
76060 + else
76061 + {
76062 + // Default key for tx (shared key)
76063 + pAd->StaCfg.DefaultKeyId = (UCHAR) KeyIdx;
76064 +
76065 + // set key material and key length
76066 + pAd->SharedKey[BSS0][KeyIdx].KeyLen = (UCHAR) pKey->KeyLength;
76067 + NdisMoveMemory(pAd->SharedKey[BSS0][KeyIdx].Key, &pKey->KeyMaterial, pKey->KeyLength);
76068 +
76069 + // Set Ciper type
76070 + if (pKey->KeyLength == 5)
76071 + pAd->SharedKey[BSS0][KeyIdx].CipherAlg = CIPHER_WEP64;
76072 + else
76073 + pAd->SharedKey[BSS0][KeyIdx].CipherAlg = CIPHER_WEP128;
76074 +
76075 + CipherAlg = pAd->SharedKey[BSS0][KeyIdx].CipherAlg;
76076 + Key = pAd->SharedKey[BSS0][KeyIdx].Key;
76077 +
76078 + // Set Group key material to Asic
76079 + AsicAddSharedKeyEntry(pAd, BSS0, KeyIdx, CipherAlg, Key, NULL, NULL);
76080 +
76081 + // Update WCID attribute table and IVEIV table for this group key table
76082 + RTMPAddWcidAttributeEntry(pAd, BSS0, KeyIdx, CipherAlg, NULL);
76083 +
76084 + }
76085 + }
76086 + }
76087 +end:
76088 + return;
76089 +}
76090 +
76091 +char * rtstrchr(const char * s, int c)
76092 +{
76093 + for(; *s != (char) c; ++s)
76094 + if (*s == '\0')
76095 + return NULL;
76096 + return (char *) s;
76097 +}
76098 +
76099 +/*
76100 +This is required for LinEX2004/kernel2.6.7 to provide iwlist scanning function
76101 +*/
76102 +
76103 +int
76104 +rt_ioctl_giwname(struct net_device *dev,
76105 + struct iw_request_info *info,
76106 + char *name, char *extra)
76107 +{
76108 +// PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76109 +
76110 +#ifdef RT2860
76111 + strncpy(name, "RT2860 Wireless", IFNAMSIZ);
76112 +#endif // RT2860 //
76113 + return 0;
76114 +}
76115 +
76116 +int rt_ioctl_siwfreq(struct net_device *dev,
76117 + struct iw_request_info *info,
76118 + struct iw_freq *freq, char *extra)
76119 +{
76120 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76121 + int chan = -1;
76122 +
76123 + //check if the interface is down
76124 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
76125 + {
76126 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
76127 + return -ENETDOWN;
76128 + }
76129 +
76130 +
76131 + if (freq->e > 1)
76132 + return -EINVAL;
76133 +
76134 + if((freq->e == 0) && (freq->m <= 1000))
76135 + chan = freq->m; // Setting by channel number
76136 + else
76137 + MAP_KHZ_TO_CHANNEL_ID( (freq->m /100) , chan); // Setting by frequency - search the table , like 2.412G, 2.422G,
76138 +
76139 + if (ChannelSanity(pAdapter, chan) == TRUE)
76140 + {
76141 + pAdapter->CommonCfg.Channel = chan;
76142 + DBGPRINT(RT_DEBUG_ERROR, ("==>rt_ioctl_siwfreq::SIOCSIWFREQ[cmd=0x%x] (Channel=%d)\n", SIOCSIWFREQ, pAdapter->CommonCfg.Channel));
76143 + }
76144 + else
76145 + return -EINVAL;
76146 +
76147 + return 0;
76148 +}
76149 +int rt_ioctl_giwfreq(struct net_device *dev,
76150 + struct iw_request_info *info,
76151 + struct iw_freq *freq, char *extra)
76152 +{
76153 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
76154 + PRTMP_ADAPTER pAdapter = NULL;
76155 + UCHAR ch;
76156 + ULONG m;
76157 +
76158 + if (dev->priv_flags == INT_MAIN)
76159 + {
76160 + pAdapter = dev->priv;
76161 + }
76162 + else
76163 + {
76164 + pVirtualAd = dev->priv;
76165 + if (pVirtualAd && pVirtualAd->RtmpDev)
76166 + pAdapter = pVirtualAd->RtmpDev->priv;
76167 + }
76168 +
76169 + if (pAdapter == NULL)
76170 + {
76171 + /* if 1st open fail, pAd will be free;
76172 + So the net_dev->priv will be NULL in 2rd open */
76173 + return -ENETDOWN;
76174 + }
76175 +
76176 + ch = pAdapter->CommonCfg.Channel;
76177 +
76178 + DBGPRINT(RT_DEBUG_TRACE,("==>rt_ioctl_giwfreq %d\n", ch));
76179 +
76180 + MAP_CHANNEL_ID_TO_KHZ(ch, m);
76181 + freq->m = m * 100;
76182 + freq->e = 1;
76183 + return 0;
76184 +}
76185 +
76186 +int rt_ioctl_siwmode(struct net_device *dev,
76187 + struct iw_request_info *info,
76188 + __u32 *mode, char *extra)
76189 +{
76190 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76191 +
76192 + //check if the interface is down
76193 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
76194 + {
76195 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
76196 + return -ENETDOWN;
76197 + }
76198 +
76199 + switch (*mode)
76200 + {
76201 + case IW_MODE_ADHOC:
76202 + Set_NetworkType_Proc(pAdapter, "Adhoc");
76203 + break;
76204 + case IW_MODE_INFRA:
76205 + Set_NetworkType_Proc(pAdapter, "Infra");
76206 + break;
76207 +#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,4,20))
76208 + case IW_MODE_MONITOR:
76209 + Set_NetworkType_Proc(pAdapter, "Monitor");
76210 + break;
76211 +#endif
76212 + default:
76213 + DBGPRINT(RT_DEBUG_TRACE, ("===>rt_ioctl_siwmode::SIOCSIWMODE (unknown %d)\n", *mode));
76214 + return -EINVAL;
76215 + }
76216 +
76217 + // Reset Ralink supplicant to not use, it will be set to start when UI set PMK key
76218 + pAdapter->StaCfg.WpaState = SS_NOTUSE;
76219 +
76220 + return 0;
76221 +}
76222 +
76223 +int rt_ioctl_giwmode(struct net_device *dev,
76224 + struct iw_request_info *info,
76225 + __u32 *mode, char *extra)
76226 +{
76227 + PRTMP_ADAPTER pAdapter = NULL;
76228 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
76229 +
76230 + if (dev->priv_flags == INT_MAIN)
76231 + {
76232 + pAdapter = dev->priv;
76233 + }
76234 + else
76235 + {
76236 + pVirtualAd = dev->priv;
76237 + if (pVirtualAd && pVirtualAd->RtmpDev)
76238 + pAdapter = pVirtualAd->RtmpDev->priv;
76239 + }
76240 +
76241 + if (pAdapter == NULL)
76242 + {
76243 + /* if 1st open fail, pAd will be free;
76244 + So the net_dev->priv will be NULL in 2rd open */
76245 + return -ENETDOWN;
76246 + }
76247 +
76248 + if (ADHOC_ON(pAdapter))
76249 + *mode = IW_MODE_ADHOC;
76250 + else if (INFRA_ON(pAdapter))
76251 + *mode = IW_MODE_INFRA;
76252 +#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,4,20))
76253 + else if (MONITOR_ON(pAdapter))
76254 + {
76255 + *mode = IW_MODE_MONITOR;
76256 + }
76257 +#endif
76258 + else
76259 + *mode = IW_MODE_AUTO;
76260 +
76261 + DBGPRINT(RT_DEBUG_TRACE, ("==>rt_ioctl_giwmode(mode=%d)\n", *mode));
76262 + return 0;
76263 +}
76264 +
76265 +int rt_ioctl_siwsens(struct net_device *dev,
76266 + struct iw_request_info *info,
76267 + char *name, char *extra)
76268 +{
76269 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76270 +
76271 + //check if the interface is down
76272 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
76273 + {
76274 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
76275 + return -ENETDOWN;
76276 + }
76277 +
76278 + return 0;
76279 +}
76280 +
76281 +int rt_ioctl_giwsens(struct net_device *dev,
76282 + struct iw_request_info *info,
76283 + char *name, char *extra)
76284 +{
76285 + return 0;
76286 +}
76287 +
76288 +int rt_ioctl_giwrange(struct net_device *dev,
76289 + struct iw_request_info *info,
76290 + struct iw_point *data, char *extra)
76291 +{
76292 + PRTMP_ADAPTER pAdapter = NULL;
76293 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
76294 + struct iw_range *range = (struct iw_range *) extra;
76295 + u16 val;
76296 + int i;
76297 +
76298 + if (dev->priv_flags == INT_MAIN)
76299 + {
76300 + pAdapter = dev->priv;
76301 + }
76302 + else
76303 + {
76304 + pVirtualAd = dev->priv;
76305 + if (pVirtualAd && pVirtualAd->RtmpDev)
76306 + pAdapter = pVirtualAd->RtmpDev->priv;
76307 + }
76308 +
76309 + if (pAdapter == NULL)
76310 + {
76311 + /* if 1st open fail, pAd will be free;
76312 + So the net_dev->priv will be NULL in 2rd open */
76313 + return -ENETDOWN;
76314 + }
76315 +
76316 + DBGPRINT(RT_DEBUG_TRACE ,("===>rt_ioctl_giwrange\n"));
76317 + data->length = sizeof(struct iw_range);
76318 + memset(range, 0, sizeof(struct iw_range));
76319 +
76320 + range->txpower_capa = IW_TXPOW_DBM;
76321 +
76322 + if (INFRA_ON(pAdapter)||ADHOC_ON(pAdapter))
76323 + {
76324 + range->min_pmp = 1 * 1024;
76325 + range->max_pmp = 65535 * 1024;
76326 + range->min_pmt = 1 * 1024;
76327 + range->max_pmt = 1000 * 1024;
76328 + range->pmp_flags = IW_POWER_PERIOD;
76329 + range->pmt_flags = IW_POWER_TIMEOUT;
76330 + range->pm_capa = IW_POWER_PERIOD | IW_POWER_TIMEOUT |
76331 + IW_POWER_UNICAST_R | IW_POWER_ALL_R;
76332 + }
76333 +
76334 + range->we_version_compiled = WIRELESS_EXT;
76335 + range->we_version_source = 14;
76336 +
76337 + range->retry_capa = IW_RETRY_LIMIT;
76338 + range->retry_flags = IW_RETRY_LIMIT;
76339 + range->min_retry = 0;
76340 + range->max_retry = 255;
76341 +
76342 + range->num_channels = pAdapter->ChannelListNum;
76343 +
76344 + val = 0;
76345 + for (i = 1; i <= range->num_channels; i++)
76346 + {
76347 + u32 m;
76348 + range->freq[val].i = pAdapter->ChannelList[i-1].Channel;
76349 + MAP_CHANNEL_ID_TO_KHZ(pAdapter->ChannelList[i-1].Channel, m);
76350 + range->freq[val].m = m * 100; /* HZ */
76351 +
76352 + range->freq[val].e = 1;
76353 + val++;
76354 + if (val == IW_MAX_FREQUENCIES)
76355 + break;
76356 + }
76357 + range->num_frequency = val;
76358 +
76359 + range->max_qual.qual = 100; /* what is correct max? This was not
76360 + * documented exactly. At least
76361 + * 69 has been observed. */
76362 + range->max_qual.level = 0; /* dB */
76363 + range->max_qual.noise = 0; /* dB */
76364 +
76365 + /* What would be suitable values for "average/typical" qual? */
76366 + range->avg_qual.qual = 20;
76367 + range->avg_qual.level = -60;
76368 + range->avg_qual.noise = -95;
76369 + range->sensitivity = 3;
76370 +
76371 + range->max_encoding_tokens = NR_WEP_KEYS;
76372 + range->num_encoding_sizes = 2;
76373 + range->encoding_size[0] = 5;
76374 + range->encoding_size[1] = 13;
76375 +
76376 + range->min_rts = 0;
76377 + range->max_rts = 2347;
76378 + range->min_frag = 256;
76379 + range->max_frag = 2346;
76380 +
76381 +#if WIRELESS_EXT > 17
76382 + /* IW_ENC_CAPA_* bit field */
76383 + range->enc_capa = IW_ENC_CAPA_WPA | IW_ENC_CAPA_WPA2 |
76384 + IW_ENC_CAPA_CIPHER_TKIP | IW_ENC_CAPA_CIPHER_CCMP;
76385 +#endif
76386 +
76387 + return 0;
76388 +}
76389 +
76390 +int rt_ioctl_siwap(struct net_device *dev,
76391 + struct iw_request_info *info,
76392 + struct sockaddr *ap_addr, char *extra)
76393 +{
76394 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76395 + NDIS_802_11_MAC_ADDRESS Bssid;
76396 +
76397 + //check if the interface is down
76398 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
76399 + {
76400 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
76401 + return -ENETDOWN;
76402 + }
76403 +
76404 + if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE)
76405 + {
76406 + RT28XX_MLME_RESET_STATE_MACHINE(pAdapter);
76407 + DBGPRINT(RT_DEBUG_TRACE, ("!!! MLME busy, reset MLME state machine !!!\n"));
76408 + }
76409 +
76410 + // tell CNTL state machine to call NdisMSetInformationComplete() after completing
76411 + // this request, because this request is initiated by NDIS.
76412 + pAdapter->MlmeAux.CurrReqIsFromNdis = FALSE;
76413 + // Prevent to connect AP again in STAMlmePeriodicExec
76414 + pAdapter->MlmeAux.AutoReconnectSsidLen= 32;
76415 +
76416 + memset(Bssid, 0, MAC_ADDR_LEN);
76417 + memcpy(Bssid, ap_addr->sa_data, MAC_ADDR_LEN);
76418 + MlmeEnqueue(pAdapter,
76419 + MLME_CNTL_STATE_MACHINE,
76420 + OID_802_11_BSSID,
76421 + sizeof(NDIS_802_11_MAC_ADDRESS),
76422 + (VOID *)&Bssid);
76423 +
76424 + DBGPRINT(RT_DEBUG_TRACE, ("IOCTL::SIOCSIWAP %02x:%02x:%02x:%02x:%02x:%02x\n",
76425 + Bssid[0], Bssid[1], Bssid[2], Bssid[3], Bssid[4], Bssid[5]));
76426 +
76427 + return 0;
76428 +}
76429 +
76430 +int rt_ioctl_giwap(struct net_device *dev,
76431 + struct iw_request_info *info,
76432 + struct sockaddr *ap_addr, char *extra)
76433 +{
76434 + PRTMP_ADAPTER pAdapter = NULL;
76435 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
76436 +
76437 + if (dev->priv_flags == INT_MAIN)
76438 + {
76439 + pAdapter = dev->priv;
76440 + }
76441 + else
76442 + {
76443 + pVirtualAd = dev->priv;
76444 + if (pVirtualAd && pVirtualAd->RtmpDev)
76445 + pAdapter = pVirtualAd->RtmpDev->priv;
76446 + }
76447 +
76448 + if (pAdapter == NULL)
76449 + {
76450 + /* if 1st open fail, pAd will be free;
76451 + So the net_dev->priv will be NULL in 2rd open */
76452 + return -ENETDOWN;
76453 + }
76454 +
76455 + if (INFRA_ON(pAdapter) || ADHOC_ON(pAdapter))
76456 + {
76457 + ap_addr->sa_family = ARPHRD_ETHER;
76458 + memcpy(ap_addr->sa_data, &pAdapter->CommonCfg.Bssid, ETH_ALEN);
76459 + }
76460 +#ifdef WPA_SUPPLICANT_SUPPORT
76461 + // Add for RT2870
76462 + else if (pAdapter->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE)
76463 + {
76464 + ap_addr->sa_family = ARPHRD_ETHER;
76465 + memcpy(ap_addr->sa_data, &pAdapter->MlmeAux.Bssid, ETH_ALEN);
76466 + }
76467 +#endif // WPA_SUPPLICANT_SUPPORT //
76468 + else
76469 + {
76470 + DBGPRINT(RT_DEBUG_TRACE, ("IOCTL::SIOCGIWAP(=EMPTY)\n"));
76471 + return -ENOTCONN;
76472 + }
76473 +
76474 + return 0;
76475 +}
76476 +
76477 +/*
76478 + * Units are in db above the noise floor. That means the
76479 + * rssi values reported in the tx/rx descriptors in the
76480 + * driver are the SNR expressed in db.
76481 + *
76482 + * If you assume that the noise floor is -95, which is an
76483 + * excellent assumption 99.5 % of the time, then you can
76484 + * derive the absolute signal level (i.e. -95 + rssi).
76485 + * There are some other slight factors to take into account
76486 + * depending on whether the rssi measurement is from 11b,
76487 + * 11g, or 11a. These differences are at most 2db and
76488 + * can be documented.
76489 + *
76490 + * NB: various calculations are based on the orinoco/wavelan
76491 + * drivers for compatibility
76492 + */
76493 +static void set_quality(PRTMP_ADAPTER pAdapter,
76494 + struct iw_quality *iq,
76495 + signed char rssi)
76496 +{
76497 + __u8 ChannelQuality;
76498 +
76499 + // Normalize Rssi
76500 + if (rssi >= -50)
76501 + ChannelQuality = 100;
76502 + else if (rssi >= -80) // between -50 ~ -80dbm
76503 + ChannelQuality = (__u8)(24 + ((rssi + 80) * 26)/10);
76504 + else if (rssi >= -90) // between -80 ~ -90dbm
76505 + ChannelQuality = (__u8)((rssi + 90) * 26)/10;
76506 + else
76507 + ChannelQuality = 0;
76508 +
76509 + iq->qual = (__u8)ChannelQuality;
76510 +
76511 + iq->level = (__u8)(rssi);
76512 + iq->noise = (pAdapter->BbpWriteLatch[66] > pAdapter->BbpTuning.FalseCcaUpperThreshold) ? ((__u8)pAdapter->BbpTuning.FalseCcaUpperThreshold) : ((__u8) pAdapter->BbpWriteLatch[66]); // noise level (dBm)
76513 + iq->noise += 256 - 143;
76514 + iq->updated = pAdapter->iw_stats.qual.updated;
76515 +}
76516 +
76517 +int rt_ioctl_iwaplist(struct net_device *dev,
76518 + struct iw_request_info *info,
76519 + struct iw_point *data, char *extra)
76520 +{
76521 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76522 +
76523 + struct sockaddr addr[IW_MAX_AP];
76524 + struct iw_quality qual[IW_MAX_AP];
76525 + int i;
76526 +
76527 + //check if the interface is down
76528 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
76529 + {
76530 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
76531 + data->length = 0;
76532 + return 0;
76533 + //return -ENETDOWN;
76534 + }
76535 +
76536 + for (i = 0; i <IW_MAX_AP ; i++)
76537 + {
76538 + if (i >= pAdapter->ScanTab.BssNr)
76539 + break;
76540 + addr[i].sa_family = ARPHRD_ETHER;
76541 + memcpy(addr[i].sa_data, &pAdapter->ScanTab.BssEntry[i].Bssid, MAC_ADDR_LEN);
76542 + set_quality(pAdapter, &qual[i], pAdapter->ScanTab.BssEntry[i].Rssi);
76543 + }
76544 + data->length = i;
76545 + memcpy(extra, &addr, i*sizeof(addr[0]));
76546 + data->flags = 1; /* signal quality present (sort of) */
76547 + memcpy(extra + i*sizeof(addr[0]), &qual, i*sizeof(qual[i]));
76548 +
76549 + return 0;
76550 +}
76551 +
76552 +#ifdef SIOCGIWSCAN
76553 +int rt_ioctl_siwscan(struct net_device *dev,
76554 + struct iw_request_info *info,
76555 + struct iw_point *data, char *extra)
76556 +{
76557 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76558 +
76559 + ULONG Now;
76560 + int Status = NDIS_STATUS_SUCCESS;
76561 +
76562 + //check if the interface is down
76563 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
76564 + {
76565 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
76566 + return -ENETDOWN;
76567 + }
76568 +
76569 + if (MONITOR_ON(pAdapter))
76570 + {
76571 + DBGPRINT(RT_DEBUG_TRACE, ("!!! Driver is in Monitor Mode now !!!\n"));
76572 + return -EINVAL;
76573 + }
76574 +
76575 +
76576 +#ifdef WPA_SUPPLICANT_SUPPORT
76577 + if (pAdapter->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE)
76578 + {
76579 + pAdapter->StaCfg.WpaSupplicantScanCount++;
76580 + }
76581 +#endif // WPA_SUPPLICANT_SUPPORT //
76582 +
76583 + pAdapter->StaCfg.bScanReqIsFromWebUI = TRUE;
76584 + if (RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
76585 + return 0;
76586 + do{
76587 + Now = jiffies;
76588 +
76589 +#ifdef WPA_SUPPLICANT_SUPPORT
76590 + if ((pAdapter->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE) &&
76591 + (pAdapter->StaCfg.WpaSupplicantScanCount > 3))
76592 + {
76593 + DBGPRINT(RT_DEBUG_TRACE, ("!!! WpaSupplicantScanCount > 3\n"));
76594 + Status = NDIS_STATUS_SUCCESS;
76595 + break;
76596 + }
76597 +#endif // WPA_SUPPLICANT_SUPPORT //
76598 +
76599 + if ((OPSTATUS_TEST_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED)) &&
76600 + ((pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPA) ||
76601 + (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK)) &&
76602 + (pAdapter->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED))
76603 + {
76604 + DBGPRINT(RT_DEBUG_TRACE, ("!!! Link UP, Port Not Secured! ignore this set::OID_802_11_BSSID_LIST_SCAN\n"));
76605 + Status = NDIS_STATUS_SUCCESS;
76606 + break;
76607 + }
76608 +
76609 + if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE)
76610 + {
76611 + RT28XX_MLME_RESET_STATE_MACHINE(pAdapter);
76612 + DBGPRINT(RT_DEBUG_TRACE, ("!!! MLME busy, reset MLME state machine !!!\n"));
76613 + }
76614 +
76615 + // tell CNTL state machine to call NdisMSetInformationComplete() after completing
76616 + // this request, because this request is initiated by NDIS.
76617 + pAdapter->MlmeAux.CurrReqIsFromNdis = FALSE;
76618 + // Reset allowed scan retries
76619 + pAdapter->StaCfg.ScanCnt = 0;
76620 + pAdapter->StaCfg.LastScanTime = Now;
76621 +
76622 + MlmeEnqueue(pAdapter,
76623 + MLME_CNTL_STATE_MACHINE,
76624 + OID_802_11_BSSID_LIST_SCAN,
76625 + 0,
76626 + NULL);
76627 +
76628 + Status = NDIS_STATUS_SUCCESS;
76629 + RT28XX_MLME_HANDLER(pAdapter);
76630 + }while(0);
76631 + return 0;
76632 +}
76633 +
76634 +int rt_ioctl_giwscan(struct net_device *dev,
76635 + struct iw_request_info *info,
76636 + struct iw_point *data, char *extra)
76637 +{
76638 +
76639 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76640 + int i=0;
76641 + char *current_ev = extra, *previous_ev = extra;
76642 + char *end_buf;
76643 + char *current_val, custom[MAX_CUSTOM_LEN] = {0};
76644 +#ifndef IWEVGENIE
76645 + char idx;
76646 +#endif // IWEVGENIE //
76647 + struct iw_event iwe;
76648 +
76649 + if (RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
76650 + {
76651 + /*
76652 + * Still scanning, indicate the caller should try again.
76653 + */
76654 + return -EAGAIN;
76655 + }
76656 +
76657 +
76658 +#ifdef WPA_SUPPLICANT_SUPPORT
76659 + if (pAdapter->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE)
76660 + {
76661 + pAdapter->StaCfg.WpaSupplicantScanCount = 0;
76662 + }
76663 +#endif // WPA_SUPPLICANT_SUPPORT //
76664 +
76665 + if (pAdapter->ScanTab.BssNr == 0)
76666 + {
76667 + data->length = 0;
76668 + return 0;
76669 + }
76670 +
76671 +#if WIRELESS_EXT >= 17
76672 + if (data->length > 0)
76673 + end_buf = extra + data->length;
76674 + else
76675 + end_buf = extra + IW_SCAN_MAX_DATA;
76676 +#else
76677 + end_buf = extra + IW_SCAN_MAX_DATA;
76678 +#endif
76679 +
76680 + for (i = 0; i < pAdapter->ScanTab.BssNr; i++)
76681 + {
76682 + if (current_ev >= end_buf)
76683 + {
76684 +#if WIRELESS_EXT >= 17
76685 + return -E2BIG;
76686 +#else
76687 + break;
76688 +#endif
76689 + }
76690 +
76691 + //MAC address
76692 + //================================
76693 + memset(&iwe, 0, sizeof(iwe));
76694 + iwe.cmd = SIOCGIWAP;
76695 + iwe.u.ap_addr.sa_family = ARPHRD_ETHER;
76696 + memcpy(iwe.u.ap_addr.sa_data, &pAdapter->ScanTab.BssEntry[i].Bssid, ETH_ALEN);
76697 +
76698 + previous_ev = current_ev;
76699 + current_ev = IWE_STREAM_ADD_EVENT(info, current_ev,end_buf, &iwe, IW_EV_ADDR_LEN);
76700 + if (current_ev == previous_ev)
76701 +#if WIRELESS_EXT >= 17
76702 + return -E2BIG;
76703 +#else
76704 + break;
76705 +#endif
76706 +
76707 + //ESSID
76708 + //================================
76709 + memset(&iwe, 0, sizeof(iwe));
76710 + iwe.cmd = SIOCGIWESSID;
76711 + iwe.u.data.length = pAdapter->ScanTab.BssEntry[i].SsidLen;
76712 + iwe.u.data.flags = 1;
76713 +
76714 + previous_ev = current_ev;
76715 + current_ev = IWE_STREAM_ADD_POINT(info, current_ev,end_buf, &iwe, pAdapter->ScanTab.BssEntry[i].Ssid);
76716 + if (current_ev == previous_ev)
76717 +#if WIRELESS_EXT >= 17
76718 + return -E2BIG;
76719 +#else
76720 + break;
76721 +#endif
76722 +
76723 + //Network Type
76724 + //================================
76725 + memset(&iwe, 0, sizeof(iwe));
76726 + iwe.cmd = SIOCGIWMODE;
76727 + if (pAdapter->ScanTab.BssEntry[i].BssType == Ndis802_11IBSS)
76728 + {
76729 + iwe.u.mode = IW_MODE_ADHOC;
76730 + }
76731 + else if (pAdapter->ScanTab.BssEntry[i].BssType == Ndis802_11Infrastructure)
76732 + {
76733 + iwe.u.mode = IW_MODE_INFRA;
76734 + }
76735 + else
76736 + {
76737 + iwe.u.mode = IW_MODE_AUTO;
76738 + }
76739 + iwe.len = IW_EV_UINT_LEN;
76740 +
76741 + previous_ev = current_ev;
76742 + current_ev = IWE_STREAM_ADD_EVENT(info, current_ev, end_buf, &iwe, IW_EV_UINT_LEN);
76743 + if (current_ev == previous_ev)
76744 +#if WIRELESS_EXT >= 17
76745 + return -E2BIG;
76746 +#else
76747 + break;
76748 +#endif
76749 +
76750 + //Channel and Frequency
76751 + //================================
76752 + memset(&iwe, 0, sizeof(iwe));
76753 + iwe.cmd = SIOCGIWFREQ;
76754 + if (INFRA_ON(pAdapter) || ADHOC_ON(pAdapter))
76755 + iwe.u.freq.m = pAdapter->ScanTab.BssEntry[i].Channel;
76756 + else
76757 + iwe.u.freq.m = pAdapter->ScanTab.BssEntry[i].Channel;
76758 + iwe.u.freq.e = 0;
76759 + iwe.u.freq.i = 0;
76760 +
76761 + previous_ev = current_ev;
76762 + current_ev = IWE_STREAM_ADD_EVENT(info, current_ev,end_buf, &iwe, IW_EV_FREQ_LEN);
76763 + if (current_ev == previous_ev)
76764 +#if WIRELESS_EXT >= 17
76765 + return -E2BIG;
76766 +#else
76767 + break;
76768 +#endif
76769 +
76770 + //Add quality statistics
76771 + //================================
76772 + memset(&iwe, 0, sizeof(iwe));
76773 + iwe.cmd = IWEVQUAL;
76774 + iwe.u.qual.level = 0;
76775 + iwe.u.qual.noise = 0;
76776 + set_quality(pAdapter, &iwe.u.qual, pAdapter->ScanTab.BssEntry[i].Rssi);
76777 + current_ev = IWE_STREAM_ADD_EVENT(info, current_ev, end_buf, &iwe, IW_EV_QUAL_LEN);
76778 + if (current_ev == previous_ev)
76779 +#if WIRELESS_EXT >= 17
76780 + return -E2BIG;
76781 +#else
76782 + break;
76783 +#endif
76784 +
76785 + //Encyption key
76786 + //================================
76787 + memset(&iwe, 0, sizeof(iwe));
76788 + iwe.cmd = SIOCGIWENCODE;
76789 + if (CAP_IS_PRIVACY_ON (pAdapter->ScanTab.BssEntry[i].CapabilityInfo ))
76790 + iwe.u.data.flags =IW_ENCODE_ENABLED | IW_ENCODE_NOKEY;
76791 + else
76792 + iwe.u.data.flags = IW_ENCODE_DISABLED;
76793 +
76794 + previous_ev = current_ev;
76795 + current_ev = IWE_STREAM_ADD_POINT(info, current_ev, end_buf,&iwe, (char *)pAdapter->SharedKey[BSS0][(iwe.u.data.flags & IW_ENCODE_INDEX)-1].Key);
76796 + if (current_ev == previous_ev)
76797 +#if WIRELESS_EXT >= 17
76798 + return -E2BIG;
76799 +#else
76800 + break;
76801 +#endif
76802 +
76803 + //Bit Rate
76804 + //================================
76805 + if (pAdapter->ScanTab.BssEntry[i].SupRateLen)
76806 + {
76807 + UCHAR tmpRate = pAdapter->ScanTab.BssEntry[i].SupRate[pAdapter->ScanTab.BssEntry[i].SupRateLen-1];
76808 + memset(&iwe, 0, sizeof(iwe));
76809 + iwe.cmd = SIOCGIWRATE;
76810 + current_val = current_ev + IW_EV_LCP_LEN;
76811 + if (tmpRate == 0x82)
76812 + iwe.u.bitrate.value = 1 * 1000000;
76813 + else if (tmpRate == 0x84)
76814 + iwe.u.bitrate.value = 2 * 1000000;
76815 + else if (tmpRate == 0x8B)
76816 + iwe.u.bitrate.value = 5.5 * 1000000;
76817 + else if (tmpRate == 0x96)
76818 + iwe.u.bitrate.value = 11 * 1000000;
76819 + else
76820 + iwe.u.bitrate.value = (tmpRate/2) * 1000000;
76821 +
76822 + iwe.u.bitrate.disabled = 0;
76823 + current_val = IWE_STREAM_ADD_VALUE(info, current_ev,
76824 + current_val, end_buf, &iwe,
76825 + IW_EV_PARAM_LEN);
76826 +
76827 + if((current_val-current_ev)>IW_EV_LCP_LEN)
76828 + current_ev = current_val;
76829 + else
76830 +#if WIRELESS_EXT >= 17
76831 + return -E2BIG;
76832 +#else
76833 + break;
76834 +#endif
76835 + }
76836 +
76837 +#ifdef IWEVGENIE
76838 + //WPA IE
76839 + if (pAdapter->ScanTab.BssEntry[i].WpaIE.IELen > 0)
76840 + {
76841 + memset(&iwe, 0, sizeof(iwe));
76842 + memset(&custom[0], 0, MAX_CUSTOM_LEN);
76843 + memcpy(custom, &(pAdapter->ScanTab.BssEntry[i].WpaIE.IE[0]),
76844 + pAdapter->ScanTab.BssEntry[i].WpaIE.IELen);
76845 + iwe.cmd = IWEVGENIE;
76846 + iwe.u.data.length = pAdapter->ScanTab.BssEntry[i].WpaIE.IELen;
76847 + current_ev = IWE_STREAM_ADD_POINT(info, current_ev, end_buf, &iwe, custom);
76848 + if (current_ev == previous_ev)
76849 +#if WIRELESS_EXT >= 17
76850 + return -E2BIG;
76851 +#else
76852 + break;
76853 +#endif
76854 + }
76855 +
76856 + //WPA2 IE
76857 + if (pAdapter->ScanTab.BssEntry[i].RsnIE.IELen > 0)
76858 + {
76859 + memset(&iwe, 0, sizeof(iwe));
76860 + memset(&custom[0], 0, MAX_CUSTOM_LEN);
76861 + memcpy(custom, &(pAdapter->ScanTab.BssEntry[i].RsnIE.IE[0]),
76862 + pAdapter->ScanTab.BssEntry[i].RsnIE.IELen);
76863 + iwe.cmd = IWEVGENIE;
76864 + iwe.u.data.length = pAdapter->ScanTab.BssEntry[i].RsnIE.IELen;
76865 + current_ev = IWE_STREAM_ADD_POINT(info, current_ev, end_buf, &iwe, custom);
76866 + if (current_ev == previous_ev)
76867 +#if WIRELESS_EXT >= 17
76868 + return -E2BIG;
76869 +#else
76870 + break;
76871 +#endif
76872 + }
76873 +#else
76874 + //WPA IE
76875 + //================================
76876 + if (pAdapter->ScanTab.BssEntry[i].WpaIE.IELen > 0)
76877 + {
76878 + NdisZeroMemory(&iwe, sizeof(iwe));
76879 + memset(&custom[0], 0, MAX_CUSTOM_LEN);
76880 + iwe.cmd = IWEVCUSTOM;
76881 + iwe.u.data.length = (pAdapter->ScanTab.BssEntry[i].WpaIE.IELen * 2) + 7;
76882 + NdisMoveMemory(custom, "wpa_ie=", 7);
76883 + for (idx = 0; idx < pAdapter->ScanTab.BssEntry[i].WpaIE.IELen; idx++)
76884 + sprintf(custom, "%s%02x", custom, pAdapter->ScanTab.BssEntry[i].WpaIE.IE[idx]);
76885 + previous_ev = current_ev;
76886 + current_ev = IWE_STREAM_ADD_POINT(info, current_ev, end_buf, &iwe, custom);
76887 + if (current_ev == previous_ev)
76888 +#if WIRELESS_EXT >= 17
76889 + return -E2BIG;
76890 +#else
76891 + break;
76892 +#endif
76893 + }
76894 +
76895 + //WPA2 IE
76896 + if (pAdapter->ScanTab.BssEntry[i].RsnIE.IELen > 0)
76897 + {
76898 + NdisZeroMemory(&iwe, sizeof(iwe));
76899 + memset(&custom[0], 0, MAX_CUSTOM_LEN);
76900 + iwe.cmd = IWEVCUSTOM;
76901 + iwe.u.data.length = (pAdapter->ScanTab.BssEntry[i].RsnIE.IELen * 2) + 7;
76902 + NdisMoveMemory(custom, "rsn_ie=", 7);
76903 + for (idx = 0; idx < pAdapter->ScanTab.BssEntry[i].RsnIE.IELen; idx++)
76904 + sprintf(custom, "%s%02x", custom, pAdapter->ScanTab.BssEntry[i].RsnIE.IE[idx]);
76905 + previous_ev = current_ev;
76906 + current_ev = IWE_STREAM_ADD_POINT(info, current_ev, end_buf, &iwe, custom);
76907 + if (current_ev == previous_ev)
76908 +#if WIRELESS_EXT >= 17
76909 + return -E2BIG;
76910 +#else
76911 + break;
76912 +#endif
76913 + }
76914 +#endif // IWEVGENIE //
76915 + }
76916 +
76917 + data->length = current_ev - extra;
76918 + pAdapter->StaCfg.bScanReqIsFromWebUI = FALSE;
76919 + DBGPRINT(RT_DEBUG_ERROR ,("===>rt_ioctl_giwscan. %d(%d) BSS returned, data->length = %d\n",i , pAdapter->ScanTab.BssNr, data->length));
76920 + return 0;
76921 +}
76922 +#endif
76923 +
76924 +int rt_ioctl_siwessid(struct net_device *dev,
76925 + struct iw_request_info *info,
76926 + struct iw_point *data, char *essid)
76927 +{
76928 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
76929 +
76930 + //check if the interface is down
76931 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
76932 + {
76933 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
76934 + return -ENETDOWN;
76935 + }
76936 +
76937 + if (data->flags)
76938 + {
76939 + PCHAR pSsidString = NULL;
76940 +
76941 + // Includes null character.
76942 + if (data->length > (IW_ESSID_MAX_SIZE + 1))
76943 + return -E2BIG;
76944 +
76945 + pSsidString = (CHAR *) kmalloc(MAX_LEN_OF_SSID+1, MEM_ALLOC_FLAG);
76946 + if (pSsidString)
76947 + {
76948 + NdisZeroMemory(pSsidString, MAX_LEN_OF_SSID+1);
76949 + NdisMoveMemory(pSsidString, essid, data->length);
76950 + if (Set_SSID_Proc(pAdapter, pSsidString) == FALSE)
76951 + return -EINVAL;
76952 + }
76953 + else
76954 + return -ENOMEM;
76955 + }
76956 + else
76957 + {
76958 + // ANY ssid
76959 + if (Set_SSID_Proc(pAdapter, "") == FALSE)
76960 + return -EINVAL;
76961 + }
76962 + return 0;
76963 +}
76964 +
76965 +int rt_ioctl_giwessid(struct net_device *dev,
76966 + struct iw_request_info *info,
76967 + struct iw_point *data, char *essid)
76968 +{
76969 + PRTMP_ADAPTER pAdapter = NULL;
76970 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
76971 +
76972 + if (dev->priv_flags == INT_MAIN)
76973 + {
76974 + pAdapter = dev->priv;
76975 + }
76976 + else
76977 + {
76978 + pVirtualAd = dev->priv;
76979 + if (pVirtualAd && pVirtualAd->RtmpDev)
76980 + pAdapter = pVirtualAd->RtmpDev->priv;
76981 + }
76982 +
76983 + if (pAdapter == NULL)
76984 + {
76985 + /* if 1st open fail, pAd will be free;
76986 + So the net_dev->priv will be NULL in 2rd open */
76987 + return -ENETDOWN;
76988 + }
76989 +
76990 + data->flags = 1;
76991 + if (MONITOR_ON(pAdapter))
76992 + {
76993 + data->length = 0;
76994 + return 0;
76995 + }
76996 +
76997 + if (OPSTATUS_TEST_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED))
76998 + {
76999 + DBGPRINT(RT_DEBUG_TRACE ,("MediaState is connected\n"));
77000 + data->length = pAdapter->CommonCfg.SsidLen;
77001 + memcpy(essid, pAdapter->CommonCfg.Ssid, pAdapter->CommonCfg.SsidLen);
77002 + }
77003 + else
77004 + {//the ANY ssid was specified
77005 + data->length = 0;
77006 + DBGPRINT(RT_DEBUG_TRACE ,("MediaState is not connected, ess\n"));
77007 + }
77008 +
77009 + return 0;
77010 +
77011 +}
77012 +
77013 +int rt_ioctl_siwnickn(struct net_device *dev,
77014 + struct iw_request_info *info,
77015 + struct iw_point *data, char *nickname)
77016 +{
77017 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
77018 +
77019 + //check if the interface is down
77020 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77021 + {
77022 + DBGPRINT(RT_DEBUG_TRACE ,("INFO::Network is down!\n"));
77023 + return -ENETDOWN;
77024 + }
77025 +
77026 + if (data->length > IW_ESSID_MAX_SIZE)
77027 + return -EINVAL;
77028 +
77029 + memset(pAdapter->nickname, 0, IW_ESSID_MAX_SIZE + 1);
77030 + memcpy(pAdapter->nickname, nickname, data->length);
77031 +
77032 +
77033 + return 0;
77034 +}
77035 +
77036 +int rt_ioctl_giwnickn(struct net_device *dev,
77037 + struct iw_request_info *info,
77038 + struct iw_point *data, char *nickname)
77039 +{
77040 + PRTMP_ADAPTER pAdapter = NULL;
77041 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
77042 +
77043 + if (dev->priv_flags == INT_MAIN)
77044 + {
77045 + pAdapter = dev->priv;
77046 + }
77047 + else
77048 + {
77049 + pVirtualAd = dev->priv;
77050 + if (pVirtualAd && pVirtualAd->RtmpDev)
77051 + pAdapter = pVirtualAd->RtmpDev->priv;
77052 + }
77053 +
77054 + if (pAdapter == NULL)
77055 + {
77056 + /* if 1st open fail, pAd will be free;
77057 + So the net_dev->priv will be NULL in 2rd open */
77058 + return -ENETDOWN;
77059 + }
77060 +
77061 + if (data->length > strlen(pAdapter->nickname) + 1)
77062 + data->length = strlen(pAdapter->nickname) + 1;
77063 + if (data->length > 0) {
77064 + memcpy(nickname, pAdapter->nickname, data->length-1);
77065 + nickname[data->length-1] = '\0';
77066 + }
77067 + return 0;
77068 +}
77069 +
77070 +int rt_ioctl_siwrts(struct net_device *dev,
77071 + struct iw_request_info *info,
77072 + struct iw_param *rts, char *extra)
77073 +{
77074 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
77075 + u16 val;
77076 +
77077 + //check if the interface is down
77078 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77079 + {
77080 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77081 + return -ENETDOWN;
77082 + }
77083 +
77084 + if (rts->disabled)
77085 + val = MAX_RTS_THRESHOLD;
77086 + else if (rts->value < 0 || rts->value > MAX_RTS_THRESHOLD)
77087 + return -EINVAL;
77088 + else if (rts->value == 0)
77089 + val = MAX_RTS_THRESHOLD;
77090 + else
77091 + val = rts->value;
77092 +
77093 + if (val != pAdapter->CommonCfg.RtsThreshold)
77094 + pAdapter->CommonCfg.RtsThreshold = val;
77095 +
77096 + return 0;
77097 +}
77098 +
77099 +int rt_ioctl_giwrts(struct net_device *dev,
77100 + struct iw_request_info *info,
77101 + struct iw_param *rts, char *extra)
77102 +{
77103 + PRTMP_ADAPTER pAdapter = NULL;
77104 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
77105 +
77106 + if (dev->priv_flags == INT_MAIN)
77107 + {
77108 + pAdapter = dev->priv;
77109 + }
77110 + else
77111 + {
77112 + pVirtualAd = dev->priv;
77113 + if (pVirtualAd && pVirtualAd->RtmpDev)
77114 + pAdapter = pVirtualAd->RtmpDev->priv;
77115 + }
77116 +
77117 + if (pAdapter == NULL)
77118 + {
77119 + /* if 1st open fail, pAd will be free;
77120 + So the net_dev->priv will be NULL in 2rd open */
77121 + return -ENETDOWN;
77122 + }
77123 +
77124 + //check if the interface is down
77125 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77126 + {
77127 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77128 + return -ENETDOWN;
77129 + }
77130 +
77131 + rts->value = pAdapter->CommonCfg.RtsThreshold;
77132 + rts->disabled = (rts->value == MAX_RTS_THRESHOLD);
77133 + rts->fixed = 1;
77134 +
77135 + return 0;
77136 +}
77137 +
77138 +int rt_ioctl_siwfrag(struct net_device *dev,
77139 + struct iw_request_info *info,
77140 + struct iw_param *frag, char *extra)
77141 +{
77142 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
77143 + u16 val;
77144 +
77145 + //check if the interface is down
77146 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77147 + {
77148 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77149 + return -ENETDOWN;
77150 + }
77151 +
77152 + if (frag->disabled)
77153 + val = MAX_FRAG_THRESHOLD;
77154 + else if (frag->value >= MIN_FRAG_THRESHOLD || frag->value <= MAX_FRAG_THRESHOLD)
77155 + val = __cpu_to_le16(frag->value & ~0x1); /* even numbers only */
77156 + else if (frag->value == 0)
77157 + val = MAX_FRAG_THRESHOLD;
77158 + else
77159 + return -EINVAL;
77160 +
77161 + pAdapter->CommonCfg.FragmentThreshold = val;
77162 + return 0;
77163 +}
77164 +
77165 +int rt_ioctl_giwfrag(struct net_device *dev,
77166 + struct iw_request_info *info,
77167 + struct iw_param *frag, char *extra)
77168 +{
77169 + PRTMP_ADAPTER pAdapter = NULL;
77170 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
77171 +
77172 + if (dev->priv_flags == INT_MAIN)
77173 + {
77174 + pAdapter = dev->priv;
77175 + }
77176 + else
77177 + {
77178 + pVirtualAd = dev->priv;
77179 + if (pVirtualAd && pVirtualAd->RtmpDev)
77180 + pAdapter = pVirtualAd->RtmpDev->priv;
77181 + }
77182 +
77183 + if (pAdapter == NULL)
77184 + {
77185 + /* if 1st open fail, pAd will be free;
77186 + So the net_dev->priv will be NULL in 2rd open */
77187 + return -ENETDOWN;
77188 + }
77189 +
77190 + //check if the interface is down
77191 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77192 + {
77193 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77194 + return -ENETDOWN;
77195 + }
77196 +
77197 + frag->value = pAdapter->CommonCfg.FragmentThreshold;
77198 + frag->disabled = (frag->value == MAX_FRAG_THRESHOLD);
77199 + frag->fixed = 1;
77200 +
77201 + return 0;
77202 +}
77203 +
77204 +#define MAX_WEP_KEY_SIZE 13
77205 +#define MIN_WEP_KEY_SIZE 5
77206 +int rt_ioctl_siwencode(struct net_device *dev,
77207 + struct iw_request_info *info,
77208 + struct iw_point *erq, char *extra)
77209 +{
77210 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
77211 +
77212 + //check if the interface is down
77213 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77214 + {
77215 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77216 + return -ENETDOWN;
77217 + }
77218 +
77219 + if ((erq->length == 0) &&
77220 + (erq->flags & IW_ENCODE_DISABLED))
77221 + {
77222 + pAdapter->StaCfg.PairCipher = Ndis802_11WEPDisabled;
77223 + pAdapter->StaCfg.GroupCipher = Ndis802_11WEPDisabled;
77224 + pAdapter->StaCfg.WepStatus = Ndis802_11WEPDisabled;
77225 + pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
77226 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
77227 + goto done;
77228 + }
77229 + else if ((erq->length == 0) &&
77230 + (erq->flags & IW_ENCODE_RESTRICTED || erq->flags & IW_ENCODE_OPEN))
77231 + {
77232 + STA_PORT_SECURED(pAdapter);
77233 + pAdapter->StaCfg.PairCipher = Ndis802_11WEPEnabled;
77234 + pAdapter->StaCfg.GroupCipher = Ndis802_11WEPEnabled;
77235 + pAdapter->StaCfg.WepStatus = Ndis802_11WEPEnabled;
77236 + pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
77237 + if (erq->flags & IW_ENCODE_RESTRICTED)
77238 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeShared;
77239 + else
77240 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
77241 + goto done;
77242 + }
77243 +
77244 + if (erq->length > 0)
77245 + {
77246 + int keyIdx = (erq->flags & IW_ENCODE_INDEX) - 1;
77247 + /* Check the size of the key */
77248 + if (erq->length > MAX_WEP_KEY_SIZE) {
77249 + return -EINVAL;
77250 + }
77251 + /* Check key index */
77252 + if ((keyIdx < 0) || (keyIdx >= NR_WEP_KEYS))
77253 + {
77254 + DBGPRINT(RT_DEBUG_TRACE ,("==>rt_ioctl_siwencode::Wrong keyIdx=%d! Using default key instead (%d)\n",
77255 + keyIdx, pAdapter->StaCfg.DefaultKeyId));
77256 +
77257 + //Using default key
77258 + keyIdx = pAdapter->StaCfg.DefaultKeyId;
77259 + }
77260 +
77261 + NdisZeroMemory(pAdapter->SharedKey[BSS0][keyIdx].Key, 16);
77262 +
77263 + if (erq->length == MAX_WEP_KEY_SIZE)
77264 + {
77265 + pAdapter->SharedKey[BSS0][keyIdx].KeyLen = MAX_WEP_KEY_SIZE;
77266 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CIPHER_WEP128;
77267 + }
77268 + else if (erq->length == MIN_WEP_KEY_SIZE)
77269 + {
77270 + pAdapter->SharedKey[BSS0][keyIdx].KeyLen = MIN_WEP_KEY_SIZE;
77271 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CIPHER_WEP64;
77272 + }
77273 + else
77274 + /* Disable the key */
77275 + pAdapter->SharedKey[BSS0][keyIdx].KeyLen = 0;
77276 +
77277 + /* Check if the key is not marked as invalid */
77278 + if(!(erq->flags & IW_ENCODE_NOKEY)) {
77279 + /* Copy the key in the driver */
77280 + NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].Key, extra, erq->length);
77281 + }
77282 + }
77283 + else
77284 + {
77285 + /* Do we want to just set the transmit key index ? */
77286 + int index = (erq->flags & IW_ENCODE_INDEX) - 1;
77287 + if ((index >= 0) && (index < 4))
77288 + {
77289 + pAdapter->StaCfg.DefaultKeyId = index;
77290 + }
77291 + else
77292 + /* Don't complain if only change the mode */
77293 + if(!erq->flags & IW_ENCODE_MODE) {
77294 + return -EINVAL;
77295 + }
77296 + }
77297 +
77298 +done:
77299 + DBGPRINT(RT_DEBUG_TRACE ,("==>rt_ioctl_siwencode::erq->flags=%x\n",erq->flags));
77300 + DBGPRINT(RT_DEBUG_TRACE ,("==>rt_ioctl_siwencode::AuthMode=%x\n",pAdapter->StaCfg.AuthMode));
77301 + DBGPRINT(RT_DEBUG_TRACE ,("==>rt_ioctl_siwencode::DefaultKeyId=%x, KeyLen = %d\n",pAdapter->StaCfg.DefaultKeyId , pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].KeyLen));
77302 + DBGPRINT(RT_DEBUG_TRACE ,("==>rt_ioctl_siwencode::WepStatus=%x\n",pAdapter->StaCfg.WepStatus));
77303 + return 0;
77304 +}
77305 +
77306 +int
77307 +rt_ioctl_giwencode(struct net_device *dev,
77308 + struct iw_request_info *info,
77309 + struct iw_point *erq, char *key)
77310 +{
77311 + int kid;
77312 + PRTMP_ADAPTER pAdapter = NULL;
77313 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
77314 +
77315 + if (dev->priv_flags == INT_MAIN)
77316 + {
77317 + pAdapter = dev->priv;
77318 + }
77319 + else
77320 + {
77321 + pVirtualAd = dev->priv;
77322 + if (pVirtualAd && pVirtualAd->RtmpDev)
77323 + pAdapter = pVirtualAd->RtmpDev->priv;
77324 + }
77325 +
77326 + if (pAdapter == NULL)
77327 + {
77328 + /* if 1st open fail, pAd will be free;
77329 + So the net_dev->priv will be NULL in 2rd open */
77330 + return -ENETDOWN;
77331 + }
77332 +
77333 + //check if the interface is down
77334 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77335 + {
77336 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77337 + return -ENETDOWN;
77338 + }
77339 +
77340 + kid = erq->flags & IW_ENCODE_INDEX;
77341 + DBGPRINT(RT_DEBUG_TRACE, ("===>rt_ioctl_giwencode %d\n", erq->flags & IW_ENCODE_INDEX));
77342 +
77343 + if (pAdapter->StaCfg.WepStatus == Ndis802_11WEPDisabled)
77344 + {
77345 + erq->length = 0;
77346 + erq->flags = IW_ENCODE_DISABLED;
77347 + }
77348 + else if ((kid > 0) && (kid <=4))
77349 + {
77350 + // copy wep key
77351 + erq->flags = kid ; /* NB: base 1 */
77352 + if (erq->length > pAdapter->SharedKey[BSS0][kid-1].KeyLen)
77353 + erq->length = pAdapter->SharedKey[BSS0][kid-1].KeyLen;
77354 + memcpy(key, pAdapter->SharedKey[BSS0][kid-1].Key, erq->length);
77355 + //if ((kid == pAdapter->PortCfg.DefaultKeyId))
77356 + //erq->flags |= IW_ENCODE_ENABLED; /* XXX */
77357 + if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeShared)
77358 + erq->flags |= IW_ENCODE_RESTRICTED; /* XXX */
77359 + else
77360 + erq->flags |= IW_ENCODE_OPEN; /* XXX */
77361 +
77362 + }
77363 + else if (kid == 0)
77364 + {
77365 + if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeShared)
77366 + erq->flags |= IW_ENCODE_RESTRICTED; /* XXX */
77367 + else
77368 + erq->flags |= IW_ENCODE_OPEN; /* XXX */
77369 + erq->length = pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].KeyLen;
77370 + memcpy(key, pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].Key, erq->length);
77371 + // copy default key ID
77372 + if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeShared)
77373 + erq->flags |= IW_ENCODE_RESTRICTED; /* XXX */
77374 + else
77375 + erq->flags |= IW_ENCODE_OPEN; /* XXX */
77376 + erq->flags = pAdapter->StaCfg.DefaultKeyId + 1; /* NB: base 1 */
77377 + erq->flags |= IW_ENCODE_ENABLED; /* XXX */
77378 + }
77379 +
77380 + return 0;
77381 +
77382 +}
77383 +
77384 +static int
77385 +rt_ioctl_setparam(struct net_device *dev, struct iw_request_info *info,
77386 + void *w, char *extra)
77387 +{
77388 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
77389 + PRTMP_ADAPTER pAdapter;
77390 + POS_COOKIE pObj;
77391 + char *this_char = extra;
77392 + char *value;
77393 + int Status=0;
77394 +
77395 + if (dev->priv_flags == INT_MAIN)
77396 + {
77397 + pAdapter = dev->priv;
77398 + }
77399 + else
77400 + {
77401 + pVirtualAd = dev->priv;
77402 + pAdapter = pVirtualAd->RtmpDev->priv;
77403 + }
77404 + pObj = (POS_COOKIE) pAdapter->OS_Cookie;
77405 +
77406 + if (pAdapter == NULL)
77407 + {
77408 + /* if 1st open fail, pAd will be free;
77409 + So the net_dev->priv will be NULL in 2rd open */
77410 + return -ENETDOWN;
77411 + }
77412 +
77413 + {
77414 + pObj->ioctl_if_type = INT_MAIN;
77415 + pObj->ioctl_if = MAIN_MBSSID;
77416 + }
77417 +
77418 + //check if the interface is down
77419 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77420 + {
77421 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77422 + return -ENETDOWN;
77423 + }
77424 +
77425 + if (!*this_char)
77426 + return -EINVAL;
77427 +
77428 + if ((value = rtstrchr(this_char, '=')) != NULL)
77429 + *value++ = 0;
77430 +
77431 + if (!value)
77432 + return -EINVAL;
77433 +
77434 + // reject setting nothing besides ANY ssid(ssidLen=0)
77435 + if (!*value && (strcmp(this_char, "SSID") != 0))
77436 + return -EINVAL;
77437 +
77438 + for (PRTMP_PRIVATE_SET_PROC = RTMP_PRIVATE_SUPPORT_PROC; PRTMP_PRIVATE_SET_PROC->name; PRTMP_PRIVATE_SET_PROC++)
77439 + {
77440 + if (strcmp(this_char, PRTMP_PRIVATE_SET_PROC->name) == 0)
77441 + {
77442 + if(!PRTMP_PRIVATE_SET_PROC->set_proc(pAdapter, value))
77443 + { //FALSE:Set private failed then return Invalid argument
77444 + Status = -EINVAL;
77445 + }
77446 + break; //Exit for loop.
77447 + }
77448 + }
77449 +
77450 + if(PRTMP_PRIVATE_SET_PROC->name == NULL)
77451 + { //Not found argument
77452 + Status = -EINVAL;
77453 + DBGPRINT(RT_DEBUG_TRACE, ("===>rt_ioctl_setparam:: (iwpriv) Not Support Set Command [%s=%s]\n", this_char, value));
77454 + }
77455 +
77456 + return Status;
77457 +}
77458 +
77459 +
77460 +static int
77461 +rt_private_get_statistics(struct net_device *dev, struct iw_request_info *info,
77462 + struct iw_point *wrq, char *extra)
77463 +{
77464 + INT Status = 0;
77465 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
77466 +
77467 + if (extra == NULL)
77468 + {
77469 + wrq->length = 0;
77470 + return -EIO;
77471 + }
77472 +
77473 + memset(extra, 0x00, IW_PRIV_SIZE_MASK);
77474 + sprintf(extra, "\n\n");
77475 +
77476 +#ifdef RALINK_ATE
77477 + if (ATE_ON(pAd))
77478 + {
77479 + sprintf(extra+strlen(extra), "Tx success = %ld\n", (ULONG)pAd->ate.TxDoneCount);
77480 + //sprintf(extra+strlen(extra), "Tx success without retry = %ld\n", (ULONG)pAd->ate.TxDoneCount);
77481 + }
77482 + else
77483 +#endif // RALINK_ATE //
77484 + {
77485 + sprintf(extra+strlen(extra), "Tx success = %ld\n", (ULONG)pAd->WlanCounters.TransmittedFragmentCount.QuadPart);
77486 + sprintf(extra+strlen(extra), "Tx success without retry = %ld\n", (ULONG)pAd->WlanCounters.TransmittedFragmentCount.QuadPart - (ULONG)pAd->WlanCounters.RetryCount.QuadPart);
77487 + }
77488 + sprintf(extra+strlen(extra), "Tx success after retry = %ld\n", (ULONG)pAd->WlanCounters.RetryCount.QuadPart);
77489 + sprintf(extra+strlen(extra), "Tx fail to Rcv ACK after retry = %ld\n", (ULONG)pAd->WlanCounters.FailedCount.QuadPart);
77490 + sprintf(extra+strlen(extra), "RTS Success Rcv CTS = %ld\n", (ULONG)pAd->WlanCounters.RTSSuccessCount.QuadPart);
77491 + sprintf(extra+strlen(extra), "RTS Fail Rcv CTS = %ld\n", (ULONG)pAd->WlanCounters.RTSFailureCount.QuadPart);
77492 +
77493 + sprintf(extra+strlen(extra), "Rx success = %ld\n", (ULONG)pAd->WlanCounters.ReceivedFragmentCount.QuadPart);
77494 + sprintf(extra+strlen(extra), "Rx with CRC = %ld\n", (ULONG)pAd->WlanCounters.FCSErrorCount.QuadPart);
77495 + sprintf(extra+strlen(extra), "Rx drop due to out of resource = %ld\n", (ULONG)pAd->Counters8023.RxNoBuffer);
77496 + sprintf(extra+strlen(extra), "Rx duplicate frame = %ld\n", (ULONG)pAd->WlanCounters.FrameDuplicateCount.QuadPart);
77497 +
77498 + sprintf(extra+strlen(extra), "False CCA (one second) = %ld\n", (ULONG)pAd->RalinkCounters.OneSecFalseCCACnt);
77499 +#ifdef RALINK_ATE
77500 + if (ATE_ON(pAd))
77501 + {
77502 + if (pAd->ate.RxAntennaSel == 0)
77503 + {
77504 + sprintf(extra+strlen(extra), "RSSI-A = %ld\n", (LONG)(pAd->ate.LastRssi0 - pAd->BbpRssiToDbmDelta));
77505 + sprintf(extra+strlen(extra), "RSSI-B (if available) = %ld\n", (LONG)(pAd->ate.LastRssi1 - pAd->BbpRssiToDbmDelta));
77506 + sprintf(extra+strlen(extra), "RSSI-C (if available) = %ld\n\n", (LONG)(pAd->ate.LastRssi2 - pAd->BbpRssiToDbmDelta));
77507 + }
77508 + else
77509 + {
77510 + sprintf(extra+strlen(extra), "RSSI = %ld\n", (LONG)(pAd->ate.LastRssi0 - pAd->BbpRssiToDbmDelta));
77511 + }
77512 + }
77513 + else
77514 +#endif // RALINK_ATE //
77515 + {
77516 + sprintf(extra+strlen(extra), "RSSI-A = %ld\n", (LONG)(pAd->StaCfg.RssiSample.LastRssi0 - pAd->BbpRssiToDbmDelta));
77517 + sprintf(extra+strlen(extra), "RSSI-B (if available) = %ld\n", (LONG)(pAd->StaCfg.RssiSample.LastRssi1 - pAd->BbpRssiToDbmDelta));
77518 + sprintf(extra+strlen(extra), "RSSI-C (if available) = %ld\n\n", (LONG)(pAd->StaCfg.RssiSample.LastRssi2 - pAd->BbpRssiToDbmDelta));
77519 + }
77520 +#ifdef WPA_SUPPLICANT_SUPPORT
77521 + sprintf(extra+strlen(extra), "WpaSupplicantUP = %d\n\n", pAd->StaCfg.WpaSupplicantUP);
77522 +#endif // WPA_SUPPLICANT_SUPPORT //
77523 +
77524 +
77525 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77526 + DBGPRINT(RT_DEBUG_TRACE, ("<== rt_private_get_statistics, wrq->length = %d\n", wrq->length));
77527 +
77528 + return Status;
77529 +}
77530 +
77531 +#ifdef DOT11_N_SUPPORT
77532 +void getBaInfo(
77533 + IN PRTMP_ADAPTER pAd,
77534 + IN PUCHAR pOutBuf)
77535 +{
77536 + INT i, j;
77537 + BA_ORI_ENTRY *pOriBAEntry;
77538 + BA_REC_ENTRY *pRecBAEntry;
77539 +
77540 + for (i=0; i<MAX_LEN_OF_MAC_TABLE; i++)
77541 + {
77542 + PMAC_TABLE_ENTRY pEntry = &pAd->MacTab.Content[i];
77543 + if (((pEntry->ValidAsCLI || pEntry->ValidAsApCli) && (pEntry->Sst == SST_ASSOC))
77544 + || (pEntry->ValidAsWDS) || (pEntry->ValidAsMesh))
77545 + {
77546 + sprintf(pOutBuf, "%s\n%02X:%02X:%02X:%02X:%02X:%02X (Aid = %d) (AP) -\n",
77547 + pOutBuf,
77548 + pEntry->Addr[0], pEntry->Addr[1], pEntry->Addr[2],
77549 + pEntry->Addr[3], pEntry->Addr[4], pEntry->Addr[5], pEntry->Aid);
77550 +
77551 + sprintf(pOutBuf, "%s[Recipient]\n", pOutBuf);
77552 + for (j=0; j < NUM_OF_TID; j++)
77553 + {
77554 + if (pEntry->BARecWcidArray[j] != 0)
77555 + {
77556 + pRecBAEntry =&pAd->BATable.BARecEntry[pEntry->BARecWcidArray[j]];
77557 + sprintf(pOutBuf, "%sTID=%d, BAWinSize=%d, LastIndSeq=%d, ReorderingPkts=%d\n", pOutBuf, j, pRecBAEntry->BAWinSize, pRecBAEntry->LastIndSeq, pRecBAEntry->list.qlen);
77558 + }
77559 + }
77560 + sprintf(pOutBuf, "%s\n", pOutBuf);
77561 +
77562 + sprintf(pOutBuf, "%s[Originator]\n", pOutBuf);
77563 + for (j=0; j < NUM_OF_TID; j++)
77564 + {
77565 + if (pEntry->BAOriWcidArray[j] != 0)
77566 + {
77567 + pOriBAEntry =&pAd->BATable.BAOriEntry[pEntry->BAOriWcidArray[j]];
77568 + sprintf(pOutBuf, "%sTID=%d, BAWinSize=%d, StartSeq=%d, CurTxSeq=%d\n", pOutBuf, j, pOriBAEntry->BAWinSize, pOriBAEntry->Sequence, pEntry->TxSeq[j]);
77569 + }
77570 + }
77571 + sprintf(pOutBuf, "%s\n\n", pOutBuf);
77572 + }
77573 + if (strlen(pOutBuf) > (IW_PRIV_SIZE_MASK - 30))
77574 + break;
77575 + }
77576 +
77577 + return;
77578 +}
77579 +#endif // DOT11_N_SUPPORT //
77580 +
77581 +static int
77582 +rt_private_show(struct net_device *dev, struct iw_request_info *info,
77583 + struct iw_point *wrq, char *extra)
77584 +{
77585 + INT Status = 0;
77586 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
77587 + PRTMP_ADAPTER pAd;
77588 + POS_COOKIE pObj;
77589 + u32 subcmd = wrq->flags;
77590 +
77591 + if (dev->priv_flags == INT_MAIN)
77592 + pAd = dev->priv;
77593 + else
77594 + {
77595 + pVirtualAd = dev->priv;
77596 + pAd = pVirtualAd->RtmpDev->priv;
77597 + }
77598 + pObj = (POS_COOKIE) pAd->OS_Cookie;
77599 +
77600 + if (pAd == NULL)
77601 + {
77602 + /* if 1st open fail, pAd will be free;
77603 + So the net_dev->priv will be NULL in 2rd open */
77604 + return -ENETDOWN;
77605 + }
77606 +
77607 + if (extra == NULL)
77608 + {
77609 + wrq->length = 0;
77610 + return -EIO;
77611 + }
77612 + memset(extra, 0x00, IW_PRIV_SIZE_MASK);
77613 +
77614 + {
77615 + pObj->ioctl_if_type = INT_MAIN;
77616 + pObj->ioctl_if = MAIN_MBSSID;
77617 + }
77618 +
77619 + switch(subcmd)
77620 + {
77621 +
77622 + case SHOW_CONN_STATUS:
77623 + if (MONITOR_ON(pAd))
77624 + {
77625 +#ifdef DOT11_N_SUPPORT
77626 + if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED &&
77627 + pAd->CommonCfg.RegTransmitSetting.field.BW)
77628 + sprintf(extra, "Monitor Mode(CentralChannel %d)\n", pAd->CommonCfg.CentralChannel);
77629 + else
77630 +#endif // DOT11_N_SUPPORT //
77631 + sprintf(extra, "Monitor Mode(Channel %d)\n", pAd->CommonCfg.Channel);
77632 + }
77633 + else
77634 + {
77635 + if (pAd->IndicateMediaState == NdisMediaStateConnected)
77636 + {
77637 + if (INFRA_ON(pAd))
77638 + {
77639 + sprintf(extra, "Connected(AP: %s[%02X:%02X:%02X:%02X:%02X:%02X])\n",
77640 + pAd->CommonCfg.Ssid,
77641 + pAd->CommonCfg.Bssid[0],
77642 + pAd->CommonCfg.Bssid[1],
77643 + pAd->CommonCfg.Bssid[2],
77644 + pAd->CommonCfg.Bssid[3],
77645 + pAd->CommonCfg.Bssid[4],
77646 + pAd->CommonCfg.Bssid[5]);
77647 + DBGPRINT(RT_DEBUG_TRACE ,("Ssid=%s ,Ssidlen = %d\n",pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen));
77648 + }
77649 + else if (ADHOC_ON(pAd))
77650 + sprintf(extra, "Connected\n");
77651 + }
77652 + else
77653 + {
77654 + sprintf(extra, "Disconnected\n");
77655 + DBGPRINT(RT_DEBUG_TRACE ,("ConnStatus is not connected\n"));
77656 + }
77657 + }
77658 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77659 + break;
77660 + case SHOW_DRVIER_VERION:
77661 + sprintf(extra, "Driver version-%s, %s %s\n", STA_DRIVER_VERSION, __DATE__, __TIME__ );
77662 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77663 + break;
77664 +#ifdef DOT11_N_SUPPORT
77665 + case SHOW_BA_INFO:
77666 + getBaInfo(pAd, extra);
77667 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77668 + break;
77669 +#endif // DOT11_N_SUPPORT //
77670 + case SHOW_DESC_INFO:
77671 + {
77672 + Show_DescInfo_Proc(pAd, NULL);
77673 + wrq->length = 0; // 1: size of '\0'
77674 + }
77675 + break;
77676 + case RAIO_OFF:
77677 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
77678 + {
77679 + sprintf(extra, "Scanning\n");
77680 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77681 + break;
77682 + }
77683 + pAd->StaCfg.bSwRadio = FALSE;
77684 + if (pAd->StaCfg.bRadio != (pAd->StaCfg.bHwRadio && pAd->StaCfg.bSwRadio))
77685 + {
77686 + pAd->StaCfg.bRadio = (pAd->StaCfg.bHwRadio && pAd->StaCfg.bSwRadio);
77687 + if (pAd->StaCfg.bRadio == FALSE)
77688 + {
77689 + MlmeRadioOff(pAd);
77690 + // Update extra information
77691 + pAd->ExtraInfo = SW_RADIO_OFF;
77692 + }
77693 + }
77694 + sprintf(extra, "Radio Off\n");
77695 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77696 + break;
77697 + case RAIO_ON:
77698 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
77699 + {
77700 + sprintf(extra, "Scanning\n");
77701 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77702 + break;
77703 + }
77704 + pAd->StaCfg.bSwRadio = TRUE;
77705 + //if (pAd->StaCfg.bRadio != (pAd->StaCfg.bHwRadio && pAd->StaCfg.bSwRadio))
77706 + {
77707 + pAd->StaCfg.bRadio = (pAd->StaCfg.bHwRadio && pAd->StaCfg.bSwRadio);
77708 + if (pAd->StaCfg.bRadio == TRUE)
77709 + {
77710 + MlmeRadioOn(pAd);
77711 + // Update extra information
77712 + pAd->ExtraInfo = EXTRA_INFO_CLEAR;
77713 + }
77714 + }
77715 + sprintf(extra, "Radio On\n");
77716 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77717 + break;
77718 +
77719 +
77720 +#ifdef QOS_DLS_SUPPORT
77721 + case SHOW_DLS_ENTRY_INFO:
77722 + {
77723 + Set_DlsEntryInfo_Display_Proc(pAd, NULL);
77724 + wrq->length = 0; // 1: size of '\0'
77725 + }
77726 + break;
77727 +#endif // QOS_DLS_SUPPORT //
77728 +
77729 + case SHOW_CFG_VALUE:
77730 + {
77731 + Status = RTMPShowCfgValue(pAd, wrq->pointer, extra);
77732 + if (Status == 0)
77733 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
77734 + }
77735 + break;
77736 + default:
77737 + DBGPRINT(RT_DEBUG_TRACE, ("%s - unknow subcmd = %d\n", __FUNCTION__, subcmd));
77738 + break;
77739 + }
77740 +
77741 + return Status;
77742 +}
77743 +
77744 +#ifdef SIOCSIWMLME
77745 +int rt_ioctl_siwmlme(struct net_device *dev,
77746 + struct iw_request_info *info,
77747 + union iwreq_data *wrqu,
77748 + char *extra)
77749 +{
77750 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
77751 + struct iw_mlme *pMlme = (struct iw_mlme *)wrqu->data.pointer;
77752 + MLME_QUEUE_ELEM MsgElem;
77753 + MLME_DISASSOC_REQ_STRUCT DisAssocReq;
77754 + MLME_DEAUTH_REQ_STRUCT DeAuthReq;
77755 +
77756 + DBGPRINT(RT_DEBUG_TRACE, ("====> %s\n", __FUNCTION__));
77757 +
77758 + if (pMlme == NULL)
77759 + return -EINVAL;
77760 +
77761 + switch(pMlme->cmd)
77762 + {
77763 +#ifdef IW_MLME_DEAUTH
77764 + case IW_MLME_DEAUTH:
77765 + DBGPRINT(RT_DEBUG_TRACE, ("====> %s - IW_MLME_DEAUTH\n", __FUNCTION__));
77766 + COPY_MAC_ADDR(DeAuthReq.Addr, pAd->CommonCfg.Bssid);
77767 + DeAuthReq.Reason = pMlme->reason_code;
77768 + MsgElem.MsgLen = sizeof(MLME_DEAUTH_REQ_STRUCT);
77769 + NdisMoveMemory(MsgElem.Msg, &DeAuthReq, sizeof(MLME_DEAUTH_REQ_STRUCT));
77770 + MlmeDeauthReqAction(pAd, &MsgElem);
77771 + if (INFRA_ON(pAd))
77772 + {
77773 + LinkDown(pAd, FALSE);
77774 + pAd->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
77775 + }
77776 + break;
77777 +#endif // IW_MLME_DEAUTH //
77778 +#ifdef IW_MLME_DISASSOC
77779 + case IW_MLME_DISASSOC:
77780 + DBGPRINT(RT_DEBUG_TRACE, ("====> %s - IW_MLME_DISASSOC\n", __FUNCTION__));
77781 + COPY_MAC_ADDR(DisAssocReq.Addr, pAd->CommonCfg.Bssid);
77782 + DisAssocReq.Reason = pMlme->reason_code;
77783 +
77784 + MsgElem.Machine = ASSOC_STATE_MACHINE;
77785 + MsgElem.MsgType = MT2_MLME_DISASSOC_REQ;
77786 + MsgElem.MsgLen = sizeof(MLME_DISASSOC_REQ_STRUCT);
77787 + NdisMoveMemory(MsgElem.Msg, &DisAssocReq, sizeof(MLME_DISASSOC_REQ_STRUCT));
77788 +
77789 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_OID_DISASSOC;
77790 + MlmeDisassocReqAction(pAd, &MsgElem);
77791 + break;
77792 +#endif // IW_MLME_DISASSOC //
77793 + default:
77794 + DBGPRINT(RT_DEBUG_TRACE, ("====> %s - Unknow Command\n", __FUNCTION__));
77795 + break;
77796 + }
77797 +
77798 + return 0;
77799 +}
77800 +#endif // SIOCSIWMLME //
77801 +
77802 +#if WIRELESS_EXT > 17
77803 +int rt_ioctl_siwauth(struct net_device *dev,
77804 + struct iw_request_info *info,
77805 + union iwreq_data *wrqu, char *extra)
77806 +{
77807 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
77808 + struct iw_param *param = &wrqu->param;
77809 +
77810 + //check if the interface is down
77811 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77812 + {
77813 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77814 + return -ENETDOWN;
77815 + }
77816 + switch (param->flags & IW_AUTH_INDEX) {
77817 + case IW_AUTH_WPA_VERSION:
77818 + if (param->value == IW_AUTH_WPA_VERSION_WPA)
77819 + {
77820 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPAPSK;
77821 + if (pAdapter->StaCfg.BssType == BSS_ADHOC)
77822 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPANone;
77823 + }
77824 + else if (param->value == IW_AUTH_WPA_VERSION_WPA2)
77825 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPA2PSK;
77826 +
77827 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_WPA_VERSION - param->value = %d!\n", __FUNCTION__, param->value));
77828 + break;
77829 + case IW_AUTH_CIPHER_PAIRWISE:
77830 + if (param->value == IW_AUTH_CIPHER_NONE)
77831 + {
77832 + pAdapter->StaCfg.WepStatus = Ndis802_11WEPDisabled;
77833 + pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
77834 + pAdapter->StaCfg.PairCipher = Ndis802_11WEPDisabled;
77835 + }
77836 + else if (param->value == IW_AUTH_CIPHER_WEP40 ||
77837 + param->value == IW_AUTH_CIPHER_WEP104)
77838 + {
77839 + pAdapter->StaCfg.WepStatus = Ndis802_11WEPEnabled;
77840 + pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
77841 + pAdapter->StaCfg.PairCipher = Ndis802_11WEPEnabled;
77842 +#ifdef WPA_SUPPLICANT_SUPPORT
77843 + pAdapter->StaCfg.IEEE8021X = FALSE;
77844 +#endif // WPA_SUPPLICANT_SUPPORT //
77845 + }
77846 + else if (param->value == IW_AUTH_CIPHER_TKIP)
77847 + {
77848 + pAdapter->StaCfg.WepStatus = Ndis802_11Encryption2Enabled;
77849 + pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
77850 + pAdapter->StaCfg.PairCipher = Ndis802_11Encryption2Enabled;
77851 + }
77852 + else if (param->value == IW_AUTH_CIPHER_CCMP)
77853 + {
77854 + pAdapter->StaCfg.WepStatus = Ndis802_11Encryption3Enabled;
77855 + pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
77856 + pAdapter->StaCfg.PairCipher = Ndis802_11Encryption3Enabled;
77857 + }
77858 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_CIPHER_PAIRWISE - param->value = %d!\n", __FUNCTION__, param->value));
77859 + break;
77860 + case IW_AUTH_CIPHER_GROUP:
77861 + if (param->value == IW_AUTH_CIPHER_NONE)
77862 + {
77863 + pAdapter->StaCfg.GroupCipher = Ndis802_11WEPDisabled;
77864 + }
77865 + else if (param->value == IW_AUTH_CIPHER_WEP40 ||
77866 + param->value == IW_AUTH_CIPHER_WEP104)
77867 + {
77868 + pAdapter->StaCfg.GroupCipher = Ndis802_11WEPEnabled;
77869 + }
77870 + else if (param->value == IW_AUTH_CIPHER_TKIP)
77871 + {
77872 + pAdapter->StaCfg.GroupCipher = Ndis802_11Encryption2Enabled;
77873 + }
77874 + else if (param->value == IW_AUTH_CIPHER_CCMP)
77875 + {
77876 + pAdapter->StaCfg.GroupCipher = Ndis802_11Encryption3Enabled;
77877 + }
77878 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_CIPHER_GROUP - param->value = %d!\n", __FUNCTION__, param->value));
77879 + break;
77880 + case IW_AUTH_KEY_MGMT:
77881 + if (param->value == IW_AUTH_KEY_MGMT_802_1X)
77882 + {
77883 + if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK)
77884 + {
77885 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPA;
77886 +#ifdef WPA_SUPPLICANT_SUPPORT
77887 + pAdapter->StaCfg.IEEE8021X = FALSE;
77888 +#endif // WPA_SUPPLICANT_SUPPORT //
77889 + }
77890 + else if (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)
77891 + {
77892 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPA2;
77893 +#ifdef WPA_SUPPLICANT_SUPPORT
77894 + pAdapter->StaCfg.IEEE8021X = FALSE;
77895 +#endif // WPA_SUPPLICANT_SUPPORT //
77896 + }
77897 +#ifdef WPA_SUPPLICANT_SUPPORT
77898 + else
77899 + // WEP 1x
77900 + pAdapter->StaCfg.IEEE8021X = TRUE;
77901 +#endif // WPA_SUPPLICANT_SUPPORT //
77902 + }
77903 + else if (param->value == 0)
77904 + {
77905 + STA_PORT_SECURED(pAdapter);
77906 + }
77907 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_KEY_MGMT - param->value = %d!\n", __FUNCTION__, param->value));
77908 + break;
77909 + case IW_AUTH_RX_UNENCRYPTED_EAPOL:
77910 + break;
77911 + case IW_AUTH_PRIVACY_INVOKED:
77912 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_PRIVACY_INVOKED - param->value = %d!\n", __FUNCTION__, param->value));
77913 + break;
77914 + case IW_AUTH_DROP_UNENCRYPTED:
77915 + if (param->value != 0)
77916 + pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
77917 + else
77918 + {
77919 + STA_PORT_SECURED(pAdapter);
77920 + }
77921 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_WPA_VERSION - param->value = %d!\n", __FUNCTION__, param->value));
77922 + break;
77923 + case IW_AUTH_80211_AUTH_ALG:
77924 + if (param->value & IW_AUTH_ALG_SHARED_KEY)
77925 + {
77926 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeShared;
77927 + }
77928 + else if (param->value & IW_AUTH_ALG_OPEN_SYSTEM)
77929 + {
77930 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
77931 + }
77932 + else
77933 + return -EINVAL;
77934 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_80211_AUTH_ALG - param->value = %d!\n", __FUNCTION__, param->value));
77935 + break;
77936 + case IW_AUTH_WPA_ENABLED:
77937 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_AUTH_WPA_ENABLED - Driver supports WPA!(param->value = %d)\n", __FUNCTION__, param->value));
77938 + break;
77939 + default:
77940 + return -EOPNOTSUPP;
77941 +}
77942 +
77943 + return 0;
77944 +}
77945 +
77946 +int rt_ioctl_giwauth(struct net_device *dev,
77947 + struct iw_request_info *info,
77948 + union iwreq_data *wrqu, char *extra)
77949 +{
77950 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
77951 + struct iw_param *param = &wrqu->param;
77952 +
77953 + //check if the interface is down
77954 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
77955 + {
77956 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
77957 + return -ENETDOWN;
77958 + }
77959 +
77960 + switch (param->flags & IW_AUTH_INDEX) {
77961 + case IW_AUTH_DROP_UNENCRYPTED:
77962 + param->value = (pAdapter->StaCfg.WepStatus == Ndis802_11WEPDisabled) ? 0 : 1;
77963 + break;
77964 +
77965 + case IW_AUTH_80211_AUTH_ALG:
77966 + param->value = (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeShared) ? IW_AUTH_ALG_SHARED_KEY : IW_AUTH_ALG_OPEN_SYSTEM;
77967 + break;
77968 +
77969 + case IW_AUTH_WPA_ENABLED:
77970 + param->value = (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA) ? 1 : 0;
77971 + break;
77972 +
77973 + default:
77974 + return -EOPNOTSUPP;
77975 + }
77976 + DBGPRINT(RT_DEBUG_TRACE, ("rt_ioctl_giwauth::param->value = %d!\n", param->value));
77977 + return 0;
77978 +}
77979 +
77980 +void fnSetCipherKey(
77981 + IN PRTMP_ADAPTER pAdapter,
77982 + IN INT keyIdx,
77983 + IN UCHAR CipherAlg,
77984 + IN BOOLEAN bGTK,
77985 + IN struct iw_encode_ext *ext)
77986 +{
77987 + NdisZeroMemory(&pAdapter->SharedKey[BSS0][keyIdx], sizeof(CIPHER_KEY));
77988 + pAdapter->SharedKey[BSS0][keyIdx].KeyLen = LEN_TKIP_EK;
77989 + NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].Key, ext->key, LEN_TKIP_EK);
77990 + NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].TxMic, ext->key + LEN_TKIP_EK, LEN_TKIP_TXMICK);
77991 + NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].RxMic, ext->key + LEN_TKIP_EK + LEN_TKIP_TXMICK, LEN_TKIP_RXMICK);
77992 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CipherAlg;
77993 +
77994 + // Update group key information to ASIC Shared Key Table
77995 + AsicAddSharedKeyEntry(pAdapter,
77996 + BSS0,
77997 + keyIdx,
77998 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg,
77999 + pAdapter->SharedKey[BSS0][keyIdx].Key,
78000 + pAdapter->SharedKey[BSS0][keyIdx].TxMic,
78001 + pAdapter->SharedKey[BSS0][keyIdx].RxMic);
78002 +
78003 + if (bGTK)
78004 + // Update ASIC WCID attribute table and IVEIV table
78005 + RTMPAddWcidAttributeEntry(pAdapter,
78006 + BSS0,
78007 + keyIdx,
78008 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg,
78009 + NULL);
78010 + else
78011 + // Update ASIC WCID attribute table and IVEIV table
78012 + RTMPAddWcidAttributeEntry(pAdapter,
78013 + BSS0,
78014 + keyIdx,
78015 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg,
78016 + &pAdapter->MacTab.Content[BSSID_WCID]);
78017 +}
78018 +
78019 +int rt_ioctl_siwencodeext(struct net_device *dev,
78020 + struct iw_request_info *info,
78021 + union iwreq_data *wrqu,
78022 + char *extra)
78023 + {
78024 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
78025 + struct iw_point *encoding = &wrqu->encoding;
78026 + struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
78027 + int keyIdx, alg = ext->alg;
78028 +
78029 + //check if the interface is down
78030 + if(!RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_INTERRUPT_IN_USE))
78031 + {
78032 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
78033 + return -ENETDOWN;
78034 + }
78035 +
78036 + if (encoding->flags & IW_ENCODE_DISABLED)
78037 + {
78038 + keyIdx = (encoding->flags & IW_ENCODE_INDEX) - 1;
78039 + // set BSSID wcid entry of the Pair-wise Key table as no-security mode
78040 + AsicRemovePairwiseKeyEntry(pAdapter, BSS0, BSSID_WCID);
78041 + pAdapter->SharedKey[BSS0][keyIdx].KeyLen = 0;
78042 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CIPHER_NONE;
78043 + AsicRemoveSharedKeyEntry(pAdapter, 0, (UCHAR)keyIdx);
78044 + NdisZeroMemory(&pAdapter->SharedKey[BSS0][keyIdx], sizeof(CIPHER_KEY));
78045 + DBGPRINT(RT_DEBUG_TRACE, ("%s::Remove all keys!(encoding->flags = %x)\n", __FUNCTION__, encoding->flags));
78046 + }
78047 + else
78048 + {
78049 + // Get Key Index and convet to our own defined key index
78050 + keyIdx = (encoding->flags & IW_ENCODE_INDEX) - 1;
78051 + if((keyIdx < 0) || (keyIdx >= NR_WEP_KEYS))
78052 + return -EINVAL;
78053 +
78054 + if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY)
78055 + {
78056 + pAdapter->StaCfg.DefaultKeyId = keyIdx;
78057 + DBGPRINT(RT_DEBUG_TRACE, ("%s::DefaultKeyId = %d\n", __FUNCTION__, pAdapter->StaCfg.DefaultKeyId));
78058 + }
78059 +
78060 + switch (alg) {
78061 + case IW_ENCODE_ALG_NONE:
78062 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_ENCODE_ALG_NONE\n", __FUNCTION__));
78063 + break;
78064 + case IW_ENCODE_ALG_WEP:
78065 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_ENCODE_ALG_WEP - ext->key_len = %d, keyIdx = %d\n", __FUNCTION__, ext->key_len, keyIdx));
78066 + if (ext->key_len == MAX_WEP_KEY_SIZE)
78067 + {
78068 + pAdapter->SharedKey[BSS0][keyIdx].KeyLen = MAX_WEP_KEY_SIZE;
78069 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CIPHER_WEP128;
78070 + }
78071 + else if (ext->key_len == MIN_WEP_KEY_SIZE)
78072 + {
78073 + pAdapter->SharedKey[BSS0][keyIdx].KeyLen = MIN_WEP_KEY_SIZE;
78074 + pAdapter->SharedKey[BSS0][keyIdx].CipherAlg = CIPHER_WEP64;
78075 + }
78076 + else
78077 + return -EINVAL;
78078 +
78079 + NdisZeroMemory(pAdapter->SharedKey[BSS0][keyIdx].Key, 16);
78080 + NdisMoveMemory(pAdapter->SharedKey[BSS0][keyIdx].Key, ext->key, ext->key_len);
78081 + break;
78082 + case IW_ENCODE_ALG_TKIP:
78083 + DBGPRINT(RT_DEBUG_TRACE, ("%s::IW_ENCODE_ALG_TKIP - keyIdx = %d, ext->key_len = %d\n", __FUNCTION__, keyIdx, ext->key_len));
78084 + if (ext->key_len == 32)
78085 + {
78086 + if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY)
78087 + {
78088 + fnSetCipherKey(pAdapter, keyIdx, CIPHER_TKIP, FALSE, ext);
78089 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA2)
78090 + {
78091 + STA_PORT_SECURED(pAdapter);
78092 + }
78093 + }
78094 + else if (ext->ext_flags & IW_ENCODE_EXT_GROUP_KEY)
78095 + {
78096 + fnSetCipherKey(pAdapter, keyIdx, CIPHER_TKIP, TRUE, ext);
78097 +
78098 + // set 802.1x port control
78099 + STA_PORT_SECURED(pAdapter);
78100 + }
78101 + }
78102 + else
78103 + return -EINVAL;
78104 + break;
78105 + case IW_ENCODE_ALG_CCMP:
78106 + if (ext->ext_flags & IW_ENCODE_EXT_SET_TX_KEY)
78107 + {
78108 + fnSetCipherKey(pAdapter, keyIdx, CIPHER_AES, FALSE, ext);
78109 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA2)
78110 + STA_PORT_SECURED(pAdapter);
78111 + }
78112 + else if (ext->ext_flags & IW_ENCODE_EXT_GROUP_KEY)
78113 + {
78114 + fnSetCipherKey(pAdapter, keyIdx, CIPHER_AES, TRUE, ext);
78115 +
78116 + // set 802.1x port control
78117 + STA_PORT_SECURED(pAdapter);
78118 + }
78119 + break;
78120 + default:
78121 + return -EINVAL;
78122 + }
78123 + }
78124 +
78125 + return 0;
78126 +}
78127 +
78128 +int
78129 +rt_ioctl_giwencodeext(struct net_device *dev,
78130 + struct iw_request_info *info,
78131 + union iwreq_data *wrqu, char *extra)
78132 +{
78133 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
78134 + PCHAR pKey = NULL;
78135 + struct iw_point *encoding = &wrqu->encoding;
78136 + struct iw_encode_ext *ext = (struct iw_encode_ext *)extra;
78137 + int idx, max_key_len;
78138 +
78139 + DBGPRINT(RT_DEBUG_TRACE ,("===> rt_ioctl_giwencodeext\n"));
78140 +
78141 + max_key_len = encoding->length - sizeof(*ext);
78142 + if (max_key_len < 0)
78143 + return -EINVAL;
78144 +
78145 + idx = encoding->flags & IW_ENCODE_INDEX;
78146 + if (idx)
78147 + {
78148 + if (idx < 1 || idx > 4)
78149 + return -EINVAL;
78150 + idx--;
78151 +
78152 + if ((pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) ||
78153 + (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled))
78154 + {
78155 + if (idx != pAd->StaCfg.DefaultKeyId)
78156 + {
78157 + ext->key_len = 0;
78158 + return 0;
78159 + }
78160 + }
78161 + }
78162 + else
78163 + idx = pAd->StaCfg.DefaultKeyId;
78164 +
78165 + encoding->flags = idx + 1;
78166 + memset(ext, 0, sizeof(*ext));
78167 +
78168 + ext->key_len = 0;
78169 + switch(pAd->StaCfg.WepStatus) {
78170 + case Ndis802_11WEPDisabled:
78171 + ext->alg = IW_ENCODE_ALG_NONE;
78172 + encoding->flags |= IW_ENCODE_DISABLED;
78173 + break;
78174 + case Ndis802_11WEPEnabled:
78175 + ext->alg = IW_ENCODE_ALG_WEP;
78176 + if (pAd->SharedKey[BSS0][idx].KeyLen > max_key_len)
78177 + return -E2BIG;
78178 + else
78179 + {
78180 + ext->key_len = pAd->SharedKey[BSS0][idx].KeyLen;
78181 + pKey = &(pAd->SharedKey[BSS0][idx].Key[0]);
78182 + }
78183 + break;
78184 + case Ndis802_11Encryption2Enabled:
78185 + case Ndis802_11Encryption3Enabled:
78186 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled)
78187 + ext->alg = IW_ENCODE_ALG_TKIP;
78188 + else
78189 + ext->alg = IW_ENCODE_ALG_CCMP;
78190 +
78191 + if (max_key_len < 32)
78192 + return -E2BIG;
78193 + else
78194 + {
78195 + ext->key_len = 32;
78196 + pKey = &pAd->StaCfg.PMK[0];
78197 + }
78198 + break;
78199 + default:
78200 + return -EINVAL;
78201 + }
78202 +
78203 + if (ext->key_len && pKey)
78204 + {
78205 + encoding->flags |= IW_ENCODE_ENABLED;
78206 + memcpy(ext->key, pKey, ext->key_len);
78207 + }
78208 +
78209 + return 0;
78210 +}
78211 +
78212 +#ifdef SIOCSIWGENIE
78213 +int rt_ioctl_siwgenie(struct net_device *dev,
78214 + struct iw_request_info *info,
78215 + union iwreq_data *wrqu, char *extra)
78216 +{
78217 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
78218 +
78219 + if (wrqu->data.length > MAX_LEN_OF_RSNIE ||
78220 + (wrqu->data.length && extra == NULL))
78221 + return -EINVAL;
78222 +
78223 + if (wrqu->data.length)
78224 + {
78225 + pAd->StaCfg.RSNIE_Len = wrqu->data.length;
78226 + NdisMoveMemory(&pAd->StaCfg.RSN_IE[0], extra, pAd->StaCfg.RSNIE_Len);
78227 + }
78228 + else
78229 + {
78230 + pAd->StaCfg.RSNIE_Len = 0;
78231 + NdisZeroMemory(&pAd->StaCfg.RSN_IE[0], MAX_LEN_OF_RSNIE);
78232 + }
78233 +
78234 + return 0;
78235 +}
78236 +#endif // SIOCSIWGENIE //
78237 +
78238 +int rt_ioctl_giwgenie(struct net_device *dev,
78239 + struct iw_request_info *info,
78240 + union iwreq_data *wrqu, char *extra)
78241 +{
78242 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
78243 +
78244 + if ((pAd->StaCfg.RSNIE_Len == 0) ||
78245 + (pAd->StaCfg.AuthMode < Ndis802_11AuthModeWPA))
78246 + {
78247 + wrqu->data.length = 0;
78248 + return 0;
78249 + }
78250 +
78251 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
78252 +#ifdef SIOCSIWGENIE
78253 + if (pAd->StaCfg.WpaSupplicantUP == WPA_SUPPLICANT_ENABLE)
78254 + {
78255 + if (wrqu->data.length < pAd->StaCfg.RSNIE_Len)
78256 + return -E2BIG;
78257 +
78258 + wrqu->data.length = pAd->StaCfg.RSNIE_Len;
78259 + memcpy(extra, &pAd->StaCfg.RSN_IE[0], pAd->StaCfg.RSNIE_Len);
78260 + }
78261 + else
78262 +#endif // SIOCSIWGENIE //
78263 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
78264 + {
78265 + UCHAR RSNIe = IE_WPA;
78266 +
78267 + if (wrqu->data.length < (pAd->StaCfg.RSNIE_Len + 2)) // ID, Len
78268 + return -E2BIG;
78269 + wrqu->data.length = pAd->StaCfg.RSNIE_Len + 2;
78270 +
78271 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK) ||
78272 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2))
78273 + RSNIe = IE_RSN;
78274 +
78275 + extra[0] = (char)RSNIe;
78276 + extra[1] = pAd->StaCfg.RSNIE_Len;
78277 + memcpy(extra+2, &pAd->StaCfg.RSN_IE[0], pAd->StaCfg.RSNIE_Len);
78278 + }
78279 +
78280 + return 0;
78281 +}
78282 +
78283 +int rt_ioctl_siwpmksa(struct net_device *dev,
78284 + struct iw_request_info *info,
78285 + union iwreq_data *wrqu,
78286 + char *extra)
78287 +{
78288 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
78289 + struct iw_pmksa *pPmksa = (struct iw_pmksa *)wrqu->data.pointer;
78290 + INT CachedIdx = 0, idx = 0;
78291 +
78292 + if (pPmksa == NULL)
78293 + return -EINVAL;
78294 +
78295 + DBGPRINT(RT_DEBUG_TRACE ,("===> rt_ioctl_siwpmksa\n"));
78296 + switch(pPmksa->cmd)
78297 + {
78298 + case IW_PMKSA_FLUSH:
78299 + NdisZeroMemory(pAd->StaCfg.SavedPMK, sizeof(BSSID_INFO)*PMKID_NO);
78300 + DBGPRINT(RT_DEBUG_TRACE ,("rt_ioctl_siwpmksa - IW_PMKSA_FLUSH\n"));
78301 + break;
78302 + case IW_PMKSA_REMOVE:
78303 + for (CachedIdx = 0; CachedIdx < pAd->StaCfg.SavedPMKNum; CachedIdx++)
78304 + {
78305 + // compare the BSSID
78306 + if (NdisEqualMemory(pPmksa->bssid.sa_data, pAd->StaCfg.SavedPMK[CachedIdx].BSSID, MAC_ADDR_LEN))
78307 + {
78308 + NdisZeroMemory(pAd->StaCfg.SavedPMK[CachedIdx].BSSID, MAC_ADDR_LEN);
78309 + NdisZeroMemory(pAd->StaCfg.SavedPMK[CachedIdx].PMKID, 16);
78310 + for (idx = CachedIdx; idx < (pAd->StaCfg.SavedPMKNum - 1); idx++)
78311 + {
78312 + NdisMoveMemory(&pAd->StaCfg.SavedPMK[idx].BSSID[0], &pAd->StaCfg.SavedPMK[idx+1].BSSID[0], MAC_ADDR_LEN);
78313 + NdisMoveMemory(&pAd->StaCfg.SavedPMK[idx].PMKID[0], &pAd->StaCfg.SavedPMK[idx+1].PMKID[0], 16);
78314 + }
78315 + pAd->StaCfg.SavedPMKNum--;
78316 + break;
78317 + }
78318 + }
78319 +
78320 + DBGPRINT(RT_DEBUG_TRACE ,("rt_ioctl_siwpmksa - IW_PMKSA_REMOVE\n"));
78321 + break;
78322 + case IW_PMKSA_ADD:
78323 + for (CachedIdx = 0; CachedIdx < pAd->StaCfg.SavedPMKNum; CachedIdx++)
78324 + {
78325 + // compare the BSSID
78326 + if (NdisEqualMemory(pPmksa->bssid.sa_data, pAd->StaCfg.SavedPMK[CachedIdx].BSSID, MAC_ADDR_LEN))
78327 + break;
78328 + }
78329 +
78330 + // Found, replace it
78331 + if (CachedIdx < PMKID_NO)
78332 + {
78333 + DBGPRINT(RT_DEBUG_OFF, ("Update PMKID, idx = %d\n", CachedIdx));
78334 + NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].BSSID[0], pPmksa->bssid.sa_data, MAC_ADDR_LEN);
78335 + NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].PMKID[0], pPmksa->pmkid, 16);
78336 + pAd->StaCfg.SavedPMKNum++;
78337 + }
78338 + // Not found, replace the last one
78339 + else
78340 + {
78341 + // Randomly replace one
78342 + CachedIdx = (pPmksa->bssid.sa_data[5] % PMKID_NO);
78343 + DBGPRINT(RT_DEBUG_OFF, ("Update PMKID, idx = %d\n", CachedIdx));
78344 + NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].BSSID[0], pPmksa->bssid.sa_data, MAC_ADDR_LEN);
78345 + NdisMoveMemory(&pAd->StaCfg.SavedPMK[CachedIdx].PMKID[0], pPmksa->pmkid, 16);
78346 + }
78347 +
78348 + DBGPRINT(RT_DEBUG_TRACE ,("rt_ioctl_siwpmksa - IW_PMKSA_ADD\n"));
78349 + break;
78350 + default:
78351 + DBGPRINT(RT_DEBUG_TRACE ,("rt_ioctl_siwpmksa - Unknow Command!!\n"));
78352 + break;
78353 + }
78354 +
78355 + return 0;
78356 +}
78357 +#endif // #if WIRELESS_EXT > 17
78358 +
78359 +#ifdef DBG
78360 +static int
78361 +rt_private_ioctl_bbp(struct net_device *dev, struct iw_request_info *info,
78362 + struct iw_point *wrq, char *extra)
78363 + {
78364 + CHAR *this_char;
78365 + CHAR *value = NULL;
78366 + UCHAR regBBP = 0;
78367 + UINT32 bbpId;
78368 + UINT32 bbpValue;
78369 + BOOLEAN bIsPrintAllBBP = FALSE;
78370 + INT Status = 0;
78371 + PRTMP_ADAPTER pAdapter = (PRTMP_ADAPTER) dev->priv;
78372 +
78373 +
78374 + memset(extra, 0x00, IW_PRIV_SIZE_MASK);
78375 +
78376 + if (wrq->length > 1) //No parameters.
78377 + {
78378 + sprintf(extra, "\n");
78379 +
78380 + //Parsing Read or Write
78381 + this_char = wrq->pointer;
78382 + DBGPRINT(RT_DEBUG_TRACE, ("this_char=%s\n", this_char));
78383 + if (!*this_char)
78384 + goto next;
78385 +
78386 + if ((value = rtstrchr(this_char, '=')) != NULL)
78387 + *value++ = 0;
78388 +
78389 + if (!value || !*value)
78390 + { //Read
78391 + DBGPRINT(RT_DEBUG_TRACE, ("this_char=%s, value=%s\n", this_char, value));
78392 + if (sscanf(this_char, "%d", &(bbpId)) == 1)
78393 + {
78394 + if (bbpId <= 136)
78395 + {
78396 +#ifdef RALINK_ATE
78397 + if (ATE_ON(pAdapter))
78398 + {
78399 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, bbpId, &regBBP);
78400 + }
78401 + else
78402 +#endif // RALINK_ATE //
78403 + {
78404 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, bbpId, &regBBP);
78405 + }
78406 + sprintf(extra+strlen(extra), "R%02d[0x%02X]:%02X\n", bbpId, bbpId*2, regBBP);
78407 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
78408 + DBGPRINT(RT_DEBUG_TRACE, ("msg=%s\n", extra));
78409 + }
78410 + else
78411 + {//Invalid parametes, so default printk all bbp
78412 + bIsPrintAllBBP = TRUE;
78413 + goto next;
78414 + }
78415 + }
78416 + else
78417 + { //Invalid parametes, so default printk all bbp
78418 + bIsPrintAllBBP = TRUE;
78419 + goto next;
78420 + }
78421 + }
78422 + else
78423 + { //Write
78424 + if ((sscanf(this_char, "%d", &(bbpId)) == 1) && (sscanf(value, "%x", &(bbpValue)) == 1))
78425 + {
78426 + if (bbpId <= 136)
78427 + {
78428 +#ifdef RALINK_ATE
78429 + if (ATE_ON(pAdapter))
78430 + {
78431 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAdapter, bbpId, bbpValue);
78432 + //Read it back for showing
78433 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, bbpId, &regBBP);
78434 + }
78435 + else
78436 +#endif // RALINK_ATE //
78437 + {
78438 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, bbpId, bbpValue);
78439 + //Read it back for showing
78440 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, bbpId, &regBBP);
78441 + }
78442 + sprintf(extra+strlen(extra), "R%02d[0x%02X]:%02X\n", bbpId, bbpId*2, regBBP);
78443 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
78444 + DBGPRINT(RT_DEBUG_TRACE, ("msg=%s\n", extra));
78445 + }
78446 + else
78447 + {//Invalid parametes, so default printk all bbp
78448 + bIsPrintAllBBP = TRUE;
78449 + goto next;
78450 + }
78451 + }
78452 + else
78453 + { //Invalid parametes, so default printk all bbp
78454 + bIsPrintAllBBP = TRUE;
78455 + goto next;
78456 + }
78457 + }
78458 + }
78459 + else
78460 + bIsPrintAllBBP = TRUE;
78461 +
78462 +next:
78463 + if (bIsPrintAllBBP)
78464 + {
78465 + memset(extra, 0x00, IW_PRIV_SIZE_MASK);
78466 + sprintf(extra, "\n");
78467 + for (bbpId = 0; bbpId <= 136; bbpId++)
78468 + {
78469 + if (strlen(extra) >= (IW_PRIV_SIZE_MASK - 10))
78470 + break;
78471 +#ifdef RALINK_ATE
78472 + if (ATE_ON(pAdapter))
78473 + {
78474 + ATE_BBP_IO_READ8_BY_REG_ID(pAdapter, bbpId, &regBBP);
78475 + }
78476 + else
78477 +#endif // RALINK_ATE //
78478 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, bbpId, &regBBP);
78479 + sprintf(extra+strlen(extra), "R%02d[0x%02X]:%02X ", bbpId, bbpId*2, regBBP);
78480 + if (bbpId%5 == 4)
78481 + sprintf(extra+strlen(extra), "\n");
78482 + }
78483 +
78484 + wrq->length = strlen(extra) + 1; // 1: size of '\0'
78485 + DBGPRINT(RT_DEBUG_TRACE, ("wrq->length = %d\n", wrq->length));
78486 + }
78487 +
78488 + DBGPRINT(RT_DEBUG_TRACE, ("<==rt_private_ioctl_bbp\n\n"));
78489 +
78490 + return Status;
78491 +}
78492 +#endif // DBG //
78493 +
78494 +int rt_ioctl_siwrate(struct net_device *dev,
78495 + struct iw_request_info *info,
78496 + union iwreq_data *wrqu, char *extra)
78497 +{
78498 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
78499 + UINT32 rate = wrqu->bitrate.value, fixed = wrqu->bitrate.fixed;
78500 +
78501 + //check if the interface is down
78502 + if(!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE))
78503 + {
78504 + DBGPRINT(RT_DEBUG_TRACE, ("rt_ioctl_siwrate::Network is down!\n"));
78505 + return -ENETDOWN;
78506 + }
78507 +
78508 + DBGPRINT(RT_DEBUG_TRACE, ("rt_ioctl_siwrate::(rate = %d, fixed = %d)\n", rate, fixed));
78509 + /* rate = -1 => auto rate
78510 + rate = X, fixed = 1 => (fixed rate X)
78511 + */
78512 + if (rate == -1)
78513 + {
78514 + //Auto Rate
78515 + pAd->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
78516 + pAd->StaCfg.bAutoTxRateSwitch = TRUE;
78517 + if ((pAd->CommonCfg.PhyMode <= PHY_11G) ||
78518 + (pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE <= MODE_OFDM))
78519 + RTMPSetDesiredRates(pAd, -1);
78520 +
78521 +#ifdef DOT11_N_SUPPORT
78522 + SetCommonHT(pAd);
78523 +#endif // DOT11_N_SUPPORT //
78524 + }
78525 + else
78526 + {
78527 + if (fixed)
78528 + {
78529 + pAd->StaCfg.bAutoTxRateSwitch = FALSE;
78530 + if ((pAd->CommonCfg.PhyMode <= PHY_11G) ||
78531 + (pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE <= MODE_OFDM))
78532 + RTMPSetDesiredRates(pAd, rate);
78533 + else
78534 + {
78535 + pAd->StaCfg.DesiredTransmitSetting.field.MCS = MCS_AUTO;
78536 +#ifdef DOT11_N_SUPPORT
78537 + SetCommonHT(pAd);
78538 +#endif // DOT11_N_SUPPORT //
78539 + }
78540 + DBGPRINT(RT_DEBUG_TRACE, ("rt_ioctl_siwrate::(HtMcs=%d)\n",pAd->StaCfg.DesiredTransmitSetting.field.MCS));
78541 + }
78542 + else
78543 + {
78544 + // TODO: rate = X, fixed = 0 => (rates <= X)
78545 + return -EOPNOTSUPP;
78546 + }
78547 + }
78548 +
78549 + return 0;
78550 +}
78551 +
78552 +int rt_ioctl_giwrate(struct net_device *dev,
78553 + struct iw_request_info *info,
78554 + union iwreq_data *wrqu, char *extra)
78555 +{
78556 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) dev->priv;
78557 + int rate_index = 0, rate_count = 0;
78558 + HTTRANSMIT_SETTING ht_setting;
78559 + __s32 ralinkrate[] =
78560 + {2, 4, 11, 22, // CCK
78561 + 12, 18, 24, 36, 48, 72, 96, 108, // OFDM
78562 + 13, 26, 39, 52, 78, 104, 117, 130, 26, 52, 78, 104, 156, 208, 234, 260, // 20MHz, 800ns GI, MCS: 0 ~ 15
78563 + 39, 78, 117, 156, 234, 312, 351, 390, // 20MHz, 800ns GI, MCS: 16 ~ 23
78564 + 27, 54, 81, 108, 162, 216, 243, 270, 54, 108, 162, 216, 324, 432, 486, 540, // 40MHz, 800ns GI, MCS: 0 ~ 15
78565 + 81, 162, 243, 324, 486, 648, 729, 810, // 40MHz, 800ns GI, MCS: 16 ~ 23
78566 + 14, 29, 43, 57, 87, 115, 130, 144, 29, 59, 87, 115, 173, 230, 260, 288, // 20MHz, 400ns GI, MCS: 0 ~ 15
78567 + 43, 87, 130, 173, 260, 317, 390, 433, // 20MHz, 400ns GI, MCS: 16 ~ 23
78568 + 30, 60, 90, 120, 180, 240, 270, 300, 60, 120, 180, 240, 360, 480, 540, 600, // 40MHz, 400ns GI, MCS: 0 ~ 15
78569 + 90, 180, 270, 360, 540, 720, 810, 900}; // 40MHz, 400ns GI, MCS: 16 ~ 23
78570 +
78571 + rate_count = sizeof(ralinkrate)/sizeof(__s32);
78572 + //check if the interface is down
78573 + if(!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE))
78574 + {
78575 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
78576 + return -ENETDOWN;
78577 + }
78578 +
78579 + if ((pAd->StaCfg.bAutoTxRateSwitch == FALSE) &&
78580 + (INFRA_ON(pAd)) &&
78581 + ((pAd->CommonCfg.PhyMode <= PHY_11G) || (pAd->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE <= MODE_OFDM)))
78582 + ht_setting.word = pAd->StaCfg.HTPhyMode.word;
78583 + else
78584 + ht_setting.word = pAd->MacTab.Content[BSSID_WCID].HTPhyMode.word;
78585 +
78586 +#ifdef DOT11_N_SUPPORT
78587 + if (ht_setting.field.MODE >= MODE_HTMIX)
78588 + {
78589 + rate_index = 12 + ((UCHAR)ht_setting.field.BW *24) + ((UCHAR)ht_setting.field.ShortGI *48) + ((UCHAR)ht_setting.field.MCS);
78590 + }
78591 + else
78592 +#endif // DOT11_N_SUPPORT //
78593 + if (ht_setting.field.MODE == MODE_OFDM)
78594 + rate_index = (UCHAR)(ht_setting.field.MCS) + 4;
78595 + else if (ht_setting.field.MODE == MODE_CCK)
78596 + rate_index = (UCHAR)(ht_setting.field.MCS);
78597 +
78598 + if (rate_index < 0)
78599 + rate_index = 0;
78600 +
78601 + if (rate_index > rate_count)
78602 + rate_index = rate_count;
78603 +
78604 + wrqu->bitrate.value = ralinkrate[rate_index] * 500000;
78605 + wrqu->bitrate.disabled = 0;
78606 +
78607 + return 0;
78608 +}
78609 +
78610 +static const iw_handler rt_handler[] =
78611 +{
78612 + (iw_handler) NULL, /* SIOCSIWCOMMIT */
78613 + (iw_handler) rt_ioctl_giwname, /* SIOCGIWNAME */
78614 + (iw_handler) NULL, /* SIOCSIWNWID */
78615 + (iw_handler) NULL, /* SIOCGIWNWID */
78616 + (iw_handler) rt_ioctl_siwfreq, /* SIOCSIWFREQ */
78617 + (iw_handler) rt_ioctl_giwfreq, /* SIOCGIWFREQ */
78618 + (iw_handler) rt_ioctl_siwmode, /* SIOCSIWMODE */
78619 + (iw_handler) rt_ioctl_giwmode, /* SIOCGIWMODE */
78620 + (iw_handler) NULL, /* SIOCSIWSENS */
78621 + (iw_handler) NULL, /* SIOCGIWSENS */
78622 + (iw_handler) NULL /* not used */, /* SIOCSIWRANGE */
78623 + (iw_handler) rt_ioctl_giwrange, /* SIOCGIWRANGE */
78624 + (iw_handler) NULL /* not used */, /* SIOCSIWPRIV */
78625 + (iw_handler) NULL /* kernel code */, /* SIOCGIWPRIV */
78626 + (iw_handler) NULL /* not used */, /* SIOCSIWSTATS */
78627 + (iw_handler) rt28xx_get_wireless_stats /* kernel code */, /* SIOCGIWSTATS */
78628 + (iw_handler) NULL, /* SIOCSIWSPY */
78629 + (iw_handler) NULL, /* SIOCGIWSPY */
78630 + (iw_handler) NULL, /* SIOCSIWTHRSPY */
78631 + (iw_handler) NULL, /* SIOCGIWTHRSPY */
78632 + (iw_handler) rt_ioctl_siwap, /* SIOCSIWAP */
78633 + (iw_handler) rt_ioctl_giwap, /* SIOCGIWAP */
78634 +#ifdef SIOCSIWMLME
78635 + (iw_handler) rt_ioctl_siwmlme, /* SIOCSIWMLME */
78636 +#else
78637 + (iw_handler) NULL, /* SIOCSIWMLME */
78638 +#endif // SIOCSIWMLME //
78639 + (iw_handler) rt_ioctl_iwaplist, /* SIOCGIWAPLIST */
78640 +#ifdef SIOCGIWSCAN
78641 + (iw_handler) rt_ioctl_siwscan, /* SIOCSIWSCAN */
78642 + (iw_handler) rt_ioctl_giwscan, /* SIOCGIWSCAN */
78643 +#else
78644 + (iw_handler) NULL, /* SIOCSIWSCAN */
78645 + (iw_handler) NULL, /* SIOCGIWSCAN */
78646 +#endif /* SIOCGIWSCAN */
78647 + (iw_handler) rt_ioctl_siwessid, /* SIOCSIWESSID */
78648 + (iw_handler) rt_ioctl_giwessid, /* SIOCGIWESSID */
78649 + (iw_handler) rt_ioctl_siwnickn, /* SIOCSIWNICKN */
78650 + (iw_handler) rt_ioctl_giwnickn, /* SIOCGIWNICKN */
78651 + (iw_handler) NULL, /* -- hole -- */
78652 + (iw_handler) NULL, /* -- hole -- */
78653 + (iw_handler) rt_ioctl_siwrate, /* SIOCSIWRATE */
78654 + (iw_handler) rt_ioctl_giwrate, /* SIOCGIWRATE */
78655 + (iw_handler) rt_ioctl_siwrts, /* SIOCSIWRTS */
78656 + (iw_handler) rt_ioctl_giwrts, /* SIOCGIWRTS */
78657 + (iw_handler) rt_ioctl_siwfrag, /* SIOCSIWFRAG */
78658 + (iw_handler) rt_ioctl_giwfrag, /* SIOCGIWFRAG */
78659 + (iw_handler) NULL, /* SIOCSIWTXPOW */
78660 + (iw_handler) NULL, /* SIOCGIWTXPOW */
78661 + (iw_handler) NULL, /* SIOCSIWRETRY */
78662 + (iw_handler) NULL, /* SIOCGIWRETRY */
78663 + (iw_handler) rt_ioctl_siwencode, /* SIOCSIWENCODE */
78664 + (iw_handler) rt_ioctl_giwencode, /* SIOCGIWENCODE */
78665 + (iw_handler) NULL, /* SIOCSIWPOWER */
78666 + (iw_handler) NULL, /* SIOCGIWPOWER */
78667 + (iw_handler) NULL, /* -- hole -- */
78668 + (iw_handler) NULL, /* -- hole -- */
78669 +#if WIRELESS_EXT > 17
78670 + (iw_handler) rt_ioctl_siwgenie, /* SIOCSIWGENIE */
78671 + (iw_handler) rt_ioctl_giwgenie, /* SIOCGIWGENIE */
78672 + (iw_handler) rt_ioctl_siwauth, /* SIOCSIWAUTH */
78673 + (iw_handler) rt_ioctl_giwauth, /* SIOCGIWAUTH */
78674 + (iw_handler) rt_ioctl_siwencodeext, /* SIOCSIWENCODEEXT */
78675 + (iw_handler) rt_ioctl_giwencodeext, /* SIOCGIWENCODEEXT */
78676 + (iw_handler) rt_ioctl_siwpmksa, /* SIOCSIWPMKSA */
78677 +#endif
78678 +};
78679 +
78680 +static const iw_handler rt_priv_handlers[] = {
78681 + (iw_handler) NULL, /* + 0x00 */
78682 + (iw_handler) NULL, /* + 0x01 */
78683 +#ifndef CONFIG_AP_SUPPORT
78684 + (iw_handler) rt_ioctl_setparam, /* + 0x02 */
78685 +#else
78686 + (iw_handler) NULL, /* + 0x02 */
78687 +#endif // CONFIG_AP_SUPPORT //
78688 +#ifdef DBG
78689 + (iw_handler) rt_private_ioctl_bbp, /* + 0x03 */
78690 +#else
78691 + (iw_handler) NULL, /* + 0x03 */
78692 +#endif
78693 + (iw_handler) NULL, /* + 0x04 */
78694 + (iw_handler) NULL, /* + 0x05 */
78695 + (iw_handler) NULL, /* + 0x06 */
78696 + (iw_handler) NULL, /* + 0x07 */
78697 + (iw_handler) NULL, /* + 0x08 */
78698 + (iw_handler) rt_private_get_statistics, /* + 0x09 */
78699 + (iw_handler) NULL, /* + 0x0A */
78700 + (iw_handler) NULL, /* + 0x0B */
78701 + (iw_handler) NULL, /* + 0x0C */
78702 + (iw_handler) NULL, /* + 0x0D */
78703 + (iw_handler) NULL, /* + 0x0E */
78704 + (iw_handler) NULL, /* + 0x0F */
78705 + (iw_handler) NULL, /* + 0x10 */
78706 + (iw_handler) rt_private_show, /* + 0x11 */
78707 + (iw_handler) NULL, /* + 0x12 */
78708 + (iw_handler) NULL, /* + 0x13 */
78709 + (iw_handler) NULL, /* + 0x15 */
78710 + (iw_handler) NULL, /* + 0x17 */
78711 + (iw_handler) NULL, /* + 0x18 */
78712 +};
78713 +
78714 +const struct iw_handler_def rt28xx_iw_handler_def =
78715 +{
78716 +#define N(a) (sizeof (a) / sizeof (a[0]))
78717 + .standard = (iw_handler *) rt_handler,
78718 + .num_standard = sizeof(rt_handler) / sizeof(iw_handler),
78719 + .private = (iw_handler *) rt_priv_handlers,
78720 + .num_private = N(rt_priv_handlers),
78721 + .private_args = (struct iw_priv_args *) privtab,
78722 + .num_private_args = N(privtab),
78723 +#if IW_HANDLER_VERSION >= 7
78724 + .get_wireless_stats = rt28xx_get_wireless_stats,
78725 +#endif
78726 +};
78727 +
78728 +INT RTMPSetInformation(
78729 + IN PRTMP_ADAPTER pAdapter,
78730 + IN OUT struct ifreq *rq,
78731 + IN INT cmd)
78732 +{
78733 + struct iwreq *wrq = (struct iwreq *) rq;
78734 + NDIS_802_11_SSID Ssid;
78735 + NDIS_802_11_MAC_ADDRESS Bssid;
78736 + RT_802_11_PHY_MODE PhyMode;
78737 + RT_802_11_STA_CONFIG StaConfig;
78738 + NDIS_802_11_RATES aryRates;
78739 + RT_802_11_PREAMBLE Preamble;
78740 + NDIS_802_11_WEP_STATUS WepStatus;
78741 + NDIS_802_11_AUTHENTICATION_MODE AuthMode = Ndis802_11AuthModeMax;
78742 + NDIS_802_11_NETWORK_INFRASTRUCTURE BssType;
78743 + NDIS_802_11_RTS_THRESHOLD RtsThresh;
78744 + NDIS_802_11_FRAGMENTATION_THRESHOLD FragThresh;
78745 + NDIS_802_11_POWER_MODE PowerMode;
78746 + PNDIS_802_11_KEY pKey = NULL;
78747 + PNDIS_802_11_WEP pWepKey =NULL;
78748 + PNDIS_802_11_REMOVE_KEY pRemoveKey = NULL;
78749 + NDIS_802_11_CONFIGURATION Config, *pConfig = NULL;
78750 + NDIS_802_11_NETWORK_TYPE NetType;
78751 + ULONG Now;
78752 + UINT KeyIdx = 0;
78753 + INT Status = NDIS_STATUS_SUCCESS, MaxPhyMode = PHY_11G;
78754 + ULONG PowerTemp;
78755 + BOOLEAN RadioState;
78756 + BOOLEAN StateMachineTouched = FALSE;
78757 +#ifdef DOT11_N_SUPPORT
78758 + OID_SET_HT_PHYMODE HT_PhyMode; //11n ,kathy
78759 +#endif // DOT11_N_SUPPORT //
78760 +#ifdef WPA_SUPPLICANT_SUPPORT
78761 + PNDIS_802_11_PMKID pPmkId = NULL;
78762 + BOOLEAN IEEE8021xState = FALSE;
78763 + BOOLEAN IEEE8021x_required_keys = FALSE;
78764 + UCHAR wpa_supplicant_enable = 0;
78765 +#endif // WPA_SUPPLICANT_SUPPORT //
78766 +
78767 +#ifdef SNMP_SUPPORT
78768 + TX_RTY_CFG_STRUC tx_rty_cfg;
78769 + ULONG ShortRetryLimit, LongRetryLimit;
78770 + UCHAR ctmp;
78771 +#endif // SNMP_SUPPORT //
78772 +
78773 +
78774 +#ifdef DOT11_N_SUPPORT
78775 + MaxPhyMode = PHY_11N_5G;
78776 +#endif // DOT11_N_SUPPORT //
78777 +
78778 +
78779 + DBGPRINT(RT_DEBUG_TRACE, ("-->RTMPSetInformation(), 0x%08x\n", cmd&0x7FFF));
78780 + switch(cmd & 0x7FFF) {
78781 + case RT_OID_802_11_COUNTRY_REGION:
78782 + if (wrq->u.data.length < sizeof(UCHAR))
78783 + Status = -EINVAL;
78784 + // Only avaliable when EEPROM not programming
78785 + else if (!(pAdapter->CommonCfg.CountryRegion & 0x80) && !(pAdapter->CommonCfg.CountryRegionForABand & 0x80))
78786 + {
78787 + ULONG Country;
78788 + UCHAR TmpPhy;
78789 +
78790 + Status = copy_from_user(&Country, wrq->u.data.pointer, wrq->u.data.length);
78791 + pAdapter->CommonCfg.CountryRegion = (UCHAR)(Country & 0x000000FF);
78792 + pAdapter->CommonCfg.CountryRegionForABand = (UCHAR)((Country >> 8) & 0x000000FF);
78793 + TmpPhy = pAdapter->CommonCfg.PhyMode;
78794 + pAdapter->CommonCfg.PhyMode = 0xff;
78795 + // Build all corresponding channel information
78796 + RTMPSetPhyMode(pAdapter, TmpPhy);
78797 +#ifdef DOT11_N_SUPPORT
78798 + SetCommonHT(pAdapter);
78799 +#endif // DOT11_N_SUPPORT //
78800 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_COUNTRY_REGION (A:%d B/G:%d)\n", pAdapter->CommonCfg.CountryRegionForABand,
78801 + pAdapter->CommonCfg.CountryRegion));
78802 + }
78803 + break;
78804 + case OID_802_11_BSSID_LIST_SCAN:
78805 + #ifdef RALINK_ATE
78806 + if (ATE_ON(pAdapter))
78807 + {
78808 + DBGPRINT(RT_DEBUG_TRACE, ("The driver is in ATE mode now\n"));
78809 + break;
78810 + }
78811 +#endif // RALINK_ATE //
78812 + Now = jiffies;
78813 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_BSSID_LIST_SCAN, TxCnt = %d \n", pAdapter->RalinkCounters.LastOneSecTotalTxCount));
78814 +
78815 + if (MONITOR_ON(pAdapter))
78816 + {
78817 + DBGPRINT(RT_DEBUG_TRACE, ("!!! Driver is in Monitor Mode now !!!\n"));
78818 + break;
78819 + }
78820 +
78821 + //Benson add 20080527, when radio off, sta don't need to scan
78822 + if (RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_RADIO_OFF))
78823 + break;
78824 +
78825 + if (RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
78826 + {
78827 + DBGPRINT(RT_DEBUG_TRACE, ("!!! Driver is scanning now !!!\n"));
78828 + pAdapter->StaCfg.bScanReqIsFromWebUI = TRUE;
78829 + Status = NDIS_STATUS_SUCCESS;
78830 + break;
78831 + }
78832 +
78833 + if (pAdapter->RalinkCounters.LastOneSecTotalTxCount > 100)
78834 + {
78835 + DBGPRINT(RT_DEBUG_TRACE, ("!!! Link UP, ignore this set::OID_802_11_BSSID_LIST_SCAN\n"));
78836 + Status = NDIS_STATUS_SUCCESS;
78837 + pAdapter->StaCfg.ScanCnt = 99; // Prevent auto scan triggered by this OID
78838 + break;
78839 + }
78840 +
78841 + if ((OPSTATUS_TEST_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED)) &&
78842 + ((pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPA) ||
78843 + (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) ||
78844 + (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) ||
78845 + (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)) &&
78846 + (pAdapter->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED))
78847 + {
78848 + DBGPRINT(RT_DEBUG_TRACE, ("!!! Link UP, Port Not Secured! ignore this set::OID_802_11_BSSID_LIST_SCAN\n"));
78849 + Status = NDIS_STATUS_SUCCESS;
78850 + pAdapter->StaCfg.ScanCnt = 99; // Prevent auto scan triggered by this OID
78851 + break;
78852 + }
78853 +
78854 +
78855 + if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE)
78856 + {
78857 + RT28XX_MLME_RESET_STATE_MACHINE(pAdapter);
78858 + DBGPRINT(RT_DEBUG_TRACE, ("!!! MLME busy, reset MLME state machine !!!\n"));
78859 + }
78860 +
78861 + // tell CNTL state machine to call NdisMSetInformationComplete() after completing
78862 + // this request, because this request is initiated by NDIS.
78863 + pAdapter->MlmeAux.CurrReqIsFromNdis = FALSE;
78864 + // Reset allowed scan retries
78865 + pAdapter->StaCfg.ScanCnt = 0;
78866 + pAdapter->StaCfg.LastScanTime = Now;
78867 +
78868 + pAdapter->StaCfg.bScanReqIsFromWebUI = TRUE;
78869 + RTMP_SET_FLAG(pAdapter, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS);
78870 + MlmeEnqueue(pAdapter,
78871 + MLME_CNTL_STATE_MACHINE,
78872 + OID_802_11_BSSID_LIST_SCAN,
78873 + 0,
78874 + NULL);
78875 +
78876 + Status = NDIS_STATUS_SUCCESS;
78877 + StateMachineTouched = TRUE;
78878 + break;
78879 + case OID_802_11_SSID:
78880 + if (wrq->u.data.length != sizeof(NDIS_802_11_SSID))
78881 + Status = -EINVAL;
78882 + else
78883 + {
78884 + PCHAR pSsidString = NULL;
78885 + Status = copy_from_user(&Ssid, wrq->u.data.pointer, wrq->u.data.length);
78886 +
78887 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_SSID (Len=%d,Ssid=%s)\n", Ssid.SsidLength, Ssid.Ssid));
78888 + if (Ssid.SsidLength > MAX_LEN_OF_SSID)
78889 + Status = -EINVAL;
78890 + else
78891 + {
78892 + if (Ssid.SsidLength == 0)
78893 + {
78894 + Set_SSID_Proc(pAdapter, "");
78895 + }
78896 + else
78897 + {
78898 + pSsidString = (CHAR *) kmalloc(MAX_LEN_OF_SSID+1, MEM_ALLOC_FLAG);
78899 + if (pSsidString)
78900 + {
78901 + NdisZeroMemory(pSsidString, MAX_LEN_OF_SSID+1);
78902 + NdisMoveMemory(pSsidString, Ssid.Ssid, Ssid.SsidLength);
78903 + Set_SSID_Proc(pAdapter, pSsidString);
78904 + kfree(pSsidString);
78905 + }
78906 + else
78907 + Status = -ENOMEM;
78908 + }
78909 + }
78910 + }
78911 + break;
78912 + case OID_802_11_BSSID:
78913 +#ifdef RALINK_ATE
78914 + if (ATE_ON(pAdapter))
78915 + {
78916 + DBGPRINT(RT_DEBUG_TRACE, ("The driver is in ATE mode now\n"));
78917 + break;
78918 + }
78919 +#endif // RALINK_ATE //
78920 + if (wrq->u.data.length != sizeof(NDIS_802_11_MAC_ADDRESS))
78921 + Status = -EINVAL;
78922 + else
78923 + {
78924 + Status = copy_from_user(&Bssid, wrq->u.data.pointer, wrq->u.data.length);
78925 +
78926 + // tell CNTL state machine to call NdisMSetInformationComplete() after completing
78927 + // this request, because this request is initiated by NDIS.
78928 + pAdapter->MlmeAux.CurrReqIsFromNdis = FALSE;
78929 +
78930 + // Prevent to connect AP again in STAMlmePeriodicExec
78931 + pAdapter->MlmeAux.AutoReconnectSsidLen= 32;
78932 +
78933 + // Reset allowed scan retries
78934 + pAdapter->StaCfg.ScanCnt = 0;
78935 +
78936 + if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE)
78937 + {
78938 + RT28XX_MLME_RESET_STATE_MACHINE(pAdapter);
78939 + DBGPRINT(RT_DEBUG_TRACE, ("!!! MLME busy, reset MLME state machine !!!\n"));
78940 + }
78941 + MlmeEnqueue(pAdapter,
78942 + MLME_CNTL_STATE_MACHINE,
78943 + OID_802_11_BSSID,
78944 + sizeof(NDIS_802_11_MAC_ADDRESS),
78945 + (VOID *)&Bssid);
78946 + Status = NDIS_STATUS_SUCCESS;
78947 + StateMachineTouched = TRUE;
78948 +
78949 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_BSSID %02x:%02x:%02x:%02x:%02x:%02x\n",
78950 + Bssid[0], Bssid[1], Bssid[2], Bssid[3], Bssid[4], Bssid[5]));
78951 + }
78952 + break;
78953 + case RT_OID_802_11_RADIO:
78954 + if (wrq->u.data.length != sizeof(BOOLEAN))
78955 + Status = -EINVAL;
78956 + else
78957 + {
78958 + Status = copy_from_user(&RadioState, wrq->u.data.pointer, wrq->u.data.length);
78959 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_RADIO (=%d)\n", RadioState));
78960 + if (pAdapter->StaCfg.bSwRadio != RadioState)
78961 + {
78962 + pAdapter->StaCfg.bSwRadio = RadioState;
78963 + if (pAdapter->StaCfg.bRadio != (pAdapter->StaCfg.bHwRadio && pAdapter->StaCfg.bSwRadio))
78964 + {
78965 + pAdapter->StaCfg.bRadio = (pAdapter->StaCfg.bHwRadio && pAdapter->StaCfg.bSwRadio);
78966 + if (pAdapter->StaCfg.bRadio == TRUE)
78967 + {
78968 + MlmeRadioOn(pAdapter);
78969 + // Update extra information
78970 + pAdapter->ExtraInfo = EXTRA_INFO_CLEAR;
78971 + }
78972 + else
78973 + {
78974 + MlmeRadioOff(pAdapter);
78975 + // Update extra information
78976 + pAdapter->ExtraInfo = SW_RADIO_OFF;
78977 + }
78978 + }
78979 + }
78980 + }
78981 + break;
78982 + case RT_OID_802_11_PHY_MODE:
78983 + if (wrq->u.data.length != sizeof(RT_802_11_PHY_MODE))
78984 + Status = -EINVAL;
78985 + else
78986 + {
78987 + Status = copy_from_user(&PhyMode, wrq->u.data.pointer, wrq->u.data.length);
78988 + if (PhyMode <= MaxPhyMode)
78989 + {
78990 + RTMPSetPhyMode(pAdapter, PhyMode);
78991 +#ifdef DOT11_N_SUPPORT
78992 + SetCommonHT(pAdapter);
78993 +#endif // DOT11_N_SUPPORT //
78994 + }
78995 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_PHY_MODE (=%d)\n", PhyMode));
78996 + }
78997 + break;
78998 + case RT_OID_802_11_STA_CONFIG:
78999 + if (wrq->u.data.length != sizeof(RT_802_11_STA_CONFIG))
79000 + Status = -EINVAL;
79001 + else
79002 + {
79003 + Status = copy_from_user(&StaConfig, wrq->u.data.pointer, wrq->u.data.length);
79004 + pAdapter->CommonCfg.bEnableTxBurst = StaConfig.EnableTxBurst;
79005 + pAdapter->CommonCfg.UseBGProtection = StaConfig.UseBGProtection;
79006 + pAdapter->CommonCfg.bUseShortSlotTime = 1; // 2003-10-30 always SHORT SLOT capable
79007 + if ((pAdapter->CommonCfg.PhyMode != StaConfig.AdhocMode) &&
79008 + (StaConfig.AdhocMode <= MaxPhyMode))
79009 + {
79010 + // allow dynamic change of "USE OFDM rate or not" in ADHOC mode
79011 + // if setting changed, need to reset current TX rate as well as BEACON frame format
79012 + if (pAdapter->StaCfg.BssType == BSS_ADHOC)
79013 + {
79014 + pAdapter->CommonCfg.PhyMode = StaConfig.AdhocMode;
79015 + RTMPSetPhyMode(pAdapter, PhyMode);
79016 + MlmeUpdateTxRates(pAdapter, FALSE, 0);
79017 + MakeIbssBeacon(pAdapter); // re-build BEACON frame
79018 + AsicEnableIbssSync(pAdapter); // copy to on-chip memory
79019 + }
79020 + }
79021 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_SET_STA_CONFIG (Burst=%d, Protection=%ld,ShortSlot=%d\n",
79022 + pAdapter->CommonCfg.bEnableTxBurst,
79023 + pAdapter->CommonCfg.UseBGProtection,
79024 + pAdapter->CommonCfg.bUseShortSlotTime));
79025 + }
79026 + break;
79027 + case OID_802_11_DESIRED_RATES:
79028 + if (wrq->u.data.length != sizeof(NDIS_802_11_RATES))
79029 + Status = -EINVAL;
79030 + else
79031 + {
79032 + Status = copy_from_user(&aryRates, wrq->u.data.pointer, wrq->u.data.length);
79033 + NdisZeroMemory(pAdapter->CommonCfg.DesireRate, MAX_LEN_OF_SUPPORTED_RATES);
79034 + NdisMoveMemory(pAdapter->CommonCfg.DesireRate, &aryRates, sizeof(NDIS_802_11_RATES));
79035 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_DESIRED_RATES (%02x,%02x,%02x,%02x,%02x,%02x,%02x,%02x)\n",
79036 + pAdapter->CommonCfg.DesireRate[0],pAdapter->CommonCfg.DesireRate[1],
79037 + pAdapter->CommonCfg.DesireRate[2],pAdapter->CommonCfg.DesireRate[3],
79038 + pAdapter->CommonCfg.DesireRate[4],pAdapter->CommonCfg.DesireRate[5],
79039 + pAdapter->CommonCfg.DesireRate[6],pAdapter->CommonCfg.DesireRate[7] ));
79040 + // Changing DesiredRate may affect the MAX TX rate we used to TX frames out
79041 + MlmeUpdateTxRates(pAdapter, FALSE, 0);
79042 + }
79043 + break;
79044 + case RT_OID_802_11_PREAMBLE:
79045 + if (wrq->u.data.length != sizeof(RT_802_11_PREAMBLE))
79046 + Status = -EINVAL;
79047 + else
79048 + {
79049 + Status = copy_from_user(&Preamble, wrq->u.data.pointer, wrq->u.data.length);
79050 + if (Preamble == Rt802_11PreambleShort)
79051 + {
79052 + pAdapter->CommonCfg.TxPreamble = Preamble;
79053 + MlmeSetTxPreamble(pAdapter, Rt802_11PreambleShort);
79054 + }
79055 + else if ((Preamble == Rt802_11PreambleLong) || (Preamble == Rt802_11PreambleAuto))
79056 + {
79057 + // if user wants AUTO, initialize to LONG here, then change according to AP's
79058 + // capability upon association.
79059 + pAdapter->CommonCfg.TxPreamble = Preamble;
79060 + MlmeSetTxPreamble(pAdapter, Rt802_11PreambleLong);
79061 + }
79062 + else
79063 + {
79064 + Status = -EINVAL;
79065 + break;
79066 + }
79067 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_PREAMBLE (=%d)\n", Preamble));
79068 + }
79069 + break;
79070 + case OID_802_11_WEP_STATUS:
79071 + if (wrq->u.data.length != sizeof(NDIS_802_11_WEP_STATUS))
79072 + Status = -EINVAL;
79073 + else
79074 + {
79075 + Status = copy_from_user(&WepStatus, wrq->u.data.pointer, wrq->u.data.length);
79076 + // Since TKIP, AES, WEP are all supported. It should not have any invalid setting
79077 + if (WepStatus <= Ndis802_11Encryption3KeyAbsent)
79078 + {
79079 + if (pAdapter->StaCfg.WepStatus != WepStatus)
79080 + {
79081 + // Config has changed
79082 + pAdapter->bConfigChanged = TRUE;
79083 + }
79084 + pAdapter->StaCfg.WepStatus = WepStatus;
79085 + pAdapter->StaCfg.OrigWepStatus = WepStatus;
79086 + pAdapter->StaCfg.PairCipher = WepStatus;
79087 + pAdapter->StaCfg.GroupCipher = WepStatus;
79088 + }
79089 + else
79090 + {
79091 + Status = -EINVAL;
79092 + break;
79093 + }
79094 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_WEP_STATUS (=%d)\n",WepStatus));
79095 + }
79096 + break;
79097 + case OID_802_11_AUTHENTICATION_MODE:
79098 + if (wrq->u.data.length != sizeof(NDIS_802_11_AUTHENTICATION_MODE))
79099 + Status = -EINVAL;
79100 + else
79101 + {
79102 + Status = copy_from_user(&AuthMode, wrq->u.data.pointer, wrq->u.data.length);
79103 + if (AuthMode > Ndis802_11AuthModeMax)
79104 + {
79105 + Status = -EINVAL;
79106 + break;
79107 + }
79108 + else
79109 + {
79110 + if (pAdapter->StaCfg.AuthMode != AuthMode)
79111 + {
79112 + // Config has changed
79113 + pAdapter->bConfigChanged = TRUE;
79114 + }
79115 + pAdapter->StaCfg.AuthMode = AuthMode;
79116 + }
79117 + pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
79118 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_AUTHENTICATION_MODE (=%d) \n",pAdapter->StaCfg.AuthMode));
79119 + }
79120 + break;
79121 + case OID_802_11_INFRASTRUCTURE_MODE:
79122 + if (wrq->u.data.length != sizeof(NDIS_802_11_NETWORK_INFRASTRUCTURE))
79123 + Status = -EINVAL;
79124 + else
79125 + {
79126 + Status = copy_from_user(&BssType, wrq->u.data.pointer, wrq->u.data.length);
79127 +
79128 + if (BssType == Ndis802_11IBSS)
79129 + Set_NetworkType_Proc(pAdapter, "Adhoc");
79130 + else if (BssType == Ndis802_11Infrastructure)
79131 + Set_NetworkType_Proc(pAdapter, "Infra");
79132 + else if (BssType == Ndis802_11Monitor)
79133 + Set_NetworkType_Proc(pAdapter, "Monitor");
79134 + else
79135 + {
79136 + Status = -EINVAL;
79137 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_INFRASTRUCTURE_MODE (unknown)\n"));
79138 + }
79139 + }
79140 + break;
79141 + case OID_802_11_REMOVE_WEP:
79142 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_REMOVE_WEP\n"));
79143 + if (wrq->u.data.length != sizeof(NDIS_802_11_KEY_INDEX))
79144 + {
79145 + Status = -EINVAL;
79146 + }
79147 + else
79148 + {
79149 + KeyIdx = *(NDIS_802_11_KEY_INDEX *) wrq->u.data.pointer;
79150 +
79151 + if (KeyIdx & 0x80000000)
79152 + {
79153 + // Should never set default bit when remove key
79154 + Status = -EINVAL;
79155 + }
79156 + else
79157 + {
79158 + KeyIdx = KeyIdx & 0x0fffffff;
79159 + if (KeyIdx >= 4){
79160 + Status = -EINVAL;
79161 + }
79162 + else
79163 + {
79164 + pAdapter->SharedKey[BSS0][KeyIdx].KeyLen = 0;
79165 + pAdapter->SharedKey[BSS0][KeyIdx].CipherAlg = CIPHER_NONE;
79166 + AsicRemoveSharedKeyEntry(pAdapter, 0, (UCHAR)KeyIdx);
79167 + }
79168 + }
79169 + }
79170 + break;
79171 + case RT_OID_802_11_RESET_COUNTERS:
79172 + NdisZeroMemory(&pAdapter->WlanCounters, sizeof(COUNTER_802_11));
79173 + NdisZeroMemory(&pAdapter->Counters8023, sizeof(COUNTER_802_3));
79174 + NdisZeroMemory(&pAdapter->RalinkCounters, sizeof(COUNTER_RALINK));
79175 + pAdapter->Counters8023.RxNoBuffer = 0;
79176 + pAdapter->Counters8023.GoodReceives = 0;
79177 + pAdapter->Counters8023.RxNoBuffer = 0;
79178 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_RESET_COUNTERS \n"));
79179 + break;
79180 + case OID_802_11_RTS_THRESHOLD:
79181 + if (wrq->u.data.length != sizeof(NDIS_802_11_RTS_THRESHOLD))
79182 + Status = -EINVAL;
79183 + else
79184 + {
79185 + Status = copy_from_user(&RtsThresh, wrq->u.data.pointer, wrq->u.data.length);
79186 + if (RtsThresh > MAX_RTS_THRESHOLD)
79187 + Status = -EINVAL;
79188 + else
79189 + pAdapter->CommonCfg.RtsThreshold = (USHORT)RtsThresh;
79190 + }
79191 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_RTS_THRESHOLD (=%ld)\n",RtsThresh));
79192 + break;
79193 + case OID_802_11_FRAGMENTATION_THRESHOLD:
79194 + if (wrq->u.data.length != sizeof(NDIS_802_11_FRAGMENTATION_THRESHOLD))
79195 + Status = -EINVAL;
79196 + else
79197 + {
79198 + Status = copy_from_user(&FragThresh, wrq->u.data.pointer, wrq->u.data.length);
79199 + pAdapter->CommonCfg.bUseZeroToDisableFragment = FALSE;
79200 + if (FragThresh > MAX_FRAG_THRESHOLD || FragThresh < MIN_FRAG_THRESHOLD)
79201 + {
79202 + if (FragThresh == 0)
79203 + {
79204 + pAdapter->CommonCfg.FragmentThreshold = MAX_FRAG_THRESHOLD;
79205 + pAdapter->CommonCfg.bUseZeroToDisableFragment = TRUE;
79206 + }
79207 + else
79208 + Status = -EINVAL;
79209 + }
79210 + else
79211 + pAdapter->CommonCfg.FragmentThreshold = (USHORT)FragThresh;
79212 + }
79213 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_FRAGMENTATION_THRESHOLD (=%ld) \n",FragThresh));
79214 + break;
79215 + case OID_802_11_POWER_MODE:
79216 + if (wrq->u.data.length != sizeof(NDIS_802_11_POWER_MODE))
79217 + Status = -EINVAL;
79218 + else
79219 + {
79220 + Status = copy_from_user(&PowerMode, wrq->u.data.pointer, wrq->u.data.length);
79221 + if (PowerMode == Ndis802_11PowerModeCAM)
79222 + Set_PSMode_Proc(pAdapter, "CAM");
79223 + else if (PowerMode == Ndis802_11PowerModeMAX_PSP)
79224 + Set_PSMode_Proc(pAdapter, "Max_PSP");
79225 + else if (PowerMode == Ndis802_11PowerModeFast_PSP)
79226 + Set_PSMode_Proc(pAdapter, "Fast_PSP");
79227 + else if (PowerMode == Ndis802_11PowerModeLegacy_PSP)
79228 + Set_PSMode_Proc(pAdapter, "Legacy_PSP");
79229 + else
79230 + Status = -EINVAL;
79231 + }
79232 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_POWER_MODE (=%d)\n",PowerMode));
79233 + break;
79234 + case RT_OID_802_11_TX_POWER_LEVEL_1:
79235 + if (wrq->u.data.length < sizeof(ULONG))
79236 + Status = -EINVAL;
79237 + else
79238 + {
79239 + Status = copy_from_user(&PowerTemp, wrq->u.data.pointer, wrq->u.data.length);
79240 + if (PowerTemp > 100)
79241 + PowerTemp = 0xffffffff; // AUTO
79242 + pAdapter->CommonCfg.TxPowerDefault = PowerTemp; //keep current setting.
79243 + pAdapter->CommonCfg.TxPowerPercentage = pAdapter->CommonCfg.TxPowerDefault;
79244 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_TX_POWER_LEVEL_1 (=%ld)\n", pAdapter->CommonCfg.TxPowerPercentage));
79245 + }
79246 + break;
79247 + case OID_802_11_NETWORK_TYPE_IN_USE:
79248 + if (wrq->u.data.length != sizeof(NDIS_802_11_NETWORK_TYPE))
79249 + Status = -EINVAL;
79250 + else
79251 + {
79252 + Status = copy_from_user(&NetType, wrq->u.data.pointer, wrq->u.data.length);
79253 +
79254 + if (NetType == Ndis802_11DS)
79255 + RTMPSetPhyMode(pAdapter, PHY_11B);
79256 + else if (NetType == Ndis802_11OFDM24)
79257 + RTMPSetPhyMode(pAdapter, PHY_11BG_MIXED);
79258 + else if (NetType == Ndis802_11OFDM5)
79259 + RTMPSetPhyMode(pAdapter, PHY_11A);
79260 + else
79261 + Status = -EINVAL;
79262 +#ifdef DOT11_N_SUPPORT
79263 + if (Status == NDIS_STATUS_SUCCESS)
79264 + SetCommonHT(pAdapter);
79265 +#endif // DOT11_N_SUPPORT //
79266 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_NETWORK_TYPE_IN_USE (=%d)\n",NetType));
79267 + }
79268 + break;
79269 + // For WPA PSK PMK key
79270 + case RT_OID_802_11_ADD_WPA:
79271 + pKey = kmalloc(wrq->u.data.length, MEM_ALLOC_FLAG);
79272 + if(pKey == NULL)
79273 + {
79274 + Status = -ENOMEM;
79275 + break;
79276 + }
79277 +
79278 + Status = copy_from_user(pKey, wrq->u.data.pointer, wrq->u.data.length);
79279 + if (pKey->Length != wrq->u.data.length)
79280 + {
79281 + Status = -EINVAL;
79282 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_ADD_WPA, Failed!!\n"));
79283 + }
79284 + else
79285 + {
79286 + if ((pAdapter->StaCfg.AuthMode != Ndis802_11AuthModeWPAPSK) &&
79287 + (pAdapter->StaCfg.AuthMode != Ndis802_11AuthModeWPA2PSK) &&
79288 + (pAdapter->StaCfg.AuthMode != Ndis802_11AuthModeWPANone) )
79289 + {
79290 + Status = -EOPNOTSUPP;
79291 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_ADD_WPA, Failed!! [AuthMode != WPAPSK/WPA2PSK/WPANONE]\n"));
79292 + }
79293 + else if ((pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) ||
79294 + (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK) ||
79295 + (pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPANone) ) // Only for WPA PSK mode
79296 + {
79297 + NdisMoveMemory(pAdapter->StaCfg.PMK, &pKey->KeyMaterial, pKey->KeyLength);
79298 + // Use RaConfig as PSK agent.
79299 + // Start STA supplicant state machine
79300 + if (pAdapter->StaCfg.AuthMode != Ndis802_11AuthModeWPANone)
79301 + pAdapter->StaCfg.WpaState = SS_START;
79302 +
79303 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_ADD_WPA (id=0x%x, Len=%d-byte)\n", pKey->KeyIndex, pKey->KeyLength));
79304 + }
79305 + else
79306 + {
79307 + pAdapter->StaCfg.WpaState = SS_NOTUSE;
79308 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_ADD_WPA (id=0x%x, Len=%d-byte)\n", pKey->KeyIndex, pKey->KeyLength));
79309 + }
79310 + }
79311 + kfree(pKey);
79312 + break;
79313 + case OID_802_11_REMOVE_KEY:
79314 + pRemoveKey = kmalloc(wrq->u.data.length, MEM_ALLOC_FLAG);
79315 + if(pRemoveKey == NULL)
79316 + {
79317 + Status = -ENOMEM;
79318 + break;
79319 + }
79320 +
79321 + Status = copy_from_user(pRemoveKey, wrq->u.data.pointer, wrq->u.data.length);
79322 + if (pRemoveKey->Length != wrq->u.data.length)
79323 + {
79324 + Status = -EINVAL;
79325 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_REMOVE_KEY, Failed!!\n"));
79326 + }
79327 + else
79328 + {
79329 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
79330 + {
79331 + RTMPWPARemoveKeyProc(pAdapter, pRemoveKey);
79332 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_REMOVE_KEY, Remove WPA Key!!\n"));
79333 + }
79334 + else
79335 + {
79336 + KeyIdx = pRemoveKey->KeyIndex;
79337 +
79338 + if (KeyIdx & 0x80000000)
79339 + {
79340 + // Should never set default bit when remove key
79341 + Status = -EINVAL;
79342 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_REMOVE_KEY, Failed!!(Should never set default bit when remove key)\n"));
79343 + }
79344 + else
79345 + {
79346 + KeyIdx = KeyIdx & 0x0fffffff;
79347 + if (KeyIdx > 3)
79348 + {
79349 + Status = -EINVAL;
79350 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_REMOVE_KEY, Failed!!(KeyId[%d] out of range)\n", KeyIdx));
79351 + }
79352 + else
79353 + {
79354 + pAdapter->SharedKey[BSS0][KeyIdx].KeyLen = 0;
79355 + pAdapter->SharedKey[BSS0][KeyIdx].CipherAlg = CIPHER_NONE;
79356 + AsicRemoveSharedKeyEntry(pAdapter, 0, (UCHAR)KeyIdx);
79357 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_REMOVE_KEY (id=0x%x, Len=%d-byte)\n", pRemoveKey->KeyIndex, pRemoveKey->Length));
79358 + }
79359 + }
79360 + }
79361 + }
79362 + kfree(pRemoveKey);
79363 + break;
79364 + // New for WPA
79365 + case OID_802_11_ADD_KEY:
79366 + pKey = kmalloc(wrq->u.data.length, MEM_ALLOC_FLAG);
79367 + if(pKey == NULL)
79368 + {
79369 + Status = -ENOMEM;
79370 + break;
79371 + }
79372 + Status = copy_from_user(pKey, wrq->u.data.pointer, wrq->u.data.length);
79373 + if (pKey->Length != wrq->u.data.length)
79374 + {
79375 + Status = -EINVAL;
79376 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_ADD_KEY, Failed!!\n"));
79377 + }
79378 + else
79379 + {
79380 + RTMPAddKey(pAdapter, pKey);
79381 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_ADD_KEY (id=0x%x, Len=%d-byte)\n", pKey->KeyIndex, pKey->KeyLength));
79382 + }
79383 + kfree(pKey);
79384 + break;
79385 + case OID_802_11_CONFIGURATION:
79386 + if (wrq->u.data.length != sizeof(NDIS_802_11_CONFIGURATION))
79387 + Status = -EINVAL;
79388 + else
79389 + {
79390 + Status = copy_from_user(&Config, wrq->u.data.pointer, wrq->u.data.length);
79391 + pConfig = &Config;
79392 +
79393 + if ((pConfig->BeaconPeriod >= 20) && (pConfig->BeaconPeriod <=400))
79394 + pAdapter->CommonCfg.BeaconPeriod = (USHORT) pConfig->BeaconPeriod;
79395 +
79396 + pAdapter->StaActive.AtimWin = (USHORT) pConfig->ATIMWindow;
79397 + MAP_KHZ_TO_CHANNEL_ID(pConfig->DSConfig, pAdapter->CommonCfg.Channel);
79398 + //
79399 + // Save the channel on MlmeAux for CntlOidRTBssidProc used.
79400 + //
79401 + pAdapter->MlmeAux.Channel = pAdapter->CommonCfg.Channel;
79402 +
79403 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_CONFIGURATION (BeacnPeriod=%ld,AtimW=%ld,Ch=%d)\n",
79404 + pConfig->BeaconPeriod, pConfig->ATIMWindow, pAdapter->CommonCfg.Channel));
79405 + // Config has changed
79406 + pAdapter->bConfigChanged = TRUE;
79407 + }
79408 + break;
79409 +#ifdef DOT11_N_SUPPORT
79410 + case RT_OID_802_11_SET_HT_PHYMODE:
79411 + if (wrq->u.data.length != sizeof(OID_SET_HT_PHYMODE))
79412 + Status = -EINVAL;
79413 + else
79414 + {
79415 + POID_SET_HT_PHYMODE pHTPhyMode = &HT_PhyMode;
79416 +
79417 + Status = copy_from_user(&HT_PhyMode, wrq->u.data.pointer, wrq->u.data.length);
79418 + DBGPRINT(RT_DEBUG_TRACE, ("Set::pHTPhyMode (PhyMode = %d,TransmitNo = %d, HtMode = %d, ExtOffset = %d , MCS = %d, BW = %d, STBC = %d, SHORTGI = %d) \n",
79419 + pHTPhyMode->PhyMode, pHTPhyMode->TransmitNo,pHTPhyMode->HtMode,pHTPhyMode->ExtOffset,
79420 + pHTPhyMode->MCS, pHTPhyMode->BW, pHTPhyMode->STBC, pHTPhyMode->SHORTGI));
79421 + if (pAdapter->CommonCfg.PhyMode >= PHY_11ABGN_MIXED)
79422 + RTMPSetHT(pAdapter, pHTPhyMode);
79423 + }
79424 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_SET_HT_PHYMODE(MCS=%d,BW=%d,SGI=%d,STBC=%d)\n",
79425 + pAdapter->StaCfg.HTPhyMode.field.MCS, pAdapter->StaCfg.HTPhyMode.field.BW, pAdapter->StaCfg.HTPhyMode.field.ShortGI,
79426 + pAdapter->StaCfg.HTPhyMode.field.STBC));
79427 + break;
79428 +#endif // DOT11_N_SUPPORT //
79429 + case RT_OID_802_11_SET_APSD_SETTING:
79430 + if (wrq->u.data.length != sizeof(ULONG))
79431 + Status = -EINVAL;
79432 + else
79433 + {
79434 + ULONG apsd ;
79435 + Status = copy_from_user(&apsd, wrq->u.data.pointer, wrq->u.data.length);
79436 +
79437 + /*-------------------------------------------------------------------
79438 + |B31~B7 | B6~B5 | B4 | B3 | B2 | B1 | B0 |
79439 + ---------------------------------------------------------------------
79440 + | Rsvd | Max SP Len | AC_VO | AC_VI | AC_BK | AC_BE | APSD Capable |
79441 + ---------------------------------------------------------------------*/
79442 + pAdapter->CommonCfg.bAPSDCapable = (apsd & 0x00000001) ? TRUE : FALSE;
79443 + pAdapter->CommonCfg.bAPSDAC_BE = ((apsd & 0x00000002) >> 1) ? TRUE : FALSE;
79444 + pAdapter->CommonCfg.bAPSDAC_BK = ((apsd & 0x00000004) >> 2) ? TRUE : FALSE;
79445 + pAdapter->CommonCfg.bAPSDAC_VI = ((apsd & 0x00000008) >> 3) ? TRUE : FALSE;
79446 + pAdapter->CommonCfg.bAPSDAC_VO = ((apsd & 0x00000010) >> 4) ? TRUE : FALSE;
79447 + pAdapter->CommonCfg.MaxSPLength = (UCHAR)((apsd & 0x00000060) >> 5);
79448 +
79449 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_SET_APSD_SETTING (apsd=0x%lx, APSDCap=%d, [BE,BK,VI,VO]=[%d/%d/%d/%d], MaxSPLen=%d)\n", apsd, pAdapter->CommonCfg.bAPSDCapable,
79450 + pAdapter->CommonCfg.bAPSDAC_BE, pAdapter->CommonCfg.bAPSDAC_BK, pAdapter->CommonCfg.bAPSDAC_VI, pAdapter->CommonCfg.bAPSDAC_VO, pAdapter->CommonCfg.MaxSPLength));
79451 + }
79452 + break;
79453 +
79454 + case RT_OID_802_11_SET_APSD_PSM:
79455 + if (wrq->u.data.length != sizeof(ULONG))
79456 + Status = -EINVAL;
79457 + else
79458 + {
79459 + // Driver needs to notify AP when PSM changes
79460 + Status = copy_from_user(&pAdapter->CommonCfg.bAPSDForcePowerSave, wrq->u.data.pointer, wrq->u.data.length);
79461 + if (pAdapter->CommonCfg.bAPSDForcePowerSave != pAdapter->StaCfg.Psm)
79462 + {
79463 + MlmeSetPsmBit(pAdapter, pAdapter->CommonCfg.bAPSDForcePowerSave);
79464 + RTMPSendNullFrame(pAdapter, pAdapter->CommonCfg.TxRate, TRUE);
79465 + }
79466 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_SET_APSD_PSM (bAPSDForcePowerSave:%d)\n", pAdapter->CommonCfg.bAPSDForcePowerSave));
79467 + }
79468 + break;
79469 +#ifdef QOS_DLS_SUPPORT
79470 + case RT_OID_802_11_SET_DLS:
79471 + if (wrq->u.data.length != sizeof(ULONG))
79472 + Status = -EINVAL;
79473 + else
79474 + {
79475 + BOOLEAN oldvalue = pAdapter->CommonCfg.bDLSCapable;
79476 + Status = copy_from_user(&pAdapter->CommonCfg.bDLSCapable, wrq->u.data.pointer, wrq->u.data.length);
79477 + if (oldvalue && !pAdapter->CommonCfg.bDLSCapable)
79478 + {
79479 + int i;
79480 + // tear down local dls table entry
79481 + for (i=0; i<MAX_NUM_OF_INIT_DLS_ENTRY; i++)
79482 + {
79483 + if (pAdapter->StaCfg.DLSEntry[i].Valid && (pAdapter->StaCfg.DLSEntry[i].Status == DLS_FINISH))
79484 + {
79485 + pAdapter->StaCfg.DLSEntry[i].Status = DLS_NONE;
79486 + pAdapter->StaCfg.DLSEntry[i].Valid = FALSE;
79487 + RTMPSendDLSTearDownFrame(pAdapter, pAdapter->StaCfg.DLSEntry[i].MacAddr);
79488 + }
79489 + }
79490 +
79491 + // tear down peer dls table entry
79492 + for (i=MAX_NUM_OF_INIT_DLS_ENTRY; i<MAX_NUM_OF_DLS_ENTRY; i++)
79493 + {
79494 + if (pAdapter->StaCfg.DLSEntry[i].Valid && (pAdapter->StaCfg.DLSEntry[i].Status == DLS_FINISH))
79495 + {
79496 + pAdapter->StaCfg.DLSEntry[i].Status = DLS_NONE;
79497 + pAdapter->StaCfg.DLSEntry[i].Valid = FALSE;
79498 + RTMPSendDLSTearDownFrame(pAdapter, pAdapter->StaCfg.DLSEntry[i].MacAddr);
79499 + }
79500 + }
79501 + }
79502 +
79503 + DBGPRINT(RT_DEBUG_TRACE,("Set::RT_OID_802_11_SET_DLS (=%d)\n", pAdapter->CommonCfg.bDLSCapable));
79504 + }
79505 + break;
79506 +
79507 + case RT_OID_802_11_SET_DLS_PARAM:
79508 + if (wrq->u.data.length != sizeof(RT_802_11_DLS_UI))
79509 + Status = -EINVAL;
79510 + else
79511 + {
79512 + RT_802_11_DLS Dls;
79513 +
79514 + NdisZeroMemory(&Dls, sizeof(RT_802_11_DLS));
79515 + RTMPMoveMemory(&Dls, wrq->u.data.pointer, sizeof(RT_802_11_DLS_UI));
79516 + MlmeEnqueue(pAdapter,
79517 + MLME_CNTL_STATE_MACHINE,
79518 + RT_OID_802_11_SET_DLS_PARAM,
79519 + sizeof(RT_802_11_DLS),
79520 + &Dls);
79521 + DBGPRINT(RT_DEBUG_TRACE,("Set::RT_OID_802_11_SET_DLS_PARAM \n"));
79522 + }
79523 + break;
79524 +#endif // QOS_DLS_SUPPORT //
79525 + case RT_OID_802_11_SET_WMM:
79526 + if (wrq->u.data.length != sizeof(BOOLEAN))
79527 + Status = -EINVAL;
79528 + else
79529 + {
79530 + Status = copy_from_user(&pAdapter->CommonCfg.bWmmCapable, wrq->u.data.pointer, wrq->u.data.length);
79531 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_SET_WMM (=%d) \n", pAdapter->CommonCfg.bWmmCapable));
79532 + }
79533 + break;
79534 +
79535 + case OID_802_11_DISASSOCIATE:
79536 +#ifdef RALINK_ATE
79537 + if (ATE_ON(pAdapter))
79538 + {
79539 + DBGPRINT(RT_DEBUG_TRACE, ("The driver is in ATE mode now\n"));
79540 + break;
79541 + }
79542 +#endif // RALINK_ATE //
79543 + //
79544 + // Set NdisRadioStateOff to TRUE, instead of called MlmeRadioOff.
79545 + // Later on, NDIS_802_11_BSSID_LIST_EX->NumberOfItems should be 0
79546 + // when query OID_802_11_BSSID_LIST.
79547 + //
79548 + // TRUE: NumberOfItems will set to 0.
79549 + // FALSE: NumberOfItems no change.
79550 + //
79551 + pAdapter->CommonCfg.NdisRadioStateOff = TRUE;
79552 + // Set to immediately send the media disconnect event
79553 + pAdapter->MlmeAux.CurrReqIsFromNdis = TRUE;
79554 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_DISASSOCIATE \n"));
79555 +
79556 + if (INFRA_ON(pAdapter))
79557 + {
79558 + if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE)
79559 + {
79560 + RT28XX_MLME_RESET_STATE_MACHINE(pAdapter);
79561 + DBGPRINT(RT_DEBUG_TRACE, ("!!! MLME busy, reset MLME state machine !!!\n"));
79562 + }
79563 +
79564 + MlmeEnqueue(pAdapter,
79565 + MLME_CNTL_STATE_MACHINE,
79566 + OID_802_11_DISASSOCIATE,
79567 + 0,
79568 + NULL);
79569 +
79570 + StateMachineTouched = TRUE;
79571 + }
79572 + break;
79573 +
79574 +#ifdef DOT11_N_SUPPORT
79575 + case RT_OID_802_11_SET_IMME_BA_CAP:
79576 + if (wrq->u.data.length != sizeof(OID_BACAP_STRUC))
79577 + Status = -EINVAL;
79578 + else
79579 + {
79580 + OID_BACAP_STRUC Orde ;
79581 + Status = copy_from_user(&Orde, wrq->u.data.pointer, wrq->u.data.length);
79582 + if (Orde.Policy > BA_NOTUSE)
79583 + {
79584 + Status = NDIS_STATUS_INVALID_DATA;
79585 + }
79586 + else if (Orde.Policy == BA_NOTUSE)
79587 + {
79588 + pAdapter->CommonCfg.BACapability.field.Policy = BA_NOTUSE;
79589 + pAdapter->CommonCfg.BACapability.field.MpduDensity = Orde.MpduDensity;
79590 + pAdapter->CommonCfg.DesiredHtPhy.MpduDensity = Orde.MpduDensity;
79591 + pAdapter->CommonCfg.DesiredHtPhy.AmsduEnable = Orde.AmsduEnable;
79592 + pAdapter->CommonCfg.DesiredHtPhy.AmsduSize= Orde.AmsduSize;
79593 + pAdapter->CommonCfg.DesiredHtPhy.MimoPs= Orde.MMPSmode;
79594 + pAdapter->CommonCfg.BACapability.field.MMPSmode = Orde.MMPSmode;
79595 + // UPdata to HT IE
79596 + pAdapter->CommonCfg.HtCapability.HtCapInfo.MimoPs = Orde.MMPSmode;
79597 + pAdapter->CommonCfg.HtCapability.HtCapInfo.AMsduSize = Orde.AmsduSize;
79598 + pAdapter->CommonCfg.HtCapability.HtCapParm.MpduDensity = Orde.MpduDensity;
79599 + }
79600 + else
79601 + {
79602 + pAdapter->CommonCfg.BACapability.field.AutoBA = Orde.AutoBA;
79603 + pAdapter->CommonCfg.BACapability.field.Policy = IMMED_BA; // we only support immediate BA.
79604 + pAdapter->CommonCfg.BACapability.field.MpduDensity = Orde.MpduDensity;
79605 + pAdapter->CommonCfg.DesiredHtPhy.MpduDensity = Orde.MpduDensity;
79606 + pAdapter->CommonCfg.DesiredHtPhy.AmsduEnable = Orde.AmsduEnable;
79607 + pAdapter->CommonCfg.DesiredHtPhy.AmsduSize= Orde.AmsduSize;
79608 + pAdapter->CommonCfg.DesiredHtPhy.MimoPs = Orde.MMPSmode;
79609 + pAdapter->CommonCfg.BACapability.field.MMPSmode = Orde.MMPSmode;
79610 +
79611 + // UPdata to HT IE
79612 + pAdapter->CommonCfg.HtCapability.HtCapInfo.MimoPs = Orde.MMPSmode;
79613 + pAdapter->CommonCfg.HtCapability.HtCapInfo.AMsduSize = Orde.AmsduSize;
79614 + pAdapter->CommonCfg.HtCapability.HtCapParm.MpduDensity = Orde.MpduDensity;
79615 +
79616 + if (pAdapter->CommonCfg.BACapability.field.RxBAWinLimit > MAX_RX_REORDERBUF)
79617 + pAdapter->CommonCfg.BACapability.field.RxBAWinLimit = MAX_RX_REORDERBUF;
79618 +
79619 + }
79620 +
79621 + pAdapter->CommonCfg.REGBACapability.word = pAdapter->CommonCfg.BACapability.word;
79622 + DBGPRINT(RT_DEBUG_TRACE, ("Set::(Orde.AutoBA = %d) (Policy=%d)(ReBAWinLimit=%d)(TxBAWinLimit=%d)(AutoMode=%d)\n",Orde.AutoBA, pAdapter->CommonCfg.BACapability.field.Policy,
79623 + pAdapter->CommonCfg.BACapability.field.RxBAWinLimit,pAdapter->CommonCfg.BACapability.field.TxBAWinLimit, pAdapter->CommonCfg.BACapability.field.AutoBA));
79624 + DBGPRINT(RT_DEBUG_TRACE, ("Set::(MimoPs = %d)(AmsduEnable = %d) (AmsduSize=%d)(MpduDensity=%d)\n",pAdapter->CommonCfg.DesiredHtPhy.MimoPs, pAdapter->CommonCfg.DesiredHtPhy.AmsduEnable,
79625 + pAdapter->CommonCfg.DesiredHtPhy.AmsduSize, pAdapter->CommonCfg.DesiredHtPhy.MpduDensity));
79626 + }
79627 +
79628 + break;
79629 + case RT_OID_802_11_ADD_IMME_BA:
79630 + DBGPRINT(RT_DEBUG_TRACE, (" Set :: RT_OID_802_11_ADD_IMME_BA \n"));
79631 + if (wrq->u.data.length != sizeof(OID_ADD_BA_ENTRY))
79632 + Status = -EINVAL;
79633 + else
79634 + {
79635 + UCHAR index;
79636 + OID_ADD_BA_ENTRY BA;
79637 + MAC_TABLE_ENTRY *pEntry;
79638 +
79639 + Status = copy_from_user(&BA, wrq->u.data.pointer, wrq->u.data.length);
79640 + if (BA.TID > 15)
79641 + {
79642 + Status = NDIS_STATUS_INVALID_DATA;
79643 + break;
79644 + }
79645 + else
79646 + {
79647 + //BATableInsertEntry
79648 + //As ad-hoc mode, BA pair is not limited to only BSSID. so add via OID.
79649 + index = BA.TID;
79650 + // in ad hoc mode, when adding BA pair, we should insert this entry into MACEntry too
79651 + pEntry = MacTableLookup(pAdapter, BA.MACAddr);
79652 + if (!pEntry)
79653 + {
79654 + DBGPRINT(RT_DEBUG_TRACE, ("RT_OID_802_11_ADD_IMME_BA. break on no connection.----:%x:%x\n", BA.MACAddr[4], BA.MACAddr[5]));
79655 + break;
79656 + }
79657 + if (BA.IsRecipient == FALSE)
79658 + {
79659 + if (pEntry->bIAmBadAtheros == TRUE)
79660 + pAdapter->CommonCfg.BACapability.field.RxBAWinLimit = 0x10;
79661 +
79662 + BAOriSessionSetUp(pAdapter, pEntry, index, 0, 100, TRUE);
79663 + }
79664 + else
79665 + {
79666 + //BATableInsertEntry(pAdapter, pEntry->Aid, BA.MACAddr, 0, 0xffff, BA.TID, BA.nMSDU, BA.IsRecipient);
79667 + }
79668 +
79669 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_802_11_ADD_IMME_BA. Rec = %d. Mac = %x:%x:%x:%x:%x:%x . \n",
79670 + BA.IsRecipient, BA.MACAddr[0], BA.MACAddr[1], BA.MACAddr[2], BA.MACAddr[2]
79671 + , BA.MACAddr[4], BA.MACAddr[5]));
79672 + }
79673 + }
79674 + break;
79675 +
79676 + case RT_OID_802_11_TEAR_IMME_BA:
79677 + DBGPRINT(RT_DEBUG_TRACE, ("Set :: RT_OID_802_11_TEAR_IMME_BA \n"));
79678 + if (wrq->u.data.length != sizeof(OID_ADD_BA_ENTRY))
79679 + Status = -EINVAL;
79680 + else
79681 + {
79682 + POID_ADD_BA_ENTRY pBA;
79683 + MAC_TABLE_ENTRY *pEntry;
79684 +
79685 + pBA = kmalloc(wrq->u.data.length, MEM_ALLOC_FLAG);
79686 +
79687 + if (pBA == NULL)
79688 + {
79689 + DBGPRINT(RT_DEBUG_TRACE, ("Set :: RT_OID_802_11_TEAR_IMME_BA kmalloc() can't allocate enough memory\n"));
79690 + Status = NDIS_STATUS_FAILURE;
79691 + }
79692 + else
79693 + {
79694 + Status = copy_from_user(pBA, wrq->u.data.pointer, wrq->u.data.length);
79695 + DBGPRINT(RT_DEBUG_TRACE, ("Set :: RT_OID_802_11_TEAR_IMME_BA(TID=%d, bAllTid=%d)\n", pBA->TID, pBA->bAllTid));
79696 +
79697 + if (!pBA->bAllTid && (pBA->TID > NUM_OF_TID))
79698 + {
79699 + Status = NDIS_STATUS_INVALID_DATA;
79700 + break;
79701 + }
79702 +
79703 + if (pBA->IsRecipient == FALSE)
79704 + {
79705 + pEntry = MacTableLookup(pAdapter, pBA->MACAddr);
79706 + DBGPRINT(RT_DEBUG_TRACE, (" pBA->IsRecipient == FALSE\n"));
79707 + if (pEntry)
79708 + {
79709 + DBGPRINT(RT_DEBUG_TRACE, (" pBA->pEntry\n"));
79710 + BAOriSessionTearDown(pAdapter, pEntry->Aid, pBA->TID, FALSE, TRUE);
79711 + }
79712 + else
79713 + DBGPRINT(RT_DEBUG_TRACE, ("Set :: Not found pEntry \n"));
79714 + }
79715 + else
79716 + {
79717 + pEntry = MacTableLookup(pAdapter, pBA->MACAddr);
79718 + if (pEntry)
79719 + {
79720 + BARecSessionTearDown( pAdapter, (UCHAR)pEntry->Aid, pBA->TID, TRUE);
79721 + }
79722 + else
79723 + DBGPRINT(RT_DEBUG_TRACE, ("Set :: Not found pEntry \n"));
79724 + }
79725 + kfree(pBA);
79726 + }
79727 + }
79728 + break;
79729 +#endif // DOT11_N_SUPPORT //
79730 +
79731 + // For WPA_SUPPLICANT to set static wep key
79732 + case OID_802_11_ADD_WEP:
79733 + pWepKey = kmalloc(wrq->u.data.length, MEM_ALLOC_FLAG);
79734 +
79735 + if(pWepKey == NULL)
79736 + {
79737 + Status = -ENOMEM;
79738 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_ADD_WEP, Failed!!\n"));
79739 + break;
79740 + }
79741 + Status = copy_from_user(pWepKey, wrq->u.data.pointer, wrq->u.data.length);
79742 + if (Status)
79743 + {
79744 + Status = -EINVAL;
79745 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_ADD_WEP, Failed (length mismatch)!!\n"));
79746 + }
79747 + else
79748 + {
79749 + KeyIdx = pWepKey->KeyIndex & 0x0fffffff;
79750 + // KeyIdx must be 0 ~ 3
79751 + if (KeyIdx > 4)
79752 + {
79753 + Status = -EINVAL;
79754 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_ADD_WEP, Failed (KeyIdx must be smaller than 4)!!\n"));
79755 + }
79756 + else
79757 + {
79758 + UCHAR CipherAlg = 0;
79759 + PUCHAR Key;
79760 +
79761 + // set key material and key length
79762 + NdisZeroMemory(pAdapter->SharedKey[BSS0][KeyIdx].Key, 16);
79763 + pAdapter->SharedKey[BSS0][KeyIdx].KeyLen = (UCHAR) pWepKey->KeyLength;
79764 + NdisMoveMemory(pAdapter->SharedKey[BSS0][KeyIdx].Key, &pWepKey->KeyMaterial, pWepKey->KeyLength);
79765 +
79766 + switch(pWepKey->KeyLength)
79767 + {
79768 + case 5:
79769 + CipherAlg = CIPHER_WEP64;
79770 + break;
79771 + case 13:
79772 + CipherAlg = CIPHER_WEP128;
79773 + break;
79774 + default:
79775 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_ADD_WEP, only support CIPHER_WEP64(len:5) & CIPHER_WEP128(len:13)!!\n"));
79776 + Status = -EINVAL;
79777 + break;
79778 + }
79779 + pAdapter->SharedKey[BSS0][KeyIdx].CipherAlg = CipherAlg;
79780 +
79781 + // Default key for tx (shared key)
79782 + if (pWepKey->KeyIndex & 0x80000000)
79783 + {
79784 +#ifdef WPA_SUPPLICANT_SUPPORT
79785 + // set key material and key length
79786 + NdisZeroMemory(pAdapter->StaCfg.DesireSharedKey[KeyIdx].Key, 16);
79787 + pAdapter->StaCfg.DesireSharedKey[KeyIdx].KeyLen = (UCHAR) pWepKey->KeyLength;
79788 + NdisMoveMemory(pAdapter->StaCfg.DesireSharedKey[KeyIdx].Key, &pWepKey->KeyMaterial, pWepKey->KeyLength);
79789 + pAdapter->StaCfg.DesireSharedKeyId = KeyIdx;
79790 + pAdapter->StaCfg.DesireSharedKey[KeyIdx].CipherAlg = CipherAlg;
79791 +#endif // WPA_SUPPLICANT_SUPPORT //
79792 + pAdapter->StaCfg.DefaultKeyId = (UCHAR) KeyIdx;
79793 + }
79794 +
79795 +#ifdef WPA_SUPPLICANT_SUPPORT
79796 + if (pAdapter->StaCfg.PortSecured == WPA_802_1X_PORT_SECURED)
79797 +#endif // WPA_SUPPLICANT_SUPPORT
79798 + {
79799 + Key = pAdapter->SharedKey[BSS0][KeyIdx].Key;
79800 +
79801 + // Set key material and cipherAlg to Asic
79802 + AsicAddSharedKeyEntry(pAdapter, BSS0, KeyIdx, CipherAlg, Key, NULL, NULL);
79803 +
79804 + if (pWepKey->KeyIndex & 0x80000000)
79805 + {
79806 + PMAC_TABLE_ENTRY pEntry = &pAdapter->MacTab.Content[BSSID_WCID];
79807 + // Assign group key info
79808 + RTMPAddWcidAttributeEntry(pAdapter, BSS0, KeyIdx, CipherAlg, NULL);
79809 + // Assign pairwise key info
79810 + RTMPAddWcidAttributeEntry(pAdapter, BSS0, KeyIdx, CipherAlg, pEntry);
79811 + }
79812 + }
79813 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_ADD_WEP (id=0x%x, Len=%d-byte), %s\n", pWepKey->KeyIndex, pWepKey->KeyLength, (pAdapter->StaCfg.PortSecured == WPA_802_1X_PORT_SECURED) ? "Port Secured":"Port NOT Secured"));
79814 + }
79815 + }
79816 + kfree(pWepKey);
79817 + break;
79818 +#ifdef WPA_SUPPLICANT_SUPPORT
79819 + case OID_SET_COUNTERMEASURES:
79820 + if (wrq->u.data.length != sizeof(int))
79821 + Status = -EINVAL;
79822 + else
79823 + {
79824 + int enabled = 0;
79825 + Status = copy_from_user(&enabled, wrq->u.data.pointer, wrq->u.data.length);
79826 + if (enabled == 1)
79827 + pAdapter->StaCfg.bBlockAssoc = TRUE;
79828 + else
79829 + // WPA MIC error should block association attempt for 60 seconds
79830 + pAdapter->StaCfg.bBlockAssoc = FALSE;
79831 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_SET_COUNTERMEASURES bBlockAssoc=%s\n", pAdapter->StaCfg.bBlockAssoc ? "TRUE":"FALSE"));
79832 + }
79833 + break;
79834 + case RT_OID_WPA_SUPPLICANT_SUPPORT:
79835 + if (wrq->u.data.length != sizeof(UCHAR))
79836 + Status = -EINVAL;
79837 + else
79838 + {
79839 + Status = copy_from_user(&wpa_supplicant_enable, wrq->u.data.pointer, wrq->u.data.length);
79840 + pAdapter->StaCfg.WpaSupplicantUP = wpa_supplicant_enable;
79841 + DBGPRINT(RT_DEBUG_TRACE, ("Set::RT_OID_WPA_SUPPLICANT_SUPPORT (=%d)\n", pAdapter->StaCfg.WpaSupplicantUP));
79842 + }
79843 + break;
79844 + case OID_802_11_DEAUTHENTICATION:
79845 + if (wrq->u.data.length != sizeof(MLME_DEAUTH_REQ_STRUCT))
79846 + Status = -EINVAL;
79847 + else
79848 + {
79849 + MLME_DEAUTH_REQ_STRUCT *pInfo;
79850 + MLME_QUEUE_ELEM *MsgElem = (MLME_QUEUE_ELEM *) kmalloc(sizeof(MLME_QUEUE_ELEM), MEM_ALLOC_FLAG);
79851 +
79852 + pInfo = (MLME_DEAUTH_REQ_STRUCT *) MsgElem->Msg;
79853 + Status = copy_from_user(pInfo, wrq->u.data.pointer, wrq->u.data.length);
79854 + MlmeDeauthReqAction(pAdapter, MsgElem);
79855 + kfree(MsgElem);
79856 +
79857 + if (INFRA_ON(pAdapter))
79858 + {
79859 + LinkDown(pAdapter, FALSE);
79860 + pAdapter->Mlme.AssocMachine.CurrState = ASSOC_IDLE;
79861 + }
79862 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_DEAUTHENTICATION (Reason=%d)\n", pInfo->Reason));
79863 + }
79864 + break;
79865 + case OID_802_11_DROP_UNENCRYPTED:
79866 + if (wrq->u.data.length != sizeof(int))
79867 + Status = -EINVAL;
79868 + else
79869 + {
79870 + int enabled = 0;
79871 + Status = copy_from_user(&enabled, wrq->u.data.pointer, wrq->u.data.length);
79872 + if (enabled == 1)
79873 + pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
79874 + else
79875 + pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_SECURED;
79876 + NdisAcquireSpinLock(&pAdapter->MacTabLock);
79877 + pAdapter->MacTab.Content[BSSID_WCID].PortSecured = pAdapter->StaCfg.PortSecured;
79878 + NdisReleaseSpinLock(&pAdapter->MacTabLock);
79879 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_DROP_UNENCRYPTED (=%d)\n", enabled));
79880 + }
79881 + break;
79882 + case OID_802_11_SET_IEEE8021X:
79883 + if (wrq->u.data.length != sizeof(BOOLEAN))
79884 + Status = -EINVAL;
79885 + else
79886 + {
79887 + Status = copy_from_user(&IEEE8021xState, wrq->u.data.pointer, wrq->u.data.length);
79888 + pAdapter->StaCfg.IEEE8021X = IEEE8021xState;
79889 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_SET_IEEE8021X (=%d)\n", IEEE8021xState));
79890 + }
79891 + break;
79892 + case OID_802_11_SET_IEEE8021X_REQUIRE_KEY:
79893 + if (wrq->u.data.length != sizeof(BOOLEAN))
79894 + Status = -EINVAL;
79895 + else
79896 + {
79897 + Status = copy_from_user(&IEEE8021x_required_keys, wrq->u.data.pointer, wrq->u.data.length);
79898 + pAdapter->StaCfg.IEEE8021x_required_keys = IEEE8021x_required_keys;
79899 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_SET_IEEE8021X_REQUIRE_KEY (%d)\n", IEEE8021x_required_keys));
79900 + }
79901 + break;
79902 + case OID_802_11_PMKID:
79903 + pPmkId = kmalloc(wrq->u.data.length, MEM_ALLOC_FLAG);
79904 +
79905 + if(pPmkId == NULL) {
79906 + Status = -ENOMEM;
79907 + break;
79908 + }
79909 + Status = copy_from_user(pPmkId, wrq->u.data.pointer, wrq->u.data.length);
79910 +
79911 + // check the PMKID information
79912 + if (pPmkId->BSSIDInfoCount == 0)
79913 + NdisZeroMemory(pAdapter->StaCfg.SavedPMK, sizeof(BSSID_INFO)*PMKID_NO);
79914 + else
79915 + {
79916 + PBSSID_INFO pBssIdInfo;
79917 + UINT BssIdx;
79918 + UINT CachedIdx;
79919 +
79920 + for (BssIdx = 0; BssIdx < pPmkId->BSSIDInfoCount; BssIdx++)
79921 + {
79922 + // point to the indexed BSSID_INFO structure
79923 + pBssIdInfo = (PBSSID_INFO) ((PUCHAR) pPmkId + 2 * sizeof(UINT) + BssIdx * sizeof(BSSID_INFO));
79924 + // Find the entry in the saved data base.
79925 + for (CachedIdx = 0; CachedIdx < pAdapter->StaCfg.SavedPMKNum; CachedIdx++)
79926 + {
79927 + // compare the BSSID
79928 + if (NdisEqualMemory(pBssIdInfo->BSSID, pAdapter->StaCfg.SavedPMK[CachedIdx].BSSID, sizeof(NDIS_802_11_MAC_ADDRESS)))
79929 + break;
79930 + }
79931 +
79932 + // Found, replace it
79933 + if (CachedIdx < PMKID_NO)
79934 + {
79935 + DBGPRINT(RT_DEBUG_OFF, ("Update OID_802_11_PMKID, idx = %d\n", CachedIdx));
79936 + NdisMoveMemory(&pAdapter->StaCfg.SavedPMK[CachedIdx], pBssIdInfo, sizeof(BSSID_INFO));
79937 + pAdapter->StaCfg.SavedPMKNum++;
79938 + }
79939 + // Not found, replace the last one
79940 + else
79941 + {
79942 + // Randomly replace one
79943 + CachedIdx = (pBssIdInfo->BSSID[5] % PMKID_NO);
79944 + DBGPRINT(RT_DEBUG_OFF, ("Update OID_802_11_PMKID, idx = %d\n", CachedIdx));
79945 + NdisMoveMemory(&pAdapter->StaCfg.SavedPMK[CachedIdx], pBssIdInfo, sizeof(BSSID_INFO));
79946 + }
79947 + }
79948 + }
79949 + if(pPmkId)
79950 + kfree(pPmkId);
79951 + break;
79952 +#endif // WPA_SUPPLICANT_SUPPORT //
79953 +
79954 +
79955 +
79956 +#ifdef SNMP_SUPPORT
79957 + case OID_802_11_SHORTRETRYLIMIT:
79958 + if (wrq->u.data.length != sizeof(ULONG))
79959 + Status = -EINVAL;
79960 + else
79961 + {
79962 + Status = copy_from_user(&ShortRetryLimit, wrq->u.data.pointer, wrq->u.data.length);
79963 + RTMP_IO_READ32(pAdapter, TX_RTY_CFG, &tx_rty_cfg.word);
79964 + tx_rty_cfg.field.ShortRtyLimit = ShortRetryLimit;
79965 + RTMP_IO_WRITE32(pAdapter, TX_RTY_CFG, tx_rty_cfg.word);
79966 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_SHORTRETRYLIMIT (tx_rty_cfg.field.ShortRetryLimit=%d, ShortRetryLimit=%ld)\n", tx_rty_cfg.field.ShortRtyLimit, ShortRetryLimit));
79967 + }
79968 + break;
79969 +
79970 + case OID_802_11_LONGRETRYLIMIT:
79971 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_LONGRETRYLIMIT \n"));
79972 + if (wrq->u.data.length != sizeof(ULONG))
79973 + Status = -EINVAL;
79974 + else
79975 + {
79976 + Status = copy_from_user(&LongRetryLimit, wrq->u.data.pointer, wrq->u.data.length);
79977 + RTMP_IO_READ32(pAdapter, TX_RTY_CFG, &tx_rty_cfg.word);
79978 + tx_rty_cfg.field.LongRtyLimit = LongRetryLimit;
79979 + RTMP_IO_WRITE32(pAdapter, TX_RTY_CFG, tx_rty_cfg.word);
79980 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_LONGRETRYLIMIT (tx_rty_cfg.field.LongRetryLimit= %d,LongRetryLimit=%ld)\n", tx_rty_cfg.field.LongRtyLimit, LongRetryLimit));
79981 + }
79982 + break;
79983 +
79984 + case OID_802_11_WEPDEFAULTKEYVALUE:
79985 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_WEPDEFAULTKEYVALUE\n"));
79986 + pKey = kmalloc(wrq->u.data.length, GFP_KERNEL);
79987 + Status = copy_from_user(pKey, wrq->u.data.pointer, wrq->u.data.length);
79988 + //pKey = &WepKey;
79989 +
79990 + if ( pKey->Length != wrq->u.data.length)
79991 + {
79992 + Status = -EINVAL;
79993 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_WEPDEFAULTKEYVALUE, Failed!!\n"));
79994 + }
79995 + KeyIdx = pKey->KeyIndex & 0x0fffffff;
79996 + DBGPRINT(RT_DEBUG_TRACE,("pKey->KeyIndex =%d, pKey->KeyLength=%d\n", pKey->KeyIndex, pKey->KeyLength));
79997 +
79998 + // it is a shared key
79999 + if (KeyIdx > 4)
80000 + Status = -EINVAL;
80001 + else
80002 + {
80003 + pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].KeyLen = (UCHAR) pKey->KeyLength;
80004 + NdisMoveMemory(&pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].Key, &pKey->KeyMaterial, pKey->KeyLength);
80005 + if (pKey->KeyIndex & 0x80000000)
80006 + {
80007 + // Default key for tx (shared key)
80008 + pAdapter->StaCfg.DefaultKeyId = (UCHAR) KeyIdx;
80009 + }
80010 + //RestartAPIsRequired = TRUE;
80011 + }
80012 + break;
80013 +
80014 +
80015 + case OID_802_11_WEPDEFAULTKEYID:
80016 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_WEPDEFAULTKEYID \n"));
80017 +
80018 + if (wrq->u.data.length != sizeof(UCHAR))
80019 + Status = -EINVAL;
80020 + else
80021 + Status = copy_from_user(&pAdapter->StaCfg.DefaultKeyId, wrq->u.data.pointer, wrq->u.data.length);
80022 +
80023 + break;
80024 +
80025 +
80026 + case OID_802_11_CURRENTCHANNEL:
80027 + DBGPRINT(RT_DEBUG_TRACE, ("Set::OID_802_11_CURRENTCHANNEL \n"));
80028 + if (wrq->u.data.length != sizeof(UCHAR))
80029 + Status = -EINVAL;
80030 + else
80031 + {
80032 + Status = copy_from_user(&ctmp, wrq->u.data.pointer, wrq->u.data.length);
80033 + sprintf(&ctmp,"%d", ctmp);
80034 + Set_Channel_Proc(pAdapter, &ctmp);
80035 + }
80036 + break;
80037 +#endif
80038 +
80039 +
80040 +
80041 + default:
80042 + DBGPRINT(RT_DEBUG_TRACE, ("Set::unknown IOCTL's subcmd = 0x%08x\n", cmd));
80043 + Status = -EOPNOTSUPP;
80044 + break;
80045 + }
80046 +
80047 +
80048 + return Status;
80049 +}
80050 +
80051 +INT RTMPQueryInformation(
80052 + IN PRTMP_ADAPTER pAdapter,
80053 + IN OUT struct ifreq *rq,
80054 + IN INT cmd)
80055 +{
80056 + struct iwreq *wrq = (struct iwreq *) rq;
80057 + NDIS_802_11_BSSID_LIST_EX *pBssidList = NULL;
80058 + PNDIS_WLAN_BSSID_EX pBss;
80059 + NDIS_802_11_SSID Ssid;
80060 + NDIS_802_11_CONFIGURATION *pConfiguration = NULL;
80061 + RT_802_11_LINK_STATUS *pLinkStatus = NULL;
80062 + RT_802_11_STA_CONFIG *pStaConfig = NULL;
80063 + NDIS_802_11_STATISTICS *pStatistics = NULL;
80064 + NDIS_802_11_RTS_THRESHOLD RtsThresh;
80065 + NDIS_802_11_FRAGMENTATION_THRESHOLD FragThresh;
80066 + NDIS_802_11_POWER_MODE PowerMode;
80067 + NDIS_802_11_NETWORK_INFRASTRUCTURE BssType;
80068 + RT_802_11_PREAMBLE PreamType;
80069 + NDIS_802_11_AUTHENTICATION_MODE AuthMode;
80070 + NDIS_802_11_WEP_STATUS WepStatus;
80071 + NDIS_MEDIA_STATE MediaState;
80072 + ULONG BssBufSize, ulInfo=0, NetworkTypeList[4], apsd = 0;
80073 + USHORT BssLen = 0;
80074 + PUCHAR pBuf = NULL, pPtr;
80075 + INT Status = NDIS_STATUS_SUCCESS;
80076 + UINT we_version_compiled;
80077 + UCHAR i, Padding = 0;
80078 + BOOLEAN RadioState;
80079 + UCHAR driverVersion[8];
80080 + OID_SET_HT_PHYMODE *pHTPhyMode = NULL;
80081 +
80082 +
80083 +#ifdef SNMP_SUPPORT
80084 + //for snmp, kathy
80085 + DefaultKeyIdxValue *pKeyIdxValue;
80086 + INT valueLen;
80087 + TX_RTY_CFG_STRUC tx_rty_cfg;
80088 + ULONG ShortRetryLimit, LongRetryLimit;
80089 + UCHAR tmp[64];
80090 +#endif //SNMP
80091 +
80092 + switch(cmd)
80093 + {
80094 + case RT_OID_DEVICE_NAME:
80095 + wrq->u.data.length = sizeof(STA_NIC_DEVICE_NAME);
80096 + Status = copy_to_user(wrq->u.data.pointer, STA_NIC_DEVICE_NAME, wrq->u.data.length);
80097 + break;
80098 + case RT_OID_VERSION_INFO:
80099 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_VERSION_INFO \n"));
80100 + wrq->u.data.length = 8*sizeof(UCHAR);
80101 + sprintf(&driverVersion[0], "%s", STA_DRIVER_VERSION);
80102 + driverVersion[7] = '\0';
80103 + if (copy_to_user(wrq->u.data.pointer, &driverVersion, wrq->u.data.length))
80104 + {
80105 + Status = -EFAULT;
80106 + }
80107 + break;
80108 +#ifdef RALINK_ATE
80109 + case RT_QUERY_ATE_TXDONE_COUNT:
80110 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_QUERY_ATE_TXDONE_COUNT \n"));
80111 + wrq->u.data.length = sizeof(UINT32);
80112 + if (copy_to_user(wrq->u.data.pointer, &pAdapter->ate.TxDoneCount, wrq->u.data.length))
80113 + {
80114 + Status = -EFAULT;
80115 + }
80116 + break;
80117 +#endif // RALINK_ATE //
80118 + case OID_802_11_BSSID_LIST:
80119 + if (RTMP_TEST_FLAG(pAdapter, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS))
80120 + {
80121 + /*
80122 + * Still scanning, indicate the caller should try again.
80123 + */
80124 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_BSSID_LIST (Still scanning)\n"));
80125 + return -EAGAIN;
80126 + }
80127 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_BSSID_LIST (%d BSS returned)\n",pAdapter->ScanTab.BssNr));
80128 + pAdapter->StaCfg.bScanReqIsFromWebUI = FALSE;
80129 + // Claculate total buffer size required
80130 + BssBufSize = sizeof(ULONG);
80131 +
80132 + for (i = 0; i < pAdapter->ScanTab.BssNr; i++)
80133 + {
80134 + // Align pointer to 4 bytes boundary.
80135 + //Padding = 4 - (pAdapter->ScanTab.BssEntry[i].VarIELen & 0x0003);
80136 + //if (Padding == 4)
80137 + // Padding = 0;
80138 + BssBufSize += (sizeof(NDIS_WLAN_BSSID_EX) - 1 + sizeof(NDIS_802_11_FIXED_IEs) + pAdapter->ScanTab.BssEntry[i].VarIELen + Padding);
80139 + }
80140 +
80141 + // For safety issue, we add 256 bytes just in case
80142 + BssBufSize += 256;
80143 + // Allocate the same size as passed from higher layer
80144 + pBuf = kmalloc(BssBufSize, MEM_ALLOC_FLAG);
80145 + if(pBuf == NULL)
80146 + {
80147 + Status = -ENOMEM;
80148 + break;
80149 + }
80150 + // Init 802_11_BSSID_LIST_EX structure
80151 + NdisZeroMemory(pBuf, BssBufSize);
80152 + pBssidList = (PNDIS_802_11_BSSID_LIST_EX) pBuf;
80153 + pBssidList->NumberOfItems = pAdapter->ScanTab.BssNr;
80154 +
80155 + // Calculate total buffer length
80156 + BssLen = 4; // Consist of NumberOfItems
80157 + // Point to start of NDIS_WLAN_BSSID_EX
80158 + // pPtr = pBuf + sizeof(ULONG);
80159 + pPtr = (PUCHAR) &pBssidList->Bssid[0];
80160 + for (i = 0; i < pAdapter->ScanTab.BssNr; i++)
80161 + {
80162 + pBss = (PNDIS_WLAN_BSSID_EX) pPtr;
80163 + NdisMoveMemory(&pBss->MacAddress, &pAdapter->ScanTab.BssEntry[i].Bssid, MAC_ADDR_LEN);
80164 + if ((pAdapter->ScanTab.BssEntry[i].Hidden == 1) && (pAdapter->StaCfg.bShowHiddenSSID == FALSE))
80165 + {
80166 + //
80167 + // We must return this SSID during 4way handshaking, otherwise Aegis will failed to parse WPA infomation
80168 + // and then failed to send EAPOl farame.
80169 + //
80170 + if ((pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA) && (pAdapter->StaCfg.PortSecured != WPA_802_1X_PORT_SECURED))
80171 + {
80172 + pBss->Ssid.SsidLength = pAdapter->ScanTab.BssEntry[i].SsidLen;
80173 + NdisMoveMemory(pBss->Ssid.Ssid, pAdapter->ScanTab.BssEntry[i].Ssid, pAdapter->ScanTab.BssEntry[i].SsidLen);
80174 + }
80175 + else
80176 + pBss->Ssid.SsidLength = 0;
80177 + }
80178 + else
80179 + {
80180 + pBss->Ssid.SsidLength = pAdapter->ScanTab.BssEntry[i].SsidLen;
80181 + NdisMoveMemory(pBss->Ssid.Ssid, pAdapter->ScanTab.BssEntry[i].Ssid, pAdapter->ScanTab.BssEntry[i].SsidLen);
80182 + }
80183 + pBss->Privacy = pAdapter->ScanTab.BssEntry[i].Privacy;
80184 + pBss->Rssi = pAdapter->ScanTab.BssEntry[i].Rssi - pAdapter->BbpRssiToDbmDelta;
80185 + pBss->NetworkTypeInUse = NetworkTypeInUseSanity(&pAdapter->ScanTab.BssEntry[i]);
80186 + pBss->Configuration.Length = sizeof(NDIS_802_11_CONFIGURATION);
80187 + pBss->Configuration.BeaconPeriod = pAdapter->ScanTab.BssEntry[i].BeaconPeriod;
80188 + pBss->Configuration.ATIMWindow = pAdapter->ScanTab.BssEntry[i].AtimWin;
80189 +
80190 + MAP_CHANNEL_ID_TO_KHZ(pAdapter->ScanTab.BssEntry[i].Channel, pBss->Configuration.DSConfig);
80191 +
80192 + if (pAdapter->ScanTab.BssEntry[i].BssType == BSS_INFRA)
80193 + pBss->InfrastructureMode = Ndis802_11Infrastructure;
80194 + else
80195 + pBss->InfrastructureMode = Ndis802_11IBSS;
80196 +
80197 + NdisMoveMemory(pBss->SupportedRates, pAdapter->ScanTab.BssEntry[i].SupRate, pAdapter->ScanTab.BssEntry[i].SupRateLen);
80198 + NdisMoveMemory(pBss->SupportedRates + pAdapter->ScanTab.BssEntry[i].SupRateLen,
80199 + pAdapter->ScanTab.BssEntry[i].ExtRate,
80200 + pAdapter->ScanTab.BssEntry[i].ExtRateLen);
80201 +
80202 + if (pAdapter->ScanTab.BssEntry[i].VarIELen == 0)
80203 + {
80204 + pBss->IELength = sizeof(NDIS_802_11_FIXED_IEs);
80205 + NdisMoveMemory(pBss->IEs, &pAdapter->ScanTab.BssEntry[i].FixIEs, sizeof(NDIS_802_11_FIXED_IEs));
80206 + pPtr = pPtr + sizeof(NDIS_WLAN_BSSID_EX) - 1 + sizeof(NDIS_802_11_FIXED_IEs);
80207 + }
80208 + else
80209 + {
80210 + pBss->IELength = (ULONG)(sizeof(NDIS_802_11_FIXED_IEs) + pAdapter->ScanTab.BssEntry[i].VarIELen);
80211 + pPtr = pPtr + sizeof(NDIS_WLAN_BSSID_EX) - 1 + sizeof(NDIS_802_11_FIXED_IEs);
80212 + NdisMoveMemory(pBss->IEs, &pAdapter->ScanTab.BssEntry[i].FixIEs, sizeof(NDIS_802_11_FIXED_IEs));
80213 + NdisMoveMemory(pBss->IEs + sizeof(NDIS_802_11_FIXED_IEs), pAdapter->ScanTab.BssEntry[i].VarIEs, pAdapter->ScanTab.BssEntry[i].VarIELen);
80214 + pPtr += pAdapter->ScanTab.BssEntry[i].VarIELen;
80215 + }
80216 + pBss->Length = (ULONG)(sizeof(NDIS_WLAN_BSSID_EX) - 1 + sizeof(NDIS_802_11_FIXED_IEs) + pAdapter->ScanTab.BssEntry[i].VarIELen + Padding);
80217 +
80218 +#if WIRELESS_EXT < 17
80219 + if ((BssLen + pBss->Length) < wrq->u.data.length)
80220 + BssLen += pBss->Length;
80221 + else
80222 + {
80223 + pBssidList->NumberOfItems = i;
80224 + break;
80225 + }
80226 +#else
80227 + BssLen += pBss->Length;
80228 +#endif
80229 + }
80230 +
80231 +#if WIRELESS_EXT < 17
80232 + wrq->u.data.length = BssLen;
80233 +#else
80234 + if (BssLen > wrq->u.data.length)
80235 + {
80236 + kfree(pBssidList);
80237 + return -E2BIG;
80238 + }
80239 + else
80240 + wrq->u.data.length = BssLen;
80241 +#endif
80242 + Status = copy_to_user(wrq->u.data.pointer, pBssidList, BssLen);
80243 + kfree(pBssidList);
80244 + break;
80245 + case OID_802_3_CURRENT_ADDRESS:
80246 + wrq->u.data.length = MAC_ADDR_LEN;
80247 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CurrentAddress, wrq->u.data.length);
80248 + break;
80249 + case OID_GEN_MEDIA_CONNECT_STATUS:
80250 + if (pAdapter->IndicateMediaState == NdisMediaStateConnected)
80251 + MediaState = NdisMediaStateConnected;
80252 + else
80253 + MediaState = NdisMediaStateDisconnected;
80254 +
80255 + wrq->u.data.length = sizeof(NDIS_MEDIA_STATE);
80256 + Status = copy_to_user(wrq->u.data.pointer, &MediaState, wrq->u.data.length);
80257 + break;
80258 + case OID_802_11_BSSID:
80259 +#ifdef RALINK_ATE
80260 + if (ATE_ON(pAdapter))
80261 + {
80262 + DBGPRINT(RT_DEBUG_TRACE, ("The driver is in ATE mode now\n"));
80263 + Status = NDIS_STATUS_RESOURCES;
80264 + break;
80265 + }
80266 +#endif // RALINK_ATE //
80267 + if (INFRA_ON(pAdapter) || ADHOC_ON(pAdapter))
80268 + {
80269 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.Bssid, sizeof(NDIS_802_11_MAC_ADDRESS));
80270 +
80271 + }
80272 + else
80273 + {
80274 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_BSSID(=EMPTY)\n"));
80275 + Status = -ENOTCONN;
80276 + }
80277 + break;
80278 + case OID_802_11_SSID:
80279 + NdisZeroMemory(&Ssid, sizeof(NDIS_802_11_SSID));
80280 + NdisZeroMemory(Ssid.Ssid, MAX_LEN_OF_SSID);
80281 + Ssid.SsidLength = pAdapter->CommonCfg.SsidLen;
80282 + memcpy(Ssid.Ssid, pAdapter->CommonCfg.Ssid, Ssid.SsidLength);
80283 + wrq->u.data.length = sizeof(NDIS_802_11_SSID);
80284 + Status = copy_to_user(wrq->u.data.pointer, &Ssid, wrq->u.data.length);
80285 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_SSID (Len=%d, ssid=%s)\n", Ssid.SsidLength,Ssid.Ssid));
80286 + break;
80287 + case RT_OID_802_11_QUERY_LINK_STATUS:
80288 + pLinkStatus = (RT_802_11_LINK_STATUS *) kmalloc(sizeof(RT_802_11_LINK_STATUS), MEM_ALLOC_FLAG);
80289 + if (pLinkStatus)
80290 + {
80291 + pLinkStatus->CurrTxRate = RateIdTo500Kbps[pAdapter->CommonCfg.TxRate]; // unit : 500 kbps
80292 + pLinkStatus->ChannelQuality = pAdapter->Mlme.ChannelQuality;
80293 + pLinkStatus->RxByteCount = pAdapter->RalinkCounters.ReceivedByteCount;
80294 + pLinkStatus->TxByteCount = pAdapter->RalinkCounters.TransmittedByteCount;
80295 + pLinkStatus->CentralChannel = pAdapter->CommonCfg.CentralChannel;
80296 + wrq->u.data.length = sizeof(RT_802_11_LINK_STATUS);
80297 + Status = copy_to_user(wrq->u.data.pointer, pLinkStatus, wrq->u.data.length);
80298 + kfree(pLinkStatus);
80299 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_LINK_STATUS\n"));
80300 + }
80301 + else
80302 + {
80303 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_LINK_STATUS(kmalloc failed)\n"));
80304 + Status = -EFAULT;
80305 + }
80306 + break;
80307 + case OID_802_11_CONFIGURATION:
80308 + pConfiguration = (NDIS_802_11_CONFIGURATION *) kmalloc(sizeof(NDIS_802_11_CONFIGURATION), MEM_ALLOC_FLAG);
80309 + if (pConfiguration)
80310 + {
80311 + pConfiguration->Length = sizeof(NDIS_802_11_CONFIGURATION);
80312 + pConfiguration->BeaconPeriod = pAdapter->CommonCfg.BeaconPeriod;
80313 + pConfiguration->ATIMWindow = pAdapter->StaActive.AtimWin;
80314 + MAP_CHANNEL_ID_TO_KHZ(pAdapter->CommonCfg.Channel, pConfiguration->DSConfig);
80315 + wrq->u.data.length = sizeof(NDIS_802_11_CONFIGURATION);
80316 + Status = copy_to_user(wrq->u.data.pointer, pConfiguration, wrq->u.data.length);
80317 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_CONFIGURATION(BeaconPeriod=%ld,AtimW=%ld,Channel=%d) \n",
80318 + pConfiguration->BeaconPeriod, pConfiguration->ATIMWindow, pAdapter->CommonCfg.Channel));
80319 + kfree(pConfiguration);
80320 + }
80321 + else
80322 + {
80323 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_CONFIGURATION(kmalloc failed)\n"));
80324 + Status = -EFAULT;
80325 + }
80326 + break;
80327 + case RT_OID_802_11_SNR_0:
80328 + if ((pAdapter->StaCfg.LastSNR0 > 0))
80329 + {
80330 + ulInfo = ((0xeb - pAdapter->StaCfg.LastSNR0) * 3) / 16 ;
80331 + wrq->u.data.length = sizeof(ulInfo);
80332 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80333 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_SNR_0(0x=%lx)\n", ulInfo));
80334 + }
80335 + else
80336 + Status = -EFAULT;
80337 + break;
80338 + case RT_OID_802_11_SNR_1:
80339 + if ((pAdapter->Antenna.field.RxPath > 1) &&
80340 + (pAdapter->StaCfg.LastSNR1 > 0))
80341 + {
80342 + ulInfo = ((0xeb - pAdapter->StaCfg.LastSNR1) * 3) / 16 ;
80343 + wrq->u.data.length = sizeof(ulInfo);
80344 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80345 + DBGPRINT(RT_DEBUG_TRACE,("Query::RT_OID_802_11_SNR_1(0x=%lx)\n",ulInfo));
80346 + }
80347 + else
80348 + Status = -EFAULT;
80349 + DBGPRINT(RT_DEBUG_TRACE,("Query::RT_OID_802_11_SNR_1(pAdapter->StaCfg.LastSNR1=%d)\n",pAdapter->StaCfg.LastSNR1));
80350 + break;
80351 + case OID_802_11_RSSI_TRIGGER:
80352 + ulInfo = pAdapter->StaCfg.RssiSample.LastRssi0 - pAdapter->BbpRssiToDbmDelta;
80353 + wrq->u.data.length = sizeof(ulInfo);
80354 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80355 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_RSSI_TRIGGER(=%ld)\n", ulInfo));
80356 + break;
80357 + case OID_802_11_RSSI:
80358 + case RT_OID_802_11_RSSI:
80359 + ulInfo = pAdapter->StaCfg.RssiSample.LastRssi0;
80360 + wrq->u.data.length = sizeof(ulInfo);
80361 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80362 + break;
80363 + case RT_OID_802_11_RSSI_1:
80364 + ulInfo = pAdapter->StaCfg.RssiSample.LastRssi1;
80365 + wrq->u.data.length = sizeof(ulInfo);
80366 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80367 + break;
80368 + case RT_OID_802_11_RSSI_2:
80369 + ulInfo = pAdapter->StaCfg.RssiSample.LastRssi2;
80370 + wrq->u.data.length = sizeof(ulInfo);
80371 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80372 + break;
80373 + case OID_802_11_STATISTICS:
80374 + pStatistics = (NDIS_802_11_STATISTICS *) kmalloc(sizeof(NDIS_802_11_STATISTICS), MEM_ALLOC_FLAG);
80375 + if (pStatistics)
80376 + {
80377 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_STATISTICS \n"));
80378 + // add the most up-to-date h/w raw counters into software counters
80379 + NICUpdateRawCounters(pAdapter);
80380 +
80381 + // Sanity check for calculation of sucessful count
80382 + if (pAdapter->WlanCounters.TransmittedFragmentCount.QuadPart < pAdapter->WlanCounters.RetryCount.QuadPart)
80383 + pAdapter->WlanCounters.TransmittedFragmentCount.QuadPart = pAdapter->WlanCounters.RetryCount.QuadPart;
80384 +
80385 + pStatistics->TransmittedFragmentCount.QuadPart = pAdapter->WlanCounters.TransmittedFragmentCount.QuadPart;
80386 + pStatistics->MulticastTransmittedFrameCount.QuadPart = pAdapter->WlanCounters.MulticastTransmittedFrameCount.QuadPart;
80387 + pStatistics->FailedCount.QuadPart = pAdapter->WlanCounters.FailedCount.QuadPart;
80388 + pStatistics->RetryCount.QuadPart = pAdapter->WlanCounters.RetryCount.QuadPart;
80389 + pStatistics->MultipleRetryCount.QuadPart = pAdapter->WlanCounters.MultipleRetryCount.QuadPart;
80390 + pStatistics->RTSSuccessCount.QuadPart = pAdapter->WlanCounters.RTSSuccessCount.QuadPart;
80391 + pStatistics->RTSFailureCount.QuadPart = pAdapter->WlanCounters.RTSFailureCount.QuadPart;
80392 + pStatistics->ACKFailureCount.QuadPart = pAdapter->WlanCounters.ACKFailureCount.QuadPart;
80393 + pStatistics->FrameDuplicateCount.QuadPart = pAdapter->WlanCounters.FrameDuplicateCount.QuadPart;
80394 + pStatistics->ReceivedFragmentCount.QuadPart = pAdapter->WlanCounters.ReceivedFragmentCount.QuadPart;
80395 + pStatistics->MulticastReceivedFrameCount.QuadPart = pAdapter->WlanCounters.MulticastReceivedFrameCount.QuadPart;
80396 +#ifdef DBG
80397 + pStatistics->FCSErrorCount = pAdapter->RalinkCounters.RealFcsErrCount;
80398 +#else
80399 + pStatistics->FCSErrorCount.QuadPart = pAdapter->WlanCounters.FCSErrorCount.QuadPart;
80400 + pStatistics->FrameDuplicateCount.u.LowPart = pAdapter->WlanCounters.FrameDuplicateCount.u.LowPart / 100;
80401 +#endif
80402 + wrq->u.data.length = sizeof(NDIS_802_11_STATISTICS);
80403 + Status = copy_to_user(wrq->u.data.pointer, pStatistics, wrq->u.data.length);
80404 + kfree(pStatistics);
80405 + }
80406 + else
80407 + {
80408 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_STATISTICS(kmalloc failed)\n"));
80409 + Status = -EFAULT;
80410 + }
80411 + break;
80412 + case OID_GEN_RCV_OK:
80413 + ulInfo = pAdapter->Counters8023.GoodReceives;
80414 + wrq->u.data.length = sizeof(ulInfo);
80415 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80416 + break;
80417 + case OID_GEN_RCV_NO_BUFFER:
80418 + ulInfo = pAdapter->Counters8023.RxNoBuffer;
80419 + wrq->u.data.length = sizeof(ulInfo);
80420 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80421 + break;
80422 + case RT_OID_802_11_PHY_MODE:
80423 + ulInfo = (ULONG)pAdapter->CommonCfg.PhyMode;
80424 + wrq->u.data.length = sizeof(ulInfo);
80425 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80426 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_PHY_MODE (=%ld)\n", ulInfo));
80427 + break;
80428 + case RT_OID_802_11_STA_CONFIG:
80429 + pStaConfig = (RT_802_11_STA_CONFIG *) kmalloc(sizeof(RT_802_11_STA_CONFIG), MEM_ALLOC_FLAG);
80430 + if (pStaConfig)
80431 + {
80432 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_STA_CONFIG\n"));
80433 + pStaConfig->EnableTxBurst = pAdapter->CommonCfg.bEnableTxBurst;
80434 + pStaConfig->EnableTurboRate = 0;
80435 + pStaConfig->UseBGProtection = pAdapter->CommonCfg.UseBGProtection;
80436 + pStaConfig->UseShortSlotTime = pAdapter->CommonCfg.bUseShortSlotTime;
80437 + //pStaConfig->AdhocMode = pAdapter->StaCfg.AdhocMode;
80438 + pStaConfig->HwRadioStatus = (pAdapter->StaCfg.bHwRadio == TRUE) ? 1 : 0;
80439 + pStaConfig->Rsv1 = 0;
80440 + pStaConfig->SystemErrorBitmap = pAdapter->SystemErrorBitmap;
80441 + wrq->u.data.length = sizeof(RT_802_11_STA_CONFIG);
80442 + Status = copy_to_user(wrq->u.data.pointer, pStaConfig, wrq->u.data.length);
80443 + kfree(pStaConfig);
80444 + }
80445 + else
80446 + {
80447 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_STA_CONFIG(kmalloc failed)\n"));
80448 + Status = -EFAULT;
80449 + }
80450 + break;
80451 + case OID_802_11_RTS_THRESHOLD:
80452 + RtsThresh = pAdapter->CommonCfg.RtsThreshold;
80453 + wrq->u.data.length = sizeof(RtsThresh);
80454 + Status = copy_to_user(wrq->u.data.pointer, &RtsThresh, wrq->u.data.length);
80455 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_RTS_THRESHOLD(=%ld)\n", RtsThresh));
80456 + break;
80457 + case OID_802_11_FRAGMENTATION_THRESHOLD:
80458 + FragThresh = pAdapter->CommonCfg.FragmentThreshold;
80459 + if (pAdapter->CommonCfg.bUseZeroToDisableFragment == TRUE)
80460 + FragThresh = 0;
80461 + wrq->u.data.length = sizeof(FragThresh);
80462 + Status = copy_to_user(wrq->u.data.pointer, &FragThresh, wrq->u.data.length);
80463 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_FRAGMENTATION_THRESHOLD(=%ld)\n", FragThresh));
80464 + break;
80465 + case OID_802_11_POWER_MODE:
80466 + PowerMode = pAdapter->StaCfg.WindowsPowerMode;
80467 + wrq->u.data.length = sizeof(PowerMode);
80468 + Status = copy_to_user(wrq->u.data.pointer, &PowerMode, wrq->u.data.length);
80469 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_POWER_MODE(=%d)\n", PowerMode));
80470 + break;
80471 + case RT_OID_802_11_RADIO:
80472 + RadioState = (BOOLEAN) pAdapter->StaCfg.bSwRadio;
80473 + wrq->u.data.length = sizeof(RadioState);
80474 + Status = copy_to_user(wrq->u.data.pointer, &RadioState, wrq->u.data.length);
80475 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_RADIO (=%d)\n", RadioState));
80476 + break;
80477 + case OID_802_11_INFRASTRUCTURE_MODE:
80478 + if (pAdapter->StaCfg.BssType == BSS_ADHOC)
80479 + BssType = Ndis802_11IBSS;
80480 + else if (pAdapter->StaCfg.BssType == BSS_INFRA)
80481 + BssType = Ndis802_11Infrastructure;
80482 + else if (pAdapter->StaCfg.BssType == BSS_MONITOR)
80483 + BssType = Ndis802_11Monitor;
80484 + else
80485 + BssType = Ndis802_11AutoUnknown;
80486 +
80487 + wrq->u.data.length = sizeof(BssType);
80488 + Status = copy_to_user(wrq->u.data.pointer, &BssType, wrq->u.data.length);
80489 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_INFRASTRUCTURE_MODE(=%d)\n", BssType));
80490 + break;
80491 + case RT_OID_802_11_PREAMBLE:
80492 + PreamType = pAdapter->CommonCfg.TxPreamble;
80493 + wrq->u.data.length = sizeof(PreamType);
80494 + Status = copy_to_user(wrq->u.data.pointer, &PreamType, wrq->u.data.length);
80495 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_PREAMBLE(=%d)\n", PreamType));
80496 + break;
80497 + case OID_802_11_AUTHENTICATION_MODE:
80498 + AuthMode = pAdapter->StaCfg.AuthMode;
80499 + wrq->u.data.length = sizeof(AuthMode);
80500 + Status = copy_to_user(wrq->u.data.pointer, &AuthMode, wrq->u.data.length);
80501 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_AUTHENTICATION_MODE(=%d)\n", AuthMode));
80502 + break;
80503 + case OID_802_11_WEP_STATUS:
80504 + WepStatus = pAdapter->StaCfg.WepStatus;
80505 + wrq->u.data.length = sizeof(WepStatus);
80506 + Status = copy_to_user(wrq->u.data.pointer, &WepStatus, wrq->u.data.length);
80507 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_WEP_STATUS(=%d)\n", WepStatus));
80508 + break;
80509 + case OID_802_11_TX_POWER_LEVEL:
80510 + wrq->u.data.length = sizeof(ULONG);
80511 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.TxPower, wrq->u.data.length);
80512 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_TX_POWER_LEVEL %x\n",pAdapter->CommonCfg.TxPower));
80513 + break;
80514 + case RT_OID_802_11_TX_POWER_LEVEL_1:
80515 + wrq->u.data.length = sizeof(ULONG);
80516 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.TxPowerPercentage, wrq->u.data.length);
80517 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_TX_POWER_LEVEL_1 (=%ld)\n", pAdapter->CommonCfg.TxPowerPercentage));
80518 + break;
80519 + case OID_802_11_NETWORK_TYPES_SUPPORTED:
80520 + if ((pAdapter->RfIcType == RFIC_2850) || (pAdapter->RfIcType == RFIC_2750))
80521 + {
80522 + NetworkTypeList[0] = 3; // NumberOfItems = 3
80523 + NetworkTypeList[1] = Ndis802_11DS; // NetworkType[1] = 11b
80524 + NetworkTypeList[2] = Ndis802_11OFDM24; // NetworkType[2] = 11g
80525 + NetworkTypeList[3] = Ndis802_11OFDM5; // NetworkType[3] = 11a
80526 + wrq->u.data.length = 16;
80527 + Status = copy_to_user(wrq->u.data.pointer, &NetworkTypeList[0], wrq->u.data.length);
80528 + }
80529 + else
80530 + {
80531 + NetworkTypeList[0] = 2; // NumberOfItems = 2
80532 + NetworkTypeList[1] = Ndis802_11DS; // NetworkType[1] = 11b
80533 + NetworkTypeList[2] = Ndis802_11OFDM24; // NetworkType[2] = 11g
80534 + wrq->u.data.length = 12;
80535 + Status = copy_to_user(wrq->u.data.pointer, &NetworkTypeList[0], wrq->u.data.length);
80536 + }
80537 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_NETWORK_TYPES_SUPPORTED\n"));
80538 + break;
80539 + case OID_802_11_NETWORK_TYPE_IN_USE:
80540 + wrq->u.data.length = sizeof(ULONG);
80541 + if (pAdapter->CommonCfg.PhyMode == PHY_11A)
80542 + ulInfo = Ndis802_11OFDM5;
80543 + else if ((pAdapter->CommonCfg.PhyMode == PHY_11BG_MIXED) || (pAdapter->CommonCfg.PhyMode == PHY_11G))
80544 + ulInfo = Ndis802_11OFDM24;
80545 + else
80546 + ulInfo = Ndis802_11DS;
80547 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80548 + break;
80549 + case RT_OID_802_11_QUERY_LAST_RX_RATE:
80550 + ulInfo = (ULONG)pAdapter->LastRxRate;
80551 + wrq->u.data.length = sizeof(ulInfo);
80552 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80553 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_LAST_RX_RATE (=%ld)\n", ulInfo));
80554 + break;
80555 + case RT_OID_802_11_QUERY_LAST_TX_RATE:
80556 + //ulInfo = (ULONG)pAdapter->LastTxRate;
80557 + ulInfo = (ULONG)pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.word;
80558 + wrq->u.data.length = sizeof(ulInfo);
80559 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80560 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_LAST_TX_RATE (=%lx)\n", ulInfo));
80561 + break;
80562 + case RT_OID_802_11_QUERY_EEPROM_VERSION:
80563 + wrq->u.data.length = sizeof(ULONG);
80564 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->EepromVersion, wrq->u.data.length);
80565 + break;
80566 + case RT_OID_802_11_QUERY_FIRMWARE_VERSION:
80567 + wrq->u.data.length = sizeof(ULONG);
80568 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->FirmwareVersion, wrq->u.data.length);
80569 + break;
80570 + case RT_OID_802_11_QUERY_NOISE_LEVEL:
80571 + wrq->u.data.length = sizeof(UCHAR);
80572 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->BbpWriteLatch[66], wrq->u.data.length);
80573 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_NOISE_LEVEL (=%d)\n", pAdapter->BbpWriteLatch[66]));
80574 + break;
80575 + case RT_OID_802_11_EXTRA_INFO:
80576 + wrq->u.data.length = sizeof(ULONG);
80577 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->ExtraInfo, wrq->u.data.length);
80578 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_EXTRA_INFO (=%ld)\n", pAdapter->ExtraInfo));
80579 + break;
80580 + case RT_OID_WE_VERSION_COMPILED:
80581 + wrq->u.data.length = sizeof(UINT);
80582 + we_version_compiled = WIRELESS_EXT;
80583 + Status = copy_to_user(wrq->u.data.pointer, &we_version_compiled, wrq->u.data.length);
80584 + break;
80585 + case RT_OID_802_11_QUERY_APSD_SETTING:
80586 + apsd = (pAdapter->CommonCfg.bAPSDCapable | (pAdapter->CommonCfg.bAPSDAC_BE << 1) | (pAdapter->CommonCfg.bAPSDAC_BK << 2)
80587 + | (pAdapter->CommonCfg.bAPSDAC_VI << 3) | (pAdapter->CommonCfg.bAPSDAC_VO << 4) | (pAdapter->CommonCfg.MaxSPLength << 5));
80588 +
80589 + wrq->u.data.length = sizeof(ULONG);
80590 + Status = copy_to_user(wrq->u.data.pointer, &apsd, wrq->u.data.length);
80591 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_APSD_SETTING (=0x%lx,APSDCap=%d,AC_BE=%d,AC_BK=%d,AC_VI=%d,AC_VO=%d,MAXSPLen=%d)\n",
80592 + apsd,pAdapter->CommonCfg.bAPSDCapable,pAdapter->CommonCfg.bAPSDAC_BE,pAdapter->CommonCfg.bAPSDAC_BK,pAdapter->CommonCfg.bAPSDAC_VI,pAdapter->CommonCfg.bAPSDAC_VO,pAdapter->CommonCfg.MaxSPLength));
80593 + break;
80594 + case RT_OID_802_11_QUERY_APSD_PSM:
80595 + wrq->u.data.length = sizeof(ULONG);
80596 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.bAPSDForcePowerSave, wrq->u.data.length);
80597 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_APSD_PSM (=%d)\n", pAdapter->CommonCfg.bAPSDForcePowerSave));
80598 + break;
80599 + case RT_OID_802_11_QUERY_WMM:
80600 + wrq->u.data.length = sizeof(BOOLEAN);
80601 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.bWmmCapable, wrq->u.data.length);
80602 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_WMM (=%d)\n", pAdapter->CommonCfg.bWmmCapable));
80603 + break;
80604 +#ifdef WPA_SUPPLICANT_SUPPORT
80605 + case RT_OID_NEW_DRIVER:
80606 + {
80607 + UCHAR enabled = 1;
80608 + wrq->u.data.length = sizeof(UCHAR);
80609 + Status = copy_to_user(wrq->u.data.pointer, &enabled, wrq->u.data.length);
80610 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_NEW_DRIVER (=%d)\n", enabled));
80611 + }
80612 + break;
80613 + case RT_OID_WPA_SUPPLICANT_SUPPORT:
80614 + wrq->u.data.length = sizeof(UCHAR);
80615 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->StaCfg.WpaSupplicantUP, wrq->u.data.length);
80616 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_WPA_SUPPLICANT_SUPPORT (=%d)\n", pAdapter->StaCfg.WpaSupplicantUP));
80617 + break;
80618 +#endif // WPA_SUPPLICANT_SUPPORT //
80619 +
80620 + case RT_OID_DRIVER_DEVICE_NAME:
80621 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_DRIVER_DEVICE_NAME \n"));
80622 + wrq->u.data.length = 16;
80623 + if (copy_to_user(wrq->u.data.pointer, pAdapter->StaCfg.dev_name, wrq->u.data.length))
80624 + {
80625 + Status = -EFAULT;
80626 + }
80627 + break;
80628 + case RT_OID_802_11_QUERY_HT_PHYMODE:
80629 + pHTPhyMode = (OID_SET_HT_PHYMODE *) kmalloc(sizeof(OID_SET_HT_PHYMODE), MEM_ALLOC_FLAG);
80630 + if (pHTPhyMode)
80631 + {
80632 + pHTPhyMode->PhyMode = pAdapter->CommonCfg.PhyMode;
80633 + pHTPhyMode->HtMode = (UCHAR)pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.field.MODE;
80634 + pHTPhyMode->BW = (UCHAR)pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.field.BW;
80635 + pHTPhyMode->MCS= (UCHAR)pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.field.MCS;
80636 + pHTPhyMode->SHORTGI= (UCHAR)pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.field.ShortGI;
80637 + pHTPhyMode->STBC= (UCHAR)pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.field.STBC;
80638 +
80639 + pHTPhyMode->ExtOffset = ((pAdapter->CommonCfg.CentralChannel < pAdapter->CommonCfg.Channel) ? (EXTCHA_BELOW) : (EXTCHA_ABOVE));
80640 + wrq->u.data.length = sizeof(OID_SET_HT_PHYMODE);
80641 + if (copy_to_user(wrq->u.data.pointer, pHTPhyMode, wrq->u.data.length))
80642 + {
80643 + Status = -EFAULT;
80644 + }
80645 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_HT_PHYMODE (PhyMode = %d, MCS =%d, BW = %d, STBC = %d, ExtOffset=%d)\n",
80646 + pHTPhyMode->HtMode, pHTPhyMode->MCS, pHTPhyMode->BW, pHTPhyMode->STBC, pHTPhyMode->ExtOffset));
80647 + DBGPRINT(RT_DEBUG_TRACE, (" MlmeUpdateTxRates (.word = %x )\n", pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.word));
80648 + }
80649 + else
80650 + {
80651 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_STA_CONFIG(kmalloc failed)\n"));
80652 + Status = -EFAULT;
80653 + }
80654 + break;
80655 + case RT_OID_802_11_COUNTRY_REGION:
80656 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_COUNTRY_REGION \n"));
80657 + wrq->u.data.length = sizeof(ulInfo);
80658 + ulInfo = pAdapter->CommonCfg.CountryRegionForABand;
80659 + ulInfo = (ulInfo << 8)|(pAdapter->CommonCfg.CountryRegion);
80660 + if (copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length))
80661 + {
80662 + Status = -EFAULT;
80663 + }
80664 + break;
80665 + case RT_OID_802_11_QUERY_DAT_HT_PHYMODE:
80666 + pHTPhyMode = (OID_SET_HT_PHYMODE *) kmalloc(sizeof(OID_SET_HT_PHYMODE), MEM_ALLOC_FLAG);
80667 + if (pHTPhyMode)
80668 + {
80669 + pHTPhyMode->PhyMode = pAdapter->CommonCfg.PhyMode;
80670 + pHTPhyMode->HtMode = (UCHAR)pAdapter->CommonCfg.RegTransmitSetting.field.HTMODE;
80671 + pHTPhyMode->BW = (UCHAR)pAdapter->CommonCfg.RegTransmitSetting.field.BW;
80672 + pHTPhyMode->MCS= (UCHAR)pAdapter->StaCfg.DesiredTransmitSetting.field.MCS;
80673 + pHTPhyMode->SHORTGI= (UCHAR)pAdapter->CommonCfg.RegTransmitSetting.field.ShortGI;
80674 + pHTPhyMode->STBC= (UCHAR)pAdapter->CommonCfg.RegTransmitSetting.field.STBC;
80675 +
80676 + wrq->u.data.length = sizeof(OID_SET_HT_PHYMODE);
80677 + if (copy_to_user(wrq->u.data.pointer, pHTPhyMode, wrq->u.data.length))
80678 + {
80679 + Status = -EFAULT;
80680 + }
80681 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_HT_PHYMODE (PhyMode = %d, MCS =%d, BW = %d, STBC = %d, ExtOffset=%d)\n",
80682 + pHTPhyMode->HtMode, pHTPhyMode->MCS, pHTPhyMode->BW, pHTPhyMode->STBC, pHTPhyMode->ExtOffset));
80683 + DBGPRINT(RT_DEBUG_TRACE, (" MlmeUpdateTxRates (.word = %x )\n", pAdapter->MacTab.Content[BSSID_WCID].HTPhyMode.word));
80684 + }
80685 + else
80686 + {
80687 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_STA_CONFIG(kmalloc failed)\n"));
80688 + Status = -EFAULT;
80689 + }
80690 + break;
80691 + case RT_OID_QUERY_MULTIPLE_CARD_SUPPORT:
80692 + wrq->u.data.length = sizeof(UCHAR);
80693 + i = 0;
80694 +#ifdef MULTIPLE_CARD_SUPPORT
80695 + i = 1;
80696 +#endif // MULTIPLE_CARD_SUPPORT //
80697 + if (copy_to_user(wrq->u.data.pointer, &i, wrq->u.data.length))
80698 + {
80699 + Status = -EFAULT;
80700 + }
80701 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_QUERY_MULTIPLE_CARD_SUPPORT(=%d) \n", i));
80702 + break;
80703 +#ifdef SNMP_SUPPORT
80704 + case RT_OID_802_11_MAC_ADDRESS:
80705 + wrq->u.data.length = MAC_ADDR_LEN;
80706 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CurrentAddress, wrq->u.data.length);
80707 + break;
80708 +
80709 + case RT_OID_802_11_MANUFACTUREROUI:
80710 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_MANUFACTUREROUI \n"));
80711 + wrq->u.data.length = ManufacturerOUI_LEN;
80712 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CurrentAddress, wrq->u.data.length);
80713 + break;
80714 +
80715 + case RT_OID_802_11_MANUFACTURERNAME:
80716 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_MANUFACTURERNAME \n"));
80717 + wrq->u.data.length = strlen(ManufacturerNAME);
80718 + Status = copy_to_user(wrq->u.data.pointer, ManufacturerNAME, wrq->u.data.length);
80719 + break;
80720 +
80721 + case RT_OID_802_11_RESOURCETYPEIDNAME:
80722 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_RESOURCETYPEIDNAME \n"));
80723 + wrq->u.data.length = strlen(ResourceTypeIdName);
80724 + Status = copy_to_user(wrq->u.data.pointer, ResourceTypeIdName, wrq->u.data.length);
80725 + break;
80726 +
80727 + case RT_OID_802_11_PRIVACYOPTIONIMPLEMENTED:
80728 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_PRIVACYOPTIONIMPLEMENTED \n"));
80729 + ulInfo = 1; // 1 is support wep else 2 is not support.
80730 + wrq->u.data.length = sizeof(ulInfo);
80731 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80732 + break;
80733 +
80734 + case RT_OID_802_11_POWERMANAGEMENTMODE:
80735 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_POWERMANAGEMENTMODE \n"));
80736 + if (pAdapter->StaCfg.Psm == PSMP_ACTION)
80737 + ulInfo = 1; // 1 is power active else 2 is power save.
80738 + else
80739 + ulInfo = 2;
80740 +
80741 + wrq->u.data.length = sizeof(ulInfo);
80742 + Status = copy_to_user(wrq->u.data.pointer, &ulInfo, wrq->u.data.length);
80743 + break;
80744 +
80745 + case OID_802_11_WEPDEFAULTKEYVALUE:
80746 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_WEPDEFAULTKEYVALUE \n"));
80747 + //KeyIdxValue.KeyIdx = pAd->PortCfg.MBSSID[pAd->IoctlIF].DefaultKeyId;
80748 + pKeyIdxValue = wrq->u.data.pointer;
80749 + DBGPRINT(RT_DEBUG_TRACE,("KeyIdxValue.KeyIdx = %d, \n",pKeyIdxValue->KeyIdx));
80750 + valueLen = pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].KeyLen;
80751 + NdisMoveMemory(pKeyIdxValue->Value,
80752 + &pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].Key,
80753 + valueLen);
80754 + pKeyIdxValue->Value[valueLen]='\0';
80755 +
80756 + wrq->u.data.length = sizeof(DefaultKeyIdxValue);
80757 +
80758 + Status = copy_to_user(wrq->u.data.pointer, pKeyIdxValue, wrq->u.data.length);
80759 + DBGPRINT(RT_DEBUG_TRACE,("DefaultKeyId = %d, total len = %d, str len=%d, KeyValue= %02x %02x %02x %02x \n", pAdapter->StaCfg.DefaultKeyId, wrq->u.data.length, pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].KeyLen,
80760 + pAdapter->SharedKey[BSS0][0].Key[0],
80761 + pAdapter->SharedKey[BSS0][1].Key[0],
80762 + pAdapter->SharedKey[BSS0][2].Key[0],
80763 + pAdapter->SharedKey[BSS0][3].Key[0]));
80764 + break;
80765 +
80766 + case OID_802_11_WEPDEFAULTKEYID:
80767 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_WEPDEFAULTKEYID \n"));
80768 + wrq->u.data.length = sizeof(UCHAR);
80769 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->StaCfg.DefaultKeyId, wrq->u.data.length);
80770 + DBGPRINT(RT_DEBUG_TRACE, ("DefaultKeyId =%d \n", pAdapter->StaCfg.DefaultKeyId));
80771 + break;
80772 +
80773 + case RT_OID_802_11_WEPKEYMAPPINGLENGTH:
80774 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_WEPKEYMAPPINGLENGTH \n"));
80775 + wrq->u.data.length = sizeof(UCHAR);
80776 + Status = copy_to_user(wrq->u.data.pointer,
80777 + &pAdapter->SharedKey[BSS0][pAdapter->StaCfg.DefaultKeyId].KeyLen,
80778 + wrq->u.data.length);
80779 + break;
80780 +
80781 + case OID_802_11_SHORTRETRYLIMIT:
80782 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_SHORTRETRYLIMIT \n"));
80783 + wrq->u.data.length = sizeof(ULONG);
80784 + RTMP_IO_READ32(pAdapter, TX_RTY_CFG, &tx_rty_cfg.word);
80785 + ShortRetryLimit = tx_rty_cfg.field.ShortRtyLimit;
80786 + DBGPRINT(RT_DEBUG_TRACE, ("ShortRetryLimit =%ld, tx_rty_cfg.field.ShortRetryLimit=%d\n", ShortRetryLimit, tx_rty_cfg.field.ShortRtyLimit));
80787 + Status = copy_to_user(wrq->u.data.pointer, &ShortRetryLimit, wrq->u.data.length);
80788 + break;
80789 +
80790 + case OID_802_11_LONGRETRYLIMIT:
80791 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_LONGRETRYLIMIT \n"));
80792 + wrq->u.data.length = sizeof(ULONG);
80793 + RTMP_IO_READ32(pAdapter, TX_RTY_CFG, &tx_rty_cfg.word);
80794 + LongRetryLimit = tx_rty_cfg.field.LongRtyLimit;
80795 + DBGPRINT(RT_DEBUG_TRACE, ("LongRetryLimit =%ld, tx_rty_cfg.field.LongRtyLimit=%d\n", LongRetryLimit, tx_rty_cfg.field.LongRtyLimit));
80796 + Status = copy_to_user(wrq->u.data.pointer, &LongRetryLimit, wrq->u.data.length);
80797 + break;
80798 +
80799 + case RT_OID_802_11_PRODUCTID:
80800 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_PRODUCTID \n"));
80801 +
80802 +#ifdef RT2860
80803 + {
80804 +
80805 + USHORT device_id;
80806 + if (((POS_COOKIE)pAdapter->OS_Cookie)->pci_dev != NULL)
80807 + pci_read_config_word(((POS_COOKIE)pAdapter->OS_Cookie)->pci_dev, PCI_DEVICE_ID, &device_id);
80808 + else
80809 + DBGPRINT(RT_DEBUG_TRACE, (" pci_dev = NULL\n"));
80810 + sprintf(tmp, "%04x %04x\n", NIC_PCI_VENDOR_ID, device_id);
80811 + }
80812 +#endif // RT2860 //
80813 + wrq->u.data.length = strlen(tmp);
80814 + Status = copy_to_user(wrq->u.data.pointer, tmp, wrq->u.data.length);
80815 + break;
80816 +
80817 + case RT_OID_802_11_MANUFACTUREID:
80818 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_MANUFACTUREID \n"));
80819 + wrq->u.data.length = strlen(ManufacturerNAME);
80820 + Status = copy_to_user(wrq->u.data.pointer, ManufacturerNAME, wrq->u.data.length);
80821 + break;
80822 +
80823 + case OID_802_11_CURRENTCHANNEL:
80824 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_CURRENTCHANNEL \n"));
80825 + wrq->u.data.length = sizeof(UCHAR);
80826 + DBGPRINT(RT_DEBUG_TRACE, ("sizeof UCHAR=%d, channel=%d \n", sizeof(UCHAR), pAdapter->CommonCfg.Channel));
80827 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.Channel, wrq->u.data.length);
80828 + DBGPRINT(RT_DEBUG_TRACE, ("Status=%d\n", Status));
80829 + break;
80830 +#endif //SNMP_SUPPORT
80831 +
80832 + case OID_802_11_BUILD_CHANNEL_EX:
80833 + {
80834 + UCHAR value;
80835 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_BUILD_CHANNEL_EX \n"));
80836 + wrq->u.data.length = sizeof(UCHAR);
80837 +#ifdef EXT_BUILD_CHANNEL_LIST
80838 + DBGPRINT(RT_DEBUG_TRACE, ("Support EXT_BUILD_CHANNEL_LIST.\n"));
80839 + value = 1;
80840 +#else
80841 + DBGPRINT(RT_DEBUG_TRACE, ("Doesn't support EXT_BUILD_CHANNEL_LIST.\n"));
80842 + value = 0;
80843 +#endif // EXT_BUILD_CHANNEL_LIST //
80844 + Status = copy_to_user(wrq->u.data.pointer, &value, 1);
80845 + DBGPRINT(RT_DEBUG_TRACE, ("Status=%d\n", Status));
80846 + }
80847 + break;
80848 +
80849 + case OID_802_11_GET_CH_LIST:
80850 + {
80851 + PRT_CHANNEL_LIST_INFO pChListBuf;
80852 +
80853 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_GET_CH_LIST \n"));
80854 + if (pAdapter->ChannelListNum == 0)
80855 + {
80856 + wrq->u.data.length = 0;
80857 + break;
80858 + }
80859 +
80860 + pChListBuf = (RT_CHANNEL_LIST_INFO *) kmalloc(sizeof(RT_CHANNEL_LIST_INFO), MEM_ALLOC_FLAG);
80861 + if (pChListBuf == NULL)
80862 + {
80863 + wrq->u.data.length = 0;
80864 + break;
80865 + }
80866 +
80867 + pChListBuf->ChannelListNum = pAdapter->ChannelListNum;
80868 + for (i = 0; i < pChListBuf->ChannelListNum; i++)
80869 + pChListBuf->ChannelList[i] = pAdapter->ChannelList[i].Channel;
80870 +
80871 + wrq->u.data.length = sizeof(RT_CHANNEL_LIST_INFO);
80872 + Status = copy_to_user(wrq->u.data.pointer, pChListBuf, sizeof(RT_CHANNEL_LIST_INFO));
80873 + DBGPRINT(RT_DEBUG_TRACE, ("Status=%d\n", Status));
80874 +
80875 + if (pChListBuf)
80876 + kfree(pChListBuf);
80877 + }
80878 + break;
80879 +
80880 + case OID_802_11_GET_COUNTRY_CODE:
80881 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_GET_COUNTRY_CODE \n"));
80882 + wrq->u.data.length = 2;
80883 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.CountryCode, 2);
80884 + DBGPRINT(RT_DEBUG_TRACE, ("Status=%d\n", Status));
80885 + break;
80886 +
80887 + case OID_802_11_GET_CHANNEL_GEOGRAPHY:
80888 + DBGPRINT(RT_DEBUG_TRACE, ("Query::OID_802_11_GET_CHANNEL_GEOGRAPHY \n"));
80889 + wrq->u.data.length = 1;
80890 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.Geography, 1);
80891 + DBGPRINT(RT_DEBUG_TRACE, ("Status=%d\n", Status));
80892 + break;
80893 +
80894 +
80895 +#ifdef QOS_DLS_SUPPORT
80896 + case RT_OID_802_11_QUERY_DLS:
80897 + wrq->u.data.length = sizeof(BOOLEAN);
80898 + Status = copy_to_user(wrq->u.data.pointer, &pAdapter->CommonCfg.bDLSCapable, wrq->u.data.length);
80899 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_DLS(=%d)\n", pAdapter->CommonCfg.bDLSCapable));
80900 + break;
80901 +
80902 + case RT_OID_802_11_QUERY_DLS_PARAM:
80903 + {
80904 + PRT_802_11_DLS_INFO pDlsInfo = kmalloc(sizeof(RT_802_11_DLS_INFO), GFP_ATOMIC);
80905 + if (pDlsInfo == NULL)
80906 + break;
80907 +
80908 + for (i=0; i<MAX_NUM_OF_DLS_ENTRY; i++)
80909 + {
80910 + RTMPMoveMemory(&pDlsInfo->Entry[i], &pAdapter->StaCfg.DLSEntry[i], sizeof(RT_802_11_DLS_UI));
80911 + }
80912 +
80913 + pDlsInfo->num = MAX_NUM_OF_DLS_ENTRY;
80914 + wrq->u.data.length = sizeof(RT_802_11_DLS_INFO);
80915 + Status = copy_to_user(wrq->u.data.pointer, pDlsInfo, wrq->u.data.length);
80916 + DBGPRINT(RT_DEBUG_TRACE, ("Query::RT_OID_802_11_QUERY_DLS_PARAM\n"));
80917 +
80918 + if (pDlsInfo)
80919 + kfree(pDlsInfo);
80920 + }
80921 + break;
80922 +#endif // QOS_DLS_SUPPORT //
80923 + default:
80924 + DBGPRINT(RT_DEBUG_TRACE, ("Query::unknown IOCTL's subcmd = 0x%08x\n", cmd));
80925 + Status = -EOPNOTSUPP;
80926 + break;
80927 + }
80928 + return Status;
80929 +}
80930 +
80931 +INT rt28xx_sta_ioctl(
80932 + IN struct net_device *net_dev,
80933 + IN OUT struct ifreq *rq,
80934 + IN INT cmd)
80935 +{
80936 + POS_COOKIE pObj;
80937 + VIRTUAL_ADAPTER *pVirtualAd = NULL;
80938 + RTMP_ADAPTER *pAd = NULL;
80939 + struct iwreq *wrq = (struct iwreq *) rq;
80940 + BOOLEAN StateMachineTouched = FALSE;
80941 + INT Status = NDIS_STATUS_SUCCESS;
80942 + USHORT subcmd;
80943 +
80944 + if (net_dev->priv_flags == INT_MAIN)
80945 + {
80946 + pAd = net_dev->priv;
80947 + }
80948 + else
80949 + {
80950 + pVirtualAd = net_dev->priv;
80951 + pAd = pVirtualAd->RtmpDev->priv;
80952 + }
80953 + pObj = (POS_COOKIE) pAd->OS_Cookie;
80954 +
80955 + if (pAd == NULL)
80956 + {
80957 + /* if 1st open fail, pAd will be free;
80958 + So the net_dev->priv will be NULL in 2rd open */
80959 + return -ENETDOWN;
80960 + }
80961 +
80962 + //check if the interface is down
80963 + if(!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_INTERRUPT_IN_USE))
80964 + {
80965 +#ifdef CONFIG_APSTA_MIXED_SUPPORT
80966 + if (wrq->u.data.pointer == NULL)
80967 + {
80968 + return Status;
80969 + }
80970 +
80971 + if (strstr(wrq->u.data.pointer, "OpMode") == NULL)
80972 +#endif // CONFIG_APSTA_MIXED_SUPPORT //
80973 + {
80974 + DBGPRINT(RT_DEBUG_TRACE, ("INFO::Network is down!\n"));
80975 + return -ENETDOWN;
80976 + }
80977 + }
80978 +
80979 + { // determine this ioctl command is comming from which interface.
80980 + pObj->ioctl_if_type = INT_MAIN;
80981 + pObj->ioctl_if = MAIN_MBSSID;
80982 + }
80983 +
80984 + switch(cmd)
80985 + {
80986 +#ifdef RALINK_ATE
80987 +#ifdef RALINK_28xx_QA
80988 + case RTPRIV_IOCTL_ATE:
80989 + {
80990 + RtmpDoAte(pAd, wrq);
80991 + }
80992 + break;
80993 +#endif // RALINK_28xx_QA //
80994 +#endif // RALINK_ATE //
80995 + case SIOCGIFHWADDR:
80996 + DBGPRINT(RT_DEBUG_TRACE, ("IOCTL::SIOCGIFHWADDR\n"));
80997 + memcpy(wrq->u.name, pAd->CurrentAddress, ETH_ALEN);
80998 + break;
80999 + case SIOCGIWNAME:
81000 + {
81001 + char *name=&wrq->u.name[0];
81002 + rt_ioctl_giwname(net_dev, NULL, name, NULL);
81003 + break;
81004 + }
81005 + case SIOCGIWESSID: //Get ESSID
81006 + {
81007 + struct iw_point *essid=&wrq->u.essid;
81008 + rt_ioctl_giwessid(net_dev, NULL, essid, essid->pointer);
81009 + break;
81010 + }
81011 + case SIOCSIWESSID: //Set ESSID
81012 + {
81013 + struct iw_point *essid=&wrq->u.essid;
81014 + rt_ioctl_siwessid(net_dev, NULL, essid, essid->pointer);
81015 + break;
81016 + }
81017 + case SIOCSIWNWID: // set network id (the cell)
81018 + case SIOCGIWNWID: // get network id
81019 + Status = -EOPNOTSUPP;
81020 + break;
81021 + case SIOCSIWFREQ: //set channel/frequency (Hz)
81022 + {
81023 + struct iw_freq *freq=&wrq->u.freq;
81024 + rt_ioctl_siwfreq(net_dev, NULL, freq, NULL);
81025 + break;
81026 + }
81027 + case SIOCGIWFREQ: // get channel/frequency (Hz)
81028 + {
81029 + struct iw_freq *freq=&wrq->u.freq;
81030 + rt_ioctl_giwfreq(net_dev, NULL, freq, NULL);
81031 + break;
81032 + }
81033 + case SIOCSIWNICKN: //set node name/nickname
81034 + {
81035 + struct iw_point *data=&wrq->u.data;
81036 + rt_ioctl_siwnickn(net_dev, NULL, data, NULL);
81037 + break;
81038 + }
81039 + case SIOCGIWNICKN: //get node name/nickname
81040 + {
81041 + struct iw_point *data=&wrq->u.data;
81042 + rt_ioctl_giwnickn(net_dev, NULL, data, NULL);
81043 + break;
81044 + }
81045 + case SIOCGIWRATE: //get default bit rate (bps)
81046 + rt_ioctl_giwrate(net_dev, NULL, &wrq->u, NULL);
81047 + break;
81048 + case SIOCSIWRATE: //set default bit rate (bps)
81049 + rt_ioctl_siwrate(net_dev, NULL, &wrq->u, NULL);
81050 + break;
81051 + case SIOCGIWRTS: // get RTS/CTS threshold (bytes)
81052 + {
81053 + struct iw_param *rts=&wrq->u.rts;
81054 + rt_ioctl_giwrts(net_dev, NULL, rts, NULL);
81055 + break;
81056 + }
81057 + case SIOCSIWRTS: //set RTS/CTS threshold (bytes)
81058 + {
81059 + struct iw_param *rts=&wrq->u.rts;
81060 + rt_ioctl_siwrts(net_dev, NULL, rts, NULL);
81061 + break;
81062 + }
81063 + case SIOCGIWFRAG: //get fragmentation thr (bytes)
81064 + {
81065 + struct iw_param *frag=&wrq->u.frag;
81066 + rt_ioctl_giwfrag(net_dev, NULL, frag, NULL);
81067 + break;
81068 + }
81069 + case SIOCSIWFRAG: //set fragmentation thr (bytes)
81070 + {
81071 + struct iw_param *frag=&wrq->u.frag;
81072 + rt_ioctl_siwfrag(net_dev, NULL, frag, NULL);
81073 + break;
81074 + }
81075 + case SIOCGIWENCODE: //get encoding token & mode
81076 + {
81077 + struct iw_point *erq=&wrq->u.encoding;
81078 + if(erq->pointer)
81079 + rt_ioctl_giwencode(net_dev, NULL, erq, erq->pointer);
81080 + break;
81081 + }
81082 + case SIOCSIWENCODE: //set encoding token & mode
81083 + {
81084 + struct iw_point *erq=&wrq->u.encoding;
81085 + if(erq->pointer)
81086 + rt_ioctl_siwencode(net_dev, NULL, erq, erq->pointer);
81087 + break;
81088 + }
81089 + case SIOCGIWAP: //get access point MAC addresses
81090 + {
81091 + struct sockaddr *ap_addr=&wrq->u.ap_addr;
81092 + rt_ioctl_giwap(net_dev, NULL, ap_addr, ap_addr->sa_data);
81093 + break;
81094 + }
81095 + case SIOCSIWAP: //set access point MAC addresses
81096 + {
81097 + struct sockaddr *ap_addr=&wrq->u.ap_addr;
81098 + rt_ioctl_siwap(net_dev, NULL, ap_addr, ap_addr->sa_data);
81099 + break;
81100 + }
81101 + case SIOCGIWMODE: //get operation mode
81102 + {
81103 + __u32 *mode=&wrq->u.mode;
81104 + rt_ioctl_giwmode(net_dev, NULL, mode, NULL);
81105 + break;
81106 + }
81107 + case SIOCSIWMODE: //set operation mode
81108 + {
81109 + __u32 *mode=&wrq->u.mode;
81110 + rt_ioctl_siwmode(net_dev, NULL, mode, NULL);
81111 + break;
81112 + }
81113 + case SIOCGIWSENS: //get sensitivity (dBm)
81114 + case SIOCSIWSENS: //set sensitivity (dBm)
81115 + case SIOCGIWPOWER: //get Power Management settings
81116 + case SIOCSIWPOWER: //set Power Management settings
81117 + case SIOCGIWTXPOW: //get transmit power (dBm)
81118 + case SIOCSIWTXPOW: //set transmit power (dBm)
81119 + case SIOCGIWRANGE: //Get range of parameters
81120 + case SIOCGIWRETRY: //get retry limits and lifetime
81121 + case SIOCSIWRETRY: //set retry limits and lifetime
81122 + Status = -EOPNOTSUPP;
81123 + break;
81124 + case RT_PRIV_IOCTL:
81125 + subcmd = wrq->u.data.flags;
81126 + if( subcmd & OID_GET_SET_TOGGLE)
81127 + Status = RTMPSetInformation(pAd, rq, subcmd);
81128 + else
81129 + Status = RTMPQueryInformation(pAd, rq, subcmd);
81130 + break;
81131 + case SIOCGIWPRIV:
81132 + if (wrq->u.data.pointer)
81133 + {
81134 + if ( access_ok(VERIFY_WRITE, wrq->u.data.pointer, sizeof(privtab)) != TRUE)
81135 + break;
81136 + wrq->u.data.length = sizeof(privtab) / sizeof(privtab[0]);
81137 + if (copy_to_user(wrq->u.data.pointer, privtab, sizeof(privtab)))
81138 + Status = -EFAULT;
81139 + }
81140 + break;
81141 + case RTPRIV_IOCTL_SET:
81142 + if(access_ok(VERIFY_READ, wrq->u.data.pointer, wrq->u.data.length) != TRUE)
81143 + break;
81144 + rt_ioctl_setparam(net_dev, NULL, NULL, wrq->u.data.pointer);
81145 + break;
81146 + case RTPRIV_IOCTL_GSITESURVEY:
81147 + RTMPIoctlGetSiteSurvey(pAd, wrq);
81148 + break;
81149 +#ifdef DBG
81150 + case RTPRIV_IOCTL_MAC:
81151 + RTMPIoctlMAC(pAd, wrq);
81152 + break;
81153 + case RTPRIV_IOCTL_E2P:
81154 + RTMPIoctlE2PROM(pAd, wrq);
81155 + break;
81156 +#endif // DBG //
81157 + case SIOCETHTOOL:
81158 + break;
81159 + default:
81160 + DBGPRINT(RT_DEBUG_ERROR, ("IOCTL::unknown IOCTL's cmd = 0x%08x\n", cmd));
81161 + Status = -EOPNOTSUPP;
81162 + break;
81163 + }
81164 +
81165 + if(StateMachineTouched) // Upper layer sent a MLME-related operations
81166 + RT28XX_MLME_HANDLER(pAd);
81167 +
81168 + return Status;
81169 +}
81170 +
81171 +/*
81172 + ==========================================================================
81173 + Description:
81174 + Set SSID
81175 + Return:
81176 + TRUE if all parameters are OK, FALSE otherwise
81177 + ==========================================================================
81178 +*/
81179 +INT Set_SSID_Proc(
81180 + IN PRTMP_ADAPTER pAdapter,
81181 + IN PUCHAR arg)
81182 +{
81183 + NDIS_802_11_SSID Ssid, *pSsid=NULL;
81184 + BOOLEAN StateMachineTouched = FALSE;
81185 + int success = TRUE;
81186 +
81187 + if( strlen(arg) <= MAX_LEN_OF_SSID)
81188 + {
81189 + NdisZeroMemory(&Ssid, sizeof(NDIS_802_11_SSID));
81190 + if (strlen(arg) != 0)
81191 + {
81192 + NdisMoveMemory(Ssid.Ssid, arg, strlen(arg));
81193 + Ssid.SsidLength = strlen(arg);
81194 + }
81195 + else //ANY ssid
81196 + {
81197 + Ssid.SsidLength = 0;
81198 + memcpy(Ssid.Ssid, "", 0);
81199 + pAdapter->StaCfg.BssType = BSS_INFRA;
81200 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
81201 + pAdapter->StaCfg.WepStatus = Ndis802_11EncryptionDisabled;
81202 + }
81203 + pSsid = &Ssid;
81204 +
81205 + if (pAdapter->Mlme.CntlMachine.CurrState != CNTL_IDLE)
81206 + {
81207 + RT28XX_MLME_RESET_STATE_MACHINE(pAdapter);
81208 + DBGPRINT(RT_DEBUG_TRACE, ("!!! MLME busy, reset MLME state machine !!!\n"));
81209 + }
81210 +
81211 + pAdapter->MlmeAux.CurrReqIsFromNdis = TRUE;
81212 + pAdapter->StaCfg.bScanReqIsFromWebUI = FALSE;
81213 + pAdapter->bConfigChanged = TRUE;
81214 +
81215 + MlmeEnqueue(pAdapter,
81216 + MLME_CNTL_STATE_MACHINE,
81217 + OID_802_11_SSID,
81218 + sizeof(NDIS_802_11_SSID),
81219 + (VOID *)pSsid);
81220 +
81221 + StateMachineTouched = TRUE;
81222 + DBGPRINT(RT_DEBUG_TRACE, ("Set_SSID_Proc::(Len=%d,Ssid=%s)\n", Ssid.SsidLength, Ssid.Ssid));
81223 + }
81224 + else
81225 + success = FALSE;
81226 +
81227 + if (StateMachineTouched) // Upper layer sent a MLME-related operations
81228 + RT28XX_MLME_HANDLER(pAdapter);
81229 +
81230 + return success;
81231 +}
81232 +
81233 +#ifdef WMM_SUPPORT
81234 +/*
81235 + ==========================================================================
81236 + Description:
81237 + Set WmmCapable Enable or Disable
81238 + Return:
81239 + TRUE if all parameters are OK, FALSE otherwise
81240 + ==========================================================================
81241 +*/
81242 +INT Set_WmmCapable_Proc(
81243 + IN PRTMP_ADAPTER pAd,
81244 + IN PUCHAR arg)
81245 +{
81246 + BOOLEAN bWmmCapable;
81247 +
81248 + bWmmCapable = simple_strtol(arg, 0, 10);
81249 +
81250 + if ((bWmmCapable == 1)
81251 + )
81252 + pAd->CommonCfg.bWmmCapable = TRUE;
81253 + else if (bWmmCapable == 0)
81254 + pAd->CommonCfg.bWmmCapable = FALSE;
81255 + else
81256 + return FALSE; //Invalid argument
81257 +
81258 + DBGPRINT(RT_DEBUG_TRACE, ("Set_WmmCapable_Proc::(bWmmCapable=%d)\n",
81259 + pAd->CommonCfg.bWmmCapable));
81260 +
81261 + return TRUE;
81262 +}
81263 +#endif // WMM_SUPPORT //
81264 +
81265 +/*
81266 + ==========================================================================
81267 + Description:
81268 + Set Network Type(Infrastructure/Adhoc mode)
81269 + Return:
81270 + TRUE if all parameters are OK, FALSE otherwise
81271 + ==========================================================================
81272 +*/
81273 +INT Set_NetworkType_Proc(
81274 + IN PRTMP_ADAPTER pAdapter,
81275 + IN PUCHAR arg)
81276 +{
81277 + UINT32 Value = 0;
81278 +
81279 + if (strcmp(arg, "Adhoc") == 0)
81280 + {
81281 + if (pAdapter->StaCfg.BssType != BSS_ADHOC)
81282 + {
81283 + // Config has changed
81284 + pAdapter->bConfigChanged = TRUE;
81285 + if (MONITOR_ON(pAdapter))
81286 + {
81287 + RTMP_IO_WRITE32(pAdapter, RX_FILTR_CFG, STANORMAL);
81288 + RTMP_IO_READ32(pAdapter, MAC_SYS_CTRL, &Value);
81289 + Value &= (~0x80);
81290 + RTMP_IO_WRITE32(pAdapter, MAC_SYS_CTRL, Value);
81291 + OPSTATUS_CLEAR_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED);
81292 + pAdapter->StaCfg.bAutoReconnect = TRUE;
81293 + LinkDown(pAdapter, FALSE);
81294 + }
81295 + if (INFRA_ON(pAdapter))
81296 + {
81297 + //BOOLEAN Cancelled;
81298 + // Set the AutoReconnectSsid to prevent it reconnect to old SSID
81299 + // Since calling this indicate user don't want to connect to that SSID anymore.
81300 + pAdapter->MlmeAux.AutoReconnectSsidLen= 32;
81301 + NdisZeroMemory(pAdapter->MlmeAux.AutoReconnectSsid, pAdapter->MlmeAux.AutoReconnectSsidLen);
81302 +
81303 + LinkDown(pAdapter, FALSE);
81304 +
81305 + DBGPRINT(RT_DEBUG_TRACE, ("NDIS_STATUS_MEDIA_DISCONNECT Event BB!\n"));
81306 + }
81307 + }
81308 + pAdapter->StaCfg.BssType = BSS_ADHOC;
81309 + pAdapter->net_dev->type = pAdapter->StaCfg.OriDevType;
81310 + DBGPRINT(RT_DEBUG_TRACE, ("===>Set_NetworkType_Proc::(AD-HOC)\n"));
81311 + }
81312 + else if (strcmp(arg, "Infra") == 0)
81313 + {
81314 + if (pAdapter->StaCfg.BssType != BSS_INFRA)
81315 + {
81316 + // Config has changed
81317 + pAdapter->bConfigChanged = TRUE;
81318 + if (MONITOR_ON(pAdapter))
81319 + {
81320 + RTMP_IO_WRITE32(pAdapter, RX_FILTR_CFG, STANORMAL);
81321 + RTMP_IO_READ32(pAdapter, MAC_SYS_CTRL, &Value);
81322 + Value &= (~0x80);
81323 + RTMP_IO_WRITE32(pAdapter, MAC_SYS_CTRL, Value);
81324 + OPSTATUS_CLEAR_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED);
81325 + pAdapter->StaCfg.bAutoReconnect = TRUE;
81326 + LinkDown(pAdapter, FALSE);
81327 + }
81328 + if (ADHOC_ON(pAdapter))
81329 + {
81330 + // Set the AutoReconnectSsid to prevent it reconnect to old SSID
81331 + // Since calling this indicate user don't want to connect to that SSID anymore.
81332 + pAdapter->MlmeAux.AutoReconnectSsidLen= 32;
81333 + NdisZeroMemory(pAdapter->MlmeAux.AutoReconnectSsid, pAdapter->MlmeAux.AutoReconnectSsidLen);
81334 +
81335 + LinkDown(pAdapter, FALSE);
81336 + }
81337 + }
81338 + pAdapter->StaCfg.BssType = BSS_INFRA;
81339 + pAdapter->net_dev->type = pAdapter->StaCfg.OriDevType;
81340 + DBGPRINT(RT_DEBUG_TRACE, ("===>Set_NetworkType_Proc::(INFRA)\n"));
81341 +
81342 + pAdapter->StaCfg.BssType = BSS_INFRA;
81343 + }
81344 + else if (strcmp(arg, "Monitor") == 0)
81345 + {
81346 + UCHAR bbpValue = 0;
81347 + BCN_TIME_CFG_STRUC csr;
81348 + OPSTATUS_CLEAR_FLAG(pAdapter, fOP_STATUS_INFRA_ON);
81349 + OPSTATUS_CLEAR_FLAG(pAdapter, fOP_STATUS_ADHOC_ON);
81350 + OPSTATUS_SET_FLAG(pAdapter, fOP_STATUS_MEDIA_STATE_CONNECTED);
81351 + // disable all periodic state machine
81352 + pAdapter->StaCfg.bAutoReconnect = FALSE;
81353 + // reset all mlme state machine
81354 + RT28XX_MLME_RESET_STATE_MACHINE(pAdapter);
81355 + DBGPRINT(RT_DEBUG_TRACE, ("fOP_STATUS_MEDIA_STATE_CONNECTED \n"));
81356 + if (pAdapter->CommonCfg.CentralChannel == 0)
81357 + {
81358 +#ifdef DOT11_N_SUPPORT
81359 + if (pAdapter->CommonCfg.PhyMode == PHY_11AN_MIXED)
81360 + pAdapter->CommonCfg.CentralChannel = 36;
81361 + else
81362 +#endif // DOT11_N_SUPPORT //
81363 + pAdapter->CommonCfg.CentralChannel = 6;
81364 + }
81365 +#ifdef DOT11_N_SUPPORT
81366 + else
81367 + N_ChannelCheck(pAdapter);
81368 +#endif // DOT11_N_SUPPORT //
81369 +
81370 +#ifdef DOT11_N_SUPPORT
81371 + if (pAdapter->CommonCfg.PhyMode >= PHY_11ABGN_MIXED &&
81372 + pAdapter->CommonCfg.RegTransmitSetting.field.BW == BW_40 &&
81373 + pAdapter->CommonCfg.RegTransmitSetting.field.EXTCHA == EXTCHA_ABOVE)
81374 + {
81375 + // 40MHz ,control channel at lower
81376 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R4, &bbpValue);
81377 + bbpValue &= (~0x18);
81378 + bbpValue |= 0x10;
81379 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R4, bbpValue);
81380 + pAdapter->CommonCfg.BBPCurrentBW = BW_40;
81381 + // RX : control channel at lower
81382 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R3, &bbpValue);
81383 + bbpValue &= (~0x20);
81384 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R3, bbpValue);
81385 +
81386 + RTMP_IO_READ32(pAdapter, TX_BAND_CFG, &Value);
81387 + Value &= 0xfffffffe;
81388 + RTMP_IO_WRITE32(pAdapter, TX_BAND_CFG, Value);
81389 + pAdapter->CommonCfg.CentralChannel = pAdapter->CommonCfg.Channel + 2;
81390 + AsicSwitchChannel(pAdapter, pAdapter->CommonCfg.CentralChannel, FALSE);
81391 + AsicLockChannel(pAdapter, pAdapter->CommonCfg.CentralChannel);
81392 + DBGPRINT(RT_DEBUG_TRACE, ("BW_40 ,control_channel(%d), CentralChannel(%d) \n",
81393 + pAdapter->CommonCfg.Channel,
81394 + pAdapter->CommonCfg.CentralChannel));
81395 + }
81396 + else if (pAdapter->CommonCfg.PhyMode >= PHY_11ABGN_MIXED &&
81397 + pAdapter->CommonCfg.RegTransmitSetting.field.BW == BW_40 &&
81398 + pAdapter->CommonCfg.RegTransmitSetting.field.EXTCHA == EXTCHA_BELOW)
81399 + {
81400 + // 40MHz ,control channel at upper
81401 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R4, &bbpValue);
81402 + bbpValue &= (~0x18);
81403 + bbpValue |= 0x10;
81404 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R4, bbpValue);
81405 + pAdapter->CommonCfg.BBPCurrentBW = BW_40;
81406 + RTMP_IO_READ32(pAdapter, TX_BAND_CFG, &Value);
81407 + Value |= 0x1;
81408 + RTMP_IO_WRITE32(pAdapter, TX_BAND_CFG, Value);
81409 +
81410 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R3, &bbpValue);
81411 + bbpValue |= (0x20);
81412 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R3, bbpValue);
81413 + pAdapter->CommonCfg.CentralChannel = pAdapter->CommonCfg.Channel - 2;
81414 + AsicSwitchChannel(pAdapter, pAdapter->CommonCfg.CentralChannel, FALSE);
81415 + AsicLockChannel(pAdapter, pAdapter->CommonCfg.CentralChannel);
81416 + DBGPRINT(RT_DEBUG_TRACE, ("BW_40 ,control_channel(%d), CentralChannel(%d) \n",
81417 + pAdapter->CommonCfg.Channel,
81418 + pAdapter->CommonCfg.CentralChannel));
81419 + }
81420 + else
81421 +#endif // DOT11_N_SUPPORT //
81422 + {
81423 + // 20MHz
81424 + RTMP_BBP_IO_READ8_BY_REG_ID(pAdapter, BBP_R4, &bbpValue);
81425 + bbpValue &= (~0x18);
81426 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R4, bbpValue);
81427 + pAdapter->CommonCfg.BBPCurrentBW = BW_20;
81428 + AsicSwitchChannel(pAdapter, pAdapter->CommonCfg.Channel, FALSE);
81429 + AsicLockChannel(pAdapter, pAdapter->CommonCfg.Channel);
81430 + DBGPRINT(RT_DEBUG_TRACE, ("BW_20, Channel(%d)\n", pAdapter->CommonCfg.Channel));
81431 + }
81432 + // Enable Rx with promiscuous reception
81433 + RTMP_IO_WRITE32(pAdapter, RX_FILTR_CFG, 0x3);
81434 + // ASIC supporsts sniffer function with replacing RSSI with timestamp.
81435 + //RTMP_IO_READ32(pAdapter, MAC_SYS_CTRL, &Value);
81436 + //Value |= (0x80);
81437 + //RTMP_IO_WRITE32(pAdapter, MAC_SYS_CTRL, Value);
81438 + // disable sync
81439 + RTMP_IO_READ32(pAdapter, BCN_TIME_CFG, &csr.word);
81440 + csr.field.bBeaconGen = 0;
81441 + csr.field.bTBTTEnable = 0;
81442 + csr.field.TsfSyncMode = 0;
81443 + RTMP_IO_WRITE32(pAdapter, BCN_TIME_CFG, csr.word);
81444 +
81445 + pAdapter->StaCfg.BssType = BSS_MONITOR;
81446 + pAdapter->net_dev->type = ARPHRD_IEEE80211_PRISM; //ARPHRD_IEEE80211; // IEEE80211
81447 + DBGPRINT(RT_DEBUG_TRACE, ("===>Set_NetworkType_Proc::(MONITOR)\n"));
81448 + }
81449 +
81450 + // Reset Ralink supplicant to not use, it will be set to start when UI set PMK key
81451 + pAdapter->StaCfg.WpaState = SS_NOTUSE;
81452 +
81453 + DBGPRINT(RT_DEBUG_TRACE, ("Set_NetworkType_Proc::(NetworkType=%d)\n", pAdapter->StaCfg.BssType));
81454 +
81455 + return TRUE;
81456 +}
81457 +
81458 +/*
81459 + ==========================================================================
81460 + Description:
81461 + Set Authentication mode
81462 + Return:
81463 + TRUE if all parameters are OK, FALSE otherwise
81464 + ==========================================================================
81465 +*/
81466 +INT Set_AuthMode_Proc(
81467 + IN PRTMP_ADAPTER pAdapter,
81468 + IN PUCHAR arg)
81469 +{
81470 + if ((strcmp(arg, "WEPAUTO") == 0) || (strcmp(arg, "wepauto") == 0))
81471 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeAutoSwitch;
81472 + else if ((strcmp(arg, "OPEN") == 0) || (strcmp(arg, "open") == 0))
81473 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeOpen;
81474 + else if ((strcmp(arg, "SHARED") == 0) || (strcmp(arg, "shared") == 0))
81475 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeShared;
81476 + else if ((strcmp(arg, "WPAPSK") == 0) || (strcmp(arg, "wpapsk") == 0))
81477 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPAPSK;
81478 + else if ((strcmp(arg, "WPANONE") == 0) || (strcmp(arg, "wpanone") == 0))
81479 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPANone;
81480 + else if ((strcmp(arg, "WPA2PSK") == 0) || (strcmp(arg, "wpa2psk") == 0))
81481 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPA2PSK;
81482 +#ifdef WPA_SUPPLICANT_SUPPORT
81483 + else if ((strcmp(arg, "WPA") == 0) || (strcmp(arg, "wpa") == 0))
81484 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPA;
81485 + else if ((strcmp(arg, "WPA2") == 0) || (strcmp(arg, "wpa2") == 0))
81486 + pAdapter->StaCfg.AuthMode = Ndis802_11AuthModeWPA2;
81487 +#endif // WPA_SUPPLICANT_SUPPORT //
81488 + else
81489 + return FALSE;
81490 +
81491 + pAdapter->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
81492 +
81493 + DBGPRINT(RT_DEBUG_TRACE, ("Set_AuthMode_Proc::(AuthMode=%d)\n", pAdapter->StaCfg.AuthMode));
81494 +
81495 + return TRUE;
81496 +}
81497 +
81498 +/*
81499 + ==========================================================================
81500 + Description:
81501 + Set Encryption Type
81502 + Return:
81503 + TRUE if all parameters are OK, FALSE otherwise
81504 + ==========================================================================
81505 +*/
81506 +INT Set_EncrypType_Proc(
81507 + IN PRTMP_ADAPTER pAdapter,
81508 + IN PUCHAR arg)
81509 +{
81510 + if ((strcmp(arg, "NONE") == 0) || (strcmp(arg, "none") == 0))
81511 + {
81512 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81513 + return TRUE; // do nothing
81514 +
81515 + pAdapter->StaCfg.WepStatus = Ndis802_11WEPDisabled;
81516 + pAdapter->StaCfg.PairCipher = Ndis802_11WEPDisabled;
81517 + pAdapter->StaCfg.GroupCipher = Ndis802_11WEPDisabled;
81518 + }
81519 + else if ((strcmp(arg, "WEP") == 0) || (strcmp(arg, "wep") == 0))
81520 + {
81521 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81522 + return TRUE; // do nothing
81523 +
81524 + pAdapter->StaCfg.WepStatus = Ndis802_11WEPEnabled;
81525 + pAdapter->StaCfg.PairCipher = Ndis802_11WEPEnabled;
81526 + pAdapter->StaCfg.GroupCipher = Ndis802_11WEPEnabled;
81527 + }
81528 + else if ((strcmp(arg, "TKIP") == 0) || (strcmp(arg, "tkip") == 0))
81529 + {
81530 + if (pAdapter->StaCfg.AuthMode < Ndis802_11AuthModeWPA)
81531 + return TRUE; // do nothing
81532 +
81533 + pAdapter->StaCfg.WepStatus = Ndis802_11Encryption2Enabled;
81534 + pAdapter->StaCfg.PairCipher = Ndis802_11Encryption2Enabled;
81535 + pAdapter->StaCfg.GroupCipher = Ndis802_11Encryption2Enabled;
81536 + }
81537 + else if ((strcmp(arg, "AES") == 0) || (strcmp(arg, "aes") == 0))
81538 + {
81539 + if (pAdapter->StaCfg.AuthMode < Ndis802_11AuthModeWPA)
81540 + return TRUE; // do nothing
81541 +
81542 + pAdapter->StaCfg.WepStatus = Ndis802_11Encryption3Enabled;
81543 + pAdapter->StaCfg.PairCipher = Ndis802_11Encryption3Enabled;
81544 + pAdapter->StaCfg.GroupCipher = Ndis802_11Encryption3Enabled;
81545 + }
81546 + else
81547 + return FALSE;
81548 +
81549 + pAdapter->StaCfg.OrigWepStatus = pAdapter->StaCfg.WepStatus;
81550 +
81551 + DBGPRINT(RT_DEBUG_TRACE, ("Set_EncrypType_Proc::(EncrypType=%d)\n", pAdapter->StaCfg.WepStatus));
81552 +
81553 + return TRUE;
81554 +}
81555 +
81556 +/*
81557 + ==========================================================================
81558 + Description:
81559 + Set Default Key ID
81560 + Return:
81561 + TRUE if all parameters are OK, FALSE otherwise
81562 + ==========================================================================
81563 +*/
81564 +INT Set_DefaultKeyID_Proc(
81565 + IN PRTMP_ADAPTER pAdapter,
81566 + IN PUCHAR arg)
81567 +{
81568 + ULONG KeyIdx;
81569 +
81570 + KeyIdx = simple_strtol(arg, 0, 10);
81571 + if((KeyIdx >= 1 ) && (KeyIdx <= 4))
81572 + pAdapter->StaCfg.DefaultKeyId = (UCHAR) (KeyIdx - 1 );
81573 + else
81574 + return FALSE; //Invalid argument
81575 +
81576 + DBGPRINT(RT_DEBUG_TRACE, ("Set_DefaultKeyID_Proc::(DefaultKeyID=%d)\n", pAdapter->StaCfg.DefaultKeyId));
81577 +
81578 + return TRUE;
81579 +}
81580 +
81581 +/*
81582 + ==========================================================================
81583 + Description:
81584 + Set WEP KEY1
81585 + Return:
81586 + TRUE if all parameters are OK, FALSE otherwise
81587 + ==========================================================================
81588 +*/
81589 +INT Set_Key1_Proc(
81590 + IN PRTMP_ADAPTER pAdapter,
81591 + IN PUCHAR arg)
81592 +{
81593 + int KeyLen;
81594 + int i;
81595 + UCHAR CipherAlg=CIPHER_WEP64;
81596 +
81597 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81598 + return TRUE; // do nothing
81599 +
81600 + KeyLen = strlen(arg);
81601 +
81602 + switch (KeyLen)
81603 + {
81604 + case 5: //wep 40 Ascii type
81605 + pAdapter->SharedKey[BSS0][0].KeyLen = KeyLen;
81606 + memcpy(pAdapter->SharedKey[BSS0][0].Key, arg, KeyLen);
81607 + CipherAlg = CIPHER_WEP64;
81608 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key1_Proc::(Key1=%s and type=%s)\n", arg, "Ascii"));
81609 + break;
81610 + case 10: //wep 40 Hex type
81611 + for(i=0; i < KeyLen; i++)
81612 + {
81613 + if( !isxdigit(*(arg+i)) )
81614 + return FALSE; //Not Hex value;
81615 + }
81616 + pAdapter->SharedKey[BSS0][0].KeyLen = KeyLen / 2 ;
81617 + AtoH(arg, pAdapter->SharedKey[BSS0][0].Key, KeyLen / 2);
81618 + CipherAlg = CIPHER_WEP64;
81619 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key1_Proc::(Key1=%s and type=%s)\n", arg, "Hex"));
81620 + break;
81621 + case 13: //wep 104 Ascii type
81622 + pAdapter->SharedKey[BSS0][0].KeyLen = KeyLen;
81623 + memcpy(pAdapter->SharedKey[BSS0][0].Key, arg, KeyLen);
81624 + CipherAlg = CIPHER_WEP128;
81625 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key1_Proc::(Key1=%s and type=%s)\n", arg, "Ascii"));
81626 + break;
81627 + case 26: //wep 104 Hex type
81628 + for(i=0; i < KeyLen; i++)
81629 + {
81630 + if( !isxdigit(*(arg+i)) )
81631 + return FALSE; //Not Hex value;
81632 + }
81633 + pAdapter->SharedKey[BSS0][0].KeyLen = KeyLen / 2 ;
81634 + AtoH(arg, pAdapter->SharedKey[BSS0][0].Key, KeyLen / 2);
81635 + CipherAlg = CIPHER_WEP128;
81636 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key1_Proc::(Key1=%s and type=%s)\n", arg, "Hex"));
81637 + break;
81638 + default: //Invalid argument
81639 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key1_Proc::Invalid argument (=%s)\n", arg));
81640 + return FALSE;
81641 + }
81642 +
81643 + pAdapter->SharedKey[BSS0][0].CipherAlg = CipherAlg;
81644 +
81645 + // Set keys (into ASIC)
81646 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81647 + ; // not support
81648 + else // Old WEP stuff
81649 + {
81650 + AsicAddSharedKeyEntry(pAdapter,
81651 + 0,
81652 + 0,
81653 + pAdapter->SharedKey[BSS0][0].CipherAlg,
81654 + pAdapter->SharedKey[BSS0][0].Key,
81655 + NULL,
81656 + NULL);
81657 + }
81658 +
81659 + return TRUE;
81660 +}
81661 +/*
81662 + ==========================================================================
81663 +
81664 + Description:
81665 + Set WEP KEY2
81666 + Return:
81667 + TRUE if all parameters are OK, FALSE otherwise
81668 + ==========================================================================
81669 +*/
81670 +INT Set_Key2_Proc(
81671 + IN PRTMP_ADAPTER pAdapter,
81672 + IN PUCHAR arg)
81673 +{
81674 + int KeyLen;
81675 + int i;
81676 + UCHAR CipherAlg=CIPHER_WEP64;
81677 +
81678 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81679 + return TRUE; // do nothing
81680 +
81681 + KeyLen = strlen(arg);
81682 +
81683 + switch (KeyLen)
81684 + {
81685 + case 5: //wep 40 Ascii type
81686 + pAdapter->SharedKey[BSS0][1].KeyLen = KeyLen;
81687 + memcpy(pAdapter->SharedKey[BSS0][1].Key, arg, KeyLen);
81688 + CipherAlg = CIPHER_WEP64;
81689 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key2_Proc::(Key2=%s and type=%s)\n", arg, "Ascii"));
81690 + break;
81691 + case 10: //wep 40 Hex type
81692 + for(i=0; i < KeyLen; i++)
81693 + {
81694 + if( !isxdigit(*(arg+i)) )
81695 + return FALSE; //Not Hex value;
81696 + }
81697 + pAdapter->SharedKey[BSS0][1].KeyLen = KeyLen / 2 ;
81698 + AtoH(arg, pAdapter->SharedKey[BSS0][1].Key, KeyLen / 2);
81699 + CipherAlg = CIPHER_WEP64;
81700 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key2_Proc::(Key2=%s and type=%s)\n", arg, "Hex"));
81701 + break;
81702 + case 13: //wep 104 Ascii type
81703 + pAdapter->SharedKey[BSS0][1].KeyLen = KeyLen;
81704 + memcpy(pAdapter->SharedKey[BSS0][1].Key, arg, KeyLen);
81705 + CipherAlg = CIPHER_WEP128;
81706 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key2_Proc::(Key2=%s and type=%s)\n", arg, "Ascii"));
81707 + break;
81708 + case 26: //wep 104 Hex type
81709 + for(i=0; i < KeyLen; i++)
81710 + {
81711 + if( !isxdigit(*(arg+i)) )
81712 + return FALSE; //Not Hex value;
81713 + }
81714 + pAdapter->SharedKey[BSS0][1].KeyLen = KeyLen / 2 ;
81715 + AtoH(arg, pAdapter->SharedKey[BSS0][1].Key, KeyLen / 2);
81716 + CipherAlg = CIPHER_WEP128;
81717 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key2_Proc::(Key2=%s and type=%s)\n", arg, "Hex"));
81718 + break;
81719 + default: //Invalid argument
81720 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key2_Proc::Invalid argument (=%s)\n", arg));
81721 + return FALSE;
81722 + }
81723 + pAdapter->SharedKey[BSS0][1].CipherAlg = CipherAlg;
81724 +
81725 + // Set keys (into ASIC)
81726 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81727 + ; // not support
81728 + else // Old WEP stuff
81729 + {
81730 + AsicAddSharedKeyEntry(pAdapter,
81731 + 0,
81732 + 1,
81733 + pAdapter->SharedKey[BSS0][1].CipherAlg,
81734 + pAdapter->SharedKey[BSS0][1].Key,
81735 + NULL,
81736 + NULL);
81737 + }
81738 +
81739 + return TRUE;
81740 +}
81741 +/*
81742 + ==========================================================================
81743 + Description:
81744 + Set WEP KEY3
81745 + Return:
81746 + TRUE if all parameters are OK, FALSE otherwise
81747 + ==========================================================================
81748 +*/
81749 +INT Set_Key3_Proc(
81750 + IN PRTMP_ADAPTER pAdapter,
81751 + IN PUCHAR arg)
81752 +{
81753 + int KeyLen;
81754 + int i;
81755 + UCHAR CipherAlg=CIPHER_WEP64;
81756 +
81757 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81758 + return TRUE; // do nothing
81759 +
81760 + KeyLen = strlen(arg);
81761 +
81762 + switch (KeyLen)
81763 + {
81764 + case 5: //wep 40 Ascii type
81765 + pAdapter->SharedKey[BSS0][2].KeyLen = KeyLen;
81766 + memcpy(pAdapter->SharedKey[BSS0][2].Key, arg, KeyLen);
81767 + CipherAlg = CIPHER_WEP64;
81768 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key3_Proc::(Key3=%s and type=Ascii)\n", arg));
81769 + break;
81770 + case 10: //wep 40 Hex type
81771 + for(i=0; i < KeyLen; i++)
81772 + {
81773 + if( !isxdigit(*(arg+i)) )
81774 + return FALSE; //Not Hex value;
81775 + }
81776 + pAdapter->SharedKey[BSS0][2].KeyLen = KeyLen / 2 ;
81777 + AtoH(arg, pAdapter->SharedKey[BSS0][2].Key, KeyLen / 2);
81778 + CipherAlg = CIPHER_WEP64;
81779 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key3_Proc::(Key3=%s and type=Hex)\n", arg));
81780 + break;
81781 + case 13: //wep 104 Ascii type
81782 + pAdapter->SharedKey[BSS0][2].KeyLen = KeyLen;
81783 + memcpy(pAdapter->SharedKey[BSS0][2].Key, arg, KeyLen);
81784 + CipherAlg = CIPHER_WEP128;
81785 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key3_Proc::(Key3=%s and type=Ascii)\n", arg));
81786 + break;
81787 + case 26: //wep 104 Hex type
81788 + for(i=0; i < KeyLen; i++)
81789 + {
81790 + if( !isxdigit(*(arg+i)) )
81791 + return FALSE; //Not Hex value;
81792 + }
81793 + pAdapter->SharedKey[BSS0][2].KeyLen = KeyLen / 2 ;
81794 + AtoH(arg, pAdapter->SharedKey[BSS0][2].Key, KeyLen / 2);
81795 + CipherAlg = CIPHER_WEP128;
81796 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key3_Proc::(Key3=%s and type=Hex)\n", arg));
81797 + break;
81798 + default: //Invalid argument
81799 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key3_Proc::Invalid argument (=%s)\n", arg));
81800 + return FALSE;
81801 + }
81802 + pAdapter->SharedKey[BSS0][2].CipherAlg = CipherAlg;
81803 +
81804 + // Set keys (into ASIC)
81805 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81806 + ; // not support
81807 + else // Old WEP stuff
81808 + {
81809 + AsicAddSharedKeyEntry(pAdapter,
81810 + 0,
81811 + 2,
81812 + pAdapter->SharedKey[BSS0][2].CipherAlg,
81813 + pAdapter->SharedKey[BSS0][2].Key,
81814 + NULL,
81815 + NULL);
81816 + }
81817 +
81818 + return TRUE;
81819 +}
81820 +/*
81821 + ==========================================================================
81822 + Description:
81823 + Set WEP KEY4
81824 + Return:
81825 + TRUE if all parameters are OK, FALSE otherwise
81826 + ==========================================================================
81827 +*/
81828 +INT Set_Key4_Proc(
81829 + IN PRTMP_ADAPTER pAdapter,
81830 + IN PUCHAR arg)
81831 +{
81832 + int KeyLen;
81833 + int i;
81834 + UCHAR CipherAlg=CIPHER_WEP64;
81835 +
81836 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81837 + return TRUE; // do nothing
81838 +
81839 + KeyLen = strlen(arg);
81840 +
81841 + switch (KeyLen)
81842 + {
81843 + case 5: //wep 40 Ascii type
81844 + pAdapter->SharedKey[BSS0][3].KeyLen = KeyLen;
81845 + memcpy(pAdapter->SharedKey[BSS0][3].Key, arg, KeyLen);
81846 + CipherAlg = CIPHER_WEP64;
81847 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key4_Proc::(Key4=%s and type=%s)\n", arg, "Ascii"));
81848 + break;
81849 + case 10: //wep 40 Hex type
81850 + for(i=0; i < KeyLen; i++)
81851 + {
81852 + if( !isxdigit(*(arg+i)) )
81853 + return FALSE; //Not Hex value;
81854 + }
81855 + pAdapter->SharedKey[BSS0][3].KeyLen = KeyLen / 2 ;
81856 + AtoH(arg, pAdapter->SharedKey[BSS0][3].Key, KeyLen / 2);
81857 + CipherAlg = CIPHER_WEP64;
81858 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key4_Proc::(Key4=%s and type=%s)\n", arg, "Hex"));
81859 + break;
81860 + case 13: //wep 104 Ascii type
81861 + pAdapter->SharedKey[BSS0][3].KeyLen = KeyLen;
81862 + memcpy(pAdapter->SharedKey[BSS0][3].Key, arg, KeyLen);
81863 + CipherAlg = CIPHER_WEP128;
81864 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key4_Proc::(Key4=%s and type=%s)\n", arg, "Ascii"));
81865 + break;
81866 + case 26: //wep 104 Hex type
81867 + for(i=0; i < KeyLen; i++)
81868 + {
81869 + if( !isxdigit(*(arg+i)) )
81870 + return FALSE; //Not Hex value;
81871 + }
81872 + pAdapter->SharedKey[BSS0][3].KeyLen = KeyLen / 2 ;
81873 + AtoH(arg, pAdapter->SharedKey[BSS0][3].Key, KeyLen / 2);
81874 + CipherAlg = CIPHER_WEP128;
81875 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key4_Proc::(Key4=%s and type=%s)\n", arg, "Hex"));
81876 + break;
81877 + default: //Invalid argument
81878 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Key4_Proc::Invalid argument (=%s)\n", arg));
81879 + return FALSE;
81880 + }
81881 + pAdapter->SharedKey[BSS0][3].CipherAlg = CipherAlg;
81882 +
81883 + // Set keys (into ASIC)
81884 + if (pAdapter->StaCfg.AuthMode >= Ndis802_11AuthModeWPA)
81885 + ; // not support
81886 + else // Old WEP stuff
81887 + {
81888 + AsicAddSharedKeyEntry(pAdapter,
81889 + 0,
81890 + 3,
81891 + pAdapter->SharedKey[BSS0][3].CipherAlg,
81892 + pAdapter->SharedKey[BSS0][3].Key,
81893 + NULL,
81894 + NULL);
81895 + }
81896 +
81897 + return TRUE;
81898 +}
81899 +
81900 +/*
81901 + ==========================================================================
81902 + Description:
81903 + Set WPA PSK key
81904 + Return:
81905 + TRUE if all parameters are OK, FALSE otherwise
81906 + ==========================================================================
81907 +*/
81908 +INT Set_WPAPSK_Proc(
81909 + IN PRTMP_ADAPTER pAdapter,
81910 + IN PUCHAR arg)
81911 +{
81912 + UCHAR keyMaterial[40];
81913 +
81914 + if ((pAdapter->StaCfg.AuthMode != Ndis802_11AuthModeWPAPSK) &&
81915 + (pAdapter->StaCfg.AuthMode != Ndis802_11AuthModeWPA2PSK) &&
81916 + (pAdapter->StaCfg.AuthMode != Ndis802_11AuthModeWPANone)
81917 + )
81918 + return TRUE; // do nothing
81919 +
81920 + DBGPRINT(RT_DEBUG_TRACE, ("Set_WPAPSK_Proc::(WPAPSK=%s)\n", arg));
81921 +
81922 + NdisZeroMemory(keyMaterial, 40);
81923 +
81924 + if ((strlen(arg) < 8) || (strlen(arg) > 64))
81925 + {
81926 + DBGPRINT(RT_DEBUG_TRACE, ("Set failed!!(WPAPSK=%s), WPAPSK key-string required 8 ~ 64 characters \n", arg));
81927 + return FALSE;
81928 + }
81929 +
81930 + if (strlen(arg) == 64)
81931 + {
81932 + AtoH(arg, keyMaterial, 32);
81933 + NdisMoveMemory(pAdapter->StaCfg.PMK, keyMaterial, 32);
81934 +
81935 + }
81936 + else
81937 + {
81938 + PasswordHash((char *)arg, pAdapter->MlmeAux.Ssid, pAdapter->MlmeAux.SsidLen, keyMaterial);
81939 + NdisMoveMemory(pAdapter->StaCfg.PMK, keyMaterial, 32);
81940 + }
81941 +
81942 +
81943 +
81944 + if(pAdapter->StaCfg.BssType == BSS_ADHOC &&
81945 + pAdapter->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
81946 + {
81947 + pAdapter->StaCfg.WpaState = SS_NOTUSE;
81948 + }
81949 + else
81950 + {
81951 + // Start STA supplicant state machine
81952 + pAdapter->StaCfg.WpaState = SS_START;
81953 + }
81954 +
81955 + return TRUE;
81956 +}
81957 +
81958 +/*
81959 + ==========================================================================
81960 + Description:
81961 + Set Power Saving mode
81962 + Return:
81963 + TRUE if all parameters are OK, FALSE otherwise
81964 + ==========================================================================
81965 +*/
81966 +INT Set_PSMode_Proc(
81967 + IN PRTMP_ADAPTER pAdapter,
81968 + IN PUCHAR arg)
81969 +{
81970 + if (pAdapter->StaCfg.BssType == BSS_INFRA)
81971 + {
81972 + if ((strcmp(arg, "Max_PSP") == 0) ||
81973 + (strcmp(arg, "max_psp") == 0) ||
81974 + (strcmp(arg, "MAX_PSP") == 0))
81975 + {
81976 + // do NOT turn on PSM bit here, wait until MlmeCheckForPsmChange()
81977 + // to exclude certain situations.
81978 + if (pAdapter->StaCfg.bWindowsACCAMEnable == FALSE)
81979 + pAdapter->StaCfg.WindowsPowerMode = Ndis802_11PowerModeMAX_PSP;
81980 + pAdapter->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeMAX_PSP;
81981 + OPSTATUS_SET_FLAG(pAdapter, fOP_STATUS_RECEIVE_DTIM);
81982 + pAdapter->StaCfg.DefaultListenCount = 5;
81983 +
81984 + }
81985 + else if ((strcmp(arg, "Fast_PSP") == 0) ||
81986 + (strcmp(arg, "fast_psp") == 0) ||
81987 + (strcmp(arg, "FAST_PSP") == 0))
81988 + {
81989 + // do NOT turn on PSM bit here, wait until MlmeCheckForPsmChange()
81990 + // to exclude certain situations.
81991 + OPSTATUS_SET_FLAG(pAdapter, fOP_STATUS_RECEIVE_DTIM);
81992 + if (pAdapter->StaCfg.bWindowsACCAMEnable == FALSE)
81993 + pAdapter->StaCfg.WindowsPowerMode = Ndis802_11PowerModeFast_PSP;
81994 + pAdapter->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeFast_PSP;
81995 + pAdapter->StaCfg.DefaultListenCount = 3;
81996 + }
81997 + else if ((strcmp(arg, "Legacy_PSP") == 0) ||
81998 + (strcmp(arg, "legacy_psp") == 0) ||
81999 + (strcmp(arg, "LEGACY_PSP") == 0))
82000 + {
82001 + // do NOT turn on PSM bit here, wait until MlmeCheckForPsmChange()
82002 + // to exclude certain situations.
82003 + OPSTATUS_SET_FLAG(pAdapter, fOP_STATUS_RECEIVE_DTIM);
82004 + if (pAdapter->StaCfg.bWindowsACCAMEnable == FALSE)
82005 + pAdapter->StaCfg.WindowsPowerMode = Ndis802_11PowerModeLegacy_PSP;
82006 + pAdapter->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeLegacy_PSP;
82007 + pAdapter->StaCfg.DefaultListenCount = 3;
82008 + }
82009 + else
82010 + {
82011 + //Default Ndis802_11PowerModeCAM
82012 + // clear PSM bit immediately
82013 + MlmeSetPsmBit(pAdapter, PWR_ACTIVE);
82014 + OPSTATUS_SET_FLAG(pAdapter, fOP_STATUS_RECEIVE_DTIM);
82015 + if (pAdapter->StaCfg.bWindowsACCAMEnable == FALSE)
82016 + pAdapter->StaCfg.WindowsPowerMode = Ndis802_11PowerModeCAM;
82017 + pAdapter->StaCfg.WindowsBatteryPowerMode = Ndis802_11PowerModeCAM;
82018 + }
82019 +
82020 + DBGPRINT(RT_DEBUG_TRACE, ("Set_PSMode_Proc::(PSMode=%ld)\n", pAdapter->StaCfg.WindowsPowerMode));
82021 + }
82022 + else
82023 + return FALSE;
82024 +
82025 +
82026 + return TRUE;
82027 +}
82028 +
82029 +#ifdef WPA_SUPPLICANT_SUPPORT
82030 +/*
82031 + ==========================================================================
82032 + Description:
82033 + Set WpaSupport flag.
82034 + Value:
82035 + 0: Driver ignore wpa_supplicant.
82036 + 1: wpa_supplicant initiates scanning and AP selection.
82037 + 2: driver takes care of scanning, AP selection, and IEEE 802.11 association parameters.
82038 + Return:
82039 + TRUE if all parameters are OK, FALSE otherwise
82040 + ==========================================================================
82041 +*/
82042 +INT Set_Wpa_Support(
82043 + IN PRTMP_ADAPTER pAd,
82044 + IN PUCHAR arg)
82045 +{
82046 +
82047 + if ( simple_strtol(arg, 0, 10) == 0)
82048 + pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_DISABLE;
82049 + else if ( simple_strtol(arg, 0, 10) == 1)
82050 + pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_ENABLE;
82051 + else if ( simple_strtol(arg, 0, 10) == 2)
82052 + pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_ENABLE_WITH_WEB_UI;
82053 + else
82054 + pAd->StaCfg.WpaSupplicantUP = WPA_SUPPLICANT_DISABLE;
82055 +
82056 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Wpa_Support::(WpaSupplicantUP=%d)\n", pAd->StaCfg.WpaSupplicantUP));
82057 +
82058 + return TRUE;
82059 +}
82060 +#endif // WPA_SUPPLICANT_SUPPORT //
82061 +
82062 +#ifdef DBG
82063 +/*
82064 + ==========================================================================
82065 + Description:
82066 + Read / Write MAC
82067 + Arguments:
82068 + pAdapter Pointer to our adapter
82069 + wrq Pointer to the ioctl argument
82070 +
82071 + Return Value:
82072 + None
82073 +
82074 + Note:
82075 + Usage:
82076 + 1.) iwpriv ra0 mac 0 ==> read MAC where Addr=0x0
82077 + 2.) iwpriv ra0 mac 0=12 ==> write MAC where Addr=0x0, value=12
82078 + ==========================================================================
82079 +*/
82080 +VOID RTMPIoctlMAC(
82081 + IN PRTMP_ADAPTER pAdapter,
82082 + IN struct iwreq *wrq)
82083 +{
82084 + CHAR *this_char;
82085 + CHAR *value;
82086 + INT j = 0, k = 0;
82087 + CHAR msg[1024];
82088 + CHAR arg[255];
82089 + ULONG macAddr = 0;
82090 + UCHAR temp[16], temp2[16];
82091 + UINT32 macValue = 0;
82092 + INT Status;
82093 +
82094 +
82095 + memset(msg, 0x00, 1024);
82096 + if (wrq->u.data.length > 1) //No parameters.
82097 + {
82098 + Status = copy_from_user(arg, wrq->u.data.pointer, (wrq->u.data.length > 255) ? 255 : wrq->u.data.length);
82099 + sprintf(msg, "\n");
82100 +
82101 + //Parsing Read or Write
82102 + this_char = arg;
82103 + if (!*this_char)
82104 + goto next;
82105 +
82106 + if ((value = rtstrchr(this_char, '=')) != NULL)
82107 + *value++ = 0;
82108 +
82109 + if (!value || !*value)
82110 + { //Read
82111 + // Sanity check
82112 + if(strlen(this_char) > 4)
82113 + goto next;
82114 +
82115 + j = strlen(this_char);
82116 + while(j-- > 0)
82117 + {
82118 + if(this_char[j] > 'f' || this_char[j] < '0')
82119 + return;
82120 + }
82121 +
82122 + // Mac Addr
82123 + k = j = strlen(this_char);
82124 + while(j-- > 0)
82125 + {
82126 + this_char[4-k+j] = this_char[j];
82127 + }
82128 +
82129 + while(k < 4)
82130 + this_char[3-k++]='0';
82131 + this_char[4]='\0';
82132 +
82133 + if(strlen(this_char) == 4)
82134 + {
82135 + AtoH(this_char, temp, 2);
82136 + macAddr = *temp*256 + temp[1];
82137 + if (macAddr < 0xFFFF)
82138 + {
82139 + RTMP_IO_READ32(pAdapter, macAddr, &macValue);
82140 + DBGPRINT(RT_DEBUG_TRACE, ("MacAddr=%lx, MacValue=%x\n", macAddr, macValue));
82141 + sprintf(msg+strlen(msg), "[0x%08lX]:%08X ", macAddr , macValue);
82142 + }
82143 + else
82144 + {//Invalid parametes, so default printk all bbp
82145 + goto next;
82146 + }
82147 + }
82148 + }
82149 + else
82150 + { //Write
82151 + memcpy(&temp2, value, strlen(value));
82152 + temp2[strlen(value)] = '\0';
82153 +
82154 + // Sanity check
82155 + if((strlen(this_char) > 4) || strlen(temp2) > 8)
82156 + goto next;
82157 +
82158 + j = strlen(this_char);
82159 + while(j-- > 0)
82160 + {
82161 + if(this_char[j] > 'f' || this_char[j] < '0')
82162 + return;
82163 + }
82164 +
82165 + j = strlen(temp2);
82166 + while(j-- > 0)
82167 + {
82168 + if(temp2[j] > 'f' || temp2[j] < '0')
82169 + return;
82170 + }
82171 +
82172 + //MAC Addr
82173 + k = j = strlen(this_char);
82174 + while(j-- > 0)
82175 + {
82176 + this_char[4-k+j] = this_char[j];
82177 + }
82178 +
82179 + while(k < 4)
82180 + this_char[3-k++]='0';
82181 + this_char[4]='\0';
82182 +
82183 + //MAC value
82184 + k = j = strlen(temp2);
82185 + while(j-- > 0)
82186 + {
82187 + temp2[8-k+j] = temp2[j];
82188 + }
82189 +
82190 + while(k < 8)
82191 + temp2[7-k++]='0';
82192 + temp2[8]='\0';
82193 +
82194 + {
82195 + AtoH(this_char, temp, 2);
82196 + macAddr = *temp*256 + temp[1];
82197 +
82198 + AtoH(temp2, temp, 4);
82199 + macValue = *temp*256*256*256 + temp[1]*256*256 + temp[2]*256 + temp[3];
82200 +
82201 + // debug mode
82202 + if (macAddr == (HW_DEBUG_SETTING_BASE + 4))
82203 + {
82204 + // 0x2bf4: byte0 non-zero: enable R17 tuning, 0: disable R17 tuning
82205 + if (macValue & 0x000000ff)
82206 + {
82207 + pAdapter->BbpTuning.bEnable = TRUE;
82208 + DBGPRINT(RT_DEBUG_TRACE,("turn on R17 tuning\n"));
82209 + }
82210 + else
82211 + {
82212 + UCHAR R66;
82213 + pAdapter->BbpTuning.bEnable = FALSE;
82214 + R66 = 0x26 + GET_LNA_GAIN(pAdapter);
82215 +#ifdef RALINK_ATE
82216 + if (ATE_ON(pAdapter))
82217 + {
82218 + ATE_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R66, (0x26 + GET_LNA_GAIN(pAdapter)));
82219 + }
82220 + else
82221 +#endif // RALINK_ATE //
82222 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAdapter, BBP_R66, (0x26 + GET_LNA_GAIN(pAdapter)));
82223 + DBGPRINT(RT_DEBUG_TRACE,("turn off R17 tuning, restore to 0x%02x\n", R66));
82224 + }
82225 + return;
82226 + }
82227 +
82228 + DBGPRINT(RT_DEBUG_TRACE, ("MacAddr=%02lx, MacValue=0x%x\n", macAddr, macValue));
82229 +
82230 + RTMP_IO_WRITE32(pAdapter, macAddr, macValue);
82231 + sprintf(msg+strlen(msg), "[0x%08lX]:%08X ", macAddr, macValue);
82232 + }
82233 + }
82234 + }
82235 +next:
82236 + if(strlen(msg) == 1)
82237 + sprintf(msg+strlen(msg), "===>Error command format!");
82238 +
82239 + // Copy the information into the user buffer
82240 + wrq->u.data.length = strlen(msg);
82241 + Status = copy_to_user(wrq->u.data.pointer, msg, wrq->u.data.length);
82242 +
82243 + DBGPRINT(RT_DEBUG_TRACE, ("<==RTMPIoctlMAC\n\n"));
82244 +}
82245 +
82246 +/*
82247 + ==========================================================================
82248 + Description:
82249 + Read / Write E2PROM
82250 + Arguments:
82251 + pAdapter Pointer to our adapter
82252 + wrq Pointer to the ioctl argument
82253 +
82254 + Return Value:
82255 + None
82256 +
82257 + Note:
82258 + Usage:
82259 + 1.) iwpriv ra0 e2p 0 ==> read E2PROM where Addr=0x0
82260 + 2.) iwpriv ra0 e2p 0=1234 ==> write E2PROM where Addr=0x0, value=1234
82261 + ==========================================================================
82262 +*/
82263 +VOID RTMPIoctlE2PROM(
82264 + IN PRTMP_ADAPTER pAdapter,
82265 + IN struct iwreq *wrq)
82266 +{
82267 + CHAR *this_char;
82268 + CHAR *value;
82269 + INT j = 0, k = 0;
82270 + CHAR msg[1024];
82271 + CHAR arg[255];
82272 + USHORT eepAddr = 0;
82273 + UCHAR temp[16], temp2[16];
82274 + USHORT eepValue;
82275 + int Status;
82276 +
82277 +
82278 + memset(msg, 0x00, 1024);
82279 + if (wrq->u.data.length > 1) //No parameters.
82280 + {
82281 + Status = copy_from_user(arg, wrq->u.data.pointer, (wrq->u.data.length > 255) ? 255 : wrq->u.data.length);
82282 + sprintf(msg, "\n");
82283 +
82284 + //Parsing Read or Write
82285 + this_char = arg;
82286 +
82287 +
82288 + if (!*this_char)
82289 + goto next;
82290 +
82291 + if ((value = rtstrchr(this_char, '=')) != NULL)
82292 + *value++ = 0;
82293 +
82294 + if (!value || !*value)
82295 + { //Read
82296 +
82297 + // Sanity check
82298 + if(strlen(this_char) > 4)
82299 + goto next;
82300 +
82301 + j = strlen(this_char);
82302 + while(j-- > 0)
82303 + {
82304 + if(this_char[j] > 'f' || this_char[j] < '0')
82305 + return;
82306 + }
82307 +
82308 + // E2PROM addr
82309 + k = j = strlen(this_char);
82310 + while(j-- > 0)
82311 + {
82312 + this_char[4-k+j] = this_char[j];
82313 + }
82314 +
82315 + while(k < 4)
82316 + this_char[3-k++]='0';
82317 + this_char[4]='\0';
82318 +
82319 + if(strlen(this_char) == 4)
82320 + {
82321 + AtoH(this_char, temp, 2);
82322 + eepAddr = *temp*256 + temp[1];
82323 + if (eepAddr < 0xFFFF)
82324 + {
82325 + RT28xx_EEPROM_READ16(pAdapter, eepAddr, eepValue);
82326 + sprintf(msg+strlen(msg), "[0x%04X]:0x%04X ", eepAddr , eepValue);
82327 + }
82328 + else
82329 + {//Invalid parametes, so default printk all bbp
82330 + goto next;
82331 + }
82332 + }
82333 + }
82334 + else
82335 + { //Write
82336 + memcpy(&temp2, value, strlen(value));
82337 + temp2[strlen(value)] = '\0';
82338 +
82339 + // Sanity check
82340 + if((strlen(this_char) > 4) || strlen(temp2) > 8)
82341 + goto next;
82342 +
82343 + j = strlen(this_char);
82344 + while(j-- > 0)
82345 + {
82346 + if(this_char[j] > 'f' || this_char[j] < '0')
82347 + return;
82348 + }
82349 + j = strlen(temp2);
82350 + while(j-- > 0)
82351 + {
82352 + if(temp2[j] > 'f' || temp2[j] < '0')
82353 + return;
82354 + }
82355 +
82356 + //MAC Addr
82357 + k = j = strlen(this_char);
82358 + while(j-- > 0)
82359 + {
82360 + this_char[4-k+j] = this_char[j];
82361 + }
82362 +
82363 + while(k < 4)
82364 + this_char[3-k++]='0';
82365 + this_char[4]='\0';
82366 +
82367 + //MAC value
82368 + k = j = strlen(temp2);
82369 + while(j-- > 0)
82370 + {
82371 + temp2[4-k+j] = temp2[j];
82372 + }
82373 +
82374 + while(k < 4)
82375 + temp2[3-k++]='0';
82376 + temp2[4]='\0';
82377 +
82378 + AtoH(this_char, temp, 2);
82379 + eepAddr = *temp*256 + temp[1];
82380 +
82381 + AtoH(temp2, temp, 2);
82382 + eepValue = *temp*256 + temp[1];
82383 +
82384 + RT28xx_EEPROM_WRITE16(pAdapter, eepAddr, eepValue);
82385 + sprintf(msg+strlen(msg), "[0x%02X]:%02X ", eepAddr, eepValue);
82386 + }
82387 + }
82388 +next:
82389 + if(strlen(msg) == 1)
82390 + sprintf(msg+strlen(msg), "===>Error command format!");
82391 +
82392 +
82393 + // Copy the information into the user buffer
82394 + wrq->u.data.length = strlen(msg);
82395 + Status = copy_to_user(wrq->u.data.pointer, msg, wrq->u.data.length);
82396 +
82397 + DBGPRINT(RT_DEBUG_TRACE, ("<==RTMPIoctlE2PROM\n"));
82398 +}
82399 +#endif // DBG //
82400 +
82401 +
82402 +
82403 +
82404 +INT Set_TGnWifiTest_Proc(
82405 + IN PRTMP_ADAPTER pAd,
82406 + IN PUCHAR arg)
82407 +{
82408 + if (simple_strtol(arg, 0, 10) == 0)
82409 + pAd->StaCfg.bTGnWifiTest = FALSE;
82410 + else
82411 + pAd->StaCfg.bTGnWifiTest = TRUE;
82412 +
82413 + DBGPRINT(RT_DEBUG_TRACE, ("IF Set_TGnWifiTest_Proc::(bTGnWifiTest=%d)\n", pAd->StaCfg.bTGnWifiTest));
82414 + return TRUE;
82415 +}
82416 +
82417 +INT Set_LongRetryLimit_Proc(
82418 + IN PRTMP_ADAPTER pAdapter,
82419 + IN PUCHAR arg)
82420 +{
82421 + TX_RTY_CFG_STRUC tx_rty_cfg;
82422 + UCHAR LongRetryLimit = (UCHAR)simple_strtol(arg, 0, 10);
82423 +
82424 + RTMP_IO_READ32(pAdapter, TX_RTY_CFG, &tx_rty_cfg.word);
82425 + tx_rty_cfg.field.LongRtyLimit = LongRetryLimit;
82426 + RTMP_IO_WRITE32(pAdapter, TX_RTY_CFG, tx_rty_cfg.word);
82427 + DBGPRINT(RT_DEBUG_TRACE, ("IF Set_LongRetryLimit_Proc::(tx_rty_cfg=0x%x)\n", tx_rty_cfg.word));
82428 + return TRUE;
82429 +}
82430 +
82431 +INT Set_ShortRetryLimit_Proc(
82432 + IN PRTMP_ADAPTER pAdapter,
82433 + IN PUCHAR arg)
82434 +{
82435 + TX_RTY_CFG_STRUC tx_rty_cfg;
82436 + UCHAR ShortRetryLimit = (UCHAR)simple_strtol(arg, 0, 10);
82437 +
82438 + RTMP_IO_READ32(pAdapter, TX_RTY_CFG, &tx_rty_cfg.word);
82439 + tx_rty_cfg.field.ShortRtyLimit = ShortRetryLimit;
82440 + RTMP_IO_WRITE32(pAdapter, TX_RTY_CFG, tx_rty_cfg.word);
82441 + DBGPRINT(RT_DEBUG_TRACE, ("IF Set_ShortRetryLimit_Proc::(tx_rty_cfg=0x%x)\n", tx_rty_cfg.word));
82442 + return TRUE;
82443 +}
82444 +
82445 +#ifdef EXT_BUILD_CHANNEL_LIST
82446 +INT Set_Ieee80211dClientMode_Proc(
82447 + IN PRTMP_ADAPTER pAdapter,
82448 + IN PUCHAR arg)
82449 +{
82450 + if (simple_strtol(arg, 0, 10) == 0)
82451 + pAdapter->StaCfg.IEEE80211dClientMode = Rt802_11_D_None;
82452 + else if (simple_strtol(arg, 0, 10) == 1)
82453 + pAdapter->StaCfg.IEEE80211dClientMode = Rt802_11_D_Flexible;
82454 + else if (simple_strtol(arg, 0, 10) == 2)
82455 + pAdapter->StaCfg.IEEE80211dClientMode = Rt802_11_D_Strict;
82456 + else
82457 + return FALSE;
82458 +
82459 + DBGPRINT(RT_DEBUG_TRACE, ("Set_Ieee802dMode_Proc::(IEEEE0211dMode=%d)\n", pAdapter->StaCfg.IEEE80211dClientMode));
82460 + return TRUE;
82461 +}
82462 +#endif // EXT_BUILD_CHANNEL_LIST //
82463 +
82464 +#ifdef CARRIER_DETECTION_SUPPORT
82465 +INT Set_CarrierDetect_Proc(
82466 + IN PRTMP_ADAPTER pAd,
82467 + IN PUCHAR arg)
82468 +{
82469 + if (simple_strtol(arg, 0, 10) == 0)
82470 + pAd->CommonCfg.CarrierDetect.Enable = FALSE;
82471 + else
82472 + pAd->CommonCfg.CarrierDetect.Enable = TRUE;
82473 +
82474 + DBGPRINT(RT_DEBUG_TRACE, ("IF Set_CarrierDetect_Proc::(CarrierDetect.Enable=%d)\n", pAd->CommonCfg.CarrierDetect.Enable));
82475 + return TRUE;
82476 +}
82477 +#endif // CARRIER_DETECTION_SUPPORT //
82478 +
82479 --- /dev/null
82480 +++ b/drivers/staging/rt2860/sta/rtmp_data.c
82481 @@ -0,0 +1,2614 @@
82482 +/*
82483 + *************************************************************************
82484 + * Ralink Tech Inc.
82485 + * 5F., No.36, Taiyuan St., Jhubei City,
82486 + * Hsinchu County 302,
82487 + * Taiwan, R.O.C.
82488 + *
82489 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
82490 + *
82491 + * This program is free software; you can redistribute it and/or modify *
82492 + * it under the terms of the GNU General Public License as published by *
82493 + * the Free Software Foundation; either version 2 of the License, or *
82494 + * (at your option) any later version. *
82495 + * *
82496 + * This program is distributed in the hope that it will be useful, *
82497 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
82498 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
82499 + * GNU General Public License for more details. *
82500 + * *
82501 + * You should have received a copy of the GNU General Public License *
82502 + * along with this program; if not, write to the *
82503 + * Free Software Foundation, Inc., *
82504 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
82505 + * *
82506 + *************************************************************************
82507 +
82508 + Module Name:
82509 + rtmp_data.c
82510 +
82511 + Abstract:
82512 + Data path subroutines
82513 +
82514 + Revision History:
82515 + Who When What
82516 + -------- ---------- ----------------------------------------------
82517 + John Aug/17/04 major modification for RT2561/2661
82518 + Jan Lee Mar/17/06 major modification for RT2860 New Ring Design
82519 +*/
82520 +#include "../rt_config.h"
82521 +
82522 +
82523 +
82524 +VOID STARxEAPOLFrameIndicate(
82525 + IN PRTMP_ADAPTER pAd,
82526 + IN MAC_TABLE_ENTRY *pEntry,
82527 + IN RX_BLK *pRxBlk,
82528 + IN UCHAR FromWhichBSSID)
82529 +{
82530 + PRT28XX_RXD_STRUC pRxD = &(pRxBlk->RxD);
82531 + PRXWI_STRUC pRxWI = pRxBlk->pRxWI;
82532 + UCHAR *pTmpBuf;
82533 +
82534 +#ifdef WPA_SUPPLICANT_SUPPORT
82535 + if (pAd->StaCfg.WpaSupplicantUP)
82536 + {
82537 + // All EAPoL frames have to pass to upper layer (ex. WPA_SUPPLICANT daemon)
82538 + // TBD : process fragmented EAPol frames
82539 + {
82540 + // In 802.1x mode, if the received frame is EAP-SUCCESS packet, turn on the PortSecured variable
82541 + if ( pAd->StaCfg.IEEE8021X == TRUE &&
82542 + (EAP_CODE_SUCCESS == WpaCheckEapCode(pAd, pRxBlk->pData, pRxBlk->DataSize, LENGTH_802_1_H)))
82543 + {
82544 + PUCHAR Key;
82545 + UCHAR CipherAlg;
82546 + int idx = 0;
82547 +
82548 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("Receive EAP-SUCCESS Packet\n"));
82549 + STA_PORT_SECURED(pAd);
82550 +
82551 + if (pAd->StaCfg.IEEE8021x_required_keys == FALSE)
82552 + {
82553 + idx = pAd->StaCfg.DesireSharedKeyId;
82554 + CipherAlg = pAd->StaCfg.DesireSharedKey[idx].CipherAlg;
82555 + Key = pAd->StaCfg.DesireSharedKey[idx].Key;
82556 +
82557 + if (pAd->StaCfg.DesireSharedKey[idx].KeyLen > 0)
82558 + {
82559 +#ifdef RT2860
82560 + MAC_TABLE_ENTRY *pEntry = &pAd->MacTab.Content[BSSID_WCID];
82561 +
82562 + // Set key material and cipherAlg to Asic
82563 + AsicAddSharedKeyEntry(pAd, BSS0, idx, CipherAlg, Key, NULL, NULL);
82564 +
82565 + // Assign group key info
82566 + RTMPAddWcidAttributeEntry(pAd, BSS0, idx, CipherAlg, NULL);
82567 +
82568 + // Assign pairwise key info
82569 + RTMPAddWcidAttributeEntry(pAd, BSS0, idx, CipherAlg, pEntry);
82570 +
82571 + pAd->IndicateMediaState = NdisMediaStateConnected;
82572 + pAd->ExtraInfo = GENERAL_LINK_UP;
82573 +#endif // RT2860 //
82574 + // For Preventing ShardKey Table is cleared by remove key procedure.
82575 + pAd->SharedKey[BSS0][idx].CipherAlg = CipherAlg;
82576 + pAd->SharedKey[BSS0][idx].KeyLen = pAd->StaCfg.DesireSharedKey[idx].KeyLen;
82577 + NdisMoveMemory(pAd->SharedKey[BSS0][idx].Key,
82578 + pAd->StaCfg.DesireSharedKey[idx].Key,
82579 + pAd->StaCfg.DesireSharedKey[idx].KeyLen);
82580 + }
82581 + }
82582 + }
82583 +
82584 + Indicate_Legacy_Packet(pAd, pRxBlk, FromWhichBSSID);
82585 + return;
82586 + }
82587 + }
82588 + else
82589 +#endif // WPA_SUPPLICANT_SUPPORT //
82590 + {
82591 + // Special DATA frame that has to pass to MLME
82592 + // 1. Cisco Aironet frames for CCX2. We need pass it to MLME for special process
82593 + // 2. EAPOL handshaking frames when driver supplicant enabled, pass to MLME for special process
82594 + {
82595 + pTmpBuf = pRxBlk->pData - LENGTH_802_11;
82596 + NdisMoveMemory(pTmpBuf, pRxBlk->pHeader, LENGTH_802_11);
82597 + REPORT_MGMT_FRAME_TO_MLME(pAd, pRxWI->WirelessCliID, pTmpBuf, pRxBlk->DataSize + LENGTH_802_11, pRxWI->RSSI0, pRxWI->RSSI1, pRxWI->RSSI2, pRxD->PlcpSignal);
82598 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("!!! report EAPOL/AIRONET DATA to MLME (len=%d) !!!\n", pRxBlk->DataSize));
82599 + }
82600 + }
82601 +
82602 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
82603 + return;
82604 +
82605 +}
82606 +
82607 +VOID STARxDataFrameAnnounce(
82608 + IN PRTMP_ADAPTER pAd,
82609 + IN MAC_TABLE_ENTRY *pEntry,
82610 + IN RX_BLK *pRxBlk,
82611 + IN UCHAR FromWhichBSSID)
82612 +{
82613 +
82614 + // non-EAP frame
82615 + if (!RTMPCheckWPAframe(pAd, pEntry, pRxBlk->pData, pRxBlk->DataSize, FromWhichBSSID))
82616 + {
82617 + {
82618 + // drop all non-EAP DATA frame before
82619 + // this client's Port-Access-Control is secured
82620 + if (pRxBlk->pHeader->FC.Wep)
82621 + {
82622 + // unsupported cipher suite
82623 + if (pAd->StaCfg.WepStatus == Ndis802_11EncryptionDisabled)
82624 + {
82625 + // release packet
82626 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
82627 + return;
82628 + }
82629 + }
82630 + else
82631 + {
82632 + // encryption in-use but receive a non-EAPOL clear text frame, drop it
82633 + if ((pAd->StaCfg.WepStatus != Ndis802_11EncryptionDisabled) &&
82634 + (pAd->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED))
82635 + {
82636 + // release packet
82637 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
82638 + return;
82639 + }
82640 + }
82641 + }
82642 + RX_BLK_CLEAR_FLAG(pRxBlk, fRX_EAP);
82643 + if (!RX_BLK_TEST_FLAG(pRxBlk, fRX_ARALINK))
82644 + {
82645 + // Normal legacy, AMPDU or AMSDU
82646 + CmmRxnonRalinkFrameIndicate(pAd, pRxBlk, FromWhichBSSID);
82647 +
82648 + }
82649 + else
82650 + {
82651 + // ARALINK
82652 + CmmRxRalinkFrameIndicate(pAd, pEntry, pRxBlk, FromWhichBSSID);
82653 + }
82654 +#ifdef QOS_DLS_SUPPORT
82655 + RX_BLK_CLEAR_FLAG(pRxBlk, fRX_DLS);
82656 +#endif // QOS_DLS_SUPPORT //
82657 + }
82658 + else
82659 + {
82660 + RX_BLK_SET_FLAG(pRxBlk, fRX_EAP);
82661 +#ifdef DOT11_N_SUPPORT
82662 + if (RX_BLK_TEST_FLAG(pRxBlk, fRX_AMPDU) && (pAd->CommonCfg.bDisableReordering == 0))
82663 + {
82664 + Indicate_AMPDU_Packet(pAd, pRxBlk, FromWhichBSSID);
82665 + }
82666 + else
82667 +#endif // DOT11_N_SUPPORT //
82668 + {
82669 + // Determin the destination of the EAP frame
82670 + // to WPA state machine or upper layer
82671 + STARxEAPOLFrameIndicate(pAd, pEntry, pRxBlk, FromWhichBSSID);
82672 + }
82673 + }
82674 +}
82675 +
82676 +
82677 +// For TKIP frame, calculate the MIC value
82678 +BOOLEAN STACheckTkipMICValue(
82679 + IN PRTMP_ADAPTER pAd,
82680 + IN MAC_TABLE_ENTRY *pEntry,
82681 + IN RX_BLK *pRxBlk)
82682 +{
82683 + PHEADER_802_11 pHeader = pRxBlk->pHeader;
82684 + UCHAR *pData = pRxBlk->pData;
82685 + USHORT DataSize = pRxBlk->DataSize;
82686 + UCHAR UserPriority = pRxBlk->UserPriority;
82687 + PCIPHER_KEY pWpaKey;
82688 + UCHAR *pDA, *pSA;
82689 +
82690 + pWpaKey = &pAd->SharedKey[BSS0][pRxBlk->pRxWI->KeyIndex];
82691 +
82692 + pDA = pHeader->Addr1;
82693 + if (RX_BLK_TEST_FLAG(pRxBlk, fRX_INFRA))
82694 + {
82695 + pSA = pHeader->Addr3;
82696 + }
82697 + else
82698 + {
82699 + pSA = pHeader->Addr2;
82700 + }
82701 +
82702 + if (RTMPTkipCompareMICValue(pAd,
82703 + pData,
82704 + pDA,
82705 + pSA,
82706 + pWpaKey->RxMic,
82707 + UserPriority,
82708 + DataSize) == FALSE)
82709 + {
82710 + DBGPRINT_RAW(RT_DEBUG_ERROR,("Rx MIC Value error 2\n"));
82711 +
82712 +#ifdef WPA_SUPPLICANT_SUPPORT
82713 + if (pAd->StaCfg.WpaSupplicantUP)
82714 + {
82715 + WpaSendMicFailureToWpaSupplicant(pAd, (pWpaKey->Type == PAIRWISEKEY) ? TRUE : FALSE);
82716 + }
82717 + else
82718 +#endif // WPA_SUPPLICANT_SUPPORT //
82719 + {
82720 + RTMPReportMicError(pAd, pWpaKey);
82721 + }
82722 +
82723 + // release packet
82724 + RELEASE_NDIS_PACKET(pAd, pRxBlk->pRxPacket, NDIS_STATUS_FAILURE);
82725 + return FALSE;
82726 + }
82727 +
82728 + return TRUE;
82729 +}
82730 +
82731 +
82732 +//
82733 +// All Rx routines use RX_BLK structure to hande rx events
82734 +// It is very important to build pRxBlk attributes
82735 +// 1. pHeader pointer to 802.11 Header
82736 +// 2. pData pointer to payload including LLC (just skip Header)
82737 +// 3. set payload size including LLC to DataSize
82738 +// 4. set some flags with RX_BLK_SET_FLAG()
82739 +//
82740 +VOID STAHandleRxDataFrame(
82741 + IN PRTMP_ADAPTER pAd,
82742 + IN RX_BLK *pRxBlk)
82743 +{
82744 + PRT28XX_RXD_STRUC pRxD = &(pRxBlk->RxD);
82745 + PRXWI_STRUC pRxWI = pRxBlk->pRxWI;
82746 + PHEADER_802_11 pHeader = pRxBlk->pHeader;
82747 + PNDIS_PACKET pRxPacket = pRxBlk->pRxPacket;
82748 + BOOLEAN bFragment = FALSE;
82749 + MAC_TABLE_ENTRY *pEntry = NULL;
82750 + UCHAR FromWhichBSSID = BSS0;
82751 + UCHAR UserPriority = 0;
82752 +
82753 + {
82754 + // before LINK UP, all DATA frames are rejected
82755 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
82756 + {
82757 + // release packet
82758 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82759 + return;
82760 + }
82761 +
82762 +#ifdef QOS_DLS_SUPPORT
82763 + //if ((pHeader->FC.FrDs == 0) && (pHeader->FC.ToDs == 0))
82764 + if (RTMPRcvFrameDLSCheck(pAd, pHeader, pRxWI->MPDUtotalByteCount, pRxD))
82765 + {
82766 + return;
82767 + }
82768 +#endif // QOS_DLS_SUPPORT //
82769 +
82770 + // Drop not my BSS frames
82771 + if (pRxD->MyBss == 0)
82772 + {
82773 + {
82774 + // release packet
82775 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82776 + return;
82777 + }
82778 + }
82779 +
82780 + pAd->RalinkCounters.RxCountSinceLastNULL++;
82781 + if (pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable && (pHeader->FC.SubType & 0x08))
82782 + {
82783 + UCHAR *pData;
82784 + DBGPRINT(RT_DEBUG_TRACE,("bAPSDCapable\n"));
82785 +
82786 + // Qos bit 4
82787 + pData = (PUCHAR)pHeader + LENGTH_802_11;
82788 + if ((*pData >> 4) & 0x01)
82789 + {
82790 + DBGPRINT(RT_DEBUG_TRACE,("RxDone- Rcv EOSP frame, driver may fall into sleep\n"));
82791 + pAd->CommonCfg.bInServicePeriod = FALSE;
82792 +
82793 + // Force driver to fall into sleep mode when rcv EOSP frame
82794 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
82795 + {
82796 + USHORT TbttNumToNextWakeUp;
82797 + USHORT NextDtim = pAd->StaCfg.DtimPeriod;
82798 + ULONG Now;
82799 +
82800 + NdisGetSystemUpTime(&Now);
82801 + NextDtim -= (USHORT)(Now - pAd->StaCfg.LastBeaconRxTime)/pAd->CommonCfg.BeaconPeriod;
82802 +
82803 + TbttNumToNextWakeUp = pAd->StaCfg.DefaultListenCount;
82804 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM) && (TbttNumToNextWakeUp > NextDtim))
82805 + TbttNumToNextWakeUp = NextDtim;
82806 +
82807 + MlmeSetPsmBit(pAd, PWR_SAVE);
82808 + // if WMM-APSD is failed, try to disable following line
82809 + AsicSleepThenAutoWakeup(pAd, TbttNumToNextWakeUp);
82810 + }
82811 + }
82812 +
82813 + if ((pHeader->FC.MoreData) && (pAd->CommonCfg.bInServicePeriod))
82814 + {
82815 + DBGPRINT(RT_DEBUG_TRACE,("Sending another trigger frame when More Data bit is set to 1\n"));
82816 + }
82817 + }
82818 +
82819 + // Drop NULL, CF-ACK(no data), CF-POLL(no data), and CF-ACK+CF-POLL(no data) data frame
82820 + if ((pHeader->FC.SubType & 0x04)) // bit 2 : no DATA
82821 + {
82822 + // release packet
82823 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82824 + return;
82825 + }
82826 +
82827 + // Drop not my BSS frame (we can not only check the MyBss bit in RxD)
82828 +#ifdef QOS_DLS_SUPPORT
82829 + if (!pAd->CommonCfg.bDLSCapable)
82830 + {
82831 +#endif // QOS_DLS_SUPPORT //
82832 + if (INFRA_ON(pAd))
82833 + {
82834 + // Infrastructure mode, check address 2 for BSSID
82835 + if (!RTMPEqualMemory(&pHeader->Addr2, &pAd->CommonCfg.Bssid, 6))
82836 + {
82837 + // Receive frame not my BSSID
82838 + // release packet
82839 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82840 + return;
82841 + }
82842 + }
82843 + else // Ad-Hoc mode or Not associated
82844 + {
82845 + // Ad-Hoc mode, check address 3 for BSSID
82846 + if (!RTMPEqualMemory(&pHeader->Addr3, &pAd->CommonCfg.Bssid, 6))
82847 + {
82848 + // Receive frame not my BSSID
82849 + // release packet
82850 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82851 + return;
82852 + }
82853 + }
82854 +#ifdef QOS_DLS_SUPPORT
82855 + }
82856 +#endif // QOS_DLS_SUPPORT //
82857 +
82858 + //
82859 + // find pEntry
82860 + //
82861 + if (pRxWI->WirelessCliID < MAX_LEN_OF_MAC_TABLE)
82862 + {
82863 + pEntry = &pAd->MacTab.Content[pRxWI->WirelessCliID];
82864 + }
82865 + else
82866 + {
82867 + // 1. release packet if infra mode
82868 + // 2. new a pEntry if ad-hoc mode
82869 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82870 + return;
82871 + }
82872 +
82873 + // infra or ad-hoc
82874 + if (INFRA_ON(pAd))
82875 + {
82876 + RX_BLK_SET_FLAG(pRxBlk, fRX_INFRA);
82877 +#ifdef QOS_DLS_SUPPORT
82878 + if ((pHeader->FC.FrDs == 0) && (pHeader->FC.ToDs == 0))
82879 + RX_BLK_SET_FLAG(pRxBlk, fRX_DLS);
82880 + else
82881 +#endif // QOS_DLS_SUPPORT //
82882 + ASSERT(pRxWI->WirelessCliID == BSSID_WCID);
82883 + }
82884 +
82885 + // check Atheros Client
82886 + if ((pEntry->bIAmBadAtheros == FALSE) && (pRxD->AMPDU == 1) && (pHeader->FC.Retry ))
82887 + {
82888 + pEntry->bIAmBadAtheros = TRUE;
82889 + pAd->CommonCfg.IOTestParm.bCurrentAtheros = TRUE;
82890 + pAd->CommonCfg.IOTestParm.bLastAtheros = TRUE;
82891 + if (!STA_AES_ON(pAd))
82892 + {
82893 + AsicUpdateProtect(pAd, 8, ALLN_SETPROTECT, TRUE, FALSE);
82894 + }
82895 + }
82896 + }
82897 +
82898 + pRxBlk->pData = (UCHAR *)pHeader;
82899 +
82900 + //
82901 + // update RxBlk->pData, DataSize
82902 + // 802.11 Header, QOS, HTC, Hw Padding
82903 + //
82904 +
82905 + // 1. skip 802.11 HEADER
82906 + {
82907 + pRxBlk->pData += LENGTH_802_11;
82908 + pRxBlk->DataSize -= LENGTH_802_11;
82909 + }
82910 +
82911 + // 2. QOS
82912 + if (pHeader->FC.SubType & 0x08)
82913 + {
82914 + RX_BLK_SET_FLAG(pRxBlk, fRX_QOS);
82915 + UserPriority = *(pRxBlk->pData) & 0x0f;
82916 + // bit 7 in QoS Control field signals the HT A-MSDU format
82917 + if ((*pRxBlk->pData) & 0x80)
82918 + {
82919 + RX_BLK_SET_FLAG(pRxBlk, fRX_AMSDU);
82920 + }
82921 +
82922 + // skip QOS contorl field
82923 + pRxBlk->pData += 2;
82924 + pRxBlk->DataSize -=2;
82925 + }
82926 + pRxBlk->UserPriority = UserPriority;
82927 +
82928 + // 3. Order bit: A-Ralink or HTC+
82929 + if (pHeader->FC.Order)
82930 + {
82931 +#ifdef AGGREGATION_SUPPORT
82932 + if ((pRxWI->PHYMODE <= MODE_OFDM) && (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_AGGREGATION_INUSED)))
82933 + {
82934 + RX_BLK_SET_FLAG(pRxBlk, fRX_ARALINK);
82935 + }
82936 + else
82937 +#endif
82938 + {
82939 +#ifdef DOT11_N_SUPPORT
82940 + RX_BLK_SET_FLAG(pRxBlk, fRX_HTC);
82941 + // skip HTC contorl field
82942 + pRxBlk->pData += 4;
82943 + pRxBlk->DataSize -= 4;
82944 +#endif // DOT11_N_SUPPORT //
82945 + }
82946 + }
82947 +
82948 + // 4. skip HW padding
82949 + if (pRxD->L2PAD)
82950 + {
82951 + // just move pData pointer
82952 + // because DataSize excluding HW padding
82953 + RX_BLK_SET_FLAG(pRxBlk, fRX_PAD);
82954 + pRxBlk->pData += 2;
82955 + }
82956 +
82957 +#ifdef DOT11_N_SUPPORT
82958 + if (pRxD->BA)
82959 + {
82960 + RX_BLK_SET_FLAG(pRxBlk, fRX_AMPDU);
82961 + }
82962 +#endif // DOT11_N_SUPPORT //
82963 +
82964 +
82965 + //
82966 + // Case I Process Broadcast & Multicast data frame
82967 + //
82968 + if (pRxD->Bcast || pRxD->Mcast)
82969 + {
82970 + INC_COUNTER64(pAd->WlanCounters.MulticastReceivedFrameCount);
82971 +
82972 + // Drop Mcast/Bcast frame with fragment bit on
82973 + if (pHeader->FC.MoreFrag)
82974 + {
82975 + // release packet
82976 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82977 + return;
82978 + }
82979 +
82980 + // Filter out Bcast frame which AP relayed for us
82981 + if (pHeader->FC.FrDs && MAC_ADDR_EQUAL(pHeader->Addr3, pAd->CurrentAddress))
82982 + {
82983 + // release packet
82984 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
82985 + return;
82986 + }
82987 +
82988 + Indicate_Legacy_Packet(pAd, pRxBlk, FromWhichBSSID);
82989 + return;
82990 + }
82991 + else if (pRxD->U2M)
82992 + {
82993 + pAd->LastRxRate = (USHORT)((pRxWI->MCS) + (pRxWI->BW <<7) + (pRxWI->ShortGI <<8)+ (pRxWI->PHYMODE <<14)) ;
82994 +
82995 +
82996 +#ifdef QOS_DLS_SUPPORT
82997 + if (RX_BLK_TEST_FLAG(pRxBlk, fRX_DLS))
82998 + {
82999 + MAC_TABLE_ENTRY *pDlsEntry = NULL;
83000 +
83001 + pDlsEntry = DlsEntryTableLookupByWcid(pAd, pRxWI->WirelessCliID, pHeader->Addr2, TRUE);
83002 + if(pDlsEntry)
83003 + Update_Rssi_Sample(pAd, &pDlsEntry->RssiSample, pRxWI);
83004 + }
83005 + else
83006 +#endif // QOS_DLS_SUPPORT //
83007 + if (ADHOC_ON(pAd))
83008 + {
83009 + pEntry = MacTableLookup(pAd, pHeader->Addr2);
83010 + if (pEntry)
83011 + Update_Rssi_Sample(pAd, &pEntry->RssiSample, pRxWI);
83012 + }
83013 +
83014 +
83015 + Update_Rssi_Sample(pAd, &pAd->StaCfg.RssiSample, pRxWI);
83016 +
83017 + pAd->StaCfg.LastSNR0 = (UCHAR)(pRxWI->SNR0);
83018 + pAd->StaCfg.LastSNR1 = (UCHAR)(pRxWI->SNR1);
83019 +
83020 + pAd->RalinkCounters.OneSecRxOkDataCnt++;
83021 +
83022 +
83023 + if (!((pHeader->Frag == 0) && (pHeader->FC.MoreFrag == 0)))
83024 + {
83025 + // re-assemble the fragmented packets
83026 + // return complete frame (pRxPacket) or NULL
83027 + bFragment = TRUE;
83028 + pRxPacket = RTMPDeFragmentDataFrame(pAd, pRxBlk);
83029 + }
83030 +
83031 + if (pRxPacket)
83032 + {
83033 + pEntry = &pAd->MacTab.Content[pRxWI->WirelessCliID];
83034 +
83035 + // process complete frame
83036 + if (bFragment && (pRxD->Decrypted) && (pEntry->WepStatus == Ndis802_11Encryption2Enabled))
83037 + {
83038 + // Minus MIC length
83039 + pRxBlk->DataSize -= 8;
83040 +
83041 + // For TKIP frame, calculate the MIC value
83042 + if (STACheckTkipMICValue(pAd, pEntry, pRxBlk) == FALSE)
83043 + {
83044 + return;
83045 + }
83046 + }
83047 +
83048 + STARxDataFrameAnnounce(pAd, pEntry, pRxBlk, FromWhichBSSID);
83049 + return;
83050 + }
83051 + else
83052 + {
83053 + // just return
83054 + // because RTMPDeFragmentDataFrame() will release rx packet,
83055 + // if packet is fragmented
83056 + return;
83057 + }
83058 + }
83059 +
83060 + ASSERT(0);
83061 + // release packet
83062 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
83063 +}
83064 +
83065 +VOID STAHandleRxMgmtFrame(
83066 + IN PRTMP_ADAPTER pAd,
83067 + IN RX_BLK *pRxBlk)
83068 +{
83069 + PRT28XX_RXD_STRUC pRxD = &(pRxBlk->RxD);
83070 + PRXWI_STRUC pRxWI = pRxBlk->pRxWI;
83071 + PHEADER_802_11 pHeader = pRxBlk->pHeader;
83072 + PNDIS_PACKET pRxPacket = pRxBlk->pRxPacket;
83073 +
83074 + do
83075 + {
83076 +
83077 + // We should collect RSSI not only U2M data but also my beacon
83078 + if ((pHeader->FC.SubType == SUBTYPE_BEACON) && (MAC_ADDR_EQUAL(&pAd->CommonCfg.Bssid, &pHeader->Addr2)))
83079 + {
83080 + Update_Rssi_Sample(pAd, &pAd->StaCfg.RssiSample, pRxWI);
83081 +
83082 + pAd->StaCfg.LastSNR0 = (UCHAR)(pRxWI->SNR0);
83083 + pAd->StaCfg.LastSNR1 = (UCHAR)(pRxWI->SNR1);
83084 + }
83085 +
83086 + // First check the size, it MUST not exceed the mlme queue size
83087 + if (pRxWI->MPDUtotalByteCount > MGMT_DMA_BUFFER_SIZE)
83088 + {
83089 + DBGPRINT_ERR(("STAHandleRxMgmtFrame: frame too large, size = %d \n", pRxWI->MPDUtotalByteCount));
83090 + break;
83091 + }
83092 +
83093 + REPORT_MGMT_FRAME_TO_MLME(pAd, pRxWI->WirelessCliID, pHeader, pRxWI->MPDUtotalByteCount,
83094 + pRxWI->RSSI0, pRxWI->RSSI1, pRxWI->RSSI2, pRxD->PlcpSignal);
83095 + } while (FALSE);
83096 +
83097 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_SUCCESS);
83098 +}
83099 +
83100 +VOID STAHandleRxControlFrame(
83101 + IN PRTMP_ADAPTER pAd,
83102 + IN RX_BLK *pRxBlk)
83103 +{
83104 +#ifdef DOT11_N_SUPPORT
83105 + PRXWI_STRUC pRxWI = pRxBlk->pRxWI;
83106 +#endif // DOT11_N_SUPPORT //
83107 + PHEADER_802_11 pHeader = pRxBlk->pHeader;
83108 + PNDIS_PACKET pRxPacket = pRxBlk->pRxPacket;
83109 +
83110 + switch (pHeader->FC.SubType)
83111 + {
83112 + case SUBTYPE_BLOCK_ACK_REQ:
83113 +#ifdef DOT11_N_SUPPORT
83114 + {
83115 + CntlEnqueueForRecv(pAd, pRxWI->WirelessCliID, (pRxWI->MPDUtotalByteCount), (PFRAME_BA_REQ)pHeader);
83116 + }
83117 + break;
83118 +#endif // DOT11_N_SUPPORT //
83119 + case SUBTYPE_BLOCK_ACK:
83120 + case SUBTYPE_ACK:
83121 + default:
83122 + break;
83123 + }
83124 +
83125 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
83126 +}
83127 +
83128 +
83129 +/*
83130 + ========================================================================
83131 +
83132 + Routine Description:
83133 + Process RxDone interrupt, running in DPC level
83134 +
83135 + Arguments:
83136 + pAd Pointer to our adapter
83137 +
83138 + Return Value:
83139 + None
83140 +
83141 + IRQL = DISPATCH_LEVEL
83142 +
83143 + Note:
83144 + This routine has to maintain Rx ring read pointer.
83145 + Need to consider QOS DATA format when converting to 802.3
83146 + ========================================================================
83147 +*/
83148 +BOOLEAN STARxDoneInterruptHandle(
83149 + IN PRTMP_ADAPTER pAd,
83150 + IN BOOLEAN argc)
83151 +{
83152 + NDIS_STATUS Status;
83153 + UINT32 RxProcessed, RxPending;
83154 + BOOLEAN bReschedule = FALSE;
83155 + RT28XX_RXD_STRUC *pRxD;
83156 + UCHAR *pData;
83157 + PRXWI_STRUC pRxWI;
83158 + PNDIS_PACKET pRxPacket;
83159 + PHEADER_802_11 pHeader;
83160 + RX_BLK RxCell;
83161 +
83162 + RxProcessed = RxPending = 0;
83163 +
83164 + // process whole rx ring
83165 + while (1)
83166 + {
83167 +
83168 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF |
83169 + fRTMP_ADAPTER_RESET_IN_PROGRESS |
83170 + fRTMP_ADAPTER_HALT_IN_PROGRESS |
83171 + fRTMP_ADAPTER_NIC_NOT_EXIST) ||
83172 + !RTMP_TEST_FLAG(pAd,fRTMP_ADAPTER_START_UP))
83173 + {
83174 + break;
83175 + }
83176 +
83177 +#ifdef RT2860
83178 + if (RxProcessed++ > MAX_RX_PROCESS_CNT)
83179 + {
83180 + // need to reschedule rx handle
83181 + bReschedule = TRUE;
83182 + break;
83183 + }
83184 +#endif // RT2860 //
83185 +
83186 + RxProcessed ++; // test
83187 +
83188 + // 1. allocate a new data packet into rx ring to replace received packet
83189 + // then processing the received packet
83190 + // 2. the callee must take charge of release of packet
83191 + // 3. As far as driver is concerned ,
83192 + // the rx packet must
83193 + // a. be indicated to upper layer or
83194 + // b. be released if it is discarded
83195 + pRxPacket = GetPacketFromRxRing(pAd, &(RxCell.RxD), &bReschedule, &RxPending);
83196 + if (pRxPacket == NULL)
83197 + {
83198 + // no more packet to process
83199 + break;
83200 + }
83201 +
83202 + // get rx ring descriptor
83203 + pRxD = &(RxCell.RxD);
83204 + // get rx data buffer
83205 + pData = GET_OS_PKT_DATAPTR(pRxPacket);
83206 + pRxWI = (PRXWI_STRUC) pData;
83207 + pHeader = (PHEADER_802_11) (pData+RXWI_SIZE) ;
83208 +
83209 +#ifdef RT_BIG_ENDIAN
83210 + RTMPFrameEndianChange(pAd, (PUCHAR)pHeader, DIR_READ, TRUE);
83211 + RTMPWIEndianChange((PUCHAR)pRxWI, TYPE_RXWI);
83212 +#endif
83213 +
83214 + // build RxCell
83215 + RxCell.pRxWI = pRxWI;
83216 + RxCell.pHeader = pHeader;
83217 + RxCell.pRxPacket = pRxPacket;
83218 + RxCell.pData = (UCHAR *) pHeader;
83219 + RxCell.DataSize = pRxWI->MPDUtotalByteCount;
83220 + RxCell.Flags = 0;
83221 +
83222 + // Increase Total receive byte counter after real data received no mater any error or not
83223 + pAd->RalinkCounters.ReceivedByteCount += pRxWI->MPDUtotalByteCount;
83224 + pAd->RalinkCounters.RxCount ++;
83225 +
83226 + INC_COUNTER64(pAd->WlanCounters.ReceivedFragmentCount);
83227 +
83228 + if (pRxWI->MPDUtotalByteCount < 14)
83229 + Status = NDIS_STATUS_FAILURE;
83230 +
83231 + if (MONITOR_ON(pAd))
83232 + {
83233 + send_monitor_packets(pAd, &RxCell);
83234 + break;
83235 + }
83236 + /* RT2870 invokes STARxDoneInterruptHandle() in rtusb_bulk.c */
83237 +#ifdef RALINK_ATE
83238 + if (ATE_ON(pAd))
83239 + {
83240 + pAd->ate.RxCntPerSec++;
83241 + ATESampleRssi(pAd, pRxWI);
83242 +#ifdef RALINK_28xx_QA
83243 + if (pAd->ate.bQARxStart == TRUE)
83244 + {
83245 + /* (*pRxD) has been swapped in GetPacketFromRxRing() */
83246 + ATE_QA_Statistics(pAd, pRxWI, pRxD, pHeader);
83247 + }
83248 +#endif // RALINK_28xx_QA //
83249 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_SUCCESS);
83250 + continue;
83251 + }
83252 +#endif // RALINK_ATE //
83253 +
83254 + // Check for all RxD errors
83255 + Status = RTMPCheckRxError(pAd, pHeader, pRxWI, pRxD);
83256 +
83257 + // Handle the received frame
83258 + if (Status == NDIS_STATUS_SUCCESS)
83259 + {
83260 + switch (pHeader->FC.Type)
83261 + {
83262 + // CASE I, receive a DATA frame
83263 + case BTYPE_DATA:
83264 + {
83265 + // process DATA frame
83266 + STAHandleRxDataFrame(pAd, &RxCell);
83267 + }
83268 + break;
83269 + // CASE II, receive a MGMT frame
83270 + case BTYPE_MGMT:
83271 + {
83272 + STAHandleRxMgmtFrame(pAd, &RxCell);
83273 + }
83274 + break;
83275 + // CASE III. receive a CNTL frame
83276 + case BTYPE_CNTL:
83277 + {
83278 + STAHandleRxControlFrame(pAd, &RxCell);
83279 + }
83280 + break;
83281 + // discard other type
83282 + default:
83283 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
83284 + break;
83285 + }
83286 + }
83287 + else
83288 + {
83289 + pAd->Counters8023.RxErrors++;
83290 + // discard this frame
83291 + RELEASE_NDIS_PACKET(pAd, pRxPacket, NDIS_STATUS_FAILURE);
83292 + }
83293 + }
83294 +
83295 + return bReschedule;
83296 +}
83297 +
83298 +/*
83299 + ========================================================================
83300 +
83301 + Routine Description:
83302 + Arguments:
83303 + pAd Pointer to our adapter
83304 +
83305 + IRQL = DISPATCH_LEVEL
83306 +
83307 + ========================================================================
83308 +*/
83309 +VOID RTMPHandleTwakeupInterrupt(
83310 + IN PRTMP_ADAPTER pAd)
83311 +{
83312 + AsicForceWakeup(pAd, FALSE);
83313 +}
83314 +
83315 +/*
83316 +========================================================================
83317 +Routine Description:
83318 + Early checking and OS-depened parsing for Tx packet send to our STA driver.
83319 +
83320 +Arguments:
83321 + NDIS_HANDLE MiniportAdapterContext Pointer refer to the device handle, i.e., the pAd.
83322 + PPNDIS_PACKET ppPacketArray The packet array need to do transmission.
83323 + UINT NumberOfPackets Number of packet in packet array.
83324 +
83325 +Return Value:
83326 + NONE
83327 +
83328 +Note:
83329 + This function do early checking and classification for send-out packet.
83330 + You only can put OS-depened & STA related code in here.
83331 +========================================================================
83332 +*/
83333 +VOID STASendPackets(
83334 + IN NDIS_HANDLE MiniportAdapterContext,
83335 + IN PPNDIS_PACKET ppPacketArray,
83336 + IN UINT NumberOfPackets)
83337 +{
83338 + UINT Index;
83339 + PRTMP_ADAPTER pAd = (PRTMP_ADAPTER) MiniportAdapterContext;
83340 + PNDIS_PACKET pPacket;
83341 + BOOLEAN allowToSend = FALSE;
83342 +
83343 +
83344 + for (Index = 0; Index < NumberOfPackets; Index++)
83345 + {
83346 + pPacket = ppPacketArray[Index];
83347 +
83348 + do
83349 + {
83350 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS) ||
83351 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS) ||
83352 + RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF))
83353 + {
83354 + // Drop send request since hardware is in reset state
83355 + break;
83356 + }
83357 + else if (!INFRA_ON(pAd) && !ADHOC_ON(pAd))
83358 + {
83359 + // Drop send request since there are no physical connection yet
83360 + break;
83361 + }
83362 + else
83363 + {
83364 + // Record that orignal packet source is from NDIS layer,so that
83365 + // later on driver knows how to release this NDIS PACKET
83366 +#ifdef QOS_DLS_SUPPORT
83367 + MAC_TABLE_ENTRY *pEntry;
83368 + PUCHAR pSrcBufVA = GET_OS_PKT_DATAPTR(pPacket);
83369 +
83370 + pEntry = MacTableLookup(pAd, pSrcBufVA);
83371 + if (pEntry && (pEntry->ValidAsDls == TRUE))
83372 + {
83373 + RTMP_SET_PACKET_WCID(pPacket, pEntry->Aid);
83374 + }
83375 + else
83376 +#endif // QOS_DLS_SUPPORT //
83377 + RTMP_SET_PACKET_WCID(pPacket, 0); // this field is useless when in STA mode
83378 + RTMP_SET_PACKET_SOURCE(pPacket, PKTSRC_NDIS);
83379 + NDIS_SET_PACKET_STATUS(pPacket, NDIS_STATUS_PENDING);
83380 + pAd->RalinkCounters.PendingNdisPacketCount++;
83381 +
83382 + allowToSend = TRUE;
83383 + }
83384 + } while(FALSE);
83385 +
83386 + if (allowToSend == TRUE)
83387 + STASendPacket(pAd, pPacket);
83388 + else
83389 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
83390 + }
83391 +
83392 + // Dequeue outgoing frames from TxSwQueue[] and process it
83393 + RTMPDeQueuePacket(pAd, FALSE, NUM_OF_TX_RING, MAX_TX_PROCESS);
83394 +
83395 +}
83396 +
83397 +
83398 +/*
83399 +========================================================================
83400 +Routine Description:
83401 + This routine is used to do packet parsing and classification for Tx packet
83402 + to STA device, and it will en-queue packets to our TxSwQueue depends on AC
83403 + class.
83404 +
83405 +Arguments:
83406 + pAd Pointer to our adapter
83407 + pPacket Pointer to send packet
83408 +
83409 +Return Value:
83410 + NDIS_STATUS_SUCCESS If succes to queue the packet into TxSwQueue.
83411 + NDIS_STATUS_FAILURE If failed to do en-queue.
83412 +
83413 +Note:
83414 + You only can put OS-indepened & STA related code in here.
83415 +========================================================================
83416 +*/
83417 +NDIS_STATUS STASendPacket(
83418 + IN PRTMP_ADAPTER pAd,
83419 + IN PNDIS_PACKET pPacket)
83420 +{
83421 + PACKET_INFO PacketInfo;
83422 + PUCHAR pSrcBufVA;
83423 + UINT SrcBufLen;
83424 + UINT AllowFragSize;
83425 + UCHAR NumberOfFrag;
83426 + UCHAR QueIdx, UserPriority;
83427 + MAC_TABLE_ENTRY *pEntry = NULL;
83428 + unsigned int IrqFlags;
83429 + UCHAR FlgIsIP = 0;
83430 + UCHAR Rate;
83431 +
83432 + // Prepare packet information structure for buffer descriptor
83433 + // chained within a single NDIS packet.
83434 + RTMP_QueryPacketInfo(pPacket, &PacketInfo, &pSrcBufVA, &SrcBufLen);
83435 +
83436 + if (pSrcBufVA == NULL)
83437 + {
83438 + DBGPRINT(RT_DEBUG_ERROR,("STASendPacket --> pSrcBufVA == NULL !!!SrcBufLen=%x\n",SrcBufLen));
83439 + // Resourece is low, system did not allocate virtual address
83440 + // return NDIS_STATUS_FAILURE directly to upper layer
83441 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
83442 + return NDIS_STATUS_FAILURE;
83443 + }
83444 +
83445 +
83446 + if (SrcBufLen < 14)
83447 + {
83448 + DBGPRINT(RT_DEBUG_ERROR,("STASendPacket --> Ndis Packet buffer error !!!\n"));
83449 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
83450 + return (NDIS_STATUS_FAILURE);
83451 + }
83452 +
83453 + // In HT rate adhoc mode, A-MPDU is often used. So need to lookup BA Table and MAC Entry.
83454 + // Note multicast packets in adhoc also use BSSID_WCID index.
83455 + {
83456 + if(INFRA_ON(pAd))
83457 + {
83458 +#ifdef QOS_DLS_SUPPORT
83459 + USHORT tmpWcid;
83460 +
83461 + tmpWcid = RTMP_GET_PACKET_WCID(pPacket);
83462 + if (VALID_WCID(tmpWcid) &&
83463 + (pAd->MacTab.Content[tmpWcid].ValidAsDls== TRUE))
83464 + {
83465 + pEntry = &pAd->MacTab.Content[tmpWcid];
83466 + Rate = pAd->MacTab.Content[tmpWcid].CurrTxRate;
83467 + }
83468 + else
83469 +#endif // QOS_DLS_SUPPORT //
83470 + {
83471 + pEntry = &pAd->MacTab.Content[BSSID_WCID];
83472 + RTMP_SET_PACKET_WCID(pPacket, BSSID_WCID);
83473 + Rate = pAd->CommonCfg.TxRate;
83474 + }
83475 + }
83476 + else if (ADHOC_ON(pAd))
83477 + {
83478 + if (*pSrcBufVA & 0x01)
83479 + {
83480 + RTMP_SET_PACKET_WCID(pPacket, MCAST_WCID);
83481 + pEntry = &pAd->MacTab.Content[MCAST_WCID];
83482 + }
83483 + else
83484 + {
83485 + pEntry = MacTableLookup(pAd, pSrcBufVA);
83486 + }
83487 + Rate = pAd->CommonCfg.TxRate;
83488 + }
83489 + }
83490 +
83491 + if (!pEntry)
83492 + {
83493 + DBGPRINT(RT_DEBUG_ERROR,("STASendPacket->Cannot find pEntry(%2x:%2x:%2x:%2x:%2x:%2x) in MacTab!\n", PRINT_MAC(pSrcBufVA)));
83494 + // Resourece is low, system did not allocate virtual address
83495 + // return NDIS_STATUS_FAILURE directly to upper layer
83496 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
83497 + return NDIS_STATUS_FAILURE;
83498 + }
83499 +
83500 + if (ADHOC_ON(pAd)
83501 + )
83502 + {
83503 + RTMP_SET_PACKET_WCID(pPacket, (UCHAR)pEntry->Aid);
83504 + }
83505 +
83506 + //
83507 + // Check the Ethernet Frame type of this packet, and set the RTMP_SET_PACKET_SPECIFIC flags.
83508 + // Here we set the PACKET_SPECIFIC flags(LLC, VLAN, DHCP/ARP, EAPOL).
83509 + RTMPCheckEtherType(pAd, pPacket);
83510 +
83511 +
83512 +
83513 + //
83514 + // WPA 802.1x secured port control - drop all non-802.1x frame before port secured
83515 + //
83516 + if (((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) ||
83517 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) ||
83518 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) ||
83519 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)
83520 +#ifdef WPA_SUPPLICANT_SUPPORT
83521 + || (pAd->StaCfg.IEEE8021X == TRUE)
83522 +#endif // WPA_SUPPLICANT_SUPPORT //
83523 +#ifdef LEAP_SUPPORT
83524 + || (pAd->StaCfg.LeapAuthMode == CISCO_AuthModeLEAP)
83525 +#endif // LEAP_SUPPORT //
83526 + )
83527 + && ((pAd->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED) || (pAd->StaCfg.MicErrCnt >= 2))
83528 + && (RTMP_GET_PACKET_EAPOL(pPacket)== FALSE)
83529 + )
83530 + {
83531 + DBGPRINT(RT_DEBUG_TRACE,("STASendPacket --> Drop packet before port secured !!!\n"));
83532 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
83533 +
83534 + return (NDIS_STATUS_FAILURE);
83535 + }
83536 +
83537 +
83538 + // STEP 1. Decide number of fragments required to deliver this MSDU.
83539 + // The estimation here is not very accurate because difficult to
83540 + // take encryption overhead into consideration here. The result
83541 + // "NumberOfFrag" is then just used to pre-check if enough free
83542 + // TXD are available to hold this MSDU.
83543 +
83544 +
83545 + if (*pSrcBufVA & 0x01) // fragmentation not allowed on multicast & broadcast
83546 + NumberOfFrag = 1;
83547 + else if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_AGGREGATION_INUSED))
83548 + NumberOfFrag = 1; // Aggregation overwhelms fragmentation
83549 + else if (CLIENT_STATUS_TEST_FLAG(pEntry, fCLIENT_STATUS_AMSDU_INUSED))
83550 + NumberOfFrag = 1; // Aggregation overwhelms fragmentation
83551 +#ifdef DOT11_N_SUPPORT
83552 + else if ((pAd->StaCfg.HTPhyMode.field.MODE == MODE_HTMIX) || (pAd->StaCfg.HTPhyMode.field.MODE == MODE_HTGREENFIELD))
83553 + NumberOfFrag = 1; // MIMO RATE overwhelms fragmentation
83554 +#endif // DOT11_N_SUPPORT //
83555 + else
83556 + {
83557 + // The calculated "NumberOfFrag" is a rough estimation because of various
83558 + // encryption/encapsulation overhead not taken into consideration. This number is just
83559 + // used to make sure enough free TXD are available before fragmentation takes place.
83560 + // In case the actual required number of fragments of an NDIS packet
83561 + // excceeds "NumberOfFrag"caculated here and not enough free TXD available, the
83562 + // last fragment (i.e. last MPDU) will be dropped in RTMPHardTransmit() due to out of
83563 + // resource, and the NDIS packet will be indicated NDIS_STATUS_FAILURE. This should
83564 + // rarely happen and the penalty is just like a TX RETRY fail. Affordable.
83565 +
83566 + AllowFragSize = (pAd->CommonCfg.FragmentThreshold) - LENGTH_802_11 - LENGTH_CRC;
83567 + NumberOfFrag = ((PacketInfo.TotalPacketLength - LENGTH_802_3 + LENGTH_802_1_H) / AllowFragSize) + 1;
83568 + // To get accurate number of fragmentation, Minus 1 if the size just match to allowable fragment size
83569 + if (((PacketInfo.TotalPacketLength - LENGTH_802_3 + LENGTH_802_1_H) % AllowFragSize) == 0)
83570 + {
83571 + NumberOfFrag--;
83572 + }
83573 + }
83574 +
83575 + // Save fragment number to Ndis packet reserved field
83576 + RTMP_SET_PACKET_FRAGMENTS(pPacket, NumberOfFrag);
83577 +
83578 +
83579 + // STEP 2. Check the requirement of RTS:
83580 + // If multiple fragment required, RTS is required only for the first fragment
83581 + // if the fragment size large than RTS threshold
83582 + // For RT28xx, Let ASIC send RTS/CTS
83583 + RTMP_SET_PACKET_RTS(pPacket, 0);
83584 + RTMP_SET_PACKET_TXRATE(pPacket, pAd->CommonCfg.TxRate);
83585 +
83586 + //
83587 + // STEP 3. Traffic classification. outcome = <UserPriority, QueIdx>
83588 + //
83589 + UserPriority = 0;
83590 + QueIdx = QID_AC_BE;
83591 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED))
83592 + {
83593 + USHORT Protocol;
83594 + UCHAR LlcSnapLen = 0, Byte0, Byte1;
83595 + do
83596 + {
83597 + // get Ethernet protocol field
83598 + Protocol = (USHORT)((pSrcBufVA[12] << 8) + pSrcBufVA[13]);
83599 + if (Protocol <= 1500)
83600 + {
83601 + // get Ethernet protocol field from LLC/SNAP
83602 + if (Sniff2BytesFromNdisBuffer(PacketInfo.pFirstBuffer, LENGTH_802_3 + 6, &Byte0, &Byte1) != NDIS_STATUS_SUCCESS)
83603 + break;
83604 +
83605 + Protocol = (USHORT)((Byte0 << 8) + Byte1);
83606 + LlcSnapLen = 8;
83607 + }
83608 +
83609 + // always AC_BE for non-IP packet
83610 + if (Protocol != 0x0800)
83611 + break;
83612 +
83613 + // get IP header
83614 + if (Sniff2BytesFromNdisBuffer(PacketInfo.pFirstBuffer, LENGTH_802_3 + LlcSnapLen, &Byte0, &Byte1) != NDIS_STATUS_SUCCESS)
83615 + break;
83616 +
83617 + // return AC_BE if packet is not IPv4
83618 + if ((Byte0 & 0xf0) != 0x40)
83619 + break;
83620 +
83621 + FlgIsIP = 1;
83622 + UserPriority = (Byte1 & 0xe0) >> 5;
83623 + QueIdx = MapUserPriorityToAccessCategory[UserPriority];
83624 +
83625 + // TODO: have to check ACM bit. apply TSPEC if ACM is ON
83626 + // TODO: downgrade UP & QueIdx before passing ACM
83627 + if (pAd->CommonCfg.APEdcaParm.bACM[QueIdx])
83628 + {
83629 + UserPriority = 0;
83630 + QueIdx = QID_AC_BE;
83631 + }
83632 + } while (FALSE);
83633 + }
83634 +
83635 + RTMP_SET_PACKET_UP(pPacket, UserPriority);
83636 +
83637 +
83638 +
83639 + // Make sure SendTxWait queue resource won't be used by other threads
83640 + RTMP_IRQ_LOCK(&pAd->irq_lock, IrqFlags);
83641 + if (pAd->TxSwQueue[QueIdx].Number >= MAX_PACKETS_IN_QUEUE)
83642 + {
83643 + RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
83644 +#ifdef BLOCK_NET_IF
83645 + StopNetIfQueue(pAd, QueIdx, pPacket);
83646 +#endif // BLOCK_NET_IF //
83647 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
83648 +
83649 + return NDIS_STATUS_FAILURE;
83650 + }
83651 + else
83652 + {
83653 + InsertTailQueue(&pAd->TxSwQueue[QueIdx], PACKET_TO_QUEUE_ENTRY(pPacket));
83654 + }
83655 + RTMP_IRQ_UNLOCK(&pAd->irq_lock, IrqFlags);
83656 +
83657 +#ifdef DOT11_N_SUPPORT
83658 + if ((pAd->CommonCfg.BACapability.field.AutoBA == TRUE)&&
83659 + (pAd->StaActive.SupportedPhyInfo.bHtEnable == TRUE))
83660 + {
83661 + if (((pEntry->TXBAbitmap & (1<<UserPriority)) == 0) &&
83662 + ((pEntry->BADeclineBitmap & (1<<UserPriority)) == 0) &&
83663 + (pEntry->PortSecured == WPA_802_1X_PORT_SECURED)
83664 + // For IOT compatibility, if
83665 + // 1. It is Ralink chip or
83666 + // 2. It is OPEN or AES mode,
83667 + // then BA session can be bulit.
83668 + && ((pEntry->ValidAsCLI && pAd->MlmeAux.APRalinkIe != 0x0) ||
83669 + (pEntry->WepStatus == Ndis802_11WEPDisabled || pEntry->WepStatus == Ndis802_11Encryption3Enabled))
83670 + )
83671 + {
83672 + BAOriSessionSetUp(pAd, pEntry, 0, 0, 10, FALSE);
83673 + }
83674 + }
83675 +#endif // DOT11_N_SUPPORT //
83676 +
83677 + pAd->RalinkCounters.OneSecOsTxCount[QueIdx]++; // TODO: for debug only. to be removed
83678 + return NDIS_STATUS_SUCCESS;
83679 +}
83680 +
83681 +
83682 +/*
83683 + ========================================================================
83684 +
83685 + Routine Description:
83686 + This subroutine will scan through releative ring descriptor to find
83687 + out avaliable free ring descriptor and compare with request size.
83688 +
83689 + Arguments:
83690 + pAd Pointer to our adapter
83691 + QueIdx Selected TX Ring
83692 +
83693 + Return Value:
83694 + NDIS_STATUS_FAILURE Not enough free descriptor
83695 + NDIS_STATUS_SUCCESS Enough free descriptor
83696 +
83697 + IRQL = PASSIVE_LEVEL
83698 + IRQL = DISPATCH_LEVEL
83699 +
83700 + Note:
83701 +
83702 + ========================================================================
83703 +*/
83704 +#ifdef RT2860
83705 +NDIS_STATUS RTMPFreeTXDRequest(
83706 + IN PRTMP_ADAPTER pAd,
83707 + IN UCHAR QueIdx,
83708 + IN UCHAR NumberRequired,
83709 + IN PUCHAR FreeNumberIs)
83710 +{
83711 + ULONG FreeNumber = 0;
83712 + NDIS_STATUS Status = NDIS_STATUS_FAILURE;
83713 +
83714 + switch (QueIdx)
83715 + {
83716 + case QID_AC_BK:
83717 + case QID_AC_BE:
83718 + case QID_AC_VI:
83719 + case QID_AC_VO:
83720 + case QID_HCCA:
83721 + if (pAd->TxRing[QueIdx].TxSwFreeIdx > pAd->TxRing[QueIdx].TxCpuIdx)
83722 + FreeNumber = pAd->TxRing[QueIdx].TxSwFreeIdx - pAd->TxRing[QueIdx].TxCpuIdx - 1;
83723 + else
83724 + FreeNumber = pAd->TxRing[QueIdx].TxSwFreeIdx + TX_RING_SIZE - pAd->TxRing[QueIdx].TxCpuIdx - 1;
83725 +
83726 + if (FreeNumber >= NumberRequired)
83727 + Status = NDIS_STATUS_SUCCESS;
83728 + break;
83729 +
83730 + case QID_MGMT:
83731 + if (pAd->MgmtRing.TxSwFreeIdx > pAd->MgmtRing.TxCpuIdx)
83732 + FreeNumber = pAd->MgmtRing.TxSwFreeIdx - pAd->MgmtRing.TxCpuIdx - 1;
83733 + else
83734 + FreeNumber = pAd->MgmtRing.TxSwFreeIdx + MGMT_RING_SIZE - pAd->MgmtRing.TxCpuIdx - 1;
83735 +
83736 + if (FreeNumber >= NumberRequired)
83737 + Status = NDIS_STATUS_SUCCESS;
83738 + break;
83739 +
83740 + default:
83741 + DBGPRINT(RT_DEBUG_ERROR,("RTMPFreeTXDRequest::Invalid QueIdx(=%d)\n", QueIdx));
83742 + break;
83743 + }
83744 + *FreeNumberIs = (UCHAR)FreeNumber;
83745 +
83746 + return (Status);
83747 +}
83748 +#endif // RT2860 //
83749 +
83750 +
83751 +
83752 +VOID RTMPSendDisassociationFrame(
83753 + IN PRTMP_ADAPTER pAd)
83754 +{
83755 +}
83756 +
83757 +VOID RTMPSendNullFrame(
83758 + IN PRTMP_ADAPTER pAd,
83759 + IN UCHAR TxRate,
83760 + IN BOOLEAN bQosNull)
83761 +{
83762 + UCHAR NullFrame[48];
83763 + ULONG Length;
83764 + PHEADER_802_11 pHeader_802_11;
83765 +
83766 +
83767 +#ifdef RALINK_ATE
83768 + if(ATE_ON(pAd))
83769 + {
83770 + return;
83771 + }
83772 +#endif // RALINK_ATE //
83773 +
83774 + // WPA 802.1x secured port control
83775 + if (((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA) ||
83776 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) ||
83777 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) ||
83778 + (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)
83779 +#ifdef WPA_SUPPLICANT_SUPPORT
83780 + || (pAd->StaCfg.IEEE8021X == TRUE)
83781 +#endif
83782 + ) &&
83783 + (pAd->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED))
83784 + {
83785 + return;
83786 + }
83787 +
83788 + NdisZeroMemory(NullFrame, 48);
83789 + Length = sizeof(HEADER_802_11);
83790 +
83791 + pHeader_802_11 = (PHEADER_802_11) NullFrame;
83792 +
83793 + pHeader_802_11->FC.Type = BTYPE_DATA;
83794 + pHeader_802_11->FC.SubType = SUBTYPE_NULL_FUNC;
83795 + pHeader_802_11->FC.ToDs = 1;
83796 + COPY_MAC_ADDR(pHeader_802_11->Addr1, pAd->CommonCfg.Bssid);
83797 + COPY_MAC_ADDR(pHeader_802_11->Addr2, pAd->CurrentAddress);
83798 + COPY_MAC_ADDR(pHeader_802_11->Addr3, pAd->CommonCfg.Bssid);
83799 +
83800 + if (pAd->CommonCfg.bAPSDForcePowerSave)
83801 + {
83802 + pHeader_802_11->FC.PwrMgmt = PWR_SAVE;
83803 + }
83804 + else
83805 + {
83806 + pHeader_802_11->FC.PwrMgmt = (pAd->StaCfg.Psm == PWR_SAVE) ? 1: 0;
83807 + }
83808 + pHeader_802_11->Duration = pAd->CommonCfg.Dsifs + RTMPCalcDuration(pAd, TxRate, 14);
83809 +
83810 + pAd->Sequence++;
83811 + pHeader_802_11->Sequence = pAd->Sequence;
83812 +
83813 + // Prepare QosNull function frame
83814 + if (bQosNull)
83815 + {
83816 + pHeader_802_11->FC.SubType = SUBTYPE_QOS_NULL;
83817 +
83818 + // copy QOS control bytes
83819 + NullFrame[Length] = 0;
83820 + NullFrame[Length+1] = 0;
83821 + Length += 2;// if pad with 2 bytes for alignment, APSD will fail
83822 + }
83823 +
83824 + HAL_KickOutNullFrameTx(pAd, 0, NullFrame, Length);
83825 +
83826 +}
83827 +
83828 +// IRQL = DISPATCH_LEVEL
83829 +VOID RTMPSendRTSFrame(
83830 + IN PRTMP_ADAPTER pAd,
83831 + IN PUCHAR pDA,
83832 + IN unsigned int NextMpduSize,
83833 + IN UCHAR TxRate,
83834 + IN UCHAR RTSRate,
83835 + IN USHORT AckDuration,
83836 + IN UCHAR QueIdx,
83837 + IN UCHAR FrameGap)
83838 +{
83839 +}
83840 +
83841 +
83842 +
83843 +// --------------------------------------------------------
83844 +// FIND ENCRYPT KEY AND DECIDE CIPHER ALGORITHM
83845 +// Find the WPA key, either Group or Pairwise Key
83846 +// LEAP + TKIP also use WPA key.
83847 +// --------------------------------------------------------
83848 +// Decide WEP bit and cipher suite to be used. Same cipher suite should be used for whole fragment burst
83849 +// In Cisco CCX 2.0 Leap Authentication
83850 +// WepStatus is Ndis802_11Encryption1Enabled but the key will use PairwiseKey
83851 +// Instead of the SharedKey, SharedKey Length may be Zero.
83852 +VOID STAFindCipherAlgorithm(
83853 + IN PRTMP_ADAPTER pAd,
83854 + IN TX_BLK *pTxBlk)
83855 +{
83856 + NDIS_802_11_ENCRYPTION_STATUS Cipher; // To indicate cipher used for this packet
83857 + UCHAR CipherAlg = CIPHER_NONE; // cipher alogrithm
83858 + UCHAR KeyIdx = 0xff;
83859 + PUCHAR pSrcBufVA;
83860 + PCIPHER_KEY pKey = NULL;
83861 +
83862 + pSrcBufVA = GET_OS_PKT_DATAPTR(pTxBlk->pPacket);
83863 +
83864 + {
83865 + // Select Cipher
83866 + if ((*pSrcBufVA & 0x01) && (ADHOC_ON(pAd)))
83867 + Cipher = pAd->StaCfg.GroupCipher; // Cipher for Multicast or Broadcast
83868 + else
83869 + Cipher = pAd->StaCfg.PairCipher; // Cipher for Unicast
83870 +
83871 + if (RTMP_GET_PACKET_EAPOL(pTxBlk->pPacket))
83872 + {
83873 + ASSERT(pAd->SharedKey[BSS0][0].CipherAlg <= CIPHER_CKIP128);
83874 +
83875 + // 4-way handshaking frame must be clear
83876 + if (!(TX_BLK_TEST_FLAG(pTxBlk, fTX_bClearEAPFrame)) && (pAd->SharedKey[BSS0][0].CipherAlg) &&
83877 + (pAd->SharedKey[BSS0][0].KeyLen))
83878 + {
83879 + CipherAlg = pAd->SharedKey[BSS0][0].CipherAlg;
83880 + KeyIdx = 0;
83881 + }
83882 + }
83883 + else if (Cipher == Ndis802_11Encryption1Enabled)
83884 + {
83885 +#ifdef LEAP_SUPPORT
83886 + if (pAd->StaCfg.CkipFlag & 0x10) // Cisco CKIP KP is on
83887 + {
83888 + if (LEAP_CCKM_ON(pAd))
83889 + {
83890 + if (((*pSrcBufVA & 0x01) && (ADHOC_ON(pAd))))
83891 + KeyIdx = 1;
83892 + else
83893 + KeyIdx = 0;
83894 + }
83895 + else
83896 + KeyIdx = pAd->StaCfg.DefaultKeyId;
83897 + }
83898 + else if (pAd->StaCfg.CkipFlag & 0x08) // only CKIP CMIC
83899 + KeyIdx = pAd->StaCfg.DefaultKeyId;
83900 + else if (LEAP_CCKM_ON(pAd))
83901 + {
83902 + if ((*pSrcBufVA & 0x01) && (ADHOC_ON(pAd)))
83903 + KeyIdx = 1;
83904 + else
83905 + KeyIdx = 0;
83906 + }
83907 + else // standard WEP64 or WEP128
83908 +#endif // LEAP_SUPPORT //
83909 + KeyIdx = pAd->StaCfg.DefaultKeyId;
83910 + }
83911 + else if ((Cipher == Ndis802_11Encryption2Enabled) ||
83912 + (Cipher == Ndis802_11Encryption3Enabled))
83913 + {
83914 + if ((*pSrcBufVA & 0x01) && (ADHOC_ON(pAd))) // multicast
83915 + KeyIdx = pAd->StaCfg.DefaultKeyId;
83916 + else if (pAd->SharedKey[BSS0][0].KeyLen)
83917 + KeyIdx = 0;
83918 + else
83919 + KeyIdx = pAd->StaCfg.DefaultKeyId;
83920 + }
83921 +
83922 + if (KeyIdx == 0xff)
83923 + CipherAlg = CIPHER_NONE;
83924 + else if ((Cipher == Ndis802_11EncryptionDisabled) || (pAd->SharedKey[BSS0][KeyIdx].KeyLen == 0))
83925 + CipherAlg = CIPHER_NONE;
83926 +#ifdef WPA_SUPPLICANT_SUPPORT
83927 + else if ( pAd->StaCfg.WpaSupplicantUP &&
83928 + (Cipher == Ndis802_11Encryption1Enabled) &&
83929 + (pAd->StaCfg.IEEE8021X == TRUE) &&
83930 + (pAd->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED))
83931 + CipherAlg = CIPHER_NONE;
83932 +#endif // WPA_SUPPLICANT_SUPPORT //
83933 + else
83934 + {
83935 + //Header_802_11.FC.Wep = 1;
83936 + CipherAlg = pAd->SharedKey[BSS0][KeyIdx].CipherAlg;
83937 + pKey = &pAd->SharedKey[BSS0][KeyIdx];
83938 + }
83939 + }
83940 +
83941 + pTxBlk->CipherAlg = CipherAlg;
83942 + pTxBlk->pKey = pKey;
83943 +}
83944 +
83945 +
83946 +VOID STABuildCommon802_11Header(
83947 + IN PRTMP_ADAPTER pAd,
83948 + IN TX_BLK *pTxBlk)
83949 +{
83950 +
83951 + HEADER_802_11 *pHeader_802_11;
83952 +#ifdef QOS_DLS_SUPPORT
83953 + BOOLEAN bDLSFrame = FALSE;
83954 + INT DlsEntryIndex = 0;
83955 +#endif // QOS_DLS_SUPPORT //
83956 +
83957 + //
83958 + // MAKE A COMMON 802.11 HEADER
83959 + //
83960 +
83961 + // normal wlan header size : 24 octets
83962 + pTxBlk->MpduHeaderLen = sizeof(HEADER_802_11);
83963 +
83964 + pHeader_802_11 = (HEADER_802_11 *) &pTxBlk->HeaderBuf[TXINFO_SIZE + TXWI_SIZE];
83965 +
83966 + NdisZeroMemory(pHeader_802_11, sizeof(HEADER_802_11));
83967 +
83968 + pHeader_802_11->FC.FrDs = 0;
83969 + pHeader_802_11->FC.Type = BTYPE_DATA;
83970 + pHeader_802_11->FC.SubType = ((TX_BLK_TEST_FLAG(pTxBlk, fTX_bWMM)) ? SUBTYPE_QDATA : SUBTYPE_DATA);
83971 +
83972 +#ifdef QOS_DLS_SUPPORT
83973 + if (INFRA_ON(pAd))
83974 + {
83975 + // Check if the frame can be sent through DLS direct link interface
83976 + // If packet can be sent through DLS, then force aggregation disable. (Hard to determine peer STA's capability)
83977 + DlsEntryIndex = RTMPCheckDLSFrame(pAd, pTxBlk->pSrcBufHeader);
83978 + if (DlsEntryIndex >= 0)
83979 + bDLSFrame = TRUE;
83980 + else
83981 + bDLSFrame = FALSE;
83982 + }
83983 +#endif // QOS_DLS_SUPPORT //
83984 +
83985 + if (pTxBlk->pMacEntry)
83986 + {
83987 + if (TX_BLK_TEST_FLAG(pTxBlk, fTX_bForceNonQoS))
83988 + {
83989 + pHeader_802_11->Sequence = pTxBlk->pMacEntry->NonQosDataSeq;
83990 + pTxBlk->pMacEntry->NonQosDataSeq = (pTxBlk->pMacEntry->NonQosDataSeq+1) & MAXSEQ;
83991 + }
83992 + else
83993 + {
83994 +#ifdef QOS_DLS_SUPPORT
83995 + if (bDLSFrame)
83996 + {
83997 + pHeader_802_11->Sequence = pAd->StaCfg.DLSEntry[DlsEntryIndex].Sequence;
83998 + pAd->StaCfg.DLSEntry[DlsEntryIndex].Sequence = (pAd->StaCfg.DLSEntry[DlsEntryIndex].Sequence+1) & MAXSEQ;
83999 + }
84000 + else
84001 +#endif // QOS_DLS_SUPPORT //
84002 + {
84003 + pHeader_802_11->Sequence = pTxBlk->pMacEntry->TxSeq[pTxBlk->UserPriority];
84004 + pTxBlk->pMacEntry->TxSeq[pTxBlk->UserPriority] = (pTxBlk->pMacEntry->TxSeq[pTxBlk->UserPriority]+1) & MAXSEQ;
84005 + }
84006 + }
84007 + }
84008 + else
84009 + {
84010 + pHeader_802_11->Sequence = pAd->Sequence;
84011 + pAd->Sequence = (pAd->Sequence+1) & MAXSEQ; // next sequence
84012 + }
84013 +
84014 + pHeader_802_11->Frag = 0;
84015 +
84016 + pHeader_802_11->FC.MoreData = TX_BLK_TEST_FLAG(pTxBlk, fTX_bMoreData);
84017 +
84018 + {
84019 + if (INFRA_ON(pAd))
84020 + {
84021 +#ifdef QOS_DLS_SUPPORT
84022 + if (bDLSFrame)
84023 + {
84024 + COPY_MAC_ADDR(pHeader_802_11->Addr1, pTxBlk->pSrcBufHeader);
84025 + COPY_MAC_ADDR(pHeader_802_11->Addr2, pAd->CurrentAddress);
84026 + COPY_MAC_ADDR(pHeader_802_11->Addr3, pAd->CommonCfg.Bssid);
84027 + pHeader_802_11->FC.ToDs = 0;
84028 + }
84029 + else
84030 +#endif // QOS_DLS_SUPPORT //
84031 + {
84032 + COPY_MAC_ADDR(pHeader_802_11->Addr1, pAd->CommonCfg.Bssid);
84033 + COPY_MAC_ADDR(pHeader_802_11->Addr2, pAd->CurrentAddress);
84034 + COPY_MAC_ADDR(pHeader_802_11->Addr3, pTxBlk->pSrcBufHeader);
84035 + pHeader_802_11->FC.ToDs = 1;
84036 + }
84037 + }
84038 + else if (ADHOC_ON(pAd))
84039 + {
84040 + COPY_MAC_ADDR(pHeader_802_11->Addr1, pTxBlk->pSrcBufHeader);
84041 + COPY_MAC_ADDR(pHeader_802_11->Addr2, pAd->CurrentAddress);
84042 + COPY_MAC_ADDR(pHeader_802_11->Addr3, pAd->CommonCfg.Bssid);
84043 + pHeader_802_11->FC.ToDs = 0;
84044 + }
84045 + }
84046 +
84047 + if (pTxBlk->CipherAlg != CIPHER_NONE)
84048 + pHeader_802_11->FC.Wep = 1;
84049 +
84050 + // -----------------------------------------------------------------
84051 + // STEP 2. MAKE A COMMON 802.11 HEADER SHARED BY ENTIRE FRAGMENT BURST. Fill sequence later.
84052 + // -----------------------------------------------------------------
84053 + if (pAd->CommonCfg.bAPSDForcePowerSave)
84054 + pHeader_802_11->FC.PwrMgmt = PWR_SAVE;
84055 + else
84056 + pHeader_802_11->FC.PwrMgmt = (pAd->StaCfg.Psm == PWR_SAVE);
84057 +}
84058 +
84059 +#ifdef DOT11_N_SUPPORT
84060 +VOID STABuildCache802_11Header(
84061 + IN RTMP_ADAPTER *pAd,
84062 + IN TX_BLK *pTxBlk,
84063 + IN UCHAR *pHeader)
84064 +{
84065 + MAC_TABLE_ENTRY *pMacEntry;
84066 + PHEADER_802_11 pHeader80211;
84067 +
84068 + pHeader80211 = (PHEADER_802_11)pHeader;
84069 + pMacEntry = pTxBlk->pMacEntry;
84070 +
84071 + //
84072 + // Update the cached 802.11 HEADER
84073 + //
84074 +
84075 + // normal wlan header size : 24 octets
84076 + pTxBlk->MpduHeaderLen = sizeof(HEADER_802_11);
84077 +
84078 + // More Bit
84079 + pHeader80211->FC.MoreData = TX_BLK_TEST_FLAG(pTxBlk, fTX_bMoreData);
84080 +
84081 + // Sequence
84082 + pHeader80211->Sequence = pMacEntry->TxSeq[pTxBlk->UserPriority];
84083 + pMacEntry->TxSeq[pTxBlk->UserPriority] = (pMacEntry->TxSeq[pTxBlk->UserPriority]+1) & MAXSEQ;
84084 +
84085 + {
84086 + // Check if the frame can be sent through DLS direct link interface
84087 + // If packet can be sent through DLS, then force aggregation disable. (Hard to determine peer STA's capability)
84088 +#ifdef QOS_DLS_SUPPORT
84089 + BOOLEAN bDLSFrame = FALSE;
84090 + INT DlsEntryIndex = 0;
84091 +
84092 + DlsEntryIndex = RTMPCheckDLSFrame(pAd, pTxBlk->pSrcBufHeader);
84093 + if (DlsEntryIndex >= 0)
84094 + bDLSFrame = TRUE;
84095 + else
84096 + bDLSFrame = FALSE;
84097 +#endif // QOS_DLS_SUPPORT //
84098 +
84099 + // The addr3 of normal packet send from DS is Dest Mac address.
84100 +#ifdef QOS_DLS_SUPPORT
84101 + if (bDLSFrame)
84102 + {
84103 + COPY_MAC_ADDR(pHeader80211->Addr1, pTxBlk->pSrcBufHeader);
84104 + COPY_MAC_ADDR(pHeader80211->Addr3, pAd->CommonCfg.Bssid);
84105 + pHeader80211->FC.ToDs = 0;
84106 + }
84107 + else
84108 +#endif // QOS_DLS_SUPPORT //
84109 + if (ADHOC_ON(pAd))
84110 + COPY_MAC_ADDR(pHeader80211->Addr3, pAd->CommonCfg.Bssid);
84111 + else
84112 + COPY_MAC_ADDR(pHeader80211->Addr3, pTxBlk->pSrcBufHeader);
84113 + }
84114 +
84115 + // -----------------------------------------------------------------
84116 + // STEP 2. MAKE A COMMON 802.11 HEADER SHARED BY ENTIRE FRAGMENT BURST. Fill sequence later.
84117 + // -----------------------------------------------------------------
84118 + if (pAd->CommonCfg.bAPSDForcePowerSave)
84119 + pHeader80211->FC.PwrMgmt = PWR_SAVE;
84120 + else
84121 + pHeader80211->FC.PwrMgmt = (pAd->StaCfg.Psm == PWR_SAVE);
84122 +}
84123 +#endif // DOT11_N_SUPPORT //
84124 +
84125 +static inline PUCHAR STA_Build_ARalink_Frame_Header(
84126 + IN RTMP_ADAPTER *pAd,
84127 + IN TX_BLK *pTxBlk)
84128 +{
84129 + PUCHAR pHeaderBufPtr;
84130 + HEADER_802_11 *pHeader_802_11;
84131 + PNDIS_PACKET pNextPacket;
84132 + UINT32 nextBufLen;
84133 + PQUEUE_ENTRY pQEntry;
84134 +
84135 + STAFindCipherAlgorithm(pAd, pTxBlk);
84136 + STABuildCommon802_11Header(pAd, pTxBlk);
84137 +
84138 +
84139 + pHeaderBufPtr = &pTxBlk->HeaderBuf[TXINFO_SIZE + TXWI_SIZE];
84140 + pHeader_802_11 = (HEADER_802_11 *) pHeaderBufPtr;
84141 +
84142 + // steal "order" bit to mark "aggregation"
84143 + pHeader_802_11->FC.Order = 1;
84144 +
84145 + // skip common header
84146 + pHeaderBufPtr += pTxBlk->MpduHeaderLen;
84147 +
84148 + if (TX_BLK_TEST_FLAG(pTxBlk, fTX_bWMM))
84149 + {
84150 + //
84151 + // build QOS Control bytes
84152 + //
84153 + *pHeaderBufPtr = (pTxBlk->UserPriority & 0x0F);
84154 +
84155 + *(pHeaderBufPtr+1) = 0;
84156 + pHeaderBufPtr +=2;
84157 + pTxBlk->MpduHeaderLen += 2;
84158 + }
84159 +
84160 + // padding at front of LLC header. LLC header should at 4-bytes aligment.
84161 + pTxBlk->HdrPadLen = (ULONG)pHeaderBufPtr;
84162 + pHeaderBufPtr = (PCHAR)ROUND_UP(pHeaderBufPtr, 4);
84163 + pTxBlk->HdrPadLen = (ULONG)(pHeaderBufPtr - pTxBlk->HdrPadLen);
84164 +
84165 + // For RA Aggregation,
84166 + // put the 2nd MSDU length(extra 2-byte field) after QOS_CONTROL in little endian format
84167 + pQEntry = pTxBlk->TxPacketList.Head;
84168 + pNextPacket = QUEUE_ENTRY_TO_PKT(pQEntry);
84169 + nextBufLen = GET_OS_PKT_LEN(pNextPacket);
84170 + if (RTMP_GET_PACKET_VLAN(pNextPacket))
84171 + nextBufLen -= LENGTH_802_1Q;
84172 +
84173 + *pHeaderBufPtr = (UCHAR)nextBufLen & 0xff;
84174 + *(pHeaderBufPtr+1) = (UCHAR)(nextBufLen >> 8);
84175 +
84176 + pHeaderBufPtr += 2;
84177 + pTxBlk->MpduHeaderLen += 2;
84178 +
84179 + return pHeaderBufPtr;
84180 +
84181 +}
84182 +
84183 +#ifdef DOT11_N_SUPPORT
84184 +static inline PUCHAR STA_Build_AMSDU_Frame_Header(
84185 + IN RTMP_ADAPTER *pAd,
84186 + IN TX_BLK *pTxBlk)
84187 +{
84188 + PUCHAR pHeaderBufPtr;//, pSaveBufPtr;
84189 + HEADER_802_11 *pHeader_802_11;
84190 +
84191 +
84192 + STAFindCipherAlgorithm(pAd, pTxBlk);
84193 + STABuildCommon802_11Header(pAd, pTxBlk);
84194 +
84195 + pHeaderBufPtr = &pTxBlk->HeaderBuf[TXINFO_SIZE + TXWI_SIZE];
84196 + pHeader_802_11 = (HEADER_802_11 *) pHeaderBufPtr;
84197 +
84198 + // skip common header
84199 + pHeaderBufPtr += pTxBlk->MpduHeaderLen;
84200 +
84201 + //
84202 + // build QOS Control bytes
84203 + //
84204 + *pHeaderBufPtr = (pTxBlk->UserPriority & 0x0F);
84205 +
84206 + //
84207 + // A-MSDU packet
84208 + //
84209 + *pHeaderBufPtr |= 0x80;
84210 +
84211 + *(pHeaderBufPtr+1) = 0;
84212 + pHeaderBufPtr +=2;
84213 + pTxBlk->MpduHeaderLen += 2;
84214 +
84215 + //pSaveBufPtr = pHeaderBufPtr;
84216 +
84217 + //
84218 + // padding at front of LLC header
84219 + // LLC header should locate at 4-octets aligment
84220 + //
84221 + // @@@ MpduHeaderLen excluding padding @@@
84222 + //
84223 + pTxBlk->HdrPadLen = (ULONG)pHeaderBufPtr;
84224 + pHeaderBufPtr = (PCHAR) ROUND_UP(pHeaderBufPtr, 4);
84225 + pTxBlk->HdrPadLen = (ULONG)(pHeaderBufPtr - pTxBlk->HdrPadLen);
84226 +
84227 + return pHeaderBufPtr;
84228 +
84229 +}
84230 +
84231 +
84232 +VOID STA_AMPDU_Frame_Tx(
84233 + IN PRTMP_ADAPTER pAd,
84234 + IN TX_BLK *pTxBlk)
84235 +{
84236 + HEADER_802_11 *pHeader_802_11;
84237 + PUCHAR pHeaderBufPtr;
84238 + USHORT FreeNumber;
84239 + MAC_TABLE_ENTRY *pMacEntry;
84240 + BOOLEAN bVLANPkt;
84241 + PQUEUE_ENTRY pQEntry;
84242 +
84243 + ASSERT(pTxBlk);
84244 +
84245 + while(pTxBlk->TxPacketList.Head)
84246 + {
84247 + pQEntry = RemoveHeadQueue(&pTxBlk->TxPacketList);
84248 + pTxBlk->pPacket = QUEUE_ENTRY_TO_PACKET(pQEntry);
84249 + if ( RTMP_FillTxBlkInfo(pAd, pTxBlk) != TRUE)
84250 + {
84251 + RELEASE_NDIS_PACKET(pAd, pTxBlk->pPacket, NDIS_STATUS_FAILURE);
84252 + continue;
84253 + }
84254 +
84255 + bVLANPkt = (RTMP_GET_PACKET_VLAN(pTxBlk->pPacket) ? TRUE : FALSE);
84256 +
84257 + pMacEntry = pTxBlk->pMacEntry;
84258 + if (pMacEntry->isCached)
84259 + {
84260 + // NOTE: Please make sure the size of pMacEntry->CachedBuf[] is smaller than pTxBlk->HeaderBuf[]!!!!
84261 + NdisMoveMemory((PUCHAR)&pTxBlk->HeaderBuf[TXINFO_SIZE], (PUCHAR)&pMacEntry->CachedBuf[0], TXWI_SIZE + sizeof(HEADER_802_11));
84262 + pHeaderBufPtr = (PUCHAR)(&pTxBlk->HeaderBuf[TXINFO_SIZE + TXWI_SIZE]);
84263 + STABuildCache802_11Header(pAd, pTxBlk, pHeaderBufPtr);
84264 + }
84265 + else
84266 + {
84267 + STAFindCipherAlgorithm(pAd, pTxBlk);
84268 + STABuildCommon802_11Header(pAd, pTxBlk);
84269 +
84270 + pHeaderBufPtr = &pTxBlk->HeaderBuf[TXINFO_SIZE + TXWI_SIZE];
84271 + }
84272 +
84273 +
84274 + pHeader_802_11 = (HEADER_802_11 *) pHeaderBufPtr;
84275 +
84276 + // skip common header
84277 + pHeaderBufPtr += pTxBlk->MpduHeaderLen;
84278 +
84279 + //
84280 + // build QOS Control bytes
84281 + //
84282 + *pHeaderBufPtr = (pTxBlk->UserPriority & 0x0F);
84283 + *(pHeaderBufPtr+1) = 0;
84284 + pHeaderBufPtr +=2;
84285 + pTxBlk->MpduHeaderLen += 2;
84286 +
84287 + //
84288 + // build HTC+
84289 + // HTC control filed following QoS field
84290 + //
84291 + if ((pAd->CommonCfg.bRdg == TRUE) && CLIENT_STATUS_TEST_FLAG(pTxBlk->pMacEntry, fCLIENT_STATUS_RDG_CAPABLE))
84292 + {
84293 + if (pMacEntry->isCached == FALSE)
84294 + {
84295 + // mark HTC bit
84296 + pHeader_802_11->FC.Order = 1;
84297 +
84298 + NdisZeroMemory(pHeaderBufPtr, 4);
84299 + *(pHeaderBufPtr+3) |= 0x80;
84300 + }
84301 + pHeaderBufPtr += 4;
84302 + pTxBlk->MpduHeaderLen += 4;
84303 + }
84304 +
84305 + //pTxBlk->MpduHeaderLen = pHeaderBufPtr - pTxBlk->HeaderBuf - TXWI_SIZE - TXINFO_SIZE;
84306 + ASSERT(pTxBlk->MpduHeaderLen >= 24);
84307 +
84308 + // skip 802.3 header
84309 + pTxBlk->pSrcBufData = pTxBlk->pSrcBufHeader + LENGTH_802_3;
84310 + pTxBlk->SrcBufLen -= LENGTH_802_3;
84311 +
84312 + // skip vlan tag
84313 + if (bVLANPkt)
84314 + {
84315 + pTxBlk->pSrcBufData += LENGTH_802_1Q;
84316 + pTxBlk->SrcBufLen -= LENGTH_802_1Q;
84317 + }
84318 +
84319 + //
84320 + // padding at front of LLC header
84321 + // LLC header should locate at 4-octets aligment
84322 + //
84323 + // @@@ MpduHeaderLen excluding padding @@@
84324 + //
84325 + pTxBlk->HdrPadLen = (ULONG)pHeaderBufPtr;
84326 + pHeaderBufPtr = (PCHAR) ROUND_UP(pHeaderBufPtr, 4);
84327 + pTxBlk->HdrPadLen = (ULONG)(pHeaderBufPtr - pTxBlk->HdrPadLen);
84328 +
84329 + {
84330 +
84331 + //
84332 + // Insert LLC-SNAP encapsulation - 8 octets
84333 + //
84334 + EXTRA_LLCSNAP_ENCAP_FROM_PKT_OFFSET(pTxBlk->pSrcBufData-2, pTxBlk->pExtraLlcSnapEncap);
84335 + if (pTxBlk->pExtraLlcSnapEncap)
84336 + {
84337 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pExtraLlcSnapEncap, 6);
84338 + pHeaderBufPtr += 6;
84339 + // get 2 octets (TypeofLen)
84340 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pSrcBufData-2, 2);
84341 + pHeaderBufPtr += 2;
84342 + pTxBlk->MpduHeaderLen += LENGTH_802_1_H;
84343 + }
84344 +
84345 + }
84346 +
84347 + if (pMacEntry->isCached)
84348 + {
84349 + RTMPWriteTxWI_Cache(pAd, (PTXWI_STRUC)(&pTxBlk->HeaderBuf[TXINFO_SIZE]), pTxBlk);
84350 + }
84351 + else
84352 + {
84353 + RTMPWriteTxWI_Data(pAd, (PTXWI_STRUC)(&pTxBlk->HeaderBuf[TXINFO_SIZE]), pTxBlk);
84354 +
84355 + NdisZeroMemory((PUCHAR)(&pMacEntry->CachedBuf[0]), sizeof(pMacEntry->CachedBuf));
84356 + NdisMoveMemory((PUCHAR)(&pMacEntry->CachedBuf[0]), (PUCHAR)(&pTxBlk->HeaderBuf[TXINFO_SIZE]), (pHeaderBufPtr - (PUCHAR)(&pTxBlk->HeaderBuf[TXINFO_SIZE])));
84357 + pMacEntry->isCached = TRUE;
84358 + }
84359 +
84360 + // calculate Transmitted AMPDU count and ByteCount
84361 + {
84362 + pAd->RalinkCounters.TransmittedMPDUsInAMPDUCount.u.LowPart ++;
84363 + pAd->RalinkCounters.TransmittedOctetsInAMPDUCount.QuadPart += pTxBlk->SrcBufLen;
84364 + }
84365 +
84366 + //FreeNumber = GET_TXRING_FREENO(pAd, QueIdx);
84367 +
84368 + HAL_WriteTxResource(pAd, pTxBlk, TRUE, &FreeNumber);
84369 +
84370 + //
84371 + // Kick out Tx
84372 + //
84373 + HAL_KickOutTx(pAd, pTxBlk, pTxBlk->QueIdx);
84374 +
84375 + pAd->RalinkCounters.KickTxCount++;
84376 + pAd->RalinkCounters.OneSecTxDoneCount++;
84377 + }
84378 +
84379 +}
84380 +
84381 +
84382 +VOID STA_AMSDU_Frame_Tx(
84383 + IN PRTMP_ADAPTER pAd,
84384 + IN TX_BLK *pTxBlk)
84385 +{
84386 + PUCHAR pHeaderBufPtr;
84387 + USHORT FreeNumber;
84388 + USHORT subFramePayloadLen = 0; // AMSDU Subframe length without AMSDU-Header / Padding.
84389 + USHORT totalMPDUSize=0;
84390 + UCHAR *subFrameHeader;
84391 + UCHAR padding = 0;
84392 + USHORT FirstTx = 0, LastTxIdx = 0;
84393 + BOOLEAN bVLANPkt;
84394 + int frameNum = 0;
84395 + PQUEUE_ENTRY pQEntry;
84396 +
84397 +
84398 + ASSERT(pTxBlk);
84399 +
84400 + ASSERT((pTxBlk->TxPacketList.Number > 1));
84401 +
84402 + while(pTxBlk->TxPacketList.Head)
84403 + {
84404 + pQEntry = RemoveHeadQueue(&pTxBlk->TxPacketList);
84405 + pTxBlk->pPacket = QUEUE_ENTRY_TO_PACKET(pQEntry);
84406 + if (RTMP_FillTxBlkInfo(pAd, pTxBlk) != TRUE)
84407 + {
84408 + RELEASE_NDIS_PACKET(pAd, pTxBlk->pPacket, NDIS_STATUS_FAILURE);
84409 + continue;
84410 + }
84411 +
84412 + bVLANPkt = (RTMP_GET_PACKET_VLAN(pTxBlk->pPacket) ? TRUE : FALSE);
84413 +
84414 + // skip 802.3 header
84415 + pTxBlk->pSrcBufData = pTxBlk->pSrcBufHeader + LENGTH_802_3;
84416 + pTxBlk->SrcBufLen -= LENGTH_802_3;
84417 +
84418 + // skip vlan tag
84419 + if (bVLANPkt)
84420 + {
84421 + pTxBlk->pSrcBufData += LENGTH_802_1Q;
84422 + pTxBlk->SrcBufLen -= LENGTH_802_1Q;
84423 + }
84424 +
84425 + if (frameNum == 0)
84426 + {
84427 + pHeaderBufPtr = STA_Build_AMSDU_Frame_Header(pAd, pTxBlk);
84428 +
84429 + // NOTE: TxWI->MPDUtotalByteCount will be updated after final frame was handled.
84430 + RTMPWriteTxWI_Data(pAd, (PTXWI_STRUC)(&pTxBlk->HeaderBuf[TXINFO_SIZE]), pTxBlk);
84431 + }
84432 + else
84433 + {
84434 + pHeaderBufPtr = &pTxBlk->HeaderBuf[0];
84435 + padding = ROUND_UP(LENGTH_AMSDU_SUBFRAMEHEAD + subFramePayloadLen, 4) - (LENGTH_AMSDU_SUBFRAMEHEAD + subFramePayloadLen);
84436 + NdisZeroMemory(pHeaderBufPtr, padding + LENGTH_AMSDU_SUBFRAMEHEAD);
84437 + pHeaderBufPtr += padding;
84438 + pTxBlk->MpduHeaderLen = padding;
84439 + }
84440 +
84441 + //
84442 + // A-MSDU subframe
84443 + // DA(6)+SA(6)+Length(2) + LLC/SNAP Encap
84444 + //
84445 + subFrameHeader = pHeaderBufPtr;
84446 + subFramePayloadLen = pTxBlk->SrcBufLen;
84447 +
84448 + NdisMoveMemory(subFrameHeader, pTxBlk->pSrcBufHeader, 12);
84449 +
84450 +
84451 + pHeaderBufPtr += LENGTH_AMSDU_SUBFRAMEHEAD;
84452 + pTxBlk->MpduHeaderLen += LENGTH_AMSDU_SUBFRAMEHEAD;
84453 +
84454 +
84455 + //
84456 + // Insert LLC-SNAP encapsulation - 8 octets
84457 + //
84458 + EXTRA_LLCSNAP_ENCAP_FROM_PKT_OFFSET(pTxBlk->pSrcBufData-2, pTxBlk->pExtraLlcSnapEncap);
84459 +
84460 + subFramePayloadLen = pTxBlk->SrcBufLen;
84461 +
84462 + if (pTxBlk->pExtraLlcSnapEncap)
84463 + {
84464 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pExtraLlcSnapEncap, 6);
84465 + pHeaderBufPtr += 6;
84466 + // get 2 octets (TypeofLen)
84467 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pSrcBufData-2, 2);
84468 + pHeaderBufPtr += 2;
84469 + pTxBlk->MpduHeaderLen += LENGTH_802_1_H;
84470 + subFramePayloadLen += LENGTH_802_1_H;
84471 + }
84472 +
84473 + // update subFrame Length field
84474 + subFrameHeader[12] = (subFramePayloadLen & 0xFF00) >> 8;
84475 + subFrameHeader[13] = subFramePayloadLen & 0xFF;
84476 +
84477 + totalMPDUSize += pTxBlk->MpduHeaderLen + pTxBlk->SrcBufLen;
84478 +
84479 + if (frameNum ==0)
84480 + FirstTx = HAL_WriteMultiTxResource(pAd, pTxBlk, frameNum, &FreeNumber);
84481 + else
84482 + LastTxIdx = HAL_WriteMultiTxResource(pAd, pTxBlk, frameNum, &FreeNumber);
84483 +
84484 + frameNum++;
84485 +
84486 + pAd->RalinkCounters.KickTxCount++;
84487 + pAd->RalinkCounters.OneSecTxDoneCount++;
84488 +
84489 + // calculate Transmitted AMSDU Count and ByteCount
84490 + {
84491 + pAd->RalinkCounters.TransmittedAMSDUCount.u.LowPart ++;
84492 + pAd->RalinkCounters.TransmittedOctetsInAMSDU.QuadPart += totalMPDUSize;
84493 + }
84494 +
84495 + }
84496 +
84497 + HAL_FinalWriteTxResource(pAd, pTxBlk, totalMPDUSize, FirstTx);
84498 + HAL_LastTxIdx(pAd, pTxBlk->QueIdx, LastTxIdx);
84499 +
84500 + //
84501 + // Kick out Tx
84502 + //
84503 + HAL_KickOutTx(pAd, pTxBlk, pTxBlk->QueIdx);
84504 +}
84505 +#endif // DOT11_N_SUPPORT //
84506 +
84507 +VOID STA_Legacy_Frame_Tx(
84508 + IN PRTMP_ADAPTER pAd,
84509 + IN TX_BLK *pTxBlk)
84510 +{
84511 + HEADER_802_11 *pHeader_802_11;
84512 + PUCHAR pHeaderBufPtr;
84513 + USHORT FreeNumber;
84514 + BOOLEAN bVLANPkt;
84515 + PQUEUE_ENTRY pQEntry;
84516 +
84517 + ASSERT(pTxBlk);
84518 +
84519 +
84520 + pQEntry = RemoveHeadQueue(&pTxBlk->TxPacketList);
84521 + pTxBlk->pPacket = QUEUE_ENTRY_TO_PACKET(pQEntry);
84522 + if (RTMP_FillTxBlkInfo(pAd, pTxBlk) != TRUE)
84523 + {
84524 + RELEASE_NDIS_PACKET(pAd, pTxBlk->pPacket, NDIS_STATUS_FAILURE);
84525 + return;
84526 + }
84527 +
84528 + if (pTxBlk->TxFrameType == TX_MCAST_FRAME)
84529 + {
84530 + INC_COUNTER64(pAd->WlanCounters.MulticastTransmittedFrameCount);
84531 + }
84532 +
84533 + if (RTMP_GET_PACKET_RTS(pTxBlk->pPacket))
84534 + TX_BLK_SET_FLAG(pTxBlk, fTX_bRtsRequired);
84535 + else
84536 + TX_BLK_CLEAR_FLAG(pTxBlk, fTX_bRtsRequired);
84537 +
84538 + bVLANPkt = (RTMP_GET_PACKET_VLAN(pTxBlk->pPacket) ? TRUE : FALSE);
84539 +
84540 + if (pTxBlk->TxRate < pAd->CommonCfg.MinTxRate)
84541 + pTxBlk->TxRate = pAd->CommonCfg.MinTxRate;
84542 +
84543 + STAFindCipherAlgorithm(pAd, pTxBlk);
84544 + STABuildCommon802_11Header(pAd, pTxBlk);
84545 +
84546 +
84547 + // skip 802.3 header
84548 + pTxBlk->pSrcBufData = pTxBlk->pSrcBufHeader + LENGTH_802_3;
84549 + pTxBlk->SrcBufLen -= LENGTH_802_3;
84550 +
84551 + // skip vlan tag
84552 + if (bVLANPkt)
84553 + {
84554 + pTxBlk->pSrcBufData += LENGTH_802_1Q;
84555 + pTxBlk->SrcBufLen -= LENGTH_802_1Q;
84556 + }
84557 +
84558 + pHeaderBufPtr = &pTxBlk->HeaderBuf[TXINFO_SIZE + TXWI_SIZE];
84559 + pHeader_802_11 = (HEADER_802_11 *) pHeaderBufPtr;
84560 +
84561 + // skip common header
84562 + pHeaderBufPtr += pTxBlk->MpduHeaderLen;
84563 +
84564 + if (TX_BLK_TEST_FLAG(pTxBlk, fTX_bWMM))
84565 + {
84566 + //
84567 + // build QOS Control bytes
84568 + //
84569 + *pHeaderBufPtr = (pTxBlk->UserPriority & 0x0F);
84570 + *(pHeaderBufPtr+1) = 0;
84571 + pHeaderBufPtr +=2;
84572 + pTxBlk->MpduHeaderLen += 2;
84573 + }
84574 +
84575 + // The remaining content of MPDU header should locate at 4-octets aligment
84576 + pTxBlk->HdrPadLen = (ULONG)pHeaderBufPtr;
84577 + pHeaderBufPtr = (PCHAR) ROUND_UP(pHeaderBufPtr, 4);
84578 + pTxBlk->HdrPadLen = (ULONG)(pHeaderBufPtr - pTxBlk->HdrPadLen);
84579 +
84580 + {
84581 +
84582 + //
84583 + // Insert LLC-SNAP encapsulation - 8 octets
84584 + //
84585 + //
84586 + // if original Ethernet frame contains no LLC/SNAP,
84587 + // then an extra LLC/SNAP encap is required
84588 + //
84589 + EXTRA_LLCSNAP_ENCAP_FROM_PKT_START(pTxBlk->pSrcBufHeader, pTxBlk->pExtraLlcSnapEncap);
84590 + if (pTxBlk->pExtraLlcSnapEncap)
84591 + {
84592 + UCHAR vlan_size;
84593 +
84594 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pExtraLlcSnapEncap, 6);
84595 + pHeaderBufPtr += 6;
84596 + // skip vlan tag
84597 + vlan_size = (bVLANPkt) ? LENGTH_802_1Q : 0;
84598 + // get 2 octets (TypeofLen)
84599 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pSrcBufHeader+12+vlan_size, 2);
84600 + pHeaderBufPtr += 2;
84601 + pTxBlk->MpduHeaderLen += LENGTH_802_1_H;
84602 + }
84603 +
84604 + }
84605 +
84606 + //
84607 + // prepare for TXWI
84608 + // use Wcid as Key Index
84609 + //
84610 +
84611 + RTMPWriteTxWI_Data(pAd, (PTXWI_STRUC)(&pTxBlk->HeaderBuf[TXINFO_SIZE]), pTxBlk);
84612 +
84613 + //FreeNumber = GET_TXRING_FREENO(pAd, QueIdx);
84614 +
84615 + HAL_WriteTxResource(pAd, pTxBlk, TRUE, &FreeNumber);
84616 +
84617 + pAd->RalinkCounters.KickTxCount++;
84618 + pAd->RalinkCounters.OneSecTxDoneCount++;
84619 +
84620 + //
84621 + // Kick out Tx
84622 + //
84623 + HAL_KickOutTx(pAd, pTxBlk, pTxBlk->QueIdx);
84624 +}
84625 +
84626 +
84627 +VOID STA_ARalink_Frame_Tx(
84628 + IN PRTMP_ADAPTER pAd,
84629 + IN TX_BLK *pTxBlk)
84630 +{
84631 + PUCHAR pHeaderBufPtr;
84632 + USHORT FreeNumber;
84633 + USHORT totalMPDUSize=0;
84634 + USHORT FirstTx, LastTxIdx;
84635 + int frameNum = 0;
84636 + BOOLEAN bVLANPkt;
84637 + PQUEUE_ENTRY pQEntry;
84638 +
84639 +
84640 + ASSERT(pTxBlk);
84641 +
84642 + ASSERT((pTxBlk->TxPacketList.Number== 2));
84643 +
84644 +
84645 + FirstTx = LastTxIdx = 0; // Is it ok init they as 0?
84646 + while(pTxBlk->TxPacketList.Head)
84647 + {
84648 + pQEntry = RemoveHeadQueue(&pTxBlk->TxPacketList);
84649 + pTxBlk->pPacket = QUEUE_ENTRY_TO_PACKET(pQEntry);
84650 +
84651 + if (RTMP_FillTxBlkInfo(pAd, pTxBlk) != TRUE)
84652 + {
84653 + RELEASE_NDIS_PACKET(pAd, pTxBlk->pPacket, NDIS_STATUS_FAILURE);
84654 + continue;
84655 + }
84656 +
84657 + bVLANPkt = (RTMP_GET_PACKET_VLAN(pTxBlk->pPacket) ? TRUE : FALSE);
84658 +
84659 + // skip 802.3 header
84660 + pTxBlk->pSrcBufData = pTxBlk->pSrcBufHeader + LENGTH_802_3;
84661 + pTxBlk->SrcBufLen -= LENGTH_802_3;
84662 +
84663 + // skip vlan tag
84664 + if (bVLANPkt)
84665 + {
84666 + pTxBlk->pSrcBufData += LENGTH_802_1Q;
84667 + pTxBlk->SrcBufLen -= LENGTH_802_1Q;
84668 + }
84669 +
84670 + if (frameNum == 0)
84671 + { // For first frame, we need to create the 802.11 header + padding(optional) + RA-AGG-LEN + SNAP Header
84672 +
84673 + pHeaderBufPtr = STA_Build_ARalink_Frame_Header(pAd, pTxBlk);
84674 +
84675 + // It's ok write the TxWI here, because the TxWI->MPDUtotalByteCount
84676 + // will be updated after final frame was handled.
84677 + RTMPWriteTxWI_Data(pAd, (PTXWI_STRUC)(&pTxBlk->HeaderBuf[TXINFO_SIZE]), pTxBlk);
84678 +
84679 +
84680 + //
84681 + // Insert LLC-SNAP encapsulation - 8 octets
84682 + //
84683 + EXTRA_LLCSNAP_ENCAP_FROM_PKT_OFFSET(pTxBlk->pSrcBufData-2, pTxBlk->pExtraLlcSnapEncap);
84684 +
84685 + if (pTxBlk->pExtraLlcSnapEncap)
84686 + {
84687 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pExtraLlcSnapEncap, 6);
84688 + pHeaderBufPtr += 6;
84689 + // get 2 octets (TypeofLen)
84690 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pSrcBufData-2, 2);
84691 + pHeaderBufPtr += 2;
84692 + pTxBlk->MpduHeaderLen += LENGTH_802_1_H;
84693 + }
84694 + }
84695 + else
84696 + { // For second aggregated frame, we need create the 802.3 header to headerBuf, because PCI will copy it to SDPtr0.
84697 +
84698 + pHeaderBufPtr = &pTxBlk->HeaderBuf[0];
84699 + pTxBlk->MpduHeaderLen = 0;
84700 +
84701 + // A-Ralink sub-sequent frame header is the same as 802.3 header.
84702 + // DA(6)+SA(6)+FrameType(2)
84703 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pSrcBufHeader, 12);
84704 + pHeaderBufPtr += 12;
84705 + // get 2 octets (TypeofLen)
84706 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pSrcBufData-2, 2);
84707 + pHeaderBufPtr += 2;
84708 + pTxBlk->MpduHeaderLen = LENGTH_ARALINK_SUBFRAMEHEAD;
84709 + }
84710 +
84711 + totalMPDUSize += pTxBlk->MpduHeaderLen + pTxBlk->SrcBufLen;
84712 +
84713 + //FreeNumber = GET_TXRING_FREENO(pAd, QueIdx);
84714 + if (frameNum ==0)
84715 + FirstTx = HAL_WriteMultiTxResource(pAd, pTxBlk, frameNum, &FreeNumber);
84716 + else
84717 + LastTxIdx = HAL_WriteMultiTxResource(pAd, pTxBlk, frameNum, &FreeNumber);
84718 +
84719 + frameNum++;
84720 +
84721 + pAd->RalinkCounters.OneSecTxAggregationCount++;
84722 + pAd->RalinkCounters.KickTxCount++;
84723 + pAd->RalinkCounters.OneSecTxDoneCount++;
84724 +
84725 + }
84726 +
84727 + HAL_FinalWriteTxResource(pAd, pTxBlk, totalMPDUSize, FirstTx);
84728 + HAL_LastTxIdx(pAd, pTxBlk->QueIdx, LastTxIdx);
84729 +
84730 + //
84731 + // Kick out Tx
84732 + //
84733 + HAL_KickOutTx(pAd, pTxBlk, pTxBlk->QueIdx);
84734 +
84735 +}
84736 +
84737 +
84738 +VOID STA_Fragment_Frame_Tx(
84739 + IN RTMP_ADAPTER *pAd,
84740 + IN TX_BLK *pTxBlk)
84741 +{
84742 + HEADER_802_11 *pHeader_802_11;
84743 + PUCHAR pHeaderBufPtr;
84744 + USHORT FreeNumber;
84745 + UCHAR fragNum = 0;
84746 + PACKET_INFO PacketInfo;
84747 + USHORT EncryptionOverhead = 0;
84748 + UINT32 FreeMpduSize, SrcRemainingBytes;
84749 + USHORT AckDuration;
84750 + UINT NextMpduSize;
84751 + BOOLEAN bVLANPkt;
84752 + PQUEUE_ENTRY pQEntry;
84753 +
84754 +
84755 + ASSERT(pTxBlk);
84756 +
84757 + pQEntry = RemoveHeadQueue(&pTxBlk->TxPacketList);
84758 + pTxBlk->pPacket = QUEUE_ENTRY_TO_PACKET(pQEntry);
84759 + if (RTMP_FillTxBlkInfo(pAd, pTxBlk) != TRUE)
84760 + {
84761 + RELEASE_NDIS_PACKET(pAd, pTxBlk->pPacket, NDIS_STATUS_FAILURE);
84762 + return;
84763 + }
84764 +
84765 + ASSERT(TX_BLK_TEST_FLAG(pTxBlk, fTX_bAllowFrag));
84766 + bVLANPkt = (RTMP_GET_PACKET_VLAN(pTxBlk->pPacket) ? TRUE : FALSE);
84767 +
84768 + STAFindCipherAlgorithm(pAd, pTxBlk);
84769 + STABuildCommon802_11Header(pAd, pTxBlk);
84770 +
84771 + if (pTxBlk->CipherAlg == CIPHER_TKIP)
84772 + {
84773 + pTxBlk->pPacket = duplicate_pkt_with_TKIP_MIC(pAd, pTxBlk->pPacket);
84774 + if (pTxBlk->pPacket == NULL)
84775 + return;
84776 + RTMP_QueryPacketInfo(pTxBlk->pPacket, &PacketInfo, &pTxBlk->pSrcBufHeader, &pTxBlk->SrcBufLen);
84777 + }
84778 +
84779 + // skip 802.3 header
84780 + pTxBlk->pSrcBufData = pTxBlk->pSrcBufHeader + LENGTH_802_3;
84781 + pTxBlk->SrcBufLen -= LENGTH_802_3;
84782 +
84783 +
84784 + // skip vlan tag
84785 + if (bVLANPkt)
84786 + {
84787 + pTxBlk->pSrcBufData += LENGTH_802_1Q;
84788 + pTxBlk->SrcBufLen -= LENGTH_802_1Q;
84789 + }
84790 +
84791 + pHeaderBufPtr = &pTxBlk->HeaderBuf[TXINFO_SIZE + TXWI_SIZE];
84792 + pHeader_802_11 = (HEADER_802_11 *)pHeaderBufPtr;
84793 +
84794 +
84795 + // skip common header
84796 + pHeaderBufPtr += pTxBlk->MpduHeaderLen;
84797 +
84798 + if (TX_BLK_TEST_FLAG(pTxBlk, fTX_bWMM))
84799 + {
84800 + //
84801 + // build QOS Control bytes
84802 + //
84803 + *pHeaderBufPtr = (pTxBlk->UserPriority & 0x0F);
84804 +
84805 + *(pHeaderBufPtr+1) = 0;
84806 + pHeaderBufPtr +=2;
84807 + pTxBlk->MpduHeaderLen += 2;
84808 + }
84809 +
84810 + //
84811 + // padding at front of LLC header
84812 + // LLC header should locate at 4-octets aligment
84813 + //
84814 + pTxBlk->HdrPadLen = (ULONG)pHeaderBufPtr;
84815 + pHeaderBufPtr = (PCHAR) ROUND_UP(pHeaderBufPtr, 4);
84816 + pTxBlk->HdrPadLen = (ULONG)(pHeaderBufPtr - pTxBlk->HdrPadLen);
84817 +
84818 +
84819 +
84820 + //
84821 + // Insert LLC-SNAP encapsulation - 8 octets
84822 + //
84823 + //
84824 + // if original Ethernet frame contains no LLC/SNAP,
84825 + // then an extra LLC/SNAP encap is required
84826 + //
84827 + EXTRA_LLCSNAP_ENCAP_FROM_PKT_START(pTxBlk->pSrcBufHeader, pTxBlk->pExtraLlcSnapEncap);
84828 + if (pTxBlk->pExtraLlcSnapEncap)
84829 + {
84830 + UCHAR vlan_size;
84831 +
84832 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pExtraLlcSnapEncap, 6);
84833 + pHeaderBufPtr += 6;
84834 + // skip vlan tag
84835 + vlan_size = (bVLANPkt) ? LENGTH_802_1Q : 0;
84836 + // get 2 octets (TypeofLen)
84837 + NdisMoveMemory(pHeaderBufPtr, pTxBlk->pSrcBufHeader+12+vlan_size, 2);
84838 + pHeaderBufPtr += 2;
84839 + pTxBlk->MpduHeaderLen += LENGTH_802_1_H;
84840 + }
84841 +
84842 +
84843 + // If TKIP is used and fragmentation is required. Driver has to
84844 + // append TKIP MIC at tail of the scatter buffer
84845 + // MAC ASIC will only perform IV/EIV/ICV insertion but no TKIP MIC
84846 + if (pTxBlk->CipherAlg == CIPHER_TKIP)
84847 + {
84848 +
84849 + // NOTE: DON'T refer the skb->len directly after following copy. Becasue the length is not adjust
84850 + // to correct lenght, refer to pTxBlk->SrcBufLen for the packet length in following progress.
84851 + NdisMoveMemory(pTxBlk->pSrcBufData + pTxBlk->SrcBufLen, &pAd->PrivateInfo.Tx.MIC[0], 8);
84852 + //skb_put((RTPKT_TO_OSPKT(pTxBlk->pPacket))->tail, 8);
84853 + pTxBlk->SrcBufLen += 8;
84854 + pTxBlk->TotalFrameLen += 8;
84855 + pTxBlk->CipherAlg = CIPHER_TKIP_NO_MIC;
84856 + }
84857 +
84858 + //
84859 + // calcuate the overhead bytes that encryption algorithm may add. This
84860 + // affects the calculate of "duration" field
84861 + //
84862 + if ((pTxBlk->CipherAlg == CIPHER_WEP64) || (pTxBlk->CipherAlg == CIPHER_WEP128))
84863 + EncryptionOverhead = 8; //WEP: IV[4] + ICV[4];
84864 + else if (pTxBlk->CipherAlg == CIPHER_TKIP_NO_MIC)
84865 + EncryptionOverhead = 12;//TKIP: IV[4] + EIV[4] + ICV[4], MIC will be added to TotalPacketLength
84866 + else if (pTxBlk->CipherAlg == CIPHER_TKIP)
84867 + EncryptionOverhead = 20;//TKIP: IV[4] + EIV[4] + ICV[4] + MIC[8]
84868 + else if (pTxBlk->CipherAlg == CIPHER_AES)
84869 + EncryptionOverhead = 16; // AES: IV[4] + EIV[4] + MIC[8]
84870 + else
84871 + EncryptionOverhead = 0;
84872 +
84873 + // decide how much time an ACK/CTS frame will consume in the air
84874 + AckDuration = RTMPCalcDuration(pAd, pAd->CommonCfg.ExpectedACKRate[pTxBlk->TxRate], 14);
84875 +
84876 + // Init the total payload length of this frame.
84877 + SrcRemainingBytes = pTxBlk->SrcBufLen;
84878 +
84879 + pTxBlk->TotalFragNum = 0xff;
84880 +
84881 + do {
84882 +
84883 + FreeMpduSize = pAd->CommonCfg.FragmentThreshold - LENGTH_CRC;
84884 +
84885 + FreeMpduSize -= pTxBlk->MpduHeaderLen;
84886 +
84887 + if (SrcRemainingBytes <= FreeMpduSize)
84888 + { // this is the last or only fragment
84889 +
84890 + pTxBlk->SrcBufLen = SrcRemainingBytes;
84891 +
84892 + pHeader_802_11->FC.MoreFrag = 0;
84893 + pHeader_802_11->Duration = pAd->CommonCfg.Dsifs + AckDuration;
84894 +
84895 + // Indicate the lower layer that this's the last fragment.
84896 + pTxBlk->TotalFragNum = fragNum;
84897 + }
84898 + else
84899 + { // more fragment is required
84900 +
84901 + pTxBlk->SrcBufLen = FreeMpduSize;
84902 +
84903 + NextMpduSize = min(((UINT)SrcRemainingBytes - pTxBlk->SrcBufLen), ((UINT)pAd->CommonCfg.FragmentThreshold));
84904 + pHeader_802_11->FC.MoreFrag = 1;
84905 + pHeader_802_11->Duration = (3 * pAd->CommonCfg.Dsifs) + (2 * AckDuration) + RTMPCalcDuration(pAd, pTxBlk->TxRate, NextMpduSize + EncryptionOverhead);
84906 + }
84907 +
84908 + if (fragNum == 0)
84909 + pTxBlk->FrameGap = IFS_HTTXOP;
84910 + else
84911 + pTxBlk->FrameGap = IFS_SIFS;
84912 +
84913 + RTMPWriteTxWI_Data(pAd, (PTXWI_STRUC)(&pTxBlk->HeaderBuf[TXINFO_SIZE]), pTxBlk);
84914 +
84915 + HAL_WriteFragTxResource(pAd, pTxBlk, fragNum, &FreeNumber);
84916 +
84917 + pAd->RalinkCounters.KickTxCount++;
84918 + pAd->RalinkCounters.OneSecTxDoneCount++;
84919 +
84920 + // Update the frame number, remaining size of the NDIS packet payload.
84921 +
84922 + // space for 802.11 header.
84923 + if (fragNum == 0 && pTxBlk->pExtraLlcSnapEncap)
84924 + pTxBlk->MpduHeaderLen -= LENGTH_802_1_H;
84925 +
84926 + fragNum++;
84927 + SrcRemainingBytes -= pTxBlk->SrcBufLen;
84928 + pTxBlk->pSrcBufData += pTxBlk->SrcBufLen;
84929 +
84930 + pHeader_802_11->Frag++; // increase Frag #
84931 +
84932 + }while(SrcRemainingBytes > 0);
84933 +
84934 + //
84935 + // Kick out Tx
84936 + //
84937 + HAL_KickOutTx(pAd, pTxBlk, pTxBlk->QueIdx);
84938 +}
84939 +
84940 +
84941 +#define RELEASE_FRAMES_OF_TXBLK(_pAd, _pTxBlk, _pQEntry, _Status) \
84942 + while(_pTxBlk->TxPacketList.Head) \
84943 + { \
84944 + _pQEntry = RemoveHeadQueue(&_pTxBlk->TxPacketList); \
84945 + RELEASE_NDIS_PACKET(_pAd, QUEUE_ENTRY_TO_PACKET(_pQEntry), _Status); \
84946 + }
84947 +
84948 +
84949 +/*
84950 + ========================================================================
84951 +
84952 + Routine Description:
84953 + Copy frame from waiting queue into relative ring buffer and set
84954 + appropriate ASIC register to kick hardware encryption before really
84955 + sent out to air.
84956 +
84957 + Arguments:
84958 + pAd Pointer to our adapter
84959 + PNDIS_PACKET Pointer to outgoing Ndis frame
84960 + NumberOfFrag Number of fragment required
84961 +
84962 + Return Value:
84963 + None
84964 +
84965 + IRQL = DISPATCH_LEVEL
84966 +
84967 + Note:
84968 +
84969 + ========================================================================
84970 +*/
84971 +NDIS_STATUS STAHardTransmit(
84972 + IN PRTMP_ADAPTER pAd,
84973 + IN TX_BLK *pTxBlk,
84974 + IN UCHAR QueIdx)
84975 +{
84976 + NDIS_PACKET *pPacket;
84977 + PQUEUE_ENTRY pQEntry;
84978 +
84979 + // ---------------------------------------------
84980 + // STEP 0. DO SANITY CHECK AND SOME EARLY PREPARATION.
84981 + // ---------------------------------------------
84982 + //
84983 + ASSERT(pTxBlk->TxPacketList.Number);
84984 + if (pTxBlk->TxPacketList.Head == NULL)
84985 + {
84986 + DBGPRINT(RT_DEBUG_ERROR, ("pTxBlk->TotalFrameNum == %ld!\n", pTxBlk->TxPacketList.Number));
84987 + return NDIS_STATUS_FAILURE;
84988 + }
84989 +
84990 + pPacket = QUEUE_ENTRY_TO_PACKET(pTxBlk->TxPacketList.Head);
84991 +
84992 +#if 0 //def CARRIER_DETECTION_SUPPORT // Roger sync Carrier
84993 + if ((pAd->CommonCfg.CarrierDetect.Enable == TRUE) && (isCarrierDetectExist(pAd) == TRUE))
84994 + {
84995 + DBGPRINT(RT_DEBUG_INFO,("STAHardTransmit --> radar detect not in normal mode !!!\n"));
84996 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
84997 + return (NDIS_STATUS_FAILURE);
84998 + }
84999 +#endif // CARRIER_DETECTION_SUPPORT //
85000 +
85001 + // ------------------------------------------------------------------
85002 + // STEP 1. WAKE UP PHY
85003 + // outgoing frame always wakeup PHY to prevent frame lost and
85004 + // turn off PSM bit to improve performance
85005 + // ------------------------------------------------------------------
85006 + // not to change PSM bit, just send this frame out?
85007 + if ((pAd->StaCfg.Psm == PWR_SAVE) && OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
85008 + {
85009 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("AsicForceWakeup At HardTx\n"));
85010 + AsicForceWakeup(pAd, TRUE);
85011 + }
85012 +
85013 + // It should not change PSM bit, when APSD turn on.
85014 + if ((!(pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable) && (pAd->CommonCfg.bAPSDForcePowerSave == FALSE))
85015 + || (RTMP_GET_PACKET_EAPOL(pTxBlk->pPacket))
85016 + || (RTMP_GET_PACKET_WAI(pTxBlk->pPacket)))
85017 + {
85018 + if ((pAd->StaCfg.Psm == PWR_SAVE) &&
85019 + (pAd->StaCfg.WindowsPowerMode == Ndis802_11PowerModeFast_PSP))
85020 + MlmeSetPsmBit(pAd, PWR_ACTIVE);
85021 + }
85022 +
85023 + switch (pTxBlk->TxFrameType)
85024 + {
85025 +#ifdef DOT11_N_SUPPORT
85026 + case TX_AMPDU_FRAME:
85027 + STA_AMPDU_Frame_Tx(pAd, pTxBlk);
85028 + break;
85029 + case TX_AMSDU_FRAME:
85030 + STA_AMSDU_Frame_Tx(pAd, pTxBlk);
85031 + break;
85032 +#endif // DOT11_N_SUPPORT //
85033 + case TX_LEGACY_FRAME:
85034 + STA_Legacy_Frame_Tx(pAd, pTxBlk);
85035 + break;
85036 + case TX_MCAST_FRAME:
85037 + STA_Legacy_Frame_Tx(pAd, pTxBlk);
85038 + break;
85039 + case TX_RALINK_FRAME:
85040 + STA_ARalink_Frame_Tx(pAd, pTxBlk);
85041 + break;
85042 + case TX_FRAG_FRAME:
85043 + STA_Fragment_Frame_Tx(pAd, pTxBlk);
85044 + break;
85045 + default:
85046 + {
85047 + // It should not happened!
85048 + DBGPRINT(RT_DEBUG_ERROR, ("Send a pacekt was not classified!! It should not happen!\n"));
85049 + while(pTxBlk->TxPacketList.Number)
85050 + {
85051 + pQEntry = RemoveHeadQueue(&pTxBlk->TxPacketList);
85052 + pPacket = QUEUE_ENTRY_TO_PACKET(pQEntry);
85053 + if (pPacket)
85054 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
85055 + }
85056 + }
85057 + break;
85058 + }
85059 +
85060 + return (NDIS_STATUS_SUCCESS);
85061 +
85062 +}
85063 +
85064 +ULONG HashBytesPolynomial(UCHAR *value, unsigned int len)
85065 +{
85066 + unsigned char *word = value;
85067 + unsigned int ret = 0;
85068 + unsigned int i;
85069 +
85070 + for(i=0; i < len; i++)
85071 + {
85072 + int mod = i % 32;
85073 + ret ^=(unsigned int) (word[i]) << mod;
85074 + ret ^=(unsigned int) (word[i]) >> (32 - mod);
85075 + }
85076 + return ret;
85077 +}
85078 +
85079 +VOID Sta_Announce_or_Forward_802_3_Packet(
85080 + IN PRTMP_ADAPTER pAd,
85081 + IN PNDIS_PACKET pPacket,
85082 + IN UCHAR FromWhichBSSID)
85083 +{
85084 + if (TRUE
85085 + )
85086 + {
85087 + announce_802_3_packet(pAd, pPacket);
85088 + }
85089 + else
85090 + {
85091 + // release packet
85092 + RELEASE_NDIS_PACKET(pAd, pPacket, NDIS_STATUS_FAILURE);
85093 + }
85094 +}
85095 +
85096 --- /dev/null
85097 +++ b/drivers/staging/rt2860/sta/sanity.c
85098 @@ -0,0 +1,420 @@
85099 +/*
85100 + *************************************************************************
85101 + * Ralink Tech Inc.
85102 + * 5F., No.36, Taiyuan St., Jhubei City,
85103 + * Hsinchu County 302,
85104 + * Taiwan, R.O.C.
85105 + *
85106 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
85107 + *
85108 + * This program is free software; you can redistribute it and/or modify *
85109 + * it under the terms of the GNU General Public License as published by *
85110 + * the Free Software Foundation; either version 2 of the License, or *
85111 + * (at your option) any later version. *
85112 + * *
85113 + * This program is distributed in the hope that it will be useful, *
85114 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
85115 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
85116 + * GNU General Public License for more details. *
85117 + * *
85118 + * You should have received a copy of the GNU General Public License *
85119 + * along with this program; if not, write to the *
85120 + * Free Software Foundation, Inc., *
85121 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
85122 + * *
85123 + *************************************************************************
85124 +
85125 + Module Name:
85126 + sanity.c
85127 +
85128 + Abstract:
85129 +
85130 + Revision History:
85131 + Who When What
85132 + -------- ---------- ----------------------------------------------
85133 + John Chang 2004-09-01 add WMM support
85134 +*/
85135 +#include "../rt_config.h"
85136 +
85137 +extern UCHAR CISCO_OUI[];
85138 +
85139 +extern UCHAR WPA_OUI[];
85140 +extern UCHAR RSN_OUI[];
85141 +extern UCHAR WME_INFO_ELEM[];
85142 +extern UCHAR WME_PARM_ELEM[];
85143 +extern UCHAR Ccx2QosInfo[];
85144 +extern UCHAR RALINK_OUI[];
85145 +extern UCHAR BROADCOM_OUI[];
85146 +
85147 +/*
85148 + ==========================================================================
85149 + Description:
85150 + MLME message sanity check
85151 + Return:
85152 + TRUE if all parameters are OK, FALSE otherwise
85153 + ==========================================================================
85154 + */
85155 +BOOLEAN MlmeStartReqSanity(
85156 + IN PRTMP_ADAPTER pAd,
85157 + IN VOID *Msg,
85158 + IN ULONG MsgLen,
85159 + OUT CHAR Ssid[],
85160 + OUT UCHAR *pSsidLen)
85161 +{
85162 + MLME_START_REQ_STRUCT *Info;
85163 +
85164 + Info = (MLME_START_REQ_STRUCT *)(Msg);
85165 +
85166 + if (Info->SsidLen > MAX_LEN_OF_SSID)
85167 + {
85168 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeStartReqSanity fail - wrong SSID length\n"));
85169 + return FALSE;
85170 + }
85171 +
85172 + *pSsidLen = Info->SsidLen;
85173 + NdisMoveMemory(Ssid, Info->Ssid, *pSsidLen);
85174 +
85175 + return TRUE;
85176 +}
85177 +
85178 +/*
85179 + ==========================================================================
85180 + Description:
85181 + MLME message sanity check
85182 + Return:
85183 + TRUE if all parameters are OK, FALSE otherwise
85184 +
85185 + IRQL = DISPATCH_LEVEL
85186 +
85187 + ==========================================================================
85188 + */
85189 +BOOLEAN PeerAssocRspSanity(
85190 + IN PRTMP_ADAPTER pAd,
85191 + IN VOID *pMsg,
85192 + IN ULONG MsgLen,
85193 + OUT PUCHAR pAddr2,
85194 + OUT USHORT *pCapabilityInfo,
85195 + OUT USHORT *pStatus,
85196 + OUT USHORT *pAid,
85197 + OUT UCHAR SupRate[],
85198 + OUT UCHAR *pSupRateLen,
85199 + OUT UCHAR ExtRate[],
85200 + OUT UCHAR *pExtRateLen,
85201 + OUT HT_CAPABILITY_IE *pHtCapability,
85202 + OUT ADD_HT_INFO_IE *pAddHtInfo, // AP might use this additional ht info IE
85203 + OUT UCHAR *pHtCapabilityLen,
85204 + OUT UCHAR *pAddHtInfoLen,
85205 + OUT UCHAR *pNewExtChannelOffset,
85206 + OUT PEDCA_PARM pEdcaParm,
85207 + OUT UCHAR *pCkipFlag)
85208 +{
85209 + CHAR IeType, *Ptr;
85210 + PFRAME_802_11 pFrame = (PFRAME_802_11)pMsg;
85211 + PEID_STRUCT pEid;
85212 + ULONG Length = 0;
85213 +
85214 + *pNewExtChannelOffset = 0xff;
85215 + *pHtCapabilityLen = 0;
85216 + *pAddHtInfoLen = 0;
85217 + COPY_MAC_ADDR(pAddr2, pFrame->Hdr.Addr2);
85218 + Ptr = pFrame->Octet;
85219 + Length += LENGTH_802_11;
85220 +
85221 + NdisMoveMemory(pCapabilityInfo, &pFrame->Octet[0], 2);
85222 + Length += 2;
85223 + NdisMoveMemory(pStatus, &pFrame->Octet[2], 2);
85224 + Length += 2;
85225 + *pCkipFlag = 0;
85226 + *pExtRateLen = 0;
85227 + pEdcaParm->bValid = FALSE;
85228 +
85229 + if (*pStatus != MLME_SUCCESS)
85230 + return TRUE;
85231 +
85232 + NdisMoveMemory(pAid, &pFrame->Octet[4], 2);
85233 + Length += 2;
85234 +
85235 + // Aid already swaped byte order in RTMPFrameEndianChange() for big endian platform
85236 + *pAid = (*pAid) & 0x3fff; // AID is low 14-bit
85237 +
85238 + // -- get supported rates from payload and advance the pointer
85239 + IeType = pFrame->Octet[6];
85240 + *pSupRateLen = pFrame->Octet[7];
85241 + if ((IeType != IE_SUPP_RATES) || (*pSupRateLen > MAX_LEN_OF_SUPPORTED_RATES))
85242 + {
85243 + DBGPRINT(RT_DEBUG_TRACE, ("PeerAssocRspSanity fail - wrong SupportedRates IE\n"));
85244 + return FALSE;
85245 + }
85246 + else
85247 + NdisMoveMemory(SupRate, &pFrame->Octet[8], *pSupRateLen);
85248 +
85249 + Length = Length + 2 + *pSupRateLen;
85250 +
85251 + // many AP implement proprietary IEs in non-standard order, we'd better
85252 + // tolerate mis-ordered IEs to get best compatibility
85253 + pEid = (PEID_STRUCT) &pFrame->Octet[8 + (*pSupRateLen)];
85254 +
85255 + // get variable fields from payload and advance the pointer
85256 + while ((Length + 2 + pEid->Len) <= MsgLen)
85257 + {
85258 + switch (pEid->Eid)
85259 + {
85260 + case IE_EXT_SUPP_RATES:
85261 + if (pEid->Len <= MAX_LEN_OF_SUPPORTED_RATES)
85262 + {
85263 + NdisMoveMemory(ExtRate, pEid->Octet, pEid->Len);
85264 + *pExtRateLen = pEid->Len;
85265 + }
85266 + break;
85267 +
85268 + case IE_HT_CAP:
85269 + case IE_HT_CAP2:
85270 + if (pEid->Len >= SIZE_HT_CAP_IE) //Note: allow extension.!!
85271 + {
85272 + NdisMoveMemory(pHtCapability, pEid->Octet, SIZE_HT_CAP_IE);
85273 +
85274 + *(USHORT *)(&pHtCapability->HtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->HtCapInfo));
85275 + *(USHORT *)(&pHtCapability->ExtHtCapInfo) = cpu2le16(*(USHORT *)(&pHtCapability->ExtHtCapInfo));
85276 +
85277 + *pHtCapabilityLen = SIZE_HT_CAP_IE;
85278 + }
85279 + else
85280 + {
85281 + DBGPRINT(RT_DEBUG_WARN, ("PeerAssocRspSanity - wrong IE_HT_CAP. \n"));
85282 + }
85283 +
85284 + break;
85285 +#ifdef DOT11_N_SUPPORT
85286 + case IE_ADD_HT:
85287 + case IE_ADD_HT2:
85288 + if (pEid->Len >= sizeof(ADD_HT_INFO_IE))
85289 + {
85290 + // This IE allows extension, but we can ignore extra bytes beyond our knowledge , so only
85291 + // copy first sizeof(ADD_HT_INFO_IE)
85292 + NdisMoveMemory(pAddHtInfo, pEid->Octet, sizeof(ADD_HT_INFO_IE));
85293 +
85294 + *(USHORT *)(&pAddHtInfo->AddHtInfo2) = cpu2le16(*(USHORT *)(&pAddHtInfo->AddHtInfo2));
85295 + *(USHORT *)(&pAddHtInfo->AddHtInfo3) = cpu2le16(*(USHORT *)(&pAddHtInfo->AddHtInfo3));
85296 +
85297 + *pAddHtInfoLen = SIZE_ADD_HT_INFO_IE;
85298 + }
85299 + else
85300 + {
85301 + DBGPRINT(RT_DEBUG_WARN, ("PeerAssocRspSanity - wrong IE_ADD_HT. \n"));
85302 + }
85303 +
85304 + break;
85305 + case IE_SECONDARY_CH_OFFSET:
85306 + if (pEid->Len == 1)
85307 + {
85308 + *pNewExtChannelOffset = pEid->Octet[0];
85309 + }
85310 + else
85311 + {
85312 + DBGPRINT(RT_DEBUG_WARN, ("PeerAssocRspSanity - wrong IE_SECONDARY_CH_OFFSET. \n"));
85313 + }
85314 +#endif // DOT11_N_SUPPORT //
85315 + break;
85316 + case IE_AIRONET_CKIP:
85317 + // 0. Check Aironet IE length, it must be larger or equal to 28
85318 + // Cisco's AP VxWork version(will not be supported) used this IE length as 28
85319 + // Cisco's AP IOS version used this IE length as 30
85320 + if (pEid->Len < (CKIP_NEGOTIATION_LENGTH - 2))
85321 + break;
85322 +
85323 + // 1. Copy CKIP flag byte to buffer for process
85324 + *pCkipFlag = *(pEid->Octet + 8);
85325 + break;
85326 +
85327 + case IE_AIRONET_IPADDRESS:
85328 + if (pEid->Len != 0x0A)
85329 + break;
85330 +
85331 + // Get Cisco Aironet IP information
85332 + if (NdisEqualMemory(pEid->Octet, CISCO_OUI, 3) == 1)
85333 + NdisMoveMemory(pAd->StaCfg.AironetIPAddress, pEid->Octet + 4, 4);
85334 + break;
85335 +
85336 + // CCX2, WMM use the same IE value
85337 + // case IE_CCX_V2:
85338 + case IE_VENDOR_SPECIFIC:
85339 + // handle WME PARAMTER ELEMENT
85340 + if (NdisEqualMemory(pEid->Octet, WME_PARM_ELEM, 6) && (pEid->Len == 24))
85341 + {
85342 + PUCHAR ptr;
85343 + int i;
85344 +
85345 + // parsing EDCA parameters
85346 + pEdcaParm->bValid = TRUE;
85347 + pEdcaParm->bQAck = FALSE; // pEid->Octet[0] & 0x10;
85348 + pEdcaParm->bQueueRequest = FALSE; // pEid->Octet[0] & 0x20;
85349 + pEdcaParm->bTxopRequest = FALSE; // pEid->Octet[0] & 0x40;
85350 + //pEdcaParm->bMoreDataAck = FALSE; // pEid->Octet[0] & 0x80;
85351 + pEdcaParm->EdcaUpdateCount = pEid->Octet[6] & 0x0f;
85352 + pEdcaParm->bAPSDCapable = (pEid->Octet[6] & 0x80) ? 1 : 0;
85353 + ptr = &pEid->Octet[8];
85354 + for (i=0; i<4; i++)
85355 + {
85356 + UCHAR aci = (*ptr & 0x60) >> 5; // b5~6 is AC INDEX
85357 + pEdcaParm->bACM[aci] = (((*ptr) & 0x10) == 0x10); // b5 is ACM
85358 + pEdcaParm->Aifsn[aci] = (*ptr) & 0x0f; // b0~3 is AIFSN
85359 + pEdcaParm->Cwmin[aci] = *(ptr+1) & 0x0f; // b0~4 is Cwmin
85360 + pEdcaParm->Cwmax[aci] = *(ptr+1) >> 4; // b5~8 is Cwmax
85361 + pEdcaParm->Txop[aci] = *(ptr+2) + 256 * (*(ptr+3)); // in unit of 32-us
85362 + ptr += 4; // point to next AC
85363 + }
85364 + }
85365 +
85366 + // handle CCX IE
85367 + else
85368 + {
85369 + // 0. Check the size and CCX admin control
85370 + if (pAd->StaCfg.CCXControl.field.Enable == 0)
85371 + break;
85372 + if (pEid->Len != 5)
85373 + break;
85374 +
85375 + // Turn CCX2 if matched
85376 + if (NdisEqualMemory(pEid->Octet, Ccx2IeInfo, 5) == 1)
85377 + pAd->StaCfg.CCXEnable = TRUE;
85378 + break;
85379 + }
85380 + break;
85381 +
85382 + default:
85383 + DBGPRINT(RT_DEBUG_TRACE, ("PeerAssocRspSanity - ignore unrecognized EID = %d\n", pEid->Eid));
85384 + break;
85385 + }
85386 +
85387 + Length = Length + 2 + pEid->Len;
85388 + pEid = (PEID_STRUCT)((UCHAR*)pEid + 2 + pEid->Len);
85389 + }
85390 +
85391 + // Force CCX2 enable to TRUE for those AP didn't replay CCX v2 IE, we still force it to be on
85392 + if (pAd->StaCfg.CCXControl.field.Enable == 1)
85393 + pAd->StaCfg.CCXEnable = TRUE;
85394 +
85395 + return TRUE;
85396 +}
85397 +
85398 +/*
85399 + ==========================================================================
85400 + Description:
85401 + MLME message sanity check
85402 + Return:
85403 + TRUE if all parameters are OK, FALSE otherwise
85404 +
85405 + IRQL = DISPATCH_LEVEL
85406 +
85407 + ==========================================================================
85408 + */
85409 +BOOLEAN PeerProbeReqSanity(
85410 + IN PRTMP_ADAPTER pAd,
85411 + IN VOID *Msg,
85412 + IN ULONG MsgLen,
85413 + OUT PUCHAR pAddr2,
85414 + OUT CHAR Ssid[],
85415 + OUT UCHAR *pSsidLen)
85416 +{
85417 + UCHAR Idx;
85418 + UCHAR RateLen;
85419 + CHAR IeType;
85420 + PFRAME_802_11 pFrame = (PFRAME_802_11)Msg;
85421 +
85422 + COPY_MAC_ADDR(pAddr2, pFrame->Hdr.Addr2);
85423 +
85424 + if ((pFrame->Octet[0] != IE_SSID) || (pFrame->Octet[1] > MAX_LEN_OF_SSID))
85425 + {
85426 + DBGPRINT(RT_DEBUG_TRACE, ("PeerProbeReqSanity fail - wrong SSID IE(Type=%d,Len=%d)\n",pFrame->Octet[0],pFrame->Octet[1]));
85427 + return FALSE;
85428 + }
85429 +
85430 + *pSsidLen = pFrame->Octet[1];
85431 + NdisMoveMemory(Ssid, &pFrame->Octet[2], *pSsidLen);
85432 +
85433 + Idx = *pSsidLen + 2;
85434 +
85435 + // -- get supported rates from payload and advance the pointer
85436 + IeType = pFrame->Octet[Idx];
85437 + RateLen = pFrame->Octet[Idx + 1];
85438 + if (IeType != IE_SUPP_RATES)
85439 + {
85440 + DBGPRINT(RT_DEBUG_TRACE, ("PeerProbeReqSanity fail - wrong SupportRates IE(Type=%d,Len=%d)\n",pFrame->Octet[Idx],pFrame->Octet[Idx+1]));
85441 + return FALSE;
85442 + }
85443 + else
85444 + {
85445 + if ((pAd->CommonCfg.PhyMode == PHY_11G) && (RateLen < 8))
85446 + return (FALSE);
85447 + }
85448 +
85449 + return TRUE;
85450 +}
85451 +
85452 +/*
85453 + ==========================================================================
85454 + Description:
85455 +
85456 + IRQL = DISPATCH_LEVEL
85457 +
85458 + ==========================================================================
85459 + */
85460 +BOOLEAN GetTimBit(
85461 + IN CHAR *Ptr,
85462 + IN USHORT Aid,
85463 + OUT UCHAR *TimLen,
85464 + OUT UCHAR *BcastFlag,
85465 + OUT UCHAR *DtimCount,
85466 + OUT UCHAR *DtimPeriod,
85467 + OUT UCHAR *MessageToMe)
85468 +{
85469 + UCHAR BitCntl, N1, N2, MyByte, MyBit;
85470 + CHAR *IdxPtr;
85471 +
85472 + IdxPtr = Ptr;
85473 +
85474 + IdxPtr ++;
85475 + *TimLen = *IdxPtr;
85476 +
85477 + // get DTIM Count from TIM element
85478 + IdxPtr ++;
85479 + *DtimCount = *IdxPtr;
85480 +
85481 + // get DTIM Period from TIM element
85482 + IdxPtr++;
85483 + *DtimPeriod = *IdxPtr;
85484 +
85485 + // get Bitmap Control from TIM element
85486 + IdxPtr++;
85487 + BitCntl = *IdxPtr;
85488 +
85489 + if ((*DtimCount == 0) && (BitCntl & 0x01))
85490 + *BcastFlag = TRUE;
85491 + else
85492 + *BcastFlag = FALSE;
85493 +
85494 + // Parse Partial Virtual Bitmap from TIM element
85495 + N1 = BitCntl & 0xfe; // N1 is the first bitmap byte#
85496 + N2 = *TimLen - 4 + N1; // N2 is the last bitmap byte#
85497 +
85498 + if ((Aid < (N1 << 3)) || (Aid >= ((N2 + 1) << 3)))
85499 + *MessageToMe = FALSE;
85500 + else
85501 + {
85502 + MyByte = (Aid >> 3) - N1; // my byte position in the bitmap byte-stream
85503 + MyBit = Aid % 16 - ((MyByte & 0x01)? 8:0);
85504 +
85505 + IdxPtr += (MyByte + 1);
85506 +
85507 + //if (*IdxPtr)
85508 + // DBGPRINT(RT_DEBUG_WARN, ("TIM bitmap = 0x%02x\n", *IdxPtr));
85509 +
85510 + if (*IdxPtr & (0x01 << MyBit))
85511 + *MessageToMe = TRUE;
85512 + else
85513 + *MessageToMe = FALSE;
85514 + }
85515 +
85516 + return TRUE;
85517 +}
85518 +
85519 --- /dev/null
85520 +++ b/drivers/staging/rt2860/sta/sync.c
85521 @@ -0,0 +1,1961 @@
85522 +/*
85523 + *************************************************************************
85524 + * Ralink Tech Inc.
85525 + * 5F., No.36, Taiyuan St., Jhubei City,
85526 + * Hsinchu County 302,
85527 + * Taiwan, R.O.C.
85528 + *
85529 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
85530 + *
85531 + * This program is free software; you can redistribute it and/or modify *
85532 + * it under the terms of the GNU General Public License as published by *
85533 + * the Free Software Foundation; either version 2 of the License, or *
85534 + * (at your option) any later version. *
85535 + * *
85536 + * This program is distributed in the hope that it will be useful, *
85537 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
85538 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
85539 + * GNU General Public License for more details. *
85540 + * *
85541 + * You should have received a copy of the GNU General Public License *
85542 + * along with this program; if not, write to the *
85543 + * Free Software Foundation, Inc., *
85544 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
85545 + * *
85546 + *************************************************************************
85547 +
85548 + Module Name:
85549 + sync.c
85550 +
85551 + Abstract:
85552 +
85553 + Revision History:
85554 + Who When What
85555 + -------- ---------- ----------------------------------------------
85556 + John Chang 2004-09-01 modified for rt2561/2661
85557 + Jan Lee 2006-08-01 modified for rt2860 for 802.11n
85558 +*/
85559 +#include "../rt_config.h"
85560 +
85561 +#define AC0_DEF_TXOP 0
85562 +#define AC1_DEF_TXOP 0
85563 +#define AC2_DEF_TXOP 94
85564 +#define AC3_DEF_TXOP 47
85565 +
85566 +VOID AdhocTurnOnQos(
85567 + IN PRTMP_ADAPTER pAd)
85568 +{
85569 + // Turn on QOs if use HT rate.
85570 + if (pAd->CommonCfg.APEdcaParm.bValid == FALSE)
85571 + {
85572 + pAd->CommonCfg.APEdcaParm.bValid = TRUE;
85573 + pAd->CommonCfg.APEdcaParm.Aifsn[0] = 3;
85574 + pAd->CommonCfg.APEdcaParm.Aifsn[1] = 7;
85575 + pAd->CommonCfg.APEdcaParm.Aifsn[2] = 1;
85576 + pAd->CommonCfg.APEdcaParm.Aifsn[3] = 1;
85577 +
85578 + pAd->CommonCfg.APEdcaParm.Cwmin[0] = 4;
85579 + pAd->CommonCfg.APEdcaParm.Cwmin[1] = 4;
85580 + pAd->CommonCfg.APEdcaParm.Cwmin[2] = 3;
85581 + pAd->CommonCfg.APEdcaParm.Cwmin[3] = 2;
85582 +
85583 + pAd->CommonCfg.APEdcaParm.Cwmax[0] = 10;
85584 + pAd->CommonCfg.APEdcaParm.Cwmax[1] = 6;
85585 + pAd->CommonCfg.APEdcaParm.Cwmax[2] = 4;
85586 + pAd->CommonCfg.APEdcaParm.Cwmax[3] = 3;
85587 +
85588 + pAd->CommonCfg.APEdcaParm.Txop[0] = 0;
85589 + pAd->CommonCfg.APEdcaParm.Txop[1] = 0;
85590 + pAd->CommonCfg.APEdcaParm.Txop[2] = AC2_DEF_TXOP;
85591 + pAd->CommonCfg.APEdcaParm.Txop[3] = AC3_DEF_TXOP;
85592 + }
85593 + AsicSetEdcaParm(pAd, &pAd->CommonCfg.APEdcaParm);
85594 +}
85595 +
85596 +/*
85597 + ==========================================================================
85598 + Description:
85599 + The sync state machine,
85600 + Parameters:
85601 + Sm - pointer to the state machine
85602 + Note:
85603 + the state machine looks like the following
85604 +
85605 + ==========================================================================
85606 + */
85607 +VOID SyncStateMachineInit(
85608 + IN PRTMP_ADAPTER pAd,
85609 + IN STATE_MACHINE *Sm,
85610 + OUT STATE_MACHINE_FUNC Trans[])
85611 +{
85612 + StateMachineInit(Sm, Trans, MAX_SYNC_STATE, MAX_SYNC_MSG, (STATE_MACHINE_FUNC)Drop, SYNC_IDLE, SYNC_MACHINE_BASE);
85613 +
85614 + // column 1
85615 + StateMachineSetAction(Sm, SYNC_IDLE, MT2_MLME_SCAN_REQ, (STATE_MACHINE_FUNC)MlmeScanReqAction);
85616 + StateMachineSetAction(Sm, SYNC_IDLE, MT2_MLME_JOIN_REQ, (STATE_MACHINE_FUNC)MlmeJoinReqAction);
85617 + StateMachineSetAction(Sm, SYNC_IDLE, MT2_MLME_START_REQ, (STATE_MACHINE_FUNC)MlmeStartReqAction);
85618 + StateMachineSetAction(Sm, SYNC_IDLE, MT2_PEER_BEACON, (STATE_MACHINE_FUNC)PeerBeacon);
85619 + StateMachineSetAction(Sm, SYNC_IDLE, MT2_PEER_PROBE_REQ, (STATE_MACHINE_FUNC)PeerProbeReqAction);
85620 +
85621 + //column 2
85622 + StateMachineSetAction(Sm, JOIN_WAIT_BEACON, MT2_MLME_SCAN_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenScan);
85623 + StateMachineSetAction(Sm, JOIN_WAIT_BEACON, MT2_MLME_JOIN_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenJoin);
85624 + StateMachineSetAction(Sm, JOIN_WAIT_BEACON, MT2_MLME_START_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenStart);
85625 + StateMachineSetAction(Sm, JOIN_WAIT_BEACON, MT2_PEER_BEACON, (STATE_MACHINE_FUNC)PeerBeaconAtJoinAction);
85626 + StateMachineSetAction(Sm, JOIN_WAIT_BEACON, MT2_BEACON_TIMEOUT, (STATE_MACHINE_FUNC)BeaconTimeoutAtJoinAction);
85627 +
85628 + // column 3
85629 + StateMachineSetAction(Sm, SCAN_LISTEN, MT2_MLME_SCAN_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenScan);
85630 + StateMachineSetAction(Sm, SCAN_LISTEN, MT2_MLME_JOIN_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenJoin);
85631 + StateMachineSetAction(Sm, SCAN_LISTEN, MT2_MLME_START_REQ, (STATE_MACHINE_FUNC)InvalidStateWhenStart);
85632 + StateMachineSetAction(Sm, SCAN_LISTEN, MT2_PEER_BEACON, (STATE_MACHINE_FUNC)PeerBeaconAtScanAction);
85633 + StateMachineSetAction(Sm, SCAN_LISTEN, MT2_PEER_PROBE_RSP, (STATE_MACHINE_FUNC)PeerBeaconAtScanAction);
85634 + StateMachineSetAction(Sm, SCAN_LISTEN, MT2_SCAN_TIMEOUT, (STATE_MACHINE_FUNC)ScanTimeoutAction);
85635 +
85636 + // timer init
85637 + RTMPInitTimer(pAd, &pAd->MlmeAux.BeaconTimer, GET_TIMER_FUNCTION(BeaconTimeout), pAd, FALSE);
85638 + RTMPInitTimer(pAd, &pAd->MlmeAux.ScanTimer, GET_TIMER_FUNCTION(ScanTimeout), pAd, FALSE);
85639 +}
85640 +
85641 +/*
85642 + ==========================================================================
85643 + Description:
85644 + Beacon timeout handler, executed in timer thread
85645 +
85646 + IRQL = DISPATCH_LEVEL
85647 +
85648 + ==========================================================================
85649 + */
85650 +VOID BeaconTimeout(
85651 + IN PVOID SystemSpecific1,
85652 + IN PVOID FunctionContext,
85653 + IN PVOID SystemSpecific2,
85654 + IN PVOID SystemSpecific3)
85655 +{
85656 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
85657 +
85658 + DBGPRINT(RT_DEBUG_TRACE,("SYNC - BeaconTimeout\n"));
85659 +
85660 + // Do nothing if the driver is starting halt state.
85661 + // This might happen when timer already been fired before cancel timer with mlmehalt
85662 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS))
85663 + return;
85664 +
85665 +#ifdef DOT11_N_SUPPORT
85666 + if ((pAd->CommonCfg.BBPCurrentBW == BW_40)
85667 + )
85668 + {
85669 + UCHAR BBPValue = 0;
85670 + AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE);
85671 + AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel);
85672 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
85673 + BBPValue &= (~0x18);
85674 + BBPValue |= 0x10;
85675 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
85676 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to 40MHz channel %d, Total BSS[%02d]\n",pAd->CommonCfg.CentralChannel, pAd->ScanTab.BssNr));
85677 + }
85678 +#endif // DOT11_N_SUPPORT //
85679 +
85680 + MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_BEACON_TIMEOUT, 0, NULL);
85681 + RT28XX_MLME_HANDLER(pAd);
85682 +}
85683 +
85684 +/*
85685 + ==========================================================================
85686 + Description:
85687 + Scan timeout handler, executed in timer thread
85688 +
85689 + IRQL = DISPATCH_LEVEL
85690 +
85691 + ==========================================================================
85692 + */
85693 +VOID ScanTimeout(
85694 + IN PVOID SystemSpecific1,
85695 + IN PVOID FunctionContext,
85696 + IN PVOID SystemSpecific2,
85697 + IN PVOID SystemSpecific3)
85698 +{
85699 + RTMP_ADAPTER *pAd = (RTMP_ADAPTER *)FunctionContext;
85700 +
85701 +
85702 + // Do nothing if the driver is starting halt state.
85703 + // This might happen when timer already been fired before cancel timer with mlmehalt
85704 + if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_HALT_IN_PROGRESS))
85705 + return;
85706 +
85707 + if (MlmeEnqueue(pAd, SYNC_STATE_MACHINE, MT2_SCAN_TIMEOUT, 0, NULL))
85708 + {
85709 + RT28XX_MLME_HANDLER(pAd);
85710 + }
85711 + else
85712 + {
85713 + // To prevent SyncMachine.CurrState is SCAN_LISTEN forever.
85714 + pAd->MlmeAux.Channel = 0;
85715 + ScanNextChannel(pAd);
85716 + if (pAd->CommonCfg.bWirelessEvent)
85717 + {
85718 + RTMPSendWirelessEvent(pAd, IW_SCAN_ENQUEUE_FAIL_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
85719 + }
85720 + }
85721 +}
85722 +
85723 +/*
85724 + ==========================================================================
85725 + Description:
85726 + MLME SCAN req state machine procedure
85727 + ==========================================================================
85728 + */
85729 +VOID MlmeScanReqAction(
85730 + IN PRTMP_ADAPTER pAd,
85731 + IN MLME_QUEUE_ELEM *Elem)
85732 +{
85733 + UCHAR Ssid[MAX_LEN_OF_SSID], SsidLen, ScanType, BssType, BBPValue = 0;
85734 + BOOLEAN TimerCancelled;
85735 + ULONG Now;
85736 + USHORT Status;
85737 + PHEADER_802_11 pHdr80211;
85738 + PUCHAR pOutBuffer = NULL;
85739 + NDIS_STATUS NStatus;
85740 +
85741 + // Check the total scan tries for one single OID command
85742 + // If this is the CCX 2.0 Case, skip that!
85743 + if ( !RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_START_UP))
85744 + {
85745 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - MlmeScanReqAction before Startup\n"));
85746 + return;
85747 + }
85748 +
85749 + // Increase the scan retry counters.
85750 + pAd->StaCfg.ScanCnt++;
85751 +
85752 +#ifdef RT2860
85753 + if ((OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE)) &&
85754 + (IDLE_ON(pAd)) &&
85755 + (pAd->StaCfg.bRadio == TRUE) &&
85756 + (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_IDLE_RADIO_OFF)))
85757 + {
85758 + RT28xxPciAsicRadioOn(pAd, GUI_IDLE_POWER_SAVE);
85759 + }
85760 +#endif // RT2860 //
85761 +
85762 + // first check the parameter sanity
85763 + if (MlmeScanReqSanity(pAd,
85764 + Elem->Msg,
85765 + Elem->MsgLen,
85766 + &BssType,
85767 + Ssid,
85768 + &SsidLen,
85769 + &ScanType))
85770 + {
85771 +
85772 + // Check for channel load and noise hist request
85773 + // Suspend MSDU only at scan request, not the last two mentioned
85774 + if ((ScanType == SCAN_CISCO_NOISE) || (ScanType == SCAN_CISCO_CHANNEL_LOAD))
85775 + {
85776 + if (pAd->StaCfg.CCXScanChannel != pAd->CommonCfg.Channel)
85777 + RTMPSuspendMsduTransmission(pAd); // Suspend MSDU transmission here
85778 + }
85779 + else
85780 + {
85781 + // Suspend MSDU transmission here
85782 + RTMPSuspendMsduTransmission(pAd);
85783 + }
85784 +
85785 + //
85786 + // To prevent data lost.
85787 + // Send an NULL data with turned PSM bit on to current associated AP before SCAN progress.
85788 + // And should send an NULL data with turned PSM bit off to AP, when scan progress done
85789 + //
85790 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) && (INFRA_ON(pAd)))
85791 + {
85792 + NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer);
85793 + if (NStatus == NDIS_STATUS_SUCCESS)
85794 + {
85795 + pHdr80211 = (PHEADER_802_11) pOutBuffer;
85796 + MgtMacHeaderInit(pAd, pHdr80211, SUBTYPE_NULL_FUNC, 1, pAd->CommonCfg.Bssid, pAd->CommonCfg.Bssid);
85797 + pHdr80211->Duration = 0;
85798 + pHdr80211->FC.Type = BTYPE_DATA;
85799 + pHdr80211->FC.PwrMgmt = PWR_SAVE;
85800 +
85801 + // Send using priority queue
85802 + MiniportMMRequest(pAd, 0, pOutBuffer, sizeof(HEADER_802_11));
85803 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeScanReqAction -- Send PSM Data frame for off channel RM\n"));
85804 + MlmeFreeMemory(pAd, pOutBuffer);
85805 + RTMPusecDelay(5000);
85806 + }
85807 + }
85808 +
85809 + NdisGetSystemUpTime(&Now);
85810 + pAd->StaCfg.LastScanTime = Now;
85811 + // reset all the timers
85812 + RTMPCancelTimer(&pAd->MlmeAux.BeaconTimer, &TimerCancelled);
85813 + RTMPCancelTimer(&pAd->MlmeAux.ScanTimer, &TimerCancelled);
85814 +
85815 + // record desired BSS parameters
85816 + pAd->MlmeAux.BssType = BssType;
85817 + pAd->MlmeAux.ScanType = ScanType;
85818 + pAd->MlmeAux.SsidLen = SsidLen;
85819 + NdisZeroMemory(pAd->MlmeAux.Ssid, MAX_LEN_OF_SSID);
85820 + NdisMoveMemory(pAd->MlmeAux.Ssid, Ssid, SsidLen);
85821 +
85822 + // start from the first channel
85823 + pAd->MlmeAux.Channel = FirstChannel(pAd);
85824 +
85825 + // Change the scan channel when dealing with CCX beacon report
85826 + if ((ScanType == SCAN_CISCO_PASSIVE) || (ScanType == SCAN_CISCO_ACTIVE) ||
85827 + (ScanType == SCAN_CISCO_CHANNEL_LOAD) || (ScanType == SCAN_CISCO_NOISE))
85828 + pAd->MlmeAux.Channel = pAd->StaCfg.CCXScanChannel;
85829 +
85830 + // Let BBP register at 20MHz to do scan
85831 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
85832 + BBPValue &= (~0x18);
85833 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
85834 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - BBP R4 to 20MHz.l\n"));
85835 + ScanNextChannel(pAd);
85836 + }
85837 + else
85838 + {
85839 + DBGPRINT_ERR(("SYNC - MlmeScanReqAction() sanity check fail\n"));
85840 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
85841 + Status = MLME_INVALID_FORMAT;
85842 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_SCAN_CONF, 2, &Status);
85843 + }
85844 +}
85845 +
85846 +/*
85847 + ==========================================================================
85848 + Description:
85849 + MLME JOIN req state machine procedure
85850 + ==========================================================================
85851 + */
85852 +VOID MlmeJoinReqAction(
85853 + IN PRTMP_ADAPTER pAd,
85854 + IN MLME_QUEUE_ELEM *Elem)
85855 +{
85856 + UCHAR BBPValue = 0;
85857 + BSS_ENTRY *pBss;
85858 + BOOLEAN TimerCancelled;
85859 + HEADER_802_11 Hdr80211;
85860 + NDIS_STATUS NStatus;
85861 + ULONG FrameLen = 0;
85862 + PUCHAR pOutBuffer = NULL;
85863 + PUCHAR pSupRate = NULL;
85864 + UCHAR SupRateLen;
85865 + PUCHAR pExtRate = NULL;
85866 + UCHAR ExtRateLen;
85867 + UCHAR ASupRate[] = {0x8C, 0x12, 0x98, 0x24, 0xb0, 0x48, 0x60, 0x6C};
85868 + UCHAR ASupRateLen = sizeof(ASupRate)/sizeof(UCHAR);
85869 + MLME_JOIN_REQ_STRUCT *pInfo = (MLME_JOIN_REQ_STRUCT *)(Elem->Msg);
85870 +
85871 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - MlmeJoinReqAction(BSS #%ld)\n", pInfo->BssIdx));
85872 +
85873 +#ifdef RT2860
85874 + if ((OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE)) &&
85875 + (IDLE_ON(pAd)) &&
85876 + (pAd->StaCfg.bRadio == TRUE) &&
85877 + (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_IDLE_RADIO_OFF)))
85878 + {
85879 + RT28xxPciAsicRadioOn(pAd, GUI_IDLE_POWER_SAVE);
85880 + }
85881 +#endif // RT2860 //
85882 +
85883 + // reset all the timers
85884 + RTMPCancelTimer(&pAd->MlmeAux.ScanTimer, &TimerCancelled);
85885 + RTMPCancelTimer(&pAd->MlmeAux.BeaconTimer, &TimerCancelled);
85886 +
85887 + pBss = &pAd->MlmeAux.SsidBssTab.BssEntry[pInfo->BssIdx];
85888 +
85889 + // record the desired SSID & BSSID we're waiting for
85890 + COPY_MAC_ADDR(pAd->MlmeAux.Bssid, pBss->Bssid);
85891 +
85892 + // If AP's SSID is not hidden, it is OK for updating ssid to MlmeAux again.
85893 + if (pBss->Hidden == 0)
85894 + {
85895 + NdisMoveMemory(pAd->MlmeAux.Ssid, pBss->Ssid, pBss->SsidLen);
85896 + pAd->MlmeAux.SsidLen = pBss->SsidLen;
85897 + }
85898 +
85899 + pAd->MlmeAux.BssType = pBss->BssType;
85900 + pAd->MlmeAux.Channel = pBss->Channel;
85901 + pAd->MlmeAux.CentralChannel = pBss->CentralChannel;
85902 +
85903 +#ifdef EXT_BUILD_CHANNEL_LIST
85904 + // Country IE of the AP will be evaluated and will be used.
85905 + if ((pAd->StaCfg.IEEE80211dClientMode != Rt802_11_D_None) &&
85906 + (pBss->bHasCountryIE == TRUE))
85907 + {
85908 + NdisMoveMemory(&pAd->CommonCfg.CountryCode[0], &pBss->CountryString[0], 2);
85909 + if (pBss->CountryString[2] == 'I')
85910 + pAd->CommonCfg.Geography = IDOR;
85911 + else if (pBss->CountryString[2] == 'O')
85912 + pAd->CommonCfg.Geography = ODOR;
85913 + else
85914 + pAd->CommonCfg.Geography = BOTH;
85915 + BuildChannelListEx(pAd);
85916 + }
85917 +#endif // EXT_BUILD_CHANNEL_LIST //
85918 +
85919 + // Let BBP register at 20MHz to do scan
85920 + RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue);
85921 + BBPValue &= (~0x18);
85922 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue);
85923 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - BBP R4 to 20MHz.l\n"));
85924 +
85925 + // switch channel and waiting for beacon timer
85926 + AsicSwitchChannel(pAd, pAd->MlmeAux.Channel, FALSE);
85927 + AsicLockChannel(pAd, pAd->MlmeAux.Channel);
85928 + RTMPSetTimer(&pAd->MlmeAux.BeaconTimer, JOIN_TIMEOUT);
85929 +
85930 + do
85931 + {
85932 + if (((pAd->CommonCfg.bIEEE80211H == 1) &&
85933 + (pAd->MlmeAux.Channel > 14) &&
85934 + RadarChannelCheck(pAd, pAd->MlmeAux.Channel))
85935 +#ifdef CARRIER_DETECTION_SUPPORT // Roger sync Carrier
85936 + || (pAd->CommonCfg.CarrierDetect.Enable == TRUE)
85937 +#endif // CARRIER_DETECTION_SUPPORT //
85938 + )
85939 + {
85940 + //
85941 + // We can't send any Probe request frame to meet 802.11h.
85942 + //
85943 + if (pBss->Hidden == 0)
85944 + break;
85945 + }
85946 +
85947 + //
85948 + // send probe request
85949 + //
85950 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer);
85951 + if (NStatus == NDIS_STATUS_SUCCESS)
85952 + {
85953 + if (pAd->MlmeAux.Channel <= 14)
85954 + {
85955 + pSupRate = pAd->CommonCfg.SupRate;
85956 + SupRateLen = pAd->CommonCfg.SupRateLen;
85957 + pExtRate = pAd->CommonCfg.ExtRate;
85958 + ExtRateLen = pAd->CommonCfg.ExtRateLen;
85959 + }
85960 + else
85961 + {
85962 + //
85963 + // Overwrite Support Rate, CCK rate are not allowed
85964 + //
85965 + pSupRate = ASupRate;
85966 + SupRateLen = ASupRateLen;
85967 + ExtRateLen = 0;
85968 + }
85969 +
85970 + if (pAd->MlmeAux.BssType == BSS_INFRA)
85971 + MgtMacHeaderInit(pAd, &Hdr80211, SUBTYPE_PROBE_REQ, 0, pAd->MlmeAux.Bssid, pAd->MlmeAux.Bssid);
85972 + else
85973 + MgtMacHeaderInit(pAd, &Hdr80211, SUBTYPE_PROBE_REQ, 0, BROADCAST_ADDR, BROADCAST_ADDR);
85974 +
85975 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
85976 + sizeof(HEADER_802_11), &Hdr80211,
85977 + 1, &SsidIe,
85978 + 1, &pAd->MlmeAux.SsidLen,
85979 + pAd->MlmeAux.SsidLen, pAd->MlmeAux.Ssid,
85980 + 1, &SupRateIe,
85981 + 1, &SupRateLen,
85982 + SupRateLen, pSupRate,
85983 + END_OF_ARGS);
85984 +
85985 + if (ExtRateLen)
85986 + {
85987 + ULONG Tmp;
85988 + MakeOutgoingFrame(pOutBuffer + FrameLen, &Tmp,
85989 + 1, &ExtRateIe,
85990 + 1, &ExtRateLen,
85991 + ExtRateLen, pExtRate,
85992 + END_OF_ARGS);
85993 + FrameLen += Tmp;
85994 + }
85995 +
85996 +
85997 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
85998 + MlmeFreeMemory(pAd, pOutBuffer);
85999 + }
86000 + } while (FALSE);
86001 +
86002 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - Switch to ch %d, Wait BEACON from %02x:%02x:%02x:%02x:%02x:%02x\n",
86003 + pBss->Channel, pBss->Bssid[0], pBss->Bssid[1], pBss->Bssid[2], pBss->Bssid[3], pBss->Bssid[4], pBss->Bssid[5]));
86004 +
86005 + pAd->Mlme.SyncMachine.CurrState = JOIN_WAIT_BEACON;
86006 +}
86007 +
86008 +/*
86009 + ==========================================================================
86010 + Description:
86011 + MLME START Request state machine procedure, starting an IBSS
86012 + ==========================================================================
86013 + */
86014 +VOID MlmeStartReqAction(
86015 + IN PRTMP_ADAPTER pAd,
86016 + IN MLME_QUEUE_ELEM *Elem)
86017 +{
86018 + UCHAR Ssid[MAX_LEN_OF_SSID], SsidLen;
86019 + BOOLEAN TimerCancelled;
86020 +
86021 + // New for WPA security suites
86022 + UCHAR VarIE[MAX_VIE_LEN]; // Total VIE length = MAX_VIE_LEN - -5
86023 + NDIS_802_11_VARIABLE_IEs *pVIE = NULL;
86024 + LARGE_INTEGER TimeStamp;
86025 + BOOLEAN Privacy;
86026 + USHORT Status;
86027 +
86028 + // Init Variable IE structure
86029 + pVIE = (PNDIS_802_11_VARIABLE_IEs) VarIE;
86030 + pVIE->Length = 0;
86031 + TimeStamp.u.LowPart = 0;
86032 + TimeStamp.u.HighPart = 0;
86033 +
86034 + if (MlmeStartReqSanity(pAd, Elem->Msg, Elem->MsgLen, Ssid, &SsidLen))
86035 + {
86036 + // reset all the timers
86037 + RTMPCancelTimer(&pAd->MlmeAux.ScanTimer, &TimerCancelled);
86038 + RTMPCancelTimer(&pAd->MlmeAux.BeaconTimer, &TimerCancelled);
86039 +
86040 + //
86041 + // Start a new IBSS. All IBSS parameters are decided now....
86042 + //
86043 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeStartReqAction - Start a new IBSS. All IBSS parameters are decided now.... \n"));
86044 + pAd->MlmeAux.BssType = BSS_ADHOC;
86045 + NdisMoveMemory(pAd->MlmeAux.Ssid, Ssid, SsidLen);
86046 + pAd->MlmeAux.SsidLen = SsidLen;
86047 +
86048 + // generate a radom number as BSSID
86049 + MacAddrRandomBssid(pAd, pAd->MlmeAux.Bssid);
86050 + DBGPRINT(RT_DEBUG_TRACE, ("MlmeStartReqAction - generate a radom number as BSSID \n"));
86051 +
86052 + Privacy = (pAd->StaCfg.WepStatus == Ndis802_11Encryption1Enabled) ||
86053 + (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) ||
86054 + (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled);
86055 + pAd->MlmeAux.CapabilityInfo = CAP_GENERATE(0,1,Privacy, (pAd->CommonCfg.TxPreamble == Rt802_11PreambleShort), 1, 0);
86056 + pAd->MlmeAux.BeaconPeriod = pAd->CommonCfg.BeaconPeriod;
86057 + pAd->MlmeAux.AtimWin = pAd->StaCfg.AtimWin;
86058 + pAd->MlmeAux.Channel = pAd->CommonCfg.Channel;
86059 +
86060 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel;
86061 + pAd->MlmeAux.CentralChannel = pAd->CommonCfg.CentralChannel;
86062 +
86063 + pAd->MlmeAux.SupRateLen= pAd->CommonCfg.SupRateLen;
86064 + NdisMoveMemory(pAd->MlmeAux.SupRate, pAd->CommonCfg.SupRate, MAX_LEN_OF_SUPPORTED_RATES);
86065 + RTMPCheckRates(pAd, pAd->MlmeAux.SupRate, &pAd->MlmeAux.SupRateLen);
86066 + pAd->MlmeAux.ExtRateLen = pAd->CommonCfg.ExtRateLen;
86067 + NdisMoveMemory(pAd->MlmeAux.ExtRate, pAd->CommonCfg.ExtRate, MAX_LEN_OF_SUPPORTED_RATES);
86068 + RTMPCheckRates(pAd, pAd->MlmeAux.ExtRate, &pAd->MlmeAux.ExtRateLen);
86069 +#ifdef DOT11_N_SUPPORT
86070 + if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED)
86071 + {
86072 + RTMPUpdateHTIE(&pAd->CommonCfg.DesiredHtPhy, &pAd->StaCfg.DesiredHtPhyInfo.MCSSet[0], &pAd->MlmeAux.HtCapability, &pAd->MlmeAux.AddHtInfo);
86073 + pAd->MlmeAux.HtCapabilityLen = sizeof(HT_CAPABILITY_IE);
86074 + // Not turn pAd->StaActive.SupportedHtPhy.bHtEnable = TRUE here.
86075 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC -pAd->StaActive.SupportedHtPhy.bHtEnable = TRUE\n"));
86076 + }
86077 + else
86078 +#endif // DOT11_N_SUPPORT //
86079 + {
86080 + pAd->MlmeAux.HtCapabilityLen = 0;
86081 + pAd->StaActive.SupportedPhyInfo.bHtEnable = FALSE;
86082 + }
86083 + // temporarily not support QOS in IBSS
86084 + NdisZeroMemory(&pAd->MlmeAux.APEdcaParm, sizeof(EDCA_PARM));
86085 + NdisZeroMemory(&pAd->MlmeAux.APQbssLoad, sizeof(QBSS_LOAD_PARM));
86086 + NdisZeroMemory(&pAd->MlmeAux.APQosCapability, sizeof(QOS_CAPABILITY_PARM));
86087 +
86088 + AsicSwitchChannel(pAd, pAd->MlmeAux.Channel, FALSE);
86089 + AsicLockChannel(pAd, pAd->MlmeAux.Channel);
86090 +
86091 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - MlmeStartReqAction(ch= %d,sup rates= %d, ext rates=%d)\n",
86092 + pAd->MlmeAux.Channel, pAd->MlmeAux.SupRateLen, pAd->MlmeAux.ExtRateLen));
86093 +
86094 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
86095 + Status = MLME_SUCCESS;
86096 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_START_CONF, 2, &Status);
86097 + }
86098 + else
86099 + {
86100 + DBGPRINT_ERR(("SYNC - MlmeStartReqAction() sanity check fail.\n"));
86101 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
86102 + Status = MLME_INVALID_FORMAT;
86103 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_START_CONF, 2, &Status);
86104 + }
86105 +}
86106 +
86107 +/*
86108 + ==========================================================================
86109 + Description:
86110 + peer sends beacon back when scanning
86111 + ==========================================================================
86112 + */
86113 +VOID PeerBeaconAtScanAction(
86114 + IN PRTMP_ADAPTER pAd,
86115 + IN MLME_QUEUE_ELEM *Elem)
86116 +{
86117 + UCHAR Bssid[MAC_ADDR_LEN], Addr2[MAC_ADDR_LEN];
86118 + UCHAR Ssid[MAX_LEN_OF_SSID], BssType, Channel, NewChannel,
86119 + SsidLen, DtimCount, DtimPeriod, BcastFlag, MessageToMe;
86120 + CF_PARM CfParm;
86121 + USHORT BeaconPeriod, AtimWin, CapabilityInfo;
86122 + PFRAME_802_11 pFrame;
86123 + LARGE_INTEGER TimeStamp;
86124 + UCHAR Erp;
86125 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES], ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
86126 + UCHAR SupRateLen, ExtRateLen;
86127 + USHORT LenVIE;
86128 + UCHAR CkipFlag;
86129 + UCHAR AironetCellPowerLimit;
86130 + EDCA_PARM EdcaParm;
86131 + QBSS_LOAD_PARM QbssLoad;
86132 + QOS_CAPABILITY_PARM QosCapability;
86133 + ULONG RalinkIe;
86134 + UCHAR VarIE[MAX_VIE_LEN]; // Total VIE length = MAX_VIE_LEN - -5
86135 + NDIS_802_11_VARIABLE_IEs *pVIE = NULL;
86136 + HT_CAPABILITY_IE HtCapability;
86137 + ADD_HT_INFO_IE AddHtInfo; // AP might use this additional ht info IE
86138 + UCHAR HtCapabilityLen = 0, PreNHtCapabilityLen = 0;
86139 + UCHAR AddHtInfoLen;
86140 + UCHAR NewExtChannelOffset = 0xff;
86141 +
86142 + pFrame = (PFRAME_802_11) Elem->Msg;
86143 + // Init Variable IE structure
86144 + pVIE = (PNDIS_802_11_VARIABLE_IEs) VarIE;
86145 + pVIE->Length = 0;
86146 +#ifdef DOT11_N_SUPPORT
86147 + RTMPZeroMemory(&HtCapability, sizeof(HtCapability));
86148 + RTMPZeroMemory(&AddHtInfo, sizeof(ADD_HT_INFO_IE));
86149 +#endif // DOT11_N_SUPPORT //
86150 +
86151 + if (PeerBeaconAndProbeRspSanity(pAd,
86152 + Elem->Msg,
86153 + Elem->MsgLen,
86154 + Elem->Channel,
86155 + Addr2,
86156 + Bssid,
86157 + Ssid,
86158 + &SsidLen,
86159 + &BssType,
86160 + &BeaconPeriod,
86161 + &Channel,
86162 + &NewChannel,
86163 + &TimeStamp,
86164 + &CfParm,
86165 + &AtimWin,
86166 + &CapabilityInfo,
86167 + &Erp,
86168 + &DtimCount,
86169 + &DtimPeriod,
86170 + &BcastFlag,
86171 + &MessageToMe,
86172 + SupRate,
86173 + &SupRateLen,
86174 + ExtRate,
86175 + &ExtRateLen,
86176 + &CkipFlag,
86177 + &AironetCellPowerLimit,
86178 + &EdcaParm,
86179 + &QbssLoad,
86180 + &QosCapability,
86181 + &RalinkIe,
86182 + &HtCapabilityLen,
86183 + &PreNHtCapabilityLen,
86184 + &HtCapability,
86185 + &AddHtInfoLen,
86186 + &AddHtInfo,
86187 + &NewExtChannelOffset,
86188 + &LenVIE,
86189 + pVIE))
86190 + {
86191 + ULONG Idx;
86192 + CHAR Rssi = 0;
86193 +
86194 + Idx = BssTableSearch(&pAd->ScanTab, Bssid, Channel);
86195 + if (Idx != BSS_NOT_FOUND)
86196 + Rssi = pAd->ScanTab.BssEntry[Idx].Rssi;
86197 +
86198 + Rssi = RTMPMaxRssi(pAd, ConvertToRssi(pAd, Elem->Rssi0, RSSI_0), ConvertToRssi(pAd, Elem->Rssi1, RSSI_1), ConvertToRssi(pAd, Elem->Rssi2, RSSI_2));
86199 +
86200 +
86201 +#ifdef DOT11_N_SUPPORT
86202 + if ((HtCapabilityLen > 0) || (PreNHtCapabilityLen > 0))
86203 + HtCapabilityLen = SIZE_HT_CAP_IE;
86204 +#endif // DOT11_N_SUPPORT //
86205 + if ((pAd->StaCfg.CCXReqType != MSRN_TYPE_UNUSED) && (Channel == pAd->StaCfg.CCXScanChannel))
86206 + {
86207 + Idx = BssTableSetEntry(pAd, &pAd->StaCfg.CCXBssTab, Bssid, Ssid, SsidLen, BssType, BeaconPeriod,
86208 + &CfParm, AtimWin, CapabilityInfo, SupRate, SupRateLen,ExtRate, ExtRateLen, &HtCapability,
86209 + &AddHtInfo, HtCapabilityLen, AddHtInfoLen, NewExtChannelOffset, Channel, Rssi, TimeStamp, CkipFlag,
86210 + &EdcaParm, &QosCapability, &QbssLoad, LenVIE, pVIE);
86211 + if (Idx != BSS_NOT_FOUND)
86212 + {
86213 + NdisMoveMemory(pAd->StaCfg.CCXBssTab.BssEntry[Idx].PTSF, &Elem->Msg[24], 4);
86214 + NdisMoveMemory(&pAd->StaCfg.CCXBssTab.BssEntry[Idx].TTSF[0], &Elem->TimeStamp.u.LowPart, 4);
86215 + NdisMoveMemory(&pAd->StaCfg.CCXBssTab.BssEntry[Idx].TTSF[4], &Elem->TimeStamp.u.LowPart, 4);
86216 + if (pAd->StaCfg.CCXReqType == MSRN_TYPE_BEACON_REQ)
86217 + AironetAddBeaconReport(pAd, Idx, Elem);
86218 + }
86219 + }
86220 + else
86221 + {
86222 + Idx = BssTableSetEntry(pAd, &pAd->ScanTab, Bssid, Ssid, SsidLen, BssType, BeaconPeriod,
86223 + &CfParm, AtimWin, CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen, &HtCapability,
86224 + &AddHtInfo, HtCapabilityLen, AddHtInfoLen, NewExtChannelOffset, Channel, Rssi, TimeStamp, CkipFlag,
86225 + &EdcaParm, &QosCapability, &QbssLoad, LenVIE, pVIE);
86226 +#ifdef DOT11_N_SUPPORT
86227 +#ifdef DOT11N_DRAFT3
86228 + if (pAd->ChannelList[pAd->CommonCfg.ChannelListIdx].bEffectedChannel == TRUE)
86229 + {
86230 + UCHAR RegClass;
86231 + PeerBeaconAndProbeRspSanity2(pAd, Elem->Msg, Elem->MsgLen, &RegClass);
86232 + TriEventTableSetEntry(pAd, &pAd->CommonCfg.TriggerEventTab, Bssid, &HtCapability, HtCapabilityLen, RegClass, Channel);
86233 + }
86234 +#endif // DOT11N_DRAFT3 //
86235 +#endif // DOT11_N_SUPPORT //
86236 + if (Idx != BSS_NOT_FOUND)
86237 + {
86238 + NdisMoveMemory(pAd->ScanTab.BssEntry[Idx].PTSF, &Elem->Msg[24], 4);
86239 + NdisMoveMemory(&pAd->ScanTab.BssEntry[Idx].TTSF[0], &Elem->TimeStamp.u.LowPart, 4);
86240 + NdisMoveMemory(&pAd->ScanTab.BssEntry[Idx].TTSF[4], &Elem->TimeStamp.u.LowPart, 4);
86241 + }
86242 + }
86243 + }
86244 + // sanity check fail, ignored
86245 +}
86246 +
86247 +/*
86248 + ==========================================================================
86249 + Description:
86250 + When waiting joining the (I)BSS, beacon received from external
86251 + ==========================================================================
86252 + */
86253 +VOID PeerBeaconAtJoinAction(
86254 + IN PRTMP_ADAPTER pAd,
86255 + IN MLME_QUEUE_ELEM *Elem)
86256 +{
86257 + UCHAR Bssid[MAC_ADDR_LEN], Addr2[MAC_ADDR_LEN];
86258 + UCHAR Ssid[MAX_LEN_OF_SSID], SsidLen, BssType, Channel, MessageToMe,
86259 + DtimCount, DtimPeriod, BcastFlag, NewChannel;
86260 + LARGE_INTEGER TimeStamp;
86261 + USHORT BeaconPeriod, AtimWin, CapabilityInfo;
86262 + CF_PARM Cf;
86263 + BOOLEAN TimerCancelled;
86264 + UCHAR Erp;
86265 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES], ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
86266 + UCHAR SupRateLen, ExtRateLen;
86267 + UCHAR CkipFlag;
86268 + USHORT LenVIE;
86269 + UCHAR AironetCellPowerLimit;
86270 + EDCA_PARM EdcaParm;
86271 + QBSS_LOAD_PARM QbssLoad;
86272 + QOS_CAPABILITY_PARM QosCapability;
86273 + USHORT Status;
86274 + UCHAR VarIE[MAX_VIE_LEN]; // Total VIE length = MAX_VIE_LEN - -5
86275 + NDIS_802_11_VARIABLE_IEs *pVIE = NULL;
86276 + ULONG RalinkIe;
86277 + ULONG Idx;
86278 + HT_CAPABILITY_IE HtCapability;
86279 + ADD_HT_INFO_IE AddHtInfo; // AP might use this additional ht info IE
86280 + UCHAR HtCapabilityLen = 0, PreNHtCapabilityLen = 0;
86281 + UCHAR AddHtInfoLen;
86282 + UCHAR NewExtChannelOffset = 0xff;
86283 +#ifdef DOT11_N_SUPPORT
86284 + UCHAR CentralChannel;
86285 +#endif // DOT11_N_SUPPORT //
86286 +
86287 + // Init Variable IE structure
86288 + pVIE = (PNDIS_802_11_VARIABLE_IEs) VarIE;
86289 + pVIE->Length = 0;
86290 + RTMPZeroMemory(&HtCapability, sizeof(HtCapability));
86291 + RTMPZeroMemory(&AddHtInfo, sizeof(ADD_HT_INFO_IE));
86292 +
86293 +
86294 + if (PeerBeaconAndProbeRspSanity(pAd,
86295 + Elem->Msg,
86296 + Elem->MsgLen,
86297 + Elem->Channel,
86298 + Addr2,
86299 + Bssid,
86300 + Ssid,
86301 + &SsidLen,
86302 + &BssType,
86303 + &BeaconPeriod,
86304 + &Channel,
86305 + &NewChannel,
86306 + &TimeStamp,
86307 + &Cf,
86308 + &AtimWin,
86309 + &CapabilityInfo,
86310 + &Erp,
86311 + &DtimCount,
86312 + &DtimPeriod,
86313 + &BcastFlag,
86314 + &MessageToMe,
86315 + SupRate,
86316 + &SupRateLen,
86317 + ExtRate,
86318 + &ExtRateLen,
86319 + &CkipFlag,
86320 + &AironetCellPowerLimit,
86321 + &EdcaParm,
86322 + &QbssLoad,
86323 + &QosCapability,
86324 + &RalinkIe,
86325 + &HtCapabilityLen,
86326 + &PreNHtCapabilityLen,
86327 + &HtCapability,
86328 + &AddHtInfoLen,
86329 + &AddHtInfo,
86330 + &NewExtChannelOffset,
86331 + &LenVIE,
86332 + pVIE))
86333 + {
86334 + // Disqualify 11b only adhoc when we are in 11g only adhoc mode
86335 + if ((BssType == BSS_ADHOC) && (pAd->CommonCfg.PhyMode == PHY_11G) && ((SupRateLen+ExtRateLen)< 12))
86336 + return;
86337 +
86338 + // BEACON from desired BSS/IBSS found. We should be able to decide most
86339 + // BSS parameters here.
86340 + // Q. But what happen if this JOIN doesn't conclude a successful ASSOCIATEION?
86341 + // Do we need to receover back all parameters belonging to previous BSS?
86342 + // A. Should be not. There's no back-door recover to previous AP. It still need
86343 + // a new JOIN-AUTH-ASSOC sequence.
86344 + if (MAC_ADDR_EQUAL(pAd->MlmeAux.Bssid, Bssid))
86345 + {
86346 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - receive desired BEACON at JoinWaitBeacon... Channel = %d\n", Channel));
86347 + RTMPCancelTimer(&pAd->MlmeAux.BeaconTimer, &TimerCancelled);
86348 +
86349 + // Update RSSI to prevent No signal display when cards first initialized
86350 + pAd->StaCfg.RssiSample.LastRssi0 = ConvertToRssi(pAd, Elem->Rssi0, RSSI_0);
86351 + pAd->StaCfg.RssiSample.LastRssi1 = ConvertToRssi(pAd, Elem->Rssi1, RSSI_1);
86352 + pAd->StaCfg.RssiSample.LastRssi2 = ConvertToRssi(pAd, Elem->Rssi2, RSSI_2);
86353 + pAd->StaCfg.RssiSample.AvgRssi0 = pAd->StaCfg.RssiSample.LastRssi0;
86354 + pAd->StaCfg.RssiSample.AvgRssi0X8 = pAd->StaCfg.RssiSample.AvgRssi0 << 3;
86355 + pAd->StaCfg.RssiSample.AvgRssi1 = pAd->StaCfg.RssiSample.LastRssi1;
86356 + pAd->StaCfg.RssiSample.AvgRssi1X8 = pAd->StaCfg.RssiSample.AvgRssi1 << 3;
86357 + pAd->StaCfg.RssiSample.AvgRssi2 = pAd->StaCfg.RssiSample.LastRssi2;
86358 + pAd->StaCfg.RssiSample.AvgRssi2X8 = pAd->StaCfg.RssiSample.AvgRssi2 << 3;
86359 +
86360 + //
86361 + // We need to check if SSID only set to any, then we can record the current SSID.
86362 + // Otherwise will cause hidden SSID association failed.
86363 + //
86364 + if (pAd->MlmeAux.SsidLen == 0)
86365 + {
86366 + NdisMoveMemory(pAd->MlmeAux.Ssid, Ssid, SsidLen);
86367 + pAd->MlmeAux.SsidLen = SsidLen;
86368 + }
86369 + else
86370 + {
86371 + Idx = BssSsidTableSearch(&pAd->ScanTab, Bssid, pAd->MlmeAux.Ssid, pAd->MlmeAux.SsidLen, Channel);
86372 +
86373 + if (Idx != BSS_NOT_FOUND)
86374 + {
86375 + //
86376 + // Multiple SSID case, used correct CapabilityInfo
86377 + //
86378 + CapabilityInfo = pAd->ScanTab.BssEntry[Idx].CapabilityInfo;
86379 + }
86380 + }
86381 + NdisMoveMemory(pAd->MlmeAux.Bssid, Bssid, MAC_ADDR_LEN);
86382 + pAd->MlmeAux.CapabilityInfo = CapabilityInfo & SUPPORTED_CAPABILITY_INFO;
86383 + pAd->MlmeAux.BssType = BssType;
86384 + pAd->MlmeAux.BeaconPeriod = BeaconPeriod;
86385 + pAd->MlmeAux.Channel = Channel;
86386 + pAd->MlmeAux.AtimWin = AtimWin;
86387 + pAd->MlmeAux.CfpPeriod = Cf.CfpPeriod;
86388 + pAd->MlmeAux.CfpMaxDuration = Cf.CfpMaxDuration;
86389 + pAd->MlmeAux.APRalinkIe = RalinkIe;
86390 +
86391 + // Copy AP's supported rate to MlmeAux for creating assoication request
86392 + // Also filter out not supported rate
86393 + pAd->MlmeAux.SupRateLen = SupRateLen;
86394 + NdisMoveMemory(pAd->MlmeAux.SupRate, SupRate, SupRateLen);
86395 + RTMPCheckRates(pAd, pAd->MlmeAux.SupRate, &pAd->MlmeAux.SupRateLen);
86396 + pAd->MlmeAux.ExtRateLen = ExtRateLen;
86397 + NdisMoveMemory(pAd->MlmeAux.ExtRate, ExtRate, ExtRateLen);
86398 + RTMPCheckRates(pAd, pAd->MlmeAux.ExtRate, &pAd->MlmeAux.ExtRateLen);
86399 +
86400 + NdisZeroMemory(pAd->StaActive.SupportedPhyInfo.MCSSet, 16);
86401 +#ifdef DOT11_N_SUPPORT
86402 + pAd->MlmeAux.NewExtChannelOffset = NewExtChannelOffset;
86403 + pAd->MlmeAux.HtCapabilityLen = HtCapabilityLen;
86404 +
86405 + // filter out un-supported ht rates
86406 + if (((HtCapabilityLen > 0) || (PreNHtCapabilityLen > 0)) && (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
86407 + {
86408 + RTMPZeroMemory(&pAd->MlmeAux.HtCapability, SIZE_HT_CAP_IE);
86409 + RTMPMoveMemory(&pAd->MlmeAux.AddHtInfo, &AddHtInfo, SIZE_ADD_HT_INFO_IE);
86410 +
86411 + // StaActive.SupportedHtPhy.MCSSet stores Peer AP's 11n Rx capability
86412 + NdisMoveMemory(pAd->StaActive.SupportedPhyInfo.MCSSet, HtCapability.MCSSet, 16);
86413 + pAd->MlmeAux.NewExtChannelOffset = NewExtChannelOffset;
86414 + pAd->MlmeAux.HtCapabilityLen = SIZE_HT_CAP_IE;
86415 + pAd->StaActive.SupportedPhyInfo.bHtEnable = TRUE;
86416 + if (PreNHtCapabilityLen > 0)
86417 + pAd->StaActive.SupportedPhyInfo.bPreNHt = TRUE;
86418 + RTMPCheckHt(pAd, BSSID_WCID, &HtCapability, &AddHtInfo);
86419 + // Copy AP Parameter to StaActive. This is also in LinkUp.
86420 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAtJoinAction! (MpduDensity=%d, MaxRAmpduFactor=%d, BW=%d)\n",
86421 + pAd->StaActive.SupportedHtPhy.MpduDensity, pAd->StaActive.SupportedHtPhy.MaxRAmpduFactor, HtCapability.HtCapInfo.ChannelWidth));
86422 +
86423 + if (AddHtInfoLen > 0)
86424 + {
86425 + CentralChannel = AddHtInfo.ControlChan;
86426 + // Check again the Bandwidth capability of this AP.
86427 + if ((AddHtInfo.ControlChan > 2)&& (AddHtInfo.AddHtInfo.ExtChanOffset == EXTCHA_BELOW) && (HtCapability.HtCapInfo.ChannelWidth == BW_40))
86428 + {
86429 + CentralChannel = AddHtInfo.ControlChan - 2;
86430 + }
86431 + else if ((AddHtInfo.AddHtInfo.ExtChanOffset == EXTCHA_ABOVE) && (HtCapability.HtCapInfo.ChannelWidth == BW_40))
86432 + {
86433 + CentralChannel = AddHtInfo.ControlChan + 2;
86434 + }
86435 +
86436 + // Check Error .
86437 + if (pAd->MlmeAux.CentralChannel != CentralChannel)
86438 + DBGPRINT(RT_DEBUG_ERROR, ("PeerBeaconAtJoinAction HT===>Beacon Central Channel = %d, Control Channel = %d. Mlmeaux CentralChannel = %d\n", CentralChannel, AddHtInfo.ControlChan, pAd->MlmeAux.CentralChannel));
86439 +
86440 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeaconAtJoinAction HT===>Central Channel = %d, Control Channel = %d, .\n", CentralChannel, AddHtInfo.ControlChan));
86441 +
86442 + }
86443 +
86444 + }
86445 + else
86446 +#endif // DOT11_N_SUPPORT //
86447 + {
86448 + // To prevent error, let legacy AP must have same CentralChannel and Channel.
86449 + if ((HtCapabilityLen == 0) && (PreNHtCapabilityLen == 0))
86450 + pAd->MlmeAux.CentralChannel = pAd->MlmeAux.Channel;
86451 +
86452 + pAd->StaActive.SupportedPhyInfo.bHtEnable = FALSE;
86453 + RTMPZeroMemory(&pAd->MlmeAux.HtCapability, SIZE_HT_CAP_IE);
86454 + RTMPZeroMemory(&pAd->MlmeAux.AddHtInfo, SIZE_ADD_HT_INFO_IE);
86455 + }
86456 +
86457 + RTMPUpdateMlmeRate(pAd);
86458 +
86459 + // copy QOS related information
86460 + if ((pAd->CommonCfg.bWmmCapable)
86461 +#ifdef DOT11_N_SUPPORT
86462 + || (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED)
86463 +#endif // DOT11_N_SUPPORT //
86464 + )
86465 + {
86466 + NdisMoveMemory(&pAd->MlmeAux.APEdcaParm, &EdcaParm, sizeof(EDCA_PARM));
86467 + NdisMoveMemory(&pAd->MlmeAux.APQbssLoad, &QbssLoad, sizeof(QBSS_LOAD_PARM));
86468 + NdisMoveMemory(&pAd->MlmeAux.APQosCapability, &QosCapability, sizeof(QOS_CAPABILITY_PARM));
86469 + }
86470 + else
86471 + {
86472 + NdisZeroMemory(&pAd->MlmeAux.APEdcaParm, sizeof(EDCA_PARM));
86473 + NdisZeroMemory(&pAd->MlmeAux.APQbssLoad, sizeof(QBSS_LOAD_PARM));
86474 + NdisZeroMemory(&pAd->MlmeAux.APQosCapability, sizeof(QOS_CAPABILITY_PARM));
86475 + }
86476 +
86477 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - after JOIN, SupRateLen=%d, ExtRateLen=%d\n",
86478 + pAd->MlmeAux.SupRateLen, pAd->MlmeAux.ExtRateLen));
86479 +
86480 +#ifdef LEAP_SUPPORT
86481 + // Update CkipFlag
86482 + pAd->StaCfg.CkipFlag = CkipFlag;
86483 +
86484 + // Keep TimeStamp for Re-Association used.
86485 + if (LEAP_CCKM_ON(pAd) && (pAd->StaCfg.CCKMLinkUpFlag == TRUE))
86486 + pAd->StaCfg.CCKMBeaconAtJoinTimeStamp = TimeStamp;
86487 +#endif // LEAP_SUPPORT //
86488 +
86489 + if (AironetCellPowerLimit != 0xFF)
86490 + {
86491 + //We need to change our TxPower for CCX 2.0 AP Control of Client Transmit Power
86492 + ChangeToCellPowerLimit(pAd, AironetCellPowerLimit);
86493 + }
86494 + else //Used the default TX Power Percentage.
86495 + pAd->CommonCfg.TxPowerPercentage = pAd->CommonCfg.TxPowerDefault;
86496 +
86497 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
86498 + Status = MLME_SUCCESS;
86499 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_JOIN_CONF, 2, &Status);
86500 + }
86501 + // not to me BEACON, ignored
86502 + }
86503 + // sanity check fail, ignore this frame
86504 +}
86505 +
86506 +/*
86507 + ==========================================================================
86508 + Description:
86509 + receive BEACON from peer
86510 +
86511 + IRQL = DISPATCH_LEVEL
86512 +
86513 + ==========================================================================
86514 + */
86515 +VOID PeerBeacon(
86516 + IN PRTMP_ADAPTER pAd,
86517 + IN MLME_QUEUE_ELEM *Elem)
86518 +{
86519 + UCHAR Bssid[MAC_ADDR_LEN], Addr2[MAC_ADDR_LEN];
86520 + CHAR Ssid[MAX_LEN_OF_SSID];
86521 + CF_PARM CfParm;
86522 + UCHAR SsidLen, MessageToMe=0, BssType, Channel, NewChannel, index=0;
86523 + UCHAR DtimCount=0, DtimPeriod=0, BcastFlag=0;
86524 + USHORT CapabilityInfo, AtimWin, BeaconPeriod;
86525 + LARGE_INTEGER TimeStamp;
86526 + USHORT TbttNumToNextWakeUp;
86527 + UCHAR Erp;
86528 + UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES], ExtRate[MAX_LEN_OF_SUPPORTED_RATES];
86529 + UCHAR SupRateLen, ExtRateLen;
86530 + UCHAR CkipFlag;
86531 + USHORT LenVIE;
86532 + UCHAR AironetCellPowerLimit;
86533 + EDCA_PARM EdcaParm;
86534 + QBSS_LOAD_PARM QbssLoad;
86535 + QOS_CAPABILITY_PARM QosCapability;
86536 + ULONG RalinkIe;
86537 + // New for WPA security suites
86538 + UCHAR VarIE[MAX_VIE_LEN]; // Total VIE length = MAX_VIE_LEN - -5
86539 + NDIS_802_11_VARIABLE_IEs *pVIE = NULL;
86540 + HT_CAPABILITY_IE HtCapability;
86541 + ADD_HT_INFO_IE AddHtInfo; // AP might use this additional ht info IE
86542 + UCHAR HtCapabilityLen, PreNHtCapabilityLen;
86543 + UCHAR AddHtInfoLen;
86544 + UCHAR NewExtChannelOffset = 0xff;
86545 +
86546 +
86547 +#ifdef RALINK_ATE
86548 + if (ATE_ON(pAd))
86549 + {
86550 + return;
86551 + }
86552 +#endif // RALINK_ATE //
86553 +
86554 + if (!(INFRA_ON(pAd) || ADHOC_ON(pAd)
86555 + ))
86556 + return;
86557 +
86558 + // Init Variable IE structure
86559 + pVIE = (PNDIS_802_11_VARIABLE_IEs) VarIE;
86560 + pVIE->Length = 0;
86561 + RTMPZeroMemory(&HtCapability, sizeof(HtCapability));
86562 + RTMPZeroMemory(&AddHtInfo, sizeof(ADD_HT_INFO_IE));
86563 +
86564 + if (PeerBeaconAndProbeRspSanity(pAd,
86565 + Elem->Msg,
86566 + Elem->MsgLen,
86567 + Elem->Channel,
86568 + Addr2,
86569 + Bssid,
86570 + Ssid,
86571 + &SsidLen,
86572 + &BssType,
86573 + &BeaconPeriod,
86574 + &Channel,
86575 + &NewChannel,
86576 + &TimeStamp,
86577 + &CfParm,
86578 + &AtimWin,
86579 + &CapabilityInfo,
86580 + &Erp,
86581 + &DtimCount,
86582 + &DtimPeriod,
86583 + &BcastFlag,
86584 + &MessageToMe,
86585 + SupRate,
86586 + &SupRateLen,
86587 + ExtRate,
86588 + &ExtRateLen,
86589 + &CkipFlag,
86590 + &AironetCellPowerLimit,
86591 + &EdcaParm,
86592 + &QbssLoad,
86593 + &QosCapability,
86594 + &RalinkIe,
86595 + &HtCapabilityLen,
86596 + &PreNHtCapabilityLen,
86597 + &HtCapability,
86598 + &AddHtInfoLen,
86599 + &AddHtInfo,
86600 + &NewExtChannelOffset,
86601 + &LenVIE,
86602 + pVIE))
86603 + {
86604 + BOOLEAN is_my_bssid, is_my_ssid;
86605 + ULONG Bssidx, Now;
86606 + BSS_ENTRY *pBss;
86607 + CHAR RealRssi = RTMPMaxRssi(pAd, ConvertToRssi(pAd, Elem->Rssi0, RSSI_0), ConvertToRssi(pAd, Elem->Rssi1, RSSI_1), ConvertToRssi(pAd, Elem->Rssi2, RSSI_2));
86608 +
86609 + is_my_bssid = MAC_ADDR_EQUAL(Bssid, pAd->CommonCfg.Bssid)? TRUE : FALSE;
86610 + is_my_ssid = SSID_EQUAL(Ssid, SsidLen, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen)? TRUE:FALSE;
86611 +
86612 +
86613 + // ignore BEACON not for my SSID
86614 + if ((! is_my_ssid) && (! is_my_bssid))
86615 + return;
86616 +
86617 + // It means STA waits disassoc completely from this AP, ignores this beacon.
86618 + if (pAd->Mlme.CntlMachine.CurrState == CNTL_WAIT_DISASSOC)
86619 + return;
86620 +
86621 +#ifdef DOT11_N_SUPPORT
86622 + // Copy Control channel for this BSSID.
86623 + if (AddHtInfoLen != 0)
86624 + Channel = AddHtInfo.ControlChan;
86625 +
86626 + if ((HtCapabilityLen > 0) || (PreNHtCapabilityLen > 0))
86627 + HtCapabilityLen = SIZE_HT_CAP_IE;
86628 +#endif // DOT11_N_SUPPORT //
86629 +
86630 + //
86631 + // Housekeeping "SsidBssTab" table for later-on ROAMing usage.
86632 + //
86633 + Bssidx = BssTableSearch(&pAd->ScanTab, Bssid, Channel);
86634 + if (Bssidx == BSS_NOT_FOUND)
86635 + {
86636 + // discover new AP of this network, create BSS entry
86637 + Bssidx = BssTableSetEntry(pAd, &pAd->ScanTab, Bssid, Ssid, SsidLen, BssType, BeaconPeriod,
86638 + &CfParm, AtimWin, CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen,
86639 + &HtCapability, &AddHtInfo,HtCapabilityLen,AddHtInfoLen,NewExtChannelOffset, Channel,
86640 + RealRssi, TimeStamp, CkipFlag, &EdcaParm, &QosCapability,
86641 + &QbssLoad, LenVIE, pVIE);
86642 + if (Bssidx == BSS_NOT_FOUND) // return if BSS table full
86643 + return;
86644 +
86645 + NdisMoveMemory(pAd->ScanTab.BssEntry[Bssidx].PTSF, &Elem->Msg[24], 4);
86646 + NdisMoveMemory(&pAd->ScanTab.BssEntry[Bssidx].TTSF[0], &Elem->TimeStamp.u.LowPart, 4);
86647 + NdisMoveMemory(&pAd->ScanTab.BssEntry[Bssidx].TTSF[4], &Elem->TimeStamp.u.LowPart, 4);
86648 +
86649 +
86650 +
86651 + }
86652 +
86653 + if ((pAd->CommonCfg.bIEEE80211H == 1) && (NewChannel != 0) && (Channel != NewChannel))
86654 + {
86655 + // Switching to channel 1 can prevent from rescanning the current channel immediately (by auto reconnection).
86656 + // In addition, clear the MLME queue and the scan table to discard the RX packets and previous scanning results.
86657 + AsicSwitchChannel(pAd, 1, FALSE);
86658 + AsicLockChannel(pAd, 1);
86659 + LinkDown(pAd, FALSE);
86660 + MlmeQueueInit(&pAd->Mlme.Queue);
86661 + BssTableInit(&pAd->ScanTab);
86662 + RTMPusecDelay(1000000); // use delay to prevent STA do reassoc
86663 +
86664 + // channel sanity check
86665 + for (index = 0 ; index < pAd->ChannelListNum; index++)
86666 + {
86667 + if (pAd->ChannelList[index].Channel == NewChannel)
86668 + {
86669 + pAd->ScanTab.BssEntry[Bssidx].Channel = NewChannel;
86670 + pAd->CommonCfg.Channel = NewChannel;
86671 + AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE);
86672 + AsicLockChannel(pAd, pAd->CommonCfg.Channel);
86673 + DBGPRINT(RT_DEBUG_TRACE, ("PeerBeacon - STA receive channel switch announcement IE (New Channel =%d)\n", NewChannel));
86674 + break;
86675 + }
86676 + }
86677 +
86678 + if (index >= pAd->ChannelListNum)
86679 + {
86680 + DBGPRINT_ERR(("PeerBeacon(can not find New Channel=%d in ChannelList[%d]\n", pAd->CommonCfg.Channel, pAd->ChannelListNum));
86681 + }
86682 + }
86683 +
86684 + // if the ssid matched & bssid unmatched, we should select the bssid with large value.
86685 + // This might happened when two STA start at the same time
86686 + if ((! is_my_bssid) && ADHOC_ON(pAd))
86687 + {
86688 + INT i;
86689 +
86690 + // Add the safeguard against the mismatch of adhoc wep status
86691 + if (pAd->StaCfg.WepStatus != pAd->ScanTab.BssEntry[Bssidx].WepStatus)
86692 + {
86693 + return;
86694 + }
86695 +
86696 + // collapse into the ADHOC network which has bigger BSSID value.
86697 + for (i = 0; i < 6; i++)
86698 + {
86699 + if (Bssid[i] > pAd->CommonCfg.Bssid[i])
86700 + {
86701 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - merge to the IBSS with bigger BSSID=%02x:%02x:%02x:%02x:%02x:%02x\n",
86702 + Bssid[0], Bssid[1], Bssid[2], Bssid[3], Bssid[4], Bssid[5]));
86703 + AsicDisableSync(pAd);
86704 + COPY_MAC_ADDR(pAd->CommonCfg.Bssid, Bssid);
86705 + AsicSetBssid(pAd, pAd->CommonCfg.Bssid);
86706 + MakeIbssBeacon(pAd); // re-build BEACON frame
86707 + AsicEnableIbssSync(pAd); // copy BEACON frame to on-chip memory
86708 + is_my_bssid = TRUE;
86709 + break;
86710 + }
86711 + else if (Bssid[i] < pAd->CommonCfg.Bssid[i])
86712 + break;
86713 + }
86714 + }
86715 +
86716 +
86717 + NdisGetSystemUpTime(&Now);
86718 + pBss = &pAd->ScanTab.BssEntry[Bssidx];
86719 + pBss->Rssi = RealRssi; // lastest RSSI
86720 + pBss->LastBeaconRxTime = Now; // last RX timestamp
86721 +
86722 + //
86723 + // BEACON from my BSSID - either IBSS or INFRA network
86724 + //
86725 + if (is_my_bssid)
86726 + {
86727 + RXWI_STRUC RxWI;
86728 +
86729 + pAd->StaCfg.DtimCount = DtimCount;
86730 + pAd->StaCfg.DtimPeriod = DtimPeriod;
86731 + pAd->StaCfg.LastBeaconRxTime = Now;
86732 +
86733 +
86734 + RxWI.RSSI0 = Elem->Rssi0;
86735 + RxWI.RSSI1 = Elem->Rssi1;
86736 + RxWI.RSSI2 = Elem->Rssi2;
86737 +
86738 + Update_Rssi_Sample(pAd, &pAd->StaCfg.RssiSample, &RxWI);
86739 + if (AironetCellPowerLimit != 0xFF)
86740 + {
86741 + //
86742 + // We get the Cisco (ccx) "TxPower Limit" required
86743 + // Changed to appropriate TxPower Limit for Ciso Compatible Extensions
86744 + //
86745 + ChangeToCellPowerLimit(pAd, AironetCellPowerLimit);
86746 + }
86747 + else
86748 + {
86749 + //
86750 + // AironetCellPowerLimit equal to 0xFF means the Cisco (ccx) "TxPower Limit" not exist.
86751 + // Used the default TX Power Percentage, that set from UI.
86752 + //
86753 + pAd->CommonCfg.TxPowerPercentage = pAd->CommonCfg.TxPowerDefault;
86754 + }
86755 +
86756 + // at least one 11b peer joined. downgrade the MaxTxRate to 11Mbps
86757 + // after last 11b peer left for several seconds, we'll auto switch back to 11G rate
86758 + // in MlmePeriodicExec()
86759 + if (ADHOC_ON(pAd) && (CAP_IS_IBSS_ON(CapabilityInfo)))
86760 + {
86761 + BOOLEAN bRestart;
86762 + BOOLEAN bnRestart;
86763 +
86764 + bRestart = FALSE;
86765 + bnRestart = FALSE;
86766 +
86767 + do
86768 + {
86769 + if ((SupRateLen+ExtRateLen <= 4) && (pAd->CommonCfg.MaxTxRate > RATE_11))
86770 + {
86771 + if (pAd->StaCfg.AdhocBOnlyJoined == FALSE)
86772 + {
86773 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - 11b peer joined. down-grade to 11b TX rates \n"));
86774 + bRestart = TRUE;
86775 + NdisMoveMemory(pAd->StaActive.SupRate, SupRate, MAX_LEN_OF_SUPPORTED_RATES);
86776 + pAd->StaActive.SupRateLen = SupRateLen;
86777 + NdisMoveMemory(pAd->StaActive.ExtRate, ExtRate, MAX_LEN_OF_SUPPORTED_RATES);
86778 + pAd->StaActive.ExtRateLen = ExtRateLen;
86779 + pAd->StaCfg.AdhocBOnlyJoined = TRUE;
86780 + pAd->StaActive.SupportedPhyInfo.bHtEnable = FALSE;
86781 + AsicSetEdcaParm(pAd, NULL);
86782 + }
86783 +
86784 + // this timestamp is for MlmePeriodicExec() to check if all 11B peers have left
86785 + pAd->StaCfg.Last11bBeaconRxTime = Now;
86786 + break;
86787 + }
86788 +#ifdef DOT11_N_SUPPORT
86789 + // Update Ht Phy.
86790 + if ((pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED))
86791 + {
86792 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) &&
86793 + !pAd->StaCfg.AdhocBGJoined &&
86794 + !pAd->StaCfg.AdhocBOnlyJoined)
86795 + AdhocTurnOnQos(pAd);
86796 +
86797 + // Handle rate switch issue when Adhoc mode
86798 + if ((SupRateLen+ExtRateLen >= 8) && (HtCapability.MCSSet[0] == 0) && (HtCapability.MCSSet[1] == 0))
86799 + {
86800 + if (pAd->StaCfg.AdhocBGJoined == FALSE)
86801 + {
86802 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - 11g peer joined. down-grade to 11g TX rates \n"));
86803 + bRestart = TRUE;
86804 + NdisMoveMemory(pAd->StaActive.SupRate, SupRate, MAX_LEN_OF_SUPPORTED_RATES);
86805 + pAd->StaActive.SupRateLen = SupRateLen;
86806 + NdisMoveMemory(pAd->StaActive.ExtRate, ExtRate, MAX_LEN_OF_SUPPORTED_RATES);
86807 + pAd->StaActive.ExtRateLen = ExtRateLen;
86808 + pAd->StaCfg.AdhocBGJoined = TRUE;
86809 + pAd->StaActive.SupportedPhyInfo.bHtEnable = FALSE;
86810 + AsicSetEdcaParm(pAd, NULL);
86811 + }
86812 +
86813 + // this timestamp is for MlmePeriodicExec() to check if all 11g peers have left
86814 + pAd->StaCfg.Last11gBeaconRxTime = Now;
86815 + break;
86816 + }
86817 + else if (!pAd->StaCfg.AdhocBGJoined &&
86818 + !pAd->StaCfg.AdhocBOnlyJoined &&
86819 + (pAd->CommonCfg.RegTransmitSetting.field.BW == BW_40) &&
86820 + (HtCapability.HtCapInfo.ChannelWidth == BW_20))
86821 + {
86822 + if (pAd->StaCfg.Adhoc20NJoined == FALSE)
86823 + {
86824 + UCHAR ByteValue = 0;
86825 +
86826 + pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel;
86827 +
86828 + pAd->StaCfg.Adhoc20NJoined = TRUE;
86829 + NdisMoveMemory(&pAd->MlmeAux.HtCapability, &HtCapability, SIZE_HT_CAP_IE);
86830 + if (AddHtInfoLen != 0)
86831 + NdisMoveMemory(&pAd->MlmeAux.AddHtInfo, &AddHtInfo, AddHtInfoLen);
86832 + NdisMoveMemory(pAd->StaActive.SupportedPhyInfo.MCSSet, HtCapability.MCSSet, 16);
86833 +
86834 + RTMPCheckHt(pAd, Elem->Wcid, &pAd->MlmeAux.HtCapability, &pAd->MlmeAux.AddHtInfo);
86835 + COPY_HTSETTINGS_FROM_MLME_AUX_TO_ACTIVE_CFG(pAd);
86836 + pAd->StaActive.SupportedPhyInfo.bHtEnable = TRUE;
86837 + bRestart = TRUE;
86838 + bnRestart = TRUE;
86839 + }
86840 + // this timestamp is for MlmePeriodicExec() to check if all 20MHz N peers have left
86841 + pAd->StaCfg.Last20NBeaconRxTime = Now;
86842 + }
86843 +
86844 + }
86845 + else
86846 +#endif // DOT11_N_SUPPORT //
86847 + {
86848 + RTMPZeroMemory(&pAd->MlmeAux.HtCapability, SIZE_HT_CAP_IE);
86849 + RTMPZeroMemory(&pAd->MlmeAux.AddHtInfo, SIZE_ADD_HT_INFO_IE);
86850 + }
86851 + }while (FALSE);
86852 +
86853 + // If peer Adhoc is legacy mode, I don't need to call MlmeUpdateHtTxRates no matter I support HT or not
86854 + if ((bRestart == TRUE) && (bnRestart == FALSE))
86855 + {
86856 + MlmeUpdateTxRates(pAd, FALSE, 0);
86857 + MakeIbssBeacon(pAd); // re-build BEACON frame
86858 + AsicEnableIbssSync(pAd); // copy to on-chip memory
86859 + }
86860 +#ifdef DOT11_N_SUPPORT
86861 + else if ((bRestart == TRUE) && (bnRestart == TRUE))
86862 + {
86863 + MlmeUpdateTxRates(pAd, FALSE, BSS0);
86864 + MlmeUpdateHtTxRates(pAd, BSS0);
86865 + MakeIbssBeacon(pAd); // re-build BEACON frame
86866 + AsicEnableIbssSync(pAd); // copy to on-chip memory
86867 + }
86868 +#endif // DOT11_N_SUPPORT //
86869 +
86870 + // At least another peer in this IBSS, declare MediaState as CONNECTED
86871 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED))
86872 + {
86873 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED);
86874 +
86875 + pAd->IndicateMediaState = NdisMediaStateConnected;
86876 + RTMP_IndicateMediaState(pAd);
86877 + pAd->ExtraInfo = GENERAL_LINK_UP;
86878 + AsicSetBssid(pAd, pAd->CommonCfg.Bssid);
86879 +
86880 + // 2003/03/12 - john
86881 + // Make sure this entry in "ScanTab" table, thus complies to Microsoft's policy that
86882 + // "site survey" result should always include the current connected network.
86883 + //
86884 + Bssidx = BssTableSearch(&pAd->ScanTab, Bssid, Channel);
86885 + if (Bssidx == BSS_NOT_FOUND)
86886 + {
86887 + Bssidx = BssTableSetEntry(pAd, &pAd->ScanTab, Bssid, Ssid, SsidLen, BssType, BeaconPeriod,
86888 + &CfParm, AtimWin, CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen, &HtCapability,
86889 + &AddHtInfo, HtCapabilityLen, AddHtInfoLen, NewExtChannelOffset, Channel, RealRssi, TimeStamp, 0,
86890 + &EdcaParm, &QosCapability, &QbssLoad, LenVIE, pVIE);
86891 + }
86892 + DBGPRINT(RT_DEBUG_TRACE, ("ADHOC fOP_STATUS_MEDIA_STATE_CONNECTED.\n"));
86893 + }
86894 +
86895 + // Ad-hoc mode is using MAC address as BA session. So we need to continuously find newly joined adhoc station by receiving beacon.
86896 + // To prevent always check this, we use wcid == RESERVED_WCID to recognize it as newly joined adhoc station.
86897 + if (ADHOC_ON(pAd) && (Elem->Wcid == RESERVED_WCID))
86898 + {
86899 + UCHAR idx;
86900 + MAC_TABLE_ENTRY *pEntry;
86901 +
86902 + // look up the existing table
86903 + pEntry = MacTableLookup(pAd, Addr2);
86904 + if (pEntry == NULL)
86905 + {
86906 + // Another adhoc joining, add to our MAC table.
86907 + pEntry = MacTableInsertEntry(pAd, Addr2, BSS0, FALSE);
86908 + if (pEntry)
86909 + {
86910 + pEntry->Sst = SST_ASSOC;
86911 + idx = pAd->StaCfg.DefaultKeyId;
86912 + // After InsertEntry, Write to ASIC on-chip table.
86913 + RT28XX_STA_SECURITY_INFO_ADD(pAd, BSS0, idx, pEntry);
86914 + DBGPRINT(RT_DEBUG_TRACE, ("ADHOC %x:%x:%x:%x:%x:%x join in.Entry=%d\n", Addr2[0],Addr2[1],Addr2[2],Addr2[3],Addr2[4],Addr2[5], pEntry->Aid));
86915 +
86916 + pEntry->HTPhyMode.word = pAd->StaCfg.HTPhyMode.word;
86917 + if (HtCapabilityLen <= 0)
86918 + {
86919 + pEntry->HTPhyMode.field.STBC = 0;
86920 + pEntry->HTPhyMode.field.BW = 0;
86921 + pEntry->HTPhyMode.field.ShortGI = 0;
86922 + if ((SupRateLen+ExtRateLen <= 4) && (pAd->CommonCfg.Channel <= 14))
86923 + {
86924 + pEntry->HTPhyMode.field.MODE = MODE_CCK;
86925 + }
86926 + else
86927 + {
86928 + pEntry->HTPhyMode.field.MODE = MODE_OFDM;
86929 + }
86930 + MlmeUpdateTxRates(pAd, FALSE, 0);
86931 + }
86932 +#ifdef DOT11_N_SUPPORT
86933 + else
86934 + {
86935 + MlmeUpdateTxRates(pAd, FALSE, 0);
86936 + MlmeUpdateHtTxRates(pAd, BSS0);
86937 + }
86938 +#endif // DOT11_N_SUPPORT //
86939 +
86940 +#ifdef WPA_SUPPLICANT_SUPPORT
86941 +#ifndef NATIVE_WPA_SUPPLICANT_SUPPORT
86942 + if (pAd->StaCfg.WpaSupplicantUP)
86943 + {
86944 + union iwreq_data wrqu;
86945 +
86946 + SendAssocIEsToWpaSupplicant(pAd);
86947 + memset(&wrqu, 0, sizeof(wrqu));
86948 + wrqu.data.flags = RT_ASSOC_EVENT_FLAG;
86949 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, NULL);
86950 + }
86951 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
86952 +#endif // WPA_SUPPLICANT_SUPPORT //
86953 +
86954 +#ifdef NATIVE_WPA_SUPPLICANT_SUPPORT
86955 + {
86956 + union iwreq_data wrqu;
86957 + wext_notify_event_assoc(pAd);
86958 +
86959 + memset(wrqu.ap_addr.sa_data, 0, MAC_ADDR_LEN);
86960 + memcpy(wrqu.ap_addr.sa_data, pAd->MlmeAux.Bssid, MAC_ADDR_LEN);
86961 + wireless_send_event(pAd->net_dev, SIOCGIWAP, &wrqu, NULL);
86962 +
86963 + }
86964 +#endif // NATIVE_WPA_SUPPLICANT_SUPPORT //
86965 + }
86966 + }
86967 + }
86968 + }
86969 +
86970 + if (INFRA_ON(pAd))
86971 + {
86972 + BOOLEAN bUseShortSlot, bUseBGProtection;
86973 +
86974 + // decide to use/change to -
86975 + // 1. long slot (20 us) or short slot (9 us) time
86976 + // 2. turn on/off RTS/CTS and/or CTS-to-self protection
86977 + // 3. short preamble
86978 +
86979 + //bUseShortSlot = pAd->CommonCfg.bUseShortSlotTime && CAP_IS_SHORT_SLOT(CapabilityInfo);
86980 + bUseShortSlot = CAP_IS_SHORT_SLOT(CapabilityInfo);
86981 + if (bUseShortSlot != OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_SHORT_SLOT_INUSED))
86982 + AsicSetSlotTime(pAd, bUseShortSlot);
86983 +
86984 + bUseBGProtection = (pAd->CommonCfg.UseBGProtection == 1) || // always use
86985 + ((pAd->CommonCfg.UseBGProtection == 0) && ERP_IS_USE_PROTECTION(Erp));
86986 +
86987 + if (pAd->CommonCfg.Channel > 14) // always no BG protection in A-band. falsely happened when switching A/G band to a dual-band AP
86988 + bUseBGProtection = FALSE;
86989 +
86990 + if (bUseBGProtection != OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED))
86991 + {
86992 + if (bUseBGProtection)
86993 + {
86994 + OPSTATUS_SET_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED);
86995 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, (OFDMSETPROTECT|CCKSETPROTECT|ALLN_SETPROTECT),FALSE,(pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent == 1));
86996 + }
86997 + else
86998 + {
86999 + OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED);
87000 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, (OFDMSETPROTECT|CCKSETPROTECT|ALLN_SETPROTECT),TRUE,(pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent == 1));
87001 + }
87002 +
87003 + DBGPRINT(RT_DEBUG_WARN, ("SYNC - AP changed B/G protection to %d\n", bUseBGProtection));
87004 + }
87005 +
87006 +#ifdef DOT11_N_SUPPORT
87007 + // check Ht protection mode. and adhere to the Non-GF device indication by AP.
87008 + if ((AddHtInfoLen != 0) &&
87009 + ((AddHtInfo.AddHtInfo2.OperaionMode != pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode) ||
87010 + (AddHtInfo.AddHtInfo2.NonGfPresent != pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent)))
87011 + {
87012 + pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent = AddHtInfo.AddHtInfo2.NonGfPresent;
87013 + pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode = AddHtInfo.AddHtInfo2.OperaionMode;
87014 + if (pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent == 1)
87015 + {
87016 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, FALSE, TRUE);
87017 + }
87018 + else
87019 + AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, FALSE, FALSE);
87020 +
87021 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - AP changed N OperaionMode to %d\n", pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode));
87022 + }
87023 +#endif // DOT11_N_SUPPORT //
87024 +
87025 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED) &&
87026 + ERP_IS_USE_BARKER_PREAMBLE(Erp))
87027 + {
87028 + MlmeSetTxPreamble(pAd, Rt802_11PreambleLong);
87029 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - AP forced to use LONG preamble\n"));
87030 + }
87031 +
87032 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED) &&
87033 + (EdcaParm.bValid == TRUE) &&
87034 + (EdcaParm.EdcaUpdateCount != pAd->CommonCfg.APEdcaParm.EdcaUpdateCount))
87035 + {
87036 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - AP change EDCA parameters(from %d to %d)\n",
87037 + pAd->CommonCfg.APEdcaParm.EdcaUpdateCount,
87038 + EdcaParm.EdcaUpdateCount));
87039 + AsicSetEdcaParm(pAd, &EdcaParm);
87040 + }
87041 +
87042 + // copy QOS related information
87043 + NdisMoveMemory(&pAd->CommonCfg.APQbssLoad, &QbssLoad, sizeof(QBSS_LOAD_PARM));
87044 + NdisMoveMemory(&pAd->CommonCfg.APQosCapability, &QosCapability, sizeof(QOS_CAPABILITY_PARM));
87045 + }
87046 +
87047 + // only INFRASTRUCTURE mode support power-saving feature
87048 + if ((INFRA_ON(pAd) && (pAd->StaCfg.Psm == PWR_SAVE)) || (pAd->CommonCfg.bAPSDForcePowerSave))
87049 + {
87050 + UCHAR FreeNumber;
87051 + // 1. AP has backlogged unicast-to-me frame, stay AWAKE, send PSPOLL
87052 + // 2. AP has backlogged broadcast/multicast frame and we want those frames, stay AWAKE
87053 + // 3. we have outgoing frames in TxRing or MgmtRing, better stay AWAKE
87054 + // 4. Psm change to PWR_SAVE, but AP not been informed yet, we better stay AWAKE
87055 + // 5. otherwise, put PHY back to sleep to save battery.
87056 + if (MessageToMe)
87057 + {
87058 +#ifdef RT2860
87059 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
87060 + {
87061 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, pAd->StaCfg.BBPR3);
87062 + // Turn clk to 80Mhz.
87063 + }
87064 +#endif // RT2860 //
87065 + if (pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable &&
87066 + pAd->CommonCfg.bAPSDAC_BE && pAd->CommonCfg.bAPSDAC_BK && pAd->CommonCfg.bAPSDAC_VI && pAd->CommonCfg.bAPSDAC_VO)
87067 + {
87068 + pAd->CommonCfg.bNeedSendTriggerFrame = TRUE;
87069 + }
87070 + else
87071 + RT28XX_PS_POLL_ENQUEUE(pAd);
87072 + }
87073 + else if (BcastFlag && (DtimCount == 0) && OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM))
87074 + {
87075 +#ifdef RT2860
87076 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
87077 + {
87078 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, pAd->StaCfg.BBPR3);
87079 + }
87080 +#endif // RT2860 //
87081 + }
87082 + else if ((pAd->TxSwQueue[QID_AC_BK].Number != 0) ||
87083 + (pAd->TxSwQueue[QID_AC_BE].Number != 0) ||
87084 + (pAd->TxSwQueue[QID_AC_VI].Number != 0) ||
87085 + (pAd->TxSwQueue[QID_AC_VO].Number != 0) ||
87086 + (RTMPFreeTXDRequest(pAd, QID_AC_BK, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) ||
87087 + (RTMPFreeTXDRequest(pAd, QID_AC_BE, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) ||
87088 + (RTMPFreeTXDRequest(pAd, QID_AC_VI, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) ||
87089 + (RTMPFreeTXDRequest(pAd, QID_AC_VO, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) ||
87090 + (RTMPFreeTXDRequest(pAd, QID_MGMT, MGMT_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS))
87091 + {
87092 + // TODO: consider scheduled HCCA. might not be proper to use traditional DTIM-based power-saving scheme
87093 + // can we cheat here (i.e. just check MGMT & AC_BE) for better performance?
87094 +#ifdef RT2860
87095 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_ADVANCE_POWER_SAVE_PCIE_DEVICE))
87096 + {
87097 + RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, pAd->StaCfg.BBPR3);
87098 + }
87099 +#endif // RT2860 //
87100 + }
87101 + else
87102 + {
87103 + USHORT NextDtim = DtimCount;
87104 +
87105 + if (NextDtim == 0)
87106 + NextDtim = DtimPeriod;
87107 +
87108 + TbttNumToNextWakeUp = pAd->StaCfg.DefaultListenCount;
87109 + if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM) && (TbttNumToNextWakeUp > NextDtim))
87110 + TbttNumToNextWakeUp = NextDtim;
87111 +
87112 + if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE))
87113 + {
87114 + AsicSleepThenAutoWakeup(pAd, TbttNumToNextWakeUp);
87115 + }
87116 + }
87117 + }
87118 + }
87119 + // not my BSSID, ignore it
87120 + }
87121 + // sanity check fail, ignore this frame
87122 +}
87123 +
87124 +/*
87125 + ==========================================================================
87126 + Description:
87127 + Receive PROBE REQ from remote peer when operating in IBSS mode
87128 + ==========================================================================
87129 + */
87130 +VOID PeerProbeReqAction(
87131 + IN PRTMP_ADAPTER pAd,
87132 + IN MLME_QUEUE_ELEM *Elem)
87133 +{
87134 + UCHAR Addr2[MAC_ADDR_LEN];
87135 + CHAR Ssid[MAX_LEN_OF_SSID];
87136 + UCHAR SsidLen;
87137 +#ifdef DOT11_N_SUPPORT
87138 + UCHAR HtLen, AddHtLen, NewExtLen;
87139 +#endif // DOT11_N_SUPPORT //
87140 + HEADER_802_11 ProbeRspHdr;
87141 + NDIS_STATUS NStatus;
87142 + PUCHAR pOutBuffer = NULL;
87143 + ULONG FrameLen = 0;
87144 + LARGE_INTEGER FakeTimestamp;
87145 + UCHAR DsLen = 1, IbssLen = 2;
87146 + UCHAR LocalErpIe[3] = {IE_ERP, 1, 0};
87147 + BOOLEAN Privacy;
87148 + USHORT CapabilityInfo;
87149 + UCHAR RSNIe = IE_WPA;
87150 +
87151 + if (! ADHOC_ON(pAd))
87152 + return;
87153 +
87154 + if (PeerProbeReqSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, Ssid, &SsidLen))
87155 + {
87156 + if ((SsidLen == 0) || SSID_EQUAL(Ssid, SsidLen, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen))
87157 + {
87158 + // allocate and send out ProbeRsp frame
87159 + NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
87160 + if (NStatus != NDIS_STATUS_SUCCESS)
87161 + return;
87162 +
87163 + //pAd->StaCfg.AtimWin = 0; // ??????
87164 +
87165 + Privacy = (pAd->StaCfg.WepStatus == Ndis802_11Encryption1Enabled) ||
87166 + (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) ||
87167 + (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled);
87168 + CapabilityInfo = CAP_GENERATE(0, 1, Privacy, (pAd->CommonCfg.TxPreamble == Rt802_11PreambleShort), 0, 0);
87169 +
87170 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
87171 + sizeof(HEADER_802_11), &ProbeRspHdr,
87172 + TIMESTAMP_LEN, &FakeTimestamp,
87173 + 2, &pAd->CommonCfg.BeaconPeriod,
87174 + 2, &CapabilityInfo,
87175 + 1, &SsidIe,
87176 + 1, &pAd->CommonCfg.SsidLen,
87177 + pAd->CommonCfg.SsidLen, pAd->CommonCfg.Ssid,
87178 + 1, &SupRateIe,
87179 + 1, &pAd->StaActive.SupRateLen,
87180 + pAd->StaActive.SupRateLen, pAd->StaActive.SupRate,
87181 + 1, &DsIe,
87182 + 1, &DsLen,
87183 + 1, &pAd->CommonCfg.Channel,
87184 + 1, &IbssIe,
87185 + 1, &IbssLen,
87186 + 2, &pAd->StaActive.AtimWin,
87187 + END_OF_ARGS);
87188 +
87189 + if (pAd->StaActive.ExtRateLen)
87190 + {
87191 + ULONG tmp;
87192 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
87193 + 3, LocalErpIe,
87194 + 1, &ExtRateIe,
87195 + 1, &pAd->StaActive.ExtRateLen,
87196 + pAd->StaActive.ExtRateLen, &pAd->StaActive.ExtRate,
87197 + END_OF_ARGS);
87198 + FrameLen += tmp;
87199 + }
87200 +
87201 + // If adhoc secruity is set for WPA-None, append the cipher suite IE
87202 + if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone)
87203 + {
87204 + ULONG tmp;
87205 + MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp,
87206 + 1, &RSNIe,
87207 + 1, &pAd->StaCfg.RSNIE_Len,
87208 + pAd->StaCfg.RSNIE_Len, pAd->StaCfg.RSN_IE,
87209 + END_OF_ARGS);
87210 + FrameLen += tmp;
87211 + }
87212 +#ifdef DOT11_N_SUPPORT
87213 + if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED)
87214 + {
87215 + ULONG TmpLen;
87216 + UCHAR BROADCOM[4] = {0x0, 0x90, 0x4c, 0x33};
87217 + HtLen = sizeof(pAd->CommonCfg.HtCapability);
87218 + AddHtLen = sizeof(pAd->CommonCfg.AddHTInfo);
87219 + NewExtLen = 1;
87220 + //New extension channel offset IE is included in Beacon, Probe Rsp or channel Switch Announcement Frame
87221 + if (pAd->bBroadComHT == TRUE)
87222 + {
87223 + MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen,
87224 + 1, &WpaIe,
87225 + 4, &BROADCOM[0],
87226 + pAd->MlmeAux.HtCapabilityLen, &pAd->MlmeAux.HtCapability,
87227 + END_OF_ARGS);
87228 + }
87229 + else
87230 + {
87231 + MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen,
87232 + 1, &HtCapIe,
87233 + 1, &HtLen,
87234 + sizeof(HT_CAPABILITY_IE), &pAd->CommonCfg.HtCapability,
87235 + 1, &AddHtInfoIe,
87236 + 1, &AddHtLen,
87237 + sizeof(ADD_HT_INFO_IE), &pAd->CommonCfg.AddHTInfo,
87238 + 1, &NewExtChanIe,
87239 + 1, &NewExtLen,
87240 + sizeof(NEW_EXT_CHAN_IE), &pAd->CommonCfg.NewExtChanOffset,
87241 + END_OF_ARGS);
87242 + }
87243 + FrameLen += TmpLen;
87244 + }
87245 +#endif // DOT11_N_SUPPORT //
87246 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
87247 + MlmeFreeMemory(pAd, pOutBuffer);
87248 + }
87249 + }
87250 +}
87251 +
87252 +VOID BeaconTimeoutAtJoinAction(
87253 + IN PRTMP_ADAPTER pAd,
87254 + IN MLME_QUEUE_ELEM *Elem)
87255 +{
87256 + USHORT Status;
87257 + DBGPRINT(RT_DEBUG_TRACE, ("SYNC - BeaconTimeoutAtJoinAction\n"));
87258 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
87259 + Status = MLME_REJ_TIMEOUT;
87260 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_JOIN_CONF, 2, &Status);
87261 +}
87262 +
87263 +/*
87264 + ==========================================================================
87265 + Description:
87266 + Scan timeout procedure. basically add channel index by 1 and rescan
87267 + ==========================================================================
87268 + */
87269 +VOID ScanTimeoutAction(
87270 + IN PRTMP_ADAPTER pAd,
87271 + IN MLME_QUEUE_ELEM *Elem)
87272 +{
87273 + pAd->MlmeAux.Channel = NextChannel(pAd, pAd->MlmeAux.Channel);
87274 +
87275 + // Only one channel scanned for CISCO beacon request
87276 + if ((pAd->MlmeAux.ScanType == SCAN_CISCO_ACTIVE) ||
87277 + (pAd->MlmeAux.ScanType == SCAN_CISCO_PASSIVE) ||
87278 + (pAd->MlmeAux.ScanType == SCAN_CISCO_NOISE) ||
87279 + (pAd->MlmeAux.ScanType == SCAN_CISCO_CHANNEL_LOAD))
87280 + pAd->MlmeAux.Channel = 0;
87281 +
87282 + // this routine will stop if pAd->MlmeAux.Channel == 0
87283 + ScanNextChannel(pAd);
87284 +}
87285 +
87286 +/*
87287 + ==========================================================================
87288 + Description:
87289 + ==========================================================================
87290 + */
87291 +VOID InvalidStateWhenScan(
87292 + IN PRTMP_ADAPTER pAd,
87293 + IN MLME_QUEUE_ELEM *Elem)
87294 +{
87295 + USHORT Status;
87296 + DBGPRINT(RT_DEBUG_TRACE, ("AYNC - InvalidStateWhenScan(state=%ld). Reset SYNC machine\n", pAd->Mlme.SyncMachine.CurrState));
87297 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
87298 + Status = MLME_STATE_MACHINE_REJECT;
87299 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_SCAN_CONF, 2, &Status);
87300 +}
87301 +
87302 +/*
87303 + ==========================================================================
87304 + Description:
87305 + ==========================================================================
87306 + */
87307 +VOID InvalidStateWhenJoin(
87308 + IN PRTMP_ADAPTER pAd,
87309 + IN MLME_QUEUE_ELEM *Elem)
87310 +{
87311 + USHORT Status;
87312 + DBGPRINT(RT_DEBUG_TRACE, ("InvalidStateWhenJoin(state=%ld). Reset SYNC machine\n", pAd->Mlme.SyncMachine.CurrState));
87313 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
87314 + Status = MLME_STATE_MACHINE_REJECT;
87315 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_JOIN_CONF, 2, &Status);
87316 +}
87317 +
87318 +/*
87319 + ==========================================================================
87320 + Description:
87321 + ==========================================================================
87322 + */
87323 +VOID InvalidStateWhenStart(
87324 + IN PRTMP_ADAPTER pAd,
87325 + IN MLME_QUEUE_ELEM *Elem)
87326 +{
87327 + USHORT Status;
87328 + DBGPRINT(RT_DEBUG_TRACE, ("InvalidStateWhenStart(state=%ld). Reset SYNC machine\n", pAd->Mlme.SyncMachine.CurrState));
87329 + pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE;
87330 + Status = MLME_STATE_MACHINE_REJECT;
87331 + MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_START_CONF, 2, &Status);
87332 +}
87333 +
87334 +/*
87335 + ==========================================================================
87336 + Description:
87337 +
87338 + IRQL = DISPATCH_LEVEL
87339 +
87340 + ==========================================================================
87341 + */
87342 +VOID EnqueuePsPoll(
87343 + IN PRTMP_ADAPTER pAd)
87344 +{
87345 +#ifdef RALINK_ATE
87346 + if (ATE_ON(pAd))
87347 + {
87348 + return;
87349 + }
87350 +#endif // RALINK_ATE //
87351 +
87352 +
87353 + if (pAd->StaCfg.WindowsPowerMode == Ndis802_11PowerModeLegacy_PSP)
87354 + pAd->PsPollFrame.FC.PwrMgmt = PWR_SAVE;
87355 + MiniportMMRequest(pAd, 0, (PUCHAR)&pAd->PsPollFrame, sizeof(PSPOLL_FRAME));
87356 +}
87357 +
87358 +
87359 +/*
87360 + ==========================================================================
87361 + Description:
87362 + ==========================================================================
87363 + */
87364 +VOID EnqueueProbeRequest(
87365 + IN PRTMP_ADAPTER pAd)
87366 +{
87367 + NDIS_STATUS NState;
87368 + PUCHAR pOutBuffer;
87369 + ULONG FrameLen = 0;
87370 + HEADER_802_11 Hdr80211;
87371 +
87372 + DBGPRINT(RT_DEBUG_TRACE, ("force out a ProbeRequest ...\n"));
87373 +
87374 + NState = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory
87375 + if (NState == NDIS_STATUS_SUCCESS)
87376 + {
87377 + MgtMacHeaderInit(pAd, &Hdr80211, SUBTYPE_PROBE_REQ, 0, BROADCAST_ADDR, BROADCAST_ADDR);
87378 +
87379 + // this ProbeRequest explicitly specify SSID to reduce unwanted ProbeResponse
87380 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
87381 + sizeof(HEADER_802_11), &Hdr80211,
87382 + 1, &SsidIe,
87383 + 1, &pAd->CommonCfg.SsidLen,
87384 + pAd->CommonCfg.SsidLen, pAd->CommonCfg.Ssid,
87385 + 1, &SupRateIe,
87386 + 1, &pAd->StaActive.SupRateLen,
87387 + pAd->StaActive.SupRateLen, pAd->StaActive.SupRate,
87388 + END_OF_ARGS);
87389 + MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen);
87390 + MlmeFreeMemory(pAd, pOutBuffer);
87391 + }
87392 +
87393 +}
87394 +
87395 +#ifdef DOT11_N_SUPPORT
87396 +#ifdef DOT11N_DRAFT3
87397 +VOID BuildEffectedChannelList(
87398 + IN PRTMP_ADAPTER pAd)
87399 +{
87400 + UCHAR EChannel[11];
87401 + UCHAR i, j, k;
87402 + UCHAR UpperChannel = 0, LowerChannel = 0;
87403 +
87404 + RTMPZeroMemory(EChannel, 11);
87405 + i = 0;
87406 + // Find upper channel and lower channel.
87407 + if (pAd->CommonCfg.CentralChannel < pAd->CommonCfg.Channel)
87408 + {
87409 + UpperChannel = pAd->CommonCfg.Channel;
87410 + LowerChannel = pAd->CommonCfg.CentralChannel;
87411 + }
87412 + else if (pAd->CommonCfg.CentralChannel > pAd->CommonCfg.Channel)
87413 + {
87414 + UpperChannel = pAd->CommonCfg.CentralChannel;
87415 + LowerChannel = pAd->CommonCfg.Channel;
87416 + }
87417 + else
87418 + {
87419 + return;
87420 + }
87421 +
87422 + // Record channels that is below lower channel..
87423 + if (LowerChannel > 1)
87424 + {
87425 + EChannel[0] = LowerChannel - 1;
87426 + i = 1;
87427 + if (LowerChannel > 2)
87428 + {
87429 + EChannel[1] = LowerChannel - 2;
87430 + i = 2;
87431 + if (LowerChannel > 3)
87432 + {
87433 + EChannel[2] = LowerChannel - 3;
87434 + i = 3;
87435 + }
87436 + }
87437 + }
87438 + // Record channels that is between lower channel and upper channel.
87439 + for (k = LowerChannel;k < UpperChannel;k++)
87440 + {
87441 + EChannel[i] = k;
87442 + i++;
87443 + }
87444 + // Record channels that is above upper channel..
87445 + if (LowerChannel < 11)
87446 + {
87447 + EChannel[i] = UpperChannel + 1;
87448 + i++;
87449 + if (LowerChannel < 10)
87450 + {
87451 + EChannel[i] = LowerChannel + 2;
87452 + i++;
87453 + if (LowerChannel < 9)
87454 + {
87455 + EChannel[i] = LowerChannel + 3;
87456 + i++;
87457 + }
87458 + }
87459 + }
87460 + //
87461 + for (j = 0;j < i;j++)
87462 + {
87463 + for (k = 0;k < pAd->ChannelListNum;k++)
87464 + {
87465 + if (pAd->ChannelList[k].Channel == EChannel[j])
87466 + {
87467 + pAd->ChannelList[k].bEffectedChannel = TRUE;
87468 + DBGPRINT(RT_DEBUG_TRACE,(" EffectedChannel( =%d)\n", EChannel[j]));
87469 + break;
87470 + }
87471 + }
87472 + }
87473 +}
87474 +#endif // DOT11N_DRAFT3 //
87475 +#endif // DOT11_N_SUPPORT //
87476 +
87477 +BOOLEAN ScanRunning(
87478 + IN PRTMP_ADAPTER pAd)
87479 +{
87480 + return (pAd->Mlme.SyncMachine.CurrState == SCAN_LISTEN) ? TRUE : FALSE;
87481 +}
87482 +
87483 --- /dev/null
87484 +++ b/drivers/staging/rt2860/sta/wpa.c
87485 @@ -0,0 +1,2086 @@
87486 +/*
87487 + *************************************************************************
87488 + * Ralink Tech Inc.
87489 + * 5F., No.36, Taiyuan St., Jhubei City,
87490 + * Hsinchu County 302,
87491 + * Taiwan, R.O.C.
87492 + *
87493 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
87494 + *
87495 + * This program is free software; you can redistribute it and/or modify *
87496 + * it under the terms of the GNU General Public License as published by *
87497 + * the Free Software Foundation; either version 2 of the License, or *
87498 + * (at your option) any later version. *
87499 + * *
87500 + * This program is distributed in the hope that it will be useful, *
87501 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
87502 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
87503 + * GNU General Public License for more details. *
87504 + * *
87505 + * You should have received a copy of the GNU General Public License *
87506 + * along with this program; if not, write to the *
87507 + * Free Software Foundation, Inc., *
87508 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
87509 + * *
87510 + *************************************************************************
87511 +
87512 + Module Name:
87513 + wpa.c
87514 +
87515 + Abstract:
87516 +
87517 + Revision History:
87518 + Who When What
87519 + -------- ---------- ----------------------------------------------
87520 + Jan Lee 03-07-22 Initial
87521 + Paul Lin 03-11-28 Modify for supplicant
87522 +*/
87523 +#include "../rt_config.h"
87524 +
87525 +#define WPARSNIE 0xdd
87526 +#define WPA2RSNIE 0x30
87527 +
87528 +//extern UCHAR BIT8[];
87529 +UCHAR CipherWpaPskTkip[] = {
87530 + 0xDD, 0x16, // RSN IE
87531 + 0x00, 0x50, 0xf2, 0x01, // oui
87532 + 0x01, 0x00, // Version
87533 + 0x00, 0x50, 0xf2, 0x02, // Multicast
87534 + 0x01, 0x00, // Number of unicast
87535 + 0x00, 0x50, 0xf2, 0x02, // unicast
87536 + 0x01, 0x00, // number of authentication method
87537 + 0x00, 0x50, 0xf2, 0x02 // authentication
87538 + };
87539 +UCHAR CipherWpaPskTkipLen = (sizeof(CipherWpaPskTkip) / sizeof(UCHAR));
87540 +
87541 +UCHAR CipherWpaPskAes[] = {
87542 + 0xDD, 0x16, // RSN IE
87543 + 0x00, 0x50, 0xf2, 0x01, // oui
87544 + 0x01, 0x00, // Version
87545 + 0x00, 0x50, 0xf2, 0x04, // Multicast
87546 + 0x01, 0x00, // Number of unicast
87547 + 0x00, 0x50, 0xf2, 0x04, // unicast
87548 + 0x01, 0x00, // number of authentication method
87549 + 0x00, 0x50, 0xf2, 0x02 // authentication
87550 + };
87551 +UCHAR CipherWpaPskAesLen = (sizeof(CipherWpaPskAes) / sizeof(UCHAR));
87552 +
87553 +UCHAR CipherSuiteCiscoCCKM[] = {
87554 + 0xDD, 0x16, // RSN IE
87555 + 0x00, 0x50, 0xf2, 0x01, // oui
87556 + 0x01, 0x00, // Version
87557 + 0x00, 0x40, 0x96, 0x01, // Multicast
87558 + 0x01, 0x00, // Number of uicast
87559 + 0x00, 0x40, 0x96, 0x01, // unicast
87560 + 0x01, 0x00, // number of authentication method
87561 + 0x00, 0x40, 0x96, 0x00 // Authentication
87562 + };
87563 +UCHAR CipherSuiteCiscoCCKMLen = (sizeof(CipherSuiteCiscoCCKM) / sizeof(UCHAR));
87564 +
87565 +UCHAR CipherSuiteCiscoCCKM24[] = {
87566 + 0xDD, 0x18, // RSN IE
87567 + 0x00, 0x50, 0xf2, 0x01, // oui
87568 + 0x01, 0x00, // Version
87569 + 0x00, 0x40, 0x96, 0x01, // Multicast
87570 + 0x01, 0x00, // Number of uicast
87571 + 0x00, 0x40, 0x96, 0x01, // unicast
87572 + 0x01, 0x00, // number of authentication method
87573 + 0x00, 0x40, 0x96, 0x00,
87574 + 0x28, 0x00// Authentication
87575 + };
87576 +
87577 +UCHAR CipherSuiteCiscoCCKM24Len = (sizeof(CipherSuiteCiscoCCKM24) / sizeof(UCHAR));
87578 +
87579 +UCHAR CipherSuiteCCXTkip[] = {
87580 + 0xDD, 0x16, // RSN IE
87581 + 0x00, 0x50, 0xf2, 0x01, // oui
87582 + 0x01, 0x00, // Version
87583 + 0x00, 0x50, 0xf2, 0x02, // Multicast
87584 + 0x01, 0x00, // Number of unicast
87585 + 0x00, 0x50, 0xf2, 0x02, // unicast
87586 + 0x01, 0x00, // number of authentication method
87587 + 0x00, 0x50, 0xf2, 0x01 // authentication
87588 + };
87589 +UCHAR CipherSuiteCCXTkipLen = (sizeof(CipherSuiteCCXTkip) / sizeof(UCHAR));
87590 +
87591 +UCHAR CCX_LLC_HDR[] = {0xAA, 0xAA, 0x03, 0x00, 0x40, 0x96, 0x00, 0x02};
87592 +UCHAR LLC_NORMAL[] = {0xAA, 0xAA, 0x03, 0x00, 0x00, 0x00};
87593 +
87594 +UCHAR EAPOL_FRAME[] = {0x88, 0x8E};
87595 +
87596 +BOOLEAN CheckRSNIE(
87597 + IN PRTMP_ADAPTER pAd,
87598 + IN PUCHAR pData,
87599 + IN UCHAR DataLen,
87600 + OUT UCHAR *Offset);
87601 +
87602 +void inc_byte_array(UCHAR *counter, int len);
87603 +
87604 +/*
87605 + ========================================================================
87606 +
87607 + Routine Description:
87608 + Classify WPA EAP message type
87609 +
87610 + Arguments:
87611 + EAPType Value of EAP message type
87612 + MsgType Internal Message definition for MLME state machine
87613 +
87614 + Return Value:
87615 + TRUE Found appropriate message type
87616 + FALSE No appropriate message type
87617 +
87618 + IRQL = DISPATCH_LEVEL
87619 +
87620 + Note:
87621 + All these constants are defined in wpa.h
87622 + For supplicant, there is only EAPOL Key message avaliable
87623 +
87624 + ========================================================================
87625 +*/
87626 +BOOLEAN WpaMsgTypeSubst(
87627 + IN UCHAR EAPType,
87628 + OUT INT *MsgType)
87629 +{
87630 + switch (EAPType)
87631 + {
87632 + case EAPPacket:
87633 + *MsgType = MT2_EAPPacket;
87634 + break;
87635 + case EAPOLStart:
87636 + *MsgType = MT2_EAPOLStart;
87637 + break;
87638 + case EAPOLLogoff:
87639 + *MsgType = MT2_EAPOLLogoff;
87640 + break;
87641 + case EAPOLKey:
87642 + *MsgType = MT2_EAPOLKey;
87643 + break;
87644 + case EAPOLASFAlert:
87645 + *MsgType = MT2_EAPOLASFAlert;
87646 + break;
87647 + default:
87648 + return FALSE;
87649 + }
87650 + return TRUE;
87651 +}
87652 +
87653 +/*
87654 + ==========================================================================
87655 + Description:
87656 + association state machine init, including state transition and timer init
87657 + Parameters:
87658 + S - pointer to the association state machine
87659 + ==========================================================================
87660 + */
87661 +VOID WpaPskStateMachineInit(
87662 + IN PRTMP_ADAPTER pAd,
87663 + IN STATE_MACHINE *S,
87664 + OUT STATE_MACHINE_FUNC Trans[])
87665 +{
87666 + StateMachineInit(S, Trans, MAX_WPA_PSK_STATE, MAX_WPA_PSK_MSG, (STATE_MACHINE_FUNC)Drop, WPA_PSK_IDLE, WPA_MACHINE_BASE);
87667 + StateMachineSetAction(S, WPA_PSK_IDLE, MT2_EAPOLKey, (STATE_MACHINE_FUNC)WpaEAPOLKeyAction);
87668 +}
87669 +
87670 +/*
87671 + ==========================================================================
87672 + Description:
87673 + This is state machine function.
87674 + When receiving EAPOL packets which is for 802.1x key management.
87675 + Use both in WPA, and WPAPSK case.
87676 + In this function, further dispatch to different functions according to the received packet. 3 categories are :
87677 + 1. normal 4-way pairwisekey and 2-way groupkey handshake
87678 + 2. MIC error (Countermeasures attack) report packet from STA.
87679 + 3. Request for pairwise/group key update from STA
87680 + Return:
87681 + ==========================================================================
87682 +*/
87683 +VOID WpaEAPOLKeyAction(
87684 + IN PRTMP_ADAPTER pAd,
87685 + IN MLME_QUEUE_ELEM *Elem)
87686 +
87687 +{
87688 + INT MsgType = EAPOL_MSG_INVALID;
87689 + PKEY_DESCRIPTER pKeyDesc;
87690 + PHEADER_802_11 pHeader; //red
87691 + UCHAR ZeroReplay[LEN_KEY_DESC_REPLAY];
87692 + UCHAR EapolVr;
87693 + KEY_INFO peerKeyInfo;
87694 +
87695 + DBGPRINT(RT_DEBUG_TRACE, ("-----> WpaEAPOLKeyAction\n"));
87696 +
87697 + // Get 802.11 header first
87698 + pHeader = (PHEADER_802_11) Elem->Msg;
87699 +
87700 + // Get EAPoL-Key Descriptor
87701 + pKeyDesc = (PKEY_DESCRIPTER) &Elem->Msg[(LENGTH_802_11 + LENGTH_802_1_H + LENGTH_EAPOL_H)];
87702 +
87703 + NdisZeroMemory((PUCHAR)&peerKeyInfo, sizeof(peerKeyInfo));
87704 + NdisMoveMemory((PUCHAR)&peerKeyInfo, (PUCHAR)&pKeyDesc->KeyInfo, sizeof(KEY_INFO));
87705 +
87706 + *((USHORT *)&peerKeyInfo) = cpu2le16(*((USHORT *)&peerKeyInfo));
87707 +
87708 +
87709 + // 1. Check EAPOL frame version and type
87710 + EapolVr = (UCHAR) Elem->Msg[LENGTH_802_11+LENGTH_802_1_H];
87711 +
87712 + if (((EapolVr != EAPOL_VER) && (EapolVr != EAPOL_VER2)) || ((pKeyDesc->Type != WPA1_KEY_DESC) && (pKeyDesc->Type != WPA2_KEY_DESC)))
87713 + {
87714 + DBGPRINT(RT_DEBUG_ERROR, ("Key descripter does not match with WPA rule\n"));
87715 + return;
87716 + }
87717 +
87718 + // First validate replay counter, only accept message with larger replay counter
87719 + // Let equal pass, some AP start with all zero replay counter
87720 + NdisZeroMemory(ZeroReplay, LEN_KEY_DESC_REPLAY);
87721 +
87722 + if((RTMPCompareMemory(pKeyDesc->ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY) != 1) &&
87723 + (RTMPCompareMemory(pKeyDesc->ReplayCounter, ZeroReplay, LEN_KEY_DESC_REPLAY) != 0))
87724 + {
87725 + DBGPRINT(RT_DEBUG_ERROR, (" ReplayCounter not match \n"));
87726 + return;
87727 + }
87728 +
87729 + // Process WPA2PSK frame
87730 + if(pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)
87731 + {
87732 + if((peerKeyInfo.KeyType == PAIRWISEKEY) &&
87733 + (peerKeyInfo.EKD_DL == 0) &&
87734 + (peerKeyInfo.KeyAck == 1) &&
87735 + (peerKeyInfo.KeyMic == 0) &&
87736 + (peerKeyInfo.Secure == 0) &&
87737 + (peerKeyInfo.Error == 0) &&
87738 + (peerKeyInfo.Request == 0))
87739 + {
87740 + MsgType = EAPOL_PAIR_MSG_1;
87741 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL Key Pairwise Message 1\n"));
87742 + } else if((peerKeyInfo.KeyType == PAIRWISEKEY) &&
87743 + (peerKeyInfo.EKD_DL == 1) &&
87744 + (peerKeyInfo.KeyAck == 1) &&
87745 + (peerKeyInfo.KeyMic == 1) &&
87746 + (peerKeyInfo.Secure == 1) &&
87747 + (peerKeyInfo.Error == 0) &&
87748 + (peerKeyInfo.Request == 0))
87749 + {
87750 + MsgType = EAPOL_PAIR_MSG_3;
87751 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL Key Pairwise Message 3\n"));
87752 + } else if((peerKeyInfo.KeyType == GROUPKEY) &&
87753 + (peerKeyInfo.EKD_DL == 1) &&
87754 + (peerKeyInfo.KeyAck == 1) &&
87755 + (peerKeyInfo.KeyMic == 1) &&
87756 + (peerKeyInfo.Secure == 1) &&
87757 + (peerKeyInfo.Error == 0) &&
87758 + (peerKeyInfo.Request == 0))
87759 + {
87760 + MsgType = EAPOL_GROUP_MSG_1;
87761 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL Key Group Message 1\n"));
87762 + }
87763 +
87764 + // We will assume link is up (assoc suceess and port not secured).
87765 + // All state has to be able to process message from previous state
87766 + switch(pAd->StaCfg.WpaState)
87767 + {
87768 + case SS_START:
87769 + if(MsgType == EAPOL_PAIR_MSG_1)
87770 + {
87771 + Wpa2PairMsg1Action(pAd, Elem);
87772 + pAd->StaCfg.WpaState = SS_WAIT_MSG_3;
87773 + }
87774 + break;
87775 +
87776 + case SS_WAIT_MSG_3:
87777 + if(MsgType == EAPOL_PAIR_MSG_1)
87778 + {
87779 + Wpa2PairMsg1Action(pAd, Elem);
87780 + pAd->StaCfg.WpaState = SS_WAIT_MSG_3;
87781 + }
87782 + else if(MsgType == EAPOL_PAIR_MSG_3)
87783 + {
87784 + Wpa2PairMsg3Action(pAd, Elem);
87785 + pAd->StaCfg.WpaState = SS_WAIT_GROUP;
87786 + }
87787 + break;
87788 +
87789 + case SS_WAIT_GROUP: // When doing group key exchange
87790 + case SS_FINISH: // This happened when update group key
87791 + if(MsgType == EAPOL_PAIR_MSG_1)
87792 + {
87793 + // Reset port secured variable
87794 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
87795 + Wpa2PairMsg1Action(pAd, Elem);
87796 + pAd->StaCfg.WpaState = SS_WAIT_MSG_3;
87797 + }
87798 + else if(MsgType == EAPOL_PAIR_MSG_3)
87799 + {
87800 + // Reset port secured variable
87801 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
87802 + Wpa2PairMsg3Action(pAd, Elem);
87803 + pAd->StaCfg.WpaState = SS_WAIT_GROUP;
87804 + }
87805 + else if(MsgType == EAPOL_GROUP_MSG_1)
87806 + {
87807 + WpaGroupMsg1Action(pAd, Elem);
87808 + pAd->StaCfg.WpaState = SS_FINISH;
87809 + }
87810 + break;
87811 +
87812 + default:
87813 + break;
87814 + }
87815 + }
87816 + // Process WPAPSK Frame
87817 + // Classify message Type, either pairwise message 1, 3, or group message 1 for supplicant
87818 + else if(pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK)
87819 + {
87820 + if((peerKeyInfo.KeyType == PAIRWISEKEY) &&
87821 + (peerKeyInfo.KeyIndex == 0) &&
87822 + (peerKeyInfo.KeyAck == 1) &&
87823 + (peerKeyInfo.KeyMic == 0) &&
87824 + (peerKeyInfo.Secure == 0) &&
87825 + (peerKeyInfo.Error == 0) &&
87826 + (peerKeyInfo.Request == 0))
87827 + {
87828 + MsgType = EAPOL_PAIR_MSG_1;
87829 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL Key Pairwise Message 1\n"));
87830 + }
87831 + else if((peerKeyInfo.KeyType == PAIRWISEKEY) &&
87832 + (peerKeyInfo.KeyIndex == 0) &&
87833 + (peerKeyInfo.KeyAck == 1) &&
87834 + (peerKeyInfo.KeyMic == 1) &&
87835 + (peerKeyInfo.Secure == 0) &&
87836 + (peerKeyInfo.Error == 0) &&
87837 + (peerKeyInfo.Request == 0))
87838 + {
87839 + MsgType = EAPOL_PAIR_MSG_3;
87840 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL Key Pairwise Message 3\n"));
87841 + }
87842 + else if((peerKeyInfo.KeyType == GROUPKEY) &&
87843 + (peerKeyInfo.KeyIndex != 0) &&
87844 + (peerKeyInfo.KeyAck == 1) &&
87845 + (peerKeyInfo.KeyMic == 1) &&
87846 + (peerKeyInfo.Secure == 1) &&
87847 + (peerKeyInfo.Error == 0) &&
87848 + (peerKeyInfo.Request == 0))
87849 + {
87850 + MsgType = EAPOL_GROUP_MSG_1;
87851 + DBGPRINT(RT_DEBUG_TRACE, ("Receive EAPOL Key Group Message 1\n"));
87852 + }
87853 +
87854 + // We will assume link is up (assoc suceess and port not secured).
87855 + // All state has to be able to process message from previous state
87856 + switch(pAd->StaCfg.WpaState)
87857 + {
87858 + case SS_START:
87859 + if(MsgType == EAPOL_PAIR_MSG_1)
87860 + {
87861 + WpaPairMsg1Action(pAd, Elem);
87862 + pAd->StaCfg.WpaState = SS_WAIT_MSG_3;
87863 + }
87864 + break;
87865 +
87866 + case SS_WAIT_MSG_3:
87867 + if(MsgType == EAPOL_PAIR_MSG_1)
87868 + {
87869 + WpaPairMsg1Action(pAd, Elem);
87870 + pAd->StaCfg.WpaState = SS_WAIT_MSG_3;
87871 + }
87872 + else if(MsgType == EAPOL_PAIR_MSG_3)
87873 + {
87874 + WpaPairMsg3Action(pAd, Elem);
87875 + pAd->StaCfg.WpaState = SS_WAIT_GROUP;
87876 + }
87877 + break;
87878 +
87879 + case SS_WAIT_GROUP: // When doing group key exchange
87880 + case SS_FINISH: // This happened when update group key
87881 + if(MsgType == EAPOL_PAIR_MSG_1)
87882 + {
87883 + WpaPairMsg1Action(pAd, Elem);
87884 + pAd->StaCfg.WpaState = SS_WAIT_MSG_3;
87885 + // Reset port secured variable
87886 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
87887 + }
87888 + else if(MsgType == EAPOL_PAIR_MSG_3)
87889 + {
87890 + WpaPairMsg3Action(pAd, Elem);
87891 + pAd->StaCfg.WpaState = SS_WAIT_GROUP;
87892 + // Reset port secured variable
87893 + pAd->StaCfg.PortSecured = WPA_802_1X_PORT_NOT_SECURED;
87894 + }
87895 + else if(MsgType == EAPOL_GROUP_MSG_1)
87896 + {
87897 + WpaGroupMsg1Action(pAd, Elem);
87898 + pAd->StaCfg.WpaState = SS_FINISH;
87899 + }
87900 + break;
87901 +
87902 + default:
87903 + break;
87904 + }
87905 + }
87906 +
87907 + DBGPRINT(RT_DEBUG_TRACE, ("<----- WpaEAPOLKeyAction\n"));
87908 +}
87909 +
87910 +/*
87911 + ========================================================================
87912 +
87913 + Routine Description:
87914 + Process Pairwise key 4-way handshaking
87915 +
87916 + Arguments:
87917 + pAd Pointer to our adapter
87918 + Elem Message body
87919 +
87920 + Return Value:
87921 + None
87922 +
87923 + Note:
87924 +
87925 + ========================================================================
87926 +*/
87927 +VOID WpaPairMsg1Action(
87928 + IN PRTMP_ADAPTER pAd,
87929 + IN MLME_QUEUE_ELEM *Elem)
87930 +{
87931 + PHEADER_802_11 pHeader;
87932 + UCHAR *mpool, *PTK, *digest;
87933 + PUCHAR pOutBuffer = NULL;
87934 + UCHAR Header802_3[14];
87935 + ULONG FrameLen = 0;
87936 + PEAPOL_PACKET pMsg1;
87937 + EAPOL_PACKET Packet;
87938 + UCHAR Mic[16];
87939 +
87940 + DBGPRINT(RT_DEBUG_TRACE, ("WpaPairMsg1Action ----->\n"));
87941 +
87942 + // allocate memory pool
87943 + os_alloc_mem(pAd, (PUCHAR *)&mpool, 256);
87944 +
87945 + if (mpool == NULL)
87946 + return;
87947 +
87948 + // PTK Len = 80.
87949 + PTK = (UCHAR *) ROUND_UP(mpool, 4);
87950 + // digest Len = 80.
87951 + digest = (UCHAR *) ROUND_UP(PTK + 80, 4);
87952 +
87953 + pHeader = (PHEADER_802_11) Elem->Msg;
87954 +
87955 + // Process message 1 from authenticator
87956 + pMsg1 = (PEAPOL_PACKET) &Elem->Msg[LENGTH_802_11 + LENGTH_802_1_H];
87957 +
87958 + // 1. Save Replay counter, it will use to verify message 3 and construct message 2
87959 + NdisMoveMemory(pAd->StaCfg.ReplayCounter, pMsg1->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
87960 +
87961 + // 2. Save ANonce
87962 + NdisMoveMemory(pAd->StaCfg.ANonce, pMsg1->KeyDesc.KeyNonce, LEN_KEY_DESC_NONCE);
87963 +
87964 + // Generate random SNonce
87965 + GenRandom(pAd, pAd->CurrentAddress, pAd->StaCfg.SNonce);
87966 +
87967 + // Calc PTK(ANonce, SNonce)
87968 + WpaCountPTK(pAd,
87969 + pAd->StaCfg.PMK,
87970 + pAd->StaCfg.ANonce,
87971 + pAd->CommonCfg.Bssid,
87972 + pAd->StaCfg.SNonce,
87973 + pAd->CurrentAddress,
87974 + PTK,
87975 + LEN_PTK);
87976 +
87977 + // Save key to PTK entry
87978 + NdisMoveMemory(pAd->StaCfg.PTK, PTK, LEN_PTK);
87979 +
87980 + // init 802.3 header and Fill Packet
87981 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
87982 +
87983 + // Zero Message 2 body
87984 + NdisZeroMemory(&Packet, sizeof(Packet));
87985 + Packet.ProVer = EAPOL_VER;
87986 + Packet.ProType = EAPOLKey;
87987 + //
87988 + // Message 2 as EAPOL-Key(0,1,0,0,0,P,0,SNonce,MIC,RSN IE)
87989 + //
87990 + Packet.KeyDesc.Type = WPA1_KEY_DESC;
87991 + // 1. Key descriptor version and appropriate RSN IE
87992 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
87993 + {
87994 + Packet.KeyDesc.KeyInfo.KeyDescVer = 2;
87995 + }
87996 + else // TKIP
87997 + {
87998 + Packet.KeyDesc.KeyInfo.KeyDescVer = 1;
87999 + }
88000 +
88001 + // fill in Data Material and its length
88002 + Packet.KeyDesc.KeyData[0] = IE_WPA;
88003 + Packet.KeyDesc.KeyData[1] = pAd->StaCfg.RSNIE_Len;
88004 + Packet.KeyDesc.KeyDataLen[1] = pAd->StaCfg.RSNIE_Len + 2;
88005 + NdisMoveMemory(&Packet.KeyDesc.KeyData[2], pAd->StaCfg.RSN_IE, pAd->StaCfg.RSNIE_Len);
88006 +
88007 + // Update packet length after decide Key data payload
88008 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE + Packet.KeyDesc.KeyDataLen[1];
88009 +
88010 + // Update Key length
88011 + Packet.KeyDesc.KeyLength[0] = pMsg1->KeyDesc.KeyLength[0];
88012 + Packet.KeyDesc.KeyLength[1] = pMsg1->KeyDesc.KeyLength[1];
88013 + // 2. Key Type PeerKey
88014 + Packet.KeyDesc.KeyInfo.KeyType = PAIRWISEKEY;
88015 +
88016 + // 3. KeyMic field presented
88017 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
88018 +
88019 + //Convert to little-endian format.
88020 + *((USHORT *)&Packet.KeyDesc.KeyInfo) = cpu2le16(*((USHORT *)&Packet.KeyDesc.KeyInfo));
88021 +
88022 +
88023 + // 4. Fill SNonce
88024 + NdisMoveMemory(Packet.KeyDesc.KeyNonce, pAd->StaCfg.SNonce, LEN_KEY_DESC_NONCE);
88025 +
88026 + // 5. Key Replay Count
88027 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY);
88028 +
88029 + // Send EAPOL(0, 1, 0, 0, 0, P, 0, SNonce, MIC, RSN_IE)
88030 + // Out buffer for transmitting message 2
88031 + MlmeAllocateMemory(pAd, (PUCHAR *)&pOutBuffer); // allocate memory
88032 + if(pOutBuffer == NULL)
88033 + {
88034 + os_free_mem(pAd, mpool);
88035 + return;
88036 + }
88037 + // Prepare EAPOL frame for MIC calculation
88038 + // Be careful, only EAPOL frame is counted for MIC calculation
88039 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88040 + Packet.Body_Len[1] + 4, &Packet,
88041 + END_OF_ARGS);
88042 +
88043 + // 6. Prepare and Fill MIC value
88044 + NdisZeroMemory(Mic, sizeof(Mic));
88045 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88046 + { // AES
88047 +
88048 + HMAC_SHA1(pOutBuffer, FrameLen, PTK, LEN_EAP_MICK, digest);
88049 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88050 + }
88051 + else
88052 + { // TKIP
88053 + hmac_md5(PTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
88054 + }
88055 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
88056 +
88057 + //hex_dump("MIC", Mic, LEN_KEY_DESC_MIC);
88058 +
88059 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88060 + LENGTH_802_3, &Header802_3,
88061 + Packet.Body_Len[1] + 4, &Packet,
88062 + END_OF_ARGS);
88063 +
88064 +
88065 + // 5. Copy frame to Tx ring and send Msg 2 to authenticator
88066 + RTMPToWirelessSta(pAd, Header802_3, LENGTH_802_3, (PUCHAR)&Packet, Packet.Body_Len[1] + 4, TRUE);
88067 +
88068 + MlmeFreeMemory(pAd, (PUCHAR)pOutBuffer);
88069 + os_free_mem(pAd, (PUCHAR)mpool);
88070 +
88071 + DBGPRINT(RT_DEBUG_TRACE, ("WpaPairMsg1Action <-----\n"));
88072 +}
88073 +
88074 +VOID Wpa2PairMsg1Action(
88075 + IN PRTMP_ADAPTER pAd,
88076 + IN MLME_QUEUE_ELEM *Elem)
88077 +{
88078 + PHEADER_802_11 pHeader;
88079 + UCHAR *mpool, *PTK, *digest;
88080 + PUCHAR pOutBuffer = NULL;
88081 + UCHAR Header802_3[14];
88082 + ULONG FrameLen = 0;
88083 + PEAPOL_PACKET pMsg1;
88084 + EAPOL_PACKET Packet;
88085 + UCHAR Mic[16];
88086 +
88087 + DBGPRINT(RT_DEBUG_TRACE, ("Wpa2PairMsg1Action ----->\n"));
88088 +
88089 + // allocate memory pool
88090 + os_alloc_mem(pAd, (PUCHAR *)&mpool, 256);
88091 +
88092 + if (mpool == NULL)
88093 + return;
88094 +
88095 + // PTK Len = 80.
88096 + PTK = (UCHAR *) ROUND_UP(mpool, 4);
88097 + // digest Len = 80.
88098 + digest = (UCHAR *) ROUND_UP(PTK + 80, 4);
88099 +
88100 + pHeader = (PHEADER_802_11) Elem->Msg;
88101 +
88102 + // Process message 1 from authenticator
88103 + pMsg1 = (PEAPOL_PACKET) &Elem->Msg[LENGTH_802_11 + LENGTH_802_1_H];
88104 +
88105 + // 1. Save Replay counter, it will use to verify message 3 and construct message 2
88106 + NdisMoveMemory(pAd->StaCfg.ReplayCounter, pMsg1->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
88107 +
88108 + // 2. Save ANonce
88109 + NdisMoveMemory(pAd->StaCfg.ANonce, pMsg1->KeyDesc.KeyNonce, LEN_KEY_DESC_NONCE);
88110 +
88111 + // Generate random SNonce
88112 + GenRandom(pAd, pAd->CurrentAddress, pAd->StaCfg.SNonce);
88113 +
88114 + if(pMsg1->KeyDesc.KeyDataLen[1] > 0 )
88115 + {
88116 + // cached PMKID
88117 + }
88118 +
88119 + // Calc PTK(ANonce, SNonce)
88120 + WpaCountPTK(pAd,
88121 + pAd->StaCfg.PMK,
88122 + pAd->StaCfg.ANonce,
88123 + pAd->CommonCfg.Bssid,
88124 + pAd->StaCfg.SNonce,
88125 + pAd->CurrentAddress,
88126 + PTK,
88127 + LEN_PTK);
88128 +
88129 + // Save key to PTK entry
88130 + NdisMoveMemory(pAd->StaCfg.PTK, PTK, LEN_PTK);
88131 +
88132 + // init 802.3 header and Fill Packet
88133 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
88134 +
88135 + // Zero message 2 body
88136 + NdisZeroMemory(&Packet, sizeof(Packet));
88137 + Packet.ProVer = EAPOL_VER;
88138 + Packet.ProType = EAPOLKey;
88139 + //
88140 + // Message 2 as EAPOL-Key(0,1,0,0,0,P,0,SNonce,MIC,RSN IE)
88141 + //
88142 + Packet.KeyDesc.Type = WPA2_KEY_DESC;
88143 +
88144 + // 1. Key descriptor version and appropriate RSN IE
88145 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88146 + {
88147 + Packet.KeyDesc.KeyInfo.KeyDescVer = 2;
88148 + }
88149 + else // TKIP
88150 + {
88151 + Packet.KeyDesc.KeyInfo.KeyDescVer = 1;
88152 + }
88153 +
88154 + // fill in Data Material and its length
88155 + Packet.KeyDesc.KeyData[0] = IE_WPA2;
88156 + Packet.KeyDesc.KeyData[1] = pAd->StaCfg.RSNIE_Len;
88157 + Packet.KeyDesc.KeyDataLen[1] = pAd->StaCfg.RSNIE_Len + 2;
88158 + NdisMoveMemory(&Packet.KeyDesc.KeyData[2], pAd->StaCfg.RSN_IE, pAd->StaCfg.RSNIE_Len);
88159 +
88160 + // Update packet length after decide Key data payload
88161 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE + Packet.KeyDesc.KeyDataLen[1];
88162 +
88163 + // 2. Key Type PeerKey
88164 + Packet.KeyDesc.KeyInfo.KeyType = PAIRWISEKEY;
88165 +
88166 + // 3. KeyMic field presented
88167 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
88168 +
88169 + // Update Key Length
88170 + Packet.KeyDesc.KeyLength[0] = 0;
88171 + Packet.KeyDesc.KeyLength[1] = pMsg1->KeyDesc.KeyLength[1];
88172 +
88173 + // 4. Fill SNonce
88174 + NdisMoveMemory(Packet.KeyDesc.KeyNonce, pAd->StaCfg.SNonce, LEN_KEY_DESC_NONCE);
88175 +
88176 + // 5. Key Replay Count
88177 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY);
88178 +
88179 + // Convert to little-endian format.
88180 + *((USHORT *)&Packet.KeyDesc.KeyInfo) = cpu2le16(*((USHORT *)&Packet.KeyDesc.KeyInfo));
88181 +
88182 + // Send EAPOL-Key(0,1,0,0,0,P,0,SNonce,MIC,RSN IE)
88183 + // Out buffer for transmitting message 2
88184 + MlmeAllocateMemory(pAd, (PUCHAR *)&pOutBuffer); // allocate memory
88185 + if(pOutBuffer == NULL)
88186 + {
88187 + os_free_mem(pAd, mpool);
88188 + return;
88189 + }
88190 +
88191 + // Prepare EAPOL frame for MIC calculation
88192 + // Be careful, only EAPOL frame is counted for MIC calculation
88193 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88194 + Packet.Body_Len[1] + 4, &Packet,
88195 + END_OF_ARGS);
88196 +
88197 + // 6. Prepare and Fill MIC value
88198 + NdisZeroMemory(Mic, sizeof(Mic));
88199 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88200 + {
88201 + // AES
88202 + HMAC_SHA1(pOutBuffer, FrameLen, PTK, LEN_EAP_MICK, digest);
88203 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88204 + }
88205 + else
88206 + {
88207 + hmac_md5(PTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
88208 + }
88209 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
88210 +
88211 +
88212 + // Make Transmitting frame
88213 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88214 + LENGTH_802_3, &Header802_3,
88215 + Packet.Body_Len[1] + 4, &Packet,
88216 + END_OF_ARGS);
88217 +
88218 +
88219 + // 5. Copy frame to Tx ring
88220 + RTMPToWirelessSta(pAd, Header802_3, LENGTH_802_3, (PUCHAR)&Packet, Packet.Body_Len[1] + 4, TRUE);
88221 +
88222 + MlmeFreeMemory(pAd, pOutBuffer);
88223 + os_free_mem(pAd, mpool);
88224 +
88225 + DBGPRINT(RT_DEBUG_TRACE, ("Wpa2PairMsg1Action <-----\n"));
88226 +
88227 +}
88228 +
88229 +/*
88230 + ========================================================================
88231 +
88232 + Routine Description:
88233 + Process Pairwise key 4-way handshaking
88234 +
88235 + Arguments:
88236 + pAd Pointer to our adapter
88237 + Elem Message body
88238 +
88239 + Return Value:
88240 + None
88241 +
88242 + Note:
88243 +
88244 + ========================================================================
88245 +*/
88246 +VOID WpaPairMsg3Action(
88247 + IN PRTMP_ADAPTER pAd,
88248 + IN MLME_QUEUE_ELEM *Elem)
88249 +
88250 +{
88251 + PHEADER_802_11 pHeader;
88252 + PUCHAR pOutBuffer = NULL;
88253 + UCHAR Header802_3[14];
88254 + ULONG FrameLen = 0;
88255 + EAPOL_PACKET Packet;
88256 + PEAPOL_PACKET pMsg3;
88257 + UCHAR Mic[16], OldMic[16];
88258 + MAC_TABLE_ENTRY *pEntry = NULL;
88259 + UCHAR skip_offset;
88260 + KEY_INFO peerKeyInfo;
88261 +
88262 + DBGPRINT(RT_DEBUG_TRACE, ("WpaPairMsg3Action ----->\n"));
88263 +
88264 + // Record 802.11 header & the received EAPOL packet Msg3
88265 + pHeader = (PHEADER_802_11) Elem->Msg;
88266 + pMsg3 = (PEAPOL_PACKET) &Elem->Msg[LENGTH_802_11 + LENGTH_802_1_H];
88267 +
88268 + NdisZeroMemory((PUCHAR)&peerKeyInfo, sizeof(peerKeyInfo));
88269 + NdisMoveMemory((PUCHAR)&peerKeyInfo, (PUCHAR)&pMsg3->KeyDesc.KeyInfo, sizeof(KEY_INFO));
88270 +
88271 + *((USHORT*)&peerKeyInfo) = cpu2le16(*((USHORT*)&peerKeyInfo));
88272 +
88273 +
88274 + // 1. Verify cipher type match
88275 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled && (peerKeyInfo.KeyDescVer != 2))
88276 + {
88277 + return;
88278 + }
88279 + else if(pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled && (peerKeyInfo.KeyDescVer != 1))
88280 + {
88281 + return;
88282 + }
88283 +
88284 + // Verify RSN IE
88285 + //if (!RTMPEqualMemory(pMsg3->KeyDesc.KeyData, pAd->MacTab.Content[BSSID_WCID].RSN_IE, pAd->MacTab.Content[BSSID_WCID].RSNIE_Len))
88286 + if (!CheckRSNIE(pAd, pMsg3->KeyDesc.KeyData, pMsg3->KeyDesc.KeyDataLen[1], &skip_offset))
88287 + {
88288 + DBGPRINT(RT_DEBUG_ERROR, ("RSN_IE Different in Msg 3 of WPA1 4-way handshake!! \n"));
88289 + hex_dump("The original RSN_IE", pAd->MacTab.Content[BSSID_WCID].RSN_IE, pAd->MacTab.Content[BSSID_WCID].RSNIE_Len);
88290 + hex_dump("The received RSN_IE", pMsg3->KeyDesc.KeyData, pMsg3->KeyDesc.KeyDataLen[1]);
88291 + return;
88292 + }
88293 + else
88294 + DBGPRINT(RT_DEBUG_TRACE, ("RSN_IE VALID in Msg 3 of WPA1 4-way handshake!! \n"));
88295 +
88296 +
88297 + // 2. Check MIC value
88298 + // Save the MIC and replace with zero
88299 + NdisMoveMemory(OldMic, pMsg3->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
88300 + NdisZeroMemory(pMsg3->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
88301 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88302 + {
88303 + // AES
88304 + UCHAR digest[80];
88305 +
88306 + HMAC_SHA1((PUCHAR) pMsg3, pMsg3->Body_Len[1] + 4, pAd->StaCfg.PTK, LEN_EAP_MICK, digest);
88307 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88308 + }
88309 + else // TKIP
88310 + {
88311 + hmac_md5(pAd->StaCfg.PTK, LEN_EAP_MICK, (PUCHAR) pMsg3, pMsg3->Body_Len[1] + 4, Mic);
88312 + }
88313 +
88314 + if(!NdisEqualMemory(OldMic, Mic, LEN_KEY_DESC_MIC))
88315 + {
88316 + DBGPRINT(RT_DEBUG_ERROR, (" MIC Different in msg 3 of 4-way handshake!!!!!!!!!! \n"));
88317 + return;
88318 + }
88319 + else
88320 + DBGPRINT(RT_DEBUG_TRACE, (" MIC VALID in msg 3 of 4-way handshake!!!!!!!!!! \n"));
88321 +
88322 + // 3. Check Replay Counter, it has to be larger than last one. No need to be exact one larger
88323 + if(RTMPCompareMemory(pMsg3->KeyDesc.ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY) != 1)
88324 + return;
88325 +
88326 + // Update new replay counter
88327 + NdisMoveMemory(pAd->StaCfg.ReplayCounter, pMsg3->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
88328 +
88329 + // 4. Double check ANonce
88330 + if(!NdisEqualMemory(pAd->StaCfg.ANonce, pMsg3->KeyDesc.KeyNonce, LEN_KEY_DESC_NONCE))
88331 + return;
88332 +
88333 + // init 802.3 header and Fill Packet
88334 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
88335 +
88336 + // Zero Message 4 body
88337 + NdisZeroMemory(&Packet, sizeof(Packet));
88338 + Packet.ProVer = EAPOL_VER;
88339 + Packet.ProType = EAPOLKey;
88340 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE; // No data field
88341 +
88342 + //
88343 + // Message 4 as EAPOL-Key(0,1,0,0,0,P,0,0,MIC,0)
88344 + //
88345 + Packet.KeyDesc.Type = WPA1_KEY_DESC;
88346 +
88347 + // Key descriptor version and appropriate RSN IE
88348 + Packet.KeyDesc.KeyInfo.KeyDescVer = peerKeyInfo.KeyDescVer;
88349 +
88350 + // Update Key Length
88351 + Packet.KeyDesc.KeyLength[0] = pMsg3->KeyDesc.KeyLength[0];
88352 + Packet.KeyDesc.KeyLength[1] = pMsg3->KeyDesc.KeyLength[1];
88353 +
88354 + // Key Type PeerKey
88355 + Packet.KeyDesc.KeyInfo.KeyType = PAIRWISEKEY;
88356 +
88357 + // KeyMic field presented
88358 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
88359 +
88360 + // In Msg3, KeyInfo.secure =0 if Group Key HS to come. 1 if no group key HS
88361 + // Station sends Msg4 KeyInfo.secure should be the same as that in Msg.3
88362 + Packet.KeyDesc.KeyInfo.Secure= peerKeyInfo.Secure;
88363 +
88364 + // Convert to little-endian format.
88365 + *((USHORT *)&Packet.KeyDesc.KeyInfo) = cpu2le16(*((USHORT *)&Packet.KeyDesc.KeyInfo));
88366 +
88367 + // Key Replay count
88368 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pMsg3->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
88369 +
88370 + // Out buffer for transmitting message 4
88371 + MlmeAllocateMemory(pAd, (PUCHAR *)&pOutBuffer); // allocate memory
88372 + if(pOutBuffer == NULL)
88373 + return;
88374 +
88375 + // Prepare EAPOL frame for MIC calculation
88376 + // Be careful, only EAPOL frame is counted for MIC calculation
88377 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88378 + Packet.Body_Len[1] + 4, &Packet,
88379 + END_OF_ARGS);
88380 +
88381 + // Prepare and Fill MIC value
88382 + NdisZeroMemory(Mic, sizeof(Mic));
88383 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88384 + {
88385 + // AES
88386 + UCHAR digest[80];
88387 +
88388 + HMAC_SHA1(pOutBuffer, FrameLen, pAd->StaCfg.PTK, LEN_EAP_MICK, digest);
88389 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88390 + }
88391 + else
88392 + {
88393 + hmac_md5(pAd->StaCfg.PTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
88394 + }
88395 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
88396 +
88397 + // Update PTK
88398 + // Prepare pair-wise key information into shared key table
88399 + NdisZeroMemory(&pAd->SharedKey[BSS0][0], sizeof(CIPHER_KEY));
88400 + pAd->SharedKey[BSS0][0].KeyLen = LEN_TKIP_EK;
88401 + NdisMoveMemory(pAd->SharedKey[BSS0][0].Key, &pAd->StaCfg.PTK[32], LEN_TKIP_EK);
88402 + NdisMoveMemory(pAd->SharedKey[BSS0][0].RxMic, &pAd->StaCfg.PTK[48], LEN_TKIP_RXMICK);
88403 + NdisMoveMemory(pAd->SharedKey[BSS0][0].TxMic, &pAd->StaCfg.PTK[48+LEN_TKIP_RXMICK], LEN_TKIP_TXMICK);
88404 +
88405 + // Decide its ChiperAlg
88406 + if (pAd->StaCfg.PairCipher == Ndis802_11Encryption2Enabled)
88407 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_TKIP;
88408 + else if (pAd->StaCfg.PairCipher == Ndis802_11Encryption3Enabled)
88409 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_AES;
88410 + else
88411 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_NONE;
88412 +
88413 + // Update these related information to MAC_TABLE_ENTRY
88414 + pEntry = &pAd->MacTab.Content[BSSID_WCID];
88415 + NdisMoveMemory(pEntry->PairwiseKey.Key, &pAd->StaCfg.PTK[32], LEN_TKIP_EK);
88416 + NdisMoveMemory(pEntry->PairwiseKey.RxMic, &pAd->StaCfg.PTK[48], LEN_TKIP_RXMICK);
88417 + NdisMoveMemory(pEntry->PairwiseKey.TxMic, &pAd->StaCfg.PTK[48+LEN_TKIP_RXMICK], LEN_TKIP_TXMICK);
88418 + pEntry->PairwiseKey.CipherAlg = pAd->SharedKey[BSS0][0].CipherAlg;
88419 +
88420 + // Update pairwise key information to ASIC Shared Key Table
88421 + AsicAddSharedKeyEntry(pAd,
88422 + BSS0,
88423 + 0,
88424 + pAd->SharedKey[BSS0][0].CipherAlg,
88425 + pAd->SharedKey[BSS0][0].Key,
88426 + pAd->SharedKey[BSS0][0].TxMic,
88427 + pAd->SharedKey[BSS0][0].RxMic);
88428 +
88429 + // Update ASIC WCID attribute table and IVEIV table
88430 + RTMPAddWcidAttributeEntry(pAd,
88431 + BSS0,
88432 + 0,
88433 + pAd->SharedKey[BSS0][0].CipherAlg,
88434 + pEntry);
88435 +
88436 + // Make transmitting frame
88437 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88438 + LENGTH_802_3, &Header802_3,
88439 + Packet.Body_Len[1] + 4, &Packet,
88440 + END_OF_ARGS);
88441 +
88442 +
88443 + // Copy frame to Tx ring and Send Message 4 to authenticator
88444 + RTMPToWirelessSta(pAd, Header802_3, LENGTH_802_3, (PUCHAR)&Packet, Packet.Body_Len[1] + 4, TRUE);
88445 +
88446 + MlmeFreeMemory(pAd, (PUCHAR)pOutBuffer);
88447 +
88448 + DBGPRINT(RT_DEBUG_TRACE, ("WpaPairMsg3Action <-----\n"));
88449 +}
88450 +
88451 +VOID Wpa2PairMsg3Action(
88452 + IN PRTMP_ADAPTER pAd,
88453 + IN MLME_QUEUE_ELEM *Elem)
88454 +
88455 +{
88456 + PHEADER_802_11 pHeader;
88457 + PUCHAR pOutBuffer = NULL;
88458 + UCHAR Header802_3[14];
88459 + ULONG FrameLen = 0;
88460 + EAPOL_PACKET Packet;
88461 + PEAPOL_PACKET pMsg3;
88462 + UCHAR Mic[16], OldMic[16];
88463 + UCHAR *mpool, *KEYDATA, *digest;
88464 + UCHAR Key[32];
88465 + MAC_TABLE_ENTRY *pEntry = NULL;
88466 + KEY_INFO peerKeyInfo;
88467 +
88468 + // allocate memory
88469 + os_alloc_mem(pAd, (PUCHAR *)&mpool, 1024);
88470 +
88471 + if(mpool == NULL)
88472 + return;
88473 +
88474 + // KEYDATA Len = 512.
88475 + KEYDATA = (UCHAR *) ROUND_UP(mpool, 4);
88476 + // digest Len = 80.
88477 + digest = (UCHAR *) ROUND_UP(KEYDATA + 512, 4);
88478 +
88479 + DBGPRINT(RT_DEBUG_TRACE, ("Wpa2PairMsg3Action ----->\n"));
88480 +
88481 + pHeader = (PHEADER_802_11) Elem->Msg;
88482 +
88483 + // Process message 3 frame.
88484 + pMsg3 = (PEAPOL_PACKET) &Elem->Msg[LENGTH_802_11 + LENGTH_802_1_H];
88485 +
88486 + NdisZeroMemory((PUCHAR)&peerKeyInfo, sizeof(peerKeyInfo));
88487 + NdisMoveMemory((PUCHAR)&peerKeyInfo, (PUCHAR)&pMsg3->KeyDesc.KeyInfo, sizeof(KEY_INFO));
88488 +
88489 + *((USHORT*)&peerKeyInfo) = cpu2le16(*((USHORT*)&peerKeyInfo));
88490 +
88491 + // 1. Verify cipher type match
88492 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled && (peerKeyInfo.KeyDescVer!= 2))
88493 + {
88494 + os_free_mem(pAd, (PUCHAR)mpool);
88495 + return;
88496 + }
88497 + else if(pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled && (peerKeyInfo.KeyDescVer != 1))
88498 + {
88499 + os_free_mem(pAd, (PUCHAR)mpool);
88500 + return;
88501 + }
88502 +
88503 + // 2. Check MIC value
88504 + // Save the MIC and replace with zero
88505 + NdisMoveMemory(OldMic, pMsg3->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
88506 + NdisZeroMemory(pMsg3->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
88507 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88508 + {
88509 + // AES
88510 + HMAC_SHA1((PUCHAR) pMsg3, pMsg3->Body_Len[1] + 4, pAd->StaCfg.PTK, LEN_EAP_MICK, digest);
88511 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88512 + }
88513 + else
88514 + {
88515 + hmac_md5(pAd->StaCfg.PTK, LEN_EAP_MICK, (PUCHAR) pMsg3, pMsg3->Body_Len[1] + 4, Mic);
88516 + }
88517 +
88518 + if(!NdisEqualMemory(OldMic, Mic, LEN_KEY_DESC_MIC))
88519 + {
88520 + DBGPRINT(RT_DEBUG_ERROR, (" MIC Different in msg 3 of 4-way handshake!!!!!!!!!! \n"));
88521 + os_free_mem(pAd, (PUCHAR)mpool);
88522 + return;
88523 + }
88524 + else
88525 + DBGPRINT(RT_DEBUG_TRACE, (" MIC VALID in msg 3 of 4-way handshake!!!!!!!!!! \n"));
88526 +
88527 + // 3. Check Replay Counter, it has to be larger than last one. No need to be exact one larger
88528 + if(RTMPCompareMemory(pMsg3->KeyDesc.ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY) != 1)
88529 + {
88530 + os_free_mem(pAd, (PUCHAR)mpool);
88531 + return;
88532 + }
88533 +
88534 + // Update new replay counter
88535 + NdisMoveMemory(pAd->StaCfg.ReplayCounter, pMsg3->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
88536 +
88537 + // 4. Double check ANonce
88538 + if(!NdisEqualMemory(pAd->StaCfg.ANonce, pMsg3->KeyDesc.KeyNonce, LEN_KEY_DESC_NONCE))
88539 + {
88540 + os_free_mem(pAd, (PUCHAR)mpool);
88541 + return;
88542 + }
88543 +
88544 + // Obtain GTK
88545 + // 5. Decrypt GTK from Key Data
88546 + DBGPRINT_RAW(RT_DEBUG_TRACE, ("EKD = %d\n", peerKeyInfo.EKD_DL));
88547 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88548 + {
88549 + // Decrypt AES GTK
88550 + AES_GTK_KEY_UNWRAP(&pAd->StaCfg.PTK[16], KEYDATA, pMsg3->KeyDesc.KeyDataLen[1],pMsg3->KeyDesc.KeyData);
88551 + }
88552 + else // TKIP
88553 + {
88554 + INT i;
88555 + // Decrypt TKIP GTK
88556 + // Construct 32 bytes RC4 Key
88557 + NdisMoveMemory(Key, pMsg3->KeyDesc.KeyIv, 16);
88558 + NdisMoveMemory(&Key[16], &pAd->StaCfg.PTK[16], 16);
88559 + ARCFOUR_INIT(&pAd->PrivateInfo.WEPCONTEXT, Key, 32);
88560 + //discard first 256 bytes
88561 + for(i = 0; i < 256; i++)
88562 + ARCFOUR_BYTE(&pAd->PrivateInfo.WEPCONTEXT);
88563 + // Decrypt GTK. Becareful, there is no ICV to check the result is correct or not
88564 + ARCFOUR_DECRYPT(&pAd->PrivateInfo.WEPCONTEXT, KEYDATA, pMsg3->KeyDesc.KeyData, pMsg3->KeyDesc.KeyDataLen[1]);
88565 + }
88566 +
88567 + if (!ParseKeyData(pAd, KEYDATA, pMsg3->KeyDesc.KeyDataLen[1], 1))
88568 + {
88569 + os_free_mem(pAd, (PUCHAR)mpool);
88570 + return;
88571 + }
88572 +
88573 + // Update GTK to ASIC
88574 + // Update group key information to ASIC Shared Key Table
88575 + AsicAddSharedKeyEntry(pAd,
88576 + BSS0,
88577 + pAd->StaCfg.DefaultKeyId,
88578 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg,
88579 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key,
88580 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].TxMic,
88581 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].RxMic);
88582 +
88583 + // Update ASIC WCID attribute table and IVEIV table
88584 + RTMPAddWcidAttributeEntry(pAd,
88585 + BSS0,
88586 + pAd->StaCfg.DefaultKeyId,
88587 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg,
88588 + NULL);
88589 +
88590 + // init 802.3 header and Fill Packet
88591 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
88592 +
88593 + // Zero message 4 body
88594 + NdisZeroMemory(&Packet, sizeof(Packet));
88595 + Packet.ProVer = EAPOL_VER;
88596 + Packet.ProType = EAPOLKey;
88597 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE; // No data field
88598 +
88599 + //
88600 + // Message 4 as EAPOL-Key(0,1,0,0,0,P,0,0,MIC,0)
88601 + //
88602 + Packet.KeyDesc.Type = WPA2_KEY_DESC;
88603 +
88604 + // Key descriptor version and appropriate RSN IE
88605 + Packet.KeyDesc.KeyInfo.KeyDescVer = peerKeyInfo.KeyDescVer;
88606 +
88607 + // Update Key Length
88608 + Packet.KeyDesc.KeyLength[0] = pMsg3->KeyDesc.KeyLength[0];
88609 + Packet.KeyDesc.KeyLength[1] = pMsg3->KeyDesc.KeyLength[1];
88610 +
88611 + // Key Type PeerKey
88612 + Packet.KeyDesc.KeyInfo.KeyType = PAIRWISEKEY;
88613 +
88614 + // KeyMic field presented
88615 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
88616 + Packet.KeyDesc.KeyInfo.Secure = 1;
88617 +
88618 + // Convert to little-endian format.
88619 + *((USHORT *)&Packet.KeyDesc.KeyInfo) = cpu2le16(*((USHORT *)&Packet.KeyDesc.KeyInfo));
88620 +
88621 + // Key Replay count
88622 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pMsg3->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
88623 +
88624 + // Out buffer for transmitting message 4
88625 + MlmeAllocateMemory(pAd, (PUCHAR *)&pOutBuffer); // allocate memory
88626 + if(pOutBuffer == NULL)
88627 + {
88628 + os_free_mem(pAd, (PUCHAR)mpool);
88629 + return;
88630 + }
88631 +
88632 + // Prepare EAPOL frame for MIC calculation
88633 + // Be careful, only EAPOL frame is counted for MIC calculation
88634 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88635 + Packet.Body_Len[1] + 4, &Packet,
88636 + END_OF_ARGS);
88637 +
88638 + // Prepare and Fill MIC value
88639 + NdisZeroMemory(Mic, sizeof(Mic));
88640 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88641 + {
88642 + // AES
88643 + HMAC_SHA1(pOutBuffer, FrameLen, pAd->StaCfg.PTK, LEN_EAP_MICK, digest);
88644 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88645 + }
88646 + else
88647 + {
88648 + hmac_md5(pAd->StaCfg.PTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
88649 + }
88650 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
88651 +
88652 + // Update PTK
88653 + // Prepare pair-wise key information into shared key table
88654 + NdisZeroMemory(&pAd->SharedKey[BSS0][0], sizeof(CIPHER_KEY));
88655 + pAd->SharedKey[BSS0][0].KeyLen = LEN_TKIP_EK;
88656 + NdisMoveMemory(pAd->SharedKey[BSS0][0].Key, &pAd->StaCfg.PTK[32], LEN_TKIP_EK);
88657 + NdisMoveMemory(pAd->SharedKey[BSS0][0].RxMic, &pAd->StaCfg.PTK[48], LEN_TKIP_RXMICK);
88658 + NdisMoveMemory(pAd->SharedKey[BSS0][0].TxMic, &pAd->StaCfg.PTK[48+LEN_TKIP_RXMICK], LEN_TKIP_TXMICK);
88659 +
88660 + // Decide its ChiperAlg
88661 + if (pAd->StaCfg.PairCipher == Ndis802_11Encryption2Enabled)
88662 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_TKIP;
88663 + else if (pAd->StaCfg.PairCipher == Ndis802_11Encryption3Enabled)
88664 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_AES;
88665 + else
88666 + pAd->SharedKey[BSS0][0].CipherAlg = CIPHER_NONE;
88667 +
88668 + // Update these related information to MAC_TABLE_ENTRY
88669 + pEntry = &pAd->MacTab.Content[BSSID_WCID];
88670 + NdisMoveMemory(&pEntry->PairwiseKey.Key, &pAd->StaCfg.PTK[32], LEN_TKIP_EK);
88671 + NdisMoveMemory(&pEntry->PairwiseKey.RxMic, &pAd->StaCfg.PTK[48], LEN_TKIP_RXMICK);
88672 + NdisMoveMemory(&pEntry->PairwiseKey.TxMic, &pAd->StaCfg.PTK[48+LEN_TKIP_RXMICK], LEN_TKIP_TXMICK);
88673 + pEntry->PairwiseKey.CipherAlg = pAd->SharedKey[BSS0][0].CipherAlg;
88674 +
88675 + // Update pairwise key information to ASIC Shared Key Table
88676 + AsicAddSharedKeyEntry(pAd,
88677 + BSS0,
88678 + 0,
88679 + pAd->SharedKey[BSS0][0].CipherAlg,
88680 + pAd->SharedKey[BSS0][0].Key,
88681 + pAd->SharedKey[BSS0][0].TxMic,
88682 + pAd->SharedKey[BSS0][0].RxMic);
88683 +
88684 + // Update ASIC WCID attribute table and IVEIV table
88685 + RTMPAddWcidAttributeEntry(pAd,
88686 + BSS0,
88687 + 0,
88688 + pAd->SharedKey[BSS0][0].CipherAlg,
88689 + pEntry);
88690 +
88691 + // Make Transmitting frame
88692 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88693 + LENGTH_802_3, &Header802_3,
88694 + Packet.Body_Len[1] + 4, &Packet,
88695 + END_OF_ARGS);
88696 +
88697 +
88698 + // Copy frame to Tx ring and Send Message 4 to authenticator
88699 + RTMPToWirelessSta(pAd, Header802_3, LENGTH_802_3, (PUCHAR)&Packet, Packet.Body_Len[1] + 4, TRUE);
88700 +
88701 + // set 802.1x port control
88702 + STA_PORT_SECURED(pAd);
88703 +
88704 + // Indicate Connected for GUI
88705 + pAd->IndicateMediaState = NdisMediaStateConnected;
88706 +
88707 + MlmeFreeMemory(pAd, (PUCHAR)pOutBuffer);
88708 + os_free_mem(pAd, (PUCHAR)mpool);
88709 +
88710 +
88711 + // send wireless event - for set key done WPA2
88712 + if (pAd->CommonCfg.bWirelessEvent)
88713 + RTMPSendWirelessEvent(pAd, IW_SET_KEY_DONE_WPA2_EVENT_FLAG, pEntry->Addr, BSS0, 0);
88714 +
88715 + DBGPRINT(RT_DEBUG_ERROR, ("Wpa2PairMsg3Action <-----\n"));
88716 +
88717 +}
88718 +
88719 +/*
88720 + ========================================================================
88721 +
88722 + Routine Description:
88723 + Process Group key 2-way handshaking
88724 +
88725 + Arguments:
88726 + pAd Pointer to our adapter
88727 + Elem Message body
88728 +
88729 + Return Value:
88730 + None
88731 +
88732 + Note:
88733 +
88734 + ========================================================================
88735 +*/
88736 +VOID WpaGroupMsg1Action(
88737 + IN PRTMP_ADAPTER pAd,
88738 + IN MLME_QUEUE_ELEM *Elem)
88739 +
88740 +{
88741 + PUCHAR pOutBuffer = NULL;
88742 + UCHAR Header802_3[14];
88743 + ULONG FrameLen = 0;
88744 + EAPOL_PACKET Packet;
88745 + PEAPOL_PACKET pGroup;
88746 + UCHAR *mpool, *digest, *KEYDATA;
88747 + UCHAR Mic[16], OldMic[16];
88748 + UCHAR GTK[32], Key[32];
88749 + KEY_INFO peerKeyInfo;
88750 +
88751 + // allocate memory
88752 + os_alloc_mem(pAd, (PUCHAR *)&mpool, 1024);
88753 +
88754 + if(mpool == NULL)
88755 + return;
88756 +
88757 + // digest Len = 80.
88758 + digest = (UCHAR *) ROUND_UP(mpool, 4);
88759 + // KEYDATA Len = 512.
88760 + KEYDATA = (UCHAR *) ROUND_UP(digest + 80, 4);
88761 +
88762 + DBGPRINT(RT_DEBUG_TRACE, ("WpaGroupMsg1Action ----->\n"));
88763 +
88764 + // Process Group Message 1 frame. skip 802.11 header(24) & LLC_SNAP header(8)
88765 + pGroup = (PEAPOL_PACKET) &Elem->Msg[LENGTH_802_11 + LENGTH_802_1_H];
88766 +
88767 + NdisZeroMemory((PUCHAR)&peerKeyInfo, sizeof(peerKeyInfo));
88768 + NdisMoveMemory((PUCHAR)&peerKeyInfo, (PUCHAR)&pGroup->KeyDesc.KeyInfo, sizeof(KEY_INFO));
88769 +
88770 + *((USHORT*)&peerKeyInfo) = cpu2le16(*((USHORT*)&peerKeyInfo));
88771 +
88772 + // 0. Check cipher type match
88773 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled && (peerKeyInfo.KeyDescVer != 2))
88774 + {
88775 + os_free_mem(pAd, (PUCHAR)mpool);
88776 + return;
88777 + }
88778 + else if (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled && (peerKeyInfo.KeyDescVer != 1))
88779 + {
88780 + os_free_mem(pAd, (PUCHAR)mpool);
88781 + return;
88782 + }
88783 +
88784 + // 1. Verify Replay counter
88785 + // Check Replay Counter, it has to be larger than last one. No need to be exact one larger
88786 + if(RTMPCompareMemory(pGroup->KeyDesc.ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY) != 1)
88787 + {
88788 + os_free_mem(pAd, (PUCHAR)mpool);
88789 + return;
88790 + }
88791 +
88792 + // Update new replay counter
88793 + NdisMoveMemory(pAd->StaCfg.ReplayCounter, pGroup->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
88794 +
88795 + // 2. Verify MIC is valid
88796 + // Save the MIC and replace with zero
88797 + NdisMoveMemory(OldMic, pGroup->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
88798 + NdisZeroMemory(pGroup->KeyDesc.KeyMic, LEN_KEY_DESC_MIC);
88799 +
88800 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88801 + { // AES
88802 + HMAC_SHA1((PUCHAR) pGroup, pGroup->Body_Len[1] + 4, pAd->StaCfg.PTK, LEN_EAP_MICK, digest);
88803 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88804 + }
88805 + else
88806 + { // TKIP
88807 + hmac_md5(pAd->StaCfg.PTK, LEN_EAP_MICK, (PUCHAR) pGroup, pGroup->Body_Len[1] + 4, Mic);
88808 + }
88809 +
88810 + if(!NdisEqualMemory(OldMic, Mic, LEN_KEY_DESC_MIC))
88811 + {
88812 + DBGPRINT(RT_DEBUG_ERROR, (" MIC Different in group msg 1 of 2-way handshake!!!!!!!!!! \n"));
88813 + MlmeFreeMemory(pAd, (PUCHAR)mpool);
88814 + return;
88815 + }
88816 + else
88817 + DBGPRINT(RT_DEBUG_TRACE, (" MIC VALID in group msg 1 of 2-way handshake!!!!!!!!!! \n"));
88818 +
88819 +
88820 + // 3. Decrypt GTK from Key Data
88821 + if (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88822 + {
88823 + // Decrypt AES GTK
88824 + AES_GTK_KEY_UNWRAP(&pAd->StaCfg.PTK[16], KEYDATA, pGroup->KeyDesc.KeyDataLen[1], pGroup->KeyDesc.KeyData);
88825 + }
88826 + else // TKIP
88827 + {
88828 + INT i;
88829 +
88830 + // Decrypt TKIP GTK
88831 + // Construct 32 bytes RC4 Key
88832 + NdisMoveMemory(Key, pGroup->KeyDesc.KeyIv, 16);
88833 + NdisMoveMemory(&Key[16], &pAd->StaCfg.PTK[16], 16);
88834 + ARCFOUR_INIT(&pAd->PrivateInfo.WEPCONTEXT, Key, 32);
88835 + //discard first 256 bytes
88836 + for(i = 0; i < 256; i++)
88837 + ARCFOUR_BYTE(&pAd->PrivateInfo.WEPCONTEXT);
88838 + // Decrypt GTK. Becareful, there is no ICV to check the result is correct or not
88839 + ARCFOUR_DECRYPT(&pAd->PrivateInfo.WEPCONTEXT, KEYDATA, pGroup->KeyDesc.KeyData, pGroup->KeyDesc.KeyDataLen[1]);
88840 + }
88841 +
88842 + // Process decrypted key data material
88843 + // Parse keyData to handle KDE format for WPA2PSK
88844 + if (peerKeyInfo.EKD_DL)
88845 + {
88846 + if (!ParseKeyData(pAd, KEYDATA, pGroup->KeyDesc.KeyDataLen[1], 0))
88847 + {
88848 + os_free_mem(pAd, (PUCHAR)mpool);
88849 + return;
88850 + }
88851 + }
88852 + else // WPAPSK
88853 + {
88854 + // set key material, TxMic and RxMic for WPAPSK
88855 + NdisMoveMemory(GTK, KEYDATA, 32);
88856 + NdisMoveMemory(pAd->StaCfg.GTK, GTK, 32);
88857 + pAd->StaCfg.DefaultKeyId = peerKeyInfo.KeyIndex;
88858 +
88859 + // Prepare pair-wise key information into shared key table
88860 + NdisZeroMemory(&pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId], sizeof(CIPHER_KEY));
88861 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].KeyLen = LEN_TKIP_EK;
88862 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key, GTK, LEN_TKIP_EK);
88863 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].RxMic, &GTK[16], LEN_TKIP_RXMICK);
88864 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].TxMic, &GTK[24], LEN_TKIP_TXMICK);
88865 +
88866 + // Update Shared Key CipherAlg
88867 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_NONE;
88868 + if (pAd->StaCfg.GroupCipher == Ndis802_11Encryption2Enabled)
88869 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_TKIP;
88870 + else if (pAd->StaCfg.GroupCipher == Ndis802_11Encryption3Enabled)
88871 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_AES;
88872 +
88873 + //hex_dump("Group Key :", pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key, LEN_TKIP_EK);
88874 + }
88875 +
88876 + // Update group key information to ASIC Shared Key Table
88877 + AsicAddSharedKeyEntry(pAd,
88878 + BSS0,
88879 + pAd->StaCfg.DefaultKeyId,
88880 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg,
88881 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key,
88882 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].TxMic,
88883 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].RxMic);
88884 +
88885 + // Update ASIC WCID attribute table and IVEIV table
88886 + RTMPAddWcidAttributeEntry(pAd,
88887 + BSS0,
88888 + pAd->StaCfg.DefaultKeyId,
88889 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg,
88890 + NULL);
88891 +
88892 + // set 802.1x port control
88893 + STA_PORT_SECURED(pAd);
88894 +
88895 + // Indicate Connected for GUI
88896 + pAd->IndicateMediaState = NdisMediaStateConnected;
88897 +
88898 + // init header and Fill Packet
88899 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
88900 +
88901 + // Zero Group message 1 body
88902 + NdisZeroMemory(&Packet, sizeof(Packet));
88903 + Packet.ProVer = EAPOL_VER;
88904 + Packet.ProType = EAPOLKey;
88905 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE; // No data field
88906 +
88907 + //
88908 + // Group Message 2 as EAPOL-Key(1,0,0,0,G,0,0,MIC,0)
88909 + //
88910 + if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)
88911 + {
88912 + Packet.KeyDesc.Type = WPA2_KEY_DESC;
88913 + }
88914 + else
88915 + {
88916 + Packet.KeyDesc.Type = WPA1_KEY_DESC;
88917 + }
88918 +
88919 + // Key descriptor version and appropriate RSN IE
88920 + Packet.KeyDesc.KeyInfo.KeyDescVer = peerKeyInfo.KeyDescVer;
88921 +
88922 + // Update Key Length
88923 + Packet.KeyDesc.KeyLength[0] = pGroup->KeyDesc.KeyLength[0];
88924 + Packet.KeyDesc.KeyLength[1] = pGroup->KeyDesc.KeyLength[1];
88925 +
88926 + // Key Index as G-Msg 1
88927 + if(pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK)
88928 + Packet.KeyDesc.KeyInfo.KeyIndex = peerKeyInfo.KeyIndex;
88929 +
88930 + // Key Type Group key
88931 + Packet.KeyDesc.KeyInfo.KeyType = GROUPKEY;
88932 +
88933 + // KeyMic field presented
88934 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
88935 +
88936 + // Secure bit
88937 + Packet.KeyDesc.KeyInfo.Secure = 1;
88938 +
88939 + // Convert to little-endian format.
88940 + *((USHORT *)&Packet.KeyDesc.KeyInfo) = cpu2le16(*((USHORT *)&Packet.KeyDesc.KeyInfo));
88941 +
88942 + // Key Replay count
88943 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pGroup->KeyDesc.ReplayCounter, LEN_KEY_DESC_REPLAY);
88944 +
88945 + // Out buffer for transmitting group message 2
88946 + MlmeAllocateMemory(pAd, (PUCHAR *)&pOutBuffer); // allocate memory
88947 + if(pOutBuffer == NULL)
88948 + {
88949 + MlmeFreeMemory(pAd, (PUCHAR)mpool);
88950 + return;
88951 + }
88952 +
88953 + // Prepare EAPOL frame for MIC calculation
88954 + // Be careful, only EAPOL frame is counted for MIC calculation
88955 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88956 + Packet.Body_Len[1] + 4, &Packet,
88957 + END_OF_ARGS);
88958 +
88959 + // Prepare and Fill MIC value
88960 + NdisZeroMemory(Mic, sizeof(Mic));
88961 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
88962 + {
88963 + // AES
88964 + HMAC_SHA1(pOutBuffer, FrameLen, pAd->StaCfg.PTK, LEN_EAP_MICK, digest);
88965 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
88966 + }
88967 + else
88968 + {
88969 + hmac_md5(pAd->StaCfg.PTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
88970 + }
88971 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
88972 +
88973 +
88974 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
88975 + LENGTH_802_3, &Header802_3,
88976 + Packet.Body_Len[1] + 4, &Packet,
88977 + END_OF_ARGS);
88978 +
88979 +
88980 + // 5. Copy frame to Tx ring and prepare for encryption
88981 + RTMPToWirelessSta(pAd, Header802_3, LENGTH_802_3, (PUCHAR)&Packet, Packet.Body_Len[1] + 4, FALSE);
88982 +
88983 + // 6 Free allocated memory
88984 + MlmeFreeMemory(pAd, (PUCHAR)pOutBuffer);
88985 + os_free_mem(pAd, (PUCHAR)mpool);
88986 +
88987 + // send wireless event - for set key done WPA2
88988 + if (pAd->CommonCfg.bWirelessEvent)
88989 + RTMPSendWirelessEvent(pAd, IW_SET_KEY_DONE_WPA2_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
88990 +
88991 + DBGPRINT(RT_DEBUG_TRACE, ("WpaGroupMsg1Action <-----\n"));
88992 +}
88993 +
88994 +/*
88995 + ========================================================================
88996 +
88997 + Routine Description:
88998 + Init WPA MAC header
88999 +
89000 + Arguments:
89001 + pAd Pointer to our adapter
89002 +
89003 + Return Value:
89004 + None
89005 +
89006 + Note:
89007 +
89008 + ========================================================================
89009 +*/
89010 +VOID WpaMacHeaderInit(
89011 + IN PRTMP_ADAPTER pAd,
89012 + IN OUT PHEADER_802_11 pHdr80211,
89013 + IN UCHAR wep,
89014 + IN PUCHAR pAddr1)
89015 +{
89016 + NdisZeroMemory(pHdr80211, sizeof(HEADER_802_11));
89017 + pHdr80211->FC.Type = BTYPE_DATA;
89018 + pHdr80211->FC.ToDs = 1;
89019 + if (wep == 1)
89020 + pHdr80211->FC.Wep = 1;
89021 +
89022 + // Addr1: BSSID, Addr2: SA, Addr3: DA
89023 + COPY_MAC_ADDR(pHdr80211->Addr1, pAddr1);
89024 + COPY_MAC_ADDR(pHdr80211->Addr2, pAd->CurrentAddress);
89025 + COPY_MAC_ADDR(pHdr80211->Addr3, pAd->CommonCfg.Bssid);
89026 + pHdr80211->Sequence = pAd->Sequence;
89027 +}
89028 +
89029 +/*
89030 + ========================================================================
89031 +
89032 + Routine Description:
89033 + Copy frame from waiting queue into relative ring buffer and set
89034 + appropriate ASIC register to kick hardware encryption before really
89035 + sent out to air.
89036 +
89037 + Arguments:
89038 + pAd Pointer to our adapter
89039 + PNDIS_PACKET Pointer to outgoing Ndis frame
89040 + NumberOfFrag Number of fragment required
89041 +
89042 + Return Value:
89043 + None
89044 +
89045 + Note:
89046 +
89047 + ========================================================================
89048 +*/
89049 +VOID RTMPToWirelessSta(
89050 + IN PRTMP_ADAPTER pAd,
89051 + IN PUCHAR pHeader802_3,
89052 + IN UINT HdrLen,
89053 + IN PUCHAR pData,
89054 + IN UINT DataLen,
89055 + IN BOOLEAN is4wayFrame)
89056 +
89057 +{
89058 + NDIS_STATUS Status;
89059 + PNDIS_PACKET pPacket;
89060 + UCHAR Index;
89061 +
89062 + do
89063 + {
89064 + // 1. build a NDIS packet and call RTMPSendPacket();
89065 + // be careful about how/when to release this internal allocated NDIS PACKET buffer
89066 + Status = RTMPAllocateNdisPacket(pAd, &pPacket, pHeader802_3, HdrLen, pData, DataLen);
89067 + if (Status != NDIS_STATUS_SUCCESS)
89068 + break;
89069 +
89070 + if (is4wayFrame)
89071 + RTMP_SET_PACKET_CLEAR_EAP_FRAME(pPacket, 1);
89072 + else
89073 + RTMP_SET_PACKET_CLEAR_EAP_FRAME(pPacket, 0);
89074 +
89075 + // 2. send out the packet
89076 + Status = STASendPacket(pAd, pPacket);
89077 + if(Status == NDIS_STATUS_SUCCESS)
89078 + {
89079 + // Dequeue one frame from TxSwQueue0..3 queue and process it
89080 + // There are three place calling dequeue for TX ring.
89081 + // 1. Here, right after queueing the frame.
89082 + // 2. At the end of TxRingTxDone service routine.
89083 + // 3. Upon NDIS call RTMPSendPackets
89084 + if((!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_BSS_SCAN_IN_PROGRESS)) &&
89085 + (!RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RESET_IN_PROGRESS)))
89086 + {
89087 + for(Index = 0; Index < 5; Index ++)
89088 + if(pAd->TxSwQueue[Index].Number > 0)
89089 + RTMPDeQueuePacket(pAd, FALSE, Index, MAX_TX_PROCESS);
89090 + }
89091 + }
89092 + } while(FALSE);
89093 +
89094 +}
89095 +
89096 +/*
89097 + ========================================================================
89098 +
89099 + Routine Description:
89100 + Check Sanity RSN IE form AP
89101 +
89102 + Arguments:
89103 +
89104 + Return Value:
89105 +
89106 +
89107 + ========================================================================
89108 +*/
89109 +BOOLEAN CheckRSNIE(
89110 + IN PRTMP_ADAPTER pAd,
89111 + IN PUCHAR pData,
89112 + IN UCHAR DataLen,
89113 + OUT UCHAR *Offset)
89114 +{
89115 + PUCHAR pVIE;
89116 + UCHAR len;
89117 + PEID_STRUCT pEid;
89118 + BOOLEAN result = FALSE;
89119 +
89120 + pVIE = pData;
89121 + len = DataLen;
89122 + *Offset = 0;
89123 +
89124 + while (len > sizeof(RSNIE2))
89125 + {
89126 + pEid = (PEID_STRUCT) pVIE;
89127 + // WPA RSN IE
89128 + if ((pEid->Eid == IE_WPA) && (NdisEqualMemory(pEid->Octet, WPA_OUI, 4)))
89129 + {
89130 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA || pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) &&
89131 + (NdisEqualMemory(pVIE, pAd->MacTab.Content[BSSID_WCID].RSN_IE, pAd->MacTab.Content[BSSID_WCID].RSNIE_Len)) &&
89132 + (pAd->MacTab.Content[BSSID_WCID].RSNIE_Len == (pEid->Len + 2)))
89133 + {
89134 + DBGPRINT(RT_DEBUG_TRACE, ("CheckRSNIE ==> WPA/WPAPSK RSN IE matched in Msg 3, Length(%d) \n", (pEid->Len + 2)));
89135 + result = TRUE;
89136 + }
89137 +
89138 + *Offset += (pEid->Len + 2);
89139 + }
89140 + // WPA2 RSN IE
89141 + else if ((pEid->Eid == IE_RSN) && (NdisEqualMemory(pEid->Octet + 2, RSN_OUI, 3)))
89142 + {
89143 + if ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2 || pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK) &&
89144 + (NdisEqualMemory(pVIE, pAd->MacTab.Content[BSSID_WCID].RSN_IE, pAd->MacTab.Content[BSSID_WCID].RSNIE_Len)) &&
89145 + (pAd->MacTab.Content[BSSID_WCID].RSNIE_Len == (pEid->Len + 2)))
89146 + {
89147 + DBGPRINT(RT_DEBUG_TRACE, ("CheckRSNIE ==> WPA2/WPA2PSK RSN IE matched in Msg 3, Length(%d) \n", (pEid->Len + 2)));
89148 + result = TRUE;
89149 + }
89150 +
89151 + *Offset += (pEid->Len + 2);
89152 + }
89153 + else
89154 + {
89155 + break;
89156 + }
89157 +
89158 + pVIE += (pEid->Len + 2);
89159 + len -= (pEid->Len + 2);
89160 + }
89161 +
89162 + DBGPRINT(RT_DEBUG_TRACE, ("CheckRSNIE ==> skip_offset(%d) \n", *Offset));
89163 +
89164 + return result;
89165 +
89166 +}
89167 +
89168 +
89169 +/*
89170 + ========================================================================
89171 +
89172 + Routine Description:
89173 + Parse KEYDATA field. KEYDATA[] May contain 2 RSN IE and optionally GTK.
89174 + GTK is encaptulated in KDE format at p.83 802.11i D10
89175 +
89176 + Arguments:
89177 +
89178 + Return Value:
89179 +
89180 + Note:
89181 + 802.11i D10
89182 +
89183 + ========================================================================
89184 +*/
89185 +BOOLEAN ParseKeyData(
89186 + IN PRTMP_ADAPTER pAd,
89187 + IN PUCHAR pKeyData,
89188 + IN UCHAR KeyDataLen,
89189 + IN UCHAR bPairewise)
89190 +{
89191 + PKDE_ENCAP pKDE = NULL;
89192 + PUCHAR pMyKeyData = pKeyData;
89193 + UCHAR KeyDataLength = KeyDataLen;
89194 + UCHAR GTKLEN;
89195 + UCHAR skip_offset;
89196 +
89197 + // Verify The RSN IE contained in Pairewise-Msg 3 and skip it
89198 + if (bPairewise)
89199 + {
89200 + // Check RSN IE whether it is WPA2/WPA2PSK
89201 + if (!CheckRSNIE(pAd, pKeyData, KeyDataLen, &skip_offset))
89202 + {
89203 + DBGPRINT(RT_DEBUG_ERROR, ("ParseKeyData ==> WPA2/WPA2PSK RSN IE mismatched \n"));
89204 + hex_dump("Get KEYDATA :", pKeyData, KeyDataLen);
89205 + return FALSE;
89206 + }
89207 + else
89208 + {
89209 + // skip RSN IE
89210 + pMyKeyData += skip_offset;
89211 + KeyDataLength -= skip_offset;
89212 +
89213 + //DBGPRINT(RT_DEBUG_TRACE, ("ParseKeyData ==> WPA2/WPA2PSK RSN IE matched in Msg 3, Length(%d) \n", skip_offset));
89214 + }
89215 + }
89216 +
89217 + DBGPRINT(RT_DEBUG_TRACE,("ParseKeyData ==> KeyDataLength %d without RSN_IE \n", KeyDataLength));
89218 +
89219 + // Parse EKD format
89220 + if (KeyDataLength >= 8)
89221 + {
89222 + pKDE = (PKDE_ENCAP) pMyKeyData;
89223 + }
89224 + else
89225 + {
89226 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: KeyDataLength is too short \n"));
89227 + return FALSE;
89228 + }
89229 +
89230 +
89231 + // Sanity check - shared key index should not be 0
89232 + if (pKDE->GTKEncap.Kid == 0)
89233 + {
89234 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: GTK Key index zero \n"));
89235 + return FALSE;
89236 + }
89237 +
89238 + // Sanity check - KED length
89239 + if (KeyDataLength < (pKDE->Len + 2))
89240 + {
89241 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: The len from KDE is too short \n"));
89242 + return FALSE;
89243 + }
89244 +
89245 + // Get GTK length - refer to IEEE 802.11i-2004 p.82
89246 + GTKLEN = pKDE->Len -6;
89247 +
89248 + if (GTKLEN < LEN_AES_KEY)
89249 + {
89250 + DBGPRINT(RT_DEBUG_ERROR, ("ERROR: GTK Key length is too short (%d) \n", GTKLEN));
89251 + return FALSE;
89252 + }
89253 + else
89254 + DBGPRINT(RT_DEBUG_TRACE, ("GTK Key with KDE formet got index=%d, len=%d \n", pKDE->GTKEncap.Kid, GTKLEN));
89255 +
89256 + // Update GTK
89257 + // set key material, TxMic and RxMic for WPAPSK
89258 + NdisMoveMemory(pAd->StaCfg.GTK, pKDE->GTKEncap.GTK, 32);
89259 + pAd->StaCfg.DefaultKeyId = pKDE->GTKEncap.Kid;
89260 +
89261 + // Update shared key table
89262 + NdisZeroMemory(&pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId], sizeof(CIPHER_KEY));
89263 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].KeyLen = LEN_TKIP_EK;
89264 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].Key, pKDE->GTKEncap.GTK, LEN_TKIP_EK);
89265 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].RxMic, &pKDE->GTKEncap.GTK[16], LEN_TKIP_RXMICK);
89266 + NdisMoveMemory(pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].TxMic, &pKDE->GTKEncap.GTK[24], LEN_TKIP_TXMICK);
89267 +
89268 + // Update Shared Key CipherAlg
89269 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_NONE;
89270 + if (pAd->StaCfg.GroupCipher == Ndis802_11Encryption2Enabled)
89271 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_TKIP;
89272 + else if (pAd->StaCfg.GroupCipher == Ndis802_11Encryption3Enabled)
89273 + pAd->SharedKey[BSS0][pAd->StaCfg.DefaultKeyId].CipherAlg = CIPHER_AES;
89274 +
89275 + return TRUE;
89276 +
89277 +}
89278 +
89279 +/*
89280 + ========================================================================
89281 +
89282 + Routine Description:
89283 + Cisco CCKM PRF function
89284 +
89285 + Arguments:
89286 + key Cisco Base Transient Key (BTK)
89287 + key_len The key length of the BTK
89288 + data Ruquest Number(RN) + BSSID
89289 + data_len The length of the data
89290 + output Store for PTK(Pairwise transient keys)
89291 + len The length of the output
89292 + Return Value:
89293 + None
89294 +
89295 + Note:
89296 + 802.1i Annex F.9
89297 +
89298 + ========================================================================
89299 +*/
89300 +VOID CCKMPRF(
89301 + IN UCHAR *key,
89302 + IN INT key_len,
89303 + IN UCHAR *data,
89304 + IN INT data_len,
89305 + OUT UCHAR *output,
89306 + IN INT len)
89307 +{
89308 + INT i;
89309 + UCHAR input[1024];
89310 + INT currentindex = 0;
89311 + INT total_len;
89312 +
89313 + NdisMoveMemory(input, data, data_len);
89314 + total_len = data_len;
89315 + input[total_len] = 0;
89316 + total_len++;
89317 + for (i = 0; i < (len + 19) / 20; i++)
89318 + {
89319 + HMAC_SHA1(input, total_len, key, key_len, &output[currentindex]);
89320 + currentindex += 20;
89321 + input[total_len - 1]++;
89322 + }
89323 +}
89324 +
89325 +/*
89326 + ========================================================================
89327 +
89328 + Routine Description:
89329 + Process MIC error indication and record MIC error timer.
89330 +
89331 + Arguments:
89332 + pAd Pointer to our adapter
89333 + pWpaKey Pointer to the WPA key structure
89334 +
89335 + Return Value:
89336 + None
89337 +
89338 + IRQL = DISPATCH_LEVEL
89339 +
89340 + Note:
89341 +
89342 + ========================================================================
89343 +*/
89344 +VOID RTMPReportMicError(
89345 + IN PRTMP_ADAPTER pAd,
89346 + IN PCIPHER_KEY pWpaKey)
89347 +{
89348 + ULONG Now;
89349 + UCHAR unicastKey = (pWpaKey->Type == PAIRWISE_KEY ? 1:0);
89350 +
89351 + // Record Last MIC error time and count
89352 + Now = jiffies;
89353 + if (pAd->StaCfg.MicErrCnt == 0)
89354 + {
89355 + pAd->StaCfg.MicErrCnt++;
89356 + pAd->StaCfg.LastMicErrorTime = Now;
89357 + NdisZeroMemory(pAd->StaCfg.ReplayCounter, 8);
89358 + }
89359 + else if (pAd->StaCfg.MicErrCnt == 1)
89360 + {
89361 + if ((pAd->StaCfg.LastMicErrorTime + (60 * OS_HZ)) < Now)
89362 + {
89363 + // Update Last MIC error time, this did not violate two MIC errors within 60 seconds
89364 + pAd->StaCfg.LastMicErrorTime = Now;
89365 + }
89366 + else
89367 + {
89368 +
89369 + if (pAd->CommonCfg.bWirelessEvent)
89370 + RTMPSendWirelessEvent(pAd, IW_COUNTER_MEASURES_EVENT_FLAG, pAd->MacTab.Content[BSSID_WCID].Addr, BSS0, 0);
89371 +
89372 + pAd->StaCfg.LastMicErrorTime = Now;
89373 + // Violate MIC error counts, MIC countermeasures kicks in
89374 + pAd->StaCfg.MicErrCnt++;
89375 + }
89376 + }
89377 + else
89378 + {
89379 + // MIC error count >= 2
89380 + // This should not happen
89381 + ;
89382 + }
89383 + MlmeEnqueue(pAd,
89384 + MLME_CNTL_STATE_MACHINE,
89385 + OID_802_11_MIC_FAILURE_REPORT_FRAME,
89386 + 1,
89387 + &unicastKey);
89388 +
89389 + if (pAd->StaCfg.MicErrCnt == 2)
89390 + {
89391 + RTMPSetTimer(&pAd->StaCfg.WpaDisassocAndBlockAssocTimer, 100);
89392 + }
89393 +}
89394 +
89395 +
89396 +#ifdef WPA_SUPPLICANT_SUPPORT
89397 +#define LENGTH_EAP_H 4
89398 +// If the received frame is EAP-Packet ,find out its EAP-Code (Request(0x01), Response(0x02), Success(0x03), Failure(0x04)).
89399 +INT WpaCheckEapCode(
89400 + IN PRTMP_ADAPTER pAd,
89401 + IN PUCHAR pFrame,
89402 + IN USHORT FrameLen,
89403 + IN USHORT OffSet)
89404 +{
89405 +
89406 + PUCHAR pData;
89407 + INT result = 0;
89408 +
89409 + if( FrameLen < OffSet + LENGTH_EAPOL_H + LENGTH_EAP_H )
89410 + return result;
89411 +
89412 + pData = pFrame + OffSet; // skip offset bytes
89413 +
89414 + if(*(pData+1) == EAPPacket) // 802.1x header - Packet Type
89415 + {
89416 + result = *(pData+4); // EAP header - Code
89417 + }
89418 +
89419 + return result;
89420 +}
89421 +
89422 +VOID WpaSendMicFailureToWpaSupplicant(
89423 + IN PRTMP_ADAPTER pAd,
89424 + IN BOOLEAN bUnicast)
89425 +{
89426 + union iwreq_data wrqu;
89427 + char custom[IW_CUSTOM_MAX] = {0};
89428 +
89429 + sprintf(custom, "MLME-MICHAELMICFAILURE.indication");
89430 + if (bUnicast)
89431 + sprintf(custom, "%s unicast", custom);
89432 + wrqu.data.length = strlen(custom);
89433 + wireless_send_event(pAd->net_dev, IWEVCUSTOM, &wrqu, custom);
89434 +
89435 + return;
89436 +}
89437 +#endif // WPA_SUPPLICANT_SUPPORT //
89438 +
89439 +VOID WpaMicFailureReportFrame(
89440 + IN PRTMP_ADAPTER pAd,
89441 + IN MLME_QUEUE_ELEM *Elem)
89442 +{
89443 + PUCHAR pOutBuffer = NULL;
89444 + UCHAR Header802_3[14];
89445 + ULONG FrameLen = 0;
89446 + EAPOL_PACKET Packet;
89447 + UCHAR Mic[16];
89448 + BOOLEAN bUnicast;
89449 +
89450 + DBGPRINT(RT_DEBUG_TRACE, ("WpaMicFailureReportFrame ----->\n"));
89451 +
89452 + bUnicast = (Elem->Msg[0] == 1 ? TRUE:FALSE);
89453 + pAd->Sequence = ((pAd->Sequence) + 1) & (MAX_SEQ_NUMBER);
89454 +
89455 + // init 802.3 header and Fill Packet
89456 + MAKE_802_3_HEADER(Header802_3, pAd->CommonCfg.Bssid, pAd->CurrentAddress, EAPOL);
89457 +
89458 + NdisZeroMemory(&Packet, sizeof(Packet));
89459 + Packet.ProVer = EAPOL_VER;
89460 + Packet.ProType = EAPOLKey;
89461 +
89462 + Packet.KeyDesc.Type = WPA1_KEY_DESC;
89463 +
89464 + // Request field presented
89465 + Packet.KeyDesc.KeyInfo.Request = 1;
89466 +
89467 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
89468 + {
89469 + Packet.KeyDesc.KeyInfo.KeyDescVer = 2;
89470 + }
89471 + else // TKIP
89472 + {
89473 + Packet.KeyDesc.KeyInfo.KeyDescVer = 1;
89474 + }
89475 +
89476 + Packet.KeyDesc.KeyInfo.KeyType = (bUnicast ? PAIRWISEKEY : GROUPKEY);
89477 +
89478 + // KeyMic field presented
89479 + Packet.KeyDesc.KeyInfo.KeyMic = 1;
89480 +
89481 + // Error field presented
89482 + Packet.KeyDesc.KeyInfo.Error = 1;
89483 +
89484 + // Update packet length after decide Key data payload
89485 + Packet.Body_Len[1] = sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE;
89486 +
89487 + // Key Replay Count
89488 + NdisMoveMemory(Packet.KeyDesc.ReplayCounter, pAd->StaCfg.ReplayCounter, LEN_KEY_DESC_REPLAY);
89489 + inc_byte_array(pAd->StaCfg.ReplayCounter, 8);
89490 +
89491 + // Convert to little-endian format.
89492 + *((USHORT *)&Packet.KeyDesc.KeyInfo) = cpu2le16(*((USHORT *)&Packet.KeyDesc.KeyInfo));
89493 +
89494 +
89495 + MlmeAllocateMemory(pAd, (PUCHAR *)&pOutBuffer); // allocate memory
89496 + if(pOutBuffer == NULL)
89497 + {
89498 + return;
89499 + }
89500 +
89501 + // Prepare EAPOL frame for MIC calculation
89502 + // Be careful, only EAPOL frame is counted for MIC calculation
89503 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
89504 + Packet.Body_Len[1] + 4, &Packet,
89505 + END_OF_ARGS);
89506 +
89507 + // Prepare and Fill MIC value
89508 + NdisZeroMemory(Mic, sizeof(Mic));
89509 + if(pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled)
89510 + { // AES
89511 + UCHAR digest[20] = {0};
89512 + HMAC_SHA1(pOutBuffer, FrameLen, pAd->StaCfg.PTK, LEN_EAP_MICK, digest);
89513 + NdisMoveMemory(Mic, digest, LEN_KEY_DESC_MIC);
89514 + }
89515 + else
89516 + { // TKIP
89517 + hmac_md5(pAd->StaCfg.PTK, LEN_EAP_MICK, pOutBuffer, FrameLen, Mic);
89518 + }
89519 + NdisMoveMemory(Packet.KeyDesc.KeyMic, Mic, LEN_KEY_DESC_MIC);
89520 +
89521 + MakeOutgoingFrame(pOutBuffer, &FrameLen,
89522 + LENGTH_802_3, &Header802_3,
89523 + Packet.Body_Len[1] + 4, &Packet,
89524 + END_OF_ARGS);
89525 +
89526 + // opy frame to Tx ring and send MIC failure report frame to authenticator
89527 + RTMPToWirelessSta(pAd, Header802_3, LENGTH_802_3, (PUCHAR)&Packet, Packet.Body_Len[1] + 4, FALSE);
89528 +
89529 + MlmeFreeMemory(pAd, (PUCHAR)pOutBuffer);
89530 +
89531 + DBGPRINT(RT_DEBUG_TRACE, ("WpaMicFailureReportFrame <-----\n"));
89532 +}
89533 +
89534 +/** from wpa_supplicant
89535 + * inc_byte_array - Increment arbitrary length byte array by one
89536 + * @counter: Pointer to byte array
89537 + * @len: Length of the counter in bytes
89538 + *
89539 + * This function increments the last byte of the counter by one and continues
89540 + * rolling over to more significant bytes if the byte was incremented from
89541 + * 0xff to 0x00.
89542 + */
89543 +void inc_byte_array(UCHAR *counter, int len)
89544 +{
89545 + int pos = len - 1;
89546 + while (pos >= 0) {
89547 + counter[pos]++;
89548 + if (counter[pos] != 0)
89549 + break;
89550 + pos--;
89551 + }
89552 +}
89553 +
89554 +VOID WpaDisassocApAndBlockAssoc(
89555 + IN PVOID SystemSpecific1,
89556 + IN PVOID FunctionContext,
89557 + IN PVOID SystemSpecific2,
89558 + IN PVOID SystemSpecific3)
89559 +{
89560 + RTMP_ADAPTER *pAd = (PRTMP_ADAPTER)FunctionContext;
89561 + MLME_DISASSOC_REQ_STRUCT DisassocReq;
89562 +
89563 + // disassoc from current AP first
89564 + DBGPRINT(RT_DEBUG_TRACE, ("RTMPReportMicError - disassociate with current AP after sending second continuous EAPOL frame\n"));
89565 + DisassocParmFill(pAd, &DisassocReq, pAd->CommonCfg.Bssid, REASON_MIC_FAILURE);
89566 + MlmeEnqueue(pAd, ASSOC_STATE_MACHINE, MT2_MLME_DISASSOC_REQ, sizeof(MLME_DISASSOC_REQ_STRUCT), &DisassocReq);
89567 +
89568 + pAd->Mlme.CntlMachine.CurrState = CNTL_WAIT_DISASSOC;
89569 + pAd->StaCfg.bBlockAssoc = TRUE;
89570 +}
89571 +
89572 --- /dev/null
89573 +++ b/drivers/staging/rt2860/TODO
89574 @@ -0,0 +1,17 @@
89575 +I'm hesitant to add a TODO file here, as the wireless developers would
89576 +really have people help them out on the "clean" rt2860 driver that can
89577 +be found at the rt2860.sf.net site.
89578 +
89579 +But, if you wish to clean up this driver instead, here's a short list of
89580 +things that need to be done to get it into a more mergable shape:
89581 +
89582 +TODO:
89583 + - checkpatch.pl clean
89584 + - sparse clean
89585 + - port to in-kernel 80211 stack
89586 + - remove reading from /etc/ config files
89587 + - review by the wireless developer community
89588 +
89589 +Please send any patches or complaints about this driver to Greg
89590 +Kroah-Hartman <greg@kroah.com> and don't bother the upstream wireless
89591 +kernel developers about it, they want nothing to do with it.
89592 --- /dev/null
89593 +++ b/drivers/staging/rt2860/wpa.h
89594 @@ -0,0 +1,356 @@
89595 +/*
89596 + *************************************************************************
89597 + * Ralink Tech Inc.
89598 + * 5F., No.36, Taiyuan St., Jhubei City,
89599 + * Hsinchu County 302,
89600 + * Taiwan, R.O.C.
89601 + *
89602 + * (c) Copyright 2002-2007, Ralink Technology, Inc.
89603 + *
89604 + * This program is free software; you can redistribute it and/or modify *
89605 + * it under the terms of the GNU General Public License as published by *
89606 + * the Free Software Foundation; either version 2 of the License, or *
89607 + * (at your option) any later version. *
89608 + * *
89609 + * This program is distributed in the hope that it will be useful, *
89610 + * but WITHOUT ANY WARRANTY; without even the implied warranty of *
89611 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
89612 + * GNU General Public License for more details. *
89613 + * *
89614 + * You should have received a copy of the GNU General Public License *
89615 + * along with this program; if not, write to the *
89616 + * Free Software Foundation, Inc., *
89617 + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
89618 + * *
89619 + *************************************************************************
89620 +
89621 + Module Name:
89622 + wpa.h
89623 +
89624 + Abstract:
89625 +
89626 + Revision History:
89627 + Who When What
89628 + -------- ---------- ----------------------------------------------
89629 + Name Date Modification logs
89630 +*/
89631 +
89632 +#ifndef __WPA_H__
89633 +#define __WPA_H__
89634 +
89635 +// EAPOL Key descripter frame format related length
89636 +#define LEN_KEY_DESC_NONCE 32
89637 +#define LEN_KEY_DESC_IV 16
89638 +#define LEN_KEY_DESC_RSC 8
89639 +#define LEN_KEY_DESC_ID 8
89640 +#define LEN_KEY_DESC_REPLAY 8
89641 +#define LEN_KEY_DESC_MIC 16
89642 +
89643 +// The length is the EAPoL-Key frame except key data field.
89644 +// Please refer to 802.11i-2004 ,Figure 43u in p.78
89645 +#define LEN_EAPOL_KEY_MSG (sizeof(KEY_DESCRIPTER) - MAX_LEN_OF_RSNIE)
89646 +
89647 +// EAP Code Type.
89648 +#define EAP_CODE_REQUEST 1
89649 +#define EAP_CODE_RESPONSE 2
89650 +#define EAP_CODE_SUCCESS 3
89651 +#define EAP_CODE_FAILURE 4
89652 +
89653 +// EAPOL frame Protocol Version
89654 +#define EAPOL_VER 1
89655 +#define EAPOL_VER2 2
89656 +
89657 +// EAPOL-KEY Descriptor Type
89658 +#define WPA1_KEY_DESC 0xfe
89659 +#define WPA2_KEY_DESC 0x02
89660 +
89661 +// Key Descriptor Version of Key Information
89662 +#define DESC_TYPE_TKIP 1
89663 +#define DESC_TYPE_AES 2
89664 +#define DESC_TYPE_MESH 3
89665 +
89666 +#define LEN_MSG1_2WAY 0x7f
89667 +#define MAX_LEN_OF_EAP_HS 256
89668 +
89669 +#define LEN_MASTER_KEY 32
89670 +
89671 +// EAPOL EK, MK
89672 +#define LEN_EAP_EK 16
89673 +#define LEN_EAP_MICK 16
89674 +#define LEN_EAP_KEY ((LEN_EAP_EK)+(LEN_EAP_MICK))
89675 +// TKIP key related
89676 +#define LEN_PMKID 16
89677 +#define LEN_TKIP_EK 16
89678 +#define LEN_TKIP_RXMICK 8
89679 +#define LEN_TKIP_TXMICK 8
89680 +#define LEN_AES_EK 16
89681 +#define LEN_AES_KEY LEN_AES_EK
89682 +#define LEN_TKIP_KEY ((LEN_TKIP_EK)+(LEN_TKIP_RXMICK)+(LEN_TKIP_TXMICK))
89683 +#define TKIP_AP_TXMICK_OFFSET ((LEN_EAP_KEY)+(LEN_TKIP_EK))
89684 +#define TKIP_AP_RXMICK_OFFSET (TKIP_AP_TXMICK_OFFSET+LEN_TKIP_TXMICK)
89685 +#define TKIP_GTK_LENGTH ((LEN_TKIP_EK)+(LEN_TKIP_RXMICK)+(LEN_TKIP_TXMICK))
89686 +#define LEN_PTK ((LEN_EAP_KEY)+(LEN_TKIP_KEY))
89687 +
89688 +// RSN IE Length definition
89689 +#define MAX_LEN_OF_RSNIE 90
89690 +#define MIN_LEN_OF_RSNIE 8
89691 +
89692 +//EAP Packet Type
89693 +#define EAPPacket 0
89694 +#define EAPOLStart 1
89695 +#define EAPOLLogoff 2
89696 +#define EAPOLKey 3
89697 +#define EAPOLASFAlert 4
89698 +#define EAPTtypeMax 5
89699 +
89700 +#define EAPOL_MSG_INVALID 0
89701 +#define EAPOL_PAIR_MSG_1 1
89702 +#define EAPOL_PAIR_MSG_2 2
89703 +#define EAPOL_PAIR_MSG_3 3
89704 +#define EAPOL_PAIR_MSG_4 4
89705 +#define EAPOL_GROUP_MSG_1 5
89706 +#define EAPOL_GROUP_MSG_2 6
89707 +
89708 +#define PAIRWISEKEY 1
89709 +#define GROUPKEY 0
89710 +
89711 +// Retry timer counter initial value
89712 +#define PEER_MSG1_RETRY_TIMER_CTR 0
89713 +#define PEER_MSG3_RETRY_TIMER_CTR 10
89714 +#define GROUP_MSG1_RETRY_TIMER_CTR 20
89715 +
89716 +
89717 +#define EAPOL_START_DISABLE 0
89718 +#define EAPOL_START_PSK 1
89719 +#define EAPOL_START_1X 2
89720 +
89721 +#define MIX_CIPHER_WPA_TKIP_ON(x) (((x) & 0x08) != 0)
89722 +#define MIX_CIPHER_WPA_AES_ON(x) (((x) & 0x04) != 0)
89723 +#define MIX_CIPHER_WPA2_TKIP_ON(x) (((x) & 0x02) != 0)
89724 +#define MIX_CIPHER_WPA2_AES_ON(x) (((x) & 0x01) != 0)
89725 +
89726 +#define ROUND_UP(__x, __y) \
89727 + (((ULONG)((__x)+((__y)-1))) & ((ULONG)~((__y)-1)))
89728 +
89729 +#define ADD_ONE_To_64BIT_VAR(_V) \
89730 +{ \
89731 + UCHAR cnt = LEN_KEY_DESC_REPLAY; \
89732 + do \
89733 + { \
89734 + cnt--; \
89735 + _V[cnt]++; \
89736 + if (cnt == 0) \
89737 + break; \
89738 + }while (_V[cnt] == 0); \
89739 +}
89740 +
89741 +#define IS_WPA_CAPABILITY(a) (((a) >= Ndis802_11AuthModeWPA) && ((a) <= Ndis802_11AuthModeWPA1PSKWPA2PSK))
89742 +
89743 +// EAPOL Key Information definition within Key descriptor format
89744 +typedef struct PACKED _KEY_INFO
89745 +{
89746 +#ifdef RT_BIG_ENDIAN
89747 + UCHAR KeyAck:1;
89748 + UCHAR Install:1;
89749 + UCHAR KeyIndex:2;
89750 + UCHAR KeyType:1;
89751 + UCHAR KeyDescVer:3;
89752 + UCHAR Rsvd:3;
89753 + UCHAR EKD_DL:1; // EKD for AP; DL for STA
89754 + UCHAR Request:1;
89755 + UCHAR Error:1;
89756 + UCHAR Secure:1;
89757 + UCHAR KeyMic:1;
89758 +#else
89759 + UCHAR KeyMic:1;
89760 + UCHAR Secure:1;
89761 + UCHAR Error:1;
89762 + UCHAR Request:1;
89763 + UCHAR EKD_DL:1; // EKD for AP; DL for STA
89764 + UCHAR Rsvd:3;
89765 + UCHAR KeyDescVer:3;
89766 + UCHAR KeyType:1;
89767 + UCHAR KeyIndex:2;
89768 + UCHAR Install:1;
89769 + UCHAR KeyAck:1;
89770 +#endif
89771 +} KEY_INFO, *PKEY_INFO;
89772 +
89773 +// EAPOL Key descriptor format
89774 +typedef struct PACKED _KEY_DESCRIPTER
89775 +{
89776 + UCHAR Type;
89777 + KEY_INFO KeyInfo;
89778 + UCHAR KeyLength[2];
89779 + UCHAR ReplayCounter[LEN_KEY_DESC_REPLAY];
89780 + UCHAR KeyNonce[LEN_KEY_DESC_NONCE];
89781 + UCHAR KeyIv[LEN_KEY_DESC_IV];
89782 + UCHAR KeyRsc[LEN_KEY_DESC_RSC];
89783 + UCHAR KeyId[LEN_KEY_DESC_ID];
89784 + UCHAR KeyMic[LEN_KEY_DESC_MIC];
89785 + UCHAR KeyDataLen[2];
89786 + UCHAR KeyData[MAX_LEN_OF_RSNIE];
89787 +} KEY_DESCRIPTER, *PKEY_DESCRIPTER;
89788 +
89789 +typedef struct PACKED _EAPOL_PACKET
89790 +{
89791 + UCHAR ProVer;
89792 + UCHAR ProType;
89793 + UCHAR Body_Len[2];
89794 + KEY_DESCRIPTER KeyDesc;
89795 +} EAPOL_PACKET, *PEAPOL_PACKET;
89796 +
89797 +//802.11i D10 page 83
89798 +typedef struct PACKED _GTK_ENCAP
89799 +{
89800 +#ifndef RT_BIG_ENDIAN
89801 + UCHAR Kid:2;
89802 + UCHAR tx:1;
89803 + UCHAR rsv:5;
89804 + UCHAR rsv1;
89805 +#else
89806 + UCHAR rsv:5;
89807 + UCHAR tx:1;
89808 + UCHAR Kid:2;
89809 + UCHAR rsv1;
89810 +#endif
89811 + UCHAR GTK[TKIP_GTK_LENGTH];
89812 +} GTK_ENCAP, *PGTK_ENCAP;
89813 +
89814 +typedef struct PACKED _KDE_ENCAP
89815 +{
89816 + UCHAR Type;
89817 + UCHAR Len;
89818 + UCHAR OUI[3];
89819 + UCHAR DataType;
89820 + GTK_ENCAP GTKEncap;
89821 +} KDE_ENCAP, *PKDE_ENCAP;
89822 +
89823 +// For WPA1
89824 +typedef struct PACKED _RSNIE {
89825 + UCHAR oui[4];
89826 + USHORT version;
89827 + UCHAR mcast[4];
89828 + USHORT ucount;
89829 + struct PACKED {
89830 + UCHAR oui[4];
89831 + }ucast[1];
89832 +} RSNIE, *PRSNIE;
89833 +
89834 +// For WPA2
89835 +typedef struct PACKED _RSNIE2 {
89836 + USHORT version;
89837 + UCHAR mcast[4];
89838 + USHORT ucount;
89839 + struct PACKED {
89840 + UCHAR oui[4];
89841 + }ucast[1];
89842 +} RSNIE2, *PRSNIE2;
89843 +
89844 +// AKM Suite
89845 +typedef struct PACKED _RSNIE_AUTH {
89846 + USHORT acount;
89847 + struct PACKED {
89848 + UCHAR oui[4];
89849 + }auth[1];
89850 +} RSNIE_AUTH,*PRSNIE_AUTH;
89851 +
89852 +typedef union PACKED _RSN_CAPABILITIES {
89853 + struct PACKED {
89854 +#ifdef RT_BIG_ENDIAN
89855 + USHORT Rsvd:10;
89856 + USHORT GTKSA_R_Counter:2;
89857 + USHORT PTKSA_R_Counter:2;
89858 + USHORT No_Pairwise:1;
89859 + USHORT PreAuth:1;
89860 +#else
89861 + USHORT PreAuth:1;
89862 + USHORT No_Pairwise:1;
89863 + USHORT PTKSA_R_Counter:2;
89864 + USHORT GTKSA_R_Counter:2;
89865 + USHORT Rsvd:10;
89866 +#endif
89867 + } field;
89868 + USHORT word;
89869 +} RSN_CAPABILITIES, *PRSN_CAPABILITIES;
89870 +
89871 +typedef struct PACKED _EAP_HDR {
89872 + UCHAR ProVer;
89873 + UCHAR ProType;
89874 + UCHAR Body_Len[2];
89875 + UCHAR code;
89876 + UCHAR identifier;
89877 + UCHAR length[2]; // including code and identifier, followed by length-2 octets of data
89878 +} EAP_HDR, *PEAP_HDR;
89879 +
89880 +// For supplicant state machine states. 802.11i Draft 4.1, p. 97
89881 +// We simplified it
89882 +typedef enum _WpaState
89883 +{
89884 + SS_NOTUSE, // 0
89885 + SS_START, // 1
89886 + SS_WAIT_MSG_3, // 2
89887 + SS_WAIT_GROUP, // 3
89888 + SS_FINISH, // 4
89889 + SS_KEYUPDATE, // 5
89890 +} WPA_STATE;
89891 +
89892 +//
89893 +// The definition of the cipher combination
89894 +//
89895 +// bit3 bit2 bit1 bit0
89896 +// +------------+------------+
89897 +// | WPA | WPA2 |
89898 +// +------+-----+------+-----+
89899 +// | TKIP | AES | TKIP | AES |
89900 +// | 0 | 1 | 1 | 0 | -> 0x06
89901 +// | 0 | 1 | 1 | 1 | -> 0x07
89902 +// | 1 | 0 | 0 | 1 | -> 0x09
89903 +// | 1 | 0 | 1 | 1 | -> 0x0B
89904 +// | 1 | 1 | 0 | 1 | -> 0x0D
89905 +// | 1 | 1 | 1 | 0 | -> 0x0E
89906 +// | 1 | 1 | 1 | 1 | -> 0x0F
89907 +// +------+-----+------+-----+
89908 +//
89909 +typedef enum _WpaMixPairCipher
89910 +{
89911 + MIX_CIPHER_NOTUSE = 0x00,
89912 + WPA_NONE_WPA2_TKIPAES = 0x03, // WPA2-TKIPAES
89913 + WPA_AES_WPA2_TKIP = 0x06,
89914 + WPA_AES_WPA2_TKIPAES = 0x07,
89915 + WPA_TKIP_WPA2_AES = 0x09,
89916 + WPA_TKIP_WPA2_TKIPAES = 0x0B,
89917 + WPA_TKIPAES_WPA2_NONE = 0x0C, // WPA-TKIPAES
89918 + WPA_TKIPAES_WPA2_AES = 0x0D,
89919 + WPA_TKIPAES_WPA2_TKIP = 0x0E,
89920 + WPA_TKIPAES_WPA2_TKIPAES = 0x0F,
89921 +} WPA_MIX_PAIR_CIPHER;
89922 +
89923 +typedef struct PACKED _RSN_IE_HEADER_STRUCT {
89924 + UCHAR Eid;
89925 + UCHAR Length;
89926 + USHORT Version; // Little endian format
89927 +} RSN_IE_HEADER_STRUCT, *PRSN_IE_HEADER_STRUCT;
89928 +
89929 +// Cipher suite selector types
89930 +typedef struct PACKED _CIPHER_SUITE_STRUCT {
89931 + UCHAR Oui[3];
89932 + UCHAR Type;
89933 +} CIPHER_SUITE_STRUCT, *PCIPHER_SUITE_STRUCT;
89934 +
89935 +// Authentication and Key Management suite selector
89936 +typedef struct PACKED _AKM_SUITE_STRUCT {
89937 + UCHAR Oui[3];
89938 + UCHAR Type;
89939 +} AKM_SUITE_STRUCT, *PAKM_SUITE_STRUCT;
89940 +
89941 +// RSN capability
89942 +typedef struct PACKED _RSN_CAPABILITY {
89943 + USHORT Rsv:10;
89944 + USHORT GTKSAReplayCnt:2;
89945 + USHORT PTKSAReplayCnt:2;
89946 + USHORT NoPairwise:1;
89947 + USHORT PreAuth:1;
89948 +} RSN_CAPABILITY, *PRSN_CAPABILITY;
89949 +
89950 +#endif